Compare commits

...

6 Commits

Author SHA1 Message Date
Simon Ser df0e75ba05 output: try skipping buffer allocation if the backend allows it
When enabling an output, skip the empty buffer allocation if the
backend accepts modesets without a buffer.

This fixes mode-setting with the noop backend.
2021-08-04 10:18:59 -04:00
Simon Ser 8a3cd28973 render/pixman/pixel_format: add more formats
Add a bunch of new formats for Pixman: a few missing 32-bit ones,
some 16-bit and 32-bit formats as well.

Mostly based on a Weston patch [1].

[1]: https://gitlab.freedesktop.org/wayland/weston/-/merge_requests/664
2021-08-03 02:53:03 -04:00
Simon Ser b913e64f95 render/pixel_format: add more formats for Pixman
These will be added to Pixman in the next commit.
2021-08-03 02:53:03 -04:00
Simon Ser 923258b0be backend/drm: preserve mode order from kernel
The kernel orders the mode list from highest to lowest. Preserve
this ordering in the wlr_output.modes list.
2021-08-02 09:28:21 -04:00
Kirill Primak f12bacf4b4 surface: don't cache frame callback lists 2021-08-02 09:10:10 +02:00
Quantum 456c6e2279 viewporter: remove crop and scale state upon destruction
According to the viewport protocol, upon wp_viewport::destroy():

> The associated wl_surface's crop and scale state is removed.
> The change is applied on the next wl_surface.commit.

Therefore, wp_viewport_destroy(viewport) should remove all viewport state.

Currently, wlroots does not remove the crop and scale state. Instead, a
client must do:

    wl_fixed_t clear = wl_fixed_from_int(-1);
    wp_viewport_set_source(viewport, clear, clear, clear, clear);
    wp_viewport_set_destination(viewport, -1, -1);
    wp_viewport_destroy(viewport);

This commit adds the necessary logic into viewport_destroy and makes
wlroots comply with the protocol.
2021-08-02 09:08:03 +02:00
6 changed files with 127 additions and 9 deletions

View File

@ -1385,7 +1385,7 @@ void scan_drm_connectors(struct wlr_drm_backend *drm) {
mode->wlr_mode.refresh,
mode->wlr_mode.preferred ? "(preferred)" : "");
wl_list_insert(&wlr_conn->output.modes, &mode->wlr_mode.link);
wl_list_insert(wlr_conn->output.modes.prev, &mode->wlr_mode.link);
}
wlr_conn->possible_crtcs = get_possible_crtcs(drm->fd, res, drm_conn);

View File

