OpenCores
URL https://opencores.org/ocsvn/or1k/or1k/trunk

Subversion Repositories or1k

[/] [or1k/] [trunk/] [linux/] [linux-2.4/] [drivers/] [usb/] [ov511.c] - Blame information for rev 1765

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 1275 phoenix
/*
2
 * OmniVision OV511 Camera-to-USB Bridge Driver
3
 *
4
 * Copyright (c) 1999-2003 Mark W. McClelland
5
 * Original decompression code Copyright 1998-2000 OmniVision Technologies
6
 * Many improvements by Bret Wallach <bwallac1@san.rr.com>
7
 * Color fixes by by Orion Sky Lawlor <olawlor@acm.org> (2/26/2000)
8
 * Snapshot code by Kevin Moore
9
 * OV7620 fixes by Charl P. Botha <cpbotha@ieee.org>
10
 * Changes by Claudio Matsuoka <claudio@conectiva.com>
11
 * Original SAA7111A code by Dave Perks <dperks@ibm.net>
12
 * URB error messages from pwc driver by Nemosoft
13
 * generic_ioctl() code from videodev.c by Gerd Knorr and Alan Cox
14
 * Memory management (rvmalloc) code from bttv driver, by Gerd Knorr and others
15
 *
16
 * Based on the Linux CPiA driver written by Peter Pregler,
17
 * Scott J. Bertin and Johannes Erdfelt.
18
 *
19
 * Please see the file: linux/Documentation/usb/ov511.txt
20
 * and the website at:  http://alpha.dyndns.org/ov511
21
 * for more info.
22
 *
23
 * This program is free software; you can redistribute it and/or modify it
24
 * under the terms of the GNU General Public License as published by the
25
 * Free Software Foundation; either version 2 of the License, or (at your
26
 * option) any later version.
27
 *
28
 * This program is distributed in the hope that it will be useful, but
29
 * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
30
 * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
31
 * for more details.
32
 *
33
 * You should have received a copy of the GNU General Public License
34
 * along with this program; if not, write to the Free Software Foundation,
35
 * Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
36
 */
37
 
38
#include <linux/config.h>
39
#include <linux/version.h>
40
#include <linux/module.h>
41
#include <linux/init.h>
42
#include <linux/fs.h>
43
#include <linux/vmalloc.h>
44
#include <linux/slab.h>
45
#include <linux/proc_fs.h>
46
#include <linux/ctype.h>
47
#include <linux/pagemap.h>
48
#include <asm/io.h>
49
#include <asm/semaphore.h>
50
#include <asm/processor.h>
51
#include <linux/wrapper.h>
52
#include <linux/mm.h>
53
 
54
#if defined (__i386__)
55
        #include <asm/cpufeature.h>
56
#endif
57
 
58
#include "ov511.h"
59
 
60
/*
61
 * Version Information
62
 */
63
#define DRIVER_VERSION "v1.63 for Linux 2.4"
64
#define EMAIL "mark@alpha.dyndns.org"
65
#define DRIVER_AUTHOR "Mark McClelland <mark@alpha.dyndns.org> & Bret Wallach \
66
        & Orion Sky Lawlor <olawlor@acm.org> & Kevin Moore & Charl P. Botha \
67
        <cpbotha@ieee.org> & Claudio Matsuoka <claudio@conectiva.com>"
68
#define DRIVER_DESC "ov511 USB Camera Driver"
69
 
70
#define OV511_I2C_RETRIES 3
71
#define ENABLE_Y_QUANTABLE 1
72
#define ENABLE_UV_QUANTABLE 1
73
 
74
#define OV511_MAX_UNIT_VIDEO 16
75
 
76
/* Pixel count * 3 bytes for RGB */
77
#define MAX_FRAME_SIZE(w, h) ((w) * (h) * 3)
78
 
79
#define MAX_DATA_SIZE(w, h) (MAX_FRAME_SIZE(w, h) + sizeof(struct timeval))
80
 
81
/* Max size * bytes per YUV420 pixel (1.5) + one extra isoc frame for safety */
82
#define MAX_RAW_DATA_SIZE(w, h) ((w) * (h) * 3 / 2 + 1024)
83
 
84
#define FATAL_ERROR(rc) ((rc) < 0 && (rc) != -EPERM)
85
 
86
/**********************************************************************
87
 * Module Parameters
88
 * (See ov511.txt for detailed descriptions of these)
89
 **********************************************************************/
90
 
91
/* These variables (and all static globals) default to zero */
92
static int autobright           = 1;
93
static int autogain             = 1;
94
static int autoexp              = 1;
95
static int debug;
96
static int snapshot;
97
static int fix_rgb_offset;
98
static int force_rgb;
99
static int cams                 = 1;
100
static int compress;
101
static int testpat;
102
static int dumppix;
103
static int led                  = 1;
104
static int dump_bridge;
105
static int dump_sensor;
106
static int printph;
107
static int phy                  = 0x1f;
108
static int phuv                 = 0x05;
109
static int pvy                  = 0x06;
110
static int pvuv                 = 0x06;
111
static int qhy                  = 0x14;
112
static int qhuv                 = 0x03;
113
static int qvy                  = 0x04;
114
static int qvuv                 = 0x04;
115
static int lightfreq;
116
static int bandingfilter;
117
static int clockdiv             = -1;
118
static int packetsize           = -1;
119
static int framedrop            = -1;
120
static int fastset;
121
static int force_palette;
122
static int backlight;
123
static int unit_video[OV511_MAX_UNIT_VIDEO];
124
static int remove_zeros;
125
static int mirror;
126
static int ov518_color;
127
 
128
MODULE_PARM(autobright, "i");
129
MODULE_PARM_DESC(autobright, "Sensor automatically changes brightness");
130
MODULE_PARM(autogain, "i");
131
MODULE_PARM_DESC(autogain, "Sensor automatically changes gain");
132
MODULE_PARM(autoexp, "i");
133
MODULE_PARM_DESC(autoexp, "Sensor automatically changes exposure");
134
MODULE_PARM(debug, "i");
135
MODULE_PARM_DESC(debug,
136
  "Debug level: 0=none, 1=inits, 2=warning, 3=config, 4=functions, 5=max");
137
MODULE_PARM(snapshot, "i");
138
MODULE_PARM_DESC(snapshot, "Enable snapshot mode");
139
MODULE_PARM(fix_rgb_offset, "i");
140
MODULE_PARM_DESC(fix_rgb_offset,
141
  "Fix vertical misalignment of red and blue at 640x480");
142
MODULE_PARM(force_rgb, "i");
143
MODULE_PARM_DESC(force_rgb, "Read RGB instead of BGR");
144
MODULE_PARM(cams, "i");
145
MODULE_PARM_DESC(cams, "Number of simultaneous cameras");
146
MODULE_PARM(compress, "i");
147
MODULE_PARM_DESC(compress, "Turn on compression (not reliable yet)");
148
MODULE_PARM(testpat, "i");
149
MODULE_PARM_DESC(testpat,
150
  "Replace image with vertical bar testpattern (only partially working)");
151
MODULE_PARM(dumppix, "i");
152
MODULE_PARM_DESC(dumppix, "Dump raw pixel data");
153
MODULE_PARM(led, "i");
154
MODULE_PARM_DESC(led,
155
  "LED policy (OV511+ or later). 0=off, 1=on (default), 2=auto (on when open)");
156
MODULE_PARM(dump_bridge, "i");
157
MODULE_PARM_DESC(dump_bridge, "Dump the bridge registers");
158
MODULE_PARM(dump_sensor, "i");
159
MODULE_PARM_DESC(dump_sensor, "Dump the sensor registers");
160
MODULE_PARM(printph, "i");
161
MODULE_PARM_DESC(printph, "Print frame start/end headers");
162
MODULE_PARM(phy, "i");
163
MODULE_PARM_DESC(phy, "Prediction range (horiz. Y)");
164
MODULE_PARM(phuv, "i");
165
MODULE_PARM_DESC(phuv, "Prediction range (horiz. UV)");
166
MODULE_PARM(pvy, "i");
167
MODULE_PARM_DESC(pvy, "Prediction range (vert. Y)");
168
MODULE_PARM(pvuv, "i");
169
MODULE_PARM_DESC(pvuv, "Prediction range (vert. UV)");
170
MODULE_PARM(qhy, "i");
171
MODULE_PARM_DESC(qhy, "Quantization threshold (horiz. Y)");
172
MODULE_PARM(qhuv, "i");
173
MODULE_PARM_DESC(qhuv, "Quantization threshold (horiz. UV)");
174
MODULE_PARM(qvy, "i");
175
MODULE_PARM_DESC(qvy, "Quantization threshold (vert. Y)");
176
MODULE_PARM(qvuv, "i");
177
MODULE_PARM_DESC(qvuv, "Quantization threshold (vert. UV)");
178
MODULE_PARM(lightfreq, "i");
179
MODULE_PARM_DESC(lightfreq,
180
  "Light frequency. Set to 50 or 60 Hz, or zero for default settings");
181
MODULE_PARM(bandingfilter, "i");
182
MODULE_PARM_DESC(bandingfilter,
183
  "Enable banding filter (to reduce effects of fluorescent lighting)");
184
MODULE_PARM(clockdiv, "i");
185
MODULE_PARM_DESC(clockdiv, "Force pixel clock divisor to a specific value");
186
MODULE_PARM(packetsize, "i");
187
MODULE_PARM_DESC(packetsize, "Force a specific isoc packet size");
188
MODULE_PARM(framedrop, "i");
189
MODULE_PARM_DESC(framedrop, "Force a specific frame drop register setting");
190
MODULE_PARM(fastset, "i");
191
MODULE_PARM_DESC(fastset, "Allows picture settings to take effect immediately");
192
MODULE_PARM(force_palette, "i");
193
MODULE_PARM_DESC(force_palette, "Force the palette to a specific value");
194
MODULE_PARM(backlight, "i");
195
MODULE_PARM_DESC(backlight, "For objects that are lit from behind");
196
MODULE_PARM(unit_video, "1-" __MODULE_STRING(OV511_MAX_UNIT_VIDEO) "i");
197
MODULE_PARM_DESC(unit_video,
198
  "Force use of specific minor number(s). 0 is not allowed.");
199
MODULE_PARM(remove_zeros, "i");
200
MODULE_PARM_DESC(remove_zeros,
201
  "Remove zero-padding from uncompressed incoming data");
202
MODULE_PARM(mirror, "i");
203
MODULE_PARM_DESC(mirror, "Reverse image horizontally");
204
MODULE_PARM(ov518_color, "i");
205
MODULE_PARM_DESC(ov518_color, "Enable OV518 color (experimental)");
206
 
207
MODULE_AUTHOR(DRIVER_AUTHOR);
208
MODULE_DESCRIPTION(DRIVER_DESC);
209
MODULE_LICENSE("GPL");
210
 
211
/**********************************************************************
212
 * Miscellaneous Globals
213
 **********************************************************************/
214
 
215
static struct usb_driver ov511_driver;
216
 
217
static struct ov51x_decomp_ops *ov511_decomp_ops;
218
static struct ov51x_decomp_ops *ov511_mmx_decomp_ops;
219
static struct ov51x_decomp_ops *ov518_decomp_ops;
220
static struct ov51x_decomp_ops *ov518_mmx_decomp_ops;
221
 
222
/* Number of times to retry a failed I2C transaction. Increase this if you
223
 * are getting "Failed to read sensor ID..." */
224
static int i2c_detect_tries = 5;
225
 
226
/* MMX support is present in kernel and CPU. Checked upon decomp module load. */
227
static int ov51x_mmx_available;
228
 
229
static struct usb_device_id device_table [] = {
230
        { USB_DEVICE(VEND_OMNIVISION, PROD_OV511) },
231
        { USB_DEVICE(VEND_OMNIVISION, PROD_OV511PLUS) },
232
        { USB_DEVICE(VEND_OMNIVISION, PROD_OV518) },
233
        { USB_DEVICE(VEND_OMNIVISION, PROD_OV518PLUS) },
234
        { USB_DEVICE(VEND_MATTEL, PROD_ME2CAM) },
235
        { }  /* Terminating entry */
236
};
237
 
238
MODULE_DEVICE_TABLE (usb, device_table);
239
 
240
static unsigned char yQuanTable511[] = OV511_YQUANTABLE;
241
static unsigned char uvQuanTable511[] = OV511_UVQUANTABLE;
242
static unsigned char yQuanTable518[] = OV518_YQUANTABLE;
243
static unsigned char uvQuanTable518[] = OV518_UVQUANTABLE;
244
 
245
/**********************************************************************
246
 * Symbolic Names
247
 **********************************************************************/
248
 
249
/* Known OV511-based cameras */
250
static struct symbolic_list camlist[] = {
251
        {   0, "Generic Camera (no ID)" },
252
        {   1, "Mustek WCam 3X" },
253
        {   3, "D-Link DSB-C300" },
254
        {   4, "Generic OV511/OV7610" },
255
        {   5, "Puretek PT-6007" },
256
        {   6, "Lifeview USB Life TV (NTSC)" },
257
        {  21, "Creative Labs WebCam 3" },
258
        {  22, "Lifeview USB Life TV (PAL D/K+B/G)" },
259
        {  36, "Koala-Cam" },
260
        {  38, "Lifeview USB Life TV (PAL)" },
261
        {  41, "Samsung Anycam MPC-M10" },
262
        {  43, "Mtekvision Zeca MV402" },
263
        {  46, "Suma eON" },
264
        {  70, "Lifeview USB Life TV (PAL/SECAM)" },
265
        { 100, "Lifeview RoboCam" },
266
        { 102, "AverMedia InterCam Elite" },
267
        { 112, "MediaForte MV300" },    /* or OV7110 evaluation kit */
268
        { 134, "Ezonics EZCam II" },
269
        { 192, "Webeye 2000B" },
270
        { 253, "Alpha Vision Tech. AlphaCam SE" },
271
        {  -1, NULL }
272
};
273
 
274
/* Video4Linux1 Palettes */
275
static struct symbolic_list v4l1_plist[] = {
276
        { VIDEO_PALETTE_GREY,   "GREY" },
277
        { VIDEO_PALETTE_HI240,  "HI240" },
278
        { VIDEO_PALETTE_RGB565, "RGB565" },
279
        { VIDEO_PALETTE_RGB24,  "RGB24" },
280
        { VIDEO_PALETTE_RGB32,  "RGB32" },
281
        { VIDEO_PALETTE_RGB555, "RGB555" },
282
        { VIDEO_PALETTE_YUV422, "YUV422" },
283
        { VIDEO_PALETTE_YUYV,   "YUYV" },
284
        { VIDEO_PALETTE_UYVY,   "UYVY" },
285
        { VIDEO_PALETTE_YUV420, "YUV420" },
286
        { VIDEO_PALETTE_YUV411, "YUV411" },
287
        { VIDEO_PALETTE_RAW,    "RAW" },
288
        { VIDEO_PALETTE_YUV422P,"YUV422P" },
289
        { VIDEO_PALETTE_YUV411P,"YUV411P" },
290
        { VIDEO_PALETTE_YUV420P,"YUV420P" },
291
        { VIDEO_PALETTE_YUV410P,"YUV410P" },
292
        { -1, NULL }
293
};
294
 
295
static struct symbolic_list brglist[] = {
296
        { BRG_OV511,            "OV511" },
297
        { BRG_OV511PLUS,        "OV511+" },
298
        { BRG_OV518,            "OV518" },
299
        { BRG_OV518PLUS,        "OV518+" },
300
        { -1, NULL }
301
};
302
 
303
#if defined(CONFIG_VIDEO_PROC_FS)
304
static struct symbolic_list senlist[] = {
305
        { SEN_OV76BE,   "OV76BE" },
306
        { SEN_OV7610,   "OV7610" },
307
        { SEN_OV7620,   "OV7620" },
308
        { SEN_OV7620AE, "OV7620AE" },
309
        { SEN_OV6620,   "OV6620" },
310
        { SEN_OV6630,   "OV6630" },
311
        { SEN_OV6630AE, "OV6630AE" },
312
        { SEN_OV6630AF, "OV6630AF" },
313
        { SEN_OV8600,   "OV8600" },
314
        { SEN_KS0127,   "KS0127" },
315
        { SEN_KS0127B,  "KS0127B" },
316
        { SEN_SAA7111A, "SAA7111A" },
317
        { -1, NULL }
318
};
319
#endif
320
 
321
/* URB error codes: */
322
static struct symbolic_list urb_errlist[] = {
323
        { -ENOSR,       "Buffer error (overrun)" },
324
        { -EPIPE,       "Stalled (device not responding)" },
325
        { -EOVERFLOW,   "Babble (bad cable?)" },
326
        { -EPROTO,      "Bit-stuff error (bad cable?)" },
327
        { -EILSEQ,      "CRC/Timeout" },
328
        { -ETIMEDOUT,   "NAK (device does not respond)" },
329
        { -1, NULL }
330
};
331
 
332
/**********************************************************************
333
 * Prototypes
334
 **********************************************************************/
335
 
336
static void ov51x_clear_snapshot(struct usb_ov511 *);
337
static inline int sensor_get_picture(struct usb_ov511 *,
338
                                     struct video_picture *);
339
#if defined(CONFIG_PROC_FS) && defined(CONFIG_VIDEO_PROC_FS)
340
static int sensor_get_exposure(struct usb_ov511 *, unsigned char *);
341
static int ov51x_control_ioctl(struct inode *, struct file *, unsigned int,
342
                               unsigned long);
343
static int ov51x_check_snapshot(struct usb_ov511 *);
344
#endif
345
 
346
/**********************************************************************
347
 * Memory management
348
 **********************************************************************/
349
 
350
/* Here we want the physical address of the memory.
351
 * This is used when initializing the contents of the area.
352
 */
353
static inline unsigned long
354
kvirt_to_pa(unsigned long adr)
355
{
356
        unsigned long kva, ret;
357
 
358
        kva = (unsigned long) page_address(vmalloc_to_page((void *)adr));
359
        kva |= adr & (PAGE_SIZE-1); /* restore the offset */
360
        ret = __pa(kva);
361
        return ret;
362
}
363
 
364
static void *
365
rvmalloc(unsigned long size)
366
{
367
        void *mem;
368
        unsigned long adr;
369
 
370
        size = PAGE_ALIGN(size);
371
        mem = vmalloc_32(size);
372
        if (!mem)
373
                return NULL;
374
 
375
        memset(mem, 0, size); /* Clear the ram out, no junk to the user */
376
        adr = (unsigned long) mem;
377
        while (size > 0) {
378
                mem_map_reserve(vmalloc_to_page((void *)adr));
379
                adr += PAGE_SIZE;
380
                size -= PAGE_SIZE;
381
        }
382
 
383
        return mem;
384
}
385
 
386
static void
387
rvfree(void *mem, unsigned long size)
388
{
389
        unsigned long adr;
390
 
391
        if (!mem)
392
                return;
393
 
394
        adr = (unsigned long) mem;
395
        while ((long) size > 0) {
396
                mem_map_unreserve(vmalloc_to_page((void *)adr));
397
                adr += PAGE_SIZE;
398
                size -= PAGE_SIZE;
399
        }
400
        vfree(mem);
401
}
402
 
403
/**********************************************************************
404
 * /proc interface
405
 * Based on the CPiA driver version 0.7.4 -claudio
406
 **********************************************************************/
407
 
408
#if defined(CONFIG_PROC_FS) && defined(CONFIG_VIDEO_PROC_FS)
409
 
410
static struct proc_dir_entry *ov511_proc_entry = NULL;
411
extern struct proc_dir_entry *video_proc_entry;
412
 
413
static struct file_operations ov511_control_fops = {
414
        .ioctl =        ov51x_control_ioctl,
415
};
416
 
417
#define YES_NO(x) ((x) ? "yes" : "no")
418
 
419
/* /proc/video/ov511/<minor#>/info */
420
static int
421
ov511_read_proc_info(char *page, char **start, off_t off, int count, int *eof,
422
                     void *data)
423
{
424
        char *out = page;
425
        int i, len;
426
        struct usb_ov511 *ov = data;
427
        struct video_picture p;
428
        unsigned char exp;
429
 
430
        if (!ov || !ov->dev)
431
                return -ENODEV;
432
 
433
        sensor_get_picture(ov, &p);
434
        sensor_get_exposure(ov, &exp);
435
 
436
        /* IMPORTANT: This output MUST be kept under PAGE_SIZE
437
         *            or we need to get more sophisticated. */
438
 
439
        out += sprintf(out, "driver_version  : %s\n", DRIVER_VERSION);
440
        out += sprintf(out, "custom_id       : %d\n", ov->customid);
441
        out += sprintf(out, "model           : %s\n", ov->desc);
442
        out += sprintf(out, "streaming       : %s\n", YES_NO(ov->streaming));
443
        out += sprintf(out, "grabbing        : %s\n", YES_NO(ov->grabbing));
444
        out += sprintf(out, "compress        : %s\n", YES_NO(ov->compress));
445
        out += sprintf(out, "subcapture      : %s\n", YES_NO(ov->sub_flag));
446
        out += sprintf(out, "sub_size        : %d %d %d %d\n",
447
                       ov->subx, ov->suby, ov->subw, ov->subh);
448
        out += sprintf(out, "data_format     : %s\n",
449
                       force_rgb ? "RGB" : "BGR");
450
        out += sprintf(out, "brightness      : %d\n", p.brightness >> 8);
451
        out += sprintf(out, "colour          : %d\n", p.colour >> 8);
452
        out += sprintf(out, "contrast        : %d\n", p.contrast >> 8);
453
        out += sprintf(out, "hue             : %d\n", p.hue >> 8);
454
        out += sprintf(out, "exposure        : %d\n", exp);
455
        out += sprintf(out, "num_frames      : %d\n", OV511_NUMFRAMES);
456
        for (i = 0; i < OV511_NUMFRAMES; i++) {
457
                out += sprintf(out, "frame           : %d\n", i);
458
                out += sprintf(out, "  depth         : %d\n",
459
                               ov->frame[i].depth);
460
                out += sprintf(out, "  size          : %d %d\n",
461
                               ov->frame[i].width, ov->frame[i].height);
462
                out += sprintf(out, "  format        : %s\n",
463
                               symbolic(v4l1_plist, ov->frame[i].format));
464
                out += sprintf(out, "  data_buffer   : 0x%p\n",
465
                               ov->frame[i].data);
466
        }
467
        out += sprintf(out, "snap_enabled    : %s\n", YES_NO(ov->snap_enabled));
468
        out += sprintf(out, "bridge          : %s\n",
469
                       symbolic(brglist, ov->bridge));
470
        out += sprintf(out, "sensor          : %s\n",
471
                       symbolic(senlist, ov->sensor));
472
        out += sprintf(out, "packet_size     : %d\n", ov->packet_size);
473
        out += sprintf(out, "framebuffer     : 0x%p\n", ov->fbuf);
474
        out += sprintf(out, "packet_numbering: %d\n", ov->packet_numbering);
475
        out += sprintf(out, "topology        : %s\n", ov->usb_path);
476
 
477
        len = out - page;
478
        len -= off;
479
        if (len < count) {
480
                *eof = 1;
481
                if (len <= 0)
482
                        return 0;
483
        } else
484
                len = count;
485
 
486
        *start = page + off;
487
 
488
        return len;
489
}
490
 
491
/* /proc/video/ov511/<minor#>/button
492
 *
493
 * When the camera's button is pressed, the output of this will change from a
494
 * 0 to a 1 (ASCII). It will retain this value until it is read, after which
495
 * it will reset to zero.
496
 *
497
 * SECURITY NOTE: Since reading this file can change the state of the snapshot
498
 * status, it is important for applications that open it to keep it locked
499
 * against access by other processes, using flock() or a similar mechanism. No
500
 * locking is provided by this driver.
501
 */
502
static int
503
ov511_read_proc_button(char *page, char **start, off_t off, int count, int *eof,
504
                       void *data)
505
{
506
        char *out = page;
507
        int len, status;
508
        struct usb_ov511 *ov = data;
509
 
510
        if (!ov || !ov->dev)
511
                return -ENODEV;
512
 
513
        status = ov51x_check_snapshot(ov);
514
        out += sprintf(out, "%d", status);
515
 
516
        if (status)
517
                ov51x_clear_snapshot(ov);
518
 
519
        len = out - page;
520
        len -= off;
521
        if (len < count) {
522
                *eof = 1;
523
                if (len <= 0)
524
                        return 0;
525
        } else {
526
                len = count;
527
        }
528
 
529
        *start = page + off;
530
 
531
        return len;
532
}
533
 
534
static void
535
create_proc_ov511_cam(struct usb_ov511 *ov)
536
{
537
        char dirname[10];
538
 
539
        if (!ov511_proc_entry || !ov)
540
                return;
541
 
542
        /* Create per-device directory */
543
        snprintf(dirname, 10, "%d", ov->vdev.minor);
544
        PDEBUG(4, "creating /proc/video/ov511/%s/", dirname);
545
        ov->proc_devdir = create_proc_entry(dirname, S_IFDIR, ov511_proc_entry);
546
        if (!ov->proc_devdir)
547
                return;
548
        ov->proc_devdir->owner = THIS_MODULE;
549
 
550
        /* Create "info" entry (human readable device information) */
551
        PDEBUG(4, "creating /proc/video/ov511/%s/info", dirname);
552
        ov->proc_info = create_proc_read_entry("info", S_IFREG|S_IRUGO|S_IWUSR,
553
                ov->proc_devdir, ov511_read_proc_info, ov);
554
        if (!ov->proc_info)
555
                return;
556
        ov->proc_info->owner = THIS_MODULE;
557
 
558
        /* Don't create it if old snapshot mode on (would cause race cond.) */
559
        if (!snapshot) {
560
                /* Create "button" entry (snapshot button status) */
561
                PDEBUG(4, "creating /proc/video/ov511/%s/button", dirname);
562
                ov->proc_button = create_proc_read_entry("button",
563
                        S_IFREG|S_IRUGO|S_IWUSR, ov->proc_devdir,
564
                        ov511_read_proc_button, ov);
565
                if (!ov->proc_button)
566
                        return;
567
                ov->proc_button->owner = THIS_MODULE;
568
        }
569
 
570
        /* Create "control" entry (ioctl() interface) */
571
        PDEBUG(4, "creating /proc/video/ov511/%s/control", dirname);
572
        lock_kernel();
573
        ov->proc_control = create_proc_entry("control", S_IFREG|S_IRUGO|S_IWUSR,
574
                ov->proc_devdir);
575
        if (!ov->proc_control) {
576
                unlock_kernel();
577
                return;
578
        }
579
        ov->proc_control->owner = THIS_MODULE;
580
        ov->proc_control->data = ov;
581
        ov->proc_control->proc_fops = &ov511_control_fops;
582
        unlock_kernel();
583
}
584
 
585
static void
586
destroy_proc_ov511_cam(struct usb_ov511 *ov)
587
{
588
        char dirname[10];
589
 
590
        if (!ov || !ov->proc_devdir)
591
                return;
592
 
593
        snprintf(dirname, 10, "%d", ov->vdev.minor);
594
 
595
        /* Destroy "control" entry */
596
        if (ov->proc_control) {
597
                PDEBUG(4, "destroying /proc/video/ov511/%s/control", dirname);
598
                remove_proc_entry("control", ov->proc_devdir);
599
                ov->proc_control = NULL;
600
        }
601
 
602
        /* Destroy "button" entry */
603
        if (ov->proc_button) {
604
                PDEBUG(4, "destroying /proc/video/ov511/%s/button", dirname);
605
                remove_proc_entry("button", ov->proc_devdir);
606
                ov->proc_button = NULL;
607
        }
608
 
609
        /* Destroy "info" entry */
610
        if (ov->proc_info) {
611
                PDEBUG(4, "destroying /proc/video/ov511/%s/info", dirname);
612
                remove_proc_entry("info", ov->proc_devdir);
613
                ov->proc_info = NULL;
614
        }
615
 
616
        /* Destroy per-device directory */
617
        PDEBUG(4, "destroying /proc/video/ov511/%s/", dirname);
618
        remove_proc_entry(dirname, ov511_proc_entry);
619
        ov->proc_devdir = NULL;
620
}
621
 
622
static void
623
proc_ov511_create(void)
624
{
625
        /* No current standard here. Alan prefers /proc/video/ as it keeps
626
         * /proc "less cluttered than /proc/randomcardifoundintheshed/"
627
         * -claudio
628
         */
629
        if (video_proc_entry == NULL) {
630
                err("Error: /proc/video/ does not exist");
631
                return;
632
        }
633
 
634
        ov511_proc_entry = create_proc_entry("ov511", S_IFDIR,
635
                                             video_proc_entry);
636
 
637
        if (ov511_proc_entry)
638
                ov511_proc_entry->owner = THIS_MODULE;
639
        else
640
                err("Unable to create /proc/video/ov511");
641
}
642
 
643
static void
644
proc_ov511_destroy(void)
645
{
646
        PDEBUG(3, "removing /proc/video/ov511");
647
 
648
        if (ov511_proc_entry == NULL)
649
                return;
650
 
651
        remove_proc_entry("ov511", video_proc_entry);
652
}
653
#endif /* CONFIG_PROC_FS && CONFIG_VIDEO_PROC_FS */
654
 
655
/**********************************************************************
656
 *
657
 * Register I/O
658
 *
659
 **********************************************************************/
660
 
661
/* Write an OV51x register */
662
static int
663
reg_w(struct usb_ov511 *ov, unsigned char reg, unsigned char value)
664
{
665
        int rc;
666
 
667
        PDEBUG(5, "0x%02X:0x%02X", reg, value);
668
 
669
        down(&ov->cbuf_lock);
670
        ov->cbuf[0] = value;
671
        rc = usb_control_msg(ov->dev,
672
                             usb_sndctrlpipe(ov->dev, 0),
673
                             (ov->bclass == BCL_OV518)?1:2 /* REG_IO */,
674
                             USB_TYPE_VENDOR | USB_RECIP_DEVICE,
675
                             0, (__u16)reg, &ov->cbuf[0], 1, HZ);
676
        up(&ov->cbuf_lock);
677
 
678
        if (rc < 0)
679
                err("reg write: error %d: %s", rc, symbolic(urb_errlist, rc));
680
 
681
        return rc;
682
}
683
 
684
/* Read from an OV51x register */
685
/* returns: negative is error, pos or zero is data */
686
static int
687
reg_r(struct usb_ov511 *ov, unsigned char reg)
688
{
689
        int rc;
690
 
691
        down(&ov->cbuf_lock);
692
        rc = usb_control_msg(ov->dev,
693
                             usb_rcvctrlpipe(ov->dev, 0),
694
                             (ov->bclass == BCL_OV518)?1:3 /* REG_IO */,
695
                             USB_DIR_IN | USB_TYPE_VENDOR | USB_RECIP_DEVICE,
696
                             0, (__u16)reg, &ov->cbuf[0], 1, HZ);
697
 
698
        if (rc < 0) {
699
                err("reg read: error %d: %s", rc, symbolic(urb_errlist, rc));
700
        } else {
701
                rc = ov->cbuf[0];
702
                PDEBUG(5, "0x%02X:0x%02X", reg, ov->cbuf[0]);
703
        }
704
 
705
        up(&ov->cbuf_lock);
706
 
707
        return rc;
708
}
709
 
710
/*
711
 * Writes bits at positions specified by mask to an OV51x reg. Bits that are in
712
 * the same position as 1's in "mask" are cleared and set to "value". Bits
713
 * that are in the same position as 0's in "mask" are preserved, regardless
714
 * of their respective state in "value".
715
 */
716
static int
717
reg_w_mask(struct usb_ov511 *ov,
718
           unsigned char reg,
719
           unsigned char value,
720
           unsigned char mask)
721
{
722
        int ret;
723
        unsigned char oldval, newval;
724
 
725
        ret = reg_r(ov, reg);
726
        if (ret < 0)
727
                return ret;
728
 
729
        oldval = (unsigned char) ret;
730
        oldval &= (~mask);              /* Clear the masked bits */
731
        value &= mask;                  /* Enforce mask on value */
732
        newval = oldval | value;        /* Set the desired bits */
733
 
734
        return (reg_w(ov, reg, newval));
735
}
736
 
737
/*
738
 * Writes multiple (n) byte value to a single register. Only valid with certain
739
 * registers (0x30 and 0xc4 - 0xce).
740
 */
741
static int
742
ov518_reg_w32(struct usb_ov511 *ov, unsigned char reg, u32 val, int n)
743
{
744
        int rc;
745
 
746
        PDEBUG(5, "0x%02X:%7d, n=%d", reg, val, n);
747
 
748
        down(&ov->cbuf_lock);
749
 
750
        *((u32 *)ov->cbuf) = __cpu_to_le32(val);
751
 
752
        rc = usb_control_msg(ov->dev,
753
                             usb_sndctrlpipe(ov->dev, 0),
754
                             1 /* REG_IO */,
755
                             USB_TYPE_VENDOR | USB_RECIP_DEVICE,
756
                             0, (__u16)reg, ov->cbuf, n, HZ);
757
        up(&ov->cbuf_lock);
758
 
759
        if (rc < 0)
760
                err("reg write multiple: error %d: %s", rc,
761
                    symbolic(urb_errlist, rc));
762
 
763
        return rc;
764
}
765
 
766
static int
767
ov511_upload_quan_tables(struct usb_ov511 *ov)
768
{
769
        unsigned char *pYTable = yQuanTable511;
770
        unsigned char *pUVTable = uvQuanTable511;
771
        unsigned char val0, val1;
772
        int i, rc, reg = R511_COMP_LUT_BEGIN;
773
 
774
        PDEBUG(4, "Uploading quantization tables");
775
 
776
        for (i = 0; i < OV511_QUANTABLESIZE / 2; i++) {
777
                if (ENABLE_Y_QUANTABLE) {
778
                        val0 = *pYTable++;
779
                        val1 = *pYTable++;
780
                        val0 &= 0x0f;
781
                        val1 &= 0x0f;
782
                        val0 |= val1 << 4;
783
                        rc = reg_w(ov, reg, val0);
784
                        if (rc < 0)
785
                                return rc;
786
                }
787
 
788
                if (ENABLE_UV_QUANTABLE) {
789
                        val0 = *pUVTable++;
790
                        val1 = *pUVTable++;
791
                        val0 &= 0x0f;
792
                        val1 &= 0x0f;
793
                        val0 |= val1 << 4;
794
                        rc = reg_w(ov, reg + OV511_QUANTABLESIZE/2, val0);
795
                        if (rc < 0)
796
                                return rc;
797
                }
798
 
799
                reg++;
800
        }
801
 
802
        return 0;
803
}
804
 
