Thursday, May 8, 2008

Microdia 0c45:612a - Patch



Driver: gspcav1
Driver Base - Homepage: mxhaard.free.fr ( Michel Xhaard )
Base file: gspcav1-20071224.tgz


Patch for: Microdia 0c45:612a "Avant" Camera
Chipset/Bridge: SN9C325 Sensor: OV7648
Link to MailList with patch

Download: Patch File









diff -Nru gspcav1-20071224/Sonix/sn9cxxx.h gspcav1-20071224-sn9c325-ov7648/Sonix/sn9cxxx.h
--- gspcav1-20071224/Sonix/sn9cxxx.h 2007-04-26 09:51:48.000000000 -0300
+++ gspcav1-20071224-sn9c325-ov7648/Sonix/sn9cxxx.h 2008-02-26 23:10:17.000000000 -0300
@@ -80,6 +80,7 @@
SN9C105,
SN9C110,
SN9C120,
+ SN9C325,
};

static __u8 sn_mi0360[] = {
@@ -114,6 +115,13 @@
0x01, 0x01, 0x08, 0x28, 0x1e, 0x20, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
//reg12 reg13 reg14 reg15 reg16 reg17 reg18 reg19 reg1a reg1b reg1c reg1d reg1e reg1f reg20 reg21 reg22 reg23
};
+
+static __u8 sn_ov7648[] =
+{
+ 0x00,0x21,0x62,0x00,0x1a,0x20,0x20,0x20,0xA1,0x6E,0x18,0x65,
+ 0x00,0x00,0x00,0x10,0x03,0x00,0x00,0x06,0x06,0x28,0x1E,0x82,
+ 0x07,0x00,0x00,0x00,0x00,0x00
+};

