pac7311.c 22.9 KB
Newer Older
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21
/*
 *		Pixart PAC7311 library
 *		Copyright (C) 2005 Thomas Kaiser thomas@kaiser-linux.li
 *
 * V4L2 by Jean-Francois Moine <http://moinejf.free.fr>
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation; either version 2 of the License, or
 * any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
 */

22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41
/* Some documentation about various registers as determined by trial and error.
   When the register addresses differ between the 7202 and the 7311 the 2
   different addresses are written as 7302addr/7311addr, when one of the 2
   addresses is a - sign that register description is not valid for the
   matching IC.

   Register page 1:

   Address	Description
   -/0x08	Unknown compressor related, must always be 8 except when not
		in 640x480 resolution and page 4 reg 2 <= 3 then set it to 9 !
   -/0x1b	Auto white balance related, bit 0 is AWB enable (inverted)
		bits 345 seem to toggle per color gains on/off (inverted)
   0x78		Global control, bit 6 controls the LED (inverted)
   -/0x80	JPEG compression ratio ? Best not touched

   Register page 3/4:

   Address	Description
   0x02		Clock divider 2-63, fps =~ 60 / val. Must be a multiple of 3 on
42
		the 7302, so one of 3, 6, 9, ..., except when between 6 and 12?
43 44 45 46
   -/0x0f	Master gain 1-245, low value = high gain
   0x10/-	Master gain 0-31
   -/0x10	Another gain 0-15, limited influence (1-2x gain I guess)
   0x21		Bitfield: 0-1 unused, 2-3 vflip/hflip, 4-5 unknown, 6-7 unused
47 48 49
   -/0x27	Seems to toggle various gains on / off, Setting bit 7 seems to
		completely disable the analog amplification block. Set to 0x68
		for max gain, 0x14 for minimal gain.
50 51
*/

52 53 54 55 56 57 58 59
#define MODULE_NAME "pac7311"

#include "gspca.h"

MODULE_AUTHOR("Thomas Kaiser thomas@kaiser-linux.li");
MODULE_DESCRIPTION("Pixart PAC7311");
MODULE_LICENSE("GPL");

60
/* specific webcam descriptor for pac7311 */
61 62 63 64
struct sd {
	struct gspca_dev gspca_dev;		/* !! must be the first item */

	unsigned char contrast;
65 66
	unsigned char gain;
	unsigned char exposure;
67
	unsigned char autogain;
68 69
	__u8 hflip;
	__u8 vflip;
70

71 72 73 74
	u8 sof_read;
	u8 autogain_ignore_frames;

	atomic_t avg_lum;
75 76 77 78 79 80 81
};

/* V4L2 controls supported by the driver */
static int sd_setcontrast(struct gspca_dev *gspca_dev, __s32 val);
static int sd_getcontrast(struct gspca_dev *gspca_dev, __s32 *val);
static int sd_setautogain(struct gspca_dev *gspca_dev, __s32 val);
static int sd_getautogain(struct gspca_dev *gspca_dev, __s32 *val);
82 83 84 85
static int sd_sethflip(struct gspca_dev *gspca_dev, __s32 val);
static int sd_gethflip(struct gspca_dev *gspca_dev, __s32 *val);
static int sd_setvflip(struct gspca_dev *gspca_dev, __s32 val);
static int sd_getvflip(struct gspca_dev *gspca_dev, __s32 *val);
86 87 88 89
static int sd_setgain(struct gspca_dev *gspca_dev, __s32 val);
static int sd_getgain(struct gspca_dev *gspca_dev, __s32 *val);
static int sd_setexposure(struct gspca_dev *gspca_dev, __s32 val);
static int sd_getexposure(struct gspca_dev *gspca_dev, __s32 *val);
90 91