805
/* OV518 quantization tables are 8x4 (instead of 8x8) */
806
static int
807
ov518_upload_quan_tables(struct usb_ov511 *ov)
808
{
809
        unsigned char *pYTable = yQuanTable518;
810
        unsigned char *pUVTable = uvQuanTable518;
811
        unsigned char val0, val1;
812
        int i, rc, reg = R511_COMP_LUT_BEGIN;
813
 
814
        PDEBUG(4, "Uploading quantization tables");
815
 
816
        for (i = 0; i < OV518_QUANTABLESIZE / 2; i++) {
817
                if (ENABLE_Y_QUANTABLE) {
818
                        val0 = *pYTable++;
819
                        val1 = *pYTable++;
820
                        val0 &= 0x0f;
821
                        val1 &= 0x0f;
822
                        val0 |= val1 << 4;
823
                        rc = reg_w(ov, reg, val0);
824
                        if (rc < 0)
825
                                return rc;
826
                }
827
 
828
                if (ENABLE_UV_QUANTABLE) {
829
                        val0 = *pUVTable++;
830
                        val1 = *pUVTable++;
831
                        val0 &= 0x0f;
832
                        val1 &= 0x0f;
833
                        val0 |= val1 << 4;
834
                        rc = reg_w(ov, reg + OV518_QUANTABLESIZE/2, val0);
835
                        if (rc < 0)
836
                                return rc;
837
                }
838
 
839
                reg++;
840
        }
841
 
842
        return 0;
843
}
844
 
845
static int
846
ov51x_reset(struct usb_ov511 *ov, unsigned char reset_type)
847
{
848
        int rc;
849
 
850
        /* Setting bit 0 not allowed on 518/518Plus */
851
        if (ov->bclass == BCL_OV518)
852
                reset_type &= 0xfe;
853
 
854
        PDEBUG(4, "Reset: type=0x%02X", reset_type);
855
 
856
        rc = reg_w(ov, R51x_SYS_RESET, reset_type);
857
        rc = reg_w(ov, R51x_SYS_RESET, 0);
858
 
859
        if (rc < 0)
860
                err("reset: command failed");
861
 
862
        return rc;
863
}
864
 
865
/**********************************************************************
866
 *
867
 * Low-level I2C I/O functions
868
 *
869
 **********************************************************************/
870
 
871
/* NOTE: Do not call this function directly!
872
 * The OV518 I2C I/O procedure is different, hence, this function.
873
 * This is normally only called from i2c_w(). Note that this function
874
 * always succeeds regardless of whether the sensor is present and working.
875
 */
876
static int
877
ov518_i2c_write_internal(struct usb_ov511 *ov,
878
                         unsigned char reg,
879
                         unsigned char value)
880
{
881
        int rc;
882
 
883
        PDEBUG(5, "0x%02X:0x%02X", reg, value);
884
 
885
        /* Select camera register */
886
        rc = reg_w(ov, R51x_I2C_SADDR_3, reg);
887
        if (rc < 0) return rc;
888
 
889
        /* Write "value" to I2C data port of OV511 */
890
        rc = reg_w(ov, R51x_I2C_DATA, value);
891
        if (rc < 0) return rc;
892
 
893
        /* Initiate 3-byte write cycle */
894
        rc = reg_w(ov, R518_I2C_CTL, 0x01);
895
        if (rc < 0) return rc;
896
 
897
        return 0;
898
}
899
 
900
/* NOTE: Do not call this function directly! */
901
static int
902
ov511_i2c_write_internal(struct usb_ov511 *ov,
903
                         unsigned char reg,
904
                         unsigned char value)
905
{
906
        int rc, retries;
907
 
908
        PDEBUG(5, "0x%02X:0x%02X", reg, value);
909
 
910
        /* Three byte write cycle */
911
        for (retries = OV511_I2C_RETRIES; ; ) {
912
                /* Select camera register */
913
                rc = reg_w(ov, R51x_I2C_SADDR_3, reg);
914
                if (rc < 0) return rc;
915
 
916
                /* Write "value" to I2C data port of OV511 */
917
                rc = reg_w(ov, R51x_I2C_DATA, value);
918
                if (rc < 0) return rc;
919
 
920
                /* Initiate 3-byte write cycle */
921
                rc = reg_w(ov, R511_I2C_CTL, 0x01);
922
                if (rc < 0) return rc;
923
 
924
                do rc = reg_r(ov, R511_I2C_CTL);
925
                while (rc > 0 && ((rc&1) == 0)); /* Retry until idle */
926
                if (rc < 0) return rc;
927
 
928
                if ((rc&2) == 0) /* Ack? */
929
                        break;
930
#if 0
931
                /* I2C abort */
932
                reg_w(ov, R511_I2C_CTL, 0x10);
933
#endif
934
                if (--retries < 0) {
935
                        err("i2c write retries exhausted");
936
                        return -1;
937
                }
938
        }
939
 
940
        return 0;
941
}
942
 
943
/* NOTE: Do not call this function directly!
944
 * The OV518 I2C I/O procedure is different, hence, this function.
945
 * This is normally only called from i2c_r(). Note that this function
946
 * always succeeds regardless of whether the sensor is present and working.
947
 */
948
static int
949
ov518_i2c_read_internal(struct usb_ov511 *ov, unsigned char reg)
950
{
951
        int rc, value;
952
 
953
        /* Select camera register */
954
        rc = reg_w(ov, R51x_I2C_SADDR_2, reg);
955
        if (rc < 0) return rc;
956
 
957
        /* Initiate 2-byte write cycle */
958
        rc = reg_w(ov, R518_I2C_CTL, 0x03);
959
        if (rc < 0) return rc;
960
 
961
        /* Initiate 2-byte read cycle */
962
        rc = reg_w(ov, R518_I2C_CTL, 0x05);
963
        if (rc < 0) return rc;
964
 
965
        value = reg_r(ov, R51x_I2C_DATA);
966
 
967
        PDEBUG(5, "0x%02X:0x%02X", reg, value);
968
 
969
        return value;
970
}
971
 
972
/* NOTE: Do not call this function directly!
973
 * returns: negative is error, pos or zero is data */
974
static int
975
ov511_i2c_read_internal(struct usb_ov511 *ov, unsigned char reg)
976
{
977
        int rc, value, retries;
978
 
979
        /* Two byte write cycle */
980
        for (retries = OV511_I2C_RETRIES; ; ) {
981
                /* Select camera register */
982
                rc = reg_w(ov, R51x_I2C_SADDR_2, reg);
983
                if (rc < 0) return rc;
984
 
985
                /* Initiate 2-byte write cycle */
986
                rc = reg_w(ov, R511_I2C_CTL, 0x03);
987
                if (rc < 0) return rc;
988
 
989
                do rc = reg_r(ov, R511_I2C_CTL);
990
                while (rc > 0 && ((rc&1) == 0)); /* Retry until idle */
991
                if (rc < 0) return rc;
992
 
993
                if ((rc&2) == 0) /* Ack? */
994
                        break;
995
 
996
                /* I2C abort */
997
                reg_w(ov, R511_I2C_CTL, 0x10);
998
 
999
                if (--retries < 0) {
1000
                        err("i2c write retries exhausted");
1001
                        return -1;
1002
                }
1003
        }
1004
 
1005
        /* Two byte read cycle */
1006
        for (retries = OV511_I2C_RETRIES; ; ) {
1007
                /* Initiate 2-byte read cycle */
1008
                rc = reg_w(ov, R511_I2C_CTL, 0x05);
1009
                if (rc < 0) return rc;
1010
 
1011
                do rc = reg_r(ov, R511_I2C_CTL);
1012
                while (rc > 0 && ((rc&1) == 0)); /* Retry until idle */
1013
                if (rc < 0) return rc;
1014
 
1015
                if ((rc&2) == 0) /* Ack? */
1016
                        break;
1017
 
1018
                /* I2C abort */
1019
                rc = reg_w(ov, R511_I2C_CTL, 0x10);
1020
                if (rc < 0) return rc;
1021
 
1022
                if (--retries < 0) {
1023
                        err("i2c read retries exhausted");
1024
                        return -1;
1025
                }
1026
        }
1027
 
1028
        value = reg_r(ov, R51x_I2C_DATA);
1029
 
1030
        PDEBUG(5, "0x%02X:0x%02X", reg, value);
1031
 
1032
        /* This is needed to make i2c_w() work */
1033
        rc = reg_w(ov, R511_I2C_CTL, 0x05);
1034
        if (rc < 0)
1035
                return rc;
1036
 
1037
        return value;
1038
}
1039
 
1040
/* returns: negative is error, pos or zero is data */
1041
static int
1042
i2c_r(struct usb_ov511 *ov, unsigned char reg)
1043
{
1044
        int rc;
1045
 
1046
        down(&ov->i2c_lock);
1047
 
1048
        if (ov->bclass == BCL_OV518)
1049
                rc = ov518_i2c_read_internal(ov, reg);
1050
        else
1051
                rc = ov511_i2c_read_internal(ov, reg);
1052
 
1053
        up(&ov->i2c_lock);
1054
 
1055
        return rc;
1056
}
1057
 
1058
static int
1059
i2c_w(struct usb_ov511 *ov, unsigned char reg, unsigned char value)
1060
{
1061
        int rc;
1062
 
1063
        down(&ov->i2c_lock);
1064
 
1065
        if (ov->bclass == BCL_OV518)
1066
                rc = ov518_i2c_write_internal(ov, reg, value);
1067
        else
1068
                rc = ov511_i2c_write_internal(ov, reg, value);
1069
 
1070
        up(&ov->i2c_lock);
1071
 
1072
        return rc;
1073
}
1074
 
1075
/* Do not call this function directly! */
1076
static int
1077
ov51x_i2c_write_mask_internal(struct usb_ov511 *ov,
1078
                              unsigned char reg,
1079
                              unsigned char value,
1080
                              unsigned char mask)
1081
{
1082
        int rc;
1083
        unsigned char oldval, newval;
1084
 
1085
        if (mask == 0xff) {
1086
                newval = value;
1087
        } else {
1088
                if (ov->bclass == BCL_OV518)
1089
                        rc = ov518_i2c_read_internal(ov, reg);
1090
                else
1091
                        rc = ov511_i2c_read_internal(ov, reg);
1092
                if (rc < 0)
1093
                        return rc;
1094
 
1095
                oldval = (unsigned char) rc;
1096
                oldval &= (~mask);              /* Clear the masked bits */
1097
                value &= mask;                  /* Enforce mask on value */
1098
                newval = oldval | value;        /* Set the desired bits */
1099
        }
1100
 
1101
        if (ov->bclass == BCL_OV518)
1102
                return (ov518_i2c_write_internal(ov, reg, newval));
1103
        else
1104
                return (ov511_i2c_write_internal(ov, reg, newval));
1105
}
1106
 
1107
/* Writes bits at positions specified by mask to an I2C reg. Bits that are in
1108
 * the same position as 1's in "mask" are cleared and set to "value". Bits
1109
 * that are in the same position as 0's in "mask" are preserved, regardless
1110
 * of their respective state in "value".
1111
 */
1112
static int
1113
i2c_w_mask(struct usb_ov511 *ov,
1114
           unsigned char reg,
1115
           unsigned char value,
1116
           unsigned char mask)
1117
{
1118
        int rc;
1119
 
1120
        down(&ov->i2c_lock);
1121
        rc = ov51x_i2c_write_mask_internal(ov, reg, value, mask);
1122
        up(&ov->i2c_lock);
1123
 
1124
        return rc;
1125
}
1126
 
1127
/* Set the read and write slave IDs. The "slave" argument is the write slave,
1128
 * and the read slave will be set to (slave + 1). ov->i2c_lock should be held
1129
 * when calling this. This should not be called from outside the i2c I/O
1130
 * functions.
1131
 */
1132
static inline int
1133
i2c_set_slave_internal(struct usb_ov511 *ov, unsigned char slave)
1134
{
1135
        int rc;
1136
 
1137
        rc = reg_w(ov, R51x_I2C_W_SID, slave);
1138
        if (rc < 0) return rc;
1139
 
1140
        rc = reg_w(ov, R51x_I2C_R_SID, slave + 1);
1141
        if (rc < 0) return rc;
1142
 
1143
        return 0;
1144
}
1145
 
1146
/* Write to a specific I2C slave ID and register, using the specified mask */
1147
static int
1148
i2c_w_slave(struct usb_ov511 *ov,
1149
            unsigned char slave,
1150
            unsigned char reg,
1151
            unsigned char value,
1152
            unsigned char mask)
1153
{
1154
        int rc = 0;
1155
 
1156
        down(&ov->i2c_lock);
1157
 
1158
        /* Set new slave IDs */
1159
        rc = i2c_set_slave_internal(ov, slave);
1160
        if (rc < 0) goto out;
1161
 
1162
        rc = ov51x_i2c_write_mask_internal(ov, reg, value, mask);
1163
 
1164
out:
1165
        /* Restore primary IDs */
1166
        if (i2c_set_slave_internal(ov, ov->primary_i2c_slave) < 0)
1167
                err("Couldn't restore primary I2C slave");
1168
 
1169
        up(&ov->i2c_lock);
1170
        return rc;
1171
}
1172
 
1173
/* Read from a specific I2C slave ID and register */
1174
static int
1175
i2c_r_slave(struct usb_ov511 *ov,
1176
            unsigned char slave,
1177
            unsigned char reg)
1178
{
1179
        int rc;
1180
 
1181
        down(&ov->i2c_lock);
1182
 
1183
        /* Set new slave IDs */
1184
        rc = i2c_set_slave_internal(ov, slave);
1185
        if (rc < 0) goto out;
1186
 
1187
        if (ov->bclass == BCL_OV518)
1188
                rc = ov518_i2c_read_internal(ov, reg);
1189
        else
1190
                rc = ov511_i2c_read_internal(ov, reg);
1191
 
1192
out:
1193
        /* Restore primary IDs */
1194
        if (i2c_set_slave_internal(ov, ov->primary_i2c_slave) < 0)
1195
                err("Couldn't restore primary I2C slave");
1196
 
1197
        up(&ov->i2c_lock);
1198
        return rc;
1199
}
1200
 
1201
/* Sets I2C read and write slave IDs. Returns <0 for error */
1202
static int
1203
ov51x_set_slave_ids(struct usb_ov511 *ov, unsigned char sid)
1204
{
1205
        int rc;
1206
 
1207
        down(&ov->i2c_lock);
1208
 
1209
        rc = i2c_set_slave_internal(ov, sid);
1210
        if (rc < 0) goto out;
1211
 
1212
        // FIXME: Is this actually necessary?
1213
        rc = ov51x_reset(ov, OV511_RESET_NOREGS);
1214
        if (rc < 0) goto out;
1215
 
1216
out:
1217
        up(&ov->i2c_lock);
1218
        return rc;
1219
}
1220
 
1221
static int
1222
write_regvals(struct usb_ov511 *ov, struct ov511_regvals * pRegvals)
1223
{
1224
        int rc;
1225
 
1226
        while (pRegvals->bus != OV511_DONE_BUS) {
1227
                if (pRegvals->bus == OV511_REG_BUS) {
1228
                        if ((rc = reg_w(ov, pRegvals->reg, pRegvals->val)) < 0)
1229
                                return rc;
1230
                } else if (pRegvals->bus == OV511_I2C_BUS) {
1231
                        if ((rc = i2c_w(ov, pRegvals->reg, pRegvals->val)) < 0)
1232
                                return rc;
1233
                } else {
1234
                        err("Bad regval array");
1235
                        return -1;
1236
                }
1237
                pRegvals++;
1238
        }
1239
        return 0;
1240
}
1241
 
1242
#ifdef OV511_DEBUG
1243
static void
1244
dump_i2c_range(struct usb_ov511 *ov, int reg1, int regn)
1245
{
1246
        int i, rc;
1247
 
1248
        for (i = reg1; i <= regn; i++) {
1249
                rc = i2c_r(ov, i);
1250
                info("Sensor[0x%02X] = 0x%02X", i, rc);
1251
        }
1252
}
1253
 
1254
static void
1255
dump_i2c_regs(struct usb_ov511 *ov)
1256
{
1257
        info("I2C REGS");
1258
        dump_i2c_range(ov, 0x00, 0x7C);
1259
}
1260
 
1261
static void
1262
dump_reg_range(struct usb_ov511 *ov, int reg1, int regn)
1263
{
1264
        int i, rc;
1265
 
1266
        for (i = reg1; i <= regn; i++) {
1267
                rc = reg_r(ov, i);
1268
                info("OV511[0x%02X] = 0x%02X", i, rc);
1269
        }
1270
}
1271
 
1272
static void
1273
ov511_dump_regs(struct usb_ov511 *ov)
1274
{
1275
        info("CAMERA INTERFACE REGS");
1276
        dump_reg_range(ov, 0x10, 0x1f);
1277
        info("DRAM INTERFACE REGS");
1278
        dump_reg_range(ov, 0x20, 0x23);
1279
        info("ISO FIFO REGS");
1280
        dump_reg_range(ov, 0x30, 0x31);
1281
        info("PIO REGS");
1282
        dump_reg_range(ov, 0x38, 0x39);
1283
        dump_reg_range(ov, 0x3e, 0x3e);
1284
        info("I2C REGS");
1285
        dump_reg_range(ov, 0x40, 0x49);
1286
        info("SYSTEM CONTROL REGS");
1287
        dump_reg_range(ov, 0x50, 0x55);
1288
        dump_reg_range(ov, 0x5e, 0x5f);
1289
        info("OmniCE REGS");
1290
        dump_reg_range(ov, 0x70, 0x79);
1291
        /* NOTE: Quantization tables are not readable. You will get the value
1292
         * in reg. 0x79 for every table register */
1293
        dump_reg_range(ov, 0x80, 0x9f);
1294
        dump_reg_range(ov, 0xa0, 0xbf);
1295
 
1296
}
1297
 
1298
static void
1299
ov518_dump_regs(struct usb_ov511 *ov)
1300
{
1301
        info("VIDEO MODE REGS");
1302
        dump_reg_range(ov, 0x20, 0x2f);
1303
        info("DATA PUMP AND SNAPSHOT REGS");
1304
        dump_reg_range(ov, 0x30, 0x3f);
1305
        info("I2C REGS");
1306
        dump_reg_range(ov, 0x40, 0x4f);
1307
        info("SYSTEM CONTROL AND VENDOR REGS");
1308
        dump_reg_range(ov, 0x50, 0x5f);
1309
        info("60 - 6F");
1310
        dump_reg_range(ov, 0x60, 0x6f);
1311
        info("70 - 7F");
1312
        dump_reg_range(ov, 0x70, 0x7f);
1313
        info("Y QUANTIZATION TABLE");
1314
        dump_reg_range(ov, 0x80, 0x8f);
1315
        info("UV QUANTIZATION TABLE");
1316
        dump_reg_range(ov, 0x90, 0x9f);
1317
        info("A0 - BF");
1318
        dump_reg_range(ov, 0xa0, 0xbf);
1319
        info("CBR");
1320
        dump_reg_range(ov, 0xc0, 0xcf);
1321
}
1322
#endif
1323
 
1324
/*****************************************************************************/
1325
 
1326
/* Temporarily stops OV511 from functioning. Must do this before changing
1327
 * registers while the camera is streaming */
1328
static inline int
1329
ov51x_stop(struct usb_ov511 *ov)
1330
{
1331
        PDEBUG(4, "stopping");
1332
        ov->stopped = 1;
1333
        if (ov->bclass == BCL_OV518)
1334
                return (reg_w_mask(ov, R51x_SYS_RESET, 0x3a, 0x3a));
1335
        else
1336
                return (reg_w(ov, R51x_SYS_RESET, 0x3d));
1337
}
1338
 
1339
/* Restarts OV511 after ov511_stop() is called. Has no effect if it is not
1340
 * actually stopped (for performance). */
1341
static inline int
1342
ov51x_restart(struct usb_ov511 *ov)
1343
{
1344
        if (ov->stopped) {
1345
                PDEBUG(4, "restarting");
1346
                ov->stopped = 0;
1347
 
1348
                /* Reinitialize the stream */
1349
                if (ov->bclass == BCL_OV518)
1350
                        reg_w(ov, 0x2f, 0x80);
1351
 
1352
                return (reg_w(ov, R51x_SYS_RESET, 0x00));
1353
        }
1354
 
1355
        return 0;
1356
}
1357
 
1358
/* Resets the hardware snapshot button */
1359
static void
1360
ov51x_clear_snapshot(struct usb_ov511 *ov)
1361
{
1362
        if (ov->bclass == BCL_OV511) {
1363
                reg_w(ov, R51x_SYS_SNAP, 0x00);
1364
                reg_w(ov, R51x_SYS_SNAP, 0x02);
1365
                reg_w(ov, R51x_SYS_SNAP, 0x00);
1366
        } else if (ov->bclass == BCL_OV518) {
1367
                warn("snapshot reset not supported yet on OV518(+)");
1368
        } else {
1369
                err("clear snap: invalid bridge type");
1370
        }
1371
}
1372
 
1373
#if defined(CONFIG_PROC_FS) && defined(CONFIG_VIDEO_PROC_FS)
1374
/* Checks the status of the snapshot button. Returns 1 if it was pressed since
1375
 * it was last cleared, and zero in all other cases (including errors) */
1376
static int
1377
ov51x_check_snapshot(struct usb_ov511 *ov)
1378
{
1379
        int ret, status = 0;
1380
 
1381
        if (ov->bclass == BCL_OV511) {
1382
                ret = reg_r(ov, R51x_SYS_SNAP);
1383
                if (ret < 0) {
1384
                        err("Error checking snspshot status (%d)", ret);
1385
                } else if (ret & 0x08) {
1386
                        status = 1;
1387
                }
1388
        } else if (ov->bclass == BCL_OV518) {
1389
                warn("snapshot check not supported yet on OV518(+)");
1390
        } else {
1391
                err("check snap: invalid bridge type");
1392
        }
1393
 
1394
        return status;
1395
}
1396
#endif
1397
 
1398
/* This does an initial reset of an OmniVision sensor and ensures that I2C
1399
 * is synchronized. Returns <0 for failure.
1400
 */
1401
static int
1402
init_ov_sensor(struct usb_ov511 *ov)
1403
{
1404
        int i, success;
1405
 
1406
        /* Reset the sensor */
1407
        if (i2c_w(ov, 0x12, 0x80) < 0) return -EIO;
1408
 
1409
        /* Wait for it to initialize */
1410
        schedule_timeout(1 + 150 * HZ / 1000);
1411
 
1412
        for (i = 0, success = 0; i < i2c_detect_tries && !success; i++) {
1413
                if ((i2c_r(ov, OV7610_REG_ID_HIGH) == 0x7F) &&
1414
                    (i2c_r(ov, OV7610_REG_ID_LOW) == 0xA2)) {
1415
                        success = 1;
1416
                        continue;
1417
                }
1418
 
1419
                /* Reset the sensor */
1420
                if (i2c_w(ov, 0x12, 0x80) < 0) return -EIO;
1421
                /* Wait for it to initialize */
1422
                schedule_timeout(1 + 150 * HZ / 1000);
1423
                /* Dummy read to sync I2C */
1424
                if (i2c_r(ov, 0x00) < 0) return -EIO;
1425
        }
1426
 
1427
        if (!success)
1428
                return -EIO;
1429
 
1430
        PDEBUG(1, "I2C synced in %d attempt(s)", i);
1431
 
1432
        return 0;
1433
}
1434
 
1435
static int
1436
ov511_set_packet_size(struct usb_ov511 *ov, int size)
1437
{
1438
        int alt, mult;
1439
 
1440
        if (ov51x_stop(ov) < 0)
1441
                return -EIO;
1442
 
1443
        mult = size >> 5;
1444
 
1445
        if (ov->bridge == BRG_OV511) {
1446
                if (size == 0) alt = OV511_ALT_SIZE_0;
1447
                else if (size == 257) alt = OV511_ALT_SIZE_257;
1448
                else if (size == 513) alt = OV511_ALT_SIZE_513;
1449
                else if (size == 769) alt = OV511_ALT_SIZE_769;
1450
                else if (size == 993) alt = OV511_ALT_SIZE_993;
1451
                else {
1452
                        err("Set packet size: invalid size (%d)", size);
1453
                        return -EINVAL;
1454
                }
1455
        } else if (ov->bridge == BRG_OV511PLUS) {
1456
                if (size == 0) alt = OV511PLUS_ALT_SIZE_0;
1457
                else if (size == 33) alt = OV511PLUS_ALT_SIZE_33;
1458
                else if (size == 129) alt = OV511PLUS_ALT_SIZE_129;
1459
                else if (size == 257) alt = OV511PLUS_ALT_SIZE_257;
1460
                else if (size == 385) alt = OV511PLUS_ALT_SIZE_385;
1461
                else if (size == 513) alt = OV511PLUS_ALT_SIZE_513;
1462
                else if (size == 769) alt = OV511PLUS_ALT_SIZE_769;
1463
                else if (size == 961) alt = OV511PLUS_ALT_SIZE_961;
1464
                else {
1465
                        err("Set packet size: invalid size (%d)", size);
1466
                        return -EINVAL;
1467
                }
1468
        } else {
1469
                err("Set packet size: Invalid bridge type");
1470
                return -EINVAL;
1471
        }
1472
 
1473
        PDEBUG(3, "%d, mult=%d, alt=%d", size, mult, alt);
1474
 
1475
        if (reg_w(ov, R51x_FIFO_PSIZE, mult) < 0)
1476
                return -EIO;
1477
 
1478
        if (usb_set_interface(ov->dev, ov->iface, alt) < 0) {
1479
                err("Set packet size: set interface error");
1480
                return -EBUSY;
1481
        }
1482
 
1483
        if (ov51x_reset(ov, OV511_RESET_NOREGS) < 0)
1484
                return -EIO;
1485
 
1486
        ov->packet_size = size;
1487
 
1488
        if (ov51x_restart(ov) < 0)
1489
                return -EIO;
1490
 
1491
        return 0;
1492
}
1493
 
1494
/* Note: Unlike the OV511/OV511+, the size argument does NOT include the
1495
 * optional packet number byte. The actual size *is* stored in ov->packet_size,
1496
 * though. */
1497
static int
1498
ov518_set_packet_size(struct usb_ov511 *ov, int size)
1499
{
1500
        int alt;
1501
 
1502
        if (ov51x_stop(ov) < 0)
1503
                return -EIO;
1504
 
1505
        if (ov->bclass == BCL_OV518) {
1506
                if (size == 0) alt = OV518_ALT_SIZE_0;
1507
                else if (size == 128) alt = OV518_ALT_SIZE_128;
1508
                else if (size == 256) alt = OV518_ALT_SIZE_256;
1509
                else if (size == 384) alt = OV518_ALT_SIZE_384;
1510
                else if (size == 512) alt = OV518_ALT_SIZE_512;
1511
                else if (size == 640) alt = OV518_ALT_SIZE_640;
1512
                else if (size == 768) alt = OV518_ALT_SIZE_768;
1513
                else if (size == 896) alt = OV518_ALT_SIZE_896;
1514
                else {
1515
                        err("Set packet size: invalid size (%d)", size);
1516
                        return -EINVAL;
1517
                }
1518
        } else {
1519
                err("Set packet size: Invalid bridge type");
1520
                return -EINVAL;
1521
        }
1522
 
1523
        PDEBUG(3, "%d, alt=%d", size, alt);
1524
 
1525
        ov->packet_size = size;
1526
        if (size > 0) {
1527
                /* Program ISO FIFO size reg (packet number isn't included) */
1528
                ov518_reg_w32(ov, 0x30, size, 2);
1529
 
1530
                if (ov->packet_numbering)
1531
                        ++ov->packet_size;
1532
        }
1533
 
1534
        if (usb_set_interface(ov->dev, ov->iface, alt) < 0) {
1535
                err("Set packet size: set interface error");
1536
                return -EBUSY;
1537
        }
1538
 
1539
        /* Initialize the stream */
1540
        if (reg_w(ov, 0x2f, 0x80) < 0)
1541
                return -EIO;
1542
 
1543
        if (ov51x_restart(ov) < 0)
1544
                return -EIO;
1545
 
1546
        if (ov51x_reset(ov, OV511_RESET_NOREGS) < 0)
1547
                return -EIO;
1548
 
1549
        return 0;
1550
}
1551
 
1552
/* Upload compression params and quantization tables. Returns 0 for success. */
1553
static int
1554
ov511_init_compression(struct usb_ov511 *ov)
1555
{
1556
        int rc = 0;
1557
 
1558
        if (!ov->compress_inited) {
1559
                reg_w(ov, 0x70, phy);
1560
                reg_w(ov, 0x71, phuv);
1561
                reg_w(ov, 0x72, pvy);
1562
                reg_w(ov, 0x73, pvuv);
1563
                reg_w(ov, 0x74, qhy);
1564
                reg_w(ov, 0x75, qhuv);
1565
                reg_w(ov, 0x76, qvy);
1566
                reg_w(ov, 0x77, qvuv);
1567
 
1568
                if (ov511_upload_quan_tables(ov) < 0) {
1569
                        err("Error uploading quantization tables");
1570
                        rc = -EIO;
1571
                        goto out;
1572
                }
1573
        }
1574
 
1575
        ov->compress_inited = 1;
1576
out:
1577
        return rc;
1578
}
1579
 
1580
/* Upload compression params and quantization tables. Returns 0 for success. */
1581
static int
1582
ov518_init_compression(struct usb_ov511 *ov)
1583
{
1584
        int rc = 0;
1585
 
1586
        if (!ov->compress_inited) {
1587
                if (ov518_upload_quan_tables(ov) < 0) {
1588
                        err("Error uploading quantization tables");
1589
                        rc = -EIO;
1590
                        goto out;
1591
                }
1592
        }
1593
 
1594
        ov->compress_inited = 1;
1595
out:
1596
        return rc;
1597
}
1598
 
1599
/* -------------------------------------------------------------------------- */
1600
 
1601
/* Sets sensor's contrast setting to "val" */
1602
static int
1603
sensor_set_contrast(struct usb_ov511 *ov, unsigned short val)
1604
{
1605
        int rc;
1606
 
1607
        PDEBUG(3, "%d", val);
1608
 
1609
        if (ov->stop_during_set)
1610
                if (ov51x_stop(ov) < 0)
1611
                        return -EIO;
1612
 
1613
        switch (ov->sensor) {
1614
        case SEN_OV7610:
1615
        case SEN_OV6620:
1616
        {
1617
                rc = i2c_w(ov, OV7610_REG_CNT, val >> 8);
1618
                if (rc < 0)
1619
                        goto out;
1620
                break;
1621
        }
1622
        case SEN_OV6630:
1623
        {
1624
                rc = i2c_w_mask(ov, OV7610_REG_CNT, val >> 12, 0x0f);
1625
                if (rc < 0)
1626
                        goto out;
1627
                break;
1628
        }
1629
        case SEN_OV7620:
1630
        {
1631
                unsigned char ctab[] = {
1632
                        0x01, 0x05, 0x09, 0x11, 0x15, 0x35, 0x37, 0x57,
1633
                        0x5b, 0xa5, 0xa7, 0xc7, 0xc9, 0xcf, 0xef, 0xff
1634
                };
1635
 
1636
                /* Use Y gamma control instead. Bit 0 enables it. */
1637
                rc = i2c_w(ov, 0x64, ctab[val>>12]);
1638
                if (rc < 0)
1639
                        goto out;
1640
                break;
1641
        }
1642
        case SEN_SAA7111A:
1643
        {
1644
                rc = i2c_w(ov, 0x0b, val >> 9);
1645
                if (rc < 0)
1646
                        goto out;
1647
                break;
1648
        }
1649
        default:
1650
        {
1651
                PDEBUG(3, "Unsupported with this sensor");
1652
                rc = -EPERM;
1653
                goto out;
1654
        }
1655
        }
1656
 
1657
        rc = 0;         /* Success */
1658
        ov->contrast = val;
1659
out:
1660
        if (ov51x_restart(ov) < 0)
1661
                return -EIO;
1662
 
1663
        return rc;
1664
}
1665
 
1666
/* Gets sensor's contrast setting */
1667
static int
1668
sensor_get_contrast(struct usb_ov511 *ov, unsigned short *val)
1669
{
1670
        int rc;
1671
 
1672
        switch (ov->sensor) {
1673
        case SEN_OV7610:
1674
        case SEN_OV6620:
1675
                rc = i2c_r(ov, OV7610_REG_CNT);
1676
                if (rc < 0)
1677
                        return rc;
1678
                else
1679
                        *val = rc << 8;
1680
                break;
1681
        case SEN_OV6630:
1682
                rc = i2c_r(ov, OV7610_REG_CNT);
1683
                if (rc < 0)
1684
                        return rc;
1685
                else
1686
                        *val = rc << 12;
1687
                break;
1688
        case SEN_OV7620:
1689
                /* Use Y gamma reg instead. Bit 0 is the enable bit. */
1690
                rc = i2c_r(ov, 0x64);
1691
                if (rc < 0)
1692
                        return rc;
1693
                else
1694
                        *val = (rc & 0xfe) << 8;
1695
                break;
1696
        case SEN_SAA7111A:
1697
                *val = ov->contrast;
1698
                break;
1699
        default:
1700
                PDEBUG(3, "Unsupported with this sensor");
1701
                return -EPERM;
1702
        }
1703
 
1704
        PDEBUG(3, "%d", *val);
1705
        ov->contrast = *val;
1706
 
1707
        return 0;
1708
}
1709
 
1710
/* -------------------------------------------------------------------------- */
1711
 
