linux/drivers/media/usb/gspca/spca500.c
<<
>>
Prefs
   1/*
   2 * SPCA500 chip based cameras initialization data
   3 *
   4 * V4L2 by Jean-Francois Moine <http://moinejf.free.fr>
   5 *
   6 * This program is free software; you can redistribute it and/or modify
   7 * it under the terms of the GNU General Public License as published by
   8 * the Free Software Foundation; either version 2 of the License, or
   9 * any later version.
  10 *
  11 * This program is distributed in the hope that it will be useful,
  12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
  13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  14 * GNU General Public License for more details.
  15 *
  16 */
  17
  18#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
  19
  20#define MODULE_NAME "spca500"
  21
  22#include "gspca.h"
  23#include "jpeg.h"
  24
  25MODULE_AUTHOR("Michel Xhaard <mxhaard@users.sourceforge.net>");
  26MODULE_DESCRIPTION("GSPCA/SPCA500 USB Camera Driver");
  27MODULE_LICENSE("GPL");
  28
  29#define QUALITY 85
  30
  31/* specific webcam descriptor */
  32struct sd {
  33        struct gspca_dev gspca_dev;             /* !! must be the first item */
  34
  35        char subtype;
  36#define AgfaCl20 0
  37#define AiptekPocketDV 1
  38#define BenqDC1016 2
  39#define CreativePCCam300 3
  40#define DLinkDSC350 4
  41#define Gsmartmini 5
  42#define IntelPocketPCCamera 6
  43#define KodakEZ200 7
  44#define LogitechClickSmart310 8
  45#define LogitechClickSmart510 9
  46#define LogitechTraveler 10
  47#define MustekGsmart300 11
  48#define Optimedia 12
  49#define PalmPixDC85 13
  50#define ToptroIndus 14
  51
  52        u8 jpeg_hdr[JPEG_HDR_SZ];
  53};
  54
  55static const struct v4l2_pix_format vga_mode[] = {
  56        {320, 240, V4L2_PIX_FMT_JPEG, V4L2_FIELD_NONE,
  57                .bytesperline = 320,
  58                .sizeimage = 320 * 240 * 3 / 8 + 590,
  59                .colorspace = V4L2_COLORSPACE_JPEG,
  60                .priv = 1},
  61        {640, 480, V4L2_PIX_FMT_JPEG, V4L2_FIELD_NONE,
  62                .bytesperline = 640,
  63                .sizeimage = 640 * 480 * 3 / 8 + 590,
  64                .colorspace = V4L2_COLORSPACE_JPEG,
  65                .priv = 0},
  66};
  67
  68static const struct v4l2_pix_format sif_mode[] = {
  69        {176, 144, V4L2_PIX_FMT_JPEG, V4L2_FIELD_NONE,
  70                .bytesperline = 176,
  71                .sizeimage = 176 * 144 * 3 / 8 + 590,
  72                .colorspace = V4L2_COLORSPACE_JPEG,
  73                .priv = 1},
  74        {352, 288, V4L2_PIX_FMT_JPEG, V4L2_FIELD_NONE,
  75                .bytesperline = 352,
  76                .sizeimage = 352 * 288 * 3 / 8 + 590,
  77                .colorspace = V4L2_COLORSPACE_JPEG,
  78                .priv = 0},
  79};
  80
  81/* Frame packet header offsets for the spca500 */
  82#define SPCA500_OFFSET_PADDINGLB 2
  83#define SPCA500_OFFSET_PADDINGHB 3
  84#define SPCA500_OFFSET_MODE      4
  85#define SPCA500_OFFSET_IMGWIDTH  5
  86#define SPCA500_OFFSET_IMGHEIGHT 6
  87#define SPCA500_OFFSET_IMGMODE   7
  88#define SPCA500_OFFSET_QTBLINDEX 8
  89#define SPCA500_OFFSET_FRAMSEQ   9
  90#define SPCA500_OFFSET_CDSPINFO  10
  91#define SPCA500_OFFSET_GPIO      11
  92#define SPCA500_OFFSET_AUGPIO    12
  93#define SPCA500_OFFSET_DATA      16
  94
  95
  96static const __u16 spca500_visual_defaults[][3] = {
  97        {0x00, 0x0003, 0x816b}, /* SSI not active sync with vsync,
  98                                 * hue (H byte) = 0,
  99                                 * saturation/hue enable,
 100                                 * brightness/contrast enable.
 101                                 */
 102        {0x00, 0x0000, 0x8167}, /* brightness = 0 */
 103        {0x00, 0x0020, 0x8168}, /* contrast = 0 */
 104        {0x00, 0x0003, 0x816b}, /* SSI not active sync with vsync,
 105                                 * hue (H byte) = 0, saturation/hue enable,
 106                                 * brightness/contrast enable.
 107                                 * was 0x0003, now 0x0000.
 108                                 */
 109        {0x00, 0x0000, 0x816a}, /* hue (L byte) = 0 */
 110        {0x00, 0x0020, 0x8169}, /* saturation = 0x20 */
 111        {0x00, 0x0050, 0x8157}, /* edge gain high threshold */
 112        {0x00, 0x0030, 0x8158}, /* edge gain low threshold */
 113        {0x00, 0x0028, 0x8159}, /* edge bandwidth high threshold */
 114        {0x00, 0x000a, 0x815a}, /* edge bandwidth low threshold */
 115        {0x00, 0x0001, 0x8202}, /* clock rate compensation = 1/25 sec/frame */
 116        {0x0c, 0x0004, 0x0000},
 117        /* set interface */
 118        {}
 119};
 120static const __u16 Clicksmart510_defaults[][3] = {
 121        {0x00, 0x00, 0x8211},
 122        {0x00, 0x01, 0x82c0},
 123        {0x00, 0x10, 0x82cb},
 124        {0x00, 0x0f, 0x800d},
 125        {0x00, 0x82, 0x8225},
 126        {0x00, 0x21, 0x8228},
 127        {0x00, 0x00, 0x8203},
 128        {0x00, 0x00, 0x8204},
 129        {0x00, 0x08, 0x8205},
 130        {0x00, 0xf8, 0x8206},
 131        {0x00, 0x28, 0x8207},
 132        {0x00, 0xa0, 0x8208},
 133        {0x00, 0x08, 0x824a},
 134        {0x00, 0x08, 0x8214},
 135        {0x00, 0x80, 0x82c1},
 136        {0x00, 0x00, 0x82c2},
 137        {0x00, 0x00, 0x82ca},
 138        {0x00, 0x80, 0x82c1},
 139        {0x00, 0x04, 0x82c2},
 140        {0x00, 0x00, 0x82ca},
 141        {0x00, 0xfc, 0x8100},
 142        {0x00, 0xfc, 0x8105},
 143        {0x00, 0x30, 0x8101},
 144        {0x00, 0x00, 0x8102},
 145        {0x00, 0x00, 0x8103},
 146        {0x00, 0x66, 0x8107},
 147        {0x00, 0x00, 0x816b},
 148        {0x00, 0x00, 0x8155},
 149        {0x00, 0x01, 0x8156},
 150        {0x00, 0x60, 0x8157},
 151        {0x00, 0x40, 0x8158},
 152        {0x00, 0x0a, 0x8159},
 153        {0x00, 0x06, 0x815a},
 154        {0x00, 0x00, 0x813f},
 155        {0x00, 0x00, 0x8200},
 156        {0x00, 0x19, 0x8201},
 157        {0x00, 0x00, 0x82c1},
 158        {0x00, 0xa0, 0x82c2},
 159        {0x00, 0x00, 0x82ca},
 160        {0x00, 0x00, 0x8117},
 161        {0x00, 0x00, 0x8118},
 162        {0x00, 0x65, 0x8119},
 163        {0x00, 0x00, 0x811a},
 164        {0x00, 0x00, 0x811b},
 165        {0x00, 0x55, 0x811c},
 166        {0x00, 0x65, 0x811d},
 167        {0x00, 0x55, 0x811e},
 168        {0x00, 0x16, 0x811f},
 169        {0x00, 0x19, 0x8120},
 170        {0x00, 0x80, 0x8103},
 171        {0x00, 0x83, 0x816b},
 172        {0x00, 0x25, 0x8168},
 173        {0x00, 0x01, 0x820f},
 174        {0x00, 0xff, 0x8115},
 175        {0x00, 0x48, 0x8116},
 176        {0x00, 0x50, 0x8151},
 177        {0x00, 0x40, 0x8152},
 178        {0x00, 0x78, 0x8153},
 179        {0x00, 0x40, 0x8154},
 180        {0x00, 0x00, 0x8167},
 181        {0x00, 0x20, 0x8168},
 182        {0x00, 0x00, 0x816a},
 183        {0x00, 0x03, 0x816b},
 184        {0x00, 0x20, 0x8169},
 185        {0x00, 0x60, 0x8157},
 186        {0x00, 0x00, 0x8190},
 187        {0x00, 0x00, 0x81a1},
 188        {0x00, 0x00, 0x81b2},
 189        {0x00, 0x27, 0x8191},
 190        {0x00, 0x27, 0x81a2},
 191        {0x00, 0x27, 0x81b3},
 192        {0x00, 0x4b, 0x8192},
 193        {0x00, 0x4b, 0x81a3},
 194        {0x00, 0x4b, 0x81b4},
 195        {0x00, 0x66, 0x8193},
 196        {0x00, 0x66, 0x81a4},
 197        {0x00, 0x66, 0x81b5},
 198        {0x00, 0x79, 0x8194},
 199        {0x00, 0x79, 0x81a5},
 200        {0x00, 0x79, 0x81b6},
 201        {0x00, 0x8a, 0x8195},
 202        {0x00, 0x8a, 0x81a6},
 203        {0x00, 0x8a, 0x81b7},
 204        {0x00, 0x9b, 0x8196},
 205        {0x00, 0x9b, 0x81a7},
 206        {0x00, 0x9b, 0x81b8},
 207        {0x00, 0xa6, 0x8197},
 208        {0x00, 0xa6, 0x81a8},
 209        {0x00, 0xa6, 0x81b9},
 210        {0x00, 0xb2, 0x8198},
 211        {0x00, 0xb2, 0x81a9},
 212        {0x00, 0xb2, 0x81ba},
 213        {0x00, 0xbe, 0x8199},
 214        {0x00, 0xbe, 0x81aa},
 215        {0x00, 0xbe, 0x81bb},
 216        {0x00, 0xc8, 0x819a},
 217        {0x00, 0xc8, 0x81ab},
 218        {0x00, 0xc8, 0x81bc},
 219        {0x00, 0xd2, 0x819b},
 220        {0x00, 0xd2, 0x81ac},
 221        {0x00, 0xd2, 0x81bd},
 222        {0x00, 0xdb, 0x819c},
 223        {0x00, 0xdb, 0x81ad},
 224        {0x00, 0xdb, 0x81be},
 225        {0x00, 0xe4, 0x819d},
 226        {0x00, 0xe4, 0x81ae},
 227        {0x00, 0xe4, 0x81bf},
 228        {0x00, 0xed, 0x819e},
 229        {0x00, 0xed, 0x81af},
 230        {0x00, 0xed, 0x81c0},
 231        {0x00, 0xf7, 0x819f},
 232        {0x00, 0xf7, 0x81b0},
 233        {0x00, 0xf7, 0x81c1},
 234        {0x00, 0xff, 0x81a0},
 235        {0x00, 0xff, 0x81b1},
 236        {0x00, 0xff, 0x81c2},
 237        {0x00, 0x03, 0x8156},
 238        {0x00, 0x00, 0x8211},
 239        {0x00, 0x20, 0x8168},
 240        {0x00, 0x01, 0x8202},
 241        {0x00, 0x30, 0x8101},
 242        {0x00, 0x00, 0x8111},
 243        {0x00, 0x00, 0x8112},
 244        {0x00, 0x00, 0x8113},
 245        {0x00, 0x00, 0x8114},
 246        {}
 247};
 248
 249static const __u8 qtable_creative_pccam[2][64] = {
 250        {                               /* Q-table Y-components */
 251         0x05, 0x03, 0x03, 0x05, 0x07, 0x0c, 0x0f, 0x12,
 252         0x04, 0x04, 0x04, 0x06, 0x08, 0x11, 0x12, 0x11,
 253         0x04, 0x04, 0x05, 0x07, 0x0c, 0x11, 0x15, 0x11,
 254         0x04, 0x05, 0x07, 0x09, 0x0f, 0x1a, 0x18, 0x13,
 255         0x05, 0x07, 0x0b, 0x11, 0x14, 0x21, 0x1f, 0x17,
 256         0x07, 0x0b, 0x11, 0x13, 0x18, 0x1f, 0x22, 0x1c,
 257         0x0f, 0x13, 0x17, 0x1a, 0x1f, 0x24, 0x24, 0x1e,
 258         0x16, 0x1c, 0x1d, 0x1d, 0x22, 0x1e, 0x1f, 0x1e},
 259        {                               /* Q-table C-components */
 260         0x05, 0x05, 0x07, 0x0e, 0x1e, 0x1e, 0x1e, 0x1e,
 261         0x05, 0x06, 0x08, 0x14, 0x1e, 0x1e, 0x1e, 0x1e,
 262         0x07, 0x08, 0x11, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e,
 263         0x0e, 0x14, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e,
 264         0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e,
 265         0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e,
 266         0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e,
 267         0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e, 0x1e}
 268};
 269
 270static const __u8 qtable_kodak_ez200[2][64] = {
 271        {                               /* Q-table Y-components */
 272         0x02, 0x01, 0x01, 0x02, 0x02, 0x04, 0x05, 0x06,
 273         0x01, 0x01, 0x01, 0x02, 0x03, 0x06, 0x06, 0x06,
 274         0x01, 0x01, 0x02, 0x02, 0x04, 0x06, 0x07, 0x06,
 275         0x01, 0x02, 0x02, 0x03, 0x05, 0x09, 0x08, 0x06,
 276         0x02, 0x02, 0x04, 0x06, 0x07, 0x0b, 0x0a, 0x08,
 277         0x02, 0x04, 0x06, 0x06, 0x08, 0x0a, 0x0b, 0x09,
 278         0x05, 0x06, 0x08, 0x09, 0x0a, 0x0c, 0x0c, 0x0a,
 279         0x07, 0x09, 0x0a, 0x0a, 0x0b, 0x0a, 0x0a, 0x0a},
 280        {                               /* Q-table C-components */
 281         0x02, 0x02, 0x02, 0x05, 0x0a, 0x0a, 0x0a, 0x0a,
 282         0x02, 0x02, 0x03, 0x07, 0x0a, 0x0a, 0x0a, 0x0a,
 283         0x02, 0x03, 0x06, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a,
 284         0x05, 0x07, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a,
 285         0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a,
 286         0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a,
 287         0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a,
 288         0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a}
 289};
 290
 291static const __u8 qtable_pocketdv[2][64] = {
 292        {               /* Q-table Y-components start registers 0x8800 */
 293         0x06, 0x04, 0x04, 0x06, 0x0a, 0x10, 0x14, 0x18,
 294         0x05, 0x05, 0x06, 0x08, 0x0a, 0x17, 0x18, 0x16,
 295         0x06, 0x05, 0x06, 0x0a, 0x10, 0x17, 0x1c, 0x16,
 296         0x06, 0x07, 0x09, 0x0c, 0x14, 0x23, 0x20, 0x19,
 297         0x07, 0x09, 0x0f, 0x16, 0x1b, 0x2c, 0x29, 0x1f,
 298         0x0a, 0x0e, 0x16, 0x1a, 0x20, 0x2a, 0x2d, 0x25,
 299         0x14, 0x1a, 0x1f, 0x23, 0x29, 0x30, 0x30, 0x28,
 300         0x1d, 0x25, 0x26, 0x27, 0x2d, 0x28, 0x29, 0x28,
 301         },
 302        {               /* Q-table C-components start registers 0x8840 */
 303         0x07, 0x07, 0x0a, 0x13, 0x28, 0x28, 0x28, 0x28,
 304         0x07, 0x08, 0x0a, 0x1a, 0x28, 0x28, 0x28, 0x28,
 305         0x0a, 0x0a, 0x16, 0x28, 0x28, 0x28, 0x28, 0x28,
 306         0x13, 0x1a, 0x28, 0x28, 0x28, 0x28, 0x28, 0x28,
 307         0x28, 0x28, 0x28, 0x28, 0x28, 0x28, 0x28, 0x28,
 308         0x28, 0x28, 0x28, 0x28, 0x28, 0x28, 0x28, 0x28,
 309         0x28, 0x28, 0x28, 0x28, 0x28, 0x28, 0x28, 0x28,
 310         0x28, 0x28, 0x28, 0x28, 0x28, 0x28, 0x28, 0x28}
 311};
 312
 313/* read 'len' bytes to gspca_dev->usb_buf */
 314static void reg_r(struct gspca_dev *gspca_dev,
 315                  __u16 index,
 316                  __u16 length)
 317{
 318        usb_control_msg(gspca_dev->dev,
 319                        usb_rcvctrlpipe(gspca_dev->dev, 0),
 320                        0,
 321                        USB_DIR_IN | USB_TYPE_VENDOR | USB_RECIP_DEVICE,
 322                        0,              /* value */
 323                        index, gspca_dev->usb_buf, length, 500);
 324}
 325
 326static int reg_w(struct gspca_dev *gspca_dev,
 327                     __u16 req, __u16 index, __u16 value)
 328{
 329        int ret;
 330
 331        gspca_dbg(gspca_dev, D_USBO, "reg write: [0x%02x] = 0x%02x\n",
 332                  index, value);
 333        ret = usb_control_msg(gspca_dev->dev,
 334                        usb_sndctrlpipe(gspca_dev->dev, 0),
 335                        req,
 336                        USB_DIR_OUT | USB_TYPE_VENDOR | USB_RECIP_DEVICE,
 337                        value, index, NULL, 0, 500);
 338        if (ret < 0)
 339                pr_err("reg write: error %d\n", ret);
 340        return ret;
 341}
 342
 343/* returns: negative is error, pos or zero is data */
 344static int reg_r_12(struct gspca_dev *gspca_dev,
 345                        __u16 req,      /* bRequest */
 346                        __u16 index,    /* wIndex */
 347                        __u16 length)   /* wLength (1 or 2 only) */
 348{
 349        int ret;
 350
 351        gspca_dev->usb_buf[1] = 0;
 352        ret = usb_control_msg(gspca_dev->dev,
 353                        usb_rcvctrlpipe(gspca_dev->dev, 0),
 354                        req,
 355                        USB_DIR_IN | USB_TYPE_VENDOR | USB_RECIP_DEVICE,
 356                        0,              /* value */
 357                        index,
 358                        gspca_dev->usb_buf, length,
 359                        500);           /* timeout */
 360        if (ret < 0) {
 361                pr_err("reg_r_12 err %d\n", ret);
 362                return ret;
 363        }
 364        return (gspca_dev->usb_buf[1] << 8) + gspca_dev->usb_buf[0];
 365}
 366
 367/*
 368 * Simple function to wait for a given 8-bit value to be returned from
 369 * a reg_read call.
 370 * Returns: negative is error or timeout, zero is success.
 371 */
 372static int reg_r_wait(struct gspca_dev *gspca_dev,
 373                        __u16 reg, __u16 index, __u16 value)
 374{
 375        int ret, cnt = 20;
 376
 377        while (--cnt > 0) {
 378                ret = reg_r_12(gspca_dev, reg, index, 1);
 379                if (ret == value)
 380                        return 0;
 381                msleep(50);
 382        }
 383        return -EIO;
 384}
 385
 386static int write_vector(struct gspca_dev *gspca_dev,
 387                        const __u16 data[][3])
 388{
 389        int ret, i = 0;
 390
 391        while (data[i][0] != 0 || data[i][1] != 0 || data[i][2] != 0) {
 392                ret = reg_w(gspca_dev, data[i][0], data[i][2], data[i][1]);
 393                if (ret < 0)
 394                        return ret;
 395                i++;
 396        }
 397        return 0;
 398}
 399
 400static int spca50x_setup_qtable(struct gspca_dev *gspca_dev,
 401                                unsigned int request,
 402                                unsigned int ybase,
 403                                unsigned int cbase,
 404                                const __u8 qtable[2][64])
 405{
 406        int i, err;
 407
 408        /* loop over y components */
 409        for (i = 0; i < 64; i++) {
 410                err = reg_w(gspca_dev, request, ybase + i, qtable[0][i]);
 411                if (err < 0)
 412                        return err;
 413        }
 414
 415        /* loop over c components */
 416        for (i = 0; i < 64; i++) {
 417                err = reg_w(gspca_dev, request, cbase + i, qtable[1][i]);
 418                if (err < 0)
 419                        return err;
 420        }
 421        return 0;
 422}
 423
 424static void spca500_ping310(struct gspca_dev *gspca_dev)
 425{
 426        reg_r(gspca_dev, 0x0d04, 2);
 427        gspca_dbg(gspca_dev, D_STREAM, "ClickSmart310 ping 0x0d04 0x%02x 0x%02x\n",
 428                  gspca_dev->usb_buf[0], gspca_dev->usb_buf[1]);
 429}
 430
 431static void spca500_clksmart310_init(struct gspca_dev *gspca_dev)
 432{
 433        reg_r(gspca_dev, 0x0d05, 2);
 434        gspca_dbg(gspca_dev, D_STREAM, "ClickSmart310 init 0x0d05 0x%02x 0x%02x\n",
 435                  gspca_dev->usb_buf[0], gspca_dev->usb_buf[1]);
 436        reg_w(gspca_dev, 0x00, 0x8167, 0x5a);
 437        spca500_ping310(gspca_dev);
 438
 439        reg_w(gspca_dev, 0x00, 0x8168, 0x22);
 440        reg_w(gspca_dev, 0x00, 0x816a, 0xc0);
 441        reg_w(gspca_dev, 0x00, 0x816b, 0x0b);
 442        reg_w(gspca_dev, 0x00, 0x8169, 0x25);
 443        reg_w(gspca_dev, 0x00, 0x8157, 0x5b);
 444        reg_w(gspca_dev, 0x00, 0x8158, 0x5b);
 445        reg_w(gspca_dev, 0x00, 0x813f, 0x03);
 446        reg_w(gspca_dev, 0x00, 0x8151, 0x4a);
 447        reg_w(gspca_dev, 0x00, 0x8153, 0x78);
 448        reg_w(gspca_dev, 0x00, 0x0d01, 0x04);
 449                                                /* 00 for adjust shutter */
 450        reg_w(gspca_dev, 0x00, 0x0d02, 0x01);
 451        reg_w(gspca_dev, 0x00, 0x8169, 0x25);
 452        reg_w(gspca_dev, 0x00, 0x0d01, 0x02);
 453}
 454
 455static void spca500_setmode(struct gspca_dev *gspca_dev,
 456                        __u8 xmult, __u8 ymult)
 457{
 458        int mode;
 459
 460        /* set x multiplier */
 461        reg_w(gspca_dev, 0, 0x8001, xmult);
 462
 463        /* set y multiplier */
 464        reg_w(gspca_dev, 0, 0x8002, ymult);
 465
 466        /* use compressed mode, VGA, with mode specific subsample */
 467        mode = gspca_dev->cam.cam_mode[(int) gspca_dev->curr_mode].priv;
 468        reg_w(gspca_dev, 0, 0x8003, mode << 4);
 469}
 470
 471static int spca500_full_reset(struct gspca_dev *gspca_dev)
 472{
 473        int err;
 474
 475        /* send the reset command */
 476        err = reg_w(gspca_dev, 0xe0, 0x0001, 0x0000);
 477        if (err < 0)
 478                return err;
 479
 480        /* wait for the reset to complete */
 481        err = reg_r_wait(gspca_dev, 0x06, 0x0000, 0x0000);
 482        if (err < 0)
 483                return err;
 484        err = reg_w(gspca_dev, 0xe0, 0x0000, 0x0000);
 485        if (err < 0)
 486                return err;
 487        err = reg_r_wait(gspca_dev, 0x06, 0, 0);
 488        if (err < 0) {
 489                gspca_err(gspca_dev, "reg_r_wait() failed\n");
 490                return err;
 491        }
 492        /* all ok */
 493        return 0;
 494}
 495
 496/* Synchro the Bridge with sensor */
 497/* Maybe that will work on all spca500 chip */
 498/* because i only own a clicksmart310 try for that chip */
 499/* using spca50x_set_packet_size() cause an Ooops here */
 500/* usb_set_interface from kernel 2.6.x clear all the urb stuff */
 501/* up-port the same feature as in 2.4.x kernel */
 502static int spca500_synch310(struct gspca_dev *gspca_dev)
 503{
 504        if (usb_set_interface(gspca_dev->dev, gspca_dev->iface, 0) < 0) {
 505                gspca_err(gspca_dev, "Set packet size: set interface error\n");
 506                goto error;
 507        }
 508        spca500_ping310(gspca_dev);
 509
 510        reg_r(gspca_dev, 0x0d00, 1);
 511
 512        /* need alt setting here */
 513        gspca_dbg(gspca_dev, D_PACK, "ClickSmart310 sync alt: %d\n",
 514                  gspca_dev->alt);
 515
 516        /* Windoze use pipe with altsetting 6 why 7 here */
 517        if (usb_set_interface(gspca_dev->dev,
 518                                gspca_dev->iface,
 519                                gspca_dev->alt) < 0) {
 520                gspca_err(gspca_dev, "Set packet size: set interface error\n");
 521                goto error;
 522        }
 523        return 0;
 524error:
 525        return -EBUSY;
 526}
 527
 528static void spca500_reinit(struct gspca_dev *gspca_dev)
 529{
 530        int err;
 531        __u8 Data;
 532
 533        /* some unknown command from Aiptek pocket dv and family300 */
 534
 535        reg_w(gspca_dev, 0x00, 0x0d01, 0x01);
 536        reg_w(gspca_dev, 0x00, 0x0d03, 0x00);
 537        reg_w(gspca_dev, 0x00, 0x0d02, 0x01);
 538
 539        /* enable drop packet */
 540        reg_w(gspca_dev, 0x00, 0x850a, 0x0001);
 541
 542        err = spca50x_setup_qtable(gspca_dev, 0x00, 0x8800, 0x8840,
 543                                 qtable_pocketdv);
 544        if (err < 0)
 545                gspca_err(gspca_dev, "spca50x_setup_qtable failed on init\n");
 546
 547        /* set qtable index */
 548        reg_w(gspca_dev, 0x00, 0x8880, 2);
 549        /* family cam Quicksmart stuff */
 550        reg_w(gspca_dev, 0x00, 0x800a, 0x00);
 551        /* Set agc transfer: synced between frames */
 552        reg_w(gspca_dev, 0x00, 0x820f, 0x01);
 553        /* Init SDRAM - needed for SDRAM access */
 554        reg_w(gspca_dev, 0x00, 0x870a, 0x04);
 555        /*Start init sequence or stream */
 556        reg_w(gspca_dev, 0, 0x8003, 0x00);
 557        /* switch to video camera mode */
 558        reg_w(gspca_dev, 0x00, 0x8000, 0x0004);
 559        msleep(2000);
 560        if (reg_r_wait(gspca_dev, 0, 0x8000, 0x44) != 0) {
 561                reg_r(gspca_dev, 0x816b, 1);
 562                Data = gspca_dev->usb_buf[0];
 563                reg_w(gspca_dev, 0x00, 0x816b, Data);
 564        }
 565}
 566
 567/* this function is called at probe time */
 568static int sd_config(struct gspca_dev *gspca_dev,
 569                        const struct usb_device_id *id)
 570{
 571        struct sd *sd = (struct sd *) gspca_dev;
 572        struct cam *cam;
 573
 574        cam = &gspca_dev->cam;
 575        sd->subtype = id->driver_info;
 576        if (sd->subtype != LogitechClickSmart310) {
 577                cam->cam_mode = vga_mode;
 578                cam->nmodes = ARRAY_SIZE(vga_mode);
 579        } else {
 580                cam->cam_mode = sif_mode;
 581                cam->nmodes = ARRAY_SIZE(sif_mode);
 582        }
 583        return 0;
 584}
 585
 586/* this function is called at probe and resume time */
 587static int sd_init(struct gspca_dev *gspca_dev)
 588{
 589        struct sd *sd = (struct sd *) gspca_dev;
 590
 591        /* initialisation of spca500 based cameras is deferred */
 592        gspca_dbg(gspca_dev, D_STREAM, "SPCA500 init\n");
 593        if (sd->subtype == LogitechClickSmart310)
 594                spca500_clksmart310_init(gspca_dev);
 595/*      else
 596                spca500_initialise(gspca_dev); */
 597        gspca_dbg(gspca_dev, D_STREAM, "SPCA500 init done\n");
 598        return 0;
 599}
 600
 601static int sd_start(struct gspca_dev *gspca_dev)
 602{
 603        struct sd *sd = (struct sd *) gspca_dev;
 604        int err;
 605        __u8 Data;
 606        __u8 xmult, ymult;
 607
 608        /* create the JPEG header */
 609        jpeg_define(sd->jpeg_hdr, gspca_dev->pixfmt.height,
 610                        gspca_dev->pixfmt.width,
 611                        0x22);          /* JPEG 411 */
 612        jpeg_set_qual(sd->jpeg_hdr, QUALITY);
 613
 614        if (sd->subtype == LogitechClickSmart310) {
 615                xmult = 0x16;
 616                ymult = 0x12;
 617        } else {
 618                xmult = 0x28;
 619                ymult = 0x1e;
 620        }
 621
 622        /* is there a sensor here ? */
 623        reg_r(gspca_dev, 0x8a04, 1);
 624        gspca_dbg(gspca_dev, D_STREAM, "Spca500 Sensor Address 0x%02x\n",
 625                  gspca_dev->usb_buf[0]);
 626        gspca_dbg(gspca_dev, D_STREAM, "Spca500 curr_mode: %d Xmult: 0x%02x, Ymult: 0x%02x",
 627                  gspca_dev->curr_mode, xmult, ymult);
 628
 629        /* setup qtable */
 630        switch (sd->subtype) {
 631        case LogitechClickSmart310:
 632                 spca500_setmode(gspca_dev, xmult, ymult);
 633
 634                /* enable drop packet */
 635                reg_w(gspca_dev, 0x00, 0x850a, 0x0001);
 636                reg_w(gspca_dev, 0x00, 0x8880, 3);
 637                err = spca50x_setup_qtable(gspca_dev,
 638                                           0x00, 0x8800, 0x8840,
 639                                           qtable_creative_pccam);
 640                if (err < 0)
 641                        gspca_err(gspca_dev, "spca50x_setup_qtable failed\n");
 642                /* Init SDRAM - needed for SDRAM access */
 643                reg_w(gspca_dev, 0x00, 0x870a, 0x04);
 644
 645                /* switch to video camera mode */
 646                reg_w(gspca_dev, 0x00, 0x8000, 0x0004);
 647                msleep(500);
 648                if (reg_r_wait(gspca_dev, 0, 0x8000, 0x44) != 0)
 649                        gspca_err(gspca_dev, "reg_r_wait() failed\n");
 650
 651                reg_r(gspca_dev, 0x816b, 1);
 652                Data = gspca_dev->usb_buf[0];
 653                reg_w(gspca_dev, 0x00, 0x816b, Data);
 654
 655                spca500_synch310(gspca_dev);
 656
 657                write_vector(gspca_dev, spca500_visual_defaults);
 658                spca500_setmode(gspca_dev, xmult, ymult);
 659                /* enable drop packet */
 660                err = reg_w(gspca_dev, 0x00, 0x850a, 0x0001);
 661                if (err < 0)
 662                        gspca_err(gspca_dev, "failed to enable drop packet\n");
 663                reg_w(gspca_dev, 0x00, 0x8880, 3);
 664                err = spca50x_setup_qtable(gspca_dev,
 665                                           0x00, 0x8800, 0x8840,
 666                                           qtable_creative_pccam);
 667                if (err < 0)
 668                        gspca_err(gspca_dev, "spca50x_setup_qtable failed\n");
 669
 670                /* Init SDRAM - needed for SDRAM access */
 671                reg_w(gspca_dev, 0x00, 0x870a, 0x04);
 672
 673                /* switch to video camera mode */
 674                reg_w(gspca_dev, 0x00, 0x8000, 0x0004);
 675
 676                if (reg_r_wait(gspca_dev, 0, 0x8000, 0x44) != 0)
 677                        gspca_err(gspca_dev, "reg_r_wait() failed\n");
 678
 679                reg_r(gspca_dev, 0x816b, 1);
 680                Data = gspca_dev->usb_buf[0];
 681                reg_w(gspca_dev, 0x00, 0x816b, Data);
 682                break;
 683        case CreativePCCam300:          /* Creative PC-CAM 300 640x480 CCD */
 684        case IntelPocketPCCamera:       /* FIXME: Temporary fix for
 685                                         *      Intel Pocket PC Camera
 686                                         *      - NWG (Sat 29th March 2003) */
 687
 688                /* do a full reset */
 689                err = spca500_full_reset(gspca_dev);
 690                if (err < 0)
 691                        gspca_err(gspca_dev, "spca500_full_reset failed\n");
 692
 693                /* enable drop packet */
 694                err = reg_w(gspca_dev, 0x00, 0x850a, 0x0001);
 695                if (err < 0)
 696                        gspca_err(gspca_dev, "failed to enable drop packet\n");
 697                reg_w(gspca_dev, 0x00, 0x8880, 3);
 698                err = spca50x_setup_qtable(gspca_dev,
 699                                           0x00, 0x8800, 0x8840,
 700                                           qtable_creative_pccam);
 701                if (err < 0)
 702                        gspca_err(gspca_dev, "spca50x_setup_qtable failed\n");
 703
 704                spca500_setmode(gspca_dev, xmult, ymult);
 705                reg_w(gspca_dev, 0x20, 0x0001, 0x0004);
 706
 707                /* switch to video camera mode */
 708                reg_w(gspca_dev, 0x00, 0x8000, 0x0004);
 709
 710                if (reg_r_wait(gspca_dev, 0, 0x8000, 0x44) != 0)
 711                        gspca_err(gspca_dev, "reg_r_wait() failed\n");
 712
 713                reg_r(gspca_dev, 0x816b, 1);
 714                Data = gspca_dev->usb_buf[0];
 715                reg_w(gspca_dev, 0x00, 0x816b, Data);
 716
 717/*              write_vector(gspca_dev, spca500_visual_defaults); */
 718                break;
 719        case KodakEZ200:                /* Kodak EZ200 */
 720
 721                /* do a full reset */
 722                err = spca500_full_reset(gspca_dev);
 723                if (err < 0)
 724                        gspca_err(gspca_dev, "spca500_full_reset failed\n");
 725                /* enable drop packet */
 726                reg_w(gspca_dev, 0x00, 0x850a, 0x0001);
 727                reg_w(gspca_dev, 0x00, 0x8880, 0);
 728                err = spca50x_setup_qtable(gspca_dev,
 729                                           0x00, 0x8800, 0x8840,
 730                                           qtable_kodak_ez200);
 731                if (err < 0)
 732                        gspca_err(gspca_dev, "spca50x_setup_qtable failed\n");
 733                spca500_setmode(gspca_dev, xmult, ymult);
 734
 735                reg_w(gspca_dev, 0x20, 0x0001, 0x0004);
 736
 737                /* switch to video camera mode */
 738                reg_w(gspca_dev, 0x00, 0x8000, 0x0004);
 739
 740                if (reg_r_wait(gspca_dev, 0, 0x8000, 0x44) != 0)
 741                        gspca_err(gspca_dev, "reg_r_wait() failed\n");
 742
 743                reg_r(gspca_dev, 0x816b, 1);
 744                Data = gspca_dev->usb_buf[0];
 745                reg_w(gspca_dev, 0x00, 0x816b, Data);
 746
 747/*              write_vector(gspca_dev, spca500_visual_defaults); */
 748                break;
 749
 750        case BenqDC1016:
 751        case DLinkDSC350:               /* FamilyCam 300 */
 752        case AiptekPocketDV:            /* Aiptek PocketDV */
 753        case Gsmartmini:                /*Mustek Gsmart Mini */
 754        case MustekGsmart300:           /* Mustek Gsmart 300 */
 755        case PalmPixDC85:
 756        case Optimedia:
 757        case ToptroIndus:
 758        case AgfaCl20:
 759                spca500_reinit(gspca_dev);
 760                reg_w(gspca_dev, 0x00, 0x0d01, 0x01);
 761                /* enable drop packet */
 762                reg_w(gspca_dev, 0x00, 0x850a, 0x0001);
 763
 764                err = spca50x_setup_qtable(gspca_dev,
 765                                   0x00, 0x8800, 0x8840, qtable_pocketdv);
 766                if (err < 0)
 767                        gspca_err(gspca_dev, "spca50x_setup_qtable failed\n");
 768                reg_w(gspca_dev, 0x00, 0x8880, 2);
 769
 770                /* familycam Quicksmart pocketDV stuff */
 771                reg_w(gspca_dev, 0x00, 0x800a, 0x00);
 772                /* Set agc transfer: synced between frames */
 773                reg_w(gspca_dev, 0x00, 0x820f, 0x01);
 774                /* Init SDRAM - needed for SDRAM access */
 775                reg_w(gspca_dev, 0x00, 0x870a, 0x04);
 776
 777                spca500_setmode(gspca_dev, xmult, ymult);
 778                /* switch to video camera mode */
 779                reg_w(gspca_dev, 0x00, 0x8000, 0x0004);
 780
 781                reg_r_wait(gspca_dev, 0, 0x8000, 0x44);
 782
 783                reg_r(gspca_dev, 0x816b, 1);
 784                Data = gspca_dev->usb_buf[0];
 785                reg_w(gspca_dev, 0x00, 0x816b, Data);
 786                break;
 787        case LogitechTraveler:
 788        case LogitechClickSmart510:
 789                reg_w(gspca_dev, 0x02, 0x00, 0x00);
 790                /* enable drop packet */
 791                reg_w(gspca_dev, 0x00, 0x850a, 0x0001);
 792
 793                err = spca50x_setup_qtable(gspca_dev,
 794                                        0x00, 0x8800,
 795                                        0x8840, qtable_creative_pccam);
 796                if (err < 0)
 797                        gspca_err(gspca_dev, "spca50x_setup_qtable failed\n");
 798                reg_w(gspca_dev, 0x00, 0x8880, 3);
 799                reg_w(gspca_dev, 0x00, 0x800a, 0x00);
 800                /* Init SDRAM - needed for SDRAM access */
 801                reg_w(gspca_dev, 0x00, 0x870a, 0x04);
 802
 803                spca500_setmode(gspca_dev, xmult, ymult);
 804
 805                /* switch to video camera mode */
 806                reg_w(gspca_dev, 0x00, 0x8000, 0x0004);
 807                reg_r_wait(gspca_dev, 0, 0x8000, 0x44);
 808
 809                reg_r(gspca_dev, 0x816b, 1);
 810                Data = gspca_dev->usb_buf[0];
 811                reg_w(gspca_dev, 0x00, 0x816b, Data);
 812                write_vector(gspca_dev, Clicksmart510_defaults);
 813                break;
 814        }
 815        return 0;
 816}
 817
 818static void sd_stopN(struct gspca_dev *gspca_dev)
 819{
 820        reg_w(gspca_dev, 0, 0x8003, 0x00);
 821
 822        /* switch to video camera mode */
 823        reg_w(gspca_dev, 0x00, 0x8000, 0x0004);
 824        reg_r(gspca_dev, 0x8000, 1);
 825        gspca_dbg(gspca_dev, D_STREAM, "stop SPCA500 done reg8000: 0x%2x\n",
 826                  gspca_dev->usb_buf[0]);
 827}
 828
 829static void sd_pkt_scan(struct gspca_dev *gspca_dev,
 830                        u8 *data,                       /* isoc packet */
 831                        int len)                        /* iso packet length */
 832{
 833        struct sd *sd = (struct sd *) gspca_dev;
 834        int i;
 835        static __u8 ffd9[] = {0xff, 0xd9};
 836
 837/* frames are jpeg 4.1.1 without 0xff escape */
 838        if (data[0] == 0xff) {
 839                if (data[1] != 0x01) {  /* drop packet */
 840/*                      gspca_dev->last_packet_type = DISCARD_PACKET; */
 841                        return;
 842                }
 843                gspca_frame_add(gspca_dev, LAST_PACKET,
 844                                        ffd9, 2);
 845
 846                /* put the JPEG header in the new frame */
 847                gspca_frame_add(gspca_dev, FIRST_PACKET,
 848                        sd->jpeg_hdr, JPEG_HDR_SZ);
 849
 850                data += SPCA500_OFFSET_DATA;
 851                len -= SPCA500_OFFSET_DATA;
 852        } else {
 853                data += 1;
 854                len -= 1;
 855        }
 856
 857        /* add 0x00 after 0xff */
 858        i = 0;
 859        do {
 860                if (data[i] == 0xff) {
 861                        gspca_frame_add(gspca_dev, INTER_PACKET,
 862                                        data, i + 1);
 863                        len -= i;
 864                        data += i;
 865                        *data = 0x00;
 866                        i = 0;
 867                }
 868                i++;
 869        } while (i < len);
 870        gspca_frame_add(gspca_dev, INTER_PACKET, data, len);
 871}
 872
 873static void setbrightness(struct gspca_dev *gspca_dev, s32 val)
 874{
 875        reg_w(gspca_dev, 0x00, 0x8167,
 876                        (__u8) (val - 128));
 877}
 878
 879static void setcontrast(struct gspca_dev *gspca_dev, s32 val)
 880{
 881        reg_w(gspca_dev, 0x00, 0x8168, val);
 882}
 883
 884static void setcolors(struct gspca_dev *gspca_dev, s32 val)
 885{
 886        reg_w(gspca_dev, 0x00, 0x8169, val);
 887}
 888
 889static int sd_s_ctrl(struct v4l2_ctrl *ctrl)
 890{
 891        struct gspca_dev *gspca_dev =
 892                container_of(ctrl->handler, struct gspca_dev, ctrl_handler);
 893
 894        gspca_dev->usb_err = 0;
 895
 896        if (!gspca_dev->streaming)
 897                return 0;
 898
 899        switch (ctrl->id) {
 900        case V4L2_CID_BRIGHTNESS:
 901                setbrightness(gspca_dev, ctrl->val);
 902                break;
 903        case V4L2_CID_CONTRAST:
 904                setcontrast(gspca_dev, ctrl->val);
 905                break;
 906        case V4L2_CID_SATURATION:
 907                setcolors(gspca_dev, ctrl->val);
 908                break;
 909        }
 910        return gspca_dev->usb_err;
 911}
 912
 913static const struct v4l2_ctrl_ops sd_ctrl_ops = {
 914        .s_ctrl = sd_s_ctrl,
 915};
 916
 917static int sd_init_controls(struct gspca_dev *gspca_dev)
 918{
 919        struct v4l2_ctrl_handler *hdl = &gspca_dev->ctrl_handler;
 920
 921        gspca_dev->vdev.ctrl_handler = hdl;
 922        v4l2_ctrl_handler_init(hdl, 3);
 923        v4l2_ctrl_new_std(hdl, &sd_ctrl_ops,
 924                        V4L2_CID_BRIGHTNESS, 0, 255, 1, 127);
 925        v4l2_ctrl_new_std(hdl, &sd_ctrl_ops,
 926                        V4L2_CID_CONTRAST, 0, 63, 1, 31);
 927        v4l2_ctrl_new_std(hdl, &sd_ctrl_ops,
 928                        V4L2_CID_SATURATION, 0, 63, 1, 31);
 929
 930        if (hdl->error) {
 931                pr_err("Could not initialize controls\n");
 932                return hdl->error;
 933        }
 934        return 0;
 935}
 936
 937/* sub-driver description */
 938static const struct sd_desc sd_desc = {
 939        .name = MODULE_NAME,
 940        .config = sd_config,
 941        .init = sd_init,
 942        .init_controls = sd_init_controls,
 943        .start = sd_start,
 944        .stopN = sd_stopN,
 945        .pkt_scan = sd_pkt_scan,
 946};
 947
 948/* -- module initialisation -- */
 949static const struct usb_device_id device_table[] = {
 950        {USB_DEVICE(0x040a, 0x0300), .driver_info = KodakEZ200},
 951        {USB_DEVICE(0x041e, 0x400a), .driver_info = CreativePCCam300},
 952        {USB_DEVICE(0x046d, 0x0890), .driver_info = LogitechTraveler},
 953        {USB_DEVICE(0x046d, 0x0900), .driver_info = LogitechClickSmart310},
 954        {USB_DEVICE(0x046d, 0x0901), .driver_info = LogitechClickSmart510},
 955        {USB_DEVICE(0x04a5, 0x300c), .driver_info = BenqDC1016},
 956        {USB_DEVICE(0x04fc, 0x7333), .driver_info = PalmPixDC85},
 957        {USB_DEVICE(0x055f, 0xc200), .driver_info = MustekGsmart300},
 958        {USB_DEVICE(0x055f, 0xc220), .driver_info = Gsmartmini},
 959        {USB_DEVICE(0x06bd, 0x0404), .driver_info = AgfaCl20},
 960        {USB_DEVICE(0x06be, 0x0800), .driver_info = Optimedia},
 961        {USB_DEVICE(0x084d, 0x0003), .driver_info = DLinkDSC350},
 962        {USB_DEVICE(0x08ca, 0x0103), .driver_info = AiptekPocketDV},
 963        {USB_DEVICE(0x2899, 0x012c), .driver_info = ToptroIndus},
 964        {USB_DEVICE(0x8086, 0x0630), .driver_info = IntelPocketPCCamera},
 965        {}
 966};
 967MODULE_DEVICE_TABLE(usb, device_table);
 968
 969/* -- device connect -- */
 970static int sd_probe(struct usb_interface *intf,
 971                        const struct usb_device_id *id)
 972{
 973        return gspca_dev_probe(intf, id, &sd_desc, sizeof(struct sd),
 974                                THIS_MODULE);
 975}
 976
 977static struct usb_driver sd_driver = {
 978        .name = MODULE_NAME,
 979        .id_table = device_table,
 980        .probe = sd_probe,
 981        .disconnect = gspca_disconnect,
 982#ifdef CONFIG_PM
 983        .suspend = gspca_suspend,
 984        .resume = gspca_resume,
 985        .reset_resume = gspca_resume,
 986#endif
 987};
 988
 989module_usb_driver(sd_driver);
 990