blob: 9d5d5985a7ea6ba2fb638145240ae8c9a7a50ca9 [file] [log] [blame]
Antoine Jacquetb7eee612007-04-27 12:30:59 -03001/*
2 * Zoran 364xx based USB webcam module version 0.72
3 *
4 * Allows you to use your USB webcam with V4L2 applications
5 * This is still in heavy developpement !
6 *
7 * Copyright (C) 2004 Antoine Jacquet <royale@zerezo.com>
8 * http://royale.zerezo.com/zr364xx/
9 *
10 * Heavily inspired by usb-skeleton.c, vicam.c, cpia.c and spca50x.c drivers
11 * V4L2 version inspired by meye.c driver
12 *
13 * This program is free software; you can redistribute it and/or modify
14 * it under the terms of the GNU General Public License as published by
15 * the Free Software Foundation; either version 2 of the License, or
16 * (at your option) any later version.
17 *
18 * This program is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU General Public License for more details.
22 *
23 * You should have received a copy of the GNU General Public License
24 * along with this program; if not, write to the Free Software
25 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
26 */
27
28
29#include <linux/version.h>
30#include <linux/module.h>
31#include <linux/init.h>
32#include <linux/usb.h>
33#include <linux/vmalloc.h>
34#include <linux/slab.h>
35#include <linux/proc_fs.h>
Antoine Jacquet2575f842007-03-05 06:32:29 -030036#include <linux/highmem.h>
Antoine Jacquetb7eee612007-04-27 12:30:59 -030037#include <media/v4l2-common.h>
Hans Verkuil35ea11f2008-07-20 08:12:02 -030038#include <media/v4l2-ioctl.h>
Antoine Jacquetb7eee612007-04-27 12:30:59 -030039
40
41/* Version Information */
42#define DRIVER_VERSION "v0.72"
43#define DRIVER_AUTHOR "Antoine Jacquet, http://royale.zerezo.com/"
44#define DRIVER_DESC "Zoran 364xx"
45
46
47/* Camera */
48#define FRAMES 2
49#define MAX_FRAME_SIZE 100000
50#define BUFFER_SIZE 0x1000
51#define CTRL_TIMEOUT 500
52
53
54/* Debug macro */
55#define DBG(x...) if (debug) info(x)
56
57
58/* Init methods, need to find nicer names for these
59 * the exact names of the chipsets would be the best if someone finds it */
60#define METHOD0 0
61#define METHOD1 1
62#define METHOD2 2
63
64
65/* Module parameters */
Douglas Schilling Landgrafff699e62008-04-22 14:41:48 -030066static int debug;
67static int mode;
Antoine Jacquetb7eee612007-04-27 12:30:59 -030068
69
70/* Module parameters interface */
71module_param(debug, int, 0644);
72MODULE_PARM_DESC(debug, "Debug level");
73module_param(mode, int, 0644);
74MODULE_PARM_DESC(mode, "0 = 320x240, 1 = 160x120, 2 = 640x480");
75
76
77/* Devices supported by this driver
78 * .driver_info contains the init method used by the camera */
79static struct usb_device_id device_table[] = {
80 {USB_DEVICE(0x08ca, 0x0109), .driver_info = METHOD0 },
81 {USB_DEVICE(0x041e, 0x4024), .driver_info = METHOD0 },
82 {USB_DEVICE(0x0d64, 0x0108), .driver_info = METHOD0 },
83 {USB_DEVICE(0x0546, 0x3187), .driver_info = METHOD0 },
84 {USB_DEVICE(0x0d64, 0x3108), .driver_info = METHOD0 },
85 {USB_DEVICE(0x0595, 0x4343), .driver_info = METHOD0 },
86 {USB_DEVICE(0x0bb0, 0x500d), .driver_info = METHOD0 },
87 {USB_DEVICE(0x0feb, 0x2004), .driver_info = METHOD0 },
88 {USB_DEVICE(0x055f, 0xb500), .driver_info = METHOD0 },
89 {USB_DEVICE(0x08ca, 0x2062), .driver_info = METHOD2 },
90 {USB_DEVICE(0x052b, 0x1a18), .driver_info = METHOD1 },
91 {USB_DEVICE(0x04c8, 0x0729), .driver_info = METHOD0 },
92 {USB_DEVICE(0x04f2, 0xa208), .driver_info = METHOD0 },
93 {USB_DEVICE(0x0784, 0x0040), .driver_info = METHOD1 },
94 {USB_DEVICE(0x06d6, 0x0034), .driver_info = METHOD0 },
95 {USB_DEVICE(0x0a17, 0x0062), .driver_info = METHOD2 },
Antoine Jacquetbebeaea2007-06-25 16:00:34 -030096 {USB_DEVICE(0x06d6, 0x003b), .driver_info = METHOD0 },
Antoine Jacquet71c04472008-01-25 22:01:53 -030097 {USB_DEVICE(0x0a17, 0x004e), .driver_info = METHOD2 },
Antoine Jacquetc0e0aff2008-01-25 22:03:10 -030098 {USB_DEVICE(0x041e, 0x405d), .driver_info = METHOD2 },
Antoine Jacquetb7eee612007-04-27 12:30:59 -030099 {} /* Terminating entry */
100};
101
102MODULE_DEVICE_TABLE(usb, device_table);
103
104
105/* Camera stuff */
106struct zr364xx_camera {
107 struct usb_device *udev; /* save off the usb device pointer */
108 struct usb_interface *interface;/* the interface for this device */
109 struct video_device *vdev; /* v4l video device */
110 u8 *framebuf;
111 int nb;
112 unsigned char *buffer;
113 int skip;
114 int brightness;
115 int width;
116 int height;
117 int method;
118 struct mutex lock;
119};
120
121
122/* function used to send initialisation commands to the camera */
123static int send_control_msg(struct usb_device *udev, u8 request, u16 value,
124 u16 index, unsigned char *cp, u16 size)
125{
126 int status;
127
128 unsigned char *transfer_buffer = kmalloc(size, GFP_KERNEL);
129 if (!transfer_buffer) {
130 info("kmalloc(%d) failed", size);
131 return -ENOMEM;
132 }
133
134 memcpy(transfer_buffer, cp, size);
135
136 status = usb_control_msg(udev,
137 usb_sndctrlpipe(udev, 0),
138 request,
139 USB_DIR_OUT | USB_TYPE_VENDOR |
140 USB_RECIP_DEVICE, value, index,
141 transfer_buffer, size, CTRL_TIMEOUT);
142
143 kfree(transfer_buffer);
144
145 if (status < 0)
146 info("Failed sending control message, error %d.", status);
147
148 return status;
149}
150
151
152/* Control messages sent to the camera to initialize it
153 * and launch the capture */
154typedef struct {
155 unsigned int value;
156 unsigned int size;
157 unsigned char *bytes;
158} message;
159
160/* method 0 */
161static unsigned char m0d1[] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 };
162static unsigned char m0d2[] = { 0, 0, 0, 0, 0, 0 };
163static unsigned char m0d3[] = { 0, 0 };
164static message m0[] = {
165 {0x1f30, 0, NULL},
166 {0xd000, 0, NULL},
167 {0x3370, sizeof(m0d1), m0d1},
168 {0x2000, 0, NULL},
169 {0x2f0f, 0, NULL},
170 {0x2610, sizeof(m0d2), m0d2},
171 {0xe107, 0, NULL},
172 {0x2502, 0, NULL},
173 {0x1f70, 0, NULL},
174 {0xd000, 0, NULL},
175 {0x9a01, sizeof(m0d3), m0d3},
176 {-1, -1, NULL}
177};
178
179/* method 1 */
180static unsigned char m1d1[] = { 0xff, 0xff };
181static unsigned char m1d2[] = { 0x00, 0x00 };
182static message m1[] = {
183 {0x1f30, 0, NULL},
184 {0xd000, 0, NULL},
185 {0xf000, 0, NULL},
186 {0x2000, 0, NULL},
187 {0x2f0f, 0, NULL},
188 {0x2650, 0, NULL},
189 {0xe107, 0, NULL},
190 {0x2502, sizeof(m1d1), m1d1},
191 {0x1f70, 0, NULL},
192 {0xd000, 0, NULL},
193 {0xd000, 0, NULL},
194 {0xd000, 0, NULL},
195 {0x9a01, sizeof(m1d2), m1d2},
196 {-1, -1, NULL}
197};
198
199/* method 2 */
200static unsigned char m2d1[] = { 0xff, 0xff };
201static message m2[] = {
202 {0x1f30, 0, NULL},
203 {0xf000, 0, NULL},
204 {0x2000, 0, NULL},
205 {0x2f0f, 0, NULL},
206 {0x2650, 0, NULL},
207 {0xe107, 0, NULL},
208 {0x2502, sizeof(m2d1), m2d1},
209 {0x1f70, 0, NULL},
210 {-1, -1, NULL}
211};
212
213/* init table */
214static message *init[3] = { m0, m1, m2 };
215
216
217/* JPEG static data in header (Huffman table, etc) */
218static unsigned char header1[] = {
219 0xFF, 0xD8,
220 /*
221 0xFF, 0xE0, 0x00, 0x10, 'J', 'F', 'I', 'F',
222 0x00, 0x01, 0x01, 0x00, 0x33, 0x8A, 0x00, 0x00, 0x33, 0x88,
223 */
224 0xFF, 0xDB, 0x00, 0x84
225};
226static unsigned char header2[] = {
227 0xFF, 0xC4, 0x00, 0x1F, 0x00, 0x00, 0x01, 0x05, 0x01, 0x01, 0x01,
228 0x01, 0x01, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
229 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0A, 0x0B,
230 0xFF, 0xC4, 0x00, 0xB5, 0x10, 0x00, 0x02, 0x01, 0x03, 0x03, 0x02,
231 0x04, 0x03, 0x05, 0x05, 0x04, 0x04, 0x00, 0x00, 0x01, 0x7D, 0x01,
232 0x02, 0x03, 0x00, 0x04, 0x11, 0x05, 0x12, 0x21, 0x31, 0x41, 0x06,
233 0x13, 0x51, 0x61, 0x07, 0x22, 0x71, 0x14, 0x32, 0x81, 0x91, 0xA1,
234 0x08, 0x23, 0x42, 0xB1, 0xC1, 0x15, 0x52, 0xD1, 0xF0, 0x24, 0x33,
235 0x62, 0x72, 0x82, 0x09, 0x0A, 0x16, 0x17, 0x18, 0x19, 0x1A, 0x25,
236 0x26, 0x27, 0x28, 0x29, 0x2A, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39,
237 0x3A, 0x43, 0x44, 0x45, 0x46, 0x47, 0x48, 0x49, 0x4A, 0x53, 0x54,
238 0x55, 0x56, 0x57, 0x58, 0x59, 0x5A, 0x63, 0x64, 0x65, 0x66, 0x67,
239 0x68, 0x69, 0x6A, 0x73, 0x74, 0x75, 0x76, 0x77, 0x78, 0x79, 0x7A,
240 0x83, 0x84, 0x85, 0x86, 0x87, 0x88, 0x89, 0x8A, 0x92, 0x93, 0x94,
241 0x95, 0x96, 0x97, 0x98, 0x99, 0x9A, 0xA2, 0xA3, 0xA4, 0xA5, 0xA6,
242 0xA7, 0xA8, 0xA9, 0xAA, 0xB2, 0xB3, 0xB4, 0xB5, 0xB6, 0xB7, 0xB8,
243 0xB9, 0xBA, 0xC2, 0xC3, 0xC4, 0xC5, 0xC6, 0xC7, 0xC8, 0xC9, 0xCA,
244 0xD2, 0xD3, 0xD4, 0xD5, 0xD6, 0xD7, 0xD8, 0xD9, 0xDA, 0xE1, 0xE2,
245 0xE3, 0xE4, 0xE5, 0xE6, 0xE7, 0xE8, 0xE9, 0xEA, 0xF1, 0xF2, 0xF3,
246 0xF4, 0xF5, 0xF6, 0xF7, 0xF8, 0xF9, 0xFA, 0xFF, 0xC4, 0x00, 0x1F,
247 0x01, 0x00, 0x03, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01,
248 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x02, 0x03, 0x04,
249 0x05, 0x06, 0x07, 0x08, 0x09, 0x0A, 0x0B, 0xFF, 0xC4, 0x00, 0xB5,
250 0x11, 0x00, 0x02, 0x01, 0x02, 0x04, 0x04, 0x03, 0x04, 0x07, 0x05,
251 0x04, 0x04, 0x00, 0x01, 0x02, 0x77, 0x00, 0x01, 0x02, 0x03, 0x11,
252 0x04, 0x05, 0x21, 0x31, 0x06, 0x12, 0x41, 0x51, 0x07, 0x61, 0x71,
253 0x13, 0x22, 0x32, 0x81, 0x08, 0x14, 0x42, 0x91, 0xA1, 0xB1, 0xC1,
254 0x09, 0x23, 0x33, 0x52, 0xF0, 0x15, 0x62, 0x72, 0xD1, 0x0A, 0x16,
255 0x24, 0x34, 0xE1, 0x25, 0xF1, 0x17, 0x18, 0x19, 0x1A, 0x26, 0x27,
256 0x28, 0x29, 0x2A, 0x35, 0x36, 0x37, 0x38, 0x39, 0x3A, 0x43, 0x44,
257 0x45, 0x46, 0x47, 0x48, 0x49, 0x4A, 0x53, 0x54, 0x55, 0x56, 0x57,
258 0x58, 0x59, 0x5A, 0x63, 0x64, 0x65, 0x66, 0x67, 0x68, 0x69, 0x6A,
259 0x73, 0x74, 0x75, 0x76, 0x77, 0x78, 0x79, 0x7A, 0x82, 0x83, 0x84,
260 0x85, 0x86, 0x87, 0x88, 0x89, 0x8A, 0x92, 0x93, 0x94, 0x95, 0x96,
261 0x97, 0x98, 0x99, 0x9A, 0xA2, 0xA3, 0xA4, 0xA5, 0xA6, 0xA7, 0xA8,
262 0xA9, 0xAA, 0xB2, 0xB3, 0xB4, 0xB5, 0xB6, 0xB7, 0xB8, 0xB9, 0xBA,
263 0xC2, 0xC3, 0xC4, 0xC5, 0xC6, 0xC7, 0xC8, 0xC9, 0xCA, 0xD2, 0xD3,
264 0xD4, 0xD5, 0xD6, 0xD7, 0xD8, 0xD9, 0xDA, 0xE2, 0xE3, 0xE4, 0xE5,
265 0xE6, 0xE7, 0xE8, 0xE9, 0xEA, 0xF2, 0xF3, 0xF4, 0xF5, 0xF6, 0xF7,
266 0xF8, 0xF9, 0xFA, 0xFF, 0xC0, 0x00, 0x11, 0x08, 0x00, 0xF0, 0x01,
267 0x40, 0x03, 0x01, 0x21, 0x00, 0x02, 0x11, 0x01, 0x03, 0x11, 0x01,
268 0xFF, 0xDA, 0x00, 0x0C, 0x03, 0x01, 0x00, 0x02, 0x11, 0x03, 0x11,
269 0x00, 0x3F, 0x00
270};
271static unsigned char header3;
272
273
274
275/********************/
276/* V4L2 integration */
277/********************/
278
279/* this function reads a full JPEG picture synchronously
280 * TODO: do it asynchronously... */
281static int read_frame(struct zr364xx_camera *cam, int framenum)
282{
283 int i, n, temp, head, size, actual_length;
Trent Piepho93566ad2007-03-07 18:19:49 -0300284 unsigned char *ptr = NULL, *jpeg;
Antoine Jacquetb7eee612007-04-27 12:30:59 -0300285
286 redo:
287 /* hardware brightness */
288 n = send_control_msg(cam->udev, 1, 0x2001, 0, NULL, 0);
289 temp = (0x60 << 8) + 127 - cam->brightness;
290 n = send_control_msg(cam->udev, 1, temp, 0, NULL, 0);
291
292 /* during the first loop we are going to insert JPEG header */
293 head = 0;
294 /* this is the place in memory where we are going to build
295 * the JPEG image */
296 jpeg = cam->framebuf + framenum * MAX_FRAME_SIZE;
297 /* read data... */
298 do {
299 n = usb_bulk_msg(cam->udev,
300 usb_rcvbulkpipe(cam->udev, 0x81),
301 cam->buffer, BUFFER_SIZE, &actual_length,
302 CTRL_TIMEOUT);
303 DBG("buffer : %d %d", cam->buffer[0], cam->buffer[1]);
304 DBG("bulk : n=%d size=%d", n, actual_length);
305 if (n < 0) {
306 info("error reading bulk msg");
307 return 0;
308 }
309 if (actual_length < 0 || actual_length > BUFFER_SIZE) {
310 info("wrong number of bytes");
311 return 0;
312 }
313
314 /* swap bytes if camera needs it */
Trent Piepho93566ad2007-03-07 18:19:49 -0300315 if (cam->method == METHOD0) {
316 u16 *buf = (u16*)cam->buffer;
317 for (i = 0; i < BUFFER_SIZE/2; i++)
318 swab16s(buf + i);
319 }
Antoine Jacquetb7eee612007-04-27 12:30:59 -0300320
321 /* write the JPEG header */
322 if (!head) {
323 DBG("jpeg header");
324 ptr = jpeg;
325 memcpy(ptr, header1, sizeof(header1));
326 ptr += sizeof(header1);
327 header3 = 0;
328 memcpy(ptr, &header3, 1);
329 ptr++;
330 memcpy(ptr, cam->buffer, 64);
331 ptr += 64;
332 header3 = 1;
333 memcpy(ptr, &header3, 1);
334 ptr++;
335 memcpy(ptr, cam->buffer + 64, 64);
336 ptr += 64;
337 memcpy(ptr, header2, sizeof(header2));
338 ptr += sizeof(header2);
339 memcpy(ptr, cam->buffer + 128,
340 actual_length - 128);
341 ptr += actual_length - 128;
342 head = 1;
343 DBG("header : %d %d %d %d %d %d %d %d %d",
344 cam->buffer[0], cam->buffer[1], cam->buffer[2],
345 cam->buffer[3], cam->buffer[4], cam->buffer[5],
346 cam->buffer[6], cam->buffer[7], cam->buffer[8]);
347 } else {
348 memcpy(ptr, cam->buffer, actual_length);
349 ptr += actual_length;
350 }
351 }
352 /* ... until there is no more */
353 while (actual_length == BUFFER_SIZE);
354
355 /* we skip the 2 first frames which are usually buggy */
356 if (cam->skip) {
357 cam->skip--;
358 goto redo;
359 }
360
361 /* go back to find the JPEG EOI marker */
362 size = ptr - jpeg;
363 ptr -= 2;
364 while (ptr > jpeg) {
365 if (*ptr == 0xFF && *(ptr + 1) == 0xD9
366 && *(ptr + 2) == 0xFF)
367 break;
368 ptr--;
369 }
370 if (ptr == jpeg)
371 DBG("No EOI marker");
372
373 /* Sometimes there is junk data in the middle of the picture,
374 * we want to skip this bogus frames */
375 while (ptr > jpeg) {
376 if (*ptr == 0xFF && *(ptr + 1) == 0xFF
377 && *(ptr + 2) == 0xFF)
378 break;
379 ptr--;
380 }
381 if (ptr != jpeg) {
382 DBG("Bogus frame ? %d", cam->nb);
383 goto redo;
384 }
385
386 DBG("jpeg : %d %d %d %d %d %d %d %d",
387 jpeg[0], jpeg[1], jpeg[2], jpeg[3],
388 jpeg[4], jpeg[5], jpeg[6], jpeg[7]);
389
390 return size;
391}
392
393
Al Viro97cf0102008-03-29 03:10:48 +0000394static ssize_t zr364xx_read(struct file *file, char __user *buf, size_t cnt,
Antoine Jacquetb7eee612007-04-27 12:30:59 -0300395 loff_t * ppos)
396{
397 unsigned long count = cnt;
398 struct video_device *vdev = video_devdata(file);
399 struct zr364xx_camera *cam;
400
401 DBG("zr364xx_read: read %d bytes.", (int) count);
402
403 if (vdev == NULL)
404 return -ENODEV;
405 cam = video_get_drvdata(vdev);
406
407 if (!buf)
408 return -EINVAL;
409
410 if (!count)
411 return -EINVAL;
412
413 /* NoMan Sux ! */
414 count = read_frame(cam, 0);
415
416 if (copy_to_user(buf, cam->framebuf, count))
417 return -EFAULT;
418
419 return count;
420}
421
422
423static int zr364xx_vidioc_querycap(struct file *file, void *priv,
424 struct v4l2_capability *cap)
425{
426 memset(cap, 0, sizeof(*cap));
427 strcpy(cap->driver, DRIVER_DESC);
428 cap->capabilities = V4L2_CAP_VIDEO_CAPTURE | V4L2_CAP_READWRITE;
429 return 0;
430}
431
432static int zr364xx_vidioc_enum_input(struct file *file, void *priv,
433 struct v4l2_input *i)
434{
435 if (i->index != 0)
436 return -EINVAL;
437 memset(i, 0, sizeof(*i));
438 i->index = 0;
439 strcpy(i->name, DRIVER_DESC " Camera");
440 i->type = V4L2_INPUT_TYPE_CAMERA;
441 return 0;
442}
443
444static int zr364xx_vidioc_g_input(struct file *file, void *priv,
445 unsigned int *i)
446{
447 *i = 0;
448 return 0;
449}
450
451static int zr364xx_vidioc_s_input(struct file *file, void *priv,
452 unsigned int i)
453{
454 if (i != 0)
455 return -EINVAL;
456 return 0;
457}
458
459static int zr364xx_vidioc_queryctrl(struct file *file, void *priv,
460 struct v4l2_queryctrl *c)
461{
462 struct video_device *vdev = video_devdata(file);
463 struct zr364xx_camera *cam;
464
465 if (vdev == NULL)
466 return -ENODEV;
467 cam = video_get_drvdata(vdev);
468
469 switch (c->id) {
470 case V4L2_CID_BRIGHTNESS:
471 c->type = V4L2_CTRL_TYPE_INTEGER;
472 strcpy(c->name, "Brightness");
473 c->minimum = 0;
474 c->maximum = 127;
475 c->step = 1;
476 c->default_value = cam->brightness;
477 c->flags = 0;
478 break;
479 default:
480 return -EINVAL;
481 }
482 return 0;
483}
484
485static int zr364xx_vidioc_s_ctrl(struct file *file, void *priv,
486 struct v4l2_control *c)
487{
488 struct video_device *vdev = video_devdata(file);
489 struct zr364xx_camera *cam;
490
491 if (vdev == NULL)
492 return -ENODEV;
493 cam = video_get_drvdata(vdev);
494
495 switch (c->id) {
496 case V4L2_CID_BRIGHTNESS:
497 cam->brightness = c->value;
498 break;
499 default:
500 return -EINVAL;
501 }
502 return 0;
503}
504
505static int zr364xx_vidioc_g_ctrl(struct file *file, void *priv,
506 struct v4l2_control *c)
507{
508 struct video_device *vdev = video_devdata(file);
509 struct zr364xx_camera *cam;
510
511 if (vdev == NULL)
512 return -ENODEV;
513 cam = video_get_drvdata(vdev);
514
515 switch (c->id) {
516 case V4L2_CID_BRIGHTNESS:
517 c->value = cam->brightness;
518 break;
519 default:
520 return -EINVAL;
521 }
522 return 0;
523}
524
Hans Verkuil78b526a2008-05-28 12:16:41 -0300525static int zr364xx_vidioc_enum_fmt_vid_cap(struct file *file,
Antoine Jacquetb7eee612007-04-27 12:30:59 -0300526 void *priv, struct v4l2_fmtdesc *f)
527{
528 if (f->index > 0)
529 return -EINVAL;
530 if (f->type != V4L2_BUF_TYPE_VIDEO_CAPTURE)
531 return -EINVAL;
532 memset(f, 0, sizeof(*f));
533 f->index = 0;
534 f->type = V4L2_BUF_TYPE_VIDEO_CAPTURE;
535 f->flags = V4L2_FMT_FLAG_COMPRESSED;
536 strcpy(f->description, "JPEG");
537 f->pixelformat = V4L2_PIX_FMT_JPEG;
538 return 0;
539}
540
Hans Verkuil78b526a2008-05-28 12:16:41 -0300541static int zr364xx_vidioc_try_fmt_vid_cap(struct file *file, void *priv,
Antoine Jacquetb7eee612007-04-27 12:30:59 -0300542 struct v4l2_format *f)
543{
544 struct video_device *vdev = video_devdata(file);
545 struct zr364xx_camera *cam;
546
547 if (vdev == NULL)
548 return -ENODEV;
549 cam = video_get_drvdata(vdev);
550
551 if (f->type != V4L2_BUF_TYPE_VIDEO_CAPTURE)
552 return -EINVAL;
553 if (f->fmt.pix.pixelformat != V4L2_PIX_FMT_JPEG)
554 return -EINVAL;
555 if (f->fmt.pix.field != V4L2_FIELD_ANY &&
556 f->fmt.pix.field != V4L2_FIELD_NONE)
557 return -EINVAL;
558 f->fmt.pix.field = V4L2_FIELD_NONE;
559 f->fmt.pix.width = cam->width;
560 f->fmt.pix.height = cam->height;
561 f->fmt.pix.bytesperline = f->fmt.pix.width * 2;
562 f->fmt.pix.sizeimage = f->fmt.pix.height * f->fmt.pix.bytesperline;
563 f->fmt.pix.colorspace = 0;
564 f->fmt.pix.priv = 0;
565 return 0;
566}
567
Hans Verkuil78b526a2008-05-28 12:16:41 -0300568static int zr364xx_vidioc_g_fmt_vid_cap(struct file *file, void *priv,
Antoine Jacquetb7eee612007-04-27 12:30:59 -0300569 struct v4l2_format *f)
570{
571 struct video_device *vdev = video_devdata(file);
572 struct zr364xx_camera *cam;
573
574 if (vdev == NULL)
575 return -ENODEV;
576 cam = video_get_drvdata(vdev);
577
578 if (f->type != V4L2_BUF_TYPE_VIDEO_CAPTURE)
579 return -EINVAL;
580 memset(&f->fmt.pix, 0, sizeof(struct v4l2_pix_format));
581 f->type = V4L2_BUF_TYPE_VIDEO_CAPTURE;
582 f->fmt.pix.pixelformat = V4L2_PIX_FMT_JPEG;
583 f->fmt.pix.field = V4L2_FIELD_NONE;
584 f->fmt.pix.width = cam->width;
585 f->fmt.pix.height = cam->height;
586 f->fmt.pix.bytesperline = f->fmt.pix.width * 2;
587 f->fmt.pix.sizeimage = f->fmt.pix.height * f->fmt.pix.bytesperline;
588 f->fmt.pix.colorspace = 0;
589 f->fmt.pix.priv = 0;
590 return 0;
591}
592
Hans Verkuil78b526a2008-05-28 12:16:41 -0300593static int zr364xx_vidioc_s_fmt_vid_cap(struct file *file, void *priv,
Antoine Jacquetb7eee612007-04-27 12:30:59 -0300594 struct v4l2_format *f)
595{
596 struct video_device *vdev = video_devdata(file);
597 struct zr364xx_camera *cam;
598
599 if (vdev == NULL)
600 return -ENODEV;
601 cam = video_get_drvdata(vdev);
602
603 if (f->type != V4L2_BUF_TYPE_VIDEO_CAPTURE)
604 return -EINVAL;
605 if (f->fmt.pix.pixelformat != V4L2_PIX_FMT_JPEG)
606 return -EINVAL;
607 if (f->fmt.pix.field != V4L2_FIELD_ANY &&
608 f->fmt.pix.field != V4L2_FIELD_NONE)
609 return -EINVAL;
610 f->fmt.pix.field = V4L2_FIELD_NONE;
611 f->fmt.pix.width = cam->width;
612 f->fmt.pix.height = cam->height;
613 f->fmt.pix.bytesperline = f->fmt.pix.width * 2;
614 f->fmt.pix.sizeimage = f->fmt.pix.height * f->fmt.pix.bytesperline;
615 f->fmt.pix.colorspace = 0;
616 f->fmt.pix.priv = 0;
617 DBG("ok!");
618 return 0;
619}
620
621static int zr364xx_vidioc_streamon(struct file *file, void *priv,
622 enum v4l2_buf_type type)
623{
624 return 0;
625}
626
627static int zr364xx_vidioc_streamoff(struct file *file, void *priv,
628 enum v4l2_buf_type type)
629{
630 return 0;
631}
632
633
634/* open the camera */
635static int zr364xx_open(struct inode *inode, struct file *file)
636{
637 struct video_device *vdev = video_devdata(file);
638 struct zr364xx_camera *cam = video_get_drvdata(vdev);
639 struct usb_device *udev = cam->udev;
640 int i, err;
641
642 DBG("zr364xx_open");
643
Antoine Jacquet69025c92008-08-18 17:09:53 -0300644 mutex_lock(&cam->lock);
645
Antoine Jacquetb7eee612007-04-27 12:30:59 -0300646 cam->skip = 2;
647
648 err = video_exclusive_open(inode, file);
Antoine Jacquet69025c92008-08-18 17:09:53 -0300649 if (err < 0)
650 goto out;
Antoine Jacquetb7eee612007-04-27 12:30:59 -0300651
652 if (!cam->framebuf) {
653 cam->framebuf = vmalloc_32(MAX_FRAME_SIZE * FRAMES);
654 if (!cam->framebuf) {
655 info("vmalloc_32 failed!");
Antoine Jacquet69025c92008-08-18 17:09:53 -0300656 err = -ENOMEM;
657 goto out;
Antoine Jacquetb7eee612007-04-27 12:30:59 -0300658 }
659 }
660
Antoine Jacquetb7eee612007-04-27 12:30:59 -0300661 for (i = 0; init[cam->method][i].size != -1; i++) {
662 err =
663 send_control_msg(udev, 1, init[cam->method][i].value,
664 0, init[cam->method][i].bytes,
665 init[cam->method][i].size);
666 if (err < 0) {
667 info("error during open sequence: %d", i);
Antoine Jacquet69025c92008-08-18 17:09:53 -0300668 goto out;
Antoine Jacquetb7eee612007-04-27 12:30:59 -0300669 }
670 }
671
672 file->private_data = vdev;
673
674 /* Added some delay here, since opening/closing the camera quickly,
675 * like Ekiga does during its startup, can crash the webcam
676 */
677 mdelay(100);
Antoine Jacquet69025c92008-08-18 17:09:53 -0300678 err = 0;
Antoine Jacquetb7eee612007-04-27 12:30:59 -0300679
Antoine Jacquet69025c92008-08-18 17:09:53 -0300680out:
Antoine Jacquetb7eee612007-04-27 12:30:59 -0300681 mutex_unlock(&cam->lock);
Antoine Jacquet69025c92008-08-18 17:09:53 -0300682 return err;
Antoine Jacquetb7eee612007-04-27 12:30:59 -0300683}
684
685
686/* release the camera */
687static int zr364xx_release(struct inode *inode, struct file *file)
688{
689 struct video_device *vdev = video_devdata(file);
690 struct zr364xx_camera *cam;
691 struct usb_device *udev;
692 int i, err;
693
694 DBG("zr364xx_release");
695
696 if (vdev == NULL)
697 return -ENODEV;
698 cam = video_get_drvdata(vdev);
699
700 udev = cam->udev;
701
702 mutex_lock(&cam->lock);
703 for (i = 0; i < 2; i++) {
704 err =
705 send_control_msg(udev, 1, init[cam->method][i].value,
706 0, init[i][cam->method].bytes,
707 init[cam->method][i].size);
708 if (err < 0) {
709 info("error during release sequence");
710 mutex_unlock(&cam->lock);
711 return err;
712 }
713 }
714
715 file->private_data = NULL;
716 video_exclusive_release(inode, file);
717
718 /* Added some delay here, since opening/closing the camera quickly,
719 * like Ekiga does during its startup, can crash the webcam
720 */
721 mdelay(100);
722
723 mutex_unlock(&cam->lock);
724 return 0;
725}
726
727
728static int zr364xx_mmap(struct file *file, struct vm_area_struct *vma)
729{
730 void *pos;
731 unsigned long start = vma->vm_start;
732 unsigned long size = vma->vm_end - vma->vm_start;
733 struct video_device *vdev = video_devdata(file);
734 struct zr364xx_camera *cam;
735
736 DBG("zr364xx_mmap: %ld\n", size);
737
738 if (vdev == NULL)
739 return -ENODEV;
740 cam = video_get_drvdata(vdev);
741
742 pos = cam->framebuf;
743 while (size > 0) {
744 if (vm_insert_page(vma, start, vmalloc_to_page(pos)))
745 return -EAGAIN;
746 start += PAGE_SIZE;
747 pos += PAGE_SIZE;
748 if (size > PAGE_SIZE)
749 size -= PAGE_SIZE;
750 else
751 size = 0;
752 }
753
754 return 0;
755}
756
757
Douglas Schilling Landgrafbdd36652007-10-29 00:37:07 -0300758static const struct file_operations zr364xx_fops = {
Antoine Jacquetb7eee612007-04-27 12:30:59 -0300759 .owner = THIS_MODULE,
760 .open = zr364xx_open,
761 .release = zr364xx_release,
762 .read = zr364xx_read,
763 .mmap = zr364xx_mmap,
764 .ioctl = video_ioctl2,
765 .llseek = no_llseek,
766};
767
Hans Verkuila3998102008-07-21 02:57:38 -0300768static const struct v4l2_ioctl_ops zr364xx_ioctl_ops = {
Antoine Jacquetb7eee612007-04-27 12:30:59 -0300769 .vidioc_querycap = zr364xx_vidioc_querycap,
Hans Verkuil78b526a2008-05-28 12:16:41 -0300770 .vidioc_enum_fmt_vid_cap = zr364xx_vidioc_enum_fmt_vid_cap,
771 .vidioc_try_fmt_vid_cap = zr364xx_vidioc_try_fmt_vid_cap,
772 .vidioc_s_fmt_vid_cap = zr364xx_vidioc_s_fmt_vid_cap,
773 .vidioc_g_fmt_vid_cap = zr364xx_vidioc_g_fmt_vid_cap,
Antoine Jacquetb7eee612007-04-27 12:30:59 -0300774 .vidioc_enum_input = zr364xx_vidioc_enum_input,
775 .vidioc_g_input = zr364xx_vidioc_g_input,
776 .vidioc_s_input = zr364xx_vidioc_s_input,
777 .vidioc_streamon = zr364xx_vidioc_streamon,
778 .vidioc_streamoff = zr364xx_vidioc_streamoff,
779 .vidioc_queryctrl = zr364xx_vidioc_queryctrl,
780 .vidioc_g_ctrl = zr364xx_vidioc_g_ctrl,
781 .vidioc_s_ctrl = zr364xx_vidioc_s_ctrl,
782};
783
Hans Verkuila3998102008-07-21 02:57:38 -0300784static struct video_device zr364xx_template = {
Hans Verkuila3998102008-07-21 02:57:38 -0300785 .name = DRIVER_DESC,
Hans Verkuila3998102008-07-21 02:57:38 -0300786 .fops = &zr364xx_fops,
787 .ioctl_ops = &zr364xx_ioctl_ops,
788 .release = video_device_release,
789 .minor = -1,
790};
791
Antoine Jacquetb7eee612007-04-27 12:30:59 -0300792
793
794/*******************/
795/* USB integration */
796/*******************/
797
798static int zr364xx_probe(struct usb_interface *intf,
799 const struct usb_device_id *id)
800{
801 struct usb_device *udev = interface_to_usbdev(intf);
802 struct zr364xx_camera *cam = NULL;
Akinobu Mita783aa8f2007-05-20 09:12:10 -0300803 int err;
Antoine Jacquetb7eee612007-04-27 12:30:59 -0300804
805 DBG("probing...");
806
807 info(DRIVER_DESC " compatible webcam plugged");
808 info("model %04x:%04x detected", udev->descriptor.idVendor,
809 udev->descriptor.idProduct);
810
Akinobu Mita783aa8f2007-05-20 09:12:10 -0300811 cam = kzalloc(sizeof(struct zr364xx_camera), GFP_KERNEL);
812 if (cam == NULL) {
Antoine Jacquetb7eee612007-04-27 12:30:59 -0300813 info("cam: out of memory !");
Akinobu Mita783aa8f2007-05-20 09:12:10 -0300814 return -ENOMEM;
Antoine Jacquetb7eee612007-04-27 12:30:59 -0300815 }
Antoine Jacquetb7eee612007-04-27 12:30:59 -0300816 /* save the init method used by this camera */
817 cam->method = id->driver_info;
818
819 cam->vdev = video_device_alloc();
820 if (cam->vdev == NULL) {
821 info("cam->vdev: out of memory !");
822 kfree(cam);
Akinobu Mita783aa8f2007-05-20 09:12:10 -0300823 return -ENOMEM;
Antoine Jacquetb7eee612007-04-27 12:30:59 -0300824 }
825 memcpy(cam->vdev, &zr364xx_template, sizeof(zr364xx_template));
826 video_set_drvdata(cam->vdev, cam);
827 if (debug)
828 cam->vdev->debug = V4L2_DEBUG_IOCTL | V4L2_DEBUG_IOCTL_ARG;
829
830 cam->udev = udev;
831
832 if ((cam->buffer = kmalloc(BUFFER_SIZE, GFP_KERNEL)) == NULL) {
833 info("cam->buffer: out of memory !");
834 video_device_release(cam->vdev);
835 kfree(cam);
836 return -ENODEV;
837 }
838
839 switch (mode) {
840 case 1:
841 info("160x120 mode selected");
842 cam->width = 160;
843 cam->height = 120;
844 break;
845 case 2:
846 info("640x480 mode selected");
847 cam->width = 640;
848 cam->height = 480;
849 break;
850 default:
851 info("320x240 mode selected");
852 cam->width = 320;
853 cam->height = 240;
854 break;
855 }
856
857 m0d1[0] = mode;
858 m1[2].value = 0xf000 + mode;
859 m2[1].value = 0xf000 + mode;
860 header2[437] = cam->height / 256;
861 header2[438] = cam->height % 256;
862 header2[439] = cam->width / 256;
863 header2[440] = cam->width % 256;
864
865 cam->nb = 0;
866 cam->brightness = 64;
867 mutex_init(&cam->lock);
868
Akinobu Mita783aa8f2007-05-20 09:12:10 -0300869 err = video_register_device(cam->vdev, VFL_TYPE_GRABBER, -1);
870 if (err) {
Antoine Jacquetb7eee612007-04-27 12:30:59 -0300871 info("video_register_device failed");
872 video_device_release(cam->vdev);
873 kfree(cam->buffer);
874 kfree(cam);
Akinobu Mita783aa8f2007-05-20 09:12:10 -0300875 return err;
Antoine Jacquetb7eee612007-04-27 12:30:59 -0300876 }
877
878 usb_set_intfdata(intf, cam);
879
880 info(DRIVER_DESC " controlling video device %d", cam->vdev->minor);
881 return 0;
882}
883
884
885static void zr364xx_disconnect(struct usb_interface *intf)
886{
887 struct zr364xx_camera *cam = usb_get_intfdata(intf);
888 usb_set_intfdata(intf, NULL);
889 dev_set_drvdata(&intf->dev, NULL);
890 info(DRIVER_DESC " webcam unplugged");
891 if (cam->vdev)
892 video_unregister_device(cam->vdev);
893 cam->vdev = NULL;
894 kfree(cam->buffer);
895 if (cam->framebuf)
896 vfree(cam->framebuf);
897 kfree(cam);
898}
899
900
901
902/**********************/
903/* Module integration */
904/**********************/
905
906static struct usb_driver zr364xx_driver = {
907 .name = "zr364xx",
908 .probe = zr364xx_probe,
909 .disconnect = zr364xx_disconnect,
910 .id_table = device_table
911};
912
913
914static int __init zr364xx_init(void)
915{
916 int retval;
Akinobu Mita783aa8f2007-05-20 09:12:10 -0300917 retval = usb_register(&zr364xx_driver);
Antoine Jacquetb7eee612007-04-27 12:30:59 -0300918 if (retval)
919 info("usb_register failed!");
920 else
921 info(DRIVER_DESC " module loaded");
922 return retval;
923}
924
925
926static void __exit zr364xx_exit(void)
927{
928 info(DRIVER_DESC " module unloaded");
929 usb_deregister(&zr364xx_driver);
930}
931
932
933module_init(zr364xx_init);
934module_exit(zr364xx_exit);
935
936MODULE_AUTHOR(DRIVER_AUTHOR);
937MODULE_DESCRIPTION(DRIVER_DESC);
938MODULE_LICENSE("GPL");