1712
/* Sets sensor's brightness setting to "val" */
1713
static int
1714
sensor_set_brightness(struct usb_ov511 *ov, unsigned short val)
1715
{
1716
        int rc;
1717
 
1718
        PDEBUG(4, "%d", val);
1719
 
1720
        if (ov->stop_during_set)
1721
                if (ov51x_stop(ov) < 0)
1722
                        return -EIO;
1723
 
1724
        switch (ov->sensor) {
1725
        case SEN_OV7610:
1726
        case SEN_OV76BE:
1727
        case SEN_OV6620:
1728
        case SEN_OV6630:
1729
                rc = i2c_w(ov, OV7610_REG_BRT, val >> 8);
1730
                if (rc < 0)
1731
                        goto out;
1732
                break;
1733
        case SEN_OV7620:
1734
                /* 7620 doesn't like manual changes when in auto mode */
1735
                if (!ov->auto_brt) {
1736
                        rc = i2c_w(ov, OV7610_REG_BRT, val >> 8);
1737
                        if (rc < 0)
1738
                                goto out;
1739
                }
1740
                break;
1741
        case SEN_SAA7111A:
1742
                rc = i2c_w(ov, 0x0a, val >> 8);
1743
                if (rc < 0)
1744
                        goto out;
1745
                break;
1746
        default:
1747
                PDEBUG(3, "Unsupported with this sensor");
1748
                rc = -EPERM;
1749
                goto out;
1750
        }
1751
 
1752
        rc = 0;         /* Success */
1753
        ov->brightness = val;
1754
out:
1755
        if (ov51x_restart(ov) < 0)
1756
                return -EIO;
1757
 
1758
        return rc;
1759
}
1760
 
1761
/* Gets sensor's brightness setting */
1762
static int
1763
sensor_get_brightness(struct usb_ov511 *ov, unsigned short *val)
1764
{
1765
        int rc;
1766
 
1767
        switch (ov->sensor) {
1768
        case SEN_OV7610:
1769
        case SEN_OV76BE:
1770
        case SEN_OV7620:
1771
        case SEN_OV6620:
1772
        case SEN_OV6630:
1773
                rc = i2c_r(ov, OV7610_REG_BRT);
1774
                if (rc < 0)
1775
                        return rc;
1776
                else
1777
                        *val = rc << 8;
1778
                break;
1779
        case SEN_SAA7111A:
1780
                *val = ov->brightness;
1781
                break;
1782
        default:
1783
                PDEBUG(3, "Unsupported with this sensor");
1784
                return -EPERM;
1785
        }
1786
 
1787
        PDEBUG(3, "%d", *val);
1788
        ov->brightness = *val;
1789
 
1790
        return 0;
1791
}
1792
 
1793
/* -------------------------------------------------------------------------- */
1794
 
1795
/* Sets sensor's saturation (color intensity) setting to "val" */
1796
static int
1797
sensor_set_saturation(struct usb_ov511 *ov, unsigned short val)
1798
{
1799
        int rc;
1800
 
1801
        PDEBUG(3, "%d", val);
1802
 
1803
        if (ov->stop_during_set)
1804
                if (ov51x_stop(ov) < 0)
1805
                        return -EIO;
1806
 
1807
        switch (ov->sensor) {
1808
        case SEN_OV7610:
1809
        case SEN_OV76BE:
1810
        case SEN_OV6620:
1811
        case SEN_OV6630:
1812
                rc = i2c_w(ov, OV7610_REG_SAT, val >> 8);
1813
                if (rc < 0)
1814
                        goto out;
1815
                break;
1816
        case SEN_OV7620:
1817
//              /* Use UV gamma control instead. Bits 0 & 7 are reserved. */
1818
//              rc = ov_i2c_write(ov->dev, 0x62, (val >> 9) & 0x7e);
1819
//              if (rc < 0)
1820
//                      goto out;
1821
                rc = i2c_w(ov, OV7610_REG_SAT, val >> 8);
1822
                if (rc < 0)
1823
                        goto out;
1824
                break;
1825
        case SEN_SAA7111A:
1826
                rc = i2c_w(ov, 0x0c, val >> 9);
1827
                if (rc < 0)
1828
                        goto out;
1829
                break;
1830
        default:
1831
                PDEBUG(3, "Unsupported with this sensor");
1832
                rc = -EPERM;
1833
                goto out;
1834
        }
1835
 
1836
        rc = 0;         /* Success */
1837
        ov->colour = val;
1838
out:
1839
        if (ov51x_restart(ov) < 0)
1840
                return -EIO;
1841
 
1842
        return rc;
1843
}
1844
 
1845
/* Gets sensor's saturation (color intensity) setting */
1846
static int
1847
sensor_get_saturation(struct usb_ov511 *ov, unsigned short *val)
1848
{
1849
        int rc;
1850
 
1851
        switch (ov->sensor) {
1852
        case SEN_OV7610:
1853
        case SEN_OV76BE:
1854
        case SEN_OV6620:
1855
        case SEN_OV6630:
1856
                rc = i2c_r(ov, OV7610_REG_SAT);
1857
                if (rc < 0)
1858
                        return rc;
1859
                else
1860
                        *val = rc << 8;
1861
                break;
1862
        case SEN_OV7620:
1863
//              /* Use UV gamma reg instead. Bits 0 & 7 are reserved. */
1864
//              rc = i2c_r(ov, 0x62);
1865
//              if (rc < 0)
1866
//                      return rc;
1867
//              else
1868
//                      *val = (rc & 0x7e) << 9;
1869
                rc = i2c_r(ov, OV7610_REG_SAT);
1870
                if (rc < 0)
1871
                        return rc;
1872
                else
1873
                        *val = rc << 8;
1874
                break;
1875
        case SEN_SAA7111A:
1876
                *val = ov->colour;
1877
                break;
1878
        default:
1879
                PDEBUG(3, "Unsupported with this sensor");
1880
                return -EPERM;
1881
        }
1882
 
1883
        PDEBUG(3, "%d", *val);
1884
        ov->colour = *val;
1885
 
1886
        return 0;
1887
}
1888
 
1889
/* -------------------------------------------------------------------------- */
1890
 
1891
/* Sets sensor's hue (red/blue balance) setting to "val" */
1892
static int
1893
sensor_set_hue(struct usb_ov511 *ov, unsigned short val)
1894
{
1895
        int rc;
1896
 
1897
        PDEBUG(3, "%d", val);
1898
 
1899
        if (ov->stop_during_set)
1900
                if (ov51x_stop(ov) < 0)
1901
                        return -EIO;
1902
 
1903
        switch (ov->sensor) {
1904
        case SEN_OV7610:
1905
        case SEN_OV6620:
1906
        case SEN_OV6630:
1907
                rc = i2c_w(ov, OV7610_REG_RED, 0xFF - (val >> 8));
1908
                if (rc < 0)
1909
                        goto out;
1910
 
1911
                rc = i2c_w(ov, OV7610_REG_BLUE, val >> 8);
1912
                if (rc < 0)
1913
                        goto out;
1914
                break;
1915
        case SEN_OV7620:
1916
// Hue control is causing problems. I will enable it once it's fixed.
1917
#if 0
1918
                rc = i2c_w(ov, 0x7a, (unsigned char)(val >> 8) + 0xb);
1919
                if (rc < 0)
1920
                        goto out;
1921
 
1922
                rc = i2c_w(ov, 0x79, (unsigned char)(val >> 8) + 0xb);
1923
                if (rc < 0)
1924
                        goto out;
1925
#endif
1926
                break;
1927
        case SEN_SAA7111A:
1928
                rc = i2c_w(ov, 0x0d, (val + 32768) >> 8);
1929
                if (rc < 0)
1930
                        goto out;
1931
                break;
1932
        default:
1933
                PDEBUG(3, "Unsupported with this sensor");
1934
                rc = -EPERM;
1935
                goto out;
1936
        }
1937
 
1938
        rc = 0;         /* Success */
1939
        ov->hue = val;
1940
out:
1941
        if (ov51x_restart(ov) < 0)
1942
                return -EIO;
1943
 
1944
        return rc;
1945
}
1946
 
1947
/* Gets sensor's hue (red/blue balance) setting */
1948
static int
1949
sensor_get_hue(struct usb_ov511 *ov, unsigned short *val)
1950
{
1951
        int rc;
1952
 
1953
        switch (ov->sensor) {
1954
        case SEN_OV7610:
1955
        case SEN_OV6620:
1956
        case SEN_OV6630:
1957
                rc = i2c_r(ov, OV7610_REG_BLUE);
1958
                if (rc < 0)
1959
                        return rc;
1960
                else
1961
                        *val = rc << 8;
1962
                break;
1963
        case SEN_OV7620:
1964
                rc = i2c_r(ov, 0x7a);
1965
                if (rc < 0)
1966
                        return rc;
1967
                else
1968
                        *val = rc << 8;
1969
                break;
1970
        case SEN_SAA7111A:
1971
                *val = ov->hue;
1972
                break;
1973
        default:
1974
                PDEBUG(3, "Unsupported with this sensor");
1975
                return -EPERM;
1976
        }
1977
 
1978
        PDEBUG(3, "%d", *val);
1979
        ov->hue = *val;
1980
 
1981
        return 0;
1982
}
1983
 
1984
/* -------------------------------------------------------------------------- */
1985
 
1986
static inline int
1987
sensor_set_picture(struct usb_ov511 *ov, struct video_picture *p)
1988
{
1989
        int rc;
1990
 
1991
        PDEBUG(4, "sensor_set_picture");
1992
 
1993
        ov->whiteness = p->whiteness;
1994
 
1995
        /* Don't return error if a setting is unsupported, or rest of settings
1996
         * will not be performed */
1997
 
1998
        rc = sensor_set_contrast(ov, p->contrast);
1999
        if (FATAL_ERROR(rc))
2000
                return rc;
2001
 
2002
        rc = sensor_set_brightness(ov, p->brightness);
2003
        if (FATAL_ERROR(rc))
2004
                return rc;
2005
 
2006
        rc = sensor_set_saturation(ov, p->colour);
2007
        if (FATAL_ERROR(rc))
2008
                return rc;
2009
 
2010
        rc = sensor_set_hue(ov, p->hue);
2011
        if (FATAL_ERROR(rc))
2012
                return rc;
2013
 
2014
        return 0;
2015
}
2016
 
2017
static inline int
2018
sensor_get_picture(struct usb_ov511 *ov, struct video_picture *p)
2019
{
2020
        int rc;
2021
 
2022
        PDEBUG(4, "sensor_get_picture");
2023
 
2024
        /* Don't return error if a setting is unsupported, or rest of settings
2025
         * will not be performed */
2026
 
2027
        rc = sensor_get_contrast(ov, &(p->contrast));
2028
        if (FATAL_ERROR(rc))
2029
                return rc;
2030
 
2031
        rc = sensor_get_brightness(ov, &(p->brightness));
2032
        if (FATAL_ERROR(rc))
2033
                return rc;
2034
 
2035
        rc = sensor_get_saturation(ov, &(p->colour));
2036
        if (FATAL_ERROR(rc))
2037
                return rc;
2038
 
2039
        rc = sensor_get_hue(ov, &(p->hue));
2040
        if (FATAL_ERROR(rc))
2041
                return rc;
2042
 
2043
        p->whiteness = 105 << 8;
2044
 
2045
        return 0;
2046
}
2047
 
2048
#if defined(CONFIG_PROC_FS) && defined(CONFIG_VIDEO_PROC_FS)
2049
// FIXME: Exposure range is only 0x00-0x7f in interlace mode
2050
/* Sets current exposure for sensor. This only has an effect if auto-exposure
2051
 * is off */
2052
static inline int
2053
sensor_set_exposure(struct usb_ov511 *ov, unsigned char val)
2054
{
2055
        int rc;
2056
 
2057
        PDEBUG(3, "%d", val);
2058
 
2059
        if (ov->stop_during_set)
2060
                if (ov51x_stop(ov) < 0)
2061
                        return -EIO;
2062
 
2063
        switch (ov->sensor) {
2064
        case SEN_OV6620:
2065
        case SEN_OV6630:
2066
        case SEN_OV7610:
2067
        case SEN_OV7620:
2068
        case SEN_OV76BE:
2069
        case SEN_OV8600:
2070
                rc = i2c_w(ov, 0x10, val);
2071
                if (rc < 0)
2072
                        goto out;
2073
 
2074
                break;
2075
        case SEN_KS0127:
2076
        case SEN_KS0127B:
2077
        case SEN_SAA7111A:
2078
                PDEBUG(3, "Unsupported with this sensor");
2079
                return -EPERM;
2080
        default:
2081
                err("Sensor not supported for set_exposure");
2082
                return -EINVAL;
2083
        }
2084
 
2085
        rc = 0;         /* Success */
2086
        ov->exposure = val;
2087
out:
2088
        if (ov51x_restart(ov) < 0)
2089
                return -EIO;
2090
 
2091
        return rc;
2092
}
2093
 
2094
/* Gets current exposure level from sensor, regardless of whether it is under
2095
 * manual control. */
2096
static int
2097
sensor_get_exposure(struct usb_ov511 *ov, unsigned char *val)
2098
{
2099
        int rc;
2100
 
2101
        switch (ov->sensor) {
2102
        case SEN_OV7610:
2103
        case SEN_OV6620:
2104
        case SEN_OV6630:
2105
        case SEN_OV7620:
2106
        case SEN_OV76BE:
2107
        case SEN_OV8600:
2108
                rc = i2c_r(ov, 0x10);
2109
                if (rc < 0)
2110
                        return rc;
2111
                else
2112
                        *val = rc;
2113
                break;
2114
        case SEN_KS0127:
2115
        case SEN_KS0127B:
2116
        case SEN_SAA7111A:
2117
                val = 0;
2118
                PDEBUG(3, "Unsupported with this sensor");
2119
                return -EPERM;
2120
        default:
2121
                err("Sensor not supported for get_exposure");
2122
                return -EINVAL;
2123
        }
2124
 
2125
        PDEBUG(3, "%d", *val);
2126
        ov->exposure = *val;
2127
 
2128
        return 0;
2129
}
2130
#endif /* CONFIG_PROC_FS && CONFIG_VIDEO_PROC_FS */
2131
 
2132
/* Turns on or off the LED. Only has an effect with OV511+/OV518(+) */
2133
static inline void
2134
ov51x_led_control(struct usb_ov511 *ov, int enable)
2135
{
2136
        PDEBUG(4, " (%s)", enable ? "turn on" : "turn off");
2137
 
2138
        if (ov->bridge == BRG_OV511PLUS)
2139
                reg_w(ov, R511_SYS_LED_CTL, enable ? 1 : 0);
2140
        else if (ov->bclass == BCL_OV518)
2141
                reg_w_mask(ov, R518_GPIO_OUT, enable ? 0x02 : 0x00, 0x02);
2142
 
2143
        return;
2144
}
2145
 
2146
/* Matches the sensor's internal frame rate to the lighting frequency.
2147
 * Valid frequencies are:
2148
 *      50 - 50Hz, for European and Asian lighting
2149
 *      60 - 60Hz, for American lighting
2150
 *
2151
 * Tested with: OV7610, OV7620, OV76BE, OV6620
2152
 * Unsupported: KS0127, KS0127B, SAA7111A
2153
 * Returns: 0 for success
2154
 */
2155
static int
2156
sensor_set_light_freq(struct usb_ov511 *ov, int freq)
2157
{
2158
        int sixty;
2159
 
2160
        PDEBUG(4, "%d Hz", freq);
2161
 
2162
        if (freq == 60)
2163
                sixty = 1;
2164
        else if (freq == 50)
2165
                sixty = 0;
2166
        else {
2167
                err("Invalid light freq (%d Hz)", freq);
2168
                return -EINVAL;
2169
        }
2170
 
2171
        switch (ov->sensor) {
2172
        case SEN_OV7610:
2173
                i2c_w_mask(ov, 0x2a, sixty?0x00:0x80, 0x80);
2174
                i2c_w(ov, 0x2b, sixty?0x00:0xac);
2175
                i2c_w_mask(ov, 0x13, 0x10, 0x10);
2176
                i2c_w_mask(ov, 0x13, 0x00, 0x10);
2177
                break;
2178
        case SEN_OV7620:
2179
        case SEN_OV76BE:
2180
        case SEN_OV8600:
2181
                i2c_w_mask(ov, 0x2a, sixty?0x00:0x80, 0x80);
2182
                i2c_w(ov, 0x2b, sixty?0x00:0xac);
2183
                i2c_w_mask(ov, 0x76, 0x01, 0x01);
2184
                break;
2185
        case SEN_OV6620:
2186
        case SEN_OV6630:
2187
                i2c_w(ov, 0x2b, sixty?0xa8:0x28);
2188
                i2c_w(ov, 0x2a, sixty?0x84:0xa4);
2189
                break;
2190
        case SEN_KS0127:
2191
        case SEN_KS0127B:
2192
        case SEN_SAA7111A:
2193
                PDEBUG(5, "Unsupported with this sensor");
2194
                return -EPERM;
2195
        default:
2196
                err("Sensor not supported for set_light_freq");
2197
                return -EINVAL;
2198
        }
2199
 
2200
        ov->lightfreq = freq;
2201
 
2202
        return 0;
2203
}
2204
 
2205
/* If enable is true, turn on the sensor's banding filter, otherwise turn it
2206
 * off. This filter tries to reduce the pattern of horizontal light/dark bands
2207
 * caused by some (usually fluorescent) lighting. The light frequency must be
2208
 * set either before or after enabling it with ov51x_set_light_freq().
2209
 *
2210
 * Tested with: OV7610, OV7620, OV76BE, OV6620.
2211
 * Unsupported: KS0127, KS0127B, SAA7111A
2212
 * Returns: 0 for success
2213
 */
2214
static inline int
2215
sensor_set_banding_filter(struct usb_ov511 *ov, int enable)
2216
{
2217
        int rc;
2218
 
2219
        PDEBUG(4, " (%s)", enable ? "turn on" : "turn off");
2220
 
2221
        if (ov->sensor == SEN_KS0127 || ov->sensor == SEN_KS0127B
2222
                || ov->sensor == SEN_SAA7111A) {
2223
                PDEBUG(5, "Unsupported with this sensor");
2224
                return -EPERM;
2225
        }
2226
 
2227
        rc = i2c_w_mask(ov, 0x2d, enable?0x04:0x00, 0x04);
2228
        if (rc < 0)
2229
                return rc;
2230
 
2231
        ov->bandfilt = enable;
2232
 
2233
        return 0;
2234
}
2235
 
2236
/* If enable is true, turn on the sensor's auto brightness control, otherwise
2237
 * turn it off.
2238
 *
2239
 * Unsupported: KS0127, KS0127B, SAA7111A
2240
 * Returns: 0 for success
2241
 */
2242
static inline int
2243
sensor_set_auto_brightness(struct usb_ov511 *ov, int enable)
2244
{
2245
        int rc;
2246
 
2247
        PDEBUG(4, " (%s)", enable ? "turn on" : "turn off");
2248
 
2249
        if (ov->sensor == SEN_KS0127 || ov->sensor == SEN_KS0127B
2250
                || ov->sensor == SEN_SAA7111A) {
2251
                PDEBUG(5, "Unsupported with this sensor");
2252
                return -EPERM;
2253
        }
2254
 
2255
        rc = i2c_w_mask(ov, 0x2d, enable?0x10:0x00, 0x10);
2256
        if (rc < 0)
2257
                return rc;
2258
 
2259
        ov->auto_brt = enable;
2260
 
2261
        return 0;
2262
}
2263
 
2264
/* If enable is true, turn on the sensor's auto exposure control, otherwise
2265
 * turn it off.
2266
 *
2267
 * Unsupported: KS0127, KS0127B, SAA7111A
2268
 * Returns: 0 for success
2269
 */
2270
static inline int
2271
sensor_set_auto_exposure(struct usb_ov511 *ov, int enable)
2272
{
2273
        PDEBUG(4, " (%s)", enable ? "turn on" : "turn off");
2274
 
2275
        switch (ov->sensor) {
2276
        case SEN_OV7610:
2277
                i2c_w_mask(ov, 0x29, enable?0x00:0x80, 0x80);
2278
                break;
2279
        case SEN_OV6620:
2280
        case SEN_OV7620:
2281
        case SEN_OV76BE:
2282
        case SEN_OV8600:
2283
                i2c_w_mask(ov, 0x13, enable?0x01:0x00, 0x01);
2284
                break;
2285
        case SEN_OV6630:
2286
                i2c_w_mask(ov, 0x28, enable?0x00:0x10, 0x10);
2287
                break;
2288
        case SEN_KS0127:
2289
        case SEN_KS0127B:
2290
        case SEN_SAA7111A:
2291
                PDEBUG(5, "Unsupported with this sensor");
2292
                return -EPERM;
2293
        default:
2294
                err("Sensor not supported for set_auto_exposure");
2295
                return -EINVAL;
2296
        }
2297
 
2298
        ov->auto_exp = enable;
2299
 
2300
        return 0;
2301
}
2302
 
2303
/* Modifies the sensor's exposure algorithm to allow proper exposure of objects
2304
 * that are illuminated from behind.
2305
 *
2306
 * Tested with: OV6620, OV7620
2307
 * Unsupported: OV7610, OV76BE, KS0127, KS0127B, SAA7111A
2308
 * Returns: 0 for success
2309
 */
2310
static int
2311
sensor_set_backlight(struct usb_ov511 *ov, int enable)
2312
{
2313
        PDEBUG(4, " (%s)", enable ? "turn on" : "turn off");
2314
 
2315
        switch (ov->sensor) {
2316
        case SEN_OV7620:
2317
        case SEN_OV8600:
2318
                i2c_w_mask(ov, 0x68, enable?0xe0:0xc0, 0xe0);
2319
                i2c_w_mask(ov, 0x29, enable?0x08:0x00, 0x08);
2320
                i2c_w_mask(ov, 0x28, enable?0x02:0x00, 0x02);
2321
                break;
2322
        case SEN_OV6620:
2323
                i2c_w_mask(ov, 0x4e, enable?0xe0:0xc0, 0xe0);
2324
                i2c_w_mask(ov, 0x29, enable?0x08:0x00, 0x08);
2325
                i2c_w_mask(ov, 0x0e, enable?0x80:0x00, 0x80);
2326
                break;
2327
        case SEN_OV6630:
2328
                i2c_w_mask(ov, 0x4e, enable?0x80:0x60, 0xe0);
2329
                i2c_w_mask(ov, 0x29, enable?0x08:0x00, 0x08);
2330
                i2c_w_mask(ov, 0x28, enable?0x02:0x00, 0x02);
2331
                break;
2332
        case SEN_OV7610:
2333
        case SEN_OV76BE:
2334
        case SEN_KS0127:
2335
        case SEN_KS0127B:
2336
        case SEN_SAA7111A:
2337
                PDEBUG(5, "Unsupported with this sensor");
2338
                return -EPERM;
2339
        default:
2340
                err("Sensor not supported for set_backlight");
2341
                return -EINVAL;
2342
        }
2343
 
2344
        ov->backlight = enable;
2345
 
2346
        return 0;
2347
}
2348
 
2349
static inline int
2350
sensor_set_mirror(struct usb_ov511 *ov, int enable)
2351
{
2352
        PDEBUG(4, " (%s)", enable ? "turn on" : "turn off");
2353
 
2354
        switch (ov->sensor) {
2355
        case SEN_OV6620:
2356
        case SEN_OV6630:
2357
        case SEN_OV7610:
2358
        case SEN_OV7620:
2359
        case SEN_OV76BE:
2360
        case SEN_OV8600:
2361
                i2c_w_mask(ov, 0x12, enable?0x40:0x00, 0x40);
2362
                break;
2363
        case SEN_KS0127:
2364
        case SEN_KS0127B:
2365
        case SEN_SAA7111A:
2366
                PDEBUG(5, "Unsupported with this sensor");
2367
                return -EPERM;
2368
        default:
2369
                err("Sensor not supported for set_mirror");
2370
                return -EINVAL;
2371
        }
2372
 
2373
        ov->mirror = enable;
2374
 
2375
        return 0;
2376
}
2377
 
2378
/* Returns number of bits per pixel (regardless of where they are located;
2379
 * planar or not), or zero for unsupported format.
2380
 */
2381
static inline int
2382
get_depth(int palette)
2383
{
2384
        switch (palette) {
2385
        case VIDEO_PALETTE_GREY:    return 8;
2386
        case VIDEO_PALETTE_YUV420:  return 12;
2387
        case VIDEO_PALETTE_YUV420P: return 12; /* Planar */
2388
        case VIDEO_PALETTE_RGB565:  return 16;
2389
        case VIDEO_PALETTE_RGB24:   return 24;
2390
        case VIDEO_PALETTE_YUV422:  return 16;
2391
        case VIDEO_PALETTE_YUYV:    return 16;
2392
        case VIDEO_PALETTE_YUV422P: return 16; /* Planar */
2393
        default:                    return 0;  /* Invalid format */
2394
        }
2395
}
2396
 
2397
/* Bytes per frame. Used by read(). Return of 0 indicates error */
2398
static inline long int
2399
get_frame_length(struct ov511_frame *frame)
2400
{
2401
        if (!frame)
2402
                return 0;
2403
        else
2404
                return ((frame->width * frame->height
2405
                         * get_depth(frame->format)) >> 3);
2406
}
2407
 
2408
static int
2409
mode_init_ov_sensor_regs(struct usb_ov511 *ov, int width, int height,
2410
                         int mode, int sub_flag, int qvga)
2411
{
2412
        int clock;
2413
 
2414
        /******** Mode (VGA/QVGA) and sensor specific regs ********/
2415
 
2416
        switch (ov->sensor) {
2417
        case SEN_OV7610:
2418
                i2c_w(ov, 0x14, qvga?0x24:0x04);
2419
// FIXME: Does this improve the image quality or frame rate?
2420
#if 0
2421
                i2c_w_mask(ov, 0x28, qvga?0x00:0x20, 0x20);
2422
                i2c_w(ov, 0x24, 0x10);
2423
                i2c_w(ov, 0x25, qvga?0x40:0x8a);
2424
                i2c_w(ov, 0x2f, qvga?0x30:0xb0);
2425
                i2c_w(ov, 0x35, qvga?0x1c:0x9c);
2426
#endif
2427
                break;
2428
        case SEN_OV7620:
2429
//              i2c_w(ov, 0x2b, 0x00);
2430
                i2c_w(ov, 0x14, qvga?0xa4:0x84);
2431
                i2c_w_mask(ov, 0x28, qvga?0x00:0x20, 0x20);
2432
                i2c_w(ov, 0x24, qvga?0x20:0x3a);
2433
                i2c_w(ov, 0x25, qvga?0x30:0x60);
2434
                i2c_w_mask(ov, 0x2d, qvga?0x40:0x00, 0x40);
2435
                i2c_w_mask(ov, 0x67, qvga?0xf0:0x90, 0xf0);
2436
                i2c_w_mask(ov, 0x74, qvga?0x20:0x00, 0x20);
2437
                break;
2438
        case SEN_OV76BE:
2439
//              i2c_w(ov, 0x2b, 0x00);
2440
                i2c_w(ov, 0x14, qvga?0xa4:0x84);
2441
// FIXME: Enable this once 7620AE uses 7620 initial settings
2442
#if 0
2443
                i2c_w_mask(ov, 0x28, qvga?0x00:0x20, 0x20);
2444
                i2c_w(ov, 0x24, qvga?0x20:0x3a);
2445
                i2c_w(ov, 0x25, qvga?0x30:0x60);
2446
                i2c_w_mask(ov, 0x2d, qvga?0x40:0x00, 0x40);
2447
                i2c_w_mask(ov, 0x67, qvga?0xb0:0x90, 0xf0);
2448
                i2c_w_mask(ov, 0x74, qvga?0x20:0x00, 0x20);
2449
#endif
2450
                break;
2451
        case SEN_OV6620:
2452
                i2c_w(ov, 0x14, qvga?0x24:0x04);
2453
                break;
2454
        case SEN_OV6630:
2455
                i2c_w(ov, 0x14, qvga?0xa0:0x80);
2456
                break;
2457
        default:
2458
                err("Invalid sensor");
2459
                return -EINVAL;
2460
        }
2461
 
2462
        /******** Palette-specific regs ********/
2463
 
2464
        if (mode == VIDEO_PALETTE_GREY) {
2465
                if (ov->sensor == SEN_OV7610 || ov->sensor == SEN_OV76BE) {
2466
                        /* these aren't valid on the OV6620/OV7620/6630? */
2467
                        i2c_w_mask(ov, 0x0e, 0x40, 0x40);
2468
                }
2469
 
2470
                if (ov->sensor == SEN_OV6630 && ov->bridge == BRG_OV518
2471
                    && ov518_color) {
2472
                        i2c_w_mask(ov, 0x12, 0x00, 0x10);
2473
                        i2c_w_mask(ov, 0x13, 0x00, 0x20);
2474
                } else {
2475
                        i2c_w_mask(ov, 0x13, 0x20, 0x20);
2476
                }
2477
        } else {
2478
                if (ov->sensor == SEN_OV7610 || ov->sensor == SEN_OV76BE) {
2479
                        /* not valid on the OV6620/OV7620/6630? */
2480
                        i2c_w_mask(ov, 0x0e, 0x00, 0x40);
2481
                }
2482
 
2483
                /* The OV518 needs special treatment. Although both the OV518
2484
                 * and the OV6630 support a 16-bit video bus, only the 8 bit Y
2485
                 * bus is actually used. The UV bus is tied to ground.
2486
                 * Therefore, the OV6630 needs to be in 8-bit multiplexed
2487
                 * output mode */
2488
 
2489
                if (ov->sensor == SEN_OV6630 && ov->bridge == BRG_OV518
2490
                    && ov518_color) {
2491
                        i2c_w_mask(ov, 0x12, 0x10, 0x10);
2492
                        i2c_w_mask(ov, 0x13, 0x20, 0x20);
2493
                } else {
2494
                        i2c_w_mask(ov, 0x13, 0x00, 0x20);
2495
                }
2496
        }
2497
 
2498
        /******** Clock programming ********/
2499
 
2500
        // FIXME: Test this with OV6630
2501
 
2502
        /* The OV6620 needs special handling. This prevents the
2503
         * severe banding that normally occurs */
2504
        if (ov->sensor == SEN_OV6620 || ov->sensor == SEN_OV6630)
2505
        {
2506
                /* Clock down */
2507
 
2508
                i2c_w(ov, 0x2a, 0x04);
2509
 
2510
                if (ov->compress) {
2511
//                      clock = 0;    /* This ensures the highest frame rate */
2512
                        clock = 3;
2513
                } else if (clockdiv == -1) {   /* If user didn't override it */
2514
                        clock = 3;    /* Gives better exposure time */
2515
                } else {
2516
                        clock = clockdiv;
2517
                }
2518
 
2519
                PDEBUG(4, "Setting clock divisor to %d", clock);
2520
 
2521
                i2c_w(ov, 0x11, clock);
2522
 
2523
                i2c_w(ov, 0x2a, 0x84);
2524
                /* This next setting is critical. It seems to improve
2525
                 * the gain or the contrast. The "reserved" bits seem
2526
                 * to have some effect in this case. */
2527
                i2c_w(ov, 0x2d, 0x85);
2528
        }
2529
        else
2530
        {
2531
                if (ov->compress) {
2532
                        clock = 1;    /* This ensures the highest frame rate */
2533
                } else if (clockdiv == -1) {   /* If user didn't override it */
2534
                        /* Calculate and set the clock divisor */
2535
                        clock = ((sub_flag ? ov->subw * ov->subh
2536
                                  : width * height)
2537
                                 * (mode == VIDEO_PALETTE_GREY ? 2 : 3) / 2)
2538
                                 / 66000;
2539
                } else {
2540
                        clock = clockdiv;
2541
                }
2542
 
2543
                PDEBUG(4, "Setting clock divisor to %d", clock);
2544
 
2545
                i2c_w(ov, 0x11, clock);
2546
        }
2547
 
2548
        /******** Special Features ********/
2549
 
2550
        if (framedrop >= 0)
2551
                i2c_w(ov, 0x16, framedrop);
2552
 
2553
        /* Test Pattern */
2554
        i2c_w_mask(ov, 0x12, (testpat?0x02:0x00), 0x02);
2555
 
2556
        /* Enable auto white balance */
2557
        i2c_w_mask(ov, 0x12, 0x04, 0x04);
2558
 
2559
        // This will go away as soon as ov51x_mode_init_sensor_regs()
2560
        // is fully tested.
2561
        /* 7620/6620/6630? don't have register 0x35, so play it safe */
2562
        if (ov->sensor == SEN_OV7610 || ov->sensor == SEN_OV76BE) {
2563
                if (width == 640 && height == 480)
2564
                        i2c_w(ov, 0x35, 0x9e);
2565
                else
2566
                        i2c_w(ov, 0x35, 0x1e);
2567
        }
2568
 
2569
        return 0;
2570
}
2571
 
2572
static int
2573
set_ov_sensor_window(struct usb_ov511 *ov, int width, int height, int mode,
2574
                     int sub_flag)
