VERY EXPERIMENTAL now EXA waits for sync before its operations - this removed the...
[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 "nv_include.h"
31
32 #include "xf86int10.h"
33
34 #include "xf86drm.h"
35
36 extern DisplayModePtr xf86ModesAdd(DisplayModePtr Modes, DisplayModePtr Additions);
37
38 /*const   OptionInfoRec * RivaAvailableOptions(int chipid, int busid);
39 Bool    RivaGetScrnInfoRec(PciChipsets *chips, int chip);*/
40
41 /*
42  * Forward definitions for the functions that make up the driver.
43  */
44 /* Mandatory functions */
45 static const OptionInfoRec * NVAvailableOptions(int chipid, int busid);
46 static void    NVIdentify(int flags);
47 static Bool    NVProbe(DriverPtr drv, int flags);
48 static Bool    NVPreInit(ScrnInfoPtr pScrn, int flags);
49 static Bool    NVScreenInit(int Index, ScreenPtr pScreen, int argc,
50                             char **argv);
51 static Bool    NVEnterVT(int scrnIndex, int flags);
52 static void    NVLeaveVT(int scrnIndex, int flags);
53 static Bool    NVCloseScreen(int scrnIndex, ScreenPtr pScreen);
54 static Bool    NVSaveScreen(ScreenPtr pScreen, int mode);
55
56 /* Optional functions */
57 static void    NVFreeScreen(int scrnIndex, int flags);
58 static ModeStatus NVValidMode(int scrnIndex, DisplayModePtr mode,
59                               Bool verbose, int flags);
60 #ifdef RANDR
61 static Bool    NVDriverFunc(ScrnInfoPtr pScrnInfo, xorgDriverFuncOp op,
62                               pointer data);
63 #endif
64
65 /* Internally used functions */
66
67 static Bool     NVMapMem(ScrnInfoPtr pScrn);
68 static Bool     NVUnmapMem(ScrnInfoPtr pScrn);
69 static void     NVSave(ScrnInfoPtr pScrn);
70 static void     NVRestore(ScrnInfoPtr pScrn);
71 static Bool     NVModeInit(ScrnInfoPtr pScrn, DisplayModePtr mode);
72
73
74 /*
75  * This contains the functions needed by the server after loading the
76  * driver module.  It must be supplied, and gets added the driver list by
77  * the Module Setup funtion in the dynamic case.  In the static case a
78  * reference to this is compiled in, and this requires that the name of
79  * this DriverRec be an upper-case version of the driver name.
80  */
81
82 _X_EXPORT DriverRec NV = {
83         NV_VERSION,
84         NV_DRIVER_NAME,
85         NVIdentify,
86         NVProbe,
87         NVAvailableOptions,
88         NULL,
89         0
90 };
91
92 struct NvFamily
93 {
94   char *name;
95   char *chipset;
96 };
97
98 static struct NvFamily NVKnownFamilies[] =
99 {
100   { "RIVA 128",    "NV03" },
101   { "RIVA TNT",    "NV04" },
102   { "RIVA TNT2",   "NV05" },
103   { "GeForce 256", "NV10" },
104   { "GeForce 2",   "NV11, NV15" },
105   { "GeForce 4MX", "NV17, NV18" },
106   { "GeForce 3",   "NV20" },
107   { "GeForce 4Ti", "NV25, NV28" },
108   { "GeForce FX",  "NV3x" },
109   { "GeForce 6",   "NV4x" },
110   { "GeForce 7",   "G7x" },
111   { NULL, NULL}
112 };
113
114 /* Known cards as of 2006/06/16 */
115
116 static SymTabRec NVKnownChipsets[] =
117 {
118   { 0x12D20018, "RIVA 128" },
119   { 0x12D20019, "RIVA 128ZX" },
120
121   { 0x10DE0020, "RIVA TNT" },
122
123   { 0x10DE0028, "RIVA TNT2" },
124   { 0x10DE002A, "Unknown TNT2" },
125   { 0x10DE002C, "Vanta" },
126   { 0x10DE0029, "RIVA TNT2 Ultra" },
127   { 0x10DE002D, "RIVA TNT2 Model 64" },
128
129   { 0x10DE00A0, "Aladdin TNT2" },
130
131   { 0x10DE0100, "GeForce 256" },
132   { 0x10DE0101, "GeForce DDR" },
133   { 0x10DE0103, "Quadro" },
134
135   { 0x10DE0110, "GeForce2 MX/MX 400" },
136   { 0x10DE0111, "GeForce2 MX 100/200" },
137   { 0x10DE0112, "GeForce2 Go" },
138   { 0x10DE0113, "Quadro2 MXR/EX/Go" },
139
140   { 0x10DE01A0, "GeForce2 Integrated GPU" },
141
142   { 0x10DE0150, "GeForce2 GTS" },
143   { 0x10DE0151, "GeForce2 Ti" },
144   { 0x10DE0152, "GeForce2 Ultra" },
145   { 0x10DE0153, "Quadro2 Pro" },
146
147   { 0x10DE0170, "GeForce4 MX 460" },
148   { 0x10DE0171, "GeForce4 MX 440" },
149   { 0x10DE0172, "GeForce4 MX 420" },
150   { 0x10DE0173, "GeForce4 MX 440-SE" },
151   { 0x10DE0174, "GeForce4 440 Go" },
152   { 0x10DE0175, "GeForce4 420 Go" },
153   { 0x10DE0176, "GeForce4 420 Go 32M" },
154   { 0x10DE0177, "GeForce4 460 Go" },
155   { 0x10DE0178, "Quadro4 550 XGL" },
156 #if defined(__powerpc__)
157   { 0x10DE0179, "GeForce4 MX (Mac)" },
158 #else
159   { 0x10DE0179, "GeForce4 440 Go 64M" },
160 #endif
161   { 0x10DE017A, "Quadro NVS" },
162   { 0x10DE017C, "Quadro4 500 GoGL" },
163   { 0x10DE017D, "GeForce4 410 Go 16M" },
164
165   { 0x10DE0181, "GeForce4 MX 440 with AGP8X" },
166   { 0x10DE0182, "GeForce4 MX 440SE with AGP8X" },
167   { 0x10DE0183, "GeForce4 MX 420 with AGP8X" },
168   { 0x10DE0185, "GeForce4 MX 4000" },
169   { 0x10DE0186, "GeForce4 448 Go" },
170   { 0x10DE0187, "GeForce4 488 Go" },
171   { 0x10DE0188, "Quadro4 580 XGL" },
172 #if defined(__powerpc__)
173   { 0x10DE0189, "GeForce4 MX with AGP8X (Mac)" },
174 #endif
175   { 0x10DE018A, "Quadro4 NVS 280 SD" },
176   { 0x10DE018B, "Quadro4 380 XGL" },
177   { 0x10DE018C, "Quadro NVS 50 PCI" },
178   { 0x10DE018D, "GeForce4 448 Go" },
179
180   { 0x10DE01F0, "GeForce4 MX Integrated GPU" },
181
182   { 0x10DE0200, "GeForce3" },
183   { 0x10DE0201, "GeForce3 Ti 200" },
184   { 0x10DE0202, "GeForce3 Ti 500" },
185   { 0x10DE0203, "Quadro DCC" },
186
187   { 0x10DE0250, "GeForce4 Ti 4600" },
188   { 0x10DE0251, "GeForce4 Ti 4400" },
189   { 0x10DE0253, "GeForce4 Ti 4200" },
190   { 0x10DE0258, "Quadro4 900 XGL" },
191   { 0x10DE0259, "Quadro4 750 XGL" },
192   { 0x10DE025B, "Quadro4 700 XGL" },
193
194   { 0x10DE0280, "GeForce4 Ti 4800" },
195   { 0x10DE0281, "GeForce4 Ti 4200 with AGP8X" },
196   { 0x10DE0282, "GeForce4 Ti 4800 SE" },
197   { 0x10DE0286, "GeForce4 4200 Go" },
198   { 0x10DE028C, "Quadro4 700 GoGL" },
199   { 0x10DE0288, "Quadro4 980 XGL" },
200   { 0x10DE0289, "Quadro4 780 XGL" },
201
202   { 0x10DE0301, "GeForce FX 5800 Ultra" },
203   { 0x10DE0302, "GeForce FX 5800" },
204   { 0x10DE0308, "Quadro FX 2000" },
205   { 0x10DE0309, "Quadro FX 1000" },
206
207   { 0x10DE0311, "GeForce FX 5600 Ultra" },
208   { 0x10DE0312, "GeForce FX 5600" },
209   { 0x10DE0314, "GeForce FX 5600XT" },
210   { 0x10DE031A, "GeForce FX Go5600" },
211   { 0x10DE031B, "GeForce FX Go5650" },
212   { 0x10DE031C, "Quadro FX Go700" },
213
214   { 0x10DE0320, "GeForce FX 5200" },
215   { 0x10DE0321, "GeForce FX 5200 Ultra" },
216   { 0x10DE0322, "GeForce FX 5200" },
217   { 0x10DE0323, "GeForce FX 5200LE" },
218   { 0x10DE0324, "GeForce FX Go5200" },
219   { 0x10DE0325, "GeForce FX Go5250" },
220   { 0x10DE0326, "GeForce FX 5500" },
221   { 0x10DE0327, "GeForce FX 5100" },
222   { 0x10DE0328, "GeForce FX Go5200 32M/64M" },
223 #if defined(__powerpc__)
224   { 0x10DE0329, "GeForce FX 5200 (Mac)" },
225 #endif
226   { 0x10DE032A, "Quadro NVS 55/280 PCI" },
227   { 0x10DE032B, "Quadro FX 500/600 PCI" },
228   { 0x10DE032C, "GeForce FX Go53xx Series" },
229   { 0x10DE032D, "GeForce FX Go5100" },
230
231   { 0x10DE0330, "GeForce FX 5900 Ultra" },
232   { 0x10DE0331, "GeForce FX 5900" },
233   { 0x10DE0332, "GeForce FX 5900XT" },
234   { 0x10DE0333, "GeForce FX 5950 Ultra" },
235   { 0x10DE0334, "GeForce FX 5900ZT" },
236   { 0x10DE0338, "Quadro FX 3000" },
237   { 0x10DE033F, "Quadro FX 700" },
238
239   { 0x10DE0341, "GeForce FX 5700 Ultra" },
240   { 0x10DE0342, "GeForce FX 5700" },
241   { 0x10DE0343, "GeForce FX 5700LE" },
242   { 0x10DE0344, "GeForce FX 5700VE" },
243   { 0x10DE0347, "GeForce FX Go5700" },
244   { 0x10DE0348, "GeForce FX Go5700" },
245   { 0x10DE034C, "Quadro FX Go1000" },
246   { 0x10DE034E, "Quadro FX 1100" },
247
248   { 0x10DE0040, "GeForce 6800 Ultra" },
249   { 0x10DE0041, "GeForce 6800" },
250   { 0x10DE0042, "GeForce 6800 LE" },
251   { 0x10DE0043, "GeForce 6800 XE" },
252   { 0x10DE0044, "GeForce 6800 XT" },
253   { 0x10DE0045, "GeForce 6800 GT" },
254   { 0x10DE0046, "GeForce 6800 GT" },
255   { 0x10DE0047, "GeForce 6800 GS" },
256   { 0x10DE0048, "GeForce 6800 XT" },
257   { 0x10DE004E, "Quadro FX 4000" },
258
259   { 0x10DE00C0, "GeForce 6800 GS" },
260   { 0x10DE00C1, "GeForce 6800" },
261   { 0x10DE00C2, "GeForce 6800 LE" },
262   { 0x10DE00C3, "GeForce 6800 XT" },
263   { 0x10DE00C8, "GeForce Go 6800" },
264   { 0x10DE00C9, "GeForce Go 6800 Ultra" },
265   { 0x10DE00CC, "Quadro FX Go1400" },
266   { 0x10DE00CD, "Quadro FX 3450/4000 SDI" },
267   { 0x10DE00CE, "Quadro FX 1400" },
268
269   { 0x10DE0140, "GeForce 6600 GT" },
270   { 0x10DE0141, "GeForce 6600" },
271   { 0x10DE0142, "GeForce 6600 LE" },
272   { 0x10DE0143, "GeForce 6600 VE" },
273   { 0x10DE0144, "GeForce Go 6600" },
274   { 0x10DE0145, "GeForce 6610 XL" },
275   { 0x10DE0146, "GeForce Go 6600 TE/6200 TE" },
276   { 0x10DE0147, "GeForce 6700 XL" },
277   { 0x10DE0148, "GeForce Go 6600" },
278   { 0x10DE0149, "GeForce Go 6600 GT" },
279   { 0x10DE014C, "Quadro FX 550" },
280   { 0x10DE014D, "Quadro FX 550" },
281   { 0x10DE014E, "Quadro FX 540" },
282   { 0x10DE014F, "GeForce 6200" },
283
284   { 0x10DE0160, "GeForce 6500" },
285   { 0x10DE0161, "GeForce 6200 TurboCache(TM)" },
286   { 0x10DE0162, "GeForce 6200SE TurboCache(TM)" },
287   { 0x10DE0163, "GeForce 6200 LE" },
288   { 0x10DE0164, "GeForce Go 6200" },
289   { 0x10DE0165, "Quadro NVS 285" },
290   { 0x10DE0166, "GeForce Go 6400" },
291   { 0x10DE0167, "GeForce Go 6200" },
292   { 0x10DE0168, "GeForce Go 6400" },
293   { 0x10DE0169, "GeForce 6250" },
294
295   { 0x10DE0211, "GeForce 6800" },
296   { 0x10DE0212, "GeForce 6800 LE" },
297   { 0x10DE0215, "GeForce 6800 GT" },
298   { 0x10DE0218, "GeForce 6800 XT" },
299
300   { 0x10DE0221, "GeForce 6200" },
301   { 0x10DE0222, "GeForce 6200 A-LE" },
302
303   { 0x10DE0090, "GeForce 7800 GTX" },
304   { 0x10DE0091, "GeForce 7800 GTX" },
305   { 0x10DE0092, "GeForce 7800 GT" },
306   { 0x10DE0093, "GeForce 7800 GS" },
307   { 0x10DE0095, "GeForce 7800 SLI" },
308   { 0x10DE0098, "GeForce Go 7800" },
309   { 0x10DE0099, "GeForce Go 7800 GTX" },
310   { 0x10DE009D, "Quadro FX 4500" },
311
312   { 0x10DE01D1, "GeForce 7300 LE" },
313   { 0x10DE01D3, "GeForce 7300 SE" },
314   { 0x10DE01D6, "GeForce Go 7200" },
315   { 0x10DE01D7, "GeForce Go 7300" },
316   { 0x10DE01D8, "GeForce Go 7400" },
317   { 0x10DE01D9, "GeForce Go 7400 GS" },
318   { 0x10DE01DA, "Quadro NVS 110M" },
319   { 0x10DE01DB, "Quadro NVS 120M" },
320   { 0x10DE01DC, "Quadro FX 350M" },
321   { 0x10DE01DD, "GeForce 7500 LE" },
322   { 0x10DE01DE, "Quadro FX 350" },
323   { 0x10DE01DF, "GeForce 7300 GS" },
324
325   { 0x10DE0391, "GeForce 7600 GT" },
326   { 0x10DE0392, "GeForce 7600 GS" },
327   { 0x10DE0393, "GeForce 7300 GT" },
328   { 0x10DE0394, "GeForce 7600 LE" },
329   { 0x10DE0395, "GeForce 7300 GT" },
330   { 0x10DE0397, "GeForce Go 7700" },
331   { 0x10DE0398, "GeForce Go 7600" },
332   { 0x10DE0399, "GeForce Go 7600 GT"},
333   { 0x10DE039A, "Quadro NVS 300M" },
334   { 0x10DE039B, "GeForce Go 7900 SE" },
335   { 0x10DE039C, "Quadro FX 550M" },
336   { 0x10DE039E, "Quadro FX 560" },
337
338   { 0x10DE0290, "GeForce 7900 GTX" },
339   { 0x10DE0291, "GeForce 7900 GT" },
340   { 0x10DE0292, "GeForce 7900 GS" },
341   { 0x10DE0298, "GeForce Go 7900 GS" },
342   { 0x10DE0299, "GeForce Go 7900 GTX" },
343   { 0x10DE029A, "Quadro FX 2500M" },
344   { 0x10DE029B, "Quadro FX 1500M" },
345   { 0x10DE029C, "Quadro FX 5500" },
346   { 0x10DE029D, "Quadro FX 3500" },
347   { 0x10DE029E, "Quadro FX 1500" },
348   { 0x10DE029F, "Quadro FX 4500 X2" },
349
350   { 0x10DE0240, "GeForce 6150" },
351   { 0x10DE0241, "GeForce 6150 LE" },
352   { 0x10DE0242, "GeForce 6100" },
353   { 0x10DE0244, "GeForce Go 6150" },
354   { 0x10DE0247, "GeForce Go 6100" },
355
356   {-1, NULL}
357 };
358
359
360 /*
361  * List of symbols from other modules that this module references.  This
362  * list is used to tell the loader that it is OK for symbols here to be
363  * unresolved providing that it hasn't been told that they haven't been
364  * told that they are essential via a call to xf86LoaderReqSymbols() or
365  * xf86LoaderReqSymLists().  The purpose is this is to avoid warnings about
366  * unresolved symbols that are not required.
367  */
368
369 static const char *vgahwSymbols[] = {
370     "vgaHWUnmapMem",
371     "vgaHWDPMSSet",
372     "vgaHWFreeHWRec",
373     "vgaHWGetHWRec",
374     "vgaHWGetIndex",
375     "vgaHWInit",
376     "vgaHWMapMem",
377     "vgaHWProtect",
378     "vgaHWRestore",
379     "vgaHWSave",
380     "vgaHWSaveScreen",
381     NULL
382 };
383
384 static const char *fbSymbols[] = {
385     "fbPictureInit",
386     "fbScreenInit",
387     NULL
388 };
389
390 static const char *xaaSymbols[] = {
391     "XAACopyROP",
392     "XAACreateInfoRec",
393     "XAADestroyInfoRec",
394     "XAAFallbackOps",
395     "XAAInit",
396     "XAAPatternROP",
397     NULL
398 };
399
400 static const char *exaSymbols[] = {
401     "exaDriverInit",
402     "exaOffscreenInit",
403     NULL
404 };
405
406 static const char *ramdacSymbols[] = {
407     "xf86CreateCursorInfoRec",
408     "xf86DestroyCursorInfoRec",
409     "xf86InitCursor",
410     NULL
411 };
412
413 static const char *ddcSymbols[] = {
414     "xf86PrintEDID",
415     "xf86DoEDID_DDC2",
416     "xf86SetDDCproperties",
417     NULL
418 };
419
420 static const char *vbeSymbols[] = {
421     "VBEInit",
422     "vbeFree",
423     "vbeDoEDID",
424     NULL
425 };
426
427 static const char *i2cSymbols[] = {
428     "xf86CreateI2CBusRec",
429     "xf86I2CBusInit",
430     NULL
431 };
432
433 static const char *shadowSymbols[] = {
434     "ShadowFBInit",
435     NULL
436 };
437
438 static const char *int10Symbols[] = {
439     "xf86FreeInt10",
440     "xf86InitInt10",
441     NULL
442 };
443
444 static const char *rivaSymbols[] = {
445    "RivaGetScrnInfoRec",
446    "RivaAvailableOptions",
447     NULL
448 };
449
450 const char *drmSymbols[] = {
451     "drmOpen", 
452     "drmAddBufs",
453     "drmAddMap",
454     "drmAgpAcquire",
455     "drmAgpVersionMajor",
456     "drmAgpVersionMinor",
457     "drmAgpAlloc",
458     "drmAgpBind",
459     "drmAgpEnable",
460     "drmAgpFree",
461     "drmAgpRelease",
462     "drmAgpUnbind",
463     "drmAuthMagic",
464     "drmCommandNone",
465     "drmCommandWrite",
466     "drmCommandWriteRead",
467     "drmCreateContext",
468     "drmCtlInstHandler",
469     "drmCtlUninstHandler",
470     "drmDestroyContext",
471     "drmFreeVersion",
472     "drmGetInterruptFromBusID",
473     "drmGetLibVersion",
474     "drmGetVersion",
475     NULL
476 };
477
478 const char *driSymbols[] = {
479     "DRICloseScreen",
480     "DRICreateInfoRec",
481     "DRIDestroyInfoRec",
482     "DRIFinishScreenInit",
483     "DRIGetSAREAPrivate",
484     "DRILock",
485     "DRIQueryVersion",
486     "DRIScreenInit",
487     "DRIUnlock",
488     "GlxSetVisualConfigs",
489     "DRICreatePCIBusID",
490     NULL
491 };
492
493
494 static MODULESETUPPROTO(nouveauSetup);
495
496 static XF86ModuleVersionInfo nouveauVersRec =
497 {
498     "nouveau",
499     MODULEVENDORSTRING,
500     MODINFOSTRING1,
501     MODINFOSTRING2,
502     XORG_VERSION_CURRENT,
503     NV_MAJOR_VERSION, NV_MINOR_VERSION, NV_PATCHLEVEL,
504     ABI_CLASS_VIDEODRV,                     /* This is a video driver */
505     ABI_VIDEODRV_VERSION,
506     MOD_CLASS_VIDEODRV,
507     {0,0,0,0}
508 };
509
510 _X_EXPORT XF86ModuleData nouveauModuleData = { &nouveauVersRec, nouveauSetup, NULL };
511
512
513 /*
514  * This is intentionally screen-independent.  It indicates the binding
515  * choice made in the first PreInit.
516  */
517 static int pix24bpp = 0;
518
519 static Bool
520 NVGetRec(ScrnInfoPtr pScrn)
521 {
522     /*
523      * Allocate an NVRec, and hook it into pScrn->driverPrivate.
524      * pScrn->driverPrivate is initialised to NULL, so we can check if
525      * the allocation has already been done.
526      */
527     if (pScrn->driverPrivate != NULL)
528         return TRUE;
529
530     pScrn->driverPrivate = xnfcalloc(sizeof(NVRec), 1);
531     /* Initialise it */
532
533     return TRUE;
534 }
535
536 static void
537 NVFreeRec(ScrnInfoPtr pScrn)
538 {
539     if (pScrn->driverPrivate == NULL)
540         return;
541     xfree(pScrn->driverPrivate);
542     pScrn->driverPrivate = NULL;
543 }
544
545
546 static pointer
547 nouveauSetup(pointer module, pointer opts, int *errmaj, int *errmin)
548 {
549     static Bool setupDone = FALSE;
550
551     /* This module should be loaded only once, but check to be sure. */
552
553     if (!setupDone) {
554         setupDone = TRUE;
555         xf86AddDriver(&NV, module, 0);
556
557         /*
558          * Modules that this driver always requires may be loaded here
559          * by calling LoadSubModule().
560          */
561         /*
562          * Tell the loader about symbols from other modules that this module
563          * might refer to.
564          */
565         LoaderRefSymLists(vgahwSymbols, xaaSymbols, exaSymbols, fbSymbols,
566 #ifdef XF86DRI
567                           drmSymbols, 
568 #endif
569                           ramdacSymbols, shadowSymbols, rivaSymbols,
570                           i2cSymbols, ddcSymbols, vbeSymbols,
571                           int10Symbols, NULL);
572
573         /*
574          * The return value must be non-NULL on success even though there
575          * is no TearDownProc.
576          */
577         return (pointer)1;
578     } else {
579         if (errmaj) *errmaj = LDR_ONCEONLY;
580         return NULL;
581     }
582 }
583
584 static const OptionInfoRec *
585 NVAvailableOptions(int chipid, int busid)
586 {
587 /*    if(chipid == 0x12D20018) {
588         if (!xf86LoadOneModule("riva128", NULL)) {
589             return NULL;
590         } else
591             return RivaAvailableOptions(chipid, busid);
592     }*/
593     
594     return NVOptions;
595 }
596
597 /* Mandatory */
598 static void
599 NVIdentify(int flags)
600 {
601     struct NvFamily *family;
602     size_t maxLen=0;
603
604     xf86DrvMsg(0, X_INFO, NV_NAME " driver " NV_DRIVER_DATE "\n");
605     xf86DrvMsg(0, X_INFO, NV_NAME " driver for NVIDIA chipset families :\n");
606
607     /* maximum length for alignment */
608     family = NVKnownFamilies;
609     while(family->name && family->chipset)
610     {
611         maxLen = max(maxLen, strlen(family->name));
612         family++;
613     }
614
615     /* display */
616     family = NVKnownFamilies;
617     while(family->name && family->chipset)
618     {
619         size_t len = strlen(family->name);
620         xf86ErrorF("\t%s", family->name);
621         while(len<maxLen+1)
622         {
623             xf86ErrorF(" ");
624             len++;
625         }
626         xf86ErrorF("(%s)\n", family->chipset);
627         family++;
628     }
629 }
630
631
632 static Bool
633 NVGetScrnInfoRec(PciChipsets *chips, int chip)
634 {
635     ScrnInfoPtr pScrn;
636
637     pScrn = xf86ConfigPciEntity(NULL, 0, chip,
638                                 chips, NULL, NULL, NULL,
639                                 NULL, NULL);
640
641     if(!pScrn) return FALSE;
642
643     pScrn->driverVersion    = NV_VERSION;
644     pScrn->driverName       = NV_DRIVER_NAME;
645     pScrn->name             = NV_NAME;
646
647     pScrn->Probe            = NVProbe;
648     pScrn->PreInit          = NVPreInit;
649     pScrn->ScreenInit       = NVScreenInit;
650     pScrn->SwitchMode       = NVSwitchMode;
651     pScrn->AdjustFrame      = NVAdjustFrame;
652     pScrn->EnterVT          = NVEnterVT;
653     pScrn->LeaveVT          = NVLeaveVT;
654     pScrn->FreeScreen       = NVFreeScreen;
655     pScrn->ValidMode        = NVValidMode;
656
657     return TRUE;
658 }
659
660 #define MAX_CHIPS MAXSCREENS
661
662
663 static CARD32 
664 NVGetPCIXpressChip (pciVideoPtr pVideo)
665 {
666     volatile CARD32 *regs;
667     CARD32 pciid, pcicmd;
668     PCITAG Tag = ((pciConfigPtr)(pVideo->thisCard))->tag;
669
670     pcicmd = pciReadLong(Tag, PCI_CMD_STAT_REG);
671     pciWriteLong(Tag, PCI_CMD_STAT_REG, pcicmd | PCI_CMD_MEM_ENABLE);
672     
673     regs = xf86MapPciMem(-1, VIDMEM_MMIO, Tag, pVideo->memBase[0], 0x2000);
674
675     pciid = regs[0x1800/4];
676
677     xf86UnMapVidMem(-1, (pointer)regs, 0x2000);
678
679     pciWriteLong(Tag, PCI_CMD_STAT_REG, pcicmd);
680
681     if((pciid & 0x0000ffff) == 0x000010DE) 
682        pciid = 0x10DE0000 | (pciid >> 16);
683     else 
684     if((pciid & 0xffff0000) == 0xDE100000) /* wrong endian */
685        pciid = 0x10DE0000 | ((pciid << 8) & 0x0000ff00) |
686                             ((pciid >> 8) & 0x000000ff);
687
688     return pciid;
689 }
690
691
692 /* Mandatory */
693 static Bool
694 NVProbe(DriverPtr drv, int flags)
695 {
696     int i;
697     GDevPtr *devSections;
698     int *usedChips;
699     SymTabRec NVChipsets[MAX_CHIPS + 1];
700     PciChipsets NVPciChipsets[MAX_CHIPS + 1];
701     pciVideoPtr *ppPci;
702     int numDevSections;
703     int numUsed;
704     Bool foundScreen = FALSE;
705
706
707     if ((numDevSections = xf86MatchDevice(NV_DRIVER_NAME, &devSections)) <= 0) 
708         return FALSE;  /* no matching device section */
709
710     if (!(ppPci = xf86GetPciVideoInfo())) 
711         return FALSE;  /* no PCI cards found */
712
713     numUsed = 0;
714
715     /* Create the NVChipsets and NVPciChipsets from found devices */
716     while (*ppPci && (numUsed < MAX_CHIPS)) {
717         if(((*ppPci)->vendor == PCI_VENDOR_NVIDIA_SGS) || 
718            ((*ppPci)->vendor == PCI_VENDOR_NVIDIA)) 
719         {
720             SymTabRec *nvchips = NVKnownChipsets;
721             int pciid = ((*ppPci)->vendor << 16) | (*ppPci)->chipType;
722             int token = pciid;
723
724             if(((token & 0xfff0) == CHIPSET_MISC_BRIDGED) ||
725                ((token & 0xfff0) == CHIPSET_G73_BRIDGED))
726             {
727                 token = NVGetPCIXpressChip(*ppPci);
728             }
729
730             while(nvchips->name) {
731                if(token == nvchips->token)
732                   break;
733                nvchips++;
734             }
735
736             if(nvchips->name) { /* found one */
737                NVChipsets[numUsed].token = pciid;
738                NVChipsets[numUsed].name = nvchips->name;
739                NVPciChipsets[numUsed].numChipset = pciid; 
740                NVPciChipsets[numUsed].PCIid = pciid;
741                NVPciChipsets[numUsed].resList = RES_SHARED_VGA;
742                numUsed++;
743             } else if ((*ppPci)->vendor == PCI_VENDOR_NVIDIA) {
744                /* look for a compatible devices which may be newer than 
745                   the NVKnownChipsets list above.  */
746                switch(token & 0xfff0) {
747                case CHIPSET_NV17:
748                case CHIPSET_NV18:
749                case CHIPSET_NV25:
750                case CHIPSET_NV28:
751                case CHIPSET_NV30:
752                case CHIPSET_NV31:
753                case CHIPSET_NV34:
754                case CHIPSET_NV35:
755                case CHIPSET_NV36:
756                case CHIPSET_NV40:
757                case CHIPSET_NV41:
758                case 0x0120:
759                case CHIPSET_NV43:
760                case CHIPSET_NV44:
761                case 0x0130:
762                case CHIPSET_G72:
763                case CHIPSET_G70:
764                case CHIPSET_NV45:
765                case CHIPSET_NV44A:
766                case 0x0230:
767                case CHIPSET_G71:
768                case CHIPSET_G73:
769                case CHIPSET_C512:
770                    NVChipsets[numUsed].token = pciid;
771                    NVChipsets[numUsed].name = "Unknown NVIDIA chip";
772                    NVPciChipsets[numUsed].numChipset = pciid;
773                    NVPciChipsets[numUsed].PCIid = pciid;
774                    NVPciChipsets[numUsed].resList = RES_SHARED_VGA;
775                    numUsed++;
776                    break;
777                default:  break;  /* we don't recognize it */
778                }
779             }
780         }
781         ppPci++;
782     }
783
784     /* terminate the list */
785     NVChipsets[numUsed].token = -1;
786     NVChipsets[numUsed].name = NULL; 
787     NVPciChipsets[numUsed].numChipset = -1;
788     NVPciChipsets[numUsed].PCIid = -1;
789     NVPciChipsets[numUsed].resList = RES_UNDEFINED;
790
791     numUsed = xf86MatchPciInstances(NV_NAME, 0, NVChipsets, NVPciChipsets,
792                                     devSections, numDevSections, drv,
793                                     &usedChips);
794                         
795     if (numUsed <= 0) 
796         return FALSE;
797
798     if (flags & PROBE_DETECT)
799         foundScreen = TRUE;
800     else for (i = 0; i < numUsed; i++) {
801         pciVideoPtr pPci;
802
803         pPci = xf86GetPciInfoForEntity(usedChips[i]);
804         if(NVGetScrnInfoRec(NVPciChipsets, usedChips[i])) 
805             foundScreen = TRUE;
806     }
807
808     xfree(devSections);
809     xfree(usedChips);
810
811     return foundScreen;
812 }
813
814 /* Usually mandatory */
815 Bool
816 NVSwitchMode(int scrnIndex, DisplayModePtr mode, int flags)
817 {
818     return NVModeInit(xf86Screens[scrnIndex], mode);
819 }
820
821 /*
822  * This function is used to initialize the Start Address - the first
823  * displayed location in the video memory.
824  */
825 /* Usually mandatory */
826 void 
827 NVAdjustFrame(int scrnIndex, int x, int y, int flags)
828 {
829     ScrnInfoPtr pScrn = xf86Screens[scrnIndex];
830     int startAddr;
831     NVPtr pNv = NVPTR(pScrn);
832     NVFBLayout *pLayout = &pNv->CurrentLayout;
833
834     startAddr = (((y*pLayout->displayWidth)+x)*(pLayout->bitsPerPixel/8));
835     startAddr += pNv->FB->offset;
836     NVSetStartAddress(pNv, startAddr);
837 }
838
839
840 /*
841  * This is called when VT switching back to the X server.  Its job is
842  * to reinitialise the video mode.
843  *
844  * We may wish to unmap video/MMIO memory too.
845  */
846
847 /* Mandatory */
848 static Bool
849 NVEnterVT(int scrnIndex, int flags)
850 {
851     ScrnInfoPtr pScrn = xf86Screens[scrnIndex];
852     NVPtr pNv = NVPTR(pScrn);
853
854     if (!NVModeInit(pScrn, pScrn->currentMode))
855         return FALSE;
856     NVAdjustFrame(scrnIndex, pScrn->frameX0, pScrn->frameY0, 0);
857
858     if(pNv->overlayAdaptor)
859         NVResetVideo(pScrn);
860     return TRUE;
861 }
862
863 /*
864  * This is called when VT switching away from the X server.  Its job is
865  * to restore the previous (text) mode.
866  *
867  * We may wish to remap video/MMIO memory too.
868  */
869
870 /* Mandatory */
871 static void
872 NVLeaveVT(int scrnIndex, int flags)
873 {
874     ScrnInfoPtr pScrn = xf86Screens[scrnIndex];
875     NVPtr pNv = NVPTR(pScrn);
876
877     NVSync(pScrn);
878     NVRestore(pScrn);
879     NVLockUnlock(pNv, 1);
880 }
881
882
883
884 static void 
885 NVBlockHandler (
886     int i, 
887     pointer blockData, 
888     pointer pTimeout,
889     pointer pReadmask
890 )
891 {
892     ScreenPtr     pScreen = screenInfo.screens[i];
893     ScrnInfoPtr   pScrnInfo = xf86Screens[i];
894     NVPtr         pNv = NVPTR(pScrnInfo);
895
896     if (pNv->DMAKickoffCallback)
897         (*pNv->DMAKickoffCallback)(pNv);
898     
899     pScreen->BlockHandler = pNv->BlockHandler;
900     (*pScreen->BlockHandler) (i, blockData, pTimeout, pReadmask);
901     pScreen->BlockHandler = NVBlockHandler;
902
903     if (pNv->VideoTimerCallback) 
904         (*pNv->VideoTimerCallback)(pScrnInfo, currentTime.milliseconds);
905
906 }
907
908
909 /*
910  * This is called at the end of each server generation.  It restores the
911  * original (text) mode.  It should also unmap the video memory, and free
912  * any per-generation data allocated by the driver.  It should finish
913  * by unwrapping and calling the saved CloseScreen function.
914  */
915
916 /* Mandatory */
917 static Bool
918 NVCloseScreen(int scrnIndex, ScreenPtr pScreen)
919 {
920     ScrnInfoPtr pScrn = xf86Screens[scrnIndex];
921     NVPtr pNv = NVPTR(pScrn);
922
923     if (pScrn->vtSema) {
924         pScrn->vtSema = FALSE;
925         NVSync(pScrn);
926         NVRestore(pScrn);
927         NVLockUnlock(pNv, 1);
928     }
929
930     NVUnmapMem(pScrn);
931     vgaHWUnmapMem(pScrn);
932     if (pNv->AccelInfoRec)
933         XAADestroyInfoRec(pNv->AccelInfoRec);
934     if (pNv->CursorInfoRec)
935         xf86DestroyCursorInfoRec(pNv->CursorInfoRec);
936     if (pNv->ShadowPtr)
937         xfree(pNv->ShadowPtr);
938     if (pNv->overlayAdaptor)
939         xfree(pNv->overlayAdaptor);
940     if (pNv->blitAdaptor)
941         xfree(pNv->blitAdaptor);
942
943     pScreen->CloseScreen = pNv->CloseScreen;
944     pScreen->BlockHandler = pNv->BlockHandler;
945     return (*pScreen->CloseScreen)(scrnIndex, pScreen);
946 }
947
948 /* Free up any persistent data structures */
949
950 /* Optional */
951 static void
952 NVFreeScreen(int scrnIndex, int flags)
953 {
954     /*
955      * This only gets called when a screen is being deleted.  It does not
956      * get called routinely at the end of a server generation.
957      */
958     if (xf86LoaderCheckSymbol("vgaHWFreeHWRec"))
959         vgaHWFreeHWRec(xf86Screens[scrnIndex]);
960     NVFreeRec(xf86Screens[scrnIndex]);
961 }
962
963
964 /* Checks if a mode is suitable for the selected chipset. */
965
966 /* Optional */
967 static ModeStatus
968 NVValidMode(int scrnIndex, DisplayModePtr mode, Bool verbose, int flags)
969 {
970     NVPtr pNv = NVPTR(xf86Screens[scrnIndex]);
971
972     if(pNv->fpWidth && pNv->fpHeight)
973       if((pNv->fpWidth < mode->HDisplay) || (pNv->fpHeight < mode->VDisplay))
974         return (MODE_PANEL);
975
976     return (MODE_OK);
977 }
978
979 static void
980 nvProbeDDC(ScrnInfoPtr pScrn, int index)
981 {
982     vbeInfoPtr pVbe;
983
984     if (xf86LoadSubModule(pScrn, "vbe")) {
985         pVbe = VBEInit(NULL,index);
986         ConfiguredMonitor = vbeDoEDID(pVbe, NULL);
987         vbeFree(pVbe);
988     }
989 }
990
991
992 Bool NVI2CInit(ScrnInfoPtr pScrn)
993 {
994     char *mod = "i2c";
995
996     if (xf86LoadSubModule(pScrn, mod)) {
997         xf86LoaderReqSymLists(i2cSymbols,NULL);
998
999         mod = "ddc";
1000         if(xf86LoadSubModule(pScrn, mod)) {
1001             xf86LoaderReqSymLists(ddcSymbols, NULL);
1002             return NVDACi2cInit(pScrn);
1003         } 
1004     }
1005
1006     xf86DrvMsg(pScrn->scrnIndex, X_WARNING,
1007               "Couldn't load %s module.  DDC probing can't be done\n", mod);
1008
1009     return FALSE;
1010 }
1011
1012 static Bool NVPreInitDRI(ScrnInfoPtr pScrn)
1013 {
1014         NVPtr pNv = NVPTR(pScrn);
1015
1016         if (!NVDRIGetVersion(pScrn))
1017                 return FALSE;
1018
1019         xf86DrvMsg(pScrn->scrnIndex, X_INFO,
1020                 "[dri] Found DRI library version %d.%d.%d and kernel"
1021                 " module version %d.%d.%d\n",
1022                 pNv->pLibDRMVersion->version_major,
1023                 pNv->pLibDRMVersion->version_minor,
1024                 pNv->pLibDRMVersion->version_patchlevel,
1025                 pNv->pKernelDRMVersion->version_major,
1026                 pNv->pKernelDRMVersion->version_minor,
1027                 pNv->pKernelDRMVersion->version_patchlevel);
1028
1029         return TRUE;
1030 }
1031
1032 /* Mandatory */
1033 Bool
1034 NVPreInit(ScrnInfoPtr pScrn, int flags)
1035 {
1036     NVPtr pNv;
1037     MessageType from;
1038     int i, max_width, max_height;
1039     ClockRangePtr clockRanges;
1040     const char *s;
1041     int config_mon_rates;
1042
1043     if (flags & PROBE_DETECT) {
1044         EntityInfoPtr pEnt = xf86GetEntityInfo(pScrn->entityList[0]);
1045
1046         if (!pEnt)
1047             return FALSE;
1048
1049         i = pEnt->index;
1050         xfree(pEnt);
1051
1052         nvProbeDDC(pScrn, i);
1053         return TRUE;
1054     }
1055
1056     /*
1057      * Note: This function is only called once at server startup, and
1058      * not at the start of each server generation.  This means that
1059      * only things that are persistent across server generations can
1060      * be initialised here.  xf86Screens[] is (pScrn is a pointer to one
1061      * of these).  Privates allocated using xf86AllocateScrnInfoPrivateIndex()  
1062      * are too, and should be used for data that must persist across
1063      * server generations.
1064      *
1065      * Per-generation data should be allocated with
1066      * AllocateScreenPrivateIndex() from the ScreenInit() function.
1067      */
1068
1069     /* Check the number of entities, and fail if it isn't one. */
1070     if (pScrn->numEntities != 1)
1071         return FALSE;
1072
1073     /* Allocate the NVRec driverPrivate */
1074     if (!NVGetRec(pScrn)) {
1075         return FALSE;
1076     }
1077     pNv = NVPTR(pScrn);
1078
1079     /* Get the entity, and make sure it is PCI. */
1080     pNv->pEnt = xf86GetEntityInfo(pScrn->entityList[0]);
1081     if (pNv->pEnt->location.type != BUS_PCI)
1082         return FALSE;
1083  
1084     /* Find the PCI info for this screen */
1085     pNv->PciInfo = xf86GetPciInfoForEntity(pNv->pEnt->index);
1086     pNv->PciTag = pciTag(pNv->PciInfo->bus, pNv->PciInfo->device,
1087                           pNv->PciInfo->func);
1088
1089     pNv->Primary = xf86IsPrimaryPci(pNv->PciInfo);
1090
1091     /* Initialize the card through int10 interface if needed */
1092     if (xf86LoadSubModule(pScrn, "int10")) {
1093         xf86LoaderReqSymLists(int10Symbols, NULL);
1094 #if !defined(__alpha__) && !defined(__powerpc__)
1095         xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Initializing int10\n");
1096         pNv->pInt = xf86InitInt10(pNv->pEnt->index);
1097 #endif
1098     }
1099    
1100     xf86SetOperatingState(resVgaIo, pNv->pEnt->index, ResUnusedOpr);
1101     xf86SetOperatingState(resVgaMem, pNv->pEnt->index, ResDisableOpr);
1102
1103     /* Set pScrn->monitor */
1104     pScrn->monitor = pScrn->confScreen->monitor;
1105
1106     /*
1107      * Set the Chipset and ChipRev, allowing config file entries to
1108      * override.
1109      */
1110     if (pNv->pEnt->device->chipset && *pNv->pEnt->device->chipset) {
1111         pScrn->chipset = pNv->pEnt->device->chipset;
1112         pNv->Chipset = xf86StringToToken(NVKnownChipsets, pScrn->chipset);
1113         from = X_CONFIG;
1114     } else if (pNv->pEnt->device->chipID >= 0) {
1115         pNv->Chipset = pNv->pEnt->device->chipID;
1116         pScrn->chipset = (char *)xf86TokenToString(NVKnownChipsets, 
1117                                                    pNv->Chipset);
1118         from = X_CONFIG;
1119         xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, "ChipID override: 0x%04X\n",
1120                    pNv->Chipset);
1121     } else {
1122         from = X_PROBED;
1123         pNv->Chipset = (pNv->PciInfo->vendor << 16) | pNv->PciInfo->chipType;
1124
1125         if(((pNv->Chipset & 0xfff0) == CHIPSET_MISC_BRIDGED) ||
1126            ((pNv->Chipset & 0xfff0) == CHIPSET_G73_BRIDGED))
1127         {
1128             pNv->Chipset = NVGetPCIXpressChip(pNv->PciInfo);
1129         }
1130
1131         pScrn->chipset = (char *)xf86TokenToString(NVKnownChipsets, 
1132                                                    pNv->Chipset);
1133         if(!pScrn->chipset)
1134           pScrn->chipset = "Unknown NVIDIA chipset";
1135     }
1136
1137     if (pNv->pEnt->device->chipRev >= 0) {
1138         pNv->ChipRev = pNv->pEnt->device->chipRev;
1139         xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, "ChipRev override: %d\n",
1140                    pNv->ChipRev);
1141     } else {
1142         pNv->ChipRev = pNv->PciInfo->chipRev;
1143     }
1144
1145     /*
1146      * This shouldn't happen because such problems should be caught in
1147      * NVProbe(), but check it just in case.
1148      */
1149     if (pScrn->chipset == NULL) {
1150         xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
1151                    "ChipID 0x%04X is not recognised\n", pNv->Chipset);
1152         xf86FreeInt10(pNv->pInt);
1153         return FALSE;
1154     }
1155     if (pNv->Chipset < 0) {
1156         xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
1157                    "Chipset \"%s\" is not recognised\n", pScrn->chipset);
1158         xf86FreeInt10(pNv->pInt);
1159         return FALSE;
1160     }
1161
1162     xf86DrvMsg(pScrn->scrnIndex, from, "Chipset: \"%s\"\n", pScrn->chipset);
1163
1164
1165     /*
1166      * The first thing we should figure out is the depth, bpp, etc.
1167      */
1168
1169     if (!xf86SetDepthBpp(pScrn, 0, 0, 0, Support32bppFb)) {
1170         xf86FreeInt10(pNv->pInt);
1171         return FALSE;
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                 xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
1183                     "Given depth (%d) is not supported by this driver\n",
1184                     pScrn->depth);
1185                 xf86FreeInt10(pNv->pInt);
1186                 return FALSE;
1187         }
1188     }
1189     xf86PrintDepthBpp(pScrn);
1190
1191     /* Get the depth24 pixmap format */
1192     if (pScrn->depth == 24 && pix24bpp == 0)
1193         pix24bpp = xf86GetBppFromDepth(pScrn, 24);
1194
1195     /*
1196      * This must happen after pScrn->display has been set because
1197      * xf86SetWeight references it.
1198      */
1199     if (pScrn->depth > 8) {
1200         /* The defaults are OK for us */
1201         rgb zeros = {0, 0, 0};
1202
1203         if (!xf86SetWeight(pScrn, zeros, zeros)) {
1204             xf86FreeInt10(pNv->pInt);
1205             return FALSE;
1206         }
1207     }
1208
1209     if (!xf86SetDefaultVisual(pScrn, -1)) {
1210         xf86FreeInt10(pNv->pInt);
1211         return FALSE;
1212     } else {
1213         /* We don't currently support DirectColor at > 8bpp */
1214         if (pScrn->depth > 8 && (pScrn->defaultVisual != TrueColor)) {
1215             xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Given default visual"
1216                        " (%s) is not supported at depth %d\n",
1217                        xf86GetVisualName(pScrn->defaultVisual), pScrn->depth);
1218             xf86FreeInt10(pNv->pInt);
1219             return FALSE;
1220         }
1221     }
1222
1223     /* The vgahw module should be loaded here when needed */
1224     if (!xf86LoadSubModule(pScrn, "vgahw")) {
1225         xf86FreeInt10(pNv->pInt);
1226         return FALSE;
1227     }
1228     
1229     xf86LoaderReqSymLists(vgahwSymbols, NULL);
1230
1231     /*
1232      * Allocate a vgaHWRec
1233      */
1234     if (!vgaHWGetHWRec(pScrn)) {
1235         xf86FreeInt10(pNv->pInt);
1236         return FALSE;
1237     }
1238     
1239     /* We use a programmable clock */
1240     pScrn->progClock = TRUE;
1241
1242     /* Collect all of the relevant option flags (fill in pScrn->options) */
1243     xf86CollectOptions(pScrn, NULL);
1244
1245     /* Process the options */
1246     if (!(pNv->Options = xalloc(sizeof(NVOptions))))
1247         return FALSE;
1248     memcpy(pNv->Options, NVOptions, sizeof(NVOptions));
1249     xf86ProcessOptions(pScrn->scrnIndex, pScrn->options, pNv->Options);
1250
1251     /* Set the bits per RGB for 8bpp mode */
1252     if (pScrn->depth == 8)
1253         pScrn->rgbBits = 8;
1254
1255     from = X_DEFAULT;
1256     pNv->HWCursor = TRUE;
1257     /*
1258      * The preferred method is to use the "hw cursor" option as a tri-state
1259      * option, with the default set above.
1260      */
1261     if (xf86GetOptValBool(pNv->Options, OPTION_HW_CURSOR, &pNv->HWCursor)) {
1262         from = X_CONFIG;
1263     }
1264     /* For compatibility, accept this too (as an override) */
1265     if (xf86ReturnOptValBool(pNv->Options, OPTION_SW_CURSOR, FALSE)) {
1266         from = X_CONFIG;
1267         pNv->HWCursor = FALSE;
1268     }
1269     xf86DrvMsg(pScrn->scrnIndex, from, "Using %s cursor\n",
1270                 pNv->HWCursor ? "HW" : "SW");
1271
1272     pNv->FpScale = TRUE;
1273     if (xf86GetOptValBool(pNv->Options, OPTION_FP_SCALE, &pNv->FpScale)) {
1274         xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, "Flat panel scaling %s\n",
1275                    pNv->FpScale ? "on" : "off");
1276     }
1277     if (xf86ReturnOptValBool(pNv->Options, OPTION_NOACCEL, FALSE)) {
1278         pNv->NoAccel = TRUE;
1279         xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, "Acceleration disabled\n");
1280     }
1281     if (xf86ReturnOptValBool(pNv->Options, OPTION_SHADOW_FB, FALSE)) {
1282         pNv->ShadowFB = TRUE;
1283         pNv->NoAccel = TRUE;
1284         xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, 
1285                 "Using \"Shadow Framebuffer\" - acceleration disabled\n");
1286     }
1287     if (!pNv->NoAccel) {
1288         from = X_DEFAULT;
1289         pNv->useEXA = TRUE;
1290         if((s = (char *)xf86GetOptValString(pNv->Options, OPTION_ACCELMETHOD))) {
1291             if(!xf86NameCmp(s,"XAA")) {
1292                 from = X_CONFIG;
1293                 pNv->useEXA = FALSE;
1294             } else if(!xf86NameCmp(s,"EXA")) {
1295                 from = X_CONFIG;
1296                 pNv->useEXA = TRUE;
1297             }
1298         }
1299         xf86DrvMsg(pScrn->scrnIndex, from, "Using %s acceleration method\n", pNv->useEXA ? "EXA" : "XAA");
1300     } else {
1301         xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, "Acceleration disabled\n");
1302     }
1303     
1304     pNv->Rotate = 0;
1305     pNv->RandRRotation = FALSE;
1306     if ((s = xf86GetOptValString(pNv->Options, OPTION_ROTATE))) {
1307       if(!xf86NameCmp(s, "CW")) {
1308         pNv->ShadowFB = TRUE;
1309         pNv->NoAccel = TRUE;
1310         pNv->HWCursor = FALSE;
1311         pNv->Rotate = 1;
1312         xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, 
1313                 "Rotating screen clockwise - acceleration disabled\n");
1314       } else
1315       if(!xf86NameCmp(s, "CCW")) {
1316         pNv->ShadowFB = TRUE;
1317         pNv->NoAccel = TRUE;
1318         pNv->HWCursor = FALSE;
1319         pNv->Rotate = -1;
1320         xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, 
1321                 "Rotating screen counter clockwise - acceleration disabled\n");
1322       } else
1323       if(!xf86NameCmp(s, "RandR")) {
1324 #ifdef RANDR
1325         pNv->ShadowFB = TRUE;
1326         pNv->NoAccel = TRUE;
1327         pNv->HWCursor = FALSE;
1328         pNv->RandRRotation = TRUE;
1329         xf86DrvMsg(pScrn->scrnIndex, X_CONFIG,
1330                 "Using RandR rotation - acceleration disabled\n");
1331 #else
1332         xf86DrvMsg(pScrn->scrnIndex, X_WARNING,
1333                 "This driver was not compiled with support for the Resize and "
1334                 "Rotate extension.  Cannot honor 'Option \"Rotate\" "
1335                 "\"RandR\"'.\n");
1336 #endif
1337       } else {
1338         xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, 
1339                 "\"%s\" is not a valid value for Option \"Rotate\"\n", s);
1340         xf86DrvMsg(pScrn->scrnIndex, X_INFO, 
1341                 "Valid options are \"CW\", \"CCW\", and \"RandR\"\n");
1342       }
1343     }
1344
1345     if(xf86GetOptValInteger(pNv->Options, OPTION_VIDEO_KEY, &(pNv->videoKey))) {
1346         xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, "video key set to 0x%x\n",
1347                                 pNv->videoKey);
1348     } else {
1349         pNv->videoKey =  (1 << pScrn->offset.red) | 
1350                           (1 << pScrn->offset.green) |
1351         (((pScrn->mask.blue >> pScrn->offset.blue) - 1) << pScrn->offset.blue); 
1352     }
1353
1354     if (xf86GetOptValBool(pNv->Options, OPTION_FLAT_PANEL, &(pNv->FlatPanel))) {
1355         xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, "forcing %s usage\n",
1356                    pNv->FlatPanel ? "DFP" : "CRTC");
1357     } else {
1358         pNv->FlatPanel = -1;   /* autodetect later */
1359     }
1360
1361     pNv->FPDither = FALSE;
1362     if (xf86GetOptValBool(pNv->Options, OPTION_FP_DITHER, &(pNv->FPDither))) 
1363         xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, "enabling flat panel dither\n");
1364
1365     if (xf86GetOptValInteger(pNv->Options, OPTION_CRTC_NUMBER,
1366                              &pNv->CRTCnumber)) 
1367     {
1368         if((pNv->CRTCnumber < 0) || (pNv->CRTCnumber > 1)) {
1369            pNv->CRTCnumber = -1;
1370            xf86DrvMsg(pScrn->scrnIndex, X_CONFIG, 
1371                       "Invalid CRTC number.  Must be 0 or 1\n");
1372         }
1373     } else {
1374         pNv->CRTCnumber = -1; /* autodetect later */
1375     }
1376
1377
1378     if (xf86GetOptValInteger(pNv->Options, OPTION_FP_TWEAK, 
1379                              &pNv->PanelTweak))
1380     {
1381         pNv->usePanelTweak = TRUE;
1382     } else {
1383         pNv->usePanelTweak = FALSE;
1384     }
1385     
1386     if (pNv->pEnt->device->MemBase != 0) {
1387         /* Require that the config file value matches one of the PCI values. */
1388         if (!xf86CheckPciMemBase(pNv->PciInfo, pNv->pEnt->device->MemBase)) {
1389             xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
1390                 "MemBase 0x%08lX doesn't match any PCI base register.\n",
1391                 pNv->pEnt->device->MemBase);
1392             xf86FreeInt10(pNv->pInt);
1393             NVFreeRec(pScrn);
1394             return FALSE;
1395         }
1396         pNv->VRAMPhysical = pNv->pEnt->device->MemBase;
1397         from = X_CONFIG;
1398     } else {
1399         if (pNv->PciInfo->memBase[1] != 0) {
1400             pNv->VRAMPhysical = pNv->PciInfo->memBase[1] & 0xff800000;
1401             from = X_PROBED;
1402         } else {
1403             xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
1404                            "No valid FB address in PCI config space\n");
1405             xf86FreeInt10(pNv->pInt);
1406             NVFreeRec(pScrn);
1407             return FALSE;
1408         }
1409     }
1410     xf86DrvMsg(pScrn->scrnIndex, from, "Linear framebuffer at 0x%lX\n",
1411                (unsigned long)pNv->VRAMPhysical);
1412
1413     if (pNv->pEnt->device->IOBase != 0) {
1414         /* Require that the config file value matches one of the PCI values. */
1415         if (!xf86CheckPciMemBase(pNv->PciInfo, pNv->pEnt->device->IOBase)) {
1416             xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
1417                 "IOBase 0x%08lX doesn't match any PCI base register.\n",
1418                 pNv->pEnt->device->IOBase);
1419             xf86FreeInt10(pNv->pInt);
1420             NVFreeRec(pScrn);
1421             return FALSE;
1422         }
1423         pNv->IOAddress = pNv->pEnt->device->IOBase;
1424         from = X_CONFIG;
1425     } else {
1426         if (pNv->PciInfo->memBase[0] != 0) {
1427             pNv->IOAddress = pNv->PciInfo->memBase[0] & 0xffffc000;
1428             from = X_PROBED;
1429         } else {
1430             xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
1431                         "No valid MMIO address in PCI config space\n");
1432             xf86FreeInt10(pNv->pInt);
1433             NVFreeRec(pScrn);
1434             return FALSE;
1435         }
1436     }
1437     xf86DrvMsg(pScrn->scrnIndex, from, "MMIO registers at 0x%lX\n",
1438                (unsigned long)pNv->IOAddress);
1439      
1440     if (xf86RegisterResources(pNv->pEnt->index, NULL, ResExclusive)) {
1441         xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
1442                 "xf86RegisterResources() found resource conflicts\n");
1443         xf86FreeInt10(pNv->pInt);
1444         NVFreeRec(pScrn);
1445         return FALSE;
1446     }
1447
1448     switch (pNv->Chipset & 0x0ff0) {
1449     case CHIPSET_NV03:   /* Riva128 */
1450          pNv->Architecture =  NV_ARCH_03;
1451          break;
1452     case CHIPSET_NV04:   /* TNT/TNT2 */
1453          pNv->Architecture =  NV_ARCH_04;
1454          break;
1455     case CHIPSET_NV10:   /* GeForce 256 */
1456     case CHIPSET_NV11:   /* GeForce2 MX */
1457     case CHIPSET_NV15:   /* GeForce2 */
1458     case CHIPSET_NV17:   /* GeForce4 MX */
1459     case CHIPSET_NV18:   /* GeForce4 MX (8x AGP) */
1460     case CHIPSET_NFORCE: /* nForce */
1461     case CHIPSET_NFORCE2:/* nForce2 */
1462          pNv->Architecture =  NV_ARCH_10;
1463          break;
1464     case CHIPSET_NV20:   /* GeForce3 */
1465     case CHIPSET_NV25:   /* GeForce4 Ti */
1466     case CHIPSET_NV28:   /* GeForce4 Ti (8x AGP) */
1467          pNv->Architecture =  NV_ARCH_20;
1468          break;
1469     case CHIPSET_NV30:   /* GeForceFX 5800 */
1470     case CHIPSET_NV31:   /* GeForceFX 5600 */
1471     case CHIPSET_NV34:   /* GeForceFX 5200 */
1472     case CHIPSET_NV35:   /* GeForceFX 5900 */
1473     case CHIPSET_NV36:   /* GeForceFX 5700 */
1474          pNv->Architecture =  NV_ARCH_30;
1475          break;
1476     case CHIPSET_NV40:   /* GeForce 6800 */
1477     case CHIPSET_NV41:   /* GeForce 6800 */
1478     case 0x0120:   /* GeForce 6800 */
1479     case CHIPSET_NV43:   /* GeForce 6600 */
1480     case CHIPSET_NV44:   /* GeForce 6200 */
1481     case CHIPSET_G72:   /* GeForce 7200, 7300, 7400 */
1482     case CHIPSET_G70:   /* GeForce 7800 */
1483     case CHIPSET_NV45:   /* GeForce 6800 */
1484     case CHIPSET_NV44A:   /* GeForce 6200 */
1485     case CHIPSET_G71:   /* GeForce 7900 */
1486     case CHIPSET_G73:   /* GeForce 7600 */
1487     case CHIPSET_C51:   /* GeForce 6100 */
1488     case CHIPSET_C512: /* Geforce 6100 (nForce 4xx) */
1489          pNv->Architecture =  NV_ARCH_40;
1490          break;
1491     default:           /* Unknown, probably >=NV40 */
1492          pNv->Architecture =  NV_ARCH_40;
1493          break;
1494     }
1495
1496     pNv->alphaCursor = (pNv->Architecture >= NV_ARCH_10) &&
1497                        ((pNv->Chipset & 0x0ff0) != CHIPSET_NV10);
1498
1499     if (NVPreInitDRI(pScrn) == FALSE) {
1500             xf86FreeInt10(pNv->pInt);
1501             return FALSE;
1502     }
1503
1504     if ((pScrn->monitor->nHsync == 0) && 
1505         (pScrn->monitor->nVrefresh == 0))
1506         config_mon_rates = FALSE;
1507     else
1508         config_mon_rates = TRUE;
1509
1510     NVCommonSetup(pScrn);
1511
1512     pScrn->videoRam = pNv->RamAmountKBytes;
1513     xf86DrvMsg(pScrn->scrnIndex, X_PROBED, "VideoRAM: %d kBytes\n",
1514                pScrn->videoRam);
1515         
1516         pNv->VRAMPhysicalSize = pScrn->videoRam * 1024;
1517
1518     /*
1519      * If the driver can do gamma correction, it should call xf86SetGamma()
1520      * here.
1521      */
1522
1523     {
1524         Gamma zeros = {0.0, 0.0, 0.0};
1525
1526         if (!xf86SetGamma(pScrn, zeros)) {
1527             xf86FreeInt10(pNv->pInt);
1528             return FALSE;
1529         }
1530     }
1531
1532     /*
1533      * Setup the ClockRanges, which describe what clock ranges are available,
1534      * and what sort of modes they can be used for.
1535      */
1536
1537     clockRanges = xnfcalloc(sizeof(ClockRange), 1);
1538     clockRanges->next = NULL;
1539     clockRanges->minClock = pNv->MinVClockFreqKHz;
1540     clockRanges->maxClock = pNv->MaxVClockFreqKHz;
1541     clockRanges->clockIndex = -1;               /* programmable */
1542     clockRanges->doubleScanAllowed = TRUE;
1543     if((pNv->Architecture == NV_ARCH_20) ||
1544          ((pNv->Architecture == NV_ARCH_10) && 
1545            ((pNv->Chipset & 0x0ff0) != CHIPSET_NV10) &&
1546            ((pNv->Chipset & 0x0ff0) != CHIPSET_NV15)))
1547     {
1548        /* HW is broken */
1549        clockRanges->interlaceAllowed = FALSE;
1550     } else {
1551        clockRanges->interlaceAllowed = TRUE;
1552     }
1553
1554     if(pNv->FlatPanel == 1) {
1555        clockRanges->interlaceAllowed = FALSE;
1556        clockRanges->doubleScanAllowed = FALSE;
1557     }
1558
1559     if(pNv->Architecture < NV_ARCH_10) {
1560        max_width = (pScrn->bitsPerPixel > 16) ? 2032 : 2048;
1561        max_height = 2048;
1562     } else {
1563        max_width = (pScrn->bitsPerPixel > 16) ? 4080 : 4096;
1564        max_height = 4096;
1565     }
1566
1567     /* If DFP, add a modeline corresponding to its panel size */
1568     if (pNv->FlatPanel && !pNv->Television && pNv->fpWidth && pNv->fpHeight) {
1569         DisplayModePtr Mode;
1570
1571         Mode = xnfcalloc(1, sizeof(DisplayModeRec));
1572         Mode = xf86CVTMode(pNv->fpWidth, pNv->fpHeight, 60.00, TRUE, FALSE);
1573         Mode->type = M_T_DRIVER;
1574         pScrn->monitor->Modes = xf86ModesAdd(pScrn->monitor->Modes, Mode);
1575
1576         if (!config_mon_rates) {
1577             if (!Mode->HSync)
1578                 Mode->HSync = ((float) Mode->Clock ) / ((float) Mode->HTotal);
1579             if (!Mode->VRefresh)
1580                 Mode->VRefresh = (1000.0 * ((float) Mode->Clock)) /
1581                     ((float) (Mode->HTotal * Mode->VTotal));
1582
1583             if (Mode->HSync < pScrn->monitor->hsync[0].lo)
1584                 pScrn->monitor->hsync[0].lo = Mode->HSync;
1585             if (Mode->HSync > pScrn->monitor->hsync[0].hi)
1586                 pScrn->monitor->hsync[0].hi = Mode->HSync;
1587             if (Mode->VRefresh < pScrn->monitor->vrefresh[0].lo)
1588                 pScrn->monitor->vrefresh[0].lo = Mode->VRefresh;
1589             if (Mode->VRefresh > pScrn->monitor->vrefresh[0].hi)
1590                 pScrn->monitor->vrefresh[0].hi = Mode->VRefresh;
1591
1592             pScrn->monitor->nHsync = 1;
1593             pScrn->monitor->nVrefresh = 1;
1594         }
1595     }
1596
1597     /*
1598      * xf86ValidateModes will check that the mode HTotal and VTotal values
1599      * don't exceed the chipset's limit if pScrn->maxHValue and
1600      * pScrn->maxVValue are set.  Since our NVValidMode() already takes
1601      * care of this, we don't worry about setting them here.
1602      */
1603     i = xf86ValidateModes(pScrn, pScrn->monitor->Modes,
1604                           pScrn->display->modes, clockRanges,
1605                           NULL, 256, max_width,
1606                           512, 128, max_height,
1607                           pScrn->display->virtualX,
1608                           pScrn->display->virtualY,
1609                           pNv->VRAMPhysicalSize / 2,
1610                           LOOKUP_BEST_REFRESH);
1611
1612     if (i == -1) {
1613         xf86FreeInt10(pNv->pInt);
1614         NVFreeRec(pScrn);
1615         return FALSE;
1616     }
1617
1618     /* Prune the modes marked as invalid */
1619     xf86PruneDriverModes(pScrn);
1620
1621     if (i == 0 || pScrn->modes == NULL) {
1622         xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "No valid modes found\n");
1623         xf86FreeInt10(pNv->pInt);
1624         NVFreeRec(pScrn);
1625         return FALSE;
1626     }
1627
1628     /*
1629      * Set the CRTC parameters for all of the modes based on the type
1630      * of mode, and the chipset's interlace requirements.
1631      *
1632      * Calling this is required if the mode->Crtc* values are used by the
1633      * driver and if the driver doesn't provide code to set them.  They
1634      * are not pre-initialised at all.
1635      */
1636     xf86SetCrtcForModes(pScrn, 0);
1637
1638     /* Set the current mode to the first in the list */
1639     pScrn->currentMode = pScrn->modes;
1640
1641     /* Print the list of modes being used */
1642     xf86PrintModes(pScrn);
1643
1644     /* Set display resolution */
1645     xf86SetDpi(pScrn, 0, 0);
1646
1647
1648     /*
1649      * XXX This should be taken into account in some way in the mode valdation
1650      * section.
1651      */
1652
1653     if (xf86LoadSubModule(pScrn, "fb") == NULL) {
1654         xf86FreeInt10(pNv->pInt);
1655         NVFreeRec(pScrn);
1656         return FALSE;
1657     }
1658
1659     xf86LoaderReqSymLists(fbSymbols, NULL);
1660     
1661     /* Load XAA if needed */
1662     if (!pNv->NoAccel) {
1663         if (!xf86LoadSubModule(pScrn, pNv->useEXA ? "exa" : "xaa")) {
1664             xf86FreeInt10(pNv->pInt);
1665             NVFreeRec(pScrn);
1666             return FALSE;
1667         }
1668         xf86LoaderReqSymLists(xaaSymbols, NULL);
1669     }
1670
1671     /* Load ramdac if needed */
1672     if (pNv->HWCursor) {
1673         if (!xf86LoadSubModule(pScrn, "ramdac")) {
1674             xf86FreeInt10(pNv->pInt);
1675             NVFreeRec(pScrn);
1676             return FALSE;
1677         }
1678         xf86LoaderReqSymLists(ramdacSymbols, NULL);
1679     }
1680
1681     /* Load shadowfb if needed */
1682     if (pNv->ShadowFB) {
1683         if (!xf86LoadSubModule(pScrn, "shadowfb")) {
1684             xf86FreeInt10(pNv->pInt);
1685             NVFreeRec(pScrn);
1686             return FALSE;
1687         }
1688         xf86LoaderReqSymLists(shadowSymbols, NULL);
1689     }
1690
1691     pNv->CurrentLayout.bitsPerPixel = pScrn->bitsPerPixel;
1692     pNv->CurrentLayout.depth = pScrn->depth;
1693     pNv->CurrentLayout.displayWidth = pScrn->displayWidth;
1694     pNv->CurrentLayout.weight.red = pScrn->weight.red;
1695     pNv->CurrentLayout.weight.green = pScrn->weight.green;
1696     pNv->CurrentLayout.weight.blue = pScrn->weight.blue;
1697     pNv->CurrentLayout.mode = pScrn->currentMode;
1698
1699     xf86FreeInt10(pNv->pInt);
1700
1701     pNv->pInt = NULL;
1702     return TRUE;
1703 }
1704
1705
1706 /*
1707  * Map the framebuffer and MMIO memory.
1708  */
1709
1710 static Bool
1711 NVMapMem(ScrnInfoPtr pScrn)
1712 {
1713         NVPtr pNv = NVPTR(pScrn);
1714
1715         pNv->FB = NVAllocateMemory(pNv, NOUVEAU_MEM_FB, pNv->VRAMPhysicalSize/2);
1716         if (!pNv->FB) {
1717                 ErrorF("Failed to allocate memory for framebuffer!\n");
1718                 return FALSE;
1719         }
1720         xf86DrvMsg(pScrn->scrnIndex, X_INFO,
1721                    "Allocated %dMiB VRAM for framebuffer + offscreen pixmaps\n",
1722                    (unsigned int)(pNv->FB->size >> 20));
1723
1724         /*XXX: have to get these after we've allocated something, otherwise
1725          *     they're uninitialised in the DRM!
1726          */
1727         pNv->VRAMSize     = NVDRMGetParam(pNv, NOUVEAU_GETPARAM_FB_SIZE);
1728         pNv->VRAMPhysical = NVDRMGetParam(pNv, NOUVEAU_GETPARAM_FB_PHYSICAL);
1729         pNv->AGPSize      = NVDRMGetParam(pNv, NOUVEAU_GETPARAM_AGP_SIZE);
1730         pNv->AGPPhysical  = NVDRMGetParam(pNv, NOUVEAU_GETPARAM_AGP_PHYSICAL);
1731         if ( ! pNv->AGPSize ) /*if no AGP*/
1732                 /*use PCI*/
1733                 pNv->SGPhysical  = NVDRMGetParam(pNv, NOUVEAU_GETPARAM_PCI_PHYSICAL);
1734
1735         int gart_scratch_size;
1736
1737         if (pNv->AGPSize) {
1738                 xf86DrvMsg(pScrn->scrnIndex, X_INFO,
1739                            "AGPGART: %dMiB available\n",
1740                            (unsigned int)(pNv->AGPSize >> 20));
1741
1742                 if (pNv->AGPSize > (16*1024*1024))
1743                         gart_scratch_size = 16*1024*1024;
1744                 else
1745                         gart_scratch_size = pNv->AGPSize;
1746
1747                 }
1748         else {
1749
1750                 gart_scratch_size = (4 << 20) - (1 << 18) ;
1751                 xf86DrvMsg(pScrn->scrnIndex, X_INFO,
1752                            "GART: PCI DMA - using %dKiB\n", gart_scratch_size >> 10);
1753                 
1754         }
1755
1756         /*The DRM allocates AGP memory, PCI as a fallback */
1757         pNv->GARTScratch = NVAllocateMemory(pNv, NOUVEAU_MEM_AGP | NOUVEAU_MEM_PCI_ACCEPTABLE,
1758                                                         gart_scratch_size);
1759         if (!pNv->GARTScratch) {
1760                 xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
1761                            "Unable to allocate GART memory\n");
1762         } else {
1763                 xf86DrvMsg(pScrn->scrnIndex, X_INFO,
1764                            "GART: mapped %dMiB at %p, offset is %d\n",
1765                            (unsigned int)(pNv->GARTScratch->size >> 20),
1766                            pNv->GARTScratch->map, pNv->GARTScratch->offset);
1767         }
1768
1769
1770         pNv->Cursor = NVAllocateMemory(pNv, NOUVEAU_MEM_FB, 64*1024);
1771         if (!pNv->Cursor) {
1772                 ErrorF("Failed to allocate memory for hardware cursor\n");
1773                 return FALSE;
1774         }
1775
1776         pNv->ScratchBuffer = NVAllocateMemory(pNv, NOUVEAU_MEM_FB,
1777                         pNv->Architecture <NV_ARCH_10 ? 8192 : 16384);
1778         if (!pNv->ScratchBuffer) {
1779                 ErrorF("Failed to allocate memory for scratch buffer\n");
1780                 return FALSE;
1781         }
1782
1783     return TRUE;
1784 }
1785
1786 /*
1787  * Unmap the framebuffer and MMIO memory.
1788  */
1789
1790 static Bool
1791 NVUnmapMem(ScrnInfoPtr pScrn)
1792 {
1793         NVPtr pNv = NVPTR(pScrn);
1794
1795         NVFreeMemory(pNv, pNv->FB);
1796         NVFreeMemory(pNv, pNv->ScratchBuffer);
1797         NVFreeMemory(pNv, pNv->Cursor);
1798
1799     return TRUE;
1800 }
1801
1802
1803 /*
1804  * Initialise a new mode. 
1805  */
1806
1807 static Bool
1808 NVModeInit(ScrnInfoPtr pScrn, DisplayModePtr mode)
1809 {
1810     vgaHWPtr hwp = VGAHWPTR(pScrn);
1811     vgaRegPtr vgaReg;
1812     NVPtr pNv = NVPTR(pScrn);
1813     NVRegPtr nvReg;
1814
1815     /* Initialise the ModeReg values */
1816     if (!vgaHWInit(pScrn, mode))
1817         return FALSE;
1818     pScrn->vtSema = TRUE;
1819
1820     vgaReg = &hwp->ModeReg;
1821     nvReg = &pNv->ModeReg;
1822
1823     if(!NVDACInit(pScrn, mode))
1824         return FALSE;
1825
1826     NVLockUnlock(pNv, 0);
1827     if(pNv->twoHeads) {
1828         nvWriteVGA(pNv, NV_VGA_CRTCX_OWNER, nvReg->crtcOwner);
1829         NVLockUnlock(pNv, 0);
1830     }
1831
1832     /* Program the registers */
1833     vgaHWProtect(pScrn, TRUE);
1834
1835     NVDACRestore(pScrn, vgaReg, nvReg, FALSE);
1836
1837 #if X_BYTE_ORDER == X_BIG_ENDIAN
1838     /* turn on LFB swapping */
1839     {
1840         unsigned char tmp;
1841
1842         tmp = nvReadVGA(pNv, NV_VGA_CRTCX_SWAPPING);
1843         tmp |= (1 << 7);
1844         nvWriteVGA(pNv, NV_VGA_CRTCX_SWAPPING, tmp);
1845     }
1846 #endif
1847
1848     NVResetGraphics(pScrn);
1849
1850     vgaHWProtect(pScrn, FALSE);
1851
1852     pNv->CurrentLayout.mode = mode;
1853
1854     return TRUE;
1855 }
1856
1857 /*
1858  * Restore the initial (text) mode.
1859  */
1860 static void 
1861 NVRestore(ScrnInfoPtr pScrn)
1862 {
1863     vgaHWPtr hwp = VGAHWPTR(pScrn);
1864     vgaRegPtr vgaReg = &hwp->SavedReg;
1865     NVPtr pNv = NVPTR(pScrn);
1866     NVRegPtr nvReg = &pNv->SavedReg;
1867
1868     NVLockUnlock(pNv, 0);
1869
1870     if(pNv->twoHeads) {
1871         nvWriteVGA(pNv, NV_VGA_CRTCX_OWNER, pNv->CRTCnumber * 0x3);
1872         NVLockUnlock(pNv, 0);
1873     }
1874
1875     /* Only restore text mode fonts/text for the primary card */
1876     vgaHWProtect(pScrn, TRUE);
1877     NVDACRestore(pScrn, vgaReg, nvReg, pNv->Primary);
1878     if(pNv->twoHeads) {
1879         nvWriteVGA(pNv, NV_VGA_CRTCX_OWNER, pNv->vtOWNER);
1880     }
1881     vgaHWProtect(pScrn, FALSE);
1882 }
1883
1884 static void NVBacklightEnable(NVPtr pNv,  Bool on)
1885 {
1886     /* This is done differently on each laptop.  Here we
1887        define the ones we know for sure. */
1888
1889 #if defined(__powerpc__)
1890     if((pNv->Chipset == 0x10DE0179) || 
1891        (pNv->Chipset == 0x10DE0189) || 
1892        (pNv->Chipset == 0x10DE0329))
1893     {
1894        /* NV17,18,34 Apple iMac, iBook, PowerBook */
1895       CARD32 tmp_pmc, tmp_pcrt;
1896       tmp_pmc = nvReadMC(pNv, 0x10F0) & 0x7FFFFFFF;
1897       tmp_pcrt = nvReadCRTC0(pNv, NV_CRTC_081C) & 0xFFFFFFFC;
1898       if(on) {
1899           tmp_pmc |= (1 << 31);
1900           tmp_pcrt |= 0x1;
1901       }
1902       nvWriteMC(pNv, 0x10F0, tmp_pmc);
1903       nvWriteCRTC0(pNv, NV_CRTC_081C, tmp_pcrt);
1904     }
1905 #endif
1906     
1907     if(pNv->LVDS) {
1908        if(pNv->twoHeads && ((pNv->Chipset & 0x0ff0) != CHIPSET_NV11)) {
1909            nvWriteMC(pNv, 0x130C, on ? 3 : 7);
1910        }
1911     } else {
1912        CARD32 fpcontrol;
1913
1914        fpcontrol = nvReadCurRAMDAC(pNv, 0x848) & 0xCfffffCC;
1915
1916        /* cut the TMDS output */
1917        if(on) fpcontrol |= pNv->fpSyncs;
1918        else fpcontrol |= 0x20000022;
1919
1920        nvWriteCurRAMDAC(pNv, 0x0848, fpcontrol);
1921     }
1922 }
1923
1924 static void
1925 NVDPMSSetLCD(ScrnInfoPtr pScrn, int PowerManagementMode, int flags)
1926 {
1927   NVPtr pNv = NVPTR(pScrn);
1928
1929   if (!pScrn->vtSema) return;
1930
1931   vgaHWDPMSSet(pScrn, PowerManagementMode, flags);
1932
1933   switch (PowerManagementMode) {
1934   case DPMSModeStandby:  /* HSync: Off, VSync: On */
1935   case DPMSModeSuspend:  /* HSync: On, VSync: Off */
1936   case DPMSModeOff:      /* HSync: Off, VSync: Off */
1937     NVBacklightEnable(pNv, 0);
1938     break;
1939   case DPMSModeOn:       /* HSync: On, VSync: On */
1940     NVBacklightEnable(pNv, 1);
1941   default:
1942     break;
1943   }
1944 }
1945
1946
1947 static void
1948 NVDPMSSet(ScrnInfoPtr pScrn, int PowerManagementMode, int flags)
1949 {
1950   unsigned char crtc1A;
1951   vgaHWPtr hwp = VGAHWPTR(pScrn);
1952
1953   if (!pScrn->vtSema) return;
1954
1955   crtc1A = hwp->readCrtc(hwp, 0x1A) & ~0xC0;
1956
1957   switch (PowerManagementMode) {
1958   case DPMSModeStandby:  /* HSync: Off, VSync: On */
1959     crtc1A |= 0x80;
1960     break;
1961   case DPMSModeSuspend:  /* HSync: On, VSync: Off */
1962     crtc1A |= 0x40;
1963     break;
1964   case DPMSModeOff:      /* HSync: Off, VSync: Off */
1965     crtc1A |= 0xC0;
1966     break;
1967   case DPMSModeOn:       /* HSync: On, VSync: On */
1968   default:
1969     break;
1970   }
1971
1972   /* vgaHWDPMSSet will merely cut the dac output */
1973   vgaHWDPMSSet(pScrn, PowerManagementMode, flags);
1974
1975   hwp->writeCrtc(hwp, 0x1A, crtc1A);
1976 }
1977
1978
1979 /* Mandatory */
1980
1981 /* This gets called at the start of each server generation */
1982
1983 static Bool
1984 NVScreenInit(int scrnIndex, ScreenPtr pScreen, int argc, char **argv)
1985 {
1986     ScrnInfoPtr pScrn;
1987     vgaHWPtr hwp;
1988     NVPtr pNv;
1989     int ret;
1990     VisualPtr visual;
1991     unsigned char *FBStart;
1992     int width, height, displayWidth, offscreenHeight, shadowHeight;
1993     BoxRec AvailFBArea;
1994
1995     /* 
1996      * First get the ScrnInfoRec
1997      */
1998     pScrn = xf86Screens[pScreen->myNum];
1999
2000     hwp = VGAHWPTR(pScrn);
2001     pNv = NVPTR(pScrn);
2002
2003     /* Map the VGA memory when the primary video */
2004     if (pNv->Primary) {
2005         hwp->MapSize = 0x10000;
2006         if (!vgaHWMapMem(pScrn))
2007             return FALSE;
2008     }
2009
2010         /* First init DRI/DRM */
2011         if (!NVDRIScreenInit(pScrn))
2012                 return FALSE;
2013
2014         /* Allocate and map memory areas we need */
2015         if (!NVMapMem(pScrn))
2016                 return FALSE;
2017
2018         /* Init DRM - Alloc FIFO */
2019         if (!NVInitDma(pScrn))
2020                 return FALSE;
2021
2022         /* setup graphics objects */
2023         if (!NVAccelCommonInit(pScrn))
2024                 return FALSE;
2025
2026         /* Save the current state */
2027         NVSave(pScrn);
2028         /* Initialise the first mode */
2029         if (!NVModeInit(pScrn, pScrn->currentMode)) {
2030             return FALSE;
2031     }
2032
2033     /* Darken the screen for aesthetic reasons and set the viewport */
2034     NVSaveScreen(pScreen, SCREEN_SAVER_ON);
2035     pScrn->AdjustFrame(scrnIndex, pScrn->frameX0, pScrn->frameY0, 0);
2036
2037     /*
2038      * The next step is to setup the screen's visuals, and initialise the
2039      * framebuffer code.  In cases where the framebuffer's default
2040      * choices for things like visual layouts and bits per RGB are OK,
2041      * this may be as simple as calling the framebuffer's ScreenInit()
2042      * function.  If not, the visuals will need to be setup before calling
2043      * a fb ScreenInit() function and fixed up after.
2044      *
2045      * For most PC hardware at depths >= 8, the defaults that fb uses
2046      * are not appropriate.  In this driver, we fixup the visuals after.
2047      */
2048
2049     /*
2050      * Reset the visual list.
2051      */
2052     miClearVisualTypes();
2053
2054     /* Setup the visuals we support. */
2055
2056     if (!miSetVisualTypes(pScrn->depth, 
2057                           miGetDefaultVisualMask(pScrn->depth), 8,
2058                           pScrn->defaultVisual))
2059           return FALSE;
2060     if (!miSetPixmapDepths ()) return FALSE;
2061
2062     /*
2063      * Call the framebuffer layer's ScreenInit function, and fill in other
2064      * pScreen fields.
2065      */
2066
2067     width = pScrn->virtualX;
2068     height = pScrn->virtualY;
2069     displayWidth = pScrn->displayWidth;
2070
2071
2072     if(pNv->Rotate) {
2073         height = pScrn->virtualX;
2074         width = pScrn->virtualY;
2075     }
2076
2077     /* If RandR rotation is enabled, leave enough space in the
2078      * framebuffer for us to rotate the screen dimensions without
2079      * changing the pitch.
2080      */
2081     if(pNv->RandRRotation)
2082         shadowHeight = max(width, height);
2083     else
2084         shadowHeight = height;
2085
2086     if(pNv->ShadowFB) {
2087         pNv->ShadowPitch = BitmapBytePad(pScrn->bitsPerPixel * width);
2088         pNv->ShadowPtr = xalloc(pNv->ShadowPitch * shadowHeight);
2089         displayWidth = pNv->ShadowPitch / (pScrn->bitsPerPixel >> 3);
2090         FBStart = pNv->ShadowPtr;
2091     } else {
2092         pNv->ShadowPtr = NULL;
2093         FBStart = pNv->FB->map;
2094     }
2095
2096     switch (pScrn->bitsPerPixel) {
2097         case 8:
2098         case 16:
2099         case 32:
2100             ret = fbScreenInit(pScreen, FBStart, width, height,
2101                                pScrn->xDpi, pScrn->yDpi,
2102                                displayWidth, pScrn->bitsPerPixel);
2103             break;
2104         default:
2105             xf86DrvMsg(scrnIndex, X_ERROR,
2106                        "Internal error: invalid bpp (%d) in NVScreenInit\n",
2107                        pScrn->bitsPerPixel);
2108             ret = FALSE;
2109             break;
2110     }
2111     if (!ret)
2112         return FALSE;
2113
2114     if (pScrn->bitsPerPixel > 8) {
2115         /* Fixup RGB ordering */
2116         visual = pScreen->visuals + pScreen->numVisuals;
2117         while (--visual >= pScreen->visuals) {
2118             if ((visual->class | DynamicClass) == DirectColor) {
2119                 visual->offsetRed = pScrn->offset.red;
2120                 visual->offsetGreen = pScrn->offset.green;
2121                 visual->offsetBlue = pScrn->offset.blue;
2122                 visual->redMask = pScrn->mask.red;
2123                 visual->greenMask = pScrn->mask.green;
2124                 visual->blueMask = pScrn->mask.blue;
2125             }
2126         }
2127     }
2128
2129     fbPictureInit (pScreen, 0, 0);
2130     
2131     xf86SetBlackWhitePixels(pScreen);
2132
2133     offscreenHeight = pNv->FB->size /
2134                      (pScrn->displayWidth * pScrn->bitsPerPixel >> 3);
2135     if(offscreenHeight > 32767)
2136         offscreenHeight = 32767;
2137
2138     if (!pNv->useEXA) {
2139     AvailFBArea.x1 = 0;
2140     AvailFBArea.y1 = 0;
2141     AvailFBArea.x2 = pScrn->displayWidth;
2142     AvailFBArea.y2 = offscreenHeight;
2143     xf86InitFBManager(pScreen, &AvailFBArea);
2144     }
2145     
2146     if (!pNv->NoAccel) {
2147         if (pNv->useEXA)
2148             NVExaInit(pScreen);
2149         else /* XAA */
2150             NVXaaInit(pScreen);
2151     }
2152     NVResetGraphics(pScrn);
2153     
2154     miInitializeBackingStore(pScreen);
2155     xf86SetBackingStore(pScreen);
2156     xf86SetSilkenMouse(pScreen);
2157
2158     /* Finish DRI init */
2159     NVDRIFinishScreenInit(pScrn);
2160
2161     /* Initialize software cursor.  
2162         Must precede creation of the default colormap */
2163     miDCInitialize(pScreen, xf86GetPointerScreenFuncs());
2164
2165     /* Initialize HW cursor layer. 
2166         Must follow software cursor initialization*/
2167     if (pNv->HWCursor) { 
2168         if(!NVCursorInit(pScreen))
2169             xf86DrvMsg(pScrn->scrnIndex, X_ERROR, 
2170                 "Hardware cursor initialization failed\n");
2171     }
2172
2173     /* Initialise default colourmap */
2174     if (!miCreateDefColormap(pScreen))
2175         return FALSE;
2176
2177     /* Initialize colormap layer.  
2178         Must follow initialization of the default colormap */
2179     if(!xf86HandleColormaps(pScreen, 256, 8, NVDACLoadPalette,
2180         NULL, CMAP_RELOAD_ON_MODE_SWITCH | CMAP_PALETTED_TRUECOLOR))
2181         return FALSE;
2182
2183     if(pNv->ShadowFB) {
2184         RefreshAreaFuncPtr refreshArea = NVRefreshArea;
2185
2186         if(pNv->Rotate || pNv->RandRRotation) {
2187            pNv->PointerMoved = pScrn->PointerMoved;
2188            if(pNv->Rotate)
2189                pScrn->PointerMoved = NVPointerMoved;
2190
2191            switch(pScrn->bitsPerPixel) {
2192                case 8:  refreshArea = NVRefreshArea8;   break;
2193                case 16: refreshArea = NVRefreshArea16;  break;
2194                case 32: refreshArea = NVRefreshArea32;  break;
2195            }
2196            if(!pNv->RandRRotation) {
2197                xf86DisableRandR();
2198                xf86DrvMsg(pScrn->scrnIndex, X_INFO,
2199                           "Driver rotation enabled, RandR disabled\n");
2200            }
2201         }
2202
2203         ShadowFBInit(pScreen, refreshArea);
2204     }
2205
2206     if(pNv->FlatPanel)
2207        xf86DPMSInit(pScreen, NVDPMSSetLCD, 0);
2208     else
2209        xf86DPMSInit(pScreen, NVDPMSSet, 0);
2210     
2211     pScrn->memPhysBase = pNv->VRAMPhysical;
2212     pScrn->fbOffset = 0;
2213
2214     if(pNv->Rotate == 0 && !pNv->RandRRotation)
2215        NVInitVideo(pScreen);
2216
2217     pScreen->SaveScreen = NVSaveScreen;
2218
2219     /* Wrap the current CloseScreen function */
2220     pNv->CloseScreen = pScreen->CloseScreen;
2221     pScreen->CloseScreen = NVCloseScreen;
2222
2223     pNv->BlockHandler = pScreen->BlockHandler;
2224     pScreen->BlockHandler = NVBlockHandler;
2225
2226 #ifdef RANDR
2227     /* Install our DriverFunc.  We have to do it this way instead of using the
2228      * HaveDriverFuncs argument to xf86AddDriver, because InitOutput clobbers
2229      * pScrn->DriverFunc */
2230     pScrn->DriverFunc = NVDriverFunc;
2231 #endif
2232
2233     /* Report any unused options (only for the first generation) */
2234     if (serverGeneration == 1) {
2235         xf86ShowUnusedOptions(pScrn->scrnIndex, pScrn->options);
2236     }
2237     return TRUE;
2238 }
2239
2240 static Bool
2241 NVSaveScreen(ScreenPtr pScreen, int mode)
2242 {
2243     return vgaHWSaveScreen(pScreen, mode);
2244 }
2245
2246 static void
2247 NVSave(ScrnInfoPtr pScrn)
2248 {
2249     NVPtr pNv = NVPTR(pScrn);
2250     NVRegPtr nvReg = &pNv->SavedReg;
2251     vgaHWPtr pVga = VGAHWPTR(pScrn);
2252     vgaRegPtr vgaReg = &pVga->SavedReg;
2253
2254     NVLockUnlock(pNv, 0);
2255     if(pNv->twoHeads) {
2256         nvWriteVGA(pNv, NV_VGA_CRTCX_OWNER, pNv->CRTCnumber * 0x3);
2257         NVLockUnlock(pNv, 0);
2258     }
2259
2260     NVDACSave(pScrn, vgaReg, nvReg, pNv->Primary);
2261 }
2262
2263 #ifdef RANDR
2264 static Bool
2265 NVRandRGetInfo(ScrnInfoPtr pScrn, Rotation *rotations)
2266 {
2267     NVPtr pNv = NVPTR(pScrn);
2268
2269     if(pNv->RandRRotation)
2270        *rotations = RR_Rotate_0 | RR_Rotate_90 | RR_Rotate_270;
2271     else
2272        *rotations = RR_Rotate_0;
2273
2274     return TRUE;
2275 }
2276
2277 static Bool
2278 NVRandRSetConfig(ScrnInfoPtr pScrn, xorgRRConfig *config)
2279 {
2280     NVPtr pNv = NVPTR(pScrn);
2281
2282     switch(config->rotation) {
2283         case RR_Rotate_0:
2284             pNv->Rotate = 0;
2285             pScrn->PointerMoved = pNv->PointerMoved;
2286             break;
2287
2288         case RR_Rotate_90:
2289             pNv->Rotate = -1;
2290             pScrn->PointerMoved = NVPointerMoved;
2291             break;
2292
2293         case RR_Rotate_270:
2294             pNv->Rotate = 1;
2295             pScrn->PointerMoved = NVPointerMoved;
2296             break;
2297
2298         default:
2299             xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
2300                     "Unexpected rotation in NVRandRSetConfig!\n");
2301             pNv->Rotate = 0;
2302             pScrn->PointerMoved = pNv->PointerMoved;
2303             return FALSE;
2304     }
2305
2306     return TRUE;
2307 }
2308
2309 static Bool
2310 NVDriverFunc(ScrnInfoPtr pScrn, xorgDriverFuncOp op, pointer data)
2311 {
2312     switch(op) {
2313        case RR_GET_INFO:
2314           return NVRandRGetInfo(pScrn, (Rotation*)data);
2315        case RR_SET_CONFIG:
2316           return NVRandRSetConfig(pScrn, (xorgRRConfig*)data);
2317        default:
2318           return FALSE;
2319     }
2320
2321     return FALSE;
2322 }
2323 #endif