aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/gpu/drm/nouveau/nvd0_display.c
diff options
context:
space:
mode:
authorBen Skeggs <bskeggs@redhat.com>2011-07-07 22:52:14 -0400
committerBen Skeggs <bskeggs@redhat.com>2011-09-20 02:07:36 -0400
commit3b6d83d1b9f9be1c9778c2c6fa6761b440734fdd (patch)
tree1c32bae50b918f50e4268b1289d495e301b166dd /drivers/gpu/drm/nouveau/nvd0_display.c
parentc6f2f71daed12f57d6f72769b49d29c7391f24ae (diff)
drm/nvd0/disp: untested LVDS support
Signed-off-by: Ben Skeggs <bskeggs@redhat.com>
Diffstat (limited to 'drivers/gpu/drm/nouveau/nvd0_display.c')
-rw-r--r--drivers/gpu/drm/nouveau/nvd0_display.c82
1 files changed, 66 insertions, 16 deletions
diff --git a/drivers/gpu/drm/nouveau/nvd0_display.c b/drivers/gpu/drm/nouveau/nvd0_display.c
index 45f8a31e9ac3..1a561d308215 100644
--- a/drivers/gpu/drm/nouveau/nvd0_display.c
+++ b/drivers/gpu/drm/nouveau/nvd0_display.c
@@ -816,26 +816,66 @@ nvd0_sor_commit(struct drm_encoder *encoder)
816} 816}
817 817
818static void 818static void
819nvd0_sor_mode_set(struct drm_encoder *encoder, struct drm_display_mode *mode, 819nvd0_sor_mode_set(struct drm_encoder *encoder, struct drm_display_mode *umode,
820 struct drm_display_mode *adjusted_mode) 820 struct drm_display_mode *mode)
821{ 821{
822 struct drm_nouveau_private *dev_priv = encoder->dev->dev_private;
822 struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); 823 struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder);
823 struct nouveau_crtc *nv_crtc = nouveau_crtc(encoder->crtc); 824 struct nouveau_crtc *nv_crtc = nouveau_crtc(encoder->crtc);
825 struct nouveau_connector *nv_connector;
826 struct nvbios *bios = &dev_priv->vbios;
824 u32 mode_ctrl = (1 << nv_crtc->index); 827 u32 mode_ctrl = (1 << nv_crtc->index);
825 u32 *push, or_config; 828 u32 *push, or_config;
826 829
827 if (nv_encoder->dcb->sorconf.link & 1) { 830 nv_connector = nouveau_encoder_connector_get(nv_encoder);
828 if (adjusted_mode->clock < 165000) 831 switch (nv_encoder->dcb->type) {
829 mode_ctrl |= 0x00000100; 832 case OUTPUT_TMDS:
830 else 833 if (nv_encoder->dcb->sorconf.link & 1) {
831 mode_ctrl |= 0x00000500; 834 if (mode->clock < 165000)
832 } else { 835 mode_ctrl |= 0x00000100;
833 mode_ctrl |= 0x00000200; 836 else
834 } 837 mode_ctrl |= 0x00000500;
838 } else {
839 mode_ctrl |= 0x00000200;
840 }
841
842 or_config = (mode_ctrl & 0x00000f00) >> 8;
843 if (mode->clock >= 165000)
844 or_config |= 0x0100;
845 break;
846 case OUTPUT_LVDS:
847 or_config = (mode_ctrl & 0x00000f00) >> 8;
848 if (bios->fp_no_ddc) {
849 if (bios->fp.dual_link)
850 or_config |= 0x0100;
851 if (bios->fp.if_is_24bit)
852 or_config |= 0x0200;
853 } else {
854 if (nv_connector->dcb->type == DCB_CONNECTOR_LVDS_SPWG) {
855 if (((u8 *)nv_connector->edid)[121] == 2)
856 or_config |= 0x0100;
857 } else
858 if (mode->clock >= bios->fp.duallink_transition_clk) {
859 or_config |= 0x0100;
860 }
835 861
836 or_config = (mode_ctrl & 0x00000f00) >> 8; 862 if (or_config & 0x0100) {
837 if (adjusted_mode->clock >= 165000) 863 if (bios->fp.strapless_is_24bit & 2)
838 or_config |= 0x0100; 864 or_config |= 0x0200;
865 } else {
866 if (bios->fp.strapless_is_24bit & 1)
867 or_config |= 0x0200;
868 }
869
870 if (nv_connector->base.display_info.bpc == 8)
871 or_config |= 0x0200;
872
873 }
874 break;
875 default:
876 BUG_ON(1);
877 break;
878 }
839 879
840 nvd0_sor_dpms(encoder, DRM_MODE_DPMS_ON); 880 nvd0_sor_dpms(encoder, DRM_MODE_DPMS_ON);
841 881
@@ -932,8 +972,16 @@ lookup_dcb(struct drm_device *dev, int id, u32 mc)
932 type = OUTPUT_ANALOG; 972 type = OUTPUT_ANALOG;
933 or = id; 973 or = id;
934 } else { 974 } else {
935 type = OUTPUT_TMDS; 975 switch (mc & 0x00000f00) {
936 or = id - 4; 976 case 0x00000000: type = OUTPUT_LVDS; break;
977 case 0x00000100: type = OUTPUT_TMDS; break;
978 case 0x00000200: type = OUTPUT_TMDS; break;
979 case 0x00000500: type = OUTPUT_TMDS; break;
980 default:
981 return NULL;
982 }
983
984 or = id - 4;
937 } 985 }
938 986
939 for (i = 0; i < dev_priv->vbios.dcb.entries; i++) { 987 for (i = 0; i < dev_priv->vbios.dcb.entries; i++) {
@@ -1024,7 +1072,8 @@ nvd0_display_unk2_handler(struct drm_device *dev)
1024 nv_wr32(dev, 0x612280 + (or * 0x800), 0x00000000); 1072 nv_wr32(dev, 0x612280 + (or * 0x800), 0x00000000);
1025 break; 1073 break;
1026 case OUTPUT_TMDS: 1074 case OUTPUT_TMDS:
1027 if (disp->irq.pclk >= 165000) 1075 case OUTPUT_LVDS:
1076 if (disp->irq.cfg & 0x00000100)
1028 tmp = 0x00000101; 1077 tmp = 0x00000101;
1029 else 1078 else
1030 tmp = 0x00000000; 1079 tmp = 0x00000000;
@@ -1298,6 +1347,7 @@ nvd0_display_create(struct drm_device *dev)
1298 1347
1299 switch (dcbe->type) { 1348 switch (dcbe->type) {
1300 case OUTPUT_TMDS: 1349 case OUTPUT_TMDS:
1350 case OUTPUT_LVDS:
1301 nvd0_sor_create(connector, dcbe); 1351 nvd0_sor_create(connector, dcbe);
1302 break; 1352 break;
1303 case OUTPUT_ANALOG: 1353 case OUTPUT_ANALOG: