2 * Pixart PAC7302 library
3 * Copyright (C) 2005 Thomas Kaiser thomas@kaiser-linux.li
5 * V4L2 by Jean-Francois Moine <http://moinejf.free.fr>
7 * Separated from Pixart PAC7311 library by Márton Németh
8 * Camera button input handling by Márton Németh <nm127@freemail.hu>
9 * Copyright (C) 2009-2010 Márton Németh <nm127@freemail.hu>
11 * This program is free software; you can redistribute it and/or modify
12 * it under the terms of the GNU General Public License as published by
13 * the Free Software Foundation; either version 2 of the License, or
16 * This program is distributed in the hope that it will be useful,
17 * but WITHOUT ANY WARRANTY; without even the implied warranty of
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19 * GNU General Public License for more details.
21 * You should have received a copy of the GNU General Public License
22 * along with this program; if not, write to the Free Software
23 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
26 /* Some documentation about various registers as determined by trial and error.
31 0x78 Global control, bit 6 controls the LED (inverted)
36 0x02 Clock divider 3-63, fps = 90 / val. Must be a multiple of 3 on
37 the 7302, so one of 3, 6, 9, ..., except when between 6 and 12?
38 0x03 Variable framerate ctrl reg2==3: 0 -> ~30 fps, 255 -> ~22fps
39 0x04 Another var framerate ctrl reg2==3, reg3==0: 0 -> ~30 fps,
40 63 -> ~27 fps, the 2 msb's must always be 1 !!
41 0x05 Another var framerate ctrl reg2==3, reg3==0, reg4==0xc0:
42 1 -> ~30 fps, 2 -> ~20 fps
43 0x0e Exposure bits 0-7, 0-448, 0 = use full frame time
44 0x0f Exposure bit 8, 0-448, 448 = no exposure at all
46 0x21 Bitfield: 0-1 unused, 2-3 vflip/hflip, 4-5 unknown, 6-7 unused
48 The registers are accessed in the following functions:
50 Page | Register | Function
51 -----+------------+---------------------------------------------------
52 0 | 0x0f..0x20 | setcolors()
53 0 | 0xa2..0xab | setbrightcont()
54 0 | 0xc5 | setredbalance()
55 0 | 0xc6 | setwhitebalance()
56 0 | 0xc7 | setbluebalance()
57 0 | 0xdc | setbrightcont(), setcolors()
58 3 | 0x02 | setexposure()
60 3 | 0x11 | setcolors(), setgain(), setexposure(), sethvflip()
61 3 | 0x21 | sethvflip()
64 #define MODULE_NAME "pac7302"
66 #include <linux/input.h>
67 #include <media/v4l2-chip-ident.h>
70 MODULE_AUTHOR("Thomas Kaiser thomas@kaiser-linux.li");
71 MODULE_DESCRIPTION("Pixart PAC7302");
72 MODULE_LICENSE("GPL");
74 /* specific webcam descriptor for pac7302 */
76 struct gspca_dev gspca_dev
; /* !! must be the first item */
78 unsigned char brightness
;
79 unsigned char contrast
;
81 unsigned char white_balance
;
82 unsigned char red_balance
;
83 unsigned char blue_balance
;
85 unsigned char autogain
;
86 unsigned short exposure
;
90 #define FL_HFLIP 0x01 /* mirrored by default */
91 #define FL_VFLIP 0x02 /* vertical flipped by default */
94 u8 autogain_ignore_frames
;
99 /* V4L2 controls supported by the driver */
100 static int sd_setbrightness(struct gspca_dev
*gspca_dev
, __s32 val
);
101 static int sd_getbrightness(struct gspca_dev
*gspca_dev
, __s32
*val
);
102 static int sd_setcontrast(struct gspca_dev
*gspca_dev
, __s32 val
);
103 static int sd_getcontrast(struct gspca_dev
*gspca_dev
, __s32
*val
);
104 static int sd_setcolors(struct gspca_dev
*gspca_dev
, __s32 val
);
105 static int sd_getcolors(struct gspca_dev
*gspca_dev
, __s32
*val
);
106 static int sd_setwhitebalance(struct gspca_dev
*gspca_dev
, __s32 val
);
107 static int sd_getwhitebalance(struct gspca_dev
*gspca_dev
, __s32
*val
);
108 static int sd_setredbalance(struct gspca_dev
*gspca_dev
, __s32 val
);
109 static int sd_getredbalance(struct gspca_dev
*gspca_dev
, __s32
*val
);
110 static int sd_setbluebalance(struct gspca_dev
*gspca_dev
, __s32 val
);
111 static int sd_getbluebalance(struct gspca_dev
*gspca_dev
, __s32
*val
);
112 static int sd_setautogain(struct gspca_dev
*gspca_dev
, __s32 val
);
113 static int sd_getautogain(struct gspca_dev
*gspca_dev
, __s32
*val
);
114 static int sd_sethflip(struct gspca_dev
*gspca_dev
, __s32 val
);
115 static int sd_gethflip(struct gspca_dev
*gspca_dev
, __s32
*val
);
116 static int sd_setvflip(struct gspca_dev
*gspca_dev
, __s32 val
);
117 static int sd_getvflip(struct gspca_dev
*gspca_dev
, __s32
*val
);
118 static int sd_setgain(struct gspca_dev
*gspca_dev
, __s32 val
);
119 static int sd_getgain(struct gspca_dev
*gspca_dev
, __s32
*val
);
120 static int sd_setexposure(struct gspca_dev
*gspca_dev
, __s32 val
);
121 static int sd_getexposure(struct gspca_dev
*gspca_dev
, __s32
*val
);
123 static const struct ctrl sd_ctrls
[] = {
126 .id
= V4L2_CID_BRIGHTNESS
,
127 .type
= V4L2_CTRL_TYPE_INTEGER
,
128 .name
= "Brightness",
130 #define BRIGHTNESS_MAX 0x20
131 .maximum
= BRIGHTNESS_MAX
,
133 #define BRIGHTNESS_DEF 0x10
134 .default_value
= BRIGHTNESS_DEF
,
136 .set
= sd_setbrightness
,
137 .get
= sd_getbrightness
,
141 .id
= V4L2_CID_CONTRAST
,
142 .type
= V4L2_CTRL_TYPE_INTEGER
,
145 #define CONTRAST_MAX 255
146 .maximum
= CONTRAST_MAX
,
148 #define CONTRAST_DEF 127
149 .default_value
= CONTRAST_DEF
,
151 .set
= sd_setcontrast
,
152 .get
= sd_getcontrast
,
156 .id
= V4L2_CID_SATURATION
,
157 .type
= V4L2_CTRL_TYPE_INTEGER
,
158 .name
= "Saturation",
160 #define COLOR_MAX 255
161 .maximum
= COLOR_MAX
,
163 #define COLOR_DEF 127
164 .default_value
= COLOR_DEF
,
171 .id
= V4L2_CID_WHITE_BALANCE_TEMPERATURE
,
172 .type
= V4L2_CTRL_TYPE_INTEGER
,
173 .name
= "White Balance",
177 #define WHITEBALANCE_DEF 4
178 .default_value
= WHITEBALANCE_DEF
,
180 .set
= sd_setwhitebalance
,
181 .get
= sd_getwhitebalance
,
185 .id
= V4L2_CID_RED_BALANCE
,
186 .type
= V4L2_CTRL_TYPE_INTEGER
,
191 #define REDBALANCE_DEF 1
192 .default_value
= REDBALANCE_DEF
,
194 .set
= sd_setredbalance
,
195 .get
= sd_getredbalance
,
199 .id
= V4L2_CID_BLUE_BALANCE
,
200 .type
= V4L2_CTRL_TYPE_INTEGER
,
205 #define BLUEBALANCE_DEF 1
206 .default_value
= BLUEBALANCE_DEF
,
208 .set
= sd_setbluebalance
,
209 .get
= sd_getbluebalance
,
214 .type
= V4L2_CTRL_TYPE_INTEGER
,
221 #define GAIN_KNEE 255 /* Gain seems to cause little noise on the pac73xx */
222 .default_value
= GAIN_DEF
,
229 .id
= V4L2_CID_EXPOSURE
,
230 .type
= V4L2_CTRL_TYPE_INTEGER
,
235 #define EXPOSURE_DEF 66 /* 33 ms / 30 fps */
236 #define EXPOSURE_KNEE 133 /* 66 ms / 15 fps */
237 .default_value
= EXPOSURE_DEF
,
239 .set
= sd_setexposure
,
240 .get
= sd_getexposure
,
244 .id
= V4L2_CID_AUTOGAIN
,
245 .type
= V4L2_CTRL_TYPE_BOOLEAN
,
250 #define AUTOGAIN_DEF 1
251 .default_value
= AUTOGAIN_DEF
,
253 .set
= sd_setautogain
,
254 .get
= sd_getautogain
,
258 .id
= V4L2_CID_HFLIP
,
259 .type
= V4L2_CTRL_TYPE_BOOLEAN
,
265 .default_value
= HFLIP_DEF
,
272 .id
= V4L2_CID_VFLIP
,
273 .type
= V4L2_CTRL_TYPE_BOOLEAN
,
279 .default_value
= VFLIP_DEF
,
286 static const struct v4l2_pix_format vga_mode
[] = {
287 {640, 480, V4L2_PIX_FMT_PJPG
, V4L2_FIELD_NONE
,
289 .sizeimage
= 640 * 480 * 3 / 8 + 590,
290 .colorspace
= V4L2_COLORSPACE_JPEG
,
294 #define LOAD_PAGE3 255
295 #define END_OF_SEQUENCE 0
298 static const __u8 init_7302
[] = {
300 0xff, 0x01, /* page 1 */
301 0x78, 0x00, /* deactivate */
303 0x78, 0x40, /* led off */
305 static const __u8 start_7302
[] = {
306 /* index, len, [value]* */
307 0xff, 1, 0x00, /* page 0 */
308 0x00, 12, 0x01, 0x40, 0x40, 0x40, 0x01, 0xe0, 0x02, 0x80,
309 0x00, 0x00, 0x00, 0x00,
310 0x0d, 24, 0x03, 0x01, 0x00, 0xb5, 0x07, 0xcb, 0x00, 0x00,
311 0x07, 0xc8, 0x00, 0xea, 0x07, 0xcf, 0x07, 0xf7,
312 0x07, 0x7e, 0x01, 0x0b, 0x00, 0x00, 0x00, 0x11,
316 0x3a, 3, 0x14, 0xff, 0x5a,
317 0x43, 11, 0x00, 0x0a, 0x18, 0x11, 0x01, 0x2c, 0x88, 0x11,
320 0x62, 4, 0x10, 0x1e, 0x1e, 0x18,
322 0x6e, 3, 0x08, 0x06, 0x00,
323 0x72, 3, 0x00, 0xff, 0x00,
324 0x7d, 23, 0x01, 0x01, 0x58, 0x46, 0x50, 0x3c, 0x50, 0x3c,
325 0x54, 0x46, 0x54, 0x56, 0x52, 0x50, 0x52, 0x50,
326 0x56, 0x64, 0xa4, 0x00, 0xda, 0x00, 0x00,
327 0xa2, 10, 0x22, 0x2c, 0x3c, 0x54, 0x69, 0x7c, 0x9c, 0xb9,
332 0xc4, 4, 0xae, 0x01, 0x04, 0x01,
334 0xd1, 11, 0x01, 0x30, 0x49, 0x5e, 0x6f, 0x7f, 0x8e, 0xa9,
337 0xff, 1, 0x01, /* page 1 */
338 0x12, 3, 0x02, 0x00, 0x01,
340 0x76, 5, 0x01, 0x20, 0x40, 0x00, 0xf2,
342 0x7f, 10, 0x4b, 0x0f, 0x01, 0x2c, 0x02, 0x58, 0x03, 0x20,
344 0x96, 5, 0x01, 0x10, 0x04, 0x01, 0x04,
345 0xc8, 14, 0x00, 0x00, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00,
346 0x07, 0x00, 0x01, 0x07, 0x04, 0x01,
349 0xde, 7, 0x00, 0x01, 0x04, 0x04, 0x00, 0x00, 0x00,
350 0xe6, 4, 0x00, 0x00, 0x00, 0x01,
352 0xff, 1, 0x02, /* page 2 */
354 0xff, 1, 0x03, /* page 3 */
355 0, LOAD_PAGE3
, /* load the page 3 */
357 0xff, 1, 0x02, /* page 2 */
359 0x22, 4, 0x1f, 0xa4, 0xf0, 0x96,
361 0x2a, 5, 0xc8, 0x00, 0x18, 0x12, 0x22,
362 0x64, 8, 0x00, 0x00, 0xf0, 0x01, 0x14, 0x44, 0x44, 0x44,
364 0xff, 1, 0x01, /* page 1 */
366 0, END_OF_SEQUENCE
/* end of sequence */
370 /* page 3 - the value SKIP says skip the index - see reg_w_page() */
371 static const __u8 page3_7302
[] = {
372 0x90, 0x40, 0x03, 0x00, 0xc0, 0x01, 0x14, 0x16,
373 0x14, 0x12, 0x00, 0x00, 0x00, 0x02, 0x33, 0x00,
374 0x0f, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
375 0x00, 0x00, 0x00, 0x47, 0x01, 0xb3, 0x01, 0x00,
376 0x00, 0x08, 0x00, 0x00, 0x0d, 0x00, 0x00, 0x21,
377 0x00, 0x00, 0x00, 0x54, 0xf4, 0x02, 0x52, 0x54,
378 0xa4, 0xb8, 0xe0, 0x2a, 0xf6, 0x00, 0x00, 0x00,
379 0x00, 0x1e, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
380 0x00, 0xfc, 0x00, 0xf2, 0x1f, 0x04, 0x00, 0x00,
381 SKIP
, 0x00, 0x00, 0xc0, 0xc0, 0x10, 0x00, 0x00,
382 0x00, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
383 0x00, 0x40, 0xff, 0x03, 0x19, 0x00, 0x00, 0x00,
384 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
385 0x00, 0x00, 0x00, 0x00, 0x00, 0xc8, 0xc8, 0xc8,
386 0xc8, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x50,
387 0x08, 0x10, 0x24, 0x40, 0x00, 0x00, 0x00, 0x00,
388 0x01, 0x00, 0x02, 0x47, 0x00, 0x00, 0x00, 0x00,
389 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
390 0x00, 0x02, 0xfa, 0x00, 0x64, 0x5a, 0x28, 0x00,
394 static void reg_w_buf(struct gspca_dev
*gspca_dev
,
396 const char *buffer
, int len
)
400 if (gspca_dev
->usb_err
< 0)
402 memcpy(gspca_dev
->usb_buf
, buffer
, len
);
403 ret
= usb_control_msg(gspca_dev
->dev
,
404 usb_sndctrlpipe(gspca_dev
->dev
, 0),
406 USB_DIR_OUT
| USB_TYPE_VENDOR
| USB_RECIP_DEVICE
,
408 index
, gspca_dev
->usb_buf
, len
,
411 PDEBUG(D_ERR
, "reg_w_buf(): "
412 "Failed to write registers to index 0x%x, error %i",
414 gspca_dev
->usb_err
= ret
;
419 static void reg_w(struct gspca_dev
*gspca_dev
,
425 if (gspca_dev
->usb_err
< 0)
427 gspca_dev
->usb_buf
[0] = value
;
428 ret
= usb_control_msg(gspca_dev
->dev
,
429 usb_sndctrlpipe(gspca_dev
->dev
, 0),
431 USB_DIR_OUT
| USB_TYPE_VENDOR
| USB_RECIP_DEVICE
,
432 0, index
, gspca_dev
->usb_buf
, 1,
435 PDEBUG(D_ERR
, "reg_w(): "
436 "Failed to write register to index 0x%x, value 0x%x, error %i",
438 gspca_dev
->usb_err
= ret
;
442 static void reg_w_seq(struct gspca_dev
*gspca_dev
,
443 const __u8
*seq
, int len
)
446 reg_w(gspca_dev
, seq
[0], seq
[1]);
451 /* load the beginning of a page */
452 static void reg_w_page(struct gspca_dev
*gspca_dev
,
453 const __u8
*page
, int len
)
458 if (gspca_dev
->usb_err
< 0)
460 for (index
= 0; index
< len
; index
++) {
461 if (page
[index
] == SKIP
) /* skip this index */
463 gspca_dev
->usb_buf
[0] = page
[index
];
464 ret
= usb_control_msg(gspca_dev
->dev
,
465 usb_sndctrlpipe(gspca_dev
->dev
, 0),
467 USB_DIR_OUT
| USB_TYPE_VENDOR
| USB_RECIP_DEVICE
,
468 0, index
, gspca_dev
->usb_buf
, 1,
471 PDEBUG(D_ERR
, "reg_w_page(): "
472 "Failed to write register to index 0x%x, "
473 "value 0x%x, error %i",
474 index
, page
[index
], ret
);
475 gspca_dev
->usb_err
= ret
;
481 /* output a variable sequence */
482 static void reg_w_var(struct gspca_dev
*gspca_dev
,
484 const __u8
*page3
, unsigned int page3_len
)
492 case END_OF_SEQUENCE
:
495 reg_w_page(gspca_dev
, page3
, page3_len
);
498 if (len
> USB_BUF_SZ
) {
499 PDEBUG(D_ERR
|D_STREAM
,
500 "Incorrect variable sequence");
510 reg_w_buf(gspca_dev
, index
, seq
, 8);
520 /* this function is called at probe time for pac7302 */
521 static int sd_config(struct gspca_dev
*gspca_dev
,
522 const struct usb_device_id
*id
)
524 struct sd
*sd
= (struct sd
*) gspca_dev
;
527 cam
= &gspca_dev
->cam
;
529 PDEBUG(D_CONF
, "Find Sensor PAC7302");
530 cam
->cam_mode
= vga_mode
; /* only 640x480 */
531 cam
->nmodes
= ARRAY_SIZE(vga_mode
);
533 sd
->brightness
= BRIGHTNESS_DEF
;
534 sd
->contrast
= CONTRAST_DEF
;
535 sd
->colors
= COLOR_DEF
;
536 sd
->white_balance
= WHITEBALANCE_DEF
;
537 sd
->red_balance
= REDBALANCE_DEF
;
538 sd
->blue_balance
= BLUEBALANCE_DEF
;
540 sd
->exposure
= EXPOSURE_DEF
;
541 sd
->autogain
= AUTOGAIN_DEF
;
542 sd
->hflip
= HFLIP_DEF
;
543 sd
->vflip
= VFLIP_DEF
;
544 sd
->flags
= id
->driver_info
;
548 /* This function is used by pac7302 only */
549 static void setbrightcont(struct gspca_dev
*gspca_dev
)
551 struct sd
*sd
= (struct sd
*) gspca_dev
;
553 static const __u8 max
[10] =
554 {0x29, 0x33, 0x42, 0x5a, 0x6e, 0x80, 0x9f, 0xbb,
556 static const __u8 delta
[10] =
557 {0x35, 0x33, 0x33, 0x2f, 0x2a, 0x25, 0x1e, 0x17,
560 reg_w(gspca_dev
, 0xff, 0x00); /* page 0 */
561 for (i
= 0; i
< 10; i
++) {
563 v
+= (sd
->brightness
- BRIGHTNESS_MAX
)
564 * 150 / BRIGHTNESS_MAX
; /* 200 ? */
565 v
-= delta
[i
] * sd
->contrast
/ CONTRAST_MAX
;
570 reg_w(gspca_dev
, 0xa2 + i
, v
);
572 reg_w(gspca_dev
, 0xdc, 0x01);
575 /* This function is used by pac7302 only */
576 static void setcolors(struct gspca_dev
*gspca_dev
)
578 struct sd
*sd
= (struct sd
*) gspca_dev
;
580 static const int a
[9] =
581 {217, -212, 0, -101, 170, -67, -38, -315, 355};
582 static const int b
[9] =
583 {19, 106, 0, 19, 106, 1, 19, 106, 1};
585 reg_w(gspca_dev
, 0xff, 0x03); /* page 3 */
586 reg_w(gspca_dev
, 0x11, 0x01);
587 reg_w(gspca_dev
, 0xff, 0x00); /* page 0 */
588 for (i
= 0; i
< 9; i
++) {
589 v
= a
[i
] * sd
->colors
/ COLOR_MAX
+ b
[i
];
590 reg_w(gspca_dev
, 0x0f + 2 * i
, (v
>> 8) & 0x07);
591 reg_w(gspca_dev
, 0x0f + 2 * i
+ 1, v
);
593 reg_w(gspca_dev
, 0xdc, 0x01);
594 PDEBUG(D_CONF
|D_STREAM
, "color: %i", sd
->colors
);
597 static void setwhitebalance(struct gspca_dev
*gspca_dev
)
599 struct sd
*sd
= (struct sd
*) gspca_dev
;
601 reg_w(gspca_dev
, 0xff, 0x00); /* page 0 */
602 reg_w(gspca_dev
, 0xc6, sd
->white_balance
);
604 reg_w(gspca_dev
, 0xdc, 0x01);
605 PDEBUG(D_CONF
|D_STREAM
, "white_balance: %i", sd
->white_balance
);
608 static void setredbalance(struct gspca_dev
*gspca_dev
)
610 struct sd
*sd
= (struct sd
*) gspca_dev
;
612 reg_w(gspca_dev
, 0xff, 0x00); /* page 0 */
613 reg_w(gspca_dev
, 0xc5, sd
->red_balance
);
615 reg_w(gspca_dev
, 0xdc, 0x01);
616 PDEBUG(D_CONF
|D_STREAM
, "red_balance: %i", sd
->red_balance
);
619 static void setbluebalance(struct gspca_dev
*gspca_dev
)
621 struct sd
*sd
= (struct sd
*) gspca_dev
;
623 reg_w(gspca_dev
, 0xff, 0x00); /* page 0 */
624 reg_w(gspca_dev
, 0xc7, sd
->blue_balance
);
626 reg_w(gspca_dev
, 0xdc, 0x01);
627 PDEBUG(D_CONF
|D_STREAM
, "blue_balance: %i", sd
->blue_balance
);
630 static void setgain(struct gspca_dev
*gspca_dev
)
632 struct sd
*sd
= (struct sd
*) gspca_dev
;
634 reg_w(gspca_dev
, 0xff, 0x03); /* page 3 */
635 reg_w(gspca_dev
, 0x10, sd
->gain
>> 3);
637 /* load registers to sensor (Bit 0, auto clear) */
638 reg_w(gspca_dev
, 0x11, 0x01);
641 static void setexposure(struct gspca_dev
*gspca_dev
)
643 struct sd
*sd
= (struct sd
*) gspca_dev
;
647 /* register 2 of frame 3 contains the clock divider configuring the
648 no fps according to the formula: 90 / reg. sd->exposure is the
649 desired exposure time in 0.5 ms. */
650 clockdiv
= (90 * sd
->exposure
+ 1999) / 2000;
652 /* Note clockdiv = 3 also works, but when running at 30 fps, depending
653 on the scene being recorded, the camera switches to another
654 quantization table for certain JPEG blocks, and we don't know how
655 to decompress these blocks. So we cap the framerate at 15 fps */
658 else if (clockdiv
> 63)
661 /* reg2 MUST be a multiple of 3, except when between 6 and 12?
662 Always round up, otherwise we cannot get the desired frametime
663 using the partial frame time exposure control */
664 if (clockdiv
< 6 || clockdiv
> 12)
665 clockdiv
= ((clockdiv
+ 2) / 3) * 3;
667 /* frame exposure time in ms = 1000 * clockdiv / 90 ->
668 exposure = (sd->exposure / 2) * 448 / (1000 * clockdiv / 90) */
669 exposure
= (sd
->exposure
* 45 * 448) / (1000 * clockdiv
);
670 /* 0 = use full frametime, 448 = no exposure, reverse it */
671 exposure
= 448 - exposure
;
673 reg_w(gspca_dev
, 0xff, 0x03); /* page 3 */
674 reg_w(gspca_dev
, 0x02, clockdiv
);
675 reg_w(gspca_dev
, 0x0e, exposure
& 0xff);
676 reg_w(gspca_dev
, 0x0f, exposure
>> 8);
678 /* load registers to sensor (Bit 0, auto clear) */
679 reg_w(gspca_dev
, 0x11, 0x01);
682 static void sethvflip(struct gspca_dev
*gspca_dev
)
684 struct sd
*sd
= (struct sd
*) gspca_dev
;
685 u8 data
, hflip
, vflip
;
688 if (sd
->flags
& FL_HFLIP
)
691 if (sd
->flags
& FL_VFLIP
)
694 reg_w(gspca_dev
, 0xff, 0x03); /* page 3 */
695 data
= (hflip
? 0x08 : 0x00) | (vflip
? 0x04 : 0x00);
696 reg_w(gspca_dev
, 0x21, data
);
698 /* load registers to sensor (Bit 0, auto clear) */
699 reg_w(gspca_dev
, 0x11, 0x01);
702 /* this function is called at probe and resume time for pac7302 */
703 static int sd_init(struct gspca_dev
*gspca_dev
)
705 reg_w_seq(gspca_dev
, init_7302
, sizeof(init_7302
)/2);
706 return gspca_dev
->usb_err
;
709 static int sd_start(struct gspca_dev
*gspca_dev
)
711 struct sd
*sd
= (struct sd
*) gspca_dev
;
715 reg_w_var(gspca_dev
, start_7302
,
716 page3_7302
, sizeof(page3_7302
));
717 setbrightcont(gspca_dev
);
718 setcolors(gspca_dev
);
719 setwhitebalance(gspca_dev
);
720 setredbalance(gspca_dev
);
721 setbluebalance(gspca_dev
);
723 setexposure(gspca_dev
);
724 sethvflip(gspca_dev
);
726 /* only resolution 640x480 is supported for pac7302 */
729 sd
->autogain_ignore_frames
= 0;
730 atomic_set(&sd
->avg_lum
, -1);
733 reg_w(gspca_dev
, 0xff, 0x01);
734 reg_w(gspca_dev
, 0x78, 0x01);
736 return gspca_dev
->usb_err
;
739 static void sd_stopN(struct gspca_dev
*gspca_dev
)
743 reg_w(gspca_dev
, 0xff, 0x01);
744 reg_w(gspca_dev
, 0x78, 0x00);
747 /* called on streamoff with alt 0 and on disconnect for pac7302 */
748 static void sd_stop0(struct gspca_dev
*gspca_dev
)
750 if (!gspca_dev
->present
)
752 reg_w(gspca_dev
, 0xff, 0x01);
753 reg_w(gspca_dev
, 0x78, 0x40);
756 /* Include pac common sof detection functions */
757 #include "pac_common.h"
759 static void do_autogain(struct gspca_dev
*gspca_dev
)
761 struct sd
*sd
= (struct sd
*) gspca_dev
;
762 int avg_lum
= atomic_read(&sd
->avg_lum
);
764 const int deadzone
= 30;
769 desired_lum
= 270 + sd
->brightness
;
771 if (sd
->autogain_ignore_frames
> 0)
772 sd
->autogain_ignore_frames
--;
773 else if (gspca_auto_gain_n_exposure(gspca_dev
, avg_lum
, desired_lum
,
774 deadzone
, GAIN_KNEE
, EXPOSURE_KNEE
))
775 sd
->autogain_ignore_frames
= PAC_AUTOGAIN_IGNORE_FRAMES
;
778 /* JPEG header, part 1 */
779 static const unsigned char pac_jpeg_header1
[] = {
780 0xff, 0xd8, /* SOI: Start of Image */
782 0xff, 0xc0, /* SOF0: Start of Frame (Baseline DCT) */
783 0x00, 0x11, /* length = 17 bytes (including this length field) */
784 0x08 /* Precision: 8 */
785 /* 2 bytes is placed here: number of image lines */
786 /* 2 bytes is placed here: samples per line */
789 /* JPEG header, continued */
790 static const unsigned char pac_jpeg_header2
[] = {
791 0x03, /* Number of image components: 3 */
792 0x01, 0x21, 0x00, /* ID=1, Subsampling 1x1, Quantization table: 0 */
793 0x02, 0x11, 0x01, /* ID=2, Subsampling 2x1, Quantization table: 1 */
794 0x03, 0x11, 0x01, /* ID=3, Subsampling 2x1, Quantization table: 1 */
796 0xff, 0xda, /* SOS: Start Of Scan */
797 0x00, 0x0c, /* length = 12 bytes (including this length field) */
798 0x03, /* number of components: 3 */
799 0x01, 0x00, /* selector 1, table 0x00 */
800 0x02, 0x11, /* selector 2, table 0x11 */
801 0x03, 0x11, /* selector 3, table 0x11 */
802 0x00, 0x3f, /* Spectral selection: 0 .. 63 */
803 0x00 /* Successive approximation: 0 */
806 static void pac_start_frame(struct gspca_dev
*gspca_dev
,
807 struct gspca_frame
*frame
,
808 __u16 lines
, __u16 samples_per_line
)
810 unsigned char tmpbuf
[4];
812 gspca_frame_add(gspca_dev
, FIRST_PACKET
,
813 pac_jpeg_header1
, sizeof(pac_jpeg_header1
));
815 tmpbuf
[0] = lines
>> 8;
816 tmpbuf
[1] = lines
& 0xff;
817 tmpbuf
[2] = samples_per_line
>> 8;
818 tmpbuf
[3] = samples_per_line
& 0xff;
820 gspca_frame_add(gspca_dev
, INTER_PACKET
,
821 tmpbuf
, sizeof(tmpbuf
));
822 gspca_frame_add(gspca_dev
, INTER_PACKET
,
823 pac_jpeg_header2
, sizeof(pac_jpeg_header2
));
826 /* this function is run at interrupt level */
827 static void sd_pkt_scan(struct gspca_dev
*gspca_dev
,
828 u8
*data
, /* isoc packet */
829 int len
) /* iso packet length */
831 struct sd
*sd
= (struct sd
*) gspca_dev
;
832 struct gspca_frame
*frame
;
835 sof
= pac_find_sof(&sd
->sof_read
, data
, len
);
837 int n
, lum_offset
, footer_length
;
839 frame
= gspca_get_i_frame(gspca_dev
);
841 gspca_dev
->last_packet_type
= DISCARD_PACKET
;
845 /* 6 bytes after the FF D9 EOF marker a number of lumination
846 bytes are send corresponding to different parts of the
847 image, the 14th and 15th byte after the EOF seem to
848 correspond to the center of the image */
849 lum_offset
= 61 + sizeof pac_sof_marker
;
852 /* Finish decoding current frame */
853 n
= (sof
- data
) - (footer_length
+ sizeof pac_sof_marker
);
855 frame
->data_end
+= n
;
858 gspca_frame_add(gspca_dev
, INTER_PACKET
,
860 if (gspca_dev
->last_packet_type
!= DISCARD_PACKET
&&
861 frame
->data_end
[-2] == 0xff &&
862 frame
->data_end
[-1] == 0xd9)
863 gspca_frame_add(gspca_dev
, LAST_PACKET
,
870 /* Get average lumination */
871 if (gspca_dev
->last_packet_type
== LAST_PACKET
&&
873 atomic_set(&sd
->avg_lum
, data
[-lum_offset
] +
874 data
[-lum_offset
+ 1]);
876 atomic_set(&sd
->avg_lum
, -1);
878 /* Start the new frame with the jpeg header */
879 /* The PAC7302 has the image rotated 90 degrees */
880 pac_start_frame(gspca_dev
, frame
,
881 gspca_dev
->width
, gspca_dev
->height
);
883 gspca_frame_add(gspca_dev
, INTER_PACKET
, data
, len
);
886 static int sd_setbrightness(struct gspca_dev
*gspca_dev
, __s32 val
)
888 struct sd
*sd
= (struct sd
*) gspca_dev
;
890 sd
->brightness
= val
;
891 if (gspca_dev
->streaming
)
892 setbrightcont(gspca_dev
);
893 return gspca_dev
->usb_err
;
896 static int sd_getbrightness(struct gspca_dev
*gspca_dev
, __s32
*val
)
898 struct sd
*sd
= (struct sd
*) gspca_dev
;
900 *val
= sd
->brightness
;
904 static int sd_setcontrast(struct gspca_dev
*gspca_dev
, __s32 val
)
906 struct sd
*sd
= (struct sd
*) gspca_dev
;
909 if (gspca_dev
->streaming
) {
910 setbrightcont(gspca_dev
);
912 return gspca_dev
->usb_err
;
915 static int sd_getcontrast(struct gspca_dev
*gspca_dev
, __s32
*val
)
917 struct sd
*sd
= (struct sd
*) gspca_dev
;
923 static int sd_setcolors(struct gspca_dev
*gspca_dev
, __s32 val
)
925 struct sd
*sd
= (struct sd
*) gspca_dev
;
928 if (gspca_dev
->streaming
)
929 setcolors(gspca_dev
);
930 return gspca_dev
->usb_err
;
933 static int sd_getcolors(struct gspca_dev
*gspca_dev
, __s32
*val
)
935 struct sd
*sd
= (struct sd
*) gspca_dev
;
941 static int sd_setwhitebalance(struct gspca_dev
*gspca_dev
, __s32 val
)
943 struct sd
*sd
= (struct sd
*) gspca_dev
;
945 sd
->white_balance
= val
;
946 if (gspca_dev
->streaming
)
947 setwhitebalance(gspca_dev
);
948 return gspca_dev
->usb_err
;
951 static int sd_getwhitebalance(struct gspca_dev
*gspca_dev
, __s32
*val
)
953 struct sd
*sd
= (struct sd
*) gspca_dev
;
955 *val
= sd
->white_balance
;
959 static int sd_setredbalance(struct gspca_dev
*gspca_dev
, __s32 val
)
961 struct sd
*sd
= (struct sd
*) gspca_dev
;
963 sd
->red_balance
= val
;
964 if (gspca_dev
->streaming
)
965 setredbalance(gspca_dev
);
966 return gspca_dev
->usb_err
;
969 static int sd_getredbalance(struct gspca_dev
*gspca_dev
, __s32
*val
)
971 struct sd
*sd
= (struct sd
*) gspca_dev
;
973 *val
= sd
->red_balance
;
977 static int sd_setbluebalance(struct gspca_dev
*gspca_dev
, __s32 val
)
979 struct sd
*sd
= (struct sd
*) gspca_dev
;
981 sd
->blue_balance
= val
;
982 if (gspca_dev
->streaming
)
983 setbluebalance(gspca_dev
);
984 return gspca_dev
->usb_err
;
987 static int sd_getbluebalance(struct gspca_dev
*gspca_dev
, __s32
*val
)
989 struct sd
*sd
= (struct sd
*) gspca_dev
;
991 *val
= sd
->blue_balance
;
995 static int sd_setgain(struct gspca_dev
*gspca_dev
, __s32 val
)
997 struct sd
*sd
= (struct sd
*) gspca_dev
;
1000 if (gspca_dev
->streaming
)
1002 return gspca_dev
->usb_err
;
1005 static int sd_getgain(struct gspca_dev
*gspca_dev
, __s32
*val
)
1007 struct sd
*sd
= (struct sd
*) gspca_dev
;
1013 static int sd_setexposure(struct gspca_dev
*gspca_dev
, __s32 val
)
1015 struct sd
*sd
= (struct sd
*) gspca_dev
;
1018 if (gspca_dev
->streaming
)
1019 setexposure(gspca_dev
);
1020 return gspca_dev
->usb_err
;
1023 static int sd_getexposure(struct gspca_dev
*gspca_dev
, __s32
*val
)
1025 struct sd
*sd
= (struct sd
*) gspca_dev
;
1027 *val
= sd
->exposure
;
1031 static int sd_setautogain(struct gspca_dev
*gspca_dev
, __s32 val
)
1033 struct sd
*sd
= (struct sd
*) gspca_dev
;
1036 /* when switching to autogain set defaults to make sure
1037 we are on a valid point of the autogain gain /
1038 exposure knee graph, and give this change time to
1039 take effect before doing autogain. */
1041 sd
->exposure
= EXPOSURE_DEF
;
1042 sd
->gain
= GAIN_DEF
;
1043 if (gspca_dev
->streaming
) {
1044 sd
->autogain_ignore_frames
=
1045 PAC_AUTOGAIN_IGNORE_FRAMES
;
1046 setexposure(gspca_dev
);
1051 return gspca_dev
->usb_err
;
1054 static int sd_getautogain(struct gspca_dev
*gspca_dev
, __s32
*val
)
1056 struct sd
*sd
= (struct sd
*) gspca_dev
;
1058 *val
= sd
->autogain
;
1062 static int sd_sethflip(struct gspca_dev
*gspca_dev
, __s32 val
)
1064 struct sd
*sd
= (struct sd
*) gspca_dev
;
1067 if (gspca_dev
->streaming
)
1068 sethvflip(gspca_dev
);
1069 return gspca_dev
->usb_err
;
1072 static int sd_gethflip(struct gspca_dev
*gspca_dev
, __s32
*val
)
1074 struct sd
*sd
= (struct sd
*) gspca_dev
;
1080 static int sd_setvflip(struct gspca_dev
*gspca_dev
, __s32 val
)
1082 struct sd
*sd
= (struct sd
*) gspca_dev
;
1085 if (gspca_dev
->streaming
)
1086 sethvflip(gspca_dev
);
1087 return gspca_dev
->usb_err
;
1090 static int sd_getvflip(struct gspca_dev
*gspca_dev
, __s32
*val
)
1092 struct sd
*sd
= (struct sd
*) gspca_dev
;
1098 #ifdef CONFIG_VIDEO_ADV_DEBUG
1099 static int sd_dbg_s_register(struct gspca_dev
*gspca_dev
,
1100 struct v4l2_dbg_register
*reg
)
1105 /* reg->reg: bit0..15: reserved for register index (wIndex is 16bit
1106 long on the USB bus)
1108 if (reg
->match
.type
== V4L2_CHIP_MATCH_HOST
&&
1109 reg
->match
.addr
== 0 &&
1110 (reg
->reg
< 0x000000ff) &&
1111 (reg
->val
<= 0x000000ff)
1113 /* Currently writing to page 0 is only supported. */
1114 /* reg_w() only supports 8bit index */
1115 index
= reg
->reg
& 0x000000ff;
1116 value
= reg
->val
& 0x000000ff;
1118 /* Note that there shall be no access to other page
1119 by any other function between the page swith and
1120 the actual register write */
1121 reg_w(gspca_dev
, 0xff, 0x00); /* page 0 */
1122 reg_w(gspca_dev
, index
, value
);
1124 reg_w(gspca_dev
, 0xdc, 0x01);
1126 return gspca_dev
->usb_err
;
1129 static int sd_chip_ident(struct gspca_dev
*gspca_dev
,
1130 struct v4l2_dbg_chip_ident
*chip
)
1134 if (chip
->match
.type
== V4L2_CHIP_MATCH_HOST
&&
1135 chip
->match
.addr
== 0) {
1137 chip
->ident
= V4L2_IDENT_UNKNOWN
;
1145 static int sd_int_pkt_scan(struct gspca_dev
*gspca_dev
,
1146 u8
*data
, /* interrupt packet data */
1147 int len
) /* interrput packet length */
1155 if ((data0
== 0x00 && data1
== 0x11) ||
1156 (data0
== 0x22 && data1
== 0x33) ||
1157 (data0
== 0x44 && data1
== 0x55) ||
1158 (data0
== 0x66 && data1
== 0x77) ||
1159 (data0
== 0x88 && data1
== 0x99) ||
1160 (data0
== 0xaa && data1
== 0xbb) ||
1161 (data0
== 0xcc && data1
== 0xdd) ||
1162 (data0
== 0xee && data1
== 0xff)) {
1163 input_report_key(gspca_dev
->input_dev
, KEY_CAMERA
, 1);
1164 input_sync(gspca_dev
->input_dev
);
1165 input_report_key(gspca_dev
->input_dev
, KEY_CAMERA
, 0);
1166 input_sync(gspca_dev
->input_dev
);
1175 /* sub-driver description for pac7302 */
1176 static const struct sd_desc sd_desc
= {
1177 .name
= MODULE_NAME
,
1179 .nctrls
= ARRAY_SIZE(sd_ctrls
),
1180 .config
= sd_config
,
1185 .pkt_scan
= sd_pkt_scan
,
1186 .dq_callback
= do_autogain
,
1187 #ifdef CONFIG_VIDEO_ADV_DEBUG
1188 .set_register
= sd_dbg_s_register
,
1189 .get_chip_ident
= sd_chip_ident
,
1192 .int_pkt_scan
= sd_int_pkt_scan
,
1196 /* -- module initialisation -- */
1197 static const struct usb_device_id device_table
[] __devinitconst
= {
1198 {USB_DEVICE(0x06f8, 0x3009)},
1199 {USB_DEVICE(0x093a, 0x2620)},
1200 {USB_DEVICE(0x093a, 0x2621)},
1201 {USB_DEVICE(0x093a, 0x2622), .driver_info
= FL_VFLIP
},
1202 {USB_DEVICE(0x093a, 0x2624), .driver_info
= FL_VFLIP
},
1203 {USB_DEVICE(0x093a, 0x2626)},
1204 {USB_DEVICE(0x093a, 0x2628)},
1205 {USB_DEVICE(0x093a, 0x2629), .driver_info
= FL_VFLIP
},
1206 {USB_DEVICE(0x093a, 0x262a)},
1207 {USB_DEVICE(0x093a, 0x262c)},
1210 MODULE_DEVICE_TABLE(usb
, device_table
);
1212 /* -- device connect -- */
1213 static int __devinit
sd_probe(struct usb_interface
*intf
,
1214 const struct usb_device_id
*id
)
1216 return gspca_dev_probe(intf
, id
, &sd_desc
, sizeof(struct sd
),
1220 static struct usb_driver sd_driver
= {
1221 .name
= MODULE_NAME
,
1222 .id_table
= device_table
,
1224 .disconnect
= gspca_disconnect
,
1226 .suspend
= gspca_suspend
,
1227 .resume
= gspca_resume
,
1231 /* -- module insert / remove -- */
1232 static int __init
sd_mod_init(void)
1235 ret
= usb_register(&sd_driver
);
1238 PDEBUG(D_PROBE
, "registered");
1241 static void __exit
sd_mod_exit(void)
1243 usb_deregister(&sd_driver
);
1244 PDEBUG(D_PROBE
, "deregistered");
1247 module_init(sd_mod_init
);
1248 module_exit(sd_mod_exit
);