Various minor tidyups
[nouveau] / src / nv_driver.c
1 /* $XdotOrg: driver/xf86-video-nv/src/nv_driver.c,v 1.21 2006/01/24 16:45:29 aplattner Exp $ */
2 /* $XConsortium: nv_driver.c /main/3 1996/10/28 05:13:37 kaleb $ */
3 /*
4  * Copyright 1996-1997  David J. McKay
5  *
6  * Permission is hereby granted, free of charge, to any person obtaining a
7  * copy of this software and associated documentation files (the "Software"),
8  * to deal in the Software without restriction, including without limitation
9  * the rights to use, copy, modify, merge, publish, distribute, sublicense,
10  * and/or sell copies of the Software, and to permit persons to whom the
11  * Software is furnished to do so, subject to the following conditions:
12  *
13  * The above copyright notice and this permission notice shall be included in
14  * all copies or substantial portions of the Software.
15  *
16  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
19  * DAVID J. MCKAY BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
20  * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
21  * OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
22  * SOFTWARE.
23  */
24
25 /* Hacked together from mga driver and 3.3.4 NVIDIA driver by Jarno Paananen
26    <jpaana@s2.org> */
27
28 /* $XFree86: xc/programs/Xserver/hw/xfree86/drivers/nv/nv_driver.c,v 1.144 2006/06/16 00:19:32 mvojkovi Exp $ */
29
30 #include <stdio.h>
31
32 #include "nv_include.h"
33
34 #include "xf86int10.h"
35
36 #include "xf86drm.h"
37
38 extern DisplayModePtr xf86ModesAdd(DisplayModePtr Modes, DisplayModePtr Additions);
39
40 /*
41  * Forward definitions for the functions that make up the driver.
42  */
43 /* Mandatory functions */
44 static const OptionInfoRec * NVAvailableOptions(int chipid, int busid);
45 static void    NVIdentify(int flags);
46 #ifndef XSERVER_LIBPCIACCESS
47 static Bool    NVProbe(DriverPtr drv, int flags);
48 #endif /* XSERVER_LIBPCIACCESS */
49 static Bool    NVPreInit(ScrnInfoPtr pScrn, int flags);
50 static Bool    NVScreenInit(int Index, ScreenPtr pScreen, int argc,
51                             char **argv);
52 static Bool    NVEnterVT(int scrnIndex, int flags);
53 static void    NVLeaveVT(int scrnIndex, int flags);
54 static Bool    NVCloseScreen(int scrnIndex, ScreenPtr pScreen);
55 static Bool    NVSaveScreen(ScreenPtr pScreen, int mode);
56
57 /* Optional functions */
58 static void    NVFreeScreen(int scrnIndex, int flags);
59 static ModeStatus NVValidMode(int scrnIndex, DisplayModePtr mode,
60                               Bool verbose, int flags);
61 static Bool    NVDriverFunc(ScrnInfoPtr pScrnInfo, xorgDriverFuncOp op,
62                               pointer data);
63
64 /* Internally used functions */
65
66 static Bool     NVMapMem(ScrnInfoPtr pScrn);
67 static Bool     NVUnmapMem(ScrnInfoPtr pScrn);
68 static void     NVSave(ScrnInfoPtr pScrn);
69 static void     NVRestore(ScrnInfoPtr pScrn);
70 static Bool     NVModeInit(ScrnInfoPtr pScrn, DisplayModePtr mode);
71
72 #ifdef XSERVER_LIBPCIACCESS
73
74 #define NOUVEAU_PCI_DEVICE(_vendor_id, _device_id) \
75         { (_vendor_id), (_device_id), PCI_MATCH_ANY, PCI_MATCH_ANY, 0x00030000, 0x00ffffff, 0 }
76
77 static const struct pci_id_match nouveau_device_match[] = {
78         NOUVEAU_PCI_DEVICE(PCI_VENDOR_NVIDIA, PCI_MATCH_ANY),
79         NOUVEAU_PCI_DEVICE(PCI_VENDOR_NVIDIA_SGS, PCI_MATCH_ANY),
80         { 0, 0, 0 },
81 };
82
83 static Bool NVPciProbe (        DriverPtr               drv,
84                                 int                     entity_num,
85                                 struct pci_device       *dev,
86                                 intptr_t                match_data      );
87
88 #endif /* XSERVER_LIBPCIACCESS */
89
90 /*
91  * This contains the functions needed by the server after loading the
92  * driver module.  It must be supplied, and gets added the driver list by
93  * the Module Setup funtion in the dynamic case.  In the static case a
94  * reference to this is compiled in, and this requires that the name of
95  * this DriverRec be an upper-case version of the driver name.
96  */
97
98 _X_EXPORT DriverRec NV = {
99         NV_VERSION,
100         NV_DRIVER_NAME,
101         NVIdentify,
102 #ifdef XSERVER_LIBPCIACCESS
103         NULL,
104 #else
105         NVProbe,
106 #endif /* XSERVER_LIBPCIACCESS */
107         NVAvailableOptions,
108         NULL,
109         0,
110         NULL,
111 #ifdef XSERVER_LIBPCIACCESS
112         nouveau_device_match,
113         NVPciProbe
114 #endif /* XSERVER_LIBPCIACCESS */
115 };
116
117 struct NvFamily
118 {
119   char *name;
120   char *chipset;
121 };
122
123 static struct NvFamily NVKnownFamilies[] =
124 {
125   { "RIVA TNT",    "NV04" },
126   { "RIVA TNT2",   "NV05" },
127   { "GeForce 256", "NV10" },
128   { "GeForce 2",   "NV11, NV15" },
129   { "GeForce 4MX", "NV17, NV18" },
130   { "GeForce 3",   "NV20" },
131   { "GeForce 4Ti", "NV25, NV28" },
132   { "GeForce FX",  "NV3x" },
133   { "GeForce 6",   "NV4x" },
134   { "GeForce 7",   "G7x" },
135   { "GeForce 8",   "G8x" },
136   { NULL, NULL}
137 };
138
139 /*
140  * List of symbols from other modules that this module references.  This
141  * list is used to tell the loader that it is OK for symbols here to be
142  * unresolved providing that it hasn't been told that they haven't been
143  * told that they are essential via a call to xf86LoaderReqSymbols() or
144  * xf86LoaderReqSymLists().  The purpose is this is to avoid warnings about
145  * unresolved symbols that are not required.
146  */
147
148 static const char *vgahwSymbols[] = {
149     "vgaHWUnmapMem",
150     "vgaHWDPMSSet",
151     "vgaHWFreeHWRec",
152     "vgaHWGetHWRec",
153     "vgaHWGetIndex",
154     "vgaHWInit",
155     "vgaHWMapMem",
156     "vgaHWProtect",
157     "vgaHWRestore",
158     "vgaHWSave",
159     "vgaHWSaveScreen",
160     NULL
161 };
162
163 static const char *fbSymbols[] = {
164     "fbPictureInit",
165     "fbScreenInit",
166     NULL
167 };
168
169 static const char *exaSymbols[] = {
170     "exaDriverInit",
171     "exaOffscreenInit",
172     NULL
173 };
174
175 static const char *ramdacSymbols[] = {
176     "xf86CreateCursorInfoRec",
177     "xf86DestroyCursorInfoRec",
178     "xf86InitCursor",
179     NULL
180 };
181
182 static const char *ddcSymbols[] = {
183     "xf86PrintEDID",
184     "xf86DoEDID_DDC2",
185     "xf86SetDDCproperties",
186     NULL
187 };
188
189 static const char *vbeSymbols[] = {
190     "VBEInit",
191     "vbeFree",
192     "vbeDoEDID",
193     NULL
194 };
195
196 static const char *i2cSymbols[] = {
197     "xf86CreateI2CBusRec",
198     "xf86I2CBusInit",
199     NULL
200 };
201
202 static const char *shadowSymbols[] = {
203     "ShadowFBInit",
204     NULL
205 };
206
207 static const char *int10Symbols[] = {
208     "xf86FreeInt10",
209     "xf86InitInt10",
210     NULL
211 };
212
213 const char *drmSymbols[] = {
214     "drmOpen", 
215     "drmAddBufs",
216     "drmAddMap",
217     "drmAgpAcquire",
218     "drmAgpVersionMajor",
219     "drmAgpVersionMinor",
220     "drmAgpAlloc",
221     "drmAgpBind",
222     "drmAgpEnable",
223     "drmAgpFree",
224     "drmAgpRelease",
225     "drmAgpUnbind",
226     "drmAuthMagic",
227     "drmCommandNone",
228     "drmCommandWrite",
229     "drmCommandWriteRead",
230     "drmCreateContext",
231     "drmCtlInstHandler",
232     "drmCtlUninstHandler",
233     "drmDestroyContext",
234     "drmFreeVersion",
235     "drmGetInterruptFromBusID",
236     "drmGetLibVersion",
237     "drmGetVersion",
238     NULL
239 };
240
241 const char *driSymbols[] = {
242     "DRICloseScreen",
243     "DRICreateInfoRec",
244     "DRIDestroyInfoRec",
245     "DRIFinishScreenInit",
246     "DRIGetSAREAPrivate",
247     "DRILock",
248     "DRIQueryVersion",
249     "DRIScreenInit",
250     "DRIUnlock",
251     "GlxSetVisualConfigs",
252     "DRICreatePCIBusID",
253     NULL
254 };
255
256
257 static MODULESETUPPROTO(nouveauSetup);
258
259 static XF86ModuleVersionInfo nouveauVersRec =
260 {
261     "nouveau",
262     MODULEVENDORSTRING,
263     MODINFOSTRING1,
264     MODINFOSTRING2,
265     XORG_VERSION_CURRENT,
266     NV_MAJOR_VERSION, NV_MINOR_VERSION, NV_PATCHLEVEL,
267     ABI_CLASS_VIDEODRV,                     /* This is a video driver */
268     ABI_VIDEODRV_VERSION,
269     MOD_CLASS_VIDEODRV,
270     {0,0,0,0}
271 };
272
273 _X_EXPORT XF86ModuleData nouveauModuleData = { &nouveauVersRec, nouveauSetup, NULL };
274
275 static Bool
276 NVGetRec(ScrnInfoPtr pScrn)
277 {
278     /*
279      * Allocate an NVRec, and hook it into pScrn->driverPrivate.
280      * pScrn->driverPrivate is initialised to NULL, so we can check if
281      * the allocation has already been done.
282      */
283     if (pScrn->driverPrivate != NULL)
284         return TRUE;
285
286     pScrn->driverPrivate = xnfcalloc(sizeof(NVRec), 1);
287     /* Initialise it */
288
289     return TRUE;
290 }
291
292 static void
293 NVFreeRec(ScrnInfoPtr pScrn)
294 {
295     if (pScrn->driverPrivate == NULL)
296         return;
297     xfree(pScrn->driverPrivate);
298     pScrn->driverPrivate = NULL;
299 }
300
301
302 static pointer
303 nouveauSetup(pointer module, pointer opts, int *errmaj, int *errmin)
304 {
305         static Bool setupDone = FALSE;
306
307         /* This module should be loaded only once, but check to be sure. */
308
309         if (!setupDone) {
310                 setupDone = TRUE;
311                 /* The 1 here is needed to turn off a backwards compatibility mode */
312                 /* Otherwise NVPciProbe() is not called */
313                 xf86AddDriver(&NV, module, 1);
314
315                 /*
316                  * Modules that this driver always requires may be loaded here
317                  * by calling LoadSubModule().
318                  */
319                 /*
320                  * Tell the loader about symbols from other modules that this module
321                  * might refer to.
322                  */
323                 LoaderRefSymLists(vgahwSymbols, exaSymbols, fbSymbols,
324 #ifdef XF86DRI
325                                 drmSymbols, 
326 #endif
327                                 ramdacSymbols, shadowSymbols,
328                                 i2cSymbols, ddcSymbols, vbeSymbols,
329                                 int10Symbols, NULL);
330
331                 /*
332                  * The return value must be non-NULL on success even though there
333                  * is no TearDownProc.
334                  */
335                 return (pointer)1;
336         } else {
337                 if (errmaj) *errmaj = LDR_ONCEONLY;
338                 return NULL;
339         }
340 }
341
342 static const OptionInfoRec *
343 NVAvailableOptions(int chipid, int busid)
344 {
345     return NVOptions;
346 }
347
348 /* Mandatory */
349 static void
350 NVIdentify(int flags)
351 {
352     struct NvFamily *family;
353     size_t maxLen=0;
354
355     xf86DrvMsg(0, X_INFO, NV_NAME " driver " NV_DRIVER_DATE "\n");
356     xf86DrvMsg(0, X_INFO, NV_NAME " driver for NVIDIA chipset families :\n");
357
358     /* maximum length for alignment */
359     family = NVKnownFamilies;
360     while(family->name && family->chipset)
361     {
362         maxLen = max(maxLen, strlen(family->name));
363         family++;
364     }
365
366     /* display */
367     family = NVKnownFamilies;
368     while(family->name && family->chipset)
369     {
370         size_t len = strlen(family->name);
371         xf86ErrorF("\t%s", family->name);
372         while(len<maxLen+1)
373         {
374             xf86ErrorF(" ");
375             len++;
376         }
377         xf86ErrorF("(%s)\n", family->chipset);
378         family++;
379     }
380 }
381
382
383 #ifndef XSERVER_LIBPCIACCESS
384 static Bool
385 NVGetScrnInfoRec(PciChipsets *chips, int chip)
386 {
387     ScrnInfoPtr pScrn;
388
389     pScrn = xf86ConfigPciEntity(NULL, 0, chip,
390                                 chips, NULL, NULL, NULL,
391                                 NULL, NULL);
392
393     if(!pScrn) return FALSE;
394
395     pScrn->driverVersion    = NV_VERSION;
396     pScrn->driverName       = NV_DRIVER_NAME;
397     pScrn->name             = NV_NAME;
398
399     pScrn->Probe = NVProbe;
400     pScrn->PreInit          = NVPreInit;
401     pScrn->ScreenInit       = NVScreenInit;
402     pScrn->SwitchMode       = NVSwitchMode;
403     pScrn->AdjustFrame      = NVAdjustFrame;
404     pScrn->EnterVT          = NVEnterVT;
405     pScrn->LeaveVT          = NVLeaveVT;
406     pScrn->FreeScreen       = NVFreeScreen;
407     pScrn->ValidMode        = NVValidMode;
408
409     return TRUE;
410 }
411 #endif
412
413 /* This returns architecture in hexdecimal, so NV40 is 0x40 */
414 static int NVGetArchitecture (volatile CARD32 *regs)
415 {
416         int architecture = 0;
417
418         /* We're dealing with >=NV10 */
419         if ((regs[0] & 0x0f000000) > 0 ) {
420                 /* Bit 27-20 contain the architecture in hex */
421                 architecture = (regs[0] & 0xff00000) >> 20;
422         /* NV04 or NV05 */
423         } else if ((regs[0] & 0xff00fff0) == 0x20004000) {
424                 architecture = 0x04;
425         }
426
427         return architecture;
428 }
429
430 /* Reading the pci_id from the card registers is the most reliable way */
431 static CARD32 NVGetPCIID (volatile CARD32 *regs)
432 {
433         CARD32 pci_id;
434
435         int architecture = NVGetArchitecture(regs);
436
437         /* Dealing with an unknown or unsupported card */
438         if (architecture == 0) {
439                 return 0;
440         }
441
442         if (architecture >= 0x40)
443                 pci_id = regs[0x88000/4];
444         else
445                 pci_id = regs[0x1800/4];
446
447         /* A pci-id can be inverted, we must correct this */
448         if ((pci_id & 0xffff) == PCI_VENDOR_NVIDIA) {
449                 pci_id = (PCI_VENDOR_NVIDIA << 16) | (pci_id >> 16);
450         } else if ((pci_id & 0xffff) == PCI_VENDOR_NVIDIA_SGS) {
451                 pci_id = (PCI_VENDOR_NVIDIA_SGS << 16) | (pci_id >> 16);
452         /* Checking endian issues */
453         } else {
454                 /* PCI_VENDOR_NVIDIA = 0x10DE */
455                 if ((pci_id & (0xffff << 16)) == (0xDE10 << 16)) { /* wrong endian */
456                         pci_id = (PCI_VENDOR_NVIDIA << 16) | ((pci_id << 8) & 0x0000ff00) |
457                                 ((pci_id >> 8) & 0x000000ff);
458                 /* PCI_VENDOR_NVIDIA_SGS = 0x12D2 */
459                 } else if ((pci_id & (0xffff << 16)) == (0xD212 << 16)) { /* wrong endian */
460                         pci_id = (PCI_VENDOR_NVIDIA_SGS << 16) | ((pci_id << 8) & 0x0000ff00) |
461                                 ((pci_id >> 8) & 0x000000ff);
462                 }
463         }
464
465         return pci_id;
466 }
467
468 #ifdef XSERVER_LIBPCIACCESS
469
470 static Bool NVPciProbe (        DriverPtr               drv,
471                                 int                     entity_num,
472                                 struct pci_device       *dev,
473                                 intptr_t                match_data      )
474 {
475         ScrnInfoPtr pScrn = NULL;
476
477         volatile uint32_t *regs = NULL;
478
479         /* Temporary mapping to discover the architecture */
480         pci_device_map_range(dev, PCI_DEV_MEM_BASE(dev, 0), 0x90000, 0,
481                              (void *) &regs);
482
483         uint8_t architecture = NVGetArchitecture(regs);
484
485         CARD32 pci_id = NVGetPCIID(regs);
486
487         pci_device_unmap_range(dev, (void *) regs, 0x90000);
488
489         /* Currently NV04 up to NV83 is supported */
490         /* For safety the fictional NV8F is used */
491         if (architecture >= 0x04 && architecture <= 0x8F) {
492
493                 /* At this stage the pci_id should be ok, so we generate this
494                  * to avoid list duplication */
495                 /* AGP bridge chips need their bridge chip id to be detected */
496                 PciChipsets NVChipsets[] = {
497                         { pci_id, PCI_DEV_PCI_ID(dev), RES_SHARED_VGA },
498                         { -1, -1, RES_UNDEFINED }
499                 };
500
501                 pScrn = xf86ConfigPciEntity(pScrn, 0, entity_num, NVChipsets, 
502                                                 NULL, NULL, NULL, NULL, NULL);
503
504                 if (pScrn != NULL) {
505                         pScrn->driverVersion    = NV_VERSION;
506                         pScrn->driverName       = NV_DRIVER_NAME;
507                         pScrn->name             = NV_NAME;
508
509                         pScrn->Probe            = NULL;
510                         pScrn->PreInit          = NVPreInit;
511                         pScrn->ScreenInit       = NVScreenInit;
512                         pScrn->SwitchMode       = NVSwitchMode;
513                         pScrn->AdjustFrame      = NVAdjustFrame;
514                         pScrn->EnterVT          = NVEnterVT;
515                         pScrn->LeaveVT          = NVLeaveVT;
516                         pScrn->FreeScreen       = NVFreeScreen;
517                         pScrn->ValidMode        = NVValidMode;
518
519                         return TRUE;
520                 }
521         }
522
523         return FALSE;
524 }
525
526 #endif /* XSERVER_LIBPCIACCESS */
527
528 #define MAX_CHIPS MAXSCREENS
529
530 #ifndef XSERVER_LIBPCIACCESS
531 /* Mandatory */
532 static Bool
533 NVProbe(DriverPtr drv, int flags)
534 {
535         int i;
536         GDevPtr *devSections;
537         int *usedChips;
538         SymTabRec NVChipsets[MAX_CHIPS + 1];
539         PciChipsets NVPciChipsets[MAX_CHIPS + 1];
540         pciVideoPtr *ppPci;
541         int numDevSections;
542         int numUsed;
543         Bool foundScreen = FALSE;
544
545         if ((numDevSections = xf86MatchDevice(NV_DRIVER_NAME, &devSections)) <= 0) 
546                 return FALSE;  /* no matching device section */
547
548         if (!(ppPci = xf86GetPciVideoInfo())) 
549                 return FALSE;  /* no PCI cards found */
550
551         numUsed = 0;
552
553         /* Create the NVChipsets and NVPciChipsets from found devices */
554         while (*ppPci && (numUsed < MAX_CHIPS)) {
555                 if (((*ppPci)->vendor == PCI_VENDOR_NVIDIA_SGS) || 
556                         ((*ppPci)->vendor == PCI_VENDOR_NVIDIA)) 
557                 {
558                         volatile CARD32 *regs;
559                         CARD32 pcicmd;
560
561                         PCI_DEV_READ_LONG(*ppPci, PCI_CMD_STAT_REG, &pcicmd);
562                         /* Enable reading memory? */
563                         PCI_DEV_WRITE_LONG(*ppPci, PCI_CMD_STAT_REG, pcicmd | PCI_CMD_MEM_ENABLE);
564
565                         regs = xf86MapPciMem(-1, VIDMEM_MMIO, PCI_DEV_TAG(*ppPci), PCI_DEV_MEM_BASE(*ppPci, 0), 0x90000);
566                         int pciid = NVGetPCIID(regs);
567
568                         int architecture = NVGetArchitecture(regs);
569                         char name[25];
570                         sprintf(name, "NVIDIA NV%02X", architecture);
571                         /* NV04 upto NV83 is supported, NV8F is fictive limit */
572                         if (architecture >= 0x04 && architecture <= 0x8F) {
573                                 NVChipsets[numUsed].token = pciid;
574                                 NVChipsets[numUsed].name = name;
575                                 NVPciChipsets[numUsed].numChipset = pciid;
576                                 /* AGP bridge chips need their bridge chip id to be detected */
577                                 NVPciChipsets[numUsed].PCIid = PCI_DEV_PCI_ID(*ppPci);
578                                 NVPciChipsets[numUsed].resList = RES_SHARED_VGA;
579                                 numUsed++;
580                         }
581                         xf86UnMapVidMem(-1, (pointer)regs, 0x90000);
582
583                         /* Reset previous state */
584                         PCI_DEV_WRITE_LONG(*ppPci, PCI_CMD_STAT_REG, pcicmd);
585                 }
586                 ppPci++;
587         }
588
589         /* terminate the list */
590         NVChipsets[numUsed].token = -1;
591         NVChipsets[numUsed].name = NULL; 
592         NVPciChipsets[numUsed].numChipset = -1;
593         NVPciChipsets[numUsed].PCIid = -1;
594         NVPciChipsets[numUsed].resList = RES_UNDEFINED;
595
596         numUsed = xf86MatchPciInstances(NV_NAME, 0, NVChipsets, NVPciChipsets,
597                                         devSections, numDevSections, drv,
598                                         &usedChips);
599
600         if (numUsed <= 0) {
601                 return FALSE;
602         }
603
604         if (flags & PROBE_DETECT) {
605                 foundScreen = TRUE;
606         } else {
607                 for (i = 0; i < numUsed; i++) {
608                         pciVideoPtr pPci;
609
610                         pPci = xf86GetPciInfoForEntity(usedChips[i]);
611                         if (NVGetScrnInfoRec(NVPciChipsets, usedChips[i])) {
612                                 foundScreen = TRUE;
613                         }
614                 }
615         }
616
617         xfree(devSections);
618         xfree(usedChips);
619
620         return foundScreen;
621 }
622 #endif /* XSERVER_LIBPCIACCESS */
623
624 Bool
625 NVSwitchMode(int scrnIndex, DisplayModePtr mode, int flags)
626 {
627         ScrnInfoPtr pScrn = xf86Screens[scrnIndex];
628         NVPtr pNv = NVPTR(pScrn);
629
630         if (pNv->randr12_enable) {
631                 /* No rotation support for the moment */
632                 return xf86SetSingleMode(pScrn, mode, RR_Rotate_0);
633         }
634
635         return NVModeInit(xf86Screens[scrnIndex], mode);
636 }
637
638 /*
639  * This function is used to initialize the Start Address - the first
640  * displayed location in the video memory.
641  */
642 /* Usually mandatory */
643 void 
644 NVAdjustFrame(int scrnIndex, int x, int y, int flags)
645 {
646         ScrnInfoPtr pScrn = xf86Screens[scrnIndex];
647         NVPtr pNv = NVPTR(pScrn);
648
649         if (pNv->randr12_enable) {
650                 xf86CrtcConfigPtr config = XF86_CRTC_CONFIG_PTR(pScrn);
651                 xf86CrtcPtr crtc = config->output[config->compat_output]->crtc;
652
653                 if (crtc && crtc->enabled) {
654                         NVCrtcSetBase(crtc, x, y, FALSE);
655                 }
656         } else {
657                 int startAddr;
658                 NVFBLayout *pLayout = &pNv->CurrentLayout;
659                 startAddr = (((y*pLayout->displayWidth)+x)*(pLayout->bitsPerPixel/8));
660                 startAddr += pNv->FB->offset;
661                 NVSetStartAddress(pNv, startAddr);
662         }
663 }
664
665 static Bool
666 NV50AcquireDisplay(ScrnInfoPtr pScrn)
667 {
668         if (!NV50DispInit(pScrn))
669                 return FALSE;
670         if (!NV50CursorAcquire(pScrn))
671                 return FALSE;
672         xf86SetDesiredModes(pScrn);
673
674         return TRUE;
675 }
676
677 static Bool
678 NV50ReleaseDisplay(ScrnInfoPtr pScrn)
679 {
680         NV50CursorRelease(pScrn);
681         NV50DispShutdown(pScrn);
682         return TRUE;
683 }
684
685 /*
686  * This is called when VT switching back to the X server.  Its job is
687  * to reinitialise the video mode.
688  *
689  * We may wish to unmap video/MMIO memory too.
690  */
691
692 /* Mandatory */
693 static Bool
694 NVEnterVT(int scrnIndex, int flags)
695 {
696         ScrnInfoPtr pScrn = xf86Screens[scrnIndex];
697         NVPtr pNv = NVPTR(pScrn);
698
699         if (pNv->randr12_enable) {
700                 xf86DrvMsg(pScrn->scrnIndex, X_INFO, "NVEnterVT is called.\n");
701                 xf86CrtcConfigPtr xf86_config = XF86_CRTC_CONFIG_PTR(pScrn);
702                 int i;
703                 pScrn->vtSema = TRUE;
704
705                 if (pNv->Architecture == NV_ARCH_50) {
706                         if (!NV50AcquireDisplay(pScrn))
707                                 return FALSE;
708                         return TRUE;
709                 }
710
711                 /* Save the current state */
712                 if (pNv->SaveGeneration != serverGeneration) {
713                         pNv->SaveGeneration = serverGeneration;
714                         NVSave(pScrn);
715                 }
716
717                 for (i = 0; i < xf86_config->num_crtc; i++) {
718                         NVCrtcLockUnlock(xf86_config->crtc[i], 0);
719                 }
720
721                 /* Reassign outputs so disabled outputs don't get stuck on the wrong crtc */
722                 for (i = 0; i < xf86_config->num_output; i++) {
723                         xf86OutputPtr output = xf86_config->output[i];
724                         NVOutputPrivatePtr nv_output = output->driver_private;
725                         if (nv_output->type == OUTPUT_TMDS || nv_output->type == OUTPUT_LVDS) {
726                                 uint8_t tmds_reg4;
727
728                                 /* Disable any crosswired tmds, to avoid picking up a signal on a disabled output */
729                                 /* Example: TMDS1 crosswired to CRTC0 (by bios) reassigned to CRTC1 in xorg, disabled. */
730                                 /* But the bios reinits it to CRTC0 when going back to VT. */
731                                 /* Because it's disabled, it doesn't get a mode set, still it picks up the signal from CRTC0 (which is another output) */
732                                 /* A legitimately crosswired output will get set properly during mode set */
733                                 if ((tmds_reg4 = NVReadTMDS(pNv, nv_output->preferred_output, 0x4)) & (1 << 3)) {
734                                         NVWriteTMDS(pNv, nv_output->preferred_output, 0x4, tmds_reg4 & ~(1 << 3));
735                                 }
736                         }
737                 }
738
739                 if (!xf86SetDesiredModes(pScrn))
740                         return FALSE;
741         } else {
742                 if (!NVModeInit(pScrn, pScrn->currentMode))
743                         return FALSE;
744
745                 NVAdjustFrame(scrnIndex, pScrn->frameX0, pScrn->frameY0, 0);
746         }
747
748         if (pNv->overlayAdaptor && pNv->Architecture != NV_ARCH_04)
749                 NV10WriteOverlayParameters(pScrn);
750         return TRUE;
751 }
752
753 /*
754  * This is called when VT switching away from the X server.  Its job is
755  * to restore the previous (text) mode.
756  *
757  * We may wish to remap video/MMIO memory too.
758  */
759
760 /* Mandatory */
761 static void
762 NVLeaveVT(int scrnIndex, int flags)
763 {
764         ScrnInfoPtr pScrn = xf86Screens[scrnIndex];
765         NVPtr pNv = NVPTR(pScrn);
766         if (pNv->randr12_enable)
767                 xf86DrvMsg(pScrn->scrnIndex, X_INFO, "NVLeaveVT is called.\n");
768
769         if (pNv->Architecture == NV_ARCH_50) {
770                 NV50ReleaseDisplay(pScrn);
771                 return;
772         }
773         NVSync(pScrn);
774         NVRestore(pScrn);
775         if (!pNv->randr12_enable)
776                 NVLockUnlock(pScrn, 1);
777 }
778
779
780
781 static void 
782 NVBlockHandler (
783         int i, 
784         pointer blockData, 
785         pointer pTimeout,
786         pointer pReadmask
787 )
788 {
789         ScreenPtr pScreen = screenInfo.screens[i];
790         ScrnInfoPtr pScrnInfo = xf86Screens[i];
791         NVPtr pNv = NVPTR(pScrnInfo);
792
793         if (!pNv->NoAccel)
794                 FIRE_RING();
795
796         pScreen->BlockHandler = pNv->BlockHandler;
797         (*pScreen->BlockHandler) (i, blockData, pTimeout, pReadmask);
798         pScreen->BlockHandler = NVBlockHandler;
799
800         if (pNv->VideoTimerCallback) 
801                 (*pNv->VideoTimerCallback)(pScrnInfo, currentTime.milliseconds);
802
803 }
804
805
806 /*
807  * This is called at the end of each server generation.  It restores the
808  * original (text) mode.  It should also unmap the video memory, and free
809  * any per-generation data allocated by the driver.  It should finish
810  * by unwrapping and calling the saved CloseScreen function.
811  */
812
813 /* Mandatory */
814 static Bool
815 NVCloseScreen(int scrnIndex, ScreenPtr pScreen)
816 {
817         ScrnInfoPtr pScrn = xf86Screens[scrnIndex];
818         NVPtr pNv = NVPTR(pScrn);
819
820         if (pScrn->vtSema) {
821                 pScrn->vtSema = FALSE;
822                 if (pNv->Architecture == NV_ARCH_50) {
823                         NV50ReleaseDisplay(pScrn);
824                 } else {
825                         if (pNv->randr12_enable)
826                                 xf86DrvMsg(pScrn->scrnIndex, X_INFO, "NVCloseScreen is called.\n");
827                         NVSync(pScrn);
828                         NVRestore(pScrn);
829                         if (!pNv->randr12_enable)
830                                 NVLockUnlock(pScrn, 1);
831                 }
832         }
833
834         NVUnmapMem(pScrn);
835         vgaHWUnmapMem(pScrn);
836         if (pNv->CursorInfoRec)
837                 xf86DestroyCursorInfoRec(pNv->CursorInfoRec);
838         if (pNv->ShadowPtr)
839                 xfree(pNv->ShadowPtr);
840         if (pNv->overlayAdaptor)
841                 xfree(pNv->overlayAdaptor);
842         if (pNv->blitAdaptor)
843                 xfree(pNv->blitAdaptor);
844
845         pScrn->vtSema = FALSE;
846         pScreen->CloseScreen = pNv->CloseScreen;
847         pScreen->BlockHandler = pNv->BlockHandler;
848         return (*pScreen->CloseScreen)(scrnIndex, pScreen);
849 }
850
851 /* Free up any persistent data structures */
852
853 /* Optional */
854 static void
855 NVFreeScreen(int scrnIndex, int flags)
856 {
857     /*
858      * This only gets called when a screen is being deleted.  It does not
859      * get called routinely at the end of a server generation.
860      */
861     if (xf86LoaderCheckSymbol("vgaHWFreeHWRec"))
862         vgaHWFreeHWRec(xf86Screens[scrnIndex]);
863     NVFreeRec(xf86Screens[scrnIndex]);
864 }
865
866
867 /* Checks if a mode is suitable for the selected chipset. */
868
869 /* Optional */
870 static ModeStatus
871 NVValidMode(int scrnIndex, DisplayModePtr mode, Bool verbose, int flags)
872 {
873     NVPtr pNv = NVPTR(xf86Screens[scrnIndex]);
874
875     if(pNv->fpWidth && pNv->fpHeight)
876       if((pNv->fpWidth < mode->HDisplay) || (pNv->fpHeight < mode->VDisplay))
877         return (MODE_PANEL);
878
879     return (MODE_OK);
880 }
881
882 Bool NVI2CInit(ScrnInfoPtr pScrn)
883 {
884         NVPtr pNv = NVPTR(pScrn);
885
886         if (xf86LoadSubModule(pScrn, "i2c") && xf86LoadSubModule(pScrn, "ddc")) {
887                 xf86LoaderReqSymLists(i2cSymbols,NULL);
888                 xf86LoaderReqSymLists(ddcSymbols, NULL);
889
890                 /* randr-1.2 clients have their DDCs initialized elsewhere */
891                 if (!pNv->randr12_enable)
892                         return NVDACi2cInit(pScrn);
893                 return true;
894         } else
895                 xf86DrvMsg(pScrn->scrnIndex, X_WARNING,
896                 "Couldn't load i2c and ddc modules.  DDC probing can't be done\n");
897         return false;
898 }
899
900 static Bool NVPreInitDRI(ScrnInfoPtr pScrn)
901 {
902         NVPtr pNv = NVPTR(pScrn);
903
904         if (!NVDRIGetVersion(pScrn))
905                 return FALSE;
906
907         xf86DrvMsg(pScrn->scrnIndex, X_INFO,
908                 "[dri] Found DRI library version %d.%d.%d and kernel"
909                 " module version %d.%d.%d\n",
910                 pNv->pLibDRMVersion->version_major,
911                 pNv->pLibDRMVersion->version_minor,
912                 pNv->pLibDRMVersion->version_patchlevel,
913                 pNv->pKernelDRMVersion->version_major,
914                 pNv->pKernelDRMVersion->version_minor,
915                 pNv->pKernelDRMVersion->version_patchlevel);
916
917         return TRUE;
918 }
919
920 static Bool
921 nv_xf86crtc_resize(ScrnInfoPtr pScrn, int width, int height)
922 {
923         xf86DrvMsg(pScrn->scrnIndex, X_INFO, "nv_xf86crtc_resize is called with %dx%d resolution.\n", width, height);
924         pScrn->virtualX = width;
925         pScrn->virtualY = height;
926         return TRUE;
927 }
928
929 static const xf86CrtcConfigFuncsRec nv_xf86crtc_config_funcs = {
930         nv_xf86crtc_resize
931 };
932
933 /* This is taken from the haiku driver */
934 /* We must accept crtc pitch constrains */
935 /* A hardware bug on some hardware requires twice the pitch */
936 static CARD8 NVGetCRTCMask(ScrnInfoPtr pScrn, CARD8 bpp)
937 {
938         CARD8 mask = 0;
939         switch(bpp) {
940                 case 8:
941                         mask = 0xf; /* 0x7 */
942                         break;
943                 case 15:
944                         mask = 0x7; /* 0x3 */
945                         break;
946                 case 16:
947                         mask = 0x7; /* 0x3 */
948                         break;
949                 case 24:
950                         mask = 0xf; /* 0x7 */
951                         break;
952                 case 32:
953                         mask = 0x3; /* 0x1 */
954                         break;
955                 default:
956                         xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Unkown color format.\n");
957                         break;
958         }
959
960         return mask;
961 }
962
963 /* This is taken from the haiku driver */
964 static CARD8 NVGetAccelerationMask(ScrnInfoPtr pScrn, CARD8 bpp)
965 {
966         NVPtr pNv = NVPTR(pScrn);
967         CARD8 mask = 0;
968         /* Identical for NV04 */
969         if (pNv->Architecture == NV_ARCH_04) {
970                 return NVGetCRTCMask(pScrn, bpp);
971         } else {
972                 switch(bpp) {
973                         case 8:
974                                 mask = 0x3f;
975                                 break;
976                         case 15:
977                                 mask = 0x1f;
978                                 break;
979                         case 16:
980                                 mask = 0x1f;
981                                 break;
982                         case 24:
983                                 mask = 0x3f;
984                                 break;
985                         case 32:
986                                 mask = 0x0f;
987                                 break;
988                         default:
989                                 xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Unkown color format.\n");
990                                 break;
991                 }
992         }
993
994         return mask;
995 }
996
997 static CARD32 NVGetVideoPitch(ScrnInfoPtr pScrn, CARD8 bpp)
998 {
999         NVPtr pNv = NVPTR(pScrn);
1000         CARD8 crtc_mask, accel_mask = 0;
1001         crtc_mask = NVGetCRTCMask(pScrn, bpp);
1002         if (!pNv->NoAccel) {
1003                 accel_mask = NVGetAccelerationMask(pScrn, bpp);
1004         }
1005
1006         /* adhere to the largest granularity imposed */
1007         if (accel_mask > crtc_mask) {
1008                 return (pScrn->virtualX + accel_mask) & ~accel_mask;
1009         } else {
1010                 return (pScrn->virtualX + crtc_mask) & ~crtc_mask;
1011         }
1012 }
1013
1014 #define NVPreInitFail(fmt, args...) do {                                    \
1015         xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "%d: "fmt, __LINE__, ##args); \
1016         if (pNv->pInt10)                                                    \
1017                 xf86FreeInt10(pNv->pInt10);                                 \
1018         NVFreeRec(pScrn);                                                   \
1019         return FALSE;                                                       \
1020 } while(0)
1021
1022 /* Mandatory */
1023 Bool
1024 NVPreInit(ScrnInfoPtr pScrn, int flags)
1025 {
1026         xf86CrtcConfigPtr xf86_config;
1027         NVPtr pNv;
1028         MessageType from;
1029         int i, max_width, max_height;
1030         ClockRangePtr clockRanges;
1031         const char *s;
1032         int config_mon_rates = FALSE;
1033         int num_crtc;
1034
1035         if (flags & PROBE_DETECT) {
1036                 EntityInfoPtr pEnt = xf86GetEntityInfo(pScrn->entityList[0]);
1037
1038                 if (!pEnt)
1039                         return FALSE;
1040
1041                 i = pEnt->index;
1042                 xfree(pEnt);
1043
1044                 if (xf86LoadSubModule(pScrn, "vbe")) {
1045                         vbeInfoPtr pVbe = VBEInit(NULL, i);
1046                         ConfiguredMonitor = vbeDoEDID(pVbe, NULL);
1047                         vbeFree(pVbe);
1048                 }
1049
1050                 return TRUE;
1051         }
1052
1053         /*
1054          * Note: This function is only called once at server startup, and
1055          * not at the start of each server generation.  This means that
1056          * only things that are persistent across server generations can
1057          * be initialised here.  xf86Screens[] is (pScrn is a pointer to one
1058          * of these).  Privates allocated using xf86AllocateScrnInfoPrivateIndex()  
1059          * are too, and should be used for data that must persist across
1060          * server generations.
1061          *
1062          * Per-generation data should be allocated with
1063          * AllocateScreenPrivateIndex() from the ScreenInit() function.
1064          */
1065
1066         /* Check the number of entities, and fail if it isn't one. */
1067         if (pScrn->numEntities != 1)
1068                 return FALSE;
1069
1070         /* Allocate the NVRec driverPrivate */
1071         if (!NVGetRec(pScrn)) {
1072                 return FALSE;
1073         }
1074         pNv = NVPTR(pScrn);
1075
1076         /* Get the entity, and make sure it is PCI. */
1077         pNv->pEnt = xf86GetEntityInfo(pScrn->entityList[0]);
1078         if (pNv->pEnt->location.type != BUS_PCI)
1079                 return FALSE;
1080  
1081         /* Find the PCI info for this screen */
1082         pNv->PciInfo = xf86GetPciInfoForEntity(pNv->pEnt->index);
1083 #ifndef XSERVER_LIBPCIACCESS
1084         pNv->PciTag = pciTag(pNv->PciInfo->bus, pNv->PciInfo->device,
1085                                 pNv->PciInfo->func);
1086 #endif /* XSERVER_LIBPCIACCESS */
1087
1088         pNv->Primary = xf86IsPrimaryPci(pNv->PciInfo);
1089
1090         /* Initialize the card through int10 interface if needed */
1091         if (xf86LoadSubModule(pScrn, "int10")) {
1092                 xf86LoaderReqSymLists(int10Symbols, NULL);
1093 #if !defined(__alpha__) && !defined(__powerpc__)
1094                 xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Initializing int10\n");
1095                 pNv->pInt10 = xf86InitInt10(pNv->pEnt->index);
1096 #endif
1097         }
1098
1099         xf86SetOperatingState(resVgaIo, pNv->pEnt->index, ResUnusedOpr);
1100         xf86SetOperatingState(resVgaMem, pNv->pEnt->index, ResDisableOpr);
1101
1102         /* Set pScrn->monitor */
1103         pScrn->monitor = pScrn->confScreen->monitor;
1104
1105         volatile uint32_t *regs = NULL;
1106 #ifdef XSERVER_LIBPCIACCESS
1107         pci_device_map_range(pNv->PciInfo, PCI_DEV_MEM_BASE(pNv->PciInfo, 0),
1108                              0x90000, 0, (void *)&regs);
1109         pNv->Chipset = NVGetPCIID(regs) & 0xffff;
1110         pNv->NVArch = NVGetArchitecture(regs);
1111         pci_device_unmap_range(pNv->PciInfo, (void *) regs, 0x90000);
1112 #else
1113         CARD32 pcicmd;
1114         PCI_DEV_READ_LONG(pNv->PciInfo, PCI_CMD_STAT_REG, &pcicmd);
1115         /* Enable reading memory? */
1116         PCI_DEV_WRITE_LONG(pNv->PciInfo, PCI_CMD_STAT_REG, pcicmd | PCI_CMD_MEM_ENABLE);
1117         regs = xf86MapPciMem(-1, VIDMEM_MMIO, pNv->PciTag, PCI_DEV_MEM_BASE(pNv->PciInfo, 0), 0x90000);
1118         pNv->Chipset = NVGetPCIID(regs) & 0xffff;
1119         pNv->NVArch = NVGetArchitecture(regs);
1120         xf86UnMapVidMem(-1, (pointer)regs, 0x90000);
1121         /* Reset previous state */
1122         PCI_DEV_WRITE_LONG(pNv->PciInfo, PCI_CMD_STAT_REG, pcicmd);
1123 #endif /* XSERVER_LIBPCIACCESS */
1124
1125         pScrn->chipset = malloc(sizeof(char) * 25);
1126         sprintf(pScrn->chipset, "NVIDIA NV%02X", pNv->NVArch);
1127
1128         if(!pScrn->chipset) {
1129                 pScrn->chipset = "Unknown NVIDIA";
1130         }
1131
1132         /*
1133         * This shouldn't happen because such problems should be caught in
1134         * NVProbe(), but check it just in case.
1135         */
1136         if (pScrn->chipset == NULL)
1137                 NVPreInitFail("ChipID 0x%04X is not recognised\n", pNv->Chipset);
1138
1139         if (pNv->NVArch < 0x04)
1140                 NVPreInitFail("Chipset \"%s\" is not recognised\n", pScrn->chipset);
1141
1142         xf86DrvMsg(pScrn->scrnIndex, X_PROBED, "Chipset: \"%s\"\n", pScrn->chipset);
1143
1144         /* The highest architecture currently supported is NV5x */
1145         if (pNv->NVArch >= 0x80) {
1146                 pNv->Architecture =  NV_ARCH_50;
1147         } else if (pNv->NVArch >= 0x60) {
1148                 pNv->Architecture =  NV_ARCH_40;
1149         } else if (pNv->NVArch >= 0x50) {
1150                 pNv->Architecture =  NV_ARCH_50;
1151         } else if (pNv->NVArch >= 0x40) {
1152                 pNv->Architecture =  NV_ARCH_40;
1153         } else if (pNv->NVArch >= 0x30) {
1154                 pNv->Architecture = NV_ARCH_30;
1155         } else if (pNv->NVArch >= 0x20) {
1156                 pNv->Architecture = NV_ARCH_20;
1157         } else if (pNv->NVArch >= 0x10) {
1158                 pNv->Architecture = NV_ARCH_10;
1159         } else if (pNv->NVArch >= 0x04) {
1160                 pNv->Architecture = NV_ARCH_04;
1161         /*  The lowest architecture currently supported is NV04 */
1162         } else {
1163                 return FALSE;
1164         }
1165
1166         /*
1167          * The first thing we should figure out is the depth, bpp, etc.
1168          */
1169
1170         if (!xf86SetDepthBpp(pScrn, 0, 0, 0, Support32bppFb)) {
1171                 NVPreInitFail("\n");
1172         } else {
1173                 /* Check that the returned depth is one we support */
1174                 switch (pScrn->depth) {
1175                         case 8:
1176                         case 15:
1177                         case 16:
1178                         case 24:
1179                                 /* OK */
1180                                 break;
1181                         default:
1182                                 NVPreInitFail("Given depth (%d) is not supported by this driver\n",
1183                                         pScrn->depth);
1184                 }
1185         }
1186         xf86PrintDepthBpp(pScrn);
1187
1188         /*
1189          * This must happen after pScrn->display has been set because
1190          * xf86SetWeight references it.
1191          */
1192         if (pScrn->depth > 8) {
1193                 /* The defaults are OK for us */
1194                 rgb zeros = {0, 0, 0};
1195
1196                 if (!xf86SetWeight(pScrn, zeros, zeros)) {
1197                         NVPreInitFail("\n");
1198                 }
1199         }
1200
1201         if (!xf86SetDefaultVisual(pScrn, -1)) {
1202                 NVPreInitFail("\n");
1203         } else {
1204                 /* We don't currently support DirectColor at > 8bpp */
1205                 if (pScrn->depth > 8 && (pScrn->defaultVisual != TrueColor)) {
1206                         NVPreInitFail("Given default visual"
1207                                 " (%s) is not supported at depth %d\n",
1208                                 xf86GetVisualName(pScrn->defaultVisual), pScrn->depth);
1209                 }
1210         }
1211
1212         /* The vgahw module should be loaded here when needed */
1213         if (!xf86LoadSubModule(pScrn, "vgahw")) {
1214                 NVPreInitFail("\n");
1215         }
1216
1217         xf86LoaderReqSymLists(vgahwSymbols, NULL);
1218
1219         /*
1220          * Allocate a vgaHWRec
1221          */
1222         if (!vgaHWGetHWRec(pScrn)) {
1223                 NVPreInitFail("\n");
1224         }
1225
1226         /* We use a programmable clock */
1227         pScrn->progClock = TRUE;
1228
1229         /* Collect all of the relevant option flags (fill in pScrn->options) */
1230         xf86CollectOptions(pScrn, NULL);
1231
1232         /* Process the options */
1233         if (!(pNv->Options = xalloc(sizeof(NVOptions))))
1234                 return FALSE;
1235         memcpy(pNv->Options, NVOptions, sizeof(NVOptions));
1236         xf86ProcessOptions(pScrn->scrnIndex, pScrn->options, pNv->Options);
1237
1238         /* Set the bits per RGB for 8bpp mode */
1239         if (pScrn->depth == 8)
1240                 pScrn->rgbBits = 8;
1241
1242         from = X_DEFAULT;
1243
1244         if (pNv->Architecture == NV_ARCH_50) {
1245                 pNv->randr12_enable = TRUE;
1246         } else {
1247                 pNv->randr12_enable = FALSE;
1248                 if (xf86ReturnOptValBool(pNv->Options, OPTION_RANDR12, FALSE)) {
1249                         pNv->randr12_enable = TRUE;
1250                 }
1251         }
1252         xf86DrvMsg(pScrn->scrnIndex, from, "Randr1.2 support %sabled\n", pNv->randr12_enable ? "en" : "dis");
1253
1254         pNv->new_restore = FALSE;
1255
1256         if (pNv->randr12_enable) {
1257                 if (xf86ReturnOptValBool(pNv->Options, OPTION_NEW_RESTORE, FALSE)) {
1258                         pNv->new_restore = TRUE;
1259                 }
1260                 xf86DrvMsg(pScrn->scrnIndex, from, "New (experimental) restore support %sabled\n", pNv->new_restore ? "en" : "dis");
1261         }
1262
1263         pNv->HWCursor = TRUE;
1264         /*
1265          * The preferred method is to use the "hw cursor" option as a tri-state
1266          * option, with the default set above.
1267          */
1268         if (xf86GetOptValBool(pNv->Options, OPTION_HW_CURSOR, &pNv->HWCursor)) {
1269                 from = X_CONFIG;
1270         }
1271         /* For compatibility, accept this too (as an override) */
1272         if (xf86ReturnOptValBool(pNv->Options, OPTION_SW_CURSOR, FALSE)) {
1273                 from = X_CONFIG;
1274                 pNv->HWCursor = FALSE;
1275         }
1276         xf86DrvMsg(pScrn->scrnIndex, from, "Using %s cursor\n",
1277                 pNv->HWCursor ? "HW" : "SW");
1278
1279         pNv->FpScale = TRUE;
1280
1281         if (xf86GetOptValBool(pNv->Options, OPTION_FP_SCALE, &pNv->FpScale)) {
1282                 xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, "Flat panel scaling %s\n",
1283                         pNv->FpScale ? "on" : "off");
1284         }
1285         if (xf86ReturnOptValBool(pNv->Options, OPTION_NOACCEL, FALSE)) {
1286                 pNv->NoAccel = TRUE;
1287                 xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, "Acceleration disabled\n");
1288         }
1289         if (xf86ReturnOptValBool(pNv->Options, OPTION_SHADOW_FB, FALSE)) {
1290                 pNv->ShadowFB = TRUE;
1291                 pNv->NoAccel = TRUE;
1292                 xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, 
1293                         "Using \"Shadow Framebuffer\" - acceleration disabled\n");
1294         }
1295
1296         pNv->Rotate = 0;
1297         pNv->RandRRotation = FALSE;
1298         /*
1299          * Rotation with a randr-1.2 driver happens at a different level, so ignore these options.
1300          */
1301         if ((s = xf86GetOptValString(pNv->Options, OPTION_ROTATE)) && !pNv->randr12_enable) {
1302                 if(!xf86NameCmp(s, "CW")) {
1303                         pNv->ShadowFB = TRUE;
1304                         pNv->NoAccel = TRUE;
1305                         pNv->HWCursor = FALSE;
1306                         pNv->Rotate = 1;
1307                         xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, 
1308                                 "Rotating screen clockwise - acceleration disabled\n");
1309                 } else if(!xf86NameCmp(s, "CCW")) {
1310                         pNv->ShadowFB = TRUE;
1311                         pNv->NoAccel = TRUE;
1312                         pNv->HWCursor = FALSE;
1313                         pNv->Rotate = -1;
1314                         xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, 
1315                                 "Rotating screen counter clockwise - acceleration disabled\n");
1316                 } else if(!xf86NameCmp(s, "RandR")) {
1317                         pNv->ShadowFB = TRUE;
1318                         pNv->NoAccel = TRUE;
1319                         pNv->HWCursor = FALSE;
1320                         pNv->RandRRotation = TRUE;
1321                         xf86DrvMsg(pScrn->scrnIndex, X_CONFIG,
1322                                 "Using RandR rotation - acceleration disabled\n");
1323                 } else {
1324                         xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, 
1325                                 "\"%s\" is not a valid value for Option \"Rotate\"\n", s);
1326                         xf86DrvMsg(pScrn->scrnIndex, X_INFO, 
1327                                 "Valid options are \"CW\", \"CCW\", and \"RandR\"\n");
1328                 }
1329         }
1330
1331         if(xf86GetOptValInteger(pNv->Options, OPTION_VIDEO_KEY, &(pNv->videoKey))) {
1332                 xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, "video key set to 0x%x\n",
1333                                         pNv->videoKey);
1334         } else {
1335                 pNv->videoKey =  (1 << pScrn->offset.red) | 
1336                                         (1 << pScrn->offset.green) |
1337                 (((pScrn->mask.blue >> pScrn->offset.blue) - 1) << pScrn->offset.blue);
1338         }
1339
1340         /* Things happen on a per output basis for a randr-1.2 driver. */
1341         if (xf86GetOptValBool(pNv->Options, OPTION_FLAT_PANEL, &(pNv->FlatPanel)) && !pNv->randr12_enable) {
1342                 xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, "forcing %s usage\n",
1343                         pNv->FlatPanel ? "DFP" : "CRTC");
1344         } else {
1345                 pNv->FlatPanel = -1; /* autodetect later */
1346         }
1347
1348         pNv->FPDither = FALSE;
1349         if (xf86GetOptValBool(pNv->Options, OPTION_FP_DITHER, &(pNv->FPDither))) 
1350                 xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, "enabling flat panel dither\n");
1351
1352         if (xf86GetOptValInteger(pNv->Options, OPTION_FP_TWEAK, 
1353                                                 &pNv->PanelTweak)) {
1354                 pNv->usePanelTweak = TRUE;
1355         } else {
1356                 pNv->usePanelTweak = FALSE;
1357         }
1358
1359         if (pNv->pEnt->device->MemBase != 0) {
1360                 /* Require that the config file value matches one of the PCI values. */
1361                 if (!xf86CheckPciMemBase(pNv->PciInfo, pNv->pEnt->device->MemBase)) {
1362                         NVPreInitFail(
1363                                 "MemBase 0x%08lX doesn't match any PCI base register.\n",
1364                                 pNv->pEnt->device->MemBase);
1365                 }
1366                 pNv->VRAMPhysical = pNv->pEnt->device->MemBase;
1367                 from = X_CONFIG;
1368         } else {
1369                 if (PCI_DEV_MEM_BASE(pNv->PciInfo, 1) != 0) {
1370                         pNv->VRAMPhysical = PCI_DEV_MEM_BASE(pNv->PciInfo, 1) & 0xff800000;
1371                         from = X_PROBED;
1372                 } else {
1373                         NVPreInitFail("No valid FB address in PCI config space\n");
1374                         return FALSE;
1375                 }
1376         }
1377         xf86DrvMsg(pScrn->scrnIndex, from, "Linear framebuffer at 0x%lX\n",
1378                 (unsigned long)pNv->VRAMPhysical);
1379
1380         if (pNv->pEnt->device->IOBase != 0) {
1381                 /* Require that the config file value matches one of the PCI values. */
1382                 if (!xf86CheckPciMemBase(pNv->PciInfo, pNv->pEnt->device->IOBase)) {
1383                         NVPreInitFail("IOBase 0x%08lX doesn't match any PCI base register.\n",
1384                                 pNv->pEnt->device->IOBase);
1385                 }
1386                 pNv->IOAddress = pNv->pEnt->device->IOBase;
1387                 from = X_CONFIG;
1388         } else {
1389                 if (PCI_DEV_MEM_BASE(pNv->PciInfo, 0) != 0) {
1390                         pNv->IOAddress = PCI_DEV_MEM_BASE(pNv->PciInfo, 0) & 0xffffc000;
1391                         from = X_PROBED;
1392                 } else {
1393                         NVPreInitFail("No valid MMIO address in PCI config space\n");
1394                 }
1395         }
1396         xf86DrvMsg(pScrn->scrnIndex, from, "MMIO registers at 0x%lX\n",
1397                 (unsigned long)pNv->IOAddress);
1398
1399         if (xf86RegisterResources(pNv->pEnt->index, NULL, ResExclusive)) {
1400                 NVPreInitFail("xf86RegisterResources() found resource conflicts\n");
1401         }
1402
1403         pNv->alphaCursor = (pNv->NVArch >= 0x11);
1404
1405         if(pNv->Architecture < NV_ARCH_10) {
1406                 max_width = (pScrn->bitsPerPixel > 16) ? 2032 : 2048;
1407                 max_height = 2048;
1408         } else {
1409                 max_width = (pScrn->bitsPerPixel > 16) ? 4080 : 4096;
1410                 max_height = 4096;
1411         }
1412
1413         if (pNv->randr12_enable) {
1414                 /* Allocate an xf86CrtcConfig */
1415                 xf86CrtcConfigInit(pScrn, &nv_xf86crtc_config_funcs);
1416                 xf86_config = XF86_CRTC_CONFIG_PTR(pScrn);
1417
1418                 xf86CrtcSetSizeRange(pScrn, 320, 200, max_width, max_height);
1419         }
1420
1421         if (NVPreInitDRI(pScrn) == FALSE) {
1422                 NVPreInitFail("\n");
1423         }
1424
1425         if (!pNv->randr12_enable) {
1426                 if ((pScrn->monitor->nHsync == 0) && 
1427                         (pScrn->monitor->nVrefresh == 0)) {
1428
1429                         config_mon_rates = FALSE;
1430                 } else {
1431                         config_mon_rates = TRUE;
1432                 }
1433         }
1434
1435         NVCommonSetup(pScrn);
1436
1437         if (pNv->randr12_enable) {
1438                 if (pNv->Architecture < NV_ARCH_50) {
1439                         NVI2CInit(pScrn);
1440
1441                         num_crtc = pNv->twoHeads ? 2 : 1;
1442                         for (i = 0; i < num_crtc; i++) {
1443                                 nv_crtc_init(pScrn, i);
1444                         }
1445
1446                         NvSetupOutputs(pScrn);
1447                 } else {
1448                         if (!NV50DispPreInit(pScrn))
1449                                 NVPreInitFail("\n");
1450                         if (!NV50CreateOutputs(pScrn))
1451                                 NVPreInitFail("\n");
1452                         NV50DispCreateCrtcs(pScrn);
1453                 }
1454
1455                 if (!xf86InitialConfiguration(pScrn, FALSE))
1456                         NVPreInitFail("No valid modes.\n");
1457         }
1458
1459         pScrn->videoRam = pNv->RamAmountKBytes;
1460         xf86DrvMsg(pScrn->scrnIndex, X_PROBED, "VideoRAM: %d kBytes\n",
1461                 pScrn->videoRam);
1462
1463         pNv->VRAMPhysicalSize = pScrn->videoRam * 1024;
1464
1465         /*
1466          * If the driver can do gamma correction, it should call xf86SetGamma()
1467          * here.
1468          */
1469
1470         {
1471                 Gamma zeros = {0.0, 0.0, 0.0};
1472
1473                 if (!xf86SetGamma(pScrn, zeros)) {
1474                         NVPreInitFail("\n");
1475                 }
1476         }
1477
1478         /*
1479          * Setup the ClockRanges, which describe what clock ranges are available,
1480          * and what sort of modes they can be used for.
1481          */
1482
1483         clockRanges = xnfcalloc(sizeof(ClockRange), 1);
1484         clockRanges->next = NULL;
1485         clockRanges->minClock = pNv->MinVClockFreqKHz;
1486         clockRanges->maxClock = pNv->MaxVClockFreqKHz;
1487         clockRanges->clockIndex = -1;           /* programmable */
1488         clockRanges->doubleScanAllowed = TRUE;
1489         if ((pNv->Architecture == NV_ARCH_20) ||
1490                 ((pNv->Architecture == NV_ARCH_10) && 
1491                 ((pNv->Chipset & 0x0ff0) != CHIPSET_NV10) &&
1492                 ((pNv->Chipset & 0x0ff0) != CHIPSET_NV15))) {
1493                 /* HW is broken */
1494                 clockRanges->interlaceAllowed = FALSE;
1495         } else {
1496                 clockRanges->interlaceAllowed = TRUE;
1497         }
1498
1499         if(pNv->FlatPanel == 1) {
1500                 clockRanges->interlaceAllowed = FALSE;
1501                 clockRanges->doubleScanAllowed = FALSE;
1502         }
1503
1504 #ifdef M_T_DRIVER
1505         /* If DFP, add a modeline corresponding to its panel size */
1506         if (pNv->FlatPanel && !pNv->Television && pNv->fpWidth && pNv->fpHeight) {
1507                 DisplayModePtr Mode;
1508
1509                 Mode = xnfcalloc(1, sizeof(DisplayModeRec));
1510                 Mode = xf86CVTMode(pNv->fpWidth, pNv->fpHeight, 60.00, TRUE, FALSE);
1511                 Mode->type = M_T_DRIVER;
1512                 pScrn->monitor->Modes = xf86ModesAdd(pScrn->monitor->Modes, Mode);
1513
1514                 if (!config_mon_rates) {
1515                         if (!Mode->HSync)
1516                                 Mode->HSync = ((float) Mode->Clock ) / ((float) Mode->HTotal);
1517                         if (!Mode->VRefresh)
1518                                 Mode->VRefresh = (1000.0 * ((float) Mode->Clock)) /
1519                                                         ((float) (Mode->HTotal * Mode->VTotal));
1520
1521                         if (Mode->HSync < pScrn->monitor->hsync[0].lo)
1522                                 pScrn->monitor->hsync[0].lo = Mode->HSync;
1523                         if (Mode->HSync > pScrn->monitor->hsync[0].hi)
1524                                 pScrn->monitor->hsync[0].hi = Mode->HSync;
1525                         if (Mode->VRefresh < pScrn->monitor->vrefresh[0].lo)
1526                                 pScrn->monitor->vrefresh[0].lo = Mode->VRefresh;
1527                         if (Mode->VRefresh > pScrn->monitor->vrefresh[0].hi)
1528                                 pScrn->monitor->vrefresh[0].hi = Mode->VRefresh;
1529
1530                         pScrn->monitor->nHsync = 1;
1531                         pScrn->monitor->nVrefresh = 1;
1532                 }
1533         }
1534 #endif
1535
1536         if (pNv->randr12_enable) {
1537                 pScrn->displayWidth = NVGetVideoPitch(pScrn, pScrn->depth);
1538         } else {
1539                 /*
1540                  * xf86ValidateModes will check that the mode HTotal and VTotal values
1541                  * don't exceed the chipset's limit if pScrn->maxHValue and
1542                  * pScrn->maxVValue are set.  Since our NVValidMode() already takes
1543                  * care of this, we don't worry about setting them here.
1544                  */
1545                 i = xf86ValidateModes(pScrn, pScrn->monitor->Modes,
1546                                         pScrn->display->modes, clockRanges,
1547                                         NULL, 256, max_width,
1548                                         512, 128, max_height,
1549                                         pScrn->display->virtualX,
1550                                         pScrn->display->virtualY,
1551                                         pNv->VRAMPhysicalSize / 2,
1552                                         LOOKUP_BEST_REFRESH);
1553
1554                 if (i == -1) {
1555                         NVPreInitFail("\n");
1556                 }
1557
1558                 /* Prune the modes marked as invalid */
1559                 xf86PruneDriverModes(pScrn);
1560
1561                 /*
1562                  * Set the CRTC parameters for all of the modes based on the type
1563                  * of mode, and the chipset's interlace requirements.
1564                  *
1565                  * Calling this is required if the mode->Crtc* values are used by the
1566                  * driver and if the driver doesn't provide code to set them.  They
1567                  * are not pre-initialised at all.
1568                  */
1569                 xf86SetCrtcForModes(pScrn, 0);
1570         }
1571
1572         if (pScrn->modes == NULL) {
1573                 NVPreInitFail("No valid modes found\n");
1574         }
1575
1576         /* Set the current mode to the first in the list */
1577         pScrn->currentMode = pScrn->modes;
1578
1579         /* Print the list of modes being used */
1580         xf86PrintModes(pScrn);
1581
1582         /* Set display resolution */
1583         xf86SetDpi(pScrn, 0, 0);
1584
1585
1586         /*
1587          * XXX This should be taken into account in some way in the mode valdation
1588          * section.
1589          */
1590
1591         if (xf86LoadSubModule(pScrn, "fb") == NULL) {
1592                 NVPreInitFail("\n");
1593         }
1594
1595         xf86LoaderReqSymLists(fbSymbols, NULL);
1596
1597         /* Load EXA if needed */
1598         if (!pNv->NoAccel) {
1599                 if (!xf86LoadSubModule(pScrn, "exa")) {
1600                         NVPreInitFail("\n");
1601                 }
1602                 xf86LoaderReqSymLists(exaSymbols, NULL);
1603         }
1604
1605         /* Load ramdac if needed */
1606         if (pNv->HWCursor) {
1607                 if (!xf86LoadSubModule(pScrn, "ramdac")) {
1608                         NVPreInitFail("\n");
1609                 }
1610                 xf86LoaderReqSymLists(ramdacSymbols, NULL);
1611         }
1612
1613         /* Load shadowfb if needed */
1614         if (pNv->ShadowFB) {
1615                 if (!xf86LoadSubModule(pScrn, "shadowfb")) {
1616                         NVPreInitFail("\n");
1617                 }
1618                 xf86LoaderReqSymLists(shadowSymbols, NULL);
1619         }
1620
1621         pNv->CurrentLayout.bitsPerPixel = pScrn->bitsPerPixel;
1622         pNv->CurrentLayout.depth = pScrn->depth;
1623         pNv->CurrentLayout.displayWidth = pScrn->displayWidth;
1624         pNv->CurrentLayout.weight.red = pScrn->weight.red;
1625         pNv->CurrentLayout.weight.green = pScrn->weight.green;
1626         pNv->CurrentLayout.weight.blue = pScrn->weight.blue;
1627         pNv->CurrentLayout.mode = pScrn->currentMode;
1628
1629         xf86FreeInt10(pNv->pInt10);
1630
1631         pNv->pInt10 = NULL;
1632         return TRUE;
1633 }
1634
1635
1636 /*
1637  * Map the framebuffer and MMIO memory.
1638  */
1639
1640 static Bool
1641 NVMapMem(ScrnInfoPtr pScrn)
1642 {
1643         NVPtr pNv = NVPTR(pScrn);
1644         int gart_scratch_size;
1645         uint64_t res;
1646
1647         nouveau_device_get_param(pNv->dev, NOUVEAU_GETPARAM_FB_SIZE, &res);
1648         pNv->VRAMSize=res;
1649         nouveau_device_get_param(pNv->dev, NOUVEAU_GETPARAM_FB_PHYSICAL, &res);
1650         pNv->VRAMPhysical=res;
1651         nouveau_device_get_param(pNv->dev, NOUVEAU_GETPARAM_AGP_SIZE, &res);
1652         pNv->AGPSize=res;
1653
1654 #if !NOUVEAU_EXA_PIXMAPS
1655         if (nouveau_bo_new(pNv->dev, NOUVEAU_BO_VRAM | NOUVEAU_BO_PIN,
1656                 0, pNv->VRAMPhysicalSize / 2, &pNv->FB)) {
1657                         xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Failed to allocate memory for framebuffer!\n");
1658                         return FALSE;
1659         }
1660         xf86DrvMsg(pScrn->scrnIndex, X_INFO,
1661                 "Allocated %dMiB VRAM for framebuffer + offscreen pixmaps\n",
1662                 (unsigned int)(pNv->FB->size >> 20));
1663 #endif
1664
1665         if (pNv->AGPSize) {
1666                 xf86DrvMsg(pScrn->scrnIndex, X_INFO,
1667                            "AGPGART: %dMiB available\n",
1668                            (unsigned int)(pNv->AGPSize >> 20));
1669                 if (pNv->AGPSize > (16*1024*1024))
1670                         gart_scratch_size = 16*1024*1024;
1671                 else
1672                         /* always leave 512kb for other things like the fifos */
1673                         gart_scratch_size = pNv->AGPSize - 512*1024;
1674         } else {
1675                 gart_scratch_size = (4 << 20) - (1 << 18) ;
1676                 xf86DrvMsg(pScrn->scrnIndex, X_INFO,
1677                            "GART: PCI DMA - using %dKiB\n",
1678                            gart_scratch_size >> 10);
1679         }
1680
1681         if (nouveau_bo_new(pNv->dev, NOUVEAU_BO_GART | NOUVEAU_BO_PIN, 0,
1682                            gart_scratch_size, &pNv->GART)) {
1683                 xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
1684                            "Unable to allocate GART memory\n");
1685         }
1686         if (pNv->GART) {
1687                 xf86DrvMsg(pScrn->scrnIndex, X_INFO,
1688                            "GART: Allocated %dMiB as a scratch buffer\n",
1689                            (unsigned int)(pNv->GART->size >> 20));
1690         }
1691
1692         if (nouveau_bo_new(pNv->dev, NOUVEAU_BO_VRAM | NOUVEAU_BO_PIN, 0,
1693                            64 * 1024, &pNv->Cursor)) {
1694                 xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
1695                            "Failed to allocate memory for hardware cursor\n");
1696                 return FALSE;
1697         }
1698
1699         if (pNv->randr12_enable) {
1700                 if (nouveau_bo_new(pNv->dev, NOUVEAU_BO_VRAM | NOUVEAU_BO_PIN, 0,
1701                         64 * 1024, &pNv->Cursor2)) {
1702                         xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
1703                                 "Failed to allocate memory for hardware cursor\n");
1704                         return FALSE;
1705                 }
1706         }
1707
1708         if (pNv->Architecture >= NV_ARCH_50) {
1709                 if (nouveau_bo_new(pNv->dev, NOUVEAU_BO_VRAM | NOUVEAU_BO_PIN,
1710                                    0, 0x1000, &pNv->CLUT)) {
1711                         xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
1712                                    "Failed to allocate memory for CLUT\n");
1713                         return FALSE;
1714                 }
1715         }
1716
1717         if ((pNv->FB && nouveau_bo_map(pNv->FB, NOUVEAU_BO_RDWR)) ||
1718             (pNv->GART && nouveau_bo_map(pNv->GART, NOUVEAU_BO_RDWR)) ||
1719             (pNv->CLUT && nouveau_bo_map(pNv->CLUT, NOUVEAU_BO_RDWR)) ||
1720             nouveau_bo_map(pNv->Cursor, NOUVEAU_BO_RDWR) ||
1721             (pNv->randr12_enable && nouveau_bo_map(pNv->Cursor2, NOUVEAU_BO_RDWR))) {
1722                 xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
1723                            "Failed to map pinned buffers\n");
1724                 return FALSE;
1725         }
1726
1727         return TRUE;
1728 }
1729
1730 /*
1731  * Unmap the framebuffer and MMIO memory.
1732  */
1733
1734 static Bool
1735 NVUnmapMem(ScrnInfoPtr pScrn)
1736 {
1737         NVPtr pNv = NVPTR(pScrn);
1738
1739         nouveau_bo_del(&pNv->FB);
1740         nouveau_bo_del(&pNv->GART);
1741         nouveau_bo_del(&pNv->Cursor);
1742         if (pNv->randr12_enable) {
1743                 nouveau_bo_del(&pNv->Cursor2);
1744         }
1745         nouveau_bo_del(&pNv->CLUT);
1746
1747         return TRUE;
1748 }
1749
1750
1751 /*
1752  * Initialise a new mode. 
1753  */
1754
1755 static Bool
1756 NVModeInit(ScrnInfoPtr pScrn, DisplayModePtr mode)
1757 {
1758     vgaHWPtr hwp = VGAHWPTR(pScrn);
1759     vgaRegPtr vgaReg;
1760     NVPtr pNv = NVPTR(pScrn);
1761     NVRegPtr nvReg;
1762
1763     /* Initialise the ModeReg values */
1764     if (!vgaHWInit(pScrn, mode))
1765         return FALSE;
1766     pScrn->vtSema = TRUE;
1767
1768     vgaReg = &hwp->ModeReg;
1769     nvReg = &pNv->ModeReg;
1770
1771     if(!NVDACInit(pScrn, mode))
1772         return FALSE;
1773
1774     NVLockUnlock(pScrn, 0);
1775     if(pNv->twoHeads) {
1776         nvWriteCurVGA(pNv, NV_VGA_CRTCX_OWNER, nvReg->crtcOwner);
1777         NVLockUnlock(pScrn, 0);
1778     }
1779
1780     /* Program the registers */
1781     vgaHWProtect(pScrn, TRUE);
1782
1783     NVDACRestore(pScrn, vgaReg, nvReg, FALSE);
1784
1785 #if X_BYTE_ORDER == X_BIG_ENDIAN
1786     /* turn on LFB swapping */
1787     {
1788         unsigned char tmp;
1789
1790         tmp = nvReadCurVGA(pNv, NV_VGA_CRTCX_SWAPPING);
1791         tmp |= (1 << 7);
1792         nvWriteCurVGA(pNv, NV_VGA_CRTCX_SWAPPING, tmp);
1793     }
1794 #endif
1795
1796     if (!pNv->NoAccel)
1797                 NVAccelCommonInit(pScrn);
1798
1799     vgaHWProtect(pScrn, FALSE);
1800
1801     pNv->CurrentLayout.mode = mode;
1802
1803     return TRUE;
1804 }
1805
1806 #define NV_MODE_PRIVATE_ID 0x4F37ED65
1807 #define NV_MODE_PRIVATE_SIZE 2
1808
1809 /* 
1810  * Match a private mode flag in a special function.
1811  * I don't want ugly casting all over the code.
1812  */
1813 Bool
1814 NVMatchModePrivate(DisplayModePtr mode, uint32_t flags)
1815 {
1816         if (!mode)
1817                 return FALSE;
1818         if (!mode->Private)
1819                 return FALSE;
1820         if (mode->PrivSize != NV_MODE_PRIVATE_SIZE)
1821                 return FALSE;
1822         if (mode->Private[0] != NV_MODE_PRIVATE_ID)
1823                 return FALSE;
1824
1825         if (mode->Private[1] & flags)
1826                 return TRUE;
1827
1828         return FALSE;
1829 }
1830
1831 static void
1832 NVRestoreConsole(xf86OutputPtr output, DisplayModePtr mode)
1833 {
1834         if (!output->crtc)
1835                 return;
1836
1837         xf86CrtcPtr crtc = output->crtc;
1838         Bool need_unlock;
1839
1840         if (!crtc->enabled)
1841                 return;
1842
1843         xf86SetModeCrtc(mode, INTERLACE_HALVE_V);
1844         DisplayModePtr adjusted_mode = xf86DuplicateMode(mode);
1845
1846         /* Sequence mimics a normal modeset. */
1847         output->funcs->dpms(output, DPMSModeOff);
1848         crtc->funcs->dpms(crtc, DPMSModeOff);
1849         need_unlock = crtc->funcs->lock(crtc);
1850         output->funcs->mode_fixup(output, mode, adjusted_mode);
1851         crtc->funcs->mode_fixup(crtc, mode, adjusted_mode);
1852         output->funcs->prepare(output);
1853         crtc->funcs->prepare(crtc);
1854         /* Always use offset (0,0). */
1855         crtc->funcs->mode_set(crtc, mode, adjusted_mode, 0, 0);
1856         output->funcs->mode_set(output, mode, adjusted_mode);
1857         crtc->funcs->commit(crtc);
1858         output->funcs->commit(output);
1859         if (need_unlock)
1860                 crtc->funcs->unlock(crtc);
1861         /* Always turn on outputs afterwards. */
1862         output->funcs->dpms(output, DPMSModeOn);
1863         crtc->funcs->dpms(crtc, DPMSModeOn);
1864
1865         /* Free mode. */
1866         xfree(adjusted_mode);
1867 }
1868
1869 #define MODEPREFIX(name) NULL, NULL, name, 0,M_T_DRIVER
1870 #define MODESUFFIX   0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,FALSE,FALSE,0,NULL,0,0.0,0.0
1871
1872 /* hblankstart: 648, hblankend: 792, vblankstart: 407, vblankend: 442 for 640x400 */
1873 static DisplayModeRec VGAModes[2] = {
1874         { MODEPREFIX("640x400"),    28320, /*25175,*/ 640,  680,  776,  800, 0,  400,  412,  414,  449, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 640x400 */
1875         { MODEPREFIX("720x400"),    28320,  720,  738,  846,  900, 0,  400,  412,  414,  449, 0, V_NHSYNC | V_PVSYNC, MODESUFFIX }, /* 720x400@70Hz */
1876 };
1877
1878 /*
1879  * Restore the initial (text) mode.
1880  */
1881 static void 
1882 NVRestore(ScrnInfoPtr pScrn)
1883 {
1884         vgaHWPtr hwp = VGAHWPTR(pScrn);
1885         vgaRegPtr vgaReg = &hwp->SavedReg;
1886         NVPtr pNv = NVPTR(pScrn);
1887         NVRegPtr nvReg = &pNv->SavedReg;
1888
1889         if (pNv->randr12_enable) {
1890                 xf86CrtcConfigPtr xf86_config = XF86_CRTC_CONFIG_PTR(pScrn);
1891                 RIVA_HW_STATE *state = &pNv->ModeReg;
1892                 int i;
1893
1894                 /* Let's wipe some state regs */
1895                 state->vpll1_a = 0;
1896                 state->vpll1_b = 0;
1897                 state->vpll2_a = 0;
1898                 state->vpll2_b = 0;
1899                 state->reg594 = 0;
1900                 state->reg580 = 0;
1901                 state->pllsel = 0;
1902                 state->sel_clk = 0;
1903                 state->crosswired = FALSE;
1904
1905                 if (pNv->new_restore) { /* new style restore. */
1906                         for (i = 0; i < xf86_config->num_crtc; i++) {
1907                                 NVCrtcLockUnlock(xf86_config->crtc[i], 0);
1908                         }
1909
1910                         /* Reset some values according to stored console value, to avoid confusion later on. */
1911                         /* Otherwise we end up with corrupted terminals. */
1912                         for (i = 0; i < xf86_config->num_crtc; i++) {
1913                                 NVCrtcPrivatePtr nv_crtc = xf86_config->crtc[i]->driver_private;
1914                                 RIVA_HW_STATE *state = &pNv->SavedReg;
1915                                 NVCrtcRegPtr savep = &state->crtc_reg[nv_crtc->head];
1916                                 uint8_t pixelDepth = pNv->console_mode[nv_crtc->head].depth/8;
1917                                 /* restore PIXEL value */
1918                                 uint32_t pixel = NVReadVgaCrtc(pNv, nv_crtc->head, NV_VGA_CRTCX_PIXEL) & ~(0xF);
1919                                 pixel |= (pixelDepth > 2) ? 3 : pixelDepth;
1920                                 NVWriteVgaCrtc(pNv, nv_crtc->head, NV_VGA_CRTCX_PIXEL, pixel);
1921                                 /* restore HDisplay and VDisplay */
1922                                 NVWriteVgaCrtc(pNv, nv_crtc->head, NV_VGA_CRTCX_HDISPE, (pNv->console_mode[nv_crtc->head].x_res)/8 - 1);
1923                                 NVWriteVgaCrtc(pNv, nv_crtc->head, NV_VGA_CRTCX_VDISPE, (pNv->console_mode[nv_crtc->head].y_res) - 1);
1924                                 /* restore CR52 */
1925                                 NVWriteVgaCrtc(pNv, nv_crtc->head, NV_VGA_CRTCX_52, pNv->misc_info.crtc_reg_52[nv_crtc->head]);
1926                                 /* restore crtc base */
1927                                 NVCrtcWriteCRTC(xf86_config->crtc[i], NV_CRTC_START, pNv->console_mode[nv_crtc->head].fb_start);
1928                                 /* Restore general control */
1929                                 NVCrtcWriteRAMDAC(xf86_config->crtc[i], NV_RAMDAC_GENERAL_CONTROL, pNv->misc_info.ramdac_general_control[nv_crtc->head]);
1930                                 /* Restore CR5758 */
1931                                 if (pNv->NVArch >= 0x17 && pNv->twoHeads)
1932                                         for (i = 0; i < 0x10; i++)
1933                                                 NVWriteVgaCrtc5758(pNv, nv_crtc->head, i, savep->CR58[i]);
1934                         }
1935
1936                         /* Restore outputs when enabled. */
1937                         for (i = 0; i < xf86_config->num_output; i++) {
1938                                 xf86OutputPtr output = xf86_config->output[i];
1939                                 if (!xf86_config->output[i]->crtc) /* not enabled? */
1940                                         continue;
1941
1942                                 NVOutputPrivatePtr nv_output = output->driver_private;
1943                                 Bool is_fp = FALSE;
1944                                 DisplayModePtr mode = NULL;
1945                                 DisplayModePtr good_mode = NULL;
1946                                 NVConsoleMode *console = &pNv->console_mode[i];
1947                                 DisplayModePtr modes = output->probed_modes;
1948                                 if (!modes) /* no modes means no restore */
1949                                         continue;
1950
1951                                 if (nv_output->type == OUTPUT_TMDS || nv_output->type == OUTPUT_LVDS)
1952                                         is_fp = TRUE;
1953
1954                                 if (console->vga_mode) {
1955                                         /* We support 640x400 and 720x400 vga modes. */
1956                                         if (console->x_res == 720)
1957                                                 good_mode = &VGAModes[1];
1958                                         else
1959                                                 good_mode = &VGAModes[0];
1960                                         if (!good_mode) /* No suitable mode found. */
1961                                                 continue;
1962                                 } else {
1963                                         NVCrtcPrivatePtr nv_crtc = output->crtc->driver_private;
1964                                         uint32_t old_clock = nv_get_clock_from_crtc(pScrn, &pNv->SavedReg, nv_crtc->head);
1965                                         uint32_t clock_diff = 0xFFFFFFFF;
1966                                         for (mode = modes; mode != NULL; mode = mode->next) {
1967                                                 /* We only have the first 8 bits of y_res - 1. */
1968                                                 /* And it's sometimes bogus. */
1969                                                 if (is_fp || !console->enabled) { /* digital outputs are run at their native clock */
1970                                                         if (mode->HDisplay == console->x_res) {
1971                                                                 if (!good_mode) /* Pick any match, in case we don't find a 60.0 Hz mode. */
1972                                                                         good_mode = mode;
1973                                                                 /* Pick a 60.0 Hz mode if there is one. */
1974                                                                 if (mode->VRefresh > 59.95 && mode->VRefresh < 60.05) {
1975                                                                         good_mode = mode;
1976                                                                         break;
1977                                                                 }
1978                                                         }
1979                                                 } else {
1980                                                         if (mode->HDisplay == console->x_res) {
1981                                                                 int temp_diff = mode->Clock - old_clock;
1982                                                                 if (temp_diff < 0)
1983                                                                         temp_diff *= -1;
1984                                                                 if (temp_diff < clock_diff) { /* converge on the closest mode */
1985                                                                         clock_diff = temp_diff;
1986                                                                         good_mode = mode;
1987                                                                 }
1988                                                         }
1989                                                 }
1990                                         }
1991                                         if (!good_mode) /* No suitable mode found. */
1992                                                 continue;
1993                                 }
1994
1995                                 mode = xf86DuplicateMode(good_mode);
1996
1997                                 INT32 *nv_mode = xnfcalloc(sizeof(INT32)*NV_MODE_PRIVATE_SIZE, 1);
1998
1999                                 /* A semi-unique identifier to avoid using other privates. */
2000                                 nv_mode[0] = NV_MODE_PRIVATE_ID;
2001
2002                                 if (console->vga_mode)
2003                                         nv_mode[1] |= NV_MODE_VGA;
2004
2005                                 nv_mode[1] |= NV_MODE_CONSOLE;
2006
2007                                 mode->Private = nv_mode;
2008                                 mode->PrivSize = NV_MODE_PRIVATE_SIZE;
2009
2010                                 uint8_t scale_backup = nv_output->scaling_mode;
2011                                 if (nv_output->type == OUTPUT_LVDS || nv_output->type == OUTPUT_TMDS)
2012                                         nv_output->scaling_mode = SCALE_FULLSCREEN;
2013
2014                                 NVRestoreConsole(output, mode);
2015
2016                                 /* Restore value, so we reenter X properly. */
2017                                 nv_output->scaling_mode = scale_backup;
2018
2019                                 xfree(mode->Private);
2020                                 xfree(mode);
2021                         }
2022
2023                         /* Force hide the cursor. */
2024                         for (i = 0; i < xf86_config->num_crtc; i++) {
2025                                 xf86_config->crtc[i]->funcs->hide_cursor(xf86_config->crtc[i]);
2026                         }
2027
2028                         /* Lock the crtc's. */
2029                         for (i = 0; i < xf86_config->num_crtc; i++) {
2030                                 NVCrtcLockUnlock(xf86_config->crtc[i], 1);
2031                         }
2032
2033                         /* Let's clean our slate once again, so we always rewrite vpll's upon returning to X. */
2034                         state->vpll1_a = 0;
2035                         state->vpll1_b = 0;
2036                         state->vpll2_a = 0;
2037                         state->vpll2_b = 0;
2038                         state->reg594 = 0;
2039                         state->reg580 = 0;
2040                         state->pllsel = 0;
2041                         state->sel_clk = 0;
2042                         state->crosswired = FALSE;
2043                 } else {
2044                         for (i = 0; i < xf86_config->num_crtc; i++) {
2045                                 NVCrtcLockUnlock(xf86_config->crtc[i], 0);
2046                         }
2047
2048                         /* Some aspects of an output needs to be restore before the crtc. */
2049                         /* In my case this has to do with the mode that i get at very low resolutions. */
2050                         /* If i do this at the end, it will not be restored properly */
2051                         for (i = 0; i < xf86_config->num_output; i++) {
2052                                 NVOutputPrivatePtr nv_output2 = xf86_config->output[i]->driver_private;
2053                                 NVOutputRegPtr regp = &nvReg->dac_reg[nv_output2->preferred_output];
2054                                 Bool crosswired = regp->TMDS[0x4] & (1 << 3);
2055                                 /* Let's guess the bios state ;-) */
2056                                 if (nv_output2->type == OUTPUT_TMDS)
2057                                         xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Restoring TMDS timings, before restoring anything else.\n");
2058                                 if (nv_output2->type == OUTPUT_LVDS)
2059                                         xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Restoring LVDS timings, before restoring anything else.\n");
2060                                 if (nv_output2->type == OUTPUT_TMDS || nv_output2->type == OUTPUT_LVDS) {
2061                                         uint32_t clock = nv_calc_tmds_clock_from_pll(xf86_config->output[i]);
2062                                         nv_set_tmds_registers(xf86_config->output[i], clock, TRUE, crosswired);
2063                                 }
2064                         }
2065
2066                         /* This needs to happen before the crtc restore happens. */
2067                         for (i = 0; i < xf86_config->num_output; i++) {
2068                                 NVOutputPrivatePtr nv_output = xf86_config->output[i]->driver_private;
2069                                 /* Select the default output resource for consistent restore. */
2070                                 if (ffs(pNv->dcb_table.entry[nv_output->dcb_entry].or) & OUTPUT_1) {
2071                                         nv_output->output_resource = 1;
2072                                 } else {
2073                                         nv_output->output_resource = 0;
2074                                 }
2075                         }
2076
2077                         for (i = 0; i < xf86_config->num_crtc; i++) {
2078                                 NVCrtcPrivatePtr nv_crtc = xf86_config->crtc[i]->driver_private;
2079                                 /* Restore this, so it doesn't mess with restore. */
2080                                 pNv->fp_regs_owner[nv_crtc->head] = nv_crtc->head;
2081                         }
2082
2083                         for (i = 0; i < xf86_config->num_crtc; i++) {
2084                                 xf86_config->crtc[i]->funcs->restore(xf86_config->crtc[i]);
2085                         }
2086
2087                         for (i = 0; i < xf86_config->num_output; i++) {
2088                                 xf86_config->output[i]->funcs->restore(xf86_config->
2089                                                                        output[i]);
2090                         }
2091
2092                         for (i = 0; i < xf86_config->num_crtc; i++) {
2093                                 NVCrtcLockUnlock(xf86_config->crtc[i], 1);
2094                         }
2095                 }
2096         } else {
2097                 NVLockUnlock(pScrn, 0);
2098
2099                 if(pNv->twoHeads) {
2100                         nvWriteCurVGA(pNv, NV_VGA_CRTCX_OWNER, pNv->crtc_active[1] * 0x3);
2101                         NVLockUnlock(pScrn, 0);
2102                 }
2103
2104                 /* Only restore text mode fonts/text for the primary card */
2105                 vgaHWProtect(pScrn, TRUE);
2106                 NVDACRestore(pScrn, vgaReg, nvReg, pNv->Primary);
2107                 vgaHWProtect(pScrn, FALSE);
2108         }
2109
2110         if (pNv->twoHeads && !pNv->new_restore) {
2111                 NVSetOwner(pScrn, 0);   /* move to head A to set owner */
2112                 NVLockVgaCrtc(pNv, 0, false);
2113                 xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Restoring CRTC_OWNER to %d.\n", pNv->vtOWNER);
2114                 NVWriteVGA(pNv, 0, NV_VGA_CRTCX_OWNER, pNv->vtOWNER);
2115                 NVLockVgaCrtc(pNv, 0, true);
2116         }
2117 }
2118
2119 static void
2120 NVLoadPalette(ScrnInfoPtr pScrn, int numColors, int *indices,
2121               LOCO * colors, VisualPtr pVisual)
2122 {
2123         xf86CrtcConfigPtr xf86_config = XF86_CRTC_CONFIG_PTR(pScrn);
2124         int c;
2125         int i, j, index;
2126         CARD16 lut_r[256], lut_g[256], lut_b[256];
2127
2128         for (c = 0; c < xf86_config->num_crtc; c++) {
2129                 xf86CrtcPtr crtc = xf86_config->crtc[c];
2130
2131                 if (crtc->enabled == 0)
2132                         continue;
2133
2134                 /* code borrowed from intel driver */
2135                 switch (pScrn->depth) {
2136                 case 15:
2137                         for (i = 0; i < numColors; i++) {
2138                                 index = indices[i];
2139                                 for (j = 0; j < 8; j++) {
2140                                         lut_r[index * 8 + j] = colors[index].red << 8;
2141                                         lut_g[index * 8 + j] = colors[index].green << 8;
2142                                         lut_b[index * 8 + j] = colors[index].blue << 8;
2143                                 }
2144                         }
2145                 case 16:
2146                         for (i = 0; i < numColors; i++) {
2147                                 index = indices[i];
2148
2149                                 if (i <= 31) {
2150                                         for (j = 0; j < 8; j++) {
2151                                                 lut_r[index * 8 + j] = colors[index].red << 8;
2152                                                 lut_b[index * 8 + j] = colors[index].blue << 8;
2153                                         }
2154                                 }
2155
2156                                 for (j = 0; j < 4; j++) {
2157                                         lut_g[index * 4 + j] = colors[index].green << 8;
2158                                 }
2159                         }
2160                 default:
2161                         for (i = 0; i < numColors; i++) {
2162                                 index = indices[i];
2163                                 lut_r[index] = colors[index].red << 8;
2164                                 lut_g[index] = colors[index].green << 8;
2165                                 lut_b[index] = colors[index].blue << 8;
2166                         }
2167                         break;
2168                 }
2169
2170                 /* Make the change through RandR */
2171                 RRCrtcGammaSet(crtc->randr_crtc, lut_r, lut_g, lut_b);
2172         }
2173 }
2174
2175 #define DEPTH_SHIFT(val, w) ((val << (8 - w)) | (val >> ((w << 1) - 8)))
2176 #define COLOR(c) (unsigned int)(0x3fff * ((c)/255.0))
2177 static void
2178 NV50LoadPalette(ScrnInfoPtr pScrn, int numColors, int *indices,
2179                 LOCO * colors, VisualPtr pVisual)
2180 {
2181         NVPtr pNv = NVPTR(pScrn);
2182         int i, index;
2183         volatile struct {
2184                 unsigned short red, green, blue, unused;
2185         } *lut = (void *) pNv->CLUT->map;
2186
2187         switch (pScrn->depth) {
2188         case 15:
2189                 for (i = 0; i < numColors; i++) {
2190                         index = indices[i];
2191                         lut[DEPTH_SHIFT(index, 5)].red =
2192                             COLOR(colors[index].red);
2193                         lut[DEPTH_SHIFT(index, 5)].green =
2194                             COLOR(colors[index].green);
2195                         lut[DEPTH_SHIFT(index, 5)].blue =
2196                             COLOR(colors[index].blue);
2197                 }
2198                 break;
2199         case 16:
2200                 for (i = 0; i < numColors; i++) {
2201                         index = indices[i];
2202                         lut[DEPTH_SHIFT(index, 6)].green =
2203                             COLOR(colors[index].green);
2204                         if (index < 32) {
2205                                 lut[DEPTH_SHIFT(index, 5)].red =
2206                                     COLOR(colors[index].red);
2207                                 lut[DEPTH_SHIFT(index, 5)].blue =
2208                                     COLOR(colors[index].blue);
2209                         }
2210                 }
2211                 break;
2212         default:
2213                 for (i = 0; i < numColors; i++) {
2214                         index = indices[i];
2215                         lut[index].red = COLOR(colors[index].red);
2216                         lut[index].green = COLOR(colors[index].green);
2217                         lut[index].blue = COLOR(colors[index].blue);
2218                 }
2219                 break;
2220         }
2221 }
2222
2223
2224 static void NVBacklightEnable(NVPtr pNv,  Bool on)
2225 {
2226     /* This is done differently on each laptop.  Here we
2227        define the ones we know for sure. */
2228
2229 #if defined(__powerpc__)
2230     if((pNv->Chipset == 0x10DE0179) || 
2231        (pNv->Chipset == 0x10DE0189) || 
2232        (pNv->Chipset == 0x10DE0329))
2233     {
2234        /* NV17,18,34 Apple iMac, iBook, PowerBook */
2235       CARD32 tmp_pmc, tmp_pcrt;
2236       tmp_pmc = nvReadMC(pNv, NV_PBUS_DEBUG_DUALHEAD_CTL) & 0x7FFFFFFF;
2237       tmp_pcrt = NVReadCRTC(pNv, 0, NV_CRTC_GPIO_EXT) & 0xFFFFFFFC;
2238       if(on) {
2239           tmp_pmc |= (1 << 31);
2240           tmp_pcrt |= 0x1;
2241       }
2242       nvWriteMC(pNv, NV_PBUS_DEBUG_DUALHEAD_CTL, tmp_pmc);
2243       NVWriteCRTC(pNv, 0, NV_CRTC_GPIO_EXT, tmp_pcrt);
2244     }
2245 #endif
2246     
2247     if(pNv->LVDS) {
2248        if(pNv->twoHeads && ((pNv->Chipset & 0x0ff0) != CHIPSET_NV11)) {
2249            nvWriteMC(pNv, 0x130C, on ? 3 : 7);
2250        }
2251     } else {
2252        CARD32 fpcontrol;
2253
2254        fpcontrol = nvReadCurRAMDAC(pNv, NV_RAMDAC_FP_CONTROL) & 0xCfffffCC;
2255
2256        /* cut the TMDS output */
2257        if(on) fpcontrol |= pNv->fpSyncs;
2258        else fpcontrol |= 0x20000022;
2259
2260        nvWriteCurRAMDAC(pNv, NV_RAMDAC_FP_CONTROL, fpcontrol);
2261     }
2262 }
2263
2264 static void
2265 NVDPMSSetLCD(ScrnInfoPtr pScrn, int PowerManagementMode, int flags)
2266 {
2267   NVPtr pNv = NVPTR(pScrn);
2268
2269   if (!pScrn->vtSema) return;
2270
2271   vgaHWDPMSSet(pScrn, PowerManagementMode, flags);
2272
2273   switch (PowerManagementMode) {
2274   case DPMSModeStandby:  /* HSync: Off, VSync: On */
2275   case DPMSModeSuspend:  /* HSync: On, VSync: Off */
2276   case DPMSModeOff:      /* HSync: Off, VSync: Off */
2277     NVBacklightEnable(pNv, 0);
2278     break;
2279   case DPMSModeOn:       /* HSync: On, VSync: On */
2280     NVBacklightEnable(pNv, 1);
2281   default:
2282     break;
2283   }
2284 }
2285
2286
2287 static void
2288 NVDPMSSet(ScrnInfoPtr pScrn, int PowerManagementMode, int flags)
2289 {
2290   unsigned char crtc1A;
2291   vgaHWPtr hwp = VGAHWPTR(pScrn);
2292
2293   if (!pScrn->vtSema) return;
2294
2295   crtc1A = hwp->readCrtc(hwp, 0x1A) & ~0xC0;
2296
2297   switch (PowerManagementMode) {
2298   case DPMSModeStandby:  /* HSync: Off, VSync: On */
2299     crtc1A |= 0x80;
2300     break;
2301   case DPMSModeSuspend:  /* HSync: On, VSync: Off */
2302     crtc1A |= 0x40;
2303     break;
2304   case DPMSModeOff:      /* HSync: Off, VSync: Off */
2305     crtc1A |= 0xC0;
2306     break;
2307   case DPMSModeOn:       /* HSync: On, VSync: On */
2308   default:
2309     break;
2310   }
2311
2312   /* vgaHWDPMSSet will merely cut the dac output */
2313   vgaHWDPMSSet(pScrn, PowerManagementMode, flags);
2314
2315   hwp->writeCrtc(hwp, 0x1A, crtc1A);
2316 }
2317
2318
2319 /* Mandatory */
2320
2321 /* This gets called at the start of each server generation */
2322
2323 static Bool
2324 NVScreenInit(int scrnIndex, ScreenPtr pScreen, int argc, char **argv)
2325 {
2326         ScrnInfoPtr pScrn;
2327         vgaHWPtr hwp;
2328         NVPtr pNv;
2329         int ret;
2330         VisualPtr visual;
2331         unsigned char *FBStart;
2332         int width, height, displayWidth, shadowHeight, i;
2333
2334         /* 
2335          * First get the ScrnInfoRec
2336          */
2337         pScrn = xf86Screens[pScreen->myNum];
2338
2339         hwp = VGAHWPTR(pScrn);
2340         pNv = NVPTR(pScrn);
2341
2342         /* Map the VGA memory when the primary video */
2343         if (pNv->Primary) {
2344                 hwp->MapSize = 0x10000;
2345                 if (!vgaHWMapMem(pScrn))
2346                         return FALSE;
2347         }
2348
2349         /* First init DRI/DRM */
2350         if (!NVDRIScreenInit(pScrn))
2351                 return FALSE;
2352
2353         /* Allocate and map memory areas we need */
2354         if (!NVMapMem(pScrn))
2355                 return FALSE;
2356
2357         if (!pNv->NoAccel) {
2358                 /* Init DRM - Alloc FIFO */
2359                 if (!NVInitDma(pScrn))
2360                         return FALSE;
2361
2362                 /* setup graphics objects */
2363                 if (!NVAccelCommonInit(pScrn))
2364                         return FALSE;
2365         }
2366
2367 #if NOUVEAU_EXA_PIXMAPS
2368         if (nouveau_bo_new(pNv->dev, NOUVEAU_BO_VRAM | NOUVEAU_BO_PIN,
2369                         0, NOUVEAU_ALIGN(pScrn->virtualX, 64) * NOUVEAU_ALIGN(pScrn->virtualY, 64) *
2370                         (pScrn->bitsPerPixel >> 3), &pNv->FB)) {
2371                 xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Failed to allocate memory for screen pixmap.\n");
2372                 return FALSE;
2373         }
2374 #endif
2375
2376         if (!pNv->randr12_enable) {
2377                 /* Save the current state */
2378                 NVSave(pScrn);
2379                 /* Initialise the first mode */
2380                 if (!NVModeInit(pScrn, pScrn->currentMode))
2381                         return FALSE;
2382
2383                 /* Darken the screen for aesthetic reasons and set the viewport */
2384                 NVSaveScreen(pScreen, SCREEN_SAVER_ON);
2385                 pScrn->AdjustFrame(scrnIndex, pScrn->frameX0, pScrn->frameY0, 0);
2386         } else {
2387                 pScrn->memPhysBase = pNv->VRAMPhysical;
2388                 pScrn->fbOffset = 0;
2389
2390                 /* Gather some misc info before the randr stuff kicks in */
2391                 if (pNv->Architecture >= NV_ARCH_10) {
2392                         pNv->misc_info.crtc_reg_52[0] = NVReadVGA(pNv, 0, NV_VGA_CRTCX_52);
2393                         pNv->misc_info.crtc_reg_52[1] = NVReadVGA(pNv, 1, NV_VGA_CRTCX_52);
2394                 }
2395                 if (pNv->Architecture == NV_ARCH_40) {
2396                         pNv->misc_info.ramdac_0_reg_580 = NVReadRAMDAC(pNv, 0, NV_RAMDAC_580);
2397                         pNv->misc_info.reg_c040 = nvReadMC(pNv, 0xc040);
2398                 }
2399                 pNv->misc_info.ramdac_general_control[0] = NVReadRAMDAC(pNv, 0, NV_RAMDAC_GENERAL_CONTROL);
2400                 pNv->misc_info.ramdac_general_control[1] = NVReadRAMDAC(pNv, 1, NV_RAMDAC_GENERAL_CONTROL);
2401                 pNv->misc_info.ramdac_0_pllsel = NVReadRAMDAC(pNv, 0, NV_RAMDAC_PLL_SELECT);
2402                 pNv->misc_info.sel_clk = NVReadRAMDAC(pNv, 0, NV_RAMDAC_SEL_CLK);
2403                 if (pNv->twoHeads) {
2404                         pNv->misc_info.output[0] = NVReadRAMDAC(pNv, 0, NV_RAMDAC_OUTPUT);
2405                         pNv->misc_info.output[1] = NVReadRAMDAC(pNv, 1, NV_RAMDAC_OUTPUT);
2406                 }
2407
2408                 for (i = 0; i <= pNv->twoHeads; i++) {
2409                         if (NVReadVGA(pNv, i, NV_VGA_CRTCX_PIXEL) & 0xf) { /* framebuffer mode */
2410                                 pNv->console_mode[i].vga_mode = FALSE;
2411                                 uint8_t var = NVReadVGA(pNv, i, NV_VGA_CRTCX_PIXEL) & 0xf;
2412                                 Bool filled = (NVReadRAMDAC(pNv, i, NV_RAMDAC_GENERAL_CONTROL) & 0x1000);
2413                                 switch (var){
2414                                         case 3:
2415                                                 if (filled)
2416                                                         pNv->console_mode[i].depth = 32;
2417                                                 else
2418                                                         pNv->console_mode[i].depth = 24;
2419                                                 /* This is pitch related. */
2420                                                 pNv->console_mode[i].bpp = 32;
2421                                                 break;
2422                                         case 2:
2423                                                 if (filled)
2424                                                         pNv->console_mode[i].depth = 16;
2425                                                 else
2426                                                         pNv->console_mode[i].depth = 15;
2427                                                 /* This is pitch related. */
2428                                                 pNv->console_mode[i].bpp = 16;
2429                                                 break;
2430                                         case 1:
2431                                                 /* 8bit mode is always filled? */
2432                                                 pNv->console_mode[i].depth = 8;
2433                                                 /* This is pitch related. */
2434                                                 pNv->console_mode[i].bpp = 8;
2435                                         default:
2436                                                 break;
2437                                 }
2438                         } else { /* vga mode */
2439                                 pNv->console_mode[i].vga_mode = TRUE;
2440                                 pNv->console_mode[i].bpp = 4;
2441                                 pNv->console_mode[i].depth = 4;
2442                         }
2443
2444                         pNv->console_mode[i].x_res = (NVReadVGA(pNv, i, NV_VGA_CRTCX_HDISPE) + 1) * 8;
2445                         pNv->console_mode[i].y_res = (NVReadVGA(pNv, i, NV_VGA_CRTCX_VDISPE) + 1); /* NV_VGA_CRTCX_VDISPE only contains the lower 8 bits. */
2446
2447                         pNv->console_mode[i].fb_start = NVReadCRTC(pNv, i, NV_CRTC_START);
2448
2449                         pNv->console_mode[i].enabled = FALSE;
2450
2451                         xf86DrvMsg(pScrn->scrnIndex, X_INFO, "CRTC %d: Console mode: %dx%d depth: %d bpp: %d crtc_start: 0x%X.\n", i, pNv->console_mode[i].x_res, pNv->console_mode[i].y_res, pNv->console_mode[i].depth, pNv->console_mode[i].bpp, pNv->console_mode[i].fb_start);
2452                 }
2453
2454                 /* Check if crtc's were enabled. */
2455                 if (pNv->misc_info.ramdac_0_pllsel & NV_RAMDAC_PLL_SELECT_PLL_SOURCE_VPLL) {
2456                         pNv->console_mode[0].enabled = TRUE;
2457                         xf86DrvMsg(pScrn->scrnIndex, X_INFO, "CRTC 0 was enabled.\n");
2458                 }
2459
2460                 if (pNv->misc_info.ramdac_0_pllsel & NV_RAMDAC_PLL_SELECT_PLL_SOURCE_VPLL2) {
2461                         pNv->console_mode[1].enabled = TRUE;
2462                         xf86DrvMsg(pScrn->scrnIndex, X_INFO, "CRTC 1 was enabled.\n");
2463                 }
2464
2465                 if (!NVEnterVT(scrnIndex, 0))
2466                         return FALSE;
2467                 NVSaveScreen(pScreen, SCREEN_SAVER_ON);
2468         }
2469
2470
2471         /*
2472          * The next step is to setup the screen's visuals, and initialise the
2473          * framebuffer code.  In cases where the framebuffer's default
2474          * choices for things like visual layouts and bits per RGB are OK,
2475          * this may be as simple as calling the framebuffer's ScreenInit()
2476          * function.  If not, the visuals will need to be setup before calling
2477          * a fb ScreenInit() function and fixed up after.
2478          *
2479          * For most PC hardware at depths >= 8, the defaults that fb uses
2480          * are not appropriate.  In this driver, we fixup the visuals after.
2481          */
2482
2483         /*
2484          * Reset the visual list.
2485          */
2486         miClearVisualTypes();
2487
2488         /* Setup the visuals we support. */
2489
2490         if (!miSetVisualTypes(pScrn->depth, 
2491                                 miGetDefaultVisualMask(pScrn->depth), 8,
2492                                 pScrn->defaultVisual))
2493                 return FALSE;
2494         if (!miSetPixmapDepths ())
2495                 return FALSE;
2496
2497         /*
2498          * Call the framebuffer layer's ScreenInit function, and fill in other
2499          * pScreen fields.
2500          */
2501
2502         width = pScrn->virtualX;
2503         height = pScrn->virtualY;
2504         displayWidth = pScrn->displayWidth;
2505
2506         if(pNv->Rotate) {
2507                 height = pScrn->virtualX;
2508                 width = pScrn->virtualY;
2509         }
2510
2511         /* If RandR rotation is enabled, leave enough space in the
2512          * framebuffer for us to rotate the screen dimensions without
2513          * changing the pitch.
2514          */
2515         if(pNv->RandRRotation) {
2516                 shadowHeight = max(width, height);
2517         } else {
2518                 shadowHeight = height;
2519         }
2520
2521         if (pNv->ShadowFB) {
2522                 pNv->ShadowPitch = BitmapBytePad(pScrn->bitsPerPixel * width);
2523                 pNv->ShadowPtr = xalloc(pNv->ShadowPitch * shadowHeight);
2524                 displayWidth = pNv->ShadowPitch / (pScrn->bitsPerPixel >> 3);
2525                 FBStart = pNv->ShadowPtr;
2526         } else {
2527                 pNv->ShadowPtr = NULL;
2528                 FBStart = pNv->FB->map;
2529         }
2530
2531         switch (pScrn->bitsPerPixel) {
2532                 case 8:
2533                 case 16:
2534                 case 32:
2535                         ret = fbScreenInit(pScreen, FBStart, width, height,
2536                                 pScrn->xDpi, pScrn->yDpi,
2537                                 displayWidth, pScrn->bitsPerPixel);
2538                         break;
2539                 default:
2540                         xf86DrvMsg(scrnIndex, X_ERROR,
2541                                 "Internal error: invalid bpp (%d) in NVScreenInit\n",
2542                                 pScrn->bitsPerPixel);
2543                         ret = FALSE;
2544                         break;
2545         }
2546         if (!ret)
2547                 return FALSE;
2548
2549         if (pScrn->bitsPerPixel > 8) {
2550                 /* Fixup RGB ordering */
2551                 visual = pScreen->visuals + pScreen->numVisuals;
2552                 while (--visual >= pScreen->visuals) {
2553                         if ((visual->class | DynamicClass) == DirectColor) {
2554                                 visual->offsetRed = pScrn->offset.red;
2555                                 visual->offsetGreen = pScrn->offset.green;
2556                                 visual->offsetBlue = pScrn->offset.blue;
2557                                 visual->redMask = pScrn->mask.red;
2558                                 visual->greenMask = pScrn->mask.green;
2559                                 visual->blueMask = pScrn->mask.blue;
2560                         }
2561                 }
2562         }
2563
2564         fbPictureInit (pScreen, 0, 0);
2565
2566         xf86SetBlackWhitePixels(pScreen);
2567
2568         if (!pNv->NoAccel) {
2569                 if (!NVExaInit(pScreen))
2570                         return FALSE;
2571                 NVAccelCommonInit(pScrn);
2572         } else if (pNv->VRAMPhysicalSize / 2 < NOUVEAU_ALIGN(pScrn->virtualX, 64) * NOUVEAU_ALIGN(pScrn->virtualY, 64) * (pScrn->bitsPerPixel >> 3)) {
2573                 xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "The virtual screen size's resolution is too big for the video RAM framebuffer at this colour depth.\n");
2574                 return FALSE;
2575         }
2576
2577
2578         miInitializeBackingStore(pScreen);
2579         xf86SetBackingStore(pScreen);
2580         xf86SetSilkenMouse(pScreen);
2581
2582         /* Finish DRI init */
2583         NVDRIFinishScreenInit(pScrn);
2584
2585         /* 
2586          * Initialize software cursor.
2587          * Must precede creation of the default colormap.
2588          */
2589         miDCInitialize(pScreen, xf86GetPointerScreenFuncs());
2590
2591         /*
2592          * Initialize HW cursor layer. 
2593          * Must follow software cursor initialization.
2594          */
2595         if (pNv->HWCursor) { 
2596                 if (pNv->Architecture < NV_ARCH_50 && !pNv->randr12_enable)
2597                         ret = NVCursorInit(pScreen);
2598                 else if (pNv->Architecture < NV_ARCH_50 && pNv->randr12_enable)
2599                         ret = NVCursorInitRandr12(pScreen);
2600                 else
2601                         ret = NV50CursorInit(pScreen);
2602
2603                 if (ret != TRUE) {
2604                         xf86DrvMsg(pScrn->scrnIndex, X_ERROR, 
2605                                 "Hardware cursor initialization failed\n");
2606                         pNv->HWCursor = FALSE;
2607                 }
2608         }
2609
2610         if (pNv->randr12_enable) {
2611                 xf86DPMSInit(pScreen, xf86DPMSSet, 0);
2612
2613                 if (!xf86CrtcScreenInit(pScreen))
2614                         return FALSE;
2615
2616                 pNv->PointerMoved = pScrn->PointerMoved;
2617                 pScrn->PointerMoved = NVPointerMoved;
2618         }
2619
2620         /* Initialise default colourmap */
2621         if (!miCreateDefColormap(pScreen))
2622                 return FALSE;
2623
2624         /*
2625          * Initialize colormap layer.
2626          * Must follow initialization of the default colormap 
2627          */
2628         if (!pNv->randr12_enable) {
2629                 if(!xf86HandleColormaps(pScreen, 256, 8, NVDACLoadPalette,
2630                                 NULL, CMAP_RELOAD_ON_MODE_SWITCH | CMAP_PALETTED_TRUECOLOR))
2631                 return FALSE;
2632         } else {
2633                 if (pNv->Architecture < NV_ARCH_50) {
2634                         if (!xf86HandleColormaps(pScreen, 256, 8, NVLoadPalette,
2635                                                 NULL,
2636                                                 CMAP_RELOAD_ON_MODE_SWITCH |
2637                                                 CMAP_PALETTED_TRUECOLOR))
2638                         return FALSE;
2639                 } else {
2640                         if (!xf86HandleColormaps(pScreen, 256, 8, NV50LoadPalette,
2641                                                 NULL, CMAP_PALETTED_TRUECOLOR))
2642                         return FALSE;
2643                 }
2644         }
2645
2646         if(pNv->ShadowFB) {
2647                 RefreshAreaFuncPtr refreshArea = NVRefreshArea;
2648
2649                 if (pNv->Rotate || pNv->RandRRotation) {
2650                         pNv->PointerMoved = pScrn->PointerMoved;
2651                         if (pNv->Rotate)
2652                                 pScrn->PointerMoved = NVPointerMoved;
2653
2654                         switch(pScrn->bitsPerPixel) {
2655                                 case 8: refreshArea = NVRefreshArea8;   break;
2656                                 case 16:        refreshArea = NVRefreshArea16;  break;
2657                                 case 32:        refreshArea = NVRefreshArea32;  break;
2658                         }
2659                         if(!pNv->RandRRotation) {
2660                                 xf86DisableRandR();
2661                                 xf86DrvMsg(pScrn->scrnIndex, X_INFO,
2662                                         "Driver rotation enabled, RandR disabled\n");
2663                         }
2664                 }
2665
2666                 ShadowFBInit(pScreen, refreshArea);
2667         }
2668
2669         if (!pNv->randr12_enable) {
2670                 if(pNv->FlatPanel) {
2671                         xf86DPMSInit(pScreen, NVDPMSSetLCD, 0);
2672                 } else {
2673                         xf86DPMSInit(pScreen, NVDPMSSet, 0);
2674                 }
2675         }
2676
2677         pScrn->memPhysBase = pNv->VRAMPhysical;
2678         pScrn->fbOffset = 0;
2679
2680         if (pNv->Rotate == 0 && !pNv->RandRRotation)
2681                 NVInitVideo(pScreen);
2682
2683         pScreen->SaveScreen = NVSaveScreen;
2684
2685         /* Wrap the current CloseScreen function */
2686         pNv->CloseScreen = pScreen->CloseScreen;
2687         pScreen->CloseScreen = NVCloseScreen;
2688
2689         pNv->BlockHandler = pScreen->BlockHandler;
2690         pScreen->BlockHandler = NVBlockHandler;
2691
2692         /* Install our DriverFunc.  We have to do it this way instead of using the
2693          * HaveDriverFuncs argument to xf86AddDriver, because InitOutput clobbers
2694          * pScrn->DriverFunc 
2695          */
2696         if (!pNv->randr12_enable)
2697                 pScrn->DriverFunc = NVDriverFunc;
2698
2699         /* Report any unused options (only for the first generation) */
2700         if (serverGeneration == 1) {
2701                 xf86ShowUnusedOptions(pScrn->scrnIndex, pScrn->options);
2702         }
2703
2704         return TRUE;
2705 }
2706
2707 static Bool
2708 NVSaveScreen(ScreenPtr pScreen, int mode)
2709 {
2710     ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
2711     NVPtr pNv = NVPTR(pScrn);
2712     int i;
2713     Bool on = xf86IsUnblank(mode);
2714     
2715     if (pNv->randr12_enable) {
2716         xf86CrtcConfigPtr xf86_config = XF86_CRTC_CONFIG_PTR(pScrn);
2717         if (pScrn->vtSema && pNv->Architecture < NV_ARCH_50) {
2718             for (i = 0; i < xf86_config->num_crtc; i++) {
2719                 
2720                 if (xf86_config->crtc[i]->enabled) {
2721                     NVCrtcPrivatePtr nv_crtc = xf86_config->crtc[i]->driver_private;
2722                     NVBlankScreen(pScrn, nv_crtc->head, !on);
2723                 }
2724             }
2725             
2726         }
2727         return TRUE;
2728     }
2729
2730         return vgaHWSaveScreen(pScreen, mode);
2731 }
2732
2733 static void
2734 NVSave(ScrnInfoPtr pScrn)
2735 {
2736         NVPtr pNv = NVPTR(pScrn);
2737         NVRegPtr nvReg = &pNv->SavedReg;
2738
2739         if (pNv->randr12_enable) {
2740                 xf86CrtcConfigPtr xf86_config = XF86_CRTC_CONFIG_PTR(pScrn);
2741                 int i;
2742
2743                 for (i = 0; i < xf86_config->num_crtc; i++) {
2744                         xf86_config->crtc[i]->funcs->save(xf86_config->crtc[i]);
2745                 }
2746
2747                 for (i = 0; i < xf86_config->num_output; i++) {
2748                         xf86_config->output[i]->funcs->save(xf86_config->
2749                                                             output[i]);
2750                 }
2751         } else {
2752                 vgaHWPtr pVga = VGAHWPTR(pScrn);
2753                 vgaRegPtr vgaReg = &pVga->SavedReg;
2754                 NVLockUnlock(pScrn, 0);
2755                 if (pNv->twoHeads) {
2756                         nvWriteCurVGA(pNv, NV_VGA_CRTCX_OWNER, pNv->crtc_active[1] * 0x3);
2757                         NVLockUnlock(pScrn, 0);
2758                 }
2759
2760                 NVDACSave(pScrn, vgaReg, nvReg, pNv->Primary);
2761         }
2762 }
2763
2764 static Bool
2765 NVRandRGetInfo(ScrnInfoPtr pScrn, Rotation *rotations)
2766 {
2767     NVPtr pNv = NVPTR(pScrn);
2768
2769     if(pNv->RandRRotation)
2770        *rotations = RR_Rotate_0 | RR_Rotate_90 | RR_Rotate_270;
2771     else
2772        *rotations = RR_Rotate_0;
2773
2774     return TRUE;
2775 }
2776
2777 static Bool
2778 NVRandRSetConfig(ScrnInfoPtr pScrn, xorgRRConfig *config)
2779 {
2780     NVPtr pNv = NVPTR(pScrn);
2781
2782     switch(config->rotation) {
2783         case RR_Rotate_0:
2784             pNv->Rotate = 0;
2785             pScrn->PointerMoved = pNv->PointerMoved;
2786             break;
2787
2788         case RR_Rotate_90:
2789             pNv->Rotate = -1;
2790             pScrn->PointerMoved = NVPointerMoved;
2791             break;
2792
2793         case RR_Rotate_270:
2794             pNv->Rotate = 1;
2795             pScrn->PointerMoved = NVPointerMoved;
2796             break;
2797
2798         default:
2799             xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
2800                     "Unexpected rotation in NVRandRSetConfig!\n");
2801             pNv->Rotate = 0;
2802             pScrn->PointerMoved = pNv->PointerMoved;
2803             return FALSE;
2804     }
2805
2806     return TRUE;
2807 }
2808
2809 static Bool
2810 NVDriverFunc(ScrnInfoPtr pScrn, xorgDriverFuncOp op, pointer data)
2811 {
2812     switch(op) {
2813        case RR_GET_INFO:
2814           return NVRandRGetInfo(pScrn, (Rotation*)data);
2815        case RR_SET_CONFIG:
2816           return NVRandRSetConfig(pScrn, (xorgRRConfig*)data);
2817        default:
2818           return FALSE;
2819     }
2820
2821     return FALSE;
2822 }