drm/nouveau/kms/nv50-: Introduce nv50_wndw_default_state()

While we don't currently read-in the hardware state of planes, now that
we're about to start exposing blend properties for all planes that can
support alpha channels: We need to make sure that the initial atomic state
for a wndw always starts off with a supported value in pixel_blend_mode.

The easiest way to do this is to introduce a nv50_wndw_default_state()
function, and use it in nv50_display_read_hw_state() - and use that
function to enforce a valid value for pixel_blend_mode during driver
startup.

Signed-off-by: Lyude Paul <lyude@redhat.com>
Reviewed-by: Dave Airlie <airlied@redhat.com>
Fixes: 860e748bdd ("drm: ensure blend mode supported if pixel format with alpha exposed")
Link: https://patch.msgid.link/20260720215058.398210-3-lyude@redhat.com
This commit is contained in:
Lyude Paul
2026-07-20 17:36:17 -04:00
parent a7e8cf887a
commit 8d092b0523
3 changed files with 27 additions and 0 deletions

View File

@@ -2768,6 +2768,7 @@ nv50_display_read_hw_state(struct nouveau_drm *drm)
{
struct drm_device *dev = drm->dev;
struct drm_encoder *encoder;
struct drm_plane *plane;
struct drm_modeset_acquire_ctx ctx;
struct nv50_disp *disp = nv50_disp(dev);
int ret;
@@ -2781,6 +2782,9 @@ nv50_display_read_hw_state(struct nouveau_drm *drm)
nv50_display_read_hw_or_state(dev, disp, nouveau_encoder(encoder));
}
drm_for_each_plane(plane, dev)
nv50_wndw_default_state(nv50_wndw(plane));
DRM_MODESET_LOCK_ALL_END(dev, ctx, ret);
}

View File

@@ -848,6 +848,28 @@ static const u64 nv50_cursor_format_modifiers[] = {
DRM_FORMAT_MOD_INVALID,
};
/*
* Setup defaults for the atomic wndw state
*/
void
nv50_wndw_default_state(struct nv50_wndw *wndw)
{
struct nv50_wndw_atom *armw = nv50_wndw_atom(wndw->plane.state);
const unsigned int blend_modes = wndw->func->blend_modes;
drm_modeset_lock_assert_held(&wndw->plane.mutex);
/* Ensure the plane's atomic state didn't default to a pixel_blend_mode we don't support */
if (blend_modes && (!(BIT(armw->state.pixel_blend_mode) & blend_modes))) {
if (blend_modes & BIT(DRM_MODE_BLEND_COVERAGE))
armw->state.pixel_blend_mode = DRM_MODE_BLEND_COVERAGE;
else if (blend_modes & BIT(DRM_MODE_BLEND_PREMULTI))
armw->state.pixel_blend_mode = DRM_MODE_BLEND_PREMULTI;
else if (blend_modes & BIT(DRM_MODE_BLEND_PIXEL_NONE))
armw->state.pixel_blend_mode = DRM_MODE_BLEND_PIXEL_NONE;
}
}
int
nv50_wndw_new_(const struct nv50_wndw_func *func, struct drm_device *dev,
enum drm_plane_type type, const char *name, int index,

View File

@@ -46,6 +46,7 @@ void nv50_wndw_flush_clr(struct nv50_wndw *, u32 *interlock, bool flush,
struct nv50_wndw_atom *);
void nv50_wndw_ntfy_enable(struct nv50_wndw *, struct nv50_wndw_atom *);
int nv50_wndw_wait_armed(struct nv50_wndw *, struct nv50_wndw_atom *);
void nv50_wndw_default_state(struct nv50_wndw *wndw);
struct nv50_wndw_func {
int (*acquire)(struct nv50_wndw *, struct nv50_wndw_atom *asyw,