static struct ctrl sd_ctrls[] = {
92
/* This control is for both the 7302 and the 7311 */
93 94 95 96 97 98
	{
	    {
		.id      = V4L2_CID_CONTRAST,
		.type    = V4L2_CTRL_TYPE_INTEGER,
		.name    = "Contrast",
		.minimum = 0,
99 100
#define CONTRAST_MAX 255
		.maximum = CONTRAST_MAX,
101
		.step    = 1,
102
#define CONTRAST_DEF 127
103
		.default_value = CONTRAST_DEF,
104 105 106 107
	    },
	    .set = sd_setcontrast,
	    .get = sd_getcontrast,
	},
108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140
/* All controls below are for both the 7302 and the 7311 */
	{
	    {
		.id      = V4L2_CID_GAIN,
		.type    = V4L2_CTRL_TYPE_INTEGER,
		.name    = "Gain",
		.minimum = 0,
#define GAIN_MAX 255
		.maximum = GAIN_MAX,
		.step    = 1,
#define GAIN_DEF 127
#define GAIN_KNEE 255 /* Gain seems to cause little noise on the pac73xx */
		.default_value = GAIN_DEF,
	    },
	    .set = sd_setgain,
	    .get = sd_getgain,
	},
	{
	    {
		.id      = V4L2_CID_EXPOSURE,
		.type    = V4L2_CTRL_TYPE_INTEGER,
		.name    = "Exposure",
		.minimum = 0,
#define EXPOSURE_MAX 255
		.maximum = EXPOSURE_MAX,
		.step    = 1,
#define EXPOSURE_DEF  16 /*  32 ms / 30 fps */
#define EXPOSURE_KNEE 50 /* 100 ms / 10 fps */
		.default_value = EXPOSURE_DEF,
	    },
	    .set = sd_setexposure,
	    .get = sd_getexposure,
	},
141 142 143 144 145 146 147 148
	{
	    {
		.id      = V4L2_CID_AUTOGAIN,
		.type    = V4L2_CTRL_TYPE_BOOLEAN,
		.name    = "Auto Gain",
		.minimum = 0,
		.maximum = 1,
		.step    = 1,
149 150
#define AUTOGAIN_DEF 1
		.default_value = AUTOGAIN_DEF,
151 152 153 154
	    },
	    .set = sd_setautogain,
	    .get = sd_getautogain,
	},
155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182
	{
	    {
		.id      = V4L2_CID_HFLIP,
		.type    = V4L2_CTRL_TYPE_BOOLEAN,
		.name    = "Mirror",
		.minimum = 0,
		.maximum = 1,
		.step    = 1,
#define HFLIP_DEF 0
		.default_value = HFLIP_DEF,
	    },
	    .set = sd_sethflip,
	    .get = sd_gethflip,
	},
	{
	    {
		.id      = V4L2_CID_VFLIP,
		.type    = V4L2_CTRL_TYPE_BOOLEAN,
		.name    = "Vflip",
		.minimum = 0,
		.maximum = 1,
		.step    = 1,
#define VFLIP_DEF 0
		.default_value = VFLIP_DEF,
	    },
	    .set = sd_setvflip,
	    .get = sd_getvflip,
	},
183 184
};

185
static const struct v4l2_pix_format vga_mode[] = {
186
	{160, 120, V4L2_PIX_FMT_PJPG, V4L2_FIELD_NONE,
187 188 189 190
		.bytesperline = 160,
		.sizeimage = 160 * 120 * 3 / 8 + 590,
		.colorspace = V4L2_COLORSPACE_JPEG,
		.priv = 2},
191
	{320, 240, V4L2_PIX_FMT_PJPG, V4L2_FIELD_NONE,
192 193 194 195
		.bytesperline = 320,
		.sizeimage = 320 * 240 * 3 / 8 + 590,
		.colorspace = V4L2_COLORSPACE_JPEG,
		.priv = 1},
196
	{640, 480, V4L2_PIX_FMT_PJPG, V4L2_FIELD_NONE,
197 198 199 200
		.bytesperline = 640,
		.sizeimage = 640 * 480 * 3 / 8 + 590,
		.colorspace = V4L2_COLORSPACE_JPEG,
		.priv = 0},
201 202
};

203 204 205 206
#define LOAD_PAGE3		255
#define LOAD_PAGE4		254
#define END_OF_SEQUENCE		0

207
/* pac 7311 */
208
static const __u8 init_7311[] = {
209 210 211
	0x78, 0x40,	/* Bit_0=start stream, Bit_6=LED */
	0x78, 0x40,	/* Bit_0=start stream, Bit_6=LED */
	0x78, 0x44,	/* Bit_0=start stream, Bit_6=LED */
212 213 214 215 216 217 218 219 220 221 222
	0xff, 0x04,
	0x27, 0x80,
	0x28, 0xca,
	0x29, 0x53,
	0x2a, 0x0e,
	0xff, 0x01,
	0x3e, 0x20,
};

