The issue is in git master and bisecting shows it to be this commit:
commit 7d9a74622e5a936e4860fcef8358619bf59adae8 Author: Chris Wilson <email address hidden> Date: Mon Jun 15 14:16:34 2015 +0100
sna: Be robust in handling DPMS failures
If we fail to turn off an output via DPMS, disable the entire CRTC in order to blank the output and save the screeen/power.
Reported-by: Lukas Hejtmanek <email address hidden> References: https://bugs.freedesktop.org/show_bug.cgi?id=90179 Signed-off-by: Chris Wilson <email address hidden>
diff --git a/src/sna/sna_display.c b/src/sna/sna_display.c index f58eb8d..efc5fc9 100644 --- a/src/sna/sna_display.c +++ b/src/sna/sna_display.c @@ -213,7 +213,7 @@ struct sna_output { int panel_vdisplay;
uint32_t dpms_id; - int dpms_mode; + uint8_t dpms_mode; struct backlight backlight; int backlight_active_level;
@@ -251,6 +251,7 @@ enum { /* XXX copied from hw/xfree86/modes/xf86Crtc.c */ OPTION_DEFAULT_MODES, };
+static void __sna_output_dpms(xf86OutputPtr output, int dpms, int fixup); static void sna_crtc_disable_cursor(struct sna *sna, struct sna_crtc *crtc);
static bool is_zaphod(ScrnInfoPtr scrn) @@ -936,7 +937,7 @@ sna_crtc_force_outputs_on(xf86CrtcPtr crtc) if (output->crtc != crtc) continue;
- output->funcs->dpms(output, DPMSModeOn); + __sna_output_dpms(output, DPMSModeOn, false); }
#if XF86_CRTC_VERSION >= 3 @@ -966,7 +967,7 @@ sna_crtc_force_outputs_off(xf86CrtcPtr crtc) if (output->crtc != crtc) continue;
- output->funcs->dpms(output, DPMSModeOff); + __sna_output_dpms(output, DPMSModeOff, false); } }
@@ -1099,7 +1100,7 @@ sna_crtc_apply(xf86CrtcPtr crtc) * and we lose track of the user settings. */ if (output->crtc == NULL) - output->funcs->dpms(output, DPMSModeOff); + __sna_output_dpms(output, DPMSModeOff, false);
if (output->crtc != crtc) continue; @@ -3580,7 +3581,7 @@ sna_output_destroy(xf86OutputPtr output) }
static void -sna_output_dpms(xf86OutputPtr output, int dpms) +__sna_output_dpms(xf86OutputPtr output, int dpms, int fixup) { struct sna *sna = to_sna(output->scrn); struct sna_output *sna_output = output->driver_private; @@ -3607,8 +3608,9 @@ sna_output_dpms(xf86OutputPtr output, int dpms) if (sna_output->backlight.iface && dpms != DPMSModeOn) { if (old_dpms == DPMSModeOn) { sna_output->backlight_active_level = sna_output_backlight_get(output); - DBG(("%s: saving current backlight %d\n", - __FUNCTION__, sna_output->backlight_active_level)); + DBG(("%s(%s:%d): saving current backlight %d\n", + __FUNCTION__, output->name, sna_output->id, + sna_output->backlight_active_level)); } sna_output->dpms_mode = dpms; sna_output_backlight_off(sna_output); @@ -3618,18 +3620,31 @@ sna_output_dpms(xf86OutputPtr output, int dpms) drmModeConnectorSetProperty(sna->kgem.fd, sna_output->id, sna_output->dpms_id, - dpms)) - dpms = old_dpms; + dpms)) { + DBG(("%s(%s:%d): failed to set DPMS to %d (fixup? %d)\n", + __FUNCTION__, output->name, sna_output->id, dpms, fixup)); + if (fixup) { + sna_crtc_disable(output->crtc, false); + return; + } + }
if (sna_output->backlight.iface && dpms == DPMSModeOn) { - DBG(("%s: restoring previous backlight %d\n", - __FUNCTION__, sna_output->backlight_active_level)); + DBG(("%s(%d:%d: restoring previous backlight %d\n", + __FUNCTION__, output->name, sna_output->id, + sna_output->backlight_active_level)); sna_output_backlight_on(sna_output); }
sna_output->dpms_mode = dpms; }
+static void +sna_output_dpms(xf86OutputPtr output, int dpms) +{ + __sna_output_dpms(output, dpms, true); +} + static bool sna_property_ignore(drmModePropertyPtr prop) { @@ -4438,10 +4453,8 @@ reset: sna_output->dpms_mode = sna_output->prop_values[i]; DBG(("%s: found 'DPMS' (idx=%d, id=%d), initial value=%d\n", __FUNCTION__, i, sna_output->dpms_id, sna_output->dpms_mode)); - } else { - sna_output->dpms_id = -1; + } else sna_output->dpms_mode = DPMSModeOff; - }
sna_output->possible_encoders = possible_encoders; sna_output->attached_encoders = attached_encoders;
The issue is in git master and bisecting shows it to be this commit:
commit 7d9a74622e5a936 e4860fcef835861 9bf59adae8
Author: Chris Wilson <email address hidden>
Date: Mon Jun 15 14:16:34 2015 +0100
sna: Be robust in handling DPMS failures
If we fail to turn off an output via DPMS, disable the entire CRTC in
order to blank the output and save the screeen/power.
Reported-by: Lukas Hejtmanek <email address hidden> /bugs.freedeskt op.org/ show_bug. cgi?id= 90179
References: https:/
Signed-off-by: Chris Wilson <email address hidden>
diff --git a/src/sna/ sna_display. c b/src/sna/ sna_display. c sna_display. c sna_display. c
index f58eb8d..efc5fc9 100644
--- a/src/sna/
+++ b/src/sna/
@@ -213,7 +213,7 @@ struct sna_output {
int panel_vdisplay;
uint32_t dpms_id; active_ level;
- int dpms_mode;
+ uint8_t dpms_mode;
struct backlight backlight;
int backlight_
@@ -251,6 +251,7 @@ enum { /* XXX copied from hw/xfree86/ modes/xf86Crtc. c */ DEFAULT_ MODES,
OPTION_
};
+static void __sna_output_ dpms(xf86Output Ptr output, int dpms, int fixup); disable_ cursor( struct sna *sna, struct sna_crtc *crtc);
static void sna_crtc_
static bool is_zaphod( ScrnInfoPtr scrn) force_outputs_ on(xf86CrtcPtr crtc)
@@ -936,7 +937,7 @@ sna_crtc_
if (output->crtc != crtc)
continue;
- output- >funcs- >dpms(output, DPMSModeOn); dpms(output, DPMSModeOn, false);
+ __sna_output_
}
#if XF86_CRTC_VERSION >= 3 force_outputs_ off(xf86CrtcPtr crtc)
@@ -966,7 +967,7 @@ sna_crtc_
if (output->crtc != crtc)
continue;
- output- >funcs- >dpms(output, DPMSModeOff); dpms(output, DPMSModeOff, false);
+ __sna_output_
}
}
@@ -1099,7 +1100,7 @@ sna_crtc_ apply(xf86CrtcP tr crtc) >funcs- >dpms(output, DPMSModeOff); dpms(output, DPMSModeOff, false);
* and we lose track of the user settings.
*/
if (output->crtc == NULL)
- output-
+ __sna_output_
if (output->crtc != crtc) destroy( xf86OutputPtr output)
continue;
@@ -3580,7 +3581,7 @@ sna_output_
}
static void dpms(xf86Output Ptr output, int dpms) output_ dpms(xf86Output Ptr output, int dpms, int fixup) output- >scrn); >driver_ private; dpms(xf86Output Ptr output, int dpms) >backlight. iface && dpms != DPMSModeOn) { output- >backlight_ active_ level = sna_output_ backlight_ get(output) ; >backlight_ active_ level)) ; >backlight_ active_ level)) ; output- >dpms_mode = dpms; output_ backlight_ off(sna_ output) ; dpms(xf86Output Ptr output, int dpms) nnectorSetPrope rty(sna- >kgem.fd, output- >id, output- >dpms_id, disable( output- >crtc, false);
-sna_output_
+__sna_
{
struct sna *sna = to_sna(
struct sna_output *sna_output = output-
@@ -3607,8 +3608,9 @@ sna_output_
if (sna_output-
if (old_dpms == DPMSModeOn) {
sna_
- DBG(("%s: saving current backlight %d\n",
- __FUNCTION__, sna_output-
+ DBG(("%s(%s:%d): saving current backlight %d\n",
+ __FUNCTION__, output->name, sna_output->id,
+ sna_output-
}
sna_
sna_
@@ -3618,18 +3620,31 @@ sna_output_
drmModeCo
sna_
sna_
- dpms))
- dpms = old_dpms;
+ dpms)) {
+ DBG(("%s(%s:%d): failed to set DPMS to %d (fixup? %d)\n",
+ __FUNCTION__, output->name, sna_output->id, dpms, fixup));
+ if (fixup) {
+ sna_crtc_
+ return;
+ }
+ }
if (sna_output- >backlight. iface && dpms == DPMSModeOn) { >backlight_ active_ level)) ; >backlight_ active_ level)) ; output_ backlight_ on(sna_ output) ;
- DBG(("%s: restoring previous backlight %d\n",
- __FUNCTION__, sna_output-
+ DBG(("%s(%d:%d: restoring previous backlight %d\n",
+ __FUNCTION__, output->name, sna_output->id,
+ sna_output-
sna_
}
sna_output- >dpms_mode = dpms;
}
+static void dpms(xf86Output Ptr output, int dpms) dpms(output, dpms, true); ignore( drmModeProperty Ptr prop) output- >dpms_mode = sna_output- >prop_values[ i];
__FUNCTION_ _, i, sna_output- >dpms_id, sna_output- >dpms_mode) ); output- >dpms_mode = DPMSModeOff;
+sna_output_
+{
+ __sna_output_
+}
+
static bool
sna_property_
{
@@ -4438,10 +4453,8 @@ reset:
sna_
DBG(("%s: found 'DPMS' (idx=%d, id=%d), initial value=%d\n",
- } else {
- sna_output->dpms_id = -1;
+ } else
sna_
- }
sna_output- >possible_ encoders = possible_encoders; >attached_ encoders = attached_encoders;
sna_output-