Merge branch 'topic/usb-audio' into for-linus
[pandora-kernel.git] / drivers / media / video / gspca / sunplus.c
1 /*
2  *              Sunplus spca504(abc) spca533 spca536 library
3  *              Copyright (C) 2005 Michel Xhaard mxhaard@magic.fr
4  *
5  * V4L2 by Jean-Francois Moine <http://moinejf.free.fr>
6  *
7  * This program is free software; you can redistribute it and/or modify
8  * it under the terms of the GNU General Public License as published by
9  * the Free Software Foundation; either version 2 of the License, or
10  * any later version.
11  *
12  * This program is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15  * GNU General Public License for more details.
16  *
17  * You should have received a copy of the GNU General Public License
18  * along with this program; if not, write to the Free Software
19  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
20  */
21
22 #define MODULE_NAME "sunplus"
23
24 #include "gspca.h"
25 #include "jpeg.h"
26
27 MODULE_AUTHOR("Michel Xhaard <mxhaard@users.sourceforge.net>");
28 MODULE_DESCRIPTION("GSPCA/SPCA5xx 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         unsigned char brightness;
36         unsigned char contrast;
37         unsigned char colors;
38         unsigned char autogain;
39         u8 quality;
40 #define QUALITY_MIN 70
41 #define QUALITY_MAX 95
42 #define QUALITY_DEF 85
43
44         char bridge;
45 #define BRIDGE_SPCA504 0
46 #define BRIDGE_SPCA504B 1
47 #define BRIDGE_SPCA504C 2
48 #define BRIDGE_SPCA533 3
49 #define BRIDGE_SPCA536 4
50         char subtype;
51 #define AiptekMiniPenCam13 1
52 #define LogitechClickSmart420 2
53 #define LogitechClickSmart820 3
54 #define MegapixV4 4
55
56         u8 *jpeg_hdr;
57 };
58
59 /* V4L2 controls supported by the driver */
60 static int sd_setbrightness(struct gspca_dev *gspca_dev, __s32 val);
61 static int sd_getbrightness(struct gspca_dev *gspca_dev, __s32 *val);
62 static int sd_setcontrast(struct gspca_dev *gspca_dev, __s32 val);
63 static int sd_getcontrast(struct gspca_dev *gspca_dev, __s32 *val);
64 static int sd_setcolors(struct gspca_dev *gspca_dev, __s32 val);
65 static int sd_getcolors(struct gspca_dev *gspca_dev, __s32 *val);
66 static int sd_setautogain(struct gspca_dev *gspca_dev, __s32 val);
67 static int sd_getautogain(struct gspca_dev *gspca_dev, __s32 *val);
68
69 static struct ctrl sd_ctrls[] = {
70 #define SD_BRIGHTNESS 0
71         {
72             {
73                 .id      = V4L2_CID_BRIGHTNESS,
74                 .type    = V4L2_CTRL_TYPE_INTEGER,
75                 .name    = "Brightness",
76                 .minimum = 0,
77                 .maximum = 0xff,
78                 .step    = 1,
79                 .default_value = 0,
80             },
81             .set = sd_setbrightness,
82             .get = sd_getbrightness,
83         },
84 #define SD_CONTRAST 1
85         {
86             {
87                 .id      = V4L2_CID_CONTRAST,
88                 .type    = V4L2_CTRL_TYPE_INTEGER,
89                 .name    = "Contrast",
90                 .minimum = 0,
91                 .maximum = 0xff,
92                 .step    = 1,
93                 .default_value = 0x20,
94             },
95             .set = sd_setcontrast,
96             .get = sd_getcontrast,
97         },
98 #define SD_COLOR 2
99         {
100             {
101                 .id      = V4L2_CID_SATURATION,
102                 .type    = V4L2_CTRL_TYPE_INTEGER,
103                 .name    = "Color",
104                 .minimum = 0,
105                 .maximum = 0xff,
106                 .step    = 1,
107                 .default_value = 0x1a,
108             },
109             .set = sd_setcolors,
110             .get = sd_getcolors,
111         },
112 #define SD_AUTOGAIN 3
113         {
114             {
115                 .id      = V4L2_CID_AUTOGAIN,
116                 .type    = V4L2_CTRL_TYPE_BOOLEAN,
117                 .name    = "Auto Gain",
118                 .minimum = 0,
119                 .maximum = 1,
120                 .step    = 1,
121                 .default_value = 1,
122             },
123             .set = sd_setautogain,
124             .get = sd_getautogain,
125         },
126 };
127
128 static const struct v4l2_pix_format vga_mode[] = {
129         {320, 240, V4L2_PIX_FMT_JPEG, V4L2_FIELD_NONE,
130                 .bytesperline = 320,
131                 .sizeimage = 320 * 240 * 3 / 8 + 590,
132                 .colorspace = V4L2_COLORSPACE_JPEG,
133                 .priv = 2},
134         {640, 480, V4L2_PIX_FMT_JPEG, V4L2_FIELD_NONE,
135                 .bytesperline = 640,
136                 .sizeimage = 640 * 480 * 3 / 8 + 590,
137                 .colorspace = V4L2_COLORSPACE_JPEG,
138                 .priv = 1},
139 };
140
141 static const struct v4l2_pix_format custom_mode[] = {
142         {320, 240, V4L2_PIX_FMT_JPEG, V4L2_FIELD_NONE,
143                 .bytesperline = 320,
144                 .sizeimage = 320 * 240 * 3 / 8 + 590,
145                 .colorspace = V4L2_COLORSPACE_JPEG,
146                 .priv = 2},
147         {464, 480, V4L2_PIX_FMT_JPEG, V4L2_FIELD_NONE,
148                 .bytesperline = 464,
149                 .sizeimage = 464 * 480 * 3 / 8 + 590,
150                 .colorspace = V4L2_COLORSPACE_JPEG,
151                 .priv = 1},
152 };
153
154 static const struct v4l2_pix_format vga_mode2[] = {
155         {176, 144, V4L2_PIX_FMT_JPEG, V4L2_FIELD_NONE,
156                 .bytesperline = 176,
157                 .sizeimage = 176 * 144 * 3 / 8 + 590,
158                 .colorspace = V4L2_COLORSPACE_JPEG,
159                 .priv = 4},
160         {320, 240, V4L2_PIX_FMT_JPEG, V4L2_FIELD_NONE,
161                 .bytesperline = 320,
162                 .sizeimage = 320 * 240 * 3 / 8 + 590,
163                 .colorspace = V4L2_COLORSPACE_JPEG,
164                 .priv = 3},
165         {352, 288, V4L2_PIX_FMT_JPEG, V4L2_FIELD_NONE,
166                 .bytesperline = 352,
167                 .sizeimage = 352 * 288 * 3 / 8 + 590,
168                 .colorspace = V4L2_COLORSPACE_JPEG,
169                 .priv = 2},
170         {640, 480, V4L2_PIX_FMT_JPEG, V4L2_FIELD_NONE,
171                 .bytesperline = 640,
172                 .sizeimage = 640 * 480 * 3 / 8 + 590,
173                 .colorspace = V4L2_COLORSPACE_JPEG,
174                 .priv = 1},
175 };
176
177 #define SPCA50X_OFFSET_DATA 10
178 #define SPCA504_PCCAM600_OFFSET_SNAPSHOT 3
179 #define SPCA504_PCCAM600_OFFSET_COMPRESS 4
180 #define SPCA504_PCCAM600_OFFSET_MODE     5
181 #define SPCA504_PCCAM600_OFFSET_DATA     14
182  /* Frame packet header offsets for the spca533 */
183 #define SPCA533_OFFSET_DATA      16
184 #define SPCA533_OFFSET_FRAMSEQ  15
185 /* Frame packet header offsets for the spca536 */
186 #define SPCA536_OFFSET_DATA      4
187 #define SPCA536_OFFSET_FRAMSEQ   1
188
189 /* Initialisation data for the Creative PC-CAM 600 */
190 static const __u16 spca504_pccam600_init_data[][3] = {
191 /*      {0xa0, 0x0000, 0x0503},  * capture mode */
192         {0x00, 0x0000, 0x2000},
193         {0x00, 0x0013, 0x2301},
194         {0x00, 0x0003, 0x2000},
195         {0x00, 0x0001, 0x21ac},
196         {0x00, 0x0001, 0x21a6},
197         {0x00, 0x0000, 0x21a7}, /* brightness */
198         {0x00, 0x0020, 0x21a8}, /* contrast */
199         {0x00, 0x0001, 0x21ac}, /* sat/hue */
200         {0x00, 0x0000, 0x21ad}, /* hue */
201         {0x00, 0x001a, 0x21ae}, /* saturation */
202         {0x00, 0x0002, 0x21a3}, /* gamma */
203         {0x30, 0x0154, 0x0008},
204         {0x30, 0x0004, 0x0006},
205         {0x30, 0x0258, 0x0009},
206         {0x30, 0x0004, 0x0000},
207         {0x30, 0x0093, 0x0004},
208         {0x30, 0x0066, 0x0005},
209         {0x00, 0x0000, 0x2000},
210         {0x00, 0x0013, 0x2301},
211         {0x00, 0x0003, 0x2000},
212         {0x00, 0x0013, 0x2301},
213         {0x00, 0x0003, 0x2000},
214         {}
215 };
216
217 /* Creative PC-CAM 600 specific open data, sent before using the
218  * generic initialisation data from spca504_open_data.
219  */
220 static const __u16 spca504_pccam600_open_data[][3] = {
221         {0x00, 0x0001, 0x2501},
222         {0x20, 0x0500, 0x0001}, /* snapshot mode */
223         {0x00, 0x0003, 0x2880},
224         {0x00, 0x0001, 0x2881},
225         {}
226 };
227
228 /* Initialisation data for the logitech clicksmart 420 */
229 static const __u16 spca504A_clicksmart420_init_data[][3] = {
230 /*      {0xa0, 0x0000, 0x0503},  * capture mode */
231         {0x00, 0x0000, 0x2000},
232         {0x00, 0x0013, 0x2301},
233         {0x00, 0x0003, 0x2000},
234         {0x00, 0x0001, 0x21ac},
235         {0x00, 0x0001, 0x21a6},
236         {0x00, 0x0000, 0x21a7}, /* brightness */
237         {0x00, 0x0020, 0x21a8}, /* contrast */
238         {0x00, 0x0001, 0x21ac}, /* sat/hue */
239         {0x00, 0x0000, 0x21ad}, /* hue */
240         {0x00, 0x001a, 0x21ae}, /* saturation */
241         {0x00, 0x0002, 0x21a3}, /* gamma */
242         {0x30, 0x0004, 0x000a},
243         {0xb0, 0x0001, 0x0000},
244
245
246         {0x0a1, 0x0080, 0x0001},
247         {0x30, 0x0049, 0x0000},
248         {0x30, 0x0060, 0x0005},
249         {0x0c, 0x0004, 0x0000},
250         {0x00, 0x0000, 0x0000},
251         {0x00, 0x0000, 0x2000},
252         {0x00, 0x0013, 0x2301},
253         {0x00, 0x0003, 0x2000},
254         {0x00, 0x0000, 0x2000},
255
256         {}
257 };
258
259 /* clicksmart 420 open data ? */
260 static const __u16 spca504A_clicksmart420_open_data[][3] = {
261         {0x00, 0x0001, 0x2501},
262         {0x20, 0x0502, 0x0000},
263         {0x06, 0x0000, 0x0000},
264         {0x00, 0x0004, 0x2880},
265         {0x00, 0x0001, 0x2881},
266 /* look like setting a qTable */
267         {0x00, 0x0006, 0x2800},
268         {0x00, 0x0004, 0x2801},
269         {0x00, 0x0004, 0x2802},
270         {0x00, 0x0006, 0x2803},
271         {0x00, 0x000a, 0x2804},
272         {0x00, 0x0010, 0x2805},
273         {0x00, 0x0014, 0x2806},
274         {0x00, 0x0018, 0x2807},
275         {0x00, 0x0005, 0x2808},
276         {0x00, 0x0005, 0x2809},
277         {0x00, 0x0006, 0x280a},
278         {0x00, 0x0008, 0x280b},
279         {0x00, 0x000a, 0x280c},
280         {0x00, 0x0017, 0x280d},
281         {0x00, 0x0018, 0x280e},
282         {0x00, 0x0016, 0x280f},
283
284         {0x00, 0x0006, 0x2810},
285         {0x00, 0x0005, 0x2811},
286         {0x00, 0x0006, 0x2812},
287         {0x00, 0x000a, 0x2813},
288         {0x00, 0x0010, 0x2814},
289         {0x00, 0x0017, 0x2815},
290         {0x00, 0x001c, 0x2816},
291         {0x00, 0x0016, 0x2817},
292         {0x00, 0x0006, 0x2818},
293         {0x00, 0x0007, 0x2819},
294         {0x00, 0x0009, 0x281a},
295         {0x00, 0x000c, 0x281b},
296         {0x00, 0x0014, 0x281c},
297         {0x00, 0x0023, 0x281d},
298         {0x00, 0x0020, 0x281e},
299         {0x00, 0x0019, 0x281f},
300
301         {0x00, 0x0007, 0x2820},
302         {0x00, 0x0009, 0x2821},
303         {0x00, 0x000f, 0x2822},
304         {0x00, 0x0016, 0x2823},
305         {0x00, 0x001b, 0x2824},
306         {0x00, 0x002c, 0x2825},
307         {0x00, 0x0029, 0x2826},
308         {0x00, 0x001f, 0x2827},
309         {0x00, 0x000a, 0x2828},
310         {0x00, 0x000e, 0x2829},
311         {0x00, 0x0016, 0x282a},
312         {0x00, 0x001a, 0x282b},
313         {0x00, 0x0020, 0x282c},
314         {0x00, 0x002a, 0x282d},
315         {0x00, 0x002d, 0x282e},
316         {0x00, 0x0025, 0x282f},
317
318         {0x00, 0x0014, 0x2830},
319         {0x00, 0x001a, 0x2831},
320         {0x00, 0x001f, 0x2832},
321         {0x00, 0x0023, 0x2833},
322         {0x00, 0x0029, 0x2834},
323         {0x00, 0x0030, 0x2835},
324         {0x00, 0x0030, 0x2836},
325         {0x00, 0x0028, 0x2837},
326         {0x00, 0x001d, 0x2838},
327         {0x00, 0x0025, 0x2839},
328         {0x00, 0x0026, 0x283a},
329         {0x00, 0x0027, 0x283b},
330         {0x00, 0x002d, 0x283c},
331         {0x00, 0x0028, 0x283d},
332         {0x00, 0x0029, 0x283e},
333         {0x00, 0x0028, 0x283f},
334
335         {0x00, 0x0007, 0x2840},
336         {0x00, 0x0007, 0x2841},
337         {0x00, 0x000a, 0x2842},
338         {0x00, 0x0013, 0x2843},
339         {0x00, 0x0028, 0x2844},
340         {0x00, 0x0028, 0x2845},
341         {0x00, 0x0028, 0x2846},
342         {0x00, 0x0028, 0x2847},
343         {0x00, 0x0007, 0x2848},
344         {0x00, 0x0008, 0x2849},
345         {0x00, 0x000a, 0x284a},
346         {0x00, 0x001a, 0x284b},
347         {0x00, 0x0028, 0x284c},
348         {0x00, 0x0028, 0x284d},
349         {0x00, 0x0028, 0x284e},
350         {0x00, 0x0028, 0x284f},
351
352         {0x00, 0x000a, 0x2850},
353         {0x00, 0x000a, 0x2851},
354         {0x00, 0x0016, 0x2852},
355         {0x00, 0x0028, 0x2853},
356         {0x00, 0x0028, 0x2854},
357         {0x00, 0x0028, 0x2855},
358         {0x00, 0x0028, 0x2856},
359         {0x00, 0x0028, 0x2857},
360         {0x00, 0x0013, 0x2858},
361         {0x00, 0x001a, 0x2859},
362         {0x00, 0x0028, 0x285a},
363         {0x00, 0x0028, 0x285b},
364         {0x00, 0x0028, 0x285c},
365         {0x00, 0x0028, 0x285d},
366         {0x00, 0x0028, 0x285e},
367         {0x00, 0x0028, 0x285f},
368
369         {0x00, 0x0028, 0x2860},
370         {0x00, 0x0028, 0x2861},
371         {0x00, 0x0028, 0x2862},
372         {0x00, 0x0028, 0x2863},
373         {0x00, 0x0028, 0x2864},
374         {0x00, 0x0028, 0x2865},
375         {0x00, 0x0028, 0x2866},
376         {0x00, 0x0028, 0x2867},
377         {0x00, 0x0028, 0x2868},
378         {0x00, 0x0028, 0x2869},
379         {0x00, 0x0028, 0x286a},
380         {0x00, 0x0028, 0x286b},
381         {0x00, 0x0028, 0x286c},
382         {0x00, 0x0028, 0x286d},
383         {0x00, 0x0028, 0x286e},
384         {0x00, 0x0028, 0x286f},
385
386         {0x00, 0x0028, 0x2870},
387         {0x00, 0x0028, 0x2871},
388         {0x00, 0x0028, 0x2872},
389         {0x00, 0x0028, 0x2873},
390         {0x00, 0x0028, 0x2874},
391         {0x00, 0x0028, 0x2875},
392         {0x00, 0x0028, 0x2876},
393         {0x00, 0x0028, 0x2877},
394         {0x00, 0x0028, 0x2878},
395         {0x00, 0x0028, 0x2879},
396         {0x00, 0x0028, 0x287a},
397         {0x00, 0x0028, 0x287b},
398         {0x00, 0x0028, 0x287c},
399         {0x00, 0x0028, 0x287d},
400         {0x00, 0x0028, 0x287e},
401         {0x00, 0x0028, 0x287f},
402
403         {0xa0, 0x0000, 0x0503},
404         {}
405 };
406
407 static const __u8 qtable_creative_pccam[2][64] = {
408         {                               /* Q-table Y-components */
409          0x05, 0x03, 0x03, 0x05, 0x07, 0x0c, 0x0f, 0x12,
410          0x04, 0x04, 0x04, 0x06, 0x08, 0x11, 0x12, 0x11,
411          0x04, 0x04, 0x05, 0x07, 0x0c, 0x11, 0x15, 0x11,
412          0x04, 0x05, 0x07, 0x09, 0x0f, 0x1a, 0x18, 0x13,
413          0x05, 0x07, 0x0b, 0x11, 0x14, 0x21, 0x1f, 0x17,
414          0x07, 0x0b, 0x11, 0x13, 0x18, 0x1f, 0x22, 0x1c,
415          0x0f, 0x13, 0x17, 0x1a, 0x1f, 0x24, 0x24, 0x1e,
416          0x16, 0x1c, 0x1d, 0x1d, 0x22, 0x1e, 0x1f, 0x1e},
417         {                               /* Q-table C-components */
418          0x05, 0x05, 0x07, 0x0e, 0x1e, 0x1e, 0x1e, 0x1e,
419          0x05, 0x06, 0x08, 0x14, 0x1e, 0x1e, 0x1e, 0x1e,
420          0x07, 0x08, 0x11, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e,
421          0x0e, 0x14, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e,
422          0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e,
423          0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e,
424          0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e,
425          0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e}
426 };
427
428 /* FIXME: This Q-table is identical to the Creative PC-CAM one,
429  *              except for one byte. Possibly a typo?
430  *              NWG: 18/05/2003.
431  */
432 static const __u8 qtable_spca504_default[2][64] = {
433         {                               /* Q-table Y-components */
434          0x05, 0x03, 0x03, 0x05, 0x07, 0x0c, 0x0f, 0x12,
435          0x04, 0x04, 0x04, 0x06, 0x08, 0x11, 0x12, 0x11,
436          0x04, 0x04, 0x05, 0x07, 0x0c, 0x11, 0x15, 0x11,
437          0x04, 0x05, 0x07, 0x09, 0x0f, 0x1a, 0x18, 0x13,
438          0x05, 0x07, 0x0b, 0x11, 0x14, 0x21, 0x1f, 0x17,
439          0x07, 0x0b, 0x11, 0x13, 0x18, 0x1f, 0x22, 0x1c,
440          0x0f, 0x13, 0x17, 0x1a, 0x1f, 0x24, 0x24, 0x1e,
441          0x16, 0x1c, 0x1d, 0x1d, 0x1d /* 0x22 */ , 0x1e, 0x1f, 0x1e,
442          },
443         {                               /* Q-table C-components */
444          0x05, 0x05, 0x07, 0x0e, 0x1e, 0x1e, 0x1e, 0x1e,
445          0x05, 0x06, 0x08, 0x14, 0x1e, 0x1e, 0x1e, 0x1e,
446          0x07, 0x08, 0x11, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e,
447          0x0e, 0x14, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e,
448          0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e,
449          0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e,
450          0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e,
451          0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e}
452 };
453
454 /* read <len> bytes to gspca_dev->usb_buf */
455 static void reg_r(struct gspca_dev *gspca_dev,
456                   __u16 req,
457                   __u16 index,
458                   __u16 len)
459 {
460 #ifdef GSPCA_DEBUG
461         if (len > USB_BUF_SZ) {
462                 err("reg_r: buffer overflow");
463                 return;
464         }
465 #endif
466         usb_control_msg(gspca_dev->dev,
467                         usb_rcvctrlpipe(gspca_dev->dev, 0),
468                         req,
469                         USB_DIR_IN | USB_TYPE_VENDOR | USB_RECIP_DEVICE,
470                         0,              /* value */
471                         index,
472                         len ? gspca_dev->usb_buf : NULL, len,
473                         500);
474 }
475
476 /* write <len> bytes from gspca_dev->usb_buf */
477 static void reg_w(struct gspca_dev *gspca_dev,
478                    __u16 req,
479                    __u16 value,
480                    __u16 index,
481                    __u16 len)
482 {
483 #ifdef GSPCA_DEBUG
484         if (len > USB_BUF_SZ) {
485                 err("reg_w: buffer overflow");
486                 return;
487         }
488 #endif
489         usb_control_msg(gspca_dev->dev,
490                         usb_sndctrlpipe(gspca_dev->dev, 0),
491                         req,
492                         USB_DIR_OUT | USB_TYPE_VENDOR | USB_RECIP_DEVICE,
493                         value, index,
494                         len ? gspca_dev->usb_buf : NULL, len,
495                         500);
496 }
497
498 /* write req / index / value */
499 static int reg_w_riv(struct usb_device *dev,
500                      __u16 req, __u16 index, __u16 value)
501 {
502         int ret;
503
504         ret = usb_control_msg(dev,
505                         usb_sndctrlpipe(dev, 0),
506                         req,
507                         USB_DIR_OUT | USB_TYPE_VENDOR | USB_RECIP_DEVICE,
508                         value, index, NULL, 0, 500);
509         PDEBUG(D_USBO, "reg write: 0x%02x,0x%02x:0x%02x, %d",
510                 req, index, value, ret);
511         if (ret < 0)
512                 PDEBUG(D_ERR, "reg write: error %d", ret);
513         return ret;
514 }
515
516 /* read 1 byte */
517 static int reg_r_1(struct gspca_dev *gspca_dev,
518                         __u16 value)    /* wValue */
519 {
520         int ret;
521
522         ret = usb_control_msg(gspca_dev->dev,
523                         usb_rcvctrlpipe(gspca_dev->dev, 0),
524                         0x20,                   /* request */
525                         USB_DIR_IN | USB_TYPE_VENDOR | USB_RECIP_DEVICE,
526                         value,
527                         0,                      /* index */
528                         gspca_dev->usb_buf, 1,
529                         500);                   /* timeout */
530         if (ret < 0) {
531                 PDEBUG(D_ERR, "reg_r_1 err %d", ret);
532                 return 0;
533         }
534         return gspca_dev->usb_buf[0];
535 }
536
537 /* read 1 or 2 bytes - returns < 0 if error */
538 static int reg_r_12(struct gspca_dev *gspca_dev,
539                         __u16 req,      /* bRequest */
540                         __u16 index,    /* wIndex */
541                         __u16 length)   /* wLength (1 or 2 only) */
542 {
543         int ret;
544
545         gspca_dev->usb_buf[1] = 0;
546         ret = usb_control_msg(gspca_dev->dev,
547                         usb_rcvctrlpipe(gspca_dev->dev, 0),
548                         req,
549                         USB_DIR_IN | USB_TYPE_VENDOR | USB_RECIP_DEVICE,
550                         0,              /* value */
551                         index,
552                         gspca_dev->usb_buf, length,
553                         500);
554         if (ret < 0) {
555                 PDEBUG(D_ERR, "reg_read err %d", ret);
556                 return -1;
557         }
558         return (gspca_dev->usb_buf[1] << 8) + gspca_dev->usb_buf[0];
559 }
560
561 static int write_vector(struct gspca_dev *gspca_dev,
562                         const __u16 data[][3])
563 {
564         struct usb_device *dev = gspca_dev->dev;
565         int ret, i = 0;
566
567         while (data[i][0] != 0 || data[i][1] != 0 || data[i][2] != 0) {
568                 ret = reg_w_riv(dev, data[i][0], data[i][2], data[i][1]);
569                 if (ret < 0) {
570                         PDEBUG(D_ERR,
571                                 "Register write failed for 0x%x,0x%x,0x%x",
572                                 data[i][0], data[i][1], data[i][2]);
573                         return ret;
574                 }
575                 i++;
576         }
577         return 0;
578 }
579
580 static int spca50x_setup_qtable(struct gspca_dev *gspca_dev,
581                                 unsigned int request,
582                                 unsigned int ybase,
583                                 unsigned int cbase,
584                                 const __u8 qtable[2][64])
585 {
586         struct usb_device *dev = gspca_dev->dev;
587         int i, err;
588
589         /* loop over y components */
590         for (i = 0; i < 64; i++) {
591                 err = reg_w_riv(dev, request, ybase + i, qtable[0][i]);
592                 if (err < 0)
593                         return err;
594         }
595
596         /* loop over c components */
597         for (i = 0; i < 64; i++) {
598                 err = reg_w_riv(dev, request, cbase + i, qtable[1][i]);
599                 if (err < 0)
600                         return err;
601         }
602         return 0;
603 }
604
605 static void spca504_acknowledged_command(struct gspca_dev *gspca_dev,
606                              __u16 req, __u16 idx, __u16 val)
607 {
608         struct usb_device *dev = gspca_dev->dev;
609         __u8 notdone;
610
611         reg_w_riv(dev, req, idx, val);
612         notdone = reg_r_12(gspca_dev, 0x01, 0x0001, 1);
613         reg_w_riv(dev, req, idx, val);
614
615         PDEBUG(D_FRAM, "before wait 0x%x", notdone);
616
617         msleep(200);
618         notdone = reg_r_12(gspca_dev, 0x01, 0x0001, 1);
619         PDEBUG(D_FRAM, "after wait 0x%x", notdone);
620 }
621
622 static void spca504A_acknowledged_command(struct gspca_dev *gspca_dev,
623                         __u16 req,
624                         __u16 idx, __u16 val, __u8 stat, __u8 count)
625 {
626         struct usb_device *dev = gspca_dev->dev;
627         __u8 status;
628         __u8 endcode;
629
630         reg_w_riv(dev, req, idx, val);
631         status = reg_r_12(gspca_dev, 0x01, 0x0001, 1);
632         endcode = stat;
633         PDEBUG(D_FRAM, "Status 0x%x Need 0x%x", status, stat);
634         if (!count)
635                 return;
636         count = 200;
637         while (--count > 0) {
638                 msleep(10);
639                 /* gsmart mini2 write a each wait setting 1 ms is enought */
640 /*              reg_w_riv(dev, req, idx, val); */
641                 status = reg_r_12(gspca_dev, 0x01, 0x0001, 1);
642                 if (status == endcode) {
643                         PDEBUG(D_FRAM, "status 0x%x after wait 0x%x",
644                                 status, 200 - count);
645                                 break;
646                 }
647         }
648 }
649
650 static int spca504B_PollingDataReady(struct gspca_dev *gspca_dev)
651 {
652         int count = 10;
653
654         while (--count > 0) {
655                 reg_r(gspca_dev, 0x21, 0, 1);
656                 if ((gspca_dev->usb_buf[0] & 0x01) == 0)
657                         break;
658                 msleep(10);
659         }
660         return gspca_dev->usb_buf[0];
661 }
662
663 static void spca504B_WaitCmdStatus(struct gspca_dev *gspca_dev)
664 {
665         int count = 50;
666
667         while (--count > 0) {
668                 reg_r(gspca_dev, 0x21, 1, 1);
669                 if (gspca_dev->usb_buf[0] != 0) {
670                         gspca_dev->usb_buf[0] = 0;
671                         reg_w(gspca_dev, 0x21, 0, 1, 1);
672                         reg_r(gspca_dev, 0x21, 1, 1);
673                         spca504B_PollingDataReady(gspca_dev);
674                         break;
675                 }
676                 msleep(10);
677         }
678 }
679
680 static void spca50x_GetFirmware(struct gspca_dev *gspca_dev)
681 {
682         __u8 *data;
683
684         data = gspca_dev->usb_buf;
685         reg_r(gspca_dev, 0x20, 0, 5);
686         PDEBUG(D_STREAM, "FirmWare : %d %d %d %d %d ",
687                 data[0], data[1], data[2], data[3], data[4]);
688         reg_r(gspca_dev, 0x23, 0, 64);
689         reg_r(gspca_dev, 0x23, 1, 64);
690 }
691
692 static void spca504B_SetSizeType(struct gspca_dev *gspca_dev)
693 {
694         struct sd *sd = (struct sd *) gspca_dev;
695         struct usb_device *dev = gspca_dev->dev;
696         __u8 Size;
697         __u8 Type;
698         int rc;
699
700         Size = gspca_dev->cam.cam_mode[(int) gspca_dev->curr_mode].priv;
701         Type = 0;
702         switch (sd->bridge) {
703         case BRIDGE_SPCA533:
704                 reg_w(gspca_dev, 0x31, 0, 0, 0);
705                 spca504B_WaitCmdStatus(gspca_dev);
706                 rc = spca504B_PollingDataReady(gspca_dev);
707                 spca50x_GetFirmware(gspca_dev);
708                 gspca_dev->usb_buf[0] = 2;                      /* type */
709                 reg_w(gspca_dev, 0x24, 0, 8, 1);
710                 reg_r(gspca_dev, 0x24, 8, 1);
711
712                 gspca_dev->usb_buf[0] = Size;
713                 reg_w(gspca_dev, 0x25, 0, 4, 1);
714                 reg_r(gspca_dev, 0x25, 4, 1);                   /* size */
715                 rc = spca504B_PollingDataReady(gspca_dev);
716
717                 /* Init the cam width height with some values get on init ? */
718                 reg_w(gspca_dev, 0x31, 0, 4, 0);
719                 spca504B_WaitCmdStatus(gspca_dev);
720                 rc = spca504B_PollingDataReady(gspca_dev);
721                 break;
722         default:
723 /* case BRIDGE_SPCA504B: */
724 /* case BRIDGE_SPCA536: */
725                 gspca_dev->usb_buf[0] = Size;
726                 reg_w(gspca_dev, 0x25, 0, 4, 1);
727                 reg_r(gspca_dev, 0x25, 4, 1);                   /* size */
728                 Type = 6;
729                 gspca_dev->usb_buf[0] = Type;
730                 reg_w(gspca_dev, 0x27, 0, 0, 1);
731                 reg_r(gspca_dev, 0x27, 0, 1);                   /* type */
732                 rc = spca504B_PollingDataReady(gspca_dev);
733                 break;
734         case BRIDGE_SPCA504:
735                 Size += 3;
736                 if (sd->subtype == AiptekMiniPenCam13) {
737                         /* spca504a aiptek */
738                         spca504A_acknowledged_command(gspca_dev,
739                                                 0x08, Size, 0,
740                                                 0x80 | (Size & 0x0f), 1);
741                         spca504A_acknowledged_command(gspca_dev,
742                                                         1, 3, 0, 0x9f, 0);
743                 } else {
744                         spca504_acknowledged_command(gspca_dev, 0x08, Size, 0);
745                 }
746                 break;
747         case BRIDGE_SPCA504C:
748                 /* capture mode */
749                 reg_w_riv(dev, 0xa0, (0x0500 | (Size & 0x0f)), 0x00);
750                 reg_w_riv(dev, 0x20, 0x01, 0x0500 | (Size & 0x0f));
751                 break;
752         }
753 }
754
755 static void spca504_wait_status(struct gspca_dev *gspca_dev)
756 {
757         int cnt;
758
759         cnt = 256;
760         while (--cnt > 0) {
761                 /* With this we get the status, when return 0 it's all ok */
762                 if (reg_r_12(gspca_dev, 0x06, 0x00, 1) == 0)
763                         return;
764                 msleep(10);
765         }
766 }
767
768 static void spca504B_setQtable(struct gspca_dev *gspca_dev)
769 {
770         gspca_dev->usb_buf[0] = 3;
771         reg_w(gspca_dev, 0x26, 0, 0, 1);
772         reg_r(gspca_dev, 0x26, 0, 1);
773         spca504B_PollingDataReady(gspca_dev);
774 }
775
776 static void sp5xx_initContBrigHueRegisters(struct gspca_dev *gspca_dev)
777 {
778         struct sd *sd = (struct sd *) gspca_dev;
779         int pollreg = 1;
780
781         switch (sd->bridge) {
782         case BRIDGE_SPCA504:
783         case BRIDGE_SPCA504C:
784                 pollreg = 0;
785                 /* fall thru */
786         default:
787 /*      case BRIDGE_SPCA533: */
788 /*      case BRIDGE_SPCA504B: */
789                 reg_w(gspca_dev, 0, 0, 0x21a7, 0);      /* brightness */
790                 reg_w(gspca_dev, 0, 0x20, 0x21a8, 0);   /* contrast */
791                 reg_w(gspca_dev, 0, 0, 0x21ad, 0);      /* hue */
792                 reg_w(gspca_dev, 0, 1, 0x21ac, 0);      /* sat/hue */
793                 reg_w(gspca_dev, 0, 0x20, 0x21ae, 0);   /* saturation */
794                 reg_w(gspca_dev, 0, 0, 0x21a3, 0);      /* gamma */
795                 break;
796         case BRIDGE_SPCA536:
797                 reg_w(gspca_dev, 0, 0, 0x20f0, 0);
798                 reg_w(gspca_dev, 0, 0x21, 0x20f1, 0);
799                 reg_w(gspca_dev, 0, 0x40, 0x20f5, 0);
800                 reg_w(gspca_dev, 0, 1, 0x20f4, 0);
801                 reg_w(gspca_dev, 0, 0x40, 0x20f6, 0);
802                 reg_w(gspca_dev, 0, 0, 0x2089, 0);
803                 break;
804         }
805         if (pollreg)
806                 spca504B_PollingDataReady(gspca_dev);
807 }
808
809 /* this function is called at probe time */
810 static int sd_config(struct gspca_dev *gspca_dev,
811                         const struct usb_device_id *id)
812 {
813         struct sd *sd = (struct sd *) gspca_dev;
814         struct cam *cam;
815
816         cam = &gspca_dev->cam;
817
818         sd->bridge = id->driver_info >> 8;
819         sd->subtype = id->driver_info;
820
821         if (sd->subtype == AiptekMiniPenCam13) {
822 /* try to get the firmware as some cam answer 2.0.1.2.2
823  * and should be a spca504b then overwrite that setting */
824                 reg_r(gspca_dev, 0x20, 0, 1);
825                 switch (gspca_dev->usb_buf[0]) {
826                 case 1:
827                         break;          /* (right bridge/subtype) */
828                 case 2:
829                         sd->bridge = BRIDGE_SPCA504B;
830                         sd->subtype = 0;
831                         break;
832                 default:
833                         return -ENODEV;
834                 }
835         }
836
837         switch (sd->bridge) {
838         default:
839 /*      case BRIDGE_SPCA504B: */
840 /*      case BRIDGE_SPCA504: */
841 /*      case BRIDGE_SPCA536: */
842                 cam->cam_mode = vga_mode;
843                 cam->nmodes = sizeof vga_mode / sizeof vga_mode[0];
844                 break;
845         case BRIDGE_SPCA533:
846                 cam->cam_mode = custom_mode;
847                 cam->nmodes = sizeof custom_mode / sizeof custom_mode[0];
848                 break;
849         case BRIDGE_SPCA504C:
850                 cam->cam_mode = vga_mode2;
851                 cam->nmodes = sizeof vga_mode2 / sizeof vga_mode2[0];
852                 break;
853         }
854         sd->brightness = sd_ctrls[SD_BRIGHTNESS].qctrl.default_value;
855         sd->contrast = sd_ctrls[SD_CONTRAST].qctrl.default_value;
856         sd->colors = sd_ctrls[SD_COLOR].qctrl.default_value;
857         sd->quality = QUALITY_DEF;
858         return 0;
859 }
860
861 /* this function is called at probe and resume time */
862 static int sd_init(struct gspca_dev *gspca_dev)
863 {
864         struct sd *sd = (struct sd *) gspca_dev;
865         struct usb_device *dev = gspca_dev->dev;
866         int rc;
867         __u8 i;
868         __u8 info[6];
869         int err_code;
870
871         switch (sd->bridge) {
872         case BRIDGE_SPCA504B:
873                 reg_w(gspca_dev, 0x1d, 0, 0, 0);
874                 reg_w(gspca_dev, 0, 1, 0x2306, 0);
875                 reg_w(gspca_dev, 0, 0, 0x0d04, 0);
876                 reg_w(gspca_dev, 0, 0, 0x2000, 0);
877                 reg_w(gspca_dev, 0, 0x13, 0x2301, 0);
878                 reg_w(gspca_dev, 0, 0, 0x2306, 0);
879                 /* fall thru */
880         case BRIDGE_SPCA533:
881                 rc = spca504B_PollingDataReady(gspca_dev);
882                 spca50x_GetFirmware(gspca_dev);
883                 break;
884         case BRIDGE_SPCA536:
885                 spca50x_GetFirmware(gspca_dev);
886                 reg_r(gspca_dev, 0x00, 0x5002, 1);
887                 gspca_dev->usb_buf[0] = 0;
888                 reg_w(gspca_dev, 0x24, 0, 0, 1);
889                 reg_r(gspca_dev, 0x24, 0, 1);
890                 rc = spca504B_PollingDataReady(gspca_dev);
891                 reg_w(gspca_dev, 0x34, 0, 0, 0);
892                 spca504B_WaitCmdStatus(gspca_dev);
893                 break;
894         case BRIDGE_SPCA504C:   /* pccam600 */
895                 PDEBUG(D_STREAM, "Opening SPCA504 (PC-CAM 600)");
896                 reg_w_riv(dev, 0xe0, 0x0000, 0x0000);
897                 reg_w_riv(dev, 0xe0, 0x0000, 0x0001);   /* reset */
898                 spca504_wait_status(gspca_dev);
899                 if (sd->subtype == LogitechClickSmart420)
900                         write_vector(gspca_dev,
901                                         spca504A_clicksmart420_open_data);
902                 else
903                         write_vector(gspca_dev, spca504_pccam600_open_data);
904                 err_code = spca50x_setup_qtable(gspca_dev,
905                                                 0x00, 0x2800,
906                                                 0x2840, qtable_creative_pccam);
907                 if (err_code < 0) {
908                         PDEBUG(D_ERR|D_STREAM, "spca50x_setup_qtable failed");
909                         return err_code;
910                 }
911                 break;
912         default:
913 /*      case BRIDGE_SPCA504: */
914                 PDEBUG(D_STREAM, "Opening SPCA504");
915                 if (sd->subtype == AiptekMiniPenCam13) {
916                         /*****************************/
917                         for (i = 0; i < 6; i++)
918                                 info[i] = reg_r_1(gspca_dev, i);
919                         PDEBUG(D_STREAM,
920                                 "Read info: %d %d %d %d %d %d."
921                                 " Should be 1,0,2,2,0,0",
922                                 info[0], info[1], info[2],
923                                 info[3], info[4], info[5]);
924                         /* spca504a aiptek */
925                         /* Set AE AWB Banding Type 3-> 50Hz 2-> 60Hz */
926                         spca504A_acknowledged_command(gspca_dev, 0x24,
927                                                         8, 3, 0x9e, 1);
928                         /* Twice sequencial need status 0xff->0x9e->0x9d */
929                         spca504A_acknowledged_command(gspca_dev, 0x24,
930                                                         8, 3, 0x9e, 0);
931
932                         spca504A_acknowledged_command(gspca_dev, 0x24,
933                                                         0, 0, 0x9d, 1);
934                         /******************************/
935                         /* spca504a aiptek */
936                         spca504A_acknowledged_command(gspca_dev, 0x08,
937                                                         6, 0, 0x86, 1);
938 /*                      reg_write (dev, 0, 0x2000, 0); */
939 /*                      reg_write (dev, 0, 0x2883, 1); */
940 /*                      spca504A_acknowledged_command (gspca_dev, 0x08,
941                                                         6, 0, 0x86, 1); */
942 /*                      spca504A_acknowledged_command (gspca_dev, 0x24,
943                                                         0, 0, 0x9D, 1); */
944                         reg_w_riv(dev, 0x0, 0x270c, 0x05); /* L92 sno1t.txt */
945                         reg_w_riv(dev, 0x0, 0x2310, 0x05);
946                         spca504A_acknowledged_command(gspca_dev, 0x01,
947                                                         0x0f, 0, 0xff, 0);
948                 }
949                 /* setup qtable */
950                 reg_w_riv(dev, 0, 0x2000, 0);
951                 reg_w_riv(dev, 0, 0x2883, 1);
952                 err_code = spca50x_setup_qtable(gspca_dev,
953                                                 0x00, 0x2800,
954                                                 0x2840,
955                                                 qtable_spca504_default);
956                 if (err_code < 0) {
957                         PDEBUG(D_ERR, "spca50x_setup_qtable failed");
958                         return err_code;
959                 }
960                 break;
961         }
962         return 0;
963 }
964
965 static int sd_start(struct gspca_dev *gspca_dev)
966 {
967         struct sd *sd = (struct sd *) gspca_dev;
968         struct usb_device *dev = gspca_dev->dev;
969         int rc;
970         int enable;
971         __u8 i;
972         __u8 info[6];
973
974         /* create the JPEG header */
975         sd->jpeg_hdr = kmalloc(JPEG_HDR_SZ, GFP_KERNEL);
976         if (!sd->jpeg_hdr)
977                 return -ENOMEM;
978         jpeg_define(sd->jpeg_hdr, gspca_dev->height, gspca_dev->width,
979                         0x22);          /* JPEG 411 */
980         jpeg_set_qual(sd->jpeg_hdr, sd->quality);
981
982         if (sd->bridge == BRIDGE_SPCA504B)
983                 spca504B_setQtable(gspca_dev);
984         spca504B_SetSizeType(gspca_dev);
985         switch (sd->bridge) {
986         default:
987 /*      case BRIDGE_SPCA504B: */
988 /*      case BRIDGE_SPCA533: */
989 /*      case BRIDGE_SPCA536: */
990                 if (sd->subtype == MegapixV4 ||
991                     sd->subtype == LogitechClickSmart820) {
992                         reg_w(gspca_dev, 0xf0, 0, 0, 0);
993                         spca504B_WaitCmdStatus(gspca_dev);
994                         reg_r(gspca_dev, 0xf0, 4, 0);
995                         spca504B_WaitCmdStatus(gspca_dev);
996                 } else {
997                         reg_w(gspca_dev, 0x31, 0, 4, 0);
998                         spca504B_WaitCmdStatus(gspca_dev);
999                         rc = spca504B_PollingDataReady(gspca_dev);
1000                 }
1001                 break;
1002         case BRIDGE_SPCA504:
1003                 if (sd->subtype == AiptekMiniPenCam13) {
1004                         for (i = 0; i < 6; i++)
1005                                 info[i] = reg_r_1(gspca_dev, i);
1006                         PDEBUG(D_STREAM,
1007                                 "Read info: %d %d %d %d %d %d."
1008                                 " Should be 1,0,2,2,0,0",
1009                                 info[0], info[1], info[2],
1010                                 info[3], info[4], info[5]);
1011                         /* spca504a aiptek */
1012                         /* Set AE AWB Banding Type 3-> 50Hz 2-> 60Hz */
1013                         spca504A_acknowledged_command(gspca_dev, 0x24,
1014                                                         8, 3, 0x9e, 1);
1015                         /* Twice sequencial need status 0xff->0x9e->0x9d */
1016                         spca504A_acknowledged_command(gspca_dev, 0x24,
1017                                                         8, 3, 0x9e, 0);
1018                         spca504A_acknowledged_command(gspca_dev, 0x24,
1019                                                         0, 0, 0x9d, 1);
1020                 } else {
1021                         spca504_acknowledged_command(gspca_dev, 0x24, 8, 3);
1022                         for (i = 0; i < 6; i++)
1023                                 info[i] = reg_r_1(gspca_dev, i);
1024                         PDEBUG(D_STREAM,
1025                                 "Read info: %d %d %d %d %d %d."
1026                                 " Should be 1,0,2,2,0,0",
1027                                 info[0], info[1], info[2],
1028                                 info[3], info[4], info[5]);
1029                         spca504_acknowledged_command(gspca_dev, 0x24, 8, 3);
1030                         spca504_acknowledged_command(gspca_dev, 0x24, 0, 0);
1031                 }
1032                 spca504B_SetSizeType(gspca_dev);
1033                 reg_w_riv(dev, 0x0, 0x270c, 0x05);      /* L92 sno1t.txt */
1034                 reg_w_riv(dev, 0x0, 0x2310, 0x05);
1035                 break;
1036         case BRIDGE_SPCA504C:
1037                 if (sd->subtype == LogitechClickSmart420) {
1038                         write_vector(gspca_dev,
1039                                         spca504A_clicksmart420_init_data);
1040                 } else {
1041                         write_vector(gspca_dev, spca504_pccam600_init_data);
1042                 }
1043                 enable = (sd->autogain ? 0x04 : 0x01);
1044                 reg_w_riv(dev, 0x0c, 0x0000, enable);   /* auto exposure */
1045                 reg_w_riv(dev, 0xb0, 0x0000, enable);   /* auto whiteness */
1046
1047                 /* set default exposure compensation and whiteness balance */
1048                 reg_w_riv(dev, 0x30, 0x0001, 800);      /* ~ 20 fps */
1049                 reg_w_riv(dev, 0x30, 0x0002, 1600);
1050                 spca504B_SetSizeType(gspca_dev);
1051                 break;
1052         }
1053         sp5xx_initContBrigHueRegisters(gspca_dev);
1054         return 0;
1055 }
1056
1057 static void sd_stopN(struct gspca_dev *gspca_dev)
1058 {
1059         struct sd *sd = (struct sd *) gspca_dev;
1060         struct usb_device *dev = gspca_dev->dev;
1061
1062         switch (sd->bridge) {
1063         default:
1064 /*      case BRIDGE_SPCA533: */
1065 /*      case BRIDGE_SPCA536: */
1066 /*      case BRIDGE_SPCA504B: */
1067                 reg_w(gspca_dev, 0x31, 0, 0, 0);
1068                 spca504B_WaitCmdStatus(gspca_dev);
1069                 spca504B_PollingDataReady(gspca_dev);
1070                 break;
1071         case BRIDGE_SPCA504:
1072         case BRIDGE_SPCA504C:
1073                 reg_w_riv(dev, 0x00, 0x2000, 0x0000);
1074
1075                 if (sd->subtype == AiptekMiniPenCam13) {
1076                         /* spca504a aiptek */
1077 /*                      spca504A_acknowledged_command(gspca_dev, 0x08,
1078                                                          6, 0, 0x86, 1); */
1079                         spca504A_acknowledged_command(gspca_dev, 0x24,
1080                                                         0x00, 0x00, 0x9d, 1);
1081                         spca504A_acknowledged_command(gspca_dev, 0x01,
1082                                                         0x0f, 0x00, 0xff, 1);
1083                 } else {
1084                         spca504_acknowledged_command(gspca_dev, 0x24, 0, 0);
1085                         reg_w_riv(dev, 0x01, 0x000f, 0x00);
1086                 }
1087                 break;
1088         }
1089 }
1090
1091 static void sd_stop0(struct gspca_dev *gspca_dev)
1092 {
1093         struct sd *sd = (struct sd *) gspca_dev;
1094
1095         kfree(sd->jpeg_hdr);
1096 }
1097
1098 static void sd_pkt_scan(struct gspca_dev *gspca_dev,
1099                         struct gspca_frame *frame,      /* target */
1100                         __u8 *data,                     /* isoc packet */
1101                         int len)                        /* iso packet length */
1102 {
1103         struct sd *sd = (struct sd *) gspca_dev;
1104         int i, sof = 0;
1105         static unsigned char ffd9[] = {0xff, 0xd9};
1106
1107 /* frames are jpeg 4.1.1 without 0xff escape */
1108         switch (sd->bridge) {
1109         case BRIDGE_SPCA533:
1110                 if (data[0] == 0xff) {
1111                         if (data[1] != 0x01) {  /* drop packet */
1112 /*                              gspca_dev->last_packet_type = DISCARD_PACKET; */
1113                                 return;
1114                         }
1115                         sof = 1;
1116                         data += SPCA533_OFFSET_DATA;
1117                         len -= SPCA533_OFFSET_DATA;
1118                 } else {
1119                         data += 1;
1120                         len -= 1;
1121                 }
1122                 break;
1123         case BRIDGE_SPCA536:
1124                 if (data[0] == 0xff) {
1125                         sof = 1;
1126                         data += SPCA536_OFFSET_DATA;
1127                         len -= SPCA536_OFFSET_DATA;
1128                 } else {
1129                         data += 2;
1130                         len -= 2;
1131                 }
1132                 break;
1133         default:
1134 /*      case BRIDGE_SPCA504: */
1135 /*      case BRIDGE_SPCA504B: */
1136                 switch (data[0]) {
1137                 case 0xfe:                      /* start of frame */
1138                         sof = 1;
1139                         data += SPCA50X_OFFSET_DATA;
1140                         len -= SPCA50X_OFFSET_DATA;
1141                         break;
1142                 case 0xff:                      /* drop packet */
1143 /*                      gspca_dev->last_packet_type = DISCARD_PACKET; */
1144                         return;
1145                 default:
1146                         data += 1;
1147                         len -= 1;
1148                         break;
1149                 }
1150                 break;
1151         case BRIDGE_SPCA504C:
1152                 switch (data[0]) {
1153                 case 0xfe:                      /* start of frame */
1154                         sof = 1;
1155                         data += SPCA504_PCCAM600_OFFSET_DATA;
1156                         len -= SPCA504_PCCAM600_OFFSET_DATA;
1157                         break;
1158                 case 0xff:                      /* drop packet */
1159 /*                      gspca_dev->last_packet_type = DISCARD_PACKET; */
1160                         return;
1161                 default:
1162                         data += 1;
1163                         len -= 1;
1164                         break;
1165                 }
1166                 break;
1167         }
1168         if (sof) {              /* start of frame */
1169                 frame = gspca_frame_add(gspca_dev, LAST_PACKET, frame,
1170                                         ffd9, 2);
1171
1172                 /* put the JPEG header in the new frame */
1173                 gspca_frame_add(gspca_dev, FIRST_PACKET, frame,
1174                         sd->jpeg_hdr, JPEG_HDR_SZ);
1175         }
1176
1177         /* add 0x00 after 0xff */
1178         i = 0;
1179         do {
1180                 if (data[i] == 0xff) {
1181                         gspca_frame_add(gspca_dev, INTER_PACKET, frame,
1182                                         data, i + 1);
1183                         len -= i;
1184                         data += i;
1185                         *data = 0x00;
1186                         i = 0;
1187                 }
1188                 i++;
1189         } while (i < len);
1190         gspca_frame_add(gspca_dev, INTER_PACKET, frame, data, len);
1191 }
1192
1193 static void setbrightness(struct gspca_dev *gspca_dev)
1194 {
1195         struct sd *sd = (struct sd *) gspca_dev;
1196         struct usb_device *dev = gspca_dev->dev;
1197
1198         switch (sd->bridge) {
1199         default:
1200 /*      case BRIDGE_SPCA533: */
1201 /*      case BRIDGE_SPCA504B: */
1202 /*      case BRIDGE_SPCA504: */
1203 /*      case BRIDGE_SPCA504C: */
1204                 reg_w_riv(dev, 0x0, 0x21a7, sd->brightness);
1205                 break;
1206         case BRIDGE_SPCA536:
1207                 reg_w_riv(dev, 0x0, 0x20f0, sd->brightness);
1208                 break;
1209         }
1210 }
1211
1212 static void setcontrast(struct gspca_dev *gspca_dev)
1213 {
1214         struct sd *sd = (struct sd *) gspca_dev;
1215         struct usb_device *dev = gspca_dev->dev;
1216
1217         switch (sd->bridge) {
1218         default:
1219 /*      case BRIDGE_SPCA533: */
1220 /*      case BRIDGE_SPCA504B: */
1221 /*      case BRIDGE_SPCA504: */
1222 /*      case BRIDGE_SPCA504C: */
1223                 reg_w_riv(dev, 0x0, 0x21a8, sd->contrast);
1224                 break;
1225         case BRIDGE_SPCA536:
1226                 reg_w_riv(dev, 0x0, 0x20f1, sd->contrast);
1227                 break;
1228         }
1229 }
1230
1231 static void setcolors(struct gspca_dev *gspca_dev)
1232 {
1233         struct sd *sd = (struct sd *) gspca_dev;
1234         struct usb_device *dev = gspca_dev->dev;
1235
1236         switch (sd->bridge) {
1237         default:
1238 /*      case BRIDGE_SPCA533: */
1239 /*      case BRIDGE_SPCA504B: */
1240 /*      case BRIDGE_SPCA504: */
1241 /*      case BRIDGE_SPCA504C: */
1242                 reg_w_riv(dev, 0x0, 0x21ae, sd->colors);
1243                 break;
1244         case BRIDGE_SPCA536:
1245                 reg_w_riv(dev, 0x0, 0x20f6, sd->colors);
1246                 break;
1247         }
1248 }
1249
1250 static int sd_setbrightness(struct gspca_dev *gspca_dev, __s32 val)
1251 {
1252         struct sd *sd = (struct sd *) gspca_dev;
1253
1254         sd->brightness = val;
1255         if (gspca_dev->streaming)
1256                 setbrightness(gspca_dev);
1257         return 0;
1258 }
1259
1260 static int sd_getbrightness(struct gspca_dev *gspca_dev, __s32 *val)
1261 {
1262         struct sd *sd = (struct sd *) gspca_dev;
1263
1264         *val = sd->brightness;
1265         return 0;
1266 }
1267
1268 static int sd_setcontrast(struct gspca_dev *gspca_dev, __s32 val)
1269 {
1270         struct sd *sd = (struct sd *) gspca_dev;
1271
1272         sd->contrast = val;
1273         if (gspca_dev->streaming)
1274                 setcontrast(gspca_dev);
1275         return 0;
1276 }
1277
1278 static int sd_getcontrast(struct gspca_dev *gspca_dev, __s32 *val)
1279 {
1280         struct sd *sd = (struct sd *) gspca_dev;
1281
1282         *val = sd->contrast;
1283         return 0;
1284 }
1285
1286 static int sd_setcolors(struct gspca_dev *gspca_dev, __s32 val)
1287 {
1288         struct sd *sd = (struct sd *) gspca_dev;
1289
1290         sd->colors = val;
1291         if (gspca_dev->streaming)
1292                 setcolors(gspca_dev);
1293         return 0;
1294 }
1295
1296 static int sd_getcolors(struct gspca_dev *gspca_dev, __s32 *val)
1297 {
1298         struct sd *sd = (struct sd *) gspca_dev;
1299
1300         *val = sd->colors;
1301         return 0;
1302 }
1303
1304 static int sd_setautogain(struct gspca_dev *gspca_dev, __s32 val)
1305 {
1306         struct sd *sd = (struct sd *) gspca_dev;
1307
1308         sd->autogain = val;
1309         return 0;
1310 }
1311
1312 static int sd_getautogain(struct gspca_dev *gspca_dev, __s32 *val)
1313 {
1314         struct sd *sd = (struct sd *) gspca_dev;
1315
1316         *val = sd->autogain;
1317         return 0;
1318 }
1319
1320 static int sd_set_jcomp(struct gspca_dev *gspca_dev,
1321                         struct v4l2_jpegcompression *jcomp)
1322 {
1323         struct sd *sd = (struct sd *) gspca_dev;
1324
1325         if (jcomp->quality < QUALITY_MIN)
1326                 sd->quality = QUALITY_MIN;
1327         else if (jcomp->quality > QUALITY_MAX)
1328                 sd->quality = QUALITY_MAX;
1329         else
1330                 sd->quality = jcomp->quality;
1331         if (gspca_dev->streaming)
1332                 jpeg_set_qual(sd->jpeg_hdr, sd->quality);
1333         return 0;
1334 }
1335
1336 static int sd_get_jcomp(struct gspca_dev *gspca_dev,
1337                         struct v4l2_jpegcompression *jcomp)
1338 {
1339         struct sd *sd = (struct sd *) gspca_dev;
1340
1341         memset(jcomp, 0, sizeof *jcomp);
1342         jcomp->quality = sd->quality;
1343         jcomp->jpeg_markers = V4L2_JPEG_MARKER_DHT
1344                         | V4L2_JPEG_MARKER_DQT;
1345         return 0;
1346 }
1347
1348 /* sub-driver description */
1349 static const struct sd_desc sd_desc = {
1350         .name = MODULE_NAME,
1351         .ctrls = sd_ctrls,
1352         .nctrls = ARRAY_SIZE(sd_ctrls),
1353         .config = sd_config,
1354         .init = sd_init,
1355         .start = sd_start,
1356         .stopN = sd_stopN,
1357         .stop0 = sd_stop0,
1358         .pkt_scan = sd_pkt_scan,
1359         .get_jcomp = sd_get_jcomp,
1360         .set_jcomp = sd_set_jcomp,
1361 };
1362
1363 /* -- module initialisation -- */
1364 #define BS(bridge, subtype) \
1365         .driver_info = (BRIDGE_ ## bridge << 8) \
1366                         | (subtype)
1367 static const __devinitdata struct usb_device_id device_table[] = {
1368         {USB_DEVICE(0x041e, 0x400b), BS(SPCA504C, 0)},
1369         {USB_DEVICE(0x041e, 0x4012), BS(SPCA504C, 0)},
1370         {USB_DEVICE(0x041e, 0x4013), BS(SPCA504C, 0)},
1371         {USB_DEVICE(0x0458, 0x7006), BS(SPCA504B, 0)},
1372         {USB_DEVICE(0x0461, 0x0821), BS(SPCA533, 0)},
1373         {USB_DEVICE(0x046d, 0x0905), BS(SPCA533, LogitechClickSmart820)},
1374         {USB_DEVICE(0x046d, 0x0960), BS(SPCA504C, LogitechClickSmart420)},
1375         {USB_DEVICE(0x0471, 0x0322), BS(SPCA504B, 0)},
1376         {USB_DEVICE(0x04a5, 0x3003), BS(SPCA504B, 0)},
1377         {USB_DEVICE(0x04a5, 0x3008), BS(SPCA533, 0)},
1378         {USB_DEVICE(0x04a5, 0x300a), BS(SPCA533, 0)},
1379         {USB_DEVICE(0x04f1, 0x1001), BS(SPCA504B, 0)},
1380         {USB_DEVICE(0x04fc, 0x500c), BS(SPCA504B, 0)},
1381         {USB_DEVICE(0x04fc, 0x504a), BS(SPCA504, AiptekMiniPenCam13)},
1382         {USB_DEVICE(0x04fc, 0x504b), BS(SPCA504B, 0)},
1383         {USB_DEVICE(0x04fc, 0x5330), BS(SPCA533, 0)},
1384         {USB_DEVICE(0x04fc, 0x5360), BS(SPCA536, 0)},
1385         {USB_DEVICE(0x04fc, 0xffff), BS(SPCA504B, 0)},
1386         {USB_DEVICE(0x052b, 0x1513), BS(SPCA533, MegapixV4)},
1387         {USB_DEVICE(0x0546, 0x3155), BS(SPCA533, 0)},
1388         {USB_DEVICE(0x0546, 0x3191), BS(SPCA504B, 0)},
1389         {USB_DEVICE(0x0546, 0x3273), BS(SPCA504B, 0)},
1390         {USB_DEVICE(0x055f, 0xc211), BS(SPCA536, 0)},
1391         {USB_DEVICE(0x055f, 0xc230), BS(SPCA533, 0)},
1392         {USB_DEVICE(0x055f, 0xc232), BS(SPCA533, 0)},
1393         {USB_DEVICE(0x055f, 0xc360), BS(SPCA536, 0)},
1394         {USB_DEVICE(0x055f, 0xc420), BS(SPCA504, 0)},
1395         {USB_DEVICE(0x055f, 0xc430), BS(SPCA533, 0)},
1396         {USB_DEVICE(0x055f, 0xc440), BS(SPCA533, 0)},
1397         {USB_DEVICE(0x055f, 0xc520), BS(SPCA504, 0)},
1398         {USB_DEVICE(0x055f, 0xc530), BS(SPCA533, 0)},
1399         {USB_DEVICE(0x055f, 0xc540), BS(SPCA533, 0)},
1400         {USB_DEVICE(0x055f, 0xc630), BS(SPCA533, 0)},
1401         {USB_DEVICE(0x055f, 0xc650), BS(SPCA533, 0)},
1402         {USB_DEVICE(0x05da, 0x1018), BS(SPCA504B, 0)},
1403         {USB_DEVICE(0x06d6, 0x0031), BS(SPCA533, 0)},
1404         {USB_DEVICE(0x0733, 0x1311), BS(SPCA533, 0)},
1405         {USB_DEVICE(0x0733, 0x1314), BS(SPCA533, 0)},
1406         {USB_DEVICE(0x0733, 0x2211), BS(SPCA533, 0)},
1407         {USB_DEVICE(0x0733, 0x2221), BS(SPCA533, 0)},
1408         {USB_DEVICE(0x0733, 0x3261), BS(SPCA536, 0)},
1409         {USB_DEVICE(0x0733, 0x3281), BS(SPCA536, 0)},
1410         {USB_DEVICE(0x08ca, 0x0104), BS(SPCA533, 0)},
1411         {USB_DEVICE(0x08ca, 0x0106), BS(SPCA533, 0)},
1412         {USB_DEVICE(0x08ca, 0x2008), BS(SPCA504B, 0)},
1413         {USB_DEVICE(0x08ca, 0x2010), BS(SPCA533, 0)},
1414         {USB_DEVICE(0x08ca, 0x2016), BS(SPCA504B, 0)},
1415         {USB_DEVICE(0x08ca, 0x2018), BS(SPCA504B, 0)},
1416         {USB_DEVICE(0x08ca, 0x2020), BS(SPCA533, 0)},
1417         {USB_DEVICE(0x08ca, 0x2022), BS(SPCA533, 0)},
1418         {USB_DEVICE(0x08ca, 0x2024), BS(SPCA536, 0)},
1419         {USB_DEVICE(0x08ca, 0x2028), BS(SPCA533, 0)},
1420         {USB_DEVICE(0x08ca, 0x2040), BS(SPCA536, 0)},
1421         {USB_DEVICE(0x08ca, 0x2042), BS(SPCA536, 0)},
1422         {USB_DEVICE(0x08ca, 0x2050), BS(SPCA536, 0)},
1423         {USB_DEVICE(0x08ca, 0x2060), BS(SPCA536, 0)},
1424         {USB_DEVICE(0x0d64, 0x0303), BS(SPCA536, 0)},
1425         {}
1426 };
1427 MODULE_DEVICE_TABLE(usb, device_table);
1428
1429 /* -- device connect -- */
1430 static int sd_probe(struct usb_interface *intf,
1431                         const struct usb_device_id *id)
1432 {
1433         return gspca_dev_probe(intf, id, &sd_desc, sizeof(struct sd),
1434                                 THIS_MODULE);
1435 }
1436
1437 static struct usb_driver sd_driver = {
1438         .name = MODULE_NAME,
1439         .id_table = device_table,
1440         .probe = sd_probe,
1441         .disconnect = gspca_disconnect,
1442 #ifdef CONFIG_PM
1443         .suspend = gspca_suspend,
1444         .resume = gspca_resume,
1445 #endif
1446 };
1447
1448 /* -- module insert / remove -- */
1449 static int __init sd_mod_init(void)
1450 {
1451         int ret;
1452         ret = usb_register(&sd_driver);
1453         if (ret < 0)
1454                 return ret;
1455         PDEBUG(D_PROBE, "registered");
1456         return 0;
1457 }
1458 static void __exit sd_mod_exit(void)
1459 {
1460         usb_deregister(&sd_driver);
1461         PDEBUG(D_PROBE, "deregistered");
1462 }
1463
1464 module_init(sd_mod_init);
1465 module_exit(sd_mod_exit);