static __u8 reg9a[] = {
0x08, 0x40, 0x20, 0x10, 0x00, 0x04
@@ -128,6 +136,20 @@
//0x3E, 0x00, 0xC3, 0x0F, 0x00, 0x00, 0x00, 0x00, 0x00
0x3E, 0x00, 0xC3, 0x0F, 0xf7, 0x0f, 0x0a, 0x00, 0x00
};
+static __u8 reg9a_sn9c325[]=
+{
+ 0x0a,0x40,0x38,0x30,0x00,0x20
+};
+static __u8 regsn20_sn9c325[]=
+{
+ 0x0A,0x3A,0x56, 0x6C ,0x7E ,0x8D ,0x9A ,0xA4 ,0xAF ,0xBB ,0xC5 ,0xCD ,0xD5 ,0xDE ,0xE8 ,0xED ,0xF5
+}
+;
+static __u8 reg84_sn9c325[] =
+{
+ 0x14,0x00,0x27,0x00,0x07,0x00,0xE4,0x0F,0xD3,0x0F,0x4B,0x00,0x48,0x00,0xC0,0x0F,0xF8,0x0F,0x00,0x00,0x00
+};
+
static __u8 hv7131r_sensor_init[][8] = {
{0xC1, 0x11, 0x01, 0x08, 0x01, 0x00, 0x00, 0x10},
{0xB1, 0x11, 0x34, 0x17, 0x7F, 0x00, 0x00, 0x10},
@@ -309,6 +331,60 @@
};
// reg0x04 reg0x07 reg 0x10
//expo = (COM1 & 0x02) | (AECHH & 0x2f <<10) [ (AECh << 2)
+static __u8 ov7648_sensor_init[][8] =
+{
+ {0xC1,0x00,0x01,0x00,0x00,0x00,0x01,0x00},
+ {0xC1,0x00,0x00,0x00,0x00,0x00,0x01,0x00},
+ {0xC1,0x00,0x01,0x00,0x00,0x00,0x01,0x00},
+ {0xA1,0x6E,0x3F,0x20,0x00,0x00,0x00,0x10},
+ {0xA1,0x6E,0x3F,0x00,0x00,0x00,0x00,0x10},
+ {0xA1,0x6E,0x3E,0x00,0x00,0x00,0x00,0x10},
+ {0xD1,0x6E,0x04,0x02,0xB1,0x02,0x39,0x10},
+ {0xD1,0x6E,0x08,0x00,0x01,0x00,0x00,0x10},
+ {0xD1,0x6E,0x0C,0x02,0x7F,0x01,0xE0,0x10},
+ {0xD1,0x6E,0x12,0x03,0x02,0x00,0x03,0x10},
+ {0xD1,0x6E,0x16,0x85,0x40,0x4A,0x40,0x10},
+ {0xC1,0x6E,0x1A,0x00,0x80,0x00,0x00,0x10},
+ {0xD1,0x6E,0x1D,0x08,0x03,0x00,0x00,0x10},
+ {0xD1,0x6E,0x23,0x00,0xB0,0x00,0x94,0x10},
+ {0xD1,0x6E,0x27,0x58,0x00,0x00,0x00,0x10},
+ {0xD1,0x6E,0x2D,0x14,0x35,0x61,0x84,0x10},
+ {0xD1,0x6E,0x31,0xA2,0xBD,0xD8,0xFF,0x10},
+ {0xD1,0x6E,0x35,0x06,0x1E,0x12,0x02,0x10},
+ {0xD1,0x6E,0x39,0xAA,0x53,0x37,0xD5,0x10},
+ {0xA1,0x6E,0x3D,0xF2,0x00,0x00,0x00,0x10},
+ {0xD1,0x6E,0x3E,0x00,0x00,0x80,0x03,0x10},
+ {0xD1,0x6E,0x42,0x03,0x00,0x00,0x00,0x10},
+ {0xC1,0x6E,0x46,0x00,0x80,0x80,0x00,0x10},
+ {0xD1,0x6E,0x4B,0x02,0xEF,0x08,0xCD,0x10},
+ {0xD1,0x6E,0x4F,0x00,0xD0,0x00,0xA0,0x10},
+ {0xD1,0x6E,0x53,0x01,0xAA,0x01,0x40,0x10},
+ {0xD1,0x6E,0x5A,0x50,0x04,0x30,0x03,0x10},
+ {0xA1,0x6E,0x5E,0x00,0x00,0x00,0x00,0x10},
+ {0xD1,0x6E,0x5F,0x10,0x40,0xFF,0x00,0x10},
+ /* {0xD1,0x6E,0x63,0x40,0x40,0x00,0x00,0x10},
+ {0xD1,0x6E,0x67,0x00,0x00,0x00,0x00,0x10}, This is currently setting a
+ {0xD1,0x6E,0x6B,0x00,0x00,0x00,0x00,0x10}, blue tint, and some things more , i leave it here for future test if
+ {0xD1,0x6E,0x6F,0x00,0x00,0x00,0x00,0x10}, somene is having problems with color on this sensor
+ {0xC1,0x6E,0x73,0x10,0x80,0xEB,0x00,0x10},
+ {0xA1,0x6E,0x1E,0x03,0x00,0x00,0x00,0x10},
+ {0xA1,0x6E,0x15,0x01,0x00,0x00,0x00,0x10},
+ {0xC1,0x6E,0x16,0x40,0x40,0x40,0x00,0x10},
+ {0xA1,0x6E,0x1D,0x08,0x00,0x00,0x00,0x10},
+ {0xA1,0x6E,0x06,0x02,0x00,0x00,0x00,0x10},
+ {0xA1,0x6E,0x07,0xB5,0x00,0x00,0x00,0x10},
+ {0xA1,0x6E,0x18,0x6B,0x00,0x00,0x00,0x10},
+ {0xA1,0x6E,0x1D,0x08,0x00,0x00,0x00,0x10},
+ {0xA1,0x6E,0x06,0x02,0x00,0x00,0x00,0x10},
+ {0xA1,0x6E,0x07,0xB8,0x00,0x00,0x00,0x10},
+ */ {0xC1,0x00,0x01,0x00,0x00,0x00,0x01,0x00},
+ {0xA1,0x6E,0x06,0x03,0x00,0x00,0x00,0x10}, //Bright...
+ {0xA1,0x6E,0x07,0x66,0x00,0x00,0x00,0x10}, //B..
+ {0xC1,0x6E,0x1A,0x03,0x65,0x90,0x00,0x10}, //Bright/Witen....
+// {0xC1,0x6E,0x16,0x45,0x40,0x60,0x00,0x10}, //Bright/Witene
+ {0, 0, 0, 0, 0, 0, 0, 0}
+};
+

