compositor-fbdev: Drop intermediate shadow buffer
Currently the fbdev compositor has its own shadow buffer when rendering with pixman, causing the following copies to occur: [pixman shadow buffer] -> [fbdev shadow buffer] -> [fbdev hardware] As the pixman render already does all output translation when compositing the intermediate shadow buffer really isn't needed, so drop it. As a side-effect this fixes updating the fbdev hardware for outputs not starting at 0x0. Signed-off-by: Sjoerd Simons <sjoerd.simons@collabora.co.uk> Reviewed-by: Pekka Paalanen <pekka.paalanen@collabora.co.uk> Reviewed-by: David FORT <contact@hardening-consulting.com> Reviewed-by: Derek Foreman <derekf@osg.samsung.com> Tested-by: Derek Foreman <derekf@osg.samsung.com>
This commit is contained in:
committed by
Derek Foreman
parent
ba9dca054e
commit
c112e0c5bc
+3
-65
@@ -90,8 +90,6 @@ struct fbdev_output {
|
|||||||
|
|
||||||
/* pixman details. */
|
/* pixman details. */
|
||||||
pixman_image_t *hw_surface;
|
pixman_image_t *hw_surface;
|
||||||
pixman_image_t *shadow_surface;
|
|
||||||
void *shadow_buf;
|
|
||||||
uint8_t depth;
|
uint8_t depth;
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -131,39 +129,11 @@ fbdev_output_repaint_pixman(struct weston_output *base, pixman_region32_t *damag
|
|||||||
{
|
{
|
||||||
struct fbdev_output *output = to_fbdev_output(base);
|
struct fbdev_output *output = to_fbdev_output(base);
|
||||||
struct weston_compositor *ec = output->base.compositor;
|
struct weston_compositor *ec = output->base.compositor;
|
||||||
pixman_box32_t *rects;
|
|
||||||
int nrects, i;
|
|
||||||
|
|
||||||
/* Repaint the damaged region onto the back buffer. */
|
/* Repaint the damaged region onto the back buffer. */
|
||||||
pixman_renderer_output_set_buffer(base, output->shadow_surface);
|
pixman_renderer_output_set_buffer(base, output->hw_surface);
|
||||||
ec->renderer->repaint_output(base, damage);
|
ec->renderer->repaint_output(base, damage);
|
||||||
|
|
||||||
/* Transform and composite onto the frame buffer. */
|
|
||||||
rects = pixman_region32_rectangles(damage, &nrects);
|
|
||||||
|
|
||||||
for (i = 0; i < nrects; i++) {
|
|
||||||
pixman_box32_t transformed_rect;
|
|
||||||
int width, height;
|
|
||||||
|
|
||||||
transformed_rect = weston_transformed_rect(base->width,
|
|
||||||
base->height,
|
|
||||||
base->transform,
|
|
||||||
1, rects[i]);
|
|
||||||
width = transformed_rect.x2 - transformed_rect.x1;
|
|
||||||
height = transformed_rect.y2 - transformed_rect.y1;
|
|
||||||
pixman_image_composite32(PIXMAN_OP_SRC,
|
|
||||||
output->shadow_surface, /* src */
|
|
||||||
NULL /* mask */,
|
|
||||||
output->hw_surface, /* dest */
|
|
||||||
transformed_rect.x1, /* src_x */
|
|
||||||
transformed_rect.y1, /* src_y */
|
|
||||||
0, 0, /* mask_x, mask_y */
|
|
||||||
transformed_rect.x1, /* dest_x */
|
|
||||||
transformed_rect.y1, /* dest_y */
|
|
||||||
width, /* width */
|
|
||||||
height /* height */);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Update the damage region. */
|
/* Update the damage region. */
|
||||||
pixman_region32_subtract(&ec->primary_plane.damage,
|
pixman_region32_subtract(&ec->primary_plane.damage,
|
||||||
&ec->primary_plane.damage, damage);
|
&ec->primary_plane.damage, damage);
|
||||||
@@ -489,8 +459,6 @@ fbdev_output_create(struct fbdev_backend *backend,
|
|||||||
struct fbdev_output *output;
|
struct fbdev_output *output;
|
||||||
struct weston_config_section *section;
|
struct weston_config_section *section;
|
||||||
int fb_fd;
|
int fb_fd;
|
||||||
int width, height;
|
|
||||||
unsigned int bytes_per_pixel;
|
|
||||||
struct wl_event_loop *loop;
|
struct wl_event_loop *loop;
|
||||||
uint32_t config_transform;
|
uint32_t config_transform;
|
||||||
char *s;
|
char *s;
|
||||||
@@ -553,24 +521,9 @@ fbdev_output_create(struct fbdev_backend *backend,
|
|||||||
config_transform,
|
config_transform,
|
||||||
1);
|
1);
|
||||||
|
|
||||||
width = output->mode.width;
|
|
||||||
height = output->mode.height;
|
|
||||||
bytes_per_pixel = output->fb_info.bits_per_pixel / 8;
|
|
||||||
|
|
||||||
output->shadow_buf = malloc(width * height * bytes_per_pixel);
|
|
||||||
output->shadow_surface =
|
|
||||||
pixman_image_create_bits(output->fb_info.pixel_format,
|
|
||||||
width, height,
|
|
||||||
output->shadow_buf,
|
|
||||||
width * bytes_per_pixel);
|
|
||||||
if (output->shadow_buf == NULL || output->shadow_surface == NULL) {
|
|
||||||
weston_log("Failed to create surface for frame buffer.\n");
|
|
||||||
goto out_hw_surface;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (backend->use_pixman) {
|
if (backend->use_pixman) {
|
||||||
if (pixman_renderer_output_create(&output->base) < 0)
|
if (pixman_renderer_output_create(&output->base) < 0)
|
||||||
goto out_shadow_surface;
|
goto out_hw_surface;
|
||||||
} else {
|
} else {
|
||||||
setenv("HYBRIS_EGLPLATFORM", "wayland", 1);
|
setenv("HYBRIS_EGLPLATFORM", "wayland", 1);
|
||||||
if (gl_renderer->output_create(&output->base,
|
if (gl_renderer->output_create(&output->base,
|
||||||
@@ -578,11 +531,10 @@ fbdev_output_create(struct fbdev_backend *backend,
|
|||||||
gl_renderer->opaque_attribs,
|
gl_renderer->opaque_attribs,
|
||||||
NULL, 0) < 0) {
|
NULL, 0) < 0) {
|
||||||
weston_log("gl_renderer_output_create failed.\n");
|
weston_log("gl_renderer_output_create failed.\n");
|
||||||
goto out_shadow_surface;
|
goto out_hw_surface;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
loop = wl_display_get_event_loop(backend->compositor->wl_display);
|
loop = wl_display_get_event_loop(backend->compositor->wl_display);
|
||||||
output->finish_frame_timer =
|
output->finish_frame_timer =
|
||||||
wl_event_loop_add_timer(loop, finish_frame_handler, output);
|
wl_event_loop_add_timer(loop, finish_frame_handler, output);
|
||||||
@@ -596,11 +548,7 @@ fbdev_output_create(struct fbdev_backend *backend,
|
|||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
out_shadow_surface:
|
|
||||||
pixman_image_unref(output->shadow_surface);
|
|
||||||
output->shadow_surface = NULL;
|
|
||||||
out_hw_surface:
|
out_hw_surface:
|
||||||
free(output->shadow_buf);
|
|
||||||
pixman_image_unref(output->hw_surface);
|
pixman_image_unref(output->hw_surface);
|
||||||
output->hw_surface = NULL;
|
output->hw_surface = NULL;
|
||||||
weston_output_destroy(&output->base);
|
weston_output_destroy(&output->base);
|
||||||
@@ -625,16 +573,6 @@ fbdev_output_destroy(struct weston_output *base)
|
|||||||
if (backend->use_pixman) {
|
if (backend->use_pixman) {
|
||||||
if (base->renderer_state != NULL)
|
if (base->renderer_state != NULL)
|
||||||
pixman_renderer_output_destroy(base);
|
pixman_renderer_output_destroy(base);
|
||||||
|
|
||||||
if (output->shadow_surface != NULL) {
|
|
||||||
pixman_image_unref(output->shadow_surface);
|
|
||||||
output->shadow_surface = NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (output->shadow_buf != NULL) {
|
|
||||||
free(output->shadow_buf);
|
|
||||||
output->shadow_buf = NULL;
|
|
||||||
}
|
|
||||||
} else {
|
} else {
|
||||||
gl_renderer->output_destroy(base);
|
gl_renderer->output_destroy(base);
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user