diff options
author | Alex Deucher <alex@botch2.(none)> | 2007-08-27 22:42:22 -0400 |
---|---|---|
committer | Alex Deucher <alex@botch2.(none)> | 2007-08-27 22:42:22 -0400 |
commit | a5a1055d64ab4fa16bfb03a412ae6c4fe69ff65d (patch) | |
tree | 8bdc0c15a1a62a9cdff9fc33c3d7a0757d35873d /src | |
parent | a12e4aa01bf1c5723c3c791ff9bdc26eef21d5ea (diff) |
RADEON: make tmds pll an output attribute
sometimes the bios tmds plls are busted for certain
monitors. sometimes the dirver tables are. Let the user
pick at run time.
Diffstat (limited to 'src')
-rw-r--r-- | src/radeon_bios.c | 17 | ||||
-rw-r--r-- | src/radeon_output.c | 70 | ||||
-rw-r--r-- | src/radeon_probe.h | 7 |
3 files changed, 72 insertions, 22 deletions
diff --git a/src/radeon_bios.c b/src/radeon_bios.c index 1ef0ff48..b24c4817 100644 --- a/src/radeon_bios.c +++ b/src/radeon_bios.c @@ -879,23 +879,6 @@ Bool RADEONGetTMDSInfoFromBIOS (xf86OutputPtr output) } return TRUE; } - - /* revision 4 has some problem as it appears in RV280, - comment it off for now, use default instead */ - /* - else if (RADEON_BIOS8(tmp) == 4) { - int stride = 0; - n = RADEON_BIOS8(tmp + 5) + 1; - if (n > 4) n = 4; - for (i=0; i<n; i++) { - radeon_output->tmds_pll[i].value = RADEON_BIOS32(tmp+stride+0x08); - radeon_output->tmds_pll[i].freq = RADEON_BIOS16(tmp+stride+0x10); - if (i == 0) stride += 10; - else stride += 6; - } - return TRUE; - } - */ } } return FALSE; diff --git a/src/radeon_output.c b/src/radeon_output.c index c2b749ae..35c6cbe4 100644 --- a/src/radeon_output.c +++ b/src/radeon_output.c @@ -152,6 +152,7 @@ static RADEONMonitorType radeon_detect_tv(ScrnInfoPtr pScrn); static RADEONMonitorType radeon_detect_primary_dac(ScrnInfoPtr pScrn, Bool color); static RADEONMonitorType radeon_detect_tv_dac(ScrnInfoPtr pScrn, Bool color); static RADEONMonitorType radeon_detect_ext_dac(ScrnInfoPtr pScrn); +static void RADEONGetTMDSInfoFromTable(xf86OutputPtr output); void RADEONPrintPortMap(ScrnInfoPtr pScrn) { @@ -1009,6 +1010,15 @@ radeon_mode_set(xf86OutputPtr output, DisplayModePtr mode, xf86CrtcPtr crtc = output->crtc; RADEONCrtcPrivatePtr radeon_crtc = crtc->driver_private; + if (radeon_output->type == OUTPUT_DVI && + radeon_output->TMDSType == TMDS_INT) { + if (radeon_output->tmds_pll_table == TMDS_PLL_BIOS) { + if (!RADEONGetTMDSInfoFromBIOS(output)) + RADEONGetTMDSInfoFromTable(output); + } else + RADEONGetTMDSInfoFromTable(output); + } + RADEONInitOutputRegisters(pScrn, &info->ModeReg, adjusted_mode, output, radeon_crtc->crtc_id); if (radeon_crtc->crtc_id == 0) @@ -1564,6 +1574,7 @@ radeon_set_backlight_level(xf86OutputPtr output, int level) } static Atom backlight_atom; +static Atom tmds_pll_atom; static Atom rmx_atom; static Atom monitor_type_atom; static Atom tv_hsize_atom; @@ -1606,6 +1617,32 @@ radeon_create_resources(xf86OutputPtr output) } } + if (radeon_output->type == OUTPUT_DVI && + radeon_output->TMDSType == TMDS_INT) { + tmds_pll_atom = MAKE_ATOM("tmds_pll"); + + err = RRConfigureOutputProperty(output->randr_output, tmds_pll_atom, + FALSE, FALSE, FALSE, 0, NULL); + if (err != 0) { + xf86DrvMsg(pScrn->scrnIndex, X_ERROR, + "RRConfigureOutputProperty error, %d\n", err); + } + /* Set the current value of the property */ +#if defined(__powerpc__) + s = "driver"; +#else + s = "bios"; +#endif + err = RRChangeOutputProperty(output->randr_output, tmds_pll_atom, + XA_STRING, 8, PropModeReplace, strlen(s), (pointer)s, + FALSE, FALSE); + if (err != 0) { + xf86DrvMsg(pScrn->scrnIndex, X_ERROR, + "RRChangeOutputProperty error, %d\n", err); + } + + } + /* RMX control - fullscreen, centered, keep ratio */ /* actually more of a crtc property as only crtc1 has rmx */ if (radeon_output->type == OUTPUT_LVDS || @@ -1785,6 +1822,19 @@ radeon_set_property(xf86OutputPtr output, Atom property, } else { return FALSE; } + } else if (property == tmds_pll_atom) { + const char *s; + if (value->type != XA_STRING || value->format != 8) + return FALSE; + s = (char*)value->data; + if (value->size == strlen("bios") && !strncmp("bios", s, strlen("bios"))) { + radeon_output->tmds_pll_table = TMDS_PLL_BIOS; + return TRUE; + } else if (value->size == strlen("driver") && !strncmp("driver", s, strlen("driver"))) { + radeon_output->tmds_pll_table = TMDS_PLL_DRIVER; + return TRUE; + } + return FALSE; } else if (property == monitor_type_atom) { const char *s; if (value->type != XA_STRING || value->format != 8) @@ -2256,7 +2306,7 @@ RADEONGetLVDSInfo (xf86OutputPtr output) } static void -RADEONGetTMDSInfo(xf86OutputPtr output) +RADEONGetTMDSInfoFromTable(xf86OutputPtr output) { ScrnInfoPtr pScrn = output->scrn; RADEONInfoPtr info = RADEONPTR(pScrn); @@ -2264,16 +2314,26 @@ RADEONGetTMDSInfo(xf86OutputPtr output) int i; for (i=0; i<4; i++) { + radeon_output->tmds_pll[i].value = default_tmds_pll[info->ChipFamily][i].value; + radeon_output->tmds_pll[i].freq = default_tmds_pll[info->ChipFamily][i].freq; + } +} + +static void +RADEONGetTMDSInfo(xf86OutputPtr output) +{ + RADEONOutputPrivatePtr radeon_output = output->driver_private; + int i; + + for (i=0; i<4; i++) { radeon_output->tmds_pll[i].value = 0; radeon_output->tmds_pll[i].freq = 0; } if (RADEONGetTMDSInfoFromBIOS(output)) return; - for (i=0; i<4; i++) { - radeon_output->tmds_pll[i].value = default_tmds_pll[info->ChipFamily][i].value; - radeon_output->tmds_pll[i].freq = default_tmds_pll[info->ChipFamily][i].freq; - } + RADEONGetTMDSInfoFromTable(output); + } static void diff --git a/src/radeon_probe.h b/src/radeon_probe.h index d79e7ad6..3bbda49e 100644 --- a/src/radeon_probe.h +++ b/src/radeon_probe.h @@ -122,6 +122,12 @@ typedef enum DVI_ANALOG } RADEONDviType; +typedef enum +{ + TMDS_PLL_BIOS, + TMDS_PLL_DRIVER +} RADEONTMDSPllType; + typedef struct { CARD32 freq; CARD32 value; @@ -196,6 +202,7 @@ typedef struct _RADEONOutputPrivateRec { int PanelPwrDly; int DotClock; RADEONTMDSPll tmds_pll[4]; + RADEONTMDSPllType tmds_pll_table; /* TV out */ TVStd default_tvStd; TVStd tvStd; |