]> err.no Git - linux-2.6/blob - drivers/media/video/gspca/sonixb.c
Merge ../linux-2.6
[linux-2.6] / drivers / media / video / gspca / sonixb.c
1 /*
2  *              sonix sn9c102 (bayer) library
3  *              Copyright (C) 2003 2004 Michel Xhaard mxhaard@magic.fr
4  * Add Pas106 Stefano Mozzi (C) 2004
5  *
6  * V4L2 by Jean-Francois Moine <http://moinejf.free.fr>
7  *
8  * This program is free software; you can redistribute it and/or modify
9  * it under the terms of the GNU General Public License as published by
10  * the Free Software Foundation; either version 2 of the License, or
11  * any later version.
12  *
13  * This program is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16  * GNU General Public License for more details.
17  *
18  * You should have received a copy of the GNU General Public License
19  * along with this program; if not, write to the Free Software
20  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
21  */
22
23 #define MODULE_NAME "sonixb"
24
25 #include "gspca.h"
26
27 MODULE_AUTHOR("Michel Xhaard <mxhaard@users.sourceforge.net>");
28 MODULE_DESCRIPTION("GSPCA/SN9C102 USB Camera Driver");
29 MODULE_LICENSE("GPL");
30
31 /* specific webcam descriptor */
32 struct sd {
33         struct gspca_dev gspca_dev;     /* !! must be the first item */
34
35         struct sd_desc sd_desc;         /* our nctrls differ dependend upon the
36                                            sensor, so we use a per cam copy */
37         atomic_t avg_lum;
38
39         unsigned char gain;
40         unsigned char exposure;
41         unsigned char brightness;
42         unsigned char autogain;
43         unsigned char autogain_ignore_frames;
44         unsigned char freq;             /* light freq filter setting */
45         unsigned char saturation;
46         unsigned char hue;
47         unsigned char contrast;
48
49         unsigned char fr_h_sz;          /* size of frame header */
50         char sensor;                    /* Type of image sensor chip */
51 #define SENSOR_HV7131R 0
52 #define SENSOR_OV6650 1
53 #define SENSOR_OV7630 2
54 #define SENSOR_OV7630_3 3
55 #define SENSOR_PAS106 4
56 #define SENSOR_PAS202 5
57 #define SENSOR_TAS5110 6
58 #define SENSOR_TAS5130CXX 7
59         char sensor_has_gain;
60         __u8 sensor_addr;
61 };
62
63 #define COMP2 0x8f
64 #define COMP 0xc7               /* 0x87 //0x07 */
65 #define COMP1 0xc9              /* 0x89 //0x09 */
66
67 #define MCK_INIT 0x63
68 #define MCK_INIT1 0x20          /*fixme: Bayer - 0x50 for JPEG ??*/
69
70 #define SYS_CLK 0x04
71
72 /* We calculate the autogain at the end of the transfer of a frame, at this
73    moment a frame with the old settings is being transmitted, and a frame is
74    being captured with the old settings. So if we adjust the autogain we must
75    ignore atleast the 2 next frames for the new settings to come into effect
76    before doing any other adjustments */
77 #define AUTOGAIN_IGNORE_FRAMES 3
78 #define AUTOGAIN_DEADZONE 1000
79 #define DESIRED_AVG_LUM 7000
80
81 /* V4L2 controls supported by the driver */
82 static int sd_setbrightness(struct gspca_dev *gspca_dev, __s32 val);
83 static int sd_getbrightness(struct gspca_dev *gspca_dev, __s32 *val);
84 static int sd_setgain(struct gspca_dev *gspca_dev, __s32 val);
85 static int sd_getgain(struct gspca_dev *gspca_dev, __s32 *val);
86 static int sd_setexposure(struct gspca_dev *gspca_dev, __s32 val);
87 static int sd_getexposure(struct gspca_dev *gspca_dev, __s32 *val);
88 static int sd_setautogain(struct gspca_dev *gspca_dev, __s32 val);
89 static int sd_getautogain(struct gspca_dev *gspca_dev, __s32 *val);
90 static int sd_setfreq(struct gspca_dev *gspca_dev, __s32 val);
91 static int sd_getfreq(struct gspca_dev *gspca_dev, __s32 *val);
92 static int sd_setsaturation(struct gspca_dev *gspca_dev, __s32 val);
93 static int sd_getsaturation(struct gspca_dev *gspca_dev, __s32 *val);
94 static int sd_sethue(struct gspca_dev *gspca_dev, __s32 val);
95 static int sd_gethue(struct gspca_dev *gspca_dev, __s32 *val);
96 static int sd_setcontrast(struct gspca_dev *gspca_dev, __s32 val);
97 static int sd_getcontrast(struct gspca_dev *gspca_dev, __s32 *val);
98
99 static struct ctrl sd_ctrls[] = {
100         {
101             {
102                 .id      = V4L2_CID_BRIGHTNESS,
103                 .type    = V4L2_CTRL_TYPE_INTEGER,
104                 .name    = "Brightness",
105                 .minimum = 0,
106                 .maximum = 255,
107                 .step    = 1,
108 #define BRIGHTNESS_DEF 127
109                 .default_value = BRIGHTNESS_DEF,
110             },
111             .set = sd_setbrightness,
112             .get = sd_getbrightness,
113         },
114         {
115             {
116                 .id      = V4L2_CID_GAIN,
117                 .type    = V4L2_CTRL_TYPE_INTEGER,
118                 .name    = "Gain",
119                 .minimum = 0,
120                 .maximum = 255,
121                 .step    = 1,
122 #define GAIN_DEF 127
123 #define GAIN_KNEE 200
124                 .default_value = GAIN_DEF,
125             },
126             .set = sd_setgain,
127             .get = sd_getgain,
128         },
129         {
130                 {
131                         .id = V4L2_CID_EXPOSURE,
132                         .type = V4L2_CTRL_TYPE_INTEGER,
133                         .name = "Exposure",
134 #define EXPOSURE_DEF  16 /*  32 ms / 30 fps */
135 #define EXPOSURE_KNEE 50 /* 100 ms / 10 fps */
136                         .minimum = 0,
137                         .maximum = 255,
138                         .step = 1,
139                         .default_value = EXPOSURE_DEF,
140                         .flags = 0,
141                 },
142                 .set = sd_setexposure,
143                 .get = sd_getexposure,
144         },
145         {
146                 {
147                         .id = V4L2_CID_AUTOGAIN,
148                         .type = V4L2_CTRL_TYPE_BOOLEAN,
149                         .name = "Automatic Gain (and Exposure)",
150                         .minimum = 0,
151                         .maximum = 1,
152                         .step = 1,
153 #define AUTOGAIN_DEF 1
154                         .default_value = AUTOGAIN_DEF,
155                         .flags = 0,
156                 },
157                 .set = sd_setautogain,
158                 .get = sd_getautogain,
159         },
160         {
161                 {
162                         .id      = V4L2_CID_POWER_LINE_FREQUENCY,
163                         .type    = V4L2_CTRL_TYPE_MENU,
164                         .name    = "Light frequency filter",
165                         .minimum = 0,
166                         .maximum = 2,   /* 0: 0, 1: 50Hz, 2:60Hz */
167                         .step    = 1,
168 #define FREQ_DEF 1
169                         .default_value = FREQ_DEF,
170                 },
171                 .set = sd_setfreq,
172                 .get = sd_getfreq,
173         },
174         {
175                 {
176                         .id      = V4L2_CID_SATURATION,
177                         .type    = V4L2_CTRL_TYPE_INTEGER,
178                         .name    = "Saturation",
179                         .minimum = 0,
180                         .maximum = 255,
181                         .step    = 1,
182 #define SATURATION_DEF 127
183                         .default_value = SATURATION_DEF,
184                 },
185                 .set = sd_setsaturation,
186                 .get = sd_getsaturation,
187         },
188         {
189                 {
190                         .id      = V4L2_CID_HUE,
191                         .type    = V4L2_CTRL_TYPE_INTEGER,
192                         .name    = "Hue",
193                         .minimum = 0,
194                         .maximum = 255,
195                         .step    = 1,
196 #define HUE_DEF 127
197                         .default_value = HUE_DEF,
198                 },
199                 .set = sd_sethue,
200                 .get = sd_gethue,
201         },
202         {
203                 {
204                         .id      = V4L2_CID_CONTRAST,
205                         .type    = V4L2_CTRL_TYPE_INTEGER,
206                         .name    = "Contrast",
207                         .minimum = 0,
208                         .maximum = 255,
209                         .step    = 1,
210 #define CONTRAST_DEF 127
211                         .default_value = CONTRAST_DEF,
212                 },
213                 .set = sd_setcontrast,
214                 .get = sd_getcontrast,
215         },
216 };
217
218 static struct v4l2_pix_format vga_mode[] = {
219         {160, 120, V4L2_PIX_FMT_SN9C10X, V4L2_FIELD_NONE,
220                 .bytesperline = 160,
221                 .sizeimage = 160 * 120,
222                 .colorspace = V4L2_COLORSPACE_SRGB,
223                 .priv = 2},
224         {320, 240, V4L2_PIX_FMT_SN9C10X, V4L2_FIELD_NONE,
225                 .bytesperline = 320,
226                 .sizeimage = 320 * 240,
227                 .colorspace = V4L2_COLORSPACE_SRGB,
228                 .priv = 1},
229         {640, 480, V4L2_PIX_FMT_SN9C10X, V4L2_FIELD_NONE,
230                 .bytesperline = 640,
231                 .sizeimage = 640 * 480,
232                 .colorspace = V4L2_COLORSPACE_SRGB,
233                 .priv = 0},
234 };
235 static struct v4l2_pix_format sif_mode[] = {
236         {176, 144, V4L2_PIX_FMT_SN9C10X, V4L2_FIELD_NONE,
237                 .bytesperline = 176,
238                 .sizeimage = 176 * 144,
239                 .colorspace = V4L2_COLORSPACE_SRGB,
240                 .priv = 1},
241         {352, 288, V4L2_PIX_FMT_SN9C10X, V4L2_FIELD_NONE,
242                 .bytesperline = 352,
243                 .sizeimage = 352 * 288,
244                 .colorspace = V4L2_COLORSPACE_SRGB,
245                 .priv = 0},
246 };
247
248 static const __u8 probe_ov7630[] = {0x08, 0x44};
249
250 static const __u8 initHv7131[] = {
251         0x46, 0x77, 0x00, 0x04, 0x00, 0x00, 0x00, 0x80, 0x11, 0x00, 0x00, 0x00,
252         0x00, 0x00,
253         0x00, 0x00, 0x00, 0x03, 0x01, 0x00,     /* shift from 0x02 0x01 0x00 */
254         0x28, 0x1e, 0x60, 0x8a, 0x20,
255         0x1d, 0x10, 0x02, 0x03, 0x0f, 0x0c
256 };
257 static const __u8 hv7131_sensor_init[][8] = {
258         {0xc0, 0x11, 0x31, 0x38, 0x2a, 0x2e, 0x00, 0x10},
259         {0xa0, 0x11, 0x01, 0x08, 0x2a, 0x2e, 0x00, 0x10},
260         {0xb0, 0x11, 0x20, 0x00, 0xd0, 0x2e, 0x00, 0x10},
261         {0xc0, 0x11, 0x25, 0x03, 0x0e, 0x28, 0x00, 0x16},
262         {0xa0, 0x11, 0x30, 0x10, 0x0e, 0x28, 0x00, 0x15},
263 };
264 static const __u8 initOv6650[] = {
265         0x44, 0x44, 0x00, 0x00, 0x00, 0x00, 0x00, 0x80,
266         0x60, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
267         0x00, 0x02, 0x01, 0x0a, 0x16, 0x12, 0x68, 0x0b,
268         0x10, 0x1d, 0x10, 0x00, 0x06, 0x1f, 0x00
269 };
270 static const __u8 ov6650_sensor_init[][8] =
271 {
272         /* Bright, contrast, etc are set througth SCBB interface.
273          * AVCAP on win2 do not send any data on this   controls. */
274         /* Anyway, some registers appears to alter bright and constrat */
275
276         /* Reset sensor */
277         {0xa0, 0x60, 0x12, 0x80, 0x00, 0x00, 0x00, 0x10},
278         /* Set clock register 0x11 low nibble is clock divider */
279         {0xd0, 0x60, 0x11, 0xc0, 0x1b, 0x18, 0xc1, 0x10},
280         /* Next some unknown stuff */
281         {0xb0, 0x60, 0x15, 0x00, 0x02, 0x18, 0xc1, 0x10},
282 /*      {0xa0, 0x60, 0x1b, 0x01, 0x02, 0x18, 0xc1, 0x10},
283                  * THIS SET GREEN SCREEN
284                  * (pixels could be innverted in decode kind of "brg",
285                  * but blue wont be there. Avoid this data ... */
286         {0xd0, 0x60, 0x26, 0x01, 0x14, 0xd8, 0xa4, 0x10}, /* format out? */
287         {0xd0, 0x60, 0x26, 0x01, 0x14, 0xd8, 0xa4, 0x10},
288         {0xa0, 0x60, 0x30, 0x3d, 0x0A, 0xd8, 0xa4, 0x10},
289         /* Enable rgb brightness control */
290         {0xa0, 0x60, 0x61, 0x08, 0x00, 0x00, 0x00, 0x10},
291         /* HDG: Note windows uses the line below, which sets both register 0x60
292            and 0x61 I believe these registers of the ov6650 are identical as
293            those of the ov7630, because if this is true the windows settings
294            add a bit additional red gain and a lot additional blue gain, which
295            matches my findings that the windows settings make blue much too
296            blue and red a little too red.
297         {0xb0, 0x60, 0x60, 0x66, 0x68, 0xd8, 0xa4, 0x10}, */
298         /* Some more unknown stuff */
299         {0xa0, 0x60, 0x68, 0x04, 0x68, 0xd8, 0xa4, 0x10},
300         {0xd0, 0x60, 0x17, 0x24, 0xd6, 0x04, 0x94, 0x10}, /* Clipreg */
301 };
302
303 static const __u8 initOv7630[] = {
304         0x04, 0x44, 0x00, 0x00, 0x00, 0x00, 0x00, 0x80, /* r01 .. r08 */
305         0x21, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* r09 .. r10 */
306         0x00, 0x02, 0x01, 0x0a,                         /* r11 .. r14 */
307         0x28, 0x1e,                     /* H & V sizes     r15 .. r16 */
308         0x68, COMP1, MCK_INIT1,                         /* r17 .. r19 */
309         0x1d, 0x10, 0x02, 0x03, 0x0f, 0x0c              /* r1a .. r1f */
310 };
311 static const __u8 initOv7630_3[] = {
312         0x44, 0x44, 0x00, 0x1a, 0x20, 0x20, 0x20, 0x80, /* r01 .. r08 */
313         0x21, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, /* r09 .. r10 */
314         0x00, 0x01, 0x01, 0x0a,                         /* r11 .. r14 */
315         0x28, 0x1e,                     /* H & V sizes     r15 .. r16 */
316         0x68, 0x8f, MCK_INIT1,                          /* r17 .. r19 */
317         0x1d, 0x10, 0x02, 0x03, 0x0f, 0x0c, 0x00,       /* r1a .. r20 */
318         0x10, 0x20, 0x30, 0x40, 0x50, 0x60, 0x70, 0x80, /* r21 .. r28 */
319         0x90, 0xa0, 0xb0, 0xc0, 0xd0, 0xe0, 0xf0, 0xff  /* r29 .. r30 */
320 };
321 static const __u8 ov7630_sensor_init_com[][8] = {
322         {0xa0, 0x21, 0x12, 0x80, 0x00, 0x00, 0x00, 0x10},
323         {0xb0, 0x21, 0x01, 0x77, 0x3a, 0x00, 0x00, 0x10},
324 /*      {0xd0, 0x21, 0x12, 0x7c, 0x01, 0x80, 0x34, 0x10},          jfm */
325         {0xd0, 0x21, 0x12, 0x1c, 0x00, 0x80, 0x34, 0x10},       /* jfm */
326         {0xa0, 0x21, 0x1b, 0x04, 0x00, 0x80, 0x34, 0x10},
327         {0xa0, 0x21, 0x20, 0x44, 0x00, 0x80, 0x34, 0x10},
328         {0xa0, 0x21, 0x23, 0xee, 0x00, 0x80, 0x34, 0x10},
329         {0xd0, 0x21, 0x26, 0xa0, 0x9a, 0xa0, 0x30, 0x10},
330         {0xb0, 0x21, 0x2a, 0x80, 0x00, 0xa0, 0x30, 0x10},
331         {0xb0, 0x21, 0x2f, 0x3d, 0x24, 0xa0, 0x30, 0x10},
332         {0xa0, 0x21, 0x32, 0x86, 0x24, 0xa0, 0x30, 0x10},
333         {0xb0, 0x21, 0x60, 0xa9, 0x4a, 0xa0, 0x30, 0x10},
334 /*      {0xb0, 0x21, 0x60, 0xa9, 0x42, 0xa0, 0x30, 0x10},        * jfm */
335         {0xa0, 0x21, 0x65, 0x00, 0x42, 0xa0, 0x30, 0x10},
336         {0xa0, 0x21, 0x69, 0x38, 0x42, 0xa0, 0x30, 0x10},
337         {0xc0, 0x21, 0x6f, 0x88, 0x0b, 0x00, 0x30, 0x10},
338         {0xc0, 0x21, 0x74, 0x21, 0x8e, 0x00, 0x30, 0x10},
339         {0xa0, 0x21, 0x7d, 0xf7, 0x8e, 0x00, 0x30, 0x10},
340         {0xd0, 0x21, 0x17, 0x1c, 0xbd, 0x06, 0xf6, 0x10},
341 };
342 static const __u8 ov7630_sensor_init[][8] = {
343         {0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, /* delay 200ms */
344         {0xa0, 0x21, 0x11, 0x01, 0xbd, 0x06, 0xf6, 0x10},       /* jfm */
345         {0xa0, 0x21, 0x10, 0x57, 0xbd, 0x06, 0xf6, 0x16},
346         {0xa0, 0x21, 0x76, 0x02, 0xbd, 0x06, 0xf6, 0x16},
347         {0xa0, 0x21, 0x00, 0x10, 0xbd, 0x06, 0xf6, 0x15},       /* gain */
348 };
349 static const __u8 ov7630_sensor_init_3[][8] = {
350         {0xa0, 0x21, 0x2a, 0xa0, 0x00, 0x00, 0x00, 0x10},
351         {0xa0, 0x21, 0x2a, 0x80, 0x00, 0x00, 0x00, 0x10},
352 };
353
354 static const __u8 initPas106[] = {
355         0x04, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x81, 0x40, 0x00, 0x00, 0x00,
356         0x00, 0x00,
357         0x00, 0x00, 0x00, 0x05, 0x01, 0x00,
358         0x16, 0x12, 0x28, COMP1, MCK_INIT1,
359         0x18, 0x10, 0x04, 0x03, 0x11, 0x0c
360 };
361 /* compression 0x86 mckinit1 0x2b */
362 static const __u8 pas106_data[][2] = {
363         {0x02, 0x04},           /* Pixel Clock Divider 6 */
364         {0x03, 0x13},           /* Frame Time MSB */
365 /*      {0x03, 0x12},            * Frame Time MSB */
366         {0x04, 0x06},           /* Frame Time LSB */
367 /*      {0x04, 0x05},            * Frame Time LSB */
368         {0x05, 0x65},           /* Shutter Time Line Offset */
369 /*      {0x05, 0x6d},            * Shutter Time Line Offset */
370 /*      {0x06, 0xb1},            * Shutter Time Pixel Offset */
371         {0x06, 0xcd},           /* Shutter Time Pixel Offset */
372         {0x07, 0xc1},           /* Black Level Subtract Sign */
373 /*      {0x07, 0x00},            * Black Level Subtract Sign */
374         {0x08, 0x06},           /* Black Level Subtract Level */
375         {0x08, 0x06},           /* Black Level Subtract Level */
376 /*      {0x08, 0x01},            * Black Level Subtract Level */
377         {0x09, 0x05},           /* Color Gain B Pixel 5 a */
378         {0x0a, 0x04},           /* Color Gain G1 Pixel 1 5 */
379         {0x0b, 0x04},           /* Color Gain G2 Pixel 1 0 5 */
380         {0x0c, 0x05},           /* Color Gain R Pixel 3 1 */
381         {0x0d, 0x00},           /* Color GainH  Pixel */
382         {0x0e, 0x0e},           /* Global Gain */
383         {0x0f, 0x00},           /* Contrast */
384         {0x10, 0x06},           /* H&V synchro polarity */
385         {0x11, 0x06},           /* ?default */
386         {0x12, 0x06},           /* DAC scale */
387         {0x14, 0x02},           /* ?default */
388         {0x13, 0x01},           /* Validate Settings */
389 };
390 static const __u8 initPas202[] = {
391         0x44, 0x44, 0x21, 0x30, 0x00, 0x00, 0x00, 0x80, 0x40, 0x00, 0x00, 0x00,
392         0x00, 0x00,
393         0x00, 0x00, 0x00, 0x07, 0x03, 0x0a,     /* 6 */
394         0x28, 0x1e, 0x28, 0x89, 0x30,
395         0x00, 0x00, 0x02, 0x03, 0x0f, 0x0c
396 };
397 static const __u8 pas202_sensor_init[][8] = {
398         {0xa0, 0x40, 0x02, 0x03, 0x00, 0x00, 0x00, 0x10},
399         {0xd0, 0x40, 0x04, 0x07, 0x34, 0x00, 0x09, 0x10},
400         {0xd0, 0x40, 0x08, 0x01, 0x00, 0x00, 0x01, 0x10},
401         {0xd0, 0x40, 0x0C, 0x00, 0x0C, 0x00, 0x32, 0x10},
402         {0xd0, 0x40, 0x10, 0x00, 0x01, 0x00, 0x63, 0x10},
403         {0xa0, 0x40, 0x15, 0x70, 0x01, 0x00, 0x63, 0x10},
404         {0xa0, 0x40, 0x18, 0x00, 0x01, 0x00, 0x63, 0x10},
405         {0xa0, 0x40, 0x11, 0x01, 0x01, 0x00, 0x63, 0x10},
406         {0xa0, 0x40, 0x03, 0x56, 0x01, 0x00, 0x63, 0x10},
407         {0xa0, 0x40, 0x11, 0x01, 0x01, 0x00, 0x63, 0x10},
408         {0xb0, 0x40, 0x04, 0x07, 0x2a, 0x00, 0x63, 0x10},
409         {0xb0, 0x40, 0x0e, 0x00, 0x3d, 0x00, 0x63, 0x10},
410
411         {0xa0, 0x40, 0x11, 0x01, 0x3d, 0x00, 0x63, 0x16},
412         {0xa0, 0x40, 0x10, 0x08, 0x3d, 0x00, 0x63, 0x15},
413         {0xa0, 0x40, 0x02, 0x04, 0x3d, 0x00, 0x63, 0x16},
414         {0xa0, 0x40, 0x11, 0x01, 0x3d, 0x00, 0x63, 0x16},
415         {0xb0, 0x40, 0x0e, 0x00, 0x31, 0x00, 0x63, 0x16},
416         {0xa0, 0x40, 0x11, 0x01, 0x31, 0x00, 0x63, 0x16},
417         {0xa0, 0x40, 0x10, 0x0e, 0x31, 0x00, 0x63, 0x15},
418         {0xa0, 0x40, 0x11, 0x01, 0x31, 0x00, 0x63, 0x16},
419 };
420
421 static const __u8 initTas5110[] = {
422         0x44, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x11, 0x00, 0x00, 0x00,
423         0x00, 0x00,
424         0x00, 0x01, 0x00, 0x46, 0x09, 0x0a,     /* shift from 0x45 0x09 0x0a */
425         0x16, 0x12, 0x60, 0x86, 0x2b,
426         0x14, 0x0a, 0x02, 0x02, 0x09, 0x07
427 };
428 static const __u8 tas5110_sensor_init[][8] = {
429         {0x30, 0x11, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x10},
430         {0x30, 0x11, 0x02, 0x20, 0xa9, 0x00, 0x00, 0x10},
431         {0xa0, 0x61, 0x9a, 0xca, 0x00, 0x00, 0x00, 0x17},
432 };
433
434 static const __u8 initTas5130[] = {
435         0x04, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x11, 0x00, 0x00, 0x00,
436         0x00, 0x00,
437         0x00, 0x01, 0x00, 0x69, 0x0c, 0x0a,
438         0x28, 0x1e, 0x60, COMP, MCK_INIT,
439         0x18, 0x10, 0x04, 0x03, 0x11, 0x0c
440 };
441 static const __u8 tas5130_sensor_init[][8] = {
442 /*      {0x30, 0x11, 0x00, 0x40, 0x47, 0x00, 0x00, 0x10},
443                                         * shutter 0x47 short exposure? */
444         {0x30, 0x11, 0x00, 0x40, 0x01, 0x00, 0x00, 0x10},
445                                         /* shutter 0x01 long exposure */
446         {0x30, 0x11, 0x02, 0x20, 0x70, 0x00, 0x00, 0x10},
447 };
448
449 /* get one byte in gspca_dev->usb_buf */
450 static void reg_r(struct gspca_dev *gspca_dev,
451                   __u16 value)
452 {
453         usb_control_msg(gspca_dev->dev,
454                         usb_rcvctrlpipe(gspca_dev->dev, 0),
455                         0,                      /* request */
456                         USB_DIR_IN | USB_TYPE_VENDOR | USB_RECIP_INTERFACE,
457                         value,
458                         0,                      /* index */
459                         gspca_dev->usb_buf, 1,
460                         500);
461 }
462
463 static void reg_w(struct gspca_dev *gspca_dev,
464                   __u16 value,
465                   const __u8 *buffer,
466                   int len)
467 {
468 #ifdef CONFIG_VIDEO_ADV_DEBUG
469         if (len > sizeof gspca_dev->usb_buf) {
470                 PDEBUG(D_ERR|D_PACK, "reg_w: buffer overflow");
471                 return;
472         }
473 #endif
474         memcpy(gspca_dev->usb_buf, buffer, len);
475         usb_control_msg(gspca_dev->dev,
476                         usb_sndctrlpipe(gspca_dev->dev, 0),
477                         0x08,                   /* request */
478                         USB_DIR_OUT | USB_TYPE_VENDOR | USB_RECIP_INTERFACE,
479                         value,
480                         0,                      /* index */
481                         gspca_dev->usb_buf, len,
482                         500);
483 }
484
485 static void reg_w_big(struct gspca_dev *gspca_dev,
486                   __u16 value,
487                   const __u8 *buffer,
488                   int len)
489 {
490         __u8 *tmpbuf;
491
492         tmpbuf = kmalloc(len, GFP_KERNEL);
493         memcpy(tmpbuf, buffer, len);
494         usb_control_msg(gspca_dev->dev,
495                         usb_sndctrlpipe(gspca_dev->dev, 0),
496                         0x08,                   /* request */
497                         USB_DIR_OUT | USB_TYPE_VENDOR | USB_RECIP_INTERFACE,
498                         value,
499                         0,                      /* index */
500                         tmpbuf, len,
501                         500);
502         kfree(tmpbuf);
503 }
504
505 static int i2c_w(struct gspca_dev *gspca_dev, const __u8 *buffer)
506 {
507         int retry = 60;
508
509         /* is i2c ready */
510         reg_w(gspca_dev, 0x08, buffer, 8);
511         while (retry--) {
512                 msleep(10);
513                 reg_r(gspca_dev, 0x08);
514                 if (gspca_dev->usb_buf[0] & 0x04) {
515                         if (gspca_dev->usb_buf[0] & 0x08)
516                                 return -1;
517                         return 0;
518                 }
519         }
520         return -1;
521 }
522
523 static void i2c_w_vector(struct gspca_dev *gspca_dev,
524                         const __u8 buffer[][8], int len)
525 {
526         for (;;) {
527                 reg_w(gspca_dev, 0x08, *buffer, 8);
528                 len -= 8;
529                 if (len <= 0)
530                         break;
531                 buffer++;
532         }
533 }
534
535 static void setbrightness(struct gspca_dev *gspca_dev)
536 {
537         struct sd *sd = (struct sd *) gspca_dev;
538         __u8 value;
539
540         switch (sd->sensor) {
541         case  SENSOR_OV6650:
542         case  SENSOR_OV7630_3:
543         case  SENSOR_OV7630: {
544                 __u8 i2cOV[] =
545                         {0xa0, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x10};
546
547                 /* change reg 0x06 */
548                 i2cOV[1] = sd->sensor_addr;
549                 i2cOV[3] = sd->brightness;
550                 if (i2c_w(gspca_dev, i2cOV) < 0)
551                         goto err;
552                 break;
553             }
554         case SENSOR_PAS106: {
555                 __u8 i2c1[] =
556                         {0xa1, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x14};
557
558                 i2c1[3] = sd->brightness >> 3;
559                 i2c1[2] = 0x0e;
560                 if (i2c_w(gspca_dev, i2c1) < 0)
561                         goto err;
562                 i2c1[3] = 0x01;
563                 i2c1[2] = 0x13;
564                 if (i2c_w(gspca_dev, i2c1) < 0)
565                         goto err;
566                 break;
567             }
568         case SENSOR_PAS202: {
569                 /* __u8 i2cpexpo1[] =
570                         {0xb0, 0x40, 0x04, 0x07, 0x2a, 0x00, 0x63, 0x16}; */
571                 __u8 i2cpexpo[] =
572                         {0xb0, 0x40, 0x0e, 0x01, 0xab, 0x00, 0x63, 0x16};
573                 __u8 i2cp202[] =
574                         {0xa0, 0x40, 0x10, 0x0e, 0x31, 0x00, 0x63, 0x15};
575                 static __u8 i2cpdoit[] =
576                         {0xa0, 0x40, 0x11, 0x01, 0x31, 0x00, 0x63, 0x16};
577
578                 /* change reg 0x10 */
579                 i2cpexpo[4] = 0xff - sd->brightness;
580 /*              if(i2c_w(gspca_dev,i2cpexpo1) < 0)
581                         goto err; */
582 /*              if(i2c_w(gspca_dev,i2cpdoit) < 0)
583                         goto err; */
584                 if (i2c_w(gspca_dev, i2cpexpo) < 0)
585                         goto err;
586                 if (i2c_w(gspca_dev, i2cpdoit) < 0)
587                         goto err;
588                 i2cp202[3] = sd->brightness >> 3;
589                 if (i2c_w(gspca_dev, i2cp202) < 0)
590                         goto err;
591                 if (i2c_w(gspca_dev, i2cpdoit) < 0)
592                         goto err;
593                 break;
594             }
595         case SENSOR_TAS5130CXX: {
596                 __u8 i2c[] =
597                         {0x30, 0x11, 0x02, 0x20, 0x70, 0x00, 0x00, 0x10};
598
599                 value = 0xff - sd->brightness;
600                 i2c[4] = value;
601                 PDEBUG(D_CONF, "brightness %d : %d", value, i2c[4]);
602                 if (i2c_w(gspca_dev, i2c) < 0)
603                         goto err;
604                 break;
605             }
606         case SENSOR_TAS5110:
607                 /* FIXME figure out howto control brightness on TAS5110 */
608                 break;
609         }
610         return;
611 err:
612         PDEBUG(D_ERR, "i2c error brightness");
613 }
614
615 static void setsensorgain(struct gspca_dev *gspca_dev)
616 {
617         struct sd *sd = (struct sd *) gspca_dev;
618         unsigned char gain = sd->gain;
619
620         switch (sd->sensor) {
621
622         case SENSOR_TAS5110: {
623                 __u8 i2c[] =
624                         {0x30, 0x11, 0x02, 0x20, 0x70, 0x00, 0x00, 0x10};
625
626                 i2c[4] = 255 - gain;
627                 if (i2c_w(gspca_dev, i2c) < 0)
628                         goto err;
629                 break;
630             }
631
632         case SENSOR_OV6650:
633                 gain >>= 1;
634                 /* fall thru */
635         case SENSOR_OV7630_3: {
636                 __u8 i2c[] = {0xa0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x10};
637
638                 i2c[1] = sd->sensor_addr;
639                 i2c[3] = gain >> 2;
640                 if (i2c_w(gspca_dev, i2c) < 0)
641                         goto err;
642                 break;
643             }
644         }
645         return;
646 err:
647         PDEBUG(D_ERR, "i2c error gain");
648 }
649
650 static void setgain(struct gspca_dev *gspca_dev)
651 {
652         struct sd *sd = (struct sd *) gspca_dev;
653         __u8 gain;
654         __u8 rgb_value;
655
656         gain = sd->gain >> 4;
657
658         /* red and blue gain */
659         rgb_value = gain << 4 | gain;
660         reg_w(gspca_dev, 0x10, &rgb_value, 1);
661         /* green gain */
662         rgb_value = gain;
663         reg_w(gspca_dev, 0x11, &rgb_value, 1);
664
665         if (sd->sensor_has_gain)
666                 setsensorgain(gspca_dev);
667 }
668
669 static void setexposure(struct gspca_dev *gspca_dev)
670 {
671         struct sd *sd = (struct sd *) gspca_dev;
672
673         switch (sd->sensor) {
674         case SENSOR_TAS5110: {
675                 __u8 reg;
676
677                 /* register 19's high nibble contains the sn9c10x clock divider
678                    The high nibble configures the no fps according to the
679                    formula: 60 / high_nibble. With a maximum of 30 fps */
680                 reg = 120 * sd->exposure / 1000;
681                 if (reg < 2)
682                         reg = 2;
683                 else if (reg > 15)
684                         reg = 15;
685                 reg = (reg << 4) | 0x0b;
686                 reg_w(gspca_dev, 0x19, &reg, 1);
687                 break;
688             }
689         case SENSOR_OV6650:
690         case SENSOR_OV7630_3: {
691                 /* The ov6650 / ov7630 have 2 registers which both influence
692                    exposure, register 11, whose low nibble sets the nr off fps
693                    according to: fps = 30 / (low_nibble + 1)
694
695                    The fps configures the maximum exposure setting, but it is
696                    possible to use less exposure then what the fps maximum
697                    allows by setting register 10. register 10 configures the
698                    actual exposure as quotient of the full exposure, with 0
699                    being no exposure at all (not very usefull) and reg10_max
700                    being max exposure possible at that framerate.
701
702                    The code maps our 0 - 510 ms exposure ctrl to these 2
703                    registers, trying to keep fps as high as possible.
704                 */
705                 __u8 i2c[] = {0xb0, 0x00, 0x10, 0x00, 0xc0, 0x00, 0x00, 0x10};
706                 int reg10, reg11;
707                 /* ov6645 datasheet says reg10_max is 9a, but that uses
708                    tline * 2 * reg10 as formula for calculating texpo, the
709                    ov6650 probably uses the same formula as the 7730 which uses
710                    tline * 4 * reg10, which explains why the reg10max we've
711                    found experimentally for the ov6650 is exactly half that of
712                    the ov6645. The ov7630 datasheet says the max is 0x41. */
713                 const int reg10_max = (sd->sensor == SENSOR_OV6650)
714                                 ? 0x4d : 0x41;
715
716                 reg11 = (60 * sd->exposure + 999) / 1000;
717                 if (reg11 < 1)
718                         reg11 = 1;
719                 else if (reg11 > 16)
720                         reg11 = 16;
721
722                 /* frame exposure time in ms = 1000 * reg11 / 30    ->
723                 reg10 = sd->exposure * 2 * reg10_max / (1000 * reg11 / 30) */
724                 reg10 = (sd->exposure * 60 * reg10_max) / (1000 * reg11);
725
726                 /* Don't allow this to get below 10 when using autogain, the
727                    steps become very large (relatively) when below 10 causing
728                    the image to oscilate from much too dark, to much too bright
729                    and back again. */
730                 if (sd->autogain && reg10 < 10)
731                         reg10 = 10;
732                 else if (reg10 > reg10_max)
733                         reg10 = reg10_max;
734
735                 /* Write reg 10 and reg11 low nibble */
736                 i2c[1] = sd->sensor_addr;
737                 i2c[3] = reg10;
738                 i2c[4] |= reg11 - 1;
739                 if (sd->sensor == SENSOR_OV7630_3) {
740                         __u8 reg76 = reg10 & 0x03;
741                         __u8 i2c_reg76[] = {0xa0, 0x21, 0x76, 0x00,
742                                             0x00, 0x00, 0x00, 0x10};
743                         reg10 >>= 2;
744                         i2c_reg76[3] = reg76;
745                         if (i2c_w(gspca_dev, i2c_reg76) < 0)
746                                 PDEBUG(D_ERR, "i2c error exposure");
747                 }
748                 if (i2c_w(gspca_dev, i2c) < 0)
749                         PDEBUG(D_ERR, "i2c error exposure");
750                 break;
751             }
752         }
753 }
754
755 static void setfreq(struct gspca_dev *gspca_dev)
756 {
757         struct sd *sd = (struct sd *) gspca_dev;
758
759         switch (sd->sensor) {
760         case SENSOR_OV6650:
761         case SENSOR_OV7630_3: {
762                 /* Framerate adjust register for artificial light 50 hz flicker
763                    compensation, identical to ov6630 0x2b register, see ov6630
764                    datasheet.
765                    0x4f -> (30 fps -> 25 fps), 0x00 -> no adjustment */
766                 __u8 i2c[] = {0xa0, 0x00, 0x2b, 0x00, 0x00, 0x00, 0x00, 0x10};
767                 switch (sd->freq) {
768                 default:
769 /*              case 0:                  * no filter*/
770 /*              case 2:                  * 60 hz */
771                         i2c[3] = 0;
772                         break;
773                 case 1:                 /* 50 hz */
774                         i2c[3] = (sd->sensor == SENSOR_OV6650)
775                                         ? 0x4f : 0x8a;
776                         break;
777                 }
778                 i2c[1] = sd->sensor_addr;
779                 if (i2c_w(gspca_dev, i2c) < 0)
780                         PDEBUG(D_ERR, "i2c error setfreq");
781                 break;
782             }
783         }
784 }
785
786 static void setsaturation(struct gspca_dev *gspca_dev)
787 {
788         struct sd *sd = (struct sd *) gspca_dev;
789
790         switch (sd->sensor) {
791 /*      case SENSOR_OV6650: */
792         case SENSOR_OV7630_3:
793         case SENSOR_OV7630: {
794                 __u8 i2c[] = {0xa0, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x10};
795                 i2c[1] = sd->sensor_addr;
796                 i2c[3] = sd->saturation & 0xf0;
797                 if (i2c_w(gspca_dev, i2c) < 0)
798                         PDEBUG(D_ERR, "i2c error setsaturation");
799                 else
800                         PDEBUG(D_CONF, "saturation set to: %d",
801                                 (int)sd->saturation);
802                 break;
803             }
804         }
805 }
806
807 static void sethue(struct gspca_dev *gspca_dev)
808 {
809         struct sd *sd = (struct sd *) gspca_dev;
810
811         switch (sd->sensor) {
812 /*      case SENSOR_OV6650: */
813         case SENSOR_OV7630_3:
814         case SENSOR_OV7630: {
815                 __u8 i2c[] = {0xa0, 0x00, 0x04, 0x00, 0x00, 0x00, 0x00, 0x10};
816                 i2c[1] = sd->sensor_addr;
817                 i2c[3] = 0x20 | (sd->hue >> 3);
818                 if (i2c_w(gspca_dev, i2c) < 0)
819                         PDEBUG(D_ERR, "i2c error setsaturation");
820                 else
821                         PDEBUG(D_CONF, "hue set to: %d", (int)sd->hue);
822                 break;
823             }
824         }
825 }
826
827 static void setcontrast(struct gspca_dev *gspca_dev)
828 {
829         struct sd *sd = (struct sd *) gspca_dev;
830
831         switch (sd->sensor) {
832 /*      case SENSOR_OV6650: */
833         case SENSOR_OV7630_3:
834         case SENSOR_OV7630: {
835                 __u8 i2c[] = {0xa0, 0x00, 0x05, 0x00, 0x00, 0x00, 0x00, 0x10};
836                 i2c[1] = sd->sensor_addr;
837                 i2c[3] = 0x20 | (sd->contrast >> 3);
838                 if (i2c_w(gspca_dev, i2c) < 0)
839                         PDEBUG(D_ERR, "i2c error setcontrast");
840                 else
841                         PDEBUG(D_CONF, "contrast set to: %d",
842                                 (int)sd->contrast);
843                 break;
844             }
845         }
846 }
847
848
849 static void do_autogain(struct gspca_dev *gspca_dev)
850 {
851         struct sd *sd = (struct sd *) gspca_dev;
852         int avg_lum = atomic_read(&sd->avg_lum);
853
854         if (avg_lum == -1)
855                 return;
856
857         if (sd->autogain_ignore_frames > 0)
858                 sd->autogain_ignore_frames--;
859         else if (gspca_auto_gain_n_exposure(gspca_dev, avg_lum,
860                         sd->brightness * DESIRED_AVG_LUM / 127,
861                         AUTOGAIN_DEADZONE, GAIN_KNEE, EXPOSURE_KNEE)) {
862                 PDEBUG(D_FRAM, "autogain: gain changed: gain: %d expo: %d\n",
863                         (int)sd->gain, (int)sd->exposure);
864                 sd->autogain_ignore_frames = AUTOGAIN_IGNORE_FRAMES;
865         }
866 }
867
868 /* this function is called at probe time */
869 static int sd_config(struct gspca_dev *gspca_dev,
870                         const struct usb_device_id *id)
871 {
872         struct sd *sd = (struct sd *) gspca_dev;
873         struct cam *cam;
874         __u16 product;
875         int sif = 0;
876
877         /* nctrls depends upon the sensor, so we use a per cam copy */
878         memcpy(&sd->sd_desc, gspca_dev->sd_desc, sizeof(struct sd_desc));
879         gspca_dev->sd_desc = &sd->sd_desc;
880
881         sd->fr_h_sz = 12;               /* default size of the frame header */
882         sd->sd_desc.nctrls = 2;         /* default nb of ctrls */
883         sd->autogain = AUTOGAIN_DEF;    /* default is autogain active */
884
885         product = id->idProduct;
886 /*      switch (id->idVendor) { */
887 /*      case 0x0c45:                             * Sonix */
888                 switch (product) {
889                 case 0x6001:                    /* SN9C102 */
890                 case 0x6005:                    /* SN9C101 */
891                 case 0x6007:                    /* SN9C101 */
892                         sd->sensor = SENSOR_TAS5110;
893                         sd->sensor_has_gain = 1;
894                         sd->sd_desc.nctrls = 4;
895                         sd->sd_desc.dq_callback = do_autogain;
896                         sif = 1;
897                         break;
898                 case 0x6009:                    /* SN9C101 */
899                 case 0x600d:                    /* SN9C101 */
900                 case 0x6029:                    /* SN9C101 */
901                         sd->sensor = SENSOR_PAS106;
902                         sif = 1;
903                         break;
904                 case 0x6011:                    /* SN9C101 - SN9C101G */
905                         sd->sensor = SENSOR_OV6650;
906                         sd->sensor_has_gain = 1;
907                         sd->sensor_addr = 0x60;
908                         sd->sd_desc.nctrls = 5;
909                         sd->sd_desc.dq_callback = do_autogain;
910                         sif = 1;
911                         break;
912                 case 0x6019:                    /* SN9C101 */
913                 case 0x602c:                    /* SN9C102 */
914                 case 0x602e:                    /* SN9C102 */
915                         sd->sensor = SENSOR_OV7630;
916                         sd->sensor_addr = 0x21;
917                         break;
918                 case 0x60b0:                    /* SN9C103 */
919                         sd->sensor = SENSOR_OV7630_3;
920                         sd->sensor_addr = 0x21;
921                         sd->fr_h_sz = 18;       /* size of frame header */
922                         sd->sensor_has_gain = 1;
923                         sd->sd_desc.nctrls = 8;
924                         sd->sd_desc.dq_callback = do_autogain;
925                         sd->autogain = 0;
926                         break;
927                 case 0x6024:                    /* SN9C102 */
928                 case 0x6025:                    /* SN9C102 */
929                         sd->sensor = SENSOR_TAS5130CXX;
930                         break;
931                 case 0x6028:                    /* SN9C102 */
932                         sd->sensor = SENSOR_PAS202;
933                         break;
934                 case 0x602d:                    /* SN9C102 */
935                         sd->sensor = SENSOR_HV7131R;
936                         break;
937                 case 0x60af:                    /* SN9C103 */
938                         sd->sensor = SENSOR_PAS202;
939                         sd->fr_h_sz = 18;       /* size of frame header (?) */
940                         break;
941                 }
942 /*              break; */
943 /*      } */
944
945         cam = &gspca_dev->cam;
946         cam->dev_name = (char *) id->driver_info;
947         cam->epaddr = 0x01;
948         if (!sif) {
949                 cam->cam_mode = vga_mode;
950                 cam->nmodes = ARRAY_SIZE(vga_mode);
951                 if (sd->sensor == SENSOR_OV7630_3) {
952                         /* We only have 320x240 & 640x480 */
953                         cam->cam_mode++;
954                         cam->nmodes--;
955                 }
956         } else {
957                 cam->cam_mode = sif_mode;
958                 cam->nmodes = ARRAY_SIZE(sif_mode);
959         }
960         sd->brightness = BRIGHTNESS_DEF;
961         sd->gain = GAIN_DEF;
962         sd->exposure = EXPOSURE_DEF;
963         sd->freq = FREQ_DEF;
964         sd->contrast = CONTRAST_DEF;
965         sd->saturation = SATURATION_DEF;
966         sd->hue = HUE_DEF;
967         if (sd->sensor == SENSOR_OV7630_3)      /* jfm: from win trace */
968                 reg_w(gspca_dev, 0x01, probe_ov7630, sizeof probe_ov7630);
969         return 0;
970 }
971
972 /* this function is called at open time */
973 static int sd_open(struct gspca_dev *gspca_dev)
974 {
975         reg_r(gspca_dev, 0x00);
976         if (gspca_dev->usb_buf[0] != 0x10)
977                 return -ENODEV;
978         return 0;
979 }
980
981 static void pas106_i2cinit(struct gspca_dev *gspca_dev)
982 {
983         int i;
984         const __u8 *data;
985         __u8 i2c1[] = { 0xa1, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x14 };
986
987         i = ARRAY_SIZE(pas106_data);
988         data = pas106_data[0];
989         while (--i >= 0) {
990                 memcpy(&i2c1[2], data, 2);
991                                         /* copy 2 bytes from the template */
992                 if (i2c_w(gspca_dev, i2c1) < 0)
993                         PDEBUG(D_ERR, "i2c error pas106");
994                 data += 2;
995         }
996 }
997
998 /* -- start the camera -- */
999 static void sd_start(struct gspca_dev *gspca_dev)
1000 {
1001         struct sd *sd = (struct sd *) gspca_dev;
1002         int mode, l;
1003         const __u8 *sn9c10x;
1004         __u8 reg01, reg17;
1005         __u8 reg17_19[3];
1006
1007         mode = gspca_dev->cam.cam_mode[(int) gspca_dev->curr_mode].priv;
1008         switch (sd->sensor) {
1009         case SENSOR_HV7131R:
1010                 sn9c10x = initHv7131;
1011                 reg17_19[0] = 0x60;
1012                 reg17_19[1] = (mode << 4) | 0x8a;
1013                 reg17_19[2] = 0x20;
1014                 break;
1015         case SENSOR_OV6650:
1016                 sn9c10x = initOv6650;
1017                 reg17_19[0] = 0x68;
1018                 reg17_19[1] = (mode << 4) | 0x8b;
1019                 reg17_19[2] = 0x20;
1020                 break;
1021         case SENSOR_OV7630:
1022                 sn9c10x = initOv7630;
1023                 reg17_19[0] = 0x68;
1024                 reg17_19[1] = (mode << 4) | COMP2;
1025                 reg17_19[2] = MCK_INIT1;
1026                 break;
1027         case SENSOR_OV7630_3:
1028                 sn9c10x = initOv7630_3;
1029                 reg17_19[0] = 0x68;
1030                 reg17_19[1] = (mode << 4) | COMP2;
1031                 reg17_19[2] = MCK_INIT1;
1032                 break;
1033         case SENSOR_PAS106:
1034                 sn9c10x = initPas106;
1035                 reg17_19[0] = 0x24;             /* 0x28 */
1036                 reg17_19[1] = (mode << 4) | COMP1;
1037                 reg17_19[2] = MCK_INIT1;
1038                 break;
1039         case SENSOR_PAS202:
1040                 sn9c10x = initPas202;
1041                 reg17_19[0] = mode ? 0x24 : 0x20;
1042                 reg17_19[1] = (mode << 4) | 0x89;
1043                 reg17_19[2] = 0x20;
1044                 break;
1045         case SENSOR_TAS5110:
1046                 sn9c10x = initTas5110;
1047                 reg17_19[0] = 0x60;
1048                 reg17_19[1] = (mode << 4) | 0x86;
1049                 reg17_19[2] = 0x2b;             /* 0xf3; */
1050                 break;
1051         default:
1052 /*      case SENSOR_TAS5130CXX: */
1053                 sn9c10x = initTas5130;
1054                 reg17_19[0] = 0x60;
1055                 reg17_19[1] = (mode << 4) | COMP;
1056                 reg17_19[2] = mode ? 0x23 : 0x43;
1057                 break;
1058         }
1059         switch (sd->sensor) {
1060         case SENSOR_OV7630:
1061                 reg01 = 0x06;
1062                 reg17 = 0x29;
1063                 l = sizeof initOv7630;
1064                 break;
1065         case SENSOR_OV7630_3:
1066                 reg01 = 0x44;
1067                 reg17 = 0x68;
1068                 l = sizeof initOv7630_3;
1069                 break;
1070         default:
1071                 reg01 = sn9c10x[0];
1072                 reg17 = sn9c10x[0x17 - 1];
1073                 l = 0x1f;
1074                 break;
1075         }
1076
1077         /* reg 0x01 bit 2 video transfert on */
1078         reg_w(gspca_dev, 0x01, &reg01, 1);
1079         /* reg 0x17 SensorClk enable inv Clk 0x60 */
1080         reg_w(gspca_dev, 0x17, &reg17, 1);
1081 /*fixme: for ov7630 102
1082         reg_w(gspca_dev, 0x01, {0x06, sn9c10x[1]}, 2); */
1083         /* Set the registers from the template */
1084         reg_w_big(gspca_dev, 0x01, sn9c10x, l);
1085         switch (sd->sensor) {
1086         case SENSOR_HV7131R:
1087                 i2c_w_vector(gspca_dev, hv7131_sensor_init,
1088                                 sizeof hv7131_sensor_init);
1089                 break;
1090         case SENSOR_OV6650:
1091                 i2c_w_vector(gspca_dev, ov6650_sensor_init,
1092                                 sizeof ov6650_sensor_init);
1093                 break;
1094         case SENSOR_OV7630:
1095                 i2c_w_vector(gspca_dev, ov7630_sensor_init_com,
1096                                 sizeof ov7630_sensor_init_com);
1097                 msleep(200);
1098                 i2c_w_vector(gspca_dev, ov7630_sensor_init,
1099                                 sizeof ov7630_sensor_init);
1100                 break;
1101         case SENSOR_OV7630_3:
1102                 i2c_w_vector(gspca_dev, ov7630_sensor_init_com,
1103                                 sizeof ov7630_sensor_init_com);
1104                 msleep(200);
1105                 i2c_w(gspca_dev, ov7630_sensor_init_3[mode]);
1106                 break;
1107         case SENSOR_PAS106:
1108                 pas106_i2cinit(gspca_dev);
1109                 break;
1110         case SENSOR_PAS202:
1111                 i2c_w_vector(gspca_dev, pas202_sensor_init,
1112                                 sizeof pas202_sensor_init);
1113                 break;
1114         case SENSOR_TAS5110:
1115                 i2c_w_vector(gspca_dev, tas5110_sensor_init,
1116                                 sizeof tas5110_sensor_init);
1117                 break;
1118         default:
1119 /*      case SENSOR_TAS5130CXX: */
1120                 i2c_w_vector(gspca_dev, tas5130_sensor_init,
1121                                 sizeof tas5130_sensor_init);
1122                 break;
1123         }
1124         /* H_size V_size 0x28, 0x1e -> 640x480. 0x16, 0x12 -> 352x288 */
1125         reg_w(gspca_dev, 0x15, &sn9c10x[0x15 - 1], 2);
1126         /* compression register */
1127         reg_w(gspca_dev, 0x18, &reg17_19[1], 1);
1128         /* H_start */
1129         reg_w(gspca_dev, 0x12, &sn9c10x[0x12 - 1], 1);
1130         /* V_START */
1131         reg_w(gspca_dev, 0x13, &sn9c10x[0x13 - 1], 1);
1132         /* reset 0x17 SensorClk enable inv Clk 0x60 */
1133                                 /*fixme: ov7630 [17]=68 8f (+20 if 102)*/
1134         reg_w(gspca_dev, 0x17, &reg17_19[0], 1);
1135         /*MCKSIZE ->3 */        /*fixme: not ov7630*/
1136         reg_w(gspca_dev, 0x19, &reg17_19[2], 1);
1137         /* AE_STRX AE_STRY AE_ENDX AE_ENDY */
1138         reg_w(gspca_dev, 0x1c, &sn9c10x[0x1c - 1], 4);
1139         /* Enable video transfert */
1140         reg_w(gspca_dev, 0x01, &sn9c10x[0], 1);
1141         /* Compression */
1142         reg_w(gspca_dev, 0x18, &reg17_19[1], 2);
1143         msleep(20);
1144
1145         setgain(gspca_dev);
1146         setbrightness(gspca_dev);
1147         setexposure(gspca_dev);
1148         setfreq(gspca_dev);
1149         setsaturation(gspca_dev);
1150         sethue(gspca_dev);
1151         setcontrast(gspca_dev);
1152
1153         sd->autogain_ignore_frames = 0;
1154         atomic_set(&sd->avg_lum, -1);
1155 }
1156
1157 static void sd_stopN(struct gspca_dev *gspca_dev)
1158 {
1159         __u8 ByteSend;
1160
1161         ByteSend = 0x09;        /* 0X00 */
1162         reg_w(gspca_dev, 0x01, &ByteSend, 1);
1163 }
1164
1165 static void sd_stop0(struct gspca_dev *gspca_dev)
1166 {
1167 }
1168
1169 static void sd_close(struct gspca_dev *gspca_dev)
1170 {
1171 }
1172
1173 static void sd_pkt_scan(struct gspca_dev *gspca_dev,
1174                         struct gspca_frame *frame,      /* target */
1175                         unsigned char *data,            /* isoc packet */
1176                         int len)                        /* iso packet length */
1177 {
1178         int i;
1179         struct sd *sd = (struct sd *) gspca_dev;
1180
1181         /* frames start with:
1182          *      ff ff 00 c4 c4 96       synchro
1183          *      00              (unknown)
1184          *      xx              (frame sequence / size / compression)
1185          *      (xx)            (idem - extra byte for sn9c103)
1186          *      ll mm           brightness sum inside auto exposure
1187          *      ll mm           brightness sum outside auto exposure
1188          *      (xx xx xx xx xx)        audio values for snc103
1189          */
1190         if (len > 6 && len < 24) {
1191                 for (i = 0; i < len - 6; i++) {
1192                         if (data[0 + i] == 0xff
1193                             && data[1 + i] == 0xff
1194                             && data[2 + i] == 0x00
1195                             && data[3 + i] == 0xc4
1196                             && data[4 + i] == 0xc4
1197                             && data[5 + i] == 0x96) {   /* start of frame */
1198                                 frame = gspca_frame_add(gspca_dev, LAST_PACKET,
1199                                                         frame, data, 0);
1200                                 if (len - i < sd->fr_h_sz) {
1201                                         atomic_set(&sd->avg_lum, -1);
1202                                         PDEBUG(D_STREAM, "packet too short to"
1203                                                 " get avg brightness");
1204                                 } else if (sd->fr_h_sz == 12) {
1205                                         atomic_set(&sd->avg_lum,
1206                                                 data[i + 8] +
1207                                                         (data[i + 9] << 8));
1208                                 } else {
1209                                         atomic_set(&sd->avg_lum,
1210                                                 data[i + 9] +
1211                                                         (data[i + 10] << 8));
1212                                 }
1213                                 data += i + sd->fr_h_sz;
1214                                 len -= i + sd->fr_h_sz;
1215                                 gspca_frame_add(gspca_dev, FIRST_PACKET,
1216                                                 frame, data, len);
1217                                 return;
1218                         }
1219                 }
1220         }
1221         gspca_frame_add(gspca_dev, INTER_PACKET,
1222                         frame, data, len);
1223 }
1224
1225 static int sd_setbrightness(struct gspca_dev *gspca_dev, __s32 val)
1226 {
1227         struct sd *sd = (struct sd *) gspca_dev;
1228
1229         sd->brightness = val;
1230         if (gspca_dev->streaming)
1231                 setbrightness(gspca_dev);
1232         return 0;
1233 }
1234
1235 static int sd_getbrightness(struct gspca_dev *gspca_dev, __s32 *val)
1236 {
1237         struct sd *sd = (struct sd *) gspca_dev;
1238
1239         *val = sd->brightness;
1240         return 0;
1241 }
1242
1243 static int sd_setgain(struct gspca_dev *gspca_dev, __s32 val)
1244 {
1245         struct sd *sd = (struct sd *) gspca_dev;
1246
1247         sd->gain = val;
1248         if (gspca_dev->streaming)
1249                 setgain(gspca_dev);
1250         return 0;
1251 }
1252
1253 static int sd_getgain(struct gspca_dev *gspca_dev, __s32 *val)
1254 {
1255         struct sd *sd = (struct sd *) gspca_dev;
1256
1257         *val = sd->gain;
1258         return 0;
1259 }
1260
1261 static int sd_setexposure(struct gspca_dev *gspca_dev, __s32 val)
1262 {
1263         struct sd *sd = (struct sd *) gspca_dev;
1264
1265         sd->exposure = val;
1266         if (gspca_dev->streaming)
1267                 setexposure(gspca_dev);
1268         return 0;
1269 }
1270
1271 static int sd_getexposure(struct gspca_dev *gspca_dev, __s32 *val)
1272 {
1273         struct sd *sd = (struct sd *) gspca_dev;
1274
1275         *val = sd->exposure;
1276         return 0;
1277 }
1278
1279 static int sd_setautogain(struct gspca_dev *gspca_dev, __s32 val)
1280 {
1281         struct sd *sd = (struct sd *) gspca_dev;
1282
1283         sd->autogain = val;
1284         /* when switching to autogain set defaults to make sure
1285            we are on a valid point of the autogain gain /
1286            exposure knee graph, and give this change time to
1287            take effect before doing autogain. */
1288         if (sd->autogain) {
1289                 sd->exposure = EXPOSURE_DEF;
1290                 sd->gain = GAIN_DEF;
1291                 if (gspca_dev->streaming) {
1292                         sd->autogain_ignore_frames = AUTOGAIN_IGNORE_FRAMES;
1293                         setexposure(gspca_dev);
1294                         setgain(gspca_dev);
1295                 }
1296         }
1297
1298         return 0;
1299 }
1300
1301 static int sd_getautogain(struct gspca_dev *gspca_dev, __s32 *val)
1302 {
1303         struct sd *sd = (struct sd *) gspca_dev;
1304
1305         *val = sd->autogain;
1306         return 0;
1307 }
1308
1309 static int sd_setfreq(struct gspca_dev *gspca_dev, __s32 val)
1310 {
1311         struct sd *sd = (struct sd *) gspca_dev;
1312
1313         sd->freq = val;
1314         if (gspca_dev->streaming)
1315                 setfreq(gspca_dev);
1316         return 0;
1317 }
1318
1319 static int sd_getfreq(struct gspca_dev *gspca_dev, __s32 *val)
1320 {
1321         struct sd *sd = (struct sd *) gspca_dev;
1322
1323         *val = sd->freq;
1324         return 0;
1325 }
1326
1327 static int sd_setsaturation(struct gspca_dev *gspca_dev, __s32 val)
1328 {
1329         struct sd *sd = (struct sd *) gspca_dev;
1330
1331         sd->saturation = val;
1332         if (gspca_dev->streaming)
1333                 setsaturation(gspca_dev);
1334         return 0;
1335 }
1336
1337 static int sd_getsaturation(struct gspca_dev *gspca_dev, __s32 *val)
1338 {
1339         struct sd *sd = (struct sd *) gspca_dev;
1340
1341         *val = sd->saturation;
1342         return 0;
1343 }
1344
1345 static int sd_sethue(struct gspca_dev *gspca_dev, __s32 val)
1346 {
1347         struct sd *sd = (struct sd *) gspca_dev;
1348
1349         sd->hue = val;
1350         if (gspca_dev->streaming)
1351                 sethue(gspca_dev);
1352         return 0;
1353 }
1354
1355 static int sd_gethue(struct gspca_dev *gspca_dev, __s32 *val)
1356 {
1357         struct sd *sd = (struct sd *) gspca_dev;
1358
1359         *val = sd->hue;
1360         return 0;
1361 }
1362
1363 static int sd_setcontrast(struct gspca_dev *gspca_dev, __s32 val)
1364 {
1365         struct sd *sd = (struct sd *) gspca_dev;
1366
1367         sd->contrast = val;
1368         if (gspca_dev->streaming)
1369                 setcontrast(gspca_dev);
1370         return 0;
1371 }
1372
1373 static int sd_getcontrast(struct gspca_dev *gspca_dev, __s32 *val)
1374 {
1375         struct sd *sd = (struct sd *) gspca_dev;
1376
1377         *val = sd->contrast;
1378         return 0;
1379 }
1380
1381 static int sd_querymenu(struct gspca_dev *gspca_dev,
1382                         struct v4l2_querymenu *menu)
1383 {
1384         switch (menu->id) {
1385         case V4L2_CID_POWER_LINE_FREQUENCY:
1386                 switch (menu->index) {
1387                 case 0:         /* V4L2_CID_POWER_LINE_FREQUENCY_DISABLED */
1388                         strcpy((char *) menu->name, "NoFliker");
1389                         return 0;
1390                 case 1:         /* V4L2_CID_POWER_LINE_FREQUENCY_50HZ */
1391                         strcpy((char *) menu->name, "50 Hz");
1392                         return 0;
1393                 case 2:         /* V4L2_CID_POWER_LINE_FREQUENCY_60HZ */
1394                         strcpy((char *) menu->name, "60 Hz");
1395                         return 0;
1396                 }
1397                 break;
1398         }
1399         return -EINVAL;
1400 }
1401
1402 /* sub-driver description */
1403 static const struct sd_desc sd_desc = {
1404         .name = MODULE_NAME,
1405         .ctrls = sd_ctrls,
1406         .nctrls = ARRAY_SIZE(sd_ctrls),
1407         .config = sd_config,
1408         .open = sd_open,
1409         .start = sd_start,
1410         .stopN = sd_stopN,
1411         .stop0 = sd_stop0,
1412         .close = sd_close,
1413         .pkt_scan = sd_pkt_scan,
1414         .querymenu = sd_querymenu,
1415 };
1416
1417 /* -- module initialisation -- */
1418 #define DVNM(name) .driver_info = (kernel_ulong_t) name
1419 static __devinitdata struct usb_device_id device_table[] = {
1420 #ifndef CONFIG_USB_SN9C102
1421         {USB_DEVICE(0x0c45, 0x6001), DVNM("Genius VideoCAM NB")},
1422         {USB_DEVICE(0x0c45, 0x6005), DVNM("Sweex Tas5110")},
1423         {USB_DEVICE(0x0c45, 0x6007), DVNM("Sonix sn9c101 + Tas5110D")},
1424         {USB_DEVICE(0x0c45, 0x6009), DVNM("spcaCam@120")},
1425         {USB_DEVICE(0x0c45, 0x600d), DVNM("spcaCam@120")},
1426 #endif
1427         {USB_DEVICE(0x0c45, 0x6011), DVNM("MAX Webcam Microdia")},
1428 #ifndef CONFIG_USB_SN9C102
1429         {USB_DEVICE(0x0c45, 0x6019), DVNM("Generic Sonix OV7630")},
1430         {USB_DEVICE(0x0c45, 0x6024), DVNM("Generic Sonix Tas5130c")},
1431         {USB_DEVICE(0x0c45, 0x6025), DVNM("Xcam Shanga")},
1432         {USB_DEVICE(0x0c45, 0x6028), DVNM("Sonix Btc Pc380")},
1433         {USB_DEVICE(0x0c45, 0x6029), DVNM("spcaCam@150")},
1434         {USB_DEVICE(0x0c45, 0x602c), DVNM("Generic Sonix OV7630")},
1435         {USB_DEVICE(0x0c45, 0x602d), DVNM("LIC-200 LG")},
1436         {USB_DEVICE(0x0c45, 0x602e), DVNM("Genius VideoCam Messenger")},
1437         {USB_DEVICE(0x0c45, 0x60af), DVNM("Trust WB3100P")},
1438         {USB_DEVICE(0x0c45, 0x60b0), DVNM("Genius VideoCam Look")},
1439 #endif
1440         {}
1441 };
1442 MODULE_DEVICE_TABLE(usb, device_table);
1443
1444 /* -- device connect -- */
1445 static int sd_probe(struct usb_interface *intf,
1446                         const struct usb_device_id *id)
1447 {
1448         return gspca_dev_probe(intf, id, &sd_desc, sizeof(struct sd),
1449                                 THIS_MODULE);
1450 }
1451
1452 static struct usb_driver sd_driver = {
1453         .name = MODULE_NAME,
1454         .id_table = device_table,
1455         .probe = sd_probe,
1456         .disconnect = gspca_disconnect,
1457 };
1458
1459 /* -- module insert / remove -- */
1460 static int __init sd_mod_init(void)
1461 {
1462         if (usb_register(&sd_driver) < 0)
1463                 return -1;
1464         PDEBUG(D_PROBE, "registered");
1465         return 0;
1466 }
1467 static void __exit sd_mod_exit(void)
1468 {
1469         usb_deregister(&sd_driver);
1470         PDEBUG(D_PROBE, "deregistered");
1471 }
1472
1473 module_init(sd_mod_init);
1474 module_exit(sd_mod_exit);