diff options
author | Ben Skeggs <bskeggs@redhat.com> | 2011-07-07 21:53:37 -0400 |
---|---|---|
committer | Ben Skeggs <bskeggs@redhat.com> | 2011-09-20 02:07:29 -0400 |
commit | ff8ff50342f377b04d576d723b79f1c98200e501 (patch) | |
tree | 258e2a7c49f19333b5e8719432218549fd0e7fe4 /drivers/gpu/drm/nouveau/nvd0_display.c | |
parent | b681993f7a48b847f3129abd8e8b3926c108a0d9 (diff) |
drm/nvd0/disp: determine U table config in or_mode_set()
Takes a gamble and presumes that we can safely store something random in
OR_MODE_CTRL+4, the hw doesn't seem to mind...
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.c | 36 |
1 files changed, 15 insertions, 21 deletions
diff --git a/drivers/gpu/drm/nouveau/nvd0_display.c b/drivers/gpu/drm/nouveau/nvd0_display.c index f4788d819ed6..60454889118d 100644 --- a/drivers/gpu/drm/nouveau/nvd0_display.c +++ b/drivers/gpu/drm/nouveau/nvd0_display.c | |||
@@ -49,7 +49,7 @@ struct nvd0_display { | |||
49 | struct dcb_entry *ena; | 49 | struct dcb_entry *ena; |
50 | int crtc; | 50 | int crtc; |
51 | int pclk; | 51 | int pclk; |
52 | u16 script; | 52 | u16 cfg; |
53 | } irq; | 53 | } irq; |
54 | }; | 54 | }; |
55 | 55 | ||
@@ -649,10 +649,11 @@ nvd0_dac_mode_set(struct drm_encoder *encoder, struct drm_display_mode *mode, | |||
649 | 649 | ||
650 | nvd0_dac_dpms(encoder, DRM_MODE_DPMS_ON); | 650 | nvd0_dac_dpms(encoder, DRM_MODE_DPMS_ON); |
651 | 651 | ||
652 | push = evo_wait(encoder->dev, 0, 2); | 652 | push = evo_wait(encoder->dev, 0, 4); |
653 | if (push) { | 653 | if (push) { |
654 | evo_mthd(push, 0x0180 + (nv_encoder->or * 0x20), 1); | 654 | evo_mthd(push, 0x0180 + (nv_encoder->or * 0x20), 2); |
655 | evo_data(push, 1 << nv_crtc->index); | 655 | evo_data(push, 1 << nv_crtc->index); |
656 | evo_data(push, 0x00ff); | ||
656 | evo_kick(push, encoder->dev, 0); | 657 | evo_kick(push, encoder->dev, 0); |
657 | } | 658 | } |
658 | 659 | ||
@@ -821,7 +822,7 @@ nvd0_sor_mode_set(struct drm_encoder *encoder, struct drm_display_mode *mode, | |||
821 | struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); | 822 | struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); |
822 | struct nouveau_crtc *nv_crtc = nouveau_crtc(encoder->crtc); | 823 | struct nouveau_crtc *nv_crtc = nouveau_crtc(encoder->crtc); |
823 | u32 mode_ctrl = (1 << nv_crtc->index); | 824 | u32 mode_ctrl = (1 << nv_crtc->index); |
824 | u32 *push; | 825 | u32 *push, or_config; |
825 | 826 | ||
826 | if (nv_encoder->dcb->sorconf.link & 1) { | 827 | if (nv_encoder->dcb->sorconf.link & 1) { |
827 | if (adjusted_mode->clock < 165000) | 828 | if (adjusted_mode->clock < 165000) |
@@ -832,12 +833,17 @@ nvd0_sor_mode_set(struct drm_encoder *encoder, struct drm_display_mode *mode, | |||
832 | mode_ctrl |= 0x00000200; | 833 | mode_ctrl |= 0x00000200; |
833 | } | 834 | } |
834 | 835 | ||
836 | or_config = (mode_ctrl & 0x00000f00) >> 8; | ||
837 | if (adjusted_mode->clock >= 165000) | ||
838 | or_config |= 0x0100; | ||
839 | |||
835 | nvd0_sor_dpms(encoder, DRM_MODE_DPMS_ON); | 840 | nvd0_sor_dpms(encoder, DRM_MODE_DPMS_ON); |
836 | 841 | ||
837 | push = evo_wait(encoder->dev, 0, 2); | 842 | push = evo_wait(encoder->dev, 0, 4); |
838 | if (push) { | 843 | if (push) { |
839 | evo_mthd(push, 0x0200 + (nv_encoder->or * 0x20), 1); | 844 | evo_mthd(push, 0x0200 + (nv_encoder->or * 0x20), 2); |
840 | evo_data(push, mode_ctrl); | 845 | evo_data(push, mode_ctrl); |
846 | evo_data(push, or_config); | ||
841 | evo_kick(push, encoder->dev, 0); | 847 | evo_kick(push, encoder->dev, 0); |
842 | } | 848 | } |
843 | 849 | ||
@@ -971,20 +977,8 @@ nvd0_display_unk1_handler(struct drm_device *dev) | |||
971 | disp->irq.dis = lookup_dcb(dev, i, mcc); | 977 | disp->irq.dis = lookup_dcb(dev, i, mcc); |
972 | 978 | ||
973 | if (mcp & (1 << crtc)) { | 979 | if (mcp & (1 << crtc)) { |
980 | disp->irq.cfg = nv_rd32(dev, 0x660184 + (i * 0x20)); | ||
974 | disp->irq.ena = lookup_dcb(dev, i, mcp); | 981 | disp->irq.ena = lookup_dcb(dev, i, mcp); |
975 | switch (disp->irq.ena->type) { | ||
976 | case OUTPUT_ANALOG: | ||
977 | disp->irq.script = 0x00ff; | ||
978 | break; | ||
979 | case OUTPUT_TMDS: | ||
980 | disp->irq.script = (mcp & 0x00000f00) >> 8; | ||
981 | if (disp->irq.pclk >= 165000) | ||
982 | disp->irq.script |= 0x0100; | ||
983 | break; | ||
984 | default: | ||
985 | disp->irq.script = 0xbeef; | ||
986 | break; | ||
987 | } | ||
988 | } | 982 | } |
989 | } | 983 | } |
990 | 984 | ||
@@ -1022,7 +1016,7 @@ nvd0_display_unk2_handler(struct drm_device *dev) | |||
1022 | goto ack; | 1016 | goto ack; |
1023 | or = ffs(dcb->or) - 1; | 1017 | or = ffs(dcb->or) - 1; |
1024 | 1018 | ||
1025 | nouveau_bios_run_display_table(dev, disp->irq.script, pclk, dcb, crtc); | 1019 | nouveau_bios_run_display_table(dev, disp->irq.cfg, pclk, dcb, crtc); |
1026 | 1020 | ||
1027 | nv_wr32(dev, 0x612200 + (crtc * 0x800), 0x00000000); | 1021 | nv_wr32(dev, 0x612200 + (crtc * 0x800), 0x00000000); |
1028 | switch (dcb->type) { | 1022 | switch (dcb->type) { |
@@ -1063,7 +1057,7 @@ nvd0_display_unk4_handler(struct drm_device *dev) | |||
1063 | if (!dcb) | 1057 | if (!dcb) |
1064 | goto ack; | 1058 | goto ack; |
1065 | 1059 | ||
1066 | nouveau_bios_run_display_table(dev, disp->irq.script, pclk, dcb, crtc); | 1060 | nouveau_bios_run_display_table(dev, disp->irq.cfg, pclk, dcb, crtc); |
1067 | 1061 | ||
1068 | ack: | 1062 | ack: |
1069 | nv_wr32(dev, 0x6101d4, 0x00000000); | 1063 | nv_wr32(dev, 0x6101d4, 0x00000000); |