USHORT usGetVbeModeNum(ScrnInfoPtr pScrn, DisplayModePtr mode) { RDCRecPtr pRDC; MODE_PRIVATE *pModePrivate; USHORT usVESAModeNum; UCHAR ucColorDepth = (UCHAR)(pScrn->bitsPerPixel); pRDC = RDCPTR(pScrn); pModePrivate = MODE_PRIVATE_PTR(mode); xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, DefaultLevel, "==Enter usGetVbeModeNum()== \n"); xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, InfoLevel, "==Display Width=0x%x, Height=0x%x, Color Depth=0x%x==\n", mode->HDisplay,mode->VDisplay,pScrn->bitsPerPixel); switch (ucColorDepth) { case 8: usVESAModeNum = pModePrivate->Mode_ID_8bpp; break; case 16: usVESAModeNum = pModePrivate->Mode_ID_16bpp; break; case 32: usVESAModeNum = pModePrivate->Mode_ID_32bpp; break; } xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, DefaultLevel, "==Exit usGetVbeModeNum() return VESA Mode = 0x%x==\n", usVESAModeNum); return usVESAModeNum; }
static Bool radeon_kernel_mode_enabled(ScrnInfoPtr pScrn, struct pci_device *pci_dev) { char *busIdString; int ret; if (!xf86LoaderCheckSymbol("DRICreatePCIBusID")) { xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 0, "[KMS] No DRICreatePCIBusID symbol, no kernel modesetting.\n"); return FALSE; } busIdString = DRICreatePCIBusID(pci_dev); ret = drmCheckModesettingSupported(busIdString); #if defined(__FreeBSD__) || defined(__FreeBSD_kernel__) if (ret) { if (xf86LoadKernelModule("radeonkms")) ret = drmCheckModesettingSupported(busIdString); } #endif free(busIdString); if (ret) { xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 0, "[KMS] drm report modesetting isn't supported.\n"); return FALSE; } xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 0, "[KMS] Kernel modesetting enabled.\n"); return TRUE; }
/* Bind GART memory with "key" at "offset" */ Bool xf86BindGARTMemory(int screenNum, int key, unsigned long offset) { agp_bind_t bind; int pageOffset; if (!GARTInit(screenNum) || (acquiredScreen != screenNum)) return FALSE; if (offset % AGP_PAGE_SIZE != 0) { xf86DrvMsg(screenNum, X_WARNING, "xf86BindGARTMemory: " "offset (0x%lx) is not page-aligned (%d)\n", offset, AGP_PAGE_SIZE); return FALSE; } pageOffset = offset / AGP_PAGE_SIZE; xf86DrvMsgVerb(screenNum, X_INFO, 3, "xf86BindGARTMemory: bind key %d at 0x%08lx " "(pgoffset %d)\n", key, offset, pageOffset); bind.agpb_pgstart = pageOffset; bind.agpb_key = key; if (ioctl(gartFd, AGPIOC_BIND, &bind) != 0) { xf86DrvMsg(screenNum, X_WARNING, "xf86BindGARTMemory: " "binding of gart memory with key %d\n" "\tat offset 0x%lx failed (%s)\n", key, offset, strerror(errno)); return FALSE; } return TRUE; }
Bool RDCSetMode(ScrnInfoPtr pScrn, DisplayModePtr mode) { RDCRecPtr pRDC; MODE_PRIVATE *pModePrivate; CBIOS_ARGUMENTS CBiosArguments; CBIOS_Extension CBiosExtension; USHORT usVESAMode; pRDC = RDCPTR(pScrn); pModePrivate = MODE_PRIVATE_PTR(mode); xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, InternalLevel, "==Enter RDCSetMode()== \n"); vRDCOpenKey(pScrn); bRDCRegInit(pScrn); CBiosExtension.pCBiosArguments = &CBiosArguments; CBiosExtension.IOAddress = (USHORT)(pRDC->RelocateIO); CBiosExtension.VideoVirtualAddress = (ULONG)(pRDC->FBVirtualAddr); CBiosArguments.reg.x.AX = OEMFunction; CBiosArguments.reg.x.BX = SetDisplay1RefreshRate; CBiosArguments.reg.lh.CL = pModePrivate->ucRRate_ID; CInt10(&CBiosExtension); usVESAMode = usGetVbeModeNum(pScrn, mode); CBiosArguments.reg.x.AX = VBESetMode; CBiosArguments.reg.x.BX = (0x4000 | usVESAMode); CInt10(&CBiosExtension); CBiosArguments.reg.x.AX = VBESetGetScanLineLength; CBiosArguments.reg.lh.BL = 0x00; CBiosArguments.reg.x.CX = (USHORT)(pScrn->displayWidth); CInt10(&CBiosExtension); xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, InternalLevel, "==Exit RDCSetMode(), return true== \n"); return (TRUE); }
static struct mtrr_wc_region * mtrr_cull_wc_region(int screenNum, unsigned long base, unsigned long size, MessageType from) { /* Some BIOS writers thought that setting wc over the mmio region of a graphics devices was a good idea. Try to fix it. */ struct mtrr_gentry gent; struct mtrr_wc_region *wcreturn = NULL, *wcr; int count, ret=0; /* Linux 2.0 users should not get a warning without -verbose */ if (!mtrr_open(2)) return NULL; for (gent.regnum = 0; ioctl(mtrr_fd, MTRRIOC_GET_ENTRY, &gent) >= 0; gent.regnum++) { if (gent.type != MTRR_TYPE_WRCOMB || gent.base + gent.size <= base || base + size <= gent.base) continue; /* Found an overlapping region. Delete it. */ wcr = xalloc(sizeof(*wcr)); if (!wcr) return NULL; wcr->sentry.base = gent.base; wcr->sentry.size = gent.size; wcr->sentry.type = MTRR_TYPE_WRCOMB; wcr->added = FALSE; count = 3; while (count-- && (ret = ioctl(mtrr_fd, MTRRIOC_KILL_ENTRY, &(wcr->sentry))) < 0); if (ret >= 0) { xf86DrvMsg(screenNum, from, "Removed MMIO write-combining range " "(0x%lx,0x%lx)\n", (unsigned long) gent.base, (unsigned long) gent.size); wcr->next = wcreturn; wcreturn = wcr; gent.regnum--; } else { xfree(wcr); xf86DrvMsgVerb(screenNum, X_WARNING, 0, "Failed to remove MMIO " "write-combining range (0x%lx,0x%lx)\n", gent.base, (unsigned long) gent.size); } } return wcreturn; }
/* * Note, the FORCE_LOW flag is currently not used or supported. */ static Bool AllocateOverlay(ScrnInfoPtr pScrn, int flags) { I830Ptr pI830 = I830PTR(pScrn); unsigned long size, alloced; Bool dryrun = ((flags & ALLOCATE_DRY_RUN) != 0); int verbosity = dryrun ? 4 : 1; const char *s = dryrun ? "[dryrun] " : ""; /* Clear overlay info */ memset(&(pI830->OverlayMem), 0, sizeof(pI830->OverlayMem)); pI830->OverlayMem.Key = -1; if (!pI830->XvEnabled) return TRUE; /* * The overlay register space needs a physical address in * system memory. We get this from the agpgart module using * a special memory type. */ size = OVERLAY_SIZE; if (flags & FORCE_LOW) flags |= FROM_POOL_ONLY | ALLOCATE_AT_BOTTOM | NEED_PHYSICAL_ADDR; else flags |= FROM_ANYWHERE | ALLOCATE_AT_TOP | NEED_PHYSICAL_ADDR; alloced = I830AllocVidMem(pScrn, &(pI830->OverlayMem), &(pI830->StolenPool), size, GTT_PAGE_SIZE, flags); /* * XXX For testing only. Don't enable this unless you know how to set * physBase. */ if (flags & FORCE_LOW) { ErrorF("AllocateOverlay() doesn't support setting FORCE_LOW\n"); return FALSE; } if (!dryrun && (alloced < size)) { xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Failed to allocate Overlay register space.\n"); /* This failure isn't fatal. */ } else { xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, verbosity, "%sAllocated %d kB for Overlay registers at 0x%x " "(0x%08x).\n", s, alloced / 1024, pI830->OverlayMem.Start, pI830->OverlayMem.Physical); } return TRUE; }
static Bool G80SorTMDSModeFixup(xf86OutputPtr output, DisplayModePtr mode, DisplayModePtr adjusted_mode) { int scrnIndex = output->scrn->scrnIndex; G80OutputPrivPtr pPriv = output->driver_private; DisplayModePtr modes = output->probed_modes; xf86DeleteMode(&pPriv->nativeMode, pPriv->nativeMode); if(modes) { // Find the preferred mode and use that as the "native" mode. // If no preferred mode is available, use the first one. DisplayModePtr mode; // Find the preferred mode. for(mode = modes; mode; mode = mode->next) { if(mode->type & M_T_PREFERRED) { xf86DrvMsgVerb(scrnIndex, X_INFO, 5, "%s: preferred mode is %s\n", output->name, mode->name); break; } } // XXX: May not want to allow scaling if no preferred mode is found. if(!mode) { mode = modes; xf86DrvMsgVerb(scrnIndex, X_INFO, 5, "%s: no preferred mode found, using %s\n", output->name, mode->name); } pPriv->nativeMode = xf86DuplicateMode(mode); G80CrtcDoModeFixup(pPriv->nativeMode, mode); } return G80SorModeFixup(output, mode, adjusted_mode); }
void fbdevHWAdjustFrame(ScrnInfoPtr pScrn, int x, int y) { fbdevHWPtr fPtr = FBDEVHWPTR(pScrn); if (x < 0 || x + fPtr->var.xres > fPtr->var.xres_virtual || y < 0 || y + fPtr->var.yres > fPtr->var.yres_virtual) return; fPtr->var.xoffset = x; fPtr->var.yoffset = y; if (-1 == ioctl(fPtr->fd, FBIOPAN_DISPLAY, (void *) &fPtr->var)) xf86DrvMsgVerb(pScrn->scrnIndex, X_WARNING, 5, "FBIOPAN_DISPLAY: %s\n", strerror(errno)); }
void fbdevHWAdjustFrame(int scrnIndex, int x, int y, int flags) { ScrnInfoPtr pScrn = xf86Screens[scrnIndex]; fbdevHWPtr fPtr = FBDEVHWPTR(pScrn); TRACE_ENTER("AdjustFrame"); if ( x < 0 || x + fPtr->var.xres > fPtr->var.xres_virtual || y < 0 || y + fPtr->var.yres > fPtr->var.yres_virtual ) return; fPtr->var.xoffset = x; fPtr->var.yoffset = y; if (-1 == ioctl(fPtr->fd,FBIOPAN_DISPLAY,(void*)&fPtr->var)) xf86DrvMsgVerb(scrnIndex, X_WARNING, 5, "FBIOPAN_DISPLAY: %s\n", strerror(errno)); }
static Bool radeon_ums_supported(ScrnInfoPtr pScrn, struct pci_device *pci_dev) { unsigned family = 0, i; for (i = 0; i < sizeof(RADEONCards) / sizeof(RADEONCardInfo); i++) { if (pci_dev->device_id == RADEONCards[i].pci_device_id) { family = RADEONCards[i].chip_family; break; } } if (family >= CHIP_FAMILY_SUMO) { xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 0, "GPU only supported with KMS, using vesa instead.\n"); return FALSE; } return TRUE; }
int I810CheckAvailableMemory(ScrnInfoPtr pScrn) { AgpInfoPtr agpinf; int maxPages; if (!xf86AgpGARTSupported() || !xf86AcquireGART(pScrn->scrnIndex) || (agpinf = xf86GetAGPInfo(pScrn->scrnIndex)) == NULL || !xf86ReleaseGART(pScrn->scrnIndex)) return -1; maxPages = agpinf->totalPages - agpinf->usedPages; xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 2, "%s: %dk available\n", "I810CheckAvailableMemory", maxPages * 4); return maxPages * 4; }
static Bool AllocateRingBuffer(ScrnInfoPtr pScrn, int flags) { I830Ptr pI830 = I830PTR(pScrn); unsigned long size, alloced; Bool dryrun = ((flags & ALLOCATE_DRY_RUN) != 0); int verbosity = dryrun ? 4 : 1; const char *s = dryrun ? "[dryrun] " : ""; /* Clear ring buffer info */ memset(&(pI830->LpRing), 0, sizeof(pI830->LpRing)); pI830->LpRing.mem.Key = -1; if (pI830->noAccel) return TRUE; /* Ring buffer */ size = PRIMARY_RINGBUFFER_SIZE; if (flags & FORCE_LOW) flags |= FROM_POOL_ONLY | ALLOCATE_AT_BOTTOM; else flags |= FROM_ANYWHERE | ALLOCATE_AT_TOP; alloced = I830AllocVidMem(pScrn, &(pI830->LpRing.mem), &(pI830->StolenPool), size, GTT_PAGE_SIZE, flags); if (alloced < size) { if (!dryrun) { xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Failed to allocate Ring Buffer space\n"); } return FALSE; } xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, verbosity, "%sAllocated %d kB for the ring buffer at 0x%x\n", s, alloced / 1024, pI830->LpRing.mem.Start); pI830->LpRing.tail_mask = pI830->LpRing.mem.Size - 1; return TRUE; }
/* Unbind GART memory with "key" */ Bool xf86UnbindGARTMemory(int screenNum, int key) { agp_unbind_t unbind; if (!GARTInit(screenNum) || (acquiredScreen != screenNum)) return FALSE; unbind.agpu_pri = 0; unbind.agpu_key = key; if (ioctl(gartFd, AGPIOC_UNBIND, &unbind) != 0) { xf86DrvMsg(screenNum, X_WARNING, "xf86UnbindGARTMemory: " "unbinding of gart memory with key %d " "failed (%s)\n", key, strerror(errno)); return FALSE; } xf86DrvMsgVerb(screenNum, X_INFO, 3, "xf86UnbindGARTMemory: unbind key %d\n", key); return TRUE; }
void RHDOutputPrintSensedType(struct rhdOutput *Output) { struct { enum rhdSensedOutput type; char *name; } list[] = { { RHD_SENSED_NONE, "none" }, { RHD_SENSED_VGA, "VGA" }, { RHD_SENSED_DVI, "DVI" }, { RHD_SENSED_TV_SVIDEO, "TV_SVIDEO"}, { RHD_SENSED_TV_COMPOSITE, "TV_COMPOSITE" }, { RHD_SENSED_TV_COMPONENT, "TV_COMPONENT" }, { 0, NULL } }; int i = 0; while (list[i].name) { if (list[i].type == Output->SensedType) { xf86DrvMsgVerb(Output->scrnIndex, X_INFO, 3, "%s: Sensed Output: %s\n",Output->Name, list[i].name); return; } i++; } }
static struct mtrr_wc_region * mtrr_add_wc_region(int screenNum, unsigned long base, unsigned long size, MessageType from) { struct mtrr_wc_region **wcr, *wcreturn, *curwcr; /* * There can be only one.... */ wcreturn = mtrr_remove_offending(screenNum, base, size, from); wcr = &wcreturn; while (*wcr) { wcr = &((*wcr)->next); } /* Linux 2.0 should not warn, unless the user explicitly asks for WC. */ if (!mtrr_open(from == X_CONFIG ? 0 : 2)) return wcreturn; *wcr = curwcr = xalloc(sizeof(**wcr)); if (!curwcr) return wcreturn; curwcr->sentry.base = base; curwcr->sentry.size = size; curwcr->sentry.type = MTRR_TYPE_WRCOMB; curwcr->added = TRUE; curwcr->next = NULL; #if SPLIT_WC_REGIONS /* * Splits up the write-combining region if it is not aligned on a * size boundary. */ { unsigned long lbase, d_size = 1; unsigned long n_size = size; unsigned long n_base = base; for (lbase = n_base, d_size = 1; !(lbase & 1); lbase = lbase >> 1, d_size <<= 1); while (d_size > n_size) d_size = d_size >> 1; DebugF("WC_BASE: 0x%lx WC_END: 0x%lx\n",base,base+d_size-1); n_base += d_size; n_size -= d_size; if (n_size) { xf86DrvMsgVerb(screenNum,X_INFO,3,"Splitting WC range: " "base: 0x%lx, size: 0x%lx\n",base,size); curwcr->next = mtrr_add_wc_region(screenNum, n_base, n_size,from); } curwcr->sentry.size = d_size; } /*****************************************************************/ #endif /* SPLIT_WC_REGIONS */ if (ioctl(mtrr_fd, MTRRIOC_ADD_ENTRY, &curwcr->sentry) >= 0) { /* Avoid printing on every VT switch */ if (xf86ServerIsInitialising()) { xf86DrvMsg(screenNum, from, "Write-combining range (0x%lx,0x%lx)\n", base, size); } return wcreturn; } else { *wcr = curwcr->next; xfree(curwcr); /* Don't complain about the VGA region: MTRR fixed regions aren't currently supported, but might be in the future. */ if ((unsigned long)base >= 0x100000) { xf86DrvMsgVerb(screenNum, X_WARNING, 0, "Failed to set up write-combining range " "(0x%lx,0x%lx)\n", base, size); } return wcreturn; } }
DisplayModePtr RDCBuildModePool(ScrnInfoPtr pScrn) { DisplayModePtr pMode = NULL, pModePoolHead = NULL, pModePoolTail = NULL; CBIOS_ARGUMENTS CBiosArguments; CBIOS_Extension CBiosExtension; RDCRecPtr pRDC = RDCPTR(pScrn); MODE_PRIVATE *pModePrivate; USHORT usSerialNum = 0; USHORT wLCDHorSize, wLCDVerSize; USHORT wVESAModeHorSize, wVESAModeVerSize; BYTE bColorDepth; xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, DefaultLevel, "==Enter RDCBuildModePool()== \n"); CBiosExtension.pCBiosArguments = &CBiosArguments; CBiosExtension.IOAddress = (USHORT)(pRDC->RelocateIO); CBiosExtension.VideoVirtualAddress = (ULONG)(pRDC->FBVirtualAddr); do { xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 5, "Mode serial Num 0x%x\n",usSerialNum); CBiosArguments.reg.x.AX = OEMFunction; CBiosArguments.reg.x.BX = QuerySupportedMode; CBiosArguments.reg.x.CX = usSerialNum++; CInt10(&CBiosExtension); wVESAModeHorSize = (USHORT)(CBiosArguments.reg.ex.EDX & 0x0000FFFF); wVESAModeVerSize = (USHORT)(CBiosArguments.reg.ex.EDX >> 16); if (CBiosArguments.reg.x.AX == VBEFunctionCallSuccessful) { pMode = SearchDisplayModeRecPtr(pModePoolHead, CBiosArguments); if (pMode == NULL) { if (pModePoolHead != NULL) { pModePoolTail->next = xnfcalloc(1, sizeof(DisplayModeRec)); pModePoolTail->next->prev = pModePoolTail; pModePoolTail = pModePoolTail->next; } else { pModePoolHead = xnfcalloc(1, sizeof(DisplayModeRec)); pModePoolHead->prev = NULL; pModePoolTail = pModePoolHead; } pModePoolTail->next = NULL; pModePoolTail->name = pcConvertResolutionToString(CBiosArguments.reg.ex.EDX); pModePoolTail->status = MODE_OK; pModePoolTail->type = M_T_BUILTIN; pModePoolTail->Flags = 0; pModePoolTail->PrivSize = sizeof(MODE_PRIVATE); pModePoolTail->Private = xnfcalloc(1, pModePoolTail->PrivSize); pModePrivate = MODE_PRIVATE_PTR(pModePoolTail); pModePoolTail->Clock = pModePoolTail->SynthClock = CBiosArguments.reg.ex.EDI; pModePoolTail->HDisplay = pModePoolTail->CrtcHDisplay = wVESAModeHorSize; pModePoolTail->VDisplay = pModePoolTail->CrtcVDisplay = wVESAModeVerSize; BTranslateIndexToRefreshRate(CBiosArguments.reg.lh.CH, &(pModePoolTail->VRefresh)); pModePoolTail->PrivFlags = (int)CBiosArguments.reg.x.SI; pModePrivate->ucRRate_ID = CBiosArguments.reg.lh.CH; } else { pModePrivate = MODE_PRIVATE_PTR(pMode); } switch (CBiosArguments.reg.lh.CL) { case 8: pModePrivate->Mode_ID_8bpp = CBiosArguments.reg.x.BX; xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 5, "pModePrivate->Mode_ID_8bpp = 0x%x\n",pModePrivate->Mode_ID_8bpp); break; case 16: pModePrivate->Mode_ID_16bpp = CBiosArguments.reg.x.BX; xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 5, "pModePrivate->Mode_ID_16bpp = 0x%x\n",pModePrivate->Mode_ID_16bpp); break; case 32: pModePrivate->Mode_ID_32bpp = CBiosArguments.reg.x.BX; xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 5, "pModePrivate->Mode_ID_32bpp = 0x%x\n",pModePrivate->Mode_ID_32bpp); break; } } } while (CBiosArguments.reg.x.AX == VBEFunctionCallSuccessful); for (bColorDepth = 0; bColorDepth < 3; bColorDepth++) { CBiosArguments.reg.x.AX = OEMFunction; CBiosArguments.reg.x.BX = QueryLCDPanelSizeMode; CBiosArguments.reg.x.CX = bColorDepth; CInt10(&CBiosExtension); if (CBiosArguments.reg.x.AX == VBEFunctionCallSuccessful) { pMode = SearchDisplayModeRecPtr(pModePoolHead, CBiosArguments); if (pMode == NULL) { if (pModePoolHead != NULL) { pModePoolTail->next = xnfcalloc(1, sizeof(DisplayModeRec)); pModePoolTail->next->prev = pModePoolTail; pModePoolTail = pModePoolTail->next; } else { pModePoolHead = xnfcalloc(1, sizeof(DisplayModeRec)); pModePoolHead->prev = NULL; pModePoolTail = pModePoolHead; } pModePoolTail->next = NULL; pModePoolTail->name = pcConvertResolutionToString(CBiosArguments.reg.ex.EDX); pModePoolTail->status = MODE_OK; pModePoolTail->type = M_T_BUILTIN; pModePoolTail->Flags = 0; pModePoolTail->PrivSize = sizeof(MODE_PRIVATE); pModePoolTail->Private = xnfcalloc(1, pModePoolTail->PrivSize); pModePrivate = MODE_PRIVATE_PTR(pModePoolTail); pModePoolTail->Clock = pModePoolTail->SynthClock = CBiosArguments.reg.ex.EDI; pModePoolTail->HDisplay = pModePoolTail->CrtcHDisplay = (CBiosArguments.reg.ex.EDX & 0x0000FFFF); pModePoolTail->VDisplay = pModePoolTail->CrtcVDisplay = (CBiosArguments.reg.ex.EDX >> 16); BTranslateIndexToRefreshRate(CBiosArguments.reg.lh.CH, &(pModePoolTail->VRefresh)); pModePoolTail->PrivFlags = (int)CBiosArguments.reg.x.SI | LCD_TIMING; pModePrivate->ucRRate_ID = CBiosArguments.reg.lh.CH; } else { pModePrivate = MODE_PRIVATE_PTR(pMode); } switch (CBiosArguments.reg.lh.CL) { case 8: pModePrivate->Mode_ID_8bpp = CBiosArguments.reg.x.BX; break; case 16: pModePrivate->Mode_ID_16bpp = CBiosArguments.reg.x.BX; break; case 32: pModePrivate->Mode_ID_32bpp = CBiosArguments.reg.x.BX; break; } }
Bool xf86InitFBManagerArea( ScreenPtr pScreen, int PixelArea, int Verbosity ) { ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum]; xRectangle Rect[3]; RegionPtr pRegion, pScreenRegion; int nRect; Bool ret = FALSE; if (PixelArea < (pScrn->displayWidth * pScrn->virtualY)) return FALSE; Rect[0].x = Rect[0].y = 0; Rect[0].width = pScrn->displayWidth; Rect[0].height = PixelArea / pScrn->displayWidth; nRect = 1; /* Add a possible partial scanline */ if ((Rect[1].height = Rect[1].width = PixelArea % pScrn->displayWidth)) { Rect[1].x = 0; Rect[1].y = Rect[0].height; Rect[1].height = 1; nRect++; } /* Factor out virtual resolution */ pRegion = RECTS_TO_REGION(pScreen, nRect, Rect, 0); if (pRegion) { if (!REGION_NAR(pRegion)) { Rect[2].x = Rect[2].y = 0; Rect[2].width = pScrn->virtualX; Rect[2].height = pScrn->virtualY; pScreenRegion = RECTS_TO_REGION(pScreen, 1, &Rect[2], 0); if (pScreenRegion) { if (!REGION_NAR(pScreenRegion)) { REGION_SUBTRACT(pScreen, pRegion, pRegion, pScreenRegion); ret = xf86InitFBManagerRegion(pScreen, pRegion); if (ret && xf86GetVerbosity() >= Verbosity) { int scrnIndex = pScrn->scrnIndex; xf86DrvMsgVerb(scrnIndex, X_INFO, Verbosity, "Largest offscreen areas (with overlaps):\n"); if (Rect[2].width < Rect[0].width) { xf86DrvMsgVerb(scrnIndex, X_INFO, Verbosity, "\t%d x %d rectangle at %d,0\n", Rect[0].width - Rect[2].width, Rect[0].height, Rect[2].width); } if (Rect[2].width < Rect[1].width) { xf86DrvMsgVerb(scrnIndex, X_INFO, Verbosity, "\t%d x %d rectangle at %d,0\n", Rect[1].width - Rect[2].width, Rect[0].height + Rect[1].height, Rect[2].width); } if (Rect[2].height < Rect[0].height) { xf86DrvMsgVerb(scrnIndex, X_INFO, Verbosity, "\t%d x %d rectangle at 0,%d\n", Rect[0].width, Rect[0].height - Rect[2].height, Rect[2].height); } if (Rect[1].height) { xf86DrvMsgVerb(scrnIndex, X_INFO, Verbosity, "\t%d x %d rectangle at 0,%d\n", Rect[1].width, Rect[0].height - Rect[2].height + Rect[1].height, Rect[2].height); } } } REGION_DESTROY(pScreen, pScreenRegion); } } REGION_DESTROY(pScreen, pRegion); } return ret; }
Bool I830Allocate3DMemory(ScrnInfoPtr pScrn, const int flags) { I830Ptr pI830 = I830PTR(pScrn); unsigned long size, alloced, align = 0; int i; Bool tileable; Bool dryrun = ((flags & ALLOCATE_DRY_RUN) != 0); int verbosity = dryrun ? 4 : 1; const char *s = dryrun ? "[dryrun] " : ""; int lines; DPRINTF(PFX, "I830Allocate3DMemory\n"); /* Back Buffer */ memset(&(pI830->BackBuffer), 0, sizeof(pI830->BackBuffer)); pI830->BackBuffer.Key = -1; tileable = !(flags & ALLOC_NO_TILING) && IsTileable(pScrn->displayWidth * pI830->cpp); if (tileable) { /* Make the height a multiple of the tile height (16) */ lines = (pScrn->virtualY + 15) / 16 * 16; } else { lines = pScrn->virtualY; } size = ROUND_TO_PAGE(pScrn->displayWidth * lines * pI830->cpp); /* * Try to allocate on the best tile-friendly boundaries. */ alloced = 0; if (tileable) { align = GetBestTileAlignment(size); for (align = GetBestTileAlignment(size); align >= KB(512); align >>= 1) { alloced = I830AllocVidMem(pScrn, &(pI830->BackBuffer), &(pI830->StolenPool), size, align, flags | FROM_ANYWHERE | ALLOCATE_AT_TOP | ALIGN_BOTH_ENDS); if (alloced >= size) break; } } if (alloced < size) { /* Give up on trying to tile */ tileable = FALSE; size = ROUND_TO_PAGE(pScrn->displayWidth * pScrn->virtualY * pI830->cpp); align = GTT_PAGE_SIZE; alloced = I830AllocVidMem(pScrn, &(pI830->BackBuffer), &(pI830->StolenPool), size, align, flags | FROM_ANYWHERE | ALLOCATE_AT_TOP); } if (alloced < size) { if (!dryrun) { xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Failed to allocate back buffer space.\n"); } return FALSE; } xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, verbosity, "%sAllocated %d kB for the back buffer at 0x%x.\n", s, alloced / 1024, pI830->BackBuffer.Start); /* Depth Buffer -- same size as the back buffer */ memset(&(pI830->DepthBuffer), 0, sizeof(pI830->DepthBuffer)); pI830->DepthBuffer.Key = -1; /* * Try to allocate on the best tile-friendly boundaries. */ alloced = 0; if (tileable) { /* Start with the previous align value. */ for (; align >= KB(512); align >>= 1) { alloced = I830AllocVidMem(pScrn, &(pI830->DepthBuffer), &(pI830->StolenPool), size, align, flags | FROM_ANYWHERE | ALLOCATE_AT_TOP | ALIGN_BOTH_ENDS); if (alloced >= size) break; } } if (alloced < size) { /* Give up on trying to tile */ tileable = FALSE; size = ROUND_TO_PAGE(pScrn->displayWidth * pScrn->virtualY * pI830->cpp); align = GTT_PAGE_SIZE; alloced = I830AllocVidMem(pScrn, &(pI830->DepthBuffer), &(pI830->StolenPool), size, align, flags | FROM_ANYWHERE | ALLOCATE_AT_TOP); } if (alloced < size) { if (!dryrun) { xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Failed to allocate depth buffer space.\n"); } return FALSE; } xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, verbosity, "%sAllocated %d kB for the depth buffer at 0x%x.\n", s, alloced / 1024, pI830->DepthBuffer.Start); /* Space for logical context. 32k is fine for right now. */ memset(&(pI830->ContextMem), 0, sizeof(pI830->ContextMem)); pI830->ContextMem.Key = -1; size = KB(32); alloced = I830AllocVidMem(pScrn, &(pI830->ContextMem), &(pI830->StolenPool), size, GTT_PAGE_SIZE, flags | FROM_ANYWHERE | ALLOCATE_AT_TOP); if (alloced < size) { if (!dryrun) { xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Failed to allocate logical context space.\n"); } return FALSE; } xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, verbosity, "%sAllocated %d kB for the logical context at 0x%x.\n", s, alloced / 1024, pI830->ContextMem.Start); /* * Space for DMA buffers, only if there's enough free for at least 1MB * of texture space. */ memset(&(pI830->BufferMem), 0, sizeof(pI830->BufferMem)); pI830->BufferMem.Key = -1; /* This should already be a page multiple */ size = I830_DMA_BUF_NR * I830_DMA_BUF_SZ; if (dryrun || (GetFreeSpace(pScrn) >= size + MB(1))) { alloced = I830AllocVidMem(pScrn, &(pI830->BufferMem), &(pI830->StolenPool), size, GTT_PAGE_SIZE, flags | FROM_ANYWHERE | ALLOCATE_AT_TOP); if (alloced < size) { if (!dryrun) { xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Failed to allocate DMA buffer space.\n"); } return FALSE; } xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, verbosity, "%sAllocated %d kB for the DMA buffers at 0x%x.\n", s, alloced / 1024, pI830->BufferMem.Start); } else { if (!dryrun) { xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Not enough free space for DMA buffers.\n"); } return FALSE; } /* Allocate the remaining space for textures. */ memset(&(pI830->TexMem), 0, sizeof(pI830->TexMem)); pI830->TexMem.Key = -1; size = GetFreeSpace(pScrn); if (dryrun && (size < MB(1))) size = MB(1); i = myLog2(size / I830_NR_TEX_REGIONS); if (i < I830_LOG_MIN_TEX_REGION_SIZE) i = I830_LOG_MIN_TEX_REGION_SIZE; pI830->TexGranularity = i; /* Truncate size */ size >>= i; size <<= i; if (size < KB(512)) { if (!dryrun) { xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Less than %d kBytes for texture space.\n", size / 1024); } return FALSE; } alloced = I830AllocVidMem(pScrn, &(pI830->TexMem), &(pI830->StolenPool), size, GTT_PAGE_SIZE, flags | FROM_ANYWHERE | ALLOCATE_AT_TOP); if (alloced < size) { if (!dryrun) { xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Failed to allocate texture space.\n"); } return FALSE; } xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, verbosity, "%sAllocated %d kB for textures at 0x%x\n", s, alloced / 1024, pI830->TexMem.Start); return TRUE; }
Bool I830Allocate2DMemory(ScrnInfoPtr pScrn, const int flags) { I830Ptr pI830 = I830PTR(pScrn); unsigned long size, alloced; Bool dryrun = ((flags & ALLOCATE_DRY_RUN) != 0); int verbosity = dryrun ? 4 : 1; const char *s = dryrun ? "[dryrun] " : ""; Bool tileable; int align, alignflags; DPRINTF(PFX, "I830Allocate2DMemory: inital is %s\n", BOOLTOSTRING(flags & ALLOC_INITIAL)); if (!pI830->StolenOnly && (!xf86AgpGARTSupported() || !xf86AcquireGART(pScrn->scrnIndex))) { if (!dryrun) { xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "AGP GART support is either not available or cannot " "be used.\n" "\tMake sure your kernel has agpgart support or has the\n" "\tagpgart module loaded.\n"); } return FALSE; } /* * The I830 is slightly different from the I830/I815, it has no * dcache and it has stolen memory by default in its gtt. All * additional memory must go after it. */ DPRINTF(PFX, "size == %luk (%lu bytes == pScrn->videoRam)\n" "pI830->StolenSize == %luk (%lu bytes)\n", pScrn->videoRam, pScrn->videoRam * 1024, pI830->StolenPool.Free.Size / 1024, pI830->StolenPool.Free.Size); if (flags & ALLOC_INITIAL) { unsigned long minspace, avail, lineSize; int cacheLines, maxCacheLines; if (pI830->NeedRingBufferLow) AllocateRingBuffer(pScrn, flags | FORCE_LOW); /* Clear everything first. */ memset(&(pI830->FbMemBox), 0, sizeof(pI830->FbMemBox)); memset(&(pI830->FrontBuffer), 0, sizeof(pI830->FrontBuffer)); pI830->FrontBuffer.Key = -1; pI830->FbMemBox.x1 = 0; pI830->FbMemBox.x2 = pScrn->displayWidth; pI830->FbMemBox.y1 = 0; pI830->FbMemBox.y2 = pScrn->virtualY; /* * Calculate how much framebuffer memory to allocate. For the * initial allocation, calculate a reasonable minimum. This is * enough for the virtual screen size, plus some pixmap cache * space. */ lineSize = pScrn->displayWidth * pI830->cpp; minspace = lineSize * pScrn->virtualY; avail = pScrn->videoRam * 1024; maxCacheLines = (avail - minspace) / lineSize; /* This shouldn't happen. */ if (maxCacheLines < 0) { xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Internal Error: " "maxCacheLines < 0 in I830Allocate2DMemory()\n"); maxCacheLines = 0; } if (maxCacheLines > (MAX_DISPLAY_HEIGHT - pScrn->virtualY)) maxCacheLines = MAX_DISPLAY_HEIGHT - pScrn->virtualY; if (pI830->CacheLines >= 0) { cacheLines = pI830->CacheLines; } else { #if 1 /* Make sure there is enough for two DVD sized YUV buffers */ cacheLines = (pScrn->depth == 24) ? 256 : 384; if (pScrn->displayWidth <= 1024) cacheLines *= 2; #else /* * Make sure there is enough for two DVD sized YUV buffers. * Make that 1.5MB, which is around what was allocated with * the old algorithm */ cacheLines = (MB(1) + KB(512)) / pI830->cpp / pScrn->displayWidth; #endif } if (cacheLines > maxCacheLines) cacheLines = maxCacheLines; pI830->FbMemBox.y2 += cacheLines; xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, verbosity, "%sAllocating at least %d scanlines for pixmap cache\n", s, cacheLines); tileable = !(flags & ALLOC_NO_TILING) && pI830->allowPageFlip && IsTileable(pScrn->displayWidth * pI830->cpp); if (tileable) { align = KB(512); alignflags = ALIGN_BOTH_ENDS; } else { align = KB(64); alignflags = 0; } size = lineSize * (pScrn->virtualY + cacheLines); size = ROUND_TO_PAGE(size); xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, verbosity, "%sInitial framebuffer allocation size: %d kByte\n", s, size / 1024); alloced = I830AllocVidMem(pScrn, &(pI830->FrontBuffer), &(pI830->StolenPool), size, align, flags | alignflags | FROM_ANYWHERE | ALLOCATE_AT_BOTTOM); if (alloced < size) { if (!dryrun) { xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Failed to allocate framebuffer.\n"); } return FALSE; } } else { unsigned long lineSize; unsigned long extra = 0; unsigned long maxFb = 0; /* * XXX Need to "free" up any 3D allocations if the DRI ended up * and make them available for 2D. The best way to do this would * be position all of those regions contiguously at the end of the * StolenPool. */ extra = GetFreeSpace(pScrn); if (extra == 0) return TRUE; maxFb = pI830->FrontBuffer.Size + extra; lineSize = pScrn->displayWidth * pI830->cpp; maxFb = ROUND_DOWN_TO(maxFb, lineSize); if (maxFb > lineSize * MAX_DISPLAY_HEIGHT) maxFb = lineSize * MAX_DISPLAY_HEIGHT; if (maxFb > pI830->FrontBuffer.Size) { unsigned long oldsize; /* * Sanity check -- the fb should be the last thing allocated at * the bottom of the stolen pool. */ if (pI830->StolenPool.Free.Start != pI830->FrontBuffer.End) { xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Internal error in I830Allocate2DMemory():\n\t" "Framebuffer isn't the last allocation at the bottom" " of StolenPool\n\t(%x != %x).\n", pI830->FrontBuffer.End, pI830->StolenPool.Free.Start); return FALSE; } /* * XXX Maybe should have a "Free" function. This should be * the only place where a region is resized, and we know that * the fb is always at the bottom of the aperture/stolen pool, * and is the only region that is allocated bottom-up. * Allowing for more general realloction would require a smarter * allocation system. */ oldsize = pI830->FrontBuffer.Size; pI830->StolenPool.Free.Size += pI830->FrontBuffer.Size; pI830->StolenPool.Free.Start -= pI830->FrontBuffer.Size; xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, verbosity, "%sUpdated framebuffer allocation size from %d " "to %d kByte\n", s, oldsize / 1024, maxFb / 1024); xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, verbosity, "%sUpdated pixmap cache from %d scanlines to %d " "scanlines\n", s, oldsize / lineSize - pScrn->virtualY, maxFb / lineSize - pScrn->virtualY); pI830->FbMemBox.y2 = maxFb / lineSize; tileable = !(flags & ALLOC_NO_TILING) && pI830->allowPageFlip && IsTileable(pScrn->displayWidth * pI830->cpp); if (tileable) { align = KB(512); alignflags = ALIGN_BOTH_ENDS; } else { align = KB(64); alignflags = 0; } alloced = I830AllocVidMem(pScrn, &(pI830->FrontBuffer), &(pI830->StolenPool), maxFb, align, flags | alignflags | FROM_ANYWHERE | ALLOCATE_AT_BOTTOM); if (alloced < maxFb) { if (!dryrun) { xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Failed to re-allocate framebuffer\n"); } return FALSE; } } return TRUE; } #if REMAP_RESERVED /* * Allocate a dummy page to pass when attempting to rebind the * pre-allocated region. */ if (!dryrun) { memset(&(pI830->Dummy), 0, sizeof(pI830->Dummy)); pI830->Dummy.Key = xf86AllocateGARTMemory(pScrn->scrnIndex, size, 0, NULL); pI830->Dummy.Offset = 0; } #endif /* Clear cursor info */ memset(&(pI830->CursorMem), 0, sizeof(pI830->CursorMem)); pI830->CursorMem.Key = -1; if (!pI830->SWCursor) { int cursFlags = 0; /* * Mouse cursor -- The i810-i830 need a physical address in system * memory from which to upload the cursor. We get this from * the agpgart module using a special memory type. */ size = HWCURSOR_SIZE; cursFlags = FROM_ANYWHERE | ALLOCATE_AT_TOP; if (pI830->CursorNeedsPhysical) cursFlags |= NEED_PHYSICAL_ADDR; alloced = I830AllocVidMem(pScrn, &(pI830->CursorMem), &(pI830->StolenPool), size, GTT_PAGE_SIZE, flags | cursFlags); if (alloced < size) { if (!dryrun) { xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Failed to allocate HW cursor space.\n"); } } else { xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, verbosity, "%sAllocated %d kB for HW cursor at 0x%x", s, alloced / 1024, pI830->CursorMem.Start); if (pI830->CursorNeedsPhysical) xf86ErrorFVerb(verbosity, " (0x%08x)", pI830->CursorMem.Physical); xf86ErrorFVerb(verbosity, "\n"); } } #ifdef I830_XV AllocateOverlay(pScrn, flags); #endif if (!pI830->NeedRingBufferLow) AllocateRingBuffer(pScrn, flags); /* Clear scratch info */ memset(&(pI830->Scratch), 0, sizeof(pI830->Scratch)); pI830->Scratch.Key = -1; if (!pI830->noAccel) { size = MAX_SCRATCH_BUFFER_SIZE; alloced = I830AllocVidMem(pScrn, &(pI830->Scratch), &(pI830->StolenPool), size, GTT_PAGE_SIZE, flags | FROM_ANYWHERE | ALLOCATE_AT_TOP); if (alloced < size) { size = MIN_SCRATCH_BUFFER_SIZE; alloced = I830AllocVidMem(pScrn, &(pI830->Scratch), &(pI830->StolenPool), size, GTT_PAGE_SIZE, flags | FROM_ANYWHERE | ALLOCATE_AT_TOP); } if (alloced < size) { if (!dryrun) { xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Failed to allocate scratch buffer space\n"); } return FALSE; } xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, verbosity, "%sAllocated %d kB for the scratch buffer at 0x%x\n", s, alloced / 1024, pI830->Scratch.Start); } return TRUE; }
void SMILynx_Save(ScrnInfoPtr pScrn) { SMIPtr pSmi = SMIPTR(pScrn); int i; CARD32 offset; SMIRegPtr save = pSmi->save; vgaHWPtr hwp = VGAHWPTR(pScrn); vgaRegPtr vgaSavePtr = &hwp->SavedReg; int vgaIOBase = hwp->IOBase; int vgaCRIndex = vgaIOBase + VGA_CRTC_INDEX_OFFSET; int vgaCRData = vgaIOBase + VGA_CRTC_DATA_OFFSET; ENTER(); /* Save the standard VGA registers */ vgaHWSave(pScrn, vgaSavePtr, VGA_SR_ALL); save->smiDACMask = VGAIN8(pSmi, VGA_DAC_MASK); VGAOUT8(pSmi, VGA_DAC_READ_ADDR, 0); for (i = 0; i < 256; i++) { save->smiDacRegs[i][0] = VGAIN8(pSmi, VGA_DAC_DATA); save->smiDacRegs[i][1] = VGAIN8(pSmi, VGA_DAC_DATA); save->smiDacRegs[i][2] = VGAIN8(pSmi, VGA_DAC_DATA); } for (i = 0, offset = 2; i < 8192; i++, offset += 8) save->smiFont[i] = *(pSmi->FBBase + offset); /* Now we save all the extended registers we need. */ save->SR17 = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x17); save->SR18 = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x18); save->SR20 = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x20); save->SR21 = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x21); save->SR22 = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x22); save->SR23 = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x23); save->SR24 = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x24); save->SR31 = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x31); save->SR32 = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x32); save->SR66 = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x66); save->SR68 = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x68); save->SR69 = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x69); save->SR6A = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x6A); save->SR6B = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x6B); save->SR6C = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x6C); save->SR6D = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x6D); save->SR81 = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x81); save->SRA0 = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0xA0); if (pSmi->Dualhead) { /* dualhead stuff */ save->SR40 = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x40); save->SR41 = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x41); save->SR42 = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x42); save->SR43 = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x43); save->SR44 = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x44); save->SR45 = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x45); save->SR48 = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x48); save->SR49 = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x49); save->SR4A = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x4A); save->SR4B = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x4B); save->SR4C = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x4C); save->SR50 = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x50); save->SR51 = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x51); save->SR52 = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x52); save->SR53 = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x53); save->SR54 = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x54); save->SR55 = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x55); save->SR56 = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x56); save->SR57 = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x57); save->SR5A = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x5A); /* PLL2 stuff */ save->SR6E = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x6E); save->SR6F = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x6F); } if (SMI_LYNXM_SERIES(pSmi->Chipset)) { /* Save common registers */ save->CR30 = VGAIN8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x30); save->CR3A = VGAIN8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x3A); for (i = 0; i < 15; i++) { save->CR90[i] = VGAIN8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x90 + i); } for (i = 0; i < 14; i++) { save->CRA0[i] = VGAIN8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0xA0 + i); } /* Save primary registers */ VGAOUT8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x9E, save->CR90[14] & ~0x20); save->CR33 = VGAIN8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x33); for (i = 0; i < 14; i++) { save->CR40[i] = VGAIN8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x40 + i); } save->CR9F = VGAIN8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x9F); /* Save secondary registers */ VGAOUT8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x9E, save->CR90[14] | 0x20); save->CR33_2 = VGAIN8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x33); for (i = 0; i < 14; i++) { save->CR40_2[i] = VGAIN8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x40 + i); } save->CR9F_2 = VGAIN8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x9F); /* PDR#1069 */ VGAOUT8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x9E, save->CR90[14]); } else { save->CR30 = VGAIN8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x30); save->CR33 = VGAIN8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x33); save->CR3A = VGAIN8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x3A); for (i = 0; i < 14; i++) { save->CR40[i] = VGAIN8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x40 + i); } } save->DPR10 = READ_DPR(pSmi, 0x10); save->DPR1C = READ_DPR(pSmi, 0x1C); save->DPR20 = READ_DPR(pSmi, 0x20); save->DPR24 = READ_DPR(pSmi, 0x24); save->DPR28 = READ_DPR(pSmi, 0x28); save->DPR2C = READ_DPR(pSmi, 0x2C); save->DPR30 = READ_DPR(pSmi, 0x30); save->DPR3C = READ_DPR(pSmi, 0x3C); save->DPR40 = READ_DPR(pSmi, 0x40); save->DPR44 = READ_DPR(pSmi, 0x44); save->VPR00 = READ_VPR(pSmi, 0x00); save->VPR0C = READ_VPR(pSmi, 0x0C); save->VPR10 = READ_VPR(pSmi, 0x10); if (pSmi->Chipset == SMI_COUGAR3DR) { save->FPR00_ = READ_FPR(pSmi, FPR00); save->FPR0C_ = READ_FPR(pSmi, FPR0C); save->FPR10_ = READ_FPR(pSmi, FPR10); } save->CPR00 = READ_CPR(pSmi, 0x00); if (!pSmi->ModeStructInit) { vgaHWCopyReg(&hwp->ModeReg, vgaSavePtr); memcpy(pSmi->mode, save, sizeof(SMIRegRec)); pSmi->ModeStructInit = TRUE; } if (pSmi->useBIOS && pSmi->pInt10 != NULL) { pSmi->pInt10->num = 0x10; pSmi->pInt10->ax = 0x0F00; xf86ExecX86int10(pSmi->pInt10); save->mode = pSmi->pInt10->ax & 0x007F; xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Current mode 0x%02X.\n", save->mode); } if (xf86GetVerbosity() > 1) { xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, VERBLEV, "Saved current video mode. Register dump:\n"); SMI_PrintRegs(pScrn); } LEAVE(); }
/* * ATIDSPPreInit -- * * This function initialises global variables used to set DSP registers on a * VT-B or later. */ Bool ATIDSPPreInit ( int iScreen, ATIPtr pATI ) { CARD32 IOValue, dsp_config, dsp_on_off, vga_dsp_config, vga_dsp_on_off; int trp; /* * VT-B's and later have additional post-dividers that are not powers of * two. */ pATI->ClockDescriptor.NumD = 8; /* Retrieve XCLK settings */ IOValue = ATIGetMach64PLLReg(PLL_XCLK_CNTL); pATI->XCLKPostDivider = GetBits(IOValue, PLL_XCLK_SRC_SEL); pATI->XCLKReferenceDivider = 1; switch (pATI->XCLKPostDivider) { case 0: case 1: case 2: case 3: break; case 4: pATI->XCLKReferenceDivider = 3; pATI->XCLKPostDivider = 0; break; default: xf86DrvMsg(iScreen, X_ERROR, "Unsupported XCLK source: %d.\n", pATI->XCLKPostDivider); return FALSE; } pATI->XCLKPostDivider -= GetBits(IOValue, PLL_MFB_TIMES_4_2B); pATI->XCLKFeedbackDivider = ATIGetMach64PLLReg(PLL_MCLK_FB_DIV); xf86DrvMsgVerb(iScreen, X_INFO, 2, "Engine XCLK %.3f MHz; Refresh rate code %d.\n", ATIDivide(pATI->XCLKFeedbackDivider * pATI->ReferenceNumerator, pATI->XCLKReferenceDivider * pATI->ClockDescriptor.MaxM * pATI->ReferenceDenominator, 1 - pATI->XCLKPostDivider, 0) / (double)1000.0, GetBits(pATI->LockData.mem_cntl, CTL_MEM_REFRESH_RATE_B)); /* Compute maximum RAS delay and friends */ trp = GetBits(pATI->LockData.mem_cntl, CTL_MEM_TRP); pATI->XCLKPageFaultDelay = GetBits(pATI->LockData.mem_cntl, CTL_MEM_TRCD) + GetBits(pATI->LockData.mem_cntl, CTL_MEM_TCRD) + trp + 2; pATI->XCLKMaxRASDelay = GetBits(pATI->LockData.mem_cntl, CTL_MEM_TRAS) + trp + 2; pATI->DisplayFIFODepth = 32; if (pATI->Chip < ATI_CHIP_264VT4) { pATI->XCLKPageFaultDelay += 2; pATI->XCLKMaxRASDelay += 3; pATI->DisplayFIFODepth = 24; } switch (pATI->MemoryType) { case MEM_264_DRAM: if (pATI->VideoRAM <= 1024) pATI->DisplayLoopLatency = 10; else { pATI->DisplayLoopLatency = 8; pATI->XCLKPageFaultDelay += 2; } break; case MEM_264_EDO: case MEM_264_PSEUDO_EDO: if (pATI->VideoRAM <= 1024) pATI->DisplayLoopLatency = 9; else { pATI->DisplayLoopLatency = 8; pATI->XCLKPageFaultDelay++; } break; case MEM_264_SDRAM: if (pATI->VideoRAM <= 1024) pATI->DisplayLoopLatency = 11; else { pATI->DisplayLoopLatency = 10; pATI->XCLKPageFaultDelay++; } break; case MEM_264_SGRAM: pATI->DisplayLoopLatency = 8; pATI->XCLKPageFaultDelay += 3; break; default: /* Set maximums */ pATI->DisplayLoopLatency = 11; pATI->XCLKPageFaultDelay += 3; break; } if (pATI->XCLKMaxRASDelay <= pATI->XCLKPageFaultDelay) pATI->XCLKMaxRASDelay = pATI->XCLKPageFaultDelay + 1; /* Allow BIOS to override */ dsp_config = inr(DSP_CONFIG); dsp_on_off = inr(DSP_ON_OFF); vga_dsp_config = inr(VGA_DSP_CONFIG); vga_dsp_on_off = inr(VGA_DSP_ON_OFF); if (dsp_config) pATI->DisplayLoopLatency = GetBits(dsp_config, DSP_LOOP_LATENCY); if ((!dsp_on_off && (pATI->Chip < ATI_CHIP_264GTPRO)) || ((dsp_on_off == vga_dsp_on_off) && (!dsp_config || !((dsp_config ^ vga_dsp_config) & DSP_XCLKS_PER_QW)))) { if (ATIDivide(GetBits(vga_dsp_on_off, VGA_DSP_OFF), GetBits(vga_dsp_config, VGA_DSP_XCLKS_PER_QW), 5, 1) > 24) pATI->DisplayFIFODepth = 32; else pATI->DisplayFIFODepth = 24; } return TRUE; }
Bool xf86DeallocateGARTMemory(int screenNum, int key) { if (!GARTInit(screenNum) || acquiredScreen != screenNum) return FALSE; if (acquiredScreen != screenNum) { xf86DrvMsg(screenNum, X_ERROR, "xf86UnbindGARTMemory: AGP not acquired by this screen\n"); return FALSE; } #ifdef __linux__ if (ioctl(gartFd, AGPIOC_DEALLOCATE, (int *)(uintptr_t)key) != 0) { #else if (ioctl(gartFd, AGPIOC_DEALLOCATE, &key) != 0) { #endif xf86DrvMsg(screenNum, X_WARNING,"xf86DeAllocateGARTMemory: " "deallocation gart memory with key %d failed\n\t(%s)\n", key, strerror(errno)); return FALSE; } return TRUE; } /* Bind GART memory with "key" at "offset" */ Bool xf86BindGARTMemory(int screenNum, int key, unsigned long offset) { struct _agp_bind bind; int pageOffset; if (!GARTInit(screenNum) || acquiredScreen != screenNum) return FALSE; if (acquiredScreen != screenNum) { xf86DrvMsg(screenNum, X_ERROR, "xf86BindGARTMemory: AGP not acquired by this screen\n"); return FALSE; } if (offset % AGP_PAGE_SIZE != 0) { xf86DrvMsg(screenNum, X_WARNING, "xf86BindGARTMemory: " "offset (0x%lx) is not page-aligned (%d)\n", offset, AGP_PAGE_SIZE); return FALSE; } pageOffset = offset / AGP_PAGE_SIZE; xf86DrvMsgVerb(screenNum, X_INFO, 3, "xf86BindGARTMemory: bind key %d at 0x%08lx " "(pgoffset %d)\n", key, offset, pageOffset); bind.pg_start = pageOffset; bind.key = key; if (ioctl(gartFd, AGPIOC_BIND, &bind) != 0) { xf86DrvMsg(screenNum, X_WARNING, "xf86BindGARTMemory: " "binding of gart memory with key %d\n" "\tat offset 0x%lx failed (%s)\n", key, offset, strerror(errno)); return FALSE; } return TRUE; } /* Unbind GART memory with "key" */ Bool xf86UnbindGARTMemory(int screenNum, int key) { struct _agp_unbind unbind; if (!GARTInit(screenNum) || acquiredScreen != screenNum) return FALSE; if (acquiredScreen != screenNum) { xf86DrvMsg(screenNum, X_ERROR, "xf86UnbindGARTMemory: AGP not acquired by this screen\n"); return FALSE; } unbind.priority = 0; unbind.key = key; if (ioctl(gartFd, AGPIOC_UNBIND, &unbind) != 0) { xf86DrvMsg(screenNum, X_WARNING, "xf86UnbindGARTMemory: " "unbinding of gart memory with key %d " "failed (%s)\n", key, strerror(errno)); return FALSE; } xf86DrvMsgVerb(screenNum, X_INFO, 3, "xf86UnbindGARTMemory: unbind key %d\n", key); return TRUE; } /* XXX Interface may change. */ Bool xf86EnableAGP(int screenNum, CARD32 mode) { agp_setup setup; if (!GARTInit(screenNum) || acquiredScreen != screenNum) return FALSE; setup.agp_mode = mode; if (ioctl(gartFd, AGPIOC_SETUP, &setup) != 0) { xf86DrvMsg(screenNum, X_WARNING, "xf86EnableAGP: " "AGPIOC_SETUP with mode %ld failed (%s)\n", (unsigned long)mode, strerror(errno)); return FALSE; } return TRUE; }
void SMILynx_WriteMode(ScrnInfoPtr pScrn, vgaRegPtr vgaSavePtr, SMIRegPtr restore) { SMIPtr pSmi = SMIPTR(pScrn); int i; CARD8 tmp; CARD32 offset; vgaHWPtr hwp = VGAHWPTR(pScrn); int vgaIOBase = hwp->IOBase; int vgaCRIndex = vgaIOBase + VGA_CRTC_INDEX_OFFSET; int vgaCRData = vgaIOBase + VGA_CRTC_DATA_OFFSET; ENTER(); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x17, restore->SR17); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x18, restore->SR18); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x20, restore->SR20); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x21, restore->SR21); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x22, restore->SR22); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x23, restore->SR23); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x24, restore->SR24); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x31, restore->SR31); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x32, restore->SR32); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x66, restore->SR66); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x68, restore->SR68); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x69, restore->SR69); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x6A, restore->SR6A); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x6B, restore->SR6B); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x6C, restore->SR6C); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x6D, restore->SR6D); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x81, restore->SR81); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0xA0, restore->SRA0); if (pSmi->useBIOS && restore->mode != 0){ pSmi->pInt10->num = 0x10; pSmi->pInt10->ax = restore->mode | 0x80; xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Setting mode 0x%02X\n", restore->mode); xf86ExecX86int10(pSmi->pInt10); /* Enable linear mode. */ outb(pSmi->PIOBase + VGA_SEQ_INDEX, 0x18); tmp = inb(pSmi->PIOBase + VGA_SEQ_DATA); outb(pSmi->PIOBase + VGA_SEQ_DATA, tmp | 0x01); /* Enable DPR/VPR registers. */ tmp = VGAIN8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x21); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x21, tmp & ~0x03); } else { /* Restore the standard VGA registers */ vgaHWRestore(pScrn, vgaSavePtr, VGA_SR_ALL); if (restore->smiDACMask) { VGAOUT8(pSmi, VGA_DAC_MASK, restore->smiDACMask); } else { VGAOUT8(pSmi, VGA_DAC_MASK, 0xFF); } VGAOUT8(pSmi, VGA_DAC_WRITE_ADDR, 0); for (i = 0; i < 256; i++) { VGAOUT8(pSmi, VGA_DAC_DATA, restore->smiDacRegs[i][0]); VGAOUT8(pSmi, VGA_DAC_DATA, restore->smiDacRegs[i][1]); VGAOUT8(pSmi, VGA_DAC_DATA, restore->smiDacRegs[i][2]); } for (i = 0, offset = 2; i < 8192; i++, offset += 8) { *(pSmi->FBBase + offset) = restore->smiFont[i]; } if (SMI_LYNXM_SERIES(pSmi->Chipset)) { /* Restore secondary registers */ VGAOUT8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x9E, restore->CR90[14] | 0x20); VGAOUT8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x33, restore->CR33_2); for (i = 0; i < 14; i++) { VGAOUT8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x40 + i, restore->CR40_2[i]); } VGAOUT8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x9F, restore->CR9F_2); /* Restore primary registers */ VGAOUT8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x9E, restore->CR90[14] & ~0x20); VGAOUT8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x33, restore->CR33); for (i = 0; i < 14; i++) { VGAOUT8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x40 + i, restore->CR40[i]); } VGAOUT8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x9F, restore->CR9F); /* Restore common registers */ VGAOUT8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x30, restore->CR30); VGAOUT8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x3A, restore->CR3A); for (i = 0; i < 15; i++) VGAOUT8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x90 + i, restore->CR90[i]); for (i = 0; i < 14; i++) VGAOUT8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0xA0 + i, restore->CRA0[i]); }else{ VGAOUT8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x30, restore->CR30); VGAOUT8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x33, restore->CR33); VGAOUT8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x3A, restore->CR3A); for (i = 0; i < 14; i++) { VGAOUT8_INDEX(pSmi, vgaCRIndex, vgaCRData, 0x40 + i, restore->CR40[i]); } } if (pSmi->Dualhead) { /* dualhead stuff */ VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x40, restore->SR40); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x41, restore->SR41); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x42, restore->SR42); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x43, restore->SR43); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x44, restore->SR44); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x45, restore->SR45); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x48, restore->SR48); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x49, restore->SR49); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x4A, restore->SR4A); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x4B, restore->SR4B); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x4C, restore->SR4C); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x50, restore->SR50); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x51, restore->SR51); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x52, restore->SR52); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x53, restore->SR53); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x54, restore->SR54); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x55, restore->SR55); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x56, restore->SR56); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x57, restore->SR57); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x5A, restore->SR5A); /* PLL2 stuff */ VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x6E, restore->SR6E); VGAOUT8_INDEX(pSmi, VGA_SEQ_INDEX, VGA_SEQ_DATA, 0x6F, restore->SR6F); } } /* Reset the graphics engine */ WRITE_DPR(pSmi, 0x10, restore->DPR10); WRITE_DPR(pSmi, 0x1C, restore->DPR1C); WRITE_DPR(pSmi, 0x20, restore->DPR20); WRITE_DPR(pSmi, 0x24, restore->DPR24); WRITE_DPR(pSmi, 0x28, restore->DPR28); WRITE_DPR(pSmi, 0x2C, restore->DPR2C); WRITE_DPR(pSmi, 0x30, restore->DPR30); WRITE_DPR(pSmi, 0x3C, restore->DPR3C); WRITE_DPR(pSmi, 0x40, restore->DPR40); WRITE_DPR(pSmi, 0x44, restore->DPR44); /* write video controller regs */ WRITE_VPR(pSmi, 0x00, restore->VPR00); WRITE_VPR(pSmi, 0x0C, restore->VPR0C); WRITE_VPR(pSmi, 0x10, restore->VPR10); if(pSmi->Chipset == SMI_COUGAR3DR) { WRITE_FPR(pSmi, FPR00, restore->FPR00_); WRITE_FPR(pSmi, FPR0C, restore->FPR0C_); WRITE_FPR(pSmi, FPR10, restore->FPR10_); } WRITE_CPR(pSmi, 0x00, restore->CPR00); if (xf86GetVerbosity() > 1) { xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, VERBLEV, "Done restoring mode. Register dump:\n"); SMI_PrintRegs(pScrn); } vgaHWProtect(pScrn, FALSE); LEAVE(); }