2575
{
2576
        int ret;
2577
        int hwsbase, hwebase, vwsbase, vwebase, hwsize, vwsize;
2578
        int hoffset, voffset, hwscale = 0, vwscale = 0;
2579
 
2580
        /* The different sensor ICs handle setting up of window differently.
2581
         * IF YOU SET IT WRONG, YOU WILL GET ALL ZERO ISOC DATA FROM OV51x!!! */
2582
        switch (ov->sensor) {
2583
        case SEN_OV7610:
2584
        case SEN_OV76BE:
2585
                hwsbase = 0x38;
2586
                hwebase = 0x3a;
2587
                vwsbase = vwebase = 0x05;
2588
                break;
2589
        case SEN_OV6620:
2590
        case SEN_OV6630:
2591
                hwsbase = 0x38;
2592
                hwebase = 0x3a;
2593
                vwsbase = 0x05;
2594
                vwebase = 0x06;
2595
                break;
2596
        case SEN_OV7620:
2597
                hwsbase = 0x2f;         /* From 7620.SET (spec is wrong) */
2598
                hwebase = 0x2f;
2599
                vwsbase = vwebase = 0x05;
2600
                break;
2601
        default:
2602
                err("Invalid sensor");
2603
                return -EINVAL;
2604
        }
2605
 
2606
        if (ov->sensor == SEN_OV6620 || ov->sensor == SEN_OV6630) {
2607
                /* Note: OV518(+) does downsample on its own) */
2608
                if ((width > 176 && height > 144)
2609
                    || ov->bclass == BCL_OV518) {  /* CIF */
2610
                        ret = mode_init_ov_sensor_regs(ov, width, height,
2611
                                mode, sub_flag, 0);
2612
                        if (ret < 0)
2613
                                return ret;
2614
                        hwscale = 1;
2615
                        vwscale = 1;  /* The datasheet says 0; it's wrong */
2616
                        hwsize = 352;
2617
                        vwsize = 288;
2618
                } else if (width > 176 || height > 144) {
2619
                        err("Illegal dimensions");
2620
                        return -EINVAL;
2621
                } else {                            /* QCIF */
2622
                        ret = mode_init_ov_sensor_regs(ov, width, height,
2623
                                mode, sub_flag, 1);
2624
                        if (ret < 0)
2625
                                return ret;
2626
                        hwsize = 176;
2627
                        vwsize = 144;
2628
                }
2629
        } else {
2630
                if (width > 320 && height > 240) {  /* VGA */
2631
                        ret = mode_init_ov_sensor_regs(ov, width, height,
2632
                                mode, sub_flag, 0);
2633
                        if (ret < 0)
2634
                                return ret;
2635
                        hwscale = 2;
2636
                        vwscale = 1;
2637
                        hwsize = 640;
2638
                        vwsize = 480;
2639
                } else if (width > 320 || height > 240) {
2640
                        err("Illegal dimensions");
2641
                        return -EINVAL;
2642
                } else {                            /* QVGA */
2643
                        ret = mode_init_ov_sensor_regs(ov, width, height,
2644
                                mode, sub_flag, 1);
2645
                        if (ret < 0)
2646
                                return ret;
2647
                        hwscale = 1;
2648
                        hwsize = 320;
2649
                        vwsize = 240;
2650
                }
2651
        }
2652
 
2653
        /* Center the window */
2654
        hoffset = ((hwsize - width) / 2) >> hwscale;
2655
        voffset = ((vwsize - height) / 2) >> vwscale;
2656
 
2657
        /* FIXME! - This needs to be changed to support 160x120 and 6620!!! */
2658
        if (sub_flag) {
2659
                i2c_w(ov, 0x17, hwsbase+(ov->subx>>hwscale));
2660
                i2c_w(ov, 0x18, hwebase+((ov->subx+ov->subw)>>hwscale));
2661
                i2c_w(ov, 0x19, vwsbase+(ov->suby>>vwscale));
2662
                i2c_w(ov, 0x1a, vwebase+((ov->suby+ov->subh)>>vwscale));
2663
        } else {
2664
                i2c_w(ov, 0x17, hwsbase + hoffset);
2665
                i2c_w(ov, 0x18, hwebase + hoffset + (hwsize>>hwscale));
2666
                i2c_w(ov, 0x19, vwsbase + voffset);
2667
                i2c_w(ov, 0x1a, vwebase + voffset + (vwsize>>vwscale));
2668
        }
2669
 
2670
#ifdef OV511_DEBUG
2671
        if (dump_sensor)
2672
                dump_i2c_regs(ov);
2673
#endif
2674
 
2675
        return 0;
2676
}
2677
 
2678
/* Set up the OV511/OV511+ with the given image parameters.
2679
 *
2680
 * Do not put any sensor-specific code in here (including I2C I/O functions)
2681
 */
2682
static int
2683
ov511_mode_init_regs(struct usb_ov511 *ov,
2684
                     int width, int height, int mode, int sub_flag)
2685
{
2686
        int hsegs, vsegs;
2687
 
2688
        if (sub_flag) {
2689
                width = ov->subw;
2690
                height = ov->subh;
2691
        }
2692
 
2693
        PDEBUG(3, "width:%d, height:%d, mode:%d, sub:%d",
2694
               width, height, mode, sub_flag);
2695
 
2696
        // FIXME: This should be moved to a 7111a-specific function once
2697
        // subcapture is dealt with properly
2698
        if (ov->sensor == SEN_SAA7111A) {
2699
                if (width == 320 && height == 240) {
2700
                        /* No need to do anything special */
2701
                } else if (width == 640 && height == 480) {
2702
                        /* Set the OV511 up as 320x480, but keep the
2703
                         * V4L resolution as 640x480 */
2704
                        width = 320;
2705
                } else {
2706
                        err("SAA7111A only allows 320x240 or 640x480");
2707
                        return -EINVAL;
2708
                }
2709
        }
2710
 
2711
        /* Make sure width and height are a multiple of 8 */
2712
        if (width % 8 || height % 8) {
2713
                err("Invalid size (%d, %d) (mode = %d)", width, height, mode);
2714
                return -EINVAL;
2715
        }
2716
 
2717
        if (width < ov->minwidth || height < ov->minheight) {
2718
                err("Requested dimensions are too small");
2719
                return -EINVAL;
2720
        }
2721
 
2722
        if (ov51x_stop(ov) < 0)
2723
                return -EIO;
2724
 
2725
        if (mode == VIDEO_PALETTE_GREY) {
2726
                reg_w(ov, R511_CAM_UV_EN, 0x00);
2727
                reg_w(ov, R511_SNAP_UV_EN, 0x00);
2728
                reg_w(ov, R511_SNAP_OPTS, 0x01);
2729
        } else {
2730
                reg_w(ov, R511_CAM_UV_EN, 0x01);
2731
                reg_w(ov, R511_SNAP_UV_EN, 0x01);
2732
                reg_w(ov, R511_SNAP_OPTS, 0x03);
2733
        }
2734
 
2735
        /* Here I'm assuming that snapshot size == image size.
2736
         * I hope that's always true. --claudio
2737
         */
2738
        hsegs = (width >> 3) - 1;
2739
        vsegs = (height >> 3) - 1;
2740
 
2741
        reg_w(ov, R511_CAM_PXCNT, hsegs);
2742
        reg_w(ov, R511_CAM_LNCNT, vsegs);
2743
        reg_w(ov, R511_CAM_PXDIV, 0x00);
2744
        reg_w(ov, R511_CAM_LNDIV, 0x00);
2745
 
2746
        /* YUV420, low pass filter on */
2747
        reg_w(ov, R511_CAM_OPTS, 0x03);
2748
 
2749
        /* Snapshot additions */
2750
        reg_w(ov, R511_SNAP_PXCNT, hsegs);
2751
        reg_w(ov, R511_SNAP_LNCNT, vsegs);
2752
        reg_w(ov, R511_SNAP_PXDIV, 0x00);
2753
        reg_w(ov, R511_SNAP_LNDIV, 0x00);
2754
 
2755
        if (ov->compress) {
2756
                /* Enable Y and UV quantization and compression */
2757
                reg_w(ov, R511_COMP_EN, 0x07);
2758
                reg_w(ov, R511_COMP_LUT_EN, 0x03);
2759
                ov51x_reset(ov, OV511_RESET_OMNICE);
2760
        }
2761
 
2762
        if (ov51x_restart(ov) < 0)
2763
                return -EIO;
2764
 
2765
        return 0;
2766
}
2767
 
2768
/* Sets up the OV518/OV518+ with the given image parameters
2769
 *
2770
 * OV518 needs a completely different approach, until we can figure out what
2771
 * the individual registers do. Also, only 15 FPS is supported now.
2772
 *
2773
 * Do not put any sensor-specific code in here (including I2C I/O functions)
2774
 */
2775
static int
2776
ov518_mode_init_regs(struct usb_ov511 *ov,
2777
                     int width, int height, int mode, int sub_flag)
2778
{
2779
        int hsegs, vsegs, hi_res;
2780
 
2781
        if (sub_flag) {
2782
                width = ov->subw;
2783
                height = ov->subh;
2784
        }
2785
 
2786
        PDEBUG(3, "width:%d, height:%d, mode:%d, sub:%d",
2787
               width, height, mode, sub_flag);
2788
 
2789
        if (width % 16 || height % 8) {
2790
                err("Invalid size (%d, %d)", width, height);
2791
                return -EINVAL;
2792
        }
2793
 
2794
        if (width < ov->minwidth || height < ov->minheight) {
2795
                err("Requested dimensions are too small");
2796
                return -EINVAL;
2797
        }
2798
 
2799
        if (width >= 320 && height >= 240) {
2800
                hi_res = 1;
2801
        } else if (width >= 320 || height >= 240) {
2802
                err("Invalid width/height combination (%d, %d)", width, height);
2803
                return -EINVAL;
2804
        } else {
2805
                hi_res = 0;
2806
        }
2807
 
2808
        if (ov51x_stop(ov) < 0)
2809
                return -EIO;
2810
 
2811
        /******** Set the mode ********/
2812
 
2813
        reg_w(ov, 0x2b, 0);
2814
        reg_w(ov, 0x2c, 0);
2815
        reg_w(ov, 0x2d, 0);
2816
        reg_w(ov, 0x2e, 0);
2817
        reg_w(ov, 0x3b, 0);
2818
        reg_w(ov, 0x3c, 0);
2819
        reg_w(ov, 0x3d, 0);
2820
        reg_w(ov, 0x3e, 0);
2821
 
2822
        if (ov->bridge == BRG_OV518 && ov518_color) {
2823
                /* OV518 needs U and V swapped */
2824
                i2c_w_mask(ov, 0x15, 0x00, 0x01);
2825
 
2826
                if (mode == VIDEO_PALETTE_GREY) {
2827
                        /* Set 16-bit input format (UV data are ignored) */
2828
                        reg_w_mask(ov, 0x20, 0x00, 0x08);
2829
 
2830
                        /* Set 8-bit (4:0:0) output format */
2831
                        reg_w_mask(ov, 0x28, 0x00, 0xf0);
2832
                        reg_w_mask(ov, 0x38, 0x00, 0xf0);
2833
                } else {
2834
                        /* Set 8-bit (YVYU) input format */
2835
                        reg_w_mask(ov, 0x20, 0x08, 0x08);
2836
 
2837
                        /* Set 12-bit (4:2:0) output format */
2838
                        reg_w_mask(ov, 0x28, 0x80, 0xf0);
2839
                        reg_w_mask(ov, 0x38, 0x80, 0xf0);
2840
                }
2841
        } else {
2842
                reg_w(ov, 0x28, (mode == VIDEO_PALETTE_GREY) ? 0x00:0x80);
2843
                reg_w(ov, 0x38, (mode == VIDEO_PALETTE_GREY) ? 0x00:0x80);
2844
        }
2845
 
2846
        hsegs = width / 16;
2847
        vsegs = height / 4;
2848
 
2849
        reg_w(ov, 0x29, hsegs);
2850
        reg_w(ov, 0x2a, vsegs);
2851
 
2852
        reg_w(ov, 0x39, hsegs);
2853
        reg_w(ov, 0x3a, vsegs);
2854
 
2855
        /* Windows driver does this here; who knows why */
2856
        reg_w(ov, 0x2f, 0x80);
2857
 
2858
        /******** Set the framerate (to 15 FPS) ********/
2859
 
2860
        /* Mode independent, but framerate dependent, regs */
2861
        reg_w(ov, 0x51, 0x02);  /* Clock divider; lower==faster */
2862
        reg_w(ov, 0x22, 0x18);
2863
        reg_w(ov, 0x23, 0xff);
2864
 
2865
        if (ov->bridge == BRG_OV518PLUS)
2866
                reg_w(ov, 0x21, 0x19);
2867
        else
2868
                reg_w(ov, 0x71, 0x19);  /* Compression-related? */
2869
 
2870
        // FIXME: Sensor-specific
2871
        /* Bit 5 is what matters here. Of course, it is "reserved" */
2872
        i2c_w(ov, 0x54, 0x23);
2873
 
2874
        reg_w(ov, 0x2f, 0x80);
2875
 
2876
        if (ov->bridge == BRG_OV518PLUS) {
2877
                reg_w(ov, 0x24, 0x94);
2878
                reg_w(ov, 0x25, 0x90);
2879
                ov518_reg_w32(ov, 0xc4,    400, 2);     /* 190h   */
2880
                ov518_reg_w32(ov, 0xc6,    540, 2);     /* 21ch   */
2881
                ov518_reg_w32(ov, 0xc7,    540, 2);     /* 21ch   */
2882
                ov518_reg_w32(ov, 0xc8,    108, 2);     /* 6ch    */
2883
                ov518_reg_w32(ov, 0xca, 131098, 3);     /* 2001ah */
2884
                ov518_reg_w32(ov, 0xcb,    532, 2);     /* 214h   */
2885
                ov518_reg_w32(ov, 0xcc,   2400, 2);     /* 960h   */
2886
                ov518_reg_w32(ov, 0xcd,     32, 2);     /* 20h    */
2887
                ov518_reg_w32(ov, 0xce,    608, 2);     /* 260h   */
2888
        } else {
2889
                reg_w(ov, 0x24, 0x9f);
2890
                reg_w(ov, 0x25, 0x90);
2891
                ov518_reg_w32(ov, 0xc4,    400, 2);     /* 190h   */
2892
                ov518_reg_w32(ov, 0xc6,    500, 2);     /* 1f4h   */
2893
                ov518_reg_w32(ov, 0xc7,    500, 2);     /* 1f4h   */
2894
                ov518_reg_w32(ov, 0xc8,    142, 2);     /* 8eh    */
2895
                ov518_reg_w32(ov, 0xca, 131098, 3);     /* 2001ah */
2896
                ov518_reg_w32(ov, 0xcb,    532, 2);     /* 214h   */
2897
                ov518_reg_w32(ov, 0xcc,   2000, 2);     /* 7d0h   */
2898
                ov518_reg_w32(ov, 0xcd,     32, 2);     /* 20h    */
2899
                ov518_reg_w32(ov, 0xce,    608, 2);     /* 260h   */
2900
        }
2901
 
2902
        reg_w(ov, 0x2f, 0x80);
2903
 
2904
        if (ov51x_restart(ov) < 0)
2905
                return -EIO;
2906
 
2907
        /* Reset it just for good measure */
2908
        if (ov51x_reset(ov, OV511_RESET_NOREGS) < 0)
2909
                return -EIO;
2910
 
2911
        return 0;
2912
}
2913
 
2914
/* This is a wrapper around the OV511, OV518, and sensor specific functions */
2915
static int
2916
mode_init_regs(struct usb_ov511 *ov,
2917
               int width, int height, int mode, int sub_flag)
2918
{
2919
        int rc = 0;
2920
 
2921
        if (!ov || !ov->dev)
2922
                return -EFAULT;
2923
 
2924
        if (ov->bclass == BCL_OV518) {
2925
                rc = ov518_mode_init_regs(ov, width, height, mode, sub_flag);
2926
        } else {
2927
                rc = ov511_mode_init_regs(ov, width, height, mode, sub_flag);
2928
        }
2929
 
2930
        if (FATAL_ERROR(rc))
2931
                return rc;
2932
 
2933
        switch (ov->sensor) {
2934
        case SEN_OV7610:
2935
        case SEN_OV7620:
2936
        case SEN_OV76BE:
2937
        case SEN_OV8600:
2938
        case SEN_OV6620:
2939
        case SEN_OV6630:
2940
                rc = set_ov_sensor_window(ov, width, height, mode, sub_flag);
2941
                break;
2942
        case SEN_KS0127:
2943
        case SEN_KS0127B:
2944
                err("KS0127-series decoders not supported yet");
2945
                rc = -EINVAL;
2946
                break;
2947
        case SEN_SAA7111A:
2948
//              rc = mode_init_saa_sensor_regs(ov, width, height, mode,
2949
//                                             sub_flag);
2950
 
2951
                PDEBUG(1, "SAA status = 0x%02X", i2c_r(ov, 0x1f));
2952
                break;
2953
        default:
2954
                err("Unknown sensor");
2955
                rc = -EINVAL;
2956
        }
2957
 
2958
        if (FATAL_ERROR(rc))
2959
                return rc;
2960
 
2961
        /* Sensor-independent settings */
2962
        rc = sensor_set_auto_brightness(ov, ov->auto_brt);
2963
        if (FATAL_ERROR(rc))
2964
                return rc;
2965
 
2966
        rc = sensor_set_auto_exposure(ov, ov->auto_exp);
2967
        if (FATAL_ERROR(rc))
2968
                return rc;
2969
 
2970
        rc = sensor_set_banding_filter(ov, bandingfilter);
2971
        if (FATAL_ERROR(rc))
2972
                return rc;
2973
 
2974
        if (ov->lightfreq) {
2975
                rc = sensor_set_light_freq(ov, lightfreq);
2976
                if (FATAL_ERROR(rc))
2977
                        return rc;
2978
        }
2979
 
2980
        rc = sensor_set_backlight(ov, ov->backlight);
2981
        if (FATAL_ERROR(rc))
2982
                return rc;
2983
 
2984
        rc = sensor_set_mirror(ov, ov->mirror);
2985
        if (FATAL_ERROR(rc))
2986
                return rc;
2987
 
2988
        return 0;
2989
}
2990
 
2991
/* This sets the default image parameters. This is useful for apps that use
2992
 * read() and do not set these.
2993
 */
2994
static int
2995
ov51x_set_default_params(struct usb_ov511 *ov)
2996
{
2997
        int i;
2998
 
2999
        /* Set default sizes in case IOCTL (VIDIOCMCAPTURE) is not used
3000
         * (using read() instead). */
3001
        for (i = 0; i < OV511_NUMFRAMES; i++) {
3002
                ov->frame[i].width = ov->maxwidth;
3003
                ov->frame[i].height = ov->maxheight;
3004
                ov->frame[i].bytes_read = 0;
3005
                if (force_palette)
3006
                        ov->frame[i].format = force_palette;
3007
                else
3008
                        ov->frame[i].format = VIDEO_PALETTE_RGB24;
3009
 
3010
                ov->frame[i].depth = get_depth(ov->frame[i].format);
3011
        }
3012
 
3013
        PDEBUG(3, "%dx%d, %s", ov->maxwidth, ov->maxheight,
3014
               symbolic(v4l1_plist, ov->frame[0].format));
3015
 
3016
        /* Initialize to max width/height, YUV420 or RGB24 (if supported) */
3017
        if (mode_init_regs(ov, ov->maxwidth, ov->maxheight,
3018
                           ov->frame[0].format, 0) < 0)
3019
                return -EINVAL;
3020
 
3021
        return 0;
3022
}
3023
 
3024
/**********************************************************************
3025
 *
3026
 * Video decoder stuff
3027
 *
3028
 **********************************************************************/
3029
 
3030
/* Set analog input port of decoder */
3031
static int
3032
decoder_set_input(struct usb_ov511 *ov, int input)
3033
{
3034
        PDEBUG(4, "port %d", input);
3035
 
3036
        switch (ov->sensor) {
3037
        case SEN_SAA7111A:
3038
        {
3039
                /* Select mode */
3040
                i2c_w_mask(ov, 0x02, input, 0x07);
3041
                /* Bypass chrominance trap for modes 4..7 */
3042
                i2c_w_mask(ov, 0x09, (input > 3) ? 0x80:0x00, 0x80);
3043
                break;
3044
        }
3045
        default:
3046
                return -EINVAL;
3047
        }
3048
 
3049
        return 0;
3050
}
3051
 
3052
/* Get ASCII name of video input */
3053
static int
3054
decoder_get_input_name(struct usb_ov511 *ov, int input, char *name)
3055
{
3056
        switch (ov->sensor) {
3057
        case SEN_SAA7111A:
3058
        {
3059
                if (input < 0 || input > 7)
3060
                        return -EINVAL;
3061
                else if (input < 4)
3062
                        sprintf(name, "CVBS-%d", input);
3063
                else // if (input < 8)
3064
                        sprintf(name, "S-Video-%d", input - 4);
3065
                break;
3066
        }
3067
        default:
3068
                sprintf(name, "%s", "Camera");
3069
        }
3070
 
3071
        return 0;
3072
}
3073
 
3074
/* Set norm (NTSC, PAL, SECAM, AUTO) */
3075
static int
3076
decoder_set_norm(struct usb_ov511 *ov, int norm)
3077
{
3078
        PDEBUG(4, "%d", norm);
3079
 
3080
        switch (ov->sensor) {
3081
        case SEN_SAA7111A:
3082
        {
3083
                int reg_8, reg_e;
3084
 
3085
                if (norm == VIDEO_MODE_NTSC) {
3086
                        reg_8 = 0x40;   /* 60 Hz */
3087
                        reg_e = 0x00;   /* NTSC M / PAL BGHI */
3088
                } else if (norm == VIDEO_MODE_PAL) {
3089
                        reg_8 = 0x00;   /* 50 Hz */
3090
                        reg_e = 0x00;   /* NTSC M / PAL BGHI */
3091
                } else if (norm == VIDEO_MODE_AUTO) {
3092
                        reg_8 = 0x80;   /* Auto field detect */
3093
                        reg_e = 0x00;   /* NTSC M / PAL BGHI */
3094
                } else if (norm == VIDEO_MODE_SECAM) {
3095
                        reg_8 = 0x00;   /* 50 Hz */
3096
                        reg_e = 0x50;   /* SECAM / PAL 4.43 */
3097
                } else {
3098
                        return -EINVAL;
3099
                }
3100
 
3101
                i2c_w_mask(ov, 0x08, reg_8, 0xc0);
3102
                i2c_w_mask(ov, 0x0e, reg_e, 0x70);
3103
                break;
3104
        }
3105
        default:
3106
                return -EINVAL;
3107
        }
3108
 
3109
        return 0;
3110
}
3111
 
3112
/**********************************************************************
3113
 *
3114
 * Color correction functions
3115
 *
3116
 **********************************************************************/
3117
 
3118
/*
3119
 * Turn a YUV4:2:0 block into an RGB block
3120
 *
3121
 * Video4Linux seems to use the blue, green, red channel
3122
 * order convention-- rgb[0] is blue, rgb[1] is green, rgb[2] is red.
3123
 *
3124
 * Color space conversion coefficients taken from the excellent
3125
 * http://www.inforamp.net/~poynton/ColorFAQ.html
3126
 * In his terminology, this is a CCIR 601.1 YCbCr -> RGB.
3127
 * Y values are given for all 4 pixels, but the U (Pb)
3128
 * and V (Pr) are assumed constant over the 2x2 block.
3129
 *
3130
 * To avoid floating point arithmetic, the color conversion
3131
 * coefficients are scaled into 16.16 fixed-point integers.
3132
 * They were determined as follows:
3133
 *
3134
 *      double brightness = 1.0;  (0->black; 1->full scale)
3135
 *      double saturation = 1.0;  (0->greyscale; 1->full color)
3136
 *      double fixScale = brightness * 256 * 256;
3137
 *      int rvScale = (int)(1.402 * saturation * fixScale);
3138
 *      int guScale = (int)(-0.344136 * saturation * fixScale);
3139
 *      int gvScale = (int)(-0.714136 * saturation * fixScale);
3140
 *      int buScale = (int)(1.772 * saturation * fixScale);
3141
 *      int yScale = (int)(fixScale);
3142
 */
3143
 
3144
/* LIMIT: convert a 16.16 fixed-point value to a byte, with clipping. */
3145
#define LIMIT(x) ((x)>0xffffff?0xff: ((x)<=0xffff?0:((x)>>16)))
3146
 
3147
static inline void
3148
move_420_block(int yTL, int yTR, int yBL, int yBR, int u, int v,
3149
               int rowPixels, unsigned char * rgb, int bits)
3150
{
3151
        const int rvScale = 91881;
3152
        const int guScale = -22553;
3153
        const int gvScale = -46801;
3154
        const int buScale = 116129;
3155
        const int yScale  = 65536;
3156
        int r, g, b;
3157
 
3158
        g = guScale * u + gvScale * v;
3159
        if (force_rgb) {
3160
                r = buScale * u;
3161
                b = rvScale * v;
3162
        } else {
3163
                r = rvScale * v;
3164
                b = buScale * u;
3165
        }
3166
 
3167
        yTL *= yScale; yTR *= yScale;
3168
        yBL *= yScale; yBR *= yScale;
3169
 
3170
        if (bits == 24) {
3171
                /* Write out top two pixels */
3172
                rgb[0] = LIMIT(b+yTL); rgb[1] = LIMIT(g+yTL);
3173
                rgb[2] = LIMIT(r+yTL);
3174
 
3175
                rgb[3] = LIMIT(b+yTR); rgb[4] = LIMIT(g+yTR);
3176
                rgb[5] = LIMIT(r+yTR);
3177
 
3178
                /* Skip down to next line to write out bottom two pixels */
3179
                rgb += 3 * rowPixels;
3180
                rgb[0] = LIMIT(b+yBL); rgb[1] = LIMIT(g+yBL);
3181
                rgb[2] = LIMIT(r+yBL);
3182
 
3183
                rgb[3] = LIMIT(b+yBR); rgb[4] = LIMIT(g+yBR);
3184
                rgb[5] = LIMIT(r+yBR);
3185
        } else if (bits == 16) {
3186
                /* Write out top two pixels */
3187
                rgb[0] = ((LIMIT(b+yTL) >> 3) & 0x1F)
3188
                        | ((LIMIT(g+yTL) << 3) & 0xE0);
3189
                rgb[1] = ((LIMIT(g+yTL) >> 5) & 0x07)
3190
                        | (LIMIT(r+yTL) & 0xF8);
3191
 
3192
                rgb[2] = ((LIMIT(b+yTR) >> 3) & 0x1F)
3193
                        | ((LIMIT(g+yTR) << 3) & 0xE0);
3194
                rgb[3] = ((LIMIT(g+yTR) >> 5) & 0x07)
3195
                        | (LIMIT(r+yTR) & 0xF8);
3196
 
3197
                /* Skip down to next line to write out bottom two pixels */
3198
                rgb += 2 * rowPixels;
3199
 
3200
                rgb[0] = ((LIMIT(b+yBL) >> 3) & 0x1F)
3201
                        | ((LIMIT(g+yBL) << 3) & 0xE0);
3202
                rgb[1] = ((LIMIT(g+yBL) >> 5) & 0x07)
3203
                        | (LIMIT(r+yBL) & 0xF8);
3204
 
3205
                rgb[2] = ((LIMIT(b+yBR) >> 3) & 0x1F)
3206
                        | ((LIMIT(g+yBR) << 3) & 0xE0);
3207
                rgb[3] = ((LIMIT(g+yBR) >> 5) & 0x07)
3208
                        | (LIMIT(r+yBR) & 0xF8);
3209
        }
3210
}
3211
 
3212
/**********************************************************************
3213
 *
3214
 * Raw data parsing
3215
 *
3216
 **********************************************************************/
3217
 
3218
/* Copies a 64-byte segment at pIn to an 8x8 block at pOut. The width of the
3219
 * image at pOut is specified by w.
3220
 */
3221
static inline void
3222
make_8x8(unsigned char *pIn, unsigned char *pOut, int w)
3223
{
3224
        unsigned char *pOut1 = pOut;
3225
        int x, y;
3226
 
3227
        for (y = 0; y < 8; y++) {
3228
                pOut1 = pOut;
3229
                for (x = 0; x < 8; x++) {
3230
                        *pOut1++ = *pIn++;
3231
                }
3232
                pOut += w;
3233
        }
3234
}
3235
 
3236
/*
3237
 * For RAW BW (YUV 4:0:0) images, data show up in 256 byte segments.
3238
 * The segments represent 4 squares of 8x8 pixels as follows:
3239
 *
3240
 *      0  1 ...  7    64  65 ...  71   ...  192 193 ... 199
3241
 *      8  9 ... 15    72  73 ...  79        200 201 ... 207
3242
 *           ...              ...                    ...
3243
 *     56 57 ... 63   120 121 ... 127        248 249 ... 255
3244
 *
3245
 */
3246
static void
3247
yuv400raw_to_yuv400p(struct ov511_frame *frame,
3248
                     unsigned char *pIn0, unsigned char *pOut0)
3249
{
3250
        int x, y;
3251
        unsigned char *pIn, *pOut, *pOutLine;
3252
 
3253
        /* Copy Y */
3254
        pIn = pIn0;
3255
        pOutLine = pOut0;
3256
        for (y = 0; y < frame->rawheight - 1; y += 8) {
3257
                pOut = pOutLine;
3258
                for (x = 0; x < frame->rawwidth - 1; x += 8) {
3259
                        make_8x8(pIn, pOut, frame->rawwidth);
3260
                        pIn += 64;
3261
                        pOut += 8;
3262
                }
3263
                pOutLine += 8 * frame->rawwidth;
3264
        }
3265
}
3266
 
3267
/*
3268
 * For YUV 4:2:0 images, the data show up in 384 byte segments.
3269
 * The first 64 bytes of each segment are U, the next 64 are V.  The U and
3270
 * V are arranged as follows:
3271
 *
3272
 *      0  1 ...  7
3273
 *      8  9 ... 15
3274
 *           ...
3275
 *     56 57 ... 63
3276
 *
3277
 * U and V are shipped at half resolution (1 U,V sample -> one 2x2 block).
3278
 *
3279
 * The next 256 bytes are full resolution Y data and represent 4 squares
3280
 * of 8x8 pixels as follows:
3281
 *
3282
 *      0  1 ...  7    64  65 ...  71   ...  192 193 ... 199
3283
 *      8  9 ... 15    72  73 ...  79        200 201 ... 207
3284
 *           ...              ...                    ...
3285
 *     56 57 ... 63   120 121 ... 127   ...  248 249 ... 255
3286
 *
3287
 * Note that the U and V data in one segment represent a 16 x 16 pixel
3288
 * area, but the Y data represent a 32 x 8 pixel area. If the width is not an
3289
 * even multiple of 32, the extra 8x8 blocks within a 32x8 block belong to the
3290
 * next horizontal stripe.
3291
 *
3292
 * If dumppix module param is set, _parse_data just dumps the incoming segments,
3293
 * verbatim, in order, into the frame. When used with vidcat -f ppm -s 640x480
3294
 * this puts the data on the standard output and can be analyzed with the
3295
 * parseppm.c utility I wrote.  That's a much faster way for figuring out how
3296
 * these data are scrambled.
3297
 */
3298
 
3299
/* Converts from raw, uncompressed segments at pIn0 to a YUV420P frame at pOut0.
3300
 *
3301
 * FIXME: Currently only handles width and height that are multiples of 16
3302
 */
3303
static void
3304
yuv420raw_to_yuv420p(struct ov511_frame *frame,
3305
                     unsigned char *pIn0, unsigned char *pOut0)
3306
{
3307
        int k, x, y;
3308
        unsigned char *pIn, *pOut, *pOutLine;
3309
        const unsigned int a = frame->rawwidth * frame->rawheight;
3310
        const unsigned int w = frame->rawwidth / 2;
3311
 
3312
        /* Copy U and V */
3313
        pIn = pIn0;
3314
        pOutLine = pOut0 + a;
3315
        for (y = 0; y < frame->rawheight - 1; y += 16) {
3316
                pOut = pOutLine;
3317
                for (x = 0; x < frame->rawwidth - 1; x += 16) {
3318
                        make_8x8(pIn, pOut, w);
3319
                        make_8x8(pIn + 64, pOut + a/4, w);
3320
                        pIn += 384;
3321
                        pOut += 8;
3322
                }
3323
                pOutLine += 8 * w;
3324
        }
3325
 
3326
        /* Copy Y */
3327
        pIn = pIn0 + 128;
3328
        pOutLine = pOut0;
3329
        k = 0;
3330
        for (y = 0; y < frame->rawheight - 1; y += 8) {
3331
                pOut = pOutLine;
3332
                for (x = 0; x < frame->rawwidth - 1; x += 8) {
3333
                        make_8x8(pIn, pOut, frame->rawwidth);
3334
                        pIn += 64;
3335
                        pOut += 8;
3336
                        if ((++k) > 3) {
3337
                                k = 0;
3338
                                pIn += 128;
3339
                        }
3340
                }
3341
                pOutLine += 8 * frame->rawwidth;
3342
        }
3343
}
3344
 
3345
/*
3346
 * fixFrameRGBoffset--
3347
 * My camera seems to return the red channel about 1 pixel
3348
 * low, and the blue channel about 1 pixel high. After YUV->RGB
3349
 * conversion, we can correct this easily. OSL 2/24/2000.
3350
 */
3351
static void
3352
fixFrameRGBoffset(struct ov511_frame *frame)
3353
{
3354
        int x, y;
3355
        int rowBytes = frame->width*3, w = frame->width;
3356
        unsigned char *rgb = frame->data;
3357
        const int shift = 1;  /* Distance to shift pixels by, vertically */
3358
 
3359
        /* Don't bother with little images */
3360
        if (frame->width < 400)
3361
                return;
3362
 
3363
        /* This only works with RGB24 */
3364
        if (frame->format != VIDEO_PALETTE_RGB24)
3365
                return;
3366
 
3367
        /* Shift red channel up */
3368
        for (y = shift; y < frame->height; y++) {
3369
                int lp = (y-shift)*rowBytes;     /* Previous line offset */
3370
                int lc = y*rowBytes;             /* Current line offset */
3371
                for (x = 0; x < w; x++)
3372
                        rgb[lp+x*3+2] = rgb[lc+x*3+2]; /* Shift red up */
3373
        }
3374
 
3375
        /* Shift blue channel down */
3376
        for (y = frame->height-shift-1; y >= 0; y--) {
3377
                int ln = (y + shift) * rowBytes;  /* Next line offset */
3378
                int lc = y * rowBytes;            /* Current line offset */
3379
                for (x = 0; x < w; x++)
3380
                        rgb[ln+x*3+0] = rgb[lc+x*3+0]; /* Shift blue down */
3381
        }
3382
}
3383
 
3384
/**********************************************************************
3385
 *
3386
 * Decompression
3387
 *
3388
 **********************************************************************/
3389
 
3390
/* Chooses a decompression module, locks it, and sets ov->decomp_ops
3391
 * accordingly. Returns -ENXIO if decompressor is not available, otherwise
3392
 * returns 0 if no other error.
3393
 */
3394
static int
3395
request_decompressor(struct usb_ov511 *ov)
3396
{
3397
        if (!ov)
3398
                return -ENODEV;
3399
 
3400
        if (ov->decomp_ops) {
3401
                err("ERROR: Decompressor already requested!");
3402
                return -EINVAL;
3403
        }
3404
 
3405
        lock_kernel();
3406
 
3407
        /* Try to get MMX, and fall back on no-MMX if necessary */
3408
        if (ov->bclass == BCL_OV511) {
3409
                if (ov511_mmx_decomp_ops) {
3410
                        PDEBUG(3, "Using OV511 MMX decompressor");
3411
                        ov->decomp_ops = ov511_mmx_decomp_ops;
3412
                } else if (ov511_decomp_ops) {
3413
                        PDEBUG(3, "Using OV511 decompressor");
3414
                        ov->decomp_ops = ov511_decomp_ops;
3415
                } else {
3416
                        err("No decompressor available");
3417
                }
3418
        } else if (ov->bclass == BCL_OV518) {
3419
                if (ov518_mmx_decomp_ops) {
3420
                        PDEBUG(3, "Using OV518 MMX decompressor");
3421
                        ov->decomp_ops = ov518_mmx_decomp_ops;
3422
                } else if (ov518_decomp_ops) {
3423
                        PDEBUG(3, "Using OV518 decompressor");
3424
                        ov->decomp_ops = ov518_decomp_ops;
3425
                } else {
3426
                        err("No decompressor available");
3427
                }
3428
        } else {
3429
                err("Unknown bridge");
3430
        }
3431
 
3432
        if (ov->decomp_ops) {
3433
                if (!ov->decomp_ops->owner) {
3434
                        ov->decomp_ops = NULL;
3435
                        unlock_kernel();
3436
                        return -ENOSYS;
3437
                }
3438
                __MOD_INC_USE_COUNT(ov->decomp_ops->owner);
3439
                unlock_kernel();
3440
                return 0;
3441
        } else {
3442
                unlock_kernel();
3443
                return -ENOSYS;
3444
        }
3445
}
3446
 
