diff --git a/backend/drm/renderer.c b/backend/drm/renderer.c index c24ff73da..0a8cd5150 100644 --- a/backend/drm/renderer.c +++ b/backend/drm/renderer.c @@ -7,7 +7,6 @@ #include #include #include -#include #include #include #include @@ -53,24 +52,22 @@ static void finish_drm_surface(struct wlr_drm_surface *surf) { return; } - wlr_swapchain_destroy(surf->swapchain); - + wlr_swapchain_finish(&surf->swapchain); memset(surf, 0, sizeof(*surf)); } bool init_drm_surface(struct wlr_drm_surface *surf, struct wlr_drm_renderer *renderer, int width, int height, const struct wlr_drm_format *drm_format) { - if (surf->swapchain != NULL && surf->swapchain->width == width && - surf->swapchain->height == height) { + if (surf->swapchain.width == width && + surf->swapchain.height == height) { return true; } finish_drm_surface(surf); - surf->swapchain = wlr_swapchain_create(renderer->allocator, width, height, - drm_format); - if (surf->swapchain == NULL) { + if (!wlr_swapchain_init(&surf->swapchain, renderer->allocator, + width, height, drm_format)) { wlr_log(WLR_ERROR, "Failed to create swapchain"); return false; } @@ -84,8 +81,8 @@ struct wlr_buffer *drm_surface_blit(struct wlr_drm_surface *surf, struct wlr_buffer *buffer) { struct wlr_renderer *renderer = surf->renderer->wlr_rend; - if (surf->swapchain->width != buffer->width || - surf->swapchain->height != buffer->height) { + if (surf->swapchain.width != buffer->width || + surf->swapchain.height != buffer->height) { wlr_log(WLR_ERROR, "Surface size doesn't match buffer size"); return NULL; } @@ -96,7 +93,7 @@ struct wlr_buffer *drm_surface_blit(struct wlr_drm_surface *surf, return NULL; } - struct wlr_buffer *dst = wlr_swapchain_acquire(surf->swapchain, NULL); + struct wlr_buffer *dst = wlr_swapchain_acquire(&surf->swapchain, NULL); if (!dst) { wlr_log(WLR_ERROR, "Failed to acquire multi-GPU swapchain buffer"); wlr_texture_destroy(tex); @@ -105,7 +102,7 @@ struct wlr_buffer *drm_surface_blit(struct wlr_drm_surface *surf, float mat[9]; wlr_matrix_identity(mat); - wlr_matrix_scale(mat, surf->swapchain->width, surf->swapchain->height); + wlr_matrix_scale(mat, surf->swapchain.width, surf->swapchain.height); if (!wlr_renderer_begin_with_buffer(renderer, dst)) { wlr_log(WLR_ERROR, "Failed to bind multi-GPU destination buffer"); diff --git a/include/backend/drm/renderer.h b/include/backend/drm/renderer.h index 5851d228c..a9aeacd5f 100644 --- a/include/backend/drm/renderer.h +++ b/include/backend/drm/renderer.h @@ -4,6 +4,7 @@ #include #include #include +#include #include struct wlr_drm_backend; @@ -19,7 +20,7 @@ struct wlr_drm_renderer { struct wlr_drm_surface { struct wlr_drm_renderer *renderer; - struct wlr_swapchain *swapchain; + struct wlr_swapchain swapchain; }; struct wlr_drm_fb { diff --git a/include/wlr/render/swapchain.h b/include/wlr/render/swapchain.h index 38b1fb8bd..e8f71af37 100644 --- a/include/wlr/render/swapchain.h +++ b/include/wlr/render/swapchain.h @@ -26,10 +26,10 @@ struct wlr_swapchain { struct wl_listener allocator_destroy; }; -struct wlr_swapchain *wlr_swapchain_create( +bool wlr_swapchain_init(struct wlr_swapchain *swapchain, struct wlr_allocator *alloc, int width, int height, const struct wlr_drm_format *format); -void wlr_swapchain_destroy(struct wlr_swapchain *swapchain); +void wlr_swapchain_finish(struct wlr_swapchain *swapchain); /** * Acquire a buffer from the swap chain. * diff --git a/include/wlr/types/wlr_output.h b/include/wlr/types/wlr_output.h index 9ea1188f4..793e9c498 100644 --- a/include/wlr/types/wlr_output.h +++ b/include/wlr/types/wlr_output.h @@ -14,6 +14,7 @@ #include #include #include +#include #include #include @@ -192,7 +193,7 @@ struct wlr_output { struct wl_list cursors; // wlr_output_cursor::link struct wlr_output_cursor *hardware_cursor; - struct wlr_swapchain *cursor_swapchain; + struct wlr_swapchain cursor_swapchain; struct wlr_buffer *cursor_front_buffer; int software_cursor_locks; // number of locks forcing software cursors @@ -200,7 +201,7 @@ struct wlr_output { struct wlr_allocator *allocator; struct wlr_renderer *renderer; - struct wlr_swapchain *swapchain; + struct wlr_swapchain swapchain; struct wlr_buffer *back_buffer; struct wl_listener display_destroy; diff --git a/render/swapchain.c b/render/swapchain.c index 943879bbe..2d47178fe 100644 --- a/render/swapchain.c +++ b/render/swapchain.c @@ -13,27 +13,25 @@ static void swapchain_handle_allocator_destroy(struct wl_listener *listener, swapchain->allocator = NULL; } -struct wlr_swapchain *wlr_swapchain_create( +bool wlr_swapchain_init(struct wlr_swapchain *swapchain, struct wlr_allocator *alloc, int width, int height, const struct wlr_drm_format *format) { - struct wlr_swapchain *swapchain = calloc(1, sizeof(*swapchain)); - if (swapchain == NULL) { - return NULL; - } - swapchain->allocator = alloc; - swapchain->width = width; - swapchain->height = height; + *swapchain = (struct wlr_swapchain){ + .allocator = alloc, + .width = width, + .height = height, + }; swapchain->format = wlr_drm_format_dup(format); if (swapchain->format == NULL) { free(swapchain); - return NULL; + return false; } swapchain->allocator_destroy.notify = swapchain_handle_allocator_destroy; wl_signal_add(&alloc->events.destroy, &swapchain->allocator_destroy); - return swapchain; + return true; } static void slot_reset(struct wlr_swapchain_slot *slot) { @@ -44,7 +42,7 @@ static void slot_reset(struct wlr_swapchain_slot *slot) { memset(slot, 0, sizeof(*slot)); } -void wlr_swapchain_destroy(struct wlr_swapchain *swapchain) { +void wlr_swapchain_finish(struct wlr_swapchain *swapchain) { if (swapchain == NULL) { return; } @@ -53,7 +51,6 @@ void wlr_swapchain_destroy(struct wlr_swapchain *swapchain) { } wl_list_remove(&swapchain->allocator_destroy.link); free(swapchain->format); - free(swapchain); } static void slot_handle_release(struct wl_listener *listener, void *data) { diff --git a/types/output/cursor.c b/types/output/cursor.c index 6ab557b59..2291e38fa 100644 --- a/types/output/cursor.c +++ b/types/output/cursor.c @@ -260,9 +260,8 @@ static struct wlr_buffer *render_cursor_buffer(struct wlr_output_cursor *cursor) } } - if (output->cursor_swapchain == NULL || - output->cursor_swapchain->width != width || - output->cursor_swapchain->height != height) { + if (output->cursor_swapchain.width != width || + output->cursor_swapchain.height != height) { struct wlr_drm_format *format = output_pick_cursor_format(output); if (format == NULL) { @@ -270,18 +269,19 @@ static struct wlr_buffer *render_cursor_buffer(struct wlr_output_cursor *cursor) return NULL; } - wlr_swapchain_destroy(output->cursor_swapchain); - output->cursor_swapchain = wlr_swapchain_create(allocator, + wlr_swapchain_finish(&output->cursor_swapchain); + bool ok = wlr_swapchain_init(&output->cursor_swapchain, allocator, width, height, format); free(format); - if (output->cursor_swapchain == NULL) { + if (!ok) { + memset(&output->cursor_swapchain, 0, sizeof(output->cursor_swapchain)); wlr_log(WLR_ERROR, "Failed to create cursor swapchain"); return NULL; } } struct wlr_buffer *buffer = - wlr_swapchain_acquire(output->cursor_swapchain, NULL); + wlr_swapchain_acquire(&output->cursor_swapchain, NULL); if (buffer == NULL) { return NULL; } diff --git a/types/output/output.c b/types/output/output.c index c6b90a1d7..26a433fe4 100644 --- a/types/output/output.c +++ b/types/output/output.c @@ -4,7 +4,6 @@ #include #include #include -#include #include #include #include @@ -248,11 +247,10 @@ void wlr_output_update_custom_mode(struct wlr_output *output, int32_t width, output->refresh = refresh; - if (output->swapchain != NULL && - (output->swapchain->width != output->width || - output->swapchain->height != output->height)) { - wlr_swapchain_destroy(output->swapchain); - output->swapchain = NULL; + if (output->swapchain.width != output->width || + output->swapchain.height != output->height) { + wlr_swapchain_finish(&output->swapchain); + memset(&output->swapchain, 0, sizeof(output->swapchain)); } struct wl_resource *resource; @@ -396,10 +394,10 @@ void wlr_output_destroy(struct wlr_output *output) { wlr_output_layer_destroy(layer); } - wlr_swapchain_destroy(output->cursor_swapchain); + wlr_swapchain_finish(&output->cursor_swapchain); wlr_buffer_unlock(output->cursor_front_buffer); - wlr_swapchain_destroy(output->swapchain); + wlr_swapchain_finish(&output->swapchain); if (output->idle_frame != NULL) { wl_event_source_remove(output->idle_frame); @@ -822,10 +820,10 @@ bool wlr_output_commit_state(struct wlr_output *output, // Destroy the swapchains when an output is disabled if ((pending.committed & WLR_OUTPUT_STATE_ENABLED) && !pending.enabled) { - wlr_swapchain_destroy(output->swapchain); - output->swapchain = NULL; - wlr_swapchain_destroy(output->cursor_swapchain); - output->cursor_swapchain = NULL; + wlr_swapchain_finish(&output->swapchain); + memset(&output->swapchain, 0, sizeof(output->swapchain)); + wlr_swapchain_finish(&output->cursor_swapchain); + memset(&output->cursor_swapchain, 0, sizeof(output->cursor_swapchain)); } if (pending.committed & WLR_OUTPUT_STATE_BUFFER) { @@ -843,8 +841,8 @@ bool wlr_output_commit_state(struct wlr_output *output, } if ((pending.committed & WLR_OUTPUT_STATE_BUFFER) && - output->swapchain != NULL) { - wlr_swapchain_set_buffer_submitted(output->swapchain, pending.buffer); + output->swapchain.width != 0) { + wlr_swapchain_set_buffer_submitted(&output->swapchain, pending.buffer); } struct wlr_output_event_commit event = { diff --git a/types/output/render.c b/types/output/render.c index d3121af1b..2a909f50e 100644 --- a/types/output/render.c +++ b/types/output/render.c @@ -3,7 +3,6 @@ #include #include #include -#include #include #include #include "backend/backend.h" @@ -31,11 +30,11 @@ bool wlr_output_init_render(struct wlr_output *output, return false; } - wlr_swapchain_destroy(output->swapchain); - output->swapchain = NULL; + wlr_swapchain_finish(&output->swapchain); + memset(&output->swapchain, 0, sizeof(output->swapchain)); - wlr_swapchain_destroy(output->cursor_swapchain); - output->cursor_swapchain = NULL; + wlr_swapchain_finish(&output->cursor_swapchain); + memset(&output->cursor_swapchain, 0, sizeof(output->cursor_swapchain)); output->allocator = allocator; output->renderer = renderer; @@ -68,10 +67,10 @@ static bool output_create_swapchain(struct wlr_output *output, return false; } - if (output->swapchain != NULL && output->swapchain->width == width && - output->swapchain->height == height && - output->swapchain->format->format == format->format && - (allow_modifiers || output->swapchain->format->len == 0)) { + if (output->swapchain.width == width && + output->swapchain.height == height && + output->swapchain.format->format == format->format && + (allow_modifiers || output->swapchain.format->len == 0)) { // no change, keep existing swapchain free(format); return true; @@ -93,17 +92,15 @@ static bool output_create_swapchain(struct wlr_output *output, wlr_drm_format_add(&format, DRM_FORMAT_MOD_INVALID); } - struct wlr_swapchain *swapchain = - wlr_swapchain_create(allocator, width, height, format); + wlr_swapchain_finish(&output->swapchain); + bool ok = wlr_swapchain_init(&output->swapchain, allocator, width, height, format); free(format); - if (swapchain == NULL) { + if (!ok) { + memset(&output->swapchain, 0, sizeof(output->swapchain)); wlr_log(WLR_ERROR, "Failed to create output swapchain"); return false; } - wlr_swapchain_destroy(output->swapchain); - output->swapchain = swapchain; - return true; } @@ -119,7 +116,7 @@ static bool output_attach_back_buffer(struct wlr_output *output, assert(renderer != NULL); struct wlr_buffer *buffer = - wlr_swapchain_acquire(output->swapchain, buffer_age); + wlr_swapchain_acquire(&output->swapchain, buffer_age); if (buffer == NULL) { return false; } @@ -247,7 +244,7 @@ bool output_ensure_buffer(struct wlr_output *output, output_clear_back_buffer(output); - if (output->swapchain->format->len == 0) { + if (output->swapchain.format->len == 0) { return false; } @@ -274,8 +271,8 @@ error_destroy_swapchain: // Destroy the modifierless swapchain so that the output does not get stuck // without modifiers. A new swapchain with modifiers will be created when // needed by output_attach_back_buffer(). - wlr_swapchain_destroy(output->swapchain); - output->swapchain = NULL; + wlr_swapchain_finish(&output->swapchain); + memset(&output->swapchain, 0, sizeof(output->swapchain)); return false; } @@ -358,12 +355,12 @@ uint32_t wlr_output_preferred_read_format(struct wlr_output *output) { bool output_is_direct_scanout(struct wlr_output *output, struct wlr_buffer *buffer) { - if (output->swapchain == NULL) { + if (output->swapchain.width == 0) { return true; } for (size_t i = 0; i < WLR_SWAPCHAIN_CAP; i++) { - if (output->swapchain->slots[i].buffer == buffer) { + if (output->swapchain.slots[i].buffer == buffer) { return false; } }