static const __u8 start_7311[] = {
/*	index, len, [value]* */
223 224
	0xff, 1,	0x01,		/* page 1 */
	0x02, 43,	0x48, 0x0a, 0x40, 0x08, 0x00, 0x00, 0x08, 0x00,
225 226 227 228 229
			0x06, 0xff, 0x11, 0xff, 0x5a, 0x30, 0x90, 0x4c,
			0x00, 0x07, 0x00, 0x0a, 0x10, 0x00, 0xa0, 0x10,
			0x02, 0x00, 0x00, 0x00, 0x00, 0x0b, 0x01, 0x00,
			0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
			0x00, 0x00, 0x00,
230
	0x3e, 42,	0x00, 0x00, 0x78, 0x52, 0x4a, 0x52, 0x78, 0x6e,
231 232 233 234 235 236 237 238 239 240 241 242 243
			0x48, 0x46, 0x48, 0x6e, 0x5f, 0x49, 0x42, 0x49,
			0x5f, 0x5f, 0x49, 0x42, 0x49, 0x5f, 0x6e, 0x48,
			0x46, 0x48, 0x6e, 0x78, 0x52, 0x4a, 0x52, 0x78,
			0x00, 0x00, 0x09, 0x1b, 0x34, 0x49, 0x5c, 0x9b,
			0xd0, 0xff,
	0x78, 6,	0x44, 0x00, 0xf2, 0x01, 0x01, 0x80,
	0x7f, 18,	0x2a, 0x1c, 0x00, 0xc8, 0x02, 0x58, 0x03, 0x84,
			0x12, 0x00, 0x1a, 0x04, 0x08, 0x0c, 0x10, 0x14,
			0x18, 0x20,
	0x96, 3,	0x01, 0x08, 0x04,
	0xa0, 4,	0x44, 0x44, 0x44, 0x04,
	0xf0, 13,	0x01, 0x00, 0x00, 0x00, 0x22, 0x00, 0x20, 0x00,
			0x3f, 0x00, 0x0a, 0x01, 0x00,
244
	0xff, 1,	0x04,		/* page 4 */
245
	0, LOAD_PAGE4,			/* load the page 4 */
246
	0x11, 1,	0x01,
247
	0, END_OF_SEQUENCE		/* end of sequence */
248 249
};

250
#define SKIP		0xaa
251
/* page 4 - the value SKIP says skip the index - see reg_w_page() */
252
static const __u8 page4_7311[] = {
253 254 255 256 257
	SKIP, SKIP, 0x04, 0x54, 0x07, 0x2b, 0x09, 0x0f,
	0x09, 0x00, SKIP, SKIP, 0x07, 0x00, 0x00, 0x62,
	0x08, SKIP, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00,
	0x00, 0x00, 0x00, 0x03, 0xa0, 0x01, 0xf4, SKIP,
	SKIP, 0x00, 0x08, SKIP, 0x03, SKIP, 0x00, 0x68,
258 259 260 261
	0xca, 0x10, 0x06, 0x78, 0x00, 0x00, 0x00, 0x00,
	0x23, 0x28, 0x04, 0x11, 0x00, 0x00
};

262
static int reg_w_buf(struct gspca_dev *gspca_dev,
263 264
		  __u8 index,
		  const char *buffer, int len)
265
{
266 267
	int ret;

268
	memcpy(gspca_dev->usb_buf, buffer, len);
269
	ret = usb_control_msg(gspca_dev->dev,
270
			usb_sndctrlpipe(gspca_dev->dev, 0),
271
			1,		/* request */
272
			USB_DIR_OUT | USB_TYPE_VENDOR | USB_RECIP_DEVICE,
273
			0,		/* value */
274
			index, gspca_dev->usb_buf, len,
275
			500);
276 277 278 279
	if (ret < 0)
		PDEBUG(D_ERR, "reg_w_buf(): "
		"Failed to write registers to index 0x%x, error %i",
		index, ret);
280
	return ret;
281 282 283
}


284
static int reg_w(struct gspca_dev *gspca_dev,
285
		  __u8 index,
286
		  __u8 value)
287
{
288 289
	int ret;

290
	gspca_dev->usb_buf[0] = value;
291
	ret = usb_control_msg(gspca_dev->dev,
292
			usb_sndctrlpipe(gspca_dev->dev, 0),
293 294
			0,			/* request */
			USB_DIR_OUT | USB_TYPE_VENDOR | USB_RECIP_DEVICE,
295
			0, index, gspca_dev->usb_buf, 1,
296
			500);
297 298 299 300
	if (ret < 0)
		PDEBUG(D_ERR, "reg_w(): "
		"Failed to write register to index 0x%x, value 0x%x, error %i",
		index, value, ret);
301
	return ret;
302 303
}

304
static int reg_w_seq(struct gspca_dev *gspca_dev,
305 306
		const __u8 *seq, int len)
{
307
	int ret = 0;
308
	while (--len >= 0) {
309 310
		if (0 <= ret)
			ret = reg_w(gspca_dev, seq[0], seq[1]);
311 312
		seq += 2;
	}
313
	return ret;
314 315 316
}