3447
/* Unlocks decompression module and nulls ov->decomp_ops. Safe to call even
3448
 * if ov->decomp_ops is NULL.
3449
 */
3450
static void
3451
release_decompressor(struct usb_ov511 *ov)
3452
{
3453
        int released = 0;       /* Did we actually do anything? */
3454
 
3455
        if (!ov)
3456
                return;
3457
 
3458
        lock_kernel();
3459
 
3460
        if (ov->decomp_ops && ov->decomp_ops->owner) {
3461
                __MOD_DEC_USE_COUNT(ov->decomp_ops->owner);
3462
                released = 1;
3463
        }
3464
 
3465
        ov->decomp_ops = NULL;
3466
 
3467
        unlock_kernel();
3468
 
3469
        if (released)
3470
                PDEBUG(3, "Decompressor released");
3471
}
3472
 
3473
static void
3474
decompress(struct usb_ov511 *ov, struct ov511_frame *frame,
3475
           unsigned char *pIn0, unsigned char *pOut0)
3476
{
3477
        if (!ov->decomp_ops)
3478
                if (request_decompressor(ov))
3479
                        return;
3480
 
3481
        PDEBUG(4, "Decompressing %d bytes", frame->bytes_recvd);
3482
 
3483
        if (frame->format == VIDEO_PALETTE_GREY
3484
            && ov->decomp_ops->decomp_400) {
3485
                int ret = ov->decomp_ops->decomp_400(
3486
                        pIn0,
3487
                        pOut0,
3488
                        frame->compbuf,
3489
                        frame->rawwidth,
3490
                        frame->rawheight,
3491
                        frame->bytes_recvd);
3492
                PDEBUG(4, "DEBUG: decomp_400 returned %d", ret);
3493
        } else if (frame->format != VIDEO_PALETTE_GREY
3494
                   && ov->decomp_ops->decomp_420) {
3495
                int ret = ov->decomp_ops->decomp_420(
3496
                        pIn0,
3497
                        pOut0,
3498
                        frame->compbuf,
3499
                        frame->rawwidth,
3500
                        frame->rawheight,
3501
                        frame->bytes_recvd);
3502
                PDEBUG(4, "DEBUG: decomp_420 returned %d", ret);
3503
        } else {
3504
                err("Decompressor does not support this format");
3505
        }
3506
}
3507
 
3508
/**********************************************************************
3509
 *
3510
 * Format conversion
3511
 *
3512
 **********************************************************************/
3513
 
3514
/* Converts from planar YUV420 to RGB24. */
3515
static void
3516
yuv420p_to_rgb(struct ov511_frame *frame,
3517
               unsigned char *pIn0, unsigned char *pOut0, int bits)
3518
{
3519
        const int numpix = frame->width * frame->height;
3520
        const int bytes = bits >> 3;
3521
        int i, j, y00, y01, y10, y11, u, v;
3522
        unsigned char *pY = pIn0;
3523
        unsigned char *pU = pY + numpix;
3524
        unsigned char *pV = pU + numpix / 4;
3525
        unsigned char *pOut = pOut0;
3526
 
3527
        for (j = 0; j <= frame->height - 2; j += 2) {
3528
                for (i = 0; i <= frame->width - 2; i += 2) {
3529
                        y00 = *pY;
3530
                        y01 = *(pY + 1);
3531
                        y10 = *(pY + frame->width);
3532
                        y11 = *(pY + frame->width + 1);
3533
                        u = (*pU++) - 128;
3534
                        v = (*pV++) - 128;
3535
 
3536
                        move_420_block(y00, y01, y10, y11, u, v,
3537
                                       frame->width, pOut, bits);
3538
 
3539
                        pY += 2;
3540
                        pOut += 2 * bytes;
3541
                }
3542
                pY += frame->width;
3543
                pOut += frame->width * bytes;
3544
        }
3545
}
3546
 
3547
/* Converts from planar YUV420 to YUV422 (YUYV). */
3548
static void
3549
yuv420p_to_yuv422(struct ov511_frame *frame,
3550
                  unsigned char *pIn0, unsigned char *pOut0)
3551
{
3552
        const int numpix = frame->width * frame->height;
3553
        int i, j;
3554
        unsigned char *pY = pIn0;
3555
        unsigned char *pU = pY + numpix;
3556
        unsigned char *pV = pU + numpix / 4;
3557
        unsigned char *pOut = pOut0;
3558
 
3559
        for (i = 0; i < numpix; i++) {
3560
                *pOut = *(pY + i);
3561
                pOut += 2;
3562
        }
3563
 
3564
        pOut = pOut0 + 1;
3565
        for (j = 0; j <= frame->height - 2 ; j += 2) {
3566
                for (i = 0; i <= frame->width - 2; i += 2) {
3567
                        int u = *pU++;
3568
                        int v = *pV++;
3569
 
3570
                        *pOut = u;
3571
                        *(pOut+2) = v;
3572
                        *(pOut+frame->width*2) = u;
3573
                        *(pOut+frame->width*2+2) = v;
3574
                        pOut += 4;
3575
                }
3576
                pOut += (frame->width * 2);
3577
        }
3578
}
3579
 
3580
/* Converts pData from planar YUV420 to planar YUV422 **in place**. */
3581
static void
3582
yuv420p_to_yuv422p(struct ov511_frame *frame, unsigned char *pData)
3583
{
3584
        const int numpix = frame->width * frame->height;
3585
        const int w = frame->width;
3586
        int j;
3587
        unsigned char *pIn, *pOut;
3588
 
3589
        /* Clear U and V */
3590
        memset(pData + numpix + numpix / 2, 127, numpix / 2);
3591
 
3592
        /* Convert V starting from beginning and working forward */
3593
        pIn = pData + numpix + numpix / 4;
3594
        pOut = pData + numpix +numpix / 2;
3595
        for (j = 0; j <= frame->height - 2; j += 2) {
3596
                memmove(pOut, pIn, w/2);
3597
                memmove(pOut + w/2, pIn, w/2);
3598
                pIn += w/2;
3599
                pOut += w;
3600
        }
3601
 
3602
        /* Convert U, starting from end and working backward */
3603
        pIn = pData + numpix + numpix / 4;
3604
        pOut = pData + numpix + numpix / 2;
3605
        for (j = 0; j <= frame->height - 2; j += 2) {
3606
                pIn -= w/2;
3607
                pOut -= w;
3608
                memmove(pOut, pIn, w/2);
3609
                memmove(pOut + w/2, pIn, w/2);
3610
        }
3611
}
3612
 
3613
/* Fuses even and odd fields together, and doubles width.
3614
 * INPUT: an odd field followed by an even field at pIn0, in YUV planar format
3615
 * OUTPUT: a normal YUV planar image, with correct aspect ratio
3616
 */
3617
static void
3618
deinterlace(struct ov511_frame *frame, int rawformat,
3619
            unsigned char *pIn0, unsigned char *pOut0)
3620
{
3621
        const int fieldheight = frame->rawheight / 2;
3622
        const int fieldpix = fieldheight * frame->rawwidth;
3623
        const int w = frame->width;
3624
        int x, y;
3625
        unsigned char *pInEven, *pInOdd, *pOut;
3626
 
3627
        PDEBUG(5, "fieldheight=%d", fieldheight);
3628
 
3629
        if (frame->rawheight != frame->height) {
3630
                err("invalid height");
3631
                return;
3632
        }
3633
 
3634
        if ((frame->rawwidth * 2) != frame->width) {
3635
                err("invalid width");
3636
                return;
3637
        }
3638
 
3639
        /* Y */
3640
        pInOdd = pIn0;
3641
        pInEven = pInOdd + fieldpix;
3642
        pOut = pOut0;
3643
        for (y = 0; y < fieldheight; y++) {
3644
                for (x = 0; x < frame->rawwidth; x++) {
3645
                        *pOut = *pInEven;
3646
                        *(pOut+1) = *pInEven++;
3647
                        *(pOut+w) = *pInOdd;
3648
                        *(pOut+w+1) = *pInOdd++;
3649
                        pOut += 2;
3650
                }
3651
                pOut += w;
3652
        }
3653
 
3654
        if (rawformat == RAWFMT_YUV420) {
3655
        /* U */
3656
                pInOdd = pIn0 + fieldpix * 2;
3657
                pInEven = pInOdd + fieldpix / 4;
3658
                for (y = 0; y < fieldheight / 2; y++) {
3659
                        for (x = 0; x < frame->rawwidth / 2; x++) {
3660
                                *pOut = *pInEven;
3661
                                *(pOut+1) = *pInEven++;
3662
                                *(pOut+w/2) = *pInOdd;
3663
                                *(pOut+w/2+1) = *pInOdd++;
3664
                                pOut += 2;
3665
                        }
3666
                        pOut += w/2;
3667
                }
3668
        /* V */
3669
                pInOdd = pIn0 + fieldpix * 2 + fieldpix / 2;
3670
                pInEven = pInOdd + fieldpix / 4;
3671
                for (y = 0; y < fieldheight / 2; y++) {
3672
                        for (x = 0; x < frame->rawwidth / 2; x++) {
3673
                                *pOut = *pInEven;
3674
                                *(pOut+1) = *pInEven++;
3675
                                *(pOut+w/2) = *pInOdd;
3676
                                *(pOut+w/2+1) = *pInOdd++;
3677
                                pOut += 2;
3678
                        }
3679
                        pOut += w/2;
3680
                }
3681
        }
3682
}
3683
 
3684
static void
3685
ov51x_postprocess_grey(struct usb_ov511 *ov, struct ov511_frame *frame)
3686
{
3687
                /* Deinterlace frame, if necessary */
3688
                if (ov->sensor == SEN_SAA7111A && frame->rawheight >= 480) {
3689
                        if (frame->compressed)
3690
                                decompress(ov, frame, frame->rawdata,
3691
                                                 frame->tempdata);
3692
                        else
3693
                                yuv400raw_to_yuv400p(frame, frame->rawdata,
3694
                                                     frame->tempdata);
3695
 
3696
                        deinterlace(frame, RAWFMT_YUV400, frame->tempdata,
3697
                                    frame->data);
3698
                } else {
3699
                        if (frame->compressed)
3700
                                decompress(ov, frame, frame->rawdata,
3701
                                                 frame->data);
3702
                        else
3703
                                yuv400raw_to_yuv400p(frame, frame->rawdata,
3704
                                                     frame->data);
3705
                }
3706
}
3707
 
3708
/* Process raw YUV420 data into the format requested by the app. Conversion
3709
 * between V4L formats is allowed.
3710
 */
3711
static void
3712
ov51x_postprocess_yuv420(struct usb_ov511 *ov, struct ov511_frame *frame)
3713
{
3714
        /* Process frame->rawdata to frame->tempdata */
3715
        if (frame->compressed)
3716
                decompress(ov, frame, frame->rawdata, frame->tempdata);
3717
        else
3718
                yuv420raw_to_yuv420p(frame, frame->rawdata, frame->tempdata);
3719
 
3720
        /* Deinterlace frame, if necessary */
3721
        if (ov->sensor == SEN_SAA7111A && frame->rawheight >= 480) {
3722
                memcpy(frame->rawdata, frame->tempdata,
3723
                        MAX_RAW_DATA_SIZE(frame->width, frame->height));
3724
                deinterlace(frame, RAWFMT_YUV420, frame->rawdata,
3725
                            frame->tempdata);
3726
        }
3727
 
3728
        /* Frame should be (width x height) and not (rawwidth x rawheight) at
3729
         * this point. */
3730
 
3731
        /* Process frame->tempdata to frame->data */
3732
        switch (frame->format) {
3733
        case VIDEO_PALETTE_RGB565:
3734
                yuv420p_to_rgb(frame, frame->tempdata, frame->data, 16);
3735
                break;
3736
        case VIDEO_PALETTE_RGB24:
3737
                yuv420p_to_rgb(frame, frame->tempdata, frame->data, 24);
3738
                break;
3739
        case VIDEO_PALETTE_YUV422:
3740
        case VIDEO_PALETTE_YUYV:
3741
                yuv420p_to_yuv422(frame, frame->tempdata, frame->data);
3742
                break;
3743
        case VIDEO_PALETTE_YUV420:
3744
        case VIDEO_PALETTE_YUV420P:
3745
                memcpy(frame->data, frame->tempdata,
3746
                        MAX_RAW_DATA_SIZE(frame->width, frame->height));
3747
                break;
3748
        case VIDEO_PALETTE_YUV422P:
3749
                /* Data is converted in place, so copy it in advance */
3750
                memcpy(frame->data, frame->tempdata,
3751
                        MAX_RAW_DATA_SIZE(frame->width, frame->height));
3752
 
3753
                yuv420p_to_yuv422p(frame, frame->data);
3754
                break;
3755
        default:
3756
                err("Cannot convert YUV420 to %s",
3757
                    symbolic(v4l1_plist, frame->format));
3758
        }
3759
 
3760
        if (fix_rgb_offset)
3761
                fixFrameRGBoffset(frame);
3762
}
3763
 
3764
/* Post-processes the specified frame. This consists of:
3765
 *      1. Decompress frame, if necessary
3766
 *      2. Deinterlace frame and scale to proper size, if necessary
3767
 *      3. Convert from YUV planar to destination format, if necessary
3768
 *      4. Fix the RGB offset, if necessary
3769
 */
3770
static void
3771
ov51x_postprocess(struct usb_ov511 *ov, struct ov511_frame *frame)
3772
{
3773
        if (dumppix) {
3774
                memset(frame->data, 0,
3775
                        MAX_DATA_SIZE(ov->maxwidth, ov->maxheight));
3776
                PDEBUG(4, "Dumping %d bytes", frame->bytes_recvd);
3777
                memcpy(frame->data, frame->rawdata, frame->bytes_recvd);
3778
        } else {
3779
                switch (frame->format) {
3780
                case VIDEO_PALETTE_GREY:
3781
                        ov51x_postprocess_grey(ov, frame);
3782
                        break;
3783
                case VIDEO_PALETTE_YUV420:
3784
                case VIDEO_PALETTE_YUV420P:
3785
                case VIDEO_PALETTE_RGB565:
3786
                case VIDEO_PALETTE_RGB24:
3787
                case VIDEO_PALETTE_YUV422:
3788
                case VIDEO_PALETTE_YUYV:
3789
                case VIDEO_PALETTE_YUV422P:
3790
                        ov51x_postprocess_yuv420(ov, frame);
3791
                        break;
3792
                default:
3793
                        err("Cannot convert data to %s",
3794
                            symbolic(v4l1_plist, frame->format));
3795
                }
3796
        }
3797
}
3798
 
3799
/**********************************************************************
3800
 *
3801
 * OV51x data transfer, IRQ handler
3802
 *
3803
 **********************************************************************/
3804
 
3805
static inline void
3806
ov511_move_data(struct usb_ov511 *ov, unsigned char *in, int n)
3807
{
3808
        int num, offset;
3809
        int pnum = in[ov->packet_size - 1];             /* Get packet number */
3810
        int max_raw = MAX_RAW_DATA_SIZE(ov->maxwidth, ov->maxheight);
3811
        struct ov511_frame *frame = &ov->frame[ov->curframe];
3812
        struct timeval *ts;
3813
 
3814
        /* SOF/EOF packets have 1st to 8th bytes zeroed and the 9th
3815
         * byte non-zero. The EOF packet has image width/height in the
3816
         * 10th and 11th bytes. The 9th byte is given as follows:
3817
         *
3818
         * bit 7: EOF
3819
         *     6: compression enabled
3820
         *     5: 422/420/400 modes
3821
         *     4: 422/420/400 modes
3822
         *     3: 1
3823
         *     2: snapshot button on
3824
         *     1: snapshot frame
3825
         *     0: even/odd field
3826
         */
3827
 
3828
        if (printph) {
3829
                info("ph(%3d): %2x %2x %2x %2x %2x %2x %2x %2x %2x %2x %2x %2x",
3830
                     pnum, in[0], in[1], in[2], in[3], in[4], in[5], in[6],
3831
                     in[7], in[8], in[9], in[10], in[11]);
3832
        }
3833
 
3834
        /* Check for SOF/EOF packet */
3835
        if ((in[0] | in[1] | in[2] | in[3] | in[4] | in[5] | in[6] | in[7]) ||
3836
            (~in[8] & 0x08))
3837
                goto check_middle;
3838
 
3839
        /* Frame end */
3840
        if (in[8] & 0x80) {
3841
                ts = (struct timeval *)(frame->data
3842
                      + MAX_FRAME_SIZE(ov->maxwidth, ov->maxheight));
3843
                do_gettimeofday(ts);
3844
 
3845
                /* Get the actual frame size from the EOF header */
3846
                frame->rawwidth = ((int)(in[9]) + 1) * 8;
3847
                frame->rawheight = ((int)(in[10]) + 1) * 8;
3848
 
3849
                PDEBUG(4, "Frame end, frame=%d, pnum=%d, w=%d, h=%d, recvd=%d",
3850
                        ov->curframe, pnum, frame->rawwidth, frame->rawheight,
3851
                        frame->bytes_recvd);
3852
 
3853
                /* Validate the header data */
3854
                RESTRICT_TO_RANGE(frame->rawwidth, ov->minwidth, ov->maxwidth);
3855
                RESTRICT_TO_RANGE(frame->rawheight, ov->minheight,
3856
                                  ov->maxheight);
3857
 
3858
                /* Don't allow byte count to exceed buffer size */
3859
                RESTRICT_TO_RANGE(frame->bytes_recvd, 8, max_raw);
3860
 
3861
                if (frame->scanstate == STATE_LINES) {
3862
                        int nextf;
3863
 
3864
                        frame->grabstate = FRAME_DONE;  // FIXME: Is this right?
3865
 
3866
                        if (waitqueue_active(&frame->wq)) {
3867
                                frame->grabstate = FRAME_DONE;
3868
                                wake_up_interruptible(&frame->wq);
3869
                        }
3870
 
3871
                        /* If next frame is ready or grabbing,
3872
                         * point to it */
3873
                        nextf = (ov->curframe + 1) % OV511_NUMFRAMES;
3874
                        if (ov->frame[nextf].grabstate == FRAME_READY
3875
                            || ov->frame[nextf].grabstate == FRAME_GRABBING) {
3876
                                ov->curframe = nextf;
3877
                                ov->frame[nextf].scanstate = STATE_SCANNING;
3878
                        } else {
3879
                                if (frame->grabstate == FRAME_DONE) {
3880
                                        PDEBUG(4, "** Frame done **");
3881
                                } else {
3882
                                        PDEBUG(4, "Frame not ready? state = %d",
3883
                                                ov->frame[nextf].grabstate);
3884
                                }
3885
 
3886
                                ov->curframe = -1;
3887
                        }
3888
                } else {
3889
                        PDEBUG(5, "Frame done, but not scanning");
3890
                }
3891
                /* Image corruption caused by misplaced frame->segment = 0
3892
                 * fixed by carlosf@conectiva.com.br
3893
                 */
3894
        } else {
3895
                /* Frame start */
3896
                PDEBUG(4, "Frame start, framenum = %d", ov->curframe);
3897
 
3898
                /* Check to see if it's a snapshot frame */
3899
                /* FIXME?? Should the snapshot reset go here? Performance? */
3900
                if (in[8] & 0x02) {
3901
                        frame->snapshot = 1;
3902
                        PDEBUG(3, "snapshot detected");
3903
                }
3904
 
3905
                frame->scanstate = STATE_LINES;
3906
                frame->bytes_recvd = 0;
3907
                frame->compressed = in[8] & 0x40;
3908
        }
3909
 
3910
check_middle:
3911
        /* Are we in a frame? */
3912
        if (frame->scanstate != STATE_LINES) {
3913
                PDEBUG(5, "Not in a frame; packet skipped");
3914
                return;
3915
        }
3916
 
3917
        /* If frame start, skip header */
3918
        if (frame->bytes_recvd == 0)
3919
                offset = 9;
3920
        else
3921
                offset = 0;
3922
 
3923
        num = n - offset - 1;
3924
 
3925
        /* Dump all data exactly as received */
3926
        if (dumppix == 2) {
3927
                frame->bytes_recvd += n - 1;
3928
                if (frame->bytes_recvd <= max_raw)
3929
                        memcpy(frame->rawdata + frame->bytes_recvd - (n - 1),
3930
                                in, n - 1);
3931
                else
3932
                        PDEBUG(3, "Raw data buffer overrun!! (%d)",
3933
                                frame->bytes_recvd - max_raw);
3934
        } else if (!frame->compressed && !remove_zeros) {
3935
                frame->bytes_recvd += num;
3936
                if (frame->bytes_recvd <= max_raw)
3937
                        memcpy(frame->rawdata + frame->bytes_recvd - num,
3938
                                in + offset, num);
3939
                else
3940
                        PDEBUG(3, "Raw data buffer overrun!! (%d)",
3941
                                frame->bytes_recvd - max_raw);
3942
        } else { /* Remove all-zero FIFO lines (aligned 32-byte blocks) */
3943
                int b, read = 0, allzero, copied = 0;
3944
                if (offset) {
3945
                        frame->bytes_recvd += 32 - offset;      // Bytes out
3946
                        memcpy(frame->rawdata,  in + offset, 32 - offset);
3947
                        read += 32;
3948
                }
3949
 
3950
                while (read < n - 1) {
3951
                        allzero = 1;
3952
                        for (b = 0; b < 32; b++) {
3953
                                if (in[read + b]) {
3954
                                        allzero = 0;
3955
                                        break;
3956
                                }
3957
                        }
3958
 
3959
                        if (allzero) {
3960
                                /* Don't copy it */
3961
                        } else {
3962
                                if (frame->bytes_recvd + copied + 32 <= max_raw)
3963
                                {
3964
                                        memcpy(frame->rawdata
3965
                                                + frame->bytes_recvd + copied,
3966
                                                in + read, 32);
3967
                                        copied += 32;
3968
                                } else {
3969
                                        PDEBUG(3, "Raw data buffer overrun!!");
3970
                                }
3971
                        }
3972
                        read += 32;
3973
                }
3974
 
3975
                frame->bytes_recvd += copied;
3976
        }
3977
}
3978
 
3979
static inline void
3980
ov518_move_data(struct usb_ov511 *ov, unsigned char *in, int n)
3981
{
3982
        int max_raw = MAX_RAW_DATA_SIZE(ov->maxwidth, ov->maxheight);
3983
        struct ov511_frame *frame = &ov->frame[ov->curframe];
3984
        struct timeval *ts;
3985
 
3986
        /* Don't copy the packet number byte */
3987
        if (ov->packet_numbering)
3988
                --n;
3989
 
3990
        /* A false positive here is likely, until OVT gives me
3991
         * the definitive SOF/EOF format */
3992
        if ((!(in[0] | in[1] | in[2] | in[3] | in[5])) && in[6]) {
3993
                if (printph) {
3994
                        info("ph: %2x %2x %2x %2x %2x %2x %2x %2x", in[0],
3995
                             in[1], in[2], in[3], in[4], in[5], in[6], in[7]);
3996
                }
3997
 
3998
                if (frame->scanstate == STATE_LINES) {
3999
                        PDEBUG(4, "Detected frame end/start");
4000
                        goto eof;
4001
                } else { //scanstate == STATE_SCANNING
4002
                        /* Frame start */
4003
                        PDEBUG(4, "Frame start, framenum = %d", ov->curframe);
4004
                        goto sof;
4005
                }
4006
        } else {
4007
                goto check_middle;
4008
        }
4009
 
4010
eof:
4011
        ts = (struct timeval *)(frame->data
4012
              + MAX_FRAME_SIZE(ov->maxwidth, ov->maxheight));
4013
        do_gettimeofday(ts);
4014
 
4015
        PDEBUG(4, "Frame end, curframe = %d, hw=%d, vw=%d, recvd=%d",
4016
                ov->curframe,
4017
                (int)(in[9]), (int)(in[10]), frame->bytes_recvd);
4018
 
4019
        // FIXME: Since we don't know the header formats yet,
4020
        // there is no way to know what the actual image size is
4021
        frame->rawwidth = frame->width;
4022
        frame->rawheight = frame->height;
4023
 
4024
        /* Validate the header data */
4025
        RESTRICT_TO_RANGE(frame->rawwidth, ov->minwidth, ov->maxwidth);
4026
        RESTRICT_TO_RANGE(frame->rawheight, ov->minheight, ov->maxheight);
4027
 
4028
        /* Don't allow byte count to exceed buffer size */
4029
        RESTRICT_TO_RANGE(frame->bytes_recvd, 8, max_raw);
4030
 
4031
        if (frame->scanstate == STATE_LINES) {
4032
                int nextf;
4033
 
4034
                frame->grabstate = FRAME_DONE;  // FIXME: Is this right?
4035
 
4036
                if (waitqueue_active(&frame->wq)) {
4037
                        frame->grabstate = FRAME_DONE;
4038
                        wake_up_interruptible(&frame->wq);
4039
                }
4040
 
4041
                /* If next frame is ready or grabbing,
4042
                 * point to it */
4043
                nextf = (ov->curframe + 1) % OV511_NUMFRAMES;
4044
                if (ov->frame[nextf].grabstate == FRAME_READY
4045
                    || ov->frame[nextf].grabstate == FRAME_GRABBING) {
4046
                        ov->curframe = nextf;
4047
                        ov->frame[nextf].scanstate = STATE_SCANNING;
4048
                        frame = &ov->frame[nextf];
4049
                } else {
4050
                        if (frame->grabstate == FRAME_DONE) {
4051
                                PDEBUG(4, "** Frame done **");
4052
                        } else {
4053
                                PDEBUG(4, "Frame not ready? state = %d",
4054
                                       ov->frame[nextf].grabstate);
4055
                        }
4056
 
4057
                        ov->curframe = -1;
4058
                        PDEBUG(4, "SOF dropped (no active frame)");
4059
                        return;  /* Nowhere to store this frame */
4060
                }
4061
        }
4062
sof:
4063
        PDEBUG(4, "Starting capture on frame %d", frame->framenum);
4064
 
4065
// Snapshot not reverse-engineered yet.
4066
#if 0
4067
        /* Check to see if it's a snapshot frame */
4068
        /* FIXME?? Should the snapshot reset go here? Performance? */
4069
        if (in[8] & 0x02) {
4070
                frame->snapshot = 1;
4071
                PDEBUG(3, "snapshot detected");
4072
        }
4073
#endif
4074
        frame->scanstate = STATE_LINES;
4075
        frame->bytes_recvd = 0;
4076
        frame->compressed = 1;
4077
 
4078
check_middle:
4079
        /* Are we in a frame? */
4080
        if (frame->scanstate != STATE_LINES) {
4081
                PDEBUG(4, "scanstate: no SOF yet");
4082
                return;
4083
        }
4084
 
4085
        /* Dump all data exactly as received */
4086
        if (dumppix == 2) {
4087
                frame->bytes_recvd += n;
4088
                if (frame->bytes_recvd <= max_raw)
4089
                        memcpy(frame->rawdata + frame->bytes_recvd - n, in, n);
4090
                else
4091
                        PDEBUG(3, "Raw data buffer overrun!! (%d)",
4092
                                frame->bytes_recvd - max_raw);
4093
        } else {
4094
                /* All incoming data are divided into 8-byte segments. If the
4095
                 * segment contains all zero bytes, it must be skipped. These
4096
                 * zero-segments allow the OV518 to mainain a constant data rate
4097
                 * regardless of the effectiveness of the compression. Segments
4098
                 * are aligned relative to the beginning of each isochronous
4099
                 * packet. The first segment in each image is a header (the
4100
                 * decompressor skips it later).
4101
                 */
4102
 
4103
                int b, read = 0, allzero, copied = 0;
4104
 
4105
                while (read < n) {
4106
                        allzero = 1;
4107
                        for (b = 0; b < 8; b++) {
4108
                                if (in[read + b]) {
4109
                                        allzero = 0;
4110
                                        break;
4111
                                }
4112
                        }
4113
 
4114
                        if (allzero) {
4115
                        /* Don't copy it */
4116
                        } else {
4117
                                if (frame->bytes_recvd + copied + 8 <= max_raw)
4118
                                {
4119
                                        memcpy(frame->rawdata
4120
                                                + frame->bytes_recvd + copied,
4121
                                                in + read, 8);
4122
                                        copied += 8;
4123
                                } else {
4124
                                        PDEBUG(3, "Raw data buffer overrun!!");
4125
                                }
4126
                        }
4127
                        read += 8;
4128
                }
4129
                frame->bytes_recvd += copied;
4130
        }
4131
}
4132
 
4133
static void
4134
ov51x_isoc_irq(struct urb *urb)
4135
{
4136
        int i;
4137
        struct usb_ov511 *ov;
4138
        struct ov511_sbuf *sbuf;
4139
 
4140
        if (!urb->context) {
4141
                PDEBUG(4, "no context");
4142
                return;
4143
        }
4144
 
4145
        sbuf = urb->context;
4146
        ov = sbuf->ov;
4147
 
4148
        if (!ov || !ov->dev || !ov->user) {
4149
                PDEBUG(4, "no device, or not open");
4150
                return;
4151
        }
4152
 
4153
        if (!ov->streaming) {
4154
                PDEBUG(4, "hmmm... not streaming, but got interrupt");
4155
                return;
4156
        }
4157
 
4158
        if (urb->status == -ENOENT || urb->status == -ECONNRESET) {
4159
                PDEBUG(4, "URB unlinked");
4160
                return;
4161
        }
4162
 
4163
        if (urb->status != -EINPROGRESS && urb->status != 0) {
4164
                err("ERROR: urb->status=%d: %s", urb->status,
4165
                    symbolic(urb_errlist, urb->status));
4166
        }
4167
 
4168
        /* Copy the data received into our frame buffer */
4169
        PDEBUG(5, "sbuf[%d]: Moving %d packets", sbuf->n,
4170
               urb->number_of_packets);
4171
        for (i = 0; i < urb->number_of_packets; i++) {
4172
                /* Warning: Don't call *_move_data() if no frame active! */
4173
                if (ov->curframe >= 0) {
4174
                        int n = urb->iso_frame_desc[i].actual_length;
4175
                        int st = urb->iso_frame_desc[i].status;
4176
                        unsigned char *cdata;
4177
 
4178
                        urb->iso_frame_desc[i].actual_length = 0;
4179
                        urb->iso_frame_desc[i].status = 0;
4180
 
4181
                        cdata = urb->transfer_buffer
4182
                                + urb->iso_frame_desc[i].offset;
4183
 
4184
                        if (!n) {
4185
                                PDEBUG(4, "Zero-length packet");
4186
                                continue;
4187
                        }
4188
 
4189
                        if (st)
4190
                                PDEBUG(2, "data error: [%d] len=%d, status=%d",
4191
                                       i, n, st);
4192
 
4193
                        if (ov->bclass == BCL_OV511)
4194
                                ov511_move_data(ov, cdata, n);
4195
                        else if (ov->bclass == BCL_OV518)
4196
                                ov518_move_data(ov, cdata, n);
4197
                        else
4198
                                err("Unknown bridge device (%d)", ov->bridge);
4199
 
4200
                } else if (waitqueue_active(&ov->wq)) {
4201
                        wake_up_interruptible(&ov->wq);
4202
                }
4203
        }
4204
 
4205
        /* Resubmit this URB */
4206
        urb->dev = ov->dev;
4207
        if ((i = usb_submit_urb(urb)) != 0)
4208
                err("usb_submit_urb() ret %d", i);
4209
 
4210
        return;
4211
}
4212
 
4213
/****************************************************************************
4214
 *
4215
 * Stream initialization and termination
4216
 *
4217
 ***************************************************************************/
4218
 
4219
static int
4220
ov51x_init_isoc(struct usb_ov511 *ov)
4221
{
4222
        struct urb *urb;
4223
        int fx, err, n, size;
4224
 
4225
        PDEBUG(3, "*** Initializing capture ***");
4226
 
4227
        ov->curframe = -1;
4228
 
4229
        if (ov->bridge == BRG_OV511) {
4230
                if (cams == 1)                          size = 993;
4231
                else if (cams == 2)                     size = 513;
4232
                else if (cams == 3 || cams == 4)        size = 257;
4233
                else {
4234
                        err("\"cams\" parameter too high!");
4235
                        return -1;
4236
                }
4237
        } else if (ov->bridge == BRG_OV511PLUS) {
4238
                if (cams == 1)                          size = 961;
4239
                else if (cams == 2)                     size = 513;
4240
                else if (cams == 3 || cams == 4)        size = 257;
4241
                else if (cams >= 5 && cams <= 8)        size = 129;
4242
                else if (cams >= 9 && cams <= 31)       size = 33;
4243
                else {
4244
                        err("\"cams\" parameter too high!");
4245
                        return -1;
4246
                }
4247
        } else if (ov->bclass == BCL_OV518) {
4248
                if (cams == 1)                          size = 896;
4249
                else if (cams == 2)                     size = 512;
4250
                else if (cams == 3 || cams == 4)        size = 256;
4251
                else if (cams >= 5 && cams <= 8)        size = 128;
4252
                else {
4253
                        err("\"cams\" parameter too high!");
4254
                        return -1;
4255
                }
4256
        } else {
4257
                err("invalid bridge type");
4258
                return -1;
4259
        }
4260
 
4261
        // FIXME: OV518 is hardcoded to 15 FPS (alternate 5) for now
4262
        if (ov->bclass == BCL_OV518) {
4263
                if (packetsize == -1) {
4264
                        ov518_set_packet_size(ov, 640);
4265
                } else {
4266
                        info("Forcing packet size to %d", packetsize);
4267
                        ov518_set_packet_size(ov, packetsize);
4268
                }
4269
        } else {
4270
                if (packetsize == -1) {
4271
                        ov511_set_packet_size(ov, size);
4272
                } else {
4273
                        info("Forcing packet size to %d", packetsize);
4274
                        ov511_set_packet_size(ov, packetsize);
4275
                }
4276
        }
4277
 
4278
        for (n = 0; n < OV511_NUMSBUF; n++) {
4279
                urb = usb_alloc_urb(FRAMES_PER_DESC);
4280
 
4281
                if (!urb) {
4282
                        err("init isoc: usb_alloc_urb ret. NULL");
4283
                        return -ENOMEM;
4284
                }
4285
                ov->sbuf[n].urb = urb;
4286
                urb->dev = ov->dev;
4287
                urb->context = &ov->sbuf[n];
4288
                urb->pipe = usb_rcvisocpipe(ov->dev, OV511_ENDPOINT_ADDRESS);
4289
                urb->transfer_flags = USB_ISO_ASAP;
4290
                urb->transfer_buffer = ov->sbuf[n].data;
4291
                urb->complete = ov51x_isoc_irq;
4292
                urb->number_of_packets = FRAMES_PER_DESC;
4293
                urb->transfer_buffer_length = ov->packet_size * FRAMES_PER_DESC;
4294
                urb->interval = 1;
4295
                for (fx = 0; fx < FRAMES_PER_DESC; fx++) {
4296
                        urb->iso_frame_desc[fx].offset = ov->packet_size * fx;
4297
                        urb->iso_frame_desc[fx].length = ov->packet_size;
4298
                }
4299
        }
4300
 
4301
        ov->streaming = 1;
4302
 
4303
        for (n = 0; n < OV511_NUMSBUF; n++) {
4304
                ov->sbuf[n].urb->dev = ov->dev;
4305
                err = usb_submit_urb(ov->sbuf[n].urb);
4306
                if (err) {
4307
                        err("init isoc: usb_submit_urb(%d) ret %d", n, err);
4308
                        return err;
4309
                }
4310
        }
4311
 
4312
        return 0;
4313
}
4314
 
