weston_buffer: Add mode to weston_buffer_reference
Add a mode argument to weston_buffer_reference which indicates whether a buffer's storage may/will be accessed, or whether the underlying storage will no longer be accessed, e.g. because it has been copied. This will be used to retain a pointer to the weston_buffer whilst being able to send a release event to the client. Signed-off-by: Daniel Stone <daniels@collabora.com>
This commit is contained in:
@@ -1201,8 +1201,15 @@ struct weston_buffer {
|
|||||||
uint64_t format_modifier;
|
uint64_t format_modifier;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
enum weston_buffer_reference_type {
|
||||||
|
BUFFER_REF_NONE,
|
||||||
|
BUFFER_MAY_BE_ACCESSED,
|
||||||
|
BUFFER_WILL_NOT_BE_ACCESSED,
|
||||||
|
};
|
||||||
|
|
||||||
struct weston_buffer_reference {
|
struct weston_buffer_reference {
|
||||||
struct weston_buffer *buffer;
|
struct weston_buffer *buffer;
|
||||||
|
enum weston_buffer_reference_type type;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct weston_buffer_viewport {
|
struct weston_buffer_viewport {
|
||||||
|
|||||||
@@ -93,7 +93,8 @@ drm_plane_state_free(struct drm_plane_state *state, bool force)
|
|||||||
|
|
||||||
if (force || state != state->plane->state_cur) {
|
if (force || state != state->plane->state_cur) {
|
||||||
drm_fb_unref(state->fb);
|
drm_fb_unref(state->fb);
|
||||||
weston_buffer_reference(&state->fb_ref.buffer, NULL);
|
weston_buffer_reference(&state->fb_ref.buffer, NULL,
|
||||||
|
BUFFER_WILL_NOT_BE_ACCESSED);
|
||||||
weston_buffer_release_reference(&state->fb_ref.release, NULL);
|
weston_buffer_release_reference(&state->fb_ref.release, NULL);
|
||||||
free(state);
|
free(state);
|
||||||
}
|
}
|
||||||
@@ -135,10 +136,20 @@ drm_plane_state_duplicate(struct drm_output_state *state_output,
|
|||||||
* buffer, then we must also transfer the reference on the client
|
* buffer, then we must also transfer the reference on the client
|
||||||
* buffer. */
|
* buffer. */
|
||||||
if (src->fb) {
|
if (src->fb) {
|
||||||
|
struct weston_buffer *buffer;
|
||||||
|
|
||||||
dst->fb = drm_fb_ref(src->fb);
|
dst->fb = drm_fb_ref(src->fb);
|
||||||
memset(&dst->fb_ref, 0, sizeof(dst->fb_ref));
|
memset(&dst->fb_ref, 0, sizeof(dst->fb_ref));
|
||||||
weston_buffer_reference(&dst->fb_ref.buffer,
|
|
||||||
src->fb_ref.buffer.buffer);
|
if (src->fb->type == BUFFER_CLIENT ||
|
||||||
|
src->fb->type == BUFFER_DMABUF) {
|
||||||
|
buffer = src->fb_ref.buffer.buffer;
|
||||||
|
} else {
|
||||||
|
buffer = NULL;
|
||||||
|
}
|
||||||
|
weston_buffer_reference(&dst->fb_ref.buffer, buffer,
|
||||||
|
buffer ? BUFFER_MAY_BE_ACCESSED :
|
||||||
|
BUFFER_WILL_NOT_BE_ACCESSED);
|
||||||
weston_buffer_release_reference(&dst->fb_ref.release,
|
weston_buffer_release_reference(&dst->fb_ref.release,
|
||||||
src->fb_ref.release.buffer_release);
|
src->fb_ref.release.buffer_release);
|
||||||
} else {
|
} else {
|
||||||
|
|||||||
@@ -139,7 +139,8 @@ drm_output_try_view_on_plane(struct drm_plane *plane,
|
|||||||
assert(state->fb_ref.buffer.buffer == NULL);
|
assert(state->fb_ref.buffer.buffer == NULL);
|
||||||
assert(state->fb_ref.release.buffer_release == NULL);
|
assert(state->fb_ref.release.buffer_release == NULL);
|
||||||
weston_buffer_reference(&state->fb_ref.buffer,
|
weston_buffer_reference(&state->fb_ref.buffer,
|
||||||
surface->buffer_ref.buffer);
|
surface->buffer_ref.buffer,
|
||||||
|
BUFFER_MAY_BE_ACCESSED);
|
||||||
weston_buffer_release_reference(&state->fb_ref.release,
|
weston_buffer_release_reference(&state->fb_ref.release,
|
||||||
surface->buffer_release_ref.buffer_release);
|
surface->buffer_release_ref.buffer_release);
|
||||||
|
|
||||||
|
|||||||
+20
-7
@@ -2334,7 +2334,8 @@ weston_surface_destroy(struct weston_surface *surface)
|
|||||||
|
|
||||||
weston_surface_state_fini(&surface->pending);
|
weston_surface_state_fini(&surface->pending);
|
||||||
|
|
||||||
weston_buffer_reference(&surface->buffer_ref, NULL);
|
weston_buffer_reference(&surface->buffer_ref, NULL,
|
||||||
|
BUFFER_WILL_NOT_BE_ACCESSED);
|
||||||
weston_buffer_release_reference(&surface->buffer_release_ref, NULL);
|
weston_buffer_release_reference(&surface->buffer_release_ref, NULL);
|
||||||
|
|
||||||
pixman_region32_fini(&surface->damage);
|
pixman_region32_fini(&surface->damage);
|
||||||
@@ -2472,8 +2473,11 @@ fail:
|
|||||||
|
|
||||||
WL_EXPORT void
|
WL_EXPORT void
|
||||||
weston_buffer_reference(struct weston_buffer_reference *ref,
|
weston_buffer_reference(struct weston_buffer_reference *ref,
|
||||||
struct weston_buffer *buffer)
|
struct weston_buffer *buffer,
|
||||||
|
enum weston_buffer_reference_type type)
|
||||||
{
|
{
|
||||||
|
assert(buffer != NULL || type == BUFFER_WILL_NOT_BE_ACCESSED);
|
||||||
|
|
||||||
if (buffer == ref->buffer)
|
if (buffer == ref->buffer)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
@@ -2562,7 +2566,9 @@ static void
|
|||||||
weston_surface_attach(struct weston_surface *surface,
|
weston_surface_attach(struct weston_surface *surface,
|
||||||
struct weston_buffer *buffer)
|
struct weston_buffer *buffer)
|
||||||
{
|
{
|
||||||
weston_buffer_reference(&surface->buffer_ref, buffer);
|
weston_buffer_reference(&surface->buffer_ref, buffer,
|
||||||
|
buffer ? BUFFER_MAY_BE_ACCESSED :
|
||||||
|
BUFFER_WILL_NOT_BE_ACCESSED);
|
||||||
|
|
||||||
if (!buffer) {
|
if (!buffer) {
|
||||||
if (weston_surface_is_mapped(surface))
|
if (weston_surface_is_mapped(surface))
|
||||||
@@ -2699,7 +2705,9 @@ output_accumulate_damage(struct weston_output *output)
|
|||||||
* clients to use single-buffering.
|
* clients to use single-buffering.
|
||||||
*/
|
*/
|
||||||
if (!pnode->surface->keep_buffer) {
|
if (!pnode->surface->keep_buffer) {
|
||||||
weston_buffer_reference(&pnode->surface->buffer_ref, NULL);
|
weston_buffer_reference(&pnode->surface->buffer_ref,
|
||||||
|
NULL,
|
||||||
|
BUFFER_WILL_NOT_BE_ACCESSED);
|
||||||
weston_buffer_release_reference(
|
weston_buffer_release_reference(
|
||||||
&pnode->surface->buffer_release_ref, NULL);
|
&pnode->surface->buffer_release_ref, NULL);
|
||||||
}
|
}
|
||||||
@@ -4226,7 +4234,8 @@ weston_subsurface_commit_from_cache(struct weston_subsurface *sub)
|
|||||||
struct weston_surface *surface = sub->surface;
|
struct weston_surface *surface = sub->surface;
|
||||||
|
|
||||||
weston_surface_commit_state(surface, &sub->cached);
|
weston_surface_commit_state(surface, &sub->cached);
|
||||||
weston_buffer_reference(&sub->cached_buffer_ref, NULL);
|
weston_buffer_reference(&sub->cached_buffer_ref, NULL,
|
||||||
|
BUFFER_WILL_NOT_BE_ACCESSED);
|
||||||
|
|
||||||
weston_surface_commit_subsurface_order(surface);
|
weston_surface_commit_subsurface_order(surface);
|
||||||
|
|
||||||
@@ -4263,7 +4272,10 @@ weston_subsurface_commit_to_cache(struct weston_subsurface *sub)
|
|||||||
weston_surface_state_set_buffer(&sub->cached,
|
weston_surface_state_set_buffer(&sub->cached,
|
||||||
surface->pending.buffer);
|
surface->pending.buffer);
|
||||||
weston_buffer_reference(&sub->cached_buffer_ref,
|
weston_buffer_reference(&sub->cached_buffer_ref,
|
||||||
surface->pending.buffer);
|
surface->pending.buffer,
|
||||||
|
surface->pending.buffer ?
|
||||||
|
BUFFER_MAY_BE_ACCESSED :
|
||||||
|
BUFFER_WILL_NOT_BE_ACCESSED);
|
||||||
weston_presentation_feedback_discard_list(
|
weston_presentation_feedback_discard_list(
|
||||||
&sub->cached.feedback_list);
|
&sub->cached.feedback_list);
|
||||||
/* zwp_surface_synchronization_v1.set_acquire_fence */
|
/* zwp_surface_synchronization_v1.set_acquire_fence */
|
||||||
@@ -4845,7 +4857,8 @@ weston_subsurface_destroy(struct weston_subsurface *sub)
|
|||||||
weston_subsurface_unlink_parent(sub);
|
weston_subsurface_unlink_parent(sub);
|
||||||
|
|
||||||
weston_surface_state_fini(&sub->cached);
|
weston_surface_state_fini(&sub->cached);
|
||||||
weston_buffer_reference(&sub->cached_buffer_ref, NULL);
|
weston_buffer_reference(&sub->cached_buffer_ref, NULL,
|
||||||
|
BUFFER_WILL_NOT_BE_ACCESSED);
|
||||||
|
|
||||||
sub->surface->committed = NULL;
|
sub->surface->committed = NULL;
|
||||||
sub->surface->committed_private = NULL;
|
sub->surface->committed_private = NULL;
|
||||||
|
|||||||
@@ -50,7 +50,8 @@ weston_buffer_send_server_error(struct weston_buffer *buffer,
|
|||||||
const char *msg);
|
const char *msg);
|
||||||
void
|
void
|
||||||
weston_buffer_reference(struct weston_buffer_reference *ref,
|
weston_buffer_reference(struct weston_buffer_reference *ref,
|
||||||
struct weston_buffer *buffer);
|
struct weston_buffer *buffer,
|
||||||
|
enum weston_buffer_reference_type type);
|
||||||
|
|
||||||
void
|
void
|
||||||
weston_buffer_release_move(struct weston_buffer_release_reference *dest,
|
weston_buffer_release_move(struct weston_buffer_release_reference *dest,
|
||||||
|
|||||||
@@ -627,7 +627,9 @@ pixman_renderer_attach(struct weston_surface *es, struct weston_buffer *buffer)
|
|||||||
struct wl_shm_buffer *shm_buffer;
|
struct wl_shm_buffer *shm_buffer;
|
||||||
const struct pixel_format_info *pixel_info;
|
const struct pixel_format_info *pixel_info;
|
||||||
|
|
||||||
weston_buffer_reference(&ps->buffer_ref, buffer);
|
weston_buffer_reference(&ps->buffer_ref, buffer,
|
||||||
|
buffer ? BUFFER_MAY_BE_ACCESSED :
|
||||||
|
BUFFER_WILL_NOT_BE_ACCESSED);
|
||||||
weston_buffer_release_reference(&ps->buffer_release_ref,
|
weston_buffer_release_reference(&ps->buffer_release_ref,
|
||||||
es->buffer_release_ref.buffer_release);
|
es->buffer_release_ref.buffer_release);
|
||||||
|
|
||||||
@@ -646,7 +648,8 @@ pixman_renderer_attach(struct weston_surface *es, struct weston_buffer *buffer)
|
|||||||
|
|
||||||
if (buffer->type != WESTON_BUFFER_SHM) {
|
if (buffer->type != WESTON_BUFFER_SHM) {
|
||||||
weston_log("Pixman renderer supports only SHM buffers\n");
|
weston_log("Pixman renderer supports only SHM buffers\n");
|
||||||
weston_buffer_reference(&ps->buffer_ref, NULL);
|
weston_buffer_reference(&ps->buffer_ref, NULL,
|
||||||
|
BUFFER_WILL_NOT_BE_ACCESSED);
|
||||||
weston_buffer_release_reference(&ps->buffer_release_ref, NULL);
|
weston_buffer_release_reference(&ps->buffer_release_ref, NULL);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -657,7 +660,8 @@ pixman_renderer_attach(struct weston_surface *es, struct weston_buffer *buffer)
|
|||||||
if (!pixel_info || !pixman_format_supported_source(pixel_info->pixman_format)) {
|
if (!pixel_info || !pixman_format_supported_source(pixel_info->pixman_format)) {
|
||||||
weston_log("Unsupported SHM buffer format 0x%x\n",
|
weston_log("Unsupported SHM buffer format 0x%x\n",
|
||||||
wl_shm_buffer_get_format(shm_buffer));
|
wl_shm_buffer_get_format(shm_buffer));
|
||||||
weston_buffer_reference(&ps->buffer_ref, NULL);
|
weston_buffer_reference(&ps->buffer_ref, NULL,
|
||||||
|
BUFFER_WILL_NOT_BE_ACCESSED);
|
||||||
weston_buffer_release_reference(&ps->buffer_release_ref, NULL);
|
weston_buffer_release_reference(&ps->buffer_release_ref, NULL);
|
||||||
weston_buffer_send_server_error(buffer,
|
weston_buffer_send_server_error(buffer,
|
||||||
"disconnecting due to unhandled buffer type");
|
"disconnecting due to unhandled buffer type");
|
||||||
@@ -693,7 +697,8 @@ pixman_renderer_surface_state_destroy(struct pixman_surface_state *ps)
|
|||||||
pixman_image_unref(ps->image);
|
pixman_image_unref(ps->image);
|
||||||
ps->image = NULL;
|
ps->image = NULL;
|
||||||
}
|
}
|
||||||
weston_buffer_reference(&ps->buffer_ref, NULL);
|
weston_buffer_reference(&ps->buffer_ref, NULL,
|
||||||
|
BUFFER_WILL_NOT_BE_ACCESSED);
|
||||||
weston_buffer_release_reference(&ps->buffer_release_ref, NULL);
|
weston_buffer_release_reference(&ps->buffer_release_ref, NULL);
|
||||||
free(ps);
|
free(ps);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1931,7 +1931,8 @@ done:
|
|||||||
pixman_region32_init(&gs->texture_damage);
|
pixman_region32_init(&gs->texture_damage);
|
||||||
gs->needs_full_upload = false;
|
gs->needs_full_upload = false;
|
||||||
|
|
||||||
weston_buffer_reference(&gs->buffer_ref, NULL);
|
weston_buffer_reference(&gs->buffer_ref, buffer,
|
||||||
|
BUFFER_WILL_NOT_BE_ACCESSED);
|
||||||
weston_buffer_release_reference(&gs->buffer_release_ref, NULL);
|
weston_buffer_release_reference(&gs->buffer_release_ref, NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -2971,7 +2972,9 @@ gl_renderer_attach(struct weston_surface *es, struct weston_buffer *buffer)
|
|||||||
EGLint format;
|
EGLint format;
|
||||||
int i;
|
int i;
|
||||||
|
|
||||||
weston_buffer_reference(&gs->buffer_ref, buffer);
|
weston_buffer_reference(&gs->buffer_ref, buffer,
|
||||||
|
buffer ? BUFFER_MAY_BE_ACCESSED :
|
||||||
|
BUFFER_WILL_NOT_BE_ACCESSED);
|
||||||
weston_buffer_release_reference(&gs->buffer_release_ref,
|
weston_buffer_release_reference(&gs->buffer_release_ref,
|
||||||
es->buffer_release_ref.buffer_release);
|
es->buffer_release_ref.buffer_release);
|
||||||
|
|
||||||
@@ -3015,7 +3018,8 @@ gl_renderer_attach(struct weston_surface *es, struct weston_buffer *buffer)
|
|||||||
weston_log("eglQueryWaylandBufferWL failed\n");
|
weston_log("eglQueryWaylandBufferWL failed\n");
|
||||||
gl_renderer_print_egl_error_state();
|
gl_renderer_print_egl_error_state();
|
||||||
}
|
}
|
||||||
weston_buffer_reference(&gs->buffer_ref, NULL);
|
weston_buffer_reference(&gs->buffer_ref, NULL,
|
||||||
|
BUFFER_WILL_NOT_BE_ACCESSED);
|
||||||
weston_buffer_release_reference(&gs->buffer_release_ref, NULL);
|
weston_buffer_release_reference(&gs->buffer_release_ref, NULL);
|
||||||
gs->buffer_type = BUFFER_TYPE_NULL;
|
gs->buffer_type = BUFFER_TYPE_NULL;
|
||||||
gs->y_inverted = true;
|
gs->y_inverted = true;
|
||||||
@@ -3199,7 +3203,8 @@ surface_state_destroy(struct gl_surface_state *gs, struct gl_renderer *gr)
|
|||||||
for (i = 0; i < gs->num_images; i++)
|
for (i = 0; i < gs->num_images; i++)
|
||||||
egl_image_unref(gs->images[i]);
|
egl_image_unref(gs->images[i]);
|
||||||
|
|
||||||
weston_buffer_reference(&gs->buffer_ref, NULL);
|
weston_buffer_reference(&gs->buffer_ref, NULL,
|
||||||
|
BUFFER_WILL_NOT_BE_ACCESSED);
|
||||||
weston_buffer_release_reference(&gs->buffer_release_ref, NULL);
|
weston_buffer_release_reference(&gs->buffer_release_ref, NULL);
|
||||||
pixman_region32_fini(&gs->texture_damage);
|
pixman_region32_fini(&gs->texture_damage);
|
||||||
free(gs);
|
free(gs);
|
||||||
|
|||||||
Reference in New Issue
Block a user