On Sat, Dec 20, 2008 at 1:48 PM, Bernhard R. Link <brl...@debian.org> wrote: > Looking at the radeon_drv sources, it looks like those are only > accessing 8 bit at RADEON_CLOCK_CNTL_INDEX and not the whole int that > radeontool is writing, changing that in the driver via > > --- xserver-xorg-video-ati-6.9.0/src/radeon_driver.c 2008-12-20 > 19:06:32.000000000 +0100 > +++ xserver-xorg-video-ati-6.9.0/src/radeon_driver.c 2008-12-20 > 18:29:24.000000000 +0100 > @@ -544,7 +544,7 @@ > unsigned char *RADEONMMIO = info->MMIO; > uint32_t data; > > - OUTREG8(RADEON_CLOCK_CNTL_INDEX, addr & 0x3f); > + OUTREG(RADEON_CLOCK_CNTL_INDEX, addr & 0x3f); > RADEONPllErrataAfterIndex(info); > data = INREG(RADEON_CLOCK_CNTL_DATA); > RADEONPllErrataAfterData(info); > @@ -558,7 +558,7 @@ > RADEONInfoPtr info = RADEONPTR(pScrn); > unsigned char *RADEONMMIO = info->MMIO; > > - OUTREG8(RADEON_CLOCK_CNTL_INDEX, (((addr) & 0x3f) | > + OUTREG(RADEON_CLOCK_CNTL_INDEX, (((addr) & 0x3f) | > RADEON_PLL_WR_EN)); > RADEONPllErrataAfterIndex(info); > OUTREG(RADEON_CLOCK_CNTL_DATA, data); > > fixes my problem (i.e. I get a working display, and it still works after > switching to virtual console and back and changing resolutions and all those > things). > > I fear that might be the case because it is overwriting some other data > in there that causes this, but I guess to know this someone with > knowledge about this registers is needed...
We only use the lower 8 bits because bits 9:8 select the pll dividers to use; changing it breaks some chips. Some rv410 chips have a similar issue. Does this patch fix it for you? Alex
diff --git a/src/legacy_output.c b/src/legacy_output.c index f9b0dff..e7d6e32 100644 --- a/src/legacy_output.c +++ b/src/legacy_output.c @@ -153,6 +153,15 @@ RADEONRestoreRMXRegisters(ScrnInfoPtr pScrn, RADEONSavePtr restore) } +static void +RADEONSelDiv0(ScrnInfoPtr pScrn) +{ + RADEONInfoPtr info = RADEONPTR(pScrn); + unsigned char *RADEONMMIO = info->MMIO; + + OUTREG(RADEON_CLOCK_CNTL_INDEX, 0); +} + /* Write LVDS registers */ void RADEONRestoreLVDSRegisters(ScrnInfoPtr pScrn, RADEONSavePtr restore) @@ -163,12 +172,7 @@ RADEONRestoreLVDSRegisters(ScrnInfoPtr pScrn, RADEONSavePtr restore) if (info->IsMobility) { OUTREG(RADEON_LVDS_GEN_CNTL, restore->lvds_gen_cntl); /*OUTREG(RADEON_LVDS_PLL_CNTL, restore->lvds_pll_cntl);*/ - - if (info->ChipFamily == CHIP_FAMILY_RV410) { - OUTREG(RADEON_CLOCK_CNTL_INDEX, 0); - } } - } void @@ -1419,6 +1423,8 @@ legacy_output_mode_set(xf86OutputPtr output, DisplayModePtr mode, case MT_LCD: ErrorF("restore LVDS\n"); RADEONRestoreLVDSRegisters(pScrn, info->ModeReg); + if ((radeon_crtc->crtc_id == 0) && (info->ChipFamily == CHIP_FAMILY_RV410)) + RADEONSelDiv0(pScrn); break; case MT_DFP: if (radeon_output->TMDSType == TMDS_INT) { @@ -1447,6 +1453,8 @@ legacy_output_mode_set(xf86OutputPtr output, DisplayModePtr mode, } else { RADEONRestoreFP2Registers(pScrn, info->ModeReg); RADEONRestoreDVOChip(pScrn, output); + if ((radeon_crtc->crtc_id == 0) && info->IsIGP) + RADEONSelDiv0(pScrn); } } break;