/* load the beginning of a page */
317
static int reg_w_page(struct gspca_dev *gspca_dev,
318 319 320
			const __u8 *page, int len)
{
	int index;
321
	int ret = 0;
322 323

	for (index = 0; index < len; index++) {
324
		if (page[index] == SKIP)		/* skip this index */
325 326
			continue;
		gspca_dev->usb_buf[0] = page[index];
327
		ret = usb_control_msg(gspca_dev->dev,
328 329 330 331 332
				usb_sndctrlpipe(gspca_dev->dev, 0),
				0,			/* request */
			USB_DIR_OUT | USB_TYPE_VENDOR | USB_RECIP_DEVICE,
				0, index, gspca_dev->usb_buf, 1,
				500);
333
		if (ret < 0) {
334 335 336 337
			PDEBUG(D_ERR, "reg_w_page(): "
			"Failed to write register to index 0x%x, "
			"value 0x%x, error %i",
			index, page[index], ret);
338 339
			break;
		}
340
	}
341
	return ret;
342 343 344
}

/* output a variable sequence */
345
static int reg_w_var(struct gspca_dev *gspca_dev,
346 347 348
			const __u8 *seq,
			const __u8 *page3, unsigned int page3_len,
			const __u8 *page4, unsigned int page4_len)
349 350
{
	int index, len;
351
	int ret = 0;
352 353 354 355 356

	for (;;) {
		index = *seq++;
		len = *seq++;
		switch (len) {
357
		case END_OF_SEQUENCE:
358
			return ret;
359
		case LOAD_PAGE4:
360
			ret = reg_w_page(gspca_dev, page4, page4_len);
361
			break;
362
		case LOAD_PAGE3:
363
			ret = reg_w_page(gspca_dev, page3, page3_len);
364 365
			break;
		default:
366
			if (len > USB_BUF_SZ) {
367 368
				PDEBUG(D_ERR|D_STREAM,
					"Incorrect variable sequence");
369
				return -EINVAL;
370 371 372
			}
			while (len > 0) {
				if (len < 8) {
373 374 375 376
					ret = reg_w_buf(gspca_dev,
						index, seq, len);
					if (ret < 0)
						return ret;
377 378 379
					seq += len;
					break;
				}
380
				ret = reg_w_buf(gspca_dev, index, seq, 8);
381 382 383 384 385
				seq += 8;
				index += 8;
				len -= 8;
			}
		}
386 387
		if (ret < 0)
			return ret;
388 389 390 391
	}
	/* not reached */
}

392
/* this function is called at probe time for pac7311 */
393 394 395 396 397 398 399
static int sd_config(struct gspca_dev *gspca_dev,
			const struct usb_device_id *id)
{
	struct sd *sd = (struct sd *) gspca_dev;
	struct cam *cam;

	cam = &gspca_dev->cam;
400

401 402 403
	PDEBUG(D_CONF, "Find Sensor PAC7311");
	cam->cam_mode = vga_mode;
	cam->nmodes = ARRAY_SIZE(vga_mode);
404

405
	sd->contrast = CONTRAST_DEF;
406 407
	sd->gain = GAIN_DEF;
	sd->exposure = EXPOSURE_DEF;
408
	sd->autogain = AUTOGAIN_DEF;
409 410
	sd->hflip = HFLIP_DEF;
	sd->vflip = VFLIP_DEF;
411 412 413
	return 0;
}

414
/* This function is used by pac7311 only */
415
static int setcontrast(struct gspca_dev *gspca_dev)
416 417
{
	struct sd *sd = (struct sd *) gspca_dev;
418
	int ret;
419

420 421 422
	ret = reg_w(gspca_dev, 0xff, 0x04);
	if (0 <= ret)
		ret = reg_w(gspca_dev, 0x10, sd->contrast >> 4);
423
	/* load registers to sensor (Bit 0, auto clear) */
424 425 426
	if (0 <= ret)
		ret = reg_w(gspca_dev, 0x11, 0x01);
	return ret;
427 428
}

429
static int setgain(struct gspca_dev *gspca_dev)
430 431
{
	struct sd *sd = (struct sd *) gspca_dev;
432
	int gain = GAIN_MAX - sd->gain;
433
	int ret;
434 435 436 437 438

	if (gain < 1)
		gain = 1;
	else if (gain > 245)
		gain = 245;
439 440 441 442 443
	ret = reg_w(gspca_dev, 0xff, 0x04);		/* page 4 */
	if (0 <= ret)
		ret = reg_w(gspca_dev, 0x0e, 0x00);
	if (0 <= ret)
		ret = reg_w(gspca_dev, 0x0f, gain);
444 445

	/* load registers to sensor (Bit 0, auto clear) */
446 447 448
	if (0 <= ret)
		ret = reg_w(gspca_dev, 0x11, 0x01);
	return ret;
449 450
}

