color: update color-management protocol to wp-v1

For a list of changes that got squashed into this commit see
https://gitlab.freedesktop.org/rmader/weston/-/commits/color-management-protocol-wp-v1-bkp

Co-authored-by: Leandro Ribeiro <leandro.ribeiro@collabora.com>
Signed-off-by: Robert Mader <robert.mader@collabora.com>
Signed-off-by: Leandro Ribeiro <leandro.ribeiro@collabora.com>
This commit is contained in:
Robert Mader 2025-02-26 12:48:53 +01:00 committed by Leandro Ribeiro
parent 6d9c42a7d2
commit 9124a98aec
16 changed files with 947 additions and 2114 deletions

View file

@ -52,16 +52,16 @@ struct color {
struct widget *parent_widget;
struct widget *widget;
struct xx_color_manager_v4 *color_manager;
struct xx_color_management_surface_v4 *color_surface;
struct wp_color_manager_v1 *color_manager;
struct wp_color_management_surface_v1 *color_surface;
struct wp_single_pixel_buffer_manager_v1 *single_pixel_manager;
struct wp_viewporter *viewporter;
struct wp_viewport *viewport;
struct pixel_color pixel_color;
enum xx_color_manager_v4_primaries primaries;
enum xx_color_manager_v4_transfer_function transfer_function;
enum wp_color_manager_v1_primaries primaries;
enum wp_color_manager_v1_transfer_function transfer_function;
float min_lum;
float max_lum;
float ref_lum;
@ -105,14 +105,14 @@ static const struct weston_option cli_options[] = {
};
static const struct valid_enum valid_primaries[] = {
{ "srgb", XX_COLOR_MANAGER_V4_PRIMARIES_SRGB },
{ "bt2020", XX_COLOR_MANAGER_V4_PRIMARIES_BT2020 },
{ "srgb", WP_COLOR_MANAGER_V1_PRIMARIES_SRGB },
{ "bt2020", WP_COLOR_MANAGER_V1_PRIMARIES_BT2020 },
};
static const struct valid_enum valid_transfer_functions[] = {
{ "srgb", XX_COLOR_MANAGER_V4_TRANSFER_FUNCTION_SRGB },
{ "pq", XX_COLOR_MANAGER_V4_TRANSFER_FUNCTION_ST2084_PQ },
{ "linear", XX_COLOR_MANAGER_V4_TRANSFER_FUNCTION_LINEAR },
{ "srgb", WP_COLOR_MANAGER_V1_TRANSFER_FUNCTION_SRGB },
{ "pq", WP_COLOR_MANAGER_V1_TRANSFER_FUNCTION_ST2084_PQ },
{ "linear", WP_COLOR_MANAGER_V1_TRANSFER_FUNCTION_EXT_LINEAR },
};
static bool
@ -196,11 +196,11 @@ validate_options(struct color *color)
validate_option(opt_primaries, &color->primaries,
valid_primaries,
ARRAY_LENGTH(valid_primaries),
XX_COLOR_MANAGER_V4_PRIMARIES_SRGB) &&
WP_COLOR_MANAGER_V1_PRIMARIES_SRGB) &&
validate_option(opt_transfer_function, &color->transfer_function,
valid_transfer_functions,
ARRAY_LENGTH(valid_transfer_functions),
XX_COLOR_MANAGER_V4_TRANSFER_FUNCTION_SRGB) &&
WP_COLOR_MANAGER_V1_TRANSFER_FUNCTION_SRGB) &&
validate_luminance(opt_min_lum, &color->min_lum, -1.f) &&
validate_luminance(opt_max_lum, &color->max_lum, -1.f) &&
validate_luminance(opt_ref_lum, &color->ref_lum, -1.f);
@ -237,7 +237,7 @@ usage(const char *program_name, int exit_code)
}
static void
supported_intent(void *data, struct xx_color_manager_v4 *xx_color_manager_v4,
supported_intent(void *data, struct wp_color_manager_v1 *wp_color_manager_v1,
uint32_t render_intent)
{
struct color *color = data;
@ -246,7 +246,7 @@ supported_intent(void *data, struct xx_color_manager_v4 *xx_color_manager_v4,
}
static void
supported_feature(void *data, struct xx_color_manager_v4 *xx_color_manager_v4,
supported_feature(void *data, struct wp_color_manager_v1 *wp_color_manager_v1,
uint32_t feature)
{
struct color *color = data;
@ -255,7 +255,7 @@ supported_feature(void *data, struct xx_color_manager_v4 *xx_color_manager_v4,
}
static void
supported_tf_named(void *data, struct xx_color_manager_v4 *xx_color_manager_v4,
supported_tf_named(void *data, struct wp_color_manager_v1 *wp_color_manager_v1,
uint32_t tf)
{
struct color *color = data;
@ -265,7 +265,7 @@ supported_tf_named(void *data, struct xx_color_manager_v4 *xx_color_manager_v4,
static void
supported_primaries_named(void *data,
struct xx_color_manager_v4 *xx_color_manager_v4,
struct wp_color_manager_v1 *wp_color_manager_v1,
uint32_t primaries)
{
struct color *color = data;
@ -273,11 +273,17 @@ supported_primaries_named(void *data,
color->supported_primaries_named |= 1 << primaries;
}
static const struct xx_color_manager_v4_listener color_manager_listener = {
static void
done(void *data, struct wp_color_manager_v1 *wp_color_manager_v1)
{
}
static const struct wp_color_manager_v1_listener color_manager_listener = {
supported_intent,
supported_feature,
supported_tf_named,
supported_primaries_named,
done,
};
static void
@ -287,12 +293,12 @@ global_handler(struct display *display, uint32_t name,
struct color *color = data;
struct wl_surface *surface = widget_get_wl_surface(color->widget);
if (strcmp(interface, xx_color_manager_v4_interface.name) == 0) {
if (strcmp(interface, wp_color_manager_v1_interface.name) == 0) {
color->color_manager = display_bind(display, name,
&xx_color_manager_v4_interface, 1);
color->color_surface = xx_color_manager_v4_get_surface(color->color_manager,
&wp_color_manager_v1_interface, 1);
color->color_surface = wp_color_manager_v1_get_surface(color->color_manager,
surface);
xx_color_manager_v4_add_listener(color->color_manager,
wp_color_manager_v1_add_listener(color->color_manager,
&color_manager_listener, color);
} else if (strcmp(interface, wp_single_pixel_buffer_manager_v1_interface.name) == 0) {
color->single_pixel_manager =
@ -311,10 +317,10 @@ check_color_requirements(struct color *color)
if (!color->color_manager) {
fprintf(stderr, "The compositor doesn't expose %s\n",
xx_color_manager_v4_interface.name);
wp_color_manager_v1_interface.name);
return false;
}
if (!(color->supported_color_features & (1 << XX_COLOR_MANAGER_V4_FEATURE_PARAMETRIC))) {
if (!(color->supported_color_features & (1 << WP_COLOR_MANAGER_V1_FEATURE_PARAMETRIC))) {
fprintf(stderr, "The color manager doesn't support the parametric creator\n");
return false;
}
@ -326,12 +332,12 @@ check_color_requirements(struct color *color)
fprintf(stderr, "The color manager doesn't support the transfer function\n");
return false;
}
if (!(color->supported_rendering_intents & (1 << XX_COLOR_MANAGER_V4_RENDER_INTENT_PERCEPTUAL))) {
if (!(color->supported_rendering_intents & (1 << WP_COLOR_MANAGER_V1_RENDER_INTENT_PERCEPTUAL))) {
fprintf(stderr, "The color manager doesn't support perceptual render intent\n");
return false;
}
if (color->min_lum != -1.f || color->max_lum != -1.f || color->ref_lum != -1.f) {
if (!(color->supported_color_features & (1 << XX_COLOR_MANAGER_V4_FEATURE_SET_LUMINANCES))) {
if (!(color->supported_color_features & (1 << WP_COLOR_MANAGER_V1_FEATURE_SET_LUMINANCES))) {
fprintf(stderr, "The color manager doesn't support setting luminances\n");
return false;
}
@ -348,10 +354,10 @@ static void
color_destroy(struct color *color)
{
if (color->color_surface)
xx_color_management_surface_v4_destroy(color->color_surface);
wp_color_management_surface_v1_destroy(color->color_surface);
if (color->color_manager)
xx_color_manager_v4_destroy(color->color_manager);
wp_color_manager_v1_destroy(color->color_manager);
if (color->single_pixel_manager)
wp_single_pixel_buffer_manager_v1_destroy(color->single_pixel_manager);
@ -432,7 +438,7 @@ set_single_pixel(struct color *color, struct widget *widget)
static void
image_description_failed(void *data,
struct xx_image_description_v4 *xx_image_description_v4,
struct wp_image_description_v1 *wp_image_description_v1,
uint32_t cause, const char *msg)
{
enum image_description_status *image_desc_status = data;
@ -444,7 +450,7 @@ image_description_failed(void *data,
}
static void
image_description_ready(void *data, struct xx_image_description_v4 *xx_image_description_v4,
image_description_ready(void *data, struct wp_image_description_v1 *wp_image_description_v1,
uint32_t identity)
{
enum image_description_status *image_desc_status = data;
@ -452,43 +458,43 @@ image_description_ready(void *data, struct xx_image_description_v4 *xx_image_des
*image_desc_status = IMAGE_DESCRIPTION_READY;
}
static const struct xx_image_description_v4_listener image_description_listener = {
static const struct wp_image_description_v1_listener image_description_listener = {
image_description_failed,
image_description_ready,
};
static struct xx_image_description_v4 *
static struct wp_image_description_v1 *
create_image_description(struct color *color, uint32_t primaries_named, uint32_t tf_named)
{
struct xx_image_description_creator_params_v4 *params_creator;
struct xx_image_description_v4 *image_description;
struct wp_image_description_creator_params_v1 *params_creator;
struct wp_image_description_v1 *image_description;
enum image_description_status image_desc_status = IMAGE_DESCRIPTION_NOT_CREATED;
int ret = 0;
params_creator = xx_color_manager_v4_new_parametric_creator(color->color_manager);
xx_image_description_creator_params_v4_set_primaries_named(params_creator, primaries_named);
xx_image_description_creator_params_v4_set_tf_named(params_creator, tf_named);
params_creator = wp_color_manager_v1_create_parametric_creator(color->color_manager);
wp_image_description_creator_params_v1_set_primaries_named(params_creator, primaries_named);
wp_image_description_creator_params_v1_set_tf_named(params_creator, tf_named);
if (color->min_lum != -1 && color->max_lum != -1 && color->ref_lum != -1)
xx_image_description_creator_params_v4_set_luminances(params_creator,
wp_image_description_creator_params_v1_set_luminances(params_creator,
color->min_lum * 10000,
color->max_lum,
color->ref_lum);
image_description = xx_image_description_creator_params_v4_create(params_creator);
xx_image_description_v4_add_listener(image_description,
image_description = wp_image_description_creator_params_v1_create(params_creator);
wp_image_description_v1_add_listener(image_description,
&image_description_listener,
&image_desc_status);
while (ret != -1 && image_desc_status == IMAGE_DESCRIPTION_NOT_CREATED)
ret = wl_display_dispatch(display_get_display(color->display));
if (ret == -1) {
xx_image_description_v4_destroy(image_description);
wp_image_description_v1_destroy(image_description);
fprintf(stderr, "Error when creating the image description: %s\n", strerror(errno));
return NULL;
}
if (image_desc_status == IMAGE_DESCRIPTION_FAILED) {
xx_image_description_v4_destroy(image_description);
wp_image_description_v1_destroy(image_description);
return NULL;
}
@ -500,7 +506,7 @@ create_image_description(struct color *color, uint32_t primaries_named, uint32_t
static bool
set_image_description(struct color *color, struct widget *widget)
{
struct xx_image_description_v4 *image_description;
struct wp_image_description_v1 *image_description;
image_description =
create_image_description(color,
@ -509,12 +515,12 @@ set_image_description(struct color *color, struct widget *widget)
if (!image_description)
return false;
xx_color_management_surface_v4_set_image_description(
wp_color_management_surface_v1_set_image_description(
color->color_surface,
image_description,
XX_COLOR_MANAGER_V4_RENDER_INTENT_PERCEPTUAL);
WP_COLOR_MANAGER_V1_RENDER_INTENT_PERCEPTUAL);
xx_image_description_v4_destroy(image_description);
wp_image_description_v1_destroy(image_description);
return true;
}

View file

@ -89,7 +89,7 @@ struct display {
struct wl_data_device_manager *data_device_manager;
struct text_cursor_position *text_cursor_position;
struct xdg_wm_base *xdg_shell;
struct xx_color_manager_v4 *color_manager;
struct wp_color_manager_v1 *color_manager;
struct zwp_tablet_manager_v2 *tablet_manager;
struct zwp_relative_pointer_manager_v1 *relative_pointer_manager;
struct zwp_pointer_constraints_v1 *pointer_constraints;
@ -215,7 +215,7 @@ struct surface {
struct wl_callback *frame_cb;
uint32_t last_time;
struct xx_color_management_surface_v4 *cm_surface;
struct wp_color_management_surface_v1 *cm_surface;
struct rectangle allocation;
struct rectangle server_allocation;
@ -476,7 +476,7 @@ struct shm_pool {
};
struct cm_image_description {
struct xx_image_description_v4 *image_desc;
struct wp_image_description_v1 *image_desc;
enum cm_image_desc_status {
CM_IMAGE_DESC_NOT_CREATED = 0,
CM_IMAGE_DESC_READY,
@ -489,27 +489,27 @@ render_intent_info_table[] = {
{
.intent = RENDER_INTENT_PERCEPTUAL,
.desc = "Perceptual",
.protocol_intent = XX_COLOR_MANAGER_V4_RENDER_INTENT_PERCEPTUAL,
.protocol_intent = WP_COLOR_MANAGER_V1_RENDER_INTENT_PERCEPTUAL,
},
{
.intent = RENDER_INTENT_RELATIVE,
.desc = "Media-relative colorimetric",
.protocol_intent = XX_COLOR_MANAGER_V4_RENDER_INTENT_RELATIVE,
.protocol_intent = WP_COLOR_MANAGER_V1_RENDER_INTENT_RELATIVE,
},
{
.intent = RENDER_INTENT_RELATIVE_BPC,
.desc = "Media-relative colorimetric + black point compensation",
.protocol_intent = XX_COLOR_MANAGER_V4_RENDER_INTENT_RELATIVE_BPC,
.protocol_intent = WP_COLOR_MANAGER_V1_RENDER_INTENT_RELATIVE_BPC,
},
{
.intent = RENDER_INTENT_SATURATION,
.desc = "Saturation",
.protocol_intent = XX_COLOR_MANAGER_V4_RENDER_INTENT_SATURATION,
.protocol_intent = WP_COLOR_MANAGER_V1_RENDER_INTENT_SATURATION,
},
{
.intent = RENDER_INTENT_ABSOLUTE,
.desc = "ICC-absolute colorimetric",
.protocol_intent = XX_COLOR_MANAGER_V4_RENDER_INTENT_ABSOLUTE,
.protocol_intent = WP_COLOR_MANAGER_V1_RENDER_INTENT_ABSOLUTE,
},
};
@ -564,7 +564,7 @@ debug_print(void *proxy, int line, const char *func, const char *fmt, ...)
#endif
static void
cm_image_desc_ready(void *data, struct xx_image_description_v4 *xx_image_description_v4,
cm_image_desc_ready(void *data, struct wp_image_description_v1 *wp_image_description_v1,
uint32_t identity)
{
struct cm_image_description *cm_image_desc = data;
@ -573,7 +573,7 @@ cm_image_desc_ready(void *data, struct xx_image_description_v4 *xx_image_descrip
}
static void
cm_image_desc_failed(void *data, struct xx_image_description_v4 *xx_image_description_v4,
cm_image_desc_failed(void *data, struct wp_image_description_v1 *wp_image_description_v1,
uint32_t cause, const char *msg)
{
struct cm_image_description *cm_image_desc = data;
@ -584,7 +584,7 @@ cm_image_desc_failed(void *data, struct xx_image_description_v4 *xx_image_descri
cm_image_desc->status = CM_IMAGE_DESC_FAILED;
}
static const struct xx_image_description_v4_listener cm_image_desc_listener = {
static const struct wp_image_description_v1_listener cm_image_desc_listener = {
.ready = cm_image_desc_ready,
.failed = cm_image_desc_failed,
};
@ -606,10 +606,10 @@ widget_set_image_description_icc(struct widget *widget, int icc_fd,
uint32_t length, uint32_t offset,
enum render_intent intent, char **err_msg)
{
struct xx_image_description_creator_icc_v4 *icc_creator;
struct wp_image_description_creator_icc_v1 *icc_creator;
struct display *display = widget->window->display;
struct surface *surface = widget->surface;
struct xx_color_manager_v4 *color_manager_wrapper;
struct wp_color_manager_v1 *color_manager_wrapper;
struct wl_event_queue *queue;
struct cm_image_description cm_image_desc;
const struct render_intent_info *intent_info;
@ -619,11 +619,11 @@ widget_set_image_description_icc(struct widget *widget, int icc_fd,
str_printf(err_msg,
"%s extension not supported by the Wayland " \
"compositor, ignoring image color profile.",
xx_color_manager_v4_interface.name);
wp_color_manager_v1_interface.name);
return false;
}
if (!((display->color_manager_features >> XX_COLOR_MANAGER_V4_FEATURE_ICC_V2_V4) & 1)) {
if (!((display->color_manager_features >> WP_COLOR_MANAGER_V1_FEATURE_ICC_V2_V4) & 1)) {
str_printf(err_msg,
"Wayland compositor does not support creating image " \
"descriptions from ICC files, ignoring color profile.");
@ -646,15 +646,15 @@ widget_set_image_description_icc(struct widget *widget, int icc_fd,
wl_proxy_set_queue((struct wl_proxy *)color_manager_wrapper, queue);
/* Create ICC image description creator and set the ICC file. */
icc_creator = xx_color_manager_v4_new_icc_creator(color_manager_wrapper);
icc_creator = wp_color_manager_v1_create_icc_creator(color_manager_wrapper);
wl_proxy_wrapper_destroy(color_manager_wrapper);
xx_image_description_creator_icc_v4_set_icc_file(icc_creator,
wp_image_description_creator_icc_v1_set_icc_file(icc_creator,
icc_fd, offset, length);
/* Create the image description. It will also destroy the ICC creator. */
cm_image_desc.status = CM_IMAGE_DESC_NOT_CREATED;
cm_image_desc.image_desc = xx_image_description_creator_icc_v4_create(icc_creator);
xx_image_description_v4_add_listener(cm_image_desc.image_desc,
cm_image_desc.image_desc = wp_image_description_creator_icc_v1_create(icc_creator);
wp_image_description_v1_add_listener(cm_image_desc.image_desc,
&cm_image_desc_listener, &cm_image_desc);
/* Wait until compositor creates the image description or gracefully
@ -662,7 +662,7 @@ widget_set_image_description_icc(struct widget *widget, int icc_fd,
while (ret != -1 && cm_image_desc.status == CM_IMAGE_DESC_NOT_CREATED)
ret = wl_display_dispatch_queue(display->display, queue);
if (ret == -1) {
xx_image_description_v4_destroy(cm_image_desc.image_desc);
wp_image_description_v1_destroy(cm_image_desc.image_desc);
wl_event_queue_destroy(queue);
str_printf(err_msg,
"Disconnected from the Wayland compositor, " \
@ -673,7 +673,7 @@ widget_set_image_description_icc(struct widget *widget, int icc_fd,
/* Gracefully failed to create image description. Error already printed
* in the handler. */
if (cm_image_desc.status == CM_IMAGE_DESC_FAILED) {
xx_image_description_v4_destroy(cm_image_desc.image_desc);
wp_image_description_v1_destroy(cm_image_desc.image_desc);
wl_event_queue_destroy(queue);
str_printf(err_msg,
"Image description creation gracefully failed.");
@ -683,14 +683,14 @@ widget_set_image_description_icc(struct widget *widget, int icc_fd,
if (!surface->cm_surface)
surface->cm_surface =
xx_color_manager_v4_get_surface(display->color_manager,
wp_color_manager_v1_get_surface(display->color_manager,
surface->surface);
xx_color_management_surface_v4_set_image_description(surface->cm_surface,
wp_color_management_surface_v1_set_image_description(surface->cm_surface,
cm_image_desc.image_desc,
intent_info->protocol_intent);
xx_image_description_v4_destroy(cm_image_desc.image_desc);
wp_image_description_v1_destroy(cm_image_desc.image_desc);
wl_event_queue_destroy(queue);
return true;
@ -1574,7 +1574,7 @@ surface_destroy(struct surface *surface)
wp_viewport_destroy(surface->viewport);
if (surface->cm_surface)
xx_color_management_surface_v4_destroy(surface->cm_surface);
wp_color_management_surface_v1_destroy(surface->cm_surface);
wl_surface_destroy(surface->surface);
@ -6687,7 +6687,7 @@ display_bind_tablets(struct display *d, uint32_t id)
}
static void
cm_supported_intent(void *data, struct xx_color_manager_v4 *xx_color_manager_v4,
cm_supported_intent(void *data, struct wp_color_manager_v1 *wp_color_manager_v1,
uint32_t render_intent)
{
struct display *d = data;
@ -6696,7 +6696,7 @@ cm_supported_intent(void *data, struct xx_color_manager_v4 *xx_color_manager_v4,
}
static void
cm_supported_feature(void *data, struct xx_color_manager_v4 *xx_color_manager_v4,
cm_supported_feature(void *data, struct wp_color_manager_v1 *wp_color_manager_v1,
uint32_t feature)
{
struct display *d = data;
@ -6705,24 +6705,31 @@ cm_supported_feature(void *data, struct xx_color_manager_v4 *xx_color_manager_v4
}
static void
cm_supported_tf_named(void *data, struct xx_color_manager_v4 *xx_color_manager_v4,
cm_supported_tf_named(void *data, struct wp_color_manager_v1 *wp_color_manager_v1,
uint32_t tf_code)
{
/* unused in this file */
}
static void
cm_supported_primaries_named(void *data, struct xx_color_manager_v4 *xx_color_manager_v4,
cm_supported_primaries_named(void *data, struct wp_color_manager_v1 *wp_color_manager_v1,
uint32_t primaries_code)
{
/* unused in this file */
}
static const struct xx_color_manager_v4_listener cm_listener = {
static void
cm_done(void *data, struct wp_color_manager_v1 *wp_color_manager_v1)
{
/* unused in this file */
}
static const struct wp_color_manager_v1_listener cm_listener = {
.supported_intent = cm_supported_intent,
.supported_feature = cm_supported_feature,
.supported_tf_named = cm_supported_tf_named,
.supported_primaries_named = cm_supported_primaries_named,
.done = cm_done,
};
static void
@ -6793,11 +6800,11 @@ registry_handle_global(void *data, struct wl_registry *registry, uint32_t id,
&wp_viewporter_interface, 1);
} else if (strcmp(interface, "zwp_tablet_manager_v2") == 0) {
display_bind_tablets(d, id);
} else if (strcmp(interface, "xx_color_manager_v4") == 0) {
} else if (strcmp(interface, "wp_color_manager_v1") == 0) {
d->color_manager =
wl_registry_bind(registry, id,
&xx_color_manager_v4_interface, 1);
xx_color_manager_v4_add_listener(d->color_manager,
&wp_color_manager_v1_interface, 1);
wp_color_manager_v1_add_listener(d->color_manager,
&cm_listener, d);
}
@ -7021,7 +7028,7 @@ display_destroy(struct display *display)
xdg_wm_base_destroy(display->xdg_shell);
if (display->color_manager)
xx_color_manager_v4_destroy(display->color_manager);
wp_color_manager_v1_destroy(display->color_manager);
if (display->shm)
wl_shm_destroy(display->shm);

View file

@ -340,16 +340,15 @@ enum weston_color_primaries {
/** Transfer functions known by libweston */
enum weston_transfer_function {
WESTON_TF_LINEAR = 0,
WESTON_TF_BT1886 = 0,
WESTON_TF_GAMMA22,
WESTON_TF_GAMMA28,
WESTON_TF_SRGB,
WESTON_TF_EXT_SRGB,
WESTON_TF_BT709,
WESTON_TF_BT1361,
WESTON_TF_ST240,
WESTON_TF_ST428,
WESTON_TF_ST2084_PQ,
WESTON_TF_EXT_LINEAR,
WESTON_TF_LOG_100,
WESTON_TF_LOG_316,
WESTON_TF_XVYCC,
@ -360,7 +359,7 @@ enum weston_transfer_function {
/** Error codes that the color profile parameters functions may return. */
enum weston_color_profile_param_builder_error {
WESTON_COLOR_PROFILE_PARAM_BUILDER_ERROR_INVALID_TF = 0,
WESTON_COLOR_PROFILE_PARAM_BUILDER_ERROR_INVALID_PRIMARIES,
WESTON_COLOR_PROFILE_PARAM_BUILDER_ERROR_INVALID_PRIMARIES_NAMED,
WESTON_COLOR_PROFILE_PARAM_BUILDER_ERROR_CIE_XY_OUT_OF_RANGE,
WESTON_COLOR_PROFILE_PARAM_BUILDER_ERROR_CREATE_FAILED,
WESTON_COLOR_PROFILE_PARAM_BUILDER_ERROR_INVALID_LUMINANCE,
@ -2095,7 +2094,7 @@ struct weston_surface {
*
* When a client uses this request, we add the wl_resource we create to
* this list. */
struct wl_list cm_feedback_surface_resource_list;
struct wl_list cm_surface_feedback_resource_list;
struct wl_resource *cm_surface;
uint64_t damage_track_id;

View file

@ -493,6 +493,7 @@ weston_color_manager_create(struct weston_compositor *compositor)
cm->base.get_color_profile_from_icc = cmlcms_get_color_profile_from_icc;
cm->base.get_color_profile_from_params = cmlcms_get_color_profile_from_params;
cm->base.send_image_desc_info = cmlcms_send_image_desc_info;
cm->base.get_parametric_color_profile = cmlcms_get_parametric_color_profile;
cm->base.destroy_color_transform = cmlcms_destroy_color_transform;
cm->base.get_surface_color_transform = cmlcms_get_surface_color_transform;
cm->base.create_output_color_outcome = cmlcms_create_output_color_outcome;

View file

@ -177,6 +177,10 @@ bool
cmlcms_send_image_desc_info(struct cm_image_desc_info *cm_image_desc_info,
struct weston_color_profile *cprof_base);
struct weston_color_profile *
cmlcms_get_parametric_color_profile(struct weston_color_profile *cprof_base,
char **errmsg);
void
cmlcms_destroy_color_profile(struct weston_color_profile *cprof_base);

View file

@ -790,14 +790,45 @@ cmlcms_send_image_desc_info(struct cm_image_desc_info *cm_image_desc_info,
weston_cm_send_primaries(cm_image_desc_info,
&primaries_info->color_gamut);
/* Target primaries, equal to the primary primaries. */
weston_cm_send_target_primaries(cm_image_desc_info,
&primaries_info->color_gamut);
/* sRGB transfer function. */
tf_info = weston_color_tf_info_from(compositor, WESTON_TF_GAMMA22);
weston_cm_send_tf_named(cm_image_desc_info, tf_info);
/* Primary luminance, default values from the protocol. */
weston_cm_send_luminances(cm_image_desc_info, 0.2, 80.0, 80.0);
/* Target luminance, min/max equals primary luminance min/max. */
weston_cm_send_target_luminances(cm_image_desc_info, 0.2, 80.0);
}
return true;
}
struct weston_color_profile *
cmlcms_get_parametric_color_profile(struct weston_color_profile *cprof_base,
char **errmsg)
{
struct weston_color_manager_lcms *cm = to_cmlcms(cprof_base->cm);
struct weston_compositor *compositor = cm->base.compositor;
struct cmlcms_color_profile *cprof = to_cmlcms_cprof(cprof_base);
switch(cprof->type) {
case CMLCMS_PROFILE_TYPE_ICC:
/* TODO: transform an ICC profile into an equivalent parametric one. */
str_printf(errmsg, "we still can't create param cprof equivalent to ICC cprof");
return NULL;
case CMLCMS_PROFILE_TYPE_PARAMS:
ref_cprof(cprof);
return cprof_base;
default:
weston_assert_not_reached(compositor, "unknown cprof type");
}
}
void
cmlcms_destroy_color_profile(struct weston_color_profile *cprof_base)
{

View file

@ -122,13 +122,13 @@ weston_cm_send_icc_file(struct cm_image_desc_info *cm_image_desc_info,
return;
}
xx_image_description_info_v4_send_icc_file(cm_image_desc_info->owner,
wp_image_description_info_v1_send_icc_file(cm_image_desc_info->owner,
fd, len);
}
/**
* For a parametric image description, sends its
* enum xx_color_manager_v4_primaries code to the client.
* enum wp_color_manager_v1_primaries code to the client.
*
* This is a helper function that should be used by the color plugin
* that owns the color profile and has information about it.
@ -140,7 +140,7 @@ WL_EXPORT void
weston_cm_send_primaries_named(struct cm_image_desc_info *cm_image_desc_info,
const struct weston_color_primaries_info *primaries_info)
{
xx_image_description_info_v4_send_primaries_named(cm_image_desc_info->owner,
wp_image_description_info_v1_send_primaries_named(cm_image_desc_info->owner,
primaries_info->protocol_primaries);
}
@ -158,24 +158,53 @@ WL_EXPORT void
weston_cm_send_primaries(struct cm_image_desc_info *cm_image_desc_info,
const struct weston_color_gamut *color_gamut)
{
xx_image_description_info_v4_send_primaries(cm_image_desc_info->owner,
wp_image_description_info_v1_send_primaries(cm_image_desc_info->owner,
/* red */
round(color_gamut->primary[0].x * 10000),
round(color_gamut->primary[0].y * 10000),
round(color_gamut->primary[0].x * 1000000),
round(color_gamut->primary[0].y * 1000000),
/* green */
round(color_gamut->primary[1].x * 10000),
round(color_gamut->primary[1].y * 10000),
round(color_gamut->primary[1].x * 1000000),
round(color_gamut->primary[1].y * 1000000),
/* blue */
round(color_gamut->primary[2].x * 10000),
round(color_gamut->primary[2].y * 10000),
round(color_gamut->primary[2].x * 1000000),
round(color_gamut->primary[2].y * 1000000),
/* white point */
round(color_gamut->white_point.x * 10000),
round(color_gamut->white_point.y * 10000));
round(color_gamut->white_point.x * 1000000),
round(color_gamut->white_point.y * 1000000));
}
/**
* For a parametric image description, sends the target color volume primaries
* and white point using CIE 1931 xy chromaticity coordinates to the client.
*
* This is a helper function that should be used by the color plugin
* that owns the color profile and has information about it.
*
* \param cm_image_desc_info The image description info object
* \param color_gamut The CIE 1931 xy chromaticity coordinates
*/
WL_EXPORT void
weston_cm_send_target_primaries(struct cm_image_desc_info *cm_image_desc_info,
const struct weston_color_gamut *color_gamut)
{
wp_image_description_info_v1_send_target_primaries(cm_image_desc_info->owner,
/* red */
round(color_gamut->primary[0].x * 1000000),
round(color_gamut->primary[0].y * 1000000),
/* green */
round(color_gamut->primary[1].x * 1000000),
round(color_gamut->primary[1].y * 1000000),
/* blue */
round(color_gamut->primary[2].x * 1000000),
round(color_gamut->primary[2].y * 1000000),
/* white point */
round(color_gamut->white_point.x * 1000000),
round(color_gamut->white_point.y * 1000000));
}
/**
* For a parametric image description, sends its
* enum xx_color_manager_v4_transfer_function code to the client.
* enum wp_color_manager_v1_transfer_function code to the client.
*
* This is a helper function that should be used by the color plugin
* that owns the color profile and has information about it.
@ -187,10 +216,51 @@ WL_EXPORT void
weston_cm_send_tf_named(struct cm_image_desc_info *cm_image_desc_info,
const struct weston_color_tf_info *tf_info)
{
xx_image_description_info_v4_send_tf_named(cm_image_desc_info->owner,
wp_image_description_info_v1_send_tf_named(cm_image_desc_info->owner,
tf_info->protocol_tf);
}
/**
* For a parametric image description, sends the primary luminances
* to the client.
*
* This is a helper function that should be used by the color plugin
* that owns the color profile and has information about it.
*
* \param cm_image_desc_info The image description info object
* \param min_lum The minimum luminance (cd/m²)
* \param max_lum The maximum luminance (cd/m²)
* \param ref_lum The reference white luminance (cd/m²)
*/
WL_EXPORT void
weston_cm_send_luminances(struct cm_image_desc_info *cm_image_desc_info,
float min_lum, float max_lum, float ref_lum)
{
wp_image_description_info_v1_send_luminances(cm_image_desc_info->owner,
min_lum * 10000,
max_lum, ref_lum);
}
/**
* For a parametric image description, sends the target luminances
* to the client.
*
* This is a helper function that should be used by the color plugin
* that owns the color profile and has information about it.
*
* \param cm_image_desc_info The image description info object
* \param min_lum The minimum target luminance (cd/m²)
* \param max_lum The maximum target luminance (cd/m²)
*/
WL_EXPORT void
weston_cm_send_target_luminances(struct cm_image_desc_info *cm_image_desc_info,
float min_lum, float max_lum)
{
wp_image_description_info_v1_send_target_luminance(cm_image_desc_info->owner,
min_lum * 10000,
max_lum);
}
/**
* Destroy an image description info object.
*/
@ -228,7 +298,7 @@ image_description_info_create(struct wl_client *client, uint32_t version,
cm_image_desc_info->compositor = compositor;
cm_image_desc_info->owner =
wl_resource_create(client, &xx_image_description_info_v4_interface,
wl_resource_create(client, &wp_image_description_info_v1_interface,
version, cm_image_desc_info_id);
if (!cm_image_desc_info->owner) {
free(cm_image_desc_info);
@ -258,7 +328,7 @@ image_description_get_information(struct wl_client *client,
if (!cm_image_desc) {
wl_resource_post_error(cm_image_desc_res,
XX_IMAGE_DESCRIPTION_V4_ERROR_NOT_READY,
WP_IMAGE_DESCRIPTION_V1_ERROR_NOT_READY,
"we gracefully failed to create this image " \
"description");
return;
@ -266,14 +336,14 @@ image_description_get_information(struct wl_client *client,
if (!cm_image_desc->cprof) {
wl_resource_post_error(cm_image_desc_res,
XX_IMAGE_DESCRIPTION_V4_ERROR_NOT_READY,
WP_IMAGE_DESCRIPTION_V1_ERROR_NOT_READY,
"image description not ready yet");
return;
}
if (!cm_image_desc->supports_get_info) {
wl_resource_post_error(cm_image_desc_res,
XX_IMAGE_DESCRIPTION_V4_ERROR_NO_INFORMATION,
WP_IMAGE_DESCRIPTION_V1_ERROR_NO_INFORMATION,
"get_information is not allowed for this "
"image description");
return;
@ -293,7 +363,7 @@ image_description_get_information(struct wl_client *client,
success = cm_image_desc->cm->send_image_desc_info(cm_image_desc_info,
cm_image_desc->cprof);
if (success)
xx_image_description_info_v4_send_done(cm_image_desc_info->owner);
wp_image_description_info_v1_send_done(cm_image_desc_info->owner);
/* All info sent, so destroy the object. */
wl_resource_destroy(cm_image_desc_info->owner);
@ -331,7 +401,7 @@ image_description_resource_destroy(struct wl_resource *cm_image_desc_res)
cm_image_desc_destroy(cm_image_desc);
}
static const struct xx_image_description_v4_interface
static const struct wp_image_description_v1_interface
image_description_implementation = {
.destroy = image_description_destroy,
.get_information = image_description_get_information,
@ -352,7 +422,7 @@ cm_image_desc_create(struct weston_color_manager *cm,
cm_image_desc = xzalloc(sizeof(*cm_image_desc));
cm_image_desc->owner =
wl_resource_create(client, &xx_image_description_v4_interface,
wl_resource_create(client, &wp_image_description_v1_interface,
version, image_description_id);
if (!cm_image_desc->owner) {
free(cm_image_desc);
@ -405,7 +475,7 @@ cm_output_get_image_description(struct wl_client *client,
* that they are invalid through that). */
if (!head) {
cm_image_desc_res =
wl_resource_create(client, &xx_image_description_v4_interface,
wl_resource_create(client, &wp_image_description_v1_interface,
version, protocol_object_id);
if (!cm_image_desc_res) {
wl_resource_post_no_memory(cm_output_res);
@ -416,8 +486,8 @@ cm_output_get_image_description(struct wl_client *client,
&image_description_implementation,
NULL, image_description_resource_destroy);
xx_image_description_v4_send_failed(cm_image_desc_res,
XX_IMAGE_DESCRIPTION_V4_CAUSE_NO_OUTPUT,
wp_image_description_v1_send_failed(cm_image_desc_res,
WP_IMAGE_DESCRIPTION_V1_CAUSE_NO_OUTPUT,
"the wl_output global no longer exists");
return;
}
@ -441,7 +511,7 @@ cm_output_get_image_description(struct wl_client *client,
return;
}
xx_image_description_v4_send_ready(cm_image_desc->owner,
wp_image_description_v1_send_ready(cm_image_desc->owner,
cm_image_desc->cprof->id);
}
@ -479,7 +549,7 @@ cm_output_resource_destroy(struct wl_resource *cm_output_res)
wl_list_remove(wl_resource_get_link(cm_output_res));
}
static const struct xx_color_management_output_v4_interface
static const struct wp_color_management_output_v1_interface
cm_output_implementation = {
.destroy = cm_output_destroy,
.get_image_description = cm_output_get_image_description,
@ -506,7 +576,7 @@ weston_output_send_image_description_changed(struct weston_output *output)
/* Send the events for each head attached to this weston_output. */
wl_list_for_each(head, &output->head_list, output_link) {
wl_resource_for_each(res, &head->cm_output_resource_list)
xx_color_management_output_v4_send_image_description_changed(res);
wp_color_management_output_v1_send_image_description_changed(res);
/* wl_output.done should be sent after collecting all the
* changes related to the output. But in Weston we are lacking
@ -536,7 +606,7 @@ cm_get_output(struct wl_client *client, struct wl_resource *cm_res,
uint32_t version = wl_resource_get_version(cm_res);
struct wl_resource *res;
res = wl_resource_create(client, &xx_color_management_output_v4_interface,
res = wl_resource_create(client, &wp_color_management_output_v1_interface,
version, cm_output_id);
if (!res) {
wl_resource_post_no_memory(cm_res);
@ -580,9 +650,8 @@ cm_surface_set_image_description(struct wl_client *client,
/* The surface might have been already gone, in such case cm_surface is
* inert. */
if (!surface) {
/* TODO: This error will be surface intert in the future */
wl_resource_post_error(cm_surface_res,
XX_COLOR_MANAGEMENT_SURFACE_V4_ERROR_IMAGE_DESCRIPTION,
WP_COLOR_MANAGEMENT_SURFACE_V1_ERROR_INERT,
"the wl_surface has already been destroyed");
return;
}
@ -590,17 +659,16 @@ cm_surface_set_image_description(struct wl_client *client,
/* Invalid image description for this request, as we gracefully failed
* to create it. */
if (!cm_image_desc) {
/* TODO: the version of the xx protocol that we are using still
* does not have an error for this. Fix when we update to the
* next version. */
wl_resource_post_no_memory(cm_surface_res);
wl_resource_post_error(cm_surface_res,
WP_COLOR_MANAGEMENT_SURFACE_V1_ERROR_IMAGE_DESCRIPTION,
"we gracefully failed to create this image description");
return;
}
/* Invalid image description for this request, as it isn't ready yet. */
if (!cm_image_desc->cprof) {
wl_resource_post_error(cm_surface_res,
XX_COLOR_MANAGEMENT_SURFACE_V4_ERROR_IMAGE_DESCRIPTION,
WP_COLOR_MANAGEMENT_SURFACE_V1_ERROR_IMAGE_DESCRIPTION,
"the image description is not ready");
return;
}
@ -611,14 +679,14 @@ cm_surface_set_image_description(struct wl_client *client,
protocol_render_intent);
if (!render_intent) {
wl_resource_post_error(cm_surface_res,
XX_COLOR_MANAGEMENT_SURFACE_V4_ERROR_RENDER_INTENT,
WP_COLOR_MANAGEMENT_SURFACE_V1_ERROR_RENDER_INTENT,
"unknown render intent");
return;
}
if (!((cm->supported_rendering_intents >> render_intent->intent) & 1)) {
wl_resource_post_error(cm_surface_res,
XX_COLOR_MANAGEMENT_SURFACE_V4_ERROR_RENDER_INTENT,
WP_COLOR_MANAGEMENT_SURFACE_V1_ERROR_RENDER_INTENT,
"unsupported render intent");
return;
}
@ -644,9 +712,8 @@ cm_surface_unset_image_description(struct wl_client *client,
/* The surface might have been already gone, in such case cm_surface is
* inert. */
if (!surface) {
/* TODO: This error will be surface intert in the future */
wl_resource_post_error(cm_surface_res,
XX_COLOR_MANAGEMENT_SURFACE_V4_ERROR_IMAGE_DESCRIPTION,
WP_COLOR_MANAGEMENT_SURFACE_V1_ERROR_INERT,
"the wl_surface has already been destroyed");
return;
}
@ -689,7 +756,7 @@ cm_surface_resource_destroy(struct wl_resource *cm_surface_res)
surface->pending.render_intent = NULL;
}
static const struct xx_color_management_surface_v4_interface
static const struct wp_color_management_surface_v1_interface
cm_surface_implementation = {
.destroy = cm_surface_destroy,
.set_image_description = cm_surface_set_image_description,
@ -710,12 +777,12 @@ cm_get_surface(struct wl_client *client, struct wl_resource *cm_res,
if (surface->cm_surface) {
wl_resource_post_error(cm_res,
XX_COLOR_MANAGER_V4_ERROR_SURFACE_EXISTS,
WP_COLOR_MANAGER_V1_ERROR_SURFACE_EXISTS,
"surface already requested");
return;
}
res = wl_resource_create(client, &xx_color_management_surface_v4_interface,
res = wl_resource_create(client, &wp_color_management_surface_v1_interface,
version, cm_surface_id);
if (!res) {
wl_resource_post_no_memory(cm_res);
@ -729,13 +796,13 @@ cm_get_surface(struct wl_client *client, struct wl_resource *cm_res,
}
/**
* Client will not use the cm_feedback_surface anymore, so we destroy its resource.
* Client will not use the cm_surface_feedback anymore, so we destroy its resource.
*/
static void
cm_feedback_surface_destroy(struct wl_client *client,
struct wl_resource *cm_feedback_surface_res)
cm_surface_feedback_destroy(struct wl_client *client,
struct wl_resource *cm_surface_feedback_res)
{
wl_resource_destroy(cm_feedback_surface_res);
wl_resource_destroy(cm_surface_feedback_res);
}
/**
@ -743,20 +810,20 @@ cm_feedback_surface_destroy(struct wl_client *client,
* the surface.
*/
static void
cm_feedback_surface_get_preferred(struct wl_client *client,
struct wl_resource *cm_feedback_surface_res,
cm_surface_feedback_get_preferred(struct wl_client *client,
struct wl_resource *cm_surface_feedback_res,
uint32_t protocol_object_id)
{
struct weston_surface *surface = wl_resource_get_user_data(cm_feedback_surface_res);
uint32_t version = wl_resource_get_version(cm_feedback_surface_res);
struct weston_surface *surface = wl_resource_get_user_data(cm_surface_feedback_res);
uint32_t version = wl_resource_get_version(cm_surface_feedback_res);
struct weston_color_manager *cm;
struct cm_image_desc *cm_image_desc;
/* The surface might have been already gone, in such case cm_feedback_surface is
/* The surface might have been already gone, in such case cm_surface_feedback is
* inert. */
if (!surface) {
wl_resource_post_error(cm_feedback_surface_res,
XX_COLOR_MANAGEMENT_FEEDBACK_SURFACE_V4_ERROR_INERT,
wl_resource_post_error(cm_surface_feedback_res,
WP_COLOR_MANAGEMENT_SURFACE_FEEDBACK_V1_ERROR_INERT,
"the wl_surface has already been destroyed");
return;
}
@ -767,38 +834,93 @@ cm_feedback_surface_get_preferred(struct wl_client *client,
client, version, protocol_object_id,
YES_GET_INFO);
if (!cm_image_desc) {
wl_resource_post_no_memory(cm_feedback_surface_res);
wl_resource_post_no_memory(cm_surface_feedback_res);
return;
}
xx_image_description_v4_send_ready(cm_image_desc->owner,
wp_image_description_v1_send_ready(cm_image_desc->owner,
cm_image_desc->cprof->id);
}
static const struct xx_color_management_feedback_surface_v4_interface
cm_feedback_surface_implementation = {
.destroy = cm_feedback_surface_destroy,
.get_preferred = cm_feedback_surface_get_preferred,
static void
cm_surface_feedback_get_preferred_parametric(struct wl_client *client,
struct wl_resource *cm_surface_feedback_res,
uint32_t protocol_object_id)
{
struct weston_surface *surface = wl_resource_get_user_data(cm_surface_feedback_res);
uint32_t version = wl_resource_get_version(cm_surface_feedback_res);
struct weston_color_manager *cm;
struct cm_image_desc *cm_image_desc;
char *err_msg;
/* The surface might have been already gone, in such case cm_surface_feedback is
* inert. */
if (!surface) {
wl_resource_post_error(cm_surface_feedback_res,
WP_COLOR_MANAGEMENT_SURFACE_FEEDBACK_V1_ERROR_INERT,
"the wl_surface has already been destroyed");
return;
}
cm = surface->compositor->color_manager;
/* Create the image description with cprof == NULL. */
cm_image_desc = cm_image_desc_create(cm, NULL, client, version,
protocol_object_id, YES_GET_INFO);
if (!cm_image_desc) {
wl_resource_post_no_memory(cm_surface_feedback_res);
return;
}
cm_image_desc->cprof =
cm->get_parametric_color_profile(surface->preferred_color_profile,
&err_msg);
/* Failed to get a parametric cprof for surface preferred cprof. */
if (!cm_image_desc->cprof) {
wp_image_description_v1_send_failed(cm_image_desc->owner,
WP_IMAGE_DESCRIPTION_V1_CAUSE_UNSUPPORTED,
err_msg);
free(err_msg);
/* Failed to create the image description, let's set the
* resource userdata to NULL (and other functions can tell that
* it is invalid through that). */
wl_resource_set_user_data(cm_image_desc->owner, NULL);
cm_image_desc_destroy(cm_image_desc);
return;
}
wp_image_description_v1_send_ready(cm_image_desc->owner,
cm_image_desc->cprof->id);
}
static const struct wp_color_management_surface_feedback_v1_interface
cm_surface_feedback_implementation = {
.destroy = cm_surface_feedback_destroy,
.get_preferred = cm_surface_feedback_get_preferred,
.get_preferred_parametric = cm_surface_feedback_get_preferred_parametric,
};
/**
* Resource destruction function for the cm_feedback_surface.
* Resource destruction function for the cm_surface_feedback.
*/
static void
cm_feedback_surface_resource_destroy(struct wl_resource *cm_feedback_surface_res)
cm_surface_feedback_resource_destroy(struct wl_resource *cm_surface_feedback_res)
{
struct weston_surface *surface = wl_resource_get_user_data(cm_feedback_surface_res);
struct weston_surface *surface = wl_resource_get_user_data(cm_surface_feedback_res);
/* For inert cm_feedback_surface, we don't have to do anything.
/* For inert cm_surface_feedback, we don't have to do anything.
*
* We already did what was necessary when cm_feedback_surface became
* We already did what was necessary when cm_surface_feedback became
* inert, in the surface destruction process: weston_surface_unref(). */
if (!surface)
return;
/* We are destroying the cm_feedback_surface_res, so simply remove it from
* weston_surface::cm_feedback_surface_resource_list. */
wl_list_remove(wl_resource_get_link(cm_feedback_surface_res));
/* We are destroying the cm_surface_feedback_res, so simply remove it from
* weston_surface::cm_surface_feedback_resource_list. */
wl_list_remove(wl_resource_get_link(cm_surface_feedback_res));
}
/**
@ -810,33 +932,34 @@ void
weston_surface_send_preferred_image_description_changed(struct weston_surface *surface)
{
struct wl_resource *res;
uint32_t id = surface->preferred_color_profile->id;
wl_resource_for_each(res, &surface->cm_feedback_surface_resource_list)
xx_color_management_feedback_surface_v4_send_preferred_changed(res);
wl_resource_for_each(res, &surface->cm_surface_feedback_resource_list)
wp_color_management_surface_feedback_v1_send_preferred_changed(res, id);
}
/**
* Client called get_feedback_surface(). We already have the backing object, so just
* Client called get_surface_feedback(). We already have the backing object, so just
* create a resource for the client.
*/
static void
cm_get_feedback_surface(struct wl_client *client, struct wl_resource *cm_res,
cm_get_surface_feedback(struct wl_client *client, struct wl_resource *cm_res,
uint32_t cm_surface_id, struct wl_resource *surface_res)
{
struct weston_surface *surface = wl_resource_get_user_data(surface_res);
uint32_t version = wl_resource_get_version(cm_res);
struct wl_resource *res;
res = wl_resource_create(client, &xx_color_management_feedback_surface_v4_interface,
res = wl_resource_create(client, &wp_color_management_surface_feedback_v1_interface,
version, cm_surface_id);
if (!res) {
wl_resource_post_no_memory(cm_res);
return;
}
wl_resource_set_implementation(res, &cm_feedback_surface_implementation,
surface, cm_feedback_surface_resource_destroy);
wl_list_insert(&surface->cm_feedback_surface_resource_list, wl_resource_get_link(res));
wl_resource_set_implementation(res, &cm_surface_feedback_implementation,
surface, cm_surface_feedback_resource_destroy);
wl_list_insert(&surface->cm_surface_feedback_resource_list, wl_resource_get_link(res));
}
/**
@ -854,27 +977,27 @@ cm_creator_icc_set_icc_file(struct wl_client *client,
const char *err_msg;
if (cm_creator_icc->icc_data_length > 0) {
err_code = XX_IMAGE_DESCRIPTION_CREATOR_ICC_V4_ERROR_ALREADY_SET;
err_code = WP_IMAGE_DESCRIPTION_CREATOR_ICC_V1_ERROR_ALREADY_SET;
err_msg = "ICC file was already set";
goto err;
}
if (length == 0 || length > (4 * 1024 * 1024)) {
err_code = XX_IMAGE_DESCRIPTION_CREATOR_ICC_V4_ERROR_BAD_SIZE;
if (length == 0 || length > (32 * 1024 * 1024)) {
err_code = WP_IMAGE_DESCRIPTION_CREATOR_ICC_V1_ERROR_BAD_SIZE;
err_msg = "invalid ICC file size, should be in the " \
"(0, 4MB] interval";
"(0, 32MB] interval";
goto err;
}
flags = fcntl(icc_profile_fd, F_GETFL);
if ((flags & O_ACCMODE) == O_WRONLY) {
err_code = XX_IMAGE_DESCRIPTION_CREATOR_ICC_V4_ERROR_BAD_FD;
err_code = WP_IMAGE_DESCRIPTION_CREATOR_ICC_V1_ERROR_BAD_FD;
err_msg = "ICC fd is not readable";
goto err;
}
if (lseek(icc_profile_fd, 0, SEEK_CUR) < 0) {
err_code = XX_IMAGE_DESCRIPTION_CREATOR_ICC_V4_ERROR_BAD_FD;
err_code = WP_IMAGE_DESCRIPTION_CREATOR_ICC_V1_ERROR_BAD_FD;
err_msg = "ICC fd is not seekable";
goto err;
}
@ -930,13 +1053,13 @@ create_image_description_color_profile_from_icc_creator(struct cm_image_desc *cm
bool ret;
if (!do_length_and_offset_fit(cm_creator_icc)) {
xx_image_description_v4_send_failed(cm_image_desc->owner,
XX_IMAGE_DESCRIPTION_V4_CAUSE_OPERATING_SYSTEM,
wp_image_description_v1_send_failed(cm_image_desc->owner,
WP_IMAGE_DESCRIPTION_V1_CAUSE_OPERATING_SYSTEM,
"length + offset does not fit off_t");
return -1;
}
/* Create buffer to read ICC profile. As they may have up to 4MB, we
/* Create buffer to read ICC profile. As they may have up to 32MB, we
* send OOM if something fails (instead of using xalloc). */
icc_prof_data = zalloc(cm_creator_icc->icc_data_length);
if (!icc_prof_data) {
@ -964,8 +1087,8 @@ create_image_description_color_profile_from_icc_creator(struct cm_image_desc *cm
/* Reading the ICC failed */
free(icc_prof_data);
str_printf(&err_msg, "failed to read ICC file: %s", strerror(errno));
xx_image_description_v4_send_failed(cm_image_desc->owner,
XX_IMAGE_DESCRIPTION_V4_CAUSE_OPERATING_SYSTEM,
wp_image_description_v1_send_failed(cm_image_desc->owner,
WP_IMAGE_DESCRIPTION_V1_CAUSE_OPERATING_SYSTEM,
err_msg);
free(err_msg);
return -1;
@ -976,7 +1099,7 @@ create_image_description_color_profile_from_icc_creator(struct cm_image_desc *cm
* the given ICC file don't simply change. */
free(icc_prof_data);
wl_resource_post_error(cm_creator_icc->owner,
XX_IMAGE_DESCRIPTION_CREATOR_ICC_V4_ERROR_OUT_OF_FILE,
WP_IMAGE_DESCRIPTION_CREATOR_ICC_V1_ERROR_OUT_OF_FILE,
"tried to read ICC beyond EOF");
return -1;
}
@ -998,15 +1121,15 @@ create_image_description_color_profile_from_icc_creator(struct cm_image_desc *cm
* color-manager plugins and decide if we should gracefully fail
* or return a protocol error.
*/
xx_image_description_v4_send_failed(cm_image_desc->owner,
XX_IMAGE_DESCRIPTION_V4_CAUSE_UNSUPPORTED,
wp_image_description_v1_send_failed(cm_image_desc->owner,
WP_IMAGE_DESCRIPTION_V1_CAUSE_UNSUPPORTED,
err_msg);
free(err_msg);
return -1;
}
cm_image_desc->cprof = cprof;
xx_image_description_v4_send_ready(cm_image_desc->owner,
wp_image_description_v1_send_ready(cm_image_desc->owner,
cm_image_desc->cprof->id);
return 0;
}
@ -1030,7 +1153,7 @@ cm_creator_icc_create(struct wl_client *client, struct wl_resource *resource,
if (cm_creator_icc->icc_data_length == 0) {
wl_resource_post_error(resource,
XX_IMAGE_DESCRIPTION_CREATOR_ICC_V4_ERROR_INCOMPLETE_SET,
WP_IMAGE_DESCRIPTION_CREATOR_ICC_V1_ERROR_INCOMPLETE_SET,
"trying to create image description before " \
"setting the ICC file");
return;
@ -1075,7 +1198,7 @@ cm_creator_icc_destructor(struct wl_resource *resource)
free(cm_creator_icc);
}
static const struct xx_image_description_creator_icc_v4_interface
static const struct wp_image_description_creator_icc_v1_interface
cm_creator_icc_implementation = {
.create = cm_creator_icc_create,
.set_icc_file = cm_creator_icc_set_icc_file,
@ -1085,7 +1208,8 @@ cm_creator_icc_implementation = {
* Creates an ICC-based image description creator for the client.
*/
static void
cm_new_image_description_creator_icc(struct wl_client *client, struct wl_resource *cm_res,
cm_create_image_description_creator_icc(struct wl_client *client,
struct wl_resource *cm_res,
uint32_t cm_creator_icc_id)
{
struct cm_creator_icc *cm_creator_icc;
@ -1094,7 +1218,7 @@ cm_new_image_description_creator_icc(struct wl_client *client, struct wl_resourc
uint32_t version = wl_resource_get_version(cm_res);
if (!((cm->supported_color_features >> WESTON_COLOR_FEATURE_ICC) & 1)) {
wl_resource_post_error(cm_res, XX_COLOR_MANAGER_V4_ERROR_UNSUPPORTED_FEATURE,
wl_resource_post_error(cm_res, WP_COLOR_MANAGER_V1_ERROR_UNSUPPORTED_FEATURE,
"creating ICC image descriptions is not supported");
return;
}
@ -1105,7 +1229,7 @@ cm_new_image_description_creator_icc(struct wl_client *client, struct wl_resourc
cm_creator_icc->icc_profile_fd = -1;
cm_creator_icc->owner =
wl_resource_create(client, &xx_image_description_creator_icc_v4_interface,
wl_resource_create(client, &wp_image_description_creator_icc_v1_interface,
version, cm_creator_icc_id);
if (!cm_creator_icc->owner)
goto err;
@ -1131,17 +1255,17 @@ cm_creator_params_error_to_protocol(struct weston_compositor *compositor,
{
switch(err) {
case WESTON_COLOR_PROFILE_PARAM_BUILDER_ERROR_INVALID_TF:
return XX_IMAGE_DESCRIPTION_CREATOR_PARAMS_V4_ERROR_INVALID_TF;
case WESTON_COLOR_PROFILE_PARAM_BUILDER_ERROR_INVALID_PRIMARIES:
return XX_IMAGE_DESCRIPTION_CREATOR_PARAMS_V4_ERROR_INVALID_PRIMARIES;
return WP_IMAGE_DESCRIPTION_CREATOR_PARAMS_V1_ERROR_INVALID_TF;
case WESTON_COLOR_PROFILE_PARAM_BUILDER_ERROR_INVALID_PRIMARIES_NAMED:
return WP_IMAGE_DESCRIPTION_CREATOR_PARAMS_V1_ERROR_INVALID_PRIMARIES_NAMED;
case WESTON_COLOR_PROFILE_PARAM_BUILDER_ERROR_INVALID_LUMINANCE:
return XX_IMAGE_DESCRIPTION_CREATOR_PARAMS_V4_ERROR_INVALID_LUMINANCE;
return WP_IMAGE_DESCRIPTION_CREATOR_PARAMS_V1_ERROR_INVALID_LUMINANCE;
case WESTON_COLOR_PROFILE_PARAM_BUILDER_ERROR_INCOMPLETE_SET:
return XX_IMAGE_DESCRIPTION_CREATOR_PARAMS_V4_ERROR_INCOMPLETE_SET;
return WP_IMAGE_DESCRIPTION_CREATOR_PARAMS_V1_ERROR_INCOMPLETE_SET;
case WESTON_COLOR_PROFILE_PARAM_BUILDER_ERROR_ALREADY_SET:
return XX_IMAGE_DESCRIPTION_CREATOR_PARAMS_V4_ERROR_ALREADY_SET;
return WP_IMAGE_DESCRIPTION_CREATOR_PARAMS_V1_ERROR_ALREADY_SET;
case WESTON_COLOR_PROFILE_PARAM_BUILDER_ERROR_UNSUPPORTED:
return XX_IMAGE_DESCRIPTION_CREATOR_PARAMS_V4_ERROR_UNSUPPORTED_FEATURE;
return WP_IMAGE_DESCRIPTION_CREATOR_PARAMS_V1_ERROR_UNSUPPORTED_FEATURE;
case WESTON_COLOR_PROFILE_PARAM_BUILDER_ERROR_CREATE_FAILED:
case WESTON_COLOR_PROFILE_PARAM_BUILDER_ERROR_CIE_XY_OUT_OF_RANGE:
/* These are not protocol errors, but should result in graceful
@ -1192,7 +1316,7 @@ cm_creator_params_set_primaries_named(struct wl_client *client, struct wl_resour
primaries_info = weston_color_primaries_info_from_protocol(primaries_named);
if (!primaries_info) {
wl_resource_post_error(resource,
XX_IMAGE_DESCRIPTION_CREATOR_PARAMS_V4_ERROR_INVALID_PRIMARIES,
WP_IMAGE_DESCRIPTION_CREATOR_PARAMS_V1_ERROR_INVALID_PRIMARIES_NAMED,
"invalid primaries named: %u", primaries_named);
return;
}
@ -1205,7 +1329,7 @@ cm_creator_params_set_primaries_named(struct wl_client *client, struct wl_resour
/**
* Set primaries for parametric-based image description creator object.
*
* The primaries we receive from clients is multiplied by 10000.
* The primaries we receive from clients are multiplied by 1000000.
*/
static void
cm_creator_params_set_primaries(struct wl_client *client, struct wl_resource *resource,
@ -1218,14 +1342,14 @@ cm_creator_params_set_primaries(struct wl_client *client, struct wl_resource *re
wl_resource_get_user_data(resource);
struct weston_color_gamut primaries;
primaries.primary[0].x = r_x / 10000.0f;
primaries.primary[0].y = r_y / 10000.0f;
primaries.primary[1].x = g_x / 10000.0f;
primaries.primary[1].y = g_y / 10000.0f;
primaries.primary[2].x = b_x / 10000.0f;
primaries.primary[2].y = b_y / 10000.0f;
primaries.white_point.x = w_x / 10000.0f;
primaries.white_point.y = w_y / 10000.0f;
primaries.primary[0].x = r_x / 1000000.0f;
primaries.primary[0].y = r_y / 1000000.0f;
primaries.primary[1].x = g_x / 1000000.0f;
primaries.primary[1].y = g_y / 1000000.0f;
primaries.primary[2].x = b_x / 1000000.0f;
primaries.primary[2].y = b_y / 1000000.0f;
primaries.white_point.x = w_x / 1000000.0f;
primaries.white_point.y = w_y / 1000000.0f;
if (!weston_color_profile_param_builder_set_primaries(cm_creator_params->builder,
&primaries))
@ -1246,7 +1370,7 @@ cm_creator_params_set_tf_named(struct wl_client *client, struct wl_resource *res
tf_info = weston_color_tf_info_from_protocol(tf_named);
if (!tf_info) {
wl_resource_post_error(resource,
XX_IMAGE_DESCRIPTION_CREATOR_PARAMS_V4_ERROR_INVALID_TF,
WP_IMAGE_DESCRIPTION_CREATOR_PARAMS_V1_ERROR_INVALID_TF,
"invalid tf named: %u", tf_named);
return;
}
@ -1295,7 +1419,7 @@ cm_creator_params_set_luminances(struct wl_client *client, struct wl_resource *r
/**
* Set mastering display primaries for parametric-based image description creator object.
*
* The primaries we receive from clients is multiplied by 10000.
* The primaries we receive from clients are multiplied by 1000000.
*/
static void
cm_creator_params_set_mastering_display_primaries(struct wl_client *client,
@ -1309,14 +1433,14 @@ cm_creator_params_set_mastering_display_primaries(struct wl_client *client,
wl_resource_get_user_data(resource);
struct weston_color_gamut primaries;
primaries.primary[0].x = r_x / 10000.0f;
primaries.primary[0].y = r_y / 10000.0f;
primaries.primary[1].x = g_x / 10000.0f;
primaries.primary[1].y = g_y / 10000.0f;
primaries.primary[2].x = b_x / 10000.0f;
primaries.primary[2].y = b_y / 10000.0f;
primaries.white_point.x = w_x / 10000.0f;
primaries.white_point.y = w_y / 10000.0f;
primaries.primary[0].x = r_x / 1000000.0f;
primaries.primary[0].y = r_y / 1000000.0f;
primaries.primary[1].x = g_x / 1000000.0f;
primaries.primary[1].y = g_y / 1000000.0f;
primaries.primary[2].x = b_x / 1000000.0f;
primaries.primary[2].y = b_y / 1000000.0f;
primaries.white_point.x = w_x / 1000000.0f;
primaries.white_point.y = w_y / 1000000.0f;
if (!weston_color_profile_param_builder_set_target_primaries(cm_creator_params->builder,
&primaries))
@ -1407,7 +1531,7 @@ cm_creator_params_create(struct wl_client *client, struct wl_resource *resource,
cm_creator_params->builder = NULL;
if (cm_image_desc->cprof) {
xx_image_description_v4_send_ready(cm_image_desc->owner,
wp_image_description_v1_send_ready(cm_image_desc->owner,
cm_image_desc->cprof->id);
} else {
protocol_err = cm_creator_params_error_to_protocol(compositor, err);
@ -1415,8 +1539,8 @@ cm_creator_params_create(struct wl_client *client, struct wl_resource *resource,
wl_resource_post_error(cm_creator_params->owner,
protocol_err, "%s", err_msg);
else
xx_image_description_v4_send_failed(cm_image_desc->owner,
XX_IMAGE_DESCRIPTION_V4_CAUSE_UNSUPPORTED,
wp_image_description_v1_send_failed(cm_image_desc->owner,
WP_IMAGE_DESCRIPTION_V1_CAUSE_UNSUPPORTED,
err_msg);
free(err_msg);
@ -1448,7 +1572,7 @@ cm_creator_params_destructor(struct wl_resource *resource)
free(cm_creator_params);
}
static const struct xx_image_description_creator_params_v4_interface
static const struct wp_image_description_creator_params_v1_interface
cm_creator_params_implementation = {
.set_primaries_named = cm_creator_params_set_primaries_named,
.set_primaries = cm_creator_params_set_primaries,
@ -1466,7 +1590,8 @@ cm_creator_params_implementation = {
* Creates a parametric image description creator for the client.
*/
static void
cm_new_image_description_creator_params(struct wl_client *client, struct wl_resource *cm_res,
cm_create_image_description_creator_params(struct wl_client *client,
struct wl_resource *cm_res,
uint32_t cm_creator_params_id)
{
struct cm_creator_params *cm_creator_params;
@ -1475,7 +1600,7 @@ cm_new_image_description_creator_params(struct wl_client *client, struct wl_reso
uint32_t version = wl_resource_get_version(cm_res);
if (!((cm->supported_color_features >> WESTON_COLOR_FEATURE_PARAMETRIC) & 1)) {
wl_resource_post_error(cm_res, XX_COLOR_MANAGER_V4_ERROR_UNSUPPORTED_FEATURE,
wl_resource_post_error(cm_res, WP_COLOR_MANAGER_V1_ERROR_UNSUPPORTED_FEATURE,
"creating parametric image descriptions " \
"is not supported");
return;
@ -1489,7 +1614,7 @@ cm_new_image_description_creator_params(struct wl_client *client, struct wl_reso
weston_color_profile_param_builder_create(compositor);
cm_creator_params->owner =
wl_resource_create(client, &xx_image_description_creator_params_v4_interface,
wl_resource_create(client, &wp_image_description_creator_params_v1_interface,
version, cm_creator_params_id);
if (!cm_creator_params->owner)
goto err;
@ -1505,6 +1630,15 @@ err:
wl_resource_post_no_memory(cm_res);
}
static void
cm_create_windows_scrgb(struct wl_client *client, struct wl_resource *cm_res,
uint32_t image_description)
{
wl_resource_post_error(cm_res,
WP_COLOR_MANAGER_V1_ERROR_UNSUPPORTED_FEATURE,
"creating windows scrgb is not supported");
}
/**
* Client will not use the color management object anymore, so we destroy its
* resource. That should not affect the other objects in any way.
@ -1515,14 +1649,15 @@ cm_destroy(struct wl_client *client, struct wl_resource *cm_res)
wl_resource_destroy(cm_res);
}
static const struct xx_color_manager_v4_interface
static const struct wp_color_manager_v1_interface
color_manager_implementation = {
.destroy = cm_destroy,
.get_output = cm_get_output,
.get_surface = cm_get_surface,
.get_feedback_surface = cm_get_feedback_surface,
.new_icc_creator = cm_new_image_description_creator_icc,
.new_parametric_creator = cm_new_image_description_creator_params,
.get_surface_feedback = cm_get_surface_feedback,
.create_icc_creator = cm_create_image_description_creator_icc,
.create_parametric_creator = cm_create_image_description_creator_params,
.create_windows_scrgb = cm_create_windows_scrgb,
};
/**
@ -1541,7 +1676,7 @@ bind_color_management(struct wl_client *client, void *data, uint32_t version,
const struct weston_color_tf_info *tf;
unsigned int i;
resource = wl_resource_create(client, &xx_color_manager_v4_interface,
resource = wl_resource_create(client, &wp_color_manager_v1_interface,
version, id);
if (!resource) {
wl_client_post_no_memory(client);
@ -1556,7 +1691,7 @@ bind_color_management(struct wl_client *client, void *data, uint32_t version,
if (!((cm->supported_color_features >> i) & 1))
continue;
feature_info = weston_color_feature_info_from(compositor, i);
xx_color_manager_v4_send_supported_feature(resource,
wp_color_manager_v1_send_supported_feature(resource,
feature_info->protocol_feature);
}
@ -1565,7 +1700,7 @@ bind_color_management(struct wl_client *client, void *data, uint32_t version,
if (!((cm->supported_rendering_intents >> i) & 1))
continue;
render_intent = weston_render_intent_info_from(compositor, i);
xx_color_manager_v4_send_supported_intent(resource,
wp_color_manager_v1_send_supported_intent(resource,
render_intent->protocol_intent);
}
@ -1574,7 +1709,7 @@ bind_color_management(struct wl_client *client, void *data, uint32_t version,
if (!((cm->supported_primaries_named >> i) & 1))
continue;
primaries = weston_color_primaries_info_from(compositor, i);
xx_color_manager_v4_send_supported_primaries_named(resource,
wp_color_manager_v1_send_supported_primaries_named(resource,
primaries->protocol_primaries);
}
@ -1583,15 +1718,17 @@ bind_color_management(struct wl_client *client, void *data, uint32_t version,
if (!((cm->supported_tf_named >> i) & 1))
continue;
tf = weston_color_tf_info_from(compositor, i);
xx_color_manager_v4_send_supported_tf_named(resource,
wp_color_manager_v1_send_supported_tf_named(resource,
tf->protocol_tf);
}
wp_color_manager_v1_send_done(resource);
}
/** Advertise color-management support
*
* Calling this initializes the color-management protocol support, so that
* xx_color_manager_v4_interface will be advertised to clients. Essentially it
* wp_color_manager_v1_interface will be advertised to clients. Essentially it
* creates a global. Do not call this function multiple times in the
* compositor's lifetime. There is no way to deinit explicitly, globals will be
* reaped when the wl_display gets destroyed.
@ -1609,7 +1746,7 @@ weston_compositor_enable_color_management_protocol(struct weston_compositor *com
WESTON_RENDER_INTENT_PERCEPTUAL);
if (!wl_global_create(compositor->wl_display,
&xx_color_manager_v4_interface,
&wp_color_manager_v1_interface,
version, compositor, bind_color_management))
return -1;

View file

@ -51,8 +51,20 @@ void
weston_cm_send_primaries(struct cm_image_desc_info *cm_image_desc_info,
const struct weston_color_gamut *color_gamut);
void
weston_cm_send_target_primaries(struct cm_image_desc_info *cm_image_desc_info,
const struct weston_color_gamut *color_gamut);
void
weston_cm_send_tf_named(struct cm_image_desc_info *cm_image_desc_info,
const struct weston_color_tf_info *tf_info);
void
weston_cm_send_luminances(struct cm_image_desc_info *cm_image_desc_info,
float min_lum, float max_lum, float ref_lum);
void
weston_cm_send_target_luminances(struct cm_image_desc_info *cm_image_desc_info,
float min_lum, float max_lum);
#endif /* WESTON_COLOR_MANAGEMENT_H */

View file

@ -245,7 +245,7 @@ weston_color_profile_param_builder_set_primaries_named(struct weston_color_profi
bool success = true;
if (!((cm->supported_primaries_named >> primaries) & 1)) {
store_error(builder, WESTON_COLOR_PROFILE_PARAM_BUILDER_ERROR_INVALID_PRIMARIES,
store_error(builder, WESTON_COLOR_PROFILE_PARAM_BUILDER_ERROR_INVALID_PRIMARIES_NAMED,
"named primaries %u not supported by the color manager",
primaries);
success = false;
@ -410,13 +410,6 @@ weston_color_profile_param_builder_set_primary_luminance(struct weston_color_pro
success = false;
}
if (max_lum < ref_lum) {
store_error(builder, WESTON_COLOR_PROFILE_PARAM_BUILDER_ERROR_INVALID_LUMINANCE,
"primary reference luminance %f shouldn't be greater than max %f",
ref_lum, max_lum);
success = false;
}
if (min_lum >= ref_lum) {
store_error(builder, WESTON_COLOR_PROFILE_PARAM_BUILDER_ERROR_INVALID_LUMINANCE,
"primary reference luminance %f shouldn't be lesser than or equal to min %f",
@ -505,8 +498,16 @@ bool
weston_color_profile_param_builder_set_target_luminance(struct weston_color_profile_param_builder *builder,
float min_lum, float max_lum)
{
struct weston_color_manager *cm = builder->compositor->color_manager;
bool success = true;
if (!((cm->supported_color_features >> WESTON_COLOR_FEATURE_SET_MASTERING_DISPLAY_PRIMARIES) & 1)) {
store_error(builder, WESTON_COLOR_PROFILE_PARAM_BUILDER_ERROR_UNSUPPORTED,
"set_mastering_display_primaries not supported by " \
"the color manager, so setting target luminance is not allowed");
success = false;
}
if (builder->group_mask & WESTON_COLOR_PROFILE_PARAMS_TARGET_LUMINANCE) {
store_error(builder, WESTON_COLOR_PROFILE_PARAM_BUILDER_ERROR_ALREADY_SET,
"target luminance was already set");
@ -684,7 +685,7 @@ validate_maxcll(struct weston_color_profile_param_builder *builder)
if (builder->params.target_min_luminance >= builder->params.maxCLL)
store_error(builder, WESTON_COLOR_PROFILE_PARAM_BUILDER_ERROR_INVALID_LUMINANCE,
"maxCLL (%f) should be greater or equal to target min luminance (%f)",
"maxCLL (%f) should be greater than target min luminance (%f)",
builder->params.maxCLL, builder->params.target_min_luminance);
if (builder->params.target_max_luminance < builder->params.maxCLL)
@ -701,7 +702,7 @@ validate_maxfall(struct weston_color_profile_param_builder *builder)
if (builder->params.target_min_luminance >= builder->params.maxFALL)
store_error(builder, WESTON_COLOR_PROFILE_PARAM_BUILDER_ERROR_INVALID_LUMINANCE,
"maxFALL (%f) should be greater or equal to min luminance (%f)",
"maxFALL (%f) should be greater than min luminance (%f)",
builder->params.maxFALL, builder->params.target_min_luminance);
if (builder->params.target_max_luminance < builder->params.maxFALL)
@ -719,6 +720,13 @@ builder_validate_params(struct weston_color_profile_param_builder *builder)
if (builder->group_mask & WESTON_COLOR_PROFILE_PARAMS_MAXFALL)
validate_maxfall(builder);
if (builder->group_mask & WESTON_COLOR_PROFILE_PARAMS_MAXCLL &&
builder->group_mask & WESTON_COLOR_PROFILE_PARAMS_MAXFALL &&
builder->params.maxFALL > builder->params.maxCLL)
store_error(builder, WESTON_COLOR_PROFILE_PARAM_BUILDER_ERROR_INVALID_LUMINANCE,
"maxFALL (%f) should not be greater than maxCLL (%f)",
builder->params.maxFALL, builder->params.maxCLL);
if (builder->group_mask & WESTON_COLOR_PROFILE_PARAMS_PRIMARIES)
validate_color_gamut(builder, &builder->params.primaries,
"primaries");
@ -746,9 +754,14 @@ builder_complete_params(struct weston_color_profile_param_builder *builder)
* protocol as well. */
if (builder->group_mask & WESTON_COLOR_PROFILE_PARAMS_TF) {
switch(builder->params.tf_info->tf) {
case WESTON_TF_BT1886:
builder->params.reference_white_luminance = 100.0;
builder->params.min_luminance = 0.01;
builder->params.max_luminance = 100.0;
break;
case WESTON_TF_ST2084_PQ:
builder->params.reference_white_luminance = 203.0;
builder->params.min_luminance = 0.0;
builder->params.min_luminance = 0.005;
builder->params.max_luminance = 10000.0;
break;
case WESTON_TF_HLG:
@ -761,29 +774,25 @@ builder_complete_params(struct weston_color_profile_param_builder *builder)
}
}
} else {
/* Primary luminance is set, but PQ TF override them anyway
* (except reference white level). Also part of the CM&HDR
* protocol. */
/* Primary luminance is set, but the CM&HDR protocol states that
* PQ TF should override max_lum with min_lum + 10000 cd/m². */
if ((builder->group_mask & WESTON_COLOR_PROFILE_PARAMS_TF) &&
builder->params.tf_info->tf == WESTON_TF_ST2084_PQ) {
builder->params.min_luminance = 0.0;
builder->params.max_luminance = 10000.0;
}
builder->params.tf_info->tf == WESTON_TF_ST2084_PQ)
builder->params.max_luminance =
builder->params.min_luminance + 10000.0;
}
/*
* If target luminance is not set, set it to negative. Same applies to
* maxCLL and maxFALL.
*/
/* CM&HDR protocol states that if target luminance is not set, the
* target min and max luminances should have the same values as the
* primary min and max luminances. */
if (!(builder->group_mask & WESTON_COLOR_PROFILE_PARAMS_TARGET_LUMINANCE)) {
builder->params.target_min_luminance = -1.0f;
builder->params.target_max_luminance = -1.0f;
builder->params.target_min_luminance = builder->params.min_luminance;
builder->params.target_max_luminance = builder->params.max_luminance;
}
/* If maxCLL and maxFALL are not set, set them to negative. */
if (!(builder->group_mask & WESTON_COLOR_PROFILE_PARAMS_MAXCLL))
builder->params.maxCLL = -1.0f;
if (!(builder->group_mask & WESTON_COLOR_PROFILE_PARAMS_MAXFALL))
builder->params.maxFALL = -1.0f;
}

View file

@ -45,38 +45,38 @@ static const struct weston_color_feature_info color_feature_info_table[] = {
.feature = WESTON_COLOR_FEATURE_ICC,
.desc = "Allow clients to use the new_icc_creator request " \
"from the CM&HDR protocol extension",
.protocol_feature = XX_COLOR_MANAGER_V4_FEATURE_ICC_V2_V4,
.protocol_feature = WP_COLOR_MANAGER_V1_FEATURE_ICC_V2_V4,
},
{
.feature = WESTON_COLOR_FEATURE_PARAMETRIC,
.desc = "Allow clients to use the new_parametric_creator " \
"request from the CM&HDR protocol extension",
.protocol_feature = XX_COLOR_MANAGER_V4_FEATURE_PARAMETRIC,
.protocol_feature = WP_COLOR_MANAGER_V1_FEATURE_PARAMETRIC,
},
{
.feature = WESTON_COLOR_FEATURE_SET_PRIMARIES,
.desc = "Allow clients to use the parametric set_primaries " \
"request from the CM&HDR protocol extension",
.protocol_feature = XX_COLOR_MANAGER_V4_FEATURE_SET_PRIMARIES,
.protocol_feature = WP_COLOR_MANAGER_V1_FEATURE_SET_PRIMARIES,
},
{
.feature = WESTON_COLOR_FEATURE_SET_TF_POWER,
.desc = "Allow clients to use the parametric set_tf_power " \
"request from the CM&HDR protocol extension",
.protocol_feature = XX_COLOR_MANAGER_V4_FEATURE_SET_TF_POWER,
.protocol_feature = WP_COLOR_MANAGER_V1_FEATURE_SET_TF_POWER,
},
{
.feature = WESTON_COLOR_FEATURE_SET_LUMINANCES,
.desc = "Allow clients to use the parametric set_luminances " \
"request from the CM&HDR protocol extension",
.protocol_feature = XX_COLOR_MANAGER_V4_FEATURE_SET_LUMINANCES,
.protocol_feature = WP_COLOR_MANAGER_V1_FEATURE_SET_LUMINANCES,
},
{
.feature = WESTON_COLOR_FEATURE_SET_MASTERING_DISPLAY_PRIMARIES,
.desc = "Allow clients to use the parametric " \
"set_mastering_display_primaries request from the " \
"CM&HDR protocol extension",
.protocol_feature = XX_COLOR_MANAGER_V4_FEATURE_SET_MASTERING_DISPLAY_PRIMARIES,
.protocol_feature = WP_COLOR_MANAGER_V1_FEATURE_SET_MASTERING_DISPLAY_PRIMARIES,
},
{
.feature = WESTON_COLOR_FEATURE_EXTENDED_TARGET_VOLUME,
@ -85,7 +85,7 @@ static const struct weston_color_feature_info color_feature_info_table[] = {
"primary color volume. This can only be supported when feature " \
"WESTON_COLOR_FEATURE_SET_MASTERING_DISPLAY_PRIMARIES " \
"is supported",
.protocol_feature = XX_COLOR_MANAGER_V4_FEATURE_EXTENDED_TARGET_VOLUME,
.protocol_feature = WP_COLOR_MANAGER_V1_FEATURE_EXTENDED_TARGET_VOLUME,
},
};
@ -93,35 +93,35 @@ static const struct weston_render_intent_info render_intent_info_table[] = {
{
.intent = WESTON_RENDER_INTENT_PERCEPTUAL,
.desc = "Perceptual",
.protocol_intent = XX_COLOR_MANAGER_V4_RENDER_INTENT_PERCEPTUAL,
.protocol_intent = WP_COLOR_MANAGER_V1_RENDER_INTENT_PERCEPTUAL,
LCMS_INTENT(INTENT_PERCEPTUAL),
.bps = false,
},
{
.intent = WESTON_RENDER_INTENT_RELATIVE,
.desc = "Media-relative colorimetric",
.protocol_intent = XX_COLOR_MANAGER_V4_RENDER_INTENT_RELATIVE,
.protocol_intent = WP_COLOR_MANAGER_V1_RENDER_INTENT_RELATIVE,
LCMS_INTENT(INTENT_RELATIVE_COLORIMETRIC),
.bps = false,
},
{
.intent = WESTON_RENDER_INTENT_SATURATION,
.desc = "Saturation",
.protocol_intent = XX_COLOR_MANAGER_V4_RENDER_INTENT_SATURATION,
.protocol_intent = WP_COLOR_MANAGER_V1_RENDER_INTENT_SATURATION,
LCMS_INTENT(INTENT_SATURATION),
.bps = false,
},
{
.intent = WESTON_RENDER_INTENT_ABSOLUTE,
.desc = "ICC-absolute colorimetric",
.protocol_intent = XX_COLOR_MANAGER_V4_RENDER_INTENT_ABSOLUTE,
.protocol_intent = WP_COLOR_MANAGER_V1_RENDER_INTENT_ABSOLUTE,
LCMS_INTENT(INTENT_ABSOLUTE_COLORIMETRIC),
.bps = false,
},
{
.intent = WESTON_RENDER_INTENT_RELATIVE_BPC,
.desc = "Media-relative colorimetric + black point compensation",
.protocol_intent = XX_COLOR_MANAGER_V4_RENDER_INTENT_RELATIVE_BPC,
.protocol_intent = WP_COLOR_MANAGER_V1_RENDER_INTENT_RELATIVE_BPC,
LCMS_INTENT(INTENT_RELATIVE_COLORIMETRIC),
.bps = true,
},
@ -132,7 +132,7 @@ static const struct weston_color_primaries_info color_primaries_info_table[] = {
.primaries = WESTON_PRIMARIES_CICP_SRGB,
.desc = "Color primaries for the sRGB color space as defined by " \
"the BT.709 standard",
.protocol_primaries = XX_COLOR_MANAGER_V4_PRIMARIES_SRGB,
.protocol_primaries = WP_COLOR_MANAGER_V1_PRIMARIES_SRGB,
.color_gamut = {
.primary = { { 0.64, 0.33 }, /* RGB order */
{ 0.30, 0.60 },
@ -144,7 +144,7 @@ static const struct weston_color_primaries_info color_primaries_info_table[] = {
{
.primaries = WESTON_PRIMARIES_CICP_PAL_M,
.desc = "Color primaries for PAL-M as defined by the BT.470 standard",
.protocol_primaries = XX_COLOR_MANAGER_V4_PRIMARIES_PAL_M,
.protocol_primaries = WP_COLOR_MANAGER_V1_PRIMARIES_PAL_M,
.color_gamut = {
.primary = { { 0.67, 0.33 }, /* RGB order */
{ 0.21, 0.71 },
@ -156,7 +156,7 @@ static const struct weston_color_primaries_info color_primaries_info_table[] = {
{
.primaries = WESTON_PRIMARIES_CICP_PAL,
.desc = "Color primaries for PAL as defined by the BT.601 standard",
.protocol_primaries = XX_COLOR_MANAGER_V4_PRIMARIES_PAL,
.protocol_primaries = WP_COLOR_MANAGER_V1_PRIMARIES_PAL,
.color_gamut = {
.primary = { { 0.64, 0.33 }, /* RGB order */
{ 0.29, 0.60 },
@ -168,7 +168,7 @@ static const struct weston_color_primaries_info color_primaries_info_table[] = {
{
.primaries = WESTON_PRIMARIES_CICP_NTSC,
.desc = "Color primaries for NTSC as defined by the BT.601 standard",
.protocol_primaries = XX_COLOR_MANAGER_V4_PRIMARIES_NTSC,
.protocol_primaries = WP_COLOR_MANAGER_V1_PRIMARIES_NTSC,
.color_gamut = {
.primary = { { 0.630, 0.340 }, /* RGB order */
{ 0.310, 0.595 },
@ -180,7 +180,7 @@ static const struct weston_color_primaries_info color_primaries_info_table[] = {
{
.primaries = WESTON_PRIMARIES_CICP_GENERIC_FILM,
.desc = "Generic film with color filters using Illuminant C",
.protocol_primaries = XX_COLOR_MANAGER_V4_PRIMARIES_GENERIC_FILM,
.protocol_primaries = WP_COLOR_MANAGER_V1_PRIMARIES_GENERIC_FILM,
.color_gamut = {
.primary = { { 0.681, 0.319 }, /* RGB order */
{ 0.243, 0.692 },
@ -193,7 +193,7 @@ static const struct weston_color_primaries_info color_primaries_info_table[] = {
.primaries = WESTON_PRIMARIES_CICP_BT2020,
.desc = "Color primaries as defined by the BT.2020 and BT.2100 " \
"standard",
.protocol_primaries = XX_COLOR_MANAGER_V4_PRIMARIES_BT2020,
.protocol_primaries = WP_COLOR_MANAGER_V1_PRIMARIES_BT2020,
.color_gamut = {
.primary = { { 0.708, 0.292 }, /* RGB order */
{ 0.170, 0.797 },
@ -205,7 +205,7 @@ static const struct weston_color_primaries_info color_primaries_info_table[] = {
{
.primaries = WESTON_PRIMARIES_CICP_CIE1931_XYZ,
.desc = "Color primaries of the full CIE 1931 XYZ color space",
.protocol_primaries = XX_COLOR_MANAGER_V4_PRIMARIES_CIE1931_XYZ,
.protocol_primaries = WP_COLOR_MANAGER_V1_PRIMARIES_CIE1931_XYZ,
.color_gamut = {
.primary = { { 1.0, 0.0 }, /* RGB order */
{ 0.0, 1.0 },
@ -218,7 +218,7 @@ static const struct weston_color_primaries_info color_primaries_info_table[] = {
.primaries = WESTON_PRIMARIES_CICP_DCI_P3,
.desc = "Color primaries of the DCI P3 color space as defined by " \
"the SMPTE RP 431 standard",
.protocol_primaries = XX_COLOR_MANAGER_V4_PRIMARIES_DCI_P3,
.protocol_primaries = WP_COLOR_MANAGER_V1_PRIMARIES_DCI_P3,
.color_gamut = {
.primary = { { 0.680, 0.320 }, /* RGB order */
{ 0.265, 0.690 },
@ -231,7 +231,7 @@ static const struct weston_color_primaries_info color_primaries_info_table[] = {
.primaries = WESTON_PRIMARIES_CICP_DISPLAY_P3,
.desc = "Color primaries of Display P3 variant of the DCI-P3 color " \
"space as defined by the SMPTE EG 432 standard",
.protocol_primaries = XX_COLOR_MANAGER_V4_PRIMARIES_DISPLAY_P3,
.protocol_primaries = WP_COLOR_MANAGER_V1_PRIMARIES_DISPLAY_P3,
.color_gamut = {
.primary = { { 0.680, 0.320 }, /* RGB order */
{ 0.265, 0.690 },
@ -244,7 +244,7 @@ static const struct weston_color_primaries_info color_primaries_info_table[] = {
.primaries = WESTON_PRIMARIES_ADOBE_RGB,
.desc = "Color primaries of the Adobe RGB color space as defined " \
"by the ISO 12640 standard",
.protocol_primaries = XX_COLOR_MANAGER_V4_PRIMARIES_ADOBE_RGB,
.protocol_primaries = WP_COLOR_MANAGER_V1_PRIMARIES_ADOBE_RGB,
.color_gamut = {
.primary = { { 0.64, 0.33 }, /* RGB order */
{ 0.21, 0.71 },
@ -257,87 +257,81 @@ static const struct weston_color_primaries_info color_primaries_info_table[] = {
static const struct weston_color_tf_info color_tf_info_table[] = {
{
.tf = WESTON_TF_LINEAR,
.desc = "Linear transfer function",
.protocol_tf = XX_COLOR_MANAGER_V4_TRANSFER_FUNCTION_LINEAR,
.tf = WESTON_TF_BT1886,
.desc = "BT.1886 transfer function",
.protocol_tf = WP_COLOR_MANAGER_V1_TRANSFER_FUNCTION_BT1886,
.count_parameters = 0,
},
{
.tf = WESTON_TF_GAMMA22,
.desc = "Assumed display gamma 2.2 transfer function",
.protocol_tf = XX_COLOR_MANAGER_V4_TRANSFER_FUNCTION_GAMMA22,
.protocol_tf = WP_COLOR_MANAGER_V1_TRANSFER_FUNCTION_GAMMA22,
.count_parameters = 0,
},
{
.tf = WESTON_TF_GAMMA28,
.desc = "Assumed display gamma 2.8 transfer function",
.protocol_tf = XX_COLOR_MANAGER_V4_TRANSFER_FUNCTION_GAMMA28,
.protocol_tf = WP_COLOR_MANAGER_V1_TRANSFER_FUNCTION_GAMMA28,
.count_parameters = 0,
},
{
.tf = WESTON_TF_EXT_LINEAR,
.desc = "Extended Linear transfer function",
.protocol_tf = WP_COLOR_MANAGER_V1_TRANSFER_FUNCTION_EXT_LINEAR,
.count_parameters = 0,
},
{
.tf = WESTON_TF_SRGB,
.desc = "sRGB piece-wise transfer function",
.protocol_tf = XX_COLOR_MANAGER_V4_TRANSFER_FUNCTION_SRGB,
.protocol_tf = WP_COLOR_MANAGER_V1_TRANSFER_FUNCTION_SRGB,
.count_parameters = 0,
},
{
.tf = WESTON_TF_EXT_SRGB,
.desc = "Extended sRGB piece-wise transfer function",
.protocol_tf = XX_COLOR_MANAGER_V4_TRANSFER_FUNCTION_EXT_SRGB,
.count_parameters = 0,
},
{
.tf = WESTON_TF_BT709,
.desc = "BT.709 transfer function",
.protocol_tf = XX_COLOR_MANAGER_V4_TRANSFER_FUNCTION_BT709,
.count_parameters = 0,
},
{
.tf = WESTON_TF_BT1361,
.desc = "BT.1361 extended transfer function",
.protocol_tf = XX_COLOR_MANAGER_V4_TRANSFER_FUNCTION_BT1361,
.protocol_tf = WP_COLOR_MANAGER_V1_TRANSFER_FUNCTION_EXT_SRGB,
.count_parameters = 0,
},
{
.tf = WESTON_TF_ST240,
.desc = "SMPTE ST 240 transfer function",
.protocol_tf = XX_COLOR_MANAGER_V4_TRANSFER_FUNCTION_ST240,
.protocol_tf = WP_COLOR_MANAGER_V1_TRANSFER_FUNCTION_ST240,
.count_parameters = 0,
},
{
.tf = WESTON_TF_ST428,
.desc = "SMPTE ST 428 transfer function",
.protocol_tf = XX_COLOR_MANAGER_V4_TRANSFER_FUNCTION_ST428,
.protocol_tf = WP_COLOR_MANAGER_V1_TRANSFER_FUNCTION_ST428,
.count_parameters = 0,
},
{
.tf = WESTON_TF_ST2084_PQ,
.desc = "Perceptual quantizer transfer function",
.protocol_tf = XX_COLOR_MANAGER_V4_TRANSFER_FUNCTION_ST2084_PQ,
.protocol_tf = WP_COLOR_MANAGER_V1_TRANSFER_FUNCTION_ST2084_PQ,
.count_parameters = 0,
},
{
.tf = WESTON_TF_LOG_100,
.desc = "Logarithmic 100:1 transfer function",
.protocol_tf = XX_COLOR_MANAGER_V4_TRANSFER_FUNCTION_LOG_100,
.protocol_tf = WP_COLOR_MANAGER_V1_TRANSFER_FUNCTION_LOG_100,
.count_parameters = 0,
},
{
.tf = WESTON_TF_LOG_316,
.desc = "Logarithmic (100*Sqrt(10) : 1) transfer function",
.protocol_tf = XX_COLOR_MANAGER_V4_TRANSFER_FUNCTION_LOG_316,
.protocol_tf = WP_COLOR_MANAGER_V1_TRANSFER_FUNCTION_LOG_316,
.count_parameters = 0,
},
{
.tf = WESTON_TF_XVYCC,
.desc = "IEC 61966-2-4 transfer function",
.protocol_tf = XX_COLOR_MANAGER_V4_TRANSFER_FUNCTION_XVYCC,
.protocol_tf = WP_COLOR_MANAGER_V1_TRANSFER_FUNCTION_XVYCC,
.count_parameters = 0,
},
{
.tf = WESTON_TF_HLG,
.desc = "Hybrid log-gamma transfer function",
.protocol_tf = XX_COLOR_MANAGER_V4_TRANSFER_FUNCTION_HLG,
.protocol_tf = WP_COLOR_MANAGER_V1_TRANSFER_FUNCTION_HLG,
.count_parameters = 0,
},
{

View file

@ -540,6 +540,21 @@ struct weston_color_manager {
(*send_image_desc_info)(struct cm_image_desc_info *cm_image_desc_info,
struct weston_color_profile *cprof_base);
/** Given a color profile, returns a reference to a profile that is
* guaranteed to be parametric and which is equivalent to the given
* profile.
*
* \param cprof_base The color profile.
* \param errmsg On success, untouched. On failure, a pointer to a
* string describing the error is stored here. The string must be
* free()'d.
* \return A reference to an equivalent parametric color profile, or
* NULL on failure.
*/
struct weston_color_profile *
(*get_parametric_color_profile)(struct weston_color_profile *cprof_base,
char **errmsg);
/** Destroy a color transform after refcount fell to zero */
void
(*destroy_color_transform)(struct weston_color_transform *xform);

View file

@ -1042,7 +1042,7 @@ weston_surface_create(struct weston_compositor *compositor)
surface->current_protection = WESTON_HDCP_DISABLE;
surface->protection_mode = WESTON_SURFACE_PROTECTION_MODE_RELAXED;
wl_list_init(&surface->cm_feedback_surface_resource_list);
wl_list_init(&surface->cm_surface_feedback_resource_list);
surface->cm_surface = NULL;
/* The surfaces start with no color profile and render intent. It's up
@ -2758,7 +2758,7 @@ weston_surface_unref(struct weston_surface *surface)
struct wl_resource *cb, *next;
struct weston_view *ev, *nv;
struct weston_pointer_constraint *constraint, *next_constraint;
struct wl_resource *cm_feedback_surface_res, *cm_feedback_surface_res_tmp;
struct wl_resource *cm_surface_feedback_res, *cm_surface_feedback_res_tmp;
struct weston_paint_node *pnode, *pntmp;
if (!surface)
@ -2814,12 +2814,12 @@ weston_surface_unref(struct weston_surface *surface)
weston_color_profile_unref(surface->color_profile);
weston_color_profile_unref(surface->preferred_color_profile);
wl_resource_for_each_safe(cm_feedback_surface_res,
cm_feedback_surface_res_tmp,
&surface->cm_feedback_surface_resource_list) {
wl_list_remove(wl_resource_get_link(cm_feedback_surface_res));
wl_list_init(wl_resource_get_link(cm_feedback_surface_res));
wl_resource_set_user_data(cm_feedback_surface_res, NULL);
wl_resource_for_each_safe(cm_surface_feedback_res,
cm_surface_feedback_res_tmp,
&surface->cm_surface_feedback_resource_list) {
wl_list_remove(wl_resource_get_link(cm_surface_feedback_res));
wl_list_init(wl_resource_get_link(cm_surface_feedback_res));
wl_resource_set_user_data(cm_surface_feedback_res, NULL);
}
if (surface->cm_surface)
wl_resource_set_user_data(surface->cm_surface, NULL);

File diff suppressed because it is too large Load diff

View file

@ -1,7 +1,7 @@
dep_scanner = dependency('wayland-scanner', native: true)
prog_scanner = find_program(dep_scanner.get_variable(pkgconfig: 'wayland_scanner'))
dep_wp = dependency('wayland-protocols', version: '>= 1.33',
dep_wp = dependency('wayland-protocols', version: '>= 1.41',
fallback: ['wayland-protocols', 'wayland_protocols'])
dir_wp_base = dep_wp.get_variable(pkgconfig: 'pkgdatadir', internal: 'pkgdatadir')
@ -16,7 +16,7 @@ install_data(
)
generated_protocols = [
[ 'color-management-v1', 'internal' ],
[ 'color-management', 'staging', 'v1' ],
[ 'fullscreen-shell', 'unstable', 'v1' ],
[ 'fractional-scale', 'staging', 'v1' ],
[ 'input-method', 'unstable', 'v1' ],

File diff suppressed because it is too large Load diff

View file

@ -44,6 +44,7 @@ enum image_descr_info_event {
IMAGE_DESCR_INFO_EVENT_PRIMARIES,
IMAGE_DESCR_INFO_EVENT_TF_NAMED,
IMAGE_DESCR_INFO_EVENT_TF_POWER_EXP,
IMAGE_DESCR_INFO_EVENT_LUMINANCES,
IMAGE_DESCR_INFO_EVENT_TARGET_PRIMARIES,
IMAGE_DESCR_INFO_EVENT_TARGET_MAXCLL,
IMAGE_DESCR_INFO_EVENT_TARGET_MAXFALL,
@ -65,7 +66,7 @@ const struct lcms_pipeline pipeline_sRGB = {
};
struct image_description {
struct xx_image_description_v4 *xx_image_descr;
struct wp_image_description_v1 *wp_image_descr;
enum image_description_status {
CM_IMAGE_DESC_NOT_CREATED = 0,
@ -81,10 +82,11 @@ struct image_description {
uint32_t icc_size;
/* For parametric images descriptions. */
enum xx_color_manager_v4_primaries primaries_named;
enum wp_color_manager_v1_primaries primaries_named;
struct weston_color_gamut primaries;
enum xx_color_manager_v4_transfer_function tf_named;
enum wp_color_manager_v1_transfer_function tf_named;
float tf_power;
float min_lum, max_lum, ref_lum;
struct weston_color_gamut target_primaries;
float target_min_lum, target_max_lum;
float target_max_cll;
@ -92,7 +94,7 @@ struct image_description {
};
struct image_description_info {
struct xx_image_description_info_v4 *xx_image_description_info;
struct wp_image_description_info_v1 *wp_image_description_info;
struct image_description *image_descr;
/* Bitfield that holds what events the compositor has sent us through
@ -102,11 +104,11 @@ struct image_description_info {
};
struct color_manager {
struct xx_color_manager_v4 *manager;
struct wp_color_manager_v1 *manager;
struct xx_color_management_output_v4 *output;
struct xx_color_management_surface_v4 *surface;
struct xx_color_management_feedback_surface_v4 *feedback_surface;
struct wp_color_management_output_v1 *output;
struct wp_color_management_surface_v1 *surface;
struct wp_color_management_surface_feedback_v1 *surface_feedback;
struct wl_list image_descr_list; /* image_description::link */
@ -117,6 +119,8 @@ struct color_manager {
/* Bitfield that holds what rendering intents are supported. If enum
* supported_render_intent v is supported, bit v will be set to 1. */
uint32_t supported_rendering_intents;
bool done;
};
static struct image_description *
@ -131,12 +135,12 @@ static void
image_description_destroy(struct image_description *image_descr)
{
wl_list_remove(&image_descr->link);
xx_image_description_v4_destroy(image_descr->xx_image_descr);
wp_image_description_v1_destroy(image_descr->wp_image_descr);
free(image_descr);
}
static void
image_descr_ready(void *data, struct xx_image_description_v4 *xx_image_description_v4,
image_descr_ready(void *data, struct wp_image_description_v1 *wp_image_description_v1,
uint32_t identity)
{
struct image_description *image_descr = data;
@ -145,7 +149,7 @@ image_descr_ready(void *data, struct xx_image_description_v4 *xx_image_descripti
}
static void
image_descr_failed(void *data, struct xx_image_description_v4 *xx_image_description_v4,
image_descr_failed(void *data, struct wp_image_description_v1 *wp_image_description_v1,
uint32_t cause, const char *msg)
{
struct image_description *image_descr = data;
@ -156,7 +160,7 @@ image_descr_failed(void *data, struct xx_image_description_v4 *xx_image_descript
" cause: %u, msg: %s\n", cause, msg);
}
static const struct xx_image_description_v4_listener
static const struct wp_image_description_v1_listener
image_descr_iface = {
.ready = image_descr_ready,
.failed = image_descr_failed,
@ -174,7 +178,7 @@ image_descr_info_received(struct image_description_info *image_descr_info,
static void
image_descr_info_primaries(void *data,
struct xx_image_description_info_v4 *xx_image_description_info_v4,
struct wp_image_description_info_v1 *wp_image_description_info_v1,
int32_t r_x, int32_t r_y, int32_t g_x, int32_t g_y,
int32_t b_x, int32_t b_y, int32_t w_x, int32_t w_y)
{
@ -185,19 +189,19 @@ image_descr_info_primaries(void *data,
image_descr_info_received(image_descr_info,
IMAGE_DESCR_INFO_EVENT_PRIMARIES);
image_descr->primaries.primary[0].x = r_x / 10000.0;
image_descr->primaries.primary[0].y = r_y / 10000.0;
image_descr->primaries.primary[1].x = g_x / 10000.0;
image_descr->primaries.primary[1].y = g_y / 10000.0;
image_descr->primaries.primary[2].x = b_x / 10000.0;
image_descr->primaries.primary[2].y = b_y / 10000.0;
image_descr->primaries.white_point.x = w_x / 10000.0;
image_descr->primaries.white_point.y = w_y / 10000.0;
image_descr->primaries.primary[0].x = r_x / 1000000.0f;
image_descr->primaries.primary[0].y = r_y / 1000000.0f;
image_descr->primaries.primary[1].x = g_x / 1000000.0f;
image_descr->primaries.primary[1].y = g_y / 1000000.0f;
image_descr->primaries.primary[2].x = b_x / 1000000.0f;
image_descr->primaries.primary[2].y = b_y / 1000000.0f;
image_descr->primaries.white_point.x = w_x / 1000000.0f;
image_descr->primaries.white_point.y = w_y / 1000000.0f;
}
static void
image_descr_info_primaries_named(void *data,
struct xx_image_description_info_v4 *xx_image_description_info_v4,
struct wp_image_description_info_v1 *wp_image_description_info_v1,
uint32_t primaries)
{
struct image_description_info *image_descr_info = data;
@ -211,7 +215,7 @@ image_descr_info_primaries_named(void *data,
static void
image_descr_info_tf_named(void *data,
struct xx_image_description_info_v4 *xx_image_description_info_v4,
struct wp_image_description_info_v1 *wp_image_description_info_v1,
uint32_t tf)
{
struct image_description_info *image_descr_info = data;
@ -225,7 +229,7 @@ image_descr_info_tf_named(void *data,
static void
image_descr_info_tf_power(void *data,
struct xx_image_description_info_v4 *xx_image_description_info_v4,
struct wp_image_description_info_v1 *wp_image_description_info_v1,
uint32_t tf_power)
{
struct image_description_info *image_descr_info = data;
@ -237,9 +241,25 @@ image_descr_info_tf_power(void *data,
image_descr->tf_power = tf_power / 10000.0;
}
static void
image_descr_info_luminances(void *data,
struct wp_image_description_info_v1 *wp_image_description_info_v1,
uint32_t min_lum, uint32_t max_lum, uint32_t ref_lum)
{
struct image_description_info *image_descr_info = data;
struct image_description *image_descr = image_descr_info->image_descr;
image_descr_info_received(image_descr_info,
IMAGE_DESCR_INFO_EVENT_LUMINANCES);
image_descr->min_lum = min_lum / 10000.0;
image_descr->max_lum = max_lum;
image_descr->ref_lum = ref_lum;
}
static void
image_descr_info_target_primaries(void *data,
struct xx_image_description_info_v4 *xx_image_description_info_v4,
struct wp_image_description_info_v1 *wp_image_description_info_v1,
int32_t r_x, int32_t r_y, int32_t g_x, int32_t g_y,
int32_t b_x, int32_t b_y, int32_t w_x, int32_t w_y)
{
@ -249,19 +269,19 @@ image_descr_info_target_primaries(void *data,
image_descr_info_received(image_descr_info,
IMAGE_DESCR_INFO_EVENT_TARGET_PRIMARIES);
image_descr->target_primaries.primary[0].x = r_x / 10000.0;
image_descr->target_primaries.primary[0].y = r_y / 10000.0;
image_descr->target_primaries.primary[1].x = g_x / 10000.0;
image_descr->target_primaries.primary[1].y = g_y / 10000.0;
image_descr->target_primaries.primary[2].x = b_x / 10000.0;
image_descr->target_primaries.primary[2].y = b_y / 10000.0;
image_descr->target_primaries.white_point.x = w_x / 10000.0;
image_descr->target_primaries.white_point.y = w_y / 10000.0;
image_descr->target_primaries.primary[0].x = r_x / 1000000.0f;
image_descr->target_primaries.primary[0].y = r_y / 1000000.0f;
image_descr->target_primaries.primary[1].x = g_x / 1000000.0f;
image_descr->target_primaries.primary[1].y = g_y / 1000000.0f;
image_descr->target_primaries.primary[2].x = b_x / 1000000.0f;
image_descr->target_primaries.primary[2].y = b_y / 1000000.0f;
image_descr->target_primaries.white_point.x = w_x / 1000000.0f;
image_descr->target_primaries.white_point.y = w_y / 1000000.0f;
}
static void
image_descr_info_target_luminance(void *data,
struct xx_image_description_info_v4 *xx_image_description_info_v4,
struct wp_image_description_info_v1 *wp_image_description_info_v1,
uint32_t min_lum, uint32_t max_lum)
{
struct image_description_info *image_descr_info = data;
@ -276,7 +296,7 @@ image_descr_info_target_luminance(void *data,
static void
image_descr_info_target_max_cll(void *data,
struct xx_image_description_info_v4 *xx_image_description_info_v4,
struct wp_image_description_info_v1 *wp_image_description_info_v1,
uint32_t maxCLL)
{
struct image_description_info *image_descr_info = data;
@ -290,7 +310,7 @@ image_descr_info_target_max_cll(void *data,
static void
image_descr_info_target_max_fall(void *data,
struct xx_image_description_info_v4 *xx_image_description_info_v4,
struct wp_image_description_info_v1 *wp_image_description_info_v1,
uint32_t maxFALL)
{
struct image_description_info *image_descr_info = data;
@ -304,7 +324,7 @@ image_descr_info_target_max_fall(void *data,
static void
image_descr_info_icc_file_event(void *data,
struct xx_image_description_info_v4 *xx_image_description_info_v4,
struct wp_image_description_info_v1 *wp_image_description_info_v1,
int32_t icc_fd, uint32_t icc_size)
{
struct image_description_info *image_descr_info = data;
@ -337,6 +357,8 @@ are_events_received_valid(struct image_description_info *image_descr_info)
* parameters make sense. */
bool received_primaries, received_primaries_named;
bool received_tf_power, received_tf_named;
bool received_target_primaries;
bool received_lum, received_target_lum;
/* Should have received the primaries somewhow. */
received_primaries_named = (events_received >>
@ -362,19 +384,19 @@ are_events_received_valid(struct image_description_info *image_descr_info)
/* If we received tf named and exp power, they must match. */
if (received_tf_named && received_tf_power) {
if (image_descr->tf_named != XX_COLOR_MANAGER_V4_TRANSFER_FUNCTION_GAMMA22 &&
image_descr->tf_named != XX_COLOR_MANAGER_V4_TRANSFER_FUNCTION_GAMMA28) {
if (image_descr->tf_named != WP_COLOR_MANAGER_V1_TRANSFER_FUNCTION_GAMMA22 &&
image_descr->tf_named != WP_COLOR_MANAGER_V1_TRANSFER_FUNCTION_GAMMA28) {
testlog(" Error: parametric image description tf " \
"named is not pure power-law, but still received " \
"tf power event\n");
return false;
} else if (image_descr->tf_named == XX_COLOR_MANAGER_V4_TRANSFER_FUNCTION_GAMMA22 &&
} else if (image_descr->tf_named == WP_COLOR_MANAGER_V1_TRANSFER_FUNCTION_GAMMA22 &&
image_descr->tf_power != 2.2f) {
testlog(" Error: parametric image description tf named " \
"is pure power-law 2.2, but tf power received is %f\n",
image_descr->tf_power);
return false;
} else if (image_descr->tf_named == XX_COLOR_MANAGER_V4_TRANSFER_FUNCTION_GAMMA28 &&
} else if (image_descr->tf_named == WP_COLOR_MANAGER_V1_TRANSFER_FUNCTION_GAMMA28 &&
image_descr->tf_power != 2.8f) {
testlog(" Error: parametric image description tf named " \
"is pure power-law 2.8, but tf power received is %f\n",
@ -383,20 +405,44 @@ are_events_received_valid(struct image_description_info *image_descr_info)
}
}
/* TODO: when target primaries, luminance, maxcll and maxfall are
* allowed? */
/* We should receive luminance. */
received_lum = (events_received >>
IMAGE_DESCR_INFO_EVENT_LUMINANCES) & 1;
if (!received_lum) {
testlog(" Error: parametric image description but no " \
"luminances received\n");
return false;
}
/* We should receive target primaries. */
received_target_primaries = (events_received >>
IMAGE_DESCR_INFO_EVENT_TARGET_PRIMARIES) & 1;
if (!received_target_primaries) {
testlog(" Error: parametric image description but no " \
"target primaries received\n");
return false;
}
/* We should receive target luminance. */
received_target_lum = (events_received >>
IMAGE_DESCR_INFO_EVENT_TARGET_LUMINANCE) & 1;
if (!received_target_lum) {
testlog(" Error: parametric image description but no " \
"target luminances received\n");
return false;
}
return true;
}
static void
image_descr_info_done(void *data,
struct xx_image_description_info_v4 *xx_image_description_info_v4)
struct wp_image_description_info_v1 *wp_image_description_info_v1)
{
struct image_description_info *image_descr_info = data;
struct image_description *image_descr = image_descr_info->image_descr;
testlog("Image description info %p done:\n", xx_image_description_info_v4);
testlog("Image description info %p done:\n", wp_image_description_info_v1);
assert(are_events_received_valid(image_descr_info));
@ -459,12 +505,13 @@ image_descr_info_done(void *data,
testlog(" Target maxFALL: %.4f\n", image_descr->target_max_fall);
}
static const struct xx_image_description_info_v4_listener
static const struct wp_image_description_info_v1_listener
image_descr_info_iface = {
.primaries = image_descr_info_primaries,
.primaries_named = image_descr_info_primaries_named,
.tf_named = image_descr_info_tf_named,
.tf_power = image_descr_info_tf_power,
.luminances = image_descr_info_luminances,
.target_primaries = image_descr_info_target_primaries,
.target_luminance = image_descr_info_target_luminance,
.target_max_cll = image_descr_info_target_max_cll,
@ -474,7 +521,7 @@ image_descr_info_iface = {
};
static void
cm_supported_intent(void *data, struct xx_color_manager_v4 *xx_color_manager_v4,
cm_supported_intent(void *data, struct wp_color_manager_v1 *wp_color_manager_v1,
uint32_t render_intent)
{
struct color_manager *cm = data;
@ -483,7 +530,7 @@ cm_supported_intent(void *data, struct xx_color_manager_v4 *xx_color_manager_v4,
}
static void
cm_supported_feature(void *data, struct xx_color_manager_v4 *xx_color_manager_v4,
cm_supported_feature(void *data, struct wp_color_manager_v1 *wp_color_manager_v1,
uint32_t feature)
{
struct color_manager *cm = data;
@ -492,7 +539,7 @@ cm_supported_feature(void *data, struct xx_color_manager_v4 *xx_color_manager_v4
}
static void
cm_supported_tf_named(void *data, struct xx_color_manager_v4 *xx_color_manager_v4,
cm_supported_tf_named(void *data, struct wp_color_manager_v1 *wp_color_manager_v1,
uint32_t tf_code)
{
/* only used to create image descriptions using parameters, which we
@ -500,19 +547,28 @@ cm_supported_tf_named(void *data, struct xx_color_manager_v4 *xx_color_manager_v
}
static void
cm_supported_primaries_named(void *data, struct xx_color_manager_v4 *xx_color_manager_v4,
cm_supported_primaries_named(void *data, struct wp_color_manager_v1 *wp_color_manager_v1,
uint32_t primaries_code)
{
/* only used to create image descriptions using parameters, which we
* won't do in this test file. */
}
static const struct xx_color_manager_v4_listener
static void
cm_done(void *data, struct wp_color_manager_v1 *wp_color_manager_v1)
{
struct color_manager *cm = data;
cm->done = true;
}
static const struct wp_color_manager_v1_listener
cm_iface = {
.supported_intent = cm_supported_intent,
.supported_feature = cm_supported_feature,
.supported_tf_named = cm_supported_tf_named,
.supported_primaries_named = cm_supported_primaries_named,
.done = cm_done,
};
static void
@ -523,37 +579,39 @@ color_manager_init(struct color_manager *cm, struct client *client)
wl_list_init(&cm->image_descr_list);
cm->manager = bind_to_singleton_global(client,
&xx_color_manager_v4_interface,
&wp_color_manager_v1_interface,
1);
xx_color_manager_v4_add_listener(cm->manager, &cm_iface, cm);
wp_color_manager_v1_add_listener(cm->manager, &cm_iface, cm);
cm->output = xx_color_manager_v4_get_output(cm->manager,
cm->output = wp_color_manager_v1_get_output(cm->manager,
client->output->wl_output);
cm->surface = xx_color_manager_v4_get_surface(cm->manager,
cm->surface = wp_color_manager_v1_get_surface(cm->manager,
client->surface->wl_surface);
cm->feedback_surface =
xx_color_manager_v4_get_feedback_surface(cm->manager,
cm->surface_feedback =
wp_color_manager_v1_get_surface_feedback(cm->manager,
client->surface->wl_surface);
client_roundtrip(client);
/* Weston supports all color features. */
assert(cm->supported_features == ((1 << XX_COLOR_MANAGER_V4_FEATURE_ICC_V2_V4) |
(1 << XX_COLOR_MANAGER_V4_FEATURE_PARAMETRIC) |
(1 << XX_COLOR_MANAGER_V4_FEATURE_SET_PRIMARIES) |
(1 << XX_COLOR_MANAGER_V4_FEATURE_SET_TF_POWER) |
(1 << XX_COLOR_MANAGER_V4_FEATURE_SET_LUMINANCES) |
(1 << XX_COLOR_MANAGER_V4_FEATURE_SET_MASTERING_DISPLAY_PRIMARIES) |
(1 << XX_COLOR_MANAGER_V4_FEATURE_EXTENDED_TARGET_VOLUME)));
assert(cm->supported_features == ((1 << WP_COLOR_MANAGER_V1_FEATURE_ICC_V2_V4) |
(1 << WP_COLOR_MANAGER_V1_FEATURE_PARAMETRIC) |
(1 << WP_COLOR_MANAGER_V1_FEATURE_SET_PRIMARIES) |
(1 << WP_COLOR_MANAGER_V1_FEATURE_SET_TF_POWER) |
(1 << WP_COLOR_MANAGER_V1_FEATURE_SET_LUMINANCES) |
(1 << WP_COLOR_MANAGER_V1_FEATURE_SET_MASTERING_DISPLAY_PRIMARIES) |
(1 << WP_COLOR_MANAGER_V1_FEATURE_EXTENDED_TARGET_VOLUME)));
/* Weston supports all rendering intents. */
assert(cm->supported_rendering_intents == ((1 << XX_COLOR_MANAGER_V4_RENDER_INTENT_PERCEPTUAL) |
(1 << XX_COLOR_MANAGER_V4_RENDER_INTENT_RELATIVE) |
(1 << XX_COLOR_MANAGER_V4_RENDER_INTENT_SATURATION) |
(1 << XX_COLOR_MANAGER_V4_RENDER_INTENT_ABSOLUTE) |
(1 << XX_COLOR_MANAGER_V4_RENDER_INTENT_RELATIVE_BPC)));
assert(cm->supported_rendering_intents == ((1 << WP_COLOR_MANAGER_V1_RENDER_INTENT_PERCEPTUAL) |
(1 << WP_COLOR_MANAGER_V1_RENDER_INTENT_RELATIVE) |
(1 << WP_COLOR_MANAGER_V1_RENDER_INTENT_SATURATION) |
(1 << WP_COLOR_MANAGER_V1_RENDER_INTENT_ABSOLUTE) |
(1 << WP_COLOR_MANAGER_V1_RENDER_INTENT_RELATIVE_BPC)));
assert(cm->done);
}
static void
@ -564,10 +622,10 @@ color_manager_fini(struct color_manager *cm)
wl_list_for_each_safe(image_descr, tmp, &cm->image_descr_list, link)
image_description_destroy(image_descr);
xx_color_management_output_v4_destroy(cm->output);
xx_color_management_surface_v4_destroy(cm->surface);
xx_color_management_feedback_surface_v4_destroy(cm->feedback_surface);
xx_color_manager_v4_destroy(cm->manager);
wp_color_management_output_v1_destroy(cm->output);
wp_color_management_surface_v1_destroy(cm->surface);
wp_color_management_surface_feedback_v1_destroy(cm->surface_feedback);
wp_color_manager_v1_destroy(cm->manager);
}
static struct image_description *
@ -575,10 +633,10 @@ get_output_image_description(struct color_manager *cm)
{
struct image_description *image_descr = image_description_create();
image_descr->xx_image_descr =
xx_color_management_output_v4_get_image_description(cm->output);
image_descr->wp_image_descr =
wp_color_management_output_v1_get_image_description(cm->output);
xx_image_description_v4_add_listener(image_descr->xx_image_descr,
wp_image_description_v1_add_listener(image_descr->wp_image_descr,
&image_descr_iface, image_descr);
wl_list_insert(&cm->image_descr_list, &image_descr->link);
@ -591,10 +649,10 @@ get_surface_preferred_image_description(struct color_manager *cm)
{
struct image_description *image_descr = image_description_create();
image_descr->xx_image_descr =
xx_color_management_feedback_surface_v4_get_preferred(cm->feedback_surface);
image_descr->wp_image_descr =
wp_color_management_surface_feedback_v1_get_preferred(cm->surface_feedback);
xx_image_description_v4_add_listener(image_descr->xx_image_descr,
wp_image_description_v1_add_listener(image_descr->wp_image_descr,
&image_descr_iface, image_descr);
wl_list_insert(&cm->image_descr_list, &image_descr->link);
@ -604,7 +662,7 @@ get_surface_preferred_image_description(struct color_manager *cm)
static struct image_description *
create_icc_based_image_description(struct color_manager *cm,
struct xx_image_description_creator_icc_v4 *image_descr_creator_icc,
struct wp_image_description_creator_icc_v1 *image_descr_creator_icc,
const char *icc_path)
{
struct image_description *image_descr = image_description_create();
@ -616,12 +674,12 @@ create_icc_based_image_description(struct color_manager *cm,
assert(fstat(icc_fd, &st) == 0);
xx_image_description_creator_icc_v4_set_icc_file(image_descr_creator_icc,
wp_image_description_creator_icc_v1_set_icc_file(image_descr_creator_icc,
icc_fd, 0, st.st_size);
image_descr->xx_image_descr =
xx_image_description_creator_icc_v4_create(image_descr_creator_icc);
image_descr->wp_image_descr =
wp_image_description_creator_icc_v1_create(image_descr_creator_icc);
xx_image_description_v4_add_listener(image_descr->xx_image_descr,
wp_image_description_v1_add_listener(image_descr->wp_image_descr,
&image_descr_iface, image_descr);
wl_list_insert(&cm->image_descr_list, &image_descr->link);
@ -695,7 +753,7 @@ TEST(smoke_test)
static void
image_descr_info_destroy(struct image_description_info *image_descr_info)
{
xx_image_description_info_v4_destroy(image_descr_info->xx_image_description_info);
wp_image_description_info_v1_destroy(image_descr_info->wp_image_description_info);
free(image_descr_info);
}
@ -708,10 +766,10 @@ image_descr_get_information(struct image_description *image_descr)
image_descr_info->image_descr = image_descr;
image_descr_info->xx_image_description_info =
xx_image_description_v4_get_information(image_descr->xx_image_descr);
image_descr_info->wp_image_description_info =
wp_image_description_v1_get_information(image_descr->wp_image_descr);
xx_image_description_info_v4_add_listener(image_descr_info->xx_image_description_info,
wp_image_description_info_v1_add_listener(image_descr_info->wp_image_description_info,
&image_descr_info_iface,
image_descr_info);
@ -778,14 +836,14 @@ TEST(create_image_description_before_setting_icc_file)
{
struct client *client;
struct color_manager cm;
struct xx_image_description_creator_icc_v4 *image_descr_creator_icc;
struct xx_image_description_v4 *image_desc;
struct wp_image_description_creator_icc_v1 *image_descr_creator_icc;
struct wp_image_description_v1 *image_desc;
client = create_client_and_test_surface(100, 100, 100, 100);
color_manager_init(&cm, client);
image_descr_creator_icc =
xx_color_manager_v4_new_icc_creator(cm.manager);
wp_color_manager_v1_create_icc_creator(cm.manager);
/* Try creating image description based on ICC profile but without
* setting the ICC file, what should fail.
@ -793,11 +851,11 @@ TEST(create_image_description_before_setting_icc_file)
* We expect a protocol error from unknown object, because the
* image_descr_creator_icc wl_proxy will get destroyed with the create
* call below. It is a destructor request. */
image_desc = xx_image_description_creator_icc_v4_create(image_descr_creator_icc);
image_desc = wp_image_description_creator_icc_v1_create(image_descr_creator_icc);
expect_protocol_error(client, NULL,
XX_IMAGE_DESCRIPTION_CREATOR_ICC_V4_ERROR_INCOMPLETE_SET);
WP_IMAGE_DESCRIPTION_CREATOR_ICC_V1_ERROR_INCOMPLETE_SET);
xx_image_description_v4_destroy(image_desc);
wp_image_description_v1_destroy(image_desc);
color_manager_fini(&cm);
client_destroy(client);
}
@ -806,7 +864,7 @@ TEST(set_unreadable_icc_fd)
{
struct client *client;
struct color_manager cm;
struct xx_image_description_creator_icc_v4 *image_descr_creator_icc;
struct wp_image_description_creator_icc_v1 *image_descr_creator_icc;
int32_t icc_fd;
struct stat st;
@ -814,7 +872,7 @@ TEST(set_unreadable_icc_fd)
color_manager_init(&cm, client);
image_descr_creator_icc =
xx_color_manager_v4_new_icc_creator(cm.manager);
wp_color_manager_v1_create_icc_creator(cm.manager);
/* The file is being open with WRITE, not READ permission. So the
* compositor should complain. */
@ -823,13 +881,13 @@ TEST(set_unreadable_icc_fd)
assert(fstat(icc_fd, &st) == 0);
/* Try setting the bad ICC file fd, it should fail. */
xx_image_description_creator_icc_v4_set_icc_file(image_descr_creator_icc,
wp_image_description_creator_icc_v1_set_icc_file(image_descr_creator_icc,
icc_fd, 0, st.st_size);
expect_protocol_error(client, &xx_image_description_creator_icc_v4_interface,
XX_IMAGE_DESCRIPTION_CREATOR_ICC_V4_ERROR_BAD_FD);
expect_protocol_error(client, &wp_image_description_creator_icc_v1_interface,
WP_IMAGE_DESCRIPTION_CREATOR_ICC_V1_ERROR_BAD_FD);
close(icc_fd);
xx_image_description_creator_icc_v4_destroy(image_descr_creator_icc);
wp_image_description_creator_icc_v1_destroy(image_descr_creator_icc);
color_manager_fini(&cm);
client_destroy(client);
}
@ -838,26 +896,26 @@ TEST(set_bad_icc_size_zero)
{
struct client *client;
struct color_manager cm;
struct xx_image_description_creator_icc_v4 *image_descr_creator_icc;
struct wp_image_description_creator_icc_v1 *image_descr_creator_icc;
int32_t icc_fd;
client = create_client_and_test_surface(100, 100, 100, 100);
color_manager_init(&cm, client);
image_descr_creator_icc =
xx_color_manager_v4_new_icc_creator(cm.manager);
wp_color_manager_v1_create_icc_creator(cm.manager);
icc_fd = open(srgb_icc_profile_path, O_RDONLY);
assert(icc_fd >= 0);
/* Try setting ICC file with a bad size, it should fail. */
xx_image_description_creator_icc_v4_set_icc_file(image_descr_creator_icc,
wp_image_description_creator_icc_v1_set_icc_file(image_descr_creator_icc,
icc_fd, 0, 0);
expect_protocol_error(client, &xx_image_description_creator_icc_v4_interface,
XX_IMAGE_DESCRIPTION_CREATOR_ICC_V4_ERROR_BAD_SIZE);
expect_protocol_error(client, &wp_image_description_creator_icc_v1_interface,
WP_IMAGE_DESCRIPTION_CREATOR_ICC_V1_ERROR_BAD_SIZE);
close(icc_fd);
xx_image_description_creator_icc_v4_destroy(image_descr_creator_icc);
wp_image_description_creator_icc_v1_destroy(image_descr_creator_icc);
color_manager_fini(&cm);
client_destroy(client);
}
@ -866,28 +924,28 @@ TEST(set_bad_icc_non_seekable)
{
struct client *client;
struct color_manager cm;
struct xx_image_description_creator_icc_v4 *image_descr_creator_icc;
struct wp_image_description_creator_icc_v1 *image_descr_creator_icc;
int32_t fds[2];
client = create_client_and_test_surface(100, 100, 100, 100);
color_manager_init(&cm, client);
image_descr_creator_icc =
xx_color_manager_v4_new_icc_creator(cm.manager);
wp_color_manager_v1_create_icc_creator(cm.manager);
/* We need a non-seekable file, and pipes are non-seekable. */
assert(pipe(fds) >= 0);
/* Pretend that it has a valid size of 1024 bytes. That still should
* fail because the fd is non-seekable. */
xx_image_description_creator_icc_v4_set_icc_file(image_descr_creator_icc,
wp_image_description_creator_icc_v1_set_icc_file(image_descr_creator_icc,
fds[0], 0, 1024);
expect_protocol_error(client, &xx_image_description_creator_icc_v4_interface,
XX_IMAGE_DESCRIPTION_CREATOR_ICC_V4_ERROR_BAD_FD);
expect_protocol_error(client, &wp_image_description_creator_icc_v1_interface,
WP_IMAGE_DESCRIPTION_CREATOR_ICC_V1_ERROR_BAD_FD);
close(fds[0]);
close(fds[1]);
xx_image_description_creator_icc_v4_destroy(image_descr_creator_icc);
wp_image_description_creator_icc_v1_destroy(image_descr_creator_icc);
color_manager_fini(&cm);
client_destroy(client);
}
@ -896,7 +954,7 @@ TEST(set_icc_twice)
{
struct client *client;
struct color_manager cm;
struct xx_image_description_creator_icc_v4 *image_descr_creator_icc;
struct wp_image_description_creator_icc_v1 *image_descr_creator_icc;
int32_t icc_fd;
struct stat st;
@ -904,24 +962,24 @@ TEST(set_icc_twice)
color_manager_init(&cm, client);
image_descr_creator_icc =
xx_color_manager_v4_new_icc_creator(cm.manager);
wp_color_manager_v1_create_icc_creator(cm.manager);
icc_fd = open(srgb_icc_profile_path, O_RDONLY);
assert(icc_fd >= 0);
assert(fstat(icc_fd, &st) == 0);
xx_image_description_creator_icc_v4_set_icc_file(image_descr_creator_icc,
wp_image_description_creator_icc_v1_set_icc_file(image_descr_creator_icc,
icc_fd, 0, st.st_size);
client_roundtrip(client);
/* Set the ICC again, what should fail. */
xx_image_description_creator_icc_v4_set_icc_file(image_descr_creator_icc,
wp_image_description_creator_icc_v1_set_icc_file(image_descr_creator_icc,
icc_fd, 0, st.st_size);
expect_protocol_error(client, &xx_image_description_creator_icc_v4_interface,
XX_IMAGE_DESCRIPTION_CREATOR_ICC_V4_ERROR_ALREADY_SET);
expect_protocol_error(client, &wp_image_description_creator_icc_v1_interface,
WP_IMAGE_DESCRIPTION_CREATOR_ICC_V1_ERROR_ALREADY_SET);
close(icc_fd);
xx_image_description_creator_icc_v4_destroy(image_descr_creator_icc);
wp_image_description_creator_icc_v1_destroy(image_descr_creator_icc);
color_manager_fini(&cm);
client_destroy(client);
}
@ -930,7 +988,7 @@ TEST(create_icc_image_description_no_info)
{
struct client *client;
struct color_manager cm;
struct xx_image_description_creator_icc_v4 *image_descr_creator_icc;
struct wp_image_description_creator_icc_v1 *image_descr_creator_icc;
struct image_description *image_descr;
struct image_description_info *image_descr_info;
@ -938,7 +996,7 @@ TEST(create_icc_image_description_no_info)
color_manager_init(&cm, client);
image_descr_creator_icc =
xx_color_manager_v4_new_icc_creator(cm.manager);
wp_color_manager_v1_create_icc_creator(cm.manager);
/* Create image description based on ICC profile */
image_descr = create_icc_based_image_description(&cm, image_descr_creator_icc,
@ -948,8 +1006,8 @@ TEST(create_icc_image_description_no_info)
/* Get image description information, and that should fail. Images
* descriptions that we create do not accept this request. */
image_descr_info = image_descr_get_information(image_descr);
expect_protocol_error(client, &xx_image_description_v4_interface,
XX_IMAGE_DESCRIPTION_V4_ERROR_NO_INFORMATION);
expect_protocol_error(client, &wp_image_description_v1_interface,
WP_IMAGE_DESCRIPTION_V1_ERROR_NO_INFORMATION);
image_descr_info_destroy(image_descr_info);
color_manager_fini(&cm);
@ -960,14 +1018,14 @@ TEST(set_surface_image_description)
{
struct client *client;
struct color_manager cm;
struct xx_image_description_creator_icc_v4 *image_descr_creator_icc;
struct wp_image_description_creator_icc_v1 *image_descr_creator_icc;
struct image_description *image_descr;
client = create_client_and_test_surface(100, 100, 100, 100);
color_manager_init(&cm, client);
image_descr_creator_icc =
xx_color_manager_v4_new_icc_creator(cm.manager);
wp_color_manager_v1_create_icc_creator(cm.manager);
/* Create image description based on ICC profile */
image_descr = create_icc_based_image_description(&cm, image_descr_creator_icc,
@ -975,9 +1033,9 @@ TEST(set_surface_image_description)
wait_until_image_description_ready(client, image_descr);
/* Set surface image description */
xx_color_management_surface_v4_set_image_description(cm.surface,
image_descr->xx_image_descr,
XX_COLOR_MANAGER_V4_RENDER_INTENT_PERCEPTUAL);
wp_color_management_surface_v1_set_image_description(cm.surface,
image_descr->wp_image_descr,
WP_COLOR_MANAGER_V1_RENDER_INTENT_PERCEPTUAL);
client_roundtrip(client);
color_manager_fini(&cm);