@ -26,6 +26,30 @@ static const struct wlr_pixel_format_info pixel_format_info[] = {
.bpp = 32,
.has_alpha = true,
},
{
.drm_format = DRM_FORMAT_RGBX8888,
.opaque_substitute = DRM_FORMAT_INVALID,
.bpp = 32,
.has_alpha = false,
},
{
.drm_format = DRM_FORMAT_RGBA8888,
.opaque_substitute = DRM_FORMAT_RGBX8888,
.bpp = 32,
.has_alpha = true,
},
{
.drm_format = DRM_FORMAT_BGRX8888,
.opaque_substitute = DRM_FORMAT_INVALID,
.bpp = 32,
.has_alpha = false,
},
{
.drm_format = DRM_FORMAT_BGRA8888,
.opaque_substitute = DRM_FORMAT_BGRX8888,
.bpp = 32,
.has_alpha = true,
},
{
.drm_format = DRM_FORMAT_BGR888,
.opaque_substitute = DRM_FORMAT_INVALID,
@ -62,6 +86,24 @@ static const struct wlr_pixel_format_info pixel_format_info[] = {
.bpp = 16,
.has_alpha = false,
},
{
.drm_format = DRM_FORMAT_BGR565,
.opaque_substitute = DRM_FORMAT_INVALID,
.bpp = 16,
.has_alpha = false,
},
{
.drm_format = DRM_FORMAT_XRGB2101010,
.opaque_substitute = DRM_FORMAT_INVALID,
.bpp = 32,
.has_alpha = false,
},
{
.drm_format = DRM_FORMAT_ARGB2101010,
.opaque_substitute = DRM_FORMAT_XRGB2101010,
.bpp = 32,
.has_alpha = true,
},
{
.drm_format = DRM_FORMAT_XBGR2101010,
.opaque_substitute = DRM_FORMAT_INVALID,

View File

@ -35,7 +35,68 @@ static const struct wlr_pixman_pixel_format formats[] = {
#else
.pixman_format = PIXMAN_a8b8g8r8,
#endif
}
},
{
.drm_format = DRM_FORMAT_RGBA8888,
#if WLR_BIG_ENDIAN
.pixman_format = PIXMAN_a8b8g8r8,
#else
.pixman_format = PIXMAN_r8g8b8a8,
#endif
},
{
.drm_format = DRM_FORMAT_RGBX8888,
#if WLR_BIG_ENDIAN
.pixman_format = PIXMAN_x8b8g8r8,
#else
.pixman_format = PIXMAN_r8g8b8x8,
#endif
},
{
.drm_format = DRM_FORMAT_BGRA8888,
#if WLR_BIG_ENDIAN
.pixman_format = PIXMAN_a8r8g8b8,
#else
.pixman_format = PIXMAN_b8g8r8a8,
#endif
},
{
.drm_format = DRM_FORMAT_BGRX8888,
#if WLR_BIG_ENDIAN
.pixman_format = PIXMAN_x8r8g8b8,
#else
.pixman_format = PIXMAN_b8g8r8x8,
#endif
},
#if WLR_LITTLE_ENDIAN
// Since DRM formats are always little-endian, they don't have an
// equivalent on big-endian if their components are spanning across
// multiple bytes.
{
.drm_format = DRM_FORMAT_RGB565,
.pixman_format = PIXMAN_r5g6b5,
},
{
.drm_format = DRM_FORMAT_BGR565,
.pixman_format = PIXMAN_b5g6r5,
},
{
.drm_format = DRM_FORMAT_ARGB2101010,
.pixman_format = PIXMAN_a2r10g10b10,
},
{
.drm_format = DRM_FORMAT_XRGB2101010,
.pixman_format = PIXMAN_x2r10g10b10,
},
{
.drm_format = DRM_FORMAT_ABGR2101010,
.pixman_format = PIXMAN_a2b10g10r10,
},
{
.drm_format = DRM_FORMAT_XBGR2101010,
.pixman_format = PIXMAN_x2b10g10r10,
},
#endif
};
pixman_format_code_t get_pixman_format_from_drm(uint32_t fmt) {

View File

@ -457,8 +457,8 @@ struct wlr_output_mode *wlr_output_preferred_mode(struct wlr_output *output) {
}
}
// No preferred mode, choose the last one
return wl_container_of(output->modes.prev, mode, link);
// No preferred mode, choose the first one
return wl_container_of(output->modes.next, mode, link);
}
static void output_state_clear_buffer(struct wlr_output_state *state) {
@ -677,6 +677,12 @@ static bool output_ensure_buffer(struct wlr_output *output) {
return true;
}
// If the backend doesn't necessarily need a new buffer on modeset, don't
// bother allocating one.
if (!output->impl->test || output->impl->test(output)) {
return true;
}
wlr_log(WLR_DEBUG, "Attaching empty buffer to output for modeset");
if (!output_attach_empty_buffer(output)) {

View File

@ -327,11 +327,6 @@ static void surface_state_move(struct wlr_surface_state *state,
if (next->committed & WLR_SURFACE_STATE_BUFFER_DAMAGE) {
pixman_region32_clear(&next->buffer_damage);
}
if (next->committed & WLR_SURFACE_STATE_FRAME_CALLBACK_LIST) {
wl_list_insert_list(&state->frame_callback_list,
&next->frame_callback_list);
wl_list_init(&next->frame_callback_list);
}
next->committed = 0;
next->cached_state_locks = 0;
@ -501,6 +496,14 @@ static void surface_commit_pending(struct wlr_surface *surface) {
surface->role->precommit(surface);
}
// It doesn't to make sense to cache callback lists, so we always move
// them to the current state.
if (surface->pending.committed & WLR_SURFACE_STATE_FRAME_CALLBACK_LIST) {
wl_list_insert_list(&surface->current.frame_callback_list,
&surface->pending.frame_callback_list);
wl_list_init(&surface->pending.frame_callback_list);
}
if (surface->pending.cached_state_locks > 0 || !wl_list_empty(&surface->cached)) {
surface_cache_pending(surface);
} else {

View File

@ -95,6 +95,12 @@ static void viewport_destroy(struct wlr_viewport *viewport) {
if (viewport == NULL) {
return;
}
struct wlr_surface_state *pending = &viewport->surface->pending;
pending->viewport.has_src = false;
pending->viewport.has_dst = false;
pending->committed |= WLR_SURFACE_STATE_VIEWPORT;
wl_resource_set_user_data(viewport->resource, NULL);
wl_list_remove(&viewport->surface_destroy.link);
wl_list_remove(&viewport->surface_commit.link);