diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/CXA2104S.c linux-2.6.1-rc1-gentoo/drivers/media/video/CXA2104S.c
--- linux-2.6.0/drivers/media/video/CXA2104S.c	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/CXA2104S.c	2004-01-06 17:28:06.000000000 +0000
@@ -0,0 +1,194 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#include <asm/io.h>
+#include "via_types.h"
+#include "compose.h"
+
+#include "i2c.h"
+#include "CXA2104S.h" 
+
+
+int  AudioQuality=AUDIO_STEREO;
+
+Bool AUDIO_MUTE=TRUE;
+
+
+void  AUDIO_WI2C(int value1, int value2, int value3 )
+{
+     int ack;
+
+     i2c_start();
+     ack=i2c_sendbyte(value1,1 );
+     ack=i2c_sendbyte(value2,1 );
+     ack=i2c_sendbyte(value3,1 );
+     i2c_stop();
+
+}
+
+
+int  AUDIO_RI2C(unsigned Sub_Addr)
+{
+    int ReadData =0,ack;
+
+    i2c_start();
+    ack=i2c_sendbyte(CXA2104S_SlaveWrite,1 );
+    ack=i2c_sendbyte(Sub_Addr,1 );
+    i2c_stop();
+
+
+    i2c_start();
+    ack=i2c_sendbyte(CXA2104S_SlaveRead,1);
+    ReadData=i2c_readbyte(1);
+    i2c_stop();
+    return(ReadData);
+
+}
+
+
+void AUDIO_INIT_REG()
+{
+      AUDIO_WI2C(CXA2104S_SlaveWrite,REG0,0x01);
+      AUDIO_WI2C(CXA2104S_SlaveWrite,REG1,0x1f);
+      AUDIO_WI2C(CXA2104S_SlaveWrite,REG2,0x1f);
+      AUDIO_WI2C(CXA2104S_SlaveWrite,REG3,0x00);  //stereo mute
+      AUDIO_WI2C(CXA2104S_SlaveWrite,REG4,0x00); 
+      
+      AUDIO_MUTE = TRUE;
+}
+
+
+void AUDIO_SELECT_STEREO()
+{
+      AudioQuality=AUDIO_STEREO;
+      
+      AUDIO_WI2C(CXA2104S_SlaveWrite,REG0,0x01);
+      AUDIO_WI2C(CXA2104S_SlaveWrite,REG1,0x1f);
+      AUDIO_WI2C(CXA2104S_SlaveWrite,REG2,0x1f);
+      AUDIO_WI2C(CXA2104S_SlaveWrite,REG3,0x01); 
+      AUDIO_WI2C(CXA2104S_SlaveWrite,REG4,0x00); 
+      
+      AUDIO_MUTE = FALSE;
+}
+
+
+void AUDIO_SELECT_SAP()
+{
+      AudioQuality=AUDIO_SAP;
+
+      AUDIO_WI2C(CXA2104S_SlaveWrite,REG0,0x0f);
+      AUDIO_WI2C(CXA2104S_SlaveWrite,REG1,0x1f);
+      AUDIO_WI2C(CXA2104S_SlaveWrite,REG2,0x1f);
+      AUDIO_WI2C(CXA2104S_SlaveWrite,REG3,0x0b); 
+      AUDIO_WI2C(CXA2104S_SlaveWrite,REG4,0x20); 
+      
+      AUDIO_MUTE = FALSE;
+}
+
+
+void AUDIO_SELECT_DUAL()
+{
+      AudioQuality=AUDIO_DUAL;
+      
+      AUDIO_WI2C(CXA2104S_SlaveWrite,REG0,0x08);
+      AUDIO_WI2C(CXA2104S_SlaveWrite,REG1,0x1f);
+      AUDIO_WI2C(CXA2104S_SlaveWrite,REG2,0x1f);
+      AUDIO_WI2C(CXA2104S_SlaveWrite,REG3,0x0f); 
+      AUDIO_WI2C(CXA2104S_SlaveWrite,REG4,0x20); 
+      
+      AUDIO_MUTE = FALSE;
+}
+
+
+void AUDIO_MUTE_ON()
+{
+    switch(AudioQuality)
+    {
+        case AUDIO_STEREO:
+             AUDIO_WI2C(CXA2104S_SlaveWrite,REG3,0x00);
+             break;
+        case AUDIO_SAP:              
+             AUDIO_WI2C(CXA2104S_SlaveWrite,REG3,0x0a);
+             break;
+        case AUDIO_DUAL:              
+             AUDIO_WI2C(CXA2104S_SlaveWrite,REG3,0x0e);
+             break;
+    }                                         
+    
+    AUDIO_MUTE = TRUE;
+    
+}
+
+
+void AUDIO_MUTE_OFF()
+{
+
+    switch(AudioQuality)
+    {
+        case AUDIO_STEREO:
+             AUDIO_WI2C(CXA2104S_SlaveWrite,REG3,0x01);
+             break;
+        case AUDIO_SAP:              
+             AUDIO_WI2C(CXA2104S_SlaveWrite,REG3,0x0b);
+             break;
+        case AUDIO_DUAL:              
+             AUDIO_WI2C(CXA2104S_SlaveWrite,REG3,0x0f);
+             break;
+    }                
+    
+    AUDIO_MUTE = FALSE;                         
+
+}
+
+
+#define AUDIO_GPIO1_ENABLE        0x80
+#define AUDIO_GPIO1_SELECT_TUNER1 0x20
+
+void AUDIO_TUNER_SWITCH(int value)
+{
+    int Reg3C4 = 0x3c4;
+    int Index3C4 = 0x50;
+    int Reg3C5 = 0x3c5;
+    int tempData, OldIndex3C4;
+
+    // save 3c4H
+    OldIndex3C4 = inb(Reg3C4);
+
+    outb(Index3C4,Reg3C4);
+    tempData = inb(Reg3C5);
+    if ( value ) /* SELECT TUNER 1 AUDIO */
+    {
+      tempData |= ( AUDIO_GPIO1_ENABLE | AUDIO_GPIO1_SELECT_TUNER1 );
+      outb(tempData,Reg3C5);
+    }
+    else         /* SELECT TUNER 0 AUDIO */
+    {
+      tempData &= (~AUDIO_GPIO1_SELECT_TUNER1 );
+      tempData |=   AUDIO_GPIO1_ENABLE;
+      outb(tempData,Reg3C5);
+    }
+
+    // restore 3c4H
+    outb(OldIndex3C4,Reg3C4);
+}
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/CXA2104S.h linux-2.6.1-rc1-gentoo/drivers/media/video/CXA2104S.h
--- linux-2.6.0/drivers/media/video/CXA2104S.h	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/CXA2104S.h	2004-01-06 17:28:06.000000000 +0000
@@ -0,0 +1,59 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#ifndef __CXA2104S_H
+#define __CXA2104S_H
+/*  Slave Address  */
+#define   CXA2104S_SlaveWrite   0x84
+#define   CXA2104S_SlaveRead    0x85
+
+/* Registers Sub-Address */
+
+#define REG0    0x00
+#define REG1    0x01
+#define REG2    0x02
+#define REG3    0x03
+#define REG4    0x04
+#define REG5    0x05
+
+/* control registers initial table */
+
+#define INIT_REG0       0x09
+#define INIT_REG1       0x1f
+#define INIT_REG2       0x1f
+#define INIT_REG3       0x03
+#define INIT_REG4       0x2c  /* force stereo mode */ 
+
+
+
+void AUDIO_INIT_REG(void);
+void AUDIO_SELECT_STEREO(void);
+void AUDIO_SELECT_SAP(void);
+void AUDIO_MUTE_ON(void);
+void AUDIO_MUTE_OFF(void);
+void AUDIO_TUNER_SWITCH(int);
+int  AUDIO_RI2C(unsigned Sub_Addr);
+void AUDIO_SELECT_DUAL(void);
+
+#endif  //End of __CXA2104S_H
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/HWDiff.c linux-2.6.1-rc1-gentoo/drivers/media/video/HWDiff.c
--- linux-2.6.0/drivers/media/video/HWDiff.c	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/HWDiff.c	2004-01-06 17:28:06.000000000 +0000
@@ -0,0 +1,162 @@
+/*************************************************************************
+ *
+ *   HWDiff.c 
+ *
+ *   Implement all Video Function for the Driver 
+ *
+ *   DATE     04/07/2003
+ *
+ *************************************************************************/
+
+#include "via_v4l.h" 
+#include "HWDiff.h"
+//#include "debug.h"
+
+#include "via_privIoctl.h"           /* for VIAGRAPHICINFO & custom ioctl command */
+
+
+/**************************************************************************
+//Global Variable for Video function
+**************************************************************************/
+VIDHWDIFFERENCE VideoHWDifference;
+
+/**************************************************************************
+//Extern Variable for Video function
+**************************************************************************/
+extern VIAGRAPHICINFO gVIAGraphicInfo;  /* 2D information */
+
+/**************************************************************************
+//Extern function for Video function
+**************************************************************************/
+
+
+/**************************************************************************
+//Defination for Video function
+************************************************************************/
+
+
+/**************************************************************************
+//Structure defination for Video function
+**************************************************************************/
+
+
+/**************************************************************************
+//function defination for Video Driver
+**************************************************************************/
+
+
+/**************************************************************************
+//function implement for Video Driver
+**************************************************************************/
+void vfInitHWDiff(void)
+{
+    LPVIDHWDIFFERENCE lpVideoHWDifference = &VideoHWDifference;
+    
+    switch( gVIAGraphicInfo.dwDeviceID )
+    {
+        case VIA_DEVICE_VT3204:
+             //HW Difference Flag
+             lpVideoHWDifference->dwThreeHQVBuffer = VID_HWDIFF_TRUE;
+             lpVideoHWDifference->dwV3SrcHeightSetting = VID_HWDIFF_TRUE;
+             lpVideoHWDifference->dwSupportExtendFIFO = VID_HWDIFF_FALSE;
+             lpVideoHWDifference->dwHQVFetchByteUnit = VID_HWDIFF_TRUE;
+             lpVideoHWDifference->dwHQVInitPatch = VID_HWDIFF_FALSE;
+             lpVideoHWDifference->dwSupportV3Gamma=VID_HWDIFF_TRUE;
+             lpVideoHWDifference->dwUpdFlip = VID_HWDIFF_TRUE;
+             lpVideoHWDifference->dwHQVDisablePatch = VID_HWDIFF_TRUE;
+             lpVideoHWDifference->dwSUBFlip = VID_HWDIFF_TRUE;
+             lpVideoHWDifference->dwNeedV3Prefetch = VID_HWDIFF_TRUE;
+             lpVideoHWDifference->dwNeedV4Prefetch = VID_HWDIFF_TRUE;
+             lpVideoHWDifference->dwUseSystemMemory = VID_HWDIFF_TRUE;//VID_HWDIFF_FALSE; Scottie[2003.5.23] for performance tuning
+             lpVideoHWDifference->dwExpandVerPatch = VID_HWDIFF_TRUE;
+             lpVideoHWDifference->dwExpandVerHorPatch = VID_HWDIFF_FALSE;
+             lpVideoHWDifference->dwV3ExpireNumTune = VID_HWDIFF_TRUE;
+             lpVideoHWDifference->dwV3FIFOThresholdTune = VID_HWDIFF_TRUE;
+             lpVideoHWDifference->dwCheckHQVFIFOEmpty = VID_HWDIFF_TRUE;
+             lpVideoHWDifference->dwUseMPEGAGP = VID_HWDIFF_FALSE;//VID_HWDIFF_TRUE; Scottie[2003.4.28] for FPGA PCI test
+             lpVideoHWDifference->dwV3FIFOPatch = VID_HWDIFF_FALSE;
+             lpVideoHWDifference->dwSupportTwoColorKey = VID_HWDIFF_FALSE; 
+             break;
+       
+        case VIA_DEVICE_VT3205:
+             //HW Difference Flag
+             lpVideoHWDifference->dwThreeHQVBuffer = VID_HWDIFF_TRUE;
+             lpVideoHWDifference->dwV3SrcHeightSetting = VID_HWDIFF_TRUE;
+             lpVideoHWDifference->dwSupportExtendFIFO = VID_HWDIFF_FALSE;
+             lpVideoHWDifference->dwHQVFetchByteUnit = VID_HWDIFF_TRUE;
+             lpVideoHWDifference->dwHQVInitPatch = VID_HWDIFF_FALSE;
+             lpVideoHWDifference->dwSupportV3Gamma=VID_HWDIFF_FALSE;
+             lpVideoHWDifference->dwUpdFlip = VID_HWDIFF_TRUE;
+             lpVideoHWDifference->dwHQVDisablePatch = VID_HWDIFF_TRUE;
+             lpVideoHWDifference->dwSUBFlip = VID_HWDIFF_TRUE;
+             lpVideoHWDifference->dwNeedV3Prefetch = VID_HWDIFF_FALSE;
+             lpVideoHWDifference->dwNeedV4Prefetch = VID_HWDIFF_FALSE;
+             lpVideoHWDifference->dwUseSystemMemory = VID_HWDIFF_TRUE;
+             lpVideoHWDifference->dwExpandVerPatch = VID_HWDIFF_TRUE;
+             lpVideoHWDifference->dwExpandVerHorPatch = VID_HWDIFF_TRUE;
+             lpVideoHWDifference->dwV3ExpireNumTune = VID_HWDIFF_TRUE;
+             lpVideoHWDifference->dwV3FIFOThresholdTune = VID_HWDIFF_TRUE;
+             lpVideoHWDifference->dwCheckHQVFIFOEmpty = VID_HWDIFF_FALSE;
+             lpVideoHWDifference->dwUseMPEGAGP = VID_HWDIFF_TRUE;
+             lpVideoHWDifference->dwV3FIFOPatch = VID_HWDIFF_FALSE;
+             lpVideoHWDifference->dwSupportTwoColorKey = VID_HWDIFF_FALSE;
+             break;
+             
+        case VIA_DEVICE_CLE1:
+        case VIA_DEVICE_CLE2:
+            switch ( gVIAGraphicInfo.RevisionID )
+             {
+                case VIA_REVISION_CLEC0:
+                case VIA_REVISION_CLEC1:
+                     //HW Difference Flag
+                     lpVideoHWDifference->dwThreeHQVBuffer = VID_HWDIFF_TRUE;
+                     lpVideoHWDifference->dwV3SrcHeightSetting = VID_HWDIFF_TRUE;
+                     lpVideoHWDifference->dwSupportExtendFIFO = VID_HWDIFF_FALSE;
+                     lpVideoHWDifference->dwHQVFetchByteUnit = VID_HWDIFF_TRUE;
+                     lpVideoHWDifference->dwHQVInitPatch = VID_HWDIFF_FALSE;
+                     lpVideoHWDifference->dwSupportV3Gamma=VID_HWDIFF_FALSE;
+                     lpVideoHWDifference->dwUpdFlip = VID_HWDIFF_TRUE;
+                     lpVideoHWDifference->dwHQVDisablePatch = VID_HWDIFF_TRUE;
+                     lpVideoHWDifference->dwSUBFlip = VID_HWDIFF_TRUE;
+                     lpVideoHWDifference->dwNeedV3Prefetch = VID_HWDIFF_FALSE;
+                     lpVideoHWDifference->dwNeedV4Prefetch = VID_HWDIFF_FALSE;
+                     lpVideoHWDifference->dwUseSystemMemory = VID_HWDIFF_FALSE;
+                     lpVideoHWDifference->dwExpandVerPatch = VID_HWDIFF_TRUE;
+                     lpVideoHWDifference->dwExpandVerHorPatch = VID_HWDIFF_TRUE;
+                     lpVideoHWDifference->dwV3ExpireNumTune = VID_HWDIFF_FALSE;
+                     lpVideoHWDifference->dwV3FIFOThresholdTune = VID_HWDIFF_FALSE;
+                     lpVideoHWDifference->dwCheckHQVFIFOEmpty = VID_HWDIFF_TRUE;
+                     lpVideoHWDifference->dwUseMPEGAGP = VID_HWDIFF_FALSE;
+                     lpVideoHWDifference->dwV3FIFOPatch = VID_HWDIFF_TRUE;
+                     lpVideoHWDifference->dwSupportTwoColorKey = VID_HWDIFF_TRUE;
+                     break;
+                default:
+                     //HW Difference Flag
+                     lpVideoHWDifference->dwThreeHQVBuffer = VID_HWDIFF_FALSE;
+                     lpVideoHWDifference->dwV3SrcHeightSetting = VID_HWDIFF_FALSE;
+                     lpVideoHWDifference->dwSupportExtendFIFO = VID_HWDIFF_TRUE;
+                     lpVideoHWDifference->dwHQVFetchByteUnit = VID_HWDIFF_FALSE;
+                     lpVideoHWDifference->dwHQVInitPatch = VID_HWDIFF_TRUE;
+                     lpVideoHWDifference->dwSupportV3Gamma=VID_HWDIFF_FALSE;
+                     lpVideoHWDifference->dwUpdFlip = VID_HWDIFF_FALSE;
+                     lpVideoHWDifference->dwHQVDisablePatch = VID_HWDIFF_FALSE;
+                     lpVideoHWDifference->dwSUBFlip = VID_HWDIFF_FALSE;
+                     lpVideoHWDifference->dwNeedV3Prefetch = VID_HWDIFF_FALSE;
+                     lpVideoHWDifference->dwNeedV4Prefetch = VID_HWDIFF_FALSE;
+                     lpVideoHWDifference->dwUseSystemMemory = VID_HWDIFF_FALSE;
+                     lpVideoHWDifference->dwExpandVerPatch = VID_HWDIFF_TRUE;
+                     lpVideoHWDifference->dwExpandVerHorPatch = VID_HWDIFF_TRUE;
+                     lpVideoHWDifference->dwV3ExpireNumTune = VID_HWDIFF_FALSE;
+                     lpVideoHWDifference->dwV3FIFOThresholdTune = VID_HWDIFF_FALSE;
+                     lpVideoHWDifference->dwCheckHQVFIFOEmpty = VID_HWDIFF_FALSE;
+                     lpVideoHWDifference->dwUseMPEGAGP = VID_HWDIFF_FALSE;
+                     lpVideoHWDifference->dwV3FIFOPatch = VID_HWDIFF_TRUE;
+                     lpVideoHWDifference->dwSupportTwoColorKey = VID_HWDIFF_FALSE;
+                     break;
+            }/*End of CLE RevisionID*/
+            break;
+        default:
+            /*Unkown DeviceID*/
+            break;             
+    }/* End of dwDeviceID*/
+}     
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/HWDiff.h linux-2.6.1-rc1-gentoo/drivers/media/video/HWDiff.h
--- linux-2.6.0/drivers/media/video/HWDiff.h	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/HWDiff.h	2004-01-06 17:28:06.000000000 +0000
@@ -0,0 +1,89 @@
+/******************************Module*Header*******************************
+* Module Name: HWDiff.h
+*
+* Put all video function and parameters.
+*
+* Copyright (c) 2003 VIA Technologies, Inc.  All rights reserved.
+**************************************************************************/
+
+#ifndef _VIDEOFUN_H
+#define _VIDEOFUN_H
+
+/**************************************************************************
+//Global Variable for Video function
+**************************************************************************/
+
+
+/**************************************************************************
+//Extern Variable for Video function
+**************************************************************************/
+
+
+/**************************************************************************
+//Extern function for Video function
+**************************************************************************/
+
+
+/**************************************************************************
+//Defination for Video HW Difference 
+**************************************************************************/
+/*For Video HW Difference */
+
+/* Device ID Definition */
+#define VIA_DEVICE_CLE1             0x3022
+#define VIA_DEVICE_CLE2             0x3122
+#define VIA_DEVICE_VT3205           0x7205
+#define VIA_DEVICE_VT3204_A0        0x7204
+#define VIA_DEVICE_VT3204           0x3108
+#define VIA_DEVICE_VT3209           0x7259
+#define VIA_DEVICE_VT3259           0x3118
+#define VIA_DEVICE_VT3264           0x3224
+
+/* Revision ID Definition */
+#define VIA_REVISION_CLEC0        0x10
+#define VIA_REVISION_CLEC1        0x11
+#define VIA_REVISION_CLECX        0x10
+
+#define VID_HWDIFF_TRUE           0x00000001
+#define VID_HWDIFF_FALSE          0x00000000
+
+/**************************************************************************
+//Structure defination for Video function
+**************************************************************************/
+/*Video HW Difference Structure*/
+typedef struct _VIDHWDIFFERENCE
+{
+    unsigned long dwThreeHQVBuffer;			/*Use Three HQV Buffers*/
+    unsigned long dwV3SrcHeightSetting;			/*Set Video Source Width and Height*/
+    unsigned long dwSupportExtendFIFO;			/*Support Extand FIFO*/
+    unsigned long dwHQVFetchByteUnit;			/*HQV Fetch Count unit is byte*/
+    unsigned long dwHQVInitPatch;			/*Initialize HQV Engine 2 times*/
+    unsigned long dwSupportV3Gamma;             /*Support V3 Gamma*/ 
+    unsigned long dwUpdFlip;				/*Set HQV3D0[15] to flip video*/
+    unsigned long dwHQVDisablePatch;			/*Change Video Engine Clock setting for HQV disable bug*/
+    unsigned long dwSUBFlip;				/*Set HQV3D0[15] to flip video for sub-picture blending*/
+    unsigned long dwNeedV3Prefetch;			/*V3 pre-fetch function for K8*/
+    unsigned long dwNeedV4Prefetch;			/*V4 pre-fetch function for K8*/
+    unsigned long dwUseSystemMemory;			/*Use system memory for DXVA compressed data buffers*/
+    unsigned long dwExpandVerPatch;			/*Patch video HW bug in expand SIM mode or same display path*/
+    unsigned long dwExpandVerHorPatch;			/*Patch video HW bug in expand SAMM mode or same display path*/
+    unsigned long dwV3ExpireNumTune;			/*Change V3 expire number setting for V3 bandwidth issue*/
+    unsigned long dwV3FIFOThresholdTune;		/*Change V3 FIFO, Threshold and Pre-threshold setting for V3 bandwidth issue*/
+    unsigned long dwCheckHQVFIFOEmpty;          /*HW Flip path, need to check HQV FIFO status*/
+    unsigned long dwUseMPEGAGP;                         /*Use MPEG AGP function*/
+    unsigned long dwV3FIFOPatch;                        /*For CLE V3 FIFO Bug (srcWidth <= 8)*/
+    unsigned long dwSupportTwoColorKey;                 /*Support two color key*/
+}VIDHWDIFFERENCE, * LPVIDHWDIFFERENCE;
+
+
+/*Wait Function Structure and Flag*/
+typedef struct _WaitHWINFO
+{
+    unsigned char* pjVideo;				/*MMIO Address Info*/
+    unsigned long dwVideoFlag;				/*Video Flag*/
+}WaitHWINFO, * LPWaitHWINFO;
+
+
+
+#endif    
+
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/Kconfig linux-2.6.1-rc1-gentoo/drivers/media/video/Kconfig
--- linux-2.6.0/drivers/media/video/Kconfig	2003-12-18 02:59:39.000000000 +0000
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/Kconfig	2004-01-06 14:51:23.000000000 +0000
@@ -274,5 +274,9 @@
 	  To compile this driver as a module, choose M here: the
 	  module will be called hexium_gemini.
 
+config VIDEO_CLE266
+	tristate "CLE266 Support"
+	depends on VIDEO_DEV && DRM_VIA
+
 endmenu
 
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/Kconfig.via linux-2.6.1-rc1-gentoo/drivers/media/video/Kconfig.via
--- linux-2.6.0/drivers/media/video/Kconfig.via	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/Kconfig.via	2004-01-06 14:24:50.000000000 +0000
@@ -0,0 +1,278 @@
+#
+# Multimedia Video device configuration
+#
+
+menu "Video For Linux"
+	depends on VIDEO_DEV
+
+comment "Video Adapters"
+
+config VIDEO_BT848
+	tristate "BT848 Video For Linux"
+	depends on VIDEO_DEV && PCI && I2C_ALGOBIT && SOUND
+	---help---
+	  Support for BT848 based frame grabber/overlay boards. This includes
+	  the Miro, Hauppauge and STB boards. Please read the material in
+	  <file:Documentation/video4linux/bttv> for more information.
+
+	  If you say Y or M here, you need to say Y or M to "I2C support" and
+	  "I2C bit-banging interfaces" in the character device section.
+
+	  To compile this driver as a module, choose M here: the
+	  module will be called bttv.
+
+config VIDEO_PMS
+	tristate "Mediavision Pro Movie Studio Video For Linux"
+	depends on VIDEO_DEV && ISA
+	help
+	  Say Y if you have such a thing.
+
+	  To compile this driver as a module, choose M here: the
+	  module will be called pms.
+
+config VIDEO_PLANB
+	tristate "PlanB Video-In on PowerMac"
+	depends on PPC_PMAC && VIDEO_DEV
+	help
+	  PlanB is the V4L driver for the PowerMac 7x00/8x00 series video
+	  input hardware. If you want to experiment with this, say Y.
+	  Otherwise, or if you don't understand a word, say N.
+	  See <http://www.cpu.lu/~mlan/planb.html> for more info.
+
+	  Saying M will compile this driver as a module (planb).
+
+config VIDEO_BWQCAM
+	tristate "Quickcam BW Video For Linux"
+	depends on VIDEO_DEV && PARPORT
+	help
+	  Say Y have if you the black and white version of the QuickCam
+	  camera. See the next option for the color version.
+
+	  To compile this driver as a module, choose M here: the
+	  module will be called bw-qcam.
+
+config VIDEO_CQCAM
+	tristate "QuickCam Colour Video For Linux (EXPERIMENTAL)"
+	depends on EXPERIMENTAL && VIDEO_DEV && PARPORT
+	help
+	  This is the video4linux driver for the colour version of the
+	  Connectix QuickCam.  If you have one of these cameras, say Y here,
+	  otherwise say N.  This driver does not work with the original
+	  monochrome QuickCam, QuickCam VC or QuickClip.  It is also available
+	  as a module (c-qcam).
+	  Read <file:Documentation/video4linux/CQcam.txt> for more information.
+
+config VIDEO_W9966
+	tristate "W9966CF Webcam (FlyCam Supra and others) Video For Linux"
+	depends on PARPORT_1284 && VIDEO_DEV && PARPORT
+	help
+	  Video4linux driver for Winbond's w9966 based Webcams.
+	  Currently tested with the LifeView FlyCam Supra.
+	  If you have one of these cameras, say Y here
+	  otherwise say N.
+	  This driver is also available as a module (w9966).
+
+	  Check out <file:Documentation/video4linux/w9966.txt> for more
+	  information.
+
+config VIDEO_CPIA
+	tristate "CPiA Video For Linux"
+	depends on VIDEO_DEV
+	---help---
+	  This is the video4linux driver for cameras based on Vision's CPiA
+	  (Colour Processor Interface ASIC), such as the Creative Labs Video
+	  Blaster Webcam II. If you have one of these cameras, say Y here
+	  and select parallel port and/or USB lowlevel support below,
+	  otherwise say N. This will not work with the Creative Webcam III.
+
+	  Please read <file:Documentation/video4linux/README.cpia> for more
+	  information.
+
+	  This driver is also available as a module (cpia).
+
+config VIDEO_CPIA_PP
+	tristate "CPiA Parallel Port Lowlevel Support"
+	depends on PARPORT_1284 && VIDEO_CPIA && PARPORT
+	help
+	  This is the lowlevel parallel port support for cameras based on
+	  Vision's CPiA (Colour Processor Interface ASIC), such as the
+	  Creative Webcam II. If you have the parallel port version of one
+	  of these cameras, say Y here, otherwise say N. It is also available
+	  as a module (cpia_pp).
+
+config VIDEO_CPIA_USB
+	tristate "CPiA USB Lowlevel Support"
+	depends on VIDEO_CPIA && USB
+	help
+	  This is the lowlevel USB support for cameras based on Vision's CPiA
+	  (Colour Processor Interface ASIC), such as the Creative Webcam II.
+	  If you have the USB version of one of these cameras, say Y here,
+	  otherwise say N. This will not work with the Creative Webcam III.
+	  It is also available as a module (cpia_usb).
+
+config VIDEO_SAA5249
+	tristate "SAA5249 Teletext processor"
+	depends on VIDEO_DEV && I2C
+	help
+	  Support for I2C bus based teletext using the SAA5249 chip. At the
+	  moment this is only useful on some European WinTV cards.
+
+	  To compile this driver as a module, choose M here: the
+	  module will be called saa5249.
+
+config TUNER_3036
+	tristate "SAB3036 tuner"
+	depends on VIDEO_DEV && I2C
+	help
+	  Say Y here to include support for Philips SAB3036 compatible tuners.
+	  If in doubt, say N.
+
+config VIDEO_VINO
+	tristate "SGI Vino Video For Linux (EXPERIMENTAL)"
+	depends on EXPERIMENTAL && VIDEO_DEV && SGI
+	help
+	  Say Y here to build in support for the Vino video input system found
+	  on SGI Indy machines.
+
+config VIDEO_STRADIS
+	tristate "Stradis 4:2:2 MPEG-2 video driver  (EXPERIMENTAL)"
+	depends on EXPERIMENTAL && VIDEO_DEV && PCI
+	help
+	  Say Y here to enable support for the Stradis 4:2:2 MPEG-2 video
+	  driver for PCI.  There is a product page at
+	  <http://www.stradis.com/decoder.html>.
+
+config VIDEO_ZORAN
+	tristate "Zoran ZR36057/36067 Video For Linux"
+	depends on VIDEO_DEV && PCI && I2C
+	help
+	  Say Y for support for MJPEG capture cards based on the Zoran
+	  36057/36067 PCI controller chipset. This includes the Iomega
+	  Buz, Pinnacle DC10+ and the Linux Media Labs LML33. There is
+	  a driver homepage at <http://mjpeg.sf.net/driver-zoran/>. For
+	  more information, check <file:Documentation/video4linux/Zoran>.
+
+	  To compile this driver as a module, choose M here: the
+	  module will be called zr36067.
+ 
+config VIDEO_ZORAN_BUZ
+	tristate "Iomega Buz support"
+	depends on VIDEO_ZORAN
+	help
+	  Support for the Iomega Buz MJPEG capture/playback card.
+
+config VIDEO_ZORAN_DC10
+	tristate "Pinnacle/Miro DC10(+) support"
+	depends on VIDEO_ZORAN
+	help
+	  Support for the Pinnacle/Miro DC10(+) MJPEG capture/playback
+	  card.
+
+config VIDEO_ZORAN_DC30
+	tristate "Pinnacle/Miro DC30(+) support"
+ 	depends on VIDEO_ZORAN
+ 	help
+	  Support for the Pinnacle/Miro DC30(+) MJPEG capture/playback
+	  card. This also supports really old DC10 cards based on the
+	  zr36050 MJPEG codec and zr36016 VFE.
+
+config VIDEO_ZORAN_LML33
+	tristate "Linux Media Labs LML33 support"
+	depends on VIDEO_ZORAN
+	help
+	  Support for the Linux Media Labs LML33 MJPEG capture/playback
+	  card.
+
+config VIDEO_ZORAN_LML33R10
+	tristate "Linux Media Labs LML33R10 support"
+	depends on VIDEO_ZORAN
+	help
+	  support for the Linux Media Labs LML33R10 MJPEG capture/playback
+	  card.
+
+config VIDEO_ZR36120
+	tristate "Zoran ZR36120/36125 Video For Linux"
+	depends on VIDEO_DEV && PCI && I2C && BROKEN
+	help
+	  Support for ZR36120/ZR36125 based frame grabber/overlay boards.
+	  This includes the Victor II, WaveWatcher, Video Wonder, Maxi-TV,
+	  and Buster boards. Please read the material in
+	  <file:Documentation/video4linux/zr36120.txt> for more information.
+
+	  To compile this driver as a module, choose M here: the
+	  module will be called zr36120.
+
+config VIDEO_MEYE
+	tristate "Sony Vaio Picturebook Motion Eye Video For Linux (EXPERIMENTAL)"
+	depends on VIDEO_DEV && SONYPI
+	---help---
+	  This is the video4linux driver for the Motion Eye camera found
+	  in the Vaio Picturebook laptops. Please read the material in
+	  <file:Documentation/video4linux/meye.txt> for more information.
+
+	  If you say Y or M here, you need to say Y or M to "Sony Programmable
+	  I/O Control Device" in the character device section.
+
+	  To compile this driver as a module, choose M here: the
+	  module will be called meye.
+
+config VIDEO_SAA7134
+	tristate "Philips SAA7134 support"
+	depends on VIDEO_DEV && PCI && I2C
+	---help---
+	  This is a video4linux driver for Philips SAA7130/7134 based
+	  TV cards.
+
+	  To compile this driver as a module, choose M here: the
+	  module will be called saa7134.
+
+config VIDEO_MXB
+	tristate "Siemens-Nixdorf 'Multimedia eXtension Board'"
+	depends on VIDEO_DEV && PCI
+	select VIDEO_SAA7146_VV
+	---help---
+	  This is a video4linux driver for the 'Multimedia eXtension Board'
+	  TV card by Siemens-Nixdorf.
+	  
+	  To compile this driver as a module, choose M here: the
+	  module will be called mxb.
+
+config VIDEO_DPC
+	tristate "Philips-Semiconductors 'dpc7146 demonstration board'"
+	depends on VIDEO_DEV && PCI
+	select VIDEO_SAA7146_VV
+	---help---
+	  This is a video4linux driver for the 'dpc7146 demonstration
+	  board' by Philips-Semiconductors. It's the reference design
+	  for SAA7146 bases boards, so if you have some unsupported
+	  saa7146 based, analog video card, chances are good that it
+	  will work with this skeleton driver.
+	  
+	  To compile this driver as a module, choose M here: the
+	  module will be called dpc7146.
+
+config VIDEO_HEXIUM_ORION
+	tristate "Hexium HV-PCI6 and Orion frame grabber"
+	depends on VIDEO_DEV && PCI
+	select VIDEO_SAA7146_VV
+	---help---
+	  This is a video4linux driver for the Hexium HV-PCI6 and
+	  Orion frame grabber cards by Hexium.
+	  
+	  To compile this driver as a module, choose M here: the
+	  module will be called hexium_orion.
+
+config VIDEO_HEXIUM_GEMINI
+	tristate "Hexium Gemini frame grabber"
+	depends on VIDEO_DEV && PCI
+	select VIDEO_SAA7146_VV
+	---help---
+	  This is a video4linux driver for the Hexium Gemini frame
+	  grabber card by Hexium. Please note that the Gemini Dual
+	  card is *not* fully supported.
+	  
+	  To compile this driver as a module, choose M here: the
+	  module will be called hexium_gemini.
+
+endmenu
+
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/Makefile linux-2.6.1-rc1-gentoo/drivers/media/video/Makefile
--- linux-2.6.0/drivers/media/video/Makefile	2003-12-18 02:58:40.000000000 +0000
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/Makefile	2004-01-06 14:51:23.000000000 +0000
@@ -7,6 +7,9 @@
 zoran-objs      :=	zr36120.o zr36120_i2c.o zr36120_mem.o
 zr36067-objs	:=	zoran_procfs.o zoran_device.o \
 			zoran_driver.o zoran_card.o
+via_v4l_drv-objs     :=      via_v4l.o via_memmgr.o vdec.o i2c.o ddmpeg.o capture.o regrec.o\
+			audio.o CXA2104S.o via_tuner.o ddover.o HWDiff.o
+
 
 obj-$(CONFIG_VIDEO_DEV) += videodev.o v4l2-common.o v4l1-compat.o
 
@@ -44,3 +47,4 @@
 obj-$(CONFIG_VIDEO_TUNER) += tuner.o tda9887.o
 obj-$(CONFIG_VIDEO_BUF)   += video-buf.o
 obj-$(CONFIG_VIDEO_BTCX)  += btcx-risc.o
+obj-$(CONFIG_VIDEO_CLE266) += via_v4l_drv.o
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/Makefile.via linux-2.6.1-rc1-gentoo/drivers/media/video/Makefile.via
--- linux-2.6.0/drivers/media/video/Makefile.via	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/Makefile.via	2004-01-06 14:24:50.000000000 +0000
@@ -0,0 +1,46 @@
+#
+# Makefile for the video capture/playback device drivers.
+#
+
+bttv-objs	:=	bttv-driver.o bttv-cards.o bttv-if.o \
+			bttv-risc.o bttv-vbi.o
+zoran-objs      :=	zr36120.o zr36120_i2c.o zr36120_mem.o
+zr36067-objs	:=	zoran_procfs.o zoran_device.o \
+			zoran_driver.o zoran_card.o
+
+obj-$(CONFIG_VIDEO_DEV) += videodev.o v4l2-common.o v4l1-compat.o
+
+obj-$(CONFIG_VIDEO_BT848) += bttv.o msp3400.o tvaudio.o \
+	tda7432.o tda9875.o
+obj-$(CONFIG_SOUND_TVMIXER) += tvmixer.o
+
+obj-$(CONFIG_VIDEO_ZR36120) += zoran.o
+obj-$(CONFIG_VIDEO_SAA5249) += saa5249.o
+obj-$(CONFIG_VIDEO_CQCAM) += c-qcam.o
+obj-$(CONFIG_VIDEO_BWQCAM) += bw-qcam.o
+obj-$(CONFIG_VIDEO_W9966) += w9966.o
+obj-$(CONFIG_VIDEO_ZORAN_BUZ) += saa7111.o saa7185.o zr36060.o
+obj-$(CONFIG_VIDEO_ZORAN_DC10) += saa7110.o adv7175.o zr36060.o
+obj-$(CONFIG_VIDEO_ZORAN_DC30) += adv7175.o vpx3220.o zr36050.o \
+	zr36016.o
+obj-$(CONFIG_VIDEO_ZORAN_LML33) += bt819.o bt856.o zr36060.o
+obj-$(CONFIG_VIDEO_ZORAN_LML33R10) += saa7114.o adv7170.o zr36060.o
+obj-$(CONFIG_VIDEO_ZORAN) += zr36067.o videocodec.o
+obj-$(CONFIG_VIDEO_PMS) += pms.o
+obj-$(CONFIG_VIDEO_PLANB) += planb.o
+obj-$(CONFIG_VIDEO_VINO) += vino.o
+obj-$(CONFIG_VIDEO_STRADIS) += stradis.o
+obj-$(CONFIG_VIDEO_CPIA) += cpia.o
+obj-$(CONFIG_VIDEO_CPIA_PP) += cpia_pp.o
+obj-$(CONFIG_VIDEO_CPIA_USB) += cpia_usb.o
+obj-$(CONFIG_VIDEO_MEYE) += meye.o
+obj-$(CONFIG_VIDEO_SAA7134) += saa7134/
+obj-$(CONFIG_VIDEO_MXB) += saa7111.o tuner.o tda9840.o tea6415c.o tea6420.o mxb.o
+obj-$(CONFIG_VIDEO_HEXIUM_ORION) += hexium_orion.o
+obj-$(CONFIG_VIDEO_HEXIUM_GEMINI) += hexium_gemini.o
+obj-$(CONFIG_VIDEO_DPC) += saa7111.o dpc7146.o
+obj-$(CONFIG_TUNER_3036) += tuner-3036.o
+
+obj-$(CONFIG_VIDEO_TUNER) += tuner.o tda9887.o
+obj-$(CONFIG_VIDEO_BUF)   += video-buf.o
+obj-$(CONFIG_VIDEO_BTCX)  += btcx-risc.o
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/audio.c linux-2.6.1-rc1-gentoo/drivers/media/video/audio.c
--- linux-2.6.0/drivers/media/video/audio.c	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/audio.c	2004-01-06 17:28:06.000000000 +0000
@@ -0,0 +1,112 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#include "via_types.h"
+#include "compose.h"
+#include "capture.h"
+
+#include "CXA2104S.h"
+#include "via_v4l.h"
+
+
+extern  __inline void Macro_SetI2CIndex(void);
+extern  __inline void Macro_RestoreI2CIndex(void);
+
+void  Audio_Control( void * lpInput )
+{
+  LPVIASETPORTATTR lpAudioAttr = (LPVIASETPORTATTR) lpInput;
+
+  Macro_SetI2CIndex();
+
+  switch ( lpAudioAttr->attribute )
+  {
+     case  ATTR_INIT_AUDIO :
+           DBG_DD("audio.c : ATTR_INIT_AUDIO \n");
+           AUDIO_INIT_REG();
+           break;
+
+     case  ATTR_MUTE_ON  :
+           AUDIO_MUTE_ON();
+           DBG_DD("audio.c : ATTR_MUTE_ON, REG3 = 0x%x\n",AUDIO_RI2C(REG3));
+
+           break;
+
+     case  ATTR_MUTE_OFF :
+           AUDIO_MUTE_OFF();
+           DBG_DD("audio.c : ATTR_MUTE_OFF, REG3 = 0x%x\n",AUDIO_RI2C(REG3));
+           break;
+
+     case  ATTR_STEREO :
+           AUDIO_SELECT_STEREO();
+           DBG_DD("audio.c : ATTR_STEREO , REG4 = 0x%x\n",AUDIO_RI2C(REG4));
+           break;
+
+     case  ATTR_SAP :
+           AUDIO_SELECT_SAP();
+           DBG_DD("audio.c : ATTR_STEREO , REG4 = 0x%x\n",AUDIO_RI2C(REG4));
+           break;
+
+     case  ATTR_TUNER_AUDIO_SWITCH :
+           AUDIO_TUNER_SWITCH(lpAudioAttr->value);
+           break;
+
+     case  ATTR_AUDIO_CONTROLByAP :
+           switch ( lpAudioAttr->value )
+           {
+             case  AUDIO_STEREO   :
+                   AUDIO_SELECT_STEREO();
+                   break;
+
+             case  AUDIO_SAP      :
+                   AUDIO_SELECT_SAP();
+                   break;
+
+             case  AUDIO_DUAL      :
+                   AUDIO_SELECT_DUAL();
+                   break;
+
+             case  AUDIO_ON       :
+                   AUDIO_MUTE_OFF();
+                   break;
+
+             case  AUDIO_OFF      :
+                   AUDIO_MUTE_ON();
+                   break;
+
+             case  AUDIO_TV0      :
+                   AUDIO_TUNER_SWITCH(0);
+                   break;
+                   
+             case  AUDIO_TV1      :
+                   AUDIO_TUNER_SWITCH(1);
+                   break;
+
+           }
+           break;
+
+     case  ATTR_VOLUME :
+           break;
+  }
+  Macro_RestoreI2CIndex();
+}
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/audio.h linux-2.6.1-rc1-gentoo/drivers/media/video/audio.h
--- linux-2.6.0/drivers/media/video/audio.h	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/audio.h	2004-01-06 17:28:06.000000000 +0000
@@ -0,0 +1,28 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#ifndef __CXAUDIO
+#define __CXAUDIO
+void  Audio_Control(void * );
+#endif  //End of __CXAUDIO
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/capture.c linux-2.6.1-rc1-gentoo/drivers/media/video/capture.c
--- linux-2.6.0/drivers/media/video/capture.c	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/capture.c	2004-01-06 23:32:50.000000000 +0000
@@ -0,0 +1,3319 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+// I N C L U D E S ----------------------------------------------------------
+#include "via_types.h"
+#include "compose.h"
+#include "via.h"
+#include "ddmpeg.h"
+#include "capture.h"
+#include "via_privIoctl.h" /* for VIAGRAPHICINFO & custom ioctl command */
+#include "HWDiff.h"
+
+#include "via_v4l.h"
+#include "via_tuner.h"
+#include "vdec.h"
+#include "regrec.h"             /* for Macro_VidREGRec funcs */
+#include "ddover.h"
+
+
+// D E F I N E --------------------------------------------------------------
+#define HasScreenSwitch           1
+#define NoScreenSwitch            0
+
+#define V1orV3onScreen1_Right     1
+#define V1orV3onScreen1_Below     2
+#define V1orV3onScreen1_Left      3
+#define V1orV3onScreen0_Left      4
+#define V1orV3onScreen1_Above     5
+#define V1orV3onScreen0_Above     6
+#define V1orV3onScreen0           9
+                   
+
+// F U N C T I O N  D E C L A R A T I O N ----------------------------------------------------------
+unsigned long  UpdateOverlayTV(LPDDUPDATEOVERLAY, via_device *via );
+void  UpdateVPort(via_device *via );
+unsigned long Upd_Capture0(unsigned long dwVideoFlag,unsigned long dwStartAddr,RECTL rSrc,RECTL rDest,unsigned long dwSrcPitch,
+                 unsigned long dwOriSrcWidth,unsigned long dwOriSrcHeight,LPDDPIXELFORMAT lpDPFsrc,
+                 unsigned long dwDeinterlaceMode,unsigned long dwColorKey,unsigned long dwChromaKey,
+                 unsigned long dwKeyLow,unsigned long dwKeyHigh,unsigned long dwChromaLow,unsigned long dwChromaHigh,unsigned long dwFlags);
+unsigned long Upd_Capture1(unsigned long dwVideoFlag,unsigned long dwStartAddr,RECTL rSrc,RECTL rDest,unsigned long dwSrcPitch,
+                 unsigned long dwOriSrcWidth,unsigned long dwOriSrcHeight,LPDDPIXELFORMAT lpDPFsrc,
+                 unsigned long dwDeinterlaceMode,unsigned long dwColorKey,unsigned long dwChromaKey,
+                 unsigned long dwKeyLow,unsigned long dwKeyHigh,unsigned long dwChromaLow,unsigned long dwChromaHigh,unsigned long dwFlags);
+
+
+// E X T E R N   G L O B A L S--------------------------------------------------------------
+extern volatile unsigned char  * lpVidMEMIO;
+extern volatile unsigned char  * lpVidMEMIOReal;
+//extern unsigned long * lpMPEGMMIO;
+
+extern LPVIAVIDCTRL  lpVideoControl ;
+extern VIAGRAPHICINFO gVIAGraphicInfo;
+extern via_device via_v4l_devices[MAX_VIA_BOARDS];
+
+extern MPGDEVICE   MPGDevice;
+extern LPMPGDEVICE lpMPGDevice;
+extern ALPHADEVICE ALPDevice;
+extern CAPDEVICE   CAPDevice[2];
+extern OVERLAYRECORD   overlayRecordV1;
+extern OVERLAYRECORD   overlayRecordV3;
+
+extern DDUPDATEOVERLAY UpdateOverlayBackup;    // for HQVcontrol func use
+
+extern Bool TV_DEINTERLACE_BOB;
+
+extern Bool MPEG_ON;
+extern Bool TV0_ON;
+extern Bool TV1_ON;
+                     
+//extern Bool TV1_MINIFY_HOR_2;
+
+//extern unsigned long   gdwVideoOn;  /* Use TV1_ON, TV0_ON, MPEG_ON to replace */
+extern unsigned long   gdwVideoFlagMPEG;
+extern unsigned long   gdwVideoFlagTV0;
+extern unsigned long   gdwVideoFlagTV1;
+extern unsigned long   gdwAlphaEnabled;
+
+//To solve the bandwidth issue
+extern unsigned char Save_3C4_16;
+extern unsigned char Save_3C4_17;
+extern unsigned char Save_3C4_18;
+
+extern unsigned long   gdwUseExtendedFIFO;
+
+/* For panning mode use */
+/* Fixed for SAMM and both of primary & secondary          */
+/* screens are in Panning Mode,Video display size          */
+/* & position may be errors while VIAAdjustFrame is called.*/
+extern int panning_old_x[2];
+extern int panning_old_y[2];
+extern int panning_x[2];
+extern int panning_y[2];
+
+extern VIDHWDIFFERENCE VideoHWDifference;
+
+// E X T E R N   F U N C T I O N S--------------------------------------------------------------
+extern unsigned long UpdateOverlay(LPDDUPDATEOVERLAY lpUpdate);   /* for SAMM mode */
+
+// G L O B A L   V A R I A B L E S ------------------------------------------
+int bSetFirst = 0;
+
+LPCAPDEVICE  lpCAPDevice0;
+LPCAPDEVICE  lpCAPDevice1;
+
+unsigned long VBI_STRIDE;
+unsigned long CAP0_MAX_COUNT,CAP1_MAX_COUNT;
+
+DDUPDATEOVERLAY UpdateOverlayTV0Backup, UpdateOverlayTV1Backup;
+
+/* for SAMM mode */
+Bool  ScreenSwitchCount = 0;
+unsigned long Position_W_Temp1 = 0, Position_W_Temp2 = 0;
+unsigned long Position_H_Temp1 = 0, Position_H_Temp2 = 0;
+//Bool  CAP1_V1_HQV_ENABLE = 0;
+int   SammMode_CaseCmd = 0;
+
+// F U N C T I O N ----------------------------------------------------------
+int VIA_CAPSetFrameBuffer( LPCAPDEVICE lpDevice)
+{
+    unsigned long  dwShift;
+
+    DBG_DD("//    VIA_CAPSetFrameBuffer: \n");
+     
+    bSetFirst = 0;
+
+
+    if ( lpDevice->byDeviceType == DEV_TV1 )  //TV1 - V3 - Capture1(Port1)
+    {
+        unsigned long  dwPitch;
+
+        lpCAPDevice1 = lpDevice;
+        dwPitch=lpCAPDevice1->dwPitch;
+
+        dwShift = dwPitch * 4;
+        VIDOutD(CAP1_CONTROL,0x80000000);  //CLK
+        VIDOutD(CAP1_FB_STARTADDR1,lpCAPDevice1->dwCAPPhysicalAddr[1]);
+        VIDOutD(CAP1_FB_STARTADDR0,lpCAPDevice1->dwCAPPhysicalAddr[0]);
+        //VIDOutD(V1_STARTADDR_1,lpCAPDevice1->dwCAPPhysicalAddr[1]+dwShift);
+        //VIDOutD(V1_STARTADDR_0,lpCAPDevice1->dwCAPPhysicalAddr[0]+dwShift);        
+        VIDOutD(V3_STARTADDR_1,lpCAPDevice1->dwCAPPhysicalAddr[1]+dwShift);
+        VIDOutD(V3_STARTADDR_0,lpCAPDevice1->dwCAPPhysicalAddr[0]+dwShift);
+        VIDOutD(CAP1_STRIDE,dwPitch);
+        //VIDOutD(V1_STRIDE,dwPitch);
+        VIDOutD(V3_STRIDE,dwPitch);
+        CAP1_MAX_COUNT   = 0x00F000f0;
+
+        //VIDOutD(V_COMPOSE_MODE, (VIDInD(V_COMPOSE_MODE)|V3_COMMAND_FIRE));
+
+        //VIDOutD(CAP1_VBI_STRIDE,dwPitch|0x00002000);
+
+        DBG_DD("00000354 %08x\n",0x80000000);
+        DBG_DD("00000388 %08lx\n",lpCAPDevice1->dwCAPPhysicalAddr[1]);
+        DBG_DD("00000384 %08lx\n",lpCAPDevice1->dwCAPPhysicalAddr[0]);
+        //DBG_DD("00000238 %08lx\n",lpCAPDevice1->dwCAPPhysicalAddr[1]+dwShift);
+        //DBG_DD("00000254 %08lx\n",lpCAPDevice1->dwCAPPhysicalAddr[0]+dwShift);
+        DBG_DD("000002A8 %08lx\n",lpCAPDevice1->dwCAPPhysicalAddr[1]+dwShift);
+        DBG_DD("000002A4 %08lx\n",lpCAPDevice1->dwCAPPhysicalAddr[0]+dwShift);
+        DBG_DD("0000038C %08lx\n",VIDInD(CAP1_STRIDE));
+        //DBG_DD("0000023C %08lx\n",VIDInD(V1_STRIDE));
+        DBG_DD("000002AC %08lx\n",VIDInD(V3_STRIDE));
+        //DBG_DD("00000370 %08x\n",VIDInD(CAP1_VBI_STRIDE));
+        /* set frame buffer address to H/W or V3 */
+    }
+
+
+    if ( lpDevice->byDeviceType == DEV_TV0 )    //TV0 - V1 - Capture0(Port0)
+    {
+        lpCAPDevice0 = lpDevice;
+        dwShift = lpCAPDevice0->dwPitch * 4;
+        VIDOutD(CAP0_CONTROL,0x80000000);  //CLK
+        VIDOutD(CAP0_FB_STARTADDR2,lpCAPDevice0->dwCAPPhysicalAddr[2]);
+        VIDOutD(CAP0_FB_STARTADDR1,lpCAPDevice0->dwCAPPhysicalAddr[1]);
+        VIDOutD(CAP0_FB_STARTADDR0,lpCAPDevice0->dwCAPPhysicalAddr[0]);
+        
+        if (gVIAGraphicInfo.Cap0_SwitchToV3)        //TV0 - V3 - Capture0 (for SAMSUNG)
+        {
+            if (gVIAGraphicInfo.RevisionID >= VIA_REVISION_CLECX)
+            {
+                VIDOutD(V3_STARTADDR_2,lpCAPDevice0->dwCAPPhysicalAddr[2]+dwShift);
+                DBG_DD("0000029C %08lx\n",lpCAPDevice0->dwCAPPhysicalAddr[2]+dwShift);
+            }
+            VIDOutD(V3_STARTADDR_1,lpCAPDevice0->dwCAPPhysicalAddr[1]+dwShift);
+            VIDOutD(V3_STARTADDR_0,lpCAPDevice0->dwCAPPhysicalAddr[0]+dwShift);
+            VIDOutD(V3_STRIDE,lpCAPDevice0->dwPitch);
+            
+            DBG_DD("000002A8 %08lx\n",lpCAPDevice0->dwCAPPhysicalAddr[1]+dwShift);
+            DBG_DD("000002A4 %08lx\n",lpCAPDevice0->dwCAPPhysicalAddr[0]+dwShift);
+            DBG_DD("000002AC %08lx\n",VIDInD(V3_STRIDE));
+        }
+        else                                        //TV0 - V1 - Capture0 (Port0)
+        {
+            VIDOutD(V1_STARTADDR_2,lpCAPDevice0->dwCAPPhysicalAddr[2]+dwShift);
+        VIDOutD(V1_STARTADDR_1,lpCAPDevice0->dwCAPPhysicalAddr[1]+dwShift);
+        VIDOutD(V1_STARTADDR_0,lpCAPDevice0->dwCAPPhysicalAddr[0]+dwShift);
+        VIDOutD(V1_STRIDE,lpCAPDevice0->dwPitch);
+            
+            DBG_DD("00000248 %08lx\n",lpCAPDevice0->dwCAPPhysicalAddr[2]+dwShift);
+            DBG_DD("00000238 %08lx\n",lpCAPDevice0->dwCAPPhysicalAddr[1]+dwShift);
+            DBG_DD("00000254 %08lx\n",lpCAPDevice0->dwCAPPhysicalAddr[0]+dwShift);
+            DBG_DD("0000023C %08lx\n",VIDInD(V1_STRIDE));
+        }
+        
+        VIDOutD(CAP0_STRIDE,lpCAPDevice0->dwPitch);
+        /*CAP0_MAX_COUNT = lpCAPDevice0->dwPitch ;*/
+        CAP0_MAX_COUNT = 0x00F200f0;
+
+        //VIDOutD(V_COMPOSE_MODE, (VIDInD(V_COMPOSE_MODE)|V1_COMMAND_FIRE));
+
+        //VIDOutD(CAP0_VBI_STRIDE,lpCAPDevice0->dwPitch|0x00002000);
+        DBG_DD("00000348 %08lx\n",lpCAPDevice0->dwCAPPhysicalAddr[2]);
+        DBG_DD("00000344 %08lx\n",lpCAPDevice0->dwCAPPhysicalAddr[1]);
+        DBG_DD("00000340 %08lx\n",lpCAPDevice0->dwCAPPhysicalAddr[0]);
+        DBG_DD("00000350 %08lx\n",VIDInD(CAP0_STRIDE));
+        //DBG_DD("0000032C %08x\n",VIDInD(CAP0_VBI_STRIDE));
+        DBG_DD("00000310 %08x\n",0x80000000);
+        /* set frame buffer address to H/W or V1 */
+    }
+
+
+    return PI_OK;
+
+} //VIA_CAPSetFrameBuffer
+
+
+
+int VIA_ALPSetFrameBuffer(LPALPHADEVICE lpDevice)
+{
+    DBG_DD("//     VIA_ALPSetFrameBuffer: \n");
+
+
+    VIDOutD(V_ALPHA_STARTADDR,lpDevice->dwALPPhysicalAddr);
+    /* Other side-effort is to set-up related Alpha Window register here,
+     * we use this to reduce anthor function call. */
+
+    VIDOutD(V_ALPHA_STRIDE,lpDevice->dwPitch);
+
+    VIDOutD(V3_ALPHA_QWORD_PER_LINE,(VIDInD(V3_ALPHA_QWORD_PER_LINE) &(~0x3ff)) | ((lpDevice->dwPitch)>>4));
+   
+    //VIDOutD(ALPHA_V3_FIFO_CONTROL,(64-32)<<24 | (64-1)<<16 | (64-32)<<8 | (64-1));
+    
+    DBG_DD("00000224 %08lx\n",lpDevice->dwALPPhysicalAddr);
+    DBG_DD("0000021C %08lx\n",lpDevice->dwPitch);
+    DBG_DD("000002B8 %08lx\n",VIDInD(V3_ALPHA_QWORD_PER_LINE));
+    //DBG_DD("00000278 %08lx\n",VIDInD(ALPHA_V3_FIFO_CONTROL));
+
+    return PI_OK;
+
+} //VIA_ALPSetFrameBuffer
+
+
+
+//   VIA 9001 I.A supports 2 Capture Port . Clients can
+//Create 2 Capture in video windows simulataneously.
+//For example :
+//      Client create 1st video window the video source is TV
+//      Client create 2nd video window the video source is from
+//      Composite/S-Video
+//In order to let driver identify which capture port is active
+//( or client intends to change attribute of capture port )
+//VIASelectVideoPort must be called before every standard
+//XVideo extension API calls.
+//   Client get function ptr "VIADriverProc" via calling
+//"XvGetPortAttribute ". The detail should discuss with
+//VIA engineer.
+
+/*******************************************
+* FUNCTION : HQV video control             *
+********************************************/
+
+unsigned long HQVControl( LPVIAVIDCTRL lpNewVidCtl )
+{
+    unsigned long   dwRet = PI_OK;
+    unsigned long   dwHQV    = lpNewVidCtl->dwHighQVDO;
+    unsigned long   dwOldHQV = lpVideoControl->dwHighQVDO;
+    DDSURFACEDESC   SurfaceDesc;
+    //LPDDSURFACEDESC lpSurfaceDesc = &SurfaceDesc;
+    via_device *via = NULL;
+
+    if ( dwHQV == VW_HIGHQVDO_OFF ) 
+    {
+        DBG_DD("//  HQVControl : DestroyHQVSurface, dwHQV=0x%08lx.\n", dwOldHQV);
+
+	if ( dwOldHQV == 1)
+	{
+	    DBG_DD("// HQVControl : MPEG \n");
+	    via = &via_v4l_devices[0];		
+	    gdwVideoFlagMPEG &= 0xFBFDFFFF;
+	    
+	    if (MPEG_ON)
+	    {
+		via_set_window(via);
+		SurfaceDesc.dwFourCC = 0x32565148;
+		VIADriverProc(0x6, &UpdateOverlayBackup);
+		
+		dwRet = VIADriverProc(DESTROYSURFACE,&SurfaceDesc);
+	    }
+	}
+	else if ( dwOldHQV == VW_HIGHQVDO_TV1 )
+        {
+            DBG_DD("//  HQVControl : Destroy TV1\n");
+            /*via = &via_v4l_devices[0];*/
+            via = &via_v4l_devices[1];
+            gdwVideoFlagTV1 &= ~(VIDEO_HQV_INUSE | CAP1_USE_HQV);
+            if (TV1_ON)
+            {
+               //UpdateOverlayTV(&UpdateOverlayTV1Backup,PORT1) ;
+               via_set_window(via);
+               SurfaceDesc.dwFourCC = FOURCC_HQVTV1;
+               dwRet=VIADriverProc(DESTROYSURFACE,&SurfaceDesc);
+            }
+        }        
+        else if ( dwOldHQV == VW_HIGHQVDO_TV0 )
+        {
+            DBG_DD("//  HQVControl : Destroy TV0\n");
+            /*via = &via_v4l_devices[1];*/
+            via = &via_v4l_devices[0];
+            gdwVideoFlagTV0 &= ~(VIDEO_HQV_INUSE | CAP0_USE_HQV);
+
+            if (TV0_ON)
+            {
+                via_set_window(via);
+                SurfaceDesc.dwFourCC = FOURCC_HQVTV0;
+                dwRet=VIADriverProc(DESTROYSURFACE,&SurfaceDesc);
+            }
+        }
+       
+//        VIDOutD(HQV_CONTROL, (VIDInD(HQV_CONTROL) & (~HQV_ENABLE)) );
+
+    }
+    else 
+    {
+        DBG_DD("// HQVControl : CreateHQVSurface, dwHQV=0x%08lx.\n", dwHQV);
+
+	if ( dwHQV == 1)
+	{
+	    gdwVideoFlagMPEG |= 0x4020000;
+	    via = &via_v4l_devices[0];		
+	    SurfaceDesc.dwFourCC = 0x31565148;
+	    
+	    VIADriverProc(CREATESURFACE,&SurfaceDesc);
+	    dwRet = VIADriverProc(0x6, &UpdateOverlayBackup);
+	    
+	    via_set_window(via);
+	    
+	}
+	else if ( dwHQV == VW_HIGHQVDO_TV1 )
+       {
+            gdwVideoFlagTV1 |= VIDEO_HQV_INUSE | CAP1_USE_HQV;
+            if (gdwVideoFlagTV1)
+            {
+                /*via = &via_v4l_devices[0];*/
+                via = &via_v4l_devices[1];
+                SurfaceDesc.dwFourCC = FOURCC_HQVTV1;
+                dwRet=VIADriverProc(CREATESURFACE,&SurfaceDesc);
+                via_set_window(via);
+            }   
+        }
+        else if ( dwHQV == VW_HIGHQVDO_TV0 )
+        {
+            gdwVideoFlagTV0 |= VIDEO_HQV_INUSE | CAP0_USE_HQV;
+            if (gdwVideoFlagTV0)
+            {
+                /*via = &via_v4l_devices[1];*/
+                via = &via_v4l_devices[0];
+                SurfaceDesc.dwFourCC = FOURCC_HQVTV0;
+                dwRet=VIADriverProc(CREATESURFACE,&SurfaceDesc);
+                via_set_window(via);
+            }   
+        }
+
+       lpVideoControl->dwHighQVDO = lpNewVidCtl->dwHighQVDO;
+       //dwRet = CreateSurface(lpSurfaceDesc);
+    }
+   
+   //lpVideoControl->dwHighQVDO = lpNewVidCtl->dwHighQVDO;
+
+   return dwRet;
+
+} //HQVControl
+
+
+/*******************************************
+*  Function : XVL Stop Video               *
+********************************************/
+void VIAStopVideo(void)
+{
+    /* stop Capture engine */
+    /* stop Video decoder  */
+
+    DBG_DD("//     VIAStopVideo: \n");
+
+    bSetFirst = 0;
+
+    Macro_VidREGRec(VIDREGREC_RESET_COUNTER, 0, 0);
+
+    switch(lpVideoControl->PORTID)
+    {
+        case PORT0 :
+                TV0_ON = FALSE;
+                
+                if (gVIAGraphicInfo.Cap0_SwitchToV3)        //TV0 - V3 - Capture0 (for SAMSUNG)
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_CONTROL,VIDInD(V3_CONTROL) & ~V3_ENABLE);
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_COMPOSE_MODE, (VIDInD(V_COMPOSE_MODE)|V3_COMMAND_FIRE));
+                }
+                else
+                {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_CONTROL,VIDInD(V1_CONTROL) & ~V1_ENABLE);
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_COMPOSE_MODE, (VIDInD(V_COMPOSE_MODE)|V1_COMMAND_FIRE));
+                }
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,CAP0_CONTROL,VIDInD(CAP0_CONTROL) & ~(C0_ENABLE));
+
+                //Kevin_0818
+                if (gdwVideoFlagTV0 & CAP0_USE_HQV)
+                {
+                    //gdwVideoFlag &= ~(VIDEO_HQV_INUSE | CAP1_USE_HQV);
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,HQV_CONTROL, (VIDInD(HQV_CONTROL) & (~HQV_ENABLE)) );
+                }
+            break;
+
+        case PORT1:
+                TV1_ON = FALSE;
+
+                /* for SAMM Mode */
+/*                if ( ( SammMode_CaseCmd == V1orV3onScreen1_Right) || ( SammMode_CaseCmd == V1orV3onScreen1_Below) ||
+                     ( SammMode_CaseCmd == V1orV3onScreen1_Left) || ( SammMode_CaseCmd == V1orV3onScreen1_Above) )             
+                {*/
+                    //Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_CONTROL,VIDInD(V1_CONTROL) & ~V1_ENABLE);
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_CONTROL,VIDInD(V3_CONTROL) & ~V3_ENABLE);
+                    //Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_COMPOSE_MODE, (VIDInD(V_COMPOSE_MODE)|V1_COMMAND_FIRE));
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_COMPOSE_MODE, (VIDInD(V_COMPOSE_MODE)|V3_COMMAND_FIRE));
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,CAP1_CONTROL,VIDInD(CAP1_CONTROL) & ~(C1_ENABLE));
+
+                    //Kevin_0818
+                    if (gdwVideoFlagTV1 & CAP1_USE_HQV)
+                    {
+                        //gdwVideoFlag &= ~(VIDEO_HQV_INUSE | CAP1_USE_HQV);
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,HQV_CONTROL, (VIDInD(HQV_CONTROL) & (~HQV_ENABLE)) );
+                    }
+/*                }
+                else
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_CONTROL,VIDInD(V3_CONTROL) & ~V3_ENABLE);
+                    if (gdwVideoFlagTV1 & CAP1_USE_HQV)
+                    {
+                        //gdwVideoFlag &= ~(VIDEO_HQV_INUSE | CAP1_USE_HQV);
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,HQV_CONTROL, (VIDInD(HQV_CONTROL) & (~HQV_ENABLE)) );
+                    }
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_COMPOSE_MODE, (VIDInD(V_COMPOSE_MODE)|V3_COMMAND_FIRE));
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,CAP1_CONTROL,VIDInD(CAP1_CONTROL) & ~(C1_ENABLE));
+                }
+                CAP1_V1_HQV_ENABLE = 0; */
+            break;
+    }
+    /*  [Kevin_0818]
+     *  Add Wait_HQV_idle
+     */
+    Macro_VidREGFlush_Hide();
+
+        if ((gdwUseExtendedFIFO)&&(!TV1_ON)&&(!TV0_ON))
+        {
+            //Restore Display fifo
+            outb(0x16, 0x3C4); outb(Save_3C4_16, 0x3C5);
+            DBG_DD("Restore 3c4.16 : %08x \n",inb(0x3C5));
+            outb(0x17, 0x3C4); outb(Save_3C4_17, 0x3C5);
+            DBG_DD("        3c4.17 : %08x \n",inb(0x3C5));
+            outb(0x18, 0x3C4); outb(Save_3C4_18, 0x3C5);
+            DBG_DD("        3c4.18 : %08x \n",inb(0x3C5));
+            gdwUseExtendedFIFO = 0;
+                }
+    
+} //VIAStopVideo
+
+
+/*******************************************
+*  Function : update alpha surface         *
+********************************************/
+unsigned long UpdateOverlayAlpha(RECTL rDest)
+{
+    VIDOutD(V_ALPHA_STRIDE,ALIGN_TO_16_BYTES((rDest.right-rDest.left)/2));
+    VIDOutD(V3_ALPHA_QWORD_PER_LINE,(VIDInD(V3_ALPHA_QWORD_PER_LINE) &(~0x3ff)) | (ALIGN_TO_16_BYTES((rDest.right-rDest.left)/2)>>4));
+    VIDOutD(V_ALPHA_WIN_END, (rDest.right<<16) | rDest.bottom );
+    VIDOutD(V_ALPHA_WIN_START, (rDest.left<<16) | rDest.top );
+
+    return PI_OK;
+}
+
+
+/*******************************************
+*  Function : Capture engine control       *
+********************************************/
+void UpdateVPort(via_device *via)
+{
+    unsigned long  dwCAPCTRL=0;
+    //unsigned long  VBICount,AVCount;
+
+    DBG_DD("// UpdateVPort: port %d\n", via->video_dev->minor);
+
+    switch (via->video_dev->minor)
+    {
+        case COMMAND_FOR_TV0 :
+        {
+            /*via = &via_v4l_devices[1];*/
+            via = &via_v4l_devices[0];
+
+                    //dwCAPCTRL =  SWAP_UYVY + IN_656_8 + BUFFER_2_MODE
+                    dwCAPCTRL =  SWAP_UYVY + IN_656_8 + BUFFER_3_MODE
+                               + C0_ENABLE + VREF_INVERT;
+
+                    if (!via->CapInfo.FieldSwap)
+                        dwCAPCTRL |= FIELD_INPUT_INVERSE;
+
+                    if (!via->CapInfo.No_HFilter)
+                        dwCAPCTRL |= H_FILTER_2;
+
+                    if (via->CapInfo.dwDeinterlaceMode == VIA_DEINTERLACE_BOB)
+                        dwCAPCTRL |= DEINTER_ODD_EVEN;
+                    else
+                        dwCAPCTRL |= DEINTER_FRAME;
+
+                    dwCAPCTRL |= 0x08000000; /* FIFO */
+
+                    if ( !bSetFirst )
+                    {
+                        if (via->video_chan.norm == VIDEO_MODE_NTSC)
+                        {
+                            //VBICount =  CAP0_MAX_COUNT/ 8;
+                            //AVCount  =  CAP0_MAX_COUNT/ 8;
+                            //Set to 0x00f200f0 for H/W limition
+                            VIDOutD(CAP0_MAXCOUNT,0x00f200f0);
+                        }
+                        else if ((via->video_chan.norm == VIDEO_MODE_PAL)
+                              || (via->video_chan.norm == VIDEO_MODE_SECAM))
+                        {
+                            //VBICount =  CAP0_MAX_COUNT/ 8;
+                            //AVCount  =  CAP0_MAX_COUNT/ 8;
+                            //for default PAL, it should be 0x012000f0
+                            // y count = 0x120(288), to fix player bug
+                            // set to 0x11b here
+                            VIDOutD(CAP0_MAXCOUNT,0x012000f0);
+                        }
+
+                        VIDOutD(CAP0_SCAL_CONTROL,(VIDInD(CAP0_SCAL_CONTROL)&0x0));
+
+                        bSetFirst = 1;
+
+                        //DBG_DD("00000338 %08x\n",VIDInD(CAP0_VBIMAX_COUNT));
+                        DBG_DD("00000334 %08lx\n",VIDInD(CAP0_MAXCOUNT));
+                    }
+
+            VIDOutD(CAP0_CONTROL, 0x80000000 | dwCAPCTRL);
+            DBG_DD("00000310 %08lx\n",VIDInD(CAP0_CONTROL));
+
+            break;
+        }
+
+        case COMMAND_FOR_TV1 :
+        {
+            /*via = &via_v4l_devices[0];*/
+            via = &via_v4l_devices[1];
+            DBG_DD("CapPort == PORT1\n");
+            DBG_DD("bSetFirst: %x\n", bSetFirst);
+
+                       dwCAPCTRL = SWAP_UYVY + IN_656_8 + BUFFER_2_MODE
+                               + C1_ENABLE + VREF_INVERT;
+
+                    if (!via->CapInfo.No_HFilter)
+                        dwCAPCTRL |= H_FILTER_2;
+
+                    if (via->CapInfo.dwDeinterlaceMode == VIA_DEINTERLACE_BOB)
+                        dwCAPCTRL |= DEINTER_ODD_EVEN;
+                    else
+                        dwCAPCTRL |= DEINTER_FRAME;
+
+                    dwCAPCTRL |=  0x08000000; /* FIFO */
+
+                    if ( !bSetFirst )
+                    {
+                        if (via->video_chan.norm == VIDEO_MODE_NTSC)
+                        {
+                            //VBICount = CAP1_MAX_COUNT/ 8;
+                            //AVCount  = CAP1_MAX_COUNT/ 8;
+                            //VIDOutD(CAP1_VBIMAX_COUNT,19<<16|VBICount);
+                            //Set to 0x00f200f0 for H/W limition
+                            VIDOutD(CAP1_MAXCOUNT,0x00f200f0);
+                        }
+                        else if ((via->video_chan.norm == VIDEO_MODE_PAL)
+                              || (via->video_chan.norm == VIDEO_MODE_SECAM))
+                        {
+                            //VBICount = CAP1_MAX_COUNT/ 8;
+                            //AVCount  = CAP1_MAX_COUNT/ 8;
+                            //VIDOutD(CAP1_VBIMAX_COUNT,25<<16|VBICount);
+                            //Set to 0x00f200f0 for H/W limition
+                            VIDOutD(CAP1_MAXCOUNT,0x012000f0);
+                        }
+
+                        /*
+                        if ( TV1_MINIFY_HOR_2 )
+                           VIDOutD(CAP1_SCAL_CONTROL,(VIDInD(CAP1_SCAL_CONTROL)&0xfffff000)|
+                                (C1_H_MINI_EN | C1_H_MINI_2 ));
+                        else
+                        */
+                           VIDOutD(CAP1_SCAL_CONTROL,(VIDInD(CAP1_SCAL_CONTROL)&0x0));
+
+                        bSetFirst = 1;
+
+                        DBG_DD("0000037C %08lx\n",VIDInD(CAP1_VBIMAX_COUNT));
+                        DBG_DD("00000378 %08lx\n",VIDInD(CAP1_MAXCOUNT));
+                    }
+
+            VIDOutD(CAP1_CONTROL,0x80000000 |dwCAPCTRL);
+            DBG_DD("00000354 %08lx\n",VIDInD(CAP1_CONTROL) );
+
+            break;
+        }
+    }
+
+}
+
+/************************************************************************************
+*  Function :   Just determine the screen is switching or not.
+*               No matter screen 0 switch to screen 1 or screen 1 switch to screen 0   
+*               For SAMM mode
+*************************************************************************************/
+unsigned long ScreenSwitch( unsigned long positionW1, unsigned long positionW2, unsigned long positionH1, unsigned long positionH2 )
+{    
+    if ( ( ((positionW1>gVIAGraphicInfo.Screen[0].dwSaveWidth)&&(positionW2<gVIAGraphicInfo.Screen[0].dwSaveWidth)) ||
+           ((positionW1<gVIAGraphicInfo.Screen[0].dwSaveWidth)&&(positionW2>gVIAGraphicInfo.Screen[0].dwSaveWidth)) ) ||
+         ( ((positionH1>gVIAGraphicInfo.Screen[0].dwSaveHeight)&&(positionH2<gVIAGraphicInfo.Screen[0].dwSaveHeight)) ||
+           ((positionH1<gVIAGraphicInfo.Screen[0].dwSaveHeight)&&(positionH2>gVIAGraphicInfo.Screen[0].dwSaveHeight)) ) )
+    {
+        return HasScreenSwitch;
+    }
+    else
+    {
+        return NoScreenSwitch;
+    }
+        
+}
+       
+/************************************************************************************************
+*  Function :   To determine V1 is on Screen 0 (V1onScreen1 = 0) or on screen 1 (V1onScreen1 = 1)
+*               and V3 is on screen 0 (V3offScreen0 = 0) or on screen 1 (V3offScreen0 = 1)      
+*               For SAMM mode
+*************************************************************************************************/
+unsigned long CapScreenSwitchManager( LPDDUPDATEOVERLAY lpUpdate, via_device *via)
+{
+    DBG_DD("CapScreenSwitchManager!!\n");
+    DBG_DD("lpUpdate->rDest.left=%ld\n",lpUpdate->rDest.left);
+    if ( (gVIAGraphicInfo.SAMM) && (lpUpdate->rDest.left > gVIAGraphicInfo.Screen[0].dwSaveWidth)
+          && (lpUpdate->rDest.left < 65535) && !(gVIAGraphicInfo.Screen1IsLeft) )
+    {   // Screen1 RightOf Screen0, V1 or V3 on Screen1
+        lpUpdate->rDest.left = lpUpdate->rDest.left - gVIAGraphicInfo.Screen[0].dwSaveWidth;
+        lpUpdate->rDest.right = lpUpdate->rDest.right - gVIAGraphicInfo.Screen[0].dwSaveWidth;
+            
+        if ( via->video_dev->minor == 0 )
+        {
+            //lpVideoControl->Cap0OnScreen1 = 1;
+            lpVideoControl->VideoStatus |= CAP0_ON_SND;            
+        }
+        else
+        {
+            //lpVideoControl->Cap1OnScreen1 = 1;
+            lpVideoControl->VideoStatus |= CAP1_ON_SND;            
+        }
+                
+            return V1orV3onScreen1_Right;
+    }
+    else if ( (gVIAGraphicInfo.SAMM) && (lpUpdate->rDest.top > gVIAGraphicInfo.Screen[0].dwSaveHeight) 
+               && (lpUpdate->rDest.top < 65535) && !(gVIAGraphicInfo.Screen1IsAbove) )
+    {   // Screen1 Below Screen0, V1 or V3 on Screen1
+        lpUpdate->rDest.top = lpUpdate->rDest.top - gVIAGraphicInfo.Screen[0].dwSaveHeight;
+        lpUpdate->rDest.bottom = lpUpdate->rDest.bottom - gVIAGraphicInfo.Screen[0].dwSaveHeight;
+        
+        if ( via->video_dev->minor == 0 )
+        {
+            //lpVideoControl->Cap0OnScreen1 = 1;
+            lpVideoControl->VideoStatus |= CAP0_ON_SND;            
+        }
+        else
+        {
+            //lpVideoControl->Cap1OnScreen1 = 1;
+            lpVideoControl->VideoStatus |= CAP1_ON_SND;            
+        }
+        
+        return V1orV3onScreen1_Below;
+    }
+    else if ( (gVIAGraphicInfo.Screen1IsLeft) && 
+             ((lpUpdate->rDest.left < gVIAGraphicInfo.Screen[0].dwSaveWidth) || (lpUpdate->rDest.left > 65535)) )
+    {   // Screen1 LeftOf Screen0, V1 or V3 on Screen1
+        if ( via->video_dev->minor == 0 )
+        {
+            //lpVideoControl->Cap0OnScreen1 = 1;
+            lpVideoControl->VideoStatus |= CAP0_ON_SND;
+            DBG_DD("Case 5!!\n");
+        }
+        else
+        {
+            //lpVideoControl->Cap1OnScreen1 = 1;
+            lpVideoControl->VideoStatus |= CAP1_ON_SND;                            
+        }
+        
+        return V1orV3onScreen1_Left;
+    }
+    else if ( (gVIAGraphicInfo.Screen1IsLeft) && (lpUpdate->rDest.left > gVIAGraphicInfo.Screen[0].dwSaveWidth) 
+               && (lpUpdate->rDest.left < 65535) )
+    {   // Screen1 LeftOf Screen0, V1 or V3 on Screen0
+        lpUpdate->rDest.left = lpUpdate->rDest.left - gVIAGraphicInfo.Screen[0].dwSaveWidth;
+        lpUpdate->rDest.right = lpUpdate->rDest.right - gVIAGraphicInfo.Screen[0].dwSaveWidth;        
+        
+        if ( via->video_dev->minor == 0 )
+        {
+            //lpVideoControl->Cap0OnScreen1 = 0;
+            lpVideoControl->VideoStatus &= ~CAP0_ON_SND;            
+        }
+        else
+        {
+            //lpVideoControl->Cap1OnScreen1 = 0;
+            lpVideoControl->VideoStatus &= ~CAP1_ON_SND;                 
+        }
+        
+        return V1orV3onScreen0_Left;
+    }    
+    else if ( (gVIAGraphicInfo.Screen1IsAbove) && 
+             ((lpUpdate->rDest.top < gVIAGraphicInfo.Screen[0].dwSaveHeight) || (lpUpdate->rDest.top > 65535)) )
+    {   // Screen1 Above Screen0, V1 or V3 on Screen1
+        if ( via->video_dev->minor == 0 )
+        {
+            //lpVideoControl->Cap0OnScreen1 = 1;
+            lpVideoControl->VideoStatus |= CAP0_ON_SND;            
+        }
+        else
+        {
+            //lpVideoControl->Cap1OnScreen1 = 1;
+            lpVideoControl->VideoStatus |= CAP1_ON_SND;            
+        }
+        
+        return V1orV3onScreen1_Above;
+    }
+    else if ( (gVIAGraphicInfo.Screen1IsAbove) && (lpUpdate->rDest.top > gVIAGraphicInfo.Screen[0].dwSaveHeight) 
+               && (lpUpdate->rDest.top < 65535) )
+    {   // Screen1 Above Screen0, V1 or V3 on Screen0
+        lpUpdate->rDest.top = lpUpdate->rDest.top - gVIAGraphicInfo.Screen[0].dwSaveHeight;
+        lpUpdate->rDest.bottom = lpUpdate->rDest.bottom - gVIAGraphicInfo.Screen[0].dwSaveHeight;        
+        
+        if ( via->video_dev->minor == 0 )
+        {
+            //lpVideoControl->Cap0OnScreen1 = 0;
+            lpVideoControl->VideoStatus &= ~CAP0_ON_SND;            
+        }
+        else
+        {
+            //lpVideoControl->Cap1OnScreen1 = 0;
+            lpVideoControl->VideoStatus &= ~CAP1_ON_SND;            
+        }
+        
+        return V1orV3onScreen0_Above;
+    }
+    else
+    {   // V1 and V3 on Screen0
+        if ( via->video_dev->minor == 0 )
+        {
+            //lpVideoControl->Cap0OnScreen1 = 0;
+            lpVideoControl->VideoStatus &= ~CAP0_ON_SND;            
+        }
+        else
+        {
+            //lpVideoControl->Cap1OnScreen1 = 0;
+            lpVideoControl->VideoStatus &= ~CAP1_ON_SND;                
+        }
+    
+        return V1orV3onScreen0;
+    }   
+}
+    
+
+/*******************************************
+*  Function : Video engine control         *
+********************************************/
+unsigned long UpdateOverlayTV(LPDDUPDATEOVERLAY lpUpdate, via_device *via)
+{
+    unsigned long dwFlags = lpUpdate->dwFlags;
+    unsigned long dwKeyLow=0, dwKeyHigh=0;
+    unsigned long dwChromaLow=0, dwChromaHigh=0;
+    unsigned long dwVideoFlag=0;
+    unsigned long dwColorKey=0, dwChromaKey=0;
+    DDUPDATEOVERLAY UpdateOverlayTVTemp;
+    int   nDstTop, nDstBottom, nDstLeft, nDstRight, nTopBak=0;
+    DDPIXELFORMAT DDPixelFormat;                //pixel format data
+    LPDDPIXELFORMAT lpDDPixelFormat = &DDPixelFormat;
+    LPOVERLAYRECORD   lpoverlayTVRecord = &overlayRecordV1;
+    
+    /*Added for SAMM Mode*/
+    int ScrnIndex = 0;
+    
+    
+   /* for SAMM Mode */
+    DBG_DD("Raw rSrc  X (%ld,%ld) Y (%ld,%ld)\n",
+                lpUpdate->rSrc.left, lpUpdate->rSrc.right, lpUpdate->rSrc.top, lpUpdate->rSrc.bottom);
+    DBG_DD("Raw rDest  X (%ld,%ld) Y (%ld,%ld)\n",
+                lpUpdate->rDest.left, lpUpdate->rDest.right, lpUpdate->rDest.top, lpUpdate->rDest.bottom);
+
+    switch (via->video_dev->minor)
+    {
+        case COMMAND_FOR_TV0 :
+            if (gVIAGraphicInfo.Cap0_SwitchToV3)        //TV0 - V3 - Capture0 (for SAMSUNG)
+            {
+                overlayRecordV3.dwV1OriHeight = lpUpdate->rSrc.bottom - lpUpdate->rSrc.top;
+            }
+            else                                        //TV0 - V1 - Capture0 (Port0)
+            {
+                overlayRecordV1.dwV1OriHeight = lpUpdate->rSrc.bottom - lpUpdate->rSrc.top;
+            }
+            break;
+        
+        case COMMAND_FOR_TV1 :
+            overlayRecordV3.dwV1OriHeight = lpUpdate->rSrc.bottom - lpUpdate->rSrc.top;
+            break;
+    }
+    
+     if ( (ScreenSwitchCount%2) == 0 )
+    {
+        Position_W_Temp1 = lpUpdate->rDest.left;
+        Position_H_Temp1 = lpUpdate->rDest.top;
+        ScreenSwitchCount++;
+    }
+    else
+    {
+        Position_W_Temp2 = lpUpdate->rDest.left;
+        Position_H_Temp2 = lpUpdate->rDest.top;
+        ScreenSwitchCount++;
+    }
+
+    DBG_DD("// UpdateOverlayTV: Resolution = %ld x %ld \n", gVIAGraphicInfo.Screen[ScrnIndex].dwWidth, gVIAGraphicInfo.Screen[ScrnIndex].dwHeight);
+    DBG_DD("// UpdateOverlayTV: Video Position = (%ld, %ld) \n", lpUpdate->rDest.left, lpUpdate->rDest.top);
+
+    /* for SAMM Mode */
+    SammMode_CaseCmd = CapScreenSwitchManager(lpUpdate, via);
+    DBG_DD("// UpdateOverlayTV: SammMode_CaseCmd = %d !!!\n", SammMode_CaseCmd);
+                   
+    /*Added for SAMM Mode*/
+    if (dwFlags & DDOVER_ON_SND)
+    {
+        ScrnIndex = 1;
+        if ( via->video_dev->minor == 0 )
+        {
+            lpVideoControl->VideoStatus |= CAP0_ON_SND;
+            DBG_DD("CAP0_ON_SND\n");
+        }
+        else
+        {
+            lpVideoControl->VideoStatus |= CAP1_ON_SND;
+            DBG_DD("CAP1_ON_SND\n");
+        }        
+    }
+    else 
+    {
+        if ( ( (via->video_dev->minor==0) && (lpVideoControl->VideoStatus & CAP0_ON_SND) ) || 
+             ( (via->video_dev->minor==1) && (lpVideoControl->VideoStatus & CAP1_ON_SND) ) )            
+    
+        {
+            ScrnIndex = 1;
+            dwFlags |= DDOVER_ON_SND;
+        }
+    }               
+    
+    /*Fixed for SAMM panning Mode*/
+    if (gVIAGraphicInfo.Screen[ScrnIndex].dwPanning) 
+    {
+        DBG_DD("// Panning!!\n");
+        lpUpdate->rDest.left = lpUpdate->rDest.left - (panning_x[ScrnIndex] - panning_old_x[ScrnIndex]);
+        lpUpdate->rDest.top = lpUpdate->rDest.top - (panning_y[ScrnIndex] - panning_old_y[ScrnIndex]);
+        lpUpdate->rDest.right = lpUpdate->rDest.right - (panning_x[ScrnIndex] - panning_old_x[ScrnIndex]);
+        lpUpdate->rDest.bottom = lpUpdate->rDest.bottom - (panning_y[ScrnIndex] - panning_old_y[ScrnIndex]);
+    }
+
+    DBG_DD("// UpdateOverlayTV: flags=%08lx, port=%d\n", dwFlags, via->video_dev->minor);
+    DBG_DD("Raw rSrc  X (%ld,%ld) Y (%ld,%ld)\n",
+                lpUpdate->rSrc.left, lpUpdate->rSrc.right, lpUpdate->rSrc.top, lpUpdate->rSrc.bottom);
+    DBG_DD("Raw rDest  X (%ld,%ld) Y (%ld,%ld)\n",
+                lpUpdate->rDest.left, lpUpdate->rDest.right, lpUpdate->rDest.top, lpUpdate->rDest.bottom);
+
+    lpDDPixelFormat->dwFlags = DDPF_FOURCC;
+    lpDDPixelFormat->dwFourCC = FOURCC_YUY2;
+
+    UpdateOverlayTVTemp = * (LPDDUPDATEOVERLAY) lpUpdate;
+
+    dwFlags |= DDOVER_INTERLEAVED;
+
+    // For Alpha windows setting
+    if (gdwAlphaEnabled)
+        dwFlags &= ~DDOVER_KEYDEST;
+
+    Macro_VidREGRec(VIDREGREC_RESET_COUNTER, 0,0);
+
+    // reduce srcHeight for overscan function
+    // to fix underline garbage
+    if (!via->CapInfo.Capture_OverScanOff)
+        lpUpdate->rSrc.bottom -= 6;
+
+    // Set Colorkey if AP requires
+    if ( dwFlags & DDOVER_KEYDEST )
+    {
+        DBG_DD("DDOVER_KEYDEST \n");
+        
+        dwColorKey = 1;
+        dwKeyLow = lpUpdate->dwColorSpaceLowValue;
+    }
+
+    // Overlay the video content into on-screen
+    if (dwFlags & DDOVER_SHOW)
+    {
+        unsigned long dwStartAddr=0, dwDeinterlaceMode=0;
+        unsigned long dwScnWidth, dwScnHeight, dwPitch=0;
+        unsigned long dwRawSrcWidth, dwRawSrcHeight;
+
+        DBG_DD("DDOVER_SHOW \n");
+
+        //for SW decode HW overlay, no HQV, SW flip use
+        dwStartAddr = overlayRecordV1.dwStartAddr;
+        DBG_DD("dwStartAddr= 0x%lx\n", dwStartAddr);
+
+        if (dwFlags & DDOVER_INTERLEAVED)
+        {
+            dwDeinterlaceMode |= DDOVER_INTERLEAVED;
+            DBG_DD("DDOVER_INTERLEAVED\n");
+        }
+        if (dwFlags & DDOVER_BOB)
+        {
+            dwDeinterlaceMode |= DDOVER_BOB;
+            DBG_DD("DDOVER_BOB\n");
+        }
+
+        if ( ((gVIAGraphicInfo.Screen[0].dwWidth > 1024)) || (gVIAGraphicInfo.SAMM) )
+        {
+            gdwUseExtendedFIFO = 1;
+        }
+        else
+        {
+            gdwUseExtendedFIFO = 0;
+        }
+
+        //
+        // Figure out actual rSrc rectangle
+        // Coz the Src rectangle AP sent is always original, ex:size(720,480) at (0,0)
+        // so the driver need to re-calc once
+        // 
+        
+        // transfer unsigned long to signed int for calc
+        nDstLeft = lpUpdate->rDest.left;
+        nDstTop  = lpUpdate->rDest.top;
+        nDstRight= lpUpdate->rDest.right;
+        nDstBottom=lpUpdate->rDest.bottom;
+
+        // Screen width & height
+        dwScnWidth  = gVIAGraphicInfo.Screen[ScrnIndex].dwWidth;
+        dwScnHeight = gVIAGraphicInfo.Screen[ScrnIndex].dwHeight;
+
+        // the original width & height AP sent
+        dwRawSrcWidth = lpUpdate->rSrc.right-lpUpdate->rSrc.left;
+        dwRawSrcHeight = lpUpdate->rSrc.bottom-lpUpdate->rSrc.top;
+
+        if (nDstLeft<0)
+            lpUpdate->rSrc.left  = (((-nDstLeft) * dwRawSrcWidth) + ((nDstRight-nDstLeft)>>1)) / (nDstRight-nDstLeft);
+        else 
+            lpUpdate->rSrc.left = 0;
+
+        if (nDstRight>dwScnWidth)
+            lpUpdate->rSrc.right = (((dwScnWidth-nDstLeft) * dwRawSrcWidth) + ((nDstRight-nDstLeft)>>1)) / (nDstRight-nDstLeft);
+        else    
+            lpUpdate->rSrc.right = dwRawSrcWidth;
+
+        if (nDstTop<0)
+        {
+           lpUpdate->rSrc.top   =  (((-nDstTop) * dwRawSrcHeight) + ((nDstBottom-nDstTop)>>1))/ (nDstBottom-nDstTop);
+           nTopBak = (-nDstTop);
+        }
+        else
+           lpUpdate->rSrc.top   = 0;
+
+        if (nDstBottom >dwScnHeight)
+            lpUpdate->rSrc.bottom = (((dwScnHeight-nDstTop) * dwRawSrcHeight) + ((nDstBottom-nDstTop)>>1)) / (nDstBottom-nDstTop);
+        else 
+            lpUpdate->rSrc.bottom = dwRawSrcHeight;
+        
+        if ( via->video_dev->minor == 0 )
+        {
+            // save src & dest rectangle param.
+            if ( gVIAGraphicInfo.Screen[ScrnIndex].dwPanning )
+            {
+                CAPDevice[0].gdwCAPDstLeft     = lpUpdate->rDest.left + (panning_x[ScrnIndex] - panning_old_x[ScrnIndex]);
+                CAPDevice[0].gdwCAPDstTop      = lpUpdate->rDest.top + (panning_y[ScrnIndex] - panning_old_y[ScrnIndex]);                
+            }
+            else 
+            {
+                CAPDevice[0].gdwCAPDstLeft     = lpUpdate->rDest.left;
+                CAPDevice[0].gdwCAPDstTop      = lpUpdate->rDest.top;                
+            }                
+            CAPDevice[0].gdwCAPDstWidth    = lpUpdate->rDest.right - lpUpdate->rDest.left;
+            CAPDevice[0].gdwCAPDstHeight   = lpUpdate->rDest.bottom - lpUpdate->rDest.top;
+
+            if (gVIAGraphicInfo.Cap0_SwitchToV3)
+            {
+            	CAPDevice[0].gdwCAPSrcWidth    = overlayRecordV3.dwV1SrcWidth = lpUpdate->rSrc.right - lpUpdate->rSrc.left;
+                CAPDevice[0].gdwCAPSrcHeight   = overlayRecordV3.dwV1SrcHeight = lpUpdate->rSrc.bottom - lpUpdate->rSrc.top;
+                overlayRecordV3.dwV1SrcLeft   = lpUpdate->rSrc.left;
+                overlayRecordV3.dwV1SrcRight  = lpUpdate->rSrc.right;
+                overlayRecordV3.dwV1SrcTop    = lpUpdate->rSrc.top;
+                overlayRecordV3.dwV1SrcBot    = lpUpdate->rSrc.bottom;
+            }
+            else
+            {
+            CAPDevice[0].gdwCAPSrcWidth    = overlayRecordV1.dwV1SrcWidth = lpUpdate->rSrc.right - lpUpdate->rSrc.left;
+            CAPDevice[0].gdwCAPSrcHeight   = overlayRecordV1.dwV1SrcHeight = lpUpdate->rSrc.bottom - lpUpdate->rSrc.top;
+            overlayRecordV1.dwV1SrcLeft   = lpUpdate->rSrc.left;
+            overlayRecordV1.dwV1SrcRight  = lpUpdate->rSrc.right;
+            overlayRecordV1.dwV1SrcTop    = lpUpdate->rSrc.top;
+            overlayRecordV1.dwV1SrcBot    = lpUpdate->rSrc.bottom;
+            }
+        }
+        else
+        {
+            // save src & dest rectangle param.
+            if ( gVIAGraphicInfo.Screen[ScrnIndex].dwPanning )
+            {
+                CAPDevice[1].gdwCAPDstLeft     = lpUpdate->rDest.left + (panning_x[ScrnIndex] - panning_old_x[ScrnIndex]);
+                CAPDevice[1].gdwCAPDstTop      = lpUpdate->rDest.top + (panning_y[ScrnIndex] - panning_old_y[ScrnIndex]);
+            }
+            else 
+            {
+                CAPDevice[1].gdwCAPDstLeft     = lpUpdate->rDest.left;
+                CAPDevice[1].gdwCAPDstTop      = lpUpdate->rDest.top;
+            }
+            CAPDevice[1].gdwCAPDstWidth    = lpUpdate->rDest.right - lpUpdate->rDest.left;
+            CAPDevice[1].gdwCAPDstHeight   = lpUpdate->rDest.bottom - lpUpdate->rDest.top;
+
+            CAPDevice[1].gdwCAPSrcWidth    = overlayRecordV3.dwV1SrcWidth = lpUpdate->rSrc.right - lpUpdate->rSrc.left;
+            CAPDevice[1].gdwCAPSrcHeight   = overlayRecordV3.dwV1SrcHeight = lpUpdate->rSrc.bottom - lpUpdate->rSrc.top;
+            //CAPDevice[1].gdwCAPSrcWidth    = overlayRecordV1.dwV1SrcWidth = lpUpdate->rSrc.right - lpUpdate->rSrc.left;
+            //CAPDevice[1].gdwCAPSrcHeight   = overlayRecordV1.dwV1SrcHeight = lpUpdate->rSrc.bottom - lpUpdate->rSrc.top;
+
+            overlayRecordV3.dwV1SrcLeft   = lpUpdate->rSrc.left;
+            overlayRecordV3.dwV1SrcRight  = lpUpdate->rSrc.right;
+            overlayRecordV3.dwV1SrcTop    = lpUpdate->rSrc.top;
+            overlayRecordV3.dwV1SrcBot    = lpUpdate->rSrc.bottom;
+            //overlayRecordV1.dwV1SrcLeft   = lpUpdate->rSrc.left;
+            //overlayRecordV1.dwV1SrcRight  = lpUpdate->rSrc.right;
+            //overlayRecordV1.dwV1SrcTop    = lpUpdate->rSrc.top;
+            //overlayRecordV1.dwV1SrcBot    = lpUpdate->rSrc.bottom;
+        }
+
+        //
+        // Figure out actual rDest rectangle
+        //
+        lpUpdate->rDest.left= nDstLeft<0 ? 0 : nDstLeft;
+        lpUpdate->rDest.top= nDstTop<0 ? 0 : nDstTop;
+        if ( lpUpdate->rDest.top >= dwScnHeight)
+           lpUpdate->rDest.top = dwScnHeight-1;
+        //lpUpdate->rDest.top= top>=dwScnHeight   ? dwScnHeight-1: top;
+        lpUpdate->rDest.right= nDstRight>dwScnWidth ? dwScnWidth: nDstRight;
+        lpUpdate->rDest.bottom= nDstBottom>dwScnHeight ? dwScnHeight: nDstBottom;
+
+        if ( via->video_dev->minor == 0 )
+        {
+            if (gVIAGraphicInfo.Cap0_SwitchToV3)
+            {
+                overlayRecordV3.dwWidth=lpUpdate->rDest.right-lpUpdate->rDest.left;
+                overlayRecordV3.dwHeight=lpUpdate->rDest.bottom-lpUpdate->rDest.top;
+            }
+            else
+            {
+            overlayRecordV1.dwWidth=lpUpdate->rDest.right-lpUpdate->rDest.left;
+            overlayRecordV1.dwHeight=lpUpdate->rDest.bottom-lpUpdate->rDest.top;
+            }
+        }
+        else
+        {
+            overlayRecordV3.dwWidth=lpUpdate->rDest.right-lpUpdate->rDest.left;
+            overlayRecordV3.dwHeight=lpUpdate->rDest.bottom-lpUpdate->rDest.top;
+            //overlayRecordV1.dwWidth=lpUpdate->rDest.right-lpUpdate->rDest.left;
+            //overlayRecordV1.dwHeight=lpUpdate->rDest.bottom-lpUpdate->rDest.top;
+        }
+
+        if ( via->video_dev->minor == 0 )
+        {
+            DBG_DD("    Updateoverlay TV0\n");
+            dwVideoFlag = gdwVideoFlagTV0;
+
+            dwPitch=lpCAPDevice0->dwPitch;
+            
+            //if ( (lpVideoControl->Cap1OnScreen1 == 1) && (lpVideoControl->Cap0OnScreen1 == 0) )
+            if ( (lpVideoControl->VideoStatus & CAP1_ON_SND) && !(lpVideoControl->VideoStatus & CAP0_ON_SND) )
+            {
+                dwVideoFlag = dwVideoFlag & ~VIDEO_1_INUSE;
+                dwVideoFlag = dwVideoFlag | VIDEO_3_INUSE;  
+            }
+
+            //if (lpVideoControl->Cap1OnScreen1 == 1)
+            if ( lpVideoControl->VideoStatus & CAP1_ON_SND )     
+            {
+                //if ( (lpVideoControl->Cap0OnScreen1 == 1) )//&& (gdwVideoFlagTV0Temp & VIDEO_1_INUSE) )
+                if ( lpVideoControl->VideoStatus & CAP0_ON_SND )     
+                {
+                    dwVideoFlag = dwVideoFlag & ~VIDEO_SHOW;
+                    DBG_DD("    Updateoverlay TV0: Capture 0 Hide !!!! \n");
+                }
+                if (!(gdwVideoFlagTV1 & VIDEO_HQV_INUSE))
+                {
+                    dwVideoFlag = dwVideoFlag | VIDEO_HQV_INUSE;
+                }
+            }
+            
+/*            if (Upd_Capture0(dwVideoFlag,dwStartAddr,lpUpdate->rSrc,lpUpdate->rDest,dwPitch,
+                overlayRecordV1.dwV1OriWidth,overlayRecordV1.dwV1OriHeight,lpDDPixelFormat,
+                //overlayRecordV3.dwV1OriWidth,overlayRecordV3.dwV1OriHeight,lpDDPixelFormat,
+                dwDeinterlaceMode,dwColorKey,dwChromaKey,
+                dwKeyLow,dwKeyHigh,dwChromaLow,dwChromaHigh,dwFlags)== PI_ERR)
+            {
+                return PI_ERR;                    
+            }*/
+
+            if (gVIAGraphicInfo.Cap0_SwitchToV3)        //TV0 - V3 - Capture0 (for SAMSUNG)
+                lpoverlayTVRecord = &overlayRecordV3;
+            else                                        //TV0 - V1 - Capture0 (Port0)
+                lpoverlayTVRecord = &overlayRecordV1;
+            
+            if (Upd_Capture0(dwVideoFlag,dwStartAddr,lpUpdate->rSrc,lpUpdate->rDest,dwPitch,
+                lpoverlayTVRecord->dwV1OriWidth,lpoverlayTVRecord->dwV1OriHeight,lpDDPixelFormat,
+                dwDeinterlaceMode,dwColorKey,dwChromaKey,
+                dwKeyLow,dwKeyHigh,dwChromaLow,dwChromaHigh,dwFlags)== PI_ERR)
+            {
+                return PI_ERR;                    
+            }
+
+            Macro_VidREGRec(VIDREGREC_RESET_COUNTER, 0,0);
+
+            if ( ScreenSwitch(Position_W_Temp1, Position_W_Temp2, Position_H_Temp1, Position_H_Temp2) )
+            {    
+                //if ( (gdwVideoFlagTV1 != 0) && (lpVideoControl->Cap1OnScreen1 == 0) )
+                if ( (gdwVideoFlagTV1 != 0) && !(lpVideoControl->VideoStatus & CAP1_ON_SND) )
+                {
+                    dwVideoFlag = gdwVideoFlagTV1;
+                    dwPitch=lpCAPDevice1->dwPitch;
+
+                    if (Upd_Capture1(dwVideoFlag,dwStartAddr,UpdateOverlayTV1Backup.rSrc,UpdateOverlayTV1Backup.rDest,dwPitch,
+                        //overlayRecordV1.dwV1OriWidth,overlayRecordV1.dwV1OriHeight,lpDDPixelFormat,
+                        overlayRecordV3.dwV1OriWidth,overlayRecordV3.dwV1OriHeight,lpDDPixelFormat,
+                        dwDeinterlaceMode,dwColorKey,dwChromaKey,
+                        dwKeyLow,dwKeyHigh,dwChromaLow,dwChromaHigh,dwFlags)== PI_ERR)
+                    {
+                        return PI_ERR;                    
+                    }
+                }
+                
+                /*if ( (gdwVideoFlagMPEG != 0) && (lpVideoControl->MPEGOnScreen1 == 0) )*/
+                if ( (gdwVideoFlagMPEG != 0) && !(lpVideoControl->VideoStatus & MPEG_ON_SND) )
+                {
+                    UpdateOverlay(&UpdateOverlayBackup);
+                }
+            } 
+
+            UpdateOverlayTV0Backup  = UpdateOverlayTVTemp;
+            TV0_ON = TRUE;
+        }
+        else if ( via->video_dev->minor == 1 )
+        {
+            DBG_DD("    Updateoverlay TV1\n");
+            dwVideoFlag = gdwVideoFlagTV1;
+
+            dwPitch=lpCAPDevice1->dwPitch;
+            
+            //if ( lpVideoControl->Cap1OnScreen1 )
+            if ( lpVideoControl->VideoStatus & CAP1_ON_SND )
+            {
+                //if ( (lpVideoControl->Cap0OnScreen1) || (!lpVideoControl->MPEGOnScreen1) )
+                if ( (lpVideoControl->VideoStatus & CAP0_ON_SND) || (lpVideoControl->VideoStatus & MPEG_ON_SND))
+                {
+                    dwVideoFlag = dwVideoFlag & ~VIDEO_SHOW;
+                    DBG_DD("    Updateoverlay TV0: Capture 0 Hide !!!! \n");
+                }
+                else
+                {
+                    dwVideoFlag = dwVideoFlag | VIDEO_1_INUSE;// | VIDEO_HQV_INUSE;
+                }
+            }
+            else 
+            {
+//              if ( lpVideoControl->Cap0OnScreen1 == 1 )
+//              {
+//                  dwVideoFlag = dwVideoFlag & ~VIDEO_HQV_INUSE;
+//              }
+                dwVideoFlag = dwVideoFlag & ~VIDEO_1_INUSE;
+                dwVideoFlag = dwVideoFlag | VIDEO_3_INUSE;
+            }
+
+
+            if (Upd_Capture1(dwVideoFlag,dwStartAddr,lpUpdate->rSrc,lpUpdate->rDest,dwPitch,
+                overlayRecordV3.dwV1OriWidth,overlayRecordV3.dwV1OriHeight,lpDDPixelFormat,
+                //overlayRecordV1.dwV1OriWidth,overlayRecordV1.dwV1OriHeight,lpDDPixelFormat,
+                dwDeinterlaceMode,dwColorKey,dwChromaKey,
+                dwKeyLow,dwKeyHigh,dwChromaLow,dwChromaHigh,dwFlags)== PI_ERR)
+            {
+                return PI_ERR;                    
+            }
+
+            if ( ScreenSwitch(Position_W_Temp1, Position_W_Temp2, Position_H_Temp1, Position_H_Temp2) )
+            {    
+                //if ( (gdwVideoFlagTV0 != 0) && (lpVideoControl->Cap1OnScreen1 == 1) )
+                if ( (gdwVideoFlagTV0 != 0) && (lpVideoControl->VideoStatus & CAP1_ON_SND) )                
+                {
+                    dwVideoFlag = gdwVideoFlagTV0;
+                    //dwVideoFlag = dwVideoFlag & ~VIDEO_HQV_INUSE & ~VIDEO_1_INUSE;
+                    dwVideoFlag = dwVideoFlag & ~VIDEO_1_INUSE;
+                    dwVideoFlag = dwVideoFlag | VIDEO_3_INUSE; 
+                    dwPitch=lpCAPDevice1->dwPitch;
+                    
+/*                    if (Upd_Capture0(dwVideoFlag,dwStartAddr,UpdateOverlayTV0Backup.rSrc,UpdateOverlayTV0Backup.rDest,dwPitch,
+                        //overlayRecordV3.dwV1OriWidth,overlayRecordV3.dwV1OriHeight,lpDDPixelFormat,
+                        overlayRecordV1.dwV1OriWidth,overlayRecordV1.dwV1OriHeight,lpDDPixelFormat,
+                        dwDeinterlaceMode,dwColorKey,dwChromaKey,
+                        dwKeyLow,dwKeyHigh,dwChromaLow,dwChromaHigh,dwFlags)== PI_ERR)
+                    {
+                        return PI_ERR;                    
+                    }*/
+                    if (Upd_Capture0(dwVideoFlag,dwStartAddr,lpUpdate->rSrc,lpUpdate->rDest,dwPitch,
+                        lpoverlayTVRecord->dwV1OriWidth,lpoverlayTVRecord->dwV1OriHeight,lpDDPixelFormat,
+                        dwDeinterlaceMode,dwColorKey,dwChromaKey,
+                        dwKeyLow,dwKeyHigh,dwChromaLow,dwChromaHigh,dwFlags)== PI_ERR)
+                    {
+                        return PI_ERR;                    
+                    }
+                }
+                
+                //if ( (gdwVideoFlagTV0 != 0) && (lpVideoControl->Cap1OnScreen1 == 0) )
+                if ( (gdwVideoFlagTV0 != 0) && !(lpVideoControl->VideoStatus & CAP1_ON_SND) )
+                {
+                    dwVideoFlag = gdwVideoFlagTV0;
+                    //dwVideoFlag = dwVideoFlag & ~VIDEO_HQV_INUSE & ~VIDEO_1_INUSE;
+                    //dwVideoFlag = dwVideoFlag | VIDEO_3_INUSE; 
+                    dwPitch=lpCAPDevice1->dwPitch;                
+
+/*                    if (Upd_Capture0(dwVideoFlag,dwStartAddr,UpdateOverlayTV0Backup.rSrc,UpdateOverlayTV0Backup.rDest,dwPitch,
+                        //overlayRecordV3.dwV1OriWidth,overlayRecordV3.dwV1OriHeight,lpDDPixelFormat,
+                        overlayRecordV1.dwV1OriWidth,overlayRecordV1.dwV1OriHeight,lpDDPixelFormat,
+                        dwDeinterlaceMode,dwColorKey,dwChromaKey,
+                        dwKeyLow,dwKeyHigh,dwChromaLow,dwChromaHigh,dwFlags)== PI_ERR)
+                    {
+                        return PI_ERR;                    
+                    }*/    
+                    if (Upd_Capture0(dwVideoFlag,dwStartAddr,lpUpdate->rSrc,lpUpdate->rDest,dwPitch,
+                        lpoverlayTVRecord->dwV1OriWidth,lpoverlayTVRecord->dwV1OriHeight,lpDDPixelFormat,
+                        dwDeinterlaceMode,dwColorKey,dwChromaKey,
+                        dwKeyLow,dwKeyHigh,dwChromaLow,dwChromaHigh,dwFlags)== PI_ERR)
+                    {
+                        return PI_ERR;                    
+                    }
+                }
+                
+                /*if ( (gdwVideoFlagMPEG != 0) && (lpVideoControl->MPEGOnScreen1 == 0) )
+                {
+                    UpdateOverlay(&UpdateOverlayBackup);
+                }*/
+            }
+
+            UpdateOverlayTV1Backup  = UpdateOverlayTVTemp;
+            TV1_ON = TRUE;
+        }
+
+        // gdwVideoOn = 1;  /* Use TV1_ON, TV0_ON, MPEG_ON to replace */
+
+        return PI_OK;
+        
+    } //end of DDOVER_SHOW
+
+    panning_old_x[ScrnIndex] = panning_x[ScrnIndex];
+    panning_old_y[ScrnIndex] = panning_y[ScrnIndex];
+
+    return PI_OK;
+} //UpdateOverlayTV
+
+/****************************************************************************
+ *
+ * Upd_Capture0()
+ *
+ ***************************************************************************/
+unsigned long Upd_Capture0(unsigned long dwVideoFlag,unsigned long dwStartAddr,RECTL rSrc,RECTL rDest,unsigned long dwSrcPitch,
+                 unsigned long dwOriSrcWidth,unsigned long dwOriSrcHeight,LPDDPIXELFORMAT lpDPFsrc,
+                 unsigned long dwDeinterlaceMode,unsigned long dwColorKey,unsigned long dwChromaKey,
+                 unsigned long dwKeyLow,unsigned long dwKeyHigh,unsigned long dwChromaLow,unsigned long dwChromaHigh,unsigned long dwFlags)
+{
+    //unsigned long dwVidCtl=0, dwCompose=(VIDInD(V_COMPOSE_MODE)&~(SELECT_VIDEO_IF_COLOR_KEY|V1_COMMAND_FIRE|V3_COMMAND_FIRE))|V_COMMAND_LOAD_VBI;
+    unsigned long dwVidCtl=0, dwCompose=(VIDInD(V_COMPOSE_MODE)&~(SELECT_VIDEO_IF_COLOR_KEY|V1_COMMAND_FIRE|V3_COMMAND_FIRE));
+    //unsigned long dwVidCtl=0, dwCompose=0;
+    unsigned long srcWidth, srcHeight,dstWidth,dstHeight;
+    unsigned long zoomCtl=0, miniCtl=0;
+    unsigned long dwHQVCtl=0;
+    unsigned long dwHQVfilterCtl=0,dwHQVminiCtl=0;
+    unsigned long dwHQVzoomflagH=0,dwHQVzoomflagV=0;
+    unsigned long dwHQVsrcWidth=0,dwHQVdstWidth=0;
+    unsigned long dwHQVsrcFetch = 0,dwHQVoffset=0;
+    unsigned long dwOffset=0,dwFetch=0,dwTmp=0;
+    unsigned long dwDisplayCountW=0;
+    unsigned long dwShift=0;
+    via_device *via = NULL;
+    LPVIDHWDIFFERENCE lpVideoHWDifference = &VideoHWDifference;
+
+    /*Added for SAMM expand Mode*/
+    unsigned long dstModifiedWidth=0,dstModifiedHeight=0;
+
+    /*Added for SAMM Mode*/
+    int ScrnIndex = 0;
+    if (dwFlags & DDOVER_ON_SND)
+    {
+        ScrnIndex = 1;
+    }    
+
+    /* 2003/10/06 Fix bug */
+    /* If Capture1 (or Capture0) has no video decoder(ex:SAA7113,SAA8108...) */
+    /* then run XawTV ./tv1 (or ./tv0), the system will hang */
+    if (dwVideoFlag & VIDEO_1_INUSE)
+    {
+        dwCompose |= V_COMMAND_LOAD_VBI;
+    }
+    else
+    {
+        if (gVIAGraphicInfo.RevisionID >= VIA_REVISION_CLECX)
+        {
+            dwCompose |= V3_COMMAND_LOAD_VBI;
+        }
+    }
+
+    /* to determine to use device video0 or video1 */
+    via = &via_v4l_devices[0];
+/*    if (dwVideoFlag & VIDEO_1_INUSE)
+    {
+        via = &via_v4l_devices[0];    //Capture0 + V1 -- /dev/video0
+        DBG_DD("//Upd_Capture0: Capture0 + V1 -- /dev/video0\n");
+    }
+    else
+    {
+        if (gVIAGraphicInfo.Cap0_SwitchToV3)        //TV0 - V3 - Capture0 (for SAMSUNG)
+        {
+            via = &via_v4l_devices[0];    //Capture0 + V3 -- /dev/video0
+            DBG_DD("//Upd_Capture0: Capture0 + V3 -- /dev/video0\n");
+        }
+        else
+        {
+        via = &via_v4l_devices[1];    //Capture1 + V3 -- /dev/video1
+            DBG_DD("//Upd_Capture0: Capture1 + V3 -- /dev/video1\n");
+        }
+    }*/
+    // V1 srcHeight-5 to fix V1 engine zoom control bug
+    // 
+    // rSrc.bottom -= 6;
+
+    DBG_DD("//Upd_Capture0: dwCompose = %8lx\n", dwCompose);
+    DBG_DD("Modified rSrc  X (%ld,%ld) Y (%ld,%ld)\n",
+                rSrc.left, rSrc.right,rSrc.top, rSrc.bottom);
+    DBG_DD("Modified rDest  X (%ld,%ld) Y (%ld,%ld)\n",
+                rDest.left, rDest.right,rDest.top, rDest.bottom);
+
+    if (dwVideoFlag & VIDEO_SHOW)    
+    {
+        // Set Alpha windows position
+        //Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_ALPHA_WIN_END, (((rDest.left)+(ALPDevice.gdwALPDstWidth)) <<16) | ((rDest.top)+(ALPDevice.gdwALPDstHeight)) );
+        //Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_ALPHA_WIN_START, (rDest.left<<16) | rDest.top );
+
+        // Setup video & HQV control registers
+        if (dwVideoFlag & VIDEO_1_INUSE)
+        {
+            if (dwVideoFlag & VIDEO_HQV_INUSE)    
+            {
+                DBG_DD(" !!!!!!!!!!!!!!!!!!!!!!! Upd_Capture0 + V1: HQV_INUSE !!\n");
+                //lpVideoControl->CAP0_V1_HQV_ENABLE = 1;
+                
+                /*=* Modify for C1 FIFO *=*/
+                switch ( DispatchVGARevisionID() )
+                {
+                    case VIA_REVISION_CLECX :
+                        dwVidCtl =  V1_COLORSPACE_SIGN | V1_SWAP_HW_HQV |
+                                        V1_EXPIRE_NUM_F | V1_YUV422;
+                        break;
+                        
+                    default:
+                        if (gdwUseExtendedFIFO)
+                        {
+                            dwVidCtl =  V1_COLORSPACE_SIGN | V1_SWAP_HW_HQV |
+                                        V1_EXPIRE_NUM_A | V1_FIFO_EXTENDED | V1_YUV422;
+                                }
+                        else
+                        {
+                            dwVidCtl =  V1_COLORSPACE_SIGN | V1_SWAP_HW_HQV |
+                                        V1_EXPIRE_NUM | V1_YUV422;
+                        }
+                        break;
+                }
+
+                if (via->CapInfo.dwDeinterlaceMode & VIA_DEINTERLACE_BOB)
+                {
+                    dwHQVCtl = HQV_SRC_CAPTURE0|HQV_YUV422|
+                               HQV_DEINTERLACE|HQV_FIELD_2_FRAME| /* field source, deinterlace bob mode */
+                               HQV_ENABLE;
+                }
+                else
+                {
+                    dwHQVCtl = HQV_SRC_CAPTURE0|HQV_YUV422|HQV_ENABLE;
+                }
+
+            }
+            else
+            {
+                DBG_DD(" !!!!!!!!!!!!!!!!!!!!!!! Upd_Capture0 + V1: NO_HQV !!\n");
+                
+                /*=* Modify for C1 FIFO *=*/
+                switch ( DispatchVGARevisionID() )
+                {
+                    case VIA_REVISION_CLECX :
+                        dwVidCtl =  V1_COLORSPACE_SIGN | V1_SWAP_HW_CAPTURE |
+                                    V1_EXPIRE_NUM_F | V1_YUV422;
+                        break;
+                        
+                    default:
+                        if (gdwUseExtendedFIFO)
+                        {
+                            dwVidCtl =  V1_COLORSPACE_SIGN | V1_SWAP_HW_CAPTURE |
+                                        V1_EXPIRE_NUM_A | V1_FIFO_EXTENDED | V1_YUV422;
+                        }                   
+                        else
+                        {
+                            dwVidCtl =  V1_COLORSPACE_SIGN | V1_SWAP_HW_CAPTURE |
+                                        V1_EXPIRE_NUM | V1_YUV422;
+                        }
+                        break;
+                }
+            }
+        }
+        else
+        {
+            if (dwVideoFlag & VIDEO_HQV_INUSE)    
+            {
+                DBG_DD(" !!!!!!!!!!!!!!!!!!!!!!! Upd_Capture0 + V3: HQV_INUSE !!\n");
+                
+                /*=* Modify for C1 FIFO *=*/
+                switch ( DispatchVGARevisionID() )
+                {
+                    case VIA_REVISION_CLECX :
+                        dwVidCtl =  V3_COLORSPACE_SIGN | V3_SWAP_HW_HQV |
+                                    V3_EXPIRE_NUM_F | V3_YUV422;
+                        break;
+                        
+                    default:
+                        dwVidCtl =  V3_COLORSPACE_SIGN | V3_SWAP_HW_HQV |
+                                    V3_EXPIRE_NUM | V3_YUV422;
+                        break;
+                }   
+                
+                if (via->CapInfo.dwDeinterlaceMode & VIA_DEINTERLACE_BOB)
+                {
+                    dwHQVCtl = HQV_SRC_CAPTURE0|HQV_YUV422|
+                               HQV_DEINTERLACE|HQV_FIELD_2_FRAME| /* field source, deinterlace bob mode */
+                               HQV_ENABLE;
+                }
+                else
+                {
+                if (dwVideoFlag & VIDEO_CAPTURE0_INUSE)
+                {
+                    dwHQVCtl = HQV_SRC_CAPTURE0|HQV_YUV422|HQV_ENABLE;
+                }
+                else
+                {
+                        if(gVIAGraphicInfo.Cap1_UseIRQ)       // Capture 1 use IRQ, for Cap1 S/W flip
+                            dwHQVCtl = HQV_SRC_SW|HQV_YUV422|HQV_ENABLE;    
+                        else
+                    dwHQVCtl = HQV_SRC_CAPTURE1|HQV_YUV422|HQV_ENABLE;
+                }
+            }
+            }
+            else
+            {
+                DBG_DD(" !!!!!!!!!!!!!!!!!!!!!!! Upd_Capture0 + V3: NO_HQV !!\n");
+                
+                /*=* Modify for C1 FIFO *=*/
+                switch ( DispatchVGARevisionID() )
+                {
+                    case VIA_REVISION_CLECX :
+                        if (dwVideoFlag & VIDEO_CAPTURE0_INUSE)
+                        {
+                            dwVidCtl =  V3_COLORSPACE_SIGN | V3_FLIP_HW_CAPTURE0 |
+                                        V3_EXPIRE_NUM_F | V3_YUV422;                
+                        }
+                        else
+                        {
+                            dwVidCtl =  V3_COLORSPACE_SIGN | V3_FLIP_HW_CAPTURE1 |
+                                        V3_EXPIRE_NUM_F | V3_YUV422;                
+                        }
+                        break;
+                        
+                    default:
+                        if (dwVideoFlag & VIDEO_CAPTURE0_INUSE)
+                        {
+                            dwVidCtl =  V3_COLORSPACE_SIGN | V3_FLIP_HW_CAPTURE0 |
+                                        V3_EXPIRE_NUM | V3_YUV422;                
+                        }
+                        else
+                        {
+                            dwVidCtl =  V3_COLORSPACE_SIGN | V3_FLIP_HW_CAPTURE1 |
+                                        V3_EXPIRE_NUM | V3_YUV422;                
+                        }
+                        break;
+                }
+            }
+        }
+
+        if ( lpVideoHWDifference->dwThreeHQVBuffer )    //CLE_C0
+        {
+            //HQV support 3 HQV buffer       
+            dwHQVCtl &= ~HQV_SW_FLIP;
+            dwHQVCtl |= HQV_TRIPLE_BUFF | HQV_FLIP_STATUS; 
+        }
+
+        if (gVIAGraphicInfo.Cap0_SwitchToV3)        //TV0 - V3 - Capture0 (for SAMSUNG)
+        {
+            overlayRecordV3.dwWidth=dstWidth = rDest.right - rDest.left;
+            overlayRecordV3.dwHeight=dstHeight = rDest.bottom - rDest.top;
+        }
+        else
+        {
+        overlayRecordV1.dwWidth=dstWidth = rDest.right - rDest.left;
+        overlayRecordV1.dwHeight=dstHeight = rDest.bottom - rDest.top;
+        }         
+        srcWidth = (unsigned long)rSrc.right - rSrc.left;
+        srcHeight = (unsigned long)rSrc.bottom - rSrc.top;
+       
+        /*Added for SAMM expand Mode*/
+        /*In SAMM expand, we need adjust x and y position, width and height zoom factor.*/
+        if  ( ((gVIAGraphicInfo.Screen[ScrnIndex].dwDVIOn)||(gVIAGraphicInfo.Screen[ScrnIndex].dwLCDOn))
+              &&(gVIAGraphicInfo.Screen[ScrnIndex].dwExpand) )
+        {
+            dstModifiedWidth=dstWidth*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelWidth)/
+                             (gVIAGraphicInfo.Screen[ScrnIndex].dwWidth)+1;
+            dstModifiedHeight=dstHeight*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelHeight)/
+                              (gVIAGraphicInfo.Screen[ScrnIndex].dwHeight)+1;
+            DBG_DD("===Expand!! \n");
+        }
+        else
+        {
+            dstModifiedWidth=dstWidth;
+            dstModifiedHeight=dstHeight;
+        }
+        DBG_DD("===dstModifiedWidth= %ld \n", dstModifiedWidth);
+        DBG_DD("===dstModifiedHeight= %ld \n", dstModifiedHeight);
+       
+
+        if (dwVideoFlag & VIDEO_HQV_INUSE)
+        {
+            //dwPitch -1 to hide the noise dot in the left down corner
+            //dwHeight -1 to hide green line in the bottom
+            
+            if ( lpVideoHWDifference->dwHQVFetchByteUnit )     // CLE_C0
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, HQV_SRC_FETCH_LINE, (((CAPDevice[0].dwPitch)-1)<<16)|(dwOriSrcHeight-1));
+            else
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, HQV_SRC_FETCH_LINE, (((CAPDevice[0].dwPitch>>3)-1)<<16)|(dwOriSrcHeight-1));
+                
+            //Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, HQV_SRC_STRIDE, ((CAPDevice[0].dwPitch>>1)<<16)|CAPDevice[0].dwPitch);
+            //Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, HQV_DST_STRIDE, CAPDevice[0].dwPitch);
+        }
+
+        // Setup X zoom factor
+        if (gVIAGraphicInfo.Cap0_SwitchToV3)        //TV0 - V3 - Capture0 (for SAMSUNG)
+            overlayRecordV3.dwFetchAlignment = 0;
+        else
+        overlayRecordV1.dwFetchAlignment = 0;
+
+        //Fixed for SAMM expand Mode
+        //if ( DDOVER_HQVCalcZoomWidth(dwVideoFlag, srcWidth , dstWidth,
+        //                          &zoomCtl, &miniCtl, &dwHQVfilterCtl, &dwHQVminiCtl,&dwHQVzoomflagH) == PI_ERR )
+        if ( DDOVER_HQVCalcZoomWidth(dwVideoFlag, srcWidth , dstModifiedWidth,
+                                  &zoomCtl, &miniCtl, &dwHQVfilterCtl, &dwHQVminiCtl,&dwHQVzoomflagH) == PI_ERR )
+        {
+            // too small to handle
+            dwFetch <<= 20;
+            if (dwVideoFlag & VIDEO_1_INUSE)    
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V12_QWORD_PER_LINE, dwFetch);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_COMPOSE_MODE , dwCompose|V1_COMMAND_FIRE );
+            }
+            else
+            {
+                dwFetch |=(VIDInD(V3_ALPHA_QWORD_PER_LINE)&(~V3_FETCH_COUNT));
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_ALPHA_QWORD_PER_LINE, dwFetch);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_COMPOSE_MODE , dwCompose|V3_COMMAND_FIRE );
+                
+            }
+            Macro_VidREGFlush();
+            return PI_ERR;
+        }
+
+        DDOver_GetDisplayCount(dwVideoFlag,lpDPFsrc,srcWidth,&dwDisplayCountW);
+        // Setup position
+        if (dwVideoFlag & VIDEO_1_INUSE)    
+        {
+            /*Fixed for SAMM expand Mode*/
+            if  ( ((gVIAGraphicInfo.Screen[ScrnIndex].dwDVIOn)||(gVIAGraphicInfo.Screen[ScrnIndex].dwLCDOn))
+                  &&(gVIAGraphicInfo.Screen[ScrnIndex].dwExpand) )
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_WIN_END_Y,
+                                 (((rDest.right-1)*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelWidth)/
+                                  (gVIAGraphicInfo.Screen[ScrnIndex].dwWidth)) <<16) +
+                                 (rDest.bottom*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelHeight)/
+                                  (gVIAGraphicInfo.Screen[ScrnIndex].dwHeight)) );                             
+                
+                if (rDest.top > 0)
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_WIN_START_Y,
+                                     ((rDest.left*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelWidth)/
+                                      (gVIAGraphicInfo.Screen[ScrnIndex].dwWidth)) <<16 ) + 
+                                     (rDest.top*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelHeight)/
+                                      (gVIAGraphicInfo.Screen[ScrnIndex].dwHeight)) );
+                }
+                else
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_WIN_START_Y,
+                                     ((rDest.left*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelWidth)/
+                                     (gVIAGraphicInfo.Screen[ScrnIndex].dwWidth)) <<16) );
+                }                
+                
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_SOURCE_HEIGHT, (srcHeight<<16)|dwDisplayCountW);
+            }
+            else
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_WIN_END_Y, ((rDest.right-1)<<16) + (rDest.bottom-1));
+                if (rDest.top > 0)
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_WIN_START_Y, (rDest.left<<16) + rDest.top );
+                }
+                else 
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_WIN_START_Y, (rDest.left<<16));
+                }
+                
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_SOURCE_HEIGHT, (srcHeight<<16)|dwDisplayCountW);
+            }
+        }
+        else
+        {
+            /*Fixed for SAMM expand Mode*/
+            if  ( ((gVIAGraphicInfo.Screen[ScrnIndex].dwDVIOn)||(gVIAGraphicInfo.Screen[ScrnIndex].dwLCDOn))
+                  &&(gVIAGraphicInfo.Screen[ScrnIndex].dwExpand) )
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_WIN_END_Y,
+                                (((rDest.right-1)*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelWidth)/
+                                 (gVIAGraphicInfo.Screen[ScrnIndex].dwWidth)) <<16) +
+                                (rDest.bottom*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelHeight)/
+                                 (gVIAGraphicInfo.Screen[ScrnIndex].dwHeight)) );         
+                                
+                if (rDest.top > 0)
+                {
+                     Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_WIN_START_Y,
+                                     ((rDest.left*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelWidth)/
+                                      (gVIAGraphicInfo.Screen[ScrnIndex].dwWidth)) <<16 ) + 
+                                     (rDest.top*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelHeight)/
+                                      (gVIAGraphicInfo.Screen[ScrnIndex].dwHeight)) );
+                }
+                else
+                {
+                     Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_WIN_START_Y,
+                                     ((rDest.left*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelWidth)/
+                                     (gVIAGraphicInfo.Screen[ScrnIndex].dwWidth)) <<16) );
+                } 
+                 
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_SOURCE_WIDTH, dwDisplayCountW);                
+            }
+            else
+            {
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_WIN_END_Y, ((rDest.right-1)<<16) + (rDest.bottom-1));
+                if (rDest.top > 0)
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_WIN_START_Y, (rDest.left<<16) + rDest.top );
+                }
+                else 
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_WIN_START_Y, (rDest.left<<16));
+                }
+                
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_SOURCE_WIDTH, dwDisplayCountW);
+        }
+        }
+        
+        //
+        // Setup Y zoom factor
+        //
+
+        //Fixed for SAMM expand Mode
+        //if ( DDOVER_HQVCalcZoomHeight(srcHeight,dstHeight,&zoomCtl,&miniCtl, &dwHQVfilterCtl, &dwHQVminiCtl ,&dwHQVzoomflagV) == PI_ERR )
+        if ( DDOVER_HQVCalcZoomHeight(srcHeight,dstModifiedHeight,&zoomCtl,&miniCtl, &dwHQVfilterCtl, &dwHQVminiCtl ,&dwHQVzoomflagV) == PI_ERR )
+        {
+            if (dwVideoFlag & VIDEO_1_INUSE)    
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_COMPOSE_MODE , dwCompose|V1_COMMAND_FIRE );
+            }
+            else
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_COMPOSE_MODE , dwCompose|V3_COMMAND_FIRE );                
+            }
+            
+            Macro_VidREGFlush();
+            return PI_ERR;
+        }
+/*        
+        if ((gVIAGraphicInfo.NoHQV_VFilter) || (srcHeight==dstHeight))
+        {
+            dwHQVfilterCtl &= 0xfffdffff;
+            DBG_DD("Upd_Capture0 : No Capture 0 HQV Vertical Filter\n");
+        }
+        
+        if ((gVIAGraphicInfo.NoHQV_HFilter) || (srcWidth==dstWidth))
+        {
+            dwHQVfilterCtl &= 0xfffffffd;
+            DBG_DD("Upd_Capture0 : No Capture 0 HQV Horizontal Filter\n");
+        }
+*/        
+        if (gVIAGraphicInfo.HQVFilter_ManualSelect)
+        {
+                switch(gVIAGraphicInfo.CapHQV_VFilterMode)
+                {
+            	    case 0: 
+            	        dwHQVfilterCtl &= 0x0000ffff;
+            	        dwHQVfilterCtl |= 0x00400000;
+                        DBG_DD("Upd_Video : No Capture HQV Vertical Filter\n");
+                        break;
+                        
+                    default:
+                        dwHQVfilterCtl &= 0x0000ffff;
+                        dwHQVfilterCtl |= HQV_V_FILTER_DEFAULT;
+                        DBG_DD("Upd_Video : Capture HQV Vertical Filter mode: FILTER_DEFAULT\n");
+                        break;
+                }
+                
+                switch(gVIAGraphicInfo.CapHQV_HFilterMode)
+                {
+            	    case 0: 
+            	        dwHQVfilterCtl &= 0xffff0000;
+            	        dwHQVfilterCtl |= 0x00000040;
+                        DBG_DD("Upd_Video : No Capture HQV horizontal Filter\n");
+                        break;
+                    
+                    default:
+                        dwHQVfilterCtl &= 0xffff0000;
+                        dwHQVfilterCtl |= HQV_H_FILTER_DEFAULT;
+                        DBG_DD("Upd_Video : Capture HQV horizontalFilter mode: FILTER_DEFAULT\n");
+                        break;
+                }
+        }
+
+        if (dwVideoFlag & VIDEO_1_INUSE)
+        {
+            if (dwVideoFlag & VIDEO_HQV_INUSE)
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, HQV_MINIFY_CONTROL, dwHQVminiCtl);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, HQV_FILTER_CONTROL, dwHQVfilterCtl);
+                dwOffset = DDOver_GetSrcStartAddress (dwVideoFlag,rSrc,rDest,dwSrcPitch,lpDPFsrc,&dwHQVoffset);
+                DBG_DD("dwOffset=%08lx dwHQVoffset=%08lx\n", dwOffset, dwHQVoffset);
+
+                dwHQVsrcWidth=(unsigned long)rSrc.right - rSrc.left;
+                dwHQVdstWidth=(unsigned long)rDest.right - rDest.left;
+                if (dwHQVsrcWidth>dwHQVdstWidth)
+                {
+                    dwOffset = dwHQVoffset;
+                    /* mark dwOffset to fix HQV bug... */
+                    //dwOffset = dwOffset * dwHQVdstWidth / dwHQVsrcWidth;
+                    //dwFetch = ((((dstWidth<<1)>>3)+overlayRecordV1.dwFetchAlignment)&~overlayRecordV1.dwFetchAlignment) << 20;
+                    //Fixed for SAMM expand Mode
+                    //dwFetch = (((((dstWidth<<1)+V1_FETCHCOUNT_ALIGNMENT)&~V1_FETCHCOUNT_ALIGNMENT)>> V1_FETCHCOUNT_UNIT)+1) << 20;
+                    dwFetch = (((((dstModifiedWidth<<1)+V1_FETCHCOUNT_ALIGNMENT)&~V1_FETCHCOUNT_ALIGNMENT)>> V1_FETCHCOUNT_UNIT)+1) << 20;                    
+                }
+                else
+                {
+                    //dwFetch = ((((dwHQVsrcWidth<<1)>>3)+overlayRecordV1.dwFetchAlignment)&~overlayRecordV1.dwFetchAlignment) << 20;
+                    dwFetch = (((((dwHQVsrcWidth<<1)+V1_FETCHCOUNT_ALIGNMENT)&~V1_FETCHCOUNT_ALIGNMENT)>> V1_FETCHCOUNT_UNIT)+1) << 20;
+                }
+
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V12_QWORD_PER_LINE, dwFetch);
+
+                // add 4 pitch shift to avoid noise video on top
+                dwShift = dwSrcPitch * 4;
+                //Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_1, lpCAPDevice0->dwHQVAddr[1]+dwShift+dwOffset);
+                //Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_0, lpCAPDevice0->dwHQVAddr[0]+dwShift+dwOffset);
+                
+                if ( lpVideoHWDifference->dwThreeHQVBuffer )    //CLE_C0
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_2, lpCAPDevice0->dwHQVAddr[2]+dwHQVoffset);
+                        
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_1, lpCAPDevice0->dwHQVAddr[1]+dwHQVoffset);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_0, lpCAPDevice0->dwHQVAddr[0]+dwHQVoffset);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_ALPHA_STARTADDR, ALPDevice.dwALPPhysicalAddr+dwOffset);
+
+                miniCtl=0;
+                if (dwHQVzoomflagH||dwHQVzoomflagV)
+                {
+                    dwTmp = 0;
+                    if (dwHQVzoomflagH)
+                    {
+                        miniCtl = V1_X_INTERPOLY;
+                        dwTmp = (zoomCtl&0xffff0000);
+                    }
+                    
+                    if (dwHQVzoomflagV)
+                    {
+                        miniCtl |= (V1_Y_INTERPOLY | V1_YCBCR_INTERPOLY);
+                        dwTmp |= (zoomCtl&0x0000ffff);
+                    }
+                    
+                    //Temporarily fix for 2D bandwidth problem. 2002/08/01
+                    if ((gdwUseExtendedFIFO))
+                    {
+                        miniCtl &= ~V1_Y_INTERPOLY;
+                    }
+
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_MINI_CONTROL, miniCtl);                
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_ZOOM_CONTROL, dwTmp);
+                }
+                else
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_MINI_CONTROL, 0);
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_ZOOM_CONTROL, 0);
+                }
+            }
+            else
+            {
+                dwShift = dwSrcPitch * 4;
+                dwOffset = DDOver_GetSrcStartAddress (dwVideoFlag,rSrc,rDest,dwSrcPitch,lpDPFsrc,&dwHQVoffset);
+                //Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_0, lpCAPDevice0->dwCAPPhysicalAddr[0]+dwShift+dwOffset);
+                //Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_1, lpCAPDevice0->dwCAPPhysicalAddr[1]+dwShift+dwOffset);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_0, lpCAPDevice0->dwCAPPhysicalAddr[0]+dwOffset);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_1, lpCAPDevice0->dwCAPPhysicalAddr[1]+dwOffset);
+                
+                //Three V1 buffer
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_2, lpCAPDevice0->dwCAPPhysicalAddr[2]+dwOffset);
+                
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_ALPHA_STARTADDR, ALPDevice.dwALPPhysicalAddr+dwOffset);
+
+                //Temporarily fix for 2D bandwidth problem. 2002/08/01
+                if ((gdwUseExtendedFIFO))
+                {
+                    miniCtl &= ~V1_Y_INTERPOLY;
+                }
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_MINI_CONTROL, miniCtl);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_ZOOM_CONTROL, zoomCtl);
+                //Fixed for SAMM expand Mode
+                //dwFetch = DDOver_GetFetch(dwVideoFlag,lpDPFsrc,srcWidth,dstWidth,dwOriSrcWidth,&dwHQVsrcFetch);
+                dwFetch = DDOver_GetFetch(dwVideoFlag,lpDPFsrc,srcWidth,dstModifiedWidth,dwOriSrcWidth,&dwHQVsrcFetch);                
+
+                if (gVIAGraphicInfo.Cap0_SwitchToV3)
+                    dwFetch = ((dwFetch+overlayRecordV3.dwFetchAlignment)&~overlayRecordV3.dwFetchAlignment) << 20;
+                else
+                dwFetch = ((dwFetch+overlayRecordV1.dwFetchAlignment)&~overlayRecordV1.dwFetchAlignment) << 20;
+                
+                //dwFetch = ((((dstWidth<<1)>>3)+overlayRecordV1.dwFetchAlignment)&~overlayRecordV1.dwFetchAlignment) << 20;
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V12_QWORD_PER_LINE, dwFetch);
+            }
+        }
+        else
+        {
+            if (dwVideoFlag & VIDEO_HQV_INUSE)
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,HQV_MINIFY_CONTROL, dwHQVminiCtl);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,HQV_FILTER_CONTROL, dwHQVfilterCtl);
+                dwOffset = DDOver_GetSrcStartAddress (dwVideoFlag,rSrc,rDest,dwSrcPitch,lpDPFsrc,&dwHQVoffset);
+                dwHQVsrcWidth=(unsigned long)rSrc.right - rSrc.left;
+                dwHQVdstWidth=(unsigned long)rDest.right - rDest.left;
+                if (dwHQVsrcWidth>dwHQVdstWidth)
+                {
+                    dwOffset = dwOffset * dwHQVdstWidth / dwHQVsrcWidth;
+                    //dwFetch = ((((dstWidth<<1)>>3)+overlayRecordV1.dwFetchAlignment)&~overlayRecordV1.dwFetchAlignment) << 20;
+                    //Fixed for SAMM expand Mode
+                    dwFetch = (((((dstModifiedWidth<<1)+V1_FETCHCOUNT_ALIGNMENT)&~V1_FETCHCOUNT_ALIGNMENT)>> V1_FETCHCOUNT_UNIT)+1) << 20;                    
+                }
+                else
+                {
+                    //dwFetch = ((((dwHQVsrcWidth<<1)>>3)+overlayRecordV1.dwFetchAlignment)&~overlayRecordV1.dwFetchAlignment) << 20;
+                    dwFetch = (((((dwHQVsrcWidth<<1)+V1_FETCHCOUNT_ALIGNMENT)&~V1_FETCHCOUNT_ALIGNMENT)>> V1_FETCHCOUNT_UNIT)+1) << 20;
+                }
+                
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_STARTADDR_0, lpCAPDevice0->dwHQVAddr[0]+dwOffset);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_STARTADDR_1, lpCAPDevice0->dwHQVAddr[1]+dwOffset);
+
+                if ( lpVideoHWDifference->dwThreeHQVBuffer )    //CLE_C0
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_STARTADDR_2, lpCAPDevice0->dwHQVAddr[2]+dwOffset);
+
+                dwFetch |= (VIDInD(V3_ALPHA_QWORD_PER_LINE)&ALPHA_FETCH_COUNT) ;
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_ALPHA_QWORD_PER_LINE, dwFetch);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_SOURCE_WIDTH, (dwHQVsrcWidth-1));
+
+                
+                miniCtl=0;
+                if (dwHQVzoomflagH||dwHQVzoomflagV)
+                {
+                    dwTmp = 0;
+                    if (dwHQVzoomflagH)
+                    {
+                        miniCtl = V1_X_INTERPOLY;
+                        dwTmp = (zoomCtl&0xffff0000);
+                    }
+                    
+                    if (dwHQVzoomflagV)
+                    {
+                        miniCtl |= (V1_Y_INTERPOLY | V1_YCBCR_INTERPOLY);
+                        dwTmp |= (zoomCtl&0x0000ffff);
+                    }
+                    
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_MINI_CONTROL, miniCtl);                
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_ZOOM_CONTROL, dwTmp);
+                }
+                else
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_ZOOM_CONTROL, 0);
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_MINI_CONTROL, 0);                
+                }
+            }
+            else
+            {
+                dwOffset = DDOver_GetSrcStartAddress (dwVideoFlag,rSrc,rDest,dwSrcPitch,lpDPFsrc,&dwHQVoffset);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_STARTADDR_1, lpCAPDevice0->dwCAPPhysicalAddr[1]+dwOffset);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_STARTADDR_0, lpCAPDevice0->dwCAPPhysicalAddr[0]+dwOffset);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_MINI_CONTROL, miniCtl);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_ZOOM_CONTROL, zoomCtl);
+                //Fixed for SAMM expand Mode
+                //dwFetch = DDOver_GetFetch(dwVideoFlag,lpDPFsrc,srcWidth,dstWidth,dwOriSrcWidth,&dwHQVsrcFetch);
+                dwFetch = DDOver_GetFetch(dwVideoFlag,lpDPFsrc,srcWidth,dstModifiedWidth,dwOriSrcWidth,&dwHQVsrcFetch);                
+
+                if (gVIAGraphicInfo.Cap0_SwitchToV3)
+                    dwFetch = ((dwFetch+overlayRecordV3.dwFetchAlignment)&~overlayRecordV3.dwFetchAlignment) << 20;
+                else
+                dwFetch = ((dwFetch+overlayRecordV1.dwFetchAlignment)&~overlayRecordV1.dwFetchAlignment) << 20;
+                
+                //dwFetch = ((((dstWidth<<1)>>3)+overlayRecordV1.dwFetchAlignment)&~overlayRecordV1.dwFetchAlignment) << 20;
+                dwFetch |= (VIDInD(V3_ALPHA_QWORD_PER_LINE)&ALPHA_FETCH_COUNT) ;
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_ALPHA_QWORD_PER_LINE, dwFetch);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_SOURCE_WIDTH, (srcWidth-1));
+                //VIDOutD(V3_ALPHA_QWORD_PER_LINE,dwFetch);
+            }
+        }
+
+        // Colorkey
+        if (dwColorKey) 
+        {
+            DBG_DD("Overlay colorkey=%08lx %08lx\n", dwKeyLow, dwKeyHigh);
+
+            dwKeyLow &= 0x00FFFFFF;
+            
+            if (lpVideoHWDifference->dwSupportTwoColorKey == VID_HWDIFF_TRUE)
+            {                    
+                dwCompose = (dwCompose & ~0x0f) | SELECT_VIDEO_IF_COLOR_KEY | SELECT_VIDEO3_IF_COLOR_KEY;
+            }
+            else
+            {
+                dwCompose = (dwCompose & ~0x0f) | SELECT_VIDEO_IF_COLOR_KEY;
+            }
+            
+            /*Modified for SAMM Mode*/
+            if (ScrnIndex == 1)
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,SND_COLOR_KEY, dwKeyLow);
+                dwCompose |= SECOND_DISPLAY_COLOR_KEY_ENABLE;
+                if ( dwVideoFlag & VIDEO_1_INUSE )
+                {
+                    dwVidCtl |= V1_ON_SND_DISPLAY;
+                } 
+                else 
+                {
+                    dwVidCtl |= V3_ON_SND_DISPLAY;
+                }
+            }
+            else
+            {    
+                if (lpVideoHWDifference->dwSupportTwoColorKey == VID_HWDIFF_TRUE)
+                {                    
+            if (dwVideoFlag & VIDEO_1_INUSE)
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_COLOR_KEY, dwKeyLow);
+            }
+            else
+            {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_COLOR_KEY, dwKeyLow);
+            }
+                }
+                else
+            {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_COLOR_KEY, dwKeyLow);    
+            } 
+        }
+        }// Colorkey
+
+        if (dwChromaKey) 
+        {
+            DBG_DD("Overlay Chromakey=%08lx %08lx\n", dwKeyLow, dwKeyHigh);
+
+            dwChromaLow  &= CHROMA_KEY_LOW;
+            dwChromaHigh &= CHROMA_KEY_HIGH;
+
+            dwChromaLow  |= (VIDInD(V_CHROMAKEY_LOW)&(~CHROMA_KEY_LOW));
+            dwChromaHigh |= (VIDInD(V_CHROMAKEY_HIGH)&(~CHROMA_KEY_HIGH));
+
+            // for Chroma Key
+            if (lpDPFsrc->dwFlags & DDPF_FOURCC)
+            {
+                    switch (lpDPFsrc->dwFourCC) {
+                    case FOURCC_YV12:
+                            //to be continued...
+                            break;
+                    case FOURCC_YUY2:
+                            //to be continued...
+                            break;
+                    default:
+                            //TOINT3;
+                            break;
+                    }
+            }
+            else if (lpDPFsrc->dwFlags & DDPF_RGB)
+            {
+                    unsigned long dwtmpLowR;
+                    unsigned long dwtmpLowG;
+                    unsigned long dwtmpLowB;
+                    unsigned long dwtmpChromaLow;
+                    unsigned long dwtmpHighR;
+                    unsigned long dwtmpHighG;
+                    unsigned long dwtmpHighB;
+                    unsigned long dwtmpChromaHigh;
+
+                    switch (lpDPFsrc->dwRGBBitCount) {
+                    case 16:
+                            if (lpDPFsrc->dwGBitMask==0x07E0) //RGB16(5:6:5)
+                            {
+                                    dwtmpLowR = (((dwChromaLow >> 11) << 3) | ((dwChromaLow >> 13) & 0x07)) & 0xFF;
+                                    dwtmpLowG = (((dwChromaLow >> 5) << 2) | ((dwChromaLow >> 9) & 0x03)) & 0xFF;
+
+                                    dwtmpHighR = (((dwChromaHigh >> 11) << 3) | ((dwChromaHigh >> 13) & 0x07)) & 0xFF;
+                                    dwtmpHighG = (((dwChromaHigh >> 5) << 2) | ((dwChromaHigh >> 9) & 0x03)) & 0xFF;
+                            }
+                            else //RGB15(5:5:5)
+                            {
+                                    dwtmpLowR = (((dwChromaLow >> 10) << 3) | ((dwChromaLow >> 12) & 0x07)) & 0xFF;
+                                    dwtmpLowG = (((dwChromaLow >> 5) << 3) | ((dwChromaLow >> 7) & 0x07)) & 0xFF;
+
+                                    dwtmpHighR = (((dwChromaHigh >> 10) << 3) | ((dwChromaHigh >> 12) & 0x07)) & 0xFF;
+                                    dwtmpHighG = (((dwChromaHigh >> 5) << 3) | ((dwChromaHigh >> 7) & 0x07)) & 0xFF;
+                            }
+                            dwtmpLowB = (((dwChromaLow << 3) | (dwChromaLow >> 2)) & 0x07) & 0xFF;
+                            dwtmpChromaLow = (dwtmpLowG << 16) | (dwtmpLowR << 8) | dwtmpLowB;
+                            dwChromaLow = ((dwChromaLow >> 24) << 24) | dwtmpChromaLow;
+
+                            dwtmpHighB = (((dwChromaHigh << 3) | (dwChromaHigh >> 2)) & 0x07) & 0xFF;
+                            dwtmpChromaHigh = (dwtmpHighG << 16) | (dwtmpHighR << 8) | dwtmpHighB;
+                            dwChromaHigh = ((dwChromaHigh >> 24) << 24) | dwtmpChromaHigh;
+                            break;
+
+                    case 32: //32 bit RGB
+                            dwtmpLowR = (dwChromaLow >> 16) & 0xFF;
+                            dwtmpLowG = (dwChromaLow >> 8) & 0xFF;
+                            dwtmpLowB = dwChromaLow & 0xFF;
+                            dwtmpChromaLow = (dwtmpLowG << 16) | (dwtmpLowR << 8) | dwtmpLowB;
+                            dwChromaLow = ((dwChromaLow >> 24) << 24) | dwtmpChromaLow;
+
+                            dwtmpHighR = (dwChromaHigh >> 16) & 0xFF;
+                            dwtmpHighG = (dwChromaHigh >> 8) & 0xFF;
+                            dwtmpHighB = dwChromaHigh & 0xFF;
+                            dwtmpChromaHigh = (dwtmpHighG << 16) | (dwtmpHighR << 8) | dwtmpHighB;
+                            dwChromaHigh = ((dwChromaHigh >> 24) << 24) | dwtmpChromaHigh;
+                            break;
+
+                    default:
+                            //TOINT3;
+                            break;
+                    }
+            }//End of DDPF_FOURCC
+
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_CHROMAKEY_HIGH,dwChromaHigh);
+            if (dwVideoFlag & VIDEO_1_INUSE)
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_CHROMAKEY_LOW, dwChromaLow);
+                //Temporarily solve the H/W Interpolation error when using Chroma Key
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_MINI_CONTROL, miniCtl & 0xFFFFFFF8);
+            }
+            else
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_CHROMAKEY_LOW, dwChromaLow|V_CHROMAKEY_V3);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_MINI_CONTROL, miniCtl & 0xFFFFFFF8);
+            }
+
+            //Modified for select video if (color key & chroma key)
+            if (dwCompose==SELECT_VIDEO_IF_COLOR_KEY)
+               dwCompose = SELECT_VIDEO_IF_COLOR_KEY | SELECT_VIDEO_IF_CHROMA_KEY;
+            else
+               dwCompose = (dwCompose & ~0x0f) | SELECT_VIDEO_IF_CHROMA_KEY;
+        }
+
+        // Determine if V1 is on top
+        DBG_DD("clip count=%d\n", via->video_win.clipcount);
+        if (via->video_win.clipcount == 0)
+            dwCompose &= ~COMPOSE_V3_TOP;
+            //dwCompose |= COMPOSE_V3_TOP;
+        //else
+        //    dwCompose |= COMPOSE_V3_TOP;
+
+        
+        // for 3123.C0 H/W bug.
+        // In SAMM mode, when one video on screen0(primary) another video on screen1(second)
+        // H/W still refer to register 298 [20] bit, so the video on screen0 will have so 
+        // garbage of the video on screen1. So, in bellow case must set 298[20] to 1.
+        // In all case which V3 is on Primary Screen, V3 must be on top.
+/*        if ( ((!(lpVideoControl->Cap1OnScreen1) || !(lpVideoControl->MPEGOnScreen1)) && (lpVideoControl->Cap0OnScreen1))
+               || (!(lpVideoControl->Cap0OnScreen1) && ((lpVideoControl->Cap1OnScreen1) || (lpVideoControl->MPEGOnScreen1))) )
+            dwCompose = dwCompose | COMPOSE_V3_TOP;
+*/
+            
+        
+        // Setup video control
+        if (dwVideoFlag & VIDEO_1_INUSE)
+        {
+            /*=* Modify for C1 FIFO *=*/
+            switch ( DispatchVGARevisionID() )
+            {
+                case VIA_REVISION_CLECX :
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_FIFO_CONTROL,
+                        V1_FIFO_DEPTH64 | V1_FIFO_PRETHRESHOLD56 | V1_FIFO_THRESHOLD56);
+                    break;
+                    
+                default:
+                    if (gdwUseExtendedFIFO)
+                    {
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_FIFO_CONTROL,
+                            V1_FIFO_DEPTH48 | V1_FIFO_PRETHRESHOLD40 | V1_FIFO_THRESHOLD40);
+                    }
+                    else
+                    {
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_FIFO_CONTROL,
+                            V1_FIFO_DEPTH32 | V1_FIFO_PRETHRESHOLD29 | V1_FIFO_THRESHOLD16);
+                    }   
+                    break;
+            }                       
+            
+            /* for SAMM Mode */          
+            //if ( lpVideoControl->Cap0OnScreen1 == 1 )
+            if ( lpVideoControl->VideoStatus & CAP0_ON_SND )
+            {
+                dwVidCtl = dwVidCtl | V1_ON_SND_DISPLAY;
+                dwCompose = dwCompose | SECOND_DISPLAY_COLOR_KEY_ENABLE;
+                DBG_DD("// Upd_Capture0: V1_ON_SND_DISPLAY !!!\n");
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STRIDE, dwSrcPitch );
+            }                        
+            else
+            {
+                dwVidCtl = dwVidCtl & 0x7FFFFFFF;
+                dwCompose = dwCompose & 0xFFFEFFFF;
+                DBG_DD("// Upd_Capture0: V1_ON_CRT !!!\n");
+            }               
+                                
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_CONTROL, dwVidCtl|V1_ENABLE);
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_COMPOSE_MODE, dwCompose|V1_COMMAND_FIRE );          
+        }
+        else
+        {
+            //Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_CONTROL, dwVidCtl&~V1_ENABLE&~V1_ON_SND_DISPLAY);
+            //Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_STRIDE, dwSrcPitch );         
+         
+            /*=* Modify for C1 FIFO *=*/
+            switch ( DispatchVGARevisionID() )
+            {
+                case VIA_REVISION_CLECX :
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,ALPHA_V3_FIFO_CONTROL,V3_FIFO_DEPTH64 | V3_FIFO_THRESHOLD56|
+                        ALPHA_FIFO_DEPTH8 | ALPHA_FIFO_THRESHOLD4);
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,ALPHA_V3_PREFIFO_CONTROL, ALPHA_FIFO_PRETHRESHOLD4|V3_FIFO_PRETHRESHOLD56);
+                    break; 
+                                  
+                default:
+                    if ((gdwUseExtendedFIFO) && !(VIDInD(V1_CONTROL) & V1_ENABLE))
+                    {
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,ALPHA_V3_FIFO_CONTROL,V3_FIFO_DEPTH48 | V3_FIFO_THRESHOLD40|
+                            ALPHA_FIFO_DEPTH8 | ALPHA_FIFO_THRESHOLD4);
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,ALPHA_V3_PREFIFO_CONTROL, ALPHA_FIFO_PRETHRESHOLD4|V3_FIFO_PRETHRESHOLD40);
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_CONTROL, dwVidCtl|V1_FIFO_EXTENDED);
+                    }
+                    else
+                    {
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,ALPHA_V3_FIFO_CONTROL,V3_FIFO_DEPTH32 | V3_FIFO_THRESHOLD16|
+                            ALPHA_FIFO_DEPTH8 | ALPHA_FIFO_THRESHOLD4);
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,ALPHA_V3_PREFIFO_CONTROL, ALPHA_FIFO_PRETHRESHOLD4|V3_FIFO_PRETHRESHOLD29);
+                    }
+                    break;
+            }
+            
+            /*switch ( DispatchVGARevisionID() )
+            {
+                case VIA_REVISION_CLECX :
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,ALPHA_V3_FIFO_CONTROL,V3_FIFO_DEPTH64 | V3_FIFO_THRESHOLD56|
+                        ALPHA_FIFO_DEPTH8 | ALPHA_FIFO_THRESHOLD4);
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,ALPHA_V3_PREFIFO_CONTROL, ALPHA_FIFO_PRETHRESHOLD4|V3_FIFO_PRETHRESHOLD56);
+                    break; 
+                                  
+                default:
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,ALPHA_V3_FIFO_CONTROL,V3_FIFO_DEPTH32 | V3_FIFO_THRESHOLD8|
+                        ALPHA_FIFO_DEPTH8 | ALPHA_FIFO_THRESHOLD4);
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,ALPHA_V3_PREFIFO_CONTROL, ALPHA_FIFO_PRETHRESHOLD4|(V3_FIFO_THRESHOLD16 >> 8) );
+                    break;
+            }*/
+            
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_CONTROL, dwVidCtl|V3_ENABLE);
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_COMPOSE_MODE, dwCompose|V3_COMMAND_FIRE|V1_COMMAND_FIRE );
+        }
+        
+        if (dwVideoFlag & VIDEO_HQV_INUSE)
+        {
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,HQV_CONTROL, dwHQVCtl|HQV_FLIP_STATUS);
+        }
+        Macro_VidREGFlush();
+
+        if (!TV0_ON)
+        {
+            if (dwVideoFlag & VIDEO_1_INUSE)
+            {
+                if (gdwUseExtendedFIFO)
+                {
+                    //Set Display FIFO
+                    WaitVBI();
+                            outb(0x17, 0x3C4); outb(0x2f, 0x3C5);
+                            outb(0x16, 0x3C4); outb((Save_3C4_16&0xf0)|0x14, 0x3C5);
+                            outb(0x18, 0x3C4); outb(0x56, 0x3C5);
+                }
+            }
+        }
+    }
+    else
+    {       
+        //Hide overlay
+        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_FIFO_CONTROL,V1_FIFO_PRETHRESHOLD12 |
+             V1_FIFO_THRESHOLD8 |V1_FIFO_DEPTH16);
+        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,ALPHA_V3_FIFO_CONTROL, ALPHA_FIFO_THRESHOLD4 
+             | ALPHA_FIFO_DEPTH8  | V3_FIFO_THRESHOLD24 | V3_FIFO_DEPTH32 );
+
+        if (dwVideoFlag&VIDEO_HQV_INUSE)
+        {
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,HQV_CONTROL, (VIDInD(HQV_CONTROL) & (~HQV_ENABLE)));            
+        }
+        
+        if (dwVideoFlag&VIDEO_1_INUSE)
+        {
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_CONTROL, (VIDInD(V1_CONTROL) & (~V1_ENABLE)));
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_COMPOSE_MODE, (VIDInD(V_COMPOSE_MODE)|V1_COMMAND_FIRE));
+        }
+        else
+        {
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_CONTROL, (VIDInD(V3_CONTROL) & (~V3_ENABLE)));
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_COMPOSE_MODE, (VIDInD(V_COMPOSE_MODE)|V3_COMMAND_FIRE));
+        }
+
+        Macro_VidREGFlush();        
+    }    
+
+    return PI_OK;
+    
+}
+
+/****************************************************************************
+ *
+ * Upd_Capture1()
+ *
+ ***************************************************************************/
+unsigned long Upd_Capture1(unsigned long dwVideoFlag,unsigned long dwStartAddr,RECTL rSrc,RECTL rDest,unsigned long dwSrcPitch,
+                 unsigned long dwOriSrcWidth,unsigned long dwOriSrcHeight,LPDDPIXELFORMAT lpDPFsrc,
+                 unsigned long dwDeinterlaceMode,unsigned long dwColorKey,unsigned long dwChromaKey,
+                 unsigned long dwKeyLow,unsigned long dwKeyHigh,unsigned long dwChromaLow,unsigned long dwChromaHigh,unsigned long dwFlags)
+{
+    //unsigned long dwVidCtl=0, dwCompose=0;
+    //unsigned long dwVidCtl=0, dwCompose=(VIDInD(V_COMPOSE_MODE)&~(SELECT_VIDEO_IF_COLOR_KEY|V1_COMMAND_FIRE|V3_COMMAND_FIRE))|V_COMMAND_LOAD_VBI;
+    unsigned long dwVidCtl=0, dwCompose=(VIDInD(V_COMPOSE_MODE)&~(SELECT_VIDEO_IF_COLOR_KEY|V1_COMMAND_FIRE|V3_COMMAND_FIRE));
+    unsigned long srcWidth, srcHeight,dstWidth,dstHeight;
+    unsigned long zoomCtl=0, miniCtl=0;
+    unsigned long dwHQVCtl=0;
+    unsigned long dwHQVfilterCtl=0,dwHQVminiCtl=0;
+    unsigned long dwHQVzoomflagH=0,dwHQVzoomflagV=0;
+    unsigned long dwHQVsrcWidth=0,dwHQVdstWidth=0;
+    unsigned long dwHQVsrcFetch = 0,dwHQVoffset=0;
+    unsigned long dwOffset=0,dwFetch=0,dwTmp=0;
+    unsigned long dwDisplayCountW=0;
+    unsigned long dwShift=0;
+    via_device *via = NULL;
+    LPVIDHWDIFFERENCE lpVideoHWDifference = &VideoHWDifference;
+
+    /*Added for SAMM expand Mode*/
+    unsigned long dstModifiedWidth=0,dstModifiedHeight=0;
+
+    /*Added for SAMM Mode*/
+    int ScrnIndex = 0;
+    if (dwFlags & DDOVER_ON_SND)
+    {
+        ScrnIndex = 1;
+    }    
+
+    /* 2003/10/06 Fix bug */
+    /* If Capture1 (or Capture0) has no video decoder(ex:SAA7113,SAA8108...) */
+    /* then run XawTV ./tv1 (or ./tv0), the system will hang */
+    if (dwVideoFlag & VIDEO_1_INUSE)
+    {
+        dwCompose |= V_COMMAND_LOAD_VBI;
+    }
+    else
+    {
+        if (gVIAGraphicInfo.RevisionID >= VIA_REVISION_CLECX)
+        {
+            dwCompose |= V3_COMMAND_LOAD_VBI;
+        }
+    }
+
+    /* for SAMM Mode */
+    // If video is on screen 1 V3 switch to V1
+    // else video is on screen 0 V1 switch to V3
+    // If screen just switch and video is on screen 1, disable V3 first then V3 switch to V1
+    // else screen just switch and video is on screen 0, disable V1 first then V1 switch to V3
+
+    //if (lpVideoControl->Cap1OnScreen1 == 1)
+    if ( lpVideoControl->VideoStatus & CAP1_ON_SND )
+    {
+        if ( ScreenSwitch(Position_W_Temp1, Position_W_Temp2, Position_H_Temp1, Position_H_Temp2) )
+        {
+            /*if (gdwVideoFlagTV1 & CAP0_USE_HQV)
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,HQV_CONTROL, (VIDInD(HQV_CONTROL) & (~HQV_ENABLE)) );
+            }*/
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_CONTROL,VIDInD(V3_CONTROL) & ~V3_ENABLE);
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_COMPOSE_MODE, (VIDInD(V_COMPOSE_MODE)|V3_COMMAND_FIRE|V1_COMMAND_FIRE));
+            Macro_VidREGFlush();
+        }
+    }
+    else
+    {
+        /*if ( (ScreenSwitch(Position_W_Temp1, Position_W_Temp2, Position_H_Temp1, Position_H_Temp2)) ||
+             ((gdwVideoFlagMPEG != 0) && (lpVideoControl->MPEGOnScreen1 == 1)) )
+        {
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_CONTROL,VIDInD(V1_CONTROL) & ~V1_ENABLE & ~V1_ON_SND_DISPLAY);
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_COMPOSE_MODE, (VIDInD(V_COMPOSE_MODE)|V1_COMMAND_FIRE));
+            Macro_VidREGFlush();
+        }*/
+        if ( ScreenSwitch(Position_W_Temp1, Position_W_Temp2, Position_H_Temp1, Position_H_Temp2) 
+             && ((gdwVideoFlagTV0 == 0)&&(gdwVideoFlagMPEG == 0)) )
+        {
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_CONTROL,VIDInD(V1_CONTROL) & ~V1_ENABLE & ~V1_ON_SND_DISPLAY);
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_COMPOSE_MODE, (VIDInD(V_COMPOSE_MODE)|V1_COMMAND_FIRE));
+            Macro_VidREGFlush();
+        }
+    }
+
+
+    /* to determine to use device video0 or video1 */
+    via = &via_v4l_devices[1];
+    /*if (dwVideoFlag & VIDEO_1_INUSE)
+        via = &via_v4l_devices[0];    //Capture0 + V1 -- /dev/video0
+    else
+        via = &via_v4l_devices[1];    //Capture1 + V3 -- /dev/video1
+    */
+    /* to fix A1 bug, the revision of A2 is 3 */
+    /*
+    if (via->revision == 3)
+        dwCompose=(VIDInD(V_COMPOSE_MODE)&~(SELECT_VIDEO_IF_COLOR_KEY|V1_COMMAND_FIRE|V3_COMMAND_FIRE));
+    else
+        dwCompose=(VIDInD(V_COMPOSE_MODE)&~(SELECT_VIDEO_IF_COLOR_KEY|V1_COMMAND_FIRE|V3_COMMAND_FIRE))|V_COMMAND_LOAD_VBI;
+    */
+    DBG_DD("//Upd_Capture1:\n");
+    DBG_DD("Modified rSrc  X (%ld,%ld) Y (%ld,%ld)\n",
+                rSrc.left, rSrc.right,rSrc.top, rSrc.bottom);
+    DBG_DD("Modified rDest  X (%ld,%ld) Y (%ld,%ld)\n",
+                rDest.left, rDest.right,rDest.top, rDest.bottom);
+
+    if (dwVideoFlag & VIDEO_SHOW)    
+    {
+        // Setup video & HQV control registers
+        if (dwVideoFlag & VIDEO_1_INUSE)
+        {
+            if (dwVideoFlag & VIDEO_HQV_INUSE)    
+            {
+                DBG_DD(" !!!!!!!!!!!!!!!!!!!!!!! Upd_Capture1 + V1: HQV_INUSE !!\n");
+                //CAP1_V1_HQV_ENABLE = 1;
+                
+                /*=* Modify for C1 FIFO *=*/
+                switch ( DispatchVGARevisionID() )
+                {
+                    case VIA_REVISION_CLECX :
+                        dwVidCtl =  V1_COLORSPACE_SIGN | V1_SWAP_HW_HQV |
+                                    V1_EXPIRE_NUM_F | V1_YUV422;
+                        break;
+                        
+                    default:
+                        if (gdwUseExtendedFIFO)
+                        {
+                            dwVidCtl =  V1_COLORSPACE_SIGN | V1_SWAP_HW_HQV |
+                                        V1_EXPIRE_NUM_A | V1_FIFO_EXTENDED | V1_YUV422;
+                            }
+                        else
+                        {
+                            dwVidCtl =  V1_COLORSPACE_SIGN | V1_SWAP_HW_HQV |
+                                        V1_EXPIRE_NUM | V1_YUV422;
+                        }
+                        break;
+                }       
+                
+                if (via->CapInfo.dwDeinterlaceMode & VIA_DEINTERLACE_BOB)
+                {
+                    if(gVIAGraphicInfo.Cap1_UseIRQ)       // Capture 1 use IRQ, for Cap1 S/W flip
+                    {
+                        dwHQVCtl = HQV_SRC_SW|HQV_YUV422| 
+                                   HQV_DEINTERLACE|HQV_FIELD_2_FRAME| /* field source, deinterlace bob mode */
+                                   HQV_ENABLE;
+                    }
+                    else
+                    {
+                    dwHQVCtl = HQV_SRC_CAPTURE1|HQV_YUV422|
+                               HQV_DEINTERLACE|HQV_FIELD_2_FRAME| /* field source, deinterlace bob mode */
+                               HQV_ENABLE;
+                }
+                }
+                else
+                {
+                    if(gVIAGraphicInfo.Cap1_UseIRQ)       // Capture 1 use IRQ, for Cap1 S/W flip
+                        dwHQVCtl = HQV_SRC_SW|HQV_YUV422|HQV_ENABLE; 
+                    else
+                    dwHQVCtl = HQV_SRC_CAPTURE1|HQV_YUV422|HQV_ENABLE;
+                    
+                } 
+            }
+            else
+            {
+                DBG_DD(" !!!!!!!!!!!!!!!!!!!!!!! Upd_Capture1 + V1: NO HQV !!\n");
+                
+                /*=* Modify for C1 FIFO *=*/
+                switch ( DispatchVGARevisionID() )
+                {
+                    case VIA_REVISION_CLECX :
+                        dwVidCtl =  V1_COLORSPACE_SIGN | V1_SWAP_HW_CAPTURE |
+                                    V1_EXPIRE_NUM_F | V1_YUV422;
+                        break;
+                        
+                    default:
+                        if (gdwUseExtendedFIFO)
+                        {
+                            dwVidCtl =  V1_COLORSPACE_SIGN | V1_SWAP_HW_CAPTURE |
+                                        V1_EXPIRE_NUM_A | V1_FIFO_EXTENDED | V1_YUV422;
+                        }
+                        else
+                        {
+                            dwVidCtl =  V1_COLORSPACE_SIGN | V1_SWAP_HW_CAPTURE |
+                                        V1_EXPIRE_NUM | V1_YUV422;
+                        }
+                        break;
+                }
+            }
+        }
+        else
+        {
+            if (dwVideoFlag & VIDEO_HQV_INUSE)    
+            {
+                DBG_DD(" !!!!!!!!!!!!!!!!!!!!!!! Upd_Capture1 + V3: HQV_INUSE !!\n");
+                
+                /*=* Modify for C1 FIFO *=*/
+                switch ( DispatchVGARevisionID() )
+                {
+                    case VIA_REVISION_CLECX :
+                            dwVidCtl =  V3_COLORSPACE_SIGN | V3_SWAP_HW_HQV |
+                            V3_EXPIRE_NUM_F | V3_YUV422;
+                        break;
+                        
+                    default:
+                        dwVidCtl =  V3_COLORSPACE_SIGN | V3_SWAP_HW_HQV |
+                                    V3_EXPIRE_NUM | V3_YUV422;
+                        break;
+                }
+
+                if (via->CapInfo.dwDeinterlaceMode & VIA_DEINTERLACE_BOB)
+                {
+                    if(gVIAGraphicInfo.Cap1_UseIRQ)       // Capture 1 use IRQ, for Cap1 S/W flip
+                    {
+                        dwHQVCtl = HQV_SRC_SW|HQV_YUV422|
+                               HQV_DEINTERLACE|HQV_FIELD_2_FRAME| /* field source, deinterlace bob mode */
+                               HQV_ENABLE;
+                    }
+                    else
+                    {
+                    dwHQVCtl = HQV_SRC_CAPTURE1|HQV_YUV422|
+                               HQV_DEINTERLACE|HQV_FIELD_2_FRAME| /* field source, deinterlace bob mode */
+                               HQV_ENABLE;
+                }
+                }
+                else
+                {
+                    if(gVIAGraphicInfo.Cap1_UseIRQ)       // Capture 1 use IRQ, for Cap1 S/W flip
+                        dwHQVCtl = HQV_SRC_SW|HQV_YUV422|HQV_ENABLE;
+                    else
+                    dwHQVCtl = HQV_SRC_CAPTURE1|HQV_YUV422|HQV_ENABLE;
+                    
+                }
+
+            }
+            else
+            {
+                DBG_DD(" !!!!!!!!!!!!!!!!!!!!!!! Upd_Capture1 + V3: NO HQV !!\n");
+                
+                /*=* Modify for C1 FIFO *=*/
+                switch ( DispatchVGARevisionID() )
+                {
+                    case VIA_REVISION_CLECX :
+                        if (dwVideoFlag & VIDEO_CAPTURE0_INUSE)
+                        {
+                            dwVidCtl =  V3_COLORSPACE_SIGN | V3_FLIP_HW_CAPTURE0 |
+                                        V3_EXPIRE_NUM_F | V3_YUV422;                
+                        }
+                        else
+                        {
+                            dwVidCtl =  V3_COLORSPACE_SIGN | V3_FLIP_HW_CAPTURE1 |
+                                        V3_EXPIRE_NUM_F | V3_YUV422;                
+                        }
+                        break;
+                        
+                    default:
+                        if (dwVideoFlag & VIDEO_CAPTURE0_INUSE)
+                        {
+                            dwVidCtl =  V3_COLORSPACE_SIGN | V3_FLIP_HW_CAPTURE0 |
+                                        V3_EXPIRE_NUM | V3_YUV422;                
+                        }
+                        else
+                        {
+                            dwVidCtl =  V3_COLORSPACE_SIGN | V3_FLIP_HW_CAPTURE1 |
+                                        V3_EXPIRE_NUM | V3_YUV422;                
+                        }
+                        break;
+                }
+            }
+        }
+
+        if ( lpVideoHWDifference->dwThreeHQVBuffer )    //CLE_C0
+        {
+            //HQV support 3 HQV buffer       
+            //dwHQVCtl &= ~HQV_SW_FLIP;      // Capture 1 use S/W flip
+            dwHQVCtl |= HQV_TRIPLE_BUFF | HQV_FLIP_STATUS; 
+        }
+
+        // Destination window key
+        overlayRecordV3.dwWidth=dstWidth = rDest.right - rDest.left;
+        overlayRecordV3.dwHeight=dstHeight = rDest.bottom - rDest.top;
+        //overlayRecordV1.dwWidth=dstWidth = rDest.right - rDest.left;
+        //overlayRecordV1.dwHeight=dstHeight = rDest.bottom - rDest.top;
+        srcWidth = (unsigned long)rSrc.right - rSrc.left;
+        srcHeight = (unsigned long)rSrc.bottom - rSrc.top;
+       
+        /*Added for SAMM expand Mode*/
+        /*In SAMM expand, we need adjust x and y position, width and height zoom factor.*/
+        if  ( ((gVIAGraphicInfo.Screen[ScrnIndex].dwDVIOn)||(gVIAGraphicInfo.Screen[ScrnIndex].dwLCDOn))
+              &&(gVIAGraphicInfo.Screen[ScrnIndex].dwExpand) )
+        {
+            dstModifiedWidth=dstWidth*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelWidth)/
+                             (gVIAGraphicInfo.Screen[ScrnIndex].dwWidth)+1;
+            dstModifiedHeight=dstHeight*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelHeight)/
+                              (gVIAGraphicInfo.Screen[ScrnIndex].dwHeight)+1;
+            DBG_DD("===Expand!! \n");
+        }
+        else
+        {
+            dstModifiedWidth=dstWidth;
+            dstModifiedHeight=dstHeight;
+        }
+        DBG_DD("===dstModifiedWidth= %ld \n", dstModifiedWidth);
+        DBG_DD("===dstModifiedHeight= %ld \n", dstModifiedHeight);
+       
+
+        if (dwVideoFlag & VIDEO_HQV_INUSE)
+        {
+            //dwPitch -1 to hide the noise dot in the left down corner
+            //dwHeight -1 to hide green line in the bottom
+            
+            if ( lpVideoHWDifference->dwHQVFetchByteUnit )    // CLE_C0
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, HQV_SRC_FETCH_LINE, (((CAPDevice[1].dwPitch)-1)<<16)|(dwOriSrcHeight-1));
+            else
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, HQV_SRC_FETCH_LINE, (((CAPDevice[1].dwPitch>>3)-1)<<16)|(dwOriSrcHeight-1));
+                
+            //Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, HQV_SRC_STRIDE, ((CAPDevice[1].dwPitch>>1)<<16)|CAPDevice[1].dwPitch);
+            //Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, HQV_DST_STRIDE, CAPDevice[1].dwPitch);
+        }
+
+        // Setup X zoom factor
+        overlayRecordV3.dwFetchAlignment = 0;
+        //overlayRecordV1.dwFetchAlignment = 0;
+
+        //Fixed for SAMM expand Mode
+        //if ( DDOVER_HQVCalcZoomWidth(dwVideoFlag, srcWidth , dstWidth,
+        //                          &zoomCtl, &miniCtl, &dwHQVfilterCtl, &dwHQVminiCtl,&dwHQVzoomflagH) == PI_ERR )
+        if ( DDOVER_HQVCalcZoomWidth(dwVideoFlag, srcWidth , dstModifiedWidth,
+                                  &zoomCtl, &miniCtl, &dwHQVfilterCtl, &dwHQVminiCtl,&dwHQVzoomflagH) == PI_ERR )
+        {
+            // too small to handle
+            dwFetch <<= 20;
+            if (dwVideoFlag & VIDEO_1_INUSE)    
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V12_QWORD_PER_LINE, dwFetch);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_COMPOSE_MODE , dwCompose|V1_COMMAND_FIRE );
+            }
+            else
+            {
+                dwFetch |=(VIDInD(V3_ALPHA_QWORD_PER_LINE)&(~V3_FETCH_COUNT));
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_ALPHA_QWORD_PER_LINE, dwFetch);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_COMPOSE_MODE , dwCompose|V3_COMMAND_FIRE );
+                
+            }
+            Macro_VidREGFlushVPE();
+            return PI_ERR;
+        }
+
+        DDOver_GetDisplayCount(dwVideoFlag,lpDPFsrc,srcWidth,&dwDisplayCountW);
+        // Setup position
+        if (dwVideoFlag & VIDEO_1_INUSE)    
+        {
+            /*Fixed for SAMM expand Mode*/
+            if  ( ((gVIAGraphicInfo.Screen[ScrnIndex].dwDVIOn)||(gVIAGraphicInfo.Screen[ScrnIndex].dwLCDOn))
+                  &&(gVIAGraphicInfo.Screen[ScrnIndex].dwExpand) )
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_WIN_END_Y,
+                                 (((rDest.right-1)*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelWidth)/
+                                  (gVIAGraphicInfo.Screen[ScrnIndex].dwWidth)) <<16) +
+                                 (rDest.bottom*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelHeight)/
+                                  (gVIAGraphicInfo.Screen[ScrnIndex].dwHeight)) );                             
+                
+                if (rDest.top > 0)
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_WIN_START_Y,
+                                     ((rDest.left*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelWidth)/
+                                      (gVIAGraphicInfo.Screen[ScrnIndex].dwWidth)) <<16 ) + 
+                                     (rDest.top*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelHeight)/
+                                      (gVIAGraphicInfo.Screen[ScrnIndex].dwHeight)) );
+                }
+                else
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_WIN_START_Y,
+                                     ((rDest.left*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelWidth)/
+                                     (gVIAGraphicInfo.Screen[ScrnIndex].dwWidth)) <<16) );
+                }                
+                
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_SOURCE_HEIGHT, (srcHeight<<16)|dwDisplayCountW);
+        }
+        else
+        {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_WIN_END_Y, ((rDest.right-1)<<16) + (rDest.bottom-1));
+                if (rDest.top > 0)
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_WIN_START_Y, (rDest.left<<16) + rDest.top );
+                }
+                else 
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_WIN_START_Y, (rDest.left<<16));
+                }
+
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_SOURCE_HEIGHT, (srcHeight<<16)|dwDisplayCountW);
+            }
+        }
+        else
+        {
+            /*Fixed for SAMM expand Mode*/
+            if  ( ((gVIAGraphicInfo.Screen[ScrnIndex].dwDVIOn)||(gVIAGraphicInfo.Screen[ScrnIndex].dwLCDOn))
+                  &&(gVIAGraphicInfo.Screen[ScrnIndex].dwExpand) )
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_WIN_END_Y,
+                                 (((rDest.right-1)*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelWidth)/
+                                  (gVIAGraphicInfo.Screen[ScrnIndex].dwWidth)) <<16) +
+                                 (rDest.bottom*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelHeight)/
+                                  (gVIAGraphicInfo.Screen[ScrnIndex].dwHeight)) );             
+                                                                
+                if (rDest.top > 0)
+                {
+                     Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_WIN_START_Y,
+                                     ((rDest.left*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelWidth)/
+                                      (gVIAGraphicInfo.Screen[ScrnIndex].dwWidth)) <<16 ) + 
+                                     (rDest.top*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelHeight)/
+                                      (gVIAGraphicInfo.Screen[ScrnIndex].dwHeight)) );
+                }
+                else
+                {
+                     Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_WIN_START_Y,
+                                     ((rDest.left*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelWidth)/
+                                     (gVIAGraphicInfo.Screen[ScrnIndex].dwWidth)) <<16) );
+                }
+                
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_SOURCE_WIDTH, dwDisplayCountW);
+            }
+            else
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_WIN_END_Y, ((rDest.right-1)<<16) + (rDest.bottom-1));
+                if (rDest.top > 0)
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_WIN_START_Y, (rDest.left<<16) + rDest.top );
+                }
+                else 
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_WIN_START_Y, (rDest.left<<16));
+                }
+                
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_SOURCE_WIDTH, dwDisplayCountW);
+            }
+        }
+        
+        //
+        // Setup Y zoom factor
+        //
+
+        //Fixed for SAMM expand Mode
+        //if ( DDOVER_HQVCalcZoomHeight(srcHeight,dstHeight,&zoomCtl,&miniCtl, &dwHQVfilterCtl, &dwHQVminiCtl ,&dwHQVzoomflagV) == PI_ERR )
+        if ( DDOVER_HQVCalcZoomHeight(srcHeight,dstModifiedHeight,&zoomCtl,&miniCtl, &dwHQVfilterCtl, &dwHQVminiCtl ,&dwHQVzoomflagV) == PI_ERR )
+        {
+            if (dwVideoFlag & VIDEO_1_INUSE)    
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_COMPOSE_MODE , dwCompose|V1_COMMAND_FIRE );
+            }
+            else
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_COMPOSE_MODE , dwCompose|V3_COMMAND_FIRE );                
+            }
+            
+            Macro_VidREGFlushVPE();
+            return PI_ERR;
+        }
+/*        
+        if ((gVIAGraphicInfo.NoHQV_VFilter) || (srcHeight==dstHeight))
+        {
+            dwHQVfilterCtl &= 0xfffdffff;
+            DBG_DD("Upd_Capture1 : No Capture 1 HQV Vertical Filter\n");
+        }
+        
+        if ((gVIAGraphicInfo.NoHQV_HFilter) || (srcWidth==dstWidth))
+        {
+            dwHQVfilterCtl &= 0xfffffffd;
+            DBG_DD("Upd_Capture1 : No Capture 1 HQV Horizontal Filter\n");
+        }
+*/        
+        if (gVIAGraphicInfo.HQVFilter_ManualSelect)
+        {
+                switch(gVIAGraphicInfo.CapHQV_VFilterMode)
+                {
+            	    case 0: 
+            	        dwHQVfilterCtl &= 0x0000ffff;
+            	        dwHQVfilterCtl |= 0x00400000;
+                        DBG_DD("Upd_Video : No Capture HQV Vertical Filter\n");
+                        break;
+                        
+                    default:
+                        dwHQVfilterCtl &= 0x0000ffff;
+                        dwHQVfilterCtl |= HQV_V_FILTER_DEFAULT;
+                        DBG_DD("Upd_Video : Capture HQV Vertical Filter mode: FILTER_DEFAULT\n");
+                        break;
+                }
+                
+                switch(gVIAGraphicInfo.CapHQV_HFilterMode)
+                {
+            	    case 0: 
+            	        dwHQVfilterCtl &= 0xffff0000;
+            	        dwHQVfilterCtl |= 0x00000040;
+                        DBG_DD("Upd_Video : No Capture HQV horizontal Filter\n");
+                        break;
+                    
+                    default:
+                        dwHQVfilterCtl &= 0xffff0000;
+                        dwHQVfilterCtl |= HQV_H_FILTER_DEFAULT;
+                        DBG_DD("Upd_Video : Capture HQV horizontalFilter mode: FILTER_DEFAULT\n");
+                        break;
+                }
+        }
+        
+        if (dwVideoFlag & VIDEO_1_INUSE)
+        {
+            if (dwVideoFlag & VIDEO_HQV_INUSE)
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, HQV_MINIFY_CONTROL, dwHQVminiCtl);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, HQV_FILTER_CONTROL, dwHQVfilterCtl);
+                dwOffset = DDOver_GetSrcStartAddress (dwVideoFlag,rSrc,rDest,dwSrcPitch,lpDPFsrc,&dwHQVoffset);
+
+                dwHQVsrcWidth=(unsigned long)rSrc.right - rSrc.left;
+                dwHQVdstWidth=(unsigned long)rDest.right - rDest.left;
+                if (dwHQVsrcWidth>dwHQVdstWidth)
+                {
+                    dwOffset = dwHQVoffset;
+                    /* mark dwOffset to fix HQV bug... */
+                    //dwOffset = dwOffset * dwHQVdstWidth / dwHQVsrcWidth;
+                    //dwFetch = ((((dstWidth<<1)>>3)+overlayRecordV3.dwFetchAlignment)&~overlayRecordV3.dwFetchAlignment) << 20;
+                    //Fixed for SAMM expand Mode
+                    //dwFetch = (((((dstWidth<<1)+V1_FETCHCOUNT_ALIGNMENT)&~V1_FETCHCOUNT_ALIGNMENT)>> V1_FETCHCOUNT_UNIT)+1) << 20;
+                    dwFetch = (((((dstModifiedWidth<<1)+V1_FETCHCOUNT_ALIGNMENT)&~V1_FETCHCOUNT_ALIGNMENT)>> V1_FETCHCOUNT_UNIT)+1) << 20;
+                }
+                else
+                {
+                    //dwFetch = ((((dwHQVsrcWidth<<1)>>3)+overlayRecordV3.dwFetchAlignment)&~overlayRecordV3.dwFetchAlignment) << 20;
+                    dwFetch = (((((dwHQVsrcWidth<<1)+V1_FETCHCOUNT_ALIGNMENT)&~V1_FETCHCOUNT_ALIGNMENT)>> V1_FETCHCOUNT_UNIT)+1) << 20;
+                }
+
+                dwShift = dwSrcPitch * 4;
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V12_QWORD_PER_LINE, dwFetch);
+                //Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_1, lpCAPDevice0->dwHQVAddr[1]+dwShift+dwOffset);
+                //Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_0, lpCAPDevice0->dwHQVAddr[0]+dwShift+dwOffset);
+
+                if (gdwVideoFlagTV0 & VIDEO_HQV_INUSE)
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_1, lpCAPDevice0->dwHQVAddr[1]+dwOffset);
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_0, lpCAPDevice0->dwHQVAddr[0]+dwOffset);
+                }
+                else
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_1, lpCAPDevice1->dwHQVAddr[1]+dwOffset);
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_0, lpCAPDevice1->dwHQVAddr[0]+dwOffset);                
+                    
+                    if ( lpVideoHWDifference->dwThreeHQVBuffer )    //CLE_C0
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_2, lpCAPDevice1->dwHQVAddr[2]+dwOffset);
+                                        
+                }
+
+                miniCtl=0;
+                if (dwHQVzoomflagH||dwHQVzoomflagV)
+                {
+                    dwTmp = 0;
+                    if (dwHQVzoomflagH)
+                    {
+                        miniCtl = V1_X_INTERPOLY;
+                        dwTmp = (zoomCtl&0xffff0000);
+                    }
+                    
+                    if (dwHQVzoomflagV)
+                    {
+                        miniCtl |= (V1_Y_INTERPOLY | V1_YCBCR_INTERPOLY);
+                        dwTmp |= (zoomCtl&0x0000ffff);
+                    }
+                    
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_MINI_CONTROL, miniCtl);                
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_ZOOM_CONTROL, dwTmp);
+                }
+                else
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_MINI_CONTROL, 0);
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_ZOOM_CONTROL, 0);
+                }
+            }
+            else
+            {
+                dwShift = dwSrcPitch * 4;
+                dwOffset = DDOver_GetSrcStartAddress (dwVideoFlag,rSrc,rDest,dwSrcPitch,lpDPFsrc,&dwHQVoffset);
+                //Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_0, lpCAPDevice0->dwCAPPhysicalAddr[0]+dwShift+dwOffset);
+                //Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_1, lpCAPDevice0->dwCAPPhysicalAddr[1]+dwShift+dwOffset);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_0, lpCAPDevice1->dwCAPPhysicalAddr[0]+dwOffset);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_1, lpCAPDevice1->dwCAPPhysicalAddr[1]+dwOffset);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_MINI_CONTROL, miniCtl);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_ZOOM_CONTROL, zoomCtl);
+                //Fixed for SAMM expand Mode
+                //dwFetch = DDOver_GetFetch(dwVideoFlag,lpDPFsrc,srcWidth,dstWidth,dwOriSrcWidth,&dwHQVsrcFetch);
+                dwFetch = DDOver_GetFetch(dwVideoFlag,lpDPFsrc,srcWidth,dstModifiedWidth,dwOriSrcWidth,&dwHQVsrcFetch);
+                dwFetch = ((dwFetch+overlayRecordV3.dwFetchAlignment)&~overlayRecordV3.dwFetchAlignment) << 20;
+                //dwFetch = ((dwFetch+overlayRecordV1.dwFetchAlignment)&~overlayRecordV1.dwFetchAlignment) << 20;
+                //dwFetch = ((((dstWidth<<1)>>3)+overlayRecordV3.dwFetchAlignment)&~overlayRecordV3.dwFetchAlignment) << 20;
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V12_QWORD_PER_LINE, dwFetch);
+            }
+        }
+        else
+        {
+            if (dwVideoFlag & VIDEO_HQV_INUSE)
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,HQV_MINIFY_CONTROL, dwHQVminiCtl);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,HQV_FILTER_CONTROL, dwHQVfilterCtl);
+                dwOffset = DDOver_GetSrcStartAddress (dwVideoFlag,rSrc,rDest,dwSrcPitch,lpDPFsrc,&dwHQVoffset);
+                dwHQVsrcWidth=(unsigned long)rSrc.right - rSrc.left;
+                dwHQVdstWidth=(unsigned long)rDest.right - rDest.left;
+                if (dwHQVsrcWidth>dwHQVdstWidth)
+                {
+                    dwOffset = dwHQVoffset;
+                    /* mark dwOffset to fix HQV bug... */
+                    //dwOffset = dwOffset * dwHQVdstWidth / dwHQVsrcWidth;
+                    //dwFetch = ((((dstWidth<<1)>>3)+overlayRecordV3.dwFetchAlignment)&~overlayRecordV3.dwFetchAlignment) << 20;
+                    //Fixed for SAMM expand Mode
+                    //dwFetch = (((((dstWidth<<1)+V1_FETCHCOUNT_ALIGNMENT)&~V1_FETCHCOUNT_ALIGNMENT)>> V1_FETCHCOUNT_UNIT)+1) << 20;
+                    dwFetch = (((((dstModifiedWidth<<1)+V1_FETCHCOUNT_ALIGNMENT)&~V1_FETCHCOUNT_ALIGNMENT)>> V1_FETCHCOUNT_UNIT)+1) << 20;
+                }
+                else
+                {
+                    //dwFetch = ((((dwHQVsrcWidth<<1)>>3)+overlayRecordV3.dwFetchAlignment)&~overlayRecordV3.dwFetchAlignment) << 20;
+                    dwFetch = (((((dwHQVsrcWidth<<1)+V1_FETCHCOUNT_ALIGNMENT)&~V1_FETCHCOUNT_ALIGNMENT)>> V1_FETCHCOUNT_UNIT)+1) << 20;
+                }
+                
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_STARTADDR_0, lpCAPDevice1->dwHQVAddr[0]+dwOffset);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_STARTADDR_1, lpCAPDevice1->dwHQVAddr[1]+dwOffset);
+                
+                if ( lpVideoHWDifference->dwThreeHQVBuffer )    //CLE_C0
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_STARTADDR_2, lpCAPDevice1->dwHQVAddr[2]+dwOffset);
+                
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_ALPHA_STARTADDR, ALPDevice.dwALPPhysicalAddr+dwOffset);
+
+                dwFetch |= (VIDInD(V3_ALPHA_QWORD_PER_LINE)&ALPHA_FETCH_COUNT) ;
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_ALPHA_QWORD_PER_LINE, dwFetch);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_SOURCE_WIDTH, (dwHQVsrcWidth-1));
+
+                
+                miniCtl=0;
+                if (dwHQVzoomflagH||dwHQVzoomflagV)
+                {
+                    dwTmp = 0;
+                    if (dwHQVzoomflagH)
+                    {
+                        miniCtl = V1_X_INTERPOLY;
+                        dwTmp = (zoomCtl&0xffff0000);
+                    }
+                    
+                    if (dwHQVzoomflagV)
+                    {
+                        miniCtl |= (V1_Y_INTERPOLY | V1_YCBCR_INTERPOLY);
+                        dwTmp |= (zoomCtl&0x0000ffff);
+                    }
+                    
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_MINI_CONTROL, miniCtl);                
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_ZOOM_CONTROL, dwTmp);
+                }
+                else
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_ZOOM_CONTROL, 0);
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_MINI_CONTROL, 0);                
+                }
+            }
+            else
+            {
+                dwOffset = DDOver_GetSrcStartAddress (dwVideoFlag,rSrc,rDest,dwSrcPitch,lpDPFsrc,&dwHQVoffset);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_STARTADDR_1, lpCAPDevice1->dwCAPPhysicalAddr[1]+dwOffset);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_STARTADDR_0, lpCAPDevice1->dwCAPPhysicalAddr[0]+dwOffset);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_ALPHA_STARTADDR, ALPDevice.dwALPPhysicalAddr+dwOffset);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_MINI_CONTROL, miniCtl);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_ZOOM_CONTROL, zoomCtl);
+                //Fixed for SAMM expand Mode
+                //dwFetch = DDOver_GetFetch(dwVideoFlag,lpDPFsrc,srcWidth,dstWidth,dwOriSrcWidth,&dwHQVsrcFetch);
+                dwFetch = DDOver_GetFetch(dwVideoFlag,lpDPFsrc,srcWidth,dstModifiedWidth,dwOriSrcWidth,&dwHQVsrcFetch);
+                dwFetch = ((dwFetch+overlayRecordV3.dwFetchAlignment)&~overlayRecordV3.dwFetchAlignment) << 20;
+                //dwFetch = ((dwFetch+overlayRecordV1.dwFetchAlignment)&~overlayRecordV1.dwFetchAlignment) << 20;
+                //dwFetch = ((((dstWidth<<1)>>3)+overlayRecordV3.dwFetchAlignment)&~overlayRecordV3.dwFetchAlignment) << 20;
+                dwFetch |= (VIDInD(V3_ALPHA_QWORD_PER_LINE)&ALPHA_FETCH_COUNT) ;
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_ALPHA_QWORD_PER_LINE, dwFetch);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_SOURCE_WIDTH, (srcWidth-1));
+                //VIDOutD(V3_ALPHA_QWORD_PER_LINE,dwFetch);
+            }
+        }
+
+        // Colorkey
+        if (dwColorKey) 
+        {
+            DBG_DD("Overlay colorkey=%08lx %08lx\n", dwKeyLow, dwKeyHigh);
+
+            dwKeyLow &= 0x00FFFFFF;
+
+            if (lpVideoHWDifference->dwSupportTwoColorKey == VID_HWDIFF_TRUE)
+            {                    
+                dwCompose = (dwCompose & ~0x0f) | SELECT_VIDEO_IF_COLOR_KEY | SELECT_VIDEO3_IF_COLOR_KEY;
+            }
+            else
+            {
+                dwCompose = (dwCompose & ~0x0f) | SELECT_VIDEO_IF_COLOR_KEY;
+            } 
+            
+            /*Modified for SAMM Mode*/
+            if (ScrnIndex == 1)
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,SND_COLOR_KEY, dwKeyLow);
+                dwCompose |= SECOND_DISPLAY_COLOR_KEY_ENABLE;
+                if ( dwVideoFlag & VIDEO_1_INUSE )
+                {
+                    dwVidCtl |= V1_ON_SND_DISPLAY;
+                } 
+                else 
+                {
+                    dwVidCtl |= V3_ON_SND_DISPLAY;
+                }
+            }
+            else
+            {    
+                if (lpVideoHWDifference->dwSupportTwoColorKey == VID_HWDIFF_TRUE)
+                {                    
+            if (dwVideoFlag & VIDEO_1_INUSE)
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_COLOR_KEY, dwKeyLow);
+            }
+            else
+            {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_COLOR_KEY, dwKeyLow);
+            }
+                }
+                else
+            {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_COLOR_KEY, dwKeyLow);    
+            }        
+        }
+        }// Colorkey
+
+        if (dwChromaKey) 
+        {
+            DBG_DD("Overlay Chromakey=%08lx %08lx\n", dwKeyLow, dwKeyHigh);
+
+            dwChromaLow  &= CHROMA_KEY_LOW;
+            dwChromaHigh &= CHROMA_KEY_HIGH;
+
+            dwChromaLow  |= (VIDInD(V_CHROMAKEY_LOW)&(~CHROMA_KEY_LOW));
+            dwChromaHigh |= (VIDInD(V_CHROMAKEY_HIGH)&(~CHROMA_KEY_HIGH));
+
+            // for Chroma Key
+            if (lpDPFsrc->dwFlags & DDPF_FOURCC)
+            {
+                    switch (lpDPFsrc->dwFourCC) {
+                    case FOURCC_YV12:
+                            //to be continued...
+                            break;
+                    case FOURCC_YUY2:
+                            //to be continued...
+                            break;
+                    default:
+                            //TOINT3;
+                            break;
+                    }
+            }
+            else if (lpDPFsrc->dwFlags & DDPF_RGB)
+            {
+                    unsigned long dwtmpLowR;
+                    unsigned long dwtmpLowG;
+                    unsigned long dwtmpLowB;
+                    unsigned long dwtmpChromaLow;
+                    unsigned long dwtmpHighR;
+                    unsigned long dwtmpHighG;
+                    unsigned long dwtmpHighB;
+                    unsigned long dwtmpChromaHigh;
+
+                    switch (lpDPFsrc->dwRGBBitCount) {
+                    case 16:
+                            if (lpDPFsrc->dwGBitMask==0x07E0) //RGB16(5:6:5)
+                            {
+                                    dwtmpLowR = (((dwChromaLow >> 11) << 3) | ((dwChromaLow >> 13) & 0x07)) & 0xFF;
+                                    dwtmpLowG = (((dwChromaLow >> 5) << 2) | ((dwChromaLow >> 9) & 0x03)) & 0xFF;
+
+                                    dwtmpHighR = (((dwChromaHigh >> 11) << 3) | ((dwChromaHigh >> 13) & 0x07)) & 0xFF;
+                                    dwtmpHighG = (((dwChromaHigh >> 5) << 2) | ((dwChromaHigh >> 9) & 0x03)) & 0xFF;
+                            }
+                            else //RGB15(5:5:5)
+                            {
+                                    dwtmpLowR = (((dwChromaLow >> 10) << 3) | ((dwChromaLow >> 12) & 0x07)) & 0xFF;
+                                    dwtmpLowG = (((dwChromaLow >> 5) << 3) | ((dwChromaLow >> 7) & 0x07)) & 0xFF;
+
+                                    dwtmpHighR = (((dwChromaHigh >> 10) << 3) | ((dwChromaHigh >> 12) & 0x07)) & 0xFF;
+                                    dwtmpHighG = (((dwChromaHigh >> 5) << 3) | ((dwChromaHigh >> 7) & 0x07)) & 0xFF;
+                            }
+                            dwtmpLowB = (((dwChromaLow << 3) | (dwChromaLow >> 2)) & 0x07) & 0xFF;
+                            dwtmpChromaLow = (dwtmpLowG << 16) | (dwtmpLowR << 8) | dwtmpLowB;
+                            dwChromaLow = ((dwChromaLow >> 24) << 24) | dwtmpChromaLow;
+
+                            dwtmpHighB = (((dwChromaHigh << 3) | (dwChromaHigh >> 2)) & 0x07) & 0xFF;
+                            dwtmpChromaHigh = (dwtmpHighG << 16) | (dwtmpHighR << 8) | dwtmpHighB;
+                            dwChromaHigh = ((dwChromaHigh >> 24) << 24) | dwtmpChromaHigh;
+                            break;
+
+                    case 32: //32 bit RGB
+                            dwtmpLowR = (dwChromaLow >> 16) & 0xFF;
+                            dwtmpLowG = (dwChromaLow >> 8) & 0xFF;
+                            dwtmpLowB = dwChromaLow & 0xFF;
+                            dwtmpChromaLow = (dwtmpLowG << 16) | (dwtmpLowR << 8) | dwtmpLowB;
+                            dwChromaLow = ((dwChromaLow >> 24) << 24) | dwtmpChromaLow;
+
+                            dwtmpHighR = (dwChromaHigh >> 16) & 0xFF;
+                            dwtmpHighG = (dwChromaHigh >> 8) & 0xFF;
+                            dwtmpHighB = dwChromaHigh & 0xFF;
+                            dwtmpChromaHigh = (dwtmpHighG << 16) | (dwtmpHighR << 8) | dwtmpHighB;
+                            dwChromaHigh = ((dwChromaHigh >> 24) << 24) | dwtmpChromaHigh;
+                            break;
+
+                    default:
+                            //TOINT3;
+                            break;
+                    }
+            }//End of DDPF_FOURCC
+
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_CHROMAKEY_HIGH,dwChromaHigh);
+            if (dwVideoFlag & VIDEO_1_INUSE)
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_CHROMAKEY_LOW, dwChromaLow);
+                //Temporarily solve the H/W Interpolation error when using Chroma Key
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_MINI_CONTROL, miniCtl & 0xFFFFFFF8);
+            }
+            else
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_CHROMAKEY_LOW, dwChromaLow|V_CHROMAKEY_V3);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_MINI_CONTROL, miniCtl & 0xFFFFFFF8);
+            }
+
+            //Modified for select video if (color key & chroma key)
+            if (dwCompose==SELECT_VIDEO_IF_COLOR_KEY)
+               dwCompose = SELECT_VIDEO_IF_COLOR_KEY | SELECT_VIDEO_IF_CHROMA_KEY;
+            else
+               dwCompose = (dwCompose & ~0x0f) | SELECT_VIDEO_IF_CHROMA_KEY;
+        }
+
+        // Determine if V3 is on top
+        if (via->video_win.clipcount == 0)
+            dwCompose |= COMPOSE_V3_TOP;
+            //dwCompose &= ~COMPOSE_V3_TOP;
+        //else
+        //    dwCompose &= ~COMPOSE_V3_TOP;
+
+        // for 3123.C0 H/W bug.
+        // In SAMM mode, when one video on screen0(primary) another video on screen1(second)
+        // H/W still refer to register 298 [20] bit, so the video on screen0 will have so 
+        // garbage of the video on screen1. So, in bellow case must set 298[20] to 1.
+        // In all case which V3 is on Primary Screen, V3 must be on top.
+        //if ( ((!(lpVideoControl->Cap1OnScreen1) || !(lpVideoControl->MPEGOnScreen1)) && (lpVideoControl->Cap0OnScreen1))
+        //       || (!(lpVideoControl->Cap0OnScreen1) && ((lpVideoControl->Cap1OnScreen1) || (lpVideoControl->MPEGOnScreen1))) )
+        //if ( ((lpVideoControl->Cap1OnScreen1)&&!(lpVideoControl->Cap0OnScreen1))
+        //     || ((lpVideoControl->Cap0OnScreen1)&&!(lpVideoControl->Cap1OnScreen1)) 
+        //     || ((lpVideoControl->MPEGOnScreen1)&&!(lpVideoControl->Cap1OnScreen1)) )
+        if ( ((lpVideoControl->VideoStatus & CAP1_ON_SND)&&!(lpVideoControl->VideoStatus & CAP0_ON_SND))
+             || ((lpVideoControl->VideoStatus & CAP0_ON_SND)&&!(lpVideoControl->VideoStatus & CAP1_ON_SND)) 
+             || ((lpVideoControl->VideoStatus & MPEG_ON_SND)&&!(lpVideoControl->VideoStatus & CAP1_ON_SND)) )
+        {
+            dwCompose = dwCompose | COMPOSE_V3_TOP;
+        }
+
+        // for SAMM Mode 
+        //if ( lpVideoControl->Cap1OnScreen1 == 1 )
+        if ( lpVideoControl->VideoStatus & CAP1_ON_SND )
+        {
+            dwVidCtl = dwVidCtl | V1_ON_SND_DISPLAY;
+            dwHQVCtl = dwHQVCtl & 0xFDFFFFFF;
+            
+            if(gVIAGraphicInfo.Cap1_UseIRQ)       // Capture 1 use IRQ, for Cap1 S/W flip
+                dwHQVCtl = dwHQVCtl | HQV_SRC_SW;
+            else
+            dwHQVCtl = dwHQVCtl | HQV_SRC_CAPTURE1;
+            
+            dwCompose = dwCompose | SECOND_DISPLAY_COLOR_KEY_ENABLE;
+        }
+        else
+        {
+            //dwVidCtl = dwVidCtl & 0x7FFFFFFF;
+            dwVidCtl = dwVidCtl & ~V1_ON_SND_DISPLAY;
+            dwVidCtl = dwVidCtl | V1_ON_CRT;
+            dwHQVCtl = dwHQVCtl & 0xFEFFFFFF;
+            dwCompose = dwCompose & 0xFFFEFFFF;
+            
+            if (gdwVideoFlagTV0 & CAP0_USE_HQV)
+                dwHQVCtl = dwHQVCtl | HQV_SRC_CAPTURE0;
+            else
+            {
+                if(gVIAGraphicInfo.Cap1_UseIRQ)       // Capture 1 use IRQ, for Cap1 S/W flip
+                    dwHQVCtl = dwHQVCtl | HQV_SRC_SW;
+                else
+                dwHQVCtl = dwHQVCtl | HQV_SRC_CAPTURE1;
+                
+            }    
+                
+/*            if ( lpVideoControl->Cap0OnScreen1 )
+            {
+                if (gdwVideoFlagTV0 & VIDEO_HQV_INUSE)
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_CONTROL, (dwVidCtl|V1_ENABLE|V1_ON_SND_DISPLAY|VIDEO_HQV_INUSE)&(~V1_SWAP_HW_CAPTURE));
+                else
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_CONTROL, dwVidCtl|V1_ENABLE|V1_ON_SND_DISPLAY);
+                    
+                dwCompose = dwCompose | SECOND_DISPLAY_COLOR_KEY_ENABLE;
+            }*/
+            //else
+                //Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_CONTROL, dwVidCtl);
+                
+//            dwCompose = dwCompose | V1_COMMAND_FIRE;
+        }  
+
+        // Setup video control
+        if (dwVideoFlag & VIDEO_1_INUSE)
+        {
+            /*=* Modify for C1 FIFO *=*/
+            switch ( DispatchVGARevisionID() )
+            {
+                case VIA_REVISION_CLECX :
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_FIFO_CONTROL,
+                        V1_FIFO_DEPTH64 | V1_FIFO_PRETHRESHOLD56 | V1_FIFO_THRESHOLD56);
+                    break;
+                    
+                default:
+                    if (gdwUseExtendedFIFO)
+                    /*if ((gdwUseExtendedFIFO) && !(VIDInD(V3_CONTROL) & V3_ENABLE))*/
+                    {
+                        DBG_DD("CLE_AX Capture 1 Extend FIFO!!!!\n");
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_FIFO_CONTROL,
+                            V1_FIFO_DEPTH48 | V1_FIFO_PRETHRESHOLD40 | V1_FIFO_THRESHOLD40);
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_MINI_CONTROL, miniCtl & ~0x00000007);
+                        /*VIDOutD(V1_MINI_CONTROL, VIDInD(V1_MINI_CONTROL)&~0x00000007);*/
+                        if (gdwVideoFlagTV0 != 0)
+                        {
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,ALPHA_V3_FIFO_CONTROL,V3_FIFO_DEPTH32 | V3_FIFO_THRESHOLD16|
+                            ALPHA_FIFO_DEPTH8 | ALPHA_FIFO_THRESHOLD4);
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,ALPHA_V3_PREFIFO_CONTROL, ALPHA_FIFO_PRETHRESHOLD4|V3_FIFO_PRETHRESHOLD29);
+                             dwCompose = dwCompose|V3_COMMAND_FIRE;
+                        }
+                    }
+                    else
+                    {
+                        DBG_DD("CLE_AX Capture 1 FIFO!!!!\n");
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_FIFO_CONTROL,
+                            V1_FIFO_DEPTH32 | V1_FIFO_PRETHRESHOLD29 | V1_FIFO_THRESHOLD16);
+                    }   
+                    break;                    
+            }
+           
+            
+            
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_CONTROL, dwVidCtl|V1_ENABLE);
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_COMPOSE_MODE, dwCompose|V1_COMMAND_FIRE );          
+        }
+        
+        
+        else
+        {
+            //Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_STRIDE, dwSrcPitch );
+            /*=* Modify for C1 FIFO *=*/
+            switch ( DispatchVGARevisionID() )
+            {
+                case VIA_REVISION_CLECX :
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,ALPHA_V3_FIFO_CONTROL,V3_FIFO_DEPTH64 | V3_FIFO_THRESHOLD56|
+                        ALPHA_FIFO_DEPTH8 | ALPHA_FIFO_THRESHOLD4);
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,ALPHA_V3_PREFIFO_CONTROL, ALPHA_FIFO_PRETHRESHOLD4|V3_FIFO_PRETHRESHOLD56);
+                    break;
+                        
+                default:
+                    if ((gdwUseExtendedFIFO) && !(VIDInD(V1_CONTROL) & V1_ENABLE))
+                    {
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,ALPHA_V3_FIFO_CONTROL,V3_FIFO_DEPTH48 | V3_FIFO_THRESHOLD40|
+                            ALPHA_FIFO_DEPTH8 | ALPHA_FIFO_THRESHOLD4);
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,ALPHA_V3_PREFIFO_CONTROL, ALPHA_FIFO_PRETHRESHOLD4|V3_FIFO_PRETHRESHOLD40);
+                    }
+                    else
+                    {
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,ALPHA_V3_FIFO_CONTROL,V3_FIFO_DEPTH32 | V3_FIFO_THRESHOLD16|
+                            ALPHA_FIFO_DEPTH8 | ALPHA_FIFO_THRESHOLD4);
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,ALPHA_V3_PREFIFO_CONTROL, ALPHA_FIFO_PRETHRESHOLD4|V3_FIFO_PRETHRESHOLD29);
+                    }
+                    break;
+            }            
+            
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_CONTROL, dwVidCtl|V3_ENABLE);
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_COMPOSE_MODE, dwCompose|V3_COMMAND_FIRE );
+                        
+        }
+        
+        if (dwVideoFlag & VIDEO_HQV_INUSE)
+        {
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,HQV_CONTROL, dwHQVCtl|HQV_FLIP_STATUS);
+        }
+        Macro_VidREGFlushVPE();
+
+        if (!TV1_ON)
+        {
+            if (!(dwVideoFlag & VIDEO_1_INUSE))
+            {
+                if (gdwUseExtendedFIFO)
+                {
+                    VIDOutD(V1_CONTROL, VIDInD(V1_CONTROL)|V1_FIFO_EXTENDED);
+                    VIDOutD(V_COMPOSE_MODE, (dwCompose|V1_COMMAND_FIRE ));
+                    //Set Display FIFO
+                    WaitVBI();
+                            outb(0x17, 0x3C4); outb(0x2f, 0x3C5);
+                            outb(0x16, 0x3C4); outb((Save_3C4_16&0xf0)|0x14, 0x3C5);
+                            outb(0x18, 0x3C4); outb(0x56, 0x3C5);
+                }
+            }
+        }
+    }
+    else
+    {       
+        //Hide overlay
+        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_FIFO_CONTROL,V1_FIFO_PRETHRESHOLD12 |
+             V1_FIFO_THRESHOLD8 |V1_FIFO_DEPTH16);
+        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,ALPHA_V3_FIFO_CONTROL, ALPHA_FIFO_THRESHOLD4 
+             | ALPHA_FIFO_DEPTH8  | V3_FIFO_THRESHOLD24 | V3_FIFO_DEPTH32 );
+
+        if (dwVideoFlag&VIDEO_HQV_INUSE)
+        {
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,HQV_CONTROL, (VIDInD(HQV_CONTROL) & (~HQV_ENABLE)));            
+        }
+        
+        if (dwVideoFlag&VIDEO_1_INUSE)
+        {
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_CONTROL, (VIDInD(V1_CONTROL) & (~V1_ENABLE)));
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_COMPOSE_MODE, (VIDInD(V_COMPOSE_MODE)|V1_COMMAND_FIRE));          
+        }
+        else
+        {
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_CONTROL, (VIDInD(V3_CONTROL) & (~V3_ENABLE)));
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_COMPOSE_MODE, (VIDInD(V_COMPOSE_MODE)|V3_COMMAND_FIRE));            
+        }
+
+        Macro_VidREGFlushVPE();        
+    }    
+
+    return PI_OK;
+    
+}
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/capture.h linux-2.6.1-rc1-gentoo/drivers/media/video/capture.h
--- linux-2.6.0/drivers/media/video/capture.h	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/capture.h	2004-01-06 17:28:06.000000000 +0000
@@ -0,0 +1,186 @@
+ /*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#ifndef __LINUX_VIACAP_H
+#define __LINUX_VIACAP_H
+
+#ifndef XFree86Server
+#include "via_types.h"
+#endif
+
+/*Definition for  CapturePortID*/
+#define PORT0     0      /* Capture Port 0*/
+#define PORT1     1      /* Capture Port 1*/
+
+typedef struct _VIAVIDCTRL{
+  unsigned short  PORTID;
+  unsigned long dwCompose;
+  unsigned long dwHighQVDO;
+  unsigned long VideoStatus;
+  unsigned long dwAction;
+  /*Bool  Cap0OnScreen1;*/   /* True: Capture0 On Screen1 ; False: Capture0 On Screen0 */
+  /*Bool  Cap1OnScreen1;*/   /* True: Capture1 On Screen1 ; False: Capture1 On Screen0 */
+  /*Bool  MPEGOnScreen1;*/   /* True: MPEG On Screen1 ; False: MPEG On Screen0 */
+} VIAVIDCTRL;
+typedef VIAVIDCTRL * LPVIAVIDCTRL;
+
+#define ACTION_SET_PORTID      0
+#define ACTION_SET_COMPOSE     1
+#define ACTION_SET_HQV         2
+#define ACTION_SET_BOB	       4
+#define ACTION_SET_VIDEOSTATUS 8
+
+
+typedef struct _VIACAPINFO{
+  int CapInterVersion;    /* The capture internal version */
+  Bool NoAutoDetect;
+  unsigned long dwDeinterlaceMode;  /* Capture deinterlace mode: bob/weave */
+  unsigned long FieldSwap;          /* input field swap, only for Capture 0 */
+  unsigned long No_HFilter;         /* Capture horizontal filter select   */
+  unsigned long Capture_OverScanOff;   /* Capture Over Scan function select    */
+  unsigned long VideoDecoder;       /* VideoDecoder type */
+  unsigned long Tuner;              /* Tuner type */
+  unsigned long TVEncoder;          /* TVEncoder type */
+  int   Vdec_Slave_Write;
+  int   Tuner_Slave_Write;
+  int   TVEncoder_Slave_Write;
+  int   DataWidth;                  /* data output bus: 8 or 16 */
+  int   CompositeMode;
+  int   SVideoMode;
+  int   TunerMode;
+  int   Scaler;                     /* 1: use video decoder scaler function, 0: not use */
+  int   Brightness;
+  int   Contrast;
+  int   Hue;
+  int   Saturation;
+  int   Standard;                   /* PAL/NTSC/SECAM */
+  unsigned long Reserved[64];       /* For future use */
+} VIACAPINFO;
+typedef VIACAPINFO * LPVIACAPINFO;
+
+
+typedef struct _VIAAUDCTRL{
+  unsigned long dwAudioMode ;  /* Audio Mode         */
+  int   nVolume     ;  /* Volume             */
+} VIAAUDCTRL ;
+typedef VIAAUDCTRL * LPVIAAUDCTRL;
+
+
+/* Definition for dwFlags */
+
+#define DDOVER_KEYDEST    0x00000004
+
+
+/*
+ * structure of Set Port Attribute
+ */
+typedef struct _VIASETPORTATTR    {
+    int                   attribute;
+    int                   value;
+} VIASETPORTATTR ;
+typedef VIASETPORTATTR  * LPVIASETPORTATTR;
+
+
+/*
+ * structure of Set Tuner
+ */
+typedef struct _VIASETTUNERDATA    {
+    int   divider;
+    int   control;
+} VIASETTUNERDATA ;
+typedef VIASETTUNERDATA  * LPVIASETTUNERDATA;
+
+
+/*Definition for  LPVIAGETPORTATTR->attribute*/
+#define ATTR_ENCODING         0                  /* XV_ENCODING  */
+#define ATTR_INIT_AUDIO       ATTR_ENCODING+50   /* XV_MUTE      */
+#define ATTR_MUTE_ON          ATTR_ENCODING+51   /* XV_MUTE      */
+#define ATTR_MUTE_OFF         ATTR_ENCODING+52   /* XV_MUTE      */
+#define ATTR_VOLUME           ATTR_ENCODING+53   /* XV_VOLUME    */
+#define ATTR_STEREO           ATTR_ENCODING+54   /* XV_VOLUME    */
+#define ATTR_SAP              ATTR_ENCODING+55   /* XV_SAP       */
+#define ATTR_TUNER_AUDIO_SWITCH   ATTR_ENCODING+56   /* XV_TUNER_AUDIO*/
+#define ATTR_AUDIO_CONTROLByAP    ATTR_ENCODING+57   /* XV_AUDIOCTRL  */
+
+
+void VIAStopVideo(void);
+
+#define DEV_TV0   0
+#define DEV_TV1   1
+
+
+typedef struct _CAPDEVICE
+{
+/* unsigned char * lpCAPOverlaySurface[3];*/   /* Max 3 Pointers to CAP Overlay Surface*/
+/* unsigned long  dwCAPPhysicalAddr[3];*/     /*Max 3 Physical address to CAP Overlay Surface*/
+ unsigned char * lpCAPOverlaySurface[4];  /*Max 4 Pointers to CAP Overlay Surface*/
+ unsigned long  dwCAPPhysicalAddr[4];     /*Max 4 Physical address to CAP Overlay Surface*/
+/* unsigned long  dwHQVAddr[2];*/			  /*Max 2 Physical address to CAP HQV Overlay Surface*/
+ unsigned long  dwHQVAddr[3];             /*Max 3 Physical address to CAP HQV Overlay Surface*/
+ unsigned long  dwWidth;                  /*CAP Source Width, not changed*/
+ unsigned long  dwHeight;                 /*CAP Source Height, not changed*/
+ unsigned long  dwPitch;                  /*CAP frame buffer pitch*/
+ unsigned char   byDeviceType;             /*Device type. Such as DEV_TV1 and DEV_TV0*/
+ unsigned long  gdwCAPSrcWidth;           /*CAP Source Width, changed if window is out of screen*/
+ unsigned long  gdwCAPSrcHeight;          /*CAP Source Height, changed if window is out of screen*/
+ unsigned long  gdwCAPDstWidth;           /*CAP Destination Width*/
+ unsigned long  gdwCAPDstHeight;          /*CAP Destination Height*/
+ unsigned long  gdwCAPDstLeft;            /*CAP Position : Left*/
+ unsigned long  gdwCAPDstTop;             /*CAP Position : Top*/
+ unsigned long  dwDeinterlaceMode;        /*BOB / WEAVE*/
+}CAPDEVICE;
+typedef CAPDEVICE * LPCAPDEVICE;
+
+int  VIA_CAPSetFrameBuffer( LPCAPDEVICE lpDevice);
+
+typedef struct _ALPHADEVICE
+{
+ unsigned char * lpALPOverlaySurface;
+ unsigned long  dwALPPhysicalAddr;
+ unsigned long  dwPitch;
+ unsigned long  gdwALPSrcWidth;
+ unsigned long  gdwALPSrcHeight;
+ unsigned long  gdwALPDstWidth;
+ unsigned long  gdwALPDstHeight;
+ unsigned long  gdwALPDstLeft;
+ unsigned long  gdwALPDstTop;
+}ALPHADEVICE;
+typedef ALPHADEVICE * LPALPHADEVICE;
+
+typedef struct{ 
+         unsigned char type;
+         unsigned char ConstantFactor;   /* only valid in bit0 - bit3 */
+         Bool AlphaEnable;       
+} ALPHACTRL ,*LPALPHACTRL;
+
+#define ALPHA_CONSTANT  0x01
+#define ALPHA_STREAM    0x02
+#define ALPHA_DISABLE   0x03
+#define ALPHA_GRAPHIC   0x04
+#define ALPHA_COMBINE   0x05
+
+
+int VIA_ALPSetFrameBuffer(LPALPHADEVICE lpDevice);
+#endif  
+
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/compose.h linux-2.6.1-rc1-gentoo/drivers/media/video/compose.h
--- linux-2.6.0/drivers/media/video/compose.h	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/compose.h	2004-01-06 17:28:06.000000000 +0000
@@ -0,0 +1,69 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+/* Definition of APs Distribution */
+#ifndef __COMPOSE_H
+#define __COMPOSE_H
+
+  /* Video Control definition */
+  #define VW_DVD_ONLY              0x00000001  /* ????????????????? */
+  #define VW_TV_ONLY               0x00000002  /* ????????????????? */
+/*#define VW_INTERNAL_OPAQUE       0x00000008 */ /* ????????????????? */
+
+  #define VW_DVD_TOP               0x00000010  /* ATOM("XV_COMPOSE") */
+  #define VW_TV_TOP                0x00000020  /* ATOM("XV_COMPOSE") */
+  #define VW_TV0_TOP               0x00000100  /* ATOM("XV_COMPOSE") */
+  #define VW_TV1_TOP               0x00000200  /* ATOM("XV_COMPOSE") */
+/*#define VW_TV_FULL               0x00000400 */ /*Not recommended*/
+
+  #define VW_BOB_TV0               0x00010000  /* ATOM("XV_BOB") */
+  #define VW_BOB_TV1               0x00020000  /* ATOM("XV_BOB") */
+/*#define VW_WEAVE_TV1             0x00040000 */ /* ATOM("XV_BOB") */
+/*#define VW_WEAVE_TV2             0x00080000 */ /* ATOM("XV_BOB") */
+
+  #define VW_HIGHQVDO_SWITCH       0x00000000  /* ATOM("XV_HIGHQVDO") */
+  #define VW_HIGHQVDO_OFF          0x00000000  /* ATOM("XV_HIGHQVDO") */
+  #define VW_HIGHQVDO_DVD          0x00000001  /* ATOM("XV_HIGHQVDO") */
+  #define VW_HIGHQVDO_TV0          0x00000002  /* ATOM("XV_HIGHQVDO") */
+  #define VW_HIGHQVDO_TV1          0x00000004  /* ATOM("XV_HIGHQVDO") */
+  
+
+  /* Audio Control definition */
+  /* Quality */
+  #define AUDIO_STEREO       0x00000001        /* ATOM("XV_AUDIOCTRL") */
+  #define AUDIO_SAP          0x00000002        /* ATOM("XV_AUDIOCTRL") */
+  #define AUDIO_DUAL         0x00000004        /* ATOM("XV_AUDIOCTRL") */
+
+  /* Mute */
+  #define AUDIO_ON           0x00000010        /* ATOM("XV_AUDIOCTRL") */
+  #define AUDIO_OFF          0x00000020        /* ATOM("XV_AUDIOCTRL") */
+
+  /* Source */  
+  #define AUDIO_TV0          0x00000100        /* ATOM("XV_AUDIOCTRL") */
+  #define AUDIO_TV1          0x00000200        /* ATOM("XV_AUDIOCTRL") */
+  #define AUDIO_SVIDEO       0x00000400        /* not available now    */
+  #define AUDIO_COMPOSE      0x00000800        /* 		               */	
+                                                
+#endif  /*end of __COMPOSE_H*/
+
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/ddmpeg.c linux-2.6.1-rc1-gentoo/drivers/media/video/ddmpeg.c
--- linux-2.6.0/drivers/media/video/ddmpeg.c	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/ddmpeg.c	2004-01-06 18:03:30.000000000 +0000
@@ -0,0 +1,5118 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+           
+// I N C L U D E S ----------------------------------------------------------
+#include <linux/delay.h>        /* for delay-stuff ex: udelay */
+#include <linux/slab.h>         /* for kmalloc/kfree */
+
+#include "via_types.h"
+#include "compose.h"
+#include "via.h"
+#include "ddmpeg.h"
+#include "capture.h"
+#include "via_privIoctl.h" /* for VIAGRAPHICINFO & custom ioctl command */
+#include "HWDiff.h"
+
+#include "vdec.h"
+#include "via_tuner.h"
+#include "audio.h"
+#include "regrec.h"
+#include "via_v4l.h"
+#include "ddover.h"
+#include "via_memmgr.h"
+
+/* Use DRM memory management */
+#include "drm.h"
+#include "via_mm.h"
+
+// D E F I N E --------------------------------------------------------------
+#define     VIA_PITCH_ALIGNMENT 8
+#define     VIA_SURFACE_ALIGNMENT 8           //256 byte
+#define     PAGECNT           4
+
+#if defined (CONFIG_DRM_VIA) | defined(CONFIG_DRM_VIA_MODULE)
+#define HAVE_DRM
+#endif
+
+// F U N C T I O N  D E C L A R A T I O N -----------------------------------
+//void VIAAlphaWin( LPALPHACTRL );
+unsigned long Upd_Video(unsigned long dwVideoFlag,unsigned long dwStartAddr,RECTL rSrc,RECTL rDest,unsigned long dwSrcPitch,
+                 unsigned long dwOriSrcWidth,unsigned long dwOriSrcHeight,LPDDPIXELFORMAT lpDPFsrc,
+                 unsigned long dwDeinterlaceMode,unsigned long dwColorKey,unsigned long dwChromaKey,
+                 unsigned long dwKeyLow,unsigned long dwKeyHigh,unsigned long dwChromaLow,unsigned long dwChromaHigh, unsigned long dwFlags);
+
+unsigned long Upd_MPEG(unsigned long dwVideoFlag,RECTL rSrc,RECTL rDest,unsigned
+                       long dwSrcPitch, unsigned long dwOriSrcWidth,unsigned long dwOriSrcHeight,LPDDPIXELFORMAT lpDPFsrc, unsigned long
+                       dwDeinterlaceMode,unsigned long dwColorKey,unsigned long dwChromaKey, unsigned long dwKeyLow,unsigned long dwKeyHigh,
+                       unsigned long dwChromaLow,unsigned long dwChromaHigh, unsigned long dwFlags );
+
+void MPEGFlipCurrentFrame( void );
+
+
+// E X T E R N   G L O B A L S ----------------------------------------------
+extern via_device   via_v4l_devices[MAX_VIA_BOARDS];
+extern LPVIAVIDCTRL lpVideoControl;     //video control
+extern VIAGRAPHICINFO gVIAGraphicInfo;  // 2D information
+
+extern volatile unsigned char  * lpVidMEMIO;
+/* Pointer to On-Screen frame buffer linear address */
+extern unsigned char  * lpPrimarySurface;
+extern VIDHWDIFFERENCE VideoHWDifference;
+
+// E X T E R N   F U N C T I O N S ------------------------------------------
+extern unsigned long HQVControl( LPVIAVIDCTRL lpNewVidCtl );
+
+//To solve the bandwidth issue
+extern unsigned char Save_3C4_16;
+extern unsigned char Save_3C4_17;
+extern unsigned char Save_3C4_18;
+extern unsigned long gdwOverlaySupport;
+
+
+
+// G L O B A L   V A R I A B L E S ------------------------------------------
+//unsigned long   gdwVideoOn = 0;
+unsigned long   gdwVideoFlagMPEG=0;
+unsigned long   gdwVideoFlagTV0=0;
+unsigned long   gdwVideoFlagTV1=0;
+unsigned long   gdwVideoFlagSW=0;
+unsigned long   gdwAlphaEnabled = 0;		// For Alpha blending use
+									// Coz enable alpha should disalbe colorkey
+/* memory management */
+ViaMMReq MPEGMemRequest;
+ViaMMReq SUBPMemRequest;
+ViaMMReq HQVMemRequest;
+ViaMMReq TV0MemRequest;
+ViaMMReq TV1MemRequest;
+ViaMMReq ALPHAMemRequest;
+ViaMMReq SWMemRequest;
+
+/* for DRM memory management */
+#ifdef HAVE_DRM
+drm_via_mem_t MPEGfbRequest;
+drm_via_mem_t SUBPfbRequest;
+drm_via_mem_t HQVfbRequest;
+drm_via_mem_t TV0fbRequest;
+drm_via_mem_t TV1fbRequest;
+drm_via_mem_t ALPHAfbRequest;
+drm_via_mem_t SWfbRequest;
+#endif
+
+/* device struct */
+CAPDEVICE   CAPDevice[2];
+ALPHADEVICE ALPDevice;
+SWDEVICE   SWDevice;
+SUBDEVICE   SUBDevice;
+MPGDEVICE   MPGDevice;
+LPMPGDEVICE lpMPGDevice = &MPGDevice;
+OVERLAYRECORD   overlayRecordV1;
+OVERLAYRECORD   overlayRecordV3;
+
+DDPIXELFORMAT DPFsrc;       // To indicate which fourcc used
+LPDDPIXELFORMAT lpDPFsrc = &DPFsrc;
+DDUPDATEOVERLAY UpdateOverlayBackup;    // For HQVcontrol func use
+                                        // To save MPEG updateoverlay info.
+//Pointer to MMIO Address
+//volatile unsigned char  * lpGEMMIO;
+//volatile unsigned char  * lpMPEGMMIO;
+
+Bool TV_DEINTERLACE_BOB = TRUE;
+
+Bool SWVideo_ON = FALSE;
+Bool MPEG_ON = FALSE;
+Bool TV0_ON  = FALSE;
+Bool TV1_ON  = FALSE;
+
+//To solve the bandwidth issue
+unsigned long   gdwUseExtendedFIFO = 0;
+
+/*Performing minify, V3 has no interpolation( only drop pixel ) horizontally and vertically. */
+/*Titan suggests that S/W use Capture engine( with interpolation ) to minify width by 2      */
+/*Otherwise, it causes poor video quality.                                                   */
+//Bool TV1_MINIFY_HOR_2 = TRUE;
+
+/* For panning mode use */
+/* Fixed for SAMM and both of primary & secondary          */
+/* screens are in Panning Mode,Video display size          */
+/* & position may be errors while VIAAdjustFrame is called.*/
+int panning_old_x[2]={0,0};
+int panning_old_y[2]={0,0};
+int panning_x[2]={0,0};
+int panning_y[2]={0,0};
+
+unsigned char VDEC_Type = 0;    /* for detect VDEC Tybe 2003-1-30 */
+//int UpdateOverlay_count = 0;
+
+
+unsigned long DispatchVGARevisionID(void)
+{
+   if ( gVIAGraphicInfo.RevisionID >= VIA_REVISION_CLECX )
+   {
+   	return  VIA_REVISION_CLECX;
+   }
+   else
+   {
+       return   gVIAGraphicInfo.RevisionID;
+   }
+}
+
+/*
+ *  Create overlay surface depend on FOURCC
+ */
+unsigned long CreateSurface( LPDDSURFACEDESC lpDDSurfaceDesc)
+{
+    unsigned long   dwWidth, dwHeight, dwPitch=0;
+    unsigned long   dwBackBufferCount;
+    unsigned long   dwRet=PI_OK;
+    unsigned long   dwAddr = 0;
+    unsigned long   SUBPFBSIZE = 0;
+    unsigned long   MPEGFBSIZE = 0;
+    unsigned long   HQVFBSIZE   = 0;
+    unsigned long   TVFBSIZE    = 0;
+    unsigned long   ALPHAFBSIZE = 0;
+    unsigned long   SWFBSIZE    = 0;
+    int             iCount;       // iCount for clean HQV FB use
+    unsigned char  * lpTmpAddr;    // for clean HQV FB use
+    VIAVIDCTRL NewvidCtrl;
+    LPVIAVIDCTRL lpNewVidCtrl = &NewvidCtrl;
+    LPVIDHWDIFFERENCE lpVideoHWDifference = &VideoHWDifference;
+    
+    /*Added for SAMM Mode*/
+    int ScrnIndex = 0;
+    
+    DBG_DD("//CreateSurface: \n");
+
+    if ( lpDDSurfaceDesc == NULL )
+        return PI_ERR;
+
+    switch (lpDDSurfaceDesc->dwFourCC)
+    {
+        case FOURCC_SUBP:
+            DBG_DD("   Create subpicture surface:\n");
+            
+            dwWidth = lpDDSurfaceDesc->dwWidth;
+            dwHeight = lpDDSurfaceDesc->dwHeight;
+            dwPitch = (dwWidth + 0x1F)&0xffffffe0;
+            
+            SUBPFBSIZE = dwPitch*dwHeight;
+            
+            if (!gVIAGraphicInfo.DRMEnabled)
+            {
+                
+            SUBPMemRequest.checkID = VIA_MID;
+                SUBPMemRequest.size = SUBPFBSIZE*2;
+            SUBPMemRequest.type = VIDMGR_TYPE_VIDEO;
+			    
+            if ( MEM_OK != viaMgr_vid_ioctl(VIAMGR_ALLOC_VIDEO, (char *)(&SUBPMemRequest) ) )
+                {
+                    DBG_DD(" Memory Allocation fail for Subpicture surface \n");
+                    return PI_ERR_CANNOT_CREATE_SURFACE;
+                }
+                dwAddr = ALIGN_TO_32_BYTES(SUBPMemRequest.offset);
+		    }
+#ifdef HAVE_DRM
+            else
+        {  
+			SUBPfbRequest.context = 1; 
+			SUBPfbRequest.size = SUBPFBSIZE*2;
+            SUBPfbRequest.type = VIDEO;
+            
+			via_fb_alloc(&SUBPfbRequest);
+			
+			dwAddr = SUBPfbRequest.offset;
+        }
+#endif
+		SUBDevice.dwSUBPhysicalAddr[1] = dwAddr + SUBPFBSIZE;
+		SUBDevice.dwSUBPhysicalAddr[0] = dwAddr;
+
+        if (SUBDevice.dwSUBPhysicalAddr[1]+SUBPFBSIZE > gVIAGraphicInfo.Screen[ScrnIndex].VideoHeapEnd)
+		{
+			DBG_DD(" Memory not enough for MPEG \n");
+                        return PI_ERR_CANNOT_CREATE_SURFACE;			
+		}
+		
+		SUBDevice.gdwSUBSrcWidth = dwWidth;
+		SUBDevice.gdwSUBSrcHeight = dwHeight;
+		SUBDevice.dwPitch = dwPitch;
+		overlayRecordV1.dwSPPitch = dwPitch;
+        
+		VIDOutD(0x1c0, dwPitch);
+		
+		DBG_DD("000003c0 %08lx\n", dwPitch );
+        
+		lpMPGDevice->dwSUBPPitch = dwPitch;
+		MPGDevice.byDeviceType = 1;
+		MPGDevice.gdwSUBP_NotVisible = 1;
+		
+		break;
+        
+        case FOURCC_VIA:
+            DBG_DD("   Create MPEG Surface:\n");
+            
+        lpDPFsrc->dwFlags = DDPF_FOURCC;
+        lpDPFsrc->dwFourCC = FOURCC_VIA;
+            
+            
+//TODO check what this optimised logic is nicely.
+            switch (DispatchVGARevisionID())
+            {
+                case VIA_REVISION_CLECX:
+            gdwVideoFlagMPEG = VIDEO_SHOW | VIDEO_MPEG_INUSE | VIDEO_HQV_INUSE | VIDEO_1_INUSE |
+                MPEG_USE_HW_FLIP | MPEG_USE_HQV | MPEG_USE_V1;/*   0x8d070000;*/
+                    break;
+                default:
+            gdwVideoFlagMPEG = VIDEO_SHOW | VIDEO_MPEG_INUSE | VIDEO_HQV_INUSE | VIDEO_1_INUSE |
+                MPEG_USE_HQV | MPEG_USE_V1; /*0x8d030000;*/
+                    break;
+            }
+            
+        if ( gdwVideoFlagTV1 & VIDEO_HQV_INUSE )
+            {
+                lpNewVidCtrl->dwHighQVDO = 0;
+            VIADriverProc( HQVCONTROL, lpNewVidCtrl );
+            }
+            
+            overlayRecordV1.dwMPEGDeinterlaceMode = 0;
+            overlayRecordV1.dwMpegDecoded = 0;
+            
+        //Color Space Conversion
+        if (!gVIAGraphicInfo.ColorSpaceChanged)    
+        {
+            switch ( DispatchVGARevisionID() )
+	     	{
+                case VIA_REVISION_CLECX :
+                    VIDOutD(V1_ColorSpaceReg_1, 0x13000DED);
+                    VIDOutD(V1_ColorSpaceReg_2, 0x13171000);         
+                    DBG_DD("000002C4 %08x\n", 0x13000DED );
+                    DBG_DD("000002C8 %08x\n", 0x13171000 );
+                    break;
+                default:
+                    VIDOutD(V1_ColorSpaceReg_1,0x140020F2);
+                    VIDOutD(V1_ColorSpaceReg_2,0x0a0a2c00);         
+                    DBG_DD("00000284 %08x\n", 0x140020F2 );
+                    DBG_DD("00000288 %08x\n", 0x0a0a2c00 );
+                    break;
+            }	
+        }
+        else
+        {
+            VIDOutD(V1_ColorSpaceReg_1, gVIAGraphicInfo.ColorSpaceValue1);
+            VIDOutD(V1_ColorSpaceReg_2, gVIAGraphicInfo.ColorSpaceValue2);
+        } 
+                
+            
+            dwBackBufferCount=lpDDSurfaceDesc->dwBackBufferCount;
+            
+            dwWidth=lpDDSurfaceDesc->dwWidth;
+            dwHeight=lpDDSurfaceDesc->dwHeight;
+            dwPitch=ALIGN_TO_32_BYTES(dwWidth);
+            
+            MPEGFBSIZE = dwPitch*dwHeight*1.5;
+			
+            if (!gVIAGraphicInfo.DRMEnabled)
+            {
+            DBG_DD("vid_ioctl\n");
+
+            MPEGMemRequest.checkID = VIA_MID;
+                MPEGMemRequest.size = MPEGFBSIZE*(dwBackBufferCount+1) + dwPitch*4;
+            MPEGMemRequest.type = VIDMGR_TYPE_VIDEO;
+			    
+            if ( MEM_OK != viaMgr_vid_ioctl(VIAMGR_ALLOC_VIDEO, (char *)(&MPEGMemRequest) ) )
+                {
+                    DBG_DD(" Memory Allocation fail for MPEG Video \n");
+                    return PI_ERR_CANNOT_CREATE_SURFACE;
+                }
+                dwAddr = ALIGN_TO_32_BYTES(MPEGMemRequest.offset);
+		    }
+#ifdef HAVE_DRM
+            else
+            {  
+            DBG_DD("fb_alloc\n");
+          
+                MPEGfbRequest.context = 1; 
+                MPEGfbRequest.size = MPEGFBSIZE*(dwBackBufferCount+1) + dwPitch*4;
+            MPEGfbRequest.type = VIDEO;
+                
+                via_fb_alloc(&MPEGfbRequest);
+                
+                dwAddr = MPEGfbRequest.offset;
+            }
+#endif
+        if (!dwAddr)
+        {
+            DBG_DD("No address. :-(\n");
+            return PI_ERR_CANNOT_CREATE_SURFACE;
+        }
+            
+            //
+            lpMPGDevice->lpMPEGOverlaySurface[0] = lpPrimarySurface + dwAddr;		    
+            lpMPGDevice->dwMPEGYPhysicalAddr[0] = dwAddr;		    
+            lpMPGDevice->dwMPEGPhysicalAddr[0] = dwAddr;
+		    
+            lpMPGDevice->dwMPEGCbPhysicalAddr[0] = lpMPGDevice->dwMPEGYPhysicalAddr[0] + dwPitch*dwHeight;
+            lpMPGDevice->dwMPEGCrPhysicalAddr[0] = lpMPGDevice->dwMPEGCbPhysicalAddr[0] + (dwPitch>>1)*(dwHeight>>1);
+            
+            for (iCount = 1; iCount<=dwBackBufferCount; iCount++)
+            {
+                lpMPGDevice->dwMPEGPhysicalAddr[iCount]= MPEGFBSIZE + lpMPGDevice->dwMPEGPhysicalAddr[iCount-1];
+                lpMPGDevice->lpMPEGOverlaySurface[iCount]= MPEGFBSIZE + lpMPGDevice->lpMPEGOverlaySurface[iCount-1];
+                lpMPGDevice->dwMPEGYPhysicalAddr[iCount]= MPEGFBSIZE + lpMPGDevice->dwMPEGYPhysicalAddr[iCount-1];
+                lpMPGDevice->dwMPEGCbPhysicalAddr[iCount]= dwPitch*dwHeight + lpMPGDevice->dwMPEGYPhysicalAddr[iCount];
+                lpMPGDevice->dwMPEGCrPhysicalAddr[iCount]= (dwPitch>>1)*(dwHeight>>1) + lpMPGDevice->dwMPEGCbPhysicalAddr[iCount];
+            }
+	
+        if (MPGDevice.dwMPEGPhysicalAddr[dwBackBufferCount]+MPEGFBSIZE > gVIAGraphicInfo.Screen[ScrnIndex].VideoHeapEnd)
+            {
+            DBG_DD(" Memory not enough for MPEG \n");
+            return PI_ERR_CANNOT_CREATE_SURFACE;
+            }
+            
+        for (iCount = 0; iCount<=dwBackBufferCount; iCount++)
+            {
+            lpTmpAddr = lpPrimarySurface + lpMPGDevice->dwMPEGPhysicalAddr[iCount];
+            unsigned long pos;
+            for (pos = 0; pos < (dwPitch*dwHeight); pos++)
+            {
+                *(lpTmpAddr++) = 0;
+            }
+            
+            for (pos = 0; pos < (dwPitch*dwHeight/2); pos++)
+            {
+                *(lpTmpAddr++) = 0x80;
+            }
+            }
+            
+            MPGDevice.dwWidth = dwWidth;
+            MPGDevice.dwHeight = dwHeight;
+            MPGDevice.dwPitch = dwPitch;
+            MPGDevice.gdwMPGSrcWidth = dwWidth;
+            MPGDevice.gdwMPGSrcHeight = dwHeight;
+            overlayRecordV1.dwV1OriWidth = dwWidth;
+            overlayRecordV1.dwV1OriHeight = dwHeight;
+            MPGDevice.lpVideoMemIO = lpVidMEMIO;
+            overlayRecordV1.dwV1OriPitch = dwPitch;
+            VIDOutD(0x3c, dwPitch);
+		
+		DBG_DD("0000023c %08lx\n", dwPitch );
+        
+        int i;
+        for (i=0; i<4; i++)
+        {
+            DBG_DD("v4l[%d].vendor %08lx\n", i, via_v4l_devices[i].vendorID);
+        }
+
+		MPGDevice.dwVendorID = via_v4l_devices[2].vendorID;
+            MPGDevice.dwDeviceID = via_v4l_devices[2].deviceID;
+            MPGDevice.dwRevisionID= via_v4l_devices[2].revision;
+            MPGDevice.dwSubVendorID= via_v4l_devices[2].subvendorID;
+            MPGDevice.dwSubDeviceID= via_v4l_devices[2].subdeviceID;
+		MPGDevice.byDeviceType=0;
+
+		if (gVIAGraphicInfo.RevisionID<=2)
+			MPGDevice.dwEnableErrorConcealment=0;
+		else
+			MPGDevice.dwEnableErrorConcealment=1;
+
+		if (!gdwVideoFlagMPEG & MPEG_USE_HQV)
+			break;
+
+	case FOURCC_HQVMPEG :
+		DBG_DD("    Create MPEG HQV Surface: \n");
+        
+		dwHeight = lpMPGDevice->dwHeight;
+		dwWidth = lpMPGDevice->dwWidth;
+		dwPitch = lpMPGDevice->dwPitch;
+
+		HQVFBSIZE = dwPitch * dwHeight * 2;
+
+		if (!gVIAGraphicInfo.DRMEnabled)
+		{
+            HQVMemRequest.checkID = VIA_MID; //
+			 //HQVMemRequest.size    = (HQVFBSIZE*2);
+			if (lpVideoHWDifference->dwThreeHQVBuffer) //
+			{
+				HQVMemRequest.size = HQVFBSIZE*3;
+			}else
+			{
+				HQVMemRequest.size = HQVFBSIZE*2;
+			}
+			//HQVMemRequest.size    = (HQVFBSIZE*2)+((dwPitch<<1)*4);
+
+            HQVMemRequest.type = VIDMGR_TYPE_VIDEO;
+
+            if (MEM_OK != viaMgr_vid_ioctl(VIAMGR_ALLOC_VIDEO, (char*)(&HQVMemRequest)))
+			{
+				DBG_DD("Memory allocation fail for MPEG HQV Video\n");
+				return PI_ERR_CANNOT_CREATE_SURFACE;
+			}
+
+            dwAddr = ALIGN_TO_32_BYTES(HQVMemRequest.offset);
+		}
+#ifdef HAVE_DRM
+		else
+		{
+			HQVfbRequest.context = 1;
+
+			if (lpVideoHWDifference->dwThreeHQVBuffer)
+				HQVfbRequest.size = (HQVFBSIZE*3);
+            else
+				HQVfbRequest.size = (HQVFBSIZE*2);
+
+            HQVfbRequest.type = VIDEO;
+			via_fb_alloc(&HQVfbRequest);
+
+			dwAddr = HQVfbRequest.offset;
+		}
+#endif
+		MPGDevice.dwHQVAddr[0]=dwAddr;
+		MPGDevice.dwHQVAddr[1]=dwAddr + HQVFBSIZE;
+
+		if (lpVideoHWDifference->dwThreeHQVBuffer)
+		{
+			MPGDevice.dwHQVAddr[2] = MPGDevice.dwHQVAddr[1] + HQVFBSIZE;
+
+            if (MPGDevice.dwHQVAddr[2] + HQVFBSIZE >= (unsigned long)gVIAGraphicInfo.Screen[ScrnIndex].VideoHeapEnd)
+			{
+				DBG_DD("//    :Memory not enough for MPEG with HQV\n");
+				return PI_ERR_CANNOT_CREATE_SURFACE;
+			}
+
+		}else
+		{
+            if (MPGDevice.dwHQVAddr[1] + HQVFBSIZE >= (unsigned long)gVIAGraphicInfo.Screen[ScrnIndex].VideoHeapEnd)
+			{
+				DBG_DD("//    :Memory not enough for MPEG with HQV\n");
+				return PI_ERR_CANNOT_CREATE_SURFACE;
+			}
+		}
+
+		//fill in the HQV buffer with 0x8000 (YUY2-black color) to clear HQV buffers
+		//shouldn;t this only blank the number of buffers being used?
+
+        for(iCount=0;iCount < (lpVideoHWDifference->dwThreeHQVBuffer ? HQVFBSIZE*3 : HQVFBSIZE*2); iCount++)
+		{
+			lpTmpAddr = lpPrimarySurface + dwAddr + iCount;
+		        if((iCount%2) == 0)
+			        *(lpTmpAddr)=0x00;
+		        else
+			*(lpTmpAddr)=0x80;
+		}
+
+		if ( lpVideoHWDifference->dwHQVFetchByteUnit )
+		{
+		    VIDOutD(HQV_SRC_FETCH_LINE, (((dwPitch)-1)<<16)|(dwHeight-1));
+            VIDOutD(HQV_SRC_STRIDE, ((dwPitch>>1)<<16)|dwPitch|HQV_FIFO_DEPTH);
+		}
+		else
+		{
+		    VIDOutD(HQV_SRC_FETCH_LINE, (((dwPitch>>3)-1)<<16)|(dwHeight-1));
+            VIDOutD(HQV_SRC_STRIDE, ((dwPitch>>1)<<16)|dwPitch);
+        }
+
+//        VIDOutD(HQV_SRC_STRIDE, ((dwPitch>>1)<<16)|dwPitch);
+	    	VIDOutD(HQV_DST_STRIDE, dwPitch*2);
+		VIDOutD(V1_STARTADDR_1,MPGDevice.dwHQVAddr[1]);
+		VIDOutD(V1_STARTADDR_0,MPGDevice.dwHQVAddr[0]);
+		VIDOutD(HQV_DST_STARTADDR1,MPGDevice.dwHQVAddr[1]);
+	    	VIDOutD(HQV_DST_STARTADDR0,MPGDevice.dwHQVAddr[0]);
+	 	if (lpVideoHWDifference->dwThreeHQVBuffer)
+		{
+			VIDOutD(V1_STARTADDR_2,MPGDevice.dwHQVAddr[2]);
+	    	    	VIDOutD(HQV_DST_STARTADDR2,MPGDevice.dwHQVAddr[2]);
+		}
+		VIDOutD(V1_STRIDE, dwPitch*2);
+
+		DBG_DD("000003e0 %08lx\n", VIDInD(0x1e0));
+		DBG_DD("000003f8 %08lx\n", VIDInD(0x1f8));
+		DBG_DD("000003f4 %08lx\n", VIDInD(0x1f4));
+		DBG_DD("00000238 %08lx\n", VIDInD(0x38));
+		DBG_DD("00000254 %08lx\n", VIDInD(0x54));
+		DBG_DD("000003f0 %08lx\n", VIDInD(0x1f0));
+		DBG_DD("000003ec %08lx\n", VIDInD(0x1ec));
+	 	if (lpVideoHWDifference->dwThreeHQVBuffer)
+		{
+			DBG_DD("00000248 %08lx\n", VIDInD(0x48));
+			DBG_DD("000003fc %08lx\n", VIDInD(0x1fc));
+		}
+		DBG_DD("0000023c %08lx\n", VIDInD(0x3c) );
+	break;
+
+	case FOURCC_TV1 :   //TV1 - V1 - Capture1(Port1)
+            /*via = &via_v4l_devices[0];*/
+            
+            DBG_DD("    Create TV1 Surface: \n");
+            // init Video status flag
+            if ((gdwVideoFlagMPEG & VIDEO_HQV_INUSE) || (gdwVideoFlagTV0 & VIDEO_HQV_INUSE))
+            {
+                gdwVideoFlagTV1 = VIDEO_SHOW | VIDEO_3_INUSE | VIDEO_CAPTURE1_INUSE;
+                //gdwVideoFlagTV1 = VIDEO_SHOW | VIDEO_1_INUSE | VIDEO_CAPTURE1_INUSE;
+                DBG_DD("    Create TV1 Surface: Capture1 + V3 : NO_HQV !!!!\n");
+            }
+            else
+            {
+                gdwVideoFlagTV1 = VIDEO_SHOW | VIDEO_3_INUSE | VIDEO_CAPTURE1_INUSE | VIDEO_HQV_INUSE | CAP1_USE_HQV;
+                //gdwVideoFlagTV1 = VIDEO_SHOW | VIDEO_1_INUSE | VIDEO_CAPTURE1_INUSE | VIDEO_HQV_INUSE | CAP1_USE_HQV;
+                lpVideoControl->dwHighQVDO = VW_HIGHQVDO_TV1;
+                DBG_DD("    Create TV1 Surface: Capture1 + V3 : HQV_INUSE !!!!\n");
+            }
+
+            //Color Space Conversion
+        if (!gVIAGraphicInfo.ColorSpaceChanged)    
+        { 
+            switch ( DispatchVGARevisionID() )
+            {
+            	case VIA_REVISION_CLECX :
+                    VIDOutD(V3_ColorSpaceReg_1, ColorSpaceValue_1_3123C0);
+                    VIDOutD(V3_ColorSpaceReg_2, ColorSpaceValue_2_3123C0);
+
+                    DBG_DD("000002C4 %08x\n",ColorSpaceValue_1_3123C0);
+                    DBG_DD("000002C8 %08x\n",ColorSpaceValue_2_3123C0);  
+                    
+                    /*if ( (gVIAGraphicInfo.HasSecondary || gVIAGraphicInfo.IsSecondary) )*/
+                    if (gVIAGraphicInfo.SAMM)
+                    { 
+                        VIDOutD(V1_ColorSpaceReg_1, ColorSpaceValue_1_3123C0);
+                        VIDOutD(V1_ColorSpaceReg_2, ColorSpaceValue_2_3123C0);
+                        
+                        DBG_DD("00000284 %08x\n",ColorSpaceValue_1_3123C0);
+                        DBG_DD("00000288 %08x\n",ColorSpaceValue_2_3123C0);
+                    }
+                    break;
+                
+                default :
+                    VIDOutD(V3_ColorSpaceReg_1, ColorSpaceValue_1);
+                    VIDOutD(V3_ColorSpaceReg_2, ColorSpaceValue_2);
+        
+                    DBG_DD("000002C4 %08x\n", ColorSpaceValue_1);
+                    DBG_DD("000002C8 %08x\n", ColorSpaceValue_2);
+            
+                    // for SAMM Mode
+                    /*if ( (gVIAGraphicInfo.HasSecondary || gVIAGraphicInfo.IsSecondary) )*/
+                    if (gVIAGraphicInfo.SAMM)
+                    {
+                        //SAMM Mode V1 Color Space Conversion
+                        VIDOutD(V1_ColorSpaceReg_1, ColorSpaceValue_1);
+                        VIDOutD(V1_ColorSpaceReg_2, ColorSpaceValue_2);
+
+                        DBG_DD("00000284 %08x\n",ColorSpaceValue_1);
+                        DBG_DD("00000288 %08x\n",ColorSpaceValue_2);            	
+                    }
+                    break;
+            }
+        }
+        else
+        {
+            VIDOutD(V3_ColorSpaceReg_1, gVIAGraphicInfo.ColorSpaceValue1);
+            VIDOutD(V3_ColorSpaceReg_2, gVIAGraphicInfo.ColorSpaceValue2);
+            VIDOutD(V1_ColorSpaceReg_1, gVIAGraphicInfo.ColorSpaceValue1);
+            VIDOutD(V1_ColorSpaceReg_2, gVIAGraphicInfo.ColorSpaceValue2);
+        } 
+                
+
+            dwBackBufferCount = lpDDSurfaceDesc->dwBackBufferCount;
+            dwWidth  = lpDDSurfaceDesc->dwWidth; 
+            dwHeight = lpDDSurfaceDesc->dwHeight;
+            dwPitch  = ALIGN_TO_32_BYTES(dwWidth*2); //YUYV packed mode
+
+            //if ( TV1_MINIFY_HOR_2 )
+            //   dwPitch>>=1;
+
+            TVFBSIZE = dwPitch*dwHeight+dwPitch*4;
+
+            if (!gVIAGraphicInfo.DRMEnabled)
+            {
+                TV1MemRequest.checkID = VIA_MID;
+                //TV1MemRequest.size    = TVFBSIZE*2; //2 frame buffers
+                TV1MemRequest.size    = TVFBSIZE*4;   //4 frame buffers, for Cap1 S/W flip
+                TV1MemRequest.type    = VIDMGR_TYPE_VIDEO;
+                if ( MEM_OK != viaMgr_vid_ioctl(VIAMGR_ALLOC_VIDEO, (char *)(&TV1MemRequest) ) )
+                {
+                    DBG_DD(" Memory Allocation fail for TV1 Video \n");
+                    return PI_ERR_CANNOT_CREATE_SURFACE;
+                }
+                dwAddr = ALIGN_TO_32_BYTES(TV1MemRequest.offset);
+            }
+#ifdef HAVE_DRM
+            else
+            {
+                TV1fbRequest.context=1;
+                //TV1fbRequest.size=TVFBSIZE*2;
+                TV1fbRequest.size=TVFBSIZE*4; //4 frame buffers, for Cap1 S/W flip
+                TV1fbRequest.type= VIDEO;
+                via_fb_alloc(&TV1fbRequest);
+
+                dwAddr = TV1fbRequest.offset;
+            }
+#endif
+
+            // fill in the HQV buffer with 0x8000 (YUV422 or YUY2-black color) to clear HQV buffers
+            //for(iCount=0;iCount<TVFBSIZE*2;iCount++)
+            for(iCount=0;iCount<TVFBSIZE*4;iCount++) //4 frame buffers, for Cap1 S/W flip
+            {
+                lpTmpAddr = lpPrimarySurface + dwAddr + iCount;
+                if((iCount%2) == 0)
+                    *(lpTmpAddr)=0x00;
+                else
+                    *(lpTmpAddr)=0x80;
+            }
+            
+            CAPDevice[1].dwCAPPhysicalAddr[0]   = dwAddr;
+            CAPDevice[1].lpCAPOverlaySurface[0] = lpPrimarySurface+dwAddr;
+
+            CAPDevice[1].dwCAPPhysicalAddr[1] = CAPDevice[1].dwCAPPhysicalAddr[0] + TVFBSIZE;
+            CAPDevice[1].lpCAPOverlaySurface[1] = CAPDevice[1].lpCAPOverlaySurface[0] + TVFBSIZE;
+
+            //4 frame buffers, for Cap1 S/W flip
+            CAPDevice[1].dwCAPPhysicalAddr[2] = CAPDevice[1].dwCAPPhysicalAddr[1] + TVFBSIZE;
+            CAPDevice[1].lpCAPOverlaySurface[2] = CAPDevice[1].lpCAPOverlaySurface[1] + TVFBSIZE;            
+            CAPDevice[1].dwCAPPhysicalAddr[3] = CAPDevice[1].dwCAPPhysicalAddr[2] + TVFBSIZE;
+            CAPDevice[1].lpCAPOverlaySurface[3] = CAPDevice[1].lpCAPOverlaySurface[2] + TVFBSIZE;
+
+            CAPDevice[1].dwWidth = dwWidth;
+            CAPDevice[1].dwHeight= dwHeight;
+            CAPDevice[1].gdwCAPSrcWidth = dwWidth;
+            CAPDevice[1].gdwCAPSrcHeight = dwHeight;
+            CAPDevice[1].dwPitch = dwPitch;
+            CAPDevice[1].byDeviceType = DEV_TV1;
+
+            // Fill image data in overlay record
+            overlayRecordV3.dwV1OriWidth  = CAPDevice[1].gdwCAPSrcWidth;
+            overlayRecordV3.dwV1OriHeight = CAPDevice[1].gdwCAPSrcHeight;
+            overlayRecordV3.dwV1OriPitch  = CAPDevice[1].dwPitch;
+            //overlayRecordV1.dwV1OriWidth  = CAPDevice[1].gdwCAPSrcWidth;
+            //overlayRecordV1.dwV1OriHeight = CAPDevice[1].gdwCAPSrcHeight;
+            //overlayRecordV1.dwV1OriPitch  = CAPDevice[1].dwPitch;
+
+            VIA_CAPSetFrameBuffer(&CAPDevice[1]);
+if (!(gdwVideoFlagTV1 & CAP1_USE_HQV))
+//if (!HQV_TV1)
+            break;
+
+        case FOURCC_HQVTV1 :
+
+            //via = &via_v4l_devices[0];
+            DBG_DD("    Create TV1-HQV Surface: \n");
+            dwPitch  = CAPDevice[1].dwPitch;
+            dwHeight = CAPDevice[1].dwHeight;
+                
+            HQVFBSIZE = dwPitch*dwHeight+dwPitch*4;
+
+
+            if (!gVIAGraphicInfo.DRMEnabled)
+            {
+                HQVMemRequest.checkID = VIA_MID;
+                //HQVMemRequest.size    = HQVFBSIZE*2;
+                
+                if ( lpVideoHWDifference->dwThreeHQVBuffer )    //CLE_C0
+                    HQVMemRequest.size    = (HQVFBSIZE * 3);
+                else
+                    HQVMemRequest.size    = (HQVFBSIZE * 2);
+                
+                HQVMemRequest.type    = VIDMGR_TYPE_VIDEO;
+                if ( MEM_OK != viaMgr_vid_ioctl(VIAMGR_ALLOC_VIDEO, (char *)(&HQVMemRequest) ) )
+                {
+                    DBG_DD(" Memory Allocation fail for TV1 HQV Video \n");
+                    return PI_ERR_CANNOT_CREATE_SURFACE;
+                }
+                dwAddr = ALIGN_TO_32_BYTES(HQVMemRequest.offset);
+            }
+#ifdef HAVE_DRM
+            else
+            {
+                HQVfbRequest.context=1;
+                //HQVfbRequest.size=HQVFBSIZE*2;
+                
+                if ( lpVideoHWDifference->dwThreeHQVBuffer )    //CLE_C0
+                    HQVfbRequest.size    = (HQVFBSIZE * 3);
+                else
+                    HQVfbRequest.size    = (HQVFBSIZE * 2);
+                
+                HQVfbRequest.type= VIDEO;
+                via_fb_alloc(&HQVfbRequest);
+
+                dwAddr = HQVfbRequest.offset;
+            }
+#endif
+
+            CAPDevice[1].dwHQVAddr[0] = dwAddr;
+            CAPDevice[1].dwHQVAddr[1] = CAPDevice[1].dwHQVAddr[0] + HQVFBSIZE;
+
+            if ( lpVideoHWDifference->dwThreeHQVBuffer )    //CLE_C0
+            {
+            	CAPDevice[1].dwHQVAddr[2] = CAPDevice[1].dwHQVAddr[1] + HQVFBSIZE;
+            	
+            	if (CAPDevice[1].dwHQVAddr[2] + HQVFBSIZE >=
+                                       (unsigned long)gVIAGraphicInfo.Screen[ScrnIndex].VideoHeapEnd)
+                {
+                    DBG_DD("//    :Memory not enough for TV1 with HQV\n");
+                    return PI_ERR_CANNOT_CREATE_SURFACE;
+                }
+            }
+            else
+            {
+            if (CAPDevice[1].dwHQVAddr[1] + HQVFBSIZE >=
+                                       (unsigned long)gVIAGraphicInfo.Screen[ScrnIndex].VideoHeapEnd)
+                {
+                    DBG_DD("//    :Memory not enough for TV1 with HQV\n");
+                return PI_ERR_CANNOT_CREATE_SURFACE;
+            }
+            }
+                                                                                                                                                                                
+            // fill in the HQV buffer with 0x8000 (YUV422 or YUY2-black color) to clear HQV buffers
+            for(iCount=0;iCount<HQVFBSIZE*2;iCount++)
+            {
+                lpTmpAddr = lpPrimarySurface + dwAddr + iCount;
+                if((iCount%2) == 0)
+                    *(lpTmpAddr)=0x00;
+                else
+                    *(lpTmpAddr)=0x80;
+            }
+            
+            //dwPitch -1 to hide the noise dot in the left down corner
+            //dwHeight -1 to hide green line in the bottom
+            
+            if ( lpVideoHWDifference->dwHQVFetchByteUnit )     // CLE_C0
+            {
+                VIDOutD(HQV_SRC_FETCH_LINE, (((dwPitch)-1)<<16)|(dwHeight-1));
+                VIDOutD(HQV_SRC_STRIDE, ((dwPitch>>1)<<16)|dwPitch|HQV_FIFO_DEPTH);
+            }    
+            else
+            {
+                VIDOutD(HQV_SRC_FETCH_LINE, (((dwPitch>>3)-1)<<16)|(dwHeight-1));
+            VIDOutD(HQV_SRC_STRIDE, ((dwPitch>>1)<<16)|dwPitch);
+            }
+            
+            //VIDOutD(HQV_SRC_STRIDE, ((dwPitch>>1)<<16)|dwPitch);
+            VIDOutD(HQV_DST_STRIDE, dwPitch);
+
+            VIDOutD(V3_STARTADDR_1,CAPDevice[1].dwHQVAddr[1]);
+            VIDOutD(V3_STARTADDR_0,CAPDevice[1].dwHQVAddr[0]);
+            //VIDOutD(V1_STARTADDR_1,CAPDevice[1].dwHQVAddr[1]);
+            //VIDOutD(V1_STARTADDR_0,CAPDevice[1].dwHQVAddr[0]);
+            VIDOutD(HQV_DST_STARTADDR1,CAPDevice[1].dwHQVAddr[1]);
+            VIDOutD(HQV_DST_STARTADDR0,CAPDevice[1].dwHQVAddr[0]);
+            //VIDOutD(V1_STRIDE, dwPitch);
+            VIDOutD(V3_STRIDE, dwPitch);
+            
+            if ( lpVideoHWDifference->dwThreeHQVBuffer )    //CLE_C0
+            {
+                VIDOutD(V3_STARTADDR_2,CAPDevice[1].dwHQVAddr[2]);
+                VIDOutD(HQV_DST_STARTADDR2,CAPDevice[1].dwHQVAddr[2]);
+                DBG_DD("0000029C %08lx\n",VIDInD(V3_STARTADDR_2) );
+                DBG_DD("000003FC %08lx\n",VIDInD(HQV_DST_STARTADDR2) );
+            }
+
+            DBG_DD("000003E0 %08lx\n",VIDInD(HQV_SRC_FETCH_LINE) );
+            DBG_DD("000003F8 %08lx\n",VIDInD(HQV_SRC_STRIDE) );
+            DBG_DD("000003F4 %08lx\n",VIDInD(HQV_DST_STRIDE) );
+            DBG_DD("000002a8 %08lx\n",VIDInD(V3_STARTADDR_1) );
+            DBG_DD("000002a4 %08lx\n",VIDInD(V3_STARTADDR_0) );
+            //DBG_DD("00000238 %08lx\n",VIDInD(V1_STARTADDR_1) );
+            //DBG_DD("00000254 %08lx\n",VIDInD(V1_STARTADDR_0) );
+            DBG_DD("000003F0 %08lx\n",VIDInD(HQV_DST_STARTADDR1) );
+            DBG_DD("000003EC %08lx\n",VIDInD(HQV_DST_STARTADDR0) );
+            DBG_DD("0000023C %08lx\n", dwPitch);
+
+            break;
+
+        case FOURCC_TV0 :   //TV0 - V1 - Capture0(Port0)
+            /*via = &via_v4l_devices[1];*/
+            DBG_DD("    Create TV0 Surface: \n");
+            // init Video status flag
+            if ((gdwVideoFlagMPEG & VIDEO_HQV_INUSE) || (gdwVideoFlagTV1 & VIDEO_HQV_INUSE))
+            {    
+                if (gVIAGraphicInfo.Cap0_SwitchToV3)        //TV0 - V3 - Capture0 (for SAMSUNG)
+                {
+                    gdwVideoFlagTV0 = VIDEO_SHOW | VIDEO_3_INUSE | VIDEO_CAPTURE0_INUSE;
+                DBG_DD("    Create TV0 Surface: Capture0 + V3 : NO_HQV !!!!\n");
+            }
+                else                                        //TV0 - V1 - Capture0 (Port0)
+                {
+                    gdwVideoFlagTV0 = VIDEO_SHOW | VIDEO_1_INUSE | VIDEO_CAPTURE0_INUSE;
+                    DBG_DD("    Create TV0 Surface: Capture0 + V1 : NO_HQV !!!!\n");
+                }
+            }
+            else
+            {
+                if (gVIAGraphicInfo.Cap0_SwitchToV3)
+                {
+                    gdwVideoFlagTV0 = VIDEO_SHOW | VIDEO_3_INUSE | VIDEO_CAPTURE0_INUSE | VIDEO_HQV_INUSE | CAP0_USE_HQV;
+                    DBG_DD("    Create TV0 Surface: Capture0 + V3 : HQV_INUSE !!!!\n");
+                }
+            else
+            {
+                gdwVideoFlagTV0 = VIDEO_SHOW | VIDEO_1_INUSE | VIDEO_CAPTURE0_INUSE | VIDEO_HQV_INUSE | CAP0_USE_HQV;
+                    DBG_DD("    Create TV0 Surface: Capture0 + V1 : HQV_INUSE !!!!\n");
+                }
+                lpVideoControl->dwHighQVDO = VW_HIGHQVDO_TV0;
+            }
+
+            //Color Space Conversion
+        if (!gVIAGraphicInfo.ColorSpaceChanged)    
+        {
+            switch ( DispatchVGARevisionID() )
+            {
+            	case VIA_REVISION_CLECX :
+                    if (gVIAGraphicInfo.Cap0_SwitchToV3)
+                    {
+                        VIDOutD(V3_ColorSpaceReg_1, ColorSpaceValue_1_3123C0);
+                        VIDOutD(V3_ColorSpaceReg_2, ColorSpaceValue_2_3123C0);
+                        DBG_DD("000002C4 %08x\n",ColorSpaceValue_1_3123C0);
+                        DBG_DD("000002C8 %08x\n",ColorSpaceValue_2_3123C0);  
+                    }
+                    else
+                    {
+                    VIDOutD(V1_ColorSpaceReg_1, ColorSpaceValue_1_3123C0);
+                    VIDOutD(V1_ColorSpaceReg_2, ColorSpaceValue_2_3123C0);
+                    DBG_DD("00000284 %08x\n",ColorSpaceValue_1_3123C0);
+                    DBG_DD("00000288 %08x\n",ColorSpaceValue_2_3123C0);
+                    }
+                    break;
+            
+                default :
+                    if (gVIAGraphicInfo.Cap0_SwitchToV3)
+                    {
+                        VIDOutD(V3_ColorSpaceReg_1, ColorSpaceValue_1);
+                        VIDOutD(V3_ColorSpaceReg_2, ColorSpaceValue_2);
+                        DBG_DD("000002C4 %08x\n",ColorSpaceValue_1);
+                        DBG_DD("000002C8 %08x\n",ColorSpaceValue_2);  
+                    }
+                    else
+                    {
+                    VIDOutD(V1_ColorSpaceReg_1, ColorSpaceValue_1);
+                    VIDOutD(V1_ColorSpaceReg_2, ColorSpaceValue_2);
+                    DBG_DD("00000284 %08x\n",ColorSpaceValue_1);
+                    DBG_DD("00000288 %08x\n",ColorSpaceValue_2);
+                    }
+                    break;
+            }
+        }
+        else
+        {
+            if (gVIAGraphicInfo.Cap0_SwitchToV3)
+            {
+                VIDOutD(V3_ColorSpaceReg_1, gVIAGraphicInfo.ColorSpaceValue1);
+                VIDOutD(V3_ColorSpaceReg_2, gVIAGraphicInfo.ColorSpaceValue2);  
+            }
+            else
+            {
+                VIDOutD(V1_ColorSpaceReg_1, gVIAGraphicInfo.ColorSpaceValue1);
+                VIDOutD(V1_ColorSpaceReg_2, gVIAGraphicInfo.ColorSpaceValue2);
+            }
+        }
+
+            dwBackBufferCount = lpDDSurfaceDesc-> dwBackBufferCount;
+            dwWidth  = lpDDSurfaceDesc->dwWidth; 
+            dwHeight = lpDDSurfaceDesc->dwHeight;
+            dwPitch  = ALIGN_TO_32_BYTES(dwWidth*2); // YUYV packed mode
+
+            TVFBSIZE = dwPitch*dwHeight+dwPitch*4;
+            if (!gVIAGraphicInfo.DRMEnabled)
+            {
+                TV0MemRequest.checkID = VIA_MID;
+                TV0MemRequest.size    = TVFBSIZE*3; // 3 frame buffers
+                TV0MemRequest.type    = VIDMGR_TYPE_VIDEO;
+                if ( viaMgr_vid_ioctl(VIAMGR_ALLOC_VIDEO, (char *)(&TV0MemRequest) ) != MEM_OK )
+                {
+                   DBG_DD(" Memory Allocation fail for TV0 Video \n");
+                   return PI_ERR_CANNOT_CREATE_SURFACE;
+                }
+                dwAddr = ALIGN_TO_32_BYTES(TV0MemRequest.offset);
+
+            }
+#ifdef HAVE_DRM
+            else
+            {
+                TV0fbRequest.context=1;
+                TV0fbRequest.size=TVFBSIZE*3;
+                TV0fbRequest.type= VIDEO;
+                via_fb_alloc(&TV0fbRequest);
+
+                dwAddr = TV0fbRequest.offset;
+                
+            }
+#endif
+
+            // fill in the HQV buffer with 0x8000 (YUV422 or YUY2-black color) to clear HQV buffers
+            for(iCount=0;iCount<TVFBSIZE*2;iCount++)
+            {
+                lpTmpAddr = lpPrimarySurface + dwAddr + iCount;
+                if((iCount%2) == 0)
+                    *(lpTmpAddr)=0x00;
+                else
+                    *(lpTmpAddr)=0x80;
+            }
+            
+            CAPDevice[0].dwCAPPhysicalAddr[0]   = dwAddr;
+            CAPDevice[0].lpCAPOverlaySurface[0] = lpPrimarySurface+dwAddr;
+            CAPDevice[0].dwCAPPhysicalAddr[1] = CAPDevice[0].dwCAPPhysicalAddr[0] + TVFBSIZE;
+            CAPDevice[0].lpCAPOverlaySurface[1] = CAPDevice[0].lpCAPOverlaySurface[0]+TVFBSIZE;
+            CAPDevice[0].dwCAPPhysicalAddr[2] = CAPDevice[0].dwCAPPhysicalAddr[1] + TVFBSIZE;
+            CAPDevice[0].lpCAPOverlaySurface[2] = CAPDevice[0].lpCAPOverlaySurface[1]+TVFBSIZE;
+
+            CAPDevice[0].dwWidth = dwWidth;
+            CAPDevice[0].dwHeight= dwHeight;
+            CAPDevice[0].gdwCAPSrcWidth = dwWidth;
+            CAPDevice[0].gdwCAPSrcHeight = dwHeight;
+            CAPDevice[0].dwPitch = dwPitch;
+            CAPDevice[0].byDeviceType = DEV_TV0;
+
+            // Fill image data in overlay record
+            if (gVIAGraphicInfo.Cap0_SwitchToV3)
+            {
+                overlayRecordV3.dwV1OriWidth  = CAPDevice[0].gdwCAPSrcWidth;
+                overlayRecordV3.dwV1OriHeight = CAPDevice[0].gdwCAPSrcHeight;
+                overlayRecordV3.dwV1OriPitch  = CAPDevice[0].dwPitch;
+            }
+            else
+            {
+            overlayRecordV1.dwV1OriWidth  = CAPDevice[0].gdwCAPSrcWidth;
+            overlayRecordV1.dwV1OriHeight = CAPDevice[0].gdwCAPSrcHeight;
+            overlayRecordV1.dwV1OriPitch  = CAPDevice[0].dwPitch;
+            }
+
+            VIA_CAPSetFrameBuffer(&CAPDevice[0]);
+
+if (!(gdwVideoFlagTV0 & CAP0_USE_HQV))
+            break;
+
+       case FOURCC_HQVTV0 :
+            //via = &via_v4l_devices[1];
+            DBG_DD("    Create TV0-HQV Surface: \n");
+            dwPitch  = CAPDevice[0].dwPitch;
+            dwHeight = CAPDevice[0].dwHeight;
+                
+            HQVFBSIZE = dwPitch*dwHeight+dwPitch*4;
+
+            if (!gVIAGraphicInfo.DRMEnabled)
+            {
+                HQVMemRequest.checkID = VIA_MID;
+                //HQVMemRequest.size    = HQVFBSIZE*2;
+                
+                if ( lpVideoHWDifference->dwThreeHQVBuffer )    //CLE_C0
+                    HQVMemRequest.size    = (HQVFBSIZE * 3);
+                else
+                    HQVMemRequest.size    = (HQVFBSIZE * 2);
+                    
+                HQVMemRequest.type    = VIDMGR_TYPE_VIDEO;
+                if ( viaMgr_vid_ioctl(VIAMGR_ALLOC_VIDEO, (char *)(&HQVMemRequest) ) != MEM_OK )
+                {
+                   DBG_DD(" Memory Allocation fail for TV0 HQV Video \n");
+                   return PI_ERR_CANNOT_CREATE_SURFACE;
+                }
+                dwAddr = ALIGN_TO_32_BYTES(HQVMemRequest.offset);
+            }
+#ifdef HAVE_DRM
+            else
+            {
+                HQVfbRequest.context=1;
+                //HQVfbRequest.size=HQVFBSIZE*2;
+                
+                if ( lpVideoHWDifference->dwThreeHQVBuffer )    //CLE_C0
+                    HQVfbRequest.size    = (HQVFBSIZE * 3);
+                else
+                    HQVfbRequest.size    = (HQVFBSIZE * 2);
+                
+                HQVfbRequest.type= VIDEO;
+                via_fb_alloc(&HQVfbRequest);
+
+                dwAddr = HQVfbRequest.offset;
+            }
+#endif
+
+            CAPDevice[0].dwHQVAddr[0] = dwAddr;
+            CAPDevice[0].dwHQVAddr[1] = CAPDevice[0].dwHQVAddr[0] + HQVFBSIZE;
+
+            if ( lpVideoHWDifference->dwThreeHQVBuffer )    //CLE_C0
+            {
+            	CAPDevice[0].dwHQVAddr[2] = CAPDevice[0].dwHQVAddr[1] + HQVFBSIZE;
+            	
+            	if (CAPDevice[0].dwHQVAddr[2] + HQVFBSIZE >=
+                                       (unsigned long)gVIAGraphicInfo.Screen[ScrnIndex].VideoHeapEnd)
+                {
+                    DBG_DD("//    :Memory not enough for TV0 with HQV\n");
+                    return PI_ERR_CANNOT_CREATE_SURFACE;
+                }
+            }
+            else
+            {
+                if (CAPDevice[0].dwHQVAddr[1] + HQVFBSIZE >=
+                                       (unsigned long)gVIAGraphicInfo.Screen[ScrnIndex].VideoHeapEnd)
+                {
+                    DBG_DD("//    :Memory not enough for TV0 with HQV\n");
+                    return PI_ERR_CANNOT_CREATE_SURFACE;
+                }
+            }
+                                                                                                                                                                                                        
+            // fill in the HQV buffer with 0x8000 (YUV422 or YUY2-black color) to clear HQV buffers
+            for(iCount=0;iCount<HQVFBSIZE*2;iCount++)
+            {
+                lpTmpAddr = lpPrimarySurface + dwAddr + iCount;
+                if((iCount%2) == 0)
+                    *(lpTmpAddr)=0x00;
+                else
+                    *(lpTmpAddr)=0x80;
+            }
+            
+
+            //dwPitch -1 to hide the noise dot in the left down corner
+            //dwHeight -1 to hide green line in the bottom
+            
+            if ( lpVideoHWDifference->dwHQVFetchByteUnit )     // CLE_C0
+            {
+                VIDOutD(HQV_SRC_FETCH_LINE, (((dwPitch)-1)<<16)|(dwHeight-1));
+                VIDOutD(HQV_SRC_STRIDE, ((dwPitch>>1)<<16)|dwPitch|HQV_FIFO_DEPTH);
+            }
+            else
+            {
+                VIDOutD(HQV_SRC_FETCH_LINE, (((dwPitch>>3)-1)<<16)|(dwHeight-1));
+            VIDOutD(HQV_SRC_STRIDE, ((dwPitch>>1)<<16)|dwPitch);
+            }    
+            
+            //VIDOutD(HQV_SRC_STRIDE, ((dwPitch>>1)<<16)|dwPitch);
+            VIDOutD(HQV_DST_STRIDE, dwPitch);
+
+            if (gVIAGraphicInfo.Cap0_SwitchToV3)
+            {
+            VIDOutD(V3_STARTADDR_1,CAPDevice[0].dwHQVAddr[1]);
+            VIDOutD(V3_STARTADDR_0,CAPDevice[0].dwHQVAddr[0]);
+                DBG_DD("000002a8 %08lx\n",VIDInD(V3_STARTADDR_1) );
+                DBG_DD("000002a4 %08lx\n",VIDInD(V3_STARTADDR_0) );
+            }
+            else
+            {
+                VIDOutD(V1_STARTADDR_1,CAPDevice[0].dwHQVAddr[1]);
+                VIDOutD(V1_STARTADDR_0,CAPDevice[0].dwHQVAddr[0]);
+                DBG_DD("00000238 %08lx\n",VIDInD(V1_STARTADDR_1) );
+                DBG_DD("00000254 %08lx\n",VIDInD(V1_STARTADDR_0) );
+            }            
+            
+            VIDOutD(HQV_DST_STARTADDR1,CAPDevice[0].dwHQVAddr[1]);
+            VIDOutD(HQV_DST_STARTADDR0,CAPDevice[0].dwHQVAddr[0]);
+            
+            if ( lpVideoHWDifference->dwThreeHQVBuffer )    //CLE_C0
+            {
+                VIDOutD(V1_STARTADDR_2,CAPDevice[0].dwHQVAddr[2]);
+                VIDOutD(HQV_DST_STARTADDR2,CAPDevice[0].dwHQVAddr[2]);
+                DBG_DD("00000248 %08lx\n",VIDInD(V1_STARTADDR_2) );
+                DBG_DD("000003FC %08lx\n",VIDInD(HQV_DST_STARTADDR2) );
+            }
+            
+            VIDOutD(V1_STRIDE, dwPitch);
+
+            DBG_DD("000003E0 %08lx\n",VIDInD(HQV_SRC_FETCH_LINE) );
+            DBG_DD("000003F8 %08lx\n",VIDInD(HQV_SRC_STRIDE) );
+            DBG_DD("000003F4 %08lx\n",VIDInD(HQV_DST_STRIDE) );
+            DBG_DD("000003F0 %08lx\n",VIDInD(HQV_DST_STARTADDR1) );
+            DBG_DD("000003EC %08lx\n",VIDInD(HQV_DST_STARTADDR0) );
+            DBG_DD("0000023C %08lx\n", dwPitch);
+                                                                                                                                                                                                            
+            break;
+
+        case FOURCC_ALPHA :
+            DBG_DD("    Create ALPHA Surface: \n");
+            dwWidth  = lpDDSurfaceDesc->dwWidth;
+            dwHeight = lpDDSurfaceDesc->dwHeight;
+            dwPitch  = ALIGN_TO_16_BYTES(dwWidth/2);
+
+            ALPHAFBSIZE = dwPitch*dwHeight;
+
+            if (!gVIAGraphicInfo.DRMEnabled)
+            {
+                ALPHAMemRequest.checkID = VIA_MID;
+                ALPHAMemRequest.size    = ALPHAFBSIZE;
+                ALPHAMemRequest.type    = VIDMGR_TYPE_VIDEO;
+                if ( MEM_OK != viaMgr_vid_ioctl(VIAMGR_ALLOC_VIDEO, (char *)(&ALPHAMemRequest) ) )
+                {
+                   DBG_DD(" Memory Allocation fail for Alpha Surface.\n");
+                   return PI_ERR_CANNOT_CREATE_SURFACE;
+                }
+                dwAddr = ALIGN_TO_32_BYTES(ALPHAMemRequest.offset);
+            }
+#ifdef HAVE_DRM
+            else
+            {
+                ALPHAfbRequest.context=1;
+                ALPHAfbRequest.size=ALPHAFBSIZE;
+                ALPHAfbRequest.type= VIDEO;
+                via_fb_alloc(&ALPHAfbRequest);
+
+                dwAddr = ALPHAfbRequest.offset;
+            }
+#endif
+
+            ALPDevice.dwALPPhysicalAddr   = dwAddr;
+            ALPDevice.lpALPOverlaySurface = lpPrimarySurface+dwAddr;
+            ALPDevice.dwPitch = dwPitch;
+            ALPDevice.gdwALPDstHeight = dwHeight;
+            ALPDevice.gdwALPDstWidth  = dwWidth ;
+            ALPDevice.gdwALPDstLeft   = 0;
+            ALPDevice.gdwALPDstTop    = 0;
+            if (ALPDevice.dwALPPhysicalAddr+ALPHAFBSIZE >=
+                                    (unsigned long)gVIAGraphicInfo.Screen[ScrnIndex].VideoHeapEnd)
+            {
+                DBG_DD("//    :Memory not enough\n");
+                
+                return PI_ERR_CANNOT_CREATE_SURFACE;
+            }
+
+            VIA_ALPSetFrameBuffer(&ALPDevice);
+
+            break;
+
+       case FOURCC_YUY2 :
+            /*via = &via_v4l_devices[0];*/
+            DBG_DD("    Create SW YUY2 Surface: \n");
+            lpDPFsrc->dwFlags = DDPF_FOURCC;
+            lpDPFsrc->dwFourCC = FOURCC_YUY2;
+
+            // init Video status flag
+            //Added for KM400
+            switch ( gVIAGraphicInfo.dwDeviceID )
+            {
+                case VIA_DEVICE_VT3205:
+                    gdwVideoFlagSW = VIDEO_HQV_INUSE | SW_USE_HQV | VIDEO_3_INUSE;
+                    break;
+                case VIA_DEVICE_CLE1:
+                case VIA_DEVICE_CLE2:
+                default:
+            gdwVideoFlagSW = VIDEO_HQV_INUSE | SW_USE_HQV | VIDEO_1_INUSE;
+                    break;
+            }
+
+            if (gdwVideoFlagTV0 & VIDEO_HQV_INUSE)
+            {
+                lpNewVidCtrl->dwHighQVDO = VW_HIGHQVDO_OFF;
+                VIADriverProc( HQVCONTROL , lpNewVidCtrl );
+            }
+            
+            //write Color Space Conversion param.
+        if (!gVIAGraphicInfo.ColorSpaceChanged)    
+        {
+            //Added for KM400
+            switch ( gVIAGraphicInfo.dwDeviceID )
+            {
+                case VIA_DEVICE_VT3205:
+                    VIDOutD(V3_ColorSpaceReg_1, ColorSpaceValue_1_32045);
+                    VIDOutD(V3_ColorSpaceReg_2, ColorSpaceValue_2_32045);                    
+                    DBG_DD("000002C4 %08x\n",ColorSpaceValue_1_32045);
+                    DBG_DD("000002C8 %08x\n",ColorSpaceValue_2_32045);
+                    break;
+                case VIA_DEVICE_CLE1:
+                case VIA_DEVICE_CLE2:
+            switch ( DispatchVGARevisionID() )
+            {
+            	case VIA_REVISION_CLECX :
+                    VIDOutD(V1_ColorSpaceReg_1, ColorSpaceValue_1_3123C0);
+                    VIDOutD(V1_ColorSpaceReg_2, ColorSpaceValue_2_3123C0);
+
+                    DBG_DD("00000284 %08x\n",ColorSpaceValue_1_3123C0);
+                    DBG_DD("00000288 %08x\n",ColorSpaceValue_2_3123C0);
+                    break;
+                
+                default :
+                    VIDOutD(V1_ColorSpaceReg_1, ColorSpaceValue_1);
+                    VIDOutD(V1_ColorSpaceReg_2, ColorSpaceValue_2);
+
+                    DBG_DD("00000284 %08x\n",ColorSpaceValue_1);
+                    DBG_DD("00000288 %08x\n",ColorSpaceValue_2);
+                    break;
+            }
+                    break;
+                default:
+                    DBG_DD("Unknown DeviceID\n");
+                    break;
+            }//End of DeviceID            
+        }
+        else
+        {
+            VIDOutD(V1_ColorSpaceReg_1, gVIAGraphicInfo.ColorSpaceValue1);
+            VIDOutD(V1_ColorSpaceReg_2, gVIAGraphicInfo.ColorSpaceValue2);
+        }
+
+            dwBackBufferCount = lpDDSurfaceDesc->dwBackBufferCount;
+            dwWidth  = lpDDSurfaceDesc->dwWidth;
+            dwHeight = lpDDSurfaceDesc->dwHeight;
+            dwPitch  = ALIGN_TO_32_BYTES(dwWidth)*2;
+            DBG_DD("    srcWidth= %ld \n", dwWidth);
+            DBG_DD("    srcHeight= %ld \n", dwHeight);
+
+            SWFBSIZE = dwPitch*dwHeight;    //YUYV
+
+            if (!gVIAGraphicInfo.DRMEnabled)
+            {
+                SWMemRequest.checkID = VIA_MID;
+                SWMemRequest.size    = SWFBSIZE*2; //2 frame buffers
+                SWMemRequest.type    = VIDMGR_TYPE_VIDEO;
+                if ( MEM_OK != viaMgr_vid_ioctl(VIAMGR_ALLOC_VIDEO, (char *)(&SWMemRequest) ) )
+                {
+                    DBG_DD(" Memory Allocation fail for SW YUY2 Video.\n");
+                    return PI_ERR_CANNOT_CREATE_SURFACE;
+                }
+                dwAddr = ALIGN_TO_32_BYTES(SWMemRequest.offset);
+            }
+#ifdef HAVE_DRM
+            else
+            {
+                SWfbRequest.context=1;
+                SWfbRequest.size=SWFBSIZE*2;
+                SWfbRequest.type= VIDEO;
+                via_fb_alloc(&SWfbRequest);
+
+                dwAddr = SWfbRequest.offset;
+            }
+#endif
+
+            //fill in the SW buffer with 0x8000 (YUY2-black color) to clear FB buffer
+            lpTmpAddr = lpPrimarySurface + dwAddr;
+            for(iCount=0;iCount<(SWFBSIZE*2);iCount++)
+            {
+                if((iCount%2) == 0)
+                    *lpTmpAddr++=0x00;
+                else
+                    *lpTmpAddr++=0x80;
+            }
+
+            SWDevice.dwSWPhysicalAddr[0]   = dwAddr;
+            SWDevice.lpSWOverlaySurface[0] = lpPrimarySurface+dwAddr;
+
+            SWDevice.dwSWPhysicalAddr[1] = SWDevice.dwSWPhysicalAddr[0] + SWFBSIZE;
+            SWDevice.lpSWOverlaySurface[1] = SWDevice.lpSWOverlaySurface[0] + SWFBSIZE;
+
+            DBG_DD("SWDevice.dwSWPhysicalAddr[0] %08lx\n", dwAddr);
+            DBG_DD("SWDevice.dwSWPhysicalAddr[1] %08lx\n", dwAddr + SWFBSIZE);
+
+            SWDevice.gdwSWSrcWidth = dwWidth;
+            SWDevice.gdwSWSrcHeight= dwHeight;
+            SWDevice.dwPitch = dwPitch;
+
+            // Fill image data in overlay record
+            overlayRecordV1.dwV1OriWidth  = dwWidth;
+            overlayRecordV1.dwV1OriHeight = dwHeight;
+            overlayRecordV1.dwV1OriPitch  = dwPitch;
+if (!(gdwVideoFlagSW & SW_USE_HQV))
+            break;
+
+        case FOURCC_HQVSW :
+            DBG_DD("//Create HQV_SW Surface\n");
+            dwWidth  = SWDevice.gdwSWSrcWidth;
+            dwHeight = SWDevice.gdwSWSrcHeight;
+            dwPitch  = SWDevice.dwPitch; 
+
+            HQVFBSIZE = dwPitch * dwHeight;
+
+            if (!gVIAGraphicInfo.DRMEnabled)
+            {
+                HQVMemRequest.checkID = VIA_MID;
+                //HQVMemRequest.size    = (HQVFBSIZE*2);
+                
+                if ( lpVideoHWDifference->dwThreeHQVBuffer )  //CLE_C0
+                    HQVMemRequest.size    = (HQVFBSIZE * 3);
+                else
+                    HQVMemRequest.size    = (HQVFBSIZE*2);
+                
+                //HQVMemRequest.size    = (HQVFBSIZE*2)+((dwPitch<<1)*4);
+                HQVMemRequest.type    = VIDMGR_TYPE_VIDEO;
+                if ( MEM_OK != viaMgr_vid_ioctl(VIAMGR_ALLOC_VIDEO, (char *)(&HQVMemRequest) ) )
+                {
+                    DBG_DD(" Memory Allocation fail for SW HQV Video.\n");
+                    return PI_ERR_CANNOT_CREATE_SURFACE;
+                }
+                dwAddr = ALIGN_TO_32_BYTES(HQVMemRequest.offset);
+            }
+#ifdef HAVE_DRM
+            else
+            {
+                HQVfbRequest.context=1;
+                
+                if ( lpVideoHWDifference->dwThreeHQVBuffer )    //CLE_C0
+                    HQVfbRequest.size=HQVFBSIZE*3;
+                else
+                    HQVfbRequest.size=HQVFBSIZE*2;
+                    
+                HQVfbRequest.type= VIDEO;
+                via_fb_alloc(&HQVfbRequest);
+
+                dwAddr = HQVfbRequest.offset;
+            }
+#endif
+
+            overlayRecordV1.dwHQVAddr[0] = dwAddr;
+            overlayRecordV1.dwHQVAddr[1] = dwAddr + HQVFBSIZE;
+
+            //if ( (lpMPGDevice->dwRevisionID) == 0x0f )    //CLE_C0
+            if ( lpVideoHWDifference->dwThreeHQVBuffer )    //CLE_C0
+            {
+                overlayRecordV1.dwHQVAddr[2] = overlayRecordV1.dwHQVAddr[1] + HQVFBSIZE;
+                
+                if (overlayRecordV1.dwHQVAddr[2] + HQVFBSIZE >=
+                                        (unsigned long)gVIAGraphicInfo.Screen[ScrnIndex].VideoHeapEnd)
+                {
+                    DBG_DD("//    :Memory not enough for MPEG with HQV\n");
+                    return PI_ERR_CANNOT_CREATE_SURFACE;
+                }
+            }
+            else
+            {
+                if (overlayRecordV1.dwHQVAddr[1] + HQVFBSIZE >=
+                                        (unsigned long)gVIAGraphicInfo.Screen[ScrnIndex].VideoHeapEnd)
+                {
+                    DBG_DD("//    :Memory not enough for MPEG with HQV\n");
+                    return PI_ERR_CANNOT_CREATE_SURFACE;
+                }
+            }
+
+            //fill in the HQV buffer with 0x8000 (YUY2-black color) to clear HQV buffers
+            for(iCount=0;iCount<HQVFBSIZE*2;iCount++)
+            {
+                lpTmpAddr = lpPrimarySurface + dwAddr + iCount;
+                if((iCount%2) == 0)
+                    *(lpTmpAddr)=0x00;
+                else
+                    *(lpTmpAddr)=0x80;
+            }
+            
+            VIDOutD(HQV_DST_STARTADDR1,overlayRecordV1.dwHQVAddr[1]);
+            VIDOutD(HQV_DST_STARTADDR0,overlayRecordV1.dwHQVAddr[0]);
+
+            if ( lpVideoHWDifference->dwThreeHQVBuffer )    //CLE_C0
+            {
+                VIDOutD(HQV_DST_STARTADDR2,overlayRecordV1.dwHQVAddr[2]);    
+                DBG_DD("000003FC %08lx\n",VIDInD(HQV_DST_STARTADDR2) );  
+            }
+
+            DBG_DD("000003F0 %08lx\n",VIDInD(HQV_DST_STARTADDR1) );
+            DBG_DD("000003EC %08lx\n",VIDInD(HQV_DST_STARTADDR0) );
+             
+            break;
+
+       case FOURCC_YV12 :
+            /*via = &via_v4l_devices[0];*/
+            DBG_DD("    Create SW YV12 Surface: \n");
+            lpDPFsrc->dwFlags = DDPF_FOURCC;
+            lpDPFsrc->dwFourCC = FOURCC_YV12;
+
+            // init Video status flag
+            switch ( gVIAGraphicInfo.dwDeviceID )
+            {
+                case VIA_DEVICE_VT3205:
+                    gdwVideoFlagSW = VIDEO_HQV_INUSE | SW_USE_HQV | VIDEO_3_INUSE;
+                    break;
+                case VIA_DEVICE_CLE1:
+                case VIA_DEVICE_CLE2:
+                default:
+            gdwVideoFlagSW = VIDEO_HQV_INUSE | SW_USE_HQV | VIDEO_1_INUSE;
+                    break;
+            }
+
+            if (gdwVideoFlagTV0 & VIDEO_HQV_INUSE)
+            {
+                lpNewVidCtrl->dwHighQVDO = VW_HIGHQVDO_OFF;
+                VIADriverProc( HQVCONTROL , lpNewVidCtrl );
+            }
+            
+            // write Color Space Conversion param. 
+        if (!gVIAGraphicInfo.ColorSpaceChanged)    
+        {
+            switch ( gVIAGraphicInfo.dwDeviceID )
+            {
+                case VIA_DEVICE_VT3205:
+                    VIDOutD(V3_ColorSpaceReg_1, ColorSpaceValue_1_32045);
+                    VIDOutD(V3_ColorSpaceReg_2, ColorSpaceValue_2_32045);                    
+                    DBG_DD("000002C4 %08x\n",ColorSpaceValue_1_32045);
+                    DBG_DD("000002C8 %08x\n",ColorSpaceValue_2_32045);
+                    break;
+                case VIA_DEVICE_CLE1:
+                case VIA_DEVICE_CLE2:
+            switch ( DispatchVGARevisionID() )
+            {
+            	case VIA_REVISION_CLECX :
+                    VIDOutD(V1_ColorSpaceReg_1, ColorSpaceValue_1_3123C0);
+                    VIDOutD(V1_ColorSpaceReg_2, ColorSpaceValue_2_3123C0);
+
+                    DBG_DD("00000284 %08x\n",ColorSpaceValue_1_3123C0);
+                    DBG_DD("00000288 %08x\n",ColorSpaceValue_2_3123C0);
+                    break;
+                
+                default :
+                    VIDOutD(V1_ColorSpaceReg_2, ColorSpaceValue_2);
+                            VIDOutD(V1_ColorSpaceReg_1, ColorSpaceValue_1);
+
+                    DBG_DD("00000288 %08x\n",ColorSpaceValue_2);
+                            DBG_DD("00000284 %08x\n",ColorSpaceValue_1);
+                    break;
+            }
+                    break;
+                default:
+                    DBG_DD("Unknown DeviceID\n");
+                    break;
+            }//End of DeviceID
+        }
+        else
+        {
+            VIDOutD(V1_ColorSpaceReg_1, gVIAGraphicInfo.ColorSpaceValue1);
+            VIDOutD(V1_ColorSpaceReg_2, gVIAGraphicInfo.ColorSpaceValue2);
+        }
+
+            dwBackBufferCount = lpDDSurfaceDesc->dwBackBufferCount;
+            dwWidth  = lpDDSurfaceDesc->dwWidth;
+            dwHeight = lpDDSurfaceDesc->dwHeight;
+            dwPitch  = ALIGN_TO_32_BYTES(dwWidth);
+            DBG_DD("    srcWidth= %ld \n", dwWidth);
+            DBG_DD("    srcHeight= %ld \n", dwHeight);
+
+            SWFBSIZE = dwPitch * dwHeight * 1.5;    //1.5 bytes per pixel
+
+            if (!gVIAGraphicInfo.DRMEnabled)
+            {
+                SWMemRequest.checkID = VIA_MID;
+                SWMemRequest.size    = SWFBSIZE*2; //2 frame buffers
+                SWMemRequest.type    = VIDMGR_TYPE_VIDEO;
+                if ( MEM_OK != viaMgr_vid_ioctl(VIAMGR_ALLOC_VIDEO, (char *)(&SWMemRequest) ) )
+                {
+                    DBG_DD(" Memory Allocation fail for SW YUY2 Video.\n");
+                    return PI_ERR_CANNOT_CREATE_SURFACE;
+                }
+                dwAddr = ALIGN_TO_32_BYTES(SWMemRequest.offset);
+            }
+#ifdef HAVE_DRM
+            else
+            {
+                SWfbRequest.context=1;
+                SWfbRequest.size=SWFBSIZE*2;
+                SWfbRequest.type= VIDEO;
+                via_fb_alloc(&SWfbRequest);
+
+                dwAddr = SWfbRequest.offset;
+            }
+#endif
+
+            //fill in the SW buffer with 0x8000 (YUY2-black color) to clear FB buffer
+            lpTmpAddr = lpPrimarySurface + dwAddr;
+            for(iCount=0;iCount<(SWFBSIZE*2);iCount++)
+            {
+                if((iCount%2) == 0)
+                    *lpTmpAddr++=0x00;
+                else
+                    *lpTmpAddr++=0x80;
+            }
+
+            SWDevice.dwSWPhysicalAddr[0]   = dwAddr;
+            SWDevice.dwSWCrPhysicalAddr[0] = SWDevice.dwSWPhysicalAddr[0]
+                                             + (dwPitch*dwHeight);
+            SWDevice.dwSWCbPhysicalAddr[0] = SWDevice.dwSWCrPhysicalAddr[0]
+                                             + ((dwPitch>>1)*(dwHeight>>1));
+            SWDevice.lpSWOverlaySurface[0] = lpPrimarySurface+dwAddr;
+
+            SWDevice.dwSWPhysicalAddr[1] = dwAddr + SWFBSIZE;
+            SWDevice.dwSWCrPhysicalAddr[1] = SWDevice.dwSWPhysicalAddr[1]
+                                             + (dwPitch*dwHeight);
+            SWDevice.dwSWCbPhysicalAddr[1] = SWDevice.dwSWCrPhysicalAddr[1]
+                                             + ((dwPitch>>1)*(dwHeight>>1));
+            SWDevice.lpSWOverlaySurface[1] = SWDevice.lpSWOverlaySurface[0] + SWFBSIZE;
+
+            DBG_DD("SWDevice.dwSWPhysicalAddr[0] %08lx\n", dwAddr);
+            DBG_DD("SWDevice.dwSWPhysicalAddr[1] %08lx\n", dwAddr + SWFBSIZE);
+
+            SWDevice.gdwSWSrcWidth = dwWidth;
+            SWDevice.gdwSWSrcHeight= dwHeight;
+            SWDevice.dwPitch = dwPitch;
+
+            // Fill image data in overlay record
+            overlayRecordV1.dwV1OriWidth  = dwWidth;
+            overlayRecordV1.dwV1OriHeight = dwHeight;
+            overlayRecordV1.dwV1OriPitch  = dwPitch;
+
+//if (!(gdwVideoFlagSW & SW_USE_HQV))
+//            break;
+//        case FOURCC_HQVSW :
+
+            // 
+            //  if sw video use HQV dwpitch should changed
+            // 
+            DBG_DD("//Create HQV_SW Surface\n");
+//            lpDPFsrc->dwFourCC = FOURCC_YUY2;
+            dwWidth  = SWDevice.gdwSWSrcWidth;
+            dwHeight = SWDevice.gdwSWSrcHeight;
+            dwPitch  = SWDevice.dwPitch; 
+
+            HQVFBSIZE = dwPitch * dwHeight * 2;
+
+            if (!gVIAGraphicInfo.DRMEnabled)
+            {
+                HQVMemRequest.checkID = VIA_MID;
+                //HQVMemRequest.size    = (HQVFBSIZE*2);
+                
+                if ( lpVideoHWDifference->dwThreeHQVBuffer )  //CLE_C0
+                    HQVMemRequest.size    = (HQVFBSIZE * 3);
+                else
+                    HQVMemRequest.size    = (HQVFBSIZE*2);
+                
+                //HQVMemRequest.size    = (HQVFBSIZE*2)+((dwPitch<<1)*4);
+                HQVMemRequest.type    = VIDMGR_TYPE_VIDEO;
+                if ( MEM_OK != viaMgr_vid_ioctl(VIAMGR_ALLOC_VIDEO, (char *)(&HQVMemRequest) ) )
+                {
+                    DBG_DD(" Memory Allocation fail for SW HQV Video.\n");
+                    return PI_ERR_CANNOT_CREATE_SURFACE;
+                }
+                dwAddr = ALIGN_TO_32_BYTES(HQVMemRequest.offset);
+            }
+#ifdef HAVE_DRM
+            else
+            {
+                HQVfbRequest.context=1;
+                
+                if ( lpVideoHWDifference->dwThreeHQVBuffer )    //CLE_C0
+                    HQVfbRequest.size=HQVFBSIZE*3;
+                else
+                    HQVfbRequest.size=HQVFBSIZE*2;
+                    
+                HQVfbRequest.type= VIDEO;
+                via_fb_alloc(&HQVfbRequest);
+
+                dwAddr = HQVfbRequest.offset;
+            }
+#endif
+
+            overlayRecordV1.dwHQVAddr[0] = dwAddr;
+            overlayRecordV1.dwHQVAddr[1] = dwAddr + HQVFBSIZE;
+
+            if ( lpVideoHWDifference->dwThreeHQVBuffer )    //CLE_C0
+            {
+                overlayRecordV1.dwHQVAddr[2] = overlayRecordV1.dwHQVAddr[1] + HQVFBSIZE;
+                
+                if (overlayRecordV1.dwHQVAddr[2] + HQVFBSIZE >=
+                            (unsigned long)gVIAGraphicInfo.Screen[ScrnIndex].VideoHeapEnd)
+                {
+                    DBG_DD("//    :Memory not enough for MPEG with HQV\n");
+                    return PI_ERR_CANNOT_CREATE_SURFACE;
+                }
+            }
+            else
+            {
+                if (overlayRecordV1.dwHQVAddr[1] + HQVFBSIZE >=
+                            (unsigned long)gVIAGraphicInfo.Screen[ScrnIndex].VideoHeapEnd)
+                {
+                    DBG_DD("//    :Memory not enough for MPEG with HQV\n");
+                    return PI_ERR_CANNOT_CREATE_SURFACE;
+                }
+            }
+
+            //fill in the HQV buffer with 0x8000 (YUY2-black color) to clear HQV buffers
+            for(iCount=0;iCount<HQVFBSIZE*2;iCount++)
+            {
+                lpTmpAddr = lpPrimarySurface + dwAddr + iCount;
+                if((iCount%2) == 0)
+                    *(lpTmpAddr)=0x00;
+                else
+                    *(lpTmpAddr)=0x80;
+            }
+            
+            VIDOutD(HQV_DST_STARTADDR1,overlayRecordV1.dwHQVAddr[1]);
+            VIDOutD(HQV_DST_STARTADDR0,overlayRecordV1.dwHQVAddr[0]);
+
+            if ( lpVideoHWDifference->dwThreeHQVBuffer )    //CLE_C0
+            {
+                VIDOutD(HQV_DST_STARTADDR2,overlayRecordV1.dwHQVAddr[2]);    
+                DBG_DD("000003FC %08lx\n",VIDInD(HQV_DST_STARTADDR2) );  
+            }
+
+            DBG_DD("000003F0 %08lx\n",VIDInD(HQV_DST_STARTADDR1) );
+            DBG_DD("000003EC %08lx\n",VIDInD(HQV_DST_STARTADDR0) );
+             
+            break;
+
+        default :
+            break;
+    }
+
+    return dwRet;
+
+} //CreateSurface
+
+
+
+
+
+/*
+ *  Destroy Surface
+ */
+unsigned long DestroySurface( LPDDSURFACEDESC lpDDSurfaceDesc)
+{
+    VIAVIDCTRL NewvidCtrl;
+    LPVIAVIDCTRL lpNewVidCtrl = &NewvidCtrl;
+
+    DBG_DD("//DestroySurface: \n");
+
+    switch (lpDDSurfaceDesc->dwFourCC)
+    {        
+        case FOURCC_SUBP:
+            SUBPMemRequest.checkID=VIA_MID;
+            SUBPMemRequest.type=VIDMGR_TYPE_VIDEO;
+
+            if (!gVIAGraphicInfo.DRMEnabled)
+            {
+                if (MEM_OK != viaMgr_vid_ioctl(VIAMGR_FREE_VIDEO, (char*)(&SUBPMemRequest) ) )
+                {
+                    DBG_DD(" Memory Free fail for subpicture \n");
+                }
+                DBG_DD(" Memory Free for subpicture \n");
+            }
+#ifdef HAVE_DRM
+		else
+		{
+			via_fb_free(&SUBPfbRequest);
+		}
+#endif			
+		break;
+
+	case FOURCC_VIA:
+		MPEGMemRequest.checkID=VIA_MID;
+		MPEGMemRequest.type=VIDMGR_TYPE_VIDEO;
+		
+		if (!gVIAGraphicInfo.DRMEnabled)
+		{
+		   if (MEM_OK != viaMgr_vid_ioctl(VIAMGR_FREE_VIDEO, (char*)(&MPEGMemRequest) ) )
+		   {
+			     DBG_DD(" Memory Free fail for MPEG Video \n");
+		   }
+		   DBG_DD(" Memory Free for MPEG Video \n");
+			
+		}
+#ifdef HAVE_DRM
+		else
+		{
+			via_fb_free(&MPEGfbRequest);
+		}
+#endif			
+		
+		if (!(gdwVideoFlagMPEG & MPEG_USE_HQV))
+		{
+			gdwVideoFlagMPEG=0;
+			break;
+		}
+
+
+	case FOURCC_HQVMPEG:
+	    HQVMemRequest.checkID = VIA_MID;
+	    HQVMemRequest.type = VIDMGR_TYPE_VIDEO;
+        
+        if (!gVIAGraphicInfo.DRMEnabled)
+        {
+            if (MEM_OK != viaMgr_vid_ioctl(VIAMGR_FREE_VIDEO, (char*)(&HQVMemRequest) ) )
+            {
+                DBG_DD(" Memory Free fail for MPEG HQV Video \n");
+            }
+            DBG_DD(" Memory Free for MPEG HQV Video \n");
+            
+        }
+#ifdef HAVE_DRM
+        else
+        {
+            via_fb_free(&HQVfbRequest);
+        }
+#endif
+        
+        gdwVideoFlagMPEG = 0;
+        
+        if (gdwVideoFlagTV1 != 0)
+		{
+            DBG_DD(" Assign HQV to TV1 \n");
+            lpNewVidCtrl->dwHighQVDO = VW_HIGHQVDO_TV1;
+            VIADriverProc( HQVCONTROL , lpNewVidCtrl );
+        }
+        break;
+        
+       case FOURCC_TV1 :
+            DBG_DD(" Destroy TV1 Surface! \n");
+            TV1MemRequest.checkID = VIA_MID;
+            TV1MemRequest.type    = VIDMGR_TYPE_VIDEO;
+
+            if (!gVIAGraphicInfo.DRMEnabled)
+            {
+                if ( MEM_OK != viaMgr_vid_ioctl(VIAMGR_FREE_VIDEO, (char *)(&TV1MemRequest) ) )
+                {
+                   DBG_DD(" Memory Free fail for TV1 Video \n");
+                }
+                DBG_DD(" Memory Free for TV1 Video \n");
+            }
+#ifdef HAVE_DRM
+            else
+                via_fb_free(&TV1fbRequest);
+#endif
+
+            if (!(gdwVideoFlagTV1 & CAP1_USE_HQV))
+            {
+                gdwVideoFlagTV1 = 0;
+                break;
+            }
+
+       case FOURCC_HQVTV1 :
+            DBG_DD(" Destroy TV1 HQV Surface! \n");
+            HQVMemRequest.checkID = VIA_MID;
+            HQVMemRequest.type    = VIDMGR_TYPE_VIDEO;
+
+            if (!gVIAGraphicInfo.DRMEnabled)
+            {
+                if ( MEM_OK != viaMgr_vid_ioctl(VIAMGR_FREE_VIDEO, (char *)(&HQVMemRequest) ) )
+                {
+                   DBG_DD(" Memory Free fail for TV1 HQV Video \n");
+                }
+                DBG_DD(" Memory Free for TV1 HQV Video \n");
+            }
+#ifdef HAVE_DRM
+            else
+                via_fb_free(&HQVfbRequest);
+#endif
+
+            if (TV1_ON == FALSE)
+                gdwVideoFlagTV1 = 0;
+            
+            if ( (gdwVideoFlagTV0 != 0) && (!gVIAGraphicInfo.HQV_ManualSwitch) )
+            {
+                lpNewVidCtrl->dwHighQVDO = VW_HIGHQVDO_TV0;
+                /*lpNewVidCtrl->dwHighQVDO = VW_HIGHQVDO_TV1;*/
+                VIADriverProc( HQVCONTROL , lpNewVidCtrl );
+            }
+            break;
+
+       case FOURCC_TV0 :
+            DBG_DD(" Destroy TV0 Surface! \n");
+            TV0MemRequest.checkID = VIA_MID;
+            TV0MemRequest.type    = VIDMGR_TYPE_VIDEO;
+
+            if (!gVIAGraphicInfo.DRMEnabled)
+            {
+                if ( viaMgr_vid_ioctl(VIAMGR_FREE_VIDEO, (char *)(&TV0MemRequest) ) != MEM_OK )
+                {
+                   DBG_DD(" Memory Free fail for TV0 Video \n");
+                }
+            }
+            
+#ifdef HAVE_DRM
+            else
+                via_fb_free(&TV0fbRequest);
+#endif
+            
+            if (!(gdwVideoFlagTV0 & CAP0_USE_HQV))
+            {
+                gdwVideoFlagTV0 = 0;
+                break;
+            }
+
+       case FOURCC_HQVTV0 :
+            DBG_DD(" Destroy TV0 HQV Surface! \n");
+            HQVMemRequest.checkID = VIA_MID;
+            HQVMemRequest.type    = VIDMGR_TYPE_VIDEO;
+
+            if (!gVIAGraphicInfo.DRMEnabled)
+            {
+                if ( viaMgr_vid_ioctl(VIAMGR_FREE_VIDEO, (char *)(&HQVMemRequest) ) != MEM_OK )
+                {
+                   DBG_DD(" Memory Free fail for TV0 HQV Video \n");
+                }
+            }
+#ifdef HAVE_DRM
+            else
+                via_fb_free(&HQVfbRequest);
+#endif
+
+            if (TV0_ON == FALSE)
+                gdwVideoFlagTV0 = 0;
+            
+            if ( (gdwVideoFlagTV1 != 0) && (!gVIAGraphicInfo.HQV_ManualSwitch) )
+            {
+                lpNewVidCtrl->dwHighQVDO = VW_HIGHQVDO_TV1;
+                /*lpNewVidCtrl->dwHighQVDO = VW_HIGHQVDO_TV0;*/
+                VIADriverProc( HQVCONTROL , lpNewVidCtrl );
+            }
+            break;
+
+       case FOURCC_ALPHA :
+            ALPHAMemRequest.checkID = VIA_MID;
+            ALPHAMemRequest.type    = VIDMGR_TYPE_VIDEO;
+
+            if (!gVIAGraphicInfo.DRMEnabled)
+            {
+                if ( MEM_OK != viaMgr_vid_ioctl(VIAMGR_FREE_VIDEO, (char *)(&ALPHAMemRequest) ) )
+                {
+                   DBG_DD(" Memory Free fail for ALPHA \n");
+                }
+                DBG_DD(" Memory Free for ALPHA \n");
+            }
+#ifdef HAVE_DRM
+            else
+                via_fb_free(&ALPHAfbRequest);
+#endif
+            break;
+
+       case FOURCC_YUY2 :
+            lpDPFsrc->dwFlags = 0;
+            lpDPFsrc->dwFourCC = 0;
+            SWMemRequest.checkID = VIA_MID;
+            SWMemRequest.type    = VIDMGR_TYPE_VIDEO;
+
+            if (!gVIAGraphicInfo.DRMEnabled)
+            {
+                if ( MEM_OK != viaMgr_vid_ioctl(VIAMGR_FREE_VIDEO, (char *)(&SWMemRequest) ) )
+                {
+                   DBG_DD(" Memory Free fail for SW YUY2 Surface \n");
+                }
+                DBG_DD(" Memory Free for SW YUY2 Surface \n");
+            }
+#ifdef HAVE_DRM
+            else
+                via_fb_free(&SWfbRequest);
+#endif
+
+            if (!(gdwVideoFlagSW & SW_USE_HQV))
+            {
+                gdwVideoFlagSW = 0;
+                break;
+            }
+
+       case FOURCC_HQVSW :
+            HQVMemRequest.checkID = VIA_MID;
+            HQVMemRequest.type    = VIDMGR_TYPE_VIDEO;
+
+            if (!gVIAGraphicInfo.DRMEnabled)
+            {
+                if ( MEM_OK != viaMgr_vid_ioctl(VIAMGR_FREE_VIDEO, (char *)(&HQVMemRequest) ) )
+                {
+                   DBG_DD(" Memory Free fail for SW YUY2 HQV Surface \n");
+                }
+                DBG_DD(" Memory Free for SW YUY2 HQV Surface \n");
+            }
+#ifdef HAVE_DRM
+            else
+                via_fb_free(&HQVfbRequest);
+#endif
+
+            gdwVideoFlagSW = 0;
+            if (gdwVideoFlagTV1 != 0)
+            {
+                DBG_DD(" Assign HQV to TV1 \n");
+                lpNewVidCtrl->dwHighQVDO = VW_HIGHQVDO_TV1;
+                VIADriverProc( HQVCONTROL , lpNewVidCtrl );
+            }
+            break;
+
+       case FOURCC_YV12 :
+            lpDPFsrc->dwFlags = 0;
+            lpDPFsrc->dwFourCC = 0;
+            SWMemRequest.checkID = VIA_MID;
+            SWMemRequest.type    = VIDMGR_TYPE_VIDEO;
+
+            if (!gVIAGraphicInfo.DRMEnabled)
+            {
+                if ( MEM_OK != viaMgr_vid_ioctl(VIAMGR_FREE_VIDEO, (char *)(&SWMemRequest) ) )
+                {
+                   DBG_DD(" Memory Free fail for SW YV12 Surface \n");
+                }
+                DBG_DD(" Memory Free for SW YV12 Surface \n");
+            }
+#ifdef HAVE_DRM
+            else
+                via_fb_free(&SWfbRequest);
+#endif
+
+            HQVMemRequest.checkID = VIA_MID;
+            HQVMemRequest.type    = VIDMGR_TYPE_VIDEO;
+
+            if (!gVIAGraphicInfo.DRMEnabled)
+            {
+                if ( MEM_OK != viaMgr_vid_ioctl(VIAMGR_FREE_VIDEO, (char *)(&HQVMemRequest) ) )
+                {
+                   DBG_DD(" Memory Free fail for SW YV12 HQV Surface \n");
+                }
+                DBG_DD(" Memory Free for SW YV12 HQV Surface \n");
+            }
+#ifdef HAVE_DRM
+            else
+                via_fb_free(&HQVfbRequest);
+#endif
+
+            gdwVideoFlagSW = 0;
+/*            if (gdwVideoFlagTV1 != 0)
+            {
+                DBG_DD(" Assign HQV to TV1 \n");
+                lpNewVidCtrl->dwHighQVDO = VW_HIGHQVDO_TV1;
+                VIADriverProc( HQVCONTROL , lpNewVidCtrl );
+            }*/
+            if (gdwVideoFlagTV1 != 0)
+            {
+                DBG_DD(" Assign HQV to TV1 \n");
+                lpNewVidCtrl->dwHighQVDO = VW_HIGHQVDO_TV1;
+                VIADriverProc( HQVCONTROL , lpNewVidCtrl );
+            }
+            break;
+
+        default :
+            break;
+    }
+
+    //memset(&MPGDevice, 0, sizeof(MPGDevice));
+    return PI_OK;
+
+} //DestroySurface
+
+
+
+/*
+ *  Lock Surface
+ */
+unsigned long LockSurface(LPDDLOCK lpLock)
+{
+
+    via_device *via;
+
+    via = &via_v4l_devices[0];
+
+    switch (lpLock->dwFourCC)
+    {
+        case FOURCC_SUBP:
+            lpLock->MPGDev = MPGDevice;
+            lpLock->SubDev = SUBDevice;
+            lpLock->dwPhysicalBase = via->mb0;
+            break;
+            
+        case FOURCC_VIA:
+            lpLock->MPGDev = MPGDevice;
+            lpLock->dwPhysicalBase = via->mb0;
+            break;
+            
+        case FOURCC_HQVMPEG:
+            lpLock->MPGDev = MPGDevice;
+            lpLock->dwPhysicalBase = via->mb0;
+            break;            
+
+        case FOURCC_TV1 :
+            lpLock->Capdev_TV1 = CAPDevice[1];
+            lpLock->dwPhysicalBase = via->mb0;
+            break;
+
+        case FOURCC_TV0 :
+            lpLock->Capdev_TV0 = CAPDevice[0];
+            lpLock->dwPhysicalBase = via->mb0;
+            break;
+
+        case FOURCC_ALPHA :
+            lpLock->Alphadev = ALPDevice ;
+            lpLock->dwPhysicalBase = via->mb0;
+            break;
+
+       case FOURCC_YUY2 :
+       case FOURCC_YV12 :
+            lpLock->SWDevice = SWDevice ;
+            lpLock->dwPhysicalBase = via->mb0;
+            break;
+
+       default :
+            break;
+    }
+         
+    return PI_OK;
+
+} //LockSurface
+
+
+unsigned long Flip(unsigned long DisplayBufferIndex)
+{
+    while ((VIDInD(HQV_CONTROL) & HQV_SW_FLIP) );
+    VIDOutD(HQV_SRC_STARTADDR_Y, SWDevice.dwSWPhysicalAddr[DisplayBufferIndex]);
+    VIDOutD(HQV_CONTROL,( VIDInD(HQV_CONTROL)&~HQV_FLIP_ODD) |HQV_SW_FLIP|HQV_FLIP_STATUS);
+
+    return PI_OK;
+}
+
+
+void VIAAlphaWin( LPALPHACTRL lpParam)
+{
+    unsigned long dwControl = 0;
+    unsigned long dwCompose = 0;
+
+    if (!lpParam->AlphaEnable)
+        return;
+    else
+    {
+        switch (lpParam->type)
+        {
+            case ALPHA_CONSTANT :
+                dwControl = 0x00000000;
+                dwControl |= (lpParam->ConstantFactor&0x0F)<<12;
+//                dwCompose = VIDInD(V_COMPOSE_MODE) & ~SELECT_VIDEO_IF_COLOR_KEY;
+
+                switch ( gVIAGraphicInfo.dwDeviceID )
+                {
+                    case VIA_DEVICE_VT3205:
+                        dwCompose = VIDInD(V_COMPOSE_MODE) & ~SELECT_VIDEO_IF_COLOR_KEY;
+                        break;
+                    case VIA_DEVICE_CLE1:
+                    case VIA_DEVICE_CLE2:
+                        switch ( DispatchVGARevisionID() )
+                        {
+                      	    case VIA_REVISION_CLECX :
+                                dwCompose = VIDInD(V_COMPOSE_MODE) & ~(SELECT_VIDEO_IF_COLOR_KEY|SELECT_VIDEO3_IF_COLOR_KEY);
+                                break;
+                            default:
+                                /* Overlay source format for V3*/
+                dwCompose = VIDInD(V_COMPOSE_MODE) & ~SELECT_VIDEO_IF_COLOR_KEY;
+                                break;
+                        }
+                        break;
+                    default:
+                        DBG_DD("Unknown DeviceID\n");
+                        break;
+                }//End of DeviceID
+                
+                gdwAlphaEnabled = 1;
+                break;
+
+            case ALPHA_STREAM :
+                dwControl = 0x00000001|0x0f<<12;
+//                dwCompose = VIDInD(V_COMPOSE_MODE) & ~SELECT_VIDEO_IF_COLOR_KEY;
+
+                switch ( gVIAGraphicInfo.dwDeviceID )
+                {
+                    case VIA_DEVICE_VT3205:
+                        dwCompose = VIDInD(V_COMPOSE_MODE) & ~SELECT_VIDEO_IF_COLOR_KEY;
+                        break;
+                    case VIA_DEVICE_CLE1:
+                    case VIA_DEVICE_CLE2:
+                        switch ( DispatchVGARevisionID() )
+                        {
+                      	    case VIA_REVISION_CLECX :
+                                dwCompose = VIDInD(V_COMPOSE_MODE) & ~(SELECT_VIDEO_IF_COLOR_KEY|SELECT_VIDEO3_IF_COLOR_KEY);
+                                break;
+                            default:
+                                /* Overlay source format for V3*/
+                dwCompose = VIDInD(V_COMPOSE_MODE) & ~SELECT_VIDEO_IF_COLOR_KEY;
+                                break;
+                        }
+                        break;
+                    default:
+                        DBG_DD("Unknown DeviceID\n");
+                        break;
+                }//End of DeviceID
+                
+                gdwAlphaEnabled = 1;
+                break;
+
+            case ALPHA_GRAPHIC :
+                dwControl = 0x00000002;
+                break;
+
+            case ALPHA_COMBINE :
+                dwControl = 0x00000001|(lpParam->ConstantFactor&0x0F)<<12;
+//                dwCompose = VIDInD(V_COMPOSE_MODE) & ~SELECT_VIDEO_IF_COLOR_KEY;
+
+                switch ( gVIAGraphicInfo.dwDeviceID )
+                {
+                    case VIA_DEVICE_VT3205:
+                dwCompose = VIDInD(V_COMPOSE_MODE) & ~SELECT_VIDEO_IF_COLOR_KEY;
+                break;
+                    case VIA_DEVICE_CLE1:
+                    case VIA_DEVICE_CLE2:
+                        switch ( DispatchVGARevisionID() )
+                        {
+                      	    case VIA_REVISION_CLECX :
+                                dwCompose = VIDInD(V_COMPOSE_MODE) & ~(SELECT_VIDEO_IF_COLOR_KEY|SELECT_VIDEO3_IF_COLOR_KEY);
+                                break;
+                            default:
+                                /* Overlay source format for V3*/
+                                dwCompose = VIDInD(V_COMPOSE_MODE) & ~SELECT_VIDEO_IF_COLOR_KEY;
+                                break;
+                        }
+                        break;
+                    default:
+                        DBG_DD("Unknown DeviceID\n");
+                        break;
+                }//End of DeviceID
+                
+                gdwAlphaEnabled = 1;
+                break;
+
+            case ALPHA_DISABLE :
+                /* H/W has no disable blending bit(s), so use Constant Alpha */
+                dwControl = 0x00000000;
+                dwControl |= (0x0f << 12);
+//                dwCompose = VIDInD(V_COMPOSE_MODE) | SELECT_VIDEO_IF_COLOR_KEY;
+
+                switch ( gVIAGraphicInfo.dwDeviceID )
+                {
+                    case VIA_DEVICE_VT3205:
+                        dwCompose = VIDInD(V_COMPOSE_MODE) | SELECT_VIDEO_IF_COLOR_KEY;
+                        break;
+                    case VIA_DEVICE_CLE1:
+                    case VIA_DEVICE_CLE2:
+                        switch ( DispatchVGARevisionID() )
+                        {
+                      	    case VIA_REVISION_CLECX :
+                                dwCompose = VIDInD(V_COMPOSE_MODE) | SELECT_VIDEO_IF_COLOR_KEY|SELECT_VIDEO3_IF_COLOR_KEY;
+                                break;
+                            default:
+                                /* Overlay source format for V3*/
+                dwCompose = VIDInD(V_COMPOSE_MODE) | SELECT_VIDEO_IF_COLOR_KEY;
+                                break;
+                        }
+                        break;
+                    default:
+                        DBG_DD("Unknown DeviceID\n");
+                        break;
+                }//End of DeviceID
+                                  
+                gdwAlphaEnabled = 0;
+                break;
+        }
+
+        dwControl |= 0x00080000; /* Expire number ;divided by 4*/
+        
+        VIDOutD(V_ALPHA_CONTROL,dwControl);
+        VIDOutD(V_COMPOSE_MODE,dwCompose);
+        DBG_DD("00000210 %08lx\n",VIDInD(V_ALPHA_CONTROL) );
+        DBG_DD("00000220 %08lx\n",VIDInD(V_COMPOSE_MODE) );
+
+    } //end if
+
+
+} //VIAAlphaWin
+
+
+/************************************************************************************************
+*  Function :   To determine V1 is on Screen 0 (V1onScreen1 = 0) or on screen 1 (V1onScreen1 = 1)
+*               and V3 is on screen 0 (V3offScreen0 = 0) or on screen 1 (V3offScreen0 = 1)      
+*               For SAMM mode
+*************************************************************************************************/
+void ScreenSwitchManager( LPDDUPDATEOVERLAY lpUpdate )
+{
+    DBG_DD("// ScreenSwitchManager:\n");
+    
+    if ( (gVIAGraphicInfo.SAMM) && (lpUpdate->rDest.left > gVIAGraphicInfo.Screen[0].dwSaveWidth) 
+          && (lpUpdate->rDest.left < 65535) && !(gVIAGraphicInfo.Screen1IsLeft) )
+    {   // Screen1 RightOf Screen0, V1 or V3 on Screen1
+        lpUpdate->rDest.left = lpUpdate->rDest.left - gVIAGraphicInfo.Screen[0].dwSaveWidth;
+        lpUpdate->rDest.right = lpUpdate->rDest.right - gVIAGraphicInfo.Screen[0].dwSaveWidth;
+            
+        //lpVideoControl->MPEGOnScreen1 = 1;
+        lpVideoControl->VideoStatus |= MPEG_ON_SND;
+        DBG_DD("//Case1\n");
+    }
+    
+    else if ( (gVIAGraphicInfo.SAMM) && (lpUpdate->rDest.top > gVIAGraphicInfo.Screen[0].dwSaveHeight)   
+               && (lpUpdate->rDest.top < 65535) && !(gVIAGraphicInfo.Screen1IsAbove) )
+    {   // Screen1 Below Screen0, V1 or V3 on Screen1
+        lpUpdate->rDest.top = lpUpdate->rDest.top - gVIAGraphicInfo.Screen[0].dwSaveHeight;
+        lpUpdate->rDest.bottom = lpUpdate->rDest.bottom - gVIAGraphicInfo.Screen[0].dwSaveHeight;
+        
+        //lpVideoControl->MPEGOnScreen1 = 1;
+        lpVideoControl->VideoStatus |= MPEG_ON_SND;
+        DBG_DD("//Case2\n");
+    }
+    
+    else if ( (gVIAGraphicInfo.Screen1IsLeft) && 
+             ((lpUpdate->rDest.left < gVIAGraphicInfo.Screen[0].dwSaveWidth) || (lpUpdate->rDest.left > 65535)) )
+    {   // Screen1 LeftOf Screen0, V1 or V3 on Screen1
+        //lpVideoControl->MPEGOnScreen1 = 1;
+        lpVideoControl->VideoStatus |= MPEG_ON_SND;
+        DBG_DD("//Case3\n");
+    }
+    
+    else if ( (gVIAGraphicInfo.Screen1IsLeft) && (lpUpdate->rDest.left > gVIAGraphicInfo.Screen[0].dwSaveWidth) 
+               && (lpUpdate->rDest.left < 65535) )
+    {   // Screen1 LeftOf Screen0, V1 or V3 on Screen0
+        lpUpdate->rDest.left = lpUpdate->rDest.left - gVIAGraphicInfo.Screen[0].dwSaveWidth;
+        lpUpdate->rDest.right = lpUpdate->rDest.right - gVIAGraphicInfo.Screen[0].dwSaveWidth;        
+        
+        //lpVideoControl->MPEGOnScreen1 = 0;
+        lpVideoControl->VideoStatus &= ~MPEG_ON_SND;
+        DBG_DD("//Case4\n");
+    }    
+    
+    else if ( (gVIAGraphicInfo.Screen1IsAbove) && 
+             ((lpUpdate->rDest.top < gVIAGraphicInfo.Screen[0].dwSaveHeight) || (lpUpdate->rDest.top > 65535)) )
+    {   // Screen1 Above Screen0, V1 or V3 on Screen1
+        //lpVideoControl->MPEGOnScreen1 = 1;
+        lpVideoControl->VideoStatus |= MPEG_ON_SND;
+        DBG_DD("//Case5\n");
+    }
+    else if ( (gVIAGraphicInfo.Screen1IsAbove) && (lpUpdate->rDest.top > gVIAGraphicInfo.Screen[0].dwSaveHeight) 
+               && (lpUpdate->rDest.top < 65535) )
+    {   // Screen1 Above Screen0, V1 or V3 on Screen0
+        lpUpdate->rDest.top = lpUpdate->rDest.top - gVIAGraphicInfo.Screen[0].dwSaveHeight;
+        lpUpdate->rDest.bottom = lpUpdate->rDest.bottom - gVIAGraphicInfo.Screen[0].dwSaveHeight;        
+       
+        //lpVideoControl->MPEGOnScreen1 = 0;
+        lpVideoControl->VideoStatus &= ~MPEG_ON_SND;
+        DBG_DD("//Case6\n");
+    }
+    else
+    {   // V1 and V3 on Screen0
+        //lpVideoControl->MPEGOnScreen1 = 0;
+        lpVideoControl->VideoStatus &= ~MPEG_ON_SND;
+        DBG_DD("//Case7\n");
+    }	
+}
+    
+
+
+/*
+ *  UpdateOverlay
+ *  Parameters:   src rectangle, dst rectangle, colorkey...
+ *  Return Value: unsigned long of state
+ *  note: Update the overlay image param.
+ */
+unsigned long UpdateOverlay(LPDDUPDATEOVERLAY lpUpdate)
+{
+    unsigned long dwFlags = lpUpdate->dwFlags;
+    unsigned long dwKeyLow=0, dwKeyHigh=0;
+    unsigned long dwChromaLow=0, dwChromaHigh=0;
+    unsigned long dwVideoFlag=0;
+    unsigned long dwColorKey=0, dwChromaKey=0;
+    //DDUPDATEOVERLAY UpdateOverlayTemp;
+    int   nDstTop, nDstBottom, nDstLeft, nDstRight, nTopBak=0;
+    
+    /*Added for SAMM Mode*/
+    int ScrnIndex = 0;
+
+    //if (UpdateOverlay_count >= 1 )
+    //    return PI_OK;
+    
+    //UpdateOverlay_count++;   
+
+    ScreenSwitchManager(lpUpdate);  
+
+    /*Added for SAMM Mode*/
+    if (dwFlags & DDOVER_ON_SND)
+    {
+        ScrnIndex = 1;
+        lpVideoControl->VideoStatus |= MPEG_ON_SND;
+    }
+    else 
+    {
+        //if (lpVideoControl->MPEGOnScreen1 == 1)
+        if ( lpVideoControl->VideoStatus & MPEG_ON_SND )
+        {
+            ScrnIndex = 1;
+            dwFlags |= DDOVER_ON_SND;
+        }
+    }
+
+    DBG_DD("// UpdateOverlay: %08lx\n", dwFlags);
+    
+    /*Fixed for SAMM panning Mode*/
+    if (gVIAGraphicInfo.Screen[ScrnIndex].dwPanning) 
+    {
+        DBG_DD("// Panning!!\n");
+        lpUpdate->rDest.left = lpUpdate->rDest.left - (panning_x[ScrnIndex] - panning_old_x[ScrnIndex]);
+        lpUpdate->rDest.top = lpUpdate->rDest.top - (panning_y[ScrnIndex] - panning_old_y[ScrnIndex]);
+        lpUpdate->rDest.right = lpUpdate->rDest.right - (panning_x[ScrnIndex] - panning_old_x[ScrnIndex]);
+        lpUpdate->rDest.bottom = lpUpdate->rDest.bottom - (panning_y[ScrnIndex] - panning_old_y[ScrnIndex]);
+    }
+
+    DBG_DD("Raw rSrc  X (%ld,%ld) Y (%ld,%ld)\n",
+                lpUpdate->rSrc.left, lpUpdate->rSrc.right, lpUpdate->rSrc.top, lpUpdate->rSrc.bottom);
+    DBG_DD("Raw rDest  X (%ld,%ld) Y (%ld,%ld)\n",
+                lpUpdate->rDest.left, lpUpdate->rDest.right, lpUpdate->rDest.top, lpUpdate->rDest.bottom);
+
+    if (gdwVideoFlagTV1 && !gdwOverlaySupport)
+        return PI_OK;
+
+    if (lpDPFsrc->dwFourCC == FOURCC_VIA)
+        dwVideoFlag = gdwVideoFlagMPEG;
+
+    if (( lpDPFsrc->dwFourCC == FOURCC_YUY2 )||( lpDPFsrc->dwFourCC == FOURCC_YV12 ))
+        dwVideoFlag = gdwVideoFlagSW;
+
+    dwFlags |= DDOVER_INTERLEAVED;
+
+    // For Alpha windows setting
+    if (gdwAlphaEnabled)
+        dwFlags &= ~DDOVER_KEYDEST;
+
+    Macro_VidREGRec(VIDREGREC_RESET_COUNTER, 0,0);
+
+    if ( dwFlags & DDOVER_HIDE )
+    {
+        DBG_DD("//    :DDOVER_HIDE \n");
+        
+        dwVideoFlag &= ~VIDEO_SHOW;
+
+        if(lpDPFsrc->dwFourCC == FOURCC_VIA)
+        {
+            if (Upd_MPEG(dwVideoFlag,lpUpdate->rSrc,lpUpdate->rDest,0,0,0,lpDPFsrc,0,
+                         0,0,0,0,0,0,dwFlags)== PI_ERR)
+            {
+                return PI_ERR;
+            }
+            
+            MPEG_ON = FALSE;
+        }
+        else
+        {
+            if (Upd_Video(dwVideoFlag,0,lpUpdate->rSrc,lpUpdate->rDest,0,0,0,lpDPFsrc,0,
+                0,0,0,0,0,0, dwFlags)== PI_ERR)
+            {
+                return PI_ERR;                    
+            }
+            SWVideo_ON = FALSE;
+        }
+        UpdateOverlayBackup.rDest.left = 0;
+        UpdateOverlayBackup.rDest.top = 0;
+        UpdateOverlayBackup.rDest.right = 0;
+        UpdateOverlayBackup.rDest.bottom = 0;
+
+        if (gdwUseExtendedFIFO)
+        {
+            //Restore Display fifo
+            outb(0x16, 0x3C4); outb(Save_3C4_16, 0x3C5);
+            DBG_DD("Restore 3c4.16 : %08x \n",inb(0x3C5));
+            outb(0x17, 0x3C4); outb(Save_3C4_17, 0x3C5);
+            DBG_DD("        3c4.17 : %08x \n",inb(0x3C5));
+            outb(0x18, 0x3C4); outb(Save_3C4_18, 0x3C5);
+            DBG_DD("        3c4.18 : %08x \n",inb(0x3C5));
+            gdwUseExtendedFIFO = 0;
+		}
+        return PI_OK;
+    }
+
+    /* If the dest rectangle doesn't change, we can return directly */
+    /*
+    if ( (UpdateOverlayBackup.rDest.left ==  lpUpdate->rDest.left) &&
+         (UpdateOverlayBackup.rDest.top ==  lpUpdate->rDest.top) &&
+         (UpdateOverlayBackup.rDest.right ==  lpUpdate->rDest.right) &&
+         (UpdateOverlayBackup.rDest.bottom ==  lpUpdate->rDest.bottom) )
+        return PI_OK;
+    */
+    UpdateOverlayBackup = * (LPDDUPDATEOVERLAY) lpUpdate;
+
+    if ( dwFlags & DDOVER_KEYDEST )
+    {
+        DBG_DD("//    :DDOVER_KEYDEST \n");
+        
+        dwColorKey = 1;
+        dwKeyLow = lpUpdate->dwColorSpaceLowValue;
+    }
+
+    if (dwFlags & DDOVER_SHOW)    
+    {
+        unsigned long dwStartAddr=0, dwDeinterlaceMode=0;
+        unsigned long dwScnWidth, dwScnHeight;
+
+        DBG_DD("//    :DDOVER_SHOW \n");
+
+        //for SW decode HW overlay use
+        dwStartAddr = VIDInD(HQV_SRC_STARTADDR_Y);
+        DBG_DD("dwStartAddr= 0x%lx\n", dwStartAddr);
+
+        if (dwFlags & DDOVER_INTERLEAVED)
+        {
+            dwDeinterlaceMode |= DDOVER_INTERLEAVED;
+            DBG_DD("DDOVER_INTERLEAVED\n");
+        }
+        if (dwFlags & DDOVER_BOB)
+        {
+            dwDeinterlaceMode |= DDOVER_BOB;
+            DBG_DD("DDOVER_BOB\n");
+        }
+
+        if ( (gVIAGraphicInfo.Screen[0].dwWidth > 1024) || (gVIAGraphicInfo.SAMM) )
+		{
+            DBG_DD("UseExtendedFIFO\n");
+			gdwUseExtendedFIFO = 1;
+		}
+		/*
+		else
+		{
+	        //Set Display FIFO
+	        outb(0x16, 0x3C4); outb((Save_3C4_16&0xf0)|0x0c, 0x3C5);
+	        DBG_DD("set     3c4.16 : %08x \n",inb(0x3C5));
+	        outb(0x18, 0x3C4); outb(0x4c, 0x3C5);
+	        DBG_DD("        3c4.18 : %08x \n",inb(0x3C5));
+		}
+        */
+        dwVideoFlag |= VIDEO_SHOW;
+
+
+        //
+        // Figure out actual rSrc rectangle
+        // Coz the Src rectangle AP sent is always original, ex:size(720,480) at (0,0)
+        // so the driver need to re-calc
+        // 
+        // transfer unsigned long to signed int for calc
+        nDstLeft = lpUpdate->rDest.left;
+        nDstTop  = lpUpdate->rDest.top;
+        nDstRight= lpUpdate->rDest.right;
+        nDstBottom=lpUpdate->rDest.bottom;
+
+        dwScnWidth  = gVIAGraphicInfo.Screen[ScrnIndex].dwWidth;
+        dwScnHeight = gVIAGraphicInfo.Screen[ScrnIndex].dwHeight;
+
+        if (nDstLeft<0)
+        {
+            //lpUpdate->rSrc.left  += (((-nDstLeft) * overlayRecordV1.dwV1OriWidth) + ((nDstRight-nDstLeft)>>1)) / (nDstRight-nDstLeft);
+            lpUpdate->rSrc.left  += (((-nDstLeft) * (lpUpdate->rSrc.right-lpUpdate->rSrc.left)) + ((nDstRight-nDstLeft)>>1)) / (nDstRight-nDstLeft);
+        }
+
+        if (nDstRight>dwScnWidth)
+        {
+            lpUpdate->rSrc.right -= (((nDstRight-dwScnWidth) * (lpUpdate->rSrc.right-lpUpdate->rSrc.left)) + ((nDstRight-nDstLeft)>>1)) / (nDstRight-nDstLeft);
+        }
+
+        if (nDstTop<0)
+        {
+           lpUpdate->rSrc.top   +=  (((-nDstTop) * (lpUpdate->rSrc.bottom-lpUpdate->rSrc.top)) + ((nDstBottom-nDstTop)>>1))/ (nDstBottom-nDstTop);
+           nTopBak = (-nDstTop);
+        }
+
+        if (nDstBottom >dwScnHeight)
+        {
+            lpUpdate->rSrc.bottom -= (((nDstBottom-dwScnHeight) * (lpUpdate->rSrc.bottom-lpUpdate->rSrc.top)) + ((nDstBottom-nDstTop)>>1)) / (nDstBottom-nDstTop);
+        }
+        
+        
+        // save modified src & original dest rectangle param.
+        if (( lpDPFsrc->dwFourCC == FOURCC_YUY2 )||( lpDPFsrc->dwFourCC == FOURCC_YV12 ))
+        {
+            if ( gVIAGraphicInfo.Screen[ScrnIndex].dwPanning )
+            {
+                SWDevice.gdwSWDstLeft     = lpUpdate->rDest.left + (panning_x[ScrnIndex] - panning_old_x[ScrnIndex]);
+                SWDevice.gdwSWDstTop      = lpUpdate->rDest.top + (panning_y[ScrnIndex] - panning_old_y[ScrnIndex]);
+            }
+            else
+            {
+                SWDevice.gdwSWDstLeft     = lpUpdate->rDest.left;
+                SWDevice.gdwSWDstTop      = lpUpdate->rDest.top;
+            }
+            
+            SWDevice.gdwSWDstWidth    = lpUpdate->rDest.right - lpUpdate->rDest.left;
+            SWDevice.gdwSWDstHeight   = lpUpdate->rDest.bottom - lpUpdate->rDest.top;
+
+            SWDevice.gdwSWSrcWidth    = overlayRecordV1.dwV1SrcWidth = lpUpdate->rSrc.right - lpUpdate->rSrc.left;
+            SWDevice.gdwSWSrcHeight   = overlayRecordV1.dwV1SrcHeight = lpUpdate->rSrc.bottom - lpUpdate->rSrc.top;
+        }
+
+        overlayRecordV1.dwV1SrcLeft   = lpUpdate->rSrc.left;
+        overlayRecordV1.dwV1SrcRight  = lpUpdate->rSrc.right;
+        overlayRecordV1.dwV1SrcTop    = lpUpdate->rSrc.top;
+        overlayRecordV1.dwV1SrcBot    = lpUpdate->rSrc.bottom;
+        
+        //
+        // Figure out actual rDest rectangle
+        //
+        lpUpdate->rDest.left= nDstLeft<0 ? 0 : nDstLeft;
+        lpUpdate->rDest.top= nDstTop<0 ? 0 : nDstTop;
+        if ( lpUpdate->rDest.top >= dwScnHeight)
+           lpUpdate->rDest.top = dwScnHeight-1;
+        //lpUpdate->rDest.top= top>=dwScnHeight   ? dwScnHeight-1: top;
+        lpUpdate->rDest.right= nDstRight>dwScnWidth ? dwScnWidth: nDstRight;
+        lpUpdate->rDest.bottom= nDstBottom>dwScnHeight ? dwScnHeight: nDstBottom;
+
+        //check which update func. (upd_MPEG, upd_video, upd_capture) to call
+        if(lpDPFsrc->dwFourCC == FOURCC_VIA)
+        {
+            //if ( (lpVideoControl->Cap0OnScreen1 == 1) && (lpVideoControl->MPEGOnScreen1 == 0) ) 
+            if ( (lpVideoControl->VideoStatus & CAP0_ON_SND) && !(lpVideoControl->VideoStatus & MPEG_ON_SND) ) 
+            {
+                dwVideoFlag = dwVideoFlag & ~VIDEO_1_INUSE;
+                dwVideoFlag = dwVideoFlag | VIDEO_3_INUSE;  
+                //dwVideoFlag = dwVideoFlag & ~VIDEO_HQV_INUSE;
+            }
+
+            if (Upd_MPEG(dwVideoFlag,lpUpdate->rSrc,lpUpdate->rDest,MPGDevice.dwPitch,
+                         overlayRecordV1.dwV1OriWidth,overlayRecordV1.dwV1OriHeight,lpDPFsrc,
+                         dwDeinterlaceMode,dwColorKey,dwChromaKey,
+                         dwKeyLow,dwKeyHigh,dwChromaLow,dwChromaHigh, dwFlags)== PI_ERR)
+            {
+                return PI_ERR;
+            }                
+            
+            MPEG_ON = TRUE;
+        }
+        else
+        {
+            if (Upd_Video(dwVideoFlag,dwStartAddr,lpUpdate->rSrc,lpUpdate->rDest,SWDevice.dwPitch,
+             overlayRecordV1.dwV1OriWidth,overlayRecordV1.dwV1OriHeight,lpDPFsrc,
+             dwDeinterlaceMode,dwColorKey,dwChromaKey,
+             dwKeyLow,dwKeyHigh,dwChromaLow,dwChromaHigh, dwFlags)== PI_ERR)
+             {
+                 return PI_ERR;                    
+             }                
+            SWVideo_ON = FALSE;
+        }
+
+        return PI_OK;
+        
+    } //end of DDOVER_SHOW
+
+    panning_old_x[ScrnIndex] = panning_x[ScrnIndex];
+    panning_old_y[ScrnIndex] = panning_y[ScrnIndex];
+
+    return PI_OK;
+
+} //UpdateOverlay
+
+
+/****************************************************************************
+ *
+ * Upd_Video()
+ *
+ ***************************************************************************/
+unsigned long Upd_Video(unsigned long dwVideoFlag,unsigned long dwStartAddr,RECTL rSrc,RECTL rDest,unsigned long dwSrcPitch,
+                 unsigned long dwOriSrcWidth,unsigned long dwOriSrcHeight,LPDDPIXELFORMAT lpDPFsrc,
+                 unsigned long dwDeinterlaceMode,unsigned long dwColorKey,unsigned long dwChromaKey,
+                 unsigned long dwKeyLow,unsigned long dwKeyHigh,unsigned long dwChromaLow,unsigned long dwChromaHigh, unsigned long dwFlags)
+{
+    //unsigned long dwVidCtl=0, dwCompose=(VIDInD(V_COMPOSE_MODE)&~(SELECT_VIDEO_IF_COLOR_KEY|V1_COMMAND_FIRE|V3_COMMAND_FIRE))|V_COMMAND_LOAD_VBI;
+    unsigned long dwVidCtl=0, dwCompose=(VIDInD(V_COMPOSE_MODE)&~(SELECT_VIDEO_IF_COLOR_KEY|V1_COMMAND_FIRE|V3_COMMAND_FIRE));
+    unsigned long srcWidth, srcHeight,dstWidth,dstHeight;
+    unsigned long zoomCtl=0, miniCtl=0;
+    unsigned long dwHQVCtl=0;
+    unsigned long dwHQVfilterCtl=0,dwHQVminiCtl=0;
+    unsigned long dwHQVzoomflagH=0,dwHQVzoomflagV=0;
+    unsigned long dwHQVsrcWidth=0,dwHQVdstWidth=0;
+    unsigned long dwHQVsrcFetch = 0,dwHQVoffset=0;
+    unsigned long dwOffset=0,dwFetch=0,dwTmp=0;
+    unsigned long dwDisplayCountW=0;
+    LPVIDHWDIFFERENCE lpVideoHWDifference = &VideoHWDifference;
+    
+    /*Added for SAMM expand Mode*/
+    unsigned long dstModifiedWidth=0,dstModifiedHeight=0;
+
+    /*Added for SAMM Mode*/
+    int ScrnIndex = 0;
+    if (dwFlags & DDOVER_ON_SND)
+    {
+        ScrnIndex = 1;
+    }
+    DBG_DD("ScrnIndex=%d\n",ScrnIndex);
+        
+    /* 2003/10/06 Fix bug */
+    /* If Capture1 (or Capture0) has no video decoder(ex:SAA7113,SAA8108...) */
+    /* then run XawTV ./tv1 (or ./tv0), the system will hang */
+        if (dwVideoFlag & VIDEO_1_INUSE)
+        {
+        dwCompose |= V_COMMAND_LOAD_VBI;
+    }
+    else
+    {
+        if (gVIAGraphicInfo.RevisionID >= VIA_REVISION_CLECX)
+        {
+            dwCompose |= V3_COMMAND_LOAD_VBI;
+        }
+    }
+    
+    DBG_DD("// Upd_Video:\n");
+    DBG_DD("Modified rSrc  X (%ld,%ld) Y (%ld,%ld)\n",
+                rSrc.left, rSrc.right,rSrc.top, rSrc.bottom);
+    DBG_DD("Modified rDest  X (%ld,%ld) Y (%ld,%ld)\n",
+                rDest.left, rDest.right,rDest.top, rDest.bottom);
+    
+    if (dwVideoFlag & VIDEO_SHOW)    
+    {
+        overlayRecordV1.dwWidth=dstWidth = rDest.right - rDest.left;
+        overlayRecordV1.dwHeight=dstHeight = rDest.bottom - rDest.top;
+        srcWidth = (unsigned long)rSrc.right - rSrc.left;
+        srcHeight = (unsigned long)rSrc.bottom - rSrc.top;
+        DBG_DD("===srcWidth= %ld \n", srcWidth);
+        DBG_DD("===srcHeight= %ld \n", srcHeight);
+        
+        /*Added for SAMM expand Mode*/
+        /*In SAMM expand, we need adjust x and y position, width and height zoom factor.*/
+        if  ( ((gVIAGraphicInfo.Screen[ScrnIndex].dwDVIOn)||(gVIAGraphicInfo.Screen[ScrnIndex].dwLCDOn))
+              &&(gVIAGraphicInfo.Screen[ScrnIndex].dwExpand) )
+        {
+            dstModifiedWidth=dstWidth*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelWidth)/
+                             (gVIAGraphicInfo.Screen[ScrnIndex].dwWidth)+1;
+            dstModifiedHeight=dstHeight*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelHeight)/
+                              (gVIAGraphicInfo.Screen[ScrnIndex].dwHeight)+1;
+            DBG_DD("===Expand!! \n");
+        }
+        else
+        {
+            dstModifiedWidth=dstWidth;
+            dstModifiedHeight=dstHeight;
+        }
+        DBG_DD("===dstModifiedWidth= %ld \n", dstModifiedWidth);
+        DBG_DD("===dstModifiedHeight= %ld \n", dstModifiedHeight);
+        
+
+        if (dwVideoFlag & VIDEO_1_INUSE)
+        {
+            // Overlay source format for V1
+            
+            /*=* Modify for C1 FIFO *=*/
+            switch ( DispatchVGARevisionID() )
+            {
+            	case VIA_REVISION_CLECX :
+                    dwVidCtl = (V1_ENABLE|V1_EXPIRE_NUM_F);
+                    break;
+                    
+                default:
+                    if (gdwUseExtendedFIFO)
+                    {
+                        dwVidCtl = (V1_ENABLE|V1_EXPIRE_NUM_A|V1_FIFO_EXTENDED);
+                    }
+                    else
+                    {
+                    dwVidCtl = (V1_ENABLE|V1_EXPIRE_NUM);
+                    }
+                    break;
+            }
+            
+            DDOver_GetV1Format(dwVideoFlag,lpDPFsrc,&dwVidCtl,&dwHQVCtl);
+        }
+        else
+        {
+            switch ( gVIAGraphicInfo.dwDeviceID )
+            {
+                case VIA_DEVICE_VT3205:
+                    dwVidCtl = (V3_ENABLE|V3_EXPIRE_NUM_3205);
+                    break;
+                case VIA_DEVICE_CLE1:
+                case VIA_DEVICE_CLE2:
+            switch ( DispatchVGARevisionID() )
+            {
+                case VIA_REVISION_CLECX :
+                    dwVidCtl = (V3_ENABLE|V3_EXPIRE_NUM_F);
+                    break;
+                default:
+                            /* Overlay source format for V3*/
+                    dwVidCtl = (V3_ENABLE|V3_EXPIRE_NUM);
+                    break;
+            }
+                    break;
+                default:
+                    DBG_DD("Unknown DeviceID\n");
+                    break;
+            }//End of DeviceID
+
+            DDOver_GetV3Format(dwVideoFlag,lpDPFsrc,&dwVidCtl,&dwHQVCtl);            
+        }
+        
+        if ( lpVideoHWDifference->dwThreeHQVBuffer )    //CLE_C0
+        {
+            //HQV support 3 HQV buffer       
+            dwHQVCtl &= ~HQV_SW_FLIP;
+            dwHQVCtl |= HQV_TRIPLE_BUFF | HQV_FLIP_STATUS; 
+        }
+        
+        // Starting address of source and Source offset
+        dwOffset = DDOver_GetSrcStartAddress (dwVideoFlag,rSrc,rDest,dwSrcPitch,lpDPFsrc,&dwHQVoffset );
+        DBG_DD("===dwOffset= 0x%lx \n", dwOffset);
+        
+        overlayRecordV1.dwOffset = dwOffset;
+
+        if (lpDPFsrc->dwFourCC == FOURCC_YV12)
+        {
+            YCBCRREC YCbCr;
+            if (dwVideoFlag & VIDEO_HQV_INUSE)    
+            {
+                dwHQVsrcWidth=(unsigned long)rSrc.right - rSrc.left;
+                dwHQVdstWidth=(unsigned long)rDest.right - rDest.left;
+                /*if (dwHQVsrcWidth>dwHQVdstWidth)
+                {
+                    dwOffset = dwOffset * dwHQVdstWidth / dwHQVsrcWidth;
+                }*/
+                    
+                if (dwVideoFlag & VIDEO_1_INUSE)
+                    {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_0, overlayRecordV1.dwHQVAddr[0]+dwOffset);
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_1, overlayRecordV1.dwHQVAddr[1]+dwOffset);
+                    
+                    if ( lpVideoHWDifference->dwThreeHQVBuffer )    //CLE_C0
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_2, overlayRecordV1.dwHQVAddr[2]+dwOffset);  
+                }
+                else
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_STARTADDR_0, overlayRecordV1.dwHQVAddr[0]+dwOffset);                    
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_STARTADDR_1, overlayRecordV1.dwHQVAddr[1]+dwOffset);
+                    
+                    if ( lpVideoHWDifference->dwThreeHQVBuffer )    //CLE_C0
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_STARTADDR_2, overlayRecordV1.dwHQVAddr[2]+dwOffset); 
+                    }
+                YCbCr = DDOVer_GetYCbCrStartAddress(dwVideoFlag,dwStartAddr,overlayRecordV1.dwOffset,overlayRecordV1.dwUVoffset,dwSrcPitch,dwOriSrcHeight);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, HQV_SRC_STARTADDR_Y, YCbCr.dwY);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, HQV_SRC_STARTADDR_U, YCbCr.dwCR);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, HQV_SRC_STARTADDR_V, YCbCr.dwCB);
+                }
+            else
+            {
+                YCbCr = DDOVer_GetYCbCrStartAddress(dwVideoFlag,dwStartAddr,overlayRecordV1.dwOffset,overlayRecordV1.dwUVoffset,dwSrcPitch,dwOriSrcHeight);
+                if (dwVideoFlag & VIDEO_1_INUSE)
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_0, YCbCr.dwY);
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_CB0, YCbCr.dwCR);
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_CR0, YCbCr.dwCB);
+            }
+            else
+                {
+                    DBG_DD("Upd_Video() : We do not support YV12 with V3!\n");
+			}
+        }
+        }
+        else
+        {
+            if (dwVideoFlag & VIDEO_HQV_INUSE)    
+                {
+                dwHQVsrcWidth=(unsigned long)rSrc.right - rSrc.left;
+                dwHQVdstWidth=(unsigned long)rDest.right - rDest.left;
+                if (dwHQVsrcWidth>dwHQVdstWidth)
+	{
+                    dwOffset = dwOffset * dwHQVdstWidth / dwHQVsrcWidth;
+	}
+			
+                if (dwVideoFlag & VIDEO_1_INUSE)
+            {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_0, overlayRecordV1.dwHQVAddr[0]+dwHQVoffset);
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_1, overlayRecordV1.dwHQVAddr[1]+dwHQVoffset);
+
+                    if ( lpVideoHWDifference->dwThreeHQVBuffer )    //CLE_C0
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_2, overlayRecordV1.dwHQVAddr[2]+dwHQVoffset);
+                }
+                else
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_STARTADDR_0, overlayRecordV1.dwHQVAddr[0]+dwHQVoffset);
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_STARTADDR_1, overlayRecordV1.dwHQVAddr[1]+dwHQVoffset);                    
+
+                    if ( lpVideoHWDifference->dwThreeHQVBuffer )    //CLE_C0
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_STARTADDR_2, overlayRecordV1.dwHQVAddr[2]+dwHQVoffset);
+                    }
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, HQV_SRC_STARTADDR_Y, dwStartAddr);
+                }
+                else
+                {
+                dwStartAddr += dwOffset;
+
+                if (dwVideoFlag & VIDEO_1_INUSE)
+                    {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STARTADDR_0, dwStartAddr);
+            }
+            else
+            {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_STARTADDR_0, dwStartAddr);                    
+                }
+            }
+        }
+
+        /*Fixed for SAMM expand Mode*/
+        /*dwFetch = DDOver_GetFetch(dwVideoFlag,lpDPFsrc,srcWidth,dstWidth,dwOriSrcWidth,&dwHQVsrcFetch);*/
+        dwFetch = DDOver_GetFetch(dwVideoFlag,lpDPFsrc,srcWidth,dstModifiedWidth,dwOriSrcWidth,&dwHQVsrcFetch);
+        DBG_DD("===dwFetch= 0x%lx \n", dwFetch);
+/*
+        //For DCT450 test-BOB INTERLEAVE
+        if ( (dwDeinterlaceMode & DDOVER_INTERLEAVED) && (dwDeinterlaceMode & DDOVER_BOB ) )
+        {
+            if (dwVideoFlag & VIDEO_HQV_INUSE)    
+            {
+                dwHQVCtl |= HQV_FIELD_2_FRAME|HQV_FRAME_2_FIELD|HQV_DEINTERLACE;                   
+                }
+				else
+            {
+                dwVidCtl |= (V1_BOB_ENABLE | V1_FRAME_BASE);
+				}
+            }
+        else if (dwDeinterlaceMode & DDOVER_BOB )
+            {
+            if (dwVideoFlag & VIDEO_HQV_INUSE)
+                {
+                //The HQV source data line count should be two times of the original line count
+                dwHQVCtl |= HQV_FIELD_2_FRAME|HQV_DEINTERLACE;
+                }
+                else
+                {
+                dwVidCtl |= V1_BOB_ENABLE;                
+                }
+        }
+*/
+        if (dwVideoFlag & VIDEO_HQV_INUSE)
+                {
+            if ( !(dwDeinterlaceMode & DDOVER_INTERLEAVED) && (dwDeinterlaceMode & DDOVER_BOB ) )
+            {
+                if ( lpVideoHWDifference->dwHQVFetchByteUnit )     // CLE_C0
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, HQV_SRC_FETCH_LINE, (((dwHQVsrcFetch)-1)<<16)|((dwOriSrcHeight<<1)-1)); 
+                else
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, HQV_SRC_FETCH_LINE, (((dwHQVsrcFetch>>3)-1)<<16)|((dwOriSrcHeight<<1)-1)); 
+                }
+                else
+                {
+                if ( lpVideoHWDifference->dwHQVFetchByteUnit )     // CLE_C0
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, HQV_SRC_FETCH_LINE, (((dwHQVsrcFetch)-1)<<16)|(dwOriSrcHeight-1));
+                else
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, HQV_SRC_FETCH_LINE, (((dwHQVsrcFetch>>3)-1)<<16)|(dwOriSrcHeight-1));
+                }
+            if (lpDPFsrc->dwFourCC == FOURCC_YV12)
+            {
+                if (dwVideoFlag & VIDEO_1_INUSE)
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STRIDE, dwSrcPitch<<1);
+            }
+                else
+            {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_STRIDE, dwSrcPitch<<1);
+            }
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, HQV_SRC_STRIDE, ((dwSrcPitch>>1)<<16)|dwSrcPitch);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, HQV_DST_STRIDE, (dwSrcPitch<<1));
+        }
+            else
+            {
+                if (dwVideoFlag & VIDEO_1_INUSE)
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STRIDE, dwSrcPitch);
+                }
+                else
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_STRIDE, dwSrcPitch);
+                }
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, HQV_SRC_STRIDE, dwSrcPitch);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, HQV_DST_STRIDE, dwSrcPitch);
+                }
+
+            }
+            else
+            {
+            if (dwVideoFlag & VIDEO_1_INUSE)
+                {
+//                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STRIDE, dwSrcPitch | (dwSrcPitch <<15) );
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_STRIDE, dwSrcPitch );
+                }
+                else
+                {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_STRIDE, dwSrcPitch | (dwSrcPitch <<15) );                
+            }
+        }
+
+        DBG_DD("rSrc  X (%ld,%ld) Y (%ld,%ld)\n",
+                rSrc.left, rSrc.right,rSrc.top, rSrc.bottom);
+        DBG_DD("rDest  X (%ld,%ld) Y (%ld,%ld)\n",
+                rDest.left, rDest.right,rDest.top, rDest.bottom);
+
+        // Destination window key
+
+        if (dwVideoFlag & VIDEO_1_INUSE)    
+        {
+            //modify for HW DVI limitation,
+            //When we enable the CRT and DVI both, then change resolution.
+            //If the resolution small than the panel physical size, the video display in Y direction will be cut.
+            //So, we need to adjust the Y top and bottom position.                                   
+
+            //Fixed for SAMM expand Mode
+            if  ( ((gVIAGraphicInfo.Screen[ScrnIndex].dwDVIOn)||(gVIAGraphicInfo.Screen[ScrnIndex].dwLCDOn))
+                  &&(gVIAGraphicInfo.Screen[ScrnIndex].dwExpand) )
+		{
+                 Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_WIN_END_Y,
+                                 (((rDest.right-1)*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelWidth)/
+                                  (gVIAGraphicInfo.Screen[ScrnIndex].dwWidth)) <<16) +
+                                 (rDest.bottom*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelHeight)/
+                                  (gVIAGraphicInfo.Screen[ScrnIndex].dwHeight)) );                             
+
+                 if (rDest.top > 0)
+                 {
+                     Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_WIN_START_Y,
+                                      ((rDest.left*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelWidth)/
+                                       (gVIAGraphicInfo.Screen[ScrnIndex].dwWidth)) <<16 ) + 
+                                      (rDest.top*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelHeight)/
+                                       (gVIAGraphicInfo.Screen[ScrnIndex].dwHeight)) );
+			}
+			else
+                 {
+                      Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_WIN_START_Y,
+                                      ((rDest.left*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelWidth)/
+                                      (gVIAGraphicInfo.Screen[ScrnIndex].dwWidth)) <<16) );
+			}
+		}
+		else
+		{
+                 Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_WIN_END_Y, ((rDest.right-1)<<16) + (rDest.bottom-1));
+                 if (rDest.top > 0)
+			{
+                     Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_WIN_START_Y, (rDest.left<<16) + rDest.top );
+			}
+			else
+			{
+                     Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_WIN_START_Y, (rDest.left<<16));
+			}
+		}
+		}
+		else
+		{
+            //Fixed for SAMM expand Mode
+            if  ( ((gVIAGraphicInfo.Screen[ScrnIndex].dwDVIOn)||(gVIAGraphicInfo.Screen[ScrnIndex].dwLCDOn))
+                  &&(gVIAGraphicInfo.Screen[ScrnIndex].dwExpand) )
+            {
+                 Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_WIN_END_Y,
+                                 (((rDest.right-1)*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelWidth)/
+                                  (gVIAGraphicInfo.Screen[ScrnIndex].dwWidth)) <<16) +
+                                 (rDest.bottom*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelHeight)/
+                                  (gVIAGraphicInfo.Screen[ScrnIndex].dwHeight)) );         
+
+                 if (rDest.top > 0)
+			{
+                      Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_WIN_START_Y,
+                                      ((rDest.left*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelWidth)/
+                                       (gVIAGraphicInfo.Screen[ScrnIndex].dwWidth)) <<16 ) + 
+                                      (rDest.top*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelHeight)/
+                                       (gVIAGraphicInfo.Screen[ScrnIndex].dwHeight)) );
+                 }
+				else
+				{
+                      Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_WIN_START_Y,
+                                      ((rDest.left*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelWidth)/
+                                      (gVIAGraphicInfo.Screen[ScrnIndex].dwWidth)) <<16) );
+			}
+		}
+		else
+		{
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_WIN_END_Y, ((rDest.right-1)<<16) + (rDest.bottom-1));
+                if (rDest.top > 0)
+			{
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_WIN_START_Y, (rDest.left<<16) + rDest.top );
+                }
+				else
+				{
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_WIN_START_Y, (rDest.left<<16));
+				}
+			}
+		}
+
+        dwCompose |= ALWAYS_SELECT_VIDEO;
+
+
+        // Setup X zoom factor
+        overlayRecordV1.dwFetchAlignment = 0;
+
+        /*Fixed for SAMM expand Mode*/
+        /*if ( DDOVER_HQVCalcZoomWidth(dwVideoFlag, srcWidth , dstWidth,
+                                  &zoomCtl, &miniCtl, &dwHQVfilterCtl, &dwHQVminiCtl,&dwHQVzoomflagH) == PI_ERR )*/
+        if ( DDOVER_HQVCalcZoomWidth(dwVideoFlag, srcWidth , dstModifiedWidth,
+                                  &zoomCtl, &miniCtl, &dwHQVfilterCtl, &dwHQVminiCtl,&dwHQVzoomflagH) == PI_ERR )
+		{
+            // too small to handle
+            dwFetch <<= 20;
+            if (dwVideoFlag & VIDEO_1_INUSE)    
+			{
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V12_QWORD_PER_LINE, dwFetch);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_COMPOSE_MODE , dwCompose|V1_COMMAND_FIRE );
+			}
+			else
+			{
+                dwFetch |=(VIDInD(V3_ALPHA_QWORD_PER_LINE)&(~V3_FETCH_COUNT));
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_ALPHA_QWORD_PER_LINE, dwFetch);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_COMPOSE_MODE , dwCompose|V3_COMMAND_FIRE );
+                
+			}
+			Macro_VidREGFlush();
+			return PI_ERR;
+		}
+
+        dwFetch <<= 20;
+        if (dwVideoFlag & VIDEO_1_INUSE)    
+        {
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V12_QWORD_PER_LINE, dwFetch);
+        }
+        else
+        {
+            dwFetch |=(VIDInD(V3_ALPHA_QWORD_PER_LINE)&(~V3_FETCH_COUNT));
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V3_ALPHA_QWORD_PER_LINE, dwFetch);
+        }
+
+        //
+        // Setup Y zoom factor
+        //
+
+        //For DCT450 test-BOB INTERLEAVE
+        if ( (dwDeinterlaceMode & DDOVER_INTERLEAVED) && (dwDeinterlaceMode & DDOVER_BOB))
+		{
+            if (!(dwVideoFlag & VIDEO_HQV_INUSE))
+			{
+                srcHeight /=2;
+                if (dwVideoFlag & VIDEO_1_INUSE)    
+				{
+                    dwVidCtl |= (V1_BOB_ENABLE | V1_FRAME_BASE);
+                }
+					else
+                {
+                    dwVidCtl |= (V3_BOB_ENABLE | V3_FRAME_BASE);                    
+				}
+		}
+            else
+				{
+                dwHQVCtl |= HQV_FIELD_2_FRAME|HQV_FRAME_2_FIELD|HQV_DEINTERLACE;                 
+				}
+			}
+        else if (dwDeinterlaceMode & DDOVER_BOB )
+        {
+            if (dwVideoFlag & VIDEO_HQV_INUSE)
+            {
+                srcHeight <<=1;
+                dwHQVCtl |= HQV_FIELD_2_FRAME|HQV_DEINTERLACE;
+		}
+		else
+		{
+                if (dwVideoFlag & VIDEO_1_INUSE)    
+				{
+                    dwVidCtl |= V1_BOB_ENABLE;                
+				}
+				else
+				{
+                    dwVidCtl |= V3_BOB_ENABLE;                    
+				}
+			}
+					}
+
+        DDOver_GetDisplayCount(dwVideoFlag,lpDPFsrc,srcWidth,&dwDisplayCountW);
+        
+        if (dwVideoFlag & VIDEO_1_INUSE) 
+        {
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V1_SOURCE_HEIGHT, (srcHeight<<16)|dwDisplayCountW);
+			}
+				else
+				{
+            if (lpVideoHWDifference->dwV3SrcHeightSetting == VID_HWDIFF_TRUE)
+					{
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_SOURCE_WIDTH, (srcHeight<<16)|dwDisplayCountW);    
+				}
+            else
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_SOURCE_WIDTH, dwDisplayCountW);    
+			}
+	}
+        
+        /*Fixed for SAMM expand Mode*/
+        /*if ( DDOVER_HQVCalcZoomHeight(srcHeight,dstHeight,&zoomCtl,&miniCtl, &dwHQVfilterCtl, &dwHQVminiCtl ,&dwHQVzoomflagV) == PI_ERR )*/
+        if ( DDOVER_HQVCalcZoomHeight(srcHeight,dstModifiedHeight,&zoomCtl,&miniCtl, &dwHQVfilterCtl, &dwHQVminiCtl ,&dwHQVzoomflagV) == PI_ERR )        
+		{
+            if (dwVideoFlag & VIDEO_1_INUSE)    
+			{
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_COMPOSE_MODE , dwCompose|V1_COMMAND_FIRE );
+				}
+				else
+				{
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_COMPOSE_MODE , dwCompose|V3_COMMAND_FIRE );                
+			}
+            
+            Macro_VidREGFlush();
+            return PI_ERR;
+		}
+
+        if (miniCtl & V1_Y_INTERPOLY)
+			{
+            if (lpDPFsrc->dwFourCC == FOURCC_YV12)
+            {
+                if (dwVideoFlag & VIDEO_HQV_INUSE)
+                {
+                    if (dwVideoFlag & VIDEO_1_INUSE)    
+                    {
+                        /*=* Modify for C1 FIFO *=*/
+                        switch ( DispatchVGARevisionID() )
+                    {
+            	            case VIA_REVISION_CLECX :
+                                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_FIFO_CONTROL,
+                                    V1_FIFO_DEPTH64 | V1_FIFO_PRETHRESHOLD56 | V1_FIFO_THRESHOLD56);
+                                break;
+                                
+                            default:
+                                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_FIFO_CONTROL,
+                                    V1_FIFO_DEPTH32 | V1_FIFO_PRETHRESHOLD29 | V1_FIFO_THRESHOLD16);
+                                break;
+                }
+            }
+            else
+            {
+                        switch ( gVIAGraphicInfo.dwDeviceID )
+                {
+                            case VIA_DEVICE_VT3205:
+                                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_FIFO_CONTROL,
+                                    (VIDInD(ALPHA_V3_FIFO_CONTROL)&ALPHA_FIFO_MASK)|V3_FIFO_DEPTH32 | V3_FIFO_THRESHOLD29);
+                                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_PREFIFO_CONTROL ,V3_FIFO_PRETHRESHOLD29 |
+                                    ( VIDInD(ALPHA_V3_PREFIFO_CONTROL)& (~V3_FIFO_MASK)) );
+                                break;
+                            case VIA_DEVICE_CLE1:
+                            case VIA_DEVICE_CLE2:
+                                switch ( DispatchVGARevisionID() )
+                {
+                      	            case VIA_REVISION_CLECX :
+                                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_FIFO_CONTROL,
+                                            (VIDInD(ALPHA_V3_FIFO_CONTROL)&ALPHA_FIFO_MASK)|V3_FIFO_DEPTH64 | V3_FIFO_THRESHOLD56);                        
+                                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_PREFIFO_CONTROL ,V3_FIFO_PRETHRESHOLD56 |
+                                            ( VIDInD(ALPHA_V3_PREFIFO_CONTROL)& (~V3_FIFO_MASK)) );
+                                        break;
+                                         
+                                    default:
+                                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_FIFO_CONTROL,
+                                            (VIDInD(ALPHA_V3_FIFO_CONTROL)&ALPHA_FIFO_MASK)|V3_FIFO_DEPTH32 | V3_FIFO_THRESHOLD16);                        
+                                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_PREFIFO_CONTROL ,(V3_FIFO_THRESHOLD16>>8) |
+                                            ( VIDInD(ALPHA_V3_PREFIFO_CONTROL)& (~V3_FIFO_MASK)) );
+                                        break;
+                }
+                                break;
+                            default:
+                                DBG_DD("Unknown DeviceID\n");
+                                break;
+                        }/*End of DeviceID*/           
+					}                    
+                }
+                else
+                {
+                    //Minified Video will be skewed if not work around
+                    if (srcWidth <= 80) //Fetch count <= 5
+                {
+                        if (dwVideoFlag & VIDEO_1_INUSE)    
+                        {
+                            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_FIFO_CONTROL,V1_FIFO_DEPTH16 );                            
+                }
+                else
+                {
+                            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_FIFO_CONTROL,
+                                (VIDInD(ALPHA_V3_FIFO_CONTROL)&ALPHA_FIFO_MASK)|V3_FIFO_DEPTH16 );                            
+                            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_PREFIFO_CONTROL ,(V3_FIFO_THRESHOLD16>>8) |
+                                ( VIDInD(ALPHA_V3_PREFIFO_CONTROL)& (~V3_FIFO_MASK)) );
+            }
+		}
+		else
+            {
+                        if (dwVideoFlag & VIDEO_1_INUSE)    
+            {
+                            /*=* Modify for C1 FIFO *=*/
+                            switch ( DispatchVGARevisionID() )
+		{
+            	                case VIA_REVISION_CLECX :
+                                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_FIFO_CONTROL,
+                                        V1_FIFO_DEPTH64 | V1_FIFO_PRETHRESHOLD56 | V1_FIFO_THRESHOLD56);
+                                    break;
+
+                                default:
+                                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_FIFO_CONTROL,
+                                        V1_FIFO_DEPTH16 | V1_FIFO_PRETHRESHOLD12 | V1_FIFO_THRESHOLD8);
+                                    break;
+			}
+			}
+			else
+			{
+                            switch ( gVIAGraphicInfo.dwDeviceID )
+                            {
+                                case VIA_DEVICE_VT3205:
+                                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_FIFO_CONTROL,
+                                        (VIDInD(ALPHA_V3_FIFO_CONTROL)&ALPHA_FIFO_MASK)|V3_FIFO_DEPTH32 | V3_FIFO_THRESHOLD29);
+                                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_PREFIFO_CONTROL ,V3_FIFO_PRETHRESHOLD29 |
+                                        ( VIDInD(ALPHA_V3_PREFIFO_CONTROL)& (~V3_FIFO_MASK)) );
+                                    break;
+                                case VIA_DEVICE_CLE1:
+                                case VIA_DEVICE_CLE2:
+                                    switch ( DispatchVGARevisionID() )
+				{
+            	                        case VIA_REVISION_CLECX :
+                                            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_FIFO_CONTROL,
+                                                (VIDInD(ALPHA_V3_FIFO_CONTROL)&ALPHA_FIFO_MASK)|V3_FIFO_DEPTH64 | V3_FIFO_THRESHOLD56);                            
+                                            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_PREFIFO_CONTROL ,V3_FIFO_PRETHRESHOLD56 |
+                                                ( VIDInD(ALPHA_V3_PREFIFO_CONTROL)& (~V3_FIFO_MASK)) );
+                                            break;
+                                    
+                                        default:
+                                            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_FIFO_CONTROL,
+                                                (VIDInD(ALPHA_V3_FIFO_CONTROL)&ALPHA_FIFO_MASK)|V3_FIFO_DEPTH16 | V3_FIFO_THRESHOLD8);                            
+                                            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_PREFIFO_CONTROL ,(V3_FIFO_THRESHOLD16>>8) |
+                                                ( VIDInD(ALPHA_V3_PREFIFO_CONTROL)& (~V3_FIFO_MASK)) );
+                                            break;
+				}
+                                    break;
+                                default:
+                                    DBG_DD("Unknown DeviceID\n");
+                                    break;
+                            }/*End of DeviceID*/                                       
+			}
+			}
+		}
+            }
+            else
+		{
+                if (dwVideoFlag & VIDEO_1_INUSE)    
+			{
+                    /*=* Modify for C1 FIFO *=*/
+                    switch ( DispatchVGARevisionID() )
+				{
+            	        case VIA_REVISION_CLECX :
+                            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_FIFO_CONTROL,
+                                V1_FIFO_DEPTH64 | V1_FIFO_PRETHRESHOLD56 | V1_FIFO_THRESHOLD56);
+                            break;
+
+                        default:
+                            if (gdwUseExtendedFIFO)
+					{
+                                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_FIFO_CONTROL,
+                                    V1_FIFO_DEPTH48 | V1_FIFO_PRETHRESHOLD40 | V1_FIFO_THRESHOLD40);
+                        }
+                        else
+                        {
+                                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_FIFO_CONTROL,
+                                    V1_FIFO_DEPTH32 | V1_FIFO_PRETHRESHOLD29 | V1_FIFO_THRESHOLD16);
+                        }
+						break;
+					}
+				}
+			else
+			{
+                    //Fix V3 bug
+                    if (srcWidth <= 8)
+                    {
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_FIFO_CONTROL,
+                            (VIDInD(ALPHA_V3_FIFO_CONTROL)&ALPHA_FIFO_MASK));
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_PREFIFO_CONTROL ,
+                            ( VIDInD(ALPHA_V3_PREFIFO_CONTROL)& (~V3_FIFO_MASK)) );
+			}
+			else
+			{
+                        switch ( gVIAGraphicInfo.dwDeviceID )
+	{
+                            case VIA_DEVICE_VT3205:
+                                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_FIFO_CONTROL,
+                                    (VIDInD(ALPHA_V3_FIFO_CONTROL)&ALPHA_FIFO_MASK)|V3_FIFO_DEPTH32 | V3_FIFO_THRESHOLD29);
+                                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_PREFIFO_CONTROL ,V3_FIFO_PRETHRESHOLD29 |
+                                    ( VIDInD(ALPHA_V3_PREFIFO_CONTROL)& (~V3_FIFO_MASK)) );
+                                break;
+                            case VIA_DEVICE_CLE1:
+                            case VIA_DEVICE_CLE2:
+                                switch ( DispatchVGARevisionID() )
+		{
+                    	            case VIA_REVISION_CLECX :
+                                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_FIFO_CONTROL,
+                                            (VIDInD(ALPHA_V3_FIFO_CONTROL)&ALPHA_FIFO_MASK)|V3_FIFO_DEPTH64 | V3_FIFO_THRESHOLD56);
+                                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_PREFIFO_CONTROL ,V3_FIFO_PRETHRESHOLD56 |
+                                            ( VIDInD(ALPHA_V3_PREFIFO_CONTROL)& (~V3_FIFO_MASK)) );                        
+                                        break;
+
+                                    default:
+                                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_FIFO_CONTROL,
+                                            (VIDInD(ALPHA_V3_FIFO_CONTROL)&ALPHA_FIFO_MASK)|V3_FIFO_DEPTH32 | V3_FIFO_THRESHOLD16);
+                                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_PREFIFO_CONTROL ,(V3_FIFO_THRESHOLD16>>8) |
+                                            ( VIDInD(ALPHA_V3_PREFIFO_CONTROL)& (~V3_FIFO_MASK)) );                        
+                                        break;
+                                }
+                                break;
+                            default:
+                                DBG_DD("Unknown DeviceID\n");
+                                break;
+                        }/*End of DeviceID*/       
+			}
+			}
+		}
+                }
+                else
+                {
+            if (lpDPFsrc->dwFourCC == FOURCC_YV12)
+                {
+                if (dwVideoFlag & VIDEO_HQV_INUSE)
+                    {
+                    if (dwVideoFlag & VIDEO_1_INUSE)    
+                {
+                        /*=* Modify for C1 FIFO *=*/
+                        switch ( DispatchVGARevisionID() )
+                        {
+            	            case VIA_REVISION_CLECX :
+                                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_FIFO_CONTROL,
+                                    V1_FIFO_DEPTH64 | V1_FIFO_PRETHRESHOLD56 | V1_FIFO_THRESHOLD56);
+                                break;
+				
+                            default:
+                                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_FIFO_CONTROL,
+                                    V1_FIFO_DEPTH32 | V1_FIFO_PRETHRESHOLD29 | V1_FIFO_THRESHOLD16);
+                                break;
+                        }
+			}
+			else
+			{
+                        switch ( gVIAGraphicInfo.dwDeviceID )
+                {
+                            case VIA_DEVICE_VT3205:
+                                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_FIFO_CONTROL,
+                                    (VIDInD(ALPHA_V3_FIFO_CONTROL)&ALPHA_FIFO_MASK)|V3_FIFO_DEPTH32 | V3_FIFO_THRESHOLD29);
+                                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_PREFIFO_CONTROL ,V3_FIFO_PRETHRESHOLD29 |
+                                    ( VIDInD(ALPHA_V3_PREFIFO_CONTROL)& (~V3_FIFO_MASK)) );
+                                break;
+                            case VIA_DEVICE_CLE1:
+                            case VIA_DEVICE_CLE2:
+                                switch ( DispatchVGARevisionID() )
+                {
+            	                    case VIA_REVISION_CLECX :
+                                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_FIFO_CONTROL,
+                                            (VIDInD(ALPHA_V3_FIFO_CONTROL)&ALPHA_FIFO_MASK)|V3_FIFO_DEPTH64 | V3_FIFO_THRESHOLD56);                        
+                                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_PREFIFO_CONTROL ,V3_FIFO_PRETHRESHOLD56 |
+                                            ( VIDInD(ALPHA_V3_PREFIFO_CONTROL)& (~V3_FIFO_MASK)) );
+                                        break;
+                
+                                    default:
+                                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_FIFO_CONTROL,
+                                            (VIDInD(ALPHA_V3_FIFO_CONTROL)&ALPHA_FIFO_MASK)|V3_FIFO_DEPTH32 | V3_FIFO_THRESHOLD16);                        
+                                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_PREFIFO_CONTROL ,(V3_FIFO_THRESHOLD16>>8) |
+                                            ( VIDInD(ALPHA_V3_PREFIFO_CONTROL)& (~V3_FIFO_MASK)) );
+                                        break;
+                                }       
+                                break;
+                            default:
+                                DBG_DD("Unknown DeviceID\n");
+                                break;
+                        }/*End of DeviceID*/                                    
+                    }
+                    }
+                    else
+                    {                    
+                    //Minified Video will be skewed if not work around
+                    if (srcWidth <= 80) //Fetch count <= 5
+                    {
+                        if (dwVideoFlag & VIDEO_1_INUSE)    
+                        {
+                            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_FIFO_CONTROL,V1_FIFO_DEPTH16 );                            
+                        }
+                        else
+                        {
+                            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_FIFO_CONTROL,
+                                (VIDInD(ALPHA_V3_FIFO_CONTROL)&ALPHA_FIFO_MASK)|V3_FIFO_DEPTH16 );                            
+                            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_PREFIFO_CONTROL ,(V3_FIFO_THRESHOLD16>>8) |
+                                ( VIDInD(ALPHA_V3_PREFIFO_CONTROL)& (~V3_FIFO_MASK)) );
+                }
+		}
+		else
+			{
+                        if (dwVideoFlag & VIDEO_1_INUSE)    
+			{
+                            /*=* Modify for C1 FIFO *=*/
+                            switch ( DispatchVGARevisionID() )
+			{
+            	                case VIA_REVISION_CLECX :
+                                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_FIFO_CONTROL,
+                                        V1_FIFO_DEPTH64 | V1_FIFO_PRETHRESHOLD56 | V1_FIFO_THRESHOLD56);
+                                    break;
+                                    
+                                default:
+                                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_FIFO_CONTROL,
+                                        V1_FIFO_DEPTH16 | V1_FIFO_PRETHRESHOLD12 | V1_FIFO_THRESHOLD8);
+                                    break;
+		}
+    }
+    else
+    {
+                            switch ( gVIAGraphicInfo.dwDeviceID )
+        {
+                                case VIA_DEVICE_VT3205:
+                                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_FIFO_CONTROL,
+                                        (VIDInD(ALPHA_V3_FIFO_CONTROL)&ALPHA_FIFO_MASK)|V3_FIFO_DEPTH32 | V3_FIFO_THRESHOLD29);
+                                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_PREFIFO_CONTROL ,V3_FIFO_PRETHRESHOLD29 |
+                                        ( VIDInD(ALPHA_V3_PREFIFO_CONTROL)& (~V3_FIFO_MASK)) );
+                                    break;
+                                case VIA_DEVICE_CLE1:
+                                case VIA_DEVICE_CLE2:
+                                    switch ( DispatchVGARevisionID() )
+        {
+                     	                case VIA_REVISION_CLECX :
+                                            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_FIFO_CONTROL,
+                                                (VIDInD(ALPHA_V3_FIFO_CONTROL)&ALPHA_FIFO_MASK)|V3_FIFO_DEPTH64 | V3_FIFO_THRESHOLD56);                            
+                                            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_PREFIFO_CONTROL ,V3_FIFO_PRETHRESHOLD56 |
+                                                ( VIDInD(ALPHA_V3_PREFIFO_CONTROL)& (~V3_FIFO_MASK)) );
+                                            break;
+
+                                        default:
+                                            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_FIFO_CONTROL,
+                                                (VIDInD(ALPHA_V3_FIFO_CONTROL)&ALPHA_FIFO_MASK)|V3_FIFO_DEPTH16 | V3_FIFO_THRESHOLD8);                            
+                                            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_PREFIFO_CONTROL ,(V3_FIFO_THRESHOLD16>>8) |
+                                                ( VIDInD(ALPHA_V3_PREFIFO_CONTROL)& (~V3_FIFO_MASK)) );
+                                            break;
+            }
+                                    break;
+                                default:
+                                    DBG_DD("Unknown DeviceID\n");
+                                    break;
+                            }/*End of DeviceID*/                  
+        }
+        }
+        }
+    }
+            else
+    {        
+        if (dwVideoFlag & VIDEO_1_INUSE)
+        {
+            /*=* Modify for C1 FIFO *=*/
+            switch ( DispatchVGARevisionID() )
+            {
+            	case VIA_REVISION_CLECX :
+                            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_FIFO_CONTROL,
+                                V1_FIFO_DEPTH64 | V1_FIFO_PRETHRESHOLD56 | V1_FIFO_THRESHOLD56);                                                    
+                    break;
+                    
+                default:
+                    if (gdwUseExtendedFIFO)
+                    {
+                                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_FIFO_CONTROL,
+                                    V1_FIFO_DEPTH48 | V1_FIFO_PRETHRESHOLD40 | V1_FIFO_THRESHOLD40);                        
+                    }
+                    else
+                    {
+                                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, V_FIFO_CONTROL,
+                                    V1_FIFO_DEPTH32 | V1_FIFO_PRETHRESHOLD29 | V1_FIFO_THRESHOLD16);
+                    }
+                    break;
+            }
+        }
+        else
+        {
+                    //Fix V3 bug
+                    if (srcWidth <= 8)
+                    {
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_FIFO_CONTROL,
+                            (VIDInD(ALPHA_V3_FIFO_CONTROL)&ALPHA_FIFO_MASK));
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_PREFIFO_CONTROL ,
+                            ( VIDInD(ALPHA_V3_PREFIFO_CONTROL)& (~V3_FIFO_MASK)) );
+                    }
+                    else
+                    {
+                        switch ( gVIAGraphicInfo.dwDeviceID )
+                        {
+                            case VIA_DEVICE_VT3205:
+                                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_FIFO_CONTROL,
+                                    (VIDInD(ALPHA_V3_FIFO_CONTROL)&ALPHA_FIFO_MASK)|V3_FIFO_DEPTH32 | V3_FIFO_THRESHOLD29);
+                                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_PREFIFO_CONTROL ,V3_FIFO_PRETHRESHOLD29 |
+                                    ( VIDInD(ALPHA_V3_PREFIFO_CONTROL)& (~V3_FIFO_MASK)) );
+                                break;
+                            case VIA_DEVICE_CLE1:
+                            case VIA_DEVICE_CLE2:
+                                switch ( DispatchVGARevisionID() )
+                                {
+            	case VIA_REVISION_CLECX :
+                                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_FIFO_CONTROL,
+                                            (VIDInD(ALPHA_V3_FIFO_CONTROL)&ALPHA_FIFO_MASK)|V3_FIFO_DEPTH64 | V3_FIFO_THRESHOLD56);
+                                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_PREFIFO_CONTROL ,V3_FIFO_PRETHRESHOLD56 |
+                                            ( VIDInD(ALPHA_V3_PREFIFO_CONTROL)& (~V3_FIFO_MASK)) );                        
+                    break;
+                    
+                default:
+                                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_FIFO_CONTROL,
+                                            (VIDInD(ALPHA_V3_FIFO_CONTROL)&ALPHA_FIFO_MASK)|V3_FIFO_DEPTH32 | V3_FIFO_THRESHOLD16);
+                                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, ALPHA_V3_PREFIFO_CONTROL ,(V3_FIFO_THRESHOLD16>>8) |
+                                            ( VIDInD(ALPHA_V3_PREFIFO_CONTROL)& (~V3_FIFO_MASK)) );                        
+                    break;
+            }
+                                break;
+                            default:
+                                DBG_DD("Unknown DeviceID\n");
+                                break;
+                        }/*End of DeviceID*/                                     
+                    }
+                }
+            }
+        }
+
+        if (dwVideoFlag & VIDEO_HQV_INUSE)
+        {
+            miniCtl=0;
+            if (dwHQVzoomflagH||dwHQVzoomflagV)
+            {
+                dwTmp = 0;
+                if (dwHQVzoomflagH)
+                {
+                    miniCtl = V1_X_INTERPOLY;
+                    dwTmp = (zoomCtl&0xffff0000);
+        }
+
+                if (dwHQVzoomflagV)
+            {
+                    miniCtl |= (V1_Y_INTERPOLY | V1_YCBCR_INTERPOLY);
+                    dwTmp |= (zoomCtl&0x0000ffff);
+                    dwHQVfilterCtl &= 0xfffdffff;
+                }
+       
+                //Temporarily fix for 2D bandwidth problem. 2002/08/01
+                if ((gdwUseExtendedFIFO))
+                {
+                    miniCtl &= ~V1_Y_INTERPOLY;
+                }
+                
+                if (dwVideoFlag & VIDEO_1_INUSE)
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_MINI_CONTROL, miniCtl);
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_ZOOM_CONTROL, dwTmp);                
+                }
+                else
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_MINI_CONTROL, miniCtl);
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_ZOOM_CONTROL, dwTmp);                                    
+                }
+            }
+            else
+            {
+                if (dwVideoFlag & VIDEO_1_INUSE)
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_MINI_CONTROL, 0);
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_ZOOM_CONTROL, 0);
+                }
+                else
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_MINI_CONTROL, 0);
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_ZOOM_CONTROL, 0);
+                }
+            }
+/*            
+            if ((gVIAGraphicInfo.NoHQV_VFilter) || (srcHeight==dstHeight))
+            {
+                dwHQVfilterCtl &= 0xfffdffff;
+                DBG_DD("Upd_Video : No MPEG HQV Vertical Filter\n");
+        }
+            
+            if ((gVIAGraphicInfo.NoHQV_HFilter) || (srcWidth==dstWidth))
+        {
+                dwHQVfilterCtl &= 0xfffffffd;
+                DBG_DD("Upd_Video : No MPEG HQV Horizontal Filter\n");
+            }
+*/            
+            if (gVIAGraphicInfo.HQVFilter_ManualSelect)
+            {
+                switch(gVIAGraphicInfo.MpegHQV_VFilterMode)
+                {
+            	    case 0: 
+                        dwHQVfilterCtl &= 0x0000ffff;
+            	        dwHQVfilterCtl |= 0x00400000;
+                        DBG_DD("Upd_Video : No MPEG HQV Vertical Filter\n");
+                        break;
+                
+                    case 1:
+                        dwHQVfilterCtl &= 0x0000ffff;
+                        dwHQVfilterCtl |= HQV_V_TAP2_11;
+                        DBG_DD("Upd_Video : MPEG HQV Vertical Filter mode: TAP2_11\n");
+                        break;
+                    
+                    case 2:
+                        dwHQVfilterCtl &= 0x0000ffff;
+                        dwHQVfilterCtl |= HQV_V_TAP4_121;
+                        DBG_DD("Upd_Video : MPEG HQV Vertical Filter mode: TAP4_121\n");
+                        break;
+                        
+                    case 3:
+                        dwHQVfilterCtl &= 0x0000ffff;
+                        dwHQVfilterCtl |= HQV_V_TAP16_1991;
+                        DBG_DD("Upd_Video : MPEG HQV Vertical Filter mode: TAP16_1991\n");
+                        break;
+                        
+                    case 4:
+                        dwHQVfilterCtl &= 0x0000ffff;
+                        dwHQVfilterCtl |= HQV_V_TAP16_141041;
+                        DBG_DD("Upd_Video : MPEG HQV Vertical Filter mode: TAP16_141041\n");
+                        break;
+                    
+                    case 5:
+                        dwHQVfilterCtl &= 0x0000ffff;
+                        dwHQVfilterCtl |= HQV_V_TAP32;
+                        DBG_DD("Upd_Video : MPEG HQV Vertical Filter mode: TAP32\n");
+                        break;
+                        
+                    default:
+                        dwHQVfilterCtl &= 0x0000ffff;
+                        dwHQVfilterCtl |= HQV_V_FILTER_DEFAULT;
+                        DBG_DD("Upd_Video : MPEG HQV Vertical Filter mode: FILTER_DEFAULT\n");
+                        break;
+                }
+                
+                switch(gVIAGraphicInfo.MpegHQV_HFilterMode)
+                {
+            	    case 0: 
+            	        dwHQVfilterCtl &= 0xffff0000;
+            	        dwHQVfilterCtl |= 0x00000040;
+                        DBG_DD("Upd_Video : No MPEG HQV horizontal Filter\n");
+                        break;
+                    
+                    default:
+                        dwHQVfilterCtl &= 0xffff0000;
+                        dwHQVfilterCtl |= HQV_H_FILTER_DEFAULT;
+                        DBG_DD("Upd_Video : MPEG HQV horizontal Filter mode: FILTER_DEFAULT\n");
+                        break;
+                }
+            }
+            
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,HQV_MINIFY_CONTROL, dwHQVminiCtl);
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,HQV_FILTER_CONTROL, dwHQVfilterCtl);
+            }
+            else
+            {
+                if (dwVideoFlag & VIDEO_1_INUSE)
+                {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_MINI_CONTROL, miniCtl);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_ZOOM_CONTROL, zoomCtl);
+                }
+                else
+                {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_MINI_CONTROL, miniCtl);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_ZOOM_CONTROL, zoomCtl);                                
+            }
+        }
+
+
+        // Colorkey
+        if (dwColorKey) 
+        {
+            DBG_DD("Overlay colorkey= low:%08lx high:%08lx\n", dwKeyLow, dwKeyHigh);
+
+            dwKeyLow &= 0x00FFFFFF;
+            
+            if (lpVideoHWDifference->dwSupportTwoColorKey == VID_HWDIFF_TRUE)
+            {
+                dwCompose = (dwCompose & ~0x0f) | SELECT_VIDEO_IF_COLOR_KEY | SELECT_VIDEO3_IF_COLOR_KEY;                
+            }
+            else
+            {
+                dwCompose = (dwCompose & ~0x0f) | SELECT_VIDEO_IF_COLOR_KEY;
+            }
+            
+            /*Modified for SAMM Mode*/
+            if (ScrnIndex == 1)
+        {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,SND_COLOR_KEY, dwKeyLow);
+                dwCompose |= SECOND_DISPLAY_COLOR_KEY_ENABLE;
+                if ( dwVideoFlag & VIDEO_1_INUSE )
+            {
+                    dwVidCtl |= V1_ON_SND_DISPLAY;
+            }
+            else
+            {
+                    dwVidCtl |= V3_ON_SND_DISPLAY;
+            }
+        }
+            else
+            {
+                if (lpVideoHWDifference->dwSupportTwoColorKey == VID_HWDIFF_TRUE)
+            {
+                if (dwVideoFlag & VIDEO_1_INUSE)
+                {
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_COLOR_KEY, dwKeyLow);
+                }
+                else
+                {                  
+                        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_COLOR_KEY, dwKeyLow);
+            }
+                }
+                else
+                {                  
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_COLOR_KEY, dwKeyLow);    
+                }
+            }
+        }/* Colorkey*/
+                
+        if (dwChromaKey) {
+            DBG_DD("Overlay Chromakey= low:%08lx high:%08lx\n", dwKeyLow, dwKeyHigh);
+
+            dwChromaLow  &= CHROMA_KEY_LOW;
+            dwChromaHigh &= CHROMA_KEY_HIGH;
+
+            dwChromaLow  |= (VIDInD(V_CHROMAKEY_LOW)&(~CHROMA_KEY_LOW));
+            dwChromaHigh |= (VIDInD(V_CHROMAKEY_HIGH)&(~CHROMA_KEY_HIGH));
+
+            // for Chroma Key
+            if (lpDPFsrc->dwFlags & DDPF_FOURCC)
+        {
+                    switch (lpDPFsrc->dwFourCC) {
+                    case FOURCC_YV12:
+                            //to be continued...
+                            break;
+                    case FOURCC_YUY2:
+                            //to be continued...
+                            break;
+                    default:
+                            //TOINT3;
+                            break;
+                    }
+            }
+            else if (lpDPFsrc->dwFlags & DDPF_RGB)
+            {
+                    unsigned long dwtmpLowR;
+                    unsigned long dwtmpLowG;
+                    unsigned long dwtmpLowB;
+                    unsigned long dwtmpChromaLow;
+                    unsigned long dwtmpHighR;
+                    unsigned long dwtmpHighG;
+                    unsigned long dwtmpHighB;
+                    unsigned long dwtmpChromaHigh;
+
+                    switch (lpDPFsrc->dwRGBBitCount) {
+                    case 16:
+                            if (lpDPFsrc->dwGBitMask==0x07E0) //RGB16(5:6:5)
+                 {
+                                    dwtmpLowR = (((dwChromaLow >> 11) << 3) | ((dwChromaLow >> 13) & 0x07)) & 0xFF;
+                                    dwtmpLowG = (((dwChromaLow >> 5) << 2) | ((dwChromaLow >> 9) & 0x03)) & 0xFF;
+
+                                    dwtmpHighR = (((dwChromaHigh >> 11) << 3) | ((dwChromaHigh >> 13) & 0x07)) & 0xFF;
+                                    dwtmpHighG = (((dwChromaHigh >> 5) << 2) | ((dwChromaHigh >> 9) & 0x03)) & 0xFF;
+                            }
+                            else //RGB15(5:5:5)
+                            {
+                                    dwtmpLowR = (((dwChromaLow >> 10) << 3) | ((dwChromaLow >> 12) & 0x07)) & 0xFF;
+                                    dwtmpLowG = (((dwChromaLow >> 5) << 3) | ((dwChromaLow >> 7) & 0x07)) & 0xFF;
+
+                                    dwtmpHighR = (((dwChromaHigh >> 10) << 3) | ((dwChromaHigh >> 12) & 0x07)) & 0xFF;
+                                    dwtmpHighG = (((dwChromaHigh >> 5) << 3) | ((dwChromaHigh >> 7) & 0x07)) & 0xFF;
+                            }
+                            dwtmpLowB = (((dwChromaLow << 3) | (dwChromaLow >> 2)) & 0x07) & 0xFF;
+                            dwtmpChromaLow = (dwtmpLowG << 16) | (dwtmpLowR << 8) | dwtmpLowB;
+                            dwChromaLow = ((dwChromaLow >> 24) << 24) | dwtmpChromaLow;
+
+                            dwtmpHighB = (((dwChromaHigh << 3) | (dwChromaHigh >> 2)) & 0x07) & 0xFF;
+                            dwtmpChromaHigh = (dwtmpHighG << 16) | (dwtmpHighR << 8) | dwtmpHighB;
+                            dwChromaHigh = ((dwChromaHigh >> 24) << 24) | dwtmpChromaHigh;
+                            break;
+
+                    case 32: //32 bit RGB
+                            dwtmpLowR = (dwChromaLow >> 16) & 0xFF;
+                            dwtmpLowG = (dwChromaLow >> 8) & 0xFF;
+                            dwtmpLowB = dwChromaLow & 0xFF;
+                            dwtmpChromaLow = (dwtmpLowG << 16) | (dwtmpLowR << 8) | dwtmpLowB;
+                            dwChromaLow = ((dwChromaLow >> 24) << 24) | dwtmpChromaLow;
+
+                            dwtmpHighR = (dwChromaHigh >> 16) & 0xFF;
+                            dwtmpHighG = (dwChromaHigh >> 8) & 0xFF;
+                            dwtmpHighB = dwChromaHigh & 0xFF;
+                            dwtmpChromaHigh = (dwtmpHighG << 16) | (dwtmpHighR << 8) | dwtmpHighB;
+                            dwChromaHigh = ((dwChromaHigh >> 24) << 24) | dwtmpChromaHigh;
+                            break;
+
+                    default:
+                            //TOINT3;
+                            break;
+                    }
+            }//End of DDPF_FOURCC
+
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_CHROMAKEY_HIGH,dwChromaHigh);
+            if (dwVideoFlag & VIDEO_1_INUSE)
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_CHROMAKEY_LOW, dwChromaLow);
+                //Temporarily solve the H/W Interpolation error when using Chroma Key
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_MINI_CONTROL, miniCtl & 0xFFFFFFF8);
+                 }
+                 else
+                 {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_CHROMAKEY_LOW, dwChromaLow|V_CHROMAKEY_V3);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_MINI_CONTROL, miniCtl & 0xFFFFFFF8);
+                 }
+
+            //Modified for select video if (color key & chroma key)
+            if (dwCompose==SELECT_VIDEO_IF_COLOR_KEY)
+               dwCompose = SELECT_VIDEO_IF_COLOR_KEY | SELECT_VIDEO_IF_CHROMA_KEY;
+            else
+               dwCompose = (dwCompose & ~0x0f) | SELECT_VIDEO_IF_CHROMA_KEY;
+            }
+
+        // determine which video stream is on top
+        /*
+        DBG_DD("        dwFlags= 0x%08lx\n", dwFlags);
+        if (dwFlags & DDOVER_CLIP)
+            dwCompose |= COMPOSE_V3_TOP;
+            else
+            dwCompose |= COMPOSE_V1_TOP;
+        */    
+        DBG_DD("        lpVideoControl->dwCompose 0x%lx\n", lpVideoControl->dwCompose);
+
+        if (lpVideoControl->dwCompose & (VW_TV1_TOP | VW_TV_TOP) )
+            dwCompose &= ~COMPOSE_V3_TOP;
+            //dwCompose |= COMPOSE_V3_TOP;
+        else if (lpVideoControl->dwCompose & (VW_TV0_TOP | VW_DVD_TOP) )
+            dwCompose |= COMPOSE_V3_TOP;
+            //dwCompose &= ~COMPOSE_V3_TOP;
+
+        DBG_DD("        dwCompose 0x%8lx\n", dwCompose);
+
+        // Setup video control
+        if (dwVideoFlag & VIDEO_HQV_INUSE)
+            {
+            if (!SWVideo_ON)
+            //if (0)
+                 {
+                DBG_DD("    First HQV\n"); 
+                Macro_VidREGFlush();
+                
+                if ( lpVideoHWDifference->dwHQVInitPatch )     
+                {
+                    WaitHQVFlipClear(((dwHQVCtl&~HQV_SW_FLIP)|HQV_FLIP_STATUS)&~HQV_ENABLE);
+                    VIDOutD( HQV_CONTROL, dwHQVCtl);
+                    WaitHQVFlip();
+                    WaitHQVFlipClear(((dwHQVCtl&~HQV_SW_FLIP)|HQV_FLIP_STATUS)&~HQV_ENABLE);
+                    VIDOutD( HQV_CONTROL, dwHQVCtl);
+                    WaitHQVFlip();
+                }
+                else    // CLE_C0
+                {
+                    VIDOutD( HQV_CONTROL, dwHQVCtl & ~HQV_SW_FLIP);
+                    VIDOutD( HQV_CONTROL, dwHQVCtl | HQV_SW_FLIP);
+                    //VIDOutD( HQV_CONTROL, dwHQVCtl | HQV_SUBPIC_FLIP);
+                    WaitHQVFlip();
+                }
+                
+                if (dwVideoFlag & VIDEO_1_INUSE)
+                {
+                    VIDOutD(V1_CONTROL, dwVidCtl);
+                    VIDOutD(V_COMPOSE_MODE, (dwCompose|V1_COMMAND_FIRE ));
+                    if (gdwUseExtendedFIFO)
+                    {
+                        //Set Display FIFO
+                        WaitVBI();
+                        outb(0x17, 0x3C4); outb(0x2f, 0x3C5);
+                        outb(0x16, 0x3C4); outb((Save_3C4_16&0xf0)|0x14, 0x3C5);
+                        outb(0x18, 0x3C4); outb(0x56, 0x3C5);
+                    }
+                 }
+                 else 
+                 {
+                    VIDOutD(V3_CONTROL, dwVidCtl);
+                    VIDOutD(V_COMPOSE_MODE, (dwCompose|V3_COMMAND_FIRE ));                    
+                 }
+	        }
+            else
+            {
+                DBG_DD("    Normal called\n"); 
+                if (dwVideoFlag & VIDEO_1_INUSE)
+                {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_CONTROL, dwVidCtl);
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_COMPOSE_MODE, (dwCompose|V1_COMMAND_FIRE ));
+        }
+        else
+        {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_CONTROL, dwVidCtl);
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_COMPOSE_MODE, (dwCompose|V3_COMMAND_FIRE ));                    
+                }
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER, HQV_CONTROL, dwHQVCtl|HQV_FLIP_STATUS);
+                //WaitHQVDone();
+                Macro_VidREGFlush();                
+            }
+        }
+        else
+        {
+            if (dwVideoFlag & VIDEO_1_INUSE)
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_CONTROL, dwVidCtl);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_COMPOSE_MODE, (dwCompose|V1_COMMAND_FIRE ));
+            }
+            else
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_CONTROL, dwVidCtl);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_COMPOSE_MODE, (dwCompose|V3_COMMAND_FIRE ));                
+            }
+            //WaitHQVDone();
+            Macro_VidREGFlush();
+        }
+        SWVideo_ON = TRUE;      
+    }
+    else
+    {
+        //Hide overlay
+        if ( lpVideoHWDifference->dwHQVDisablePatch )     // CLE_C0
+        {
+            outb(0x2E, 0x3C4);
+            outb(0xEF, 0x3C5);
+        }
+        
+        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_FIFO_CONTROL,V1_FIFO_PRETHRESHOLD12 |
+             V1_FIFO_THRESHOLD8 |V1_FIFO_DEPTH16);
+        Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,ALPHA_V3_FIFO_CONTROL, ALPHA_FIFO_THRESHOLD4 
+             | ALPHA_FIFO_DEPTH8  | V3_FIFO_THRESHOLD24 | V3_FIFO_DEPTH32 );
+
+        if (dwVideoFlag&VIDEO_HQV_INUSE)
+        {
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,HQV_CONTROL, (VIDInD(HQV_CONTROL) & (~HQV_ENABLE)));            
+        }
+
+        if (dwVideoFlag&VIDEO_1_INUSE)
+        {
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_CONTROL, (VIDInD(V1_CONTROL) & (~V1_ENABLE)));
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_COMPOSE_MODE, (VIDInD(V_COMPOSE_MODE)|V1_COMMAND_FIRE));
+        }
+        else
+        {
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_CONTROL, (VIDInD(V3_CONTROL) & (~V3_ENABLE)));        
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_COMPOSE_MODE, (VIDInD(V_COMPOSE_MODE)|V3_COMMAND_FIRE));
+        }
+        
+        Macro_VidREGFlush();        
+
+        if ( lpVideoHWDifference->dwHQVDisablePatch )     // CLE_C0
+        {
+            outb(0x2E, 0x3C4);
+            outb(0xFF, 0x3C5);
+        }          
+    }  
+
+    return PI_OK;    
+}
+
+
+void MPEGFlipCurrentFrame()
+{
+	DBG_DD("// MPEGFlipCurrentFrame\n");
+
+	unsigned long tmpCmd = VIDInD(0xc00);
+
+	if (overlayRecordV1.dwDisplayPictStruct == 3 &&
+		!overlayRecordV1.dwMPEGDeinterlaceMode )
+	{
+		VIDOutD(0xc00, lpMPGDevice->dwMPEGDisplayIndex | 0x8c);
+	}//8661
+	else
+	{//8671
+		VIDOutD(0xc00, lpMPGDevice->dwMPEGDisplayIndex | 0x84);
+	}
+
+	if (!tmpCmd & 0x00008000) //HQV_SUBPIC_FLIP perhaps?
+	{
+		VIDOutD(0xc00,tmpCmd);
+	}
+}
+
+
+unsigned long Upd_MPEG( unsigned long dwVideoFlag,
+                        RECTL rSrc,
+                        RECTL rDest,
+                        unsigned long dwSrcPitch,
+                        unsigned long dwOriSrcWidth,
+                        unsigned long dwOriSrcHeight,
+                        LPDDPIXELFORMAT lpDPFsrc,
+                        unsigned long dwDeinterlaceMode,
+                        unsigned long dwColorKey,
+                        unsigned long dwChromaKey,
+                        unsigned long dwKeyLow,
+                        unsigned long dwKeyHigh,
+                        unsigned long dwChromaLow,
+                        unsigned long dwChromaHigh,
+			unsigned long dwFlags)
+{
+    unsigned long srcWidth, srcHeight,dstWidth,dstHeight;
+    unsigned long dwVidCtl=0, dwCompose=(VIDInD(V_COMPOSE_MODE)&~(SELECT_VIDEO_IF_COLOR_KEY|V1_COMMAND_FIRE|V3_COMMAND_FIRE));
+    unsigned long zoomCtl=0, miniCtl=0;
+    unsigned long dwHQVCtl=0;
+    unsigned long dwHQVfilterCtl=0,dwHQVminiCtl=0;
+    unsigned long dwHQVzoomflagH=0,dwHQVzoomflagV=0;
+    unsigned long dwHQVsrcWidth=0,dwHQVdstWidth=0;
+    unsigned long dwHQVsrcFetch = 0,dwHQVoffset=0;
+    unsigned long dwOffset = 0, dwFetch=0, dwTmp=0;
+    unsigned long dwDisplayCountW=0;
+    
+    LPVIDHWDIFFERENCE lpVideoHWDifference = &VideoHWDifference;
+
+    /*Added for SAMM expand Mode*/
+    unsigned long dstModifiedWidth=0,dstModifiedHeight=0;
+
+    /*Added for SAMM Mode*/
+    int ScrnIndex = 0;
+    if (dwFlags & DDOVER_ON_SND)
+    {
+        ScrnIndex = 1;
+    }
+    DBG_DD("ScrnIndex=%d\n",ScrnIndex);
+
+    DBG_DD("//Upd_MPEG:\n");
+    DBG_DD("Modified rSrc  X (%ld,%ld) Y (%ld,%ld)\n",
+           rSrc.left, rSrc.right,rSrc.top, rSrc.bottom);
+    DBG_DD("Modified rDest  X (%ld,%ld) Y (%ld,%ld)\n",
+           rDest.left, rDest.right,rDest.top, rDest.bottom);
+    
+
+    DBG_DD("MPGDevice.lpVideoMemIO %08lx\n",MPGDevice.lpVideoMemIO);
+    DBG_DD("lpMPGDevice->lpMPEGOverlaySurface[0] %08lx\n", lpMPGDevice->lpMPEGOverlaySurface[0]);
+    DBG_DD("lpMPGDevice->lpMPEGOverlaySurface[1] %08lx\n", lpMPGDevice->lpMPEGOverlaySurface[1]);
+    DBG_DD("lpMPGDevice->lpMPEGOverlaySurface[2] %08lx\n", lpMPGDevice->lpMPEGOverlaySurface[2]);
+    DBG_DD("lpMPGDevice->lpMPEGOverlaySurface[3] %08lx\n", lpMPGDevice->lpMPEGOverlaySurface[3]);
+    DBG_DD("lpMPGDevice->dwMPEGPhysicalAddr[0] %08lx\n", lpMPGDevice->dwMPEGPhysicalAddr[0]);
+    DBG_DD("lpMPGDevice->dwMPEGPhysicalAddr[1] %08lx\n", lpMPGDevice->dwMPEGPhysicalAddr[1]);
+    DBG_DD("lpMPGDevice->dwMPEGPhysicalAddr[2] %08lx\n", lpMPGDevice->dwMPEGPhysicalAddr[2]);
+    DBG_DD("lpMPGDevice->dwMPEGPhysicalAddr[3] %08lx\n", lpMPGDevice->dwMPEGPhysicalAddr[3]);
+    DBG_DD("lpMPGDevice->gdwSetBufferIndex %08lx\n", lpMPGDevice->gdwSetBufferIndex);
+    DBG_DD("lpMPGDevice->dwMPEGYPhysicalAddr[0] %08lx\n", lpMPGDevice->dwMPEGYPhysicalAddr[0]);
+    DBG_DD("lpMPGDevice->dwMPEGCbPhysicalAddr[0] %08lx\n", lpMPGDevice->dwMPEGCbPhysicalAddr[0]);
+    DBG_DD("lpMPGDevice->dwMPEGCrPhysicalAddr[0] %08lx\n", lpMPGDevice->dwMPEGCrPhysicalAddr[0]);
+    DBG_DD("lpMPGDevice->dwMPEGYPhysicalAddr[1] %08lx\n", lpMPGDevice->dwMPEGYPhysicalAddr[1]);
+    DBG_DD("lpMPGDevice->dwMPEGCbPhysicalAddr[1] %08lx\n", lpMPGDevice->dwMPEGCbPhysicalAddr[1]);
+    DBG_DD("lpMPGDevice->dwMPEGCrPhysicalAddr[1] %08lx\n", lpMPGDevice->dwMPEGCrPhysicalAddr[1]);
+    DBG_DD("lpMPGDevice->dwMPEGYPhysicalAddr[2] %08lx\n", lpMPGDevice->dwMPEGYPhysicalAddr[2]);
+    DBG_DD("lpMPGDevice->dwMPEGCbPhysicalAddr[2] %08lx\n", lpMPGDevice->dwMPEGCbPhysicalAddr[2]);
+    DBG_DD("lpMPGDevice->dwMPEGCrPhysicalAddr[2] %08lx\n", lpMPGDevice->dwMPEGCrPhysicalAddr[2]);    
+    DBG_DD("lpMPGDevice->dwMPEGYPhysicalAddr[3] %08lx\n", lpMPGDevice->dwMPEGYPhysicalAddr[3]);
+    DBG_DD("lpMPGDevice->dwMPEGCbPhysicalAddr[3] %08lx\n", lpMPGDevice->dwMPEGCbPhysicalAddr[3]);
+    DBG_DD("lpMPGDevice->dwMPEGCrPhysicalAddr[3] %08lx\n", lpMPGDevice->dwMPEGCrPhysicalAddr[3]);
+
+    DBG_DD("lpMPGDevice->dwMPEGDisplayIndex %04x\n", lpMPGDevice->dwMPEGDisplayIndex);
+    DBG_DD("lpMPGDevice->dwHQVAddr[0] %08lx\n", lpMPGDevice->dwHQVAddr[0]);
+    DBG_DD("lpMPGDevice->dwHQVAddr[1] %08lx\n", lpMPGDevice->dwHQVAddr[1]);
+    DBG_DD("lpMPGDevice->dwEnableErrorConcealment %04x\n",lpMPGDevice->dwEnableErrorConcealment );
+    DBG_DD("lpMPGDevice->dwVendorID %04x\n", lpMPGDevice->dwVendorID);
+    DBG_DD("lpMPGDevice->dwDeviceID %04x\n", lpMPGDevice->dwDeviceID);
+    DBG_DD("lpMPGDevice->dwRevisionID %04x\n", lpMPGDevice->dwRevisionID);
+    DBG_DD("lpMPGDevice->dwSubVendorID %04x\n", lpMPGDevice->dwSubVendorID);
+    DBG_DD("lpMPGDevice->dwSubDeviceID %04x\n", lpMPGDevice->dwSubDeviceID);
+
+    if (DispatchVGARevisionID() == VIA_REVISION_CLECX)
+            {
+        if (dwVideoFlag & VIDEO_1_INUSE)
+            {
+            dwCompose |= V_COMMAND_LOAD_VBI | V3_COMMAND_LOAD_VBI;
+            }
+        }
+
+//a9d3
+    if (dwVideoFlag & VIDEO_SHOW /*0x80000000*/ )
+    {
+        overlayRecordV1.dwWidth = dstWidth = rDest.right - rDest.left;
+        overlayRecordV1.dwHeight =dstHeight= rDest.bottom - rDest.top;
+        srcWidth = (unsigned long)rSrc.right - rSrc.left;
+        srcHeight = (unsigned long)rSrc.bottom - rSrc.top;
+
+        DBG_DD("===srcWidth= %ld \n", srcWidth);
+        DBG_DD("===srcHeight= %ld \n", srcHeight);
+
+        /*Added for SAMM expand Mode*/
+        /*In SAMM expand, we need adjust x and y position, width and height zoom factor.*/
+        if  ( ((gVIAGraphicInfo.Screen[ScrnIndex].dwDVIOn)||(gVIAGraphicInfo.Screen[ScrnIndex].dwLCDOn))
+              &&(gVIAGraphicInfo.Screen[ScrnIndex].dwExpand) )
+            {
+            dstModifiedWidth=dstWidth*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelWidth)/
+                             (gVIAGraphicInfo.Screen[ScrnIndex].dwWidth)+1;
+            dstModifiedHeight=dstHeight*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelHeight)/
+                              (gVIAGraphicInfo.Screen[ScrnIndex].dwHeight)+1;
+            DBG_DD("===Expand!! \n");
+            }
+            else
+            {
+            dstModifiedWidth=dstWidth;
+            dstModifiedHeight=dstHeight;
+        }
+        DBG_DD("===dstModifiedWidth= %ld \n", dstModifiedWidth);
+        DBG_DD("===dstModifiedHeight= %ld \n", dstModifiedHeight);
+
+        if ((dwDeinterlaceMode & (DDOVER_BOB|DDOVER_INTERLEAVED)) == (DDOVER_BOB|DDOVER_INTERLEAVED))
+        {
+            DBG_DD("//   dwMPEGDeinterlace: BOB\n");
+            overlayRecordV1.dwMPEGDeinterlaceMode = VIA_DEINTERLACE_BOB;
+            overlayRecordV1.dwMPEGProgressiveMode = VIA_NON_PROGRESSIVE;
+        }
+        else
+        {
+            DBG_DD("//   dwMPEGDeinterlace: WEAVE\n");
+            overlayRecordV1.dwMPEGDeinterlaceMode = VIA_DEINTERLACE_WEAVE;
+            overlayRecordV1.dwDisplayPictStruct = 3;
+            overlayRecordV1.dwMPEGProgressiveMode = VIA_PROGRESSIVE;
+        }
+
+        if (dwVideoFlag & VIDEO_1_INUSE /* 0x01000000 */)
+            {
+            DBG_DD("//Upd_MPEG: V1 + HQV\n");
+            
+            switch ( DispatchVGARevisionID() )
+                {
+                case VIA_REVISION_CLECX:
+                    dwVidCtl = (V1_ENABLE|V1_EXPIRE_NUM_F);
+                    break;
+                default:
+                    if (gdwUseExtendedFIFO)
+                        dwVidCtl = (V1_ENABLE|V1_EXPIRE_NUM_A|V1_FIFO_EXTENDED);
+                else
+                        dwVidCtl = (V1_ENABLE|V1_EXPIRE_NUM);
+                    break;
+            }
+            
+            DDOver_GetV1Format(dwVideoFlag, lpDPFsrc, &dwVidCtl, &dwHQVCtl);
+        }//c140
+            else
+            {
+            DBG_DD("//Upd_MPEG: V3 + HQV\n");
+            switch ( DispatchVGARevisionID() )
+            {
+                case VIA_REVISION_CLECX :
+                    dwVidCtl = (V3_ENABLE|V3_EXPIRE_NUM_F);
+                    break;
+
+                default:
+                    dwVidCtl = (V3_ENABLE|V3_EXPIRE_NUM);
+                    break;
+            }
+
+            DDOver_GetV3Format(dwVideoFlag, lpDPFsrc, &dwVidCtl, &dwHQVCtl);
+        }//aaba
+        
+        if (lpVideoHWDifference->dwThreeHQVBuffer)
+        {
+            dwHQVCtl = ( dwHQVCtl & ~HQV_SW_FLIP) | HQV_FLIP_STATUS | HQV_TRIPLE_BUFF;
+        }
+        
+        overlayRecordV1.dwOffset = dwOffset = DDOver_GetSrcStartAddress(dwVideoFlag, rSrc, rDest, dwSrcPitch, lpDPFsrc, &dwHQVoffset);
+        
+        if (dwVideoFlag & MPEG_USE_HW_FLIP ) //0x40000
+        {
+            //bf70;
+            if (dwVideoFlag & VIDEO_HQV_INUSE /*0x4000000*/)
+            {//abe9
+                if (dwVideoFlag & VIDEO_1_INUSE /*0x1000000*/ )
+            {
+                    Macro_VidREGRec(1, V1_STARTADDR_0, lpMPGDevice->dwHQVAddr[0]+dwOffset);
+                    Macro_VidREGRec(1, V1_STARTADDR_1, lpMPGDevice->dwHQVAddr[1]+dwOffset);
+                    
+                    if (lpVideoHWDifference->dwThreeHQVBuffer)
+                    {
+                        Macro_VidREGRec(1, V1_STARTADDR_2, lpMPGDevice->dwHQVAddr[2] + dwOffset);
+                    }
+            }
+            else
+            {
+                    Macro_VidREGRec(1, V3_STARTADDR_0, lpMPGDevice->dwHQVAddr[0]+dwOffset);
+                    Macro_VidREGRec(1, V3_STARTADDR_1, lpMPGDevice->dwHQVAddr[1]+dwOffset);
+                    
+                    if (lpVideoHWDifference->dwThreeHQVBuffer)
+                {
+                        Macro_VidREGRec(1, V3_STARTADDR_2, lpMPGDevice->dwHQVAddr[2] + dwOffset);
+                }
+                }
+            }
+            else
+            { //bf7c
+        	    Macro_VidREGRec(1, V1_STARTADDR_0,   lpMPGDevice->dwMPEGYPhysicalAddr[0]+overlayRecordV1.dwOffset);
+        	    Macro_VidREGRec(1, V1_STARTADDR_CB0, lpMPGDevice->dwMPEGCbPhysicalAddr[0]+overlayRecordV1.dwUVoffset);
+        	    Macro_VidREGRec(1, V1_STARTADDR_CR0, lpMPGDevice->dwMPEGCrPhysicalAddr[0]+overlayRecordV1.dwUVoffset);
+                
+        	    Macro_VidREGRec(1, V1_STARTADDR_1,   lpMPGDevice->dwMPEGYPhysicalAddr[1]+overlayRecordV1.dwOffset);
+        	    Macro_VidREGRec(1, V1_STARTADDR_CB1, lpMPGDevice->dwMPEGCbPhysicalAddr[1]+overlayRecordV1.dwUVoffset);
+        	    Macro_VidREGRec(1, V1_STARTADDR_CR1, lpMPGDevice->dwMPEGCrPhysicalAddr[1]+overlayRecordV1.dwUVoffset);
+                
+                Macro_VidREGRec(1, V1_STARTADDR_2,   lpMPGDevice->dwMPEGYPhysicalAddr[2]+overlayRecordV1.dwOffset);
+        	    Macro_VidREGRec(1, V1_STARTADDR_CB2, lpMPGDevice->dwMPEGCbPhysicalAddr[2]+overlayRecordV1.dwUVoffset);
+                Macro_VidREGRec(1, V1_STARTADDR_CR2, lpMPGDevice->dwMPEGCrPhysicalAddr[2]+overlayRecordV1.dwUVoffset);
+                
+        	    Macro_VidREGRec(1, V1_STARTADDR_3,   lpMPGDevice->dwMPEGYPhysicalAddr[3]+overlayRecordV1.dwOffset);
+        	    Macro_VidREGRec(1, V1_STARTADDR_CB3, lpMPGDevice->dwMPEGCbPhysicalAddr[3]+overlayRecordV1.dwUVoffset);
+        	    Macro_VidREGRec(1, V1_STARTADDR_CR3, lpMPGDevice->dwMPEGCrPhysicalAddr[3]+overlayRecordV1.dwUVoffset);
+        }
+        }
+        else //ab55
+        {
+            unsigned long i,ebp = 0;
+        
+            for (i = 0; i<=3; i++)
+        {
+                if (MPGDevice.dwMPEGYPhysicalAddr[i] == VIDInD(0x1d4))
+            {
+                    ebp = i;
+            }
+            }
+            
+            DBG_DD("0x1d4 - %08lx\n", VIDInD(0x1d4));
+            DBG_DD("0x1d8 - %08lx\n", VIDInD(0x1d8));
+            DBG_DD("0x1dc - %08lx\n", VIDInD(0x1dc));
+
+            for (i=0; i<=3; i++)
+                {
+                DBG_DD("MPGDevice.dwMPEGYPhysicalAddr[%d] == %08lx\n", i, MPGDevice.dwMPEGYPhysicalAddr[i]);
+            }
+            
+            DBG_DD("===dwBufferIndex=0x%lx\n",ebp);
+            
+            if (dwVideoFlag & VIDEO_HQV_INUSE /*0x4000000*/)
+                    {
+                Macro_VidREGRec(1, HQV_SRC_STARTADDR_Y, lpMPGDevice->dwMPEGYPhysicalAddr[ebp]);
+                Macro_VidREGRec(1, HQV_SRC_STARTADDR_U, lpMPGDevice->dwMPEGCbPhysicalAddr[ebp]);
+                Macro_VidREGRec(1, HQV_SRC_STARTADDR_V, lpMPGDevice->dwMPEGCrPhysicalAddr[ebp]);
+
+                if (dwVideoFlag & VIDEO_1_INUSE /*0x1000000*/ )
+                        {
+                    Macro_VidREGRec(1,V1_STARTADDR_0, lpMPGDevice->dwHQVAddr[0] + overlayRecordV1.dwOffset);
+                    Macro_VidREGRec(1,V1_STARTADDR_1, lpMPGDevice->dwHQVAddr[1] + overlayRecordV1.dwOffset);
+                                
+                    if (lpVideoHWDifference->dwThreeHQVBuffer)
+                    {
+                        Macro_VidREGRec(1, V1_STARTADDR_2, lpMPGDevice->dwHQVAddr[2] + overlayRecordV1.dwOffset);
+                        }
+                    }
+                    else
+                    {
+                    Macro_VidREGRec(1,V3_STARTADDR_0, lpMPGDevice->dwHQVAddr[0] + overlayRecordV1.dwOffset);
+                    Macro_VidREGRec(1,V3_STARTADDR_1, lpMPGDevice->dwHQVAddr[1] + overlayRecordV1.dwOffset);
+                                
+                    if (lpVideoHWDifference->dwThreeHQVBuffer)
+                    {
+                        Macro_VidREGRec(1, V3_STARTADDR_2, lpMPGDevice->dwHQVAddr[2] + overlayRecordV1.dwOffset );
+                        }
+                    }
+                }
+                else
+                {
+                Macro_VidREGRec(1, V1_STARTADDR_0,   lpMPGDevice->dwMPEGYPhysicalAddr[ebp] + overlayRecordV1.dwOffset);
+                Macro_VidREGRec(1, V1_STARTADDR_CB0, lpMPGDevice->dwMPEGCbPhysicalAddr[ebp] + overlayRecordV1.dwUVoffset);
+                Macro_VidREGRec(1, V1_STARTADDR_CR0, lpMPGDevice->dwMPEGCrPhysicalAddr[ebp] + overlayRecordV1.dwUVoffset);
+                        }    
+        }
+
+        //ac37
+//		dwFetch = DDOver_GetFetch(dwVideoFlag, lpDPFsrc, srcWidth, dstWidth, dwOriSrcWidth,&dwHQVsrcFetch);
+        dwFetch = DDOver_GetFetch(dwVideoFlag,lpDPFsrc,srcWidth,dstModifiedWidth,dwOriSrcWidth,&dwHQVsrcFetch);
+        
+		DBG_DD("===dwFetch= 0x%lx\n", dwFetch);
+
+		if (dwVideoFlag & VIDEO_HQV_INUSE /*0x4000000*/ )
+                        {
+			if (lpDPFsrc->dwFourCC == FOURCC_VIA /*0x4E4B4C57*/)
+			{ // bd06
+				if (dwVideoFlag & VIDEO_1_INUSE /*0x1000000*/ )
+				{ //bd12
+					Macro_VidREGRec(1, V1_STRIDE, dwSrcPitch << 1 );
+                        }
+				else
+				{ //bd95
+                    Macro_VidREGRec(1, V3_STRIDE, dwSrcPitch << 1 );
+                    }
+//bd1f
+				if (lpVideoHWDifference->dwHQVFetchByteUnit)
+					Macro_VidREGRec(1, HQV_SRC_FETCH_LINE, (dwOriSrcHeight-1) | ((lpMPGDevice->dwWidth-1)<<0x10) );
+                    else
+                    Macro_VidREGRec(1, HQV_SRC_FETCH_LINE, (dwOriSrcHeight-1) | ((lpMPGDevice->dwWidth>>3)-1)<<0x10);
+                                    
+                Macro_VidREGRec(1, HQV_SRC_STRIDE, (lpMPGDevice->dwPitch>>1)<<0x10 | (lpMPGDevice->dwPitch));
+                Macro_VidREGRec(1, HQV_DST_STRIDE, dwSrcPitch <<1 );
+                            }
+//bc20
+            else if (lpDPFsrc->dwFourCC == FOURCC_IYUV /* 0x56555949 */)
+            {
+                if ( dwVideoFlag & VIDEO_1_INUSE )
+                {
+                    Macro_VidREGRec(1,V1_STRIDE, lpMPGDevice->dwPitch<<1);
+                        }
+                        else
+                        {
+                    Macro_VidREGRec(1,V3_STRIDE, lpMPGDevice->dwPitch<<1);
+                }
+                                    
+                if (lpVideoHWDifference->dwHQVFetchByteUnit)
+                {
+                    Macro_VidREGRec(1,HQV_SRC_FETCH_LINE, (lpMPGDevice->dwWidth-1) | (lpMPGDevice->dwHeight-1) );
+                            }
+                else
+                {
+                    Macro_VidREGRec(1,HQV_SRC_FETCH_LINE, (((lpMPGDevice->dwWidth>>3)-1)<<16) | (lpMPGDevice->dwHeight-1) );
+                        }
+                Macro_VidREGRec(1, HQV_SRC_STRIDE, (lpMPGDevice->dwPitch>>1)<<0x10 | (lpMPGDevice->dwPitch));
+                Macro_VidREGRec(1, HQV_DST_STRIDE, lpMPGDevice->dwPitch << 1);
+                    }
+//BC9D
+            if (!dwVideoFlag & MPEG_USE_HW_FLIP /* 0x40000 */)
+            {
+                Macro_VidREGRec( 1, HQV_CONTROL, dwHQVCtl );
+                }
+            
+            }
+        else //BDB0
+                {
+            if (lpDPFsrc->dwFourCC == FOURCC_IYUV)
+                    {
+                if (dwVideoFlag & VIDEO_1_INUSE )
+                            {
+                    Macro_VidREGRec(1,V1_STRIDE, lpMPGDevice->dwPitch<<16 | lpMPGDevice->dwPitch);
+                            }
+                            else
+                            {
+                    Macro_VidREGRec(1,V3_STRIDE, lpMPGDevice->dwPitch<<16 | lpMPGDevice->dwPitch);
+                    }                        
+
+                //   be0d
+                }
+                else
+                {
+                if (!dwVideoFlag & VIDEO_1_INUSE )
+                    {
+                    dwSrcPitch |= dwSrcPitch<<16;
+                    Macro_VidREGRec(1, V3_STRIDE, dwSrcPitch);
+                    }
+                    else
+                    {
+                    dwSrcPitch |= dwSrcPitch<<16;
+                    Macro_VidREGRec(1, V1_STRIDE, dwSrcPitch);
+               }
+            }
+        }
+
+//ac9d
+
+		if (dwVideoFlag & VIDEO_1_INUSE )
+                        {
+			if  (((gVIAGraphicInfo.Screen[ScrnIndex].dwDVIOn)||(gVIAGraphicInfo.Screen[ScrnIndex].dwLCDOn))&&(gVIAGraphicInfo.Screen[ScrnIndex].dwExpand))
+			{//fd
+				Macro_VidREGRec(1, V1_WIN_END_Y,  ((rDest.right-1)<<16) + (rDest.bottom*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelHeight)/gVIAGraphicInfo.Screen[ScrnIndex].dwHeight));
+				if (rDest.top)
+					Macro_VidREGRec(1, V1_WIN_START_Y, (rDest.left<<16) + (rDest.top*(gVIAGraphicInfo.Screen[ScrnIndex].dwPanelHeight)/gVIAGraphicInfo.Screen[ScrnIndex].dwHeight));
+				else
+					Macro_VidREGRec(1, V1_WIN_START_Y, (rDest.left<<16));
+                                
+                        }
+			else
+			{//d5
+				Macro_VidREGRec(1, V1_WIN_END_Y, ((rDest.right-1)<<16) + (rDest.bottom-1));
+
+				if (rDest.top)
+					Macro_VidREGRec(1, V1_WIN_START_Y, (rDest.left<<16) + (rDest.top));
+				else
+					Macro_VidREGRec(1, V1_WIN_START_Y, (rDest.left<<16));
+                    }
+                }
+		else
+		{ //bb60
+			Macro_VidREGRec(1, V3_WIN_END_Y, (rDest.right-1)<<16 | (rDest.bottom-1));
+
+			if (rDest.top)
+				Macro_VidREGRec(1, V3_WIN_START_Y, (rDest.left<<16) | rDest.top );
+			else
+				Macro_VidREGRec(1, V3_WIN_START_Y, (rDest.left<<16) );
+            }
+
+//ad0f
+        if ( DDOVER_HQVCalcZoomWidth(dwVideoFlag, srcWidth , dstModifiedWidth,
+                                  &zoomCtl, &miniCtl, &dwHQVfilterCtl, &dwHQVminiCtl,&dwHQVzoomflagH) == PI_ERR )
+//		if ( DDOVER_HQVCalcZoomWidth(dwVideoFlag, srcWidth, dstWidth, &zoomCtl, &miniCtl, &dwHQVfilterCtl, &dwHQVminiCtl, &dwHQVzoomflagH) == PI_ERR)
+		{
+			//baa0
+			dwFetch <<= 0x14;
+			if (dwVideoFlag & VIDEO_1_INUSE )
+			{
+				Macro_VidREGRec(1, V12_QWORD_PER_LINE, dwFetch);
+				Macro_VidREGRec(1, V_COMPOSE_MODE, dwCompose | V1_COMMAND_FIRE);
+        }
+        else 
+        {
+				Macro_VidREGRec(1, V3_ALPHA_QWORD_PER_LINE, dwFetch | (VIDInD(V3_ALPHA_QWORD_PER_LINE) & 0xc00fffff));
+				Macro_VidREGRec(1, V_COMPOSE_MODE, dwCompose | V3_COMMAND_FIRE);
+			}
+			Macro_VidREGFlush();
+			return PI_ERR;
+		}
+//ad56
+
+		dwFetch <<= 0x14;
+    if (dwVideoFlag & VIDEO_1_INUSE)
+            {                
+        Macro_VidREGRec(1, V12_QWORD_PER_LINE, dwFetch);
+    }
+    else
+    {
+        Macro_VidREGRec(1, V3_ALPHA_QWORD_PER_LINE, dwFetch | (VIDInD(V3_ALPHA_QWORD_PER_LINE) & 0xc00fffff) );
+    }
+
+    DDOver_GetDisplayCount(dwVideoFlag,lpDPFsrc,srcWidth,&dwDisplayCountW);
+        
+    if (lpDPFsrc->dwFourCC == FOURCC_IYUV)
+                {
+                    if (dwVideoFlag & VIDEO_1_INUSE)    
+                    {
+/* TIDY IFS */
+            if ( dwVideoFlag & VIDEO_HQV_INUSE )
+                Macro_VidREGRec(1, V1_SOURCE_HEIGHT, (lpMPGDevice->dwHeight)<<16 | dwDisplayCountW);
+            else
+                        {
+                if (overlayRecordV1.dwMPEGDeinterlaceMode == 1 )
+                    Macro_VidREGRec(1, V1_SOURCE_HEIGHT, (lpMPGDevice->dwHeight>>1)<<16 | dwDisplayCountW);
+                else
+                    Macro_VidREGRec(1, V1_SOURCE_HEIGHT, (lpMPGDevice->dwHeight)<<16 | dwDisplayCountW);
+                        }
+                    }
+                    else
+            Macro_VidREGRec(1, V3_SOURCE_WIDTH, dwDisplayCountW); /* check shouldnt this say SOURCE_HEIGHT */
+    }
+    else
+                    {
+        if (dwVideoFlag & VIDEO_1_INUSE )
+                        {
+            if (dwVideoFlag & VIDEO_HQV_INUSE )
+                Macro_VidREGRec(1,V1_SOURCE_HEIGHT, (srcHeight << 16)| dwDisplayCountW);
+            else
+            {
+                if (overlayRecordV1.dwMPEGDeinterlaceMode == 1 )
+                    Macro_VidREGRec(1,V1_SOURCE_HEIGHT, (srcHeight >> 1)<<16 | dwDisplayCountW);
+                else
+                    Macro_VidREGRec(1,V1_SOURCE_HEIGHT, (srcHeight)<<16 | dwDisplayCountW);
+                    }
+                }
+                else
+            Macro_VidREGRec(1, V3_SOURCE_WIDTH, dwDisplayCountW);
+    }
+    //add2
+    
+    if ( DDOVER_HQVCalcZoomHeight(srcHeight,dstModifiedHeight,&zoomCtl,&miniCtl, &dwHQVfilterCtl, &dwHQVminiCtl ,&dwHQVzoomflagV) == PI_ERR )        
+//		if ( DDOVER_HQVCalcZoomHeight(srcHeight, dstHeight,&zoomCtl,&miniCtl,&dwHQVfilterCtl, &dwHQVminiCtl ,&dwHQVzoomflagV) == PI_ERR )
+                {
+        if ( dwVideoFlag & VIDEO_1_INUSE )
+                        {
+            Macro_VidREGRec(1, V_COMPOSE_MODE, dwCompose|V1_COMMAND_FIRE);
+                        }    
+                        else
+                        {
+            Macro_VidREGRec(1, V_COMPOSE_MODE, dwCompose|V3_COMMAND_FIRE);
+                        }
+        Macro_VidREGFlush();
+        return PI_ERR;
+                    }
+    
+    if (dwVideoFlag & VIDEO_HQV_INUSE )
+                    {
+        if (dwVideoFlag & VIDEO_1_INUSE )
+                        {
+            switch (DispatchVGARevisionID() )
+                            {
+				case VIA_REVISION_CLECX:
+					Macro_VidREGRec(1, V_FIFO_CONTROL, V1_FIFO_DEPTH64 | V1_FIFO_PRETHRESHOLD56 | V1_FIFO_THRESHOLD56 );
+                                    break;
+                                default:
+					if (!gdwUseExtendedFIFO)
+						Macro_VidREGRec(1,V_FIFO_CONTROL, V1_FIFO_DEPTH32 | V1_FIFO_THRESHOLD16 | V1_FIFO_PRETHRESHOLD29 );
+					else
+						Macro_VidREGRec(1,V_FIFO_CONTROL, V1_FIFO_DEPTH48 | V1_FIFO_THRESHOLD40 | V1_FIFO_PRETHRESHOLD40 );
+                                    break;
+                            }
+                        }
+        else //b8e7
+                        {
+            switch (DispatchVGARevisionID() )
+                            {
+				case VIA_REVISION_CLECX:
+					Macro_VidREGRec(1,ALPHA_V3_FIFO_CONTROL,(VIDInD(0x78)&0xffff0000) | V3_FIFO_DEPTH64 | V3_FIFO_THRESHOLD48|V3_FIFO_THRESHOLD8 ); /* CHECK FLAGS */
+					Macro_VidREGRec(1,ALPHA_V3_PREFIFO_CONTROL,(VIDInD(0x68)&0xffffff80)| V3_FIFO_PRETHRESHOLD56);
+                                    break;
+                                default:
+					Macro_VidREGRec(1,ALPHA_V3_FIFO_CONTROL,(VIDInD(0x78)&0xffff0000) | V3_FIFO_THRESHOLD16 | V3_FIFO_DEPTH32 );
+                    Macro_VidREGRec(1,ALPHA_V3_PREFIFO_CONTROL,(VIDInD(0x68)&0xffffff80) | 0x10); /* CHECK FLAGS */ 
+                                    break;
+                            }
+                        }
+                    }
+            else
+//b960
+            {
+        if (srcWidth <= 0x50)
+        {// b98d
+            if (dwVideoFlag & VIDEO_1_INUSE )
+                            {
+                Macro_VidREGRec(1, V_FIFO_CONTROL, V1_FIFO_DEPTH16 );
+                            }
+                            else
+                            {
+                Macro_VidREGRec(1, ALPHA_V3_FIFO_CONTROL,(VIDInD(0x78)&0xffff0000) | V3_FIFO_DEPTH16 );
+                    }
+                }
+        else // b967
+                {
+            if (dwVideoFlag & VIDEO_1_INUSE)
+                    {
+                switch (DispatchVGARevisionID() )
+                {
+					case VIA_REVISION_CLECX:
+						Macro_VidREGRec(1, V_FIFO_CONTROL, 0x3800383F);
+						break;
+					default:
+						Macro_VidREGRec(1, V_FIFO_CONTROL, 0x0C00080F);
+						break;
+                }
+                    }
+                    else
+                    {
+                switch (DispatchVGARevisionID() )
+                        {
+					case VIA_REVISION_CLECX:
+						Macro_VidREGRec(1,ALPHA_V3_FIFO_CONTROL,(VIDInD(0x78)&0xffff0000)|0x383f);
+                        Macro_VidREGRec(1,ALPHA_V3_PREFIFO_CONTROL,(VIDInD(0x68)&0xffffff80)|0x38);
+                                break;
+                            default:
+						Macro_VidREGRec(1,ALPHA_V3_FIFO_CONTROL,(VIDInD(0x78)&0xffff0000)|0x80f);
+						Macro_VidREGRec(1,ALPHA_V3_PREFIFO_CONTROL,(VIDInD(0x68)&0xffffff80)|0x10);
+                            break;
+                        }                
+                    }
+                }
+            }
+//ae3f
+//ae41
+    if (!dwVideoFlag & VIDEO_HQV_INUSE)
+        {
+//hmmm is that the right member? (displaypictstruct)?
+        if ((dwVideoFlag & MPEG_USE_HW_FLIP ) &&
+            ((overlayRecordV1.dwDisplayPictStruct-1 <= 1) ||
+             overlayRecordV1.dwMPEGDeinterlaceMode == 1 ))
+            {
+            //b893
+            if (zoomCtl & 0x3ff)
+            {//b8bb
+					zoomCtl = 0x8000 | ((zoomCtl & 0x3ff)>>1) | (zoomCtl & 0xfffffc00);
+				}
+				else
+                {
+					zoomCtl = 0x8000 | 0x200 | (zoomCtl & 0xfffffc00);
+				}
+                }
+			//ae7b
+		}
+//ae7b
+                
+		if (dwVideoFlag & VIDEO_HQV_INUSE )
+		{//ae87
+/* CHECK AND FIX **
+			if ( gVIAGraphicInfo.Screen[ScrnIndex].NoHQV_VFilter )
+                {
+                dwHQVfilterCtl &= ~HQV_V_LOWPASS_4TAP;
+                DBG_DD("Upd_MPEG: No MPEG HQV vertical filter\n");
+			}//aea5
+*/
+			Macro_VidREGRec(1, HQV_MINIFY_CONTROL, dwHQVminiCtl);
+            Macro_VidREGRec(1, HQV_FILTER_CONTROL, dwHQVfilterCtl);
+       
+			miniCtl = 0;
+       
+            if (!dwHQVzoomflagH && !dwHQVzoomflagV)
+            {
+//b7cc
+                if (overlayRecordV1.dwDisplayPictStruct-1 <= 1 ||
+                    overlayRecordV1.dwMPEGDeinterlaceMode == 1)
+                {
+                    miniCtl = V1_YCBCR_INTERPOLY | V1_Y_INTERPOLY;
+                if (dwVideoFlag & VIDEO_1_INUSE)
+                {
+                        Macro_VidREGRec(1, V1_MINI_CONTROL, V1_YCBCR_INTERPOLY | V1_Y_INTERPOLY);
+                        Macro_VidREGRec(1, V1_ZOOM_CONTROL, 0);
+                }
+                else
+                {
+                        Macro_VidREGRec(1, V3_MINI_CONTROL, V3_YCBCR_INTERPOLY | V3_Y_INTERPOLY );
+                        Macro_VidREGRec(1, V3_ZOOM_CONTROL, 0);
+                    }
+                }
+            }
+            else
+            {
+                if (dwHQVzoomflagH)
+                {
+                    miniCtl = V1_X_INTERPOLY;
+                    dwTmp = zoomCtl & 0xffff0000;
+                }
+
+                if (dwHQVzoomflagV)
+                {
+                    miniCtl |= (V1_Y_INTERPOLY|V1_YCBCR_INTERPOLY);
+                    dwTmp |= zoomCtl & 0x0000ffff;
+                }
+                else
+                {
+					if (overlayRecordV1.dwDisplayPictStruct-1 <= 1 ||
+						overlayRecordV1.dwMPEGDeinterlaceMode == 1)
+					{
+						miniCtl |= 5;
+                }
+            }
+//af1a
+                if (gdwUseExtendedFIFO)
+            {
+                    miniCtl &= 0xfffffffe;
+            }
+            
+                if ( dwVideoFlag & VIDEO_1_INUSE )
+                {
+                    Macro_VidREGRec(1,V1_MINI_CONTROL, miniCtl);
+                    Macro_VidREGRec(1,V1_ZOOM_CONTROL, dwTmp);
+        }
+        else
+        {
+                    Macro_VidREGRec(1,V3_MINI_CONTROL, miniCtl);
+                    Macro_VidREGRec(1,V3_ZOOM_CONTROL,dwTmp);
+                }
+
+            }
+
+		}
+		else
+		{ //b850
+            if (dwVideoFlag & VIDEO_1_INUSE)
+            {
+               Macro_VidREGRec(1,V1_MINI_CONTROL, miniCtl);
+                Macro_VidREGRec(1,V1_ZOOM_CONTROL, zoomCtl);
+            }//b874
+            else
+            {
+                Macro_VidREGRec(1,V3_MINI_CONTROL, miniCtl);
+                Macro_VidREGRec(1,V3_ZOOM_CONTROL, zoomCtl);
+            }
+        }
+
+        // Colorkey
+        if (dwColorKey) 
+        {
+            DBG_DD("Overlay colorkey= low:%08lx high:%08lx\n", dwKeyLow, dwKeyHigh);
+
+            dwKeyLow &= 0x00FFFFFF;
+            
+            if (lpVideoHWDifference->dwSupportTwoColorKey == VID_HWDIFF_TRUE)
+            {                    
+                dwCompose = (dwCompose & ~0x0f) | SELECT_VIDEO_IF_COLOR_KEY | SELECT_VIDEO3_IF_COLOR_KEY;                
+            }
+            else
+            {
+                dwCompose = (dwCompose & ~0x0f) | SELECT_VIDEO_IF_COLOR_KEY;
+            }
+            
+            /*Modified for SAMM Mode*/
+            if (ScrnIndex == 1)
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,SND_COLOR_KEY, dwKeyLow);
+                dwCompose |= SECOND_DISPLAY_COLOR_KEY_ENABLE;
+                if ( dwVideoFlag & VIDEO_1_INUSE )
+                {
+                    dwVidCtl |= V1_ON_SND_DISPLAY;
+                } 
+                else 
+                {
+                    dwVidCtl |= V3_ON_SND_DISPLAY;
+                }
+            }
+            else
+            {    
+                if (lpVideoHWDifference->dwSupportTwoColorKey == VID_HWDIFF_TRUE)
+                {                    
+            if (dwVideoFlag & VIDEO_1_INUSE)
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_COLOR_KEY, dwKeyLow);
+            }
+            else
+            {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_COLOR_KEY, dwKeyLow);
+            }
+                }
+                else
+            {
+                    Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_COLOR_KEY, dwKeyLow);    
+            }
+        }
+        }/* Colorkey*/
+
+        DBG_DD("Compose %08lx\n",dwCompose);
+
+        if (dwChromaKey) {
+            DBG_DD("Overlay Chromakey= low:%08lx high:%08lx\n", dwKeyLow, dwKeyHigh);
+
+            dwChromaLow  &= CHROMA_KEY_LOW;
+            dwChromaHigh &= CHROMA_KEY_HIGH;
+
+            dwChromaLow  |= (VIDInD(V_CHROMAKEY_LOW)&(~CHROMA_KEY_LOW));
+            dwChromaHigh |= (VIDInD(V_CHROMAKEY_HIGH)&(~CHROMA_KEY_HIGH));
+
+            // for Chroma Key
+            if (lpDPFsrc->dwFlags & DDPF_FOURCC)
+            {
+                    switch (lpDPFsrc->dwFourCC) {
+                    case FOURCC_YV12:
+                            //to be continued...
+                            break;
+                    case FOURCC_YUY2:
+                            //to be continued...
+                            break;
+                    default:
+                            //TOINT3;
+                            break;
+                    }
+            }
+            else if (lpDPFsrc->dwFlags & DDPF_RGB)
+            {
+                    unsigned long dwtmpLowR;
+                    unsigned long dwtmpLowG;
+                    unsigned long dwtmpLowB;
+                    unsigned long dwtmpChromaLow;
+                    unsigned long dwtmpHighR;
+                    unsigned long dwtmpHighG;
+                    unsigned long dwtmpHighB;
+                    unsigned long dwtmpChromaHigh;
+
+                    switch (lpDPFsrc->dwRGBBitCount) {
+                    case 16:
+                            if (lpDPFsrc->dwGBitMask==0x07E0) //RGB16(5:6:5)
+                            {
+                                    dwtmpLowR = (((dwChromaLow >> 11) << 3) | ((dwChromaLow >> 13) & 0x07)) & 0xFF;
+                                    dwtmpLowG = (((dwChromaLow >> 5) << 2) | ((dwChromaLow >> 9) & 0x03)) & 0xFF;
+
+                                    dwtmpHighR = (((dwChromaHigh >> 11) << 3) | ((dwChromaHigh >> 13) & 0x07)) & 0xFF;
+                                    dwtmpHighG = (((dwChromaHigh >> 5) << 2) | ((dwChromaHigh >> 9) & 0x03)) & 0xFF;
+                            }
+                            else //RGB15(5:5:5)
+                            {
+                                    dwtmpLowR = (((dwChromaLow >> 10) << 3) | ((dwChromaLow >> 12) & 0x07)) & 0xFF;
+                                    dwtmpLowG = (((dwChromaLow >> 5) << 3) | ((dwChromaLow >> 7) & 0x07)) & 0xFF;
+
+                                    dwtmpHighR = (((dwChromaHigh >> 10) << 3) | ((dwChromaHigh >> 12) & 0x07)) & 0xFF;
+                                    dwtmpHighG = (((dwChromaHigh >> 5) << 3) | ((dwChromaHigh >> 7) & 0x07)) & 0xFF;
+                            }
+                            dwtmpLowB = (((dwChromaLow << 3) | (dwChromaLow >> 2)) & 0x07) & 0xFF;
+                            dwtmpChromaLow = (dwtmpLowG << 16) | (dwtmpLowR << 8) | dwtmpLowB;
+                            dwChromaLow = ((dwChromaLow >> 24) << 24) | dwtmpChromaLow;
+
+                            dwtmpHighB = (((dwChromaHigh << 3) | (dwChromaHigh >> 2)) & 0x07) & 0xFF;
+                            dwtmpChromaHigh = (dwtmpHighG << 16) | (dwtmpHighR << 8) | dwtmpHighB;
+                            dwChromaHigh = ((dwChromaHigh >> 24) << 24) | dwtmpChromaHigh;
+                            break;
+
+                    case 32: //32 bit RGB
+                            dwtmpLowR = (dwChromaLow >> 16) & 0xFF;
+                            dwtmpLowG = (dwChromaLow >> 8) & 0xFF;
+                            dwtmpLowB = dwChromaLow & 0xFF;
+                            dwtmpChromaLow = (dwtmpLowG << 16) | (dwtmpLowR << 8) | dwtmpLowB;
+                            dwChromaLow = ((dwChromaLow >> 24) << 24) | dwtmpChromaLow;
+
+                            dwtmpHighR = (dwChromaHigh >> 16) & 0xFF;
+                            dwtmpHighG = (dwChromaHigh >> 8) & 0xFF;
+                            dwtmpHighB = dwChromaHigh & 0xFF;
+                            dwtmpChromaHigh = (dwtmpHighG << 16) | (dwtmpHighR << 8) | dwtmpHighB;
+                            dwChromaHigh = ((dwChromaHigh >> 24) << 24) | dwtmpChromaHigh;
+                            break;
+
+                    default:
+                            //TOINT3;
+                            break;
+                    }
+            }//End of DDPF_FOURCC
+
+            Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_CHROMAKEY_HIGH,dwChromaHigh);
+            if (dwVideoFlag & VIDEO_1_INUSE)
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_CHROMAKEY_LOW, dwChromaLow);
+                //Temporarily solve the H/W Interpolation error when using Chroma Key
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V1_MINI_CONTROL, miniCtl & 0xFFFFFFF8);
+            }
+            else
+            {
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V_CHROMAKEY_LOW, dwChromaLow|V_CHROMAKEY_V3);
+                Macro_VidREGRec(VIDREGREC_SAVE_REGISTER,V3_MINI_CONTROL, miniCtl & 0xFFFFFFF8);
+            }
+
+            //Modified for select video if (color key & chroma key)
+            if (dwCompose==SELECT_VIDEO_IF_COLOR_KEY)
+               dwCompose = SELECT_VIDEO_IF_COLOR_KEY | SELECT_VIDEO_IF_CHROMA_KEY;
+            else
+               dwCompose = (dwCompose & ~0x0f) | SELECT_VIDEO_IF_CHROMA_KEY;
+        }
+
+/* CHECK FLAGS */
+        if (lpVideoControl->dwCompose & 0x02200000 )
+        {
+			dwCompose &= ~COMPOSE_V3_TOP;
+        }
+        else if (lpVideoControl->dwCompose & 0x01100000 )
+		{
+            dwCompose |= COMPOSE_V3_TOP;
+		}
+
+	/* CHECK AND FIX ** 
+		if (lpVideoControl->MPEGOnScreen1 == 1)
+		{//b48a
+			DBG_DD("//Upd MPEG: V1_ON_SND_DISPLAY!!\n");
+			dwVidCtl |= V1_ON_SND_DISPLAY;
+            dwCompose |= SECOND_DISPLAY_COLOR_KEY_ENABLE;
+            dwCompose |= COMPOSE_V3_TOP;
+        }
+		else */
+		{
+			DBG_DD("//Upd MPEG: V1_ON_CRT!!\n");
+
+			dwVidCtl &= ~V1_ON_SND_DISPLAY;
+			dwCompose &= ~SECOND_DISPLAY_COLOR_KEY_ENABLE;
+
+			/* CHECK AND FIX **
+			if (lpVideoControl->Cap0OnScreen1)
+        {
+				Macro_VidREGRec(1, V1_CONTROL, (dwVidCtl & ~V1_SWAP_HW_HQV ) | (V1_ON_SND_DISPLAY|V1_SWAP_HW_CAPTURE));
+				dwCompose |= SECOND_DISPLAY_COLOR_KEY_ENABLE|COMPOSE_V3_TOP;
+			}
+			else */
+
+			{//b45b
+				Macro_VidREGRec(1, V1_CONTROL, dwVidCtl);
+			}
+
+			dwCompose |= V1_COMMAND_FIRE;
+		}
+		//b10b
+		DBG_DD("dwVideoFlag %08lx\n", dwVideoFlag);
+		DBG_DD("MPEG_ON %d\n", MPEG_ON);
+			
+		if ( dwVideoFlag & VIDEO_HQV_INUSE )
+            {
+			if (!MPEG_ON && !(dwVideoFlag & MPEG_USE_HW_FLIP))
+                //b121
+            {//b261
+                DBG_DD("1\n");
+                
+                Macro_VidREGFlush();
+                if (lpVideoHWDifference->dwHQVInitPatch)
+                {
+                    DBG_DD("1a\n");
+                    WaitHQVFlipClear((dwHQVCtl | HQV_FLIP_STATUS ) & ~(HQV_ENABLE|HQV_SW_FLIP));
+                    VIDOutD(HQV_CONTROL, dwHQVCtl);
+                    WaitHQVFlip();
+                    
+                    WaitHQVFlipClear((dwHQVCtl | HQV_FLIP_STATUS) & ~(HQV_ENABLE|HQV_SW_FLIP));
+                    VIDOutD(HQV_CONTROL, dwHQVCtl);
+                    WaitHQVFlip();
+                }
+                else
+                {
+                    DBG_DD("1b\n");
+                    VIDOutD(HQV_CONTROL, dwHQVCtl & ~HQV_SW_FLIP );
+                    VIDOutD(HQV_CONTROL, dwHQVCtl | HQV_SW_FLIP );
+                    WaitHQVFlip();
+                }
+                
+                if ( dwVideoFlag & VIDEO_1_INUSE )
+                {
+                    DBG_DD("1c\n");
+                    VIDOutD(V1_CONTROL, dwVidCtl);
+                    VIDOutD(V_COMPOSE_MODE, dwCompose | V1_COMMAND_FIRE);
+                    
+                    if (gdwUseExtendedFIFO)
+                    {
+                        DBG_DD("1d\n");
+                        WaitVBI();
+                        outb(0x14, 0x3c4);
+                        outb(0x2f, 0x3c5);
+                        outb(0x16, 0x3c4);
+                        outb((Save_3C4_16 & 0xFFFFFFF0) | 0x14, 0x3c5);
+                        outb(0x18,0x3c4);
+                        outb(0x56,0x3c5);
+                    }
+                }
+                else //b38d
+                {
+                    DBG_DD("1e\n");
+                    VIDOutD(V3_CONTROL, dwVidCtl);
+                    VIDOutD(V_COMPOSE_MODE, dwCompose | V3_COMMAND_FIRE);
+                }
+                DBG_DD("1f\n");
+				
+				//>>b1d0
+            }
+            else
+            {
+				DBG_DD("2\n");
+				//b12d
+				if (lpVideoHWDifference->dwHQVInitPatch)
+				{//b230
+					VIDOutD(HQV_CONTROL, dwHQVCtl & ~HQV_SW_FLIP );
+					VIDOutD(HQV_CONTROL, dwHQVCtl | HQV_FLIP_STATUS | HQV_SUBPIC_FLIP );
+					WaitHQVFlip();
+				}//b13b
+                
+                DBG_DD("3\n");
+                
+                if (dwVideoFlag & VIDEO_1_INUSE )
+                {
+                    Macro_VidREGRec(1,V1_CONTROL, dwVidCtl);
+                    Macro_VidREGRec(1,V_COMPOSE_MODE, dwCompose | V1_COMMAND_FIRE );
+                }
+                else //b20d
+                {
+                    Macro_VidREGRec(1,V3_CONTROL, dwVidCtl);
+                    Macro_VidREGRec(1,V_COMPOSE_MODE, dwCompose | V3_COMMAND_FIRE );
+                }//b162
+                DBG_DD("4\n");
+                
+                Macro_VidREGRec(1,HQV_CONTROL, dwHQVCtl | HQV_FLIP_STATUS );
+                Macro_VidREGFlush();                
+                DBG_DD("5\n");
+                
+                if (dwVideoFlag & MPEG_USE_HW_FLIP)
+                {
+                    if (overlayRecordV1.dwMpegDecoded)
+                    {//b206
+                        MPEGFlipCurrentFrame();
+                        //>>b1d0
+        }
+        else
+        {
+            if (dwVideoFlag & VIDEO_1_INUSE)
+            {
+                            VIDOutD(V_COMPOSE_MODE, dwCompose & ~V1_COMMAND_FIRE);
+                        }
+                        else
+                        {//b1fa
+                            VIDOutD(V_COMPOSE_MODE, dwCompose & ~V3_COMMAND_FIRE);
+                        }
+                        // >> b1d0
+                    //
+                    //
+                        DBG_DD("Macro_VidREGFlush:%08x %08lx\n",0x98, VIDInD(V_COMPOSE_MODE));
+//                  Macro_VidREGFlush();
+                    }
+                }
+			}//b1d0
+			//>>b1d0
+            }
+            else
+		{//b3f0
+			if (dwVideoFlag & VIDEO_1_INUSE)
+            {
+				Macro_VidREGRec(1, V1_CONTROL, dwVidCtl);
+				dwCompose |= V1_COMMAND_FIRE;
+            }
+			else //b43c
+			{
+				Macro_VidREGRec(1,V3_CONTROL,dwVidCtl);
+				dwCompose |= V3_COMMAND_FIRE;
+			}
+
+			Macro_VidREGRec(1, V_COMPOSE_MODE, dwCompose);
+            Macro_VidREGFlush();
+
+			if (dwVideoFlag & MPEG_USE_HW_FLIP)
+			{
+				MPEGFlipCurrentFrame();
+        }
+    }
+//b1d0
+        MPEG_ON = 1;
+    }
+//c200
+    else
+    {
+        DBG_DD("//   :Hide overlay\n");
+
+        if (lpVideoHWDifference->dwHQVDisablePatch)
+        {
+            outb(0x2E, 0x3C4);
+            outb(0xEF, 0x3C5);
+        }
+        
+        Macro_VidREGRec(1, V_FIFO_CONTROL, V1_FIFO_DEPTH16 | V1_FIFO_THRESHOLD8 | V1_FIFO_PRETHRESHOLD12 );
+        Macro_VidREGRec(1, ALPHA_V3_FIFO_CONTROL, V3_FIFO_DEPTH32 | V3_FIFO_THRESHOLD24 | ALPHA_FIFO_THRESHOLD4 | ALPHA_FIFO_DEPTH8 );
+
+        if (dwVideoFlag & VIDEO_HQV_INUSE)
+        {
+            Macro_VidREGRec(1,SUBP_CONTROL_STRIDE, VIDInD(SUBP_CONTROL_STRIDE) & ~SUBP_HQV_ENABLE );
+            Macro_VidREGRec(1,HQV_CONTROL, VIDInD(HQV_CONTROL) & ~HQV_ENABLE );
+        }
+
+        if (dwVideoFlag & VIDEO_1_INUSE)
+        {
+            if ( gVIAGraphicInfo.Screen[ScrnIndex].dwWidth > 0x400 )
+            {
+                Macro_VidREGRec(1, V1_CONTROL, (VIDInD(V1_CONTROL) & ~V1_ENABLE ) | V1_FIFO_EXTENDED );
+        }
+        else
+        {
+                Macro_VidREGRec(1, V1_CONTROL, VIDInD(V1_CONTROL) & ~V1_ENABLE);
+            }
+
+            Macro_VidREGRec(1, V_COMPOSE_MODE, VIDInD(V_COMPOSE_MODE) | V1_COMMAND_FIRE);
+        }
+        else
+        {
+            Macro_VidREGRec(1, V3_CONTROL, VIDInD(V3_CONTROL) & ~V3_ENABLE );
+            Macro_VidREGRec(1, V_COMPOSE_MODE, VIDInD(V_COMPOSE_MODE)|V3_COMMAND_FIRE );
+        }
+        
+        Macro_VidREGFlush();        
+
+        if ( lpVideoHWDifference->dwHQVDisablePatch )
+        {
+            outb(0x2e, 0x3c4);
+            outb(0xff, 0x3c5);
+        }          
+    }  
+
+//b1da
+    return PI_OK;    
+}
+
+
+/************************************************************************/
+
+/*
+ * Driver entry point
+ */
+unsigned long VIADriverProc(unsigned long wAction, void * lpParam)
+{
+    unsigned long dwRet = PI_ERR;
+
+    switch ( wAction )
+    {
+        /* Surface functions      */
+        case CREATESURFACE :
+            dwRet = CreateSurface( (LPDDSURFACEDESC) lpParam);
+            break;
+
+        case DESTROYSURFACE :
+            dwRet = DestroySurface((LPDDSURFACEDESC) lpParam);
+            break;
+
+        case LOCKSURFACE :
+            dwRet = LockSurface((LPDDLOCK) lpParam);
+            break;
+
+        case UNLOCKSURFACE :
+            break;
+
+        case UPDATEOVERLAY :
+            dwRet = UpdateOverlay( (LPDDUPDATEOVERLAY) lpParam);
+            break;
+
+        case FLIP :
+            dwRet = Flip(*((unsigned long *)lpParam) );
+            break;
+
+        /* Video Control functions      */
+        case SETALPHAWIN :
+            VIAAlphaWin( (LPALPHACTRL)lpParam);
+            dwRet = PI_OK;
+            break;
+
+        case HQVCONTROL :
+             dwRet = HQVControl( (LPVIAVIDCTRL)lpParam );
+             break;
+
+        /* Video Decoder and Tuner functions */
+        /* Remove video decoder func here
+         * the related func can be called directly.
+         */
+
+        case SETPORTATTRIBUTE :
+//            dwRet = VIASetPortAttribute( (LPVIASETPORTATTR) lpParam, via);
+            break;
+
+        case TUNER_DETECT :
+             dwRet = PI_OK;
+             break;
+
+        case TUNER_INIT :
+             dwRet = PI_OK;
+             break;
+
+        case TUNER_SETCHANNEL      :
+             
+             break;
+
+        /* Audio Chip Control          */
+        case AUDIOCONTROL           :
+             Audio_Control(lpParam);
+             break;
+
+        default :
+            DBG_DD("//    : Function not supported\n");
+            break;
+    }
+
+    return dwRet;
+
+
+} //VIADriverProc
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/ddmpeg.h linux-2.6.1-rc1-gentoo/drivers/media/video/ddmpeg.h
--- linux-2.6.0/drivers/media/video/ddmpeg.h	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/ddmpeg.h	2004-01-06 17:28:06.000000000 +0000
@@ -0,0 +1,477 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#ifndef _LINUX_VIDEO_H
+#define _LINUX_VIDEO_H
+
+#include "capture.h"
+/*#include "via_privIoctl.h"*/     /* for VIAGRAPHICINFO & custom ioctl command */
+
+/*
+ *  Overlay surfaces ( frame buffers ) we use
+ */
+#define NUM_FRAME_BUFFERS           8
+
+/*
+ * Alignment macro functions
+ */
+#define ALIGN_TO_32_BYTES(f)         (((f) + 31) & ~31)
+#define ALIGN_TO_16_BYTES(f)         (((f) + 15) & ~15)
+#define ALIGN_TO_256_BITS(f)         (((f) + 255) & ~255)
+#define ALIGN_TO_8_BYTES(f)          (((f) + 7) & ~7)
+#define ALIGN_TO_64_BITS(f)          (((f) + 63) & ~63)
+#define ENG_ALIGN_BYTE              ALIGN_TO_32_BYTES
+#define ENG_ALIGN_BIT               ALIGN_TO_256_BITS
+
+/*
+ * FOURCC definitions
+ */
+
+#define FOURCC_VIA     0x4E4B4C57  /*VIA*/
+#define FOURCC_SUBP    0x50425553  /*SUBP*/
+#define FOURCC_TV0     0x00325654  /*TV0*/
+#define FOURCC_TV1     0x00315654  /*TV1*/
+#define FOURCC_ALPHA   0x48504C41  /*ALPH*/
+#define FOURCC_YUY2    0x32595559  /*YUY2*/
+#define FOURCC_YV12    0x32315659  /*YV12*/
+#define FOURCC_Y211    0x31313259
+#define FOURCC_UYVY    0x59565955
+#define FOURCC_YVYU    0x55595659
+#define FOURCC_IYUV    0x56555949  /* #define FOURCC_IYUV   'VUYI'*/
+
+#define FOURCC_HQVMPEG 0x31565148  /*HQV1*/
+#define FOURCC_HQVTV0  0x33565148  /*HQV3*/
+#define FOURCC_HQVTV1  0x32565148  /*HQV2*/
+#define FOURCC_HQVSW   0x34565148  /*HQV4*/
+
+
+
+/*
+ * Actions for MPEG functions
+ */
+
+#define CREATEDRIVER               0x00
+#define DESTROYDRIVER              CREATEDRIVER +1
+#define CREATESURFACE              CREATEDRIVER +2
+#define DESTROYSURFACE             CREATEDRIVER +3
+#define LOCKSURFACE                CREATEDRIVER +4
+#define UNLOCKSURFACE              CREATEDRIVER +5
+#define UPDATEOVERLAY              CREATEDRIVER +6
+#define FLIP                       CREATEDRIVER +7  
+#define SETALPHAWIN                CREATEDRIVER +8
+#define BEGINPICTRE                CREATEDRIVER +9
+#define BEGINPICTURE               CREATEDRIVER +9
+#define ENDPICTURE                 CREATEDRIVER +10
+#define SLICERECEIVEDATA           CREATEDRIVER +11
+#define DRIVERPROC                 CREATEDRIVER +12
+#define DISPLAYCONTROL             CREATEDRIVER +13
+#define SUBPICTURE                 CREATEDRIVER +14
+#define SETDEINTERLACEMODE         CREATEDRIVER +15
+#define MPEGENABLE                 CREATEDRIVER +16  
+#define MPEGGETPICTYPE             CREATEDRIVER +17  
+#define FF_START                   CREATEDRIVER +18  
+#define FF_END                     CREATEDRIVER +19
+#define INITSURFACEMANAGER         CREATEDRIVER +20
+#define FREESURFACEMANAGER         CREATEDRIVER +21
+
+/*
+ * Actions for Capture functions  / XV standard functions
+ */
+
+#define PUTVIDEO                CREATEDRIVER +100
+#define PUTSTILL                CREATEDRIVER +101
+#define GETVIDEO                CREATEDRIVER +102
+#define GETSTILL                CREATEDRIVER +103
+#define STOPVIDEO               CREATEDRIVER +104
+#define SETPORTATTRIBUTE        CREATEDRIVER +105
+#define GETPORTATTRIBUTE        CREATEDRIVER +106
+#define SELECTCAPTUREPORT       CREATEDRIVER +107
+#define VIDEOCONTROL            CREATEDRIVER +108
+#define HQVCONTROL              CREATEDRIVER +109
+#define PUTIMAGE                CREATEDRIVER +110
+
+#define VDEC_DETECT             CREATEDRIVER +150
+#define VDEC_INIT               CREATEDRIVER +151
+#define TUNER_DETECT            CREATEDRIVER +152
+#define TUNER_INIT              CREATEDRIVER +153
+#define TUNER_SETTVBAND_CABLE   CREATEDRIVER +154
+#define TUNER_SETCHANNEL        CREATEDRIVER +155
+
+#define AUDIOCONTROL            CREATEDRIVER +170
+
+/*
+ * Define for Utility functions using XvPutImage.
+ */
+/* Primary ID */
+#define	UT_XV_FUNC_BIOS			0x11   /* Primary ID */
+#define	UT_XV_FUNC_DRIVER		0x12
+#define	UT_XV_FUNC_DEVICE		0x13
+#define	UT_XV_FUNC_PANEL		0x14
+#define	UT_XV_FUNC_TV			0x15
+#define	UT_XV_FUNC_GAMMA		0x16
+/* Secondary ID */
+#define	UT_XV_FUNC_BIOS_GetChipID			0x01    /* Get Chip ID */
+#define UT_XV_FUNC_BIOS_GetVersion			0x02    /* Get the version of the BIOS */
+#define	UT_XV_FUNC_BIOS_GetDate				0x03    /* Get the date (year, month, day) of the BIOS. */
+#define	UT_XV_FUNC_BIOS_GetVideoMemSizeMB	0x04    /* Get the video memory size, in MB */
+
+#define	UT_XV_FUNC_DRIVER_GetFileName			0x01
+#define	UT_XV_FUNC_DRIVER_GetFileVersion		0x02
+/* Return value */
+#define	UT_RESULT_OK			1    /* Return value */
+#define	UT_RESULT_FAIL			0
+#define	UT_RESULT_NO_FUNC		-1
+
+
+/*
+ * Structures for create surface
+ */
+typedef struct _DDSURFACEDESC
+{
+    unsigned long     dwSize;      /* size of the DDSURFACEDESC structure*/
+    unsigned long     dwFlags;     /* determines what fields are valid*/
+    unsigned long     dwHeight;    /* height of surface to be created*/
+    unsigned long     dwWidth;     /* width of input surface*/
+    unsigned long      lPitch;      /* distance to start of next line(return value)*/
+    unsigned long     dwBackBufferCount;     /* number of back buffers requested*/
+    void *    lpSurface;             /* pointer to the surface memory*/
+    unsigned long     dwColorSpaceLowValue;  /* low boundary of color space that is to*/
+                                     /* be treated as Color Key, inclusive*/
+    unsigned long     dwColorSpaceHighValue; /* high boundary of color space that is*/
+                                     /* to be treated as Color Key, inclusive*/
+    unsigned long     dwFourCC;              /* (FOURCC code)*/
+} DDSURFACEDESC;
+typedef DDSURFACEDESC * LPDDSURFACEDESC;
+
+
+/*
+ * Structures for SubPicture
+ */
+typedef struct _SUBDEVICE
+{
+ unsigned char * lpSUBOverlaySurface[2];   /*Max 2 Pointers to SUB Overlay Surface*/
+ unsigned long  dwSUBPhysicalAddr[2];     /*Max 2 Physical address to SUB Overlay Surface*/
+ unsigned long  dwPitch;                  /*SUB frame buffer pitch*/
+ unsigned long  gdwSUBSrcWidth;           /*SUB Source Width*/
+ unsigned long  gdwSUBSrcHeight;          /*SUB Source Height*/
+ unsigned long  gdwSUBDstWidth;           /*SUB Destination Width*/
+ unsigned long  gdwSUBDstHeight;          /*SUB Destination Height*/
+ unsigned long  gdwSUBDstLeft;            /*SUB Position : Left*/
+ unsigned long  gdwSUBDstTop;             /*SUB Position : Top*/
+}SUBDEVICE;
+typedef SUBDEVICE * LPSUBDEVICE;
+
+
+/*
+ * Structures for H/W mpeg decode
+ */
+typedef struct _MPGDEVICE
+{
+ unsigned char * lpVideoMemIO;             /* Pointer to Video Memory MAP IO */
+ unsigned char * lpMPEGOverlaySurface[NUM_FRAME_BUFFERS];/* Max 4 Pointers to MPEG Overlay Surface */
+ unsigned long  dwMPEGPhysicalAddr[NUM_FRAME_BUFFERS];  /* Max 4 Physical address to MPEG Overlay Surface */
+ unsigned long  dwWidth;                  /* MPEG coded_picture_width                                */
+ unsigned long  dwHeight;                 /* MPEG coded_picture_height                               */
+ unsigned long  dwPitch;                  /* MPEG frame buffer pitch                                 */
+ unsigned long  dwPageNum;                /* Frame buffer Number                                     */
+ unsigned char   byDeviceType;             /* Device type. Such as DEV_MPEG and DEV_SUBP              */
+ unsigned long  gdwSetBufferIndex;        /* Used to assigned buffer pointer in SetOverlayBuffer()   */
+ unsigned long  gdwMPGState;              /* MPG states                                              */
+ unsigned long  gdwSUBPState;             /* Sub Picture states                                      */
+ unsigned long  dwSubpPageNum;            /* SubPicture Frame buffer Number                          */
+ unsigned long  dwSUBPPitch;              /* SubPicture Pitch                                        */
+ unsigned long  gdwSUBPSrcLeft;           /* SubPicture Position : Left                              */
+ unsigned long  gdwSUBPSrcTop;            /* SubPicture Position : Top                               */
+ unsigned long  gdwSUBPSrcWidth;          /* SubPicture Source Width                                 */
+ unsigned long  gdwSUBPSrcHeight;         /* SubPicture Source Height                                */
+ unsigned long  gdwSUBPDisplayIndex;      /* Subpicture Display Index                                */
+ unsigned long  gdwMPGSrcWidth;           /* MPEG Source Width                                       */
+ unsigned long  gdwMPGSrcHeight;          /* MPEG Source Height                                      */
+ unsigned long  gdwMPGDstWidth;           /* MPEG Destination Width                                  */
+ unsigned long  gdwMPGDstHeight;          /* MPEG Destination Height                                 */
+ unsigned long  gdwMPGDstLeft;            /* MPEG Position : Left                                    */
+ unsigned long  gdwMPGDstTop;             /* MPEG Position : Top                                     */
+ unsigned long  dwDeinterlaceMode;        /* BOB / WEAVE                                             */
+ unsigned long  gdwSUBP_NotVisible;
+ unsigned long  dwMPEGYPhysicalAddr[NUM_FRAME_BUFFERS];   /* Physical address to MPEG Y Overlay Surface  */
+ unsigned long  dwMPEGCbPhysicalAddr[NUM_FRAME_BUFFERS];  /* Physical address to MPEG Cb Overlay Surface */
+ unsigned long  dwMPEGCrPhysicalAddr[NUM_FRAME_BUFFERS];  /* Physical address to MPEG Cr Overlay Surface */
+ unsigned long  dwMPEGDisplayIndex ;      /* Currently display index                     */
+ unsigned long  dwHQVAddr[3];             /* Physical address to HQV surface -- CLE_C0   */
+ /*unsigned long  dwHQVAddr[2];*/             /* Physical address to HQV surface             */
+ unsigned long  dwEnableErrorConcealment; /* For MPEG ErrorConcealment                   */
+ /* Chip Info */
+ unsigned long  dwVendorID;
+ unsigned long  dwDeviceID;
+ unsigned long  dwRevisionID;
+ unsigned long  dwSubVendorID;
+ unsigned long  dwSubDeviceID;
+}MPGDEVICE, * LPMPGDEVICE;
+
+
+/*
+ * Structures for S/W mpeg decode
+ */
+typedef struct _SWDEVICE
+{
+ unsigned char * lpSWOverlaySurface[2];   /* Max 2 Pointers to SW Overlay Surface*/
+ unsigned long  dwSWPhysicalAddr[2];     /*Max 2 Physical address to SW Overlay Surface */
+ unsigned long  dwSWCbPhysicalAddr[2];  /* Physical address to SW Cb Overlay Surface, for YV12 format use */
+ unsigned long  dwSWCrPhysicalAddr[2];  /* Physical address to SW Cr Overlay Surface, for YV12 format use */
+ unsigned long  dwHQVAddr[3];             /* Physical address to HQV surface -- CLE_C0   */
+ /*unsigned long  dwHQVAddr[2];*/			  /*Max 2 Physical address to SW HQV Overlay Surface*/
+ unsigned long  dwWidth;                  /*SW Source Width, not changed*/
+ unsigned long  dwHeight;                 /*SW Source Height, not changed*/
+ unsigned long  dwPitch;                  /*SW frame buffer pitch*/
+ unsigned long  gdwSWSrcWidth;           /*SW Source Width, changed if window is out of screen*/
+ unsigned long  gdwSWSrcHeight;          /*SW Source Height, changed if window is out of screen*/
+ unsigned long  gdwSWDstWidth;           /*SW Destination Width*/
+ unsigned long  gdwSWDstHeight;          /*SW Destination Height*/
+ unsigned long  gdwSWDstLeft;            /*SW Position : Left*/
+ unsigned long  gdwSWDstTop;             /*SW Position : Top*/
+ unsigned long  dwDeinterlaceMode;        /*BOB / WEAVE*/
+}SWDEVICE;
+typedef SWDEVICE * LPSWDEVICE;
+
+
+/* Device Type of MPGDEVICE */
+#define DEV_MPEG    0
+#define DEV_SUBP    1
+
+/* dwDecodePictStruct and dwDisplayPictStruct of VIAMPGSURFACE */
+#define VIA_PICT_STRUCT_TOP                 0x00000001
+#define VIA_PICT_STRUCT_BOTTOM              0x00000002
+#define VIA_PICT_STRUCT_FRAME               0x00000003
+
+/*
+ * Structures for LOCK surface
+ */
+
+typedef struct _DDLOCK
+{
+    unsigned long     dwVersion;             
+    unsigned long     dwFourCC;
+    unsigned long     dwPhysicalBase;
+    SUBDEVICE SubDev;
+    CAPDEVICE Capdev_TV0;
+    CAPDEVICE Capdev_TV1;
+    ALPHADEVICE Alphadev;
+	MPGDEVICE MPGDev;
+    SWDEVICE SWDevice;
+} DDLOCK;
+typedef DDLOCK * LPDDLOCK;
+
+
+/*
+ * structure for passing information to DDHAL UpdateOverlay fn
+ */
+typedef struct _RECTL
+{
+    unsigned long     left;
+    unsigned long     top;
+    unsigned long     right;
+    unsigned long     bottom;
+} RECTL;
+
+typedef struct _DDUPDATEOVERLAY
+{
+    RECTL     rDest;          /* dest rect */
+    RECTL     rSrc;           /* src rect */
+    unsigned long     dwFlags;        /* flags */
+    unsigned long     dwColorSpaceLowValue;
+    unsigned long     dwColorSpaceHighValue;
+    unsigned long     dwFourcc;
+} DDUPDATEOVERLAY;
+typedef DDUPDATEOVERLAY * LPDDUPDATEOVERLAY;
+
+typedef struct _ADJUSTFRAME
+{
+    int     x;
+    int     y;
+    unsigned long     dwFlags; /*Added for SAMM*/
+} ADJUSTFRAME;
+typedef ADJUSTFRAME * LPADJUSTFRAME;
+
+/* Definition for dwFlags */
+#define DDOVER_HIDE       0x00000001
+#define DDOVER_SHOW       0x00000002
+#define DDOVER_KEYDEST    0x00000004
+#define DDOVER_ENABLE     0x00000008
+#define DDOVER_CLIP       0x00000010
+#define DDOVER_ON_SND     0x80000000 /*Video is on Secondary Screen*/
+#define DDOVER_ON_PRI     0x00000000 /*Video is on Primary Screen*/
+
+/*
+ * Display each field of video port data individually without
+ * causing any jittery artifacts
+ */
+#define DDOVER_BOB                       	0x00200000l
+
+/*
+ * Indicates that bob/weave decisions should not be overridden by other
+ * interfaces.
+ */
+#define DDOVER_OVERRIDEBOBWEAVE			0x00400000l
+
+/*
+ * Indicates that the surface memory is composed of interleaved fields.
+ */
+#define DDOVER_INTERLEAVED			0x00800000l
+
+/*
+ * Indicates that bob will be performed using hardware rather than
+ * software or emulated.
+ */
+#define DDOVER_BOBHARDWARE			0x01000000l
+
+typedef struct _DDFLIP
+{
+   unsigned long dwBuffIndex;
+   unsigned long dwFlags;
+} DDFLIP;
+typedef DDFLIP * LPDDFLIP;
+
+typedef struct
+{
+    unsigned long   dwWidth;
+    unsigned long   dwHeight;
+    unsigned long   dwOffset;
+    unsigned long   dwUVoffset;
+    unsigned long   dwFlipTime;
+    unsigned long   dwFlipTag;
+    unsigned long   dwStartAddr;
+    unsigned long   dwV1OriWidth;
+    unsigned long   dwV1OriHeight;
+    unsigned long   dwV1OriPitch;
+    unsigned long   dwV1SrcWidth;
+    unsigned long   dwV1SrcHeight;
+    unsigned long   dwV1SrcLeft;
+    unsigned long   dwV1SrcRight;
+    unsigned long   dwV1SrcTop;
+    unsigned long   dwV1SrcBot;
+    unsigned long   dwSPWidth;
+    unsigned long   dwSPHeight;
+    unsigned long   dwSPLeft;
+    unsigned long   dwSPRight;
+    unsigned long   dwSPTop;
+    unsigned long   dwSPBot;
+    unsigned long   dwSPOffset;
+    unsigned long   dwSPstartAddr;
+    unsigned long   dwDisplayPictStruct;
+	unsigned long	dwDisplayBuffIndex;        /* Display buffer Index. 0 to ( dwBufferNumber -1) */
+    unsigned long   dwFetchAlignment;
+    unsigned long   dwSPPitch;
+    unsigned long   dwHQVAddr[3];          /* CLE_C0 */
+    /*unsigned long   dwHQVAddr[2];*/
+    unsigned long   dwMPEGDeinterlaceMode; /* default value : VIA_DEINTERLACE_WEAVE */
+    unsigned long   dwMPEGProgressiveMode; /* default value : VIA_PROGRESSIVE */
+    unsigned long   dwHQVheapInfo;         /* video memory heap of the HQV buffer */
+    unsigned long   dwVideoControl;        /* video control flag */
+    unsigned long   dwminifyH; 			   /* Horizontal minify factor */
+    unsigned long   dwminifyV;			   /* Vertical minify factor */
+	unsigned long	dwMpegDecoded;
+} OVERLAYRECORD;
+typedef OVERLAYRECORD * LPOVERLAYRECORD;
+
+/* DeinterLace Mode */
+#define VIA_DEINTERLACE_WEAVE               0x00000000
+#define VIA_DEINTERLACE_BOB                 0x00000001
+#define VIA_NON_PROGRESSIVE                 0x00000000
+#define VIA_PROGRESSIVE                     0x00000010
+
+/*
+ * DDPIXELFORMAT
+ */
+typedef struct _DDPIXELFORMAT
+{
+    unsigned long	dwSize;			/* size of structure */
+    unsigned long	dwFlags;		/* pixel format flags */
+    unsigned long	dwFourCC;		/* (FOURCC code) */
+
+	unsigned long	dwRGBBitCount;		/* how many bits per pixel */
+	unsigned long	dwYUVBitCount;		/* how many bits per pixel */
+	unsigned long	dwZBufferBitDepth;	/* how many bits for z buffers */
+	unsigned long	dwAlphaBitDepth;	/* how many bits for alpha channels */
+
+	unsigned long	dwRBitMask;		/* mask for red bit */
+	unsigned long	dwYBitMask;		/* mask for Y bits */
+
+	unsigned long	dwGBitMask;		/* mask for green bits */
+	unsigned long	dwUBitMask;		/* mask for U bits */
+
+	unsigned long	dwBBitMask;		/* mask for blue bits */
+	unsigned long	dwVBitMask;		/* mask for V bits */
+
+	unsigned long	dwRGBAlphaBitMask;	/* mask for alpha channel */
+	unsigned long	dwYUVAlphaBitMask;	/* mask for alpha channel */
+	unsigned long	dwRGBZBitMask;		/* mask for Z channel */
+	unsigned long	dwYUVZBitMask;		/* mask for Z channel */
+} DDPIXELFORMAT;
+typedef DDPIXELFORMAT * LPDDPIXELFORMAT;
+
+/****************************************************************************
+ *
+ * PIXELFORMAT FLAGS
+ *
+ ****************************************************************************/
+
+/*
+ * The FourCC code is valid.
+ */
+#define DDPF_FOURCC				0x00000004l
+
+/*
+ * The RGB data in the pixel format structure is valid.
+ */
+#define DDPF_RGB				0x00000040l
+
+
+
+/*
+ * Return value of Proprietary Interface
+ */
+
+#define PI_OK                              0x00
+#define PI_ERR                             0x01
+#define PI_ERR_NO_X_WINDOW                 PI_ERR +1
+#define PI_ERR_CANNOT_OPEN_VIDEO_DEVICE    PI_ERR +2
+#define PI_ERR_CANNOT_USE_IOCTL            PI_ERR +3
+#define PI_ERR_CANNOT_CREATE_SURFACE       PI_ERR +4
+
+
+/*
+ * Exported Driver functions
+ */
+
+unsigned long VIADriverProc(unsigned long wAction, void * lpParam);
+unsigned long VIABeginPicture(void * lpMPGSurface);
+unsigned long VIAEndPicture(void * lpMPGSurface);
+unsigned long VIASliceReceiveData(unsigned long dwByteCount, unsigned char * lpData);
+unsigned long VIADisplayControl(unsigned long devType, void * lpData);
+unsigned long VIASUBPicture(void * lpSubp);
+unsigned long VIASetDeInterlaceMode(unsigned long dwMode);
+int PrivPutImage(unsigned char* buf);
+unsigned long DispatchVGARevisionID(void);
+
+#endif
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/ddover.c linux-2.6.1-rc1-gentoo/drivers/media/video/ddover.c
--- linux-2.6.0/drivers/media/video/ddover.c	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/ddover.c	2004-01-06 17:28:06.000000000 +0000
@@ -0,0 +1,1028 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+ 
+// I N C L U D E S ---------------------------------------------------------
+
+#include "via_types.h"
+#include "via.h"
+#include "ddmpeg.h"
+#include "via_privIoctl.h" /* for VIAGRAPHICINFO & custom ioctl command */
+#include "HWDiff.h"
+
+#include "ddover.h"
+#include "via_v4l.h"
+
+// E X T E R N   G L O B A L S--------------------------------------------------------------
+
+extern MPGDEVICE   MPGDevice;
+extern OVERLAYRECORD    overlayRecordV1;
+extern OVERLAYRECORD    overlayRecordV3;
+extern VIAGRAPHICINFO gVIAGraphicInfo;     //2D information
+
+// F U N C T I O N ----------------------------------------------------------
+
+void DDOver_GetV1Format(unsigned long dwVideoFlag,LPDDPIXELFORMAT lpDPF, unsigned long * lpdwVidCtl,unsigned long * lpdwHQVCtl )
+{
+
+   if (lpDPF->dwFlags & DDPF_FOURCC)
+   {
+       *lpdwVidCtl |= V1_COLORSPACE_SIGN;
+       switch (lpDPF->dwFourCC) {
+       case FOURCC_YV12:
+            if (dwVideoFlag&VIDEO_HQV_INUSE)
+            {
+                *lpdwVidCtl |= (V1_YUV422 | V1_SWAP_HW_HQV );
+                *lpdwHQVCtl |= HQV_SRC_SW|HQV_YUV420|HQV_ENABLE|HQV_SW_FLIP;
+            }
+            else
+            {
+                *lpdwVidCtl |= V1_YCbCr420;
+            }
+            break;
+       case FOURCC_IYUV:
+       case FOURCC_VIA:
+            if (dwVideoFlag&VIDEO_HQV_INUSE)
+            {
+                if ((overlayRecordV1.dwDisplayPictStruct == VIA_PICT_STRUCT_TOP)||
+                    (overlayRecordV1.dwDisplayPictStruct == VIA_PICT_STRUCT_BOTTOM)||
+                    (overlayRecordV1.dwMPEGDeinterlaceMode == VIA_DEINTERLACE_BOB))
+                {
+                    //Field Display
+                    *lpdwVidCtl |= (V1_YUV422 | V1_SWAP_HW_HQV );
+                    if (dwVideoFlag&MPEG_USE_HW_FLIP)
+                    {
+                    	if (!(gVIAGraphicInfo.NoMPEGAddOneLineOnBottom))
+                    	{
+                            *lpdwHQVCtl |= HQV_DEINTERLACE;
+                        }
+
+                        *lpdwHQVCtl |= HQV_SRC_MC|HQV_YUV420|HQV_ENABLE |HQV_FIELD_2_FRAME|HQV_FRAME_2_FIELD;
+
+                        if (overlayRecordV1.dwMPEGProgressiveMode == VIA_NON_PROGRESSIVE)
+                        {
+                            *lpdwHQVCtl |= HQV_FIELD_UV;
+                        }
+                    }
+                    else
+                    {
+                    	if (!(gVIAGraphicInfo.NoMPEGAddOneLineOnBottom))
+                    	{
+                            *lpdwHQVCtl |= HQV_DEINTERLACE;
+                        }
+
+                        *lpdwHQVCtl |= HQV_SRC_SW|HQV_YUV420|HQV_ENABLE|HQV_SW_FLIP|HQV_FIELD_2_FRAME|HQV_FRAME_2_FIELD;
+
+                        if (overlayRecordV1.dwMPEGProgressiveMode == VIA_NON_PROGRESSIVE)
+                        {
+                            *lpdwHQVCtl |= HQV_FIELD_UV;
+                        }
+                    }
+                }
+                else
+                {
+                    //Frame Display
+                    *lpdwVidCtl |= (V1_YUV422 | V1_SWAP_HW_HQV );
+                    if (dwVideoFlag&MPEG_USE_HW_FLIP)
+                    {
+                        *lpdwHQVCtl |= HQV_SRC_MC|HQV_YUV420|HQV_ENABLE;
+                    }
+                    else
+                    {
+                        *lpdwHQVCtl |= HQV_SRC_SW|HQV_YUV420|HQV_ENABLE|HQV_SW_FLIP;
+                    }
+                }                
+            }
+            else
+            {
+                //Without HQV engine
+                if (dwVideoFlag&MPEG_USE_HW_FLIP)
+                {
+                    *lpdwVidCtl |= (V1_YCbCr420 | V1_SWAP_HW_MC );
+                    if (((overlayRecordV1.dwDisplayPictStruct == VIA_PICT_STRUCT_TOP   )||
+                         (overlayRecordV1.dwDisplayPictStruct == VIA_PICT_STRUCT_BOTTOM)||
+                         (overlayRecordV1.dwMPEGDeinterlaceMode == VIA_DEINTERLACE_BOB ))&&
+                         (overlayRecordV1.dwMPEGProgressiveMode == VIA_NON_PROGRESSIVE))
+                    {
+                        //CLE bug 
+                        //*lpdwVidCtl |= V1_SRC_IS_FIELD_PIC;
+                    }
+                }
+                else
+                {                    
+                    if ((overlayRecordV1.dwDisplayPictStruct == VIA_PICT_STRUCT_TOP)||
+                        (overlayRecordV1.dwDisplayPictStruct == VIA_PICT_STRUCT_BOTTOM)||
+                        (overlayRecordV1.dwMPEGDeinterlaceMode == VIA_DEINTERLACE_BOB))
+                    {
+                        *lpdwVidCtl |= (V1_YCbCr420 |V1_SWAP_SW | V1_BOB_ENABLE | V1_FRAME_BASE);
+                        if (overlayRecordV1.dwMPEGProgressiveMode == VIA_NON_PROGRESSIVE)
+                        {
+                            //CLE bug                             
+                            //*lpdwVidCtl |= V1_SRC_IS_FIELD_PIC;
+                        }
+                    }
+                    else
+                    {
+                        *lpdwVidCtl |= (V1_YCbCr420 | V1_SWAP_SW );
+                    }                
+                }
+            }
+            break;
+
+       case FOURCC_YUY2:
+            DBG_DD("DDOver_GetV1Format : FOURCC_YUY2\n");
+            if (dwVideoFlag&VIDEO_HQV_INUSE)
+            {
+                *lpdwVidCtl |= (V1_YUV422 | V1_SWAP_HW_HQV );
+                *lpdwHQVCtl |= HQV_SRC_SW|HQV_YUV422|HQV_ENABLE|HQV_SW_FLIP;
+            }
+            else
+            {
+                *lpdwVidCtl |= V1_YUV422;
+            }
+            break;
+
+       default :
+            DBG_DD("DDOver_GetV1Format : Invalid FOURCC format :(0x%lx)in V1!\n", lpDPF->dwFourCC);
+            *lpdwVidCtl |= V1_YUV422;
+            break;
+       }
+   }
+   else if (lpDPF->dwFlags & DDPF_RGB)
+   {
+       switch (lpDPF->dwRGBBitCount) {
+       case 16:
+            if (dwVideoFlag&VIDEO_HQV_INUSE)
+            {
+                *lpdwVidCtl |= (V1_RGB16 | V1_SWAP_HW_HQV );
+                *lpdwHQVCtl |= HQV_SRC_SW|HQV_ENABLE|HQV_SW_FLIP;
+                *lpdwHQVCtl |= (lpDPF->dwGBitMask==0x07E0 ?
+                            HQV_RGB16 : HQV_RGB15);
+            }
+            else
+            {
+                *lpdwVidCtl |= (lpDPF->dwGBitMask==0x07E0 ?
+                            V1_RGB16 : V1_RGB15);
+            }
+           break;
+       case 32:
+            if (dwVideoFlag&VIDEO_HQV_INUSE)
+            {
+                *lpdwVidCtl |= (V1_RGB32 | V1_SWAP_HW_HQV );
+                *lpdwHQVCtl |= HQV_SRC_SW|HQV_RGB32|HQV_ENABLE|HQV_SW_FLIP;
+            }
+            else
+            {
+                *lpdwVidCtl |= V1_RGB32;
+            }
+           break;
+
+       default :
+            DBG_DD("DDOver_GetV1Format : invalid RGB format %ld bits\n",lpDPF->dwRGBBitCount);
+            break;
+       }
+   }
+}
+
+void DDOver_GetV3Format(unsigned long dwVideoFlag,LPDDPIXELFORMAT lpDPF, unsigned long * lpdwVidCtl,unsigned long * lpdwHQVCtl )
+{
+
+   if (lpDPF->dwFlags & DDPF_FOURCC)
+   {
+       *lpdwVidCtl |= V3_COLORSPACE_SIGN;
+       switch (lpDPF->dwFourCC) {
+       case FOURCC_YV12:
+            if (dwVideoFlag&VIDEO_HQV_INUSE)
+            {
+                *lpdwVidCtl |= (V3_YUV422 | V3_SWAP_HW_HQV );
+                *lpdwHQVCtl |= HQV_SRC_SW|HQV_YUV420|HQV_ENABLE|HQV_SW_FLIP;
+            }
+            else
+            {
+                //*lpdwVidCtl |= V3_YCbCr420;
+                DBG_DD("DDOver_GetV3Format : Invalid FOURCC format :(0x%lx)in V3!\n", lpDPF->dwFourCC);
+            }
+            break;
+       case FOURCC_IYUV:
+       case FOURCC_VIA:
+            if (dwVideoFlag&VIDEO_HQV_INUSE)
+            {
+                if ((overlayRecordV1.dwDisplayPictStruct == VIA_PICT_STRUCT_TOP)||
+                    (overlayRecordV1.dwDisplayPictStruct == VIA_PICT_STRUCT_BOTTOM)||
+                    (overlayRecordV1.dwMPEGDeinterlaceMode == VIA_DEINTERLACE_BOB))
+                {
+                    //Field Display
+                    *lpdwVidCtl |= (V3_YUV422 | V3_SWAP_HW_HQV );
+                    if (dwVideoFlag&MPEG_USE_HW_FLIP)
+                    {
+                        *lpdwHQVCtl |= HQV_SRC_MC|HQV_YUV420|HQV_ENABLE |HQV_DEINTERLACE|HQV_FIELD_2_FRAME|HQV_FRAME_2_FIELD;
+                        if (overlayRecordV1.dwMPEGProgressiveMode == VIA_NON_PROGRESSIVE)
+                        {
+                            *lpdwHQVCtl |= HQV_FIELD_UV;
+                        }
+                    }
+                    else
+                    {
+                        *lpdwHQVCtl |= HQV_SRC_SW|HQV_YUV420|HQV_ENABLE|HQV_SW_FLIP;
+                        if (overlayRecordV1.dwMPEGProgressiveMode == VIA_NON_PROGRESSIVE)
+                        {
+                            *lpdwHQVCtl |= HQV_FIELD_UV;
+                        }
+                    }
+                }
+                else
+                {
+                    //Frame Display
+                    *lpdwVidCtl |= (V3_YUV422 | V3_SWAP_HW_HQV );
+                    if (dwVideoFlag&MPEG_USE_HW_FLIP)
+                    {
+                        *lpdwHQVCtl |= HQV_SRC_MC|HQV_YUV420|HQV_ENABLE;
+                    }
+                    else
+                    {
+                        *lpdwHQVCtl |= HQV_SRC_SW|HQV_YUV420|HQV_ENABLE|HQV_SW_FLIP;
+                    }
+                }                
+            }
+            else
+            {
+                DBG_DD("DDOver_GetV3Format : Invalid FOURCC format :(0x%lx)in V3!\n", lpDPF->dwFourCC);
+            }
+            break;
+
+       case FOURCC_YUY2:
+            if (dwVideoFlag&VIDEO_HQV_INUSE)
+            {
+                *lpdwVidCtl |= (V3_YUV422 | V3_SWAP_HW_HQV );
+                *lpdwHQVCtl |= HQV_SRC_SW|HQV_YUV422|HQV_ENABLE|HQV_SW_FLIP;
+            }
+            else
+            {
+                *lpdwVidCtl |= V3_YUV422;
+            }
+            break;
+
+       default :
+            DBG_DD("DDOver_GetV3Format : Invalid FOURCC format :(0x%lx)in V3!\n", lpDPF->dwFourCC);
+            *lpdwVidCtl |= V3_YUV422;
+            break;
+       }
+   }
+   else if (lpDPF->dwFlags & DDPF_RGB) {
+       switch (lpDPF->dwRGBBitCount) {
+       case 16:
+            if (dwVideoFlag&VIDEO_HQV_INUSE)
+            {
+                *lpdwVidCtl |= (V3_RGB16 | V3_SWAP_HW_HQV );
+                *lpdwHQVCtl |= HQV_SRC_SW|HQV_ENABLE|HQV_SW_FLIP;
+                *lpdwHQVCtl |= (lpDPF->dwGBitMask==0x07E0 ?
+                            HQV_RGB16 : HQV_RGB15);
+            }
+            else
+            {
+                *lpdwVidCtl |= (lpDPF->dwGBitMask==0x07E0 ?
+                            V3_RGB16 : V3_RGB15);
+            }
+           break;
+       case 32:
+            if (dwVideoFlag&VIDEO_HQV_INUSE)
+            {
+                *lpdwVidCtl |= (V3_RGB32 | V3_SWAP_HW_HQV );
+                *lpdwHQVCtl |= HQV_SRC_SW|HQV_RGB32|HQV_ENABLE|HQV_SW_FLIP;
+            }
+            else
+            {
+                *lpdwVidCtl |= V3_RGB32;
+            }
+           break;
+
+       default :
+            DBG_DD("DDOver_GetV3Format : invalid RGB format %ld bits\n",lpDPF->dwRGBBitCount);
+            break;
+       }
+   }
+}
+
+unsigned long DDOver_GetSrcStartAddress (unsigned long dwVideoFlag,RECTL rSrc,RECTL rDest, unsigned long dwSrcPitch,LPDDPIXELFORMAT lpDPF,unsigned long * lpHQVoffset )
+{
+   unsigned long dwOffset=0;
+   unsigned long dwHQVsrcWidth=0,dwHQVdstWidth=0;
+   unsigned long dwHQVsrcHeight=0,dwHQVdstHeight=0;
+   unsigned long dwHQVSrcTopOffset=0,dwHQVSrcLeftOffset=0;
+   unsigned long dwAlign = ~3;
+   
+   dwHQVsrcWidth = (unsigned long)(rSrc.right - rSrc.left);
+   dwHQVdstWidth = (unsigned long)(rDest.right - rDest.left);
+   dwHQVsrcHeight = (unsigned long)(rSrc.bottom - rSrc.top);
+   dwHQVdstHeight = (unsigned long)(rDest.bottom - rDest.top);
+
+    if (dwVideoFlag&VIDEO_HQV_INUSE)
+    {
+         dwAlign = ~3; /*4 bytes alignment if use HQV*/
+    }
+    else
+    {
+        if (dwHQVsrcWidth>dwHQVdstWidth)
+        {
+             dwAlign = ~15; /*16 bytes alignment if minify*/
+        }
+        else
+        {
+             dwAlign = ~3; /*4 bytes alignment if no minify*/
+        }
+    }
+    
+   if ( (rSrc.left != 0) || (rSrc.top != 0) )
+   {
+
+       if (lpDPF->dwFlags & DDPF_FOURCC)
+       {
+           switch (lpDPF->dwFourCC)
+           {
+            case FOURCC_YUY2:
+            case FOURCC_UYVY:
+            case FOURCC_YVYU:
+                DBG_DD("GetSrcStartAddress : FOURCC format :(0x%lx)\n", lpDPF->dwFourCC);
+                if (dwVideoFlag&VIDEO_HQV_INUSE)
+                {
+                        if (dwHQVsrcHeight>dwHQVdstHeight)
+                        {
+                            dwHQVSrcTopOffset = (rSrc.top * dwHQVdstHeight / dwHQVsrcHeight)* dwSrcPitch;
+                        }
+                        else
+                        {
+                            dwHQVSrcTopOffset = rSrc.top * (dwSrcPitch);
+                        }
+                        
+                        if (dwHQVsrcWidth>dwHQVdstWidth)
+                        {
+                            dwHQVSrcLeftOffset = ((rSrc.left << 1)&dwAlign) * dwHQVdstWidth / dwHQVsrcWidth;
+                        }
+                        else
+                        {
+                            dwHQVSrcLeftOffset = (rSrc.left << 1)&dwAlign ;
+                        }
+                        dwOffset = *lpHQVoffset = dwHQVSrcTopOffset+dwHQVSrcLeftOffset;
+                    }
+                    else
+                    {   
+                        dwOffset = ((rSrc.top * dwSrcPitch) +
+                                   (rSrc.left << 1)&dwAlign);
+                    }
+                    break;
+/*
+                if (dwVideoFlag&VIDEO_HQV_INUSE)
+                {
+                    //dwOffset = (((rSrc.top&~3) * (dwSrcPitch)) +
+                    //           ((rSrc.left << 1)&~31));
+
+                    if (dwHQVsrcHeight>dwHQVdstHeight)
+                    {
+                        dwHQVSrcTopOffset = ((rSrc.top&~3) * dwHQVdstHeight / dwHQVsrcHeight)* dwSrcPitch;
+                    }
+                    else
+                    {
+                        dwHQVSrcTopOffset = (rSrc.top&~3) * (dwSrcPitch);
+                    }
+                    
+                    if (dwHQVsrcWidth>dwHQVdstWidth)
+                    {
+                        dwHQVSrcLeftOffset = ((rSrc.left << 1)&~31) * dwHQVdstWidth / dwHQVsrcWidth;
+                    }
+                    else
+                    {
+                        dwHQVSrcLeftOffset = (rSrc.left << 1)&~31 ;
+                    }
+                    *lpHQVoffset = dwHQVSrcTopOffset+dwHQVSrcLeftOffset;
+                }
+                else
+                {   
+                    dwOffset = ((rSrc.top * dwSrcPitch) +
+                               ((rSrc.left << 1)&dwAlign));
+                }
+                break;
+*/
+            case FOURCC_IYUV:
+            case FOURCC_VIA:
+
+                    if (dwVideoFlag&VIDEO_HQV_INUSE)
+                    {   
+                        if (dwHQVsrcWidth>dwHQVdstWidth)
+                        {
+                            if (dwHQVsrcHeight>dwHQVdstHeight)
+                            {
+                                dwOffset = (((rSrc.top* dwHQVdstHeight / dwHQVsrcHeight) * (dwSrcPitch<<1)) + 
+                                            ((rSrc.left << 1)* dwHQVdstWidth / dwHQVsrcWidth)&dwAlign);
+                            }
+                            else
+                            {
+                                dwOffset = ((rSrc.top * (dwSrcPitch<<1)) + 
+                                            ((rSrc.left << 1)* dwHQVdstWidth / dwHQVsrcWidth)&dwAlign);
+                            }                             
+                        }
+                        else
+                        {
+                            if (dwHQVsrcHeight>dwHQVdstHeight)
+                            {
+                                dwOffset = (((rSrc.top* dwHQVdstHeight / dwHQVsrcHeight) * (dwSrcPitch<<1)) + 
+                                            (rSrc.left << 1)&dwAlign);
+                            }
+                            else
+                            {
+                                dwOffset = ((rSrc.top * (dwSrcPitch<<1)) + (rSrc.left << 1)&dwAlign);
+                            }                        
+                        }                    
+                    }
+                    else
+                    {
+                         dwOffset = ((((rSrc.top&~3) * dwSrcPitch) +
+                                    rSrc.left)&dwAlign) ;
+                         if (rSrc.top >0)
+                         {
+                            overlayRecordV1.dwUVoffset = (((((rSrc.top&~3)>>1) * dwSrcPitch) +
+                                            rSrc.left)&dwAlign) >>1;
+                         }
+                         else
+                         {
+                            overlayRecordV1.dwUVoffset = dwOffset >>1 ;
+                         }
+                    }
+                    break;
+/*
+                if (dwVideoFlag&VIDEO_HQV_INUSE)
+                {   
+                    unsigned long dwDstTop=0, dwDstLeft=0;
+
+                    dwDstTop = ((rSrc.top * MPGDevice.gdwMPGDstHeight) + (MPGDevice.dwHeight>>1))/MPGDevice.dwHeight;
+                    dwDstLeft = ((rSrc.left * MPGDevice.gdwMPGDstWidth) + (MPGDevice.dwWidth>>1))/MPGDevice.dwWidth;
+
+                    if (MPGDevice.gdwMPGDstHeight < MPGDevice.dwHeight)
+                        dwOffset = dwDstTop * (MPGDevice.dwPitch <<1);
+                    else
+                        dwOffset = rSrc.top * (MPGDevice.dwPitch <<1);
+                
+                    if (MPGDevice.gdwMPGDstWidth < MPGDevice.dwWidth)
+                        dwOffset += (dwDstLeft<<1)&~31;
+                    else
+                        dwOffset += (rSrc.left<<1)&~31;
+                }
+                else
+                {
+                     dwOffset = ((((rSrc.top&~3) * dwSrcPitch) +
+                                rSrc.left)&~31) ;
+                     if (rSrc.top >0)
+                     {
+                        overlayRecordV1.dwUVoffset = (((((rSrc.top&~3)>>1) * dwSrcPitch) +
+                                        rSrc.left)&~31) >>1;
+                     }
+                     else
+                     {
+                        overlayRecordV1.dwUVoffset = dwOffset >>1 ;
+                     }
+                }
+                break;
+*/
+            case FOURCC_YV12:
+                /*Fixed for panning*/
+                if (dwVideoFlag&VIDEO_HQV_INUSE)
+                {
+                    if (dwHQVsrcWidth>dwHQVdstWidth && dwHQVsrcHeight>dwHQVdstHeight)
+                    {
+                        dwOffset = ((rSrc.top * dwHQVdstHeight / dwHQVsrcHeight * (dwSrcPitch<<1)) +
+                                (((rSrc.left<<1) * dwHQVdstWidth / dwHQVsrcWidth) &dwAlign));                             
+                    }
+                    else if (dwHQVsrcWidth>dwHQVdstWidth )
+                    {
+                        dwOffset = ((rSrc.top * (dwSrcPitch<<1)) +
+                                (((rSrc.left<<1) * dwHQVdstWidth / dwHQVsrcWidth) &dwAlign));                             
+                    }                     
+                    else if (dwHQVsrcHeight>dwHQVdstHeight)
+                    {
+                        dwOffset = ((rSrc.top * dwHQVdstHeight / dwHQVsrcHeight * (dwSrcPitch<<1)) +
+                                ((rSrc.left<<1) &dwAlign));                                          
+                    }                     
+                    else
+                    {
+                        dwOffset = ((rSrc.top * (dwSrcPitch<<1)) +
+                                ((rSrc.left<<1) &dwAlign));     
+                    }
+                }
+                else
+                {
+                    dwOffset = ((((rSrc.top&~3) * dwSrcPitch) +
+                                rSrc.left)&dwAlign) ;
+                    if (rSrc.top >0)
+                    {
+                        overlayRecordV1.dwUVoffset = (((((rSrc.top&~3)>>1) * dwSrcPitch) +
+                                       rSrc.left)&dwAlign) >>1;
+                    }
+                    else
+                    {
+                        overlayRecordV1.dwUVoffset = dwOffset >>1 ;
+                    }
+                }
+                break;
+
+            default:
+                DBG_DD("DDOver_GetSrcStartAddress : Invalid FOURCC format :(0x%lx)in V3!\n", lpDPF->dwFourCC);
+                break;
+            }
+       }
+       else if (lpDPF->dwFlags & DDPF_RGB)
+       {
+                if (dwVideoFlag&VIDEO_HQV_INUSE)
+                {
+                    dwOffset = (((rSrc.top&~3) * (dwSrcPitch<<1)) +
+                                ((rSrc.left << 1)&~31));
+
+                    if (dwHQVsrcHeight>dwHQVdstHeight)
+                    {
+                        dwHQVSrcTopOffset = ((rSrc.top&~3) * dwHQVdstHeight / dwHQVsrcHeight)* dwSrcPitch;
+                    }
+                    else
+                    {
+                        dwHQVSrcTopOffset = (rSrc.top&~3) * (dwSrcPitch);
+                    }
+                    
+                    if (dwHQVsrcWidth>dwHQVdstWidth)
+                    {
+                        dwHQVSrcLeftOffset = ((rSrc.left << 1)&~31) * dwHQVdstWidth / dwHQVsrcWidth;
+                    }
+                    else
+                    {
+                        dwHQVSrcLeftOffset = (rSrc.left << 1)&~31 ;
+                    }
+                    *lpHQVoffset = dwHQVSrcTopOffset+dwHQVSrcLeftOffset;
+
+                }
+                else
+                {
+                    dwOffset = (rSrc.top * dwSrcPitch) +
+                           ((rSrc.left * lpDPF->dwRGBBitCount) >> 3);
+                }
+       }
+   }
+   else 
+   {
+        overlayRecordV1.dwUVoffset = dwOffset = 0;
+   }
+
+   return dwOffset;
+}
+
+YCBCRREC DDOVer_GetYCbCrStartAddress(unsigned long dwVideoFlag,unsigned long dwStartAddr, unsigned long dwOffset,unsigned long dwUVoffset,unsigned long dwSrcPitch/*lpGbl->lPitch*/,unsigned long dwSrcHeight/*lpGbl->wHeight*/)
+{
+   YCBCRREC YCbCr;
+
+   //dwStartAddr =  (unsigned long)lpGbl->fpVidMem - VideoBase;
+   if (dwVideoFlag&VIDEO_HQV_INUSE)
+   {
+       YCbCr.dwY   =  dwStartAddr;
+       YCbCr.dwCB  =  dwStartAddr + dwSrcPitch * dwSrcHeight ;
+       YCbCr.dwCR  =  dwStartAddr + dwSrcPitch * dwSrcHeight
+                         + dwSrcPitch * (dwSrcHeight >>2);
+   }
+   else
+   {
+       YCbCr.dwY   =  dwStartAddr+dwOffset;
+       YCbCr.dwCB  =  dwStartAddr + dwSrcPitch * dwSrcHeight 
+                         + dwUVoffset;
+       YCbCr.dwCR  =  dwStartAddr + dwSrcPitch * dwSrcHeight
+                         + dwSrcPitch * (dwSrcHeight >>2) 
+                         + dwUVoffset;
+   }
+   return YCbCr;
+}
+
+
+unsigned long DDOVER_HQVCalcZoomWidth(unsigned long dwVideoFlag, unsigned long srcWidth , unsigned long dstWidth,
+                           unsigned long * lpzoomCtl, unsigned long * lpminiCtl, unsigned long * lpHQVfilterCtl, unsigned long * lpHQVminiCtl,unsigned long * lpHQVzoomflag)
+{
+    unsigned long dwTmp;
+
+    if (srcWidth == dstWidth)
+    {       
+        *lpHQVfilterCtl |= HQV_H_FILTER_DEFAULT;
+    }
+    else
+    {
+    
+        if (srcWidth < dstWidth) {
+            // zoom in
+            *lpzoomCtl = srcWidth*0x0800 / dstWidth;
+            *lpzoomCtl = (((*lpzoomCtl) & 0x7FF) << 16) | V1_X_ZOOM_ENABLE;
+            *lpminiCtl |= ( V1_X_INTERPOLY );  // set up interpolation
+            *lpHQVzoomflag = 1;
+            *lpHQVfilterCtl |= HQV_H_FILTER_DEFAULT ;
+        } else if (srcWidth > dstWidth) {
+            // zoom out
+            unsigned long srcWidth1;
+    
+            //HQV rounding patch
+            //dwTmp = dstWidth*0x0800 / srcWidth;
+            dwTmp = dstWidth*0x0800*0x400 / srcWidth;
+            dwTmp = dwTmp / 0x400 + ((dwTmp & 0x3ff)?1:0);
+
+            *lpHQVminiCtl = (dwTmp & 0x7FF)| HQV_H_MINIFY_ENABLE;
+    
+    
+            srcWidth1 = srcWidth >> 1;
+            if (srcWidth1 <= dstWidth) {
+                *lpminiCtl |= V1_X_DIV_2+V1_X_INTERPOLY;
+                if (dwVideoFlag&VIDEO_1_INUSE)
+                {
+                    overlayRecordV1.dwFetchAlignment = 3;
+                    overlayRecordV1.dwminifyH = 2;
+                }
+                else
+                {
+                    overlayRecordV3.dwFetchAlignment = 3;
+                    overlayRecordV3.dwminifyH = 2;
+                }
+                *lpHQVfilterCtl |= HQV_H_TAP4_121;
+                //*lpHQVminiCtl = 0x00000c00;
+            }
+            else {
+                srcWidth1 >>= 1;
+    
+                if (srcWidth1 <= dstWidth) {
+                    *lpminiCtl |= V1_X_DIV_4+V1_X_INTERPOLY;
+                    if (dwVideoFlag&VIDEO_1_INUSE)
+                    {
+                        overlayRecordV1.dwFetchAlignment = 7;
+                        overlayRecordV1.dwminifyH = 4;
+                    }
+                    else
+                    {
+                        overlayRecordV3.dwFetchAlignment = 7;
+                        overlayRecordV3.dwminifyH = 4;
+                    }
+                    *lpHQVfilterCtl |= HQV_H_TAP4_121;
+                    //*lpHQVminiCtl = 0x00000a00;
+                }
+                else {
+                    srcWidth1 >>= 1;
+    
+                    if (srcWidth1 <= dstWidth) {
+                        *lpminiCtl |= V1_X_DIV_8+V1_X_INTERPOLY;
+                        if (dwVideoFlag&VIDEO_1_INUSE)
+                        {
+                            overlayRecordV1.dwFetchAlignment = 15;
+                            overlayRecordV1.dwminifyH = 8;
+                        }
+                        else
+                        {
+                            overlayRecordV3.dwFetchAlignment = 15;
+                            overlayRecordV3.dwminifyH = 8;
+                        }
+                        *lpHQVfilterCtl |= HQV_H_TAP8_12221;
+                        //*lpHQVminiCtl = 0x00000900;
+                    }
+                    else {
+                        srcWidth1 >>= 1;
+    
+                        if (srcWidth1 <= dstWidth) {
+                            *lpminiCtl |= V1_X_DIV_16+V1_X_INTERPOLY;
+                            if (dwVideoFlag&VIDEO_1_INUSE)
+                            {
+                                overlayRecordV1.dwFetchAlignment = 15;
+                                overlayRecordV1.dwminifyH = 16;
+                            }
+                            else
+                            {
+                                overlayRecordV3.dwFetchAlignment = 15;
+                                overlayRecordV3.dwminifyH = 16;
+                            }
+                            *lpHQVfilterCtl |= HQV_H_TAP8_12221;
+                            //*lpHQVminiCtl = 0x00000880;
+                        }
+                        else {
+                            // too small to handle
+                            //VIDOutD(V_COMPOSE_MODE, dwCompose);
+                            //lpUO->ddRVal = PI_OK;
+                            //return DDHAL_DRIVER_NOTHANDLED;
+                            *lpminiCtl |= V1_X_DIV_16+V1_X_INTERPOLY;
+                            if (dwVideoFlag&VIDEO_1_INUSE)
+                            {
+                                overlayRecordV1.dwFetchAlignment = 15;
+                                overlayRecordV1.dwminifyH = 16;
+                            }
+                            else
+                            {
+                                overlayRecordV3.dwFetchAlignment = 15;
+                                overlayRecordV3.dwminifyH = 16;
+                            }
+                            *lpHQVfilterCtl |= HQV_H_TAP8_12221;
+                        }
+                    }
+                }
+            }
+    
+            *lpHQVminiCtl |= HQV_HDEBLOCK_FILTER;
+
+            if (srcWidth1 < dstWidth) {
+                //CLE bug
+                //*lpzoomCtl = srcWidth1*0x0800 / dstWidth;
+                *lpzoomCtl = (srcWidth1-2)*0x0800 / dstWidth;                
+                *lpzoomCtl = ((*lpzoomCtl & 0x7FF) << 16) | V1_X_ZOOM_ENABLE;
+            }
+        }
+    }
+
+    return ~PI_ERR;
+}
+
+unsigned long DDOVER_HQVCalcZoomHeight (unsigned long srcHeight,unsigned long dstHeight,
+                             unsigned long * lpzoomCtl, unsigned long * lpminiCtl, unsigned long * lpHQVfilterCtl, unsigned long * lpHQVminiCtl,unsigned long * lpHQVzoomflag)
+{
+    unsigned long dwTmp;
+    
+    /*if (gVIAGraphicInfo.dwExpand)
+    {
+        dstHeight = dstHeight + 1;
+    }*/
+    
+    if (srcHeight < dstHeight) 
+    {
+        // zoom in
+        dwTmp = srcHeight * 0x0400 / dstHeight;
+        *lpzoomCtl |= ((dwTmp & 0x3FF) | V1_Y_ZOOM_ENABLE);
+        *lpminiCtl |= (V1_Y_INTERPOLY | V1_YCBCR_INTERPOLY);
+        *lpHQVzoomflag = 1;
+        *lpHQVfilterCtl |= HQV_V_TAP4_121;
+    } 
+    else if (srcHeight == dstHeight)
+    {       
+        *lpHQVfilterCtl |= HQV_V_TAP4_121;
+    }
+    else if (srcHeight > dstHeight) 
+    {
+        // zoom out
+        unsigned long srcHeight1;
+      
+        //HQV rounding patch
+        //dwTmp = dstHeight*0x0800 / srcHeight;
+        dwTmp = dstHeight*0x0800*0x400 / srcHeight;
+        dwTmp = dwTmp / 0x400 + ((dwTmp & 0x3ff)?1:0);
+        
+        *lpHQVminiCtl |= ((dwTmp& 0x7FF)<<16)|HQV_V_MINIFY_ENABLE;
+      
+        srcHeight1 = srcHeight >> 1;
+        if (srcHeight1 <= dstHeight) 
+        {
+            *lpminiCtl |= V1_Y_DIV_2;
+            *lpHQVfilterCtl |= HQV_V_TAP4_121 ;
+            //*lpHQVminiCtl |= 0x0c000000;
+        }
+        else 
+        {
+            srcHeight1 >>= 1;
+            if (srcHeight1 <= dstHeight) 
+            {
+                *lpminiCtl |= V1_Y_DIV_4;
+                *lpHQVfilterCtl |= HQV_V_TAP4_121 ;
+                //*lpHQVminiCtl |= 0x0a000000;
+            }
+            else 
+            {
+                srcHeight1 >>= 1;
+      
+                if (srcHeight1 <= dstHeight) 
+                {
+                    *lpminiCtl |= V1_Y_DIV_8;
+                    *lpHQVfilterCtl |= HQV_V_TAP8_12221;
+                    //*lpHQVminiCtl |= 0x09000000;
+                }
+                else 
+                {
+                    srcHeight1 >>= 1;
+      
+                    if (srcHeight1 <= dstHeight) 
+                    {
+                        *lpminiCtl |= V1_Y_DIV_16;
+                        *lpHQVfilterCtl |= HQV_V_TAP8_12221;
+                        //*lpHQVminiCtl |= 0x08800000;
+                    }
+                    else 
+                    {
+                        // too small to handle
+                        //VIDOutD(V_COMPOSE_MODE, dwCompose);
+                        //lpUO->ddRVal = PI_OK;
+                        //Fixed QAW91013
+                        //return DDHAL_DRIVER_NOTHANDLED;
+                        *lpminiCtl |= V1_Y_DIV_16;
+                        *lpHQVfilterCtl |= HQV_V_TAP8_12221;
+                    }
+                }
+            }
+        }
+      
+        *lpHQVminiCtl |= HQV_VDEBLOCK_FILTER;
+
+        if (srcHeight1 < dstHeight) 
+        {
+            dwTmp = srcHeight1 * 0x0400 / dstHeight;
+            *lpzoomCtl |= ((dwTmp & 0x3FF) | V1_Y_ZOOM_ENABLE);
+            *lpminiCtl |= ( V1_Y_INTERPOLY|V1_YCBCR_INTERPOLY);
+        }
+    }
+    
+    return ~PI_ERR;
+}
+
+
+unsigned long DDOver_GetFetch(unsigned long dwVideoFlag,LPDDPIXELFORMAT lpDPF,unsigned long dwSrcWidth,unsigned long dwDstWidth,unsigned long dwOriSrcWidth,unsigned long * lpHQVsrcFetch)
+{
+   unsigned long dwFetch=0;
+   
+   if (lpDPF->dwFlags & DDPF_FOURCC)
+   {
+       DBG_DD("DDOver_GetFetch : FourCC= 0x%lx\n", lpDPF->dwFourCC);
+       switch (lpDPF->dwFourCC) {
+       case FOURCC_YV12:
+            if (dwVideoFlag&VIDEO_HQV_INUSE)
+            {
+                *lpHQVsrcFetch = dwOriSrcWidth;
+                if (dwDstWidth >= dwSrcWidth)
+                    dwFetch = ((((dwSrcWidth<<1)+V1_FETCHCOUNT_ALIGNMENT)&~V1_FETCHCOUNT_ALIGNMENT) >> V1_FETCHCOUNT_UNIT)+1;
+                else
+                    dwFetch = ((((dwDstWidth<<1)+V1_FETCHCOUNT_ALIGNMENT)&~V1_FETCHCOUNT_ALIGNMENT) >> V1_FETCHCOUNT_UNIT)+1;            
+            }
+            else
+            {
+                // we fetch one more quadword to avoid get less video data
+                //dwFetch = (((dwSrcWidth +V1_FETCHCOUNT_ALIGNMENT)&~V1_FETCHCOUNT_ALIGNMENT)>> V1_FETCHCOUNT_UNIT) +1;
+                dwFetch = (((dwSrcWidth + 0x1F)&~0x1f)>> V1_FETCHCOUNT_UNIT);
+            }
+            break;
+       case FOURCC_IYUV:
+       case FOURCC_VIA:
+            if (dwVideoFlag&VIDEO_HQV_INUSE)
+            {
+                if (dwDstWidth >= dwSrcWidth)
+                    dwFetch = ((((dwSrcWidth<<1)+V1_FETCHCOUNT_ALIGNMENT)&~V1_FETCHCOUNT_ALIGNMENT) >> V1_FETCHCOUNT_UNIT)+1;
+                else
+                    dwFetch = ((((dwDstWidth<<1)+V1_FETCHCOUNT_ALIGNMENT)&~V1_FETCHCOUNT_ALIGNMENT) >> V1_FETCHCOUNT_UNIT)+1;
+            
+            }
+            else
+            {
+                //Comment by Vinecnt ,we fetch one more quadword to avoid get less video data
+                dwFetch = (((dwSrcWidth +V1_FETCHCOUNT_ALIGNMENT)&~V1_FETCHCOUNT_ALIGNMENT)>> V1_FETCHCOUNT_UNIT) +1;
+            }
+            break;
+       case FOURCC_UYVY:
+       case FOURCC_YVYU:
+       case FOURCC_YUY2:
+            if (dwVideoFlag&VIDEO_HQV_INUSE)
+            {
+                *lpHQVsrcFetch = dwOriSrcWidth<<1;
+                if (dwDstWidth >= dwSrcWidth)
+                    dwFetch = ((((dwSrcWidth<<1)+V1_FETCHCOUNT_ALIGNMENT)&~V1_FETCHCOUNT_ALIGNMENT) >> V1_FETCHCOUNT_UNIT)+1;
+                else
+                    dwFetch = ((((dwDstWidth<<1)+V1_FETCHCOUNT_ALIGNMENT)&~V1_FETCHCOUNT_ALIGNMENT) >> V1_FETCHCOUNT_UNIT)+1;
+            }
+            else
+            {
+                //Comment by Vinecnt ,we fetch one more quadword to avoid get less video data
+                dwFetch = ((((dwSrcWidth<<1)+V1_FETCHCOUNT_ALIGNMENT)&~V1_FETCHCOUNT_ALIGNMENT) >> V1_FETCHCOUNT_UNIT)+1;
+            }
+            break;
+       default :
+            DBG_DD("DDOver_GetFetch : Invalid FOURCC format :(0x%lx)in V1!\n", lpDPF->dwFourCC);
+            break;
+       }
+   }
+   else if (lpDPF->dwFlags & DDPF_RGB) {
+       switch (lpDPF->dwRGBBitCount) {
+       case 16:
+            if (dwVideoFlag&VIDEO_HQV_INUSE)
+            {
+                *lpHQVsrcFetch = dwOriSrcWidth<<1;
+                if (dwDstWidth >= dwSrcWidth)
+                    dwFetch = ((((dwSrcWidth<<1)+V1_FETCHCOUNT_ALIGNMENT)&~V1_FETCHCOUNT_ALIGNMENT) >> V1_FETCHCOUNT_UNIT)+1;
+                else
+                    dwFetch = ((((dwDstWidth<<1)+V1_FETCHCOUNT_ALIGNMENT)&~V1_FETCHCOUNT_ALIGNMENT) >> V1_FETCHCOUNT_UNIT)+1;
+            }
+            else
+            {
+                //Comment by Vinecnt ,we fetch one more quadword to avoid get less video data
+                dwFetch = ((((dwSrcWidth<<1)+V1_FETCHCOUNT_ALIGNMENT)&~V1_FETCHCOUNT_ALIGNMENT) >> V1_FETCHCOUNT_UNIT)+1;
+            }
+           break;
+       case 32:
+            if (dwVideoFlag&VIDEO_HQV_INUSE)
+            {
+                *lpHQVsrcFetch = dwOriSrcWidth<<2;
+                if (dwDstWidth >= dwSrcWidth)
+                    dwFetch = ((((dwSrcWidth<<2)+V1_FETCHCOUNT_ALIGNMENT)&~V1_FETCHCOUNT_ALIGNMENT) >> V1_FETCHCOUNT_UNIT)+1;
+                else
+                    dwFetch = ((((dwDstWidth<<2)+V1_FETCHCOUNT_ALIGNMENT)&~V1_FETCHCOUNT_ALIGNMENT) >> V1_FETCHCOUNT_UNIT)+1;
+            }
+            else
+            {
+                //Comment by Vinecnt ,we fetch one more quadword to avoid get less video data
+                dwFetch = ((((dwSrcWidth<<2)+V1_FETCHCOUNT_ALIGNMENT)&~V1_FETCHCOUNT_ALIGNMENT) >> V1_FETCHCOUNT_UNIT)+1;
+            }
+           break;
+
+       default :
+            DBG_DD("DDOver_GetFetch : invalid RGB format %ld bits\n",lpDPF->dwRGBBitCount);
+            break;
+       }
+   }
+
+   //Fix plannar mode problem
+   if (dwFetch <4)
+   {
+        dwFetch = 4;
+   }
+   return dwFetch;
+}
+
+void DDOver_GetDisplayCount(unsigned long dwVideoFlag,LPDDPIXELFORMAT lpDPF,unsigned long dwSrcWidth,unsigned long * lpDisplayCountW)
+{
+    
+   //unsigned long dwFetch=0;
+   
+   if (lpDPF->dwFlags & DDPF_FOURCC)
+   {
+       switch (lpDPF->dwFourCC) {
+       case FOURCC_YV12:
+       case FOURCC_UYVY:
+       case FOURCC_YVYU:
+       case FOURCC_YUY2:
+       case FOURCC_IYUV:
+       case FOURCC_VIA:
+            if (dwVideoFlag&VIDEO_HQV_INUSE)
+            {
+                *lpDisplayCountW = dwSrcWidth - 1;
+            }
+            else
+            {
+                //*lpDisplayCountW = dwSrcWidth - 2*overlayRecordV1.dwminifyH;
+                *lpDisplayCountW = dwSrcWidth - overlayRecordV1.dwminifyH;
+            }
+            break;
+       default :
+            DBG_DD("DDOver_GetDisplayCount : Invalid FOURCC format :(0x%lx)in V1!\n", lpDPF->dwFourCC);
+            if (dwVideoFlag&VIDEO_HQV_INUSE)
+            {
+                *lpDisplayCountW = dwSrcWidth - 1;
+            }
+            else
+            {
+                //*lpDisplayCountW = dwSrcWidth - 2*overlayRecordV1.dwminifyH;
+                *lpDisplayCountW = dwSrcWidth - overlayRecordV1.dwminifyH;
+            }
+            break;
+       }
+   }
+   else if (lpDPF->dwFlags & DDPF_RGB) {
+       switch (lpDPF->dwRGBBitCount) {
+       case 16:
+       case 32:
+            if (dwVideoFlag&VIDEO_HQV_INUSE)
+            {
+                *lpDisplayCountW = dwSrcWidth - 1;
+            }
+            else
+            {
+                *lpDisplayCountW = dwSrcWidth - overlayRecordV1.dwminifyH;
+            }
+            break;
+
+       default :
+            DBG_DD("DDOver_GetDisplayCount : invalid RGB format %ld bits\n",lpDPF->dwRGBBitCount);
+            if (dwVideoFlag&VIDEO_HQV_INUSE)
+            {
+                *lpDisplayCountW = dwSrcWidth - 1;
+            }
+            else
+            {
+                *lpDisplayCountW = dwSrcWidth - overlayRecordV1.dwminifyH;
+            }
+            break;
+       }
+   }   
+}
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/ddover.h linux-2.6.1-rc1-gentoo/drivers/media/video/ddover.h
--- linux-2.6.0/drivers/media/video/ddover.h	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/ddover.h	2004-01-06 17:28:06.000000000 +0000
@@ -0,0 +1,47 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#ifndef __DDOVER
+#define __DDOVER
+
+#define PLUS_HEIGHT 1 //V003
+
+typedef struct _YCBCRREC  {
+  unsigned long  dwY ;
+  unsigned long  dwCB;
+  unsigned long  dwCR;
+} YCBCRREC;
+
+void DDOver_GetV1Format(unsigned long dwVideoFlag,LPDDPIXELFORMAT lpDPF, unsigned long * lpdwVidCtl,unsigned long * lpdwHQVCtl );
+void DDOver_GetV3Format(unsigned long dwVideoFlag,LPDDPIXELFORMAT lpDPF, unsigned long * lpdwVidCtl,unsigned long * lpdwHQVCtl );
+unsigned long DDOverHQV_GetFormat(LPDDPIXELFORMAT lpDPF, unsigned long dwVidCtl,unsigned long * lpdwHQVCtl );
+unsigned long DDOver_GetSrcStartAddress (unsigned long dwVideoFlag,RECTL rSrc,RECTL rDest, unsigned long dwSrcPitch,LPDDPIXELFORMAT lpDPF,unsigned long * lpHQVoffset );
+YCBCRREC DDOVer_GetYCbCrStartAddress(unsigned long dwVideoFlag,unsigned long dwStartAddr, unsigned long dwOffset,unsigned long dwUVoffset,unsigned long dwSrcPitch/*lpGbl->lPitch*/,unsigned long dwSrcHeight/*lpGbl->wHeight*/);
+unsigned long DDOVER_HQVCalcZoomWidth(unsigned long dwVideoFlag, unsigned long srcWidth , unsigned long dstWidth,
+                           unsigned long * lpzoomCtl, unsigned long * lpminiCtl, unsigned long * lpHQVfilterCtl, unsigned long * lpHQVminiCtl,unsigned long * lpHQVzoomflag);
+unsigned long DDOVER_HQVCalcZoomHeight (unsigned long srcHeight,unsigned long dstHeight,
+                             unsigned long * lpzoomCtl, unsigned long * lpminiCtl, unsigned long * lpHQVfilterCtl, unsigned long * lpHQVminiCtl,unsigned long * lpHQVzoomflag);
+unsigned long DDOver_GetFetch(unsigned long dwVideoFlag,LPDDPIXELFORMAT lpDPF,unsigned long dwSrcWidth,unsigned long dwDstWidth,unsigned long dwOriSrcWidth,unsigned long * lpHQVsrcFetch);
+void DDOver_GetDisplayCount(unsigned long dwVideoFlag,LPDDPIXELFORMAT lpDPF,unsigned long dwSrcWidth,unsigned long * lpDisplayCountW);
+#endif //End of  __DDOVER
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/drm.h linux-2.6.1-rc1-gentoo/drivers/media/video/drm.h
--- linux-2.6.0/drivers/media/video/drm.h	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/drm.h	2004-01-06 17:28:06.000000000 +0000
@@ -0,0 +1,424 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#ifndef _DRM_H_
+#define _DRM_H_
+
+#if defined(__linux__)
+#include <linux/config.h>
+#include <asm/ioctl.h>		/* For _IO* macros */
+#define DRM_IOCTL_NR(n)	     _IOC_NR(n)
+#elif defined(__FreeBSD__)
+#include <sys/ioccom.h>
+#define DRM_IOCTL_NR(n)	     ((n) & 0xff)
+#endif
+
+#define XFREE86_VERSION(major,minor,patch,snap) \
+		((major << 16) | (minor << 8) | patch)
+
+#ifndef CONFIG_XFREE86_VERSION
+#define CONFIG_XFREE86_VERSION XFREE86_VERSION(4,1,0,0)
+#endif
+
+#if CONFIG_XFREE86_VERSION < XFREE86_VERSION(4,1,0,0)
+#define DRM_PROC_DEVICES "/proc/devices"
+#define DRM_PROC_MISC	 "/proc/misc"
+#define DRM_PROC_DRM	 "/proc/drm"
+#define DRM_DEV_DRM	 "/dev/drm"
+#define DRM_DEV_MODE	 (S_IRUSR|S_IWUSR|S_IRGRP|S_IWGRP)
+#define DRM_DEV_UID	 0
+#define DRM_DEV_GID	 0
+#endif
+
+#if CONFIG_XFREE86_VERSION >= XFREE86_VERSION(4,1,0,0)
+#define DRM_MAJOR       226
+#define DRM_MAX_MINOR   15
+#endif
+#define DRM_NAME	"drm"	  /* Name in kernel, /dev, and /proc	    */
+#define DRM_MIN_ORDER	5	  /* At least 2^5 bytes = 32 bytes	    */
+#define DRM_MAX_ORDER	22	  /* Up to 2^22 bytes = 4MB		    */
+#define DRM_RAM_PERCENT 10	  /* How much system ram can we lock?	    */
+
+#define _DRM_LOCK_HELD	0x80000000 /* Hardware lock is held		    */
+#define _DRM_LOCK_CONT	0x40000000 /* Hardware lock is contended	    */
+#define _DRM_LOCK_IS_HELD(lock)	   ((lock) & _DRM_LOCK_HELD)
+#define _DRM_LOCK_IS_CONT(lock)	   ((lock) & _DRM_LOCK_CONT)
+#define _DRM_LOCKING_CONTEXT(lock) ((lock) & ~(_DRM_LOCK_HELD|_DRM_LOCK_CONT))
+
+typedef unsigned long drm_handle_t;
+typedef unsigned int  drm_context_t;
+typedef unsigned int  drm_drawable_t;
+typedef unsigned int  drm_magic_t;
+
+/* Warning: If you change this structure, make sure you change
+ * XF86DRIClipRectRec in the server as well */
+
+typedef struct drm_clip_rect {
+	unsigned short	x1;
+	unsigned short	y1;
+	unsigned short	x2;
+	unsigned short	y2;
+} drm_clip_rect_t;
+
+typedef struct drm_tex_region {
+	unsigned char	next;
+	unsigned char	prev;
+	unsigned char	in_use;
+	unsigned char	padding;
+	unsigned int	age;
+} drm_tex_region_t;
+
+/* Seperate include files for the i810/mga/r128 specific structures */
+#include "via_drm.h"
+
+typedef struct drm_version {
+	int    version_major;	  /* Major version			    */
+	int    version_minor;	  /* Minor version			    */
+	int    version_patchlevel;/* Patch level			    */
+	size_t name_len;	  /* Length of name buffer		    */
+	char   *name;		  /* Name of driver			    */
+	size_t date_len;	  /* Length of date buffer		    */
+	char   *date;		  /* User-space buffer to hold date	    */
+	size_t desc_len;	  /* Length of desc buffer		    */
+	char   *desc;		  /* User-space buffer to hold desc	    */
+} drm_version_t;
+
+typedef struct drm_unique {
+	size_t unique_len;	  /* Length of unique			    */
+	char   *unique;		  /* Unique name for driver instantiation   */
+} drm_unique_t;
+
+typedef struct drm_list {
+	int		 count;	  /* Length of user-space structures	    */
+	drm_version_t	 *version;
+} drm_list_t;
+
+typedef struct drm_block {
+	int		 unused;
+} drm_block_t;
+
+typedef struct drm_control {
+	enum {
+		DRM_ADD_COMMAND,
+		DRM_RM_COMMAND,
+		DRM_INST_HANDLER,
+		DRM_UNINST_HANDLER
+	}		 func;
+	int		 irq;
+} drm_control_t;
+
+typedef enum drm_map_type {
+	_DRM_FRAME_BUFFER   = 0,  /* WC (no caching), no core dump	    */
+	_DRM_REGISTERS	    = 1,  /* no caching, no core dump		    */
+	_DRM_SHM	    = 2,  /* shared, cached			    */
+	_DRM_AGP            = 3,  /* AGP/GART                               */
+	_DRM_SCATTER_GATHER = 4	  /* Scatter/gather memory for PCI DMA      */
+} drm_map_type_t;
+
+typedef enum drm_map_flags {
+	_DRM_RESTRICTED	     = 0x01, /* Cannot be mapped to user-virtual    */
+	_DRM_READ_ONLY	     = 0x02,
+	_DRM_LOCKED	     = 0x04, /* shared, cached, locked		    */
+	_DRM_KERNEL	     = 0x08, /* kernel requires access		    */
+	_DRM_WRITE_COMBINING = 0x10, /* use write-combining if available    */
+	_DRM_CONTAINS_LOCK   = 0x20, /* SHM page that contains lock	    */
+	_DRM_REMOVABLE	     = 0x40  /* Removable mapping		    */
+} drm_map_flags_t;
+
+typedef struct drm_ctx_priv_map {
+	unsigned int	ctx_id;  /* Context requesting private mapping */
+	void		*handle; /* Handle of map */
+} drm_ctx_priv_map_t;
+
+typedef struct drm_map {
+	unsigned long	offset;	 /* Requested physical address (0 for SAREA)*/
+	unsigned long	size;	 /* Requested physical size (bytes)	    */
+	drm_map_type_t	type;	 /* Type of memory to map		    */
+	drm_map_flags_t flags;	 /* Flags				    */
+	void		*handle; /* User-space: "Handle" to pass to mmap    */
+				 /* Kernel-space: kernel-virtual address    */
+	int		mtrr;	 /* MTRR slot used			    */
+				 /* Private data			    */
+} drm_map_t;
+
+typedef struct drm_client {
+	int		idx;	/* Which client desired?                    */
+	int		auth;	/* Is client authenticated?                 */
+	unsigned long	pid;	/* Process id                               */
+	unsigned long	uid;	/* User id                                  */
+	unsigned long	magic;	/* Magic                                    */
+	unsigned long	iocs;	/* Ioctl count                              */
+} drm_client_t;
+
+typedef enum {
+	_DRM_STAT_LOCK,
+	_DRM_STAT_OPENS,
+	_DRM_STAT_CLOSES,
+	_DRM_STAT_IOCTLS,
+	_DRM_STAT_LOCKS,
+	_DRM_STAT_UNLOCKS,
+	_DRM_STAT_VALUE,	/* Generic value                      */
+	_DRM_STAT_BYTE,		/* Generic byte counter (1024bytes/K) */
+	_DRM_STAT_COUNT,	/* Generic non-byte counter (1000/k)  */
+
+	_DRM_STAT_IRQ,		/* IRQ */
+	_DRM_STAT_PRIMARY,	/* Primary DMA bytes */
+	_DRM_STAT_SECONDARY,	/* Secondary DMA bytes */
+	_DRM_STAT_DMA,		/* DMA */
+	_DRM_STAT_SPECIAL,	/* Special DMA (e.g., priority or polled) */
+	_DRM_STAT_MISSED	/* Missed DMA opportunity */
+
+				/* Add to the *END* of the list */
+} drm_stat_type_t;
+
+typedef struct drm_stats {
+	unsigned long count;
+	struct {
+		unsigned long   value;
+		drm_stat_type_t type;
+	} data[15];
+} drm_stats_t;
+
+typedef enum drm_lock_flags {
+	_DRM_LOCK_READY	     = 0x01, /* Wait until hardware is ready for DMA */
+	_DRM_LOCK_QUIESCENT  = 0x02, /* Wait until hardware quiescent	     */
+	_DRM_LOCK_FLUSH	     = 0x04, /* Flush this context's DMA queue first */
+	_DRM_LOCK_FLUSH_ALL  = 0x08, /* Flush all DMA queues first	     */
+				/* These *HALT* flags aren't supported yet
+				   -- they will be used to support the
+				   full-screen DGA-like mode. */
+	_DRM_HALT_ALL_QUEUES = 0x10, /* Halt all current and future queues   */
+	_DRM_HALT_CUR_QUEUES = 0x20  /* Halt all current queues		     */
+} drm_lock_flags_t;
+
+typedef struct drm_lock {
+	int		 context;
+	drm_lock_flags_t flags;
+} drm_lock_t;
+
+typedef enum drm_dma_flags {	      /* These values *MUST* match xf86drm.h */
+				      /* Flags for DMA buffer dispatch	     */
+	_DRM_DMA_BLOCK	      = 0x01, /* Block until buffer dispatched.
+					 Note, the buffer may not yet have
+					 been processed by the hardware --
+					 getting a hardware lock with the
+					 hardware quiescent will ensure
+					 that the buffer has been
+					 processed.			     */
+	_DRM_DMA_WHILE_LOCKED = 0x02, /* Dispatch while lock held	     */
+	_DRM_DMA_PRIORITY     = 0x04, /* High priority dispatch		     */
+
+				      /* Flags for DMA buffer request	     */
+	_DRM_DMA_WAIT	      = 0x10, /* Wait for free buffers		     */
+	_DRM_DMA_SMALLER_OK   = 0x20, /* Smaller-than-requested buffers ok   */
+	_DRM_DMA_LARGER_OK    = 0x40  /* Larger-than-requested buffers ok    */
+} drm_dma_flags_t;
+
+typedef struct drm_buf_desc {
+	int	      count;	 /* Number of buffers of this size	     */
+	int	      size;	 /* Size in bytes			     */
+	int	      low_mark;	 /* Low water mark			     */
+	int	      high_mark; /* High water mark			     */
+	enum {
+		_DRM_PAGE_ALIGN = 0x01, /* Align on page boundaries for DMA  */
+		_DRM_AGP_BUFFER = 0x02, /* Buffer is in agp space            */
+		_DRM_SG_BUFFER  = 0x04  /* Scatter/gather memory buffer      */
+	}	      flags;
+	unsigned long agp_start; /* Start address of where the agp buffers
+				  * are in the agp aperture */
+} drm_buf_desc_t;
+
+typedef struct drm_buf_info {
+	int	       count;	/* Entries in list			     */
+	drm_buf_desc_t *list;
+} drm_buf_info_t;
+
+typedef struct drm_buf_free {
+	int	       count;
+	int	       *list;
+} drm_buf_free_t;
+
+typedef struct drm_buf_pub {
+	int		  idx;	       /* Index into master buflist	     */
+	int		  total;       /* Buffer size			     */
+	int		  used;	       /* Amount of buffer in use (for DMA)  */
+	void		  *address;    /* Address of buffer		     */
+} drm_buf_pub_t;
+
+typedef struct drm_buf_map {
+	int	      count;	/* Length of buflist			    */
+	void	      *virtual;	/* Mmaped area in user-virtual		    */
+	drm_buf_pub_t *list;	/* Buffer information			    */
+} drm_buf_map_t;
+
+typedef struct drm_dma {
+				/* Indices here refer to the offset into
+				   buflist in drm_buf_get_t.  */
+	int		context;	  /* Context handle		    */
+	int		send_count;	  /* Number of buffers to send	    */
+	int		*send_indices;	  /* List of handles to buffers	    */
+	int		*send_sizes;	  /* Lengths of data to send	    */
+	drm_dma_flags_t flags;		  /* Flags			    */
+	int		request_count;	  /* Number of buffers requested    */
+	int		request_size;	  /* Desired size for buffers	    */
+	int		*request_indices; /* Buffer information		    */
+	int		*request_sizes;
+	int		granted_count;	  /* Number of buffers granted	    */
+} drm_dma_t;
+
+typedef enum {
+	_DRM_CONTEXT_PRESERVED = 0x01,
+	_DRM_CONTEXT_2DONLY    = 0x02
+} drm_ctx_flags_t;
+
+typedef struct drm_ctx {
+	drm_context_t	handle;
+	drm_ctx_flags_t flags;
+} drm_ctx_t;
+
+typedef struct drm_ctx_res {
+	int		count;
+	drm_ctx_t	*contexts;
+} drm_ctx_res_t;
+
+typedef struct drm_draw {
+	drm_drawable_t	handle;
+} drm_draw_t;
+
+typedef struct drm_auth {
+	drm_magic_t	magic;
+} drm_auth_t;
+
+typedef struct drm_irq_busid {
+	int irq;
+	int busnum;
+	int devnum;
+	int funcnum;
+} drm_irq_busid_t;
+
+typedef struct drm_agp_mode {
+	unsigned long mode;
+} drm_agp_mode_t;
+
+				/* For drm_agp_alloc -- allocated a buffer */
+typedef struct drm_agp_buffer {
+	unsigned long size;	/* In bytes -- will round to page boundary */
+	unsigned long handle;	/* Used for BIND/UNBIND ioctls */
+	unsigned long type;     /* Type of memory to allocate  */
+        unsigned long physical; /* Physical used by i810       */
+} drm_agp_buffer_t;
+
+				/* For drm_agp_bind */
+typedef struct drm_agp_binding {
+	unsigned long handle;   /* From drm_agp_buffer */
+	unsigned long offset;	/* In bytes -- will round to page boundary */
+} drm_agp_binding_t;
+
+typedef struct drm_agp_info {
+	int            agp_version_major;
+	int            agp_version_minor;
+	unsigned long  mode;
+	unsigned long  aperture_base;  /* physical address */
+	unsigned long  aperture_size;  /* bytes */
+	unsigned long  memory_allowed; /* bytes */
+	unsigned long  memory_used;
+
+				/* PCI information */
+	unsigned short id_vendor;
+	unsigned short id_device;
+} drm_agp_info_t;
+
+typedef struct drm_scatter_gather {
+	unsigned long size;	/* In bytes -- will round to page boundary */
+	unsigned long handle;	/* Used for mapping / unmapping */
+} drm_scatter_gather_t;
+
+#define DRM_IOCTL_BASE			'd'
+#define DRM_IO(nr)			_IO(DRM_IOCTL_BASE,nr)
+#define DRM_IOR(nr,size)		_IOR(DRM_IOCTL_BASE,nr,size)
+#define DRM_IOW(nr,size)		_IOW(DRM_IOCTL_BASE,nr,size)
+#define DRM_IOWR(nr,size)		_IOWR(DRM_IOCTL_BASE,nr,size)
+
+
+#define DRM_IOCTL_VERSION		DRM_IOWR(0x00, drm_version_t)
+#define DRM_IOCTL_GET_UNIQUE		DRM_IOWR(0x01, drm_unique_t)
+#define DRM_IOCTL_GET_MAGIC		DRM_IOR( 0x02, drm_auth_t)
+#define DRM_IOCTL_IRQ_BUSID		DRM_IOWR(0x03, drm_irq_busid_t)
+#define DRM_IOCTL_GET_MAP               DRM_IOWR(0x04, drm_map_t)
+#define DRM_IOCTL_GET_CLIENT            DRM_IOWR(0x05, drm_client_t)
+#define DRM_IOCTL_GET_STATS             DRM_IOR( 0x06, drm_stats_t)
+
+#define DRM_IOCTL_SET_UNIQUE		DRM_IOW( 0x10, drm_unique_t)
+#define DRM_IOCTL_AUTH_MAGIC		DRM_IOW( 0x11, drm_auth_t)
+#define DRM_IOCTL_BLOCK			DRM_IOWR(0x12, drm_block_t)
+#define DRM_IOCTL_UNBLOCK		DRM_IOWR(0x13, drm_block_t)
+#define DRM_IOCTL_CONTROL		DRM_IOW( 0x14, drm_control_t)
+#define DRM_IOCTL_ADD_MAP		DRM_IOWR(0x15, drm_map_t)
+#define DRM_IOCTL_ADD_BUFS		DRM_IOWR(0x16, drm_buf_desc_t)
+#define DRM_IOCTL_MARK_BUFS		DRM_IOW( 0x17, drm_buf_desc_t)
+#define DRM_IOCTL_INFO_BUFS		DRM_IOWR(0x18, drm_buf_info_t)
+#define DRM_IOCTL_MAP_BUFS		DRM_IOWR(0x19, drm_buf_map_t)
+#define DRM_IOCTL_FREE_BUFS		DRM_IOW( 0x1a, drm_buf_free_t)
+
+#define DRM_IOCTL_RM_MAP		DRM_IOW( 0x1b, drm_map_t)
+
+#define DRM_IOCTL_SET_SAREA_CTX		DRM_IOW( 0x1c, drm_ctx_priv_map_t)
+#define DRM_IOCTL_GET_SAREA_CTX 	DRM_IOWR(0x1d, drm_ctx_priv_map_t)
+
+#define DRM_IOCTL_ADD_CTX		DRM_IOWR(0x20, drm_ctx_t)
+#define DRM_IOCTL_RM_CTX		DRM_IOWR(0x21, drm_ctx_t)
+#define DRM_IOCTL_MOD_CTX		DRM_IOW( 0x22, drm_ctx_t)
+#define DRM_IOCTL_GET_CTX		DRM_IOWR(0x23, drm_ctx_t)
+#define DRM_IOCTL_SWITCH_CTX		DRM_IOW( 0x24, drm_ctx_t)
+#define DRM_IOCTL_NEW_CTX		DRM_IOW( 0x25, drm_ctx_t)
+#define DRM_IOCTL_RES_CTX		DRM_IOWR(0x26, drm_ctx_res_t)
+#define DRM_IOCTL_ADD_DRAW		DRM_IOWR(0x27, drm_draw_t)
+#define DRM_IOCTL_RM_DRAW		DRM_IOWR(0x28, drm_draw_t)
+#define DRM_IOCTL_DMA			DRM_IOWR(0x29, drm_dma_t)
+#define DRM_IOCTL_LOCK			DRM_IOW( 0x2a, drm_lock_t)
+#define DRM_IOCTL_UNLOCK		DRM_IOW( 0x2b, drm_lock_t)
+#define DRM_IOCTL_FINISH		DRM_IOW( 0x2c, drm_lock_t)
+
+#define DRM_IOCTL_AGP_ACQUIRE		DRM_IO(  0x30)
+#define DRM_IOCTL_AGP_RELEASE		DRM_IO(  0x31)
+#define DRM_IOCTL_AGP_ENABLE		DRM_IOW( 0x32, drm_agp_mode_t)
+#define DRM_IOCTL_AGP_INFO		DRM_IOR( 0x33, drm_agp_info_t)
+#define DRM_IOCTL_AGP_ALLOC		DRM_IOWR(0x34, drm_agp_buffer_t)
+#define DRM_IOCTL_AGP_FREE		DRM_IOW( 0x35, drm_agp_buffer_t)
+#define DRM_IOCTL_AGP_BIND		DRM_IOW( 0x36, drm_agp_binding_t)
+#define DRM_IOCTL_AGP_UNBIND		DRM_IOW( 0x37, drm_agp_binding_t)
+
+#define DRM_IOCTL_SG_ALLOC		DRM_IOW( 0x38, drm_scatter_gather_t)
+#define DRM_IOCTL_SG_FREE		DRM_IOW( 0x39, drm_scatter_gather_t)
+
+/* VIA specific ioctls */
+#define DRM_IOCTL_VIA_ALLOCMEM	DRM_IOWR(0x40, drm_via_mem_t)
+#define DRM_IOCTL_VIA_FREEMEM	DRM_IOW(0x41, drm_via_mem_t)
+#define DRM_IOCTL_VIA_AGP_INIT	DRM_IOWR(0x42, drm_via_agp_t)
+#define DRM_IOCTL_VIA_FB_INIT	DRM_IOWR(0x43, drm_via_fb_t)
+#define DRM_IOCTL_VIA_MAP_INIT	DRM_IOWR(0x44, drm_via_init_t)
+#define DRM_IOCTL_VIA_FLUSH_AGP	DRM_IOW(0x45, drm_via_flush_agp_t)
+#define DRM_IOCTL_VIA_FLUSH_SYS	DRM_IOW(0x46, drm_via_flush_sys_t)
+
+#endif
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/i2c.c linux-2.6.1-rc1-gentoo/drivers/media/video/i2c.c
--- linux-2.6.0/drivers/media/video/i2c.c	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/i2c.c	2004-01-06 17:28:06.000000000 +0000
@@ -0,0 +1,211 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+/*------------------------------------------------
+   I2C Module
+  ------------------------------------------------*/
+#include <asm/io.h>
+#include <linux/delay.h>	/* for delay-stuff ex: udelay */
+#include "via_types.h"
+
+#include "i2c.h"
+#include "via_v4l.h"
+
+
+int I2CReg3C4  = 0x3c4;
+int I2CReg3C5    = 0x3c5;
+int I2CReg3C4Index   = I2CIndexVDEC;
+
+
+
+void I2C_enable(void)
+{
+    int tempI2Cdata, Reg3C4H;
+
+    //DBG_DD("I2C_enable\n");
+    // save 3c4H
+    Reg3C4H = inb(I2CReg3C4);
+
+    outb(I2CReg3C4Index,I2CReg3C4);
+    tempI2Cdata = inb(I2CReg3C5);
+
+    tempI2Cdata |= 0x01; //bit 0:I2C Serial Port Enable
+    outb(tempI2Cdata,I2CReg3C5);
+
+    // restore 3c4H
+    outb(Reg3C4H,I2CReg3C4);
+        
+} //I2C_enable
+
+
+void I2C_SET( unsigned SCL, unsigned SDA )
+{
+        int I2CData, regSave;
+
+        regSave = inb(I2CReg3C4);
+        outb(I2CReg3C4Index,I2CReg3C4);
+
+        I2CData = inb(I2CReg3C5);
+        I2CData &= 0xcf;  //bit5 SPCLCK, bit4 SDATA
+        I2CData |= (( SCL << 5 ) | ( SDA << 4 ));
+        outb(I2CData,I2CReg3C5);
+
+        // restore 3c4H
+        outb(regSave,I2CReg3C4);
+
+}
+
+int  I2C_GET(void)
+{
+    int SDA=0,regSave;
+
+    // save 3c4H
+    regSave = inb(I2CReg3C4);
+
+    outb(I2CReg3C4Index,I2CReg3C4);
+    SDA = ( inb(I2CReg3C5) >> 2) & 0x01;
+
+    // restore 3c4H
+    outb(regSave,I2CReg3C4);
+
+    return(SDA);
+
+}
+
+
+void i2c_one(void)
+{
+        I2C_SET( 0, 1);
+        I2C_SET( 1, 1);
+        udelay(100); 
+        I2C_SET( 0, 1);
+        udelay(100); 
+}
+
+void i2c_zero(void)
+{
+        I2C_SET( 0, 0);
+        I2C_SET( 1, 0);
+        udelay(100); 
+        I2C_SET( 0, 0);
+        udelay(100); 
+}
+
+void i2c_start(void)
+{
+        I2C_SET( 0, 1);
+        I2C_SET( 1, 1);
+        udelay(100); 
+        I2C_SET( 1, 0);
+        udelay(100); 
+        I2C_SET( 0, 0);
+        udelay(100); 
+}
+
+void i2c_stop(void)
+{
+        I2C_SET( 0, 0);
+        I2C_SET( 1, 0);
+        udelay(100); 
+        I2C_SET( 1, 1);
+        udelay(100); 
+}
+
+
+
+int i2c_ack(void)
+{
+        int ack;
+
+        I2C_SET( 0, 1);
+        I2C_SET( 1, 1);
+        ack = I2C_GET();
+        I2C_SET( 0, 1);
+        return ack;
+}
+
+
+
+int i2c_sendbyte( unsigned char data, int wait_for_ack)
+{
+        int i, ack;
+
+        //DBG_DD("i2c_sendbyte\n");
+        I2C_SET( 0, 0);
+        for (i = 7; i >= 0; i--)
+        {   
+                (data & (1 << i)) ? i2c_one() : i2c_zero();
+                //udelay(100);
+    	}
+        if (wait_for_ack)
+                udelay(1000);
+
+        ack = i2c_ack();
+        //udelay(1000); 
+
+        return ack;
+}
+
+
+unsigned char i2c_readbyte( int last)
+{
+        int i;
+        unsigned char data = 0;
+
+        //DBG_DD("i2c_readbyte\n");
+        I2C_SET( 0, 1);
+        for (i = 7; i >= 0; i--) {
+                I2C_SET( 1, 1);
+                if (I2C_GET())
+                        data |= (1 << i);
+                I2C_SET( 0, 1);
+        }
+        last ? i2c_one() : i2c_zero();
+        return data;
+}
+
+int i2c_read( unsigned char addr)
+{
+        int ret;
+
+        i2c_start();
+        i2c_sendbyte( addr, 0);
+        ret = i2c_readbyte( 1);
+        i2c_stop();
+        return ret;
+}
+
+
+/* delay in unit of millisecond */
+struct timespec timesleep;
+void I2C_Delay1( unsigned long delay)
+{
+    timesleep.tv_sec = 0;
+    timesleep.tv_nsec = 1000;
+    udelay(1000);
+
+} //I2C_Delay1
+
+
+
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/i2c.h linux-2.6.1-rc1-gentoo/drivers/media/video/i2c.h
--- linux-2.6.0/drivers/media/video/i2c.h	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/i2c.h	2004-01-06 17:28:06.000000000 +0000
@@ -0,0 +1,40 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#ifndef __I2C_H
+#define __I2C_H
+
+#define I2CTime                          1
+#define I2CIndexVDEC                     0x31
+#define I2CIndexTUNER                    0x31
+//#define I2CIndexTUNER                    0x26
+
+void I2C_enable(void);
+void i2c_start(void);
+void i2c_stop(void);
+int  i2c_sendbyte( unsigned char data, int wait_for_ack);
+unsigned char i2c_readbyte( int last);
+void    I2C_Delay1(unsigned long);
+
+#endif     //__I2C_H
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/regrec.c linux-2.6.1-rc1-gentoo/drivers/media/video/regrec.c
--- linux-2.6.0/drivers/media/video/regrec.c	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/regrec.c	2004-01-06 17:28:06.000000000 +0000
@@ -0,0 +1,193 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#include "via_types.h"
+#include "via.h"
+
+#include "via_v4l.h"
+#include "regrec.h"
+
+extern volatile unsigned char  * lpVidMEMIO;
+//extern unsigned long gdwVideoOn;
+extern Bool MPEG_ON;
+
+static VIDEOREGISTER VidReg[VIDEO_REG_NUM];
+static unsigned long gdwVidRegCounter;
+
+
+// I N L I N E --------------------------------------------------------------
+
+__inline void WaitHQVIdle(void)
+{
+    while (!IN_HQV_FIRE);
+}
+
+__inline void WaitVideoCommandFire(void)
+{
+    //while (IN_VIDEO_FIRE);
+    unsigned long volatile *pdwState = (unsigned long volatile *) (lpVidMEMIO+V_COMPOSE_MODE);
+    //pdwState = (unsigned long volatile *) (lpVidMEMIO+V_COMPOSE_MODE);
+    while ((*pdwState & V1_COMMAND_FIRE)||(*pdwState & V3_COMMAND_FIRE));
+}
+
+__inline void WaitHQVFlip(void)
+{
+    unsigned long volatile *pdwState = (unsigned long volatile *) lpVidMEMIO;
+    pdwState = (unsigned long volatile *) (lpVidMEMIO+HQV_CONTROL);
+    while (!(*pdwState & HQV_FLIP_STATUS) );
+/*
+    while (!((*pdwState & 0xc0)== 0xc0) );
+    while (!((*pdwState & 0xc0)!= 0xc0) );
+*/    
+}
+
+__inline void WaitHQVFlipClear(unsigned long dwData)
+{
+    unsigned long volatile *pdwState = (unsigned long volatile *) (lpVidMEMIO+HQV_CONTROL);
+    *pdwState =dwData;
+
+    while ((*pdwState & HQV_FLIP_STATUS) )
+    {
+        VIDOutD(HQV_CONTROL, *pdwState|HQV_FLIP_STATUS);
+    }
+}
+
+__inline void WaitHQVFIFOEmpty(void)
+{
+    unsigned long volatile *pdwState = (unsigned long volatile *) (lpVidMEMIO+HQV_CONTROL); 
+    
+    while ((*pdwState & HQV_FIFO_STATUS) );
+}
+
+__inline void WaitVBI()
+{
+    while (IN_VIDEO_DISPLAY);
+}
+
+__inline void WaitHQVDone()
+{
+    unsigned long volatile *pdwState = (unsigned long volatile *) (lpVidMEMIO+HQV_CONTROL);
+    //pdwState = (unsigned long volatile *) (GEAddr+HQV_CONTROL);
+
+    //if (*pdwState & HQV_ENABLE)
+    if (MPEG_ON)
+    {
+        while ((*pdwState & HQV_SW_FLIP) );
+    }
+}
+
+__inline void Macro_VidREGFlush(void)
+{
+    unsigned long i;
+    
+    WaitVideoCommandFire();
+
+    for (i=0; i< gdwVidRegCounter; i++ )
+    {
+        VIDOutD(VidReg[i].dwIndex, VidReg[i].dwData);
+        DBG_DD("Macro_VidREGFlush:%08lx %08lx\n",VidReg[i].dwIndex+0x200,VidReg[i].dwData);
+    }
+}
+
+__inline void Macro_VidREGFlush_Hide(void)
+{
+    unsigned long i;
+    
+    WaitHQVIdle();
+    WaitHQVIdle();
+    WaitVideoCommandFire();
+
+    for (i=0; i< gdwVidRegCounter; i++ )
+    {
+        VIDOutD(VidReg[i].dwIndex, VidReg[i].dwData);
+        DBG_DD("Macro_VidREGFlush:%08lx %08lx\n",VidReg[i].dwIndex+0x200,VidReg[i].dwData);
+    }
+}
+
+__inline void Macro_VidREGRec(unsigned long dwAction, unsigned long dwIndex, unsigned long dwData)
+{
+
+  switch (dwAction)
+  {
+     case VIDREGREC_RESET_COUNTER :
+          gdwVidRegCounter = 0;
+          break;
+
+     case VIDREGREC_SAVE_REGISTER:
+          VidReg[gdwVidRegCounter].dwIndex = dwIndex;
+          VidReg[gdwVidRegCounter].dwData  = dwData;
+          gdwVidRegCounter++;
+          if ( gdwVidRegCounter > VIDEO_REG_NUM){
+             DBG_DD("Macro_VidREGRec:Out of Video register space");
+          }
+
+          break;
+
+     default :
+          DBG_DD("Macro_VidREGRec:Unknow action");
+          break;
+  }
+}
+
+__inline void Macro_VidREGFlushVPE(void)
+//void Macro_VidREGFlushVPE(LPVIATHKINFO sData)
+{
+    unsigned long i;
+    unsigned long volatile *pdwState = (unsigned long volatile *) lpVidMEMIO;
+    pdwState = (unsigned long volatile *) (lpVidMEMIO+V_COMPOSE_MODE);
+
+    while ((*pdwState & V1_COMMAND_FIRE)||(*pdwState & V3_COMMAND_FIRE));
+
+    for (i=0; i< gdwVidRegCounter; i++ )
+    {
+     	VIDOutD(VidReg[i].dwIndex, VidReg[i].dwData);
+        DBG_DD("Macro_VidREGFlush V3:%08lx %08lx\n",VidReg[i].dwIndex+0x200,VidReg[i].dwData);
+    }
+}
+
+__inline void Macro_VidREGRecVPE(unsigned long dwAction, unsigned long dwIndex, unsigned long dwData)
+//void Macro_VidREGRecVPE(unsigned long dwAction, unsigned long dwIndex, unsigned long dwData)
+{
+
+  switch (dwAction)
+  {
+     case VIDREGREC_RESET_COUNTER :
+          gdwVidRegCounter = 0;
+          break;
+
+     case VIDREGREC_SAVE_REGISTER:
+          VidReg[gdwVidRegCounter].dwIndex = dwIndex;
+          VidReg[gdwVidRegCounter].dwData  = dwData;
+          gdwVidRegCounter++;
+          if ( gdwVidRegCounter > VIDEO_REG_NUM){
+             //TOINT3;
+          }
+
+          break;
+
+     default :
+          //TOINT3;
+          break;
+  }
+}
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/regrec.h linux-2.6.1-rc1-gentoo/drivers/media/video/regrec.h
--- linux-2.6.0/drivers/media/video/regrec.h	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/regrec.h	2004-01-06 17:28:06.000000000 +0000
@@ -0,0 +1,58 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#ifndef __REGREC
+#define __REGREC
+#define VIDREGREC_RESET_COUNTER   0
+#define VIDREGREC_SAVE_REGISTER   VIDREGREC_RESET_COUNTER +1
+#define VIDREGREC_FLUSH_REGISTER  VIDREGREC_RESET_COUNTER +2
+#define VIDEO_REG_NUM  100
+
+#define IN_HQV_FIRE     (*((unsigned long volatile *)(lpVidMEMIO+HQV_CONTROL))&HQV_IDLE)
+#define IN_VIDEO_FIRE   (*((unsigned long volatile *)(lpVidMEMIO+V_COMPOSE_MODE))&V1_COMMAND_FIRE)
+#define IN_HQV_FLIP     (*((unsigned long volatile *)(lpVidMEMIO+HQV_CONTROL))&HQV_FLIP_STATUS) 
+#define IN_VIDEO_DISPLAY     (*((unsigned long volatile *)(lpVidMEMIO+V_FLAGS))&VBI_STATUS) 
+
+//#define IN_DISPLAY      (VIDInD(V_FLAGS) & 0x200)
+//#define IN_VBLANK       (!IN_DISPLAY)
+
+typedef struct
+{
+  unsigned long dwIndex;
+  unsigned long dwData;
+}VIDEOREGISTER;
+
+__inline void WaitHQVIdle(void);
+__inline void WaitVideoCommandFire(void);
+__inline void WaitHQVFlip(void);
+__inline void WaitHQVFlipClear(unsigned long dwData);
+__inline void WaitVBI(void);
+__inline void WaitHQVDone(void);
+__inline void WaitHQVFIFOEmpty(void);
+__inline void Macro_VidREGFlush(void);
+__inline void Macro_VidREGFlush_Hide(void);
+__inline void Macro_VidREGRec(unsigned long dwAction, unsigned long dwIndex, unsigned long dwData);
+__inline void Macro_VidREGFlushVPE(void);
+__inline void Macro_VidREGRecVPE(unsigned long dwAction, unsigned long dwIndex, unsigned long dwData);
+#endif //end of __REGREC
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/vdec.c linux-2.6.1-rc1-gentoo/drivers/media/video/vdec.c
--- linux-2.6.0/drivers/media/video/vdec.c	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/vdec.c	2004-01-06 23:30:03.000000000 +0000
@@ -0,0 +1,794 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+/*------------------------------------------------
+   Video decoder module
+  ------------------------------------------------*/
+
+#include "via_types.h"
+
+#include "i2c.h"
+#include "vdec.h"
+
+// E X T E R N   G L O B A L S--------------------------------------------------------------
+extern int bSetFirst;
+
+// G L O B A L S ------------------------------------------------------------
+
+
+/*
+ *  WriteReg
+ *
+ *  write data to video decoder registers
+ * 
+ *  [input]
+ *  value1: slave write address, value2: sub address(index), value3: fill value
+ *  output : N/A
+ */
+void  WriteReg(int Slave_Write, int Sub_Addr, int value )
+{
+     int ack=1;
+     //DBG_DD("VDEC: WriteReg()\n");
+     i2c_start();
+     ack=i2c_sendbyte(Slave_Write,0 );
+     ack=i2c_sendbyte(Sub_Addr,0 );
+     ack=i2c_sendbyte(value,0 );
+     i2c_stop();
+
+}
+
+
+/*
+ *  ReadReg
+ *
+ *  read data from video decoder registers
+ * 
+ *  [input]
+ *  value1: slave addr, value2: sub addr(index)
+ *  [return]
+ *  value
+ */
+int  ReadReg(int Salve_Write, int Salve_Read, int Sub_Addr)
+{
+    int ReadData =0, ack=1;
+
+    //DBG_DD("VDEC: ReadReg()\n");
+    i2c_start();
+    
+    ack=i2c_sendbyte(Salve_Write,1 );
+    ack=i2c_sendbyte(Sub_Addr,1 );
+    //DBG_DD("send sub_addr ack = 0x%x\n", ack);
+    i2c_stop();
+
+    i2c_start();
+    ack=i2c_sendbyte(Salve_Read,1);
+    //DBG_DD("before readbyte ack = 0x%x\n", ack);
+    ReadData=i2c_readbyte(1);
+    i2c_stop();
+    
+    return(ReadData);
+}
+
+/************************************************************************/
+int  Get7108ChipID(unsigned Sub_Addr)
+{
+    int ReadData =0, ack=1;
+
+//    DBG_DD("VDEC: Get 7108 chip version!!\n");
+    
+    i2c_start();
+    ack=i2c_sendbyte(0x88,1 );
+    ack=i2c_sendbyte(Sub_Addr,1 );
+    //DBG_DD("send sub_addr ack = 0x%x\n", ack);
+    i2c_stop();
+
+    i2c_start();
+    ack=i2c_sendbyte(0x89,1);
+    //DBG_DD("before readbyte ack = 0x%x\n", ack);
+    ReadData=i2c_readbyte(1);
+    i2c_stop();
+    
+    return(ReadData);	
+}	
+
+/************************************************************************/
+
+Bool   VDEC_FindModule(via_device *via)
+{
+
+    I2C_enable();
+
+    switch (via->video_dev->minor)
+    {
+    case COMMAND_FOR_TV0 :  /* Find video decoder type of capture 0 */
+ 	    if ( (Get7108ChipID(0x1c) == 0x04) 
+ 	        && ( (ReadReg(Philips7108H_Slave_Write40, Philips7108H_Slave_Read41, 0x00) >> 4) == 0x00 ) ) //SA7108
+	    {
+            DBG_DD("via_v4l : Video Decoder SAA7108 for capture 0 found! \n");
+            via->CapInfo.VideoDecoder = SAA7108H;
+            via->CapInfo.Vdec_Slave_Write = 0x40;
+            return TRUE;
+        }
+        else if ( (((ReadReg(Philips7113H_Slave_Write48, 
+                        Philips7113H_Slave_Read49, 0x00))&0xf0) == 0x00)
+                  ||(((ReadReg(Philips7113H_Slave_Write48, 
+                        Philips7113H_Slave_Read49, 0x00))&0xf0) == 0x10) )
+        {
+            DBG_DD("via_v4l : Video Decoder SAA7113 for capture 0 found! \n");
+            via->CapInfo.VideoDecoder = SAA7113H;
+            via->CapInfo.Vdec_Slave_Write = 0x48;
+            return TRUE;
+        }
+        else
+        {
+    	    DBG_DD("via_v4l : Video Decoder for capture 0 not found! \n");
+    	    via->CapInfo.VideoDecoder = 0;
+            return FALSE;
+        }
+        break;
+
+    case COMMAND_FOR_TV1 :  /* Find video decoder type of capture 1 */
+ 	    if ( (Get7108ChipID(0x1c) == 0x04) 
+ 	        && ( (ReadReg(Philips7108H_Slave_Write42, Philips7108H_Slave_Read43, 0x00) >> 4) == 0x00 ) ) //SA7108
+	    {
+            DBG_DD("via_v4l : Video Decoder SAA7108 for capture 1 found! \n");
+            via->CapInfo.VideoDecoder = SAA7108H;
+            via->CapInfo.Vdec_Slave_Write = 0x42;
+            return TRUE;
+        }
+        else if ( (((ReadReg(Philips7113H_Slave_Write4a, 
+                        Philips7113H_Slave_Read4b, 0x00))&0xf0) == 0x00)
+                  ||(((ReadReg(Philips7113H_Slave_Write4a, 
+                        Philips7113H_Slave_Read4b, 0x00))&0xf0) == 0x10) )
+        {
+            DBG_DD("via_v4l : Video Decoder SAA7113 for capture 1 found! \n");
+            via->CapInfo.VideoDecoder = SAA7113H;
+            via->CapInfo.Vdec_Slave_Write = 0x4a;
+            return TRUE;
+        }
+        /*else if ( (((ReadReg(0x40,0x41, 0x00))&0xf0) == 0x00)
+                  ||(((ReadReg(0x40,0x41, 0x00))&0xf0) == 0x10) )
+        {
+            DBG_DD("via_v4l : Video Decoder SAA7114 for capture 1 found! \n");
+            via->CapInfo.VideoDecoder = SAA7114H;
+            via->CapInfo.Vdec_Slave_Write = 0x40;
+            return TRUE;
+        }*/
+        else
+        {
+    	    DBG_DD("via_v4l : Video Decoder for capture 1 not found! \n");
+    	    via->CapInfo.VideoDecoder = 0;
+            return FALSE;
+        }
+        break;
+    }
+
+    return FALSE;
+}
+
+void    VDEC_Initialize(via_device *via)
+{
+
+   switch ( via->CapInfo.VideoDecoder ) {
+          case   SAA7113H :
+                 DBG_DD("//        : VDEC_INitialize : SAA7113H\n");
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x01, 0x08);
+                 if (via->CapInfo.NoAutoDetect)
+                 {
+                     WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x02, 0xc0|via->CapInfo.CompositeMode);
+                 }
+                 else
+                 {
+                     WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x02, 0xc9);
+                 }
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x03, 0x33);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x04, 0x00);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x05, 0x00);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x06, 0xE9);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x07, 0x0D);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x08, 0xf8);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x09, 0x01);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x0A, 0x80);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x0B, 0x47);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x0C, 0x40);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x0D, 0x00);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x0E, 0x01);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x0F, 0x2A);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x10, 0x40); // set D3, detail see SAA7113H spec P.59
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x11, 0x08);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x12, 0xb7);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x13, 0x00);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x14, 0x00);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x15, 0x00);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x16, 0x00);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x17, 0x00);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x40, 0x02);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x41, 0xFF);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x42, 0xFF);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x43, 0xFF);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x44, 0xFF);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x45, 0xFF);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x46, 0xFF);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x47, 0xFF);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x48, 0xFF);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x49, 0xFF);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x4A, 0xFF);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x4B, 0xFF);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x4C, 0xFF);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x4D, 0xFF);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x4E, 0xFF);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x4F, 0xFF);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x50, 0xFF);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x51, 0xFF);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x52, 0xFF);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x53, 0xFF);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x54, 0xFF);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x55, 0xFF);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x56, 0xFF);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x57, 0xFF);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x58, 0x00);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x59, 0x54);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x5A, 0x0a);
+                 WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x5B, 0x83);
+                 break;
+
+          case   SAA7108H :
+                 DBG_DD("//        : VDEC_INitialize : SAA7108H\n");
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x01, 0x08 );
+                 if (via->CapInfo.NoAutoDetect)
+                 {
+                     WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x02, 0xc0|via->CapInfo.CompositeMode);
+                 }
+                 else
+                 {
+                     WriteReg( via->CapInfo.Vdec_Slave_Write, 0x02, 0xc0 );
+                 }
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x03, 0x10 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x04, 0x90 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x05, 0x90 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x06, 0xeb );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x07, 0xe0 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x08, 0x98 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x09, 0x80 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x0A, 0x80 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x0B, 0x44 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x0C, 0x40 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x0D, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x0E, 0x89 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x0F, 0x2a );
+                 
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x10, 0x0e );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x11, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x12, 0x00 );
+                 /*  Set 0x13 OFTS[2:0]=001 can fix Philip DVD732K player has garbage
+                  *  line on top through capture port.
+                  *  detail see SAA7114H spec P.101 or SAA7108E
+                  */
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x13, 0x01 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x14, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x15, 0x11 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x16, 0xfe );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x17, 0x40 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x18, 0x40 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x19, 0x80 );
+                 
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x80, 0x1c );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x81, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x82, 0x00 );
+                 if (via->CapInfo.Scaler)
+                 {
+                     WriteReg( via->CapInfo.Vdec_Slave_Write, 0x83, 0x00 );
+                 }
+                 else
+                 {
+                     WriteReg( via->CapInfo.Vdec_Slave_Write, 0x83, 0x01 );
+                 }
+
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x84, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x85, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x86, 0x45 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x87, 0x01 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x88, 0xf0 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x8F, 0x0b );
+                 
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x90, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x91, 0x08 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x92, 0x09 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x93, 0x80 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x94, 0x02 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x95, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x96, 0xd0 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x97, 0x02 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x98, 0x12 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x99, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x9A, 0xff );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x9B, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x9C, 0xd0 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x9D, 0x02 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x9E, 0xff );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x9F, 0x00 );
+                 
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xA0, 0x01 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xA1, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xA2, 0x00 );
+                 
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xA4, 0x80 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xA5, 0x40 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xA6, 0x40 );
+                 
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xA8, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xA9, 0x04 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xAA, 0x00 );
+                 
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xAC, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xAD, 0x02 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xAE, 0x00 );
+                 
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xB0, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xB1, 0x04 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xB2, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xB3, 0x04 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xB4, 0x00 );
+                 
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xB8, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xB9, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xBA, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xBB, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xBC, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xBD, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xBE, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xBF, 0x00 );
+                 
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x88, 0xd0 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x88, 0xf0 );
+                 break;
+          case   SAA7114H :
+                 DBG_DD("//        : VDEC_INitialize : SAA7114H\n");
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x01, 0x08 );
+                 if (via->CapInfo.NoAutoDetect)
+                 {
+                     WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x02, 0xc0|via->CapInfo.CompositeMode);
+                 }
+                 else
+                 {
+                     WriteReg( via->CapInfo.Vdec_Slave_Write, 0x02, 0xc2 );
+                 }
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x03, 0x10 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x04, 0x90 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x05, 0x90 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x06, 0xeb );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x07, 0xe0 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x08, 0x98 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x09, 0x80 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x0A, 0x80 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x0B, 0x44 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x0C, 0x40 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x0D, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x0E, 0x89 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x0F, 0x2a );
+                 
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x10, 0x0e );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x11, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x12, 0x00 );
+                 /*  Set 0x13 OFTS[2:0]=001 can fix Philip DVD732K player has garbage
+                  *  line on top through capture port.
+                  *  detail see SAA7114H spec P.101 or SAA7108E
+                  */
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x13, 0x01 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x14, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x15, 0x11 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x16, 0xfe );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x17, 0x40 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x18, 0x40 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x19, 0x80 );
+                 
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x80, 0x1c );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x81, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x82, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x83, 0x01 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x84, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x85, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x86, 0x45 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x87, 0x01 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x88, 0xf0 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x8F, 0x0b );
+                 
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x90, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x91, 0x08 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x92, 0x09 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x93, 0x80 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x94, 0x02 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x95, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x96, 0xd0 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x97, 0x02 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x98, 0x12 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x99, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x9A, 0xff );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x9B, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x9C, 0xd0 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x9D, 0x02 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x9E, 0xff );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x9F, 0x00 );
+                 
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xA0, 0x01 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xA1, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xA2, 0x00 );
+                 
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xA4, 0x80 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xA5, 0x40 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xA6, 0x40 );
+                 
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xA8, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xA9, 0x04 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xAA, 0x00 );
+                 
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xAC, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xAD, 0x02 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xAE, 0x00 );
+                 
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xB0, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xB1, 0x04 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xB2, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xB3, 0x04 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xB4, 0x00 );
+                 
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xB8, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xB9, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xBA, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xBB, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xBC, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xBD, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xBE, 0x00 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0xBF, 0x00 );
+                 
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x88, 0xd0 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x88, 0xf0 );
+                 break;
+      }
+}
+
+
+
+
+
+void   VDEC_Input_Composite(via_device *via)
+{
+   //DBG_DD("VDEC: VDEC_Input_Composite()\n");
+
+   switch ( via->CapInfo.VideoDecoder ) {
+          case   SAA7113H :
+                 //Bits D7 and D6 : Amplifier plus anti-alias filter active
+                 //Bits D5 and D4 : +-2LSB
+                 //Bits D3 to  D0 : Input AI11, Mode 0(CVBS)
+                 if (via->CapInfo.NoAutoDetect)
+                 {
+                     WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x02, 0xc0|via->CapInfo.CompositeMode);
+                 }
+                 else
+                 {
+                     WriteReg(via->CapInfo.Vdec_Slave_Write, 0x02, 0xC2);
+                 }
+
+                 //To be continued. The vlue is for 60HZ 525 Lines (NTSC)
+                 //WriteReg(via->CapInfo.Vdec_Slave_Write,
+                 //               0x08,0xe8);
+
+                 //Bit 7 : 0 , Not Full luminanc bandwidth
+                 WriteReg(via->CapInfo.Vdec_Slave_Write, 0x09,0x01);
+                 break;
+          
+          case   SAA7108H :
+                 if (via->CapInfo.NoAutoDetect)
+                 {
+                     WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x02, 0xc0|via->CapInfo.CompositeMode);
+                 }
+                 else
+                 {
+                     WriteReg( via->CapInfo.Vdec_Slave_Write, 0x02, 0xc0 );
+                 }
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x09, 0x40 );
+
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x08, 0x58 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x08, 0xf8 );
+
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x88, 0xd0 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x88, 0xf0 );
+                 break;
+          case   SAA7114H :
+                 if (via->CapInfo.NoAutoDetect)
+                 {
+                     WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x02, 0xc0|via->CapInfo.CompositeMode);
+                 }
+                 else
+                 {
+                     WriteReg( via->CapInfo.Vdec_Slave_Write, 0x02, 0xc2 );
+                 }
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x09, 0x40 );
+
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x08, 0x58 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x08, 0xf8 );
+
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x88, 0xd0 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x88, 0xf0 );
+                 break;
+
+     }
+}
+
+
+
+
+void   VDEC_Input_SVIDEO(via_device *via)
+{
+   //DBG_DD("VDEC: VDEC_Input_SVIDEO()\n");
+
+   switch ( via->CapInfo.VideoDecoder ) {
+          case   SAA7113H :
+                 //Bits D7 and D6 : Amplifier plus anti-alias filter active
+                 //Bits D5 and D4 : +-2LSB
+                 //Bits D3 to  D0 : Input AI12, AI22, Mode 9(SVIDEO)
+                 if (via->CapInfo.NoAutoDetect)
+                 {
+                     WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x02, 0xc0|via->CapInfo.SVideoMode);
+                 }
+                 else
+                 {
+                     WriteReg(via->CapInfo.Vdec_Slave_Write, 0x02, 0xC9);
+                 }
+
+                 //To be continued. The vlue is for 60HZ 525 Lines (NTSC)
+                 //WriteReg(via->CapInfo.Vdec_Slave_Write,
+                 //               0x08,0xe8);
+
+                 //Bit 7 : 1 , Full luminanc bandwidth
+                 WriteReg(via->CapInfo.Vdec_Slave_Write, 0x09,0x81);
+                 break;
+                 
+          case   SAA7108H :
+                 if (via->CapInfo.NoAutoDetect)
+                 {
+                     WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x02, 0xc0|via->CapInfo.SVideoMode);
+                 }
+                 else
+                 {
+                     WriteReg( via->CapInfo.Vdec_Slave_Write, 0x02, 0xC6 );
+                 }
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x09, 0x80 );
+
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x08, 0x58 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x08, 0xf8 );
+
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x88, 0xd0 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x88, 0xf0 );
+                 break;
+
+          case   SAA7114H :
+                 if (via->CapInfo.NoAutoDetect)
+                 {
+                     WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x02, 0xc0|via->CapInfo.SVideoMode);
+                 }
+                 else
+                 {
+                     WriteReg( via->CapInfo.Vdec_Slave_Write, 0x02, 0xC7 );
+                 }
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x09, 0x80 );
+
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x08, 0x58 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x08, 0xf8 );
+
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x88, 0xd0 );
+                 WriteReg( via->CapInfo.Vdec_Slave_Write, 0x88, 0xf0 );
+                 break;
+    }
+
+}
+
+
+void   VDEC_Input_TV(via_device *via)
+{
+   //DBG_DD("VDEC: VDEC_Input_TV()\n");
+   switch ( via->CapInfo.VideoDecoder ) {
+          case   SAA7113H :
+                 //Bits D7 and D6 : Amplifier plus anti-alias filter active
+                 //Bits D5 and D4 : +-2LSB
+                 //Bits D3 to  D0 : Input AI21, Mode 2(TV)
+                 if (via->CapInfo.NoAutoDetect)
+                 {
+                     WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x02, 0xc0|via->CapInfo.TunerMode);
+                 }
+                 else
+                 {
+                     WriteReg(via->CapInfo.Vdec_Slave_Write, 0x02, 0xC0);
+                 }
+
+                 //To be continued. The vlue is for 60HZ 525 Lines (NTSC)
+                 //WriteReg(via->CapInfo.Vdec_Slave_Write,
+                 //               0x08,0xe8);
+
+                 //Bit 7 : 0 , Not Full luminanc bandwidth
+                 WriteReg(via->CapInfo.Vdec_Slave_Write, 0x09,0x01);
+
+                 break;
+                 
+          case   SAA7108H :
+                 break;
+
+          case   SAA7114H :
+                 //Bits D7 and D6 : Amplifier plus anti-alias filter active
+                 //Bits D5 and D4 : +-2LSB
+                 //Bits D3 to  D0 : Input AI21, Mode 2(TV)
+                 if (via->CapInfo.NoAutoDetect)
+                 {
+                     WriteReg(  via->CapInfo.Vdec_Slave_Write, 0x02, 0xc0|via->CapInfo.TunerMode);
+                 }
+                 else
+                 {
+                     WriteReg(via->CapInfo.Vdec_Slave_Write, 0x02, 0xC0);
+                 }
+
+                 break;
+    }
+}
+
+
+
+void   VDEC_Saturation(unsigned char data, via_device *via)
+{
+   switch ( via->CapInfo.VideoDecoder ) {
+          case   SAA7113H :
+          case   SAA7108H :
+          case   SAA7114H :
+                 WriteReg(via->CapInfo.Vdec_Slave_Write, 0x0C, data);
+                 break;
+   }
+
+}
+
+void   VDEC_Hue(unsigned char data, via_device *via)
+{
+   switch ( via->CapInfo.VideoDecoder ) {
+          case   SAA7113H :
+          case   SAA7108H :
+          case   SAA7114H :
+                 WriteReg(via->CapInfo.Vdec_Slave_Write, 0x0D, data);
+                 break;
+   }
+
+}
+
+void   VDEC_Brightness(unsigned char data, via_device *via)
+{
+   switch ( via->CapInfo.VideoDecoder ) {
+          case   SAA7113H :
+          case   SAA7108H :
+          case   SAA7114H :
+                 WriteReg(via->CapInfo.Vdec_Slave_Write, 0x0A, data);
+                 break;
+   }
+
+}
+
+void   VDEC_Contrast(unsigned char data, via_device *via)
+{
+   switch ( via->CapInfo.VideoDecoder ) {
+          case   SAA7113H :
+          case   SAA7108H :
+          case   SAA7114H :
+                 WriteReg(via->CapInfo.Vdec_Slave_Write, 0x0B, data);
+                 break;
+   }
+
+}
+
+void   VDEC_Luminance(unsigned char data, via_device *via)
+{
+   switch ( via->CapInfo.VideoDecoder ) {
+          case   SAA7113H :
+          case   SAA7108H :
+          case   SAA7114H :
+                 WriteReg(via->CapInfo.Vdec_Slave_Write, 0x09, data);
+                 break;
+   }
+
+}
+
+void     VDEC_Standard_SECAM(via_device *via)
+{
+   bSetFirst = 0;
+
+   switch ( via->CapInfo.VideoDecoder ){
+      case SAA7113H :
+              WriteReg(via->CapInfo.Vdec_Slave_Write, 0x08, 0xa8);
+              WriteReg(via->CapInfo.Vdec_Slave_Write, 0x0E, 0x51);
+              WriteReg(via->CapInfo.Vdec_Slave_Write, 0x40, 0x0a);
+              WriteReg(via->CapInfo.Vdec_Slave_Write, 0x5A, 0x07);
+              break;
+      
+      case SAA7108H :
+      case SAA7114H :
+              WriteReg( via->CapInfo.Vdec_Slave_Write, 0x8F, 0x08 );
+              WriteReg( via->CapInfo.Vdec_Slave_Write, 0x9A, 0x30 );
+              WriteReg( via->CapInfo.Vdec_Slave_Write, 0x9B, 0x01 );
+              WriteReg( via->CapInfo.Vdec_Slave_Write, 0x9E, 0x30 );
+              WriteReg( via->CapInfo.Vdec_Slave_Write, 0x9F, 0x01 );
+              WriteReg( via->CapInfo.Vdec_Slave_Write, 0x88, 0xd0 );
+              WriteReg( via->CapInfo.Vdec_Slave_Write, 0x88, 0xf0 );
+                          
+              break;
+
+   }
+}
+
+void     VDEC_Standard_PAL(via_device *via)
+{
+   //DBG_DD("VDEC: VDEC_Standard_PAL()\n");
+   bSetFirst = 0;
+
+   switch ( via->CapInfo.VideoDecoder ){
+      case SAA7113H :
+              WriteReg(via->CapInfo.Vdec_Slave_Write, 0x08, 0xa8);
+              WriteReg(via->CapInfo.Vdec_Slave_Write, 0x0E, 0x01);
+              WriteReg(via->CapInfo.Vdec_Slave_Write, 0x40, 0x0a);
+              WriteReg(via->CapInfo.Vdec_Slave_Write, 0x5A, 0x07);
+              break;
+      
+      case SAA7108H :
+      case SAA7114H :
+              WriteReg( via->CapInfo.Vdec_Slave_Write, 0x08, 0xd8 );
+              WriteReg( via->CapInfo.Vdec_Slave_Write, 0x0E, 0x89 );
+              WriteReg( via->CapInfo.Vdec_Slave_Write, 0x40, 0x0a );
+              WriteReg( via->CapInfo.Vdec_Slave_Write, 0x5A, 0x07 );      
+              break;              
+              
+   }
+}
+
+void     VDEC_Standard_NTSC(via_device *via)
+{
+   //DBG_DD("VDEC: VDEC_Standard_NTSC()\n");
+   bSetFirst = 0;
+
+   switch ( via->CapInfo.VideoDecoder ){
+      case SAA7113H :
+              WriteReg(via->CapInfo.Vdec_Slave_Write, 0x08, 0xe8);
+              WriteReg(via->CapInfo.Vdec_Slave_Write, 0x0E, 0x01);
+              WriteReg(via->CapInfo.Vdec_Slave_Write, 0x40, 0x02);
+              WriteReg(via->CapInfo.Vdec_Slave_Write, 0x5A, 0x0a);
+              break;
+      
+      case SAA7108H :
+      case SAA7114H :
+              WriteReg( via->CapInfo.Vdec_Slave_Write, 0x8F, 0x0b );
+              WriteReg( via->CapInfo.Vdec_Slave_Write, 0x9A, 0xff );
+              WriteReg( via->CapInfo.Vdec_Slave_Write, 0x9B, 0x00 );
+              WriteReg( via->CapInfo.Vdec_Slave_Write, 0x9E, 0xff );
+              WriteReg( via->CapInfo.Vdec_Slave_Write, 0x9F, 0x00 );
+              WriteReg( via->CapInfo.Vdec_Slave_Write, 0x88, 0xd0 );
+              WriteReg( via->CapInfo.Vdec_Slave_Write, 0x88, 0xf0 );
+
+              break;           
+
+    }
+}
+
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/vdec.h linux-2.6.1-rc1-gentoo/drivers/media/video/vdec.h
--- linux-2.6.0/drivers/media/video/vdec.h	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/vdec.h	2004-01-06 17:28:06.000000000 +0000
@@ -0,0 +1,63 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#ifndef  __VDEC_H
+#define  __VDEC_H
+
+#ifdef __KERNEL__
+#include "via_v4l.h"
+#endif
+
+#define Philips7113H_Slave_Write48  0x48
+#define Philips7113H_Slave_Read49   0x49
+#define Philips7113H_Slave_Write4a  0x4a
+#define Philips7113H_Slave_Read4b   0x4b
+
+#define Philips7108H_Slave_Write40  0x40
+#define Philips7108H_Slave_Read41   0x41
+#define Philips7108H_Slave_Write42  0x42
+#define Philips7108H_Slave_Read43   0x43
+
+#define SAA7113H                    0x01
+#define SAA7108H                    0x02
+#define SAA7114H                    0x03
+
+
+#ifdef __KERNEL__
+Bool     VDEC_FindModule(via_device *via);
+void     VDEC_Initialize(via_device *via);
+void     VDEC_Standard_NTSC(via_device *via);
+void     VDEC_Standard_PAL(via_device *via);
+void     VDEC_Standard_SECAM(via_device *via);
+void     VDEC_Input_Composite(via_device *via);
+void     VDEC_Input_SVIDEO(via_device *via);
+void     VDEC_Input_TV(via_device *via);
+void     VDEC_Saturation(unsigned char data, via_device *via);
+void     VDEC_Hue(unsigned char data, via_device *via);
+void     VDEC_Brightness(unsigned char data, via_device *via);
+void     VDEC_Contrast(unsigned char data, via_device *via);
+void     VDEC_Luminance(unsigned char data, via_device *via);
+#endif /* __KERNEL__ */
+
+#endif   /* __VDEC_H */
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/via.h linux-2.6.1-rc1-gentoo/drivers/media/video/via.h
--- linux-2.6.0/drivers/media/video/via.h	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/via.h	2004-01-06 17:28:06.000000000 +0000
@@ -0,0 +1,600 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+/* Video status flag */
+
+#define VIDEO_SHOW              0x80000000  /*Video on*/
+#define VIDEO_HIDE              0x00000000  /*Video off*/
+#define VIDEO_MPEG_INUSE        0x08000000  /*Video is used with MPEG */
+#define VIDEO_HQV_INUSE         0x04000000  /*Video is used with HQV*/
+#define VIDEO_CAPTURE0_INUSE    0x02000000  /*Video is used with CAPTURE 0*/
+#define VIDEO_CAPTURE1_INUSE    0x00000000  /*Video is used with CAPTURE 1*/
+#define VIDEO_1_INUSE           0x01000000  /*Video 1 is used with software flip*/
+#define VIDEO_3_INUSE           0x00000000  /*Video 3 is used with software flip*/
+#define MPEG_USE_V1             0x00010000  /*[16] : 1:MPEG use V1, 0:MPEG use V3*/
+#define MPEG_USE_V3             0x00000000  /*[16] : 1:MPEG use V1, 0:MPEG use V3*/
+#define MPEG_USE_HQV            0x00020000  /*[17] : 1:MPEG use HQV,0:MPEG not use HQV*/
+#define MPEG_USE_HW_FLIP        0x00040000  /*[18] : 1:MPEG use H/W flip,0:MPEG use S/W flip*/
+#define MPEG_USE_SW_FLIP        0x00000000  /*[18] : 1:MPEG use H/W flip,0:MPEG use S/W flip*/
+#define CAP0_USE_V1             0x00001000  /*[12] : 1:Capture 0 use V1, 0:Capture 0 use V3*/
+#define CAP0_USE_V3             0x00000000  /*[12] : 1:Capture 0 use V1, 0:Capture 0 use V3*/
+#define CAP0_USE_HQV            0x00002000  /*[13] : 1:Capture 0 use HQV,0:Capture 0 not use HQV*/
+#define CAP0_USE_HW_FLIP        0x00004000  /*[14] : 1:Capture 0 use H/W flip,0:Capture 0 use S/W flip*/
+#define CAP0_USE_CCIR656        0x00008000  /*[15] : 1:Capture 0 use CCIR656,0:Capture 0 CCIR601*/
+#define CAP1_USE_V1             0x00000100  /*[ 8] : 1:Capture 1 use V1, 0:Capture 1 use V3*/
+#define CAP1_USE_V3             0x00000000  /*[ 8] : 1:Capture 1 use V1, 0:Capture 1 use V3*/
+#define CAP1_USE_HQV            0x00000200  /*[ 9] : 1:Capture 1 use HQV,0:Capture 1 not use HQV*/
+#define CAP1_USE_HW_FLIP        0x00000400  /*[10] : 1:Capture 1 use H/W flip,0:Capture 1 use S/W flip  */
+#define SW_USE_V1               0x00000010  /*[ 4] : 1:Capture 1 use V1, 0:Capture 1 use V3             */
+#define SW_USE_V3               0x00000000  /*[ 4] : 1:Capture 1 use V1, 0:Capture 1 use V3             */
+#define SW_USE_HQV              0x00000020  /*[ 5] : 1:Capture 1 use HQV,0:Capture 1 not use HQV        */
+     
+/*
+#define VIDEO1_INUSE            0x00000010  //[ 4] : 1:Video 1 is used with S/W flip
+#define VIDEO1_USE_HQV          0x00000020  //[ 5] : 1:Video 1 use HQV with S/W flip
+#define VIDEO3_INUSE            0x00000001  //[ 0] : 1:Video 3 is used with S/W flip
+#define VIDEO3_USE_HQV          0x00000002  //[ 1] : 1:Video 3 use HQV with S/W flip
+*/
+
+/* H/W registers for Video Engine */
+
+/*
+ *      bus master
+ */
+#define PCI_MASTER_ENABLE       0x01
+#define PCI_MASTER_SCATTER      0x00
+#define PCI_MASTER_SINGLE       0x02
+#define PCI_MASTER_GUI          0x00
+#define PCI_MASTER_VIDEO        0x04
+#define PCI_MASTER_INPUT        0x00
+#define PCI_MASTER_OUTPUT       0x08
+
+/*
+ *      video registers
+ */
+#define V_FLAGS				    0x00
+#define V_CAP_STATUS            0x04
+#define V_FLIP_STATUS           0x04
+#define V_ALPHA_WIN_START       0x08
+#define V_ALPHA_WIN_END         0x0C
+#define V_ALPHA_CONTROL         0x10
+#define V_CRT_STARTADDR         0x14
+#define V_CRT_STARTADDR_2       0x18
+#define V_ALPHA_STRIDE          0x1C
+#define V_COLOR_KEY             0x20
+#define V_ALPHA_STARTADDR       0x24
+#define V_CHROMAKEY_LOW         0x28
+#define V_CHROMAKEY_HIGH        0x2C
+#define V1_CONTROL              0x30
+#define V12_QWORD_PER_LINE      0x34
+#define V1_STARTADDR_1          0x38
+#define V1_STARTADDR_Y1         V1_STARTADDR_1
+#define V1_STRIDE               0x3C
+#define V1_WIN_START_Y          0x40
+#define V1_WIN_START_X          0x42
+#define V1_WIN_END_Y            0x44
+#define V1_WIN_END_X            0x46
+#define V1_STARTADDR_2          0x48
+#define V1_STARTADDR_Y2         V1_STARTADDR_2
+#define V1_ZOOM_CONTROL         0x4C
+#define V1_MINI_CONTROL         0x50
+#define V1_STARTADDR_0          0x54
+#define V1_STARTADDR_Y0         V1_STARTADDR_0
+#define V_FIFO_CONTROL          0x58
+#define V1_STARTADDR_3          0x5C
+#define V1_STARTADDR_Y3         V1_STARTADDR_3
+#define HI_CONTROL              0x60
+#define SND_COLOR_KEY           0x64
+#define ALPHA_V3_PREFIFO_CONTROL   0x68
+#define V1_SOURCE_HEIGHT        0x6C
+#define HI_TRANSPARENT_COLOR    0x70
+#define V_DISPLAY_TEMP          0x74  /* No use */
+#define ALPHA_V3_FIFO_CONTROL   0x78
+#define V3_SOURCE_WIDTH         0x7C
+#define V3_COLOR_KEY            0x80
+#define V1_ColorSpaceReg_1      0x84
+#define V1_ColorSpaceReg_2      0x88
+#define V1_STARTADDR_CB0        0x8C
+#define V1_OPAQUE_CONTROL       0x90  /* To be deleted */
+#define V3_OPAQUE_CONTROL       0x94  /* To be deleted */
+#define V_COMPOSE_MODE          0x98
+#define V3_STARTADDR_2          0x9C
+#define V3_CONTROL              0xA0
+#define V3_STARTADDR_0          0xA4
+#define V3_STARTADDR_1          0xA8
+#define V3_STRIDE               0xAC
+#define V3_WIN_START_Y          0xB0
+#define V3_WIN_START_X          0xB2
+#define V3_WIN_END_Y            0xB4
+#define V3_WIN_END_X            0xB6
+#define V3_ALPHA_QWORD_PER_LINE 0xB8
+#define V3_ZOOM_CONTROL         0xBC
+#define V3_MINI_CONTROL         0xC0
+#define V3_ColorSpaceReg_1      0xC4
+#define V3_ColorSpaceReg_2      0xC8
+#define V3_DISPLAY_TEMP         0xCC  /* No use */
+#define V1_STARTADDR_CB1        0xE4
+#define V1_STARTADDR_CB2        0xE8
+#define V1_STARTADDR_CB3        0xEC
+#define V1_STARTADDR_CR0        0xF0
+#define V1_STARTADDR_CR1        0xF4
+#define V1_STARTADDR_CR2        0xF8
+#define V1_STARTADDR_CR3        0xFC
+
+/* Video Capture Engine Registers 
+ * Capture Port 1
+ */
+#define CAP0_MASKS          0x100
+#define CAP1_MASKS          0x104
+#define CAP0_CONTROL        0x110
+#define CAP0_H_RANGE        0x114
+#define CAP0_V_RANGE        0x118
+#define CAP0_SCAL_CONTROL   0x11C 
+#define CAP0_VBI_H_RANGE    0x120
+#define CAP0_VBI_V_RANGE    0x124
+#define CAP0_VBI_STARTADDR  0x128
+#define CAP0_VBI_STRIDE     0x12C 
+#define CAP0_ANCIL_COUNT    0x130
+#define CAP0_MAXCOUNT       0x134
+#define CAP0_VBIMAX_COUNT   0x138
+#define CAP0_DATA_COUNT     0x13C 
+#define CAP0_FB_STARTADDR0  0x140
+#define CAP0_FB_STARTADDR1  0x144
+#define CAP0_FB_STARTADDR2  0x148
+#define CAP0_STRIDE         0x150
+/* Capture Port 2 */
+#define CAP1_CONTROL        0x154
+#define CAP1_SCAL_CONTROL   0x160
+#define CAP1_VBI_H_RANGE    0x164 /*To be deleted*/
+#define CAP1_VBI_V_RANGE    0x168 /*To be deleted*/
+#define CAP1_VBI_STARTADDR  0x16C /*To be deleted*/
+#define CAP1_VBI_STRIDE     0x170 /*To be deleted*/
+#define CAP1_ANCIL_COUNT    0x174 /*To be deleted*/
+#define CAP1_MAXCOUNT       0x178
+#define CAP1_VBIMAX_COUNT   0x17C /*To be deleted*/
+#define CAP1_DATA_COUNT     0x180 
+#define CAP1_FB_STARTADDR0  0x184
+#define CAP1_FB_STARTADDR1  0x188
+#define CAP1_STRIDE         0x18C 
+
+/* SUBPICTURE Registers */
+#define SUBP_CONTROL_STRIDE     0x1C0
+#define SUBP_STARTADDR          0x1C4
+#define RAM_TABLE_CONTROL       0x1C8
+#define RAM_TABLE_READ          0x1CC
+
+/* HQV Registers */
+#define HQV_CONTROL             0x1D0
+#define HQV_SRC_STARTADDR_Y     0x1D4
+#define HQV_SRC_STARTADDR_U     0x1D8
+#define HQV_SRC_STARTADDR_V     0x1DC
+#define HQV_SRC_FETCH_LINE      0x1E0
+#define HQV_FILTER_CONTROL      0x1E4
+#define HQV_MINIFY_CONTROL      0x1E8
+#define HQV_DST_STARTADDR0      0x1EC
+#define HQV_DST_STARTADDR1      0x1F0
+#define HQV_DST_STARTADDR2      0x1FC
+#define HQV_DST_STRIDE          0x1F4
+#define HQV_SRC_STRIDE          0x1F8
+
+
+/*
+ *  Video command definition
+ */
+ 
+/* #define V_FLIP_STATUS           0x204 */
+#define V3_STARTADDR_UPDSTATUS          0x00000008
+
+
+/* #define V_ALPHA_CONTROL         0x210 */
+#define ALPHA_WIN_EXPIRENUMBER_4        0x00040000
+#define ALPHA_WIN_CONSTANT_FACTOR_4     0x00004000
+#define ALPHA_WIN_CONSTANT_FACTOR_12    0x0000c000
+#define ALPHA_WIN_BLENDING_CONSTANT     0x00000000
+#define ALPHA_WIN_BLENDING_ALPHA        0x00000001
+#define ALPHA_WIN_BLENDING_GRAPHIC      0x00000002
+#define ALPHA_WIN_PREFIFO_THRESHOLD_12  0x000c0000
+#define ALPHA_WIN_FIFO_THRESHOLD_8      0x000c0000
+#define ALPHA_WIN_FIFO_DEPTH_16         0x00100000
+
+/* V_CHROMAKEY_LOW         0x228 */
+#define V_CHROMAKEY_V3          0x80000000
+
+/* V1_CONTROL                   0x230 */
+#define V1_ENABLE               0x00000001
+#define V1_FULL_SCREEN          0x00000002
+#define V1_YUV422               0x00000000
+#define V1_RGB32                0x00000004
+#define V1_RGB15                0x00000008
+#define V1_RGB16                0x0000000C
+#define V1_YCbCr420             0x00000010
+#define V1_COLORSPACE_SIGN      0x00000080
+#define V1_SRC_IS_FIELD_PIC     0x00000200
+#define V1_SRC_IS_FRAME_PIC     0x00000000
+#define V1_BOB_ENABLE           0x00400000
+#define V1_FIELD_BASE           0x00000000
+#define V1_FRAME_BASE           0x01000000
+#define V1_SWAP_SW              0x00000000
+#define V1_SWAP_HW_HQV          0x02000000
+#define V1_SWAP_HW_CAPTURE      0x04000000
+#define V1_SWAP_HW_MC           0x06000000
+/* #define V1_DOUBLE_BUFFERS       0x00000000 */
+/* #define V1_QUADRUPLE_BUFFERS    0x18000000 */
+#define V1_EXPIRE_NUM           0x00050000
+#define V1_EXPIRE_NUM_A         0x000a0000
+#define V1_EXPIRE_NUM_F         0x000f0000 /* jason */
+#define V1_FIFO_EXTENDED        0x00200000
+#define V1_ON_CRT               0x00000000
+#define V1_ON_SND_DISPLAY       0x80000000
+#define V1_FIFO_32V1_32V2       0x00000000
+#define V1_FIFO_48V1_32V2       0x00200000
+
+/* V12_QWORD_PER_LINE           0x234 */
+#define V1_FETCH_COUNT          0x3ff00000
+#define V1_FETCHCOUNT_ALIGNMENT 0x0000000f
+#define V1_FETCHCOUNT_UNIT      0x00000004   /* Doubld QWORD */
+
+/* V1_STRIDE */
+#define V1_STRIDE_YMASK         0x00001fff
+#define V1_STRIDE_UVMASK        0x1ff00000
+
+/* V1_ZOOM_CONTROL              0x24C */
+#define V1_X_ZOOM_ENABLE        0x80000000
+#define V1_Y_ZOOM_ENABLE        0x00008000
+
+/* V1_MINI_CONTROL              0x250 */
+#define V1_X_INTERPOLY          0x00000002  /* X interpolation */
+#define V1_Y_INTERPOLY          0x00000001  /* Y interpolation */
+#define V1_YCBCR_INTERPOLY      0x00000004  /* Y, Cb, Cr all interpolation */
+#define V1_X_DIV_2              0x01000000
+#define V1_X_DIV_4              0x03000000
+#define V1_X_DIV_8              0x05000000
+#define V1_X_DIV_16             0x07000000
+#define V1_Y_DIV_2              0x00010000
+#define V1_Y_DIV_4              0x00030000
+#define V1_Y_DIV_8              0x00050000
+#define V1_Y_DIV_16             0x00070000
+
+/* V1_STARTADDR0               0x254 */
+#define SW_FLIP_ODD             0x08000000
+
+/* V_FIFO_CONTROL               0x258
+ * IA2 has 32 level FIFO for packet mode video format
+ *         32 level FIFO for planar mode video YV12. with extension reg 230 bit 21 enable
+ *         16 level FIFO for planar mode video YV12. with extension reg 230 bit 21 disable
+ * BCos of 128 bits. 1 level in IA2 = 2 level in VT3122
+ */
+#define V1_FIFO_DEPTH12         0x0000000B
+#define V1_FIFO_DEPTH16         0x0000000F
+#define V1_FIFO_DEPTH32         0x0000001F
+#define V1_FIFO_DEPTH48         0x0000002F
+#define V1_FIFO_DEPTH64         0x0000003F   
+#define V1_FIFO_THRESHOLD6      0x00000600
+#define V1_FIFO_THRESHOLD8      0x00000800
+#define V1_FIFO_THRESHOLD12     0x00000C00
+#define V1_FIFO_THRESHOLD16     0x00001000
+#define V1_FIFO_THRESHOLD24     0x00001800
+#define V1_FIFO_THRESHOLD32     0x00002000
+#define V1_FIFO_THRESHOLD40     0x00002800  
+#define V1_FIFO_THRESHOLD48     0x00003000   
+#define V1_FIFO_THRESHOLD56     0x00003800  
+#define V1_FIFO_THRESHOLD61     0x00003D00  
+#define V1_FIFO_PRETHRESHOLD10  0x0A000000
+#define V1_FIFO_PRETHRESHOLD12  0x0C000000
+#define V1_FIFO_PRETHRESHOLD29  0x1d000000
+#define V1_FIFO_PRETHRESHOLD40  0x28000000  
+#define V1_FIFO_PRETHRESHOLD44  0x2c000000
+#define V1_FIFO_PRETHRESHOLD56  0x38000000   
+#define V1_FIFO_PRETHRESHOLD61  0x3D000000   
+
+/* ALPHA_V3_FIFO_CONTROL        0x278
+ * IA2 has 32 level FIFO for packet mode video format
+ *         32 level FIFO for planar mode video YV12. with extension reg 230 bit 21 enable
+ *         16 level FIFO for planar mode video YV12. with extension reg 230 bit 21 disable
+ *          8 level FIFO for ALPHA
+ * BCos of 128 bits. 1 level in IA2 = 2 level in VT3122
+ */
+#define V3_FIFO_DEPTH16         0x0000000F
+#define V3_FIFO_DEPTH24         0x00000017
+#define V3_FIFO_DEPTH32         0x0000001F
+#define V3_FIFO_DEPTH48         0x0000002F
+#define V3_FIFO_DEPTH64         0x0000003F   
+#define V3_FIFO_THRESHOLD8      0x00000800
+#define V3_FIFO_THRESHOLD12     0x00000C00
+#define V3_FIFO_THRESHOLD16     0x00001000
+#define V3_FIFO_THRESHOLD24     0x00001800
+#define V3_FIFO_THRESHOLD29     0x00001D00 
+#define V3_FIFO_THRESHOLD32     0x00002000
+#define V3_FIFO_THRESHOLD40     0x00002800  
+#define V3_FIFO_THRESHOLD48     0x00003000   
+#define V3_FIFO_THRESHOLD56     0x00003800   
+#define V3_FIFO_THRESHOLD61     0x00003D00   
+#define V3_FIFO_PRETHRESHOLD10  0x0000000A
+#define V3_FIFO_PRETHRESHOLD12  0x0000000C
+#define V3_FIFO_PRETHRESHOLD29  0x0000001d
+#define V3_FIFO_PRETHRESHOLD40  0x00000028  
+#define V3_FIFO_PRETHRESHOLD44  0x0000002c
+#define V3_FIFO_PRETHRESHOLD56  0x00000038   
+#define V3_FIFO_PRETHRESHOLD61  0x0000003D   
+#define V3_FIFO_MASK            0x0000007F
+#define ALPHA_FIFO_DEPTH8       0x00070000
+#define ALPHA_FIFO_THRESHOLD4   0x04000000
+#define ALPHA_FIFO_MASK         0xffff0000
+#define ALPHA_FIFO_PRETHRESHOLD4 0x00040000
+
+/* IA2 */
+#define ColorSpaceValue_1       0x140020f2
+#define ColorSpaceValue_2       0x0a0a2c00
+
+#define ColorSpaceValue_1_3123C0      0x13000DED
+#define ColorSpaceValue_2_3123C0      0x13171000
+#define ColorSpaceValue_1_32045       0x13000DED 
+#define ColorSpaceValue_2_32045       0x13171000 
+
+/* For TV setting */
+#define ColorSpaceValue_1TV     0x140020f2
+#define ColorSpaceValue_2TV     0x0a0a2c00
+
+/* V_COMPOSE_MODE               0x298 */
+#define SELECT_VIDEO_IF_COLOR_KEY               0x00000001  /* select video if (color key),otherwise select graphics */
+#define SELECT_VIDEO3_IF_COLOR_KEY              0x00000020  /* For 3123C0, select video3 if (color key),otherwise select graphics */
+#define SELECT_VIDEO_IF_CHROMA_KEY              0x00000002  /* 0x0000000a  //select video if (chroma key ),otherwise select graphics */
+#define ALWAYS_SELECT_VIDEO                     0x00000000  /* always select video,Chroma key and Color key disable */
+#define COMPOSE_V1_V3           0x00000000  /* V1 on top of V3 */
+#define COMPOSE_V3_V1           0x00100000  /* V3 on top of V1 */
+#define COMPOSE_V1_TOP          0x00000000
+#define COMPOSE_V3_TOP          0x00100000
+#define V1_COMMAND_FIRE         0x80000000  /* V1 commands fire */
+#define V3_COMMAND_FIRE         0x40000000  /* V3 commands fire */
+#define V_COMMAND_LOAD          0x20000000  /* Video register always loaded */
+#define V_COMMAND_LOAD_VBI      0x10000000  /* Video register always loaded at vbi without waiting source flip */
+#define V3_COMMAND_LOAD         0x08000000  /* CLE_C0 Video3 register always loaded */
+#define V3_COMMAND_LOAD_VBI     0x00000100  /* CLE_C0 Video3 register always loaded at vbi without waiting source flip */
+#define SECOND_DISPLAY_COLOR_KEY_ENABLE         0x00010000
+
+/* #define V3_STARTADDR_0          0x2A4*/
+#define PLAY_ODD_FIELD          0x08000000
+#define PLAY_EVEN_FIELD         0x00000000
+
+/* V3_ZOOM_CONTROL              0x2bc */
+#define V3_X_ZOOM_ENABLE        0x80000000
+#define V3_Y_ZOOM_ENABLE        0x00008000
+
+/* V3_MINI_CONTROL              0x2c0 */
+#define V3_X_INTERPOLY          0x00000002  /* X interpolation */
+#define V3_Y_INTERPOLY          0x00000001  /* Y interpolation */
+#define V3_YCBCR_INTERPOLY      0x00000004  /* Y, Cb, Cr all interpolation */
+#define V3_X_DIV_2              0x01000000
+#define V3_X_DIV_4              0x03000000
+#define V3_X_DIV_8              0x05000000
+#define V3_X_DIV_16             0x07000000
+#define V3_Y_DIV_2              0x00010000
+#define V3_Y_DIV_4              0x00030000
+#define V3_Y_DIV_8              0x00050000
+#define V3_Y_DIV_16             0x00070000
+
+/* SUBP_CONTROL_STRIDE              0x3c0 */
+#define SUBP_HQV_ENABLE             0x00010000
+#define SUBP_IA44                   0x00020000
+#define SUBP_AI44                   0x00000000
+#define SUBP_STRIDE_MASK            0x00001fff
+#define SUBP_CONTROL_MASK           0x00070000
+
+/* RAM_TABLE_CONTROL                0x3c8 */
+#define RAM_TABLE_RGB_ENABLE        0x00000007
+
+
+/* For Capture1 S/W flip */
+/* #define CAP1_MASKS               0x304 */
+#define CAP_END_OF_ACTIVE_VIDEO_FRAME_STATUS     0x00000001
+#define CAP_FIELD_STATUS                         0x00000004  /* 0:even ; 1:odd */
+#define CAP_WORKING_FRAME_STATUS                 0x00000008
+#define END_OF_FRAME_INTERRUPT_MASK_ENABLE       0x00000100
+
+
+/* CAPTURE0_CONTROL                  0x310 */
+#define C0_ENABLE           		0x00000001
+#define BUFFER_2_MODE       		0x00000000
+#define BUFFER_3_MODE       		0x00000004
+#define BUFFER_4_MODE       		0x00000006
+#define SWAP_YUYV           		0x00000000 
+#define SWAP_UYVY           		0x00000100   
+#define SWAP_YVYU           		0x00000200
+#define SWAP_VYUY           		0x00000300
+#define IN_601_8            		0x00000000
+#define IN_656_8            		0x00000010
+#define IN_601_16           		0x00000020
+#define IN_656_16           		0x00000030
+#define DEINTER_ODD         		0x00000000
+#define DEINTER_EVEN        		0x00001000   
+#define DEINTER_ODD_EVEN    		0x00002000
+#define DEINTER_FRAME       		0x00003000
+#define VIP_1               		0x00000000 
+#define VIP_2               		0x00000400
+#define H_FILTER_2          		0x00010000
+#define H_FILTER_4          		0x00020000 
+#define H_FILTER_8_1331     		0x00030000 
+#define H_FILTER_8_12221    		0x00040000
+#define VIP_ENABLE          		0x00000008
+#define EN_FIELD_SIG        		0x00000800  
+#define VREF_INVERT         		0x00100000
+#define FIELD_INPUT_INVERSE    		0x00400000
+#define FIELD_INVERSE       		0x40000000
+
+#define C1_H_MINI_EN        		0x00000800
+#define C0_H_MINI_EN        		0x00000800
+#define C1_V_MINI_EN        		0x04000000
+#define C0_V_MINI_EN        		0x04000000
+#define C1_H_MINI_2         		0x00000400
+
+/* CAPTURE1_CONTROL                  0x354 */
+#define C1_ENABLE           		0x00000001
+
+/* V3_CONTROL                   0x2A0 */
+#define V3_ENABLE               0x00000001
+#define V3_FULL_SCREEN          0x00000002
+#define V3_YUV422               0x00000000
+#define V3_RGB32                0x00000004
+#define V3_RGB15                0x00000008
+#define V3_RGB16                0x0000000C
+#define V3_COLORSPACE_SIGN      0x00000080
+#define V3_EXPIRE_NUM           0x00040000
+#define V3_EXPIRE_NUM_F         0x000f0000 
+#define V3_EXPIRE_NUM_3205      0x00080000
+#define V3_EXPIRE_NUM_3204      0x00100000
+#define V3_BOB_ENABLE           0x00400000
+#define V3_FIELD_BASE           0x00000000
+#define V3_FRAME_BASE           0x01000000
+#define V3_SWAP_SW              0x00000000
+#define V3_SWAP_HW_HQV          0x02000000
+#define V3_FLIP_HW_CAPTURE0     0x04000000
+#define V3_FLIP_HW_CAPTURE1     0x06000000
+#define V3_ON_SND_DISPLAY       0x80000000  
+
+/* V3_ALPHA_FETCH_COUNT           0x2B8 */
+#define V3_FETCH_COUNT          0x3ff00000
+#define ALPHA_FETCH_COUNT       0x000003ff
+
+/* HQV_CONTROL             0x3D0 */
+#define HQV_RGB32           0x00000000
+#define HQV_RGB16           0x20000000
+#define HQV_RGB15           0x30000000
+#define HQV_YUV422          0x80000000
+#define HQV_YUV420          0xC0000000
+#define HQV_ENABLE          0x08000000
+#define HQV_SRC_SW          0x00000000
+#define HQV_SRC_MC          0x01000000
+#define HQV_SRC_CAPTURE0    0x02000000
+#define HQV_SRC_CAPTURE1    0x03000000
+#define HQV_FLIP_EVEN       0x00000000
+#define HQV_FLIP_ODD        0x00000020
+#define HQV_SW_FLIP         0x00000010   /* Write 1 to flip HQV buffer */
+#define HQV_DEINTERLACE     0x00010000   /* First line of odd field will be repeated 3 times */
+#define HQV_FIELD_2_FRAME   0x00020000   /* Src is field. Display each line 2 times */
+#define HQV_FRAME_2_FIELD   0x00040000   /* Src is field. Display field */
+#define HQV_FRAME_UV        0x00000000   /* Src is Non-interleaved */
+#define HQV_FIELD_UV        0x00100000   /* Src is interleaved */
+#define HQV_IDLE            0x00000008   
+#define HQV_FLIP_STATUS     0x00000001   
+#define HQV_DOUBLE_BUFF     0x00000000
+#define HQV_TRIPLE_BUFF     0x04000000
+#define HQV_SUBPIC_FLIP     0x00008000
+#define HQV_FIFO_STATUS     0x00001000  
+
+/* HQV_FILTER_CONTROL      0x3E4 */
+#define HQV_H_LOWPASS_2TAP  0x00000001
+#define HQV_H_LOWPASS_4TAP  0x00000002
+#define HQV_H_LOWPASS_8TAP1 0x00000003   /* To be deleted */
+#define HQV_H_LOWPASS_8TAP2 0x00000004   /* To be deleted */
+#define HQV_H_HIGH_PASS     0x00000008
+#define HQV_H_LOW_PASS      0x00000000
+#define HQV_V_LOWPASS_2TAP  0x00010000
+#define HQV_V_LOWPASS_4TAP  0x00020000
+#define HQV_V_LOWPASS_8TAP1 0x00030000
+#define HQV_V_LOWPASS_8TAP2 0x00040000
+#define HQV_V_HIGH_PASS     0x00080000
+#define HQV_V_LOW_PASS      0x00000000
+#define HQV_H_HIPASS_F1_DEFAULT 0x00000040
+#define HQV_H_HIPASS_F2_DEFAULT 0x00000000
+#define HQV_V_HIPASS_F1_DEFAULT 0x00400000
+#define HQV_V_HIPASS_F2_DEFAULT 0x00000000
+#define HQV_H_HIPASS_F1_2TAP    0x00000050
+#define HQV_H_HIPASS_F2_2TAP    0x00000100
+#define HQV_V_HIPASS_F1_2TAP    0x00500000
+#define HQV_V_HIPASS_F2_2TAP    0x01000000
+#define HQV_H_HIPASS_F1_4TAP    0x00000060
+#define HQV_H_HIPASS_F2_4TAP    0x00000200
+#define HQV_V_HIPASS_F1_4TAP    0x00600000
+#define HQV_V_HIPASS_F2_4TAP    0x02000000
+#define HQV_H_HIPASS_F1_8TAP    0x00000080
+#define HQV_H_HIPASS_F2_8TAP    0x00000400
+#define HQV_V_HIPASS_F1_8TAP    0x00800000
+#define HQV_V_HIPASS_F2_8TAP    0x04000000
+/* IA2 NEW */
+#define HQV_V_FILTER2           0x00080000
+#define HQV_H_FILTER2           0x00000008
+#define HQV_H_TAP2_11           0x00000041
+#define HQV_H_TAP4_121          0x00000042
+#define HQV_H_TAP4_1111         0x00000401
+#define HQV_H_TAP8_1331         0x00000221
+#define HQV_H_TAP8_12221        0x00000402
+#define HQV_H_TAP16_1991        0x00000159
+#define HQV_H_TAP16_141041      0x0000026A
+#define HQV_H_TAP32             0x0000015A
+#define HQV_V_TAP2_11           0x00410000
+#define HQV_V_TAP4_121          0x00420000
+#define HQV_V_TAP4_1111         0x04010000
+#define HQV_V_TAP8_1331         0x02210000
+#define HQV_V_TAP8_12221        0x04020000
+#define HQV_V_TAP16_1991        0x01590000
+#define HQV_V_TAP16_141041      0x026A0000
+#define HQV_V_TAP32             0x015A0000
+#define HQV_V_FILTER_DEFAULT    0x00420000
+#define HQV_H_FILTER_DEFAULT    0x00000040
+
+
+
+
+/* HQV_MINI_CONTROL        0x3E8 */
+#define HQV_H_MINIFY_ENABLE 0x00000800
+#define HQV_V_MINIFY_ENABLE 0x08000000
+#define HQV_VDEBLOCK_FILTER 0x80000000
+#define HQV_HDEBLOCK_FILTER 0x00008000
+
+/* HQV_SRC_STRIDE          0x3F8 */
+#define HQV_FIFO_DEPTH          0x00030000   /* HQV_FIFO_DEPTH_32045, HQV_FIFO_DEPTH_3123C0 */
+
+
+#define CHROMA_KEY_LOW          0x00FFFFFF
+#define CHROMA_KEY_HIGH         0x00FFFFFF
+
+/* V_CAP_STATUS */
+#define V_ST_UPDATE_NOT_YET     0x00000003
+#define V1_ST_UPDATE_NOT_YET    0x00000001
+#define V3_ST_UPDATE_NOT_YET    0x00000008
+
+#define VBI_STATUS              0x00000002
+
+/*
+ *      Macros for Video MMIO
+ */
+#ifndef V4L2
+#define VIDInB(port)            *((volatile unsigned char *)(lpVidMEMIO + (port)))
+#define VIDInW(port)            *((volatile unsigned short *)(lpVidMEMIO + (port)))
+#define VIDInD(port)            *((volatile unsigned long *)(lpVidMEMIO + (port)))
+#define VIDOutB(port, data)     *((volatile unsigned char *)(lpVidMEMIO + (port))) = (data)
+#define VIDOutW(port, data)     *((volatile unsigned short *)(lpVidMEMIO + (port))) = (data)
+#define VIDOutD(port, data)     *((volatile unsigned long *)(lpVidMEMIO + (port))) = (data)
+#define MPGOutD(port, data)     *((volatile unsigned long *)(lpMPEGMMIO +(port))) = (data)
+#define MPGInD(port)            *((volatile unsigned long *)(lpMPEGMMIO +(port)))
+#endif 
+
+/*
+ *      Macros for GE MMIO
+ */
+#define GEInW(port)             *((volatile unsigned short *)(lpGEMMIO + (port)))
+#define GEInD(port)             *((volatile unsigned long *)(lpGEMMIO + (port)))
+#define GEOutW(port, data)      *((volatile unsigned short *)(lpGEMMIO + (port))) = (data)
+#define GEOutD(port, data)      *((volatile unsigned long *)(lpGEMMIO + (port))) = (data)
+
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/via_drm.h linux-2.6.1-rc1-gentoo/drivers/media/video/via_drm.h
--- linux-2.6.0/drivers/media/video/via_drm.h	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/via_drm.h	2004-01-06 17:28:06.000000000 +0000
@@ -0,0 +1,197 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#ifndef _VIA_DRM_H_
+#define _VIA_DRM_H_
+
+/* WARNING: These defines must be the same as what the Xserver uses.
+ * if you change them, you must change the defines in the Xserver.
+ */
+
+#ifndef _VIA_DEFINES_
+#define _VIA_DEFINES_
+
+#define VIA_DMA_BUF_ORDER		12
+#define VIA_DMA_BUF_SZ 		        (1 << VIA_DMA_BUF_ORDER)
+#define VIA_DMA_BUF_NR 			256
+#define VIA_NR_SAREA_CLIPRECTS 		8
+
+/* Each region is a minimum of 64k, and there are at most 64 of them.
+ */
+#define VIA_NR_TEX_REGIONS 64
+#define VIA_LOG_MIN_TEX_REGION_SIZE 16
+#endif
+
+#define VIA_UPLOAD_TEX0IMAGE  0x1 /* handled clientside */
+#define VIA_UPLOAD_TEX1IMAGE  0x2 /* handled clientside */
+#define VIA_UPLOAD_CTX        0x4
+#define VIA_UPLOAD_BUFFERS    0x8
+#define VIA_UPLOAD_TEX0       0x10
+#define VIA_UPLOAD_TEX1       0x20
+#define VIA_UPLOAD_CLIPRECTS  0x40
+#define VIA_UPLOAD_ALL        0xff
+
+
+/* Indices into buf.Setup where various bits of state are mirrored per
+ * context and per buffer.  These can be fired at the card as a unit,
+ * or in a piecewise fashion as required.
+ */
+ 
+#define VIA_TEX_SETUP_SIZE 8
+
+/* Flags for clear ioctl
+ */
+#define VIA_FRONT   0x1
+#define VIA_BACK    0x2
+#define VIA_DEPTH   0x4
+#define VIA_STENCIL 0x8
+#define VIDEO 0
+#define AGP 1
+typedef struct {
+    unsigned int offset;
+    unsigned int size;
+} drm_via_agp_t;    
+
+typedef struct {
+    unsigned int offset;
+    unsigned int size;
+} drm_via_fb_t;    
+
+typedef struct {
+    unsigned int context;
+    unsigned int type;
+    unsigned int size;
+    unsigned long index;
+    unsigned long offset;
+} drm_via_mem_t;    
+
+typedef struct _drm_via_init {
+    enum {
+	VIA_INIT_MAP = 0x01,
+	VIA_CLEANUP_MAP = 0x02
+    } func;
+/*    
+#if CONFIG_XFREE86_VERSION < XFREE86_VERSION(4,1,0,0)
+    int ring_map_idx;
+    int buffer_map_idx;
+#else
+    unsigned int mmio_offset;
+    unsigned int buffers_offset;
+#endif
+*/
+    unsigned long sarea_priv_offset;
+/*    unsigned int ring_start;
+    unsigned int ring_end;
+    unsigned int ring_size;*/
+/*    unsigned int front_offset;
+    unsigned int back_offset;
+    unsigned int depth_offset;*/
+/*    unsigned int overlay_offset;
+    unsigned int overlay_physical;*/
+/*    unsigned int w;
+    unsigned int h;
+    unsigned int pitch;
+    unsigned int pitch_bits; */
+    unsigned long fb_offset;
+    unsigned long mmio_offset;
+    unsigned long agpAddr;
+} drm_via_init_t;
+
+/* Warning: If you change the SAREA structure you must change the Xserver
+ * structure as well */
+
+typedef struct _drm_via_tex_region {
+    unsigned char next, prev;	/* indices to form a circular LRU  */
+    unsigned char inUse;	/* owned by a client, or free? */
+    int age;			/* tracked by clients to update local LRU's */
+} drm_via_tex_region_t;
+
+typedef struct _drm_via_sarea {
+    unsigned int dirty;
+
+    unsigned int nbox;
+    drm_clip_rect_t boxes[VIA_NR_SAREA_CLIPRECTS];
+
+    /* Maintain an LRU of contiguous regions of texture space.  If
+     * you think you own a region of texture memory, and it has an
+     * age different to the one you set, then you are mistaken and
+     * it has been stolen by another client.  If global texAge
+     * hasn't changed, there is no need to walk the list.
+     *
+     * These regions can be used as a proxy for the fine-grained
+     * texture information of other clients - by maintaining them
+     * in the same lru which is used to age their own textures,
+     * clients have an approximate lru for the whole of global
+     * texture space, and can make informed decisions as to which
+     * areas to kick out.  There is no need to choose whether to
+     * kick out your own texture or someone else's - simply eject
+     * them all in LRU order.  
+     */
+   
+    drm_via_tex_region_t texList[VIA_NR_TEX_REGIONS + 1]; 
+				/* Last elt is sentinal */
+    int texAge;			/* last time texture was uploaded */
+/*    int last_enqueue;	*/	/* last time a buffer was enqueued */
+/*    int last_dispatch;	*/	/* age of the most recently dispatched buffer */
+/*    int last_quiescent; */    	
+    int ctxOwner;		/* last context to upload state */
+
+    int vertexPrim;
+} drm_via_sarea_t;
+
+typedef struct _drm_via_flush_agp {
+    unsigned int offset;
+    unsigned int size;
+    unsigned int index;		
+    int discard;	/* client is finished with the buffer? */
+} drm_via_flush_agp_t;
+
+typedef struct _drm_via_flush_sys {
+    unsigned int offset;
+    unsigned int size;
+    unsigned long index;		
+    int discard;	/* client is finished with the buffer? */
+} drm_via_flush_sys_t;
+
+#ifdef __KERNEL__
+int via_fb_init(struct inode *inode, struct file *filp, unsigned int cmd,
+		unsigned long arg);		
+int via_mem_alloc(struct inode *inode, struct file *filp, unsigned int cmd,
+  		unsigned long arg);				
+int via_mem_free(struct inode *inode, struct file *filp, unsigned int cmd,
+		unsigned long arg);		
+int via_agp_init(struct inode *inode, struct file *filp, unsigned int cmd,
+		unsigned long arg);				
+int via_dma_alloc(struct inode *inode, struct file *filp, unsigned int cmd,
+		unsigned long arg);				
+int via_dma_free(struct inode *inode, struct file *filp, unsigned int cmd,
+		unsigned long arg);				
+int via_map_init(struct inode *inode, struct file *filp, unsigned int cmd,
+		unsigned long arg);				
+int via_flush_agp(struct inode *inode, struct file *filp, unsigned int cmd,
+		unsigned long arg);				
+int via_flush_sys(struct inode *inode, struct file *filp, unsigned int cmd,
+		unsigned long arg);				
+#endif
+#endif /* _VIA_DRM_H_ */
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/via_memmgr.c linux-2.6.1-rc1-gentoo/drivers/media/video/via_memmgr.c
--- linux-2.6.0/drivers/media/video/via_memmgr.c	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/via_memmgr.c	2004-01-06 17:28:06.000000000 +0000
@@ -0,0 +1,495 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#include <linux/slab.h>         /* for kmalloc/kfree */
+#include "via_types.h"
+
+#include "via_v4l.h"
+#include "via_memmgr.h"
+
+/* kernel module global variables */
+ViaOffScrnPtr MemLayOut; 
+unsigned long viabase0;      /* physical address of frame buffer */ 
+unsigned long viaBankSize;   /* Amount of total frame buffer */
+                             /* Set 8MB default,update by Xserver */
+Bool   XserverIsUp = FALSE ; /* If Xserver had run(register action) */
+unsigned long   S2D_Count  = 0;
+unsigned long   S3D_Count  = 0;
+unsigned long   Video_Count = 0;
+
+void PrintFBMem()
+{
+ OffMemRange *used,*unused;
+
+ unused = MemLayOut->unused;
+ used   = MemLayOut->used;
+
+ DBG_DD("\n");
+ DBG_DD("mem.c : Used   ID, StartAddr,  EndAddr,     size,     type,     this,     next\n");
+ while (used != NULL)
+ {
+    DBG_DD("mem.c : %08lx,  %08lx, %08lx, %08lx, %08x, %p, %p \n",
+              used->ID, used->StartAddr, used->EndAddr,used->size, used->type, used, used->next );
+    used = nextq(used);
+
+ }
+
+ DBG_DD("\n");
+ DBG_DD("mem.c : Unused ID, StartAddr,  EndAddr,     size,     type,     this,     next\n");
+ while (unused != NULL)
+ {
+    DBG_DD("mem.c :  %08lx,  %08lx, %08lx, %08lx, %08x, %p, %p \n",
+              unused->ID,unused->StartAddr, unused->EndAddr,unused->size, unused->type,
+              unused, unused->next  );
+    unused = nextq(unused);
+
+ }
+}
+
+void MergeL(OffMemRange * left , unsigned long size)
+{
+    left->EndAddr  = endq(left)  + size;
+    left->size     = sizeq(left) + size;
+}
+
+void MergeR(OffMemRange * right, unsigned long Addr,unsigned long size)
+{
+       right->StartAddr = Addr;
+       right->size      = sizeq(right) + size;
+}
+
+void MergeLR(OffMemRange *left, OffMemRange *right, unsigned long S_Addr,unsigned long size)
+{
+       left->size = sizeq(left) + sizeq(right) + size;
+       left->EndAddr  = endq(right);
+       left->next = nextq(right);
+}
+
+OffMemRange * lastq( OffMemRange *qSet )
+{
+       while ( nextq(qSet) != NULL )
+              qSet = nextq(qSet);
+
+       return qSet;
+}
+
+OffMemRange * prevq(OffMemRange *qSet, OffMemRange *curq )
+{
+
+       /* First Queue */
+       if ( qSet == curq )
+          return NULL;
+
+       while ( qSet != NULL ){
+             if ( nextq(qSet ) == curq )
+                return qSet;
+              qSet = nextq(qSet);
+       }
+
+       /* Warnning! Not Found. This should not happen */
+       return NULL;
+}
+
+OffMemRange * numNinq(OffMemRange *qSet, int N )
+{
+    int i=1;
+
+    for ( i=1; i< N; i++ ){
+        qSet = nextq(qSet);
+        if ( qSet == NULL )
+           return NULL;
+    }
+
+    return qSet;
+
+}
+
+void swapq(OffMemRange *qSet ,OffMemRange *L, OffMemRange *R )
+{
+       OffMemRange *tmp, *prevL, *prevR, *nextL, *nextR;
+
+       prevL = prevq(qSet,L);
+       prevR = prevq(qSet,R);
+       nextL = nextq(L);
+       nextR = nextq(R);
+
+       tmp = (OffMemRange *) kmalloc(sizeof(OffMemRange), GFP_KERNEL);
+       memcpy((void *)tmp,(void *) R ,sizeof(OffMemRange));
+       memcpy((void *)R  ,(void *) L ,sizeof(OffMemRange));
+       memcpy((void *)L  ,(void *)tmp,sizeof(OffMemRange));
+
+       L->next = nextR;
+       R->next = nextL;
+       if ( prevL != NULL )
+          prevL->next = R;
+       if ( prevR != NULL )
+          prevR->next = L;
+
+       deleteq(tmp);
+}
+
+
+OffMemRange * viaAllocSurface(int *size ,int alignment)
+{
+  int new_size ;
+  unsigned long old_addr;
+  OffMemRange *fq,*sq,*bq=NULL;
+  Bool isFind = FALSE ;
+
+  DBG_DD("mem.c : viaAllocSurface \n");
+  /* new_size = (*size + alignment - 1) & ~(alignment-1) ;
+     aligap = new_size - *size; */
+  new_size = *size;
+  
+  fq = MemLayOut->unused;
+  DBG_DD("mem.c : MemLayOut->unused: %p \n", MemLayOut->unused);
+  bq = fq;
+  while ( fq )
+   {
+         /* we must find the smaller-suitable memory for allocation */
+         if ( (endq(fq) - startq(fq) + 1 ) >= new_size ){
+             isFind = TRUE;
+             break;
+         }
+         bq = fq ;
+         fq = nextq(fq) ;
+   }
+
+  if (!isFind){
+       DBG_DD("mem.c : viaAllocSurface : No surface available\n");
+       PrintMemLayOut();
+       return NULL ;
+  }
+  else{
+        old_addr = startq(fq);
+        fq->StartAddr = startq(fq) + new_size ;
+        fq->size      = sizeq(fq) - new_size;
+
+        /* No memory left in this queue */
+        if (startq(fq) == endq(fq) + 1)
+           {
+            if ( bq == MemLayOut->unused ){
+               fq = nextq(fq);
+               deleteq(MemLayOut->unused);
+               MemLayOut->unused = fq ;
+            }
+            else{
+               bq->next = nextq(fq) ;
+               deleteq(fq);
+            }
+           }
+                
+        if (MemLayOut->used == NULL ){
+            MemLayOut->used = kmalloc( sizeof( OffMemRange), GFP_KERNEL );
+            MemLayOut->used->StartAddr = old_addr;
+            MemLayOut->used->EndAddr   = old_addr + new_size - 1;
+            MemLayOut->used->size      = new_size;
+            MemLayOut->used->next = NULL ;
+            DBG_DD("mem.c : viaAllocSurface : First Used \n");
+            PrintMemLayOut();
+            return (MemLayOut->used);
+           }
+
+        sq = MemLayOut->used ;
+
+        while (sq->next !=NULL  )
+             sq = nextq(sq);
+        sq->next = kmalloc( sizeof( OffMemRange), GFP_KERNEL );
+        sq = nextq(sq);
+        sq->next = NULL;
+        sq->StartAddr = old_addr;
+        sq->EndAddr   = old_addr + new_size - 1;
+        sq->size      = new_size;
+        DBG_DD("mem.c : viaAllocSurface : 2\n");
+        PrintMemLayOut();
+        return (sq);
+      }
+
+
+}
+
+Bool viaFreeSurface(unsigned long S_Addr,int size,unsigned char ctype)
+{
+  Bool isFind;
+  OffMemRange *this_free,*fq,*bq;
+  OffMemRange *rightq=NULL,*leftq=NULL;
+  Bool fm = FALSE, bm = FALSE, bRightest=FALSE;
+
+  DBG_DD("mem.c : viaFreeSurface : \n");
+  isFind = FALSE;
+  this_free = MemLayOut->used;
+  fq = MemLayOut->unused;
+  bq = NULL;
+
+  bq = this_free;
+  /* Find the queue to be deleted */
+  while (this_free != NULL) {
+        if (startq(this_free) == S_Addr && size ==sizeq(this_free) && typeq(this_free) == ctype){
+        /*if (this_free->StartAddr == S_Addr && size ==this_free->size && this_free->type == ctype){*/
+           isFind = TRUE;
+           break;
+        }
+        else
+        {
+           bq = this_free;
+           this_free = nextq(this_free);
+        }
+  }
+
+
+  if ( ! isFind ) {
+     PrintMemLayOut();
+     DBG_DD("mem.c : viaFreeSurface : Warnning! Surface to be freed not found. \n");
+     return isFind ;
+  }
+
+  /* bq is the first queue in the link list */
+  if (bq == this_free && isFind){
+          MemLayOut->used = nextq(bq) ;
+          deleteq(this_free);
+  /* bq -> this_free                        */
+  }else if(bq != this_free && isFind) {
+          bq->next = nextq(this_free);
+          deleteq(this_free);
+  }
+
+  DBG_DD("mem.c : viaFreeSurface : 2\n");
+  /* add the free memory block to unused queue,first we find the
+             "correct" queue to insert */
+
+ /* ====================================================================== */
+  bq = fq; /* where fq is MemLayOut->unused */
+
+
+  while( fq!=NULL )
+  {
+       /* fq -> this_free->nextq(fq) */
+       if ( (endq(fq)  == (S_Addr - 1)) && (nextq(fq)->StartAddr == (S_Addr + size)) ){
+          bm = TRUE ;
+          fm = TRUE ;
+          leftq = fq;
+          rightq = nextq(fq);
+          break;
+       }
+
+       /* fq -> this_free */
+       if (endq(fq)  == (S_Addr - 1) ){
+          bm = TRUE ;
+          leftq = fq;
+          break;
+       }
+
+       /* this_free -> fq */
+       if ( startq(fq) == (S_Addr + size) ) {
+          fm = TRUE ;
+          rightq = fq;
+          break;
+       }
+
+       bq=fq;
+       fq = nextq(fq);
+  }
+
+  DBG_DD("mem.c : viaFreeSurface : 3\n");
+
+
+  if ( fm && bm ){
+     PrintMemLayOut();
+     DBG_DD("mem.c : viaFreeSurface : MergeLR\n");
+     MergeLR(leftq, rightq, S_Addr, size);
+     PrintMemLayOut();
+     deleteq(rightq);
+  }
+  else if ( fm ){
+     DBG_DD("mem.c : viaFreeSurface : MergeR\n");
+     MergeR(rightq ,S_Addr, size);
+  }
+  else if ( bm ) {
+     DBG_DD("mem.c : viaFreeSurface : MergeL\n");
+     MergeL(leftq ,size);
+  }
+
+  /* Merged and return */
+  if ( fm || bm ){
+     PrintMemLayOut();
+     return isFind ;
+  }
+
+  /* sort it when insert unused queue */
+  fq = MemLayOut->unused;
+  bq = nextq(fq);
+
+  /* fq -> NULL */
+  if ( bq == NULL ){
+     OffMemRange * this_add;
+     this_add = (OffMemRange *)kmalloc(sizeof(OffMemRange), GFP_KERNEL);
+     this_add->StartAddr = S_Addr;
+     this_add->EndAddr   = S_Addr + size -1;
+     this_add->type      = ctype;
+     this_add->size      = size;
+
+
+     if ( startq(fq) > S_Addr ) {
+          MemLayOut->unused = this_add;
+          this_add->next    = fq;
+     }
+     else{
+          fq->next       = this_add;
+          this_add->next = NULL;
+     }
+     PrintMemLayOut();
+     return isFind;
+  }
+  /* fq -> bq */
+  else{
+      while (fq != NULL && bq != NULL){
+          if ( (startq(fq) < S_Addr) && (startq(bq) > S_Addr) )
+              break;
+          else {
+              fq = nextq(fq);
+              bq = nextq(bq);
+          }
+      }
+  }
+
+  if ( bq == NULL )
+     bRightest = TRUE;
+
+  if (MemLayOut->unused == NULL) {
+       MemLayOut->unused = kmalloc(sizeof(OffMemRange), GFP_KERNEL);
+       bq= MemLayOut->unused;
+       bq->next = NULL;
+  }else { /* fq -> bq and bq = NULL*/
+       if ( bRightest ) {
+         bq = kmalloc(sizeof(OffMemRange), GFP_KERNEL);
+         bq->next = NULL;
+         fq->next = bq;
+         bq->EndAddr = S_Addr+size-1;
+         bq->StartAddr = S_Addr;
+         bq->size = size;
+       }
+       else { /* fq -> bq */
+          OffMemRange * cq;
+          cq = kmalloc(sizeof(OffMemRange), GFP_KERNEL);
+          fq->next = cq;
+          cq->next = bq;
+          cq->EndAddr = S_Addr+size-1;
+          cq->StartAddr = S_Addr;
+          cq->size = size;
+       }
+  }
+
+
+  PrintMemLayOut();
+  return isFind ;
+ /* ====================================================================== */
+}
+
+
+int viaMgr_vid_ioctl(unsigned int cmd, char *arg)
+{
+     DBG_DD("mem.c: IOCTL : cmd = %08x \n",cmd);
+     switch (cmd){
+
+        case VIAMGR_ALLOC_2D:
+        case VIAMGR_ALLOC_3D:
+        case VIAMGR_ALLOC_VIDEO:
+        {
+                ViaMMReq MMReq; 
+                int req_size;
+                OffMemRange *offset;
+
+                memcpy(&MMReq ,(ViaMMReq *)arg,sizeof(ViaMMReq));
+
+                if (MMReq.checkID != VIA_MID) 
+                   {
+                         DBG_DD("mem.c: fail ID code.\n");
+                         return MEM_ERROR;
+                   }
+
+                DBG_DD("mem.c: Alloc type = %08x\n",MMReq.type);
+                req_size = MMReq.size;        
+                if( (offset=viaAllocSurface(&req_size,0 )) == NULL)
+                     return(MEM_ERROR);
+               
+
+                switch (MMReq.type) { 
+                     case VIDMGR_TYPE_2D : 
+                             offset->ID = S2D_Count;  
+                             S2D_Count ++;
+                             break;
+                     case VIDMGR_TYPE_3D :
+                             offset->ID = S3D_Count;
+                             S3D_Count ++;
+                             break;
+                     case VIDMGR_TYPE_VIDEO :
+                             offset->ID = Video_Count ; 
+                             Video_Count ++;
+                             break;
+                     default :
+                             DBG_DD("mem.c: Invalid buffer type! \n");
+                             return(MEM_ERROR);
+
+                }
+
+                offset->type = MMReq.type;
+                offset->priority = MMReq.priority;
+                offset->capability = MMReq.capability;
+                MMReq.offset = offset->StartAddr;
+                MMReq.ID     = offset->ID;
+                memcpy((ViaMMReq *)arg,&MMReq,sizeof(ViaMMReq));
+
+                return MEM_OK;
+        }
+
+        case VIAMGR_FREE_2D:
+        case VIAMGR_FREE_3D:
+        case VIAMGR_FREE_VIDEO:
+        {
+                ViaMMReq fm ;
+
+                memcpy(&fm ,(ViaMMReq *)arg,sizeof(ViaMMReq));
+                if (fm.checkID != VIA_MID)
+                   {
+                         DBG_DD("mem.c: fail ID code.\n");
+                         return(MEM_ERROR);
+                   }
+                DBG_DD("mem.c:  VIAMGR_FREE type = %08x ,size = %lx\n",
+                         fm.type,fm.size);
+                
+                if(!viaFreeSurface(fm.offset,(int)fm.size,fm.type))
+                   { 
+                       return(MEM_ERROR);
+                   } 
+                   return MEM_OK;
+        }
+
+        default :
+                  DBG_DD("mem.c:  Invalid ioctl cmd! \n");
+                  return(MEM_ERROR);
+      } /* end of switch */
+
+
+      return MEM_OK;
+}
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/via_memmgr.h linux-2.6.1-rc1-gentoo/drivers/media/video/via_memmgr.h
--- linux-2.6.0/drivers/media/video/via_memmgr.h	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/via_memmgr.h	2004-01-06 17:28:06.000000000 +0000
@@ -0,0 +1,133 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+ 
+/* kernel internal memory management */
+
+#ifndef __LINUX_MEM_H
+#define __LINUX_MEM_H
+
+#include <linux/videodev.h>
+
+
+struct offrange
+           {
+            unsigned long      StartAddr;
+            unsigned long      EndAddr;
+            unsigned long      size;
+            unsigned char      type;
+            unsigned long      ID;
+            unsigned char      priority;
+            unsigned char      capability;  
+            unsigned char      status;
+            struct offrange    * next ;
+           };
+
+typedef struct offrange OffMemRange ;
+
+typedef struct {
+          OffMemRange         *unused;
+          OffMemRange         *used;
+               } ViaOffScrnRec, *ViaOffScrnPtr;
+
+/* user-app use */
+
+typedef struct { 
+          unsigned long       size;
+          unsigned long       offset;
+          unsigned long       checkID;
+          unsigned long       ID;
+          unsigned char       type;
+          unsigned char       priority;
+          unsigned char       capability;
+          unsigned char       alignment;    
+          unsigned char       num;
+                             
+               } ViaMMReq;
+
+typedef struct { 
+          unsigned long       StartAddr;
+          unsigned long       size;
+          unsigned long       ID;
+          unsigned char       type;
+          unsigned char       priority;
+          unsigned char       capability;
+               } ViaMMInfo;
+
+/* Xserver Sync Protocol */
+typedef struct {
+         unsigned long BeginAddr;
+         unsigned long EndAddr;
+               } XserverSyncK;
+/*  
+typedef unsigned int Bool;
+#define FALSE 0 
+#define TRUE  1;
+*/
+#define VIA_MID  0x00004567 
+
+/* memory type */
+#define VIDMGR_TYPE_2D                    0x11
+#define VIDMGR_TYPE_3D                    0x12
+#define VIDMGR_TYPE_VIDEO                 0x13
+  
+/* memory priority */
+#define VIDMGR_PRI_LOW                    0x21
+#define VIDMGR_PRI_NORM                   0x22
+#define VIDMGR_PRI_HIGHT                  0x23
+
+/* memory capability  */
+#define VIDMGR_CAP_MOVABLE                0x31
+#define VIDMGR_CAP_IMMOVABLE              0x32
+
+/* memory return value  */
+#define MEM_OK       0
+#define MEM_ERROR   -1
+
+
+/* memory macro functions */
+#define nextq(x)    x->next
+#define sizeq(x)    x->size
+#define endq(x)     x->EndAddr
+#define startq(x)   x->StartAddr
+#define deleteq(x)  kfree(x)
+#define typeq(x)    x->type
+
+#define VIAMGR_INFO_2D          0x00004001
+#define VIAMGR_INFO_3D          0x00004002
+#define VIAMGR_INFO_VIDEO       0x00004003
+#define VIAMGR_ALLOC_2D         0x00004004
+#define VIAMGR_ALLOC_3D         0x00004005
+#define VIAMGR_ALLOC_VIDEO      0x00004006
+#define VIAMGR_FREE_2D          0x00004007
+#define VIAMGR_FREE_3D          0x00004008
+#define VIAMGR_FREE_VIDEO       0x00004009
+
+
+void PrintFBMem(void);
+OffMemRange * viaAllocSurface(int *size ,int alignment);
+Bool viaFreeSurface(unsigned long S_Addr,int size,unsigned char ctype);
+int  viaMgr_vid_ioctl(unsigned int cmd, char *arg);
+
+
+#endif /* end of LINUX_MEM_H */
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/via_mm.h linux-2.6.1-rc1-gentoo/drivers/media/video/via_mm.h
--- linux-2.6.0/drivers/media/video/via_mm.h	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/via_mm.h	2004-01-06 17:28:06.000000000 +0000
@@ -0,0 +1,45 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+#ifndef _via_drm_mm_h_
+#define _via_drm_mm_h_
+
+typedef struct {
+    unsigned int context;
+    unsigned int size;
+    unsigned long offset;
+    unsigned int free;
+} drm_via_mm_t;
+
+typedef struct {
+    unsigned int size;
+    unsigned long handle;
+    void *virtual;
+} drm_via_dma_t;
+
+int via_fb_alloc(drm_via_mem_t *mem);
+int via_fb_free(drm_via_mem_t *mem);
+int via_agp_alloc(drm_via_mem_t *mem);
+int via_agp_free(drm_via_mem_t *mem);
+
+#endif
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/via_mmap.c linux-2.6.1-rc1-gentoo/drivers/media/video/via_mmap.c
--- linux-2.6.0/drivers/media/video/via_mmap.c	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/via_mmap.c	2004-01-06 17:28:06.000000000 +0000
@@ -0,0 +1,84 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#include <linux/autoconf.h>
+#if defined(MODULE) && defined(CONFIG_MODVERSIONS)
+#define MODVERSIONS
+#include <linux/modversions.h>
+#endif
+
+#include <linux/types.h>
+#include <linux/config.h>
+#include <linux/version.h>
+#include <linux/module.h>
+#include <linux/kernel.h>
+#include <linux/sched.h>
+#include <linux/init.h>
+#include <linux/pci.h>
+#include <linux/interrupt.h>
+#include <linux/wrapper.h>
+
+#include "via_mmap.h"
+
+void * rvmalloc(signed long size)
+{
+	void * mem;
+	unsigned long adr, page;
+
+	mem=vmalloc_32(size);
+	if (NULL == mem)
+		printk(KERN_INFO "km: vmalloc_32(%ld) failed\n",size);
+	if (mem) 
+	{
+		memset(mem, 0, size); /* Clear the ram out, no junk to the user */
+	        adr=(unsigned long) mem;
+		while (size > 0) 
+                {
+	                page = kvirt_to_pa(adr);
+			mem_map_reserve(virt_to_page(__va(page)));
+			adr+=PAGE_SIZE;
+			size-=PAGE_SIZE;
+		}
+	}
+	return mem;
+}
+
+void rvfree(void * mem, signed long size)
+{
+        unsigned long adr, page;
+        
+	if (mem) 
+	{
+	        adr=(unsigned long) mem;
+		while (size > 0) 
+                {
+	                page = kvirt_to_pa(adr);
+			mem_map_unreserve(virt_to_page(__va(page)));
+			adr+=PAGE_SIZE;
+			size-=PAGE_SIZE;
+		}
+		vfree(mem);
+	}
+}
+
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/via_mmap.h linux-2.6.1-rc1-gentoo/drivers/media/video/via_mmap.h
--- linux-2.6.0/drivers/media/video/via_mmap.h	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/via_mmap.h	2004-01-06 17:28:06.000000000 +0000
@@ -0,0 +1,120 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#ifndef __KM_MEMORY_H__
+#define __KM_MEMORY_H__
+
+/*******************************/
+/* Memory management functions */
+/*******************************/
+
+#define MDEBUG(x)	do { } while(0)		/* Debug memory management */
+#ifndef VMALLOC_VMADDR
+#define VMALLOC_VMADDR(x) ((unsigned long)(x))
+#endif
+
+/* [DaveM] I've recoded most of this so that:
+ * 1) It's easier to tell what is happening
+ * 2) It's more portable, especially for translating things
+ *    out of vmalloc mapped areas in the kernel.
+ * 3) Less unnecessary translations happen.
+ *
+ * The code used to assume that the kernel vmalloc mappings
+ * existed in the page tables of every process, this is simply
+ * not guarenteed.  We now use pgd_offset_k which is the
+ * defined way to get at the kernel page tables.
+ */
+
+/* Given PGD from the address space's page table, return the kernel
+ * virtual mapping of the physical memory mapped at ADR.
+ */
+static inline unsigned long uvirt_to_kva(pgd_t *pgd, unsigned long adr)
+{
+    unsigned long ret = 0UL;
+	pmd_t *pmd;
+	pte_t *ptep, pte;
+  
+	if (!pgd_none(*pgd))
+	{
+		pmd = pmd_offset(pgd, adr);
+        if (!pmd_none(*pmd))
+        {
+	        ptep = pte_offset_map(pmd, adr);
+            pte = *ptep;
+            if(pte_present(pte))
+            {
+				ret  = (unsigned long) page_address(pte_page(pte));
+				ret |= (adr & (PAGE_SIZE - 1));
+			}
+        }
+    }
+    MDEBUG(printk("uv2kva(%lx-->%lx)", adr, ret));
+
+	return ret;
+}
+
+static inline unsigned long uvirt_to_bus(unsigned long adr) 
+{
+    unsigned long kva, ret;
+
+    kva = uvirt_to_kva(pgd_offset(current->mm, adr), adr);
+	ret = virt_to_bus((void *)kva);
+    MDEBUG(printk("uv2b(%lx-->%lx)", adr, ret));
+
+    return ret;
+}
+
+static inline unsigned long kvirt_to_bus(unsigned long adr) 
+{
+    unsigned long va, kva, ret;
+
+    va = VMALLOC_VMADDR(adr);
+    kva = uvirt_to_kva(pgd_offset_k(va), va);
+	ret = virt_to_bus((void *)kva);
+    MDEBUG(printk("kv2b(%lx-->%lx)", adr, ret));
+
+    return ret;
+}
+
+/* Here we want the physical address of the memory.
+ * This is used when initializing the contents of the
+ * area and marking the pages as reserved.
+ */
+static inline unsigned long kvirt_to_pa(unsigned long adr) 
+{
+    unsigned long va, kva, ret;
+
+    va = VMALLOC_VMADDR(adr);
+    kva = uvirt_to_kva(pgd_offset_k(va), va);
+	ret = __pa(kva);
+    MDEBUG(printk("kv2pa(%lx-->%lx)", adr, ret));
+
+    return ret;
+}
+
+void * rvmalloc(signed long size);
+void rvfree(void * mem, signed long size);
+
+
+#endif
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/via_privIoctl.h linux-2.6.1-rc1-gentoo/drivers/media/video/via_privIoctl.h
--- linux-2.6.0/drivers/media/video/via_privIoctl.h	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/via_privIoctl.h	2004-01-06 17:28:06.000000000 +0000
@@ -0,0 +1,102 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#ifndef __via_privIoctl_h
+#define __via_privIoctl_h
+
+/* #include <linux/videodev.h> */
+#include <asm/ioctl.h>
+#include "capture.h"
+
+#define BASE_VIDIOCPRIVATE	192		/* 192-255 are private */
+
+/*Added for SAMM*/
+typedef struct {
+    unsigned long dwWidth;          /* On screen Width                  */
+    unsigned long dwHeight;         /* On screen Height                 */
+    unsigned long dwSaveWidth;      /* On screen Width for Panning      */
+    unsigned long dwSaveHeight;     /* On screen Height for Panning     */
+    unsigned long dwBPP;            /* Bits Per Pixel                   */
+    unsigned long dwPitch;          /* On screen pitch= width x BPP     */
+    unsigned long dwRefreshRate;    /* Refresh rate of the mode         */
+    unsigned long TotalVRAM;        /* Total Video RAM in unit of byte  */
+    unsigned long VideoHeapBase;    /* Physical Start of video heap     */
+    unsigned long VideoHeapEnd;     /* Physical End of video heap       */
+    unsigned long dwDVIOn;    	    /* Is it DVI simultaneous mode ?    */
+    unsigned long dwLCDOn;    	    /* Is it LCD simultaneous mode ?    */
+    unsigned long dwExpand;    	    /* Is DVI in expand mode ?          */
+    unsigned long dwPanning;    	/* Is DVI in Pannig mode ?          */
+    unsigned long dwPanelWidth;     /* Panel physical Width             */
+    unsigned long dwPanelHeight;    /* Panel physical Height            */
+    unsigned long dwActiveDevice;   /* Active Device; ex. CRT or LCD    */       
+}SCREENINFO, * LPSCREENINFO;
+
+typedef struct {
+    unsigned long HQVFilter_ManualSelect;    /* HQV Filter_Manual Select         */
+    int MpegHQV_VFilterMode;                 /* MPEG HQV vertical filter mode    */
+    int MpegHQV_HFilterMode;                 /* MPEG HQV horizontal filter mode  */
+    int CapHQV_VFilterMode;                  /* Capture HQV vertical filter mode */
+    int CapHQV_HFilterMode;                  /* Capture HQV horizontal filter mode */
+    unsigned long SetMpeg_FBNumber;          /* Set Mpeg decode frame buffer number */
+    unsigned long Cap1_UseIRQ;               /* Capture 1 use IRQ select, for S/W flip or H/W auto flip */
+    unsigned long Cap0_SwitchToV3;           /* Capture 0 use V3 engine, only for SAMSUNG project */
+    unsigned long HQV_ManualSwitch;      /* HQV engine manual switch select      */
+    Bool  ColorSpaceChanged;                 /* The setting value of color space been changed by user    */
+    unsigned long ColorSpaceValue1;          /* User set color value from utility , after driver convert */
+    unsigned long ColorSpaceValue2;          /* User set color value from utility , after driver convert */
+    Bool  DRMEnabled;               /* kernel module DRM flag           */
+    Bool  Screen1IsLeft;            /* True: Screen1 LeftOf Screen0 ; False: Screen1 RightOf Screen0 */
+    Bool  Screen1IsAbove;           /* True: Screen1 Above Screen0 ; False: Screen1 Below Screen0 */
+    Bool  SAMM;                     /* True: XServer in SAMM mode  */
+    int   RevisionID;               /* The chip revision ID */
+    unsigned long dwDeviceID;       /* The chip device ID */
+    unsigned long dwActiveDevice;   /* ActiveDevice; ex. SAMM: CRT+LCD  */
+    SCREENINFO  Screen[2];          /* Information for Primary & Secondary Screens*/      
+    unsigned long NoMPEGAddOneLineOnBottom;    /* Disable HQV bob-deinterlacing, 0x3D0[16] */
+    Bool  ReDrawColorkey;           /* ReDrawColorKey at viaPutImageG everytime*/
+    unsigned long Reserved[9];     /* For future use */
+}VIAGRAPHICINFO, * LPVIAGRAPHICINFO;
+
+/* via private ioctls */
+
+#define VIAMGR_INFO_XSERVERON   _IOW ('v', BASE_VIDIOCPRIVATE+1, VIAGRAPHICINFO)
+#define VIAMGR_INFO_XSERVEROFF  _IO  ('v', BASE_VIDIOCPRIVATE+2 )
+#define VIA_VID_GET_2D_INFO     _IOR ('v', BASE_VIDIOCPRIVATE+3, VIAGRAPHICINFO)
+#define VIA_VID_SET_2D_INFO     _IOW ('v', BASE_VIDIOCPRIVATE+4, VIAGRAPHICINFO)
+#define VIA_VID_GET_VIDCTL		_IOR ('v', BASE_VIDIOCPRIVATE+5, VIAVIDCTRL)
+#define VIA_VID_SET_VIDCTL		_IOW ('v', BASE_VIDIOCPRIVATE+6, VIAVIDCTRL)
+#define VIA_VID_CREATESURFACE	_IOW ('v', BASE_VIDIOCPRIVATE+7, DDSURFACEDESC)
+#define VIA_VID_DESTROYSURFACE	_IOW ('v', BASE_VIDIOCPRIVATE+8, DDSURFACEDESC)
+#define VIA_VID_LOCKSURFACE		_IOWR ('v', BASE_VIDIOCPRIVATE+9, DDLOCK)
+#define VIA_VID_UPDATEOVERLAY	_IOW ('v', BASE_VIDIOCPRIVATE+10, DDUPDATEOVERLAY)
+#define VIA_VID_SETALPHAWIN		_IOW ('v', BASE_VIDIOCPRIVATE+11, ALPHACTRL)
+#define VIA_VID_UPDATEALPHA		_IOW ('v', BASE_VIDIOCPRIVATE+12, RECTL)
+#define VIA_VID_ADJUSTFRAME		_IOW ('v', BASE_VIDIOCPRIVATE+13, ADJUSTFRAME)
+#define VIA_VID_FLIP    		_IOW ('v', BASE_VIDIOCPRIVATE+14, unsigned long)
+
+#define VIA_VID_GET_CAP_INFO     _IOR ('v', BASE_VIDIOCPRIVATE+18, VIACAPINFO)
+#define VIA_VID_SET_CAP_INFO     _IOW ('v', BASE_VIDIOCPRIVATE+19, VIACAPINFO)
+
+
+#endif  /* end of __via_privIoctl_h */
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/via_tuner.c linux-2.6.1-rc1-gentoo/drivers/media/video/via_tuner.c
--- linux-2.6.0/drivers/media/video/via_tuner.c	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/via_tuner.c	2004-01-06 23:33:49.000000000 +0000
@@ -0,0 +1,148 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+/*------------------------------------------------
+   Tuner Module
+  ------------------------------------------------*/
+#include "via_types.h"
+
+#include "i2c.h"
+#include "via_tuner.h"
+
+extern int I2CReg3C4Index   ;
+
+__inline void Macro_SetI2CIndex(void)
+{
+   I2CReg3C4Index   = I2CIndexTUNER;
+}
+
+__inline void Macro_RestoreI2CIndex(void)
+{
+   I2CReg3C4Index   = I2CIndexVDEC;
+}
+
+void  WriteTuner(int i1, int i2, int i3 )
+{
+
+    int temp1;
+    int ack;
+  //   DBG_DD("Tuner.c: WriteTuner()\n");
+    Macro_SetI2CIndex();
+
+    i2c_start();
+    ack=i2c_sendbyte(i1,1 );
+    temp1 = i2 >> 8;
+    ack=i2c_sendbyte(temp1,1 );
+    ack=i2c_sendbyte(i2,1 );
+    temp1 = i3 >> 8;
+    ack=i2c_sendbyte(temp1,1 );
+    ack=i2c_sendbyte(i3,1 );
+    i2c_stop();
+
+    Macro_RestoreI2CIndex();
+}
+
+/*  ReadTuner
+*/
+
+int  ReadTuner(int SlaveAdd )
+{
+     int StatusData=0, ack;
+
+//   DBG_DD("Tuner.c: ReadTuner()\n");
+
+     Macro_SetI2CIndex();
+
+     i2c_start();
+     ack=i2c_sendbyte(SlaveAdd,1 );
+     StatusData=i2c_readbyte(1);
+     i2c_stop();
+
+     Macro_RestoreI2CIndex();
+
+     return StatusData;
+
+}
+
+
+
+Bool   TUNER_FindModule(via_device *via)
+{
+    int ack = 1;
+
+    //DBG_DD("Tuner.c: TUNER_DetectFI1236()\n");
+    Macro_SetI2CIndex();
+
+    switch (via->video_dev->minor)
+    {
+    case COMMAND_FOR_TV0 :  /* Find tuner type of capture 0 */
+        via->CapInfo.Tuner = FI1236MK2;
+        via->CapInfo.Tuner_Slave_Write = FI1236_0;
+
+        I2C_enable();
+
+        i2c_start();
+        ack=i2c_sendbyte(via->CapInfo.Tuner_Slave_Write,1 );
+        i2c_stop();
+        ack = ack & 0x01;
+        if ( ! ack  )
+        {
+            DBG_DD("via_v4l : Tuner Philip FI1236 for capture 0 found! \n");
+            return TRUE;
+        }
+        break;
+
+    case COMMAND_FOR_TV1 :  /* Find tuner type of capture 1 */
+        via->CapInfo.Tuner = FI1236MK2;
+        via->CapInfo.Tuner_Slave_Write = FI1236_1;
+
+        I2C_enable();
+
+        i2c_start();
+        ack=i2c_sendbyte(via->CapInfo.Tuner_Slave_Write,1 );
+        i2c_stop();
+        ack = ack & 0x01;
+        if ( ! ack  )
+        {
+            DBG_DD("via_v4l : Tuner Philip FI1236 for capture 1 found! \n");
+            return TRUE;
+        }
+        break;
+    }
+
+    DBG_DD("via_v4l : Tuner for capture not found! \n");
+    return FALSE;
+
+}
+
+
+
+void TUNER_ProgChannel(via_device *via, int nDivider, int nControl )
+{
+
+   DBG_DD("Tuner.c :Slave=0x%08x, Divider = 0x%08x, Control = 0x%08x\n",
+              via->CapInfo.Tuner_Slave_Write,  nDivider, nControl );
+   WriteTuner(via->CapInfo.Tuner_Slave_Write,  nDivider, nControl );
+
+}
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/via_tuner.h linux-2.6.1-rc1-gentoo/drivers/media/video/via_tuner.h
--- linux-2.6.0/drivers/media/video/via_tuner.h	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/via_tuner.h	2004-01-06 17:28:06.000000000 +0000
@@ -0,0 +1,45 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#ifndef __TUNER_H
+#define __TUNER_H
+
+#ifdef __KERNEL__
+#include "via_v4l.h"
+#endif
+
+#define       FI1236MK2     0x01
+
+
+#define   FI1236     0x0c6  /* address of Philips FI1236 */
+#define   FI1236_0   0x0c6
+#define   FI1236_1   0x0c0
+
+
+#ifdef __KERNEL__
+Bool  TUNER_FindModule(via_device *via);
+void  TUNER_ProgChannel(via_device *via, int nDivider, int nControl );
+#endif
+
+#endif   /* __TUNER_H */
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/via_types.h linux-2.6.1-rc1-gentoo/drivers/media/video/via_types.h
--- linux-2.6.0/drivers/media/video/via_types.h	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/via_types.h	2004-01-06 17:28:06.000000000 +0000
@@ -0,0 +1,45 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+/*
+ *	Define types used in the codes
+ *	in terms of X11 base types.
+ */
+
+#ifndef VIA_TYPES_H
+#define VIA_TYPES_H
+
+#ifndef Bool
+typedef int Bool;
+#endif
+
+#ifndef TRUE
+#define TRUE 1
+#endif
+
+#ifndef FALSE
+#define FALSE 0
+#endif
+
+#endif
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/via_v4l.c linux-2.6.1-rc1-gentoo/drivers/media/video/via_v4l.c
--- linux-2.6.0/drivers/media/video/via_v4l.c	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/via_v4l.c	2004-01-06 23:28:42.000000000 +0000
@@ -0,0 +1,2359 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+           
+// I N C L U D E S ----------------------------------------------------------
+#define __VIA_V4L_C__
+//#include <stdlib.h>             /* For lrand48() & srand48() */
+#include <linux/time.h>         /* for do_gettimeofday */
+#include <linux/version.h>
+#include <linux/module.h>       /* for module-version */
+#include <linux/delay.h>        /* for delay-stuff */
+#include <linux/slab.h>         /* for kmalloc/kfree */
+#include <linux/mm.h>           /* remap_page_range */
+#include <asm/pgtable.h>
+#include <asm/page.h>
+#include <linux/pci.h>          /* for pci-config-stuff, vendor ids etc. */
+#include <linux/init.h>         /* for "__init" */
+#include <linux/interrupt.h>    /* for IMMEDIATE_BH */
+#include <linux/vmalloc.h>
+#include <linux/kernel.h>
+#include <linux/major.h>
+#include <linux/poll.h>
+#include <linux/signal.h>
+#include <asm/io.h>
+#include <linux/kmod.h>
+#include <linux/device.h>
+//#include <linux/i2c.h>
+//#include <linux/i2c-id.h>
+
+#include "via_types.h"
+#include "ddmpeg.h"
+#include "capture.h"
+#include "via.h"       /* H/W register definition */
+#include "compose.h"
+#include "via_privIoctl.h" /* for VIAGRAPHICINFO & custom ioctl command */
+#include "HWDiff.h"
+
+#include "via_v4l.h"            /* V4L header file */
+#include "via_mmap.h"           /* mmap related funcs header */
+#include "via_memmgr.h"         /* memory management */
+#include "i2c.h"                /* i2c header */
+#include "vdec.h"               /* video decoder header */
+#include "via_tuner.h"               /* tuner header */
+
+
+// D E F I N E --------------------------------------------------------------
+/* App "xawtv" attribute from 0 to 65535 */
+/* But SAA7113H needs 0 to 255           */
+#define Attr_Mapping(x)   x = ( x >> 8 )
+#define LOW_BAND 0x0CB0
+#define MID_BAND 0x1f10
+#define USE_CAPTURE1
+
+
+// E X T E R N   G L O B A L S--------------------------------------------------------------
+extern CAPDEVICE   CAPDevice[2];
+extern ALPHADEVICE ALPDevice;
+extern SWDEVICE   SWDevice;
+extern SUBDEVICE   SUBDevice;
+extern MPGDEVICE   MPGDevice;
+
+extern Bool AUDIO_MUTE;
+
+/* memory management global variables */ 
+extern ViaOffScrnPtr MemLayOut; 
+extern unsigned long viabase0;      /* physical address of frame buffer */ 
+extern unsigned long viaBankSize;   /* Amount of total frame buffer */
+                             /* Set 8MB default,update by Xserver */
+extern Bool   XserverIsUp; /* If Xserver had run(register action) */
+
+extern unsigned long   gdwVideoFlagMPEG;
+extern unsigned long   gdwVideoFlagTV0;
+extern unsigned long   gdwVideoFlagTV1;
+
+/* For panning mode use */
+extern int panning_old_x[2];
+extern int panning_old_y[2];
+extern int panning_x[2];
+extern int panning_y[2];
+
+// E X T E R N   F U N C T I O N S ------------------------------------------
+extern unsigned long UpdateOverlayAlpha(RECTL rDest);
+extern void  UpdateVPort(via_device *via);
+extern unsigned long UpdateOverlayTV(LPDDUPDATEOVERLAY lpUpdate,via_device *via);
+extern __inline void Macro_SetI2CIndex(void);
+extern __inline void Macro_RestoreI2CIndex(void);
+extern void AUDIO_MUTE_ON(void);
+extern void AUDIO_MUTE_OFF(void);
+
+extern void vfInitHWDiff(via_device *via);  
+
+// G L O B A L S ------------------------------------------------------------
+/* module parameters */
+int km_debug = 0;
+
+MODULE_PARM(km_debug,"i");
+MODULE_PARM_DESC(km_debug, "debug level (default: 0)");
+
+MODULE_DESCRIPTION("via_v4l_drv - v4l driver module for VIA CLE266");
+MODULE_AUTHOR("Kevin Huang");
+#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,10)
+MODULE_LICENSE("GPL");
+#endif
+
+/* global variables */
+int via_v4l_num = 0;
+via_device via_v4l_devices[MAX_VIA_BOARDS];
+static unsigned int gbuffers = 2;
+//static unsigned int gbufsize = 720*576*2;
+
+volatile unsigned char  * lpVidMEMIO;    // mem-map IO address
+unsigned char  * lpPrimarySurface;    // OnScreen FB linear address
+
+/* XServer related global variables */
+VIAGRAPHICINFO gVIAGraphicInfo;
+LPVIAVIDCTRL   lpVideoControl;
+
+//To solve the bandwidth issue
+unsigned char Save_3C4_16 =0;
+unsigned char Save_3C4_17 =0;
+unsigned char Save_3C4_18 =0;
+
+Bool Address0_Switch = TRUE;       // 1: buffer 0 switch to 2
+                                   // 0: buffer 2 switch back to 0
+Bool Address1_Switch = TRUE;       // 1: buffer 1 switch to 3
+                                   // 0: buffer 3 switch back to 1
+Bool V3Address0_Switch = TRUE;     // 1: buffer 0 switch to 2
+                                   // 0: buffer 2 switch back to 0
+Bool V3Address1_Switch = TRUE;     // 1: buffer 1 switch to 3
+                                   // 0: buffer 3 switch back to 1                                 
+
+unsigned long gdwOverlaySupport=1;
+#define DDR100SUPPORTMODECOUNT 24
+#define DDR133UNSUPPORTMODECOUNT 19
+MODEINFO SupportDDR100[DDR100SUPPORTMODECOUNT]=
+         {{640,480,8,60}, {640,480,8,75}, {640,480,8,85}, {640,480,8,100}, {640,480,8,120},
+          {640,480,16,60}, {640,480,16,75}, {640,480,16,85}, {640,480,16,100}, {640,480,16,120},
+          {640,480,32,60}, {640,480,32,75}, {640,480,32,85}, {640,480,16,100}, {640,480,32,120},
+          {800,600,8,60}, {800,600,8,75}, {800,600,8,85}, {800,600,8,100}, {800,600,16,60},
+          {800,600,16,75}, {800,600,16,85}, {800,600,32,60}, {1024,768,8,60}};
+
+MODEINFO UnSupportDDR133[DDR133UNSUPPORTMODECOUNT]=
+         {{1152,864,32,75}, {1280,768,32,75}, {1280,768,32,85}, {1280,960,32,60}, {1280,960,32,75},
+          {1280,960,32,85}, {1280,1024,16,85}, {1280,1024,32,60}, {1280,1024,32,75}, {1280,1024,32,85},
+          {1400,1050,16,85}, {1400,1050,32,60}, {1400,1050,32,75}, {1400,1050,32,85}, {1600,1200,8,75},
+          {1600,1200,8,85}, {1600,1200,16,75}, {1600,1200,16,85}, {1600,1200,32,60}};
+
+/* ----------------------------------------------------------------------- */
+/* sysfs                                                                   */
+
+static ssize_t show_card(struct class_device *cd, char *buf)
+{
+        struct video_device *vfd = to_video_device(cd);
+	via_device *via= dev_get_drvdata(vfd->dev);
+	return sprintf(buf, "%d\n", via ? 0: -1);
+}
+static CLASS_DEVICE_ATTR(card, S_IRUGO, show_card, NULL);
+			
+// F U N C T I O N S----------------------------------------------------------
+
+Bool DecideOverlaySupport(void)
+{
+    unsigned long iCount;   
+    int ScrnIndex = 0;//Need to check!!
+
+    outb(0x3d,0x3d4);
+    switch ((inb(0x3d5) & 0x70) >> 4) 
+    {
+        case 0:
+        case SDR100:
+            break;
+
+        case SDR133:
+            break;
+
+        case DDR100:
+            for (iCount=0; iCount < DDR100SUPPORTMODECOUNT; iCount++)
+            {
+                if ( (gVIAGraphicInfo.Screen[ScrnIndex].dwWidth == SupportDDR100[iCount].dwWidth) && 
+                     (gVIAGraphicInfo.Screen[ScrnIndex].dwHeight == SupportDDR100[iCount].dwHeight) &&
+                     (gVIAGraphicInfo.Screen[ScrnIndex].dwBPP == SupportDDR100[iCount].dwBPP) && 
+                     (gVIAGraphicInfo.Screen[ScrnIndex].dwRefreshRate == SupportDDR100[iCount].dwRefreshRate) )
+                {
+                    return TRUE;
+                    break;
+                }                         
+            }
+
+            return FALSE;
+            break;
+
+        case DDR133:
+            for (iCount=0; iCount < DDR133UNSUPPORTMODECOUNT; iCount++)
+            {
+                if ( (gVIAGraphicInfo.Screen[ScrnIndex].dwWidth == UnSupportDDR133[iCount].dwWidth) && 
+                     (gVIAGraphicInfo.Screen[ScrnIndex].dwHeight == UnSupportDDR133[iCount].dwHeight) &&
+                     (gVIAGraphicInfo.Screen[ScrnIndex].dwBPP == UnSupportDDR133[iCount].dwBPP) && 
+                     (gVIAGraphicInfo.Screen[ScrnIndex].dwRefreshRate == UnSupportDDR133[iCount].dwRefreshRate) )
+                {
+                    return FALSE;
+                    break;
+                }                         
+            }
+
+            return TRUE;
+            break;
+    }
+
+    return FALSE;
+}
+
+
+/*
+ *  i2c helper functions
+ */
+
+/* Detect Video-decoder & Init registers */
+void InitializeVDEC(via_device *via)
+{
+    int tempI2Cdata, Reg3C4H;
+
+    // save 3c4H
+    Reg3C4H = inb(0x3c4);
+
+    outb(0x12,0x3c4);
+    tempI2Cdata = inb(0x3c5);
+
+    if (via->CapInfo.NoAutoDetect)
+    {
+        DBG_DD("VideoDecoder %lx\n", via->CapInfo.VideoDecoder);
+        VDEC_Initialize(via);
+    }
+    else
+    {
+        if (VDEC_FindModule(via) == TRUE)
+        {
+            VDEC_Initialize(via);
+        }
+    }
+
+    // restore 3c4H
+    outb(Reg3C4H,0x3c4);
+
+}
+
+/* Detect TUNER */
+void InitializeTUNER(via_device *via)
+{
+    int tempI2Cdata, Reg3C4H;
+
+    // save 3c4H
+    Reg3C4H = inb(0x3c4);
+
+    outb(0x12,0x3c4);
+    tempI2Cdata = inb(0x3c5);
+
+    if (!(via->CapInfo.NoAutoDetect))
+    {
+        TUNER_FindModule(via);
+    }
+
+    // restore 3c4H
+    outb(Reg3C4H,0x3c4);
+
+}
+
+/* Detect audio-controller & Init registers */
+void  InitializeAudio(void)
+{
+    LPVIASETPORTATTR lpParam =  (LPVIASETPORTATTR)kmalloc(sizeof(VIASETPORTATTR), GFP_KERNEL);
+
+    lpParam->attribute = ATTR_INIT_AUDIO;
+    VIADriverProc(AUDIOCONTROL,lpParam );
+
+    if ( lpParam )
+       kfree(lpParam);
+}
+
+
+/*
+ *  CreateTVSurface() : allocate offscreen memory block
+ */
+static int CreateTVSurface(via_device *via)
+{
+    LPDDSURFACEDESC lpSurfaceDesc = (LPDDSURFACEDESC)kmalloc(sizeof(DDSURFACEDESC), GFP_KERNEL);
+
+    //DBG_DD("via_v4l:CreateTVSurface() via 0x%p\n", via);
+    switch (via->video_dev->minor)
+    {
+    case COMMAND_FOR_TV0 :
+        if (!(lpVideoControl->VideoStatus & TV0SURFACE_CREATED))
+            lpSurfaceDesc->dwFourCC = FOURCC_TV0;
+        else
+            return TRUE;
+        break;
+        
+    case COMMAND_FOR_TV1 :
+        if (!(lpVideoControl->VideoStatus & TV1SURFACE_CREATED))
+            lpSurfaceDesc->dwFourCC = FOURCC_TV1;
+        else
+            return TRUE;
+        break;
+    }
+
+    /* To be continued. width, height for NTSC / PAL /SECAM */
+    lpSurfaceDesc->dwWidth  = 720;
+//    lpSurfaceDesc->dwHeight = 480;
+    lpSurfaceDesc->dwHeight = 576;
+    lpSurfaceDesc->dwBackBufferCount = 2;
+    lpSurfaceDesc->dwColorSpaceLowValue = via->color_key;
+
+    if ( VIADriverProc(CREATESURFACE,lpSurfaceDesc) != PI_OK )
+        DBG_DD("via_v4l:CreateSurface fail\n");
+    
+    switch (via->video_dev->minor)
+    {
+    case COMMAND_FOR_TV0 :
+        lpVideoControl->VideoStatus |= TV0SURFACE_CREATED;
+        DBG_DD(" via_v4l : Create TV0 Surface, VideoStatus=0x%08lx : \n",lpVideoControl->VideoStatus);
+        break;
+    
+    case COMMAND_FOR_TV1 :
+        lpVideoControl->VideoStatus |= TV1SURFACE_CREATED;
+        DBG_DD(" via_v4l : Create TV1 Surface, VideoStatus=0x%08lx : \n",lpVideoControl->VideoStatus);
+        break;
+    }
+    
+    kfree(lpSurfaceDesc);
+    return TRUE;
+}
+
+
+/*
+ *  DestroyTVSurface() : free offscreen memory block
+ */
+void DestroyTVSurface(via_device *via)
+{
+    LPDDSURFACEDESC lpSurfaceDesc = (LPDDSURFACEDESC)kmalloc(sizeof(DDSURFACEDESC), GFP_KERNEL);
+
+    /*if ( via->video_dev->minor == 0 )*/
+    if ( via->video_dev->minor == 1 )
+    {
+        if (lpVideoControl->VideoStatus & TV1SURFACE_CREATED) 
+        {
+            lpSurfaceDesc->dwFourCC = FOURCC_TV1;
+            DBG_DD(" via_v4l : Destroy TV1 Surface\n");
+        }
+        else
+        {
+            DBG_DD(" via_v4l : No TV1 Surface Destroyed, PortID = %d, VideoStatus =0x%08lx : \n",
+                  lpVideoControl->PORTID, lpVideoControl->VideoStatus);
+            return;
+        }
+    }
+    else
+    {
+        if (lpVideoControl->VideoStatus & TV0SURFACE_CREATED)
+        {
+            lpSurfaceDesc->dwFourCC = FOURCC_TV0;
+            DBG_DD(" via_v4l : Destroy TV0 Surface\n");
+        }
+        else
+        {
+            DBG_DD(" via_v4l : No TV0 Surface Destroyed, PortID = %d, VideoStatus =0x%08lx : \n",
+                  lpVideoControl->PORTID, lpVideoControl->VideoStatus);
+            return;
+        }
+    }
+
+
+    VIADriverProc(DESTROYSURFACE,lpSurfaceDesc);
+
+        //down(&via->lock);
+    /*if ( via->video_dev->minor == 0 )*/
+    if ( via->video_dev->minor == 1 )
+    {
+       lpVideoControl->VideoStatus &= (~TV1SURFACE_CREATED);
+       lpVideoControl->PORTID = PORT1;
+    }
+    else
+    {
+       lpVideoControl->VideoStatus &= (~TV0SURFACE_CREATED);
+       lpVideoControl->PORTID = PORT0;
+    }
+
+    //up(&via->lock);
+
+    kfree(lpSurfaceDesc);
+
+    return;
+}
+
+
+/*
+ *  via_set_window() : overlay video image on screen
+ */
+void via_set_window(via_device *via)
+{
+    DDUPDATEOVERLAY      UpdateOverlay_Cap;
+    LPDDUPDATEOVERLAY    lpUpdateOverlay = &UpdateOverlay_Cap;
+
+    DBG_DD(" via_v4l : set_window: Dst %dx%d, %d, %d \n",
+               via->video_win.width, via->video_win.height, via->video_win.x, via->video_win.y);
+
+    if (lpVideoControl->PORTID == PORT0)
+    {
+        lpVideoControl->VideoStatus |= TV0_VIDEO_ON;
+    }
+    else if (lpVideoControl->PORTID == PORT1)
+    {
+        lpVideoControl->VideoStatus |= TV1_VIDEO_ON;
+    }
+
+
+    lpUpdateOverlay->rSrc.left = 0;
+    lpUpdateOverlay->rSrc.top = 0;
+    lpUpdateOverlay->rSrc.right = 720;
+
+    if (via->video_chan.norm == VIDEO_MODE_NTSC)
+    {
+        /*if (via->video_dev->minor == 0)*/ /* capture 1 */
+        if (via->video_dev->minor == 1) /* capture 1 */
+        {
+            if (!(gdwVideoFlagTV1 & VIDEO_HQV_INUSE) && (via->CapInfo.dwDeinterlaceMode == VIA_DEINTERLACE_BOB))
+            {
+                lpUpdateOverlay->rSrc.bottom = 240;
+            }
+            else
+            {
+                lpUpdateOverlay->rSrc.bottom = 480;
+            }
+        }
+        else /* capture 0 */
+        {
+            if (!(gdwVideoFlagTV0 & VIDEO_HQV_INUSE) && (via->CapInfo.dwDeinterlaceMode == VIA_DEINTERLACE_BOB))
+            {
+                lpUpdateOverlay->rSrc.bottom = 240;
+            }
+            else
+            {
+                lpUpdateOverlay->rSrc.bottom = 480;
+            }
+        }
+    }
+    else if ( (via->video_chan.norm == VIDEO_MODE_PAL) || (via->video_chan.norm == VIDEO_MODE_SECAM) )
+    {
+        /*if (via->video_dev->minor == 0)*/ /* capture 1 */
+        if (via->video_dev->minor == 1) /* capture 1 */
+        {
+            if (!(gdwVideoFlagTV1 & VIDEO_HQV_INUSE) && (via->CapInfo.dwDeinterlaceMode == VIA_DEINTERLACE_BOB))
+            {
+                lpUpdateOverlay->rSrc.bottom = 288;
+            }
+            else
+            {
+                lpUpdateOverlay->rSrc.bottom = 576;
+            }
+        }
+        else /* capture 0 */
+        {
+            if (!(gdwVideoFlagTV0 & VIDEO_HQV_INUSE) && (via->CapInfo.dwDeinterlaceMode == VIA_DEINTERLACE_BOB))
+            {
+                lpUpdateOverlay->rSrc.bottom = 288;
+            }
+            else
+            {
+                lpUpdateOverlay->rSrc.bottom = 576;
+            }
+        }
+    }
+
+    lpUpdateOverlay->rDest.left = via->video_win.x;
+    lpUpdateOverlay->rDest.top = via->video_win.y;
+    lpUpdateOverlay->rDest.right = via->video_win.x + via->video_win.width;
+    lpUpdateOverlay->rDest.bottom = via->video_win.y + via->video_win.height;
+
+    if(via->video_cap.type & VID_TYPE_CHROMAKEY)
+        lpUpdateOverlay->dwFlags = DDOVER_SHOW | DDOVER_KEYDEST;
+    else
+        lpUpdateOverlay->dwFlags = DDOVER_SHOW;
+
+    // Fixed for SAMM in Panning Mode
+    // if ADJUSTFRAME-> VIDIOCSWIN is called
+    if (via->video_win.flags == 1)
+    {
+        lpUpdateOverlay->dwFlags |= DDOVER_ON_SND;
+    }
+    
+    lpUpdateOverlay->dwColorSpaceLowValue = via->color_key;
+    lpUpdateOverlay->dwColorSpaceHighValue = via->color_key;
+
+    lpUpdateOverlay->dwFourcc = FOURCC_YUY2;
+
+    UpdateVPort(via) ;
+    UpdateOverlayTV(lpUpdateOverlay, via) ;
+
+}
+
+void EnableInterrupt(void)
+{
+  unsigned long dwRegVal;
+  
+  #ifdef USE_CAPTURE0
+  #ifdef USE_DMA_CH1
+  dwRegVal = 0x90800000;
+  #else
+  dwRegVal = 0x90000000;
+  #endif
+  #else //USE_CAPTURE0
+  #ifdef USE_DMA_CH1
+  dwRegVal = 0x81800000;
+  #else
+  dwRegVal = 0x81000000;
+  #endif
+  #endif //USE_CAPTURE0
+  VIDOutD(V_FLAGS, VIDInD(V_FLAGS) | dwRegVal);        
+
+}
+
+void DisableInterrupt(void)
+{
+  unsigned long dwRegVal;
+
+  //Clear all status and Interrupt enable bit but keep all mask  
+  
+  dwRegVal = 0x0000ffff;
+  VIDOutD(V_FLAGS, dwRegVal);
+  
+}
+
+/*
+ *  v4l-device-related-functions
+ */
+
+static int km_open(struct inode *inode, struct file *file)
+{
+    int minor = iminor(inode);
+    via_device *via = NULL;
+    unsigned int i;
+
+    for (i = 0; i < MAX_VIA_BOARDS; i++) {
+        if (via_v4l_devices[i].video_dev->minor == minor) {
+                 via = &via_v4l_devices[i];
+                 break;
+        }
+    }
+
+    if (NULL == via)
+        return -ENODEV;
+			    
+    DBG_DD("via_v4l: open is called.\n");
+    //DBG_DD("via_v4l: dev= %p\n", dev);
+    //DBG_DD("via_v4l: via= %p\n", via);
+
+    via->frame.buf_ptr=0;
+    via->frame_even.buf_ptr=0;
+    via->buf_read_from=0;
+    via->total_frames=0;
+    via->overrun=0;
+    via->user_count++;
+    
+    switch ( via->deviceID )
+    {
+        case VIA_DEVICE_VT3205:
+            break;        
+        case VIA_DEVICE_CLE1:
+        case VIA_DEVICE_CLE2:
+            EnableInterrupt();            
+            break;            
+        default:
+            break;
+    }
+
+    file->private_data = via;
+    return 0;
+}
+
+
+static int km_close(struct inode *inode, struct file *file)
+{
+    via_device *via=(via_device *) file->private_data;
+
+    DBG_DD("via_v4l: close is called.\n");
+
+    via->user_count--;
+
+    switch (via->video_dev->minor)
+    {
+    case COMMAND_FOR_TV0 :
+    case COMMAND_FOR_TV1 :
+        if (via->user_count == 0)
+        {
+            DestroyTVSurface(via);
+        }
+        break;
+
+    case COMMAND_FOR_OTHER :
+    default:
+        break;
+    }
+    return 0;
+}
+
+static ssize_t km_write(struct file *file, const char *data, size_t count, loff_t *ppos)
+{
+    return -EINVAL;
+}
+
+static ssize_t km_read(struct file *file, char *data, size_t count, loff_t *ppos)
+{
+    return 0;
+}
+
+static int km_ioctl(struct inode *inode, struct file *file, unsigned int cmd, unsigned long ul_arg)
+{
+    via_device *via=(via_device *)file->private_data;
+    int i,ret = 0;
+    void *arg = (void *) ul_arg;
+
+    switch(cmd)
+    {
+        case VIA_VID_UPDATEOVERLAY:
+        {
+            DDUPDATEOVERLAY  UpdateOverlay;
+            LPDDUPDATEOVERLAY lpUpdateOverlay = &UpdateOverlay;
+
+            DBG_DD("via_v4l: ioctl VIA_VID_UPDATEOVERLAY\n");
+
+            if(copy_from_user(lpUpdateOverlay, arg, sizeof(DDUPDATEOVERLAY)))
+                return -EFAULT;
+
+            //down(&via->lock);
+            if (PI_OK == VIADriverProc(UPDATEOVERLAY , lpUpdateOverlay))
+            {
+                //up(&via->lock);
+                return ret;
+            }
+            else
+            {
+                //up(&via->lock);
+                return -EFAULT;
+            }
+        }
+
+        case VIDIOCGCAP:
+        {
+            struct video_capability b;
+
+            DBG_DD("via_v4l: ioctl VIDIOCGCAP\n");
+            strcpy(b.name,via->video_dev->name);
+
+            /*if (via->video_dev->minor==0)*/
+            if (via->video_dev->minor==1)
+            {
+                b.type = VID_TYPE_CAPTURE|
+                         VID_TYPE_CLIPPING|
+                         VID_TYPE_CHROMAKEY|
+                         VID_TYPE_SCALES;
+
+                /* If TV0 not on or overlay supported,
+                 * we have overlay capability for TV1(capture1), unless bolck it
+                 */
+                if (!(VIDInD(V1_CONTROL)&V1_ENABLE) || DecideOverlaySupport())
+                {
+                    b.type |= VID_TYPE_OVERLAY;
+                }
+
+                if (via->CapInfo.Tuner != 0)
+                {
+                    b.type |= VID_TYPE_TUNER;
+                }
+            }
+            else
+            {
+                DBG_DD("via_v4l: DecideOverlaySupport: %d\n", DecideOverlaySupport());
+
+                b.type = VID_TYPE_CAPTURE|
+                         VID_TYPE_CLIPPING|
+                         VID_TYPE_CHROMAKEY|
+                         VID_TYPE_SCALES;
+
+                /* If TV1 not on or overlay supported,
+                 * we have overlay capability for TV0(capture0), unless bolck it
+                 */
+                if (!(VIDInD(V3_CONTROL)&V3_ENABLE) || DecideOverlaySupport())
+                {
+                    b.type |= VID_TYPE_OVERLAY;
+                }
+
+                if (via->CapInfo.Tuner != 0)
+                {
+                    b.type |= VID_TYPE_TUNER;
+                }
+            }
+
+            b.channels = 3;
+            b.audios = 0;
+            b.maxwidth = 1600;
+            b.maxheight = 1200;
+            b.minwidth = 48;
+            b.minheight = 32;
+            memcpy(&via->video_cap, &b, sizeof(b));
+
+            if(copy_to_user(arg,&b,sizeof(b)))
+                return -EFAULT;
+
+            return ret;
+        }
+
+        case VIDIOCGCHAN:
+        {
+            struct video_channel v;
+
+            if(copy_from_user(&v, arg,sizeof(v)))
+                    return -EFAULT;
+            DBG_DD("via_v4l: ioctl VIDIOCGCHAN: get channel %d param.\n", v.channel);
+            v.flags = VIDEO_VC_AUDIO;
+            v.tuners = 0;
+            v.type = VIDEO_TYPE_CAMERA;
+            v.norm = VIDEO_MODE_NTSC;
+
+            if (v.channel>=3)
+                return -EINVAL;
+
+            if (v.channel==0)
+                strcpy(v.name,"Composite");
+            else if (v.channel==1)
+            {
+                strcpy(v.name,"Television");
+                v.flags|=VIDEO_VC_TUNER;
+                v.type=VIDEO_TYPE_TV;
+                v.tuners=1;
+            }
+            else
+                strcpy(v.name,"S-Video");
+            if(copy_to_user(arg,&v,sizeof(v)))
+                    return -EFAULT;
+            
+            return ret;
+        }
+        case VIDIOCSCHAN:
+        {
+            struct video_channel v;
+
+            if(copy_from_user(&v, arg,sizeof(v)))
+                return -EFAULT;
+            DBG_DD("via_v4l: ioctl VIDIOCSCHAN: set channel %d param.\n", v.channel);
+                if (v.channel>=3)
+                      return -EINVAL;
+            DBG_DD("v.name = %s\n",v.name);
+            DBG_DD("v.norm = %d\n",v.norm);
+            DBG_DD("via->video_dev->minor %d\n", via->video_dev->minor);
+            
+            via->video_chan = v;
+
+            switch (v.channel)
+            {
+            case 0 :
+                VDEC_Input_Composite(via);
+                DBG_DD("via_v4l: video decoder set to Composite input\n");
+                break;
+            case 1 :
+                VDEC_Input_TV(via);
+                DBG_DD("via_v4l: video decoder set to TV input\n");
+                break;
+            case 2 :
+                VDEC_Input_SVIDEO(via);
+                DBG_DD("via_v4l: video decoder set to SVideo input\n");
+                break;
+            }
+
+            switch (v.norm)
+            {
+            case VIDEO_MODE_PAL :
+                VDEC_Standard_PAL(via);
+                DBG_DD("via_v4l: vdec set to PAL norm\n");
+                
+                /*if ((via->video_dev->minor == 0) && (lpVideoControl->VideoStatus & TV1SURFACE_CREATED))*/
+                if ((via->video_dev->minor == 1) && (lpVideoControl->VideoStatus & TV1SURFACE_CREATED))
+                {
+                    via_set_window(via);
+                }
+                /*else if ((via->video_dev->minor == 1) && (lpVideoControl->VideoStatus & TV0SURFACE_CREATED))*/
+                else if ((via->video_dev->minor == 0) && (lpVideoControl->VideoStatus & TV0SURFACE_CREATED))
+                {
+                    via_set_window(via);
+                }
+                break;
+            case VIDEO_MODE_NTSC :
+                VDEC_Standard_NTSC(via);
+                DBG_DD("via_v4l: vdec set to NTSC norm\n");
+
+                /*if ((via->video_dev->minor == 0) && (lpVideoControl->VideoStatus & TV1SURFACE_CREATED))*/
+                if ((via->video_dev->minor == 1) && (lpVideoControl->VideoStatus & TV1SURFACE_CREATED))
+                {
+                    via_set_window(via);
+                }
+                /*else if ((via->video_dev->minor == 1) && (lpVideoControl->VideoStatus & TV0SURFACE_CREATED))*/
+                else if ((via->video_dev->minor == 0) && (lpVideoControl->VideoStatus & TV0SURFACE_CREATED))
+                {
+                    via_set_window(via);
+                }
+                break;
+            case VIDEO_MODE_SECAM :
+                VDEC_Standard_SECAM(via);
+                DBG_DD("via_v4l: vdec set to PAL norm\n");
+
+                /*if ((via->video_dev->minor == 0) && (lpVideoControl->VideoStatus & TV1SURFACE_CREATED))*/
+                if ((via->video_dev->minor == 1) && (lpVideoControl->VideoStatus & TV1SURFACE_CREATED))
+                {
+                    via_set_window(via);
+                }
+                /*else if ((via->video_dev->minor == 1) && (lpVideoControl->VideoStatus & TV0SURFACE_CREATED))*/
+                else if ((via->video_dev->minor == 0) && (lpVideoControl->VideoStatus & TV0SURFACE_CREATED))
+                {
+                    via_set_window(via);
+                }
+                break;
+            }
+            
+            return ret;
+        }
+
+        case VIDIOCGPICT:
+        {
+            struct video_picture p=via->video_pic;
+
+            if (via->CapInfo.NoAutoDetect)
+            {
+                via->video_pic.brightness = via->CapInfo.Brightness << 8;
+                via->video_pic.contrast = via->CapInfo.Contrast << 8;
+                via->video_pic.hue = via->CapInfo.Hue << 8;
+                via->video_pic.colour = via->CapInfo.Saturation << 8;
+            }
+
+            DBG_DD("via_v4l: ioctl VIDIOCGPICT\n");
+            DBG_DD("  brightness %d\n", via->video_pic.brightness);
+            DBG_DD("  contrast: %d\n", via->video_pic.contrast);
+            DBG_DD("  hue %d\n", via->video_pic.hue);
+            DBG_DD("  saturation %d\n", via->video_pic.colour);
+            if(copy_to_user(arg, &p, sizeof(via->video_pic)))
+                return -EFAULT;
+
+            return ret;
+        }
+
+        case VIDIOCSPICT:
+        {
+            struct video_picture p;
+
+            DBG_DD("via_v4l: ioctl VIDIOCSPICT\n");
+            if(copy_from_user(&p, arg,sizeof(p)))
+                return -EFAULT;
+
+            DBG_DD("via_v4l: set brightness: %d\n", p.brightness);
+            VDEC_Brightness(Attr_Mapping(p.brightness), via);
+            DBG_DD("via_v4l: set hue: %d\n", p.hue);
+            VDEC_Hue(Attr_Mapping(p.hue), via);
+            DBG_DD("via_v4l: set saturation: %d\n", p.colour);
+            VDEC_Saturation(Attr_Mapping(p.colour), via);
+            DBG_DD("via_v4l: set contrast: %d\n", p.contrast);
+            VDEC_Contrast(Attr_Mapping(p.contrast), via);
+
+            return ret;
+        }
+
+        case VIDIOCGWIN:
+        {
+
+            DBG_DD("via_v4l: ioctl VIDIOCGWIN\n");
+            if(copy_to_user(arg,&via->video_win,sizeof(via->video_win)))
+                return -EFAULT;
+
+            return ret;
+        }
+
+        case VIDIOCSWIN:
+        {
+            struct video_window vw;
+            //struct video_clip *vcp = NULL;
+            int ScrnIndex = 0;
+                        
+            DBG_DD("via_v4l: ioctl VIDIOCSWIN\n");
+            if(copy_from_user(&vw,arg,sizeof(vw)))
+                return -EFAULT;
+
+            memcpy(&via->video_win, &vw, sizeof(vw));
+
+            if ( vw.flags == 1 )
+            {
+                ScrnIndex = 1;
+            } 
+/*
+            if (via->video_dev->minor==1)
+            {
+                if (gVIAGraphicInfo.CapInfo[1].dwDeinterlaceMode == VIA_DEINTERLACE_WEAVE)
+                {
+                    via->CapInfo.dwDeinterlaceMode = VIA_DEINTERLACE_WEAVE;
+                }
+                else if (gVIAGraphicInfo.CapInfo[1].dwDeinterlaceMode == VIA_DEINTERLACE_BOB)
+                {
+                    via->CapInfo.dwDeinterlaceMode = VIA_DEINTERLACE_BOB;
+                }
+            }
+            else
+            {
+                if (gVIAGraphicInfo.CapInfo[0].dwDeinterlaceMode == VIA_DEINTERLACE_WEAVE)
+                {
+                    via->CapInfo.dwDeinterlaceMode = VIA_DEINTERLACE_WEAVE;
+                }
+                else if (gVIAGraphicInfo.CapInfo[0].dwDeinterlaceMode == VIA_DEINTERLACE_BOB)
+                {
+                    via->CapInfo.dwDeinterlaceMode = VIA_DEINTERLACE_BOB;
+                }
+            } 
+*/
+
+            DBG_DD("via_v4l: chromakey 0x%x\n", vw.chromakey);
+            // This setting is for Alpha, if the colorkey sent from
+            // AP is 0x00ffffff, then means AP will use alpha, 
+            // so we should disable colorkey
+            if (vw.chromakey == 0x00ffffff)
+                via->video_cap.type &= ~VID_TYPE_CHROMAKEY;
+
+            // Coz xawtv AP doesn't deal with the colorkey in 
+            // different depth, we deal with it here.
+            // RGB32->RGB565 : red_component >>3, green_component >>2, blue_component >>3
+            if (gVIAGraphicInfo.Screen[ScrnIndex].dwBPP == 32)
+                via->color_key = vw.chromakey;
+            else if (gVIAGraphicInfo.Screen[ScrnIndex].dwBPP == 16)
+            {
+                via->color_key = ((((vw.chromakey & 0xff0000)>>16)>>3)<<11)|
+                                 ((((vw.chromakey & 0x00ff00)>>8)>>2)<<5)|
+                                 ((vw.chromakey & 0x0000ff)>>3);
+            }
+            else if (gVIAGraphicInfo.Screen[ScrnIndex].dwBPP == 8)
+                via->color_key = 0xd8;
+
+            DBG_DD("VideoStatus=0x%08lx\n", lpVideoControl->VideoStatus);
+            if(!CreateTVSurface(via))
+                return -EFAULT;
+
+            DBG_DD("minor=%d\n", via->video_dev->minor);
+            DBG_DD("clip count=%d\n", vw.clipcount);
+            DBG_DD("chromakey=%lx\n", via->color_key);
+
+            via_set_window(via);
+
+            /*
+            if ((vw.clipcount == 0) && (via->video_dev->minor == COMMAND_FOR_TV1) )
+                VIDOutD(V_COMPOSE_MODE ,VIDInD(V_COMPOSE_MODE) | COMPOSE_V3_TOP);
+            else if ((vw.clipcount == 0) && (via->video_dev->minor == COMMAND_FOR_TV0) )
+                VIDOutD(V_COMPOSE_MODE ,VIDInD(V_COMPOSE_MODE) & ~COMPOSE_V3_TOP);
+            */
+            // do 2d BitBlt on driver
+            /*
+            VIDOutD(VIA_REG_DSTCOLORKEY, 0x321);
+            VIDOutD(VIA_REG_DIMENSION, 30 << 16 | 60);
+            VIDOutD(VIA_REG_DSTPOS, 600 << 16 | 800);
+            VIDOutD(VIA_REG_GECMD, 0x00000001| 0x00002000 | 0xF0000000);
+            */
+            return ret;
+        }
+
+        case VIDIOCGFBUF:
+        {
+            int ScrnIndex = 0;//Need to check!!
+
+            DBG_DD("via_v4l: ioctl VIDIOCGFBUF\n");
+
+            /* get frame buffer(On screen or PrimarySurface) parameter */
+            via->video_buf.base = (void *) via->mb0;
+            via->video_buf.width = gVIAGraphicInfo.Screen[ScrnIndex].dwWidth;
+            via->video_buf.height = gVIAGraphicInfo.Screen[ScrnIndex].dwHeight;
+            via->video_buf.depth = gVIAGraphicInfo.Screen[ScrnIndex].dwBPP;
+            via->video_buf.bytesperline = gVIAGraphicInfo.Screen[ScrnIndex].dwPitch;
+
+            if(copy_to_user(arg, &via->video_buf,sizeof(via->video_buf)))
+                return -EFAULT;
+            return ret;
+                        
+        }
+
+        case VIDIOCSFBUF:
+        {
+            struct video_buffer v;
+
+            DBG_DD("via_v4l: ioctl VIDIOCSFBUF\n");
+            if(!capable(CAP_SYS_ADMIN) &&
+               !capable(CAP_SYS_RAWIO))
+                return -EPERM;
+            if(copy_from_user(&v, arg,sizeof(v)))
+                return -EFAULT;
+            if(v.depth!=8 && v.depth!=15 && v.depth!=16 && 
+               v.depth!=24 && v.depth!=32 && v.width > 16 &&
+               v.height > 16 && v.bytesperline > 16)
+                return -EINVAL;
+        
+            DBG_DD("Display at %p is %d by %d, bytedepth %d, bpl %d\n",
+                    v.base, v.width,v.height, v.depth, v.bytesperline);
+            
+            memcpy(&via->video_buf, &v, sizeof(v));
+            //CreateTVSurface(via);
+
+            return ret;
+        }
+
+        case VIDIOCCAPTURE:
+        {
+            int v;
+
+            if(copy_from_user(&v, arg,sizeof(v)))
+                return -EFAULT;
+            DBG_DD("via_v4l: ioctl VIDIOCCAPTURE: %d\n", v);
+            /*DBG_DD("via_v4l:       command for TV%d\n", via->video_dev->minor+1);*/
+            DBG_DD("via_v4l:       command for TV%d\n", via->video_dev->minor);
+
+            if (v == 1)
+            {
+                if (via->video_dev->minor == COMMAND_FOR_TV1)
+                    VIDOutD(CAP1_CONTROL, VIDInD(CAP1_CONTROL) | C1_ENABLE);
+                else
+                    VIDOutD(CAP0_CONTROL, VIDInD(CAP0_CONTROL) | C0_ENABLE);
+            }
+            else
+            {
+                if (via->video_dev->minor == COMMAND_FOR_TV1)
+                {
+                    VIDOutD(CAP1_CONTROL, VIDInD(CAP1_CONTROL) & ~C1_ENABLE);
+                    lpVideoControl->PORTID = PORT1;
+                    VIAStopVideo();
+                    //DestroyTVSurface(via);
+                }
+                else
+                {
+                    VIDOutD(CAP0_CONTROL, VIDInD(CAP0_CONTROL) & ~C0_ENABLE);
+                    lpVideoControl->PORTID = PORT0;
+                    VIAStopVideo();
+                    //DestroyTVSurface(via);
+                }
+            }
+            return ret;
+        }
+
+        case VIDIOCGTUNER:
+        {  
+            struct video_tuner v;
+
+            DBG_DD("via_v4l: ioctl VIDIOCGTUNER\n");
+            if(copy_from_user(&v,arg,sizeof(v))!=0)
+                return -EFAULT;
+
+            strcpy(v.name, "Television");
+            v.rangelow=0;
+            v.rangehigh=0xFFFFFFFF;
+            v.flags=VIDEO_TUNER_PAL|VIDEO_TUNER_NTSC|VIDEO_TUNER_SECAM;
+            v.mode = via->video_chan.norm;
+            v.signal = 0;
+            if(copy_to_user(arg,&v,sizeof(v)))
+                return -EFAULT;
+
+            return 0;
+        }
+
+        /* We have but one tuner */
+        case VIDIOCSTUNER:
+        {
+            struct video_tuner v;
+
+            DBG_DD("via_v4l: ioctl VIDIOCSTUNER\n");
+            if(copy_from_user(&v, arg, sizeof(v)))
+                return -EFAULT;
+
+            /* Only one channel has a tuner */
+            if(v.tuner != 1)
+                return -EINVAL;
+                                
+            if(v.mode!=VIDEO_MODE_PAL&&v.mode!=VIDEO_MODE_NTSC
+                &&v.mode!=VIDEO_MODE_SECAM)
+                return -EOPNOTSUPP;
+            if (via->video_chan.norm != v.mode)
+            {
+                  via->video_chan.norm = v.mode;
+            }
+
+            return 0;
+        }
+
+        case VIDIOCGFREQ:
+        {
+            unsigned long v=via->freq;
+
+            DBG_DD("via_v4l: ioctl VIDIOCGFREQ: freq= 0x%lx\n", v);
+            if(copy_to_user(arg,&v,sizeof(v)))
+                return -EFAULT;
+
+            return 0;
+        }
+
+        case VIDIOCSFREQ:
+        {
+            unsigned long v;
+            LPVIASETTUNERDATA lpTunerParam =  (LPVIASETTUNERDATA)kmalloc(sizeof(VIASETTUNERDATA), GFP_KERNEL);
+            short    divider = 0;
+
+            DBG_DD("via_v4l: ioctl VIDIOCSFREQ: freq= 0x%lx\n", v);
+            if(copy_from_user(&v, arg, sizeof(v)))
+                return -EFAULT;
+
+            via->freq=v;
+
+            divider=v;
+            if (via->video_chan.channel == 2)
+            {
+                switch(via->video_chan.norm)
+                {
+                case VIDEO_MODE_PAL   :
+                     divider=633+(short)v;
+                     break;
+                case VIDEO_MODE_NTSC  :
+                     divider=733+(short)v;
+                     break;
+                }
+            }
+
+            lpTunerParam->divider = divider;
+            lpTunerParam->control = 0x8E00;
+
+            if ( divider <= LOW_BAND )
+            {
+               lpTunerParam->control = lpTunerParam->control | 0xA0;
+            }
+            else{
+               if ( divider <= MID_BAND )
+                  lpTunerParam->control = lpTunerParam->control | 0x90;
+               else
+                  lpTunerParam->control = lpTunerParam->control | 0x30;
+            }
+
+            DBG_DD(" via_video.c : SetTunerChannel : Divider = 0x%08x, Control= 0x%08x, \n",
+                    lpTunerParam->divider,lpTunerParam->control);
+
+            //VIADriverProc( TUNER_SETCHANNEL , lpTunerParam);
+
+             if (!AUDIO_MUTE)
+             {
+                Macro_SetI2CIndex();
+                AUDIO_MUTE_ON();
+                Macro_RestoreI2CIndex();
+
+                TUNER_ProgChannel( via, ((LPVIASETTUNERDATA)lpTunerParam)->divider,
+                                   ((LPVIASETTUNERDATA)lpTunerParam)->control);
+                
+                // Delay for a while to eliminate the unpleasant sound noise while changing channels
+                // This will cause too much Delay.
+                udelay(1);
+                
+                Macro_SetI2CIndex();
+                AUDIO_MUTE_OFF();   
+                Macro_RestoreI2CIndex();                            
+             }
+             else 
+             {
+                TUNER_ProgChannel( via, ((LPVIASETTUNERDATA)lpTunerParam)->divider,
+                                   ((LPVIASETTUNERDATA)lpTunerParam)->control);             
+             }
+
+            if ( lpTunerParam )
+                kfree(lpTunerParam);
+
+            return 0;
+        }
+    
+        case VIDIOCGMBUF:
+        {
+                struct video_mbuf vm;
+                memset(&vm, 0 , sizeof(vm));
+                vm.size=via->dwVideoRambytes;
+                vm.frames=gbuffers;
+
+                DBG_DD("via_v4l: ioctl VIDIOCGMBUF\n");
+
+                for (i = 0; i < gbuffers; i++)
+                        vm.offsets[i] = CAPDevice[1].dwCAPPhysicalAddr[i];
+                if(copy_to_user(arg, &vm, sizeof(vm)))
+                        return -EFAULT;
+
+                return ret;
+        }
+
+        case VIDIOCMCAPTURE:
+        {
+                struct video_mmap vm;
+                int ret=0;
+
+                DBG_DD("via_v4l: ioctl VIDIOCMCAPTURE\n");
+                if(copy_from_user(&vm, arg, sizeof(vm)))
+                        return -EFAULT;
+                //ret = vgrab(via, &vm);
+
+                return ret;
+        }
+                
+        case VIDIOCSYNC:
+        {
+
+                DBG_DD("via_v4l: ioctl VIDIOCSYNC\n");
+
+                return ret;
+        }
+
+        case VIA_VID_GET_2D_INFO:
+        {
+            DBG_DD("via_v4l: ioctl VIA_VID_GET_2D_INFO\n");
+
+            if(copy_to_user(arg, &gVIAGraphicInfo,sizeof(gVIAGraphicInfo)))
+                return -EFAULT;
+
+            return ret;
+        }
+        case VIA_VID_SET_2D_INFO:
+        {
+            int ScrnIndex = 0;//Need to check!!
+            
+            DBG_DD("via_v4l: ioctl VIA_VID_SET_2D_INFO\n");
+            
+            if(copy_from_user(&gVIAGraphicInfo, arg, sizeof(gVIAGraphicInfo)))
+                return -EFAULT;
+
+            // Save MCLK value
+            outb(0x16, 0x3C4); Save_3C4_16 = inb(0x3C5);
+            DBG_DD("store 3c4.16 : %08x \n",inb(0x3C5));
+            outb(0x17, 0x3C4); Save_3C4_17 = inb(0x3C5);
+            DBG_DD("store 3c4.17 : %08x \n",inb(0x3C5));
+            outb(0x18, 0x3C4); Save_3C4_18 = inb(0x3C5);
+            DBG_DD("store 3c4.18 : %08x \n",inb(0x3C5));
+
+            DBG_DD("videoheapbase: 0x%lx\n", gVIAGraphicInfo.Screen[ScrnIndex].VideoHeapBase);
+            DBG_DD("videoheapend: 0x%lx\n", gVIAGraphicInfo.Screen[ScrnIndex].VideoHeapEnd);
+            DBG_DD("dwWidth: 0x%lx\n", gVIAGraphicInfo.Screen[ScrnIndex].dwWidth);
+            
+            return ret;
+        }
+
+        case VIA_VID_GET_VIDCTL:
+        {
+            DBG_DD("via_v4l: ioctl VIA_VID_GET_VIDCTL\n");
+
+            if(copy_to_user(arg, lpVideoControl,sizeof(VIAVIDCTRL)))
+                return -EFAULT;
+
+            return ret;
+        }
+
+        case VIA_VID_SET_VIDCTL:
+        {
+            VIAVIDCTRL NewvidCtrl;
+            LPVIAVIDCTRL lpNewVidCtrl = &NewvidCtrl;
+            
+            DBG_DD("via_v4l: ioctl VIA_VID_SET_VIDCTL\n");
+            
+            if(copy_from_user(lpNewVidCtrl, arg, sizeof(VIAVIDCTRL)))
+                return -EFAULT;
+
+            DBG_DD("VidCtrl.PORTID 0x%x\n", lpNewVidCtrl->PORTID);
+            DBG_DD("VidCtrl.HighQVDO 0x%lx\n", lpNewVidCtrl->dwHighQVDO);
+            
+            switch (lpNewVidCtrl->dwAction) {
+                            
+                case ACTION_SET_PORTID :
+                    DBG_DD(" ACTION_SET_PORTID\n");
+                    lpVideoControl->PORTID =  lpNewVidCtrl->PORTID;
+                    break;
+
+                case ACTION_SET_COMPOSE :
+                    DBG_DD(" ACTION_SET_COMPOSE\n");
+                    if (lpVideoControl->dwCompose != lpNewVidCtrl->dwCompose) 
+                    {
+                        lpVideoControl->dwCompose = lpNewVidCtrl->dwCompose;
+                        if (lpVideoControl->dwCompose & (VW_TV1_TOP | VW_TV_TOP) )
+                        {
+                            unsigned long volatile *pdwState = (unsigned long volatile *) lpVidMEMIO;
+                            pdwState = (unsigned long volatile *) (lpVidMEMIO+V_COMPOSE_MODE);
+                            while ((*pdwState & V1_COMMAND_FIRE));
+                            VIDOutD(V_COMPOSE_MODE, *pdwState | COMPOSE_V3_V1 );
+                        }
+                        else if (lpVideoControl->dwCompose & (VW_TV0_TOP | VW_DVD_TOP) )
+                        {
+                            unsigned long volatile *pdwState = (unsigned long volatile *) lpVidMEMIO;
+                            pdwState = (unsigned long volatile *) (lpVidMEMIO+V_COMPOSE_MODE);
+                            while ((*pdwState & V1_COMMAND_FIRE));
+                            VIDOutD(V_COMPOSE_MODE, *pdwState & (~COMPOSE_V3_V1) );
+                        }
+                    }
+                    else
+                    {
+                        DBG_DD("ACTION_SET_COMPOSE:not changed\n");
+                    }
+                    break;
+                    
+                case ACTION_SET_HQV:
+                     DBG_DD("ACTION_SET_HQV!!!!\n");
+                     //lpNewVidCtrl->dwHighQVDO = VW_HIGHQVDO_OFF;
+                     VIADriverProc( HQVCONTROL , lpNewVidCtrl );
+                     break;
+
+                case ACTION_SET_VIDEOSTATUS:
+                    lpVideoControl->VideoStatus = lpNewVidCtrl->VideoStatus;
+                    DBG_DD(" VideoStatus: %lx\n", lpVideoControl->VideoStatus);
+                    break;
+
+            }
+            
+            return ret;
+        }
+
+        case VIA_VID_CREATESURFACE:
+        {
+            DDSURFACEDESC ddSurfaceDesc;
+            LPDDSURFACEDESC lpSurfaceDesc = &ddSurfaceDesc;
+
+            DBG_DD("via_v4l: ioctl VIA_VID_CREATESURFACE\n");
+
+            if(copy_from_user(lpSurfaceDesc, arg, sizeof(DDSURFACEDESC)))
+                return -EFAULT;
+
+            gdwOverlaySupport = DecideOverlaySupport();
+
+            if (PI_OK == VIADriverProc(CREATESURFACE, lpSurfaceDesc))
+                return ret;
+            else
+                return -EFAULT;
+        }
+
+        case VIA_VID_DESTROYSURFACE:
+        {
+            DDSURFACEDESC ddSurfaceDesc;
+            LPDDSURFACEDESC lpSurfaceDesc = &ddSurfaceDesc;
+
+            DBG_DD("via_v4l: ioctl VIA_VID_DESTROYSURFACE\n");
+
+            if(copy_from_user(lpSurfaceDesc, arg, sizeof(DDSURFACEDESC)))
+                return -EFAULT;
+
+            if (PI_OK == VIADriverProc(DESTROYSURFACE, lpSurfaceDesc))
+                return ret;
+            else
+                return -EFAULT;
+        }
+
+        case VIA_VID_LOCKSURFACE:
+        {
+            DDLOCK  ddLock;
+            LPDDLOCK lpddLock = &ddLock;
+
+            DBG_DD("via_v4l: ioctl VIA_VID_LOCKSURFACE\n");
+
+            if(copy_from_user(lpddLock, arg, sizeof(DDLOCK)))
+                return -EFAULT;
+
+            if (PI_OK == VIADriverProc(LOCKSURFACE , lpddLock))
+            {
+                if(copy_to_user( arg, lpddLock,sizeof(DDLOCK)))
+                    return -EFAULT;
+
+                return ret;
+            }
+            else
+                return -EFAULT;
+        }
+
+        case VIA_VID_SETALPHAWIN:
+        {
+            ALPHACTRL AlphaCtrl;
+            LPALPHACTRL lpAlphaCtrl = &AlphaCtrl;
+            
+            DBG_DD("via_v4l: ioctl VIA_VID_SETALPHAWIN\n");
+
+            if(copy_from_user(lpAlphaCtrl, arg, sizeof(ALPHACTRL)))
+                return -EFAULT;
+
+            if (PI_OK == VIADriverProc(SETALPHAWIN , lpAlphaCtrl))
+                return ret;
+            else
+                return -EFAULT;
+        }
+                
+        case VIA_VID_UPDATEALPHA:
+        {
+            RECTL rDest;
+            
+            DBG_DD("via_v4l: ioctl VIA_VID_UPDATEALPHA\n");
+
+            if(copy_from_user(&rDest, arg, sizeof(RECTL)))
+                return -EFAULT;
+
+            if (PI_OK == UpdateOverlayAlpha(rDest))
+                return ret;
+            else
+                return -EFAULT;
+        }
+
+        case VIA_VID_ADJUSTFRAME:
+        {
+            ADJUSTFRAME AdjustFrame;
+            int ScrnIndex = 0;
+
+            DBG_DD("via_v4l: ioctl VIA_VID_ADJUSTFRAME\n");
+
+            if(copy_from_user(&AdjustFrame, arg,sizeof(ADJUSTFRAME)))
+                return -EFAULT;
+            
+            /*Modified for SAMM*/
+            if (AdjustFrame.dwFlags & DDOVER_ON_SND)
+            {
+                ScrnIndex = 1;
+            }
+            panning_x[ScrnIndex] = AdjustFrame.x;
+            panning_y[ScrnIndex] = AdjustFrame.y;
+
+            return ret;
+        }
+
+        case VIA_VID_FLIP:
+        {
+            unsigned long DisplayBufferIndex;
+
+            if(copy_from_user(&DisplayBufferIndex, arg,sizeof(DisplayBufferIndex)))
+                return -EFAULT;
+            DBG_DD("via_v4l: ioctl VIA_VID_FLIP: %ld\n", DisplayBufferIndex);
+
+            if (PI_OK == VIADriverProc(FLIP , &DisplayBufferIndex))
+                return ret;
+            else
+                return -EFAULT;
+        }
+
+        case VIAMGR_INFO_XSERVERON:
+        {
+            int ScrnIndex = 0;//Need to check!!
+            
+            //XserverSyncK xa;
+            //OffMemRange *usedq,*unusedq,*tq;
+            //VIAMEMINFO VIAMemInfo;
+
+            // Set to improve capture bandwidth issue
+            outb(0x40, 0x3C4); outb(inb(0x3C5)|0x10, 0x3C5);
+
+            if(copy_from_user(&gVIAGraphicInfo, arg, sizeof(gVIAGraphicInfo)))
+                return -EFAULT;
+
+            //viaMgr_init_module(&gVIAGraphicInfo);
+
+            lpPrimarySurface = ioremap(via->mb0, gVIAGraphicInfo.Screen[ScrnIndex].TotalVRAM);
+            /* This will get total 64MB mem-map space, and waste the memory */
+            //lpPrimarySurface = (unsigned char *)ioremap(via->mb0, pci_resource_len(dev, 0));
+            DBG_DD("via_v4l: IOCTL : VIAMGR_INFO_XSERVERON : Begin 0x%lx,End 0x%lx\n"
+                      , gVIAGraphicInfo.Screen[ScrnIndex].VideoHeapBase, gVIAGraphicInfo.Screen[ScrnIndex].VideoHeapEnd);
+            DBG_DD("via_v4l: lpPrimarySurface: 0x%p, length=0x%lx\n", lpPrimarySurface, gVIAGraphicInfo.Screen[ScrnIndex].TotalVRAM);
+            DBG_DD("dwWidth: 0x%lx\n", gVIAGraphicInfo.Screen[ScrnIndex].dwWidth);
+            DBG_DD("dwHeight: 0x%lx\n", gVIAGraphicInfo.Screen[ScrnIndex].dwHeight);
+            DBG_DD("dwBPP: 0x%lx\n", gVIAGraphicInfo.Screen[ScrnIndex].dwBPP);
+            DBG_DD("dwRefreshRate: 0x%lx\n", gVIAGraphicInfo.Screen[ScrnIndex].dwRefreshRate);
+            DBG_DD("DRMEnabled: 0x%x\n", gVIAGraphicInfo.DRMEnabled);
+
+            gVIAGraphicInfo.dwDeviceID = (unsigned long) via->deviceID;
+            gVIAGraphicInfo.RevisionID = (int) via->revision;
+            printk("via_v4l: Revision:%d\n",via->revision);
+            vfInitHWDiff(via);
+
+/* Marked the codes, coz it seems no use. */
+#if 0
+            if (!XserverIsUp)
+            {
+                 XserverIsUp = TRUE ;
+            }
+            else
+            {  /* support Xsever restart ;
+                   so we free all allocations */
+
+                usedq = MemLayOut->used;
+                while (usedq != NULL)
+                {
+                    tq = usedq ;
+                    usedq =nextq(tq);
+                    deleteq(tq);
+                }
+
+                unusedq = MemLayOut->unused;
+                while (unusedq != NULL)
+                {
+                    tq = unusedq;
+                    unusedq =nextq(tq);
+                    deleteq(tq);
+                }
+                MemLayOut->unused = NULL;
+                MemLayOut->used = NULL;
+             }
+#endif
+             if (!gVIAGraphicInfo.DRMEnabled)
+             {
+                 viaBankSize = gVIAGraphicInfo.Screen[ScrnIndex].TotalVRAM;
+                 MemLayOut = (ViaOffScrnPtr)kmalloc(sizeof(ViaOffScrnRec), GFP_KERNEL);
+                 MemLayOut->unused = (OffMemRange *)kmalloc(sizeof(OffMemRange), GFP_KERNEL);
+                 memset(MemLayOut->unused, 0, sizeof(OffMemRange));
+                 MemLayOut->unused->StartAddr = gVIAGraphicInfo.Screen[ScrnIndex].VideoHeapBase;
+                 MemLayOut->unused->EndAddr   = gVIAGraphicInfo.Screen[ScrnIndex].VideoHeapEnd;
+                 MemLayOut->unused->size      = gVIAGraphicInfo.Screen[ScrnIndex].VideoHeapEnd - gVIAGraphicInfo.Screen[ScrnIndex].VideoHeapBase + 1;
+                 MemLayOut->unused->next      = NULL;
+                 MemLayOut->used              = NULL;
+                 PrintMemLayOut();
+             }
+             return MEM_OK;
+
+        }
+
+        case VIAMGR_INFO_XSERVEROFF:
+        {
+            OffMemRange *usedq,*unusedq,*tq;
+
+            DBG_DD("via_v4l: IOCTL : VIAMGR_INFO_XSERVEROFF. \n");
+
+            if (!gVIAGraphicInfo.DRMEnabled)
+            {
+                usedq = MemLayOut->used;
+                while (usedq != NULL)
+                {
+                    tq = usedq ;
+                    usedq =nextq(tq);
+                    deleteq(tq);
+                }
+                unusedq = MemLayOut->unused;
+                while (unusedq != NULL)
+                {
+                    tq = unusedq;
+                    unusedq =nextq(tq);
+                    deleteq(tq);
+                }
+
+                deleteq(MemLayOut);
+                /* Marked the XserverIsUp, coz it seems no use. */
+                //XserverIsUp = FALSE ;
+                lpVideoControl->VideoStatus = VIDEO_NULL;
+                PrintMemLayOut();
+            }
+
+            /* If capture engine doesn't shutdown, turn off it here */
+            VIDOutD(CAP0_CONTROL, VIDInD(CAP0_CONTROL) & ~C0_ENABLE);
+            VIDOutD(CAP1_CONTROL, VIDInD(CAP1_CONTROL) & ~C1_ENABLE);
+
+            /* Reset panning mode parameter */
+            /*Modified for SAMM*/
+            panning_x[0] = 0;
+            panning_y[0] = 0;
+            panning_old_x[0] = 0;
+            panning_old_y[0] = 0;
+            panning_x[1] = 0;
+            panning_y[1] = 0;
+            panning_old_x[1] = 0;
+            panning_old_y[1] = 0;
+
+            return MEM_OK;
+        }
+
+        case VIA_VID_GET_CAP_INFO:
+        {
+            DBG_DD("via_v4l: ioctl VIA_VID_GET_CAP_INFO\n");
+
+            if(copy_to_user(arg, &via->CapInfo,sizeof(via->CapInfo)))
+                return -EFAULT;
+
+            return ret;
+        }
+
+        case VIA_VID_SET_CAP_INFO:
+        {
+            DBG_DD("via_v4l: ioctl VIA_VID_SET_CAP_INFO\n");
+            
+            if(copy_from_user(&via->CapInfo, arg, sizeof(via->CapInfo)))
+                return -EFAULT;
+            
+            DBG_DD("vdec address: 0x%x\n", via->CapInfo.Vdec_Slave_Write);
+            /* 3rd party Device Init */
+            InitializeVDEC(via);   /* Init the saa7113 video decoder */
+            InitializeTUNER(via);  /* Init the FI1236 tuner */
+            //InitializeAudio();  // Init Sony CXA2104S audio chip
+
+            return ret;
+        }
+
+    }
+    return -EINVAL;
+}
+
+
+/*
+ *      This maps the vmalloced and reserved fbuffer to user space.
+ *
+ *  FIXME: 
+ *  - PAGE_READONLY should suffice!?
+ *  - remap_page_range is kind of inefficient for page by page remapping.
+ *    But e.g. pte_alloc() does not work in modules ... :-(
+ */
+static int
+km_mmap(struct file *file, struct vm_area_struct *vma)
+{
+    via_device *via=(via_device *)file->private_data;
+#if 0
+    unsigned long start=(unsigned long) adr;
+    unsigned long page,pos;
+    int ret=0;
+
+    DBG_DD("via_v4l: mmap is called, size=0x%lx\n", size);
+    down(&via->lock);
+
+    if (size>via->dwVideoRambytes)
+        return -EINVAL;
+
+    pos=(unsigned long) lpPrimarySurface;
+    while (size > 0)
+    {
+        page = kvirt_to_pa(pos);
+        /* int remap_page_range(virt_add, phys_add, size, protection); */
+        if (remap_page_range(start, page, PAGE_SIZE, PAGE_SHARED))
+            return -EAGAIN;
+        start+=PAGE_SIZE;
+        pos+=PAGE_SIZE;
+        size-=PAGE_SIZE;
+    }
+#endif
+    up(&via->lock);
+
+    return 0;
+}
+
+static unsigned int km_poll(struct file *file, struct poll_table_struct *wait)
+{
+    return 0;
+}
+
+struct file_operations via_v4l2_fops = {
+        owner:          THIS_MODULE,
+        read:           km_read,
+        write:          km_write,
+        open:           km_open,
+        ioctl:          km_ioctl,
+        release:        km_close,
+        poll:           km_poll,
+	mmap:		km_mmap,
+};
+
+
+/*********************************************************************************/
+/*  irq-handler functions
+ */
+
+static irqreturn_t via_irq(int irq, void *dev_id, struct pt_regs *regs)
+{
+    via_device *via;
+    unsigned long Cap1_Masks_Temp;
+    unsigned long HQV_Control_Temp;
+    unsigned long V3_Control_Temp;
+    struct video_device *dev = dev_id;
+    
+    if (dev == NULL) 
+    {
+        DBG_DD ("IRQ %d for invalid device\n", irq);
+        return IRQ_NONE;
+    }
+
+//    DBG_DD("via_v4l: via_irq is called.\n");
+    via=&via_v4l_devices[1];    
+    Cap1_Masks_Temp = VIDInD(CAP1_MASKS);
+
+    if ( !(Cap1_Masks_Temp&CAP_END_OF_ACTIVE_VIDEO_FRAME_STATUS) ||
+         !(Cap1_Masks_Temp&END_OF_FRAME_INTERRUPT_MASK_ENABLE) )
+    {
+//    	DBG_DD ("Not via_v4l Capture 1 interrupt!\n");
+        return IRQ_NONE;
+    }                      
+    else               // Is our interrupt  // Reg304[0]==1 & Reg304[8]==1 Cap1 finish writing a buffer
+    {
+      if(gVIAGraphicInfo.Cap1_UseIRQ)       // Capture 1 use IRQ, for Cap1 S/W flip
+      {
+    	DBG_DD("via_v4l: via_irq: Cap1 finish writing a buffer.\n");
+    	DBG_DD("via_v4l: via_irq: Cap1 Mask = 0x%lx.\n", Cap1_Masks_Temp);
+    	
+    	via->interrupt_count++;
+        DBG_DD("via_v4l: via_irq: interrupt_count = %ld\n", via->interrupt_count);
+    	
+    	VIDOutD(CAP1_MASKS, Cap1_Masks_Temp | CAP_END_OF_ACTIVE_VIDEO_FRAME_STATUS);    // end Cap1 interrupt
+    	
+        if ((gdwVideoFlagMPEG & VIDEO_HQV_INUSE) || (gdwVideoFlagTV0 & VIDEO_HQV_INUSE))    // Cap1 can not use HQV
+        {
+            DBG_DD("via_v4l: via_irq: Cap1 can not use HQV.\n");
+            
+            if ( Cap1_Masks_Temp&CAP_WORKING_FRAME_STATUS )         // Cap1 now working on buffer 1
+    	    {
+    	        DBG_DD("via_v4l: via_irq: Cap1 now working on buffer 1.\n");
+    	        DBG_DD("via_v4l: via_irq: V3Address0_Switch = %d.\n", V3Address0_Switch);
+    	    
+    	        if (V3Address0_Switch)
+    	        {
+    	            DBG_DD("via_v4l: via_irq: Switch Cap1 buffer 0 to CAP1 Physical buffer 2.\n");
+    	            VIDOutD(CAP1_FB_STARTADDR0,CAPDevice[1].dwCAPPhysicalAddr[2]);
+    	    
+    	            if ( !(VIDInD(V_FLIP_STATUS)&V3_STARTADDR_UPDSTATUS) )
+    	            {
+    	                V3_Control_Temp = VIDInD(V3_CONTROL)&~V3_FLIP_HW_CAPTURE1;
+    	                V3_Control_Temp = V3_Control_Temp|V3_BOB_ENABLE|V3_SWAP_SW;
+    	                VIDOutD(V3_CONTROL, V3_Control_Temp);
+    	                DBG_DD("via_v4l: via_irq: 2A0 = 0x%lx.\n", V3_Control_Temp);
+    	                DBG_DD("via_v4l: via_irq: Flip buffer 0.\n");
+    	        
+    	                if (Cap1_Masks_Temp&CAP_FIELD_STATUS)
+    	                {    
+    	                   VIDOutD(V3_STARTADDR_0, (CAPDevice[1].dwCAPPhysicalAddr[0]|PLAY_ODD_FIELD));
+//    	                   V3_Control_Temp = V3_Control_Temp|V3_BOB_ENABLE|V3_SWAP_SW;
+//    	                   VIDOutD(V3_CONTROL, V3_Control_Temp);
+//    	                   DBG_DD("via_v4l: via_irq: 2A0 = 0x%lx.\n", V3_Control_Temp);
+    	                }
+    	                else
+    	                {
+    	                    VIDOutD(V3_STARTADDR_0, (CAPDevice[1].dwCAPPhysicalAddr[0]&~PLAY_ODD_FIELD));
+    	                }
+    	            }
+    	            VIDOutD(V_COMPOSE_MODE, (VIDInD(V_COMPOSE_MODE)|V3_COMMAND_FIRE));
+    	            V3Address0_Switch = FALSE;
+    	        }
+    	        else 
+    	        {
+    	    	    DBG_DD("via_v4l: via_irq: Switch Cap1 buffer 0 to CAP1 Physical buffer 0.\n");
+    	    	    VIDOutD(CAP1_FB_STARTADDR0,CAPDevice[1].dwCAPPhysicalAddr[0]);
+    	    
+    	            if ( !(VIDInD(V_FLIP_STATUS)&V3_STARTADDR_UPDSTATUS) )
+    	            {
+    	                V3_Control_Temp = VIDInD(V3_CONTROL)&~V3_FLIP_HW_CAPTURE1;
+    	                V3_Control_Temp = V3_Control_Temp|V3_BOB_ENABLE|V3_SWAP_SW;
+    	                VIDOutD(V3_CONTROL, V3_Control_Temp);
+    	                DBG_DD("via_v4l: via_irq: 2A0 = 0x%lx.\n", V3_Control_Temp);
+    	                DBG_DD("via_v4l: via_irq: Flip buffer 2.\n");
+    	        
+    	                if (Cap1_Masks_Temp&CAP_FIELD_STATUS)
+    	                {    
+    	                   VIDOutD(V3_STARTADDR_0, (CAPDevice[1].dwCAPPhysicalAddr[2]|PLAY_ODD_FIELD));
+    	                   //DBG_DD("via_v4l: via_irq: 3D0 = 0x%lx.\n", HQV_Control_Temp);
+    	                }
+    	                else
+    	                {
+    	                    VIDOutD(V3_STARTADDR_0, (CAPDevice[1].dwCAPPhysicalAddr[2]&~PLAY_ODD_FIELD));
+    	                    //DBG_DD("via_v4l: via_irq: 3D0 = 0x%lx.\n", HQV_Control_Temp);
+    	                }
+    	            }
+    	            VIDOutD(V_COMPOSE_MODE, (VIDInD(V_COMPOSE_MODE)|V3_COMMAND_FIRE));
+    	            V3Address0_Switch = TRUE;
+    	        }
+    	    }
+    	    else          // Cap1 now working on buffer 0
+    	    {
+    	        DBG_DD("via_v4l: via_irq: Cap1 now working on buffer 0.\n");
+    	        DBG_DD("via_v4l: via_irq: V3Address1_Switch = %d.\n", V3Address1_Switch);
+    	    
+    	        if (V3Address1_Switch)
+    	        {
+    	            DBG_DD("via_v4l: via_irq: Switch Cap1 buffer 1 to CAP1 Physical buffer 3.\n");
+    	            VIDOutD(CAP1_FB_STARTADDR1,CAPDevice[1].dwCAPPhysicalAddr[3]);
+    	    
+    	            if ( !(VIDInD(V_FLIP_STATUS)&V3_STARTADDR_UPDSTATUS) )
+    	            {
+    	                V3_Control_Temp = VIDInD(V3_CONTROL)&~V3_FLIP_HW_CAPTURE1;
+    	                V3_Control_Temp = V3_Control_Temp|V3_BOB_ENABLE|V3_SWAP_SW;
+    	                VIDOutD(V3_CONTROL, V3_Control_Temp);
+    	                DBG_DD("via_v4l: via_irq: 2A0 = 0x%lx.\n", V3_Control_Temp);
+    	                DBG_DD("via_v4l: via_irq: Flip buffer 1.\n");
+    	        
+    	                if (Cap1_Masks_Temp&CAP_FIELD_STATUS)
+    	                {    
+    	                   VIDOutD(V3_STARTADDR_0, (CAPDevice[1].dwCAPPhysicalAddr[1]|PLAY_ODD_FIELD));
+    	                   //DBG_DD("via_v4l: via_irq: 3D0 = 0x%lx.\n", HQV_Control_Temp);
+    	                }
+    	                else
+    	                {
+    	                    VIDOutD(V3_STARTADDR_0, (CAPDevice[1].dwCAPPhysicalAddr[1]&~PLAY_ODD_FIELD));
+    	                    //DBG_DD("via_v4l: via_irq: 3D0 = 0x%lx.\n", HQV_Control_Temp);
+    	                }
+    	            }
+    	            VIDOutD(V_COMPOSE_MODE, (VIDInD(V_COMPOSE_MODE)|V3_COMMAND_FIRE));
+    	            V3Address1_Switch = FALSE;
+    	        }
+    	        else 
+    	        {
+    	    	    DBG_DD("via_v4l: via_irq: Switch Cap1 buffer 1 to CAP1 Physical buffer 1.\n");
+    	    	    VIDOutD(CAP1_FB_STARTADDR1,CAPDevice[1].dwCAPPhysicalAddr[1]);
+    	    
+    	            if ( !(VIDInD(V_FLIP_STATUS)&V3_STARTADDR_UPDSTATUS) )
+    	            {
+    	                V3_Control_Temp = VIDInD(V3_CONTROL)&~V3_FLIP_HW_CAPTURE1;
+    	                V3_Control_Temp = V3_Control_Temp|V3_BOB_ENABLE|V3_SWAP_SW;
+    	                VIDOutD(V3_CONTROL, V3_Control_Temp);
+    	                DBG_DD("via_v4l: via_irq: 2A0 = 0x%lx.\n", V3_Control_Temp);
+    	                DBG_DD("via_v4l: via_irq: Flip buffer 3.\n");
+    	        
+    	                if (Cap1_Masks_Temp&CAP_FIELD_STATUS)
+    	                {    
+    	                   VIDOutD(V3_STARTADDR_0, (CAPDevice[1].dwCAPPhysicalAddr[3]|PLAY_ODD_FIELD));
+    	                   //DBG_DD("via_v4l: via_irq: 3D0 = 0x%lx.\n", HQV_Control_Temp);
+    	                }
+    	                else
+    	                {
+    	                    VIDOutD(V3_STARTADDR_0, (CAPDevice[1].dwCAPPhysicalAddr[3]&~PLAY_ODD_FIELD));
+    	                    //DBG_DD("via_v4l: via_irq: 3D0 = 0x%lx.\n", HQV_Control_Temp);
+    	                }
+    	            }
+    	            VIDOutD(V_COMPOSE_MODE, (VIDInD(V_COMPOSE_MODE)|V3_COMMAND_FIRE));
+    	            V3Address1_Switch = TRUE;
+    	        }
+    	    }
+        }
+        
+        else          // Cap1 can use HQV
+        {
+    	    DBG_DD("via_v4l: via_irq: Cap1 can use HQV.\n");
+    	    
+    	    if ( Cap1_Masks_Temp&CAP_WORKING_FRAME_STATUS )         // Cap1 now working on buffer 1
+    	    {
+    	        DBG_DD("via_v4l: via_irq: Cap1 now working on buffer 1.\n");
+    	        DBG_DD("via_v4l: via_irq: Address0_Switch = %d.\n", Address0_Switch);
+    	    
+    	        if (Address0_Switch)
+    	        {
+    	            DBG_DD("via_v4l: via_irq: Switch Cap1 buffer 0 to CAP1 Physical buffer 2.\n");
+    	            VIDOutD(CAP1_FB_STARTADDR0,CAPDevice[1].dwCAPPhysicalAddr[2]);
+    	    
+    	            if ( !(VIDInD(HQV_CONTROL)&HQV_SW_FLIP) )
+    	            {
+    	                HQV_Control_Temp = (VIDInD(HQV_CONTROL)&~HQV_FLIP_ODD);
+    	                DBG_DD("via_v4l: via_irq: Flip buffer 0.\n");
+    	                VIDOutD(HQV_SRC_STARTADDR_Y, CAPDevice[1].dwCAPPhysicalAddr[0]);
+    	        
+    	                if (Cap1_Masks_Temp&CAP_FIELD_STATUS)
+    	                {    
+    	                   HQV_Control_Temp = HQV_Control_Temp|HQV_FLIP_ODD|HQV_SW_FLIP;
+    	                   VIDOutD(HQV_CONTROL, HQV_Control_Temp);
+    	                   DBG_DD("via_v4l: via_irq: 3D0 = 0x%lx.\n", HQV_Control_Temp);
+    	                }
+    	                else
+    	                {
+    	                    HQV_Control_Temp = HQV_Control_Temp|HQV_FLIP_EVEN|HQV_SW_FLIP;
+    	                    VIDOutD(HQV_CONTROL, HQV_Control_Temp);
+    	                    DBG_DD("via_v4l: via_irq: 3D0 = 0x%lx.\n", HQV_Control_Temp);
+    	                }
+    	            }
+    	            Address0_Switch = FALSE;
+    	        }
+    	        else 
+    	        {
+    	    	    DBG_DD("via_v4l: via_irq: Switch Cap1 buffer 0 to CAP1 Physical buffer 0.\n");
+    	    	    VIDOutD(CAP1_FB_STARTADDR0,CAPDevice[1].dwCAPPhysicalAddr[0]);
+    	    
+    	            if ( !(VIDInD(HQV_CONTROL)&HQV_SW_FLIP) )
+    	            {
+    	                HQV_Control_Temp = (VIDInD(HQV_CONTROL)&~HQV_FLIP_ODD);
+    	                DBG_DD("via_v4l: via_irq: Flip buffer 2.\n");
+    	                VIDOutD(HQV_SRC_STARTADDR_Y, CAPDevice[1].dwCAPPhysicalAddr[2]);
+    	        
+    	                if (Cap1_Masks_Temp&CAP_FIELD_STATUS)
+    	                {
+    	                    HQV_Control_Temp = HQV_Control_Temp|HQV_FLIP_ODD|HQV_SW_FLIP;
+    	                    VIDOutD(HQV_CONTROL, HQV_Control_Temp);
+    	                    DBG_DD("via_v4l: via_irq: 3D0 = 0x%lx.\n", HQV_Control_Temp);
+    	                }
+    	                else
+    	                {
+    	                    HQV_Control_Temp = HQV_Control_Temp|HQV_FLIP_EVEN|HQV_SW_FLIP;
+    	                    VIDOutD(HQV_CONTROL, HQV_Control_Temp);
+    	                    DBG_DD("via_v4l: via_irq: 3D0 = 0x%lx.\n", HQV_Control_Temp);
+    	                }
+    	            }
+    	            Address0_Switch = TRUE;
+    	        }
+    	    }
+    	    else          // Cap1 now working on buffer 0
+    	    {
+    	        DBG_DD("via_v4l: via_irq: Cap1 now working on buffer 0.\n");
+    	        DBG_DD("via_v4l: via_irq: Address1_Switch = %d.\n", Address1_Switch);
+    	    
+    	        if (Address1_Switch)
+    	        {
+    	            DBG_DD("via_v4l: via_irq: Switch Cap1 buffer 1 to CAP1 Physical buffer 3.\n");
+    	            VIDOutD(CAP1_FB_STARTADDR1,CAPDevice[1].dwCAPPhysicalAddr[3]);
+    	    
+    	            if ( !(VIDInD(HQV_CONTROL)&HQV_SW_FLIP) )
+    	            {
+        	        HQV_Control_Temp = (VIDInD(HQV_CONTROL)&~HQV_FLIP_ODD);
+    	                DBG_DD("via_v4l: via_irq: Flip buffer 1.\n");
+    	                VIDOutD(HQV_SRC_STARTADDR_Y, CAPDevice[1].dwCAPPhysicalAddr[1]);
+    	        
+    	                if (Cap1_Masks_Temp&CAP_FIELD_STATUS)
+    	                {
+    	                    HQV_Control_Temp = HQV_Control_Temp|HQV_FLIP_ODD|HQV_SW_FLIP;
+    	                    VIDOutD(HQV_CONTROL, HQV_Control_Temp);
+    	                    DBG_DD("via_v4l: via_irq: 3D0 = 0x%lx.\n", HQV_Control_Temp);
+    	                }
+    	                else
+    	                {
+    	                    HQV_Control_Temp = HQV_Control_Temp|HQV_FLIP_EVEN|HQV_SW_FLIP;
+    	                    VIDOutD(HQV_CONTROL, HQV_Control_Temp);
+    	                    DBG_DD("via_v4l: via_irq: 3D0 = 0x%lx.\n", HQV_Control_Temp);
+    	                }
+    	            }
+    	            Address1_Switch = FALSE;
+    	        }
+    	        else 
+    	        {
+    	    	    DBG_DD("via_v4l: via_irq: Switch Cap1 buffer 1 to CAP1 Physical buffer 1.\n");
+    	    	    VIDOutD(CAP1_FB_STARTADDR1,CAPDevice[1].dwCAPPhysicalAddr[1]);
+    	    
+    	            if ( !(VIDInD(HQV_CONTROL)&HQV_SW_FLIP) )
+    	            {
+    	                HQV_Control_Temp = (VIDInD(HQV_CONTROL)&~HQV_FLIP_ODD);
+    	                DBG_DD("via_v4l: via_irq: Flip buffer 3.\n");
+    	                VIDOutD(HQV_SRC_STARTADDR_Y, CAPDevice[1].dwCAPPhysicalAddr[3]);
+    	        
+    	                if (Cap1_Masks_Temp&CAP_FIELD_STATUS)
+    	                {
+    	                    HQV_Control_Temp = HQV_Control_Temp|HQV_FLIP_ODD|HQV_SW_FLIP;
+    	                    VIDOutD(HQV_CONTROL, HQV_Control_Temp);
+    	                    DBG_DD("via_v4l: via_irq: 3D0 = 0x%lx.\n", HQV_Control_Temp);
+    	                }
+    	                else
+    	                {
+    	                    HQV_Control_Temp = HQV_Control_Temp|HQV_FLIP_EVEN|HQV_SW_FLIP;
+    	                    VIDOutD(HQV_CONTROL, HQV_Control_Temp);
+    	                    DBG_DD("via_v4l: via_irq: 3D0 = 0x%lx.\n", HQV_Control_Temp);
+    	                }
+    	            }
+    	            Address1_Switch = TRUE;
+    	        }
+    	    }
+    	}
+      }
+      else
+      {
+      	  VIDOutD(CAP1_MASKS, Cap1_Masks_Temp | CAP_END_OF_ACTIVE_VIDEO_FRAME_STATUS);    // end Cap1 interrupt
+      	  DBG_DD("via_v4l: via_irq: Capture 1 use H/W auto flip.\n");
+      }
+    }
+        
+    return IRQ_HANDLED;
+    
+    
+#if 0
+    while(1){
+    /*  DBG_DD("beep %ld\n", via->interrupt_count); */
+        if(!rage128_is_capture_irq_active(via)){
+            status=readl(via->reg_aperture+RAGE128_GEN_INT_STATUS);
+            mask=readl(via->reg_aperture+RAGE128_GEN_INT_CNTL);
+            if(!(status & mask))return;
+            rage128_wait_for_idle(via);
+            if(status & (1<<16))acknowledge_dma(via);
+            writel(status & mask, via->reg_aperture+RAGE128_GEN_INT_STATUS);
+            count--;
+            if(count<0){
+                DBG_DD(KERN_ERR "Kmultimedia: IRQ %d locked up, disabling interrupts in the hardware\n", via->dev->irq);
+                writel(0, via->reg_aperture+RAGE128_GEN_INT_STATUS);
+            }
+        }
+    }
+#endif
+}
+
+
+static struct video_device via_template=
+{
+        owner:          THIS_MODULE,
+        name:           "via_v4l",
+        type:           VID_TYPE_CAPTURE|VID_TYPE_OVERLAY|VID_TYPE_TELETEXT|\
+                        VID_TYPE_SCALES|VID_TYPE_CLIPPING,
+        hardware:       VID_HARDWARE_BT848,
+        fops:           &via_v4l2_fops,
+        minor:          -1,
+};
+
+static struct video_device *vdev_init(via_device *via,
+				      struct video_device *template,
+				      char *type)
+{
+	struct video_device *vfd;
+
+	vfd = video_device_alloc();
+	if (NULL == vfd)
+		return NULL;
+	*vfd = *template;
+	vfd->minor   = -1;
+	vfd->dev     = &via->dev->dev;
+	vfd->release = video_device_release;
+	snprintf(vfd->name, sizeof(vfd->name), "CLE266 rev %d", via->revision);
+	return vfd;
+}
+
+
+/*********************************************************************************/
+/* Register v4l device function                                                  */
+
+#if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,5)
+# define do_video_register(dev,type,nr) video_register_device(dev,type)
+#else
+# define do_video_register(dev,type,nr) video_register_device(dev,type,nr)
+#endif
+
+static int __devinit init_via_video_dev(via_device *via)
+{
+    int j;
+
+    DBG_DD("via_v4l: init via_device\n");
+
+    init_MUTEX(&via->lock);
+
+    /* reset user count for this device */
+    via->user_count = 0;
+
+    /* init video status */
+    lpVideoControl->VideoStatus = VIDEO_NULL;
+    
+    // init via video capture parameter: picture & window
+    via->video_pic.colour = 0x40 << 8;
+    via->video_pic.brightness = 0x80 << 8;
+    via->video_pic.hue = 0x0 << 8;
+    via->video_pic.contrast = 0x47 << 8;
+    via->video_pic.whiteness = 32768;
+    via->video_pic.depth = 16;
+    via->video_pic.palette = VIDEO_PALETTE_YUV422;
+
+    via->video_win.x=10;
+    via->video_win.y=10;
+    via->video_win.width=720;
+    via->video_win.height=480;
+
+        /*if (via->video_dev->minor==0)*/
+/*        if (via->video_dev->minor==1)
+        {
+            if (gVIAGraphicInfo.Cap1_Deinterlace == VIA_DEINTERLACE_WEAVE)
+            {
+                via->CapInfo.dwDeinterlaceMode = VIA_DEINTERLACE_WEAVE;
+            }
+            else if (gVIAGraphicInfo.Cap1_Deinterlace == VIA_DEINTERLACE_BOB)
+            {
+                via->CapInfo.dwDeinterlaceMode = VIA_DEINTERLACE_BOB;
+            }
+        }
+        else
+        {
+            if (gVIAGraphicInfo.Cap0_Deinterlace == VIA_DEINTERLACE_WEAVE)
+            {
+                via->CapInfo.dwDeinterlaceMode = VIA_DEINTERLACE_WEAVE;
+            }
+            else if (gVIAGraphicInfo.Cap0_Deinterlace == VIA_DEINTERLACE_BOB)
+            {
+                via->CapInfo.dwDeinterlaceMode = VIA_DEINTERLACE_BOB;
+            }
+        }   
+*/
+        if (!(via->gbuf = kmalloc(sizeof(struct via_gbuf)*gbuffers,GFP_KERNEL)))
+                return -1;
+
+        for (j = 0; j < gbuffers; j++)
+        {
+                if (!(via->gbuf[j].risc = kmalloc(16384,GFP_KERNEL)))
+                        return -1;
+        }
+
+    via->video_dev = vdev_init(via, &via_template, "video");
+    if (NULL == via->video_dev)
+        return -1;
+    if (video_register_device(via->video_dev,VFL_TYPE_GRABBER,-1)<0)
+        return -1;
+    video_device_create_file(via->video_dev, &class_device_attr_card);
+
+    printk("via_v4l: registered video device (%d) corresponds to /dev/video%d\n", via->video_dev->minor, via->video_dev->minor);
+
+    return 0;
+}
+
+
+static void __devexit via_remove(struct pci_dev *pci_dev)
+{
+    int i;
+    via_device *via = pci_get_drvdata(pci_dev);
+
+    /* Disable video interrupt then free irq handler */
+    switch ( via->deviceID )
+    {
+        case VIA_DEVICE_VT3205:
+            break;
+
+        case VIA_DEVICE_CLE1:
+        case VIA_DEVICE_CLE2:
+            DisableInterrupt();
+            free_irq(via->dev->irq, via->video_dev);
+            break;
+
+        default:
+            break;
+    }
+
+    for (i=0;i<MAX_VIA_BOARDS;i++)
+    {
+        via = &via_v4l_devices[i];
+        if (via->video_dev) {
+	    if (-1 != via->video_dev->minor)
+	        video_unregister_device(via->video_dev);
+	    else
+	        video_device_release(via->video_dev);
+	    via->video_dev = NULL;
+            DBG_DD("via_v4l: Remove v4l device %d. interrupt_count=%ld\n",
+                  i, via->interrupt_count);
+	}
+    }
+    
+    iounmap(via->mem);
+    iounmap(lpPrimarySurface);
+    kfree(lpVideoControl);
+
+    /*
+    release_mem_region(pci_resource_start(pci_dev,1),
+                           pci_resource_len(pci_dev,1));
+    release_mem_region(pci_resource_start(pci_dev,0),
+                           pci_resource_len(pci_dev,0));
+    */
+    pci_set_drvdata(pci_dev, NULL);
+}
+
+
+static int __devinit via_probe(struct pci_dev *dev, const struct pci_device_id *pci_id)
+{
+    //int i, result;
+    via_device *via;
+    void *irq_handler=NULL;
+    int result=0;
+    //unsigned char bMemSize = 0;
+    struct pci_dev *dev2;
+
+    /* exceed the max. handled cards */
+    if (via_v4l_num > MAX_VIA_BOARDS)
+        return -ENOMEM;
+
+
+        /* Lock the mem-map IO region */
+        /*
+        if (!request_mem_region(pci_resource_start(dev, 1),
+                                pci_resource_len(dev, 1),
+                                "via_v4l")) {
+                return -EBUSY;
+        }
+
+        if (!request_mem_region(pci_resource_start(dev, 0),
+                                pci_resource_len(dev, 0),
+                                "via_v4l")) {
+                return -EBUSY;
+        }
+        */
+
+    /* Add struct initial codes */
+    memset(&MPGDevice, 0, sizeof(MPGDevice));
+    memset(&SUBDevice, 0, sizeof(SUBDevice));
+    memset(&SWDevice, 0, sizeof(SWDevice));
+    memset(&CAPDevice[0], 0, sizeof(CAPDevice[0]));
+    memset(&CAPDevice[1], 0, sizeof(CAPDevice[1]));
+    memset(&ALPDevice, 0, sizeof(ALPDevice));
+
+    /*  Setup 3 capture devices.
+     *  The 3rd capture device is for proprietary
+     *  and Xv path.
+     */
+    for (; via_v4l_num<MAX_VIA_BOARDS; via_v4l_num++)
+    {
+        via=&via_v4l_devices[via_v4l_num];
+        via->dev=dev;
+        via->interrupt_count=0;
+
+        //init_waitqueue_head(&(via->frameq));
+
+        if (via_v4l_num == 0)
+        {
+            if (pci_enable_device(dev) < 0) 
+            {
+                printk("via_v4l: Can't enable device.\n");
+                        return -EIO;
+            }
+        }
+
+        pci_read_config_word(dev, PCI_VENDOR_ID, &via->vendorID);
+        pci_read_config_word(dev, PCI_DEVICE_ID, &via->deviceID);
+        //pci_read_config_byte(dev, PCI_REVISION_ID, &via->revision);
+
+        /*  Kevin Huang [2003.09.30] The real revision ID is not exist in 0x08 of PCI
+         *  config space, H/W design hide it at bus:0, devicee:0, function:0
+         *  Host bridge: 1106:3123, index :0xF6
+         *
+         */
+	if ((dev2 = pci_find_slot(0, 0)))
+            pci_read_config_byte(dev2, 0xF6, &via->revision);
+        pci_read_config_word(dev, PCI_SUBSYSTEM_VENDOR_ID, &via->subvendorID);
+        pci_read_config_word(dev, PCI_SUBSYSTEM_ID, &via->subdeviceID);
+        printk("via_v4l: Device name:(%s), slot_name:%s (0x%04x:0x%04x) Revision:%d\n",
+                    dev->pretty_name, dev->slot_name, via->vendorID, via->deviceID, via->revision);
+
+        via->mb0 = pci_resource_start(dev, 0);  /* physical video memory base */
+        via->mb1 = pci_resource_start(dev, 1);  /* physical MMIO memory base */
+        DBG_DD("via_v4l: irq: %d, memory base address 0: 0x%lx\n, memory base address 1: 0x%lx\n",
+                via->dev->irq, via->mb0, via->mb1);
+
+        /* Only needs to do once */
+        if (via_v4l_num == 0)
+        {
+            lpVidMEMIO = ioremap(via->mb1, 0x400) + 0x200;
+            //lpVidMEMIO = (unsigned char *)kmalloc(4096, GFP_KERNEL);
+
+            /* init video control parameter */
+            lpVideoControl = kmalloc(sizeof(VIAVIDCTRL), GFP_KERNEL);
+            DBG_DD("via_v4l: lpVideoControl=0x%p\n", lpVideoControl);
+            memset(lpVideoControl,0,sizeof(VIAVIDCTRL));
+            lpVideoControl->PORTID = PORT1;
+            lpVideoControl->dwCompose = VW_TV1_TOP;
+            lpVideoControl->dwHighQVDO = VW_HIGHQVDO_OFF;
+
+        }
+
+        /* memory-map io for read/write register */
+        via->mem = (unsigned char *)lpVidMEMIO - 0x200;
+        DBG_DD("via_v4l: mem-map IO address: 0x%p, length = 0x%lx\n", via->mem, pci_resource_len(dev, 1));
+        if ( 0 == via->mem )
+        {
+            DBG_DD("via_v4l: cannot remap pci-address!\n");
+            return -ENODEV;
+        }
+
+        /* frame buffer physical base address */
+        via->video_buf.base = (void *)via->mb0;
+        DBG_DD("via_v4l: frame buffer physical base address: 0x%p\n", via->video_buf.base);
+
+        /* Only needs to do once */
+        if (via_v4l_num == 0)
+        {
+        pci_set_master(dev);
+        pci_set_drvdata(dev, via);
+        }
+
+        if(init_via_video_dev(via) < 0)
+        {
+            via_remove(dev);
+            return -EIO;
+        }
+
+        /* enable video interrupt & set irq handler */
+        switch ( via->deviceID )
+        {
+            case VIA_DEVICE_VT3205:
+                break;
+        
+            case VIA_DEVICE_CLE1:
+            case VIA_DEVICE_CLE2:
+                /* Only needs to do once */
+                if (via_v4l_num == 0)
+                {
+                    EnableInterrupt();
+                    irq_handler=via_irq;
+            
+                    result = request_irq(via->dev->irq, irq_handler,
+                                         SA_SHIRQ | SA_INTERRUPT,"via_v4l", via->video_dev);
+            
+                    if (result==-EINVAL)
+                    {
+                        DBG_DD(KERN_ERR "via_v4l: Bad irq number or handler\n");
+                    }
+                    if (result==-EBUSY)
+                    {
+                        DBG_DD(KERN_ERR "via_v4l: IRQ %d busy, change your PnP config in BIOS\n", via->dev->irq);
+                    }
+                    if (result < 0)
+                    {
+                         DBG_DD(KERN_ERR " Could not install irq handler...\n");
+                    }
+                }
+                break;
+            
+            default:
+                break;
+        }//End of DeviceID
+
+        DBG_DD("\n\n");
+    }
+
+    return 0;
+
+}
+
+
+
+
+static struct pci_device_id via_v4l_pci_tbl[] __devinitdata = {
+        /* via cards */
+        {0x1106, 0x3122,
+         PCI_ANY_ID, PCI_ANY_ID, },
+        {0x1106, 0x3022,
+         PCI_ANY_ID, PCI_ANY_ID, },
+        {0x1106, 0x7205,
+         PCI_ANY_ID, PCI_ANY_ID, },                 
+        {0,}
+};
+
+MODULE_DEVICE_TABLE(pci, via_v4l_pci_tbl);
+
+static struct pci_driver via_v4l_pci_driver = {
+        name:     "via_v4l",
+        id_table: via_v4l_pci_tbl,
+        probe:    via_probe,
+        remove:   via_remove,
+};
+
+
+#ifdef MODULE
+static int __init via_init_module(void)
+{
+    DBG_DD("via_v4l: v4l module loaded\n");
+    return pci_module_init(&via_v4l_pci_driver);
+}
+
+void via_cleanup_module(void)
+{
+    DBG_DD("via_v4l: v4l module cleanup.\n");
+    pci_unregister_driver(&via_v4l_pci_driver);
+    return;
+}
+
+module_init(via_init_module);
+module_exit(via_cleanup_module);
+
+#endif
diff -u -r -N --exclude='*.cmd' --exclude='*.o' --exclude='*.ko' --exclude='*.mod.c' linux-2.6.0/drivers/media/video/via_v4l.h linux-2.6.1-rc1-gentoo/drivers/media/video/via_v4l.h
--- linux-2.6.0/drivers/media/video/via_v4l.h	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.1-rc1-gentoo/drivers/media/video/via_v4l.h	2004-01-06 22:54:01.000000000 +0000
@@ -0,0 +1,154 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#ifndef __VIA_V4L_H__
+#define __VIA_V4L_H__
+
+#include <linux/videodev.h>
+#include <asm/io.h> 			 /* for accessing devices */
+#include "capture.h"
+
+
+#define MAX_VIA_BOARDS		3
+
+#define MAX_VIA_OPENS		5
+#define MAX_VIA_CAPTURE_BUFFERS	64
+
+struct via_gbuf {
+	int stat;
+#define GBUFFER_UNUSED       0
+#define GBUFFER_GRABBING     1
+#define GBUFFER_DONE         2
+#define GBUFFER_ERROR        3
+	struct timeval tv;
+	
+	u16 width;
+	u16 height;
+	u16 fmt;
+	
+	u32 *risc;
+	unsigned long ro;
+	unsigned long re;
+};
+
+typedef struct {
+	u32 from_addr;
+	u32 to_addr;
+	u32 command;
+	u32 reserved;
+	} bm_list_descriptor;
+
+typedef struct {
+	char *buffer;
+	long timestamp;
+	long buf_size;
+	long buf_ptr;
+	long buf_free;
+	int dma_active;
+	bm_list_descriptor *dma_table;
+	} SINGLE_FRAME;
+
+typedef struct _via_device{
+	struct video_device *video_dev;	
+	struct video_picture video_pic;
+	struct video_window video_win;
+	struct video_buffer video_buf;
+	struct video_channel video_chan;
+	struct video_capability video_cap;
+
+	int user_count;             /* Count how many user use the device */
+
+    struct semaphore lock;		/* for semaphore use */
+
+	struct pci_dev *dev;
+	unsigned short vendorID;		/* The chip vendor ID */
+	unsigned short deviceID;		/* The chip device ID */
+	unsigned char revision;		/* The chip revision ID */
+	unsigned short subvendorID;  /* The chip subsystem vendor ID */
+	unsigned short subdeviceID;	/* The chip subsystem device ID */
+
+	unsigned long mb0;      	/* PCI memory base 0 for GFX & video frame buffer */
+	unsigned long mb1;      	/* PCI memory base 1 for mem-map IO */
+	unsigned long color_key;
+	unsigned long freq;
+	unsigned char *mem;   		/* pointer to mapped IO memory */
+	wait_queue_head_t frameq;
+	unsigned long interrupt_count;
+	int nr;						// record the minor number 
+	int buf_read_from;			// read from frame 0 or 1
+	SINGLE_FRAME frame;			// frame 0 struct
+	SINGLE_FRAME frame_even;	// frame 1 struct
+	long total_frames;			// total read frames
+	long overrun;				// ??
+    VIACAPINFO  CapInfo;
+    VIAAUDCTRL  AudCtrl;
+	char *fbuffer;				/* Pointer to a allocated memory for km_mmap */
+	struct via_gbuf *gbuf;
+
+    unsigned long dwVideoRambytes;    /* video memory in unit of bytes */
+
+	} via_device;
+
+
+typedef struct {
+  unsigned long dwWidth;          /* On screen Width                  */
+  unsigned long dwHeight;         /* On screen Height                 */
+  unsigned long dwBPP;            /* Bits Per Pixel                   */
+  unsigned long dwRefreshRate;    /* Refresh rate of the mode         */
+}MODEINFO, * LPMODEINFO;
+
+#define SDR100  1
+#define SDR133  2
+#define DDR100  3
+#define DDR133  4
+
+
+/* Definition for VideoStatus */
+#define VIDEO_NULL              0x00000000
+#define TV0SURFACE_CREATED      0x00000001
+#define TV1SURFACE_CREATED      0x00000002
+#define SWOV_SURFACE_CREATED    0x00000004
+#define HW_MPEG_ON              0x00000010
+#define TV0_VIDEO_ON            0x00000020
+#define TV1_VIDEO_ON            0x00000040
+#define SW_VIDEO_ON             0x00000080
+#define CAP0_ON_SND             0x00000100
+#define CAP1_ON_SND             0x00000200
+#define MPEG_ON_SND             0x00000400
+
+#define COMMAND_FOR_TV0   0
+#define COMMAND_FOR_TV1   1
+#define COMMAND_FOR_OTHER 2
+
+/* debug options */
+#ifndef __VIA_V4L_C__
+extern int km_debug;
+#endif
+
+#define DBG_DD   if(km_debug) printk
+#define PrintMemLayOut   PrintFBMem
+
+void via_set_window(via_device *via);
+
+#endif
diff -u -r -N --exclude='*.o' linux-2.6.0/drivers/char/drm/Kconfig linux-2.6.0-gentoo/drivers/char/drm/Kconfig
--- linux-2.6.0/drivers/char/drm/Kconfig	2003-12-18 02:59:28.000000000 +0000
+++ linux-2.6.0-gentoo/drivers/char/drm/Kconfig	2003-12-22 17:50:28.000000000 +0000
@@ -81,3 +80,11 @@
           chipset. If M is selected the module will be called sis. AGP
           support is required for this driver to work.
 
+config DRM_VIA
+	tristate "VIA CLE266"
+	depends on DRM && AGP
+	help
+	  Choose this option if you have a VIA CLE266 or compatibel video 
+          chipset. If M is selected the module will be called via. AGP
+          support is required for this driver to work.
+
diff -u -r -N --exclude='*.o' linux-2.6.0/drivers/char/drm/Makefile linux-2.6.0-gentoo/drivers/char/drm/Makefile
--- linux-2.6.0/drivers/char/drm/Makefile	2003-12-18 02:59:42.000000000 +0000
+++ linux-2.6.0-gentoo/drivers/char/drm/Makefile	2003-12-22 17:52:04.000000000 +0000
@@ -11,6 +11,7 @@
 radeon-objs := radeon_drv.o radeon_cp.o radeon_state.o radeon_mem.o radeon_irq.o
 ffb-objs    := ffb_drv.o ffb_context.o
 sis-objs    := sis_drv.o sis_ds.o sis_mm.o
+via-objs    := via_drv.o via_ds.o via_map.o via_mm.o
 
 obj-$(CONFIG_DRM_GAMMA) += gamma.o
 obj-$(CONFIG_DRM_TDFX)	+= tdfx.o
@@ -21,4 +22,5 @@
 obj-$(CONFIG_DRM_I830)	+= i830.o
 obj-$(CONFIG_DRM_FFB)   += ffb.o
 obj-$(CONFIG_DRM_SIS)   += sis.o
+obj-$(CONFIG_DRM_VIA)   += via.o
 
diff -u -r -N --exclude='*.o' linux-2.6.0/drivers/char/drm/via.h linux-2.6.0-gentoo/drivers/char/drm/via.h
--- linux-2.6.0/drivers/char/drm/via.h	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.0-gentoo/drivers/char/drm/via.h	2003-12-22 17:54:30.000000000 +0000
@@ -0,0 +1,46 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+#ifndef __VIA_H__
+#define __VIA_H__
+
+
+#define DRM(x) viadrv_##x
+
+
+#define __HAVE_AGP		1
+#define __MUST_HAVE_AGP		0
+#define __HAVE_MTRR		1
+#define __HAVE_CTX_BITMAP	1
+
+
+#define DRIVER_AGP_BUFFERS_MAP( dev )					\
+	((drm_via_private_t *)((dev)->dev_private))->buffers
+
+extern int via_init_context(int context);
+extern int via_final_context(int context);
+
+#define DRIVER_CTX_CTOR via_init_context
+#define DRIVER_CTX_DTOR via_final_context
+
+#endif
diff -u -r -N --exclude='*.o' linux-2.6.0/drivers/char/drm/via_drm.h linux-2.6.0-gentoo/drivers/char/drm/via_drm.h
--- linux-2.6.0/drivers/char/drm/via_drm.h	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.0-gentoo/drivers/char/drm/via_drm.h	2003-12-22 17:54:30.000000000 +0000
@@ -0,0 +1,156 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+#ifndef _VIA_DRM_H_
+#define _VIA_DRM_H_
+
+/* WARNING: These defines must be the same as what the Xserver uses.
+ * if you change them, you must change the defines in the Xserver.
+ */
+
+#ifndef _VIA_DEFINES_
+#define _VIA_DEFINES_
+
+#define VIA_DMA_BUF_ORDER		12
+#define VIA_DMA_BUF_SZ 		        (1 << VIA_DMA_BUF_ORDER)
+#define VIA_DMA_BUF_NR 			256
+#define VIA_NR_SAREA_CLIPRECTS 		8
+
+/* Each region is a minimum of 64k, and there are at most 64 of them.
+ */
+#define VIA_NR_TEX_REGIONS 64
+#define VIA_LOG_MIN_TEX_REGION_SIZE 16
+#endif
+
+#define VIA_UPLOAD_TEX0IMAGE  0x1 /* handled clientside */
+#define VIA_UPLOAD_TEX1IMAGE  0x2 /* handled clientside */
+#define VIA_UPLOAD_CTX        0x4
+#define VIA_UPLOAD_BUFFERS    0x8
+#define VIA_UPLOAD_TEX0       0x10
+#define VIA_UPLOAD_TEX1       0x20
+#define VIA_UPLOAD_CLIPRECTS  0x40
+#define VIA_UPLOAD_ALL        0xff
+
+/* VIA specific ioctls */
+#define DRM_IOCTL_VIA_ALLOCMEM	DRM_IOWR(0x40, drm_via_mem_t)
+#define DRM_IOCTL_VIA_FREEMEM	DRM_IOW(0x41, drm_via_mem_t)
+#define DRM_IOCTL_VIA_AGP_INIT	DRM_IOWR(0x42, drm_via_agp_t)
+#define DRM_IOCTL_VIA_FB_INIT	DRM_IOWR(0x43, drm_via_fb_t)
+#define DRM_IOCTL_VIA_MAP_INIT	DRM_IOWR(0x44, drm_via_init_t)
+
+/* Indices into buf.Setup where various bits of state are mirrored per
+ * context and per buffer.  These can be fired at the card as a unit,
+ * or in a piecewise fashion as required.
+ */
+ 
+#define VIA_TEX_SETUP_SIZE 8
+
+/* Flags for clear ioctl
+ */
+#define VIA_FRONT   0x1
+#define VIA_BACK    0x2
+#define VIA_DEPTH   0x4
+#define VIA_STENCIL 0x8
+#define VIDEO 0
+#define AGP 1
+
+typedef struct {
+	unsigned int offset;
+	unsigned int size;
+} drm_via_agp_t;    
+
+typedef struct {
+	unsigned int offset;
+	unsigned int size;
+} drm_via_fb_t;    
+
+typedef struct {
+	unsigned int context;
+	unsigned int type;
+	unsigned int size;
+	unsigned long index;
+	unsigned long offset;
+} drm_via_mem_t;    
+
+typedef struct _drm_via_init {
+	enum {
+		VIA_INIT_MAP = 0x01,
+		VIA_CLEANUP_MAP = 0x02
+	} func;
+
+	unsigned long sarea_priv_offset;
+	unsigned long fb_offset;
+	unsigned long mmio_offset;
+	unsigned long agpAddr;
+} drm_via_init_t;
+
+/* Warning: If you change the SAREA structure you must change the Xserver
+ * structure as well */
+
+typedef struct _drm_via_tex_region {
+	unsigned char next, prev;	/* indices to form a circular LRU  */
+	unsigned char inUse;		/* owned by a client, or free? */
+	int age;			/* tracked by clients to update local LRU's */
+} drm_via_tex_region_t;
+
+typedef struct _drm_via_sarea {
+	unsigned int dirty;
+	unsigned int nbox;
+	drm_clip_rect_t boxes[VIA_NR_SAREA_CLIPRECTS];   
+	drm_via_tex_region_t texList[VIA_NR_TEX_REGIONS + 1]; 
+	int texAge;		/* last time texture was uploaded */
+	int ctxOwner;		/* last context to upload state */
+	int vertexPrim;
+} drm_via_sarea_t;
+
+typedef struct _drm_via_flush_agp {
+	unsigned int offset;
+	unsigned int size;
+	unsigned int index;		
+	int discard;	/* client is finished with the buffer? */
+} drm_via_flush_agp_t;
+
+typedef struct _drm_via_flush_sys {
+	unsigned int offset;
+	unsigned int size;
+	unsigned long index;		
+	int discard;	/* client is finished with the buffer? */
+} drm_via_flush_sys_t;
+
+#ifdef __KERNEL__
+int via_fb_init(struct inode *inode, struct file *filp, unsigned int cmd,
+		unsigned long arg);		
+int via_mem_alloc(struct inode *inode, struct file *filp, unsigned int cmd,
+  		unsigned long arg);				
+int via_mem_free(struct inode *inode, struct file *filp, unsigned int cmd,
+		unsigned long arg);		
+int via_agp_init(struct inode *inode, struct file *filp, unsigned int cmd,
+		unsigned long arg);				
+int via_dma_alloc(struct inode *inode, struct file *filp, unsigned int cmd,
+		unsigned long arg);				
+int via_dma_free(struct inode *inode, struct file *filp, unsigned int cmd,
+		unsigned long arg);				
+int via_map_init(struct inode *inode, struct file *filp, unsigned int cmd,
+		unsigned long arg);				
+#endif
+#endif /* _VIA_DRM_H_ */
diff -u -r -N --exclude='*.o' linux-2.6.0/drivers/char/drm/via_drv.c linux-2.6.0-gentoo/drivers/char/drm/via_drv.c
--- linux-2.6.0/drivers/char/drm/via_drv.c	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.0-gentoo/drivers/char/drm/via_drv.c	2003-12-26 22:59:17.000000000 +0000
@@ -0,0 +1,66 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+#include <linux/config.h>
+#include "via.h"
+#include "drmP.h"
+#include "via_drm.h"
+#include "via_drv.h"
+
+#define DRIVER_AUTHOR	"VIA"
+
+#define DRIVER_NAME		"via"
+#define DRIVER_DESC		"VIA CLE 266"
+#define DRIVER_DATE		"20020814"
+
+#define DRIVER_MAJOR		1
+#define DRIVER_MINOR		1
+#define DRIVER_PATCHLEVEL	0
+
+
+#define DRIVER_IOCTLS \
+        [DRM_IOCTL_NR(DRM_IOCTL_VIA_ALLOCMEM)]  = { via_mem_alloc, 1, 0 }, \
+        [DRM_IOCTL_NR(DRM_IOCTL_VIA_FREEMEM)]   = { via_mem_free,  1, 0 }, \
+        [DRM_IOCTL_NR(DRM_IOCTL_VIA_AGP_INIT)]  = { via_agp_init,  1, 0 }, \
+	[DRM_IOCTL_NR(DRM_IOCTL_VIA_FB_INIT)]   = { via_fb_init,   1, 0 }, \
+        [DRM_IOCTL_NR(DRM_IOCTL_VIA_MAP_INIT)]  = { via_map_init,  1, 0 }
+
+
+#define __HAVE_COUNTERS		0
+
+#include "drm_auth.h"
+#include "drm_agpsupport.h"
+#include "drm_bufs.h"
+#include "drm_context.h"
+#include "drm_dma.h"
+#include "drm_drawable.h"
+#include "drm_drv.h"
+#include "drm_fops.h"
+#include "drm_init.h"
+#include "drm_ioctl.h"
+/*NMGRILO  #include "drm_lists.h" */
+#include "drm_lock.h"
+#include "drm_memory.h"
+#include "drm_proc.h"
+#include "drm_vm.h"
+#include "drm_stub.h"
diff -u -r -N --exclude='*.o' linux-2.6.0/drivers/char/drm/via_drv.h linux-2.6.0-gentoo/drivers/char/drm/via_drv.h
--- linux-2.6.0/drivers/char/drm/via_drv.h	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.0-gentoo/drivers/char/drm/via_drv.h	2003-12-22 17:54:30.000000000 +0000
@@ -0,0 +1,149 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+#ifndef _VIA_DRV_H_
+#define _VIA_DRV_H_
+
+typedef struct drm_via_private {
+	drm_via_sarea_t *sarea_priv;
+	drm_map_t *sarea;
+	drm_map_t *fb;
+	drm_map_t *mmio;
+	unsigned long agpAddr;
+} drm_via_private_t;
+
+extern int via_do_init_map(drm_device_t *dev, drm_via_init_t *init);
+extern int via_do_cleanup_map(drm_device_t *dev);
+extern int via_map_init(struct inode *inode, struct file *filp,
+		   unsigned int cmd, unsigned long arg);
+
+/*=* [DBG] For RedHat7.3 insert kernel module has unresolved symbol
+   cmpxchg() *=*/
+
+/* Include this here so that driver can be used with older kernels. */
+#ifndef __HAVE_ARCH_CMPXCHG 
+
+#ifdef CONFIG_SMP
+#define LOCK_PREFIX "lock ; "
+#else
+#define LOCK_PREFIX ""
+#endif		
+
+#if defined(__alpha__)
+static __inline__ unsigned long
+__cmpxchg_u32(volatile int *m, int old, int new)
+{
+	unsigned long prev, cmp;
+
+	__asm__ __volatile__(
+	"1:	ldl_l %0,%2\n"
+	"	cmpeq %0,%3,%1\n"
+	"	beq %1,2f\n"
+	"	mov %4,%1\n"
+	"	stl_c %1,%2\n"
+	"	beq %1,3f\n"
+	"2:	mb\n"
+	".subsection 2\n"
+	"3:	br 1b\n"
+	".previous"
+	: "=&r"(prev), "=&r"(cmp), "=m"(*m)
+	: "r"((long) old), "r"(new), "m"(*m));
+
+	return prev;
+}
+
+static __inline__ unsigned long
+__cmpxchg_u64(volatile long *m, unsigned long old, unsigned long new)
+{
+	unsigned long prev, cmp;
+
+	__asm__ __volatile__(
+	"1:	ldq_l %0,%2\n"
+	"	cmpeq %0,%3,%1\n"
+	"	beq %1,2f\n"
+	"	mov %4,%1\n"
+	"	stq_c %1,%2\n"
+	"	beq %1,3f\n"
+	"2:	mb\n"
+	".subsection 2\n"
+	"3:	br 1b\n"
+	".previous"
+	: "=&r"(prev), "=&r"(cmp), "=m"(*m)
+	: "r"((long) old), "r"(new), "m"(*m));
+
+	return prev;
+}
+
+static __inline__ unsigned long
+__cmpxchg(volatile void *ptr, unsigned long old, unsigned long new, int size)
+{
+	switch (size) {
+		case 4:
+			return __cmpxchg_u32(ptr, old, new);
+		case 8:
+			return __cmpxchg_u64(ptr, old, new);
+	}
+	return old;
+}
+#define cmpxchg(ptr,o,n)						 \
+  ({									 \
+     __typeof__(*(ptr)) _o_ = (o);					 \
+     __typeof__(*(ptr)) _n_ = (n);					 \
+     (__typeof__(*(ptr))) __cmpxchg((ptr), (unsigned long)_o_,		 \
+				    (unsigned long)_n_, sizeof(*(ptr))); \
+  })
+
+#elif __i386__
+static inline unsigned long __cmpxchg(volatile void *ptr, unsigned long old,
+				      unsigned long new, int size)
+{
+	unsigned long prev;
+	switch (size) {
+	case 1:
+		__asm__ __volatile__(LOCK_PREFIX "cmpxchgb %b1,%2"
+				     : "=a"(prev)
+				     : "q"(new), "m"(*__xg(ptr)), "0"(old)
+				     : "memory");
+		return prev;
+	case 2:
+		__asm__ __volatile__(LOCK_PREFIX "cmpxchgw %w1,%2"
+				     : "=a"(prev)
+				     : "q"(new), "m"(*__xg(ptr)), "0"(old)
+				     : "memory");
+		return prev;
+	case 4:
+		__asm__ __volatile__(LOCK_PREFIX "cmpxchgl %1,%2"
+				     : "=a"(prev)
+				     : "q"(new), "m"(*__xg(ptr)), "0"(old)
+				     : "memory");
+		return prev;
+	}
+	return old;
+}
+
+#define cmpxchg(ptr,o,n)						\
+  ((__typeof__(*(ptr)))__cmpxchg((ptr),(unsigned long)(o),		\
+				 (unsigned long)(n),sizeof(*(ptr))))
+#endif /* i386 & alpha */
+#endif
+#endif
diff -u -r -N --exclude='*.o' linux-2.6.0/drivers/char/drm/via_ds.c linux-2.6.0-gentoo/drivers/char/drm/via_ds.c
--- linux-2.6.0/drivers/char/drm/via_ds.c	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.0-gentoo/drivers/char/drm/via_ds.c	2003-12-22 17:54:34.000000000 +0000
@@ -0,0 +1,395 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ *
+ * Fixes:
+ *	Changed to use via_ prefixes on globals
+ *	Fixed malloc failure paths
+ *	Reformatted to Linux style
+ *	Removed ITEM_TYPE typedef, FREE/MALLOC and other macro bits
+ */
+
+#define __NO_VERSION__
+#include <linux/module.h>
+#include <linux/delay.h>
+#include <linux/errno.h>
+#include <linux/kernel.h>
+#include <linux/slab.h>
+#include <linux/poll.h>
+#include <asm/io.h>
+#include <linux/pci.h>
+
+#include "via_ds.h"
+
+#warning "Fix variable/global names to use via_"
+
+extern unsigned int VIA_DEBUG;
+
+set_t *via_set_init(void)
+{
+	int i;
+	set_t *set;
+	set = (set_t *)kmalloc(sizeof(set_t), GFP_KERNEL);
+	if(set == NULL)
+		return NULL;
+	for (i = 0; i < SET_SIZE; i++) {
+		set->list[i].free_next = i + 1;
+		set->list[i].alloc_next = -1;
+	}
+	set->list[SET_SIZE - 1].free_next = -1;
+	set->free = 0;
+	set->alloc = -1;
+	set->trace = -1;
+	return set;
+}
+
+int via_set_add(set_t * set, unsigned int item)
+{
+	int free = set->free;
+	if (free != -1) {
+		set->list[free].val = item;
+		set->free = set->list[free].free_next;
+	} else {
+		return 0;
+	}
+	set->list[free].alloc_next = set->alloc;
+	set->alloc = free;
+	set->list[free].free_next = -1;
+	return 1;
+}
+
+int via_set_del(set_t * set, unsigned int item)
+{
+	int alloc = set->alloc;
+	int prev = -1;
+
+	while (alloc != -1) {
+		if (set->list[alloc].val == item) {
+			if (prev != -1)
+				set->list[prev].alloc_next = set->list[alloc].alloc_next;
+			else
+				set->alloc = set->list[alloc].alloc_next;
+			break;
+		}
+		prev = alloc;
+		alloc = set->list[alloc].alloc_next;
+	}
+
+	if (alloc == -1)
+		return 0;
+
+	set->list[alloc].free_next = set->free;
+	set->free = alloc;
+	set->list[alloc].alloc_next = -1;
+
+	return 1;
+}
+
+/* setFirst -> setAdd -> setNext is wrong */
+
+int via_set_first(set_t * set, unsigned int * item)
+{
+	if (set->alloc == -1)
+		return 0;
+
+	*item = set->list[set->alloc].val;
+	set->trace = set->list[set->alloc].alloc_next;
+
+
+	return 1;
+}
+
+int via_set_next(set_t * set, unsigned int * item)
+{
+	if (set->trace == -1)
+		return 0;
+
+	*item = set->list[set->trace].val;
+	set->trace = set->list[set->trace].alloc_next;
+
+	return 1;
+}
+
+int via_set_destroy(set_t * set)
+{
+	kfree(set);
+	return 1;
+}
+
+#define ISFREE(bptr) ((bptr)->free)
+
+#define PRINTF(fmt, arg...) do{}while(0)
+
+void via_mmDumpMemInfo(memHeap_t * heap)
+{
+	TMemBlock *p;
+
+	PRINTF("Memory heap %p:\n", heap);
+
+	if (heap == 0)
+		PRINTF("  heap == 0\n");
+	else {
+		p = (TMemBlock *) heap;
+
+		while (p) {
+			PRINTF("  Offset:%08x, Size:%08x, %c%c\n", p->ofs, p->size, p->free ? '.' : 'U', p->reserved ? 'R' : '.');
+			p = p->next;
+		}
+	}
+
+	PRINTF("End of memory blocks\n");
+}
+
+memHeap_t *via_mmInit(int ofs, int size)
+{
+	PMemBlock blocks;
+
+	if (size <= 0)
+		return 0;
+
+
+	blocks = (TMemBlock *) kmalloc(sizeof(TMemBlock), GFP_KERNEL);
+
+	if (blocks) {
+		memset(blocks, 0, sizeof(TMemBlock));
+		blocks->ofs = ofs;
+		blocks->size = size;
+		blocks->free = 1;
+		return (memHeap_t *) blocks;
+	} else
+		return NULL;
+}
+
+memHeap_t *via_mmAddRange(memHeap_t * heap, int ofs, int size)
+{
+	PMemBlock blocks;
+	blocks = (TMemBlock *) kmalloc(2 *  sizeof(TMemBlock), GFP_KERNEL);
+
+	if (blocks) {
+		memset(blocks, 0, 2 * sizeof(TMemBlock));
+		blocks[0].size = size;
+		blocks[0].free = 1;
+		blocks[0].ofs = ofs;
+		blocks[0].next = &blocks[1];
+
+		/* Discontinuity - stops JoinBlock from trying to join non-adjacent
+		 * ranges.
+		 */
+		blocks[1].size = 0;
+		blocks[1].free = 0;
+		blocks[1].ofs = ofs + size;
+		blocks[1].next = (PMemBlock) heap;
+		return (memHeap_t *) blocks;
+	} else
+		return heap;
+}
+
+static TMemBlock *SliceBlock(TMemBlock * p, int startofs, int size, int reserved, int alignment)
+{
+	TMemBlock *newblock;
+
+	/* break left */
+	if (startofs > p->ofs) {
+		newblock = (TMemBlock *) kmalloc(sizeof(TMemBlock), GFP_KERNEL);
+		if(newblock == NULL)
+			return NULL;
+		memset(newblock, 0, sizeof(TMemBlock));
+		newblock->ofs = startofs;
+		newblock->size = p->size - (startofs - p->ofs);
+		newblock->free = 1;
+		newblock->next = p->next;
+		p->size -= newblock->size;
+		p->next = newblock;
+		p = newblock;
+	}
+
+	/* break right */
+	if (size < p->size) {
+		newblock = (TMemBlock *) kmalloc(sizeof(TMemBlock), GFP_KERNEL);
+		if(newblock == NULL)
+			return NULL;
+		memset(newblock, 0, sizeof(TMemBlock));
+		newblock->ofs = startofs + size;
+		newblock->size = p->size - size;
+		newblock->free = 1;
+		newblock->next = p->next;
+		p->size = size;
+		p->next = newblock;
+	}
+
+	/* p = middle block */
+	p->align = alignment;
+	p->free = 0;
+	p->reserved = reserved;
+	return p;
+}
+
+PMemBlock via_mmAllocMem(memHeap_t * heap, int size, int align2, int startSearch)
+{
+	int mask, startofs, endofs;
+	TMemBlock *p;
+
+	if (!heap || align2 < 0 || size <= 0)
+		return NULL;
+
+	mask = (1 << align2) - 1;
+	startofs = 0;
+	p = (TMemBlock *) heap;
+
+	while (p) {
+		if (ISFREE(p)) {
+			startofs = (p->ofs + mask) & ~mask;
+
+			if (startofs < startSearch)
+				startofs = startSearch;
+
+			endofs = startofs + size;
+
+			if (endofs <= (p->ofs + p->size))
+				break;
+		}
+
+		p = p->next;
+	}
+
+	if (!p)
+		return NULL;
+
+	p = SliceBlock(p, startofs, size, 0, mask + 1);
+	p->heap = heap;
+
+	return p;
+}
+
+static __inline__ int Join2Blocks(TMemBlock * p)
+{
+	if (p->free && p->next && p->next->free) {
+		TMemBlock *q = p->next;
+		p->size += q->size;
+		p->next = q->next;
+		kfree(q);
+
+		return 1;
+	}
+
+	return 0;
+}
+
+int via_mmFreeMem(PMemBlock b)
+{
+	TMemBlock *p, *prev;
+
+	if (!b)
+		return 0;
+
+	if (!b->heap) {
+		return -1;
+	}
+
+	p = b->heap;
+	prev = NULL;
+
+	while (p && p != b) {
+		prev = p;
+		p = p->next;
+	}
+
+	if (!p || p->free || p->reserved) {
+		if (!p)
+			BUG();
+		else if (p->free)
+			BUG();
+		else
+			BUG();
+		return -1;
+	}
+
+	p->free = 1;
+	Join2Blocks(p);
+
+	if (prev)
+		Join2Blocks(prev);
+
+	return 0;
+}
+
+int via_mm_ReserveMem(memHeap_t * heap, int offset, int size)
+{
+	int endofs;
+	TMemBlock *p;
+
+	if (!heap || size <= 0)
+		return -1;
+	endofs = offset + size;
+	p = (TMemBlock *) heap;
+
+	while (p && p->ofs <= offset) {
+		if (ISFREE(p) && endofs <= (p->ofs + p->size)) {
+			SliceBlock(p, offset, size, 1, 1);
+			return 0;
+		}
+		p = p->next;
+	}
+	return -1;
+}
+
+int via_mm_FreeReserved(memHeap_t * heap, int offset)
+{
+	TMemBlock *p, *prev;
+
+	if (!heap)
+		return -1;
+
+	p = (TMemBlock *) heap;
+	prev = NULL;
+
+	while (p && p->ofs != offset) {
+		prev = p;
+		p = p->next;
+	}
+
+	if (!p || !p->reserved)
+		return -1;
+	p->free = 1;
+	p->reserved = 0;
+	Join2Blocks(p);
+
+	if (prev)
+		Join2Blocks(prev);
+
+	return 0;
+}
+
+void via_mm_Destroy(memHeap_t * heap)
+{
+	TMemBlock *p, *q;
+
+	if (!heap)
+		return;
+	p = (TMemBlock *) heap;
+
+	while (p) {
+		q = p->next;
+		kfree(p);
+		p = q;
+	}
+}
diff -u -r -N --exclude='*.o' linux-2.6.0/drivers/char/drm/via_ds.h linux-2.6.0-gentoo/drivers/char/drm/via_ds.h
--- linux-2.6.0/drivers/char/drm/via_ds.h	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.0-gentoo/drivers/char/drm/via_ds.h	2003-12-22 17:54:30.000000000 +0000
@@ -0,0 +1,134 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#ifndef _via_ds_h_
+#define _via_ds_h_
+
+/* Set Data Structure */
+
+#define SET_SIZE 5000
+
+typedef struct {
+	unsigned int val;
+	int alloc_next, free_next;
+} list_item_t;
+
+typedef struct {
+	int alloc;
+	int free;
+	int trace;
+	list_item_t list[SET_SIZE];
+} set_t;
+
+set_t *via_set_init(void);
+int via_set_add(set_t *set, unsigned int item);
+int via_set_del(set_t *set, unsigned int item);
+int via_set_first(set_t *set, unsigned int *item);
+int via_set_next(set_t *set, unsigned int *item);
+int via_set_destroy(set_t *set);
+
+#endif
+
+
+#ifndef MM_INC
+#define MM_INC
+
+struct mem_block_t {
+	struct mem_block_t *next;
+	struct mem_block_t *heap;
+	int ofs,size;
+	int align;
+	int free:1;
+	int reserved:1;
+};
+typedef struct mem_block_t TMemBlock;
+typedef struct mem_block_t *PMemBlock;
+
+/* a heap is just the first block in a chain */
+typedef struct mem_block_t memHeap_t;
+
+static __inline__ int mmBlockSize(PMemBlock b)
+{
+	return b->size;
+}
+
+static __inline__ int mmOffset(PMemBlock b)
+{
+	return b->ofs;
+}
+
+static __inline__ void mmMarkReserved(PMemBlock b)
+{
+	b->reserved = 1;
+}
+
+/* 
+ * input: total size in bytes
+ * return: a heap pointer if OK, NULL if error
+ */
+
+memHeap_t *via_mmInit(int ofs, int size);
+
+memHeap_t *via_mmAddRange(memHeap_t *heap, int ofs, int size);
+
+
+/*
+ * Allocate 'size' bytes with 2^align2 bytes alignment,
+ * restrict the search to free memory after 'startSearch'
+ * depth and back buffers should be in different 4mb banks
+ * to get better page hits if possible
+ * input:	size = size of block
+ *       	align2 = 2^align2 bytes alignment
+ *		startSearch = linear offset from start of heap to begin search
+ * return: pointer to the allocated block, 0 if error
+ */
+
+PMemBlock  via_mmAllocMem(memHeap_t *heap, int size, int align2, int startSearch);
+
+/*
+ * Free block starts at offset
+ * input: pointer to a block
+ * return: 0 if OK, -1 if error
+ */
+int  via_mmFreeMem(PMemBlock b);
+
+/*
+ * Reserve 'size' bytes block start at offset
+ * This is used to prevent allocation of memory already used
+ * by the X server for the front buffer, pixmaps, and cursor
+ * input: size, offset
+ * output: 0 if OK, -1 if error
+ */
+int via_mmReserveMem(memHeap_t *heap, int offset,int size);
+int via_mmFreeReserved(memHeap_t *heap, int offset);
+
+/*
+ * destroy MM
+ */
+void via_mmDestroy(memHeap_t *mmInit);
+
+/* For debuging purpose. */
+void via_mmDumpMemInfo(memHeap_t *mmInit);
+
+#endif
diff -u -r -N --exclude='*.o' linux-2.6.0/drivers/char/drm/via_map.c linux-2.6.0-gentoo/drivers/char/drm/via_map.c
--- linux-2.6.0/drivers/char/drm/via_map.c	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.0-gentoo/drivers/char/drm/via_map.c	2003-12-22 18:00:54.000000000 +0000
@@ -0,0 +1,120 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+#define __NO_VERSION__
+#include "via.h"
+#include "drmP.h"
+/* NMGRILO */
+#include "via_drm.h"
+#include "via_drv.h"
+
+int via_do_init_map(drm_device_t *dev, drm_via_init_t *init)
+{
+	drm_via_private_t *dev_priv;
+	struct list_head *list;
+
+	DRM_DEBUG("%s\n", __FUNCTION__);
+
+	dev_priv = DRM(alloc)(sizeof(drm_via_private_t), DRM_MEM_DRIVER);
+	if (dev_priv == NULL)
+		return -ENOMEM;
+
+	memset(dev_priv, 0, sizeof(drm_via_private_t));
+	
+	list_for_each(list, &dev->maplist->head) {
+		drm_map_list_t *r_list = (drm_map_list_t *)list;
+		if ( r_list->map &&
+		    r_list->map->type == _DRM_SHM &&
+		    r_list->map->flags & _DRM_CONTAINS_LOCK) {
+			dev_priv->sarea = r_list->map;
+ 			break;
+ 		}
+ 	}
+	if (!dev_priv->sarea) {
+		DRM_ERROR("could not find sarea!\n");
+		dev->dev_private = (void *)dev_priv;
+		via_do_cleanup_map(dev);
+		return -EINVAL;
+	}
+
+	DRM_FIND_MAP(dev_priv->fb, init->fb_offset);
+	if (!dev_priv->fb) {
+		DRM_ERROR("could not find framebuffer!\n");
+		dev->dev_private = (void *)dev_priv;
+		via_do_cleanup_map(dev);
+		return -EINVAL;
+	}
+	DRM_FIND_MAP(dev_priv->mmio, init->mmio_offset);
+	if (!dev_priv->mmio) {
+		DRM_ERROR("could not find mmio region!\n");
+		dev->dev_private = (void *)dev_priv;
+		via_do_cleanup_map(dev);
+		return -EINVAL;
+	}
+	
+	dev_priv->sarea_priv = 	(drm_via_sarea_t *)((u8 *)dev_priv->sarea->handle +
+				     init->sarea_priv_offset);
+
+	dev_priv->agpAddr = init->agpAddr;
+
+	dev->dev_private = (void *)dev_priv;
+
+	return 0;
+}
+
+int via_do_cleanup_map(drm_device_t *dev)
+{
+	if (dev->dev_private) {
+
+		drm_via_private_t *dev_priv = dev->dev_private;
+
+		DRM(free)(dev_priv, sizeof(drm_via_private_t),
+			   DRM_MEM_DRIVER);
+		dev->dev_private = NULL;
+	}
+
+	return 0;
+}
+
+int via_map_init(struct inode *inode, struct file *filp,
+		   unsigned int cmd, unsigned long arg)
+{
+	drm_file_t *priv = filp->private_data;
+	drm_device_t *dev = priv->dev;
+	drm_via_init_t init;
+
+	DRM_DEBUG("%s\n", __FUNCTION__);
+
+	if (copy_from_user(&init, (drm_via_init_t *)arg, sizeof(init)))
+		return -EFAULT;
+
+	switch (init.func) {
+	    case VIA_INIT_MAP:
+		return via_do_init_map(dev, &init);
+	    case VIA_CLEANUP_MAP:
+		return via_do_cleanup_map(dev);
+	}
+
+	return -EINVAL;
+}
+
diff -u -r -N --exclude='*.o' linux-2.6.0/drivers/char/drm/via_mm.c linux-2.6.0-gentoo/drivers/char/drm/via_mm.c
--- linux-2.6.0/drivers/char/drm/via_mm.c	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.0-gentoo/drivers/char/drm/via_mm.c	2003-12-26 22:59:28.000000000 +0000
@@ -0,0 +1,342 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#define __NO_VERSION__
+#include "via.h"
+#include "drmP.h"
+#include "via_drm.h"
+#include "via_drv.h"
+#include "via_ds.h"
+#include "via_mm.h"
+
+#define MAX_CONTEXT 100
+
+unsigned int VIA_DEBUG = 1;
+
+typedef struct {
+	int used;
+	int context;
+	set_t *sets[2]; /* 0 for frame buffer, 1 for AGP , 2 for System*/
+} via_context_t;
+
+static via_context_t global_ppriv[MAX_CONTEXT];
+
+static int add_alloc_set(int context, int type, unsigned int val)
+{
+	int i, retval = 0;
+  
+	for (i = 0; i < MAX_CONTEXT; i++)
+	{
+		if (global_ppriv[i].used && global_ppriv[i].context == context) 
+		{
+			retval = via_set_add(global_ppriv[i].sets[type], val);
+			break;
+		}
+	}
+  	return retval;
+}
+
+static int del_alloc_set(int context, int type, unsigned int val)
+{  
+	int i, retval = 0;
+  
+	for (i = 0; i < MAX_CONTEXT; i++)
+		if (global_ppriv[i].used && global_ppriv[i].context == context) 
+		{
+			retval = via_set_del(global_ppriv[i].sets[type], val);
+			break;
+		}
+	return retval;
+}
+
+/* agp memory management */ 
+
+static memHeap_t *AgpHeap = NULL;
+
+#warning "FIXME: heap re-init cases ?"
+int via_agp_init(struct inode *inode, struct file *filp, unsigned int cmd,
+		  unsigned long arg)
+{
+	drm_via_agp_t agp;
+  
+	if (copy_from_user(&agp, (drm_via_agp_t *)arg, sizeof(agp)))
+		return -EFAULT;
+
+	AgpHeap = via_mmInit(agp.offset, agp.size);
+
+	DRM_DEBUG("offset = %u, size = %u", agp.offset, agp.size);
+	return 0;
+}
+
+/* fb memory management */ 
+static memHeap_t *FBHeap = NULL;
+
+int via_fb_init(struct inode *inode, struct file *filp, unsigned int cmd,
+		  unsigned long arg)
+{
+	drm_via_fb_t fb;
+
+	if  (copy_from_user(&fb, (drm_via_fb_t *)arg, sizeof(fb)))
+		return -EFAULT;
+
+	FBHeap = via_mmInit(fb.offset, fb.size);
+	DRM_DEBUG("offset = %u, size = %u", fb.offset, fb.size);
+
+	return 0;
+}
+
+int via_init_context(int context)
+{
+	int i;
+    
+	for (i = 0; i < MAX_CONTEXT ; i++)
+		if (global_ppriv[i].used && (global_ppriv[i].context == context))
+			break;
+    
+	if (i >= MAX_CONTEXT) {
+		for (i = 0; i < MAX_CONTEXT ; i++) {
+			if (!global_ppriv[i].used) {
+				global_ppriv[i].context = context;
+			    	global_ppriv[i].used = 1;
+			    	global_ppriv[i].sets[0] = via_set_init();
+			    	global_ppriv[i].sets[1] = via_set_init();
+			    	DRM_DEBUG("init allocation set, socket=%d, context = %d\n", 
+			                 i, context);
+				break;
+			}
+		}
+	
+		if ((i >= MAX_CONTEXT) || (global_ppriv[i].sets[0] == NULL) ||
+			(global_ppriv[i].sets[1] == NULL)) {
+			return 0;
+		}
+	}
+
+	return 1;
+}
+
+int via_final_context(int context)
+{
+	int i;
+	for (i=0; i<MAX_CONTEXT; i++)
+		if (global_ppriv[i].used && (global_ppriv[i].context == context))
+			break;
+    
+	if (i < MAX_CONTEXT) {
+		set_t *set;
+		unsigned int item;
+		int retval;
+	  
+	  	DRM_DEBUG("find socket %d, context = %d\n", i, context);
+	    
+		/* Video Memory */
+		set = global_ppriv[i].sets[0];
+		retval = via_set_first(set, &item);
+		while (retval) {
+			DRM_DEBUG("free video memory 0x%x\n", item);
+			via_mmFreeMem((PMemBlock)item);
+			retval = via_set_next(set, &item);
+		}
+		via_set_destroy(set);
+	    
+		/* AGP Memory */
+		set = global_ppriv[i].sets[1];
+		retval = via_set_first(set, &item);
+		while (retval) {
+			DRM_DEBUG("free agp memory 0x%x\n", item);
+			via_mmFreeMem((PMemBlock)item);
+			retval = via_set_next(set, &item);
+		}
+		via_set_destroy(set);
+	
+		global_ppriv[i].used = 0;	  
+	}
+    	return 1;
+}
+
+int via_mem_alloc(struct inode *inode, struct file *filp, unsigned int cmd,
+		  unsigned long arg)
+{
+	drm_via_mem_t mem;
+    
+	if (copy_from_user(&mem, (drm_via_mem_t *)arg, sizeof(mem)))
+		return -EFAULT;
+
+	switch (mem.type) {
+		case VIDEO :
+			if (via_fb_alloc(&mem) < 0)
+				return -ENOMEM;
+			if (copy_to_user((drm_via_mem_t *)arg, &mem, sizeof(mem))) 
+				return -EFAULT;
+			return 0;
+		case AGP :
+			if (via_agp_alloc(&mem) < 0)
+				return -ENOMEM;
+			if (copy_to_user((drm_via_mem_t *)arg, &mem, sizeof(mem))) 
+				return -EFAULT;
+			return 0;
+	}
+	return -EINVAL;
+}
+
+int via_fb_alloc(drm_via_mem_t* mem)
+{
+	drm_via_mm_t fb;
+	PMemBlock block;
+	int retval = 0;
+   
+	if (!FBHeap)
+		return -1;
+
+	fb.size = mem->size;
+	fb.context = mem->context;
+  
+	block = via_mmAllocMem(FBHeap, fb.size, 5, 0);
+	if (block) {
+		fb.offset = block->ofs;
+		fb.free = (unsigned int)block;
+		if (!add_alloc_set(fb.context, VIDEO, fb.free)) {
+    			DRM_DEBUG("adding to allocation set fails\n");
+			via_mmFreeMem((PMemBlock)fb.free);
+			retval = -1;
+		}
+	} else {  
+		fb.offset = 0;
+		fb.size = 0;
+		fb.free = 0;
+	}
+   
+	mem->offset = fb.offset;
+	mem->index = fb.free;
+
+	DRM_DEBUG("alloc fb, size = %d, offset = %d\n", fb.size, (int)fb.offset);
+  
+	return retval;
+}
+
+int via_agp_alloc(drm_via_mem_t* mem)
+{
+	drm_via_mm_t agp;
+	PMemBlock block;
+	int retval = 0;
+
+	if (!AgpHeap)
+		return -1;
+
+	agp.size = mem->size;
+	agp.context = mem->context;
+  
+	block = via_mmAllocMem(AgpHeap, agp.size, 5, 0);
+	if (block) {
+		agp.offset = block->ofs;
+		agp.free = (unsigned int)block;
+		if (!add_alloc_set(agp.context, AGP, agp.free)) {
+			DRM_DEBUG("adding to allocation set fails\n");
+			via_mmFreeMem((PMemBlock)agp.free);
+			retval = -1;
+		}
+	} else {  
+		agp.offset = 0;
+		agp.size = 0;
+		agp.free = 0;
+	}	
+   
+	mem->offset = agp.offset;
+	mem->index = agp.free;
+
+	DRM_DEBUG("alloc agp, size = %d, offset = %d\n", agp.size, (unsigned int)agp.offset);
+	return retval;
+}
+
+int via_mem_free(struct inode *inode, struct file *filp, unsigned int cmd,
+		  unsigned long arg)
+{
+	drm_via_mem_t mem;
+    
+	if (copy_from_user(&mem, (drm_via_mem_t *)arg, sizeof(mem)))
+		return -EFAULT;
+	
+	switch (mem.type) 
+	{
+	case VIDEO :
+	    if (via_fb_free(&mem) == 0)
+		return 0;
+	    break;
+	case AGP :
+	    if (via_agp_free(&mem) == 0)
+		return 0;
+	    break;
+	}
+	return -EINVAL;
+}
+
+int via_fb_free(drm_via_mem_t* mem)
+{
+	drm_via_mm_t fb;
+	int retval = 0;
+
+    
+	if (!FBHeap)
+		return -1;
+
+	fb.free = mem->index;
+	fb.context = mem->context;
+    
+	if (!fb.free)
+		return -1;
+
+	via_mmFreeMem((PMemBlock)fb.free);
+    
+	if (!del_alloc_set(fb.context, VIDEO, fb.free))
+		retval = -1;
+    
+	DRM_DEBUG("free fb, free = %d\n", fb.free);
+    
+	return retval;
+} 
+
+int via_agp_free(drm_via_mem_t* mem)
+{
+	drm_via_mm_t agp;
+  
+	int retval = 0;
+
+	agp.free = mem->index;
+	agp.context = mem->context;
+    
+	if (!agp.free)
+		return -1;
+
+	via_mmFreeMem((PMemBlock)agp.free);
+    
+	if (!del_alloc_set(agp.context, AGP, agp.free))
+		retval = -1;
+
+	DRM_DEBUG("free agp, free = %d\n", agp.free);
+	return retval;
+}
+
+EXPORT_SYMBOL(via_fb_alloc);
+EXPORT_SYMBOL(via_fb_free);
+
diff -u -r -N --exclude='*.o' linux-2.6.0/drivers/char/drm/via_mm.h linux-2.6.0-gentoo/drivers/char/drm/via_mm.h
--- linux-2.6.0/drivers/char/drm/via_mm.h	1970-01-01 01:00:00.000000000 +0100
+++ linux-2.6.0-gentoo/drivers/char/drm/via_mm.h	2003-12-22 17:54:30.000000000 +0000
@@ -0,0 +1,46 @@
+/*
+ * Copyright 1998-2003 VIA Technologies, Inc. All Rights Reserved.
+ * Copyright 2001-2003 S3 Graphics, Inc. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sub license,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the
+ * next paragraph) shall be included in all copies or substantial portions
+ * of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * VIA, S3 GRAPHICS, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
+ * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#ifndef _via_drm_mm_h_
+#define _via_drm_mm_h_
+
+typedef struct {
+	unsigned int context;
+	unsigned int size;
+	unsigned long offset;
+	unsigned int free;
+} drm_via_mm_t;
+
+typedef struct {
+	unsigned int size;
+	unsigned long handle;
+	void *virtual;
+} drm_via_dma_t;
+
+int via_fb_alloc(drm_via_mem_t *mem);
+int via_fb_free(drm_via_mem_t *mem);
+int via_agp_alloc(drm_via_mem_t *mem);
+int via_agp_free(drm_via_mem_t *mem);
+
+#endif
