]> Pileus Git - ~andy/linux/commitdiff
staging: xgifb: vb_setmode: move functions to avoid forward declarations
authorAaro Koskinen <aaro.koskinen@iki.fi>
Sun, 13 Mar 2011 10:26:07 +0000 (12:26 +0200)
committerGreg Kroah-Hartman <gregkh@suse.de>
Mon, 14 Mar 2011 18:52:24 +0000 (11:52 -0700)
Move functions to avoid forward declarations.

Signed-off-by: Aaro Koskinen <aaro.koskinen@iki.fi>
Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
drivers/staging/xgifb/vb_setmode.c

index 542352449e2834e89b74e69424c5a421895d363d..693be078595b84e9683c0cf1b24e478b1d8c0089 100644 (file)
 #define XGI_MASK_DUAL_CHIP       0x04  /* SR3A */
 #endif
 
-
-
-static unsigned char  XGI_AjustCRT2Rate(unsigned short ModeNo,
-                       unsigned short ModeIdIndex,
-                       unsigned short RefreshRateTableIndex,
-                       unsigned short *i, struct vb_device_info *pVBInfo);
-static unsigned char  XGI_GetModePtr(unsigned short ModeNo,
-                       unsigned short ModeIdIndex,
-                       struct vb_device_info *pVBInfo);
-static unsigned short XGI_GetOffset(unsigned short ModeNo,
-                       unsigned short ModeIdIndex,
-                       unsigned short RefreshRateTableIndex,
-                       struct xgi_hw_device_info *HwDeviceExtension,
-                       struct vb_device_info *pVBInfo);
-static unsigned short XGI_GetColorDepth(unsigned short ModeNo,
-                       unsigned short ModeIdIndex,
-                       struct vb_device_info *pVBInfo);
-static unsigned short XGI_GetVGAHT2(struct vb_device_info *pVBInfo);
-static unsigned short XGI_GetVCLK2Ptr(unsigned short ModeNo,
-                       unsigned short ModeIdIndex,
-                       unsigned short RefreshRateTableIndex,
-                       struct xgi_hw_device_info *HwDeviceExtension,
-                       struct vb_device_info *pVBInfo);
-static void XGI_VBLongWait(struct vb_device_info *pVBInfo);
-static void XGI_SaveCRT2Info(unsigned short ModeNo, struct vb_device_info *pVBInfo);
-static void XGI_GetCRT2Data(unsigned short ModeNo, unsigned short ModeIdIndex, unsigned short RefreshRateTableIndex, struct vb_device_info *pVBInfo);
-static void XGI_GetCRT2ResInfo(unsigned short ModeNo, unsigned short ModeIdIndex, struct vb_device_info *pVBInfo);
-static void XGI_PreSetGroup1(unsigned short ModeNo, unsigned short ModeIdIndex, struct xgi_hw_device_info *HwDeviceExtension, unsigned short RefreshRateTableIndex, struct vb_device_info *pVBInfo);
-static void XGI_SetGroup1(unsigned short ModeNo, unsigned short ModeIdIndex, struct xgi_hw_device_info *HwDeviceExtension, unsigned short RefreshRateTableIndex, struct vb_device_info *pVBInfo);
-static void XGI_SetLockRegs(unsigned short ModeNo, unsigned short ModeIdIndex, struct xgi_hw_device_info *HwDeviceExtension, unsigned short RefreshRateTableIndex, struct vb_device_info *pVBInfo);
-static void XGI_SetLCDRegs(unsigned short ModeNo, unsigned short ModeIdIndex, struct xgi_hw_device_info *HwDeviceExtension, unsigned short RefreshRateTableIndex, struct vb_device_info *pVBInfo);
-static void XGI_SetGroup2(unsigned short ModeNo, unsigned short ModeIdIndex, unsigned short RefreshRateTableIndex, struct xgi_hw_device_info *HwDeviceExtension, struct vb_device_info *pVBInfo);
-static void XGI_SetGroup3(unsigned short ModeNo, unsigned short ModeIdIndex, struct vb_device_info *pVBInfo);
-static void XGI_SetGroup4(unsigned short ModeNo, unsigned short ModeIdIndex, unsigned short RefreshRateTableIndex, struct xgi_hw_device_info *HwDeviceExtension, struct vb_device_info *pVBInfo);
-static void XGI_SetGroup5(unsigned short ModeNo, unsigned short ModeIdIndex, struct vb_device_info *pVBInfo);
-static void *XGI_GetLcdPtr(unsigned short BX,  unsigned short ModeNo, unsigned short ModeIdIndex, unsigned short RefreshRateTableIndex, struct vb_device_info *pVBInfo);
-static void *XGI_GetTVPtr(unsigned short BX, unsigned short ModeNo, unsigned short ModeIdIndex, unsigned short RefreshRateTableIndex, struct vb_device_info *pVBInfo);
-static void XGI_AutoThreshold(struct vb_device_info *pVBInfo);
-static void XGI_SetTap4Regs(struct vb_device_info *pVBInfo);
-
-static void XGI_SetCRT1Group(struct xgi_hw_device_info *HwDeviceExtension, unsigned short ModeNo, unsigned short ModeIdIndex, struct vb_device_info *pVBInfo);
-static void XGI_SetXG21CRTC(unsigned short ModeNo, unsigned short ModeIdIndex, unsigned short RefreshRateTableIndex, struct vb_device_info *pVBInfo);
-static void XGI_SetXG21LCD(struct vb_device_info *pVBInfo, unsigned short RefreshRateTableIndex, unsigned short ModeNo);
-static void XGI_SetXG27CRTC(unsigned short ModeNo, unsigned short ModeIdIndex, unsigned short RefreshRateTableIndex, struct vb_device_info *pVBInfo);
-static void XGI_SetXG27LCD(struct vb_device_info *pVBInfo, unsigned short RefreshRateTableIndex, unsigned short ModeNo);
-static void XGI_UpdateXG21CRTC(unsigned short ModeNo, struct vb_device_info *pVBInfo, unsigned short RefreshRateTableIndex);
-static void XGI_SetSeqRegs(unsigned short ModeNo, unsigned short StandTableIndex, unsigned short ModeIdIndex, struct vb_device_info *pVBInfo);
-static void XGI_SetMiscRegs(unsigned short StandTableIndex, struct vb_device_info *pVBInfo);
-static void XGI_SetCRTCRegs(struct xgi_hw_device_info *HwDeviceExtension, unsigned short StandTableIndex, struct vb_device_info *pVBInfo);
-static void XGI_SetATTRegs(unsigned short ModeNo, unsigned short StandTableIndex, unsigned short ModeIdIndex, struct vb_device_info *pVBInfo);
-static void XGI_SetGRCRegs(unsigned short StandTableIndex, struct vb_device_info *pVBInfo);
-static void XGI_ClearExt1Regs(struct vb_device_info *pVBInfo);
-
-static void XGI_SetSync(unsigned short RefreshRateTableIndex, struct vb_device_info *pVBInfo);
-static void XGI_SetCRT1CRTC(unsigned short ModeNo, unsigned short ModeIdIndex, unsigned short RefreshRateTableIndex, struct vb_device_info *pVBInfo, struct xgi_hw_device_info *HwDeviceExtension);
-static void XGI_SetCRT1Timing_H(struct vb_device_info *pVBInfo, struct xgi_hw_device_info *HwDeviceExtension);
-static void XGI_SetCRT1Timing_V(unsigned short ModeIdIndex, unsigned short ModeNo, struct vb_device_info *pVBInfo);
-static void XGI_SetCRT1DE(struct xgi_hw_device_info *HwDeviceExtension, unsigned short ModeNo, unsigned short ModeIdIndex, unsigned short RefreshRateTableIndex, struct vb_device_info *pVBInfo);
-static void XGI_SetCRT1VCLK(unsigned short ModeNo, unsigned short ModeIdIndex, struct xgi_hw_device_info *HwDeviceExtension, unsigned short RefreshRateTableIndex, struct vb_device_info *pVBInfo);
-static void XGI_SetCRT1FIFO(unsigned short ModeNo, struct xgi_hw_device_info *HwDeviceExtension, struct vb_device_info *pVBInfo);
-static void XGI_SetCRT1ModeRegs(struct xgi_hw_device_info *HwDeviceExtension, unsigned short ModeNo, unsigned short ModeIdIndex, unsigned short RefreshRateTableIndex, struct vb_device_info *pVBInfo);
-static void XGI_SetVCLKState(struct xgi_hw_device_info *HwDeviceExtension, unsigned short ModeNo, unsigned short RefreshRateTableIndex, struct vb_device_info *pVBInfo);
-
-static void XGI_LoadDAC(unsigned short ModeNo, unsigned short ModeIdIndex, struct vb_device_info *pVBInfo);
-static void XGI_WriteDAC(unsigned short dl, unsigned short ah, unsigned short al, unsigned short dh, struct vb_device_info *pVBInfo);
-/*void     XGI_ClearBuffer(struct xgi_hw_device_info *HwDeviceExtension, unsigned short ModeNo, struct vb_device_info *pVBInfo);*/
-static void XGI_SetLCDAGroup(unsigned short ModeNo, unsigned short ModeIdIndex, struct xgi_hw_device_info *HwDeviceExtension, struct vb_device_info *pVBInfo);
-static void XGI_GetLVDSResInfo(unsigned short ModeNo, unsigned short ModeIdIndex,
-                       struct vb_device_info *pVBInfo);
-static void XGI_GetLVDSData(unsigned short ModeNo, unsigned short ModeIdIndex, unsigned short RefreshRateTableIndex, struct vb_device_info *pVBInfo);
-static void XGI_ModCRT1Regs(unsigned short ModeNo, unsigned short ModeIdIndex,
-                       unsigned short RefreshRateTableIndex,
-                       struct xgi_hw_device_info *HwDeviceExtension,
-                       struct vb_device_info *pVBInfo);
-static void XGI_SetLVDSRegs(unsigned short ModeNo, unsigned short ModeIdIndex, unsigned short RefreshRateTableIndex, struct vb_device_info *pVBInfo);
-static void XGI_UpdateModeInfo(struct xgi_hw_device_info *HwDeviceExtension, struct vb_device_info *pVBInfo);
-static void XGI_SetCRT2ECLK(unsigned short ModeNo, unsigned short ModeIdIndex, unsigned short RefreshRateTableIndex, struct vb_device_info *pVBInfo);
-static void XGI_GetLCDSync(unsigned short *HSyncWidth, unsigned short *VSyncWidth, struct vb_device_info *pVBInfo);
-static void XGI_SetCRT2VCLK(unsigned short ModeNo, unsigned short ModeIdIndex, unsigned short RefreshRateTableIndex, struct vb_device_info *pVBInfo);
-static void XGI_OEM310Setting(unsigned short ModeNo, unsigned short ModeIdIndex, struct vb_device_info *pVBInfo);
-static void XGI_SetDelayComp(struct vb_device_info *pVBInfo);
-static void XGI_SetLCDCap(struct vb_device_info *pVBInfo);
-static void XGI_SetLCDCap_A(unsigned short tempcx, struct vb_device_info *pVBInfo);
-static void XGI_SetLCDCap_B(unsigned short tempcx, struct vb_device_info *pVBInfo);
-static void SetSpectrum(struct vb_device_info *pVBInfo);
-static void XGI_SetAntiFlicker(unsigned short ModeNo, unsigned short ModeIdIndex, struct vb_device_info *pVBInfo);
-static void XGI_SetEdgeEnhance(unsigned short ModeNo, unsigned short ModeIdIndex, struct vb_device_info *pVBInfo);
-static void XGI_SetPhaseIncr(struct vb_device_info *pVBInfo);
-static void XGI_SetYFilter(unsigned short ModeNo, unsigned short ModeIdIndex, struct vb_device_info *pVBInfo);
-static void XGI_GetTVPtrIndex2(unsigned short *tempbx, unsigned char* tempcl,
-                       unsigned char *tempch, struct vb_device_info *pVBInfo);
-static void XGI_CloseCRTC(struct xgi_hw_device_info *, struct vb_device_info *pVBInfo);
-static void XGI_GetRAMDAC2DATA(unsigned short ModeNo, unsigned short ModeIdIndex, unsigned short RefreshRateTableIndex, struct vb_device_info *pVBInfo);
-static void XGINew_EnableCRT2(struct vb_device_info *pVBInfo);
-static void XGI_SetCRT1Offset(unsigned short ModeNo, unsigned short ModeIdIndex, unsigned short RefreshRateTableIndex, struct xgi_hw_device_info *HwDeviceExtension, struct vb_device_info *pVBInfo);
-static void XGI_GetLCDVCLKPtr(unsigned char *di_0, unsigned char *di_1,
-                       struct vb_device_info *pVBInfo);
-static unsigned char XGI_GetVCLKPtr(unsigned short RefreshRateTableIndex,
-                       unsigned short ModeNo,
-                       unsigned short ModeIdIndex,
-                       struct vb_device_info *pVBInfo);
-static void XGI_GetVCLKLen(unsigned char tempal, unsigned char *di_0,
-                       unsigned char *di_1, struct vb_device_info *pVBInfo);
-static unsigned short XGI_GetLCDCapPtr(struct vb_device_info *pVBInfo);
-static unsigned short XGI_GetLCDCapPtr1(struct vb_device_info *pVBInfo);
-static struct XGI301C_Tap4TimingStruct *XGI_GetTap4Ptr(unsigned short tempcx, struct vb_device_info *pVBInfo);
-static unsigned char XGI_XG21GetPSCValue(struct vb_device_info *pVBInfo);
-static unsigned char XGI_XG27GetPSCValue(struct vb_device_info *pVBInfo);
-static void XGI_SetXG21LVDSPara(unsigned short ModeNo, unsigned short ModeIdIndex, struct vb_device_info *pVBInfo);
-static void XGI_SetXG27LVDSPara(unsigned short ModeNo, unsigned short ModeIdIndex, struct vb_device_info *pVBInfo);
-static unsigned char XGI_SetDefaultVCLK(struct vb_device_info *pVBInfo);
-
 static unsigned short XGINew_MDA_DAC[] = {
        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
        0x15, 0x15, 0x15, 0x15, 0x15, 0x15, 0x15, 0x15,
@@ -312,1486 +200,1233 @@ void InitTo330Pointer(unsigned char ChipType, struct vb_device_info *pVBInfo)
 
 }
 
-unsigned char XGISetModeNew(struct xgi_hw_device_info *HwDeviceExtension,
-                       unsigned short ModeNo)
+static unsigned char XGI_GetModePtr(unsigned short ModeNo, unsigned short ModeIdIndex,
+               struct vb_device_info *pVBInfo)
 {
-       unsigned short ModeIdIndex;
-       /* unsigned char *pVBInfo->FBAddr = HwDeviceExtension->pjVideoMemoryAddress; */
-       struct vb_device_info VBINF;
-       struct vb_device_info *pVBInfo = &VBINF;
-       pVBInfo->ROMAddr = HwDeviceExtension->pjVirtualRomBase;
-       pVBInfo->BaseAddr = (unsigned long) HwDeviceExtension->pjIOAddress;
-       pVBInfo->IF_DEF_LVDS = 0;
-       pVBInfo->IF_DEF_CH7005 = 0;
-       pVBInfo->IF_DEF_LCDA = 1;
-       pVBInfo->IF_DEF_CH7017 = 0;
-       pVBInfo->IF_DEF_CH7007 = 0; /* [Billy] 2007/05/14 */
-       pVBInfo->IF_DEF_VideoCapture = 0;
-       pVBInfo->IF_DEF_ScaleLCD = 0;
-       pVBInfo->IF_DEF_OEMUtil = 0;
-       pVBInfo->IF_DEF_PWD = 0;
+       unsigned char index;
 
-       if (HwDeviceExtension->jChipType >= XG20) { /* kuku 2004/06/25 */
-               pVBInfo->IF_DEF_YPbPr = 0;
-               pVBInfo->IF_DEF_HiVision = 0;
-               pVBInfo->IF_DEF_CRT2Monitor = 0;
-               pVBInfo->VBType = 0; /*set VBType default 0*/
-       } else if (HwDeviceExtension->jChipType >= XG40) {
-               pVBInfo->IF_DEF_YPbPr = 1;
-               pVBInfo->IF_DEF_HiVision = 1;
-               pVBInfo->IF_DEF_CRT2Monitor = 1;
-       } else {
-               pVBInfo->IF_DEF_YPbPr = 1;
-               pVBInfo->IF_DEF_HiVision = 1;
-               pVBInfo->IF_DEF_CRT2Monitor = 0;
+       if (ModeNo <= 0x13)
+               index = pVBInfo->SModeIDTable[ModeIdIndex].St_StTableIndex;
+       else {
+               if (pVBInfo->ModeType <= 0x02)
+                       index = 0x1B; /* 02 -> ModeEGA */
+               else
+                       index = 0x0F;
        }
+       return index; /* Get pVBInfo->StandTable index */
+}
 
-       pVBInfo->P3c4 = pVBInfo->BaseAddr + 0x14;
-       pVBInfo->P3d4 = pVBInfo->BaseAddr + 0x24;
-       pVBInfo->P3c0 = pVBInfo->BaseAddr + 0x10;
-       pVBInfo->P3ce = pVBInfo->BaseAddr + 0x1e;
-       pVBInfo->P3c2 = pVBInfo->BaseAddr + 0x12;
-       pVBInfo->P3cc = pVBInfo->BaseAddr + 0x1C;
-       pVBInfo->P3ca = pVBInfo->BaseAddr + 0x1a;
-       pVBInfo->P3c6 = pVBInfo->BaseAddr + 0x16;
-       pVBInfo->P3c7 = pVBInfo->BaseAddr + 0x17;
-       pVBInfo->P3c8 = pVBInfo->BaseAddr + 0x18;
-       pVBInfo->P3c9 = pVBInfo->BaseAddr + 0x19;
-       pVBInfo->P3da = pVBInfo->BaseAddr + 0x2A;
-       pVBInfo->Part0Port = pVBInfo->BaseAddr + XGI_CRT2_PORT_00;
-       pVBInfo->Part1Port = pVBInfo->BaseAddr + XGI_CRT2_PORT_04;
-       pVBInfo->Part2Port = pVBInfo->BaseAddr + XGI_CRT2_PORT_10;
-       pVBInfo->Part3Port = pVBInfo->BaseAddr + XGI_CRT2_PORT_12;
-       pVBInfo->Part4Port = pVBInfo->BaseAddr + XGI_CRT2_PORT_14;
-       pVBInfo->Part5Port = pVBInfo->BaseAddr + XGI_CRT2_PORT_14 + 2;
+/*
+unsigned char XGI_SetBIOSData(unsigned short ModeNo, unsigned short ModeIdIndex) {
+       return (0);
+}
+*/
 
-       if (HwDeviceExtension->jChipType == XG21) { /* for x86 Linux, XG21 LVDS */
-               if ((XGINew_GetReg1(pVBInfo->P3d4, 0x38) & 0xE0) == 0xC0)
-                       pVBInfo->IF_DEF_LVDS = 1;
-       }
-       if (HwDeviceExtension->jChipType == XG27) {
-               if ((XGINew_GetReg1(pVBInfo->P3d4, 0x38) & 0xE0) == 0xC0) {
-                       if (XGINew_GetReg1(pVBInfo->P3d4, 0x30) & 0x20)
-                               pVBInfo->IF_DEF_LVDS = 1;
+/* unsigned char XGI_ClearBankRegs(unsigned short ModeNo, unsigned short ModeIdIndex) {
+       return( 0 ) ;
+}
+*/
+
+static void XGI_SetSeqRegs(unsigned short ModeNo, unsigned short StandTableIndex,
+               unsigned short ModeIdIndex, struct vb_device_info *pVBInfo)
+{
+       unsigned char tempah, SRdata;
+
+       unsigned short i, modeflag;
+
+       if (ModeNo <= 0x13)
+               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag;
+       else
+               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
+
+       XGINew_SetReg1(pVBInfo->P3c4, 0x00, 0x03); /* Set SR0 */
+       tempah = pVBInfo->StandTable[StandTableIndex].SR[0];
+
+       i = SetCRT2ToLCDA;
+       if (pVBInfo->VBInfo & SetCRT2ToLCDA) {
+               tempah |= 0x01;
+       } else {
+               if (pVBInfo->VBInfo & (SetCRT2ToTV | SetCRT2ToLCD)) {
+                       if (pVBInfo->VBInfo & SetInSlaveMode)
+                               tempah |= 0x01;
                }
        }
 
-       if (HwDeviceExtension->jChipType < XG20) /* kuku 2004/06/25 */
-               XGI_GetVBType(pVBInfo);
+       tempah |= 0x20; /* screen off */
+       XGINew_SetReg1(pVBInfo->P3c4, 0x01, tempah); /* Set SR1 */
 
-       InitTo330Pointer(HwDeviceExtension->jChipType, pVBInfo);
-       if (ModeNo & 0x80) {
-               ModeNo = ModeNo & 0x7F;
-               /* XGINew_flag_clearbuffer = 0; */
+       for (i = 02; i <= 04; i++) {
+               SRdata = pVBInfo->StandTable[StandTableIndex].SR[i - 1]; /* Get SR2,3,4 from file */
+               XGINew_SetReg1(pVBInfo->P3c4, i, SRdata); /* Set SR2 3 4 */
        }
-       /* else {
-               XGINew_flag_clearbuffer = 1;
+}
+
+static void XGI_SetMiscRegs(unsigned short StandTableIndex,
+               struct vb_device_info *pVBInfo)
+{
+       unsigned char Miscdata;
+
+       Miscdata = pVBInfo->StandTable[StandTableIndex].MISC; /* Get Misc from file */
+       /*
+       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV | VB_XGI302LV | VB_XGI301C)) {
+               if (pVBInfo->VBInfo & SetCRT2ToLCDA) {
+                       Miscdata |= 0x0C;
+               }
        }
        */
-       XGINew_SetReg1(pVBInfo->P3c4, 0x05, 0x86);
 
-       if (HwDeviceExtension->jChipType < XG20) /* kuku 2004/06/25 1.Openkey */
-               XGI_UnLockCRT2(HwDeviceExtension, pVBInfo);
+       XGINew_SetReg3(pVBInfo->P3c2, Miscdata); /* Set Misc(3c2) */
+}
 
-       XGI_SearchModeID(ModeNo, &ModeIdIndex, pVBInfo);
+static void XGI_SetCRTCRegs(struct xgi_hw_device_info *HwDeviceExtension,
+               unsigned short StandTableIndex, struct vb_device_info *pVBInfo)
+{
+       unsigned char CRTCdata;
+       unsigned short i;
 
-       XGI_GetVGAType(HwDeviceExtension, pVBInfo);
+       CRTCdata = (unsigned char) XGINew_GetReg1(pVBInfo->P3d4, 0x11);
+       CRTCdata &= 0x7f;
+       XGINew_SetReg1(pVBInfo->P3d4, 0x11, CRTCdata); /* Unlock CRTC */
 
-       if (HwDeviceExtension->jChipType < XG20) { /* kuku 2004/06/25 */
-               XGI_GetVBInfo(ModeNo, ModeIdIndex, HwDeviceExtension, pVBInfo);
-               XGI_GetTVInfo(ModeNo, ModeIdIndex, pVBInfo);
-               XGI_GetLCDInfo(ModeNo, ModeIdIndex, pVBInfo);
-               XGI_DisableBridge(HwDeviceExtension, pVBInfo);
-               /* XGI_OpenCRTC(HwDeviceExtension, pVBInfo); */
+       for (i = 0; i <= 0x18; i++) {
+               CRTCdata = pVBInfo->StandTable[StandTableIndex].CRTC[i]; /* Get CRTC from file */
+               XGINew_SetReg1(pVBInfo->P3d4, i, CRTCdata); /* Set CRTC(3d4) */
+       }
+       /*
+       if ((HwDeviceExtension->jChipType == XGI_630) && (HwDeviceExtension->jChipRevision == 0x30)) {
+               if (pVBInfo->VBInfo & SetInSlaveMode) {
+                       if (pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToTV)) {
+                               XGINew_SetReg1(pVBInfo->P3d4, 0x18, 0xFE);
+                       }
+               }
+       }
+       */
+}
 
-               if (pVBInfo->VBInfo & (SetSimuScanMode | SetCRT2ToLCDA)) {
-                       XGI_SetCRT1Group(HwDeviceExtension, ModeNo,
-                                       ModeIdIndex, pVBInfo);
+static void XGI_SetATTRegs(unsigned short ModeNo, unsigned short StandTableIndex,
+               unsigned short ModeIdIndex, struct vb_device_info *pVBInfo)
+{
+       unsigned char ARdata;
+       unsigned short i, modeflag;
 
-                       if (pVBInfo->VBInfo & SetCRT2ToLCDA) {
-                               XGI_SetLCDAGroup(ModeNo, ModeIdIndex,
-                                               HwDeviceExtension, pVBInfo);
-                       }
-               } else {
-                       if (!(pVBInfo->VBInfo & SwitchToCRT2)) {
-                               XGI_SetCRT1Group(HwDeviceExtension, ModeNo,
-                                               ModeIdIndex, pVBInfo);
+       if (ModeNo <= 0x13)
+               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag;
+       else
+               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
+
+       for (i = 0; i <= 0x13; i++) {
+               ARdata = pVBInfo->StandTable[StandTableIndex].ATTR[i];
+               if (modeflag & Charx8Dot) { /* ifndef Dot9 */
+                       if (i == 0x13) {
                                if (pVBInfo->VBInfo & SetCRT2ToLCDA) {
-                                       XGI_SetLCDAGroup(ModeNo, ModeIdIndex,
-                                                       HwDeviceExtension,
-                                                       pVBInfo);
+                                       ARdata = 0;
+                               } else {
+                                       if (pVBInfo->VBInfo & (SetCRT2ToTV
+                                                       | SetCRT2ToLCD)) {
+                                               if (pVBInfo->VBInfo
+                                                               & SetInSlaveMode)
+                                                       ARdata = 0;
+                                       }
                                }
                        }
                }
 
-               if (pVBInfo->VBInfo & (SetSimuScanMode | SwitchToCRT2)) {
-                       switch (HwDeviceExtension->ujVBChipID) {
-                       case VB_CHIP_301:
-                               XGI_SetCRT2Group301(ModeNo, HwDeviceExtension,
-                                               pVBInfo); /*add for CRT2 */
-                               break;
+               XGINew_GetReg2(pVBInfo->P3da); /* reset 3da */
+               XGINew_SetReg3(pVBInfo->P3c0, i); /* set index */
+               XGINew_SetReg3(pVBInfo->P3c0, ARdata); /* set data */
+       }
 
-                       case VB_CHIP_302:
-                               XGI_SetCRT2Group301(ModeNo, HwDeviceExtension,
-                                               pVBInfo); /*add for CRT2 */
-                               break;
+       XGINew_GetReg2(pVBInfo->P3da); /* reset 3da */
+       XGINew_SetReg3(pVBInfo->P3c0, 0x14); /* set index */
+       XGINew_SetReg3(pVBInfo->P3c0, 0x00); /* set data */
+       XGINew_GetReg2(pVBInfo->P3da); /* Enable Attribute */
+       XGINew_SetReg3(pVBInfo->P3c0, 0x20);
+}
 
-                       default:
-                               break;
-                       }
-               }
+static void XGI_SetGRCRegs(unsigned short StandTableIndex,
+               struct vb_device_info *pVBInfo)
+{
+       unsigned char GRdata;
+       unsigned short i;
 
-               XGI_SetCRT2ModeRegs(ModeNo, HwDeviceExtension, pVBInfo);
-               XGI_OEM310Setting(ModeNo, ModeIdIndex, pVBInfo); /*0212*/
-               XGI_CloseCRTC(HwDeviceExtension, pVBInfo);
-               XGI_EnableBridge(HwDeviceExtension, pVBInfo);
-       } /* !XG20 */
-       else {
-               if (pVBInfo->IF_DEF_LVDS == 1)
-                       if (!XGI_XG21CheckLVDSMode(ModeNo, ModeIdIndex, pVBInfo))
-                               return 0;
+       for (i = 0; i <= 0x08; i++) {
+               GRdata = pVBInfo->StandTable[StandTableIndex].GRC[i]; /* Get GR from file */
+               XGINew_SetReg1(pVBInfo->P3ce, i, GRdata); /* Set GR(3ce) */
+       }
 
-               if (ModeNo <= 0x13) {
-                       pVBInfo->ModeType
-                                       = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag
-                                                       & ModeInfoFlag;
-               } else {
-                       pVBInfo->ModeType
-                                       = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag
-                                                       & ModeInfoFlag;
-               }
-
-               pVBInfo->SetFlag = 0;
-               if (pVBInfo->IF_DEF_CH7007 != 1)
-                       pVBInfo->VBInfo = DisableCRT2Display;
-
-               XGI_DisplayOff(HwDeviceExtension, pVBInfo);
-
-               XGI_SetCRT1Group(HwDeviceExtension, ModeNo, ModeIdIndex,
-                               pVBInfo);
-
-               XGI_DisplayOn(HwDeviceExtension, pVBInfo);
-               /*
-               if (HwDeviceExtension->jChipType == XG21)
-                       XGINew_SetRegANDOR(pVBInfo->P3c4, 0x09, ~0x80, 0x80);
-               */
+       if (pVBInfo->ModeType > ModeVGA) {
+               GRdata = (unsigned char) XGINew_GetReg1(pVBInfo->P3ce, 0x05);
+               GRdata &= 0xBF; /* 256 color disable */
+               XGINew_SetReg1(pVBInfo->P3ce, 0x05, GRdata);
        }
+}
 
-       /*
-       if (ModeNo <= 0x13) {
-               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag;
-       } else {
-               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
-       }
-       pVBInfo->ModeType = modeflag&ModeInfoFlag;
-       pVBInfo->SetFlag = 0x00;
-       pVBInfo->VBInfo = DisableCRT2Display;
-       temp = XGINew_CheckMemorySize(HwDeviceExtension, ModeNo, ModeIdIndex, pVBInfo);
+static void XGI_ClearExt1Regs(struct vb_device_info *pVBInfo)
+{
+       unsigned short i;
 
-       if (temp == 0)
-               return (0);
+       for (i = 0x0A; i <= 0x0E; i++)
+               XGINew_SetReg1(pVBInfo->P3c4, i, 0x00); /* Clear SR0A-SR0E */
+}
 
-       XGI_DisplayOff(HwDeviceExtension, pVBInfo) ;
-       XGI_SetCRT1Group(HwDeviceExtension, ModeNo, ModeIdIndex, pVBInfo);
-       XGI_DisplayOn(HwDeviceExtension, pVBInfo);
-       */
+static unsigned char XGI_SetDefaultVCLK(struct vb_device_info *pVBInfo)
+{
 
-       XGI_UpdateModeInfo(HwDeviceExtension, pVBInfo);
+       XGINew_SetRegANDOR(pVBInfo->P3c4, 0x31, ~0x30, 0x20);
+       XGINew_SetReg1(pVBInfo->P3c4, 0x2B, pVBInfo->VCLKData[0].SR2B);
+       XGINew_SetReg1(pVBInfo->P3c4, 0x2C, pVBInfo->VCLKData[0].SR2C);
 
-       if (HwDeviceExtension->jChipType < XG20) { /* kuku 2004/06/25 */
-               XGI_LockCRT2(HwDeviceExtension, pVBInfo);
-       }
+       XGINew_SetRegANDOR(pVBInfo->P3c4, 0x31, ~0x30, 0x10);
+       XGINew_SetReg1(pVBInfo->P3c4, 0x2B, pVBInfo->VCLKData[1].SR2B);
+       XGINew_SetReg1(pVBInfo->P3c4, 0x2C, pVBInfo->VCLKData[1].SR2C);
 
-       return 1;
+       XGINew_SetRegAND(pVBInfo->P3c4, 0x31, ~0x30);
+       return 0;
 }
 
-static void XGI_SetCRT1Group(struct xgi_hw_device_info *HwDeviceExtension,
-               unsigned short ModeNo, unsigned short ModeIdIndex,
+static unsigned char XGI_AjustCRT2Rate(unsigned short ModeNo,
+               unsigned short ModeIdIndex,
+               unsigned short RefreshRateTableIndex, unsigned short *i,
                struct vb_device_info *pVBInfo)
 {
-       unsigned short StandTableIndex, RefreshRateTableIndex, b3CC, temp;
-
-       unsigned short XGINew_P3cc = pVBInfo->P3cc;
+       unsigned short tempax, tempbx, resinfo, modeflag, infoflag;
 
-       /* XGINew_CRT1Mode = ModeNo; // SaveModeID */
-       StandTableIndex = XGI_GetModePtr(ModeNo, ModeIdIndex, pVBInfo);
-       /* XGI_SetBIOSData(ModeNo, ModeIdIndex); */
-       /* XGI_ClearBankRegs(ModeNo, ModeIdIndex); */
-       XGI_SetSeqRegs(ModeNo, StandTableIndex, ModeIdIndex, pVBInfo);
-       XGI_SetMiscRegs(StandTableIndex, pVBInfo);
-       XGI_SetCRTCRegs(HwDeviceExtension, StandTableIndex, pVBInfo);
-       XGI_SetATTRegs(ModeNo, StandTableIndex, ModeIdIndex, pVBInfo);
-       XGI_SetGRCRegs(StandTableIndex, pVBInfo);
-       XGI_ClearExt1Regs(pVBInfo);
+       if (ModeNo <= 0x13)
+               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag; /* si+St_ModeFlag */
+       else
+               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
 
-       /* if (pVBInfo->IF_DEF_ExpLink) */
-       if (HwDeviceExtension->jChipType == XG27) {
-               if (pVBInfo->IF_DEF_LVDS == 0)
-                       XGI_SetDefaultVCLK(pVBInfo);
-       }
+       resinfo = pVBInfo->EModeIDTable[ModeIdIndex].Ext_RESINFO;
+       tempbx = pVBInfo->RefIndex[RefreshRateTableIndex + (*i)].ModeID;
+       tempax = 0;
 
-       temp = ~ProgrammingCRT2;
-       pVBInfo->SetFlag &= temp;
-       pVBInfo->SelectCRT2Rate = 0;
+       if (pVBInfo->IF_DEF_LVDS == 0) {
+               if (pVBInfo->VBInfo & SetCRT2ToRAMDAC) {
+                       tempax |= SupportRAMDAC2;
 
-       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
-                       | VB_XGI302LV | VB_XGI301C)) {
-               if (pVBInfo->VBInfo & (SetSimuScanMode | SetCRT2ToLCDA
-                               | SetInSlaveMode)) {
-                       pVBInfo->SetFlag |= ProgrammingCRT2;
+                       if (pVBInfo->VBType & VB_XGI301C)
+                               tempax |= SupportCRT2in301C;
                }
-       }
 
-       RefreshRateTableIndex = XGI_GetRatePtrCRT2(HwDeviceExtension, ModeNo,
-                       ModeIdIndex, pVBInfo);
-       if (RefreshRateTableIndex != 0xFFFF) {
-               XGI_SetSync(RefreshRateTableIndex, pVBInfo);
-               XGI_SetCRT1CRTC(ModeNo, ModeIdIndex, RefreshRateTableIndex,
-                               pVBInfo, HwDeviceExtension);
-               XGI_SetCRT1DE(HwDeviceExtension, ModeNo, ModeIdIndex,
-                               RefreshRateTableIndex, pVBInfo);
-               XGI_SetCRT1Offset(ModeNo, ModeIdIndex, RefreshRateTableIndex,
-                               HwDeviceExtension, pVBInfo);
-               XGI_SetCRT1VCLK(ModeNo, ModeIdIndex, HwDeviceExtension,
-                               RefreshRateTableIndex, pVBInfo);
-       }
+               if (pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) { /* 301b */
+                       tempax |= SupportLCD;
 
-       if ((HwDeviceExtension->jChipType >= XG20)
-                       && (HwDeviceExtension->jChipType < XG27)) { /* fix H/W DCLK/2 bug */
-               if ((ModeNo == 0x00) | (ModeNo == 0x01)) {
-                       XGINew_SetReg1(pVBInfo->P3c4, 0x2B, 0x4E);
-                       XGINew_SetReg1(pVBInfo->P3c4, 0x2C, 0xE9);
-                       b3CC = (unsigned char) XGINew_GetReg2(XGINew_P3cc);
-                       XGINew_SetReg3(XGINew_P3cc, (b3CC |= 0x0C));
-               } else if ((ModeNo == 0x04) | (ModeNo == 0x05) | (ModeNo
-                               == 0x0D)) {
-                       XGINew_SetReg1(pVBInfo->P3c4, 0x2B, 0x1B);
-                       XGINew_SetReg1(pVBInfo->P3c4, 0x2C, 0xE3);
-                       b3CC = (unsigned char) XGINew_GetReg2(XGINew_P3cc);
-                       XGINew_SetReg3(XGINew_P3cc, (b3CC |= 0x0C));
+                       if (pVBInfo->LCDResInfo != Panel1280x1024) {
+                               if (pVBInfo->LCDResInfo != Panel1280x960) {
+                                       if (pVBInfo->LCDInfo & LCDNonExpanding) {
+                                               if (resinfo >= 9) {
+                                                       tempax = 0;
+                                                       return 0;
+                                               }
+                                       }
+                               }
+                       }
                }
-       }
 
-       if (HwDeviceExtension->jChipType >= XG21) {
-               temp = XGINew_GetReg1(pVBInfo->P3d4, 0x38);
-               if (temp & 0xA0) {
+               if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV) { /* for HiTV */
+                       if ((pVBInfo->VBType & VB_XGI301LV)
+                                       && (pVBInfo->VBExtInfo == VB_YPbPr1080i)) {
+                               tempax |= SupportYPbPr;
+                               if (pVBInfo->VBInfo & SetInSlaveMode) {
+                                       if (resinfo == 4)
+                                               return 0;
 
-                       /* XGINew_SetRegAND(pVBInfo->P3d4, 0x4A, ~0x20); *//* Enable write GPIOF */
-                       /* XGINew_SetRegAND(pVBInfo->P3d4, 0x48, ~0x20); *//* P. DWN */
-                       /* XG21 CRT1 Timing */
-                       if (HwDeviceExtension->jChipType == XG27)
-                               XGI_SetXG27CRTC(ModeNo, ModeIdIndex,
-                                               RefreshRateTableIndex, pVBInfo);
-                       else
-                               XGI_SetXG21CRTC(ModeNo, ModeIdIndex,
-                                               RefreshRateTableIndex, pVBInfo);
+                                       if (resinfo == 3)
+                                               return 0;
 
-                       XGI_UpdateXG21CRTC(ModeNo, pVBInfo,
-                                       RefreshRateTableIndex);
+                                       if (resinfo > 7)
+                                               return 0;
+                               }
+                       } else {
+                               tempax |= SupportHiVisionTV;
+                               if (pVBInfo->VBInfo & SetInSlaveMode) {
+                                       if (resinfo == 4)
+                                               return 0;
 
-                       if (HwDeviceExtension->jChipType == XG27)
-                               XGI_SetXG27LCD(pVBInfo, RefreshRateTableIndex,
-                                               ModeNo);
-                       else
-                               XGI_SetXG21LCD(pVBInfo, RefreshRateTableIndex,
-                                               ModeNo);
+                                       if (resinfo == 3) {
+                                               if (pVBInfo->SetFlag
+                                                               & TVSimuMode)
+                                                       return 0;
+                                       }
 
-                       if (pVBInfo->IF_DEF_LVDS == 1) {
-                               if (HwDeviceExtension->jChipType == XG27)
-                                       XGI_SetXG27LVDSPara(ModeNo,
-                                                       ModeIdIndex, pVBInfo);
-                               else
-                                       XGI_SetXG21LVDSPara(ModeNo,
-                                                       ModeIdIndex, pVBInfo);
+                                       if (resinfo > 7)
+                                               return 0;
+                               }
                        }
-                       /* XGINew_SetRegOR(pVBInfo->P3d4, 0x48, 0x20); *//* P. ON */
-               }
-       }
+               } else {
+                       if (pVBInfo->VBInfo & (SetCRT2ToAVIDEO
+                                       | SetCRT2ToSVIDEO | SetCRT2ToSCART
+                                       | SetCRT2ToYPbPr | SetCRT2ToHiVisionTV)) {
+                               tempax |= SupportTV;
 
-       pVBInfo->SetFlag &= (~ProgrammingCRT2);
-       XGI_SetCRT1FIFO(ModeNo, HwDeviceExtension, pVBInfo);
-       XGI_SetCRT1ModeRegs(HwDeviceExtension, ModeNo, ModeIdIndex,
-                       RefreshRateTableIndex, pVBInfo);
+                               if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B
+                                               | VB_XGI301LV | VB_XGI302LV
+                                               | VB_XGI301C)) {
+                                       tempax |= SupportTV1024;
+                               }
 
-       /* XGI_LoadCharacter(); //dif ifdef TVFont */
+                               if (!(pVBInfo->VBInfo & SetPALTV)) {
+                                       if (modeflag & NoSupportSimuTV) {
+                                               if (pVBInfo->VBInfo
+                                                               & SetInSlaveMode) {
+                                                       if (!(pVBInfo->VBInfo
+                                                                       & SetNotSimuMode)) {
+                                                               return 0;
+                                                       }
+                                               }
+                                       }
+                               }
+                       }
+               }
+       } else { /* for LVDS */
+               if (pVBInfo->IF_DEF_CH7005 == 1) {
+                       if (pVBInfo->VBInfo & SetCRT2ToTV)
+                               tempax |= SupportCHTV;
+               }
 
-       XGI_LoadDAC(ModeNo, ModeIdIndex, pVBInfo);
-       /* XGI_ClearBuffer(HwDeviceExtension, ModeNo, pVBInfo); */
-}
+               if (pVBInfo->VBInfo & SetCRT2ToLCD) {
+                       tempax |= SupportLCD;
 
-static unsigned char XGI_GetModePtr(unsigned short ModeNo, unsigned short ModeIdIndex,
-               struct vb_device_info *pVBInfo)
-{
-       unsigned char index;
+                       if (resinfo > 0x08)
+                               return 0; /* 1024x768 */
 
-       if (ModeNo <= 0x13)
-               index = pVBInfo->SModeIDTable[ModeIdIndex].St_StTableIndex;
-       else {
-               if (pVBInfo->ModeType <= 0x02)
-                       index = 0x1B; /* 02 -> ModeEGA */
-               else
-                       index = 0x0F;
-       }
-       return index; /* Get pVBInfo->StandTable index */
-}
+                       if (pVBInfo->LCDResInfo < Panel1024x768) {
+                               if (resinfo > 0x07)
+                                       return 0; /* 800x600 */
 
-/*
-unsigned char XGI_SetBIOSData(unsigned short ModeNo, unsigned short ModeIdIndex) {
-       return (0);
-}
-*/
-
-/* unsigned char XGI_ClearBankRegs(unsigned short ModeNo, unsigned short ModeIdIndex) {
-       return( 0 ) ;
-}
-*/
-
-static void XGI_SetSeqRegs(unsigned short ModeNo, unsigned short StandTableIndex,
-               unsigned short ModeIdIndex, struct vb_device_info *pVBInfo)
-{
-       unsigned char tempah, SRdata;
-
-       unsigned short i, modeflag;
-
-       if (ModeNo <= 0x13)
-               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag;
-       else
-               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
+                               if (resinfo == 0x04)
+                                       return 0; /* 512x384 */
+                       }
+               }
+       }
 
-       XGINew_SetReg1(pVBInfo->P3c4, 0x00, 0x03); /* Set SR0 */
-       tempah = pVBInfo->StandTable[StandTableIndex].SR[0];
+       for (; pVBInfo->RefIndex[RefreshRateTableIndex + (*i)].ModeID == tempbx; (*i)--) {
+               infoflag
+                               = pVBInfo->RefIndex[RefreshRateTableIndex
+                                               + (*i)].Ext_InfoFlag;
+               if (infoflag & tempax)
+                       return 1;
 
-       i = SetCRT2ToLCDA;
-       if (pVBInfo->VBInfo & SetCRT2ToLCDA) {
-               tempah |= 0x01;
-       } else {
-               if (pVBInfo->VBInfo & (SetCRT2ToTV | SetCRT2ToLCD)) {
-                       if (pVBInfo->VBInfo & SetInSlaveMode)
-                               tempah |= 0x01;
-               }
+               if ((*i) == 0)
+                       break;
        }
 
-       tempah |= 0x20; /* screen off */
-       XGINew_SetReg1(pVBInfo->P3c4, 0x01, tempah); /* Set SR1 */
+       for ((*i) = 0;; (*i)++) {
+               infoflag
+                               = pVBInfo->RefIndex[RefreshRateTableIndex
+                                               + (*i)].Ext_InfoFlag;
+               if (pVBInfo->RefIndex[RefreshRateTableIndex + (*i)].ModeID
+                               != tempbx) {
+                       return 0;
+               }
 
-       for (i = 02; i <= 04; i++) {
-               SRdata = pVBInfo->StandTable[StandTableIndex].SR[i - 1]; /* Get SR2,3,4 from file */
-               XGINew_SetReg1(pVBInfo->P3c4, i, SRdata); /* Set SR2 3 4 */
+               if (infoflag & tempax)
+                       return 1;
        }
+       return 1;
 }
 
-static void XGI_SetMiscRegs(unsigned short StandTableIndex,
+static void XGI_SetSync(unsigned short RefreshRateTableIndex,
                struct vb_device_info *pVBInfo)
 {
-       unsigned char Miscdata;
-
-       Miscdata = pVBInfo->StandTable[StandTableIndex].MISC; /* Get Misc from file */
-       /*
-       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV | VB_XGI302LV | VB_XGI301C)) {
-               if (pVBInfo->VBInfo & SetCRT2ToLCDA) {
-                       Miscdata |= 0x0C;
-               }
-       }
-       */
+       unsigned short sync, temp;
 
-       XGINew_SetReg3(pVBInfo->P3c2, Miscdata); /* Set Misc(3c2) */
+       sync = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_InfoFlag >> 8; /* di+0x00 */
+       sync &= 0xC0;
+       temp = 0x2F;
+       temp |= sync;
+       XGINew_SetReg3(pVBInfo->P3c2, temp); /* Set Misc(3c2) */
 }
 
-static void XGI_SetCRTCRegs(struct xgi_hw_device_info *HwDeviceExtension,
-               unsigned short StandTableIndex, struct vb_device_info *pVBInfo)
+static void XGI_SetCRT1Timing_H(struct vb_device_info *pVBInfo,
+               struct xgi_hw_device_info *HwDeviceExtension)
 {
-       unsigned char CRTCdata;
-       unsigned short i;
+       unsigned char data, data1, pushax;
+       unsigned short i, j;
 
-       CRTCdata = (unsigned char) XGINew_GetReg1(pVBInfo->P3d4, 0x11);
-       CRTCdata &= 0x7f;
-       XGINew_SetReg1(pVBInfo->P3d4, 0x11, CRTCdata); /* Unlock CRTC */
+       /* XGINew_SetReg1(pVBInfo->P3d4, 0x51, 0); */
+       /* XGINew_SetReg1(pVBInfo->P3d4, 0x56, 0); */
+       /* XGINew_SetRegANDOR(pVBInfo->P3d4, 0x11, 0x7f, 0x00); */
 
-       for (i = 0; i <= 0x18; i++) {
-               CRTCdata = pVBInfo->StandTable[StandTableIndex].CRTC[i]; /* Get CRTC from file */
-               XGINew_SetReg1(pVBInfo->P3d4, i, CRTCdata); /* Set CRTC(3d4) */
-       }
-       /*
-       if ((HwDeviceExtension->jChipType == XGI_630) && (HwDeviceExtension->jChipRevision == 0x30)) {
-               if (pVBInfo->VBInfo & SetInSlaveMode) {
-                       if (pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToTV)) {
-                               XGINew_SetReg1(pVBInfo->P3d4, 0x18, 0xFE);
-                       }
-               }
+       data = (unsigned char) XGINew_GetReg1(pVBInfo->P3d4, 0x11); /* unlock cr0-7 */
+       data &= 0x7F;
+       XGINew_SetReg1(pVBInfo->P3d4, 0x11, data);
+
+       data = pVBInfo->TimingH[0].data[0];
+       XGINew_SetReg1(pVBInfo->P3d4, 0, data);
+
+       for (i = 0x01; i <= 0x04; i++) {
+               data = pVBInfo->TimingH[0].data[i];
+               XGINew_SetReg1(pVBInfo->P3d4, (unsigned short) (i + 1), data);
        }
-       */
-}
 
-static void XGI_SetATTRegs(unsigned short ModeNo, unsigned short StandTableIndex,
-               unsigned short ModeIdIndex, struct vb_device_info *pVBInfo)
-{
-       unsigned char ARdata;
-       unsigned short i, modeflag;
+       for (i = 0x05; i <= 0x06; i++) {
+               data = pVBInfo->TimingH[0].data[i];
+               XGINew_SetReg1(pVBInfo->P3c4, (unsigned short) (i + 6), data);
+       }
 
-       if (ModeNo <= 0x13)
-               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag;
-       else
-               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
+       j = (unsigned char) XGINew_GetReg1(pVBInfo->P3c4, 0x0e);
+       j &= 0x1F;
+       data = pVBInfo->TimingH[0].data[7];
+       data &= 0xE0;
+       data |= j;
+       XGINew_SetReg1(pVBInfo->P3c4, 0x0e, data);
 
-       for (i = 0; i <= 0x13; i++) {
-               ARdata = pVBInfo->StandTable[StandTableIndex].ATTR[i];
-               if (modeflag & Charx8Dot) { /* ifndef Dot9 */
-                       if (i == 0x13) {
-                               if (pVBInfo->VBInfo & SetCRT2ToLCDA) {
-                                       ARdata = 0;
-                               } else {
-                                       if (pVBInfo->VBInfo & (SetCRT2ToTV
-                                                       | SetCRT2ToLCD)) {
-                                               if (pVBInfo->VBInfo
-                                                               & SetInSlaveMode)
-                                                       ARdata = 0;
-                                       }
-                               }
-                       }
+       if (HwDeviceExtension->jChipType >= XG20) {
+               data = (unsigned char) XGINew_GetReg1(pVBInfo->P3d4, 0x04);
+               data = data - 1;
+               XGINew_SetReg1(pVBInfo->P3d4, 0x04, data);
+               data = (unsigned char) XGINew_GetReg1(pVBInfo->P3d4, 0x05);
+               data1 = data;
+               data1 &= 0xE0;
+               data &= 0x1F;
+               if (data == 0) {
+                       pushax = data;
+                       data = (unsigned char) XGINew_GetReg1(pVBInfo->P3c4,
+                                       0x0c);
+                       data &= 0xFB;
+                       XGINew_SetReg1(pVBInfo->P3c4, 0x0c, data);
+                       data = pushax;
                }
-
-               XGINew_GetReg2(pVBInfo->P3da); /* reset 3da */
-               XGINew_SetReg3(pVBInfo->P3c0, i); /* set index */
-               XGINew_SetReg3(pVBInfo->P3c0, ARdata); /* set data */
+               data = data - 1;
+               data |= data1;
+               XGINew_SetReg1(pVBInfo->P3d4, 0x05, data);
+               data = (unsigned char) XGINew_GetReg1(pVBInfo->P3c4, 0x0e);
+               data = data >> 5;
+               data = data + 3;
+               if (data > 7)
+                       data = data - 7;
+               data = data << 5;
+               XGINew_SetRegANDOR(pVBInfo->P3c4, 0x0e, ~0xE0, data);
        }
-
-       XGINew_GetReg2(pVBInfo->P3da); /* reset 3da */
-       XGINew_SetReg3(pVBInfo->P3c0, 0x14); /* set index */
-       XGINew_SetReg3(pVBInfo->P3c0, 0x00); /* set data */
-       XGINew_GetReg2(pVBInfo->P3da); /* Enable Attribute */
-       XGINew_SetReg3(pVBInfo->P3c0, 0x20);
 }
 
-static void XGI_SetGRCRegs(unsigned short StandTableIndex,
+static void XGI_SetCRT1Timing_V(unsigned short ModeIdIndex, unsigned short ModeNo,
                struct vb_device_info *pVBInfo)
 {
-       unsigned char GRdata;
-       unsigned short i;
+       unsigned char data;
+       unsigned short i, j;
 
-       for (i = 0; i <= 0x08; i++) {
-               GRdata = pVBInfo->StandTable[StandTableIndex].GRC[i]; /* Get GR from file */
-               XGINew_SetReg1(pVBInfo->P3ce, i, GRdata); /* Set GR(3ce) */
+       /* XGINew_SetReg1(pVBInfo->P3d4, 0x51, 0); */
+       /* XGINew_SetReg1(pVBInfo->P3d4, 0x56, 0); */
+       /* XGINew_SetRegANDOR(pVBInfo->P3d4, 0x11, 0x7f, 0x00); */
+
+       for (i = 0x00; i <= 0x01; i++) {
+               data = pVBInfo->TimingV[0].data[i];
+               XGINew_SetReg1(pVBInfo->P3d4, (unsigned short) (i + 6), data);
        }
 
-       if (pVBInfo->ModeType > ModeVGA) {
-               GRdata = (unsigned char) XGINew_GetReg1(pVBInfo->P3ce, 0x05);
-               GRdata &= 0xBF; /* 256 color disable */
-               XGINew_SetReg1(pVBInfo->P3ce, 0x05, GRdata);
+       for (i = 0x02; i <= 0x03; i++) {
+               data = pVBInfo->TimingV[0].data[i];
+               XGINew_SetReg1(pVBInfo->P3d4, (unsigned short) (i + 0x0e), data);
        }
-}
 
-static void XGI_ClearExt1Regs(struct vb_device_info *pVBInfo)
-{
-       unsigned short i;
+       for (i = 0x04; i <= 0x05; i++) {
+               data = pVBInfo->TimingV[0].data[i];
+               XGINew_SetReg1(pVBInfo->P3d4, (unsigned short) (i + 0x11), data);
+       }
 
-       for (i = 0x0A; i <= 0x0E; i++)
-               XGINew_SetReg1(pVBInfo->P3c4, i, 0x00); /* Clear SR0A-SR0E */
-}
+       j = (unsigned char) XGINew_GetReg1(pVBInfo->P3c4, 0x0a);
+       j &= 0xC0;
+       data = pVBInfo->TimingV[0].data[6];
+       data &= 0x3F;
+       data |= j;
+       XGINew_SetReg1(pVBInfo->P3c4, 0x0a, data);
 
-static unsigned char XGI_SetDefaultVCLK(struct vb_device_info *pVBInfo)
-{
+       data = pVBInfo->TimingV[0].data[6];
+       data &= 0x80;
+       data = data >> 2;
 
-       XGINew_SetRegANDOR(pVBInfo->P3c4, 0x31, ~0x30, 0x20);
-       XGINew_SetReg1(pVBInfo->P3c4, 0x2B, pVBInfo->VCLKData[0].SR2B);
-       XGINew_SetReg1(pVBInfo->P3c4, 0x2C, pVBInfo->VCLKData[0].SR2C);
+       if (ModeNo <= 0x13)
+               i = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag;
+       else
+               i = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
 
-       XGINew_SetRegANDOR(pVBInfo->P3c4, 0x31, ~0x30, 0x10);
-       XGINew_SetReg1(pVBInfo->P3c4, 0x2B, pVBInfo->VCLKData[1].SR2B);
-       XGINew_SetReg1(pVBInfo->P3c4, 0x2C, pVBInfo->VCLKData[1].SR2C);
+       i &= DoubleScanMode;
+       if (i)
+               data |= 0x80;
 
-       XGINew_SetRegAND(pVBInfo->P3c4, 0x31, ~0x30);
-       return 0;
+       j = (unsigned char) XGINew_GetReg1(pVBInfo->P3d4, 0x09);
+       j &= 0x5F;
+       data |= j;
+       XGINew_SetReg1(pVBInfo->P3d4, 0x09, data);
 }
 
-unsigned short XGI_GetRatePtrCRT2(struct xgi_hw_device_info *pXGIHWDE,
-               unsigned short ModeNo, unsigned short ModeIdIndex,
-               struct vb_device_info *pVBInfo)
+static void XGI_SetCRT1CRTC(unsigned short ModeNo, unsigned short ModeIdIndex,
+               unsigned short RefreshRateTableIndex,
+               struct vb_device_info *pVBInfo,
+               struct xgi_hw_device_info *HwDeviceExtension)
 {
-       short LCDRefreshIndex[] = { 0x00, 0x00, 0x03, 0x01 },
-                       LCDARefreshIndex[] = { 0x00, 0x00, 0x03, 0x01, 0x01,
-                                       0x01, 0x01 };
-
-       unsigned short RefreshRateTableIndex, i, modeflag, index, temp;
-
-       if (ModeNo <= 0x13)
-               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag;
-       else
-               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
-
-       if (pVBInfo->IF_DEF_CH7005 == 1) {
-               if (pVBInfo->VBInfo & SetCRT2ToTV) {
-                       if (modeflag & HalfDCLK)
-                               return 0;
-               }
-       }
-
-       if (ModeNo < 0x14)
-               return 0xFFFF;
-
-       index = XGINew_GetReg1(pVBInfo->P3d4, 0x33);
-       index = index >> pVBInfo->SelectCRT2Rate;
-       index &= 0x0F;
-
-       if (pVBInfo->LCDInfo & LCDNonExpanding)
-               index = 0;
+       unsigned char index, data;
+       unsigned short i;
 
-       if (index > 0)
-               index--;
+       index = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT1CRTC; /* Get index */
+       index = index & IndexMask;
 
-       if (pVBInfo->SetFlag & ProgrammingCRT2) {
-               if (pVBInfo->IF_DEF_CH7005 == 1) {
-                       if (pVBInfo->VBInfo & SetCRT2ToTV)
-                               index = 0;
-               }
+       data = (unsigned char) XGINew_GetReg1(pVBInfo->P3d4, 0x11);
+       data &= 0x7F;
+       XGINew_SetReg1(pVBInfo->P3d4, 0x11, data); /* Unlock CRTC */
 
-               if (pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
-                       if (pVBInfo->IF_DEF_LVDS == 0) {
-                               if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B
-                                               | VB_XGI301LV | VB_XGI302LV
-                                               | VB_XGI301C))
-                                       temp
-                                                       = LCDARefreshIndex[pVBInfo->LCDResInfo
-                                                                       & 0x0F]; /* 301b */
-                               else
-                                       temp
-                                                       = LCDRefreshIndex[pVBInfo->LCDResInfo
-                                                                       & 0x0F];
+       for (i = 0; i < 8; i++)
+               pVBInfo->TimingH[0].data[i]
+                               = pVBInfo->XGINEWUB_CRT1Table[index].CR[i];
 
-                               if (index > temp)
-                                       index = temp;
-                       } else {
-                               index = 0;
-                       }
-               }
-       }
+       for (i = 0; i < 7; i++)
+               pVBInfo->TimingV[0].data[i]
+                               = pVBInfo->XGINEWUB_CRT1Table[index].CR[i + 8];
 
-       RefreshRateTableIndex = pVBInfo->EModeIDTable[ModeIdIndex].REFindex;
-       ModeNo = pVBInfo->RefIndex[RefreshRateTableIndex].ModeID;
-       if (pXGIHWDE->jChipType >= XG20) { /* for XG20, XG21, XG27 */
-               /*
-               if (pVBInfo->RefIndex[RefreshRateTableIndex].Ext_InfoFlag & XG2xNotSupport) {
-                       index++;
-               }
-               */
-               if ((pVBInfo->RefIndex[RefreshRateTableIndex].XRes == 800)
-                               && (pVBInfo->RefIndex[RefreshRateTableIndex].YRes
-                                               == 600)) {
-                       index++;
-               }
-               /* Alan 10/19/2007; do the similiar adjustment like XGISearchCRT1Rate() */
-               if ((pVBInfo->RefIndex[RefreshRateTableIndex].XRes == 1024)
-                               && (pVBInfo->RefIndex[RefreshRateTableIndex].YRes
-                                               == 768)) {
-                       index++;
-               }
-               if ((pVBInfo->RefIndex[RefreshRateTableIndex].XRes == 1280)
-                               && (pVBInfo->RefIndex[RefreshRateTableIndex].YRes
-                                               == 1024)) {
-                       index++;
-               }
-       }
+       XGI_SetCRT1Timing_H(pVBInfo, HwDeviceExtension);
 
-       i = 0;
-       do {
-               if (pVBInfo->RefIndex[RefreshRateTableIndex + i].ModeID
-                               != ModeNo)
-                       break;
-               temp
-                               = pVBInfo->RefIndex[RefreshRateTableIndex + i].Ext_InfoFlag;
-               temp &= ModeInfoFlag;
-               if (temp < pVBInfo->ModeType)
-                       break;
-               i++;
-               index--;
+       XGI_SetCRT1Timing_V(ModeIdIndex, ModeNo, pVBInfo);
 
-       } while (index != 0xFFFF);
-       if (!(pVBInfo->VBInfo & SetCRT2ToRAMDAC)) {
-               if (pVBInfo->VBInfo & SetInSlaveMode) {
-                       temp
-                                       = pVBInfo->RefIndex[RefreshRateTableIndex
-                                                       + i - 1].Ext_InfoFlag;
-                       if (temp & InterlaceMode)
-                               i++;
-               }
-       }
-       i--;
-       if ((pVBInfo->SetFlag & ProgrammingCRT2)) {
-               temp = XGI_AjustCRT2Rate(ModeNo, ModeIdIndex,
-                               RefreshRateTableIndex, &i, pVBInfo);
-       }
-       return RefreshRateTableIndex + i; /* return (0x01 | (temp1<<1)); */
+       if (pVBInfo->ModeType > 0x03)
+               XGINew_SetReg1(pVBInfo->P3d4, 0x14, 0x4F);
 }
 
-static unsigned char XGI_AjustCRT2Rate(unsigned short ModeNo,
-               unsigned short ModeIdIndex,
-               unsigned short RefreshRateTableIndex, unsigned short *i,
+/* --------------------------------------------------------------------- */
+/* Function : XGI_SetXG21CRTC */
+/* Input : Stand or enhance CRTC table */
+/* Output : Fill CRT Hsync/Vsync to SR2E/SR2F/SR30/SR33/SR34/SR3F */
+/* Description : Set LCD timing */
+/* --------------------------------------------------------------------- */
+static void XGI_SetXG21CRTC(unsigned short ModeNo, unsigned short ModeIdIndex,
+               unsigned short RefreshRateTableIndex,
                struct vb_device_info *pVBInfo)
 {
-       unsigned short tempax, tempbx, resinfo, modeflag, infoflag;
-
-       if (ModeNo <= 0x13)
-               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag; /* si+St_ModeFlag */
-       else
-               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
+       unsigned char StandTableIndex, index, Tempax, Tempbx, Tempcx, Tempdx;
+       unsigned short Temp1, Temp2, Temp3;
 
-       resinfo = pVBInfo->EModeIDTable[ModeIdIndex].Ext_RESINFO;
-       tempbx = pVBInfo->RefIndex[RefreshRateTableIndex + (*i)].ModeID;
-       tempax = 0;
+       if (ModeNo <= 0x13) {
+               StandTableIndex = XGI_GetModePtr(ModeNo, ModeIdIndex, pVBInfo);
+               Tempax = pVBInfo->StandTable[StandTableIndex].CRTC[4]; /* CR04 HRS */
+               XGINew_SetReg1(pVBInfo->P3c4, 0x2E, Tempax); /* SR2E [7:0]->HRS */
+               Tempbx = pVBInfo->StandTable[StandTableIndex].CRTC[5]; /* Tempbx: CR05 HRE */
+               Tempbx &= 0x1F; /* Tempbx: HRE[4:0] */
+               Tempcx = Tempax;
+               Tempcx &= 0xE0; /* Tempcx: HRS[7:5] */
+               Tempdx = Tempcx | Tempbx; /* Tempdx(HRE): HRS[7:5]HRE[4:0] */
+               if (Tempbx < (Tempax & 0x1F)) /* IF HRE < HRS */
+                       Tempdx |= 0x20; /* Tempdx: HRE = HRE + 0x20 */
+               Tempdx <<= 2; /* Tempdx << 2 */
+               XGINew_SetReg1(pVBInfo->P3c4, 0x2F, Tempdx); /* SR2F [7:2]->HRE */
+               XGINew_SetRegANDOR(pVBInfo->P3c4, 0x30, 0xE3, 00);
 
-       if (pVBInfo->IF_DEF_LVDS == 0) {
-               if (pVBInfo->VBInfo & SetCRT2ToRAMDAC) {
-                       tempax |= SupportRAMDAC2;
+               Tempax = pVBInfo->StandTable[StandTableIndex].CRTC[16]; /* Tempax: CR16 VRS */
+               Tempbx = Tempax; /* Tempbx=Tempax */
+               Tempax &= 0x01; /* Tempax: VRS[0] */
+               XGINew_SetRegOR(pVBInfo->P3c4, 0x33, Tempax); /* SR33[0]->VRS */
+               Tempax = pVBInfo->StandTable[StandTableIndex].CRTC[7]; /* Tempax: CR7 VRS */
+               Tempdx = Tempbx >> 1; /* Tempdx: VRS[7:1] */
+               Tempcx = Tempax & 0x04; /* Tempcx: CR7[2] */
+               Tempcx <<= 5; /* Tempcx[7]: VRS[8] */
+               Tempdx |= Tempcx; /* Tempdx: VRS[8:1] */
+               XGINew_SetReg1(pVBInfo->P3c4, 0x34, Tempdx); /* SR34[7:0]: VRS[8:1] */
 
-                       if (pVBInfo->VBType & VB_XGI301C)
-                               tempax |= SupportCRT2in301C;
-               }
+               Temp1 = Tempcx << 1; /* Temp1[8]: VRS[8] unsigned char -> unsigned short */
+               Temp1 |= Tempbx; /* Temp1[8:0]: VRS[8:0] */
+               Tempax &= 0x80; /* Tempax[7]: CR7[7] */
+               Temp2 = Tempax << 2; /* Temp2[9]: VRS[9] */
+               Temp1 |= Temp2; /* Temp1[9:0]: VRS[9:0] */
 
-               if (pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) { /* 301b */
-                       tempax |= SupportLCD;
+               Tempax = pVBInfo->StandTable[StandTableIndex].CRTC[17]; /* CR16 VRE */
+               Tempax &= 0x0F; /* Tempax[3:0]: VRE[3:0] */
+               Temp2 = Temp1 & 0x3F0; /* Temp2[9:4]: VRS[9:4] */
+               Temp2 |= Tempax; /* Temp2[9:0]: VRE[9:0] */
+               Temp3 = Temp1 & 0x0F; /* Temp3[3:0]: VRS[3:0] */
+               if (Tempax < Temp3) /* VRE[3:0]<VRS[3:0] */
+                       Temp2 |= 0x10; /* Temp2: VRE + 0x10 */
+               Temp2 &= 0xFF; /* Temp2[7:0]: VRE[7:0] */
+               Tempax = (unsigned char) Temp2; /* Tempax[7:0]: VRE[7:0] */
+               Tempax <<= 2; /* Tempax << 2: VRE[5:0] */
+               Temp1 &= 0x600; /* Temp1[10:9]: VRS[10:9] */
+               Temp1 >>= 9; /* [10:9]->[1:0] */
+               Tempbx = (unsigned char) Temp1; /* Tempbx[1:0]: VRS[10:9] */
+               Tempax |= Tempbx; /* VRE[5:0]VRS[10:9] */
+               Tempax &= 0x7F;
+               XGINew_SetReg1(pVBInfo->P3c4, 0x3F, Tempax); /* SR3F D[7:2]->VRE D[1:0]->VRS */
+       } else {
+               index = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT1CRTC;
+               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[3]; /* Tempax: CR4 HRS */
+               Tempcx = Tempax; /* Tempcx: HRS */
+               XGINew_SetReg1(pVBInfo->P3c4, 0x2E, Tempax); /* SR2E[7:0]->HRS */
 
-                       if (pVBInfo->LCDResInfo != Panel1280x1024) {
-                               if (pVBInfo->LCDResInfo != Panel1280x960) {
-                                       if (pVBInfo->LCDInfo & LCDNonExpanding) {
-                                               if (resinfo >= 9) {
-                                                       tempax = 0;
-                                                       return 0;
-                                               }
-                                       }
-                               }
-                       }
-               }
+               Tempdx = pVBInfo->XGINEWUB_CRT1Table[index].CR[5]; /* SRB */
+               Tempdx &= 0xC0; /* Tempdx[7:6]: SRB[7:6] */
+               Temp1 = Tempdx; /* Temp1[7:6]: HRS[9:8] */
+               Temp1 <<= 2; /* Temp1[9:8]: HRS[9:8] */
+               Temp1 |= Tempax; /* Temp1[9:0]: HRS[9:0] */
 
-               if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV) { /* for HiTV */
-                       if ((pVBInfo->VBType & VB_XGI301LV)
-                                       && (pVBInfo->VBExtInfo == VB_YPbPr1080i)) {
-                               tempax |= SupportYPbPr;
-                               if (pVBInfo->VBInfo & SetInSlaveMode) {
-                                       if (resinfo == 4)
-                                               return 0;
+               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[4]; /* CR5 HRE */
+               Tempax &= 0x1F; /* Tempax[4:0]: HRE[4:0] */
 
-                                       if (resinfo == 3)
-                                               return 0;
+               Tempbx = pVBInfo->XGINEWUB_CRT1Table[index].CR[6]; /* SRC */
+               Tempbx &= 0x04; /* Tempbx[2]: HRE[5] */
+               Tempbx <<= 3; /* Tempbx[5]: HRE[5] */
+               Tempax |= Tempbx; /* Tempax[5:0]: HRE[5:0] */
 
-                                       if (resinfo > 7)
-                                               return 0;
-                               }
-                       } else {
-                               tempax |= SupportHiVisionTV;
-                               if (pVBInfo->VBInfo & SetInSlaveMode) {
-                                       if (resinfo == 4)
-                                               return 0;
+               Temp2 = Temp1 & 0x3C0; /* Temp2[9:6]: HRS[9:6] */
+               Temp2 |= Tempax; /* Temp2[9:0]: HRE[9:0] */
 
-                                       if (resinfo == 3) {
-                                               if (pVBInfo->SetFlag
-                                                               & TVSimuMode)
-                                                       return 0;
-                                       }
+               Tempcx &= 0x3F; /* Tempcx[5:0]: HRS[5:0] */
+               if (Tempax < Tempcx) /* HRE < HRS */
+                       Temp2 |= 0x40; /* Temp2 + 0x40 */
 
-                                       if (resinfo > 7)
-                                               return 0;
-                               }
-                       }
-               } else {
-                       if (pVBInfo->VBInfo & (SetCRT2ToAVIDEO
-                                       | SetCRT2ToSVIDEO | SetCRT2ToSCART
-                                       | SetCRT2ToYPbPr | SetCRT2ToHiVisionTV)) {
-                               tempax |= SupportTV;
-
-                               if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B
-                                               | VB_XGI301LV | VB_XGI302LV
-                                               | VB_XGI301C)) {
-                                       tempax |= SupportTV1024;
-                               }
-
-                               if (!(pVBInfo->VBInfo & SetPALTV)) {
-                                       if (modeflag & NoSupportSimuTV) {
-                                               if (pVBInfo->VBInfo
-                                                               & SetInSlaveMode) {
-                                                       if (!(pVBInfo->VBInfo
-                                                                       & SetNotSimuMode)) {
-                                                               return 0;
-                                                       }
-                                               }
-                                       }
-                               }
-                       }
-               }
-       } else { /* for LVDS */
-               if (pVBInfo->IF_DEF_CH7005 == 1) {
-                       if (pVBInfo->VBInfo & SetCRT2ToTV)
-                               tempax |= SupportCHTV;
-               }
-
-               if (pVBInfo->VBInfo & SetCRT2ToLCD) {
-                       tempax |= SupportLCD;
-
-                       if (resinfo > 0x08)
-                               return 0; /* 1024x768 */
-
-                       if (pVBInfo->LCDResInfo < Panel1024x768) {
-                               if (resinfo > 0x07)
-                                       return 0; /* 800x600 */
+               Temp2 &= 0xFF;
+               Tempax = (unsigned char) Temp2; /* Tempax: HRE[7:0] */
+               Tempax <<= 2; /* Tempax[7:2]: HRE[5:0] */
+               Tempdx >>= 6; /* Tempdx[7:6]->[1:0] HRS[9:8] */
+               Tempax |= Tempdx; /* HRE[5:0]HRS[9:8] */
+               XGINew_SetReg1(pVBInfo->P3c4, 0x2F, Tempax); /* SR2F D[7:2]->HRE, D[1:0]->HRS */
+               XGINew_SetRegANDOR(pVBInfo->P3c4, 0x30, 0xE3, 00);
 
-                               if (resinfo == 0x04)
-                                       return 0; /* 512x384 */
-                       }
-               }
-       }
+               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[10]; /* CR10 VRS */
+               Tempbx = Tempax; /* Tempbx: VRS */
+               Tempax &= 0x01; /* Tempax[0]: VRS[0] */
+               XGINew_SetRegOR(pVBInfo->P3c4, 0x33, Tempax); /* SR33[0]->VRS[0] */
+               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[9]; /* CR7[2][7] VRE */
+               Tempcx = Tempbx >> 1; /* Tempcx[6:0]: VRS[7:1] */
+               Tempdx = Tempax & 0x04; /* Tempdx[2]: CR7[2] */
+               Tempdx <<= 5; /* Tempdx[7]: VRS[8] */
+               Tempcx |= Tempdx; /* Tempcx[7:0]: VRS[8:1] */
+               XGINew_SetReg1(pVBInfo->P3c4, 0x34, Tempcx); /* SR34[8:1]->VRS */
 
-       for (; pVBInfo->RefIndex[RefreshRateTableIndex + (*i)].ModeID == tempbx; (*i)--) {
-               infoflag
-                               = pVBInfo->RefIndex[RefreshRateTableIndex
-                                               + (*i)].Ext_InfoFlag;
-               if (infoflag & tempax)
-                       return 1;
+               Temp1 = Tempdx; /* Temp1[7]: Tempdx[7] */
+               Temp1 <<= 1; /* Temp1[8]: VRS[8] */
+               Temp1 |= Tempbx; /* Temp1[8:0]: VRS[8:0] */
+               Tempax &= 0x80;
+               Temp2 = Tempax << 2; /* Temp2[9]: VRS[9] */
+               Temp1 |= Temp2; /* Temp1[9:0]: VRS[9:0] */
+               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[14]; /* Tempax: SRA */
+               Tempax &= 0x08; /* Tempax[3]: VRS[3] */
+               Temp2 = Tempax;
+               Temp2 <<= 7; /* Temp2[10]: VRS[10] */
+               Temp1 |= Temp2; /* Temp1[10:0]: VRS[10:0] */
 
-               if ((*i) == 0)
-                       break;
-       }
+               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[11]; /* Tempax: CR11 VRE */
+               Tempax &= 0x0F; /* Tempax[3:0]: VRE[3:0] */
+               Tempbx = pVBInfo->XGINEWUB_CRT1Table[index].CR[14]; /* Tempbx: SRA */
+               Tempbx &= 0x20; /* Tempbx[5]: VRE[5] */
+               Tempbx >>= 1; /* Tempbx[4]: VRE[4] */
+               Tempax |= Tempbx; /* Tempax[4:0]: VRE[4:0] */
+               Temp2 = Temp1 & 0x7E0; /* Temp2[10:5]: VRS[10:5] */
+               Temp2 |= Tempax; /* Temp2[10:5]: VRE[10:5] */
 
-       for ((*i) = 0;; (*i)++) {
-               infoflag
-                               = pVBInfo->RefIndex[RefreshRateTableIndex
-                                               + (*i)].Ext_InfoFlag;
-               if (pVBInfo->RefIndex[RefreshRateTableIndex + (*i)].ModeID
-                               != tempbx) {
-                       return 0;
-               }
+               Temp3 = Temp1 & 0x1F; /* Temp3[4:0]: VRS[4:0] */
+               if (Tempax < Temp3) /* VRE < VRS */
+                       Temp2 |= 0x20; /* VRE + 0x20 */
 
-               if (infoflag & tempax)
-                       return 1;
+               Temp2 &= 0xFF;
+               Tempax = (unsigned char) Temp2; /* Tempax: VRE[7:0] */
+               Tempax <<= 2; /* Tempax[7:0]; VRE[5:0]00 */
+               Temp1 &= 0x600; /* Temp1[10:9]: VRS[10:9] */
+               Temp1 >>= 9; /* Temp1[1:0]: VRS[10:9] */
+               Tempbx = (unsigned char) Temp1;
+               Tempax |= Tempbx; /* Tempax[7:0]: VRE[5:0]VRS[10:9] */
+               Tempax &= 0x7F;
+               XGINew_SetReg1(pVBInfo->P3c4, 0x3F, Tempax); /* SR3F D[7:2]->VRE D[1:0]->VRS */
        }
-       return 1;
 }
 
-static void XGI_SetSync(unsigned short RefreshRateTableIndex,
+static void XGI_SetXG27CRTC(unsigned short ModeNo, unsigned short ModeIdIndex,
+               unsigned short RefreshRateTableIndex,
                struct vb_device_info *pVBInfo)
 {
-       unsigned short sync, temp;
+       unsigned short StandTableIndex, index, Tempax, Tempbx, Tempcx, Tempdx;
 
-       sync = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_InfoFlag >> 8; /* di+0x00 */
-       sync &= 0xC0;
-       temp = 0x2F;
-       temp |= sync;
-       XGINew_SetReg3(pVBInfo->P3c2, temp); /* Set Misc(3c2) */
-}
+       if (ModeNo <= 0x13) {
+               StandTableIndex = XGI_GetModePtr(ModeNo, ModeIdIndex, pVBInfo);
+               Tempax = pVBInfo->StandTable[StandTableIndex].CRTC[4]; /* CR04 HRS */
+               XGINew_SetReg1(pVBInfo->P3c4, 0x2E, Tempax); /* SR2E [7:0]->HRS */
+               Tempbx = pVBInfo->StandTable[StandTableIndex].CRTC[5]; /* Tempbx: CR05 HRE */
+               Tempbx &= 0x1F; /* Tempbx: HRE[4:0] */
+               Tempcx = Tempax;
+               Tempcx &= 0xE0; /* Tempcx: HRS[7:5] */
+               Tempdx = Tempcx | Tempbx; /* Tempdx(HRE): HRS[7:5]HRE[4:0] */
+               if (Tempbx < (Tempax & 0x1F)) /* IF HRE < HRS */
+                       Tempdx |= 0x20; /* Tempdx: HRE = HRE + 0x20 */
+               Tempdx <<= 2; /* Tempdx << 2 */
+               XGINew_SetReg1(pVBInfo->P3c4, 0x2F, Tempdx); /* SR2F [7:2]->HRE */
+               XGINew_SetRegANDOR(pVBInfo->P3c4, 0x30, 0xE3, 00);
 
-static void XGI_SetCRT1CRTC(unsigned short ModeNo, unsigned short ModeIdIndex,
-               unsigned short RefreshRateTableIndex,
-               struct vb_device_info *pVBInfo,
-               struct xgi_hw_device_info *HwDeviceExtension)
-{
-       unsigned char index, data;
-       unsigned short i;
+               Tempax = pVBInfo->StandTable[StandTableIndex].CRTC[16]; /* Tempax: CR10 VRS */
+               XGINew_SetReg1(pVBInfo->P3c4, 0x34, Tempax); /* SR34[7:0]->VRS */
+               Tempcx = Tempax; /* Tempcx=Tempax=VRS[7:0] */
+               Tempax = pVBInfo->StandTable[StandTableIndex].CRTC[7]; /* Tempax[7][2]: CR7[7][2] VRS[9][8] */
+               Tempbx = Tempax; /* Tempbx=CR07 */
+               Tempax &= 0x04; /* Tempax[2]: CR07[2] VRS[8] */
+               Tempax >>= 2;
+               XGINew_SetRegANDOR(pVBInfo->P3c4, 0x35, ~0x01, Tempax); /* SR35 D[0]->VRS D[8] */
+               Tempcx |= (Tempax << 8); /* Tempcx[8] |= VRS[8] */
+               Tempcx |= (Tempbx & 0x80) << 2; /* Tempcx[9] |= VRS[9] */
 
-       index = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT1CRTC; /* Get index */
-       index = index & IndexMask;
+               Tempax = pVBInfo->StandTable[StandTableIndex].CRTC[17]; /* CR11 VRE */
+               Tempax &= 0x0F; /* Tempax: VRE[3:0] */
+               Tempbx = Tempcx; /* Tempbx=Tempcx=VRS[9:0] */
+               Tempbx &= 0x3F0; /* Tempbx[9:4]: VRS[9:4] */
+               Tempbx |= Tempax; /* Tempbx[9:0]: VRE[9:0] */
+               if (Tempax <= (Tempcx & 0x0F)) /* VRE[3:0]<=VRS[3:0] */
+                       Tempbx |= 0x10; /* Tempbx: VRE + 0x10 */
+               Tempax = (unsigned char) Tempbx & 0xFF; /* Tempax[7:0]: VRE[7:0] */
+               Tempax <<= 2; /* Tempax << 2: VRE[5:0] */
+               Tempcx = (Tempcx & 0x600) >> 8; /* Tempcx VRS[10:9] */
+               XGINew_SetRegANDOR(pVBInfo->P3c4, 0x3F, ~0xFC, Tempax); /* SR3F D[7:2]->VRE D[5:0] */
+               XGINew_SetRegANDOR(pVBInfo->P3c4, 0x35, ~0x06, Tempcx); /* SR35 D[2:1]->VRS[10:9] */
+       } else {
+               index = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT1CRTC;
+               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[3]; /* Tempax: CR4 HRS */
+               Tempbx = Tempax; /* Tempbx: HRS[7:0] */
+               XGINew_SetReg1(pVBInfo->P3c4, 0x2E, Tempax); /* SR2E[7:0]->HRS */
 
-       data = (unsigned char) XGINew_GetReg1(pVBInfo->P3d4, 0x11);
-       data &= 0x7F;
-       XGINew_SetReg1(pVBInfo->P3d4, 0x11, data); /* Unlock CRTC */
+               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[5]; /* SR0B */
+               Tempax &= 0xC0; /* Tempax[7:6]: SR0B[7:6]: HRS[9:8]*/
+               Tempbx |= (Tempax << 2); /* Tempbx: HRS[9:0] */
 
-       for (i = 0; i < 8; i++)
-               pVBInfo->TimingH[0].data[i]
-                               = pVBInfo->XGINEWUB_CRT1Table[index].CR[i];
+               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[4]; /* CR5 HRE */
+               Tempax &= 0x1F; /* Tempax[4:0]: HRE[4:0] */
+               Tempcx = Tempax; /* Tempcx: HRE[4:0] */
 
-       for (i = 0; i < 7; i++)
-               pVBInfo->TimingV[0].data[i]
-                               = pVBInfo->XGINEWUB_CRT1Table[index].CR[i + 8];
+               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[6]; /* SRC */
+               Tempax &= 0x04; /* Tempax[2]: HRE[5] */
+               Tempax <<= 3; /* Tempax[5]: HRE[5] */
+               Tempcx |= Tempax; /* Tempcx[5:0]: HRE[5:0] */
 
-       XGI_SetCRT1Timing_H(pVBInfo, HwDeviceExtension);
+               Tempbx = Tempbx & 0x3C0; /* Tempbx[9:6]: HRS[9:6] */
+               Tempbx |= Tempcx; /* Tempbx: HRS[9:6]HRE[5:0] */
 
-       XGI_SetCRT1Timing_V(ModeIdIndex, ModeNo, pVBInfo);
+               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[3]; /* Tempax: CR4 HRS */
+               Tempax &= 0x3F; /* Tempax: HRS[5:0] */
+               if (Tempcx <= Tempax) /* HRE[5:0] < HRS[5:0] */
+                       Tempbx += 0x40; /* Tempbx= Tempbx + 0x40 : HRE[9:0]*/
 
-       if (pVBInfo->ModeType > 0x03)
-               XGINew_SetReg1(pVBInfo->P3d4, 0x14, 0x4F);
-}
+               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[5]; /* SR0B */
+               Tempax &= 0xC0; /* Tempax[7:6]: SR0B[7:6]: HRS[9:8]*/
+               Tempax >>= 6; /* Tempax[1:0]: HRS[9:8]*/
+               Tempax |= ((Tempbx << 2) & 0xFF); /* Tempax[7:2]: HRE[5:0] */
+               XGINew_SetReg1(pVBInfo->P3c4, 0x2F, Tempax); /* SR2F [7:2][1:0]: HRE[5:0]HRS[9:8] */
+               XGINew_SetRegANDOR(pVBInfo->P3c4, 0x30, 0xE3, 00);
 
-static void XGI_SetCRT1Timing_H(struct vb_device_info *pVBInfo,
-               struct xgi_hw_device_info *HwDeviceExtension)
-{
-       unsigned char data, data1, pushax;
-       unsigned short i, j;
+               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[10]; /* CR10 VRS */
+               XGINew_SetReg1(pVBInfo->P3c4, 0x34, Tempax); /* SR34[7:0]->VRS[7:0] */
 
-       /* XGINew_SetReg1(pVBInfo->P3d4, 0x51, 0); */
-       /* XGINew_SetReg1(pVBInfo->P3d4, 0x56, 0); */
-       /* XGINew_SetRegANDOR(pVBInfo->P3d4, 0x11, 0x7f, 0x00); */
+               Tempcx = Tempax; /* Tempcx <= VRS[7:0] */
+               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[9]; /* CR7[7][2] VRS[9][8] */
+               Tempbx = Tempax; /* Tempbx <= CR07[7:0] */
+               Tempax = Tempax & 0x04; /* Tempax[2]: CR7[2]: VRS[8] */
+               Tempax >>= 2; /* Tempax[0]: VRS[8] */
+               XGINew_SetRegANDOR(pVBInfo->P3c4, 0x35, ~0x01, Tempax); /* SR35[0]: VRS[8] */
+               Tempcx |= (Tempax << 8); /* Tempcx <= VRS[8:0] */
+               Tempcx |= ((Tempbx & 0x80) << 2); /* Tempcx <= VRS[9:0] */
+               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[14]; /* Tempax: SR0A */
+               Tempax &= 0x08; /* SR0A[3] VRS[10] */
+               Tempcx |= (Tempax << 7); /* Tempcx <= VRS[10:0] */
 
-       data = (unsigned char) XGINew_GetReg1(pVBInfo->P3d4, 0x11); /* unlock cr0-7 */
-       data &= 0x7F;
-       XGINew_SetReg1(pVBInfo->P3d4, 0x11, data);
+               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[11]; /* Tempax: CR11 VRE */
+               Tempax &= 0x0F; /* Tempax[3:0]: VRE[3:0] */
+               Tempbx = pVBInfo->XGINEWUB_CRT1Table[index].CR[14]; /* Tempbx: SR0A */
+               Tempbx &= 0x20; /* Tempbx[5]: SR0A[5]: VRE[4] */
+               Tempbx >>= 1; /* Tempbx[4]: VRE[4] */
+               Tempax |= Tempbx; /* Tempax[4:0]: VRE[4:0] */
+               Tempbx = Tempcx; /* Tempbx: VRS[10:0] */
+               Tempbx &= 0x7E0; /* Tempbx[10:5]: VRS[10:5] */
+               Tempbx |= Tempax; /* Tempbx: VRS[10:5]VRE[4:0] */
 
-       data = pVBInfo->TimingH[0].data[0];
-       XGINew_SetReg1(pVBInfo->P3d4, 0, data);
+               if (Tempbx <= Tempcx) /* VRE <= VRS */
+                       Tempbx |= 0x20; /* VRE + 0x20 */
 
-       for (i = 0x01; i <= 0x04; i++) {
-               data = pVBInfo->TimingH[0].data[i];
-               XGINew_SetReg1(pVBInfo->P3d4, (unsigned short) (i + 1), data);
+               Tempax = (Tempbx << 2) & 0xFF; /* Tempax: Tempax[7:0]; VRE[5:0]00 */
+               XGINew_SetRegANDOR(pVBInfo->P3c4, 0x3F, ~0xFC, Tempax); /* SR3F[7:2]:VRE[5:0] */
+               Tempax = Tempcx >> 8;
+               XGINew_SetRegANDOR(pVBInfo->P3c4, 0x35, ~0x07, Tempax); /* SR35[2:0]:VRS[10:8] */
        }
+}
 
-       for (i = 0x05; i <= 0x06; i++) {
-               data = pVBInfo->TimingH[0].data[i];
-               XGINew_SetReg1(pVBInfo->P3c4, (unsigned short) (i + 6), data);
+/* --------------------------------------------------------------------- */
+/* Function : XGI_SetXG21LCD */
+/* Input : */
+/* Output : FCLK duty cycle, FCLK delay compensation */
+/* Description : All values set zero */
+/* --------------------------------------------------------------------- */
+static void XGI_SetXG21LCD(struct vb_device_info *pVBInfo,
+               unsigned short RefreshRateTableIndex, unsigned short ModeNo)
+{
+       unsigned short Data, Temp, b3CC;
+       unsigned short XGI_P3cc;
+
+       XGI_P3cc = pVBInfo->P3cc;
+
+       XGINew_SetReg1(pVBInfo->P3d4, 0x2E, 0x00);
+       XGINew_SetReg1(pVBInfo->P3d4, 0x2F, 0x00);
+       XGINew_SetReg1(pVBInfo->P3d4, 0x46, 0x00);
+       XGINew_SetReg1(pVBInfo->P3d4, 0x47, 0x00);
+       if (((*pVBInfo->pDVOSetting) & 0xC0) == 0xC0) {
+               XGINew_SetReg1(pVBInfo->P3d4, 0x2E, *pVBInfo->pCR2E);
+               XGINew_SetReg1(pVBInfo->P3d4, 0x2F, *pVBInfo->pCR2F);
+               XGINew_SetReg1(pVBInfo->P3d4, 0x46, *pVBInfo->pCR46);
+               XGINew_SetReg1(pVBInfo->P3d4, 0x47, *pVBInfo->pCR47);
        }
 
-       j = (unsigned char) XGINew_GetReg1(pVBInfo->P3c4, 0x0e);
-       j &= 0x1F;
-       data = pVBInfo->TimingH[0].data[7];
-       data &= 0xE0;
-       data |= j;
-       XGINew_SetReg1(pVBInfo->P3c4, 0x0e, data);
+       Temp = XGINew_GetReg1(pVBInfo->P3d4, 0x37);
 
-       if (HwDeviceExtension->jChipType >= XG20) {
-               data = (unsigned char) XGINew_GetReg1(pVBInfo->P3d4, 0x04);
-               data = data - 1;
-               XGINew_SetReg1(pVBInfo->P3d4, 0x04, data);
-               data = (unsigned char) XGINew_GetReg1(pVBInfo->P3d4, 0x05);
-               data1 = data;
-               data1 &= 0xE0;
-               data &= 0x1F;
-               if (data == 0) {
-                       pushax = data;
-                       data = (unsigned char) XGINew_GetReg1(pVBInfo->P3c4,
-                                       0x0c);
-                       data &= 0xFB;
-                       XGINew_SetReg1(pVBInfo->P3c4, 0x0c, data);
-                       data = pushax;
-               }
-               data = data - 1;
-               data |= data1;
-               XGINew_SetReg1(pVBInfo->P3d4, 0x05, data);
-               data = (unsigned char) XGINew_GetReg1(pVBInfo->P3c4, 0x0e);
-               data = data >> 5;
-               data = data + 3;
-               if (data > 7)
-                       data = data - 7;
-               data = data << 5;
-               XGINew_SetRegANDOR(pVBInfo->P3c4, 0x0e, ~0xE0, data);
+       if (Temp & 0x01) {
+               XGINew_SetRegOR(pVBInfo->P3c4, 0x06, 0x40); /* 18 bits FP */
+               XGINew_SetRegOR(pVBInfo->P3c4, 0x09, 0x40);
+       }
+
+       XGINew_SetRegOR(pVBInfo->P3c4, 0x1E, 0x01); /* Negative blank polarity */
+
+       XGINew_SetRegAND(pVBInfo->P3c4, 0x30, ~0x20);
+       XGINew_SetRegAND(pVBInfo->P3c4, 0x35, ~0x80);
+
+       if (ModeNo <= 0x13) {
+               b3CC = (unsigned char) XGINew_GetReg2(XGI_P3cc);
+               if (b3CC & 0x40)
+                       XGINew_SetRegOR(pVBInfo->P3c4, 0x30, 0x20); /* Hsync polarity */
+               if (b3CC & 0x80)
+                       XGINew_SetRegOR(pVBInfo->P3c4, 0x35, 0x80); /* Vsync polarity */
+       } else {
+               Data = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_InfoFlag;
+               if (Data & 0x4000)
+                       XGINew_SetRegOR(pVBInfo->P3c4, 0x30, 0x20); /* Hsync polarity */
+               if (Data & 0x8000)
+                       XGINew_SetRegOR(pVBInfo->P3c4, 0x35, 0x80); /* Vsync polarity */
        }
 }
 
-static void XGI_SetCRT1Timing_V(unsigned short ModeIdIndex, unsigned short ModeNo,
-               struct vb_device_info *pVBInfo)
+static void XGI_SetXG27LCD(struct vb_device_info *pVBInfo,
+               unsigned short RefreshRateTableIndex, unsigned short ModeNo)
 {
-       unsigned char data;
-       unsigned short i, j;
+       unsigned short Data, Temp, b3CC;
+       unsigned short XGI_P3cc;
 
-       /* XGINew_SetReg1(pVBInfo->P3d4, 0x51, 0); */
-       /* XGINew_SetReg1(pVBInfo->P3d4, 0x56, 0); */
-       /* XGINew_SetRegANDOR(pVBInfo->P3d4, 0x11, 0x7f, 0x00); */
+       XGI_P3cc = pVBInfo->P3cc;
 
-       for (i = 0x00; i <= 0x01; i++) {
-               data = pVBInfo->TimingV[0].data[i];
-               XGINew_SetReg1(pVBInfo->P3d4, (unsigned short) (i + 6), data);
-       }
+       XGINew_SetReg1(pVBInfo->P3d4, 0x2E, 0x00);
+       XGINew_SetReg1(pVBInfo->P3d4, 0x2F, 0x00);
+       XGINew_SetReg1(pVBInfo->P3d4, 0x46, 0x00);
+       XGINew_SetReg1(pVBInfo->P3d4, 0x47, 0x00);
 
-       for (i = 0x02; i <= 0x03; i++) {
-               data = pVBInfo->TimingV[0].data[i];
-               XGINew_SetReg1(pVBInfo->P3d4, (unsigned short) (i + 0x0e), data);
+       Temp = XGINew_GetReg1(pVBInfo->P3d4, 0x37);
+       if ((Temp & 0x03) == 0) { /* dual 12 */
+               XGINew_SetReg1(pVBInfo->P3d4, 0x46, 0x13);
+               XGINew_SetReg1(pVBInfo->P3d4, 0x47, 0x13);
        }
 
-       for (i = 0x04; i <= 0x05; i++) {
-               data = pVBInfo->TimingV[0].data[i];
-               XGINew_SetReg1(pVBInfo->P3d4, (unsigned short) (i + 0x11), data);
+       if (((*pVBInfo->pDVOSetting) & 0xC0) == 0xC0) {
+               XGINew_SetReg1(pVBInfo->P3d4, 0x2E, *pVBInfo->pCR2E);
+               XGINew_SetReg1(pVBInfo->P3d4, 0x2F, *pVBInfo->pCR2F);
+               XGINew_SetReg1(pVBInfo->P3d4, 0x46, *pVBInfo->pCR46);
+               XGINew_SetReg1(pVBInfo->P3d4, 0x47, *pVBInfo->pCR47);
        }
 
-       j = (unsigned char) XGINew_GetReg1(pVBInfo->P3c4, 0x0a);
-       j &= 0xC0;
-       data = pVBInfo->TimingV[0].data[6];
-       data &= 0x3F;
-       data |= j;
-       XGINew_SetReg1(pVBInfo->P3c4, 0x0a, data);
-
-       data = pVBInfo->TimingV[0].data[6];
-       data &= 0x80;
-       data = data >> 2;
+       XGI_SetXG27FPBits(pVBInfo);
 
-       if (ModeNo <= 0x13)
-               i = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag;
-       else
-               i = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
+       XGINew_SetRegOR(pVBInfo->P3c4, 0x1E, 0x01); /* Negative blank polarity */
 
-       i &= DoubleScanMode;
-       if (i)
-               data |= 0x80;
+       XGINew_SetRegAND(pVBInfo->P3c4, 0x30, ~0x20); /* Hsync polarity */
+       XGINew_SetRegAND(pVBInfo->P3c4, 0x35, ~0x80); /* Vsync polarity */
 
-       j = (unsigned char) XGINew_GetReg1(pVBInfo->P3d4, 0x09);
-       j &= 0x5F;
-       data |= j;
-       XGINew_SetReg1(pVBInfo->P3d4, 0x09, data);
+       if (ModeNo <= 0x13) {
+               b3CC = (unsigned char) XGINew_GetReg2(XGI_P3cc);
+               if (b3CC & 0x40)
+                       XGINew_SetRegOR(pVBInfo->P3c4, 0x30, 0x20); /* Hsync polarity */
+               if (b3CC & 0x80)
+                       XGINew_SetRegOR(pVBInfo->P3c4, 0x35, 0x80); /* Vsync polarity */
+       } else {
+               Data = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_InfoFlag;
+               if (Data & 0x4000)
+                       XGINew_SetRegOR(pVBInfo->P3c4, 0x30, 0x20); /* Hsync polarity */
+               if (Data & 0x8000)
+                       XGINew_SetRegOR(pVBInfo->P3c4, 0x35, 0x80); /* Vsync polarity */
+       }
 }
 
 /* --------------------------------------------------------------------- */
-/* Function : XGI_SetXG21CRTC */
-/* Input : Stand or enhance CRTC table */
-/* Output : Fill CRT Hsync/Vsync to SR2E/SR2F/SR30/SR33/SR34/SR3F */
-/* Description : Set LCD timing */
+/* Function : XGI_UpdateXG21CRTC */
+/* Input : */
+/* Output : CRT1 CRTC */
+/* Description : Modify CRT1 Hsync/Vsync to fix LCD mode timing */
 /* --------------------------------------------------------------------- */
-static void XGI_SetXG21CRTC(unsigned short ModeNo, unsigned short ModeIdIndex,
+static void XGI_UpdateXG21CRTC(unsigned short ModeNo, struct vb_device_info *pVBInfo,
+               unsigned short RefreshRateTableIndex)
+{
+       int i, index = -1;
+
+       XGINew_SetRegAND(pVBInfo->P3d4, 0x11, 0x7F); /* Unlock CR0~7 */
+       if (ModeNo <= 0x13) {
+               for (i = 0; i < 12; i++) {
+                       if (ModeNo == pVBInfo->UpdateCRT1[i].ModeID)
+                               index = i;
+               }
+       } else {
+               if (ModeNo == 0x2E
+                               && (pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT1CRTC
+                                               == RES640x480x60))
+                       index = 12;
+               else if (ModeNo == 0x2E
+                               && (pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT1CRTC
+                                               == RES640x480x72))
+                       index = 13;
+               else if (ModeNo == 0x2F)
+                       index = 14;
+               else if (ModeNo == 0x50)
+                       index = 15;
+               else if (ModeNo == 0x59)
+                       index = 16;
+       }
+
+       if (index != -1) {
+               XGINew_SetReg1(pVBInfo->P3d4, 0x02,
+                               pVBInfo->UpdateCRT1[index].CR02);
+               XGINew_SetReg1(pVBInfo->P3d4, 0x03,
+                               pVBInfo->UpdateCRT1[index].CR03);
+               XGINew_SetReg1(pVBInfo->P3d4, 0x15,
+                               pVBInfo->UpdateCRT1[index].CR15);
+               XGINew_SetReg1(pVBInfo->P3d4, 0x16,
+                               pVBInfo->UpdateCRT1[index].CR16);
+       }
+}
+
+static void XGI_SetCRT1DE(struct xgi_hw_device_info *HwDeviceExtension,
+               unsigned short ModeNo, unsigned short ModeIdIndex,
                unsigned short RefreshRateTableIndex,
                struct vb_device_info *pVBInfo)
 {
-       unsigned char StandTableIndex, index, Tempax, Tempbx, Tempcx, Tempdx;
-       unsigned short Temp1, Temp2, Temp3;
+       unsigned short resindex, tempax, tempbx, tempcx, temp, modeflag;
+
+       unsigned char data;
+
+       resindex = XGI_GetResInfo(ModeNo, ModeIdIndex, pVBInfo);
 
        if (ModeNo <= 0x13) {
-               StandTableIndex = XGI_GetModePtr(ModeNo, ModeIdIndex, pVBInfo);
-               Tempax = pVBInfo->StandTable[StandTableIndex].CRTC[4]; /* CR04 HRS */
-               XGINew_SetReg1(pVBInfo->P3c4, 0x2E, Tempax); /* SR2E [7:0]->HRS */
-               Tempbx = pVBInfo->StandTable[StandTableIndex].CRTC[5]; /* Tempbx: CR05 HRE */
-               Tempbx &= 0x1F; /* Tempbx: HRE[4:0] */
-               Tempcx = Tempax;
-               Tempcx &= 0xE0; /* Tempcx: HRS[7:5] */
-               Tempdx = Tempcx | Tempbx; /* Tempdx(HRE): HRS[7:5]HRE[4:0] */
-               if (Tempbx < (Tempax & 0x1F)) /* IF HRE < HRS */
-                       Tempdx |= 0x20; /* Tempdx: HRE = HRE + 0x20 */
-               Tempdx <<= 2; /* Tempdx << 2 */
-               XGINew_SetReg1(pVBInfo->P3c4, 0x2F, Tempdx); /* SR2F [7:2]->HRE */
-               XGINew_SetRegANDOR(pVBInfo->P3c4, 0x30, 0xE3, 00);
+               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag;
+               tempax = pVBInfo->StResInfo[resindex].HTotal;
+               tempbx = pVBInfo->StResInfo[resindex].VTotal;
+       } else {
+               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
+               tempax = pVBInfo->ModeResInfo[resindex].HTotal;
+               tempbx = pVBInfo->ModeResInfo[resindex].VTotal;
+       }
 
-               Tempax = pVBInfo->StandTable[StandTableIndex].CRTC[16]; /* Tempax: CR16 VRS */
-               Tempbx = Tempax; /* Tempbx=Tempax */
-               Tempax &= 0x01; /* Tempax: VRS[0] */
-               XGINew_SetRegOR(pVBInfo->P3c4, 0x33, Tempax); /* SR33[0]->VRS */
-               Tempax = pVBInfo->StandTable[StandTableIndex].CRTC[7]; /* Tempax: CR7 VRS */
-               Tempdx = Tempbx >> 1; /* Tempdx: VRS[7:1] */
-               Tempcx = Tempax & 0x04; /* Tempcx: CR7[2] */
-               Tempcx <<= 5; /* Tempcx[7]: VRS[8] */
-               Tempdx |= Tempcx; /* Tempdx: VRS[8:1] */
-               XGINew_SetReg1(pVBInfo->P3c4, 0x34, Tempdx); /* SR34[7:0]: VRS[8:1] */
+       if (modeflag & HalfDCLK)
+               tempax = tempax >> 1;
 
-               Temp1 = Tempcx << 1; /* Temp1[8]: VRS[8] unsigned char -> unsigned short */
-               Temp1 |= Tempbx; /* Temp1[8:0]: VRS[8:0] */
-               Tempax &= 0x80; /* Tempax[7]: CR7[7] */
-               Temp2 = Tempax << 2; /* Temp2[9]: VRS[9] */
-               Temp1 |= Temp2; /* Temp1[9:0]: VRS[9:0] */
+       if (ModeNo > 0x13) {
+               if (modeflag & HalfDCLK)
+                       tempax = tempax << 1;
 
-               Tempax = pVBInfo->StandTable[StandTableIndex].CRTC[17]; /* CR16 VRE */
-               Tempax &= 0x0F; /* Tempax[3:0]: VRE[3:0] */
-               Temp2 = Temp1 & 0x3F0; /* Temp2[9:4]: VRS[9:4] */
-               Temp2 |= Tempax; /* Temp2[9:0]: VRE[9:0] */
-               Temp3 = Temp1 & 0x0F; /* Temp3[3:0]: VRS[3:0] */
-               if (Tempax < Temp3) /* VRE[3:0]<VRS[3:0] */
-                       Temp2 |= 0x10; /* Temp2: VRE + 0x10 */
-               Temp2 &= 0xFF; /* Temp2[7:0]: VRE[7:0] */
-               Tempax = (unsigned char) Temp2; /* Tempax[7:0]: VRE[7:0] */
-               Tempax <<= 2; /* Tempax << 2: VRE[5:0] */
-               Temp1 &= 0x600; /* Temp1[10:9]: VRS[10:9] */
-               Temp1 >>= 9; /* [10:9]->[1:0] */
-               Tempbx = (unsigned char) Temp1; /* Tempbx[1:0]: VRS[10:9] */
-               Tempax |= Tempbx; /* VRE[5:0]VRS[10:9] */
-               Tempax &= 0x7F;
-               XGINew_SetReg1(pVBInfo->P3c4, 0x3F, Tempax); /* SR3F D[7:2]->VRE D[1:0]->VRS */
-       } else {
-               index = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT1CRTC;
-               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[3]; /* Tempax: CR4 HRS */
-               Tempcx = Tempax; /* Tempcx: HRS */
-               XGINew_SetReg1(pVBInfo->P3c4, 0x2E, Tempax); /* SR2E[7:0]->HRS */
+               temp = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_InfoFlag;
 
-               Tempdx = pVBInfo->XGINEWUB_CRT1Table[index].CR[5]; /* SRB */
-               Tempdx &= 0xC0; /* Tempdx[7:6]: SRB[7:6] */
-               Temp1 = Tempdx; /* Temp1[7:6]: HRS[9:8] */
-               Temp1 <<= 2; /* Temp1[9:8]: HRS[9:8] */
-               Temp1 |= Tempax; /* Temp1[9:0]: HRS[9:0] */
+               if (temp & InterlaceMode)
+                       tempbx = tempbx >> 1;
 
-               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[4]; /* CR5 HRE */
-               Tempax &= 0x1F; /* Tempax[4:0]: HRE[4:0] */
+               if (modeflag & DoubleScanMode)
+                       tempbx = tempbx << 1;
+       }
 
-               Tempbx = pVBInfo->XGINEWUB_CRT1Table[index].CR[6]; /* SRC */
-               Tempbx &= 0x04; /* Tempbx[2]: HRE[5] */
-               Tempbx <<= 3; /* Tempbx[5]: HRE[5] */
-               Tempax |= Tempbx; /* Tempax[5:0]: HRE[5:0] */
+       tempcx = 8;
 
-               Temp2 = Temp1 & 0x3C0; /* Temp2[9:6]: HRS[9:6] */
-               Temp2 |= Tempax; /* Temp2[9:0]: HRE[9:0] */
+       /* if (!(modeflag & Charx8Dot)) */
+       /* tempcx = 9; */
 
-               Tempcx &= 0x3F; /* Tempcx[5:0]: HRS[5:0] */
-               if (Tempax < Tempcx) /* HRE < HRS */
-                       Temp2 |= 0x40; /* Temp2 + 0x40 */
+       tempax /= tempcx;
+       tempax -= 1;
+       tempbx -= 1;
+       tempcx = tempax;
+       temp = (unsigned char) XGINew_GetReg1(pVBInfo->P3d4, 0x11);
+       data = (unsigned char) XGINew_GetReg1(pVBInfo->P3d4, 0x11);
+       data &= 0x7F;
+       XGINew_SetReg1(pVBInfo->P3d4, 0x11, data); /* Unlock CRTC */
+       XGINew_SetReg1(pVBInfo->P3d4, 0x01, (unsigned short) (tempcx & 0xff));
+       XGINew_SetRegANDOR(pVBInfo->P3d4, 0x0b, ~0x0c,
+                       (unsigned short) ((tempcx & 0x0ff00) >> 10));
+       XGINew_SetReg1(pVBInfo->P3d4, 0x12, (unsigned short) (tempbx & 0xff));
+       tempax = 0;
+       tempbx = tempbx >> 8;
 
-               Temp2 &= 0xFF;
-               Tempax = (unsigned char) Temp2; /* Tempax: HRE[7:0] */
-               Tempax <<= 2; /* Tempax[7:2]: HRE[5:0] */
-               Tempdx >>= 6; /* Tempdx[7:6]->[1:0] HRS[9:8] */
-               Tempax |= Tempdx; /* HRE[5:0]HRS[9:8] */
-               XGINew_SetReg1(pVBInfo->P3c4, 0x2F, Tempax); /* SR2F D[7:2]->HRE, D[1:0]->HRS */
-               XGINew_SetRegANDOR(pVBInfo->P3c4, 0x30, 0xE3, 00);
+       if (tempbx & 0x01)
+               tempax |= 0x02;
 
-               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[10]; /* CR10 VRS */
-               Tempbx = Tempax; /* Tempbx: VRS */
-               Tempax &= 0x01; /* Tempax[0]: VRS[0] */
-               XGINew_SetRegOR(pVBInfo->P3c4, 0x33, Tempax); /* SR33[0]->VRS[0] */
-               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[9]; /* CR7[2][7] VRE */
-               Tempcx = Tempbx >> 1; /* Tempcx[6:0]: VRS[7:1] */
-               Tempdx = Tempax & 0x04; /* Tempdx[2]: CR7[2] */
-               Tempdx <<= 5; /* Tempdx[7]: VRS[8] */
-               Tempcx |= Tempdx; /* Tempcx[7:0]: VRS[8:1] */
-               XGINew_SetReg1(pVBInfo->P3c4, 0x34, Tempcx); /* SR34[8:1]->VRS */
+       if (tempbx & 0x02)
+               tempax |= 0x40;
 
-               Temp1 = Tempdx; /* Temp1[7]: Tempdx[7] */
-               Temp1 <<= 1; /* Temp1[8]: VRS[8] */
-               Temp1 |= Tempbx; /* Temp1[8:0]: VRS[8:0] */
-               Tempax &= 0x80;
-               Temp2 = Tempax << 2; /* Temp2[9]: VRS[9] */
-               Temp1 |= Temp2; /* Temp1[9:0]: VRS[9:0] */
-               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[14]; /* Tempax: SRA */
-               Tempax &= 0x08; /* Tempax[3]: VRS[3] */
-               Temp2 = Tempax;
-               Temp2 <<= 7; /* Temp2[10]: VRS[10] */
-               Temp1 |= Temp2; /* Temp1[10:0]: VRS[10:0] */
+       XGINew_SetRegANDOR(pVBInfo->P3d4, 0x07, ~0x42, tempax);
+       data = (unsigned char) XGINew_GetReg1(pVBInfo->P3d4, 0x07);
+       data &= 0xFF;
+       tempax = 0;
 
-               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[11]; /* Tempax: CR11 VRE */
-               Tempax &= 0x0F; /* Tempax[3:0]: VRE[3:0] */
-               Tempbx = pVBInfo->XGINEWUB_CRT1Table[index].CR[14]; /* Tempbx: SRA */
-               Tempbx &= 0x20; /* Tempbx[5]: VRE[5] */
-               Tempbx >>= 1; /* Tempbx[4]: VRE[4] */
-               Tempax |= Tempbx; /* Tempax[4:0]: VRE[4:0] */
-               Temp2 = Temp1 & 0x7E0; /* Temp2[10:5]: VRS[10:5] */
-               Temp2 |= Tempax; /* Temp2[10:5]: VRE[10:5] */
+       if (tempbx & 0x04)
+               tempax |= 0x02;
 
-               Temp3 = Temp1 & 0x1F; /* Temp3[4:0]: VRS[4:0] */
-               if (Tempax < Temp3) /* VRE < VRS */
-                       Temp2 |= 0x20; /* VRE + 0x20 */
+       XGINew_SetRegANDOR(pVBInfo->P3d4, 0x0a, ~0x02, tempax);
+       XGINew_SetReg1(pVBInfo->P3d4, 0x11, temp);
+}
 
-               Temp2 &= 0xFF;
-               Tempax = (unsigned char) Temp2; /* Tempax: VRE[7:0] */
-               Tempax <<= 2; /* Tempax[7:0]; VRE[5:0]00 */
-               Temp1 &= 0x600; /* Temp1[10:9]: VRS[10:9] */
-               Temp1 >>= 9; /* Temp1[1:0]: VRS[10:9] */
-               Tempbx = (unsigned char) Temp1;
-               Tempax |= Tempbx; /* Tempax[7:0]: VRE[5:0]VRS[10:9] */
-               Tempax &= 0x7F;
-               XGINew_SetReg1(pVBInfo->P3c4, 0x3F, Tempax); /* SR3F D[7:2]->VRE D[1:0]->VRS */
-       }
+unsigned short XGI_GetResInfo(unsigned short ModeNo,
+               unsigned short ModeIdIndex, struct vb_device_info *pVBInfo)
+{
+       unsigned short resindex;
+
+       if (ModeNo <= 0x13)
+               resindex = pVBInfo->SModeIDTable[ModeIdIndex].St_ResInfo; /* si+St_ResInfo */
+       else
+               resindex = pVBInfo->EModeIDTable[ModeIdIndex].Ext_RESINFO; /* si+Ext_ResInfo */
+       return resindex;
 }
 
-static void XGI_SetXG27CRTC(unsigned short ModeNo, unsigned short ModeIdIndex,
+static void XGI_SetCRT1Offset(unsigned short ModeNo, unsigned short ModeIdIndex,
                unsigned short RefreshRateTableIndex,
+               struct xgi_hw_device_info *HwDeviceExtension,
                struct vb_device_info *pVBInfo)
 {
-       unsigned short StandTableIndex, index, Tempax, Tempbx, Tempcx, Tempdx;
-
-       if (ModeNo <= 0x13) {
-               StandTableIndex = XGI_GetModePtr(ModeNo, ModeIdIndex, pVBInfo);
-               Tempax = pVBInfo->StandTable[StandTableIndex].CRTC[4]; /* CR04 HRS */
-               XGINew_SetReg1(pVBInfo->P3c4, 0x2E, Tempax); /* SR2E [7:0]->HRS */
-               Tempbx = pVBInfo->StandTable[StandTableIndex].CRTC[5]; /* Tempbx: CR05 HRE */
-               Tempbx &= 0x1F; /* Tempbx: HRE[4:0] */
-               Tempcx = Tempax;
-               Tempcx &= 0xE0; /* Tempcx: HRS[7:5] */
-               Tempdx = Tempcx | Tempbx; /* Tempdx(HRE): HRS[7:5]HRE[4:0] */
-               if (Tempbx < (Tempax & 0x1F)) /* IF HRE < HRS */
-                       Tempdx |= 0x20; /* Tempdx: HRE = HRE + 0x20 */
-               Tempdx <<= 2; /* Tempdx << 2 */
-               XGINew_SetReg1(pVBInfo->P3c4, 0x2F, Tempdx); /* SR2F [7:2]->HRE */
-               XGINew_SetRegANDOR(pVBInfo->P3c4, 0x30, 0xE3, 00);
+       unsigned short temp, ah, al, temp2, i, DisplayUnit;
 
-               Tempax = pVBInfo->StandTable[StandTableIndex].CRTC[16]; /* Tempax: CR10 VRS */
-               XGINew_SetReg1(pVBInfo->P3c4, 0x34, Tempax); /* SR34[7:0]->VRS */
-               Tempcx = Tempax; /* Tempcx=Tempax=VRS[7:0] */
-               Tempax = pVBInfo->StandTable[StandTableIndex].CRTC[7]; /* Tempax[7][2]: CR7[7][2] VRS[9][8] */
-               Tempbx = Tempax; /* Tempbx=CR07 */
-               Tempax &= 0x04; /* Tempax[2]: CR07[2] VRS[8] */
-               Tempax >>= 2;
-               XGINew_SetRegANDOR(pVBInfo->P3c4, 0x35, ~0x01, Tempax); /* SR35 D[0]->VRS D[8] */
-               Tempcx |= (Tempax << 8); /* Tempcx[8] |= VRS[8] */
-               Tempcx |= (Tempbx & 0x80) << 2; /* Tempcx[9] |= VRS[9] */
+       /* GetOffset */
+       temp = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeInfo;
+       temp = temp >> 8;
+       temp = pVBInfo->ScreenOffset[temp];
 
-               Tempax = pVBInfo->StandTable[StandTableIndex].CRTC[17]; /* CR11 VRE */
-               Tempax &= 0x0F; /* Tempax: VRE[3:0] */
-               Tempbx = Tempcx; /* Tempbx=Tempcx=VRS[9:0] */
-               Tempbx &= 0x3F0; /* Tempbx[9:4]: VRS[9:4] */
-               Tempbx |= Tempax; /* Tempbx[9:0]: VRE[9:0] */
-               if (Tempax <= (Tempcx & 0x0F)) /* VRE[3:0]<=VRS[3:0] */
-                       Tempbx |= 0x10; /* Tempbx: VRE + 0x10 */
-               Tempax = (unsigned char) Tempbx & 0xFF; /* Tempax[7:0]: VRE[7:0] */
-               Tempax <<= 2; /* Tempax << 2: VRE[5:0] */
-               Tempcx = (Tempcx & 0x600) >> 8; /* Tempcx VRS[10:9] */
-               XGINew_SetRegANDOR(pVBInfo->P3c4, 0x3F, ~0xFC, Tempax); /* SR3F D[7:2]->VRE D[5:0] */
-               XGINew_SetRegANDOR(pVBInfo->P3c4, 0x35, ~0x06, Tempcx); /* SR35 D[2:1]->VRS[10:9] */
-       } else {
-               index = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT1CRTC;
-               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[3]; /* Tempax: CR4 HRS */
-               Tempbx = Tempax; /* Tempbx: HRS[7:0] */
-               XGINew_SetReg1(pVBInfo->P3c4, 0x2E, Tempax); /* SR2E[7:0]->HRS */
+       temp2 = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_InfoFlag;
+       temp2 &= InterlaceMode;
 
-               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[5]; /* SR0B */
-               Tempax &= 0xC0; /* Tempax[7:6]: SR0B[7:6]: HRS[9:8]*/
-               Tempbx |= (Tempax << 2); /* Tempbx: HRS[9:0] */
+       if (temp2)
+               temp = temp << 1;
 
-               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[4]; /* CR5 HRE */
-               Tempax &= 0x1F; /* Tempax[4:0]: HRE[4:0] */
-               Tempcx = Tempax; /* Tempcx: HRE[4:0] */
+       temp2 = pVBInfo->ModeType - ModeEGA;
 
-               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[6]; /* SRC */
-               Tempax &= 0x04; /* Tempax[2]: HRE[5] */
-               Tempax <<= 3; /* Tempax[5]: HRE[5] */
-               Tempcx |= Tempax; /* Tempcx[5:0]: HRE[5:0] */
+       switch (temp2) {
+       case 0:
+               temp2 = 1;
+               break;
+       case 1:
+               temp2 = 2;
+               break;
+       case 2:
+               temp2 = 4;
+               break;
+       case 3:
+               temp2 = 4;
+               break;
+       case 4:
+               temp2 = 6;
+               break;
+       case 5:
+               temp2 = 8;
+               break;
+       default:
+               break;
+       }
 
-               Tempbx = Tempbx & 0x3C0; /* Tempbx[9:6]: HRS[9:6] */
-               Tempbx |= Tempcx; /* Tempbx: HRS[9:6]HRE[5:0] */
+       if ((ModeNo >= 0x26) && (ModeNo <= 0x28))
+               temp = temp * temp2 + temp2 / 2;
+       else
+               temp *= temp2;
 
-               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[3]; /* Tempax: CR4 HRS */
-               Tempax &= 0x3F; /* Tempax: HRS[5:0] */
-               if (Tempcx <= Tempax) /* HRE[5:0] < HRS[5:0] */
-                       Tempbx += 0x40; /* Tempbx= Tempbx + 0x40 : HRE[9:0]*/
+       /* SetOffset */
+       DisplayUnit = temp;
+       temp2 = temp;
+       temp = temp >> 8; /* ah */
+       temp &= 0x0F;
+       i = XGINew_GetReg1(pVBInfo->P3c4, 0x0E);
+       i &= 0xF0;
+       i |= temp;
+       XGINew_SetReg1(pVBInfo->P3c4, 0x0E, i);
 
-               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[5]; /* SR0B */
-               Tempax &= 0xC0; /* Tempax[7:6]: SR0B[7:6]: HRS[9:8]*/
-               Tempax >>= 6; /* Tempax[1:0]: HRS[9:8]*/
-               Tempax |= ((Tempbx << 2) & 0xFF); /* Tempax[7:2]: HRE[5:0] */
-               XGINew_SetReg1(pVBInfo->P3c4, 0x2F, Tempax); /* SR2F [7:2][1:0]: HRE[5:0]HRS[9:8] */
-               XGINew_SetRegANDOR(pVBInfo->P3c4, 0x30, 0xE3, 00);
+       temp = (unsigned char) temp2;
+       temp &= 0xFF; /* al */
+       XGINew_SetReg1(pVBInfo->P3d4, 0x13, temp);
 
-               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[10]; /* CR10 VRS */
-               XGINew_SetReg1(pVBInfo->P3c4, 0x34, Tempax); /* SR34[7:0]->VRS[7:0] */
+       /* SetDisplayUnit */
+       temp2 = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_InfoFlag;
+       temp2 &= InterlaceMode;
+       if (temp2)
+               DisplayUnit >>= 1;
 
-               Tempcx = Tempax; /* Tempcx <= VRS[7:0] */
-               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[9]; /* CR7[7][2] VRS[9][8] */
-               Tempbx = Tempax; /* Tempbx <= CR07[7:0] */
-               Tempax = Tempax & 0x04; /* Tempax[2]: CR7[2]: VRS[8] */
-               Tempax >>= 2; /* Tempax[0]: VRS[8] */
-               XGINew_SetRegANDOR(pVBInfo->P3c4, 0x35, ~0x01, Tempax); /* SR35[0]: VRS[8] */
-               Tempcx |= (Tempax << 8); /* Tempcx <= VRS[8:0] */
-               Tempcx |= ((Tempbx & 0x80) << 2); /* Tempcx <= VRS[9:0] */
-               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[14]; /* Tempax: SR0A */
-               Tempax &= 0x08; /* SR0A[3] VRS[10] */
-               Tempcx |= (Tempax << 7); /* Tempcx <= VRS[10:0] */
-
-               Tempax = pVBInfo->XGINEWUB_CRT1Table[index].CR[11]; /* Tempax: CR11 VRE */
-               Tempax &= 0x0F; /* Tempax[3:0]: VRE[3:0] */
-               Tempbx = pVBInfo->XGINEWUB_CRT1Table[index].CR[14]; /* Tempbx: SR0A */
-               Tempbx &= 0x20; /* Tempbx[5]: SR0A[5]: VRE[4] */
-               Tempbx >>= 1; /* Tempbx[4]: VRE[4] */
-               Tempax |= Tempbx; /* Tempax[4:0]: VRE[4:0] */
-               Tempbx = Tempcx; /* Tempbx: VRS[10:0] */
-               Tempbx &= 0x7E0; /* Tempbx[10:5]: VRS[10:5] */
-               Tempbx |= Tempax; /* Tempbx: VRS[10:5]VRE[4:0] */
+       DisplayUnit = DisplayUnit << 5;
+       ah = (DisplayUnit & 0xff00) >> 8;
+       al = DisplayUnit & 0x00ff;
+       if (al == 0)
+               ah += 1;
+       else
+               ah += 2;
 
-               if (Tempbx <= Tempcx) /* VRE <= VRS */
-                       Tempbx |= 0x20; /* VRE + 0x20 */
+       if (HwDeviceExtension->jChipType >= XG20)
+               if ((ModeNo == 0x4A) | (ModeNo == 0x49))
+                       ah -= 1;
 
-               Tempax = (Tempbx << 2) & 0xFF; /* Tempax: Tempax[7:0]; VRE[5:0]00 */
-               XGINew_SetRegANDOR(pVBInfo->P3c4, 0x3F, ~0xFC, Tempax); /* SR3F[7:2]:VRE[5:0] */
-               Tempax = Tempcx >> 8;
-               XGINew_SetRegANDOR(pVBInfo->P3c4, 0x35, ~0x07, Tempax); /* SR35[2:0]:VRS[10:8] */
-       }
+       XGINew_SetReg1(pVBInfo->P3c4, 0x10, ah);
 }
 
-/* --------------------------------------------------------------------- */
-/* Function : XGI_SetXG21LCD */
-/* Input : */
-/* Output : FCLK duty cycle, FCLK delay compensation */
-/* Description : All values set zero */
-/* --------------------------------------------------------------------- */
-static void XGI_SetXG21LCD(struct vb_device_info *pVBInfo,
-               unsigned short RefreshRateTableIndex, unsigned short ModeNo)
+static unsigned short XGI_GetVCLK2Ptr(unsigned short ModeNo,
+               unsigned short ModeIdIndex,
+               unsigned short RefreshRateTableIndex,
+               struct xgi_hw_device_info *HwDeviceExtension,
+               struct vb_device_info *pVBInfo)
 {
-       unsigned short Data, Temp, b3CC;
-       unsigned short XGI_P3cc;
-
-       XGI_P3cc = pVBInfo->P3cc;
-
-       XGINew_SetReg1(pVBInfo->P3d4, 0x2E, 0x00);
-       XGINew_SetReg1(pVBInfo->P3d4, 0x2F, 0x00);
-       XGINew_SetReg1(pVBInfo->P3d4, 0x46, 0x00);
-       XGINew_SetReg1(pVBInfo->P3d4, 0x47, 0x00);
-       if (((*pVBInfo->pDVOSetting) & 0xC0) == 0xC0) {
-               XGINew_SetReg1(pVBInfo->P3d4, 0x2E, *pVBInfo->pCR2E);
-               XGINew_SetReg1(pVBInfo->P3d4, 0x2F, *pVBInfo->pCR2F);
-               XGINew_SetReg1(pVBInfo->P3d4, 0x46, *pVBInfo->pCR46);
-               XGINew_SetReg1(pVBInfo->P3d4, 0x47, *pVBInfo->pCR47);
-       }
-
-       Temp = XGINew_GetReg1(pVBInfo->P3d4, 0x37);
-
-       if (Temp & 0x01) {
-               XGINew_SetRegOR(pVBInfo->P3c4, 0x06, 0x40); /* 18 bits FP */
-               XGINew_SetRegOR(pVBInfo->P3c4, 0x09, 0x40);
-       }
+       unsigned short tempbx;
 
-       XGINew_SetRegOR(pVBInfo->P3c4, 0x1E, 0x01); /* Negative blank polarity */
+       unsigned short LCDXlat1VCLK[4] = { VCLK65 + 2, VCLK65 + 2, VCLK65 + 2,
+                       VCLK65 + 2 };
+       unsigned short LCDXlat2VCLK[4] = { VCLK108_2 + 5, VCLK108_2 + 5,
+                       VCLK108_2 + 5, VCLK108_2 + 5 };
+       unsigned short LVDSXlat1VCLK[4] = { VCLK40, VCLK40, VCLK40, VCLK40 };
+       unsigned short LVDSXlat2VCLK[4] = { VCLK65 + 2, VCLK65 + 2, VCLK65 + 2,
+                       VCLK65 + 2 };
+       unsigned short LVDSXlat3VCLK[4] = { VCLK65 + 2, VCLK65 + 2, VCLK65 + 2,
+                       VCLK65 + 2 };
 
-       XGINew_SetRegAND(pVBInfo->P3c4, 0x30, ~0x20);
-       XGINew_SetRegAND(pVBInfo->P3c4, 0x35, ~0x80);
+       unsigned short CRT2Index, VCLKIndex;
+       unsigned short modeflag, resinfo;
+       unsigned char *CHTVVCLKPtr = NULL;
 
        if (ModeNo <= 0x13) {
-               b3CC = (unsigned char) XGINew_GetReg2(XGI_P3cc);
-               if (b3CC & 0x40)
-                       XGINew_SetRegOR(pVBInfo->P3c4, 0x30, 0x20); /* Hsync polarity */
-               if (b3CC & 0x80)
-                       XGINew_SetRegOR(pVBInfo->P3c4, 0x35, 0x80); /* Vsync polarity */
+               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag; /* si+St_ResInfo */
+               resinfo = pVBInfo->SModeIDTable[ModeIdIndex].St_ResInfo;
+               CRT2Index = pVBInfo->SModeIDTable[ModeIdIndex].St_CRT2CRTC;
        } else {
-               Data = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_InfoFlag;
-               if (Data & 0x4000)
-                       XGINew_SetRegOR(pVBInfo->P3c4, 0x30, 0x20); /* Hsync polarity */
-               if (Data & 0x8000)
-                       XGINew_SetRegOR(pVBInfo->P3c4, 0x35, 0x80); /* Vsync polarity */
+               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag; /* si+Ext_ResInfo */
+               resinfo = pVBInfo->EModeIDTable[ModeIdIndex].Ext_RESINFO;
+               CRT2Index
+                               = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT2CRTC;
        }
-}
-
-static void XGI_SetXG27LCD(struct vb_device_info *pVBInfo,
-               unsigned short RefreshRateTableIndex, unsigned short ModeNo)
-{
-       unsigned short Data, Temp, b3CC;
-       unsigned short XGI_P3cc;
 
-       XGI_P3cc = pVBInfo->P3cc;
+       if (pVBInfo->IF_DEF_LVDS == 0) {
+               CRT2Index = CRT2Index >> 6; /*  for LCD */
+               if (pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) { /*301b*/
+                       if (pVBInfo->LCDResInfo != Panel1024x768)
+                               VCLKIndex = LCDXlat2VCLK[CRT2Index];
+                       else
+                               VCLKIndex = LCDXlat1VCLK[CRT2Index];
+               } else { /* for TV */
+                       if (pVBInfo->VBInfo & SetCRT2ToTV) {
+                               if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV) {
+                                       if (pVBInfo->SetFlag & RPLLDIV2XO) {
+                                               VCLKIndex = HiTVVCLKDIV2;
 
-       XGINew_SetReg1(pVBInfo->P3d4, 0x2E, 0x00);
-       XGINew_SetReg1(pVBInfo->P3d4, 0x2F, 0x00);
-       XGINew_SetReg1(pVBInfo->P3d4, 0x46, 0x00);
-       XGINew_SetReg1(pVBInfo->P3d4, 0x47, 0x00);
+                                               VCLKIndex += 25;
 
-       Temp = XGINew_GetReg1(pVBInfo->P3d4, 0x37);
-       if ((Temp & 0x03) == 0) { /* dual 12 */
-               XGINew_SetReg1(pVBInfo->P3d4, 0x46, 0x13);
-               XGINew_SetReg1(pVBInfo->P3d4, 0x47, 0x13);
-       }
+                                       } else {
+                                               VCLKIndex = HiTVVCLK;
 
-       if (((*pVBInfo->pDVOSetting) & 0xC0) == 0xC0) {
-               XGINew_SetReg1(pVBInfo->P3d4, 0x2E, *pVBInfo->pCR2E);
-               XGINew_SetReg1(pVBInfo->P3d4, 0x2F, *pVBInfo->pCR2F);
-               XGINew_SetReg1(pVBInfo->P3d4, 0x46, *pVBInfo->pCR46);
-               XGINew_SetReg1(pVBInfo->P3d4, 0x47, *pVBInfo->pCR47);
-       }
+                                               VCLKIndex += 25;
 
-       XGI_SetXG27FPBits(pVBInfo);
+                                       }
 
-       XGINew_SetRegOR(pVBInfo->P3c4, 0x1E, 0x01); /* Negative blank polarity */
+                                       if (pVBInfo->SetFlag & TVSimuMode) {
+                                               if (modeflag & Charx8Dot) {
+                                                       VCLKIndex
+                                                                       = HiTVSimuVCLK;
 
-       XGINew_SetRegAND(pVBInfo->P3c4, 0x30, ~0x20); /* Hsync polarity */
-       XGINew_SetRegAND(pVBInfo->P3c4, 0x35, ~0x80); /* Vsync polarity */
+                                                       VCLKIndex += 25;
 
-       if (ModeNo <= 0x13) {
-               b3CC = (unsigned char) XGINew_GetReg2(XGI_P3cc);
-               if (b3CC & 0x40)
-                       XGINew_SetRegOR(pVBInfo->P3c4, 0x30, 0x20); /* Hsync polarity */
-               if (b3CC & 0x80)
-                       XGINew_SetRegOR(pVBInfo->P3c4, 0x35, 0x80); /* Vsync polarity */
-       } else {
-               Data = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_InfoFlag;
-               if (Data & 0x4000)
-                       XGINew_SetRegOR(pVBInfo->P3c4, 0x30, 0x20); /* Hsync polarity */
-               if (Data & 0x8000)
-                       XGINew_SetRegOR(pVBInfo->P3c4, 0x35, 0x80); /* Vsync polarity */
-       }
-}
+                                               } else {
+                                                       VCLKIndex
+                                                                       = HiTVTextVCLK;
 
-/* --------------------------------------------------------------------- */
-/* Function : XGI_UpdateXG21CRTC */
-/* Input : */
-/* Output : CRT1 CRTC */
-/* Description : Modify CRT1 Hsync/Vsync to fix LCD mode timing */
-/* --------------------------------------------------------------------- */
-static void XGI_UpdateXG21CRTC(unsigned short ModeNo, struct vb_device_info *pVBInfo,
-               unsigned short RefreshRateTableIndex)
-{
-       int i, index = -1;
+                                                       VCLKIndex += 25;
 
-       XGINew_SetRegAND(pVBInfo->P3d4, 0x11, 0x7F); /* Unlock CR0~7 */
-       if (ModeNo <= 0x13) {
-               for (i = 0; i < 12; i++) {
-                       if (ModeNo == pVBInfo->UpdateCRT1[i].ModeID)
-                               index = i;
-               }
-       } else {
-               if (ModeNo == 0x2E
-                               && (pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT1CRTC
-                                               == RES640x480x60))
-                       index = 12;
-               else if (ModeNo == 0x2E
-                               && (pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT1CRTC
-                                               == RES640x480x72))
-                       index = 13;
-               else if (ModeNo == 0x2F)
-                       index = 14;
-               else if (ModeNo == 0x50)
-                       index = 15;
-               else if (ModeNo == 0x59)
-                       index = 16;
-       }
+                                               }
+                                       }
 
-       if (index != -1) {
-               XGINew_SetReg1(pVBInfo->P3d4, 0x02,
-                               pVBInfo->UpdateCRT1[index].CR02);
-               XGINew_SetReg1(pVBInfo->P3d4, 0x03,
-                               pVBInfo->UpdateCRT1[index].CR03);
-               XGINew_SetReg1(pVBInfo->P3d4, 0x15,
-                               pVBInfo->UpdateCRT1[index].CR15);
-               XGINew_SetReg1(pVBInfo->P3d4, 0x16,
-                               pVBInfo->UpdateCRT1[index].CR16);
-       }
-}
+                                       if (pVBInfo->VBType & VB_XGI301LV) { /* 301lv */
+                                               if (!(pVBInfo->VBExtInfo
+                                                               == VB_YPbPr1080i)) {
+                                                       VCLKIndex
+                                                                       = YPbPr750pVCLK;
+                                                       if (!(pVBInfo->VBExtInfo
+                                                                       == VB_YPbPr750p)) {
+                                                               VCLKIndex
+                                                                               = YPbPr525pVCLK;
+                                                               if (!(pVBInfo->VBExtInfo
+                                                                               == VB_YPbPr525p)) {
+                                                                       VCLKIndex
+                                                                                       = YPbPr525iVCLK_2;
+                                                                       if (!(pVBInfo->SetFlag
+                                                                                       & RPLLDIV2XO))
+                                                                               VCLKIndex
+                                                                                               = YPbPr525iVCLK;
+                                                               }
+                                                       }
+                                               }
+                                       }
+                               } else {
+                                       if (pVBInfo->VBInfo & SetCRT2ToTV) {
+                                               if (pVBInfo->SetFlag
+                                                               & RPLLDIV2XO) {
+                                                       VCLKIndex = TVVCLKDIV2;
 
-static void XGI_SetCRT1DE(struct xgi_hw_device_info *HwDeviceExtension,
-               unsigned short ModeNo, unsigned short ModeIdIndex,
-               unsigned short RefreshRateTableIndex,
-               struct vb_device_info *pVBInfo)
-{
-       unsigned short resindex, tempax, tempbx, tempcx, temp, modeflag;
+                                                       VCLKIndex += 25;
 
-       unsigned char data;
+                                               } else {
+                                                       VCLKIndex = TVVCLK;
 
-       resindex = XGI_GetResInfo(ModeNo, ModeIdIndex, pVBInfo);
+                                                       VCLKIndex += 25;
 
-       if (ModeNo <= 0x13) {
-               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag;
-               tempax = pVBInfo->StResInfo[resindex].HTotal;
-               tempbx = pVBInfo->StResInfo[resindex].VTotal;
-       } else {
-               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
-               tempax = pVBInfo->ModeResInfo[resindex].HTotal;
-               tempbx = pVBInfo->ModeResInfo[resindex].VTotal;
-       }
-
-       if (modeflag & HalfDCLK)
-               tempax = tempax >> 1;
-
-       if (ModeNo > 0x13) {
-               if (modeflag & HalfDCLK)
-                       tempax = tempax << 1;
-
-               temp = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_InfoFlag;
-
-               if (temp & InterlaceMode)
-                       tempbx = tempbx >> 1;
-
-               if (modeflag & DoubleScanMode)
-                       tempbx = tempbx << 1;
-       }
-
-       tempcx = 8;
-
-       /* if (!(modeflag & Charx8Dot)) */
-       /* tempcx = 9; */
-
-       tempax /= tempcx;
-       tempax -= 1;
-       tempbx -= 1;
-       tempcx = tempax;
-       temp = (unsigned char) XGINew_GetReg1(pVBInfo->P3d4, 0x11);
-       data = (unsigned char) XGINew_GetReg1(pVBInfo->P3d4, 0x11);
-       data &= 0x7F;
-       XGINew_SetReg1(pVBInfo->P3d4, 0x11, data); /* Unlock CRTC */
-       XGINew_SetReg1(pVBInfo->P3d4, 0x01, (unsigned short) (tempcx & 0xff));
-       XGINew_SetRegANDOR(pVBInfo->P3d4, 0x0b, ~0x0c,
-                       (unsigned short) ((tempcx & 0x0ff00) >> 10));
-       XGINew_SetReg1(pVBInfo->P3d4, 0x12, (unsigned short) (tempbx & 0xff));
-       tempax = 0;
-       tempbx = tempbx >> 8;
-
-       if (tempbx & 0x01)
-               tempax |= 0x02;
-
-       if (tempbx & 0x02)
-               tempax |= 0x40;
-
-       XGINew_SetRegANDOR(pVBInfo->P3d4, 0x07, ~0x42, tempax);
-       data = (unsigned char) XGINew_GetReg1(pVBInfo->P3d4, 0x07);
-       data &= 0xFF;
-       tempax = 0;
-
-       if (tempbx & 0x04)
-               tempax |= 0x02;
-
-       XGINew_SetRegANDOR(pVBInfo->P3d4, 0x0a, ~0x02, tempax);
-       XGINew_SetReg1(pVBInfo->P3d4, 0x11, temp);
-}
-
-unsigned short XGI_GetResInfo(unsigned short ModeNo,
-               unsigned short ModeIdIndex, struct vb_device_info *pVBInfo)
-{
-       unsigned short resindex;
-
-       if (ModeNo <= 0x13)
-               resindex = pVBInfo->SModeIDTable[ModeIdIndex].St_ResInfo; /* si+St_ResInfo */
-       else
-               resindex = pVBInfo->EModeIDTable[ModeIdIndex].Ext_RESINFO; /* si+Ext_ResInfo */
-       return resindex;
-}
-
-static void XGI_SetCRT1Offset(unsigned short ModeNo, unsigned short ModeIdIndex,
-               unsigned short RefreshRateTableIndex,
-               struct xgi_hw_device_info *HwDeviceExtension,
-               struct vb_device_info *pVBInfo)
-{
-       unsigned short temp, ah, al, temp2, i, DisplayUnit;
+                                               }
+                                       }
+                               }
+                       } else { /* for CRT2 */
+                               VCLKIndex = (unsigned char) XGINew_GetReg2(
+                                               (pVBInfo->P3ca + 0x02)); /* Port 3cch */
+                               VCLKIndex = ((VCLKIndex >> 2) & 0x03);
+                               if (ModeNo > 0x13) {
+                                       VCLKIndex
+                                                       = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRTVCLK; /* di+Ext_CRTVCLK */
+                                       VCLKIndex &= IndexMask;
+                               }
+                       }
+               }
+       } else { /* LVDS */
+               if (ModeNo <= 0x13)
+                       VCLKIndex = CRT2Index;
+               else
+                       VCLKIndex = CRT2Index;
 
-       /* GetOffset */
-       temp = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeInfo;
-       temp = temp >> 8;
-       temp = pVBInfo->ScreenOffset[temp];
+               if (pVBInfo->IF_DEF_CH7005 == 1) {
+                       if (!(pVBInfo->VBInfo & SetCRT2ToLCD)) {
+                               VCLKIndex &= 0x1f;
+                               tempbx = 0;
 
-       temp2 = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_InfoFlag;
-       temp2 &= InterlaceMode;
+                               if (pVBInfo->VBInfo & SetPALTV)
+                                       tempbx += 2;
 
-       if (temp2)
-               temp = temp << 1;
+                               if (pVBInfo->VBInfo & SetCHTVOverScan)
+                                       tempbx += 1;
 
-       temp2 = pVBInfo->ModeType - ModeEGA;
+                               switch (tempbx) {
+                               case 0:
+                                       CHTVVCLKPtr = pVBInfo->CHTVVCLKUNTSC;
+                                       break;
+                               case 1:
+                                       CHTVVCLKPtr = pVBInfo->CHTVVCLKONTSC;
+                                       break;
+                               case 2:
+                                       CHTVVCLKPtr = pVBInfo->CHTVVCLKUPAL;
+                                       break;
+                               case 3:
+                                       CHTVVCLKPtr = pVBInfo->CHTVVCLKOPAL;
+                                       break;
+                               default:
+                                       break;
+                               }
 
-       switch (temp2) {
-       case 0:
-               temp2 = 1;
-               break;
-       case 1:
-               temp2 = 2;
-               break;
-       case 2:
-               temp2 = 4;
-               break;
-       case 3:
-               temp2 = 4;
-               break;
-       case 4:
-               temp2 = 6;
-               break;
-       case 5:
-               temp2 = 8;
-               break;
-       default:
-               break;
+                               VCLKIndex = CHTVVCLKPtr[VCLKIndex];
+                       }
+               } else {
+                       VCLKIndex = VCLKIndex >> 6;
+                       if ((pVBInfo->LCDResInfo == Panel800x600)
+                                       || (pVBInfo->LCDResInfo == Panel320x480))
+                               VCLKIndex = LVDSXlat1VCLK[VCLKIndex];
+                       else if ((pVBInfo->LCDResInfo == Panel1024x768)
+                                       || (pVBInfo->LCDResInfo
+                                                       == Panel1024x768x75))
+                               VCLKIndex = LVDSXlat2VCLK[VCLKIndex];
+                       else
+                               VCLKIndex = LVDSXlat3VCLK[VCLKIndex];
+               }
        }
+       /* VCLKIndex = VCLKIndex&IndexMask; */
 
-       if ((ModeNo >= 0x26) && (ModeNo <= 0x28))
-               temp = temp * temp2 + temp2 / 2;
-       else
-               temp *= temp2;
-
-       /* SetOffset */
-       DisplayUnit = temp;
-       temp2 = temp;
-       temp = temp >> 8; /* ah */
-       temp &= 0x0F;
-       i = XGINew_GetReg1(pVBInfo->P3c4, 0x0E);
-       i &= 0xF0;
-       i |= temp;
-       XGINew_SetReg1(pVBInfo->P3c4, 0x0E, i);
-
-       temp = (unsigned char) temp2;
-       temp &= 0xFF; /* al */
-       XGINew_SetReg1(pVBInfo->P3d4, 0x13, temp);
-
-       /* SetDisplayUnit */
-       temp2 = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_InfoFlag;
-       temp2 &= InterlaceMode;
-       if (temp2)
-               DisplayUnit >>= 1;
-
-       DisplayUnit = DisplayUnit << 5;
-       ah = (DisplayUnit & 0xff00) >> 8;
-       al = DisplayUnit & 0x00ff;
-       if (al == 0)
-               ah += 1;
-       else
-               ah += 2;
-
-       if (HwDeviceExtension->jChipType >= XG20)
-               if ((ModeNo == 0x4A) | (ModeNo == 0x49))
-                       ah -= 1;
-
-       XGINew_SetReg1(pVBInfo->P3c4, 0x10, ah);
+       return VCLKIndex;
 }
 
 static void XGI_SetCRT1VCLK(unsigned short ModeNo, unsigned short ModeIdIndex,
@@ -1887,38 +1522,91 @@ static void XGI_SetCRT1FIFO(unsigned short ModeNo,
                XGI_SetXG21FPBits(pVBInfo); /* Fix SR9[7:6] can't read back */
 }
 
-static void XGI_SetCRT1ModeRegs(struct xgi_hw_device_info *HwDeviceExtension,
-               unsigned short ModeNo, unsigned short ModeIdIndex,
-               unsigned short RefreshRateTableIndex,
+static void XGI_SetVCLKState(struct xgi_hw_device_info *HwDeviceExtension,
+               unsigned short ModeNo, unsigned short RefreshRateTableIndex,
                struct vb_device_info *pVBInfo)
 {
-       unsigned short data, data2, data3, infoflag = 0, modeflag, resindex,
-                       xres;
+       unsigned short data, data2 = 0;
+       short VCLK;
 
-       if (ModeNo > 0x13) {
-               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
-               infoflag
-                               = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_InfoFlag;
-       } else
-               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag; /* si+St_ModeFlag */
+       unsigned char index;
 
-       if (XGINew_GetReg1(pVBInfo->P3d4, 0x31) & 0x01)
-               XGINew_SetRegANDOR(pVBInfo->P3c4, 0x1F, 0x3F, 0x00);
+       if (ModeNo <= 0x13)
+               VCLK = 0;
+       else {
+               index = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRTVCLK;
+               index &= IndexMask;
+               VCLK = pVBInfo->VCLKData[index].CLOCK;
+       }
 
-       if (ModeNo > 0x13)
-               data = infoflag;
-       else
-               data = 0;
+       data = XGINew_GetReg1(pVBInfo->P3c4, 0x32);
+       data &= 0xf3;
+       if (VCLK >= 200)
+               data |= 0x0c; /* VCLK > 200 */
 
-       data2 = 0;
+       if (HwDeviceExtension->jChipType >= XG20)
+               data &= ~0x04; /* 2 pixel mode */
 
-       if (ModeNo > 0x13) {
-               if (pVBInfo->ModeType > 0x02) {
-                       data2 |= 0x02;
-                       data3 = pVBInfo->ModeType - ModeVGA;
-                       data3 = data3 << 2;
-                       data2 |= data3;
-               }
+       XGINew_SetReg1(pVBInfo->P3c4, 0x32, data);
+
+       if (HwDeviceExtension->jChipType < XG20) {
+               data = XGINew_GetReg1(pVBInfo->P3c4, 0x1F);
+               data &= 0xE7;
+               if (VCLK < 200)
+                       data |= 0x10;
+               XGINew_SetReg1(pVBInfo->P3c4, 0x1F, data);
+       }
+
+       /*  Jong for Adavantech LCD ripple issue
+       if ((VCLK >= 0) && (VCLK < 135))
+               data2 = 0x03;
+       else if ((VCLK >= 135) && (VCLK < 160))
+               data2 = 0x02;
+       else if ((VCLK >= 160) && (VCLK < 260))
+               data2 = 0x01;
+       else if (VCLK > 260)
+               data2 = 0x00;
+       */
+       data2 = 0x00;
+
+       XGINew_SetRegANDOR(pVBInfo->P3c4, 0x07, 0xFC, data2);
+       if (HwDeviceExtension->jChipType >= XG27)
+               XGINew_SetRegANDOR(pVBInfo->P3c4, 0x40, 0xFC, data2 & 0x03);
+
+}
+
+static void XGI_SetCRT1ModeRegs(struct xgi_hw_device_info *HwDeviceExtension,
+               unsigned short ModeNo, unsigned short ModeIdIndex,
+               unsigned short RefreshRateTableIndex,
+               struct vb_device_info *pVBInfo)
+{
+       unsigned short data, data2, data3, infoflag = 0, modeflag, resindex,
+                       xres;
+
+       if (ModeNo > 0x13) {
+               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
+               infoflag
+                               = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_InfoFlag;
+       } else
+               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag; /* si+St_ModeFlag */
+
+       if (XGINew_GetReg1(pVBInfo->P3d4, 0x31) & 0x01)
+               XGINew_SetRegANDOR(pVBInfo->P3c4, 0x1F, 0x3F, 0x00);
+
+       if (ModeNo > 0x13)
+               data = infoflag;
+       else
+               data = 0;
+
+       data2 = 0;
+
+       if (ModeNo > 0x13) {
+               if (pVBInfo->ModeType > 0x02) {
+                       data2 |= 0x02;
+                       data3 = pVBInfo->ModeType - ModeVGA;
+                       data3 = data3 << 2;
+                       data2 |= data3;
+               }
        }
 
        data &= InterlaceMode;
@@ -2002,60 +1690,6 @@ static void XGI_SetCRT1ModeRegs(struct xgi_hw_device_info *HwDeviceExtension,
 
 }
 
-static void XGI_SetVCLKState(struct xgi_hw_device_info *HwDeviceExtension,
-               unsigned short ModeNo, unsigned short RefreshRateTableIndex,
-               struct vb_device_info *pVBInfo)
-{
-       unsigned short data, data2 = 0;
-       short VCLK;
-
-       unsigned char index;
-
-       if (ModeNo <= 0x13)
-               VCLK = 0;
-       else {
-               index = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRTVCLK;
-               index &= IndexMask;
-               VCLK = pVBInfo->VCLKData[index].CLOCK;
-       }
-
-       data = XGINew_GetReg1(pVBInfo->P3c4, 0x32);
-       data &= 0xf3;
-       if (VCLK >= 200)
-               data |= 0x0c; /* VCLK > 200 */
-
-       if (HwDeviceExtension->jChipType >= XG20)
-               data &= ~0x04; /* 2 pixel mode */
-
-       XGINew_SetReg1(pVBInfo->P3c4, 0x32, data);
-
-       if (HwDeviceExtension->jChipType < XG20) {
-               data = XGINew_GetReg1(pVBInfo->P3c4, 0x1F);
-               data &= 0xE7;
-               if (VCLK < 200)
-                       data |= 0x10;
-               XGINew_SetReg1(pVBInfo->P3c4, 0x1F, data);
-       }
-
-       /*  Jong for Adavantech LCD ripple issue
-       if ((VCLK >= 0) && (VCLK < 135))
-               data2 = 0x03;
-       else if ((VCLK >= 135) && (VCLK < 160))
-               data2 = 0x02;
-       else if ((VCLK >= 160) && (VCLK < 260))
-               data2 = 0x01;
-       else if (VCLK > 260)
-               data2 = 0x00;
-       */
-       data2 = 0x00;
-
-       XGINew_SetRegANDOR(pVBInfo->P3c4, 0x07, 0xFC, data2);
-       if (HwDeviceExtension->jChipType >= XG27)
-               XGINew_SetRegANDOR(pVBInfo->P3c4, 0x40, 0xFC, data2 & 0x03);
-
-}
-
-
 /*
 void XGI_VesaLowResolution(unsigned short ModeNo, unsigned short ModeIdIndex, struct vb_device_info *pVBInfo)
 {
@@ -2088,6 +1722,33 @@ void XGI_VesaLowResolution(unsigned short ModeNo, unsigned short ModeIdIndex, st
 }
 */
 
+static void XGI_WriteDAC(unsigned short dl, unsigned short ah, unsigned short al,
+               unsigned short dh, struct vb_device_info *pVBInfo)
+{
+       unsigned short temp, bh, bl;
+
+       bh = ah;
+       bl = al;
+
+       if (dl != 0) {
+               temp = bh;
+               bh = dh;
+               dh = temp;
+               if (dl == 1) {
+                       temp = bl;
+                       bl = dh;
+                       dh = temp;
+               } else {
+                       temp = bl;
+                       bl = bh;
+                       bh = temp;
+               }
+       }
+       XGINew_SetReg3(pVBInfo->P3c9, (unsigned short) dh);
+       XGINew_SetReg3(pVBInfo->P3c9, (unsigned short) bh);
+       XGINew_SetReg3(pVBInfo->P3c9, (unsigned short) bl);
+}
+
 static void XGI_LoadDAC(unsigned short ModeNo, unsigned short ModeIdIndex,
                struct vb_device_info *pVBInfo)
 {
@@ -2180,53 +1841,6 @@ static void XGI_LoadDAC(unsigned short ModeNo, unsigned short ModeIdIndex,
        }
 }
 
-static void XGI_WriteDAC(unsigned short dl, unsigned short ah, unsigned short al,
-               unsigned short dh, struct vb_device_info *pVBInfo)
-{
-       unsigned short temp, bh, bl;
-
-       bh = ah;
-       bl = al;
-
-       if (dl != 0) {
-               temp = bh;
-               bh = dh;
-               dh = temp;
-               if (dl == 1) {
-                       temp = bl;
-                       bl = dh;
-                       dh = temp;
-               } else {
-                       temp = bl;
-                       bl = bh;
-                       bh = temp;
-               }
-       }
-       XGINew_SetReg3(pVBInfo->P3c9, (unsigned short) dh);
-       XGINew_SetReg3(pVBInfo->P3c9, (unsigned short) bh);
-       XGINew_SetReg3(pVBInfo->P3c9, (unsigned short) bl);
-}
-
-static void XGI_SetLCDAGroup(unsigned short ModeNo, unsigned short ModeIdIndex,
-               struct xgi_hw_device_info *HwDeviceExtension,
-               struct vb_device_info *pVBInfo)
-{
-       unsigned short RefreshRateTableIndex;
-       /* unsigned short temp ; */
-
-       /* pVBInfo->SelectCRT2Rate = 0; */
-
-       pVBInfo->SetFlag |= ProgrammingCRT2;
-       RefreshRateTableIndex = XGI_GetRatePtrCRT2(HwDeviceExtension, ModeNo,
-                       ModeIdIndex, pVBInfo);
-       XGI_GetLVDSResInfo(ModeNo, ModeIdIndex, pVBInfo);
-       XGI_GetLVDSData(ModeNo, ModeIdIndex, RefreshRateTableIndex, pVBInfo);
-       XGI_ModCRT1Regs(ModeNo, ModeIdIndex, RefreshRateTableIndex,
-                       HwDeviceExtension, pVBInfo);
-       XGI_SetLVDSRegs(ModeNo, ModeIdIndex, RefreshRateTableIndex, pVBInfo);
-       XGI_SetCRT2ECLK(ModeNo, ModeIdIndex, RefreshRateTableIndex, pVBInfo);
-}
-
 static void XGI_GetLVDSResInfo(unsigned short ModeNo, unsigned short ModeIdIndex,
                struct vb_device_info *pVBInfo)
 {
@@ -2276,4312 +1890,4394 @@ static void XGI_GetLVDSResInfo(unsigned short ModeNo, unsigned short ModeIdIndex
        pVBInfo->VDE = yres;
 }
 
-static void XGI_GetLVDSData(unsigned short ModeNo, unsigned short ModeIdIndex,
+static void *XGI_GetLcdPtr(unsigned short BX, unsigned short ModeNo,
+               unsigned short ModeIdIndex,
                unsigned short RefreshRateTableIndex,
                struct vb_device_info *pVBInfo)
 {
-       unsigned short tempbx;
-       struct XGI330_LVDSDataStruct *LCDPtr = NULL;
-       struct XGI330_CHTVDataStruct *TVPtr = NULL;
+       unsigned short i, tempdx, tempcx, tempbx, tempal, modeflag, table;
 
-       tempbx = 2;
+       struct XGI330_LCDDataTablStruct *tempdi = NULL;
 
-       if (pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
-               LCDPtr = (struct XGI330_LVDSDataStruct *) XGI_GetLcdPtr(tempbx,
-                               ModeNo, ModeIdIndex, RefreshRateTableIndex,
-                               pVBInfo);
-               pVBInfo->VGAHT = LCDPtr->VGAHT;
-               pVBInfo->VGAVT = LCDPtr->VGAVT;
-               pVBInfo->HT = LCDPtr->LCDHT;
-               pVBInfo->VT = LCDPtr->LCDVT;
+       tempbx = BX;
+
+       if (ModeNo <= 0x13) {
+               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag;
+               tempal = pVBInfo->SModeIDTable[ModeIdIndex].St_CRT2CRTC;
+       } else {
+               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
+               tempal = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT2CRTC;
        }
-       if (pVBInfo->IF_DEF_CH7017 == 1) {
-               if (pVBInfo->VBInfo & SetCRT2ToTV) {
-                       TVPtr = (struct XGI330_CHTVDataStruct *) XGI_GetTVPtr(
-                                       tempbx, ModeNo, ModeIdIndex,
-                                       RefreshRateTableIndex, pVBInfo);
-                       pVBInfo->VGAHT = TVPtr->VGAHT;
-                       pVBInfo->VGAVT = TVPtr->VGAVT;
-                       pVBInfo->HT = TVPtr->LCDHT;
-                       pVBInfo->VT = TVPtr->LCDVT;
+
+       tempal = tempal & 0x0f;
+
+       if (tempbx <= 1) { /* ExpLink */
+               if (ModeNo <= 0x13) {
+                       tempal = pVBInfo->SModeIDTable[ModeIdIndex].St_CRT2CRTC; /* find no Ext_CRT2CRTC2 */
+               } else {
+                       tempal
+                                       = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT2CRTC;
                }
-       }
 
-       if (pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
-               if (!(pVBInfo->LCDInfo & (SetLCDtoNonExpanding
-                               | EnableScalingLCD))) {
-                       if ((pVBInfo->LCDResInfo == Panel1024x768)
-                                       || (pVBInfo->LCDResInfo
-                                                       == Panel1024x768x75)) {
-                               pVBInfo->HDE = 1024;
-                               pVBInfo->VDE = 768;
-                       } else if ((pVBInfo->LCDResInfo == Panel1280x1024)
-                                       || (pVBInfo->LCDResInfo
-                                                       == Panel1280x1024x75)) {
-                               pVBInfo->HDE = 1280;
-                               pVBInfo->VDE = 1024;
-                       } else if (pVBInfo->LCDResInfo == Panel1400x1050) {
-                               pVBInfo->HDE = 1400;
-                               pVBInfo->VDE = 1050;
-                       } else {
-                               pVBInfo->HDE = 1600;
-                               pVBInfo->VDE = 1200;
-                       }
+               if (pVBInfo->VBInfo & SetCRT2ToLCDA) {
+                       if (ModeNo <= 0x13)
+                               tempal
+                                               = pVBInfo->SModeIDTable[ModeIdIndex].St_CRT2CRTC2;
+                       else
+                               tempal
+                                               = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT2CRTC2;
                }
-       }
-}
 
-static void XGI_ModCRT1Regs(unsigned short ModeNo, unsigned short ModeIdIndex,
-               unsigned short RefreshRateTableIndex,
-               struct xgi_hw_device_info *HwDeviceExtension,
-               struct vb_device_info *pVBInfo)
-{
-       unsigned char index;
-       unsigned short tempbx, i;
-       struct XGI_LVDSCRT1HDataStruct *LCDPtr = NULL;
-       struct XGI_LVDSCRT1VDataStruct *LCDPtr1 = NULL;
-       /* struct XGI330_CHTVDataStruct *TVPtr = NULL; */
-       struct XGI_CH7007TV_TimingHStruct *CH7007TV_TimingHPtr = NULL;
-       struct XGI_CH7007TV_TimingVStruct *CH7007TV_TimingVPtr = NULL;
+               if (tempbx & 0x01)
+                       tempal = (tempal >> 4);
 
-       if (ModeNo <= 0x13)
-               index = pVBInfo->SModeIDTable[ModeIdIndex].St_CRT2CRTC;
-       else
-               index = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT2CRTC;
+               tempal = (tempal & 0x0f);
+       }
 
-       index = index & IndexMask;
+       tempcx = LCDLenList[tempbx]; /* mov cl,byte ptr cs:LCDLenList[bx] */
 
-       if ((pVBInfo->IF_DEF_ScaleLCD == 0) || ((pVBInfo->IF_DEF_ScaleLCD == 1)
-                       && (!(pVBInfo->LCDInfo & EnableScalingLCD)))) {
-               tempbx = 0;
+       if (pVBInfo->LCDInfo & EnableScalingLCD) { /* ScaleLCD */
+               if ((tempbx == 5) || (tempbx) == 7)
+                       tempcx = LCDDesDataLen2;
+               else if ((tempbx == 3) || (tempbx == 8))
+                       tempcx = LVDSDesDataLen2;
+       }
+       /* mov di, word ptr cs:LCDDataList[bx] */
+       /* tempdi = pVideoMemory[LCDDataList + tempbx * 2] | (pVideoMemory[LCDDataList + tempbx * 2 + 1] << 8); */
 
-               if (pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
-                       LCDPtr
-                                       = (struct XGI_LVDSCRT1HDataStruct *) XGI_GetLcdPtr(
-                                                       tempbx, ModeNo,
-                                                       ModeIdIndex,
-                                                       RefreshRateTableIndex,
-                                                       pVBInfo);
+       switch (tempbx) {
+       case 0:
+               tempdi = XGI_EPLLCDCRT1Ptr_H;
+               break;
+       case 1:
+               tempdi = XGI_EPLLCDCRT1Ptr_V;
+               break;
+       case 2:
+               tempdi = XGI_EPLLCDDataPtr;
+               break;
+       case 3:
+               tempdi = XGI_EPLLCDDesDataPtr;
+               break;
+       case 4:
+               tempdi = XGI_LCDDataTable;
+               break;
+       case 5:
+               tempdi = XGI_LCDDesDataTable;
+               break;
+       case 6:
+               tempdi = XGI_EPLCHLCDRegPtr;
+               break;
+       case 7:
+       case 8:
+       case 9:
+               tempdi = NULL;
+               break;
+       default:
+               break;
+       }
 
-                       for (i = 0; i < 8; i++)
-                               pVBInfo->TimingH[0].data[i] = LCDPtr[0].Reg[i];
-               }
+       if (tempdi == NULL) /* OEMUtil */
+               return NULL;
 
-               if (pVBInfo->IF_DEF_CH7007 == 1) {
-                       if (pVBInfo->VBInfo & SetCRT2ToTV) {
-                               CH7007TV_TimingHPtr
-                                               = (struct XGI_CH7007TV_TimingHStruct *) XGI_GetTVPtr(
-                                                               tempbx,
-                                                               ModeNo,
-                                                               ModeIdIndex,
-                                                               RefreshRateTableIndex,
-                                                               pVBInfo);
+       table = tempbx;
+       i = 0;
 
-                               for (i = 0; i < 8; i++)
-                                       pVBInfo->TimingH[0].data[i]
-                                                       = CH7007TV_TimingHPtr[0].data[i];
-                       }
+       while (tempdi[i].PANELID != 0xff) {
+               tempdx = pVBInfo->LCDResInfo;
+               if (tempbx & 0x0080) { /* OEMUtil */
+                       tempbx &= (~0x0080);
+                       tempdx = pVBInfo->LCDTypeInfo;
                }
 
-               /* if (pVBInfo->IF_DEF_CH7017 == 1) {
-                       if (pVBInfo->VBInfo & SetCRT2ToTV)
-                               TVPtr = (struct XGI330_CHTVDataStruct *)XGI_GetTVPtr(tempbx, ModeNo, ModeIdIndex, RefreshRateTableIndex, pVBInfo);
-               }
-               */
+               if (pVBInfo->LCDInfo & EnableScalingLCD)
+                       tempdx &= (~PanelResInfo);
 
-               XGI_SetCRT1Timing_H(pVBInfo, HwDeviceExtension);
+               if (tempdi[i].PANELID == tempdx) {
+                       tempbx = tempdi[i].MASK;
+                       tempdx = pVBInfo->LCDInfo;
 
-               if (pVBInfo->IF_DEF_CH7007 == 1) {
-                       XGINew_SetReg1(pVBInfo->P3c4, 0x2E,
-                                       CH7007TV_TimingHPtr[0].data[8]);
-                       XGINew_SetReg1(pVBInfo->P3c4, 0x2F,
-                                       CH7007TV_TimingHPtr[0].data[9]);
-               }
+                       if (ModeNo <= 0x13) /* alan 09/10/2003 */
+                               tempdx |= SetLCDStdMode;
 
-               tempbx = 1;
+                       if (modeflag & HalfDCLK)
+                               tempdx |= SetLCDLowResolution;
 
-               if (pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
-                       LCDPtr1
-                                       = (struct XGI_LVDSCRT1VDataStruct *) XGI_GetLcdPtr(
-                                                       tempbx, ModeNo,
-                                                       ModeIdIndex,
-                                                       RefreshRateTableIndex,
-                                                       pVBInfo);
-                       for (i = 0; i < 7; i++)
-                               pVBInfo->TimingV[0].data[i] = LCDPtr1[0].Reg[i];
+                       tempbx &= tempdx;
+                       if (tempbx == tempdi[i].CAP)
+                               break;
                }
+               i++;
+       }
 
-               if (pVBInfo->IF_DEF_CH7007 == 1) {
-                       if (pVBInfo->VBInfo & SetCRT2ToTV) {
-                               CH7007TV_TimingVPtr
-                                               = (struct XGI_CH7007TV_TimingVStruct *) XGI_GetTVPtr(
-                                                               tempbx,
-                                                               ModeNo,
-                                                               ModeIdIndex,
-                                                               RefreshRateTableIndex,
-                                                               pVBInfo);
-
-                               for (i = 0; i < 7; i++)
-                                       pVBInfo->TimingV[0].data[i]
-                                                       = CH7007TV_TimingVPtr[0].data[i];
-                       }
-               }
-               /* if (pVBInfo->IF_DEF_CH7017 == 1) {
-                       if (pVBInfo->VBInfo & SetCRT2ToTV)
-                               TVPtr = (struct XGI330_CHTVDataStruct *)XGI_GetTVPtr(tempbx, ModeNo, ModeIdIndex, RefreshRateTableIndex, pVBInfo);
+       if (table == 0) {
+               switch (tempdi[i].DATAPTR) {
+               case 0:
+                       return &XGI_LVDSCRT11024x768_1_H[tempal];
+                       break;
+               case 1:
+                       return &XGI_LVDSCRT11024x768_2_H[tempal];
+                       break;
+               case 2:
+                       return &XGI_LVDSCRT11280x1024_1_H[tempal];
+                       break;
+               case 3:
+                       return &XGI_LVDSCRT11280x1024_2_H[tempal];
+                       break;
+               case 4:
+                       return &XGI_LVDSCRT11400x1050_1_H[tempal];
+                       break;
+               case 5:
+                       return &XGI_LVDSCRT11400x1050_2_H[tempal];
+                       break;
+               case 6:
+                       return &XGI_LVDSCRT11600x1200_1_H[tempal];
+                       break;
+               case 7:
+                       return &XGI_LVDSCRT11024x768_1_Hx75[tempal];
+                       break;
+               case 8:
+                       return &XGI_LVDSCRT11024x768_2_Hx75[tempal];
+                       break;
+               case 9:
+                       return &XGI_LVDSCRT11280x1024_1_Hx75[tempal];
+                       break;
+               case 10:
+                       return &XGI_LVDSCRT11280x1024_2_Hx75[tempal];
+                       break;
+               default:
+                       break;
                }
-               */
-
-               XGI_SetCRT1Timing_V(ModeIdIndex, ModeNo, pVBInfo);
-
-               if (pVBInfo->IF_DEF_CH7007 == 1) {
-                       XGINew_SetRegANDOR(pVBInfo->P3c4, 0x33, ~0x01,
-                                       CH7007TV_TimingVPtr[0].data[7] & 0x01);
-                       XGINew_SetReg1(pVBInfo->P3c4, 0x34,
-                                       CH7007TV_TimingVPtr[0].data[8]);
-                       XGINew_SetReg1(pVBInfo->P3c4, 0x3F,
-                                       CH7007TV_TimingVPtr[0].data[9]);
-
+       } else if (table == 1) {
+               switch (tempdi[i].DATAPTR) {
+               case 0:
+                       return &XGI_LVDSCRT11024x768_1_V[tempal];
+                       break;
+               case 1:
+                       return &XGI_LVDSCRT11024x768_2_V[tempal];
+                       break;
+               case 2:
+                       return &XGI_LVDSCRT11280x1024_1_V[tempal];
+                       break;
+               case 3:
+                       return &XGI_LVDSCRT11280x1024_2_V[tempal];
+                       break;
+               case 4:
+                       return &XGI_LVDSCRT11400x1050_1_V[tempal];
+                       break;
+               case 5:
+                       return &XGI_LVDSCRT11400x1050_2_V[tempal];
+                       break;
+               case 6:
+                       return &XGI_LVDSCRT11600x1200_1_V[tempal];
+                       break;
+               case 7:
+                       return &XGI_LVDSCRT11024x768_1_Vx75[tempal];
+                       break;
+               case 8:
+                       return &XGI_LVDSCRT11024x768_2_Vx75[tempal];
+                       break;
+               case 9:
+                       return &XGI_LVDSCRT11280x1024_1_Vx75[tempal];
+                       break;
+               case 10:
+                       return &XGI_LVDSCRT11280x1024_2_Vx75[tempal];
+                       break;
+               default:
+                       break;
                }
-       }
-}
-
-static void XGI_SetLVDSRegs(unsigned short ModeNo, unsigned short ModeIdIndex,
-               unsigned short RefreshRateTableIndex,
-               struct vb_device_info *pVBInfo)
-{
-       unsigned short tempbx, tempax, tempcx, tempdx, push1, push2, modeflag;
-       unsigned long temp, temp1, temp2, temp3, push3;
-       struct XGI330_LCDDataDesStruct *LCDPtr = NULL;
-       struct XGI330_LCDDataDesStruct2 *LCDPtr1 = NULL;
-
-       if (ModeNo > 0x13)
-               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
-       else
-               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag;
-
-       if (!(pVBInfo->SetFlag & Win9xDOSMode)) {
-               if ((pVBInfo->IF_DEF_CH7017 == 0) || (pVBInfo->VBInfo
-                               & (SetCRT2ToLCD | SetCRT2ToLCDA))) {
-                       if (pVBInfo->IF_DEF_OEMUtil == 1) {
-                               tempbx = 8;
-                               LCDPtr
-                                               = (struct XGI330_LCDDataDesStruct *) XGI_GetLcdPtr(
-                                                               tempbx,
-                                                               ModeNo,
-                                                               ModeIdIndex,
-                                                               RefreshRateTableIndex,
-                                                               pVBInfo);
-                       }
-
-                       if ((pVBInfo->IF_DEF_OEMUtil == 0) || (LCDPtr == NULL)) {
-                               tempbx = 3;
-                               if (pVBInfo->LCDInfo & EnableScalingLCD)
-                                       LCDPtr1
-                                                       = (struct XGI330_LCDDataDesStruct2 *) XGI_GetLcdPtr(
-                                                                       tempbx,
-                                                                       ModeNo,
-                                                                       ModeIdIndex,
-                                                                       RefreshRateTableIndex,
-                                                                       pVBInfo);
-                               else
-                                       LCDPtr
-                                                       = (struct XGI330_LCDDataDesStruct *) XGI_GetLcdPtr(
-                                                                       tempbx,
-                                                                       ModeNo,
-                                                                       ModeIdIndex,
-                                                                       RefreshRateTableIndex,
-                                                                       pVBInfo);
-                       }
-
-                       XGI_GetLCDSync(&tempax, &tempbx, pVBInfo);
-                       push1 = tempbx;
-                       push2 = tempax;
-
-                       /* GetLCDResInfo */
-                       if ((pVBInfo->LCDResInfo == Panel1024x768)
-                                       || (pVBInfo->LCDResInfo
-                                                       == Panel1024x768x75)) {
-                               tempax = 1024;
-                               tempbx = 768;
-                       } else if ((pVBInfo->LCDResInfo == Panel1280x1024)
-                                       || (pVBInfo->LCDResInfo
-                                                       == Panel1280x1024x75)) {
-                               tempax = 1280;
-                               tempbx = 1024;
-                       } else if (pVBInfo->LCDResInfo == Panel1400x1050) {
-                               tempax = 1400;
-                               tempbx = 1050;
-                       } else {
-                               tempax = 1600;
-                               tempbx = 1200;
-                       }
-
-                       if (pVBInfo->LCDInfo & SetLCDtoNonExpanding) {
-                               pVBInfo->HDE = tempax;
-                               pVBInfo->VDE = tempbx;
-                               pVBInfo->VGAHDE = tempax;
-                               pVBInfo->VGAVDE = tempbx;
-                       }
-
-                       if ((pVBInfo->IF_DEF_ScaleLCD == 1)
-                                       && (pVBInfo->LCDInfo & EnableScalingLCD)) {
-                               tempax = pVBInfo->HDE;
-                               tempbx = pVBInfo->VDE;
-                       }
-
-                       tempax = pVBInfo->HT;
-
-                       if (pVBInfo->LCDInfo & EnableScalingLCD)
-                               tempbx = LCDPtr1->LCDHDES;
+       } else if (table == 2) {
+               switch (tempdi[i].DATAPTR) {
+               case 0:
+                       return &XGI_LVDS1024x768Data_1[tempal];
+                       break;
+               case 1:
+                       return &XGI_LVDS1024x768Data_2[tempal];
+                       break;
+               case 2:
+                       return &XGI_LVDS1280x1024Data_1[tempal];
+                       break;
+               case 3:
+                       return &XGI_LVDS1280x1024Data_2[tempal];
+                       break;
+               case 4:
+                       return &XGI_LVDS1400x1050Data_1[tempal];
+                       break;
+               case 5:
+                       return &XGI_LVDS1400x1050Data_2[tempal];
+                       break;
+               case 6:
+                       return &XGI_LVDS1600x1200Data_1[tempal];
+                       break;
+               case 7:
+                       return &XGI_LVDSNoScalingData[tempal];
+                       break;
+               case 8:
+                       return &XGI_LVDS1024x768Data_1x75[tempal];
+                       break;
+               case 9:
+                       return &XGI_LVDS1024x768Data_2x75[tempal];
+                       break;
+               case 10:
+                       return &XGI_LVDS1280x1024Data_1x75[tempal];
+                       break;
+               case 11:
+                       return &XGI_LVDS1280x1024Data_2x75[tempal];
+                       break;
+               case 12:
+                       return &XGI_LVDSNoScalingDatax75[tempal];
+                       break;
+               default:
+                       break;
+               }
+       } else if (table == 3) {
+               switch (tempdi[i].DATAPTR) {
+               case 0:
+                       return &XGI_LVDS1024x768Des_1[tempal];
+                       break;
+               case 1:
+                       return &XGI_LVDS1024x768Des_3[tempal];
+                       break;
+               case 2:
+                       return &XGI_LVDS1024x768Des_2[tempal];
+                       break;
+               case 3:
+                       return &XGI_LVDS1280x1024Des_1[tempal];
+                       break;
+               case 4:
+                       return &XGI_LVDS1280x1024Des_2[tempal];
+                       break;
+               case 5:
+                       return &XGI_LVDS1400x1050Des_1[tempal];
+                       break;
+               case 6:
+                       return &XGI_LVDS1400x1050Des_2[tempal];
+                       break;
+               case 7:
+                       return &XGI_LVDS1600x1200Des_1[tempal];
+                       break;
+               case 8:
+                       return &XGI_LVDSNoScalingDesData[tempal];
+                       break;
+               case 9:
+                       return &XGI_LVDS1024x768Des_1x75[tempal];
+                       break;
+               case 10:
+                       return &XGI_LVDS1024x768Des_3x75[tempal];
+                       break;
+               case 11:
+                       return &XGI_LVDS1024x768Des_2x75[tempal];
+                       break;
+               case 12:
+                       return &XGI_LVDS1280x1024Des_1x75[tempal];
+                       break;
+               case 13:
+                       return &XGI_LVDS1280x1024Des_2x75[tempal];
+                       break;
+               case 14:
+                       return &XGI_LVDSNoScalingDesDatax75[tempal];
+                       break;
+               default:
+                       break;
+               }
+       } else if (table == 4) {
+               switch (tempdi[i].DATAPTR) {
+               case 0:
+                       return &XGI_ExtLCD1024x768Data[tempal];
+                       break;
+               case 1:
+                       return &XGI_StLCD1024x768Data[tempal];
+                       break;
+               case 2:
+                       return &XGI_CetLCD1024x768Data[tempal];
+                       break;
+               case 3:
+                       return &XGI_ExtLCD1280x1024Data[tempal];
+                       break;
+               case 4:
+                       return &XGI_StLCD1280x1024Data[tempal];
+                       break;
+               case 5:
+                       return &XGI_CetLCD1280x1024Data[tempal];
+                       break;
+               case 6:
+                       return &XGI_ExtLCD1400x1050Data[tempal];
+                       break;
+               case 7:
+                       return &XGI_StLCD1400x1050Data[tempal];
+                       break;
+               case 8:
+                       return &XGI_CetLCD1400x1050Data[tempal];
+                       break;
+               case 9:
+                       return &XGI_ExtLCD1600x1200Data[tempal];
+                       break;
+               case 10:
+                       return &XGI_StLCD1600x1200Data[tempal];
+                       break;
+               case 11:
+                       return &XGI_NoScalingData[tempal];
+                       break;
+               case 12:
+                       return &XGI_ExtLCD1024x768x75Data[tempal];
+                       break;
+               case 13:
+                       return &XGI_ExtLCD1024x768x75Data[tempal];
+                       break;
+               case 14:
+                       return &XGI_CetLCD1024x768x75Data[tempal];
+                       break;
+               case 15:
+                       return &XGI_ExtLCD1280x1024x75Data[tempal];
+                       break;
+               case 16:
+                       return &XGI_StLCD1280x1024x75Data[tempal];
+                       break;
+               case 17:
+                       return &XGI_CetLCD1280x1024x75Data[tempal];
+                       break;
+               case 18:
+                       return &XGI_NoScalingDatax75[tempal];
+                       break;
+               default:
+                       break;
+               }
+       } else if (table == 5) {
+               switch (tempdi[i].DATAPTR) {
+               case 0:
+                       return &XGI_ExtLCDDes1024x768Data[tempal];
+                       break;
+               case 1:
+                       return &XGI_StLCDDes1024x768Data[tempal];
+                       break;
+               case 2:
+                       return &XGI_CetLCDDes1024x768Data[tempal];
+                       break;
+               case 3:
+                       if ((pVBInfo->VBType & VB_XGI301LV) || (pVBInfo->VBType
+                                       & VB_XGI302LV))
+                               return &XGI_ExtLCDDLDes1280x1024Data[tempal];
                        else
-                               tempbx = LCDPtr->LCDHDES;
-
-                       tempcx = pVBInfo->HDE;
-                       tempbx = tempbx & 0x0fff;
-                       tempcx += tempbx;
-
-                       if (tempcx >= tempax)
-                               tempcx -= tempax;
-
-                       XGINew_SetReg1(pVBInfo->Part1Port, 0x1A, tempbx & 0x07);
-
-                       tempcx = tempcx >> 3;
-                       tempbx = tempbx >> 3;
-
-                       XGINew_SetReg1(pVBInfo->Part1Port, 0x16,
-                                       (unsigned short) (tempbx & 0xff));
-                       XGINew_SetReg1(pVBInfo->Part1Port, 0x17,
-                                       (unsigned short) (tempcx & 0xff));
-
-                       tempax = pVBInfo->HT;
-
-                       if (pVBInfo->LCDInfo & EnableScalingLCD)
-                               tempbx = LCDPtr1->LCDHRS;
+                               return &XGI_ExtLCDDes1280x1024Data[tempal];
+                       break;
+               case 4:
+                       if ((pVBInfo->VBType & VB_XGI301LV) || (pVBInfo->VBType
+                                       & VB_XGI302LV))
+                               return &XGI_StLCDDLDes1280x1024Data[tempal];
                        else
-                               tempbx = LCDPtr->LCDHRS;
-
-                       tempcx = push2;
-
-                       if (pVBInfo->LCDInfo & EnableScalingLCD)
-                               tempcx = LCDPtr1->LCDHSync;
-
-                       tempcx += tempbx;
-
-                       if (tempcx >= tempax)
-                               tempcx -= tempax;
-
-                       tempax = tempbx & 0x07;
-                       tempax = tempax >> 5;
-                       tempcx = tempcx >> 3;
-                       tempbx = tempbx >> 3;
-
-                       tempcx &= 0x1f;
-                       tempax |= tempcx;
-
-                       XGINew_SetReg1(pVBInfo->Part1Port, 0x15, tempax);
-                       XGINew_SetReg1(pVBInfo->Part1Port, 0x14,
-                                       (unsigned short) (tempbx & 0xff));
-
-                       tempax = pVBInfo->VT;
-                       if (pVBInfo->LCDInfo & EnableScalingLCD)
-                               tempbx = LCDPtr1->LCDVDES;
+                               return &XGI_StLCDDes1280x1024Data[tempal];
+                       break;
+               case 5:
+                       if ((pVBInfo->VBType & VB_XGI301LV) || (pVBInfo->VBType
+                                       & VB_XGI302LV))
+                               return &XGI_CetLCDDLDes1280x1024Data[tempal];
+                       else
+                               return &XGI_CetLCDDes1280x1024Data[tempal];
+                       break;
+               case 6:
+                       if ((pVBInfo->VBType & VB_XGI301LV) || (pVBInfo->VBType
+                                       & VB_XGI302LV))
+                               return &XGI_ExtLCDDLDes1400x1050Data[tempal];
+                       else
+                               return &XGI_ExtLCDDes1400x1050Data[tempal];
+                       break;
+               case 7:
+                       if ((pVBInfo->VBType & VB_XGI301LV) || (pVBInfo->VBType
+                                       & VB_XGI302LV))
+                               return &XGI_StLCDDLDes1400x1050Data[tempal];
+                       else
+                               return &XGI_StLCDDes1400x1050Data[tempal];
+                       break;
+               case 8:
+                       return &XGI_CetLCDDes1400x1050Data[tempal];
+                       break;
+               case 9:
+                       return &XGI_CetLCDDes1400x1050Data2[tempal];
+                       break;
+               case 10:
+                       if ((pVBInfo->VBType & VB_XGI301LV) || (pVBInfo->VBType
+                                       & VB_XGI302LV))
+                               return &XGI_ExtLCDDLDes1600x1200Data[tempal];
+                       else
+                               return &XGI_ExtLCDDes1600x1200Data[tempal];
+                       break;
+               case 11:
+                       if ((pVBInfo->VBType & VB_XGI301LV) || (pVBInfo->VBType
+                                       & VB_XGI302LV))
+                               return &XGI_StLCDDLDes1600x1200Data[tempal];
+                       else
+                               return &XGI_StLCDDes1600x1200Data[tempal];
+                       break;
+               case 12:
+                       return &XGI_NoScalingDesData[tempal];
+                       break;
+               case 13:
+                       return &XGI_ExtLCDDes1024x768x75Data[tempal];
+                       break;
+               case 14:
+                       return &XGI_StLCDDes1024x768x75Data[tempal];
+                       break;
+               case 15:
+                       return &XGI_CetLCDDes1024x768x75Data[tempal];
+                       break;
+               case 16:
+                       if ((pVBInfo->VBType & VB_XGI301LV) || (pVBInfo->VBType
+                                       & VB_XGI302LV))
+                               return &XGI_ExtLCDDLDes1280x1024x75Data[tempal];
                        else
-                               tempbx = LCDPtr->LCDVDES;
-                       tempcx = pVBInfo->VDE;
-
-                       tempbx = tempbx & 0x0fff;
-                       tempcx += tempbx;
-                       if (tempcx >= tempax)
-                               tempcx -= tempax;
-
-                       XGINew_SetReg1(pVBInfo->Part1Port, 0x1b,
-                                       (unsigned short) (tempbx & 0xff));
-                       XGINew_SetReg1(pVBInfo->Part1Port, 0x1c,
-                                       (unsigned short) (tempcx & 0xff));
-
-                       tempbx = (tempbx >> 8) & 0x07;
-                       tempcx = (tempcx >> 8) & 0x07;
-
-                       XGINew_SetReg1(pVBInfo->Part1Port, 0x1d,
-                                       (unsigned short) ((tempcx << 3)
-                                                       | tempbx));
-
-                       tempax = pVBInfo->VT;
-                       if (pVBInfo->LCDInfo & EnableScalingLCD)
-                               tempbx = LCDPtr1->LCDVRS;
+                               return &XGI_ExtLCDDes1280x1024x75Data[tempal];
+                       break;
+               case 17:
+                       if ((pVBInfo->VBType & VB_XGI301LV) || (pVBInfo->VBType
+                                       & VB_XGI302LV))
+                               return &XGI_StLCDDLDes1280x1024x75Data[tempal];
                        else
-                               tempbx = LCDPtr->LCDVRS;
-
-                       /* tempbx = tempbx >> 4; */
-                       tempcx = push1;
-
-                       if (pVBInfo->LCDInfo & EnableScalingLCD)
-                               tempcx = LCDPtr1->LCDVSync;
-
-                       tempcx += tempbx;
-                       if (tempcx >= tempax)
-                               tempcx -= tempax;
-
-                       XGINew_SetReg1(pVBInfo->Part1Port, 0x18,
-                                       (unsigned short) (tempbx & 0xff));
-                       XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x19, ~0x0f,
-                                       (unsigned short) (tempcx & 0x0f));
-
-                       tempax = ((tempbx >> 8) & 0x07) << 3;
-
-                       tempbx = pVBInfo->VGAVDE;
-                       if (tempbx != pVBInfo->VDE)
-                               tempax |= 0x40;
-
-                       if (pVBInfo->LCDInfo & EnableLVDSDDA)
-                               tempax |= 0x40;
-
-                       XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x1a, 0x07,
-                                       tempax);
-
-                       tempcx = pVBInfo->VGAVT;
-                       tempbx = pVBInfo->VDE;
-                       tempax = pVBInfo->VGAVDE;
-                       tempcx -= tempax;
-
-                       temp = tempax; /* 0430 ylshieh */
-                       temp1 = (temp << 18) / tempbx;
-
-                       tempdx = (unsigned short) ((temp << 18) % tempbx);
-
-                       if (tempdx != 0)
-                               temp1 += 1;
-
-                       temp2 = temp1;
-                       push3 = temp2;
-
-                       XGINew_SetReg1(pVBInfo->Part1Port, 0x37,
-                                       (unsigned short) (temp2 & 0xff));
-                       XGINew_SetReg1(pVBInfo->Part1Port, 0x36,
-                                       (unsigned short) ((temp2 >> 8) & 0xff));
-
-                       tempbx = (unsigned short) (temp2 >> 16);
-                       tempax = tempbx & 0x03;
-
-                       tempbx = pVBInfo->VGAVDE;
-                       if (tempbx == pVBInfo->VDE)
-                               tempax |= 0x04;
-
-                       XGINew_SetReg1(pVBInfo->Part1Port, 0x35, tempax);
-
-                       if (pVBInfo->VBType & VB_XGI301C) {
-                               temp2 = push3;
-                               XGINew_SetReg1(pVBInfo->Part4Port, 0x3c,
-                                               (unsigned short) (temp2 & 0xff));
-                               XGINew_SetReg1(pVBInfo->Part4Port, 0x3b,
-                                               (unsigned short) ((temp2 >> 8)
-                                                               & 0xff));
-                               tempbx = (unsigned short) (temp2 >> 16);
-                               XGINew_SetRegANDOR(pVBInfo->Part4Port, 0x3a,
-                                               ~0xc0,
-                                               (unsigned short) ((tempbx
-                                                               & 0xff) << 6));
-
-                               tempcx = pVBInfo->VGAVDE;
-                               if (tempcx == pVBInfo->VDE)
-                                       XGINew_SetRegANDOR(pVBInfo->Part4Port,
-                                                       0x30, ~0x0c, 0x00);
-                               else
-                                       XGINew_SetRegANDOR(pVBInfo->Part4Port,
-                                                       0x30, ~0x0c, 0x08);
-                       }
-
-                       tempcx = pVBInfo->VGAHDE;
-                       tempbx = pVBInfo->HDE;
-
-                       temp1 = tempcx << 16;
-
-                       tempax = (unsigned short) (temp1 / tempbx);
-
-                       if ((tempbx & 0xffff) == (tempcx & 0xffff))
-                               tempax = 65535;
-
-                       temp3 = tempax;
-                       temp1 = pVBInfo->VGAHDE << 16;
-
-                       temp1 /= temp3;
-                       temp3 = temp3 << 16;
-                       temp1 -= 1;
-
-                       temp3 = (temp3 & 0xffff0000) + (temp1 & 0xffff);
-
-                       tempax = (unsigned short) (temp3 & 0xff);
-                       XGINew_SetReg1(pVBInfo->Part1Port, 0x1f, tempax);
-
-                       temp1 = pVBInfo->VGAVDE << 18;
-                       temp1 = temp1 / push3;
-                       tempbx = (unsigned short) (temp1 & 0xffff);
-
-                       if (pVBInfo->LCDResInfo == Panel1024x768)
-                               tempbx -= 1;
-
-                       tempax = ((tempbx >> 8) & 0xff) << 3;
-                       tempax |= (unsigned short) ((temp3 >> 8) & 0x07);
-                       XGINew_SetReg1(pVBInfo->Part1Port, 0x20,
-                                       (unsigned short) (tempax & 0xff));
-                       XGINew_SetReg1(pVBInfo->Part1Port, 0x21,
-                                       (unsigned short) (tempbx & 0xff));
-
-                       temp3 = temp3 >> 16;
-
-                       if (modeflag & HalfDCLK)
-                               temp3 = temp3 >> 1;
-
-                       XGINew_SetReg1(pVBInfo->Part1Port, 0x22,
-                                       (unsigned short) ((temp3 >> 8) & 0xff));
-                       XGINew_SetReg1(pVBInfo->Part1Port, 0x23,
-                                       (unsigned short) (temp3 & 0xff));
+                               return &XGI_StLCDDes1280x1024x75Data[tempal];
+                       break;
+               case 18:
+                       if ((pVBInfo->VBType & VB_XGI301LV) || (pVBInfo->VBType
+                                       & VB_XGI302LV))
+                               return &XGI_CetLCDDLDes1280x1024x75Data[tempal];
+                       else
+                               return &XGI_CetLCDDes1280x1024x75Data[tempal];
+                       break;
+               case 19:
+                       return &XGI_NoScalingDesDatax75[tempal];
+                       break;
+               default:
+                       break;
                }
-       }
-}
-
-static void XGI_SetCRT2ECLK(unsigned short ModeNo, unsigned short ModeIdIndex,
-               unsigned short RefreshRateTableIndex,
-               struct vb_device_info *pVBInfo)
-{
-       unsigned char di_0, di_1, tempal;
-       int i;
-
-       tempal = XGI_GetVCLKPtr(RefreshRateTableIndex, ModeNo, ModeIdIndex,
-                       pVBInfo);
-       XGI_GetVCLKLen(tempal, &di_0, &di_1, pVBInfo);
-       XGI_GetLCDVCLKPtr(&di_0, &di_1, pVBInfo);
-
-       for (i = 0; i < 4; i++) {
-               XGINew_SetRegANDOR(pVBInfo->P3d4, 0x31, ~0x30,
-                               (unsigned short) (0x10 * i));
-               if (pVBInfo->IF_DEF_CH7007 == 1) {
-                       XGINew_SetReg1(pVBInfo->P3c4, 0x2b, di_0);
-                       XGINew_SetReg1(pVBInfo->P3c4, 0x2c, di_1);
-               } else if ((!(pVBInfo->VBInfo & SetCRT2ToLCDA))
-                               && (!(pVBInfo->VBInfo & SetInSlaveMode))) {
-                       XGINew_SetReg1(pVBInfo->P3c4, 0x2e, di_0);
-                       XGINew_SetReg1(pVBInfo->P3c4, 0x2f, di_1);
-               } else {
-                       XGINew_SetReg1(pVBInfo->P3c4, 0x2b, di_0);
-                       XGINew_SetReg1(pVBInfo->P3c4, 0x2c, di_1);
+       } else if (table == 6) {
+               switch (tempdi[i].DATAPTR) {
+               case 0:
+                       return &XGI_CH7017LV1024x768[tempal];
+                       break;
+               case 1:
+                       return &XGI_CH7017LV1400x1050[tempal];
+                       break;
+               default:
+                       break;
                }
        }
+       return NULL;
 }
 
-static void XGI_UpdateModeInfo(struct xgi_hw_device_info *HwDeviceExtension,
+static void *XGI_GetTVPtr(unsigned short BX, unsigned short ModeNo,
+               unsigned short ModeIdIndex,
+               unsigned short RefreshRateTableIndex,
                struct vb_device_info *pVBInfo)
 {
-       unsigned short tempcl, tempch, temp, tempbl, tempax;
-
-       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
-                       | VB_XGI302LV | VB_XGI301C)) {
-               tempcl = 0;
-               tempch = 0;
-               temp = XGINew_GetReg1(pVBInfo->P3c4, 0x01);
-
-               if (!(temp & 0x20)) {
-                       temp = XGINew_GetReg1(pVBInfo->P3d4, 0x17);
-                       if (temp & 0x80) {
-                               if ((HwDeviceExtension->jChipType >= XG20)
-                                               || (HwDeviceExtension->jChipType
-                                                               >= XG40))
-                                       temp = XGINew_GetReg1(pVBInfo->P3d4,
-                                                       0x53);
-                               else
-                                       temp = XGINew_GetReg1(pVBInfo->P3d4,
-                                                       0x63);
-
-                               if (!(temp & 0x40))
-                                       tempcl |= ActiveCRT1;
-                       }
-               }
+       unsigned short i, tempdx, tempbx, tempal, modeflag, table;
+       struct XGI330_TVDataTablStruct *tempdi = NULL;
 
-               temp = XGINew_GetReg1(pVBInfo->Part1Port, 0x2e);
-               temp &= 0x0f;
+       tempbx = BX;
 
-               if (!(temp == 0x08)) {
-                       tempax = XGINew_GetReg1(pVBInfo->Part1Port, 0x13); /* Check ChannelA by Part1_13 [2003/10/03] */
-                       if (tempax & 0x04)
-                               tempcl = tempcl | ActiveLCD;
+       if (ModeNo <= 0x13) {
+               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag;
+               tempal = pVBInfo->SModeIDTable[ModeIdIndex].St_CRT2CRTC;
+       } else {
+               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
+               tempal = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT2CRTC;
+       }
 
-                       temp &= 0x05;
+       tempal = tempal & 0x3f;
+       table = tempbx;
 
-                       if (!(tempcl & ActiveLCD))
-                               if (temp == 0x01)
-                                       tempcl |= ActiveCRT2;
+       switch (tempbx) {
+       case 0:
+               tempdi = NULL; /*EPLCHTVCRT1Ptr_H;*/
+               if (pVBInfo->IF_DEF_CH7007 == 1)
+                       tempdi = XGI_EPLCHTVCRT1Ptr;
 
-                       if (temp == 0x04)
-                               tempcl |= ActiveLCD;
+               break;
+       case 1:
+               tempdi = NULL; /*EPLCHTVCRT1Ptr_V;*/
+               if (pVBInfo->IF_DEF_CH7007 == 1)
+                       tempdi = XGI_EPLCHTVCRT1Ptr;
 
-                       if (temp == 0x05) {
-                               temp = XGINew_GetReg1(pVBInfo->Part2Port, 0x00);
+               break;
+       case 2:
+               tempdi = XGI_EPLCHTVDataPtr;
+               break;
+       case 3:
+               tempdi = NULL;
+               break;
+       case 4:
+               tempdi = XGI_TVDataTable;
+               break;
+       case 5:
+               tempdi = NULL;
+               break;
+       case 6:
+               tempdi = XGI_EPLCHTVRegPtr;
+               break;
+       default:
+               break;
+       }
 
-                               if (!(temp & 0x08))
-                                       tempch |= ActiveAVideo;
+       if (tempdi == NULL) /* OEMUtil */
+               return NULL;
 
-                               if (!(temp & 0x04))
-                                       tempch |= ActiveSVideo;
+       tempdx = pVBInfo->TVInfo;
 
-                               if (temp & 0x02)
-                                       tempch |= ActiveSCART;
+       if (pVBInfo->VBInfo & SetInSlaveMode)
+               tempdx = tempdx | SetTVLockMode;
 
-                               if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV) {
-                                       if (temp & 0x01)
-                                               tempch |= ActiveHiTV;
-                               }
+       if (modeflag & HalfDCLK)
+               tempdx = tempdx | SetTVLowResolution;
 
-                               if (pVBInfo->VBInfo & SetCRT2ToYPbPr) {
-                                       temp = XGINew_GetReg1(
-                                                       pVBInfo->Part2Port,
-                                                       0x4d);
+       i = 0;
 
-                                       if (temp & 0x10)
-                                               tempch |= ActiveYPbPr;
-                               }
+       while (tempdi[i].MASK != 0xffff) {
+               if ((tempdx & tempdi[i].MASK) == tempdi[i].CAP)
+                       break;
+               i++;
+       }
 
-                               if (tempch != 0)
-                                       tempcl |= ActiveTV;
-                       }
+       if (table == 0x00) { /* 07/05/22 */
+       } else if (table == 0x01) {
+       } else if (table == 0x04) {
+               switch (tempdi[i].DATAPTR) {
+               case 0:
+                       return &XGI_ExtPALData[tempal];
+                       break;
+               case 1:
+                       return &XGI_ExtNTSCData[tempal];
+                       break;
+               case 2:
+                       return &XGI_StPALData[tempal];
+                       break;
+               case 3:
+                       return &XGI_StNTSCData[tempal];
+                       break;
+               case 4:
+                       return &XGI_ExtHiTVData[tempal];
+                       break;
+               case 5:
+                       return &XGI_St2HiTVData[tempal];
+                       break;
+               case 6:
+                       return &XGI_ExtYPbPr525iData[tempal];
+                       break;
+               case 7:
+                       return &XGI_ExtYPbPr525pData[tempal];
+                       break;
+               case 8:
+                       return &XGI_ExtYPbPr750pData[tempal];
+                       break;
+               case 9:
+                       return &XGI_StYPbPr525iData[tempal];
+                       break;
+               case 10:
+                       return &XGI_StYPbPr525pData[tempal];
+                       break;
+               case 11:
+                       return &XGI_StYPbPr750pData[tempal];
+                       break;
+               case 12: /* avoid system hang */
+                       return &XGI_ExtNTSCData[tempal];
+                       break;
+               case 13:
+                       return &XGI_St1HiTVData[tempal];
+                       break;
+               default:
+                       break;
                }
-
-               temp = XGINew_GetReg1(pVBInfo->P3d4, 0x3d);
-               if (tempcl & ActiveLCD) {
-                       if ((pVBInfo->SetFlag & ReserveTVOption)) {
-                               if (temp & ActiveTV)
-                                       tempcl |= ActiveTV;
-                       }
+       } else if (table == 0x02) {
+               switch (tempdi[i].DATAPTR) {
+               case 0:
+                       return &XGI_CHTVUNTSCData[tempal];
+                       break;
+               case 1:
+                       return &XGI_CHTVONTSCData[tempal];
+                       break;
+               case 2:
+                       return &XGI_CHTVUPALData[tempal];
+                       break;
+               case 3:
+                       return &XGI_CHTVOPALData[tempal];
+                       break;
+               default:
+                       break;
                }
-               temp = tempcl;
-               tempbl = ~ModeSwitchStatus;
-               XGINew_SetRegANDOR(pVBInfo->P3d4, 0x3d, tempbl, temp);
-
-               if (!(pVBInfo->SetFlag & ReserveTVOption))
-                       XGINew_SetReg1(pVBInfo->P3d4, 0x3e, tempch);
-       } else {
-               return;
+       } else if (table == 0x06) {
        }
+       return NULL;
 }
 
-void XGI_GetVGAType(struct xgi_hw_device_info *HwDeviceExtension,
+static void XGI_GetLVDSData(unsigned short ModeNo, unsigned short ModeIdIndex,
+               unsigned short RefreshRateTableIndex,
                struct vb_device_info *pVBInfo)
 {
-       /*
-       if ( HwDeviceExtension->jChipType >= XG20 ) {
-               pVBInfo->Set_VGAType = XG20;
-       } else if (HwDeviceExtension->jChipType >= XG40) {
-               pVBInfo->Set_VGAType = VGA_XGI340;
-       }
-       */
-       pVBInfo->Set_VGAType = HwDeviceExtension->jChipType;
-}
+       unsigned short tempbx;
+       struct XGI330_LVDSDataStruct *LCDPtr = NULL;
+       struct XGI330_CHTVDataStruct *TVPtr = NULL;
 
-void XGI_GetVBType(struct vb_device_info *pVBInfo)
-{
-       unsigned short flag, tempbx, tempah;
+       tempbx = 2;
 
-       if (pVBInfo->IF_DEF_CH7007 == 1) {
-               pVBInfo->VBType = VB_CH7007;
-               return;
+       if (pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
+               LCDPtr = (struct XGI330_LVDSDataStruct *) XGI_GetLcdPtr(tempbx,
+                               ModeNo, ModeIdIndex, RefreshRateTableIndex,
+                               pVBInfo);
+               pVBInfo->VGAHT = LCDPtr->VGAHT;
+               pVBInfo->VGAVT = LCDPtr->VGAVT;
+               pVBInfo->HT = LCDPtr->LCDHT;
+               pVBInfo->VT = LCDPtr->LCDVT;
+       }
+       if (pVBInfo->IF_DEF_CH7017 == 1) {
+               if (pVBInfo->VBInfo & SetCRT2ToTV) {
+                       TVPtr = (struct XGI330_CHTVDataStruct *) XGI_GetTVPtr(
+                                       tempbx, ModeNo, ModeIdIndex,
+                                       RefreshRateTableIndex, pVBInfo);
+                       pVBInfo->VGAHT = TVPtr->VGAHT;
+                       pVBInfo->VGAVT = TVPtr->VGAVT;
+                       pVBInfo->HT = TVPtr->LCDHT;
+                       pVBInfo->VT = TVPtr->LCDVT;
+               }
        }
-       if (pVBInfo->IF_DEF_LVDS == 0) {
-               tempbx = VB_XGI302B;
-               flag = XGINew_GetReg1(pVBInfo->Part4Port, 0x00);
-               if (flag != 0x02) {
-                       tempbx = VB_XGI301;
-                       flag = XGINew_GetReg1(pVBInfo->Part4Port, 0x01);
-                       if (flag >= 0xB0) {
-                               tempbx = VB_XGI301B;
-                               if (flag >= 0xC0) {
-                                       tempbx = VB_XGI301C;
-                                       if (flag >= 0xD0) {
-                                               tempbx = VB_XGI301LV;
-                                               if (flag >= 0xE0) {
-                                                       tempbx = VB_XGI302LV;
-                                                       tempah
-                                                                       = XGINew_GetReg1(
-                                                                                       pVBInfo->Part4Port,
-                                                                                       0x39);
-                                                       if (tempah != 0xFF)
-                                                               tempbx
-                                                                               = VB_XGI301C;
-                                               }
-                                       }
-                               }
-
-                               if (tempbx & (VB_XGI301B | VB_XGI302B)) {
-                                       flag = XGINew_GetReg1(
-                                                       pVBInfo->Part4Port,
-                                                       0x23);
 
-                                       if (!(flag & 0x02))
-                                               tempbx = tempbx | VB_NoLCD;
-                               }
+       if (pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
+               if (!(pVBInfo->LCDInfo & (SetLCDtoNonExpanding
+                               | EnableScalingLCD))) {
+                       if ((pVBInfo->LCDResInfo == Panel1024x768)
+                                       || (pVBInfo->LCDResInfo
+                                                       == Panel1024x768x75)) {
+                               pVBInfo->HDE = 1024;
+                               pVBInfo->VDE = 768;
+                       } else if ((pVBInfo->LCDResInfo == Panel1280x1024)
+                                       || (pVBInfo->LCDResInfo
+                                                       == Panel1280x1024x75)) {
+                               pVBInfo->HDE = 1280;
+                               pVBInfo->VDE = 1024;
+                       } else if (pVBInfo->LCDResInfo == Panel1400x1050) {
+                               pVBInfo->HDE = 1400;
+                               pVBInfo->VDE = 1050;
+                       } else {
+                               pVBInfo->HDE = 1600;
+                               pVBInfo->VDE = 1200;
                        }
                }
-               pVBInfo->VBType = tempbx;
        }
-       /*
-       else if (pVBInfo->IF_DEF_CH7017 == 1)
-               pVBInfo->VBType = VB_CH7017;
-       else //LVDS
-               pVBInfo->VBType = VB_LVDS_NS;
-        */
-
 }
 
-void XGI_GetVBInfo(unsigned short ModeNo, unsigned short ModeIdIndex,
+static void XGI_ModCRT1Regs(unsigned short ModeNo, unsigned short ModeIdIndex,
+               unsigned short RefreshRateTableIndex,
                struct xgi_hw_device_info *HwDeviceExtension,
                struct vb_device_info *pVBInfo)
 {
-       unsigned short tempax, push, tempbx, temp, modeflag;
+       unsigned char index;
+       unsigned short tempbx, i;
+       struct XGI_LVDSCRT1HDataStruct *LCDPtr = NULL;
+       struct XGI_LVDSCRT1VDataStruct *LCDPtr1 = NULL;
+       /* struct XGI330_CHTVDataStruct *TVPtr = NULL; */
+       struct XGI_CH7007TV_TimingHStruct *CH7007TV_TimingHPtr = NULL;
+       struct XGI_CH7007TV_TimingVStruct *CH7007TV_TimingVPtr = NULL;
 
        if (ModeNo <= 0x13)
-               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag;
+               index = pVBInfo->SModeIDTable[ModeIdIndex].St_CRT2CRTC;
        else
-               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
-
-       pVBInfo->SetFlag = 0;
-       pVBInfo->ModeType = modeflag & ModeInfoFlag;
-       tempbx = 0;
+               index = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT2CRTC;
 
-       if (pVBInfo->VBType & 0xFFFF) {
-               temp = XGINew_GetReg1(pVBInfo->P3d4, 0x30); /* Check Display Device */
-               tempbx = tempbx | temp;
-               temp = XGINew_GetReg1(pVBInfo->P3d4, 0x31);
-               push = temp;
-               push = push << 8;
-               tempax = temp << 8;
-               tempbx = tempbx | tempax;
-               temp = (SetCRT2ToDualEdge | SetCRT2ToYPbPr | SetCRT2ToLCDA
-                               | SetInSlaveMode | DisableCRT2Display);
-               temp = 0xFFFF ^ temp;
-               tempbx &= temp;
+       index = index & IndexMask;
 
-               temp = XGINew_GetReg1(pVBInfo->P3d4, 0x38);
+       if ((pVBInfo->IF_DEF_ScaleLCD == 0) || ((pVBInfo->IF_DEF_ScaleLCD == 1)
+                       && (!(pVBInfo->LCDInfo & EnableScalingLCD)))) {
+               tempbx = 0;
 
-               if (pVBInfo->IF_DEF_LCDA == 1) {
+               if (pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
+                       LCDPtr
+                                       = (struct XGI_LVDSCRT1HDataStruct *) XGI_GetLcdPtr(
+                                                       tempbx, ModeNo,
+                                                       ModeIdIndex,
+                                                       RefreshRateTableIndex,
+                                                       pVBInfo);
 
-                       if ((pVBInfo->Set_VGAType >= XG20)
-                                       || (pVBInfo->Set_VGAType >= XG40)) {
-                               if (pVBInfo->IF_DEF_LVDS == 0) {
-                                       /* if ((pVBInfo->VBType & VB_XGI302B) || (pVBInfo->VBType & VB_XGI301LV) || (pVBInfo->VBType & VB_XGI302LV) || (pVBInfo->VBType & VB_XGI301C)) */
-                                       if (pVBInfo->VBType & (VB_XGI302B
-                                                       | VB_XGI301LV
-                                                       | VB_XGI302LV
-                                                       | VB_XGI301C)) {
-                                               if (temp & EnableDualEdge) {
-                                                       tempbx
-                                                                       |= SetCRT2ToDualEdge;
+                       for (i = 0; i < 8; i++)
+                               pVBInfo->TimingH[0].data[i] = LCDPtr[0].Reg[i];
+               }
 
-                                                       if (temp & SetToLCDA)
-                                                               tempbx
-                                                                               |= SetCRT2ToLCDA;
-                                               }
-                                       }
-                               } else if (pVBInfo->IF_DEF_CH7017 == 1) {
-                                       if (pVBInfo->VBType & VB_CH7017) {
-                                               if (temp & EnableDualEdge) {
-                                                       tempbx
-                                                                       |= SetCRT2ToDualEdge;
+               if (pVBInfo->IF_DEF_CH7007 == 1) {
+                       if (pVBInfo->VBInfo & SetCRT2ToTV) {
+                               CH7007TV_TimingHPtr
+                                               = (struct XGI_CH7007TV_TimingHStruct *) XGI_GetTVPtr(
+                                                               tempbx,
+                                                               ModeNo,
+                                                               ModeIdIndex,
+                                                               RefreshRateTableIndex,
+                                                               pVBInfo);
 
-                                                       if (temp & SetToLCDA)
-                                                               tempbx
-                                                                               |= SetCRT2ToLCDA;
-                                               }
-                                       }
-                               }
+                               for (i = 0; i < 8; i++)
+                                       pVBInfo->TimingH[0].data[i]
+                                                       = CH7007TV_TimingHPtr[0].data[i];
                        }
                }
 
-               if (pVBInfo->IF_DEF_YPbPr == 1) {
-                       if (((pVBInfo->IF_DEF_LVDS == 0) && ((pVBInfo->VBType
-                                       & VB_XGI301LV) || (pVBInfo->VBType
-                                       & VB_XGI302LV) || (pVBInfo->VBType
-                                       & VB_XGI301C)))
-                                       || ((pVBInfo->IF_DEF_CH7017 == 1)
-                                                       && (pVBInfo->VBType
-                                                                       & VB_CH7017))
-                                       || ((pVBInfo->IF_DEF_CH7007 == 1)
-                                                       && (pVBInfo->VBType
-                                                                       & VB_CH7007))) { /* [Billy] 07/05/04 */
-                               if (temp & SetYPbPr) { /* temp = CR38 */
-                                       if (pVBInfo->IF_DEF_HiVision == 1) {
-                                               temp = XGINew_GetReg1(
-                                                               pVBInfo->P3d4,
-                                                               0x35); /* shampoo add for new scratch */
-                                               temp &= YPbPrMode;
-                                               tempbx |= SetCRT2ToHiVisionTV;
+               /* if (pVBInfo->IF_DEF_CH7017 == 1) {
+                       if (pVBInfo->VBInfo & SetCRT2ToTV)
+                               TVPtr = (struct XGI330_CHTVDataStruct *)XGI_GetTVPtr(tempbx, ModeNo, ModeIdIndex, RefreshRateTableIndex, pVBInfo);
+               }
+               */
 
-                                               if (temp != YPbPrMode1080i) {
-                                                       tempbx
-                                                                       &= (~SetCRT2ToHiVisionTV);
-                                                       tempbx
-                                                                       |= SetCRT2ToYPbPr;
-                                               }
-                                       }
+               XGI_SetCRT1Timing_H(pVBInfo, HwDeviceExtension);
 
-                                       /* tempbx |= SetCRT2ToYPbPr; */
-                               }
-                       }
+               if (pVBInfo->IF_DEF_CH7007 == 1) {
+                       XGINew_SetReg1(pVBInfo->P3c4, 0x2E,
+                                       CH7007TV_TimingHPtr[0].data[8]);
+                       XGINew_SetReg1(pVBInfo->P3c4, 0x2F,
+                                       CH7007TV_TimingHPtr[0].data[9]);
                }
 
-               tempax = push; /* restore CR31 */
+               tempbx = 1;
 
-               if (pVBInfo->IF_DEF_LVDS == 0) {
-                       if (pVBInfo->IF_DEF_YPbPr == 1) {
-                               if (pVBInfo->IF_DEF_HiVision == 1)
-                                       temp = 0x09FC;
-                               else
-                                       temp = 0x097C;
-                       } else {
-                               if (pVBInfo->IF_DEF_HiVision == 1)
-                                       temp = 0x01FC;
-                               else
-                                       temp = 0x017C;
-                       }
-               } else { /* 3nd party chip */
-                       if (pVBInfo->IF_DEF_CH7017 == 1)
-                               temp = (SetCRT2ToTV | SetCRT2ToLCD
-                                               | SetCRT2ToLCDA);
-                       else if (pVBInfo->IF_DEF_CH7007 == 1) { /* [Billy] 07/05/03 */
-                               temp = SetCRT2ToTV;
-                       } else
-                               temp = SetCRT2ToLCD;
+               if (pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
+                       LCDPtr1
+                                       = (struct XGI_LVDSCRT1VDataStruct *) XGI_GetLcdPtr(
+                                                       tempbx, ModeNo,
+                                                       ModeIdIndex,
+                                                       RefreshRateTableIndex,
+                                                       pVBInfo);
+                       for (i = 0; i < 7; i++)
+                               pVBInfo->TimingV[0].data[i] = LCDPtr1[0].Reg[i];
                }
 
-               if (!(tempbx & temp)) {
-                       tempax |= DisableCRT2Display;
-                       tempbx = 0;
-               }
+               if (pVBInfo->IF_DEF_CH7007 == 1) {
+                       if (pVBInfo->VBInfo & SetCRT2ToTV) {
+                               CH7007TV_TimingVPtr
+                                               = (struct XGI_CH7007TV_TimingVStruct *) XGI_GetTVPtr(
+                                                               tempbx,
+                                                               ModeNo,
+                                                               ModeIdIndex,
+                                                               RefreshRateTableIndex,
+                                                               pVBInfo);
 
-               if (pVBInfo->IF_DEF_LCDA == 1) { /* Select Display Device */
-                       if (!(pVBInfo->VBType & VB_NoLCD)) {
-                               if (tempbx & SetCRT2ToLCDA) {
-                                       if (tempbx & SetSimuScanMode)
-                                               tempbx
-                                                               &= (~(SetCRT2ToLCD
-                                                                               | SetCRT2ToRAMDAC
-                                                                               | SwitchToCRT2));
-                                       else
-                                               tempbx
-                                                               &= (~(SetCRT2ToLCD
-                                                                               | SetCRT2ToRAMDAC
-                                                                               | SetCRT2ToTV
-                                                                               | SwitchToCRT2));
-                               }
+                               for (i = 0; i < 7; i++)
+                                       pVBInfo->TimingV[0].data[i]
+                                                       = CH7007TV_TimingVPtr[0].data[i];
                        }
                }
-
-               /* shampoo add */
-               if (!(tempbx & (SwitchToCRT2 | SetSimuScanMode))) { /* for driver abnormal */
-                       if (pVBInfo->IF_DEF_CRT2Monitor == 1) {
-                               if (tempbx & SetCRT2ToRAMDAC) {
-                                       tempbx &= (0xFF00 | SetCRT2ToRAMDAC
-                                                       | SwitchToCRT2
-                                                       | SetSimuScanMode);
-                                       tempbx &= (0x00FF | (~SetCRT2ToYPbPr));
-                               }
-                       } else {
-                               tempbx &= (~(SetCRT2ToRAMDAC | SetCRT2ToLCD
-                                               | SetCRT2ToTV));
-                       }
+               /* if (pVBInfo->IF_DEF_CH7017 == 1) {
+                       if (pVBInfo->VBInfo & SetCRT2ToTV)
+                               TVPtr = (struct XGI330_CHTVDataStruct *)XGI_GetTVPtr(tempbx, ModeNo, ModeIdIndex, RefreshRateTableIndex, pVBInfo);
                }
+               */
 
-               if (!(pVBInfo->VBType & VB_NoLCD)) {
-                       if (tempbx & SetCRT2ToLCD) {
-                               tempbx &= (0xFF00 | SetCRT2ToLCD | SwitchToCRT2
-                                               | SetSimuScanMode);
-                               tempbx &= (0x00FF | (~SetCRT2ToYPbPr));
-                       }
-               }
+               XGI_SetCRT1Timing_V(ModeIdIndex, ModeNo, pVBInfo);
 
-               if (tempbx & SetCRT2ToSCART) {
-                       tempbx &= (0xFF00 | SetCRT2ToSCART | SwitchToCRT2
-                                       | SetSimuScanMode);
-                       tempbx &= (0x00FF | (~SetCRT2ToYPbPr));
-               }
+               if (pVBInfo->IF_DEF_CH7007 == 1) {
+                       XGINew_SetRegANDOR(pVBInfo->P3c4, 0x33, ~0x01,
+                                       CH7007TV_TimingVPtr[0].data[7] & 0x01);
+                       XGINew_SetReg1(pVBInfo->P3c4, 0x34,
+                                       CH7007TV_TimingVPtr[0].data[8]);
+                       XGINew_SetReg1(pVBInfo->P3c4, 0x3F,
+                                       CH7007TV_TimingVPtr[0].data[9]);
 
-               if (pVBInfo->IF_DEF_YPbPr == 1) {
-                       if (tempbx & SetCRT2ToYPbPr)
-                               tempbx &= (0xFF00 | SwitchToCRT2
-                                               | SetSimuScanMode);
                }
+       }
+}
 
-               if (pVBInfo->IF_DEF_HiVision == 1) {
-                       if (tempbx & SetCRT2ToHiVisionTV)
-                               tempbx &= (0xFF00 | SetCRT2ToHiVisionTV
-                                               | SwitchToCRT2
-                                               | SetSimuScanMode);
-               }
+static unsigned short XGI_GetLCDCapPtr(struct vb_device_info *pVBInfo)
+{
+       unsigned char tempal, tempah, tempbl, i;
+
+       tempah = XGINew_GetReg1(pVBInfo->P3d4, 0x36);
+       tempal = tempah & 0x0F;
+       tempah = tempah & 0xF0;
+       i = 0;
+       tempbl = pVBInfo->LCDCapList[i].LCD_ID;
 
-               if (tempax & DisableCRT2Display) { /* Set Display Device Info */
-                       if (!(tempbx & (SwitchToCRT2 | SetSimuScanMode)))
-                               tempbx = DisableCRT2Display;
+       while (tempbl != 0xFF) {
+               if (tempbl & 0x80) { /* OEMUtil */
+                       tempal = tempah;
+                       tempbl = tempbl & ~(0x80);
                }
 
-               if (!(tempbx & DisableCRT2Display)) {
-                       if ((!(tempbx & DriverMode))
-                                       || (!(modeflag & CRT2Mode))) {
-                               if (pVBInfo->IF_DEF_LCDA == 1) {
-                                       if (!(tempbx & SetCRT2ToLCDA))
-                                               tempbx
-                                                               |= (SetInSlaveMode
-                                                                               | SetSimuScanMode);
-                               }
+               if (tempal == tempbl)
+                       break;
 
-                               if (pVBInfo->IF_DEF_VideoCapture == 1) {
-                                       if (((HwDeviceExtension->jChipType
-                                                       == XG40)
-                                                       && (pVBInfo->Set_VGAType
-                                                                       == XG40))
-                                                       || ((HwDeviceExtension->jChipType
-                                                                       == XG41)
-                                                                       && (pVBInfo->Set_VGAType
-                                                                                       == XG41))
-                                                       || ((HwDeviceExtension->jChipType
-                                                                       == XG42)
-                                                                       && (pVBInfo->Set_VGAType
-                                                                                       == XG42))
-                                                       || ((HwDeviceExtension->jChipType
-                                                                       == XG45)
-                                                                       && (pVBInfo->Set_VGAType
-                                                                                       == XG45))) {
-                                               if (ModeNo <= 13) {
-                                                       if (!(tempbx
-                                                                       & SetCRT2ToRAMDAC)) { /*CRT2 not need to support*/
-                                                               tempbx
-                                                                               &= (0x00FF
-                                                                                               | (~SetInSlaveMode));
-                                                               pVBInfo->SetFlag
-                                                                               |= EnableVCMode;
-                                                       }
-                                               }
-                                       }
-                               }
-                       }
+               i++;
 
-                       /* LCD+TV can't support in slave mode (Force LCDA+TV->LCDB) */
-                       if ((tempbx & SetInSlaveMode) && (tempbx
-                                       & SetCRT2ToLCDA)) {
-                               tempbx ^= (SetCRT2ToLCD | SetCRT2ToLCDA
-                                               | SetCRT2ToDualEdge);
-                               pVBInfo->SetFlag |= ReserveTVOption;
-                       }
-               }
+               tempbl = pVBInfo->LCDCapList[i].LCD_ID;
        }
 
-       pVBInfo->VBInfo = tempbx;
+       return i;
 }
 
-void XGI_GetTVInfo(unsigned short ModeNo, unsigned short ModeIdIndex,
-               struct vb_device_info *pVBInfo)
+static unsigned short XGI_GetLCDCapPtr1(struct vb_device_info *pVBInfo)
 {
-       unsigned short temp, tempbx = 0, resinfo = 0, modeflag, index1;
+       unsigned short tempah, tempal, tempbl, i;
 
-       tempbx = 0;
-       resinfo = 0;
+       tempal = pVBInfo->LCDResInfo;
+       tempah = pVBInfo->LCDTypeInfo;
 
-       if (pVBInfo->VBInfo & SetCRT2ToTV) {
-               if (ModeNo <= 0x13) {
-                       modeflag
-                                       = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag; /* si+St_ModeFlag */
-                       resinfo = pVBInfo->SModeIDTable[ModeIdIndex].St_ResInfo; /* si+St_ResInfo */
-               } else {
-                       modeflag
-                                       = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
-                       resinfo
-                                       = pVBInfo->EModeIDTable[ModeIdIndex].Ext_RESINFO; /* si+Ext_ResInfo */
-               }
+       i = 0;
+       tempbl = pVBInfo->LCDCapList[i].LCD_ID;
 
-               if (pVBInfo->VBInfo & SetCRT2ToTV) {
-                       temp = XGINew_GetReg1(pVBInfo->P3d4, 0x35);
-                       tempbx = temp;
-                       if (tempbx & SetPALTV) {
-                               tempbx &= (SetCHTVOverScan | SetPALMTV
-                                               | SetPALNTV | SetPALTV);
-                               if (tempbx & SetPALMTV)
-                                       tempbx &= ~SetPALTV; /* set to NTSC if PAL-M */
-                       } else
-                               tempbx &= (SetCHTVOverScan | SetNTSCJ
-                                               | SetPALTV);
-                       /*
-                       if (pVBInfo->IF_DEF_LVDS == 0) {
-                               index1 = XGINew_GetReg1(pVBInfo->P3d4, 0x38); //PAL-M/PAL-N Info
-                               temp2 = (index1 & 0xC0) >> 5; //00:PAL, 01:PAL-M, 10:PAL-N
-                               tempbx |= temp2;
-                               if (temp2 & 0x02)          //PAL-M
-                                       tempbx &= (~SetPALTV);
-                       }
-                       */
+       while (tempbl != 0xFF) {
+               if ((tempbl & 0x80) && (tempbl != 0x80)) {
+                       tempal = tempah;
+                       tempbl &= ~0x80;
                }
 
-               if (pVBInfo->IF_DEF_CH7017 == 1) {
-                       tempbx = XGINew_GetReg1(pVBInfo->P3d4, 0x35);
+               if (tempal == tempbl)
+                       break;
 
-                       if (tempbx & TVOverScan)
-                               tempbx |= SetCHTVOverScan;
-               }
+               i++;
+               tempbl = pVBInfo->LCDCapList[i].LCD_ID;
+       }
 
-               if (pVBInfo->IF_DEF_CH7007 == 1) { /* [Billy] 07/05/04 */
-                       tempbx = XGINew_GetReg1(pVBInfo->P3d4, 0x35);
+       if (tempbl == 0xFF) {
+               pVBInfo->LCDResInfo = Panel1024x768;
+               pVBInfo->LCDTypeInfo = 0;
+               i = 0;
+       }
 
-                       if (tempbx & TVOverScan)
-                               tempbx |= SetCHTVOverScan;
-               }
+       return i;
+}
 
-               if (pVBInfo->IF_DEF_LVDS == 0) {
-                       if (pVBInfo->VBInfo & SetCRT2ToSCART)
-                               tempbx |= SetPALTV;
-               }
+static void XGI_GetLCDSync(unsigned short *HSyncWidth, unsigned short *VSyncWidth,
+               struct vb_device_info *pVBInfo)
+{
+       unsigned short Index;
 
-               if (pVBInfo->IF_DEF_YPbPr == 1) {
-                       if (pVBInfo->VBInfo & SetCRT2ToYPbPr) {
-                               index1 = XGINew_GetReg1(pVBInfo->P3d4, 0x35);
-                               index1 &= YPbPrMode;
+       Index = XGI_GetLCDCapPtr(pVBInfo);
+       *HSyncWidth = pVBInfo->LCDCapList[Index].LCD_HSyncWidth;
+       *VSyncWidth = pVBInfo->LCDCapList[Index].LCD_VSyncWidth;
 
-                               if (index1 == YPbPrMode525i)
-                                       tempbx |= SetYPbPrMode525i;
+       return;
+}
 
-                               if (index1 == YPbPrMode525p)
-                                       tempbx = tempbx | SetYPbPrMode525p;
-                               if (index1 == YPbPrMode750p)
-                                       tempbx = tempbx | SetYPbPrMode750p;
-                       }
-               }
+static void XGI_SetLVDSRegs(unsigned short ModeNo, unsigned short ModeIdIndex,
+               unsigned short RefreshRateTableIndex,
+               struct vb_device_info *pVBInfo)
+{
+       unsigned short tempbx, tempax, tempcx, tempdx, push1, push2, modeflag;
+       unsigned long temp, temp1, temp2, temp3, push3;
+       struct XGI330_LCDDataDesStruct *LCDPtr = NULL;
+       struct XGI330_LCDDataDesStruct2 *LCDPtr1 = NULL;
 
-               if (pVBInfo->IF_DEF_HiVision == 1) {
-                       if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV)
-                               tempbx = tempbx | SetYPbPrMode1080i | SetPALTV;
-               }
+       if (ModeNo > 0x13)
+               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
+       else
+               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag;
 
-               if (pVBInfo->IF_DEF_LVDS == 0) { /* shampoo */
-                       if ((pVBInfo->VBInfo & SetInSlaveMode)
-                                       && (!(pVBInfo->VBInfo & SetNotSimuMode)))
-                               tempbx |= TVSimuMode;
+       if (!(pVBInfo->SetFlag & Win9xDOSMode)) {
+               if ((pVBInfo->IF_DEF_CH7017 == 0) || (pVBInfo->VBInfo
+                               & (SetCRT2ToLCD | SetCRT2ToLCDA))) {
+                       if (pVBInfo->IF_DEF_OEMUtil == 1) {
+                               tempbx = 8;
+                               LCDPtr
+                                               = (struct XGI330_LCDDataDesStruct *) XGI_GetLcdPtr(
+                                                               tempbx,
+                                                               ModeNo,
+                                                               ModeIdIndex,
+                                                               RefreshRateTableIndex,
+                                                               pVBInfo);
+                       }
 
-                       if (!(tempbx & SetPALTV) && (modeflag > 13) && (resinfo
-                                       == 8)) /* NTSC 1024x768, */
-                               tempbx |= NTSC1024x768;
+                       if ((pVBInfo->IF_DEF_OEMUtil == 0) || (LCDPtr == NULL)) {
+                               tempbx = 3;
+                               if (pVBInfo->LCDInfo & EnableScalingLCD)
+                                       LCDPtr1
+                                                       = (struct XGI330_LCDDataDesStruct2 *) XGI_GetLcdPtr(
+                                                                       tempbx,
+                                                                       ModeNo,
+                                                                       ModeIdIndex,
+                                                                       RefreshRateTableIndex,
+                                                                       pVBInfo);
+                               else
+                                       LCDPtr
+                                                       = (struct XGI330_LCDDataDesStruct *) XGI_GetLcdPtr(
+                                                                       tempbx,
+                                                                       ModeNo,
+                                                                       ModeIdIndex,
+                                                                       RefreshRateTableIndex,
+                                                                       pVBInfo);
+                       }
 
-                       tempbx |= RPLLDIV2XO;
+                       XGI_GetLCDSync(&tempax, &tempbx, pVBInfo);
+                       push1 = tempbx;
+                       push2 = tempax;
 
-                       if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV) {
-                               if (pVBInfo->VBInfo & SetInSlaveMode)
-                                       tempbx &= (~RPLLDIV2XO);
+                       /* GetLCDResInfo */
+                       if ((pVBInfo->LCDResInfo == Panel1024x768)
+                                       || (pVBInfo->LCDResInfo
+                                                       == Panel1024x768x75)) {
+                               tempax = 1024;
+                               tempbx = 768;
+                       } else if ((pVBInfo->LCDResInfo == Panel1280x1024)
+                                       || (pVBInfo->LCDResInfo
+                                                       == Panel1280x1024x75)) {
+                               tempax = 1280;
+                               tempbx = 1024;
+                       } else if (pVBInfo->LCDResInfo == Panel1400x1050) {
+                               tempax = 1400;
+                               tempbx = 1050;
                        } else {
-                               if (tempbx & (SetYPbPrMode525p
-                                               | SetYPbPrMode750p))
-                                       tempbx &= (~RPLLDIV2XO);
-                               else if (!(pVBInfo->VBType & (VB_XGI301B
-                                               | VB_XGI302B | VB_XGI301LV
-                                               | VB_XGI302LV | VB_XGI301C))) {
-                                       if (tempbx & TVSimuMode)
-                                               tempbx &= (~RPLLDIV2XO);
-                               }
+                               tempax = 1600;
+                               tempbx = 1200;
+                       }
+
+                       if (pVBInfo->LCDInfo & SetLCDtoNonExpanding) {
+                               pVBInfo->HDE = tempax;
+                               pVBInfo->VDE = tempbx;
+                               pVBInfo->VGAHDE = tempax;
+                               pVBInfo->VGAVDE = tempbx;
+                       }
+
+                       if ((pVBInfo->IF_DEF_ScaleLCD == 1)
+                                       && (pVBInfo->LCDInfo & EnableScalingLCD)) {
+                               tempax = pVBInfo->HDE;
+                               tempbx = pVBInfo->VDE;
                        }
-               }
-       }
-       pVBInfo->TVInfo = tempbx;
-}
 
-unsigned char XGI_GetLCDInfo(unsigned short ModeNo, unsigned short ModeIdIndex,
-               struct vb_device_info *pVBInfo)
-{
-       unsigned short temp, tempax, tempbx, modeflag, resinfo = 0, LCDIdIndex;
+                       tempax = pVBInfo->HT;
 
-       pVBInfo->LCDResInfo = 0;
-       pVBInfo->LCDTypeInfo = 0;
-       pVBInfo->LCDInfo = 0;
+                       if (pVBInfo->LCDInfo & EnableScalingLCD)
+                               tempbx = LCDPtr1->LCDHDES;
+                       else
+                               tempbx = LCDPtr->LCDHDES;
 
-       if (ModeNo <= 0x13) {
-               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag; /* si+St_ModeFlag // */
-       } else {
-               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
-               resinfo = pVBInfo->EModeIDTable[ModeIdIndex].Ext_RESINFO; /* si+Ext_ResInfo // */
-       }
+                       tempcx = pVBInfo->HDE;
+                       tempbx = tempbx & 0x0fff;
+                       tempcx += tempbx;
 
-       temp = XGINew_GetReg1(pVBInfo->P3d4, 0x36); /* Get LCD Res.Info */
-       tempbx = temp & 0x0F;
+                       if (tempcx >= tempax)
+                               tempcx -= tempax;
 
-       if (tempbx == 0)
-               tempbx = Panel1024x768; /* default */
+                       XGINew_SetReg1(pVBInfo->Part1Port, 0x1A, tempbx & 0x07);
 
-       /* LCD75 [2003/8/22] Vicent */
-       if ((tempbx == Panel1024x768) || (tempbx == Panel1280x1024)) {
-               if (pVBInfo->VBInfo & DriverMode) {
-                       tempax = XGINew_GetReg1(pVBInfo->P3d4, 0x33);
-                       if (pVBInfo->VBInfo & SetCRT2ToLCDA)
-                               tempax &= 0x0F;
+                       tempcx = tempcx >> 3;
+                       tempbx = tempbx >> 3;
+
+                       XGINew_SetReg1(pVBInfo->Part1Port, 0x16,
+                                       (unsigned short) (tempbx & 0xff));
+                       XGINew_SetReg1(pVBInfo->Part1Port, 0x17,
+                                       (unsigned short) (tempcx & 0xff));
+
+                       tempax = pVBInfo->HT;
+
+                       if (pVBInfo->LCDInfo & EnableScalingLCD)
+                               tempbx = LCDPtr1->LCDHRS;
                        else
-                               tempax = tempax >> 4;
+                               tempbx = LCDPtr->LCDHRS;
 
-                       if ((resinfo == 6) || (resinfo == 9)) {
-                               if (tempax >= 3)
-                                       tempbx |= PanelRef75Hz;
-                       } else if ((resinfo == 7) || (resinfo == 8)) {
-                               if (tempax >= 4)
-                                       tempbx |= PanelRef75Hz;
-                       }
-               }
-       }
+                       tempcx = push2;
 
-       pVBInfo->LCDResInfo = tempbx;
+                       if (pVBInfo->LCDInfo & EnableScalingLCD)
+                               tempcx = LCDPtr1->LCDHSync;
 
-       /* End of LCD75 */
+                       tempcx += tempbx;
 
-       if (pVBInfo->IF_DEF_OEMUtil == 1)
-               pVBInfo->LCDTypeInfo = (temp & 0xf0) >> 4;
+                       if (tempcx >= tempax)
+                               tempcx -= tempax;
 
-       if (!(pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)))
-               return 0;
+                       tempax = tempbx & 0x07;
+                       tempax = tempax >> 5;
+                       tempcx = tempcx >> 3;
+                       tempbx = tempbx >> 3;
 
-       tempbx = 0;
+                       tempcx &= 0x1f;
+                       tempax |= tempcx;
 
-       temp = XGINew_GetReg1(pVBInfo->P3d4, 0x37);
+                       XGINew_SetReg1(pVBInfo->Part1Port, 0x15, tempax);
+                       XGINew_SetReg1(pVBInfo->Part1Port, 0x14,
+                                       (unsigned short) (tempbx & 0xff));
 
-       temp &= (ScalingLCD | LCDNonExpanding | LCDSyncBit | SetPWDEnable);
+                       tempax = pVBInfo->VT;
+                       if (pVBInfo->LCDInfo & EnableScalingLCD)
+                               tempbx = LCDPtr1->LCDVDES;
+                       else
+                               tempbx = LCDPtr->LCDVDES;
+                       tempcx = pVBInfo->VDE;
 
-       if ((pVBInfo->IF_DEF_ScaleLCD == 1) && (temp & LCDNonExpanding))
-               temp &= ~EnableScalingLCD;
+                       tempbx = tempbx & 0x0fff;
+                       tempcx += tempbx;
+                       if (tempcx >= tempax)
+                               tempcx -= tempax;
 
-       tempbx |= temp;
+                       XGINew_SetReg1(pVBInfo->Part1Port, 0x1b,
+                                       (unsigned short) (tempbx & 0xff));
+                       XGINew_SetReg1(pVBInfo->Part1Port, 0x1c,
+                                       (unsigned short) (tempcx & 0xff));
 
-       LCDIdIndex = XGI_GetLCDCapPtr1(pVBInfo);
+                       tempbx = (tempbx >> 8) & 0x07;
+                       tempcx = (tempcx >> 8) & 0x07;
 
-       tempax = pVBInfo->LCDCapList[LCDIdIndex].LCD_Capability;
+                       XGINew_SetReg1(pVBInfo->Part1Port, 0x1d,
+                                       (unsigned short) ((tempcx << 3)
+                                                       | tempbx));
 
-       if (pVBInfo->IF_DEF_LVDS == 0) { /* shampoo */
-               if (((pVBInfo->VBType & VB_XGI302LV) || (pVBInfo->VBType
-                               & VB_XGI301C)) && (tempax & LCDDualLink)) {
-                       tempbx |= SetLCDDualLink;
-               }
-       }
+                       tempax = pVBInfo->VT;
+                       if (pVBInfo->LCDInfo & EnableScalingLCD)
+                               tempbx = LCDPtr1->LCDVRS;
+                       else
+                               tempbx = LCDPtr->LCDVRS;
 
-       if (pVBInfo->IF_DEF_CH7017 == 1) {
-               if (tempax & LCDDualLink)
-                       tempbx |= SetLCDDualLink;
-       }
+                       /* tempbx = tempbx >> 4; */
+                       tempcx = push1;
 
-       if (pVBInfo->IF_DEF_LVDS == 0) {
-               if ((pVBInfo->LCDResInfo == Panel1400x1050) && (pVBInfo->VBInfo
-                               & SetCRT2ToLCD) && (ModeNo > 0x13) && (resinfo
-                               == 9) && (!(tempbx & EnableScalingLCD)))
-                       tempbx |= SetLCDtoNonExpanding; /* set to center in 1280x1024 LCDB for Panel1400x1050 */
-       }
+                       if (pVBInfo->LCDInfo & EnableScalingLCD)
+                               tempcx = LCDPtr1->LCDVSync;
 
-       /*
-       if (tempax & LCDBToA) {
-               tempbx |= SetLCDBToA;
-       }
-       */
+                       tempcx += tempbx;
+                       if (tempcx >= tempax)
+                               tempcx -= tempax;
 
-       if (pVBInfo->IF_DEF_ExpLink == 1) {
-               if (modeflag & HalfDCLK) {
-                       /* if (!(pVBInfo->LCDInfo&LCDNonExpanding)) */
-                       if (!(tempbx & SetLCDtoNonExpanding)) {
-                               tempbx |= EnableLVDSDDA;
-                       } else {
-                               if (ModeNo > 0x13) {
-                                       if (pVBInfo->LCDResInfo
-                                                       == Panel1024x768) {
-                                               if (resinfo == 4) { /* 512x384  */
-                                                       tempbx |= EnableLVDSDDA;
-                                               }
-                                       }
-                               }
-                       }
-               }
-       }
+                       XGINew_SetReg1(pVBInfo->Part1Port, 0x18,
+                                       (unsigned short) (tempbx & 0xff));
+                       XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x19, ~0x0f,
+                                       (unsigned short) (tempcx & 0x0f));
 
-       if (pVBInfo->VBInfo & SetInSlaveMode) {
-               if (pVBInfo->VBInfo & SetNotSimuMode)
-                       tempbx |= LCDVESATiming;
-       } else {
-               tempbx |= LCDVESATiming;
-       }
+                       tempax = ((tempbx >> 8) & 0x07) << 3;
 
-       pVBInfo->LCDInfo = tempbx;
+                       tempbx = pVBInfo->VGAVDE;
+                       if (tempbx != pVBInfo->VDE)
+                               tempax |= 0x40;
 
-       if (pVBInfo->IF_DEF_PWD == 1) {
-               if (pVBInfo->LCDInfo & SetPWDEnable) {
-                       if ((pVBInfo->VBType & VB_XGI302LV) || (pVBInfo->VBType
-                                       & VB_XGI301C)) {
-                               if (!(tempax & PWDEnable))
-                                       pVBInfo->LCDInfo &= ~SetPWDEnable;
-                       }
-               }
-       }
+                       if (pVBInfo->LCDInfo & EnableLVDSDDA)
+                               tempax |= 0x40;
 
-       if (pVBInfo->IF_DEF_LVDS == 0) {
-               if (tempax & (LockLCDBToA | StLCDBToA)) {
-                       if (pVBInfo->VBInfo & SetInSlaveMode) {
-                               if (!(tempax & LockLCDBToA)) {
-                                       if (ModeNo <= 0x13) {
-                                               pVBInfo->VBInfo
-                                                               &= ~(SetSimuScanMode
-                                                                               | SetInSlaveMode
-                                                                               | SetCRT2ToLCD);
-                                               pVBInfo->VBInfo
-                                                               |= SetCRT2ToLCDA
-                                                                               | SetCRT2ToDualEdge;
-                                       }
-                               }
-                       }
-               }
-       }
+                       XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x1a, 0x07,
+                                       tempax);
 
-       /*
-       if (pVBInfo->IF_DEF_LVDS == 0) {
-               if (tempax & (LockLCDBToA | StLCDBToA)) {
-                       if (pVBInfo->VBInfo & SetInSlaveMode) {
-                               if (!((!(tempax & LockLCDBToA)) && (ModeNo > 0x13))) {
-                                       pVBInfo->VBInfo&=~(SetSimuScanMode|SetInSlaveMode|SetCRT2ToLCD);
-                                       pVBInfo->VBInfo|=SetCRT2ToLCDA|SetCRT2ToDualEdge;
-                               }
-                       }
-               }
-       }
-       */
+                       tempcx = pVBInfo->VGAVT;
+                       tempbx = pVBInfo->VDE;
+                       tempax = pVBInfo->VGAVDE;
+                       tempcx -= tempax;
 
-       return 1;
-}
+                       temp = tempax; /* 0430 ylshieh */
+                       temp1 = (temp << 18) / tempbx;
 
-unsigned char XGI_SearchModeID(unsigned short ModeNo,
-               unsigned short *ModeIdIndex, struct vb_device_info *pVBInfo)
-{
-       if (ModeNo <= 5)
-               ModeNo |= 1;
-       if (ModeNo <= 0x13) {
-               /* for (*ModeIdIndex=0; *ModeIdIndex < sizeof(pVBInfo->SModeIDTable) / sizeof(struct XGI_StStruct); (*ModeIdIndex)++) */
-               for (*ModeIdIndex = 0;; (*ModeIdIndex)++) {
-                       if (pVBInfo->SModeIDTable[*ModeIdIndex].St_ModeID == ModeNo)
-                               break;
-                       if (pVBInfo->SModeIDTable[*ModeIdIndex].St_ModeID == 0xFF)
-                               return 0;
-               }
+                       tempdx = (unsigned short) ((temp << 18) % tempbx);
 
-               if (ModeNo == 0x07)
-                       (*ModeIdIndex)++; /* 400 lines */
-               if (ModeNo <= 3)
-                       (*ModeIdIndex) += 2; /* 400 lines */
-               /* else 350 lines */
-       } else {
-               /* for (*ModeIdIndex=0; *ModeIdIndex < sizeof(pVBInfo->EModeIDTable) / sizeof(struct XGI_ExtStruct); (*ModeIdIndex)++) */
-               for (*ModeIdIndex = 0;; (*ModeIdIndex)++) {
-                       if (pVBInfo->EModeIDTable[*ModeIdIndex].Ext_ModeID == ModeNo)
-                               break;
-                       if (pVBInfo->EModeIDTable[*ModeIdIndex].Ext_ModeID == 0xFF)
-                               return 0;
-               }
-       }
+                       if (tempdx != 0)
+                               temp1 += 1;
+
+                       temp2 = temp1;
+                       push3 = temp2;
+
+                       XGINew_SetReg1(pVBInfo->Part1Port, 0x37,
+                                       (unsigned short) (temp2 & 0xff));
+                       XGINew_SetReg1(pVBInfo->Part1Port, 0x36,
+                                       (unsigned short) ((temp2 >> 8) & 0xff));
 
-       return 1;
-}
+                       tempbx = (unsigned short) (temp2 >> 16);
+                       tempax = tempbx & 0x03;
 
-/* win2000 MM adapter not support standard mode! */
+                       tempbx = pVBInfo->VGAVDE;
+                       if (tempbx == pVBInfo->VDE)
+                               tempax |= 0x04;
 
-#if 0
-static unsigned char XGINew_CheckMemorySize(
-               struct xgi_hw_device_info *HwDeviceExtension,
-               unsigned short ModeNo,
-               unsigned short ModeIdIndex,
-               struct vb_device_info *pVBInfo)
-{
-       unsigned short memorysize, modeflag, temp, temp1, tmp;
+                       XGINew_SetReg1(pVBInfo->Part1Port, 0x35, tempax);
 
-       /*
-       if ((HwDeviceExtension->jChipType == XGI_650) ||
-       (HwDeviceExtension->jChipType == XGI_650M)) {
-               return 1;
-       }
-       */
+                       if (pVBInfo->VBType & VB_XGI301C) {
+                               temp2 = push3;
+                               XGINew_SetReg1(pVBInfo->Part4Port, 0x3c,
+                                               (unsigned short) (temp2 & 0xff));
+                               XGINew_SetReg1(pVBInfo->Part4Port, 0x3b,
+                                               (unsigned short) ((temp2 >> 8)
+                                                               & 0xff));
+                               tempbx = (unsigned short) (temp2 >> 16);
+                               XGINew_SetRegANDOR(pVBInfo->Part4Port, 0x3a,
+                                               ~0xc0,
+                                               (unsigned short) ((tempbx
+                                                               & 0xff) << 6));
 
-       if (ModeNo <= 0x13)
-               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag;
-       else
-               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
+                               tempcx = pVBInfo->VGAVDE;
+                               if (tempcx == pVBInfo->VDE)
+                                       XGINew_SetRegANDOR(pVBInfo->Part4Port,
+                                                       0x30, ~0x0c, 0x00);
+                               else
+                                       XGINew_SetRegANDOR(pVBInfo->Part4Port,
+                                                       0x30, ~0x0c, 0x08);
+                       }
 
-       /* ModeType = modeflag&ModeInfoFlag; // Get mode type */
+                       tempcx = pVBInfo->VGAHDE;
+                       tempbx = pVBInfo->HDE;
 
-       memorysize = modeflag & MemoryInfoFlag;
-       memorysize = memorysize > MemorySizeShift;
-       memorysize++; /* Get memory size */
+                       temp1 = tempcx << 16;
 
-       temp = XGINew_GetReg1(pVBInfo->P3c4, 0x14); /* Get DRAM Size */
-       tmp = temp;
+                       tempax = (unsigned short) (temp1 / tempbx);
 
-       if (HwDeviceExtension->jChipType == XG40) {
-               temp = 1 << ((temp & 0x0F0) >> 4); /* memory size per channel SR14[7:4] */
-               if ((tmp & 0x0c) == 0x0C) { /* Qual channels */
-                       temp <<= 2;
-               } else if ((tmp & 0x0c) == 0x08) { /* Dual channels */
-                       temp <<= 1;
-               }
-       } else if (HwDeviceExtension->jChipType == XG42) {
-               temp = 1 << ((temp & 0x0F0) >> 4); /* memory size per channel SR14[7:4] */
-               if ((tmp & 0x04) == 0x04) { /* Dual channels */
-                       temp <<= 1;
-               }
-       } else if (HwDeviceExtension->jChipType == XG45) {
-               temp = 1 << ((temp & 0x0F0) >> 4); /* memory size per channel SR14[7:4] */
-               if ((tmp & 0x0c) == 0x0C) { /* Qual channels */
-                       temp <<= 2;
-               } else if ((tmp & 0x0c) == 0x08) { /* triple channels */
-                       temp1 = temp;
-                       temp <<= 1;
-                       temp += temp1;
-               } else if ((tmp & 0x0c) == 0x04) { /* Dual channels */
-                       temp <<= 1;
-               }
-       }
-       if (temp < memorysize)
-               return 0;
-       else
-               return 1;
-}
-#endif
+                       if ((tempbx & 0xffff) == (tempcx & 0xffff))
+                               tempax = 65535;
 
-/*
-void XGINew_IsLowResolution(unsigned short ModeNo, unsigned short ModeIdIndex, unsigned char XGINew_CheckMemorySize(struct xgi_hw_device_info *HwDeviceExtension, unsigned short ModeNo, unsigned short ModeIdIndex, struct vb_device_info *pVBInfo)
-{
-       unsigned short data ;
-       unsigned short ModeFlag ;
+                       temp3 = tempax;
+                       temp1 = pVBInfo->VGAHDE << 16;
 
-       data = XGINew_GetReg1(pVBInfo->P3c4, 0x0F);
-       data &= 0x7F;
-       XGINew_SetReg1(pVBInfo->P3c4, 0x0F, data);
+                       temp1 /= temp3;
+                       temp3 = temp3 << 16;
+                       temp1 -= 1;
 
-       if (ModeNo > 0x13) {
-               ModeFlag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
-               if ((ModeFlag & HalfDCLK) && (ModeFlag & DoubleScanMode)) {
-                       data = XGINew_GetReg1(pVBInfo->P3c4, 0x0F);
-                       data |= 0x80;
-                       XGINew_SetReg1(pVBInfo->P3c4, 0x0F, data);
-                       data = XGINew_GetReg1(pVBInfo->P3c4, 0x01);
-                       data &= 0xF7;
-                       XGINew_SetReg1(pVBInfo->P3c4, 0x01, data);
-               }
-       }
-}
-*/
+                       temp3 = (temp3 & 0xffff0000) + (temp1 & 0xffff);
 
-void XGI_DisplayOn(struct xgi_hw_device_info *pXGIHWDE,
-               struct vb_device_info *pVBInfo)
-{
+                       tempax = (unsigned short) (temp3 & 0xff);
+                       XGINew_SetReg1(pVBInfo->Part1Port, 0x1f, tempax);
 
-       XGINew_SetRegANDOR(pVBInfo->P3c4, 0x01, 0xDF, 0x00);
-       if (pXGIHWDE->jChipType == XG21) {
-               if (pVBInfo->IF_DEF_LVDS == 1) {
-                       if (!(XGI_XG21GetPSCValue(pVBInfo) & 0x1)) {
-                               XGI_XG21BLSignalVDD(0x01, 0x01, pVBInfo); /* LVDS VDD on */
-                               XGI_XG21SetPanelDelay(2, pVBInfo);
-                       }
-                       if (!(XGI_XG21GetPSCValue(pVBInfo) & 0x20))
-                               XGI_XG21BLSignalVDD(0x20, 0x20, pVBInfo); /* LVDS signal on */
-                       XGI_XG21SetPanelDelay(3, pVBInfo);
-                       XGI_XG21BLSignalVDD(0x02, 0x02, pVBInfo); /* LVDS backlight on */
-               } else {
-                       XGI_XG21BLSignalVDD(0x20, 0x20, pVBInfo); /* DVO/DVI signal on */
-               }
+                       temp1 = pVBInfo->VGAVDE << 18;
+                       temp1 = temp1 / push3;
+                       tempbx = (unsigned short) (temp1 & 0xffff);
 
-       }
+                       if (pVBInfo->LCDResInfo == Panel1024x768)
+                               tempbx -= 1;
 
-       if (pVBInfo->IF_DEF_CH7007 == 1) { /* [Billy] 07/05/23 For CH7007 */
+                       tempax = ((tempbx >> 8) & 0xff) << 3;
+                       tempax |= (unsigned short) ((temp3 >> 8) & 0x07);
+                       XGINew_SetReg1(pVBInfo->Part1Port, 0x20,
+                                       (unsigned short) (tempax & 0xff));
+                       XGINew_SetReg1(pVBInfo->Part1Port, 0x21,
+                                       (unsigned short) (tempbx & 0xff));
 
-       }
+                       temp3 = temp3 >> 16;
 
-       if (pXGIHWDE->jChipType == XG27) {
-               if (pVBInfo->IF_DEF_LVDS == 1) {
-                       if (!(XGI_XG27GetPSCValue(pVBInfo) & 0x1)) {
-                               XGI_XG27BLSignalVDD(0x01, 0x01, pVBInfo); /* LVDS VDD on */
-                               XGI_XG21SetPanelDelay(2, pVBInfo);
-                       }
-                       if (!(XGI_XG27GetPSCValue(pVBInfo) & 0x20))
-                               XGI_XG27BLSignalVDD(0x20, 0x20, pVBInfo); /* LVDS signal on */
-                       XGI_XG21SetPanelDelay(3, pVBInfo);
-                       XGI_XG27BLSignalVDD(0x02, 0x02, pVBInfo); /* LVDS backlight on */
-               } else {
-                       XGI_XG27BLSignalVDD(0x20, 0x20, pVBInfo); /* DVO/DVI signal on */
-               }
+                       if (modeflag & HalfDCLK)
+                               temp3 = temp3 >> 1;
 
+                       XGINew_SetReg1(pVBInfo->Part1Port, 0x22,
+                                       (unsigned short) ((temp3 >> 8) & 0xff));
+                       XGINew_SetReg1(pVBInfo->Part1Port, 0x23,
+                                       (unsigned short) (temp3 & 0xff));
+               }
        }
 }
 
-void XGI_DisplayOff(struct xgi_hw_device_info *pXGIHWDE,
+/* --------------------------------------------------------------------- */
+/* Function : XGI_GETLCDVCLKPtr */
+/* Input : */
+/* Output : al -> VCLK Index */
+/* Description : */
+/* --------------------------------------------------------------------- */
+static void XGI_GetLCDVCLKPtr(unsigned char *di_0, unsigned char *di_1,
                struct vb_device_info *pVBInfo)
 {
+       unsigned short index;
 
-       if (pXGIHWDE->jChipType == XG21) {
-               if (pVBInfo->IF_DEF_LVDS == 1) {
-                       XGI_XG21BLSignalVDD(0x02, 0x00, pVBInfo); /* LVDS backlight off */
-                       XGI_XG21SetPanelDelay(3, pVBInfo);
-               } else {
-                       XGI_XG21BLSignalVDD(0x20, 0x00, pVBInfo); /* DVO/DVI signal off */
+       if (pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
+               if (pVBInfo->IF_DEF_ScaleLCD == 1) {
+                       if (pVBInfo->LCDInfo & EnableScalingLCD)
+                               return;
                }
-       }
 
-       if (pVBInfo->IF_DEF_CH7007 == 1) { /* [Billy] 07/05/23 For CH7007 */
-               /* if (IsCH7007TVMode(pVBInfo) == 0) */
-               {
-               }
-       }
+               /* index = XGI_GetLCDCapPtr(pVBInfo); */
+               index = XGI_GetLCDCapPtr1(pVBInfo);
 
-       if (pXGIHWDE->jChipType == XG27) {
-               if ((XGI_XG27GetPSCValue(pVBInfo) & 0x2)) {
-                       XGI_XG27BLSignalVDD(0x02, 0x00, pVBInfo); /* LVDS backlight off */
-                       XGI_XG21SetPanelDelay(3, pVBInfo);
+               if (pVBInfo->VBInfo & SetCRT2ToLCD) { /* LCDB */
+                       *di_0 = pVBInfo->LCDCapList[index].LCUCHAR_VCLKData1;
+                       *di_1 = pVBInfo->LCDCapList[index].LCUCHAR_VCLKData2;
+               } else { /* LCDA */
+                       *di_0 = pVBInfo->LCDCapList[index].LCDA_VCLKData1;
+                       *di_1 = pVBInfo->LCDCapList[index].LCDA_VCLKData2;
                }
-
-               if (pVBInfo->IF_DEF_LVDS == 0)
-                       XGI_XG27BLSignalVDD(0x20, 0x00, pVBInfo); /* DVO/DVI signal off */
        }
-
-       XGINew_SetRegANDOR(pVBInfo->P3c4, 0x01, 0xDF, 0x20);
-}
-
-static void XGI_WaitDisply(struct vb_device_info *pVBInfo)
-{
-       while ((XGINew_GetReg2(pVBInfo->P3da) & 0x01))
-               break;
-
-       while (!(XGINew_GetReg2(pVBInfo->P3da) & 0x01))
-               break;
+       return;
 }
 
-void XGI_SenseCRT1(struct vb_device_info *pVBInfo)
+static unsigned char XGI_GetVCLKPtr(unsigned short RefreshRateTableIndex,
+               unsigned short ModeNo, unsigned short ModeIdIndex,
+               struct vb_device_info *pVBInfo)
 {
-       unsigned char CRTCData[17] = { 0x5F, 0x4F, 0x50, 0x82, 0x55, 0x81,
-                       0x0B, 0x3E, 0xE9, 0x0B, 0xDF, 0xE7, 0x04, 0x00, 0x00,
-                       0x05, 0x00 };
-
-       unsigned char SR01 = 0, SR1F = 0, SR07 = 0, SR06 = 0;
-
-       unsigned char CR17, CR63, SR31;
-       unsigned short temp;
-       unsigned char DAC_TEST_PARMS[3] = { 0x0F, 0x0F, 0x0F };
-
-       int i;
-       XGINew_SetReg1(pVBInfo->P3c4, 0x05, 0x86);
-
-       /* [2004/05/06] Vicent to fix XG42 single LCD sense to CRT+LCD */
-       XGINew_SetReg1(pVBInfo->P3d4, 0x57, 0x4A);
-       XGINew_SetReg1(pVBInfo->P3d4, 0x53, (unsigned char) (XGINew_GetReg1(
-                       pVBInfo->P3d4, 0x53) | 0x02));
 
-       SR31 = (unsigned char) XGINew_GetReg1(pVBInfo->P3c4, 0x31);
-       CR63 = (unsigned char) XGINew_GetReg1(pVBInfo->P3d4, 0x63);
-       SR01 = (unsigned char) XGINew_GetReg1(pVBInfo->P3c4, 0x01);
+       unsigned short index, modeflag;
+       unsigned short tempbx;
+       unsigned char tempal;
+       unsigned char *CHTVVCLKPtr = NULL;
 
-       XGINew_SetReg1(pVBInfo->P3c4, 0x01, (unsigned char) (SR01 & 0xDF));
-       XGINew_SetReg1(pVBInfo->P3d4, 0x63, (unsigned char) (CR63 & 0xBF));
+       if (ModeNo <= 0x13)
+               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag; /* si+St_ResInfo */
+       else
+               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag; /* si+Ext_ResInfo */
 
-       CR17 = (unsigned char) XGINew_GetReg1(pVBInfo->P3d4, 0x17);
-       XGINew_SetReg1(pVBInfo->P3d4, 0x17, (unsigned char) (CR17 | 0x80));
+       if ((pVBInfo->SetFlag & ProgrammingCRT2) && (!(pVBInfo->LCDInfo
+                       & EnableScalingLCD))) { /* {LCDA/LCDB} */
+               index = XGI_GetLCDCapPtr(pVBInfo);
+               tempal = pVBInfo->LCDCapList[index].LCD_VCLK;
 
-       SR1F = (unsigned char) XGINew_GetReg1(pVBInfo->P3c4, 0x1F);
-       XGINew_SetReg1(pVBInfo->P3c4, 0x1F, (unsigned char) (SR1F | 0x04));
+               if (pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA))
+                       return tempal;
 
-       SR07 = (unsigned char) XGINew_GetReg1(pVBInfo->P3c4, 0x07);
-       XGINew_SetReg1(pVBInfo->P3c4, 0x07, (unsigned char) (SR07 & 0xFB));
-       SR06 = (unsigned char) XGINew_GetReg1(pVBInfo->P3c4, 0x06);
-       XGINew_SetReg1(pVBInfo->P3c4, 0x06, (unsigned char) (SR06 & 0xC3));
+               /* {TV} */
+               if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
+                               | VB_XGI302LV | VB_XGI301C)) {
+                       if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV) {
+                               tempal = HiTVVCLKDIV2;
+                               if (!(pVBInfo->TVInfo & RPLLDIV2XO))
+                                       tempal = HiTVVCLK;
+                               if (pVBInfo->TVInfo & TVSimuMode) {
+                                       tempal = HiTVSimuVCLK;
+                                       if (!(modeflag & Charx8Dot))
+                                               tempal = HiTVTextVCLK;
 
-       XGINew_SetReg1(pVBInfo->P3d4, 0x11, 0x00);
+                               }
+                               return tempal;
+                       }
 
-       for (i = 0; i < 8; i++)
-               XGINew_SetReg1(pVBInfo->P3d4, (unsigned short) i, CRTCData[i]);
+                       if (pVBInfo->TVInfo & SetYPbPrMode750p) {
+                               tempal = YPbPr750pVCLK;
+                               return tempal;
+                       }
 
-       for (i = 8; i < 11; i++)
-               XGINew_SetReg1(pVBInfo->P3d4, (unsigned short) (i + 8),
-                               CRTCData[i]);
+                       if (pVBInfo->TVInfo & SetYPbPrMode525p) {
+                               tempal = YPbPr525pVCLK;
+                               return tempal;
+                       }
 
-       for (i = 11; i < 13; i++)
-               XGINew_SetReg1(pVBInfo->P3d4, (unsigned short) (i + 4),
-                               CRTCData[i]);
+                       tempal = NTSC1024VCLK;
 
-       for (i = 13; i < 16; i++)
-               XGINew_SetReg1(pVBInfo->P3c4, (unsigned short) (i - 3),
-                               CRTCData[i]);
+                       if (!(pVBInfo->TVInfo & NTSC1024x768)) {
+                               tempal = TVVCLKDIV2;
+                               if (!(pVBInfo->TVInfo & RPLLDIV2XO))
+                                       tempal = TVVCLK;
+                       }
 
-       XGINew_SetReg1(pVBInfo->P3c4, 0x0E, (unsigned char) (CRTCData[16]
-                       & 0xE0));
+                       if (pVBInfo->VBInfo & SetCRT2ToTV)
+                               return tempal;
+               }
+               /* else if ((pVBInfo->IF_DEF_CH7017==1)&&(pVBInfo->VBType&VB_CH7017)) {
+                       if (ModeNo<=0x13)
+                               *tempal = pVBInfo->SModeIDTable[ModeIdIndex].St_CRT2CRTC;
+                       else
+                               *tempal = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT2CRTC;
+                       *tempal = *tempal & 0x1F;
+                       tempbx = 0;
+                       if (pVBInfo->TVInfo & SetPALTV)
+                               tempbx = tempbx + 2;
+                       if (pVBInfo->TVInfo & SetCHTVOverScan)
+                               tempbx++;
+                       tempbx = tempbx << 1;
+               } */
+       } /* {End of VB} */
 
-       XGINew_SetReg1(pVBInfo->P3c4, 0x31, 0x00);
-       XGINew_SetReg1(pVBInfo->P3c4, 0x2B, 0x1B);
-       XGINew_SetReg1(pVBInfo->P3c4, 0x2C, 0xE1);
+       if ((pVBInfo->IF_DEF_CH7007 == 1) && (pVBInfo->VBType & VB_CH7007)) { /* [Billy] 07/05/08 CH7007 */
+               /* VideoDebugPrint((0, "XGI_GetVCLKPtr: pVBInfo->IF_DEF_CH7007==1\n")); */
+               if ((pVBInfo->VBInfo & SetCRT2ToTV)) {
+                       if (ModeNo <= 0x13) {
+                               tempal
+                                               = pVBInfo->SModeIDTable[ModeIdIndex].St_CRT2CRTC;
+                       } else {
+                               tempal
+                                               = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT2CRTC;
+                       }
 
-       XGINew_SetReg3(pVBInfo->P3c8, 0x00);
+                       tempal = tempal & 0x0F;
+                       tempbx = 0;
 
-       for (i = 0; i < 256; i++) {
-               XGINew_SetReg3((pVBInfo->P3c8 + 1),
-                               (unsigned char) DAC_TEST_PARMS[0]);
-               XGINew_SetReg3((pVBInfo->P3c8 + 1),
-                               (unsigned char) DAC_TEST_PARMS[1]);
-               XGINew_SetReg3((pVBInfo->P3c8 + 1),
-                               (unsigned char) DAC_TEST_PARMS[2]);
-       }
+                       if (pVBInfo->TVInfo & SetPALTV)
+                               tempbx = tempbx + 2;
 
-       XGI_VBLongWait(pVBInfo);
-       XGI_VBLongWait(pVBInfo);
-       XGI_VBLongWait(pVBInfo);
+                       if (pVBInfo->TVInfo & SetCHTVOverScan)
+                               tempbx++;
 
-       mdelay(1);
+                       /** tempbx = tempbx << 1; CH7007 ? **/
 
-       XGI_WaitDisply(pVBInfo);
-       temp = XGINew_GetReg2(pVBInfo->P3c2);
+                       /* [Billy]07/05/29 CH7007 */
+                       if (pVBInfo->IF_DEF_CH7007 == 1) {
+                               switch (tempbx) {
+                               case 0:
+                                       CHTVVCLKPtr = XGI7007_CHTVVCLKUNTSC;
+                                       break;
+                               case 1:
+                                       CHTVVCLKPtr = XGI7007_CHTVVCLKONTSC;
+                                       break;
+                               case 2:
+                                       CHTVVCLKPtr = XGI7007_CHTVVCLKUPAL;
+                                       break;
+                               case 3:
+                                       CHTVVCLKPtr = XGI7007_CHTVVCLKOPAL;
+                                       break;
+                               default:
+                                       break;
 
-       if (temp & 0x10)
-               XGINew_SetRegANDOR(pVBInfo->P3d4, 0x32, 0xDF, 0x20);
-       else
-               XGINew_SetRegANDOR(pVBInfo->P3d4, 0x32, 0xDF, 0x00);
+                               }
+                       }
+                       /* else {
+                               switch(tempbx) {
+                               case 0:
+                                       CHTVVCLKPtr = pVBInfo->CHTVVCLKUNTSC;
+                                       break;
+                               case 1:
+                                       CHTVVCLKPtr = pVBInfo->CHTVVCLKONTSC;
+                                       break;
+                               case 2:
+                                       CHTVVCLKPtr = pVBInfo->CHTVVCLKUPAL;
+                                       break;
+                               case 3:
+                                       CHTVVCLKPtr = pVBInfo->CHTVVCLKOPAL;
+                                       break;
+                               default:
+                                       break;
+                               }
+                       }
+                       */
 
-       /* alan, avoid display something, set BLACK DAC if not restore DAC */
-       XGINew_SetReg3(pVBInfo->P3c8, 0x00);
+                       tempal = CHTVVCLKPtr[tempal];
+                       return tempal;
+               }
 
-       for (i = 0; i < 256; i++) {
-               XGINew_SetReg3((pVBInfo->P3c8 + 1), 0);
-               XGINew_SetReg3((pVBInfo->P3c8 + 1), 0);
-               XGINew_SetReg3((pVBInfo->P3c8 + 1), 0);
        }
 
-       XGINew_SetReg1(pVBInfo->P3c4, 0x01, SR01);
-       XGINew_SetReg1(pVBInfo->P3d4, 0x63, CR63);
-       XGINew_SetReg1(pVBInfo->P3c4, 0x31, SR31);
+       tempal = (unsigned char) XGINew_GetReg2((pVBInfo->P3ca + 0x02));
+       tempal = tempal >> 2;
+       tempal &= 0x03;
 
-       /* [2004/05/11] Vicent */
-       XGINew_SetReg1(pVBInfo->P3d4, 0x53, (unsigned char) (XGINew_GetReg1(
-                       pVBInfo->P3d4, 0x53) & 0xFD));
-       XGINew_SetReg1(pVBInfo->P3c4, 0x1F, (unsigned char) SR1F);
+       if ((pVBInfo->LCDInfo & EnableScalingLCD) && (modeflag & Charx8Dot)) /* for Dot8 Scaling LCD */
+               tempal = tempal ^ tempal; /* ; set to VCLK25MHz always */
+
+       if (ModeNo <= 0x13)
+               return tempal;
+
+       tempal = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRTVCLK;
+       return tempal;
 }
 
-#if 0
-static void XGI_WaitDisplay(struct vb_device_info *pVBInfo)
+static void XGI_GetVCLKLen(unsigned char tempal, unsigned char *di_0,
+               unsigned char *di_1, struct vb_device_info *pVBInfo)
 {
-       while (!(XGINew_GetReg2(pVBInfo->P3da) & 0x01));
-       while (XGINew_GetReg2(pVBInfo->P3da) & 0x01);
+       if (pVBInfo->IF_DEF_CH7007 == 1) { /* [Billy] 2007/05/16 */
+               /* VideoDebugPrint((0, "XGI_GetVCLKLen: pVBInfo->IF_DEF_CH7007==1\n")); */
+               *di_0 = (unsigned char) XGI_CH7007VCLKData[tempal].SR2B;
+               *di_1 = (unsigned char) XGI_CH7007VCLKData[tempal].SR2C;
+       } else if (pVBInfo->VBType & (VB_XGI301 | VB_XGI301B | VB_XGI302B
+                       | VB_XGI301LV | VB_XGI302LV | VB_XGI301C)) {
+               if ((!(pVBInfo->VBInfo & SetCRT2ToLCDA)) && (pVBInfo->SetFlag
+                               & ProgrammingCRT2)) {
+                       *di_0 = (unsigned char) XGI_VBVCLKData[tempal].SR2B;
+                       *di_1 = XGI_VBVCLKData[tempal].SR2C;
+               }
+       } else {
+               *di_0 = XGI_VCLKData[tempal].SR2B;
+               *di_1 = XGI_VCLKData[tempal].SR2C;
+       }
 }
-#endif
 
-unsigned char XGI_SetCRT2Group301(unsigned short ModeNo,
-               struct xgi_hw_device_info *HwDeviceExtension,
+static void XGI_SetCRT2ECLK(unsigned short ModeNo, unsigned short ModeIdIndex,
+               unsigned short RefreshRateTableIndex,
                struct vb_device_info *pVBInfo)
 {
-       unsigned short tempbx, ModeIdIndex, RefreshRateTableIndex;
+       unsigned char di_0, di_1, tempal;
+       int i;
 
-       tempbx = pVBInfo->VBInfo;
-       pVBInfo->SetFlag |= ProgrammingCRT2;
-       XGI_SearchModeID(ModeNo, &ModeIdIndex, pVBInfo);
-       pVBInfo->SelectCRT2Rate = 4;
-       RefreshRateTableIndex = XGI_GetRatePtrCRT2(HwDeviceExtension, ModeNo,
-                       ModeIdIndex, pVBInfo);
-       XGI_SaveCRT2Info(ModeNo, pVBInfo);
-       XGI_GetCRT2ResInfo(ModeNo, ModeIdIndex, pVBInfo);
-       XGI_GetCRT2Data(ModeNo, ModeIdIndex, RefreshRateTableIndex, pVBInfo);
-       XGI_PreSetGroup1(ModeNo, ModeIdIndex, HwDeviceExtension,
-                       RefreshRateTableIndex, pVBInfo);
-       XGI_SetGroup1(ModeNo, ModeIdIndex, HwDeviceExtension,
-                       RefreshRateTableIndex, pVBInfo);
-       XGI_SetLockRegs(ModeNo, ModeIdIndex, HwDeviceExtension,
-                       RefreshRateTableIndex, pVBInfo);
-       XGI_SetGroup2(ModeNo, ModeIdIndex, RefreshRateTableIndex,
-                       HwDeviceExtension, pVBInfo);
-       XGI_SetLCDRegs(ModeNo, ModeIdIndex, HwDeviceExtension,
-                       RefreshRateTableIndex, pVBInfo);
-       XGI_SetTap4Regs(pVBInfo);
-       XGI_SetGroup3(ModeNo, ModeIdIndex, pVBInfo);
-       XGI_SetGroup4(ModeNo, ModeIdIndex, RefreshRateTableIndex,
-                       HwDeviceExtension, pVBInfo);
-       XGI_SetCRT2VCLK(ModeNo, ModeIdIndex, RefreshRateTableIndex, pVBInfo);
-       XGI_SetGroup5(ModeNo, ModeIdIndex, pVBInfo);
-       XGI_AutoThreshold(pVBInfo);
-       return 1;
+       tempal = XGI_GetVCLKPtr(RefreshRateTableIndex, ModeNo, ModeIdIndex,
+                       pVBInfo);
+       XGI_GetVCLKLen(tempal, &di_0, &di_1, pVBInfo);
+       XGI_GetLCDVCLKPtr(&di_0, &di_1, pVBInfo);
+
+       for (i = 0; i < 4; i++) {
+               XGINew_SetRegANDOR(pVBInfo->P3d4, 0x31, ~0x30,
+                               (unsigned short) (0x10 * i));
+               if (pVBInfo->IF_DEF_CH7007 == 1) {
+                       XGINew_SetReg1(pVBInfo->P3c4, 0x2b, di_0);
+                       XGINew_SetReg1(pVBInfo->P3c4, 0x2c, di_1);
+               } else if ((!(pVBInfo->VBInfo & SetCRT2ToLCDA))
+                               && (!(pVBInfo->VBInfo & SetInSlaveMode))) {
+                       XGINew_SetReg1(pVBInfo->P3c4, 0x2e, di_0);
+                       XGINew_SetReg1(pVBInfo->P3c4, 0x2f, di_1);
+               } else {
+                       XGINew_SetReg1(pVBInfo->P3c4, 0x2b, di_0);
+                       XGINew_SetReg1(pVBInfo->P3c4, 0x2c, di_1);
+               }
+       }
 }
 
-static void XGI_AutoThreshold(struct vb_device_info *pVBInfo)
+static void XGI_UpdateModeInfo(struct xgi_hw_device_info *HwDeviceExtension,
+               struct vb_device_info *pVBInfo)
 {
-       if (!(pVBInfo->SetFlag & Win9xDOSMode))
-               XGINew_SetRegOR(pVBInfo->Part1Port, 0x01, 0x40);
-}
+       unsigned short tempcl, tempch, temp, tempbl, tempax;
 
-static void XGI_SaveCRT2Info(unsigned short ModeNo, struct vb_device_info *pVBInfo)
-{
-       unsigned short temp1, temp2;
+       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
+                       | VB_XGI302LV | VB_XGI301C)) {
+               tempcl = 0;
+               tempch = 0;
+               temp = XGINew_GetReg1(pVBInfo->P3c4, 0x01);
 
-       XGINew_SetReg1(pVBInfo->P3d4, 0x34, ModeNo); /* reserve CR34 for CRT1 Mode No */
-       temp1 = (pVBInfo->VBInfo & SetInSlaveMode) >> 8;
-       temp2 = ~(SetInSlaveMode >> 8);
-       XGINew_SetRegANDOR(pVBInfo->P3d4, 0x31, temp2, temp1);
-}
+               if (!(temp & 0x20)) {
+                       temp = XGINew_GetReg1(pVBInfo->P3d4, 0x17);
+                       if (temp & 0x80) {
+                               if ((HwDeviceExtension->jChipType >= XG20)
+                                               || (HwDeviceExtension->jChipType
+                                                               >= XG40))
+                                       temp = XGINew_GetReg1(pVBInfo->P3d4,
+                                                       0x53);
+                               else
+                                       temp = XGINew_GetReg1(pVBInfo->P3d4,
+                                                       0x63);
 
-static void XGI_GetCRT2ResInfo(unsigned short ModeNo, unsigned short ModeIdIndex,
-               struct vb_device_info *pVBInfo)
-{
-       unsigned short xres, yres, modeflag, resindex;
+                               if (!(temp & 0x40))
+                                       tempcl |= ActiveCRT1;
+                       }
+               }
 
-       resindex = XGI_GetResInfo(ModeNo, ModeIdIndex, pVBInfo);
-       if (ModeNo <= 0x13) {
-               xres = pVBInfo->StResInfo[resindex].HTotal;
-               yres = pVBInfo->StResInfo[resindex].VTotal;
-               /* modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag; si+St_ResInfo */
-       } else {
-               xres = pVBInfo->ModeResInfo[resindex].HTotal; /* xres->ax */
-               yres = pVBInfo->ModeResInfo[resindex].VTotal; /* yres->bx */
-               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag; /* si+St_ModeFlag */
+               temp = XGINew_GetReg1(pVBInfo->Part1Port, 0x2e);
+               temp &= 0x0f;
 
-               /*
-               if (pVBInfo->IF_DEF_FSTN) {
-                       xres *= 2;
-                       yres *= 2;
-                } else {
-               */
-               if (modeflag & HalfDCLK)
-                       xres *= 2;
+               if (!(temp == 0x08)) {
+                       tempax = XGINew_GetReg1(pVBInfo->Part1Port, 0x13); /* Check ChannelA by Part1_13 [2003/10/03] */
+                       if (tempax & 0x04)
+                               tempcl = tempcl | ActiveLCD;
 
-               if (modeflag & DoubleScanMode)
-                       yres *= 2;
-               /* } */
-       }
+                       temp &= 0x05;
 
-       if (pVBInfo->VBInfo & SetCRT2ToLCD) {
-               if (pVBInfo->IF_DEF_LVDS == 0) {
-                       if (pVBInfo->LCDResInfo == Panel1600x1200) {
-                               if (!(pVBInfo->LCDInfo & LCDVESATiming)) {
-                                       if (yres == 1024)
-                                               yres = 1056;
+                       if (!(tempcl & ActiveLCD))
+                               if (temp == 0x01)
+                                       tempcl |= ActiveCRT2;
+
+                       if (temp == 0x04)
+                               tempcl |= ActiveLCD;
+
+                       if (temp == 0x05) {
+                               temp = XGINew_GetReg1(pVBInfo->Part2Port, 0x00);
+
+                               if (!(temp & 0x08))
+                                       tempch |= ActiveAVideo;
+
+                               if (!(temp & 0x04))
+                                       tempch |= ActiveSVideo;
+
+                               if (temp & 0x02)
+                                       tempch |= ActiveSCART;
+
+                               if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV) {
+                                       if (temp & 0x01)
+                                               tempch |= ActiveHiTV;
                                }
-                       }
 
-                       if (pVBInfo->LCDResInfo == Panel1280x1024) {
-                               if (yres == 400)
-                                       yres = 405;
-                               else if (yres == 350)
-                                       yres = 360;
+                               if (pVBInfo->VBInfo & SetCRT2ToYPbPr) {
+                                       temp = XGINew_GetReg1(
+                                                       pVBInfo->Part2Port,
+                                                       0x4d);
 
-                               if (pVBInfo->LCDInfo & LCDVESATiming) {
-                                       if (yres == 360)
-                                               yres = 375;
+                                       if (temp & 0x10)
+                                               tempch |= ActiveYPbPr;
                                }
+
+                               if (tempch != 0)
+                                       tempcl |= ActiveTV;
                        }
+               }
 
-                       if (pVBInfo->LCDResInfo == Panel1024x768) {
-                               if (!(pVBInfo->LCDInfo & LCDVESATiming)) {
-                                       if (!(pVBInfo->LCDInfo
-                                                       & LCDNonExpanding)) {
-                                               if (yres == 350)
-                                                       yres = 357;
-                                               else if (yres == 400)
-                                                       yres = 420;
-                                               else if (yres == 480)
-                                                       yres = 525;
-                                       }
-                               }
+               temp = XGINew_GetReg1(pVBInfo->P3d4, 0x3d);
+               if (tempcl & ActiveLCD) {
+                       if ((pVBInfo->SetFlag & ReserveTVOption)) {
+                               if (temp & ActiveTV)
+                                       tempcl |= ActiveTV;
                        }
                }
+               temp = tempcl;
+               tempbl = ~ModeSwitchStatus;
+               XGINew_SetRegANDOR(pVBInfo->P3d4, 0x3d, tempbl, temp);
 
-               if (xres == 720)
-                       xres = 640;
+               if (!(pVBInfo->SetFlag & ReserveTVOption))
+                       XGINew_SetReg1(pVBInfo->P3d4, 0x3e, tempch);
+       } else {
+               return;
        }
+}
 
-       pVBInfo->VGAHDE = xres;
-       pVBInfo->HDE = xres;
-       pVBInfo->VGAVDE = yres;
-       pVBInfo->VDE = yres;
+void XGI_GetVGAType(struct xgi_hw_device_info *HwDeviceExtension,
+               struct vb_device_info *pVBInfo)
+{
+       /*
+       if ( HwDeviceExtension->jChipType >= XG20 ) {
+               pVBInfo->Set_VGAType = XG20;
+       } else if (HwDeviceExtension->jChipType >= XG40) {
+               pVBInfo->Set_VGAType = VGA_XGI340;
+       }
+       */
+       pVBInfo->Set_VGAType = HwDeviceExtension->jChipType;
 }
 
-static unsigned char XGI_IsLCDDualLink(struct vb_device_info *pVBInfo)
+void XGI_GetVBType(struct vb_device_info *pVBInfo)
 {
+       unsigned short flag, tempbx, tempah;
 
-       if ((pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) &&
-                       (pVBInfo->LCDInfo & SetLCDDualLink)) /* shampoo0129 */
-               return 1;
+       if (pVBInfo->IF_DEF_CH7007 == 1) {
+               pVBInfo->VBType = VB_CH7007;
+               return;
+       }
+       if (pVBInfo->IF_DEF_LVDS == 0) {
+               tempbx = VB_XGI302B;
+               flag = XGINew_GetReg1(pVBInfo->Part4Port, 0x00);
+               if (flag != 0x02) {
+                       tempbx = VB_XGI301;
+                       flag = XGINew_GetReg1(pVBInfo->Part4Port, 0x01);
+                       if (flag >= 0xB0) {
+                               tempbx = VB_XGI301B;
+                               if (flag >= 0xC0) {
+                                       tempbx = VB_XGI301C;
+                                       if (flag >= 0xD0) {
+                                               tempbx = VB_XGI301LV;
+                                               if (flag >= 0xE0) {
+                                                       tempbx = VB_XGI302LV;
+                                                       tempah
+                                                                       = XGINew_GetReg1(
+                                                                                       pVBInfo->Part4Port,
+                                                                                       0x39);
+                                                       if (tempah != 0xFF)
+                                                               tempbx
+                                                                               = VB_XGI301C;
+                                               }
+                                       }
+                               }
+
+                               if (tempbx & (VB_XGI301B | VB_XGI302B)) {
+                                       flag = XGINew_GetReg1(
+                                                       pVBInfo->Part4Port,
+                                                       0x23);
+
+                                       if (!(flag & 0x02))
+                                               tempbx = tempbx | VB_NoLCD;
+                               }
+                       }
+               }
+               pVBInfo->VBType = tempbx;
+       }
+       /*
+       else if (pVBInfo->IF_DEF_CH7017 == 1)
+               pVBInfo->VBType = VB_CH7017;
+       else //LVDS
+               pVBInfo->VBType = VB_LVDS_NS;
+        */
 
-       return 0;
 }
 
-static void XGI_GetCRT2Data(unsigned short ModeNo, unsigned short ModeIdIndex,
-               unsigned short RefreshRateTableIndex,
+void XGI_GetVBInfo(unsigned short ModeNo, unsigned short ModeIdIndex,
+               struct xgi_hw_device_info *HwDeviceExtension,
                struct vb_device_info *pVBInfo)
 {
-       unsigned short tempax = 0, tempbx, modeflag, resinfo;
+       unsigned short tempax, push, tempbx, temp, modeflag;
 
-       struct XGI_LCDDataStruct *LCDPtr = NULL;
-       struct XGI_TVDataStruct *TVPtr = NULL;
+       if (ModeNo <= 0x13)
+               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag;
+       else
+               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
 
-       if (ModeNo <= 0x13) {
-               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag; /* si+St_ResInfo */
-               resinfo = pVBInfo->SModeIDTable[ModeIdIndex].St_ResInfo;
-       } else {
-               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag; /* si+Ext_ResInfo */
-               resinfo = pVBInfo->EModeIDTable[ModeIdIndex].Ext_RESINFO;
-       }
+       pVBInfo->SetFlag = 0;
+       pVBInfo->ModeType = modeflag & ModeInfoFlag;
+       tempbx = 0;
+
+       if (pVBInfo->VBType & 0xFFFF) {
+               temp = XGINew_GetReg1(pVBInfo->P3d4, 0x30); /* Check Display Device */
+               tempbx = tempbx | temp;
+               temp = XGINew_GetReg1(pVBInfo->P3d4, 0x31);
+               push = temp;
+               push = push << 8;
+               tempax = temp << 8;
+               tempbx = tempbx | tempax;
+               temp = (SetCRT2ToDualEdge | SetCRT2ToYPbPr | SetCRT2ToLCDA
+                               | SetInSlaveMode | DisableCRT2Display);
+               temp = 0xFFFF ^ temp;
+               tempbx &= temp;
+
+               temp = XGINew_GetReg1(pVBInfo->P3d4, 0x38);
+
+               if (pVBInfo->IF_DEF_LCDA == 1) {
+
+                       if ((pVBInfo->Set_VGAType >= XG20)
+                                       || (pVBInfo->Set_VGAType >= XG40)) {
+                               if (pVBInfo->IF_DEF_LVDS == 0) {
+                                       /* if ((pVBInfo->VBType & VB_XGI302B) || (pVBInfo->VBType & VB_XGI301LV) || (pVBInfo->VBType & VB_XGI302LV) || (pVBInfo->VBType & VB_XGI301C)) */
+                                       if (pVBInfo->VBType & (VB_XGI302B
+                                                       | VB_XGI301LV
+                                                       | VB_XGI302LV
+                                                       | VB_XGI301C)) {
+                                               if (temp & EnableDualEdge) {
+                                                       tempbx
+                                                                       |= SetCRT2ToDualEdge;
 
-       pVBInfo->NewFlickerMode = 0;
-       pVBInfo->RVBHRS = 50;
+                                                       if (temp & SetToLCDA)
+                                                               tempbx
+                                                                               |= SetCRT2ToLCDA;
+                                               }
+                                       }
+                               } else if (pVBInfo->IF_DEF_CH7017 == 1) {
+                                       if (pVBInfo->VBType & VB_CH7017) {
+                                               if (temp & EnableDualEdge) {
+                                                       tempbx
+                                                                       |= SetCRT2ToDualEdge;
 
-       if (pVBInfo->VBInfo & SetCRT2ToRAMDAC) {
-               XGI_GetRAMDAC2DATA(ModeNo, ModeIdIndex, RefreshRateTableIndex,
-                               pVBInfo);
-               return;
-       }
+                                                       if (temp & SetToLCDA)
+                                                               tempbx
+                                                                               |= SetCRT2ToLCDA;
+                                               }
+                                       }
+                               }
+                       }
+               }
 
-       tempbx = 4;
+               if (pVBInfo->IF_DEF_YPbPr == 1) {
+                       if (((pVBInfo->IF_DEF_LVDS == 0) && ((pVBInfo->VBType
+                                       & VB_XGI301LV) || (pVBInfo->VBType
+                                       & VB_XGI302LV) || (pVBInfo->VBType
+                                       & VB_XGI301C)))
+                                       || ((pVBInfo->IF_DEF_CH7017 == 1)
+                                                       && (pVBInfo->VBType
+                                                                       & VB_CH7017))
+                                       || ((pVBInfo->IF_DEF_CH7007 == 1)
+                                                       && (pVBInfo->VBType
+                                                                       & VB_CH7007))) { /* [Billy] 07/05/04 */
+                               if (temp & SetYPbPr) { /* temp = CR38 */
+                                       if (pVBInfo->IF_DEF_HiVision == 1) {
+                                               temp = XGINew_GetReg1(
+                                                               pVBInfo->P3d4,
+                                                               0x35); /* shampoo add for new scratch */
+                                               temp &= YPbPrMode;
+                                               tempbx |= SetCRT2ToHiVisionTV;
 
-       if (pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
-               LCDPtr = (struct XGI_LCDDataStruct *) XGI_GetLcdPtr(tempbx,
-                               ModeNo, ModeIdIndex, RefreshRateTableIndex,
-                               pVBInfo);
+                                               if (temp != YPbPrMode1080i) {
+                                                       tempbx
+                                                                       &= (~SetCRT2ToHiVisionTV);
+                                                       tempbx
+                                                                       |= SetCRT2ToYPbPr;
+                                               }
+                                       }
 
-               pVBInfo->RVBHCMAX = LCDPtr->RVBHCMAX;
-               pVBInfo->RVBHCFACT = LCDPtr->RVBHCFACT;
-               pVBInfo->VGAHT = LCDPtr->VGAHT;
-               pVBInfo->VGAVT = LCDPtr->VGAVT;
-               pVBInfo->HT = LCDPtr->LCDHT;
-               pVBInfo->VT = LCDPtr->LCDVT;
+                                       /* tempbx |= SetCRT2ToYPbPr; */
+                               }
+                       }
+               }
 
-               if (pVBInfo->LCDResInfo == Panel1024x768) {
-                       tempax = 1024;
-                       tempbx = 768;
+               tempax = push; /* restore CR31 */
 
-                       if (!(pVBInfo->LCDInfo & LCDVESATiming)) {
-                               if (pVBInfo->VGAVDE == 357)
-                                       tempbx = 527;
-                               else if (pVBInfo->VGAVDE == 420)
-                                       tempbx = 620;
-                               else if (pVBInfo->VGAVDE == 525)
-                                       tempbx = 775;
-                               else if (pVBInfo->VGAVDE == 600)
-                                       tempbx = 775;
-                               /* else if (pVBInfo->VGAVDE==350) tempbx=560; */
-                               /* else if (pVBInfo->VGAVDE==400) tempbx=640; */
+               if (pVBInfo->IF_DEF_LVDS == 0) {
+                       if (pVBInfo->IF_DEF_YPbPr == 1) {
+                               if (pVBInfo->IF_DEF_HiVision == 1)
+                                       temp = 0x09FC;
                                else
-                                       tempbx = 768;
+                                       temp = 0x097C;
+                       } else {
+                               if (pVBInfo->IF_DEF_HiVision == 1)
+                                       temp = 0x01FC;
+                               else
+                                       temp = 0x017C;
+                       }
+               } else { /* 3nd party chip */
+                       if (pVBInfo->IF_DEF_CH7017 == 1)
+                               temp = (SetCRT2ToTV | SetCRT2ToLCD
+                                               | SetCRT2ToLCDA);
+                       else if (pVBInfo->IF_DEF_CH7007 == 1) { /* [Billy] 07/05/03 */
+                               temp = SetCRT2ToTV;
                        } else
-                               tempbx = 768;
-               } else if (pVBInfo->LCDResInfo == Panel1024x768x75) {
-                       tempax = 1024;
-                       tempbx = 768;
-               } else if (pVBInfo->LCDResInfo == Panel1280x1024) {
-                       tempax = 1280;
-                       if (pVBInfo->VGAVDE == 360)
-                               tempbx = 768;
-                       else if (pVBInfo->VGAVDE == 375)
-                               tempbx = 800;
-                       else if (pVBInfo->VGAVDE == 405)
-                               tempbx = 864;
-                       else
-                               tempbx = 1024;
-               } else if (pVBInfo->LCDResInfo == Panel1280x1024x75) {
-                       tempax = 1280;
-                       tempbx = 1024;
-               } else if (pVBInfo->LCDResInfo == Panel1280x960) {
-                       tempax = 1280;
-                       if (pVBInfo->VGAVDE == 350)
-                               tempbx = 700;
-                       else if (pVBInfo->VGAVDE == 400)
-                               tempbx = 800;
-                       else if (pVBInfo->VGAVDE == 1024)
-                               tempbx = 960;
-                       else
-                               tempbx = 960;
-               } else if (pVBInfo->LCDResInfo == Panel1400x1050) {
-                       tempax = 1400;
-                       tempbx = 1050;
+                               temp = SetCRT2ToLCD;
+               }
 
-                       if (pVBInfo->VGAVDE == 1024) {
-                               tempax = 1280;
-                               tempbx = 1024;
-                       }
-               } else if (pVBInfo->LCDResInfo == Panel1600x1200) {
-                       tempax = 1600;
-                       tempbx = 1200; /* alan 10/14/2003 */
-                       if (!(pVBInfo->LCDInfo & LCDVESATiming)) {
-                               if (pVBInfo->VGAVDE == 350)
-                                       tempbx = 875;
-                               else if (pVBInfo->VGAVDE == 400)
-                                       tempbx = 1000;
-                       }
+               if (!(tempbx & temp)) {
+                       tempax |= DisableCRT2Display;
+                       tempbx = 0;
                }
 
-               if (pVBInfo->LCDInfo & LCDNonExpanding) {
-                       tempax = pVBInfo->VGAHDE;
-                       tempbx = pVBInfo->VGAVDE;
+               if (pVBInfo->IF_DEF_LCDA == 1) { /* Select Display Device */
+                       if (!(pVBInfo->VBType & VB_NoLCD)) {
+                               if (tempbx & SetCRT2ToLCDA) {
+                                       if (tempbx & SetSimuScanMode)
+                                               tempbx
+                                                               &= (~(SetCRT2ToLCD
+                                                                               | SetCRT2ToRAMDAC
+                                                                               | SwitchToCRT2));
+                                       else
+                                               tempbx
+                                                               &= (~(SetCRT2ToLCD
+                                                                               | SetCRT2ToRAMDAC
+                                                                               | SetCRT2ToTV
+                                                                               | SwitchToCRT2));
+                               }
+                       }
                }
 
-               pVBInfo->HDE = tempax;
-               pVBInfo->VDE = tempbx;
-               return;
-       }
+               /* shampoo add */
+               if (!(tempbx & (SwitchToCRT2 | SetSimuScanMode))) { /* for driver abnormal */
+                       if (pVBInfo->IF_DEF_CRT2Monitor == 1) {
+                               if (tempbx & SetCRT2ToRAMDAC) {
+                                       tempbx &= (0xFF00 | SetCRT2ToRAMDAC
+                                                       | SwitchToCRT2
+                                                       | SetSimuScanMode);
+                                       tempbx &= (0x00FF | (~SetCRT2ToYPbPr));
+                               }
+                       } else {
+                               tempbx &= (~(SetCRT2ToRAMDAC | SetCRT2ToLCD
+                                               | SetCRT2ToTV));
+                       }
+               }
 
-       if (pVBInfo->VBInfo & (SetCRT2ToTV)) {
-               tempbx = 4;
-               TVPtr = (struct XGI_TVDataStruct *) XGI_GetTVPtr(tempbx,
-                               ModeNo, ModeIdIndex, RefreshRateTableIndex,
-                               pVBInfo);
+               if (!(pVBInfo->VBType & VB_NoLCD)) {
+                       if (tempbx & SetCRT2ToLCD) {
+                               tempbx &= (0xFF00 | SetCRT2ToLCD | SwitchToCRT2
+                                               | SetSimuScanMode);
+                               tempbx &= (0x00FF | (~SetCRT2ToYPbPr));
+                       }
+               }
 
-               pVBInfo->RVBHCMAX = TVPtr->RVBHCMAX;
-               pVBInfo->RVBHCFACT = TVPtr->RVBHCFACT;
-               pVBInfo->VGAHT = TVPtr->VGAHT;
-               pVBInfo->VGAVT = TVPtr->VGAVT;
-               pVBInfo->HDE = TVPtr->TVHDE;
-               pVBInfo->VDE = TVPtr->TVVDE;
-               pVBInfo->RVBHRS = TVPtr->RVBHRS;
-               pVBInfo->NewFlickerMode = TVPtr->FlickerMode;
+               if (tempbx & SetCRT2ToSCART) {
+                       tempbx &= (0xFF00 | SetCRT2ToSCART | SwitchToCRT2
+                                       | SetSimuScanMode);
+                       tempbx &= (0x00FF | (~SetCRT2ToYPbPr));
+               }
 
-               if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV) {
-                       if (resinfo == 0x08)
-                               pVBInfo->NewFlickerMode = 0x40;
-                       else if (resinfo == 0x09)
-                               pVBInfo->NewFlickerMode = 0x40;
-                       else if (resinfo == 0x12)
-                               pVBInfo->NewFlickerMode = 0x40;
+               if (pVBInfo->IF_DEF_YPbPr == 1) {
+                       if (tempbx & SetCRT2ToYPbPr)
+                               tempbx &= (0xFF00 | SwitchToCRT2
+                                               | SetSimuScanMode);
+               }
 
-                       if (pVBInfo->VGAVDE == 350)
-                               pVBInfo->TVInfo |= TVSimuMode;
+               if (pVBInfo->IF_DEF_HiVision == 1) {
+                       if (tempbx & SetCRT2ToHiVisionTV)
+                               tempbx &= (0xFF00 | SetCRT2ToHiVisionTV
+                                               | SwitchToCRT2
+                                               | SetSimuScanMode);
+               }
 
-                       tempax = ExtHiTVHT;
-                       tempbx = ExtHiTVVT;
+               if (tempax & DisableCRT2Display) { /* Set Display Device Info */
+                       if (!(tempbx & (SwitchToCRT2 | SetSimuScanMode)))
+                               tempbx = DisableCRT2Display;
+               }
 
-                       if (pVBInfo->VBInfo & SetInSlaveMode) {
-                               if (pVBInfo->TVInfo & TVSimuMode) {
-                                       tempax = StHiTVHT;
-                                       tempbx = StHiTVVT;
+               if (!(tempbx & DisableCRT2Display)) {
+                       if ((!(tempbx & DriverMode))
+                                       || (!(modeflag & CRT2Mode))) {
+                               if (pVBInfo->IF_DEF_LCDA == 1) {
+                                       if (!(tempbx & SetCRT2ToLCDA))
+                                               tempbx
+                                                               |= (SetInSlaveMode
+                                                                               | SetSimuScanMode);
+                               }
 
-                                       if (!(modeflag & Charx8Dot)) {
-                                               tempax = StHiTextTVHT;
-                                               tempbx = StHiTextTVVT;
+                               if (pVBInfo->IF_DEF_VideoCapture == 1) {
+                                       if (((HwDeviceExtension->jChipType
+                                                       == XG40)
+                                                       && (pVBInfo->Set_VGAType
+                                                                       == XG40))
+                                                       || ((HwDeviceExtension->jChipType
+                                                                       == XG41)
+                                                                       && (pVBInfo->Set_VGAType
+                                                                                       == XG41))
+                                                       || ((HwDeviceExtension->jChipType
+                                                                       == XG42)
+                                                                       && (pVBInfo->Set_VGAType
+                                                                                       == XG42))
+                                                       || ((HwDeviceExtension->jChipType
+                                                                       == XG45)
+                                                                       && (pVBInfo->Set_VGAType
+                                                                                       == XG45))) {
+                                               if (ModeNo <= 13) {
+                                                       if (!(tempbx
+                                                                       & SetCRT2ToRAMDAC)) { /*CRT2 not need to support*/
+                                                               tempbx
+                                                                               &= (0x00FF
+                                                                                               | (~SetInSlaveMode));
+                                                               pVBInfo->SetFlag
+                                                                               |= EnableVCMode;
+                                                       }
+                                               }
                                        }
                                }
                        }
-               } else if (pVBInfo->VBInfo & SetCRT2ToYPbPr) {
-                       if (pVBInfo->TVInfo & SetYPbPrMode750p) {
-                               tempax = YPbPrTV750pHT; /* Ext750pTVHT */
-                               tempbx = YPbPrTV750pVT; /* Ext750pTVVT */
-                       }
 
-                       if (pVBInfo->TVInfo & SetYPbPrMode525p) {
-                               tempax = YPbPrTV525pHT; /* Ext525pTVHT */
-                               tempbx = YPbPrTV525pVT; /* Ext525pTVVT */
-                       } else if (pVBInfo->TVInfo & SetYPbPrMode525i) {
-                               tempax = YPbPrTV525iHT; /* Ext525iTVHT */
-                               tempbx = YPbPrTV525iVT; /* Ext525iTVVT */
-                               if (pVBInfo->TVInfo & NTSC1024x768)
-                                       tempax = NTSC1024x768HT;
-                       }
-               } else {
-                       tempax = PALHT;
-                       tempbx = PALVT;
-                       if (!(pVBInfo->TVInfo & SetPALTV)) {
-                               tempax = NTSCHT;
-                               tempbx = NTSCVT;
-                               if (pVBInfo->TVInfo & NTSC1024x768)
-                                       tempax = NTSC1024x768HT;
+                       /* LCD+TV can't support in slave mode (Force LCDA+TV->LCDB) */
+                       if ((tempbx & SetInSlaveMode) && (tempbx
+                                       & SetCRT2ToLCDA)) {
+                               tempbx ^= (SetCRT2ToLCD | SetCRT2ToLCDA
+                                               | SetCRT2ToDualEdge);
+                               pVBInfo->SetFlag |= ReserveTVOption;
                        }
                }
-
-               pVBInfo->HT = tempax;
-               pVBInfo->VT = tempbx;
-               return;
        }
+
+       pVBInfo->VBInfo = tempbx;
 }
 
-static void XGI_SetCRT2VCLK(unsigned short ModeNo, unsigned short ModeIdIndex,
-               unsigned short RefreshRateTableIndex,
+void XGI_GetTVInfo(unsigned short ModeNo, unsigned short ModeIdIndex,
                struct vb_device_info *pVBInfo)
 {
-       unsigned char di_0, di_1, tempal;
-
-       tempal = XGI_GetVCLKPtr(RefreshRateTableIndex, ModeNo, ModeIdIndex,
-                       pVBInfo);
-       XGI_GetVCLKLen(tempal, &di_0, &di_1, pVBInfo);
-       XGI_GetLCDVCLKPtr(&di_0, &di_1, pVBInfo);
+       unsigned short temp, tempbx = 0, resinfo = 0, modeflag, index1;
 
-       if (pVBInfo->VBType & VB_XGI301) { /* shampoo 0129 */
-               /* 301 */
-               XGINew_SetReg1(pVBInfo->Part4Port, 0x0A, 0x10);
-               XGINew_SetReg1(pVBInfo->Part4Port, 0x0B, di_1);
-               XGINew_SetReg1(pVBInfo->Part4Port, 0x0A, di_0);
-       } else { /* 301b/302b/301lv/302lv */
-               XGINew_SetReg1(pVBInfo->Part4Port, 0x0A, di_0);
-               XGINew_SetReg1(pVBInfo->Part4Port, 0x0B, di_1);
-       }
+       tempbx = 0;
+       resinfo = 0;
 
-       XGINew_SetReg1(pVBInfo->Part4Port, 0x00, 0x12);
+       if (pVBInfo->VBInfo & SetCRT2ToTV) {
+               if (ModeNo <= 0x13) {
+                       modeflag
+                                       = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag; /* si+St_ModeFlag */
+                       resinfo = pVBInfo->SModeIDTable[ModeIdIndex].St_ResInfo; /* si+St_ResInfo */
+               } else {
+                       modeflag
+                                       = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
+                       resinfo
+                                       = pVBInfo->EModeIDTable[ModeIdIndex].Ext_RESINFO; /* si+Ext_ResInfo */
+               }
 
-       if (pVBInfo->VBInfo & SetCRT2ToRAMDAC)
-               XGINew_SetRegOR(pVBInfo->Part4Port, 0x12, 0x28);
-       else
-               XGINew_SetRegOR(pVBInfo->Part4Port, 0x12, 0x08);
-}
+               if (pVBInfo->VBInfo & SetCRT2ToTV) {
+                       temp = XGINew_GetReg1(pVBInfo->P3d4, 0x35);
+                       tempbx = temp;
+                       if (tempbx & SetPALTV) {
+                               tempbx &= (SetCHTVOverScan | SetPALMTV
+                                               | SetPALNTV | SetPALTV);
+                               if (tempbx & SetPALMTV)
+                                       tempbx &= ~SetPALTV; /* set to NTSC if PAL-M */
+                       } else
+                               tempbx &= (SetCHTVOverScan | SetNTSCJ
+                                               | SetPALTV);
+                       /*
+                       if (pVBInfo->IF_DEF_LVDS == 0) {
+                               index1 = XGINew_GetReg1(pVBInfo->P3d4, 0x38); //PAL-M/PAL-N Info
+                               temp2 = (index1 & 0xC0) >> 5; //00:PAL, 01:PAL-M, 10:PAL-N
+                               tempbx |= temp2;
+                               if (temp2 & 0x02)          //PAL-M
+                                       tempbx &= (~SetPALTV);
+                       }
+                       */
+               }
 
-/* --------------------------------------------------------------------- */
-/* Function : XGI_GETLCDVCLKPtr */
-/* Input : */
-/* Output : al -> VCLK Index */
-/* Description : */
-/* --------------------------------------------------------------------- */
-static void XGI_GetLCDVCLKPtr(unsigned char *di_0, unsigned char *di_1,
-               struct vb_device_info *pVBInfo)
-{
-       unsigned short index;
+               if (pVBInfo->IF_DEF_CH7017 == 1) {
+                       tempbx = XGINew_GetReg1(pVBInfo->P3d4, 0x35);
 
-       if (pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
-               if (pVBInfo->IF_DEF_ScaleLCD == 1) {
-                       if (pVBInfo->LCDInfo & EnableScalingLCD)
-                               return;
+                       if (tempbx & TVOverScan)
+                               tempbx |= SetCHTVOverScan;
                }
 
-               /* index = XGI_GetLCDCapPtr(pVBInfo); */
-               index = XGI_GetLCDCapPtr1(pVBInfo);
+               if (pVBInfo->IF_DEF_CH7007 == 1) { /* [Billy] 07/05/04 */
+                       tempbx = XGINew_GetReg1(pVBInfo->P3d4, 0x35);
 
-               if (pVBInfo->VBInfo & SetCRT2ToLCD) { /* LCDB */
-                       *di_0 = pVBInfo->LCDCapList[index].LCUCHAR_VCLKData1;
-                       *di_1 = pVBInfo->LCDCapList[index].LCUCHAR_VCLKData2;
-               } else { /* LCDA */
-                       *di_0 = pVBInfo->LCDCapList[index].LCDA_VCLKData1;
-                       *di_1 = pVBInfo->LCDCapList[index].LCDA_VCLKData2;
+                       if (tempbx & TVOverScan)
+                               tempbx |= SetCHTVOverScan;
                }
-       }
-       return;
-}
 
-static unsigned char XGI_GetVCLKPtr(unsigned short RefreshRateTableIndex,
-               unsigned short ModeNo, unsigned short ModeIdIndex,
-               struct vb_device_info *pVBInfo)
-{
+               if (pVBInfo->IF_DEF_LVDS == 0) {
+                       if (pVBInfo->VBInfo & SetCRT2ToSCART)
+                               tempbx |= SetPALTV;
+               }
 
-       unsigned short index, modeflag;
-       unsigned short tempbx;
-       unsigned char tempal;
-       unsigned char *CHTVVCLKPtr = NULL;
+               if (pVBInfo->IF_DEF_YPbPr == 1) {
+                       if (pVBInfo->VBInfo & SetCRT2ToYPbPr) {
+                               index1 = XGINew_GetReg1(pVBInfo->P3d4, 0x35);
+                               index1 &= YPbPrMode;
 
-       if (ModeNo <= 0x13)
-               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag; /* si+St_ResInfo */
-       else
-               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag; /* si+Ext_ResInfo */
+                               if (index1 == YPbPrMode525i)
+                                       tempbx |= SetYPbPrMode525i;
 
-       if ((pVBInfo->SetFlag & ProgrammingCRT2) && (!(pVBInfo->LCDInfo
-                       & EnableScalingLCD))) { /* {LCDA/LCDB} */
-               index = XGI_GetLCDCapPtr(pVBInfo);
-               tempal = pVBInfo->LCDCapList[index].LCD_VCLK;
+                               if (index1 == YPbPrMode525p)
+                                       tempbx = tempbx | SetYPbPrMode525p;
+                               if (index1 == YPbPrMode750p)
+                                       tempbx = tempbx | SetYPbPrMode750p;
+                       }
+               }
 
-               if (pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA))
-                       return tempal;
+               if (pVBInfo->IF_DEF_HiVision == 1) {
+                       if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV)
+                               tempbx = tempbx | SetYPbPrMode1080i | SetPALTV;
+               }
 
-               /* {TV} */
-               if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
-                               | VB_XGI302LV | VB_XGI301C)) {
-                       if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV) {
-                               tempal = HiTVVCLKDIV2;
-                               if (!(pVBInfo->TVInfo & RPLLDIV2XO))
-                                       tempal = HiTVVCLK;
-                               if (pVBInfo->TVInfo & TVSimuMode) {
-                                       tempal = HiTVSimuVCLK;
-                                       if (!(modeflag & Charx8Dot))
-                                               tempal = HiTVTextVCLK;
+               if (pVBInfo->IF_DEF_LVDS == 0) { /* shampoo */
+                       if ((pVBInfo->VBInfo & SetInSlaveMode)
+                                       && (!(pVBInfo->VBInfo & SetNotSimuMode)))
+                               tempbx |= TVSimuMode;
+
+                       if (!(tempbx & SetPALTV) && (modeflag > 13) && (resinfo
+                                       == 8)) /* NTSC 1024x768, */
+                               tempbx |= NTSC1024x768;
+
+                       tempbx |= RPLLDIV2XO;
 
+                       if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV) {
+                               if (pVBInfo->VBInfo & SetInSlaveMode)
+                                       tempbx &= (~RPLLDIV2XO);
+                       } else {
+                               if (tempbx & (SetYPbPrMode525p
+                                               | SetYPbPrMode750p))
+                                       tempbx &= (~RPLLDIV2XO);
+                               else if (!(pVBInfo->VBType & (VB_XGI301B
+                                               | VB_XGI302B | VB_XGI301LV
+                                               | VB_XGI302LV | VB_XGI301C))) {
+                                       if (tempbx & TVSimuMode)
+                                               tempbx &= (~RPLLDIV2XO);
                                }
-                               return tempal;
                        }
+               }
+       }
+       pVBInfo->TVInfo = tempbx;
+}
 
-                       if (pVBInfo->TVInfo & SetYPbPrMode750p) {
-                               tempal = YPbPr750pVCLK;
-                               return tempal;
-                       }
+unsigned char XGI_GetLCDInfo(unsigned short ModeNo, unsigned short ModeIdIndex,
+               struct vb_device_info *pVBInfo)
+{
+       unsigned short temp, tempax, tempbx, modeflag, resinfo = 0, LCDIdIndex;
 
-                       if (pVBInfo->TVInfo & SetYPbPrMode525p) {
-                               tempal = YPbPr525pVCLK;
-                               return tempal;
-                       }
+       pVBInfo->LCDResInfo = 0;
+       pVBInfo->LCDTypeInfo = 0;
+       pVBInfo->LCDInfo = 0;
 
-                       tempal = NTSC1024VCLK;
+       if (ModeNo <= 0x13) {
+               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag; /* si+St_ModeFlag // */
+       } else {
+               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
+               resinfo = pVBInfo->EModeIDTable[ModeIdIndex].Ext_RESINFO; /* si+Ext_ResInfo // */
+       }
 
-                       if (!(pVBInfo->TVInfo & NTSC1024x768)) {
-                               tempal = TVVCLKDIV2;
-                               if (!(pVBInfo->TVInfo & RPLLDIV2XO))
-                                       tempal = TVVCLK;
-                       }
+       temp = XGINew_GetReg1(pVBInfo->P3d4, 0x36); /* Get LCD Res.Info */
+       tempbx = temp & 0x0F;
 
-                       if (pVBInfo->VBInfo & SetCRT2ToTV)
-                               return tempal;
-               }
-               /* else if ((pVBInfo->IF_DEF_CH7017==1)&&(pVBInfo->VBType&VB_CH7017)) {
-                       if (ModeNo<=0x13)
-                               *tempal = pVBInfo->SModeIDTable[ModeIdIndex].St_CRT2CRTC;
+       if (tempbx == 0)
+               tempbx = Panel1024x768; /* default */
+
+       /* LCD75 [2003/8/22] Vicent */
+       if ((tempbx == Panel1024x768) || (tempbx == Panel1280x1024)) {
+               if (pVBInfo->VBInfo & DriverMode) {
+                       tempax = XGINew_GetReg1(pVBInfo->P3d4, 0x33);
+                       if (pVBInfo->VBInfo & SetCRT2ToLCDA)
+                               tempax &= 0x0F;
                        else
-                               *tempal = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT2CRTC;
-                       *tempal = *tempal & 0x1F;
-                       tempbx = 0;
-                       if (pVBInfo->TVInfo & SetPALTV)
-                               tempbx = tempbx + 2;
-                       if (pVBInfo->TVInfo & SetCHTVOverScan)
-                               tempbx++;
-                       tempbx = tempbx << 1;
-               } */
-       } /* {End of VB} */
+                               tempax = tempax >> 4;
 
-       if ((pVBInfo->IF_DEF_CH7007 == 1) && (pVBInfo->VBType & VB_CH7007)) { /* [Billy] 07/05/08 CH7007 */
-               /* VideoDebugPrint((0, "XGI_GetVCLKPtr: pVBInfo->IF_DEF_CH7007==1\n")); */
-               if ((pVBInfo->VBInfo & SetCRT2ToTV)) {
-                       if (ModeNo <= 0x13) {
-                               tempal
-                                               = pVBInfo->SModeIDTable[ModeIdIndex].St_CRT2CRTC;
-                       } else {
-                               tempal
-                                               = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT2CRTC;
+                       if ((resinfo == 6) || (resinfo == 9)) {
+                               if (tempax >= 3)
+                                       tempbx |= PanelRef75Hz;
+                       } else if ((resinfo == 7) || (resinfo == 8)) {
+                               if (tempax >= 4)
+                                       tempbx |= PanelRef75Hz;
                        }
+               }
+       }
 
-                       tempal = tempal & 0x0F;
-                       tempbx = 0;
-
-                       if (pVBInfo->TVInfo & SetPALTV)
-                               tempbx = tempbx + 2;
+       pVBInfo->LCDResInfo = tempbx;
 
-                       if (pVBInfo->TVInfo & SetCHTVOverScan)
-                               tempbx++;
+       /* End of LCD75 */
 
-                       /** tempbx = tempbx << 1; CH7007 ? **/
+       if (pVBInfo->IF_DEF_OEMUtil == 1)
+               pVBInfo->LCDTypeInfo = (temp & 0xf0) >> 4;
 
-                       /* [Billy]07/05/29 CH7007 */
-                       if (pVBInfo->IF_DEF_CH7007 == 1) {
-                               switch (tempbx) {
-                               case 0:
-                                       CHTVVCLKPtr = XGI7007_CHTVVCLKUNTSC;
-                                       break;
-                               case 1:
-                                       CHTVVCLKPtr = XGI7007_CHTVVCLKONTSC;
-                                       break;
-                               case 2:
-                                       CHTVVCLKPtr = XGI7007_CHTVVCLKUPAL;
-                                       break;
-                               case 3:
-                                       CHTVVCLKPtr = XGI7007_CHTVVCLKOPAL;
-                                       break;
-                               default:
-                                       break;
+       if (!(pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)))
+               return 0;
 
-                               }
-                       }
-                       /* else {
-                               switch(tempbx) {
-                               case 0:
-                                       CHTVVCLKPtr = pVBInfo->CHTVVCLKUNTSC;
-                                       break;
-                               case 1:
-                                       CHTVVCLKPtr = pVBInfo->CHTVVCLKONTSC;
-                                       break;
-                               case 2:
-                                       CHTVVCLKPtr = pVBInfo->CHTVVCLKUPAL;
-                                       break;
-                               case 3:
-                                       CHTVVCLKPtr = pVBInfo->CHTVVCLKOPAL;
-                                       break;
-                               default:
-                                       break;
-                               }
-                       }
-                       */
+       tempbx = 0;
 
-                       tempal = CHTVVCLKPtr[tempal];
-                       return tempal;
-               }
+       temp = XGINew_GetReg1(pVBInfo->P3d4, 0x37);
 
-       }
+       temp &= (ScalingLCD | LCDNonExpanding | LCDSyncBit | SetPWDEnable);
 
-       tempal = (unsigned char) XGINew_GetReg2((pVBInfo->P3ca + 0x02));
-       tempal = tempal >> 2;
-       tempal &= 0x03;
+       if ((pVBInfo->IF_DEF_ScaleLCD == 1) && (temp & LCDNonExpanding))
+               temp &= ~EnableScalingLCD;
 
-       if ((pVBInfo->LCDInfo & EnableScalingLCD) && (modeflag & Charx8Dot)) /* for Dot8 Scaling LCD */
-               tempal = tempal ^ tempal; /* ; set to VCLK25MHz always */
+       tempbx |= temp;
 
-       if (ModeNo <= 0x13)
-               return tempal;
+       LCDIdIndex = XGI_GetLCDCapPtr1(pVBInfo);
 
-       tempal = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRTVCLK;
-       return tempal;
-}
+       tempax = pVBInfo->LCDCapList[LCDIdIndex].LCD_Capability;
 
-static void XGI_GetVCLKLen(unsigned char tempal, unsigned char *di_0,
-               unsigned char *di_1, struct vb_device_info *pVBInfo)
-{
-       if (pVBInfo->IF_DEF_CH7007 == 1) { /* [Billy] 2007/05/16 */
-               /* VideoDebugPrint((0, "XGI_GetVCLKLen: pVBInfo->IF_DEF_CH7007==1\n")); */
-               *di_0 = (unsigned char) XGI_CH7007VCLKData[tempal].SR2B;
-               *di_1 = (unsigned char) XGI_CH7007VCLKData[tempal].SR2C;
-       } else if (pVBInfo->VBType & (VB_XGI301 | VB_XGI301B | VB_XGI302B
-                       | VB_XGI301LV | VB_XGI302LV | VB_XGI301C)) {
-               if ((!(pVBInfo->VBInfo & SetCRT2ToLCDA)) && (pVBInfo->SetFlag
-                               & ProgrammingCRT2)) {
-                       *di_0 = (unsigned char) XGI_VBVCLKData[tempal].SR2B;
-                       *di_1 = XGI_VBVCLKData[tempal].SR2C;
+       if (pVBInfo->IF_DEF_LVDS == 0) { /* shampoo */
+               if (((pVBInfo->VBType & VB_XGI302LV) || (pVBInfo->VBType
+                               & VB_XGI301C)) && (tempax & LCDDualLink)) {
+                       tempbx |= SetLCDDualLink;
                }
-       } else {
-               *di_0 = XGI_VCLKData[tempal].SR2B;
-               *di_1 = XGI_VCLKData[tempal].SR2C;
        }
-}
-
-static void XGI_SetCRT2Offset(unsigned short ModeNo,
-               unsigned short ModeIdIndex,
-               unsigned short RefreshRateTableIndex,
-               struct xgi_hw_device_info *HwDeviceExtension,
-               struct vb_device_info *pVBInfo)
-{
-       unsigned short offset;
-       unsigned char temp;
 
-       if (pVBInfo->VBInfo & SetInSlaveMode)
-               return;
+       if (pVBInfo->IF_DEF_CH7017 == 1) {
+               if (tempax & LCDDualLink)
+                       tempbx |= SetLCDDualLink;
+       }
 
-       offset = XGI_GetOffset(ModeNo, ModeIdIndex, RefreshRateTableIndex,
-                       HwDeviceExtension, pVBInfo);
-       temp = (unsigned char) (offset & 0xFF);
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x07, temp);
-       temp = (unsigned char) ((offset & 0xFF00) >> 8);
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x09, temp);
-       temp = (unsigned char) (((offset >> 3) & 0xFF) + 1);
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x03, temp);
-}
+       if (pVBInfo->IF_DEF_LVDS == 0) {
+               if ((pVBInfo->LCDResInfo == Panel1400x1050) && (pVBInfo->VBInfo
+                               & SetCRT2ToLCD) && (ModeNo > 0x13) && (resinfo
+                               == 9) && (!(tempbx & EnableScalingLCD)))
+                       tempbx |= SetLCDtoNonExpanding; /* set to center in 1280x1024 LCDB for Panel1400x1050 */
+       }
 
-static unsigned short XGI_GetOffset(unsigned short ModeNo, unsigned short ModeIdIndex,
-               unsigned short RefreshRateTableIndex,
-               struct xgi_hw_device_info *HwDeviceExtension,
-               struct vb_device_info *pVBInfo)
-{
-       unsigned short temp, colordepth, modeinfo, index, infoflag,
-                       ColorDepth[] = { 0x01, 0x02, 0x04 };
+       /*
+       if (tempax & LCDBToA) {
+               tempbx |= SetLCDBToA;
+       }
+       */
 
-       modeinfo = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeInfo;
-       if (ModeNo <= 0x14)
-               infoflag = 0;
-       else
-               infoflag = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_InfoFlag;
+       if (pVBInfo->IF_DEF_ExpLink == 1) {
+               if (modeflag & HalfDCLK) {
+                       /* if (!(pVBInfo->LCDInfo&LCDNonExpanding)) */
+                       if (!(tempbx & SetLCDtoNonExpanding)) {
+                               tempbx |= EnableLVDSDDA;
+                       } else {
+                               if (ModeNo > 0x13) {
+                                       if (pVBInfo->LCDResInfo
+                                                       == Panel1024x768) {
+                                               if (resinfo == 4) { /* 512x384  */
+                                                       tempbx |= EnableLVDSDDA;
+                                               }
+                                       }
+                               }
+                       }
+               }
+       }
 
-       index = (modeinfo >> 8) & 0xFF;
+       if (pVBInfo->VBInfo & SetInSlaveMode) {
+               if (pVBInfo->VBInfo & SetNotSimuMode)
+                       tempbx |= LCDVESATiming;
+       } else {
+               tempbx |= LCDVESATiming;
+       }
 
-       temp = pVBInfo->ScreenOffset[index];
+       pVBInfo->LCDInfo = tempbx;
 
-       if (infoflag & InterlaceMode)
-               temp = temp << 1;
+       if (pVBInfo->IF_DEF_PWD == 1) {
+               if (pVBInfo->LCDInfo & SetPWDEnable) {
+                       if ((pVBInfo->VBType & VB_XGI302LV) || (pVBInfo->VBType
+                                       & VB_XGI301C)) {
+                               if (!(tempax & PWDEnable))
+                                       pVBInfo->LCDInfo &= ~SetPWDEnable;
+                       }
+               }
+       }
 
-       colordepth = XGI_GetColorDepth(ModeNo, ModeIdIndex, pVBInfo);
+       if (pVBInfo->IF_DEF_LVDS == 0) {
+               if (tempax & (LockLCDBToA | StLCDBToA)) {
+                       if (pVBInfo->VBInfo & SetInSlaveMode) {
+                               if (!(tempax & LockLCDBToA)) {
+                                       if (ModeNo <= 0x13) {
+                                               pVBInfo->VBInfo
+                                                               &= ~(SetSimuScanMode
+                                                                               | SetInSlaveMode
+                                                                               | SetCRT2ToLCD);
+                                               pVBInfo->VBInfo
+                                                               |= SetCRT2ToLCDA
+                                                                               | SetCRT2ToDualEdge;
+                                       }
+                               }
+                       }
+               }
+       }
 
-       if ((ModeNo >= 0x7C) && (ModeNo <= 0x7E)) {
-               temp = ModeNo - 0x7C;
-               colordepth = ColorDepth[temp];
-               temp = 0x6B;
-               if (infoflag & InterlaceMode)
-                       temp = temp << 1;
-               return temp * colordepth;
-       } else {
-               return temp * colordepth;
+       /*
+       if (pVBInfo->IF_DEF_LVDS == 0) {
+               if (tempax & (LockLCDBToA | StLCDBToA)) {
+                       if (pVBInfo->VBInfo & SetInSlaveMode) {
+                               if (!((!(tempax & LockLCDBToA)) && (ModeNo > 0x13))) {
+                                       pVBInfo->VBInfo&=~(SetSimuScanMode|SetInSlaveMode|SetCRT2ToLCD);
+                                       pVBInfo->VBInfo|=SetCRT2ToLCDA|SetCRT2ToDualEdge;
+                               }
+                       }
+               }
        }
-}
+       */
 
-static void XGI_SetCRT2FIFO(struct vb_device_info *pVBInfo)
-{
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x01, 0x3B); /* threshold high ,disable auto threshold */
-       XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x02, ~(0x3F), 0x04); /* threshold low default 04h */
+       return 1;
 }
 
-static void XGI_PreSetGroup1(unsigned short ModeNo, unsigned short ModeIdIndex,
-               struct xgi_hw_device_info *HwDeviceExtension,
-               unsigned short RefreshRateTableIndex,
-               struct vb_device_info *pVBInfo)
+unsigned char XGI_SearchModeID(unsigned short ModeNo,
+               unsigned short *ModeIdIndex, struct vb_device_info *pVBInfo)
 {
-       unsigned short tempcx = 0, CRT1Index = 0, resinfo = 0;
+       if (ModeNo <= 5)
+               ModeNo |= 1;
+       if (ModeNo <= 0x13) {
+               /* for (*ModeIdIndex=0; *ModeIdIndex < sizeof(pVBInfo->SModeIDTable) / sizeof(struct XGI_StStruct); (*ModeIdIndex)++) */
+               for (*ModeIdIndex = 0;; (*ModeIdIndex)++) {
+                       if (pVBInfo->SModeIDTable[*ModeIdIndex].St_ModeID == ModeNo)
+                               break;
+                       if (pVBInfo->SModeIDTable[*ModeIdIndex].St_ModeID == 0xFF)
+                               return 0;
+               }
 
-       if (ModeNo > 0x13) {
-               CRT1Index = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT1CRTC;
-               CRT1Index &= IndexMask;
-               resinfo = pVBInfo->EModeIDTable[ModeIdIndex].Ext_RESINFO;
+               if (ModeNo == 0x07)
+                       (*ModeIdIndex)++; /* 400 lines */
+               if (ModeNo <= 3)
+                       (*ModeIdIndex) += 2; /* 400 lines */
+               /* else 350 lines */
+       } else {
+               /* for (*ModeIdIndex=0; *ModeIdIndex < sizeof(pVBInfo->EModeIDTable) / sizeof(struct XGI_ExtStruct); (*ModeIdIndex)++) */
+               for (*ModeIdIndex = 0;; (*ModeIdIndex)++) {
+                       if (pVBInfo->EModeIDTable[*ModeIdIndex].Ext_ModeID == ModeNo)
+                               break;
+                       if (pVBInfo->EModeIDTable[*ModeIdIndex].Ext_ModeID == 0xFF)
+                               return 0;
+               }
        }
 
-       XGI_SetCRT2Offset(ModeNo, ModeIdIndex, RefreshRateTableIndex,
-                       HwDeviceExtension, pVBInfo);
-       XGI_SetCRT2FIFO(pVBInfo);
-       /* XGI_SetCRT2Sync(ModeNo,RefreshRateTableIndex); */
-
-       for (tempcx = 4; tempcx < 7; tempcx++)
-               XGINew_SetReg1(pVBInfo->Part1Port, tempcx, 0x0);
-
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x50, 0x00);
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x02, 0x44); /* temp 0206 */
+       return 1;
 }
 
-static void XGI_SetGroup1(unsigned short ModeNo, unsigned short ModeIdIndex,
+/* win2000 MM adapter not support standard mode! */
+
+#if 0
+static unsigned char XGINew_CheckMemorySize(
                struct xgi_hw_device_info *HwDeviceExtension,
-               unsigned short RefreshRateTableIndex,
+               unsigned short ModeNo,
+               unsigned short ModeIdIndex,
                struct vb_device_info *pVBInfo)
 {
-       unsigned short temp = 0, tempax = 0, tempbx = 0, tempcx = 0,
-                       pushbx = 0, CRT1Index = 0, modeflag, resinfo = 0;
+       unsigned short memorysize, modeflag, temp, temp1, tmp;
 
-       if (ModeNo > 0x13) {
-               CRT1Index = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT1CRTC;
-               CRT1Index &= IndexMask;
-               resinfo = pVBInfo->EModeIDTable[ModeIdIndex].Ext_RESINFO;
+       /*
+       if ((HwDeviceExtension->jChipType == XGI_650) ||
+       (HwDeviceExtension->jChipType == XGI_650M)) {
+               return 1;
        }
+       */
 
        if (ModeNo <= 0x13)
                modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag;
        else
                modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
 
-       /* bainy change table name */
-       if (modeflag & HalfDCLK) {
-               temp = (pVBInfo->VGAHT / 2 - 1) & 0x0FF; /* BTVGA2HT 0x08,0x09 */
-               XGINew_SetReg1(pVBInfo->Part1Port, 0x08, temp);
-               temp = (((pVBInfo->VGAHT / 2 - 1) & 0xFF00) >> 8) << 4;
-               XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x09, ~0x0F0, temp);
-               temp = (pVBInfo->VGAHDE / 2 + 16) & 0x0FF; /* BTVGA2HDEE 0x0A,0x0C */
-               XGINew_SetReg1(pVBInfo->Part1Port, 0x0A, temp);
-               tempcx = ((pVBInfo->VGAHT - pVBInfo->VGAHDE) / 2) >> 2;
-               pushbx = pVBInfo->VGAHDE / 2 + 16;
-               tempcx = tempcx >> 1;
-               tempbx = pushbx + tempcx; /* bx BTVGA@HRS 0x0B,0x0C */
-               tempcx += tempbx;
+       /* ModeType = modeflag&ModeInfoFlag; // Get mode type */
 
-               if (pVBInfo->VBInfo & SetCRT2ToRAMDAC) {
-                       tempbx = pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[4];
-                       tempbx |= ((pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[14]
-                                                       & 0xC0) << 2);
-                       tempbx = (tempbx - 3) << 3; /* (VGAHRS-3)*8 */
-                       tempcx = pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[5];
-                       tempcx &= 0x1F;
-                       temp = pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[15];
-                       temp = (temp & 0x04) << (5 - 2); /* VGAHRE D[5] */
-                       tempcx = ((tempcx | temp) - 3) << 3; /* (VGAHRE-3)*8 */
-               }
+       memorysize = modeflag & MemoryInfoFlag;
+       memorysize = memorysize > MemorySizeShift;
+       memorysize++; /* Get memory size */
 
-               tempbx += 4;
-               tempcx += 4;
+       temp = XGINew_GetReg1(pVBInfo->P3c4, 0x14); /* Get DRAM Size */
+       tmp = temp;
 
-               if (tempcx > (pVBInfo->VGAHT / 2))
-                       tempcx = pVBInfo->VGAHT / 2;
+       if (HwDeviceExtension->jChipType == XG40) {
+               temp = 1 << ((temp & 0x0F0) >> 4); /* memory size per channel SR14[7:4] */
+               if ((tmp & 0x0c) == 0x0C) { /* Qual channels */
+                       temp <<= 2;
+               } else if ((tmp & 0x0c) == 0x08) { /* Dual channels */
+                       temp <<= 1;
+               }
+       } else if (HwDeviceExtension->jChipType == XG42) {
+               temp = 1 << ((temp & 0x0F0) >> 4); /* memory size per channel SR14[7:4] */
+               if ((tmp & 0x04) == 0x04) { /* Dual channels */
+                       temp <<= 1;
+               }
+       } else if (HwDeviceExtension->jChipType == XG45) {
+               temp = 1 << ((temp & 0x0F0) >> 4); /* memory size per channel SR14[7:4] */
+               if ((tmp & 0x0c) == 0x0C) { /* Qual channels */
+                       temp <<= 2;
+               } else if ((tmp & 0x0c) == 0x08) { /* triple channels */
+                       temp1 = temp;
+                       temp <<= 1;
+                       temp += temp1;
+               } else if ((tmp & 0x0c) == 0x04) { /* Dual channels */
+                       temp <<= 1;
+               }
+       }
+       if (temp < memorysize)
+               return 0;
+       else
+               return 1;
+}
+#endif
 
-               temp = tempbx & 0x00FF;
+/*
+void XGINew_IsLowResolution(unsigned short ModeNo, unsigned short ModeIdIndex, unsigned char XGINew_CheckMemorySize(struct xgi_hw_device_info *HwDeviceExtension, unsigned short ModeNo, unsigned short ModeIdIndex, struct vb_device_info *pVBInfo)
+{
+       unsigned short data ;
+       unsigned short ModeFlag ;
 
-               XGINew_SetReg1(pVBInfo->Part1Port, 0x0B, temp);
-       } else {
-               temp = (pVBInfo->VGAHT - 1) & 0x0FF; /* BTVGA2HT 0x08,0x09 */
-               XGINew_SetReg1(pVBInfo->Part1Port, 0x08, temp);
-               temp = (((pVBInfo->VGAHT - 1) & 0xFF00) >> 8) << 4;
-               XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x09, ~0x0F0, temp);
-               temp = (pVBInfo->VGAHDE + 16) & 0x0FF; /* BTVGA2HDEE 0x0A,0x0C */
-               XGINew_SetReg1(pVBInfo->Part1Port, 0x0A, temp);
-               tempcx = (pVBInfo->VGAHT - pVBInfo->VGAHDE) >> 2; /* cx */
-               pushbx = pVBInfo->VGAHDE + 16;
-               tempcx = tempcx >> 1;
-               tempbx = pushbx + tempcx; /* bx BTVGA@HRS 0x0B,0x0C */
-               tempcx += tempbx;
+       data = XGINew_GetReg1(pVBInfo->P3c4, 0x0F);
+       data &= 0x7F;
+       XGINew_SetReg1(pVBInfo->P3c4, 0x0F, data);
 
-               if (pVBInfo->VBInfo & SetCRT2ToRAMDAC) {
-                       tempbx = pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[3];
-                       tempbx |= ((pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[5]
-                                                       & 0xC0) << 2);
-                       tempbx = (tempbx - 3) << 3; /* (VGAHRS-3)*8 */
-                       tempcx = pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[4];
-                       tempcx &= 0x1F;
-                       temp = pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[6];
-                       temp = (temp & 0x04) << (5 - 2); /* VGAHRE D[5] */
-                       tempcx = ((tempcx | temp) - 3) << 3; /* (VGAHRE-3)*8 */
-                       tempbx += 16;
-                       tempcx += 16;
+       if (ModeNo > 0x13) {
+               ModeFlag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
+               if ((ModeFlag & HalfDCLK) && (ModeFlag & DoubleScanMode)) {
+                       data = XGINew_GetReg1(pVBInfo->P3c4, 0x0F);
+                       data |= 0x80;
+                       XGINew_SetReg1(pVBInfo->P3c4, 0x0F, data);
+                       data = XGINew_GetReg1(pVBInfo->P3c4, 0x01);
+                       data &= 0xF7;
+                       XGINew_SetReg1(pVBInfo->P3c4, 0x01, data);
                }
+       }
+}
+*/
 
-               if (tempcx > pVBInfo->VGAHT)
-                       tempcx = pVBInfo->VGAHT;
+static unsigned char XG21GPIODataTransfer(unsigned char ujDate)
+{
+       unsigned char ujRet = 0;
+       unsigned char i = 0;
 
-               temp = tempbx & 0x00FF;
-               XGINew_SetReg1(pVBInfo->Part1Port, 0x0B, temp);
+       for (i = 0; i < 8; i++) {
+               ujRet = ujRet << 1;
+               /* ujRet |= GETBITS(ujDate >> i, 0:0); */
+               ujRet |= (ujDate >> i) & 1;
        }
 
-       tempax = (tempax & 0x00FF) | (tempbx & 0xFF00);
-       tempbx = pushbx;
-       tempbx = (tempbx & 0x00FF) | ((tempbx & 0xFF00) << 4);
-       tempax |= (tempbx & 0xFF00);
-       temp = (tempax & 0xFF00) >> 8;
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x0C, temp);
-       temp = tempcx & 0x00FF;
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x0D, temp);
-       tempcx = (pVBInfo->VGAVT - 1);
-       temp = tempcx & 0x00FF;
+       return ujRet;
+}
 
-       if (pVBInfo->IF_DEF_CH7005 == 1) {
-               if (pVBInfo->VBInfo & 0x0C)
-                       temp--;
-       }
+/*----------------------------------------------------------------------------*/
+/* output                                                                     */
+/*      bl[5] : LVDS signal                                                   */
+/*      bl[1] : LVDS backlight                                                */
+/*      bl[0] : LVDS VDD                                                      */
+/*----------------------------------------------------------------------------*/
+static unsigned char XGI_XG21GetPSCValue(struct vb_device_info *pVBInfo)
+{
+       unsigned char CR4A, temp;
 
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x0E, temp);
-       tempbx = pVBInfo->VGAVDE - 1;
-       temp = tempbx & 0x00FF;
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x0F, temp);
-       temp = ((tempbx & 0xFF00) << 3) >> 8;
-       temp |= ((tempcx & 0xFF00) >> 8);
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x12, temp);
+       CR4A = XGINew_GetReg1(pVBInfo->P3d4, 0x4A);
+       XGINew_SetRegAND(pVBInfo->P3d4, 0x4A, ~0x23); /* enable GPIO write */
 
-       tempax = pVBInfo->VGAVDE;
-       tempbx = pVBInfo->VGAVDE;
-       tempcx = pVBInfo->VGAVT;
-       tempbx = (pVBInfo->VGAVT + pVBInfo->VGAVDE) >> 1; /* BTVGA2VRS 0x10,0x11 */
-       tempcx = ((pVBInfo->VGAVT - pVBInfo->VGAVDE) >> 4) + tempbx + 1; /* BTVGA2VRE 0x11 */
+       temp = XGINew_GetReg1(pVBInfo->P3d4, 0x48);
 
-       if (pVBInfo->VBInfo & SetCRT2ToRAMDAC) {
-               tempbx = pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[10];
-               temp = pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[9];
+       temp = XG21GPIODataTransfer(temp);
+       temp &= 0x23;
+       XGINew_SetReg1(pVBInfo->P3d4, 0x4A, CR4A);
+       return temp;
+}
+
+/*----------------------------------------------------------------------------*/
+/* output                                                                     */
+/*      bl[5] : LVDS signal                                                   */
+/*      bl[1] : LVDS backlight                                                */
+/*      bl[0] : LVDS VDD                                                      */
+/*----------------------------------------------------------------------------*/
+static unsigned char XGI_XG27GetPSCValue(struct vb_device_info *pVBInfo)
+{
+       unsigned char CR4A, CRB4, temp;
 
-               if (temp & 0x04)
-                       tempbx |= 0x0100;
+       CR4A = XGINew_GetReg1(pVBInfo->P3d4, 0x4A);
+       XGINew_SetRegAND(pVBInfo->P3d4, 0x4A, ~0x0C); /* enable GPIO write */
 
-               if (temp & 0x080)
-                       tempbx |= 0x0200;
+       temp = XGINew_GetReg1(pVBInfo->P3d4, 0x48);
 
-               temp = pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[14];
+       temp &= 0x0C;
+       temp >>= 2;
+       XGINew_SetReg1(pVBInfo->P3d4, 0x4A, CR4A);
+       CRB4 = XGINew_GetReg1(pVBInfo->P3d4, 0xB4);
+       temp |= ((CRB4 & 0x04) << 3);
+       return temp;
+}
 
-               if (temp & 0x08)
-                       tempbx |= 0x0400;
+void XGI_DisplayOn(struct xgi_hw_device_info *pXGIHWDE,
+               struct vb_device_info *pVBInfo)
+{
+
+       XGINew_SetRegANDOR(pVBInfo->P3c4, 0x01, 0xDF, 0x00);
+       if (pXGIHWDE->jChipType == XG21) {
+               if (pVBInfo->IF_DEF_LVDS == 1) {
+                       if (!(XGI_XG21GetPSCValue(pVBInfo) & 0x1)) {
+                               XGI_XG21BLSignalVDD(0x01, 0x01, pVBInfo); /* LVDS VDD on */
+                               XGI_XG21SetPanelDelay(2, pVBInfo);
+                       }
+                       if (!(XGI_XG21GetPSCValue(pVBInfo) & 0x20))
+                               XGI_XG21BLSignalVDD(0x20, 0x20, pVBInfo); /* LVDS signal on */
+                       XGI_XG21SetPanelDelay(3, pVBInfo);
+                       XGI_XG21BLSignalVDD(0x02, 0x02, pVBInfo); /* LVDS backlight on */
+               } else {
+                       XGI_XG21BLSignalVDD(0x20, 0x20, pVBInfo); /* DVO/DVI signal on */
+               }
 
-               temp = pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[11];
-               tempcx = (tempcx & 0xFF00) | (temp & 0x00FF);
        }
 
-       temp = tempbx & 0x00FF;
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x10, temp);
-       temp = ((tempbx & 0xFF00) >> 8) << 4;
-       temp = ((tempcx & 0x000F) | (temp));
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x11, temp);
-       tempax = 0;
+       if (pVBInfo->IF_DEF_CH7007 == 1) { /* [Billy] 07/05/23 For CH7007 */
 
-       if (modeflag & DoubleScanMode)
-               tempax |= 0x80;
+       }
 
-       if (modeflag & HalfDCLK)
-               tempax |= 0x40;
+       if (pXGIHWDE->jChipType == XG27) {
+               if (pVBInfo->IF_DEF_LVDS == 1) {
+                       if (!(XGI_XG27GetPSCValue(pVBInfo) & 0x1)) {
+                               XGI_XG27BLSignalVDD(0x01, 0x01, pVBInfo); /* LVDS VDD on */
+                               XGI_XG21SetPanelDelay(2, pVBInfo);
+                       }
+                       if (!(XGI_XG27GetPSCValue(pVBInfo) & 0x20))
+                               XGI_XG27BLSignalVDD(0x20, 0x20, pVBInfo); /* LVDS signal on */
+                       XGI_XG21SetPanelDelay(3, pVBInfo);
+                       XGI_XG27BLSignalVDD(0x02, 0x02, pVBInfo); /* LVDS backlight on */
+               } else {
+                       XGI_XG27BLSignalVDD(0x20, 0x20, pVBInfo); /* DVO/DVI signal on */
+               }
 
-       XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x2C, ~0x0C0, tempax);
+       }
 }
 
-static void XGI_SetLockRegs(unsigned short ModeNo, unsigned short ModeIdIndex,
-               struct xgi_hw_device_info *HwDeviceExtension,
-               unsigned short RefreshRateTableIndex,
+void XGI_DisplayOff(struct xgi_hw_device_info *pXGIHWDE,
                struct vb_device_info *pVBInfo)
 {
-       unsigned short push1, push2, tempax, tempbx = 0, tempcx, temp, resinfo,
-                       modeflag, CRT1Index;
 
-       if (ModeNo <= 0x13) {
-               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag; /* si+St_ResInfo */
-               resinfo = pVBInfo->SModeIDTable[ModeIdIndex].St_ResInfo;
-       } else {
-               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag; /* si+Ext_ResInfo */
-               resinfo = pVBInfo->EModeIDTable[ModeIdIndex].Ext_RESINFO;
-               CRT1Index = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT1CRTC;
-               CRT1Index &= IndexMask;
+       if (pXGIHWDE->jChipType == XG21) {
+               if (pVBInfo->IF_DEF_LVDS == 1) {
+                       XGI_XG21BLSignalVDD(0x02, 0x00, pVBInfo); /* LVDS backlight off */
+                       XGI_XG21SetPanelDelay(3, pVBInfo);
+               } else {
+                       XGI_XG21BLSignalVDD(0x20, 0x00, pVBInfo); /* DVO/DVI signal off */
+               }
        }
 
-       if (!(pVBInfo->VBInfo & SetInSlaveMode))
-               return;
-
-       temp = 0xFF; /* set MAX HT */
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x03, temp);
-       /* if (modeflag & Charx8Dot) */
-       /*      tempcx = 0x08; */
-       /* else */
-       tempcx = 0x08;
-
-       if (pVBInfo->VBType & (VB_XGI301LV | VB_XGI302LV | VB_XGI301C))
-               modeflag |= Charx8Dot;
+       if (pVBInfo->IF_DEF_CH7007 == 1) { /* [Billy] 07/05/23 For CH7007 */
+               /* if (IsCH7007TVMode(pVBInfo) == 0) */
+               {
+               }
+       }
 
-       tempax = pVBInfo->VGAHDE; /* 0x04 Horizontal Display End */
+       if (pXGIHWDE->jChipType == XG27) {
+               if ((XGI_XG27GetPSCValue(pVBInfo) & 0x2)) {
+                       XGI_XG27BLSignalVDD(0x02, 0x00, pVBInfo); /* LVDS backlight off */
+                       XGI_XG21SetPanelDelay(3, pVBInfo);
+               }
 
-       if (modeflag & HalfDCLK)
-               tempax = tempax >> 1;
+               if (pVBInfo->IF_DEF_LVDS == 0)
+                       XGI_XG27BLSignalVDD(0x20, 0x00, pVBInfo); /* DVO/DVI signal off */
+       }
 
-       tempax = (tempax / tempcx) - 1;
-       tempbx |= ((tempax & 0x00FF) << 8);
-       temp = tempax & 0x00FF;
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x04, temp);
+       XGINew_SetRegANDOR(pVBInfo->P3c4, 0x01, 0xDF, 0x20);
+}
 
-       temp = (tempbx & 0xFF00) >> 8;
+static void XGI_WaitDisply(struct vb_device_info *pVBInfo)
+{
+       while ((XGINew_GetReg2(pVBInfo->P3da) & 0x01))
+               break;
 
-       if (pVBInfo->VBInfo & SetCRT2ToTV) {
-               if (!(pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
-                               | VB_XGI302LV | VB_XGI301C)))
-                       temp += 2;
+       while (!(XGINew_GetReg2(pVBInfo->P3da) & 0x01))
+               break;
+}
 
-               if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV) {
-                       if (pVBInfo->VBType & VB_XGI301LV) {
-                               if (pVBInfo->VBExtInfo == VB_YPbPr1080i) {
-                                       if (resinfo == 7)
-                                               temp -= 2;
-                               }
-                       } else if (resinfo == 7) {
-                               temp -= 2;
-                       }
-               }
-       }
+#if 0
+static void XGI_WaitDisplay(struct vb_device_info *pVBInfo)
+{
+       while (!(XGINew_GetReg2(pVBInfo->P3da) & 0x01));
+       while (XGINew_GetReg2(pVBInfo->P3da) & 0x01);
+}
+#endif
 
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x05, temp); /* 0x05 Horizontal Display Start */
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x06, 0x03); /* 0x06 Horizontal Blank end */
+static void XGI_AutoThreshold(struct vb_device_info *pVBInfo)
+{
+       if (!(pVBInfo->SetFlag & Win9xDOSMode))
+               XGINew_SetRegOR(pVBInfo->Part1Port, 0x01, 0x40);
+}
 
-       if (!(pVBInfo->VBInfo & DisableCRT2Display)) { /* 030226 bainy */
-               if (pVBInfo->VBInfo & SetCRT2ToTV)
-                       tempax = pVBInfo->VGAHT;
-               else
-                       tempax = XGI_GetVGAHT2(pVBInfo);
-       }
+static void XGI_SaveCRT2Info(unsigned short ModeNo, struct vb_device_info *pVBInfo)
+{
+       unsigned short temp1, temp2;
 
-       if (tempax >= pVBInfo->VGAHT)
-               tempax = pVBInfo->VGAHT;
+       XGINew_SetReg1(pVBInfo->P3d4, 0x34, ModeNo); /* reserve CR34 for CRT1 Mode No */
+       temp1 = (pVBInfo->VBInfo & SetInSlaveMode) >> 8;
+       temp2 = ~(SetInSlaveMode >> 8);
+       XGINew_SetRegANDOR(pVBInfo->P3d4, 0x31, temp2, temp1);
+}
 
-       if (modeflag & HalfDCLK)
-               tempax = tempax >> 1;
+static void XGI_GetCRT2ResInfo(unsigned short ModeNo, unsigned short ModeIdIndex,
+               struct vb_device_info *pVBInfo)
+{
+       unsigned short xres, yres, modeflag, resindex;
 
-       tempax = (tempax / tempcx) - 5;
-       tempcx = tempax; /* 20030401 0x07 horizontal Retrace Start */
-       if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV) {
-               temp = (tempbx & 0x00FF) - 1;
-               if (!(modeflag & HalfDCLK)) {
-                       temp -= 6;
-                       if (pVBInfo->TVInfo & TVSimuMode) {
-                               temp -= 4;
-                               if (ModeNo > 0x13)
-                                       temp -= 10;
-                       }
-               }
+       resindex = XGI_GetResInfo(ModeNo, ModeIdIndex, pVBInfo);
+       if (ModeNo <= 0x13) {
+               xres = pVBInfo->StResInfo[resindex].HTotal;
+               yres = pVBInfo->StResInfo[resindex].VTotal;
+               /* modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag; si+St_ResInfo */
        } else {
-               /* tempcx = tempbx & 0x00FF ; */
-               tempbx = (tempbx & 0xFF00) >> 8;
-               tempcx = (tempcx + tempbx) >> 1;
-               temp = (tempcx & 0x00FF) + 2;
-
-               if (pVBInfo->VBInfo & SetCRT2ToTV) {
-                       temp -= 1;
-                       if (!(modeflag & HalfDCLK)) {
-                               if ((modeflag & Charx8Dot)) {
-                                       temp += 4;
-                                       if (pVBInfo->VGAHDE >= 800)
-                                               temp -= 6;
-                               }
-                       }
-               } else {
-                       if (!(modeflag & HalfDCLK)) {
-                               temp -= 4;
-                               if (pVBInfo->LCDResInfo != Panel1280x960) {
-                                       if (pVBInfo->VGAHDE >= 800) {
-                                               temp -= 7;
-                                               if (pVBInfo->ModeType
-                                                               == ModeEGA) {
-                                                       if (pVBInfo->VGAVDE
-                                                                       == 1024) {
-                                                               temp += 15;
-                                                               if (pVBInfo->LCDResInfo
-                                                                               != Panel1280x1024) {
-                                                                       temp
-                                                                                       += 7;
-                                                               }
-                                                       }
-                                               }
-
-                                               if (pVBInfo->VGAHDE >= 1280) {
-                                                       if (pVBInfo->LCDResInfo
-                                                                       != Panel1280x960) {
-                                                               if (pVBInfo->LCDInfo
-                                                                               & LCDNonExpanding) {
-                                                                       temp
-                                                                                       += 28;
-                                                               }
-                                                       }
-                                               }
-                                       }
-                               }
-                       }
-               }
-       }
+               xres = pVBInfo->ModeResInfo[resindex].HTotal; /* xres->ax */
+               yres = pVBInfo->ModeResInfo[resindex].VTotal; /* yres->bx */
+               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag; /* si+St_ModeFlag */
 
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x07, temp); /* 0x07 Horizontal Retrace Start */
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x08, 0); /* 0x08 Horizontal Retrace End */
+               /*
+               if (pVBInfo->IF_DEF_FSTN) {
+                       xres *= 2;
+                       yres *= 2;
+                } else {
+               */
+               if (modeflag & HalfDCLK)
+                       xres *= 2;
 
-       if (pVBInfo->VBInfo & SetCRT2ToTV) {
-               if (pVBInfo->TVInfo & TVSimuMode) {
-                       if ((ModeNo == 0x06) || (ModeNo == 0x10) || (ModeNo
-                                       == 0x11) || (ModeNo == 0x13) || (ModeNo
-                                       == 0x0F)) {
-                               XGINew_SetReg1(pVBInfo->Part1Port, 0x07, 0x5b);
-                               XGINew_SetReg1(pVBInfo->Part1Port, 0x08, 0x03);
-                       }
+               if (modeflag & DoubleScanMode)
+                       yres *= 2;
+               /* } */
+       }
 
-                       if ((ModeNo == 0x00) || (ModeNo == 0x01)) {
-                               if (pVBInfo->TVInfo & SetNTSCTV) {
-                                       XGINew_SetReg1(pVBInfo->Part1Port,
-                                                       0x07, 0x2A);
-                                       XGINew_SetReg1(pVBInfo->Part1Port,
-                                                       0x08, 0x61);
-                               } else {
-                                       XGINew_SetReg1(pVBInfo->Part1Port,
-                                                       0x07, 0x2A);
-                                       XGINew_SetReg1(pVBInfo->Part1Port,
-                                                       0x08, 0x41);
-                                       XGINew_SetReg1(pVBInfo->Part1Port,
-                                                       0x0C, 0xF0);
+       if (pVBInfo->VBInfo & SetCRT2ToLCD) {
+               if (pVBInfo->IF_DEF_LVDS == 0) {
+                       if (pVBInfo->LCDResInfo == Panel1600x1200) {
+                               if (!(pVBInfo->LCDInfo & LCDVESATiming)) {
+                                       if (yres == 1024)
+                                               yres = 1056;
                                }
                        }
 
-                       if ((ModeNo == 0x02) || (ModeNo == 0x03) || (ModeNo
-                                       == 0x07)) {
-                               if (pVBInfo->TVInfo & SetNTSCTV) {
-                                       XGINew_SetReg1(pVBInfo->Part1Port,
-                                                       0x07, 0x54);
-                                       XGINew_SetReg1(pVBInfo->Part1Port,
-                                                       0x08, 0x00);
-                               } else {
-                                       XGINew_SetReg1(pVBInfo->Part1Port,
-                                                       0x07, 0x55);
-                                       XGINew_SetReg1(pVBInfo->Part1Port,
-                                                       0x08, 0x00);
-                                       XGINew_SetReg1(pVBInfo->Part1Port,
-                                                       0x0C, 0xF0);
+                       if (pVBInfo->LCDResInfo == Panel1280x1024) {
+                               if (yres == 400)
+                                       yres = 405;
+                               else if (yres == 350)
+                                       yres = 360;
+
+                               if (pVBInfo->LCDInfo & LCDVESATiming) {
+                                       if (yres == 360)
+                                               yres = 375;
                                }
                        }
 
-                       if ((ModeNo == 0x04) || (ModeNo == 0x05) || (ModeNo
-                                       == 0x0D) || (ModeNo == 0x50)) {
-                               if (pVBInfo->TVInfo & SetNTSCTV) {
-                                       XGINew_SetReg1(pVBInfo->Part1Port,
-                                                       0x07, 0x30);
-                                       XGINew_SetReg1(pVBInfo->Part1Port,
-                                                       0x08, 0x03);
-                               } else {
-                                       XGINew_SetReg1(pVBInfo->Part1Port,
-                                                       0x07, 0x2f);
-                                       XGINew_SetReg1(pVBInfo->Part1Port,
-                                                       0x08, 0x02);
+                       if (pVBInfo->LCDResInfo == Panel1024x768) {
+                               if (!(pVBInfo->LCDInfo & LCDVESATiming)) {
+                                       if (!(pVBInfo->LCDInfo
+                                                       & LCDNonExpanding)) {
+                                               if (yres == 350)
+                                                       yres = 357;
+                                               else if (yres == 400)
+                                                       yres = 420;
+                                               else if (yres == 480)
+                                                       yres = 525;
+                                       }
                                }
                        }
                }
+
+               if (xres == 720)
+                       xres = 640;
        }
 
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x18, 0x03); /* 0x18 SR0B */
-       XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x19, 0xF0, 0x00);
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x09, 0xFF); /* 0x09 Set Max VT */
+       pVBInfo->VGAHDE = xres;
+       pVBInfo->HDE = xres;
+       pVBInfo->VGAVDE = yres;
+       pVBInfo->VDE = yres;
+}
 
-       tempbx = pVBInfo->VGAVT;
-       push1 = tempbx;
-       tempcx = 0x121;
-       tempbx = pVBInfo->VGAVDE; /* 0x0E Virtical Display End */
+static unsigned char XGI_IsLCDDualLink(struct vb_device_info *pVBInfo)
+{
 
-       if (tempbx == 357)
-               tempbx = 350;
-       if (tempbx == 360)
-               tempbx = 350;
-       if (tempbx == 375)
-               tempbx = 350;
-       if (tempbx == 405)
-               tempbx = 400;
-       if (tempbx == 525)
-               tempbx = 480;
+       if ((pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) &&
+                       (pVBInfo->LCDInfo & SetLCDDualLink)) /* shampoo0129 */
+               return 1;
 
-       push2 = tempbx;
+       return 0;
+}
+
+static void XGI_GetRAMDAC2DATA(unsigned short ModeNo, unsigned short ModeIdIndex,
+               unsigned short RefreshRateTableIndex,
+               struct vb_device_info *pVBInfo)
+{
+       unsigned short tempax, tempbx, temp1, temp2, modeflag = 0, tempcx,
+                       StandTableIndex, CRT1Index;
+
+       pVBInfo->RVBHCMAX = 1;
+       pVBInfo->RVBHCFACT = 1;
+
+       if (ModeNo <= 0x13) {
+               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag;
+               StandTableIndex = XGI_GetModePtr(ModeNo, ModeIdIndex, pVBInfo);
+               tempax = pVBInfo->StandTable[StandTableIndex].CRTC[0];
+               tempbx = pVBInfo->StandTable[StandTableIndex].CRTC[6];
+               temp1 = pVBInfo->StandTable[StandTableIndex].CRTC[7];
+       } else {
+               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
+               CRT1Index
+                               = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT1CRTC;
+               CRT1Index &= IndexMask;
+               temp1
+                               = (unsigned short) pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[0];
+               temp2
+                               = (unsigned short) pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[5];
+               tempax = (temp1 & 0xFF) | ((temp2 & 0x03) << 8);
+               tempbx
+                               = (unsigned short) pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[8];
+               tempcx
+                               = (unsigned short) pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[14]
+                                               << 8;
+               tempcx &= 0x0100;
+               tempcx = tempcx << 2;
+               tempbx |= tempcx;
+               temp1
+                               = (unsigned short) pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[9];
+       }
+
+       if (temp1 & 0x01)
+               tempbx |= 0x0100;
+
+       if (temp1 & 0x20)
+               tempbx |= 0x0200;
+       tempax += 5;
+
+       if (modeflag & Charx8Dot)
+               tempax *= 8;
+       else
+               tempax *= 9;
+
+       pVBInfo->VGAHT = tempax;
+       pVBInfo->HT = tempax;
+       tempbx++;
+       pVBInfo->VGAVT = tempbx;
+       pVBInfo->VT = tempbx;
+}
+
+static void XGI_GetCRT2Data(unsigned short ModeNo, unsigned short ModeIdIndex,
+               unsigned short RefreshRateTableIndex,
+               struct vb_device_info *pVBInfo)
+{
+       unsigned short tempax = 0, tempbx, modeflag, resinfo;
+
+       struct XGI_LCDDataStruct *LCDPtr = NULL;
+       struct XGI_TVDataStruct *TVPtr = NULL;
+
+       if (ModeNo <= 0x13) {
+               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag; /* si+St_ResInfo */
+               resinfo = pVBInfo->SModeIDTable[ModeIdIndex].St_ResInfo;
+       } else {
+               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag; /* si+Ext_ResInfo */
+               resinfo = pVBInfo->EModeIDTable[ModeIdIndex].Ext_RESINFO;
+       }
+
+       pVBInfo->NewFlickerMode = 0;
+       pVBInfo->RVBHRS = 50;
+
+       if (pVBInfo->VBInfo & SetCRT2ToRAMDAC) {
+               XGI_GetRAMDAC2DATA(ModeNo, ModeIdIndex, RefreshRateTableIndex,
+                               pVBInfo);
+               return;
+       }
+
+       tempbx = 4;
+
+       if (pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
+               LCDPtr = (struct XGI_LCDDataStruct *) XGI_GetLcdPtr(tempbx,
+                               ModeNo, ModeIdIndex, RefreshRateTableIndex,
+                               pVBInfo);
+
+               pVBInfo->RVBHCMAX = LCDPtr->RVBHCMAX;
+               pVBInfo->RVBHCFACT = LCDPtr->RVBHCFACT;
+               pVBInfo->VGAHT = LCDPtr->VGAHT;
+               pVBInfo->VGAVT = LCDPtr->VGAVT;
+               pVBInfo->HT = LCDPtr->LCDHT;
+               pVBInfo->VT = LCDPtr->LCDVT;
 
-       if (pVBInfo->VBInfo & SetCRT2ToLCD) {
                if (pVBInfo->LCDResInfo == Panel1024x768) {
+                       tempax = 1024;
+                       tempbx = 768;
+
+                       if (!(pVBInfo->LCDInfo & LCDVESATiming)) {
+                               if (pVBInfo->VGAVDE == 357)
+                                       tempbx = 527;
+                               else if (pVBInfo->VGAVDE == 420)
+                                       tempbx = 620;
+                               else if (pVBInfo->VGAVDE == 525)
+                                       tempbx = 775;
+                               else if (pVBInfo->VGAVDE == 600)
+                                       tempbx = 775;
+                               /* else if (pVBInfo->VGAVDE==350) tempbx=560; */
+                               /* else if (pVBInfo->VGAVDE==400) tempbx=640; */
+                               else
+                                       tempbx = 768;
+                       } else
+                               tempbx = 768;
+               } else if (pVBInfo->LCDResInfo == Panel1024x768x75) {
+                       tempax = 1024;
+                       tempbx = 768;
+               } else if (pVBInfo->LCDResInfo == Panel1280x1024) {
+                       tempax = 1280;
+                       if (pVBInfo->VGAVDE == 360)
+                               tempbx = 768;
+                       else if (pVBInfo->VGAVDE == 375)
+                               tempbx = 800;
+                       else if (pVBInfo->VGAVDE == 405)
+                               tempbx = 864;
+                       else
+                               tempbx = 1024;
+               } else if (pVBInfo->LCDResInfo == Panel1280x1024x75) {
+                       tempax = 1280;
+                       tempbx = 1024;
+               } else if (pVBInfo->LCDResInfo == Panel1280x960) {
+                       tempax = 1280;
+                       if (pVBInfo->VGAVDE == 350)
+                               tempbx = 700;
+                       else if (pVBInfo->VGAVDE == 400)
+                               tempbx = 800;
+                       else if (pVBInfo->VGAVDE == 1024)
+                               tempbx = 960;
+                       else
+                               tempbx = 960;
+               } else if (pVBInfo->LCDResInfo == Panel1400x1050) {
+                       tempax = 1400;
+                       tempbx = 1050;
+
+                       if (pVBInfo->VGAVDE == 1024) {
+                               tempax = 1280;
+                               tempbx = 1024;
+                       }
+               } else if (pVBInfo->LCDResInfo == Panel1600x1200) {
+                       tempax = 1600;
+                       tempbx = 1200; /* alan 10/14/2003 */
                        if (!(pVBInfo->LCDInfo & LCDVESATiming)) {
-                               if (tempbx == 350)
-                                       tempbx += 5;
-                               if (tempbx == 480)
-                                       tempbx += 5;
+                               if (pVBInfo->VGAVDE == 350)
+                                       tempbx = 875;
+                               else if (pVBInfo->VGAVDE == 400)
+                                       tempbx = 1000;
                        }
                }
-       }
-       tempbx--;
-       temp = tempbx & 0x00FF;
-       tempbx--;
-       temp = tempbx & 0x00FF;
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x10, temp); /* 0x10 vertical Blank Start */
-       tempbx = push2;
-       tempbx--;
-       temp = tempbx & 0x00FF;
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x0E, temp);
-
-       if (tempbx & 0x0100)
-               tempcx |= 0x0002;
-
-       tempax = 0x000B;
 
-       if (modeflag & DoubleScanMode)
-               tempax |= 0x08000;
+               if (pVBInfo->LCDInfo & LCDNonExpanding) {
+                       tempax = pVBInfo->VGAHDE;
+                       tempbx = pVBInfo->VGAVDE;
+               }
 
-       if (tempbx & 0x0200)
-               tempcx |= 0x0040;
+               pVBInfo->HDE = tempax;
+               pVBInfo->VDE = tempbx;
+               return;
+       }
 
-       temp = (tempax & 0xFF00) >> 8;
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x0B, temp);
+       if (pVBInfo->VBInfo & (SetCRT2ToTV)) {
+               tempbx = 4;
+               TVPtr = (struct XGI_TVDataStruct *) XGI_GetTVPtr(tempbx,
+                               ModeNo, ModeIdIndex, RefreshRateTableIndex,
+                               pVBInfo);
 
-       if (tempbx & 0x0400)
-               tempcx |= 0x0600;
+               pVBInfo->RVBHCMAX = TVPtr->RVBHCMAX;
+               pVBInfo->RVBHCFACT = TVPtr->RVBHCFACT;
+               pVBInfo->VGAHT = TVPtr->VGAHT;
+               pVBInfo->VGAVT = TVPtr->VGAVT;
+               pVBInfo->HDE = TVPtr->TVHDE;
+               pVBInfo->VDE = TVPtr->TVVDE;
+               pVBInfo->RVBHRS = TVPtr->RVBHRS;
+               pVBInfo->NewFlickerMode = TVPtr->FlickerMode;
 
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x11, 0x00); /* 0x11 Vertival Blank End */
+               if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV) {
+                       if (resinfo == 0x08)
+                               pVBInfo->NewFlickerMode = 0x40;
+                       else if (resinfo == 0x09)
+                               pVBInfo->NewFlickerMode = 0x40;
+                       else if (resinfo == 0x12)
+                               pVBInfo->NewFlickerMode = 0x40;
 
-       tempax = push1;
-       tempax -= tempbx; /* 0x0C Vertical Retrace Start */
-       tempax = tempax >> 2;
-       push1 = tempax; /* push ax */
+                       if (pVBInfo->VGAVDE == 350)
+                               pVBInfo->TVInfo |= TVSimuMode;
 
-       if (resinfo != 0x09) {
-               tempax = tempax << 1;
-               tempbx += tempax;
-       }
+                       tempax = ExtHiTVHT;
+                       tempbx = ExtHiTVVT;
 
-       if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV) {
-               if (pVBInfo->VBType & VB_XGI301LV) {
-                       if (pVBInfo->TVInfo & SetYPbPrMode1080i) {
-                               tempbx -= 10;
-                       } else {
+                       if (pVBInfo->VBInfo & SetInSlaveMode) {
                                if (pVBInfo->TVInfo & TVSimuMode) {
-                                       if (pVBInfo->TVInfo & SetPALTV) {
-                                               if (pVBInfo->VBType
-                                                               & VB_XGI301LV) {
-                                                       if (!(pVBInfo->TVInfo
-                                                                       & (SetYPbPrMode525p
-                                                                                       | SetYPbPrMode750p
-                                                                                       | SetYPbPrMode1080i)))
-                                                               tempbx += 40;
-                                               } else {
-                                                       tempbx += 40;
-                                               }
+                                       tempax = StHiTVHT;
+                                       tempbx = StHiTVVT;
+
+                                       if (!(modeflag & Charx8Dot)) {
+                                               tempax = StHiTextTVHT;
+                                               tempbx = StHiTextTVVT;
                                        }
                                }
                        }
+               } else if (pVBInfo->VBInfo & SetCRT2ToYPbPr) {
+                       if (pVBInfo->TVInfo & SetYPbPrMode750p) {
+                               tempax = YPbPrTV750pHT; /* Ext750pTVHT */
+                               tempbx = YPbPrTV750pVT; /* Ext750pTVVT */
+                       }
+
+                       if (pVBInfo->TVInfo & SetYPbPrMode525p) {
+                               tempax = YPbPrTV525pHT; /* Ext525pTVHT */
+                               tempbx = YPbPrTV525pVT; /* Ext525pTVVT */
+                       } else if (pVBInfo->TVInfo & SetYPbPrMode525i) {
+                               tempax = YPbPrTV525iHT; /* Ext525iTVHT */
+                               tempbx = YPbPrTV525iVT; /* Ext525iTVVT */
+                               if (pVBInfo->TVInfo & NTSC1024x768)
+                                       tempax = NTSC1024x768HT;
+                       }
                } else {
-                       tempbx -= 10;
-               }
-       } else {
-               if (pVBInfo->TVInfo & TVSimuMode) {
-                       if (pVBInfo->TVInfo & SetPALTV) {
-                               if (pVBInfo->VBType & VB_XGI301LV) {
-                                       if (!(pVBInfo->TVInfo
-                                                       & (SetYPbPrMode525p
-                                                                       | SetYPbPrMode750p
-                                                                       | SetYPbPrMode1080i)))
-                                               tempbx += 40;
-                               } else {
-                                       tempbx += 40;
-                               }
+                       tempax = PALHT;
+                       tempbx = PALVT;
+                       if (!(pVBInfo->TVInfo & SetPALTV)) {
+                               tempax = NTSCHT;
+                               tempbx = NTSCVT;
+                               if (pVBInfo->TVInfo & NTSC1024x768)
+                                       tempax = NTSC1024x768HT;
                        }
                }
-       }
-       tempax = push1;
-       tempax = tempax >> 2;
-       tempax++;
-       tempax += tempbx;
-       push1 = tempax; /* push ax */
 
-       if ((pVBInfo->TVInfo & SetPALTV)) {
-               if (tempbx <= 513) {
-                       if (tempax >= 513)
-                               tempbx = 513;
-               }
+               pVBInfo->HT = tempax;
+               pVBInfo->VT = tempbx;
+               return;
        }
-
-       temp = tempbx & 0x00FF;
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x0C, temp);
-       tempbx--;
-       temp = tempbx & 0x00FF;
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x10, temp);
-
-       if (tempbx & 0x0100)
-               tempcx |= 0x0008;
-
-       if (tempbx & 0x0200)
-               XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x0B, 0x0FF, 0x20);
-
-       tempbx++;
-
-       if (tempbx & 0x0100)
-               tempcx |= 0x0004;
-
-       if (tempbx & 0x0200)
-               tempcx |= 0x0080;
-
-       if (tempbx & 0x0400)
-               tempcx |= 0x0C00;
-
-       tempbx = push1; /* pop ax */
-       temp = tempbx & 0x00FF;
-       temp &= 0x0F;
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x0D, temp); /* 0x0D vertical Retrace End */
-
-       if (tempbx & 0x0010)
-               tempcx |= 0x2000;
-
-       temp = tempcx & 0x00FF;
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x0A, temp); /* 0x0A CR07 */
-       temp = (tempcx & 0x0FF00) >> 8;
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x17, temp); /* 0x17 SR0A */
-       tempax = modeflag;
-       temp = (tempax & 0xFF00) >> 8;
-
-       temp = (temp >> 1) & 0x09;
-
-       if (pVBInfo->VBType & (VB_XGI301LV | VB_XGI302LV | VB_XGI301C))
-               temp |= 0x01;
-
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x16, temp); /* 0x16 SR01 */
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x0F, 0); /* 0x0F CR14 */
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x12, 0); /* 0x12 CR17 */
-
-       if (pVBInfo->LCDInfo & LCDRGB18Bit)
-               temp = 0x80;
-       else
-               temp = 0x00;
-
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x1A, temp); /* 0x1A SR0E */
-
-       return;
 }
 
-static void XGI_SetGroup2(unsigned short ModeNo, unsigned short ModeIdIndex,
+static void XGI_SetCRT2VCLK(unsigned short ModeNo, unsigned short ModeIdIndex,
                unsigned short RefreshRateTableIndex,
-               struct xgi_hw_device_info *HwDeviceExtension,
                struct vb_device_info *pVBInfo)
 {
-       unsigned short i, j, tempax, tempbx, tempcx, temp, push1, push2,
-                       modeflag, resinfo, crt2crtc;
-       unsigned char *TimingPoint;
+       unsigned char di_0, di_1, tempal;
 
-       unsigned long longtemp, tempeax, tempebx, temp2, tempecx;
+       tempal = XGI_GetVCLKPtr(RefreshRateTableIndex, ModeNo, ModeIdIndex,
+                       pVBInfo);
+       XGI_GetVCLKLen(tempal, &di_0, &di_1, pVBInfo);
+       XGI_GetLCDVCLKPtr(&di_0, &di_1, pVBInfo);
 
-       if (ModeNo <= 0x13) {
-               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag; /* si+St_ResInfo */
-               resinfo = pVBInfo->SModeIDTable[ModeIdIndex].St_ResInfo;
-               crt2crtc = pVBInfo->SModeIDTable[ModeIdIndex].St_CRT2CRTC;
-       } else {
-               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag; /* si+Ext_ResInfo */
-               resinfo = pVBInfo->EModeIDTable[ModeIdIndex].Ext_RESINFO;
-               crt2crtc
-                               = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT2CRTC;
+       if (pVBInfo->VBType & VB_XGI301) { /* shampoo 0129 */
+               /* 301 */
+               XGINew_SetReg1(pVBInfo->Part4Port, 0x0A, 0x10);
+               XGINew_SetReg1(pVBInfo->Part4Port, 0x0B, di_1);
+               XGINew_SetReg1(pVBInfo->Part4Port, 0x0A, di_0);
+       } else { /* 301b/302b/301lv/302lv */
+               XGINew_SetReg1(pVBInfo->Part4Port, 0x0A, di_0);
+               XGINew_SetReg1(pVBInfo->Part4Port, 0x0B, di_1);
        }
 
-       tempax = 0;
-
-       if (!(pVBInfo->VBInfo & SetCRT2ToAVIDEO))
-               tempax |= 0x0800;
-
-       if (!(pVBInfo->VBInfo & SetCRT2ToSVIDEO))
-               tempax |= 0x0400;
-
-       if (pVBInfo->VBInfo & SetCRT2ToSCART)
-               tempax |= 0x0200;
+       XGINew_SetReg1(pVBInfo->Part4Port, 0x00, 0x12);
 
-       if (!(pVBInfo->TVInfo & SetPALTV))
-               tempax |= 0x1000;
+       if (pVBInfo->VBInfo & SetCRT2ToRAMDAC)
+               XGINew_SetRegOR(pVBInfo->Part4Port, 0x12, 0x28);
+       else
+               XGINew_SetRegOR(pVBInfo->Part4Port, 0x12, 0x08);
+}
 
-       if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV)
-               tempax |= 0x0100;
+static unsigned short XGI_GetColorDepth(unsigned short ModeNo,
+               unsigned short ModeIdIndex, struct vb_device_info *pVBInfo)
+{
+       unsigned short ColorDepth[6] = { 1, 2, 4, 4, 6, 8 };
+       short index;
+       unsigned short modeflag;
 
-       if (pVBInfo->TVInfo & (SetYPbPrMode525p | SetYPbPrMode750p))
-               tempax &= 0xfe00;
+       if (ModeNo <= 0x13)
+               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag;
+       else
+               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
 
-       tempax = (tempax & 0xff00) >> 8;
+       index = (modeflag & ModeInfoFlag) - ModeEGA;
 
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x0, tempax);
-       TimingPoint = pVBInfo->NTSCTiming;
+       if (index < 0)
+               index = 0;
 
-       if (pVBInfo->TVInfo & SetPALTV)
-               TimingPoint = pVBInfo->PALTiming;
+       return ColorDepth[index];
+}
 
-       if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV) {
-               TimingPoint = pVBInfo->HiTVExtTiming;
+static unsigned short XGI_GetOffset(unsigned short ModeNo, unsigned short ModeIdIndex,
+               unsigned short RefreshRateTableIndex,
+               struct xgi_hw_device_info *HwDeviceExtension,
+               struct vb_device_info *pVBInfo)
+{
+       unsigned short temp, colordepth, modeinfo, index, infoflag,
+                       ColorDepth[] = { 0x01, 0x02, 0x04 };
 
-               if (pVBInfo->VBInfo & SetInSlaveMode)
-                       TimingPoint = pVBInfo->HiTVSt2Timing;
+       modeinfo = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeInfo;
+       if (ModeNo <= 0x14)
+               infoflag = 0;
+       else
+               infoflag = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_InfoFlag;
 
-               if (pVBInfo->SetFlag & TVSimuMode)
-                       TimingPoint = pVBInfo->HiTVSt1Timing;
+       index = (modeinfo >> 8) & 0xFF;
 
-               if (!(modeflag & Charx8Dot))
-                       TimingPoint = pVBInfo->HiTVTextTiming;
-       }
+       temp = pVBInfo->ScreenOffset[index];
 
-       if (pVBInfo->VBInfo & SetCRT2ToYPbPr) {
-               if (pVBInfo->TVInfo & SetYPbPrMode525i)
-                       TimingPoint = pVBInfo->YPbPr525iTiming;
+       if (infoflag & InterlaceMode)
+               temp = temp << 1;
 
-               if (pVBInfo->TVInfo & SetYPbPrMode525p)
-                       TimingPoint = pVBInfo->YPbPr525pTiming;
+       colordepth = XGI_GetColorDepth(ModeNo, ModeIdIndex, pVBInfo);
 
-               if (pVBInfo->TVInfo & SetYPbPrMode750p)
-                       TimingPoint = pVBInfo->YPbPr750pTiming;
+       if ((ModeNo >= 0x7C) && (ModeNo <= 0x7E)) {
+               temp = ModeNo - 0x7C;
+               colordepth = ColorDepth[temp];
+               temp = 0x6B;
+               if (infoflag & InterlaceMode)
+                       temp = temp << 1;
+               return temp * colordepth;
+       } else {
+               return temp * colordepth;
        }
+}
 
-       for (i = 0x01, j = 0; i <= 0x2D; i++, j++)
-               XGINew_SetReg1(pVBInfo->Part2Port, i, TimingPoint[j]);
+static void XGI_SetCRT2Offset(unsigned short ModeNo,
+               unsigned short ModeIdIndex,
+               unsigned short RefreshRateTableIndex,
+               struct xgi_hw_device_info *HwDeviceExtension,
+               struct vb_device_info *pVBInfo)
+{
+       unsigned short offset;
+       unsigned char temp;
 
-       for (i = 0x39; i <= 0x45; i++, j++)
-               XGINew_SetReg1(pVBInfo->Part2Port, i, TimingPoint[j]); /* di->temp2[j] */
+       if (pVBInfo->VBInfo & SetInSlaveMode)
+               return;
 
-       if (pVBInfo->VBInfo & SetCRT2ToTV)
-               XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x3A, 0x1F, 0x00);
+       offset = XGI_GetOffset(ModeNo, ModeIdIndex, RefreshRateTableIndex,
+                       HwDeviceExtension, pVBInfo);
+       temp = (unsigned char) (offset & 0xFF);
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x07, temp);
+       temp = (unsigned char) ((offset & 0xFF00) >> 8);
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x09, temp);
+       temp = (unsigned char) (((offset >> 3) & 0xFF) + 1);
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x03, temp);
+}
 
-       temp = pVBInfo->NewFlickerMode;
-       temp &= 0x80;
-       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x0A, 0xFF, temp);
+static void XGI_SetCRT2FIFO(struct vb_device_info *pVBInfo)
+{
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x01, 0x3B); /* threshold high ,disable auto threshold */
+       XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x02, ~(0x3F), 0x04); /* threshold low default 04h */
+}
 
-       if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV)
-               tempax = 950;
+static void XGI_PreSetGroup1(unsigned short ModeNo, unsigned short ModeIdIndex,
+               struct xgi_hw_device_info *HwDeviceExtension,
+               unsigned short RefreshRateTableIndex,
+               struct vb_device_info *pVBInfo)
+{
+       unsigned short tempcx = 0, CRT1Index = 0, resinfo = 0;
 
-       if (pVBInfo->TVInfo & SetPALTV)
-               tempax = 520;
-       else
-               tempax = 440;
+       if (ModeNo > 0x13) {
+               CRT1Index = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT1CRTC;
+               CRT1Index &= IndexMask;
+               resinfo = pVBInfo->EModeIDTable[ModeIdIndex].Ext_RESINFO;
+       }
 
-       if (pVBInfo->VDE <= tempax) {
-               tempax -= pVBInfo->VDE;
-               tempax = tempax >> 2;
-               tempax = (tempax & 0x00FF) | ((tempax & 0x00FF) << 8);
-               push1 = tempax;
-               temp = (tempax & 0xFF00) >> 8;
-               temp += (unsigned short) TimingPoint[0];
+       XGI_SetCRT2Offset(ModeNo, ModeIdIndex, RefreshRateTableIndex,
+                       HwDeviceExtension, pVBInfo);
+       XGI_SetCRT2FIFO(pVBInfo);
+       /* XGI_SetCRT2Sync(ModeNo,RefreshRateTableIndex); */
 
-               if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
-                               | VB_XGI302LV | VB_XGI301C)) {
-                       if (pVBInfo->VBInfo & (SetCRT2ToAVIDEO
-                                       | SetCRT2ToSVIDEO | SetCRT2ToSCART
-                                       | SetCRT2ToYPbPr)) {
-                               tempcx = pVBInfo->VGAHDE;
-                               if (tempcx >= 1024) {
-                                       temp = 0x17; /* NTSC */
-                                       if (pVBInfo->TVInfo & SetPALTV)
-                                               temp = 0x19; /* PAL */
-                               }
-                       }
-               }
+       for (tempcx = 4; tempcx < 7; tempcx++)
+               XGINew_SetReg1(pVBInfo->Part1Port, tempcx, 0x0);
 
-               XGINew_SetReg1(pVBInfo->Part2Port, 0x01, temp);
-               tempax = push1;
-               temp = (tempax & 0xFF00) >> 8;
-               temp += TimingPoint[1];
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x50, 0x00);
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x02, 0x44); /* temp 0206 */
+}
 
-               if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
-                               | VB_XGI302LV | VB_XGI301C)) {
-                       if ((pVBInfo->VBInfo & (SetCRT2ToAVIDEO
-                                       | SetCRT2ToSVIDEO | SetCRT2ToSCART
-                                       | SetCRT2ToYPbPr))) {
-                               tempcx = pVBInfo->VGAHDE;
-                               if (tempcx >= 1024) {
-                                       temp = 0x1D; /* NTSC */
-                                       if (pVBInfo->TVInfo & SetPALTV)
-                                               temp = 0x52; /* PAL */
-                               }
-                       }
-               }
-               XGINew_SetReg1(pVBInfo->Part2Port, 0x02, temp);
+static void XGI_SetGroup1(unsigned short ModeNo, unsigned short ModeIdIndex,
+               struct xgi_hw_device_info *HwDeviceExtension,
+               unsigned short RefreshRateTableIndex,
+               struct vb_device_info *pVBInfo)
+{
+       unsigned short temp = 0, tempax = 0, tempbx = 0, tempcx = 0,
+                       pushbx = 0, CRT1Index = 0, modeflag, resinfo = 0;
+
+       if (ModeNo > 0x13) {
+               CRT1Index = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT1CRTC;
+               CRT1Index &= IndexMask;
+               resinfo = pVBInfo->EModeIDTable[ModeIdIndex].Ext_RESINFO;
        }
 
-       /* 301b */
-       tempcx = pVBInfo->HT;
+       if (ModeNo <= 0x13)
+               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag;
+       else
+               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
 
-       if (XGI_IsLCDDualLink(pVBInfo))
+       /* bainy change table name */
+       if (modeflag & HalfDCLK) {
+               temp = (pVBInfo->VGAHT / 2 - 1) & 0x0FF; /* BTVGA2HT 0x08,0x09 */
+               XGINew_SetReg1(pVBInfo->Part1Port, 0x08, temp);
+               temp = (((pVBInfo->VGAHT / 2 - 1) & 0xFF00) >> 8) << 4;
+               XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x09, ~0x0F0, temp);
+               temp = (pVBInfo->VGAHDE / 2 + 16) & 0x0FF; /* BTVGA2HDEE 0x0A,0x0C */
+               XGINew_SetReg1(pVBInfo->Part1Port, 0x0A, temp);
+               tempcx = ((pVBInfo->VGAHT - pVBInfo->VGAHDE) / 2) >> 2;
+               pushbx = pVBInfo->VGAHDE / 2 + 16;
                tempcx = tempcx >> 1;
+               tempbx = pushbx + tempcx; /* bx BTVGA@HRS 0x0B,0x0C */
+               tempcx += tempbx;
 
-       tempcx -= 2;
-       temp = tempcx & 0x00FF;
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x1B, temp);
+               if (pVBInfo->VBInfo & SetCRT2ToRAMDAC) {
+                       tempbx = pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[4];
+                       tempbx |= ((pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[14]
+                                                       & 0xC0) << 2);
+                       tempbx = (tempbx - 3) << 3; /* (VGAHRS-3)*8 */
+                       tempcx = pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[5];
+                       tempcx &= 0x1F;
+                       temp = pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[15];
+                       temp = (temp & 0x04) << (5 - 2); /* VGAHRE D[5] */
+                       tempcx = ((tempcx | temp) - 3) << 3; /* (VGAHRE-3)*8 */
+               }
 
-       temp = (tempcx & 0xFF00) >> 8;
-       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x1D, ~0x0F, temp);
+               tempbx += 4;
+               tempcx += 4;
 
-       tempcx = pVBInfo->HT >> 1;
-       push1 = tempcx; /* push cx */
-       tempcx += 7;
+               if (tempcx > (pVBInfo->VGAHT / 2))
+                       tempcx = pVBInfo->VGAHT / 2;
 
-       if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV)
-               tempcx -= 4;
+               temp = tempbx & 0x00FF;
 
-       temp = tempcx & 0x00FF;
-       temp = temp << 4;
-       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x22, 0x0F, temp);
+               XGINew_SetReg1(pVBInfo->Part1Port, 0x0B, temp);
+       } else {
+               temp = (pVBInfo->VGAHT - 1) & 0x0FF; /* BTVGA2HT 0x08,0x09 */
+               XGINew_SetReg1(pVBInfo->Part1Port, 0x08, temp);
+               temp = (((pVBInfo->VGAHT - 1) & 0xFF00) >> 8) << 4;
+               XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x09, ~0x0F0, temp);
+               temp = (pVBInfo->VGAHDE + 16) & 0x0FF; /* BTVGA2HDEE 0x0A,0x0C */
+               XGINew_SetReg1(pVBInfo->Part1Port, 0x0A, temp);
+               tempcx = (pVBInfo->VGAHT - pVBInfo->VGAHDE) >> 2; /* cx */
+               pushbx = pVBInfo->VGAHDE + 16;
+               tempcx = tempcx >> 1;
+               tempbx = pushbx + tempcx; /* bx BTVGA@HRS 0x0B,0x0C */
+               tempcx += tempbx;
 
-       tempbx = TimingPoint[j] | ((TimingPoint[j + 1]) << 8);
-       tempbx += tempcx;
-       push2 = tempbx;
-       temp = tempbx & 0x00FF;
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x24, temp);
-       temp = (tempbx & 0xFF00) >> 8;
-       temp = temp << 4;
-       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x25, 0x0F, temp);
+               if (pVBInfo->VBInfo & SetCRT2ToRAMDAC) {
+                       tempbx = pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[3];
+                       tempbx |= ((pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[5]
+                                                       & 0xC0) << 2);
+                       tempbx = (tempbx - 3) << 3; /* (VGAHRS-3)*8 */
+                       tempcx = pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[4];
+                       tempcx &= 0x1F;
+                       temp = pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[6];
+                       temp = (temp & 0x04) << (5 - 2); /* VGAHRE D[5] */
+                       tempcx = ((tempcx | temp) - 3) << 3; /* (VGAHRE-3)*8 */
+                       tempbx += 16;
+                       tempcx += 16;
+               }
 
-       tempbx = push2;
-       tempbx = tempbx + 8;
-       if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV) {
-               tempbx = tempbx - 4;
-               tempcx = tempbx;
-       }
+               if (tempcx > pVBInfo->VGAHT)
+                       tempcx = pVBInfo->VGAHT;
 
-       temp = (tempbx & 0x00FF) << 4;
-       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x29, 0x0F, temp);
+               temp = tempbx & 0x00FF;
+               XGINew_SetReg1(pVBInfo->Part1Port, 0x0B, temp);
+       }
 
-       j += 2;
-       tempcx += (TimingPoint[j] | ((TimingPoint[j + 1]) << 8));
+       tempax = (tempax & 0x00FF) | (tempbx & 0xFF00);
+       tempbx = pushbx;
+       tempbx = (tempbx & 0x00FF) | ((tempbx & 0xFF00) << 4);
+       tempax |= (tempbx & 0xFF00);
+       temp = (tempax & 0xFF00) >> 8;
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x0C, temp);
        temp = tempcx & 0x00FF;
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x27, temp);
-       temp = ((tempcx & 0xFF00) >> 8) << 4;
-       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x28, 0x0F, temp);
-
-       tempcx += 8;
-       if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV)
-               tempcx -= 4;
-
-       temp = tempcx & 0xFF;
-       temp = temp << 4;
-       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x2A, 0x0F, temp);
-
-       tempcx = push1; /* pop cx */
-       j += 2;
-       temp = TimingPoint[j] | ((TimingPoint[j + 1]) << 8);
-       tempcx -= temp;
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x0D, temp);
+       tempcx = (pVBInfo->VGAVT - 1);
        temp = tempcx & 0x00FF;
-       temp = temp << 4;
-       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x2D, 0x0F, temp);
-
-       tempcx -= 11;
 
-       if (!(pVBInfo->VBInfo & SetCRT2ToTV)) {
-               tempax = XGI_GetVGAHT2(pVBInfo);
-               tempcx = tempax - 1;
+       if (pVBInfo->IF_DEF_CH7005 == 1) {
+               if (pVBInfo->VBInfo & 0x0C)
+                       temp--;
        }
-       temp = tempcx & 0x00FF;
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x2E, temp);
-
-       tempbx = pVBInfo->VDE;
 
-       if (pVBInfo->VGAVDE == 360)
-               tempbx = 746;
-       if (pVBInfo->VGAVDE == 375)
-               tempbx = 746;
-       if (pVBInfo->VGAVDE == 405)
-               tempbx = 853;
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x0E, temp);
+       tempbx = pVBInfo->VGAVDE - 1;
+       temp = tempbx & 0x00FF;
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x0F, temp);
+       temp = ((tempbx & 0xFF00) << 3) >> 8;
+       temp |= ((tempcx & 0xFF00) >> 8);
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x12, temp);
 
-       if (pVBInfo->VBInfo & SetCRT2ToTV) {
-               if (pVBInfo->VBType & (VB_XGI301LV | VB_XGI302LV | VB_XGI301C)) {
-                       if (!(pVBInfo->TVInfo & (SetYPbPrMode525p
-                                       | SetYPbPrMode750p)))
-                               tempbx = tempbx >> 1;
-               } else
-                       tempbx = tempbx >> 1;
-       }
+       tempax = pVBInfo->VGAVDE;
+       tempbx = pVBInfo->VGAVDE;
+       tempcx = pVBInfo->VGAVT;
+       tempbx = (pVBInfo->VGAVT + pVBInfo->VGAVDE) >> 1; /* BTVGA2VRS 0x10,0x11 */
+       tempcx = ((pVBInfo->VGAVT - pVBInfo->VGAVDE) >> 4) + tempbx + 1; /* BTVGA2VRE 0x11 */
 
-       tempbx -= 2;
-       temp = tempbx & 0x00FF;
+       if (pVBInfo->VBInfo & SetCRT2ToRAMDAC) {
+               tempbx = pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[10];
+               temp = pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[9];
 
-       if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV) {
-               if (pVBInfo->VBType & VB_XGI301LV) {
-                       if (pVBInfo->TVInfo & SetYPbPrMode1080i) {
-                               if (pVBInfo->VBInfo & SetInSlaveMode) {
-                                       if (ModeNo == 0x2f)
-                                               temp += 1;
-                               }
-                       }
-               } else {
-                       if (pVBInfo->VBInfo & SetInSlaveMode) {
-                               if (ModeNo == 0x2f)
-                                       temp += 1;
-                       }
-               }
-       }
+               if (temp & 0x04)
+                       tempbx |= 0x0100;
 
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x2F, temp);
+               if (temp & 0x080)
+                       tempbx |= 0x0200;
 
-       temp = (tempcx & 0xFF00) >> 8;
-       temp |= ((tempbx & 0xFF00) >> 8) << 6;
+               temp = pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[14];
 
-       if (!(pVBInfo->VBInfo & SetCRT2ToHiVisionTV)) {
-               if (pVBInfo->VBType & VB_XGI301LV) {
-                       if (pVBInfo->TVInfo & SetYPbPrMode1080i) {
-                               temp |= 0x10;
+               if (temp & 0x08)
+                       tempbx |= 0x0400;
 
-                               if (!(pVBInfo->VBInfo & SetCRT2ToSVIDEO))
-                                       temp |= 0x20;
-                       }
-               } else {
-                       temp |= 0x10;
-                       if (!(pVBInfo->VBInfo & SetCRT2ToSVIDEO))
-                               temp |= 0x20;
-               }
+               temp = pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[11];
+               tempcx = (tempcx & 0xFF00) | (temp & 0x00FF);
        }
 
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x30, temp);
+       temp = tempbx & 0x00FF;
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x10, temp);
+       temp = ((tempbx & 0xFF00) >> 8) << 4;
+       temp = ((tempcx & 0x000F) | (temp));
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x11, temp);
+       tempax = 0;
 
-       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
-                       | VB_XGI302LV | VB_XGI301C)) { /* TV gatingno */
-               tempbx = pVBInfo->VDE;
-               tempcx = tempbx - 2;
+       if (modeflag & DoubleScanMode)
+               tempax |= 0x80;
 
-               if (pVBInfo->VBInfo & SetCRT2ToTV) {
-                       if (!(pVBInfo->TVInfo & (SetYPbPrMode525p
-                                       | SetYPbPrMode750p)))
-                               tempbx = tempbx >> 1;
-               }
+       if (modeflag & HalfDCLK)
+               tempax |= 0x40;
 
-               if (pVBInfo->VBType & (VB_XGI302LV | VB_XGI301C)) {
-                       temp = 0;
-                       if (tempcx & 0x0400)
-                               temp |= 0x20;
+       XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x2C, ~0x0C0, tempax);
+}
 
-                       if (tempbx & 0x0400)
-                               temp |= 0x40;
+static unsigned short XGI_GetVGAHT2(struct vb_device_info *pVBInfo)
+{
+       unsigned long tempax, tempbx;
 
-                       XGINew_SetReg1(pVBInfo->Part4Port, 0x10, temp);
-               }
+       tempbx = ((pVBInfo->VGAVT - pVBInfo->VGAVDE) * pVBInfo->RVBHCMAX)
+                       & 0xFFFF;
+       tempax = (pVBInfo->VT - pVBInfo->VDE) * pVBInfo->RVBHCFACT;
+       tempax = (tempax * pVBInfo->HT) / tempbx;
 
-               temp = (((tempbx - 3) & 0x0300) >> 8) << 5;
-               XGINew_SetReg1(pVBInfo->Part2Port, 0x46, temp);
-               temp = (tempbx - 3) & 0x00FF;
-               XGINew_SetReg1(pVBInfo->Part2Port, 0x47, temp);
-       }
+       return (unsigned short) tempax;
+}
 
-       tempbx = tempbx & 0x00FF;
+static void XGI_SetLockRegs(unsigned short ModeNo, unsigned short ModeIdIndex,
+               struct xgi_hw_device_info *HwDeviceExtension,
+               unsigned short RefreshRateTableIndex,
+               struct vb_device_info *pVBInfo)
+{
+       unsigned short push1, push2, tempax, tempbx = 0, tempcx, temp, resinfo,
+                       modeflag, CRT1Index;
 
-       if (!(modeflag & HalfDCLK)) {
-               tempcx = pVBInfo->VGAHDE;
-               if (tempcx >= pVBInfo->HDE) {
-                       tempbx |= 0x2000;
-                       tempax &= 0x00FF;
-               }
+       if (ModeNo <= 0x13) {
+               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag; /* si+St_ResInfo */
+               resinfo = pVBInfo->SModeIDTable[ModeIdIndex].St_ResInfo;
+       } else {
+               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag; /* si+Ext_ResInfo */
+               resinfo = pVBInfo->EModeIDTable[ModeIdIndex].Ext_RESINFO;
+               CRT1Index = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT1CRTC;
+               CRT1Index &= IndexMask;
        }
 
-       tempcx = 0x0101;
+       if (!(pVBInfo->VBInfo & SetInSlaveMode))
+               return;
 
-       if (pVBInfo->VBInfo & SetCRT2ToTV) { /*301b*/
-               if (pVBInfo->VGAHDE >= 1024) {
-                       tempcx = 0x1920;
-                       if (pVBInfo->VGAHDE >= 1280) {
-                               tempcx = 0x1420;
-                               tempbx = tempbx & 0xDFFF;
-                       }
-               }
-       }
+       temp = 0xFF; /* set MAX HT */
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x03, temp);
+       /* if (modeflag & Charx8Dot) */
+       /*      tempcx = 0x08; */
+       /* else */
+       tempcx = 0x08;
 
-       if (!(tempbx & 0x2000)) {
-               if (modeflag & HalfDCLK)
-                       tempcx = (tempcx & 0xFF00) | ((tempcx & 0x00FF) << 1);
+       if (pVBInfo->VBType & (VB_XGI301LV | VB_XGI302LV | VB_XGI301C))
+               modeflag |= Charx8Dot;
 
-               push1 = tempbx;
-               tempeax = pVBInfo->VGAHDE;
-               tempebx = (tempcx & 0xFF00) >> 8;
-               longtemp = tempeax * tempebx;
-               tempecx = tempcx & 0x00FF;
-               longtemp = longtemp / tempecx;
+       tempax = pVBInfo->VGAHDE; /* 0x04 Horizontal Display End */
 
-               /* 301b */
-               tempecx = 8 * 1024;
+       if (modeflag & HalfDCLK)
+               tempax = tempax >> 1;
 
-               if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
-                               | VB_XGI302LV | VB_XGI301C)) {
-                       tempecx = tempecx * 8;
-               }
+       tempax = (tempax / tempcx) - 1;
+       tempbx |= ((tempax & 0x00FF) << 8);
+       temp = tempax & 0x00FF;
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x04, temp);
 
-               longtemp = longtemp * tempecx;
-               tempecx = pVBInfo->HDE;
-               temp2 = longtemp % tempecx;
-               tempeax = longtemp / tempecx;
-               if (temp2 != 0)
-                       tempeax += 1;
+       temp = (tempbx & 0xFF00) >> 8;
 
-               tempax = (unsigned short) tempeax;
+       if (pVBInfo->VBInfo & SetCRT2ToTV) {
+               if (!(pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
+                               | VB_XGI302LV | VB_XGI301C)))
+                       temp += 2;
 
-               /* 301b */
-               if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
-                               | VB_XGI302LV | VB_XGI301C)) {
-                       tempcx = ((tempax & 0xFF00) >> 5) >> 8;
+               if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV) {
+                       if (pVBInfo->VBType & VB_XGI301LV) {
+                               if (pVBInfo->VBExtInfo == VB_YPbPr1080i) {
+                                       if (resinfo == 7)
+                                               temp -= 2;
+                               }
+                       } else if (resinfo == 7) {
+                               temp -= 2;
+                       }
                }
-               /* end 301b */
-
-               tempbx = push1;
-               tempbx = (unsigned short) (((tempeax & 0x0000FF00) & 0x1F00)
-                               | (tempbx & 0x00FF));
-               tempax = (unsigned short) (((tempeax & 0x000000FF) << 8)
-                               | (tempax & 0x00FF));
-               temp = (tempax & 0xFF00) >> 8;
-       } else {
-               temp = (tempax & 0x00FF) >> 8;
        }
 
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x44, temp);
-       temp = (tempbx & 0xFF00) >> 8;
-       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x45, ~0x03F, temp);
-       temp = tempcx & 0x00FF;
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x05, temp); /* 0x05 Horizontal Display Start */
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x06, 0x03); /* 0x06 Horizontal Blank end */
 
-       if (tempbx & 0x2000)
-               temp = 0;
+       if (!(pVBInfo->VBInfo & DisableCRT2Display)) { /* 030226 bainy */
+               if (pVBInfo->VBInfo & SetCRT2ToTV)
+                       tempax = pVBInfo->VGAHT;
+               else
+                       tempax = XGI_GetVGAHT2(pVBInfo);
+       }
 
-       if (!(pVBInfo->VBInfo & SetCRT2ToLCD))
-               temp |= 0x18;
+       if (tempax >= pVBInfo->VGAHT)
+               tempax = pVBInfo->VGAHT;
 
-       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x46, ~0x1F, temp);
-       if (pVBInfo->TVInfo & SetPALTV) {
-               tempbx = 0x0382;
-               tempcx = 0x007e;
+       if (modeflag & HalfDCLK)
+               tempax = tempax >> 1;
+
+       tempax = (tempax / tempcx) - 5;
+       tempcx = tempax; /* 20030401 0x07 horizontal Retrace Start */
+       if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV) {
+               temp = (tempbx & 0x00FF) - 1;
+               if (!(modeflag & HalfDCLK)) {
+                       temp -= 6;
+                       if (pVBInfo->TVInfo & TVSimuMode) {
+                               temp -= 4;
+                               if (ModeNo > 0x13)
+                                       temp -= 10;
+                       }
+               }
        } else {
-               tempbx = 0x0369;
-               tempcx = 0x0061;
-       }
+               /* tempcx = tempbx & 0x00FF ; */
+               tempbx = (tempbx & 0xFF00) >> 8;
+               tempcx = (tempcx + tempbx) >> 1;
+               temp = (tempcx & 0x00FF) + 2;
 
-       temp = tempbx & 0x00FF;
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x4b, temp);
-       temp = tempcx & 0x00FF;
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x4c, temp);
+               if (pVBInfo->VBInfo & SetCRT2ToTV) {
+                       temp -= 1;
+                       if (!(modeflag & HalfDCLK)) {
+                               if ((modeflag & Charx8Dot)) {
+                                       temp += 4;
+                                       if (pVBInfo->VGAHDE >= 800)
+                                               temp -= 6;
+                               }
+                       }
+               } else {
+                       if (!(modeflag & HalfDCLK)) {
+                               temp -= 4;
+                               if (pVBInfo->LCDResInfo != Panel1280x960) {
+                                       if (pVBInfo->VGAHDE >= 800) {
+                                               temp -= 7;
+                                               if (pVBInfo->ModeType
+                                                               == ModeEGA) {
+                                                       if (pVBInfo->VGAVDE
+                                                                       == 1024) {
+                                                               temp += 15;
+                                                               if (pVBInfo->LCDResInfo
+                                                                               != Panel1280x1024) {
+                                                                       temp
+                                                                                       += 7;
+                                                               }
+                                                       }
+                                               }
 
-       temp = ((tempcx & 0xFF00) >> 8) & 0x03;
-       temp = temp << 2;
-       temp |= ((tempbx & 0xFF00) >> 8) & 0x03;
+                                               if (pVBInfo->VGAHDE >= 1280) {
+                                                       if (pVBInfo->LCDResInfo
+                                                                       != Panel1280x960) {
+                                                               if (pVBInfo->LCDInfo
+                                                                               & LCDNonExpanding) {
+                                                                       temp
+                                                                                       += 28;
+                                                               }
+                                                       }
+                                               }
+                                       }
+                               }
+                       }
+               }
+       }
 
-       if (pVBInfo->VBInfo & SetCRT2ToYPbPr) {
-               temp |= 0x10;
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x07, temp); /* 0x07 Horizontal Retrace Start */
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x08, 0); /* 0x08 Horizontal Retrace End */
 
-               if (pVBInfo->TVInfo & SetYPbPrMode525p)
-                       temp |= 0x20;
+       if (pVBInfo->VBInfo & SetCRT2ToTV) {
+               if (pVBInfo->TVInfo & TVSimuMode) {
+                       if ((ModeNo == 0x06) || (ModeNo == 0x10) || (ModeNo
+                                       == 0x11) || (ModeNo == 0x13) || (ModeNo
+                                       == 0x0F)) {
+                               XGINew_SetReg1(pVBInfo->Part1Port, 0x07, 0x5b);
+                               XGINew_SetReg1(pVBInfo->Part1Port, 0x08, 0x03);
+                       }
 
-               if (pVBInfo->TVInfo & SetYPbPrMode750p)
-                       temp |= 0x60;
-       }
+                       if ((ModeNo == 0x00) || (ModeNo == 0x01)) {
+                               if (pVBInfo->TVInfo & SetNTSCTV) {
+                                       XGINew_SetReg1(pVBInfo->Part1Port,
+                                                       0x07, 0x2A);
+                                       XGINew_SetReg1(pVBInfo->Part1Port,
+                                                       0x08, 0x61);
+                               } else {
+                                       XGINew_SetReg1(pVBInfo->Part1Port,
+                                                       0x07, 0x2A);
+                                       XGINew_SetReg1(pVBInfo->Part1Port,
+                                                       0x08, 0x41);
+                                       XGINew_SetReg1(pVBInfo->Part1Port,
+                                                       0x0C, 0xF0);
+                               }
+                       }
 
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x4d, temp);
-       temp = XGINew_GetReg1(pVBInfo->Part2Port, 0x43); /* 301b change */
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x43, (unsigned short) (temp - 3));
+                       if ((ModeNo == 0x02) || (ModeNo == 0x03) || (ModeNo
+                                       == 0x07)) {
+                               if (pVBInfo->TVInfo & SetNTSCTV) {
+                                       XGINew_SetReg1(pVBInfo->Part1Port,
+                                                       0x07, 0x54);
+                                       XGINew_SetReg1(pVBInfo->Part1Port,
+                                                       0x08, 0x00);
+                               } else {
+                                       XGINew_SetReg1(pVBInfo->Part1Port,
+                                                       0x07, 0x55);
+                                       XGINew_SetReg1(pVBInfo->Part1Port,
+                                                       0x08, 0x00);
+                                       XGINew_SetReg1(pVBInfo->Part1Port,
+                                                       0x0C, 0xF0);
+                               }
+                       }
 
-       if (!(pVBInfo->TVInfo & (SetYPbPrMode525p | SetYPbPrMode750p))) {
-               if (pVBInfo->TVInfo & NTSC1024x768) {
-                       TimingPoint = XGI_NTSC1024AdjTime;
-                       for (i = 0x1c, j = 0; i <= 0x30; i++, j++) {
-                               XGINew_SetReg1(pVBInfo->Part2Port, i,
-                                               TimingPoint[j]);
+                       if ((ModeNo == 0x04) || (ModeNo == 0x05) || (ModeNo
+                                       == 0x0D) || (ModeNo == 0x50)) {
+                               if (pVBInfo->TVInfo & SetNTSCTV) {
+                                       XGINew_SetReg1(pVBInfo->Part1Port,
+                                                       0x07, 0x30);
+                                       XGINew_SetReg1(pVBInfo->Part1Port,
+                                                       0x08, 0x03);
+                               } else {
+                                       XGINew_SetReg1(pVBInfo->Part1Port,
+                                                       0x07, 0x2f);
+                                       XGINew_SetReg1(pVBInfo->Part1Port,
+                                                       0x08, 0x02);
+                               }
                        }
-                       XGINew_SetReg1(pVBInfo->Part2Port, 0x43, 0x72);
                }
        }
 
-       /* [ycchen] 01/14/03 Modify for 301C PALM Support */
-       if (pVBInfo->VBType & VB_XGI301C) {
-               if (pVBInfo->TVInfo & SetPALMTV)
-                       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x4E, ~0x08,
-                                       0x08); /* PALM Mode */
-       }
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x18, 0x03); /* 0x18 SR0B */
+       XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x19, 0xF0, 0x00);
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x09, 0xFF); /* 0x09 Set Max VT */
 
-       if (pVBInfo->TVInfo & SetPALMTV) {
-               tempax = (unsigned char) XGINew_GetReg1(pVBInfo->Part2Port,
-                               0x01);
-               tempax--;
-               XGINew_SetRegAND(pVBInfo->Part2Port, 0x01, tempax);
+       tempbx = pVBInfo->VGAVT;
+       push1 = tempbx;
+       tempcx = 0x121;
+       tempbx = pVBInfo->VGAVDE; /* 0x0E Virtical Display End */
 
-               /* if ( !( pVBInfo->VBType & VB_XGI301C ) ) */
-               XGINew_SetRegAND(pVBInfo->Part2Port, 0x00, 0xEF);
-       }
+       if (tempbx == 357)
+               tempbx = 350;
+       if (tempbx == 360)
+               tempbx = 350;
+       if (tempbx == 375)
+               tempbx = 350;
+       if (tempbx == 405)
+               tempbx = 400;
+       if (tempbx == 525)
+               tempbx = 480;
 
-       if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV) {
-               if (!(pVBInfo->VBInfo & SetInSlaveMode))
-                       XGINew_SetReg1(pVBInfo->Part2Port, 0x0B, 0x00);
-       }
+       push2 = tempbx;
 
-       if (pVBInfo->VBInfo & SetCRT2ToTV)
-               return;
-}
+       if (pVBInfo->VBInfo & SetCRT2ToLCD) {
+               if (pVBInfo->LCDResInfo == Panel1024x768) {
+                       if (!(pVBInfo->LCDInfo & LCDVESATiming)) {
+                               if (tempbx == 350)
+                                       tempbx += 5;
+                               if (tempbx == 480)
+                                       tempbx += 5;
+                       }
+               }
+       }
+       tempbx--;
+       temp = tempbx & 0x00FF;
+       tempbx--;
+       temp = tempbx & 0x00FF;
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x10, temp); /* 0x10 vertical Blank Start */
+       tempbx = push2;
+       tempbx--;
+       temp = tempbx & 0x00FF;
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x0E, temp);
 
-static void XGI_SetLCDRegs(unsigned short ModeNo, unsigned short ModeIdIndex,
-               struct xgi_hw_device_info *HwDeviceExtension,
-               unsigned short RefreshRateTableIndex,
-               struct vb_device_info *pVBInfo)
-{
-       unsigned short push1, push2, pushbx, tempax, tempbx, tempcx, temp,
-                       tempah, tempbh, tempch, resinfo, modeflag, CRT1Index;
+       if (tempbx & 0x0100)
+               tempcx |= 0x0002;
 
-       struct XGI_LCDDesStruct *LCDBDesPtr = NULL;
+       tempax = 0x000B;
 
-       if (ModeNo <= 0x13) {
-               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag; /* si+St_ResInfo */
-               resinfo = pVBInfo->SModeIDTable[ModeIdIndex].St_ResInfo;
-       } else {
-               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag; /* si+Ext_ResInfo */
-               resinfo = pVBInfo->EModeIDTable[ModeIdIndex].Ext_RESINFO;
-               CRT1Index
-                               = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT1CRTC;
-               CRT1Index &= IndexMask;
-       }
+       if (modeflag & DoubleScanMode)
+               tempax |= 0x08000;
 
-       if (!(pVBInfo->VBInfo & SetCRT2ToLCD))
-               return;
+       if (tempbx & 0x0200)
+               tempcx |= 0x0040;
 
-       tempbx = pVBInfo->HDE; /* RHACTE=HDE-1 */
+       temp = (tempax & 0xFF00) >> 8;
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x0B, temp);
 
-       if (XGI_IsLCDDualLink(pVBInfo))
-               tempbx = tempbx >> 1;
+       if (tempbx & 0x0400)
+               tempcx |= 0x0600;
 
-       tempbx -= 1;
-       temp = tempbx & 0x00FF;
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x2C, temp);
-       temp = (tempbx & 0xFF00) >> 8;
-       temp = temp << 4;
-       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x2B, 0x0F, temp);
-       temp = 0x01;
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x11, 0x00); /* 0x11 Vertival Blank End */
 
-       if (pVBInfo->LCDResInfo == Panel1280x1024) {
-               if (pVBInfo->ModeType == ModeEGA) {
-                       if (pVBInfo->VGAHDE >= 1024) {
-                               temp = 0x02;
-                               if (pVBInfo->LCDInfo & LCDVESATiming)
-                                       temp = 0x01;
+       tempax = push1;
+       tempax -= tempbx; /* 0x0C Vertical Retrace Start */
+       tempax = tempax >> 2;
+       push1 = tempax; /* push ax */
+
+       if (resinfo != 0x09) {
+               tempax = tempax << 1;
+               tempbx += tempax;
+       }
+
+       if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV) {
+               if (pVBInfo->VBType & VB_XGI301LV) {
+                       if (pVBInfo->TVInfo & SetYPbPrMode1080i) {
+                               tempbx -= 10;
+                       } else {
+                               if (pVBInfo->TVInfo & TVSimuMode) {
+                                       if (pVBInfo->TVInfo & SetPALTV) {
+                                               if (pVBInfo->VBType
+                                                               & VB_XGI301LV) {
+                                                       if (!(pVBInfo->TVInfo
+                                                                       & (SetYPbPrMode525p
+                                                                                       | SetYPbPrMode750p
+                                                                                       | SetYPbPrMode1080i)))
+                                                               tempbx += 40;
+                                               } else {
+                                                       tempbx += 40;
+                                               }
+                                       }
+                               }
+                       }
+               } else {
+                       tempbx -= 10;
+               }
+       } else {
+               if (pVBInfo->TVInfo & TVSimuMode) {
+                       if (pVBInfo->TVInfo & SetPALTV) {
+                               if (pVBInfo->VBType & VB_XGI301LV) {
+                                       if (!(pVBInfo->TVInfo
+                                                       & (SetYPbPrMode525p
+                                                                       | SetYPbPrMode750p
+                                                                       | SetYPbPrMode1080i)))
+                                               tempbx += 40;
+                               } else {
+                                       tempbx += 40;
+                               }
                        }
                }
        }
+       tempax = push1;
+       tempax = tempax >> 2;
+       tempax++;
+       tempax += tempbx;
+       push1 = tempax; /* push ax */
 
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x0B, temp);
-       tempbx = pVBInfo->VDE; /* RTVACTEO=(VDE-1)&0xFF */
-       push1 = tempbx;
+       if ((pVBInfo->TVInfo & SetPALTV)) {
+               if (tempbx <= 513) {
+                       if (tempax >= 513)
+                               tempbx = 513;
+               }
+       }
+
+       temp = tempbx & 0x00FF;
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x0C, temp);
        tempbx--;
        temp = tempbx & 0x00FF;
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x03, temp);
-       temp = ((tempbx & 0xFF00) >> 8) & 0x07;
-       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x0C, ~0x07, temp);
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x10, temp);
 
-       tempcx = pVBInfo->VT - 1;
-       push2 = tempcx + 1;
-       temp = tempcx & 0x00FF; /* RVTVT=VT-1 */
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x19, temp);
-       temp = (tempcx & 0xFF00) >> 8;
-       temp = temp << 5;
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x1A, temp);
-       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x09, 0xF0, 0x00);
-       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x0A, 0xF0, 0x00);
-       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x17, 0xFB, 0x00);
-       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x18, 0xDF, 0x00);
+       if (tempbx & 0x0100)
+               tempcx |= 0x0008;
 
-       /* Customized LCDB Des no add */
-       tempbx = 5;
-       LCDBDesPtr = (struct XGI_LCDDesStruct *) XGI_GetLcdPtr(tempbx, ModeNo,
-                       ModeIdIndex, RefreshRateTableIndex, pVBInfo);
-       tempah = pVBInfo->LCDResInfo;
-       tempah &= PanelResInfo;
+       if (tempbx & 0x0200)
+               XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x0B, 0x0FF, 0x20);
 
-       if ((tempah == Panel1024x768) || (tempah == Panel1024x768x75)) {
-               tempbx = 1024;
-               tempcx = 768;
-       } else if ((tempah == Panel1280x1024) || (tempah == Panel1280x1024x75)) {
-               tempbx = 1280;
-               tempcx = 1024;
-       } else if (tempah == Panel1400x1050) {
-               tempbx = 1400;
-               tempcx = 1050;
-       } else {
-               tempbx = 1600;
-               tempcx = 1200;
-       }
+       tempbx++;
 
-       if (pVBInfo->LCDInfo & EnableScalingLCD) {
-               tempbx = pVBInfo->HDE;
-               tempcx = pVBInfo->VDE;
-       }
+       if (tempbx & 0x0100)
+               tempcx |= 0x0004;
 
-       pushbx = tempbx;
-       tempax = pVBInfo->VT;
-       pVBInfo->LCDHDES = LCDBDesPtr->LCDHDES;
-       pVBInfo->LCDHRS = LCDBDesPtr->LCDHRS;
-       pVBInfo->LCDVDES = LCDBDesPtr->LCDVDES;
-       pVBInfo->LCDVRS = LCDBDesPtr->LCDVRS;
-       tempbx = pVBInfo->LCDVDES;
-       tempcx += tempbx;
+       if (tempbx & 0x0200)
+               tempcx |= 0x0080;
 
-       if (tempcx >= tempax)
-               tempcx -= tempax; /* lcdvdes */
+       if (tempbx & 0x0400)
+               tempcx |= 0x0C00;
 
-       temp = tempbx & 0x00FF; /* RVEQ1EQ=lcdvdes */
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x05, temp);
-       temp = tempcx & 0x00FF;
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x06, temp);
-       tempch = ((tempcx & 0xFF00) >> 8) & 0x07;
-       tempbh = ((tempbx & 0xFF00) >> 8) & 0x07;
-       tempah = tempch;
-       tempah = tempah << 3;
-       tempah |= tempbh;
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x02, tempah);
+       tempbx = push1; /* pop ax */
+       temp = tempbx & 0x00FF;
+       temp &= 0x0F;
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x0D, temp); /* 0x0D vertical Retrace End */
 
-       /* getlcdsync() */
-       XGI_GetLCDSync(&tempax, &tempbx, pVBInfo);
-       tempcx = tempbx;
-       tempax = pVBInfo->VT;
-       tempbx = pVBInfo->LCDVRS;
+       if (tempbx & 0x0010)
+               tempcx |= 0x2000;
 
-       /* if (SetLCD_Info & EnableScalingLCD) */
-       tempcx += tempbx;
-       if (tempcx >= tempax)
-               tempcx -= tempax;
+       temp = tempcx & 0x00FF;
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x0A, temp); /* 0x0A CR07 */
+       temp = (tempcx & 0x0FF00) >> 8;
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x17, temp); /* 0x17 SR0A */
+       tempax = modeflag;
+       temp = (tempax & 0xFF00) >> 8;
 
-       temp = tempbx & 0x00FF; /* RTVACTEE=lcdvrs */
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x04, temp);
-       temp = (tempbx & 0xFF00) >> 8;
-       temp = temp << 4;
-       temp |= (tempcx & 0x000F);
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x01, temp);
-       tempcx = pushbx;
-       tempax = pVBInfo->HT;
-       tempbx = pVBInfo->LCDHDES;
-       tempbx &= 0x0FFF;
+       temp = (temp >> 1) & 0x09;
 
-       if (XGI_IsLCDDualLink(pVBInfo)) {
-               tempax = tempax >> 1;
-               tempbx = tempbx >> 1;
-               tempcx = tempcx >> 1;
-       }
+       if (pVBInfo->VBType & (VB_XGI301LV | VB_XGI302LV | VB_XGI301C))
+               temp |= 0x01;
 
-       if (pVBInfo->VBType & VB_XGI302LV)
-               tempbx += 1;
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x16, temp); /* 0x16 SR01 */
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x0F, 0); /* 0x0F CR14 */
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x12, 0); /* 0x12 CR17 */
 
-       if (pVBInfo->VBType & VB_XGI301C) /* tap4 */
-               tempbx += 1;
+       if (pVBInfo->LCDInfo & LCDRGB18Bit)
+               temp = 0x80;
+       else
+               temp = 0x00;
 
-       tempcx += tempbx;
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x1A, temp); /* 0x1A SR0E */
 
-       if (tempcx >= tempax)
-               tempcx -= tempax;
+       return;
+}
 
-       temp = tempbx & 0x00FF;
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x1F, temp); /* RHBLKE=lcdhdes */
-       temp = ((tempbx & 0xFF00) >> 8) << 4;
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x20, temp);
-       temp = tempcx & 0x00FF;
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x23, temp); /* RHEQPLE=lcdhdee */
-       temp = (tempcx & 0xFF00) >> 8;
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x25, temp);
+static void XGI_SetGroup2(unsigned short ModeNo, unsigned short ModeIdIndex,
+               unsigned short RefreshRateTableIndex,
+               struct xgi_hw_device_info *HwDeviceExtension,
+               struct vb_device_info *pVBInfo)
+{
+       unsigned short i, j, tempax, tempbx, tempcx, temp, push1, push2,
+                       modeflag, resinfo, crt2crtc;
+       unsigned char *TimingPoint;
 
-       /* getlcdsync() */
-       XGI_GetLCDSync(&tempax, &tempbx, pVBInfo);
-       tempcx = tempax;
-       tempax = pVBInfo->HT;
-       tempbx = pVBInfo->LCDHRS;
-       /* if ( SetLCD_Info & EnableScalingLCD) */
-       if (XGI_IsLCDDualLink(pVBInfo)) {
-               tempax = tempax >> 1;
-               tempbx = tempbx >> 1;
-               tempcx = tempcx >> 1;
+       unsigned long longtemp, tempeax, tempebx, temp2, tempecx;
+
+       if (ModeNo <= 0x13) {
+               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag; /* si+St_ResInfo */
+               resinfo = pVBInfo->SModeIDTable[ModeIdIndex].St_ResInfo;
+               crt2crtc = pVBInfo->SModeIDTable[ModeIdIndex].St_CRT2CRTC;
+       } else {
+               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag; /* si+Ext_ResInfo */
+               resinfo = pVBInfo->EModeIDTable[ModeIdIndex].Ext_RESINFO;
+               crt2crtc
+                               = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT2CRTC;
        }
 
-       if (pVBInfo->VBType & VB_XGI302LV)
-               tempbx += 1;
+       tempax = 0;
+
+       if (!(pVBInfo->VBInfo & SetCRT2ToAVIDEO))
+               tempax |= 0x0800;
 
-       tempcx += tempbx;
+       if (!(pVBInfo->VBInfo & SetCRT2ToSVIDEO))
+               tempax |= 0x0400;
 
-       if (tempcx >= tempax)
-               tempcx -= tempax;
+       if (pVBInfo->VBInfo & SetCRT2ToSCART)
+               tempax |= 0x0200;
 
-       temp = tempbx & 0x00FF; /* RHBURSTS=lcdhrs */
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x1C, temp);
+       if (!(pVBInfo->TVInfo & SetPALTV))
+               tempax |= 0x1000;
 
-       temp = (tempbx & 0xFF00) >> 8;
-       temp = temp << 4;
-       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x1D, ~0x0F0, temp);
-       temp = tempcx & 0x00FF; /* RHSYEXP2S=lcdhre */
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x21, temp);
+       if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV)
+               tempax |= 0x0100;
 
-       if (!(pVBInfo->LCDInfo & LCDVESATiming)) {
-               if (pVBInfo->VGAVDE == 525) {
-                       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B
-                                       | VB_XGI301LV | VB_XGI302LV
-                                       | VB_XGI301C)) {
-                               temp = 0xC6;
-                       } else
-                               temp = 0xC4;
+       if (pVBInfo->TVInfo & (SetYPbPrMode525p | SetYPbPrMode750p))
+               tempax &= 0xfe00;
 
-                       XGINew_SetReg1(pVBInfo->Part2Port, 0x2f, temp);
-                       XGINew_SetReg1(pVBInfo->Part2Port, 0x30, 0xB3);
-               }
+       tempax = (tempax & 0xff00) >> 8;
 
-               if (pVBInfo->VGAVDE == 420) {
-                       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B
-                                       | VB_XGI301LV | VB_XGI302LV
-                                       | VB_XGI301C)) {
-                               temp = 0x4F;
-                       } else
-                               temp = 0x4E;
-                       XGINew_SetReg1(pVBInfo->Part2Port, 0x2f, temp);
-               }
-       }
-}
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x0, tempax);
+       TimingPoint = pVBInfo->NTSCTiming;
 
-/* --------------------------------------------------------------------- */
-/* Function : XGI_GetTap4Ptr */
-/* Input : */
-/* Output : di -> Tap4 Reg. Setting Pointer */
-/* Description : */
-/* --------------------------------------------------------------------- */
-static struct XGI301C_Tap4TimingStruct *XGI_GetTap4Ptr(unsigned short tempcx,
-               struct vb_device_info *pVBInfo)
-{
-       unsigned short tempax, tempbx, i;
+       if (pVBInfo->TVInfo & SetPALTV)
+               TimingPoint = pVBInfo->PALTiming;
 
-       struct XGI301C_Tap4TimingStruct *Tap4TimingPtr;
+       if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV) {
+               TimingPoint = pVBInfo->HiTVExtTiming;
 
-       if (tempcx == 0) {
-               tempax = pVBInfo->VGAHDE;
-               tempbx = pVBInfo->HDE;
-       } else {
-               tempax = pVBInfo->VGAVDE;
-               tempbx = pVBInfo->VDE;
-       }
+               if (pVBInfo->VBInfo & SetInSlaveMode)
+                       TimingPoint = pVBInfo->HiTVSt2Timing;
 
-       if (tempax < tempbx)
-               return &EnlargeTap4Timing[0];
-       else if (tempax == tempbx)
-               return &NoScaleTap4Timing[0]; /* 1:1 */
-       else
-               Tap4TimingPtr = NTSCTap4Timing; /* NTSC */
+               if (pVBInfo->SetFlag & TVSimuMode)
+                       TimingPoint = pVBInfo->HiTVSt1Timing;
 
-       if (pVBInfo->TVInfo & SetPALTV)
-               Tap4TimingPtr = PALTap4Timing;
+               if (!(modeflag & Charx8Dot))
+                       TimingPoint = pVBInfo->HiTVTextTiming;
+       }
 
        if (pVBInfo->VBInfo & SetCRT2ToYPbPr) {
                if (pVBInfo->TVInfo & SetYPbPrMode525i)
-                       Tap4TimingPtr = YPbPr525iTap4Timing;
+                       TimingPoint = pVBInfo->YPbPr525iTiming;
+
                if (pVBInfo->TVInfo & SetYPbPrMode525p)
-                       Tap4TimingPtr = YPbPr525pTap4Timing;
+                       TimingPoint = pVBInfo->YPbPr525pTiming;
+
                if (pVBInfo->TVInfo & SetYPbPrMode750p)
-                       Tap4TimingPtr = YPbPr750pTap4Timing;
+                       TimingPoint = pVBInfo->YPbPr750pTiming;
        }
 
+       for (i = 0x01, j = 0; i <= 0x2D; i++, j++)
+               XGINew_SetReg1(pVBInfo->Part2Port, i, TimingPoint[j]);
+
+       for (i = 0x39; i <= 0x45; i++, j++)
+               XGINew_SetReg1(pVBInfo->Part2Port, i, TimingPoint[j]); /* di->temp2[j] */
+
+       if (pVBInfo->VBInfo & SetCRT2ToTV)
+               XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x3A, 0x1F, 0x00);
+
+       temp = pVBInfo->NewFlickerMode;
+       temp &= 0x80;
+       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x0A, 0xFF, temp);
+
        if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV)
-               Tap4TimingPtr = HiTVTap4Timing;
+               tempax = 950;
 
-       i = 0;
-       while (Tap4TimingPtr[i].DE != 0xFFFF) {
-               if (Tap4TimingPtr[i].DE == tempax)
-                       break;
-               i++;
+       if (pVBInfo->TVInfo & SetPALTV)
+               tempax = 520;
+       else
+               tempax = 440;
+
+       if (pVBInfo->VDE <= tempax) {
+               tempax -= pVBInfo->VDE;
+               tempax = tempax >> 2;
+               tempax = (tempax & 0x00FF) | ((tempax & 0x00FF) << 8);
+               push1 = tempax;
+               temp = (tempax & 0xFF00) >> 8;
+               temp += (unsigned short) TimingPoint[0];
+
+               if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
+                               | VB_XGI302LV | VB_XGI301C)) {
+                       if (pVBInfo->VBInfo & (SetCRT2ToAVIDEO
+                                       | SetCRT2ToSVIDEO | SetCRT2ToSCART
+                                       | SetCRT2ToYPbPr)) {
+                               tempcx = pVBInfo->VGAHDE;
+                               if (tempcx >= 1024) {
+                                       temp = 0x17; /* NTSC */
+                                       if (pVBInfo->TVInfo & SetPALTV)
+                                               temp = 0x19; /* PAL */
+                               }
+                       }
+               }
+
+               XGINew_SetReg1(pVBInfo->Part2Port, 0x01, temp);
+               tempax = push1;
+               temp = (tempax & 0xFF00) >> 8;
+               temp += TimingPoint[1];
+
+               if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
+                               | VB_XGI302LV | VB_XGI301C)) {
+                       if ((pVBInfo->VBInfo & (SetCRT2ToAVIDEO
+                                       | SetCRT2ToSVIDEO | SetCRT2ToSCART
+                                       | SetCRT2ToYPbPr))) {
+                               tempcx = pVBInfo->VGAHDE;
+                               if (tempcx >= 1024) {
+                                       temp = 0x1D; /* NTSC */
+                                       if (pVBInfo->TVInfo & SetPALTV)
+                                               temp = 0x52; /* PAL */
+                               }
+                       }
+               }
+               XGINew_SetReg1(pVBInfo->Part2Port, 0x02, temp);
        }
-       return &Tap4TimingPtr[i];
-}
 
-static void XGI_SetTap4Regs(struct vb_device_info *pVBInfo)
-{
-       unsigned short i, j;
+       /* 301b */
+       tempcx = pVBInfo->HT;
 
-       struct XGI301C_Tap4TimingStruct *Tap4TimingPtr;
+       if (XGI_IsLCDDualLink(pVBInfo))
+               tempcx = tempcx >> 1;
 
-       if (!(pVBInfo->VBType & VB_XGI301C))
-               return;
+       tempcx -= 2;
+       temp = tempcx & 0x00FF;
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x1B, temp);
 
-#ifndef Tap4
-       XGINew_SetRegAND(pVBInfo->Part2Port, 0x4E, 0xEB); /* Disable Tap4 */
-#else            /* Tap4 Setting */
+       temp = (tempcx & 0xFF00) >> 8;
+       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x1D, ~0x0F, temp);
 
-       Tap4TimingPtr = XGI_GetTap4Ptr(0, pVBInfo); /* Set Horizontal Scaling */
-       for (i = 0x80, j = 0; i <= 0xBF; i++, j++)
-               XGINew_SetReg1(pVBInfo->Part2Port, i, Tap4TimingPtr->Reg[j]);
+       tempcx = pVBInfo->HT >> 1;
+       push1 = tempcx; /* push cx */
+       tempcx += 7;
 
-       if ((pVBInfo->VBInfo & SetCRT2ToTV) && (!(pVBInfo->VBInfo & SetCRT2ToHiVisionTV))) {
-               Tap4TimingPtr = XGI_GetTap4Ptr(1, pVBInfo); /* Set Vertical Scaling */
-               for (i = 0xC0, j = 0; i < 0xFF; i++, j++)
-                       XGINew_SetReg1(pVBInfo->Part2Port, i, Tap4TimingPtr->Reg[j]);
+       if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV)
+               tempcx -= 4;
+
+       temp = tempcx & 0x00FF;
+       temp = temp << 4;
+       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x22, 0x0F, temp);
+
+       tempbx = TimingPoint[j] | ((TimingPoint[j + 1]) << 8);
+       tempbx += tempcx;
+       push2 = tempbx;
+       temp = tempbx & 0x00FF;
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x24, temp);
+       temp = (tempbx & 0xFF00) >> 8;
+       temp = temp << 4;
+       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x25, 0x0F, temp);
+
+       tempbx = push2;
+       tempbx = tempbx + 8;
+       if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV) {
+               tempbx = tempbx - 4;
+               tempcx = tempbx;
        }
 
-       if ((pVBInfo->VBInfo & SetCRT2ToTV) && (!(pVBInfo->VBInfo & SetCRT2ToHiVisionTV)))
-               XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x4E, ~0x14, 0x04); /* Enable V.Scaling */
-       else
-               XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x4E, ~0x14, 0x10); /* Enable H.Scaling */
-#endif
-}
+       temp = (tempbx & 0x00FF) << 4;
+       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x29, 0x0F, temp);
 
-static void XGI_SetGroup3(unsigned short ModeNo, unsigned short ModeIdIndex,
-               struct vb_device_info *pVBInfo)
-{
-       unsigned short i;
-       unsigned char *tempdi;
-       unsigned short modeflag;
+       j += 2;
+       tempcx += (TimingPoint[j] | ((TimingPoint[j + 1]) << 8));
+       temp = tempcx & 0x00FF;
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x27, temp);
+       temp = ((tempcx & 0xFF00) >> 8) << 4;
+       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x28, 0x0F, temp);
 
-       if (ModeNo <= 0x13)
-               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag; /* si+St_ResInfo */
-       else
-               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag; /* si+Ext_ResInfo */
+       tempcx += 8;
+       if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV)
+               tempcx -= 4;
 
-       XGINew_SetReg1(pVBInfo->Part3Port, 0x00, 0x00);
-       if (pVBInfo->TVInfo & SetPALTV) {
-               XGINew_SetReg1(pVBInfo->Part3Port, 0x13, 0xFA);
-               XGINew_SetReg1(pVBInfo->Part3Port, 0x14, 0xC8);
-       } else {
-               XGINew_SetReg1(pVBInfo->Part3Port, 0x13, 0xF5);
-               XGINew_SetReg1(pVBInfo->Part3Port, 0x14, 0xB7);
+       temp = tempcx & 0xFF;
+       temp = temp << 4;
+       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x2A, 0x0F, temp);
+
+       tempcx = push1; /* pop cx */
+       j += 2;
+       temp = TimingPoint[j] | ((TimingPoint[j + 1]) << 8);
+       tempcx -= temp;
+       temp = tempcx & 0x00FF;
+       temp = temp << 4;
+       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x2D, 0x0F, temp);
+
+       tempcx -= 11;
+
+       if (!(pVBInfo->VBInfo & SetCRT2ToTV)) {
+               tempax = XGI_GetVGAHT2(pVBInfo);
+               tempcx = tempax - 1;
        }
+       temp = tempcx & 0x00FF;
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x2E, temp);
 
-       if (!(pVBInfo->VBInfo & SetCRT2ToTV))
-               return;
+       tempbx = pVBInfo->VDE;
 
-       if (pVBInfo->TVInfo & SetPALMTV) {
-               XGINew_SetReg1(pVBInfo->Part3Port, 0x13, 0xFA);
-               XGINew_SetReg1(pVBInfo->Part3Port, 0x14, 0xC8);
-               XGINew_SetReg1(pVBInfo->Part3Port, 0x3D, 0xA8);
+       if (pVBInfo->VGAVDE == 360)
+               tempbx = 746;
+       if (pVBInfo->VGAVDE == 375)
+               tempbx = 746;
+       if (pVBInfo->VGAVDE == 405)
+               tempbx = 853;
+
+       if (pVBInfo->VBInfo & SetCRT2ToTV) {
+               if (pVBInfo->VBType & (VB_XGI301LV | VB_XGI302LV | VB_XGI301C)) {
+                       if (!(pVBInfo->TVInfo & (SetYPbPrMode525p
+                                       | SetYPbPrMode750p)))
+                               tempbx = tempbx >> 1;
+               } else
+                       tempbx = tempbx >> 1;
        }
 
-       if ((pVBInfo->VBInfo & SetCRT2ToHiVisionTV) || (pVBInfo->VBInfo
-                       & SetCRT2ToYPbPr)) {
-               if (pVBInfo->TVInfo & SetYPbPrMode525i)
-                       return;
+       tempbx -= 2;
+       temp = tempbx & 0x00FF;
 
-               tempdi = pVBInfo->HiTVGroup3Data;
-               if (pVBInfo->SetFlag & TVSimuMode) {
-                       tempdi = pVBInfo->HiTVGroup3Simu;
-                       if (!(modeflag & Charx8Dot))
-                               tempdi = pVBInfo->HiTVGroup3Text;
+       if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV) {
+               if (pVBInfo->VBType & VB_XGI301LV) {
+                       if (pVBInfo->TVInfo & SetYPbPrMode1080i) {
+                               if (pVBInfo->VBInfo & SetInSlaveMode) {
+                                       if (ModeNo == 0x2f)
+                                               temp += 1;
+                               }
+                       }
+               } else {
+                       if (pVBInfo->VBInfo & SetInSlaveMode) {
+                               if (ModeNo == 0x2f)
+                                       temp += 1;
+                       }
                }
+       }
 
-               if (pVBInfo->TVInfo & SetYPbPrMode525p)
-                       tempdi = pVBInfo->Ren525pGroup3;
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x2F, temp);
 
-               if (pVBInfo->TVInfo & SetYPbPrMode750p)
-                       tempdi = pVBInfo->Ren750pGroup3;
+       temp = (tempcx & 0xFF00) >> 8;
+       temp |= ((tempbx & 0xFF00) >> 8) << 6;
 
-               for (i = 0; i <= 0x3E; i++)
-                       XGINew_SetReg1(pVBInfo->Part3Port, i, tempdi[i]);
+       if (!(pVBInfo->VBInfo & SetCRT2ToHiVisionTV)) {
+               if (pVBInfo->VBType & VB_XGI301LV) {
+                       if (pVBInfo->TVInfo & SetYPbPrMode1080i) {
+                               temp |= 0x10;
 
-               if (pVBInfo->VBType & VB_XGI301C) { /* Marcovision */
-                       if (pVBInfo->TVInfo & SetYPbPrMode525p)
-                               XGINew_SetReg1(pVBInfo->Part3Port, 0x28, 0x3f);
+                               if (!(pVBInfo->VBInfo & SetCRT2ToSVIDEO))
+                                       temp |= 0x20;
+                       }
+               } else {
+                       temp |= 0x10;
+                       if (!(pVBInfo->VBInfo & SetCRT2ToSVIDEO))
+                               temp |= 0x20;
                }
        }
-       return;
-} /* {end of XGI_SetGroup3} */
 
-static void XGI_SetGroup4(unsigned short ModeNo, unsigned short ModeIdIndex,
-               unsigned short RefreshRateTableIndex,
-               struct xgi_hw_device_info *HwDeviceExtension,
-               struct vb_device_info *pVBInfo)
-{
-       unsigned short tempax, tempcx, tempbx, modeflag, temp, temp2;
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x30, temp);
 
-       unsigned long tempebx, tempeax, templong;
+       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
+                       | VB_XGI302LV | VB_XGI301C)) { /* TV gatingno */
+               tempbx = pVBInfo->VDE;
+               tempcx = tempbx - 2;
 
-       if (ModeNo <= 0x13)
-               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag; /* si+St_ResInfo */
-       else
-               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag; /* si+Ext_ResInfo */
+               if (pVBInfo->VBInfo & SetCRT2ToTV) {
+                       if (!(pVBInfo->TVInfo & (SetYPbPrMode525p
+                                       | SetYPbPrMode750p)))
+                               tempbx = tempbx >> 1;
+               }
 
-       temp = pVBInfo->RVBHCFACT;
-       XGINew_SetReg1(pVBInfo->Part4Port, 0x13, temp);
+               if (pVBInfo->VBType & (VB_XGI302LV | VB_XGI301C)) {
+                       temp = 0;
+                       if (tempcx & 0x0400)
+                               temp |= 0x20;
 
-       tempbx = pVBInfo->RVBHCMAX;
-       temp = tempbx & 0x00FF;
-       XGINew_SetReg1(pVBInfo->Part4Port, 0x14, temp);
-       temp2 = ((tempbx & 0xFF00) >> 8) << 7;
-       tempcx = pVBInfo->VGAHT - 1;
-       temp = tempcx & 0x00FF;
-       XGINew_SetReg1(pVBInfo->Part4Port, 0x16, temp);
+                       if (tempbx & 0x0400)
+                               temp |= 0x40;
 
-       temp = ((tempcx & 0xFF00) >> 8) << 3;
-       temp2 |= temp;
+                       XGINew_SetReg1(pVBInfo->Part4Port, 0x10, temp);
+               }
 
-       tempcx = pVBInfo->VGAVT - 1;
-       if (!(pVBInfo->VBInfo & SetCRT2ToTV))
-               tempcx -= 5;
+               temp = (((tempbx - 3) & 0x0300) >> 8) << 5;
+               XGINew_SetReg1(pVBInfo->Part2Port, 0x46, temp);
+               temp = (tempbx - 3) & 0x00FF;
+               XGINew_SetReg1(pVBInfo->Part2Port, 0x47, temp);
+       }
 
-       temp = tempcx & 0x00FF;
-       XGINew_SetReg1(pVBInfo->Part4Port, 0x17, temp);
-       temp = temp2 | ((tempcx & 0xFF00) >> 8);
-       XGINew_SetReg1(pVBInfo->Part4Port, 0x15, temp);
-       XGINew_SetRegOR(pVBInfo->Part4Port, 0x0D, 0x08);
-       tempcx = pVBInfo->VBInfo;
-       tempbx = pVBInfo->VGAHDE;
+       tempbx = tempbx & 0x00FF;
 
-       if (modeflag & HalfDCLK)
-               tempbx = tempbx >> 1;
+       if (!(modeflag & HalfDCLK)) {
+               tempcx = pVBInfo->VGAHDE;
+               if (tempcx >= pVBInfo->HDE) {
+                       tempbx |= 0x2000;
+                       tempax &= 0x00FF;
+               }
+       }
 
-       if (XGI_IsLCDDualLink(pVBInfo))
-               tempbx = tempbx >> 1;
+       tempcx = 0x0101;
 
-       if (tempcx & SetCRT2ToHiVisionTV) {
-               temp = 0;
-               if (tempbx <= 1024)
-                       temp = 0xA0;
-               if (tempbx == 1280)
-                       temp = 0xC0;
-       } else if (tempcx & SetCRT2ToTV) {
-               temp = 0xA0;
-               if (tempbx <= 800)
-                       temp = 0x80;
-       } else {
-               temp = 0x80;
-               if (pVBInfo->VBInfo & SetCRT2ToLCD) {
-                       temp = 0;
-                       if (tempbx > 800)
-                               temp = 0x60;
+       if (pVBInfo->VBInfo & SetCRT2ToTV) { /*301b*/
+               if (pVBInfo->VGAHDE >= 1024) {
+                       tempcx = 0x1920;
+                       if (pVBInfo->VGAHDE >= 1280) {
+                               tempcx = 0x1420;
+                               tempbx = tempbx & 0xDFFF;
+                       }
                }
        }
 
-       if (pVBInfo->TVInfo & (SetYPbPrMode525p | SetYPbPrMode750p)) {
-               temp = 0x00;
-               if (pVBInfo->VGAHDE == 1280)
-                       temp = 0x40;
-               if (pVBInfo->VGAHDE == 1024)
-                       temp = 0x20;
-       }
-       XGINew_SetRegANDOR(pVBInfo->Part4Port, 0x0E, ~0xEF, temp);
+       if (!(tempbx & 0x2000)) {
+               if (modeflag & HalfDCLK)
+                       tempcx = (tempcx & 0xFF00) | ((tempcx & 0x00FF) << 1);
 
-       tempebx = pVBInfo->VDE;
+               push1 = tempbx;
+               tempeax = pVBInfo->VGAHDE;
+               tempebx = (tempcx & 0xFF00) >> 8;
+               longtemp = tempeax * tempebx;
+               tempecx = tempcx & 0x00FF;
+               longtemp = longtemp / tempecx;
 
-       if (tempcx & SetCRT2ToHiVisionTV) {
-               if (!(temp & 0xE000))
-                       tempbx = tempbx >> 1;
-       }
+               /* 301b */
+               tempecx = 8 * 1024;
 
-       tempcx = pVBInfo->RVBHRS;
-       temp = tempcx & 0x00FF;
-       XGINew_SetReg1(pVBInfo->Part4Port, 0x18, temp);
+               if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
+                               | VB_XGI302LV | VB_XGI301C)) {
+                       tempecx = tempecx * 8;
+               }
 
-       tempeax = pVBInfo->VGAVDE;
-       tempcx |= 0x04000;
+               longtemp = longtemp * tempecx;
+               tempecx = pVBInfo->HDE;
+               temp2 = longtemp % tempecx;
+               tempeax = longtemp / tempecx;
+               if (temp2 != 0)
+                       tempeax += 1;
 
-       if (tempeax <= tempebx) {
-               tempcx = (tempcx & (~0x4000));
-               tempeax = pVBInfo->VGAVDE;
-       } else {
-               tempeax -= tempebx;
-       }
+               tempax = (unsigned short) tempeax;
 
-       templong = (tempeax * 256 * 1024) % tempebx;
-       tempeax = (tempeax * 256 * 1024) / tempebx;
-       tempebx = tempeax;
+               /* 301b */
+               if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
+                               | VB_XGI302LV | VB_XGI301C)) {
+                       tempcx = ((tempax & 0xFF00) >> 5) >> 8;
+               }
+               /* end 301b */
 
-       if (templong != 0)
-               tempebx++;
+               tempbx = push1;
+               tempbx = (unsigned short) (((tempeax & 0x0000FF00) & 0x1F00)
+                               | (tempbx & 0x00FF));
+               tempax = (unsigned short) (((tempeax & 0x000000FF) << 8)
+                               | (tempax & 0x00FF));
+               temp = (tempax & 0xFF00) >> 8;
+       } else {
+               temp = (tempax & 0x00FF) >> 8;
+       }
 
-       temp = (unsigned short) (tempebx & 0x000000FF);
-       XGINew_SetReg1(pVBInfo->Part4Port, 0x1B, temp);
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x44, temp);
+       temp = (tempbx & 0xFF00) >> 8;
+       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x45, ~0x03F, temp);
+       temp = tempcx & 0x00FF;
 
-       temp = (unsigned short) ((tempebx & 0x0000FF00) >> 8);
-       XGINew_SetReg1(pVBInfo->Part4Port, 0x1A, temp);
-       tempbx = (unsigned short) (tempebx >> 16);
-       temp = tempbx & 0x00FF;
-       temp = temp << 4;
-       temp |= ((tempcx & 0xFF00) >> 8);
-       XGINew_SetReg1(pVBInfo->Part4Port, 0x19, temp);
+       if (tempbx & 0x2000)
+               temp = 0;
 
-       /* 301b */
-       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
-                       | VB_XGI302LV | VB_XGI301C)) {
-               temp = 0x0028;
-               XGINew_SetReg1(pVBInfo->Part4Port, 0x1C, temp);
-               tempax = pVBInfo->VGAHDE;
-               if (modeflag & HalfDCLK)
-                       tempax = tempax >> 1;
+       if (!(pVBInfo->VBInfo & SetCRT2ToLCD))
+               temp |= 0x18;
 
-               if (XGI_IsLCDDualLink(pVBInfo))
-                       tempax = tempax >> 1;
+       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x46, ~0x1F, temp);
+       if (pVBInfo->TVInfo & SetPALTV) {
+               tempbx = 0x0382;
+               tempcx = 0x007e;
+       } else {
+               tempbx = 0x0369;
+               tempcx = 0x0061;
+       }
 
-               /* if((pVBInfo->VBInfo&(SetCRT2ToLCD))||((pVBInfo->TVInfo&SetYPbPrMode525p)||(pVBInfo->TVInfo&SetYPbPrMode750p))) { */
-               if (pVBInfo->VBInfo & SetCRT2ToLCD) {
-                       if (tempax > 800)
-                               tempax -= 800;
-               } else {
-                       if (pVBInfo->VGAHDE > 800) {
-                               if (pVBInfo->VGAHDE == 1024)
-                                       tempax = (tempax * 25 / 32) - 1;
-                               else
-                                       tempax = (tempax * 20 / 32) - 1;
-                       }
-               }
-               tempax -= 1;
+       temp = tempbx & 0x00FF;
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x4b, temp);
+       temp = tempcx & 0x00FF;
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x4c, temp);
 
-               /*
-               if (pVBInfo->VBInfo & (SetCRT2ToTV | SetCRT2ToHiVisionTV)) {
-                       if (pVBInfo->VBType & VB_XGI301LV) {
-                               if (!(pVBInfo->TVInfo & (SetYPbPrMode525p | SetYPbPrMode750p | SetYPbPrMode1080i))) {
-                                       if (pVBInfo->VGAHDE > 800) {
-                                               if (pVBInfo->VGAHDE == 1024)
-                                                       tempax = (tempax * 25 / 32) - 1;
-                                               else
-                                                       tempax = (tempax * 20 / 32) - 1;
-                                       }
-                               }
-                       } else {
-                               if (pVBInfo->VGAHDE > 800) {
-                                       if (pVBInfo->VGAHDE == 1024)
-                                               tempax = (tempax * 25 / 32) - 1;
-                                       else
-                                               tempax = (tempax * 20 / 32) - 1;
-                               }
-                       }
-               }
-               */
+       temp = ((tempcx & 0xFF00) >> 8) & 0x03;
+       temp = temp << 2;
+       temp |= ((tempbx & 0xFF00) >> 8) & 0x03;
 
-               temp = (tempax & 0xFF00) >> 8;
-               temp = ((temp & 0x0003) << 4);
-               XGINew_SetReg1(pVBInfo->Part4Port, 0x1E, temp);
-               temp = (tempax & 0x00FF);
-               XGINew_SetReg1(pVBInfo->Part4Port, 0x1D, temp);
+       if (pVBInfo->VBInfo & SetCRT2ToYPbPr) {
+               temp |= 0x10;
 
-               if (pVBInfo->VBInfo & (SetCRT2ToTV | SetCRT2ToHiVisionTV)) {
-                       if (pVBInfo->VGAHDE > 800)
-                               XGINew_SetRegOR(pVBInfo->Part4Port, 0x1E, 0x08);
+               if (pVBInfo->TVInfo & SetYPbPrMode525p)
+                       temp |= 0x20;
 
-               }
-               temp = 0x0036;
+               if (pVBInfo->TVInfo & SetYPbPrMode750p)
+                       temp |= 0x60;
+       }
 
-               if (pVBInfo->VBInfo & SetCRT2ToTV) {
-                       if (!(pVBInfo->TVInfo & (NTSC1024x768
-                                       | SetYPbPrMode525p | SetYPbPrMode750p
-                                       | SetYPbPrMode1080i))) {
-                               temp |= 0x0001;
-                               if ((pVBInfo->VBInfo & SetInSlaveMode)
-                                               && (!(pVBInfo->TVInfo
-                                                               & TVSimuMode)))
-                                       temp &= (~0x0001);
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x4d, temp);
+       temp = XGINew_GetReg1(pVBInfo->Part2Port, 0x43); /* 301b change */
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x43, (unsigned short) (temp - 3));
+
+       if (!(pVBInfo->TVInfo & (SetYPbPrMode525p | SetYPbPrMode750p))) {
+               if (pVBInfo->TVInfo & NTSC1024x768) {
+                       TimingPoint = XGI_NTSC1024AdjTime;
+                       for (i = 0x1c, j = 0; i <= 0x30; i++, j++) {
+                               XGINew_SetReg1(pVBInfo->Part2Port, i,
+                                               TimingPoint[j]);
                        }
+                       XGINew_SetReg1(pVBInfo->Part2Port, 0x43, 0x72);
                }
+       }
 
-               XGINew_SetRegANDOR(pVBInfo->Part4Port, 0x1F, 0x00C0, temp);
-               tempbx = pVBInfo->HT;
-               if (XGI_IsLCDDualLink(pVBInfo))
-                       tempbx = tempbx >> 1;
-               tempbx = (tempbx >> 1) - 2;
-               temp = ((tempbx & 0x0700) >> 8) << 3;
-               XGINew_SetRegANDOR(pVBInfo->Part4Port, 0x21, 0x00C0, temp);
-               temp = tempbx & 0x00FF;
-               XGINew_SetReg1(pVBInfo->Part4Port, 0x22, temp);
+       /* [ycchen] 01/14/03 Modify for 301C PALM Support */
+       if (pVBInfo->VBType & VB_XGI301C) {
+               if (pVBInfo->TVInfo & SetPALMTV)
+                       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x4E, ~0x08,
+                                       0x08); /* PALM Mode */
        }
-       /* end 301b */
 
-       if (pVBInfo->ISXPDOS == 0)
-               XGI_SetCRT2VCLK(ModeNo, ModeIdIndex, RefreshRateTableIndex,
-                               pVBInfo);
-}
+       if (pVBInfo->TVInfo & SetPALMTV) {
+               tempax = (unsigned char) XGINew_GetReg1(pVBInfo->Part2Port,
+                               0x01);
+               tempax--;
+               XGINew_SetRegAND(pVBInfo->Part2Port, 0x01, tempax);
 
-static void XGI_SetGroup5(unsigned short ModeNo, unsigned short ModeIdIndex,
-               struct vb_device_info *pVBInfo)
-{
-       unsigned short Pindex, Pdata;
+               /* if ( !( pVBInfo->VBType & VB_XGI301C ) ) */
+               XGINew_SetRegAND(pVBInfo->Part2Port, 0x00, 0xEF);
+       }
 
-       Pindex = pVBInfo->Part5Port;
-       Pdata = pVBInfo->Part5Port + 1;
-       if (pVBInfo->ModeType == ModeVGA) {
-               if (!(pVBInfo->VBInfo & (SetInSlaveMode | LoadDACFlag
-                               | CRT2DisplayFlag))) {
-                       XGINew_EnableCRT2(pVBInfo);
-                       /* LoadDAC2(pVBInfo->Part5Port, ModeNo, ModeIdIndex); */
-               }
+       if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV) {
+               if (!(pVBInfo->VBInfo & SetInSlaveMode))
+                       XGINew_SetReg1(pVBInfo->Part2Port, 0x0B, 0x00);
        }
-       return;
+
+       if (pVBInfo->VBInfo & SetCRT2ToTV)
+               return;
 }
 
-static void *XGI_GetLcdPtr(unsigned short BX, unsigned short ModeNo,
-               unsigned short ModeIdIndex,
+static void XGI_SetLCDRegs(unsigned short ModeNo, unsigned short ModeIdIndex,
+               struct xgi_hw_device_info *HwDeviceExtension,
                unsigned short RefreshRateTableIndex,
                struct vb_device_info *pVBInfo)
 {
-       unsigned short i, tempdx, tempcx, tempbx, tempal, modeflag, table;
-
-       struct XGI330_LCDDataTablStruct *tempdi = NULL;
+       unsigned short push1, push2, pushbx, tempax, tempbx, tempcx, temp,
+                       tempah, tempbh, tempch, resinfo, modeflag, CRT1Index;
 
-       tempbx = BX;
+       struct XGI_LCDDesStruct *LCDBDesPtr = NULL;
 
        if (ModeNo <= 0x13) {
-               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag;
-               tempal = pVBInfo->SModeIDTable[ModeIdIndex].St_CRT2CRTC;
+               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag; /* si+St_ResInfo */
+               resinfo = pVBInfo->SModeIDTable[ModeIdIndex].St_ResInfo;
        } else {
-               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
-               tempal = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT2CRTC;
+               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag; /* si+Ext_ResInfo */
+               resinfo = pVBInfo->EModeIDTable[ModeIdIndex].Ext_RESINFO;
+               CRT1Index
+                               = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT1CRTC;
+               CRT1Index &= IndexMask;
        }
 
-       tempal = tempal & 0x0f;
+       if (!(pVBInfo->VBInfo & SetCRT2ToLCD))
+               return;
 
-       if (tempbx <= 1) { /* ExpLink */
-               if (ModeNo <= 0x13) {
-                       tempal = pVBInfo->SModeIDTable[ModeIdIndex].St_CRT2CRTC; /* find no Ext_CRT2CRTC2 */
-               } else {
-                       tempal
-                                       = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT2CRTC;
-               }
+       tempbx = pVBInfo->HDE; /* RHACTE=HDE-1 */
 
-               if (pVBInfo->VBInfo & SetCRT2ToLCDA) {
-                       if (ModeNo <= 0x13)
-                               tempal
-                                               = pVBInfo->SModeIDTable[ModeIdIndex].St_CRT2CRTC2;
-                       else
-                               tempal
-                                               = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT2CRTC2;
-               }
+       if (XGI_IsLCDDualLink(pVBInfo))
+               tempbx = tempbx >> 1;
 
-               if (tempbx & 0x01)
-                       tempal = (tempal >> 4);
+       tempbx -= 1;
+       temp = tempbx & 0x00FF;
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x2C, temp);
+       temp = (tempbx & 0xFF00) >> 8;
+       temp = temp << 4;
+       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x2B, 0x0F, temp);
+       temp = 0x01;
 
-               tempal = (tempal & 0x0f);
+       if (pVBInfo->LCDResInfo == Panel1280x1024) {
+               if (pVBInfo->ModeType == ModeEGA) {
+                       if (pVBInfo->VGAHDE >= 1024) {
+                               temp = 0x02;
+                               if (pVBInfo->LCDInfo & LCDVESATiming)
+                                       temp = 0x01;
+                       }
+               }
        }
 
-       tempcx = LCDLenList[tempbx]; /* mov cl,byte ptr cs:LCDLenList[bx] */
-
-       if (pVBInfo->LCDInfo & EnableScalingLCD) { /* ScaleLCD */
-               if ((tempbx == 5) || (tempbx) == 7)
-                       tempcx = LCDDesDataLen2;
-               else if ((tempbx == 3) || (tempbx == 8))
-                       tempcx = LVDSDesDataLen2;
-       }
-       /* mov di, word ptr cs:LCDDataList[bx] */
-       /* tempdi = pVideoMemory[LCDDataList + tempbx * 2] | (pVideoMemory[LCDDataList + tempbx * 2 + 1] << 8); */
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x0B, temp);
+       tempbx = pVBInfo->VDE; /* RTVACTEO=(VDE-1)&0xFF */
+       push1 = tempbx;
+       tempbx--;
+       temp = tempbx & 0x00FF;
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x03, temp);
+       temp = ((tempbx & 0xFF00) >> 8) & 0x07;
+       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x0C, ~0x07, temp);
 
-       switch (tempbx) {
-       case 0:
-               tempdi = XGI_EPLLCDCRT1Ptr_H;
-               break;
-       case 1:
-               tempdi = XGI_EPLLCDCRT1Ptr_V;
-               break;
-       case 2:
-               tempdi = XGI_EPLLCDDataPtr;
-               break;
-       case 3:
-               tempdi = XGI_EPLLCDDesDataPtr;
-               break;
-       case 4:
-               tempdi = XGI_LCDDataTable;
-               break;
-       case 5:
-               tempdi = XGI_LCDDesDataTable;
-               break;
-       case 6:
-               tempdi = XGI_EPLCHLCDRegPtr;
-               break;
-       case 7:
-       case 8:
-       case 9:
-               tempdi = NULL;
-               break;
-       default:
-               break;
-       }
+       tempcx = pVBInfo->VT - 1;
+       push2 = tempcx + 1;
+       temp = tempcx & 0x00FF; /* RVTVT=VT-1 */
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x19, temp);
+       temp = (tempcx & 0xFF00) >> 8;
+       temp = temp << 5;
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x1A, temp);
+       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x09, 0xF0, 0x00);
+       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x0A, 0xF0, 0x00);
+       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x17, 0xFB, 0x00);
+       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x18, 0xDF, 0x00);
 
-       if (tempdi == NULL) /* OEMUtil */
-               return NULL;
+       /* Customized LCDB Des no add */
+       tempbx = 5;
+       LCDBDesPtr = (struct XGI_LCDDesStruct *) XGI_GetLcdPtr(tempbx, ModeNo,
+                       ModeIdIndex, RefreshRateTableIndex, pVBInfo);
+       tempah = pVBInfo->LCDResInfo;
+       tempah &= PanelResInfo;
 
-       table = tempbx;
-       i = 0;
+       if ((tempah == Panel1024x768) || (tempah == Panel1024x768x75)) {
+               tempbx = 1024;
+               tempcx = 768;
+       } else if ((tempah == Panel1280x1024) || (tempah == Panel1280x1024x75)) {
+               tempbx = 1280;
+               tempcx = 1024;
+       } else if (tempah == Panel1400x1050) {
+               tempbx = 1400;
+               tempcx = 1050;
+       } else {
+               tempbx = 1600;
+               tempcx = 1200;
+       }
 
-       while (tempdi[i].PANELID != 0xff) {
-               tempdx = pVBInfo->LCDResInfo;
-               if (tempbx & 0x0080) { /* OEMUtil */
-                       tempbx &= (~0x0080);
-                       tempdx = pVBInfo->LCDTypeInfo;
-               }
+       if (pVBInfo->LCDInfo & EnableScalingLCD) {
+               tempbx = pVBInfo->HDE;
+               tempcx = pVBInfo->VDE;
+       }
 
-               if (pVBInfo->LCDInfo & EnableScalingLCD)
-                       tempdx &= (~PanelResInfo);
+       pushbx = tempbx;
+       tempax = pVBInfo->VT;
+       pVBInfo->LCDHDES = LCDBDesPtr->LCDHDES;
+       pVBInfo->LCDHRS = LCDBDesPtr->LCDHRS;
+       pVBInfo->LCDVDES = LCDBDesPtr->LCDVDES;
+       pVBInfo->LCDVRS = LCDBDesPtr->LCDVRS;
+       tempbx = pVBInfo->LCDVDES;
+       tempcx += tempbx;
 
-               if (tempdi[i].PANELID == tempdx) {
-                       tempbx = tempdi[i].MASK;
-                       tempdx = pVBInfo->LCDInfo;
+       if (tempcx >= tempax)
+               tempcx -= tempax; /* lcdvdes */
 
-                       if (ModeNo <= 0x13) /* alan 09/10/2003 */
-                               tempdx |= SetLCDStdMode;
+       temp = tempbx & 0x00FF; /* RVEQ1EQ=lcdvdes */
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x05, temp);
+       temp = tempcx & 0x00FF;
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x06, temp);
+       tempch = ((tempcx & 0xFF00) >> 8) & 0x07;
+       tempbh = ((tempbx & 0xFF00) >> 8) & 0x07;
+       tempah = tempch;
+       tempah = tempah << 3;
+       tempah |= tempbh;
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x02, tempah);
 
-                       if (modeflag & HalfDCLK)
-                               tempdx |= SetLCDLowResolution;
+       /* getlcdsync() */
+       XGI_GetLCDSync(&tempax, &tempbx, pVBInfo);
+       tempcx = tempbx;
+       tempax = pVBInfo->VT;
+       tempbx = pVBInfo->LCDVRS;
 
-                       tempbx &= tempdx;
-                       if (tempbx == tempdi[i].CAP)
-                               break;
-               }
-               i++;
-       }
+       /* if (SetLCD_Info & EnableScalingLCD) */
+       tempcx += tempbx;
+       if (tempcx >= tempax)
+               tempcx -= tempax;
 
-       if (table == 0) {
-               switch (tempdi[i].DATAPTR) {
-               case 0:
-                       return &XGI_LVDSCRT11024x768_1_H[tempal];
-                       break;
-               case 1:
-                       return &XGI_LVDSCRT11024x768_2_H[tempal];
-                       break;
-               case 2:
-                       return &XGI_LVDSCRT11280x1024_1_H[tempal];
-                       break;
-               case 3:
-                       return &XGI_LVDSCRT11280x1024_2_H[tempal];
-                       break;
-               case 4:
-                       return &XGI_LVDSCRT11400x1050_1_H[tempal];
-                       break;
-               case 5:
-                       return &XGI_LVDSCRT11400x1050_2_H[tempal];
-                       break;
-               case 6:
-                       return &XGI_LVDSCRT11600x1200_1_H[tempal];
-                       break;
-               case 7:
-                       return &XGI_LVDSCRT11024x768_1_Hx75[tempal];
-                       break;
-               case 8:
-                       return &XGI_LVDSCRT11024x768_2_Hx75[tempal];
-                       break;
-               case 9:
-                       return &XGI_LVDSCRT11280x1024_1_Hx75[tempal];
-                       break;
-               case 10:
-                       return &XGI_LVDSCRT11280x1024_2_Hx75[tempal];
-                       break;
-               default:
-                       break;
-               }
-       } else if (table == 1) {
-               switch (tempdi[i].DATAPTR) {
-               case 0:
-                       return &XGI_LVDSCRT11024x768_1_V[tempal];
-                       break;
-               case 1:
-                       return &XGI_LVDSCRT11024x768_2_V[tempal];
-                       break;
-               case 2:
-                       return &XGI_LVDSCRT11280x1024_1_V[tempal];
-                       break;
-               case 3:
-                       return &XGI_LVDSCRT11280x1024_2_V[tempal];
-                       break;
-               case 4:
-                       return &XGI_LVDSCRT11400x1050_1_V[tempal];
-                       break;
-               case 5:
-                       return &XGI_LVDSCRT11400x1050_2_V[tempal];
-                       break;
-               case 6:
-                       return &XGI_LVDSCRT11600x1200_1_V[tempal];
-                       break;
-               case 7:
-                       return &XGI_LVDSCRT11024x768_1_Vx75[tempal];
-                       break;
-               case 8:
-                       return &XGI_LVDSCRT11024x768_2_Vx75[tempal];
-                       break;
-               case 9:
-                       return &XGI_LVDSCRT11280x1024_1_Vx75[tempal];
-                       break;
-               case 10:
-                       return &XGI_LVDSCRT11280x1024_2_Vx75[tempal];
-                       break;
-               default:
-                       break;
-               }
-       } else if (table == 2) {
-               switch (tempdi[i].DATAPTR) {
-               case 0:
-                       return &XGI_LVDS1024x768Data_1[tempal];
-                       break;
-               case 1:
-                       return &XGI_LVDS1024x768Data_2[tempal];
-                       break;
-               case 2:
-                       return &XGI_LVDS1280x1024Data_1[tempal];
-                       break;
-               case 3:
-                       return &XGI_LVDS1280x1024Data_2[tempal];
-                       break;
-               case 4:
-                       return &XGI_LVDS1400x1050Data_1[tempal];
-                       break;
-               case 5:
-                       return &XGI_LVDS1400x1050Data_2[tempal];
-                       break;
-               case 6:
-                       return &XGI_LVDS1600x1200Data_1[tempal];
-                       break;
-               case 7:
-                       return &XGI_LVDSNoScalingData[tempal];
-                       break;
-               case 8:
-                       return &XGI_LVDS1024x768Data_1x75[tempal];
-                       break;
-               case 9:
-                       return &XGI_LVDS1024x768Data_2x75[tempal];
-                       break;
-               case 10:
-                       return &XGI_LVDS1280x1024Data_1x75[tempal];
-                       break;
-               case 11:
-                       return &XGI_LVDS1280x1024Data_2x75[tempal];
-                       break;
-               case 12:
-                       return &XGI_LVDSNoScalingDatax75[tempal];
-                       break;
-               default:
-                       break;
-               }
-       } else if (table == 3) {
-               switch (tempdi[i].DATAPTR) {
-               case 0:
-                       return &XGI_LVDS1024x768Des_1[tempal];
-                       break;
-               case 1:
-                       return &XGI_LVDS1024x768Des_3[tempal];
-                       break;
-               case 2:
-                       return &XGI_LVDS1024x768Des_2[tempal];
-                       break;
-               case 3:
-                       return &XGI_LVDS1280x1024Des_1[tempal];
-                       break;
-               case 4:
-                       return &XGI_LVDS1280x1024Des_2[tempal];
-                       break;
-               case 5:
-                       return &XGI_LVDS1400x1050Des_1[tempal];
-                       break;
-               case 6:
-                       return &XGI_LVDS1400x1050Des_2[tempal];
-                       break;
-               case 7:
-                       return &XGI_LVDS1600x1200Des_1[tempal];
-                       break;
-               case 8:
-                       return &XGI_LVDSNoScalingDesData[tempal];
-                       break;
-               case 9:
-                       return &XGI_LVDS1024x768Des_1x75[tempal];
-                       break;
-               case 10:
-                       return &XGI_LVDS1024x768Des_3x75[tempal];
-                       break;
-               case 11:
-                       return &XGI_LVDS1024x768Des_2x75[tempal];
-                       break;
-               case 12:
-                       return &XGI_LVDS1280x1024Des_1x75[tempal];
-                       break;
-               case 13:
-                       return &XGI_LVDS1280x1024Des_2x75[tempal];
-                       break;
-               case 14:
-                       return &XGI_LVDSNoScalingDesDatax75[tempal];
-                       break;
-               default:
-                       break;
+       temp = tempbx & 0x00FF; /* RTVACTEE=lcdvrs */
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x04, temp);
+       temp = (tempbx & 0xFF00) >> 8;
+       temp = temp << 4;
+       temp |= (tempcx & 0x000F);
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x01, temp);
+       tempcx = pushbx;
+       tempax = pVBInfo->HT;
+       tempbx = pVBInfo->LCDHDES;
+       tempbx &= 0x0FFF;
+
+       if (XGI_IsLCDDualLink(pVBInfo)) {
+               tempax = tempax >> 1;
+               tempbx = tempbx >> 1;
+               tempcx = tempcx >> 1;
+       }
+
+       if (pVBInfo->VBType & VB_XGI302LV)
+               tempbx += 1;
+
+       if (pVBInfo->VBType & VB_XGI301C) /* tap4 */
+               tempbx += 1;
+
+       tempcx += tempbx;
+
+       if (tempcx >= tempax)
+               tempcx -= tempax;
+
+       temp = tempbx & 0x00FF;
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x1F, temp); /* RHBLKE=lcdhdes */
+       temp = ((tempbx & 0xFF00) >> 8) << 4;
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x20, temp);
+       temp = tempcx & 0x00FF;
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x23, temp); /* RHEQPLE=lcdhdee */
+       temp = (tempcx & 0xFF00) >> 8;
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x25, temp);
+
+       /* getlcdsync() */
+       XGI_GetLCDSync(&tempax, &tempbx, pVBInfo);
+       tempcx = tempax;
+       tempax = pVBInfo->HT;
+       tempbx = pVBInfo->LCDHRS;
+       /* if ( SetLCD_Info & EnableScalingLCD) */
+       if (XGI_IsLCDDualLink(pVBInfo)) {
+               tempax = tempax >> 1;
+               tempbx = tempbx >> 1;
+               tempcx = tempcx >> 1;
+       }
+
+       if (pVBInfo->VBType & VB_XGI302LV)
+               tempbx += 1;
+
+       tempcx += tempbx;
+
+       if (tempcx >= tempax)
+               tempcx -= tempax;
+
+       temp = tempbx & 0x00FF; /* RHBURSTS=lcdhrs */
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x1C, temp);
+
+       temp = (tempbx & 0xFF00) >> 8;
+       temp = temp << 4;
+       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x1D, ~0x0F0, temp);
+       temp = tempcx & 0x00FF; /* RHSYEXP2S=lcdhre */
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x21, temp);
+
+       if (!(pVBInfo->LCDInfo & LCDVESATiming)) {
+               if (pVBInfo->VGAVDE == 525) {
+                       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B
+                                       | VB_XGI301LV | VB_XGI302LV
+                                       | VB_XGI301C)) {
+                               temp = 0xC6;
+                       } else
+                               temp = 0xC4;
+
+                       XGINew_SetReg1(pVBInfo->Part2Port, 0x2f, temp);
+                       XGINew_SetReg1(pVBInfo->Part2Port, 0x30, 0xB3);
                }
-       } else if (table == 4) {
-               switch (tempdi[i].DATAPTR) {
-               case 0:
-                       return &XGI_ExtLCD1024x768Data[tempal];
-                       break;
-               case 1:
-                       return &XGI_StLCD1024x768Data[tempal];
-                       break;
-               case 2:
-                       return &XGI_CetLCD1024x768Data[tempal];
-                       break;
-               case 3:
-                       return &XGI_ExtLCD1280x1024Data[tempal];
-                       break;
-               case 4:
-                       return &XGI_StLCD1280x1024Data[tempal];
-                       break;
-               case 5:
-                       return &XGI_CetLCD1280x1024Data[tempal];
-                       break;
-               case 6:
-                       return &XGI_ExtLCD1400x1050Data[tempal];
-                       break;
-               case 7:
-                       return &XGI_StLCD1400x1050Data[tempal];
-                       break;
-               case 8:
-                       return &XGI_CetLCD1400x1050Data[tempal];
-                       break;
-               case 9:
-                       return &XGI_ExtLCD1600x1200Data[tempal];
-                       break;
-               case 10:
-                       return &XGI_StLCD1600x1200Data[tempal];
-                       break;
-               case 11:
-                       return &XGI_NoScalingData[tempal];
-                       break;
-               case 12:
-                       return &XGI_ExtLCD1024x768x75Data[tempal];
-                       break;
-               case 13:
-                       return &XGI_ExtLCD1024x768x75Data[tempal];
-                       break;
-               case 14:
-                       return &XGI_CetLCD1024x768x75Data[tempal];
-                       break;
-               case 15:
-                       return &XGI_ExtLCD1280x1024x75Data[tempal];
-                       break;
-               case 16:
-                       return &XGI_StLCD1280x1024x75Data[tempal];
-                       break;
-               case 17:
-                       return &XGI_CetLCD1280x1024x75Data[tempal];
-                       break;
-               case 18:
-                       return &XGI_NoScalingDatax75[tempal];
-                       break;
-               default:
-                       break;
+
+               if (pVBInfo->VGAVDE == 420) {
+                       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B
+                                       | VB_XGI301LV | VB_XGI302LV
+                                       | VB_XGI301C)) {
+                               temp = 0x4F;
+                       } else
+                               temp = 0x4E;
+                       XGINew_SetReg1(pVBInfo->Part2Port, 0x2f, temp);
                }
-       } else if (table == 5) {
-               switch (tempdi[i].DATAPTR) {
-               case 0:
-                       return &XGI_ExtLCDDes1024x768Data[tempal];
-                       break;
-               case 1:
-                       return &XGI_StLCDDes1024x768Data[tempal];
-                       break;
-               case 2:
-                       return &XGI_CetLCDDes1024x768Data[tempal];
-                       break;
-               case 3:
-                       if ((pVBInfo->VBType & VB_XGI301LV) || (pVBInfo->VBType
-                                       & VB_XGI302LV))
-                               return &XGI_ExtLCDDLDes1280x1024Data[tempal];
-                       else
-                               return &XGI_ExtLCDDes1280x1024Data[tempal];
-                       break;
-               case 4:
-                       if ((pVBInfo->VBType & VB_XGI301LV) || (pVBInfo->VBType
-                                       & VB_XGI302LV))
-                               return &XGI_StLCDDLDes1280x1024Data[tempal];
-                       else
-                               return &XGI_StLCDDes1280x1024Data[tempal];
-                       break;
-               case 5:
-                       if ((pVBInfo->VBType & VB_XGI301LV) || (pVBInfo->VBType
-                                       & VB_XGI302LV))
-                               return &XGI_CetLCDDLDes1280x1024Data[tempal];
-                       else
-                               return &XGI_CetLCDDes1280x1024Data[tempal];
-                       break;
-               case 6:
-                       if ((pVBInfo->VBType & VB_XGI301LV) || (pVBInfo->VBType
-                                       & VB_XGI302LV))
-                               return &XGI_ExtLCDDLDes1400x1050Data[tempal];
-                       else
-                               return &XGI_ExtLCDDes1400x1050Data[tempal];
-                       break;
-               case 7:
-                       if ((pVBInfo->VBType & VB_XGI301LV) || (pVBInfo->VBType
-                                       & VB_XGI302LV))
-                               return &XGI_StLCDDLDes1400x1050Data[tempal];
-                       else
-                               return &XGI_StLCDDes1400x1050Data[tempal];
-                       break;
-               case 8:
-                       return &XGI_CetLCDDes1400x1050Data[tempal];
-                       break;
-               case 9:
-                       return &XGI_CetLCDDes1400x1050Data2[tempal];
-                       break;
-               case 10:
-                       if ((pVBInfo->VBType & VB_XGI301LV) || (pVBInfo->VBType
-                                       & VB_XGI302LV))
-                               return &XGI_ExtLCDDLDes1600x1200Data[tempal];
-                       else
-                               return &XGI_ExtLCDDes1600x1200Data[tempal];
-                       break;
-               case 11:
-                       if ((pVBInfo->VBType & VB_XGI301LV) || (pVBInfo->VBType
-                                       & VB_XGI302LV))
-                               return &XGI_StLCDDLDes1600x1200Data[tempal];
-                       else
-                               return &XGI_StLCDDes1600x1200Data[tempal];
-                       break;
-               case 12:
-                       return &XGI_NoScalingDesData[tempal];
-                       break;
-               case 13:
-                       return &XGI_ExtLCDDes1024x768x75Data[tempal];
-                       break;
-               case 14:
-                       return &XGI_StLCDDes1024x768x75Data[tempal];
-                       break;
-               case 15:
-                       return &XGI_CetLCDDes1024x768x75Data[tempal];
-                       break;
-               case 16:
-                       if ((pVBInfo->VBType & VB_XGI301LV) || (pVBInfo->VBType
-                                       & VB_XGI302LV))
-                               return &XGI_ExtLCDDLDes1280x1024x75Data[tempal];
-                       else
-                               return &XGI_ExtLCDDes1280x1024x75Data[tempal];
-                       break;
-               case 17:
-                       if ((pVBInfo->VBType & VB_XGI301LV) || (pVBInfo->VBType
-                                       & VB_XGI302LV))
-                               return &XGI_StLCDDLDes1280x1024x75Data[tempal];
-                       else
-                               return &XGI_StLCDDes1280x1024x75Data[tempal];
-                       break;
-               case 18:
-                       if ((pVBInfo->VBType & VB_XGI301LV) || (pVBInfo->VBType
-                                       & VB_XGI302LV))
-                               return &XGI_CetLCDDLDes1280x1024x75Data[tempal];
-                       else
-                               return &XGI_CetLCDDes1280x1024x75Data[tempal];
-                       break;
-               case 19:
-                       return &XGI_NoScalingDesDatax75[tempal];
-                       break;
-               default:
+       }
+}
+
+/* --------------------------------------------------------------------- */
+/* Function : XGI_GetTap4Ptr */
+/* Input : */
+/* Output : di -> Tap4 Reg. Setting Pointer */
+/* Description : */
+/* --------------------------------------------------------------------- */
+static struct XGI301C_Tap4TimingStruct *XGI_GetTap4Ptr(unsigned short tempcx,
+               struct vb_device_info *pVBInfo)
+{
+       unsigned short tempax, tempbx, i;
+
+       struct XGI301C_Tap4TimingStruct *Tap4TimingPtr;
+
+       if (tempcx == 0) {
+               tempax = pVBInfo->VGAHDE;
+               tempbx = pVBInfo->HDE;
+       } else {
+               tempax = pVBInfo->VGAVDE;
+               tempbx = pVBInfo->VDE;
+       }
+
+       if (tempax < tempbx)
+               return &EnlargeTap4Timing[0];
+       else if (tempax == tempbx)
+               return &NoScaleTap4Timing[0]; /* 1:1 */
+       else
+               Tap4TimingPtr = NTSCTap4Timing; /* NTSC */
+
+       if (pVBInfo->TVInfo & SetPALTV)
+               Tap4TimingPtr = PALTap4Timing;
+
+       if (pVBInfo->VBInfo & SetCRT2ToYPbPr) {
+               if (pVBInfo->TVInfo & SetYPbPrMode525i)
+                       Tap4TimingPtr = YPbPr525iTap4Timing;
+               if (pVBInfo->TVInfo & SetYPbPrMode525p)
+                       Tap4TimingPtr = YPbPr525pTap4Timing;
+               if (pVBInfo->TVInfo & SetYPbPrMode750p)
+                       Tap4TimingPtr = YPbPr750pTap4Timing;
+       }
+
+       if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV)
+               Tap4TimingPtr = HiTVTap4Timing;
+
+       i = 0;
+       while (Tap4TimingPtr[i].DE != 0xFFFF) {
+               if (Tap4TimingPtr[i].DE == tempax)
                        break;
+               i++;
+       }
+       return &Tap4TimingPtr[i];
+}
+
+static void XGI_SetTap4Regs(struct vb_device_info *pVBInfo)
+{
+       unsigned short i, j;
+
+       struct XGI301C_Tap4TimingStruct *Tap4TimingPtr;
+
+       if (!(pVBInfo->VBType & VB_XGI301C))
+               return;
+
+#ifndef Tap4
+       XGINew_SetRegAND(pVBInfo->Part2Port, 0x4E, 0xEB); /* Disable Tap4 */
+#else            /* Tap4 Setting */
+
+       Tap4TimingPtr = XGI_GetTap4Ptr(0, pVBInfo); /* Set Horizontal Scaling */
+       for (i = 0x80, j = 0; i <= 0xBF; i++, j++)
+               XGINew_SetReg1(pVBInfo->Part2Port, i, Tap4TimingPtr->Reg[j]);
+
+       if ((pVBInfo->VBInfo & SetCRT2ToTV) && (!(pVBInfo->VBInfo & SetCRT2ToHiVisionTV))) {
+               Tap4TimingPtr = XGI_GetTap4Ptr(1, pVBInfo); /* Set Vertical Scaling */
+               for (i = 0xC0, j = 0; i < 0xFF; i++, j++)
+                       XGINew_SetReg1(pVBInfo->Part2Port, i, Tap4TimingPtr->Reg[j]);
+       }
+
+       if ((pVBInfo->VBInfo & SetCRT2ToTV) && (!(pVBInfo->VBInfo & SetCRT2ToHiVisionTV)))
+               XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x4E, ~0x14, 0x04); /* Enable V.Scaling */
+       else
+               XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x4E, ~0x14, 0x10); /* Enable H.Scaling */
+#endif
+}
+
+static void XGI_SetGroup3(unsigned short ModeNo, unsigned short ModeIdIndex,
+               struct vb_device_info *pVBInfo)
+{
+       unsigned short i;
+       unsigned char *tempdi;
+       unsigned short modeflag;
+
+       if (ModeNo <= 0x13)
+               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag; /* si+St_ResInfo */
+       else
+               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag; /* si+Ext_ResInfo */
+
+       XGINew_SetReg1(pVBInfo->Part3Port, 0x00, 0x00);
+       if (pVBInfo->TVInfo & SetPALTV) {
+               XGINew_SetReg1(pVBInfo->Part3Port, 0x13, 0xFA);
+               XGINew_SetReg1(pVBInfo->Part3Port, 0x14, 0xC8);
+       } else {
+               XGINew_SetReg1(pVBInfo->Part3Port, 0x13, 0xF5);
+               XGINew_SetReg1(pVBInfo->Part3Port, 0x14, 0xB7);
+       }
+
+       if (!(pVBInfo->VBInfo & SetCRT2ToTV))
+               return;
+
+       if (pVBInfo->TVInfo & SetPALMTV) {
+               XGINew_SetReg1(pVBInfo->Part3Port, 0x13, 0xFA);
+               XGINew_SetReg1(pVBInfo->Part3Port, 0x14, 0xC8);
+               XGINew_SetReg1(pVBInfo->Part3Port, 0x3D, 0xA8);
+       }
+
+       if ((pVBInfo->VBInfo & SetCRT2ToHiVisionTV) || (pVBInfo->VBInfo
+                       & SetCRT2ToYPbPr)) {
+               if (pVBInfo->TVInfo & SetYPbPrMode525i)
+                       return;
+
+               tempdi = pVBInfo->HiTVGroup3Data;
+               if (pVBInfo->SetFlag & TVSimuMode) {
+                       tempdi = pVBInfo->HiTVGroup3Simu;
+                       if (!(modeflag & Charx8Dot))
+                               tempdi = pVBInfo->HiTVGroup3Text;
                }
-       } else if (table == 6) {
-               switch (tempdi[i].DATAPTR) {
-               case 0:
-                       return &XGI_CH7017LV1024x768[tempal];
-                       break;
-               case 1:
-                       return &XGI_CH7017LV1400x1050[tempal];
-                       break;
-               default:
-                       break;
+
+               if (pVBInfo->TVInfo & SetYPbPrMode525p)
+                       tempdi = pVBInfo->Ren525pGroup3;
+
+               if (pVBInfo->TVInfo & SetYPbPrMode750p)
+                       tempdi = pVBInfo->Ren750pGroup3;
+
+               for (i = 0; i <= 0x3E; i++)
+                       XGINew_SetReg1(pVBInfo->Part3Port, i, tempdi[i]);
+
+               if (pVBInfo->VBType & VB_XGI301C) { /* Marcovision */
+                       if (pVBInfo->TVInfo & SetYPbPrMode525p)
+                               XGINew_SetReg1(pVBInfo->Part3Port, 0x28, 0x3f);
                }
        }
-       return NULL;
-}
+       return;
+} /* {end of XGI_SetGroup3} */
 
-static void *XGI_GetTVPtr(unsigned short BX, unsigned short ModeNo,
-               unsigned short ModeIdIndex,
+static void XGI_SetGroup4(unsigned short ModeNo, unsigned short ModeIdIndex,
                unsigned short RefreshRateTableIndex,
+               struct xgi_hw_device_info *HwDeviceExtension,
                struct vb_device_info *pVBInfo)
 {
-       unsigned short i, tempdx, tempbx, tempal, modeflag, table;
-       struct XGI330_TVDataTablStruct *tempdi = NULL;
+       unsigned short tempax, tempcx, tempbx, modeflag, temp, temp2;
 
-       tempbx = BX;
+       unsigned long tempebx, tempeax, templong;
+
+       if (ModeNo <= 0x13)
+               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag; /* si+St_ResInfo */
+       else
+               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag; /* si+Ext_ResInfo */
+
+       temp = pVBInfo->RVBHCFACT;
+       XGINew_SetReg1(pVBInfo->Part4Port, 0x13, temp);
+
+       tempbx = pVBInfo->RVBHCMAX;
+       temp = tempbx & 0x00FF;
+       XGINew_SetReg1(pVBInfo->Part4Port, 0x14, temp);
+       temp2 = ((tempbx & 0xFF00) >> 8) << 7;
+       tempcx = pVBInfo->VGAHT - 1;
+       temp = tempcx & 0x00FF;
+       XGINew_SetReg1(pVBInfo->Part4Port, 0x16, temp);
+
+       temp = ((tempcx & 0xFF00) >> 8) << 3;
+       temp2 |= temp;
+
+       tempcx = pVBInfo->VGAVT - 1;
+       if (!(pVBInfo->VBInfo & SetCRT2ToTV))
+               tempcx -= 5;
+
+       temp = tempcx & 0x00FF;
+       XGINew_SetReg1(pVBInfo->Part4Port, 0x17, temp);
+       temp = temp2 | ((tempcx & 0xFF00) >> 8);
+       XGINew_SetReg1(pVBInfo->Part4Port, 0x15, temp);
+       XGINew_SetRegOR(pVBInfo->Part4Port, 0x0D, 0x08);
+       tempcx = pVBInfo->VBInfo;
+       tempbx = pVBInfo->VGAHDE;
+
+       if (modeflag & HalfDCLK)
+               tempbx = tempbx >> 1;
+
+       if (XGI_IsLCDDualLink(pVBInfo))
+               tempbx = tempbx >> 1;
+
+       if (tempcx & SetCRT2ToHiVisionTV) {
+               temp = 0;
+               if (tempbx <= 1024)
+                       temp = 0xA0;
+               if (tempbx == 1280)
+                       temp = 0xC0;
+       } else if (tempcx & SetCRT2ToTV) {
+               temp = 0xA0;
+               if (tempbx <= 800)
+                       temp = 0x80;
+       } else {
+               temp = 0x80;
+               if (pVBInfo->VBInfo & SetCRT2ToLCD) {
+                       temp = 0;
+                       if (tempbx > 800)
+                               temp = 0x60;
+               }
+       }
+
+       if (pVBInfo->TVInfo & (SetYPbPrMode525p | SetYPbPrMode750p)) {
+               temp = 0x00;
+               if (pVBInfo->VGAHDE == 1280)
+                       temp = 0x40;
+               if (pVBInfo->VGAHDE == 1024)
+                       temp = 0x20;
+       }
+       XGINew_SetRegANDOR(pVBInfo->Part4Port, 0x0E, ~0xEF, temp);
+
+       tempebx = pVBInfo->VDE;
+
+       if (tempcx & SetCRT2ToHiVisionTV) {
+               if (!(temp & 0xE000))
+                       tempbx = tempbx >> 1;
+       }
+
+       tempcx = pVBInfo->RVBHRS;
+       temp = tempcx & 0x00FF;
+       XGINew_SetReg1(pVBInfo->Part4Port, 0x18, temp);
+
+       tempeax = pVBInfo->VGAVDE;
+       tempcx |= 0x04000;
+
+       if (tempeax <= tempebx) {
+               tempcx = (tempcx & (~0x4000));
+               tempeax = pVBInfo->VGAVDE;
+       } else {
+               tempeax -= tempebx;
+       }
+
+       templong = (tempeax * 256 * 1024) % tempebx;
+       tempeax = (tempeax * 256 * 1024) / tempebx;
+       tempebx = tempeax;
+
+       if (templong != 0)
+               tempebx++;
+
+       temp = (unsigned short) (tempebx & 0x000000FF);
+       XGINew_SetReg1(pVBInfo->Part4Port, 0x1B, temp);
+
+       temp = (unsigned short) ((tempebx & 0x0000FF00) >> 8);
+       XGINew_SetReg1(pVBInfo->Part4Port, 0x1A, temp);
+       tempbx = (unsigned short) (tempebx >> 16);
+       temp = tempbx & 0x00FF;
+       temp = temp << 4;
+       temp |= ((tempcx & 0xFF00) >> 8);
+       XGINew_SetReg1(pVBInfo->Part4Port, 0x19, temp);
+
+       /* 301b */
+       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
+                       | VB_XGI302LV | VB_XGI301C)) {
+               temp = 0x0028;
+               XGINew_SetReg1(pVBInfo->Part4Port, 0x1C, temp);
+               tempax = pVBInfo->VGAHDE;
+               if (modeflag & HalfDCLK)
+                       tempax = tempax >> 1;
 
-       if (ModeNo <= 0x13) {
-               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag;
-               tempal = pVBInfo->SModeIDTable[ModeIdIndex].St_CRT2CRTC;
-       } else {
-               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
-               tempal = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT2CRTC;
-       }
+               if (XGI_IsLCDDualLink(pVBInfo))
+                       tempax = tempax >> 1;
 
-       tempal = tempal & 0x3f;
-       table = tempbx;
+               /* if((pVBInfo->VBInfo&(SetCRT2ToLCD))||((pVBInfo->TVInfo&SetYPbPrMode525p)||(pVBInfo->TVInfo&SetYPbPrMode750p))) { */
+               if (pVBInfo->VBInfo & SetCRT2ToLCD) {
+                       if (tempax > 800)
+                               tempax -= 800;
+               } else {
+                       if (pVBInfo->VGAHDE > 800) {
+                               if (pVBInfo->VGAHDE == 1024)
+                                       tempax = (tempax * 25 / 32) - 1;
+                               else
+                                       tempax = (tempax * 20 / 32) - 1;
+                       }
+               }
+               tempax -= 1;
 
-       switch (tempbx) {
-       case 0:
-               tempdi = NULL; /*EPLCHTVCRT1Ptr_H;*/
-               if (pVBInfo->IF_DEF_CH7007 == 1)
-                       tempdi = XGI_EPLCHTVCRT1Ptr;
+               /*
+               if (pVBInfo->VBInfo & (SetCRT2ToTV | SetCRT2ToHiVisionTV)) {
+                       if (pVBInfo->VBType & VB_XGI301LV) {
+                               if (!(pVBInfo->TVInfo & (SetYPbPrMode525p | SetYPbPrMode750p | SetYPbPrMode1080i))) {
+                                       if (pVBInfo->VGAHDE > 800) {
+                                               if (pVBInfo->VGAHDE == 1024)
+                                                       tempax = (tempax * 25 / 32) - 1;
+                                               else
+                                                       tempax = (tempax * 20 / 32) - 1;
+                                       }
+                               }
+                       } else {
+                               if (pVBInfo->VGAHDE > 800) {
+                                       if (pVBInfo->VGAHDE == 1024)
+                                               tempax = (tempax * 25 / 32) - 1;
+                                       else
+                                               tempax = (tempax * 20 / 32) - 1;
+                               }
+                       }
+               }
+               */
 
-               break;
-       case 1:
-               tempdi = NULL; /*EPLCHTVCRT1Ptr_V;*/
-               if (pVBInfo->IF_DEF_CH7007 == 1)
-                       tempdi = XGI_EPLCHTVCRT1Ptr;
+               temp = (tempax & 0xFF00) >> 8;
+               temp = ((temp & 0x0003) << 4);
+               XGINew_SetReg1(pVBInfo->Part4Port, 0x1E, temp);
+               temp = (tempax & 0x00FF);
+               XGINew_SetReg1(pVBInfo->Part4Port, 0x1D, temp);
 
-               break;
-       case 2:
-               tempdi = XGI_EPLCHTVDataPtr;
-               break;
-       case 3:
-               tempdi = NULL;
-               break;
-       case 4:
-               tempdi = XGI_TVDataTable;
-               break;
-       case 5:
-               tempdi = NULL;
-               break;
-       case 6:
-               tempdi = XGI_EPLCHTVRegPtr;
-               break;
-       default:
-               break;
-       }
+               if (pVBInfo->VBInfo & (SetCRT2ToTV | SetCRT2ToHiVisionTV)) {
+                       if (pVBInfo->VGAHDE > 800)
+                               XGINew_SetRegOR(pVBInfo->Part4Port, 0x1E, 0x08);
 
-       if (tempdi == NULL) /* OEMUtil */
-               return NULL;
+               }
+               temp = 0x0036;
 
-       tempdx = pVBInfo->TVInfo;
+               if (pVBInfo->VBInfo & SetCRT2ToTV) {
+                       if (!(pVBInfo->TVInfo & (NTSC1024x768
+                                       | SetYPbPrMode525p | SetYPbPrMode750p
+                                       | SetYPbPrMode1080i))) {
+                               temp |= 0x0001;
+                               if ((pVBInfo->VBInfo & SetInSlaveMode)
+                                               && (!(pVBInfo->TVInfo
+                                                               & TVSimuMode)))
+                                       temp &= (~0x0001);
+                       }
+               }
 
-       if (pVBInfo->VBInfo & SetInSlaveMode)
-               tempdx = tempdx | SetTVLockMode;
+               XGINew_SetRegANDOR(pVBInfo->Part4Port, 0x1F, 0x00C0, temp);
+               tempbx = pVBInfo->HT;
+               if (XGI_IsLCDDualLink(pVBInfo))
+                       tempbx = tempbx >> 1;
+               tempbx = (tempbx >> 1) - 2;
+               temp = ((tempbx & 0x0700) >> 8) << 3;
+               XGINew_SetRegANDOR(pVBInfo->Part4Port, 0x21, 0x00C0, temp);
+               temp = tempbx & 0x00FF;
+               XGINew_SetReg1(pVBInfo->Part4Port, 0x22, temp);
+       }
+       /* end 301b */
 
-       if (modeflag & HalfDCLK)
-               tempdx = tempdx | SetTVLowResolution;
+       if (pVBInfo->ISXPDOS == 0)
+               XGI_SetCRT2VCLK(ModeNo, ModeIdIndex, RefreshRateTableIndex,
+                               pVBInfo);
+}
 
-       i = 0;
+static void XGINew_EnableCRT2(struct vb_device_info *pVBInfo)
+{
+       XGINew_SetRegANDOR(pVBInfo->P3c4, 0x1E, 0xFF, 0x20);
+}
 
-       while (tempdi[i].MASK != 0xffff) {
-               if ((tempdx & tempdi[i].MASK) == tempdi[i].CAP)
-                       break;
-               i++;
-       }
+static void XGI_SetGroup5(unsigned short ModeNo, unsigned short ModeIdIndex,
+               struct vb_device_info *pVBInfo)
+{
+       unsigned short Pindex, Pdata;
 
-       if (table == 0x00) { /* 07/05/22 */
-       } else if (table == 0x01) {
-       } else if (table == 0x04) {
-               switch (tempdi[i].DATAPTR) {
-               case 0:
-                       return &XGI_ExtPALData[tempal];
-                       break;
-               case 1:
-                       return &XGI_ExtNTSCData[tempal];
-                       break;
-               case 2:
-                       return &XGI_StPALData[tempal];
-                       break;
-               case 3:
-                       return &XGI_StNTSCData[tempal];
-                       break;
-               case 4:
-                       return &XGI_ExtHiTVData[tempal];
-                       break;
-               case 5:
-                       return &XGI_St2HiTVData[tempal];
-                       break;
-               case 6:
-                       return &XGI_ExtYPbPr525iData[tempal];
-                       break;
-               case 7:
-                       return &XGI_ExtYPbPr525pData[tempal];
-                       break;
-               case 8:
-                       return &XGI_ExtYPbPr750pData[tempal];
-                       break;
-               case 9:
-                       return &XGI_StYPbPr525iData[tempal];
-                       break;
-               case 10:
-                       return &XGI_StYPbPr525pData[tempal];
-                       break;
-               case 11:
-                       return &XGI_StYPbPr750pData[tempal];
-                       break;
-               case 12: /* avoid system hang */
-                       return &XGI_ExtNTSCData[tempal];
-                       break;
-               case 13:
-                       return &XGI_St1HiTVData[tempal];
-                       break;
-               default:
-                       break;
-               }
-       } else if (table == 0x02) {
-               switch (tempdi[i].DATAPTR) {
-               case 0:
-                       return &XGI_CHTVUNTSCData[tempal];
-                       break;
-               case 1:
-                       return &XGI_CHTVONTSCData[tempal];
-                       break;
-               case 2:
-                       return &XGI_CHTVUPALData[tempal];
-                       break;
-               case 3:
-                       return &XGI_CHTVOPALData[tempal];
-                       break;
-               default:
-                       break;
+       Pindex = pVBInfo->Part5Port;
+       Pdata = pVBInfo->Part5Port + 1;
+       if (pVBInfo->ModeType == ModeVGA) {
+               if (!(pVBInfo->VBInfo & (SetInSlaveMode | LoadDACFlag
+                               | CRT2DisplayFlag))) {
+                       XGINew_EnableCRT2(pVBInfo);
+                       /* LoadDAC2(pVBInfo->Part5Port, ModeNo, ModeIdIndex); */
                }
-       } else if (table == 0x06) {
        }
-       return NULL;
+       return;
 }
 
 /* --------------------------------------------------------------------- */
@@ -6680,69 +6376,12 @@ static void XGI_SetPanelDelay(unsigned short tempbl, struct vb_device_info *pVBI
 static void XGI_SetPanelPower(unsigned short tempah, unsigned short tempbl,
                struct vb_device_info *pVBInfo)
 {
-       if (pVBInfo->VBType & (VB_XGI301LV | VB_XGI302LV | VB_XGI301C))
-               XGINew_SetRegANDOR(pVBInfo->Part4Port, 0x26, tempbl, tempah);
-       else
-               XGINew_SetRegANDOR(pVBInfo->P3c4, 0x11, tempbl, tempah);
-}
-
-static unsigned char XG21GPIODataTransfer(unsigned char ujDate)
-{
-       unsigned char ujRet = 0;
-       unsigned char i = 0;
-
-       for (i = 0; i < 8; i++) {
-               ujRet = ujRet << 1;
-               /* ujRet |= GETBITS(ujDate >> i, 0:0); */
-               ujRet |= (ujDate >> i) & 1;
-       }
-
-       return ujRet;
-}
-
-/*----------------------------------------------------------------------------*/
-/* output                                                                     */
-/*      bl[5] : LVDS signal                                                   */
-/*      bl[1] : LVDS backlight                                                */
-/*      bl[0] : LVDS VDD                                                      */
-/*----------------------------------------------------------------------------*/
-static unsigned char XGI_XG21GetPSCValue(struct vb_device_info *pVBInfo)
-{
-       unsigned char CR4A, temp;
-
-       CR4A = XGINew_GetReg1(pVBInfo->P3d4, 0x4A);
-       XGINew_SetRegAND(pVBInfo->P3d4, 0x4A, ~0x23); /* enable GPIO write */
-
-       temp = XGINew_GetReg1(pVBInfo->P3d4, 0x48);
-
-       temp = XG21GPIODataTransfer(temp);
-       temp &= 0x23;
-       XGINew_SetReg1(pVBInfo->P3d4, 0x4A, CR4A);
-       return temp;
-}
-
-/*----------------------------------------------------------------------------*/
-/* output                                                                     */
-/*      bl[5] : LVDS signal                                                   */
-/*      bl[1] : LVDS backlight                                                */
-/*      bl[0] : LVDS VDD                                                      */
-/*----------------------------------------------------------------------------*/
-static unsigned char XGI_XG27GetPSCValue(struct vb_device_info *pVBInfo)
-{
-       unsigned char CR4A, CRB4, temp;
-
-       CR4A = XGINew_GetReg1(pVBInfo->P3d4, 0x4A);
-       XGINew_SetRegAND(pVBInfo->P3d4, 0x4A, ~0x0C); /* enable GPIO write */
-
-       temp = XGINew_GetReg1(pVBInfo->P3d4, 0x48);
-
-       temp &= 0x0C;
-       temp >>= 2;
-       XGINew_SetReg1(pVBInfo->P3d4, 0x4A, CR4A);
-       CRB4 = XGINew_GetReg1(pVBInfo->P3d4, 0xB4);
-       temp |= ((CRB4 & 0x04) << 3);
-       return temp;
+       if (pVBInfo->VBType & (VB_XGI301LV | VB_XGI302LV | VB_XGI301C))
+               XGINew_SetRegANDOR(pVBInfo->Part4Port, 0x26, tempbl, tempah);
+       else
+               XGINew_SetRegANDOR(pVBInfo->P3c4, 0x11, tempbl, tempah);
 }
+
 /*----------------------------------------------------------------------------*/
 /* input                                                                      */
 /*      bl[5] : 1;LVDS signal on                                              */
@@ -7386,453 +7025,575 @@ static unsigned char XGI_EnableChISLCD(struct vb_device_info *pVBInfo)
        if (tempah & 0x01) /* Chk LCDB Mode */
                return 1;
 
-       return 0;
+       return 0;
+}
+
+void XGI_DisableBridge(struct xgi_hw_device_info *HwDeviceExtension,
+               struct vb_device_info *pVBInfo)
+{
+       unsigned short tempax, tempbx, tempah = 0, tempbl = 0;
+
+       if (pVBInfo->SetFlag == Win9xDOSMode)
+               return;
+
+       if (HwDeviceExtension->jChipType < XG40) {
+               if ((!(pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)))
+                               || (XGI_DisableChISLCD(pVBInfo))) {
+                       if (!XGI_IsLCDON(pVBInfo)) {
+                               if (pVBInfo->LCDInfo & SetPWDEnable)
+                                       XGI_EnablePWD(pVBInfo);
+                               else {
+                                       pVBInfo->LCDInfo &= ~SetPWDEnable;
+                                       XGI_DisablePWD(pVBInfo);
+                                       if (pVBInfo->VBType & (VB_XGI301LV
+                                                       | VB_XGI302LV
+                                                       | VB_XGI301C)) {
+                                               tempbx = 0xFE; /* not 01h */
+                                               tempax = 0;
+                                       } else {
+                                               tempbx = 0xF7; /* not 08h */
+                                               tempax = 0x08;
+                                       }
+                                       XGI_SetPanelPower(tempax, tempbx,
+                                                       pVBInfo);
+                                       XGI_SetPanelDelay(3, pVBInfo);
+                               }
+                       } /* end if (!XGI_IsLCDON(pVBInfo)) */
+               }
+       }
+
+       /*
+       if (CH7017) {
+               if (!(pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2toLCDA)) || (XGI_DisableChISLCD(pVBInfo))) {
+                       if (!XGI_IsLCDON(pVBInfo)) {
+                               if (DISCHARGE) {
+                                       tempbx = XGINew_GetCH7005(0x61);
+                                       if (tempbx < 0x01) // first time we power up
+                                               XGINew_SetCH7005(0x0066); // and disable power sequence
+                                       else
+                                               XGINew_SetCH7005(0x5f66); // leave VDD on - disable power
+                               }
+                       }
+               }
+       }
+       */
+
+       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
+                       | VB_XGI302LV | VB_XGI301C)) {
+               tempah = 0x3F;
+               if (!(pVBInfo->VBInfo & (DisableCRT2Display | SetSimuScanMode))) {
+                       if (pVBInfo->VBInfo & SetCRT2ToLCDA) {
+                               if (pVBInfo->VBInfo & SetCRT2ToDualEdge) {
+                                       tempah = 0x7F; /* Disable Channel A */
+                                       if (!(pVBInfo->VBInfo & SetCRT2ToLCDA))
+                                               tempah = 0xBF; /* Disable Channel B */
+
+                                       if (pVBInfo->SetFlag & DisableChB)
+                                               tempah &= 0xBF; /* force to disable Cahnnel */
+
+                                       if (pVBInfo->SetFlag & DisableChA)
+                                               tempah &= 0x7F; /* Force to disable Channel B */
+                               }
+                       }
+               }
+
+               XGINew_SetRegAND(pVBInfo->Part4Port, 0x1F, tempah); /* disable part4_1f */
+
+               if (pVBInfo->VBType & (VB_XGI302LV | VB_XGI301C)) {
+                       if (((pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)))
+                                       || (XGI_DisableChISLCD(pVBInfo))
+                                       || (XGI_IsLCDON(pVBInfo)))
+                               XGINew_SetRegOR(pVBInfo->Part4Port, 0x30, 0x80); /* LVDS Driver power down */
+               }
+
+               if ((pVBInfo->SetFlag & DisableChA) || (pVBInfo->VBInfo
+                               & (DisableCRT2Display | SetCRT2ToLCDA
+                                               | SetSimuScanMode))) {
+                       if (pVBInfo->SetFlag & GatingCRT)
+                               XGI_EnableGatingCRT(HwDeviceExtension, pVBInfo);
+                       XGI_DisplayOff(HwDeviceExtension, pVBInfo);
+               }
+
+               if (pVBInfo->VBInfo & SetCRT2ToLCDA) {
+                       if ((pVBInfo->SetFlag & DisableChA) || (pVBInfo->VBInfo
+                                       & SetCRT2ToLCDA))
+                               XGINew_SetRegAND(pVBInfo->Part1Port, 0x1e, 0xdf); /* Power down */
+               }
+
+               XGINew_SetRegAND(pVBInfo->P3c4, 0x32, 0xdf); /* disable TV as primary VGA swap */
+
+               if ((pVBInfo->VBInfo & (SetSimuScanMode | SetCRT2ToDualEdge)))
+                       XGINew_SetRegAND(pVBInfo->Part2Port, 0x00, 0xdf);
+
+               if ((pVBInfo->SetFlag & DisableChB) || (pVBInfo->VBInfo
+                               & (DisableCRT2Display | SetSimuScanMode))
+                               || ((!(pVBInfo->VBInfo & SetCRT2ToLCDA))
+                                               && (pVBInfo->VBInfo
+                                                               & (SetCRT2ToRAMDAC
+                                                                               | SetCRT2ToLCD
+                                                                               | SetCRT2ToTV))))
+                       XGINew_SetRegOR(pVBInfo->Part1Port, 0x00, 0x80); /* BScreenOff=1 */
+
+               if ((pVBInfo->SetFlag & DisableChB) || (pVBInfo->VBInfo
+                               & (DisableCRT2Display | SetSimuScanMode))
+                               || (!(pVBInfo->VBInfo & SetCRT2ToLCDA))
+                               || (pVBInfo->VBInfo & (SetCRT2ToRAMDAC
+                                               | SetCRT2ToLCD | SetCRT2ToTV))) {
+                       tempah = XGINew_GetReg1(pVBInfo->Part1Port, 0x00); /* save Part1 index 0 */
+                       XGINew_SetRegOR(pVBInfo->Part1Port, 0x00, 0x10); /* BTDAC = 1, avoid VB reset */
+                       XGINew_SetRegAND(pVBInfo->Part1Port, 0x1E, 0xDF); /* disable CRT2 */
+                       XGINew_SetReg1(pVBInfo->Part1Port, 0x00, tempah); /* restore Part1 index 0 */
+               }
+       } else { /* {301} */
+               if (pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToTV)) {
+                       XGINew_SetRegOR(pVBInfo->Part1Port, 0x00, 0x80); /* BScreenOff=1 */
+                       XGINew_SetRegAND(pVBInfo->Part1Port, 0x1E, 0xDF); /* Disable CRT2 */
+                       XGINew_SetRegAND(pVBInfo->P3c4, 0x32, 0xDF); /* Disable TV asPrimary VGA swap */
+               }
+
+               if (pVBInfo->VBInfo & (DisableCRT2Display | SetCRT2ToLCDA
+                               | SetSimuScanMode))
+                       XGI_DisplayOff(HwDeviceExtension, pVBInfo);
+       }
+
+       if (HwDeviceExtension->jChipType < XG40) {
+               if (!(pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA))
+                               || (XGI_DisableChISLCD(pVBInfo))
+                               || (XGI_IsLCDON(pVBInfo))) {
+                       if (pVBInfo->LCDInfo & SetPWDEnable) {
+                               if (pVBInfo->LCDInfo & SetPWDEnable)
+                                       XGI_BacklightByDrv(pVBInfo);
+                               else {
+                                       XGI_SetPanelDelay(4, pVBInfo);
+                                       if (pVBInfo->VBType & VB_XGI301LV) {
+                                               tempbl = 0xFD;
+                                               tempah = 0x00;
+                                       } else {
+                                               tempbl = 0xFB;
+                                               tempah = 0x04;
+                                       }
+                               }
+                       }
+                       XGI_SetPanelPower(tempah, tempbl, pVBInfo);
+               }
+       }
+}
+
+/* --------------------------------------------------------------------- */
+/* Function : XGI_GetTVPtrIndex */
+/* Input : */
+/* Output : */
+/* Description : bx 0 : ExtNTSC */
+/* 1 : StNTSC */
+/* 2 : ExtPAL */
+/* 3 : StPAL */
+/* 4 : ExtHiTV */
+/* 5 : StHiTV */
+/* 6 : Ext525i */
+/* 7 : St525i */
+/* 8 : Ext525p */
+/* 9 : St525p */
+/* A : Ext750p */
+/* B : St750p */
+/* --------------------------------------------------------------------- */
+static unsigned short XGI_GetTVPtrIndex(struct vb_device_info *pVBInfo)
+{
+       unsigned short tempbx = 0;
+
+       if (pVBInfo->TVInfo & SetPALTV)
+               tempbx = 2;
+       if (pVBInfo->TVInfo & SetYPbPrMode1080i)
+               tempbx = 4;
+       if (pVBInfo->TVInfo & SetYPbPrMode525i)
+               tempbx = 6;
+       if (pVBInfo->TVInfo & SetYPbPrMode525p)
+               tempbx = 8;
+       if (pVBInfo->TVInfo & SetYPbPrMode750p)
+               tempbx = 10;
+       if (pVBInfo->TVInfo & TVSimuMode)
+               tempbx++;
+
+       return tempbx;
+}
+
+/* --------------------------------------------------------------------- */
+/* Function : XGI_GetTVPtrIndex2 */
+/* Input : */
+/* Output : bx 0 : NTSC */
+/* 1 : PAL */
+/* 2 : PALM */
+/* 3 : PALN */
+/* 4 : NTSC1024x768 */
+/* 5 : PAL-M 1024x768 */
+/* 6-7: reserved */
+/* cl 0 : YFilter1 */
+/* 1 : YFilter2 */
+/* ch 0 : 301A */
+/* 1 : 301B/302B/301LV/302LV */
+/* Description : */
+/* --------------------------------------------------------------------- */
+static void XGI_GetTVPtrIndex2(unsigned short *tempbx, unsigned char *tempcl,
+               unsigned char *tempch, struct vb_device_info *pVBInfo)
+{
+       *tempbx = 0;
+       *tempcl = 0;
+       *tempch = 0;
+
+       if (pVBInfo->TVInfo & SetPALTV)
+               *tempbx = 1;
+
+       if (pVBInfo->TVInfo & SetPALMTV)
+               *tempbx = 2;
+
+       if (pVBInfo->TVInfo & SetPALNTV)
+               *tempbx = 3;
+
+       if (pVBInfo->TVInfo & NTSC1024x768) {
+               *tempbx = 4;
+               if (pVBInfo->TVInfo & SetPALMTV)
+                       *tempbx = 5;
+       }
+
+       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
+                       | VB_XGI302LV | VB_XGI301C)) {
+               if ((!(pVBInfo->VBInfo & SetInSlaveMode)) || (pVBInfo->TVInfo
+                               & TVSimuMode)) {
+                       *tempbx += 8;
+                       *tempcl += 1;
+               }
+       }
+
+       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
+                       | VB_XGI302LV | VB_XGI301C))
+               (*tempch)++;
 }
 
-static unsigned short XGI_GetLCDCapPtr(struct vb_device_info *pVBInfo)
+static void XGI_SetDelayComp(struct vb_device_info *pVBInfo)
 {
-       unsigned char tempal, tempah, tempbl, i;
-
-       tempah = XGINew_GetReg1(pVBInfo->P3d4, 0x36);
-       tempal = tempah & 0x0F;
-       tempah = tempah & 0xF0;
-       i = 0;
-       tempbl = pVBInfo->LCDCapList[i].LCD_ID;
+       unsigned short index;
 
-       while (tempbl != 0xFF) {
-               if (tempbl & 0x80) { /* OEMUtil */
-                       tempal = tempah;
-                       tempbl = tempbl & ~(0x80);
-               }
+       unsigned char tempah, tempbl, tempbh;
 
-               if (tempal == tempbl)
-                       break;
+       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
+                       | VB_XGI302LV | VB_XGI301C)) {
+               if (pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA
+                               | SetCRT2ToTV | SetCRT2ToRAMDAC)) {
+                       tempbl = 0;
+                       tempbh = 0;
 
-               i++;
+                       index = XGI_GetTVPtrIndex(pVBInfo); /* Get TV Delay */
+                       tempbl = pVBInfo->XGI_TVDelayList[index];
 
-               tempbl = pVBInfo->LCDCapList[i].LCD_ID;
-       }
+                       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B
+                                       | VB_XGI301LV | VB_XGI302LV
+                                       | VB_XGI301C))
+                               tempbl = pVBInfo->XGI_TVDelayList2[index];
 
-       return i;
-}
+                       if (pVBInfo->VBInfo & SetCRT2ToDualEdge)
+                               tempbl = tempbl >> 4;
+                       /*
+                       if (pVBInfo->VBInfo & SetCRT2ToRAMDAC)
+                               tempbl = CRT2Delay1;    // Get CRT2 Delay
+                       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV | VB_XGI302LV | VB_XGI301C))
+                               tempbl = CRT2Delay2;
+                       */
+                       if (pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
+                               index = XGI_GetLCDCapPtr(pVBInfo); /* Get LCD Delay */
+                               tempbh = pVBInfo->LCDCapList[index].LCD_DelayCompensation;
 
-static unsigned short XGI_GetLCDCapPtr1(struct vb_device_info *pVBInfo)
-{
-       unsigned short tempah, tempal, tempbl, i;
+                               if (!(pVBInfo->VBInfo & SetCRT2ToLCDA))
+                                       tempbl = tempbh;
+                       }
 
-       tempal = pVBInfo->LCDResInfo;
-       tempah = pVBInfo->LCDTypeInfo;
+                       tempbl &= 0x0F;
+                       tempbh &= 0xF0;
+                       tempah = XGINew_GetReg1(pVBInfo->Part1Port, 0x2D);
 
-       i = 0;
-       tempbl = pVBInfo->LCDCapList[i].LCD_ID;
+                       if (pVBInfo->VBInfo & (SetCRT2ToRAMDAC | SetCRT2ToLCD
+                                       | SetCRT2ToTV)) { /* Channel B */
+                               tempah &= 0xF0;
+                               tempah |= tempbl;
+                       }
 
-       while (tempbl != 0xFF) {
-               if ((tempbl & 0x80) && (tempbl != 0x80)) {
-                       tempal = tempah;
-                       tempbl &= ~0x80;
+                       if (pVBInfo->VBInfo & SetCRT2ToLCDA) { /* Channel A */
+                               tempah &= 0x0F;
+                               tempah |= tempbh;
+                       }
+                       XGINew_SetReg1(pVBInfo->Part1Port, 0x2D, tempah);
+               }
+       } else if (pVBInfo->IF_DEF_LVDS == 1) {
+               tempbl = 0;
+               tempbh = 0;
+               if (pVBInfo->VBInfo & SetCRT2ToLCD) {
+                       tempah
+                                       = pVBInfo->LCDCapList[XGI_GetLCDCapPtr(
+                                                       pVBInfo)].LCD_DelayCompensation; /* / Get LCD Delay */
+                       tempah &= 0x0f;
+                       tempah = tempah << 4;
+                       XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x2D, 0x0f,
+                                       tempah);
                }
+       }
+}
 
-               if (tempal == tempbl)
-                       break;
+static void XGI_SetLCDCap_A(unsigned short tempcx, struct vb_device_info *pVBInfo)
+{
+       unsigned short temp;
 
-               i++;
-               tempbl = pVBInfo->LCDCapList[i].LCD_ID;
+       temp = XGINew_GetReg1(pVBInfo->P3d4, 0x37);
+
+       if (temp & LCDRGB18Bit) {
+               XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x19, 0x0F,
+                               (unsigned short) (0x20 | (tempcx & 0x00C0))); /* Enable Dither */
+               XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x1A, 0x7F, 0x80);
+       } else {
+               XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x19, 0x0F,
+                               (unsigned short) (0x30 | (tempcx & 0x00C0)));
+               XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x1A, 0x7F, 0x00);
        }
 
-       if (tempbl == 0xFF) {
-               pVBInfo->LCDResInfo = Panel1024x768;
-               pVBInfo->LCDTypeInfo = 0;
-               i = 0;
+       /*
+       if (tempcx & EnableLCD24bpp) {  // 24bits
+               XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x19, 0x0F, (unsigned short)(0x30 | (tempcx&0x00C0)));
+               XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x1A, 0x7F, 0x00);
+       } else {
+               XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x19, 0x0F, (unsigned short)(0x20 | (tempcx&0x00C0))); // Enable Dither
+               XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x1A, 0x7F, 0x80);
        }
+       */
+}
 
-       return i;
+/* --------------------------------------------------------------------- */
+/* Function : XGI_SetLCDCap_B */
+/* Input : cx -> LCD Capability */
+/* Output : */
+/* Description : */
+/* --------------------------------------------------------------------- */
+static void XGI_SetLCDCap_B(unsigned short tempcx, struct vb_device_info *pVBInfo)
+{
+       if (tempcx & EnableLCD24bpp) /* 24bits */
+               XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x1A, 0xE0,
+                               (unsigned short) (((tempcx & 0x00ff) >> 6)
+                                               | 0x0c));
+       else
+               XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x1A, 0xE0,
+                               (unsigned short) (((tempcx & 0x00ff) >> 6)
+                                               | 0x18)); /* Enable Dither */
 }
 
-static void XGI_GetLCDSync(unsigned short *HSyncWidth, unsigned short *VSyncWidth,
-               struct vb_device_info *pVBInfo)
+static void SetSpectrum(struct vb_device_info *pVBInfo)
 {
-       unsigned short Index;
+       unsigned short index;
 
-       Index = XGI_GetLCDCapPtr(pVBInfo);
-       *HSyncWidth = pVBInfo->LCDCapList[Index].LCD_HSyncWidth;
-       *VSyncWidth = pVBInfo->LCDCapList[Index].LCD_VSyncWidth;
+       index = XGI_GetLCDCapPtr(pVBInfo);
 
-       return;
+       XGINew_SetRegAND(pVBInfo->Part4Port, 0x30, 0x8F); /* disable down spectrum D[4] */
+       XGI_LongWait(pVBInfo);
+       XGINew_SetRegOR(pVBInfo->Part4Port, 0x30, 0x20); /* reset spectrum */
+       XGI_LongWait(pVBInfo);
+
+       XGINew_SetReg1(pVBInfo->Part4Port, 0x31,
+                       pVBInfo->LCDCapList[index].Spectrum_31);
+       XGINew_SetReg1(pVBInfo->Part4Port, 0x32,
+                       pVBInfo->LCDCapList[index].Spectrum_32);
+       XGINew_SetReg1(pVBInfo->Part4Port, 0x33,
+                       pVBInfo->LCDCapList[index].Spectrum_33);
+       XGINew_SetReg1(pVBInfo->Part4Port, 0x34,
+                       pVBInfo->LCDCapList[index].Spectrum_34);
+       XGI_LongWait(pVBInfo);
+       XGINew_SetRegOR(pVBInfo->Part4Port, 0x30, 0x40); /* enable spectrum */
 }
 
-void XGI_EnableBridge(struct xgi_hw_device_info *HwDeviceExtension,
-               struct vb_device_info *pVBInfo)
+static void XGI_SetLCDCap(struct vb_device_info *pVBInfo)
 {
-       unsigned short tempbl, tempah;
-
-       if (pVBInfo->SetFlag == Win9xDOSMode) {
-               if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
-                               | VB_XGI302LV | VB_XGI301C)) {
-                       XGI_DisplayOn(HwDeviceExtension, pVBInfo);
-                       return;
-               } else
-                       /* LVDS or CH7017 */
-                       return;
-       }
-
-       if (HwDeviceExtension->jChipType < XG40) {
-               if (!XGI_DisableChISLCD(pVBInfo)) {
-                       if ((XGI_EnableChISLCD(pVBInfo)) || (pVBInfo->VBInfo
-                                       & (SetCRT2ToLCD | SetCRT2ToLCDA))) {
-                               if (pVBInfo->LCDInfo & SetPWDEnable) {
-                                       XGI_EnablePWD(pVBInfo);
-                               } else {
-                                       pVBInfo->LCDInfo &= (~SetPWDEnable);
-                                       if (pVBInfo->VBType & (VB_XGI301LV
-                                                       | VB_XGI302LV
-                                                       | VB_XGI301C)) {
-                                               tempbl = 0xFD;
-                                               tempah = 0x02;
-                                       } else {
-                                               tempbl = 0xFB;
-                                               tempah = 0x00;
-                                       }
+       unsigned short tempcx;
 
-                                       XGI_SetPanelPower(tempah, tempbl,
-                                                       pVBInfo);
-                                       XGI_SetPanelDelay(1, pVBInfo);
-                               }
-                       }
-               }
-       } /* Not 340 */
+       tempcx = pVBInfo->LCDCapList[XGI_GetLCDCapPtr(pVBInfo)].LCD_Capability;
 
        if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
                        | VB_XGI302LV | VB_XGI301C)) {
-               if (!(pVBInfo->SetFlag & DisableChA)) {
-                       if (pVBInfo->SetFlag & EnableChA) {
-                               XGINew_SetReg1(pVBInfo->Part1Port, 0x1E, 0x20); /* Power on */
-                       } else {
-                               if (pVBInfo->VBInfo & SetCRT2ToDualEdge) { /* SetCRT2ToLCDA ) */
-                                       XGINew_SetReg1(pVBInfo->Part1Port,
-                                                       0x1E, 0x20); /* Power on */
-                               }
-                       }
-               }
-
-               if (!(pVBInfo->SetFlag & DisableChB)) {
-                       if ((pVBInfo->SetFlag & EnableChB) || (pVBInfo->VBInfo
-                                       & (SetCRT2ToLCD | SetCRT2ToTV
-                                                       | SetCRT2ToRAMDAC))) {
-                               tempah = (unsigned char) XGINew_GetReg1(
-                                               pVBInfo->P3c4, 0x32);
-                               tempah &= 0xDF;
-                               if (pVBInfo->VBInfo & SetInSlaveMode) {
-                                       if (!(pVBInfo->VBInfo & SetCRT2ToRAMDAC))
-                                               tempah |= 0x20;
-                               }
-                               XGINew_SetReg1(pVBInfo->P3c4, 0x32, tempah);
-                               XGINew_SetRegOR(pVBInfo->P3c4, 0x1E, 0x20);
-
-                               tempah = (unsigned char) XGINew_GetReg1(
-                                               pVBInfo->Part1Port, 0x2E);
-
-                               if (!(tempah & 0x80))
-                                       XGINew_SetRegOR(pVBInfo->Part1Port,
-                                                       0x2E, 0x80); /* BVBDOENABLE = 1 */
-
-                               XGINew_SetRegAND(pVBInfo->Part1Port, 0x00, 0x7F); /* BScreenOFF = 0 */
-                       }
-               }
-
-               if ((pVBInfo->SetFlag & (EnableChA | EnableChB))
-                               || (!(pVBInfo->VBInfo & DisableCRT2Display))) {
-                       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x00, ~0xE0,
-                                       0x20); /* shampoo 0129 */
-                       if (pVBInfo->VBType & (VB_XGI302LV | VB_XGI301C)) {
-                               if (!XGI_DisableChISLCD(pVBInfo)) {
-                                       if (XGI_EnableChISLCD(pVBInfo)
-                                                       || (pVBInfo->VBInfo
-                                                                       & (SetCRT2ToLCD
-                                                                                       | SetCRT2ToLCDA)))
-                                               XGINew_SetRegAND(
-                                                               pVBInfo->Part4Port,
-                                                               0x2A, 0x7F); /* LVDS PLL power on */
-                               }
-                               XGINew_SetRegAND(pVBInfo->Part4Port, 0x30, 0x7F); /* LVDS Driver power on */
-                       }
+               if (pVBInfo->VBType & (VB_XGI301LV | VB_XGI302LV | VB_XGI301C)) { /* 301LV/302LV only */
+                       /* Set 301LV Capability */
+                       XGINew_SetReg1(pVBInfo->Part4Port, 0x24,
+                                       (unsigned char) (tempcx & 0x1F));
                }
+               /* VB Driving */
+               XGINew_SetRegANDOR(pVBInfo->Part4Port, 0x0D,
+                               ~((EnableVBCLKDRVLOW | EnablePLLSPLOW) >> 8),
+                               (unsigned short) ((tempcx & (EnableVBCLKDRVLOW
+                                               | EnablePLLSPLOW)) >> 8));
+       }
 
-               tempah = 0x00;
-
-               if (!(pVBInfo->VBInfo & DisableCRT2Display)) {
-                       tempah = 0xc0;
+       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
+                       | VB_XGI302LV | VB_XGI301C)) {
+               if (pVBInfo->VBInfo & SetCRT2ToLCD)
+                       XGI_SetLCDCap_B(tempcx, pVBInfo);
+               else if (pVBInfo->VBInfo & SetCRT2ToLCDA)
+                       XGI_SetLCDCap_A(tempcx, pVBInfo);
 
-                       if (!(pVBInfo->VBInfo & SetSimuScanMode)) {
-                               if (pVBInfo->VBInfo & SetCRT2ToLCDA) {
-                                       if (pVBInfo->VBInfo & SetCRT2ToDualEdge) {
-                                               tempah = tempah & 0x40;
-                                               if (pVBInfo->VBInfo
-                                                               & SetCRT2ToLCDA)
-                                                       tempah = tempah ^ 0xC0;
+               if (pVBInfo->VBType & (VB_XGI302LV | VB_XGI301C)) {
+                       if (tempcx & EnableSpectrum)
+                               SetSpectrum(pVBInfo);
+               }
+       } else {
+               /* LVDS,CH7017 */
+               XGI_SetLCDCap_A(tempcx, pVBInfo);
+       }
+}
 
-                                               if (pVBInfo->SetFlag
-                                                               & DisableChB)
-                                                       tempah &= 0xBF;
+/* --------------------------------------------------------------------- */
+/* Function : XGI_SetAntiFlicker */
+/* Input : */
+/* Output : */
+/* Description : Set TV Customized Param. */
+/* --------------------------------------------------------------------- */
+static void XGI_SetAntiFlicker(unsigned short ModeNo, unsigned short ModeIdIndex,
+               struct vb_device_info *pVBInfo)
+{
+       unsigned short tempbx, index;
 
-                                               if (pVBInfo->SetFlag
-                                                               & DisableChA)
-                                                       tempah &= 0x7F;
+       unsigned char tempah;
 
-                                               if (pVBInfo->SetFlag
-                                                               & EnableChB)
-                                                       tempah |= 0x40;
+       if (pVBInfo->TVInfo & (SetYPbPrMode525p | SetYPbPrMode750p))
+               return;
 
-                                               if (pVBInfo->SetFlag
-                                                               & EnableChA)
-                                                       tempah |= 0x80;
-                                       }
-                               }
-                       }
-               }
+       tempbx = XGI_GetTVPtrIndex(pVBInfo);
+       tempbx &= 0xFE;
 
-               XGINew_SetRegOR(pVBInfo->Part4Port, 0x1F, tempah); /* EnablePart4_1F */
+       if (ModeNo <= 0x13)
+               index = pVBInfo->SModeIDTable[ModeIdIndex].VB_StTVFlickerIndex;
+       else
+               index = pVBInfo->EModeIDTable[ModeIdIndex].VB_ExtTVFlickerIndex;
 
-               if (pVBInfo->SetFlag & Win9xDOSMode) {
-                       XGI_DisplayOn(HwDeviceExtension, pVBInfo);
-                       return;
-               }
+       tempbx += index;
+       tempah = TVAntiFlickList[tempbx];
+       tempah = tempah << 4;
 
-               if (!(pVBInfo->SetFlag & DisableChA)) {
-                       XGI_VBLongWait(pVBInfo);
-                       if (!(pVBInfo->SetFlag & GatingCRT)) {
-                               XGI_DisableGatingCRT(HwDeviceExtension, pVBInfo);
-                               XGI_DisplayOn(HwDeviceExtension, pVBInfo);
-                               XGI_VBLongWait(pVBInfo);
-                       }
-               }
-       } /* 301 */
-       else { /* LVDS */
-               if (pVBInfo->VBInfo & (SetCRT2ToTV | SetCRT2ToLCD
-                               | SetCRT2ToLCDA))
-                       XGINew_SetRegOR(pVBInfo->Part1Port, 0x1E, 0x20); /* enable CRT2 */
+       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x0A, 0x8F, tempah);
+}
 
-               tempah = (unsigned char) XGINew_GetReg1(pVBInfo->Part1Port,
-                               0x2E);
-               if (!(tempah & 0x80))
-                       XGINew_SetRegOR(pVBInfo->Part1Port, 0x2E, 0x80); /* BVBDOENABLE = 1 */
+static void XGI_SetEdgeEnhance(unsigned short ModeNo, unsigned short ModeIdIndex,
+               struct vb_device_info *pVBInfo)
+{
+       unsigned short tempbx, index;
 
-               XGINew_SetRegAND(pVBInfo->Part1Port, 0x00, 0x7F);
-               XGI_DisplayOn(HwDeviceExtension, pVBInfo);
-       } /* End of VB */
+       unsigned char tempah;
 
-       if (HwDeviceExtension->jChipType < XG40) {
-               if (!XGI_EnableChISLCD(pVBInfo)) {
-                       if (pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
-                               if (XGI_BacklightByDrv(pVBInfo))
-                                       return;
-                       } else
-                               return;
-               }
+       tempbx = XGI_GetTVPtrIndex(pVBInfo);
+       tempbx &= 0xFE;
 
-               if (pVBInfo->LCDInfo & SetPWDEnable) {
-                       XGI_FirePWDEnable(pVBInfo);
-                       return;
-               }
+       if (ModeNo <= 0x13)
+               index = pVBInfo->SModeIDTable[ModeIdIndex].VB_StTVEdgeIndex;
+       else
+               index = pVBInfo->EModeIDTable[ModeIdIndex].VB_ExtTVEdgeIndex;
 
-               XGI_SetPanelDelay(2, pVBInfo);
+       tempbx += index;
+       tempah = TVEdgeList[tempbx];
+       tempah = tempah << 5;
 
-               if (pVBInfo->VBType & (VB_XGI301LV | VB_XGI302LV | VB_XGI301C)) {
-                       tempah = 0x01;
-                       tempbl = 0xFE; /* turn on backlght */
-               } else {
-                       tempbl = 0xF7;
-                       tempah = 0x00;
-               }
-               XGI_SetPanelPower(tempah, tempbl, pVBInfo);
-       }
+       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x3A, 0x1F, tempah);
 }
 
-void XGI_DisableBridge(struct xgi_hw_device_info *HwDeviceExtension,
-               struct vb_device_info *pVBInfo)
+static void XGI_SetPhaseIncr(struct vb_device_info *pVBInfo)
 {
-       unsigned short tempax, tempbx, tempah = 0, tempbl = 0;
+       unsigned short tempbx;
 
-       if (pVBInfo->SetFlag == Win9xDOSMode)
-               return;
+       unsigned char tempcl, tempch;
 
-       if (HwDeviceExtension->jChipType < XG40) {
-               if ((!(pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)))
-                               || (XGI_DisableChISLCD(pVBInfo))) {
-                       if (!XGI_IsLCDON(pVBInfo)) {
-                               if (pVBInfo->LCDInfo & SetPWDEnable)
-                                       XGI_EnablePWD(pVBInfo);
-                               else {
-                                       pVBInfo->LCDInfo &= ~SetPWDEnable;
-                                       XGI_DisablePWD(pVBInfo);
-                                       if (pVBInfo->VBType & (VB_XGI301LV
-                                                       | VB_XGI302LV
-                                                       | VB_XGI301C)) {
-                                               tempbx = 0xFE; /* not 01h */
-                                               tempax = 0;
-                                       } else {
-                                               tempbx = 0xF7; /* not 08h */
-                                               tempax = 0x08;
-                                       }
-                                       XGI_SetPanelPower(tempax, tempbx,
-                                                       pVBInfo);
-                                       XGI_SetPanelDelay(3, pVBInfo);
-                               }
-                       } /* end if (!XGI_IsLCDON(pVBInfo)) */
-               }
-       }
+       unsigned long tempData;
 
-       /*
-       if (CH7017) {
-               if (!(pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2toLCDA)) || (XGI_DisableChISLCD(pVBInfo))) {
-                       if (!XGI_IsLCDON(pVBInfo)) {
-                               if (DISCHARGE) {
-                                       tempbx = XGINew_GetCH7005(0x61);
-                                       if (tempbx < 0x01) // first time we power up
-                                               XGINew_SetCH7005(0x0066); // and disable power sequence
-                                       else
-                                               XGINew_SetCH7005(0x5f66); // leave VDD on - disable power
-                               }
-                       }
-               }
-       }
-       */
+       XGI_GetTVPtrIndex2(&tempbx, &tempcl, &tempch, pVBInfo); /* bx, cl, ch */
+       tempData = TVPhaseList[tempbx];
 
-       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
-                       | VB_XGI302LV | VB_XGI301C)) {
-               tempah = 0x3F;
-               if (!(pVBInfo->VBInfo & (DisableCRT2Display | SetSimuScanMode))) {
-                       if (pVBInfo->VBInfo & SetCRT2ToLCDA) {
-                               if (pVBInfo->VBInfo & SetCRT2ToDualEdge) {
-                                       tempah = 0x7F; /* Disable Channel A */
-                                       if (!(pVBInfo->VBInfo & SetCRT2ToLCDA))
-                                               tempah = 0xBF; /* Disable Channel B */
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x31, (unsigned short) (tempData
+                       & 0x000000FF));
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x32, (unsigned short) ((tempData
+                       & 0x0000FF00) >> 8));
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x33, (unsigned short) ((tempData
+                       & 0x00FF0000) >> 16));
+       XGINew_SetReg1(pVBInfo->Part2Port, 0x34, (unsigned short) ((tempData
+                       & 0xFF000000) >> 24));
+}
 
-                                       if (pVBInfo->SetFlag & DisableChB)
-                                               tempah &= 0xBF; /* force to disable Cahnnel */
+static void XGI_SetYFilter(unsigned short ModeNo, unsigned short ModeIdIndex,
+               struct vb_device_info *pVBInfo)
+{
+       unsigned short tempbx, index;
 
-                                       if (pVBInfo->SetFlag & DisableChA)
-                                               tempah &= 0x7F; /* Force to disable Channel B */
-                               }
-                       }
-               }
+       unsigned char tempcl, tempch, tempal, *filterPtr;
 
-               XGINew_SetRegAND(pVBInfo->Part4Port, 0x1F, tempah); /* disable part4_1f */
+       XGI_GetTVPtrIndex2(&tempbx, &tempcl, &tempch, pVBInfo); /* bx, cl, ch */
 
-               if (pVBInfo->VBType & (VB_XGI302LV | VB_XGI301C)) {
-                       if (((pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)))
-                                       || (XGI_DisableChISLCD(pVBInfo))
-                                       || (XGI_IsLCDON(pVBInfo)))
-                               XGINew_SetRegOR(pVBInfo->Part4Port, 0x30, 0x80); /* LVDS Driver power down */
-               }
+       switch (tempbx) {
+       case 0x00:
+       case 0x04:
+               filterPtr = NTSCYFilter1;
+               break;
 
-               if ((pVBInfo->SetFlag & DisableChA) || (pVBInfo->VBInfo
-                               & (DisableCRT2Display | SetCRT2ToLCDA
-                                               | SetSimuScanMode))) {
-                       if (pVBInfo->SetFlag & GatingCRT)
-                               XGI_EnableGatingCRT(HwDeviceExtension, pVBInfo);
-                       XGI_DisplayOff(HwDeviceExtension, pVBInfo);
-               }
+       case 0x01:
+               filterPtr = PALYFilter1;
+               break;
 
-               if (pVBInfo->VBInfo & SetCRT2ToLCDA) {
-                       if ((pVBInfo->SetFlag & DisableChA) || (pVBInfo->VBInfo
-                                       & SetCRT2ToLCDA))
-                               XGINew_SetRegAND(pVBInfo->Part1Port, 0x1e, 0xdf); /* Power down */
-               }
+       case 0x02:
+       case 0x05:
+       case 0x0D:
+               filterPtr = PALMYFilter1;
+               break;
+
+       case 0x03:
+               filterPtr = PALNYFilter1;
+               break;
 
-               XGINew_SetRegAND(pVBInfo->P3c4, 0x32, 0xdf); /* disable TV as primary VGA swap */
+       case 0x08:
+       case 0x0C:
+               filterPtr = NTSCYFilter2;
+               break;
 
-               if ((pVBInfo->VBInfo & (SetSimuScanMode | SetCRT2ToDualEdge)))
-                       XGINew_SetRegAND(pVBInfo->Part2Port, 0x00, 0xdf);
+       case 0x0A:
+               filterPtr = PALMYFilter2;
+               break;
 
-               if ((pVBInfo->SetFlag & DisableChB) || (pVBInfo->VBInfo
-                               & (DisableCRT2Display | SetSimuScanMode))
-                               || ((!(pVBInfo->VBInfo & SetCRT2ToLCDA))
-                                               && (pVBInfo->VBInfo
-                                                               & (SetCRT2ToRAMDAC
-                                                                               | SetCRT2ToLCD
-                                                                               | SetCRT2ToTV))))
-                       XGINew_SetRegOR(pVBInfo->Part1Port, 0x00, 0x80); /* BScreenOff=1 */
+       case 0x0B:
+               filterPtr = PALNYFilter2;
+               break;
 
-               if ((pVBInfo->SetFlag & DisableChB) || (pVBInfo->VBInfo
-                               & (DisableCRT2Display | SetSimuScanMode))
-                               || (!(pVBInfo->VBInfo & SetCRT2ToLCDA))
-                               || (pVBInfo->VBInfo & (SetCRT2ToRAMDAC
-                                               | SetCRT2ToLCD | SetCRT2ToTV))) {
-                       tempah = XGINew_GetReg1(pVBInfo->Part1Port, 0x00); /* save Part1 index 0 */
-                       XGINew_SetRegOR(pVBInfo->Part1Port, 0x00, 0x10); /* BTDAC = 1, avoid VB reset */
-                       XGINew_SetRegAND(pVBInfo->Part1Port, 0x1E, 0xDF); /* disable CRT2 */
-                       XGINew_SetReg1(pVBInfo->Part1Port, 0x00, tempah); /* restore Part1 index 0 */
-               }
-       } else { /* {301} */
-               if (pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToTV)) {
-                       XGINew_SetRegOR(pVBInfo->Part1Port, 0x00, 0x80); /* BScreenOff=1 */
-                       XGINew_SetRegAND(pVBInfo->Part1Port, 0x1E, 0xDF); /* Disable CRT2 */
-                       XGINew_SetRegAND(pVBInfo->P3c4, 0x32, 0xDF); /* Disable TV asPrimary VGA swap */
-               }
+       case 0x09:
+               filterPtr = PALYFilter2;
+               break;
 
-               if (pVBInfo->VBInfo & (DisableCRT2Display | SetCRT2ToLCDA
-                               | SetSimuScanMode))
-                       XGI_DisplayOff(HwDeviceExtension, pVBInfo);
+       default:
+               return;
        }
 
-       if (HwDeviceExtension->jChipType < XG40) {
-               if (!(pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA))
-                               || (XGI_DisableChISLCD(pVBInfo))
-                               || (XGI_IsLCDON(pVBInfo))) {
-                       if (pVBInfo->LCDInfo & SetPWDEnable) {
-                               if (pVBInfo->LCDInfo & SetPWDEnable)
-                                       XGI_BacklightByDrv(pVBInfo);
-                               else {
-                                       XGI_SetPanelDelay(4, pVBInfo);
-                                       if (pVBInfo->VBType & VB_XGI301LV) {
-                                               tempbl = 0xFD;
-                                               tempah = 0x00;
-                                       } else {
-                                               tempbl = 0xFB;
-                                               tempah = 0x04;
-                                       }
-                               }
-                       }
-                       XGI_SetPanelPower(tempah, tempbl, pVBInfo);
-               }
-       }
-}
+       if (ModeNo <= 0x13)
+               tempal = pVBInfo->SModeIDTable[ModeIdIndex].VB_StTVYFilterIndex;
+       else
+               tempal
+                               = pVBInfo->EModeIDTable[ModeIdIndex].VB_ExtTVYFilterIndex;
 
-/* --------------------------------------------------------------------- */
-/* Function : XGI_GetTVPtrIndex */
-/* Input : */
-/* Output : */
-/* Description : bx 0 : ExtNTSC */
-/* 1 : StNTSC */
-/* 2 : ExtPAL */
-/* 3 : StPAL */
-/* 4 : ExtHiTV */
-/* 5 : StHiTV */
-/* 6 : Ext525i */
-/* 7 : St525i */
-/* 8 : Ext525p */
-/* 9 : St525p */
-/* A : Ext750p */
-/* B : St750p */
-/* --------------------------------------------------------------------- */
-static unsigned short XGI_GetTVPtrIndex(struct vb_device_info *pVBInfo)
-{
-       unsigned short tempbx = 0;
+       if (tempcl == 0)
+               index = tempal * 4;
+       else
+               index = tempal * 7;
 
-       if (pVBInfo->TVInfo & SetPALTV)
-               tempbx = 2;
-       if (pVBInfo->TVInfo & SetYPbPrMode1080i)
-               tempbx = 4;
-       if (pVBInfo->TVInfo & SetYPbPrMode525i)
-               tempbx = 6;
-       if (pVBInfo->TVInfo & SetYPbPrMode525p)
-               tempbx = 8;
-       if (pVBInfo->TVInfo & SetYPbPrMode750p)
-               tempbx = 10;
-       if (pVBInfo->TVInfo & TVSimuMode)
-               tempbx++;
+       if ((tempcl == 0) && (tempch == 1)) {
+               XGINew_SetReg1(pVBInfo->Part2Port, 0x35, 0);
+               XGINew_SetReg1(pVBInfo->Part2Port, 0x36, 0);
+               XGINew_SetReg1(pVBInfo->Part2Port, 0x37, 0);
+               XGINew_SetReg1(pVBInfo->Part2Port, 0x38, filterPtr[index++]);
+       } else {
+               XGINew_SetReg1(pVBInfo->Part2Port, 0x35, filterPtr[index++]);
+               XGINew_SetReg1(pVBInfo->Part2Port, 0x36, filterPtr[index++]);
+               XGINew_SetReg1(pVBInfo->Part2Port, 0x37, filterPtr[index++]);
+               XGINew_SetReg1(pVBInfo->Part2Port, 0x38, filterPtr[index++]);
+       }
 
-       return tempbx;
+       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
+                       | VB_XGI302LV | VB_XGI301C)) {
+               XGINew_SetReg1(pVBInfo->Part2Port, 0x48, filterPtr[index++]);
+               XGINew_SetReg1(pVBInfo->Part2Port, 0x49, filterPtr[index++]);
+               XGINew_SetReg1(pVBInfo->Part2Port, 0x4A, filterPtr[index++]);
+       }
 }
 
 /* --------------------------------------------------------------------- */
@@ -7864,962 +7625,1088 @@ static void XGI_OEM310Setting(unsigned short ModeNo, unsigned short ModeIdIndex,
        }
 }
 
-static void XGI_SetDelayComp(struct vb_device_info *pVBInfo)
+/* --------------------------------------------------------------------- */
+/* Function : XGI_SetCRT2ModeRegs */
+/* Input : */
+/* Output : */
+/* Description : Origin code for crt2group */
+/* --------------------------------------------------------------------- */
+void XGI_SetCRT2ModeRegs(unsigned short ModeNo,
+               struct xgi_hw_device_info *HwDeviceExtension,
+               struct vb_device_info *pVBInfo)
 {
-       unsigned short index;
-
-       unsigned char tempah, tempbl, tempbh;
+       unsigned short tempbl;
+       short tempcl;
 
-       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
-                       | VB_XGI302LV | VB_XGI301C)) {
-               if (pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA
-                               | SetCRT2ToTV | SetCRT2ToRAMDAC)) {
-                       tempbl = 0;
-                       tempbh = 0;
+       unsigned char tempah;
 
-                       index = XGI_GetTVPtrIndex(pVBInfo); /* Get TV Delay */
-                       tempbl = pVBInfo->XGI_TVDelayList[index];
+       /* XGINew_SetReg1(pVBInfo->Part1Port, 0x03, 0x00); // fix write part1 index 0 BTDRAM bit Bug */
+       tempah = 0;
+       if (!(pVBInfo->VBInfo & DisableCRT2Display)) {
+               tempah = XGINew_GetReg1(pVBInfo->Part1Port, 0x00);
+               tempah &= ~0x10; /* BTRAMDAC */
+               tempah |= 0x40; /* BTRAM */
 
-                       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B
-                                       | VB_XGI301LV | VB_XGI302LV
-                                       | VB_XGI301C))
-                               tempbl = pVBInfo->XGI_TVDelayList2[index];
+               if (pVBInfo->VBInfo & (SetCRT2ToRAMDAC | SetCRT2ToTV
+                               | SetCRT2ToLCD)) {
+                       tempah = 0x40; /* BTDRAM */
+                       if (ModeNo > 0x13) {
+                               tempcl = pVBInfo->ModeType;
+                               tempcl -= ModeVGA;
+                               if (tempcl >= 0) {
+                                       tempah = (0x008 >> tempcl); /* BT Color */
+                                       if (tempah == 0)
+                                               tempah = 1;
+                                       tempah |= 0x040;
+                               }
+                       }
+                       if (pVBInfo->VBInfo & SetInSlaveMode)
+                               tempah ^= 0x50; /* BTDAC */
+               }
+       }
 
-                       if (pVBInfo->VBInfo & SetCRT2ToDualEdge)
-                               tempbl = tempbl >> 4;
-                       /*
-                       if (pVBInfo->VBInfo & SetCRT2ToRAMDAC)
-                               tempbl = CRT2Delay1;    // Get CRT2 Delay
-                       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV | VB_XGI302LV | VB_XGI301C))
-                               tempbl = CRT2Delay2;
-                       */
-                       if (pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
-                               index = XGI_GetLCDCapPtr(pVBInfo); /* Get LCD Delay */
-                               tempbh = pVBInfo->LCDCapList[index].LCD_DelayCompensation;
+       /* 0210 shampoo
+       if (pVBInfo->VBInfo & DisableCRT2Display) {
+               tempah = 0;
+       }
 
-                               if (!(pVBInfo->VBInfo & SetCRT2ToLCDA))
-                                       tempbl = tempbh;
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x00, tempah);
+       if (pVBInfo->VBInfo & (SetCRT2ToRAMDAC | SetCRT2ToTV | SetCRT2ToLCD)) {
+               tempcl = pVBInfo->ModeType;
+               if (ModeNo > 0x13) {
+                       tempcl -= ModeVGA;
+                       if ((tempcl > 0) || (tempcl == 0)) {
+                               tempah=(0x008>>tempcl) ;
+                               if (tempah == 0)
+                                       tempah = 1;
+                               tempah |= 0x040;
                        }
+               } else {
+                       tempah = 0x040;
+               }
 
-                       tempbl &= 0x0F;
-                       tempbh &= 0xF0;
-                       tempah = XGINew_GetReg1(pVBInfo->Part1Port, 0x2D);
+               if (pVBInfo->VBInfo & SetInSlaveMode) {
+                       tempah = (tempah ^ 0x050);
+               }
+       }
+       */
 
-                       if (pVBInfo->VBInfo & (SetCRT2ToRAMDAC | SetCRT2ToLCD
-                                       | SetCRT2ToTV)) { /* Channel B */
-                               tempah &= 0xF0;
-                               tempah |= tempbl;
-                       }
+       XGINew_SetReg1(pVBInfo->Part1Port, 0x00, tempah);
+       tempah = 0x08;
+       tempbl = 0xf0;
+
+       if (pVBInfo->VBInfo & DisableCRT2Display) {
+               XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x2e, tempbl, tempah);
+       } else {
+               tempah = 0x00;
+               tempbl = 0xff;
+
+               if (pVBInfo->VBInfo & (SetCRT2ToRAMDAC | SetCRT2ToTV
+                               | SetCRT2ToLCD | SetCRT2ToLCDA)) {
+                       if ((pVBInfo->VBInfo & SetCRT2ToLCDA)
+                                       && (!(pVBInfo->VBInfo & SetSimuScanMode))) {
+                               tempbl &= 0xf7;
+                               tempah |= 0x01;
+                               XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x2e,
+                                               tempbl, tempah);
+                       } else {
+                               if (pVBInfo->VBInfo & SetCRT2ToLCDA) {
+                                       tempbl &= 0xf7;
+                                       tempah |= 0x01;
+                               }
+
+                               if (pVBInfo->VBInfo & (SetCRT2ToRAMDAC
+                                               | SetCRT2ToTV | SetCRT2ToLCD)) {
+                                       tempbl &= 0xf8;
+                                       tempah = 0x01;
+
+                                       if (!(pVBInfo->VBInfo & SetInSlaveMode))
+                                               tempah |= 0x02;
+
+                                       if (!(pVBInfo->VBInfo & SetCRT2ToRAMDAC)) {
+                                               tempah = tempah ^ 0x05;
+                                               if (!(pVBInfo->VBInfo
+                                                               & SetCRT2ToLCD))
+                                                       tempah = tempah ^ 0x01;
+                                       }
 
-                       if (pVBInfo->VBInfo & SetCRT2ToLCDA) { /* Channel A */
-                               tempah &= 0x0F;
-                               tempah |= tempbh;
+                                       if (!(pVBInfo->VBInfo
+                                                       & SetCRT2ToDualEdge))
+                                               tempah |= 0x08;
+                                       XGINew_SetRegANDOR(pVBInfo->Part1Port,
+                                                       0x2e, tempbl, tempah);
+                               } else {
+                                       XGINew_SetRegANDOR(pVBInfo->Part1Port,
+                                                       0x2e, tempbl, tempah);
+                               }
                        }
-                       XGINew_SetReg1(pVBInfo->Part1Port, 0x2D, tempah);
-               }
-       } else if (pVBInfo->IF_DEF_LVDS == 1) {
-               tempbl = 0;
-               tempbh = 0;
-               if (pVBInfo->VBInfo & SetCRT2ToLCD) {
-                       tempah
-                                       = pVBInfo->LCDCapList[XGI_GetLCDCapPtr(
-                                                       pVBInfo)].LCD_DelayCompensation; /* / Get LCD Delay */
-                       tempah &= 0x0f;
-                       tempah = tempah << 4;
-                       XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x2D, 0x0f,
+               } else {
+                       XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x2e, tempbl,
                                        tempah);
                }
        }
-}
 
-static void XGI_SetLCDCap(struct vb_device_info *pVBInfo)
-{
-       unsigned short tempcx;
+       if (pVBInfo->VBInfo & (SetCRT2ToRAMDAC | SetCRT2ToTV | SetCRT2ToLCD
+                       | SetCRT2ToLCDA)) {
+               tempah &= (~0x08);
+               if ((pVBInfo->ModeType == ModeVGA) && (!(pVBInfo->VBInfo
+                               & SetInSlaveMode))) {
+                       tempah |= 0x010;
+               }
+               tempah |= 0x080;
 
-       tempcx = pVBInfo->LCDCapList[XGI_GetLCDCapPtr(pVBInfo)].LCD_Capability;
+               if (pVBInfo->VBInfo & SetCRT2ToTV) {
+                       /* if (!(pVBInfo->TVInfo & (SetYPbPrMode525p | SetYPbPrMode750p))) { */
+                       tempah |= 0x020;
+                       if (ModeNo > 0x13) {
+                               if (pVBInfo->VBInfo & DriverMode)
+                                       tempah = tempah ^ 0x20;
+                       }
+                       /* } */
+               }
 
-       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
-                       | VB_XGI302LV | VB_XGI301C)) {
-               if (pVBInfo->VBType & (VB_XGI301LV | VB_XGI302LV | VB_XGI301C)) { /* 301LV/302LV only */
-                       /* Set 301LV Capability */
-                       XGINew_SetReg1(pVBInfo->Part4Port, 0x24,
-                                       (unsigned char) (tempcx & 0x1F));
+               XGINew_SetRegANDOR(pVBInfo->Part4Port, 0x0D, ~0x0BF, tempah);
+               tempah = 0;
+
+               if (pVBInfo->LCDInfo & SetLCDDualLink)
+                       tempah |= 0x40;
+
+               if (pVBInfo->VBInfo & SetCRT2ToTV) {
+                       /* if ((!(pVBInfo->VBInfo & SetCRT2ToHiVisionTV)) && (!(pVBInfo->TVInfo & (SetYPbPrMode525p | SetYPbPrMode750p)))) { */
+                       if (pVBInfo->TVInfo & RPLLDIV2XO)
+                               tempah |= 0x40;
+                       /* } */
                }
-               /* VB Driving */
-               XGINew_SetRegANDOR(pVBInfo->Part4Port, 0x0D,
-                               ~((EnableVBCLKDRVLOW | EnablePLLSPLOW) >> 8),
-                               (unsigned short) ((tempcx & (EnableVBCLKDRVLOW
-                                               | EnablePLLSPLOW)) >> 8));
+
+               if ((pVBInfo->LCDResInfo == Panel1280x1024)
+                               || (pVBInfo->LCDResInfo == Panel1280x1024x75))
+                       tempah |= 0x80;
+
+               if (pVBInfo->LCDResInfo == Panel1280x960)
+                       tempah |= 0x80;
+
+               XGINew_SetReg1(pVBInfo->Part4Port, 0x0C, tempah);
        }
 
        if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
                        | VB_XGI302LV | VB_XGI301C)) {
-               if (pVBInfo->VBInfo & SetCRT2ToLCD)
-                       XGI_SetLCDCap_B(tempcx, pVBInfo);
-               else if (pVBInfo->VBInfo & SetCRT2ToLCDA)
-                       XGI_SetLCDCap_A(tempcx, pVBInfo);
+               tempah = 0;
+               tempbl = 0xfb;
 
-               if (pVBInfo->VBType & (VB_XGI302LV | VB_XGI301C)) {
-                       if (tempcx & EnableSpectrum)
-                               SetSpectrum(pVBInfo);
+               if (pVBInfo->VBInfo & SetCRT2ToDualEdge) {
+                       tempbl = 0xff;
+                       if (pVBInfo->VBInfo & SetCRT2ToLCDA)
+                               tempah |= 0x04; /* shampoo 0129 */
                }
-       } else {
-               /* LVDS,CH7017 */
-               XGI_SetLCDCap_A(tempcx, pVBInfo);
-       }
-}
 
-static void XGI_SetLCDCap_A(unsigned short tempcx, struct vb_device_info *pVBInfo)
-{
-       unsigned short temp;
+               XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x13, tempbl, tempah);
+               tempah = 0x00;
+               tempbl = 0xcf;
+               if (!(pVBInfo->VBInfo & DisableCRT2Display)) {
+                       if (pVBInfo->VBInfo & SetCRT2ToDualEdge)
+                               tempah |= 0x30;
+               }
 
-       temp = XGINew_GetReg1(pVBInfo->P3d4, 0x37);
+               XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x2c, tempbl, tempah);
+               tempah = 0;
+               tempbl = 0x3f;
 
-       if (temp & LCDRGB18Bit) {
-               XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x19, 0x0F,
-                               (unsigned short) (0x20 | (tempcx & 0x00C0))); /* Enable Dither */
-               XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x1A, 0x7F, 0x80);
-       } else {
-               XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x19, 0x0F,
-                               (unsigned short) (0x30 | (tempcx & 0x00C0)));
-               XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x1A, 0x7F, 0x00);
+               if (!(pVBInfo->VBInfo & DisableCRT2Display)) {
+                       if (pVBInfo->VBInfo & SetCRT2ToDualEdge)
+                               tempah |= 0xc0;
+               }
+               XGINew_SetRegANDOR(pVBInfo->Part4Port, 0x21, tempbl, tempah);
        }
 
-       /*
-       if (tempcx & EnableLCD24bpp) {  // 24bits
-               XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x19, 0x0F, (unsigned short)(0x30 | (tempcx&0x00C0)));
-               XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x1A, 0x7F, 0x00);
-       } else {
-               XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x19, 0x0F, (unsigned short)(0x20 | (tempcx&0x00C0))); // Enable Dither
-               XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x1A, 0x7F, 0x80);
+       tempah = 0;
+       tempbl = 0x7f;
+       if (!(pVBInfo->VBInfo & SetCRT2ToLCDA)) {
+               tempbl = 0xff;
+               if (!(pVBInfo->VBInfo & SetCRT2ToDualEdge))
+                       tempah |= 0x80;
        }
-       */
-}
-
-/* --------------------------------------------------------------------- */
-/* Function : XGI_SetLCDCap_B */
-/* Input : cx -> LCD Capability */
-/* Output : */
-/* Description : */
-/* --------------------------------------------------------------------- */
-static void XGI_SetLCDCap_B(unsigned short tempcx, struct vb_device_info *pVBInfo)
-{
-       if (tempcx & EnableLCD24bpp) /* 24bits */
-               XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x1A, 0xE0,
-                               (unsigned short) (((tempcx & 0x00ff) >> 6)
-                                               | 0x0c));
-       else
-               XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x1A, 0xE0,
-                               (unsigned short) (((tempcx & 0x00ff) >> 6)
-                                               | 0x18)); /* Enable Dither */
-}
-
-static void SetSpectrum(struct vb_device_info *pVBInfo)
-{
-       unsigned short index;
-
-       index = XGI_GetLCDCapPtr(pVBInfo);
 
-       XGINew_SetRegAND(pVBInfo->Part4Port, 0x30, 0x8F); /* disable down spectrum D[4] */
-       XGI_LongWait(pVBInfo);
-       XGINew_SetRegOR(pVBInfo->Part4Port, 0x30, 0x20); /* reset spectrum */
-       XGI_LongWait(pVBInfo);
+       XGINew_SetRegANDOR(pVBInfo->Part4Port, 0x23, tempbl, tempah);
 
-       XGINew_SetReg1(pVBInfo->Part4Port, 0x31,
-                       pVBInfo->LCDCapList[index].Spectrum_31);
-       XGINew_SetReg1(pVBInfo->Part4Port, 0x32,
-                       pVBInfo->LCDCapList[index].Spectrum_32);
-       XGINew_SetReg1(pVBInfo->Part4Port, 0x33,
-                       pVBInfo->LCDCapList[index].Spectrum_33);
-       XGINew_SetReg1(pVBInfo->Part4Port, 0x34,
-                       pVBInfo->LCDCapList[index].Spectrum_34);
-       XGI_LongWait(pVBInfo);
-       XGINew_SetRegOR(pVBInfo->Part4Port, 0x30, 0x40); /* enable spectrum */
+       if (pVBInfo->VBType & (VB_XGI302LV | VB_XGI301C)) {
+               if (pVBInfo->LCDInfo & SetLCDDualLink) {
+                       XGINew_SetRegOR(pVBInfo->Part4Port, 0x27, 0x20);
+                       XGINew_SetRegOR(pVBInfo->Part4Port, 0x34, 0x10);
+               }
+       }
 }
 
-/* --------------------------------------------------------------------- */
-/* Function : XGI_SetAntiFlicker */
-/* Input : */
-/* Output : */
-/* Description : Set TV Customized Param. */
-/* --------------------------------------------------------------------- */
-static void XGI_SetAntiFlicker(unsigned short ModeNo, unsigned short ModeIdIndex,
+static void XGI_CloseCRTC(struct xgi_hw_device_info *HwDeviceExtension,
                struct vb_device_info *pVBInfo)
 {
-       unsigned short tempbx, index;
-
-       unsigned char tempah;
-
-       if (pVBInfo->TVInfo & (SetYPbPrMode525p | SetYPbPrMode750p))
-               return;
-
-       tempbx = XGI_GetTVPtrIndex(pVBInfo);
-       tempbx &= 0xFE;
+       unsigned short tempbx;
 
-       if (ModeNo <= 0x13)
-               index = pVBInfo->SModeIDTable[ModeIdIndex].VB_StTVFlickerIndex;
-       else
-               index = pVBInfo->EModeIDTable[ModeIdIndex].VB_ExtTVFlickerIndex;
+       tempbx = 0;
 
-       tempbx += index;
-       tempah = TVAntiFlickList[tempbx];
-       tempah = tempah << 4;
+       if (pVBInfo->VBInfo & SetCRT2ToLCDA)
+               tempbx = 0x08A0;
 
-       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x0A, 0x8F, tempah);
 }
 
-static void XGI_SetEdgeEnhance(unsigned short ModeNo, unsigned short ModeIdIndex,
+void XGI_OpenCRTC(struct xgi_hw_device_info *HwDeviceExtension,
                struct vb_device_info *pVBInfo)
 {
-       unsigned short tempbx, index;
-
-       unsigned char tempah;
-
-       tempbx = XGI_GetTVPtrIndex(pVBInfo);
-       tempbx &= 0xFE;
-
-       if (ModeNo <= 0x13)
-               index = pVBInfo->SModeIDTable[ModeIdIndex].VB_StTVEdgeIndex;
-       else
-               index = pVBInfo->EModeIDTable[ModeIdIndex].VB_ExtTVEdgeIndex;
-
-       tempbx += index;
-       tempah = TVEdgeList[tempbx];
-       tempah = tempah << 5;
-
-       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x3A, 0x1F, tempah);
+       unsigned short tempbx;
+       tempbx = 0;
 }
 
-static void XGI_SetPhaseIncr(struct vb_device_info *pVBInfo)
+void XGI_UnLockCRT2(struct xgi_hw_device_info *HwDeviceExtension,
+               struct vb_device_info *pVBInfo)
 {
-       unsigned short tempbx;
 
-       unsigned char tempcl, tempch;
-
-       unsigned long tempData;
-
-       XGI_GetTVPtrIndex2(&tempbx, &tempcl, &tempch, pVBInfo); /* bx, cl, ch */
-       tempData = TVPhaseList[tempbx];
-
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x31, (unsigned short) (tempData
-                       & 0x000000FF));
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x32, (unsigned short) ((tempData
-                       & 0x0000FF00) >> 8));
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x33, (unsigned short) ((tempData
-                       & 0x00FF0000) >> 16));
-       XGINew_SetReg1(pVBInfo->Part2Port, 0x34, (unsigned short) ((tempData
-                       & 0xFF000000) >> 24));
+       XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x2f, 0xFF, 0x01);
+
 }
 
-static void XGI_SetYFilter(unsigned short ModeNo, unsigned short ModeIdIndex,
+void XGI_LockCRT2(struct xgi_hw_device_info *HwDeviceExtension,
                struct vb_device_info *pVBInfo)
 {
-       unsigned short tempbx, index;
 
-       unsigned char tempcl, tempch, tempal, *filterPtr;
+       XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x2F, 0xFE, 0x00);
 
-       XGI_GetTVPtrIndex2(&tempbx, &tempcl, &tempch, pVBInfo); /* bx, cl, ch */
+}
 
-       switch (tempbx) {
-       case 0x00:
-       case 0x04:
-               filterPtr = NTSCYFilter1;
-               break;
+unsigned char XGI_BridgeIsOn(struct vb_device_info *pVBInfo)
+{
+       unsigned short flag;
 
-       case 0x01:
-               filterPtr = PALYFilter1;
-               break;
+       if (pVBInfo->IF_DEF_LVDS == 1) {
+               return 1;
+       } else {
+               flag = XGINew_GetReg1(pVBInfo->Part4Port, 0x00);
+               if ((flag == 1) || (flag == 2))
+                       return 1; /* 301b */
+               else
+                       return 0;
+       }
+}
 
-       case 0x02:
-       case 0x05:
-       case 0x0D:
-               filterPtr = PALMYFilter1;
-               break;
+void XGI_LongWait(struct vb_device_info *pVBInfo)
+{
+       unsigned short i;
 
-       case 0x03:
-               filterPtr = PALNYFilter1;
-               break;
+       i = XGINew_GetReg1(pVBInfo->P3c4, 0x1F);
 
-       case 0x08:
-       case 0x0C:
-               filterPtr = NTSCYFilter2;
-               break;
+       if (!(i & 0xC0)) {
+               for (i = 0; i < 0xFFFF; i++) {
+                       if (!(XGINew_GetReg2(pVBInfo->P3da) & 0x08))
+                               break;
+               }
 
-       case 0x0A:
-               filterPtr = PALMYFilter2;
-               break;
+               for (i = 0; i < 0xFFFF; i++) {
+                       if ((XGINew_GetReg2(pVBInfo->P3da) & 0x08))
+                               break;
+               }
+       }
+}
 
-       case 0x0B:
-               filterPtr = PALNYFilter2;
-               break;
+static void XGI_VBLongWait(struct vb_device_info *pVBInfo)
+{
+       unsigned short tempal, temp, i, j;
+       return;
+       if (!(pVBInfo->VBInfo & SetCRT2ToTV)) {
+               temp = 0;
+               for (i = 0; i < 3; i++) {
+                       for (j = 0; j < 100; j++) {
+                               tempal = XGINew_GetReg2(pVBInfo->P3da);
+                               if (temp & 0x01) { /* VBWaitMode2 */
+                                       if ((tempal & 0x08))
+                                               continue;
 
-       case 0x09:
-               filterPtr = PALYFilter2;
-               break;
+                                       if (!(tempal & 0x08))
+                                               break;
 
-       default:
-               return;
+                               } else { /* VBWaitMode1 */
+                                       if (!(tempal & 0x08))
+                                               continue;
+
+                                       if ((tempal & 0x08))
+                                               break;
+                               }
+                       }
+                       temp = temp ^ 0x01;
+               }
+       } else {
+               XGI_LongWait(pVBInfo);
        }
+       return;
+}
 
-       if (ModeNo <= 0x13)
-               tempal = pVBInfo->SModeIDTable[ModeIdIndex].VB_StTVYFilterIndex;
-       else
-               tempal
-                               = pVBInfo->EModeIDTable[ModeIdIndex].VB_ExtTVYFilterIndex;
+unsigned short XGI_GetRatePtrCRT2(struct xgi_hw_device_info *pXGIHWDE,
+               unsigned short ModeNo, unsigned short ModeIdIndex,
+               struct vb_device_info *pVBInfo)
+{
+       short LCDRefreshIndex[] = { 0x00, 0x00, 0x03, 0x01 },
+                       LCDARefreshIndex[] = { 0x00, 0x00, 0x03, 0x01, 0x01,
+                                       0x01, 0x01 };
 
-       if (tempcl == 0)
-               index = tempal * 4;
+       unsigned short RefreshRateTableIndex, i, modeflag, index, temp;
+
+       if (ModeNo <= 0x13)
+               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag;
        else
-               index = tempal * 7;
+               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
 
-       if ((tempcl == 0) && (tempch == 1)) {
-               XGINew_SetReg1(pVBInfo->Part2Port, 0x35, 0);
-               XGINew_SetReg1(pVBInfo->Part2Port, 0x36, 0);
-               XGINew_SetReg1(pVBInfo->Part2Port, 0x37, 0);
-               XGINew_SetReg1(pVBInfo->Part2Port, 0x38, filterPtr[index++]);
-       } else {
-               XGINew_SetReg1(pVBInfo->Part2Port, 0x35, filterPtr[index++]);
-               XGINew_SetReg1(pVBInfo->Part2Port, 0x36, filterPtr[index++]);
-               XGINew_SetReg1(pVBInfo->Part2Port, 0x37, filterPtr[index++]);
-               XGINew_SetReg1(pVBInfo->Part2Port, 0x38, filterPtr[index++]);
+       if (pVBInfo->IF_DEF_CH7005 == 1) {
+               if (pVBInfo->VBInfo & SetCRT2ToTV) {
+                       if (modeflag & HalfDCLK)
+                               return 0;
+               }
        }
 
-       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
-                       | VB_XGI302LV | VB_XGI301C)) {
-               XGINew_SetReg1(pVBInfo->Part2Port, 0x48, filterPtr[index++]);
-               XGINew_SetReg1(pVBInfo->Part2Port, 0x49, filterPtr[index++]);
-               XGINew_SetReg1(pVBInfo->Part2Port, 0x4A, filterPtr[index++]);
-       }
-}
+       if (ModeNo < 0x14)
+               return 0xFFFF;
 
-/* --------------------------------------------------------------------- */
-/* Function : XGI_GetTVPtrIndex2 */
-/* Input : */
-/* Output : bx 0 : NTSC */
-/* 1 : PAL */
-/* 2 : PALM */
-/* 3 : PALN */
-/* 4 : NTSC1024x768 */
-/* 5 : PAL-M 1024x768 */
-/* 6-7: reserved */
-/* cl 0 : YFilter1 */
-/* 1 : YFilter2 */
-/* ch 0 : 301A */
-/* 1 : 301B/302B/301LV/302LV */
-/* Description : */
-/* --------------------------------------------------------------------- */
-static void XGI_GetTVPtrIndex2(unsigned short *tempbx, unsigned char *tempcl,
-               unsigned char *tempch, struct vb_device_info *pVBInfo)
-{
-       *tempbx = 0;
-       *tempcl = 0;
-       *tempch = 0;
+       index = XGINew_GetReg1(pVBInfo->P3d4, 0x33);
+       index = index >> pVBInfo->SelectCRT2Rate;
+       index &= 0x0F;
 
-       if (pVBInfo->TVInfo & SetPALTV)
-               *tempbx = 1;
+       if (pVBInfo->LCDInfo & LCDNonExpanding)
+               index = 0;
 
-       if (pVBInfo->TVInfo & SetPALMTV)
-               *tempbx = 2;
+       if (index > 0)
+               index--;
 
-       if (pVBInfo->TVInfo & SetPALNTV)
-               *tempbx = 3;
+       if (pVBInfo->SetFlag & ProgrammingCRT2) {
+               if (pVBInfo->IF_DEF_CH7005 == 1) {
+                       if (pVBInfo->VBInfo & SetCRT2ToTV)
+                               index = 0;
+               }
 
-       if (pVBInfo->TVInfo & NTSC1024x768) {
-               *tempbx = 4;
-               if (pVBInfo->TVInfo & SetPALMTV)
-                       *tempbx = 5;
+               if (pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
+                       if (pVBInfo->IF_DEF_LVDS == 0) {
+                               if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B
+                                               | VB_XGI301LV | VB_XGI302LV
+                                               | VB_XGI301C))
+                                       temp
+                                                       = LCDARefreshIndex[pVBInfo->LCDResInfo
+                                                                       & 0x0F]; /* 301b */
+                               else
+                                       temp
+                                                       = LCDRefreshIndex[pVBInfo->LCDResInfo
+                                                                       & 0x0F];
+
+                               if (index > temp)
+                                       index = temp;
+                       } else {
+                               index = 0;
+                       }
+               }
        }
 
-       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
-                       | VB_XGI302LV | VB_XGI301C)) {
-               if ((!(pVBInfo->VBInfo & SetInSlaveMode)) || (pVBInfo->TVInfo
-                               & TVSimuMode)) {
-                       *tempbx += 8;
-                       *tempcl += 1;
+       RefreshRateTableIndex = pVBInfo->EModeIDTable[ModeIdIndex].REFindex;
+       ModeNo = pVBInfo->RefIndex[RefreshRateTableIndex].ModeID;
+       if (pXGIHWDE->jChipType >= XG20) { /* for XG20, XG21, XG27 */
+               /*
+               if (pVBInfo->RefIndex[RefreshRateTableIndex].Ext_InfoFlag & XG2xNotSupport) {
+                       index++;
+               }
+               */
+               if ((pVBInfo->RefIndex[RefreshRateTableIndex].XRes == 800)
+                               && (pVBInfo->RefIndex[RefreshRateTableIndex].YRes
+                                               == 600)) {
+                       index++;
+               }
+               /* Alan 10/19/2007; do the similiar adjustment like XGISearchCRT1Rate() */
+               if ((pVBInfo->RefIndex[RefreshRateTableIndex].XRes == 1024)
+                               && (pVBInfo->RefIndex[RefreshRateTableIndex].YRes
+                                               == 768)) {
+                       index++;
+               }
+               if ((pVBInfo->RefIndex[RefreshRateTableIndex].XRes == 1280)
+                               && (pVBInfo->RefIndex[RefreshRateTableIndex].YRes
+                                               == 1024)) {
+                       index++;
+               }
+       }
+
+       i = 0;
+       do {
+               if (pVBInfo->RefIndex[RefreshRateTableIndex + i].ModeID
+                               != ModeNo)
+                       break;
+               temp
+                               = pVBInfo->RefIndex[RefreshRateTableIndex + i].Ext_InfoFlag;
+               temp &= ModeInfoFlag;
+               if (temp < pVBInfo->ModeType)
+                       break;
+               i++;
+               index--;
+
+       } while (index != 0xFFFF);
+       if (!(pVBInfo->VBInfo & SetCRT2ToRAMDAC)) {
+               if (pVBInfo->VBInfo & SetInSlaveMode) {
+                       temp
+                                       = pVBInfo->RefIndex[RefreshRateTableIndex
+                                                       + i - 1].Ext_InfoFlag;
+                       if (temp & InterlaceMode)
+                               i++;
                }
        }
+       i--;
+       if ((pVBInfo->SetFlag & ProgrammingCRT2)) {
+               temp = XGI_AjustCRT2Rate(ModeNo, ModeIdIndex,
+                               RefreshRateTableIndex, &i, pVBInfo);
+       }
+       return RefreshRateTableIndex + i; /* return (0x01 | (temp1<<1)); */
+}
 
-       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
-                       | VB_XGI302LV | VB_XGI301C))
-               (*tempch)++;
+static void XGI_SetLCDAGroup(unsigned short ModeNo, unsigned short ModeIdIndex,
+               struct xgi_hw_device_info *HwDeviceExtension,
+               struct vb_device_info *pVBInfo)
+{
+       unsigned short RefreshRateTableIndex;
+       /* unsigned short temp ; */
+
+       /* pVBInfo->SelectCRT2Rate = 0; */
+
+       pVBInfo->SetFlag |= ProgrammingCRT2;
+       RefreshRateTableIndex = XGI_GetRatePtrCRT2(HwDeviceExtension, ModeNo,
+                       ModeIdIndex, pVBInfo);
+       XGI_GetLVDSResInfo(ModeNo, ModeIdIndex, pVBInfo);
+       XGI_GetLVDSData(ModeNo, ModeIdIndex, RefreshRateTableIndex, pVBInfo);
+       XGI_ModCRT1Regs(ModeNo, ModeIdIndex, RefreshRateTableIndex,
+                       HwDeviceExtension, pVBInfo);
+       XGI_SetLVDSRegs(ModeNo, ModeIdIndex, RefreshRateTableIndex, pVBInfo);
+       XGI_SetCRT2ECLK(ModeNo, ModeIdIndex, RefreshRateTableIndex, pVBInfo);
 }
 
-/* --------------------------------------------------------------------- */
-/* Function : XGI_SetCRT2ModeRegs */
-/* Input : */
-/* Output : */
-/* Description : Origin code for crt2group */
-/* --------------------------------------------------------------------- */
-void XGI_SetCRT2ModeRegs(unsigned short ModeNo,
+unsigned char XGI_SetCRT2Group301(unsigned short ModeNo,
                struct xgi_hw_device_info *HwDeviceExtension,
                struct vb_device_info *pVBInfo)
 {
-       unsigned short tempbl;
-       short tempcl;
+       unsigned short tempbx, ModeIdIndex, RefreshRateTableIndex;
 
-       unsigned char tempah;
+       tempbx = pVBInfo->VBInfo;
+       pVBInfo->SetFlag |= ProgrammingCRT2;
+       XGI_SearchModeID(ModeNo, &ModeIdIndex, pVBInfo);
+       pVBInfo->SelectCRT2Rate = 4;
+       RefreshRateTableIndex = XGI_GetRatePtrCRT2(HwDeviceExtension, ModeNo,
+                       ModeIdIndex, pVBInfo);
+       XGI_SaveCRT2Info(ModeNo, pVBInfo);
+       XGI_GetCRT2ResInfo(ModeNo, ModeIdIndex, pVBInfo);
+       XGI_GetCRT2Data(ModeNo, ModeIdIndex, RefreshRateTableIndex, pVBInfo);
+       XGI_PreSetGroup1(ModeNo, ModeIdIndex, HwDeviceExtension,
+                       RefreshRateTableIndex, pVBInfo);
+       XGI_SetGroup1(ModeNo, ModeIdIndex, HwDeviceExtension,
+                       RefreshRateTableIndex, pVBInfo);
+       XGI_SetLockRegs(ModeNo, ModeIdIndex, HwDeviceExtension,
+                       RefreshRateTableIndex, pVBInfo);
+       XGI_SetGroup2(ModeNo, ModeIdIndex, RefreshRateTableIndex,
+                       HwDeviceExtension, pVBInfo);
+       XGI_SetLCDRegs(ModeNo, ModeIdIndex, HwDeviceExtension,
+                       RefreshRateTableIndex, pVBInfo);
+       XGI_SetTap4Regs(pVBInfo);
+       XGI_SetGroup3(ModeNo, ModeIdIndex, pVBInfo);
+       XGI_SetGroup4(ModeNo, ModeIdIndex, RefreshRateTableIndex,
+                       HwDeviceExtension, pVBInfo);
+       XGI_SetCRT2VCLK(ModeNo, ModeIdIndex, RefreshRateTableIndex, pVBInfo);
+       XGI_SetGroup5(ModeNo, ModeIdIndex, pVBInfo);
+       XGI_AutoThreshold(pVBInfo);
+       return 1;
+}
 
-       /* XGINew_SetReg1(pVBInfo->Part1Port, 0x03, 0x00); // fix write part1 index 0 BTDRAM bit Bug */
-       tempah = 0;
-       if (!(pVBInfo->VBInfo & DisableCRT2Display)) {
-               tempah = XGINew_GetReg1(pVBInfo->Part1Port, 0x00);
-               tempah &= ~0x10; /* BTRAMDAC */
-               tempah |= 0x40; /* BTRAM */
+void XGI_SenseCRT1(struct vb_device_info *pVBInfo)
+{
+       unsigned char CRTCData[17] = { 0x5F, 0x4F, 0x50, 0x82, 0x55, 0x81,
+                       0x0B, 0x3E, 0xE9, 0x0B, 0xDF, 0xE7, 0x04, 0x00, 0x00,
+                       0x05, 0x00 };
 
-               if (pVBInfo->VBInfo & (SetCRT2ToRAMDAC | SetCRT2ToTV
-                               | SetCRT2ToLCD)) {
-                       tempah = 0x40; /* BTDRAM */
-                       if (ModeNo > 0x13) {
-                               tempcl = pVBInfo->ModeType;
-                               tempcl -= ModeVGA;
-                               if (tempcl >= 0) {
-                                       tempah = (0x008 >> tempcl); /* BT Color */
-                                       if (tempah == 0)
-                                               tempah = 1;
-                                       tempah |= 0x040;
-                               }
-                       }
-                       if (pVBInfo->VBInfo & SetInSlaveMode)
-                               tempah ^= 0x50; /* BTDAC */
-               }
-       }
+       unsigned char SR01 = 0, SR1F = 0, SR07 = 0, SR06 = 0;
 
-       /* 0210 shampoo
-       if (pVBInfo->VBInfo & DisableCRT2Display) {
-               tempah = 0;
-       }
+       unsigned char CR17, CR63, SR31;
+       unsigned short temp;
+       unsigned char DAC_TEST_PARMS[3] = { 0x0F, 0x0F, 0x0F };
 
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x00, tempah);
-       if (pVBInfo->VBInfo & (SetCRT2ToRAMDAC | SetCRT2ToTV | SetCRT2ToLCD)) {
-               tempcl = pVBInfo->ModeType;
-               if (ModeNo > 0x13) {
-                       tempcl -= ModeVGA;
-                       if ((tempcl > 0) || (tempcl == 0)) {
-                               tempah=(0x008>>tempcl) ;
-                               if (tempah == 0)
-                                       tempah = 1;
-                               tempah |= 0x040;
-                       }
-               } else {
-                       tempah = 0x040;
-               }
+       int i;
+       XGINew_SetReg1(pVBInfo->P3c4, 0x05, 0x86);
 
-               if (pVBInfo->VBInfo & SetInSlaveMode) {
-                       tempah = (tempah ^ 0x050);
-               }
-       }
-       */
+       /* [2004/05/06] Vicent to fix XG42 single LCD sense to CRT+LCD */
+       XGINew_SetReg1(pVBInfo->P3d4, 0x57, 0x4A);
+       XGINew_SetReg1(pVBInfo->P3d4, 0x53, (unsigned char) (XGINew_GetReg1(
+                       pVBInfo->P3d4, 0x53) | 0x02));
 
-       XGINew_SetReg1(pVBInfo->Part1Port, 0x00, tempah);
-       tempah = 0x08;
-       tempbl = 0xf0;
+       SR31 = (unsigned char) XGINew_GetReg1(pVBInfo->P3c4, 0x31);
+       CR63 = (unsigned char) XGINew_GetReg1(pVBInfo->P3d4, 0x63);
+       SR01 = (unsigned char) XGINew_GetReg1(pVBInfo->P3c4, 0x01);
 
-       if (pVBInfo->VBInfo & DisableCRT2Display) {
-               XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x2e, tempbl, tempah);
-       } else {
-               tempah = 0x00;
-               tempbl = 0xff;
+       XGINew_SetReg1(pVBInfo->P3c4, 0x01, (unsigned char) (SR01 & 0xDF));
+       XGINew_SetReg1(pVBInfo->P3d4, 0x63, (unsigned char) (CR63 & 0xBF));
 
-               if (pVBInfo->VBInfo & (SetCRT2ToRAMDAC | SetCRT2ToTV
-                               | SetCRT2ToLCD | SetCRT2ToLCDA)) {
-                       if ((pVBInfo->VBInfo & SetCRT2ToLCDA)
-                                       && (!(pVBInfo->VBInfo & SetSimuScanMode))) {
-                               tempbl &= 0xf7;
-                               tempah |= 0x01;
-                               XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x2e,
-                                               tempbl, tempah);
-                       } else {
-                               if (pVBInfo->VBInfo & SetCRT2ToLCDA) {
-                                       tempbl &= 0xf7;
-                                       tempah |= 0x01;
-                               }
+       CR17 = (unsigned char) XGINew_GetReg1(pVBInfo->P3d4, 0x17);
+       XGINew_SetReg1(pVBInfo->P3d4, 0x17, (unsigned char) (CR17 | 0x80));
 
-                               if (pVBInfo->VBInfo & (SetCRT2ToRAMDAC
-                                               | SetCRT2ToTV | SetCRT2ToLCD)) {
-                                       tempbl &= 0xf8;
-                                       tempah = 0x01;
+       SR1F = (unsigned char) XGINew_GetReg1(pVBInfo->P3c4, 0x1F);
+       XGINew_SetReg1(pVBInfo->P3c4, 0x1F, (unsigned char) (SR1F | 0x04));
 
-                                       if (!(pVBInfo->VBInfo & SetInSlaveMode))
-                                               tempah |= 0x02;
+       SR07 = (unsigned char) XGINew_GetReg1(pVBInfo->P3c4, 0x07);
+       XGINew_SetReg1(pVBInfo->P3c4, 0x07, (unsigned char) (SR07 & 0xFB));
+       SR06 = (unsigned char) XGINew_GetReg1(pVBInfo->P3c4, 0x06);
+       XGINew_SetReg1(pVBInfo->P3c4, 0x06, (unsigned char) (SR06 & 0xC3));
 
-                                       if (!(pVBInfo->VBInfo & SetCRT2ToRAMDAC)) {
-                                               tempah = tempah ^ 0x05;
-                                               if (!(pVBInfo->VBInfo
-                                                               & SetCRT2ToLCD))
-                                                       tempah = tempah ^ 0x01;
-                                       }
+       XGINew_SetReg1(pVBInfo->P3d4, 0x11, 0x00);
 
-                                       if (!(pVBInfo->VBInfo
-                                                       & SetCRT2ToDualEdge))
-                                               tempah |= 0x08;
-                                       XGINew_SetRegANDOR(pVBInfo->Part1Port,
-                                                       0x2e, tempbl, tempah);
-                               } else {
-                                       XGINew_SetRegANDOR(pVBInfo->Part1Port,
-                                                       0x2e, tempbl, tempah);
-                               }
-                       }
-               } else {
-                       XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x2e, tempbl,
-                                       tempah);
-               }
-       }
+       for (i = 0; i < 8; i++)
+               XGINew_SetReg1(pVBInfo->P3d4, (unsigned short) i, CRTCData[i]);
 
-       if (pVBInfo->VBInfo & (SetCRT2ToRAMDAC | SetCRT2ToTV | SetCRT2ToLCD
-                       | SetCRT2ToLCDA)) {
-               tempah &= (~0x08);
-               if ((pVBInfo->ModeType == ModeVGA) && (!(pVBInfo->VBInfo
-                               & SetInSlaveMode))) {
-                       tempah |= 0x010;
-               }
-               tempah |= 0x080;
+       for (i = 8; i < 11; i++)
+               XGINew_SetReg1(pVBInfo->P3d4, (unsigned short) (i + 8),
+                               CRTCData[i]);
 
-               if (pVBInfo->VBInfo & SetCRT2ToTV) {
-                       /* if (!(pVBInfo->TVInfo & (SetYPbPrMode525p | SetYPbPrMode750p))) { */
-                       tempah |= 0x020;
-                       if (ModeNo > 0x13) {
-                               if (pVBInfo->VBInfo & DriverMode)
-                                       tempah = tempah ^ 0x20;
-                       }
-                       /* } */
-               }
+       for (i = 11; i < 13; i++)
+               XGINew_SetReg1(pVBInfo->P3d4, (unsigned short) (i + 4),
+                               CRTCData[i]);
 
-               XGINew_SetRegANDOR(pVBInfo->Part4Port, 0x0D, ~0x0BF, tempah);
-               tempah = 0;
+       for (i = 13; i < 16; i++)
+               XGINew_SetReg1(pVBInfo->P3c4, (unsigned short) (i - 3),
+                               CRTCData[i]);
 
-               if (pVBInfo->LCDInfo & SetLCDDualLink)
-                       tempah |= 0x40;
+       XGINew_SetReg1(pVBInfo->P3c4, 0x0E, (unsigned char) (CRTCData[16]
+                       & 0xE0));
 
-               if (pVBInfo->VBInfo & SetCRT2ToTV) {
-                       /* if ((!(pVBInfo->VBInfo & SetCRT2ToHiVisionTV)) && (!(pVBInfo->TVInfo & (SetYPbPrMode525p | SetYPbPrMode750p)))) { */
-                       if (pVBInfo->TVInfo & RPLLDIV2XO)
-                               tempah |= 0x40;
-                       /* } */
-               }
+       XGINew_SetReg1(pVBInfo->P3c4, 0x31, 0x00);
+       XGINew_SetReg1(pVBInfo->P3c4, 0x2B, 0x1B);
+       XGINew_SetReg1(pVBInfo->P3c4, 0x2C, 0xE1);
 
-               if ((pVBInfo->LCDResInfo == Panel1280x1024)
-                               || (pVBInfo->LCDResInfo == Panel1280x1024x75))
-                       tempah |= 0x80;
+       XGINew_SetReg3(pVBInfo->P3c8, 0x00);
+
+       for (i = 0; i < 256; i++) {
+               XGINew_SetReg3((pVBInfo->P3c8 + 1),
+                               (unsigned char) DAC_TEST_PARMS[0]);
+               XGINew_SetReg3((pVBInfo->P3c8 + 1),
+                               (unsigned char) DAC_TEST_PARMS[1]);
+               XGINew_SetReg3((pVBInfo->P3c8 + 1),
+                               (unsigned char) DAC_TEST_PARMS[2]);
+       }
+
+       XGI_VBLongWait(pVBInfo);
+       XGI_VBLongWait(pVBInfo);
+       XGI_VBLongWait(pVBInfo);
+
+       mdelay(1);
+
+       XGI_WaitDisply(pVBInfo);
+       temp = XGINew_GetReg2(pVBInfo->P3c2);
+
+       if (temp & 0x10)
+               XGINew_SetRegANDOR(pVBInfo->P3d4, 0x32, 0xDF, 0x20);
+       else
+               XGINew_SetRegANDOR(pVBInfo->P3d4, 0x32, 0xDF, 0x00);
 
-               if (pVBInfo->LCDResInfo == Panel1280x960)
-                       tempah |= 0x80;
+       /* alan, avoid display something, set BLACK DAC if not restore DAC */
+       XGINew_SetReg3(pVBInfo->P3c8, 0x00);
 
-               XGINew_SetReg1(pVBInfo->Part4Port, 0x0C, tempah);
+       for (i = 0; i < 256; i++) {
+               XGINew_SetReg3((pVBInfo->P3c8 + 1), 0);
+               XGINew_SetReg3((pVBInfo->P3c8 + 1), 0);
+               XGINew_SetReg3((pVBInfo->P3c8 + 1), 0);
        }
 
-       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
-                       | VB_XGI302LV | VB_XGI301C)) {
-               tempah = 0;
-               tempbl = 0xfb;
-
-               if (pVBInfo->VBInfo & SetCRT2ToDualEdge) {
-                       tempbl = 0xff;
-                       if (pVBInfo->VBInfo & SetCRT2ToLCDA)
-                               tempah |= 0x04; /* shampoo 0129 */
-               }
+       XGINew_SetReg1(pVBInfo->P3c4, 0x01, SR01);
+       XGINew_SetReg1(pVBInfo->P3d4, 0x63, CR63);
+       XGINew_SetReg1(pVBInfo->P3c4, 0x31, SR31);
 
-               XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x13, tempbl, tempah);
-               tempah = 0x00;
-               tempbl = 0xcf;
-               if (!(pVBInfo->VBInfo & DisableCRT2Display)) {
-                       if (pVBInfo->VBInfo & SetCRT2ToDualEdge)
-                               tempah |= 0x30;
-               }
+       /* [2004/05/11] Vicent */
+       XGINew_SetReg1(pVBInfo->P3d4, 0x53, (unsigned char) (XGINew_GetReg1(
+                       pVBInfo->P3d4, 0x53) & 0xFD));
+       XGINew_SetReg1(pVBInfo->P3c4, 0x1F, (unsigned char) SR1F);
+}
 
-               XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x2c, tempbl, tempah);
-               tempah = 0;
-               tempbl = 0x3f;
+void XGI_EnableBridge(struct xgi_hw_device_info *HwDeviceExtension,
+               struct vb_device_info *pVBInfo)
+{
+       unsigned short tempbl, tempah;
 
-               if (!(pVBInfo->VBInfo & DisableCRT2Display)) {
-                       if (pVBInfo->VBInfo & SetCRT2ToDualEdge)
-                               tempah |= 0xc0;
-               }
-               XGINew_SetRegANDOR(pVBInfo->Part4Port, 0x21, tempbl, tempah);
+       if (pVBInfo->SetFlag == Win9xDOSMode) {
+               if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
+                               | VB_XGI302LV | VB_XGI301C)) {
+                       XGI_DisplayOn(HwDeviceExtension, pVBInfo);
+                       return;
+               } else
+                       /* LVDS or CH7017 */
+                       return;
        }
 
-       tempah = 0;
-       tempbl = 0x7f;
-       if (!(pVBInfo->VBInfo & SetCRT2ToLCDA)) {
-               tempbl = 0xff;
-               if (!(pVBInfo->VBInfo & SetCRT2ToDualEdge))
-                       tempah |= 0x80;
-       }
+       if (HwDeviceExtension->jChipType < XG40) {
+               if (!XGI_DisableChISLCD(pVBInfo)) {
+                       if ((XGI_EnableChISLCD(pVBInfo)) || (pVBInfo->VBInfo
+                                       & (SetCRT2ToLCD | SetCRT2ToLCDA))) {
+                               if (pVBInfo->LCDInfo & SetPWDEnable) {
+                                       XGI_EnablePWD(pVBInfo);
+                               } else {
+                                       pVBInfo->LCDInfo &= (~SetPWDEnable);
+                                       if (pVBInfo->VBType & (VB_XGI301LV
+                                                       | VB_XGI302LV
+                                                       | VB_XGI301C)) {
+                                               tempbl = 0xFD;
+                                               tempah = 0x02;
+                                       } else {
+                                               tempbl = 0xFB;
+                                               tempah = 0x00;
+                                       }
 
-       XGINew_SetRegANDOR(pVBInfo->Part4Port, 0x23, tempbl, tempah);
+                                       XGI_SetPanelPower(tempah, tempbl,
+                                                       pVBInfo);
+                                       XGI_SetPanelDelay(1, pVBInfo);
+                               }
+                       }
+               }
+       } /* Not 340 */
 
-       if (pVBInfo->VBType & (VB_XGI302LV | VB_XGI301C)) {
-               if (pVBInfo->LCDInfo & SetLCDDualLink) {
-                       XGINew_SetRegOR(pVBInfo->Part4Port, 0x27, 0x20);
-                       XGINew_SetRegOR(pVBInfo->Part4Port, 0x34, 0x10);
+       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
+                       | VB_XGI302LV | VB_XGI301C)) {
+               if (!(pVBInfo->SetFlag & DisableChA)) {
+                       if (pVBInfo->SetFlag & EnableChA) {
+                               XGINew_SetReg1(pVBInfo->Part1Port, 0x1E, 0x20); /* Power on */
+                       } else {
+                               if (pVBInfo->VBInfo & SetCRT2ToDualEdge) { /* SetCRT2ToLCDA ) */
+                                       XGINew_SetReg1(pVBInfo->Part1Port,
+                                                       0x1E, 0x20); /* Power on */
+                               }
+                       }
                }
-       }
-}
 
-static void XGI_CloseCRTC(struct xgi_hw_device_info *HwDeviceExtension,
-               struct vb_device_info *pVBInfo)
-{
-       unsigned short tempbx;
+               if (!(pVBInfo->SetFlag & DisableChB)) {
+                       if ((pVBInfo->SetFlag & EnableChB) || (pVBInfo->VBInfo
+                                       & (SetCRT2ToLCD | SetCRT2ToTV
+                                                       | SetCRT2ToRAMDAC))) {
+                               tempah = (unsigned char) XGINew_GetReg1(
+                                               pVBInfo->P3c4, 0x32);
+                               tempah &= 0xDF;
+                               if (pVBInfo->VBInfo & SetInSlaveMode) {
+                                       if (!(pVBInfo->VBInfo & SetCRT2ToRAMDAC))
+                                               tempah |= 0x20;
+                               }
+                               XGINew_SetReg1(pVBInfo->P3c4, 0x32, tempah);
+                               XGINew_SetRegOR(pVBInfo->P3c4, 0x1E, 0x20);
 
-       tempbx = 0;
+                               tempah = (unsigned char) XGINew_GetReg1(
+                                               pVBInfo->Part1Port, 0x2E);
 
-       if (pVBInfo->VBInfo & SetCRT2ToLCDA)
-               tempbx = 0x08A0;
+                               if (!(tempah & 0x80))
+                                       XGINew_SetRegOR(pVBInfo->Part1Port,
+                                                       0x2E, 0x80); /* BVBDOENABLE = 1 */
 
-}
+                               XGINew_SetRegAND(pVBInfo->Part1Port, 0x00, 0x7F); /* BScreenOFF = 0 */
+                       }
+               }
 
-void XGI_OpenCRTC(struct xgi_hw_device_info *HwDeviceExtension,
-               struct vb_device_info *pVBInfo)
-{
-       unsigned short tempbx;
-       tempbx = 0;
-}
+               if ((pVBInfo->SetFlag & (EnableChA | EnableChB))
+                               || (!(pVBInfo->VBInfo & DisableCRT2Display))) {
+                       XGINew_SetRegANDOR(pVBInfo->Part2Port, 0x00, ~0xE0,
+                                       0x20); /* shampoo 0129 */
+                       if (pVBInfo->VBType & (VB_XGI302LV | VB_XGI301C)) {
+                               if (!XGI_DisableChISLCD(pVBInfo)) {
+                                       if (XGI_EnableChISLCD(pVBInfo)
+                                                       || (pVBInfo->VBInfo
+                                                                       & (SetCRT2ToLCD
+                                                                                       | SetCRT2ToLCDA)))
+                                               XGINew_SetRegAND(
+                                                               pVBInfo->Part4Port,
+                                                               0x2A, 0x7F); /* LVDS PLL power on */
+                               }
+                               XGINew_SetRegAND(pVBInfo->Part4Port, 0x30, 0x7F); /* LVDS Driver power on */
+                       }
+               }
 
-static void XGI_GetRAMDAC2DATA(unsigned short ModeNo, unsigned short ModeIdIndex,
-               unsigned short RefreshRateTableIndex,
-               struct vb_device_info *pVBInfo)
-{
-       unsigned short tempax, tempbx, temp1, temp2, modeflag = 0, tempcx,
-                       StandTableIndex, CRT1Index;
+               tempah = 0x00;
 
-       pVBInfo->RVBHCMAX = 1;
-       pVBInfo->RVBHCFACT = 1;
+               if (!(pVBInfo->VBInfo & DisableCRT2Display)) {
+                       tempah = 0xc0;
 
-       if (ModeNo <= 0x13) {
-               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag;
-               StandTableIndex = XGI_GetModePtr(ModeNo, ModeIdIndex, pVBInfo);
-               tempax = pVBInfo->StandTable[StandTableIndex].CRTC[0];
-               tempbx = pVBInfo->StandTable[StandTableIndex].CRTC[6];
-               temp1 = pVBInfo->StandTable[StandTableIndex].CRTC[7];
-       } else {
-               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
-               CRT1Index
-                               = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT1CRTC;
-               CRT1Index &= IndexMask;
-               temp1
-                               = (unsigned short) pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[0];
-               temp2
-                               = (unsigned short) pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[5];
-               tempax = (temp1 & 0xFF) | ((temp2 & 0x03) << 8);
-               tempbx
-                               = (unsigned short) pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[8];
-               tempcx
-                               = (unsigned short) pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[14]
-                                               << 8;
-               tempcx &= 0x0100;
-               tempcx = tempcx << 2;
-               tempbx |= tempcx;
-               temp1
-                               = (unsigned short) pVBInfo->XGINEWUB_CRT1Table[CRT1Index].CR[9];
-       }
+                       if (!(pVBInfo->VBInfo & SetSimuScanMode)) {
+                               if (pVBInfo->VBInfo & SetCRT2ToLCDA) {
+                                       if (pVBInfo->VBInfo & SetCRT2ToDualEdge) {
+                                               tempah = tempah & 0x40;
+                                               if (pVBInfo->VBInfo
+                                                               & SetCRT2ToLCDA)
+                                                       tempah = tempah ^ 0xC0;
 
-       if (temp1 & 0x01)
-               tempbx |= 0x0100;
+                                               if (pVBInfo->SetFlag
+                                                               & DisableChB)
+                                                       tempah &= 0xBF;
 
-       if (temp1 & 0x20)
-               tempbx |= 0x0200;
-       tempax += 5;
+                                               if (pVBInfo->SetFlag
+                                                               & DisableChA)
+                                                       tempah &= 0x7F;
 
-       if (modeflag & Charx8Dot)
-               tempax *= 8;
-       else
-               tempax *= 9;
+                                               if (pVBInfo->SetFlag
+                                                               & EnableChB)
+                                                       tempah |= 0x40;
 
-       pVBInfo->VGAHT = tempax;
-       pVBInfo->HT = tempax;
-       tempbx++;
-       pVBInfo->VGAVT = tempbx;
-       pVBInfo->VT = tempbx;
-}
+                                               if (pVBInfo->SetFlag
+                                                               & EnableChA)
+                                                       tempah |= 0x80;
+                                       }
+                               }
+                       }
+               }
 
-static unsigned short XGI_GetColorDepth(unsigned short ModeNo,
-               unsigned short ModeIdIndex, struct vb_device_info *pVBInfo)
-{
-       unsigned short ColorDepth[6] = { 1, 2, 4, 4, 6, 8 };
-       short index;
-       unsigned short modeflag;
+               XGINew_SetRegOR(pVBInfo->Part4Port, 0x1F, tempah); /* EnablePart4_1F */
 
-       if (ModeNo <= 0x13)
-               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag;
-       else
-               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
+               if (pVBInfo->SetFlag & Win9xDOSMode) {
+                       XGI_DisplayOn(HwDeviceExtension, pVBInfo);
+                       return;
+               }
+
+               if (!(pVBInfo->SetFlag & DisableChA)) {
+                       XGI_VBLongWait(pVBInfo);
+                       if (!(pVBInfo->SetFlag & GatingCRT)) {
+                               XGI_DisableGatingCRT(HwDeviceExtension, pVBInfo);
+                               XGI_DisplayOn(HwDeviceExtension, pVBInfo);
+                               XGI_VBLongWait(pVBInfo);
+                       }
+               }
+       } /* 301 */
+       else { /* LVDS */
+               if (pVBInfo->VBInfo & (SetCRT2ToTV | SetCRT2ToLCD
+                               | SetCRT2ToLCDA))
+                       XGINew_SetRegOR(pVBInfo->Part1Port, 0x1E, 0x20); /* enable CRT2 */
 
-       index = (modeflag & ModeInfoFlag) - ModeEGA;
+               tempah = (unsigned char) XGINew_GetReg1(pVBInfo->Part1Port,
+                               0x2E);
+               if (!(tempah & 0x80))
+                       XGINew_SetRegOR(pVBInfo->Part1Port, 0x2E, 0x80); /* BVBDOENABLE = 1 */
 
-       if (index < 0)
-               index = 0;
+               XGINew_SetRegAND(pVBInfo->Part1Port, 0x00, 0x7F);
+               XGI_DisplayOn(HwDeviceExtension, pVBInfo);
+       } /* End of VB */
 
-       return ColorDepth[index];
-}
+       if (HwDeviceExtension->jChipType < XG40) {
+               if (!XGI_EnableChISLCD(pVBInfo)) {
+                       if (pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) {
+                               if (XGI_BacklightByDrv(pVBInfo))
+                                       return;
+                       } else
+                               return;
+               }
 
-void XGI_UnLockCRT2(struct xgi_hw_device_info *HwDeviceExtension,
-               struct vb_device_info *pVBInfo)
-{
+               if (pVBInfo->LCDInfo & SetPWDEnable) {
+                       XGI_FirePWDEnable(pVBInfo);
+                       return;
+               }
 
-       XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x2f, 0xFF, 0x01);
+               XGI_SetPanelDelay(2, pVBInfo);
 
+               if (pVBInfo->VBType & (VB_XGI301LV | VB_XGI302LV | VB_XGI301C)) {
+                       tempah = 0x01;
+                       tempbl = 0xFE; /* turn on backlght */
+               } else {
+                       tempbl = 0xF7;
+                       tempah = 0x00;
+               }
+               XGI_SetPanelPower(tempah, tempbl, pVBInfo);
+       }
 }
 
-void XGI_LockCRT2(struct xgi_hw_device_info *HwDeviceExtension,
+static void XGI_SetCRT1Group(struct xgi_hw_device_info *HwDeviceExtension,
+               unsigned short ModeNo, unsigned short ModeIdIndex,
                struct vb_device_info *pVBInfo)
 {
+       unsigned short StandTableIndex, RefreshRateTableIndex, b3CC, temp;
 
-       XGINew_SetRegANDOR(pVBInfo->Part1Port, 0x2F, 0xFE, 0x00);
-
-}
-
-static void XGINew_EnableCRT2(struct vb_device_info *pVBInfo)
-{
-       XGINew_SetRegANDOR(pVBInfo->P3c4, 0x1E, 0xFF, 0x20);
-}
+       unsigned short XGINew_P3cc = pVBInfo->P3cc;
 
-unsigned char XGI_BridgeIsOn(struct vb_device_info *pVBInfo)
-{
-       unsigned short flag;
+       /* XGINew_CRT1Mode = ModeNo; // SaveModeID */
+       StandTableIndex = XGI_GetModePtr(ModeNo, ModeIdIndex, pVBInfo);
+       /* XGI_SetBIOSData(ModeNo, ModeIdIndex); */
+       /* XGI_ClearBankRegs(ModeNo, ModeIdIndex); */
+       XGI_SetSeqRegs(ModeNo, StandTableIndex, ModeIdIndex, pVBInfo);
+       XGI_SetMiscRegs(StandTableIndex, pVBInfo);
+       XGI_SetCRTCRegs(HwDeviceExtension, StandTableIndex, pVBInfo);
+       XGI_SetATTRegs(ModeNo, StandTableIndex, ModeIdIndex, pVBInfo);
+       XGI_SetGRCRegs(StandTableIndex, pVBInfo);
+       XGI_ClearExt1Regs(pVBInfo);
 
-       if (pVBInfo->IF_DEF_LVDS == 1) {
-               return 1;
-       } else {
-               flag = XGINew_GetReg1(pVBInfo->Part4Port, 0x00);
-               if ((flag == 1) || (flag == 2))
-                       return 1; /* 301b */
-               else
-                       return 0;
+       /* if (pVBInfo->IF_DEF_ExpLink) */
+       if (HwDeviceExtension->jChipType == XG27) {
+               if (pVBInfo->IF_DEF_LVDS == 0)
+                       XGI_SetDefaultVCLK(pVBInfo);
        }
-}
-
-void XGI_LongWait(struct vb_device_info *pVBInfo)
-{
-       unsigned short i;
 
-       i = XGINew_GetReg1(pVBInfo->P3c4, 0x1F);
+       temp = ~ProgrammingCRT2;
+       pVBInfo->SetFlag &= temp;
+       pVBInfo->SelectCRT2Rate = 0;
 
-       if (!(i & 0xC0)) {
-               for (i = 0; i < 0xFFFF; i++) {
-                       if (!(XGINew_GetReg2(pVBInfo->P3da) & 0x08))
-                               break;
+       if (pVBInfo->VBType & (VB_XGI301B | VB_XGI302B | VB_XGI301LV
+                       | VB_XGI302LV | VB_XGI301C)) {
+               if (pVBInfo->VBInfo & (SetSimuScanMode | SetCRT2ToLCDA
+                               | SetInSlaveMode)) {
+                       pVBInfo->SetFlag |= ProgrammingCRT2;
                }
+       }
 
-               for (i = 0; i < 0xFFFF; i++) {
-                       if ((XGINew_GetReg2(pVBInfo->P3da) & 0x08))
-                               break;
+       RefreshRateTableIndex = XGI_GetRatePtrCRT2(HwDeviceExtension, ModeNo,
+                       ModeIdIndex, pVBInfo);
+       if (RefreshRateTableIndex != 0xFFFF) {
+               XGI_SetSync(RefreshRateTableIndex, pVBInfo);
+               XGI_SetCRT1CRTC(ModeNo, ModeIdIndex, RefreshRateTableIndex,
+                               pVBInfo, HwDeviceExtension);
+               XGI_SetCRT1DE(HwDeviceExtension, ModeNo, ModeIdIndex,
+                               RefreshRateTableIndex, pVBInfo);
+               XGI_SetCRT1Offset(ModeNo, ModeIdIndex, RefreshRateTableIndex,
+                               HwDeviceExtension, pVBInfo);
+               XGI_SetCRT1VCLK(ModeNo, ModeIdIndex, HwDeviceExtension,
+                               RefreshRateTableIndex, pVBInfo);
+       }
+
+       if ((HwDeviceExtension->jChipType >= XG20)
+                       && (HwDeviceExtension->jChipType < XG27)) { /* fix H/W DCLK/2 bug */
+               if ((ModeNo == 0x00) | (ModeNo == 0x01)) {
+                       XGINew_SetReg1(pVBInfo->P3c4, 0x2B, 0x4E);
+                       XGINew_SetReg1(pVBInfo->P3c4, 0x2C, 0xE9);
+                       b3CC = (unsigned char) XGINew_GetReg2(XGINew_P3cc);
+                       XGINew_SetReg3(XGINew_P3cc, (b3CC |= 0x0C));
+               } else if ((ModeNo == 0x04) | (ModeNo == 0x05) | (ModeNo
+                               == 0x0D)) {
+                       XGINew_SetReg1(pVBInfo->P3c4, 0x2B, 0x1B);
+                       XGINew_SetReg1(pVBInfo->P3c4, 0x2C, 0xE3);
+                       b3CC = (unsigned char) XGINew_GetReg2(XGINew_P3cc);
+                       XGINew_SetReg3(XGINew_P3cc, (b3CC |= 0x0C));
                }
        }
-}
 
-static void XGI_VBLongWait(struct vb_device_info *pVBInfo)
-{
-       unsigned short tempal, temp, i, j;
-       return;
-       if (!(pVBInfo->VBInfo & SetCRT2ToTV)) {
-               temp = 0;
-               for (i = 0; i < 3; i++) {
-                       for (j = 0; j < 100; j++) {
-                               tempal = XGINew_GetReg2(pVBInfo->P3da);
-                               if (temp & 0x01) { /* VBWaitMode2 */
-                                       if ((tempal & 0x08))
-                                               continue;
+       if (HwDeviceExtension->jChipType >= XG21) {
+               temp = XGINew_GetReg1(pVBInfo->P3d4, 0x38);
+               if (temp & 0xA0) {
 
-                                       if (!(tempal & 0x08))
-                                               break;
+                       /* XGINew_SetRegAND(pVBInfo->P3d4, 0x4A, ~0x20); *//* Enable write GPIOF */
+                       /* XGINew_SetRegAND(pVBInfo->P3d4, 0x48, ~0x20); *//* P. DWN */
+                       /* XG21 CRT1 Timing */
+                       if (HwDeviceExtension->jChipType == XG27)
+                               XGI_SetXG27CRTC(ModeNo, ModeIdIndex,
+                                               RefreshRateTableIndex, pVBInfo);
+                       else
+                               XGI_SetXG21CRTC(ModeNo, ModeIdIndex,
+                                               RefreshRateTableIndex, pVBInfo);
 
-                               } else { /* VBWaitMode1 */
-                                       if (!(tempal & 0x08))
-                                               continue;
+                       XGI_UpdateXG21CRTC(ModeNo, pVBInfo,
+                                       RefreshRateTableIndex);
 
-                                       if ((tempal & 0x08))
-                                               break;
-                               }
+                       if (HwDeviceExtension->jChipType == XG27)
+                               XGI_SetXG27LCD(pVBInfo, RefreshRateTableIndex,
+                                               ModeNo);
+                       else
+                               XGI_SetXG21LCD(pVBInfo, RefreshRateTableIndex,
+                                               ModeNo);
+
+                       if (pVBInfo->IF_DEF_LVDS == 1) {
+                               if (HwDeviceExtension->jChipType == XG27)
+                                       XGI_SetXG27LVDSPara(ModeNo,
+                                                       ModeIdIndex, pVBInfo);
+                               else
+                                       XGI_SetXG21LVDSPara(ModeNo,
+                                                       ModeIdIndex, pVBInfo);
                        }
-                       temp = temp ^ 0x01;
+                       /* XGINew_SetRegOR(pVBInfo->P3d4, 0x48, 0x20); *//* P. ON */
                }
-       } else {
-               XGI_LongWait(pVBInfo);
        }
-       return;
-}
 
-static unsigned short XGI_GetVGAHT2(struct vb_device_info *pVBInfo)
-{
-       unsigned long tempax, tempbx;
+       pVBInfo->SetFlag &= (~ProgrammingCRT2);
+       XGI_SetCRT1FIFO(ModeNo, HwDeviceExtension, pVBInfo);
+       XGI_SetCRT1ModeRegs(HwDeviceExtension, ModeNo, ModeIdIndex,
+                       RefreshRateTableIndex, pVBInfo);
 
-       tempbx = ((pVBInfo->VGAVT - pVBInfo->VGAVDE) * pVBInfo->RVBHCMAX)
-                       & 0xFFFF;
-       tempax = (pVBInfo->VT - pVBInfo->VDE) * pVBInfo->RVBHCFACT;
-       tempax = (tempax * pVBInfo->HT) / tempbx;
+       /* XGI_LoadCharacter(); //dif ifdef TVFont */
 
-       return (unsigned short) tempax;
+       XGI_LoadDAC(ModeNo, ModeIdIndex, pVBInfo);
+       /* XGI_ClearBuffer(HwDeviceExtension, ModeNo, pVBInfo); */
 }
 
-static unsigned short XGI_GetVCLK2Ptr(unsigned short ModeNo,
-               unsigned short ModeIdIndex,
-               unsigned short RefreshRateTableIndex,
-               struct xgi_hw_device_info *HwDeviceExtension,
-               struct vb_device_info *pVBInfo)
+unsigned char XGISetModeNew(struct xgi_hw_device_info *HwDeviceExtension,
+                       unsigned short ModeNo)
 {
-       unsigned short tempbx;
+       unsigned short ModeIdIndex;
+       /* unsigned char *pVBInfo->FBAddr = HwDeviceExtension->pjVideoMemoryAddress; */
+       struct vb_device_info VBINF;
+       struct vb_device_info *pVBInfo = &VBINF;
+       pVBInfo->ROMAddr = HwDeviceExtension->pjVirtualRomBase;
+       pVBInfo->BaseAddr = (unsigned long) HwDeviceExtension->pjIOAddress;
+       pVBInfo->IF_DEF_LVDS = 0;
+       pVBInfo->IF_DEF_CH7005 = 0;
+       pVBInfo->IF_DEF_LCDA = 1;
+       pVBInfo->IF_DEF_CH7017 = 0;
+       pVBInfo->IF_DEF_CH7007 = 0; /* [Billy] 2007/05/14 */
+       pVBInfo->IF_DEF_VideoCapture = 0;
+       pVBInfo->IF_DEF_ScaleLCD = 0;
+       pVBInfo->IF_DEF_OEMUtil = 0;
+       pVBInfo->IF_DEF_PWD = 0;
+
+       if (HwDeviceExtension->jChipType >= XG20) { /* kuku 2004/06/25 */
+               pVBInfo->IF_DEF_YPbPr = 0;
+               pVBInfo->IF_DEF_HiVision = 0;
+               pVBInfo->IF_DEF_CRT2Monitor = 0;
+               pVBInfo->VBType = 0; /*set VBType default 0*/
+       } else if (HwDeviceExtension->jChipType >= XG40) {
+               pVBInfo->IF_DEF_YPbPr = 1;
+               pVBInfo->IF_DEF_HiVision = 1;
+               pVBInfo->IF_DEF_CRT2Monitor = 1;
+       } else {
+               pVBInfo->IF_DEF_YPbPr = 1;
+               pVBInfo->IF_DEF_HiVision = 1;
+               pVBInfo->IF_DEF_CRT2Monitor = 0;
+       }
+
+       pVBInfo->P3c4 = pVBInfo->BaseAddr + 0x14;
+       pVBInfo->P3d4 = pVBInfo->BaseAddr + 0x24;
+       pVBInfo->P3c0 = pVBInfo->BaseAddr + 0x10;
+       pVBInfo->P3ce = pVBInfo->BaseAddr + 0x1e;
+       pVBInfo->P3c2 = pVBInfo->BaseAddr + 0x12;
+       pVBInfo->P3cc = pVBInfo->BaseAddr + 0x1C;
+       pVBInfo->P3ca = pVBInfo->BaseAddr + 0x1a;
+       pVBInfo->P3c6 = pVBInfo->BaseAddr + 0x16;
+       pVBInfo->P3c7 = pVBInfo->BaseAddr + 0x17;
+       pVBInfo->P3c8 = pVBInfo->BaseAddr + 0x18;
+       pVBInfo->P3c9 = pVBInfo->BaseAddr + 0x19;
+       pVBInfo->P3da = pVBInfo->BaseAddr + 0x2A;
+       pVBInfo->Part0Port = pVBInfo->BaseAddr + XGI_CRT2_PORT_00;
+       pVBInfo->Part1Port = pVBInfo->BaseAddr + XGI_CRT2_PORT_04;
+       pVBInfo->Part2Port = pVBInfo->BaseAddr + XGI_CRT2_PORT_10;
+       pVBInfo->Part3Port = pVBInfo->BaseAddr + XGI_CRT2_PORT_12;
+       pVBInfo->Part4Port = pVBInfo->BaseAddr + XGI_CRT2_PORT_14;
+       pVBInfo->Part5Port = pVBInfo->BaseAddr + XGI_CRT2_PORT_14 + 2;
 
-       unsigned short LCDXlat1VCLK[4] = { VCLK65 + 2, VCLK65 + 2, VCLK65 + 2,
-                       VCLK65 + 2 };
-       unsigned short LCDXlat2VCLK[4] = { VCLK108_2 + 5, VCLK108_2 + 5,
-                       VCLK108_2 + 5, VCLK108_2 + 5 };
-       unsigned short LVDSXlat1VCLK[4] = { VCLK40, VCLK40, VCLK40, VCLK40 };
-       unsigned short LVDSXlat2VCLK[4] = { VCLK65 + 2, VCLK65 + 2, VCLK65 + 2,
-                       VCLK65 + 2 };
-       unsigned short LVDSXlat3VCLK[4] = { VCLK65 + 2, VCLK65 + 2, VCLK65 + 2,
-                       VCLK65 + 2 };
+       if (HwDeviceExtension->jChipType == XG21) { /* for x86 Linux, XG21 LVDS */
+               if ((XGINew_GetReg1(pVBInfo->P3d4, 0x38) & 0xE0) == 0xC0)
+                       pVBInfo->IF_DEF_LVDS = 1;
+       }
+       if (HwDeviceExtension->jChipType == XG27) {
+               if ((XGINew_GetReg1(pVBInfo->P3d4, 0x38) & 0xE0) == 0xC0) {
+                       if (XGINew_GetReg1(pVBInfo->P3d4, 0x30) & 0x20)
+                               pVBInfo->IF_DEF_LVDS = 1;
+               }
+       }
 
-       unsigned short CRT2Index, VCLKIndex;
-       unsigned short modeflag, resinfo;
-       unsigned char *CHTVVCLKPtr = NULL;
+       if (HwDeviceExtension->jChipType < XG20) /* kuku 2004/06/25 */
+               XGI_GetVBType(pVBInfo);
 
-       if (ModeNo <= 0x13) {
-               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag; /* si+St_ResInfo */
-               resinfo = pVBInfo->SModeIDTable[ModeIdIndex].St_ResInfo;
-               CRT2Index = pVBInfo->SModeIDTable[ModeIdIndex].St_CRT2CRTC;
-       } else {
-               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag; /* si+Ext_ResInfo */
-               resinfo = pVBInfo->EModeIDTable[ModeIdIndex].Ext_RESINFO;
-               CRT2Index
-                               = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRT2CRTC;
+       InitTo330Pointer(HwDeviceExtension->jChipType, pVBInfo);
+       if (ModeNo & 0x80) {
+               ModeNo = ModeNo & 0x7F;
+               /* XGINew_flag_clearbuffer = 0; */
+       }
+       /* else {
+               XGINew_flag_clearbuffer = 1;
        }
+       */
+       XGINew_SetReg1(pVBInfo->P3c4, 0x05, 0x86);
 
-       if (pVBInfo->IF_DEF_LVDS == 0) {
-               CRT2Index = CRT2Index >> 6; /*  for LCD */
-               if (pVBInfo->VBInfo & (SetCRT2ToLCD | SetCRT2ToLCDA)) { /*301b*/
-                       if (pVBInfo->LCDResInfo != Panel1024x768)
-                               VCLKIndex = LCDXlat2VCLK[CRT2Index];
-                       else
-                               VCLKIndex = LCDXlat1VCLK[CRT2Index];
-               } else { /* for TV */
-                       if (pVBInfo->VBInfo & SetCRT2ToTV) {
-                               if (pVBInfo->VBInfo & SetCRT2ToHiVisionTV) {
-                                       if (pVBInfo->SetFlag & RPLLDIV2XO) {
-                                               VCLKIndex = HiTVVCLKDIV2;
+       if (HwDeviceExtension->jChipType < XG20) /* kuku 2004/06/25 1.Openkey */
+               XGI_UnLockCRT2(HwDeviceExtension, pVBInfo);
 
-                                               VCLKIndex += 25;
+       XGI_SearchModeID(ModeNo, &ModeIdIndex, pVBInfo);
 
-                                       } else {
-                                               VCLKIndex = HiTVVCLK;
+       XGI_GetVGAType(HwDeviceExtension, pVBInfo);
 
-                                               VCLKIndex += 25;
+       if (HwDeviceExtension->jChipType < XG20) { /* kuku 2004/06/25 */
+               XGI_GetVBInfo(ModeNo, ModeIdIndex, HwDeviceExtension, pVBInfo);
+               XGI_GetTVInfo(ModeNo, ModeIdIndex, pVBInfo);
+               XGI_GetLCDInfo(ModeNo, ModeIdIndex, pVBInfo);
+               XGI_DisableBridge(HwDeviceExtension, pVBInfo);
+               /* XGI_OpenCRTC(HwDeviceExtension, pVBInfo); */
 
-                                       }
+               if (pVBInfo->VBInfo & (SetSimuScanMode | SetCRT2ToLCDA)) {
+                       XGI_SetCRT1Group(HwDeviceExtension, ModeNo,
+                                       ModeIdIndex, pVBInfo);
 
-                                       if (pVBInfo->SetFlag & TVSimuMode) {
-                                               if (modeflag & Charx8Dot) {
-                                                       VCLKIndex
-                                                                       = HiTVSimuVCLK;
+                       if (pVBInfo->VBInfo & SetCRT2ToLCDA) {
+                               XGI_SetLCDAGroup(ModeNo, ModeIdIndex,
+                                               HwDeviceExtension, pVBInfo);
+                       }
+               } else {
+                       if (!(pVBInfo->VBInfo & SwitchToCRT2)) {
+                               XGI_SetCRT1Group(HwDeviceExtension, ModeNo,
+                                               ModeIdIndex, pVBInfo);
+                               if (pVBInfo->VBInfo & SetCRT2ToLCDA) {
+                                       XGI_SetLCDAGroup(ModeNo, ModeIdIndex,
+                                                       HwDeviceExtension,
+                                                       pVBInfo);
+                               }
+                       }
+               }
 
-                                                       VCLKIndex += 25;
+               if (pVBInfo->VBInfo & (SetSimuScanMode | SwitchToCRT2)) {
+                       switch (HwDeviceExtension->ujVBChipID) {
+                       case VB_CHIP_301:
+                               XGI_SetCRT2Group301(ModeNo, HwDeviceExtension,
+                                               pVBInfo); /*add for CRT2 */
+                               break;
 
-                                               } else {
-                                                       VCLKIndex
-                                                                       = HiTVTextVCLK;
+                       case VB_CHIP_302:
+                               XGI_SetCRT2Group301(ModeNo, HwDeviceExtension,
+                                               pVBInfo); /*add for CRT2 */
+                               break;
 
-                                                       VCLKIndex += 25;
+                       default:
+                               break;
+                       }
+               }
 
-                                               }
-                                       }
+               XGI_SetCRT2ModeRegs(ModeNo, HwDeviceExtension, pVBInfo);
+               XGI_OEM310Setting(ModeNo, ModeIdIndex, pVBInfo); /*0212*/
+               XGI_CloseCRTC(HwDeviceExtension, pVBInfo);
+               XGI_EnableBridge(HwDeviceExtension, pVBInfo);
+       } /* !XG20 */
+       else {
+               if (pVBInfo->IF_DEF_LVDS == 1)
+                       if (!XGI_XG21CheckLVDSMode(ModeNo, ModeIdIndex, pVBInfo))
+                               return 0;
 
-                                       if (pVBInfo->VBType & VB_XGI301LV) { /* 301lv */
-                                               if (!(pVBInfo->VBExtInfo
-                                                               == VB_YPbPr1080i)) {
-                                                       VCLKIndex
-                                                                       = YPbPr750pVCLK;
-                                                       if (!(pVBInfo->VBExtInfo
-                                                                       == VB_YPbPr750p)) {
-                                                               VCLKIndex
-                                                                               = YPbPr525pVCLK;
-                                                               if (!(pVBInfo->VBExtInfo
-                                                                               == VB_YPbPr525p)) {
-                                                                       VCLKIndex
-                                                                                       = YPbPr525iVCLK_2;
-                                                                       if (!(pVBInfo->SetFlag
-                                                                                       & RPLLDIV2XO))
-                                                                               VCLKIndex
-                                                                                               = YPbPr525iVCLK;
-                                                               }
-                                                       }
-                                               }
-                                       }
-                               } else {
-                                       if (pVBInfo->VBInfo & SetCRT2ToTV) {
-                                               if (pVBInfo->SetFlag
-                                                               & RPLLDIV2XO) {
-                                                       VCLKIndex = TVVCLKDIV2;
+               if (ModeNo <= 0x13) {
+                       pVBInfo->ModeType
+                                       = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag
+                                                       & ModeInfoFlag;
+               } else {
+                       pVBInfo->ModeType
+                                       = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag
+                                                       & ModeInfoFlag;
+               }
 
-                                                       VCLKIndex += 25;
+               pVBInfo->SetFlag = 0;
+               if (pVBInfo->IF_DEF_CH7007 != 1)
+                       pVBInfo->VBInfo = DisableCRT2Display;
 
-                                               } else {
-                                                       VCLKIndex = TVVCLK;
+               XGI_DisplayOff(HwDeviceExtension, pVBInfo);
 
-                                                       VCLKIndex += 25;
+               XGI_SetCRT1Group(HwDeviceExtension, ModeNo, ModeIdIndex,
+                               pVBInfo);
 
-                                               }
-                                       }
-                               }
-                       } else { /* for CRT2 */
-                               VCLKIndex = (unsigned char) XGINew_GetReg2(
-                                               (pVBInfo->P3ca + 0x02)); /* Port 3cch */
-                               VCLKIndex = ((VCLKIndex >> 2) & 0x03);
-                               if (ModeNo > 0x13) {
-                                       VCLKIndex
-                                                       = pVBInfo->RefIndex[RefreshRateTableIndex].Ext_CRTVCLK; /* di+Ext_CRTVCLK */
-                                       VCLKIndex &= IndexMask;
-                               }
-                       }
-               }
-       } else { /* LVDS */
-               if (ModeNo <= 0x13)
-                       VCLKIndex = CRT2Index;
-               else
-                       VCLKIndex = CRT2Index;
+               XGI_DisplayOn(HwDeviceExtension, pVBInfo);
+               /*
+               if (HwDeviceExtension->jChipType == XG21)
+                       XGINew_SetRegANDOR(pVBInfo->P3c4, 0x09, ~0x80, 0x80);
+               */
+       }
 
-               if (pVBInfo->IF_DEF_CH7005 == 1) {
-                       if (!(pVBInfo->VBInfo & SetCRT2ToLCD)) {
-                               VCLKIndex &= 0x1f;
-                               tempbx = 0;
+       /*
+       if (ModeNo <= 0x13) {
+               modeflag = pVBInfo->SModeIDTable[ModeIdIndex].St_ModeFlag;
+       } else {
+               modeflag = pVBInfo->EModeIDTable[ModeIdIndex].Ext_ModeFlag;
+       }
+       pVBInfo->ModeType = modeflag&ModeInfoFlag;
+       pVBInfo->SetFlag = 0x00;
+       pVBInfo->VBInfo = DisableCRT2Display;
+       temp = XGINew_CheckMemorySize(HwDeviceExtension, ModeNo, ModeIdIndex, pVBInfo);
 
-                               if (pVBInfo->VBInfo & SetPALTV)
-                                       tempbx += 2;
+       if (temp == 0)
+               return (0);
 
-                               if (pVBInfo->VBInfo & SetCHTVOverScan)
-                                       tempbx += 1;
+       XGI_DisplayOff(HwDeviceExtension, pVBInfo) ;
+       XGI_SetCRT1Group(HwDeviceExtension, ModeNo, ModeIdIndex, pVBInfo);
+       XGI_DisplayOn(HwDeviceExtension, pVBInfo);
+       */
 
-                               switch (tempbx) {
-                               case 0:
-                                       CHTVVCLKPtr = pVBInfo->CHTVVCLKUNTSC;
-                                       break;
-                               case 1:
-                                       CHTVVCLKPtr = pVBInfo->CHTVVCLKONTSC;
-                                       break;
-                               case 2:
-                                       CHTVVCLKPtr = pVBInfo->CHTVVCLKUPAL;
-                                       break;
-                               case 3:
-                                       CHTVVCLKPtr = pVBInfo->CHTVVCLKOPAL;
-                                       break;
-                               default:
-                                       break;
-                               }
+       XGI_UpdateModeInfo(HwDeviceExtension, pVBInfo);
 
-                               VCLKIndex = CHTVVCLKPtr[VCLKIndex];
-                       }
-               } else {
-                       VCLKIndex = VCLKIndex >> 6;
-                       if ((pVBInfo->LCDResInfo == Panel800x600)
-                                       || (pVBInfo->LCDResInfo == Panel320x480))
-                               VCLKIndex = LVDSXlat1VCLK[VCLKIndex];
-                       else if ((pVBInfo->LCDResInfo == Panel1024x768)
-                                       || (pVBInfo->LCDResInfo
-                                                       == Panel1024x768x75))
-                               VCLKIndex = LVDSXlat2VCLK[VCLKIndex];
-                       else
-                               VCLKIndex = LVDSXlat3VCLK[VCLKIndex];
-               }
+       if (HwDeviceExtension->jChipType < XG20) { /* kuku 2004/06/25 */
+               XGI_LockCRT2(HwDeviceExtension, pVBInfo);
        }
-       /* VCLKIndex = VCLKIndex&IndexMask; */
 
-       return VCLKIndex;
+       return 1;
 }
-