libweston: Add support to set content-protection for a weston_surface

The protection requested for a given surface, must reach through the
weston_surface::pending_state, in the commit-cycle for the
weston_surface, so that it gets updated in the next commit.

As some protection is requested for a given weston_surface, it means
protection must be set for each of the outputs which show the surface.

While setting the protection of a weston_output, care must be taken
so as to avoid, degrading the protection of another surfaces, enjoying
the protection. For this purpose, all the weston_surfaces that are
shown on a weston_output are checked for their desired protection.
The highest of all such desired protections must be set for the
weston_output to avoid degrading of existing protected surfaces.
A surface requesting protection for a lower content-type can still be
provided protection for a higher type but the converse cannot be
allowed.

This patch adds support to set content-protection for a suface, which
inturn sets the content-protection for each of the outputs on which
it is shown, provided, none of the existing surface's protection
request is downgraded.

Signed-off-by: Ankit Nautiyal <ankit.k.nautiyal@intel.com>
dev
Ankit Nautiyal 6 years ago
parent 4f64ff8b2f
commit 4b6e73d617
  1. 5
      include/libweston/libweston.h
  2. 37
      libweston/compositor.c

@ -1439,6 +1439,9 @@ struct weston_surface_state {
/* zwp_surface_synchronization_v1.get_release */ /* zwp_surface_synchronization_v1.get_release */
struct weston_buffer_release_reference buffer_release_ref; struct weston_buffer_release_reference buffer_release_ref;
/* weston_protected_surface.set_type */
enum weston_hdcp_protection desired_protection;
}; };
struct weston_surface_activation_data { struct weston_surface_activation_data {
@ -1568,6 +1571,8 @@ struct weston_surface {
struct wl_resource *synchronization_resource; struct wl_resource *synchronization_resource;
int acquire_fence_fd; int acquire_fence_fd;
struct weston_buffer_release_reference buffer_release_ref; struct weston_buffer_release_reference buffer_release_ref;
enum weston_hdcp_protection desired_protection;
}; };
struct weston_subsurface { struct weston_subsurface {

@ -479,6 +479,8 @@ weston_surface_state_init(struct weston_surface_state *state)
state->buffer_viewport.changed = 0; state->buffer_viewport.changed = 0;
state->acquire_fence_fd = -1; state->acquire_fence_fd = -1;
state->desired_protection = WESTON_HDCP_DISABLE;
} }
static void static void
@ -561,6 +563,8 @@ weston_surface_create(struct weston_compositor *compositor)
surface->acquire_fence_fd = -1; surface->acquire_fence_fd = -1;
surface->desired_protection = WESTON_HDCP_DISABLE;
return surface; return surface;
} }
@ -2528,6 +2532,7 @@ weston_output_repaint(struct weston_output *output, void *repaint_data)
pixman_region32_t output_damage; pixman_region32_t output_damage;
int r; int r;
uint32_t frame_time_msec; uint32_t frame_time_msec;
enum weston_hdcp_protection highest_requested = WESTON_HDCP_DISABLE;
if (output->destroying) if (output->destroying)
return 0; return 0;
@ -2537,6 +2542,23 @@ weston_output_repaint(struct weston_output *output, void *repaint_data)
/* Rebuild the surface list and update surface transforms up front. */ /* Rebuild the surface list and update surface transforms up front. */
weston_compositor_build_view_list(ec); weston_compositor_build_view_list(ec);
/* Find the highest protection desired for an output */
wl_list_for_each(ev, &ec->view_list, link) {
if (ev->surface->output_mask & (1u << output->id)) {
/*
* The desired_protection of the output should be the
* maximum of the desired_protection of the surfaces,
* that are displayed on that output, to avoid
* reducing the protection for existing surfaces.
*/
if (ev->surface->desired_protection > highest_requested)
highest_requested =
ev->surface->desired_protection;
}
}
output->desired_protection = highest_requested;
if (output->assign_planes && !output->disable_planes) { if (output->assign_planes && !output->disable_planes) {
output->assign_planes(output, repaint_data); output->assign_planes(output, repaint_data);
} else { } else {
@ -3328,6 +3350,16 @@ apply_damage_buffer(pixman_region32_t *dest,
pixman_region32_clear(&state->damage_buffer); pixman_region32_clear(&state->damage_buffer);
} }
static void
weston_surface_set_desired_protection(struct weston_surface *surface,
enum weston_hdcp_protection protection)
{
if (surface->desired_protection == protection)
return;
surface->desired_protection = protection;
weston_surface_damage(surface);
}
static void static void
weston_surface_commit_state(struct weston_surface *surface, weston_surface_commit_state(struct weston_surface *surface,
struct weston_surface_state *state) struct weston_surface_state *state)
@ -3349,7 +3381,6 @@ weston_surface_commit_state(struct weston_surface *surface,
/* zwp_surface_synchronization_v1.get_release */ /* zwp_surface_synchronization_v1.get_release */
weston_buffer_release_move(&surface->buffer_release_ref, weston_buffer_release_move(&surface->buffer_release_ref,
&state->buffer_release_ref); &state->buffer_release_ref);
weston_surface_attach(surface, state->buffer); weston_surface_attach(surface, state->buffer);
} }
weston_surface_state_set_buffer(state, NULL); weston_surface_state_set_buffer(state, NULL);
@ -3419,6 +3450,9 @@ weston_surface_commit_state(struct weston_surface *surface,
&state->feedback_list); &state->feedback_list);
wl_list_init(&state->feedback_list); wl_list_init(&state->feedback_list);
/* weston_protected_surface.set_type */
weston_surface_set_desired_protection(surface, state->desired_protection);
wl_signal_emit(&surface->commit_signal, surface); wl_signal_emit(&surface->commit_signal, surface);
} }
@ -3718,6 +3752,7 @@ weston_subsurface_commit_to_cache(struct weston_subsurface *sub)
weston_buffer_release_move(&sub->cached.buffer_release_ref, weston_buffer_release_move(&sub->cached.buffer_release_ref,
&surface->pending.buffer_release_ref); &surface->pending.buffer_release_ref);
} }
sub->cached.desired_protection = surface->pending.desired_protection;
assert(surface->pending.acquire_fence_fd == -1); assert(surface->pending.acquire_fence_fd == -1);
assert(surface->pending.buffer_release_ref.buffer_release == NULL); assert(surface->pending.buffer_release_ref.buffer_release == NULL);
sub->cached.sx += surface->pending.sx; sub->cached.sx += surface->pending.sx;

Loading…
Cancel
Save