[PATCH 3/7] compositor: Let renderers create and destroy surface state on their own

Ander Conselvan de Oliveira conselvan2 at gmail.com
Mon Oct 28 09:38:18 CET 2013


On 10/25/2013 06:27 PM, Jason Ekstrand wrote:
> Ander,
> When I was working on views, I really wanted to get rid of the
> create_surface functions too... Thanks.  That said, you should probably
> also get rid of create_view (It's only used by rpi).

I wrote these patches before the views work was merged, and when I 
rebased I tried not to change it much. Maybe this can be a follow up patch.

Ander

> --Jason Ekstrand
>
>
> On Fri, Oct 25, 2013 at 8:26 AM, Ander Conselvan de Oliveira
> <ander.conselvan.de.oliveira at intel.com
> <mailto:ander.conselvan.de.oliveira at intel.com>> wrote:
>
>     Remove create_surface() and destroy_surface() from the renderer
>     interface and change the renderers to create surface state on demand
>     and destroy it using the weston_surface's destroy signal.
>
>     Also make sure the surfaces' renderer state is reset to NULL on
>     destruction.
>
>     This is a step towards runtime switchable renderers.
>
>     (rpi-renderer changes are only compile-tested)
>     ---
>       src/compositor.c      |    8 -------
>       src/compositor.h      |    2 --
>       src/gl-renderer.c     |   61
>     ++++++++++++++++++++++++++++++++++---------------
>       src/noop-renderer.c   |   13 -----------
>       src/pixman-renderer.c |   50 ++++++++++++++++++++++++++++------------
>       src/rpi-renderer.c    |   54
>     ++++++++++++++++++++++++++++---------------
>       6 files changed, 112 insertions(+), 76 deletions(-)
>
>     diff --git a/src/compositor.c b/src/compositor.c
>     index 2ed6b1e..563bade 100644
>     --- a/src/compositor.c
>     +++ b/src/compositor.c
>     @@ -407,11 +407,6 @@ weston_surface_create(struct weston_compositor
>     *compositor)
>              surface->compositor = compositor;
>              surface->ref_count = 1;
>
>     -       if (compositor->renderer->create_surface(surface) < 0) {
>     -               free(surface);
>     -               return NULL;
>     -       }
>     -
>              surface->buffer_transform = WL_OUTPUT_TRANSFORM_NORMAL;
>              surface->buffer_scale = 1;
>              surface->pending.buffer_transform = surface->buffer_transform;
>     @@ -1220,7 +1215,6 @@ weston_view_destroy(struct weston_view *view)
>       WL_EXPORT void
>       weston_surface_destroy(struct weston_surface *surface)
>       {
>     -       struct weston_compositor *compositor = surface->compositor;
>              struct weston_frame_callback *cb, *next;
>              struct weston_view *ev, *nv;
>
>     @@ -1248,8 +1242,6 @@ weston_surface_destroy(struct weston_surface
>     *surface)
>
>              weston_buffer_reference(&surface->buffer_ref, NULL);
>
>     -       compositor->renderer->destroy_surface(surface);
>     -
>              pixman_region32_fini(&surface->damage);
>              pixman_region32_fini(&surface->opaque);
>              pixman_region32_fini(&surface->input);
>     diff --git a/src/compositor.h b/src/compositor.h
>     index 73722b5..e60a512 100644
>     --- a/src/compositor.h
>     +++ b/src/compositor.h
>     @@ -521,12 +521,10 @@ struct weston_renderer {
>                                     pixman_region32_t *output_damage);
>              void (*flush_damage)(struct weston_surface *surface);
>              void (*attach)(struct weston_surface *es, struct
>     weston_buffer *buffer);
>     -       int (*create_surface)(struct weston_surface *surface);
>              int (*create_view)(struct weston_view *view);
>              void (*surface_set_color)(struct weston_surface *surface,
>                                     float red, float green,
>                                     float blue, float alpha);
>     -       void (*destroy_surface)(struct weston_surface *surface);
>              void (*destroy_view)(struct weston_view *view);
>              void (*destroy)(struct weston_compositor *ec);
>       };
>     diff --git a/src/gl-renderer.c b/src/gl-renderer.c
>     index 0f0b5f7..d792530 100644
>     --- a/src/gl-renderer.c
>     +++ b/src/gl-renderer.c
>     @@ -79,6 +79,10 @@ struct gl_surface_state {
>              int pitch; /* in pixels */
>              int height; /* in pixels */
>              int y_inverted;
>     +
>     +       struct weston_surface *surface;
>     +
>     +       struct wl_listener surface_destroy_listener;
>       };
>
>       struct gl_renderer {
>     @@ -134,9 +138,15 @@ get_output_state(struct weston_output *output)
>              return (struct gl_output_state *)output->renderer_state;
>       }
>
>     +static int
>     +gl_renderer_create_surface(struct weston_surface *surface);
>     +
>       static inline struct gl_surface_state *
>       get_surface_state(struct weston_surface *surface)
>       {
>     +       if (!surface->renderer_state)
>     +               gl_renderer_create_surface(surface);
>     +
>              return (struct gl_surface_state *)surface->renderer_state;
>       }
>
>     @@ -997,6 +1007,8 @@ gl_renderer_attach_shm(struct weston_surface
>     *es, struct weston_buffer *buffer,
>                      gs->needs_full_upload = 1;
>                      gs->y_inverted = 1;
>
>     +               gs->surface = surface;
>     +
>                      ensure_textures(gs, 1);
>                      glBindTexture(GL_TEXTURE_2D, gs->textures[0]);
>                      glTexImage2D(GL_TEXTURE_2D, 0, GL_BGRA_EXT,
>     @@ -1136,6 +1148,31 @@ gl_renderer_surface_set_color(struct
>     weston_surface *surface,
>              gs->shader = &gr->solid_shader;
>       }
>
>     +static void
>     +surface_state_handle_surface_destroy(struct wl_listener *listener,
>     void *data)
>     +{
>     +       struct gl_surface_state *gs;
>     +       struct gl_renderer *gr;
>     +       struct weston_surface *surface = data;
>     +       int i;
>     +
>     +       gr = get_renderer(surface->compositor);
>     +
>     +       gs = container_of(listener, struct gl_surface_state,
>     +                         surface_destroy_listener);
>     +
>     +       gs->surface->renderer_state = NULL;
>     +
>     +       glDeleteTextures(gs->num_textures, gs->textures);
>     +
>     +       for (i = 0; i < gs->num_images; i++)
>     +               gr->destroy_image(gr->egl_display, gs->images[i]);
>     +
>     +       weston_buffer_reference(&gs->buffer_ref, NULL);
>     +       pixman_region32_fini(&gs->texture_damage);
>     +       free(gs);
>     +}
>     +
>       static int
>       gl_renderer_create_surface(struct weston_surface *surface)
>       {
>     @@ -1155,24 +1192,12 @@ gl_renderer_create_surface(struct
>     weston_surface *surface)
>              pixman_region32_init(&gs->texture_damage);
>              surface->renderer_state = gs;
>
>     -       return 0;
>     -}
>     +       gs->surface_destroy_listener.notify =
>     +               surface_state_handle_surface_destroy;
>     +       wl_signal_add(&surface->destroy_signal,
>     +                     &gs->surface_destroy_listener);
>
>     -static void
>     -gl_renderer_destroy_surface(struct weston_surface *surface)
>     -{
>     -       struct gl_surface_state *gs = get_surface_state(surface);
>     -       struct gl_renderer *gr = get_renderer(surface->compositor);
>     -       int i;
>     -
>     -       glDeleteTextures(gs->num_textures, gs->textures);
>     -
>     -       for (i = 0; i < gs->num_images; i++)
>     -               gr->destroy_image(gr->egl_display, gs->images[i]);
>     -
>     -       weston_buffer_reference(&gs->buffer_ref, NULL);
>     -       pixman_region32_fini(&gs->texture_damage);
>     -       free(gs);
>     +       return 0;
>       }
>
>       static const char vertex_shader[] =
>     @@ -1655,9 +1680,7 @@ gl_renderer_create(struct weston_compositor
>     *ec, EGLNativeDisplayType display,
>              gr->base.repaint_output = gl_renderer_repaint_output;
>              gr->base.flush_damage = gl_renderer_flush_damage;
>              gr->base.attach = gl_renderer_attach;
>     -       gr->base.create_surface = gl_renderer_create_surface;
>              gr->base.surface_set_color = gl_renderer_surface_set_color;
>     -       gr->base.destroy_surface = gl_renderer_destroy_surface;
>              gr->base.destroy = gl_renderer_destroy;
>
>              gr->egl_display = eglGetDisplay(display);
>     diff --git a/src/noop-renderer.c b/src/noop-renderer.c
>     index 91659f5..ad750b5 100644
>     --- a/src/noop-renderer.c
>     +++ b/src/noop-renderer.c
>     @@ -51,12 +51,6 @@ noop_renderer_attach(struct weston_surface *es,
>     struct weston_buffer *buffer)
>       {
>       }
>
>     -static int
>     -noop_renderer_create_surface(struct weston_surface *surface)
>     -{
>     -       return 0;
>     -}
>     -
>       static void
>       noop_renderer_surface_set_color(struct weston_surface *surface,
>                       float red, float green, float blue, float alpha)
>     @@ -64,11 +58,6 @@ noop_renderer_surface_set_color(struct
>     weston_surface *surface,
>       }
>
>       static void
>     -noop_renderer_destroy_surface(struct weston_surface *surface)
>     -{
>     -}
>     -
>     -static void
>       noop_renderer_destroy(struct weston_compositor *ec)
>       {
>              free(ec->renderer);
>     @@ -88,9 +77,7 @@ noop_renderer_init(struct weston_compositor *ec)
>              renderer->repaint_output = noop_renderer_repaint_output;
>              renderer->flush_damage = noop_renderer_flush_damage;
>              renderer->attach = noop_renderer_attach;
>     -       renderer->create_surface = noop_renderer_create_surface;
>              renderer->surface_set_color = noop_renderer_surface_set_color;
>     -       renderer->destroy_surface = noop_renderer_destroy_surface;
>              renderer->destroy = noop_renderer_destroy;
>              ec->renderer = renderer;
>
>     diff --git a/src/pixman-renderer.c b/src/pixman-renderer.c
>     index 0d85e07..98a910c 100644
>     --- a/src/pixman-renderer.c
>     +++ b/src/pixman-renderer.c
>     @@ -37,8 +37,12 @@ struct pixman_output_state {
>       };
>
>       struct pixman_surface_state {
>     +       struct weston_surface *surface;
>     +
>              pixman_image_t *image;
>              struct weston_buffer_reference buffer_ref;
>     +
>     +       struct wl_listener surface_destroy_listener;
>       };
>
>       struct pixman_renderer {
>     @@ -55,9 +59,15 @@ get_output_state(struct weston_output *output)
>              return (struct pixman_output_state *)output->renderer_state;
>       }
>
>     +static int
>     +pixman_renderer_create_surface(struct weston_surface *surface);
>     +
>       static inline struct pixman_surface_state *
>       get_surface_state(struct weston_surface *surface)
>       {
>     +       if (!surface->renderer_state)
>     +               pixman_renderer_create_surface(surface);
>     +
>              return (struct pixman_surface_state *)surface->renderer_state;
>       }
>
>     @@ -582,6 +592,24 @@ pixman_renderer_attach(struct weston_surface
>     *es, struct weston_buffer *buffer)
>                      wl_shm_buffer_get_stride(shm_buffer));
>       }
>
>     +static void
>     +surface_state_handle_surface_destroy(struct wl_listener *listener,
>     void *data)
>     +{
>     +       struct pixman_surface_state *ps;
>     +
>     +       ps = container_of(listener, struct pixman_surface_state,
>     +                         surface_destroy_listener);
>     +
>     +       ps->surface->renderer_state = NULL;
>     +
>     +       if (ps->image) {
>     +               pixman_image_unref(ps->image);
>     +               ps->image = NULL;
>     +       }
>     +       weston_buffer_reference(&ps->buffer_ref, NULL);
>     +       free(ps);
>     +}
>     +
>       static int
>       pixman_renderer_create_surface(struct weston_surface *surface)
>       {
>     @@ -593,6 +621,13 @@ pixman_renderer_create_surface(struct
>     weston_surface *surface)
>
>              surface->renderer_state = ps;
>
>     +       ps->surface = surface;
>     +
>     +       ps->surface_destroy_listener.notify =
>     +               surface_state_handle_surface_destroy;
>     +       wl_signal_add(&surface->destroy_signal,
>     +                     &ps->surface_destroy_listener);
>     +
>              return 0;
>       }
>
>     @@ -617,19 +652,6 @@ pixman_renderer_surface_set_color(struct
>     weston_surface *es,
>       }
>
>       static void
>     -pixman_renderer_destroy_surface(struct weston_surface *surface)
>     -{
>     -       struct pixman_surface_state *ps = get_surface_state(surface);
>     -
>     -       if (ps->image) {
>     -               pixman_image_unref(ps->image);
>     -               ps->image = NULL;
>     -       }
>     -       weston_buffer_reference(&ps->buffer_ref, NULL);
>     -       free(ps);
>     -}
>     -
>     -static void
>       pixman_renderer_destroy(struct weston_compositor *ec)
>       {
>              struct pixman_renderer *pr = get_renderer(ec);
>     @@ -676,9 +698,7 @@ pixman_renderer_init(struct weston_compositor *ec)
>              renderer->base.repaint_output = pixman_renderer_repaint_output;
>              renderer->base.flush_damage = pixman_renderer_flush_damage;
>              renderer->base.attach = pixman_renderer_attach;
>     -       renderer->base.create_surface = pixman_renderer_create_surface;
>              renderer->base.surface_set_color =
>     pixman_renderer_surface_set_color;
>     -       renderer->base.destroy_surface =
>     pixman_renderer_destroy_surface;
>              renderer->base.destroy = pixman_renderer_destroy;
>              ec->renderer = &renderer->base;
>              ec->capabilities |= WESTON_CAP_ROTATION_ANY;
>     diff --git a/src/rpi-renderer.c b/src/rpi-renderer.c
>     index ea48b08..5de4d43 100644
>     --- a/src/rpi-renderer.c
>     +++ b/src/rpi-renderer.c
>     @@ -120,6 +120,8 @@ struct rpir_surface {
>
>              struct weston_buffer_reference buffer_ref;
>              enum buffer_type buffer_type;
>     +
>     +       struct wl_listener surface_destroy_listener;
>       };
>
>       struct rpir_view {
>     @@ -167,9 +169,15 @@ struct rpi_renderer {
>              int has_bind_display;
>       };
>
>     +static int
>     +rpi_renderer_create_surface(struct weston_surface *base);
>     +
>       static inline struct rpir_surface *
>       to_rpir_surface(struct weston_surface *surface)
>       {
>     +       if (!surface->renderer_state)
>     +               rpi_renderer_create_surface(surface);
>     +
>              return surface->renderer_state;
>       }
>
>     @@ -1395,6 +1403,27 @@ rpi_renderer_attach(struct weston_surface
>     *base, struct weston_buffer *buffer)
>              }
>       }
>
>     +static void
>     +rpir_surface_handle_surface_destroy(struct wl_listener *listener,
>     void *data)
>     +{
>     +       struct rpir_surface *surface;
>     +       struct weston_surface *base = data;
>     +
>     +       surface = container_of(listener, struct rpir_surface,
>     +                              surface_destroy_listener);
>     +
>     +       assert(surface);
>     +       assert(surface->surface == base);
>     +       if (!surface)
>     +               return;
>     +
>     +       surface->surface = NULL;
>     +       base->renderer_state = NULL;
>     +
>     +       if (wl_list_empty(&surface->views))
>     +               rpir_surface_destroy(surface);
>     +}
>     +
>       static int
>       rpi_renderer_create_surface(struct weston_surface *base)
>       {
>     @@ -1409,6 +1438,12 @@ rpi_renderer_create_surface(struct
>     weston_surface *base)
>
>              surface->surface = base;
>              base->renderer_state = surface;
>     +
>     +       surface->surface_destroy_listener.notify =
>     +               rpir_surface_handle_surface_destroy;
>     +       wl_signal_add(&base->destroy_signal,
>     +                     &surface->surface_destroy_listener);
>     +
>              return 0;
>       }
>
>     @@ -1471,23 +1506,6 @@ rpi_renderer_surface_set_color(struct
>     weston_surface *base,
>       }
>
>       static void
>     -rpi_renderer_destroy_surface(struct weston_surface *base)
>     -{
>     -       struct rpir_surface *surface = to_rpir_surface(base);
>     -
>     -       assert(surface);
>     -       assert(surface->surface == base);
>     -       if (!surface)
>     -               return;
>     -
>     -       surface->surface = NULL;
>     -       base->renderer_state = NULL;
>     -
>     -       if (wl_list_empty(&surface->views))
>     -               rpir_surface_destroy(surface);
>     -}
>     -
>     -static void
>       rpi_renderer_destroy_view(struct weston_view *base)
>       {
>              struct rpir_view *view = to_rpir_view(base);
>     @@ -1546,10 +1564,8 @@ rpi_renderer_create(struct weston_compositor
>     *compositor,
>              renderer->base.repaint_output = rpi_renderer_repaint_output;
>              renderer->base.flush_damage = rpi_renderer_flush_damage;
>              renderer->base.attach = rpi_renderer_attach;
>     -       renderer->base.create_surface = rpi_renderer_create_surface;
>              renderer->base.create_view = rpi_renderer_create_view;
>              renderer->base.surface_set_color =
>     rpi_renderer_surface_set_color;
>     -       renderer->base.destroy_surface = rpi_renderer_destroy_surface;
>              renderer->base.destroy_view = rpi_renderer_destroy_view;
>              renderer->base.destroy = rpi_renderer_destroy;
>
>     --
>     1.7.9.5
>
>     _______________________________________________
>     wayland-devel mailing list
>     wayland-devel at lists.freedesktop.org
>     <mailto:wayland-devel at lists.freedesktop.org>
>     http://lists.freedesktop.org/mailman/listinfo/wayland-devel
>
>
>
>
> _______________________________________________
> wayland-devel mailing list
> wayland-devel at lists.freedesktop.org
> http://lists.freedesktop.org/mailman/listinfo/wayland-devel
>



More information about the wayland-devel mailing list