4315
static void
4316
ov51x_unlink_isoc(struct usb_ov511 *ov)
4317
{
4318
        int n;
4319
 
4320
        /* Unschedule all of the iso td's */
4321
        for (n = OV511_NUMSBUF - 1; n >= 0; n--) {
4322
                if (ov->sbuf[n].urb) {
4323
                        usb_unlink_urb(ov->sbuf[n].urb);
4324
                        usb_free_urb(ov->sbuf[n].urb);
4325
                        ov->sbuf[n].urb = NULL;
4326
                }
4327
        }
4328
}
4329
 
4330
static void
4331
ov51x_stop_isoc(struct usb_ov511 *ov)
4332
{
4333
        if (!ov->streaming || !ov->dev)
4334
                return;
4335
 
4336
        PDEBUG(3, "*** Stopping capture ***");
4337
 
4338
        if (ov->bclass == BCL_OV518)
4339
                ov518_set_packet_size(ov, 0);
4340
        else
4341
                ov511_set_packet_size(ov, 0);
4342
 
4343
        ov->streaming = 0;
4344
 
4345
        ov51x_unlink_isoc(ov);
4346
}
4347
 
4348
static int
4349
ov51x_new_frame(struct usb_ov511 *ov, int framenum)
4350
{
4351
        struct ov511_frame *frame;
4352
        int newnum;
4353
 
4354
        PDEBUG(4, "ov->curframe = %d, framenum = %d", ov->curframe, framenum);
4355
 
4356
        if (!ov->dev)
4357
                return -1;
4358
 
4359
        /* If we're not grabbing a frame right now and the other frame is */
4360
        /* ready to be grabbed into, then use it instead */
4361
        if (ov->curframe == -1) {
4362
                newnum = (framenum - 1 + OV511_NUMFRAMES) % OV511_NUMFRAMES;
4363
                if (ov->frame[newnum].grabstate == FRAME_READY)
4364
                        framenum = newnum;
4365
        } else
4366
                return 0;
4367
 
4368
        frame = &ov->frame[framenum];
4369
 
4370
        PDEBUG(4, "framenum = %d, width = %d, height = %d", framenum,
4371
               frame->width, frame->height);
4372
 
4373
        frame->grabstate = FRAME_GRABBING;
4374
        frame->scanstate = STATE_SCANNING;
4375
        frame->snapshot = 0;
4376
 
4377
        ov->curframe = framenum;
4378
 
4379
        /* Make sure it's not too big */
4380
        if (frame->width > ov->maxwidth)
4381
                frame->width = ov->maxwidth;
4382
 
4383
        frame->width &= ~7L;            /* Multiple of 8 */
4384
 
4385
        if (frame->height > ov->maxheight)
4386
                frame->height = ov->maxheight;
4387
 
4388
        frame->height &= ~3L;           /* Multiple of 4 */
4389
 
4390
        return 0;
4391
}
4392
 
4393
/****************************************************************************
4394
 *
4395
 * Buffer management
4396
 *
4397
 ***************************************************************************/
4398
 
4399
/*
4400
 * - You must acquire buf_lock before entering this function.
4401
 * - Because this code will free any non-null pointer, you must be sure to null
4402
 *   them if you explicitly free them somewhere else!
4403
 */
4404
static void
4405
ov51x_do_dealloc(struct usb_ov511 *ov)
4406
{
4407
        int i;
4408
        PDEBUG(4, "entered");
4409
 
4410
        if (ov->fbuf) {
4411
                rvfree(ov->fbuf, OV511_NUMFRAMES
4412
                       * MAX_DATA_SIZE(ov->maxwidth, ov->maxheight));
4413
                ov->fbuf = NULL;
4414
        }
4415
 
4416
        if (ov->rawfbuf) {
4417
                vfree(ov->rawfbuf);
4418
                ov->rawfbuf = NULL;
4419
        }
4420
 
4421
        if (ov->tempfbuf) {
4422
                vfree(ov->tempfbuf);
4423
                ov->tempfbuf = NULL;
4424
        }
4425
 
4426
        for (i = 0; i < OV511_NUMSBUF; i++) {
4427
                if (ov->sbuf[i].data) {
4428
                        kfree(ov->sbuf[i].data);
4429
                        ov->sbuf[i].data = NULL;
4430
                }
4431
        }
4432
 
4433
        for (i = 0; i < OV511_NUMFRAMES; i++) {
4434
                ov->frame[i].data = NULL;
4435
                ov->frame[i].rawdata = NULL;
4436
                ov->frame[i].tempdata = NULL;
4437
                if (ov->frame[i].compbuf) {
4438
                        free_page((unsigned long) ov->frame[i].compbuf);
4439
                        ov->frame[i].compbuf = NULL;
4440
                }
4441
        }
4442
 
4443
        PDEBUG(4, "buffer memory deallocated");
4444
        ov->buf_state = BUF_NOT_ALLOCATED;
4445
        PDEBUG(4, "leaving");
4446
}
4447
 
4448
static int
4449
ov51x_alloc(struct usb_ov511 *ov)
4450
{
4451
        int i;
4452
        const int w = ov->maxwidth;
4453
        const int h = ov->maxheight;
4454
        const int data_bufsize = OV511_NUMFRAMES * MAX_DATA_SIZE(w, h);
4455
        const int raw_bufsize = OV511_NUMFRAMES * MAX_RAW_DATA_SIZE(w, h);
4456
 
4457
        PDEBUG(4, "entered");
4458
        down(&ov->buf_lock);
4459
 
4460
        if (ov->buf_state == BUF_ALLOCATED)
4461
                goto out;
4462
 
4463
        ov->fbuf = rvmalloc(data_bufsize);
4464
        if (!ov->fbuf)
4465
                goto error;
4466
 
4467
        ov->rawfbuf = vmalloc(raw_bufsize);
4468
        if (!ov->rawfbuf)
4469
                goto error;
4470
 
4471
        memset(ov->rawfbuf, 0, raw_bufsize);
4472
 
4473
        ov->tempfbuf = vmalloc(raw_bufsize);
4474
        if (!ov->tempfbuf)
4475
                goto error;
4476
 
4477
        memset(ov->tempfbuf, 0, raw_bufsize);
4478
 
4479
        for (i = 0; i < OV511_NUMSBUF; i++) {
4480
                ov->sbuf[i].data = kmalloc(FRAMES_PER_DESC *
4481
                        MAX_FRAME_SIZE_PER_DESC, GFP_KERNEL);
4482
                if (!ov->sbuf[i].data)
4483
                        goto error;
4484
 
4485
                PDEBUG(4, "sbuf[%d] @ %p", i, ov->sbuf[i].data);
4486
        }
4487
 
4488
        for (i = 0; i < OV511_NUMFRAMES; i++) {
4489
                ov->frame[i].data = ov->fbuf + i * MAX_DATA_SIZE(w, h);
4490
                ov->frame[i].rawdata = ov->rawfbuf
4491
                 + i * MAX_RAW_DATA_SIZE(w, h);
4492
                ov->frame[i].tempdata = ov->tempfbuf
4493
                 + i * MAX_RAW_DATA_SIZE(w, h);
4494
 
4495
                ov->frame[i].compbuf =
4496
                 (unsigned char *) __get_free_page(GFP_KERNEL);
4497
                if (!ov->frame[i].compbuf)
4498
                        goto error;
4499
 
4500
                PDEBUG(4, "frame[%d] @ %p", i, ov->frame[i].data);
4501
        }
4502
 
4503
        ov->buf_state = BUF_ALLOCATED;
4504
out:
4505
        up(&ov->buf_lock);
4506
        PDEBUG(4, "leaving");
4507
        return 0;
4508
error:
4509
        ov51x_do_dealloc(ov);
4510
        up(&ov->buf_lock);
4511
        PDEBUG(4, "errored");
4512
        return -ENOMEM;
4513
}
4514
 
4515
static void
4516
ov51x_dealloc(struct usb_ov511 *ov, int now)
4517
{
4518
        PDEBUG(4, "entered");
4519
        down(&ov->buf_lock);
4520
        ov51x_do_dealloc(ov);
4521
        up(&ov->buf_lock);
4522
        PDEBUG(4, "leaving");
4523
}
4524
 
4525
/****************************************************************************
4526
 *
4527
 * V4L 1 API
4528
 *
4529
 ***************************************************************************/
4530
 
4531
static int
4532
ov51x_v4l1_open(struct inode *inode, struct file *file)
4533
{
4534
        struct video_device *vdev = video_devdata(file);
4535
        struct usb_ov511 *ov = vdev->priv;
4536
        int err, i;
4537
 
4538
        PDEBUG(4, "opening");
4539
 
4540
        down(&ov->lock);
4541
 
4542
        err = -EBUSY;
4543
        if (ov->user)
4544
                goto out;
4545
 
4546
        err = ov51x_alloc(ov);
4547
        if (err < 0)
4548
                goto out;
4549
 
4550
        ov->sub_flag = 0;
4551
 
4552
        /* In case app doesn't set them... */
4553
        err = ov51x_set_default_params(ov);
4554
        if (err < 0)
4555
                goto out;
4556
 
4557
        /* Make sure frames are reset */
4558
        for (i = 0; i < OV511_NUMFRAMES; i++) {
4559
                ov->frame[i].grabstate = FRAME_UNUSED;
4560
                ov->frame[i].bytes_read = 0;
4561
        }
4562
 
4563
        /* If compression is on, make sure now that a
4564
         * decompressor can be loaded */
4565
        if (ov->compress && !ov->decomp_ops) {
4566
                err = request_decompressor(ov);
4567
                if (err && !dumppix)
4568
                        goto out;
4569
        }
4570
 
4571
        err = ov51x_init_isoc(ov);
4572
        if (err) {
4573
                ov51x_dealloc(ov, 0);
4574
                goto out;
4575
        }
4576
 
4577
        ov->user++;
4578
        file->private_data = vdev;
4579
 
4580
        if (ov->led_policy == LED_AUTO)
4581
                ov51x_led_control(ov, 1);
4582
 
4583
out:
4584
        up(&ov->lock);
4585
        return err;
4586
}
4587
 
4588
static int
4589
ov51x_v4l1_close(struct inode *inode, struct file *file)
4590
{
4591
        struct video_device *vdev = file->private_data;
4592
        struct usb_ov511 *ov = vdev->priv;
4593
 
4594
        PDEBUG(4, "ov511_close");
4595
 
4596
        down(&ov->lock);
4597
 
4598
        ov->user--;
4599
        ov51x_stop_isoc(ov);
4600
 
4601
        release_decompressor(ov);
4602
 
4603
        if (ov->led_policy == LED_AUTO)
4604
                ov51x_led_control(ov, 0);
4605
 
4606
        if (ov->dev)
4607
                ov51x_dealloc(ov, 0);
4608
 
4609
        up(&ov->lock);
4610
 
4611
        /* Device unplugged while open. Only a minimum of unregistration is done
4612
         * here; the disconnect callback already did the rest. */
4613
        if (!ov->dev) {
4614
                down(&ov->cbuf_lock);
4615
                kfree(ov->cbuf);
4616
                ov->cbuf = NULL;
4617
                up(&ov->cbuf_lock);
4618
 
4619
                ov51x_dealloc(ov, 1);
4620
                kfree(ov);
4621
                ov = NULL;
4622
        }
4623
 
4624
        file->private_data = NULL;
4625
        return 0;
4626
}
4627
 
4628
/* Do not call this function directly! */
4629
static int
4630
ov51x_v4l1_ioctl_internal(struct inode *inode, struct file *file,
4631
                          unsigned int cmd, void *arg)
4632
{
4633
        struct video_device *vdev = file->private_data;
4634
        struct usb_ov511 *ov = vdev->priv;
4635
 
4636
        PDEBUG(5, "IOCtl: 0x%X", cmd);
4637
 
4638
        if (!ov->dev)
4639
                return -EIO;
4640
 
4641
        switch (cmd) {
4642
        case VIDIOCGCAP:
4643
        {
4644
                struct video_capability *b = arg;
4645
 
4646
                PDEBUG(4, "VIDIOCGCAP");
4647
 
4648
                memset(b, 0, sizeof(struct video_capability));
4649
                sprintf(b->name, "%s USB Camera",
4650
                        symbolic(brglist, ov->bridge));
4651
                b->type = VID_TYPE_CAPTURE | VID_TYPE_SUBCAPTURE;
4652
                b->channels = ov->num_inputs;
4653
                b->audios = 0;
4654
                b->maxwidth = ov->maxwidth;
4655
                b->maxheight = ov->maxheight;
4656
                b->minwidth = ov->minwidth;
4657
                b->minheight = ov->minheight;
4658
 
4659
                return 0;
4660
        }
4661
        case VIDIOCGCHAN:
4662
        {
4663
                struct video_channel *v = arg;
4664
 
4665
                PDEBUG(4, "VIDIOCGCHAN");
4666
 
4667
                if ((unsigned)(v->channel) >= ov->num_inputs) {
4668
                        err("Invalid channel (%d)", v->channel);
4669
                        return -EINVAL;
4670
                }
4671
 
4672
                v->norm = ov->norm;
4673
                v->type = VIDEO_TYPE_CAMERA;
4674
                v->flags = 0;
4675
//              v->flags |= (ov->has_decoder) ? VIDEO_VC_NORM : 0;
4676
                v->tuners = 0;
4677
                decoder_get_input_name(ov, v->channel, v->name);
4678
 
4679
                return 0;
4680
        }
4681
        case VIDIOCSCHAN:
4682
        {
4683
                struct video_channel *v = arg;
4684
                int err;
4685
 
4686
                PDEBUG(4, "VIDIOCSCHAN");
4687
 
4688
                /* Make sure it's not a camera */
4689
                if (!ov->has_decoder) {
4690
                        if (v->channel == 0)
4691
                                return 0;
4692
                        else
4693
                                return -EINVAL;
4694
                }
4695
 
4696
                if (v->norm != VIDEO_MODE_PAL &&
4697
                    v->norm != VIDEO_MODE_NTSC &&
4698
                    v->norm != VIDEO_MODE_SECAM &&
4699
                    v->norm != VIDEO_MODE_AUTO) {
4700
                        err("Invalid norm (%d)", v->norm);
4701
                        return -EINVAL;
4702
                }
4703
 
4704
                if ((unsigned)(v->channel) >= ov->num_inputs) {
4705
                        err("Invalid channel (%d)", v->channel);
4706
                        return -EINVAL;
4707
                }
4708
 
4709
                err = decoder_set_input(ov, v->channel);
4710
                if (err)
4711
                        return err;
4712
 
4713
                err = decoder_set_norm(ov, v->norm);
4714
                if (err)
4715
                        return err;
4716
 
4717
                return 0;
4718
        }
4719
        case VIDIOCGPICT:
4720
        {
4721
                struct video_picture *p = arg;
4722
 
4723
                PDEBUG(4, "VIDIOCGPICT");
4724
 
4725
                memset(p, 0, sizeof(struct video_picture));
4726
                if (sensor_get_picture(ov, p))
4727
                        return -EIO;
4728
 
4729
                /* Can we get these from frame[0]? -claudio? */
4730
                p->depth = ov->frame[0].depth;
4731
                p->palette = ov->frame[0].format;
4732
 
4733
                return 0;
4734
        }
4735
        case VIDIOCSPICT:
4736
        {
4737
                struct video_picture *p = arg;
4738
                int i;
4739
 
4740
                PDEBUG(4, "VIDIOCSPICT");
4741
 
4742
                if (!get_depth(p->palette))
4743
                        return -EINVAL;
4744
 
4745
                if (sensor_set_picture(ov, p))
4746
                        return -EIO;
4747
 
4748
                if (force_palette && p->palette != force_palette) {
4749
                        info("Palette rejected (%s)",
4750
                             symbolic(v4l1_plist, p->palette));
4751
                        return -EINVAL;
4752
                }
4753
 
4754
                // FIXME: Format should be independent of frames
4755
                if (p->palette != ov->frame[0].format) {
4756
                        PDEBUG(4, "Detected format change");
4757
 
4758
                        /* If we're collecting previous frame wait
4759
                           before changing modes */
4760
                        interruptible_sleep_on(&ov->wq);
4761
                        if (signal_pending(current)) return -EINTR;
4762
 
4763
                        mode_init_regs(ov, ov->frame[0].width,
4764
                                ov->frame[0].height, p->palette, ov->sub_flag);
4765
                }
4766
 
4767
                PDEBUG(4, "Setting depth=%d, palette=%s",
4768
                       p->depth, symbolic(v4l1_plist, p->palette));
4769
 
4770
                for (i = 0; i < OV511_NUMFRAMES; i++) {
4771
                        ov->frame[i].depth = p->depth;
4772
                        ov->frame[i].format = p->palette;
4773
                }
4774
 
4775
                return 0;
4776
        }
4777
        case VIDIOCGCAPTURE:
4778
        {
4779
                int *vf = arg;
4780
 
4781
                PDEBUG(4, "VIDIOCGCAPTURE");
4782
 
4783
                ov->sub_flag = *vf;
4784
                return 0;
4785
        }
4786
        case VIDIOCSCAPTURE:
4787
        {
4788
                struct video_capture *vc = arg;
4789
 
4790
                PDEBUG(4, "VIDIOCSCAPTURE");
4791
 
4792
                if (vc->flags)
4793
                        return -EINVAL;
4794
                if (vc->decimation)
4795
                        return -EINVAL;
4796
 
4797
                vc->x &= ~3L;
4798
                vc->y &= ~1L;
4799
                vc->y &= ~31L;
4800
 
4801
                if (vc->width == 0)
4802
                        vc->width = 32;
4803
 
4804
                vc->height /= 16;
4805
                vc->height *= 16;
4806
                if (vc->height == 0)
4807
                        vc->height = 16;
4808
 
4809
                ov->subx = vc->x;
4810
                ov->suby = vc->y;
4811
                ov->subw = vc->width;
4812
                ov->subh = vc->height;
4813
 
4814
                return 0;
4815
        }
4816
        case VIDIOCSWIN:
4817
        {
4818
                struct video_window *vw = arg;
4819
                int i, result;
4820
 
4821
                PDEBUG(4, "VIDIOCSWIN: %dx%d", vw->width, vw->height);
4822
 
4823
#if 0
4824
                if (vw->flags)
4825
                        return -EINVAL;
4826
                if (vw->clipcount)
4827
                        return -EINVAL;
4828
                if (vw->height != ov->maxheight)
4829
                        return -EINVAL;
4830
                if (vw->width != ov->maxwidth)
4831
                        return -EINVAL;
4832
#endif
4833
 
4834
                /* If we're collecting previous frame wait
4835
                   before changing modes */
4836
                interruptible_sleep_on(&ov->wq);
4837
                if (signal_pending(current)) return -EINTR;
4838
 
4839
                result = mode_init_regs(ov, vw->width, vw->height,
4840
                        ov->frame[0].format, ov->sub_flag);
4841
                if (result < 0)
4842
                        return result;
4843
 
4844
                for (i = 0; i < OV511_NUMFRAMES; i++) {
4845
                        ov->frame[i].width = vw->width;
4846
                        ov->frame[i].height = vw->height;
4847
                }
4848
 
4849
                return 0;
4850
        }
4851
        case VIDIOCGWIN:
4852
        {
4853
                struct video_window *vw = arg;
4854
 
4855
                memset(vw, 0, sizeof(struct video_window));
4856
                vw->x = 0;               /* FIXME */
4857
                vw->y = 0;
4858
                vw->width = ov->frame[0].width;
4859
                vw->height = ov->frame[0].height;
4860
                vw->flags = 30;
4861
 
4862
                PDEBUG(4, "VIDIOCGWIN: %dx%d", vw->width, vw->height);
4863
 
4864
                return 0;
4865
        }
4866
        case VIDIOCGMBUF:
4867
        {
4868
                struct video_mbuf *vm = arg;
4869
                int i;
4870
 
4871
                PDEBUG(4, "VIDIOCGMBUF");
4872
 
4873
                memset(vm, 0, sizeof(struct video_mbuf));
4874
                vm->size = OV511_NUMFRAMES
4875
                           * MAX_DATA_SIZE(ov->maxwidth, ov->maxheight);
4876
                vm->frames = OV511_NUMFRAMES;
4877
 
4878
                vm->offsets[0] = 0;
4879
                for (i = 1; i < OV511_NUMFRAMES; i++) {
4880
                        vm->offsets[i] = vm->offsets[i-1]
4881
                           + MAX_DATA_SIZE(ov->maxwidth, ov->maxheight);
4882
                }
4883
 
4884
                return 0;
4885
        }
4886
        case VIDIOCMCAPTURE:
4887
        {
4888
                struct video_mmap *vm = arg;
4889
                int ret, depth;
4890
                unsigned int f = vm->frame;
4891
 
4892
                PDEBUG(4, "VIDIOCMCAPTURE: frame: %d, %dx%d, %s", f, vm->width,
4893
                        vm->height, symbolic(v4l1_plist, vm->format));
4894
 
4895
                depth = get_depth(vm->format);
4896
                if (!depth) {
4897
                        PDEBUG(2, "VIDIOCMCAPTURE: invalid format (%s)",
4898
                               symbolic(v4l1_plist, vm->format));
4899
                        return -EINVAL;
4900
                }
4901
 
4902
                if (f >= OV511_NUMFRAMES) {
4903
                        err("VIDIOCMCAPTURE: invalid frame (%d)", f);
4904
                        return -EINVAL;
4905
                }
4906
 
4907
                if (vm->width > ov->maxwidth
4908
                    || vm->height > ov->maxheight) {
4909
                        err("VIDIOCMCAPTURE: requested dimensions too big");
4910
                        return -EINVAL;
4911
                }
4912
 
4913
                if (ov->frame[f].grabstate == FRAME_GRABBING) {
4914
                        PDEBUG(4, "VIDIOCMCAPTURE: already grabbing");
4915
                        return -EBUSY;
4916
                }
4917
 
4918
                if (force_palette && (vm->format != force_palette)) {
4919
                        PDEBUG(2, "palette rejected (%s)",
4920
                               symbolic(v4l1_plist, vm->format));
4921
                        return -EINVAL;
4922
                }
4923
 
4924
                if ((ov->frame[f].width != vm->width) ||
4925
                    (ov->frame[f].height != vm->height) ||
4926
                    (ov->frame[f].format != vm->format) ||
4927
                    (ov->frame[f].sub_flag != ov->sub_flag) ||
4928
                    (ov->frame[f].depth != depth)) {
4929
                        PDEBUG(4, "VIDIOCMCAPTURE: change in image parameters");
4930
 
4931
                        /* If we're collecting previous frame wait
4932
                           before changing modes */
4933
                        interruptible_sleep_on(&ov->wq);
4934
                        if (signal_pending(current)) return -EINTR;
4935
                        ret = mode_init_regs(ov, vm->width, vm->height,
4936
                                vm->format, ov->sub_flag);
4937
#if 0
4938
                        if (ret < 0) {
4939
                                PDEBUG(1, "Got error while initializing regs ");
4940
                                return ret;
4941
                        }
4942
#endif
4943
                        ov->frame[f].width = vm->width;
4944
                        ov->frame[f].height = vm->height;
4945
                        ov->frame[f].format = vm->format;
4946
                        ov->frame[f].sub_flag = ov->sub_flag;
4947
                        ov->frame[f].depth = depth;
4948
                }
4949
 
4950
                /* Mark it as ready */
4951
                ov->frame[f].grabstate = FRAME_READY;
4952
 
4953
                PDEBUG(4, "VIDIOCMCAPTURE: renewing frame %d", f);
4954
 
4955
                return ov51x_new_frame(ov, f);
4956
        }
4957
        case VIDIOCSYNC:
4958
        {
4959
                unsigned int fnum = *((unsigned int *) arg);
4960
                struct ov511_frame *frame;
4961
                int rc;
4962
 
4963
                if (fnum >= OV511_NUMFRAMES) {
4964
                        err("VIDIOCSYNC: invalid frame (%d)", fnum);
4965
                        return -EINVAL;
4966
                }
4967
 
4968
                frame = &ov->frame[fnum];
4969
 
4970
                PDEBUG(4, "syncing to frame %d, grabstate = %d", fnum,
4971
                       frame->grabstate);
4972
 
4973
                switch (frame->grabstate) {
4974
                case FRAME_UNUSED:
4975
                        return -EINVAL;
4976
                case FRAME_READY:
4977
                case FRAME_GRABBING:
4978
                case FRAME_ERROR:
4979
redo:
4980
                        if (!ov->dev)
4981
                                return -EIO;
4982
 
4983
                        rc = wait_event_interruptible(frame->wq,
4984
                            (frame->grabstate == FRAME_DONE)
4985
                            || (frame->grabstate == FRAME_ERROR));
4986
 
4987
                        if (rc)
4988
                                return rc;
4989
 
4990
                        if (frame->grabstate == FRAME_ERROR) {
4991
                                int ret;
4992
 
4993
                                if ((ret = ov51x_new_frame(ov, fnum)) < 0)
4994
                                        return ret;
4995
                                goto redo;
4996
                        }
4997
                        /* Fall through */
4998
                case FRAME_DONE:
4999
                        if (ov->snap_enabled && !frame->snapshot) {
5000
                                int ret;
5001
                                if ((ret = ov51x_new_frame(ov, fnum)) < 0)
5002
                                        return ret;
5003
                                goto redo;
5004
                        }
5005
 
5006
                        frame->grabstate = FRAME_UNUSED;
5007
 
5008
                        /* Reset the hardware snapshot button */
5009
                        /* FIXME - Is this the best place for this? */
5010
                        if ((ov->snap_enabled) && (frame->snapshot)) {
5011
                                frame->snapshot = 0;
5012
                                ov51x_clear_snapshot(ov);
5013
                        }
5014
 
5015
                        /* Decompression, format conversion, etc... */
5016
                        ov51x_postprocess(ov, frame);
5017
 
5018
                        break;
5019
                } /* end switch */
5020
 
5021
                return 0;
5022
        }
5023
        case VIDIOCGFBUF:
5024
        {
5025
                struct video_buffer *vb = arg;
5026
 
5027
                PDEBUG(4, "VIDIOCGFBUF");
5028
 
5029
                memset(vb, 0, sizeof(struct video_buffer));
5030
 
5031
                return 0;
5032
        }
5033
        case VIDIOCGUNIT:
5034
        {
5035
                struct video_unit *vu = arg;
5036
 
5037
                PDEBUG(4, "VIDIOCGUNIT");
5038
 
5039
                memset(vu, 0, sizeof(struct video_unit));
5040
 
5041
                vu->video = ov->vdev.minor;
5042
                vu->vbi = VIDEO_NO_UNIT;
5043
                vu->radio = VIDEO_NO_UNIT;
5044
                vu->audio = VIDEO_NO_UNIT;
5045
                vu->teletext = VIDEO_NO_UNIT;
5046
 
5047
                return 0;
5048
        }
5049
        case OV511IOC_WI2C:
5050
        {
5051
                struct ov511_i2c_struct *w = arg;
5052
 
5053
                return i2c_w_slave(ov, w->slave, w->reg, w->value, w->mask);
5054
        }
5055
        case OV511IOC_RI2C:
5056
        {
5057
                struct ov511_i2c_struct *r = arg;
5058
                int rc;
5059
 
5060
                rc = i2c_r_slave(ov, r->slave, r->reg);
5061
                if (rc < 0)
5062
                        return rc;
5063
 
5064
                r->value = rc;
5065
                return 0;
5066
        }
5067
        default:
5068
                PDEBUG(3, "Unsupported IOCtl: 0x%X", cmd);
5069
                return -ENOIOCTLCMD;
5070
        } /* end switch */
5071
 
5072
        return 0;
5073
}
5074
 
5075
static int
5076
ov51x_v4l1_ioctl(struct inode *inode, struct file *file,
5077
                 unsigned int cmd, unsigned long arg)
5078
{
5079
        struct video_device *vdev = file->private_data;
5080
        struct usb_ov511 *ov = vdev->priv;
5081
        int rc;
5082
 
5083
        if (down_interruptible(&ov->lock))
5084
                return -EINTR;
5085
 
5086
        rc = video_usercopy(inode, file, cmd, arg, ov51x_v4l1_ioctl_internal);
5087
 
5088
        up(&ov->lock);
5089
        return rc;
5090
}
5091
 
5092
static int
5093
ov51x_v4l1_read(struct file *file, char *buf, size_t cnt, loff_t *ppos)
5094
{
5095
        struct video_device *vdev = file->private_data;
5096
        int noblock = file->f_flags&O_NONBLOCK;
5097
        unsigned long count = cnt;
5098
        struct usb_ov511 *ov = vdev->priv;
5099
        int i, rc = 0, frmx = -1;
5100
        struct ov511_frame *frame;
5101
 
5102
        if (down_interruptible(&ov->lock))
5103
                return -EINTR;
5104
 
5105
        PDEBUG(4, "%ld bytes, noblock=%d", count, noblock);
5106
 
5107
        if (!vdev || !buf) {
5108
                rc = -EFAULT;
5109
                goto error;
5110
        }
5111
 
5112
        if (!ov->dev) {
5113
                rc = -EIO;
5114
                goto error;
5115
        }
5116
 
5117
// FIXME: Only supports two frames
5118
        /* See if a frame is completed, then use it. */
5119
        if (ov->frame[0].grabstate >= FRAME_DONE)        /* _DONE or _ERROR */
5120
                frmx = 0;
5121
        else if (ov->frame[1].grabstate >= FRAME_DONE)/* _DONE or _ERROR */
5122
                frmx = 1;
5123
 
5124
        /* If nonblocking we return immediately */
5125
        if (noblock && (frmx == -1)) {
5126
                rc = -EAGAIN;
5127
                goto error;
5128
        }
5129
 
5130
        /* If no FRAME_DONE, look for a FRAME_GRABBING state. */
5131
        /* See if a frame is in process (grabbing), then use it. */
5132
        if (frmx == -1) {
5133
                if (ov->frame[0].grabstate == FRAME_GRABBING)
5134
                        frmx = 0;
5135
                else if (ov->frame[1].grabstate == FRAME_GRABBING)
5136
                        frmx = 1;
5137
        }
5138
 
5139
        /* If no frame is active, start one. */
5140
        if (frmx == -1) {
5141
                if ((rc = ov51x_new_frame(ov, frmx = 0))) {
5142
                        err("read: ov51x_new_frame error");
5143
                        goto error;
5144
                }
5145
        }
5146
 
5147
        frame = &ov->frame[frmx];
5148
 
5149
restart:
5150
        if (!ov->dev) {
5151
                rc = -EIO;
5152
                goto error;
5153
        }
5154
 
5155
        /* Wait while we're grabbing the image */
5156
        PDEBUG(4, "Waiting image grabbing");
5157
        rc = wait_event_interruptible(frame->wq,
5158
                (frame->grabstate == FRAME_DONE)
5159
                || (frame->grabstate == FRAME_ERROR));
5160
 
5161
        if (rc)
5162
                goto error;
5163
 
5164
        PDEBUG(4, "Got image, frame->grabstate = %d", frame->grabstate);
5165
        PDEBUG(4, "bytes_recvd = %d", frame->bytes_recvd);
5166
 
5167
        if (frame->grabstate == FRAME_ERROR) {
5168
                frame->bytes_read = 0;
5169
                err("** ick! ** Errored frame %d", ov->curframe);
5170
                if (ov51x_new_frame(ov, frmx)) {
5171
                        err("read: ov51x_new_frame error");
5172
                        goto error;
5173
                }
5174
                goto restart;
5175
        }
5176
 
5177
 
5178
        /* Repeat until we get a snapshot frame */
5179
        if (ov->snap_enabled)
5180
                PDEBUG(4, "Waiting snapshot frame");
5181
        if (ov->snap_enabled && !frame->snapshot) {
5182
                frame->bytes_read = 0;
5183
                if ((rc = ov51x_new_frame(ov, frmx))) {
5184
                        err("read: ov51x_new_frame error");
5185
                        goto error;
5186
                }
5187
                goto restart;
5188
        }
5189
 
5190
        /* Clear the snapshot */
5191
        if (ov->snap_enabled && frame->snapshot) {
5192
                frame->snapshot = 0;
5193
                ov51x_clear_snapshot(ov);
5194
        }
5195
 
5196
        /* Decompression, format conversion, etc... */
5197
        ov51x_postprocess(ov, frame);
5198
 
5199
        PDEBUG(4, "frmx=%d, bytes_read=%ld, length=%ld", frmx,
5200
                frame->bytes_read,
5201
                get_frame_length(frame));
5202
 
5203
        /* copy bytes to user space; we allow for partials reads */
5204
//      if ((count + frame->bytes_read)
5205
//          > get_frame_length((struct ov511_frame *)frame))
5206
//              count = frame->scanlength - frame->bytes_read;
5207
 
5208
        /* FIXME - count hardwired to be one frame... */
5209
        count = get_frame_length(frame);
5210
 
5211
        PDEBUG(4, "Copy to user space: %ld bytes", count);
5212
        if ((i = copy_to_user(buf, frame->data + frame->bytes_read, count))) {
5213
                PDEBUG(4, "Copy failed! %d bytes not copied", i);
5214
                rc = -EFAULT;
5215
                goto error;
5216
        }
5217
 
5218
        frame->bytes_read += count;
5219
        PDEBUG(4, "{copy} count used=%ld, new bytes_read=%ld",
5220
                count, frame->bytes_read);
5221
 
5222
        /* If all data have been read... */
5223
        if (frame->bytes_read
5224
            >= get_frame_length(frame)) {
5225
                frame->bytes_read = 0;
5226
 
5227
// FIXME: Only supports two frames
5228
                /* Mark it as available to be used again. */
5229
                ov->frame[frmx].grabstate = FRAME_UNUSED;
5230
                if ((rc = ov51x_new_frame(ov, !frmx))) {
5231
                        err("ov51x_new_frame returned error");
5232
                        goto error;
5233
                }
5234
        }
5235
 
5236
        PDEBUG(4, "read finished, returning %ld (sweet)", count);
5237
 
5238
        up(&ov->lock);
5239
        return count;
5240
 
5241
error:
5242
        up(&ov->lock);
5243
        return rc;
5244
}
5245
 
