root/drivers/media/usb/gspca/pac7302.c

/* [<][>][^][v][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. reg_w_buf
  2. reg_w
  3. reg_w_seq
  4. reg_w_page
  5. reg_w_var
  6. sd_config
  7. setbrightcont
  8. setcolors
  9. setwhitebalance
  10. rgbbalance_ctrl_to_reg_value
  11. setredbalance
  12. setbluebalance
  13. setgain
  14. setexposure
  15. sethvflip
  16. setsharpness
  17. sd_init
  18. sd_s_ctrl
  19. sd_init_controls
  20. sd_start
  21. sd_stopN
  22. sd_stop0
  23. do_autogain
  24. sd_pkt_scan
  25. sd_dbg_s_register
  26. sd_int_pkt_scan
  27. sd_probe

   1 // SPDX-License-Identifier: GPL-2.0-or-later
   2 /*
   3  * Pixart PAC7302 driver
   4  *
   5  * Copyright (C) 2008-2012 Jean-Francois Moine <http://moinejf.free.fr>
   6  * Copyright (C) 2005 Thomas Kaiser thomas@kaiser-linux.li
   7  *
   8  * Separated from Pixart PAC7311 library by Márton Németh
   9  * Camera button input handling by Márton Németh <nm127@freemail.hu>
  10  * Copyright (C) 2009-2010 Márton Németh <nm127@freemail.hu>
  11  */
  12 
  13 /*
  14  * Some documentation about various registers as determined by trial and error.
  15  *
  16  * Register page 0:
  17  *
  18  * Address      Description
  19  * 0x01         Red balance control
  20  * 0x02         Green balance control
  21  * 0x03         Blue balance control
  22  *                   The Windows driver uses a quadratic approach to map
  23  *                   the settable values (0-200) on register values:
  24  *                   min=0x20, default=0x40, max=0x80
  25  * 0x0f-0x20    Color and saturation control
  26  * 0xa2-0xab    Brightness, contrast and gamma control
  27  * 0xb6         Sharpness control (bits 0-4)
  28  *
  29  * Register page 1:
  30  *
  31  * Address      Description
  32  * 0x78         Global control, bit 6 controls the LED (inverted)
  33  * 0x80         Compression balance, 2 interesting settings:
  34  *              0x0f Default
  35  *              0x50 Values >= this switch the camera to a lower compression,
  36  *                   using the same table for both luminance and chrominance.
  37  *                   This gives a sharper picture. Only usable when running
  38  *                   at < 15 fps! Note currently the driver does not use this
  39  *                   as the quality gain is small and the generated JPG-s are
  40  *                   only understood by v4l-utils >= 0.8.9
  41  *
  42  * Register page 3:
  43  *
  44  * Address      Description
  45  * 0x02         Clock divider 3-63, fps = 90 / val. Must be a multiple of 3 on
  46  *              the 7302, so one of 3, 6, 9, ..., except when between 6 and 12?
  47  * 0x03         Variable framerate ctrl reg2==3: 0 -> ~30 fps, 255 -> ~22fps
  48  * 0x04         Another var framerate ctrl reg2==3, reg3==0: 0 -> ~30 fps,
  49  *              63 -> ~27 fps, the 2 msb's must always be 1 !!
  50  * 0x05         Another var framerate ctrl reg2==3, reg3==0, reg4==0xc0:
  51  *              1 -> ~30 fps, 2 -> ~20 fps
  52  * 0x0e         Exposure bits 0-7, 0-448, 0 = use full frame time
  53  * 0x0f         Exposure bit 8, 0-448, 448 = no exposure at all
  54  * 0x10         Gain 0-31
  55  * 0x12         Another gain 0-31, unlike 0x10 this one seems to start with an
  56  *              amplification value of 1 rather then 0 at its lowest setting
  57  * 0x21         Bitfield: 0-1 unused, 2-3 vflip/hflip, 4-5 unknown, 6-7 unused
  58  * 0x80         Another framerate control, best left at 1, moving it from 1 to
  59  *              2 causes the framerate to become 3/4th of what it was, and
  60  *              also seems to cause pixel averaging, resulting in an effective
  61  *              resolution of 320x240 and thus a much blockier image
  62  *
  63  * The registers are accessed in the following functions:
  64  *
  65  * Page | Register   | Function
  66  * -----+------------+---------------------------------------------------
  67  *  0   | 0x01       | setredbalance()
  68  *  0   | 0x03       | setbluebalance()
  69  *  0   | 0x0f..0x20 | setcolors()
  70  *  0   | 0xa2..0xab | setbrightcont()
  71  *  0   | 0xb6       | setsharpness()
  72  *  0   | 0xc6       | setwhitebalance()
  73  *  0   | 0xdc       | setbrightcont(), setcolors()
  74  *  3   | 0x02       | setexposure()
  75  *  3   | 0x10, 0x12 | setgain()
  76  *  3   | 0x11       | setcolors(), setgain(), setexposure(), sethvflip()
  77  *  3   | 0x21       | sethvflip()
  78  */
  79 
  80 #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
  81 
  82 #include <linux/input.h>
  83 #include "gspca.h"
  84 /* Include pac common sof detection functions */
  85 #include "pac_common.h"
  86 
  87 #define PAC7302_RGB_BALANCE_MIN           0
  88 #define PAC7302_RGB_BALANCE_MAX         200
  89 #define PAC7302_RGB_BALANCE_DEFAULT     100
  90 #define PAC7302_GAIN_DEFAULT             15
  91 #define PAC7302_GAIN_KNEE                42
  92 #define PAC7302_EXPOSURE_DEFAULT         66 /* 33 ms / 30 fps */
  93 #define PAC7302_EXPOSURE_KNEE           133 /* 66 ms / 15 fps */
  94 
  95 MODULE_AUTHOR("Jean-Francois Moine <http://moinejf.free.fr>, Thomas Kaiser thomas@kaiser-linux.li");
  96 MODULE_DESCRIPTION("Pixart PAC7302");
  97 MODULE_LICENSE("GPL");
  98 
  99 struct sd {
 100         struct gspca_dev gspca_dev;             /* !! must be the first item */
 101 
 102         struct { /* brightness / contrast cluster */
 103                 struct v4l2_ctrl *brightness;
 104                 struct v4l2_ctrl *contrast;
 105         };
 106         struct v4l2_ctrl *saturation;
 107         struct v4l2_ctrl *white_balance;
 108         struct v4l2_ctrl *red_balance;
 109         struct v4l2_ctrl *blue_balance;
 110         struct { /* flip cluster */
 111                 struct v4l2_ctrl *hflip;
 112                 struct v4l2_ctrl *vflip;
 113         };
 114         struct v4l2_ctrl *sharpness;
 115         u8 flags;
 116 #define FL_HFLIP 0x01           /* mirrored by default */
 117 #define FL_VFLIP 0x02           /* vertical flipped by default */
 118 
 119         u8 sof_read;
 120         s8 autogain_ignore_frames;
 121 
 122         atomic_t avg_lum;
 123 };
 124 
 125 static const struct v4l2_pix_format vga_mode[] = {
 126         {640, 480, V4L2_PIX_FMT_PJPG, V4L2_FIELD_NONE,
 127                 .bytesperline = 640,
 128                 .sizeimage = 640 * 480 * 3 / 8 + 590,
 129                 .colorspace = V4L2_COLORSPACE_JPEG,
 130         },
 131 };
 132 
 133 #define LOAD_PAGE3              255
 134 #define END_OF_SEQUENCE         0
 135 
 136 static const u8 init_7302[] = {
 137 /*      index,value */
 138         0xff, 0x01,             /* page 1 */
 139         0x78, 0x00,             /* deactivate */
 140         0xff, 0x01,
 141         0x78, 0x40,             /* led off */
 142 };
 143 static const u8 start_7302[] = {
 144 /*      index, len, [value]* */
 145         0xff, 1,        0x00,           /* page 0 */
 146         0x00, 12,       0x01, 0x40, 0x40, 0x40, 0x01, 0xe0, 0x02, 0x80,
 147                         0x00, 0x00, 0x00, 0x00,
 148         0x0d, 24,       0x03, 0x01, 0x00, 0xb5, 0x07, 0xcb, 0x00, 0x00,
 149                         0x07, 0xc8, 0x00, 0xea, 0x07, 0xcf, 0x07, 0xf7,
 150                         0x07, 0x7e, 0x01, 0x0b, 0x00, 0x00, 0x00, 0x11,
 151         0x26, 2,        0xaa, 0xaa,
 152         0x2e, 1,        0x31,
 153         0x38, 1,        0x01,
 154         0x3a, 3,        0x14, 0xff, 0x5a,
 155         0x43, 11,       0x00, 0x0a, 0x18, 0x11, 0x01, 0x2c, 0x88, 0x11,
 156                         0x00, 0x54, 0x11,
 157         0x55, 1,        0x00,
 158         0x62, 4,        0x10, 0x1e, 0x1e, 0x18,
 159         0x6b, 1,        0x00,
 160         0x6e, 3,        0x08, 0x06, 0x00,
 161         0x72, 3,        0x00, 0xff, 0x00,
 162         0x7d, 23,       0x01, 0x01, 0x58, 0x46, 0x50, 0x3c, 0x50, 0x3c,
 163                         0x54, 0x46, 0x54, 0x56, 0x52, 0x50, 0x52, 0x50,
 164                         0x56, 0x64, 0xa4, 0x00, 0xda, 0x00, 0x00,
 165         0xa2, 10,       0x22, 0x2c, 0x3c, 0x54, 0x69, 0x7c, 0x9c, 0xb9,
 166                         0xd2, 0xeb,
 167         0xaf, 1,        0x02,
 168         0xb5, 2,        0x08, 0x08,
 169         0xb8, 2,        0x08, 0x88,
 170         0xc4, 4,        0xae, 0x01, 0x04, 0x01,
 171         0xcc, 1,        0x00,
 172         0xd1, 11,       0x01, 0x30, 0x49, 0x5e, 0x6f, 0x7f, 0x8e, 0xa9,
 173                         0xc1, 0xd7, 0xec,
 174         0xdc, 1,        0x01,
 175         0xff, 1,        0x01,           /* page 1 */
 176         0x12, 3,        0x02, 0x00, 0x01,
 177         0x3e, 2,        0x00, 0x00,
 178         0x76, 5,        0x01, 0x20, 0x40, 0x00, 0xf2,
 179         0x7c, 1,        0x00,
 180         0x7f, 10,       0x4b, 0x0f, 0x01, 0x2c, 0x02, 0x58, 0x03, 0x20,
 181                         0x02, 0x00,
 182         0x96, 5,        0x01, 0x10, 0x04, 0x01, 0x04,
 183         0xc8, 14,       0x00, 0x00, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00,
 184                         0x07, 0x00, 0x01, 0x07, 0x04, 0x01,
 185         0xd8, 1,        0x01,
 186         0xdb, 2,        0x00, 0x01,
 187         0xde, 7,        0x00, 0x01, 0x04, 0x04, 0x00, 0x00, 0x00,
 188         0xe6, 4,        0x00, 0x00, 0x00, 0x01,
 189         0xeb, 1,        0x00,
 190         0xff, 1,        0x02,           /* page 2 */
 191         0x22, 1,        0x00,
 192         0xff, 1,        0x03,           /* page 3 */
 193         0, LOAD_PAGE3,                  /* load the page 3 */
 194         0x11, 1,        0x01,
 195         0xff, 1,        0x02,           /* page 2 */
 196         0x13, 1,        0x00,
 197         0x22, 4,        0x1f, 0xa4, 0xf0, 0x96,
 198         0x27, 2,        0x14, 0x0c,
 199         0x2a, 5,        0xc8, 0x00, 0x18, 0x12, 0x22,
 200         0x64, 8,        0x00, 0x00, 0xf0, 0x01, 0x14, 0x44, 0x44, 0x44,
 201         0x6e, 1,        0x08,
 202         0xff, 1,        0x01,           /* page 1 */
 203         0x78, 1,        0x00,
 204         0, END_OF_SEQUENCE              /* end of sequence */
 205 };
 206 
 207 #define SKIP            0xaa
 208 /* page 3 - the value SKIP says skip the index - see reg_w_page() */
 209 static const u8 page3_7302[] = {
 210         0x90, 0x40, 0x03, 0x00, 0xc0, 0x01, 0x14, 0x16,
 211         0x14, 0x12, 0x00, 0x00, 0x00, 0x02, 0x33, 0x00,
 212         0x0f, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
 213         0x00, 0x00, 0x00, 0x47, 0x01, 0xb3, 0x01, 0x00,
 214         0x00, 0x08, 0x00, 0x00, 0x0d, 0x00, 0x00, 0x21,
 215         0x00, 0x00, 0x00, 0x54, 0xf4, 0x02, 0x52, 0x54,
 216         0xa4, 0xb8, 0xe0, 0x2a, 0xf6, 0x00, 0x00, 0x00,
 217         0x00, 0x1e, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
 218         0x00, 0xfc, 0x00, 0xf2, 0x1f, 0x04, 0x00, 0x00,
 219         SKIP, 0x00, 0x00, 0xc0, 0xc0, 0x10, 0x00, 0x00,
 220         0x00, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
 221         0x00, 0x40, 0xff, 0x03, 0x19, 0x00, 0x00, 0x00,
 222         0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
 223         0x00, 0x00, 0x00, 0x00, 0x00, 0xc8, 0xc8, 0xc8,
 224         0xc8, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x50,
 225         0x08, 0x10, 0x24, 0x40, 0x00, 0x00, 0x00, 0x00,
 226         0x01, 0x00, 0x02, 0x47, 0x00, 0x00, 0x00, 0x00,
 227         0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
 228         0x00, 0x02, 0xfa, 0x00, 0x64, 0x5a, 0x28, 0x00,
 229         0x00
 230 };
 231 
 232 static void reg_w_buf(struct gspca_dev *gspca_dev,
 233                 u8 index,
 234                   const u8 *buffer, int len)
 235 {
 236         int ret;
 237 
 238         if (gspca_dev->usb_err < 0)
 239                 return;
 240         memcpy(gspca_dev->usb_buf, buffer, len);
 241         ret = usb_control_msg(gspca_dev->dev,
 242                         usb_sndctrlpipe(gspca_dev->dev, 0),
 243                         0,              /* request */
 244                         USB_DIR_OUT | USB_TYPE_VENDOR | USB_RECIP_DEVICE,
 245                         0,              /* value */
 246                         index, gspca_dev->usb_buf, len,
 247                         500);
 248         if (ret < 0) {
 249                 pr_err("reg_w_buf failed i: %02x error %d\n",
 250                        index, ret);
 251                 gspca_dev->usb_err = ret;
 252         }
 253 }
 254 
 255 
 256 static void reg_w(struct gspca_dev *gspca_dev,
 257                 u8 index,
 258                 u8 value)
 259 {
 260         int ret;
 261 
 262         if (gspca_dev->usb_err < 0)
 263                 return;
 264         gspca_dev->usb_buf[0] = value;
 265         ret = usb_control_msg(gspca_dev->dev,
 266                         usb_sndctrlpipe(gspca_dev->dev, 0),
 267                         0,                      /* request */
 268                         USB_DIR_OUT | USB_TYPE_VENDOR | USB_RECIP_DEVICE,
 269                         0, index, gspca_dev->usb_buf, 1,
 270                         500);
 271         if (ret < 0) {
 272                 pr_err("reg_w() failed i: %02x v: %02x error %d\n",
 273                        index, value, ret);
 274                 gspca_dev->usb_err = ret;
 275         }
 276 }
 277 
 278 static void reg_w_seq(struct gspca_dev *gspca_dev,
 279                 const u8 *seq, int len)
 280 {
 281         while (--len >= 0) {
 282                 reg_w(gspca_dev, seq[0], seq[1]);
 283                 seq += 2;
 284         }
 285 }
 286 
 287 /* load the beginning of a page */
 288 static void reg_w_page(struct gspca_dev *gspca_dev,
 289                         const u8 *page, int len)
 290 {
 291         int index;
 292         int ret = 0;
 293 
 294         if (gspca_dev->usb_err < 0)
 295                 return;
 296         for (index = 0; index < len; index++) {
 297                 if (page[index] == SKIP)                /* skip this index */
 298                         continue;
 299                 gspca_dev->usb_buf[0] = page[index];
 300                 ret = usb_control_msg(gspca_dev->dev,
 301                                 usb_sndctrlpipe(gspca_dev->dev, 0),
 302                                 0,                      /* request */
 303                         USB_DIR_OUT | USB_TYPE_VENDOR | USB_RECIP_DEVICE,
 304                                 0, index, gspca_dev->usb_buf, 1,
 305                                 500);
 306                 if (ret < 0) {
 307                         pr_err("reg_w_page() failed i: %02x v: %02x error %d\n",
 308                                index, page[index], ret);
 309                         gspca_dev->usb_err = ret;
 310                         break;
 311                 }
 312         }
 313 }
 314 
 315 /* output a variable sequence */
 316 static void reg_w_var(struct gspca_dev *gspca_dev,
 317                         const u8 *seq,
 318                         const u8 *page3, unsigned int page3_len)
 319 {
 320         int index, len;
 321 
 322         for (;;) {
 323                 index = *seq++;
 324                 len = *seq++;
 325                 switch (len) {
 326                 case END_OF_SEQUENCE:
 327                         return;
 328                 case LOAD_PAGE3:
 329                         reg_w_page(gspca_dev, page3, page3_len);
 330                         break;
 331                 default:
 332                         if (len > USB_BUF_SZ) {
 333                                 gspca_err(gspca_dev, "Incorrect variable sequence\n");
 334                                 return;
 335                         }
 336                         while (len > 0) {
 337                                 if (len < 8) {
 338                                         reg_w_buf(gspca_dev,
 339                                                 index, seq, len);
 340                                         seq += len;
 341                                         break;
 342                                 }
 343                                 reg_w_buf(gspca_dev, index, seq, 8);
 344                                 seq += 8;
 345                                 index += 8;
 346                                 len -= 8;
 347                         }
 348                 }
 349         }
 350         /* not reached */
 351 }
 352 
 353 /* this function is called at probe time for pac7302 */
 354 static int sd_config(struct gspca_dev *gspca_dev,
 355                         const struct usb_device_id *id)
 356 {
 357         struct sd *sd = (struct sd *) gspca_dev;
 358         struct cam *cam;
 359 
 360         cam = &gspca_dev->cam;
 361 
 362         cam->cam_mode = vga_mode;       /* only 640x480 */
 363         cam->nmodes = ARRAY_SIZE(vga_mode);
 364 
 365         sd->flags = id->driver_info;
 366         return 0;
 367 }
 368 
 369 static void setbrightcont(struct gspca_dev *gspca_dev)
 370 {
 371         struct sd *sd = (struct sd *) gspca_dev;
 372         int i, v;
 373         static const u8 max[10] =
 374                 {0x29, 0x33, 0x42, 0x5a, 0x6e, 0x80, 0x9f, 0xbb,
 375                  0xd4, 0xec};
 376         static const u8 delta[10] =
 377                 {0x35, 0x33, 0x33, 0x2f, 0x2a, 0x25, 0x1e, 0x17,
 378                  0x11, 0x0b};
 379 
 380         reg_w(gspca_dev, 0xff, 0x00);           /* page 0 */
 381         for (i = 0; i < 10; i++) {
 382                 v = max[i];
 383                 v += (sd->brightness->val - (s32)sd->brightness->maximum)
 384                         * 150 / (s32)sd->brightness->maximum; /* 200 ? */
 385                 v -= delta[i] * sd->contrast->val / (s32)sd->contrast->maximum;
 386                 if (v < 0)
 387                         v = 0;
 388                 else if (v > 0xff)
 389                         v = 0xff;
 390                 reg_w(gspca_dev, 0xa2 + i, v);
 391         }
 392         reg_w(gspca_dev, 0xdc, 0x01);
 393 }
 394 
 395 static void setcolors(struct gspca_dev *gspca_dev)
 396 {
 397         struct sd *sd = (struct sd *) gspca_dev;
 398         int i, v;
 399         static const int a[9] =
 400                 {217, -212, 0, -101, 170, -67, -38, -315, 355};
 401         static const int b[9] =
 402                 {19, 106, 0, 19, 106, 1, 19, 106, 1};
 403 
 404         reg_w(gspca_dev, 0xff, 0x03);                   /* page 3 */
 405         reg_w(gspca_dev, 0x11, 0x01);
 406         reg_w(gspca_dev, 0xff, 0x00);                   /* page 0 */
 407         for (i = 0; i < 9; i++) {
 408                 v = a[i] * sd->saturation->val / (s32)sd->saturation->maximum;
 409                 v += b[i];
 410                 reg_w(gspca_dev, 0x0f + 2 * i, (v >> 8) & 0x07);
 411                 reg_w(gspca_dev, 0x0f + 2 * i + 1, v);
 412         }
 413         reg_w(gspca_dev, 0xdc, 0x01);
 414 }
 415 
 416 static void setwhitebalance(struct gspca_dev *gspca_dev)
 417 {
 418         struct sd *sd = (struct sd *) gspca_dev;
 419 
 420         reg_w(gspca_dev, 0xff, 0x00);           /* page 0 */
 421         reg_w(gspca_dev, 0xc6, sd->white_balance->val);
 422 
 423         reg_w(gspca_dev, 0xdc, 0x01);
 424 }
 425 
 426 static u8 rgbbalance_ctrl_to_reg_value(s32 rgb_ctrl_val)
 427 {
 428         const unsigned int k = 1000;    /* precision factor */
 429         unsigned int norm;
 430 
 431         /* Normed value [0...k] */
 432         norm = k * (rgb_ctrl_val - PAC7302_RGB_BALANCE_MIN)
 433                     / (PAC7302_RGB_BALANCE_MAX - PAC7302_RGB_BALANCE_MIN);
 434         /* Qudratic apporach improves control at small (register) values: */
 435         return 64 * norm * norm / (k*k)  +  32 * norm / k  +  32;
 436         /* Y = 64*X*X + 32*X + 32
 437          * => register values 0x20-0x80; Windows driver uses these limits */
 438 
 439         /* NOTE: for full value range (0x00-0xff) use
 440          *         Y = 254*X*X + X
 441          *         => 254 * norm * norm / (k*k)  +  1 * norm / k        */
 442 }
 443 
 444 static void setredbalance(struct gspca_dev *gspca_dev)
 445 {
 446         struct sd *sd = (struct sd *) gspca_dev;
 447 
 448         reg_w(gspca_dev, 0xff, 0x00);                   /* page 0 */
 449         reg_w(gspca_dev, 0x01,
 450               rgbbalance_ctrl_to_reg_value(sd->red_balance->val));
 451 
 452         reg_w(gspca_dev, 0xdc, 0x01);
 453 }
 454 
 455 static void setbluebalance(struct gspca_dev *gspca_dev)
 456 {
 457         struct sd *sd = (struct sd *) gspca_dev;
 458 
 459         reg_w(gspca_dev, 0xff, 0x00);                   /* page 0 */
 460         reg_w(gspca_dev, 0x03,
 461               rgbbalance_ctrl_to_reg_value(sd->blue_balance->val));
 462 
 463         reg_w(gspca_dev, 0xdc, 0x01);
 464 }
 465 
 466 static void setgain(struct gspca_dev *gspca_dev)
 467 {
 468         u8 reg10, reg12;
 469 
 470         if (gspca_dev->gain->val < 32) {
 471                 reg10 = gspca_dev->gain->val;
 472                 reg12 = 0;
 473         } else {
 474                 reg10 = 31;
 475                 reg12 = gspca_dev->gain->val - 31;
 476         }
 477 
 478         reg_w(gspca_dev, 0xff, 0x03);                   /* page 3 */
 479         reg_w(gspca_dev, 0x10, reg10);
 480         reg_w(gspca_dev, 0x12, reg12);
 481 
 482         /* load registers to sensor (Bit 0, auto clear) */
 483         reg_w(gspca_dev, 0x11, 0x01);
 484 }
 485 
 486 static void setexposure(struct gspca_dev *gspca_dev)
 487 {
 488         u8 clockdiv;
 489         u16 exposure;
 490 
 491         /*
 492          * Register 2 of frame 3 contains the clock divider configuring the
 493          * no fps according to the formula: 90 / reg. sd->exposure is the
 494          * desired exposure time in 0.5 ms.
 495          */
 496         clockdiv = (90 * gspca_dev->exposure->val + 1999) / 2000;
 497 
 498         /*
 499          * Note clockdiv = 3 also works, but when running at 30 fps, depending
 500          * on the scene being recorded, the camera switches to another
 501          * quantization table for certain JPEG blocks, and we don't know how
 502          * to decompress these blocks. So we cap the framerate at 15 fps.
 503          */
 504         if (clockdiv < 6)
 505                 clockdiv = 6;
 506         else if (clockdiv > 63)
 507                 clockdiv = 63;
 508 
 509         /*
 510          * Register 2 MUST be a multiple of 3, except when between 6 and 12?
 511          * Always round up, otherwise we cannot get the desired frametime
 512          * using the partial frame time exposure control.
 513          */
 514         if (clockdiv < 6 || clockdiv > 12)
 515                 clockdiv = ((clockdiv + 2) / 3) * 3;
 516 
 517         /*
 518          * frame exposure time in ms = 1000 * clockdiv / 90    ->
 519          * exposure = (sd->exposure / 2) * 448 / (1000 * clockdiv / 90)
 520          */
 521         exposure = (gspca_dev->exposure->val * 45 * 448) / (1000 * clockdiv);
 522         /* 0 = use full frametime, 448 = no exposure, reverse it */
 523         exposure = 448 - exposure;
 524 
 525         reg_w(gspca_dev, 0xff, 0x03);                   /* page 3 */
 526         reg_w(gspca_dev, 0x02, clockdiv);
 527         reg_w(gspca_dev, 0x0e, exposure & 0xff);
 528         reg_w(gspca_dev, 0x0f, exposure >> 8);
 529 
 530         /* load registers to sensor (Bit 0, auto clear) */
 531         reg_w(gspca_dev, 0x11, 0x01);
 532 }
 533 
 534 static void sethvflip(struct gspca_dev *gspca_dev)
 535 {
 536         struct sd *sd = (struct sd *) gspca_dev;
 537         u8 data, hflip, vflip;
 538 
 539         hflip = sd->hflip->val;
 540         if (sd->flags & FL_HFLIP)
 541                 hflip = !hflip;
 542         vflip = sd->vflip->val;
 543         if (sd->flags & FL_VFLIP)
 544                 vflip = !vflip;
 545 
 546         reg_w(gspca_dev, 0xff, 0x03);                   /* page 3 */
 547         data = (hflip ? 0x08 : 0x00) | (vflip ? 0x04 : 0x00);
 548         reg_w(gspca_dev, 0x21, data);
 549 
 550         /* load registers to sensor (Bit 0, auto clear) */
 551         reg_w(gspca_dev, 0x11, 0x01);
 552 }
 553 
 554 static void setsharpness(struct gspca_dev *gspca_dev)
 555 {
 556         struct sd *sd = (struct sd *) gspca_dev;
 557 
 558         reg_w(gspca_dev, 0xff, 0x00);           /* page 0 */
 559         reg_w(gspca_dev, 0xb6, sd->sharpness->val);
 560 
 561         reg_w(gspca_dev, 0xdc, 0x01);
 562 }
 563 
 564 /* this function is called at probe and resume time for pac7302 */
 565 static int sd_init(struct gspca_dev *gspca_dev)
 566 {
 567         reg_w_seq(gspca_dev, init_7302, sizeof(init_7302)/2);
 568         return gspca_dev->usb_err;
 569 }
 570 
 571 static int sd_s_ctrl(struct v4l2_ctrl *ctrl)
 572 {
 573         struct gspca_dev *gspca_dev =
 574                 container_of(ctrl->handler, struct gspca_dev, ctrl_handler);
 575         struct sd *sd = (struct sd *)gspca_dev;
 576 
 577         gspca_dev->usb_err = 0;
 578 
 579         if (ctrl->id == V4L2_CID_AUTOGAIN && ctrl->is_new && ctrl->val) {
 580                 /* when switching to autogain set defaults to make sure
 581                    we are on a valid point of the autogain gain /
 582                    exposure knee graph, and give this change time to
 583                    take effect before doing autogain. */
 584                 gspca_dev->exposure->val    = PAC7302_EXPOSURE_DEFAULT;
 585                 gspca_dev->gain->val        = PAC7302_GAIN_DEFAULT;
 586                 sd->autogain_ignore_frames  = PAC_AUTOGAIN_IGNORE_FRAMES;
 587         }
 588 
 589         if (!gspca_dev->streaming)
 590                 return 0;
 591 
 592         switch (ctrl->id) {
 593         case V4L2_CID_BRIGHTNESS:
 594                 setbrightcont(gspca_dev);
 595                 break;
 596         case V4L2_CID_SATURATION:
 597                 setcolors(gspca_dev);
 598                 break;
 599         case V4L2_CID_WHITE_BALANCE_TEMPERATURE:
 600                 setwhitebalance(gspca_dev);
 601                 break;
 602         case V4L2_CID_RED_BALANCE:
 603                 setredbalance(gspca_dev);
 604                 break;
 605         case V4L2_CID_BLUE_BALANCE:
 606                 setbluebalance(gspca_dev);
 607                 break;
 608         case V4L2_CID_AUTOGAIN:
 609                 if (gspca_dev->exposure->is_new || (ctrl->is_new && ctrl->val))
 610                         setexposure(gspca_dev);
 611                 if (gspca_dev->gain->is_new || (ctrl->is_new && ctrl->val))
 612                         setgain(gspca_dev);
 613                 break;
 614         case V4L2_CID_HFLIP:
 615                 sethvflip(gspca_dev);
 616                 break;
 617         case V4L2_CID_SHARPNESS:
 618                 setsharpness(gspca_dev);
 619                 break;
 620         default:
 621                 return -EINVAL;
 622         }
 623         return gspca_dev->usb_err;
 624 }
 625 
 626 static const struct v4l2_ctrl_ops sd_ctrl_ops = {
 627         .s_ctrl = sd_s_ctrl,
 628 };
 629 
 630 /* this function is called at probe time */
 631 static int sd_init_controls(struct gspca_dev *gspca_dev)
 632 {
 633         struct sd *sd = (struct sd *) gspca_dev;
 634         struct v4l2_ctrl_handler *hdl = &gspca_dev->ctrl_handler;
 635 
 636         gspca_dev->vdev.ctrl_handler = hdl;
 637         v4l2_ctrl_handler_init(hdl, 12);
 638 
 639         sd->brightness = v4l2_ctrl_new_std(hdl, &sd_ctrl_ops,
 640                                         V4L2_CID_BRIGHTNESS, 0, 32, 1, 16);
 641         sd->contrast = v4l2_ctrl_new_std(hdl, &sd_ctrl_ops,
 642                                         V4L2_CID_CONTRAST, 0, 255, 1, 127);
 643 
 644         sd->saturation = v4l2_ctrl_new_std(hdl, &sd_ctrl_ops,
 645                                         V4L2_CID_SATURATION, 0, 255, 1, 127);
 646         sd->white_balance = v4l2_ctrl_new_std(hdl, &sd_ctrl_ops,
 647                                         V4L2_CID_WHITE_BALANCE_TEMPERATURE,
 648                                         0, 255, 1, 55);
 649         sd->red_balance = v4l2_ctrl_new_std(hdl, &sd_ctrl_ops,
 650                                         V4L2_CID_RED_BALANCE,
 651                                         PAC7302_RGB_BALANCE_MIN,
 652                                         PAC7302_RGB_BALANCE_MAX,
 653                                         1, PAC7302_RGB_BALANCE_DEFAULT);
 654         sd->blue_balance = v4l2_ctrl_new_std(hdl, &sd_ctrl_ops,
 655                                         V4L2_CID_BLUE_BALANCE,
 656                                         PAC7302_RGB_BALANCE_MIN,
 657                                         PAC7302_RGB_BALANCE_MAX,
 658                                         1, PAC7302_RGB_BALANCE_DEFAULT);
 659 
 660         gspca_dev->autogain = v4l2_ctrl_new_std(hdl, &sd_ctrl_ops,
 661                                         V4L2_CID_AUTOGAIN, 0, 1, 1, 1);
 662         gspca_dev->exposure = v4l2_ctrl_new_std(hdl, &sd_ctrl_ops,
 663                                         V4L2_CID_EXPOSURE, 0, 1023, 1,
 664                                         PAC7302_EXPOSURE_DEFAULT);
 665         gspca_dev->gain = v4l2_ctrl_new_std(hdl, &sd_ctrl_ops,
 666                                         V4L2_CID_GAIN, 0, 62, 1,
 667                                         PAC7302_GAIN_DEFAULT);
 668 
 669         sd->hflip = v4l2_ctrl_new_std(hdl, &sd_ctrl_ops,
 670                 V4L2_CID_HFLIP, 0, 1, 1, 0);
 671         sd->vflip = v4l2_ctrl_new_std(hdl, &sd_ctrl_ops,
 672                 V4L2_CID_VFLIP, 0, 1, 1, 0);
 673 
 674         sd->sharpness = v4l2_ctrl_new_std(hdl, &sd_ctrl_ops,
 675                                         V4L2_CID_SHARPNESS, 0, 15, 1, 8);
 676 
 677         if (hdl->error) {
 678                 pr_err("Could not initialize controls\n");
 679                 return hdl->error;
 680         }
 681 
 682         v4l2_ctrl_cluster(2, &sd->brightness);
 683         v4l2_ctrl_auto_cluster(3, &gspca_dev->autogain, 0, false);
 684         v4l2_ctrl_cluster(2, &sd->hflip);
 685         return 0;
 686 }
 687 
 688 /* -- start the camera -- */
 689 static int sd_start(struct gspca_dev *gspca_dev)
 690 {
 691         struct sd *sd = (struct sd *) gspca_dev;
 692 
 693         reg_w_var(gspca_dev, start_7302,
 694                 page3_7302, sizeof(page3_7302));
 695 
 696         sd->sof_read = 0;
 697         sd->autogain_ignore_frames = 0;
 698         atomic_set(&sd->avg_lum, 270 + sd->brightness->val);
 699 
 700         /* start stream */
 701         reg_w(gspca_dev, 0xff, 0x01);
 702         reg_w(gspca_dev, 0x78, 0x01);
 703 
 704         return gspca_dev->usb_err;
 705 }
 706 
 707 static void sd_stopN(struct gspca_dev *gspca_dev)
 708 {
 709 
 710         /* stop stream */
 711         reg_w(gspca_dev, 0xff, 0x01);
 712         reg_w(gspca_dev, 0x78, 0x00);
 713 }
 714 
 715 /* called on streamoff with alt 0 and on disconnect for pac7302 */
 716 static void sd_stop0(struct gspca_dev *gspca_dev)
 717 {
 718         if (!gspca_dev->present)
 719                 return;
 720         reg_w(gspca_dev, 0xff, 0x01);
 721         reg_w(gspca_dev, 0x78, 0x40);
 722 }
 723 
 724 static void do_autogain(struct gspca_dev *gspca_dev)
 725 {
 726         struct sd *sd = (struct sd *) gspca_dev;
 727         int avg_lum = atomic_read(&sd->avg_lum);
 728         int desired_lum;
 729         const int deadzone = 30;
 730 
 731         if (sd->autogain_ignore_frames < 0)
 732                 return;
 733 
 734         if (sd->autogain_ignore_frames > 0) {
 735                 sd->autogain_ignore_frames--;
 736         } else {
 737                 desired_lum = 270 + sd->brightness->val;
 738 
 739                 if (gspca_expo_autogain(gspca_dev, avg_lum, desired_lum,
 740                                         deadzone, PAC7302_GAIN_KNEE,
 741                                         PAC7302_EXPOSURE_KNEE))
 742                         sd->autogain_ignore_frames =
 743                                                 PAC_AUTOGAIN_IGNORE_FRAMES;
 744         }
 745 }
 746 
 747 /* JPEG header */
 748 static const u8 jpeg_header[] = {
 749         0xff, 0xd8,     /* SOI: Start of Image */
 750 
 751         0xff, 0xc0,     /* SOF0: Start of Frame (Baseline DCT) */
 752         0x00, 0x11,     /* length = 17 bytes (including this length field) */
 753         0x08,           /* Precision: 8 */
 754         0x02, 0x80,     /* height = 640 (image rotated) */
 755         0x01, 0xe0,     /* width = 480 */
 756         0x03,           /* Number of image components: 3 */
 757         0x01, 0x21, 0x00, /* ID=1, Subsampling 1x1, Quantization table: 0 */
 758         0x02, 0x11, 0x01, /* ID=2, Subsampling 2x1, Quantization table: 1 */
 759         0x03, 0x11, 0x01, /* ID=3, Subsampling 2x1, Quantization table: 1 */
 760 
 761         0xff, 0xda,     /* SOS: Start Of Scan */
 762         0x00, 0x0c,     /* length = 12 bytes (including this length field) */
 763         0x03,           /* number of components: 3 */
 764         0x01, 0x00,     /* selector 1, table 0x00 */
 765         0x02, 0x11,     /* selector 2, table 0x11 */
 766         0x03, 0x11,     /* selector 3, table 0x11 */
 767         0x00, 0x3f,     /* Spectral selection: 0 .. 63 */
 768         0x00            /* Successive approximation: 0 */
 769 };
 770 
 771 /* this function is run at interrupt level */
 772 static void sd_pkt_scan(struct gspca_dev *gspca_dev,
 773                         u8 *data,                       /* isoc packet */
 774                         int len)                        /* iso packet length */
 775 {
 776         struct sd *sd = (struct sd *) gspca_dev;
 777         u8 *image;
 778         u8 *sof;
 779 
 780         sof = pac_find_sof(gspca_dev, &sd->sof_read, data, len);
 781         if (sof) {
 782                 int n, lum_offset, footer_length;
 783 
 784                 /*
 785                  * 6 bytes after the FF D9 EOF marker a number of lumination
 786                  * bytes are send corresponding to different parts of the
 787                  * image, the 14th and 15th byte after the EOF seem to
 788                  * correspond to the center of the image.
 789                  */
 790                 lum_offset = 61 + sizeof pac_sof_marker;
 791                 footer_length = 74;
 792 
 793                 /* Finish decoding current frame */
 794                 n = (sof - data) - (footer_length + sizeof pac_sof_marker);
 795                 if (n < 0) {
 796                         gspca_dev->image_len += n;
 797                         n = 0;
 798                 } else {
 799                         gspca_frame_add(gspca_dev, INTER_PACKET, data, n);
 800                 }
 801 
 802                 image = gspca_dev->image;
 803                 if (image != NULL
 804                  && image[gspca_dev->image_len - 2] == 0xff
 805                  && image[gspca_dev->image_len - 1] == 0xd9)
 806                         gspca_frame_add(gspca_dev, LAST_PACKET, NULL, 0);
 807 
 808                 n = sof - data;
 809                 len -= n;
 810                 data = sof;
 811 
 812                 /* Get average lumination */
 813                 if (gspca_dev->last_packet_type == LAST_PACKET &&
 814                                 n >= lum_offset)
 815                         atomic_set(&sd->avg_lum, data[-lum_offset] +
 816                                                 data[-lum_offset + 1]);
 817 
 818                 /* Start the new frame with the jpeg header */
 819                 /* The PAC7302 has the image rotated 90 degrees */
 820                 gspca_frame_add(gspca_dev, FIRST_PACKET,
 821                                 jpeg_header, sizeof jpeg_header);
 822         }
 823         gspca_frame_add(gspca_dev, INTER_PACKET, data, len);
 824 }
 825 
 826 #ifdef CONFIG_VIDEO_ADV_DEBUG
 827 static int sd_dbg_s_register(struct gspca_dev *gspca_dev,
 828                         const struct v4l2_dbg_register *reg)
 829 {
 830         u8 index;
 831         u8 value;
 832 
 833         /*
 834          * reg->reg: bit0..15: reserved for register index (wIndex is 16bit
 835          *                     long on the USB bus)
 836          */
 837         if (reg->match.addr == 0 &&
 838             (reg->reg < 0x000000ff) &&
 839             (reg->val <= 0x000000ff)
 840         ) {
 841                 /* Currently writing to page 0 is only supported. */
 842                 /* reg_w() only supports 8bit index */
 843                 index = reg->reg;
 844                 value = reg->val;
 845 
 846                 /*
 847                  * Note that there shall be no access to other page
 848                  * by any other function between the page switch and
 849                  * the actual register write.
 850                  */
 851                 reg_w(gspca_dev, 0xff, 0x00);           /* page 0 */
 852                 reg_w(gspca_dev, index, value);
 853 
 854                 reg_w(gspca_dev, 0xdc, 0x01);
 855         }
 856         return gspca_dev->usb_err;
 857 }
 858 #endif
 859 
 860 #if IS_ENABLED(CONFIG_INPUT)
 861 static int sd_int_pkt_scan(struct gspca_dev *gspca_dev,
 862                         u8 *data,               /* interrupt packet data */
 863                         int len)                /* interrupt packet length */
 864 {
 865         int ret = -EINVAL;
 866         u8 data0, data1;
 867 
 868         if (len == 2) {
 869                 data0 = data[0];
 870                 data1 = data[1];
 871                 if ((data0 == 0x00 && data1 == 0x11) ||
 872                     (data0 == 0x22 && data1 == 0x33) ||
 873                     (data0 == 0x44 && data1 == 0x55) ||
 874                     (data0 == 0x66 && data1 == 0x77) ||
 875                     (data0 == 0x88 && data1 == 0x99) ||
 876                     (data0 == 0xaa && data1 == 0xbb) ||
 877                     (data0 == 0xcc && data1 == 0xdd) ||
 878                     (data0 == 0xee && data1 == 0xff)) {
 879                         input_report_key(gspca_dev->input_dev, KEY_CAMERA, 1);
 880                         input_sync(gspca_dev->input_dev);
 881                         input_report_key(gspca_dev->input_dev, KEY_CAMERA, 0);
 882                         input_sync(gspca_dev->input_dev);
 883                         ret = 0;
 884                 }
 885         }
 886 
 887         return ret;
 888 }
 889 #endif
 890 
 891 /* sub-driver description for pac7302 */
 892 static const struct sd_desc sd_desc = {
 893         .name = KBUILD_MODNAME,
 894         .config = sd_config,
 895         .init = sd_init,
 896         .init_controls = sd_init_controls,
 897         .start = sd_start,
 898         .stopN = sd_stopN,
 899         .stop0 = sd_stop0,
 900         .pkt_scan = sd_pkt_scan,
 901         .dq_callback = do_autogain,
 902 #ifdef CONFIG_VIDEO_ADV_DEBUG
 903         .set_register = sd_dbg_s_register,
 904 #endif
 905 #if IS_ENABLED(CONFIG_INPUT)
 906         .int_pkt_scan = sd_int_pkt_scan,
 907 #endif
 908 };
 909 
 910 /* -- module initialisation -- */
 911 static const struct usb_device_id device_table[] = {
 912         {USB_DEVICE(0x06f8, 0x3009)},
 913         {USB_DEVICE(0x06f8, 0x301b)},
 914         {USB_DEVICE(0x093a, 0x2620)},
 915         {USB_DEVICE(0x093a, 0x2621)},
 916         {USB_DEVICE(0x093a, 0x2622), .driver_info = FL_VFLIP},
 917         {USB_DEVICE(0x093a, 0x2623), .driver_info = FL_VFLIP},
 918         {USB_DEVICE(0x093a, 0x2624), .driver_info = FL_VFLIP},
 919         {USB_DEVICE(0x093a, 0x2625)},
 920         {USB_DEVICE(0x093a, 0x2626)},
 921         {USB_DEVICE(0x093a, 0x2627), .driver_info = FL_VFLIP},
 922         {USB_DEVICE(0x093a, 0x2628)},
 923         {USB_DEVICE(0x093a, 0x2629), .driver_info = FL_VFLIP},
 924         {USB_DEVICE(0x093a, 0x262a)},
 925         {USB_DEVICE(0x093a, 0x262c)},
 926         {USB_DEVICE(0x145f, 0x013c)},
 927         {USB_DEVICE(0x1ae7, 0x2001)}, /* SpeedLink Snappy Mic SL-6825-SBK */
 928         {}
 929 };
 930 MODULE_DEVICE_TABLE(usb, device_table);
 931 
 932 /* -- device connect -- */
 933 static int sd_probe(struct usb_interface *intf,
 934                         const struct usb_device_id *id)
 935 {
 936         return gspca_dev_probe(intf, id, &sd_desc, sizeof(struct sd),
 937                                 THIS_MODULE);
 938 }
 939 
 940 static struct usb_driver sd_driver = {
 941         .name = KBUILD_MODNAME,
 942         .id_table = device_table,
 943         .probe = sd_probe,
 944         .disconnect = gspca_disconnect,
 945 #ifdef CONFIG_PM
 946         .suspend = gspca_suspend,
 947         .resume = gspca_resume,
 948         .reset_resume = gspca_resume,
 949 #endif
 950 };
 951 
 952 module_usb_driver(sd_driver);

/* [<][>][^][v][top][bottom][index][help] */