diff --git a/include/libweston/libweston.h b/include/libweston/libweston.h index f881b94f..09bb4b4c 100644 --- a/include/libweston/libweston.h +++ b/include/libweston/libweston.h @@ -283,6 +283,26 @@ struct weston_head { enum weston_hdcp_protection current_protection; }; +/** Output properties derived from its color characteristics and profile + * + * These are constructed by a color manager. + * + * A weston_output_color_outcome owns (a reference to) everything it contains. + * + * \ingroup output + * \internal + */ +struct weston_output_color_outcome { + /** sRGB to output color space transformation */ + struct weston_color_transform *from_sRGB_to_output; + + /** sRGB to blending color space transformation */ + struct weston_color_transform *from_sRGB_to_blend; + + /** Blending to output color space transformation */ + struct weston_color_transform *from_blend_to_output; +}; + /** Content producer for heads * * \rst @@ -392,12 +412,14 @@ struct weston_output { int scale; struct weston_color_profile *color_profile; - struct weston_color_transform *from_sRGB_to_output; - struct weston_color_transform *from_sRGB_to_blend; - struct weston_color_transform *from_blend_to_output; bool from_blend_to_output_by_backend; enum weston_eotf_mode eotf_mode; + /* XXX: temporary allocation to be removed in the next commit */ + struct weston_output_color_outcome colorout_; + + struct weston_output_color_outcome *color_outcome; + int (*enable)(struct weston_output *output); int (*disable)(struct weston_output *output); diff --git a/libweston/color.h b/libweston/color.h index 7c1335fa..b5064587 100644 --- a/libweston/color.h +++ b/libweston/color.h @@ -385,4 +385,7 @@ weston_eotf_mode_to_str(enum weston_eotf_mode e); char * weston_eotf_mask_to_str(uint32_t eotf_mask); +void +weston_output_color_outcome_destroy(struct weston_output_color_outcome **pco); + #endif /* WESTON_COLOR_H */ diff --git a/libweston/compositor.c b/libweston/compositor.c index b7944b84..8c77bacf 100644 --- a/libweston/compositor.c +++ b/libweston/compositor.c @@ -6463,15 +6463,24 @@ weston_output_transform_coordinate(struct weston_output *output, *y = p.f[1] / p.f[3]; } -static void -weston_output_reset_color_transforms(struct weston_output *output) +WL_EXPORT void +weston_output_color_outcome_destroy(struct weston_output_color_outcome **pco) { - weston_color_transform_unref(output->from_sRGB_to_output); - output->from_sRGB_to_output = NULL; - weston_color_transform_unref(output->from_sRGB_to_blend); - output->from_sRGB_to_blend = NULL; - weston_color_transform_unref(output->from_blend_to_output); - output->from_blend_to_output = NULL; + struct weston_output_color_outcome *co = *pco; + + if (!co) + return; + + weston_color_transform_unref(co->from_sRGB_to_output); + co->from_sRGB_to_output = NULL; + weston_color_transform_unref(co->from_sRGB_to_blend); + co->from_sRGB_to_blend = NULL; + weston_color_transform_unref(co->from_blend_to_output); + co->from_blend_to_output = NULL; + + /* XXX: added in the next commit */ + /* free(co); */ + *pco = NULL; } static bool @@ -6498,11 +6507,15 @@ weston_output_set_color_transforms(struct weston_output *output) return false; } - weston_output_reset_color_transforms(output); - output->from_blend_to_output = blend_to_output; + weston_output_color_outcome_destroy(&output->color_outcome); + + /* XXX: temporary allocation to be removed in the next commit */ + output->color_outcome = &output->colorout_; + + output->color_outcome->from_blend_to_output = blend_to_output; + output->color_outcome->from_sRGB_to_output = sRGB_to_output; + output->color_outcome->from_sRGB_to_blend = sRGB_to_blend; output->from_blend_to_output_by_backend = false; - output->from_sRGB_to_output = sRGB_to_output; - output->from_sRGB_to_blend = sRGB_to_blend; weston_log("Output '%s' using color profile: %s\n", output->name, weston_color_profile_get_description(output->color_profile)); @@ -6567,7 +6580,7 @@ weston_compositor_remove_output(struct weston_output *output) weston_view_assign_output(view); } - weston_output_reset_color_transforms(output); + weston_output_color_outcome_destroy(&output->color_outcome); weston_presentation_feedback_discard_list(&output->feedback_list); @@ -6986,7 +6999,7 @@ weston_output_enable(struct weston_output *output) */ if (output->enable(output) < 0) { weston_log("Enabling output \"%s\" failed.\n", output->name); - weston_output_reset_color_transforms(output); + weston_output_color_outcome_destroy(&output->color_outcome); return -1; } @@ -7146,6 +7159,7 @@ weston_output_release(struct weston_output *output) weston_compositor_remove_output(output); weston_color_profile_unref(output->color_profile); + assert(output->color_outcome == NULL); pixman_region32_fini(&output->region); wl_list_remove(&output->link); diff --git a/libweston/pixman-renderer.c b/libweston/pixman-renderer.c index d93e7ed2..17e5d17f 100644 --- a/libweston/pixman-renderer.c +++ b/libweston/pixman-renderer.c @@ -582,7 +582,7 @@ pixman_renderer_repaint_output(struct weston_output *output, pixman_region32_t hw_damage; assert(output->from_blend_to_output_by_backend || - output->from_blend_to_output == NULL); + output->color_outcome->from_blend_to_output == NULL); if (!po->hw_buffer) { po->hw_extra_damage = NULL; diff --git a/libweston/renderer-gl/gl-renderer.c b/libweston/renderer-gl/gl-renderer.c index b29b4ad3..201bc7fa 100644 --- a/libweston/renderer-gl/gl-renderer.c +++ b/libweston/renderer-gl/gl-renderer.c @@ -740,6 +740,7 @@ triangle_fan_debug(struct gl_renderer *gr, static int color_idx = 0; struct gl_shader_config alt; const GLfloat *col; + struct weston_color_transform *ctransf; static const GLfloat color[][4] = { { 1.0, 0.0, 0.0, 1.0 }, { 0.0, 1.0, 0.0, 1.0 }, @@ -758,8 +759,8 @@ triangle_fan_debug(struct gl_renderer *gr, .unicolor = { col[0], col[1], col[2], col[3] }, }; - if (!gl_shader_config_set_color_transform(&alt, - output->from_sRGB_to_blend)) { + ctransf = output->color_outcome->from_sRGB_to_blend; + if (!gl_shader_config_set_color_transform(&alt, ctransf)) { weston_log("GL-renderer: %s failed to generate a color transformation.\n", __func__); return; @@ -932,6 +933,7 @@ static void censor_override(struct gl_shader_config *sconf, struct weston_output *output) { + struct weston_color_transform *ctransf; struct gl_shader_config alt = { .req = { .variant = SHADER_VARIANT_SOLID, @@ -942,8 +944,8 @@ censor_override(struct gl_shader_config *sconf, .unicolor = { 0.40, 0.0, 0.0, 1.0 }, }; - if (!gl_shader_config_set_color_transform(&alt, - output->from_sRGB_to_blend)) { + ctransf = output->color_outcome->from_sRGB_to_blend; + if (!gl_shader_config_set_color_transform(&alt, ctransf)) { weston_log("GL-renderer: %s failed to generate a color transformation.\n", __func__); } @@ -1307,6 +1309,7 @@ draw_output_borders(struct weston_output *output, }, .view_alpha = 1.0f, }; + struct weston_color_transform *ctransf; struct gl_output_state *go = get_output_state(output); struct gl_renderer *gr = get_renderer(output->compositor); struct gl_border_image *top, *bottom, *left, *right; @@ -1315,7 +1318,8 @@ draw_output_borders(struct weston_output *output, if (border_status == BORDER_STATUS_CLEAN) return; /* Clean. Nothing to do. */ - if (!gl_shader_config_set_color_transform(&sconf, output->from_sRGB_to_output)) { + ctransf = output->color_outcome->from_sRGB_to_output; + if (!gl_shader_config_set_color_transform(&sconf, ctransf)) { weston_log("GL-renderer: %s failed to generate a color transformation.\n", __func__); return; } @@ -1550,13 +1554,15 @@ blit_shadow_to_output(struct weston_output *output, struct gl_renderer *gr = get_renderer(output->compositor); double width = output->current_mode->width; double height = output->current_mode->height; + struct weston_color_transform *ctransf; pixman_box32_t *rects; int n_rects; int i; pixman_region32_t translated_damage; GLfloat verts[4 * 2]; - if (!gl_shader_config_set_color_transform(&sconf, output->from_blend_to_output)) { + ctransf = output->color_outcome->from_blend_to_output; + if (!gl_shader_config_set_color_transform(&sconf, ctransf)) { weston_log("GL-renderer: %s failed to generate a color transformation.\n", __func__); return; } @@ -1624,7 +1630,8 @@ gl_renderer_repaint_output(struct weston_output *output, struct weston_paint_node *pnode; assert(output->from_blend_to_output_by_backend || - output->from_blend_to_output == NULL || shadow_exists(go)); + output->color_outcome->from_blend_to_output == NULL || + shadow_exists(go)); if (use_output(output) < 0) return; @@ -3439,7 +3446,7 @@ gl_renderer_output_create(struct weston_output *output, go->begin_render_sync = EGL_NO_SYNC_KHR; go->end_render_sync = EGL_NO_SYNC_KHR; - if ((output->from_blend_to_output != NULL && + if ((output->color_outcome->from_blend_to_output != NULL && output->from_blend_to_output_by_backend == false) || quirks->gl_force_full_redraw_of_shadow_fb) { assert(gr->gl_supports_color_transforms);