5246
static int
5247
ov51x_v4l1_mmap(struct file *file, struct vm_area_struct *vma)
5248
{
5249
        struct video_device *vdev = file->private_data;
5250
        unsigned long start = vma->vm_start;
5251
        unsigned long size  = vma->vm_end - vma->vm_start;
5252
        struct usb_ov511 *ov = vdev->priv;
5253
        unsigned long page, pos;
5254
 
5255
        if (ov->dev == NULL)
5256
                return -EIO;
5257
 
5258
        PDEBUG(4, "mmap: %ld (%lX) bytes", size, size);
5259
 
5260
        if (size > (((OV511_NUMFRAMES
5261
                      * MAX_DATA_SIZE(ov->maxwidth, ov->maxheight)
5262
                      + PAGE_SIZE - 1) & ~(PAGE_SIZE - 1))))
5263
                return -EINVAL;
5264
 
5265
        if (down_interruptible(&ov->lock))
5266
                return -EINTR;
5267
 
5268
        pos = (unsigned long)ov->fbuf;
5269
        while (size > 0) {
5270
                page = kvirt_to_pa(pos);
5271
                if (remap_page_range(start, page, PAGE_SIZE, PAGE_SHARED)) {
5272
                        up(&ov->lock);
5273
                        return -EAGAIN;
5274
                }
5275
                start += PAGE_SIZE;
5276
                pos += PAGE_SIZE;
5277
                if (size > PAGE_SIZE)
5278
                        size -= PAGE_SIZE;
5279
                else
5280
                        size = 0;
5281
        }
5282
 
5283
        up(&ov->lock);
5284
        return 0;
5285
}
5286
 
5287
static struct file_operations ov511_fops = {
5288
        .owner =        THIS_MODULE,
5289
        .open =         ov51x_v4l1_open,
5290
        .release =      ov51x_v4l1_close,
5291
        .read =         ov51x_v4l1_read,
5292
        .mmap =         ov51x_v4l1_mmap,
5293
        .ioctl =        ov51x_v4l1_ioctl,
5294
        .llseek =       no_llseek,
5295
};
5296
 
5297
static struct video_device vdev_template = {
5298
        .owner =        THIS_MODULE,
5299
        .name =         "OV511 USB Camera",
5300
        .type =         VID_TYPE_CAPTURE,
5301
        .hardware =     VID_HARDWARE_OV511,
5302
        .fops =         &ov511_fops,
5303
};
5304
 
5305
#if defined(CONFIG_PROC_FS) && defined(CONFIG_VIDEO_PROC_FS)
5306
static int
5307
ov51x_control_ioctl(struct inode *inode, struct file *file, unsigned int cmd,
5308
                    unsigned long ularg)
5309
{
5310
        struct proc_dir_entry *pde = inode->u.generic_ip;
5311
        struct usb_ov511 *ov;
5312
        void *arg = (void *) ularg;
5313
        int rc;
5314
 
5315
        if (!pde)
5316
                return -ENOENT;
5317
 
5318
        ov = pde->data;
5319
        if (!ov)
5320
                return -ENODEV;
5321
 
5322
        if (!ov->dev)
5323
                return -EIO;
5324
 
5325
        /* Should we pass through standard V4L IOCTLs? */
5326
 
5327
        switch (cmd) {
5328
        case OV511IOC_GINTVER:
5329
        {
5330
                int ver = OV511_INTERFACE_VER;
5331
 
5332
                PDEBUG(4, "Get interface version: %d", ver);
5333
                if (copy_to_user(arg, &ver, sizeof(ver)))
5334
                        return -EFAULT;
5335
 
5336
                return 0;
5337
        }
5338
        case OV511IOC_GUSHORT:
5339
        {
5340
                struct ov511_ushort_opt opt;
5341
 
5342
                if (copy_from_user(&opt, arg, sizeof(opt)))
5343
                        return -EFAULT;
5344
 
5345
                switch (opt.optnum) {
5346
                case OV511_USOPT_BRIGHT:
5347
                        rc = sensor_get_brightness(ov, &(opt.val));
5348
                        if (rc) return rc;
5349
                        break;
5350
                case OV511_USOPT_SAT:
5351
                        rc = sensor_get_saturation(ov, &(opt.val));
5352
                        if (rc) return rc;
5353
                        break;
5354
                case OV511_USOPT_HUE:
5355
                        rc = sensor_get_hue(ov, &(opt.val));
5356
                        if (rc) return rc;
5357
                        break;
5358
                case OV511_USOPT_CONTRAST:
5359
                        rc = sensor_get_contrast(ov, &(opt.val));
5360
                        if (rc) return rc;
5361
                        break;
5362
                default:
5363
                        err("Invalid get short option number");
5364
                        return -EINVAL;
5365
                }
5366
 
5367
                if (copy_to_user(arg, &opt, sizeof(opt)))
5368
                        return -EFAULT;
5369
 
5370
                return 0;
5371
        }
5372
        case OV511IOC_SUSHORT:
5373
        {
5374
                struct ov511_ushort_opt opt;
5375
 
5376
                if (copy_from_user(&opt, arg, sizeof(opt)))
5377
                        return -EFAULT;
5378
 
5379
                switch (opt.optnum) {
5380
                case OV511_USOPT_BRIGHT:
5381
                        rc = sensor_set_brightness(ov, opt.val);
5382
                        if (rc) return rc;
5383
                        break;
5384
                case OV511_USOPT_SAT:
5385
                        rc = sensor_set_saturation(ov, opt.val);
5386
                        if (rc) return rc;
5387
                        break;
5388
                case OV511_USOPT_HUE:
5389
                        rc = sensor_set_hue(ov, opt.val);
5390
                        if (rc) return rc;
5391
                        break;
5392
                case OV511_USOPT_CONTRAST:
5393
                        rc = sensor_set_contrast(ov, opt.val);
5394
                        if (rc) return rc;
5395
                        break;
5396
                default:
5397
                        err("Invalid set short option number");
5398
                        return -EINVAL;
5399
                }
5400
 
5401
                return 0;
5402
        }
5403
        case OV511IOC_GUINT:
5404
        {
5405
                struct ov511_uint_opt opt;
5406
 
5407
                if (copy_from_user(&opt, arg, sizeof(opt)))
5408
                        return -EFAULT;
5409
 
5410
                switch (opt.optnum) {
5411
                case OV511_UIOPT_POWER_FREQ:
5412
                        opt.val = ov->lightfreq;
5413
                        break;
5414
                case OV511_UIOPT_BFILTER:
5415
                        opt.val = ov->bandfilt;
5416
                        break;
5417
                case OV511_UIOPT_LED:
5418
                        opt.val = ov->led_policy;
5419
                        break;
5420
                case OV511_UIOPT_DEBUG:
5421
                        opt.val = debug;
5422
                        break;
5423
                case OV511_UIOPT_COMPRESS:
5424
                        opt.val = ov->compress;
5425
                        break;
5426
                default:
5427
                        err("Invalid get int option number");
5428
                        return -EINVAL;
5429
                }
5430
 
5431
                if (copy_to_user(arg, &opt, sizeof(opt)))
5432
                        return -EFAULT;
5433
 
5434
                return 0;
5435
        }
5436
        case OV511IOC_SUINT:
5437
        {
5438
                struct ov511_uint_opt opt;
5439
 
5440
                if (copy_from_user(&opt, arg, sizeof(opt)))
5441
                        return -EFAULT;
5442
 
5443
                switch (opt.optnum) {
5444
                case OV511_UIOPT_POWER_FREQ:
5445
                        rc = sensor_set_light_freq(ov, opt.val);
5446
                        if (rc) return rc;
5447
                        break;
5448
                case OV511_UIOPT_BFILTER:
5449
                        rc = sensor_set_banding_filter(ov, opt.val);
5450
                        if (rc) return rc;
5451
                        break;
5452
                case OV511_UIOPT_LED:
5453
                        if (opt.val <= 2) {
5454
                                ov->led_policy = opt.val;
5455
                                if (ov->led_policy == LED_OFF)
5456
                                        ov51x_led_control(ov, 0);
5457
                                else if (ov->led_policy == LED_ON)
5458
                                        ov51x_led_control(ov, 1);
5459
                        } else {
5460
                                return -EINVAL;
5461
                        }
5462
                        break;
5463
                case OV511_UIOPT_DEBUG:
5464
                        if (opt.val <= 5)
5465
                                debug = opt.val;
5466
                        else
5467
                                return -EINVAL;
5468
                        break;
5469
                case OV511_UIOPT_COMPRESS:
5470
                        ov->compress = opt.val;
5471
                        if (ov->compress) {
5472
                                if (ov->bclass == BCL_OV511)
5473
                                        ov511_init_compression(ov);
5474
                                else if (ov->bclass == BCL_OV518)
5475
                                        ov518_init_compression(ov);
5476
                        }
5477
                        break;
5478
                default:
5479
                        err("Invalid get int option number");
5480
                        return -EINVAL;
5481
                }
5482
 
5483
                return 0;
5484
        }
5485
        case OV511IOC_WI2C:
5486
        {
5487
                struct ov511_i2c_struct w;
5488
 
5489
                if (copy_from_user(&w, arg, sizeof(w)))
5490
                        return -EFAULT;
5491
 
5492
                return i2c_w_slave(ov, w.slave, w.reg, w.value, w.mask);
5493
        }
5494
        case OV511IOC_RI2C:
5495
        {
5496
                struct ov511_i2c_struct r;
5497
 
5498
                if (copy_from_user(&r, arg, sizeof(r)))
5499
                        return -EFAULT;
5500
 
5501
                rc = i2c_r_slave(ov, r.slave, r.reg);
5502
                if (rc < 0)
5503
                        return rc;
5504
 
5505
                r.value = rc;
5506
 
5507
                if (copy_to_user(arg, &r, sizeof(r)))
5508
                        return -EFAULT;
5509
 
5510
                return 0;
5511
        }
5512
        default:
5513
                return -EINVAL;
5514
        } /* end switch */
5515
 
5516
        return 0;
5517
}
5518
#endif
5519
 
5520
/****************************************************************************
5521
 *
5522
 * OV511 and sensor configuration
5523
 *
5524
 ***************************************************************************/
5525
 
5526
/* This initializes the OV7610, OV7620, or OV76BE sensor. The OV76BE uses
5527
 * the same register settings as the OV7610, since they are very similar.
5528
 */
5529
static int
5530
ov7xx0_configure(struct usb_ov511 *ov)
5531
{
5532
        int i, success;
5533
        int rc;
5534
 
5535
        /* Lawrence Glaister <lg@jfm.bc.ca> reports:
5536
         *
5537
         * Register 0x0f in the 7610 has the following effects:
5538
         *
5539
         * 0x85 (AEC method 1): Best overall, good contrast range
5540
         * 0x45 (AEC method 2): Very overexposed
5541
         * 0xa5 (spec sheet default): Ok, but the black level is
5542
         *      shifted resulting in loss of contrast
5543
         * 0x05 (old driver setting): very overexposed, too much
5544
         *      contrast
5545
         */
5546
        static struct ov511_regvals aRegvalsNorm7610[] = {
5547
                { OV511_I2C_BUS, 0x10, 0xff },
5548
                { OV511_I2C_BUS, 0x16, 0x06 },
5549
                { OV511_I2C_BUS, 0x28, 0x24 },
5550
                { OV511_I2C_BUS, 0x2b, 0xac },
5551
                { OV511_I2C_BUS, 0x12, 0x00 },
5552
                { OV511_I2C_BUS, 0x38, 0x81 },
5553
                { OV511_I2C_BUS, 0x28, 0x24 },  /* 0c */
5554
                { OV511_I2C_BUS, 0x0f, 0x85 },  /* lg's setting */
5555
                { OV511_I2C_BUS, 0x15, 0x01 },
5556
                { OV511_I2C_BUS, 0x20, 0x1c },
5557
                { OV511_I2C_BUS, 0x23, 0x2a },
5558
                { OV511_I2C_BUS, 0x24, 0x10 },
5559
                { OV511_I2C_BUS, 0x25, 0x8a },
5560
                { OV511_I2C_BUS, 0x26, 0xa2 },
5561
                { OV511_I2C_BUS, 0x27, 0xc2 },
5562
                { OV511_I2C_BUS, 0x2a, 0x04 },
5563
                { OV511_I2C_BUS, 0x2c, 0xfe },
5564
                { OV511_I2C_BUS, 0x2d, 0x93 },
5565
                { OV511_I2C_BUS, 0x30, 0x71 },
5566
                { OV511_I2C_BUS, 0x31, 0x60 },
5567
                { OV511_I2C_BUS, 0x32, 0x26 },
5568
                { OV511_I2C_BUS, 0x33, 0x20 },
5569
                { OV511_I2C_BUS, 0x34, 0x48 },
5570
                { OV511_I2C_BUS, 0x12, 0x24 },
5571
                { OV511_I2C_BUS, 0x11, 0x01 },
5572
                { OV511_I2C_BUS, 0x0c, 0x24 },
5573
                { OV511_I2C_BUS, 0x0d, 0x24 },
5574
                { OV511_DONE_BUS, 0x0, 0x00 },
5575
        };
5576
 
5577
        static struct ov511_regvals aRegvalsNorm7620[] = {
5578
                { OV511_I2C_BUS, 0x00, 0x00 },
5579
                { OV511_I2C_BUS, 0x01, 0x80 },
5580
                { OV511_I2C_BUS, 0x02, 0x80 },
5581
                { OV511_I2C_BUS, 0x03, 0xc0 },
5582
                { OV511_I2C_BUS, 0x06, 0x60 },
5583
                { OV511_I2C_BUS, 0x07, 0x00 },
5584
                { OV511_I2C_BUS, 0x0c, 0x24 },
5585
                { OV511_I2C_BUS, 0x0c, 0x24 },
5586
                { OV511_I2C_BUS, 0x0d, 0x24 },
5587
                { OV511_I2C_BUS, 0x11, 0x01 },
5588
                { OV511_I2C_BUS, 0x12, 0x24 },
5589
                { OV511_I2C_BUS, 0x13, 0x01 },
5590
                { OV511_I2C_BUS, 0x14, 0x84 },
5591
                { OV511_I2C_BUS, 0x15, 0x01 },
5592
                { OV511_I2C_BUS, 0x16, 0x03 },
5593
                { OV511_I2C_BUS, 0x17, 0x2f },
5594
                { OV511_I2C_BUS, 0x18, 0xcf },
5595
                { OV511_I2C_BUS, 0x19, 0x06 },
5596
                { OV511_I2C_BUS, 0x1a, 0xf5 },
5597
                { OV511_I2C_BUS, 0x1b, 0x00 },
5598
                { OV511_I2C_BUS, 0x20, 0x18 },
5599
                { OV511_I2C_BUS, 0x21, 0x80 },
5600
                { OV511_I2C_BUS, 0x22, 0x80 },
5601
                { OV511_I2C_BUS, 0x23, 0x00 },
5602
                { OV511_I2C_BUS, 0x26, 0xa2 },
5603
                { OV511_I2C_BUS, 0x27, 0xea },
5604
                { OV511_I2C_BUS, 0x28, 0x20 },
5605
                { OV511_I2C_BUS, 0x29, 0x00 },
5606
                { OV511_I2C_BUS, 0x2a, 0x10 },
5607
                { OV511_I2C_BUS, 0x2b, 0x00 },
5608
                { OV511_I2C_BUS, 0x2c, 0x88 },
5609
                { OV511_I2C_BUS, 0x2d, 0x91 },
5610
                { OV511_I2C_BUS, 0x2e, 0x80 },
5611
                { OV511_I2C_BUS, 0x2f, 0x44 },
5612
                { OV511_I2C_BUS, 0x60, 0x27 },
5613
                { OV511_I2C_BUS, 0x61, 0x02 },
5614
                { OV511_I2C_BUS, 0x62, 0x5f },
5615
                { OV511_I2C_BUS, 0x63, 0xd5 },
5616
                { OV511_I2C_BUS, 0x64, 0x57 },
5617
                { OV511_I2C_BUS, 0x65, 0x83 },
5618
                { OV511_I2C_BUS, 0x66, 0x55 },
5619
                { OV511_I2C_BUS, 0x67, 0x92 },
5620
                { OV511_I2C_BUS, 0x68, 0xcf },
5621
                { OV511_I2C_BUS, 0x69, 0x76 },
5622
                { OV511_I2C_BUS, 0x6a, 0x22 },
5623
                { OV511_I2C_BUS, 0x6b, 0x00 },
5624
                { OV511_I2C_BUS, 0x6c, 0x02 },
5625
                { OV511_I2C_BUS, 0x6d, 0x44 },
5626
                { OV511_I2C_BUS, 0x6e, 0x80 },
5627
                { OV511_I2C_BUS, 0x6f, 0x1d },
5628
                { OV511_I2C_BUS, 0x70, 0x8b },
5629
                { OV511_I2C_BUS, 0x71, 0x00 },
5630
                { OV511_I2C_BUS, 0x72, 0x14 },
5631
                { OV511_I2C_BUS, 0x73, 0x54 },
5632
                { OV511_I2C_BUS, 0x74, 0x00 },
5633
                { OV511_I2C_BUS, 0x75, 0x8e },
5634
                { OV511_I2C_BUS, 0x76, 0x00 },
5635
                { OV511_I2C_BUS, 0x77, 0xff },
5636
                { OV511_I2C_BUS, 0x78, 0x80 },
5637
                { OV511_I2C_BUS, 0x79, 0x80 },
5638
                { OV511_I2C_BUS, 0x7a, 0x80 },
5639
                { OV511_I2C_BUS, 0x7b, 0xe2 },
5640
                { OV511_I2C_BUS, 0x7c, 0x00 },
5641
                { OV511_DONE_BUS, 0x0, 0x00 },
5642
        };
5643
 
5644
        PDEBUG(4, "starting configuration");
5645
 
5646
        /* This looks redundant, but is necessary for WebCam 3 */
5647
        ov->primary_i2c_slave = OV7xx0_SID;
5648
        if (ov51x_set_slave_ids(ov, OV7xx0_SID) < 0)
5649
                return -1;
5650
 
5651
        if (init_ov_sensor(ov) >= 0) {
5652
                PDEBUG(1, "OV7xx0 sensor initalized (method 1)");
5653
        } else {
5654
                /* Reset the 76xx */
5655
                if (i2c_w(ov, 0x12, 0x80) < 0) return -1;
5656
 
5657
                /* Wait for it to initialize */
5658
                schedule_timeout(1 + 150 * HZ / 1000);
5659
 
5660
                i = 0;
5661
                success = 0;
5662
                while (i <= i2c_detect_tries) {
5663
                        if ((i2c_r(ov, OV7610_REG_ID_HIGH) == 0x7F) &&
5664
                            (i2c_r(ov, OV7610_REG_ID_LOW) == 0xA2)) {
5665
                                success = 1;
5666
                                break;
5667
                        } else {
5668
                                i++;
5669
                        }
5670
                }
5671
 
5672
// Was (i == i2c_detect_tries) previously. This obviously used to always report
5673
// success. Whether anyone actually depended on that bug is unknown
5674
                if ((i >= i2c_detect_tries) && (success == 0)) {
5675
                        err("Failed to read sensor ID. You might not have an");
5676
                        err("OV7610/20, or it may be not responding. Report");
5677
                        err("this to " EMAIL);
5678
                        err("This is only a warning. You can attempt to use");
5679
                        err("your camera anyway");
5680
// Only issue a warning for now
5681
//                      return -1;
5682
                } else {
5683
                        PDEBUG(1, "OV7xx0 initialized (method 2, %dx)", i+1);
5684
                }
5685
        }
5686
 
5687
        /* Detect sensor (sub)type */
5688
        rc = i2c_r(ov, OV7610_REG_COM_I);
5689
 
5690
        if (rc < 0) {
5691
                err("Error detecting sensor type");
5692
                return -1;
5693
        } else if ((rc & 3) == 3) {
5694
                info("Sensor is an OV7610");
5695
                ov->sensor = SEN_OV7610;
5696
        } else if ((rc & 3) == 1) {
5697
                /* I don't know what's different about the 76BE yet. */
5698
                if (i2c_r(ov, 0x15) & 1)
5699
                        info("Sensor is an OV7620AE");
5700
                else
5701
                        info("Sensor is an OV76BE");
5702
 
5703
                /* OV511+ will return all zero isoc data unless we
5704
                 * configure the sensor as a 7620. Someone needs to
5705
                 * find the exact reg. setting that causes this. */
5706
                if (ov->bridge == BRG_OV511PLUS) {
5707
                        info("Enabling 511+/7620AE workaround");
5708
                        ov->sensor = SEN_OV7620;
5709
                } else {
5710
                        ov->sensor = SEN_OV76BE;
5711
                }
5712
        } else if ((rc & 3) == 0) {
5713
                info("Sensor is an OV7620");
5714
                ov->sensor = SEN_OV7620;
5715
        } else {
5716
                err("Unknown image sensor version: %d", rc & 3);
5717
                return -1;
5718
        }
5719
 
5720
        if (ov->sensor == SEN_OV7620) {
5721
                PDEBUG(4, "Writing 7620 registers");
5722
                if (write_regvals(ov, aRegvalsNorm7620))
5723
                        return -1;
5724
        } else {
5725
                PDEBUG(4, "Writing 7610 registers");
5726
                if (write_regvals(ov, aRegvalsNorm7610))
5727
                        return -1;
5728
        }
5729
 
5730
        /* Set sensor-specific vars */
5731
        ov->maxwidth = 640;
5732
        ov->maxheight = 480;
5733
        ov->minwidth = 64;
5734
        ov->minheight = 48;
5735
 
5736
        // FIXME: These do not match the actual settings yet
5737
        ov->brightness = 0x80 << 8;
5738
        ov->contrast = 0x80 << 8;
5739
        ov->colour = 0x80 << 8;
5740
        ov->hue = 0x80 << 8;
5741
 
5742
        return 0;
5743
}
5744
 
5745
/* This initializes the OV6620, OV6630, OV6630AE, or OV6630AF sensor. */
5746
static int
5747
ov6xx0_configure(struct usb_ov511 *ov)
5748
{
5749
        int rc;
5750
 
5751
        static struct ov511_regvals aRegvalsNorm6x20[] = {
5752
                { OV511_I2C_BUS, 0x12, 0x80 }, /* reset */
5753
                { OV511_I2C_BUS, 0x11, 0x01 },
5754
                { OV511_I2C_BUS, 0x03, 0x60 },
5755
                { OV511_I2C_BUS, 0x05, 0x7f }, /* For when autoadjust is off */
5756
                { OV511_I2C_BUS, 0x07, 0xa8 },
5757
                /* The ratio of 0x0c and 0x0d  controls the white point */
5758
                { OV511_I2C_BUS, 0x0c, 0x24 },
5759
                { OV511_I2C_BUS, 0x0d, 0x24 },
5760
                { OV511_I2C_BUS, 0x0f, 0x15 }, /* COMS */
5761
                { OV511_I2C_BUS, 0x10, 0x75 }, /* AEC Exposure time */
5762
                { OV511_I2C_BUS, 0x12, 0x24 }, /* Enable AGC */
5763
                { OV511_I2C_BUS, 0x14, 0x04 },
5764
                /* 0x16: 0x06 helps frame stability with moving objects */
5765
                { OV511_I2C_BUS, 0x16, 0x06 },
5766
//              { OV511_I2C_BUS, 0x20, 0x30 }, /* Aperture correction enable */
5767
                { OV511_I2C_BUS, 0x26, 0xb2 }, /* BLC enable */
5768
                /* 0x28: 0x05 Selects RGB format if RGB on */
5769
                { OV511_I2C_BUS, 0x28, 0x05 },
5770
                { OV511_I2C_BUS, 0x2a, 0x04 }, /* Disable framerate adjust */
5771
//              { OV511_I2C_BUS, 0x2b, 0xac }, /* Framerate; Set 2a[7] first */
5772
                { OV511_I2C_BUS, 0x2d, 0x99 },
5773
                { OV511_I2C_BUS, 0x33, 0xa0 }, /* Color Procesing Parameter */
5774
                { OV511_I2C_BUS, 0x34, 0xd2 }, /* Max A/D range */
5775
                { OV511_I2C_BUS, 0x38, 0x8b },
5776
                { OV511_I2C_BUS, 0x39, 0x40 },
5777
 
5778
                { OV511_I2C_BUS, 0x3c, 0x39 }, /* Enable AEC mode changing */
5779
                { OV511_I2C_BUS, 0x3c, 0x3c }, /* Change AEC mode */
5780
                { OV511_I2C_BUS, 0x3c, 0x24 }, /* Disable AEC mode changing */
5781
 
5782
                { OV511_I2C_BUS, 0x3d, 0x80 },
5783
                /* These next two registers (0x4a, 0x4b) are undocumented. They
5784
                 * control the color balance */
5785
                { OV511_I2C_BUS, 0x4a, 0x80 },
5786
                { OV511_I2C_BUS, 0x4b, 0x80 },
5787
                { OV511_I2C_BUS, 0x4d, 0xd2 }, /* This reduces noise a bit */
5788
                { OV511_I2C_BUS, 0x4e, 0xc1 },
5789
                { OV511_I2C_BUS, 0x4f, 0x04 },
5790
// Do 50-53 have any effect?
5791
// Toggle 0x12[2] off and on here?
5792
                { OV511_DONE_BUS, 0x0, 0x00 },  /* END MARKER */
5793
        };
5794
 
5795
        static struct ov511_regvals aRegvalsNorm6x30[] = {
5796
                { OV511_I2C_BUS, 0x12, 0x80 }, /* reset */
5797
                { OV511_I2C_BUS, 0x11, 0x00 },
5798
                { OV511_I2C_BUS, 0x03, 0x60 },
5799
                { OV511_I2C_BUS, 0x05, 0x7f }, /* For when autoadjust is off */
5800
                { OV511_I2C_BUS, 0x07, 0xa8 },
5801
                /* The ratio of 0x0c and 0x0d  controls the white point */
5802
                { OV511_I2C_BUS, 0x0c, 0x24 },
5803
                { OV511_I2C_BUS, 0x0d, 0x24 },
5804
                { OV511_I2C_BUS, 0x0e, 0x20 },
5805
//              { OV511_I2C_BUS, 0x14, 0x80 },
5806
                { OV511_I2C_BUS, 0x16, 0x03 },
5807
//              { OV511_I2C_BUS, 0x20, 0x30 }, /* Aperture correction enable */
5808
                // 21 & 22? The suggested values look wrong. Go with default
5809
                { OV511_I2C_BUS, 0x23, 0xc0 },
5810
                { OV511_I2C_BUS, 0x25, 0x9a }, // Check this against default
5811
//              { OV511_I2C_BUS, 0x26, 0xb2 }, /* BLC enable */
5812
 
5813
                /* 0x28: 0x05 Selects RGB format if RGB on */
5814
//              { OV511_I2C_BUS, 0x28, 0x05 },
5815
//              { OV511_I2C_BUS, 0x28, 0x45 }, // DEBUG: Tristate UV bus
5816
 
5817
                { OV511_I2C_BUS, 0x2a, 0x04 }, /* Disable framerate adjust */
5818
//              { OV511_I2C_BUS, 0x2b, 0xac }, /* Framerate; Set 2a[7] first */
5819
                { OV511_I2C_BUS, 0x2d, 0x99 },
5820
//              { OV511_I2C_BUS, 0x33, 0x26 }, // Reserved bits on 6620
5821
//              { OV511_I2C_BUS, 0x34, 0x03 }, /* Max A/D range */
5822
//              { OV511_I2C_BUS, 0x38, 0x83 },
5823
//              { OV511_I2C_BUS, 0x39, 0xc0 }, // 6630 adds bit 7
5824
//              { OV511_I2C_BUS, 0x3c, 0x39 }, /* Enable AEC mode changing */
5825
//              { OV511_I2C_BUS, 0x3c, 0x3c }, /* Change AEC mode */
5826
//              { OV511_I2C_BUS, 0x3c, 0x24 }, /* Disable AEC mode changing */
5827
                { OV511_I2C_BUS, 0x3d, 0x80 },
5828
//              { OV511_I2C_BUS, 0x3f, 0x0e },
5829
 
5830
                /* These next two registers (0x4a, 0x4b) are undocumented. They
5831
                 * control the color balance */
5832
//              { OV511_I2C_BUS, 0x4a, 0x80 }, // Check these
5833
//              { OV511_I2C_BUS, 0x4b, 0x80 },
5834
                { OV511_I2C_BUS, 0x4d, 0x10 }, /* U = 0.563u, V = 0.714v */
5835
                { OV511_I2C_BUS, 0x4e, 0x40 },
5836
 
5837
                /* UV average mode, color killer: strongest */
5838
                { OV511_I2C_BUS, 0x4f, 0x07 },
5839
 
5840
                { OV511_I2C_BUS, 0x54, 0x23 }, /* Max AGC gain: 18dB */
5841
                { OV511_I2C_BUS, 0x57, 0x81 }, /* (default) */
5842
                { OV511_I2C_BUS, 0x59, 0x01 }, /* AGC dark current comp: +1 */
5843
                { OV511_I2C_BUS, 0x5a, 0x2c }, /* (undocumented) */
5844
                { OV511_I2C_BUS, 0x5b, 0x0f }, /* AWB chrominance levels */
5845
//              { OV511_I2C_BUS, 0x5c, 0x10 },
5846
                { OV511_DONE_BUS, 0x0, 0x00 },  /* END MARKER */
5847
        };
5848
 
5849
        PDEBUG(4, "starting sensor configuration");
5850
 
5851
        if (init_ov_sensor(ov) < 0) {
5852
                err("Failed to read sensor ID. You might not have an OV6xx0,");
5853
                err("or it may be not responding. Report this to " EMAIL);
5854
                return -1;
5855
        } else {
5856
                PDEBUG(1, "OV6xx0 sensor detected");
5857
        }
5858
 
5859
        /* Detect sensor (sub)type */
5860
        rc = i2c_r(ov, OV7610_REG_COM_I);
5861
 
5862
        if (rc < 0) {
5863
                err("Error detecting sensor type");
5864
                return -1;
5865
        }
5866
 
5867
        if ((rc & 3) == 0) {
5868
                ov->sensor = SEN_OV6630;
5869
                info("Sensor is an OV6630");
5870
        } else if ((rc & 3) == 1) {
5871
                ov->sensor = SEN_OV6620;
5872
                info("Sensor is an OV6620");
5873
        } else if ((rc & 3) == 2) {
5874
                ov->sensor = SEN_OV6630;
5875
                info("Sensor is an OV6630AE");
5876
        } else if ((rc & 3) == 3) {
5877
                ov->sensor = SEN_OV6630;
5878
                info("Sensor is an OV6630AF");
5879
        }
5880
 
5881
        /* Set sensor-specific vars */
5882
        ov->maxwidth = 352;
5883
        ov->maxheight = 288;
5884
        ov->minwidth = 64;
5885
        ov->minheight = 48;
5886
 
5887
        // FIXME: These do not match the actual settings yet
5888
        ov->brightness = 0x80 << 8;
5889
        ov->contrast = 0x80 << 8;
5890
        ov->colour = 0x80 << 8;
5891
        ov->hue = 0x80 << 8;
5892
 
5893
        if (ov->sensor == SEN_OV6620) {
5894
                PDEBUG(4, "Writing 6x20 registers");
5895
                if (write_regvals(ov, aRegvalsNorm6x20))
5896
                        return -1;
5897
        } else {
5898
                PDEBUG(4, "Writing 6x30 registers");
5899
                if (write_regvals(ov, aRegvalsNorm6x30))
5900
                        return -1;
5901
        }
5902
 
5903
        return 0;
5904
}
5905
 
5906
/* This initializes the KS0127 and KS0127B video decoders. */
5907
static int
5908
ks0127_configure(struct usb_ov511 *ov)
5909
{
5910
        int rc;
5911
 
5912
// FIXME: I don't know how to sync or reset it yet
5913
#if 0
5914
        if (ov51x_init_ks_sensor(ov) < 0) {
5915
                err("Failed to initialize the KS0127");
5916
                return -1;
5917
        } else {
5918
                PDEBUG(1, "KS012x(B) sensor detected");
5919
        }
5920
#endif
5921
 
5922
        /* Detect decoder subtype */
5923
        rc = i2c_r(ov, 0x00);
5924
        if (rc < 0) {
5925
                err("Error detecting sensor type");
5926
                return -1;
5927
        } else if (rc & 0x08) {
5928
                rc = i2c_r(ov, 0x3d);
5929
                if (rc < 0) {
5930
                        err("Error detecting sensor type");
5931
                        return -1;
5932
                } else if ((rc & 0x0f) == 0) {
5933
                        info("Sensor is a KS0127");
5934
                        ov->sensor = SEN_KS0127;
5935
                } else if ((rc & 0x0f) == 9) {
5936
                        info("Sensor is a KS0127B Rev. A");
5937
                        ov->sensor = SEN_KS0127B;
5938
                }
5939
        } else {
5940
                err("Error: Sensor is an unsupported KS0122");
5941
                return -1;
5942
        }
5943
 
5944
        /* Set sensor-specific vars */
5945
        ov->maxwidth = 640;
5946
        ov->maxheight = 480;
5947
        ov->minwidth = 64;
5948
        ov->minheight = 48;
5949
 
5950
        // FIXME: These do not match the actual settings yet
5951
        ov->brightness = 0x80 << 8;
5952
        ov->contrast = 0x80 << 8;
5953
        ov->colour = 0x80 << 8;
5954
        ov->hue = 0x80 << 8;
5955
 
5956
        /* This device is not supported yet. Bail out now... */
5957
        err("This sensor is not supported yet.");
5958
        return -1;
5959
 
5960
        return 0;
5961
}
5962
 