451
static int setexposure(struct gspca_dev *gspca_dev)
452 453
{
	struct sd *sd = (struct sd *) gspca_dev;
454
	int ret;
455 456 457 458 459 460 461 462 463 464
	__u8 reg;

	/* register 2 of frame 3/4 contains the clock divider configuring the
	   no fps according to the formula: 60 / reg. sd->exposure is the
	   desired exposure time in ms. */
	reg = 120 * sd->exposure / 1000;
	if (reg < 2)
		reg = 2;
	else if (reg > 63)
		reg = 63;
465

466 467 468
	ret = reg_w(gspca_dev, 0xff, 0x04);		/* page 4 */
	if (0 <= ret)
		ret = reg_w(gspca_dev, 0x02, reg);
469 470
	/* Page 1 register 8 must always be 0x08 except when not in
	   640x480 mode and Page3/4 reg 2 <= 3 then it must be 9 */
471 472
	if (0 <= ret)
		ret = reg_w(gspca_dev, 0xff, 0x01);
473
	if (gspca_dev->cam.cam_mode[(int)gspca_dev->curr_mode].priv &&
474 475 476 477 478 479 480
			reg <= 3) {
		if (0 <= ret)
			ret = reg_w(gspca_dev, 0x08, 0x09);
	} else {
		if (0 <= ret)
			ret = reg_w(gspca_dev, 0x08, 0x08);
	}
481

482
	/* load registers to sensor (Bit 0, auto clear) */
483 484 485
	if (0 <= ret)
		ret = reg_w(gspca_dev, 0x11, 0x01);
	return ret;
486 487
}

488
static int sethvflip(struct gspca_dev *gspca_dev)
489 490
{
	struct sd *sd = (struct sd *) gspca_dev;
491
	int ret;
492 493
	__u8 data;

494
	ret = reg_w(gspca_dev, 0xff, 0x04);		/* page 4 */
495
	data = (sd->hflip ? 0x04 : 0x00) | (sd->vflip ? 0x08 : 0x00);
496 497
	if (0 <= ret)
		ret = reg_w(gspca_dev, 0x21, data);
498
	/* load registers to sensor (Bit 0, auto clear) */
499 500 501
	if (0 <= ret)
		ret = reg_w(gspca_dev, 0x11, 0x01);
	return ret;
502 503
}

504
/* this function is called at probe and resume time for pac7311 */
505
static int sd_init(struct gspca_dev *gspca_dev)
506
{
507
	return reg_w_seq(gspca_dev, init_7311, sizeof(init_7311)/2);
508 509
}

510
static int sd_start(struct gspca_dev *gspca_dev)
511
{
512
	struct sd *sd = (struct sd *) gspca_dev;
513
	int ret;
514

515
	sd->sof_read = 0;
516

517
	ret = reg_w_var(gspca_dev, start_7311,
518 519
		NULL, 0,
		page4_7311, sizeof(page4_7311));
520 521 522 523 524 525 526 527
	if (0 <= ret)
		ret = setcontrast(gspca_dev);
	if (0 <= ret)
		ret = setgain(gspca_dev);
	if (0 <= ret)
		ret = setexposure(gspca_dev);
	if (0 <= ret)
		ret = sethvflip(gspca_dev);
528 529

	/* set correct resolution */
530
	switch (gspca_dev->cam.cam_mode[(int) gspca_dev->curr_mode].priv) {
531
	case 2:					/* 160x120 pac7311 */
532 533 534 535 536 537
		if (0 <= ret)
			ret = reg_w(gspca_dev, 0xff, 0x01);
		if (0 <= ret)
			ret = reg_w(gspca_dev, 0x17, 0x20);
		if (0 <= ret)
			ret = reg_w(gspca_dev, 0x87, 0x10);
538
		break;
539
	case 1:					/* 320x240 pac7311 */
540 541 542 543 544 545
		if (0 <= ret)
			ret = reg_w(gspca_dev, 0xff, 0x01);
		if (0 <= ret)
			ret = reg_w(gspca_dev, 0x17, 0x30);
		if (0 <= ret)
			ret = reg_w(gspca_dev, 0x87, 0x11);
546 547
		break;
	case 0:					/* 640x480 */
548 549 550 551 552 553
		if (0 <= ret)
			ret = reg_w(gspca_dev, 0xff, 0x01);
		if (0 <= ret)
			ret = reg_w(gspca_dev, 0x17, 0x00);
		if (0 <= ret)
			ret = reg_w(gspca_dev, 0x87, 0x12);
554 555 556
		break;
	}

557 558 559
	sd->sof_read = 0;
	sd->autogain_ignore_frames = 0;
	atomic_set(&sd->avg_lum, -1);
560 561

	/* start stream */
562 563 564 565
	if (0 <= ret)
		ret = reg_w(gspca_dev, 0xff, 0x01);
	if (0 <= ret)
		ret = reg_w(gspca_dev, 0x78, 0x05);
566

567
	return ret;
568 569 570 571
}