#if 0
static __u8 qtable1[] = {
@@ -607,6 +683,19 @@
i++;
}
}
+static void
+ ov7648_InitSensor(struct usb_spca50x *spca50x)
+{
+ int i = 0;
+ struct usb_device *dev = spca50x->dev;
+
+ while (ov7648_sensor_init[i][0])
+ {
+ sn9c102p_i2cwritebuf(dev, ov7648_sensor_init[i]);
+ i++;
+ }
+}
+
static int
sn9cxxx_init(struct usb_spca50x *spca50x)
{
@@ -615,6 +704,7 @@
__u8 *sn9c1xx = NULL;
__u8 regF1 = 0x01;
__u8 regGpio[] = { 0x29, 0x74 };
+ __u8 regGpioAlt = 0x62;
__u8 data = 0x00;
/* setup a selector by customid */
switch (spca50x->sensor) {
@@ -630,7 +720,11 @@
case SENSOR_OV7660:
sn9c1xx = sn_ov7660;
break;
+ case SENSOR_OV7648:
+ sn9c1xx = sn_ov7648;
+ break;
}
+
if (sn9c1xx == NULL)
return -ENODEV;
sonixRegWrite(dev, 0x08, 0xf1, 0x0000, ®F1, 1);
@@ -660,6 +754,11 @@
regGpio[1] = 0x70;
sonixRegWrite(dev, 0x08, 0x02, 0x0000, regGpio, 2);
break;
+ case SN9C325:
+ if (regF1 != 0x12 )
+ return -ENODEV;
+ sonixRegWrite(dev, 0x08, 0x02, 0x0000, ®GpioAlt, 1);
+ break;;
}

