This should be a small power savings. Tested on Lenovo T410 (Ironlake), LVDS
VGA and DisplayPort, up to 1920x1200R.

v2: Add Sandybridge support, fix obvious math error.

Acked-by: Zhenyu Wang <zhen...@linux.intel.com>
Signed-off-by: Adam Jackson <a...@redhat.com>
---
 drivers/gpu/drm/i915/intel_display.c |   26 ++++++++++++++++++++------
 drivers/gpu/drm/i915/intel_drv.h     |    1 +
 2 files changed, 21 insertions(+), 6 deletions(-)

diff --git a/drivers/gpu/drm/i915/intel_display.c 
b/drivers/gpu/drm/i915/intel_display.c
index 1a7c7ac..f532fc6 100644
--- a/drivers/gpu/drm/i915/intel_display.c
+++ b/drivers/gpu/drm/i915/intel_display.c
@@ -1524,7 +1524,8 @@ static void ironlake_fdi_link_train(struct drm_crtc *crtc)
        /* enable CPU FDI TX and PCH FDI RX */
        temp = I915_READ(fdi_tx_reg);
        temp |= FDI_TX_ENABLE;
-       temp |= FDI_DP_PORT_WIDTH_X4; /* default */
+       temp &= ~(7 << 19);
+       temp |= (intel_crtc->fdi_lanes - 1) << 19;
        temp &= ~FDI_LINK_TRAIN_NONE;
        temp |= FDI_LINK_TRAIN_PATTERN_1;
        I915_WRITE(fdi_tx_reg, temp);
@@ -1624,7 +1625,8 @@ static void gen6_fdi_link_train(struct drm_crtc *crtc)
        /* enable CPU FDI TX and PCH FDI RX */
        temp = I915_READ(fdi_tx_reg);
        temp |= FDI_TX_ENABLE;
-       temp |= FDI_DP_PORT_WIDTH_X4; /* default */
+       temp &= ~(7 << 19);
+       temp |= (intel_crtc->fdi_lanes - 1) << 19;
        temp &= ~FDI_LINK_TRAIN_NONE;
        temp |= FDI_LINK_TRAIN_PATTERN_1;
        temp &= ~FDI_LINK_TRAIN_VOL_EMP_MASK;
@@ -1786,8 +1788,9 @@ static void ironlake_crtc_dpms(struct drm_crtc *crtc, int 
mode)
                         */
                        temp &= ~(0x7 << 16);
                        temp |= (pipe_bpc << 11);
-                       I915_WRITE(fdi_rx_reg, temp | FDI_RX_PLL_ENABLE |
-                                       FDI_DP_PORT_WIDTH_X4); /* default 4 
lanes */
+                       temp &= ~(7 << 19);
+                       temp |= (intel_crtc->fdi_lanes - 1) << 19;
+                       I915_WRITE(fdi_rx_reg, temp | FDI_RX_PLL_ENABLE);
                        I915_READ(fdi_rx_reg);
                        udelay(200);
 
@@ -3260,7 +3263,7 @@ static int intel_crtc_mode_set(struct drm_crtc *crtc,
 
        /* FDI link */
        if (HAS_PCH_SPLIT(dev)) {
-               int lane, link_bw, bpp;
+               int lane = 0, link_bw, bpp;
                /* eDP doesn't require FDI link, so just set DP M/N
                   according to current link config */
                if (is_edp) {
@@ -3276,7 +3279,6 @@ static int intel_crtc_mode_set(struct drm_crtc *crtc,
                                target_clock = mode->clock;
                        else
                                target_clock = adjusted_mode->clock;
-                       lane = 4;
                        link_bw = 270000;
                }
 
@@ -3328,6 +3330,18 @@ static int intel_crtc_mode_set(struct drm_crtc *crtc,
                        bpp = 24;
                }
 
+               if (!lane) {
+                       /* 
+                        * Account for spread spectrum to avoid
+                        * oversubscribing the link. Max center spread
+                        * is 2.5%; use 5% for safety's sake.
+                        */
+                       u32 bps = target_clock * bpp * 21 / 20;
+                       lane = bps / (link_bw * 8) + 1;
+               }
+
+               intel_crtc->fdi_lanes = lane;
+
                ironlake_compute_m_n(bpp, lane, target_clock, link_bw, &m_n);
        }
 
diff --git a/drivers/gpu/drm/i915/intel_drv.h b/drivers/gpu/drm/i915/intel_drv.h
index c15ec47..d716f35 100644
--- a/drivers/gpu/drm/i915/intel_drv.h
+++ b/drivers/gpu/drm/i915/intel_drv.h
@@ -154,6 +154,7 @@ struct intel_crtc {
        bool lowfreq_avail;
        struct intel_overlay *overlay;
        struct intel_unpin_work *unpin_work;
+       int fdi_lanes;
 };
 
 #define to_intel_crtc(x) container_of(x, struct intel_crtc, base)
-- 
1.6.6.1

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
http://lists.freedesktop.org/mailman/listinfo/intel-gfx

Reply via email to