static void sd_stopN(struct gspca_dev *gspca_dev)
{
572 573 574 575 576 577 578 579 580 581 582 583 584 585 586 587 588 589 590 591 592
	int ret;

	ret = reg_w(gspca_dev, 0xff, 0x04);
	if (0 <= ret)
		ret = reg_w(gspca_dev, 0x27, 0x80);
	if (0 <= ret)
		ret = reg_w(gspca_dev, 0x28, 0xca);
	if (0 <= ret)
		ret = reg_w(gspca_dev, 0x29, 0x53);
	if (0 <= ret)
		ret = reg_w(gspca_dev, 0x2a, 0x0e);
	if (0 <= ret)
		ret = reg_w(gspca_dev, 0xff, 0x01);
	if (0 <= ret)
		ret = reg_w(gspca_dev, 0x3e, 0x20);
	if (0 <= ret)
		ret = reg_w(gspca_dev, 0x78, 0x44); /* Bit_0=start stream, Bit_6=LED */
	if (0 <= ret)
		ret = reg_w(gspca_dev, 0x78, 0x44); /* Bit_0=start stream, Bit_6=LED */
	if (0 <= ret)
		ret = reg_w(gspca_dev, 0x78, 0x44); /* Bit_0=start stream, Bit_6=LED */
593 594
}

595
/* called on streamoff with alt 0 and on disconnect for 7311 */
596 597 598 599
static void sd_stop0(struct gspca_dev *gspca_dev)
{
}

600 601 602
/* Include pac common sof detection functions */
#include "pac_common.h"

603
static void do_autogain(struct gspca_dev *gspca_dev)
604
{
605 606
	struct sd *sd = (struct sd *) gspca_dev;
	int avg_lum = atomic_read(&sd->avg_lum);
607
	int desired_lum, deadzone;
608 609 610 611

	if (avg_lum == -1)
		return;

612 613
	desired_lum = 200;
	deadzone = 20;
614 615 616 617

	if (sd->autogain_ignore_frames > 0)
		sd->autogain_ignore_frames--;
	else if (gspca_auto_gain_n_exposure(gspca_dev, avg_lum, desired_lum,
618
			deadzone, GAIN_KNEE, EXPOSURE_KNEE))
619
		sd->autogain_ignore_frames = PAC_AUTOGAIN_IGNORE_FRAMES;
620 621
}

622
/* JPEG header, part 1 */
623
static const unsigned char pac_jpeg_header1[] = {
624 625 626 627 628 629 630
  0xff, 0xd8,		/* SOI: Start of Image */

  0xff, 0xc0,		/* SOF0: Start of Frame (Baseline DCT) */
  0x00, 0x11,		/* length = 17 bytes (including this length field) */
  0x08			/* Precision: 8 */
  /* 2 bytes is placed here: number of image lines */
  /* 2 bytes is placed here: samples per line */
631 632
};

633
/* JPEG header, continued */
634
static const unsigned char pac_jpeg_header2[] = {
635 636 637 638 639 640 641 642 643 644 645 646 647
  0x03,			/* Number of image components: 3 */
  0x01, 0x21, 0x00,	/* ID=1, Subsampling 1x1, Quantization table: 0 */
  0x02, 0x11, 0x01,	/* ID=2, Subsampling 2x1, Quantization table: 1 */
  0x03, 0x11, 0x01,	/* ID=3, Subsampling 2x1, Quantization table: 1 */

  0xff, 0xda,		/* SOS: Start Of Scan */
  0x00, 0x0c,		/* length = 12 bytes (including this length field) */
  0x03,			/* number of components: 3 */
  0x01, 0x00,		/* selector 1, table 0x00 */
  0x02, 0x11,		/* selector 2, table 0x11 */
  0x03, 0x11,		/* selector 3, table 0x11 */
  0x00, 0x3f,		/* Spectral selection: 0 .. 63 */
  0x00			/* Successive approximation: 0 */
648 649
};