regF1 = 0x01;
@@ -708,6 +807,7 @@
struct usb_device *dev = spca50x->dev;
__u8 stophv7131[] = { 0xA1, 0x11, 0x02, 0x09, 0x00, 0x00, 0x00, 0x10 };
__u8 stopmi0360[] = { 0xB1, 0x5D, 0x07, 0x00, 0x00, 0x00, 0x00, 0x10 };
+
__u8 regF1 = 0x01;
__u8 data = 0x0b;
__u8 *sn9c1xx = NULL;
@@ -728,6 +828,10 @@
case SENSOR_OV7660:
sn9c1xx = sn_ov7660;
break;
+ case SENSOR_OV7648:
+ sn9c1xx = sn_ov7648;
+ data = 0x29;
+ break;
}
if (sn9c1xx == NULL)
return;
@@ -746,6 +850,7 @@
__u8 C0[] = { 0x2d, 0x2d, 0x3a, 0x05, 0x04, 0x3f };
__u8 CA[] = { 0x28, 0xd8, 0x14, 0xec };
__u8 CE[] = { 0x32, 0xdd, 0x2d, 0xdd }; //MI0360
+ __u8 CE_sn9c325[] = { 0x32, 0xdd, 0x32, 0xdd }; //OV7648 - SN9C325
__u8 data = 0;
__u8 regF1 = 0x00;
__u8 reg17 = 0x61;
@@ -765,6 +870,10 @@
case SENSOR_OV7660:
sn9c1xx = sn_ov7660;
break;
+ case SENSOR_OV7648:
+ sn9c1xx = sn_ov7648;
+ break;
+
}
if (sn9c1xx == NULL)
return;
@@ -773,15 +882,19 @@
sonixRegWrite(dev, 0x08, 0x01, 0x0000, &sn9c1xx[1], 2);
sonixRegWrite(dev, 0x08, 0x08, 0x0000, &sn9c1xx[8], 2);
sonixRegWrite(dev, 0x08, 0x17, 0x0000, &sn9c1xx[0x17], 3);
-
- sonixRegWrite(dev, 0x08, 0x9a, 0x0000, reg9a, 6);
+ if( spca50x->customid == SN9C325 )
+ sonixRegWrite(dev, 0x08, 0x9a, 0x0000, reg9a_sn9c325, 6);
+ else
+ sonixRegWrite(dev, 0x08, 0x9a, 0x0000, reg9a, 6);
data = 0x60;
sonixRegWrite(dev, 0x08, 0xD4, 0x0000, &data, 1);
-
sonixRegWrite(dev, 0x08, 0x03, 0x0000, &sn9c1xx[3], 0x0f);
data = 0x43;
sonixRegWrite(dev, 0x08, 0x01, 0x0000, &data, 1);
- data = 0x61;
+ if( spca50x->customid == SN9C325 )
+ data = 0xae;
+ else
+ data = 0x61;
sonixRegWrite(dev, 0x08, 0x17, 0x0000, &data, 1);
data = 0x42;
sonixRegWrite(dev, 0x08, 0x01, 0x0000, &data, 1);
@@ -805,18 +918,38 @@
sonixRegWrite(dev, 0x08, 0xc8, 0x0000, &DC29[4], 1);
sonixRegWrite(dev, 0x08, 0xc9, 0x0000, &DC29[5], 1);
sonixRegWrite(dev, 0x08, 0x18, 0x0000, &sn9c1xx[0x18], 1);
- data = 0x60;
+ if( spca50x->customid == SN9C325 )
+ data = 0xAE;
+ else
+ data = 0x60;
sonixRegWrite(dev, 0x08, 0x17, 0x0000, &data, 1);
sonixRegWrite(dev, 0x08, 0x05, 0x0000, &sn9c1xx[5], 1);
sonixRegWrite(dev, 0x08, 0x07, 0x0000, &sn9c1xx[7], 1);
sonixRegWrite(dev, 0x08, 0x06, 0x0000, &sn9c1xx[6], 1);
sonixRegWrite(dev, 0x08, 0x14, 0x0000, &sn9c1xx[0x14], 1);
- sonixRegWrite(dev, 0x08, 0x20, 0x0000, regsn20, 0x11);
+ if( spca50x->customid == SN9C325 )
+ sonixRegWrite(dev, 0x08, 0x20, 0x0000, regsn20_sn9c325, 0x11);
+ else
+ sonixRegWrite(dev, 0x08, 0x20, 0x0000, regsn20, 0x11);
+
for (i = 0; i < 8; i++)
- sonixRegWrite(dev, 0x08, 0x84, 0x0000, reg84, 0x15);
- data = 0x08;
+ {
+ if( spca50x->customid == SN9C325 )
+ sonixRegWrite(dev, 0x08, 0x84, 0x0000, reg84_sn9c325, 0x15);
+ else
+ sonixRegWrite(dev, 0x08, 0x84, 0x0000, reg84, 0x15);
+ }
+
+ if( spca50x->customid == SN9C325 )
+ data = 0x0a;
+ else
+ data = 0x08;
sonixRegWrite(dev, 0x08, 0x9a, 0x0000, &data, 1);
- data = 0x59;
+
+ if( spca50x->customid == SN9C325 )
+ data = 0x60;
+ else
+ data = 0x59;
sonixRegWrite(dev, 0x08, 0x99, 0x0000, &data, 1);

switch (spca50x->sensor) {
@@ -859,10 +992,22 @@
}

break;
+ case SENSOR_OV7648:
+ reg17 = 0xa2;
+ reg1 = 0x44;
+ ov7648_InitSensor(spca50x);
+ if (spca50x->mode){ //320x2...
+ }
+ else { //640x...
+ }
+ break;;
}
sonixRegWrite(dev, 0x08, 0xc0, 0x0000, C0, 6);
sonixRegWrite(dev, 0x08, 0xca, 0x0000, CA, 4);
- sonixRegWrite(dev, 0x08, 0xce, 0x0000, CE, 4); //?? {0x1e,0xdd,0x2d,0xe7}
+ if( spca50x->customid == SN9C325 )
+ sonixRegWrite(dev, 0x08, 0xce, 0x0000, CE_sn9c325, 4);
+ else
+ sonixRegWrite(dev, 0x08, 0xce, 0x0000, CE, 4); //?? {0x1e,0xdd,0x2d,0xe7}

