aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorPatrik Jakobsson <patrik.r.jakobsson@gmail.com>2013-04-07 10:35:50 -0400
committerPatrik Jakobsson <patrik.r.jakobsson@gmail.com>2013-04-07 11:09:37 -0400
commit749387dc8d8270b279f27a0a794cdf4f4a4aa774 (patch)
treeaf60d046754eed815c74952f2fa8129580aa6d04
parent888eef2e8c2d9fc2e6ccf58fb4a8f9f6d8ff9a22 (diff)
drm/gma500: Fix hibernation problems on sdvo encoders
The state of the SDVO chip is more difficult to save than the LVDS so we do a full mode set on the crtc to get SDVO operational again. The SDVOB/C register is also stored just in case we have special bits set in the future. Signed-off-by: Patrik Jakobsson <patrik.r.jakobsson@gmail.com>
-rw-r--r--drivers/gpu/drm/gma500/psb_intel_sdvo.c34
1 files changed, 34 insertions, 0 deletions
diff --git a/drivers/gpu/drm/gma500/psb_intel_sdvo.c b/drivers/gpu/drm/gma500/psb_intel_sdvo.c
index a4cc777ab7a6..cd1b40722edd 100644
--- a/drivers/gpu/drm/gma500/psb_intel_sdvo.c
+++ b/drivers/gpu/drm/gma500/psb_intel_sdvo.c
@@ -134,6 +134,9 @@ struct psb_intel_sdvo {
134 134
135 /* Input timings for adjusted_mode */ 135 /* Input timings for adjusted_mode */
136 struct psb_intel_sdvo_dtd input_dtd; 136 struct psb_intel_sdvo_dtd input_dtd;
137
138 /* Saved SDVO output states */
139 uint32_t saveSDVO; /* Can be SDVOB or SDVOC depending on sdvo_reg */
137}; 140};
138 141
139struct psb_intel_sdvo_connector { 142struct psb_intel_sdvo_connector {
@@ -1830,6 +1833,35 @@ done:
1830#undef CHECK_PROPERTY 1833#undef CHECK_PROPERTY
1831} 1834}
1832 1835
1836static void psb_intel_sdvo_save(struct drm_connector *connector)
1837{
1838 struct drm_device *dev = connector->dev;
1839 struct psb_intel_encoder *psb_intel_encoder =
1840 psb_intel_attached_encoder(connector);
1841 struct psb_intel_sdvo *sdvo =
1842 to_psb_intel_sdvo(&psb_intel_encoder->base);
1843
1844 sdvo->saveSDVO = REG_READ(sdvo->sdvo_reg);
1845}
1846
1847static void psb_intel_sdvo_restore(struct drm_connector *connector)
1848{
1849 struct drm_device *dev = connector->dev;
1850 struct drm_encoder *encoder =
1851 &psb_intel_attached_encoder(connector)->base;
1852 struct psb_intel_sdvo *sdvo = to_psb_intel_sdvo(encoder);
1853 struct drm_crtc *crtc = encoder->crtc;
1854
1855 REG_WRITE(sdvo->sdvo_reg, sdvo->saveSDVO);
1856
1857 /* Force dpms on upon resume */
1858 psb_intel_sdvo_dpms(encoder, DRM_MODE_DPMS_ON);
1859
1860 /* Force a full mode set on the crtc. We're supposed to have the
1861 mode_config lock already. */
1862 drm_crtc_helper_set_mode(crtc, &crtc->mode, crtc->x, crtc->y, NULL);
1863}
1864
1833static const struct drm_encoder_helper_funcs psb_intel_sdvo_helper_funcs = { 1865static const struct drm_encoder_helper_funcs psb_intel_sdvo_helper_funcs = {
1834 .dpms = psb_intel_sdvo_dpms, 1866 .dpms = psb_intel_sdvo_dpms,
1835 .mode_fixup = psb_intel_sdvo_mode_fixup, 1867 .mode_fixup = psb_intel_sdvo_mode_fixup,
@@ -1840,6 +1872,8 @@ static const struct drm_encoder_helper_funcs psb_intel_sdvo_helper_funcs = {
1840 1872
1841static const struct drm_connector_funcs psb_intel_sdvo_connector_funcs = { 1873static const struct drm_connector_funcs psb_intel_sdvo_connector_funcs = {
1842 .dpms = drm_helper_connector_dpms, 1874 .dpms = drm_helper_connector_dpms,
1875 .save = psb_intel_sdvo_save,
1876 .restore = psb_intel_sdvo_restore,
1843 .detect = psb_intel_sdvo_detect, 1877 .detect = psb_intel_sdvo_detect,
1844 .fill_modes = drm_helper_probe_single_connector_modes, 1878 .fill_modes = drm_helper_probe_single_connector_modes,
1845 .set_property = psb_intel_sdvo_set_property, 1879 .set_property = psb_intel_sdvo_set_property,