650 651 652 653 654 655
static void pac_start_frame(struct gspca_dev *gspca_dev,
		struct gspca_frame *frame,
		__u16 lines, __u16 samples_per_line)
{
	unsigned char tmpbuf[4];

656
	gspca_frame_add(gspca_dev, FIRST_PACKET,
657 658 659 660 661 662 663
		pac_jpeg_header1, sizeof(pac_jpeg_header1));

	tmpbuf[0] = lines >> 8;
	tmpbuf[1] = lines & 0xff;
	tmpbuf[2] = samples_per_line >> 8;
	tmpbuf[3] = samples_per_line & 0xff;

664
	gspca_frame_add(gspca_dev, INTER_PACKET,
665
		tmpbuf, sizeof(tmpbuf));
666
	gspca_frame_add(gspca_dev, INTER_PACKET,
667 668 669
		pac_jpeg_header2, sizeof(pac_jpeg_header2));
}

670
/* this function is run at interrupt level */
671
static void sd_pkt_scan(struct gspca_dev *gspca_dev,
672
			u8 *data,			/* isoc packet */
673 674 675
			int len)			/* iso packet length */
{
	struct sd *sd = (struct sd *) gspca_dev;
676
	unsigned char *sof;
677
	struct gspca_frame *frame;
678

679
	sof = pac_find_sof(&sd->sof_read, data, len);
680 681 682
	if (sof) {
		int n, lum_offset, footer_length;

683 684 685 686 687 688
		frame = gspca_get_i_frame(gspca_dev);
		if (frame == NULL) {
			gspca_dev->last_packet_type = DISCARD_PACKET;
			return;
		}

689 690 691 692 693 694
		/* 6 bytes after the FF D9 EOF marker a number of lumination
		   bytes are send corresponding to different parts of the
		   image, the 14th and 15th byte after the EOF seem to
		   correspond to the center of the image */
		lum_offset = 24 + sizeof pac_sof_marker;
		footer_length = 26;
695 696 697 698 699 700 701

		/* Finish decoding current frame */
		n = (sof - data) - (footer_length + sizeof pac_sof_marker);
		if (n < 0) {
			frame->data_end += n;
			n = 0;
		}
702
		gspca_frame_add(gspca_dev, INTER_PACKET,
703 704 705 706
					data, n);
		if (gspca_dev->last_packet_type != DISCARD_PACKET &&
				frame->data_end[-2] == 0xff &&
				frame->data_end[-1] == 0xd9)
707
			gspca_frame_add(gspca_dev, LAST_PACKET,
708 709 710 711 712 713 714 715
						NULL, 0);

		n = sof - data;
		len -= n;
		data = sof;

		/* Get average lumination */
		if (gspca_dev->last_packet_type == LAST_PACKET &&
716 717
				n >= lum_offset)
			atomic_set(&sd->avg_lum, data[-lum_offset] +
718
						data[-lum_offset + 1]);
719
		else
720 721 722
			atomic_set(&sd->avg_lum, -1);

		/* Start the new frame with the jpeg header */
723 724
		pac_start_frame(gspca_dev, frame,
			gspca_dev->height, gspca_dev->width);
725
	}
726
	gspca_frame_add(gspca_dev, INTER_PACKET, data, len);
727 728 729 730 731 732 733
}

static int sd_setcontrast(struct gspca_dev *gspca_dev, __s32 val)
{
	struct sd *sd = (struct sd *) gspca_dev;

	sd->contrast = val;
734
	if (gspca_dev->streaming) {
735
		setcontrast(gspca_dev);
736
	}
737 738 739 740 741 742 743 744 745 746 747
	return 0;
}

static int sd_getcontrast(struct gspca_dev *gspca_dev, __s32 *val)
{
	struct sd *sd = (struct sd *) gspca_dev;

	*val = sd->contrast;
	return 0;
}

748 749 750 751 752 753 754 755 756 757 758 759 760 761 762 763 764 765 766 767 768 769 770 771 772 773 774 775 776 777 778 779 780 781 782 783
static int sd_setgain(struct gspca_dev *gspca_dev, __s32 val)
{
	struct sd *sd = (struct sd *) gspca_dev;

	sd->gain = val;
	if (gspca_dev->streaming)
		setgain(gspca_dev);
	return 0;
}

static int sd_getgain(struct gspca_dev *gspca_dev, __s32 *val)
{
	struct sd *sd = (struct sd *) gspca_dev;

	*val = sd->gain;
	return 0;
}

static int sd_setexposure(struct gspca_dev *gspca_dev, __s32 val)
{
	struct sd *sd = (struct sd *) gspca_dev;

	sd->exposure = val;
	if (gspca_dev->streaming)
		setexposure(gspca_dev);
	return 0;
}

