diff options
author | Alex Deucher <alexdeucher@gmail.com> | 2009-04-23 14:06:06 -0400 |
---|---|---|
committer | Alex Deucher <alexdeucher@gmail.com> | 2009-04-23 14:06:06 -0400 |
commit | 7ed27b926f28a1f088eace5034a7d9985f13752d (patch) | |
tree | 442b87188f2ecec1ca7f7e695fc77e6009483f8e | |
parent | 0da80f34b5aa5999d2030ffbc5187328fa4e4ae5 (diff) |
r2xx/r3xx/r4xx: further i2c fixups
- hw i2c engine has pin selection on r2xx/r2xx/r3xx chips
- also switch hw i2c pin sel for external tmds
-rw-r--r-- | src/legacy_output.c | 11 | ||||
-rw-r--r-- | src/radeon.h | 2 | ||||
-rw-r--r-- | src/radeon_output.c | 31 | ||||
-rw-r--r-- | src/radeon_probe.h | 1 | ||||
-rw-r--r-- | src/radeon_reg.h | 32 |
5 files changed, 41 insertions, 36 deletions
diff --git a/src/legacy_output.c b/src/legacy_output.c index 423a3e2..7134ee1 100644 --- a/src/legacy_output.c +++ b/src/legacy_output.c @@ -150,7 +150,6 @@ void RADEONGetExtTMDSInfo(ScrnInfoPtr pScrn, radeon_dvo_ptr dvo) { RADEONInfoPtr info = RADEONPTR(pScrn); - I2CBusPtr pDVOBus; if (!info->IsAtomBios) { #if defined(__powerpc__) @@ -162,11 +161,11 @@ RADEONGetExtTMDSInfo(ScrnInfoPtr pScrn, radeon_dvo_ptr dvo) dvo->dvo_i2c_slave_addr = 0x70; } #endif - if (RADEONI2CInit(pScrn, &pDVOBus, "DVO", &dvo->dvo_i2c)) { + if (RADEONI2CInit(pScrn, &dvo->pI2CBus, "DVO", &dvo->dvo_i2c)) { dvo->DVOChip = - RADEONDVODeviceInit(pDVOBus, dvo->dvo_i2c_slave_addr); + RADEONDVODeviceInit(dvo->pI2CBus, dvo->dvo_i2c_slave_addr); if (!dvo->DVOChip) - xfree(pDVOBus); + xfree(dvo->pI2CBus); } } } @@ -481,7 +480,7 @@ RADEONRestoreDVOChip(ScrnInfoPtr pScrn, xf86OutputPtr output) if (!dvo->DVOChip) return; - RADEONI2CDoLock(output, TRUE); + RADEONI2CDoLock(output, dvo->pI2CBus, TRUE); if (!RADEONInitExtTMDSInfoFromBIOS(output)) { if (dvo->DVOChip) { switch(info->ext_tmds_chip) { @@ -511,7 +510,7 @@ RADEONRestoreDVOChip(ScrnInfoPtr pScrn, xf86OutputPtr output) } } } - RADEONI2CDoLock(output, FALSE); + RADEONI2CDoLock(output, dvo->pI2CBus, FALSE); } #if 0 diff --git a/src/radeon.h b/src/radeon.h index eaaff25..24a592c 100644 --- a/src/radeon.h +++ b/src/radeon.h @@ -1161,7 +1161,7 @@ extern void RADEONPrintPortMap(ScrnInfoPtr pScrn); extern void RADEONSetOutputType(ScrnInfoPtr pScrn, RADEONOutputPrivatePtr radeon_output); extern Bool RADEONSetupConnectors(ScrnInfoPtr pScrn); -extern Bool RADEONI2CDoLock(xf86OutputPtr output, Bool lock_state); +extern Bool RADEONI2CDoLock(xf86OutputPtr output, I2CBusPtr b, Bool lock_state); /* radeon_tv.c */ diff --git a/src/radeon_output.c b/src/radeon_output.c index e545c79..67d94fe 100644 --- a/src/radeon_output.c +++ b/src/radeon_output.c @@ -217,24 +217,14 @@ radeon_ddc_connected(xf86OutputPtr output) RADEONMonitorType MonType = MT_NONE; xf86MonPtr MonInfo = NULL; RADEONOutputPrivatePtr radeon_output = output->driver_private; - unsigned char *RADEONMMIO = info->MMIO; if (radeon_output->pI2CBus) { - /* RV410 appears to have a bug where the hw i2c in reset - * holds the i2c port in a bad state - switch hw i2c away before - * doing DDC - do this for all r300s for safety sakes */ - if (IS_R300_VARIANT) { - if (radeon_output->ddc_i2c.mask_clk_reg == RADEON_GPIO_VGA_DDC) - OUTREG(RADEON_DVI_I2C_CNTL_0, 0x30); - else - OUTREG(RADEON_DVI_I2C_CNTL_0, 0x20); - } if (info->get_hardcoded_edid_from_bios) MonInfo = RADEONGetHardCodedEDIDFromBIOS(output); if (MonInfo == NULL) { - RADEONI2CDoLock(output, TRUE); + RADEONI2CDoLock(output, radeon_output->pI2CBus, TRUE); MonInfo = xf86OutputGetEDID(output, radeon_output->pI2CBus); - RADEONI2CDoLock(output, FALSE); + RADEONI2CDoLock(output, radeon_output->pI2CBus, FALSE); } } if (MonInfo) { @@ -1653,16 +1643,27 @@ static const xf86OutputFuncsRec radeon_output_funcs = { }; Bool -RADEONI2CDoLock(xf86OutputPtr output, int lock_state) +RADEONI2CDoLock(xf86OutputPtr output, I2CBusPtr b, int lock_state) { ScrnInfoPtr pScrn = output->scrn; RADEONInfoPtr info = RADEONPTR(pScrn); - RADEONOutputPrivatePtr radeon_output = output->driver_private; - RADEONI2CBusPtr pRADEONI2CBus = radeon_output->pI2CBus->DriverPrivate.ptr; + RADEONI2CBusPtr pRADEONI2CBus = b->DriverPrivate.ptr; unsigned char *RADEONMMIO = info->MMIO; uint32_t temp; if (lock_state) { + /* RV410 appears to have a bug where the hw i2c in reset + * holds the i2c port in a bad state - switch hw i2c away before + * doing DDC - do this for all r200s/r300s for safety sakes */ + if ((info->ChipFamily >= CHIP_FAMILY_R200) && (!IS_AVIVO_VARIANT)) { + if (pRADEONI2CBus->mask_clk_reg == RADEON_GPIO_CRT2_DDC) + OUTREG(RADEON_DVI_I2C_CNTL_0, (RADEON_I2C_SOFT_RST | + R200_DVI_I2C_PIN_SEL(R200_SEL_DVI_DDC))); + else + OUTREG(RADEON_DVI_I2C_CNTL_0, (RADEON_I2C_SOFT_RST | + R200_DVI_I2C_PIN_SEL(R200_SEL_CRT2_DDC))); + } + temp = INREG(pRADEONI2CBus->a_clk_reg); temp &= ~(pRADEONI2CBus->a_clk_mask); OUTREG(pRADEONI2CBus->a_clk_reg, temp); diff --git a/src/radeon_probe.h b/src/radeon_probe.h index 6479972..3e4f47c 100644 --- a/src/radeon_probe.h +++ b/src/radeon_probe.h @@ -216,6 +216,7 @@ typedef struct _radeon_lvds { typedef struct _radeon_dvo { /* dvo */ + I2CBusPtr pI2CBus; I2CDevPtr DVOChip; RADEONI2CBusRec dvo_i2c; int dvo_i2c_slave_addr; diff --git a/src/radeon_reg.h b/src/radeon_reg.h index 1cc7640..85923d1 100644 --- a/src/radeon_reg.h +++ b/src/radeon_reg.h @@ -1009,24 +1009,28 @@ /* Multimedia I2C bus */ #define RADEON_I2C_CNTL_0 0x0090 -#define RADEON_I2C_DONE (1<<0) -#define RADEON_I2C_NACK (1<<1) -#define RADEON_I2C_HALT (1<<2) -#define RADEON_I2C_SOFT_RST (1<<5) -#define RADEON_I2C_DRIVE_EN (1<<6) -#define RADEON_I2C_DRIVE_SEL (1<<7) -#define RADEON_I2C_START (1<<8) -#define RADEON_I2C_STOP (1<<9) -#define RADEON_I2C_RECEIVE (1<<10) -#define RADEON_I2C_ABORT (1<<11) -#define RADEON_I2C_GO (1<<12) +#define RADEON_I2C_DONE (1 << 0) +#define RADEON_I2C_NACK (1 << 1) +#define RADEON_I2C_HALT (1 << 2) +#define RADEON_I2C_SOFT_RST (1 << 5) +#define RADEON_I2C_DRIVE_EN (1 << 6) +#define RADEON_I2C_DRIVE_SEL (1 << 7) +#define RADEON_I2C_START (1 << 8) +#define RADEON_I2C_STOP (1 << 9) +#define RADEON_I2C_RECEIVE (1 << 10) +#define RADEON_I2C_ABORT (1 << 11) +#define RADEON_I2C_GO (1 << 12) #define RADEON_I2C_CNTL_1 0x0094 -#define RADEON_I2C_SEL (1<<16) -#define RADEON_I2C_EN (1<<17) +#define RADEON_I2C_SEL (1 << 16) +#define RADEON_I2C_EN (1 << 17) #define RADEON_I2C_DATA 0x0098 #define RADEON_DVI_I2C_CNTL_0 0x02e0 -#define RADEON_DVI_I2C_CNTL_1 0x02e4 /* ? */ +# define R200_DVI_I2C_PIN_SEL(x) ((x) << 3) +# define R200_SEL_DVI_DDC 0 +# define R200_SEL_VGA_DDC 1 +# define R200_SEL_CRT2_DDC 2 +#define RADEON_DVI_I2C_CNTL_1 0x02e4 #define RADEON_DVI_I2C_DATA 0x02e8 #define RADEON_INTERRUPT_LINE 0x0f3c /* PCI */ |