2
* Sunplus spca561 subdriver
4
* Copyright (C) 2004 Michel Xhaard mxhaard@magic.fr
6
* V4L2 by Jean-Francois Moine <http://moinejf.free.fr>
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
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.
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
23
#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
25
#define MODULE_NAME "spca561"
27
#include <linux/input.h>
30
MODULE_AUTHOR("Michel Xhaard <mxhaard@users.sourceforge.net>");
31
MODULE_DESCRIPTION("GSPCA/SPCA561 USB Camera Driver");
32
MODULE_LICENSE("GPL");
34
/* specific webcam descriptor */
36
struct gspca_dev gspca_dev; /* !! must be the first item */
38
__u16 exposure; /* rev12a only */
39
#define EXPOSURE_MIN 1
40
#define EXPOSURE_DEF 700 /* == 10 fps */
41
#define EXPOSURE_MAX (2047 + 325) /* see setexposure */
43
__u8 contrast; /* rev72a only */
44
#define CONTRAST_MIN 0x00
45
#define CONTRAST_DEF 0x20
46
#define CONTRAST_MAX 0x3f
48
__u8 brightness; /* rev72a only */
49
#define BRIGHTNESS_MIN 0
50
#define BRIGHTNESS_DEF 0x20
51
#define BRIGHTNESS_MAX 0x3f
59
#define AUTOGAIN_MIN 0
60
#define AUTOGAIN_DEF 1
61
#define AUTOGAIN_MAX 1
63
__u8 gain; /* rev12a only */
69
__u8 expo12a; /* expo/gain? for rev 12a */
76
#define AG_CNT_START 13
79
static const struct v4l2_pix_format sif_012a_mode[] = {
80
{160, 120, V4L2_PIX_FMT_SGBRG8, V4L2_FIELD_NONE,
82
.sizeimage = 160 * 120,
83
.colorspace = V4L2_COLORSPACE_SRGB,
85
{176, 144, V4L2_PIX_FMT_SGBRG8, V4L2_FIELD_NONE,
87
.sizeimage = 176 * 144,
88
.colorspace = V4L2_COLORSPACE_SRGB,
90
{320, 240, V4L2_PIX_FMT_SPCA561, V4L2_FIELD_NONE,
92
.sizeimage = 320 * 240 * 4 / 8,
93
.colorspace = V4L2_COLORSPACE_SRGB,
95
{352, 288, V4L2_PIX_FMT_SPCA561, V4L2_FIELD_NONE,
97
.sizeimage = 352 * 288 * 4 / 8,
98
.colorspace = V4L2_COLORSPACE_SRGB,
102
static const struct v4l2_pix_format sif_072a_mode[] = {
103
{160, 120, V4L2_PIX_FMT_SGBRG8, V4L2_FIELD_NONE,
105
.sizeimage = 160 * 120,
106
.colorspace = V4L2_COLORSPACE_SRGB,
108
{176, 144, V4L2_PIX_FMT_SGBRG8, V4L2_FIELD_NONE,
110
.sizeimage = 176 * 144,
111
.colorspace = V4L2_COLORSPACE_SRGB,
113
{320, 240, V4L2_PIX_FMT_SGBRG8, V4L2_FIELD_NONE,
115
.sizeimage = 320 * 240,
116
.colorspace = V4L2_COLORSPACE_SRGB,
118
{352, 288, V4L2_PIX_FMT_SGBRG8, V4L2_FIELD_NONE,
120
.sizeimage = 352 * 288,
121
.colorspace = V4L2_COLORSPACE_SRGB,
126
* Initialization data
127
* I'm not very sure how to split initialization from open data
128
* chunks. For now, we'll consider everything as initialization
130
/* Frame packet header offsets for the spca561 */
131
#define SPCA561_OFFSET_SNAP 1
132
#define SPCA561_OFFSET_TYPE 2
133
#define SPCA561_OFFSET_COMPRESS 3
134
#define SPCA561_OFFSET_FRAMSEQ 4
135
#define SPCA561_OFFSET_GPIO 5
136
#define SPCA561_OFFSET_USBBUFF 6
137
#define SPCA561_OFFSET_WIN2GRAVE 7
138
#define SPCA561_OFFSET_WIN2RAVE 8
139
#define SPCA561_OFFSET_WIN2BAVE 9
140
#define SPCA561_OFFSET_WIN2GBAVE 10
141
#define SPCA561_OFFSET_WIN1GRAVE 11
142
#define SPCA561_OFFSET_WIN1RAVE 12
143
#define SPCA561_OFFSET_WIN1BAVE 13
144
#define SPCA561_OFFSET_WIN1GBAVE 14
145
#define SPCA561_OFFSET_FREQ 15
146
#define SPCA561_OFFSET_VSYNC 16
147
#define SPCA561_INDEX_I2C_BASE 0x8800
148
#define SPCA561_SNAPBIT 0x20
149
#define SPCA561_SNAPCTRL 0x40
151
static const u16 rev72a_reset[][2] = {
152
{0x0000, 0x8114}, /* Software GPIO output data */
153
{0x0001, 0x8114}, /* Software GPIO output data */
154
{0x0000, 0x8112}, /* Some kind of reset */
157
static const __u16 rev72a_init_data1[][2] = {
158
{0x0003, 0x8701}, /* PCLK clock delay adjustment */
159
{0x0001, 0x8703}, /* HSYNC from cmos inverted */
160
{0x0011, 0x8118}, /* Enable and conf sensor */
161
{0x0001, 0x8118}, /* Conf sensor */
162
{0x0092, 0x8804}, /* I know nothing about these */
163
{0x0010, 0x8802}, /* 0x88xx registers, so I won't */
166
static const u16 rev72a_init_sensor1[][2] = {
181
static const __u16 rev72a_init_data2[][2] = {
182
{0x0018, 0x8601}, /* Pixel/line selection for color separation */
183
{0x0000, 0x8602}, /* Optical black level for user setting */
184
{0x0060, 0x8604}, /* Optical black horizontal offset */
185
{0x0002, 0x8605}, /* Optical black vertical offset */
186
{0x0000, 0x8603}, /* Non-automatic optical black level */
187
{0x0002, 0x865b}, /* Horizontal offset for valid pixels */
188
{0x0000, 0x865f}, /* Vertical valid pixels window (x2) */
189
{0x00b0, 0x865d}, /* Horizontal valid pixels window (x2) */
190
{0x0090, 0x865e}, /* Vertical valid lines window (x2) */
191
{0x00e0, 0x8406}, /* Memory buffer threshold */
192
{0x0000, 0x8660}, /* Compensation memory stuff */
193
{0x0002, 0x8201}, /* Output address for r/w serial EEPROM */
194
{0x0008, 0x8200}, /* Clear valid bit for serial EEPROM */
195
{0x0001, 0x8200}, /* OprMode to be executed by hardware */
197
{0x0000, 0x8611}, /* R offset for white balance */
198
{0x00fd, 0x8612}, /* Gr offset for white balance */
199
{0x0003, 0x8613}, /* B offset for white balance */
200
{0x0000, 0x8614}, /* Gb offset for white balance */
202
{0x0035, 0x8651}, /* R gain for white balance */
203
{0x0040, 0x8652}, /* Gr gain for white balance */
204
{0x005f, 0x8653}, /* B gain for white balance */
205
{0x0040, 0x8654}, /* Gb gain for white balance */
206
{0x0002, 0x8502}, /* Maximum average bit rate stuff */
209
{0x0087, 0x8700}, /* Set master clock (96Mhz????) */
210
{0x0081, 0x8702}, /* Master clock output enable */
212
{0x0000, 0x8500}, /* Set image type (352x288 no compression) */
213
/* Originally was 0x0010 (352x288 compression) */
215
{0x0002, 0x865b}, /* Horizontal offset for valid pixels */
216
{0x0003, 0x865c}, /* Vertical offset for valid lines */
219
static const u16 rev72a_init_sensor2[][2] = {
222
{0x0005, 0x002f}, /* blanking control column */
223
{0x0006, 0x0000}, /* blanking mode row*/
225
{0x0009, 0x1061}, /* setexposure times && pixel clock
226
* 0001 0 | 000 0110 0001 */
231
/******************** QC Express etch2 stuff ********************/
232
static const __u16 Pb100_1map8300[][2] = {
236
{0x8303, 0x0125}, /* image area */
239
{0x833c, 0x0001}, /*fixme: win:07*/
241
{0x832f, 0x1904}, /*fixme: was 0419*/
247
static const __u16 Pb100_2map8300[][2] = {
254
static const __u16 spca561_161rev12A_data1[][2] = {
255
{0x29, 0x8118}, /* Control register (various enable bits) */
256
{0x08, 0x8114}, /* GPIO: Led off */
257
{0x0e, 0x8112}, /* 0x0e stream off 0x3e stream on */
258
{0x00, 0x8102}, /* white balance - new */
260
{0x04, 0x8802}, /* windows uses 08 */
263
static const __u16 spca561_161rev12A_data2[][2] = {
270
{0x07, 0x8201}, /* windows uses 02 */
279
{0x07, 0x8601}, /* white balance - new */
280
{0x07, 0x8602}, /* white balance - new */
281
{0x00, 0x8610}, /* *red */
282
{0x00, 0x8611}, /* 3f *green */
283
{0x00, 0x8612}, /* green *blue */
284
{0x00, 0x8613}, /* blue *green */
285
{0x43, 0x8614}, /* green *red - white balance - was 0x35 */
286
{0x40, 0x8615}, /* 40 *green - white balance - was 0x35 */
287
{0x71, 0x8616}, /* 7a *blue - white balance - was 0x35 */
288
{0x40, 0x8617}, /* 40 *green - white balance - was 0x35 */
290
{0x0c, 0x8620}, /* 0c */
291
{0xc8, 0x8631}, /* c8 */
292
{0xc8, 0x8634}, /* c8 */
293
{0x23, 0x8635}, /* 23 */
294
{0x1f, 0x8636}, /* 1f */
295
{0xdd, 0x8637}, /* dd */
296
{0xe1, 0x8638}, /* e1 */
297
{0x1d, 0x8639}, /* 1d */
298
{0x21, 0x863a}, /* 21 */
299
{0xe3, 0x863b}, /* e3 */
300
{0xdf, 0x863c}, /* df */
303
/* {0x99, 0x8700}, * - white balance - new (removed) */
304
/* HDG we used to do this in stop0, making the init state and the state
305
after a start / stop different, so do this here instead. */
310
static void reg_w_val(struct usb_device *dev, __u16 index, __u8 value)
314
ret = usb_control_msg(dev, usb_sndctrlpipe(dev, 0),
316
USB_DIR_OUT | USB_TYPE_VENDOR | USB_RECIP_DEVICE,
317
value, index, NULL, 0, 500);
318
PDEBUG(D_USBO, "reg write: 0x%02x:0x%02x", index, value);
320
pr_err("reg write: error %d\n", ret);
323
static void write_vector(struct gspca_dev *gspca_dev,
324
const __u16 data[][2])
326
struct usb_device *dev = gspca_dev->dev;
330
while (data[i][1] != 0) {
331
reg_w_val(dev, data[i][1], data[i][0]);
336
/* read 'len' bytes to gspca_dev->usb_buf */
337
static void reg_r(struct gspca_dev *gspca_dev,
338
__u16 index, __u16 length)
340
usb_control_msg(gspca_dev->dev,
341
usb_rcvctrlpipe(gspca_dev->dev, 0),
343
USB_DIR_IN | USB_TYPE_VENDOR | USB_RECIP_DEVICE,
345
index, gspca_dev->usb_buf, length, 500);
348
/* write 'len' bytes from gspca_dev->usb_buf */
349
static void reg_w_buf(struct gspca_dev *gspca_dev,
350
__u16 index, __u16 len)
352
usb_control_msg(gspca_dev->dev,
353
usb_sndctrlpipe(gspca_dev->dev, 0),
355
USB_DIR_OUT | USB_TYPE_VENDOR | USB_RECIP_DEVICE,
357
index, gspca_dev->usb_buf, len, 500);
360
static void i2c_write(struct gspca_dev *gspca_dev, __u16 value, __u16 reg)
364
reg_w_val(gspca_dev->dev, 0x8801, reg);
365
reg_w_val(gspca_dev->dev, 0x8805, value);
366
reg_w_val(gspca_dev->dev, 0x8800, value >> 8);
368
reg_r(gspca_dev, 0x8803, 1);
369
if (!gspca_dev->usb_buf[0])
375
static int i2c_read(struct gspca_dev *gspca_dev, __u16 reg, __u8 mode)
380
reg_w_val(gspca_dev->dev, 0x8804, 0x92);
381
reg_w_val(gspca_dev->dev, 0x8801, reg);
382
reg_w_val(gspca_dev->dev, 0x8802, mode | 0x01);
384
reg_r(gspca_dev, 0x8803, 1);
385
if (!gspca_dev->usb_buf[0]) {
386
reg_r(gspca_dev, 0x8800, 1);
387
value = gspca_dev->usb_buf[0];
388
reg_r(gspca_dev, 0x8805, 1);
389
return ((int) value << 8) | gspca_dev->usb_buf[0];
396
static void sensor_mapwrite(struct gspca_dev *gspca_dev,
397
const __u16 (*sensormap)[2])
399
while ((*sensormap)[0]) {
400
gspca_dev->usb_buf[0] = (*sensormap)[1];
401
gspca_dev->usb_buf[1] = (*sensormap)[1] >> 8;
402
reg_w_buf(gspca_dev, (*sensormap)[0], 2);
407
static void write_sensor_72a(struct gspca_dev *gspca_dev,
408
const __u16 (*sensor)[2])
410
while ((*sensor)[0]) {
411
i2c_write(gspca_dev, (*sensor)[1], (*sensor)[0]);
416
static void init_161rev12A(struct gspca_dev *gspca_dev)
418
write_vector(gspca_dev, spca561_161rev12A_data1);
419
sensor_mapwrite(gspca_dev, Pb100_1map8300);
420
/*fixme: should be in sd_start*/
421
write_vector(gspca_dev, spca561_161rev12A_data2);
422
sensor_mapwrite(gspca_dev, Pb100_2map8300);
425
/* this function is called at probe time */
426
static int sd_config(struct gspca_dev *gspca_dev,
427
const struct usb_device_id *id)
429
struct sd *sd = (struct sd *) gspca_dev;
431
__u16 vendor, product;
434
/* Read frm global register the USB product and vendor IDs, just to
435
* prove that we can communicate with the device. This works, which
436
* confirms at we are communicating properly and that the device
438
reg_r(gspca_dev, 0x8104, 1);
439
data1 = gspca_dev->usb_buf[0];
440
reg_r(gspca_dev, 0x8105, 1);
441
data2 = gspca_dev->usb_buf[0];
442
vendor = (data2 << 8) | data1;
443
reg_r(gspca_dev, 0x8106, 1);
444
data1 = gspca_dev->usb_buf[0];
445
reg_r(gspca_dev, 0x8107, 1);
446
data2 = gspca_dev->usb_buf[0];
447
product = (data2 << 8) | data1;
448
if (vendor != id->idVendor || product != id->idProduct) {
449
PDEBUG(D_PROBE, "Bad vendor / product from device");
453
cam = &gspca_dev->cam;
454
gspca_dev->nbalt = 7 + 1; /* choose alternate 7 first */
456
sd->chip_revision = id->driver_info;
457
if (sd->chip_revision == Rev012A) {
458
cam->cam_mode = sif_012a_mode;
459
cam->nmodes = ARRAY_SIZE(sif_012a_mode);
461
cam->cam_mode = sif_072a_mode;
462
cam->nmodes = ARRAY_SIZE(sif_072a_mode);
464
sd->brightness = BRIGHTNESS_DEF;
465
sd->contrast = CONTRAST_DEF;
467
sd->exposure = EXPOSURE_DEF;
468
sd->autogain = AUTOGAIN_DEF;
470
sd->expo12a = EXPO12A_DEF;
474
/* this function is called at probe and resume time */
475
static int sd_init_12a(struct gspca_dev *gspca_dev)
477
PDEBUG(D_STREAM, "Chip revision: 012a");
478
init_161rev12A(gspca_dev);
481
static int sd_init_72a(struct gspca_dev *gspca_dev)
483
PDEBUG(D_STREAM, "Chip revision: 072a");
484
write_vector(gspca_dev, rev72a_reset);
486
write_vector(gspca_dev, rev72a_init_data1);
487
write_sensor_72a(gspca_dev, rev72a_init_sensor1);
488
write_vector(gspca_dev, rev72a_init_data2);
489
write_sensor_72a(gspca_dev, rev72a_init_sensor2);
490
reg_w_val(gspca_dev->dev, 0x8112, 0x30);
495
static void setbrightness(struct gspca_dev *gspca_dev)
497
struct sd *sd = (struct sd *) gspca_dev;
498
struct usb_device *dev = gspca_dev->dev;
501
value = sd->brightness;
503
/* offsets for white balance */
504
reg_w_val(dev, 0x8611, value); /* R */
505
reg_w_val(dev, 0x8612, value); /* Gr */
506
reg_w_val(dev, 0x8613, value); /* B */
507
reg_w_val(dev, 0x8614, value); /* Gb */
510
static void setwhite(struct gspca_dev *gspca_dev)
512
struct sd *sd = (struct sd *) gspca_dev;
517
/* try to emulate MS-win as possible */
519
red = 0x20 + white * 3 / 8;
520
blue = 0x90 - white * 5 / 8;
521
if (sd->chip_revision == Rev012A) {
525
red += sd->contrast - 0x20;
526
blue += sd->contrast - 0x20;
528
reg_w_val(gspca_dev->dev, reg, red);
529
reg_w_val(gspca_dev->dev, reg + 2, blue);
532
static void setcontrast(struct gspca_dev *gspca_dev)
534
struct sd *sd = (struct sd *) gspca_dev;
535
struct usb_device *dev = gspca_dev->dev;
538
if (sd->chip_revision != Rev072A)
540
value = sd->contrast + 0x20;
542
/* gains for white balance */
544
/* reg_w_val(dev, 0x8651, value); * R - done by setwhite */
545
reg_w_val(dev, 0x8652, value); /* Gr */
546
/* reg_w_val(dev, 0x8653, value); * B - done by setwhite */
547
reg_w_val(dev, 0x8654, value); /* Gb */
551
static void setexposure(struct gspca_dev *gspca_dev)
553
struct sd *sd = (struct sd *) gspca_dev;
556
/* Register 0x8309 controls exposure for the spca561,
557
the basic exposure setting goes from 1-2047, where 1 is completely
558
dark and 2047 is very bright. It not only influences exposure but
559
also the framerate (to allow for longer exposure) from 1 - 300 it
560
only raises the exposure time then from 300 - 600 it halves the
561
framerate to be able to further raise the exposure time and for every
562
300 more it halves the framerate again. This allows for a maximum
563
exposure time of circa 0.2 - 0.25 seconds (30 / (2000/3000) fps).
564
Sometimes this is not enough, the 1-2047 uses bits 0-10, bits 11-12
565
configure a divider for the base framerate which us used at the
566
exposure setting of 1-300. These bits configure the base framerate
567
according to the following formula: fps = 60 / (value + 2) */
569
/* We choose to use the high bits setting the fixed framerate divisor
570
asap, as setting high basic exposure setting without the fixed
571
divider in combination with high gains makes the cam stop */
572
int table[] = { 0, 450, 550, 625, EXPOSURE_MAX };
574
for (i = 0; i < ARRAY_SIZE(table) - 1; i++) {
575
if (sd->exposure <= table[i + 1]) {
576
expo = sd->exposure - table[i];
584
gspca_dev->usb_buf[0] = expo;
585
gspca_dev->usb_buf[1] = expo >> 8;
586
reg_w_buf(gspca_dev, 0x8309, 2);
590
static void setgain(struct gspca_dev *gspca_dev)
592
struct sd *sd = (struct sd *) gspca_dev;
594
/* gain reg low 6 bits 0-63 gain, bit 6 and 7, both double the
595
sensitivity when set, so 31 + one of them set == 63, and 15
596
with both of them set == 63 */
598
gspca_dev->usb_buf[0] = sd->gain;
599
else if (sd->gain < 128)
600
gspca_dev->usb_buf[0] = (sd->gain / 2) | 0x40;
602
gspca_dev->usb_buf[0] = (sd->gain / 4) | 0xc0;
604
gspca_dev->usb_buf[1] = 0;
605
reg_w_buf(gspca_dev, 0x8335, 2);
608
static void setautogain(struct gspca_dev *gspca_dev)
610
struct sd *sd = (struct sd *) gspca_dev;
613
sd->ag_cnt = AG_CNT_START;
618
static int sd_start_12a(struct gspca_dev *gspca_dev)
620
struct usb_device *dev = gspca_dev->dev;
622
static const __u8 Reg8391[8] =
623
{0x92, 0x30, 0x20, 0x00, 0x0c, 0x00, 0x00, 0x00};
625
mode = gspca_dev->cam.cam_mode[(int) gspca_dev->curr_mode].priv;
627
/* Use compression on 320x240 and above */
628
reg_w_val(dev, 0x8500, 0x10 | mode);
630
/* I couldn't get the compression to work below 320x240
631
* Fortunately at these resolutions the bandwidth
632
* is sufficient to push raw frames at ~20fps */
633
reg_w_val(dev, 0x8500, mode);
634
} /* -- qq@kuku.eu.org */
636
gspca_dev->usb_buf[0] = 0xaa;
637
gspca_dev->usb_buf[1] = 0x00;
638
reg_w_buf(gspca_dev, 0x8307, 2);
639
/* clock - lower 0x8X values lead to fps > 30 */
640
reg_w_val(gspca_dev->dev, 0x8700, 0x8a);
641
/* 0x8f 0x85 0x27 clock */
642
reg_w_val(gspca_dev->dev, 0x8112, 0x1e | 0x20);
643
reg_w_val(gspca_dev->dev, 0x850b, 0x03);
644
memcpy(gspca_dev->usb_buf, Reg8391, 8);
645
reg_w_buf(gspca_dev, 0x8391, 8);
646
reg_w_buf(gspca_dev, 0x8390, 8);
649
setexposure(gspca_dev);
651
/* Led ON (bit 3 -> 0 */
652
reg_w_val(gspca_dev->dev, 0x8114, 0x00);
655
static int sd_start_72a(struct gspca_dev *gspca_dev)
657
struct usb_device *dev = gspca_dev->dev;
661
write_vector(gspca_dev, rev72a_reset);
663
write_vector(gspca_dev, rev72a_init_data1);
664
write_sensor_72a(gspca_dev, rev72a_init_sensor1);
666
mode = gspca_dev->cam.cam_mode[(int) gspca_dev->curr_mode].priv;
670
Clck = 0x27; /* ms-win 0x87 */
682
reg_w_val(dev, 0x8700, Clck); /* 0x27 clock */
683
reg_w_val(dev, 0x8702, 0x81);
684
reg_w_val(dev, 0x8500, mode); /* mode */
685
write_sensor_72a(gspca_dev, rev72a_init_sensor2);
686
setcontrast(gspca_dev);
687
/* setbrightness(gspca_dev); * fixme: bad values */
688
setautogain(gspca_dev);
689
reg_w_val(dev, 0x8112, 0x10 | 0x20);
693
static void sd_stopN(struct gspca_dev *gspca_dev)
695
struct sd *sd = (struct sd *) gspca_dev;
697
if (sd->chip_revision == Rev012A) {
698
reg_w_val(gspca_dev->dev, 0x8112, 0x0e);
699
/* Led Off (bit 3 -> 1 */
700
reg_w_val(gspca_dev->dev, 0x8114, 0x08);
702
reg_w_val(gspca_dev->dev, 0x8112, 0x20);
703
/* reg_w_val(gspca_dev->dev, 0x8102, 0x00); ?? */
707
static void do_autogain(struct gspca_dev *gspca_dev)
709
struct sd *sd = (struct sd *) gspca_dev;
715
__u8 luma_mean = 110;
716
__u8 luma_delta = 20;
721
if (--sd->ag_cnt >= 0)
723
sd->ag_cnt = AG_CNT_START;
725
switch (sd->chip_revision) {
727
reg_r(gspca_dev, 0x8621, 1);
728
Gr = gspca_dev->usb_buf[0];
729
reg_r(gspca_dev, 0x8622, 1);
730
R = gspca_dev->usb_buf[0];
731
reg_r(gspca_dev, 0x8623, 1);
732
B = gspca_dev->usb_buf[0];
733
reg_r(gspca_dev, 0x8624, 1);
734
Gb = gspca_dev->usb_buf[0];
735
y = (77 * R + 75 * (Gr + Gb) + 29 * B) >> 8;
736
/* u= (128*B-(43*(Gr+Gb+R))) >> 8; */
737
/* v= (128*R-(53*(Gr+Gb))-21*B) >> 8; */
738
/* PDEBUG(D_CONF,"reading Y %d U %d V %d ",y,u,v); */
740
if (y < luma_mean - luma_delta ||
741
y > luma_mean + luma_delta) {
742
expotimes = i2c_read(gspca_dev, 0x09, 0x10);
744
expotimes = expotimes & 0x07ff;
746
"Exposition Times 0x%03X Clock 0x%04X ",
747
expotimes,pixelclk); */
748
gainG = i2c_read(gspca_dev, 0x35, 0x10);
750
"reading Gain register %d", gainG); */
752
expotimes += (luma_mean - y) >> spring;
753
gainG += (luma_mean - y) / 50;
755
"compute expotimes %d gain %d",
762
i2c_write(gspca_dev, gainG, 0x35);
764
if (expotimes > 0x0256)
766
else if (expotimes < 3)
768
i2c_write(gspca_dev, expotimes | pixelclk, 0x09);
774
static void sd_pkt_scan(struct gspca_dev *gspca_dev,
775
u8 *data, /* isoc packet */
776
int len) /* iso packet length */
778
struct sd *sd = (struct sd *) gspca_dev;
781
switch (*data++) { /* sequence number */
782
case 0: /* start of frame */
783
gspca_frame_add(gspca_dev, LAST_PACKET, NULL, 0);
785
/* This should never happen */
787
PDEBUG(D_ERR, "Short SOF packet, ignoring");
788
gspca_dev->last_packet_type = DISCARD_PACKET;
792
#if defined(CONFIG_INPUT) || defined(CONFIG_INPUT_MODULE)
793
if (data[0] & 0x20) {
794
input_report_key(gspca_dev->input_dev, KEY_CAMERA, 1);
795
input_sync(gspca_dev->input_dev);
796
input_report_key(gspca_dev->input_dev, KEY_CAMERA, 0);
797
input_sync(gspca_dev->input_dev);
801
if (data[1] & 0x10) {
802
/* compressed bayer */
803
gspca_frame_add(gspca_dev, FIRST_PACKET, data, len);
805
/* raw bayer (with a header, which we skip) */
806
if (sd->chip_revision == Rev012A) {
813
gspca_frame_add(gspca_dev, FIRST_PACKET, data, len);
816
case 0xff: /* drop (empty mpackets) */
819
gspca_frame_add(gspca_dev, INTER_PACKET, data, len);
823
static int sd_setbrightness(struct gspca_dev *gspca_dev, __s32 val)
825
struct sd *sd = (struct sd *) gspca_dev;
827
sd->brightness = val;
828
if (gspca_dev->streaming)
829
setbrightness(gspca_dev);
833
static int sd_getbrightness(struct gspca_dev *gspca_dev, __s32 *val)
835
struct sd *sd = (struct sd *) gspca_dev;
837
*val = sd->brightness;
842
static int sd_setcontrast(struct gspca_dev *gspca_dev, __s32 val)
844
struct sd *sd = (struct sd *) gspca_dev;
847
if (gspca_dev->streaming)
848
setcontrast(gspca_dev);
852
static int sd_getcontrast(struct gspca_dev *gspca_dev, __s32 *val)
854
struct sd *sd = (struct sd *) gspca_dev;
860
static int sd_setautogain(struct gspca_dev *gspca_dev, __s32 val)
862
struct sd *sd = (struct sd *) gspca_dev;
865
if (gspca_dev->streaming)
866
setautogain(gspca_dev);
870
static int sd_getautogain(struct gspca_dev *gspca_dev, __s32 *val)
872
struct sd *sd = (struct sd *) gspca_dev;
878
static int sd_setwhite(struct gspca_dev *gspca_dev, __s32 val)
880
struct sd *sd = (struct sd *) gspca_dev;
883
if (gspca_dev->streaming)
888
static int sd_getwhite(struct gspca_dev *gspca_dev, __s32 *val)
890
struct sd *sd = (struct sd *) gspca_dev;
897
static int sd_setexposure(struct gspca_dev *gspca_dev, __s32 val)
899
struct sd *sd = (struct sd *) gspca_dev;
902
if (gspca_dev->streaming)
903
setexposure(gspca_dev);
907
static int sd_getexposure(struct gspca_dev *gspca_dev, __s32 *val)
909
struct sd *sd = (struct sd *) gspca_dev;
916
static int sd_setgain(struct gspca_dev *gspca_dev, __s32 val)
918
struct sd *sd = (struct sd *) gspca_dev;
921
if (gspca_dev->streaming)
926
static int sd_getgain(struct gspca_dev *gspca_dev, __s32 *val)
928
struct sd *sd = (struct sd *) gspca_dev;
935
static const struct ctrl sd_ctrls_12a[] = {
939
.type = V4L2_CTRL_TYPE_INTEGER,
944
.default_value = HUE_DEF,
951
.id = V4L2_CID_EXPOSURE,
952
.type = V4L2_CTRL_TYPE_INTEGER,
954
.minimum = EXPOSURE_MIN,
955
.maximum = EXPOSURE_MAX,
957
.default_value = EXPOSURE_DEF,
959
.set = sd_setexposure,
960
.get = sd_getexposure,
965
.type = V4L2_CTRL_TYPE_INTEGER,
970
.default_value = GAIN_DEF,
977
static const struct ctrl sd_ctrls_72a[] = {
981
.type = V4L2_CTRL_TYPE_INTEGER,
986
.default_value = HUE_DEF,
993
.id = V4L2_CID_BRIGHTNESS,
994
.type = V4L2_CTRL_TYPE_INTEGER,
995
.name = "Brightness",
996
.minimum = BRIGHTNESS_MIN,
997
.maximum = BRIGHTNESS_MAX,
999
.default_value = BRIGHTNESS_DEF,
1001
.set = sd_setbrightness,
1002
.get = sd_getbrightness,
1006
.id = V4L2_CID_CONTRAST,
1007
.type = V4L2_CTRL_TYPE_INTEGER,
1009
.minimum = CONTRAST_MIN,
1010
.maximum = CONTRAST_MAX,
1012
.default_value = CONTRAST_DEF,
1014
.set = sd_setcontrast,
1015
.get = sd_getcontrast,
1019
.id = V4L2_CID_AUTOGAIN,
1020
.type = V4L2_CTRL_TYPE_BOOLEAN,
1021
.name = "Auto Gain",
1022
.minimum = AUTOGAIN_MIN,
1023
.maximum = AUTOGAIN_MAX,
1025
.default_value = AUTOGAIN_DEF,
1027
.set = sd_setautogain,
1028
.get = sd_getautogain,
1032
/* sub-driver description */
1033
static const struct sd_desc sd_desc_12a = {
1034
.name = MODULE_NAME,
1035
.ctrls = sd_ctrls_12a,
1036
.nctrls = ARRAY_SIZE(sd_ctrls_12a),
1037
.config = sd_config,
1038
.init = sd_init_12a,
1039
.start = sd_start_12a,
1041
.pkt_scan = sd_pkt_scan,
1042
#if defined(CONFIG_INPUT) || defined(CONFIG_INPUT_MODULE)
1046
static const struct sd_desc sd_desc_72a = {
1047
.name = MODULE_NAME,
1048
.ctrls = sd_ctrls_72a,
1049
.nctrls = ARRAY_SIZE(sd_ctrls_72a),
1050
.config = sd_config,
1051
.init = sd_init_72a,
1052
.start = sd_start_72a,
1054
.pkt_scan = sd_pkt_scan,
1055
.dq_callback = do_autogain,
1056
#if defined(CONFIG_INPUT) || defined(CONFIG_INPUT_MODULE)
1060
static const struct sd_desc *sd_desc[2] = {
1065
/* -- module initialisation -- */
1066
static const struct usb_device_id device_table[] = {
1067
{USB_DEVICE(0x041e, 0x401a), .driver_info = Rev072A},
1068
{USB_DEVICE(0x041e, 0x403b), .driver_info = Rev012A},
1069
{USB_DEVICE(0x0458, 0x7004), .driver_info = Rev072A},
1070
{USB_DEVICE(0x0461, 0x0815), .driver_info = Rev072A},
1071
{USB_DEVICE(0x046d, 0x0928), .driver_info = Rev012A},
1072
{USB_DEVICE(0x046d, 0x0929), .driver_info = Rev012A},
1073
{USB_DEVICE(0x046d, 0x092a), .driver_info = Rev012A},
1074
{USB_DEVICE(0x046d, 0x092b), .driver_info = Rev012A},
1075
{USB_DEVICE(0x046d, 0x092c), .driver_info = Rev012A},
1076
{USB_DEVICE(0x046d, 0x092d), .driver_info = Rev012A},
1077
{USB_DEVICE(0x046d, 0x092e), .driver_info = Rev012A},
1078
{USB_DEVICE(0x046d, 0x092f), .driver_info = Rev012A},
1079
{USB_DEVICE(0x04fc, 0x0561), .driver_info = Rev072A},
1080
{USB_DEVICE(0x060b, 0xa001), .driver_info = Rev072A},
1081
{USB_DEVICE(0x10fd, 0x7e50), .driver_info = Rev072A},
1082
{USB_DEVICE(0xabcd, 0xcdee), .driver_info = Rev072A},
1086
MODULE_DEVICE_TABLE(usb, device_table);
1088
/* -- device connect -- */
1089
static int sd_probe(struct usb_interface *intf,
1090
const struct usb_device_id *id)
1092
return gspca_dev_probe(intf, id,
1093
sd_desc[id->driver_info],
1098
static struct usb_driver sd_driver = {
1099
.name = MODULE_NAME,
1100
.id_table = device_table,
1102
.disconnect = gspca_disconnect,
1104
.suspend = gspca_suspend,
1105
.resume = gspca_resume,
1109
/* -- module insert / remove -- */
1110
static int __init sd_mod_init(void)
1112
return usb_register(&sd_driver);
1114
static void __exit sd_mod_exit(void)
1116
usb_deregister(&sd_driver);
1119
module_init(sd_mod_init);
1120
module_exit(sd_mod_exit);