static int sd_getexposure(struct gspca_dev *gspca_dev, __s32 *val)
{
	struct sd *sd = (struct sd *) gspca_dev;

	*val = sd->exposure;
	return 0;
}

784 785 786 787 788
static int sd_setautogain(struct gspca_dev *gspca_dev, __s32 val)
{
	struct sd *sd = (struct sd *) gspca_dev;

	sd->autogain = val;
789 790 791 792 793 794 795 796 797 798 799 800 801 802
	/* when switching to autogain set defaults to make sure
	   we are on a valid point of the autogain gain /
	   exposure knee graph, and give this change time to
	   take effect before doing autogain. */
	if (sd->autogain) {
		sd->exposure = EXPOSURE_DEF;
		sd->gain = GAIN_DEF;
		if (gspca_dev->streaming) {
			sd->autogain_ignore_frames =
				PAC_AUTOGAIN_IGNORE_FRAMES;
			setexposure(gspca_dev);
			setgain(gspca_dev);
		}
	}
803

804 805 806 807 808 809 810 811 812 813 814
	return 0;
}

static int sd_getautogain(struct gspca_dev *gspca_dev, __s32 *val)
{
	struct sd *sd = (struct sd *) gspca_dev;

	*val = sd->autogain;
	return 0;
}

815 816 817 818 819 820 821 822 823 824 825 826 827 828 829 830 831 832 833 834 835 836 837 838 839 840 841 842 843 844 845 846 847 848 849 850
static int sd_sethflip(struct gspca_dev *gspca_dev, __s32 val)
{
	struct sd *sd = (struct sd *) gspca_dev;

	sd->hflip = val;
	if (gspca_dev->streaming)
		sethvflip(gspca_dev);
	return 0;
}

static int sd_gethflip(struct gspca_dev *gspca_dev, __s32 *val)
{
	struct sd *sd = (struct sd *) gspca_dev;

	*val = sd->hflip;
	return 0;
}

static int sd_setvflip(struct gspca_dev *gspca_dev, __s32 val)
{
	struct sd *sd = (struct sd *) gspca_dev;

	sd->vflip = val;
	if (gspca_dev->streaming)
		sethvflip(gspca_dev);
	return 0;
}

static int sd_getvflip(struct gspca_dev *gspca_dev, __s32 *val)
{
	struct sd *sd = (struct sd *) gspca_dev;

	*val = sd->vflip;
	return 0;
}

851
/* sub-driver description for pac7311 */
852 853 854 855 856
static struct sd_desc sd_desc = {
	.name = MODULE_NAME,
	.ctrls = sd_ctrls,
	.nctrls = ARRAY_SIZE(sd_ctrls),
	.config = sd_config,
857
	.init = sd_init,
858 859 860 861
	.start = sd_start,
	.stopN = sd_stopN,
	.stop0 = sd_stop0,
	.pkt_scan = sd_pkt_scan,
862
	.dq_callback = do_autogain,
863 864 865
};

/* -- module initialisation -- */
866
static const struct usb_device_id device_table[] __devinitconst = {
867 868 869 870 871 872
	{USB_DEVICE(0x093a, 0x2600)},
	{USB_DEVICE(0x093a, 0x2601)},
	{USB_DEVICE(0x093a, 0x2603)},
	{USB_DEVICE(0x093a, 0x2608)},
	{USB_DEVICE(0x093a, 0x260e)},
	{USB_DEVICE(0x093a, 0x260f)},
873 874 875 876 877
	{}
};
MODULE_DEVICE_TABLE(usb, device_table);

/* -- device connect -- */
878
static int __devinit sd_probe(struct usb_interface *intf,
879 880 881 882 883 884 885 886 887 888 889
			const struct usb_device_id *id)
{
	return gspca_dev_probe(intf, id, &sd_desc, sizeof(struct sd),
				THIS_MODULE);
}

static struct usb_driver sd_driver = {
	.name = MODULE_NAME,
	.id_table = device_table,
	.probe = sd_probe,
	.disconnect = gspca_disconnect,
890 891 892 893
#ifdef CONFIG_PM
	.suspend = gspca_suspend,
	.resume = gspca_resume,
#endif
894 895 896 897 898
};

/* -- module insert / remove -- */
static int __init sd_mod_init(void)
{
899 900 901
	int ret;
	ret = usb_register(&sd_driver);
	if (ret < 0)
902
		return ret;
903
	PDEBUG(D_PROBE, "registered");
904 905 906 907 908 909 910 911 912 913
	return 0;
}
static void __exit sd_mod_exit(void)
{
	usb_deregister(&sd_driver);
	PDEBUG(D_PROBE, "deregistered");
}

module_init(sd_mod_init);
module_exit(sd_mod_exit);