commit fd0e372

Michael Forney  ·  2014-01-16 10:16:47 +0000 UTC
parent 682473b
Port to new wld API

This temporarily drops SHM support.
13 files changed,  +88, -315
+15, -99
  1@@ -1,6 +1,5 @@
  2 #include "swc.h"
  3 #include "compositor.h"
  4-#include "cursor_surface.h"
  5 #include "data_device_manager.h"
  6 #include "drm.h"
  7 #include "drm_buffer.h"
  8@@ -11,6 +10,7 @@
  9 #include "seat.h"
 10 #include "surface.h"
 11 #include "util.h"
 12+#include "view.h"
 13 
 14 #include <stdlib.h>
 15 #include <stdio.h>
 16@@ -47,54 +47,22 @@ struct view
 17 
 18 struct buffer_state
 19 {
 20-    struct wld_drawable * drawable;
 21-    /* Only used for SHM buffers */
 22-    pixman_image_t * dst, * src;
 23+    struct wld_buffer * buffer;
 24     struct wl_listener destroy_listener;
 25 };
 26 
 27 struct render_target
 28 {
 29-    struct wld_drawable * drawable;
 30+    struct wld_buffer * buffer;
 31     pixman_rectangle32_t geometry;
 32 };
 33 
 34-static inline uint32_t pixman_format(uint32_t format)
 35-{
 36-    switch (format)
 37-    {
 38-        case WL_SHM_FORMAT_XRGB8888:
 39-            return PIXMAN_x8r8g8b8;
 40-        case WL_SHM_FORMAT_ARGB8888:
 41-            return PIXMAN_a8r8g8b8;
 42-    }
 43-
 44-    return 0;
 45-}
 46-
 47-static inline uint32_t wld_format(uint32_t format)
 48-{
 49-    switch (format)
 50-    {
 51-        case WL_SHM_FORMAT_XRGB8888:
 52-            return WLD_FORMAT_XRGB8888;
 53-        case WL_SHM_FORMAT_ARGB8888:
 54-            return WLD_FORMAT_ARGB8888;
 55-    }
 56-
 57-    return 0;
 58-}
 59-
 60 static void handle_buffer_destroy(struct wl_listener * listener, void * data)
 61 {
 62     struct buffer_state * state
 63         = CONTAINER_OF(listener, typeof(*state), destroy_listener);
 64 
 65-    if (state->dst)
 66-        pixman_image_unref(state->dst);
 67-    if (state->src)
 68-        pixman_image_unref(state->src);
 69-    wld_destroy_drawable(state->drawable);
 70+    wld_destroy_buffer(state->buffer);
 71     free(state);
 72 }
 73 
 74@@ -147,9 +115,10 @@ static void repaint_surface(struct render_target * target,
 75 
 76         pixman_region32_translate(&surface_damage,
 77                                   -surface->geometry.x, -surface->geometry.y);
 78-        wld_copy_region(state->drawable, target->drawable, &surface_damage,
 79+        wld_copy_region(swc.drm->renderer, state->buffer,
 80                         surface->geometry.x - target->geometry.x,
 81-                        surface->geometry.y - target->geometry.y);
 82+                        surface->geometry.y - target->geometry.y,
 83+                        &surface_damage);
 84     }
 85 
 86     pixman_region32_fini(&surface_damage);
 87@@ -161,7 +130,7 @@ static void repaint_surface(struct render_target * target,
 88 
 89         pixman_region32_translate(&border_damage,
 90                                   -target->geometry.x, -target->geometry.y);
 91-        wld_fill_region(target->drawable, view->border.color, &border_damage);
 92+        wld_fill_region(swc.drm->renderer, view->border.color, &border_damage);
 93     }
 94 
 95     pixman_region32_fini(&border_damage);
 96@@ -183,7 +152,7 @@ static void renderer_repaint(struct render_target * target,
 97     {
 98         pixman_region32_translate(base_damage,
 99                                   -target->geometry.x, -target->geometry.y);
100-        wld_fill_region(target->drawable, 0xff000000, base_damage);
101+        wld_fill_region(swc.drm->renderer, 0xff000000, base_damage);
102     }
103 
104     wl_list_for_each_reverse(surface, surfaces, link)
105@@ -192,14 +161,13 @@ static void renderer_repaint(struct render_target * target,
106             repaint_surface(target, surface, damage);
107     }
108 
109-    wld_flush(target->drawable);
110+    wld_flush(swc.drm->renderer);
111 }
112 
113 static void renderer_attach(struct swc_surface * surface,
114                             struct wl_resource * resource)
115 {
116     struct buffer_state * state;
117-    struct wl_shm_buffer * shm_buffer;
118     struct swc_drm_buffer * drm_buffer;
119 
120     if (!resource)
121@@ -212,30 +180,12 @@ static void renderer_attach(struct swc_surface * surface,
122     if (!(state = malloc(sizeof *state)))
123         return;
124 
125-    if ((shm_buffer = wl_shm_buffer_get(resource)))
126-    {
127-        uint32_t width = wl_shm_buffer_get_width(shm_buffer),
128-                 height = wl_shm_buffer_get_height(shm_buffer),
129-                 format = wl_shm_buffer_get_format(shm_buffer),
130-                 pitch = wl_shm_buffer_get_stride(shm_buffer);
131-        void * data = wl_shm_buffer_get_data(shm_buffer);
132-
133-        state->drawable = wld_drm_create_drawable(swc.drm->context,
134-                                                  width, height,
135-                                                  wld_format(format));
136-        state->src = pixman_image_create_bits_no_clear(pixman_format(format),
137-                                                       width, height,
138-                                                       data, pitch);
139-        state->dst = wld_map(state->drawable);
140-    }
141-    else if ((drm_buffer = swc_drm_buffer_get(resource)))
142+    if ((drm_buffer = swc_drm_buffer_get(resource)))
143     {
144         if (!(state = malloc(sizeof *state)))
145             return;
146 
147-        state->drawable = drm_buffer->drawable;
148-        state->src = NULL;
149-        state->dst = NULL;
150+        state->buffer = drm_buffer->wld;
151     }
152     else
153     {
154@@ -249,18 +199,6 @@ static void renderer_attach(struct swc_surface * surface,
155 
156 static void renderer_flush_surface(struct swc_surface * surface)
157 {
158-    struct buffer_state * state;
159-
160-    state = buffer_state(surface->state.buffer);
161-    assert(state);
162-
163-    if (!state->src || !state->dst)
164-        return;
165-
166-    pixman_image_set_clip_region32(state->src, &surface->state.damage);
167-    pixman_image_composite32(PIXMAN_OP_SRC, state->src, NULL, state->dst,
168-                             0, 0, 0, 0, 0, 0,
169-                             state->drawable->width, state->drawable->height);
170 }
171 
172 /* }}} */
173@@ -636,13 +574,13 @@ static void repaint_output(struct swc_compositor * compositor,
174     pixman_region32_init(&base_damage);
175     pixman_region32_subtract(&base_damage, damage, &compositor->opaque);
176 
177-    target.drawable = swc_plane_get_buffer(&output->framebuffer_plane);
178+    target.buffer = swc_plane_get_buffer(&output->framebuffer_plane);
179     target.geometry.x = output->framebuffer_plane.output->geometry.x
180         + output->framebuffer_plane.x;
181     target.geometry.y = output->framebuffer_plane.output->geometry.y
182         + output->framebuffer_plane.y;
183-    target.geometry.width = target.drawable->width;
184-    target.geometry.height = target.drawable->height;
185+    target.geometry.width = target.buffer->width;
186+    target.geometry.height = target.buffer->height;
187 
188     renderer_repaint(&target, damage, &base_damage,
189                      &compositor->surfaces);
190@@ -778,26 +716,6 @@ static void handle_drm_event(struct wl_listener * listener, void * data)
191     }
192 }
193 
194-static void handle_pointer_event(struct wl_listener * listener, void * data)
195-{
196-    struct swc_event * event = data;
197-    struct swc_pointer_event_data * event_data = event->data;
198-    struct swc_compositor * compositor;
199-
200-    compositor = CONTAINER_OF(listener, typeof(*compositor), pointer_listener);
201-
202-    switch (event->type)
203-    {
204-        case SWC_POINTER_CURSOR_CHANGED:
205-            if (event_data->old)
206-                swc_surface_set_view(event_data->old, NULL);
207-
208-            if (event_data->new)
209-                swc_surface_set_view(event_data->new, &compositor->cursor_view);
210-            break;
211-    }
212-}
213-
214 static void handle_terminate(uint32_t time, uint32_t value, void * data)
215 {
216     struct wl_display * display = data;
217@@ -873,10 +791,8 @@ bool swc_compositor_initialize(struct swc_compositor * compositor,
218 
219     compositor->display = display;
220     compositor->drm_listener.notify = &handle_drm_event;
221-    compositor->pointer_listener.notify = &handle_pointer_event;
222     compositor->scheduled_updates = 0;
223     compositor->pending_flips = 0;
224-    swc_view_initialize(&compositor->cursor_view, &swc_cursor_view_impl);
225     compositor->pointer_handler = (struct swc_pointer_handler) {
226         .focus = &handle_focus,
227         .motion = &handle_motion
+0, -3
 1@@ -29,12 +29,9 @@ struct swc_compositor
 2         uint32_t scheduled_updates;
 3     };
 4 
 5-    struct swc_view cursor_view;
 6-
 7     struct swc_pointer_handler pointer_handler;
 8 
 9     struct wl_listener drm_listener;
10-    struct wl_listener pointer_listener;
11 };
12 
13 bool swc_compositor_initialize(struct swc_compositor * compositor,
+0, -114
  1@@ -1,114 +0,0 @@
  2-/* swc: cursor_surface.c
  3- *
  4- * Copyright (c) 2013 Michael Forney
  5- *
  6- * Permission is hereby granted, free of charge, to any person obtaining a copy
  7- * of this software and associated documentation files (the "Software"), to deal
  8- * in the Software without restriction, including without limitation the rights
  9- * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 10- * copies of the Software, and to permit persons to whom the Software is
 11- * furnished to do so, subject to the following conditions:
 12- *
 13- * The above copyright notice and this permission notice shall be included in
 14- * all copies or substantial portions of the Software.
 15- *
 16- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 17- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 18- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 19- * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 20- * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 21- * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
 22- * SOFTWARE.
 23- */
 24-
 25-#include "cursor_surface.h"
 26-#include "compositor.h"
 27-#include "output.h"
 28-#include "plane.h"
 29-
 30-#include <string.h>
 31-#include <wld/wld.h>
 32-
 33-/* Cursor view */
 34-static const uint32_t cursor_buffer_size = 64 * 64 * 4;
 35-
 36-static void update_plane(struct swc_plane * plane, void * data)
 37-{
 38-    struct wld_drawable * drawable = swc_plane_get_buffer(plane);
 39-
 40-    wld_write(drawable, data, cursor_buffer_size);
 41-    swc_plane_flip(plane);
 42-}
 43-
 44-static void attach(struct swc_surface * surface,
 45-                   struct wl_resource * resource)
 46-{
 47-    struct swc_compositor * compositor = CONTAINER_OF
 48-        (surface->view, typeof(*compositor), cursor_view);
 49-
 50-    if (pixman_region32_not_empty(&surface->state.damage))
 51-    {
 52-        struct wl_shm_buffer * buffer = wl_shm_buffer_get(resource);
 53-        uint32_t width, height;
 54-
 55-        if (!buffer)
 56-            return;
 57-
 58-        width = wl_shm_buffer_get_width(buffer);
 59-        height = wl_shm_buffer_get_height(buffer);
 60-
 61-        if (width <= 64 && height <= 64)
 62-        {
 63-            struct swc_output * output;
 64-            char data[cursor_buffer_size];
 65-
 66-            memset(data, 0, sizeof data);
 67-            pixman_blt(wl_shm_buffer_get_data(buffer), (uint32_t *) data,
 68-                       wl_shm_buffer_get_stride(buffer) >> 2, 64, 32, 32,
 69-                       0, 0, 0, 0, width, height);
 70-            wl_buffer_send_release(resource);
 71-            pixman_region32_clear(&surface->state.damage);
 72-
 73-            wl_list_for_each(output, &compositor->outputs, link)
 74-            {
 75-                if (swc_rectangle_overlap(&output->geometry,
 76-                                          &surface->geometry))
 77-                {
 78-                    update_plane(&output->cursor_plane, data);
 79-                }
 80-            }
 81-        }
 82-    }
 83-}
 84-
 85-static void update(struct swc_surface * surface)
 86-{
 87-    swc_surface_send_frame_callbacks(surface, swc_time());
 88-}
 89-
 90-static void move(struct swc_surface * surface, int32_t x, int32_t y)
 91-{
 92-    struct swc_compositor * compositor = CONTAINER_OF
 93-        (surface->view, typeof(*compositor), cursor_view);
 94-    struct swc_output * output;
 95-
 96-    surface->geometry.x = x;
 97-    surface->geometry.y = y;
 98-
 99-    wl_list_for_each(output, &compositor->outputs, link)
100-    {
101-        if (swc_rectangle_overlap(&output->geometry, &surface->geometry))
102-        {
103-            swc_plane_move(&output->cursor_plane,
104-                           surface->geometry.x - output->geometry.x,
105-                           surface->geometry.y - output->geometry.y);
106-        }
107-    }
108-}
109-
110-const struct swc_view_impl swc_cursor_view_impl = {
111-    .attach = &attach,
112-    .update = &update,
113-    .move = &move
114-};
115-
+0, -32
 1@@ -1,32 +0,0 @@
 2-/* swc: cursor_surface.h
 3- *
 4- * Copyright (c) 2013 Michael Forney
 5- *
 6- * Permission is hereby granted, free of charge, to any person obtaining a copy
 7- * of this software and associated documentation files (the "Software"), to deal
 8- * in the Software without restriction, including without limitation the rights
 9- * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
10- * copies of the Software, and to permit persons to whom the Software is
11- * furnished to do so, subject to the following conditions:
12- *
13- * The above copyright notice and this permission notice shall be included in
14- * all copies or substantial portions of the Software.
15- *
16- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
19- * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20- * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21- * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
22- * SOFTWARE.
23- */
24-
25-#ifndef SWC_CURSOR_SURFACE_H
26-#define SWC_CURSOR_SURFACE_H
27-
28-#include "view.h"
29-
30-extern const struct swc_view_impl swc_cursor_view_impl;
31-
32-#endif
33-
+28, -17
  1@@ -72,16 +72,17 @@ static void create_buffer(struct wl_client * client,
  2                           uint32_t name, int32_t width, int32_t height,
  3                           uint32_t stride, uint32_t format)
  4 {
  5-    struct wld_drawable * drawable;
  6+    struct wld_buffer * wld;
  7     struct swc_drm_buffer * buffer;
  8+    union wld_object object = { .u32 = name };
  9 
 10-    drawable = wld_drm_import_gem(swc.drm->context, width, height, format,
 11-                                  name, stride);
 12+    wld = wld_import_buffer(swc.drm->context, WLD_DRM_OBJECT_GEM_NAME, object,
 13+                            width, height, format, stride);
 14 
 15-    if (!drawable)
 16+    if (!wld)
 17         goto error0;
 18 
 19-    buffer = swc_drm_buffer_new(client, id, drawable);
 20+    buffer = swc_drm_buffer_new(client, id, wld);
 21 
 22     if (!buffer)
 23         goto error1;
 24@@ -89,7 +90,7 @@ static void create_buffer(struct wl_client * client,
 25     return;
 26 
 27   error1:
 28-    wld_destroy_drawable(drawable);
 29+    wld_destroy_buffer(wld);
 30   error0:
 31     wl_resource_post_no_memory(resource);
 32 }
 33@@ -114,17 +115,18 @@ static void create_prime_buffer(struct wl_client * client,
 34                                 int32_t offset1, int32_t stride1,
 35                                 int32_t offset2, int32_t stride2)
 36 {
 37-    struct wld_drawable * drawable;
 38+    struct wld_buffer * wld;
 39     struct swc_drm_buffer * buffer;
 40+    union wld_object object = { .i = fd };
 41 
 42-    drawable = wld_drm_import(swc.drm->context, width, height, format,
 43-                              fd, stride0);
 44+    wld = wld_import_buffer(swc.drm->context, WLD_DRM_OBJECT_PRIME_FD, object,
 45+                            width, height, format, stride0);
 46     close(fd);
 47 
 48-    if (!drawable)
 49+    if (!wld)
 50         goto error0;
 51 
 52-    buffer = swc_drm_buffer_new(client, id, drawable);
 53+    buffer = swc_drm_buffer_new(client, id, wld);
 54 
 55     if (!buffer)
 56         goto error1;
 57@@ -132,7 +134,7 @@ static void create_prime_buffer(struct wl_client * client,
 58     return;
 59 
 60   error1:
 61-    wld_destroy_drawable(drawable);
 62+    wld_destroy_buffer(wld);
 63   error0:
 64     wl_resource_post_no_memory(resource);
 65 }
 66@@ -350,13 +352,19 @@ bool swc_drm_initialize(const char * seat_name)
 67         goto error2;
 68     }
 69 
 70+    if (!(swc.drm->renderer = wld_create_renderer(swc.drm->context)))
 71+    {
 72+        ERROR("Could not create WLD DRM renderer\n");
 73+        goto error3;
 74+    }
 75+
 76     drm.global = wl_global_create(swc.display, &wl_drm_interface, 2,
 77                                   NULL, &bind_drm);
 78 
 79     if (!drm.global)
 80     {
 81         ERROR("Could not create wl_drm global\n");
 82-        goto error3;
 83+        goto error4;
 84     }
 85 
 86     drm.event_source = wl_event_loop_add_fd
 87@@ -365,15 +373,17 @@ bool swc_drm_initialize(const char * seat_name)
 88     if (!drm.event_source)
 89     {
 90         ERROR("Could not create DRM event source\n");
 91-        goto error4;
 92+        goto error5;
 93     }
 94 
 95     return true;
 96 
 97-  error4:
 98+  error5:
 99     wl_global_destroy(drm.global);
100+  error4:
101+    wld_destroy_renderer(swc.drm->renderer);
102   error3:
103-    wld_drm_destroy_context(swc.drm->context);
104+    wld_destroy_context(swc.drm->context);
105   error2:
106     close(swc.drm->fd);
107   error1:
108@@ -386,7 +396,8 @@ void swc_drm_finalize()
109 {
110     wl_event_source_remove(drm.event_source);
111     wl_global_destroy(drm.global);
112-    wld_drm_destroy_context(swc.drm->context);
113+    wld_destroy_renderer(swc.drm->renderer);
114+    wld_destroy_context(swc.drm->context);
115     free(drm.path);
116     close(swc.drm->fd);
117 }
+2, -1
 1@@ -19,7 +19,8 @@ struct swc_drm_event_data
 2 struct swc_drm
 3 {
 4     int fd;
 5-    struct wld_drm_context * context;
 6+    struct wld_context * context;
 7+    struct wld_renderer * renderer;
 8     struct wl_signal event_signal;
 9 };
10 
+2, -2
 1@@ -45,7 +45,7 @@ static void buffer_destroy(struct wl_resource * resource)
 2 }
 3 
 4 struct swc_drm_buffer * swc_drm_buffer_new
 5-    (struct wl_client * client, uint32_t id, struct wld_drawable * drawable)
 6+    (struct wl_client * client, uint32_t id, struct wld_buffer * wld)
 7 {
 8     struct swc_drm_buffer * buffer;
 9 
10@@ -57,7 +57,7 @@ struct swc_drm_buffer * swc_drm_buffer_new
11     buffer->resource = wl_resource_create(client, &wl_buffer_interface, 1, id);
12     wl_resource_set_implementation(buffer->resource, &drm_buffer_implementation,
13                                    buffer, &buffer_destroy);
14-    buffer->drawable = drawable;
15+    buffer->wld = wld;
16 
17     return buffer;
18 }
+2, -2
 1@@ -31,11 +31,11 @@ struct wl_client;
 2 struct swc_drm_buffer
 3 {
 4     struct wl_resource * resource;
 5-    struct wld_drawable * drawable;
 6+    struct wld_buffer * wld;
 7 };
 8 
 9 struct swc_drm_buffer * swc_drm_buffer_new
10-    (struct wl_client * client, uint32_t id, struct wld_drawable * drawable);
11+    (struct wl_client * client, uint32_t id, struct wld_buffer * wld);
12 
13 struct swc_drm_buffer * swc_drm_buffer_get(struct wl_resource * resource);
14 
+0, -1
1@@ -35,7 +35,6 @@ SWC_SOURCES =                       \
2     libswc/output.c                 \
3     libswc/plane.c                  \
4     libswc/surface.c                \
5-    libswc/cursor_surface.c         \
6     libswc/region.c                 \
7     libswc/input_focus.c            \
8     libswc/keyboard.c               \
+35, -38
  1@@ -35,56 +35,54 @@
  2 
  3 struct framebuffer
  4 {
  5-    struct wld_drawable * drawable;
  6-    uint32_t fb_id;
  7+    struct wld_buffer * buffer;
  8+    uint32_t id;
  9 };
 10 
 11 static bool framebuffer_initialize(struct swc_plane * plane)
 12 {
 13-    struct framebuffer * buffer
 14-        = swc_double_buffer_front(&plane->double_buffer);
 15+    struct framebuffer * fb = swc_double_buffer_front(&plane->double_buffer);
 16 
 17     return drmModeSetCrtc(swc.drm->fd, plane->output->crtc_id,
 18-                          buffer->fb_id, 0, 0, &plane->output->connector_id, 1,
 19+                          fb->id, 0, 0, &plane->output->connector_id, 1,
 20                           &plane->output->current_mode->info) == 0;
 21 }
 22 
 23 static void * framebuffer_create_buffer(struct swc_plane * plane)
 24 {
 25-    struct wld_drawable * drawable;
 26+    struct wld_buffer * buffer;
 27     struct swc_output * output = plane->output;
 28-    struct framebuffer * buffer;
 29-    uint32_t handle;
 30+    struct framebuffer * fb;
 31+    union wld_object object;
 32 
 33-    if (!(buffer = malloc(sizeof *buffer)))
 34+    if (!(fb = malloc(sizeof *fb)))
 35         goto error0;
 36 
 37-    drawable = wld_drm_create_drawable(swc.drm->context,
 38-                                       output->geometry.width,
 39-                                       output->geometry.height,
 40-                                       WLD_FORMAT_XRGB8888);
 41+    buffer = wld_create_buffer(swc.drm->context,
 42+                               output->geometry.width, output->geometry.height,
 43+                               WLD_FORMAT_XRGB8888);
 44 
 45-    if (!drawable)
 46+    if (!buffer)
 47     {
 48-        fprintf(stderr, "Could not create DRM drawable for framebuffer\n");
 49+        fprintf(stderr, "Could not create DRM buffer for framebuffer\n");
 50         goto error1;
 51     }
 52 
 53-    handle = wld_drm_get_handle(drawable);
 54+    wld_export(buffer, WLD_DRM_OBJECT_HANDLE, &object);
 55 
 56-    if (drmModeAddFB(swc.drm->fd, drawable->width, drawable->height,
 57-                     24, 32, drawable->pitch, handle, &buffer->fb_id) != 0)
 58+    if (drmModeAddFB(swc.drm->fd, buffer->width, buffer->height,
 59+                     24, 32, buffer->pitch, object.u32, &fb->id) != 0)
 60     {
 61         fprintf(stderr, "drmModeAddFB failed\n");
 62         goto error2;
 63     }
 64 
 65-    buffer->drawable = drawable;
 66+    fb->buffer = buffer;
 67 
 68     return buffer;
 69 
 70   error2:
 71-    wld_destroy_drawable(drawable);
 72+    wld_destroy_buffer(buffer);
 73   error1:
 74     free(buffer);
 75   error0:
 76@@ -93,25 +91,25 @@ static void * framebuffer_create_buffer(struct swc_plane * plane)
 77 
 78 static void framebuffer_destroy_buffer(struct swc_plane * plane, void * data)
 79 {
 80-    struct framebuffer * buffer = data;
 81+    struct framebuffer * fb = data;
 82 
 83-    drmModeRmFB(swc.drm->fd, buffer->fb_id);
 84-    wld_destroy_drawable(buffer->drawable);
 85+    drmModeRmFB(swc.drm->fd, fb->id);
 86+    wld_destroy_buffer(fb->buffer);
 87 }
 88 
 89-static struct wld_drawable * framebuffer_get_buffer(void * data)
 90+static struct wld_buffer * framebuffer_get_buffer(void * data)
 91 {
 92-    struct framebuffer * buffer = data;
 93+    struct framebuffer * fb = data;
 94 
 95-    return buffer->drawable;
 96+    return fb->buffer;
 97 }
 98 
 99 static bool framebuffer_flip(struct swc_plane * plane)
100 {
101     struct swc_output * output = plane->output;
102-    struct framebuffer * buffer = swc_double_buffer_back(&plane->double_buffer);
103+    struct framebuffer * fb = swc_double_buffer_back(&plane->double_buffer);
104 
105-    return drmModePageFlip(swc.drm->fd, output->crtc_id, buffer->fb_id,
106+    return drmModePageFlip(swc.drm->fd, output->crtc_id, fb->id,
107                            DRM_MODE_PAGE_FLIP_EVENT, output) == 0;
108 }
109 
110@@ -130,30 +128,29 @@ static bool cursor_initialize(struct swc_plane * plane)
111 
112 static void * cursor_create_buffer(struct swc_plane * plane)
113 {
114-    return wld_drm_create_drawable(swc.drm->context, 64, 64,
115-                                   WLD_FORMAT_ARGB8888);
116+    return wld_create_buffer(swc.drm->context, 64, 64, WLD_FORMAT_ARGB8888);
117 }
118 
119 static void cursor_destroy_buffer(struct swc_plane * plane, void * data)
120 {
121-    struct wld_drawable * drawable = data;
122+    struct wld_buffer * buffer = data;
123 
124-    wld_destroy_drawable(drawable);
125+    wld_destroy_buffer(buffer);
126 }
127 
128-static struct wld_drawable * cursor_get_buffer(void * data)
129+static struct wld_buffer * cursor_get_buffer(void * data)
130 {
131     return data;
132 }
133 
134 static bool cursor_flip(struct swc_plane * plane)
135 {
136-    struct wld_drawable * drawable
137-        = swc_double_buffer_back(&plane->double_buffer);
138-    int handle = wld_drm_get_handle(drawable);
139+    struct wld_buffer * buffer = swc_double_buffer_back(&plane->double_buffer);
140+    union wld_object object;
141 
142+    wld_export(buffer, WLD_DRM_OBJECT_HANDLE, &object);
143     return drmModeSetCursor(swc.drm->fd, plane->output->crtc_id,
144-                            handle, 64, 64) == 0;
145+                            object.u32, 64, 64) == 0;
146 }
147 
148 static bool cursor_move(struct swc_plane * plane, int32_t x, int32_t y)
149@@ -216,7 +213,7 @@ bool swc_plane_move(struct swc_plane * plane, int32_t x, int32_t y)
150         return false;
151 }
152 
153-struct wld_drawable * swc_plane_get_buffer(struct swc_plane * plane)
154+struct wld_buffer * swc_plane_get_buffer(struct swc_plane * plane)
155 {
156     void * back = swc_double_buffer_back(&plane->double_buffer);
157 
+2, -2
 1@@ -33,7 +33,7 @@ struct swc_plane_interface
 2     bool (* initialize)(struct swc_plane * plane);
 3     void * (* create_buffer)(struct swc_plane * plane);
 4     void (* destroy_buffer)(struct swc_plane * plane, void * data);
 5-    struct wld_drawable * (* get_buffer)(void * data);
 6+    struct wld_buffer * (* get_buffer)(void * data);
 7     bool (* flip)(struct swc_plane * plane);
 8     bool (* move)(struct swc_plane * plane, int32_t x, int32_t y);
 9 };
10@@ -57,7 +57,7 @@ bool swc_plane_flip(struct swc_plane * plane);
11 
12 bool swc_plane_move(struct swc_plane * plane, int32_t x, int32_t y);
13 
14-struct wld_drawable * swc_plane_get_buffer(struct swc_plane * plane);
15+struct wld_buffer * swc_plane_get_buffer(struct swc_plane * plane);
16 
17 extern const struct swc_plane_interface swc_framebuffer_plane;
18 extern const struct swc_plane_interface swc_cursor_plane;
+2, -2
 1@@ -255,8 +255,8 @@ static void commit(struct wl_client * client, struct wl_resource * resource)
 2             }
 3             else if ((drm_buffer = swc_drm_buffer_get(surface->state.buffer)))
 4             {
 5-                set_size(surface, drm_buffer->drawable->width,
 6-                         drm_buffer->drawable->height);
 7+                set_size(surface,
 8+                         drm_buffer->wld->width, drm_buffer->wld->height);
 9             }
10             else
11                 WARNING("Unknown buffer type attached\n");
+0, -2
1@@ -61,8 +61,6 @@ static void setup_compositor()
2     swc.seat->pointer->handler = &compositor.pointer_handler;
3     wl_signal_add(&swc.seat->pointer->focus.event_signal,
4                   swc_window_enter_listener);
5-    wl_signal_add(&swc.seat->pointer->event_signal,
6-                  &compositor.pointer_listener);
7 
8     /* Calculate pointer region */
9     pixman_region32_init(&pointer_region);