1 #include <linux/types.h>
2 #include <linux/delay.h> /* udelay */
4 #include <linux/vmalloc.h>
10 #include "vb_struct.h"
12 #include "vb_setmode.h"
18 static const unsigned short XGINew_DDRDRAM_TYPE340
[4][5] = {
19 { 2, 13, 9, 64, 0x45},
20 { 2, 12, 9, 32, 0x35},
21 { 2, 12, 8, 16, 0x31},
22 { 2, 11, 8, 8, 0x21} };
24 static const unsigned short XGINew_DDRDRAM_TYPE20
[12][5] = {
25 { 2, 14, 11, 128, 0x5D},
26 { 2, 14, 10, 64, 0x59},
27 { 2, 13, 11, 64, 0x4D},
28 { 2, 14, 9, 32, 0x55},
29 { 2, 13, 10, 32, 0x49},
30 { 2, 12, 11, 32, 0x3D},
31 { 2, 14, 8, 16, 0x51},
32 { 2, 13, 9, 16, 0x45},
33 { 2, 12, 10, 16, 0x39},
36 { 2, 12, 8, 4, 0x31} };
38 #define XGIFB_ROM_SIZE 65536
41 XGINew_GetXG20DRAMType(struct xgi_hw_device_info
*HwDeviceExtension
,
42 struct vb_device_info
*pVBInfo
)
44 unsigned char data
, temp
;
46 if (HwDeviceExtension
->jChipType
< XG20
) {
47 if (*pVBInfo
->pSoftSetting
& SoftDRAMType
) {
48 data
= *pVBInfo
->pSoftSetting
& 0x07;
51 data
= xgifb_reg_get(pVBInfo
->P3c4
, 0x39) & 0x02;
53 data
= (xgifb_reg_get(pVBInfo
->P3c4
, 0x3A) &
57 } else if (HwDeviceExtension
->jChipType
== XG27
) {
58 if (*pVBInfo
->pSoftSetting
& SoftDRAMType
) {
59 data
= *pVBInfo
->pSoftSetting
& 0x07;
62 temp
= xgifb_reg_get(pVBInfo
->P3c4
, 0x3B);
63 /* SR3B[7][3]MAA15 MAA11 (Power on Trapping) */
64 if ((temp
& 0x88) == 0x80)
69 } else if (HwDeviceExtension
->jChipType
== XG21
) {
70 /* Independent GPIO control */
71 xgifb_reg_and(pVBInfo
->P3d4
, 0xB4, ~0x02);
73 xgifb_reg_or(pVBInfo
->P3d4
, 0x4A, 0x80); /* Enable GPIOH read */
74 /* GPIOF 0:DVI 1:DVO */
75 temp
= xgifb_reg_get(pVBInfo
->P3d4
, 0x48);
77 /* for current XG20 & XG21, GPIOH is floating, driver will
78 * fix DDR temporarily */
79 if (temp
& 0x01) /* DVI read GPIOH */
83 /* ~HOTPLUG_SUPPORT */
84 xgifb_reg_or(pVBInfo
->P3d4
, 0xB4, 0x02);
87 data
= xgifb_reg_get(pVBInfo
->P3d4
, 0x97) & 0x01;
96 static void XGINew_DDR1x_MRS_340(unsigned long P3c4
,
97 struct vb_device_info
*pVBInfo
)
99 xgifb_reg_set(P3c4
, 0x18, 0x01);
100 xgifb_reg_set(P3c4
, 0x19, 0x20);
101 xgifb_reg_set(P3c4
, 0x16, 0x00);
102 xgifb_reg_set(P3c4
, 0x16, 0x80);
104 if (*pVBInfo
->pXGINew_DRAMTypeDefinition
!= 0x0C) { /* Samsung F Die */
106 xgifb_reg_set(P3c4
, 0x18, 0x00);
107 xgifb_reg_set(P3c4
, 0x19, 0x20);
108 xgifb_reg_set(P3c4
, 0x16, 0x00);
109 xgifb_reg_set(P3c4
, 0x16, 0x80);
115 pVBInfo
->SR15
[2][pVBInfo
->ram_type
]); /* SR18 */
116 xgifb_reg_set(P3c4
, 0x19, 0x01);
117 xgifb_reg_set(P3c4
, 0x16, pVBInfo
->SR16
[0]);
118 xgifb_reg_set(P3c4
, 0x16, pVBInfo
->SR16
[1]);
120 xgifb_reg_set(P3c4
, 0x1B, 0x03);
124 pVBInfo
->SR15
[2][pVBInfo
->ram_type
]); /* SR18 */
125 xgifb_reg_set(P3c4
, 0x19, 0x00);
126 xgifb_reg_set(P3c4
, 0x16, pVBInfo
->SR16
[2]);
127 xgifb_reg_set(P3c4
, 0x16, pVBInfo
->SR16
[3]);
128 xgifb_reg_set(P3c4
, 0x1B, 0x00);
131 static void XGINew_SetMemoryClock(struct xgi_hw_device_info
*HwDeviceExtension
,
132 struct vb_device_info
*pVBInfo
)
135 xgifb_reg_set(pVBInfo
->P3c4
,
137 pVBInfo
->MCLKData
[pVBInfo
->ram_type
].SR28
);
138 xgifb_reg_set(pVBInfo
->P3c4
,
140 pVBInfo
->MCLKData
[pVBInfo
->ram_type
].SR29
);
141 xgifb_reg_set(pVBInfo
->P3c4
,
143 pVBInfo
->MCLKData
[pVBInfo
->ram_type
].SR2A
);
145 xgifb_reg_set(pVBInfo
->P3c4
,
147 pVBInfo
->ECLKData
[pVBInfo
->ram_type
].SR2E
);
148 xgifb_reg_set(pVBInfo
->P3c4
,
150 pVBInfo
->ECLKData
[pVBInfo
->ram_type
].SR2F
);
151 xgifb_reg_set(pVBInfo
->P3c4
,
153 pVBInfo
->ECLKData
[pVBInfo
->ram_type
].SR30
);
155 /* [Vicent] 2004/07/07,
156 * When XG42 ECLK = MCLK = 207MHz, Set SR32 D[1:0] = 10b */
157 /* [Hsuan] 2004/08/20,
158 * Modify SR32 value, when MCLK=207MHZ, ELCK=250MHz,
159 * Set SR32 D[1:0] = 10b */
160 if (HwDeviceExtension
->jChipType
== XG42
) {
161 if ((pVBInfo
->MCLKData
[pVBInfo
->ram_type
].SR28
== 0x1C) &&
162 (pVBInfo
->MCLKData
[pVBInfo
->ram_type
].SR29
== 0x01) &&
163 (((pVBInfo
->ECLKData
[pVBInfo
->ram_type
].SR2E
== 0x1C) &&
164 (pVBInfo
->ECLKData
[pVBInfo
->ram_type
].SR2F
== 0x01)) ||
165 ((pVBInfo
->ECLKData
[pVBInfo
->ram_type
].SR2E
== 0x22) &&
166 (pVBInfo
->ECLKData
[pVBInfo
->ram_type
].SR2F
== 0x01))))
167 xgifb_reg_set(pVBInfo
->P3c4
,
169 ((unsigned char) xgifb_reg_get(
170 pVBInfo
->P3c4
, 0x32) & 0xFC) | 0x02);
174 static void XGINew_DDRII_Bootup_XG27(
175 struct xgi_hw_device_info
*HwDeviceExtension
,
176 unsigned long P3c4
, struct vb_device_info
*pVBInfo
)
178 unsigned long P3d4
= P3c4
+ 0x10;
179 pVBInfo
->ram_type
= XGINew_GetXG20DRAMType(HwDeviceExtension
, pVBInfo
);
180 XGINew_SetMemoryClock(HwDeviceExtension
, pVBInfo
);
182 /* Set Double Frequency */
183 /* xgifb_reg_set(P3d4, 0x97, 0x11); *//* CR97 */
184 xgifb_reg_set(P3d4
, 0x97, *pVBInfo
->pXGINew_CR97
); /* CR97 */
188 xgifb_reg_set(P3c4
, 0x18, 0x00); /* Set SR18 */ /* EMRS2 */
189 xgifb_reg_set(P3c4
, 0x19, 0x80); /* Set SR19 */
190 xgifb_reg_set(P3c4
, 0x16, 0x20); /* Set SR16 */
192 xgifb_reg_set(P3c4
, 0x16, 0xA0); /* Set SR16 */
195 xgifb_reg_set(P3c4
, 0x18, 0x00); /* Set SR18 */ /* EMRS3 */
196 xgifb_reg_set(P3c4
, 0x19, 0xC0); /* Set SR19 */
197 xgifb_reg_set(P3c4
, 0x16, 0x20); /* Set SR16 */
199 xgifb_reg_set(P3c4
, 0x16, 0xA0); /* Set SR16 */
202 xgifb_reg_set(P3c4
, 0x18, 0x00); /* Set SR18 */ /* EMRS1 */
203 xgifb_reg_set(P3c4
, 0x19, 0x40); /* Set SR19 */
204 xgifb_reg_set(P3c4
, 0x16, 0x20); /* Set SR16 */
206 xgifb_reg_set(P3c4
, 0x16, 0xA0); /* Set SR16 */
209 xgifb_reg_set(P3c4
, 0x18, 0x42); /* Set SR18 */ /* MRS, DLL Enable */
210 xgifb_reg_set(P3c4
, 0x19, 0x0A); /* Set SR19 */
211 xgifb_reg_set(P3c4
, 0x16, 0x00); /* Set SR16 */
213 xgifb_reg_set(P3c4
, 0x16, 0x00); /* Set SR16 */
214 xgifb_reg_set(P3c4
, 0x16, 0x80); /* Set SR16 */
217 xgifb_reg_set(P3c4
, 0x1B, 0x04); /* Set SR1B */
219 xgifb_reg_set(P3c4
, 0x1B, 0x00); /* Set SR1B */
221 xgifb_reg_set(P3c4
, 0x18, 0x42); /* Set SR18 */ /* MRS, DLL Reset */
222 xgifb_reg_set(P3c4
, 0x19, 0x08); /* Set SR19 */
223 xgifb_reg_set(P3c4
, 0x16, 0x00); /* Set SR16 */
226 xgifb_reg_set(P3c4
, 0x16, 0x83); /* Set SR16 */
229 xgifb_reg_set(P3c4
, 0x18, 0x80); /* Set SR18 */ /* MRS, ODT */
230 xgifb_reg_set(P3c4
, 0x19, 0x46); /* Set SR19 */
231 xgifb_reg_set(P3c4
, 0x16, 0x20); /* Set SR16 */
233 xgifb_reg_set(P3c4
, 0x16, 0xA0); /* Set SR16 */
236 xgifb_reg_set(P3c4
, 0x18, 0x00); /* Set SR18 */ /* EMRS */
237 xgifb_reg_set(P3c4
, 0x19, 0x40); /* Set SR19 */
238 xgifb_reg_set(P3c4
, 0x16, 0x20); /* Set SR16 */
240 xgifb_reg_set(P3c4
, 0x16, 0xA0); /* Set SR16 */
243 /* Set SR1B refresh control 000:close; 010:open */
244 xgifb_reg_set(P3c4
, 0x1B, 0x04);
249 static void XGINew_DDR2_MRS_XG20(struct xgi_hw_device_info
*HwDeviceExtension
,
250 unsigned long P3c4
, struct vb_device_info
*pVBInfo
)
252 unsigned long P3d4
= P3c4
+ 0x10;
254 pVBInfo
->ram_type
= XGINew_GetXG20DRAMType(HwDeviceExtension
, pVBInfo
);
255 XGINew_SetMemoryClock(HwDeviceExtension
, pVBInfo
);
257 xgifb_reg_set(P3d4
, 0x97, 0x11); /* CR97 */
260 xgifb_reg_set(P3c4
, 0x18, 0x00); /* EMRS2 */
261 xgifb_reg_set(P3c4
, 0x19, 0x80);
262 xgifb_reg_set(P3c4
, 0x16, 0x05);
263 xgifb_reg_set(P3c4
, 0x16, 0x85);
265 xgifb_reg_set(P3c4
, 0x18, 0x00); /* EMRS3 */
266 xgifb_reg_set(P3c4
, 0x19, 0xC0);
267 xgifb_reg_set(P3c4
, 0x16, 0x05);
268 xgifb_reg_set(P3c4
, 0x16, 0x85);
270 xgifb_reg_set(P3c4
, 0x18, 0x00); /* EMRS1 */
271 xgifb_reg_set(P3c4
, 0x19, 0x40);
272 xgifb_reg_set(P3c4
, 0x16, 0x05);
273 xgifb_reg_set(P3c4
, 0x16, 0x85);
275 /* xgifb_reg_set(P3c4, 0x18, 0x52); */ /* MRS1 */
276 xgifb_reg_set(P3c4
, 0x18, 0x42); /* MRS1 */
277 xgifb_reg_set(P3c4
, 0x19, 0x02);
278 xgifb_reg_set(P3c4
, 0x16, 0x05);
279 xgifb_reg_set(P3c4
, 0x16, 0x85);
282 xgifb_reg_set(P3c4
, 0x1B, 0x04); /* SR1B */
284 xgifb_reg_set(P3c4
, 0x1B, 0x00); /* SR1B */
287 /* xgifb_reg_set(P3c4 ,0x18, 0x52); */ /* MRS2 */
288 xgifb_reg_set(P3c4
, 0x18, 0x42); /* MRS1 */
289 xgifb_reg_set(P3c4
, 0x19, 0x00);
290 xgifb_reg_set(P3c4
, 0x16, 0x05);
291 xgifb_reg_set(P3c4
, 0x16, 0x85);
296 static void XGINew_DDR1x_MRS_XG20(unsigned long P3c4
,
297 struct vb_device_info
*pVBInfo
)
299 xgifb_reg_set(P3c4
, 0x18, 0x01);
300 xgifb_reg_set(P3c4
, 0x19, 0x40);
301 xgifb_reg_set(P3c4
, 0x16, 0x00);
302 xgifb_reg_set(P3c4
, 0x16, 0x80);
305 xgifb_reg_set(P3c4
, 0x18, 0x00);
306 xgifb_reg_set(P3c4
, 0x19, 0x40);
307 xgifb_reg_set(P3c4
, 0x16, 0x00);
308 xgifb_reg_set(P3c4
, 0x16, 0x80);
312 pVBInfo
->SR15
[2][pVBInfo
->ram_type
]); /* SR18 */
313 /* xgifb_reg_set(P3c4, 0x18, 0x31); */
314 xgifb_reg_set(P3c4
, 0x19, 0x01);
315 xgifb_reg_set(P3c4
, 0x16, 0x03);
316 xgifb_reg_set(P3c4
, 0x16, 0x83);
318 xgifb_reg_set(P3c4
, 0x1B, 0x03);
320 /* xgifb_reg_set(P3c4, 0x18, 0x31); */
323 pVBInfo
->SR15
[2][pVBInfo
->ram_type
]); /* SR18 */
324 xgifb_reg_set(P3c4
, 0x19, 0x00);
325 xgifb_reg_set(P3c4
, 0x16, 0x03);
326 xgifb_reg_set(P3c4
, 0x16, 0x83);
327 xgifb_reg_set(P3c4
, 0x1B, 0x00);
330 static void XGINew_DDR1x_DefaultRegister(
331 struct xgi_hw_device_info
*HwDeviceExtension
,
332 unsigned long Port
, struct vb_device_info
*pVBInfo
)
334 unsigned long P3d4
= Port
, P3c4
= Port
- 0x10;
336 if (HwDeviceExtension
->jChipType
>= XG20
) {
337 XGINew_SetMemoryClock(HwDeviceExtension
, pVBInfo
);
340 pVBInfo
->CR40
[11][pVBInfo
->ram_type
]); /* CR82 */
343 pVBInfo
->CR40
[12][pVBInfo
->ram_type
]); /* CR85 */
346 pVBInfo
->CR40
[13][pVBInfo
->ram_type
]); /* CR86 */
348 xgifb_reg_set(P3d4
, 0x98, 0x01);
349 xgifb_reg_set(P3d4
, 0x9A, 0x02);
351 XGINew_DDR1x_MRS_XG20(P3c4
, pVBInfo
);
353 XGINew_SetMemoryClock(HwDeviceExtension
, pVBInfo
);
355 switch (HwDeviceExtension
->jChipType
) {
361 pVBInfo
->CR40
[11][pVBInfo
->ram_type
]);
365 pVBInfo
->CR40
[12][pVBInfo
->ram_type
]);
369 pVBInfo
->CR40
[13][pVBInfo
->ram_type
]);
372 xgifb_reg_set(P3d4
, 0x82, 0x88);
373 xgifb_reg_set(P3d4
, 0x86, 0x00);
374 /* Insert read command for delay */
375 xgifb_reg_get(P3d4
, 0x86);
376 xgifb_reg_set(P3d4
, 0x86, 0x88);
377 xgifb_reg_get(P3d4
, 0x86);
380 pVBInfo
->CR40
[13][pVBInfo
->ram_type
]);
381 xgifb_reg_set(P3d4
, 0x82, 0x77);
382 xgifb_reg_set(P3d4
, 0x85, 0x00);
384 /* Insert read command for delay */
385 xgifb_reg_get(P3d4
, 0x85);
386 xgifb_reg_set(P3d4
, 0x85, 0x88);
388 /* Insert read command for delay */
389 xgifb_reg_get(P3d4
, 0x85);
393 pVBInfo
->CR40
[12][pVBInfo
->ram_type
]);
397 pVBInfo
->CR40
[11][pVBInfo
->ram_type
]);
401 xgifb_reg_set(P3d4
, 0x97, 0x00);
402 xgifb_reg_set(P3d4
, 0x98, 0x01);
403 xgifb_reg_set(P3d4
, 0x9A, 0x02);
404 XGINew_DDR1x_MRS_340(P3c4
, pVBInfo
);
408 static void XGINew_DDR2_DefaultRegister(
409 struct xgi_hw_device_info
*HwDeviceExtension
,
410 unsigned long Port
, struct vb_device_info
*pVBInfo
)
412 unsigned long P3d4
= Port
, P3c4
= Port
- 0x10;
414 /* keep following setting sequence, each setting in
415 * the same reg insert idle */
416 xgifb_reg_set(P3d4
, 0x82, 0x77);
417 xgifb_reg_set(P3d4
, 0x86, 0x00);
418 xgifb_reg_get(P3d4
, 0x86); /* Insert read command for delay */
419 xgifb_reg_set(P3d4
, 0x86, 0x88);
420 xgifb_reg_get(P3d4
, 0x86); /* Insert read command for delay */
422 xgifb_reg_set(P3d4
, 0x86, pVBInfo
->CR40
[13][pVBInfo
->ram_type
]);
423 xgifb_reg_set(P3d4
, 0x82, 0x77);
424 xgifb_reg_set(P3d4
, 0x85, 0x00);
425 xgifb_reg_get(P3d4
, 0x85); /* Insert read command for delay */
426 xgifb_reg_set(P3d4
, 0x85, 0x88);
427 xgifb_reg_get(P3d4
, 0x85); /* Insert read command for delay */
430 pVBInfo
->CR40
[12][pVBInfo
->ram_type
]); /* CR85 */
431 if (HwDeviceExtension
->jChipType
== XG27
)
433 xgifb_reg_set(P3d4
, 0x82, pVBInfo
->CR40
[11][pVBInfo
->ram_type
]);
435 xgifb_reg_set(P3d4
, 0x82, 0xA8); /* CR82 */
437 xgifb_reg_set(P3d4
, 0x98, 0x01);
438 xgifb_reg_set(P3d4
, 0x9A, 0x02);
439 if (HwDeviceExtension
->jChipType
== XG27
)
440 XGINew_DDRII_Bootup_XG27(HwDeviceExtension
, P3c4
, pVBInfo
);
442 XGINew_DDR2_MRS_XG20(HwDeviceExtension
, P3c4
, pVBInfo
);
445 static void XGINew_SetDRAMDefaultRegister340(
446 struct xgi_hw_device_info
*HwDeviceExtension
,
447 unsigned long Port
, struct vb_device_info
*pVBInfo
)
449 unsigned char temp
, temp1
, temp2
, temp3
, i
, j
, k
;
451 unsigned long P3d4
= Port
, P3c4
= Port
- 0x10;
453 xgifb_reg_set(P3d4
, 0x6D, pVBInfo
->CR40
[8][pVBInfo
->ram_type
]);
454 xgifb_reg_set(P3d4
, 0x68, pVBInfo
->CR40
[5][pVBInfo
->ram_type
]);
455 xgifb_reg_set(P3d4
, 0x69, pVBInfo
->CR40
[6][pVBInfo
->ram_type
]);
456 xgifb_reg_set(P3d4
, 0x6A, pVBInfo
->CR40
[7][pVBInfo
->ram_type
]);
459 for (i
= 0; i
< 4; i
++) {
460 /* CR6B DQS fine tune delay */
461 temp
= pVBInfo
->CR6B
[pVBInfo
->ram_type
][i
];
462 for (j
= 0; j
< 4; j
++) {
463 temp1
= ((temp
>> (2 * j
)) & 0x03) << 2;
465 xgifb_reg_set(P3d4
, 0x6B, temp2
);
466 /* Insert read command for delay */
467 xgifb_reg_get(P3d4
, 0x6B);
474 for (i
= 0; i
< 4; i
++) {
475 /* CR6E DQM fine tune delay */
476 temp
= pVBInfo
->CR6E
[pVBInfo
->ram_type
][i
];
477 for (j
= 0; j
< 4; j
++) {
478 temp1
= ((temp
>> (2 * j
)) & 0x03) << 2;
480 xgifb_reg_set(P3d4
, 0x6E, temp2
);
481 /* Insert read command for delay */
482 xgifb_reg_get(P3d4
, 0x6E);
489 for (k
= 0; k
< 4; k
++) {
490 /* CR6E_D[1:0] select channel */
491 xgifb_reg_and_or(P3d4
, 0x6E, 0xFC, temp3
);
493 for (i
= 0; i
< 8; i
++) {
494 /* CR6F DQ fine tune delay */
495 temp
= pVBInfo
->CR6F
[pVBInfo
->ram_type
][8 * k
+ i
];
496 for (j
= 0; j
< 4; j
++) {
497 temp1
= (temp
>> (2 * j
)) & 0x03;
499 xgifb_reg_set(P3d4
, 0x6F, temp2
);
500 /* Insert read command for delay */
501 xgifb_reg_get(P3d4
, 0x6F);
511 pVBInfo
->CR40
[9][pVBInfo
->ram_type
]); /* CR80 */
514 pVBInfo
->CR40
[10][pVBInfo
->ram_type
]); /* CR81 */
517 /* CR89 terminator type select */
518 temp
= pVBInfo
->CR89
[pVBInfo
->ram_type
][0];
519 for (j
= 0; j
< 4; j
++) {
520 temp1
= (temp
>> (2 * j
)) & 0x03;
522 xgifb_reg_set(P3d4
, 0x89, temp2
);
523 xgifb_reg_get(P3d4
, 0x89); /* Insert read command for delay */
528 temp
= pVBInfo
->CR89
[pVBInfo
->ram_type
][1];
531 xgifb_reg_set(P3d4
, 0x89, temp2
);
533 temp
= pVBInfo
->CR40
[3][pVBInfo
->ram_type
];
535 temp2
= (temp
>> 4) & 0x07;
537 xgifb_reg_set(P3d4
, 0x45, temp1
); /* CR45 */
538 xgifb_reg_set(P3d4
, 0x99, temp2
); /* CR99 */
539 xgifb_reg_or(P3d4
, 0x40, temp3
); /* CR40_D[7] */
542 pVBInfo
->CR40
[0][pVBInfo
->ram_type
]); /* CR41 */
544 if (HwDeviceExtension
->jChipType
== XG27
)
545 xgifb_reg_set(P3d4
, 0x8F, *pVBInfo
->pCR8F
); /* CR8F */
547 for (j
= 0; j
<= 6; j
++) /* CR90 - CR96 */
548 xgifb_reg_set(P3d4
, (0x90 + j
),
549 pVBInfo
->CR40
[14 + j
][pVBInfo
->ram_type
]);
551 for (j
= 0; j
<= 2; j
++) /* CRC3 - CRC5 */
552 xgifb_reg_set(P3d4
, (0xC3 + j
),
553 pVBInfo
->CR40
[21 + j
][pVBInfo
->ram_type
]);
555 for (j
= 0; j
< 2; j
++) /* CR8A - CR8B */
556 xgifb_reg_set(P3d4
, (0x8A + j
),
557 pVBInfo
->CR40
[1 + j
][pVBInfo
->ram_type
]);
559 if ((HwDeviceExtension
->jChipType
== XG41
) ||
560 (HwDeviceExtension
->jChipType
== XG42
))
561 xgifb_reg_set(P3d4
, 0x8C, 0x87);
565 pVBInfo
->CR40
[4][pVBInfo
->ram_type
]); /* CR59 */
567 xgifb_reg_set(P3d4
, 0x83, 0x09); /* CR83 */
568 xgifb_reg_set(P3d4
, 0x87, 0x00); /* CR87 */
569 xgifb_reg_set(P3d4
, 0xCF, *pVBInfo
->pCRCF
); /* CRCF */
570 if (pVBInfo
->ram_type
) {
571 /* xgifb_reg_set(P3c4, 0x17, 0xC0); */ /* SR17 DDRII */
572 xgifb_reg_set(P3c4
, 0x17, 0x80); /* SR17 DDRII */
573 if (HwDeviceExtension
->jChipType
== XG27
)
574 xgifb_reg_set(P3c4
, 0x17, 0x02); /* SR17 DDRII */
577 xgifb_reg_set(P3c4
, 0x17, 0x00); /* SR17 DDR */
579 xgifb_reg_set(P3c4
, 0x1A, 0x87); /* SR1A */
581 temp
= XGINew_GetXG20DRAMType(HwDeviceExtension
, pVBInfo
);
583 XGINew_DDR1x_DefaultRegister(HwDeviceExtension
, P3d4
, pVBInfo
);
585 xgifb_reg_set(P3d4
, 0xB0, 0x80); /* DDRII Dual frequency mode */
586 XGINew_DDR2_DefaultRegister(HwDeviceExtension
, P3d4
, pVBInfo
);
590 pVBInfo
->SR15
[3][pVBInfo
->ram_type
]); /* SR1B */
593 static void XGINew_SetDRAMSizingType(int index
,
594 const unsigned short DRAMTYPE_TABLE
[][5],
595 struct vb_device_info
*pVBInfo
)
599 data
= DRAMTYPE_TABLE
[index
][4];
600 xgifb_reg_and_or(pVBInfo
->P3c4
, 0x13, 0x80, data
);
602 /* should delay 50 ns */
605 static unsigned short XGINew_SetDRAMSizeReg(int index
,
606 const unsigned short DRAMTYPE_TABLE
[][5],
607 struct vb_device_info
*pVBInfo
)
609 unsigned short data
= 0, memsize
= 0;
611 unsigned char ChannelNo
;
613 RankSize
= DRAMTYPE_TABLE
[index
][3] * pVBInfo
->ram_bus
/ 32;
614 data
= xgifb_reg_get(pVBInfo
->P3c4
, 0x13);
622 if (pVBInfo
->ram_channel
== 3)
625 ChannelNo
= pVBInfo
->ram_channel
;
627 if (ChannelNo
* RankSize
<= 256) {
628 while ((RankSize
>>= 1) > 0)
633 /* [2004/03/25] Vicent, Fix DRAM Sizing Error */
634 xgifb_reg_set(pVBInfo
->P3c4
,
636 (xgifb_reg_get(pVBInfo
->P3c4
, 0x14) & 0x0F) |
639 /* data |= pVBInfo->ram_channel << 2; */
640 /* data |= (pVBInfo->ram_bus / 64) << 1; */
641 /* xgifb_reg_set(pVBInfo->P3c4, 0x14, data); */
644 /* XGINew_SetDRAMModeRegister340(pVBInfo); */
649 static unsigned short XGINew_SetDRAMSize20Reg(int index
,
650 const unsigned short DRAMTYPE_TABLE
[][5],
651 struct vb_device_info
*pVBInfo
)
653 unsigned short data
= 0, memsize
= 0;
655 unsigned char ChannelNo
;
657 RankSize
= DRAMTYPE_TABLE
[index
][3] * pVBInfo
->ram_bus
/ 8;
658 data
= xgifb_reg_get(pVBInfo
->P3c4
, 0x13);
666 if (pVBInfo
->ram_channel
== 3)
669 ChannelNo
= pVBInfo
->ram_channel
;
671 if (ChannelNo
* RankSize
<= 256) {
672 while ((RankSize
>>= 1) > 0)
677 /* [2004/03/25] Vicent, Fix DRAM Sizing Error */
678 xgifb_reg_set(pVBInfo
->P3c4
,
680 (xgifb_reg_get(pVBInfo
->P3c4
, 0x14) & 0x0F) |
684 /* data |= pVBInfo->ram_channel << 2; */
685 /* data |= (pVBInfo->ram_bus / 64) << 1; */
686 /* xgifb_reg_set(pVBInfo->P3c4, 0x14, data); */
689 /* XGINew_SetDRAMModeRegister340(pVBInfo); */
694 static int XGINew_ReadWriteRest(unsigned short StopAddr
,
695 unsigned short StartAddr
, struct vb_device_info
*pVBInfo
)
698 unsigned long Position
= 0;
699 void __iomem
*fbaddr
= pVBInfo
->FBAddr
;
701 writel(Position
, fbaddr
+ Position
);
703 for (i
= StartAddr
; i
<= StopAddr
; i
++) {
705 writel(Position
, fbaddr
+ Position
);
708 udelay(500); /* [Vicent] 2004/04/16.
709 Fix #1759 Memory Size error in Multi-Adapter. */
713 if (readl(fbaddr
+ Position
) != Position
)
716 for (i
= StartAddr
; i
<= StopAddr
; i
++) {
718 if (readl(fbaddr
+ Position
) != Position
)
724 static unsigned char XGINew_CheckFrequence(struct vb_device_info
*pVBInfo
)
728 data
= xgifb_reg_get(pVBInfo
->P3d4
, 0x97);
730 if ((data
& 0x10) == 0) {
731 data
= xgifb_reg_get(pVBInfo
->P3c4
, 0x39);
732 data
= (data
& 0x02) >> 1;
739 static void XGINew_CheckChannel(struct xgi_hw_device_info
*HwDeviceExtension
,
740 struct vb_device_info
*pVBInfo
)
744 switch (HwDeviceExtension
->jChipType
) {
747 data
= xgifb_reg_get(pVBInfo
->P3d4
, 0x97);
749 pVBInfo
->ram_channel
= 1; /* XG20 "JUST" one channel */
751 if (data
== 0) { /* Single_32_16 */
753 if ((HwDeviceExtension
->ulVideoMemorySize
- 1)
756 pVBInfo
->ram_bus
= 32; /* 32 bits */
757 /* 22bit + 2 rank + 32bit */
758 xgifb_reg_set(pVBInfo
->P3c4
, 0x13, 0xB1);
759 xgifb_reg_set(pVBInfo
->P3c4
, 0x14, 0x52);
762 if (XGINew_ReadWriteRest(24, 23, pVBInfo
) == 1)
765 if ((HwDeviceExtension
->ulVideoMemorySize
- 1) >
767 /* 22bit + 1 rank + 32bit */
768 xgifb_reg_set(pVBInfo
->P3c4
,
771 xgifb_reg_set(pVBInfo
->P3c4
,
776 if (XGINew_ReadWriteRest(23,
783 if ((HwDeviceExtension
->ulVideoMemorySize
- 1) >
785 pVBInfo
->ram_bus
= 16; /* 16 bits */
786 /* 22bit + 2 rank + 16bit */
787 xgifb_reg_set(pVBInfo
->P3c4
, 0x13, 0xB1);
788 xgifb_reg_set(pVBInfo
->P3c4
, 0x14, 0x41);
791 if (XGINew_ReadWriteRest(23, 22, pVBInfo
) == 1)
794 xgifb_reg_set(pVBInfo
->P3c4
,
800 } else { /* Dual_16_8 */
801 if ((HwDeviceExtension
->ulVideoMemorySize
- 1) >
803 pVBInfo
->ram_bus
= 16; /* 16 bits */
804 /* (0x31:12x8x2) 22bit + 2 rank */
805 xgifb_reg_set(pVBInfo
->P3c4
, 0x13, 0xB1);
807 xgifb_reg_set(pVBInfo
->P3c4
, 0x14, 0x41);
810 if (XGINew_ReadWriteRest(23, 22, pVBInfo
) == 1)
813 if ((HwDeviceExtension
->ulVideoMemorySize
- 1) >
815 /* (0x31:12x8x2) 22bit + 1 rank */
816 xgifb_reg_set(pVBInfo
->P3c4
,
820 xgifb_reg_set(pVBInfo
->P3c4
,
825 if (XGINew_ReadWriteRest(22,
832 if ((HwDeviceExtension
->ulVideoMemorySize
- 1) >
834 pVBInfo
->ram_bus
= 8; /* 8 bits */
835 /* (0x31:12x8x2) 22bit + 2 rank */
836 xgifb_reg_set(pVBInfo
->P3c4
, 0x13, 0xB1);
838 xgifb_reg_set(pVBInfo
->P3c4
, 0x14, 0x30);
841 if (XGINew_ReadWriteRest(22, 21, pVBInfo
) == 1)
843 else /* (0x31:12x8x2) 22bit + 1 rank */
844 xgifb_reg_set(pVBInfo
->P3c4
,
853 pVBInfo
->ram_bus
= 16; /* 16 bits */
854 pVBInfo
->ram_channel
= 1; /* Single channel */
855 xgifb_reg_set(pVBInfo
->P3c4
, 0x14, 0x51); /* 32Mx16 bit*/
858 if (XGINew_CheckFrequence(pVBInfo
) == 1) {
859 pVBInfo
->ram_bus
= 32; /* 32 bits */
860 pVBInfo
->ram_channel
= 3; /* Quad Channel */
861 xgifb_reg_set(pVBInfo
->P3c4
, 0x13, 0xA1);
862 xgifb_reg_set(pVBInfo
->P3c4
, 0x14, 0x4C);
864 if (XGINew_ReadWriteRest(25, 23, pVBInfo
) == 1)
867 pVBInfo
->ram_channel
= 2; /* Dual channels */
868 xgifb_reg_set(pVBInfo
->P3c4
, 0x14, 0x48);
870 if (XGINew_ReadWriteRest(24, 23, pVBInfo
) == 1)
873 xgifb_reg_set(pVBInfo
->P3c4
, 0x14, 0x49);
875 if (XGINew_ReadWriteRest(24, 23, pVBInfo
) == 1)
878 pVBInfo
->ram_channel
= 3;
879 xgifb_reg_set(pVBInfo
->P3c4
, 0x13, 0x21);
880 xgifb_reg_set(pVBInfo
->P3c4
, 0x14, 0x3C);
882 if (XGINew_ReadWriteRest(24, 23, pVBInfo
) == 1)
885 xgifb_reg_set(pVBInfo
->P3c4
, 0x14, 0x38);
887 if (XGINew_ReadWriteRest(8, 4, pVBInfo
) == 1)
890 xgifb_reg_set(pVBInfo
->P3c4
, 0x14, 0x39);
892 pVBInfo
->ram_bus
= 64; /* 64 bits */
893 pVBInfo
->ram_channel
= 2; /* Dual channels */
894 xgifb_reg_set(pVBInfo
->P3c4
, 0x13, 0xA1);
895 xgifb_reg_set(pVBInfo
->P3c4
, 0x14, 0x5A);
897 if (XGINew_ReadWriteRest(25, 24, pVBInfo
) == 1)
900 pVBInfo
->ram_channel
= 1; /* Single channels */
901 xgifb_reg_set(pVBInfo
->P3c4
, 0x14, 0x52);
903 if (XGINew_ReadWriteRest(24, 23, pVBInfo
) == 1)
906 xgifb_reg_set(pVBInfo
->P3c4
, 0x14, 0x53);
908 if (XGINew_ReadWriteRest(24, 23, pVBInfo
) == 1)
911 pVBInfo
->ram_channel
= 2; /* Dual channels */
912 xgifb_reg_set(pVBInfo
->P3c4
, 0x13, 0x21);
913 xgifb_reg_set(pVBInfo
->P3c4
, 0x14, 0x4A);
915 if (XGINew_ReadWriteRest(24, 23, pVBInfo
) == 1)
918 pVBInfo
->ram_channel
= 1; /* Single channels */
919 xgifb_reg_set(pVBInfo
->P3c4
, 0x14, 0x42);
921 if (XGINew_ReadWriteRest(8, 4, pVBInfo
) == 1)
924 xgifb_reg_set(pVBInfo
->P3c4
, 0x14, 0x43);
931 XG42 SR14 D[3] Reserve
932 D[2] = 1, Dual Channel
935 It's Different from Other XG40 Series.
937 if (XGINew_CheckFrequence(pVBInfo
) == 1) { /* DDRII, DDR2x */
938 pVBInfo
->ram_bus
= 32; /* 32 bits */
939 pVBInfo
->ram_channel
= 2; /* 2 Channel */
940 xgifb_reg_set(pVBInfo
->P3c4
, 0x13, 0xA1);
941 xgifb_reg_set(pVBInfo
->P3c4
, 0x14, 0x44);
943 if (XGINew_ReadWriteRest(24, 23, pVBInfo
) == 1)
946 xgifb_reg_set(pVBInfo
->P3c4
, 0x13, 0x21);
947 xgifb_reg_set(pVBInfo
->P3c4
, 0x14, 0x34);
948 if (XGINew_ReadWriteRest(23, 22, pVBInfo
) == 1)
951 pVBInfo
->ram_channel
= 1; /* Single Channel */
952 xgifb_reg_set(pVBInfo
->P3c4
, 0x13, 0xA1);
953 xgifb_reg_set(pVBInfo
->P3c4
, 0x14, 0x40);
955 if (XGINew_ReadWriteRest(23, 22, pVBInfo
) == 1)
958 xgifb_reg_set(pVBInfo
->P3c4
, 0x13, 0x21);
959 xgifb_reg_set(pVBInfo
->P3c4
, 0x14, 0x30);
962 pVBInfo
->ram_bus
= 64; /* 64 bits */
963 pVBInfo
->ram_channel
= 1; /* 1 channels */
964 xgifb_reg_set(pVBInfo
->P3c4
, 0x13, 0xA1);
965 xgifb_reg_set(pVBInfo
->P3c4
, 0x14, 0x52);
967 if (XGINew_ReadWriteRest(24, 23, pVBInfo
) == 1)
970 xgifb_reg_set(pVBInfo
->P3c4
, 0x13, 0x21);
971 xgifb_reg_set(pVBInfo
->P3c4
, 0x14, 0x42);
979 if (XGINew_CheckFrequence(pVBInfo
) == 1) { /* DDRII */
980 pVBInfo
->ram_bus
= 32; /* 32 bits */
981 pVBInfo
->ram_channel
= 3;
982 xgifb_reg_set(pVBInfo
->P3c4
, 0x13, 0xA1);
983 xgifb_reg_set(pVBInfo
->P3c4
, 0x14, 0x4C);
985 if (XGINew_ReadWriteRest(25, 23, pVBInfo
) == 1)
988 pVBInfo
->ram_channel
= 2; /* 2 channels */
989 xgifb_reg_set(pVBInfo
->P3c4
, 0x14, 0x48);
991 if (XGINew_ReadWriteRest(24, 23, pVBInfo
) == 1)
994 xgifb_reg_set(pVBInfo
->P3c4
, 0x13, 0x21);
995 xgifb_reg_set(pVBInfo
->P3c4
, 0x14, 0x3C);
997 if (XGINew_ReadWriteRest(24, 23, pVBInfo
) == 1) {
998 pVBInfo
->ram_channel
= 3; /* 4 channels */
1000 pVBInfo
->ram_channel
= 2; /* 2 channels */
1001 xgifb_reg_set(pVBInfo
->P3c4
, 0x14, 0x38);
1004 pVBInfo
->ram_bus
= 64; /* 64 bits */
1005 pVBInfo
->ram_channel
= 2; /* 2 channels */
1006 xgifb_reg_set(pVBInfo
->P3c4
, 0x13, 0xA1);
1007 xgifb_reg_set(pVBInfo
->P3c4
, 0x14, 0x5A);
1009 if (XGINew_ReadWriteRest(25, 24, pVBInfo
) == 1) {
1012 xgifb_reg_set(pVBInfo
->P3c4
, 0x13, 0x21);
1013 xgifb_reg_set(pVBInfo
->P3c4
, 0x14, 0x4A);
1020 static int XGINew_DDRSizing340(struct xgi_hw_device_info
*HwDeviceExtension
,
1021 struct vb_device_info
*pVBInfo
)
1024 unsigned short memsize
, addr
;
1026 xgifb_reg_set(pVBInfo
->P3c4
, 0x15, 0x00); /* noninterleaving */
1027 xgifb_reg_set(pVBInfo
->P3c4
, 0x1C, 0x00); /* nontiling */
1028 XGINew_CheckChannel(HwDeviceExtension
, pVBInfo
);
1030 if (HwDeviceExtension
->jChipType
>= XG20
) {
1031 for (i
= 0; i
< 12; i
++) {
1032 XGINew_SetDRAMSizingType(i
,
1033 XGINew_DDRDRAM_TYPE20
,
1035 memsize
= XGINew_SetDRAMSize20Reg(i
,
1036 XGINew_DDRDRAM_TYPE20
,
1041 addr
= memsize
+ (pVBInfo
->ram_channel
- 2) + 20;
1042 if ((HwDeviceExtension
->ulVideoMemorySize
- 1) <
1043 (unsigned long) (1 << addr
))
1046 if (XGINew_ReadWriteRest(addr
, 5, pVBInfo
) == 1)
1050 for (i
= 0; i
< 4; i
++) {
1051 XGINew_SetDRAMSizingType(i
,
1052 XGINew_DDRDRAM_TYPE340
,
1054 memsize
= XGINew_SetDRAMSizeReg(i
,
1055 XGINew_DDRDRAM_TYPE340
,
1061 addr
= memsize
+ (pVBInfo
->ram_channel
- 2) + 20;
1062 if ((HwDeviceExtension
->ulVideoMemorySize
- 1) <
1063 (unsigned long) (1 << addr
))
1066 if (XGINew_ReadWriteRest(addr
, 9, pVBInfo
) == 1)
1073 static void XGINew_SetDRAMSize_340(struct xgifb_video_info
*xgifb_info
,
1074 struct xgi_hw_device_info
*HwDeviceExtension
,
1075 struct vb_device_info
*pVBInfo
)
1077 unsigned short data
;
1079 pVBInfo
->FBAddr
= HwDeviceExtension
->pjVideoMemoryAddress
;
1081 XGISetModeNew(xgifb_info
, HwDeviceExtension
, 0x2e);
1083 data
= xgifb_reg_get(pVBInfo
->P3c4
, 0x21);
1084 /* disable read cache */
1085 xgifb_reg_set(pVBInfo
->P3c4
, 0x21, (unsigned short) (data
& 0xDF));
1086 XGI_DisplayOff(xgifb_info
, HwDeviceExtension
, pVBInfo
);
1088 /* data = xgifb_reg_get(pVBInfo->P3c4, 0x1); */
1089 /* data |= 0x20 ; */
1090 /* xgifb_reg_set(pVBInfo->P3c4, 0x01, data); *//* Turn OFF Display */
1091 XGINew_DDRSizing340(HwDeviceExtension
, pVBInfo
);
1092 data
= xgifb_reg_get(pVBInfo
->P3c4
, 0x21);
1093 /* enable read cache */
1094 xgifb_reg_set(pVBInfo
->P3c4
, 0x21, (unsigned short) (data
| 0x20));
1097 static u8
*xgifb_copy_rom(struct pci_dev
*dev
, size_t *rom_size
)
1099 void __iomem
*rom_address
;
1102 rom_address
= pci_map_rom(dev
, rom_size
);
1103 if (rom_address
== NULL
)
1106 rom_copy
= vzalloc(XGIFB_ROM_SIZE
);
1107 if (rom_copy
== NULL
)
1110 *rom_size
= min_t(size_t, *rom_size
, XGIFB_ROM_SIZE
);
1111 memcpy_fromio(rom_copy
, rom_address
, *rom_size
);
1114 pci_unmap_rom(dev
, rom_address
);
1118 static void xgifb_read_vbios(struct pci_dev
*pdev
,
1119 struct vb_device_info
*pVBInfo
)
1121 struct xgifb_video_info
*xgifb_info
= pci_get_drvdata(pdev
);
1125 struct XGI21_LVDSCapStruct
*lvds
;
1129 if (xgifb_info
->chip
!= XG21
)
1131 pVBInfo
->IF_DEF_LVDS
= 0;
1132 vbios
= xgifb_copy_rom(pdev
, &vbios_size
);
1133 if (vbios
== NULL
) {
1134 dev_err(&pdev
->dev
, "video BIOS not available\n");
1137 if (vbios_size
<= 0x65)
1140 * The user can ignore the LVDS bit in the BIOS and force the display
1143 if (!(vbios
[0x65] & 0x1) &&
1144 (!xgifb_info
->display2_force
||
1145 xgifb_info
->display2
!= XGIFB_DISP_LCD
)) {
1149 if (vbios_size
<= 0x317)
1151 i
= vbios
[0x316] | (vbios
[0x317] << 8);
1152 if (vbios_size
<= i
- 1)
1160 * Read the LVDS table index scratch register set by the BIOS.
1162 entry
= xgifb_reg_get(xgifb_info
->dev_info
.P3d4
, 0x36);
1166 lvds
= &xgifb_info
->lvds_data
;
1167 if (vbios_size
<= i
+ 24)
1169 lvds
->LVDS_Capability
= vbios
[i
] | (vbios
[i
+ 1] << 8);
1170 lvds
->LVDSHT
= vbios
[i
+ 2] | (vbios
[i
+ 3] << 8);
1171 lvds
->LVDSVT
= vbios
[i
+ 4] | (vbios
[i
+ 5] << 8);
1172 lvds
->LVDSHDE
= vbios
[i
+ 6] | (vbios
[i
+ 7] << 8);
1173 lvds
->LVDSVDE
= vbios
[i
+ 8] | (vbios
[i
+ 9] << 8);
1174 lvds
->LVDSHFP
= vbios
[i
+ 10] | (vbios
[i
+ 11] << 8);
1175 lvds
->LVDSVFP
= vbios
[i
+ 12] | (vbios
[i
+ 13] << 8);
1176 lvds
->LVDSHSYNC
= vbios
[i
+ 14] | (vbios
[i
+ 15] << 8);
1177 lvds
->LVDSVSYNC
= vbios
[i
+ 16] | (vbios
[i
+ 17] << 8);
1178 lvds
->VCLKData1
= vbios
[i
+ 18];
1179 lvds
->VCLKData2
= vbios
[i
+ 19];
1180 lvds
->PSC_S1
= vbios
[i
+ 20];
1181 lvds
->PSC_S2
= vbios
[i
+ 21];
1182 lvds
->PSC_S3
= vbios
[i
+ 22];
1183 lvds
->PSC_S4
= vbios
[i
+ 23];
1184 lvds
->PSC_S5
= vbios
[i
+ 24];
1186 pVBInfo
->IF_DEF_LVDS
= 1;
1189 dev_err(&pdev
->dev
, "video BIOS corrupted\n");
1193 static void XGINew_ChkSenseStatus(struct xgi_hw_device_info
*HwDeviceExtension
,
1194 struct vb_device_info
*pVBInfo
)
1196 unsigned short tempbx
= 0, temp
, tempcx
, CR3CData
;
1198 temp
= xgifb_reg_get(pVBInfo
->P3d4
, 0x32);
1200 if (temp
& Monitor1Sense
)
1201 tempbx
|= ActiveCRT1
;
1202 if (temp
& LCDSense
)
1203 tempbx
|= ActiveLCD
;
1204 if (temp
& Monitor2Sense
)
1205 tempbx
|= ActiveCRT2
;
1206 if (temp
& TVSense
) {
1208 if (temp
& AVIDEOSense
)
1209 tempbx
|= (ActiveAVideo
<< 8);
1210 if (temp
& SVIDEOSense
)
1211 tempbx
|= (ActiveSVideo
<< 8);
1212 if (temp
& SCARTSense
)
1213 tempbx
|= (ActiveSCART
<< 8);
1214 if (temp
& HiTVSense
)
1215 tempbx
|= (ActiveHiTV
<< 8);
1216 if (temp
& YPbPrSense
)
1217 tempbx
|= (ActiveYPbPr
<< 8);
1220 tempcx
= xgifb_reg_get(pVBInfo
->P3d4
, 0x3d);
1221 tempcx
|= (xgifb_reg_get(pVBInfo
->P3d4
, 0x3e) << 8);
1223 if (tempbx
& tempcx
) {
1224 CR3CData
= xgifb_reg_get(pVBInfo
->P3d4
, 0x3c);
1225 if (!(CR3CData
& DisplayDeviceFromCMOS
)) {
1227 if (*pVBInfo
->pSoftSetting
& ModeSoftSetting
)
1232 if (*pVBInfo
->pSoftSetting
& ModeSoftSetting
)
1237 xgifb_reg_set(pVBInfo
->P3d4
, 0x3d, (tempbx
& 0x00FF));
1238 xgifb_reg_set(pVBInfo
->P3d4
, 0x3e, ((tempbx
& 0xFF00) >> 8));
1241 static void XGINew_SetModeScratch(struct xgi_hw_device_info
*HwDeviceExtension
,
1242 struct vb_device_info
*pVBInfo
)
1244 unsigned short temp
, tempcl
= 0, tempch
= 0, CR31Data
, CR38Data
;
1246 temp
= xgifb_reg_get(pVBInfo
->P3d4
, 0x3d);
1247 temp
|= xgifb_reg_get(pVBInfo
->P3d4
, 0x3e) << 8;
1248 temp
|= (xgifb_reg_get(pVBInfo
->P3d4
, 0x31) & (DriverMode
>> 8)) << 8;
1250 if (pVBInfo
->IF_DEF_CRT2Monitor
== 1) {
1251 if (temp
& ActiveCRT2
)
1252 tempcl
= SetCRT2ToRAMDAC
;
1255 if (temp
& ActiveLCD
) {
1256 tempcl
|= SetCRT2ToLCD
;
1257 if (temp
& DriverMode
) {
1258 if (temp
& ActiveTV
) {
1259 tempch
= SetToLCDA
| EnableDualEdge
;
1260 temp
^= SetCRT2ToLCD
;
1262 if ((temp
>> 8) & ActiveAVideo
)
1263 tempcl
|= SetCRT2ToAVIDEO
;
1264 if ((temp
>> 8) & ActiveSVideo
)
1265 tempcl
|= SetCRT2ToSVIDEO
;
1266 if ((temp
>> 8) & ActiveSCART
)
1267 tempcl
|= SetCRT2ToSCART
;
1269 if (pVBInfo
->IF_DEF_HiVision
== 1) {
1270 if ((temp
>> 8) & ActiveHiTV
)
1271 tempcl
|= SetCRT2ToHiVisionTV
;
1274 if (pVBInfo
->IF_DEF_YPbPr
== 1) {
1275 if ((temp
>> 8) & ActiveYPbPr
)
1281 if ((temp
>> 8) & ActiveAVideo
)
1282 tempcl
|= SetCRT2ToAVIDEO
;
1283 if ((temp
>> 8) & ActiveSVideo
)
1284 tempcl
|= SetCRT2ToSVIDEO
;
1285 if ((temp
>> 8) & ActiveSCART
)
1286 tempcl
|= SetCRT2ToSCART
;
1288 if (pVBInfo
->IF_DEF_HiVision
== 1) {
1289 if ((temp
>> 8) & ActiveHiTV
)
1290 tempcl
|= SetCRT2ToHiVisionTV
;
1293 if (pVBInfo
->IF_DEF_YPbPr
== 1) {
1294 if ((temp
>> 8) & ActiveYPbPr
)
1299 tempcl
|= SetSimuScanMode
;
1300 if ((!(temp
& ActiveCRT1
)) && ((temp
& ActiveLCD
) || (temp
& ActiveTV
)
1301 || (temp
& ActiveCRT2
)))
1302 tempcl
^= (SetSimuScanMode
| SwitchToCRT2
);
1303 if ((temp
& ActiveLCD
) && (temp
& ActiveTV
))
1304 tempcl
^= (SetSimuScanMode
| SwitchToCRT2
);
1305 xgifb_reg_set(pVBInfo
->P3d4
, 0x30, tempcl
);
1307 CR31Data
= xgifb_reg_get(pVBInfo
->P3d4
, 0x31);
1308 CR31Data
&= ~(SetNotSimuMode
>> 8);
1309 if (!(temp
& ActiveCRT1
))
1310 CR31Data
|= (SetNotSimuMode
>> 8);
1311 CR31Data
&= ~(DisableCRT2Display
>> 8);
1312 if (!((temp
& ActiveLCD
) || (temp
& ActiveTV
) || (temp
& ActiveCRT2
)))
1313 CR31Data
|= (DisableCRT2Display
>> 8);
1314 xgifb_reg_set(pVBInfo
->P3d4
, 0x31, CR31Data
);
1316 CR38Data
= xgifb_reg_get(pVBInfo
->P3d4
, 0x38);
1317 CR38Data
&= ~SetYPbPr
;
1319 xgifb_reg_set(pVBInfo
->P3d4
, 0x38, CR38Data
);
1323 static unsigned short XGINew_SenseLCD(struct xgi_hw_device_info
1325 struct vb_device_info
*pVBInfo
)
1327 unsigned short temp
;
1330 if (HwDeviceExtension
->ulCRT2LCDType
== LCD_UNKNOWN
) {
1333 temp
= (unsigned short) HwDeviceExtension
->ulCRT2LCDType
;
1334 switch (HwDeviceExtension
->ulCRT2LCDType
) {
1362 xgifb_reg_and_or(pVBInfo
->P3d4
, 0x36, 0xF0, temp
);
1367 static void XGINew_GetXG21Sense(struct xgi_hw_device_info
*HwDeviceExtension
,
1368 struct vb_device_info
*pVBInfo
)
1373 if (pVBInfo
->IF_DEF_LVDS
) { /* For XG21 LVDS */
1374 xgifb_reg_or(pVBInfo
->P3d4
, 0x32, LCDSense
);
1376 xgifb_reg_and_or(pVBInfo
->P3d4
, 0x38, ~0xE0, 0xC0);
1379 /* Enable GPIOA/B read */
1380 xgifb_reg_and_or(pVBInfo
->P3d4
, 0x4A, ~0x03, 0x03);
1381 Temp
= xgifb_reg_get(pVBInfo
->P3d4
, 0x48) & 0xC0;
1382 if (Temp
== 0xC0) { /* DVI & DVO GPIOA/B pull high */
1383 XGINew_SenseLCD(HwDeviceExtension
, pVBInfo
);
1384 xgifb_reg_or(pVBInfo
->P3d4
, 0x32, LCDSense
);
1385 /* Enable read GPIOF */
1386 xgifb_reg_and_or(pVBInfo
->P3d4
, 0x4A, ~0x20, 0x20);
1387 Temp
= xgifb_reg_get(pVBInfo
->P3d4
, 0x48) & 0x04;
1389 xgifb_reg_and_or(pVBInfo
->P3d4
,
1392 0x80); /* TMDS on chip */
1394 xgifb_reg_and_or(pVBInfo
->P3d4
,
1397 0xA0); /* Only DVO on chip */
1398 /* Disable read GPIOF */
1399 xgifb_reg_and(pVBInfo
->P3d4
, 0x4A, ~0x20);
1406 static void XGINew_GetXG27Sense(struct xgi_hw_device_info
*HwDeviceExtension
,
1407 struct vb_device_info
*pVBInfo
)
1409 unsigned char Temp
, bCR4A
;
1411 pVBInfo
->IF_DEF_LVDS
= 0;
1412 bCR4A
= xgifb_reg_get(pVBInfo
->P3d4
, 0x4A);
1413 /* Enable GPIOA/B/C read */
1414 xgifb_reg_and_or(pVBInfo
->P3d4
, 0x4A, ~0x07, 0x07);
1415 Temp
= xgifb_reg_get(pVBInfo
->P3d4
, 0x48) & 0x07;
1416 xgifb_reg_set(pVBInfo
->P3d4
, 0x4A, bCR4A
);
1420 xgifb_reg_and_or(pVBInfo
->P3d4
, 0x38, ~0xE0, 0xC0);
1421 xgifb_reg_set(pVBInfo
->P3d4
, 0x30, 0x21);
1423 /* TMDS/DVO setting */
1424 xgifb_reg_and_or(pVBInfo
->P3d4
, 0x38, ~0xE0, 0xA0);
1426 xgifb_reg_or(pVBInfo
->P3d4
, 0x32, LCDSense
);
1430 static unsigned char GetXG21FPBits(struct vb_device_info
*pVBInfo
)
1432 unsigned char CR38
, CR4A
, temp
;
1434 CR4A
= xgifb_reg_get(pVBInfo
->P3d4
, 0x4A);
1435 /* enable GPIOE read */
1436 xgifb_reg_and_or(pVBInfo
->P3d4
, 0x4A, ~0x10, 0x10);
1437 CR38
= xgifb_reg_get(pVBInfo
->P3d4
, 0x38);
1439 if ((CR38
& 0xE0) > 0x80) {
1440 temp
= xgifb_reg_get(pVBInfo
->P3d4
, 0x48);
1445 xgifb_reg_set(pVBInfo
->P3d4
, 0x4A, CR4A
);
1450 static unsigned char GetXG27FPBits(struct vb_device_info
*pVBInfo
)
1452 unsigned char CR4A
, temp
;
1454 CR4A
= xgifb_reg_get(pVBInfo
->P3d4
, 0x4A);
1455 /* enable GPIOA/B/C read */
1456 xgifb_reg_and_or(pVBInfo
->P3d4
, 0x4A, ~0x03, 0x03);
1457 temp
= xgifb_reg_get(pVBInfo
->P3d4
, 0x48);
1461 temp
= ((temp
& 0x04) >> 1) || ((~temp
) & 0x01);
1463 xgifb_reg_set(pVBInfo
->P3d4
, 0x4A, CR4A
);
1468 unsigned char XGIInitNew(struct pci_dev
*pdev
)
1470 struct xgifb_video_info
*xgifb_info
= pci_get_drvdata(pdev
);
1471 struct xgi_hw_device_info
*HwDeviceExtension
= &xgifb_info
->hw_info
;
1472 struct vb_device_info VBINF
;
1473 struct vb_device_info
*pVBInfo
= &VBINF
;
1474 unsigned char i
, temp
= 0, temp1
;
1475 /* VBIOSVersion[5]; */
1477 /* unsigned long j, k; */
1479 pVBInfo
->FBAddr
= HwDeviceExtension
->pjVideoMemoryAddress
;
1481 pVBInfo
->BaseAddr
= (unsigned long) HwDeviceExtension
->pjIOAddress
;
1483 /* Newdebugcode(0x99); */
1485 if (pVBInfo
->FBAddr
== NULL
) {
1486 printk("\n pVBInfo->FBAddr == 0 ");
1490 if (pVBInfo
->BaseAddr
== 0) {
1491 printk("\npVBInfo->BaseAddr == 0 ");
1496 outb(0x67, (pVBInfo
->BaseAddr
+ 0x12)); /* 3c2 <- 67 ,ynlai */
1498 pVBInfo
->ISXPDOS
= 0;
1503 /* VBIOSVersion[4] = 0x0; */
1505 /* 09/07/99 modify by domao */
1507 pVBInfo
->P3c4
= pVBInfo
->BaseAddr
+ 0x14;
1508 pVBInfo
->P3d4
= pVBInfo
->BaseAddr
+ 0x24;
1509 pVBInfo
->P3c0
= pVBInfo
->BaseAddr
+ 0x10;
1510 pVBInfo
->P3ce
= pVBInfo
->BaseAddr
+ 0x1e;
1511 pVBInfo
->P3c2
= pVBInfo
->BaseAddr
+ 0x12;
1512 pVBInfo
->P3ca
= pVBInfo
->BaseAddr
+ 0x1a;
1513 pVBInfo
->P3c6
= pVBInfo
->BaseAddr
+ 0x16;
1514 pVBInfo
->P3c7
= pVBInfo
->BaseAddr
+ 0x17;
1515 pVBInfo
->P3c8
= pVBInfo
->BaseAddr
+ 0x18;
1516 pVBInfo
->P3c9
= pVBInfo
->BaseAddr
+ 0x19;
1517 pVBInfo
->P3da
= pVBInfo
->BaseAddr
+ 0x2A;
1518 pVBInfo
->Part0Port
= pVBInfo
->BaseAddr
+ XGI_CRT2_PORT_00
;
1519 pVBInfo
->Part1Port
= pVBInfo
->BaseAddr
+ XGI_CRT2_PORT_04
;
1520 pVBInfo
->Part2Port
= pVBInfo
->BaseAddr
+ XGI_CRT2_PORT_10
;
1521 pVBInfo
->Part3Port
= pVBInfo
->BaseAddr
+ XGI_CRT2_PORT_12
;
1522 pVBInfo
->Part4Port
= pVBInfo
->BaseAddr
+ XGI_CRT2_PORT_14
;
1523 pVBInfo
->Part5Port
= pVBInfo
->BaseAddr
+ XGI_CRT2_PORT_14
+ 2;
1526 if (HwDeviceExtension
->jChipType
< XG20
) /* kuku 2004/06/25 */
1527 /* Run XGI_GetVBType before InitTo330Pointer */
1528 XGI_GetVBType(pVBInfo
);
1530 InitTo330Pointer(HwDeviceExtension
->jChipType
, pVBInfo
);
1532 xgifb_read_vbios(pdev
, pVBInfo
);
1535 xgifb_reg_set(pVBInfo
->P3c4
, 0x05, 0x86);
1538 /* GetXG21Sense (GPIO) */
1539 if (HwDeviceExtension
->jChipType
== XG21
)
1540 XGINew_GetXG21Sense(HwDeviceExtension
, pVBInfo
);
1542 if (HwDeviceExtension
->jChipType
== XG27
)
1543 XGINew_GetXG27Sense(HwDeviceExtension
, pVBInfo
);
1547 /* 2.Reset Extended register */
1549 for (i
= 0x06; i
< 0x20; i
++)
1550 xgifb_reg_set(pVBInfo
->P3c4
, i
, 0);
1552 for (i
= 0x21; i
<= 0x27; i
++)
1553 xgifb_reg_set(pVBInfo
->P3c4
, i
, 0);
1555 /* for(i = 0x06; i <= 0x27; i++) */
1556 /* xgifb_reg_set(pVBInfo->P3c4, i, 0); */
1560 for (i
= 0x31; i
<= 0x3B; i
++)
1561 xgifb_reg_set(pVBInfo
->P3c4
, i
, 0);
1564 /* [Hsuan] 2004/08/20 Auto over driver for XG42 */
1565 if (HwDeviceExtension
->jChipType
== XG42
)
1566 xgifb_reg_set(pVBInfo
->P3c4
, 0x3B, 0xC0);
1568 /* for (i = 0x30; i <= 0x3F; i++) */
1569 /* xgifb_reg_set(pVBInfo->P3d4, i, 0); */
1571 for (i
= 0x79; i
<= 0x7C; i
++)
1572 xgifb_reg_set(pVBInfo
->P3d4
, i
, 0); /* shampoo 0208 */
1576 if (HwDeviceExtension
->jChipType
>= XG20
)
1577 xgifb_reg_set(pVBInfo
->P3d4
, 0x97, *pVBInfo
->pXGINew_CR97
);
1581 pVBInfo->ram_type = XGINew_GetXG20DRAMType(HwDeviceExtension, pVBInfo);
1586 /* 4.SetDefExt1Regs begin */
1587 xgifb_reg_set(pVBInfo
->P3c4
, 0x07, *pVBInfo
->pSR07
);
1588 if (HwDeviceExtension
->jChipType
== XG27
) {
1589 xgifb_reg_set(pVBInfo
->P3c4
, 0x40, *pVBInfo
->pSR40
);
1590 xgifb_reg_set(pVBInfo
->P3c4
, 0x41, *pVBInfo
->pSR41
);
1592 xgifb_reg_set(pVBInfo
->P3c4
, 0x11, 0x0F);
1593 xgifb_reg_set(pVBInfo
->P3c4
, 0x1F, *pVBInfo
->pSR1F
);
1594 /* xgifb_reg_set(pVBInfo->P3c4, 0x20, 0x20); */
1595 /* alan, 2001/6/26 Frame buffer can read/write SR20 */
1596 xgifb_reg_set(pVBInfo
->P3c4
, 0x20, 0xA0);
1597 /* Hsuan, 2006/01/01 H/W request for slow corner chip */
1598 xgifb_reg_set(pVBInfo
->P3c4
, 0x36, 0x70);
1599 if (HwDeviceExtension
->jChipType
== XG27
) /* Alan 12/07/2006 */
1600 xgifb_reg_set(pVBInfo
->P3c4
, 0x36, *pVBInfo
->pSR36
);
1603 /* xgifb_reg_set(pVBInfo->P3c4, 0x11, SR11); */
1607 if (HwDeviceExtension
->jChipType
< XG20
) { /* kuku 2004/06/25 */
1612 temp1 = xgifb_reg_get(pVBInfo->P3c4, 0x3B);
1614 if (temp1 == 0x02) {
1615 outl(0x80000000, 0xcf8);
1616 ChipsetID = inl(0x0cfc);
1617 outl(0x8000002C, 0xcf8);
1618 VendorID = inl(0x0cfc);
1619 VendorID &= 0x0000FFFF;
1620 outl(0x8001002C, 0xcf8);
1621 GraphicVendorID = inl(0x0cfc);
1622 GraphicVendorID &= 0x0000FFFF;
1624 if (ChipsetID == 0x7301039)
1625 xgifb_reg_set(pVBInfo->P3d4, 0x5F, 0x09);
1627 ChipsetID &= 0x0000FFFF;
1629 if ((ChipsetID == 0x700E) ||
1630 (ChipsetID == 0x1022) ||
1631 (ChipsetID == 0x1106) ||
1632 (ChipsetID == 0x10DE)) {
1633 if (ChipsetID == 0x1106) {
1634 if ((VendorID == 0x1019) &&
1635 (GraphicVendorID == 0x1019))
1636 xgifb_reg_set(pVBInfo->P3d4,
1640 xgifb_reg_set(pVBInfo->P3d4,
1644 xgifb_reg_set(pVBInfo->P3d4,
1654 /* Set AGP customize registers (in SetDefAGPRegs) Start */
1655 for (i
= 0x47; i
<= 0x4C; i
++)
1656 xgifb_reg_set(pVBInfo
->P3d4
,
1658 pVBInfo
->AGPReg
[i
- 0x47]);
1660 for (i
= 0x70; i
<= 0x71; i
++)
1661 xgifb_reg_set(pVBInfo
->P3d4
,
1663 pVBInfo
->AGPReg
[6 + i
- 0x70]);
1665 for (i
= 0x74; i
<= 0x77; i
++)
1666 xgifb_reg_set(pVBInfo
->P3d4
,
1668 pVBInfo
->AGPReg
[8 + i
- 0x74]);
1669 /* Set AGP customize registers (in SetDefAGPRegs) End */
1670 /* [Hsuan]2004/12/14 AGP Input Delay Adjustment on 850 */
1671 /* outl(0x80000000, 0xcf8); */
1672 /* ChipsetID = inl(0x0cfc); */
1673 /* if (ChipsetID == 0x25308086) */
1674 /* xgifb_reg_set(pVBInfo->P3d4, 0x77, 0xF0); */
1676 pci_read_config_dword(pdev
, 0x50, &Temp
);
1681 xgifb_reg_set(pVBInfo
->P3d4
, 0x48, 0x20); /* CR48 */
1686 xgifb_reg_set(pVBInfo
->P3c4
, 0x23, *pVBInfo
->pSR23
);
1687 xgifb_reg_set(pVBInfo
->P3c4
, 0x24, *pVBInfo
->pSR24
);
1688 xgifb_reg_set(pVBInfo
->P3c4
, 0x25, pVBInfo
->SR25
[0]);
1691 if (HwDeviceExtension
->jChipType
< XG20
) { /* kuku 2004/06/25 */
1693 XGI_UnLockCRT2(HwDeviceExtension
, pVBInfo
);
1694 /* alan, disable VideoCapture */
1695 xgifb_reg_and_or(pVBInfo
->Part0Port
, 0x3F, 0xEF, 0x00);
1696 xgifb_reg_set(pVBInfo
->Part1Port
, 0x00, 0x00);
1697 /* chk if BCLK>=100MHz */
1698 temp1
= (unsigned char) xgifb_reg_get(pVBInfo
->P3d4
, 0x7B);
1699 temp
= (unsigned char) ((temp1
>> 4) & 0x0F);
1701 xgifb_reg_set(pVBInfo
->Part1Port
,
1703 (*pVBInfo
->pCRT2Data_1_2
));
1707 xgifb_reg_set(pVBInfo
->Part1Port
, 0x2E, 0x08); /* use VB */
1710 xgifb_reg_set(pVBInfo
->P3c4
, 0x27, 0x1F);
1712 if ((HwDeviceExtension
->jChipType
== XG42
) &&
1713 XGINew_GetXG20DRAMType(HwDeviceExtension
, pVBInfo
) != 0) {
1715 xgifb_reg_set(pVBInfo
->P3c4
,
1717 (*pVBInfo
->pSR31
& 0x3F) | 0x40);
1718 xgifb_reg_set(pVBInfo
->P3c4
,
1720 (*pVBInfo
->pSR32
& 0xFC) | 0x01);
1722 xgifb_reg_set(pVBInfo
->P3c4
, 0x31, *pVBInfo
->pSR31
);
1723 xgifb_reg_set(pVBInfo
->P3c4
, 0x32, *pVBInfo
->pSR32
);
1725 xgifb_reg_set(pVBInfo
->P3c4
, 0x33, *pVBInfo
->pSR33
);
1729 SetPowerConsume (HwDeviceExtension, pVBInfo->P3c4); */
1731 if (HwDeviceExtension
->jChipType
< XG20
) { /* kuku 2004/06/25 */
1732 if (XGI_BridgeIsOn(pVBInfo
) == 1) {
1733 if (pVBInfo
->IF_DEF_LVDS
== 0) {
1734 xgifb_reg_set(pVBInfo
->Part2Port
, 0x00, 0x1C);
1735 xgifb_reg_set(pVBInfo
->Part4Port
,
1737 *pVBInfo
->pCRT2Data_4_D
);
1738 xgifb_reg_set(pVBInfo
->Part4Port
,
1740 *pVBInfo
->pCRT2Data_4_E
);
1741 xgifb_reg_set(pVBInfo
->Part4Port
,
1743 *pVBInfo
->pCRT2Data_4_10
);
1744 xgifb_reg_set(pVBInfo
->Part4Port
, 0x0F, 0x3F);
1747 XGI_LockCRT2(HwDeviceExtension
, pVBInfo
);
1756 XGI_SenseCRT1(pVBInfo
);
1759 /* XGINew_DetectMonitor(HwDeviceExtension); */
1760 if (HwDeviceExtension
->jChipType
== XG21
) {
1763 xgifb_reg_and_or(pVBInfo
->P3d4
,
1766 Monitor1Sense
); /* Z9 default has CRT */
1767 temp
= GetXG21FPBits(pVBInfo
);
1768 xgifb_reg_and_or(pVBInfo
->P3d4
, 0x37, ~0x01, temp
);
1772 if (HwDeviceExtension
->jChipType
== XG27
) {
1773 xgifb_reg_and_or(pVBInfo
->P3d4
,
1776 Monitor1Sense
); /* Z9 default has CRT */
1777 temp
= GetXG27FPBits(pVBInfo
);
1778 xgifb_reg_and_or(pVBInfo
->P3d4
, 0x37, ~0x03, temp
);
1782 pVBInfo
->ram_type
= XGINew_GetXG20DRAMType(HwDeviceExtension
, pVBInfo
);
1784 XGINew_SetDRAMDefaultRegister340(HwDeviceExtension
,
1789 XGINew_SetDRAMSize_340(xgifb_info
, HwDeviceExtension
, pVBInfo
);
1794 /* SetDefExt2Regs begin */
1797 temp = (unsigned char) xgifb_reg_get(pVBInfo->P3c4, 0x3A);
1803 *pVBInfo->pSR21 &= 0xEF;
1805 xgifb_reg_set(pVBInfo->P3c4, 0x21, *pVBInfo->pSR21);
1807 *pVBInfo->pSR22 &= 0x20;
1808 xgifb_reg_set(pVBInfo->P3c4, 0x22, *pVBInfo->pSR22);
1810 /* base = 0x80000000; */
1811 /* OutPortLong(0xcf8, base); */
1812 /* Temp = (InPortLong(0xcfc) & 0xFFFF); */
1813 /* if (Temp == 0x1039) { */
1814 xgifb_reg_set(pVBInfo
->P3c4
,
1816 (unsigned char) ((*pVBInfo
->pSR22
) & 0xFE));
1818 /* xgifb_reg_set(pVBInfo->P3c4, 0x22, *pVBInfo->pSR22); */
1821 xgifb_reg_set(pVBInfo
->P3c4
, 0x21, *pVBInfo
->pSR21
);
1825 XGINew_ChkSenseStatus(HwDeviceExtension
, pVBInfo
);
1826 XGINew_SetModeScratch(HwDeviceExtension
, pVBInfo
);
1830 xgifb_reg_set(pVBInfo
->P3d4
, 0x8c, 0x87);
1831 xgifb_reg_set(pVBInfo
->P3c4
, 0x14, 0x31);