mirror of
https://github.com/brl/mutter.git
synced 2024-12-23 11:32:04 +00:00
kms/crtc: Read gamma state when prediction failed
If we did a mode set, the gamma may have been changed by the kernel, and if we didn't also update the gamma in the same transaction, we have no way to predict the current gamma ramp state. In this case, read the gamma state directly from KMS. This should be relatively harmless regarding the race conditions the state prediction was meant to solve, as the worst case is we get none or out of date gamma ramps; and since this is for when gamma ramps are not updated at mode setting time, we'd get intermediate gamma state to begin with, so it's not worse than what we currently do anyway. Fixes: https://gitlab.gnome.org/GNOME/mutter/issues/851 https://gitlab.gnome.org/GNOME/mutter/merge_requests/840
This commit is contained in:
parent
1cc249fe18
commit
1b4709794e
@ -143,14 +143,26 @@ meta_kms_crtc_update_state (MetaKmsCrtc *crtc)
|
||||
drmModeFreeCrtc (drm_crtc);
|
||||
}
|
||||
|
||||
static void
|
||||
clear_gamma_state (MetaKmsCrtc *crtc)
|
||||
{
|
||||
crtc->current_state.gamma.size = 0;
|
||||
g_clear_pointer (&crtc->current_state.gamma.red, g_free);
|
||||
g_clear_pointer (&crtc->current_state.gamma.green, g_free);
|
||||
g_clear_pointer (&crtc->current_state.gamma.blue, g_free);
|
||||
}
|
||||
|
||||
void
|
||||
meta_kms_crtc_predict_state (MetaKmsCrtc *crtc,
|
||||
MetaKmsUpdate *update)
|
||||
{
|
||||
gboolean is_gamma_valid;
|
||||
GList *mode_sets;
|
||||
GList *crtc_gammas;
|
||||
GList *l;
|
||||
|
||||
is_gamma_valid = TRUE;
|
||||
|
||||
mode_sets = meta_kms_update_get_mode_sets (update);
|
||||
for (l = mode_sets; l; l = l->next)
|
||||
{
|
||||
@ -178,6 +190,8 @@ meta_kms_crtc_predict_state (MetaKmsCrtc *crtc,
|
||||
crtc->current_state.drm_mode = (drmModeModeInfo) { 0 };
|
||||
}
|
||||
|
||||
is_gamma_valid = FALSE;
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
@ -196,8 +210,36 @@ meta_kms_crtc_predict_state (MetaKmsCrtc *crtc,
|
||||
g_memdup (gamma->green, gamma->size * sizeof (uint16_t));
|
||||
crtc->current_state.gamma.blue =
|
||||
g_memdup (gamma->blue, gamma->size * sizeof (uint16_t));
|
||||
|
||||
is_gamma_valid = TRUE;
|
||||
break;
|
||||
}
|
||||
|
||||
if (!is_gamma_valid)
|
||||
{
|
||||
if (crtc->current_state.is_drm_mode_valid)
|
||||
{
|
||||
MetaKmsImplDevice *impl_device;
|
||||
drmModeCrtc *drm_crtc;
|
||||
|
||||
impl_device = meta_kms_device_get_impl_device (crtc->device);
|
||||
drm_crtc = drmModeGetCrtc (meta_kms_impl_device_get_fd (impl_device),
|
||||
crtc->id);
|
||||
if (drm_crtc)
|
||||
{
|
||||
read_gamma_state (crtc, impl_device, drm_crtc);
|
||||
drmModeFreeCrtc (drm_crtc);
|
||||
}
|
||||
else
|
||||
{
|
||||
clear_gamma_state (crtc);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
clear_gamma_state (crtc);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
MetaKmsCrtc *
|
||||
@ -220,9 +262,7 @@ meta_kms_crtc_finalize (GObject *object)
|
||||
{
|
||||
MetaKmsCrtc *crtc = META_KMS_CRTC (object);
|
||||
|
||||
g_clear_pointer (&crtc->current_state.gamma.red, g_free);
|
||||
g_clear_pointer (&crtc->current_state.gamma.green, g_free);
|
||||
g_clear_pointer (&crtc->current_state.gamma.blue, g_free);
|
||||
clear_gamma_state (crtc);
|
||||
|
||||
G_OBJECT_CLASS (meta_kms_crtc_parent_class)->finalize (object);
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user