// here change size mode 0 -> VGA; 1 -> CIF
data = 0x40 | sn9c1xx[0x18] | (spca50x->mode << 4);
diff -Nru gspcav1-20071224/Sonix/sonix.h gspcav1-20071224-sn9c325-ov7648/Sonix/sonix.h
--- gspcav1-20071224/Sonix/sonix.h 2007-11-22 11:52:16.000000000 -0300
+++ gspcav1-20071224-sn9c325-ov7648/Sonix/sonix.h 2008-02-26 01:51:01.000000000 -0300
@@ -654,6 +654,7 @@
case SENSOR_HV7131R:
case SENSOR_MI0360:
case SENSOR_PAS202:
+ case SENSOR_OV7648:
set_sonixVGA(spca50x);
break;
case SENSOR_PAS106:
diff -Nru gspcav1-20071224/gspca.h gspcav1-20071224-sn9c325-ov7648/gspca.h
--- gspcav1-20071224/gspca.h 2007-12-24 13:56:47.000000000 -0300
+++ gspcav1-20071224-sn9c325-ov7648/gspca.h 2008-02-26 01:46:21.000000000 -0300
@@ -129,7 +129,7 @@
#define SENSOR_OV7670 29
#define SENSOR_MI1310_SOC 30
#define SENSOR_MC501CB 31
-
+#define SENSOR_OV7648 35
/* Alternate interface transfer sizes */
#define SPCA50X_ALT_SIZE_0 0
#define SPCA50X_ALT_SIZE_128 1
diff -Nru gspcav1-20071224/gspca_core.c gspcav1-20071224-sn9c325-ov7648/gspca_core.c
--- gspcav1-20071224/gspca_core.c 2007-12-24 13:56:47.000000000 -0300
+++ gspcav1-20071224-sn9c325-ov7648/gspca_core.c 2008-02-26 01:49:48.000000000 -0300
@@ -422,6 +422,7 @@
Lenovo,
LogitechQC4Notebooks,
PhilipsSPC220NC,
+ AvantCamera,
LastCamera
};
static struct cam_list clist[] = {
@@ -620,6 +621,7 @@
{Lenovo,"lenovo MI1310_SOC"},
{LogitechQC4Notebooks,"Logitech QuickCam for Notebooks"},
{PhilipsSPC220NC,"Philips SPC220NC PAC207"},
+ {AvantCamera,"Avant Camera"},
{-1, NULL}
};
static __devinitdata struct usb_device_id device_table[] = {
@@ -834,6 +836,7 @@
{USB_DEVICE(0x046d, 0x08af)}, /* Logitech QuickCam Cool */
{USB_DEVICE(0x093a, 0x2472)}, /* PAC207 Genius VideoCam ge110 */
{USB_DEVICE(0x093a, 0x2463)}, /* Philips spc200nc pac207 */
+ {USB_DEVICE(0x0c45, 0x612a)}, /* Philips spc200nc pac207 */
{USB_DEVICE(0x0000, 0x0000)}, /* MystFromOri Unknow Camera */
{} /* Terminating entry */
};
@@ -1926,6 +1929,7 @@
case SENSOR_OV7660:
case SENSOR_OV7620:
case SENSOR_MC501CB:
+ case SENSOR_OV7648:
break;
default:
PDEBUG(0,
@@ -3889,6 +3893,14 @@
spca50x->i2c_ctrl_reg = 0x20;
spca50x->i2c_base = 0x11;
break;
+ case 0x612a:
+ spca50x->desc = AvantCamera;
+ spca50x->bridge =BRIDGE_SN9CXXX;
+ spca50x->sensor = SENSOR_OV7648;
+ spca50x->customid = SN9C325;
+ spca50x->i2c_ctrl_reg = 0x81;
+ spca50x->i2c_base = 0x21;
+ break;
case 0x6024:
case 0x6025:
spca50x->desc = Sonix6025;



1 comment:

Leonardo Pigñer said...

Que bueno!! Otro parche para Microdia!!

Este es un Blog re-interesante!!! :P

Besito