diff options
author | Eric Anholt <eric@anholt.net> | 2006-08-08 15:51:58 -0700 |
---|---|---|
committer | Eric Anholt <anholt@FreeBSD.org> | 2006-08-08 15:59:17 -0700 |
commit | d150b53d102c511f3c9245ef1f6fd36c12b01ca3 (patch) | |
tree | 3d314bdcae0fc404680406eb0f265c36d5ddb208 /src/i830_driver.c | |
parent | bb65a4dc55b416437d61ccbee8b6056fe8e08357 (diff) | |
parent | bc5f56568021d8c63313e2b6bf30710e7516c04a (diff) |
Merge branch 'i965', adding i965G support.
Conflicts:
src/i830_cursor.c
src/i830_driver.c
Diffstat (limited to 'src/i830_driver.c')
-rw-r--r-- | src/i830_driver.c | 377 |
1 files changed, 335 insertions, 42 deletions
diff --git a/src/i830_driver.c b/src/i830_driver.c index 5cbb280e..62a62abb 100644 --- a/src/i830_driver.c +++ b/src/i830_driver.c @@ -150,6 +150,11 @@ USE OR OTHER DEALINGS IN THE SOFTWARE. * 09/2005 Alan Hourihane * - Add Intel(R) 945GM support. * + * 10/2005 Alan Hourihane, Keith Whitwell, Brian Paul + * - Added Rotation support + * + * 12/2005 Alan Hourihane, Keith Whitwell + * - Add Intel(R) 965G support. */ #ifdef HAVE_CONFIG_H @@ -186,6 +191,10 @@ USE OR OTHER DEALINGS IN THE SOFTWARE. #include "shadow.h" #include "i830.h" +#ifdef HAS_MTRR_SUPPORT +#include <asm/mtrr.h> +#endif + #ifdef XF86DRI #include "dri.h" #endif @@ -205,6 +214,10 @@ static SymTabRec I830BIOSChipsets[] = { {PCI_CHIP_I915_GM, "915GM"}, {PCI_CHIP_I945_G, "945G"}, {PCI_CHIP_I945_GM, "945GM"}, + {PCI_CHIP_I965_G, "965G"}, + {PCI_CHIP_I965_G_1, "965G"}, + {PCI_CHIP_I965_Q, "965Q"}, + {PCI_CHIP_I946_GZ, "946GZ"}, {-1, NULL} }; @@ -218,6 +231,10 @@ static PciChipsets I830BIOSPciChipsets[] = { {PCI_CHIP_I915_GM, PCI_CHIP_I915_GM, RES_SHARED_VGA}, {PCI_CHIP_I945_G, PCI_CHIP_I945_G, RES_SHARED_VGA}, {PCI_CHIP_I945_GM, PCI_CHIP_I945_GM, RES_SHARED_VGA}, + {PCI_CHIP_I965_G, PCI_CHIP_I965_G, RES_SHARED_VGA}, + {PCI_CHIP_I965_G_1, PCI_CHIP_I965_G_1, RES_SHARED_VGA}, + {PCI_CHIP_I965_Q, PCI_CHIP_I965_Q, RES_SHARED_VGA}, + {PCI_CHIP_I946_GZ, PCI_CHIP_I946_GZ, RES_SHARED_VGA}, {-1, -1, RES_UNDEFINED} }; @@ -2090,7 +2107,7 @@ GetNextDisplayDeviceList(ScrnInfoPtr pScrn, int toggle) CARD32 VODA = (CARD32)((CARD32*)pVbe->memory)[i]; xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Next ACPI _DGS [%d] 0x%lx\n", - i, (unsigned long) VODA); + i, VODA); /* Check if it's a custom Video Output Device Attribute */ if (!(VODA & 0x80000000)) @@ -2147,8 +2164,7 @@ GetAttachableDisplayDeviceList(ScrnInfoPtr pScrn) for (i=0; i<(pVbe->pInt10->cx & 0xff); i++) xf86DrvMsg(pScrn->scrnIndex, X_INFO, - "Attachable device 0x%lx.\n", - (unsigned long) ((CARD32*)pVbe->memory)[i]); + "Attachable device 0x%lx.\n", ((CARD32*)pVbe->memory)[i]); return pVbe->pInt10->cx & 0xffff; } @@ -3063,8 +3079,11 @@ I830DetectMemory(ScrnInfoPtr pScrn) gmch_ctrl = pciReadWord(bridge, I830_GMCH_CTRL); /* We need to reduce the stolen size, by the GTT and the popup. - * The GTT varying according the the FbMapSize and the popup is 4KB */ - range = (pI830->FbMapSize / (1024*1024)) + 4; + * The GTT varying according the the FbMapSize and the popup is 4KB. */ + if (IS_I965G(pI830)) + range = 512 + 4; /* Fixed 512KB size for i965 */ + else + range = (pI830->FbMapSize / MB(1)) + 4; if (IS_I85X(pI830) || IS_I865G(pI830) || IS_I9XX(pI830)) { switch (gmch_ctrl & I830_GMCH_GMS_MASK) { @@ -3110,6 +3129,12 @@ I830DetectMemory(ScrnInfoPtr pScrn) break; } } + +#if 0 + /* And 64KB page aligned */ + memsize &= ~0xFFFF; +#endif + if (memsize > 0) { xf86DrvMsg(pScrn->scrnIndex, X_INFO, "detected %d kB stolen memory.\n", memsize / 1024); @@ -3481,7 +3506,7 @@ I830LoadPalette(ScrnInfoPtr pScrn, int numColors, int *indices, unsigned char r, g, b; CARD32 val, temp; int palreg; - int dspreg, dspbase; + int dspreg, dspbase, dspsurf; DPRINTF(PFX, "I830LoadPalette: numColors: %d\n", numColors); pI830 = I830PTR(pScrn); @@ -3563,10 +3588,12 @@ I830LoadPalette(ScrnInfoPtr pScrn, int numColors, int *indices, palreg = PALETTE_A; dspreg = DSPACNTR; dspbase = DSPABASE; + dspsurf = DSPASURF; } else { palreg = PALETTE_B; dspreg = DSPBCNTR; dspbase = DSPBBASE; + dspsurf = DSPBSURF; } /* To ensure gamma is enabled we need to turn off and on the plane */ @@ -3575,6 +3602,8 @@ I830LoadPalette(ScrnInfoPtr pScrn, int numColors, int *indices, OUTREG(dspbase, INREG(dspbase)); OUTREG(dspreg, temp | DISPPLANE_GAMMA_ENABLE); OUTREG(dspbase, INREG(dspbase)); + if (IS_I965G(pI830)) + OUTREG(dspsurf, INREG(dspsurf)); /* It seems that an initial read is needed. */ temp = INREG(palreg); @@ -3983,6 +4012,16 @@ I830BIOSPreInit(ScrnInfoPtr pScrn, int flags) case PCI_CHIP_I945_GM: chipname = "945GM"; break; + case PCI_CHIP_I965_G: + case PCI_CHIP_I965_G_1: + chipname = "965G"; + break; + case PCI_CHIP_I965_Q: + chipname = "965Q"; + break; + case PCI_CHIP_I946_GZ: + chipname = "946GZ"; + break; default: chipname = "unknown chipset"; break; @@ -4689,7 +4728,7 @@ I830BIOSPreInit(ScrnInfoPtr pScrn, int flags) * or, at least it's meant to..... alas it doesn't seem to always work. */ if (pI830->devicePresence) { - int req=0, att=0, enc=0; + int req, att, enc; GetDevicePresence(pScrn, &req, &att, &enc); for (i = 0; i < NumDisplayTypes; i++) { xf86DrvMsg(pScrn->scrnIndex, X_INFO, @@ -4838,6 +4877,9 @@ I830BIOSPreInit(ScrnInfoPtr pScrn, int flags) else pI830->CursorNeedsPhysical = FALSE; + if (IS_I965G(pI830)) + pI830->CursorNeedsPhysical = FALSE; + /* Force ring buffer to be in low memory for all chipsets */ pI830->NeedRingBufferLow = TRUE; @@ -5561,8 +5603,12 @@ CheckInheritedState(ScrnInfoPtr pScrn) } #if 0 - if (errors) - I830PrintErrorState(pScrn); + if (errors) { + if (IS_I965G(pI830)) + I965PrintErrorState(pScrn); + else + I830PrintErrorState(pScrn); + } #endif if (fatal) @@ -5592,8 +5638,15 @@ ResetState(ScrnInfoPtr pScrn, Bool flush) pI830->entityPrivate->RingRunning = 0; /* Reset the fence registers to 0 */ - for (i = 0; i < 8; i++) - OUTREG(FENCE + i * 4, 0); + if (IS_I965G(pI830)) { + for (i = 0; i < FENCE_NEW_NR; i++) { + OUTREG(FENCE_NEW + i * 8, 0); + OUTREG(FENCE_NEW + 4 + i * 8, 0); + } + } else { + for (i = 0; i < FENCE_NR; i++) + OUTREG(FENCE + i * 4, 0); + } /* Flush the ring buffer (if enabled), then disable it. */ if (pI830->AccelInfoRec != NULL && flush) { @@ -5623,10 +5676,21 @@ SetFenceRegs(ScrnInfoPtr pScrn) if (!I830IsPrimary(pScrn)) return; - for (i = 0; i < 8; i++) { - OUTREG(FENCE + i * 4, pI830->ModeReg.Fence[i]); - if (I810_DEBUG & DEBUG_VERBOSE_VGA) - ErrorF("Fence Register : %x\n", pI830->ModeReg.Fence[i]); + if (IS_I965G(pI830)) { + for (i = 0; i < FENCE_NEW_NR; i++) { + OUTREG(FENCE_NEW + i * 8, pI830->ModeReg.Fence[i]); + OUTREG(FENCE_NEW + 4 + i * 8, pI830->ModeReg.Fence[i+FENCE_NEW_NR]); + if (I810_DEBUG & DEBUG_VERBOSE_VGA) { + ErrorF("Fence Start Register : %x\n", pI830->ModeReg.Fence[i]); + ErrorF("Fence End Register : %x\n", pI830->ModeReg.Fence[i+FENCE_NEW_NR]); + } + } + } else { + for (i = 0; i < FENCE_NR; i++) { + OUTREG(FENCE + i * 4, pI830->ModeReg.Fence[i]); + if (I810_DEBUG & DEBUG_VERBOSE_VGA) + ErrorF("Fence Register : %x\n", pI830->ModeReg.Fence[i]); + } } } @@ -5727,6 +5791,12 @@ SaveHWState(ScrnInfoPtr pScrn) vgaHWSave(pScrn, vgaReg, VGA_SR_FONTS); pVesa = pI830->vesa; + + if (IS_I965G(pI830)) { + pI830->savedAsurf = INREG(DSPASURF); + pI830->savedBsurf = INREG(DSPBSURF); + } + /* * This save/restore method doesn't work for 845G BIOS, or for some * other platforms. Enable it in all cases. @@ -5779,9 +5849,6 @@ RestoreHWState(ScrnInfoPtr pScrn) DPRINTF(PFX, "RestoreHWState\n"); -#ifdef XF86DRI - I830DRISetVBlankInterrupt (pScrn, FALSE); -#endif if (I830IsPrimary(pScrn) && pI830->pipe != pI830->origPipe) SetBIOSPipe(pScrn, pI830->origPipe); else @@ -5840,6 +5907,11 @@ RestoreHWState(ScrnInfoPtr pScrn) VBESetDisplayStart(pVbe, pVesa->x, pVesa->y, TRUE); + if (IS_I965G(pI830)) { + OUTREG(DSPASURF, pI830->savedAsurf); + OUTREG(DSPBSURF, pI830->savedBsurf); + } + vgaHWRestore(pScrn, vgaReg, VGA_SR_FONTS); vgaHWLock(hwp); @@ -6109,6 +6181,25 @@ I830VESASetMode(ScrnInfoPtr pScrn, DisplayModePtr pMode) } } +#if 0 + { /* I965G ENABLE TILING */ + planeA = INREG(DSPACNTR) | 1<<10; + OUTREG(DSPACNTR, planeA); + /* flush the change. */ + temp = INREG(DSPABASE); + OUTREG(DSPABASE, temp); + } +#else + { /* I965G DISABLE TILING */ + planeA = INREG(DSPACNTR) & ~1<<10; + OUTREG(DSPACNTR, planeA); + /* flush the change. */ + temp = INREG(DSPABASE); + OUTREG(DSPABASE, temp); + OUTREG(DSPASURF, INREG(DSPASURF)); + } +#endif + /* * The BIOS may not set a scanline pitch that would require more video * memory than it's aware of. We check for this later, and set it @@ -6168,6 +6259,10 @@ I830VESASetMode(ScrnInfoPtr pScrn, DisplayModePtr pMode) /* flush the change. */ temp = INREG(DSPABASE); OUTREG(DSPABASE, temp); + if (IS_I965G(pI830)) { + temp = INREG(DSPASURF); + OUTREG(DSPASURF, temp); + } } if (pI830->planeEnabled[1]) { xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Enabling plane B.\n"); @@ -6178,6 +6273,10 @@ I830VESASetMode(ScrnInfoPtr pScrn, DisplayModePtr pMode) /* flush the change. */ temp = INREG(DSPBADDR); OUTREG(DSPBADDR, temp); + if (IS_I965G(pI830)) { + temp = INREG(DSPBSURF); + OUTREG(DSPBSURF, temp); + } } planeA = INREG(DSPACNTR); @@ -6210,6 +6309,7 @@ I830VESASetMode(ScrnInfoPtr pScrn, DisplayModePtr pMode) CARD32 stridereg = !pI830->pipe ? DSPASTRIDE : DSPBSTRIDE; CARD32 basereg = !pI830->pipe ? DSPABASE : DSPBBASE; CARD32 sizereg = !pI830->pipe ? DSPASIZE : DSPBSIZE; + CARD32 surfreg = !pI830->pipe ? DSPASURF : DSPBSURF; I830Ptr pI8301 = I830PTR(pI830->entityPrivate->pScrn_1); temp = INREG(stridereg); @@ -6223,12 +6323,17 @@ I830VESASetMode(ScrnInfoPtr pScrn, DisplayModePtr pMode) /* Trigger update */ temp = INREG(basereg); OUTREG(basereg, temp); + if (IS_I965G(pI830)) { + temp = INREG(surfreg); + OUTREG(surfreg, temp); + } if (pI830->entityPrivate && pI830->entityPrivate->pScrn_2) { I830Ptr pI8302 = I830PTR(pI830->entityPrivate->pScrn_2); stridereg = pI830->pipe ? DSPASTRIDE : DSPBSTRIDE; basereg = pI830->pipe ? DSPABASE : DSPBBASE; sizereg = pI830->pipe ? DSPASIZE : DSPBSIZE; + surfreg = pI830->pipe ? DSPASURF : DSPBSURF; temp = INREG(stridereg); if (temp / pI8302->cpp != (CARD32)(pI8302->displayWidth)) { @@ -6241,11 +6346,16 @@ I830VESASetMode(ScrnInfoPtr pScrn, DisplayModePtr pMode) /* Trigger update */ temp = INREG(basereg); OUTREG(basereg, temp); + if (IS_I965G(pI830)) { + temp = INREG(surfreg); + OUTREG(surfreg, temp); + } } } else { CARD32 stridereg = pI830->pipe ? DSPASTRIDE : DSPBSTRIDE; CARD32 basereg = pI830->pipe ? DSPABASE : DSPBBASE; CARD32 sizereg = pI830->pipe ? DSPASIZE : DSPBSIZE; + CARD32 surfreg = pI830->pipe ? DSPASURF : DSPBSURF; I830Ptr pI8301 = I830PTR(pI830->entityPrivate->pScrn_1); I830Ptr pI8302 = I830PTR(pI830->entityPrivate->pScrn_2); @@ -6260,10 +6370,15 @@ I830VESASetMode(ScrnInfoPtr pScrn, DisplayModePtr pMode) /* Trigger update */ temp = INREG(basereg); OUTREG(basereg, temp); + if (IS_I965G(pI830)) { + temp = INREG(surfreg); + OUTREG(surfreg, temp); + } stridereg = !pI830->pipe ? DSPASTRIDE : DSPBSTRIDE; basereg = !pI830->pipe ? DSPABASE : DSPBBASE; sizereg = !pI830->pipe ? DSPASIZE : DSPBSIZE; + surfreg = !pI830->pipe ? DSPASURF : DSPBSURF; temp = INREG(stridereg); if (temp / pI8302->cpp != ((CARD32)pI8302->displayWidth)) { @@ -6276,12 +6391,17 @@ I830VESASetMode(ScrnInfoPtr pScrn, DisplayModePtr pMode) /* Trigger update */ temp = INREG(basereg); OUTREG(basereg, temp); + if (IS_I965G(pI830)) { + temp = INREG(surfreg); + OUTREG(surfreg, temp); + } } } else { for (i = 0; i < pI830->availablePipes; i++) { CARD32 stridereg = i ? DSPBSTRIDE : DSPASTRIDE; CARD32 basereg = i ? DSPBBASE : DSPABASE; CARD32 sizereg = i ? DSPBSIZE : DSPASIZE; + CARD32 surfreg = i ? DSPBSURF : DSPASURF; if (!pI830->planeEnabled[i]) continue; @@ -6312,6 +6432,10 @@ I830VESASetMode(ScrnInfoPtr pScrn, DisplayModePtr pMode) /* Trigger update */ temp = INREG(basereg); OUTREG(basereg, temp); + if (IS_I965G(pI830)) { + temp = INREG(surfreg); + OUTREG(surfreg, temp); + } } } @@ -6414,9 +6538,13 @@ I830VESASetMode(ScrnInfoPtr pScrn, DisplayModePtr pMode) SetHWOperatingState(pScrn); #endif -#ifdef XF86DRI - I830DRISetVBlankInterrupt (pScrn, TRUE); +#if 0 + if (IS_I965G(pI830)) + I965PrintErrorState(pScrn); + else + I830PrintErrorState(pScrn); #endif + #ifdef XF86DRI if (didLock) I830DRIUnlock(pScrn); @@ -6470,6 +6598,59 @@ I830PrintErrorState(ScrnInfoPtr pScrn) INREG16(HWSTAM), INREG16(IER), INREG16(IMR), INREG16(IIR)); } +void +I965PrintErrorState(ScrnInfoPtr pScrn) +{ + I830Ptr pI830 = I830PTR(pScrn); + + ErrorF("pgetbl_ctl: 0x%lx pgetbl_err: 0x%lx\n", + INREG(PGETBL_CTL), INREG(PGE_ERR)); + + ErrorF("ipeir: %lx iphdr: %lx\n", INREG(IPEIR_I965), INREG(IPEHR_I965)); + + ErrorF("LP ring tail: %lx head: %lx len: %lx start %lx\n", + INREG(LP_RING + RING_TAIL), + INREG(LP_RING + RING_HEAD) & HEAD_ADDR, + INREG(LP_RING + RING_LEN), INREG(LP_RING + RING_START)); + + ErrorF("Err ID (eir): %x Err Status (esr): %x Err Mask (emr): %x\n", + INREG(EIR), INREG(ESR), INREG(EMR)); + + ErrorF("instdone: %x instdone_1: %x\n", INREG(INST_DONE_I965), INREG(INST_DONE_1)); + ErrorF("instpm: %x\n", INREG(INST_PM)); + + ErrorF("memmode: %lx instps: %lx\n", INREG(MEMMODE), INREG(INST_PS_I965)); + + ErrorF("HW Status mask (hwstam): %x\nIRQ enable (ier): %x imr: %x iir: %x\n", + INREG(HWSTAM), INREG(IER), INREG(IMR), INREG(IIR)); + + ErrorF("acthd: %lx dma_fadd_p: %lx\n", INREG(ACTHD), INREG(DMA_FADD_P)); + ErrorF("ecoskpd: %lx excc: %lx\n", INREG(ECOSKPD), INREG(EXCC)); + + ErrorF("cache_mode: %x/%x\n", INREG(CACHE_MODE_0), INREG(CACHE_MODE_1)); + ErrorF("mi_arb_state: %x\n", INREG(MI_ARB_STATE)); + + ErrorF("IA_VERTICES_COUNT_QW %x/%x\n", INREG(IA_VERTICES_COUNT_QW), INREG(IA_VERTICES_COUNT_QW+4)); + ErrorF("IA_PRIMITIVES_COUNT_QW %x/%x\n", INREG(IA_PRIMITIVES_COUNT_QW), INREG(IA_PRIMITIVES_COUNT_QW+4)); + + ErrorF("VS_INVOCATION_COUNT_QW %x/%x\n", INREG(VS_INVOCATION_COUNT_QW), INREG(VS_INVOCATION_COUNT_QW+4)); + + ErrorF("GS_INVOCATION_COUNT_QW %x/%x\n", INREG(GS_INVOCATION_COUNT_QW), INREG(GS_INVOCATION_COUNT_QW+4)); + ErrorF("GS_PRIMITIVES_COUNT_QW %x/%x\n", INREG(GS_PRIMITIVES_COUNT_QW), INREG(GS_PRIMITIVES_COUNT_QW+4)); + + ErrorF("CL_INVOCATION_COUNT_QW %x/%x\n", INREG(CL_INVOCATION_COUNT_QW), INREG(CL_INVOCATION_COUNT_QW+4)); + ErrorF("CL_PRIMITIVES_COUNT_QW %x/%x\n", INREG(CL_PRIMITIVES_COUNT_QW), INREG(CL_PRIMITIVES_COUNT_QW+4)); + + ErrorF("PS_INVOCATION_COUNT_QW %x/%x\n", INREG(PS_INVOCATION_COUNT_QW), INREG(PS_INVOCATION_COUNT_QW+4)); + ErrorF("PS_DEPTH_COUNT_QW %x/%x\n", INREG(PS_DEPTH_COUNT_QW), INREG(PS_DEPTH_COUNT_QW+4)); + + ErrorF("WIZ_CTL %x\n", INREG(WIZ_CTL)); + ErrorF("TS_CTL %x TS_DEBUG_DATA %x\n", INREG(TS_CTL), INREG(TS_DEBUG_DATA)); + ErrorF("TD_CTL %x / %x\n", INREG(TD_CTL), INREG(TD_CTL2)); + + +} + #ifdef I830DEBUG static void dump_DSPACNTR(ScrnInfoPtr pScrn) @@ -6696,7 +6877,8 @@ I830CreateScreenResources (ScreenPtr pScreen) if (!(*pScreen->CreateScreenResources)(pScreen)) return FALSE; - if (pI830->rotation != RR_Rotate_0) { + if (xf86LoaderCheckSymbol("I830RandRSetConfig") && pI830->rotation != RR_Rotate_0) { + Rotation (*I830RandRSetConfig)(ScreenPtr pScreen, Rotation rr, int rate, RRScreenSizePtr pSize) = NULL; RRScreenSize p; Rotation requestedRotation = pI830->rotation; @@ -6708,9 +6890,12 @@ I830CreateScreenResources (ScreenPtr pScreen) p.mmWidth = pScreen->mmWidth; p.mmHeight = pScreen->mmHeight; - pI830->starting = TRUE; /* abuse this for dual head & rotation */ - I830RandRSetConfig (pScreen, requestedRotation, 0, &p); - pI830->starting = FALSE; + I830RandRSetConfig = LoaderSymbol("I830RandRSetConfig"); + if (I830RandRSetConfig) { + pI830->starting = TRUE; /* abuse this for dual head & rotation */ + (*I830RandRSetConfig) (pScreen, requestedRotation, 0, &p); + pI830->starting = FALSE; + } } return TRUE; @@ -6763,6 +6948,9 @@ IntelEmitInvarientState(ScrnInfoPtr pScrn) I830Ptr pI830 = I830PTR(pScrn); CARD32 ctx_addr; + if (pI830->noAccel) + return; + ctx_addr = pI830->ContextMem.Start; /* Align to a 2k boundry */ ctx_addr = ((ctx_addr + 2048 - 1) / 2048) * 2048; @@ -6776,10 +6964,13 @@ IntelEmitInvarientState(ScrnInfoPtr pScrn) ADVANCE_LP_RING(); } - if (IS_I9XX(pI830)) - I915EmitInvarientState(pScrn); - else - I830EmitInvarientState(pScrn); + if (!IS_I965G(pI830)) + { + if (IS_I9XX(pI830)) + I915EmitInvarientState(pScrn); + else + I830EmitInvarientState(pScrn); + } } static Bool @@ -6809,6 +7000,47 @@ I830BIOSScreenInit(int scrnIndex, ScreenPtr pScreen, int argc, char **argv) pI830->RotatedMem2.Key = -1; } +#ifdef HAS_MTRR_SUPPORT + { + int fd; + struct mtrr_gentry gentry; + struct mtrr_sentry sentry; + + if ( ( fd = open ("/proc/mtrr", O_RDONLY, 0) ) != -1 ) { + for (gentry.regnum = 0; ioctl (fd, MTRRIOC_GET_ENTRY, &gentry) == 0; + ++gentry.regnum) { + + if (gentry.size < 1) { + /* DISABLED */ + continue; + } + + /* Check the MTRR range is one we like and if not - remove it. + * The Xserver common layer will then setup the right range + * for us. + */ + if (gentry.base == pI830->LinearAddr && + gentry.size < pI830->FbMapSize) { + + xf86DrvMsg(pScrn->scrnIndex, X_INFO, + "Removing bad MTRR range (base 0x%lx, size 0x%x)\n", + gentry.base, gentry.size); + + sentry.base = gentry.base; + sentry.size = gentry.size; + sentry.type = gentry.type; + + if (ioctl (fd, MTRRIOC_DEL_ENTRY, &sentry) == -1) { + xf86DrvMsg(pScrn->scrnIndex, X_ERROR, + "Failed to remove bad MTRR range\n"); + } + } + } + close(fd); + } + } +#endif + if (xf86IsEntityShared(pScrn->entityList[0])) { /* PreInit failed on the second head, so make sure we turn it off */ if (I830IsPrimary(pScrn) && !pI830->entityPrivate->pScrn_2) { @@ -7183,7 +7415,11 @@ I830BIOSScreenInit(int scrnIndex, ScreenPtr pScreen, int argc, char **argv) xf86DisableRandR(); /* Disable built-in RandR extension */ shadowSetup(pScreen); /* support all rotations */ - I830RandRInit(pScreen, RR_Rotate_0 | RR_Rotate_90 | RR_Rotate_180 | RR_Rotate_270); + if (IS_I965G(pI830)) { + I830RandRInit(pScreen, RR_Rotate_0); /* only 0 degrees for I965G */ + } else { + I830RandRInit(pScreen, RR_Rotate_0 | RR_Rotate_90 | RR_Rotate_180 | RR_Rotate_270); + } pI830->PointerMoved = pScrn->PointerMoved; pScrn->PointerMoved = I830PointerMoved; pI830->CreateScreenResources = pScreen->CreateScreenResources; @@ -7200,6 +7436,20 @@ I830BIOSScreenInit(int scrnIndex, ScreenPtr pScreen, int argc, char **argv) I830_dump_registers(pScrn); #endif + if (IS_I965G(pI830)) { + /* turn off clock gating */ +#if 0 + OUTREG(0x6204, 0x70804000); + OUTREG(0x6208, 0x00000001); +#else + OUTREG(0x6204, 0x70000000); +#endif + /* Enable DAP stateless accesses. + * Required for all i965 steppings. + */ + OUTREG(SVG_WORK_CTL, 0x00000010); + } + pI830->starting = FALSE; pI830->closing = FALSE; pI830->suspended = FALSE; @@ -7279,16 +7529,36 @@ I830AdjustFrame(int scrnIndex, int x, int y, int flags) if (pI830->Clone) { if (!pI830->pipe == 0) { - OUTREG(DSPABASE, Start + ((y * pScrn->displayWidth + x) * pI830->cpp)); + if (!IS_I965G(pI830)) { + OUTREG(DSPABASE, Start + ((y * pScrn->displayWidth + x) * pI830->cpp)); + } else { + OUTREG(DSPABASE, 0); + OUTREG(DSPASURF, Start + ((y * pScrn->displayWidth + x) * pI830->cpp)); + } } else { - OUTREG(DSPBBASE, Start + ((y * pScrn->displayWidth + x) * pI830->cpp)); + if (!IS_I965G(pI830)) { + OUTREG(DSPBBASE, Start + ((y * pScrn->displayWidth + x) * pI830->cpp)); + } else { + OUTREG(DSPBBASE, 0); + OUTREG(DSPBSURF, Start + ((y * pScrn->displayWidth + x) * pI830->cpp)); + } } } if (pI830->pipe == 0) { - OUTREG(DSPABASE, Start + ((y * pScrn->displayWidth + x) * pI830->cpp)); + if (!IS_I965G(pI830)) { + OUTREG(DSPABASE, Start + ((y * pScrn->displayWidth + x) * pI830->cpp)); + } else { + OUTREG(DSPABASE, 0); + OUTREG(DSPASURF, Start + ((y * pScrn->displayWidth + x) * pI830->cpp)); + } } else { - OUTREG(DSPBBASE, Start + ((y * pScrn->displayWidth + x) * pI830->cpp)); + if (!IS_I965G(pI830)) { + OUTREG(DSPBBASE, Start + ((y * pScrn->displayWidth + x) * pI830->cpp)); + } else { + OUTREG(DSPBBASE, 0); + OUTREG(DSPBSURF, Start + ((y * pScrn->displayWidth + x) * pI830->cpp)); + } } } @@ -7363,6 +7633,8 @@ I830BIOSLeaveVT(int scrnIndex, int flags) #ifdef XF86DRI if (pI830->directRenderingOpen) { DRILock(screenInfo.screens[pScrn->scrnIndex], 0); + + I830DRISetVBlankInterrupt (pScrn, FALSE); drmCtlUninstHandler(pI830->drmSubFD); } @@ -7795,12 +8067,21 @@ I830BIOSEnterVT(int scrnIndex, int flags) #ifdef XF86DRI if (pI830->directRenderingEnabled) { if (!pI830->starting) { + ScreenPtr pScreen = pScrn->pScreen; + drmI830Sarea *sarea = (drmI830Sarea *) DRIGetSAREAPrivate(pScreen); + int i; + I830DRIResume(screenInfo.screens[scrnIndex]); + I830DRISetVBlankInterrupt (pScrn, TRUE); I830RefreshRing(pScrn); I830Sync(pScrn); DO_RING_IDLE(); + sarea->texAge++; + for(i = 0; i < I830_NR_TEX_REGIONS+1 ; i++) + sarea->texList[i].age = sarea->texAge; + DPRINTF(PFX, "calling dri unlock\n"); DRIUnlock(screenInfo.screens[pScrn->scrnIndex]); } @@ -7860,7 +8141,8 @@ I830BIOSSwitchMode(int scrnIndex, DisplayModePtr mode, int flags) * The extra WindowTable check detects a rotation at startup. */ if ( (!WindowTable[pScrn->scrnIndex] || pspix->devPrivate.ptr == NULL) && - !pI830->DGAactive && (pScrn->PointerMoved == I830PointerMoved) ) { + !pI830->DGAactive && (pScrn->PointerMoved == I830PointerMoved) && + !IS_I965G(pI830)) { if (!I830Rotate(pScrn, mode)) ret = FALSE; } @@ -7903,7 +8185,7 @@ I830BIOSSaveScreen(ScreenPtr pScreen, int mode) ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum]; I830Ptr pI830 = I830PTR(pScrn); Bool on = xf86IsUnblank(mode); - CARD32 temp, ctrl, base; + CARD32 temp, ctrl, base, surf; DPRINTF(PFX, "I830BIOSSaveScreen: %d, on is %s\n", mode, BOOLTOSTRING(on)); @@ -7911,9 +8193,11 @@ I830BIOSSaveScreen(ScreenPtr pScreen, int mode) if (pI830->pipe == 0) { ctrl = DSPACNTR; base = DSPABASE; + surf = DSPASURF; } else { ctrl = DSPBCNTR; base = DSPBADDR; + surf = DSPBSURF; } if (pI830->planeEnabled[pI830->pipe]) { temp = INREG(ctrl); @@ -7925,6 +8209,10 @@ I830BIOSSaveScreen(ScreenPtr pScreen, int mode) /* Flush changes */ temp = INREG(base); OUTREG(base, temp); + if (IS_I965G(pI830)) { + temp = INREG(surf); + OUTREG(surf, temp); + } } if (pI830->CursorInfoRec && !pI830->SWCursor && pI830->cursorOn) { @@ -8059,9 +8347,7 @@ I830BIOSCloseScreen(int scrnIndex, ScreenPtr pScreen) pI830->used3D = NULL; } - if (pI830->shadowReq.minorversion >= 1) - pScrn->PointerMoved = pI830->PointerMoved; - + pScrn->PointerMoved = pI830->PointerMoved; pScrn->vtSema = FALSE; pI830->closing = FALSE; pScreen->CloseScreen = pI830->CloseScreen; @@ -8389,10 +8675,17 @@ I830CheckDevicesTimer(OsTimerPtr timer, CARD32 now, pointer arg) offset = pI8301->FrontBuffer2.Start + ((pScrn->frameY0 * pI830->displayWidth + pScrn->frameX0) * pI830->cpp); } - if (pI830->pipe == 0) - adjust = INREG(DSPABASE); - else - adjust = INREG(DSPBBASE); + if (IS_I965G(pI830)) { + if (pI830->pipe == 0) + adjust = INREG(DSPASURF); + else + adjust = INREG(DSPBSURF); + } else { + if (pI830->pipe == 0) + adjust = INREG(DSPABASE); + else + adjust = INREG(DSPBBASE); + } if (adjust != offset) { xf86DrvMsg(pScrn->scrnIndex, X_WARNING, |