4 * Mode initializing code (CRT2 section)
5 * for SiS 300/305/540/630/730,
6 * SiS 315/550/[M]650/651/[M]661[FGM]X/[M]74x[GX]/330/[M]76x[GX],
8 * (Universal module for Linux kernel framebuffer and X.org/XFree86 4.x)
10 * Copyright (C) 2001-2005 by Thomas Winischhofer, Vienna, Austria
12 * If distributed as part of the Linux kernel, the following license terms
15 * * This program is free software; you can redistribute it and/or modify
16 * * it under the terms of the GNU General Public License as published by
17 * * the Free Software Foundation; either version 2 of the named License,
18 * * or any later version.
20 * * This program is distributed in the hope that it will be useful,
21 * * but WITHOUT ANY WARRANTY; without even the implied warranty of
22 * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
23 * * GNU General Public License for more details.
25 * * You should have received a copy of the GNU General Public License
26 * * along with this program; if not, write to the Free Software
27 * * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA
29 * Otherwise, the following license terms apply:
31 * * Redistribution and use in source and binary forms, with or without
32 * * modification, are permitted provided that the following conditions
34 * * 1) Redistributions of source code must retain the above copyright
35 * * notice, this list of conditions and the following disclaimer.
36 * * 2) Redistributions in binary form must reproduce the above copyright
37 * * notice, this list of conditions and the following disclaimer in the
38 * * documentation and/or other materials provided with the distribution.
39 * * 3) The name of the author may not be used to endorse or promote products
40 * * derived from this software without specific prior written permission.
42 * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
43 * * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
44 * * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
45 * * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
46 * * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
47 * * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
48 * * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
49 * * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
50 * * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
51 * * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
53 * Author: Thomas Winischhofer <thomas@winischhofer.net>
55 * Formerly based on non-functional code-fragements for 300 series by SiS, Inc.
61 #define SET_EMI /* 302LV/ELV: Set EMI values */
65 #define SET_PWD /* 301/302LV: Set PWD */
68 #define COMPAL_HACK /* Needed for Compal 1400x1050 (EMI) */
69 #define COMPAQ_HACK /* Needed for Inventec/Compaq 1280x1024 (EMI) */
70 #define ASUS_HACK /* Needed for Asus A2H 1024x768 (EMI) */
74 #ifdef CONFIG_FB_SIS_300
78 #ifdef CONFIG_FB_SIS_315
82 #define SiS_I2CDELAY 1000
83 #define SiS_I2CDELAYSHORT 150
85 static unsigned short SiS_GetBIOSLCDResInfo(struct SiS_Private *SiS_Pr);
86 static void SiS_SetCH70xx(struct SiS_Private *SiS_Pr, unsigned short reg, unsigned char val);
88 /*********************************************/
89 /* HELPER: Lock/Unlock CRT2 */
90 /*********************************************/
93 SiS_UnLockCRT2(struct SiS_Private *SiS_Pr)
95 if(SiS_Pr->ChipType == XGI_20)
97 else if(SiS_Pr->ChipType >= SIS_315H)
98 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x2f,0x01);
100 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x24,0x01);
105 SiS_LockCRT2(struct SiS_Private *SiS_Pr)
107 if(SiS_Pr->ChipType == XGI_20)
109 else if(SiS_Pr->ChipType >= SIS_315H)
110 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x2F,0xFE);
112 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x24,0xFE);
115 /*********************************************/
116 /* HELPER: Write SR11 */
117 /*********************************************/
120 SiS_SetRegSR11ANDOR(struct SiS_Private *SiS_Pr, unsigned short DataAND, unsigned short DataOR)
122 if(SiS_Pr->ChipType >= SIS_661) {
126 SiS_SetRegANDOR(SiS_Pr->SiS_P3c4,0x11,DataAND,DataOR);
129 /*********************************************/
130 /* HELPER: Get Pointer to LCD structure */
131 /*********************************************/
133 #ifdef CONFIG_FB_SIS_315
134 static unsigned char *
135 GetLCDStructPtr661(struct SiS_Private *SiS_Pr)
137 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
138 unsigned char *myptr = NULL;
139 unsigned short romindex = 0, reg = 0, idx = 0;
141 /* Use the BIOS tables only for LVDS panels; TMDS is unreliable
142 * due to the variaty of panels the BIOS doesn't know about.
143 * Exception: If the BIOS has better knowledge (such as in case
144 * of machines with a 301C and a panel that does not support DDC)
145 * use the BIOS data as well.
148 if((SiS_Pr->SiS_ROMNew) &&
149 ((SiS_Pr->SiS_VBType & VB_SISLVDS) || (!SiS_Pr->PanelSelfDetected))) {
151 if(SiS_Pr->ChipType < SIS_661) reg = 0x3c;
154 idx = (SiS_GetReg(SiS_Pr->SiS_P3d4,reg) & 0x1f) * 26;
157 myptr = (unsigned char *)&SiS_LCDStruct661[idx];
159 romindex = SISGETROMW(0x100);
162 myptr = &ROMAddr[romindex];
168 static unsigned short
169 GetLCDStructPtr661_2(struct SiS_Private *SiS_Pr)
171 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
172 unsigned short romptr = 0;
174 /* Use the BIOS tables only for LVDS panels; TMDS is unreliable
175 * due to the variaty of panels the BIOS doesn't know about.
176 * Exception: If the BIOS has better knowledge (such as in case
177 * of machines with a 301C and a panel that does not support DDC)
178 * use the BIOS data as well.
181 if((SiS_Pr->SiS_ROMNew) &&
182 ((SiS_Pr->SiS_VBType & VB_SISLVDS) || (!SiS_Pr->PanelSelfDetected))) {
183 romptr = SISGETROMW(0x102);
184 romptr += ((SiS_GetReg(SiS_Pr->SiS_P3d4,0x36) >> 4) * SiS_Pr->SiS661LCD2TableSize);
191 /*********************************************/
192 /* Adjust Rate for CRT2 */
193 /*********************************************/
196 SiS_AdjustCRT2Rate(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex,
197 unsigned short RRTI, unsigned short *i)
199 unsigned short checkmask=0, modeid, infoflag;
201 modeid = SiS_Pr->SiS_RefIndex[RRTI + (*i)].ModeID;
203 if(SiS_Pr->SiS_VBType & VB_SISVB) {
205 if(SiS_Pr->SiS_VBInfo & SetCRT2ToRAMDAC) {
207 checkmask |= SupportRAMDAC2;
208 if(SiS_Pr->ChipType >= SIS_315H) {
209 checkmask |= SupportRAMDAC2_135;
210 if(SiS_Pr->SiS_VBType & VB_SIS30xBLV) {
211 checkmask |= SupportRAMDAC2_162;
212 if(SiS_Pr->SiS_VBType & VB_SISRAMDAC202) {
213 checkmask |= SupportRAMDAC2_202;
218 } else if(SiS_Pr->SiS_VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
220 checkmask |= SupportLCD;
221 if(SiS_Pr->ChipType >= SIS_315H) {
222 if(SiS_Pr->SiS_VBType & VB_SISVB) {
223 if((SiS_Pr->SiS_LCDInfo & DontExpandLCD) && (SiS_Pr->SiS_LCDInfo & LCDPass11)) {
224 if(modeid == 0x2e) checkmask |= Support64048060Hz;
229 } else if(SiS_Pr->SiS_VBInfo & SetCRT2ToHiVision) {
231 checkmask |= SupportHiVision;
233 } else if(SiS_Pr->SiS_VBInfo & (SetCRT2ToYPbPr525750|SetCRT2ToAVIDEO|SetCRT2ToSVIDEO|SetCRT2ToSCART)) {
235 checkmask |= SupportTV;
236 if(SiS_Pr->SiS_VBType & VB_SIS30xBLV) {
237 checkmask |= SupportTV1024;
238 if(SiS_Pr->SiS_VBInfo & SetCRT2ToYPbPr525750) {
239 if(SiS_Pr->SiS_TVMode & TVSetYPbPr750p) {
240 checkmask |= SupportYPbPr750p;
249 if(SiS_Pr->SiS_IF_DEF_CH70xx != 0) {
250 if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) {
251 checkmask |= SupportCHTV;
255 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) {
256 checkmask |= SupportLCD;
261 /* Look backwards in table for matching CRT2 mode */
262 for(; SiS_Pr->SiS_RefIndex[RRTI + (*i)].ModeID == modeid; (*i)--) {
263 infoflag = SiS_Pr->SiS_RefIndex[RRTI + (*i)].Ext_InfoFlag;
264 if(infoflag & checkmask) return true;
268 /* Look through the whole mode-section of the table from the beginning
269 * for a matching CRT2 mode if no mode was found yet.
271 for((*i) = 0; ; (*i)++) {
272 if(SiS_Pr->SiS_RefIndex[RRTI + (*i)].ModeID != modeid) break;
273 infoflag = SiS_Pr->SiS_RefIndex[RRTI + (*i)].Ext_InfoFlag;
274 if(infoflag & checkmask) return true;
279 /*********************************************/
281 /*********************************************/
284 SiS_GetRatePtr(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex)
286 unsigned short RRTI,i,backup_i;
287 unsigned short modeflag,index,temp,backupindex;
288 static const unsigned short LCDRefreshIndex[] = {
289 0x00, 0x00, 0x01, 0x01,
290 0x01, 0x01, 0x01, 0x01,
291 0x01, 0x01, 0x01, 0x01,
292 0x01, 0x01, 0x01, 0x01,
293 0x00, 0x00, 0x00, 0x00
296 /* Do NOT check for UseCustomMode here, will skrew up FIFO */
297 if(ModeNo == 0xfe) return 0;
300 modeflag = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_ModeFlag;
302 modeflag = SiS_Pr->SiS_EModeIDTable[ModeIdIndex].Ext_ModeFlag;
305 if(SiS_Pr->SiS_IF_DEF_CH70xx != 0) {
306 if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) {
307 if(modeflag & HalfDCLK) return 0;
311 if(ModeNo < 0x14) return 0xFFFF;
313 index = (SiS_GetReg(SiS_Pr->SiS_P3d4,0x33) >> SiS_Pr->SiS_SelectCRT2Rate) & 0x0F;
316 if(index > 0) index--;
318 if(SiS_Pr->SiS_SetFlag & ProgrammingCRT2) {
319 if(SiS_Pr->SiS_VBType & VB_SISVB) {
320 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) {
321 if(SiS_Pr->SiS_VBType & VB_NoLCD) index = 0;
322 else if(SiS_Pr->SiS_LCDInfo & DontExpandLCD) index = backupindex = 0;
324 if(SiS_Pr->SiS_VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
325 if(!(SiS_Pr->SiS_VBType & VB_NoLCD)) {
326 temp = LCDRefreshIndex[SiS_GetBIOSLCDResInfo(SiS_Pr)];
327 if(index > temp) index = temp;
331 if(SiS_Pr->SiS_VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) index = 0;
332 if(SiS_Pr->SiS_IF_DEF_CH70xx != 0) {
333 if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) index = 0;
338 RRTI = SiS_Pr->SiS_EModeIDTable[ModeIdIndex].REFindex;
339 ModeNo = SiS_Pr->SiS_RefIndex[RRTI].ModeID;
341 if(SiS_Pr->ChipType >= SIS_315H) {
342 if(!(SiS_Pr->SiS_VBInfo & DriverMode)) {
343 if( (SiS_Pr->SiS_EModeIDTable[ModeIdIndex].Ext_VESAID == 0x105) ||
344 (SiS_Pr->SiS_EModeIDTable[ModeIdIndex].Ext_VESAID == 0x107) ) {
345 if(backupindex <= 1) RRTI++;
352 if(SiS_Pr->SiS_RefIndex[RRTI + i].ModeID != ModeNo) break;
353 temp = SiS_Pr->SiS_RefIndex[RRTI + i].Ext_InfoFlag;
354 temp &= ModeTypeMask;
355 if(temp < SiS_Pr->SiS_ModeType) break;
358 } while(index != 0xFFFF);
360 if(!(SiS_Pr->SiS_VBInfo & SetCRT2ToRAMDAC)) {
361 if(SiS_Pr->SiS_VBInfo & SetInSlaveMode) {
362 temp = SiS_Pr->SiS_RefIndex[RRTI + i - 1].Ext_InfoFlag;
363 if(temp & InterlaceMode) i++;
369 if((SiS_Pr->SiS_SetFlag & ProgrammingCRT2) && (!(SiS_Pr->SiS_VBInfo & DisableCRT2Display))) {
371 if(!(SiS_AdjustCRT2Rate(SiS_Pr, ModeNo, ModeIdIndex, RRTI, &i))) {
379 /*********************************************/
380 /* STORE CRT2 INFO in CR34 */
381 /*********************************************/
384 SiS_SaveCRT2Info(struct SiS_Private *SiS_Pr, unsigned short ModeNo)
386 unsigned short temp1, temp2;
388 /* Store CRT1 ModeNo in CR34 */
389 SiS_SetReg(SiS_Pr->SiS_P3d4,0x34,ModeNo);
390 temp1 = (SiS_Pr->SiS_VBInfo & SetInSlaveMode) >> 8;
391 temp2 = ~(SetInSlaveMode >> 8);
392 SiS_SetRegANDOR(SiS_Pr->SiS_P3d4,0x31,temp2,temp1);
395 /*********************************************/
396 /* HELPER: GET SOME DATA FROM BIOS ROM */
397 /*********************************************/
399 #ifdef CONFIG_FB_SIS_300
401 SiS_CR36BIOSWord23b(struct SiS_Private *SiS_Pr)
403 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
404 unsigned short temp,temp1;
406 if(SiS_Pr->SiS_UseROM) {
407 if((ROMAddr[0x233] == 0x12) && (ROMAddr[0x234] == 0x34)) {
408 temp = 1 << ((SiS_GetReg(SiS_Pr->SiS_P3d4,0x36) >> 4) & 0x0f);
409 temp1 = SISGETROMW(0x23b);
410 if(temp1 & temp) return true;
417 SiS_CR36BIOSWord23d(struct SiS_Private *SiS_Pr)
419 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
420 unsigned short temp,temp1;
422 if(SiS_Pr->SiS_UseROM) {
423 if((ROMAddr[0x233] == 0x12) && (ROMAddr[0x234] == 0x34)) {
424 temp = 1 << ((SiS_GetReg(SiS_Pr->SiS_P3d4,0x36) >> 4) & 0x0f);
425 temp1 = SISGETROMW(0x23d);
426 if(temp1 & temp) return true;
433 /*********************************************/
434 /* HELPER: DELAY FUNCTIONS */
435 /*********************************************/
438 SiS_DDC2Delay(struct SiS_Private *SiS_Pr, unsigned int delaytime)
440 while (delaytime-- > 0)
441 SiS_GetReg(SiS_Pr->SiS_P3c4, 0x05);
444 #if defined(CONFIG_FB_SIS_300) || defined(CONFIG_FB_SIS_315)
446 SiS_GenericDelay(struct SiS_Private *SiS_Pr, unsigned short delay)
448 SiS_DDC2Delay(SiS_Pr, delay * 36);
452 #ifdef CONFIG_FB_SIS_315
454 SiS_LongDelay(struct SiS_Private *SiS_Pr, unsigned short delay)
457 SiS_GenericDelay(SiS_Pr, 6623);
462 #if defined(CONFIG_FB_SIS_300) || defined(CONFIG_FB_SIS_315)
464 SiS_ShortDelay(struct SiS_Private *SiS_Pr, unsigned short delay)
467 SiS_GenericDelay(SiS_Pr, 66);
473 SiS_PanelDelay(struct SiS_Private *SiS_Pr, unsigned short DelayTime)
475 #if defined(CONFIG_FB_SIS_300) || defined(CONFIG_FB_SIS_315)
476 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
477 unsigned short PanelID, DelayIndex, Delay=0;
480 if(SiS_Pr->ChipType < SIS_315H) {
482 #ifdef CONFIG_FB_SIS_300
484 PanelID = SiS_GetReg(SiS_Pr->SiS_P3d4,0x36);
485 if(SiS_Pr->SiS_VBType & VB_SISVB) {
486 if(SiS_Pr->SiS_VBType & VB_SIS301) PanelID &= 0xf7;
487 if(!(SiS_GetReg(SiS_Pr->SiS_P3c4,0x18) & 0x10)) PanelID = 0x12;
489 DelayIndex = PanelID >> 4;
490 if((DelayTime >= 2) && ((PanelID & 0x0f) == 1)) {
493 if(DelayTime >= 2) DelayTime -= 2;
494 if(!(DelayTime & 0x01)) {
495 Delay = SiS_Pr->SiS_PanelDelayTbl[DelayIndex].timer[0];
497 Delay = SiS_Pr->SiS_PanelDelayTbl[DelayIndex].timer[1];
499 if(SiS_Pr->SiS_UseROM) {
500 if(ROMAddr[0x220] & 0x40) {
501 if(!(DelayTime & 0x01)) Delay = (unsigned short)ROMAddr[0x225];
502 else Delay = (unsigned short)ROMAddr[0x226];
506 SiS_ShortDelay(SiS_Pr, Delay);
508 #endif /* CONFIG_FB_SIS_300 */
512 #ifdef CONFIG_FB_SIS_315
514 if((SiS_Pr->ChipType >= SIS_661) ||
515 (SiS_Pr->ChipType <= SIS_315PRO) ||
516 (SiS_Pr->ChipType == SIS_330) ||
517 (SiS_Pr->SiS_ROMNew)) {
519 if(!(DelayTime & 0x01)) {
520 SiS_DDC2Delay(SiS_Pr, 0x1000);
522 SiS_DDC2Delay(SiS_Pr, 0x4000);
525 } else if (SiS_Pr->SiS_IF_DEF_LVDS == 1) { /* 315 series, LVDS; Special */
527 if(SiS_Pr->SiS_IF_DEF_CH70xx == 0) {
528 PanelID = SiS_GetReg(SiS_Pr->SiS_P3d4,0x36);
529 if(SiS_Pr->SiS_CustomT == CUT_CLEVO1400) {
530 if(!(SiS_GetReg(SiS_Pr->SiS_P3c4,0x1b) & 0x10)) PanelID = 0x12;
532 if(SiS_Pr->SiS_CustomT == CUT_COMPAQ1280) {
533 DelayIndex = PanelID & 0x0f;
535 DelayIndex = PanelID >> 4;
537 if((DelayTime >= 2) && ((PanelID & 0x0f) == 1)) {
540 if(DelayTime >= 2) DelayTime -= 2;
541 if(!(DelayTime & 0x01)) {
542 Delay = SiS_Pr->SiS_PanelDelayTblLVDS[DelayIndex].timer[0];
544 Delay = SiS_Pr->SiS_PanelDelayTblLVDS[DelayIndex].timer[1];
546 if((SiS_Pr->SiS_UseROM) && (!(SiS_Pr->SiS_ROMNew))) {
547 if(ROMAddr[0x13c] & 0x40) {
548 if(!(DelayTime & 0x01)) {
549 Delay = (unsigned short)ROMAddr[0x17e];
551 Delay = (unsigned short)ROMAddr[0x17f];
556 SiS_ShortDelay(SiS_Pr, Delay);
559 } else if(SiS_Pr->SiS_VBType & VB_SISVB) { /* 315 series, all bridges */
561 DelayIndex = SiS_GetReg(SiS_Pr->SiS_P3d4,0x36) >> 4;
562 if(!(DelayTime & 0x01)) {
563 Delay = SiS_Pr->SiS_PanelDelayTbl[DelayIndex].timer[0];
565 Delay = SiS_Pr->SiS_PanelDelayTbl[DelayIndex].timer[1];
568 SiS_DDC2Delay(SiS_Pr, Delay);
572 #endif /* CONFIG_FB_SIS_315 */
577 #ifdef CONFIG_FB_SIS_315
579 SiS_PanelDelayLoop(struct SiS_Private *SiS_Pr, unsigned short DelayTime, unsigned short DelayLoop)
582 for(i = 0; i < DelayLoop; i++) {
583 SiS_PanelDelay(SiS_Pr, DelayTime);
588 /*********************************************/
589 /* HELPER: WAIT-FOR-RETRACE FUNCTIONS */
590 /*********************************************/
593 SiS_WaitRetrace1(struct SiS_Private *SiS_Pr)
595 unsigned short watchdog;
597 if(SiS_GetReg(SiS_Pr->SiS_P3c4,0x1f) & 0xc0) return;
598 if(!(SiS_GetReg(SiS_Pr->SiS_P3d4,0x17) & 0x80)) return;
601 while((SiS_GetRegByte(SiS_Pr->SiS_P3da) & 0x08) && --watchdog);
603 while((!(SiS_GetRegByte(SiS_Pr->SiS_P3da) & 0x08)) && --watchdog);
606 #if defined(CONFIG_FB_SIS_300) || defined(CONFIG_FB_SIS_315)
608 SiS_WaitRetrace2(struct SiS_Private *SiS_Pr, unsigned short reg)
610 unsigned short watchdog;
613 while((SiS_GetReg(SiS_Pr->SiS_Part1Port,reg) & 0x02) && --watchdog);
615 while((!(SiS_GetReg(SiS_Pr->SiS_Part1Port,reg) & 0x02)) && --watchdog);
620 SiS_WaitVBRetrace(struct SiS_Private *SiS_Pr)
622 if(SiS_Pr->ChipType < SIS_315H) {
623 #ifdef CONFIG_FB_SIS_300
624 if(SiS_Pr->SiS_VBType & VB_SIS30xBLV) {
625 if(!(SiS_GetReg(SiS_Pr->SiS_Part1Port,0x00) & 0x20)) return;
627 if(!(SiS_GetReg(SiS_Pr->SiS_Part1Port,0x00) & 0x80)) {
628 SiS_WaitRetrace1(SiS_Pr);
630 SiS_WaitRetrace2(SiS_Pr, 0x25);
634 #ifdef CONFIG_FB_SIS_315
635 if(!(SiS_GetReg(SiS_Pr->SiS_Part1Port,0x00) & 0x40)) {
636 SiS_WaitRetrace1(SiS_Pr);
638 SiS_WaitRetrace2(SiS_Pr, 0x30);
645 SiS_VBWait(struct SiS_Private *SiS_Pr)
647 unsigned short tempal,temp,i,j;
650 for(i = 0; i < 3; i++) {
651 for(j = 0; j < 100; j++) {
652 tempal = SiS_GetRegByte(SiS_Pr->SiS_P3da);
654 if((tempal & 0x08)) continue;
657 if(!(tempal & 0x08)) continue;
666 SiS_VBLongWait(struct SiS_Private *SiS_Pr)
668 if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) {
671 SiS_WaitRetrace1(SiS_Pr);
675 /*********************************************/
677 /*********************************************/
679 #ifdef CONFIG_FB_SIS_300
681 SiS_Is301B(struct SiS_Private *SiS_Pr)
683 if(SiS_GetReg(SiS_Pr->SiS_Part4Port,0x01) >= 0xb0) return true;
689 SiS_CRT2IsLCD(struct SiS_Private *SiS_Pr)
691 if(SiS_Pr->ChipType == SIS_730) {
692 if(SiS_GetReg(SiS_Pr->SiS_P3c4,0x13) & 0x20) return true;
694 if(SiS_GetReg(SiS_Pr->SiS_P3d4,0x30) & 0x20) return true;
699 SiS_IsDualEdge(struct SiS_Private *SiS_Pr)
701 #ifdef CONFIG_FB_SIS_315
702 if(SiS_Pr->ChipType >= SIS_315H) {
703 if((SiS_Pr->ChipType != SIS_650) || (SiS_GetReg(SiS_Pr->SiS_P3d4,0x5f) & 0xf0)) {
704 if(SiS_GetReg(SiS_Pr->SiS_P3d4,0x38) & EnableDualEdge) return true;
712 SiS_IsVAMode(struct SiS_Private *SiS_Pr)
714 #ifdef CONFIG_FB_SIS_315
717 if(SiS_Pr->ChipType >= SIS_315H) {
718 flag = SiS_GetReg(SiS_Pr->SiS_P3d4,0x38);
719 if((flag & EnableDualEdge) && (flag & SetToLCDA)) return true;
725 #ifdef CONFIG_FB_SIS_315
727 SiS_IsVAorLCD(struct SiS_Private *SiS_Pr)
729 if(SiS_IsVAMode(SiS_Pr)) return true;
730 if(SiS_CRT2IsLCD(SiS_Pr)) return true;
736 SiS_IsDualLink(struct SiS_Private *SiS_Pr)
738 #ifdef CONFIG_FB_SIS_315
739 if(SiS_Pr->ChipType >= SIS_315H) {
740 if((SiS_CRT2IsLCD(SiS_Pr)) ||
741 (SiS_IsVAMode(SiS_Pr))) {
742 if(SiS_Pr->SiS_LCDInfo & LCDDualLink) return true;
749 #ifdef CONFIG_FB_SIS_315
751 SiS_TVEnabled(struct SiS_Private *SiS_Pr)
753 if((SiS_GetReg(SiS_Pr->SiS_Part2Port,0x00) & 0x0f) != 0x0c) return true;
754 if(SiS_Pr->SiS_VBType & VB_SISYPBPR) {
755 if(SiS_GetReg(SiS_Pr->SiS_Part2Port,0x4d) & 0x10) return true;
761 #ifdef CONFIG_FB_SIS_315
763 SiS_LCDAEnabled(struct SiS_Private *SiS_Pr)
765 if(SiS_GetReg(SiS_Pr->SiS_Part1Port,0x13) & 0x04) return true;
770 #ifdef CONFIG_FB_SIS_315
772 SiS_WeHaveBacklightCtrl(struct SiS_Private *SiS_Pr)
774 if((SiS_Pr->ChipType >= SIS_315H) && (SiS_Pr->ChipType < SIS_661)) {
775 if(SiS_GetReg(SiS_Pr->SiS_P3d4,0x79) & 0x10) return true;
781 #ifdef CONFIG_FB_SIS_315
783 SiS_IsNotM650orLater(struct SiS_Private *SiS_Pr)
787 if(SiS_Pr->ChipType == SIS_650) {
788 flag = SiS_GetReg(SiS_Pr->SiS_P3d4,0x5f) & 0xf0;
789 /* Check for revision != A0 only */
790 if((flag == 0xe0) || (flag == 0xc0) ||
791 (flag == 0xb0) || (flag == 0x90)) return false;
792 } else if(SiS_Pr->ChipType >= SIS_661) return false;
797 #ifdef CONFIG_FB_SIS_315
799 SiS_IsYPbPr(struct SiS_Private *SiS_Pr)
801 if(SiS_Pr->ChipType >= SIS_315H) {
803 if(SiS_GetReg(SiS_Pr->SiS_P3d4,0x38) & EnableCHYPbPr) return true;
809 #ifdef CONFIG_FB_SIS_315
811 SiS_IsChScart(struct SiS_Private *SiS_Pr)
813 if(SiS_Pr->ChipType >= SIS_315H) {
815 if(SiS_GetReg(SiS_Pr->SiS_P3d4,0x38) & EnableCHScart) return true;
821 #ifdef CONFIG_FB_SIS_315
823 SiS_IsTVOrYPbPrOrScart(struct SiS_Private *SiS_Pr)
827 if(SiS_Pr->ChipType >= SIS_315H) {
828 flag = SiS_GetReg(SiS_Pr->SiS_P3d4,0x30);
829 if(flag & SetCRT2ToTV) return true;
830 flag = SiS_GetReg(SiS_Pr->SiS_P3d4,0x38);
831 if(flag & EnableCHYPbPr) return true; /* = YPrPb = 0x08 */
832 if(flag & EnableCHScart) return true; /* = Scart = 0x04 - TW */
834 flag = SiS_GetReg(SiS_Pr->SiS_P3d4,0x30);
835 if(flag & SetCRT2ToTV) return true;
841 #ifdef CONFIG_FB_SIS_315
843 SiS_IsLCDOrLCDA(struct SiS_Private *SiS_Pr)
847 if(SiS_Pr->ChipType >= SIS_315H) {
848 flag = SiS_GetReg(SiS_Pr->SiS_P3d4,0x30);
849 if(flag & SetCRT2ToLCD) return true;
850 flag = SiS_GetReg(SiS_Pr->SiS_P3d4,0x38);
851 if(flag & SetToLCDA) return true;
853 flag = SiS_GetReg(SiS_Pr->SiS_P3d4,0x30);
854 if(flag & SetCRT2ToLCD) return true;
861 SiS_HaveBridge(struct SiS_Private *SiS_Pr)
865 if(SiS_Pr->SiS_IF_DEF_LVDS == 1) {
867 } else if(SiS_Pr->SiS_VBType & VB_SISVB) {
868 flag = SiS_GetReg(SiS_Pr->SiS_Part4Port,0x00);
869 if((flag == 1) || (flag == 2)) return true;
875 SiS_BridgeIsEnabled(struct SiS_Private *SiS_Pr)
879 if(SiS_HaveBridge(SiS_Pr)) {
880 flag = SiS_GetReg(SiS_Pr->SiS_Part1Port,0x00);
881 if(SiS_Pr->ChipType < SIS_315H) {
883 if((flag == 0x80) || (flag == 0x20)) return true;
886 if((flag == 0x40) || (flag == 0x10)) return true;
893 SiS_BridgeInSlavemode(struct SiS_Private *SiS_Pr)
895 unsigned short flag1;
897 flag1 = SiS_GetReg(SiS_Pr->SiS_P3d4,0x31);
898 if(flag1 & (SetInSlaveMode >> 8)) return true;
902 /*********************************************/
903 /* GET VIDEO BRIDGE CONFIG INFO */
904 /*********************************************/
906 /* Setup general purpose IO for Chrontel communication */
907 #ifdef CONFIG_FB_SIS_300
909 SiS_SetChrontelGPIO(struct SiS_Private *SiS_Pr, unsigned short myvbinfo)
911 unsigned int acpibase;
914 if(!(SiS_Pr->SiS_ChSW)) return;
916 acpibase = sisfb_read_lpc_pci_dword(SiS_Pr, 0x74);
918 if(!acpibase) return;
919 temp = SiS_GetRegShort((acpibase + 0x3c)); /* ACPI register 0x3c: GP Event 1 I/O mode select */
921 SiS_SetRegShort((acpibase + 0x3c), temp);
922 temp = SiS_GetRegShort((acpibase + 0x3c));
923 temp = SiS_GetRegShort((acpibase + 0x3a)); /* ACPI register 0x3a: GP Pin Level (low/high) */
925 if(!(myvbinfo & SetCRT2ToTV)) temp |= 0x0100;
926 SiS_SetRegShort((acpibase + 0x3a), temp);
927 temp = SiS_GetRegShort((acpibase + 0x3a));
932 SiS_GetVBInfo(struct SiS_Private *SiS_Pr, unsigned short ModeNo,
933 unsigned short ModeIdIndex, int checkcrt2mode)
935 unsigned short tempax, tempbx, temp;
936 unsigned short modeflag, resinfo = 0;
938 SiS_Pr->SiS_SetFlag = 0;
940 modeflag = SiS_GetModeFlag(SiS_Pr, ModeNo, ModeIdIndex);
942 SiS_Pr->SiS_ModeType = modeflag & ModeTypeMask;
944 if((ModeNo > 0x13) && (!SiS_Pr->UseCustomMode)) {
945 resinfo = SiS_Pr->SiS_EModeIDTable[ModeIdIndex].Ext_RESINFO;
950 if(SiS_HaveBridge(SiS_Pr)) {
952 temp = SiS_GetReg(SiS_Pr->SiS_P3d4,0x30);
954 tempax = SiS_GetReg(SiS_Pr->SiS_P3d4,0x31) << 8;
955 tempax &= (DriverMode | LoadDACFlag | SetNotSimuMode | SetPALTV);
958 #ifdef CONFIG_FB_SIS_315
959 if(SiS_Pr->ChipType >= SIS_315H) {
960 if(SiS_Pr->SiS_VBType & VB_SISLCDA) {
962 /* Mode 0x03 is never in driver mode */
963 SiS_SetRegAND(SiS_Pr->SiS_P3d4,0x31,0xbf);
965 if(!(SiS_GetReg(SiS_Pr->SiS_P3d4,0x31) & (DriverMode >> 8))) {
966 /* Reset LCDA setting if not driver mode */
967 SiS_SetRegAND(SiS_Pr->SiS_P3d4,0x38,0xfc);
970 if(SiS_Pr->SiS_UseLCDA) {
971 if(SiS_GetReg(SiS_Pr->SiS_P3d4,0x5f) & 0xF0) {
972 if((ModeNo <= 0x13) || (!(SiS_GetReg(SiS_Pr->SiS_P3d4,0x31) & (DriverMode >> 8)))) {
973 SiS_SetRegOR(SiS_Pr->SiS_P3d4,0x38,(EnableDualEdge | SetToLCDA));
978 temp = SiS_GetReg(SiS_Pr->SiS_P3d4,0x38);
979 if((temp & (EnableDualEdge | SetToLCDA)) == (EnableDualEdge | SetToLCDA)) {
980 tempbx |= SetCRT2ToLCDA;
984 if(SiS_Pr->ChipType >= SIS_661) { /* New CR layout */
985 tempbx &= ~(SetCRT2ToYPbPr525750 | SetCRT2ToHiVision);
986 if(SiS_GetReg(SiS_Pr->SiS_P3d4,0x38) & 0x04) {
987 temp = SiS_GetReg(SiS_Pr->SiS_P3d4,0x35) & 0xe0;
988 if(temp == 0x60) tempbx |= SetCRT2ToHiVision;
989 else if(SiS_Pr->SiS_VBType & VB_SISYPBPR) {
990 tempbx |= SetCRT2ToYPbPr525750;
995 if(SiS_Pr->SiS_IF_DEF_LVDS == 1) {
996 temp = SiS_GetReg(SiS_Pr->SiS_P3d4,0x38);
997 if(temp & SetToLCDA) {
998 tempbx |= SetCRT2ToLCDA;
1000 if(SiS_Pr->SiS_IF_DEF_CH70xx != 0) {
1001 if(temp & EnableCHYPbPr) {
1002 tempbx |= SetCRT2ToCHYPbPr;
1008 #endif /* CONFIG_FB_SIS_315 */
1010 if(!(SiS_Pr->SiS_VBType & VB_SISVGA2)) {
1011 tempbx &= ~(SetCRT2ToRAMDAC);
1014 if(SiS_Pr->SiS_VBType & VB_SISVB) {
1015 temp = SetCRT2ToSVIDEO |
1022 SetCRT2ToYPbPr525750;
1024 if(SiS_Pr->ChipType >= SIS_315H) {
1025 if(SiS_Pr->SiS_IF_DEF_CH70xx != 0) {
1026 temp = SetCRT2ToAVIDEO |
1033 temp = SetCRT2ToLCDA |
1037 if(SiS_Pr->SiS_IF_DEF_CH70xx != 0) {
1038 temp = SetCRT2ToTV | SetCRT2ToLCD;
1040 temp = SetCRT2ToLCD;
1045 if(!(tempbx & temp)) {
1046 tempax = DisableCRT2Display;
1050 if(SiS_Pr->SiS_VBType & VB_SISVB) {
1052 unsigned short clearmask = ( DriverMode |
1053 DisableCRT2Display |
1061 if(tempbx & SetCRT2ToLCDA) tempbx &= (clearmask | SetCRT2ToLCDA);
1062 if(tempbx & SetCRT2ToRAMDAC) tempbx &= (clearmask | SetCRT2ToRAMDAC);
1063 if(tempbx & SetCRT2ToLCD) tempbx &= (clearmask | SetCRT2ToLCD);
1064 if(tempbx & SetCRT2ToSCART) tempbx &= (clearmask | SetCRT2ToSCART);
1065 if(tempbx & SetCRT2ToHiVision) tempbx &= (clearmask | SetCRT2ToHiVision);
1066 if(tempbx & SetCRT2ToYPbPr525750) tempbx &= (clearmask | SetCRT2ToYPbPr525750);
1070 if(SiS_Pr->ChipType >= SIS_315H) {
1071 if(tempbx & SetCRT2ToLCDA) {
1072 tempbx &= (0xFF00|SwitchCRT2|SetSimuScanMode);
1075 if(SiS_Pr->SiS_IF_DEF_CH70xx != 0) {
1076 if(tempbx & SetCRT2ToTV) {
1077 tempbx &= (0xFF00|SetCRT2ToTV|SwitchCRT2|SetSimuScanMode);
1080 if(tempbx & SetCRT2ToLCD) {
1081 tempbx &= (0xFF00|SetCRT2ToLCD|SwitchCRT2|SetSimuScanMode);
1083 if(SiS_Pr->ChipType >= SIS_315H) {
1084 if(tempbx & SetCRT2ToLCDA) {
1085 tempbx |= SetCRT2ToLCD;
1091 if(tempax & DisableCRT2Display) {
1092 if(!(tempbx & (SwitchCRT2 | SetSimuScanMode))) {
1093 tempbx = SetSimuScanMode | DisableCRT2Display;
1097 if(!(tempbx & DriverMode)) tempbx |= SetSimuScanMode;
1099 /* LVDS/CHRONTEL (LCD/TV) and 301BDH (LCD) can only be slave in 8bpp modes */
1100 if(SiS_Pr->SiS_ModeType <= ModeVGA) {
1101 if( (SiS_Pr->SiS_IF_DEF_LVDS == 1) ||
1102 ((SiS_Pr->SiS_VBType & VB_NoLCD) && (tempbx & SetCRT2ToLCD)) ) {
1103 modeflag &= (~CRT2Mode);
1107 if(!(tempbx & SetSimuScanMode)) {
1108 if(tempbx & SwitchCRT2) {
1109 if((!(modeflag & CRT2Mode)) && (checkcrt2mode)) {
1110 if(resinfo != SIS_RI_1600x1200) {
1111 tempbx |= SetSimuScanMode;
1115 if(SiS_BridgeIsEnabled(SiS_Pr)) {
1116 if(!(tempbx & DriverMode)) {
1117 if(SiS_BridgeInSlavemode(SiS_Pr)) {
1118 tempbx |= SetSimuScanMode;
1125 if(!(tempbx & DisableCRT2Display)) {
1126 if(tempbx & DriverMode) {
1127 if(tempbx & SetSimuScanMode) {
1128 if((!(modeflag & CRT2Mode)) && (checkcrt2mode)) {
1129 if(resinfo != SIS_RI_1600x1200) {
1130 tempbx |= SetInSlaveMode;
1135 tempbx |= SetInSlaveMode;
1141 SiS_Pr->SiS_VBInfo = tempbx;
1143 #ifdef CONFIG_FB_SIS_300
1144 if(SiS_Pr->ChipType == SIS_630) {
1145 SiS_SetChrontelGPIO(SiS_Pr, SiS_Pr->SiS_VBInfo);
1150 printk(KERN_DEBUG "sisfb: (init301: VBInfo= 0x%04x, SetFlag=0x%04x)\n",
1151 SiS_Pr->SiS_VBInfo, SiS_Pr->SiS_SetFlag);
1155 /*********************************************/
1156 /* DETERMINE YPbPr MODE */
1157 /*********************************************/
1160 SiS_SetYPbPr(struct SiS_Private *SiS_Pr)
1165 /* Note: This variable is only used on 30xLV systems.
1166 * CR38 has a different meaning on LVDS/CH7019 systems.
1167 * On 661 and later, these bits moved to CR35.
1169 * On 301, 301B, only HiVision 1080i is supported.
1170 * On 30xLV, 301C, only YPbPr 1080i is supported.
1173 SiS_Pr->SiS_YPbPr = 0;
1174 if(SiS_Pr->ChipType >= SIS_661) return;
1176 if(SiS_Pr->SiS_VBType) {
1177 if(SiS_Pr->SiS_VBInfo & SetCRT2ToHiVision) {
1178 SiS_Pr->SiS_YPbPr = YPbPrHiVision;
1182 if(SiS_Pr->ChipType >= SIS_315H) {
1183 if(SiS_Pr->SiS_VBType & VB_SISYPBPR) {
1184 temp = SiS_GetReg(SiS_Pr->SiS_P3d4,0x38);
1186 switch((temp >> 4)) {
1187 case 0x00: SiS_Pr->SiS_YPbPr = YPbPr525i; break;
1188 case 0x01: SiS_Pr->SiS_YPbPr = YPbPr525p; break;
1189 case 0x02: SiS_Pr->SiS_YPbPr = YPbPr750p; break;
1190 case 0x03: SiS_Pr->SiS_YPbPr = YPbPrHiVision; break;
1198 /*********************************************/
1199 /* DETERMINE TVMode flag */
1200 /*********************************************/
1203 SiS_SetTVMode(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex)
1205 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
1206 unsigned short temp, temp1, resinfo = 0, romindex = 0;
1207 unsigned char OutputSelect = *SiS_Pr->pSiS_OutputSelect;
1209 SiS_Pr->SiS_TVMode = 0;
1211 if(!(SiS_Pr->SiS_VBInfo & SetCRT2ToTV)) return;
1212 if(SiS_Pr->UseCustomMode) return;
1215 resinfo = SiS_Pr->SiS_EModeIDTable[ModeIdIndex].Ext_RESINFO;
1218 if(SiS_Pr->ChipType < SIS_661) {
1220 if(SiS_Pr->SiS_VBInfo & SetPALTV) SiS_Pr->SiS_TVMode |= TVSetPAL;
1222 if(SiS_Pr->SiS_VBType & VB_SISVB) {
1224 if((SiS_Pr->ChipType == SIS_630) ||
1225 (SiS_Pr->ChipType == SIS_730)) {
1228 } else if(SiS_Pr->ChipType >= SIS_315H) {
1230 if(SiS_Pr->ChipType < XGI_20) {
1232 if(SiS_Pr->ChipType >= SIS_330) romindex = 0x11b;
1236 if(romindex && SiS_Pr->SiS_UseROM && (!(SiS_Pr->SiS_ROMNew))) {
1237 OutputSelect = ROMAddr[romindex];
1238 if(!(OutputSelect & EnablePALMN)) {
1239 SiS_SetRegAND(SiS_Pr->SiS_P3d4,temp,0x3F);
1242 temp1 = SiS_GetReg(SiS_Pr->SiS_P3d4,temp);
1243 if(SiS_Pr->SiS_TVMode & TVSetPAL) {
1244 if(temp1 & EnablePALM) { /* 0x40 */
1245 SiS_Pr->SiS_TVMode |= TVSetPALM;
1246 SiS_Pr->SiS_TVMode &= ~TVSetPAL;
1247 } else if(temp1 & EnablePALN) { /* 0x80 */
1248 SiS_Pr->SiS_TVMode |= TVSetPALN;
1251 if(temp1 & EnableNTSCJ) { /* 0x40 */
1252 SiS_Pr->SiS_TVMode |= TVSetNTSCJ;
1256 /* Translate HiVision/YPbPr to our new flags */
1257 if(SiS_Pr->SiS_VBInfo & SetCRT2ToHiVision) {
1258 if(SiS_Pr->SiS_YPbPr == YPbPr750p) SiS_Pr->SiS_TVMode |= TVSetYPbPr750p;
1259 else if(SiS_Pr->SiS_YPbPr == YPbPr525p) SiS_Pr->SiS_TVMode |= TVSetYPbPr525p;
1260 else if(SiS_Pr->SiS_YPbPr == YPbPrHiVision) SiS_Pr->SiS_TVMode |= TVSetHiVision;
1261 else SiS_Pr->SiS_TVMode |= TVSetYPbPr525i;
1262 if(SiS_Pr->SiS_TVMode & (TVSetYPbPr750p | TVSetYPbPr525p | TVSetYPbPr525i)) {
1263 SiS_Pr->SiS_VBInfo &= ~SetCRT2ToHiVision;
1264 SiS_Pr->SiS_VBInfo |= SetCRT2ToYPbPr525750;
1265 } else if(SiS_Pr->SiS_TVMode & TVSetHiVision) {
1266 SiS_Pr->SiS_TVMode |= TVSetPAL;
1269 } else if(SiS_Pr->SiS_IF_DEF_CH70xx != 0) {
1270 if(SiS_Pr->SiS_CHOverScan) {
1271 if(SiS_Pr->SiS_IF_DEF_CH70xx == 1) {
1272 temp = SiS_GetReg(SiS_Pr->SiS_P3d4,0x35);
1273 if((temp & TVOverScan) || (SiS_Pr->SiS_CHOverScan == 1)) {
1274 SiS_Pr->SiS_TVMode |= TVSetCHOverScan;
1276 } else if(SiS_Pr->SiS_IF_DEF_CH70xx == 2) {
1277 temp = SiS_GetReg(SiS_Pr->SiS_P3d4,0x79);
1278 if((temp & 0x80) || (SiS_Pr->SiS_CHOverScan == 1)) {
1279 SiS_Pr->SiS_TVMode |= TVSetCHOverScan;
1282 if(SiS_Pr->SiS_CHSOverScan) {
1283 SiS_Pr->SiS_TVMode |= TVSetCHOverScan;
1286 if(SiS_Pr->SiS_IF_DEF_CH70xx == 2) {
1287 temp = SiS_GetReg(SiS_Pr->SiS_P3d4,0x38);
1288 if(SiS_Pr->SiS_TVMode & TVSetPAL) {
1289 if(temp & EnablePALM) SiS_Pr->SiS_TVMode |= TVSetPALM;
1290 else if(temp & EnablePALN) SiS_Pr->SiS_TVMode |= TVSetPALN;
1292 if(temp & EnableNTSCJ) {
1293 SiS_Pr->SiS_TVMode |= TVSetNTSCJ;
1299 } else { /* 661 and later */
1301 temp1 = SiS_GetReg(SiS_Pr->SiS_P3d4,0x35);
1303 SiS_Pr->SiS_TVMode |= TVSetPAL;
1305 SiS_Pr->SiS_TVMode |= TVSetPALN;
1306 } else if(temp1 & 0x04) {
1307 if(SiS_Pr->SiS_VBType & VB_SISVB) {
1308 SiS_Pr->SiS_TVMode &= ~TVSetPAL;
1310 SiS_Pr->SiS_TVMode |= TVSetPALM;
1314 SiS_Pr->SiS_TVMode |= TVSetNTSCJ;
1317 if(SiS_Pr->SiS_IF_DEF_CH70xx == 2) {
1318 if(SiS_Pr->SiS_CHOverScan) {
1319 if((temp1 & 0x10) || (SiS_Pr->SiS_CHOverScan == 1)) {
1320 SiS_Pr->SiS_TVMode |= TVSetCHOverScan;
1324 if(SiS_Pr->SiS_VBType & VB_SISVB) {
1325 if(SiS_Pr->SiS_VBInfo & SetCRT2ToYPbPr525750) {
1327 if(temp1 == 0x00) SiS_Pr->SiS_TVMode |= TVSetYPbPr525i;
1328 else if(temp1 == 0x20) SiS_Pr->SiS_TVMode |= TVSetYPbPr525p;
1329 else if(temp1 == 0x40) SiS_Pr->SiS_TVMode |= TVSetYPbPr750p;
1330 } else if(SiS_Pr->SiS_VBInfo & SetCRT2ToHiVision) {
1331 SiS_Pr->SiS_TVMode |= (TVSetHiVision | TVSetPAL);
1333 if(SiS_Pr->SiS_VBInfo & (SetCRT2ToYPbPr525750 | SetCRT2ToHiVision)) {
1334 if(resinfo == SIS_RI_800x480 || resinfo == SIS_RI_1024x576 || resinfo == SIS_RI_1280x720) {
1335 SiS_Pr->SiS_TVMode |= TVAspect169;
1337 temp1 = SiS_GetReg(SiS_Pr->SiS_P3d4,0x39);
1339 if(SiS_Pr->SiS_TVMode & (TVSetYPbPr750p | TVSetHiVision)) {
1340 SiS_Pr->SiS_TVMode |= TVAspect169;
1342 SiS_Pr->SiS_TVMode |= TVAspect43LB;
1345 SiS_Pr->SiS_TVMode |= TVAspect43;
1352 if(SiS_Pr->SiS_VBInfo & SetCRT2ToSCART) SiS_Pr->SiS_TVMode |= TVSetPAL;
1354 if(SiS_Pr->SiS_VBType & VB_SISVB) {
1356 if(SiS_Pr->SiS_VBInfo & SetCRT2ToHiVision) {
1357 SiS_Pr->SiS_TVMode |= TVSetPAL;
1358 SiS_Pr->SiS_TVMode &= ~(TVSetPALM | TVSetPALN | TVSetNTSCJ);
1359 } else if(SiS_Pr->SiS_VBInfo & SetCRT2ToYPbPr525750) {
1360 if(SiS_Pr->SiS_TVMode & (TVSetYPbPr525i | TVSetYPbPr525p | TVSetYPbPr750p)) {
1361 SiS_Pr->SiS_TVMode &= ~(TVSetPAL | TVSetNTSCJ | TVSetPALM | TVSetPALN);
1365 if(SiS_Pr->SiS_VBInfo & SetInSlaveMode) {
1366 if(!(SiS_Pr->SiS_VBInfo & SetNotSimuMode)) {
1367 SiS_Pr->SiS_TVMode |= TVSetTVSimuMode;
1371 if(!(SiS_Pr->SiS_TVMode & TVSetPAL)) {
1372 if(resinfo == SIS_RI_1024x768) {
1373 if(SiS_Pr->SiS_TVMode & TVSetYPbPr525p) {
1374 SiS_Pr->SiS_TVMode |= TVSet525p1024;
1375 } else if(!(SiS_Pr->SiS_TVMode & (TVSetHiVision | TVSetYPbPr750p))) {
1376 SiS_Pr->SiS_TVMode |= TVSetNTSC1024;
1381 SiS_Pr->SiS_TVMode |= TVRPLLDIV2XO;
1382 if((SiS_Pr->SiS_VBInfo & SetCRT2ToHiVision) &&
1383 (SiS_Pr->SiS_VBInfo & SetInSlaveMode)) {
1384 SiS_Pr->SiS_TVMode &= ~TVRPLLDIV2XO;
1385 } else if(SiS_Pr->SiS_TVMode & (TVSetYPbPr525p | TVSetYPbPr750p)) {
1386 SiS_Pr->SiS_TVMode &= ~TVRPLLDIV2XO;
1387 } else if(!(SiS_Pr->SiS_VBType & VB_SIS30xBLV)) {
1388 if(SiS_Pr->SiS_TVMode & TVSetTVSimuMode) {
1389 SiS_Pr->SiS_TVMode &= ~TVRPLLDIV2XO;
1395 SiS_Pr->SiS_VBInfo &= ~SetPALTV;
1398 /*********************************************/
1400 /*********************************************/
1402 static unsigned short
1403 SiS_GetBIOSLCDResInfo(struct SiS_Private *SiS_Pr)
1405 unsigned short temp = SiS_Pr->SiS_LCDResInfo;
1406 /* Translate my LCDResInfo to BIOS value */
1408 case Panel_1280x768_2: temp = Panel_1280x768; break;
1409 case Panel_1280x800_2: temp = Panel_1280x800; break;
1410 case Panel_1280x854: temp = Panel661_1280x854; break;
1416 SiS_GetLCDInfoBIOS(struct SiS_Private *SiS_Pr)
1418 #ifdef CONFIG_FB_SIS_315
1419 unsigned char *ROMAddr;
1420 unsigned short temp;
1422 if((ROMAddr = GetLCDStructPtr661(SiS_Pr))) {
1423 if((temp = SISGETROMW(6)) != SiS_Pr->PanelHT) {
1424 SiS_Pr->SiS_NeedRomModeData = true;
1425 SiS_Pr->PanelHT = temp;
1427 if((temp = SISGETROMW(8)) != SiS_Pr->PanelVT) {
1428 SiS_Pr->SiS_NeedRomModeData = true;
1429 SiS_Pr->PanelVT = temp;
1431 SiS_Pr->PanelHRS = SISGETROMW(10);
1432 SiS_Pr->PanelHRE = SISGETROMW(12);
1433 SiS_Pr->PanelVRS = SISGETROMW(14);
1434 SiS_Pr->PanelVRE = SISGETROMW(16);
1435 SiS_Pr->PanelVCLKIdx315 = VCLK_CUSTOM_315;
1436 SiS_Pr->SiS_VCLKData[VCLK_CUSTOM_315].CLOCK =
1437 SiS_Pr->SiS_VBVCLKData[VCLK_CUSTOM_315].CLOCK = (unsigned short)((unsigned char)ROMAddr[18]);
1438 SiS_Pr->SiS_VCLKData[VCLK_CUSTOM_315].SR2B =
1439 SiS_Pr->SiS_VBVCLKData[VCLK_CUSTOM_315].Part4_A = ROMAddr[19];
1440 SiS_Pr->SiS_VCLKData[VCLK_CUSTOM_315].SR2C =
1441 SiS_Pr->SiS_VBVCLKData[VCLK_CUSTOM_315].Part4_B = ROMAddr[20];
1448 SiS_CheckScaling(struct SiS_Private *SiS_Pr, unsigned short resinfo,
1449 const unsigned char *nonscalingmodes)
1452 while(nonscalingmodes[i] != 0xff) {
1453 if(nonscalingmodes[i++] == resinfo) {
1454 if((SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) ||
1455 (SiS_Pr->UsePanelScaler == -1)) {
1456 SiS_Pr->SiS_LCDInfo |= DontExpandLCD;
1464 SiS_GetLCDResInfo(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex)
1466 unsigned short temp,modeflag,resinfo=0,modexres=0,modeyres=0;
1467 bool panelcanscale = false;
1468 #ifdef CONFIG_FB_SIS_300
1469 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
1470 static const unsigned char SiS300SeriesLCDRes[] =
1471 { 0, 1, 2, 3, 7, 4, 5, 8,
1472 0, 0, 10, 0, 0, 0, 0, 15 };
1474 #ifdef CONFIG_FB_SIS_315
1475 unsigned char *myptr = NULL;
1478 SiS_Pr->SiS_LCDResInfo = 0;
1479 SiS_Pr->SiS_LCDTypeInfo = 0;
1480 SiS_Pr->SiS_LCDInfo = 0;
1481 SiS_Pr->PanelHRS = 999; /* HSync start */
1482 SiS_Pr->PanelHRE = 999; /* HSync end */
1483 SiS_Pr->PanelVRS = 999; /* VSync start */
1484 SiS_Pr->PanelVRE = 999; /* VSync end */
1485 SiS_Pr->SiS_NeedRomModeData = false;
1487 /* Alternative 1600x1200@60 timing for 1600x1200 LCDA */
1488 SiS_Pr->Alternate1600x1200 = false;
1490 if(!(SiS_Pr->SiS_VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA))) return;
1492 modeflag = SiS_GetModeFlag(SiS_Pr, ModeNo, ModeIdIndex);
1494 if((ModeNo > 0x13) && (!SiS_Pr->UseCustomMode)) {
1495 resinfo = SiS_Pr->SiS_EModeIDTable[ModeIdIndex].Ext_RESINFO;
1496 modexres = SiS_Pr->SiS_ModeResInfo[resinfo].HTotal;
1497 modeyres = SiS_Pr->SiS_ModeResInfo[resinfo].VTotal;
1500 temp = SiS_GetReg(SiS_Pr->SiS_P3d4,0x36);
1502 /* For broken BIOSes: Assume 1024x768 */
1503 if(temp == 0) temp = 0x02;
1505 if((SiS_Pr->ChipType >= SIS_661) || (SiS_Pr->SiS_ROMNew)) {
1506 SiS_Pr->SiS_LCDTypeInfo = (SiS_GetReg(SiS_Pr->SiS_P3d4,0x39) & 0x7c) >> 2;
1507 } else if((SiS_Pr->ChipType < SIS_315H) || (SiS_Pr->ChipType >= SIS_661)) {
1508 SiS_Pr->SiS_LCDTypeInfo = temp >> 4;
1510 SiS_Pr->SiS_LCDTypeInfo = (temp & 0x0F) - 1;
1513 #ifdef CONFIG_FB_SIS_300
1514 if(SiS_Pr->ChipType < SIS_315H) {
1515 /* Very old BIOSes only know 7 sizes (NetVista 2179, 1.01g) */
1516 if(SiS_Pr->SiS_VBType & VB_SIS301) {
1517 if(temp < 0x0f) temp &= 0x07;
1519 /* Translate 300 series LCDRes to 315 series for unified usage */
1520 temp = SiS300SeriesLCDRes[temp];
1524 /* Translate to our internal types */
1525 #ifdef CONFIG_FB_SIS_315
1526 if(SiS_Pr->ChipType == SIS_550) {
1527 if (temp == Panel310_1152x768) temp = Panel_320x240_2; /* Verified working */
1528 else if(temp == Panel310_320x240_2) temp = Panel_320x240_2;
1529 else if(temp == Panel310_320x240_3) temp = Panel_320x240_3;
1530 } else if(SiS_Pr->ChipType >= SIS_661) {
1531 if(temp == Panel661_1280x854) temp = Panel_1280x854;
1535 if(SiS_Pr->SiS_VBType & VB_SISLVDS) { /* SiS LVDS */
1536 if(temp == Panel310_1280x768) {
1537 temp = Panel_1280x768_2;
1539 if(SiS_Pr->SiS_ROMNew) {
1540 if(temp == Panel661_1280x800) {
1541 temp = Panel_1280x800_2;
1546 SiS_Pr->SiS_LCDResInfo = temp;
1548 #ifdef CONFIG_FB_SIS_300
1549 if(SiS_Pr->SiS_IF_DEF_LVDS == 1) {
1550 if(SiS_Pr->SiS_CustomT == CUT_BARCO1366) {
1551 SiS_Pr->SiS_LCDResInfo = Panel_Barco1366;
1552 } else if(SiS_Pr->SiS_CustomT == CUT_PANEL848) {
1553 SiS_Pr->SiS_LCDResInfo = Panel_848x480;
1554 } else if(SiS_Pr->SiS_CustomT == CUT_PANEL856) {
1555 SiS_Pr->SiS_LCDResInfo = Panel_856x480;
1560 if(SiS_Pr->SiS_VBType & VB_SISVB) {
1561 if(SiS_Pr->SiS_LCDResInfo < SiS_Pr->SiS_PanelMin301)
1562 SiS_Pr->SiS_LCDResInfo = SiS_Pr->SiS_PanelMin301;
1564 if(SiS_Pr->SiS_LCDResInfo < SiS_Pr->SiS_PanelMinLVDS)
1565 SiS_Pr->SiS_LCDResInfo = SiS_Pr->SiS_PanelMinLVDS;
1568 temp = SiS_GetReg(SiS_Pr->SiS_P3d4,0x37);
1569 SiS_Pr->SiS_LCDInfo = temp & ~0x000e;
1570 /* Need temp below! */
1572 /* These must/can't scale no matter what */
1573 switch(SiS_Pr->SiS_LCDResInfo) {
1574 case Panel_320x240_1:
1575 case Panel_320x240_2:
1576 case Panel_320x240_3:
1577 case Panel_1280x960:
1578 SiS_Pr->SiS_LCDInfo &= ~DontExpandLCD;
1581 SiS_Pr->SiS_LCDInfo |= DontExpandLCD;
1584 panelcanscale = (bool)(SiS_Pr->SiS_LCDInfo & DontExpandLCD);
1586 if(!SiS_Pr->UsePanelScaler) SiS_Pr->SiS_LCDInfo &= ~DontExpandLCD;
1587 else if(SiS_Pr->UsePanelScaler == 1) SiS_Pr->SiS_LCDInfo |= DontExpandLCD;
1589 /* Dual link, Pass 1:1 BIOS default, etc. */
1590 #ifdef CONFIG_FB_SIS_315
1591 if(SiS_Pr->ChipType >= SIS_661) {
1592 if(SiS_Pr->SiS_LCDInfo & DontExpandLCD) {
1593 if(temp & 0x08) SiS_Pr->SiS_LCDInfo |= LCDPass11;
1595 if(SiS_Pr->SiS_VBType & VB_SISDUALLINK) {
1596 if(SiS_Pr->SiS_ROMNew) {
1597 if(temp & 0x02) SiS_Pr->SiS_LCDInfo |= LCDDualLink;
1598 } else if((myptr = GetLCDStructPtr661(SiS_Pr))) {
1599 if(myptr[2] & 0x01) SiS_Pr->SiS_LCDInfo |= LCDDualLink;
1602 } else if(SiS_Pr->ChipType >= SIS_315H) {
1603 if(SiS_Pr->SiS_LCDInfo & DontExpandLCD) {
1604 if(SiS_GetReg(SiS_Pr->SiS_P3d4,0x39) & 0x01) SiS_Pr->SiS_LCDInfo |= LCDPass11;
1606 if((SiS_Pr->SiS_ROMNew) && (!(SiS_Pr->PanelSelfDetected))) {
1607 SiS_Pr->SiS_LCDInfo &= ~(LCDRGB18Bit);
1608 temp = SiS_GetReg(SiS_Pr->SiS_P3d4,0x35);
1609 if(temp & 0x01) SiS_Pr->SiS_LCDInfo |= LCDRGB18Bit;
1610 if(SiS_Pr->SiS_VBType & VB_SISDUALLINK) {
1611 if(temp & 0x02) SiS_Pr->SiS_LCDInfo |= LCDDualLink;
1613 } else if(!(SiS_Pr->SiS_ROMNew)) {
1614 if(SiS_Pr->SiS_VBType & VB_SISDUALLINK) {
1615 if((SiS_Pr->SiS_CustomT == CUT_CLEVO1024) &&
1616 (SiS_Pr->SiS_LCDResInfo == Panel_1024x768)) {
1617 SiS_Pr->SiS_LCDInfo |= LCDDualLink;
1619 if((SiS_Pr->SiS_LCDResInfo == Panel_1280x1024) ||
1620 (SiS_Pr->SiS_LCDResInfo == Panel_1400x1050) ||
1621 (SiS_Pr->SiS_LCDResInfo == Panel_1600x1200) ||
1622 (SiS_Pr->SiS_LCDResInfo == Panel_1680x1050)) {
1623 SiS_Pr->SiS_LCDInfo |= LCDDualLink;
1631 if((SiS_Pr->SiS_IF_DEF_LVDS == 1) || (SiS_Pr->SiS_VBType & VB_NoLCD)) {
1632 /* Always center screen on LVDS (if scaling is disabled) */
1633 SiS_Pr->SiS_LCDInfo &= ~LCDPass11;
1634 } else if(SiS_Pr->SiS_VBType & VB_SISVB) {
1635 if(SiS_Pr->SiS_VBType & VB_SISLVDS) {
1636 /* Always center screen on SiS LVDS (if scaling is disabled) */
1637 SiS_Pr->SiS_LCDInfo &= ~LCDPass11;
1639 /* By default, pass 1:1 on SiS TMDS (if scaling is supported) */
1640 if(panelcanscale) SiS_Pr->SiS_LCDInfo |= LCDPass11;
1641 if(SiS_Pr->CenterScreen == 1) SiS_Pr->SiS_LCDInfo &= ~LCDPass11;
1645 SiS_Pr->PanelVCLKIdx300 = VCLK65_300;
1646 SiS_Pr->PanelVCLKIdx315 = VCLK108_2_315;
1648 switch(SiS_Pr->SiS_LCDResInfo) {
1649 case Panel_320x240_1:
1650 case Panel_320x240_2:
1651 case Panel_320x240_3: SiS_Pr->PanelXRes = 640; SiS_Pr->PanelYRes = 480;
1652 SiS_Pr->PanelVRS = 24; SiS_Pr->PanelVRE = 3;
1653 SiS_Pr->PanelVCLKIdx300 = VCLK28;
1654 SiS_Pr->PanelVCLKIdx315 = VCLK28;
1656 case Panel_640x480: SiS_Pr->PanelXRes = 640; SiS_Pr->PanelYRes = 480;
1657 SiS_Pr->PanelVRE = 3;
1658 SiS_Pr->PanelVCLKIdx300 = VCLK28;
1659 SiS_Pr->PanelVCLKIdx315 = VCLK28;
1661 case Panel_800x600: SiS_Pr->PanelXRes = 800; SiS_Pr->PanelYRes = 600;
1662 SiS_Pr->PanelHT = 1056; SiS_Pr->PanelVT = 628;
1663 SiS_Pr->PanelHRS = 40; SiS_Pr->PanelHRE = 128;
1664 SiS_Pr->PanelVRS = 1; SiS_Pr->PanelVRE = 4;
1665 SiS_Pr->PanelVCLKIdx300 = VCLK40;
1666 SiS_Pr->PanelVCLKIdx315 = VCLK40;
1668 case Panel_1024x600: SiS_Pr->PanelXRes = 1024; SiS_Pr->PanelYRes = 600;
1669 SiS_Pr->PanelHT = 1344; SiS_Pr->PanelVT = 800;
1670 SiS_Pr->PanelHRS = 24; SiS_Pr->PanelHRE = 136;
1671 SiS_Pr->PanelVRS = 2 /* 88 */ ; SiS_Pr->PanelVRE = 6;
1672 SiS_Pr->PanelVCLKIdx300 = VCLK65_300;
1673 SiS_Pr->PanelVCLKIdx315 = VCLK65_315;
1675 case Panel_1024x768: SiS_Pr->PanelXRes = 1024; SiS_Pr->PanelYRes = 768;
1676 SiS_Pr->PanelHT = 1344; SiS_Pr->PanelVT = 806;
1677 SiS_Pr->PanelHRS = 24; SiS_Pr->PanelHRE = 136;
1678 SiS_Pr->PanelVRS = 3; SiS_Pr->PanelVRE = 6;
1679 if(SiS_Pr->ChipType < SIS_315H) {
1680 SiS_Pr->PanelHRS = 23;
1681 SiS_Pr->PanelVRE = 5;
1683 SiS_Pr->PanelVCLKIdx300 = VCLK65_300;
1684 SiS_Pr->PanelVCLKIdx315 = VCLK65_315;
1685 SiS_GetLCDInfoBIOS(SiS_Pr);
1687 case Panel_1152x768: SiS_Pr->PanelXRes = 1152; SiS_Pr->PanelYRes = 768;
1688 SiS_Pr->PanelHT = 1344; SiS_Pr->PanelVT = 806;
1689 SiS_Pr->PanelHRS = 24; SiS_Pr->PanelHRE = 136;
1690 SiS_Pr->PanelVRS = 3; SiS_Pr->PanelVRE = 6;
1691 if(SiS_Pr->ChipType < SIS_315H) {
1692 SiS_Pr->PanelHRS = 23;
1693 SiS_Pr->PanelVRE = 5;
1695 SiS_Pr->PanelVCLKIdx300 = VCLK65_300;
1696 SiS_Pr->PanelVCLKIdx315 = VCLK65_315;
1698 case Panel_1152x864: SiS_Pr->PanelXRes = 1152; SiS_Pr->PanelYRes = 864;
1700 case Panel_1280x720: SiS_Pr->PanelXRes = 1280; SiS_Pr->PanelYRes = 720;
1701 SiS_Pr->PanelHT = 1650; SiS_Pr->PanelVT = 750;
1702 SiS_Pr->PanelHRS = 110; SiS_Pr->PanelHRE = 40;
1703 SiS_Pr->PanelVRS = 5; SiS_Pr->PanelVRE = 5;
1704 SiS_Pr->PanelVCLKIdx315 = VCLK_1280x720;
1705 /* Data above for TMDS (projector); get from BIOS for LVDS */
1706 SiS_GetLCDInfoBIOS(SiS_Pr);
1708 case Panel_1280x768: SiS_Pr->PanelXRes = 1280; SiS_Pr->PanelYRes = 768;
1709 if(SiS_Pr->SiS_IF_DEF_LVDS == 1) {
1710 SiS_Pr->PanelHT = 1408; SiS_Pr->PanelVT = 806;
1711 SiS_Pr->PanelVCLKIdx300 = VCLK81_300; /* ? */
1712 SiS_Pr->PanelVCLKIdx315 = VCLK81_315; /* ? */
1714 SiS_Pr->PanelHT = 1688; SiS_Pr->PanelVT = 802;
1715 SiS_Pr->PanelHRS = 48; SiS_Pr->PanelHRE = 112;
1716 SiS_Pr->PanelVRS = 3; SiS_Pr->PanelVRE = 6;
1717 SiS_Pr->PanelVCLKIdx300 = VCLK81_300;
1718 SiS_Pr->PanelVCLKIdx315 = VCLK81_315;
1721 case Panel_1280x768_2: SiS_Pr->PanelXRes = 1280; SiS_Pr->PanelYRes = 768;
1722 SiS_Pr->PanelHT = 1660; SiS_Pr->PanelVT = 806;
1723 SiS_Pr->PanelHRS = 48; SiS_Pr->PanelHRE = 112;
1724 SiS_Pr->PanelVRS = 3; SiS_Pr->PanelVRE = 6;
1725 SiS_Pr->PanelVCLKIdx315 = VCLK_1280x768_2;
1726 SiS_GetLCDInfoBIOS(SiS_Pr);
1728 case Panel_1280x800: SiS_Pr->PanelXRes = 1280; SiS_Pr->PanelYRes = 800;
1729 SiS_Pr->PanelHT = 1408; SiS_Pr->PanelVT = 816;
1730 SiS_Pr->PanelHRS = 21; SiS_Pr->PanelHRE = 24;
1731 SiS_Pr->PanelVRS = 4; SiS_Pr->PanelVRE = 3;
1732 SiS_Pr->PanelVCLKIdx315 = VCLK_1280x800_315;
1733 SiS_GetLCDInfoBIOS(SiS_Pr);
1735 case Panel_1280x800_2: SiS_Pr->PanelXRes = 1280; SiS_Pr->PanelYRes = 800;
1736 SiS_Pr->PanelHT = 1552; SiS_Pr->PanelVT = 812;
1737 SiS_Pr->PanelHRS = 48; SiS_Pr->PanelHRE = 112;
1738 SiS_Pr->PanelVRS = 4; SiS_Pr->PanelVRE = 3;
1739 SiS_Pr->PanelVCLKIdx315 = VCLK_1280x800_315_2;
1740 SiS_GetLCDInfoBIOS(SiS_Pr);
1742 case Panel_1280x854: SiS_Pr->PanelXRes = 1280; SiS_Pr->PanelYRes = 854;
1743 SiS_Pr->PanelHT = 1664; SiS_Pr->PanelVT = 861;
1744 SiS_Pr->PanelHRS = 16; SiS_Pr->PanelHRE = 112;
1745 SiS_Pr->PanelVRS = 1; SiS_Pr->PanelVRE = 3;
1746 SiS_Pr->PanelVCLKIdx315 = VCLK_1280x854;
1747 SiS_GetLCDInfoBIOS(SiS_Pr);
1749 case Panel_1280x960: SiS_Pr->PanelXRes = 1280; SiS_Pr->PanelYRes = 960;
1750 SiS_Pr->PanelHT = 1800; SiS_Pr->PanelVT = 1000;
1751 SiS_Pr->PanelVCLKIdx300 = VCLK108_3_300;
1752 SiS_Pr->PanelVCLKIdx315 = VCLK108_3_315;
1753 if(resinfo == SIS_RI_1280x1024) {
1754 SiS_Pr->PanelVCLKIdx300 = VCLK100_300;
1755 SiS_Pr->PanelVCLKIdx315 = VCLK100_315;
1758 case Panel_1280x1024: SiS_Pr->PanelXRes = 1280; SiS_Pr->PanelYRes = 1024;
1759 SiS_Pr->PanelHT = 1688; SiS_Pr->PanelVT = 1066;
1760 SiS_Pr->PanelHRS = 48; SiS_Pr->PanelHRE = 112;
1761 SiS_Pr->PanelVRS = 1; SiS_Pr->PanelVRE = 3;
1762 SiS_Pr->PanelVCLKIdx300 = VCLK108_3_300;
1763 SiS_Pr->PanelVCLKIdx315 = VCLK108_2_315;
1764 SiS_GetLCDInfoBIOS(SiS_Pr);
1766 case Panel_1400x1050: SiS_Pr->PanelXRes = 1400; SiS_Pr->PanelYRes = 1050;
1767 SiS_Pr->PanelHT = 1688; SiS_Pr->PanelVT = 1066;
1768 SiS_Pr->PanelHRS = 48; SiS_Pr->PanelHRE = 112;
1769 SiS_Pr->PanelVRS = 1; SiS_Pr->PanelVRE = 3;
1770 SiS_Pr->PanelVCLKIdx315 = VCLK108_2_315;
1771 SiS_GetLCDInfoBIOS(SiS_Pr);
1773 case Panel_1600x1200: SiS_Pr->PanelXRes = 1600; SiS_Pr->PanelYRes = 1200;
1774 SiS_Pr->PanelHT = 2160; SiS_Pr->PanelVT = 1250;
1775 SiS_Pr->PanelHRS = 64; SiS_Pr->PanelHRE = 192;
1776 SiS_Pr->PanelVRS = 1; SiS_Pr->PanelVRE = 3;
1777 SiS_Pr->PanelVCLKIdx315 = VCLK162_315;
1778 if(SiS_Pr->SiS_VBType & VB_SISTMDSLCDA) {
1779 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCDA) {
1780 SiS_Pr->PanelHT = 1760; SiS_Pr->PanelVT = 1235;
1781 SiS_Pr->PanelHRS = 48; SiS_Pr->PanelHRE = 32;
1782 SiS_Pr->PanelVRS = 2; SiS_Pr->PanelVRE = 4;
1783 SiS_Pr->PanelVCLKIdx315 = VCLK130_315;
1784 SiS_Pr->Alternate1600x1200 = true;
1786 } else if(SiS_Pr->SiS_IF_DEF_LVDS) {
1787 SiS_Pr->PanelHT = 2048; SiS_Pr->PanelVT = 1320;
1788 SiS_Pr->PanelHRS = SiS_Pr->PanelHRE = 999;
1789 SiS_Pr->PanelVRS = SiS_Pr->PanelVRE = 999;
1791 SiS_GetLCDInfoBIOS(SiS_Pr);
1793 case Panel_1680x1050: SiS_Pr->PanelXRes = 1680; SiS_Pr->PanelYRes = 1050;
1794 SiS_Pr->PanelHT = 1900; SiS_Pr->PanelVT = 1066;
1795 SiS_Pr->PanelHRS = 26; SiS_Pr->PanelHRE = 76;
1796 SiS_Pr->PanelVRS = 3; SiS_Pr->PanelVRE = 6;
1797 SiS_Pr->PanelVCLKIdx315 = VCLK121_315;
1798 SiS_GetLCDInfoBIOS(SiS_Pr);
1800 case Panel_Barco1366: SiS_Pr->PanelXRes = 1360; SiS_Pr->PanelYRes = 1024;
1801 SiS_Pr->PanelHT = 1688; SiS_Pr->PanelVT = 1066;
1803 case Panel_848x480: SiS_Pr->PanelXRes = 848; SiS_Pr->PanelYRes = 480;
1804 SiS_Pr->PanelHT = 1088; SiS_Pr->PanelVT = 525;
1806 case Panel_856x480: SiS_Pr->PanelXRes = 856; SiS_Pr->PanelYRes = 480;
1807 SiS_Pr->PanelHT = 1088; SiS_Pr->PanelVT = 525;
1809 case Panel_Custom: SiS_Pr->PanelXRes = SiS_Pr->CP_MaxX;
1810 SiS_Pr->PanelYRes = SiS_Pr->CP_MaxY;
1811 SiS_Pr->PanelHT = SiS_Pr->CHTotal;
1812 SiS_Pr->PanelVT = SiS_Pr->CVTotal;
1813 if(SiS_Pr->CP_PreferredIndex != -1) {
1814 SiS_Pr->PanelXRes = SiS_Pr->CP_HDisplay[SiS_Pr->CP_PreferredIndex];
1815 SiS_Pr->PanelYRes = SiS_Pr->CP_VDisplay[SiS_Pr->CP_PreferredIndex];
1816 SiS_Pr->PanelHT = SiS_Pr->CP_HTotal[SiS_Pr->CP_PreferredIndex];
1817 SiS_Pr->PanelVT = SiS_Pr->CP_VTotal[SiS_Pr->CP_PreferredIndex];
1818 SiS_Pr->PanelHRS = SiS_Pr->CP_HSyncStart[SiS_Pr->CP_PreferredIndex];
1819 SiS_Pr->PanelHRE = SiS_Pr->CP_HSyncEnd[SiS_Pr->CP_PreferredIndex];
1820 SiS_Pr->PanelVRS = SiS_Pr->CP_VSyncStart[SiS_Pr->CP_PreferredIndex];
1821 SiS_Pr->PanelVRE = SiS_Pr->CP_VSyncEnd[SiS_Pr->CP_PreferredIndex];
1822 SiS_Pr->PanelHRS -= SiS_Pr->PanelXRes;
1823 SiS_Pr->PanelHRE -= SiS_Pr->PanelHRS;
1824 SiS_Pr->PanelVRS -= SiS_Pr->PanelYRes;
1825 SiS_Pr->PanelVRE -= SiS_Pr->PanelVRS;
1826 if(SiS_Pr->CP_PrefClock) {
1828 SiS_Pr->PanelVCLKIdx315 = VCLK_CUSTOM_315;
1829 SiS_Pr->PanelVCLKIdx300 = VCLK_CUSTOM_300;
1830 if(SiS_Pr->ChipType < SIS_315H) idx = VCLK_CUSTOM_300;
1831 else idx = VCLK_CUSTOM_315;
1832 SiS_Pr->SiS_VCLKData[idx].CLOCK =
1833 SiS_Pr->SiS_VBVCLKData[idx].CLOCK = SiS_Pr->CP_PrefClock;
1834 SiS_Pr->SiS_VCLKData[idx].SR2B =
1835 SiS_Pr->SiS_VBVCLKData[idx].Part4_A = SiS_Pr->CP_PrefSR2B;
1836 SiS_Pr->SiS_VCLKData[idx].SR2C =
1837 SiS_Pr->SiS_VBVCLKData[idx].Part4_B = SiS_Pr->CP_PrefSR2C;
1841 default: SiS_Pr->PanelXRes = 1024; SiS_Pr->PanelYRes = 768;
1842 SiS_Pr->PanelHT = 1344; SiS_Pr->PanelVT = 806;
1847 if( (SiS_Pr->SiS_IF_DEF_FSTN) ||
1848 (SiS_Pr->SiS_IF_DEF_DSTN) ||
1849 (SiS_Pr->SiS_CustomT == CUT_BARCO1366) ||
1850 (SiS_Pr->SiS_CustomT == CUT_BARCO1024) ||
1851 (SiS_Pr->SiS_CustomT == CUT_PANEL848) ||
1852 (SiS_Pr->SiS_CustomT == CUT_PANEL856) ) {
1853 SiS_Pr->PanelHRS = 999;
1854 SiS_Pr->PanelHRE = 999;
1857 if( (SiS_Pr->SiS_CustomT == CUT_BARCO1366) ||
1858 (SiS_Pr->SiS_CustomT == CUT_BARCO1024) ||
1859 (SiS_Pr->SiS_CustomT == CUT_PANEL848) ||
1860 (SiS_Pr->SiS_CustomT == CUT_PANEL856) ) {
1861 SiS_Pr->PanelVRS = 999;
1862 SiS_Pr->PanelVRE = 999;
1865 /* DontExpand overrule */
1866 if((SiS_Pr->SiS_VBType & VB_SISVB) && (!(SiS_Pr->SiS_VBType & VB_NoLCD))) {
1868 if((SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) && (modeflag & NoSupportLCDScale)) {
1869 /* No scaling for this mode on any panel (LCD=CRT2)*/
1870 SiS_Pr->SiS_LCDInfo |= DontExpandLCD;
1873 switch(SiS_Pr->SiS_LCDResInfo) {
1876 case Panel_1152x864:
1877 case Panel_1280x768: /* TMDS only */
1878 SiS_Pr->SiS_LCDInfo |= DontExpandLCD;
1881 case Panel_800x600: {
1882 static const unsigned char nonscalingmodes[] = {
1883 SIS_RI_720x480, SIS_RI_720x576, SIS_RI_768x576, SIS_RI_800x480, 0xff
1885 SiS_CheckScaling(SiS_Pr, resinfo, nonscalingmodes);
1888 case Panel_1024x768: {
1889 static const unsigned char nonscalingmodes[] = {
1890 SIS_RI_720x480, SIS_RI_720x576, SIS_RI_768x576, SIS_RI_800x480, SIS_RI_848x480,
1891 SIS_RI_856x480, SIS_RI_960x540, SIS_RI_960x600, SIS_RI_1024x576,SIS_RI_1024x600,
1894 SiS_CheckScaling(SiS_Pr, resinfo, nonscalingmodes);
1897 case Panel_1280x720: {
1898 static const unsigned char nonscalingmodes[] = {
1899 SIS_RI_720x480, SIS_RI_720x576, SIS_RI_768x576, SIS_RI_800x480, SIS_RI_848x480,
1900 SIS_RI_856x480, SIS_RI_960x540, SIS_RI_960x600, SIS_RI_1024x576,SIS_RI_1024x600,
1903 SiS_CheckScaling(SiS_Pr, resinfo, nonscalingmodes);
1904 if(SiS_Pr->PanelHT == 1650) {
1905 SiS_Pr->SiS_LCDInfo |= DontExpandLCD;
1909 case Panel_1280x768_2: { /* LVDS only */
1910 static const unsigned char nonscalingmodes[] = {
1911 SIS_RI_720x480, SIS_RI_720x576, SIS_RI_768x576, SIS_RI_800x480, SIS_RI_848x480,
1912 SIS_RI_856x480, SIS_RI_960x540, SIS_RI_960x600, SIS_RI_1024x576,SIS_RI_1024x600,
1913 SIS_RI_1152x768,0xff
1915 SiS_CheckScaling(SiS_Pr, resinfo, nonscalingmodes);
1917 case SIS_RI_1280x720: if(SiS_Pr->UsePanelScaler == -1) {
1918 SiS_Pr->SiS_LCDInfo |= DontExpandLCD;
1924 case Panel_1280x800: { /* SiS TMDS special (Averatec 6200 series) */
1925 static const unsigned char nonscalingmodes[] = {
1926 SIS_RI_720x480, SIS_RI_720x576, SIS_RI_768x576, SIS_RI_800x480, SIS_RI_848x480,
1927 SIS_RI_856x480, SIS_RI_960x540, SIS_RI_960x600, SIS_RI_1024x576,SIS_RI_1024x600,
1928 SIS_RI_1152x768,SIS_RI_1280x720,SIS_RI_1280x768,0xff
1930 SiS_CheckScaling(SiS_Pr, resinfo, nonscalingmodes);
1933 case Panel_1280x800_2: { /* SiS LVDS */
1934 static const unsigned char nonscalingmodes[] = {
1935 SIS_RI_720x480, SIS_RI_720x576, SIS_RI_768x576, SIS_RI_800x480, SIS_RI_848x480,
1936 SIS_RI_856x480, SIS_RI_960x540, SIS_RI_960x600, SIS_RI_1024x576,SIS_RI_1024x600,
1937 SIS_RI_1152x768,0xff
1939 SiS_CheckScaling(SiS_Pr, resinfo, nonscalingmodes);
1941 case SIS_RI_1280x720:
1942 case SIS_RI_1280x768: if(SiS_Pr->UsePanelScaler == -1) {
1943 SiS_Pr->SiS_LCDInfo |= DontExpandLCD;
1949 case Panel_1280x854: { /* SiS LVDS */
1950 static const unsigned char nonscalingmodes[] = {
1951 SIS_RI_720x480, SIS_RI_720x576, SIS_RI_768x576, SIS_RI_800x480, SIS_RI_848x480,
1952 SIS_RI_856x480, SIS_RI_960x540, SIS_RI_960x600, SIS_RI_1024x576,SIS_RI_1024x600,
1953 SIS_RI_1152x768,0xff
1955 SiS_CheckScaling(SiS_Pr, resinfo, nonscalingmodes);
1957 case SIS_RI_1280x720:
1958 case SIS_RI_1280x768:
1959 case SIS_RI_1280x800: if(SiS_Pr->UsePanelScaler == -1) {
1960 SiS_Pr->SiS_LCDInfo |= DontExpandLCD;
1966 case Panel_1280x960: {
1967 static const unsigned char nonscalingmodes[] = {
1968 SIS_RI_720x480, SIS_RI_720x576, SIS_RI_768x576, SIS_RI_800x480, SIS_RI_848x480,
1969 SIS_RI_856x480, SIS_RI_960x540, SIS_RI_960x600, SIS_RI_1024x576,SIS_RI_1024x600,
1970 SIS_RI_1152x768,SIS_RI_1152x864,SIS_RI_1280x720,SIS_RI_1280x768,SIS_RI_1280x800,
1971 SIS_RI_1280x854,0xff
1973 SiS_CheckScaling(SiS_Pr, resinfo, nonscalingmodes);
1976 case Panel_1280x1024: {
1977 static const unsigned char nonscalingmodes[] = {
1978 SIS_RI_720x480, SIS_RI_720x576, SIS_RI_768x576, SIS_RI_800x480, SIS_RI_848x480,
1979 SIS_RI_856x480, SIS_RI_960x540, SIS_RI_960x600, SIS_RI_1024x576,SIS_RI_1024x600,
1980 SIS_RI_1152x768,SIS_RI_1152x864,SIS_RI_1280x720,SIS_RI_1280x768,SIS_RI_1280x800,
1981 SIS_RI_1280x854,SIS_RI_1280x960,0xff
1983 SiS_CheckScaling(SiS_Pr, resinfo, nonscalingmodes);
1986 case Panel_1400x1050: {
1987 static const unsigned char nonscalingmodes[] = {
1988 SIS_RI_720x480, SIS_RI_720x576, SIS_RI_768x576, SIS_RI_800x480, SIS_RI_848x480,
1989 SIS_RI_856x480, SIS_RI_960x540, SIS_RI_960x600, SIS_RI_1024x576,SIS_RI_1024x600,
1990 SIS_RI_1152x768,SIS_RI_1152x864,SIS_RI_1280x768,SIS_RI_1280x800,SIS_RI_1280x854,
1991 SIS_RI_1280x960,0xff
1993 SiS_CheckScaling(SiS_Pr, resinfo, nonscalingmodes);
1995 case SIS_RI_1280x720: if(SiS_Pr->UsePanelScaler == -1) {
1996 SiS_Pr->SiS_LCDInfo |= DontExpandLCD;
1999 case SIS_RI_1280x1024: SiS_Pr->SiS_LCDInfo |= DontExpandLCD;
2004 case Panel_1600x1200: {
2005 static const unsigned char nonscalingmodes[] = {
2006 SIS_RI_720x480, SIS_RI_720x576, SIS_RI_768x576, SIS_RI_800x480, SIS_RI_848x480,
2007 SIS_RI_856x480, SIS_RI_960x540, SIS_RI_960x600, SIS_RI_1024x576,SIS_RI_1024x600,
2008 SIS_RI_1152x768,SIS_RI_1152x864,SIS_RI_1280x720,SIS_RI_1280x768,SIS_RI_1280x800,
2009 SIS_RI_1280x854,SIS_RI_1280x960,SIS_RI_1360x768,SIS_RI_1360x1024,0xff
2011 SiS_CheckScaling(SiS_Pr, resinfo, nonscalingmodes);
2014 case Panel_1680x1050: {
2015 static const unsigned char nonscalingmodes[] = {
2016 SIS_RI_720x480, SIS_RI_720x576, SIS_RI_768x576, SIS_RI_800x480, SIS_RI_848x480,
2017 SIS_RI_856x480, SIS_RI_960x540, SIS_RI_960x600, SIS_RI_1024x576,SIS_RI_1024x600,
2018 SIS_RI_1152x768,SIS_RI_1152x864,SIS_RI_1280x854,SIS_RI_1280x960,SIS_RI_1360x768,
2019 SIS_RI_1360x1024,0xff
2021 SiS_CheckScaling(SiS_Pr, resinfo, nonscalingmodes);
2027 #ifdef CONFIG_FB_SIS_300
2028 if(SiS_Pr->SiS_IF_DEF_LVDS == 1) {
2029 if(SiS_Pr->SiS_CustomT == CUT_PANEL848 || SiS_Pr->SiS_CustomT == CUT_PANEL856) {
2030 SiS_Pr->SiS_LCDInfo = 0x80 | 0x40 | 0x20; /* neg h/v sync, RGB24(D0 = 0) */
2034 if(SiS_Pr->ChipType < SIS_315H) {
2035 if(SiS_Pr->SiS_IF_DEF_LVDS == 1) {
2036 if(SiS_Pr->SiS_UseROM) {
2037 if((ROMAddr[0x233] == 0x12) && (ROMAddr[0x234] == 0x34)) {
2038 if(!(ROMAddr[0x235] & 0x02)) {
2039 SiS_Pr->SiS_LCDInfo &= (~DontExpandLCD);
2043 } else if(SiS_Pr->SiS_VBType & VB_SIS30xBLV) {
2044 if((SiS_Pr->SiS_SetFlag & SetDOSMode) && ((ModeNo == 0x03) || (ModeNo == 0x10))) {
2045 SiS_Pr->SiS_LCDInfo &= (~DontExpandLCD);
2053 if(modexres == SiS_Pr->PanelXRes && modeyres == SiS_Pr->PanelYRes) {
2054 SiS_Pr->SiS_LCDInfo &= ~LCDPass11;
2057 if(SiS_Pr->SiS_IF_DEF_TRUMPION) {
2058 SiS_Pr->SiS_LCDInfo |= (DontExpandLCD | LCDPass11);
2061 switch(SiS_Pr->SiS_LCDResInfo) {
2063 SiS_Pr->SiS_LCDInfo |= (DontExpandLCD | LCDPass11);
2065 case Panel_1280x800:
2066 /* Don't pass 1:1 by default (TMDS special) */
2067 if(SiS_Pr->CenterScreen == -1) SiS_Pr->SiS_LCDInfo &= ~LCDPass11;
2069 case Panel_1280x960:
2070 SiS_Pr->SiS_LCDInfo &= ~LCDPass11;
2073 if((!SiS_Pr->CP_PrefClock) ||
2074 (modexres > SiS_Pr->PanelXRes) || (modeyres > SiS_Pr->PanelYRes)) {
2075 SiS_Pr->SiS_LCDInfo |= LCDPass11;
2080 if((SiS_Pr->UseCustomMode) || (SiS_Pr->SiS_CustomT == CUT_UNKNOWNLCD)) {
2081 SiS_Pr->SiS_LCDInfo |= (DontExpandLCD | LCDPass11);
2084 /* (In)validate LCDPass11 flag */
2085 if(!(SiS_Pr->SiS_LCDInfo & DontExpandLCD)) {
2086 SiS_Pr->SiS_LCDInfo &= ~LCDPass11;
2090 if(!((SiS_Pr->ChipType < SIS_315H) && (SiS_Pr->SiS_SetFlag & SetDOSMode))) {
2092 if((SiS_Pr->SiS_IF_DEF_LVDS == 1) || (SiS_Pr->SiS_VBType & VB_NoLCD)) {
2093 if(SiS_Pr->SiS_IF_DEF_TRUMPION == 0) {
2094 if(ModeNo == 0x12) {
2095 if(SiS_Pr->SiS_LCDInfo & LCDPass11) {
2096 SiS_Pr->SiS_SetFlag |= EnableLVDSDDA;
2098 } else if(ModeNo > 0x13) {
2099 if(SiS_Pr->SiS_LCDResInfo == Panel_1024x600) {
2100 if(!(SiS_Pr->SiS_LCDInfo & DontExpandLCD)) {
2101 if((resinfo == SIS_RI_800x600) || (resinfo == SIS_RI_400x300)) {
2102 SiS_Pr->SiS_SetFlag |= EnableLVDSDDA;
2110 if(modeflag & HalfDCLK) {
2111 if(SiS_Pr->SiS_IF_DEF_TRUMPION == 1) {
2112 SiS_Pr->SiS_SetFlag |= EnableLVDSDDA;
2113 } else if(SiS_Pr->SiS_LCDInfo & DontExpandLCD) {
2114 SiS_Pr->SiS_SetFlag |= EnableLVDSDDA;
2115 } else if(SiS_Pr->SiS_LCDResInfo == Panel_640x480) {
2116 SiS_Pr->SiS_SetFlag |= EnableLVDSDDA;
2117 } else if(ModeNo > 0x13) {
2118 if(SiS_Pr->SiS_LCDResInfo == Panel_1024x768) {
2119 if(resinfo == SIS_RI_512x384) SiS_Pr->SiS_SetFlag |= EnableLVDSDDA;
2120 } else if(SiS_Pr->SiS_LCDResInfo == Panel_800x600) {
2121 if(resinfo == SIS_RI_400x300) SiS_Pr->SiS_SetFlag |= EnableLVDSDDA;
2129 if(SiS_Pr->SiS_VBInfo & SetInSlaveMode) {
2130 if(SiS_Pr->SiS_VBInfo & SetNotSimuMode) {
2131 SiS_Pr->SiS_SetFlag |= LCDVESATiming;
2134 SiS_Pr->SiS_SetFlag |= LCDVESATiming;
2138 printk(KERN_DEBUG "sisfb: (LCDInfo=0x%04x LCDResInfo=0x%02x LCDTypeInfo=0x%02x)\n",
2139 SiS_Pr->SiS_LCDInfo, SiS_Pr->SiS_LCDResInfo, SiS_Pr->SiS_LCDTypeInfo);
2143 /*********************************************/
2145 /*********************************************/
2148 SiS_GetVCLK2Ptr(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex,
2149 unsigned short RefreshRateTableIndex)
2151 unsigned short CRT2Index, VCLKIndex = 0, VCLKIndexGEN = 0, VCLKIndexGENCRT = 0;
2152 unsigned short resinfo, tempbx;
2153 const unsigned char *CHTVVCLKPtr = NULL;
2155 if(ModeNo <= 0x13) {
2156 resinfo = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_ResInfo;
2157 CRT2Index = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_CRT2CRTC;
2158 VCLKIndexGEN = (SiS_GetRegByte((SiS_Pr->SiS_P3ca+0x02)) >> 2) & 0x03;
2159 VCLKIndexGENCRT = VCLKIndexGEN;
2161 resinfo = SiS_Pr->SiS_EModeIDTable[ModeIdIndex].Ext_RESINFO;
2162 CRT2Index = SiS_Pr->SiS_RefIndex[RefreshRateTableIndex].Ext_CRT2CRTC;
2163 VCLKIndexGEN = SiS_Pr->SiS_RefIndex[RefreshRateTableIndex].Ext_CRTVCLK;
2164 VCLKIndexGENCRT = SiS_GetRefCRTVCLK(SiS_Pr, RefreshRateTableIndex,
2165 (SiS_Pr->SiS_SetFlag & ProgrammingCRT2) ? SiS_Pr->SiS_UseWideCRT2 : SiS_Pr->SiS_UseWide);
2168 if(SiS_Pr->SiS_VBType & VB_SISVB) { /* 30x/B/LV */
2170 if(SiS_Pr->SiS_SetFlag & ProgrammingCRT2) {
2173 if(SiS_Pr->SiS_VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) { /* LCD */
2175 if(SiS_Pr->ChipType < SIS_315H) {
2176 VCLKIndex = SiS_Pr->PanelVCLKIdx300;
2177 if((SiS_Pr->SiS_LCDInfo & DontExpandLCD) && (SiS_Pr->SiS_LCDInfo & LCDPass11)) {
2178 VCLKIndex = VCLKIndexGEN;
2181 VCLKIndex = SiS_Pr->PanelVCLKIdx315;
2182 if((SiS_Pr->SiS_LCDInfo & DontExpandLCD) && (SiS_Pr->SiS_LCDInfo & LCDPass11)) {
2184 /* Correct those whose IndexGEN doesn't match VBVCLK array */
2185 case SIS_RI_720x480: VCLKIndex = VCLK_720x480; break;
2186 case SIS_RI_720x576: VCLKIndex = VCLK_720x576; break;
2187 case SIS_RI_768x576: VCLKIndex = VCLK_768x576; break;
2188 case SIS_RI_848x480: VCLKIndex = VCLK_848x480; break;
2189 case SIS_RI_856x480: VCLKIndex = VCLK_856x480; break;
2190 case SIS_RI_800x480: VCLKIndex = VCLK_800x480; break;
2191 case SIS_RI_1024x576: VCLKIndex = VCLK_1024x576; break;
2192 case SIS_RI_1152x864: VCLKIndex = VCLK_1152x864; break;
2193 case SIS_RI_1280x720: VCLKIndex = VCLK_1280x720; break;
2194 case SIS_RI_1360x768: VCLKIndex = VCLK_1360x768; break;
2195 default: VCLKIndex = VCLKIndexGEN;
2198 if(ModeNo <= 0x13) {
2199 if(SiS_Pr->ChipType <= SIS_315PRO) {
2200 if(SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_CRT2CRTC == 1) VCLKIndex = 0x42;
2202 if(SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_CRT2CRTC == 1) VCLKIndex = 0x00;
2205 if(SiS_Pr->ChipType <= SIS_315PRO) {
2206 if(VCLKIndex == 0) VCLKIndex = 0x41;
2207 if(VCLKIndex == 1) VCLKIndex = 0x43;
2208 if(VCLKIndex == 4) VCLKIndex = 0x44;
2213 } else if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) { /* TV */
2215 if(SiS_Pr->SiS_VBInfo & SetCRT2ToHiVision) {
2216 if(SiS_Pr->SiS_TVMode & TVRPLLDIV2XO) VCLKIndex = HiTVVCLKDIV2;
2217 else VCLKIndex = HiTVVCLK;
2218 if(SiS_Pr->SiS_TVMode & TVSetTVSimuMode) VCLKIndex = HiTVSimuVCLK;
2219 } else if(SiS_Pr->SiS_TVMode & TVSetYPbPr750p) VCLKIndex = YPbPr750pVCLK;
2220 else if(SiS_Pr->SiS_TVMode & TVSetYPbPr525p) VCLKIndex = TVVCLKDIV2;
2221 else if(SiS_Pr->SiS_TVMode & TVRPLLDIV2XO) VCLKIndex = TVVCLKDIV2;
2222 else VCLKIndex = TVVCLK;
2224 if(SiS_Pr->ChipType < SIS_315H) VCLKIndex += TVCLKBASE_300;
2225 else VCLKIndex += TVCLKBASE_315;
2229 VCLKIndex = VCLKIndexGENCRT;
2230 if(SiS_Pr->ChipType < SIS_315H) {
2232 if( (SiS_Pr->ChipType == SIS_630) &&
2233 (SiS_Pr->ChipRevision >= 0x30)) {
2234 if(VCLKIndex == 0x14) VCLKIndex = 0x34;
2236 /* Better VGA2 clock for 1280x1024@75 */
2237 if(VCLKIndex == 0x17) VCLKIndex = 0x45;
2242 } else { /* If not programming CRT2 */
2244 VCLKIndex = VCLKIndexGENCRT;
2245 if(SiS_Pr->ChipType < SIS_315H) {
2247 if( (SiS_Pr->ChipType != SIS_630) &&
2248 (SiS_Pr->ChipType != SIS_300) ) {
2249 if(VCLKIndex == 0x1b) VCLKIndex = 0x48;
2257 VCLKIndex = CRT2Index;
2259 if(SiS_Pr->SiS_SetFlag & ProgrammingCRT2) {
2261 if( (SiS_Pr->SiS_IF_DEF_CH70xx != 0) && (SiS_Pr->SiS_VBInfo & SetCRT2ToTV) ) {
2265 if(SiS_Pr->SiS_TVMode & TVSetCHOverScan) tempbx += 1;
2266 if(SiS_Pr->SiS_TVMode & TVSetPAL) {
2268 if(SiS_Pr->SiS_ModeType > ModeVGA) {
2269 if(SiS_Pr->SiS_CHSOverScan) tempbx = 8;
2271 if(SiS_Pr->SiS_TVMode & TVSetPALM) {
2273 if(SiS_Pr->SiS_TVMode & TVSetCHOverScan) tempbx += 1;
2274 } else if(SiS_Pr->SiS_TVMode & TVSetPALN) {
2276 if(SiS_Pr->SiS_TVMode & TVSetCHOverScan) tempbx += 1;
2280 case 0: CHTVVCLKPtr = SiS_Pr->SiS_CHTVVCLKUNTSC; break;
2281 case 1: CHTVVCLKPtr = SiS_Pr->SiS_CHTVVCLKONTSC; break;
2282 case 2: CHTVVCLKPtr = SiS_Pr->SiS_CHTVVCLKUPAL; break;
2283 case 3: CHTVVCLKPtr = SiS_Pr->SiS_CHTVVCLKOPAL; break;
2284 case 4: CHTVVCLKPtr = SiS_Pr->SiS_CHTVVCLKUPALM; break;
2285 case 5: CHTVVCLKPtr = SiS_Pr->SiS_CHTVVCLKOPALM; break;
2286 case 6: CHTVVCLKPtr = SiS_Pr->SiS_CHTVVCLKUPALN; break;
2287 case 7: CHTVVCLKPtr = SiS_Pr->SiS_CHTVVCLKOPALN; break;
2288 case 8: CHTVVCLKPtr = SiS_Pr->SiS_CHTVVCLKSOPAL; break;
2289 default: CHTVVCLKPtr = SiS_Pr->SiS_CHTVVCLKOPAL; break;
2291 VCLKIndex = CHTVVCLKPtr[VCLKIndex];
2293 } else if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) {
2295 if(SiS_Pr->ChipType < SIS_315H) {
2296 VCLKIndex = SiS_Pr->PanelVCLKIdx300;
2298 VCLKIndex = SiS_Pr->PanelVCLKIdx315;
2301 #ifdef CONFIG_FB_SIS_300
2302 /* Special Timing: Barco iQ Pro R series */
2303 if(SiS_Pr->SiS_CustomT == CUT_BARCO1366) VCLKIndex = 0x44;
2305 /* Special Timing: 848x480 and 856x480 parallel lvds panels */
2306 if(SiS_Pr->SiS_CustomT == CUT_PANEL848 || SiS_Pr->SiS_CustomT == CUT_PANEL856) {
2307 if(SiS_Pr->ChipType < SIS_315H) {
2308 VCLKIndex = VCLK34_300;
2309 /* if(resinfo == SIS_RI_1360x768) VCLKIndex = ?; */
2311 VCLKIndex = VCLK34_315;
2312 /* if(resinfo == SIS_RI_1360x768) VCLKIndex = ?; */
2319 VCLKIndex = VCLKIndexGENCRT;
2320 if(SiS_Pr->ChipType < SIS_315H) {
2322 if( (SiS_Pr->ChipType == SIS_630) &&
2323 (SiS_Pr->ChipRevision >= 0x30) ) {
2324 if(VCLKIndex == 0x14) VCLKIndex = 0x2e;
2330 } else { /* if not programming CRT2 */
2332 VCLKIndex = VCLKIndexGENCRT;
2333 if(SiS_Pr->ChipType < SIS_315H) {
2335 if( (SiS_Pr->ChipType != SIS_630) &&
2336 (SiS_Pr->ChipType != SIS_300) ) {
2337 if(VCLKIndex == 0x1b) VCLKIndex = 0x48;
2340 if(SiS_Pr->ChipType == SIS_730) {
2341 if(VCLKIndex == 0x0b) VCLKIndex = 0x40; /* 1024x768-70 */
2342 if(VCLKIndex == 0x0d) VCLKIndex = 0x41; /* 1024x768-75 */
2355 /*********************************************/
2356 /* SET CRT2 MODE TYPE REGISTERS */
2357 /*********************************************/
2360 SiS_SetCRT2ModeRegs(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex)
2362 unsigned short i, j, modeflag, tempah=0;
2364 #if defined(CONFIG_FB_SIS_300) || defined(CONFIG_FB_SIS_315)
2365 unsigned short tempbl;
2367 #ifdef CONFIG_FB_SIS_315
2368 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
2369 unsigned short tempah2, tempbl2;
2372 modeflag = SiS_GetModeFlag(SiS_Pr, ModeNo, ModeIdIndex);
2374 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCDA) {
2376 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x00,0xAF,0x40);
2377 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x2E,0xF7);
2381 for(i=0,j=4; i<3; i++,j++) SiS_SetReg(SiS_Pr->SiS_Part1Port,j,0);
2382 if(SiS_Pr->ChipType >= SIS_315H) {
2383 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x02,0x7F);
2386 tempcl = SiS_Pr->SiS_ModeType;
2388 if(SiS_Pr->ChipType < SIS_315H) {
2390 #ifdef CONFIG_FB_SIS_300 /* ---- 300 series ---- */
2392 /* For 301BDH: (with LCD via LVDS) */
2393 if(SiS_Pr->SiS_VBType & VB_NoLCD) {
2394 tempbl = SiS_GetReg(SiS_Pr->SiS_P3c4,0x32);
2397 if((SiS_Pr->SiS_VBInfo & SetCRT2ToTV) || (SiS_Pr->SiS_VBInfo & SetCRT2ToRAMDAC)) {
2401 SiS_SetReg(SiS_Pr->SiS_P3c4,0x32,tempbl);
2407 tempah = ((0x10 >> tempcl) | 0x80);
2409 } else tempah = 0x80;
2411 if(SiS_Pr->SiS_VBInfo & SetInSlaveMode) tempah ^= 0xA0;
2413 #endif /* CONFIG_FB_SIS_300 */
2417 #ifdef CONFIG_FB_SIS_315 /* ------- 315/330 series ------ */
2422 tempah = (0x08 >> tempcl);
2423 if (tempah == 0) tempah = 1;
2426 } else tempah = 0x40;
2428 if(SiS_Pr->SiS_VBInfo & SetInSlaveMode) tempah ^= 0x50;
2430 #endif /* CONFIG_FB_SIS_315 */
2434 if(SiS_Pr->SiS_VBInfo & DisableCRT2Display) tempah = 0;
2436 if(SiS_Pr->ChipType < SIS_315H) {
2437 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x00,tempah);
2439 #ifdef CONFIG_FB_SIS_315
2440 if(SiS_Pr->SiS_IF_DEF_LVDS == 1) {
2441 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x00,0xa0,tempah);
2442 } else if(SiS_Pr->SiS_VBType & VB_SISVB) {
2444 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x00,tempah);
2446 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x00,0xa0,tempah);
2452 if(SiS_Pr->SiS_VBType & VB_SISVB) {
2455 if(!(SiS_Pr->SiS_VBInfo & SetInSlaveMode)) {
2458 if(!(SiS_Pr->SiS_VBInfo & SetCRT2ToRAMDAC)) {
2460 if(!(SiS_Pr->SiS_VBInfo & SetCRT2ToLCD)) {
2465 if(SiS_Pr->ChipType < SIS_315H) {
2467 if(SiS_Pr->SiS_VBInfo & DisableCRT2Display) tempah = 0;
2469 tempah = (tempah << 5) & 0xFF;
2470 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x01,tempah);
2471 tempah = (tempah >> 5) & 0xFF;
2475 if(SiS_Pr->SiS_VBInfo & DisableCRT2Display) tempah = 0x08;
2476 else if(!(SiS_IsDualEdge(SiS_Pr))) tempah |= 0x08;
2477 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x2E,0xF0,tempah);
2482 if((SiS_Pr->SiS_ModeType == ModeVGA) && (!(SiS_Pr->SiS_VBInfo & SetInSlaveMode))) {
2487 if(SiS_Pr->SiS_VBType & VB_SIS301) {
2488 if(SiS_Pr->PanelXRes < 1280 && SiS_Pr->PanelYRes < 960) tempah &= ~0x80;
2491 if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) {
2492 if(!(SiS_Pr->SiS_TVMode & (TVSetYPbPr750p | TVSetYPbPr525p))) {
2493 if(SiS_Pr->SiS_VBInfo & SetInSlaveMode) {
2499 SiS_SetRegANDOR(SiS_Pr->SiS_Part4Port,0x0D,0x40,tempah);
2502 if(SiS_Pr->SiS_VBType & VB_SIS301) {
2503 if(SiS_Pr->PanelXRes < 1280 && SiS_Pr->PanelYRes < 960) tempah = 0;
2506 if(SiS_IsDualLink(SiS_Pr)) tempah |= 0x40;
2508 if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) {
2509 if(SiS_Pr->SiS_TVMode & TVRPLLDIV2XO) {
2514 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x0C,tempah);
2518 if(SiS_Pr->ChipType >= SIS_315H) {
2520 #ifdef CONFIG_FB_SIS_315
2521 /* LVDS can only be slave in 8bpp modes */
2523 if((modeflag & CRT2Mode) && (SiS_Pr->SiS_ModeType > ModeVGA)) {
2524 if(SiS_Pr->SiS_VBInfo & DriverMode) {
2529 if(!(SiS_Pr->SiS_VBInfo & SetInSlaveMode)) tempah |= 0x02;
2531 if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) tempah ^= 0x01;
2533 if(SiS_Pr->SiS_VBInfo & DisableCRT2Display) tempah = 1;
2535 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x2e,0xF0,tempah);
2540 #ifdef CONFIG_FB_SIS_300
2542 if( (!(SiS_Pr->SiS_VBInfo & SetInSlaveMode)) && (SiS_Pr->SiS_ModeType > ModeVGA) ) {
2547 if(SiS_Pr->SiS_VBInfo & DisableCRT2Display) tempah = 0;
2549 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x01,tempah);
2558 if(SiS_Pr->SiS_VBType & VB_SISVB) {
2560 if(SiS_Pr->ChipType >= SIS_315H) {
2562 #ifdef CONFIG_FB_SIS_315
2563 /* unsigned char bridgerev = SiS_GetReg(SiS_Pr->SiS_Part4Port,0x01); */
2565 /* The following is nearly unpreditable and varies from machine
2566 * to machine. Especially the 301DH seems to be a real trouble
2567 * maker. Some BIOSes simply set the registers (like in the
2568 * NoLCD-if-statements here), some set them according to the
2569 * LCDA stuff. It is very likely that some machines are not
2570 * treated correctly in the following, very case-orientated
2571 * code. What do I do then...?
2574 /* 740 variants match for 30xB, 301B-DH, 30xLV */
2577 tempah = 0x04; /* For all bridges */
2579 if(!(SiS_Pr->SiS_VBInfo & SetCRT2ToLCDA)) {
2581 if(SiS_IsDualEdge(SiS_Pr)) {
2585 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x13,tempbl,tempah);
2588 /* The following two are responsible for eventually wrong colors
2589 * in TV output. The DH (VB_NoLCD) conditions are unknown; the
2590 * b0 was found in some 651 machine (Pim; P4_23=0xe5); the b1 version
2591 * in a 650 box (Jake). What is the criteria?
2592 * Addendum: Another combination 651+301B-DH(b1) (Rapo) needs same
2593 * treatment like the 651+301B-DH(b0) case. Seems more to be the
2594 * chipset than the bridge revision.
2597 if((IS_SIS740) || (SiS_Pr->ChipType >= SIS_661) || (SiS_Pr->SiS_ROMNew)) {
2600 if((SiS_Pr->SiS_VBInfo & DisableCRT2Display) ||
2601 ((SiS_Pr->SiS_ROMNew) && (!(ROMAddr[0x5b] & 0x04)))) {
2605 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x2c,0xcf,tempah);
2606 SiS_SetRegANDOR(SiS_Pr->SiS_Part4Port,0x21,0x3f,tempbl);
2607 } else if(SiS_Pr->SiS_VBType & VB_SIS301) {
2608 /* Fixes "TV-blue-bug" on 315+301 */
2609 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x2c,0xcf); /* For 301 */
2610 SiS_SetRegAND(SiS_Pr->SiS_Part4Port,0x21,0x3f);
2611 } else if(SiS_Pr->SiS_VBType & VB_SISLVDS) {
2612 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x2c,0x30); /* For 30xLV */
2613 SiS_SetRegOR(SiS_Pr->SiS_Part4Port,0x21,0xc0);
2614 } else if(SiS_Pr->SiS_VBType & VB_NoLCD) { /* For 301B-DH */
2615 tempah = 0x30; tempah2 = 0xc0;
2616 tempbl = 0xcf; tempbl2 = 0x3f;
2617 if(SiS_Pr->SiS_TVBlue == 0) {
2618 tempah = tempah2 = 0x00;
2619 } else if(SiS_Pr->SiS_TVBlue == -1) {
2620 /* Set on 651/M650, clear on 315/650 */
2621 if(!(IS_SIS65x)) /* (bridgerev != 0xb0) */ {
2622 tempah = tempah2 = 0x00;
2625 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x2c,tempbl,tempah);
2626 SiS_SetRegANDOR(SiS_Pr->SiS_Part4Port,0x21,tempbl2,tempah2);
2628 tempah = 0x30; tempah2 = 0xc0; /* For 30xB, 301C */
2629 tempbl = 0xcf; tempbl2 = 0x3f;
2630 if(!(SiS_Pr->SiS_VBInfo & SetCRT2ToLCDA)) {
2631 tempah = tempah2 = 0x00;
2632 if(SiS_IsDualEdge(SiS_Pr)) {
2633 tempbl = tempbl2 = 0xff;
2636 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x2c,tempbl,tempah);
2637 SiS_SetRegANDOR(SiS_Pr->SiS_Part4Port,0x21,tempbl2,tempah2);
2642 if(SiS_Pr->SiS_VBInfo & DisableCRT2Display) tempah = 0x00;
2643 SiS_SetRegANDOR(SiS_Pr->SiS_Part4Port,0x23,0x7f,tempah);
2647 if(!(SiS_Pr->SiS_VBInfo & SetCRT2ToLCDA)) {
2649 if(!(SiS_IsDualEdge(SiS_Pr))) tempah = 0x80;
2651 SiS_SetRegANDOR(SiS_Pr->SiS_Part4Port,0x23,tempbl,tempah);
2654 #endif /* CONFIG_FB_SIS_315 */
2656 } else if(SiS_Pr->SiS_VBType & VB_SIS30xBLV) {
2658 #ifdef CONFIG_FB_SIS_300
2659 SiS_SetRegAND(SiS_Pr->SiS_Part4Port,0x21,0x3f);
2661 if((SiS_Pr->SiS_VBInfo & DisableCRT2Display) ||
2662 ((SiS_Pr->SiS_VBType & VB_NoLCD) &&
2663 (SiS_Pr->SiS_VBInfo & SetCRT2ToLCD))) {
2664 SiS_SetRegAND(SiS_Pr->SiS_Part4Port,0x23,0x7F);
2666 SiS_SetRegOR(SiS_Pr->SiS_Part4Port,0x23,0x80);
2672 if(SiS_Pr->SiS_VBType & VB_SIS30xBLV) {
2673 SiS_SetRegOR(SiS_Pr->SiS_Part4Port,0x0D,0x80);
2674 if(SiS_Pr->SiS_VBType & VB_SIS30xCLV) {
2675 SiS_SetRegOR(SiS_Pr->SiS_Part4Port,0x3A,0xC0);
2681 #ifdef CONFIG_FB_SIS_315
2682 if(SiS_Pr->ChipType >= SIS_315H) {
2684 if(SiS_Pr->SiS_IF_DEF_CH70xx != 0) {
2688 if(!(SiS_Pr->SiS_VBInfo & SetCRT2ToLCDA)) {
2690 if(SiS_IsDualEdge(SiS_Pr)) tempbl = 0xff;
2692 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x13,tempbl,tempah);
2694 if(SiS_Pr->SiS_VBInfo & DisableCRT2Display) {
2695 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x13,0xfb);
2698 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x2c,0x30);
2700 } else if(SiS_Pr->ChipType == SIS_550) {
2702 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x13,0xfb);
2703 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x2c,0x30);
2714 /*********************************************/
2715 /* GET RESOLUTION DATA */
2716 /*********************************************/
2719 SiS_GetResInfo(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex)
2722 return ((unsigned short)SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_ResInfo);
2724 return ((unsigned short)SiS_Pr->SiS_EModeIDTable[ModeIdIndex].Ext_RESINFO);
2728 SiS_GetCRT2ResInfo(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex)
2730 unsigned short xres, yres, modeflag=0, resindex;
2732 if(SiS_Pr->UseCustomMode) {
2733 xres = SiS_Pr->CHDisplay;
2734 if(SiS_Pr->CModeFlag & HalfDCLK) xres <<= 1;
2735 SiS_Pr->SiS_VGAHDE = SiS_Pr->SiS_HDE = xres;
2736 /* DoubleScanMode-check done in CheckCalcCustomMode()! */
2737 SiS_Pr->SiS_VGAVDE = SiS_Pr->SiS_VDE = SiS_Pr->CVDisplay;
2741 resindex = SiS_GetResInfo(SiS_Pr,ModeNo,ModeIdIndex);
2743 if(ModeNo <= 0x13) {
2744 xres = SiS_Pr->SiS_StResInfo[resindex].HTotal;
2745 yres = SiS_Pr->SiS_StResInfo[resindex].VTotal;
2747 xres = SiS_Pr->SiS_ModeResInfo[resindex].HTotal;
2748 yres = SiS_Pr->SiS_ModeResInfo[resindex].VTotal;
2749 modeflag = SiS_Pr->SiS_EModeIDTable[ModeIdIndex].Ext_ModeFlag;
2752 if(!SiS_Pr->SiS_IF_DEF_DSTN && !SiS_Pr->SiS_IF_DEF_FSTN) {
2754 if((SiS_Pr->ChipType >= SIS_315H) && (SiS_Pr->SiS_IF_DEF_LVDS == 1)) {
2755 if((ModeNo != 0x03) && (SiS_Pr->SiS_SetFlag & SetDOSMode)) {
2756 if(yres == 350) yres = 400;
2758 if(SiS_GetReg(SiS_Pr->SiS_P3d4,0x3a) & 0x01) {
2759 if(ModeNo == 0x12) yres = 400;
2763 if(modeflag & HalfDCLK) xres <<= 1;
2764 if(modeflag & DoubleScanMode) yres <<= 1;
2768 if((SiS_Pr->SiS_VBType & VB_SISVB) && (!(SiS_Pr->SiS_VBType & VB_NoLCD))) {
2770 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) {
2771 switch(SiS_Pr->SiS_LCDResInfo) {
2772 case Panel_1024x768:
2773 if(!(SiS_Pr->SiS_SetFlag & LCDVESATiming)) {
2774 if(!(SiS_Pr->SiS_LCDInfo & DontExpandLCD)) {
2775 if(yres == 350) yres = 357;
2776 if(yres == 400) yres = 420;
2777 if(yres == 480) yres = 525;
2781 case Panel_1280x1024:
2782 if(!(SiS_Pr->SiS_LCDInfo & DontExpandLCD)) {
2783 /* BIOS bug - does this regardless of scaling */
2784 if(yres == 400) yres = 405;
2786 if(yres == 350) yres = 360;
2787 if(SiS_Pr->SiS_SetFlag & LCDVESATiming) {
2788 if(yres == 360) yres = 375;
2791 case Panel_1600x1200:
2792 if(!(SiS_Pr->SiS_SetFlag & LCDVESATiming)) {
2793 if(yres == 1024) yres = 1056;
2801 if(SiS_Pr->SiS_VBType & VB_SISVB) {
2802 if(SiS_Pr->SiS_VBInfo & (SetCRT2ToLCD | SetCRT2ToHiVision)) {
2803 if(xres == 720) xres = 640;
2805 } else if(xres == 720) xres = 640;
2807 if(SiS_Pr->SiS_SetFlag & SetDOSMode) {
2809 if(SiS_Pr->ChipType >= SIS_315H) {
2810 if(SiS_GetReg(SiS_Pr->SiS_P3c4,0x17) & 0x80) yres = 480;
2812 if(SiS_GetReg(SiS_Pr->SiS_P3c4,0x13) & 0x80) yres = 480;
2814 if(SiS_Pr->SiS_IF_DEF_DSTN || SiS_Pr->SiS_IF_DEF_FSTN) yres = 480;
2818 SiS_Pr->SiS_VGAHDE = SiS_Pr->SiS_HDE = xres;
2819 SiS_Pr->SiS_VGAVDE = SiS_Pr->SiS_VDE = yres;
2822 /*********************************************/
2823 /* GET CRT2 TIMING DATA */
2824 /*********************************************/
2827 SiS_GetCRT2Ptr(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex,
2828 unsigned short RefreshRateTableIndex, unsigned short *CRT2Index,
2829 unsigned short *ResIndex)
2831 unsigned short tempbx=0, tempal=0, resinfo=0;
2833 if(ModeNo <= 0x13) {
2834 tempal = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_CRT2CRTC;
2836 tempal = SiS_Pr->SiS_RefIndex[RefreshRateTableIndex].Ext_CRT2CRTC;
2837 resinfo = SiS_Pr->SiS_EModeIDTable[ModeIdIndex].Ext_RESINFO;
2840 if((SiS_Pr->SiS_VBType & VB_SISVB) && (SiS_Pr->SiS_IF_DEF_LVDS == 0)) {
2842 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) { /* LCD */
2844 tempbx = SiS_Pr->SiS_LCDResInfo;
2845 if(!(SiS_Pr->SiS_SetFlag & LCDVESATiming)) tempbx += 32;
2848 if(SiS_Pr->SiS_LCDResInfo == Panel_1680x1050) {
2849 if (resinfo == SIS_RI_1280x800) tempal = 9;
2850 else if(resinfo == SIS_RI_1400x1050) tempal = 11;
2851 } else if((SiS_Pr->SiS_LCDResInfo == Panel_1280x800) ||
2852 (SiS_Pr->SiS_LCDResInfo == Panel_1280x800_2) ||
2853 (SiS_Pr->SiS_LCDResInfo == Panel_1280x854)) {
2854 if (resinfo == SIS_RI_1280x768) tempal = 9;
2857 if(SiS_Pr->SiS_LCDInfo & DontExpandLCD) {
2858 /* Pass 1:1 only (center-screen handled outside) */
2859 /* This is never called for the panel's native resolution */
2860 /* since Pass1:1 will not be set in this case */
2862 if(ModeNo >= 0x13) {
2863 tempal = SiS_Pr->SiS_RefIndex[RefreshRateTableIndex].Ext_CRT2CRTC_NS;
2867 #ifdef CONFIG_FB_SIS_315
2868 if(SiS_Pr->SiS_CustomT == CUT_COMPAQ1280) {
2869 if(SiS_Pr->SiS_LCDResInfo == Panel_1280x1024) {
2870 if(!(SiS_Pr->SiS_LCDInfo & DontExpandLCD)) {
2872 if(!(SiS_Pr->SiS_SetFlag & LCDVESATiming)) tempbx++;
2880 if(SiS_Pr->SiS_VBInfo & SetCRT2ToHiVision) {
2881 /* if(SiS_Pr->SiS_VGAVDE > 480) SiS_Pr->SiS_TVMode &= (~TVSetTVSimuMode); */
2883 if(SiS_Pr->SiS_VBInfo & SetInSlaveMode) {
2885 if(!(SiS_Pr->SiS_TVMode & TVSetTVSimuMode)) tempbx = 14;
2887 } else if(SiS_Pr->SiS_VBInfo & SetCRT2ToYPbPr525750) {
2888 if(SiS_Pr->SiS_TVMode & TVSetYPbPr750p) tempbx = 7;
2889 else if(SiS_Pr->SiS_TVMode & TVSetYPbPr525p) tempbx = 6;
2891 if(SiS_Pr->SiS_TVMode & TVSetTVSimuMode) tempbx += 5;
2893 if(SiS_Pr->SiS_TVMode & TVSetPAL) tempbx = 3;
2895 if(SiS_Pr->SiS_TVMode & TVSetTVSimuMode) tempbx += 5;
2903 if(SiS_Pr->SiS_VBInfo & SetCRT2ToTVNoHiVision) {
2905 case SIS_RI_720x480:
2907 if(SiS_Pr->SiS_TVMode & (TVSetPAL | TVSetPALN)) tempal = 9;
2909 case SIS_RI_720x576:
2910 case SIS_RI_768x576:
2911 case SIS_RI_1024x576: /* Not in NTSC or YPBPR mode (except 1080i)! */
2913 if(SiS_Pr->SiS_VBInfo & SetCRT2ToYPbPr525750) {
2914 if(SiS_Pr->SiS_TVMode & TVSetYPbPr750p) tempal = 8;
2917 case SIS_RI_800x480:
2920 case SIS_RI_512x384:
2921 case SIS_RI_1024x768:
2923 if(SiS_Pr->SiS_VBInfo & SetCRT2ToYPbPr525750) {
2924 if(SiS_Pr->SiS_TVMode & TVSetYPbPr525p) tempal = 8;
2927 case SIS_RI_1280x720:
2928 if(SiS_Pr->SiS_VBInfo & SetCRT2ToYPbPr525750) {
2929 if(SiS_Pr->SiS_TVMode & TVSetYPbPr750p) tempal = 9;
2936 *CRT2Index = tempbx;
2939 } else { /* LVDS, 301B-DH (if running on LCD) */
2942 if((SiS_Pr->SiS_IF_DEF_CH70xx) && (SiS_Pr->SiS_VBInfo & SetCRT2ToTV)) {
2945 if(SiS_Pr->SiS_TVMode & TVSetPAL) {
2947 if(SiS_Pr->SiS_ModeType > ModeVGA) {
2948 if(SiS_Pr->SiS_CHSOverScan) tempbx = 99;
2950 if(SiS_Pr->SiS_TVMode & TVSetPALM) tempbx = 94;
2951 else if(SiS_Pr->SiS_TVMode & TVSetPALN) tempbx = 96;
2954 if(SiS_Pr->SiS_TVMode & TVSetCHOverScan) tempbx++;
2959 switch(SiS_Pr->SiS_LCDResInfo) {
2960 case Panel_640x480: tempbx = 12; break;
2961 case Panel_320x240_1: tempbx = 10; break;
2962 case Panel_320x240_2:
2963 case Panel_320x240_3: tempbx = 14; break;
2964 case Panel_800x600: tempbx = 16; break;
2965 case Panel_1024x600: tempbx = 18; break;
2966 case Panel_1152x768:
2967 case Panel_1024x768: tempbx = 20; break;
2968 case Panel_1280x768: tempbx = 22; break;
2969 case Panel_1280x1024: tempbx = 24; break;
2970 case Panel_1400x1050: tempbx = 26; break;
2971 case Panel_1600x1200: tempbx = 28; break;
2972 #ifdef CONFIG_FB_SIS_300
2973 case Panel_Barco1366: tempbx = 80; break;
2977 switch(SiS_Pr->SiS_LCDResInfo) {
2978 case Panel_320x240_1:
2979 case Panel_320x240_2:
2980 case Panel_320x240_3:
2984 if(SiS_Pr->SiS_LCDInfo & DontExpandLCD) tempbx++;
2987 if(SiS_Pr->SiS_LCDInfo & LCDPass11) tempbx = 30;
2989 #ifdef CONFIG_FB_SIS_300
2990 if(SiS_Pr->SiS_CustomT == CUT_BARCO1024) {
2992 if(SiS_Pr->SiS_LCDInfo & DontExpandLCD) tempbx++;
2993 } else if(SiS_Pr->SiS_CustomT == CUT_PANEL848 || SiS_Pr->SiS_CustomT == CUT_PANEL856) {
2995 if(SiS_Pr->SiS_LCDInfo & DontExpandLCD) tempbx++;
3001 (*CRT2Index) = tempbx;
3002 (*ResIndex) = tempal & 0x1F;
3007 SiS_GetRAMDAC2DATA(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex,
3008 unsigned short RefreshRateTableIndex)
3010 unsigned short tempax=0, tempbx=0, index, dotclock;
3011 unsigned short temp1=0, modeflag=0, tempcx=0;
3013 SiS_Pr->SiS_RVBHCMAX = 1;
3014 SiS_Pr->SiS_RVBHCFACT = 1;
3016 if(ModeNo <= 0x13) {
3018 modeflag = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_ModeFlag;
3019 index = SiS_GetModePtr(SiS_Pr,ModeNo,ModeIdIndex);
3021 tempax = SiS_Pr->SiS_StandTable[index].CRTC[0];
3022 tempbx = SiS_Pr->SiS_StandTable[index].CRTC[6];
3023 temp1 = SiS_Pr->SiS_StandTable[index].CRTC[7];
3025 dotclock = (modeflag & Charx8Dot) ? 8 : 9;
3029 modeflag = SiS_Pr->SiS_EModeIDTable[ModeIdIndex].Ext_ModeFlag;
3030 index = SiS_GetRefCRT1CRTC(SiS_Pr, RefreshRateTableIndex, SiS_Pr->SiS_UseWideCRT2);
3032 tempax = SiS_Pr->SiS_CRT1Table[index].CR[0];
3033 tempax |= (SiS_Pr->SiS_CRT1Table[index].CR[14] << 8);
3035 tempbx = SiS_Pr->SiS_CRT1Table[index].CR[6];
3036 tempcx = SiS_Pr->SiS_CRT1Table[index].CR[13] << 8;
3040 temp1 = SiS_Pr->SiS_CRT1Table[index].CR[7];
3046 if(temp1 & 0x01) tempbx |= 0x0100;
3047 if(temp1 & 0x20) tempbx |= 0x0200;
3051 if(modeflag & HalfDCLK) tempax <<= 1;
3055 SiS_Pr->SiS_VGAHT = SiS_Pr->SiS_HT = tempax;
3056 SiS_Pr->SiS_VGAVT = SiS_Pr->SiS_VT = tempbx;
3060 SiS_CalcPanelLinkTiming(struct SiS_Private *SiS_Pr, unsigned short ModeNo,
3061 unsigned short ModeIdIndex, unsigned short RefreshRateTableIndex)
3063 unsigned short ResIndex;
3065 if(SiS_Pr->SiS_LCDInfo & DontExpandLCD) {
3066 if(SiS_Pr->SiS_LCDInfo & LCDPass11) {
3067 if(SiS_Pr->UseCustomMode) {
3068 ResIndex = SiS_Pr->CHTotal;
3069 if(SiS_Pr->CModeFlag & HalfDCLK) ResIndex <<= 1;
3070 SiS_Pr->SiS_VGAHT = SiS_Pr->SiS_HT = ResIndex;
3071 SiS_Pr->SiS_VGAVT = SiS_Pr->SiS_VT = SiS_Pr->CVTotal;
3074 ResIndex = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_CRT2CRTC;
3076 ResIndex = SiS_Pr->SiS_RefIndex[RefreshRateTableIndex].Ext_CRT2CRTC_NS;
3078 if(ResIndex == 0x09) {
3079 if(SiS_Pr->Alternate1600x1200) ResIndex = 0x20; /* 1600x1200 LCDA */
3080 else if(SiS_Pr->SiS_IF_DEF_LVDS == 1) ResIndex = 0x21; /* 1600x1200 LVDS */
3082 SiS_Pr->SiS_VGAHT = SiS_Pr->SiS_NoScaleData[ResIndex].VGAHT;
3083 SiS_Pr->SiS_VGAVT = SiS_Pr->SiS_NoScaleData[ResIndex].VGAVT;
3084 SiS_Pr->SiS_HT = SiS_Pr->SiS_NoScaleData[ResIndex].LCDHT;
3085 SiS_Pr->SiS_VT = SiS_Pr->SiS_NoScaleData[ResIndex].LCDVT;
3088 SiS_Pr->SiS_VGAHT = SiS_Pr->SiS_HT = SiS_Pr->PanelHT;
3089 SiS_Pr->SiS_VGAVT = SiS_Pr->SiS_VT = SiS_Pr->PanelVT;
3092 /* This handles custom modes and custom panels */
3093 SiS_Pr->SiS_HDE = SiS_Pr->PanelXRes;
3094 SiS_Pr->SiS_VDE = SiS_Pr->PanelYRes;
3095 SiS_Pr->SiS_HT = SiS_Pr->PanelHT;
3096 SiS_Pr->SiS_VT = SiS_Pr->PanelVT;
3097 SiS_Pr->SiS_VGAHT = SiS_Pr->PanelHT - (SiS_Pr->PanelXRes - SiS_Pr->SiS_VGAHDE);
3098 SiS_Pr->SiS_VGAVT = SiS_Pr->PanelVT - (SiS_Pr->PanelYRes - SiS_Pr->SiS_VGAVDE);
3103 SiS_GetCRT2DataLVDS(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex,
3104 unsigned short RefreshRateTableIndex)
3106 unsigned short CRT2Index, ResIndex, backup;
3107 const struct SiS_LVDSData *LVDSData = NULL;
3109 SiS_GetCRT2ResInfo(SiS_Pr, ModeNo, ModeIdIndex);
3111 if(SiS_Pr->SiS_VBType & VB_SISVB) {
3112 SiS_Pr->SiS_RVBHCMAX = 1;
3113 SiS_Pr->SiS_RVBHCFACT = 1;
3114 SiS_Pr->SiS_NewFlickerMode = 0;
3115 SiS_Pr->SiS_RVBHRS = 50;
3116 SiS_Pr->SiS_RY1COE = 0;
3117 SiS_Pr->SiS_RY2COE = 0;
3118 SiS_Pr->SiS_RY3COE = 0;
3119 SiS_Pr->SiS_RY4COE = 0;
3120 SiS_Pr->SiS_RVBHRS2 = 0;
3123 if((SiS_Pr->SiS_VBType & VB_SISVB) && (SiS_Pr->SiS_VBInfo & SetCRT2ToLCDA)) {
3125 #ifdef CONFIG_FB_SIS_315
3126 SiS_CalcPanelLinkTiming(SiS_Pr, ModeNo, ModeIdIndex, RefreshRateTableIndex);
3127 SiS_CalcLCDACRT1Timing(SiS_Pr, ModeNo, ModeIdIndex);
3132 /* 301BDH needs LVDS Data */
3133 backup = SiS_Pr->SiS_IF_DEF_LVDS;
3134 if((SiS_Pr->SiS_VBType & VB_NoLCD) && (SiS_Pr->SiS_VBInfo & SetCRT2ToLCD)) {
3135 SiS_Pr->SiS_IF_DEF_LVDS = 1;
3138 SiS_GetCRT2Ptr(SiS_Pr, ModeNo, ModeIdIndex, RefreshRateTableIndex,
3139 &CRT2Index, &ResIndex);
3141 SiS_Pr->SiS_IF_DEF_LVDS = backup;
3144 case 10: LVDSData = SiS_Pr->SiS_LVDS320x240Data_1; break;
3145 case 14: LVDSData = SiS_Pr->SiS_LVDS320x240Data_2; break;
3146 case 12: LVDSData = SiS_Pr->SiS_LVDS640x480Data_1; break;
3147 case 16: LVDSData = SiS_Pr->SiS_LVDS800x600Data_1; break;
3148 case 18: LVDSData = SiS_Pr->SiS_LVDS1024x600Data_1; break;
3149 case 20: LVDSData = SiS_Pr->SiS_LVDS1024x768Data_1; break;
3150 #ifdef CONFIG_FB_SIS_300
3151 case 80: LVDSData = SiS_Pr->SiS_LVDSBARCO1366Data_1; break;
3152 case 81: LVDSData = SiS_Pr->SiS_LVDSBARCO1366Data_2; break;
3153 case 82: LVDSData = SiS_Pr->SiS_LVDSBARCO1024Data_1; break;
3154 case 84: LVDSData = SiS_Pr->SiS_LVDS848x480Data_1; break;
3155 case 85: LVDSData = SiS_Pr->SiS_LVDS848x480Data_2; break;
3157 case 90: LVDSData = SiS_Pr->SiS_CHTVUNTSCData; break;
3158 case 91: LVDSData = SiS_Pr->SiS_CHTVONTSCData; break;
3159 case 92: LVDSData = SiS_Pr->SiS_CHTVUPALData; break;
3160 case 93: LVDSData = SiS_Pr->SiS_CHTVOPALData; break;
3161 case 94: LVDSData = SiS_Pr->SiS_CHTVUPALMData; break;
3162 case 95: LVDSData = SiS_Pr->SiS_CHTVOPALMData; break;
3163 case 96: LVDSData = SiS_Pr->SiS_CHTVUPALNData; break;
3164 case 97: LVDSData = SiS_Pr->SiS_CHTVOPALNData; break;
3165 case 99: LVDSData = SiS_Pr->SiS_CHTVSOPALData; break;
3169 SiS_Pr->SiS_VGAHT = (LVDSData+ResIndex)->VGAHT;
3170 SiS_Pr->SiS_VGAVT = (LVDSData+ResIndex)->VGAVT;
3171 SiS_Pr->SiS_HT = (LVDSData+ResIndex)->LCDHT;
3172 SiS_Pr->SiS_VT = (LVDSData+ResIndex)->LCDVT;
3174 SiS_CalcPanelLinkTiming(SiS_Pr, ModeNo, ModeIdIndex, RefreshRateTableIndex);
3177 if( (!(SiS_Pr->SiS_VBType & VB_SISVB)) &&
3178 (SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) &&
3179 (!(SiS_Pr->SiS_LCDInfo & LCDPass11)) ) {
3180 if( (!(SiS_Pr->SiS_LCDInfo & DontExpandLCD)) ||
3181 (SiS_Pr->SiS_SetFlag & SetDOSMode) ) {
3182 SiS_Pr->SiS_HDE = SiS_Pr->PanelXRes;
3183 SiS_Pr->SiS_VDE = SiS_Pr->PanelYRes;
3184 #ifdef CONFIG_FB_SIS_300
3185 if(SiS_Pr->SiS_CustomT == CUT_BARCO1366) {
3186 if(ResIndex < 0x08) {
3187 SiS_Pr->SiS_HDE = 1280;
3188 SiS_Pr->SiS_VDE = 1024;
3198 SiS_GetCRT2Data301(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex,
3199 unsigned short RefreshRateTableIndex)
3201 unsigned char *ROMAddr = NULL;
3202 unsigned short tempax, tempbx, modeflag, romptr=0;
3203 unsigned short resinfo, CRT2Index, ResIndex;
3204 const struct SiS_LCDData *LCDPtr = NULL;
3205 const struct SiS_TVData *TVPtr = NULL;
3206 #ifdef CONFIG_FB_SIS_315
3210 if(ModeNo <= 0x13) {
3211 modeflag = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_ModeFlag;
3212 resinfo = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_ResInfo;
3213 } else if(SiS_Pr->UseCustomMode) {
3214 modeflag = SiS_Pr->CModeFlag;
3217 modeflag = SiS_Pr->SiS_EModeIDTable[ModeIdIndex].Ext_ModeFlag;
3218 resinfo = SiS_Pr->SiS_EModeIDTable[ModeIdIndex].Ext_RESINFO;
3219 #ifdef CONFIG_FB_SIS_315
3220 resinfo661 = SiS_Pr->SiS_EModeIDTable[ModeIdIndex].ROMMODEIDX661;
3221 if( (SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) &&
3222 (SiS_Pr->SiS_SetFlag & LCDVESATiming) &&
3223 (resinfo661 >= 0) &&
3224 (SiS_Pr->SiS_NeedRomModeData) ) {
3225 if((ROMAddr = GetLCDStructPtr661(SiS_Pr))) {
3226 if((romptr = (SISGETROMW(21)))) {
3227 romptr += (resinfo661 * 10);
3228 ROMAddr = SiS_Pr->VirtualRomBase;
3235 SiS_Pr->SiS_NewFlickerMode = 0;
3236 SiS_Pr->SiS_RVBHRS = 50;
3237 SiS_Pr->SiS_RY1COE = 0;
3238 SiS_Pr->SiS_RY2COE = 0;
3239 SiS_Pr->SiS_RY3COE = 0;
3240 SiS_Pr->SiS_RY4COE = 0;
3241 SiS_Pr->SiS_RVBHRS2 = 0;
3243 SiS_GetCRT2ResInfo(SiS_Pr,ModeNo,ModeIdIndex);
3245 if(SiS_Pr->SiS_VBInfo & SetCRT2ToRAMDAC) {
3247 if(SiS_Pr->UseCustomMode) {
3249 SiS_Pr->SiS_RVBHCMAX = 1;
3250 SiS_Pr->SiS_RVBHCFACT = 1;
3251 SiS_Pr->SiS_HDE = SiS_Pr->SiS_VGAHDE;
3252 SiS_Pr->SiS_VDE = SiS_Pr->SiS_VGAVDE;
3254 tempax = SiS_Pr->CHTotal;
3255 if(modeflag & HalfDCLK) tempax <<= 1;
3256 SiS_Pr->SiS_VGAHT = SiS_Pr->SiS_HT = tempax;
3257 SiS_Pr->SiS_VGAVT = SiS_Pr->SiS_VT = SiS_Pr->CVTotal;
3261 SiS_GetRAMDAC2DATA(SiS_Pr, ModeNo, ModeIdIndex, RefreshRateTableIndex);
3265 } else if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) {
3267 SiS_GetCRT2Ptr(SiS_Pr,ModeNo,ModeIdIndex,RefreshRateTableIndex,
3268 &CRT2Index,&ResIndex);
3271 case 2: TVPtr = SiS_Pr->SiS_ExtHiTVData; break;
3272 case 3: TVPtr = SiS_Pr->SiS_ExtPALData; break;
3273 case 4: TVPtr = SiS_Pr->SiS_ExtNTSCData; break;
3274 case 5: TVPtr = SiS_Pr->SiS_Ext525iData; break;
3275 case 6: TVPtr = SiS_Pr->SiS_Ext525pData; break;
3276 case 7: TVPtr = SiS_Pr->SiS_Ext750pData; break;
3277 case 8: TVPtr = SiS_Pr->SiS_StPALData; break;
3278 case 9: TVPtr = SiS_Pr->SiS_StNTSCData; break;
3279 case 10: TVPtr = SiS_Pr->SiS_St525iData; break;
3280 case 11: TVPtr = SiS_Pr->SiS_St525pData; break;
3281 case 12: TVPtr = SiS_Pr->SiS_St750pData; break;
3282 case 13: TVPtr = SiS_Pr->SiS_St1HiTVData; break;
3283 case 14: TVPtr = SiS_Pr->SiS_St2HiTVData; break;
3284 default: TVPtr = SiS_Pr->SiS_StPALData; break;
3287 SiS_Pr->SiS_RVBHCMAX = (TVPtr+ResIndex)->RVBHCMAX;
3288 SiS_Pr->SiS_RVBHCFACT = (TVPtr+ResIndex)->RVBHCFACT;
3289 SiS_Pr->SiS_VGAHT = (TVPtr+ResIndex)->VGAHT;
3290 SiS_Pr->SiS_VGAVT = (TVPtr+ResIndex)->VGAVT;
3291 SiS_Pr->SiS_HDE = (TVPtr+ResIndex)->TVHDE;
3292 SiS_Pr->SiS_VDE = (TVPtr+ResIndex)->TVVDE;
3293 SiS_Pr->SiS_RVBHRS2 = (TVPtr+ResIndex)->RVBHRS2 & 0x0fff;
3294 if(modeflag & HalfDCLK) {
3295 SiS_Pr->SiS_RVBHRS = (TVPtr+ResIndex)->HALFRVBHRS;
3296 if(SiS_Pr->SiS_RVBHRS2) {
3297 SiS_Pr->SiS_RVBHRS2 = ((SiS_Pr->SiS_RVBHRS2 + 3) >> 1) - 3;
3298 tempax = ((TVPtr+ResIndex)->RVBHRS2 >> 12) & 0x07;
3299 if((TVPtr+ResIndex)->RVBHRS2 & 0x8000) SiS_Pr->SiS_RVBHRS2 -= tempax;
3300 else SiS_Pr->SiS_RVBHRS2 += tempax;
3303 SiS_Pr->SiS_RVBHRS = (TVPtr+ResIndex)->RVBHRS;
3305 SiS_Pr->SiS_NewFlickerMode = ((TVPtr+ResIndex)->FlickerMode) << 7;
3307 if(SiS_Pr->SiS_VBInfo & SetCRT2ToHiVision) {
3309 if((resinfo == SIS_RI_960x600) ||
3310 (resinfo == SIS_RI_1024x768) ||
3311 (resinfo == SIS_RI_1280x1024) ||
3312 (resinfo == SIS_RI_1280x720)) {
3313 SiS_Pr->SiS_NewFlickerMode = 0x40;
3316 if(SiS_Pr->SiS_VGAVDE == 350) SiS_Pr->SiS_TVMode |= TVSetTVSimuMode;
3318 SiS_Pr->SiS_HT = ExtHiTVHT;
3319 SiS_Pr->SiS_VT = ExtHiTVVT;
3320 if(SiS_Pr->SiS_VBInfo & SetInSlaveMode) {
3321 if(SiS_Pr->SiS_TVMode & TVSetTVSimuMode) {
3322 SiS_Pr->SiS_HT = StHiTVHT;
3323 SiS_Pr->SiS_VT = StHiTVVT;
3327 } else if(SiS_Pr->SiS_VBInfo & SetCRT2ToYPbPr525750) {
3329 if(SiS_Pr->SiS_TVMode & TVSetYPbPr750p) {
3330 SiS_Pr->SiS_HT = 1650;
3331 SiS_Pr->SiS_VT = 750;
3332 } else if(SiS_Pr->SiS_TVMode & TVSetYPbPr525p) {
3333 SiS_Pr->SiS_HT = NTSCHT;
3334 if(SiS_Pr->SiS_TVMode & TVSet525p1024) SiS_Pr->SiS_HT = NTSC2HT;
3335 SiS_Pr->SiS_VT = NTSCVT;
3337 SiS_Pr->SiS_HT = NTSCHT;
3338 if(SiS_Pr->SiS_TVMode & TVSetNTSC1024) SiS_Pr->SiS_HT = NTSC2HT;
3339 SiS_Pr->SiS_VT = NTSCVT;
3344 SiS_Pr->SiS_RY1COE = (TVPtr+ResIndex)->RY1COE;
3345 SiS_Pr->SiS_RY2COE = (TVPtr+ResIndex)->RY2COE;
3346 SiS_Pr->SiS_RY3COE = (TVPtr+ResIndex)->RY3COE;
3347 SiS_Pr->SiS_RY4COE = (TVPtr+ResIndex)->RY4COE;
3349 if(modeflag & HalfDCLK) {
3350 SiS_Pr->SiS_RY1COE = 0x00;
3351 SiS_Pr->SiS_RY2COE = 0xf4;
3352 SiS_Pr->SiS_RY3COE = 0x10;
3353 SiS_Pr->SiS_RY4COE = 0x38;
3356 if(!(SiS_Pr->SiS_TVMode & TVSetPAL)) {
3357 SiS_Pr->SiS_HT = NTSCHT;
3358 if(SiS_Pr->SiS_TVMode & TVSetNTSC1024) SiS_Pr->SiS_HT = NTSC2HT;
3359 SiS_Pr->SiS_VT = NTSCVT;
3361 SiS_Pr->SiS_HT = PALHT;
3362 SiS_Pr->SiS_VT = PALVT;
3367 } else if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) {
3369 SiS_Pr->SiS_RVBHCMAX = 1;
3370 SiS_Pr->SiS_RVBHCFACT = 1;
3372 if(SiS_Pr->UseCustomMode) {
3374 SiS_Pr->SiS_HDE = SiS_Pr->SiS_VGAHDE;
3375 SiS_Pr->SiS_VDE = SiS_Pr->SiS_VGAVDE;
3377 tempax = SiS_Pr->CHTotal;
3378 if(modeflag & HalfDCLK) tempax <<= 1;
3379 SiS_Pr->SiS_VGAHT = SiS_Pr->SiS_HT = tempax;
3380 SiS_Pr->SiS_VGAVT = SiS_Pr->SiS_VT = SiS_Pr->CVTotal;
3386 if((SiS_Pr->SiS_LCDInfo & DontExpandLCD) && (!(SiS_Pr->SiS_LCDInfo & LCDPass11))) {
3388 SiS_Pr->SiS_VGAHT = SiS_Pr->PanelHT;
3389 SiS_Pr->SiS_VGAVT = SiS_Pr->PanelVT;
3390 SiS_Pr->SiS_HT = SiS_Pr->PanelHT;
3391 SiS_Pr->SiS_VT = SiS_Pr->PanelVT;
3394 } else if( (!(SiS_Pr->SiS_LCDInfo & DontExpandLCD)) && (romptr) && (ROMAddr) ) {
3396 #ifdef CONFIG_FB_SIS_315
3397 SiS_Pr->SiS_RVBHCMAX = ROMAddr[romptr];
3398 SiS_Pr->SiS_RVBHCFACT = ROMAddr[romptr+1];
3399 SiS_Pr->SiS_VGAHT = ROMAddr[romptr+2] | ((ROMAddr[romptr+3] & 0x0f) << 8);
3400 SiS_Pr->SiS_VGAVT = (ROMAddr[romptr+4] << 4) | ((ROMAddr[romptr+3] & 0xf0) >> 4);
3401 SiS_Pr->SiS_HT = ROMAddr[romptr+5] | ((ROMAddr[romptr+6] & 0x0f) << 8);
3402 SiS_Pr->SiS_VT = (ROMAddr[romptr+7] << 4) | ((ROMAddr[romptr+6] & 0xf0) >> 4);
3403 SiS_Pr->SiS_RVBHRS2 = ROMAddr[romptr+8] | ((ROMAddr[romptr+9] & 0x0f) << 8);
3404 if((SiS_Pr->SiS_RVBHRS2) && (modeflag & HalfDCLK)) {
3405 SiS_Pr->SiS_RVBHRS2 = ((SiS_Pr->SiS_RVBHRS2 + 3) >> 1) - 3;
3406 tempax = (ROMAddr[romptr+9] >> 4) & 0x07;
3407 if(ROMAddr[romptr+9] & 0x80) SiS_Pr->SiS_RVBHRS2 -= tempax;
3408 else SiS_Pr->SiS_RVBHRS2 += tempax;
3410 if(SiS_Pr->SiS_VGAHT) gotit = true;
3412 SiS_Pr->SiS_LCDInfo |= DontExpandLCD;
3413 SiS_Pr->SiS_LCDInfo &= ~LCDPass11;
3414 SiS_Pr->SiS_RVBHCMAX = 1;
3415 SiS_Pr->SiS_RVBHCFACT = 1;
3416 SiS_Pr->SiS_VGAHT = SiS_Pr->PanelHT;
3417 SiS_Pr->SiS_VGAVT = SiS_Pr->PanelVT;
3418 SiS_Pr->SiS_HT = SiS_Pr->PanelHT;
3419 SiS_Pr->SiS_VT = SiS_Pr->PanelVT;
3420 SiS_Pr->SiS_RVBHRS2 = 0;
3429 SiS_GetCRT2Ptr(SiS_Pr,ModeNo,ModeIdIndex,RefreshRateTableIndex,
3430 &CRT2Index,&ResIndex);
3433 case Panel_1024x768 : LCDPtr = SiS_Pr->SiS_ExtLCD1024x768Data; break;
3434 case Panel_1024x768 + 32: LCDPtr = SiS_Pr->SiS_St2LCD1024x768Data; break;
3435 case Panel_1280x720 :
3436 case Panel_1280x720 + 32: LCDPtr = SiS_Pr->SiS_LCD1280x720Data; break;
3437 case Panel_1280x768_2 : LCDPtr = SiS_Pr->SiS_ExtLCD1280x768_2Data; break;
3438 case Panel_1280x768_2+ 32: LCDPtr = SiS_Pr->SiS_StLCD1280x768_2Data; break;
3439 case Panel_1280x800 :
3440 case Panel_1280x800 + 32: LCDPtr = SiS_Pr->SiS_LCD1280x800Data; break;
3441 case Panel_1280x800_2 :
3442 case Panel_1280x800_2+ 32: LCDPtr = SiS_Pr->SiS_LCD1280x800_2Data; break;
3443 case Panel_1280x854 :
3444 case Panel_1280x854 + 32: LCDPtr = SiS_Pr->SiS_LCD1280x854Data; break;
3445 case Panel_1280x960 :
3446 case Panel_1280x960 + 32: LCDPtr = SiS_Pr->SiS_LCD1280x960Data; break;
3447 case Panel_1280x1024 : LCDPtr = SiS_Pr->SiS_ExtLCD1280x1024Data; break;
3448 case Panel_1280x1024 + 32: LCDPtr = SiS_Pr->SiS_St2LCD1280x1024Data; break;
3449 case Panel_1400x1050 : LCDPtr = SiS_Pr->SiS_ExtLCD1400x1050Data; break;
3450 case Panel_1400x1050 + 32: LCDPtr = SiS_Pr->SiS_StLCD1400x1050Data; break;
3451 case Panel_1600x1200 : LCDPtr = SiS_Pr->SiS_ExtLCD1600x1200Data; break;
3452 case Panel_1600x1200 + 32: LCDPtr = SiS_Pr->SiS_StLCD1600x1200Data; break;
3453 case Panel_1680x1050 :
3454 case Panel_1680x1050 + 32: LCDPtr = SiS_Pr->SiS_LCD1680x1050Data; break;
3455 case 100 : LCDPtr = SiS_Pr->SiS_NoScaleData; break;
3456 #ifdef CONFIG_FB_SIS_315
3457 case 200 : LCDPtr = SiS310_ExtCompaq1280x1024Data; break;
3458 case 201 : LCDPtr = SiS_Pr->SiS_St2LCD1280x1024Data; break;
3460 default : LCDPtr = SiS_Pr->SiS_ExtLCD1024x768Data; break;
3463 SiS_Pr->SiS_RVBHCMAX = (LCDPtr+ResIndex)->RVBHCMAX;
3464 SiS_Pr->SiS_RVBHCFACT = (LCDPtr+ResIndex)->RVBHCFACT;
3465 SiS_Pr->SiS_VGAHT = (LCDPtr+ResIndex)->VGAHT;
3466 SiS_Pr->SiS_VGAVT = (LCDPtr+ResIndex)->VGAVT;
3467 SiS_Pr->SiS_HT = (LCDPtr+ResIndex)->LCDHT;
3468 SiS_Pr->SiS_VT = (LCDPtr+ResIndex)->LCDVT;
3472 tempax = SiS_Pr->PanelXRes;
3473 tempbx = SiS_Pr->PanelYRes;
3475 switch(SiS_Pr->SiS_LCDResInfo) {
3476 case Panel_1024x768:
3477 if(SiS_Pr->SiS_SetFlag & LCDVESATiming) {
3478 if(SiS_Pr->ChipType < SIS_315H) {
3479 if (SiS_Pr->SiS_VGAVDE == 350) tempbx = 560;
3480 else if(SiS_Pr->SiS_VGAVDE == 400) tempbx = 640;
3483 if (SiS_Pr->SiS_VGAVDE == 357) tempbx = 527;
3484 else if(SiS_Pr->SiS_VGAVDE == 420) tempbx = 620;
3485 else if(SiS_Pr->SiS_VGAVDE == 525) tempbx = 775;
3486 else if(SiS_Pr->SiS_VGAVDE == 600) tempbx = 775;
3487 else if(SiS_Pr->SiS_VGAVDE == 350) tempbx = 560;
3488 else if(SiS_Pr->SiS_VGAVDE == 400) tempbx = 640;
3491 case Panel_1280x960:
3492 if (SiS_Pr->SiS_VGAVDE == 350) tempbx = 700;
3493 else if(SiS_Pr->SiS_VGAVDE == 400) tempbx = 800;
3494 else if(SiS_Pr->SiS_VGAVDE == 1024) tempbx = 960;
3496 case Panel_1280x1024:
3497 if (SiS_Pr->SiS_VGAVDE == 360) tempbx = 768;
3498 else if(SiS_Pr->SiS_VGAVDE == 375) tempbx = 800;
3499 else if(SiS_Pr->SiS_VGAVDE == 405) tempbx = 864;
3501 case Panel_1600x1200:
3502 if(!(SiS_Pr->SiS_SetFlag & LCDVESATiming)) {
3503 if (SiS_Pr->SiS_VGAVDE == 350) tempbx = 875;
3504 else if(SiS_Pr->SiS_VGAVDE == 400) tempbx = 1000;
3509 if(SiS_Pr->SiS_LCDInfo & DontExpandLCD) {
3510 tempax = SiS_Pr->SiS_VGAHDE;
3511 tempbx = SiS_Pr->SiS_VGAVDE;
3514 SiS_Pr->SiS_HDE = tempax;
3515 SiS_Pr->SiS_VDE = tempbx;
3521 SiS_GetCRT2Data(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex,
3522 unsigned short RefreshRateTableIndex)
3525 if(SiS_Pr->SiS_VBType & VB_SISVB) {
3527 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCDA) {
3528 SiS_GetCRT2DataLVDS(SiS_Pr, ModeNo, ModeIdIndex, RefreshRateTableIndex);
3530 if((SiS_Pr->SiS_VBType & VB_NoLCD) && (SiS_Pr->SiS_VBInfo & SetCRT2ToLCD)) {
3531 /* Need LVDS Data for LCD on 301B-DH */
3532 SiS_GetCRT2DataLVDS(SiS_Pr, ModeNo, ModeIdIndex, RefreshRateTableIndex);
3534 SiS_GetCRT2Data301(SiS_Pr, ModeNo, ModeIdIndex, RefreshRateTableIndex);
3540 SiS_GetCRT2DataLVDS(SiS_Pr, ModeNo, ModeIdIndex, RefreshRateTableIndex);
3545 /*********************************************/
3546 /* GET LVDS DES (SKEW) DATA */
3547 /*********************************************/
3549 static const struct SiS_LVDSDes *
3550 SiS_GetLVDSDesPtr(struct SiS_Private *SiS_Pr)
3552 const struct SiS_LVDSDes *PanelDesPtr = NULL;
3554 #ifdef CONFIG_FB_SIS_300
3555 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) {
3557 if(SiS_Pr->ChipType < SIS_315H) {
3558 if(SiS_Pr->SiS_LCDTypeInfo == 4) {
3559 if(SiS_Pr->SiS_CustomT == CUT_BARCO1366) {
3560 PanelDesPtr = SiS_Pr->SiS_PanelType04_1a;
3561 if(SiS_Pr->SiS_LCDInfo & DontExpandLCD) {
3562 PanelDesPtr = SiS_Pr->SiS_PanelType04_2a;
3564 } else if(SiS_Pr->SiS_CustomT == CUT_BARCO1024) {
3565 PanelDesPtr = SiS_Pr->SiS_PanelType04_1b;
3566 if(SiS_Pr->SiS_LCDInfo & DontExpandLCD) {
3567 PanelDesPtr = SiS_Pr->SiS_PanelType04_2b;
3578 SiS_GetLVDSDesData(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex,
3579 unsigned short RefreshRateTableIndex)
3581 unsigned short modeflag, ResIndex;
3582 const struct SiS_LVDSDes *PanelDesPtr = NULL;
3584 SiS_Pr->SiS_LCDHDES = 0;
3585 SiS_Pr->SiS_LCDVDES = 0;
3587 /* Some special cases */
3588 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) {
3591 if(SiS_Pr->SiS_IF_DEF_TRUMPION) {
3592 if(SiS_Pr->SiS_LCDResInfo == Panel_1024x768) {
3593 if(SiS_Pr->SiS_VGAVDE == SiS_Pr->PanelYRes) {
3594 SiS_Pr->SiS_LCDVDES = SiS_Pr->PanelVT - 1;
3600 /* 640x480 on LVDS */
3601 if(SiS_Pr->ChipType < SIS_315H) {
3602 if(SiS_Pr->SiS_LCDResInfo == Panel_640x480 && SiS_Pr->SiS_LCDTypeInfo == 3) {
3603 SiS_Pr->SiS_LCDHDES = 8;
3604 if (SiS_Pr->SiS_VGAVDE >= 480) SiS_Pr->SiS_LCDVDES = 512;
3605 else if(SiS_Pr->SiS_VGAVDE >= 400) SiS_Pr->SiS_LCDVDES = 436;
3606 else if(SiS_Pr->SiS_VGAVDE >= 350) SiS_Pr->SiS_LCDVDES = 440;
3613 if( (SiS_Pr->UseCustomMode) ||
3614 (SiS_Pr->SiS_LCDResInfo == Panel_Custom) ||
3615 (SiS_Pr->SiS_CustomT == CUT_PANEL848) ||
3616 (SiS_Pr->SiS_CustomT == CUT_PANEL856) ||
3617 (SiS_Pr->SiS_LCDInfo & LCDPass11) ) {
3621 if(ModeNo <= 0x13) ResIndex = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_CRT2CRTC;
3622 else ResIndex = SiS_Pr->SiS_RefIndex[RefreshRateTableIndex].Ext_CRT2CRTC;
3624 if((SiS_Pr->SiS_VBType & VB_SIS30xBLV) && (SiS_Pr->SiS_VBInfo & SetCRT2ToLCDA)) {
3626 #ifdef CONFIG_FB_SIS_315
3627 if(SiS_Pr->SiS_LCDInfo & DontExpandLCD) {
3628 /* non-pass 1:1 only, see above */
3629 if(SiS_Pr->SiS_VGAHDE != SiS_Pr->PanelXRes) {
3630 SiS_Pr->SiS_LCDHDES = SiS_Pr->SiS_HT - ((SiS_Pr->PanelXRes - SiS_Pr->SiS_VGAHDE) / 2);
3632 if(SiS_Pr->SiS_VGAVDE != SiS_Pr->PanelYRes) {
3633 SiS_Pr->SiS_LCDVDES = SiS_Pr->SiS_VT - ((SiS_Pr->PanelYRes - SiS_Pr->SiS_VGAVDE) / 2);
3636 if(SiS_Pr->SiS_VGAVDE == SiS_Pr->PanelYRes) {
3637 switch(SiS_Pr->SiS_CustomT) {
3638 case CUT_UNIWILL1024:
3639 case CUT_UNIWILL10242:
3641 if(SiS_Pr->SiS_LCDResInfo == Panel_1024x768) {
3642 SiS_Pr->SiS_LCDVDES = SiS_Pr->PanelVT - 1;
3646 switch(SiS_Pr->SiS_LCDResInfo) {
3647 case Panel_1280x1024:
3648 if(SiS_Pr->SiS_CustomT != CUT_COMPAQ1280) {
3649 SiS_Pr->SiS_LCDVDES = SiS_Pr->PanelVT - 1;
3652 case Panel_1280x800: /* Verified for Averatec 6240 */
3653 case Panel_1280x800_2: /* Verified for Asus A4L */
3654 case Panel_1280x854: /* Not verified yet FIXME */
3655 SiS_Pr->SiS_LCDVDES = SiS_Pr->PanelVT - 1;
3663 if((SiS_Pr->SiS_IF_DEF_CH70xx != 0) && (SiS_Pr->SiS_VBInfo & SetCRT2ToTV)) {
3665 if((SiS_Pr->SiS_TVMode & TVSetPAL) && (!(SiS_Pr->SiS_TVMode & TVSetPALM))) {
3666 if(ResIndex <= 3) SiS_Pr->SiS_LCDHDES = 256;
3669 } else if((PanelDesPtr = SiS_GetLVDSDesPtr(SiS_Pr))) {
3671 SiS_Pr->SiS_LCDHDES = (PanelDesPtr+ResIndex)->LCDHDES;
3672 SiS_Pr->SiS_LCDVDES = (PanelDesPtr+ResIndex)->LCDVDES;
3674 } else if(SiS_Pr->SiS_LCDInfo & DontExpandLCD) {
3676 if(SiS_Pr->SiS_VGAHDE != SiS_Pr->PanelXRes) {
3677 SiS_Pr->SiS_LCDHDES = SiS_Pr->SiS_HT - ((SiS_Pr->PanelXRes - SiS_Pr->SiS_VGAHDE) / 2);
3679 if(SiS_Pr->SiS_VGAVDE != SiS_Pr->PanelYRes) {
3680 SiS_Pr->SiS_LCDVDES = SiS_Pr->SiS_VT - ((SiS_Pr->PanelYRes - SiS_Pr->SiS_VGAVDE) / 2);
3682 if(SiS_Pr->ChipType < SIS_315H) {
3683 SiS_Pr->SiS_LCDVDES = SiS_Pr->PanelVT - 1;
3685 switch(SiS_Pr->SiS_LCDResInfo) {
3687 case Panel_1024x768:
3688 case Panel_1280x1024:
3689 SiS_Pr->SiS_LCDVDES = SiS_Pr->PanelVT;
3691 case Panel_1400x1050:
3692 SiS_Pr->SiS_LCDVDES = SiS_Pr->PanelVT - 1;
3700 if(SiS_Pr->ChipType < SIS_315H) {
3701 #ifdef CONFIG_FB_SIS_300
3702 switch(SiS_Pr->SiS_LCDResInfo) {
3704 if(SiS_Pr->SiS_VGAVDE == SiS_Pr->PanelYRes) {
3705 SiS_Pr->SiS_LCDVDES = SiS_Pr->PanelVT - 1;
3707 SiS_Pr->SiS_LCDHDES = SiS_Pr->PanelHT + 3;
3708 SiS_Pr->SiS_LCDVDES = SiS_Pr->PanelVT;
3709 if(SiS_Pr->SiS_VGAVDE == 400) SiS_Pr->SiS_LCDVDES -= 2;
3710 else SiS_Pr->SiS_LCDVDES -= 4;
3713 case Panel_1024x768:
3714 if(SiS_Pr->SiS_VGAVDE == SiS_Pr->PanelYRes) {
3715 SiS_Pr->SiS_LCDVDES = SiS_Pr->PanelVT - 1;
3717 SiS_Pr->SiS_LCDHDES = SiS_Pr->PanelHT - 1;
3718 if(SiS_Pr->SiS_VGAVDE <= 400) SiS_Pr->SiS_LCDVDES = SiS_Pr->PanelVT - 8;
3719 if(SiS_Pr->SiS_VGAVDE <= 350) SiS_Pr->SiS_LCDVDES = SiS_Pr->PanelVT - 12;
3722 case Panel_1024x600:
3724 if( (SiS_Pr->SiS_VGAHDE == SiS_Pr->PanelXRes) &&
3725 (SiS_Pr->SiS_VGAVDE == SiS_Pr->PanelYRes) ) {
3726 SiS_Pr->SiS_LCDVDES = SiS_Pr->PanelVT - 1;
3728 SiS_Pr->SiS_LCDHDES = SiS_Pr->PanelHT - 1;
3733 switch(SiS_Pr->SiS_LCDTypeInfo) {
3735 SiS_Pr->SiS_LCDHDES = SiS_Pr->SiS_LCDVDES = 0;
3737 case 3: /* 640x480 only? */
3738 SiS_Pr->SiS_LCDHDES = 8;
3739 if (SiS_Pr->SiS_VGAVDE >= 480) SiS_Pr->SiS_LCDVDES = 512;
3740 else if(SiS_Pr->SiS_VGAVDE >= 400) SiS_Pr->SiS_LCDVDES = 436;
3741 else if(SiS_Pr->SiS_VGAVDE >= 350) SiS_Pr->SiS_LCDVDES = 440;
3746 #ifdef CONFIG_FB_SIS_315
3747 switch(SiS_Pr->SiS_LCDResInfo) {
3748 case Panel_1024x768:
3749 case Panel_1280x1024:
3750 if(SiS_Pr->SiS_VGAVDE == SiS_Pr->PanelYRes) {
3751 SiS_Pr->SiS_LCDVDES = SiS_Pr->PanelVT - 1;
3754 case Panel_320x240_1:
3755 case Panel_320x240_2:
3756 case Panel_320x240_3:
3757 SiS_Pr->SiS_LCDVDES = 524;
3764 if((ModeNo <= 0x13) && (SiS_Pr->SiS_LCDInfo & DontExpandLCD)) {
3765 modeflag = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_ModeFlag;
3766 if((SiS_Pr->SiS_VBType & VB_SIS30xBLV) && (SiS_Pr->SiS_VBInfo & SetCRT2ToLCDA)) {
3767 if(!(modeflag & HalfDCLK)) SiS_Pr->SiS_LCDHDES = 632;
3768 } else if(!(SiS_Pr->SiS_SetFlag & SetDOSMode)) {
3769 if(SiS_Pr->SiS_LCDResInfo != Panel_1280x1024) {
3770 if(SiS_Pr->SiS_LCDResInfo >= Panel_1024x768) {
3771 if(SiS_Pr->ChipType < SIS_315H) {
3772 if(!(modeflag & HalfDCLK)) SiS_Pr->SiS_LCDHDES = 320;
3774 #ifdef CONFIG_FB_SIS_315
3775 if(SiS_Pr->SiS_LCDResInfo == Panel_1024x768) SiS_Pr->SiS_LCDHDES = 480;
3776 if(SiS_Pr->SiS_LCDResInfo == Panel_1400x1050) SiS_Pr->SiS_LCDHDES = 804;
3777 if(SiS_Pr->SiS_LCDResInfo == Panel_1600x1200) SiS_Pr->SiS_LCDHDES = 704;
3778 if(!(modeflag & HalfDCLK)) {
3779 SiS_Pr->SiS_LCDHDES = 320;
3780 if(SiS_Pr->SiS_LCDResInfo == Panel_1400x1050) SiS_Pr->SiS_LCDHDES = 632;
3781 if(SiS_Pr->SiS_LCDResInfo == Panel_1600x1200) SiS_Pr->SiS_LCDHDES = 542;
3792 /*********************************************/
3793 /* DISABLE VIDEO BRIDGE */
3794 /*********************************************/
3796 #ifdef CONFIG_FB_SIS_315
3798 SiS_HandlePWD(struct SiS_Private *SiS_Pr)
3802 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
3803 unsigned short romptr = GetLCDStructPtr661_2(SiS_Pr);
3804 unsigned char drivermode = SiS_GetReg(SiS_Pr->SiS_P3d4,0x31) & 0x40;
3805 unsigned short temp;
3807 if( (SiS_Pr->SiS_VBType & VB_SISPWD) &&
3809 (SiS_Pr->SiS_PWDOffset) ) {
3810 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x2b,ROMAddr[romptr + SiS_Pr->SiS_PWDOffset + 0]);
3811 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x2c,ROMAddr[romptr + SiS_Pr->SiS_PWDOffset + 1]);
3812 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x2d,ROMAddr[romptr + SiS_Pr->SiS_PWDOffset + 2]);
3813 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x2e,ROMAddr[romptr + SiS_Pr->SiS_PWDOffset + 3]);
3814 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x2f,ROMAddr[romptr + SiS_Pr->SiS_PWDOffset + 4]);
3816 if((ROMAddr[romptr + 2] & (0x06 << 1)) && !drivermode) {
3820 SiS_SetRegANDOR(SiS_Pr->SiS_Part4Port,0x27,0x7f,temp);
3827 /* NEVER use any variables (VBInfo), this will be called
3828 * from outside the context of modeswitch!
3829 * MUST call getVBType before calling this
3832 SiS_DisableBridge(struct SiS_Private *SiS_Pr)
3834 #ifdef CONFIG_FB_SIS_315
3835 unsigned short tempah, pushax=0, modenum;
3837 unsigned short temp=0;
3839 if(SiS_Pr->SiS_VBType & VB_SISVB) {
3841 if(SiS_Pr->SiS_VBType & VB_SIS30xBLV) { /* ===== For 30xB/C/LV ===== */
3843 if(SiS_Pr->ChipType < SIS_315H) {
3845 #ifdef CONFIG_FB_SIS_300 /* 300 series */
3847 if(!(SiS_CR36BIOSWord23b(SiS_Pr))) {
3848 if(SiS_Pr->SiS_VBType & VB_SISLVDS) {
3849 SiS_SetRegAND(SiS_Pr->SiS_Part4Port,0x26,0xFE);
3851 SiS_SetRegSR11ANDOR(SiS_Pr,0xF7,0x08);
3853 SiS_PanelDelay(SiS_Pr, 3);
3855 if(SiS_Is301B(SiS_Pr)) {
3856 SiS_SetRegAND(SiS_Pr->SiS_Part4Port,0x1f,0x3f);
3857 SiS_ShortDelay(SiS_Pr,1);
3859 SiS_SetRegAND(SiS_Pr->SiS_Part2Port,0x00,0xDF);
3860 SiS_DisplayOff(SiS_Pr);
3861 SiS_SetRegAND(SiS_Pr->SiS_P3c4,0x32,0xDF);
3862 SiS_SetRegAND(SiS_Pr->SiS_P3c4,0x1E,0xDF);
3863 SiS_UnLockCRT2(SiS_Pr);
3864 if(!(SiS_Pr->SiS_VBType & VB_SISLVDS)) {
3865 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x01,0x80);
3866 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x02,0x40);
3868 if( (!(SiS_CRT2IsLCD(SiS_Pr))) ||
3869 (!(SiS_CR36BIOSWord23d(SiS_Pr))) ) {
3870 SiS_PanelDelay(SiS_Pr, 2);
3871 if(SiS_Pr->SiS_VBType & VB_SISLVDS) {
3872 SiS_SetRegAND(SiS_Pr->SiS_Part4Port,0x26,0xFD);
3874 SiS_SetRegSR11ANDOR(SiS_Pr,0xFB,0x04);
3878 #endif /* CONFIG_FB_SIS_300 */
3882 #ifdef CONFIG_FB_SIS_315 /* 315 series */
3885 bool custom1 = (SiS_Pr->SiS_CustomT == CUT_COMPAQ1280) ||
3886 (SiS_Pr->SiS_CustomT == CUT_CLEVO1400);
3888 modenum = SiS_GetReg(SiS_Pr->SiS_P3d4,0x34) & 0x7f;
3890 if(SiS_Pr->SiS_VBType & VB_SISLVDS) {
3893 if(SiS_Pr->SiS_VBType & VB_SISEMI) {
3894 if(SiS_Pr->SiS_CustomT != CUT_CLEVO1400) {
3895 SiS_SetRegAND(SiS_Pr->SiS_Part4Port,0x30,0x0c);
3900 didpwd = SiS_HandlePWD(SiS_Pr);
3902 if( (modenum <= 0x13) ||
3903 (SiS_IsVAMode(SiS_Pr)) ||
3904 (!(SiS_IsDualEdge(SiS_Pr))) ) {
3906 SiS_SetRegAND(SiS_Pr->SiS_Part4Port,0x26,0xfe);
3907 if(custom1) SiS_PanelDelay(SiS_Pr, 3);
3909 SiS_SetRegAND(SiS_Pr->SiS_Part4Port,0x26,0xfc);
3914 SiS_DDC2Delay(SiS_Pr,0xff00);
3915 SiS_DDC2Delay(SiS_Pr,0xe000);
3916 SiS_SetRegByte(SiS_Pr->SiS_P3c6,0x00);
3917 pushax = SiS_GetReg(SiS_Pr->SiS_P3c4,0x06);
3919 SiS_SetRegAND(SiS_Pr->SiS_P3c4,0x06,0xE3);
3921 SiS_PanelDelay(SiS_Pr, 3);
3926 if(!(SiS_IsNotM650orLater(SiS_Pr))) {
3927 /* if(SiS_Pr->ChipType < SIS_340) {*/
3929 if(SiS_IsVAMode(SiS_Pr)) tempah = 0xf7;
3930 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x4c,tempah);
3934 if(SiS_Pr->SiS_VBType & VB_SISLVDS) {
3935 SiS_SetRegAND(SiS_Pr->SiS_Part4Port,0x1F,~0x10);
3939 if(SiS_IsDualEdge(SiS_Pr)) {
3941 if(!(SiS_IsVAMode(SiS_Pr))) tempah = 0xbf;
3943 SiS_SetRegAND(SiS_Pr->SiS_Part4Port,0x1F,tempah);
3945 if((SiS_IsVAMode(SiS_Pr)) ||
3946 ((SiS_Pr->SiS_VBType & VB_SISLVDS) && (modenum <= 0x13))) {
3948 SiS_DisplayOff(SiS_Pr);
3949 if(SiS_Pr->SiS_VBType & VB_SISLVDS) {
3950 SiS_PanelDelay(SiS_Pr, 2);
3952 SiS_SetRegAND(SiS_Pr->SiS_P3c4,0x32,0xDF);
3953 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x1E,0xDF);
3957 if((!(SiS_IsVAMode(SiS_Pr))) ||
3958 ((SiS_Pr->SiS_VBType & VB_SISLVDS) && (modenum <= 0x13))) {
3960 if(!(SiS_IsDualEdge(SiS_Pr))) {
3961 SiS_SetRegAND(SiS_Pr->SiS_Part2Port,0x00,0xdf);
3962 SiS_DisplayOff(SiS_Pr);
3964 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x00,0x80);
3966 if(SiS_Pr->SiS_VBType & VB_SISLVDS) {
3967 SiS_PanelDelay(SiS_Pr, 2);
3970 SiS_SetRegAND(SiS_Pr->SiS_P3c4,0x32,0xDF);
3971 temp = SiS_GetReg(SiS_Pr->SiS_Part1Port,0x00);
3972 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x00,0x10);
3973 SiS_SetRegAND(SiS_Pr->SiS_P3c4,0x1E,0xDF);
3974 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x00,temp);
3978 if(SiS_IsNotM650orLater(SiS_Pr)) {
3979 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x2e,0x7f);
3982 if(SiS_Pr->SiS_VBType & VB_SISLVDS) {
3984 if( (!(SiS_IsVAMode(SiS_Pr))) &&
3985 (!(SiS_CRT2IsLCD(SiS_Pr))) &&
3986 (!(SiS_IsDualEdge(SiS_Pr))) ) {
3988 if(custom1) SiS_PanelDelay(SiS_Pr, 2);
3990 SiS_SetRegAND(SiS_Pr->SiS_Part4Port,0x26,0xFD);
3992 if(custom1) SiS_PanelDelay(SiS_Pr, 4);
3996 SiS_SetReg(SiS_Pr->SiS_P3c4,0x06,pushax);
3997 if(SiS_Pr->SiS_VBType & VB_SISEMI) {
3998 if(SiS_IsVAorLCD(SiS_Pr)) {
3999 SiS_PanelDelayLoop(SiS_Pr, 3, 20);
4006 #endif /* CONFIG_FB_SIS_315 */
4010 } else { /* ============ For 301 ================ */
4012 if(SiS_Pr->ChipType < SIS_315H) {
4013 #ifdef CONFIG_FB_SIS_300
4014 if(!(SiS_CR36BIOSWord23b(SiS_Pr))) {
4015 SiS_SetRegSR11ANDOR(SiS_Pr,0xF7,0x08);
4016 SiS_PanelDelay(SiS_Pr, 3);
4021 SiS_SetRegAND(SiS_Pr->SiS_Part2Port,0x00,0xDF); /* disable VB */
4022 SiS_DisplayOff(SiS_Pr);
4024 if(SiS_Pr->ChipType >= SIS_315H) {
4025 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x00,0x80);
4028 SiS_SetRegAND(SiS_Pr->SiS_P3c4,0x32,0xDF); /* disable lock mode */
4030 if(SiS_Pr->ChipType >= SIS_315H) {
4031 temp = SiS_GetReg(SiS_Pr->SiS_Part1Port,0x00);
4032 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x00,0x10);
4033 SiS_SetRegOR(SiS_Pr->SiS_P3c4,0x1E,0x20);
4034 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x00,temp);
4036 #ifdef CONFIG_FB_SIS_300
4037 SiS_SetRegAND(SiS_Pr->SiS_P3c4,0x1E,0xDF); /* disable CRT2 */
4038 if( (!(SiS_CRT2IsLCD(SiS_Pr))) ||
4039 (!(SiS_CR36BIOSWord23d(SiS_Pr))) ) {
4040 SiS_PanelDelay(SiS_Pr, 2);
4041 SiS_SetRegSR11ANDOR(SiS_Pr,0xFB,0x04);
4048 } else { /* ============ For LVDS =============*/
4050 if(SiS_Pr->ChipType < SIS_315H) {
4052 #ifdef CONFIG_FB_SIS_300 /* 300 series */
4054 if(SiS_Pr->SiS_IF_DEF_CH70xx == 1) {
4055 SiS_SetCH700x(SiS_Pr,0x0E,0x09);
4058 if(SiS_Pr->ChipType == SIS_730) {
4059 if(!(SiS_GetReg(SiS_Pr->SiS_P3c4,0x11) & 0x08)) {
4060 SiS_WaitVBRetrace(SiS_Pr);
4062 if(!(SiS_CR36BIOSWord23b(SiS_Pr))) {
4063 SiS_SetRegSR11ANDOR(SiS_Pr,0xF7,0x08);
4064 SiS_PanelDelay(SiS_Pr, 3);
4067 if(!(SiS_GetReg(SiS_Pr->SiS_P3c4,0x11) & 0x08)) {
4068 if(!(SiS_GetReg(SiS_Pr->SiS_P3c4,0x13) & 0x40)) {
4069 if(!(SiS_CR36BIOSWord23b(SiS_Pr))) {
4070 SiS_WaitVBRetrace(SiS_Pr);
4071 if(!(SiS_GetReg(SiS_Pr->SiS_P3c4,0x06) & 0x1c)) {
4072 SiS_DisplayOff(SiS_Pr);
4074 SiS_SetRegSR11ANDOR(SiS_Pr,0xF7,0x08);
4075 SiS_PanelDelay(SiS_Pr, 3);
4081 SiS_DisplayOff(SiS_Pr);
4083 SiS_SetRegAND(SiS_Pr->SiS_P3c4,0x32,0xDF);
4085 SiS_SetRegAND(SiS_Pr->SiS_P3c4,0x1E,0xDF);
4086 SiS_UnLockCRT2(SiS_Pr);
4087 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x01,0x80);
4088 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x02,0x40);
4090 if( (!(SiS_CRT2IsLCD(SiS_Pr))) ||
4091 (!(SiS_CR36BIOSWord23d(SiS_Pr))) ) {
4092 SiS_PanelDelay(SiS_Pr, 2);
4093 SiS_SetRegSR11ANDOR(SiS_Pr,0xFB,0x04);
4096 #endif /* CONFIG_FB_SIS_300 */
4100 #ifdef CONFIG_FB_SIS_315 /* 315 series */
4102 if(!(SiS_IsNotM650orLater(SiS_Pr))) {
4103 /*if(SiS_Pr->ChipType < SIS_340) { */ /* XGI needs this */
4104 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x4c,~0x18);
4108 if(SiS_Pr->SiS_IF_DEF_CH70xx != 0) {
4110 if(SiS_Pr->ChipType == SIS_740) {
4111 temp = SiS_GetCH701x(SiS_Pr,0x61);
4113 SiS_SetCH701x(SiS_Pr,0x76,0xac);
4114 SiS_SetCH701x(SiS_Pr,0x66,0x00);
4117 if( (!(SiS_IsDualEdge(SiS_Pr))) ||
4118 (SiS_IsTVOrYPbPrOrScart(SiS_Pr)) ) {
4119 SiS_SetCH701x(SiS_Pr,0x49,0x3e);
4123 if( (!(SiS_IsDualEdge(SiS_Pr))) ||
4124 (SiS_IsVAMode(SiS_Pr)) ) {
4125 SiS_Chrontel701xBLOff(SiS_Pr);
4126 SiS_Chrontel701xOff(SiS_Pr);
4129 if(SiS_Pr->ChipType != SIS_740) {
4130 if( (!(SiS_IsDualEdge(SiS_Pr))) ||
4131 (SiS_IsTVOrYPbPrOrScart(SiS_Pr)) ) {
4132 SiS_SetCH701x(SiS_Pr,0x49,0x01);
4138 if(SiS_Pr->SiS_IF_DEF_CH70xx == 0) {
4139 SiS_SetRegSR11ANDOR(SiS_Pr,0xF7,0x08);
4140 SiS_PanelDelay(SiS_Pr, 3);
4143 if( (SiS_Pr->SiS_IF_DEF_CH70xx == 0) ||
4144 (!(SiS_IsDualEdge(SiS_Pr))) ||
4145 (!(SiS_IsTVOrYPbPrOrScart(SiS_Pr))) ) {
4146 SiS_DisplayOff(SiS_Pr);
4149 if( (SiS_Pr->SiS_IF_DEF_CH70xx == 0) ||
4150 (!(SiS_IsDualEdge(SiS_Pr))) ||
4151 (!(SiS_IsVAMode(SiS_Pr))) ) {
4152 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x00,0x80);
4155 if(SiS_Pr->ChipType == SIS_740) {
4156 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x2e,0x7f);
4159 SiS_SetRegAND(SiS_Pr->SiS_P3c4,0x32,0xDF);
4161 if( (SiS_Pr->SiS_IF_DEF_CH70xx == 0) ||
4162 (!(SiS_IsDualEdge(SiS_Pr))) ||
4163 (!(SiS_IsVAMode(SiS_Pr))) ) {
4164 SiS_SetRegAND(SiS_Pr->SiS_P3c4,0x1E,0xDF);
4167 if(SiS_Pr->SiS_IF_DEF_CH70xx == 0) {
4168 if(SiS_CRT2IsLCD(SiS_Pr)) {
4169 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x1e,0xdf);
4170 if(SiS_Pr->ChipType == SIS_550) {
4171 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x1e,0xbf);
4172 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x1e,0xef);
4176 if(SiS_Pr->ChipType == SIS_740) {
4177 if(SiS_IsLCDOrLCDA(SiS_Pr)) {
4178 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x1e,0xdf);
4180 } else if(SiS_IsVAMode(SiS_Pr)) {
4181 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x1e,0xdf);
4185 if(SiS_Pr->SiS_IF_DEF_CH70xx != 0) {
4186 if(SiS_IsDualEdge(SiS_Pr)) {
4187 /* SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x13,0xff); */
4189 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x13,0xfb);
4193 SiS_UnLockCRT2(SiS_Pr);
4195 if(SiS_Pr->ChipType == SIS_550) {
4196 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x01,0x80); /* DirectDVD PAL?*/
4197 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x02,0x40); /* VB clock / 4 ? */
4198 } else if( (SiS_Pr->SiS_IF_DEF_CH70xx == 0) ||
4199 (!(SiS_IsDualEdge(SiS_Pr))) ||
4200 (!(SiS_IsVAMode(SiS_Pr))) ) {
4201 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x2e,0xf7);
4204 if(SiS_Pr->SiS_IF_DEF_CH70xx == 0) {
4205 if(SiS_CRT2IsLCD(SiS_Pr)) {
4206 if(!(SiS_WeHaveBacklightCtrl(SiS_Pr))) {
4207 SiS_PanelDelay(SiS_Pr, 2);
4208 SiS_SetRegSR11ANDOR(SiS_Pr,0xFB,0x04);
4213 #endif /* CONFIG_FB_SIS_315 */
4221 /*********************************************/
4222 /* ENABLE VIDEO BRIDGE */
4223 /*********************************************/
4225 /* NEVER use any variables (VBInfo), this will be called
4226 * from outside the context of a mode switch!
4227 * MUST call getVBType before calling this
4231 SiS_EnableBridge(struct SiS_Private *SiS_Pr)
4233 unsigned short temp=0, tempah;
4234 #ifdef CONFIG_FB_SIS_315
4235 unsigned short temp1, pushax=0;
4236 bool delaylong = false;
4239 if(SiS_Pr->SiS_VBType & VB_SISVB) {
4241 if(SiS_Pr->SiS_VBType & VB_SIS30xBLV) { /* ====== For 301B et al ====== */
4243 if(SiS_Pr->ChipType < SIS_315H) {
4245 #ifdef CONFIG_FB_SIS_300 /* 300 series */
4247 if(SiS_CRT2IsLCD(SiS_Pr)) {
4248 if(SiS_Pr->SiS_VBType & VB_SISLVDS) {
4249 SiS_SetRegOR(SiS_Pr->SiS_Part4Port,0x26,0x02);
4250 } else if(SiS_Pr->SiS_VBType & VB_NoLCD) {
4251 SiS_SetRegSR11ANDOR(SiS_Pr,0xFB,0x00);
4253 if(SiS_Pr->SiS_VBType & (VB_SISLVDS | VB_NoLCD)) {
4254 if(!(SiS_CR36BIOSWord23d(SiS_Pr))) {
4255 SiS_PanelDelay(SiS_Pr, 0);
4260 if((SiS_Pr->SiS_VBType & VB_NoLCD) &&
4261 (SiS_CRT2IsLCD(SiS_Pr))) {
4263 SiS_SetRegOR(SiS_Pr->SiS_P3c4,0x1E,0x20); /* Enable CRT2 */
4264 SiS_DisplayOn(SiS_Pr);
4265 SiS_UnLockCRT2(SiS_Pr);
4266 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x02,0xBF);
4267 if(SiS_BridgeInSlavemode(SiS_Pr)) {
4268 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x01,0x1F);
4270 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x01,0x1F,0x40);
4272 if(!(SiS_GetReg(SiS_Pr->SiS_P3c4,0x13) & 0x40)) {
4273 if(!(SiS_GetReg(SiS_Pr->SiS_P3c4,0x16) & 0x10)) {
4274 if(!(SiS_CR36BIOSWord23b(SiS_Pr))) {
4275 SiS_PanelDelay(SiS_Pr, 1);
4277 SiS_WaitVBRetrace(SiS_Pr);
4278 SiS_SetRegSR11ANDOR(SiS_Pr,0xF7,0x00);
4284 temp = SiS_GetReg(SiS_Pr->SiS_P3c4,0x32) & 0xDF; /* lock mode */
4285 if(SiS_BridgeInSlavemode(SiS_Pr)) {
4286 tempah = SiS_GetReg(SiS_Pr->SiS_P3d4,0x30);
4287 if(!(tempah & SetCRT2ToRAMDAC)) temp |= 0x20;
4289 SiS_SetReg(SiS_Pr->SiS_P3c4,0x32,temp);
4290 SiS_SetRegOR(SiS_Pr->SiS_P3c4,0x1E,0x20);
4291 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x00,0x1F,0x20); /* enable VB processor */
4292 SiS_SetRegOR(SiS_Pr->SiS_Part4Port,0x1F,0xC0);
4293 SiS_DisplayOn(SiS_Pr);
4294 if(SiS_Pr->SiS_VBType & VB_SISLVDS) {
4295 if(SiS_CRT2IsLCD(SiS_Pr)) {
4296 if(!(SiS_GetReg(SiS_Pr->SiS_P3c4,0x16) & 0x10)) {
4297 if(!(SiS_CR36BIOSWord23b(SiS_Pr))) {
4298 SiS_PanelDelay(SiS_Pr, 1);
4300 SiS_SetRegOR(SiS_Pr->SiS_Part4Port,0x26,0x01);
4308 #endif /* CONFIG_FB_SIS_300 */
4312 #ifdef CONFIG_FB_SIS_315 /* 315 series */
4315 unsigned char r30=0, r31=0, r32=0, r33=0, cr36=0;
4317 /* unsigned short emidelay=0; */
4320 if(SiS_Pr->SiS_VBType & VB_SISLVDS) {
4321 SiS_SetRegAND(SiS_Pr->SiS_Part4Port,0x1f,0xef);
4323 if(SiS_Pr->SiS_VBType & VB_SISEMI) {
4324 SiS_SetRegAND(SiS_Pr->SiS_Part4Port,0x30,0x0c);
4329 if(!(SiS_IsNotM650orLater(SiS_Pr))) {
4330 /*if(SiS_Pr->ChipType < SIS_340) { */
4332 if(SiS_LCDAEnabled(SiS_Pr)) {
4333 if(SiS_TVEnabled(SiS_Pr)) tempah = 0x18;
4336 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x4c,tempah);
4340 if(SiS_Pr->SiS_VBType & VB_SISLVDS) {
4342 SiS_SetRegByte(SiS_Pr->SiS_P3c6,0x00);
4343 SiS_DisplayOff(SiS_Pr);
4344 pushax = SiS_GetReg(SiS_Pr->SiS_P3c4,0x06);
4346 SiS_SetRegAND(SiS_Pr->SiS_P3c4,0x06,0xE3);
4349 didpwd = SiS_HandlePWD(SiS_Pr);
4351 if(SiS_IsVAorLCD(SiS_Pr)) {
4353 if(!(SiS_GetReg(SiS_Pr->SiS_Part4Port,0x26) & 0x02)) {
4354 SiS_PanelDelayLoop(SiS_Pr, 3, 2);
4355 SiS_SetRegOR(SiS_Pr->SiS_Part4Port,0x26,0x02);
4356 SiS_PanelDelayLoop(SiS_Pr, 3, 2);
4357 if(SiS_Pr->SiS_VBType & VB_SISEMI) {
4358 SiS_GenericDelay(SiS_Pr, 17664);
4362 SiS_PanelDelayLoop(SiS_Pr, 3, 2);
4363 if(SiS_Pr->SiS_VBType & VB_SISEMI) {
4364 SiS_GenericDelay(SiS_Pr, 17664);
4369 if(!(SiS_GetReg(SiS_Pr->SiS_P3d4,0x31) & 0x40)) {
4370 SiS_PanelDelayLoop(SiS_Pr, 3, 10);
4376 if(!(SiS_IsVAMode(SiS_Pr))) {
4378 temp = SiS_GetReg(SiS_Pr->SiS_P3c4,0x32) & 0xDF;
4379 if(SiS_BridgeInSlavemode(SiS_Pr)) {
4380 tempah = SiS_GetReg(SiS_Pr->SiS_P3d4,0x30);
4381 if(!(tempah & SetCRT2ToRAMDAC)) {
4382 if(!(SiS_LCDAEnabled(SiS_Pr))) temp |= 0x20;
4385 SiS_SetReg(SiS_Pr->SiS_P3c4,0x32,temp);
4387 SiS_SetRegOR(SiS_Pr->SiS_P3c4,0x1E,0x20); /* enable CRT2 */
4389 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x2e,0x7f);
4390 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x2e,0x80);
4392 if(SiS_Pr->SiS_VBType & VB_SISLVDS) {
4393 SiS_PanelDelay(SiS_Pr, 2);
4398 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x1e,0x20);
4402 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x00,0x1f,0x20);
4403 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x2e,0x80);
4405 if(SiS_Pr->SiS_VBType & VB_SISPOWER) {
4406 if( (SiS_LCDAEnabled(SiS_Pr)) ||
4407 (SiS_CRT2IsLCD(SiS_Pr)) ) {
4408 /* Enable "LVDS PLL power on" (even on 301C) */
4409 SiS_SetRegAND(SiS_Pr->SiS_Part4Port,0x2a,0x7f);
4410 /* Enable "LVDS Driver Power on" (even on 301C) */
4411 SiS_SetRegAND(SiS_Pr->SiS_Part4Port,0x30,0x7f);
4416 if(SiS_IsDualEdge(SiS_Pr)) {
4418 if(!(SiS_IsVAMode(SiS_Pr))) tempah = 0x40;
4420 SiS_SetRegOR(SiS_Pr->SiS_Part4Port,0x1F,tempah);
4422 if(SiS_Pr->SiS_VBType & VB_SISLVDS) {
4424 SiS_PanelDelay(SiS_Pr, 2);
4426 SiS_SetRegOR(SiS_Pr->SiS_Part4Port,0x1f,0x10);
4427 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x2e,0x80);
4429 if(SiS_Pr->SiS_CustomT != CUT_CLEVO1400) {
4431 if(SiS_Pr->SiS_VBType & VB_SISEMI) {
4432 SiS_SetRegAND(SiS_Pr->SiS_Part4Port,0x30,0x0c);
4433 SiS_GenericDelay(SiS_Pr, 2048);
4436 SiS_SetRegOR(SiS_Pr->SiS_Part4Port,0x27,0x0c);
4438 if(SiS_Pr->SiS_VBType & VB_SISEMI) {
4440 cr36 = SiS_GetReg(SiS_Pr->SiS_P3d4,0x36);
4442 if(SiS_Pr->SiS_ROMNew) {
4443 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
4444 unsigned short romptr = GetLCDStructPtr661_2(SiS_Pr);
4446 SiS_SetRegOR(SiS_Pr->SiS_Part4Port,0x30,0x20); /* Reset */
4448 SiS_Pr->EMI_31 = ROMAddr[romptr + SiS_Pr->SiS_EMIOffset + 0];
4449 SiS_Pr->EMI_32 = ROMAddr[romptr + SiS_Pr->SiS_EMIOffset + 1];
4450 SiS_Pr->EMI_33 = ROMAddr[romptr + SiS_Pr->SiS_EMIOffset + 2];
4451 if(ROMAddr[romptr + 1] & 0x10) SiS_Pr->EMI_30 = 0x40;
4452 /* emidelay = SISGETROMW((romptr + 0x22)); */
4453 SiS_Pr->HaveEMI = SiS_Pr->HaveEMILCD = SiS_Pr->OverruleEMI = true;
4458 /* Compal 1400x1050: 0x05, 0x60, 0x00 YES (1.10.7w; CR36=69) */
4459 /* Compal 1400x1050: 0x0d, 0x70, 0x40 YES (1.10.7x; CR36=69) */
4460 /* Acer 1280x1024: 0x12, 0xd0, 0x6b NO (1.10.9k; CR36=73) */
4461 /* Compaq 1280x1024: 0x0d, 0x70, 0x6b YES (1.12.04b; CR36=03) */
4462 /* Clevo 1024x768: 0x05, 0x60, 0x33 NO (1.10.8e; CR36=12, DL!) */
4463 /* Clevo 1024x768: 0x0d, 0x70, 0x40 (if type == 3) YES (1.10.8y; CR36=?2) */
4464 /* Clevo 1024x768: 0x05, 0x60, 0x33 (if type != 3) YES (1.10.8y; CR36=?2) */
4465 /* Asus 1024x768: ? ? (1.10.8o; CR36=?2) */
4466 /* Asus 1024x768: 0x08, 0x10, 0x3c (problematic) YES (1.10.8q; CR36=22) */
4468 if(SiS_Pr->HaveEMI) {
4469 r30 = SiS_Pr->EMI_30; r31 = SiS_Pr->EMI_31;
4470 r32 = SiS_Pr->EMI_32; r33 = SiS_Pr->EMI_33;
4475 /* EMI_30 is read at driver start; however, the BIOS sets this
4476 * (if it is used) only if the LCD is in use. In case we caught
4477 * the machine while on TV output, this bit is not set and we
4478 * don't know if it should be set - hence our detection is wrong.
4479 * Work-around this here:
4482 if((!SiS_Pr->HaveEMI) || (!SiS_Pr->HaveEMILCD)) {
4483 switch((cr36 & 0x0f)) {
4486 if(SiS_Pr->SiS_CustomT == CUT_CLEVO1024) r30 &= ~0x40;
4487 if(!SiS_Pr->HaveEMI) {
4488 r31 = 0x05; r32 = 0x60; r33 = 0x33;
4489 if((cr36 & 0xf0) == 0x30) {
4490 r31 = 0x0d; r32 = 0x70; r33 = 0x40;
4494 case 3: /* 1280x1024 */
4495 if(SiS_Pr->SiS_CustomT == CUT_COMPAQ1280) r30 |= 0x40;
4496 if(!SiS_Pr->HaveEMI) {
4497 r31 = 0x12; r32 = 0xd0; r33 = 0x6b;
4498 if(SiS_Pr->SiS_CustomT == CUT_COMPAQ1280) {
4499 r31 = 0x0d; r32 = 0x70; r33 = 0x6b;
4503 case 9: /* 1400x1050 */
4505 if(!SiS_Pr->HaveEMI) {
4506 r31 = 0x05; r32 = 0x60; r33 = 0x00;
4507 if(SiS_Pr->SiS_CustomT == CUT_COMPAL1400_2) {
4508 r31 = 0x0d; r32 = 0x70; r33 = 0x40; /* BIOS values */
4512 case 11: /* 1600x1200 - unknown */
4514 if(!SiS_Pr->HaveEMI) {
4515 r31 = 0x05; r32 = 0x60; r33 = 0x00;
4520 /* BIOS values don't work so well sometimes */
4521 if(!SiS_Pr->OverruleEMI) {
4523 if(SiS_Pr->SiS_CustomT == CUT_COMPAL1400_2) {
4524 if((cr36 & 0x0f) == 0x09) {
4525 r30 = 0x60; r31 = 0x05; r32 = 0x60; r33 = 0x00;
4530 if(SiS_Pr->SiS_CustomT == CUT_COMPAQ1280) {
4531 if((cr36 & 0x0f) == 0x03) {
4532 r30 = 0x20; r31 = 0x12; r32 = 0xd0; r33 = 0x6b;
4537 if(SiS_Pr->SiS_CustomT == CUT_ASUSA2H_2) {
4538 if((cr36 & 0x0f) == 0x02) {
4539 /* r30 = 0x60; r31 = 0x05; r32 = 0x60; r33 = 0x33; */ /* rev 2 */
4540 /* r30 = 0x20; r31 = 0x05; r32 = 0x60; r33 = 0x33; */ /* rev 3 */
4541 /* r30 = 0x60; r31 = 0x0d; r32 = 0x70; r33 = 0x40; */ /* rev 4 */
4542 /* r30 = 0x20; r31 = 0x0d; r32 = 0x70; r33 = 0x40; */ /* rev 5 */
4548 if(!(SiS_Pr->OverruleEMI && (!r30) && (!r31) && (!r32) && (!r33))) {
4549 SiS_SetRegOR(SiS_Pr->SiS_Part4Port,0x30,0x20); /* Reset */
4550 SiS_GenericDelay(SiS_Pr, 2048);
4552 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x31,r31);
4553 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x32,r32);
4554 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x33,r33);
4555 #endif /* SET_EMI */
4557 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x34,0x10);
4560 if( (SiS_LCDAEnabled(SiS_Pr)) ||
4561 (SiS_CRT2IsLCD(SiS_Pr)) ) {
4563 /*SiS_SetRegOR(SiS_Pr->SiS_Part4Port,0x2a,0x80);*/
4564 SiS_PanelDelayLoop(SiS_Pr, 3, 5);
4566 SiS_PanelDelayLoop(SiS_Pr, 3, 5);
4569 SiS_WaitVBRetrace(SiS_Pr);
4570 SiS_WaitVBRetrace(SiS_Pr);
4571 if(SiS_Pr->SiS_CustomT == CUT_ASUSA2H_2) {
4572 SiS_GenericDelay(SiS_Pr, 1280);
4574 SiS_SetRegOR(SiS_Pr->SiS_Part4Port,0x30,0x40); /* Enable */
4575 /*SiS_SetRegAND(SiS_Pr->SiS_Part4Port,0x2a,0x7f);*/
4582 if(!(SiS_WeHaveBacklightCtrl(SiS_Pr))) {
4583 if(SiS_IsVAorLCD(SiS_Pr)) {
4584 SiS_PanelDelayLoop(SiS_Pr, 3, 10);
4586 SiS_PanelDelayLoop(SiS_Pr, 3, 10);
4588 SiS_WaitVBRetrace(SiS_Pr);
4589 if(SiS_Pr->SiS_VBType & VB_SISEMI) {
4590 SiS_GenericDelay(SiS_Pr, 2048);
4591 SiS_WaitVBRetrace(SiS_Pr);
4594 SiS_SetRegOR(SiS_Pr->SiS_Part4Port,0x26,0x01);
4596 SiS_SetRegOR(SiS_Pr->SiS_Part4Port,0x26,0x03);
4601 SiS_SetReg(SiS_Pr->SiS_P3c4,0x06,pushax);
4602 SiS_DisplayOn(SiS_Pr);
4603 SiS_SetRegByte(SiS_Pr->SiS_P3c6,0xff);
4607 if(!(SiS_WeHaveBacklightCtrl(SiS_Pr))) {
4608 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x00,0x7f);
4611 #endif /* CONFIG_FB_SIS_315 */
4615 } else { /* ============ For 301 ================ */
4617 if(SiS_Pr->ChipType < SIS_315H) {
4618 if(SiS_CRT2IsLCD(SiS_Pr)) {
4619 SiS_SetRegSR11ANDOR(SiS_Pr,0xFB,0x00);
4620 SiS_PanelDelay(SiS_Pr, 0);
4624 temp = SiS_GetReg(SiS_Pr->SiS_P3c4,0x32) & 0xDF; /* lock mode */
4625 if(SiS_BridgeInSlavemode(SiS_Pr)) {
4626 tempah = SiS_GetReg(SiS_Pr->SiS_P3d4,0x30);
4627 if(!(tempah & SetCRT2ToRAMDAC)) temp |= 0x20;
4629 SiS_SetReg(SiS_Pr->SiS_P3c4,0x32,temp);
4631 SiS_SetRegOR(SiS_Pr->SiS_P3c4,0x1E,0x20); /* enable CRT2 */
4633 if(SiS_Pr->ChipType >= SIS_315H) {
4634 temp = SiS_GetReg(SiS_Pr->SiS_Part1Port,0x2E);
4635 if(!(temp & 0x80)) {
4636 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x2E,0x80); /* BVBDOENABLE=1 */
4640 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x00,0x1F,0x20); /* enable VB processor */
4642 SiS_VBLongWait(SiS_Pr);
4643 SiS_DisplayOn(SiS_Pr);
4644 if(SiS_Pr->ChipType >= SIS_315H) {
4645 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x00,0x7f);
4647 SiS_VBLongWait(SiS_Pr);
4649 if(SiS_Pr->ChipType < SIS_315H) {
4650 if(SiS_CRT2IsLCD(SiS_Pr)) {
4651 SiS_PanelDelay(SiS_Pr, 1);
4652 SiS_SetRegSR11ANDOR(SiS_Pr,0xF7,0x00);
4658 } else { /* =================== For LVDS ================== */
4660 if(SiS_Pr->ChipType < SIS_315H) {
4662 #ifdef CONFIG_FB_SIS_300 /* 300 series */
4664 if(SiS_CRT2IsLCD(SiS_Pr)) {
4665 if(SiS_Pr->ChipType == SIS_730) {
4666 SiS_PanelDelay(SiS_Pr, 1);
4667 SiS_PanelDelay(SiS_Pr, 1);
4668 SiS_PanelDelay(SiS_Pr, 1);
4670 SiS_SetRegSR11ANDOR(SiS_Pr,0xFB,0x00);
4671 if(!(SiS_CR36BIOSWord23d(SiS_Pr))) {
4672 SiS_PanelDelay(SiS_Pr, 0);
4676 SiS_SetRegOR(SiS_Pr->SiS_P3c4,0x1E,0x20);
4677 SiS_DisplayOn(SiS_Pr);
4678 SiS_UnLockCRT2(SiS_Pr);
4679 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x02,0xBF);
4680 if(SiS_BridgeInSlavemode(SiS_Pr)) {
4681 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x01,0x1F);
4683 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x01,0x1F,0x40);
4686 if(SiS_Pr->SiS_IF_DEF_CH70xx == 1) {
4687 if(!(SiS_CRT2IsLCD(SiS_Pr))) {
4688 SiS_WaitVBRetrace(SiS_Pr);
4689 SiS_SetCH700x(SiS_Pr,0x0E,0x0B);
4693 if(SiS_CRT2IsLCD(SiS_Pr)) {
4694 if(!(SiS_GetReg(SiS_Pr->SiS_P3c4,0x13) & 0x40)) {
4695 if(!(SiS_GetReg(SiS_Pr->SiS_P3c4,0x16) & 0x10)) {
4696 if(!(SiS_CR36BIOSWord23b(SiS_Pr))) {
4697 SiS_PanelDelay(SiS_Pr, 1);
4698 SiS_PanelDelay(SiS_Pr, 1);
4700 SiS_WaitVBRetrace(SiS_Pr);
4701 SiS_SetRegSR11ANDOR(SiS_Pr,0xF7,0x00);
4706 #endif /* CONFIG_FB_SIS_300 */
4710 #ifdef CONFIG_FB_SIS_315 /* 315 series */
4712 if(!(SiS_IsNotM650orLater(SiS_Pr))) {
4713 /*if(SiS_Pr->ChipType < SIS_340) {*/ /* XGI needs this */
4714 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x4c,0x18);
4718 if(SiS_Pr->SiS_IF_DEF_CH70xx == 0) {
4719 if(SiS_CRT2IsLCD(SiS_Pr)) {
4720 SiS_SetRegSR11ANDOR(SiS_Pr,0xFB,0x00);
4721 SiS_PanelDelay(SiS_Pr, 0);
4725 SiS_SetRegOR(SiS_Pr->SiS_P3c4,0x1E,0x20);
4726 SiS_UnLockCRT2(SiS_Pr);
4728 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x2e,0xf7);
4730 if(SiS_Pr->SiS_IF_DEF_CH70xx == 2) {
4731 temp = SiS_GetCH701x(SiS_Pr,0x66);
4733 SiS_Chrontel701xBLOff(SiS_Pr);
4736 if(SiS_Pr->ChipType != SIS_550) {
4737 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x2e,0x7f);
4740 if(SiS_Pr->ChipType == SIS_740) {
4741 if(SiS_Pr->SiS_IF_DEF_CH70xx == 2) {
4742 if(SiS_IsLCDOrLCDA(SiS_Pr)) {
4743 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x1E,0x20);
4748 temp1 = SiS_GetReg(SiS_Pr->SiS_Part1Port,0x2E);
4749 if(!(temp1 & 0x80)) {
4750 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x2E,0x80);
4753 if(SiS_Pr->SiS_IF_DEF_CH70xx == 2) {
4755 SiS_Chrontel701xBLOn(SiS_Pr);
4759 if(SiS_Pr->SiS_IF_DEF_CH70xx == 0) {
4760 if(SiS_CRT2IsLCD(SiS_Pr)) {
4761 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x1E,0x20);
4762 if(SiS_Pr->ChipType == SIS_550) {
4763 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x1E,0x40);
4764 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x1E,0x10);
4767 } else if(SiS_IsVAMode(SiS_Pr)) {
4768 if(SiS_Pr->ChipType != SIS_740) {
4769 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x1E,0x20);
4773 if(!(SiS_WeHaveBacklightCtrl(SiS_Pr))) {
4774 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x00,0x7f);
4777 if(SiS_Pr->SiS_IF_DEF_CH70xx == 2) {
4778 if(SiS_IsTVOrYPbPrOrScart(SiS_Pr)) {
4779 SiS_Chrontel701xOn(SiS_Pr);
4781 if( (SiS_IsVAMode(SiS_Pr)) ||
4782 (SiS_IsLCDOrLCDA(SiS_Pr)) ) {
4783 SiS_ChrontelDoSomething1(SiS_Pr);
4787 if(SiS_Pr->SiS_IF_DEF_CH70xx == 2) {
4788 if(!(SiS_WeHaveBacklightCtrl(SiS_Pr))) {
4789 if( (SiS_IsVAMode(SiS_Pr)) ||
4790 (SiS_IsLCDOrLCDA(SiS_Pr)) ) {
4791 SiS_Chrontel701xBLOn(SiS_Pr);
4792 SiS_ChrontelInitTVVSync(SiS_Pr);
4795 } else if(SiS_Pr->SiS_IF_DEF_CH70xx == 0) {
4796 if(!(SiS_WeHaveBacklightCtrl(SiS_Pr))) {
4797 if(SiS_CRT2IsLCD(SiS_Pr)) {
4798 SiS_PanelDelay(SiS_Pr, 1);
4799 SiS_SetRegSR11ANDOR(SiS_Pr,0xF7,0x00);
4804 #endif /* CONFIG_FB_SIS_315 */
4812 /*********************************************/
4813 /* SET PART 1 REGISTER GROUP */
4814 /*********************************************/
4816 /* Set CRT2 OFFSET / PITCH */
4818 SiS_SetCRT2Offset(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex,
4819 unsigned short RRTI)
4821 unsigned short offset;
4824 if(SiS_Pr->SiS_VBInfo & SetInSlaveMode) return;
4826 offset = SiS_GetOffset(SiS_Pr,ModeNo,ModeIdIndex,RRTI);
4828 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x07,(offset & 0xFF));
4829 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x09,(offset >> 8));
4831 temp = (unsigned char)(((offset >> 3) & 0xFF) + 1);
4832 if(offset & 0x07) temp++;
4833 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x03,temp);
4836 /* Set CRT2 sync and PanelLink mode */
4838 SiS_SetCRT2Sync(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short RefreshRateTableIndex)
4840 unsigned short tempah=0, tempbl, infoflag;
4844 if(SiS_Pr->UseCustomMode) {
4845 infoflag = SiS_Pr->CInfoFlag;
4847 infoflag = SiS_Pr->SiS_RefIndex[RefreshRateTableIndex].Ext_InfoFlag;
4850 if(SiS_Pr->SiS_IF_DEF_LVDS == 1) { /* LVDS */
4852 if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) {
4854 } else if((SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) && (SiS_Pr->SiS_LCDInfo & LCDSync)) {
4855 tempah = SiS_Pr->SiS_LCDInfo;
4856 } else tempah = infoflag >> 8;
4859 if(!(SiS_Pr->SiS_LCDInfo & LCDRGB18Bit)) tempah |= 0x10;
4860 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) {
4861 if((SiS_Pr->SiS_CustomT == CUT_BARCO1366) ||
4862 (SiS_Pr->SiS_CustomT == CUT_BARCO1024)) {
4865 if( (SiS_Pr->SiS_IF_DEF_FSTN) ||
4866 (SiS_Pr->SiS_IF_DEF_DSTN) ||
4867 (SiS_Pr->SiS_IF_DEF_TRUMPION) ||
4868 (SiS_Pr->SiS_CustomT == CUT_PANEL848) ||
4869 (SiS_Pr->SiS_CustomT == CUT_PANEL856) ) {
4872 if( (SiS_Pr->SiS_IF_DEF_FSTN) ||
4873 (SiS_Pr->SiS_IF_DEF_DSTN) ) {
4877 if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) {
4878 if(SiS_Pr->ChipType >= SIS_315H) {
4881 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x13,0xE7,tempah);
4882 /* Don't care about 12/18/24 bit mode - TV is via VGA, not PL */
4884 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x19,0x0F,0xe0);
4887 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x19,0x0F,tempah);
4890 } else if(SiS_Pr->SiS_VBType & VB_SISVB) {
4892 if(SiS_Pr->ChipType < SIS_315H) {
4894 #ifdef CONFIG_FB_SIS_300 /* ---- 300 series --- */
4896 if(SiS_Pr->SiS_VBType & VB_SIS30xBLV) { /* 630 - 301B(-DH) */
4898 tempah = infoflag >> 8;
4900 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) {
4901 if(SiS_Pr->SiS_LCDInfo & LCDSync) {
4902 tempah = SiS_Pr->SiS_LCDInfo;
4903 tempbl = (tempah >> 6) & 0x03;
4908 if(!(SiS_Pr->SiS_LCDInfo & LCDRGB18Bit)) tempah |= 0x10;
4910 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x19,0x0F,tempah);
4911 if((SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) && (!(SiS_Pr->SiS_VBType & VB_NoLCD))) {
4912 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x1a,0xf0,tempbl);
4915 } else { /* 630 - 301 */
4917 tempah = ((infoflag >> 8) & 0xc0) | 0x20;
4918 if(!(SiS_Pr->SiS_LCDInfo & LCDRGB18Bit)) tempah |= 0x10;
4919 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x19,0x0F,tempah);
4923 #endif /* CONFIG_FB_SIS_300 */
4927 #ifdef CONFIG_FB_SIS_315 /* ------- 315 series ------ */
4929 if(SiS_Pr->SiS_VBType & VB_SISLVDS) { /* 315 - LVDS */
4932 if((SiS_Pr->SiS_CustomT == CUT_COMPAQ1280) &&
4933 (SiS_Pr->SiS_LCDResInfo == Panel_1280x1024)) {
4934 tempah = infoflag >> 8;
4935 if(SiS_Pr->SiS_LCDInfo & LCDSync) {
4936 tempbl = ((SiS_Pr->SiS_LCDInfo & 0xc0) >> 6);
4938 } else if((SiS_Pr->SiS_CustomT == CUT_CLEVO1400) &&
4939 (SiS_Pr->SiS_LCDResInfo == Panel_1400x1050)) {
4940 tempah = infoflag >> 8;
4943 tempah = SiS_GetReg(SiS_Pr->SiS_P3d4,0x37);
4944 tempbl = (tempah >> 6) & 0x03;
4946 if(!(SiS_Pr->SiS_LCDInfo & LCDRGB18Bit)) tempbl |= 0x04;
4950 if(!(SiS_Pr->SiS_LCDInfo & LCDRGB18Bit)) tempah |= 0x10;
4951 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCDA) tempah |= 0xc0;
4952 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x19,0x0F,tempah);
4953 if(SiS_Pr->SiS_VBType & VB_SIS30xBLV) {
4954 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) {
4955 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x1a,0xf0,tempbl);
4959 } else { /* 315 - TMDS */
4961 tempah = tempbl = infoflag >> 8;
4962 if(!SiS_Pr->UseCustomMode) {
4964 if((SiS_Pr->SiS_VBType & VB_SIS30xC) && (SiS_Pr->SiS_VBInfo & SetCRT2ToRAMDAC)) {
4965 if(ModeNo <= 0x13) {
4966 tempah = SiS_GetRegByte((SiS_Pr->SiS_P3ca+0x02));
4969 if(SiS_Pr->SiS_VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
4970 if(!(SiS_Pr->SiS_LCDInfo & LCDPass11)) {
4971 if(SiS_Pr->SiS_LCDInfo & LCDSync) {
4972 tempah = SiS_Pr->SiS_LCDInfo;
4973 tempbl = (tempah >> 6) & 0x03;
4980 if(!(SiS_Pr->SiS_LCDInfo & LCDRGB18Bit)) tempah |= 0x10;
4981 if(SiS_Pr->SiS_VBType & VB_NoLCD) {
4982 /* Imitate BIOS bug */
4983 if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) tempah |= 0xc0;
4985 if((SiS_Pr->SiS_VBType & VB_SIS30xC) && (SiS_Pr->SiS_VBInfo & SetCRT2ToRAMDAC)) {
4988 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x13,0xe7,tempah);
4990 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x19,0x0F,tempah);
4991 if(SiS_Pr->SiS_VBType & VB_SIS30xBLV) {
4992 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) {
4993 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x1a,0xf0,tempbl);
4999 #endif /* CONFIG_FB_SIS_315 */
5004 /* Set CRT2 FIFO on 300/540/630/730 */
5005 #ifdef CONFIG_FB_SIS_300
5007 SiS_SetCRT2FIFO_300(struct SiS_Private *SiS_Pr,unsigned short ModeNo)
5009 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
5010 unsigned short temp, index, modeidindex, refreshratetableindex;
5011 unsigned short VCLK = 0, MCLK, colorth = 0, data2 = 0;
5012 unsigned short tempbx, tempcl, CRT1ModeNo, CRT2ModeNo, SelectRate_backup;
5013 unsigned int data, pci50, pciA0;
5014 static const unsigned char colortharray[] = {
5018 SelectRate_backup = SiS_Pr->SiS_SelectCRT2Rate;
5020 if(!SiS_Pr->CRT1UsesCustomMode) {
5022 CRT1ModeNo = SiS_Pr->SiS_CRT1Mode; /* get CRT1 ModeNo */
5023 SiS_SearchModeID(SiS_Pr, &CRT1ModeNo, &modeidindex);
5024 SiS_Pr->SiS_SetFlag &= (~ProgrammingCRT2);
5025 SiS_Pr->SiS_SelectCRT2Rate = 0;
5026 refreshratetableindex = SiS_GetRatePtr(SiS_Pr, CRT1ModeNo, modeidindex);
5028 if(CRT1ModeNo >= 0x13) {
5030 index = SiS_GetRefCRTVCLK(SiS_Pr, refreshratetableindex, SiS_Pr->SiS_UseWide);
5031 VCLK = SiS_Pr->SiS_VCLKData[index].CLOCK;
5033 /* Get colordepth */
5034 colorth = SiS_GetColorDepth(SiS_Pr,CRT1ModeNo,modeidindex) >> 1;
5035 if(!colorth) colorth++;
5043 VCLK = SiS_Pr->CSRClock_CRT1;
5045 /* Get color depth */
5046 colorth = colortharray[((SiS_Pr->CModeFlag_CRT1 & ModeTypeMask) - 2)];
5050 if(CRT1ModeNo >= 0x13) {
5052 if(SiS_Pr->ChipType == SIS_300) {
5053 index = SiS_GetReg(SiS_Pr->SiS_P3c4,0x3A);
5055 index = SiS_GetReg(SiS_Pr->SiS_P3c4,0x1A);
5058 MCLK = SiS_Pr->SiS_MCLKData_0[index].CLOCK;
5060 temp = ((SiS_GetReg(SiS_Pr->SiS_P3c4,0x14) >> 6) & 0x03) << 1;
5064 data2 = temp - ((colorth * VCLK) / MCLK);
5066 temp = (28 * 16) % data2;
5067 data2 = (28 * 16) / data2;
5070 if(SiS_Pr->ChipType == SIS_300) {
5072 SiS_GetFIFOThresholdIndex300(SiS_Pr, &tempbx, &tempcl);
5073 data = SiS_GetFIFOThresholdB300(tempbx, tempcl);
5077 pci50 = sisfb_read_nbridge_pci_dword(SiS_Pr, 0x50);
5078 pciA0 = sisfb_read_nbridge_pci_dword(SiS_Pr, 0xa0);
5080 if(SiS_Pr->ChipType == SIS_730) {
5082 index = (unsigned short)(((pciA0 >> 28) & 0x0f) * 3);
5083 index += (unsigned short)(((pci50 >> 9)) & 0x03);
5085 /* BIOS BUG (2.04.5d, 2.04.6a use ah here, which is unset!) */
5086 index = 0; /* -- do it like the BIOS anyway... */
5093 index = (pci50 >> 1) & 0x07;
5095 if(pci50 & 0x01) index += 6;
5096 if(!(pciA0 & 0x01)) index += 24;
5098 if(SiS_GetReg(SiS_Pr->SiS_P3c4,0x14) & 0x80) index += 12;
5102 data = SiS_GetLatencyFactor630(SiS_Pr, index) + 15;
5103 if(!(SiS_GetReg(SiS_Pr->SiS_P3c4,0x14) & 0x80)) data += 5;
5107 data += data2; /* CRT1 Request Period */
5109 SiS_Pr->SiS_SetFlag |= ProgrammingCRT2;
5110 SiS_Pr->SiS_SelectCRT2Rate = SelectRate_backup;
5112 if(!SiS_Pr->UseCustomMode) {
5114 CRT2ModeNo = ModeNo;
5115 SiS_SearchModeID(SiS_Pr, &CRT2ModeNo, &modeidindex);
5117 refreshratetableindex = SiS_GetRatePtr(SiS_Pr, CRT2ModeNo, modeidindex);
5120 index = SiS_GetVCLK2Ptr(SiS_Pr, CRT2ModeNo, modeidindex, refreshratetableindex);
5121 VCLK = SiS_Pr->SiS_VCLKData[index].CLOCK;
5123 if((SiS_Pr->SiS_CustomT == CUT_BARCO1366) || (SiS_Pr->SiS_CustomT == CUT_BARCO1024)) {
5124 if(SiS_Pr->SiS_UseROM) {
5125 if(ROMAddr[0x220] & 0x01) {
5126 VCLK = ROMAddr[0x229] | (ROMAddr[0x22a] << 8);
5135 VCLK = SiS_Pr->CSRClock;
5139 /* Get colordepth */
5140 colorth = SiS_GetColorDepth(SiS_Pr,CRT2ModeNo,modeidindex) >> 1;
5141 if(!colorth) colorth++;
5143 data = data * VCLK * colorth;
5144 temp = data % (MCLK << 4);
5145 data = data / (MCLK << 4);
5148 if(data < 6) data = 6;
5149 else if(data > 0x14) data = 0x14;
5151 if(SiS_Pr->ChipType == SIS_300) {
5153 if((data <= 0x0f) || (SiS_Pr->SiS_LCDResInfo == Panel_1280x1024))
5157 if(( (SiS_Pr->ChipType == SIS_630) ||
5158 (SiS_Pr->ChipType == SIS_730) ) &&
5159 (SiS_Pr->ChipRevision >= 0x30))
5162 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x01,0xe0,temp);
5164 if((SiS_Pr->ChipType == SIS_630) &&
5165 (SiS_Pr->ChipRevision >= 0x30)) {
5166 if(data > 0x13) data = 0x13;
5168 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x02,0xe0,data);
5170 } else { /* If mode <= 0x13, we just restore everything */
5172 SiS_Pr->SiS_SetFlag |= ProgrammingCRT2;
5173 SiS_Pr->SiS_SelectCRT2Rate = SelectRate_backup;
5179 /* Set CRT2 FIFO on 315/330 series */
5180 #ifdef CONFIG_FB_SIS_315
5182 SiS_SetCRT2FIFO_310(struct SiS_Private *SiS_Pr)
5184 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x01,0x3B);
5185 if( (SiS_Pr->ChipType == SIS_760) &&
5186 (SiS_Pr->SiS_SysFlags & SF_760LFB) &&
5187 (SiS_Pr->SiS_ModeType == Mode32Bpp) &&
5188 (SiS_Pr->SiS_VGAHDE >= 1280) &&
5189 (SiS_Pr->SiS_VGAVDE >= 1024) ) {
5190 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x2f,0x03);
5191 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x01,0x3b);
5192 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x4d,0xc0);
5193 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x2f,0x01);
5194 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x4d,0xc0);
5195 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x02,0x6e);
5197 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x02,~0x3f,0x04);
5203 static unsigned short
5204 SiS_GetVGAHT2(struct SiS_Private *SiS_Pr)
5206 unsigned int tempax,tempbx;
5208 tempbx = (SiS_Pr->SiS_VGAVT - SiS_Pr->SiS_VGAVDE) * SiS_Pr->SiS_RVBHCMAX;
5209 tempax = (SiS_Pr->SiS_VT - SiS_Pr->SiS_VDE) * SiS_Pr->SiS_RVBHCFACT;
5210 tempax = (tempax * SiS_Pr->SiS_HT) / tempbx;
5211 return (unsigned short)tempax;
5214 /* Set Part 1 / SiS bridge slave mode */
5216 SiS_SetGroup1_301(struct SiS_Private *SiS_Pr, unsigned short ModeNo,unsigned short ModeIdIndex,
5217 unsigned short RefreshRateTableIndex)
5219 unsigned short temp, modeflag, i, j, xres=0, VGAVDE;
5220 static const unsigned short CRTranslation[] = {
5221 /* CR0 CR1 CR2 CR3 CR4 CR5 CR6 CR7 */
5222 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a,
5223 /* CR8 CR9 SR0A SR0B SR0C SR0D SR0E CR0F */
5224 0x00, 0x0b, 0x17, 0x18, 0x19, 0x00, 0x1a, 0x00,
5225 /* CR10 CR11 CR12 CR13 CR14 CR15 CR16 CR17 */
5226 0x0c, 0x0d, 0x0e, 0x00, 0x0f, 0x10, 0x11, 0x00
5229 if(ModeNo <= 0x13) {
5230 modeflag = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_ModeFlag;
5231 } else if(SiS_Pr->UseCustomMode) {
5232 modeflag = SiS_Pr->CModeFlag;
5233 xres = SiS_Pr->CHDisplay;
5235 modeflag = SiS_Pr->SiS_EModeIDTable[ModeIdIndex].Ext_ModeFlag;
5236 xres = SiS_Pr->SiS_RefIndex[RefreshRateTableIndex].XRes;
5239 /* The following is only done if bridge is in slave mode: */
5241 if(SiS_Pr->ChipType >= SIS_315H) {
5242 if(xres >= 1600) { /* BIOS: == 1600 */
5243 SiS_SetRegOR(SiS_Pr->SiS_P3c4,0x31,0x04);
5247 SiS_Pr->CHTotal = 8224; /* Max HT, 0x2020, results in 0x3ff in registers */
5249 SiS_Pr->CHDisplay = SiS_Pr->SiS_VGAHDE;
5250 if(modeflag & HalfDCLK) SiS_Pr->CHDisplay >>= 1;
5252 SiS_Pr->CHBlankStart = SiS_Pr->CHDisplay;
5253 if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) {
5254 SiS_Pr->CHBlankStart += 16;
5257 SiS_Pr->CHBlankEnd = 32;
5258 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) {
5259 if(xres == 1600) SiS_Pr->CHBlankEnd += 80;
5262 temp = SiS_Pr->SiS_VGAHT - 96;
5263 if(!(modeflag & HalfDCLK)) temp -= 32;
5264 if(SiS_Pr->SiS_LCDInfo & LCDPass11) {
5265 temp = SiS_GetReg(SiS_Pr->SiS_P3d4,0x04);
5266 temp |= ((SiS_GetReg(SiS_Pr->SiS_P3c4,0x0b) & 0xc0) << 2);
5270 if(SiS_Pr->SiS_RVBHRS2) temp = SiS_Pr->SiS_RVBHRS2;
5272 SiS_Pr->CHSyncStart = temp;
5274 SiS_Pr->CHSyncEnd = 0xffe8; /* results in 0x2000 in registers */
5276 SiS_Pr->CVTotal = 2049; /* Max VT, 0x0801, results in 0x7ff in registers */
5278 VGAVDE = SiS_Pr->SiS_VGAVDE;
5279 if (VGAVDE == 357) VGAVDE = 350;
5280 else if(VGAVDE == 360) VGAVDE = 350;
5281 else if(VGAVDE == 375) VGAVDE = 350;
5282 else if(VGAVDE == 405) VGAVDE = 400;
5283 else if(VGAVDE == 420) VGAVDE = 400;
5284 else if(VGAVDE == 525) VGAVDE = 480;
5285 else if(VGAVDE == 1056) VGAVDE = 1024;
5286 SiS_Pr->CVDisplay = VGAVDE;
5288 SiS_Pr->CVBlankStart = SiS_Pr->CVDisplay;
5290 SiS_Pr->CVBlankEnd = 1;
5291 if(ModeNo == 0x3c) SiS_Pr->CVBlankEnd = 226;
5293 temp = (SiS_Pr->SiS_VGAVT - VGAVDE) >> 1;
5294 SiS_Pr->CVSyncStart = VGAVDE + temp;
5297 SiS_Pr->CVSyncEnd = SiS_Pr->CVSyncStart + temp;
5299 SiS_CalcCRRegisters(SiS_Pr, 0);
5300 SiS_Pr->CCRT1CRTC[16] &= ~0xE0;
5302 for(i = 0; i <= 7; i++) {
5303 SiS_SetReg(SiS_Pr->SiS_Part1Port,CRTranslation[i],SiS_Pr->CCRT1CRTC[i]);
5305 for(i = 0x10, j = 8; i <= 0x12; i++, j++) {
5306 SiS_SetReg(SiS_Pr->SiS_Part1Port,CRTranslation[i],SiS_Pr->CCRT1CRTC[j]);
5308 for(i = 0x15, j = 11; i <= 0x16; i++, j++) {
5309 SiS_SetReg(SiS_Pr->SiS_Part1Port,CRTranslation[i],SiS_Pr->CCRT1CRTC[j]);
5311 for(i = 0x0a, j = 13; i <= 0x0c; i++, j++) {
5312 SiS_SetReg(SiS_Pr->SiS_Part1Port,CRTranslation[i],SiS_Pr->CCRT1CRTC[j]);
5315 temp = SiS_Pr->CCRT1CRTC[16] & 0xE0;
5316 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,CRTranslation[0x0E],0x1F,temp);
5318 temp = (SiS_Pr->CCRT1CRTC[16] & 0x01) << 5;
5319 if(modeflag & DoubleScanMode) temp |= 0x80;
5320 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,CRTranslation[0x09],0x5F,temp);
5323 temp |= (SiS_GetReg(SiS_Pr->SiS_P3c4,0x01) & 0x01);
5324 if(modeflag & HalfDCLK) temp |= 0x08;
5325 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x16,temp); /* SR01: HalfDCLK[3], 8/9 div dotclock[0] */
5327 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x0F,0x00); /* CR14: (text mode: underline location) */
5328 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x12,0x00); /* CR17: n/a */
5331 if(SiS_Pr->SiS_LCDInfo & LCDRGB18Bit) {
5332 temp = (SiS_GetReg(SiS_Pr->SiS_Part1Port,0x00) & 0x01) << 7;
5334 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x1A,temp); /* SR0E, dither[7] */
5336 temp = SiS_GetRegByte((SiS_Pr->SiS_P3ca+0x02));
5337 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x1b,temp); /* ? */
5341 * This is used for LVDS, LCDA and Chrontel TV output
5342 * 300/LVDS+TV, 300/301B-DH, 315/LVDS+TV, 315/LCDA
5345 SiS_SetGroup1_LVDS(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex,
5346 unsigned short RefreshRateTableIndex)
5348 unsigned short modeflag, resinfo = 0;
5349 unsigned short push2, tempax, tempbx, tempcx, temp;
5350 unsigned int tempeax = 0, tempebx, tempecx, tempvcfact = 0;
5351 bool islvds = false, issis = false, chkdclkfirst = false;
5352 #ifdef CONFIG_FB_SIS_300
5353 unsigned short crt2crtc = 0;
5355 #ifdef CONFIG_FB_SIS_315
5356 unsigned short pushcx;
5359 if(ModeNo <= 0x13) {
5360 modeflag = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_ModeFlag;
5361 resinfo = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_ResInfo;
5362 #ifdef CONFIG_FB_SIS_300
5363 crt2crtc = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_CRT2CRTC;
5365 } else if(SiS_Pr->UseCustomMode) {
5366 modeflag = SiS_Pr->CModeFlag;
5368 modeflag = SiS_Pr->SiS_EModeIDTable[ModeIdIndex].Ext_ModeFlag;
5369 resinfo = SiS_Pr->SiS_EModeIDTable[ModeIdIndex].Ext_RESINFO;
5370 #ifdef CONFIG_FB_SIS_300
5371 crt2crtc = SiS_Pr->SiS_RefIndex[RefreshRateTableIndex].Ext_CRT2CRTC;
5375 /* is lvds if really LVDS, or 301B-DH with external LVDS transmitter */
5376 if((SiS_Pr->SiS_IF_DEF_LVDS == 1) || (SiS_Pr->SiS_VBType & VB_NoLCD)) {
5380 /* is really sis if sis bridge, but not 301B-DH */
5381 if((SiS_Pr->SiS_VBType & VB_SISVB) && (!(SiS_Pr->SiS_VBType & VB_NoLCD))) {
5385 if((SiS_Pr->ChipType >= SIS_315H) && (islvds) && (!(SiS_Pr->SiS_VBInfo & SetCRT2ToLCDA))) {
5386 if((!SiS_Pr->SiS_IF_DEF_FSTN) && (!SiS_Pr->SiS_IF_DEF_DSTN)) {
5387 chkdclkfirst = true;
5391 #ifdef CONFIG_FB_SIS_315
5392 if((SiS_Pr->ChipType >= SIS_315H) && (SiS_Pr->SiS_VBInfo & SetCRT2ToLCDA)) {
5394 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x2D,0x10);
5395 } else if(IS_SIS740) {
5397 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x13,0xfb,0x04);
5398 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x2D,0x03);
5399 } else if(SiS_Pr->SiS_VBType & VB_SISVB) {
5400 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x2D,0x10);
5404 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x13,0xfb,0x04);
5405 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x2D,0x00);
5406 } else if(SiS_Pr->SiS_VBType & VB_SISVB) {
5407 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x2D,0x0f);
5408 if(SiS_Pr->SiS_VBType & VB_SIS30xC) {
5409 if((SiS_Pr->SiS_LCDResInfo == Panel_1024x768) ||
5410 (SiS_Pr->SiS_LCDResInfo == Panel_1280x1024)) {
5411 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x2D,0x20);
5421 tempax = SiS_Pr->SiS_LCDHDES;
5423 if(SiS_Pr->SiS_VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
5424 if(!SiS_Pr->SiS_IF_DEF_FSTN && !SiS_Pr->SiS_IF_DEF_DSTN) {
5425 if((SiS_Pr->SiS_LCDResInfo == Panel_640x480) &&
5426 (!(SiS_Pr->SiS_VBInfo & SetInSlaveMode))) {
5433 temp = (tempax & 0x0007);
5434 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x1A,temp); /* BPLHDESKEW[2:0] */
5435 temp = (tempax >> 3) & 0x00FF;
5436 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x16,temp); /* BPLHDESKEW[10:3] */
5438 tempbx = SiS_Pr->SiS_HDE;
5439 if(SiS_Pr->SiS_VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
5440 if(!(SiS_Pr->SiS_LCDInfo & LCDPass11)) {
5441 tempbx = SiS_Pr->PanelXRes;
5443 if((SiS_Pr->SiS_LCDResInfo == Panel_320x240_1) ||
5444 (SiS_Pr->SiS_LCDResInfo == Panel_320x240_2) ||
5445 (SiS_Pr->SiS_LCDResInfo == Panel_320x240_3)) {
5451 if(tempax >= SiS_Pr->SiS_HT) tempax -= SiS_Pr->SiS_HT;
5454 if(temp & 0x07) temp += 8;
5456 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x17,temp); /* BPLHDEE */
5458 tempcx = (SiS_Pr->SiS_HT - tempbx) >> 2;
5460 if(SiS_Pr->SiS_VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
5461 if(!(SiS_Pr->SiS_LCDInfo & LCDPass11)) {
5462 if(SiS_Pr->PanelHRS != 999) tempcx = SiS_Pr->PanelHRS;
5467 if(tempcx >= SiS_Pr->SiS_HT) tempcx -= SiS_Pr->SiS_HT;
5469 temp = (tempcx >> 3) & 0x00FF;
5470 if(SiS_Pr->SiS_VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
5471 if(SiS_Pr->SiS_IF_DEF_TRUMPION) {
5472 if(SiS_Pr->SiS_LCDResInfo == Panel_1024x768) {
5476 case 0x0d: temp = 0x56; break;
5477 case 0x10: temp = 0x60; break;
5478 case 0x13: temp = 0x5f; break;
5488 case 0x5e: temp = 0x54; break;
5493 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x14,temp); /* BPLHRS */
5495 if(SiS_Pr->SiS_VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
5497 if(!(SiS_Pr->SiS_LCDInfo & LCDPass11)) {
5499 if(SiS_Pr->PanelHRE != 999) {
5500 temp = tempcx + SiS_Pr->PanelHRE;
5501 if(temp >= SiS_Pr->SiS_HT) temp -= SiS_Pr->SiS_HT;
5510 temp |= ((tempcx & 0x07) << 5);
5511 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x15,temp); /* BPLHRE */
5515 tempax = SiS_Pr->SiS_VGAVDE;
5516 if(SiS_Pr->SiS_VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
5517 if(!(SiS_Pr->SiS_LCDInfo & LCDPass11)) {
5518 tempax = SiS_Pr->PanelYRes;
5522 tempbx = SiS_Pr->SiS_LCDVDES + tempax;
5523 if(tempbx >= SiS_Pr->SiS_VT) tempbx -= SiS_Pr->SiS_VT;
5527 tempcx = SiS_Pr->SiS_VGAVT - SiS_Pr->SiS_VGAVDE;
5528 if(SiS_Pr->ChipType < SIS_315H) {
5529 if(SiS_Pr->SiS_VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
5530 if(!(SiS_Pr->SiS_LCDInfo & LCDPass11)) {
5531 tempcx = SiS_Pr->SiS_VGAVT - SiS_Pr->PanelYRes;
5535 if(islvds) tempcx >>= 1;
5538 if( (SiS_Pr->SiS_VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) &&
5539 (!(SiS_Pr->SiS_LCDInfo & LCDPass11)) &&
5540 (SiS_Pr->PanelVRS != 999) ) {
5541 tempcx = SiS_Pr->PanelVRS;
5546 if(SiS_Pr->ChipType < SIS_315H) tempbx++;
5547 else if(issis) tempbx++;
5550 if(tempbx >= SiS_Pr->SiS_VT) tempbx -= SiS_Pr->SiS_VT;
5552 temp = tempbx & 0x00FF;
5553 if(SiS_Pr->SiS_IF_DEF_TRUMPION) {
5554 if(SiS_Pr->SiS_LCDResInfo == Panel_1024x768) {
5555 if(ModeNo == 0x10) temp = 0xa9;
5558 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x18,temp); /* BPLVRS */
5563 if(SiS_Pr->SiS_VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
5564 if(!(SiS_Pr->SiS_LCDInfo & LCDPass11)) {
5565 if(SiS_Pr->PanelVRE != 999) tempcx = SiS_Pr->PanelVRE;
5570 temp = tempcx & 0x000F;
5571 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x19,0xF0,temp); /* BPLVRE */
5573 temp = ((tempbx >> 8) & 0x07) << 3;
5574 if(SiS_Pr->SiS_IF_DEF_FSTN || SiS_Pr->SiS_IF_DEF_DSTN) {
5575 if(SiS_Pr->SiS_HDE != 640) {
5576 if(SiS_Pr->SiS_VGAVDE != SiS_Pr->SiS_VDE) temp |= 0x40;
5578 } else if(SiS_Pr->SiS_VGAVDE != SiS_Pr->SiS_VDE) temp |= 0x40;
5579 if(SiS_Pr->SiS_SetFlag & EnableLVDSDDA) temp |= 0x40;
5581 if((SiS_Pr->ChipType >= SIS_315H) ||
5582 (SiS_Pr->ChipRevision >= 0x30)) {
5584 if((SiS_Pr->SiS_IF_DEF_CH70xx == 1) && (SiS_Pr->SiS_VBInfo & SetCRT2ToTV)) {
5585 if(SiS_GetReg(SiS_Pr->SiS_Part1Port,0x00) & 0x03) temp |= 0x80;
5587 /* Chrontel 701x operates in 24bit mode (8-8-8, 2x12bit multiplexed) via VGA2 */
5588 if(SiS_Pr->SiS_LCDInfo & LCDRGB18Bit) {
5589 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCDA) {
5590 if(SiS_GetReg(SiS_Pr->SiS_P3c4,0x06) & 0x10) temp |= 0x80;
5592 if(SiS_GetReg(SiS_Pr->SiS_Part1Port,0x00) & 0x01) temp |= 0x80;
5596 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x1A,tempbx,temp);
5598 tempbx = push2; /* BPLVDEE */
5600 tempcx = SiS_Pr->SiS_LCDVDES; /* BPLVDES */
5602 if(SiS_Pr->SiS_VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
5603 switch(SiS_Pr->SiS_LCDResInfo) {
5605 tempbx = SiS_Pr->SiS_VGAVDE - 1;
5606 tempcx = SiS_Pr->SiS_VGAVDE;
5609 if(!(SiS_Pr->SiS_VBInfo & SetInSlaveMode)) {
5610 if(resinfo == SIS_RI_800x600) tempcx++;
5613 case Panel_1024x600:
5614 if(!(SiS_Pr->SiS_VBInfo & SetInSlaveMode)) {
5615 if(resinfo == SIS_RI_1024x600) tempcx++;
5616 if(SiS_Pr->SiS_LCDInfo & DontExpandLCD) {
5617 if(resinfo == SIS_RI_800x600) tempcx++;
5621 case Panel_1024x768:
5622 if(SiS_Pr->ChipType < SIS_315H) {
5623 if(!(SiS_Pr->SiS_VBInfo & SetInSlaveMode)) {
5624 if(resinfo == SIS_RI_1024x768) tempcx++;
5631 temp = ((tempbx >> 8) & 0x07) << 3;
5632 temp |= ((tempcx >> 8) & 0x07);
5633 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x1D,temp);
5634 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x1C,tempbx);
5635 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x1B,tempcx);
5637 /* Vertical scaling */
5639 if(SiS_Pr->ChipType < SIS_315H) {
5641 #ifdef CONFIG_FB_SIS_300 /* 300 series */
5642 tempeax = SiS_Pr->SiS_VGAVDE << 6;
5643 temp = (tempeax % (unsigned int)SiS_Pr->SiS_VDE);
5644 tempeax = tempeax / (unsigned int)SiS_Pr->SiS_VDE;
5647 if(SiS_Pr->SiS_SetFlag & EnableLVDSDDA) tempeax = 0x3F;
5649 temp = (unsigned short)(tempeax & 0x00FF);
5650 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x1E,temp); /* BPLVCFACT */
5652 #endif /* CONFIG_FB_SIS_300 */
5656 #ifdef CONFIG_FB_SIS_315 /* 315 series */
5657 tempeax = SiS_Pr->SiS_VGAVDE << 18;
5658 tempebx = SiS_Pr->SiS_VDE;
5659 temp = (tempeax % tempebx);
5660 tempeax = tempeax / tempebx;
5662 tempvcfact = tempeax;
5664 temp = (unsigned short)(tempeax & 0x00FF);
5665 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x37,temp);
5666 temp = (unsigned short)((tempeax & 0x00FF00) >> 8);
5667 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x36,temp);
5668 temp = (unsigned short)((tempeax & 0x00030000) >> 16);
5669 if(SiS_Pr->SiS_VDE == SiS_Pr->SiS_VGAVDE) temp |= 0x04;
5670 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x35,temp);
5672 if(SiS_Pr->SiS_VBType & VB_SISPART4SCALER) {
5673 temp = (unsigned short)(tempeax & 0x00FF);
5674 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x3c,temp);
5675 temp = (unsigned short)((tempeax & 0x00FF00) >> 8);
5676 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x3b,temp);
5677 temp = (unsigned short)(((tempeax & 0x00030000) >> 16) << 6);
5678 SiS_SetRegANDOR(SiS_Pr->SiS_Part4Port,0x3a,0x3f,temp);
5680 if(SiS_Pr->SiS_VDE != SiS_Pr->SiS_VGAVDE) temp |= 0x08;
5681 SiS_SetRegANDOR(SiS_Pr->SiS_Part4Port,0x30,0xf3,temp);
5687 /* Horizontal scaling */
5689 tempeax = SiS_Pr->SiS_VGAHDE; /* 1f = ( (VGAHDE * 65536) / ( (VGAHDE * 65536) / HDE ) ) - 1*/
5691 if(modeflag & HalfDCLK) tempeax >>= 1;
5693 tempebx = tempeax << 16;
5694 if(SiS_Pr->SiS_HDE == tempeax) {
5697 tempecx = tempebx / SiS_Pr->SiS_HDE;
5698 if(SiS_Pr->ChipType >= SIS_315H) {
5699 if(tempebx % SiS_Pr->SiS_HDE) tempecx++;
5703 if(SiS_Pr->ChipType >= SIS_315H) {
5704 tempeax = (tempebx / tempecx) - 1;
5706 tempeax = ((SiS_Pr->SiS_VGAHT << 16) / tempecx) - 1;
5708 tempecx = (tempecx << 16) | (tempeax & 0xFFFF);
5709 temp = (unsigned short)(tempecx & 0x00FF);
5710 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x1F,temp);
5712 if(SiS_Pr->ChipType >= SIS_315H) {
5713 tempeax = (SiS_Pr->SiS_VGAVDE << 18) / tempvcfact;
5714 tempbx = (unsigned short)(tempeax & 0xFFFF);
5716 tempeax = SiS_Pr->SiS_VGAVDE << 6;
5717 tempbx = tempvcfact & 0x3f;
5718 if(tempbx == 0) tempbx = 64;
5720 tempbx = (unsigned short)(tempeax & 0xFFFF);
5722 if(SiS_Pr->SiS_LCDResInfo == Panel_1024x768) tempbx--;
5723 if(SiS_Pr->SiS_SetFlag & EnableLVDSDDA) {
5724 if((!SiS_Pr->SiS_IF_DEF_FSTN) && (!SiS_Pr->SiS_IF_DEF_DSTN)) tempbx = 1;
5725 else if(SiS_Pr->SiS_LCDResInfo != Panel_640x480) tempbx = 1;
5728 temp = ((tempbx >> 8) & 0x07) << 3;
5729 temp = temp | ((tempecx >> 8) & 0x07);
5730 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x20,temp);
5731 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x21,tempbx);
5733 tempecx >>= 16; /* BPLHCFACT */
5735 if(modeflag & HalfDCLK) tempecx >>= 1;
5737 temp = (unsigned short)((tempecx & 0xFF00) >> 8);
5738 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x22,temp);
5739 temp = (unsigned short)(tempecx & 0x00FF);
5740 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x23,temp);
5742 #ifdef CONFIG_FB_SIS_315
5743 if(SiS_Pr->ChipType >= SIS_315H) {
5744 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCDA) {
5745 if((islvds) || (SiS_Pr->SiS_VBInfo & VB_SISLVDS)) {
5746 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x1e,0x20);
5750 if(SiS_Pr->ChipType == SIS_740) {
5751 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x1e,0x03);
5753 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x1e,0x23);
5760 #ifdef CONFIG_FB_SIS_300
5761 if(SiS_Pr->SiS_IF_DEF_TRUMPION) {
5762 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
5763 unsigned char *trumpdata;
5764 int i, j = crt2crtc;
5765 unsigned char TrumpMode13[4] = { 0x01, 0x10, 0x2c, 0x00 };
5766 unsigned char TrumpMode10_1[4] = { 0x01, 0x10, 0x27, 0x00 };
5767 unsigned char TrumpMode10_2[4] = { 0x01, 0x16, 0x10, 0x00 };
5769 if(SiS_Pr->SiS_UseROM) {
5770 trumpdata = &ROMAddr[0x8001 + (j * 80)];
5772 if(SiS_Pr->SiS_LCDTypeInfo == 0x0e) j += 7;
5773 trumpdata = &SiS300_TrumpionData[j][0];
5776 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x02,0xbf);
5777 for(i=0; i<5; i++) {
5778 SiS_SetTrumpionBlock(SiS_Pr, trumpdata);
5780 if(SiS_Pr->SiS_LCDResInfo == Panel_1024x768) {
5781 if(ModeNo == 0x13) {
5782 for(i=0; i<4; i++) {
5783 SiS_SetTrumpionBlock(SiS_Pr, &TrumpMode13[0]);
5785 } else if(ModeNo == 0x10) {
5786 for(i=0; i<4; i++) {
5787 SiS_SetTrumpionBlock(SiS_Pr, &TrumpMode10_1[0]);
5788 SiS_SetTrumpionBlock(SiS_Pr, &TrumpMode10_2[0]);
5792 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x02,0x40);
5796 #ifdef CONFIG_FB_SIS_315
5797 if(SiS_Pr->SiS_IF_DEF_FSTN || SiS_Pr->SiS_IF_DEF_DSTN) {
5798 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x25,0x00);
5799 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x26,0x00);
5800 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x27,0x00);
5801 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x28,0x87);
5802 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x29,0x5A);
5803 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x2A,0x4B);
5804 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x44,~0x07,0x03);
5805 tempax = SiS_Pr->SiS_HDE; /* Blps = lcdhdee(lcdhdes+HDE) + 64 */
5806 if(SiS_Pr->SiS_LCDResInfo == Panel_320x240_1 ||
5807 SiS_Pr->SiS_LCDResInfo == Panel_320x240_2 ||
5808 SiS_Pr->SiS_LCDResInfo == Panel_320x240_3) tempax >>= 1;
5810 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x38,tempax & 0xff);
5811 temp = (tempax >> 8) << 3;
5812 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x35,~0x078,temp);
5813 tempax += 32; /* Blpe = lBlps+32 */
5814 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x39,tempax & 0xff);
5815 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x3A,0x00); /* Bflml = 0 */
5816 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x3C,~0x007);
5818 tempax = SiS_Pr->SiS_VDE;
5819 if(SiS_Pr->SiS_LCDResInfo == Panel_320x240_1 ||
5820 SiS_Pr->SiS_LCDResInfo == Panel_320x240_2 ||
5821 SiS_Pr->SiS_LCDResInfo == Panel_320x240_3) tempax >>= 1;
5823 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x3B,tempax & 0xff);
5824 temp = (tempax >> 8) << 3;
5825 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x3C,~0x038,temp);
5827 tempeax = SiS_Pr->SiS_HDE;
5828 if(SiS_Pr->SiS_LCDResInfo == Panel_320x240_1 ||
5829 SiS_Pr->SiS_LCDResInfo == Panel_320x240_2 ||
5830 SiS_Pr->SiS_LCDResInfo == Panel_320x240_3) tempeax >>= 1;
5831 tempeax <<= 2; /* BDxFIFOSTOP = (HDE*4)/128 */
5832 temp = tempeax & 0x7f;
5835 temp = tempeax & 0x3f;
5836 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x45,temp);
5837 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x3F,0x00); /* BDxWadrst0 */
5838 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x3E,0x00);
5839 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x3D,0x10);
5840 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x3C,~0x040);
5842 tempax = SiS_Pr->SiS_HDE;
5843 if(SiS_Pr->SiS_LCDResInfo == Panel_320x240_1 ||
5844 SiS_Pr->SiS_LCDResInfo == Panel_320x240_2 ||
5845 SiS_Pr->SiS_LCDResInfo == Panel_320x240_3) tempax >>= 1;
5846 tempax >>= 4; /* BDxWadroff = HDE*4/8/8 */
5848 temp = tempax & 0x00FF;
5849 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x43,temp);
5850 temp = ((tempax & 0xFF00) >> 8) << 3;
5851 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port, 0x44, 0x07, temp);
5853 tempax = SiS_Pr->SiS_VDE; /* BDxWadrst1 = BDxWadrst0 + BDxWadroff * VDE */
5854 if(SiS_Pr->SiS_LCDResInfo == Panel_320x240_1 ||
5855 SiS_Pr->SiS_LCDResInfo == Panel_320x240_2 ||
5856 SiS_Pr->SiS_LCDResInfo == Panel_320x240_3) tempax >>= 1;
5857 tempeax = tempax * pushcx;
5858 temp = tempeax & 0xFF;
5859 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x42,temp);
5860 temp = (tempeax & 0xFF00) >> 8;
5861 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x41,temp);
5862 temp = ((tempeax & 0xFF0000) >> 16) | 0x10;
5863 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x40,temp);
5864 temp = ((tempeax & 0x01000000) >> 24) << 7;
5865 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port, 0x3C, 0x7F, temp);
5867 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x2F,0x03);
5868 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x03,0x50);
5869 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x04,0x00);
5870 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x2F,0x01);
5871 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x19,0x38);
5873 if(SiS_Pr->SiS_IF_DEF_FSTN) {
5874 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x2b,0x02);
5875 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x2c,0x00);
5876 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x2d,0x00);
5877 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x35,0x0c);
5878 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x36,0x00);
5879 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x37,0x00);
5880 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x38,0x80);
5881 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x39,0xA0);
5882 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x3a,0x00);
5883 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x3b,0xf0);
5884 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x3c,0x00);
5885 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x3d,0x10);
5886 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x3e,0x00);
5887 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x3f,0x00);
5888 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x40,0x10);
5889 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x41,0x25);
5890 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x42,0x80);
5891 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x43,0x14);
5892 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x44,0x03);
5893 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x45,0x0a);
5896 #endif /* CONFIG_FB_SIS_315 */
5901 SiS_SetGroup1(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex,
5902 unsigned short RefreshRateTableIndex)
5904 #if defined(CONFIG_FB_SIS_300) || defined(CONFIG_FB_SIS_315)
5905 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
5907 unsigned short temp=0, tempax=0, tempbx=0, tempcx=0, bridgeadd=0;
5908 unsigned short pushbx=0, CRT1Index=0, modeflag, resinfo=0;
5909 #ifdef CONFIG_FB_SIS_315
5910 unsigned short tempbl=0;
5913 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCDA) {
5914 SiS_SetGroup1_LVDS(SiS_Pr, ModeNo, ModeIdIndex, RefreshRateTableIndex);
5918 if(ModeNo <= 0x13) {
5919 modeflag = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_ModeFlag;
5920 } else if(SiS_Pr->UseCustomMode) {
5921 modeflag = SiS_Pr->CModeFlag;
5923 CRT1Index = SiS_GetRefCRT1CRTC(SiS_Pr, RefreshRateTableIndex, SiS_Pr->SiS_UseWideCRT2);
5924 resinfo = SiS_Pr->SiS_EModeIDTable[ModeIdIndex].Ext_RESINFO;
5925 modeflag = SiS_Pr->SiS_EModeIDTable[ModeIdIndex].Ext_ModeFlag;
5928 SiS_SetCRT2Offset(SiS_Pr, ModeNo, ModeIdIndex, RefreshRateTableIndex);
5930 if( ! ((SiS_Pr->ChipType >= SIS_315H) &&
5931 (SiS_Pr->SiS_IF_DEF_LVDS == 1) &&
5932 (SiS_Pr->SiS_VBInfo & SetInSlaveMode)) ) {
5934 if(SiS_Pr->ChipType < SIS_315H ) {
5935 #ifdef CONFIG_FB_SIS_300
5936 SiS_SetCRT2FIFO_300(SiS_Pr, ModeNo);
5939 #ifdef CONFIG_FB_SIS_315
5940 SiS_SetCRT2FIFO_310(SiS_Pr);
5944 /* 1. Horizontal setup */
5946 if(SiS_Pr->ChipType < SIS_315H ) {
5948 #ifdef CONFIG_FB_SIS_300 /* ------------- 300 series --------------*/
5950 temp = (SiS_Pr->SiS_VGAHT - 1) & 0x0FF; /* BTVGA2HT 0x08,0x09 */
5951 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x08,temp); /* CRT2 Horizontal Total */
5953 temp = (((SiS_Pr->SiS_VGAHT - 1) & 0xFF00) >> 8) << 4;
5954 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x09,0x0f,temp); /* CRT2 Horizontal Total Overflow [7:4] */
5956 temp = (SiS_Pr->SiS_VGAHDE + 12) & 0x0FF; /* BTVGA2HDEE 0x0A,0x0C */
5957 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x0A,temp); /* CRT2 Horizontal Display Enable End */
5959 pushbx = SiS_Pr->SiS_VGAHDE + 12; /* bx BTVGA2HRS 0x0B,0x0C */
5960 tempcx = (SiS_Pr->SiS_VGAHT - SiS_Pr->SiS_VGAHDE) >> 2;
5961 tempbx = pushbx + tempcx;
5967 #endif /* CONFIG_FB_SIS_300 */
5971 #ifdef CONFIG_FB_SIS_315 /* ------------------- 315/330 series --------------- */
5973 tempcx = SiS_Pr->SiS_VGAHT; /* BTVGA2HT 0x08,0x09 */
5974 if(modeflag & HalfDCLK) {
5975 if(SiS_Pr->SiS_VBType & VB_SISVB) {
5978 tempax = SiS_Pr->SiS_VGAHDE >> 1;
5979 tempcx = SiS_Pr->SiS_HT - SiS_Pr->SiS_HDE + tempax;
5980 if(SiS_Pr->SiS_LCDInfo & DontExpandLCD) {
5981 tempcx = SiS_Pr->SiS_HT - tempax;
5986 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x08,tempcx); /* CRT2 Horizontal Total */
5987 temp = (tempcx >> 4) & 0xF0;
5988 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x09,0x0F,temp); /* CRT2 Horizontal Total Overflow [7:4] */
5990 tempcx = SiS_Pr->SiS_VGAHT; /* BTVGA2HDEE 0x0A,0x0C */
5991 tempbx = SiS_Pr->SiS_VGAHDE;
5994 if(modeflag & HalfDCLK) {
6000 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x0A,tempbx); /* CRT2 Horizontal Display Enable End */
6009 if(SiS_Pr->SiS_VBType & VB_SISVB) {
6010 if(SiS_Pr->ChipType >= SIS_661) {
6011 if((SiS_Pr->SiS_LCDResInfo == Panel_1600x1200) ||
6012 (SiS_Pr->SiS_LCDResInfo == Panel_1280x1024)) {
6013 if(resinfo == SIS_RI_1280x1024) {
6014 tempcx = (tempcx & 0xff00) | 0x30;
6015 } else if(resinfo == SIS_RI_1600x1200) {
6016 tempcx = (tempcx & 0xff00) | 0xff;
6022 #endif /* CONFIG_FB_SIS_315 */
6024 } /* 315/330 series */
6026 if(SiS_Pr->SiS_VBType & VB_SISVB) {
6028 if(SiS_Pr->UseCustomMode) {
6029 tempbx = SiS_Pr->CHSyncStart + bridgeadd;
6030 tempcx = SiS_Pr->CHSyncEnd + bridgeadd;
6031 tempax = SiS_Pr->SiS_VGAHT;
6032 if(modeflag & HalfDCLK) tempax >>= 1;
6034 if(tempcx > tempax) tempcx = tempax;
6037 if(SiS_Pr->SiS_VBInfo & SetCRT2ToRAMDAC) {
6038 unsigned char cr4, cr14, cr5, cr15;
6039 if(SiS_Pr->UseCustomMode) {
6040 cr4 = SiS_Pr->CCRT1CRTC[4];
6041 cr14 = SiS_Pr->CCRT1CRTC[14];
6042 cr5 = SiS_Pr->CCRT1CRTC[5];
6043 cr15 = SiS_Pr->CCRT1CRTC[15];
6045 cr4 = SiS_Pr->SiS_CRT1Table[CRT1Index].CR[4];
6046 cr14 = SiS_Pr->SiS_CRT1Table[CRT1Index].CR[14];
6047 cr5 = SiS_Pr->SiS_CRT1Table[CRT1Index].CR[5];
6048 cr15 = SiS_Pr->SiS_CRT1Table[CRT1Index].CR[15];
6050 tempbx = ((cr4 | ((cr14 & 0xC0) << 2)) - 3) << 3; /* (VGAHRS-3)*8 */
6051 tempcx = (((cr5 & 0x1f) | ((cr15 & 0x04) << (5-2))) - 3) << 3; /* (VGAHRE-3)*8 */
6053 tempcx |= (tempbx & 0xFF00);
6054 tempbx += bridgeadd;
6055 tempcx += bridgeadd;
6056 tempax = SiS_Pr->SiS_VGAHT;
6057 if(modeflag & HalfDCLK) tempax >>= 1;
6059 if(tempcx > tempax) tempcx = tempax;
6062 if(SiS_Pr->SiS_TVMode & (TVSetNTSC1024 | TVSet525p1024)) {
6064 tempcx = 1044; /* HWCursor bug! */
6069 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x0B,tempbx); /* CRT2 Horizontal Retrace Start */
6071 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x0D,tempcx); /* CRT2 Horizontal Retrace End */
6073 temp = ((tempbx >> 8) & 0x0F) | ((pushbx >> 4) & 0xF0);
6074 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x0C,temp); /* Overflow */
6076 /* 2. Vertical setup */
6078 tempcx = SiS_Pr->SiS_VGAVT - 1;
6079 temp = tempcx & 0x00FF;
6081 if(SiS_Pr->ChipType < SIS_661) {
6082 if(SiS_Pr->SiS_IF_DEF_LVDS == 1) {
6083 if(SiS_Pr->ChipType < SIS_315H) {
6084 if(SiS_Pr->SiS_IF_DEF_CH70xx != 0) {
6085 if(SiS_Pr->SiS_VBInfo & (SetCRT2ToSVIDEO | SetCRT2ToAVIDEO)) {
6092 } else if(SiS_Pr->ChipType >= SIS_315H) {
6096 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x0E,temp); /* CRT2 Vertical Total */
6098 tempbx = SiS_Pr->SiS_VGAVDE - 1;
6099 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x0F,tempbx); /* CRT2 Vertical Display Enable End */
6101 temp = ((tempbx >> 5) & 0x38) | ((tempcx >> 8) & 0x07);
6102 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x12,temp); /* Overflow */
6104 if((SiS_Pr->ChipType >= SIS_315H) && (SiS_Pr->ChipType < SIS_661)) {
6111 if(tempcx < 4) tempcx = 4;
6116 tempbx = (SiS_Pr->SiS_VGAVT + SiS_Pr->SiS_VGAVDE) >> 1; /* BTVGA2VRS 0x10,0x11 */
6117 tempcx = ((SiS_Pr->SiS_VGAVT - SiS_Pr->SiS_VGAVDE) >> 4) + tempbx + 1; /* BTVGA2VRE 0x11 */
6120 if(SiS_Pr->SiS_VBType & VB_SISVB) {
6121 if(SiS_Pr->UseCustomMode) {
6122 tempbx = SiS_Pr->CVSyncStart;
6123 tempcx = SiS_Pr->CVSyncEnd;
6125 if(SiS_Pr->SiS_VBInfo & SetCRT2ToRAMDAC) {
6126 unsigned char cr8, cr7, cr13;
6127 if(SiS_Pr->UseCustomMode) {
6128 cr8 = SiS_Pr->CCRT1CRTC[8];
6129 cr7 = SiS_Pr->CCRT1CRTC[7];
6130 cr13 = SiS_Pr->CCRT1CRTC[13];
6131 tempcx = SiS_Pr->CCRT1CRTC[9];
6133 cr8 = SiS_Pr->SiS_CRT1Table[CRT1Index].CR[8];
6134 cr7 = SiS_Pr->SiS_CRT1Table[CRT1Index].CR[7];
6135 cr13 = SiS_Pr->SiS_CRT1Table[CRT1Index].CR[13];
6136 tempcx = SiS_Pr->SiS_CRT1Table[CRT1Index].CR[9];
6139 if(cr7 & 0x04) tempbx |= 0x0100;
6140 if(cr7 & 0x80) tempbx |= 0x0200;
6141 if(cr13 & 0x08) tempbx |= 0x0400;
6144 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x10,tempbx); /* CRT2 Vertical Retrace Start */
6146 temp = ((tempbx >> 4) & 0x70) | (tempcx & 0x0F);
6147 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x11,temp); /* CRT2 Vert. Retrace End; Overflow */
6149 /* 3. Panel delay compensation */
6151 if(SiS_Pr->ChipType < SIS_315H) {
6153 #ifdef CONFIG_FB_SIS_300 /* ---------- 300 series -------------- */
6155 if(SiS_Pr->SiS_VBType & VB_SISVB) {
6157 if(SiS_Pr->ChipType == SIS_300) {
6159 if(SiS_Pr->SiS_LCDResInfo == Panel_1024x768) temp = 0x2c;
6160 if(SiS_Pr->SiS_LCDResInfo == Panel_1280x1024) temp = 0x20;
6162 if(SiS_Pr->SiS_VBType & VB_SIS301) {
6163 if(SiS_Pr->SiS_LCDResInfo == Panel_1280x1024) temp = 0x20;
6165 if(SiS_Pr->SiS_LCDResInfo == Panel_1280x960) temp = 0x24;
6166 if(SiS_Pr->SiS_LCDResInfo == Panel_Custom) temp = 0x2c;
6167 if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) temp = 0x08;
6168 if(SiS_Pr->SiS_VBInfo & SetCRT2ToHiVision) {
6169 if(SiS_Pr->SiS_VBInfo & SetInSlaveMode) temp = 0x2c;
6172 if(SiS_Pr->SiS_UseROM) {
6173 if(ROMAddr[0x220] & 0x80) {
6174 if(SiS_Pr->SiS_VBInfo & SetCRT2ToTVNoYPbPrHiVision)
6175 temp = ROMAddr[0x221];
6176 else if(SiS_Pr->SiS_VBInfo & SetCRT2ToHiVision)
6177 temp = ROMAddr[0x222];
6178 else if(SiS_Pr->SiS_LCDResInfo == Panel_1280x1024)
6179 temp = ROMAddr[0x223];
6181 temp = ROMAddr[0x224];
6184 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) {
6185 if(SiS_Pr->PDC != -1) temp = SiS_Pr->PDC;
6190 if(!(SiS_Pr->SiS_VBInfo & SetCRT2ToTV)) {
6191 if(SiS_Pr->SiS_LCDResInfo == Panel_640x480) temp = 0x04;
6193 if(SiS_Pr->SiS_UseROM) {
6194 if(ROMAddr[0x220] & 0x80) {
6195 temp = ROMAddr[0x220];
6198 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) {
6199 if(SiS_Pr->PDC != -1) temp = SiS_Pr->PDC;
6205 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x13,~0x3C,temp); /* Panel Link Delay Compensation; (Software Command Reset; Power Saving) */
6207 #endif /* CONFIG_FB_SIS_300 */
6211 #ifdef CONFIG_FB_SIS_315 /* --------------- 315/330 series ---------------*/
6213 if(SiS_Pr->ChipType < SIS_661) {
6215 if(SiS_Pr->SiS_IF_DEF_LVDS == 1) {
6217 if(SiS_Pr->ChipType == SIS_740) temp = 0x03;
6220 if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) temp = 0x0a;
6222 if(SiS_Pr->ChipType == SIS_650) {
6223 if(SiS_Pr->SiS_IF_DEF_CH70xx != 0) {
6224 if(!(SiS_Pr->SiS_VBInfo & SetCRT2ToTV)) tempbl = 0x0F;
6228 if(SiS_Pr->SiS_IF_DEF_DSTN || SiS_Pr->SiS_IF_DEF_FSTN) {
6231 if((SiS_Pr->SiS_UseROM) && (!(SiS_Pr->SiS_ROMNew))) {
6232 if(ROMAddr[0x13c] & 0x80) tempbl = 0xf0;
6236 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x2D,tempbl,temp); /* Panel Link Delay Compensation */
6242 if(modeflag & DoubleScanMode) tempax |= 0x80;
6243 if(modeflag & HalfDCLK) tempax |= 0x40;
6244 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x2C,0x3f,tempax);
6246 #endif /* CONFIG_FB_SIS_315 */
6252 if(SiS_Pr->SiS_VBType & VB_SISVB) {
6253 if((SiS_Pr->SiS_VBType & VB_NoLCD) && (SiS_Pr->SiS_VBInfo & SetCRT2ToLCD)) {
6254 /* For 301BDH with LCD, we set up the Panel Link */
6255 SiS_SetGroup1_LVDS(SiS_Pr, ModeNo, ModeIdIndex, RefreshRateTableIndex);
6256 } else if(SiS_Pr->SiS_VBInfo & SetInSlaveMode) {
6257 SiS_SetGroup1_301(SiS_Pr, ModeNo, ModeIdIndex, RefreshRateTableIndex);
6260 if(SiS_Pr->ChipType < SIS_315H) {
6261 SiS_SetGroup1_LVDS(SiS_Pr, ModeNo, ModeIdIndex, RefreshRateTableIndex);
6263 if(SiS_Pr->SiS_IF_DEF_CH70xx != 0) {
6264 if((!(SiS_Pr->SiS_VBInfo & SetCRT2ToTV)) || (SiS_Pr->SiS_VBInfo & SetInSlaveMode)) {
6265 SiS_SetGroup1_LVDS(SiS_Pr, ModeNo,ModeIdIndex,RefreshRateTableIndex);
6268 SiS_SetGroup1_LVDS(SiS_Pr, ModeNo,ModeIdIndex,RefreshRateTableIndex);
6274 /*********************************************/
6275 /* SET PART 2 REGISTER GROUP */
6276 /*********************************************/
6278 #ifdef CONFIG_FB_SIS_315
6279 static unsigned char *
6280 SiS_GetGroup2CLVXPtr(struct SiS_Private *SiS_Pr, int tabletype)
6282 const unsigned char *tableptr = NULL;
6283 unsigned short a, b, p = 0;
6285 a = SiS_Pr->SiS_VGAHDE;
6286 b = SiS_Pr->SiS_HDE;
6288 a = SiS_Pr->SiS_VGAVDE;
6289 b = SiS_Pr->SiS_VDE;
6293 tableptr = SiS_Part2CLVX_1;
6295 tableptr = SiS_Part2CLVX_2;
6297 if(SiS_Pr->SiS_TVMode & TVSetPAL) {
6298 tableptr = SiS_Part2CLVX_4;
6300 tableptr = SiS_Part2CLVX_3;
6302 if(SiS_Pr->SiS_VBInfo & SetCRT2ToYPbPr525750) {
6303 if(SiS_Pr->SiS_TVMode & TVSetYPbPr525i) tableptr = SiS_Part2CLVX_3;
6304 else if(SiS_Pr->SiS_TVMode & TVSetYPbPr525p) tableptr = SiS_Part2CLVX_3;
6305 else tableptr = SiS_Part2CLVX_5;
6306 } else if(SiS_Pr->SiS_VBInfo & SetCRT2ToHiVision) {
6307 tableptr = SiS_Part2CLVX_6;
6310 if((tableptr[p] | tableptr[p+1] << 8) == a) break;
6312 } while((tableptr[p] | tableptr[p+1] << 8) != 0xffff);
6313 if((tableptr[p] | tableptr[p+1] << 8) == 0xffff) p -= 0x42;
6316 return ((unsigned char *)&tableptr[p]);
6320 SiS_SetGroup2_C_ELV(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex,
6321 unsigned short RefreshRateTableIndex)
6323 unsigned char *tableptr;
6327 if(!(SiS_Pr->SiS_VBType & VB_SISTAP4SCALER)) return;
6329 tableptr = SiS_GetGroup2CLVXPtr(SiS_Pr, 0);
6330 for(i = 0x80, j = 0; i <= 0xbf; i++, j++) {
6331 SiS_SetReg(SiS_Pr->SiS_Part2Port, i, tableptr[j]);
6333 if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) {
6334 tableptr = SiS_GetGroup2CLVXPtr(SiS_Pr, 1);
6335 for(i = 0xc0, j = 0; i <= 0xff; i++, j++) {
6336 SiS_SetReg(SiS_Pr->SiS_Part2Port, i, tableptr[j]);
6340 if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) temp |= 0x04;
6341 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x4e,0xeb,temp);
6345 SiS_GetCRT2Part2Ptr(struct SiS_Private *SiS_Pr,unsigned short ModeNo,unsigned short ModeIdIndex,
6346 unsigned short RefreshRateTableIndex,unsigned short *CRT2Index,
6347 unsigned short *ResIndex)
6350 if(SiS_Pr->ChipType < SIS_315H) return false;
6353 (*ResIndex) = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_CRT2CRTC;
6355 (*ResIndex) = SiS_Pr->SiS_RefIndex[RefreshRateTableIndex].Ext_CRT2CRTC;
6357 (*ResIndex) &= 0x3f;
6360 if(SiS_Pr->SiS_LCDResInfo == Panel_1024x768) {
6361 if(!(SiS_Pr->SiS_SetFlag & LCDVESATiming)) {
6366 if(SiS_Pr->SiS_CustomT == CUT_ASUSA2H_2) {
6367 if(SiS_Pr->SiS_LCDResInfo == Panel_1024x768) {
6368 if(SiS_Pr->SiS_SetFlag & LCDVESATiming) (*CRT2Index) = 206;
6371 return (((*CRT2Index) != 0));
6375 #ifdef CONFIG_FB_SIS_300
6377 SiS_Group2LCDSpecial(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short crt2crtc)
6379 unsigned short tempcx;
6380 static const unsigned char atable[] = {
6381 0xc3,0x9e,0xc3,0x9e,0x02,0x02,0x02,
6382 0xab,0x87,0xab,0x9e,0xe7,0x02,0x02
6385 if(!SiS_Pr->UseCustomMode) {
6386 if( ( ( (SiS_Pr->ChipType == SIS_630) ||
6387 (SiS_Pr->ChipType == SIS_730) ) &&
6388 (SiS_Pr->ChipRevision > 2) ) &&
6389 (SiS_Pr->SiS_LCDResInfo == Panel_1024x768) &&
6390 (!(SiS_Pr->SiS_SetFlag & LCDVESATiming)) &&
6391 (!(SiS_Pr->SiS_LCDInfo & DontExpandLCD)) ) {
6392 if(ModeNo == 0x13) {
6393 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x04,0xB9);
6394 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x05,0xCC);
6395 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x06,0xA6);
6396 } else if((crt2crtc & 0x3F) == 4) {
6397 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x01,0x2B);
6398 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x02,0x13);
6399 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x04,0xE5);
6400 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x05,0x08);
6401 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x06,0xE2);
6405 if(SiS_Pr->ChipType < SIS_315H) {
6406 if(SiS_Pr->SiS_LCDTypeInfo == 0x0c) {
6409 if(!(SiS_Pr->SiS_VBInfo & SetNotSimuMode)) {
6410 if(SiS_Pr->SiS_VBInfo & SetInSlaveMode) {
6416 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x06,0xff);
6419 if(!(SiS_Pr->SiS_VBInfo & SetNotSimuMode)) {
6420 if(SiS_Pr->SiS_VBInfo & SetInSlaveMode) {
6422 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x01,0x28);
6426 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x02,0x18);
6427 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x04,atable[tempcx]);
6433 /* For ECS A907. Highly preliminary. */
6435 SiS_Set300Part2Regs(struct SiS_Private *SiS_Pr, unsigned short ModeIdIndex, unsigned short RefreshRateTableIndex,
6436 unsigned short ModeNo)
6438 const struct SiS_Part2PortTbl *CRT2Part2Ptr = NULL;
6439 unsigned short crt2crtc, resindex;
6442 if(SiS_Pr->ChipType != SIS_300) return;
6443 if(!(SiS_Pr->SiS_VBType & VB_SIS30xBLV)) return;
6444 if(SiS_Pr->UseCustomMode) return;
6446 if(ModeNo <= 0x13) {
6447 crt2crtc = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_CRT2CRTC;
6449 crt2crtc = SiS_Pr->SiS_RefIndex[RefreshRateTableIndex].Ext_CRT2CRTC;
6452 resindex = crt2crtc & 0x3F;
6453 if(SiS_Pr->SiS_SetFlag & LCDVESATiming) CRT2Part2Ptr = SiS_Pr->SiS_CRT2Part2_1024x768_1;
6454 else CRT2Part2Ptr = SiS_Pr->SiS_CRT2Part2_1024x768_2;
6456 /* The BIOS code (1.16.51,56) is obviously a fragment! */
6458 CRT2Part2Ptr = SiS_Pr->SiS_CRT2Part2_1024x768_1;
6462 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x01,0x80,(CRT2Part2Ptr+resindex)->CR[0]);
6463 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x02,0x80,(CRT2Part2Ptr+resindex)->CR[1]);
6464 for(i = 2, j = 0x04; j <= 0x06; i++, j++ ) {
6465 SiS_SetReg(SiS_Pr->SiS_Part2Port,j,(CRT2Part2Ptr+resindex)->CR[i]);
6467 for(j = 0x1c; j <= 0x1d; i++, j++ ) {
6468 SiS_SetReg(SiS_Pr->SiS_Part2Port,j,(CRT2Part2Ptr+resindex)->CR[i]);
6470 for(j = 0x1f; j <= 0x21; i++, j++ ) {
6471 SiS_SetReg(SiS_Pr->SiS_Part2Port,j,(CRT2Part2Ptr+resindex)->CR[i]);
6473 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x23,(CRT2Part2Ptr+resindex)->CR[10]);
6474 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x25,0x0f,(CRT2Part2Ptr+resindex)->CR[11]);
6479 SiS_SetTVSpecial(struct SiS_Private *SiS_Pr, unsigned short ModeNo)
6481 if(!(SiS_Pr->SiS_VBType & VB_SIS30xBLV)) return;
6482 if(!(SiS_Pr->SiS_VBInfo & SetCRT2ToTVNoHiVision)) return;
6483 if(SiS_Pr->SiS_TVMode & (TVSetYPbPr525p | TVSetYPbPr750p)) return;
6485 if(!(SiS_Pr->SiS_TVMode & TVSetPAL)) {
6486 if(SiS_Pr->SiS_TVMode & TVSetNTSC1024) {
6487 const unsigned char specialtv[] = {
6488 0xa7,0x07,0xf2,0x6e,0x17,0x8b,0x73,0x53,
6489 0x13,0x40,0x34,0xf4,0x63,0xbb,0xcc,0x7a,
6490 0x58,0xe4,0x73,0xda,0x13
6493 for(i = 0x1c, j = 0; i <= 0x30; i++, j++) {
6494 SiS_SetReg(SiS_Pr->SiS_Part2Port,i,specialtv[j]);
6496 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x43,0x72);
6497 if(!(SiS_Pr->SiS_VBInfo & SetCRT2ToYPbPr525750)) {
6498 if(SiS_Pr->SiS_TVMode & TVSetPALM) {
6499 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x01,0x14);
6500 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x02,0x1b);
6502 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x01,0x14); /* 15 */
6503 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x02,0x1a); /* 1b */
6508 if((ModeNo == 0x38) || (ModeNo == 0x4a) || (ModeNo == 0x64) ||
6509 (ModeNo == 0x52) || (ModeNo == 0x58) || (ModeNo == 0x5c)) {
6510 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x01,0x1b); /* 21 */
6511 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x02,0x54); /* 5a */
6513 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x01,0x1a); /* 21 */
6514 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x02,0x53); /* 5a */
6520 SiS_SetGroup2_Tail(struct SiS_Private *SiS_Pr, unsigned short ModeNo)
6522 unsigned short temp;
6524 if(!(SiS_Pr->SiS_SetFlag & LCDVESATiming)) {
6525 if(SiS_Pr->SiS_VGAVDE == 525) {
6527 if(SiS_Pr->SiS_ModeType <= ModeVGA) {
6529 if(SiS_Pr->SiS_VBType & VB_SIS30xBLV) temp += 2;
6531 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x2f,temp);
6532 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x30,0xb3);
6533 } else if(SiS_Pr->SiS_VGAVDE == 420) {
6535 if(SiS_Pr->SiS_ModeType <= ModeVGA) {
6537 if(SiS_Pr->SiS_VBType & VB_SIS30xBLV) temp++;
6539 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x2f,temp);
6543 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) {
6544 if(SiS_Pr->SiS_LCDResInfo == Panel_1400x1050) {
6545 if(SiS_Pr->SiS_VBType & VB_SIS30xB) {
6546 SiS_SetRegOR(SiS_Pr->SiS_Part2Port,0x1a,0x03);
6547 /* Not always for LV, see SetGrp2 */
6550 if(ModeNo <= 0x13) temp = 3;
6551 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x0b,temp);
6554 /* 651+301C, for 1280x768 - do I really need that? */
6555 if((SiS_Pr->SiS_PanelXRes == 1280) && (SiS_Pr->SiS_PanelYRes == 768)) {
6556 if(SiS_Pr->SiS_VBInfo & SetSimuScanMode) {
6557 if(((SiS_Pr->SiS_HDE == 640) && (SiS_Pr->SiS_VDE == 480)) ||
6558 ((SiS_Pr->SiS_HDE == 320) && (SiS_Pr->SiS_VDE == 240))) {
6559 SiS_SetReg(SiS_Part2Port,0x01,0x2b);
6560 SiS_SetReg(SiS_Part2Port,0x02,0x13);
6561 SiS_SetReg(SiS_Part2Port,0x04,0xe5);
6562 SiS_SetReg(SiS_Part2Port,0x05,0x08);
6563 SiS_SetReg(SiS_Part2Port,0x06,0xe2);
6564 SiS_SetReg(SiS_Part2Port,0x1c,0x21);
6565 SiS_SetReg(SiS_Part2Port,0x1d,0x45);
6566 SiS_SetReg(SiS_Part2Port,0x1f,0x0b);
6567 SiS_SetReg(SiS_Part2Port,0x20,0x00);
6568 SiS_SetReg(SiS_Part2Port,0x21,0xa9);
6569 SiS_SetReg(SiS_Part2Port,0x23,0x0b);
6570 SiS_SetReg(SiS_Part2Port,0x25,0x04);
6579 SiS_SetGroup2(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex,
6580 unsigned short RefreshRateTableIndex)
6582 unsigned short i, j, tempax, tempbx, tempcx, tempch, tempcl, temp;
6583 unsigned short push2, modeflag, crt2crtc, bridgeoffset;
6584 unsigned int longtemp, PhaseIndex;
6586 const unsigned char *TimingPoint;
6587 #ifdef CONFIG_FB_SIS_315
6588 unsigned short resindex, CRT2Index;
6589 const struct SiS_Part2PortTbl *CRT2Part2Ptr = NULL;
6591 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCDA) return;
6594 if(ModeNo <= 0x13) {
6595 modeflag = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_ModeFlag;
6596 crt2crtc = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_CRT2CRTC;
6597 } else if(SiS_Pr->UseCustomMode) {
6598 modeflag = SiS_Pr->CModeFlag;
6601 modeflag = SiS_Pr->SiS_EModeIDTable[ModeIdIndex].Ext_ModeFlag;
6602 crt2crtc = SiS_Pr->SiS_RefIndex[RefreshRateTableIndex].Ext_CRT2CRTC;
6606 if(!(SiS_Pr->SiS_VBInfo & SetCRT2ToAVIDEO)) temp |= 0x08;
6607 if(!(SiS_Pr->SiS_VBInfo & SetCRT2ToSVIDEO)) temp |= 0x04;
6608 if(SiS_Pr->SiS_VBInfo & SetCRT2ToSCART) temp |= 0x02;
6609 if(SiS_Pr->SiS_VBInfo & SetCRT2ToHiVision) temp |= 0x01;
6611 if(!(SiS_Pr->SiS_TVMode & TVSetPAL)) temp |= 0x10;
6613 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x00,temp);
6615 PhaseIndex = 0x01; /* SiS_PALPhase */
6616 TimingPoint = SiS_Pr->SiS_PALTiming;
6619 if( (SiS_Pr->SiS_VBType & VB_SIS30xBLV) &&
6620 ( (!(SiS_Pr->SiS_VBInfo & SetInSlaveMode)) ||
6621 (SiS_Pr->SiS_TVMode & TVSetTVSimuMode) ) ) {
6625 if(SiS_Pr->SiS_VBInfo & SetCRT2ToHiVision) {
6627 TimingPoint = SiS_Pr->SiS_HiTVExtTiming;
6628 if(SiS_Pr->SiS_VBInfo & SetInSlaveMode) {
6629 TimingPoint = SiS_Pr->SiS_HiTVSt2Timing;
6630 if(SiS_Pr->SiS_TVMode & TVSetTVSimuMode) {
6631 TimingPoint = SiS_Pr->SiS_HiTVSt1Timing;
6635 } else if(SiS_Pr->SiS_VBInfo & SetCRT2ToYPbPr525750) {
6638 if(SiS_Pr->SiS_TVMode & TVSetYPbPr750p) i = 2;
6639 else if(SiS_Pr->SiS_TVMode & TVSetYPbPr525p) i = 1;
6641 TimingPoint = &SiS_YPbPrTable[i][0];
6643 PhaseIndex = 0x00; /* SiS_NTSCPhase */
6645 } else if(SiS_Pr->SiS_TVMode & TVSetPAL) {
6647 if(newtvphase) PhaseIndex = 0x09; /* SiS_PALPhase2 */
6651 TimingPoint = SiS_Pr->SiS_NTSCTiming;
6652 PhaseIndex = (SiS_Pr->SiS_TVMode & TVSetNTSCJ) ? 0x01 : 0x00; /* SiS_PALPhase : SiS_NTSCPhase */
6653 if(newtvphase) PhaseIndex += 8; /* SiS_PALPhase2 : SiS_NTSCPhase2 */
6657 if(SiS_Pr->SiS_TVMode & (TVSetPALM | TVSetPALN)) {
6658 PhaseIndex = (SiS_Pr->SiS_TVMode & TVSetPALM) ? 0x02 : 0x03; /* SiS_PALMPhase : SiS_PALNPhase */
6659 if(newtvphase) PhaseIndex += 8; /* SiS_PALMPhase2 : SiS_PALNPhase2 */
6662 if(SiS_Pr->SiS_TVMode & TVSetNTSC1024) {
6663 if(SiS_Pr->SiS_TVMode & TVSetPALM) {
6664 PhaseIndex = 0x05; /* SiS_SpecialPhaseM */
6665 } else if(SiS_Pr->SiS_TVMode & TVSetNTSCJ) {
6666 PhaseIndex = 0x11; /* SiS_SpecialPhaseJ */
6668 PhaseIndex = 0x10; /* SiS_SpecialPhase */
6672 for(i = 0x31, j = 0; i <= 0x34; i++, j++) {
6673 SiS_SetReg(SiS_Pr->SiS_Part2Port,i,SiS_TVPhase[(PhaseIndex * 4) + j]);
6676 for(i = 0x01, j = 0; i <= 0x2D; i++, j++) {
6677 SiS_SetReg(SiS_Pr->SiS_Part2Port,i,TimingPoint[j]);
6679 for(i = 0x39; i <= 0x45; i++, j++) {
6680 SiS_SetReg(SiS_Pr->SiS_Part2Port,i,TimingPoint[j]);
6683 if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) {
6684 if(SiS_Pr->SiS_ModeType != ModeText) {
6685 SiS_SetRegAND(SiS_Pr->SiS_Part2Port,0x3A,0x1F);
6689 SiS_SetRegOR(SiS_Pr->SiS_Part2Port,0x0A,SiS_Pr->SiS_NewFlickerMode);
6691 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x35,SiS_Pr->SiS_RY1COE);
6692 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x36,SiS_Pr->SiS_RY2COE);
6693 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x37,SiS_Pr->SiS_RY3COE);
6694 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x38,SiS_Pr->SiS_RY4COE);
6696 if(SiS_Pr->SiS_VBInfo & SetCRT2ToHiVision) tempax = 950;
6697 else if(SiS_Pr->SiS_TVMode & TVSetYPbPr750p) tempax = 680;
6698 else if(SiS_Pr->SiS_TVMode & TVSetPAL) tempax = 520;
6699 else tempax = 440; /* NTSC, YPbPr 525 */
6701 if( ((SiS_Pr->SiS_VBInfo & SetCRT2ToHiVision) && (SiS_Pr->SiS_VDE <= tempax)) ||
6702 ( (SiS_Pr->SiS_VBInfo & SetCRT2ToTVNoHiVision) &&
6703 ((SiS_Pr->SiS_VGAHDE == 1024) || (SiS_Pr->SiS_VDE <= tempax)) ) ) {
6705 tempax -= SiS_Pr->SiS_VDE;
6707 if(!(SiS_Pr->SiS_TVMode & (TVSetYPbPr525p | TVSetYPbPr750p))) {
6712 temp = tempax + (unsigned short)TimingPoint[0];
6713 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x01,temp);
6715 temp = tempax + (unsigned short)TimingPoint[1];
6716 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x02,temp);
6718 if((SiS_Pr->SiS_VBInfo & SetCRT2ToTVNoYPbPrHiVision) && (SiS_Pr->SiS_VGAHDE >= 1024)) {
6719 if(SiS_Pr->SiS_TVMode & TVSetPAL) {
6720 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x01,0x1b);
6721 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x02,0x54);
6723 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x01,0x17);
6724 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x02,0x1d);
6730 tempcx = SiS_Pr->SiS_HT;
6731 if(SiS_IsDualLink(SiS_Pr)) tempcx >>= 1;
6733 if(SiS_Pr->SiS_VBType & VB_SIS30xBLV) tempcx--;
6734 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x1B,tempcx);
6735 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x1D,0xF0,((tempcx >> 8) & 0x0f));
6737 tempcx = SiS_Pr->SiS_HT >> 1;
6738 if(SiS_IsDualLink(SiS_Pr)) tempcx >>= 1;
6740 if(SiS_Pr->SiS_VBInfo & SetCRT2ToHiVision) tempcx -= 4;
6741 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x22,0x0F,((tempcx << 4) & 0xf0));
6743 tempbx = TimingPoint[j] | (TimingPoint[j+1] << 8);
6745 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x24,tempbx);
6746 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x25,0x0F,((tempbx >> 4) & 0xf0));
6749 if(SiS_Pr->SiS_VBInfo & SetCRT2ToHiVision) {
6753 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x29,0x0F,((tempbx << 4) & 0xf0));
6756 tempcx += (TimingPoint[j] | (TimingPoint[j+1] << 8));
6757 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x27,tempcx);
6758 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x28,0x0F,((tempcx >> 4) & 0xf0));
6761 if(SiS_Pr->SiS_VBInfo & SetCRT2ToHiVision) tempcx -= 4;
6762 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x2A,0x0F,((tempcx << 4) & 0xf0));
6764 tempcx = SiS_Pr->SiS_HT >> 1;
6765 if(SiS_IsDualLink(SiS_Pr)) tempcx >>= 1;
6767 tempcx -= (TimingPoint[j] | ((TimingPoint[j+1]) << 8));
6768 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x2D,0x0F,((tempcx << 4) & 0xf0));
6771 if(!(SiS_Pr->SiS_VBInfo & SetCRT2ToTV)) {
6772 tempcx = SiS_GetVGAHT2(SiS_Pr) - 1;
6774 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x2E,tempcx);
6776 tempbx = SiS_Pr->SiS_VDE;
6777 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) {
6778 if(SiS_Pr->SiS_VGAVDE == 360) tempbx = 746;
6779 if(SiS_Pr->SiS_VGAVDE == 375) tempbx = 746;
6780 if(SiS_Pr->SiS_VGAVDE == 405) tempbx = 853;
6781 } else if( (SiS_Pr->SiS_VBInfo & SetCRT2ToTV) &&
6782 (!(SiS_Pr->SiS_TVMode & (TVSetYPbPr525p|TVSetYPbPr750p))) ) {
6784 if(SiS_Pr->ChipType >= SIS_315H) {
6785 if(SiS_Pr->SiS_TVMode & TVSetTVSimuMode) {
6786 if((ModeNo <= 0x13) && (crt2crtc == 1)) tempbx++;
6787 } else if(SiS_Pr->SiS_VBInfo & SetInSlaveMode) {
6788 if(SiS_Pr->SiS_ModeType <= ModeVGA) {
6789 if(crt2crtc == 4) tempbx++;
6793 if(SiS_Pr->SiS_VBInfo & SetInSlaveMode) {
6794 if(SiS_Pr->SiS_VBInfo & SetCRT2ToHiVision) {
6795 if((ModeNo == 0x2f) || (ModeNo == 0x5d) || (ModeNo == 0x5e)) tempbx++;
6797 if(!(SiS_Pr->SiS_TVMode & TVSetPAL)) {
6798 if(ModeNo == 0x03) tempbx++; /* From 1.10.7w - doesn't make sense */
6803 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x2F,tempbx);
6805 temp = (tempcx >> 8) & 0x0F;
6806 temp |= ((tempbx >> 2) & 0xC0);
6807 if(SiS_Pr->SiS_VBInfo & (SetCRT2ToSVIDEO | SetCRT2ToAVIDEO)) {
6809 if(SiS_Pr->SiS_VBInfo & SetCRT2ToAVIDEO) temp |= 0x20;
6811 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x30,temp);
6813 if(SiS_Pr->SiS_VBType & VB_SISPART4OVERFLOW) {
6814 SiS_SetRegANDOR(SiS_Pr->SiS_Part4Port,0x10,0xdf,((tempbx & 0x0400) >> 5));
6817 if(SiS_Pr->SiS_VBType & VB_SIS30xBLV) {
6818 tempbx = SiS_Pr->SiS_VDE;
6819 if( (SiS_Pr->SiS_VBInfo & SetCRT2ToTV) &&
6820 (!(SiS_Pr->SiS_TVMode & (TVSetYPbPr525p | TVSetYPbPr750p))) ) {
6824 temp = ((tempbx >> 3) & 0x60) | 0x18;
6825 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x46,temp);
6826 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x47,tempbx);
6828 if(SiS_Pr->SiS_VBType & VB_SISPART4OVERFLOW) {
6829 SiS_SetRegANDOR(SiS_Pr->SiS_Part4Port,0x10,0xbf,((tempbx & 0x0400) >> 4));
6834 if(!(modeflag & HalfDCLK)) {
6835 if(SiS_Pr->SiS_VGAHDE >= SiS_Pr->SiS_HDE) {
6841 tempch = tempcl = 0x01;
6842 if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) {
6843 if(SiS_Pr->SiS_VGAHDE >= 960) {
6844 if((!(modeflag & HalfDCLK)) || (SiS_Pr->ChipType < SIS_315H)) {
6846 if(SiS_Pr->SiS_VGAHDE >= 1280) {
6849 } else if(SiS_Pr->SiS_VGAHDE >= 1024) {
6852 tempch = 25; /* OK */
6858 if(!(tempbx & 0x20)) {
6859 if(modeflag & HalfDCLK) tempcl <<= 1;
6860 longtemp = ((SiS_Pr->SiS_VGAHDE * tempch) / tempcl) << 13;
6861 if(SiS_Pr->SiS_VBType & VB_SIS30xBLV) longtemp <<= 3;
6862 tempax = longtemp / SiS_Pr->SiS_HDE;
6863 if(longtemp % SiS_Pr->SiS_HDE) tempax++;
6864 tempbx |= ((tempax >> 8) & 0x1F);
6865 tempcx = tempax >> 13;
6868 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x44,tempax);
6869 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x45,0xC0,tempbx);
6871 if(SiS_Pr->SiS_VBType & VB_SIS30xBLV) {
6874 if(tempbx & 0x20) tempcx = 0;
6875 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x46,0xF8,tempcx);
6877 if(SiS_Pr->SiS_TVMode & TVSetPAL) {
6884 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x4B,tempbx);
6885 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x4C,tempcx);
6886 temp = (tempcx & 0x0300) >> 6;
6887 temp |= ((tempbx >> 8) & 0x03);
6888 if(SiS_Pr->SiS_VBInfo & SetCRT2ToYPbPr525750) {
6890 if(SiS_Pr->SiS_TVMode & TVSetYPbPr525p) temp |= 0x20;
6891 else if(SiS_Pr->SiS_TVMode & TVSetYPbPr750p) temp |= 0x40;
6893 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x4D,temp);
6895 temp = SiS_GetReg(SiS_Pr->SiS_Part2Port,0x43);
6896 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x43,(temp - 3));
6898 SiS_SetTVSpecial(SiS_Pr, ModeNo);
6900 if(SiS_Pr->SiS_VBType & VB_SIS30xCLV) {
6902 if(SiS_Pr->SiS_TVMode & TVSetPALM) temp = 8;
6903 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x4e,0xf7,temp);
6908 if(SiS_Pr->SiS_TVMode & TVSetPALM) {
6909 if(!(SiS_Pr->SiS_TVMode & TVSetNTSC1024)) {
6910 temp = SiS_GetReg(SiS_Pr->SiS_Part2Port,0x01);
6911 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x01,(temp - 1));
6913 SiS_SetRegAND(SiS_Pr->SiS_Part2Port,0x00,0xEF);
6916 if(SiS_Pr->SiS_VBInfo & SetCRT2ToHiVision) {
6917 if(!(SiS_Pr->SiS_VBInfo & SetInSlaveMode)) {
6918 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x0B,0x00);
6922 if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) return;
6924 /* From here: Part2 LCD setup */
6926 tempbx = SiS_Pr->SiS_HDE;
6927 if(SiS_IsDualLink(SiS_Pr)) tempbx >>= 1;
6928 tempbx--; /* RHACTE = HDE - 1 */
6929 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x2C,tempbx);
6930 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x2B,0x0F,((tempbx >> 4) & 0xf0));
6933 if(SiS_Pr->SiS_LCDResInfo == Panel_1280x1024) {
6934 if(SiS_Pr->SiS_ModeType == ModeEGA) {
6935 if(SiS_Pr->SiS_VGAHDE >= 1024) {
6937 if(SiS_Pr->SiS_SetFlag & LCDVESATiming) {
6943 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x0B,temp);
6945 tempbx = SiS_Pr->SiS_VDE - 1;
6946 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x03,tempbx);
6947 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x0C,0xF8,((tempbx >> 8) & 0x07));
6949 tempcx = SiS_Pr->SiS_VT - 1;
6950 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x19,tempcx);
6951 temp = (tempcx >> 3) & 0xE0;
6952 if(SiS_Pr->SiS_LCDInfo & LCDRGB18Bit) {
6953 /* Enable dithering; only do this for 32bpp mode */
6954 if(SiS_GetReg(SiS_Pr->SiS_Part1Port,0x00) & 0x01) {
6958 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x1A,0x0f,temp);
6960 SiS_SetRegAND(SiS_Pr->SiS_Part2Port,0x09,0xF0);
6961 SiS_SetRegAND(SiS_Pr->SiS_Part2Port,0x0A,0xF0);
6963 SiS_SetRegAND(SiS_Pr->SiS_Part2Port,0x17,0xFB);
6964 SiS_SetRegAND(SiS_Pr->SiS_Part2Port,0x18,0xDF);
6966 #ifdef CONFIG_FB_SIS_315
6967 if(SiS_GetCRT2Part2Ptr(SiS_Pr, ModeNo, ModeIdIndex, RefreshRateTableIndex,
6968 &CRT2Index, &resindex)) {
6970 case 206: CRT2Part2Ptr = SiS310_CRT2Part2_Asus1024x768_3; break;
6972 case 200: CRT2Part2Ptr = SiS_Pr->SiS_CRT2Part2_1024x768_1; break;
6975 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x01,0x80,(CRT2Part2Ptr+resindex)->CR[0]);
6976 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x02,0x80,(CRT2Part2Ptr+resindex)->CR[1]);
6977 for(i = 2, j = 0x04; j <= 0x06; i++, j++ ) {
6978 SiS_SetReg(SiS_Pr->SiS_Part2Port,j,(CRT2Part2Ptr+resindex)->CR[i]);
6980 for(j = 0x1c; j <= 0x1d; i++, j++ ) {
6981 SiS_SetReg(SiS_Pr->SiS_Part2Port,j,(CRT2Part2Ptr+resindex)->CR[i]);
6983 for(j = 0x1f; j <= 0x21; i++, j++ ) {
6984 SiS_SetReg(SiS_Pr->SiS_Part2Port,j,(CRT2Part2Ptr+resindex)->CR[i]);
6986 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x23,(CRT2Part2Ptr+resindex)->CR[10]);
6987 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x25,0x0f,(CRT2Part2Ptr+resindex)->CR[11]);
6989 SiS_SetGroup2_Tail(SiS_Pr, ModeNo);
6994 /* Checked for 1024x768, 1280x1024, 1400x1050, 1600x1200 */
6995 /* Clevo dual-link 1024x768 */
6996 /* Compaq 1280x1024 has HT 1696 sometimes (calculation OK, if given HT is correct) */
6997 /* Acer: OK, but uses different setting for VESA timing at 640/800/1024 and 640x400 */
6999 if(SiS_Pr->SiS_LCDInfo & DontExpandLCD) {
7000 if((SiS_Pr->SiS_LCDInfo & LCDPass11) || (SiS_Pr->PanelYRes == SiS_Pr->SiS_VDE)) {
7001 tempbx = SiS_Pr->SiS_VDE - 1;
7002 tempcx = SiS_Pr->SiS_VT - 1;
7004 tempbx = SiS_Pr->SiS_VDE + ((SiS_Pr->PanelYRes - SiS_Pr->SiS_VDE) / 2);
7005 tempcx = SiS_Pr->SiS_VT - ((SiS_Pr->PanelYRes - SiS_Pr->SiS_VDE) / 2);
7008 tempbx = SiS_Pr->PanelYRes;
7009 tempcx = SiS_Pr->SiS_VT;
7011 if(SiS_Pr->PanelYRes != SiS_Pr->SiS_VDE) {
7012 tempax = SiS_Pr->PanelYRes;
7013 /* if(SiS_Pr->SiS_VGAVDE == 525) tempax += 0x3c; */ /* 651+301C */
7014 if(SiS_Pr->PanelYRes < SiS_Pr->SiS_VDE) {
7015 tempax = tempcx = 0;
7017 tempax -= SiS_Pr->SiS_VDE;
7021 tempcx -= tempax; /* lcdvdes */
7022 tempbx -= tempax; /* lcdvdee */
7025 /* Non-expanding: lcdvdes = tempcx = VT-1; lcdvdee = tempbx = VDE-1 */
7027 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x05,tempcx); /* lcdvdes */
7028 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x06,tempbx); /* lcdvdee */
7030 temp = (tempbx >> 5) & 0x38;
7031 temp |= ((tempcx >> 8) & 0x07);
7032 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x02,temp);
7034 tempax = SiS_Pr->SiS_VDE;
7035 if((SiS_Pr->SiS_LCDInfo & DontExpandLCD) && (!(SiS_Pr->SiS_LCDInfo & LCDPass11))) {
7036 tempax = SiS_Pr->PanelYRes;
7038 tempcx = (SiS_Pr->SiS_VT - tempax) >> 4;
7039 if((SiS_Pr->SiS_LCDInfo & DontExpandLCD) && (!(SiS_Pr->SiS_LCDInfo & LCDPass11))) {
7040 if(SiS_Pr->PanelYRes != SiS_Pr->SiS_VDE) {
7041 tempcx = (SiS_Pr->SiS_VT - tempax) / 10;
7045 tempbx = ((SiS_Pr->SiS_VT + SiS_Pr->SiS_VDE) >> 1) - 1;
7046 if(SiS_Pr->SiS_LCDInfo & DontExpandLCD) {
7047 if(SiS_Pr->PanelYRes != SiS_Pr->SiS_VDE) {
7048 if(!(SiS_Pr->SiS_LCDInfo & LCDPass11)) { /* ? */
7049 tempax = SiS_Pr->SiS_VT - SiS_Pr->PanelYRes;
7050 if(tempax % 4) { tempax >>= 2; tempax++; }
7051 else { tempax >>= 2; }
7052 tempbx -= (tempax - 1);
7055 if(tempbx <= SiS_Pr->SiS_VDE) tempbx = SiS_Pr->SiS_VDE + 1;
7059 if(SiS_Pr->SiS_LCDResInfo == Panel_1024x768) {
7061 if((!(SiS_Pr->SiS_LCDInfo & DontExpandLCD)) || (crt2crtc == 6)) {
7062 if(SiS_Pr->SiS_SetFlag & LCDVESATiming) {
7069 /* non-expanding: lcdvrs = ((VT + VDE) / 2) - 10 */
7071 if(SiS_Pr->UseCustomMode) {
7072 tempbx = SiS_Pr->CVSyncStart;
7075 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x04,tempbx); /* lcdvrs */
7077 temp = (tempbx >> 4) & 0xF0;
7078 tempbx += (tempcx + 1);
7079 temp |= (tempbx & 0x0F);
7081 if(SiS_Pr->UseCustomMode) {
7083 temp |= (SiS_Pr->CVSyncEnd & 0x0f);
7086 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x01,temp);
7088 #ifdef CONFIG_FB_SIS_300
7089 SiS_Group2LCDSpecial(SiS_Pr, ModeNo, crt2crtc);
7093 if(SiS_Pr->SiS_VBType & VB_SIS30xBLV) bridgeoffset += 2;
7094 if(SiS_Pr->SiS_VBType & VB_SIS30xCLV) bridgeoffset += 2; /* OK for Averatec 1280x800 (301C) */
7095 if(SiS_IsDualLink(SiS_Pr)) bridgeoffset++;
7096 else if(SiS_Pr->SiS_VBType & VB_SIS302LV) bridgeoffset++; /* OK for Asus A4L 1280x800 */
7097 /* Higher bridgeoffset shifts to the LEFT */
7100 if((SiS_Pr->SiS_LCDInfo & DontExpandLCD) && (!(SiS_Pr->SiS_LCDInfo & LCDPass11))) {
7101 if(SiS_Pr->PanelXRes != SiS_Pr->SiS_HDE) {
7102 temp = SiS_Pr->SiS_HT - ((SiS_Pr->PanelXRes - SiS_Pr->SiS_HDE) / 2);
7103 if(SiS_IsDualLink(SiS_Pr)) temp >>= 1;
7106 temp += bridgeoffset;
7107 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x1F,temp); /* lcdhdes */
7108 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x20,0x0F,((temp >> 4) & 0xf0));
7110 tempcx = SiS_Pr->SiS_HT;
7111 tempax = tempbx = SiS_Pr->SiS_HDE;
7112 if((SiS_Pr->SiS_LCDInfo & DontExpandLCD) && (!(SiS_Pr->SiS_LCDInfo & LCDPass11))) {
7113 if(SiS_Pr->PanelXRes != SiS_Pr->SiS_HDE) {
7114 tempax = SiS_Pr->PanelXRes;
7115 tempbx = SiS_Pr->PanelXRes - ((SiS_Pr->PanelXRes - SiS_Pr->SiS_HDE) / 2);
7118 if(SiS_IsDualLink(SiS_Pr)) {
7124 tempbx += bridgeoffset;
7126 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x23,tempbx); /* lcdhdee */
7127 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x25,0xF0,((tempbx >> 8) & 0x0f));
7129 tempcx = (tempcx - tempax) >> 2;
7134 if(SiS_Pr->SiS_LCDResInfo == Panel_1280x1024) {
7135 if(SiS_Pr->SiS_LCDInfo & DontExpandLCD) {
7136 if(SiS_Pr->SiS_LCDInfo & LCDPass11) {
7137 if(SiS_Pr->SiS_HDE == 1280) tempbx = (tempbx & 0xff00) | 0x47;
7142 if(SiS_Pr->UseCustomMode) {
7143 tempbx = SiS_Pr->CHSyncStart;
7144 if(modeflag & HalfDCLK) tempbx <<= 1;
7145 if(SiS_IsDualLink(SiS_Pr)) tempbx >>= 1;
7146 tempbx += bridgeoffset;
7149 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x1C,tempbx); /* lcdhrs */
7150 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x1D,0x0F,((tempbx >> 4) & 0xf0));
7155 if((SiS_Pr->SiS_LCDInfo & DontExpandLCD) && (!(SiS_Pr->SiS_LCDInfo & LCDPass11))) {
7156 if(SiS_Pr->PanelXRes != SiS_Pr->SiS_HDE) tempcx >>= 2;
7160 if(SiS_Pr->UseCustomMode) {
7161 tempbx = SiS_Pr->CHSyncEnd;
7162 if(modeflag & HalfDCLK) tempbx <<= 1;
7163 if(SiS_IsDualLink(SiS_Pr)) tempbx >>= 1;
7164 tempbx += bridgeoffset;
7167 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x21,tempbx); /* lcdhre */
7169 SiS_SetGroup2_Tail(SiS_Pr, ModeNo);
7171 #ifdef CONFIG_FB_SIS_300
7172 SiS_Set300Part2Regs(SiS_Pr, ModeIdIndex, RefreshRateTableIndex, ModeNo);
7174 #ifdef CONFIG_FB_SIS_315
7175 } /* CRT2-LCD from table */
7179 /*********************************************/
7180 /* SET PART 3 REGISTER GROUP */
7181 /*********************************************/
7184 SiS_SetGroup3(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex)
7187 const unsigned char *tempdi;
7189 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCDA) return;
7192 SiS_SetReg(SiS_Pr->SiS_Part3Port,0x00,0x00);
7197 if(SiS_Pr->SiS_TVMode & TVSetPAL) {
7198 SiS_SetReg(SiS_Pr->SiS_Part3Port,0x13,0xFA);
7199 SiS_SetReg(SiS_Pr->SiS_Part3Port,0x14,0xC8);
7201 SiS_SetReg(SiS_Pr->SiS_Part3Port,0x13,0xF5);
7202 SiS_SetReg(SiS_Pr->SiS_Part3Port,0x14,0xB7);
7205 if(SiS_Pr->SiS_TVMode & TVSetPALM) {
7206 SiS_SetReg(SiS_Pr->SiS_Part3Port,0x13,0xFA);
7207 SiS_SetReg(SiS_Pr->SiS_Part3Port,0x14,0xC8);
7208 SiS_SetReg(SiS_Pr->SiS_Part3Port,0x3D,0xA8);
7212 if(SiS_Pr->SiS_VBInfo & SetCRT2ToHiVision) {
7213 tempdi = SiS_Pr->SiS_HiTVGroup3Data;
7214 if(SiS_Pr->SiS_TVMode & TVSetTVSimuMode) {
7215 tempdi = SiS_Pr->SiS_HiTVGroup3Simu;
7217 } else if(SiS_Pr->SiS_VBInfo & SetCRT2ToYPbPr525750) {
7218 if(!(SiS_Pr->SiS_TVMode & TVSetYPbPr525i)) {
7219 tempdi = SiS_HiTVGroup3_1;
7220 if(SiS_Pr->SiS_TVMode & TVSetYPbPr750p) tempdi = SiS_HiTVGroup3_2;
7224 for(i=0; i<=0x3E; i++) {
7225 SiS_SetReg(SiS_Pr->SiS_Part3Port,i,tempdi[i]);
7227 if(SiS_Pr->SiS_VBType & VB_SIS30xCLV) {
7228 if(SiS_Pr->SiS_TVMode & TVSetYPbPr525p) {
7229 SiS_SetReg(SiS_Pr->SiS_Part3Port,0x28,0x3f);
7239 /*********************************************/
7240 /* SET PART 4 REGISTER GROUP */
7241 /*********************************************/
7243 #ifdef CONFIG_FB_SIS_315
7246 SiS_ShiftXPos(struct SiS_Private *SiS_Pr, int shift)
7248 unsigned short temp, temp1, temp2;
7250 temp1 = SiS_GetReg(SiS_Pr->SiS_Part2Port,0x1f);
7251 temp2 = SiS_GetReg(SiS_Pr->SiS_Part2Port,0x20);
7252 temp = (unsigned short)((int)((temp1 | ((temp2 & 0xf0) << 4))) + shift);
7253 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x1f,temp);
7254 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x20,0x0f,((temp >> 4) & 0xf0));
7255 temp = SiS_GetReg(SiS_Pr->SiS_Part2Port,0x2b) & 0x0f;
7256 temp = (unsigned short)((int)(temp) + shift);
7257 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x2b,0xf0,(temp & 0x0f));
7258 temp1 = SiS_GetReg(SiS_Pr->SiS_Part2Port,0x43);
7259 temp2 = SiS_GetReg(SiS_Pr->SiS_Part2Port,0x42);
7260 temp = (unsigned short)((int)((temp1 | ((temp2 & 0xf0) << 4))) + shift);
7261 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x43,temp);
7262 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x42,0x0f,((temp >> 4) & 0xf0));
7267 SiS_SetGroup4_C_ELV(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex)
7269 unsigned short temp, temp1;
7270 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
7272 if(!(SiS_Pr->SiS_VBType & VB_SIS30xCLV)) return;
7273 if(!(SiS_Pr->SiS_VBInfo & (SetCRT2ToHiVision | SetCRT2ToYPbPr525750))) return;
7275 if(SiS_Pr->ChipType >= XGI_20) return;
7277 if((SiS_Pr->ChipType >= SIS_661) && (SiS_Pr->SiS_ROMNew)) {
7278 if(!(ROMAddr[0x61] & 0x04)) return;
7281 SiS_SetRegOR(SiS_Pr->SiS_Part4Port,0x3a,0x08);
7282 temp = SiS_GetReg(SiS_Pr->SiS_Part4Port,0x3a);
7283 if(!(temp & 0x01)) {
7284 SiS_SetRegAND(SiS_Pr->SiS_Part4Port,0x3a,0xdf);
7285 SiS_SetRegAND(SiS_Pr->SiS_Part4Port,0x25,0xfc);
7286 if((SiS_Pr->ChipType < SIS_661) && (!(SiS_Pr->SiS_ROMNew))) {
7287 SiS_SetRegAND(SiS_Pr->SiS_Part4Port,0x25,0xf8);
7289 SiS_SetRegAND(SiS_Pr->SiS_Part4Port,0x0f,0xfb);
7290 if(SiS_Pr->SiS_TVMode & TVSetYPbPr750p) temp = 0x0000;
7291 else if(SiS_Pr->SiS_TVMode & TVSetYPbPr525p) temp = 0x0002;
7292 else if(SiS_Pr->SiS_TVMode & TVSetHiVision) temp = 0x0400;
7294 if((SiS_Pr->ChipType >= SIS_661) || (SiS_Pr->SiS_ROMNew)) {
7296 if(SiS_Pr->SiS_TVMode & TVAspect43) temp1 = 4;
7297 SiS_SetRegANDOR(SiS_Pr->SiS_Part4Port,0x0f,0xfb,temp1);
7298 if(SiS_Pr->SiS_TVMode & TVAspect43LB) temp |= 0x01;
7299 SiS_SetRegANDOR(SiS_Pr->SiS_Part4Port,0x26,0x7c,(temp & 0xff));
7300 SiS_SetRegANDOR(SiS_Pr->SiS_Part4Port,0x3a,0xfb,(temp >> 8));
7302 SiS_SetRegAND(SiS_Pr->SiS_P3d4,0x39,0xfd);
7305 temp1 = SiS_GetReg(SiS_Pr->SiS_P3d4,0x3b) & 0x03;
7306 if(temp1 == 0x01) temp |= 0x01;
7307 if(temp1 == 0x03) temp |= 0x04; /* ? why not 0x10? */
7308 SiS_SetRegANDOR(SiS_Pr->SiS_Part4Port,0x26,0xf8,(temp & 0xff));
7309 SiS_SetRegANDOR(SiS_Pr->SiS_Part4Port,0x3a,0xfb,(temp >> 8));
7311 SiS_SetRegAND(SiS_Pr->SiS_Part4Port,0x3b,0xfd);
7316 if(SiS_Pr->ChipType >= SIS_661) { /* ? */
7317 if(SiS_Pr->SiS_TVMode & TVAspect43) {
7318 if(SiS_Pr->SiS_TVMode & TVSetYPbPr750p) {
7319 if(resinfo == SIS_RI_1024x768) {
7320 SiS_ShiftXPos(SiS_Pr, 97);
7322 SiS_ShiftXPos(SiS_Pr, 111);
7324 } else if(SiS_Pr->SiS_TVMode & TVSetHiVision) {
7325 SiS_ShiftXPos(SiS_Pr, 136);
7337 SiS_SetCRT2VCLK(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex,
7338 unsigned short RefreshRateTableIndex)
7340 unsigned short vclkindex, temp, reg1, reg2;
7342 if(SiS_Pr->UseCustomMode) {
7343 reg1 = SiS_Pr->CSR2B;
7344 reg2 = SiS_Pr->CSR2C;
7346 vclkindex = SiS_GetVCLK2Ptr(SiS_Pr, ModeNo, ModeIdIndex, RefreshRateTableIndex);
7347 reg1 = SiS_Pr->SiS_VBVCLKData[vclkindex].Part4_A;
7348 reg2 = SiS_Pr->SiS_VBVCLKData[vclkindex].Part4_B;
7351 if(SiS_Pr->SiS_VBType & VB_SIS30xBLV) {
7352 if(SiS_Pr->SiS_TVMode & (TVSetNTSC1024 | TVSet525p1024)) {
7353 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x0a,0x57);
7354 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x0b,0x46);
7355 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x1f,0xf6);
7357 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x0a,reg1);
7358 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x0b,reg2);
7361 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x0a,0x01);
7362 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x0b,reg2);
7363 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x0a,reg1);
7365 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x12,0x00);
7367 if(SiS_Pr->SiS_VBInfo & SetCRT2ToRAMDAC) temp |= 0x20;
7368 SiS_SetRegOR(SiS_Pr->SiS_Part4Port,0x12,temp);
7372 SiS_SetDualLinkEtc(struct SiS_Private *SiS_Pr)
7374 if(SiS_Pr->ChipType >= SIS_315H) {
7375 if(SiS_Pr->SiS_VBType & VB_SISDUALLINK) {
7376 if((SiS_CRT2IsLCD(SiS_Pr)) ||
7377 (SiS_IsVAMode(SiS_Pr))) {
7378 if(SiS_Pr->SiS_LCDInfo & LCDDualLink) {
7379 SiS_SetRegOR(SiS_Pr->SiS_Part4Port,0x27,0x2c);
7381 SiS_SetRegAND(SiS_Pr->SiS_Part4Port,0x27,~0x20);
7386 if(SiS_Pr->SiS_VBType & VB_SISEMI) {
7387 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x2a,0x00);
7389 SiS_SetRegAND(SiS_Pr->SiS_Part4Port,0x30,0x0c);
7391 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x34,0x10);
7396 SiS_SetGroup4(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex,
7397 unsigned short RefreshRateTableIndex)
7399 unsigned short tempax, tempcx, tempbx, modeflag, temp, resinfo;
7400 unsigned int tempebx, tempeax, templong;
7402 if(ModeNo <= 0x13) {
7403 modeflag = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_ModeFlag;
7404 resinfo = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_ResInfo;
7405 } else if(SiS_Pr->UseCustomMode) {
7406 modeflag = SiS_Pr->CModeFlag;
7409 modeflag = SiS_Pr->SiS_EModeIDTable[ModeIdIndex].Ext_ModeFlag;
7410 resinfo = SiS_Pr->SiS_EModeIDTable[ModeIdIndex].Ext_RESINFO;
7413 if(SiS_Pr->ChipType >= SIS_315H) {
7414 if(SiS_Pr->SiS_VBType & VB_SISLVDS) {
7415 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCDA) {
7416 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x24,0x0e);
7421 if(SiS_Pr->SiS_VBType & (VB_SIS30xCLV | VB_SIS302LV)) {
7422 if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) {
7423 SiS_SetRegAND(SiS_Pr->SiS_Part4Port,0x10,0x9f);
7427 if(SiS_Pr->ChipType >= SIS_315H) {
7428 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCDA) {
7429 SiS_SetDualLinkEtc(SiS_Pr);
7434 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x13,SiS_Pr->SiS_RVBHCFACT);
7436 tempbx = SiS_Pr->SiS_RVBHCMAX;
7437 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x14,tempbx);
7439 temp = (tempbx >> 1) & 0x80;
7441 tempcx = SiS_Pr->SiS_VGAHT - 1;
7442 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x16,tempcx);
7444 temp |= ((tempcx >> 5) & 0x78);
7446 tempcx = SiS_Pr->SiS_VGAVT - 1;
7447 if(!(SiS_Pr->SiS_VBInfo & SetCRT2ToTV)) tempcx -= 5;
7448 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x17,tempcx);
7450 temp |= ((tempcx >> 8) & 0x07);
7451 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x15,temp);
7453 tempbx = SiS_Pr->SiS_VGAHDE;
7454 if(modeflag & HalfDCLK) tempbx >>= 1;
7455 if(SiS_IsDualLink(SiS_Pr)) tempbx >>= 1;
7457 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) {
7459 if(tempbx > 800) temp = 0x60;
7460 } else if(SiS_Pr->SiS_VBInfo & SetCRT2ToHiVision) {
7462 if(tempbx > 1024) temp = 0xC0;
7463 else if(tempbx >= 960) temp = 0xA0;
7464 } else if(SiS_Pr->SiS_TVMode & (TVSetYPbPr525p | TVSetYPbPr750p)) {
7466 if(tempbx >= 1280) temp = 0x40;
7467 else if(tempbx >= 1024) temp = 0x20;
7470 if(tempbx >= 1024) temp = 0xA0;
7473 temp |= SiS_Pr->Init_P4_0E;
7475 if(SiS_Pr->SiS_VBType & VB_SIS301) {
7476 if(SiS_Pr->SiS_LCDResInfo != Panel_1280x1024) {
7482 SiS_SetRegANDOR(SiS_Pr->SiS_Part4Port,0x0E,0x10,temp);
7484 tempeax = SiS_Pr->SiS_VGAVDE;
7485 tempebx = SiS_Pr->SiS_VDE;
7486 if(SiS_Pr->SiS_VBInfo & SetCRT2ToHiVision) {
7487 if(!(temp & 0xE0)) tempebx >>=1;
7490 tempcx = SiS_Pr->SiS_RVBHRS;
7491 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x18,tempcx);
7495 if(tempeax <= tempebx) {
7501 tempeax *= (256 * 1024);
7502 templong = tempeax % tempebx;
7504 if(templong) tempeax++;
7506 temp = (unsigned short)(tempeax & 0x000000FF);
7507 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x1B,temp);
7508 temp = (unsigned short)((tempeax & 0x0000FF00) >> 8);
7509 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x1A,temp);
7510 temp = (unsigned short)((tempeax >> 12) & 0x70); /* sic! */
7511 temp |= (tempcx & 0x4F);
7512 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x19,temp);
7514 if(SiS_Pr->SiS_VBType & VB_SIS30xBLV) {
7516 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x1C,0x28);
7518 /* Calc Linebuffer max address and set/clear decimode */
7520 if(SiS_Pr->SiS_TVMode & (TVSetHiVision | TVSetYPbPr750p)) tempbx = 0x08;
7521 tempax = SiS_Pr->SiS_VGAHDE;
7522 if(modeflag & HalfDCLK) tempax >>= 1;
7523 if(SiS_IsDualLink(SiS_Pr)) tempax >>= 1;
7525 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) {
7529 if(tempax == 960) tempax *= 25; /* Correct */
7530 else if(tempax == 1024) tempax *= 25;
7536 if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) {
7537 if(resinfo == SIS_RI_1024x768 ||
7538 resinfo == SIS_RI_1024x576 ||
7539 resinfo == SIS_RI_1280x1024 ||
7540 resinfo == SIS_RI_1280x720) {
7541 /* Otherwise white line or garbage at right edge */
7542 tempax = (tempax & 0xff00) | 0x20;
7548 temp = ((tempax >> 4) & 0x30) | tempbx;
7549 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x1D,tempax);
7550 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x1E,temp);
7552 temp = 0x0036; tempbx = 0xD0;
7553 if((SiS_Pr->ChipType >= SIS_315H) && (SiS_Pr->SiS_VBType & VB_SISLVDS)) {
7554 temp = 0x0026; tempbx = 0xC0; /* See En/DisableBridge() */
7556 if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) {
7557 if(!(SiS_Pr->SiS_TVMode & (TVSetNTSC1024 | TVSetHiVision | TVSetYPbPr750p | TVSetYPbPr525p))) {
7559 if(SiS_Pr->SiS_VBInfo & SetInSlaveMode) {
7560 if(!(SiS_Pr->SiS_TVMode & TVSetTVSimuMode)) {
7566 SiS_SetRegANDOR(SiS_Pr->SiS_Part4Port,0x1F,tempbx,temp);
7568 tempbx = SiS_Pr->SiS_HT >> 1;
7569 if(SiS_IsDualLink(SiS_Pr)) tempbx >>= 1;
7571 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x22,tempbx);
7572 temp = (tempbx >> 5) & 0x38;
7573 SiS_SetRegANDOR(SiS_Pr->SiS_Part4Port,0x21,0xC0,temp);
7575 if(SiS_Pr->SiS_VBType & VB_SISLVDS) {
7576 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) {
7577 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x24,0x0e);
7578 /* LCD-too-dark-error-source, see FinalizeLCD() */
7582 SiS_SetDualLinkEtc(SiS_Pr);
7586 SiS_SetCRT2VCLK(SiS_Pr, ModeNo, ModeIdIndex, RefreshRateTableIndex);
7589 /*********************************************/
7590 /* SET PART 5 REGISTER GROUP */
7591 /*********************************************/
7594 SiS_SetGroup5(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex)
7597 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCDA) return;
7599 if(SiS_Pr->SiS_ModeType == ModeVGA) {
7600 if(!(SiS_Pr->SiS_VBInfo & (SetInSlaveMode | LoadDACFlag))) {
7601 SiS_SetRegOR(SiS_Pr->SiS_P3c4,0x1E,0x20);
7602 SiS_LoadDAC(SiS_Pr, ModeNo, ModeIdIndex);
7607 /*********************************************/
7608 /* MODIFY CRT1 GROUP FOR SLAVE MODE */
7609 /*********************************************/
7612 SiS_GetLVDSCRT1Ptr(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex,
7613 unsigned short RefreshRateTableIndex, unsigned short *ResIndex,
7614 unsigned short *DisplayType)
7616 unsigned short modeflag = 0;
7617 bool checkhd = true;
7619 /* Pass 1:1 not supported here */
7621 if(ModeNo <= 0x13) {
7622 modeflag = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_ModeFlag;
7623 (*ResIndex) = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_CRT2CRTC;
7625 modeflag = SiS_Pr->SiS_EModeIDTable[ModeIdIndex].Ext_ModeFlag;
7626 (*ResIndex) = SiS_Pr->SiS_RefIndex[RefreshRateTableIndex].Ext_CRT2CRTC;
7629 (*ResIndex) &= 0x3F;
7631 if((SiS_Pr->SiS_IF_DEF_CH70xx) && (SiS_Pr->SiS_VBInfo & SetCRT2ToTV)) {
7633 (*DisplayType) = 80;
7634 if((SiS_Pr->SiS_TVMode & TVSetPAL) && (!(SiS_Pr->SiS_TVMode & TVSetPALM))) {
7635 (*DisplayType) = 82;
7636 if(SiS_Pr->SiS_ModeType > ModeVGA) {
7637 if(SiS_Pr->SiS_CHSOverScan) (*DisplayType) = 84;
7640 if((*DisplayType) != 84) {
7641 if(SiS_Pr->SiS_TVMode & TVSetCHOverScan) (*DisplayType)++;
7647 switch(SiS_Pr->SiS_LCDResInfo) {
7648 case Panel_320x240_1: (*DisplayType) = 50;
7651 case Panel_320x240_2: (*DisplayType) = 14;
7653 case Panel_320x240_3: (*DisplayType) = 18;
7655 case Panel_640x480: (*DisplayType) = 10;
7657 case Panel_1024x600: (*DisplayType) = 26;
7659 default: return true;
7663 if(modeflag & HalfDCLK) (*DisplayType)++;
7666 if(SiS_Pr->SiS_LCDResInfo == Panel_1024x600) {
7667 if(SiS_Pr->SiS_LCDInfo & DontExpandLCD) (*DisplayType) += 2;
7676 SiS_ModCRT1CRTC(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex,
7677 unsigned short RefreshRateTableIndex)
7679 unsigned short tempah, i, modeflag, j, ResIndex, DisplayType;
7680 const struct SiS_LVDSCRT1Data *LVDSCRT1Ptr=NULL;
7681 static const unsigned short CRIdx[] = {
7682 0x00, 0x02, 0x03, 0x04, 0x05, 0x06,
7683 0x07, 0x10, 0x11, 0x15, 0x16
7686 if((SiS_Pr->SiS_CustomT == CUT_BARCO1366) ||
7687 (SiS_Pr->SiS_CustomT == CUT_BARCO1024) ||
7688 (SiS_Pr->SiS_CustomT == CUT_PANEL848) ||
7689 (SiS_Pr->SiS_CustomT == CUT_PANEL856) )
7692 if(SiS_Pr->SiS_IF_DEF_LVDS) {
7693 if(!(SiS_Pr->SiS_VBInfo & SetCRT2ToLCDA)) {
7694 if(!(SiS_Pr->SiS_VBInfo & SetInSlaveMode)) return;
7696 } else if(SiS_Pr->SiS_VBType & VB_SISVB) {
7697 if(!(SiS_Pr->SiS_VBInfo & SetInSlaveMode)) return;
7700 if(SiS_Pr->SiS_LCDInfo & LCDPass11) return;
7702 if(SiS_Pr->ChipType < SIS_315H) {
7703 if(SiS_Pr->SiS_SetFlag & SetDOSMode) return;
7706 if(!(SiS_GetLVDSCRT1Ptr(SiS_Pr, ModeNo, ModeIdIndex, RefreshRateTableIndex,
7707 &ResIndex, &DisplayType))) {
7711 switch(DisplayType) {
7712 case 50: LVDSCRT1Ptr = SiS_Pr->SiS_LVDSCRT1320x240_1; break; /* xSTN */
7713 case 14: LVDSCRT1Ptr = SiS_Pr->SiS_LVDSCRT1320x240_2; break; /* xSTN */
7714 case 15: LVDSCRT1Ptr = SiS_Pr->SiS_LVDSCRT1320x240_2_H; break; /* xSTN */
7715 case 18: LVDSCRT1Ptr = SiS_Pr->SiS_LVDSCRT1320x240_3; break; /* xSTN */
7716 case 19: LVDSCRT1Ptr = SiS_Pr->SiS_LVDSCRT1320x240_3_H; break; /* xSTN */
7717 case 10: LVDSCRT1Ptr = SiS_Pr->SiS_LVDSCRT1640x480_1; break;
7718 case 11: LVDSCRT1Ptr = SiS_Pr->SiS_LVDSCRT1640x480_1_H; break;
7719 #if 0 /* Works better with calculated numbers */
7720 case 26: LVDSCRT1Ptr = SiS_Pr->SiS_LVDSCRT11024x600_1; break;
7721 case 27: LVDSCRT1Ptr = SiS_Pr->SiS_LVDSCRT11024x600_1_H; break;
7722 case 28: LVDSCRT1Ptr = SiS_Pr->SiS_LVDSCRT11024x600_2; break;
7723 case 29: LVDSCRT1Ptr = SiS_Pr->SiS_LVDSCRT11024x600_2_H; break;
7725 case 80: LVDSCRT1Ptr = SiS_Pr->SiS_CHTVCRT1UNTSC; break;
7726 case 81: LVDSCRT1Ptr = SiS_Pr->SiS_CHTVCRT1ONTSC; break;
7727 case 82: LVDSCRT1Ptr = SiS_Pr->SiS_CHTVCRT1UPAL; break;
7728 case 83: LVDSCRT1Ptr = SiS_Pr->SiS_CHTVCRT1OPAL; break;
7729 case 84: LVDSCRT1Ptr = SiS_Pr->SiS_CHTVCRT1SOPAL; break;
7734 SiS_SetRegAND(SiS_Pr->SiS_P3d4,0x11,0x7f);
7736 for(i = 0; i <= 10; i++) {
7737 tempah = (LVDSCRT1Ptr + ResIndex)->CR[i];
7738 SiS_SetReg(SiS_Pr->SiS_P3d4,CRIdx[i],tempah);
7741 for(i = 0x0A, j = 11; i <= 0x0C; i++, j++) {
7742 tempah = (LVDSCRT1Ptr + ResIndex)->CR[j];
7743 SiS_SetReg(SiS_Pr->SiS_P3c4,i,tempah);
7746 tempah = (LVDSCRT1Ptr + ResIndex)->CR[14] & 0xE0;
7747 SiS_SetRegANDOR(SiS_Pr->SiS_P3c4,0x0E,0x1f,tempah);
7749 if(ModeNo <= 0x13) modeflag = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_ModeFlag;
7750 else modeflag = SiS_Pr->SiS_EModeIDTable[ModeIdIndex].Ext_ModeFlag;
7752 tempah = ((LVDSCRT1Ptr + ResIndex)->CR[14] & 0x01) << 5;
7753 if(modeflag & DoubleScanMode) tempah |= 0x80;
7754 SiS_SetRegANDOR(SiS_Pr->SiS_P3d4,0x09,~0x020,tempah);
7758 SiS_CalcLCDACRT1Timing(SiS_Pr, ModeNo, ModeIdIndex);
7763 /*********************************************/
7765 /*********************************************/
7768 SiS_SetCRT2ECLK(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex,
7769 unsigned short RefreshRateTableIndex)
7771 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
7772 unsigned short clkbase, vclkindex = 0;
7773 unsigned char sr2b, sr2c;
7775 if(SiS_Pr->SiS_LCDInfo & LCDPass11) {
7776 SiS_Pr->SiS_SetFlag &= (~ProgrammingCRT2);
7777 if(SiS_Pr->SiS_RefIndex[RefreshRateTableIndex].Ext_CRTVCLK == 2) {
7778 RefreshRateTableIndex--;
7780 vclkindex = SiS_GetVCLK2Ptr(SiS_Pr, ModeNo, ModeIdIndex,
7781 RefreshRateTableIndex);
7782 SiS_Pr->SiS_SetFlag |= ProgrammingCRT2;
7784 vclkindex = SiS_GetVCLK2Ptr(SiS_Pr, ModeNo, ModeIdIndex,
7785 RefreshRateTableIndex);
7788 sr2b = SiS_Pr->SiS_VCLKData[vclkindex].SR2B;
7789 sr2c = SiS_Pr->SiS_VCLKData[vclkindex].SR2C;
7791 if((SiS_Pr->SiS_CustomT == CUT_BARCO1366) || (SiS_Pr->SiS_CustomT == CUT_BARCO1024)) {
7792 if(SiS_Pr->SiS_UseROM) {
7793 if(ROMAddr[0x220] & 0x01) {
7794 sr2b = ROMAddr[0x227];
7795 sr2c = ROMAddr[0x228];
7801 if(!(SiS_Pr->SiS_VBInfo & SetCRT2ToLCDA)) {
7802 if(!(SiS_Pr->SiS_VBInfo & SetInSlaveMode)) {
7807 SiS_SetReg(SiS_Pr->SiS_P3c4,0x31,0x20);
7808 SiS_SetReg(SiS_Pr->SiS_P3c4,clkbase,sr2b);
7809 SiS_SetReg(SiS_Pr->SiS_P3c4,clkbase+1,sr2c);
7810 SiS_SetReg(SiS_Pr->SiS_P3c4,0x31,0x10);
7811 SiS_SetReg(SiS_Pr->SiS_P3c4,clkbase,sr2b);
7812 SiS_SetReg(SiS_Pr->SiS_P3c4,clkbase+1,sr2c);
7813 SiS_SetReg(SiS_Pr->SiS_P3c4,0x31,0x00);
7814 SiS_SetReg(SiS_Pr->SiS_P3c4,clkbase,sr2b);
7815 SiS_SetReg(SiS_Pr->SiS_P3c4,clkbase+1,sr2c);
7818 /*********************************************/
7819 /* SET UP CHRONTEL CHIPS */
7820 /*********************************************/
7823 SiS_SetCHTVReg(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex,
7824 unsigned short RefreshRateTableIndex)
7826 unsigned short TVType, resindex;
7827 const struct SiS_CHTVRegData *CHTVRegData = NULL;
7830 resindex = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_CRT2CRTC;
7832 resindex = SiS_Pr->SiS_RefIndex[RefreshRateTableIndex].Ext_CRT2CRTC;
7837 if(SiS_Pr->SiS_TVMode & TVSetCHOverScan) TVType += 1;
7838 if(SiS_Pr->SiS_TVMode & TVSetPAL) {
7840 if(SiS_Pr->SiS_ModeType > ModeVGA) {
7841 if(SiS_Pr->SiS_CHSOverScan) TVType = 8;
7843 if(SiS_Pr->SiS_TVMode & TVSetPALM) {
7845 if(SiS_Pr->SiS_TVMode & TVSetCHOverScan) TVType += 1;
7846 } else if(SiS_Pr->SiS_TVMode & TVSetPALN) {
7848 if(SiS_Pr->SiS_TVMode & TVSetCHOverScan) TVType += 1;
7853 case 0: CHTVRegData = SiS_Pr->SiS_CHTVReg_UNTSC; break;
7854 case 1: CHTVRegData = SiS_Pr->SiS_CHTVReg_ONTSC; break;
7855 case 2: CHTVRegData = SiS_Pr->SiS_CHTVReg_UPAL; break;
7856 case 3: CHTVRegData = SiS_Pr->SiS_CHTVReg_OPAL; break;
7857 case 4: CHTVRegData = SiS_Pr->SiS_CHTVReg_UPALM; break;
7858 case 5: CHTVRegData = SiS_Pr->SiS_CHTVReg_OPALM; break;
7859 case 6: CHTVRegData = SiS_Pr->SiS_CHTVReg_UPALN; break;
7860 case 7: CHTVRegData = SiS_Pr->SiS_CHTVReg_OPALN; break;
7861 case 8: CHTVRegData = SiS_Pr->SiS_CHTVReg_SOPAL; break;
7862 default: CHTVRegData = SiS_Pr->SiS_CHTVReg_OPAL; break;
7866 if(SiS_Pr->SiS_IF_DEF_CH70xx == 1) {
7868 #ifdef CONFIG_FB_SIS_300
7870 /* Chrontel 7005 - I assume that it does not come with a 315 series chip */
7872 /* We don't support modes >800x600 */
7873 if (resindex > 5) return;
7875 if(SiS_Pr->SiS_TVMode & TVSetPAL) {
7876 SiS_SetCH700x(SiS_Pr,0x04,0x43); /* 0x40=76uA (PAL); 0x03=15bit non-multi RGB*/
7877 SiS_SetCH700x(SiS_Pr,0x09,0x69); /* Black level for PAL (105)*/
7879 SiS_SetCH700x(SiS_Pr,0x04,0x03); /* upper nibble=71uA (NTSC), 0x03=15bit non-multi RGB*/
7880 SiS_SetCH700x(SiS_Pr,0x09,0x71); /* Black level for NTSC (113)*/
7883 SiS_SetCH700x(SiS_Pr,0x00,CHTVRegData[resindex].Reg[0]); /* Mode register */
7884 SiS_SetCH700x(SiS_Pr,0x07,CHTVRegData[resindex].Reg[1]); /* Start active video register */
7885 SiS_SetCH700x(SiS_Pr,0x08,CHTVRegData[resindex].Reg[2]); /* Position overflow register */
7886 SiS_SetCH700x(SiS_Pr,0x0a,CHTVRegData[resindex].Reg[3]); /* Horiz Position register */
7887 SiS_SetCH700x(SiS_Pr,0x0b,CHTVRegData[resindex].Reg[4]); /* Vertical Position register */
7889 /* Set minimum flicker filter for Luma channel (SR1-0=00),
7890 minimum text enhancement (S3-2=10),
7891 maximum flicker filter for Chroma channel (S5-4=10)
7892 =00101000=0x28 (When reading, S1-0->S3-2, and S3-2->S1-0!)
7894 SiS_SetCH700x(SiS_Pr,0x01,0x28);
7896 /* Set video bandwidth
7897 High bandwidth Luma composite video filter(S0=1)
7898 low bandwidth Luma S-video filter (S2-1=00)
7899 disable peak filter in S-video channel (S3=0)
7900 high bandwidth Chroma Filter (S5-4=11)
7903 SiS_SetCH700x(SiS_Pr,0x03,0xb1); /* old: 3103 */
7905 /* Register 0x3D does not exist in non-macrovision register map
7906 (Maybe this is a macrovision register?)
7909 SiS_SetCH70xx(SiS_Pr,0x3d,0x00);
7912 /* Register 0x10 only contains 1 writable bit (S0) for sensing,
7913 all other bits a read-only. Macrovision?
7915 SiS_SetCH70xxANDOR(SiS_Pr,0x10,0x00,0x1F);
7917 /* Register 0x11 only contains 3 writable bits (S0-S2) for
7918 contrast enhancement (set to 010 -> gain 1 Yout = 17/16*(Yin-30) )
7920 SiS_SetCH70xxANDOR(SiS_Pr,0x11,0x02,0xF8);
7924 SiS_SetCH70xxANDOR(SiS_Pr,0x1c,0x00,0xEF);
7926 if(!(SiS_Pr->SiS_TVMode & TVSetPAL)) { /* ---- NTSC ---- */
7927 if(SiS_Pr->SiS_TVMode & TVSetCHOverScan) {
7928 if(resindex == 0x04) { /* 640x480 overscan: Mode 16 */
7929 SiS_SetCH70xxANDOR(SiS_Pr,0x20,0x00,0xEF); /* loop filter off */
7930 SiS_SetCH70xxANDOR(SiS_Pr,0x21,0x01,0xFE); /* ACIV on, no need to set FSCI */
7931 } else if(resindex == 0x05) { /* 800x600 overscan: Mode 23 */
7932 SiS_SetCH70xxANDOR(SiS_Pr,0x18,0x01,0xF0); /* 0x18-0x1f: FSCI 469,762,048 */
7933 SiS_SetCH70xxANDOR(SiS_Pr,0x19,0x0C,0xF0);
7934 SiS_SetCH70xxANDOR(SiS_Pr,0x1a,0x00,0xF0);
7935 SiS_SetCH70xxANDOR(SiS_Pr,0x1b,0x00,0xF0);
7936 SiS_SetCH70xxANDOR(SiS_Pr,0x1c,0x00,0xF0);
7937 SiS_SetCH70xxANDOR(SiS_Pr,0x1d,0x00,0xF0);
7938 SiS_SetCH70xxANDOR(SiS_Pr,0x1e,0x00,0xF0);
7939 SiS_SetCH70xxANDOR(SiS_Pr,0x1f,0x00,0xF0);
7940 SiS_SetCH70xxANDOR(SiS_Pr,0x20,0x01,0xEF); /* Loop filter on for mode 23 */
7941 SiS_SetCH70xxANDOR(SiS_Pr,0x21,0x00,0xFE); /* ACIV off, need to set FSCI */
7944 if(resindex == 0x04) { /* ----- 640x480 underscan; Mode 17 */
7945 SiS_SetCH70xxANDOR(SiS_Pr,0x20,0x00,0xEF); /* loop filter off */
7946 SiS_SetCH70xxANDOR(SiS_Pr,0x21,0x01,0xFE);
7947 } else if(resindex == 0x05) { /* ----- 800x600 underscan: Mode 24 */
7949 SiS_SetCH70xxANDOR(SiS_Pr,0x18,0x01,0xF0); /* (FSCI was 0x1f1c71c7 - this is for mode 22) */
7950 SiS_SetCH70xxANDOR(SiS_Pr,0x19,0x09,0xF0); /* FSCI for mode 24 is 428,554,851 */
7951 SiS_SetCH70xxANDOR(SiS_Pr,0x1a,0x08,0xF0); /* 198b3a63 */
7952 SiS_SetCH70xxANDOR(SiS_Pr,0x1b,0x0b,0xF0);
7953 SiS_SetCH70xxANDOR(SiS_Pr,0x1c,0x04,0xF0);
7954 SiS_SetCH70xxANDOR(SiS_Pr,0x1d,0x01,0xF0);
7955 SiS_SetCH70xxANDOR(SiS_Pr,0x1e,0x06,0xF0);
7956 SiS_SetCH70xxANDOR(SiS_Pr,0x1f,0x05,0xF0);
7957 SiS_SetCH70xxANDOR(SiS_Pr,0x20,0x00,0xEF); /* loop filter off for mode 24 */
7958 SiS_SetCH70xxANDOR(SiS_Pr,0x21,0x00,0xFE); * ACIV off, need to set FSCI */
7959 #endif /* All alternatives wrong (datasheet wrong?), don't use FSCI */
7960 SiS_SetCH70xxANDOR(SiS_Pr,0x20,0x00,0xEF); /* loop filter off */
7961 SiS_SetCH70xxANDOR(SiS_Pr,0x21,0x01,0xFE);
7964 } else { /* ---- PAL ---- */
7965 /* We don't play around with FSCI in PAL mode */
7966 if(resindex == 0x04) {
7967 SiS_SetCH70xxANDOR(SiS_Pr,0x20,0x00,0xEF); /* loop filter off */
7968 SiS_SetCH70xxANDOR(SiS_Pr,0x21,0x01,0xFE); /* ACIV on */
7970 SiS_SetCH70xxANDOR(SiS_Pr,0x20,0x00,0xEF); /* loop filter off */
7971 SiS_SetCH70xxANDOR(SiS_Pr,0x21,0x01,0xFE); /* ACIV on */
7979 /* Chrontel 7019 - assumed that it does not come with a 300 series chip */
7981 #ifdef CONFIG_FB_SIS_315
7983 unsigned short temp;
7985 /* We don't support modes >1024x768 */
7986 if (resindex > 6) return;
7988 temp = CHTVRegData[resindex].Reg[0];
7989 if(SiS_Pr->SiS_TVMode & TVSetNTSCJ) temp |= 0x10;
7990 SiS_SetCH701x(SiS_Pr,0x00,temp);
7992 SiS_SetCH701x(SiS_Pr,0x01,CHTVRegData[resindex].Reg[1]);
7993 SiS_SetCH701x(SiS_Pr,0x02,CHTVRegData[resindex].Reg[2]);
7994 SiS_SetCH701x(SiS_Pr,0x04,CHTVRegData[resindex].Reg[3]);
7995 SiS_SetCH701x(SiS_Pr,0x03,CHTVRegData[resindex].Reg[4]);
7996 SiS_SetCH701x(SiS_Pr,0x05,CHTVRegData[resindex].Reg[5]);
7997 SiS_SetCH701x(SiS_Pr,0x06,CHTVRegData[resindex].Reg[6]);
7999 temp = CHTVRegData[resindex].Reg[7];
8000 if(SiS_Pr->SiS_TVMode & TVSetNTSCJ) temp = 0x66;
8001 SiS_SetCH701x(SiS_Pr,0x07,temp);
8003 SiS_SetCH701x(SiS_Pr,0x08,CHTVRegData[resindex].Reg[8]);
8004 SiS_SetCH701x(SiS_Pr,0x15,CHTVRegData[resindex].Reg[9]);
8005 SiS_SetCH701x(SiS_Pr,0x1f,CHTVRegData[resindex].Reg[10]);
8006 SiS_SetCH701x(SiS_Pr,0x0c,CHTVRegData[resindex].Reg[11]);
8007 SiS_SetCH701x(SiS_Pr,0x0d,CHTVRegData[resindex].Reg[12]);
8008 SiS_SetCH701x(SiS_Pr,0x0e,CHTVRegData[resindex].Reg[13]);
8009 SiS_SetCH701x(SiS_Pr,0x0f,CHTVRegData[resindex].Reg[14]);
8010 SiS_SetCH701x(SiS_Pr,0x10,CHTVRegData[resindex].Reg[15]);
8012 temp = SiS_GetCH701x(SiS_Pr,0x21) & ~0x02;
8013 /* D1 should be set for PAL, PAL-N and NTSC-J,
8014 but I won't do that for PAL unless somebody
8015 tells me to do so. Since the BIOS uses
8016 non-default CIV values and blacklevels,
8017 this might be compensated anyway.
8019 if(SiS_Pr->SiS_TVMode & (TVSetPALN | TVSetNTSCJ)) temp |= 0x02;
8020 SiS_SetCH701x(SiS_Pr,0x21,temp);
8032 #ifdef CONFIG_FB_SIS_315 /* ----------- 315 series only ---------- */
8035 SiS_Chrontel701xBLOn(struct SiS_Private *SiS_Pr)
8037 unsigned short temp;
8039 /* Enable Chrontel 7019 LCD panel backlight */
8040 if(SiS_Pr->SiS_IF_DEF_CH70xx == 2) {
8041 if(SiS_Pr->ChipType == SIS_740) {
8042 SiS_SetCH701x(SiS_Pr,0x66,0x65);
8044 temp = SiS_GetCH701x(SiS_Pr,0x66);
8046 SiS_SetCH701x(SiS_Pr,0x66,temp);
8052 SiS_Chrontel701xBLOff(struct SiS_Private *SiS_Pr)
8054 unsigned short temp;
8056 /* Disable Chrontel 7019 LCD panel backlight */
8057 if(SiS_Pr->SiS_IF_DEF_CH70xx == 2) {
8058 temp = SiS_GetCH701x(SiS_Pr,0x66);
8060 SiS_SetCH701x(SiS_Pr,0x66,temp);
8065 SiS_ChrontelPowerSequencing(struct SiS_Private *SiS_Pr)
8067 static const unsigned char regtable[] = { 0x67, 0x68, 0x69, 0x6a, 0x6b };
8068 static const unsigned char table1024_740[] = { 0x01, 0x02, 0x01, 0x01, 0x01 };
8069 static const unsigned char table1400_740[] = { 0x01, 0x6e, 0x01, 0x01, 0x01 };
8070 static const unsigned char asus1024_740[] = { 0x19, 0x6e, 0x01, 0x19, 0x09 };
8071 static const unsigned char asus1400_740[] = { 0x19, 0x6e, 0x01, 0x19, 0x09 };
8072 static const unsigned char table1024_650[] = { 0x01, 0x02, 0x01, 0x01, 0x02 };
8073 static const unsigned char table1400_650[] = { 0x01, 0x02, 0x01, 0x01, 0x02 };
8074 const unsigned char *tableptr = NULL;
8077 /* Set up Power up/down timing */
8079 if(SiS_Pr->ChipType == SIS_740) {
8080 if(SiS_Pr->SiS_LCDResInfo == Panel_1024x768) {
8081 if(SiS_Pr->SiS_CustomT == CUT_ASUSL3000D) tableptr = asus1024_740;
8082 else tableptr = table1024_740;
8083 } else if((SiS_Pr->SiS_LCDResInfo == Panel_1280x1024) ||
8084 (SiS_Pr->SiS_LCDResInfo == Panel_1400x1050) ||
8085 (SiS_Pr->SiS_LCDResInfo == Panel_1600x1200)) {
8086 if(SiS_Pr->SiS_CustomT == CUT_ASUSL3000D) tableptr = asus1400_740;
8087 else tableptr = table1400_740;
8090 if(SiS_Pr->SiS_LCDResInfo == Panel_1024x768) {
8091 tableptr = table1024_650;
8092 } else if((SiS_Pr->SiS_LCDResInfo == Panel_1280x1024) ||
8093 (SiS_Pr->SiS_LCDResInfo == Panel_1400x1050) ||
8094 (SiS_Pr->SiS_LCDResInfo == Panel_1600x1200)) {
8095 tableptr = table1400_650;
8099 for(i=0; i<5; i++) {
8100 SiS_SetCH701x(SiS_Pr, regtable[i], tableptr[i]);
8105 SiS_SetCH701xForLCD(struct SiS_Private *SiS_Pr)
8107 const unsigned char *tableptr = NULL;
8108 unsigned short tempbh;
8110 static const unsigned char regtable[] = {
8111 0x1c, 0x5f, 0x64, 0x6f, 0x70, 0x71,
8112 0x72, 0x73, 0x74, 0x76, 0x78, 0x7d, 0x66
8114 static const unsigned char table1024_740[] = {
8115 0x60, 0x02, 0x00, 0x07, 0x40, 0xed,
8116 0xa3, 0xc8, 0xc7, 0xac, 0xe0, 0x02, 0x44
8118 static const unsigned char table1280_740[] = {
8119 0x60, 0x03, 0x11, 0x00, 0x40, 0xe3,
8120 0xad, 0xdb, 0xf6, 0xac, 0xe0, 0x02, 0x44
8122 static const unsigned char table1400_740[] = {
8123 0x60, 0x03, 0x11, 0x00, 0x40, 0xe3,
8124 0xad, 0xdb, 0xf6, 0xac, 0xe0, 0x02, 0x44
8126 static const unsigned char table1600_740[] = {
8127 0x60, 0x04, 0x11, 0x00, 0x40, 0xe3,
8128 0xad, 0xde, 0xf6, 0xac, 0x60, 0x1a, 0x44
8130 static const unsigned char table1024_650[] = {
8131 0x60, 0x02, 0x00, 0x07, 0x40, 0xed,
8132 0xa3, 0xc8, 0xc7, 0xac, 0x60, 0x02
8134 static const unsigned char table1280_650[] = {
8135 0x60, 0x03, 0x11, 0x00, 0x40, 0xe3,
8136 0xad, 0xdb, 0xf6, 0xac, 0xe0, 0x02
8138 static const unsigned char table1400_650[] = {
8139 0x60, 0x03, 0x11, 0x00, 0x40, 0xef,
8140 0xad, 0xdb, 0xf6, 0xac, 0x60, 0x02
8142 static const unsigned char table1600_650[] = {
8143 0x60, 0x04, 0x11, 0x00, 0x40, 0xe3,
8144 0xad, 0xde, 0xf6, 0xac, 0x60, 0x1a
8147 if(SiS_Pr->ChipType == SIS_740) {
8148 if(SiS_Pr->SiS_LCDResInfo == Panel_1024x768) tableptr = table1024_740;
8149 else if(SiS_Pr->SiS_LCDResInfo == Panel_1280x1024) tableptr = table1280_740;
8150 else if(SiS_Pr->SiS_LCDResInfo == Panel_1400x1050) tableptr = table1400_740;
8151 else if(SiS_Pr->SiS_LCDResInfo == Panel_1600x1200) tableptr = table1600_740;
8154 if(SiS_Pr->SiS_LCDResInfo == Panel_1024x768) tableptr = table1024_650;
8155 else if(SiS_Pr->SiS_LCDResInfo == Panel_1280x1024) tableptr = table1280_650;
8156 else if(SiS_Pr->SiS_LCDResInfo == Panel_1400x1050) tableptr = table1400_650;
8157 else if(SiS_Pr->SiS_LCDResInfo == Panel_1600x1200) tableptr = table1600_650;
8161 tempbh = SiS_GetCH701x(SiS_Pr,0x74);
8162 if((tempbh == 0xf6) || (tempbh == 0xc7)) {
8163 tempbh = SiS_GetCH701x(SiS_Pr,0x73);
8164 if(tempbh == 0xc8) {
8165 if(SiS_Pr->SiS_LCDResInfo == Panel_1024x768) return;
8166 } else if(tempbh == 0xdb) {
8167 if(SiS_Pr->SiS_LCDResInfo == Panel_1280x1024) return;
8168 if(SiS_Pr->SiS_LCDResInfo == Panel_1400x1050) return;
8169 } else if(tempbh == 0xde) {
8170 if(SiS_Pr->SiS_LCDResInfo == Panel_1600x1200) return;
8174 if(SiS_Pr->ChipType == SIS_740) tempbh = 0x0d;
8177 for(i = 0; i < tempbh; i++) {
8178 SiS_SetCH701x(SiS_Pr, regtable[i], tableptr[i]);
8180 SiS_ChrontelPowerSequencing(SiS_Pr);
8181 tempbh = SiS_GetCH701x(SiS_Pr,0x1e);
8183 SiS_SetCH701x(SiS_Pr,0x1e,tempbh);
8185 if(SiS_Pr->ChipType == SIS_740) {
8186 tempbh = SiS_GetCH701x(SiS_Pr,0x1c);
8188 SiS_SetCH701x(SiS_Pr,0x1c,tempbh);
8189 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x2d,0x03);
8190 tempbh = SiS_GetCH701x(SiS_Pr,0x64);
8192 SiS_SetCH701x(SiS_Pr,0x64,tempbh);
8193 tempbh = SiS_GetCH701x(SiS_Pr,0x03);
8195 SiS_SetCH701x(SiS_Pr,0x03,tempbh);
8200 SiS_ChrontelResetVSync(struct SiS_Private *SiS_Pr)
8202 unsigned char temp, temp1;
8204 temp1 = SiS_GetCH701x(SiS_Pr,0x49);
8205 SiS_SetCH701x(SiS_Pr,0x49,0x3e);
8206 temp = SiS_GetCH701x(SiS_Pr,0x47);
8207 temp &= 0x7f; /* Use external VSYNC */
8208 SiS_SetCH701x(SiS_Pr,0x47,temp);
8209 SiS_LongDelay(SiS_Pr, 3);
8210 temp = SiS_GetCH701x(SiS_Pr,0x47);
8211 temp |= 0x80; /* Use internal VSYNC */
8212 SiS_SetCH701x(SiS_Pr,0x47,temp);
8213 SiS_SetCH701x(SiS_Pr,0x49,temp1);
8217 SiS_Chrontel701xOn(struct SiS_Private *SiS_Pr)
8219 unsigned short temp;
8221 if(SiS_Pr->SiS_IF_DEF_CH70xx == 2) {
8222 if(SiS_Pr->ChipType == SIS_740) {
8223 temp = SiS_GetCH701x(SiS_Pr,0x1c);
8224 temp |= 0x04; /* Invert XCLK phase */
8225 SiS_SetCH701x(SiS_Pr,0x1c,temp);
8227 if(SiS_IsYPbPr(SiS_Pr)) {
8228 temp = SiS_GetCH701x(SiS_Pr,0x01);
8230 temp |= 0x80; /* Enable YPrPb (HDTV) */
8231 SiS_SetCH701x(SiS_Pr,0x01,temp);
8233 if(SiS_IsChScart(SiS_Pr)) {
8234 temp = SiS_GetCH701x(SiS_Pr,0x01);
8236 temp |= 0xc0; /* Enable SCART + CVBS */
8237 SiS_SetCH701x(SiS_Pr,0x01,temp);
8239 if(SiS_Pr->ChipType == SIS_740) {
8240 SiS_ChrontelResetVSync(SiS_Pr);
8241 SiS_SetCH701x(SiS_Pr,0x49,0x20); /* Enable TV path */
8243 SiS_SetCH701x(SiS_Pr,0x49,0x20); /* Enable TV path */
8244 temp = SiS_GetCH701x(SiS_Pr,0x49);
8245 if(SiS_IsYPbPr(SiS_Pr)) {
8246 temp = SiS_GetCH701x(SiS_Pr,0x73);
8248 SiS_SetCH701x(SiS_Pr,0x73,temp);
8250 temp = SiS_GetCH701x(SiS_Pr,0x47);
8252 SiS_SetCH701x(SiS_Pr,0x47,temp);
8253 SiS_LongDelay(SiS_Pr, 2);
8254 temp = SiS_GetCH701x(SiS_Pr,0x47);
8256 SiS_SetCH701x(SiS_Pr,0x47,temp);
8262 SiS_Chrontel701xOff(struct SiS_Private *SiS_Pr)
8264 unsigned short temp;
8266 /* Complete power down of LVDS */
8267 if(SiS_Pr->SiS_IF_DEF_CH70xx == 2) {
8268 if(SiS_Pr->ChipType == SIS_740) {
8269 SiS_LongDelay(SiS_Pr, 1);
8270 SiS_GenericDelay(SiS_Pr, 5887);
8271 SiS_SetCH701x(SiS_Pr,0x76,0xac);
8272 SiS_SetCH701x(SiS_Pr,0x66,0x00);
8274 SiS_LongDelay(SiS_Pr, 2);
8275 temp = SiS_GetCH701x(SiS_Pr,0x76);
8277 SiS_SetCH701x(SiS_Pr,0x76,temp);
8278 SiS_SetCH701x(SiS_Pr,0x66,0x00);
8284 SiS_ChrontelResetDB(struct SiS_Private *SiS_Pr)
8286 unsigned short temp;
8288 if(SiS_Pr->ChipType == SIS_740) {
8290 temp = SiS_GetCH701x(SiS_Pr,0x4a); /* Version ID */
8294 if(SiS_WeHaveBacklightCtrl(SiS_Pr)) {
8295 temp = SiS_GetCH701x(SiS_Pr,0x49);
8296 SiS_SetCH701x(SiS_Pr,0x49,0x3e);
8299 /* Reset Chrontel 7019 datapath */
8300 SiS_SetCH701x(SiS_Pr,0x48,0x10);
8301 SiS_LongDelay(SiS_Pr, 1);
8302 SiS_SetCH701x(SiS_Pr,0x48,0x18);
8304 if(SiS_WeHaveBacklightCtrl(SiS_Pr)) {
8305 SiS_ChrontelResetVSync(SiS_Pr);
8306 SiS_SetCH701x(SiS_Pr,0x49,temp);
8311 /* Clear/set/clear GPIO */
8312 temp = SiS_GetCH701x(SiS_Pr,0x5c);
8314 SiS_SetCH701x(SiS_Pr,0x5c,temp);
8315 temp = SiS_GetCH701x(SiS_Pr,0x5c);
8317 SiS_SetCH701x(SiS_Pr,0x5c,temp);
8318 temp = SiS_GetCH701x(SiS_Pr,0x5c);
8320 SiS_SetCH701x(SiS_Pr,0x5c,temp);
8321 temp = SiS_GetCH701x(SiS_Pr,0x61);
8323 SiS_SetCH701xForLCD(SiS_Pr);
8328 /* Reset Chrontel 7019 datapath */
8329 SiS_SetCH701x(SiS_Pr,0x48,0x10);
8330 SiS_LongDelay(SiS_Pr, 1);
8331 SiS_SetCH701x(SiS_Pr,0x48,0x18);
8336 SiS_ChrontelInitTVVSync(struct SiS_Private *SiS_Pr)
8338 unsigned short temp;
8340 if(SiS_Pr->ChipType == SIS_740) {
8342 if(SiS_WeHaveBacklightCtrl(SiS_Pr)) {
8343 SiS_ChrontelResetVSync(SiS_Pr);
8348 SiS_SetCH701x(SiS_Pr,0x76,0xaf); /* Power up LVDS block */
8349 temp = SiS_GetCH701x(SiS_Pr,0x49);
8351 if(temp != 1) { /* TV block powered? (0 = yes, 1 = no) */
8352 temp = SiS_GetCH701x(SiS_Pr,0x47);
8354 SiS_SetCH701x(SiS_Pr,0x47,temp); /* enable VSYNC */
8355 SiS_LongDelay(SiS_Pr, 3);
8356 temp = SiS_GetCH701x(SiS_Pr,0x47);
8358 SiS_SetCH701x(SiS_Pr,0x47,temp); /* disable VSYNC */
8365 SiS_ChrontelDoSomething3(struct SiS_Private *SiS_Pr, unsigned short ModeNo)
8367 unsigned short temp,temp1;
8369 if(SiS_Pr->ChipType == SIS_740) {
8371 temp = SiS_GetCH701x(SiS_Pr,0x61);
8374 SiS_SetCH701x(SiS_Pr,0x61,temp);
8376 SiS_SetCH701x(SiS_Pr,0x66,0x45); /* Panel power on */
8377 SiS_SetCH701x(SiS_Pr,0x76,0xaf); /* All power on */
8378 SiS_LongDelay(SiS_Pr, 1);
8379 SiS_GenericDelay(SiS_Pr, 5887);
8384 temp = SiS_GetCH701x(SiS_Pr,0x61);
8387 SiS_SetCH701x(SiS_Pr,0x61,temp);
8390 SiS_SetCH701x(SiS_Pr,0x76,0xac);
8391 temp = SiS_GetCH701x(SiS_Pr,0x66);
8393 SiS_SetCH701x(SiS_Pr,0x66,temp);
8395 if(SiS_WeHaveBacklightCtrl(SiS_Pr)) {
8396 SiS_GenericDelay(SiS_Pr, 1023);
8398 SiS_GenericDelay(SiS_Pr, 767);
8402 SiS_GenericDelay(SiS_Pr, 767);
8404 temp = SiS_GetCH701x(SiS_Pr,0x76);
8406 SiS_SetCH701x(SiS_Pr,0x76,temp);
8407 temp = SiS_GetCH701x(SiS_Pr,0x66);
8409 SiS_SetCH701x(SiS_Pr,0x66,temp);
8410 SiS_LongDelay(SiS_Pr, 1);
8416 SiS_ChrontelDoSomething2(struct SiS_Private *SiS_Pr)
8418 unsigned short temp;
8420 SiS_LongDelay(SiS_Pr, 1);
8423 temp = SiS_GetCH701x(SiS_Pr,0x66);
8424 temp &= 0x04; /* PLL stable? -> bail out */
8425 if(temp == 0x04) break;
8427 if(SiS_Pr->ChipType == SIS_740) {
8428 /* Power down LVDS output, PLL normal operation */
8429 SiS_SetCH701x(SiS_Pr,0x76,0xac);
8432 SiS_SetCH701xForLCD(SiS_Pr);
8434 temp = SiS_GetCH701x(SiS_Pr,0x76);
8435 temp &= 0xfb; /* Reset PLL */
8436 SiS_SetCH701x(SiS_Pr,0x76,temp);
8437 SiS_LongDelay(SiS_Pr, 2);
8438 temp = SiS_GetCH701x(SiS_Pr,0x76);
8439 temp |= 0x04; /* PLL normal operation */
8440 SiS_SetCH701x(SiS_Pr,0x76,temp);
8441 if(SiS_Pr->ChipType == SIS_740) {
8442 SiS_SetCH701x(SiS_Pr,0x78,0xe0); /* PLL loop filter */
8444 SiS_SetCH701x(SiS_Pr,0x78,0x60);
8446 SiS_LongDelay(SiS_Pr, 2);
8449 SiS_SetCH701x(SiS_Pr,0x77,0x00); /* MV? */
8453 SiS_ChrontelDoSomething1(struct SiS_Private *SiS_Pr)
8455 unsigned short temp;
8457 temp = SiS_GetCH701x(SiS_Pr,0x03);
8458 temp |= 0x80; /* Set datapath 1 to TV */
8459 temp &= 0xbf; /* Set datapath 2 to LVDS */
8460 SiS_SetCH701x(SiS_Pr,0x03,temp);
8462 if(SiS_Pr->ChipType == SIS_740) {
8464 temp = SiS_GetCH701x(SiS_Pr,0x1c);
8465 temp &= 0xfb; /* Normal XCLK phase */
8466 SiS_SetCH701x(SiS_Pr,0x1c,temp);
8468 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x2d,0x03);
8470 temp = SiS_GetCH701x(SiS_Pr,0x64);
8471 temp |= 0x40; /* ? Bit not defined */
8472 SiS_SetCH701x(SiS_Pr,0x64,temp);
8474 temp = SiS_GetCH701x(SiS_Pr,0x03);
8475 temp &= 0x3f; /* D1 input to both LVDS and TV */
8476 SiS_SetCH701x(SiS_Pr,0x03,temp);
8478 if(SiS_Pr->SiS_CustomT == CUT_ASUSL3000D) {
8479 SiS_SetCH701x(SiS_Pr,0x63,0x40); /* LVDS off */
8480 SiS_LongDelay(SiS_Pr, 1);
8481 SiS_SetCH701x(SiS_Pr,0x63,0x00); /* LVDS on */
8482 SiS_ChrontelResetDB(SiS_Pr);
8483 SiS_ChrontelDoSomething2(SiS_Pr);
8484 SiS_ChrontelDoSomething3(SiS_Pr, 0);
8486 temp = SiS_GetCH701x(SiS_Pr,0x66);
8488 SiS_ChrontelResetDB(SiS_Pr);
8489 SiS_ChrontelDoSomething2(SiS_Pr);
8490 SiS_ChrontelDoSomething3(SiS_Pr, 0);
8496 SiS_ChrontelResetDB(SiS_Pr);
8497 SiS_ChrontelDoSomething2(SiS_Pr);
8498 temp = SiS_GetReg(SiS_Pr->SiS_P3d4,0x34);
8499 SiS_ChrontelDoSomething3(SiS_Pr,temp);
8500 SiS_SetCH701x(SiS_Pr,0x76,0xaf); /* All power on, LVDS normal operation */
8505 #endif /* 315 series */
8507 /*********************************************/
8508 /* MAIN: SET CRT2 REGISTER GROUP */
8509 /*********************************************/
8512 SiS_SetCRT2Group(struct SiS_Private *SiS_Pr, unsigned short ModeNo)
8514 #ifdef CONFIG_FB_SIS_300
8515 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
8517 unsigned short ModeIdIndex, RefreshRateTableIndex;
8519 SiS_Pr->SiS_SetFlag |= ProgrammingCRT2;
8521 if(!SiS_Pr->UseCustomMode) {
8522 SiS_SearchModeID(SiS_Pr, &ModeNo, &ModeIdIndex);
8527 /* Used for shifting CR33 */
8528 SiS_Pr->SiS_SelectCRT2Rate = 4;
8530 SiS_UnLockCRT2(SiS_Pr);
8532 RefreshRateTableIndex = SiS_GetRatePtr(SiS_Pr, ModeNo, ModeIdIndex);
8534 SiS_SaveCRT2Info(SiS_Pr,ModeNo);
8536 if(SiS_Pr->SiS_SetFlag & LowModeTests) {
8537 SiS_DisableBridge(SiS_Pr);
8538 if((SiS_Pr->SiS_IF_DEF_LVDS == 1) && (SiS_Pr->ChipType == SIS_730)) {
8539 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x00,0x80);
8541 SiS_SetCRT2ModeRegs(SiS_Pr, ModeNo, ModeIdIndex);
8544 if(SiS_Pr->SiS_VBInfo & DisableCRT2Display) {
8545 SiS_LockCRT2(SiS_Pr);
8546 SiS_DisplayOn(SiS_Pr);
8550 SiS_GetCRT2Data(SiS_Pr, ModeNo, ModeIdIndex, RefreshRateTableIndex);
8552 /* Set up Panel Link for LVDS and LCDA */
8553 SiS_Pr->SiS_LCDHDES = SiS_Pr->SiS_LCDVDES = 0;
8554 if( (SiS_Pr->SiS_IF_DEF_LVDS == 1) ||
8555 ((SiS_Pr->SiS_VBType & VB_NoLCD) && (SiS_Pr->SiS_VBInfo & SetCRT2ToLCD)) ||
8556 ((SiS_Pr->ChipType >= SIS_315H) && (SiS_Pr->SiS_VBType & VB_SIS30xBLV)) ) {
8557 SiS_GetLVDSDesData(SiS_Pr, ModeNo, ModeIdIndex, RefreshRateTableIndex);
8560 if(SiS_Pr->SiS_SetFlag & LowModeTests) {
8561 SiS_SetGroup1(SiS_Pr, ModeNo, ModeIdIndex, RefreshRateTableIndex);
8564 if(SiS_Pr->SiS_VBType & VB_SISVB) {
8566 if(SiS_Pr->SiS_SetFlag & LowModeTests) {
8568 SiS_SetGroup2(SiS_Pr, ModeNo, ModeIdIndex, RefreshRateTableIndex);
8569 #ifdef CONFIG_FB_SIS_315
8570 SiS_SetGroup2_C_ELV(SiS_Pr, ModeNo, ModeIdIndex, RefreshRateTableIndex);
8572 SiS_SetGroup3(SiS_Pr, ModeNo, ModeIdIndex);
8573 SiS_SetGroup4(SiS_Pr, ModeNo, ModeIdIndex, RefreshRateTableIndex);
8574 #ifdef CONFIG_FB_SIS_315
8575 SiS_SetGroup4_C_ELV(SiS_Pr, ModeNo, ModeIdIndex);
8577 SiS_SetGroup5(SiS_Pr, ModeNo, ModeIdIndex);
8579 SiS_SetCRT2Sync(SiS_Pr, ModeNo, RefreshRateTableIndex);
8581 /* For 301BDH (Panel link initialization): */
8582 if((SiS_Pr->SiS_VBType & VB_NoLCD) && (SiS_Pr->SiS_VBInfo & SetCRT2ToLCD)) {
8584 if(!((SiS_Pr->SiS_SetFlag & SetDOSMode) && ((ModeNo == 0x03) || (ModeNo == 0x10)))) {
8585 if(SiS_Pr->SiS_VBInfo & SetInSlaveMode) {
8586 SiS_ModCRT1CRTC(SiS_Pr, ModeNo, ModeIdIndex, RefreshRateTableIndex);
8589 SiS_SetCRT2ECLK(SiS_Pr, ModeNo, ModeIdIndex, RefreshRateTableIndex);
8595 SiS_SetCRT2Sync(SiS_Pr, ModeNo, RefreshRateTableIndex);
8597 SiS_ModCRT1CRTC(SiS_Pr,ModeNo,ModeIdIndex,RefreshRateTableIndex);
8599 SiS_SetCRT2ECLK(SiS_Pr,ModeNo,ModeIdIndex,RefreshRateTableIndex);
8601 if(SiS_Pr->SiS_SetFlag & LowModeTests) {
8602 if(SiS_Pr->SiS_IF_DEF_CH70xx != 0) {
8603 if(SiS_Pr->SiS_VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
8604 if(SiS_Pr->SiS_IF_DEF_CH70xx == 2) {
8605 #ifdef CONFIG_FB_SIS_315
8606 SiS_SetCH701xForLCD(SiS_Pr);
8610 if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) {
8611 SiS_SetCHTVReg(SiS_Pr,ModeNo,ModeIdIndex,RefreshRateTableIndex);
8618 #ifdef CONFIG_FB_SIS_300
8619 if(SiS_Pr->ChipType < SIS_315H) {
8620 if(SiS_Pr->SiS_SetFlag & LowModeTests) {
8621 if(SiS_Pr->SiS_UseOEM) {
8622 if((SiS_Pr->SiS_UseROM) && (SiS_Pr->SiS_UseOEM == -1)) {
8623 if((ROMAddr[0x233] == 0x12) && (ROMAddr[0x234] == 0x34)) {
8624 SiS_OEM300Setting(SiS_Pr, ModeNo, ModeIdIndex, RefreshRateTableIndex);
8627 SiS_OEM300Setting(SiS_Pr, ModeNo, ModeIdIndex, RefreshRateTableIndex);
8630 if(SiS_Pr->SiS_IF_DEF_LVDS == 1) {
8631 if((SiS_Pr->SiS_CustomT == CUT_BARCO1366) ||
8632 (SiS_Pr->SiS_CustomT == CUT_BARCO1024)) {
8633 SetOEMLCDData2(SiS_Pr, ModeNo, ModeIdIndex,RefreshRateTableIndex);
8635 SiS_DisplayOn(SiS_Pr);
8641 #ifdef CONFIG_FB_SIS_315
8642 if(SiS_Pr->ChipType >= SIS_315H) {
8643 if(SiS_Pr->SiS_SetFlag & LowModeTests) {
8644 if(SiS_Pr->ChipType < SIS_661) {
8645 SiS_FinalizeLCD(SiS_Pr, ModeNo, ModeIdIndex);
8646 SiS_OEM310Setting(SiS_Pr, ModeNo, ModeIdIndex, RefreshRateTableIndex);
8648 SiS_OEM661Setting(SiS_Pr, ModeNo, ModeIdIndex, RefreshRateTableIndex);
8650 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x01,0x40);
8655 if(SiS_Pr->SiS_SetFlag & LowModeTests) {
8656 SiS_EnableBridge(SiS_Pr);
8659 SiS_DisplayOn(SiS_Pr);
8661 if(SiS_Pr->SiS_IF_DEF_CH70xx == 1) {
8662 if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) {
8663 /* Disable LCD panel when using TV */
8664 SiS_SetRegSR11ANDOR(SiS_Pr,0xFF,0x0C);
8666 /* Disable TV when using LCD */
8667 SiS_SetCH70xxANDOR(SiS_Pr,0x0e,0x01,0xf8);
8671 if(SiS_Pr->SiS_SetFlag & LowModeTests) {
8672 SiS_LockCRT2(SiS_Pr);
8679 /*********************************************/
8680 /* ENABLE/DISABLE LCD BACKLIGHT (SIS) */
8681 /*********************************************/
8684 SiS_SiS30xBLOn(struct SiS_Private *SiS_Pr)
8686 /* Switch on LCD backlight on SiS30xLV */
8687 SiS_DDC2Delay(SiS_Pr,0xff00);
8688 if(!(SiS_GetReg(SiS_Pr->SiS_Part4Port,0x26) & 0x02)) {
8689 SiS_SetRegOR(SiS_Pr->SiS_Part4Port,0x26,0x02);
8690 SiS_WaitVBRetrace(SiS_Pr);
8692 if(!(SiS_GetReg(SiS_Pr->SiS_Part4Port,0x26) & 0x01)) {
8693 SiS_SetRegOR(SiS_Pr->SiS_Part4Port,0x26,0x01);
8698 SiS_SiS30xBLOff(struct SiS_Private *SiS_Pr)
8700 /* Switch off LCD backlight on SiS30xLV */
8701 SiS_SetRegAND(SiS_Pr->SiS_Part4Port,0x26,0xFE);
8702 SiS_DDC2Delay(SiS_Pr,0xff00);
8705 /*********************************************/
8706 /* DDC RELATED FUNCTIONS */
8707 /*********************************************/
8710 SiS_SetupDDCN(struct SiS_Private *SiS_Pr)
8712 SiS_Pr->SiS_DDC_NData = ~SiS_Pr->SiS_DDC_Data;
8713 SiS_Pr->SiS_DDC_NClk = ~SiS_Pr->SiS_DDC_Clk;
8714 if((SiS_Pr->SiS_DDC_Index == 0x11) && (SiS_Pr->SiS_SensibleSR11)) {
8715 SiS_Pr->SiS_DDC_NData &= 0x0f;
8716 SiS_Pr->SiS_DDC_NClk &= 0x0f;
8720 #ifdef CONFIG_FB_SIS_300
8721 static unsigned char *
8722 SiS_SetTrumpBlockLoop(struct SiS_Private *SiS_Pr, unsigned char *dataptr)
8725 unsigned short tempah,temp;
8726 unsigned char *mydataptr;
8728 for(i=0; i<20; i++) { /* Do 20 attempts to write */
8729 mydataptr = dataptr;
8731 if(!num) return mydataptr;
8733 SiS_SetStop(SiS_Pr);
8734 SiS_DDC2Delay(SiS_Pr,SiS_I2CDELAYSHORT * 2);
8736 if(SiS_SetStart(SiS_Pr)) continue; /* Set start condition */
8737 tempah = SiS_Pr->SiS_DDC_DeviceAddr;
8738 temp = SiS_WriteDDC2Data(SiS_Pr,tempah); /* Write DAB (S0=0=write) */
8739 if(temp) continue; /* (ERROR: no ack) */
8740 tempah = *mydataptr++;
8741 temp = SiS_WriteDDC2Data(SiS_Pr,tempah); /* Write register number */
8742 if(temp) continue; /* (ERROR: no ack) */
8743 for(j=0; j<num; j++) {
8744 tempah = *mydataptr++;
8745 temp = SiS_WriteDDC2Data(SiS_Pr,tempah);/* Write DAB (S0=0=write) */
8749 if(SiS_SetStop(SiS_Pr)) continue;
8756 SiS_SetTrumpionBlock(struct SiS_Private *SiS_Pr, unsigned char *dataptr)
8758 SiS_Pr->SiS_DDC_DeviceAddr = 0xF0; /* DAB (Device Address Byte) */
8759 SiS_Pr->SiS_DDC_Index = 0x11; /* Bit 0 = SC; Bit 1 = SD */
8760 SiS_Pr->SiS_DDC_Data = 0x02; /* Bitmask in IndexReg for Data */
8761 SiS_Pr->SiS_DDC_Clk = 0x01; /* Bitmask in IndexReg for Clk */
8762 SiS_SetupDDCN(SiS_Pr);
8764 SiS_SetSwitchDDC2(SiS_Pr);
8767 dataptr = SiS_SetTrumpBlockLoop(SiS_Pr, dataptr);
8768 if(!dataptr) return false;
8774 /* The Chrontel 700x is connected to the 630/730 via
8775 * the 630/730's DDC/I2C port.
8777 * On 630(S)T chipset, the index changed from 0x11 to
8778 * 0x0a, possibly for working around the DDC problems
8782 SiS_SetChReg(struct SiS_Private *SiS_Pr, unsigned short reg, unsigned char val, unsigned short myor)
8784 unsigned short temp, i;
8786 for(i=0; i<20; i++) { /* Do 20 attempts to write */
8788 SiS_SetStop(SiS_Pr);
8789 SiS_DDC2Delay(SiS_Pr,SiS_I2CDELAYSHORT * 4);
8791 if(SiS_SetStart(SiS_Pr)) continue; /* Set start condition */
8792 temp = SiS_WriteDDC2Data(SiS_Pr, SiS_Pr->SiS_DDC_DeviceAddr); /* Write DAB (S0=0=write) */
8793 if(temp) continue; /* (ERROR: no ack) */
8794 temp = SiS_WriteDDC2Data(SiS_Pr, (reg | myor)); /* Write RAB (700x: set bit 7, see datasheet) */
8795 if(temp) continue; /* (ERROR: no ack) */
8796 temp = SiS_WriteDDC2Data(SiS_Pr, val); /* Write data */
8797 if(temp) continue; /* (ERROR: no ack) */
8798 if(SiS_SetStop(SiS_Pr)) continue; /* Set stop condition */
8799 SiS_Pr->SiS_ChrontelInit = 1;
8805 /* Write to Chrontel 700x */
8807 SiS_SetCH700x(struct SiS_Private *SiS_Pr, unsigned short reg, unsigned char val)
8809 SiS_Pr->SiS_DDC_DeviceAddr = 0xEA; /* DAB (Device Address Byte) */
8811 SiS_DDC2Delay(SiS_Pr,SiS_I2CDELAYSHORT);
8813 if(!(SiS_Pr->SiS_ChrontelInit)) {
8814 SiS_Pr->SiS_DDC_Index = 0x11; /* Bit 0 = SC; Bit 1 = SD */
8815 SiS_Pr->SiS_DDC_Data = 0x02; /* Bitmask in IndexReg for Data */
8816 SiS_Pr->SiS_DDC_Clk = 0x01; /* Bitmask in IndexReg for Clk */
8817 SiS_SetupDDCN(SiS_Pr);
8820 if( (!(SiS_SetChReg(SiS_Pr, reg, val, 0x80))) &&
8821 (!(SiS_Pr->SiS_ChrontelInit)) ) {
8822 SiS_Pr->SiS_DDC_Index = 0x0a;
8823 SiS_Pr->SiS_DDC_Data = 0x80;
8824 SiS_Pr->SiS_DDC_Clk = 0x40;
8825 SiS_SetupDDCN(SiS_Pr);
8827 SiS_SetChReg(SiS_Pr, reg, val, 0x80);
8831 /* Write to Chrontel 701x */
8832 /* Parameter is [Data (S15-S8) | Register no (S7-S0)] */
8834 SiS_SetCH701x(struct SiS_Private *SiS_Pr, unsigned short reg, unsigned char val)
8836 SiS_Pr->SiS_DDC_Index = 0x11; /* Bit 0 = SC; Bit 1 = SD */
8837 SiS_Pr->SiS_DDC_Data = 0x08; /* Bitmask in IndexReg for Data */
8838 SiS_Pr->SiS_DDC_Clk = 0x04; /* Bitmask in IndexReg for Clk */
8839 SiS_SetupDDCN(SiS_Pr);
8840 SiS_Pr->SiS_DDC_DeviceAddr = 0xEA; /* DAB (Device Address Byte) */
8841 SiS_SetChReg(SiS_Pr, reg, val, 0);
8846 SiS_SetCH70xx(struct SiS_Private *SiS_Pr, unsigned short reg, unsigned char val)
8848 if(SiS_Pr->SiS_IF_DEF_CH70xx == 1)
8849 SiS_SetCH700x(SiS_Pr, reg, val);
8851 SiS_SetCH701x(SiS_Pr, reg, val);
8854 static unsigned short
8855 SiS_GetChReg(struct SiS_Private *SiS_Pr, unsigned short myor)
8857 unsigned short tempah, temp, i;
8859 for(i=0; i<20; i++) { /* Do 20 attempts to read */
8861 SiS_SetStop(SiS_Pr);
8862 SiS_DDC2Delay(SiS_Pr,SiS_I2CDELAYSHORT * 4);
8864 if(SiS_SetStart(SiS_Pr)) continue; /* Set start condition */
8865 temp = SiS_WriteDDC2Data(SiS_Pr,SiS_Pr->SiS_DDC_DeviceAddr); /* Write DAB (S0=0=write) */
8866 if(temp) continue; /* (ERROR: no ack) */
8867 temp = SiS_WriteDDC2Data(SiS_Pr,SiS_Pr->SiS_DDC_ReadAddr | myor); /* Write RAB (700x: | 0x80) */
8868 if(temp) continue; /* (ERROR: no ack) */
8869 if (SiS_SetStart(SiS_Pr)) continue; /* Re-start */
8870 temp = SiS_WriteDDC2Data(SiS_Pr,SiS_Pr->SiS_DDC_DeviceAddr | 0x01);/* DAB (S0=1=read) */
8871 if(temp) continue; /* (ERROR: no ack) */
8872 tempah = SiS_ReadDDC2Data(SiS_Pr); /* Read byte */
8873 if(SiS_SetStop(SiS_Pr)) continue; /* Stop condition */
8874 SiS_Pr->SiS_ChrontelInit = 1;
8880 /* Read from Chrontel 700x */
8881 /* Parameter is [Register no (S7-S0)] */
8883 SiS_GetCH700x(struct SiS_Private *SiS_Pr, unsigned short tempbx)
8885 unsigned short result;
8887 SiS_Pr->SiS_DDC_DeviceAddr = 0xEA; /* DAB */
8889 SiS_DDC2Delay(SiS_Pr,SiS_I2CDELAYSHORT);
8891 if(!(SiS_Pr->SiS_ChrontelInit)) {
8892 SiS_Pr->SiS_DDC_Index = 0x11; /* Bit 0 = SC; Bit 1 = SD */
8893 SiS_Pr->SiS_DDC_Data = 0x02; /* Bitmask in IndexReg for Data */
8894 SiS_Pr->SiS_DDC_Clk = 0x01; /* Bitmask in IndexReg for Clk */
8895 SiS_SetupDDCN(SiS_Pr);
8898 SiS_Pr->SiS_DDC_ReadAddr = tempbx;
8900 if( ((result = SiS_GetChReg(SiS_Pr,0x80)) == 0xFFFF) &&
8901 (!SiS_Pr->SiS_ChrontelInit) ) {
8903 SiS_Pr->SiS_DDC_Index = 0x0a;
8904 SiS_Pr->SiS_DDC_Data = 0x80;
8905 SiS_Pr->SiS_DDC_Clk = 0x40;
8906 SiS_SetupDDCN(SiS_Pr);
8908 result = SiS_GetChReg(SiS_Pr,0x80);
8913 /* Read from Chrontel 701x */
8914 /* Parameter is [Register no (S7-S0)] */
8916 SiS_GetCH701x(struct SiS_Private *SiS_Pr, unsigned short tempbx)
8918 SiS_Pr->SiS_DDC_Index = 0x11; /* Bit 0 = SC; Bit 1 = SD */
8919 SiS_Pr->SiS_DDC_Data = 0x08; /* Bitmask in IndexReg for Data */
8920 SiS_Pr->SiS_DDC_Clk = 0x04; /* Bitmask in IndexReg for Clk */
8921 SiS_SetupDDCN(SiS_Pr);
8922 SiS_Pr->SiS_DDC_DeviceAddr = 0xEA; /* DAB */
8924 SiS_Pr->SiS_DDC_ReadAddr = tempbx;
8926 return SiS_GetChReg(SiS_Pr,0);
8929 /* Read from Chrontel 70xx */
8930 /* Parameter is [Register no (S7-S0)] */
8933 SiS_GetCH70xx(struct SiS_Private *SiS_Pr, unsigned short tempbx)
8935 if(SiS_Pr->SiS_IF_DEF_CH70xx == 1)
8936 return SiS_GetCH700x(SiS_Pr, tempbx);
8938 return SiS_GetCH701x(SiS_Pr, tempbx);
8942 SiS_SetCH70xxANDOR(struct SiS_Private *SiS_Pr, unsigned short reg,
8943 unsigned char myor, unsigned short myand)
8945 unsigned short tempbl;
8947 tempbl = (SiS_GetCH70xx(SiS_Pr, (reg & 0xFF)) & myand) | myor;
8948 SiS_SetCH70xx(SiS_Pr, reg, tempbl);
8951 /* Our own DDC functions */
8954 SiS_InitDDCRegs(struct SiS_Private *SiS_Pr, unsigned int VBFlags, int VGAEngine,
8955 unsigned short adaptnum, unsigned short DDCdatatype, bool checkcr32,
8956 unsigned int VBFlags2)
8958 unsigned char ddcdtype[] = { 0xa0, 0xa0, 0xa0, 0xa2, 0xa6 };
8959 unsigned char flag, cr32;
8960 unsigned short temp = 0, myadaptnum = adaptnum;
8963 if(!(VBFlags2 & VB2_SISTMDSBRIDGE)) return 0xFFFF;
8964 if((VBFlags2 & VB2_30xBDH) && (adaptnum == 1)) return 0xFFFF;
8967 /* adapternum for SiS bridges: 0 = CRT1, 1 = LCD, 2 = VGA2 */
8969 SiS_Pr->SiS_ChrontelInit = 0; /* force re-detection! */
8971 SiS_Pr->SiS_DDC_SecAddr = 0;
8972 SiS_Pr->SiS_DDC_DeviceAddr = ddcdtype[DDCdatatype];
8973 SiS_Pr->SiS_DDC_Port = SiS_Pr->SiS_P3c4;
8974 SiS_Pr->SiS_DDC_Index = 0x11;
8977 cr32 = SiS_GetReg(SiS_Pr->SiS_P3d4,0x32);
8980 if(VBFlags2 & VB2_SISBRIDGE) {
8981 if(myadaptnum == 0) {
8982 if(!(cr32 & 0x20)) {
8984 if(!(cr32 & 0x10)) {
8986 if(!(cr32 & 0x08)) {
8995 if(VGAEngine == SIS_300_VGA) { /* 300 series */
8997 if(myadaptnum != 0) {
8999 if(VBFlags2 & VB2_SISBRIDGE) {
9000 SiS_Pr->SiS_DDC_Port = SiS_Pr->SiS_Part4Port;
9001 SiS_Pr->SiS_DDC_Index = 0x0f;
9005 if(!(VBFlags2 & VB2_301)) {
9006 if((cr32 & 0x80) && (checkcr32)) {
9007 if(myadaptnum >= 1) {
9008 if(!(cr32 & 0x08)) {
9010 if(!(cr32 & 0x10)) return 0xFFFF;
9016 temp = 4 - (myadaptnum * 2);
9019 } else { /* 315/330 series */
9021 /* here we simplify: 0 = CRT1, 1 = CRT2 (VGA, LCD) */
9023 if(VBFlags2 & VB2_SISBRIDGE) {
9024 if(myadaptnum == 2) {
9029 if(myadaptnum == 1) {
9031 if(VBFlags2 & VB2_SISBRIDGE) {
9032 SiS_Pr->SiS_DDC_Port = SiS_Pr->SiS_Part4Port;
9033 SiS_Pr->SiS_DDC_Index = 0x0f;
9037 if((cr32 & 0x80) && (checkcr32)) {
9038 if(myadaptnum >= 1) {
9039 if(!(cr32 & 0x08)) {
9041 if(!(cr32 & 0x10)) return 0xFFFF;
9047 if(myadaptnum == 1) {
9049 if(VBFlags2 & VB2_LVDS) flag = 0xff;
9055 SiS_Pr->SiS_DDC_Data = 0x02 << temp;
9056 SiS_Pr->SiS_DDC_Clk = 0x01 << temp;
9058 SiS_SetupDDCN(SiS_Pr);
9063 static unsigned short
9064 SiS_WriteDABDDC(struct SiS_Private *SiS_Pr)
9066 if(SiS_SetStart(SiS_Pr)) return 0xFFFF;
9067 if(SiS_WriteDDC2Data(SiS_Pr, SiS_Pr->SiS_DDC_DeviceAddr)) {
9070 if(SiS_WriteDDC2Data(SiS_Pr, SiS_Pr->SiS_DDC_SecAddr)) {
9076 static unsigned short
9077 SiS_PrepareReadDDC(struct SiS_Private *SiS_Pr)
9079 if(SiS_SetStart(SiS_Pr)) return 0xFFFF;
9080 if(SiS_WriteDDC2Data(SiS_Pr, (SiS_Pr->SiS_DDC_DeviceAddr | 0x01))) {
9086 static unsigned short
9087 SiS_PrepareDDC(struct SiS_Private *SiS_Pr)
9089 if(SiS_WriteDABDDC(SiS_Pr)) SiS_WriteDABDDC(SiS_Pr);
9090 if(SiS_PrepareReadDDC(SiS_Pr)) return (SiS_PrepareReadDDC(SiS_Pr));
9095 SiS_SendACK(struct SiS_Private *SiS_Pr, unsigned short yesno)
9097 SiS_SetSCLKLow(SiS_Pr);
9099 SiS_SetRegANDOR(SiS_Pr->SiS_DDC_Port,
9100 SiS_Pr->SiS_DDC_Index,
9101 SiS_Pr->SiS_DDC_NData,
9102 SiS_Pr->SiS_DDC_Data);
9104 SiS_SetRegANDOR(SiS_Pr->SiS_DDC_Port,
9105 SiS_Pr->SiS_DDC_Index,
9106 SiS_Pr->SiS_DDC_NData,
9109 SiS_SetSCLKHigh(SiS_Pr);
9112 static unsigned short
9113 SiS_DoProbeDDC(struct SiS_Private *SiS_Pr)
9115 unsigned char mask, value;
9116 unsigned short temp, ret=0;
9117 bool failed = false;
9119 SiS_SetSwitchDDC2(SiS_Pr);
9120 if(SiS_PrepareDDC(SiS_Pr)) {
9121 SiS_SetStop(SiS_Pr);
9126 if(SiS_Pr->SiS_DDC_DeviceAddr == 0xa0) {
9127 temp = (unsigned char)SiS_ReadDDC2Data(SiS_Pr);
9128 SiS_SendACK(SiS_Pr, 0);
9138 temp = (unsigned char)SiS_ReadDDC2Data(SiS_Pr);
9139 SiS_SendACK(SiS_Pr, 1);
9141 if(temp == value) ret = 0;
9144 if(SiS_Pr->SiS_DDC_DeviceAddr == 0xa0) {
9145 if(temp == 0x30) ret = 0;
9149 SiS_SetStop(SiS_Pr);
9155 SiS_ProbeDDC(struct SiS_Private *SiS_Pr)
9157 unsigned short flag;
9160 SiS_Pr->SiS_DDC_DeviceAddr = 0xa0;
9161 if(!(SiS_DoProbeDDC(SiS_Pr))) flag |= 0x02;
9162 SiS_Pr->SiS_DDC_DeviceAddr = 0xa2;
9163 if(!(SiS_DoProbeDDC(SiS_Pr))) flag |= 0x08;
9164 SiS_Pr->SiS_DDC_DeviceAddr = 0xa6;
9165 if(!(SiS_DoProbeDDC(SiS_Pr))) flag |= 0x10;
9166 if(!(flag & 0x1a)) flag = 0;
9172 SiS_ReadDDC(struct SiS_Private *SiS_Pr, unsigned short DDCdatatype, unsigned char *buffer)
9174 unsigned short flag, length, i;
9175 unsigned char chksum,gotcha;
9177 if(DDCdatatype > 4) return 0xFFFF;
9180 SiS_SetSwitchDDC2(SiS_Pr);
9181 if(!(SiS_PrepareDDC(SiS_Pr))) {
9183 if(DDCdatatype != 1) length = 255;
9186 for(i=0; i<length; i++) {
9187 buffer[i] = (unsigned char)SiS_ReadDDC2Data(SiS_Pr);
9188 chksum += buffer[i];
9189 gotcha |= buffer[i];
9190 SiS_SendACK(SiS_Pr, 0);
9192 buffer[i] = (unsigned char)SiS_ReadDDC2Data(SiS_Pr);
9193 chksum += buffer[i];
9194 SiS_SendACK(SiS_Pr, 1);
9195 if(gotcha) flag = (unsigned short)chksum;
9200 SiS_SetStop(SiS_Pr);
9204 /* Our private DDC functions
9206 It complies somewhat with the corresponding VESA function
9207 in arguments and return values.
9209 Since this is probably called before the mode is changed,
9210 we use our pre-detected pSiS-values instead of SiS_Pr as
9211 regards chipset and video bridge type.
9214 adaptnum: 0=CRT1(analog), 1=CRT2/LCD(digital), 2=CRT2/VGA2(analog)
9215 CRT2 DDC is only supported on SiS301, 301B, 301C, 302B.
9216 LCDA is CRT1, but DDC is read from CRT2 port.
9217 DDCdatatype: 0=Probe, 1=EDID, 2=EDID+VDIF, 3=EDID V2 (P&D), 4=EDID V2 (FPDI-2)
9218 buffer: ptr to 256 data bytes which will be filled with read data.
9220 Returns 0xFFFF if error, otherwise
9221 if DDCdatatype > 0: Returns 0 if reading OK (included a correct checksum)
9222 if DDCdatatype = 0: Returns supported DDC modes
9226 SiS_HandleDDC(struct SiS_Private *SiS_Pr, unsigned int VBFlags, int VGAEngine,
9227 unsigned short adaptnum, unsigned short DDCdatatype, unsigned char *buffer,
9228 unsigned int VBFlags2)
9230 unsigned char sr1f, cr17=1;
9231 unsigned short result;
9239 if((!(VBFlags2 & VB2_VIDEOBRIDGE)) && (adaptnum > 0))
9242 if(SiS_InitDDCRegs(SiS_Pr, VBFlags, VGAEngine, adaptnum, DDCdatatype, false, VBFlags2) == 0xFFFF)
9245 sr1f = SiS_GetReg(SiS_Pr->SiS_P3c4,0x1f);
9246 SiS_SetRegANDOR(SiS_Pr->SiS_P3c4,0x1f,0x3f,0x04);
9247 if(VGAEngine == SIS_300_VGA) {
9248 cr17 = SiS_GetReg(SiS_Pr->SiS_P3d4,0x17) & 0x80;
9250 SiS_SetRegOR(SiS_Pr->SiS_P3d4,0x17,0x80);
9251 SiS_SetReg(SiS_Pr->SiS_P3c4,0x00,0x01);
9252 SiS_SetReg(SiS_Pr->SiS_P3c4,0x00,0x03);
9255 if((sr1f) || (!cr17)) {
9256 SiS_WaitRetrace1(SiS_Pr);
9257 SiS_WaitRetrace1(SiS_Pr);
9258 SiS_WaitRetrace1(SiS_Pr);
9259 SiS_WaitRetrace1(SiS_Pr);
9262 if(DDCdatatype == 0) {
9263 result = SiS_ProbeDDC(SiS_Pr);
9265 result = SiS_ReadDDC(SiS_Pr, DDCdatatype, buffer);
9266 if((!result) && (DDCdatatype == 1)) {
9267 if((buffer[0] == 0x00) && (buffer[1] == 0xff) &&
9268 (buffer[2] == 0xff) && (buffer[3] == 0xff) &&
9269 (buffer[4] == 0xff) && (buffer[5] == 0xff) &&
9270 (buffer[6] == 0xff) && (buffer[7] == 0x00) &&
9271 (buffer[0x12] == 1)) {
9272 if(!SiS_Pr->DDCPortMixup) {
9274 if(!(buffer[0x14] & 0x80)) result = 0xFFFE;
9276 if(buffer[0x14] & 0x80) result = 0xFFFE;
9282 SiS_SetReg(SiS_Pr->SiS_P3c4,0x1f,sr1f);
9283 if(VGAEngine == SIS_300_VGA) {
9284 SiS_SetRegANDOR(SiS_Pr->SiS_P3d4,0x17,0x7f,cr17);
9289 /* Generic I2C functions for Chrontel & DDC --------- */
9292 SiS_SetSwitchDDC2(struct SiS_Private *SiS_Pr)
9294 SiS_SetSCLKHigh(SiS_Pr);
9295 SiS_WaitRetrace1(SiS_Pr);
9297 SiS_SetSCLKLow(SiS_Pr);
9298 SiS_WaitRetrace1(SiS_Pr);
9302 SiS_ReadDDC1Bit(struct SiS_Private *SiS_Pr)
9304 SiS_WaitRetrace1(SiS_Pr);
9305 return ((SiS_GetReg(SiS_Pr->SiS_P3c4,0x11) & 0x02) >> 1);
9308 /* Set I2C start condition */
9309 /* This is done by a SD high-to-low transition while SC is high */
9310 static unsigned short
9311 SiS_SetStart(struct SiS_Private *SiS_Pr)
9313 if(SiS_SetSCLKLow(SiS_Pr)) return 0xFFFF; /* (SC->low) */
9314 SiS_SetRegANDOR(SiS_Pr->SiS_DDC_Port,
9315 SiS_Pr->SiS_DDC_Index,
9316 SiS_Pr->SiS_DDC_NData,
9317 SiS_Pr->SiS_DDC_Data); /* SD->high */
9318 if(SiS_SetSCLKHigh(SiS_Pr)) return 0xFFFF; /* SC->high */
9319 SiS_SetRegANDOR(SiS_Pr->SiS_DDC_Port,
9320 SiS_Pr->SiS_DDC_Index,
9321 SiS_Pr->SiS_DDC_NData,
9322 0x00); /* SD->low = start condition */
9323 if(SiS_SetSCLKHigh(SiS_Pr)) return 0xFFFF; /* (SC->low) */
9327 /* Set I2C stop condition */
9328 /* This is done by a SD low-to-high transition while SC is high */
9329 static unsigned short
9330 SiS_SetStop(struct SiS_Private *SiS_Pr)
9332 if(SiS_SetSCLKLow(SiS_Pr)) return 0xFFFF; /* (SC->low) */
9333 SiS_SetRegANDOR(SiS_Pr->SiS_DDC_Port,
9334 SiS_Pr->SiS_DDC_Index,
9335 SiS_Pr->SiS_DDC_NData,
9336 0x00); /* SD->low */
9337 if(SiS_SetSCLKHigh(SiS_Pr)) return 0xFFFF; /* SC->high */
9338 SiS_SetRegANDOR(SiS_Pr->SiS_DDC_Port,
9339 SiS_Pr->SiS_DDC_Index,
9340 SiS_Pr->SiS_DDC_NData,
9341 SiS_Pr->SiS_DDC_Data); /* SD->high = stop condition */
9342 if(SiS_SetSCLKHigh(SiS_Pr)) return 0xFFFF; /* (SC->high) */
9346 /* Write 8 bits of data */
9347 static unsigned short
9348 SiS_WriteDDC2Data(struct SiS_Private *SiS_Pr, unsigned short tempax)
9350 unsigned short i,flag,temp;
9353 for(i = 0; i < 8; i++) {
9354 SiS_SetSCLKLow(SiS_Pr); /* SC->low */
9356 SiS_SetRegANDOR(SiS_Pr->SiS_DDC_Port,
9357 SiS_Pr->SiS_DDC_Index,
9358 SiS_Pr->SiS_DDC_NData,
9359 SiS_Pr->SiS_DDC_Data); /* Write bit (1) to SD */
9361 SiS_SetRegANDOR(SiS_Pr->SiS_DDC_Port,
9362 SiS_Pr->SiS_DDC_Index,
9363 SiS_Pr->SiS_DDC_NData,
9364 0x00); /* Write bit (0) to SD */
9366 SiS_SetSCLKHigh(SiS_Pr); /* SC->high */
9369 temp = SiS_CheckACK(SiS_Pr); /* Check acknowledge */
9373 static unsigned short
9374 SiS_ReadDDC2Data(struct SiS_Private *SiS_Pr)
9376 unsigned short i, temp, getdata;
9379 for(i = 0; i < 8; i++) {
9381 SiS_SetSCLKLow(SiS_Pr);
9382 SiS_SetRegANDOR(SiS_Pr->SiS_DDC_Port,
9383 SiS_Pr->SiS_DDC_Index,
9384 SiS_Pr->SiS_DDC_NData,
9385 SiS_Pr->SiS_DDC_Data);
9386 SiS_SetSCLKHigh(SiS_Pr);
9387 temp = SiS_GetReg(SiS_Pr->SiS_DDC_Port,SiS_Pr->SiS_DDC_Index);
9388 if(temp & SiS_Pr->SiS_DDC_Data) getdata |= 0x01;
9393 static unsigned short
9394 SiS_SetSCLKLow(struct SiS_Private *SiS_Pr)
9396 SiS_SetRegANDOR(SiS_Pr->SiS_DDC_Port,
9397 SiS_Pr->SiS_DDC_Index,
9398 SiS_Pr->SiS_DDC_NClk,
9399 0x00); /* SetSCLKLow() */
9400 SiS_DDC2Delay(SiS_Pr,SiS_I2CDELAYSHORT);
9404 static unsigned short
9405 SiS_SetSCLKHigh(struct SiS_Private *SiS_Pr)
9407 unsigned short temp, watchdog=1000;
9409 SiS_SetRegANDOR(SiS_Pr->SiS_DDC_Port,
9410 SiS_Pr->SiS_DDC_Index,
9411 SiS_Pr->SiS_DDC_NClk,
9412 SiS_Pr->SiS_DDC_Clk); /* SetSCLKHigh() */
9414 temp = SiS_GetReg(SiS_Pr->SiS_DDC_Port,SiS_Pr->SiS_DDC_Index);
9415 } while((!(temp & SiS_Pr->SiS_DDC_Clk)) && --watchdog);
9419 SiS_DDC2Delay(SiS_Pr,SiS_I2CDELAYSHORT);
9423 /* Check I2C acknowledge */
9424 /* Returns 0 if ack ok, non-0 if ack not ok */
9425 static unsigned short
9426 SiS_CheckACK(struct SiS_Private *SiS_Pr)
9428 unsigned short tempah;
9430 SiS_SetSCLKLow(SiS_Pr); /* (SC->low) */
9431 SiS_SetRegANDOR(SiS_Pr->SiS_DDC_Port,
9432 SiS_Pr->SiS_DDC_Index,
9433 SiS_Pr->SiS_DDC_NData,
9434 SiS_Pr->SiS_DDC_Data); /* (SD->high) */
9435 SiS_SetSCLKHigh(SiS_Pr); /* SC->high = clock impulse for ack */
9436 tempah = SiS_GetReg(SiS_Pr->SiS_DDC_Port,SiS_Pr->SiS_DDC_Index); /* Read SD */
9437 SiS_SetSCLKLow(SiS_Pr); /* SC->low = end of clock impulse */
9438 if(tempah & SiS_Pr->SiS_DDC_Data) return 1; /* Ack OK if bit = 0 */
9442 /* End of I2C functions ----------------------- */
9445 /* =============== SiS 315/330 O.E.M. ================= */
9447 #ifdef CONFIG_FB_SIS_315
9449 static unsigned short
9450 GetRAMDACromptr(struct SiS_Private *SiS_Pr)
9452 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
9453 unsigned short romptr;
9455 if(SiS_Pr->ChipType < SIS_330) {
9456 romptr = SISGETROMW(0x128);
9457 if(SiS_Pr->SiS_VBType & VB_SIS30xB)
9458 romptr = SISGETROMW(0x12a);
9460 romptr = SISGETROMW(0x1a8);
9461 if(SiS_Pr->SiS_VBType & VB_SIS30xB)
9462 romptr = SISGETROMW(0x1aa);
9467 static unsigned short
9468 GetLCDromptr(struct SiS_Private *SiS_Pr)
9470 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
9471 unsigned short romptr;
9473 if(SiS_Pr->ChipType < SIS_330) {
9474 romptr = SISGETROMW(0x120);
9475 if(SiS_Pr->SiS_VBType & VB_SIS30xBLV)
9476 romptr = SISGETROMW(0x122);
9478 romptr = SISGETROMW(0x1a0);
9479 if(SiS_Pr->SiS_VBType & VB_SIS30xBLV)
9480 romptr = SISGETROMW(0x1a2);
9485 static unsigned short
9486 GetTVromptr(struct SiS_Private *SiS_Pr)
9488 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
9489 unsigned short romptr;
9491 if(SiS_Pr->ChipType < SIS_330) {
9492 romptr = SISGETROMW(0x114);
9493 if(SiS_Pr->SiS_VBType & VB_SIS30xBLV)
9494 romptr = SISGETROMW(0x11a);
9496 romptr = SISGETROMW(0x194);
9497 if(SiS_Pr->SiS_VBType & VB_SIS30xBLV)
9498 romptr = SISGETROMW(0x19a);
9503 static unsigned short
9504 GetLCDPtrIndexBIOS(struct SiS_Private *SiS_Pr)
9506 unsigned short index;
9508 if((IS_SIS650) && (SiS_Pr->SiS_VBType & VB_SISLVDS)) {
9509 if(!(SiS_IsNotM650orLater(SiS_Pr))) {
9510 if((index = SiS_GetReg(SiS_Pr->SiS_P3d4,0x36) & 0xf0)) {
9513 if(SiS_Pr->SiS_LCDInfo & DontExpandLCD) index += 2;
9514 else if(!(SiS_Pr->SiS_SetFlag & LCDVESATiming)) index++;
9520 index = SiS_GetBIOSLCDResInfo(SiS_Pr) & 0x0F;
9521 if(SiS_Pr->SiS_LCDResInfo == Panel_1400x1050) index -= 5;
9522 if(SiS_Pr->SiS_VBType & VB_SIS301C) { /* 1.15.20 and later (not VB specific) */
9523 if(SiS_Pr->SiS_LCDResInfo == Panel_1600x1200) index -= 5;
9524 if(SiS_Pr->SiS_LCDResInfo == Panel_1280x768) index -= 5;
9526 if(SiS_Pr->SiS_LCDResInfo == Panel_1600x1200) index -= 6;
9530 if(SiS_Pr->SiS_LCDInfo & DontExpandLCD) index += 2;
9531 else if(!(SiS_Pr->SiS_SetFlag & LCDVESATiming)) index++;
9535 static unsigned short
9536 GetLCDPtrIndex(struct SiS_Private *SiS_Pr)
9538 unsigned short index;
9540 index = ((SiS_GetBIOSLCDResInfo(SiS_Pr) & 0x0F) - 1) * 3;
9541 if(SiS_Pr->SiS_LCDInfo & DontExpandLCD) index += 2;
9542 else if(!(SiS_Pr->SiS_SetFlag & LCDVESATiming)) index++;
9546 static unsigned short
9547 GetTVPtrIndex(struct SiS_Private *SiS_Pr)
9549 unsigned short index;
9552 if(SiS_Pr->SiS_TVMode & TVSetPAL) index = 1;
9553 if(SiS_Pr->SiS_VBInfo & SetCRT2ToHiVision) index = 2;
9555 if(SiS_Pr->SiS_VBInfo & SetCRT2ToYPbPr525750) index = 0;
9559 if((SiS_Pr->SiS_VBInfo & SetInSlaveMode) &&
9560 (SiS_Pr->SiS_TVMode & TVSetTVSimuMode)) {
9568 GetOEMTVPtr661_2_GEN(struct SiS_Private *SiS_Pr, int addme)
9570 unsigned short index = 0, temp = 0;
9572 if(SiS_Pr->SiS_TVMode & TVSetPAL) index = 1;
9573 if(SiS_Pr->SiS_TVMode & TVSetPALM) index = 2;
9574 if(SiS_Pr->SiS_TVMode & TVSetPALN) index = 3;
9575 if(SiS_Pr->SiS_TVMode & TVSetNTSCJ) index = 6;
9576 if(SiS_Pr->SiS_TVMode & TVSetNTSC1024) {
9578 if(SiS_Pr->SiS_TVMode & TVSetPALM) index++;
9579 if(SiS_Pr->SiS_TVMode & TVSetNTSCJ) index = 7;
9582 if(SiS_Pr->SiS_VBType & VB_SIS30xBLV) {
9583 if((!(SiS_Pr->SiS_VBInfo & SetInSlaveMode)) ||
9584 (SiS_Pr->SiS_TVMode & TVSetTVSimuMode)) {
9590 return (unsigned int)(index | (temp << 16));
9594 GetOEMTVPtr661_2_OLD(struct SiS_Private *SiS_Pr)
9596 return (GetOEMTVPtr661_2_GEN(SiS_Pr, 8));
9601 GetOEMTVPtr661_2_NEW(struct SiS_Private *SiS_Pr)
9603 return (GetOEMTVPtr661_2_GEN(SiS_Pr, 6));
9608 GetOEMTVPtr661(struct SiS_Private *SiS_Pr)
9612 if(SiS_Pr->SiS_TVMode & TVSetPAL) index = 2;
9613 if(SiS_Pr->SiS_ROMNew) {
9614 if(SiS_Pr->SiS_TVMode & TVSetYPbPr525i) index = 4;
9615 if(SiS_Pr->SiS_TVMode & TVSetYPbPr525p) index = 6;
9616 if(SiS_Pr->SiS_TVMode & TVSetYPbPr750p) index = 8;
9617 if(SiS_Pr->SiS_TVMode & TVSetHiVision) index = 10;
9619 if(SiS_Pr->SiS_TVMode & TVSetHiVision) index = 4;
9620 if(SiS_Pr->SiS_TVMode & TVSetYPbPr525i) index = 6;
9621 if(SiS_Pr->SiS_TVMode & TVSetYPbPr525p) index = 8;
9622 if(SiS_Pr->SiS_TVMode & TVSetYPbPr750p) index = 10;
9625 if(SiS_Pr->SiS_TVMode & TVSetTVSimuMode) index++;
9631 SetDelayComp(struct SiS_Private *SiS_Pr, unsigned short ModeNo)
9633 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
9634 unsigned short delay=0,index,myindex,temp,romptr=0;
9635 bool dochiptest = true;
9637 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCDA) {
9638 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x20,0xbf);
9640 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x35,0x7f);
9643 /* Find delay (from ROM, internal tables, PCI subsystem) */
9645 if(SiS_Pr->SiS_VBInfo & SetCRT2ToRAMDAC) { /* ------------ VGA */
9647 if((SiS_Pr->SiS_UseROM) && (!(SiS_Pr->SiS_ROMNew))) {
9648 romptr = GetRAMDACromptr(SiS_Pr);
9650 if(romptr) delay = ROMAddr[romptr];
9653 if(SiS_Pr->SiS_VBType & VB_SIS30xB) {
9656 } else if(IS_SIS740) {
9658 } else if(SiS_Pr->ChipType < SIS_330) {
9663 } else if(SiS_Pr->SiS_IF_DEF_LVDS == 1) {
9668 } else if(SiS_Pr->SiS_VBInfo & (SetCRT2ToLCD|SetCRT2ToLCDA)) { /* ---------- LCD/LCDA */
9670 bool gotitfrompci = false;
9672 /* Could we detect a PDC for LCD or did we get a user-defined? If yes, use it */
9674 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) {
9675 if(SiS_Pr->PDC != -1) {
9676 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x2d,0xf0,((SiS_Pr->PDC >> 1) & 0x0f));
9677 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x35,0x7f,((SiS_Pr->PDC & 0x01) << 7));
9681 if(SiS_Pr->PDCA != -1) {
9682 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x2d,0x0f,((SiS_Pr->PDCA << 3) & 0xf0));
9683 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x20,0xbf,((SiS_Pr->PDCA & 0x01) << 6));
9690 if(SiS_Pr->SiS_LCDResInfo == Panel_Custom) {
9691 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCDA) {
9693 if((SiS_Pr->PanelXRes <= 1280) && (SiS_Pr->PanelYRes <= 1024)) {
9696 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x2d,0x0f,delay);
9699 if(SiS_Pr->SiS_VBType & VB_SIS301C) {
9701 if((SiS_Pr->PanelXRes > 1280) && (SiS_Pr->PanelYRes > 1024)) {
9704 } else if(SiS_Pr->SiS_VBType & VB_SISLVDS) {
9705 if(IS_SIS740) delay = 0x01;
9708 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x2d,0xf0,delay);
9713 /* This is a piece of typical SiS crap: They code the OEM LCD
9714 * delay into the code, at no defined place in the BIOS.
9715 * We now have to start doing a PCI subsystem check here.
9718 switch(SiS_Pr->SiS_CustomT) {
9719 case CUT_COMPAQ1280:
9720 case CUT_COMPAQ12802:
9721 if(SiS_Pr->SiS_LCDResInfo == Panel_1280x1024) {
9722 gotitfrompci = true;
9728 case CUT_CLEVO14002:
9729 gotitfrompci = true;
9734 case CUT_CLEVO10242:
9735 if(SiS_Pr->SiS_LCDResInfo == Panel_1024x768) {
9736 gotitfrompci = true;
9739 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x2D,delay);
9745 /* Could we find it through the PCI ID? If no, use ROM or table */
9749 index = GetLCDPtrIndexBIOS(SiS_Pr);
9750 myindex = GetLCDPtrIndex(SiS_Pr);
9752 if(IS_SIS650 && (SiS_Pr->SiS_VBType & VB_SISLVDS)) {
9754 if(SiS_IsNotM650orLater(SiS_Pr)) {
9756 if((SiS_Pr->SiS_UseROM) && (!(SiS_Pr->SiS_ROMNew))) {
9757 /* Always use the second pointer on 650; some BIOSes */
9758 /* still carry old 301 data at the first location */
9759 /* romptr = SISGETROMW(0x120); */
9760 /* if(SiS_Pr->SiS_VBType & VB_SIS302LV) */
9761 romptr = SISGETROMW(0x122);
9763 delay = ROMAddr[(romptr + index)];
9765 delay = SiS310_LCDDelayCompensation_650301LV[myindex];
9770 delay = SiS310_LCDDelayCompensation_651301LV[myindex];
9771 if(SiS_Pr->SiS_VBType & (VB_SIS302LV | VB_SIS302ELV))
9772 delay = SiS310_LCDDelayCompensation_651302LV[myindex];
9776 } else if(SiS_Pr->SiS_UseROM &&
9777 (!(SiS_Pr->SiS_ROMNew)) &&
9778 (SiS_Pr->SiS_LCDResInfo != Panel_1280x1024) &&
9779 (SiS_Pr->SiS_LCDResInfo != Panel_1280x768) &&
9780 (SiS_Pr->SiS_LCDResInfo != Panel_1280x960) &&
9781 (SiS_Pr->SiS_LCDResInfo != Panel_1600x1200) &&
9782 ((romptr = GetLCDromptr(SiS_Pr)))) {
9784 /* Data for 1280x1024 wrong in 301B BIOS */
9785 /* Data for 1600x1200 wrong in 301C BIOS */
9786 delay = ROMAddr[(romptr + index)];
9788 } else if(SiS_Pr->SiS_IF_DEF_LVDS == 1) {
9790 if(IS_SIS740) delay = 0x03;
9795 delay = SiS310_LCDDelayCompensation_301[myindex];
9796 if(SiS_Pr->SiS_VBType & VB_SISLVDS) {
9797 if(IS_SIS740) delay = 0x01;
9798 else if(SiS_Pr->ChipType <= SIS_315PRO) delay = SiS310_LCDDelayCompensation_3xx301LV[myindex];
9799 else delay = SiS310_LCDDelayCompensation_650301LV[myindex];
9800 } else if(SiS_Pr->SiS_VBType & VB_SIS301C) {
9801 if(IS_SIS740) delay = 0x01; /* ? */
9803 if(SiS_Pr->SiS_LCDResInfo == Panel_1600x1200) delay = 0x00; /* experience */
9804 } else if(SiS_Pr->SiS_VBType & VB_SIS30xB) {
9805 if(IS_SIS740) delay = 0x01;
9806 else delay = SiS310_LCDDelayCompensation_3xx301B[myindex];
9811 } /* got it from PCI */
9813 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCDA) {
9814 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x2D,0x0F,((delay << 4) & 0xf0));
9818 } else if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) { /* ------------ TV */
9820 index = GetTVPtrIndex(SiS_Pr);
9822 if(IS_SIS650 && (SiS_Pr->SiS_VBType & VB_SISLVDS)) {
9824 if(SiS_IsNotM650orLater(SiS_Pr)) {
9826 if((SiS_Pr->SiS_UseROM) && (!(SiS_Pr->SiS_ROMNew))) {
9827 /* Always use the second pointer on 650; some BIOSes */
9828 /* still carry old 301 data at the first location */
9829 /* romptr = SISGETROMW(0x114); */
9830 /* if(SiS_Pr->SiS_VBType & VB_SIS302LV) */
9831 romptr = SISGETROMW(0x11a);
9833 delay = ROMAddr[romptr + index];
9837 delay = SiS310_TVDelayCompensation_301B[index];
9843 switch(SiS_Pr->SiS_CustomT) {
9844 case CUT_COMPAQ1280:
9845 case CUT_COMPAQ12802:
9847 case CUT_CLEVO14002:
9852 case CUT_CLEVO10242:
9857 delay = SiS310_TVDelayCompensation_651301LV[index];
9858 if(SiS_Pr->SiS_VBType & VB_SIS302LV) {
9859 delay = SiS310_TVDelayCompensation_651302LV[index];
9864 } else if((SiS_Pr->SiS_UseROM) && (!(SiS_Pr->SiS_ROMNew))) {
9866 romptr = GetTVromptr(SiS_Pr);
9868 delay = ROMAddr[romptr + index];
9870 } else if(SiS_Pr->SiS_IF_DEF_LVDS == 1) {
9872 delay = SiS310_TVDelayCompensation_LVDS[index];
9876 delay = SiS310_TVDelayCompensation_301[index];
9877 if(SiS_Pr->SiS_VBType & VB_SIS30xBLV) {
9879 delay = SiS310_TVDelayCompensation_740301B[index];
9880 /* LV: use 301 data? BIOS bug? */
9882 delay = SiS310_TVDelayCompensation_301B[index];
9883 if(SiS_Pr->SiS_VBType & VB_SIS301C) delay = 0x02;
9889 if(SiS_LCDAEnabled(SiS_Pr)) {
9898 if(SiS_Pr->SiS_VBType & VB_SISVB) {
9900 if(IS_SIS650 && (SiS_Pr->SiS_VBType & VB_SISLVDS) && dochiptest) {
9902 temp = (SiS_GetReg(SiS_Pr->SiS_P3d4,0x36) & 0xf0) >> 4;
9903 if(temp == 8) { /* 1400x1050 BIOS (COMPAL) */
9906 } else if(temp == 6) {
9909 } else if(temp > 7) { /* 1280x1024 BIOS (which one?) */
9912 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x2D,delay);
9916 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x2D,0xF0,delay);
9922 if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) {
9923 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x2D,0xF0,delay);
9925 if(IS_SIS650 && (SiS_Pr->SiS_IF_DEF_CH70xx != 0)) {
9927 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x2D,0x0F,delay);
9929 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x2D,0xF0,delay);
9938 SetAntiFlicker(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex)
9940 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
9941 unsigned short index,temp,temp1,romptr=0;
9943 if(SiS_Pr->SiS_TVMode & (TVSetYPbPr750p|TVSetYPbPr525p)) return;
9946 index = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].VB_StTVFlickerIndex;
9948 index = SiS_Pr->SiS_EModeIDTable[ModeIdIndex].VB_ExtTVFlickerIndex;
9950 temp = GetTVPtrIndex(SiS_Pr);
9951 temp >>= 1; /* 0: NTSC/YPbPr, 1: PAL, 2: HiTV */
9954 if(SiS_Pr->SiS_UseROM && (!(SiS_Pr->SiS_ROMNew))) {
9955 if(SiS_Pr->ChipType >= SIS_661) {
9956 temp1 = GetOEMTVPtr661(SiS_Pr);
9958 romptr = SISGETROMW(0x260);
9959 if(SiS_Pr->ChipType >= SIS_760) {
9960 romptr = SISGETROMW(0x360);
9962 } else if(SiS_Pr->ChipType >= SIS_330) {
9963 romptr = SISGETROMW(0x192);
9965 romptr = SISGETROMW(0x112);
9971 temp = ROMAddr[romptr + temp1 + index];
9973 temp = SiS310_TVAntiFlick1[temp][index];
9977 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x0A,0x8f,temp); /* index 0A D[6:4] */
9981 SetEdgeEnhance(struct SiS_Private *SiS_Pr, unsigned short ModeNo,unsigned short ModeIdIndex)
9983 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
9984 unsigned short index,temp,temp1,romptr=0;
9986 temp = temp1 = GetTVPtrIndex(SiS_Pr) >> 1; /* 0: NTSC/YPbPr, 1: PAL, 2: HiTV */
9989 index = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].VB_StTVEdgeIndex;
9991 index = SiS_Pr->SiS_EModeIDTable[ModeIdIndex].VB_ExtTVEdgeIndex;
9993 if(SiS_Pr->SiS_UseROM && (!(SiS_Pr->SiS_ROMNew))) {
9994 if(SiS_Pr->ChipType >= SIS_661) {
9995 romptr = SISGETROMW(0x26c);
9996 if(SiS_Pr->ChipType >= SIS_760) {
9997 romptr = SISGETROMW(0x36c);
9999 temp1 = GetOEMTVPtr661(SiS_Pr);
10001 } else if(SiS_Pr->ChipType >= SIS_330) {
10002 romptr = SISGETROMW(0x1a4);
10004 romptr = SISGETROMW(0x124);
10010 temp = ROMAddr[romptr + temp1 + index];
10012 temp = SiS310_TVEdge1[temp][index];
10015 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x3A,0x1F,temp); /* index 0A D[7:5] */
10019 SetYFilter(struct SiS_Private *SiS_Pr, unsigned short ModeNo,unsigned short ModeIdIndex)
10021 unsigned short index, temp, i, j;
10023 if(ModeNo <= 0x13) {
10024 index = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].VB_StTVYFilterIndex;
10026 index = SiS_Pr->SiS_EModeIDTable[ModeIdIndex].VB_ExtTVYFilterIndex;
10029 temp = GetTVPtrIndex(SiS_Pr) >> 1; /* 0: NTSC/YPbPr, 1: PAL, 2: HiTV */
10031 if(SiS_Pr->SiS_TVMode & TVSetNTSCJ) temp = 1; /* NTSC-J uses PAL */
10032 else if(SiS_Pr->SiS_TVMode & TVSetPALM) temp = 3; /* PAL-M */
10033 else if(SiS_Pr->SiS_TVMode & TVSetPALN) temp = 4; /* PAL-N */
10034 if(SiS_Pr->SiS_VBInfo & SetCRT2ToHiVision) temp = 1; /* HiVision uses PAL */
10036 if(SiS_Pr->SiS_VBType & VB_SIS30xBLV) {
10037 for(i=0x35, j=0; i<=0x38; i++, j++) {
10038 SiS_SetReg(SiS_Pr->SiS_Part2Port,i,SiS310_TVYFilter2[temp][index][j]);
10040 for(i=0x48; i<=0x4A; i++, j++) {
10041 SiS_SetReg(SiS_Pr->SiS_Part2Port,i,SiS310_TVYFilter2[temp][index][j]);
10044 for(i=0x35, j=0; i<=0x38; i++, j++) {
10045 SiS_SetReg(SiS_Pr->SiS_Part2Port,i,SiS310_TVYFilter1[temp][index][j]);
10051 SetPhaseIncr(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex)
10053 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
10054 unsigned short index,temp,i,j,resinfo,romptr=0;
10055 unsigned int lindex;
10057 if(!(SiS_Pr->SiS_VBInfo & SetCRT2ToTV)) return;
10059 /* NTSC-J data not in BIOS, and already set in SetGroup2 */
10060 if(SiS_Pr->SiS_TVMode & TVSetNTSCJ) return;
10062 if((SiS_Pr->ChipType >= SIS_661) || SiS_Pr->SiS_ROMNew) {
10063 lindex = GetOEMTVPtr661_2_OLD(SiS_Pr) & 0xffff;
10065 for(j=0, i=0x31; i<=0x34; i++, j++) {
10066 SiS_SetReg(SiS_Pr->SiS_Part2Port,i,SiS_TVPhase[lindex + j]);
10071 /* PAL-M, PAL-N not in BIOS, and already set in SetGroup2 */
10072 if(SiS_Pr->SiS_TVMode & (TVSetPALM | TVSetPALN)) return;
10075 resinfo = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_ResInfo;
10077 resinfo = SiS_Pr->SiS_EModeIDTable[ModeIdIndex].Ext_RESINFO;
10080 temp = GetTVPtrIndex(SiS_Pr);
10081 /* 0: NTSC Graphics, 1: NTSC Text, 2: PAL Graphics,
10082 * 3: PAL Text, 4: HiTV Graphics 5: HiTV Text
10084 if(SiS_Pr->SiS_UseROM) {
10085 romptr = SISGETROMW(0x116);
10086 if(SiS_Pr->ChipType >= SIS_330) {
10087 romptr = SISGETROMW(0x196);
10089 if(SiS_Pr->SiS_VBType & VB_SIS30xBLV) {
10090 romptr = SISGETROMW(0x11c);
10091 if(SiS_Pr->ChipType >= SIS_330) {
10092 romptr = SISGETROMW(0x19c);
10094 if((SiS_Pr->SiS_VBInfo & SetInSlaveMode) && (!(SiS_Pr->SiS_TVMode & TVSetTVSimuMode))) {
10095 romptr = SISGETROMW(0x116);
10096 if(SiS_Pr->ChipType >= SIS_330) {
10097 romptr = SISGETROMW(0x196);
10103 romptr += (temp << 2);
10104 for(j=0, i=0x31; i<=0x34; i++, j++) {
10105 SiS_SetReg(SiS_Pr->SiS_Part2Port,i,ROMAddr[romptr + j]);
10109 temp >>= 1; /* 0:NTSC, 1:PAL, 2:HiTV */
10110 for(j=0, i=0x31; i<=0x34; i++, j++) {
10111 if(!(SiS_Pr->SiS_VBType & VB_SIS30xBLV))
10112 SiS_SetReg(SiS_Pr->SiS_Part2Port,i,SiS310_TVPhaseIncr1[temp][index][j]);
10113 else if((!(SiS_Pr->SiS_VBInfo & SetInSlaveMode)) || (SiS_Pr->SiS_TVMode & TVSetTVSimuMode))
10114 SiS_SetReg(SiS_Pr->SiS_Part2Port,i,SiS310_TVPhaseIncr2[temp][index][j]);
10116 SiS_SetReg(SiS_Pr->SiS_Part2Port,i,SiS310_TVPhaseIncr1[temp][index][j]);
10120 if((SiS_Pr->SiS_VBType & VB_SIS30xBLV) && (!(SiS_Pr->SiS_VBInfo & SetCRT2ToHiVision))) {
10121 if((!(SiS_Pr->SiS_TVMode & (TVSetPAL | TVSetYPbPr525p | TVSetYPbPr750p))) && (ModeNo > 0x13)) {
10122 if((resinfo == SIS_RI_640x480) ||
10123 (resinfo == SIS_RI_800x600)) {
10124 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x31,0x21);
10125 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x32,0xf0);
10126 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x33,0xf5);
10127 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x34,0x7f);
10128 } else if(resinfo == SIS_RI_1024x768) {
10129 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x31,0x1e);
10130 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x32,0x8b);
10131 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x33,0xfb);
10132 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x34,0x7b);
10139 SetDelayComp661(struct SiS_Private *SiS_Pr, unsigned short ModeNo,
10140 unsigned short ModeIdIndex, unsigned short RTI)
10142 unsigned short delay = 0, romptr = 0, index, lcdpdcindex;
10143 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
10145 if(!(SiS_Pr->SiS_VBInfo & (SetCRT2ToTV | SetCRT2ToLCD | SetCRT2ToLCDA | SetCRT2ToRAMDAC)))
10148 /* 1. New ROM: VGA2 and LCD/LCDA-Pass1:1 */
10149 /* (If a custom mode is used, Pass1:1 is always set; hence we do this:) */
10151 if(SiS_Pr->SiS_ROMNew) {
10152 if((SiS_Pr->SiS_VBInfo & SetCRT2ToRAMDAC) ||
10153 ((SiS_Pr->SiS_VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) &&
10154 (SiS_Pr->SiS_LCDInfo & LCDPass11))) {
10156 if(SiS_Pr->UseCustomMode) {
10157 index = SiS_Pr->CSRClock;
10158 } else if(ModeNo > 0x13) {
10159 index = SiS_GetVCLK2Ptr(SiS_Pr,ModeNo,ModeIdIndex,RTI);
10160 index = SiS_Pr->SiS_VCLKData[index].CLOCK;
10162 if(index < 25) index = 25;
10163 index = ((index / 25) - 1) << 1;
10164 if((ROMAddr[0x5b] & 0x80) || (SiS_Pr->SiS_VBInfo & (SetCRT2ToRAMDAC | SetCRT2ToLCD))) {
10167 romptr = SISGETROMW(0x104);
10168 delay = ROMAddr[romptr + index];
10169 if(SiS_Pr->SiS_VBInfo & (SetCRT2ToRAMDAC | SetCRT2ToLCD)) {
10170 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x2d,0xf0,((delay >> 1) & 0x0f));
10171 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x35,0x7f,((delay & 0x01) << 7));
10173 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x2d,0x0f,((delay << 3) & 0xf0));
10174 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x20,0xbf,((delay & 0x01) << 6));
10180 /* 2. Old ROM: VGA2 and LCD/LCDA-Pass 1:1 */
10182 if(SiS_Pr->UseCustomMode) delay = 0x04;
10183 else if(ModeNo <= 0x13) delay = 0x04;
10184 else delay = (SiS_Pr->SiS_RefIndex[RTI].Ext_PDC >> 4);
10185 delay |= (delay << 8);
10187 if(SiS_Pr->ChipType >= XGI_20) {
10190 if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) {
10193 if(SiS_Pr->SiS_XGIROM) {
10194 index = GetTVPtrIndex(SiS_Pr);
10195 if((romptr = SISGETROMW(0x35e))) {
10196 delay = (ROMAddr[romptr + index] & 0x0f) << 1;
10197 delay |= (delay << 8);
10201 if(SiS_Pr->SiS_VBInfo & SetCRT2ToHiVision) {
10202 if(SiS_Pr->ChipType == XGI_40 && SiS_Pr->ChipRevision == 0x02) {
10208 } else if(SiS_Pr->ChipType >= SIS_340) {
10211 if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) {
10214 /* TODO (eventually) */
10216 } else if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) {
10220 index = GetOEMTVPtr661(SiS_Pr);
10221 if(SiS_Pr->SiS_ROMNew) {
10222 romptr = SISGETROMW(0x106);
10223 if(SiS_Pr->SiS_VBType & VB_UMC) romptr += 12;
10224 delay = ROMAddr[romptr + index];
10227 if(index > 3) delay = 0;
10230 } else if(SiS_Pr->SiS_VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
10232 /* 4. LCD, LCDA (for new ROM only LV and non-Pass 1:1) */
10234 if( (SiS_Pr->SiS_LCDResInfo != Panel_Custom) &&
10235 ((romptr = GetLCDStructPtr661_2(SiS_Pr))) ) {
10237 lcdpdcindex = (SiS_Pr->SiS_VBType & VB_UMC) ? 14 : 12;
10239 /* For LVDS (and sometimes TMDS), the BIOS must know about the correct value */
10240 delay = ROMAddr[romptr + lcdpdcindex + 1]; /* LCD */
10241 delay |= (ROMAddr[romptr + lcdpdcindex] << 8); /* LCDA */
10245 /* TMDS: Set our own, since BIOS has no idea */
10246 /* (This is done on >=661 only, since <661 is calling this only for LVDS) */
10247 if(!(SiS_Pr->SiS_LCDInfo & LCDPass11)) {
10248 switch(SiS_Pr->SiS_LCDResInfo) {
10249 case Panel_1024x768: delay = 0x0008; break;
10250 case Panel_1280x720: delay = 0x0004; break;
10251 case Panel_1280x768:
10252 case Panel_1280x768_2:delay = 0x0004; break;
10253 case Panel_1280x800:
10254 case Panel_1280x800_2:delay = 0x0004; break; /* Verified for 1280x800 */
10255 case Panel_1280x854: delay = 0x0004; break; /* FIXME */
10256 case Panel_1280x1024: delay = 0x1e04; break;
10257 case Panel_1400x1050: delay = 0x0004; break;
10258 case Panel_1600x1200: delay = 0x0400; break;
10259 case Panel_1680x1050: delay = 0x0e04; break;
10261 if((SiS_Pr->PanelXRes <= 1024) && (SiS_Pr->PanelYRes <= 768)) {
10263 } else if((SiS_Pr->PanelXRes == 1280) && (SiS_Pr->PanelYRes == 1024)) {
10265 } else if((SiS_Pr->PanelXRes <= 1400) && (SiS_Pr->PanelYRes <= 1050)) {
10267 } else if((SiS_Pr->PanelXRes <= 1600) && (SiS_Pr->PanelYRes <= 1200)) {
10275 /* Override by detected or user-set values */
10276 /* (but only if, for some reason, we can't read value from BIOS) */
10277 if((SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) && (SiS_Pr->PDC != -1)) {
10278 delay = SiS_Pr->PDC & 0x1f;
10280 if((SiS_Pr->SiS_VBInfo & SetCRT2ToLCDA) && (SiS_Pr->PDCA != -1)) {
10281 delay = (SiS_Pr->PDCA & 0x1f) << 8;
10288 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCDA) {
10290 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x2d,0x0f,((delay << 3) & 0xf0));
10291 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x20,0xbf,((delay & 0x01) << 6));
10293 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x2d,0xf0,((delay >> 1) & 0x0f));
10294 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x35,0x7f,((delay & 0x01) << 7));
10299 SetCRT2SyncDither661(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short RTI)
10301 unsigned short infoflag;
10302 unsigned char temp;
10304 if(SiS_Pr->SiS_VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
10306 if(ModeNo <= 0x13) {
10307 infoflag = SiS_GetRegByte(SiS_Pr->SiS_P3ca+2);
10308 } else if(SiS_Pr->UseCustomMode) {
10309 infoflag = SiS_Pr->CInfoFlag;
10311 infoflag = SiS_Pr->SiS_RefIndex[RTI].Ext_InfoFlag;
10314 if(!(SiS_Pr->SiS_LCDInfo & LCDPass11)) {
10315 infoflag = SiS_GetReg(SiS_Pr->SiS_P3d4,0x37); /* No longer check D5 */
10320 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) {
10321 temp = (infoflag >> 6) | 0x0c;
10322 if(SiS_Pr->SiS_LCDInfo & LCDRGB18Bit) {
10324 if(SiS_Pr->SiS_ModeType >= Mode24Bpp) temp |= 0x10;
10326 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x1a,0xe0,temp);
10329 if(SiS_Pr->SiS_LCDInfo & LCDRGB18Bit) temp = 0x20;
10331 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x19,0x0f,temp);
10333 if(SiS_Pr->SiS_LCDInfo & LCDRGB18Bit) {
10334 if(SiS_Pr->SiS_ModeType >= Mode24Bpp) temp |= 0x80;
10336 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x1a,0x7f,temp);
10343 SetPanelParms661(struct SiS_Private *SiS_Pr)
10345 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
10346 unsigned short romptr, temp1, temp2;
10348 if(SiS_Pr->SiS_VBType & (VB_SISLVDS | VB_SIS30xC)) {
10349 SiS_SetRegAND(SiS_Pr->SiS_Part4Port,0x24,0x0f);
10352 if(SiS_Pr->SiS_VBType & VB_SISLVDS) {
10353 if(SiS_Pr->LVDSHL != -1) {
10354 SiS_SetRegANDOR(SiS_Pr->SiS_Part4Port,0x24,0xfc,SiS_Pr->LVDSHL);
10358 if(SiS_Pr->SiS_ROMNew) {
10360 if((romptr = GetLCDStructPtr661_2(SiS_Pr))) {
10361 if(SiS_Pr->SiS_VBType & VB_SISLVDS) {
10362 temp1 = (ROMAddr[romptr] & 0x03) | 0x0c;
10364 if(SiS_Pr->LVDSHL != -1) {
10368 SiS_SetRegANDOR(SiS_Pr->SiS_Part4Port,0x24,temp2,temp1);
10370 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) {
10371 temp1 = (ROMAddr[romptr + 1] & 0x80) >> 1;
10372 SiS_SetRegANDOR(SiS_Pr->SiS_Part4Port,0x0d,0xbf,temp1);
10380 SiS_OEM310Setting(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex, unsigned short RRTI)
10382 if((SiS_Pr->SiS_ROMNew) && (SiS_Pr->SiS_VBType & VB_SISLVDS)) {
10383 SetDelayComp661(SiS_Pr, ModeNo, ModeIdIndex, RRTI);
10384 if(SiS_Pr->SiS_VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
10385 SetCRT2SyncDither661(SiS_Pr, ModeNo, RRTI);
10386 SetPanelParms661(SiS_Pr);
10389 SetDelayComp(SiS_Pr,ModeNo);
10392 if((SiS_Pr->SiS_VBType & VB_SISVB) && (SiS_Pr->SiS_VBInfo & SetCRT2ToTV)) {
10393 SetAntiFlicker(SiS_Pr,ModeNo,ModeIdIndex);
10394 SetPhaseIncr(SiS_Pr,ModeNo,ModeIdIndex);
10395 SetYFilter(SiS_Pr,ModeNo,ModeIdIndex);
10396 if(SiS_Pr->SiS_VBType & VB_SIS301) {
10397 SetEdgeEnhance(SiS_Pr,ModeNo,ModeIdIndex);
10403 SiS_OEM661Setting(struct SiS_Private *SiS_Pr, unsigned short ModeNo,
10404 unsigned short ModeIdIndex, unsigned short RRTI)
10406 if(SiS_Pr->SiS_VBType & VB_SISVB) {
10408 SetDelayComp661(SiS_Pr, ModeNo, ModeIdIndex, RRTI);
10410 if(SiS_Pr->SiS_VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
10411 SetCRT2SyncDither661(SiS_Pr, ModeNo, RRTI);
10412 SetPanelParms661(SiS_Pr);
10415 if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) {
10416 SetPhaseIncr(SiS_Pr, ModeNo, ModeIdIndex);
10417 SetYFilter(SiS_Pr, ModeNo, ModeIdIndex);
10418 SetAntiFlicker(SiS_Pr, ModeNo, ModeIdIndex);
10419 if(SiS_Pr->SiS_VBType & VB_SIS301) {
10420 SetEdgeEnhance(SiS_Pr, ModeNo, ModeIdIndex);
10427 * This finalizes some CRT2 registers for the very panel used.
10428 * If we have a backup if these registers, we use it; otherwise
10429 * we set the register according to most BIOSes. However, this
10430 * function looks quite different in every BIOS, so you better
10431 * pray that we have a backup...
10434 SiS_FinalizeLCD(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex)
10436 unsigned short tempcl,tempch,tempbl,tempbh,tempbx,tempax,temp;
10437 unsigned short resinfo,modeflag;
10439 if(!(SiS_Pr->SiS_VBType & VB_SISLVDS)) return;
10440 if(SiS_Pr->SiS_ROMNew) return;
10442 if(SiS_Pr->SiS_VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
10443 if(SiS_Pr->LVDSHL != -1) {
10444 SiS_SetRegANDOR(SiS_Pr->SiS_Part4Port,0x24,0xfc,SiS_Pr->LVDSHL);
10448 if(SiS_Pr->SiS_LCDResInfo == Panel_Custom) return;
10449 if(SiS_Pr->UseCustomMode) return;
10451 switch(SiS_Pr->SiS_CustomT) {
10452 case CUT_COMPAQ1280:
10453 case CUT_COMPAQ12802:
10454 case CUT_CLEVO1400:
10455 case CUT_CLEVO14002:
10459 if(ModeNo <= 0x13) {
10460 resinfo = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_ResInfo;
10461 modeflag = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_ModeFlag;
10463 resinfo = SiS_Pr->SiS_EModeIDTable[ModeIdIndex].Ext_RESINFO;
10464 modeflag = SiS_Pr->SiS_EModeIDTable[ModeIdIndex].Ext_ModeFlag;
10468 if(!(SiS_GetReg(SiS_Pr->SiS_P3d4, 0x5f) & 0xf0)) {
10469 if(SiS_Pr->SiS_CustomT == CUT_CLEVO1024) {
10470 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x1e,0x02);
10472 SiS_SetRegOR(SiS_Pr->SiS_Part1Port,0x1e,0x03);
10477 if(SiS_Pr->SiS_CustomT == CUT_CLEVO1024) {
10478 if(SiS_Pr->SiS_LCDResInfo == Panel_1024x768) {
10479 /* Maybe all panels? */
10480 if(SiS_Pr->LVDSHL == -1) {
10481 SiS_SetRegANDOR(SiS_Pr->SiS_Part4Port,0x24,0xfc,0x01);
10487 if(SiS_Pr->SiS_CustomT == CUT_CLEVO10242) {
10488 if(SiS_Pr->SiS_VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
10489 if(SiS_Pr->SiS_LCDResInfo == Panel_1024x768) {
10490 if(SiS_Pr->LVDSHL == -1) {
10491 /* Maybe all panels? */
10492 SiS_SetRegANDOR(SiS_Pr->SiS_Part4Port,0x24,0xfc,0x01);
10494 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCDA) {
10495 tempch = SiS_GetReg(SiS_Pr->SiS_P3d4,0x36) >> 4;
10497 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x18,0x02);
10498 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x1b,0x25);
10499 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x1c,0x00);
10500 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x1d,0x1b);
10508 if(SiS_Pr->SiS_VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
10509 if(SiS_Pr->SiS_LCDResInfo == Panel_1024x768) {
10510 if(SiS_Pr->SiS_VBType & VB_SISEMI) {
10511 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x2a,0x00);
10513 SiS_SetRegAND(SiS_Pr->SiS_Part4Port,0x30,0x0c);
10515 SiS_SetReg(SiS_Pr->SiS_Part4Port,0x34,0x10);
10517 } else if(SiS_Pr->SiS_LCDResInfo == Panel_1280x1024) {
10518 if(SiS_Pr->LVDSHL == -1) {
10519 /* Maybe ACER only? */
10520 SiS_SetRegANDOR(SiS_Pr->SiS_Part4Port,0x24,0xfc,0x01);
10523 tempch = SiS_GetReg(SiS_Pr->SiS_P3d4,0x36) >> 4;
10524 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCDA) {
10525 if(SiS_Pr->SiS_LCDResInfo == Panel_1400x1050) {
10526 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x1f,0x76);
10527 } else if(SiS_Pr->SiS_LCDResInfo == Panel_1024x768) {
10528 if(tempch == 0x03) {
10529 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x18,0x02);
10530 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x1b,0x25);
10531 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x1c,0x00);
10532 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x1d,0x1b);
10534 if(SiS_Pr->Backup && (SiS_Pr->Backup_Mode == ModeNo)) {
10535 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x14,SiS_Pr->Backup_14);
10536 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x15,SiS_Pr->Backup_15);
10537 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x16,SiS_Pr->Backup_16);
10538 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x17,SiS_Pr->Backup_17);
10539 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x18,SiS_Pr->Backup_18);
10540 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x19,SiS_Pr->Backup_19);
10541 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x1a,SiS_Pr->Backup_1a);
10542 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x1b,SiS_Pr->Backup_1b);
10543 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x1c,SiS_Pr->Backup_1c);
10544 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x1d,SiS_Pr->Backup_1d);
10545 } else if(!(SiS_Pr->SiS_LCDInfo & DontExpandLCD)) { /* 1.10.8w */
10546 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x14,0x90);
10547 if(ModeNo <= 0x13) {
10548 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x18,0x11);
10549 if((resinfo == 0) || (resinfo == 2)) return;
10550 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x18,0x18);
10551 if((resinfo == 1) || (resinfo == 3)) return;
10553 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x18,0x02);
10554 if((ModeNo > 0x13) && (resinfo == SIS_RI_1024x768)) {
10555 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x18,0x02); /* 1.10.7u */
10557 tempbx = 806; /* 0x326 */ /* other older BIOSes */
10559 temp = tempbx & 0xff;
10560 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x1b,temp);
10561 temp = (tempbx >> 8) & 0x03;
10562 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x1d,0xf8,temp);
10565 } else if(ModeNo <= 0x13) {
10567 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x18,0x70);
10568 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x19,0xff);
10569 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x1b,0x48);
10570 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x1d,0x12);
10572 if(!(modeflag & HalfDCLK)) {
10573 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x14,0x20);
10574 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x15,0x1a);
10575 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x16,0x28);
10576 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x17,0x00);
10577 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x18,0x4c);
10578 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x19,0xdc);
10579 if(ModeNo == 0x12) {
10582 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x18,0x95);
10583 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x19,0xdc);
10584 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x1a,0x10);
10585 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x1b,0x95);
10586 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x1c,0x48);
10587 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x1d,0x12);
10590 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x18,0x95);
10591 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x1b,0x48);
10594 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x1b,0x95);
10602 tempcl = tempbh = SiS_GetReg(SiS_Pr->SiS_Part2Port,0x01);
10606 tempbl = SiS_GetReg(SiS_Pr->SiS_Part2Port,0x04);
10607 tempbx = (tempbh << 8) | tempbl;
10608 if(SiS_Pr->SiS_LCDResInfo == Panel_1024x768) {
10609 if((resinfo == SIS_RI_1024x768) || (!(SiS_Pr->SiS_LCDInfo & DontExpandLCD))) {
10610 if(SiS_Pr->SiS_SetFlag & LCDVESATiming) {
10613 if(tempbx > 770) tempbx = 770;
10614 if(SiS_Pr->SiS_VGAVDE < 600) {
10615 tempax = 768 - SiS_Pr->SiS_VGAVDE;
10616 tempax >>= 4; /* 1.10.7w; 1.10.6s: 3; */
10617 if(SiS_Pr->SiS_VGAVDE <= 480) tempax >>= 4; /* 1.10.7w; 1.10.6s: < 480; >>=1; */
10623 temp = tempbx & 0xff;
10624 SiS_SetReg(SiS_Pr->SiS_Part2Port,0x04,temp);
10625 temp = ((tempbx & 0xff00) >> 4) | tempcl;
10626 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x01,0x80,temp);
10633 /* ================= SiS 300 O.E.M. ================== */
10635 #ifdef CONFIG_FB_SIS_300
10638 SetOEMLCDData2(struct SiS_Private *SiS_Pr, unsigned short ModeNo,unsigned short ModeIdIndex,
10639 unsigned short RefTabIndex)
10641 unsigned short crt2crtc=0, modeflag, myindex=0;
10642 unsigned char temp;
10645 if(ModeNo <= 0x13) {
10646 modeflag = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_ModeFlag;
10647 crt2crtc = SiS_Pr->SiS_SModeIDTable[ModeIdIndex].St_CRT2CRTC;
10649 modeflag = SiS_Pr->SiS_EModeIDTable[ModeIdIndex].Ext_ModeFlag;
10650 crt2crtc = SiS_Pr->SiS_RefIndex[RefTabIndex].Ext_CRT2CRTC;
10655 if(SiS_Pr->SiS_CustomT == CUT_BARCO1024) {
10656 SiS_SetRegAND(SiS_Pr->SiS_Part1Port,0x13,0xdf);
10659 if(SiS_Pr->SiS_CustomT == CUT_BARCO1366) {
10660 if(modeflag & HalfDCLK) myindex = 1;
10662 if(SiS_Pr->SiS_SetFlag & LowModeTests) {
10663 for(i=0; i<7; i++) {
10664 if(barco_p1[myindex][crt2crtc][i][0]) {
10665 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,
10666 barco_p1[myindex][crt2crtc][i][0],
10667 barco_p1[myindex][crt2crtc][i][2],
10668 barco_p1[myindex][crt2crtc][i][1]);
10672 temp = SiS_GetReg(SiS_Pr->SiS_Part1Port,0x00);
10674 temp = SiS_GetReg(SiS_Pr->SiS_Part1Port,0x18);
10676 SiS_SetReg(SiS_Pr->SiS_Part1Port,0x18,temp);
10681 static unsigned short
10682 GetOEMLCDPtr(struct SiS_Private *SiS_Pr, int Flag)
10684 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
10685 unsigned short tempbx=0,romptr=0;
10686 static const unsigned char customtable300[] = {
10687 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,
10688 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff
10690 static const unsigned char customtable630[] = {
10691 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,
10692 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff
10695 if(SiS_Pr->ChipType == SIS_300) {
10697 tempbx = SiS_GetReg(SiS_Pr->SiS_P3d4,0x36) & 0x0f;
10698 if(SiS_Pr->SiS_VBType & VB_SIS301) tempbx &= 0x07;
10700 if(!(SiS_Pr->SiS_SetFlag & LCDVESATiming)) tempbx += 4;
10701 if(SiS_Pr->SiS_LCDResInfo == Panel_1024x768) {
10702 if(SiS_Pr->SiS_LCDInfo & DontExpandLCD) tempbx += 3;
10704 if(SiS_Pr->SiS_UseROM) {
10705 if(ROMAddr[0x235] & 0x80) {
10706 tempbx = SiS_Pr->SiS_LCDTypeInfo;
10708 romptr = SISGETROMW(0x255);
10709 if(romptr) tempbx = ROMAddr[romptr + SiS_Pr->SiS_LCDTypeInfo];
10710 else tempbx = customtable300[SiS_Pr->SiS_LCDTypeInfo];
10711 if(tempbx == 0xFF) return 0xFFFF;
10714 if(!(SiS_Pr->SiS_SetFlag & LCDVESATiming)) tempbx++;
10721 if(SiS_Pr->SiS_UseROM) {
10722 romptr = SISGETROMW(0x255);
10723 if(romptr) tempbx = ROMAddr[romptr + SiS_Pr->SiS_LCDTypeInfo];
10724 else tempbx = 0xff;
10726 tempbx = customtable630[SiS_Pr->SiS_LCDTypeInfo];
10728 if(tempbx == 0xFF) return 0xFFFF;
10730 if(SiS_Pr->SiS_VBInfo & SetInSlaveMode) tempbx += 2;
10731 if(SiS_Pr->SiS_LCDInfo & DontExpandLCD) tempbx++;
10734 tempbx = SiS_Pr->SiS_LCDTypeInfo << 2;
10735 if(SiS_Pr->SiS_VBInfo & SetInSlaveMode) tempbx += 2;
10736 if(SiS_Pr->SiS_LCDInfo & DontExpandLCD) tempbx++;
10744 SetOEMLCDDelay(struct SiS_Private *SiS_Pr, unsigned short ModeNo,unsigned short ModeIdIndex)
10746 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
10747 unsigned short index,temp,romptr=0;
10749 if(SiS_Pr->SiS_LCDResInfo == Panel_Custom) return;
10751 if(SiS_Pr->SiS_UseROM) {
10752 if(!(ROMAddr[0x237] & 0x01)) return;
10753 if(!(ROMAddr[0x237] & 0x02)) return;
10754 romptr = SISGETROMW(0x24b);
10757 /* The Panel Compensation Delay should be set according to tables
10758 * here. Unfortunately, various BIOS versions don't care about
10759 * a uniform way using eg. ROM byte 0x220, but use different
10760 * hard coded delays (0x04, 0x20, 0x18) in SetGroup1().
10761 * Thus we don't set this if the user selected a custom pdc or if
10762 * we otherwise detected a valid pdc.
10764 if(SiS_Pr->PDC != -1) return;
10766 temp = GetOEMLCDPtr(SiS_Pr, 0);
10768 if(SiS_Pr->UseCustomMode)
10771 index = SiS_Pr->SiS_VBModeIDTable[ModeIdIndex].VB_LCDDelayIndex;
10773 if(SiS_Pr->ChipType != SIS_300) {
10775 romptr += (temp * 2);
10776 romptr = SISGETROMW(romptr);
10778 temp = ROMAddr[romptr];
10780 if(SiS_Pr->SiS_VBType & VB_SISVB) {
10781 temp = SiS300_OEMLCDDelay2[temp][index];
10783 temp = SiS300_OEMLCDDelay3[temp][index];
10787 if(SiS_Pr->SiS_UseROM && (ROMAddr[0x235] & 0x80)) {
10789 romptr += (temp * 2);
10790 romptr = SISGETROMW(romptr);
10792 temp = ROMAddr[romptr];
10794 temp = SiS300_OEMLCDDelay5[temp][index];
10797 if(SiS_Pr->SiS_UseROM) {
10798 romptr = ROMAddr[0x249] | (ROMAddr[0x24a] << 8);
10800 romptr += (temp * 2);
10801 romptr = SISGETROMW(romptr);
10803 temp = ROMAddr[romptr];
10805 temp = SiS300_OEMLCDDelay4[temp][index];
10808 temp = SiS300_OEMLCDDelay4[temp][index];
10813 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x13,~0x3C,temp); /* index 0A D[6:4] */
10817 SetOEMLCDData(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex)
10819 #if 0 /* Unfinished; Data table missing */
10820 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
10821 unsigned short index,temp;
10823 if((SiS_Pr->SiS_UseROM) {
10824 if(!(ROMAddr[0x237] & 0x01)) return;
10825 if(!(ROMAddr[0x237] & 0x04)) return;
10826 /* No rom pointer in BIOS header! */
10829 temp = GetOEMLCDPtr(SiS_Pr, 1);
10830 if(temp == 0xFFFF) return;
10832 index = SiS_Pr->SiS_VBModeIDTable[ModeIdIndex]._VB_LCDHIndex;
10833 for(i=0x14, j=0; i<=0x17; i++, j++) {
10834 SiS_SetReg(SiS_Pr->SiS_Part1Port,i,SiS300_LCDHData[temp][index][j]);
10836 SiS_SetRegANDOR(SiS_SiS_Part1Port,0x1a, 0xf8, (SiS300_LCDHData[temp][index][j] & 0x07));
10838 index = SiS_Pr->SiS_VBModeIDTable[ModeIdIndex]._VB_LCDVIndex;
10839 SiS_SetReg(SiS_SiS_Part1Port,0x18, SiS300_LCDVData[temp][index][0]);
10840 SiS_SetRegANDOR(SiS_SiS_Part1Port,0x19, 0xF0, SiS300_LCDVData[temp][index][1]);
10841 SiS_SetRegANDOR(SiS_SiS_Part1Port,0x1A, 0xC7, (SiS300_LCDVData[temp][index][2] & 0x38));
10842 for(i=0x1b, j=3; i<=0x1d; i++, j++) {
10843 SiS_SetReg(SiS_Pr->SiS_Part1Port,i,SiS300_LCDVData[temp][index][j]);
10848 static unsigned short
10849 GetOEMTVPtr(struct SiS_Private *SiS_Pr)
10851 unsigned short index;
10854 if(!(SiS_Pr->SiS_VBInfo & SetInSlaveMode)) index += 4;
10855 if(SiS_Pr->SiS_VBType & VB_SISVB) {
10856 if(SiS_Pr->SiS_VBInfo & SetCRT2ToSCART) index += 2;
10857 else if(SiS_Pr->SiS_VBInfo & SetCRT2ToHiVision) index += 3;
10858 else if(SiS_Pr->SiS_TVMode & TVSetPAL) index += 1;
10860 if(SiS_Pr->SiS_TVMode & TVSetCHOverScan) index += 2;
10861 if(SiS_Pr->SiS_TVMode & TVSetPAL) index += 1;
10867 SetOEMTVDelay(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex)
10869 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
10870 unsigned short index,temp,romptr=0;
10872 if(SiS_Pr->SiS_UseROM) {
10873 if(!(ROMAddr[0x238] & 0x01)) return;
10874 if(!(ROMAddr[0x238] & 0x02)) return;
10875 romptr = SISGETROMW(0x241);
10878 temp = GetOEMTVPtr(SiS_Pr);
10880 index = SiS_Pr->SiS_VBModeIDTable[ModeIdIndex].VB_TVDelayIndex;
10883 romptr += (temp * 2);
10884 romptr = SISGETROMW(romptr);
10886 temp = ROMAddr[romptr];
10888 if(SiS_Pr->SiS_VBType & VB_SISVB) {
10889 temp = SiS300_OEMTVDelay301[temp][index];
10891 temp = SiS300_OEMTVDelayLVDS[temp][index];
10895 SiS_SetRegANDOR(SiS_Pr->SiS_Part1Port,0x13,~0x3C,temp);
10899 SetOEMAntiFlicker(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex)
10901 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
10902 unsigned short index,temp,romptr=0;
10904 if(SiS_Pr->SiS_UseROM) {
10905 if(!(ROMAddr[0x238] & 0x01)) return;
10906 if(!(ROMAddr[0x238] & 0x04)) return;
10907 romptr = SISGETROMW(0x243);
10910 temp = GetOEMTVPtr(SiS_Pr);
10912 index = SiS_Pr->SiS_VBModeIDTable[ModeIdIndex].VB_TVFlickerIndex;
10915 romptr += (temp * 2);
10916 romptr = SISGETROMW(romptr);
10918 temp = ROMAddr[romptr];
10920 temp = SiS300_OEMTVFlicker[temp][index];
10923 SiS_SetRegANDOR(SiS_Pr->SiS_Part2Port,0x0A,0x8F,temp);
10927 SetOEMPhaseIncr(struct SiS_Private *SiS_Pr, unsigned short ModeNo,unsigned short ModeIdIndex)
10929 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
10930 unsigned short index,i,j,temp,romptr=0;
10932 if(SiS_Pr->SiS_VBInfo & SetCRT2ToHiVision) return;
10934 if(SiS_Pr->SiS_TVMode & (TVSetNTSC1024 | TVSetNTSCJ | TVSetPALM | TVSetPALN)) return;
10936 if(SiS_Pr->SiS_UseROM) {
10937 if(!(ROMAddr[0x238] & 0x01)) return;
10938 if(!(ROMAddr[0x238] & 0x08)) return;
10939 romptr = SISGETROMW(0x245);
10942 temp = GetOEMTVPtr(SiS_Pr);
10944 index = SiS_Pr->SiS_VBModeIDTable[ModeIdIndex].VB_TVPhaseIndex;
10946 if(SiS_Pr->SiS_VBType & VB_SIS30xBLV) {
10947 for(i=0x31, j=0; i<=0x34; i++, j++) {
10948 SiS_SetReg(SiS_Pr->SiS_Part2Port,i,SiS300_Phase2[temp][index][j]);
10952 romptr += (temp * 2);
10953 romptr = SISGETROMW(romptr);
10954 romptr += (index * 4);
10955 for(i=0x31, j=0; i<=0x34; i++, j++) {
10956 SiS_SetReg(SiS_Pr->SiS_Part2Port,i,ROMAddr[romptr + j]);
10959 for(i=0x31, j=0; i<=0x34; i++, j++) {
10960 SiS_SetReg(SiS_Pr->SiS_Part2Port,i,SiS300_Phase1[temp][index][j]);
10967 SetOEMYFilter(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex)
10969 unsigned char *ROMAddr = SiS_Pr->VirtualRomBase;
10970 unsigned short index,temp,i,j,romptr=0;
10972 if(SiS_Pr->SiS_VBInfo & (SetCRT2ToSCART | SetCRT2ToHiVision | SetCRT2ToYPbPr525750)) return;
10974 if(SiS_Pr->SiS_UseROM) {
10975 if(!(ROMAddr[0x238] & 0x01)) return;
10976 if(!(ROMAddr[0x238] & 0x10)) return;
10977 romptr = SISGETROMW(0x247);
10980 temp = GetOEMTVPtr(SiS_Pr);
10982 if(SiS_Pr->SiS_TVMode & TVSetPALM) temp = 8;
10983 else if(SiS_Pr->SiS_TVMode & TVSetPALN) temp = 9;
10984 /* NTSCJ uses NTSC filters */
10986 index = SiS_Pr->SiS_VBModeIDTable[ModeIdIndex].VB_TVYFilterIndex;
10988 if(SiS_Pr->SiS_VBType & VB_SIS30xBLV) {
10989 for(i=0x35, j=0; i<=0x38; i++, j++) {
10990 SiS_SetReg(SiS_Pr->SiS_Part2Port,i,SiS300_Filter2[temp][index][j]);
10992 for(i=0x48; i<=0x4A; i++, j++) {
10993 SiS_SetReg(SiS_Pr->SiS_Part2Port,i,SiS300_Filter2[temp][index][j]);
10996 if((romptr) && (!(SiS_Pr->SiS_TVMode & (TVSetPALM|TVSetPALN)))) {
10997 romptr += (temp * 2);
10998 romptr = SISGETROMW(romptr);
10999 romptr += (index * 4);
11000 for(i=0x35, j=0; i<=0x38; i++, j++) {
11001 SiS_SetReg(SiS_Pr->SiS_Part2Port,i,ROMAddr[romptr + j]);
11004 for(i=0x35, j=0; i<=0x38; i++, j++) {
11005 SiS_SetReg(SiS_Pr->SiS_Part2Port,i,SiS300_Filter1[temp][index][j]);
11011 static unsigned short
11012 SiS_SearchVBModeID(struct SiS_Private *SiS_Pr, unsigned short *ModeNo)
11014 unsigned short ModeIdIndex;
11015 unsigned char VGAINFO = SiS_Pr->SiS_VGAINFO;
11017 if(*ModeNo <= 5) *ModeNo |= 1;
11019 for(ModeIdIndex=0; ; ModeIdIndex++) {
11020 if(SiS_Pr->SiS_VBModeIDTable[ModeIdIndex].ModeID == *ModeNo) break;
11021 if(SiS_Pr->SiS_VBModeIDTable[ModeIdIndex].ModeID == 0xFF) return 0;
11024 if(*ModeNo != 0x07) {
11025 if(*ModeNo > 0x03) return ModeIdIndex;
11026 if(VGAINFO & 0x80) return ModeIdIndex;
11030 if(VGAINFO & 0x10) ModeIdIndex++; /* 400 lines */
11031 /* else 350 lines */
11032 return ModeIdIndex;
11036 SiS_OEM300Setting(struct SiS_Private *SiS_Pr, unsigned short ModeNo, unsigned short ModeIdIndex,
11037 unsigned short RefTableIndex)
11039 unsigned short OEMModeIdIndex = 0;
11041 if(!SiS_Pr->UseCustomMode) {
11042 OEMModeIdIndex = SiS_SearchVBModeID(SiS_Pr,&ModeNo);
11043 if(!(OEMModeIdIndex)) return;
11046 if(SiS_Pr->SiS_VBInfo & SetCRT2ToLCD) {
11047 SetOEMLCDDelay(SiS_Pr, ModeNo, OEMModeIdIndex);
11048 if(SiS_Pr->SiS_IF_DEF_LVDS == 1) {
11049 SetOEMLCDData(SiS_Pr, ModeNo, OEMModeIdIndex);
11052 if(SiS_Pr->UseCustomMode) return;
11053 if(SiS_Pr->SiS_VBInfo & SetCRT2ToTV) {
11054 SetOEMTVDelay(SiS_Pr, ModeNo,OEMModeIdIndex);
11055 if(SiS_Pr->SiS_VBType & VB_SISVB) {
11056 SetOEMAntiFlicker(SiS_Pr, ModeNo, OEMModeIdIndex);
11057 SetOEMPhaseIncr(SiS_Pr, ModeNo, OEMModeIdIndex);
11058 SetOEMYFilter(SiS_Pr, ModeNo, OEMModeIdIndex);