5963
/* This initializes the SAA7111A video decoder. */
5964
static int
5965
saa7111a_configure(struct usb_ov511 *ov)
5966
{
5967
        int rc;
5968
 
5969
        /* Since there is no register reset command, all registers must be
5970
         * written, otherwise gives erratic results */
5971
        static struct ov511_regvals aRegvalsNormSAA7111A[] = {
5972
                { OV511_I2C_BUS, 0x06, 0xce },
5973
                { OV511_I2C_BUS, 0x07, 0x00 },
5974
                { OV511_I2C_BUS, 0x10, 0x44 }, /* YUV422, 240/286 lines */
5975
                { OV511_I2C_BUS, 0x0e, 0x01 }, /* NTSC M or PAL BGHI */
5976
                { OV511_I2C_BUS, 0x00, 0x00 },
5977
                { OV511_I2C_BUS, 0x01, 0x00 },
5978
                { OV511_I2C_BUS, 0x03, 0x23 },
5979
                { OV511_I2C_BUS, 0x04, 0x00 },
5980
                { OV511_I2C_BUS, 0x05, 0x00 },
5981
                { OV511_I2C_BUS, 0x08, 0xc8 }, /* Auto field freq */
5982
                { OV511_I2C_BUS, 0x09, 0x01 }, /* Chrom. trap off, APER=0.25 */
5983
                { OV511_I2C_BUS, 0x0a, 0x80 }, /* BRIG=128 */
5984
                { OV511_I2C_BUS, 0x0b, 0x40 }, /* CONT=1.0 */
5985
                { OV511_I2C_BUS, 0x0c, 0x40 }, /* SATN=1.0 */
5986
                { OV511_I2C_BUS, 0x0d, 0x00 }, /* HUE=0 */
5987
                { OV511_I2C_BUS, 0x0f, 0x00 },
5988
                { OV511_I2C_BUS, 0x11, 0x0c },
5989
                { OV511_I2C_BUS, 0x12, 0x00 },
5990
                { OV511_I2C_BUS, 0x13, 0x00 },
5991
                { OV511_I2C_BUS, 0x14, 0x00 },
5992
                { OV511_I2C_BUS, 0x15, 0x00 },
5993
                { OV511_I2C_BUS, 0x16, 0x00 },
5994
                { OV511_I2C_BUS, 0x17, 0x00 },
5995
                { OV511_I2C_BUS, 0x02, 0xc0 },  /* Composite input 0 */
5996
                { OV511_DONE_BUS, 0x0, 0x00 },
5997
        };
5998
 
5999
// FIXME: I don't know how to sync or reset it yet
6000
#if 0
6001
        if (ov51x_init_saa_sensor(ov) < 0) {
6002
                err("Failed to initialize the SAA7111A");
6003
                return -1;
6004
        } else {
6005
                PDEBUG(1, "SAA7111A sensor detected");
6006
        }
6007
#endif
6008
 
6009
        /* 640x480 not supported with PAL */
6010
        if (ov->pal) {
6011
                ov->maxwidth = 320;
6012
                ov->maxheight = 240;            /* Even field only */
6013
        } else {
6014
                ov->maxwidth = 640;
6015
                ov->maxheight = 480;            /* Even/Odd fields */
6016
        }
6017
 
6018
        ov->minwidth = 320;
6019
        ov->minheight = 240;            /* Even field only */
6020
 
6021
        ov->has_decoder = 1;
6022
        ov->num_inputs = 8;
6023
        ov->norm = VIDEO_MODE_AUTO;
6024
        ov->stop_during_set = 0; /* Decoder guarantees stable image */
6025
 
6026
        /* Decoder doesn't change these values, so we use these instead of
6027
         * acutally reading the registers (which doesn't work) */
6028
        ov->brightness = 0x80 << 8;
6029
        ov->contrast = 0x40 << 9;
6030
        ov->colour = 0x40 << 9;
6031
        ov->hue = 32768;
6032
 
6033
        PDEBUG(4, "Writing SAA7111A registers");
6034
        if (write_regvals(ov, aRegvalsNormSAA7111A))
6035
                return -1;
6036
 
6037
        /* Detect version of decoder. This must be done after writing the
6038
         * initial regs or the decoder will lock up. */
6039
        rc = i2c_r(ov, 0x00);
6040
 
6041
        if (rc < 0) {
6042
                err("Error detecting sensor version");
6043
                return -1;
6044
        } else {
6045
                info("Sensor is an SAA7111A (version 0x%x)", rc);
6046
                ov->sensor = SEN_SAA7111A;
6047
        }
6048
 
6049
        // FIXME: Fix this for OV518(+)
6050
        /* Latch to negative edge of clock. Otherwise, we get incorrect
6051
         * colors and jitter in the digital signal. */
6052
        if (ov->bclass == BCL_OV511)
6053
                reg_w(ov, 0x11, 0x00);
6054
        else
6055
                warn("SAA7111A not yet supported with OV518/OV518+");
6056
 
6057
        return 0;
6058
}
6059
 
6060
/* This initializes the OV511/OV511+ and the sensor */
6061
static int
6062
ov511_configure(struct usb_ov511 *ov)
6063
{
6064
        static struct ov511_regvals aRegvalsInit511[] = {
6065
                { OV511_REG_BUS, R51x_SYS_RESET,        0x7f },
6066
                { OV511_REG_BUS, R51x_SYS_INIT,         0x01 },
6067
                { OV511_REG_BUS, R51x_SYS_RESET,        0x7f },
6068
                { OV511_REG_BUS, R51x_SYS_INIT,         0x01 },
6069
                { OV511_REG_BUS, R51x_SYS_RESET,        0x3f },
6070
                { OV511_REG_BUS, R51x_SYS_INIT,         0x01 },
6071
                { OV511_REG_BUS, R51x_SYS_RESET,        0x3d },
6072
                { OV511_DONE_BUS, 0x0, 0x00},
6073
        };
6074
 
6075
        static struct ov511_regvals aRegvalsNorm511[] = {
6076
                { OV511_REG_BUS, R511_DRAM_FLOW_CTL,    0x01 },
6077
                { OV511_REG_BUS, R51x_SYS_SNAP,         0x00 },
6078
                { OV511_REG_BUS, R51x_SYS_SNAP,         0x02 },
6079
                { OV511_REG_BUS, R51x_SYS_SNAP,         0x00 },
6080
                { OV511_REG_BUS, R511_FIFO_OPTS,        0x1f },
6081
                { OV511_REG_BUS, R511_COMP_EN,          0x00 },
6082
                { OV511_REG_BUS, R511_COMP_LUT_EN,      0x03 },
6083
                { OV511_DONE_BUS, 0x0, 0x00 },
6084
        };
6085
 
6086
        static struct ov511_regvals aRegvalsNorm511Plus[] = {
6087
                { OV511_REG_BUS, R511_DRAM_FLOW_CTL,    0xff },
6088
                { OV511_REG_BUS, R51x_SYS_SNAP,         0x00 },
6089
                { OV511_REG_BUS, R51x_SYS_SNAP,         0x02 },
6090
                { OV511_REG_BUS, R51x_SYS_SNAP,         0x00 },
6091
                { OV511_REG_BUS, R511_FIFO_OPTS,        0xff },
6092
                { OV511_REG_BUS, R511_COMP_EN,          0x00 },
6093
                { OV511_REG_BUS, R511_COMP_LUT_EN,      0x03 },
6094
                { OV511_DONE_BUS, 0x0, 0x00 },
6095
        };
6096
 
6097
        PDEBUG(4, "");
6098
 
6099
        ov->customid = reg_r(ov, R511_SYS_CUST_ID);
6100
        if (ov->customid < 0) {
6101
                err("Unable to read camera bridge registers");
6102
                goto error;
6103
        }
6104
 
6105
        PDEBUG (1, "CustomID = %d", ov->customid);
6106
        ov->desc = symbolic(camlist, ov->customid);
6107
        info("model: %s", ov->desc);
6108
 
6109
        if (0 == strcmp(ov->desc, NOT_DEFINED_STR)) {
6110
                err("Camera type (%d) not recognized", ov->customid);
6111
                err("Please notify " EMAIL " of the name,");
6112
                err("manufacturer, model, and this number of your camera.");
6113
                err("Also include the output of the detection process.");
6114
        }
6115
 
6116
        if (ov->customid == 70)         /* USB Life TV (PAL/SECAM) */
6117
                ov->pal = 1;
6118
 
6119
        if (write_regvals(ov, aRegvalsInit511)) goto error;
6120
 
6121
        if (ov->led_policy == LED_OFF || ov->led_policy == LED_AUTO)
6122
                ov51x_led_control(ov, 0);
6123
 
6124
        /* The OV511+ has undocumented bits in the flow control register.
6125
         * Setting it to 0xff fixes the corruption with moving objects. */
6126
        if (ov->bridge == BRG_OV511) {
6127
                if (write_regvals(ov, aRegvalsNorm511)) goto error;
6128
        } else if (ov->bridge == BRG_OV511PLUS) {
6129
                if (write_regvals(ov, aRegvalsNorm511Plus)) goto error;
6130
        } else {
6131
                err("Invalid bridge");
6132
        }
6133
 
6134
        if (ov511_init_compression(ov)) goto error;
6135
 
6136
        ov->packet_numbering = 1;
6137
        ov511_set_packet_size(ov, 0);
6138
 
6139
        ov->snap_enabled = snapshot;
6140
 
6141
        /* Test for 7xx0 */
6142
        PDEBUG(3, "Testing for 0V7xx0");
6143
        ov->primary_i2c_slave = OV7xx0_SID;
6144
        if (ov51x_set_slave_ids(ov, OV7xx0_SID) < 0)
6145
                goto error;
6146
 
6147
        if (i2c_w(ov, 0x12, 0x80) < 0) {
6148
                /* Test for 6xx0 */
6149
                PDEBUG(3, "Testing for 0V6xx0");
6150
                ov->primary_i2c_slave = OV6xx0_SID;
6151
                if (ov51x_set_slave_ids(ov, OV6xx0_SID) < 0)
6152
                        goto error;
6153
 
6154
                if (i2c_w(ov, 0x12, 0x80) < 0) {
6155
                        /* Test for 8xx0 */
6156
                        PDEBUG(3, "Testing for 0V8xx0");
6157
                        ov->primary_i2c_slave = OV8xx0_SID;
6158
                        if (ov51x_set_slave_ids(ov, OV8xx0_SID) < 0)
6159
                                goto error;
6160
 
6161
                        if (i2c_w(ov, 0x12, 0x80) < 0) {
6162
                                /* Test for SAA7111A */
6163
                                PDEBUG(3, "Testing for SAA7111A");
6164
                                ov->primary_i2c_slave = SAA7111A_SID;
6165
                                if (ov51x_set_slave_ids(ov, SAA7111A_SID) < 0)
6166
                                        goto error;
6167
 
6168
                                if (i2c_w(ov, 0x0d, 0x00) < 0) {
6169
                                        /* Test for KS0127 */
6170
                                        PDEBUG(3, "Testing for KS0127");
6171
                                        ov->primary_i2c_slave = KS0127_SID;
6172
                                        if (ov51x_set_slave_ids(ov, KS0127_SID) < 0)
6173
                                                goto error;
6174
 
6175
                                        if (i2c_w(ov, 0x10, 0x00) < 0) {
6176
                                                err("Can't determine sensor slave IDs");
6177
                                                goto error;
6178
                                        } else {
6179
                                                if (ks0127_configure(ov) < 0) {
6180
                                                        err("Failed to configure KS0127");
6181
                                                        goto error;
6182
                                                }
6183
                                        }
6184
                                } else {
6185
                                        if (saa7111a_configure(ov) < 0) {
6186
                                                err("Failed to configure SAA7111A");
6187
                                                goto error;
6188
                                        }
6189
                                }
6190
                        } else {
6191
                                err("Detected unsupported OV8xx0 sensor");
6192
                                goto error;
6193
                        }
6194
                } else {
6195
                        if (ov6xx0_configure(ov) < 0) {
6196
                                err("Failed to configure OV6xx0");
6197
                                goto error;
6198
                        }
6199
                }
6200
        } else {
6201
                if (ov7xx0_configure(ov) < 0) {
6202
                        err("Failed to configure OV7xx0");
6203
                        goto error;
6204
                }
6205
        }
6206
 
6207
        return 0;
6208
 
6209
error:
6210
        err("OV511 Config failed");
6211
 
6212
        return -EBUSY;
6213
}
6214
 
6215
/* This initializes the OV518/OV518+ and the sensor */
6216
static int
6217
ov518_configure(struct usb_ov511 *ov)
6218
{
6219
        /* For 518 and 518+ */
6220
        static struct ov511_regvals aRegvalsInit518[] = {
6221
                { OV511_REG_BUS, R51x_SYS_RESET,        0x40 },
6222
                { OV511_REG_BUS, R51x_SYS_INIT,         0xe1 },
6223
                { OV511_REG_BUS, R51x_SYS_RESET,        0x3e },
6224
                { OV511_REG_BUS, R51x_SYS_INIT,         0xe1 },
6225
                { OV511_REG_BUS, R51x_SYS_RESET,        0x00 },
6226
                { OV511_REG_BUS, R51x_SYS_INIT,         0xe1 },
6227
                { OV511_REG_BUS, 0x46,                  0x00 },
6228
                { OV511_REG_BUS, 0x5d,                  0x03 },
6229
                { OV511_DONE_BUS, 0x0, 0x00},
6230
        };
6231
 
6232
        static struct ov511_regvals aRegvalsNorm518[] = {
6233
                { OV511_REG_BUS, R51x_SYS_SNAP,         0x02 }, /* Reset */
6234
                { OV511_REG_BUS, R51x_SYS_SNAP,         0x01 }, /* Enable */
6235
                { OV511_REG_BUS, 0x31,                  0x0f },
6236
                { OV511_REG_BUS, 0x5d,                  0x03 },
6237
                { OV511_REG_BUS, 0x24,                  0x9f },
6238
                { OV511_REG_BUS, 0x25,                  0x90 },
6239
                { OV511_REG_BUS, 0x20,                  0x00 },
6240
                { OV511_REG_BUS, 0x51,                  0x04 },
6241
                { OV511_REG_BUS, 0x71,                  0x19 },
6242
                { OV511_DONE_BUS, 0x0, 0x00 },
6243
        };
6244
 
6245
        static struct ov511_regvals aRegvalsNorm518Plus[] = {
6246
                { OV511_REG_BUS, R51x_SYS_SNAP,         0x02 }, /* Reset */
6247
                { OV511_REG_BUS, R51x_SYS_SNAP,         0x01 }, /* Enable */
6248
                { OV511_REG_BUS, 0x31,                  0x0f },
6249
                { OV511_REG_BUS, 0x5d,                  0x03 },
6250
                { OV511_REG_BUS, 0x24,                  0x9f },
6251
                { OV511_REG_BUS, 0x25,                  0x90 },
6252
                { OV511_REG_BUS, 0x20,                  0x60 },
6253
                { OV511_REG_BUS, 0x51,                  0x02 },
6254
                { OV511_REG_BUS, 0x71,                  0x19 },
6255
                { OV511_REG_BUS, 0x40,                  0xff },
6256
                { OV511_REG_BUS, 0x41,                  0x42 },
6257
                { OV511_REG_BUS, 0x46,                  0x00 },
6258
                { OV511_REG_BUS, 0x33,                  0x04 },
6259
                { OV511_REG_BUS, 0x21,                  0x19 },
6260
                { OV511_REG_BUS, 0x3f,                  0x10 },
6261
                { OV511_DONE_BUS, 0x0, 0x00 },
6262
        };
6263
 
6264
        PDEBUG(4, "");
6265
 
6266
        /* First 5 bits of custom ID reg are a revision ID on OV518 */
6267
        info("Device revision %d", 0x1F & reg_r(ov, R511_SYS_CUST_ID));
6268
 
6269
        /* Give it the default description */
6270
        ov->desc = symbolic(camlist, 0);
6271
 
6272
        if (write_regvals(ov, aRegvalsInit518)) goto error;
6273
 
6274
        /* Set LED GPIO pin to output mode */
6275
        if (reg_w_mask(ov, 0x57, 0x00, 0x02) < 0) goto error;
6276
 
6277
        /* LED is off by default with OV518; have to explicitly turn it on */
6278
        if (ov->led_policy == LED_OFF || ov->led_policy == LED_AUTO)
6279
                ov51x_led_control(ov, 0);
6280
        else
6281
                ov51x_led_control(ov, 1);
6282
 
6283
        /* Don't require compression if dumppix is enabled; otherwise it's
6284
         * required. OV518 has no uncompressed mode, to save RAM. */
6285
        if (!dumppix && !ov->compress) {
6286
                ov->compress = 1;
6287
                warn("Compression required with OV518...enabling");
6288
        }
6289
 
6290
        if (ov->bridge == BRG_OV518) {
6291
                if (write_regvals(ov, aRegvalsNorm518)) goto error;
6292
        } else if (ov->bridge == BRG_OV518PLUS) {
6293
                if (write_regvals(ov, aRegvalsNorm518Plus)) goto error;
6294
        } else {
6295
                err("Invalid bridge");
6296
        }
6297
 
6298
        if (reg_w(ov, 0x2f, 0x80) < 0) goto error;
6299
 
6300
        if (ov518_init_compression(ov)) goto error;
6301
 
6302
        if (ov->bridge == BRG_OV518)
6303
        {
6304
                struct usb_interface *ifp = &ov->dev->config[0].interface[0];
6305
                __u16 mxps = ifp->altsetting[7].endpoint[0].wMaxPacketSize;
6306
 
6307
                /* Some OV518s have packet numbering by default, some don't */
6308
                if (mxps == 897)
6309
                        ov->packet_numbering = 1;
6310
                else
6311
                        ov->packet_numbering = 0;
6312
        } else {
6313
                /* OV518+ has packet numbering turned on by default */
6314
                ov->packet_numbering = 1;
6315
        }
6316
 
6317
        ov518_set_packet_size(ov, 0);
6318
 
6319
        ov->snap_enabled = snapshot;
6320
 
6321
        /* Test for 76xx */
6322
        ov->primary_i2c_slave = OV7xx0_SID;
6323
        if (ov51x_set_slave_ids(ov, OV7xx0_SID) < 0)
6324
                goto error;
6325
 
6326
        /* The OV518 must be more aggressive about sensor detection since
6327
         * I2C write will never fail if the sensor is not present. We have
6328
         * to try to initialize the sensor to detect its presence */
6329
 
6330
        if (init_ov_sensor(ov) < 0) {
6331
                /* Test for 6xx0 */
6332
                ov->primary_i2c_slave = OV6xx0_SID;
6333
                if (ov51x_set_slave_ids(ov, OV6xx0_SID) < 0)
6334
                        goto error;
6335
 
6336
                if (init_ov_sensor(ov) < 0) {
6337
                        /* Test for 8xx0 */
6338
                        ov->primary_i2c_slave = OV8xx0_SID;
6339
                        if (ov51x_set_slave_ids(ov, OV8xx0_SID) < 0)
6340
                                goto error;
6341
 
6342
                        if (init_ov_sensor(ov) < 0) {
6343
                                err("Can't determine sensor slave IDs");
6344
                                goto error;
6345
                        } else {
6346
                                err("Detected unsupported OV8xx0 sensor");
6347
                                goto error;
6348
                        }
6349
                } else {
6350
                        if (ov6xx0_configure(ov) < 0) {
6351
                                err("Failed to configure OV6xx0");
6352
                                goto error;
6353
                        }
6354
                }
6355
        } else {
6356
                if (ov7xx0_configure(ov) < 0) {
6357
                        err("Failed to configure OV7xx0");
6358
                        goto error;
6359
                }
6360
        }
6361
 
6362
        ov->maxwidth = 352;
6363
        ov->maxheight = 288;
6364
 
6365
        // The OV518 cannot go as low as the sensor can
6366
        ov->minwidth = 160;
6367
        ov->minheight = 120;
6368
 
6369
        return 0;
6370
 
6371
error:
6372
        err("OV518 Config failed");
6373
 
6374
        return -EBUSY;
6375
}
6376
 
6377
 
6378
/****************************************************************************
6379
 *
6380
 *  USB routines
6381
 *
6382
 ***************************************************************************/
6383
 
6384
static void *
6385
ov51x_probe(struct usb_device *dev, unsigned int ifnum,
6386
            const struct usb_device_id *id)
6387
{
6388
        struct usb_interface_descriptor *interface;
6389
        struct usb_ov511 *ov;
6390
        int i;
6391
        int registered = 0;
6392
 
6393
        PDEBUG(1, "probing for device...");
6394
 
6395
        /* We don't handle multi-config cameras */
6396
        if (dev->descriptor.bNumConfigurations != 1)
6397
                return NULL;
6398
 
6399
        interface = &dev->actconfig->interface[ifnum].altsetting[0];
6400
 
6401
        /* Checking vendor/product should be enough, but what the hell */
6402
        if (interface->bInterfaceClass != 0xFF)
6403
                return NULL;
6404
        if (interface->bInterfaceSubClass != 0x00)
6405
                return NULL;
6406
 
6407
        /* Since code below may sleep, we use this as a lock */
6408
        MOD_INC_USE_COUNT;
6409
 
6410
        if ((ov = kmalloc(sizeof(*ov), GFP_KERNEL)) == NULL) {
6411
                err("couldn't kmalloc ov struct");
6412
                goto error_out;
6413
        }
6414
 
6415
        memset(ov, 0, sizeof(*ov));
6416
 
6417
        ov->dev = dev;
6418
        ov->iface = interface->bInterfaceNumber;
6419
        ov->led_policy = led;
6420
        ov->compress = compress;
6421
        ov->lightfreq = lightfreq;
6422
        ov->num_inputs = 1;        /* Video decoder init functs. change this */
6423
        ov->stop_during_set = !fastset;
6424
        ov->backlight = backlight;
6425
        ov->mirror = mirror;
6426
        ov->auto_brt = autobright;
6427
        ov->auto_gain = autogain;
6428
        ov->auto_exp = autoexp;
6429
 
6430
        switch (dev->descriptor.idProduct) {
6431
        case PROD_OV511:
6432
                ov->bridge = BRG_OV511;
6433
                ov->bclass = BCL_OV511;
6434
                break;
6435
        case PROD_OV511PLUS:
6436
                ov->bridge = BRG_OV511PLUS;
6437
                ov->bclass = BCL_OV511;
6438
                break;
6439
        case PROD_OV518:
6440
                ov->bridge = BRG_OV518;
6441
                ov->bclass = BCL_OV518;
6442
                break;
6443
        case PROD_OV518PLUS:
6444
                ov->bridge = BRG_OV518PLUS;
6445
                ov->bclass = BCL_OV518;
6446
                break;
6447
        case PROD_ME2CAM:
6448
                if (dev->descriptor.idVendor != VEND_MATTEL)
6449
                        goto error;
6450
                ov->bridge = BRG_OV511PLUS;
6451
                ov->bclass = BCL_OV511;
6452
                break;
6453
        default:
6454
                err("Unknown product ID 0x%04x", dev->descriptor.idProduct);
6455
                goto error_dealloc;
6456
        }
6457
 
6458
        info("USB %s video device found", symbolic(brglist, ov->bridge));
6459
 
6460
        /* Workaround for some applications that want data in RGB
6461
         * instead of BGR. */
6462
        if (force_rgb)
6463
                info("data format set to RGB");
6464
 
6465
        init_waitqueue_head(&ov->wq);
6466
 
6467
        init_MUTEX(&ov->lock);  /* to 1 == available */
6468
        init_MUTEX(&ov->buf_lock);
6469
        init_MUTEX(&ov->param_lock);
6470
        init_MUTEX(&ov->i2c_lock);
6471
        init_MUTEX(&ov->cbuf_lock);
6472
 
6473
        ov->buf_state = BUF_NOT_ALLOCATED;
6474
 
6475
        if (usb_make_path(dev, ov->usb_path, OV511_USB_PATH_LEN) < 0) {
6476
                err("usb_make_path error");
6477
                goto error_dealloc;
6478
        }
6479
 
6480
        /* Allocate control transfer buffer. */
6481
        /* Must be kmalloc()'ed, for DMA compatibility */
6482
        ov->cbuf = kmalloc(OV511_CBUF_SIZE, GFP_KERNEL);
6483
        if (!ov->cbuf)
6484
                goto error;
6485
 
6486
        if (ov->bclass == BCL_OV518) {
6487
                if (ov518_configure(ov) < 0)
6488
                        goto error;
6489
        } else {
6490
                if (ov511_configure(ov) < 0)
6491
                        goto error;
6492
        }
6493
 
6494
        for (i = 0; i < OV511_NUMFRAMES; i++) {
6495
                ov->frame[i].framenum = i;
6496
                init_waitqueue_head(&ov->frame[i].wq);
6497
        }
6498
 
6499
        for (i = 0; i < OV511_NUMSBUF; i++) {
6500
                ov->sbuf[i].ov = ov;
6501
                spin_lock_init(&ov->sbuf[i].lock);
6502
                ov->sbuf[i].n = i;
6503
        }
6504
 
6505
        /* Unnecessary? (This is done on open(). Need to make sure variables
6506
         * are properly initialized without this before removing it, though). */
6507
        if (ov51x_set_default_params(ov) < 0)
6508
                goto error;
6509
 
6510
#ifdef OV511_DEBUG
6511
        if (dump_bridge) {
6512
                if (ov->bclass == BCL_OV511)
6513
                        ov511_dump_regs(ov);
6514
                else
6515
                        ov518_dump_regs(ov);
6516
        }
6517
#endif
6518
 
6519
        memcpy(&ov->vdev, &vdev_template, sizeof(vdev_template));
6520
        ov->vdev.priv = ov;
6521
 
6522
        for (i = 0; i < OV511_MAX_UNIT_VIDEO; i++) {
6523
                /* Minor 0 cannot be specified; assume user wants autodetect */
6524
                if (unit_video[i] == 0)
6525
                        break;
6526
 
6527
                if (video_register_device(&ov->vdev, VFL_TYPE_GRABBER,
6528
                        unit_video[i]) >= 0) {
6529
                        registered = 1;
6530
                        break;
6531
                }
6532
        }
6533
 
6534
        /* Use the next available one */
6535
        if (!registered &&
6536
            video_register_device(&ov->vdev, VFL_TYPE_GRABBER, -1) < 0) {
6537
                err("video_register_device failed");
6538
                goto error;
6539
        }
6540
 
6541
        info("Device at %s registered to minor %d", ov->usb_path,
6542
             ov->vdev.minor);
6543
 
6544
#if defined(CONFIG_PROC_FS) && defined(CONFIG_VIDEO_PROC_FS)
6545
        create_proc_ov511_cam(ov);
6546
#endif
6547
 
6548
        MOD_DEC_USE_COUNT;
6549
        return ov;
6550
 
6551
error:
6552
#if defined(CONFIG_PROC_FS) && defined(CONFIG_VIDEO_PROC_FS)
6553
        /* Safe to call even if entry doesn't exist */
6554
        destroy_proc_ov511_cam(ov);
6555
#endif
6556
 
6557
        if (ov->cbuf) {
6558
                down(&ov->cbuf_lock);
6559
                kfree(ov->cbuf);
6560
                ov->cbuf = NULL;
6561
                up(&ov->cbuf_lock);
6562
        }
6563
 
6564
error_dealloc:
6565
        if (ov) {
6566
                kfree(ov);
6567
                ov = NULL;
6568
        }
6569
 
6570
error_out:
6571
        MOD_DEC_USE_COUNT;
6572
        err("Camera initialization failed");
6573
        return NULL;
6574
}
6575
 
6576
 
6577
static void
6578
ov51x_disconnect(struct usb_device *dev, void *ptr)
6579
{
6580
        struct usb_ov511 *ov = (struct usb_ov511 *) ptr;
6581
        int n;
6582
 
6583
        MOD_INC_USE_COUNT;
6584
 
6585
        PDEBUG(3, "");
6586
 
6587
        video_unregister_device(&ov->vdev);
6588
        if (ov->user)
6589
                PDEBUG(3, "Device open...deferring video_unregister_device");
6590
 
6591
        for (n = 0; n < OV511_NUMFRAMES; n++)
6592
                ov->frame[n].grabstate = FRAME_ERROR;
6593
 
6594
        ov->curframe = -1;
6595
 
6596
        /* This will cause the process to request another frame */
6597
        for (n = 0; n < OV511_NUMFRAMES; n++)
6598
                if (waitqueue_active(&ov->frame[n].wq))
6599
                        wake_up_interruptible(&ov->frame[n].wq);
6600
        if (waitqueue_active(&ov->wq))
6601
                wake_up_interruptible(&ov->wq);
6602
 
6603
        ov->streaming = 0;
6604
 
6605
        ov51x_unlink_isoc(ov);
6606
 
6607
#if defined(CONFIG_PROC_FS) && defined(CONFIG_VIDEO_PROC_FS)
6608
        destroy_proc_ov511_cam(ov);
6609
#endif
6610
 
6611
        ov->dev = NULL;
6612
 
6613
        /* Free the memory */
6614
        if (ov && !ov->user) {
6615
                down(&ov->cbuf_lock);
6616
                kfree(ov->cbuf);
6617
                ov->cbuf = NULL;
6618
                up(&ov->cbuf_lock);
6619
 
6620
                ov51x_dealloc(ov, 1);
6621
                kfree(ov);
6622
                ov = NULL;
6623
        }
6624
 
6625
        MOD_DEC_USE_COUNT;
6626
 
6627
        PDEBUG(3, "Disconnect complete");
6628
}
6629
 
6630
static struct usb_driver ov511_driver = {
6631
        .name =         "ov511",
6632
        .id_table =     device_table,
6633
        .probe =        ov51x_probe,
6634
        .disconnect =   ov51x_disconnect
6635
};
6636
 
6637
 
6638
/****************************************************************************
6639
 *
6640
 *  Module routines
6641
 *
6642
 ***************************************************************************/
6643
 
6644
/* Returns 0 for success */
6645
int
6646
ov511_register_decomp_module(int ver, struct ov51x_decomp_ops *ops, int ov518,
6647
                             int mmx)
6648
{
6649
        if (ver != DECOMP_INTERFACE_VER) {
6650
                err("Decompression module has incompatible");
6651
                err("interface version %d", ver);
6652
                err("Interface version %d is required", DECOMP_INTERFACE_VER);
6653
                return -EINVAL;
6654
        }
6655
 
6656
        if (!ops)
6657
                return -EFAULT;
6658
 
6659
        if (mmx && !ov51x_mmx_available) {
6660
                err("MMX not available on this system or kernel");
6661
                return -EINVAL;
6662
        }
6663
 
6664
        lock_kernel();
6665
 
6666
        if (ov518) {
6667
                if (mmx) {
6668
                        if (ov518_mmx_decomp_ops)
6669
                                goto err_in_use;
6670
                        else
6671
                                ov518_mmx_decomp_ops = ops;
6672
                } else {
6673
                        if (ov518_decomp_ops)
6674
                                goto err_in_use;
6675
                        else
6676
                                ov518_decomp_ops = ops;
6677
                }
6678
        } else {
6679
                if (mmx) {
6680
                        if (ov511_mmx_decomp_ops)
6681
                                goto err_in_use;
6682
                        else
6683
                                ov511_mmx_decomp_ops = ops;
6684
                } else {
6685
                        if (ov511_decomp_ops)
6686
                                goto err_in_use;
6687
                        else
6688
                                ov511_decomp_ops = ops;
6689
                }
6690
        }
6691
 
6692
        MOD_INC_USE_COUNT;
6693
 
6694
        unlock_kernel();
6695
        return 0;
6696
 
6697
err_in_use:
6698
        unlock_kernel();
6699
        return -EBUSY;
6700
}
6701
 
6702
void
6703
ov511_deregister_decomp_module(int ov518, int mmx)
6704
{
6705
        lock_kernel();
6706
 
6707
        if (ov518) {
6708
                if (mmx)
6709
                        ov518_mmx_decomp_ops = NULL;
6710
                else
6711
                        ov518_decomp_ops = NULL;
6712
        } else {
6713
                if (mmx)
6714
                        ov511_mmx_decomp_ops = NULL;
6715
                else
6716
                        ov511_decomp_ops = NULL;
6717
        }
6718
 
6719
        MOD_DEC_USE_COUNT;
6720
 
6721
        unlock_kernel();
6722
}
6723
 
6724
static int __init
6725
usb_ov511_init(void)
6726
{
6727
#if defined(CONFIG_PROC_FS) && defined(CONFIG_VIDEO_PROC_FS)
6728
        proc_ov511_create();
6729
#endif
6730
 
6731
        if (usb_register(&ov511_driver) < 0)
6732
                return -1;
6733
 
6734
#if defined (__i386__)
6735
        if (test_bit(X86_FEATURE_MMX, boot_cpu_data.x86_capability))
6736
                ov51x_mmx_available = 1;
6737
#endif
6738
 
6739
        info(DRIVER_VERSION " : " DRIVER_DESC);
6740
 
6741
        return 0;
6742
}
6743
 
6744
static void __exit
6745
usb_ov511_exit(void)
6746
{
6747
        usb_deregister(&ov511_driver);
6748
        info("driver deregistered");
6749
 
6750
#if defined(CONFIG_PROC_FS) && defined(CONFIG_VIDEO_PROC_FS)
6751
        proc_ov511_destroy();
6752
#endif
6753
}
6754
 
6755
module_init(usb_ov511_init);
6756
module_exit(usb_ov511_exit);
6757
 
6758
EXPORT_SYMBOL(ov511_register_decomp_module);
6759
EXPORT_SYMBOL(ov511_deregister_decomp_module);

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.