1/***************************************************************************
2 * Video4Linux driver for W996[87]CF JPEG USB Dual Mode Camera Chip.       *
3 *                                                                         *
4 * Copyright (C) 2002-2004 by Luca Risolia <luca.risolia@studio.unibo.it>  *
5 *                                                                         *
6 * - Memory management code from bttv driver by Ralph Metzler,             *
7 *   Marcus Metzler and Gerd Knorr.                                        *
8 * - I2C interface to kernel, high-level image sensor control routines and *
9 *   some symbolic names from OV511 driver by Mark W. McClelland.          *
10 * - Low-level I2C fast write function by Piotr Czerczak.                  *
11 * - Low-level I2C read function by Frederic Jouault.                      *
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., 675 Mass Ave, Cambridge, MA 02139, USA.               *
26 ***************************************************************************/
27
28#include <linux/module.h>
29#include <linux/kernel.h>
30#include <linux/kmod.h>
31#include <linux/init.h>
32#include <linux/fs.h>
33#include <linux/vmalloc.h>
34#include <linux/slab.h>
35#include <linux/mm.h>
36#include <linux/string.h>
37#include <linux/errno.h>
38#include <linux/sched.h>
39#include <linux/ioctl.h>
40#include <linux/delay.h>
41#include <linux/stddef.h>
42#include <asm/page.h>
43#include <asm/uaccess.h>
44#include <linux/page-flags.h>
45#include <linux/moduleparam.h>
46
47#include "w9968cf.h"
48#include "w9968cf_decoder.h"
49
50static struct w9968cf_vpp_t* w9968cf_vpp;
51static DECLARE_WAIT_QUEUE_HEAD(w9968cf_vppmod_wait);
52
53static LIST_HEAD(w9968cf_dev_list); /* head of V4L registered cameras list */
54static DEFINE_MUTEX(w9968cf_devlist_mutex); /* semaphore for list traversal */
55
56static DECLARE_RWSEM(w9968cf_disconnect); /* prevent races with open() */
57
58
59/****************************************************************************
60 * Module macros and parameters                                             *
61 ****************************************************************************/
62
63MODULE_DEVICE_TABLE(usb, winbond_id_table);
64
65MODULE_AUTHOR(W9968CF_MODULE_AUTHOR" "W9968CF_AUTHOR_EMAIL);
66MODULE_DESCRIPTION(W9968CF_MODULE_NAME);
67MODULE_VERSION(W9968CF_MODULE_VERSION);
68MODULE_LICENSE(W9968CF_MODULE_LICENSE);
69MODULE_SUPPORTED_DEVICE("Video");
70
71static int ovmod_load = W9968CF_OVMOD_LOAD;
72static unsigned short simcams = W9968CF_SIMCAMS;
73static short video_nr[]={[0 ... W9968CF_MAX_DEVICES-1] = -1}; /*-1=first free*/
74static unsigned int packet_size[] = {[0 ... W9968CF_MAX_DEVICES-1] =
75				     W9968CF_PACKET_SIZE};
76static unsigned short max_buffers[] = {[0 ... W9968CF_MAX_DEVICES-1] =
77				       W9968CF_BUFFERS};
78static int double_buffer[] = {[0 ... W9968CF_MAX_DEVICES-1] =
79			      W9968CF_DOUBLE_BUFFER};
80static int clamping[] = {[0 ... W9968CF_MAX_DEVICES-1] = W9968CF_CLAMPING};
81static unsigned short filter_type[]= {[0 ... W9968CF_MAX_DEVICES-1] =
82				      W9968CF_FILTER_TYPE};
83static int largeview[]= {[0 ... W9968CF_MAX_DEVICES-1] = W9968CF_LARGEVIEW};
84static unsigned short decompression[] = {[0 ... W9968CF_MAX_DEVICES-1] =
85					 W9968CF_DECOMPRESSION};
86static int upscaling[]= {[0 ... W9968CF_MAX_DEVICES-1] = W9968CF_UPSCALING};
87static unsigned short force_palette[] = {[0 ... W9968CF_MAX_DEVICES-1] = 0};
88static int force_rgb[] = {[0 ... W9968CF_MAX_DEVICES-1] = W9968CF_FORCE_RGB};
89static int autobright[] = {[0 ... W9968CF_MAX_DEVICES-1] = W9968CF_AUTOBRIGHT};
90static int autoexp[] = {[0 ... W9968CF_MAX_DEVICES-1] = W9968CF_AUTOEXP};
91static unsigned short lightfreq[] = {[0 ... W9968CF_MAX_DEVICES-1] =
92				     W9968CF_LIGHTFREQ};
93static int bandingfilter[] = {[0 ... W9968CF_MAX_DEVICES-1]=
94			      W9968CF_BANDINGFILTER};
95static short clockdiv[] = {[0 ... W9968CF_MAX_DEVICES-1] = W9968CF_CLOCKDIV};
96static int backlight[] = {[0 ... W9968CF_MAX_DEVICES-1] = W9968CF_BACKLIGHT};
97static int mirror[] = {[0 ... W9968CF_MAX_DEVICES-1] = W9968CF_MIRROR};
98static int monochrome[] = {[0 ... W9968CF_MAX_DEVICES-1]=W9968CF_MONOCHROME};
99static unsigned int brightness[] = {[0 ... W9968CF_MAX_DEVICES-1] =
100				    W9968CF_BRIGHTNESS};
101static unsigned int hue[] = {[0 ... W9968CF_MAX_DEVICES-1] = W9968CF_HUE};
102static unsigned int colour[]={[0 ... W9968CF_MAX_DEVICES-1] = W9968CF_COLOUR};
103static unsigned int contrast[] = {[0 ... W9968CF_MAX_DEVICES-1] =
104				  W9968CF_CONTRAST};
105static unsigned int whiteness[] = {[0 ... W9968CF_MAX_DEVICES-1] =
106				   W9968CF_WHITENESS};
107#ifdef W9968CF_DEBUG
108static unsigned short debug = W9968CF_DEBUG_LEVEL;
109static int specific_debug = W9968CF_SPECIFIC_DEBUG;
110#endif
111
112static unsigned int param_nv[24]; /* number of values per parameter */
113
114#ifdef CONFIG_KMOD
115module_param(ovmod_load, bool, 0644);
116#endif
117module_param(simcams, ushort, 0644);
118module_param_array(video_nr, short, &param_nv[0], 0444);
119module_param_array(packet_size, uint, &param_nv[1], 0444);
120module_param_array(max_buffers, ushort, &param_nv[2], 0444);
121module_param_array(double_buffer, bool, &param_nv[3], 0444);
122module_param_array(clamping, bool, &param_nv[4], 0444);
123module_param_array(filter_type, ushort, &param_nv[5], 0444);
124module_param_array(largeview, bool, &param_nv[6], 0444);
125module_param_array(decompression, ushort, &param_nv[7], 0444);
126module_param_array(upscaling, bool, &param_nv[8], 0444);
127module_param_array(force_palette, ushort, &param_nv[9], 0444);
128module_param_array(force_rgb, ushort, &param_nv[10], 0444);
129module_param_array(autobright, bool, &param_nv[11], 0444);
130module_param_array(autoexp, bool, &param_nv[12], 0444);
131module_param_array(lightfreq, ushort, &param_nv[13], 0444);
132module_param_array(bandingfilter, bool, &param_nv[14], 0444);
133module_param_array(clockdiv, short, &param_nv[15], 0444);
134module_param_array(backlight, bool, &param_nv[16], 0444);
135module_param_array(mirror, bool, &param_nv[17], 0444);
136module_param_array(monochrome, bool, &param_nv[18], 0444);
137module_param_array(brightness, uint, &param_nv[19], 0444);
138module_param_array(hue, uint, &param_nv[20], 0444);
139module_param_array(colour, uint, &param_nv[21], 0444);
140module_param_array(contrast, uint, &param_nv[22], 0444);
141module_param_array(whiteness, uint, &param_nv[23], 0444);
142#ifdef W9968CF_DEBUG
143module_param(debug, ushort, 0644);
144module_param(specific_debug, bool, 0644);
145#endif
146
147#ifdef CONFIG_KMOD
148MODULE_PARM_DESC(ovmod_load,
149		 "\n<0|1> Automatic 'ovcamchip' module loading."
150		 "\n0 disabled, 1 enabled."
151		 "\nIf enabled,'insmod' searches for the required 'ovcamchip'"
152		 "\nmodule in the system, according to its configuration, and"
153		 "\nattempts to load that module automatically. This action is"
154		 "\nperformed once as soon as the 'w9968cf' module is loaded"
155		 "\ninto memory."
156		 "\nDefault value is "__MODULE_STRING(W9968CF_OVMOD_LOAD)"."
157		 "\n");
158#endif
159MODULE_PARM_DESC(simcams,
160		 "\n<n> Number of cameras allowed to stream simultaneously."
161		 "\nn may vary from 0 to "
162		 __MODULE_STRING(W9968CF_MAX_DEVICES)"."
163		 "\nDefault value is "__MODULE_STRING(W9968CF_SIMCAMS)"."
164		 "\n");
165MODULE_PARM_DESC(video_nr,
166		 "\n<-1|n[,...]> Specify V4L minor mode number."
167		 "\n -1 = use next available (default)"
168		 "\n  n = use minor number n (integer >= 0)"
169		 "\nYou can specify up to "__MODULE_STRING(W9968CF_MAX_DEVICES)
170		 " cameras this way."
171		 "\nFor example:"
172		 "\nvideo_nr=-1,2,-1 would assign minor number 2 to"
173		 "\nthe second camera and use auto for the first"
174		 "\none and for every other camera."
175		 "\n");
176MODULE_PARM_DESC(packet_size,
177		 "\n<n[,...]> Specify the maximum data payload"
178		 "\nsize in bytes for alternate settings, for each device."
179		 "\nn is scaled between 63 and 1023 "
180		 "(default is "__MODULE_STRING(W9968CF_PACKET_SIZE)")."
181		 "\n");
182MODULE_PARM_DESC(max_buffers,
183		 "\n<n[,...]> For advanced users."
184		 "\nSpecify the maximum number of video frame buffers"
185		 "\nto allocate for each device, from 2 to "
186		 __MODULE_STRING(W9968CF_MAX_BUFFERS)
187		 ". (default is "__MODULE_STRING(W9968CF_BUFFERS)")."
188		 "\n");
189MODULE_PARM_DESC(double_buffer,
190		 "\n<0|1[,...]> "
191		 "Hardware double buffering: 0 disabled, 1 enabled."
192		 "\nIt should be enabled if you want smooth video output: if"
193		 "\nyou obtain out of sync. video, disable it, or try to"
194		 "\ndecrease the 'clockdiv' module parameter value."
195		 "\nDefault value is "__MODULE_STRING(W9968CF_DOUBLE_BUFFER)
196		 " for every device."
197		 "\n");
198MODULE_PARM_DESC(clamping,
199		 "\n<0|1[,...]> Video data clamping: 0 disabled, 1 enabled."
200		 "\nDefault value is "__MODULE_STRING(W9968CF_CLAMPING)
201		 " for every device."
202		 "\n");
203MODULE_PARM_DESC(filter_type,
204		 "\n<0|1|2[,...]> Video filter type."
205		 "\n0 none, 1 (1-2-1) 3-tap filter, "
206		 "2 (2-3-6-3-2) 5-tap filter."
207		 "\nDefault value is "__MODULE_STRING(W9968CF_FILTER_TYPE)
208		 " for every device."
209		 "\nThe filter is used to reduce noise and aliasing artifacts"
210		 "\nproduced by the CCD or CMOS image sensor, and the scaling"
211		 " process."
212		 "\n");
213MODULE_PARM_DESC(largeview,
214		 "\n<0|1[,...]> Large view: 0 disabled, 1 enabled."
215		 "\nDefault value is "__MODULE_STRING(W9968CF_LARGEVIEW)
216		 " for every device."
217		 "\n");
218MODULE_PARM_DESC(upscaling,
219		 "\n<0|1[,...]> Software scaling (for non-compressed video):"
220		 "\n0 disabled, 1 enabled."
221		 "\nDisable it if you have a slow CPU or you don't have"
222		 " enough memory."
223		 "\nDefault value is "__MODULE_STRING(W9968CF_UPSCALING)
224		 " for every device."
225		 "\nIf 'w9968cf-vpp' is not present, this parameter is"
226		 " set to 0."
227		 "\n");
228MODULE_PARM_DESC(decompression,
229		 "\n<0|1|2[,...]> Software video decompression:"
230		 "\n- 0 disables decompression (doesn't allow formats needing"
231		 " decompression)"
232		 "\n- 1 forces decompression (allows formats needing"
233		 " decompression only);"
234		 "\n- 2 allows any permitted formats."
235		 "\nFormats supporting compressed video are YUV422P and"
236		 " YUV420P/YUV420 "
237		 "\nin any resolutions where both width and height are "
238		 "a multiple of 16."
239		 "\nDefault value is "__MODULE_STRING(W9968CF_DECOMPRESSION)
240		 " for every device."
241		 "\nIf 'w9968cf-vpp' is not present, forcing decompression is "
242		 "\nnot allowed; in this case this parameter is set to 2."
243		 "\n");
244MODULE_PARM_DESC(force_palette,
245		 "\n<0"
246		 "|" __MODULE_STRING(VIDEO_PALETTE_UYVY)
247		 "|" __MODULE_STRING(VIDEO_PALETTE_YUV420)
248		 "|" __MODULE_STRING(VIDEO_PALETTE_YUV422P)
249		 "|" __MODULE_STRING(VIDEO_PALETTE_YUV420P)
250		 "|" __MODULE_STRING(VIDEO_PALETTE_YUYV)
251		 "|" __MODULE_STRING(VIDEO_PALETTE_YUV422)
252		 "|" __MODULE_STRING(VIDEO_PALETTE_GREY)
253		 "|" __MODULE_STRING(VIDEO_PALETTE_RGB555)
254		 "|" __MODULE_STRING(VIDEO_PALETTE_RGB565)
255		 "|" __MODULE_STRING(VIDEO_PALETTE_RGB24)
256		 "|" __MODULE_STRING(VIDEO_PALETTE_RGB32)
257		 "[,...]>"
258		 " Force picture palette."
259		 "\nIn order:"
260		 "\n- 0 allows any of the following formats:"
261		 "\n- UYVY    16 bpp - Original video, compression disabled"
262		 "\n- YUV420  12 bpp - Original video, compression enabled"
263		 "\n- YUV422P 16 bpp - Original video, compression enabled"
264		 "\n- YUV420P 12 bpp - Original video, compression enabled"
265		 "\n- YUVY    16 bpp - Software conversion from UYVY"
266		 "\n- YUV422  16 bpp - Software conversion from UYVY"
267		 "\n- GREY     8 bpp - Software conversion from UYVY"
268		 "\n- RGB555  16 bpp - Software conversion from UYVY"
269		 "\n- RGB565  16 bpp - Software conversion from UYVY"
270		 "\n- RGB24   24 bpp - Software conversion from UYVY"
271		 "\n- RGB32   32 bpp - Software conversion from UYVY"
272		 "\nWhen not 0, this parameter will override 'decompression'."
273		 "\nDefault value is 0 for every device."
274		 "\nInitial palette is "
275		 __MODULE_STRING(W9968CF_PALETTE_DECOMP_ON)"."
276		 "\nIf 'w9968cf-vpp' is not present, this parameter is"
277		 " set to 9 (UYVY)."
278		 "\n");
279MODULE_PARM_DESC(force_rgb,
280		 "\n<0|1[,...]> Read RGB video data instead of BGR:"
281		 "\n 1 = use RGB component ordering."
282		 "\n 0 = use BGR component ordering."
283		 "\nThis parameter has effect when using RGBX palettes only."
284		 "\nDefault value is "__MODULE_STRING(W9968CF_FORCE_RGB)
285		 " for every device."
286		 "\n");
287MODULE_PARM_DESC(autobright,
288		 "\n<0|1[,...]> Image sensor automatically changes brightness:"
289		 "\n 0 = no, 1 = yes"
290		 "\nDefault value is "__MODULE_STRING(W9968CF_AUTOBRIGHT)
291		 " for every device."
292		 "\n");
293MODULE_PARM_DESC(autoexp,
294		 "\n<0|1[,...]> Image sensor automatically changes exposure:"
295		 "\n 0 = no, 1 = yes"
296		 "\nDefault value is "__MODULE_STRING(W9968CF_AUTOEXP)
297		 " for every device."
298		 "\n");
299MODULE_PARM_DESC(lightfreq,
300		 "\n<50|60[,...]> Light frequency in Hz:"
301		 "\n 50 for European and Asian lighting,"
302		 " 60 for American lighting."
303		 "\nDefault value is "__MODULE_STRING(W9968CF_LIGHTFREQ)
304		 " for every device."
305		 "\n");
306MODULE_PARM_DESC(bandingfilter,
307		 "\n<0|1[,...]> Banding filter to reduce effects of"
308		 " fluorescent lighting:"
309		 "\n 0 disabled, 1 enabled."
310		 "\nThis filter tries to reduce the pattern of horizontal"
311		 "\nlight/dark bands caused by some (usually fluorescent)"
312		 " lighting."
313		 "\nDefault value is "__MODULE_STRING(W9968CF_BANDINGFILTER)
314		 " for every device."
315		 "\n");
316MODULE_PARM_DESC(clockdiv,
317		 "\n<-1|n[,...]> "
318		 "Force pixel clock divisor to a specific value (for experts):"
319		 "\n  n may vary from 0 to 127."
320		 "\n -1 for automatic value."
321		 "\nSee also the 'double_buffer' module parameter."
322		 "\nDefault value is "__MODULE_STRING(W9968CF_CLOCKDIV)
323		 " for every device."
324		 "\n");
325MODULE_PARM_DESC(backlight,
326		 "\n<0|1[,...]> Objects are lit from behind:"
327		 "\n 0 = no, 1 = yes"
328		 "\nDefault value is "__MODULE_STRING(W9968CF_BACKLIGHT)
329		 " for every device."
330		 "\n");
331MODULE_PARM_DESC(mirror,
332		 "\n<0|1[,...]> Reverse image horizontally:"
333		 "\n 0 = no, 1 = yes"
334		 "\nDefault value is "__MODULE_STRING(W9968CF_MIRROR)
335		 " for every device."
336		 "\n");
337MODULE_PARM_DESC(monochrome,
338		 "\n<0|1[,...]> Use image sensor as monochrome sensor:"
339		 "\n 0 = no, 1 = yes"
340		 "\nNot all the sensors support monochrome color."
341		 "\nDefault value is "__MODULE_STRING(W9968CF_MONOCHROME)
342		 " for every device."
343		 "\n");
344MODULE_PARM_DESC(brightness,
345		 "\n<n[,...]> Set picture brightness (0-65535)."
346		 "\nDefault value is "__MODULE_STRING(W9968CF_BRIGHTNESS)
347		 " for every device."
348		 "\nThis parameter has no effect if 'autobright' is enabled."
349		 "\n");
350MODULE_PARM_DESC(hue,
351		 "\n<n[,...]> Set picture hue (0-65535)."
352		 "\nDefault value is "__MODULE_STRING(W9968CF_HUE)
353		 " for every device."
354		 "\n");
355MODULE_PARM_DESC(colour,
356		 "\n<n[,...]> Set picture saturation (0-65535)."
357		 "\nDefault value is "__MODULE_STRING(W9968CF_COLOUR)
358		 " for every device."
359		 "\n");
360MODULE_PARM_DESC(contrast,
361		 "\n<n[,...]> Set picture contrast (0-65535)."
362		 "\nDefault value is "__MODULE_STRING(W9968CF_CONTRAST)
363		 " for every device."
364		 "\n");
365MODULE_PARM_DESC(whiteness,
366		 "\n<n[,...]> Set picture whiteness (0-65535)."
367		 "\nDefault value is "__MODULE_STRING(W9968CF_WHITENESS)
368		 " for every device."
369		 "\n");
370#ifdef W9968CF_DEBUG
371MODULE_PARM_DESC(debug,
372		 "\n<n> Debugging information level, from 0 to 6:"
373		 "\n0 = none (use carefully)"
374		 "\n1 = critical errors"
375		 "\n2 = significant informations"
376		 "\n3 = configuration or general messages"
377		 "\n4 = warnings"
378		 "\n5 = called functions"
379		 "\n6 = function internals"
380		 "\nLevel 5 and 6 are useful for testing only, when only "
381		 "one device is used."
382		 "\nDefault value is "__MODULE_STRING(W9968CF_DEBUG_LEVEL)"."
383		 "\n");
384MODULE_PARM_DESC(specific_debug,
385		 "\n<0|1> Enable or disable specific debugging messages:"
386		 "\n0 = print messages concerning every level"
387		 " <= 'debug' level."
388		 "\n1 = print messages concerning the level"
389		 " indicated by 'debug'."
390		 "\nDefault value is "
391		 __MODULE_STRING(W9968CF_SPECIFIC_DEBUG)"."
392		 "\n");
393#endif /* W9968CF_DEBUG */
394
395
396
397/****************************************************************************
398 * Some prototypes                                                          *
399 ****************************************************************************/
400
401/* Video4linux interface */
402static const struct file_operations w9968cf_fops;
403static int w9968cf_open(struct inode*, struct file*);
404static int w9968cf_release(struct inode*, struct file*);
405static int w9968cf_mmap(struct file*, struct vm_area_struct*);
406static int w9968cf_ioctl(struct inode*, struct file*, unsigned, unsigned long);
407static ssize_t w9968cf_read(struct file*, char __user *, size_t, loff_t*);
408static int w9968cf_v4l_ioctl(struct inode*, struct file*, unsigned int,
409			     void __user *);
410
411/* USB-specific */
412static int w9968cf_start_transfer(struct w9968cf_device*);
413static int w9968cf_stop_transfer(struct w9968cf_device*);
414static int w9968cf_write_reg(struct w9968cf_device*, u16 value, u16 index);
415static int w9968cf_read_reg(struct w9968cf_device*, u16 index);
416static int w9968cf_write_fsb(struct w9968cf_device*, u16* data);
417static int w9968cf_write_sb(struct w9968cf_device*, u16 value);
418static int w9968cf_read_sb(struct w9968cf_device*);
419static int w9968cf_upload_quantizationtables(struct w9968cf_device*);
420static void w9968cf_urb_complete(struct urb *urb);
421
422/* Low-level I2C (SMBus) I/O */
423static int w9968cf_smbus_start(struct w9968cf_device*);
424static int w9968cf_smbus_stop(struct w9968cf_device*);
425static int w9968cf_smbus_write_byte(struct w9968cf_device*, u8 v);
426static int w9968cf_smbus_read_byte(struct w9968cf_device*, u8* v);
427static int w9968cf_smbus_write_ack(struct w9968cf_device*);
428static int w9968cf_smbus_read_ack(struct w9968cf_device*);
429static int w9968cf_smbus_refresh_bus(struct w9968cf_device*);
430static int w9968cf_i2c_adap_read_byte(struct w9968cf_device* cam,
431				      u16 address, u8* value);
432static int w9968cf_i2c_adap_read_byte_data(struct w9968cf_device*, u16 address,
433					   u8 subaddress, u8* value);
434static int w9968cf_i2c_adap_write_byte(struct w9968cf_device*,
435				       u16 address, u8 subaddress);
436static int w9968cf_i2c_adap_fastwrite_byte_data(struct w9968cf_device*,
437						u16 address, u8 subaddress,
438						u8 value);
439
440/* I2C interface to kernel */
441static int w9968cf_i2c_init(struct w9968cf_device*);
442static int w9968cf_i2c_smbus_xfer(struct i2c_adapter*, u16 addr,
443				  unsigned short flags, char read_write,
444				  u8 command, int size, union i2c_smbus_data*);
445static u32 w9968cf_i2c_func(struct i2c_adapter*);
446static int w9968cf_i2c_attach_inform(struct i2c_client*);
447static int w9968cf_i2c_detach_inform(struct i2c_client*);
448static int w9968cf_i2c_control(struct i2c_adapter*, unsigned int cmd,
449			       unsigned long arg);
450
451/* Memory management */
452static void* rvmalloc(unsigned long size);
453static void rvfree(void *mem, unsigned long size);
454static void w9968cf_deallocate_memory(struct w9968cf_device*);
455static int  w9968cf_allocate_memory(struct w9968cf_device*);
456
457/* High-level image sensor control functions */
458static int w9968cf_sensor_set_control(struct w9968cf_device*,int cid,int val);
459static int w9968cf_sensor_get_control(struct w9968cf_device*,int cid,int *val);
460static int w9968cf_sensor_cmd(struct w9968cf_device*,
461			      unsigned int cmd, void *arg);
462static int w9968cf_sensor_init(struct w9968cf_device*);
463static int w9968cf_sensor_update_settings(struct w9968cf_device*);
464static int w9968cf_sensor_get_picture(struct w9968cf_device*);
465static int w9968cf_sensor_update_picture(struct w9968cf_device*,
466					 struct video_picture pict);
467
468/* Other helper functions */
469static void w9968cf_configure_camera(struct w9968cf_device*,struct usb_device*,
470				     enum w9968cf_model_id,
471				     const unsigned short dev_nr);
472static void w9968cf_adjust_configuration(struct w9968cf_device*);
473static int w9968cf_turn_on_led(struct w9968cf_device*);
474static int w9968cf_init_chip(struct w9968cf_device*);
475static inline u16 w9968cf_valid_palette(u16 palette);
476static inline u16 w9968cf_valid_depth(u16 palette);
477static inline u8 w9968cf_need_decompression(u16 palette);
478static int w9968cf_set_picture(struct w9968cf_device*, struct video_picture);
479static int w9968cf_set_window(struct w9968cf_device*, struct video_window);
480static int w9968cf_postprocess_frame(struct w9968cf_device*,
481				     struct w9968cf_frame_t*);
482static int w9968cf_adjust_window_size(struct w9968cf_device*, u16* w, u16* h);
483static void w9968cf_init_framelist(struct w9968cf_device*);
484static void w9968cf_push_frame(struct w9968cf_device*, u8 f_num);
485static void w9968cf_pop_frame(struct w9968cf_device*,struct w9968cf_frame_t**);
486static void w9968cf_release_resources(struct w9968cf_device*);
487
488
489
490/****************************************************************************
491 * Symbolic names                                                           *
492 ****************************************************************************/
493
494/* Used to represent a list of values and their respective symbolic names */
495struct w9968cf_symbolic_list {
496	const int num;
497	const char *name;
498};
499
500/*--------------------------------------------------------------------------
501  Returns the name of the matching element in the symbolic_list array. The
502  end of the list must be marked with an element that has a NULL name.
503  --------------------------------------------------------------------------*/
504static inline const char *
505symbolic(struct w9968cf_symbolic_list list[], const int num)
506{
507	int i;
508
509	for (i = 0; list[i].name != NULL; i++)
510		if (list[i].num == num)
511			return (list[i].name);
512
513	return "Unknown";
514}
515
516static struct w9968cf_symbolic_list camlist[] = {
517	{ W9968CF_MOD_GENERIC, "W996[87]CF JPEG USB Dual Mode Camera" },
518	{ W9968CF_MOD_CLVBWGP, "Creative Labs Video Blaster WebCam Go Plus" },
519
520	/* Other cameras (having the same descriptors as Generic W996[87]CF) */
521	{ W9968CF_MOD_ADPVDMA, "Aroma Digi Pen VGA Dual Mode ADG-5000" },
522	{ W9986CF_MOD_AAU, "AVerMedia AVerTV USB" },
523	{ W9968CF_MOD_CLVBWG, "Creative Labs Video Blaster WebCam Go" },
524	{ W9968CF_MOD_LL, "Lebon LDC-035A" },
525	{ W9968CF_MOD_EEEMC, "Ezonics EZ-802 EZMega Cam" },
526	{ W9968CF_MOD_OOE, "OmniVision OV8610-EDE" },
527	{ W9968CF_MOD_ODPVDMPC, "OPCOM Digi Pen VGA Dual Mode Pen Camera" },
528	{ W9968CF_MOD_PDPII, "Pretec Digi Pen-II" },
529	{ W9968CF_MOD_PDP480, "Pretec DigiPen-480" },
530
531	{  -1, NULL }
532};
533
534static struct w9968cf_symbolic_list senlist[] = {
535	{ CC_OV76BE,   "OV76BE" },
536	{ CC_OV7610,   "OV7610" },
537	{ CC_OV7620,   "OV7620" },
538	{ CC_OV7620AE, "OV7620AE" },
539	{ CC_OV6620,   "OV6620" },
540	{ CC_OV6630,   "OV6630" },
541	{ CC_OV6630AE, "OV6630AE" },
542	{ CC_OV6630AF, "OV6630AF" },
543	{ -1, NULL }
544};
545
546/* Video4Linux1 palettes */
547static struct w9968cf_symbolic_list v4l1_plist[] = {
548	{ VIDEO_PALETTE_GREY,    "GREY" },
549	{ VIDEO_PALETTE_HI240,   "HI240" },
550	{ VIDEO_PALETTE_RGB565,  "RGB565" },
551	{ VIDEO_PALETTE_RGB24,   "RGB24" },
552	{ VIDEO_PALETTE_RGB32,   "RGB32" },
553	{ VIDEO_PALETTE_RGB555,  "RGB555" },
554	{ VIDEO_PALETTE_YUV422,  "YUV422" },
555	{ VIDEO_PALETTE_YUYV,    "YUYV" },
556	{ VIDEO_PALETTE_UYVY,    "UYVY" },
557	{ VIDEO_PALETTE_YUV420,  "YUV420" },
558	{ VIDEO_PALETTE_YUV411,  "YUV411" },
559	{ VIDEO_PALETTE_RAW,     "RAW" },
560	{ VIDEO_PALETTE_YUV422P, "YUV422P" },
561	{ VIDEO_PALETTE_YUV411P, "YUV411P" },
562	{ VIDEO_PALETTE_YUV420P, "YUV420P" },
563	{ VIDEO_PALETTE_YUV410P, "YUV410P" },
564	{ -1, NULL }
565};
566
567/* Decoder error codes: */
568static struct w9968cf_symbolic_list decoder_errlist[] = {
569	{ W9968CF_DEC_ERR_CORRUPTED_DATA, "Corrupted data" },
570	{ W9968CF_DEC_ERR_BUF_OVERFLOW,   "Buffer overflow" },
571	{ W9968CF_DEC_ERR_NO_SOI,         "SOI marker not found" },
572	{ W9968CF_DEC_ERR_NO_SOF0,        "SOF0 marker not found" },
573	{ W9968CF_DEC_ERR_NO_SOS,         "SOS marker not found" },
574	{ W9968CF_DEC_ERR_NO_EOI,         "EOI marker not found" },
575	{ -1, NULL }
576};
577
578/* URB error codes: */
579static struct w9968cf_symbolic_list urb_errlist[] = {
580	{ -ENOMEM,    "No memory for allocation of internal structures" },
581	{ -ENOSPC,    "The host controller's bandwidth is already consumed" },
582	{ -ENOENT,    "URB was canceled by unlink_urb" },
583	{ -EXDEV,     "ISO transfer only partially completed" },
584	{ -EAGAIN,    "Too match scheduled for the future" },
585	{ -ENXIO,     "URB already queued" },
586	{ -EFBIG,     "Too much ISO frames requested" },
587	{ -ENOSR,     "Buffer error (overrun)" },
588	{ -EPIPE,     "Specified endpoint is stalled (device not responding)"},
589	{ -EOVERFLOW, "Babble (too much data)" },
590	{ -EPROTO,    "Bit-stuff error (bad cable?)" },
591	{ -EILSEQ,    "CRC/Timeout" },
592	{ -ETIME,     "Device does not respond to token" },
593	{ -ETIMEDOUT, "Device does not respond to command" },
594	{ -1, NULL }
595};
596
597/****************************************************************************
598 * Memory management functions                                              *
599 ****************************************************************************/
600static void* rvmalloc(unsigned long size)
601{
602	void* mem;
603	unsigned long adr;
604
605	size = PAGE_ALIGN(size);
606	mem = vmalloc_32(size);
607	if (!mem)
608		return NULL;
609
610	memset(mem, 0, size); /* Clear the ram out, no junk to the user */
611	adr = (unsigned long) mem;
612	while (size > 0) {
613		SetPageReserved(vmalloc_to_page((void *)adr));
614		adr += PAGE_SIZE;
615		size -= PAGE_SIZE;
616	}
617
618	return mem;
619}
620
621
622static void rvfree(void* mem, unsigned long size)
623{
624	unsigned long adr;
625
626	if (!mem)
627		return;
628
629	adr = (unsigned long) mem;
630	while ((long) size > 0) {
631		ClearPageReserved(vmalloc_to_page((void *)adr));
632		adr += PAGE_SIZE;
633		size -= PAGE_SIZE;
634	}
635	vfree(mem);
636}
637
638
639/*--------------------------------------------------------------------------
640  Deallocate previously allocated memory.
641  --------------------------------------------------------------------------*/
642static void w9968cf_deallocate_memory(struct w9968cf_device* cam)
643{
644	u8 i;
645
646	/* Free the isochronous transfer buffers */
647	for (i = 0; i < W9968CF_URBS; i++) {
648		kfree(cam->transfer_buffer[i]);
649		cam->transfer_buffer[i] = NULL;
650	}
651
652	/* Free temporary frame buffer */
653	if (cam->frame_tmp.buffer) {
654		rvfree(cam->frame_tmp.buffer, cam->frame_tmp.size);
655		cam->frame_tmp.buffer = NULL;
656	}
657
658	/* Free helper buffer */
659	if (cam->frame_vpp.buffer) {
660		rvfree(cam->frame_vpp.buffer, cam->frame_vpp.size);
661		cam->frame_vpp.buffer = NULL;
662	}
663
664	/* Free video frame buffers */
665	if (cam->frame[0].buffer) {
666		rvfree(cam->frame[0].buffer, cam->nbuffers*cam->frame[0].size);
667		cam->frame[0].buffer = NULL;
668	}
669
670	cam->nbuffers = 0;
671
672	DBG(5, "Memory successfully deallocated")
673}
674
675
676/*--------------------------------------------------------------------------
677  Allocate memory buffers for USB transfers and video frames.
678  This function is called by open() only.
679  Return 0 on success, a negative number otherwise.
680  --------------------------------------------------------------------------*/
681static int w9968cf_allocate_memory(struct w9968cf_device* cam)
682{
683	const u16 p_size = wMaxPacketSize[cam->altsetting-1];
684	void* buff = NULL;
685	unsigned long hw_bufsize, vpp_bufsize;
686	u8 i, bpp;
687
688	/* NOTE: Deallocation is done elsewhere in case of error */
689
690	/* Calculate the max amount of raw data per frame from the device */
691	hw_bufsize = cam->maxwidth*cam->maxheight*2;
692
693	/* Calculate the max buf. size needed for post-processing routines */
694	bpp = (w9968cf_vpp) ? 4 : 2;
695	if (cam->upscaling)
696		vpp_bufsize = max(W9968CF_MAX_WIDTH*W9968CF_MAX_HEIGHT*bpp,
697				  cam->maxwidth*cam->maxheight*bpp);
698	else
699		vpp_bufsize = cam->maxwidth*cam->maxheight*bpp;
700
701	/* Allocate memory for the isochronous transfer buffers */
702	for (i = 0; i < W9968CF_URBS; i++) {
703		if (!(cam->transfer_buffer[i] =
704		      kzalloc(W9968CF_ISO_PACKETS*p_size, GFP_KERNEL))) {
705			DBG(1, "Couldn't allocate memory for the isochronous "
706			       "transfer buffers (%u bytes)",
707			    p_size * W9968CF_ISO_PACKETS)
708			return -ENOMEM;
709		}
710	}
711
712	/* Allocate memory for the temporary frame buffer */
713	if (!(cam->frame_tmp.buffer = rvmalloc(hw_bufsize))) {
714		DBG(1, "Couldn't allocate memory for the temporary "
715		       "video frame buffer (%lu bytes)", hw_bufsize)
716		return -ENOMEM;
717	}
718	cam->frame_tmp.size = hw_bufsize;
719	cam->frame_tmp.number = -1;
720
721	/* Allocate memory for the helper buffer */
722	if (w9968cf_vpp) {
723		if (!(cam->frame_vpp.buffer = rvmalloc(vpp_bufsize))) {
724			DBG(1, "Couldn't allocate memory for the helper buffer"
725			       " (%lu bytes)", vpp_bufsize)
726			return -ENOMEM;
727		}
728		cam->frame_vpp.size = vpp_bufsize;
729	} else
730		cam->frame_vpp.buffer = NULL;
731
732	/* Allocate memory for video frame buffers */
733	cam->nbuffers = cam->max_buffers;
734	while (cam->nbuffers >= 2) {
735		if ((buff = rvmalloc(cam->nbuffers * vpp_bufsize)))
736			break;
737		else
738			cam->nbuffers--;
739	}
740
741	if (!buff) {
742		DBG(1, "Couldn't allocate memory for the video frame buffers")
743		cam->nbuffers = 0;
744		return -ENOMEM;
745	}
746
747	if (cam->nbuffers != cam->max_buffers)
748		DBG(2, "Couldn't allocate memory for %u video frame buffers. "
749		       "Only memory for %u buffers has been allocated",
750		    cam->max_buffers, cam->nbuffers)
751
752	for (i = 0; i < cam->nbuffers; i++) {
753		cam->frame[i].buffer = buff + i*vpp_bufsize;
754		cam->frame[i].size = vpp_bufsize;
755		cam->frame[i].number = i;
756		/* Circular list */
757		if (i != cam->nbuffers-1)
758			cam->frame[i].next = &cam->frame[i+1];
759		else
760			cam->frame[i].next = &cam->frame[0];
761		cam->frame[i].status = F_UNUSED;
762	}
763
764	DBG(5, "Memory successfully allocated")
765	return 0;
766}
767
768
769
770/****************************************************************************
771 * USB-specific functions                                                   *
772 ****************************************************************************/
773
774/*--------------------------------------------------------------------------
775  This is an handler function which is called after the URBs are completed.
776  It collects multiple data packets coming from the camera by putting them
777  into frame buffers: one or more zero data length data packets are used to
778  mark the end of a video frame; the first non-zero data packet is the start
779  of the next video frame; if an error is encountered in a packet, the entire
780  video frame is discarded and grabbed again.
781  If there are no requested frames in the FIFO list, packets are collected into
782  a temporary buffer.
783  --------------------------------------------------------------------------*/
784static void w9968cf_urb_complete(struct urb *urb)
785{
786	struct w9968cf_device* cam = (struct w9968cf_device*)urb->context;
787	struct w9968cf_frame_t** f;
788	unsigned int len, status;
789	void* pos;
790	u8 i;
791	int err = 0;
792
793	if ((!cam->streaming) || cam->disconnected) {
794		DBG(4, "Got interrupt, but not streaming")
795		return;
796	}
797
798	/* "(*f)" will be used instead of "cam->frame_current" */
799	f = &cam->frame_current;
800
801	/* If a frame has been requested and we are grabbing into
802	   the temporary frame, we'll switch to that requested frame */
803	if ((*f) == &cam->frame_tmp && *cam->requested_frame) {
804		if (cam->frame_tmp.status == F_GRABBING) {
805			w9968cf_pop_frame(cam, &cam->frame_current);
806			(*f)->status = F_GRABBING;
807			(*f)->length = cam->frame_tmp.length;
808			memcpy((*f)->buffer, cam->frame_tmp.buffer,
809			       (*f)->length);
810			DBG(6, "Switched from temp. frame to frame #%d",
811			    (*f)->number)
812		}
813	}
814
815	for (i = 0; i < urb->number_of_packets; i++) {
816		len = urb->iso_frame_desc[i].actual_length;
817		status = urb->iso_frame_desc[i].status;
818		pos = urb->iso_frame_desc[i].offset + urb->transfer_buffer;
819
820		if (status && len != 0) {
821			DBG(4, "URB failed, error in data packet "
822			       "(error #%u, %s)",
823			    status, symbolic(urb_errlist, status))
824			(*f)->status = F_ERROR;
825			continue;
826		}
827
828		if (len) { /* start of frame */
829
830			if ((*f)->status == F_UNUSED) {
831				(*f)->status = F_GRABBING;
832				(*f)->length = 0;
833			}
834
835			/* Buffer overflows shouldn't happen, however...*/
836			if ((*f)->length + len > (*f)->size) {
837				DBG(4, "Buffer overflow: bad data packets")
838				(*f)->status = F_ERROR;
839			}
840
841			if ((*f)->status == F_GRABBING) {
842				memcpy((*f)->buffer + (*f)->length, pos, len);
843				(*f)->length += len;
844			}
845
846		} else if ((*f)->status == F_GRABBING) { /* end of frame */
847
848			DBG(6, "Frame #%d successfully grabbed", (*f)->number)
849
850			if (cam->vpp_flag & VPP_DECOMPRESSION) {
851				err = w9968cf_vpp->check_headers((*f)->buffer,
852								 (*f)->length);
853				if (err) {
854					DBG(4, "Skip corrupted frame: %s",
855					    symbolic(decoder_errlist, err))
856					(*f)->status = F_UNUSED;
857					continue; /* grab this frame again */
858				}
859			}
860
861			(*f)->status = F_READY;
862			(*f)->queued = 0;
863
864			/* Take a pointer to the new frame from the FIFO list.
865			   If the list is empty,we'll use the temporary frame*/
866			if (*cam->requested_frame)
867				w9968cf_pop_frame(cam, &cam->frame_current);
868			else {
869				cam->frame_current = &cam->frame_tmp;
870				(*f)->status = F_UNUSED;
871			}
872
873		} else if ((*f)->status == F_ERROR)
874			(*f)->status = F_UNUSED; /* grab it again */
875
876		PDBGG("Frame length %lu | pack.#%u | pack.len. %u | state %d",
877		      (unsigned long)(*f)->length, i, len, (*f)->status)
878
879	} /* end for */
880
881	/* Resubmit this URB */
882	urb->dev = cam->usbdev;
883	urb->status = 0;
884	spin_lock(&cam->urb_lock);
885	if (cam->streaming)
886		if ((err = usb_submit_urb(urb, GFP_ATOMIC))) {
887			cam->misconfigured = 1;
888			DBG(1, "Couldn't resubmit the URB: error %d, %s",
889			    err, symbolic(urb_errlist, err))
890		}
891	spin_unlock(&cam->urb_lock);
892
893	/* Wake up the user process */
894	wake_up_interruptible(&cam->wait_queue);
895}
896
897
898/*---------------------------------------------------------------------------
899  Setup the URB structures for the isochronous transfer.
900  Submit the URBs so that the data transfer begins.
901  Return 0 on success, a negative number otherwise.
902  ---------------------------------------------------------------------------*/
903static int w9968cf_start_transfer(struct w9968cf_device* cam)
904{
905	struct usb_device *udev = cam->usbdev;
906	struct urb* urb;
907	const u16 p_size = wMaxPacketSize[cam->altsetting-1];
908	u16 w, h, d;
909	int vidcapt;
910	u32 t_size;
911	int err = 0;
912	s8 i, j;
913
914	for (i = 0; i < W9968CF_URBS; i++) {
915		urb = usb_alloc_urb(W9968CF_ISO_PACKETS, GFP_KERNEL);
916		cam->urb[i] = urb;
917		if (!urb) {
918			for (j = 0; j < i; j++)
919				usb_free_urb(cam->urb[j]);
920			DBG(1, "Couldn't allocate the URB structures")
921			return -ENOMEM;
922		}
923
924		urb->dev = udev;
925		urb->context = (void*)cam;
926		urb->pipe = usb_rcvisocpipe(udev, 1);
927		urb->transfer_flags = URB_ISO_ASAP;
928		urb->number_of_packets = W9968CF_ISO_PACKETS;
929		urb->complete = w9968cf_urb_complete;
930		urb->transfer_buffer = cam->transfer_buffer[i];
931		urb->transfer_buffer_length = p_size*W9968CF_ISO_PACKETS;
932		urb->interval = 1;
933		for (j = 0; j < W9968CF_ISO_PACKETS; j++) {
934			urb->iso_frame_desc[j].offset = p_size*j;
935			urb->iso_frame_desc[j].length = p_size;
936		}
937	}
938
939	/* Transfer size per frame, in WORD ! */
940	d = cam->hw_depth;
941	w = cam->hw_width;
942	h = cam->hw_height;
943
944	t_size = (w*h*d)/16;
945
946	err = w9968cf_write_reg(cam, 0xbf17, 0x00); /* reset everything */
947	err += w9968cf_write_reg(cam, 0xbf10, 0x00); /* normal operation */
948
949	/* Transfer size */
950	err += w9968cf_write_reg(cam, t_size & 0xffff, 0x3d); /* low bits */
951	err += w9968cf_write_reg(cam, t_size >> 16, 0x3e);    /* high bits */
952
953	if (cam->vpp_flag & VPP_DECOMPRESSION)
954		err += w9968cf_upload_quantizationtables(cam);
955
956	vidcapt = w9968cf_read_reg(cam, 0x16); /* read picture settings */
957	err += w9968cf_write_reg(cam, vidcapt|0x8000, 0x16); /* capt. enable */
958
959	err += usb_set_interface(udev, 0, cam->altsetting);
960	err += w9968cf_write_reg(cam, 0x8a05, 0x3c); /* USB FIFO enable */
961
962	if (err || (vidcapt < 0)) {
963		for (i = 0; i < W9968CF_URBS; i++)
964			usb_free_urb(cam->urb[i]);
965		DBG(1, "Couldn't tell the camera to start the data transfer")
966		return err;
967	}
968
969	w9968cf_init_framelist(cam);
970
971	/* Begin to grab into the temporary buffer */
972	cam->frame_tmp.status = F_UNUSED;
973	cam->frame_tmp.queued = 0;
974	cam->frame_current = &cam->frame_tmp;
975
976	if (!(cam->vpp_flag & VPP_DECOMPRESSION))
977		DBG(5, "Isochronous transfer size: %lu bytes/frame",
978		    (unsigned long)t_size*2)
979
980	DBG(5, "Starting the isochronous transfer...")
981
982	cam->streaming = 1;
983
984	/* Submit the URBs */
985	for (i = 0; i < W9968CF_URBS; i++) {
986		err = usb_submit_urb(cam->urb[i], GFP_KERNEL);
987		if (err) {
988			cam->streaming = 0;
989			for (j = i-1; j >= 0; j--) {
990				usb_kill_urb(cam->urb[j]);
991				usb_free_urb(cam->urb[j]);
992			}
993			DBG(1, "Couldn't send a transfer request to the "
994			       "USB core (error #%d, %s)", err,
995			    symbolic(urb_errlist, err))
996			return err;
997		}
998	}
999
1000	return 0;
1001}
1002
1003
1004/*--------------------------------------------------------------------------
1005  Stop the isochronous transfer and set alternate setting to 0 (0Mb/s).
1006  Return 0 on success, a negative number otherwise.
1007  --------------------------------------------------------------------------*/
1008static int w9968cf_stop_transfer(struct w9968cf_device* cam)
1009{
1010	struct usb_device *udev = cam->usbdev;
1011	unsigned long lock_flags;
1012	int err = 0;
1013	s8 i;
1014
1015	if (!cam->streaming)
1016		return 0;
1017
1018	/* This avoids race conditions with usb_submit_urb()
1019	   in the URB completition handler */
1020	spin_lock_irqsave(&cam->urb_lock, lock_flags);
1021	cam->streaming = 0;
1022	spin_unlock_irqrestore(&cam->urb_lock, lock_flags);
1023
1024	for (i = W9968CF_URBS-1; i >= 0; i--)
1025		if (cam->urb[i]) {
1026			usb_kill_urb(cam->urb[i]);
1027			usb_free_urb(cam->urb[i]);
1028			cam->urb[i] = NULL;
1029		}
1030
1031	if (cam->disconnected)
1032		goto exit;
1033
1034	err = w9968cf_write_reg(cam, 0x0a05, 0x3c); /* stop USB transfer */
1035	err += usb_set_interface(udev, 0, 0); /* 0 Mb/s */
1036	err += w9968cf_write_reg(cam, 0x0000, 0x39); /* disable JPEG encoder */
1037	err += w9968cf_write_reg(cam, 0x0000, 0x16); /* stop video capture */
1038
1039	if (err) {
1040		DBG(2, "Failed to tell the camera to stop the isochronous "
1041		       "transfer. However this is not a critical error.")
1042		return -EIO;
1043	}
1044
1045exit:
1046	DBG(5, "Isochronous transfer stopped")
1047	return 0;
1048}
1049
1050
1051/*--------------------------------------------------------------------------
1052  Write a W9968CF register.
1053  Return 0 on success, -1 otherwise.
1054  --------------------------------------------------------------------------*/
1055static int w9968cf_write_reg(struct w9968cf_device* cam, u16 value, u16 index)
1056{
1057	struct usb_device* udev = cam->usbdev;
1058	int res;
1059
1060	res = usb_control_msg(udev, usb_sndctrlpipe(udev, 0), 0,
1061			      USB_TYPE_VENDOR | USB_DIR_OUT | USB_RECIP_DEVICE,
1062			      value, index, NULL, 0, W9968CF_USB_CTRL_TIMEOUT);
1063
1064	if (res < 0)
1065		DBG(4, "Failed to write a register "
1066		       "(value 0x%04X, index 0x%02X, error #%d, %s)",
1067		    value, index, res, symbolic(urb_errlist, res))
1068
1069	return (res >= 0) ? 0 : -1;
1070}
1071
1072
1073/*--------------------------------------------------------------------------
1074  Read a W9968CF register.
1075  Return the register value on success, -1 otherwise.
1076  --------------------------------------------------------------------------*/
1077static int w9968cf_read_reg(struct w9968cf_device* cam, u16 index)
1078{
1079	struct usb_device* udev = cam->usbdev;
1080	u16* buff = cam->control_buffer;
1081	int res;
1082
1083	res = usb_control_msg(udev, usb_rcvctrlpipe(udev, 0), 1,
1084			      USB_DIR_IN | USB_TYPE_VENDOR | USB_RECIP_DEVICE,
1085			      0, index, buff, 2, W9968CF_USB_CTRL_TIMEOUT);
1086
1087	if (res < 0)
1088		DBG(4, "Failed to read a register "
1089		       "(index 0x%02X, error #%d, %s)",
1090		    index, res, symbolic(urb_errlist, res))
1091
1092	return (res >= 0) ? (int)(*buff) : -1;
1093}
1094
1095
1096/*--------------------------------------------------------------------------
1097  Write 64-bit data to the fast serial bus registers.
1098  Return 0 on success, -1 otherwise.
1099  --------------------------------------------------------------------------*/
1100static int w9968cf_write_fsb(struct w9968cf_device* cam, u16* data)
1101{
1102	struct usb_device* udev = cam->usbdev;
1103	u16 value;
1104	int res;
1105
1106	value = *data++;
1107
1108	res = usb_control_msg(udev, usb_sndctrlpipe(udev, 0), 0,
1109			      USB_TYPE_VENDOR | USB_DIR_OUT | USB_RECIP_DEVICE,
1110			      value, 0x06, data, 6, W9968CF_USB_CTRL_TIMEOUT);
1111
1112	if (res < 0)
1113		DBG(4, "Failed to write the FSB registers "
1114		       "(error #%d, %s)", res, symbolic(urb_errlist, res))
1115
1116	return (res >= 0) ? 0 : -1;
1117}
1118
1119
1120/*--------------------------------------------------------------------------
1121  Write data to the serial bus control register.
1122  Return 0 on success, a negative number otherwise.
1123  --------------------------------------------------------------------------*/
1124static int w9968cf_write_sb(struct w9968cf_device* cam, u16 value)
1125{
1126	int err = 0;
1127
1128	err = w9968cf_write_reg(cam, value, 0x01);
1129	udelay(W9968CF_I2C_BUS_DELAY);
1130
1131	return err;
1132}
1133
1134
1135/*--------------------------------------------------------------------------
1136  Read data from the serial bus control register.
1137  Return 0 on success, a negative number otherwise.
1138  --------------------------------------------------------------------------*/
1139static int w9968cf_read_sb(struct w9968cf_device* cam)
1140{
1141	int v = 0;
1142
1143	v = w9968cf_read_reg(cam, 0x01);
1144	udelay(W9968CF_I2C_BUS_DELAY);
1145
1146	return v;
1147}
1148
1149
1150/*--------------------------------------------------------------------------
1151  Upload quantization tables for the JPEG compression.
1152  This function is called by w9968cf_start_transfer().
1153  Return 0 on success, a negative number otherwise.
1154  --------------------------------------------------------------------------*/
1155static int w9968cf_upload_quantizationtables(struct w9968cf_device* cam)
1156{
1157	u16 a, b;
1158	int err = 0, i, j;
1159
1160	err += w9968cf_write_reg(cam, 0x0010, 0x39); /* JPEG clock enable */
1161
1162	for (i = 0, j = 0; i < 32; i++, j += 2) {
1163		a = Y_QUANTABLE[j] | ((unsigned)(Y_QUANTABLE[j+1]) << 8);
1164		b = UV_QUANTABLE[j] | ((unsigned)(UV_QUANTABLE[j+1]) << 8);
1165		err += w9968cf_write_reg(cam, a, 0x40+i);
1166		err += w9968cf_write_reg(cam, b, 0x60+i);
1167	}
1168	err += w9968cf_write_reg(cam, 0x0012, 0x39); /* JPEG encoder enable */
1169
1170	return err;
1171}
1172
1173
1174
1175/****************************************************************************
1176 * Low-level I2C I/O functions.                                             *
1177 * The adapter supports the following I2C transfer functions:               *
1178 * i2c_adap_fastwrite_byte_data() (at 400 kHz bit frequency only)           *
1179 * i2c_adap_read_byte_data()                                                *
1180 * i2c_adap_read_byte()                                                     *
1181 ****************************************************************************/
1182
1183static int w9968cf_smbus_start(struct w9968cf_device* cam)
1184{
1185	int err = 0;
1186
1187	err += w9968cf_write_sb(cam, 0x0011); /* SDE=1, SDA=0, SCL=1 */
1188	err += w9968cf_write_sb(cam, 0x0010); /* SDE=1, SDA=0, SCL=0 */
1189
1190	return err;
1191}
1192
1193
1194static int w9968cf_smbus_stop(struct w9968cf_device* cam)
1195{
1196	int err = 0;
1197
1198	err += w9968cf_write_sb(cam, 0x0011); /* SDE=1, SDA=0, SCL=1 */
1199	err += w9968cf_write_sb(cam, 0x0013); /* SDE=1, SDA=1, SCL=1 */
1200
1201	return err;
1202}
1203
1204
1205static int w9968cf_smbus_write_byte(struct w9968cf_device* cam, u8 v)
1206{
1207	u8 bit;
1208	int err = 0, sda;
1209
1210	for (bit = 0 ; bit < 8 ; bit++) {
1211		sda = (v & 0x80) ? 2 : 0;
1212		v <<= 1;
1213		/* SDE=1, SDA=sda, SCL=0 */
1214		err += w9968cf_write_sb(cam, 0x10 | sda);
1215		/* SDE=1, SDA=sda, SCL=1 */
1216		err += w9968cf_write_sb(cam, 0x11 | sda);
1217		/* SDE=1, SDA=sda, SCL=0 */
1218		err += w9968cf_write_sb(cam, 0x10 | sda);
1219	}
1220
1221	return err;
1222}
1223
1224
1225static int w9968cf_smbus_read_byte(struct w9968cf_device* cam, u8* v)
1226{
1227	u8 bit;
1228	int err = 0;
1229
1230	*v = 0;
1231	for (bit = 0 ; bit < 8 ; bit++) {
1232		*v <<= 1;
1233		err += w9968cf_write_sb(cam, 0x0013);
1234		*v |= (w9968cf_read_sb(cam) & 0x0008) ? 1 : 0;
1235		err += w9968cf_write_sb(cam, 0x0012);
1236	}
1237
1238	return err;
1239}
1240
1241
1242static int w9968cf_smbus_write_ack(struct w9968cf_device* cam)
1243{
1244	int err = 0;
1245
1246	err += w9968cf_write_sb(cam, 0x0010); /* SDE=1, SDA=0, SCL=0 */
1247	err += w9968cf_write_sb(cam, 0x0011); /* SDE=1, SDA=0, SCL=1 */
1248	err += w9968cf_write_sb(cam, 0x0010); /* SDE=1, SDA=0, SCL=0 */
1249
1250	return err;
1251}
1252
1253
1254static int w9968cf_smbus_read_ack(struct w9968cf_device* cam)
1255{
1256	int err = 0, sda;
1257
1258	err += w9968cf_write_sb(cam, 0x0013); /* SDE=1, SDA=1, SCL=1 */
1259	sda = (w9968cf_read_sb(cam) & 0x08) ? 1 : 0; /* sda = SDA */
1260	err += w9968cf_write_sb(cam, 0x0012); /* SDE=1, SDA=1, SCL=0 */
1261	if (sda < 0)
1262		err += sda;
1263	if (sda == 1) {
1264		DBG(6, "Couldn't receive the ACK")
1265		err += -1;
1266	}
1267
1268	return err;
1269}
1270
1271
1272/* This seems to refresh the communication through the serial bus */
1273static int w9968cf_smbus_refresh_bus(struct w9968cf_device* cam)
1274{
1275	int err = 0, j;
1276
1277	for (j = 1; j <= 10; j++) {
1278		err = w9968cf_write_reg(cam, 0x0020, 0x01);
1279		err += w9968cf_write_reg(cam, 0x0000, 0x01);
1280		if (err)
1281			break;
1282	}
1283
1284	return err;
1285}
1286
1287
1288/* SMBus protocol: S Addr Wr [A] Subaddr [A] Value [A] P */
1289static int
1290w9968cf_i2c_adap_fastwrite_byte_data(struct w9968cf_device* cam,
1291				     u16 address, u8 subaddress,u8 value)
1292{
1293	u16* data = cam->data_buffer;
1294	int err = 0;
1295
1296	err += w9968cf_smbus_refresh_bus(cam);
1297
1298	/* Enable SBUS outputs */
1299	err += w9968cf_write_sb(cam, 0x0020);
1300
1301	data[0] = 0x082f | ((address & 0x80) ? 0x1500 : 0x0);
1302	data[0] |= (address & 0x40) ? 0x4000 : 0x0;
1303	data[1] = 0x2082 | ((address & 0x40) ? 0x0005 : 0x0);
1304	data[1] |= (address & 0x20) ? 0x0150 : 0x0;
1305	data[1] |= (address & 0x10) ? 0x5400 : 0x0;
1306	data[2] = 0x8208 | ((address & 0x08) ? 0x0015 : 0x0);
1307	data[2] |= (address & 0x04) ? 0x0540 : 0x0;
1308	data[2] |= (address & 0x02) ? 0x5000 : 0x0;
1309	data[3] = 0x1d20 | ((address & 0x02) ? 0x0001 : 0x0);
1310	data[3] |= (address & 0x01) ? 0x0054 : 0x0;
1311
1312	err += w9968cf_write_fsb(cam, data);
1313
1314	data[0] = 0x8208 | ((subaddress & 0x80) ? 0x0015 : 0x0);
1315	data[0] |= (subaddress & 0x40) ? 0x0540 : 0x0;
1316	data[0] |= (subaddress & 0x20) ? 0x5000 : 0x0;
1317	data[1] = 0x0820 | ((subaddress & 0x20) ? 0x0001 : 0x0);
1318	data[1] |= (subaddress & 0x10) ? 0x0054 : 0x0;
1319	data[1] |= (subaddress & 0x08) ? 0x1500 : 0x0;
1320	data[1] |= (subaddress & 0x04) ? 0x4000 : 0x0;
1321	data[2] = 0x2082 | ((subaddress & 0x04) ? 0x0005 : 0x0);
1322	data[2] |= (subaddress & 0x02) ? 0x0150 : 0x0;
1323	data[2] |= (subaddress & 0x01) ? 0x5400 : 0x0;
1324	data[3] = 0x001d;
1325
1326	err += w9968cf_write_fsb(cam, data);
1327
1328	data[0] = 0x8208 | ((value & 0x80) ? 0x0015 : 0x0);
1329	data[0] |= (value & 0x40) ? 0x0540 : 0x0;
1330	data[0] |= (value & 0x20) ? 0x5000 : 0x0;
1331	data[1] = 0x0820 | ((value & 0x20) ? 0x0001 : 0x0);
1332	data[1] |= (value & 0x10) ? 0x0054 : 0x0;
1333	data[1] |= (value & 0x08) ? 0x1500 : 0x0;
1334	data[1] |= (value & 0x04) ? 0x4000 : 0x0;
1335	data[2] = 0x2082 | ((value & 0x04) ? 0x0005 : 0x0);
1336	data[2] |= (value & 0x02) ? 0x0150 : 0x0;
1337	data[2] |= (value & 0x01) ? 0x5400 : 0x0;
1338	data[3] = 0xfe1d;
1339
1340	err += w9968cf_write_fsb(cam, data);
1341
1342	/* Disable SBUS outputs */
1343	err += w9968cf_write_sb(cam, 0x0000);
1344
1345	if (!err)
1346		DBG(5, "I2C write byte data done, addr.0x%04X, subaddr.0x%02X "
1347		       "value 0x%02X", address, subaddress, value)
1348	else
1349		DBG(5, "I2C write byte data failed, addr.0x%04X, "
1350		       "subaddr.0x%02X, value 0x%02X",
1351		    address, subaddress, value)
1352
1353	return err;
1354}
1355
1356
1357/* SMBus protocol: S Addr Wr [A] Subaddr [A] P S Addr+1 Rd [A] [Value] NA P */
1358static int
1359w9968cf_i2c_adap_read_byte_data(struct w9968cf_device* cam,
1360				u16 address, u8 subaddress,
1361				u8* value)
1362{
1363	int err = 0;
1364
1365	/* Serial data enable */
1366	err += w9968cf_write_sb(cam, 0x0013); /* don't change ! */
1367
1368	err += w9968cf_smbus_start(cam);
1369	err += w9968cf_smbus_write_byte(cam, address);
1370	err += w9968cf_smbus_read_ack(cam);
1371	err += w9968cf_smbus_write_byte(cam, subaddress);
1372	err += w9968cf_smbus_read_ack(cam);
1373	err += w9968cf_smbus_stop(cam);
1374	err += w9968cf_smbus_start(cam);
1375	err += w9968cf_smbus_write_byte(cam, address + 1);
1376	err += w9968cf_smbus_read_ack(cam);
1377	err += w9968cf_smbus_read_byte(cam, value);
1378	err += w9968cf_smbus_write_ack(cam);
1379	err += w9968cf_smbus_stop(cam);
1380
1381	/* Serial data disable */
1382	err += w9968cf_write_sb(cam, 0x0000);
1383
1384	if (!err)
1385		DBG(5, "I2C read byte data done, addr.0x%04X, "
1386		       "subaddr.0x%02X, value 0x%02X",
1387		    address, subaddress, *value)
1388	else
1389		DBG(5, "I2C read byte data failed, addr.0x%04X, "
1390		       "subaddr.0x%02X, wrong value 0x%02X",
1391		    address, subaddress, *value)
1392
1393	return err;
1394}
1395
1396
1397/* SMBus protocol: S Addr+1 Rd [A] [Value] NA P */
1398static int
1399w9968cf_i2c_adap_read_byte(struct w9968cf_device* cam,
1400			   u16 address, u8* value)
1401{
1402	int err = 0;
1403
1404	/* Serial data enable */
1405	err += w9968cf_write_sb(cam, 0x0013);
1406
1407	err += w9968cf_smbus_start(cam);
1408	err += w9968cf_smbus_write_byte(cam, address + 1);
1409	err += w9968cf_smbus_read_ack(cam);
1410	err += w9968cf_smbus_read_byte(cam, value);
1411	err += w9968cf_smbus_write_ack(cam);
1412	err += w9968cf_smbus_stop(cam);
1413
1414	/* Serial data disable */
1415	err += w9968cf_write_sb(cam, 0x0000);
1416
1417	if (!err)
1418		DBG(5, "I2C read byte done, addr.0x%04X, "
1419		       "value 0x%02X", address, *value)
1420	else
1421		DBG(5, "I2C read byte failed, addr.0x%04X, "
1422		       "wrong value 0x%02X", address, *value)
1423
1424	return err;
1425}
1426
1427
1428/* SMBus protocol: S Addr Wr [A] Value [A] P */
1429static int
1430w9968cf_i2c_adap_write_byte(struct w9968cf_device* cam,
1431			    u16 address, u8 value)
1432{
1433	DBG(4, "i2c_write_byte() is an unsupported transfer mode")
1434	return -EINVAL;
1435}
1436
1437
1438
1439/****************************************************************************
1440 * I2C interface to kernel                                                  *
1441 ****************************************************************************/
1442
1443static int
1444w9968cf_i2c_smbus_xfer(struct i2c_adapter *adapter, u16 addr,
1445		       unsigned short flags, char read_write, u8 command,
1446		       int size, union i2c_smbus_data *data)
1447{
1448	struct w9968cf_device* cam = i2c_get_adapdata(adapter);
1449	u8 i;
1450	int err = 0;
1451
1452	switch (addr) {
1453		case OV6xx0_SID:
1454		case OV7xx0_SID:
1455			break;
1456		default:
1457			DBG(4, "Rejected slave ID 0x%04X", addr)
1458			return -EINVAL;
1459	}
1460
1461	if (size == I2C_SMBUS_BYTE) {
1462		/* Why addr <<= 1? See OVXXX0_SID defines in ovcamchip.h */
1463		addr <<= 1;
1464
1465		if (read_write == I2C_SMBUS_WRITE)
1466			err = w9968cf_i2c_adap_write_byte(cam, addr, command);
1467		else if (read_write == I2C_SMBUS_READ)
1468			err = w9968cf_i2c_adap_read_byte(cam,addr,&data->byte);
1469
1470	} else if (size == I2C_SMBUS_BYTE_DATA) {
1471		addr <<= 1;
1472
1473		if (read_write == I2C_SMBUS_WRITE)
1474			err = w9968cf_i2c_adap_fastwrite_byte_data(cam, addr,
1475							  command, data->byte);
1476		else if (read_write == I2C_SMBUS_READ) {
1477			for (i = 1; i <= W9968CF_I2C_RW_RETRIES; i++) {
1478				err = w9968cf_i2c_adap_read_byte_data(cam,addr,
1479							 command, &data->byte);
1480				if (err) {
1481					if (w9968cf_smbus_refresh_bus(cam)) {
1482						err = -EIO;
1483						break;
1484					}
1485				} else
1486					break;
1487			}
1488
1489		} else
1490			return -EINVAL;
1491
1492	} else {
1493		DBG(4, "Unsupported I2C transfer mode (%d)", size)
1494		return -EINVAL;
1495	}
1496
1497	return err;
1498}
1499
1500
1501static u32 w9968cf_i2c_func(struct i2c_adapter* adap)
1502{
1503	return I2C_FUNC_SMBUS_READ_BYTE |
1504	       I2C_FUNC_SMBUS_READ_BYTE_DATA  |
1505	       I2C_FUNC_SMBUS_WRITE_BYTE_DATA;
1506}
1507
1508
1509static int w9968cf_i2c_attach_inform(struct i2c_client* client)
1510{
1511	struct w9968cf_device* cam = i2c_get_adapdata(client->adapter);
1512	int id = client->driver->id, err = 0;
1513
1514	if (id == I2C_DRIVERID_OVCAMCHIP) {
1515		cam->sensor_client = client;
1516		err = w9968cf_sensor_init(cam);
1517		if (err) {
1518			cam->sensor_client = NULL;
1519			return err;
1520		}
1521	} else {
1522		DBG(4, "Rejected client [%s] with driver [%s]",
1523		    client->name, client->driver->driver.name)
1524		return -EINVAL;
1525	}
1526
1527	DBG(5, "I2C attach client [%s] with driver [%s]",
1528	    client->name, client->driver->driver.name)
1529
1530	return 0;
1531}
1532
1533
1534static int w9968cf_i2c_detach_inform(struct i2c_client* client)
1535{
1536	struct w9968cf_device* cam = i2c_get_adapdata(client->adapter);
1537
1538	if (cam->sensor_client == client)
1539		cam->sensor_client = NULL;
1540
1541	DBG(5, "I2C detach client [%s]", client->name)
1542
1543	return 0;
1544}
1545
1546
1547static int
1548w9968cf_i2c_control(struct i2c_adapter* adapter, unsigned int cmd,
1549		    unsigned long arg)
1550{
1551	return 0;
1552}
1553
1554
1555static int w9968cf_i2c_init(struct w9968cf_device* cam)
1556{
1557	int err = 0;
1558
1559	static struct i2c_algorithm algo = {
1560		.smbus_xfer =    w9968cf_i2c_smbus_xfer,
1561		.algo_control =  w9968cf_i2c_control,
1562		.functionality = w9968cf_i2c_func,
1563	};
1564
1565	static struct i2c_adapter adap = {
1566		.id =                I2C_HW_SMBUS_W9968CF,
1567		.class =             I2C_CLASS_CAM_DIGITAL,
1568		.owner =             THIS_MODULE,
1569		.client_register =   w9968cf_i2c_attach_inform,
1570		.client_unregister = w9968cf_i2c_detach_inform,
1571		.algo =              &algo,
1572	};
1573
1574	memcpy(&cam->i2c_adapter, &adap, sizeof(struct i2c_adapter));
1575	strcpy(cam->i2c_adapter.name, "w9968cf");
1576	cam->i2c_adapter.dev.parent = &cam->usbdev->dev;
1577	i2c_set_adapdata(&cam->i2c_adapter, cam);
1578
1579	DBG(6, "Registering I2C adapter with kernel...")
1580
1581	err = i2c_add_adapter(&cam->i2c_adapter);
1582	if (err)
1583		DBG(1, "Failed to register the I2C adapter")
1584	else
1585		DBG(5, "I2C adapter registered")
1586
1587	return err;
1588}
1589
1590
1591
1592/****************************************************************************
1593 * Helper functions                                                         *
1594 ****************************************************************************/
1595
1596/*--------------------------------------------------------------------------
1597  Turn on the LED on some webcams. A beep should be heard too.
1598  Return 0 on success, a negative number otherwise.
1599  --------------------------------------------------------------------------*/
1600static int w9968cf_turn_on_led(struct w9968cf_device* cam)
1601{
1602	int err = 0;
1603
1604	err += w9968cf_write_reg(cam, 0xff00, 0x00); /* power-down */
1605	err += w9968cf_write_reg(cam, 0xbf17, 0x00); /* reset everything */
1606	err += w9968cf_write_reg(cam, 0xbf10, 0x00); /* normal operation */
1607	err += w9968cf_write_reg(cam, 0x0010, 0x01); /* serial bus, SDS high */
1608	err += w9968cf_write_reg(cam, 0x0000, 0x01); /* serial bus, SDS low */
1609	err += w9968cf_write_reg(cam, 0x0010, 0x01); /* ..high 'beep-beep' */
1610
1611	if (err)
1612		DBG(2, "Couldn't turn on the LED")
1613
1614	DBG(5, "LED turned on")
1615
1616	return err;
1617}
1618
1619
1620/*--------------------------------------------------------------------------
1621  Write some registers for the device initialization.
1622  This function is called once on open().
1623  Return 0 on success, a negative number otherwise.
1624  --------------------------------------------------------------------------*/
1625static int w9968cf_init_chip(struct w9968cf_device* cam)
1626{
1627	unsigned long hw_bufsize = cam->maxwidth*cam->maxheight*2,
1628		      y0 = 0x0000,
1629		      u0 = y0 + hw_bufsize/2,
1630		      v0 = u0 + hw_bufsize/4,
1631		      y1 = v0 + hw_bufsize/4,
1632		      u1 = y1 + hw_bufsize/2,
1633		      v1 = u1 + hw_bufsize/4;
1634	int err = 0;
1635
1636	err += w9968cf_write_reg(cam, 0xff00, 0x00); /* power off */
1637	err += w9968cf_write_reg(cam, 0xbf10, 0x00); /* power on */
1638
1639	err += w9968cf_write_reg(cam, 0x405d, 0x03); /* DRAM timings */
1640	err += w9968cf_write_reg(cam, 0x0030, 0x04); /* SDRAM timings */
1641
1642	err += w9968cf_write_reg(cam, y0 & 0xffff, 0x20); /* Y buf.0, low */
1643	err += w9968cf_write_reg(cam, y0 >> 16, 0x21);    /* Y buf.0, high */
1644	err += w9968cf_write_reg(cam, u0 & 0xffff, 0x24); /* U buf.0, low */
1645	err += w9968cf_write_reg(cam, u0 >> 16, 0x25);    /* U buf.0, high */
1646	err += w9968cf_write_reg(cam, v0 & 0xffff, 0x28); /* V buf.0, low */
1647	err += w9968cf_write_reg(cam, v0 >> 16, 0x29);    /* V buf.0, high */
1648
1649	err += w9968cf_write_reg(cam, y1 & 0xffff, 0x22); /* Y buf.1, low */
1650	err += w9968cf_write_reg(cam, y1 >> 16, 0x23);    /* Y buf.1, high */
1651	err += w9968cf_write_reg(cam, u1 & 0xffff, 0x26); /* U buf.1, low */
1652	err += w9968cf_write_reg(cam, u1 >> 16, 0x27);    /* U buf.1, high */
1653	err += w9968cf_write_reg(cam, v1 & 0xffff, 0x2a); /* V buf.1, low */
1654	err += w9968cf_write_reg(cam, v1 >> 16, 0x2b);    /* V buf.1, high */
1655
1656	err += w9968cf_write_reg(cam, y1 & 0xffff, 0x32); /* JPEG buf 0 low */
1657	err += w9968cf_write_reg(cam, y1 >> 16, 0x33);    /* JPEG buf 0 high */
1658
1659	err += w9968cf_write_reg(cam, y1 & 0xffff, 0x34); /* JPEG buf 1 low */
1660	err += w9968cf_write_reg(cam, y1 >> 16, 0x35);    /* JPEG bug 1 high */
1661
1662	err += w9968cf_write_reg(cam, 0x0000, 0x36);/* JPEG restart interval */
1663	err += w9968cf_write_reg(cam, 0x0804, 0x37);/*JPEG VLE FIFO threshold*/
1664	err += w9968cf_write_reg(cam, 0x0000, 0x38);/* disable hw up-scaling */
1665	err += w9968cf_write_reg(cam, 0x0000, 0x3f); /* JPEG/MCTL test data */
1666
1667	err += w9968cf_set_picture(cam, cam->picture); /* this before */
1668	err += w9968cf_set_window(cam, cam->window);
1669
1670	if (err)
1671		DBG(1, "Chip initialization failed")
1672	else
1673		DBG(5, "Chip successfully initialized")
1674
1675	return err;
1676}
1677
1678
1679/*--------------------------------------------------------------------------
1680  Return non-zero if the palette is supported, 0 otherwise.
1681  --------------------------------------------------------------------------*/
1682static inline u16 w9968cf_valid_palette(u16 palette)
1683{
1684	u8 i = 0;
1685	while (w9968cf_formatlist[i].palette != 0) {
1686		if (palette == w9968cf_formatlist[i].palette)
1687			return palette;
1688		i++;
1689	}
1690	return 0;
1691}
1692
1693
1694/*--------------------------------------------------------------------------
1695  Return the depth corresponding to the given palette.
1696  Palette _must_ be supported !
1697  --------------------------------------------------------------------------*/
1698static inline u16 w9968cf_valid_depth(u16 palette)
1699{
1700	u8 i=0;
1701	while (w9968cf_formatlist[i].palette != palette)
1702		i++;
1703
1704	return w9968cf_formatlist[i].depth;
1705}
1706
1707
1708/*--------------------------------------------------------------------------
1709  Return non-zero if the format requires decompression, 0 otherwise.
1710  --------------------------------------------------------------------------*/
1711static inline u8 w9968cf_need_decompression(u16 palette)
1712{
1713	u8 i = 0;
1714	while (w9968cf_formatlist[i].palette != 0) {
1715		if (palette == w9968cf_formatlist[i].palette)
1716			return w9968cf_formatlist[i].compression;
1717		i++;
1718	}
1719	return 0;
1720}
1721
1722
1723/*--------------------------------------------------------------------------
1724  Change the picture settings of the camera.
1725  Return 0 on success, a negative number otherwise.
1726  --------------------------------------------------------------------------*/
1727static int
1728w9968cf_set_picture(struct w9968cf_device* cam, struct video_picture pict)
1729{
1730	u16 fmt, hw_depth, hw_palette, reg_v = 0x0000;
1731	int err = 0;
1732
1733	/* Make sure we are using a valid depth */
1734	pict.depth = w9968cf_valid_depth(pict.palette);
1735
1736	fmt = pict.palette;
1737
1738	hw_depth = pict.depth; /* depth used by the winbond chip */
1739	hw_palette = pict.palette; /* palette used by the winbond chip */
1740
1741	/* VS & HS polarities */
1742	reg_v = (cam->vs_polarity << 12) | (cam->hs_polarity << 11);
1743
1744	switch (fmt)
1745	{
1746		case VIDEO_PALETTE_UYVY:
1747			reg_v |= 0x0000;
1748			cam->vpp_flag = VPP_NONE;
1749			break;
1750		case VIDEO_PALETTE_YUV422P:
1751			reg_v |= 0x0002;
1752			cam->vpp_flag = VPP_DECOMPRESSION;
1753			break;
1754		case VIDEO_PALETTE_YUV420:
1755		case VIDEO_PALETTE_YUV420P:
1756			reg_v |= 0x0003;
1757			cam->vpp_flag = VPP_DECOMPRESSION;
1758			break;
1759		case VIDEO_PALETTE_YUYV:
1760		case VIDEO_PALETTE_YUV422:
1761			reg_v |= 0x0000;
1762			cam->vpp_flag = VPP_SWAP_YUV_BYTES;
1763			hw_palette = VIDEO_PALETTE_UYVY;
1764			break;
1765		/* Original video is used instead of RGBX palettes.
1766		   Software conversion later. */
1767		case VIDEO_PALETTE_GREY:
1768		case VIDEO_PALETTE_RGB555:
1769		case VIDEO_PALETTE_RGB565:
1770		case VIDEO_PALETTE_RGB24:
1771		case VIDEO_PALETTE_RGB32:
1772			reg_v |= 0x0000; /* UYVY 16 bit is used */
1773			hw_depth = 16;
1774			hw_palette = VIDEO_PALETTE_UYVY;
1775			cam->vpp_flag = VPP_UYVY_TO_RGBX;
1776			break;
1777	}
1778
1779	/* NOTE: due to memory issues, it is better to disable the hardware
1780		 double buffering during compression */
1781	if (cam->double_buffer && !(cam->vpp_flag & VPP_DECOMPRESSION))
1782		reg_v |= 0x0080;
1783
1784	if (cam->clamping)
1785		reg_v |= 0x0020;
1786
1787	if (cam->filter_type == 1)
1788		reg_v |= 0x0008;
1789	else if (cam->filter_type == 2)
1790		reg_v |= 0x000c;
1791
1792	if ((err = w9968cf_write_reg(cam, reg_v, 0x16)))
1793		goto error;
1794
1795	if ((err = w9968cf_sensor_update_picture(cam, pict)))
1796		goto error;
1797
1798	/* If all went well, update the device data structure */
1799	memcpy(&cam->picture, &pict, sizeof(pict));
1800	cam->hw_depth = hw_depth;
1801	cam->hw_palette = hw_palette;
1802
1803	/* Settings changed, so we clear the frame buffers */
1804	memset(cam->frame[0].buffer, 0, cam->nbuffers*cam->frame[0].size);
1805
1806	DBG(4, "Palette is %s, depth is %u bpp",
1807	    symbolic(v4l1_plist, pict.palette), pict.depth)
1808
1809	return 0;
1810
1811error:
1812	DBG(1, "Failed to change picture settings")
1813	return err;
1814}
1815
1816
1817/*--------------------------------------------------------------------------
1818  Change the capture area size of the camera.
1819  This function _must_ be called _after_ w9968cf_set_picture().
1820  Return 0 on success, a negative number otherwise.
1821  --------------------------------------------------------------------------*/
1822static int
1823w9968cf_set_window(struct w9968cf_device* cam, struct video_window win)
1824{
1825	u16 x, y, w, h, scx, scy, cw, ch, ax, ay;
1826	unsigned long fw, fh;
1827	struct ovcamchip_window s_win;
1828	int err = 0;
1829
1830	#define SC(x) ((x) << 10)
1831	#define UNSC(x) ((x) >> 10)
1832
1833	/* Make sure we are using a supported resolution */
1834	if ((err = w9968cf_adjust_window_size(cam, (u16*)&win.width,
1835					      (u16*)&win.height)))
1836		goto error;
1837
1838	/* Scaling factors */
1839	fw = SC(win.width) / cam->maxwidth;
1840	fh = SC(win.height) / cam->maxheight;
1841
1842	/* Set up the width and height values used by the chip */
1843	if ((win.width > cam->maxwidth) || (win.height > cam->maxheight)) {
1844		cam->vpp_flag |= VPP_UPSCALE;
1845		/* Calculate largest w,h mantaining the same w/h ratio */
1846		w = (fw >= fh) ? cam->maxwidth : SC(win.width)/fh;
1847		h = (fw >= fh) ? SC(win.height)/fw : cam->maxheight;
1848		if (w < cam->minwidth) /* just in case */
1849			w = cam->minwidth;
1850		if (h < cam->minheight) /* just in case */
1851			h = cam->minheight;
1852	} else {
1853		cam->vpp_flag &= ~VPP_UPSCALE;
1854		w = win.width;
1855		h = win.height;
1856	}
1857
1858	/* x,y offsets of the cropped area */
1859	scx = cam->start_cropx;
1860	scy = cam->start_cropy;
1861
1862	/* Calculate cropped area manteining the right w/h ratio */
1863	if (cam->largeview && !(cam->vpp_flag & VPP_UPSCALE)) {
1864		cw = (fw >= fh) ? cam->maxwidth : SC(win.width)/fh;
1865		ch = (fw >= fh) ? SC(win.height)/fw : cam->maxheight;
1866	} else {
1867		cw = w;
1868		ch = h;
1869	}
1870
1871	/* Setup the window of the sensor */
1872	s_win.format = VIDEO_PALETTE_UYVY;
1873	s_win.width = cam->maxwidth;
1874	s_win.height = cam->maxheight;
1875	s_win.quarter = 0; /* full progressive video */
1876
1877	/* Center it */
1878	s_win.x = (s_win.width - cw) / 2;
1879	s_win.y = (s_win.height - ch) / 2;
1880
1881	/* Clock divisor */
1882	if (cam->clockdiv >= 0)
1883		s_win.clockdiv = cam->clockdiv; /* manual override */
1884	else
1885		switch (cam->sensor) {
1886			case CC_OV6620:
1887				s_win.clockdiv = 0;
1888				break;
1889			case CC_OV6630:
1890				s_win.clockdiv = 0;
1891				break;
1892			case CC_OV76BE:
1893			case CC_OV7610:
1894			case CC_OV7620:
1895				s_win.clockdiv = 0;
1896				break;
1897			default:
1898				s_win.clockdiv = W9968CF_DEF_CLOCKDIVISOR;
1899		}
1900
1901	/* We have to scale win.x and win.y offsets */
1902	if ( (cam->largeview && !(cam->vpp_flag & VPP_UPSCALE))
1903	     || (cam->vpp_flag & VPP_UPSCALE) ) {
1904		ax = SC(win.x)/fw;
1905		ay = SC(win.y)/fh;
1906	} else {
1907		ax = win.x;
1908		ay = win.y;
1909	}
1910
1911	if ((ax + cw) > cam->maxwidth)
1912		ax = cam->maxwidth - cw;
1913
1914	if ((ay + ch) > cam->maxheight)
1915		ay = cam->maxheight - ch;
1916
1917	/* Adjust win.x, win.y */
1918	if ( (cam->largeview && !(cam->vpp_flag & VPP_UPSCALE))
1919	     || (cam->vpp_flag & VPP_UPSCALE) ) {
1920		win.x = UNSC(ax*fw);
1921		win.y = UNSC(ay*fh);
1922	} else {
1923		win.x = ax;
1924		win.y = ay;
1925	}
1926
1927	/* Offsets used by the chip */
1928	x = ax + s_win.x;
1929	y = ay + s_win.y;
1930
1931	/* Go ! */
1932	if ((err = w9968cf_sensor_cmd(cam, OVCAMCHIP_CMD_S_MODE, &s_win)))
1933		goto error;
1934
1935	err += w9968cf_write_reg(cam, scx + x, 0x10);
1936	err += w9968cf_write_reg(cam, scy + y, 0x11);
1937	err += w9968cf_write_reg(cam, scx + x + cw, 0x12);
1938	err += w9968cf_write_reg(cam, scy + y + ch, 0x13);
1939	err += w9968cf_write_reg(cam, w, 0x14);
1940	err += w9968cf_write_reg(cam, h, 0x15);
1941
1942	/* JPEG width & height */
1943	err += w9968cf_write_reg(cam, w, 0x30);
1944	err += w9968cf_write_reg(cam, h, 0x31);
1945
1946	/* Y & UV frame buffer strides (in WORD) */
1947	if (cam->vpp_flag & VPP_DECOMPRESSION) {
1948		err += w9968cf_write_reg(cam, w/2, 0x2c);
1949		err += w9968cf_write_reg(cam, w/4, 0x2d);
1950	} else
1951		err += w9968cf_write_reg(cam, w, 0x2c);
1952
1953	if (err)
1954		goto error;
1955
1956	/* If all went well, update the device data structure */
1957	memcpy(&cam->window, &win, sizeof(win));
1958	cam->hw_width = w;
1959	cam->hw_height = h;
1960
1961	/* Settings changed, so we clear the frame buffers */
1962	memset(cam->frame[0].buffer, 0, cam->nbuffers*cam->frame[0].size);
1963
1964	DBG(4, "The capture area is %dx%d, Offset (x,y)=(%u,%u)",
1965	    win.width, win.height, win.x, win.y)
1966
1967	PDBGG("x=%u ,y=%u, w=%u, h=%u, ax=%u, ay=%u, s_win.x=%u, s_win.y=%u, "
1968	      "cw=%u, ch=%u, win.x=%u, win.y=%u, win.width=%u, win.height=%u",
1969	      x, y, w, h, ax, ay, s_win.x, s_win.y, cw, ch, win.x, win.y,
1970	      win.width, win.height)
1971
1972	return 0;
1973
1974error:
1975	DBG(1, "Failed to change the capture area size")
1976	return err;
1977}
1978
1979
1980/*--------------------------------------------------------------------------
1981  Adjust the asked values for window width and height.
1982  Return 0 on success, -1 otherwise.
1983  --------------------------------------------------------------------------*/
1984static int
1985w9968cf_adjust_window_size(struct w9968cf_device* cam, u16* width, u16* height)
1986{
1987	u16 maxw, maxh;
1988
1989	if ((*width < cam->minwidth) || (*height < cam->minheight))
1990		return -ERANGE;
1991
1992	maxw = cam->upscaling && !(cam->vpp_flag & VPP_DECOMPRESSION) &&
1993	       w9968cf_vpp ? max((u16)W9968CF_MAX_WIDTH, cam->maxwidth)
1994			   : cam->maxwidth;
1995	maxh = cam->upscaling && !(cam->vpp_flag & VPP_DECOMPRESSION) &&
1996	       w9968cf_vpp ? max((u16)W9968CF_MAX_HEIGHT, cam->maxheight)
1997			   : cam->maxheight;
1998
1999	if (*width > maxw)
2000		*width = maxw;
2001	if (*height > maxh)
2002		*height = maxh;
2003
2004	if (cam->vpp_flag & VPP_DECOMPRESSION) {
2005		*width  &= ~15L; /* multiple of 16 */
2006		*height &= ~15L;
2007	}
2008
2009	PDBGG("Window size adjusted w=%u, h=%u ", *width, *height)
2010
2011	return 0;
2012}
2013
2014
2015/*--------------------------------------------------------------------------
2016  Initialize the FIFO list of requested frames.
2017  --------------------------------------------------------------------------*/
2018static void w9968cf_init_framelist(struct w9968cf_device* cam)
2019{
2020	u8 i;
2021
2022	for (i = 0; i < cam->nbuffers; i++) {
2023		cam->requested_frame[i] = NULL;
2024		cam->frame[i].queued = 0;
2025		cam->frame[i].status = F_UNUSED;
2026	}
2027}
2028
2029
2030/*--------------------------------------------------------------------------
2031  Add a frame in the FIFO list of requested frames.
2032  This function is called in process context.
2033  --------------------------------------------------------------------------*/
2034static void w9968cf_push_frame(struct w9968cf_device* cam, u8 f_num)
2035{
2036	u8 f;
2037	unsigned long lock_flags;
2038
2039	spin_lock_irqsave(&cam->flist_lock, lock_flags);
2040
2041	for (f=0; cam->requested_frame[f] != NULL; f++);
2042	cam->requested_frame[f] = &cam->frame[f_num];
2043	cam->frame[f_num].queued = 1;
2044	cam->frame[f_num].status = F_UNUSED; /* clear the status */
2045
2046	spin_unlock_irqrestore(&cam->flist_lock, lock_flags);
2047
2048	DBG(6, "Frame #%u pushed into the FIFO list. Position %u", f_num, f)
2049}
2050
2051
2052/*--------------------------------------------------------------------------
2053  Read, store and remove the first pointer in the FIFO list of requested
2054  frames. This function is called in interrupt context.
2055  --------------------------------------------------------------------------*/
2056static void
2057w9968cf_pop_frame(struct w9968cf_device* cam, struct w9968cf_frame_t** framep)
2058{
2059	u8 i;
2060
2061	spin_lock(&cam->flist_lock);
2062
2063	*framep = cam->requested_frame[0];
2064
2065	/* Shift the list of pointers */
2066	for (i = 0; i < cam->nbuffers-1; i++)
2067		cam->requested_frame[i] = cam->requested_frame[i+1];
2068	cam->requested_frame[i] = NULL;
2069
2070	spin_unlock(&cam->flist_lock);
2071
2072	DBG(6,"Popped frame #%d from the list", (*framep)->number)
2073}
2074
2075
2076/*--------------------------------------------------------------------------
2077  High-level video post-processing routine on grabbed frames.
2078  Return 0 on success, a negative number otherwise.
2079  --------------------------------------------------------------------------*/
2080static int
2081w9968cf_postprocess_frame(struct w9968cf_device* cam,
2082			  struct w9968cf_frame_t* fr)
2083{
2084	void *pIn = fr->buffer, *pOut = cam->frame_vpp.buffer, *tmp;
2085	u16 w = cam->window.width,
2086	    h = cam->window.height,
2087	    d = cam->picture.depth,
2088	    fmt = cam->picture.palette,
2089	    rgb = cam->force_rgb,
2090	    hw_w = cam->hw_width,
2091	    hw_h = cam->hw_height,
2092	    hw_d = cam->hw_depth;
2093	int err = 0;
2094
2095	#define _PSWAP(pIn, pOut) {tmp = (pIn); (pIn) = (pOut); (pOut) = tmp;}
2096
2097	if (cam->vpp_flag & VPP_DECOMPRESSION) {
2098		memcpy(pOut, pIn, fr->length);
2099		_PSWAP(pIn, pOut)
2100		err = w9968cf_vpp->decode(pIn, fr->length, hw_w, hw_h, pOut);
2101		PDBGG("Compressed frame length: %lu",(unsigned long)fr->length)
2102		fr->length = (hw_w*hw_h*hw_d)/8;
2103		_PSWAP(pIn, pOut)
2104		if (err) {
2105			DBG(4, "An error occurred while decoding the frame: "
2106			       "%s", symbolic(decoder_errlist, err))
2107			return err;
2108		} else
2109			DBG(6, "Frame decoded")
2110	}
2111
2112	if (cam->vpp_flag & VPP_SWAP_YUV_BYTES) {
2113		w9968cf_vpp->swap_yuvbytes(pIn, fr->length);
2114		DBG(6, "Original UYVY component ordering changed")
2115	}
2116
2117	if (cam->vpp_flag & VPP_UPSCALE) {
2118		w9968cf_vpp->scale_up(pIn, pOut, hw_w, hw_h, hw_d, w, h);
2119		fr->length = (w*h*hw_d)/8;
2120		_PSWAP(pIn, pOut)
2121		DBG(6, "Vertical up-scaling done: %u,%u,%ubpp->%u,%u",
2122		    hw_w, hw_h, hw_d, w, h)
2123	}
2124
2125	if (cam->vpp_flag & VPP_UYVY_TO_RGBX) {
2126		w9968cf_vpp->uyvy_to_rgbx(pIn, fr->length, pOut, fmt, rgb);
2127		fr->length = (w*h*d)/8;
2128		_PSWAP(pIn, pOut)
2129		DBG(6, "UYVY-16bit to %s conversion done",
2130		    symbolic(v4l1_plist, fmt))
2131	}
2132
2133	if (pOut == fr->buffer)
2134		memcpy(fr->buffer, cam->frame_vpp.buffer, fr->length);
2135
2136	return 0;
2137}
2138
2139
2140
2141/****************************************************************************
2142 * Image sensor control routines                                            *
2143 ****************************************************************************/
2144
2145static int
2146w9968cf_sensor_set_control(struct w9968cf_device* cam, int cid, int val)
2147{
2148	struct ovcamchip_control ctl;
2149	int err;
2150
2151	ctl.id = cid;
2152	ctl.value = val;
2153
2154	err = w9968cf_sensor_cmd(cam, OVCAMCHIP_CMD_S_CTRL, &ctl);
2155
2156	return err;
2157}
2158
2159
2160static int
2161w9968cf_sensor_get_control(struct w9968cf_device* cam, int cid, int* val)
2162{
2163	struct ovcamchip_control ctl;
2164	int err;
2165
2166	ctl.id = cid;
2167
2168	err = w9968cf_sensor_cmd(cam, OVCAMCHIP_CMD_G_CTRL, &ctl);
2169	if (!err)
2170		*val = ctl.value;
2171
2172	return err;
2173}
2174
2175
2176static int
2177w9968cf_sensor_cmd(struct w9968cf_device* cam, unsigned int cmd, void* arg)
2178{
2179	struct i2c_client* c = cam->sensor_client;
2180	int rc = 0;
2181
2182	if (!c || !c->driver || !c->driver->command)
2183		return -EINVAL;
2184
2185	rc = c->driver->command(c, cmd, arg);
2186	/* The I2C driver returns -EPERM on non-supported controls */
2187	return (rc < 0 && rc != -EPERM) ? rc : 0;
2188}
2189
2190
2191/*--------------------------------------------------------------------------
2192  Update some settings of the image sensor.
2193  Returns: 0 on success, a negative number otherwise.
2194  --------------------------------------------------------------------------*/
2195static int w9968cf_sensor_update_settings(struct w9968cf_device* cam)
2196{
2197	int err = 0;
2198
2199	/* Auto brightness */
2200	err = w9968cf_sensor_set_control(cam, OVCAMCHIP_CID_AUTOBRIGHT,
2201					 cam->auto_brt);
2202	if (err)
2203		return err;
2204
2205	/* Auto exposure */
2206	err = w9968cf_sensor_set_control(cam, OVCAMCHIP_CID_AUTOEXP,
2207					 cam->auto_exp);
2208	if (err)
2209		return err;
2210
2211	/* Banding filter */
2212	err = w9968cf_sensor_set_control(cam, OVCAMCHIP_CID_BANDFILT,
2213					 cam->bandfilt);
2214	if (err)
2215		return err;
2216
2217	/* Light frequency */
2218	err = w9968cf_sensor_set_control(cam, OVCAMCHIP_CID_FREQ,
2219					 cam->lightfreq);
2220	if (err)
2221		return err;
2222
2223	/* Back light */
2224	err = w9968cf_sensor_set_control(cam, OVCAMCHIP_CID_BACKLIGHT,
2225					 cam->backlight);
2226	if (err)
2227		return err;
2228
2229	/* Mirror */
2230	err = w9968cf_sensor_set_control(cam, OVCAMCHIP_CID_MIRROR,
2231					 cam->mirror);
2232	if (err)
2233		return err;
2234
2235	return 0;
2236}
2237
2238
2239/*--------------------------------------------------------------------------
2240  Get some current picture settings from the image sensor and update the
2241  internal 'picture' structure of the camera.
2242  Returns: 0 on success, a negative number otherwise.
2243  --------------------------------------------------------------------------*/
2244static int w9968cf_sensor_get_picture(struct w9968cf_device* cam)
2245{
2246	int err, v;
2247
2248	err = w9968cf_sensor_get_control(cam, OVCAMCHIP_CID_CONT, &v);
2249	if (err)
2250		return err;
2251	cam->picture.contrast = v;
2252
2253	err = w9968cf_sensor_get_control(cam, OVCAMCHIP_CID_BRIGHT, &v);
2254	if (err)
2255		return err;
2256	cam->picture.brightness = v;
2257
2258	err = w9968cf_sensor_get_control(cam, OVCAMCHIP_CID_SAT, &v);
2259	if (err)
2260		return err;
2261	cam->picture.colour = v;
2262
2263	err = w9968cf_sensor_get_control(cam, OVCAMCHIP_CID_HUE, &v);
2264	if (err)
2265		return err;
2266	cam->picture.hue = v;
2267
2268	DBG(5, "Got picture settings from the image sensor")
2269
2270	PDBGG("Brightness, contrast, hue, colour, whiteness are "
2271	      "%u,%u,%u,%u,%u", cam->picture.brightness,cam->picture.contrast,
2272	      cam->picture.hue, cam->picture.colour, cam->picture.whiteness)
2273
2274	return 0;
2275}
2276
2277
2278/*--------------------------------------------------------------------------
2279  Update picture settings of the image sensor.
2280  Returns: 0 on success, a negative number otherwise.
2281  --------------------------------------------------------------------------*/
2282static int
2283w9968cf_sensor_update_picture(struct w9968cf_device* cam,
2284			      struct video_picture pict)
2285{
2286	int err = 0;
2287
2288	if ((!cam->sensor_initialized)
2289	    || pict.contrast != cam->picture.contrast) {
2290		err = w9968cf_sensor_set_control(cam, OVCAMCHIP_CID_CONT,
2291						 pict.contrast);
2292		if (err)
2293			goto fail;
2294		DBG(4, "Contrast changed from %u to %u",
2295		    cam->picture.contrast, pict.contrast)
2296		cam->picture.contrast = pict.contrast;
2297	}
2298
2299	if (((!cam->sensor_initialized) ||
2300	    pict.brightness != cam->picture.brightness) && (!cam->auto_brt)) {
2301		err = w9968cf_sensor_set_control(cam, OVCAMCHIP_CID_BRIGHT,
2302						 pict.brightness);
2303		if (err)
2304			goto fail;
2305		DBG(4, "Brightness changed from %u to %u",
2306		    cam->picture.brightness, pict.brightness)
2307		cam->picture.brightness = pict.brightness;
2308	}
2309
2310	if ((!cam->sensor_initialized) || pict.colour != cam->picture.colour) {
2311		err = w9968cf_sensor_set_control(cam, OVCAMCHIP_CID_SAT,
2312						 pict.colour);
2313		if (err)
2314			goto fail;
2315		DBG(4, "Colour changed from %u to %u",
2316		    cam->picture.colour, pict.colour)
2317		cam->picture.colour = pict.colour;
2318	}
2319
2320	if ((!cam->sensor_initialized) || pict.hue != cam->picture.hue) {
2321		err = w9968cf_sensor_set_control(cam, OVCAMCHIP_CID_HUE,
2322						 pict.hue);
2323		if (err)
2324			goto fail;
2325		DBG(4, "Hue changed from %u to %u",
2326		    cam->picture.hue, pict.hue)
2327		cam->picture.hue = pict.hue;
2328	}
2329
2330	return 0;
2331
2332fail:
2333	DBG(4, "Failed to change sensor picture setting")
2334	return err;
2335}
2336
2337
2338
2339/****************************************************************************
2340 * Camera configuration                                                     *
2341 ****************************************************************************/
2342
2343/*--------------------------------------------------------------------------
2344  This function is called when a supported image sensor is detected.
2345  Return 0 if the initialization succeeds, a negative number otherwise.
2346  --------------------------------------------------------------------------*/
2347static int w9968cf_sensor_init(struct w9968cf_device* cam)
2348{
2349	int err = 0;
2350
2351	if ((err = w9968cf_sensor_cmd(cam, OVCAMCHIP_CMD_INITIALIZE,
2352				      &cam->monochrome)))
2353		goto error;
2354
2355	if ((err = w9968cf_sensor_cmd(cam, OVCAMCHIP_CMD_Q_SUBTYPE,
2356				      &cam->sensor)))
2357		goto error;
2358
2359	/* NOTE: Make sure width and height are a multiple of 16 */
2360	switch (cam->sensor_client->addr) {
2361		case OV6xx0_SID:
2362			cam->maxwidth = 352;
2363			cam->maxheight = 288;
2364			cam->minwidth = 64;
2365			cam->minheight = 48;
2366			break;
2367		case OV7xx0_SID:
2368			cam->maxwidth = 640;
2369			cam->maxheight = 480;
2370			cam->minwidth = 64;
2371			cam->minheight = 48;
2372			break;
2373		default:
2374			DBG(1, "Not supported image sensor detected for %s",
2375			    symbolic(camlist, cam->id))
2376			return -EINVAL;
2377	}
2378
2379	/* These values depend on the ones in the ovxxx0.c sources */
2380	switch (cam->sensor) {
2381		case CC_OV7620:
2382			cam->start_cropx = 287;
2383			cam->start_cropy = 35;
2384			cam->vs_polarity = 1;
2385			cam->hs_polarity = 1;
2386			break;
2387		default:
2388			cam->start_cropx = 320;
2389			cam->start_cropy = 35;
2390			cam->vs_polarity = 1;
2391			cam->hs_polarity = 0;
2392	}
2393
2394	if ((err = w9968cf_sensor_update_settings(cam)))
2395		goto error;
2396
2397	if ((err = w9968cf_sensor_update_picture(cam, cam->picture)))
2398		goto error;
2399
2400	cam->sensor_initialized = 1;
2401
2402	DBG(2, "%s image sensor initialized", symbolic(senlist, cam->sensor))
2403	return 0;
2404
2405error:
2406	cam->sensor_initialized = 0;
2407	cam->sensor = CC_UNKNOWN;
2408	DBG(1, "Image sensor initialization failed for %s (/dev/video%d). "
2409	       "Try to detach and attach this device again",
2410	    symbolic(camlist, cam->id), cam->v4ldev->minor)
2411	return err;
2412}
2413
2414
2415/*--------------------------------------------------------------------------
2416  Fill some basic fields in the main device data structure.
2417  This function is called once on w9968cf_usb_probe() for each recognized
2418  camera.
2419  --------------------------------------------------------------------------*/
2420static void
2421w9968cf_configure_camera(struct w9968cf_device* cam,
2422			 struct usb_device* udev,
2423			 enum w9968cf_model_id mod_id,
2424			 const unsigned short dev_nr)
2425{
2426	mutex_init(&cam->fileop_mutex);
2427	init_waitqueue_head(&cam->open);
2428	spin_lock_init(&cam->urb_lock);
2429	spin_lock_init(&cam->flist_lock);
2430
2431	cam->users = 0;
2432	cam->disconnected = 0;
2433	cam->id = mod_id;
2434	cam->sensor = CC_UNKNOWN;
2435	cam->sensor_initialized = 0;
2436
2437	/* Calculate the alternate setting number (from 1 to 16)
2438	   according to the 'packet_size' module parameter */
2439	if (packet_size[dev_nr] < W9968CF_MIN_PACKET_SIZE)
2440		packet_size[dev_nr] = W9968CF_MIN_PACKET_SIZE;
2441	for (cam->altsetting = 1;
2442	     packet_size[dev_nr] < wMaxPacketSize[cam->altsetting-1];
2443	     cam->altsetting++);
2444
2445	cam->max_buffers = (max_buffers[dev_nr] < 2 ||
2446			    max_buffers[dev_nr] > W9968CF_MAX_BUFFERS)
2447			   ? W9968CF_BUFFERS : (u8)max_buffers[dev_nr];
2448
2449	cam->double_buffer = (double_buffer[dev_nr] == 0 ||
2450			      double_buffer[dev_nr] == 1)
2451			     ? (u8)double_buffer[dev_nr]:W9968CF_DOUBLE_BUFFER;
2452
2453	cam->clamping = (clamping[dev_nr] == 0 || clamping[dev_nr] == 1)
2454			? (u8)clamping[dev_nr] : W9968CF_CLAMPING;
2455
2456	cam->filter_type = (filter_type[dev_nr] == 0 ||
2457			    filter_type[dev_nr] == 1 ||
2458			    filter_type[dev_nr] == 2)
2459			   ? (u8)filter_type[dev_nr] : W9968CF_FILTER_TYPE;
2460
2461	cam->capture = 1;
2462
2463	cam->largeview = (largeview[dev_nr] == 0 || largeview[dev_nr] == 1)
2464			 ? (u8)largeview[dev_nr] : W9968CF_LARGEVIEW;
2465
2466	cam->decompression = (decompression[dev_nr] == 0 ||
2467			      decompression[dev_nr] == 1 ||
2468			      decompression[dev_nr] == 2)
2469			     ? (u8)decompression[dev_nr]:W9968CF_DECOMPRESSION;
2470
2471	cam->upscaling = (upscaling[dev_nr] == 0 ||
2472			  upscaling[dev_nr] == 1)
2473			 ? (u8)upscaling[dev_nr] : W9968CF_UPSCALING;
2474
2475	cam->auto_brt = (autobright[dev_nr] == 0 || autobright[dev_nr] == 1)
2476			? (u8)autobright[dev_nr] : W9968CF_AUTOBRIGHT;
2477
2478	cam->auto_exp = (autoexp[dev_nr] == 0 || autoexp[dev_nr] == 1)
2479			? (u8)autoexp[dev_nr] : W9968CF_AUTOEXP;
2480
2481	cam->lightfreq = (lightfreq[dev_nr] == 50 || lightfreq[dev_nr] == 60)
2482			 ? (u8)lightfreq[dev_nr] : W9968CF_LIGHTFREQ;
2483
2484	cam->bandfilt = (bandingfilter[dev_nr] == 0 ||
2485			 bandingfilter[dev_nr] == 1)
2486			? (u8)bandingfilter[dev_nr] : W9968CF_BANDINGFILTER;
2487
2488	cam->backlight = (backlight[dev_nr] == 0 || backlight[dev_nr] == 1)
2489			 ? (u8)backlight[dev_nr] : W9968CF_BACKLIGHT;
2490
2491	cam->clockdiv = (clockdiv[dev_nr] == -1 || clockdiv[dev_nr] >= 0)
2492			? (s8)clockdiv[dev_nr] : W9968CF_CLOCKDIV;
2493
2494	cam->mirror = (mirror[dev_nr] == 0 || mirror[dev_nr] == 1)
2495		      ? (u8)mirror[dev_nr] : W9968CF_MIRROR;
2496
2497	cam->monochrome = (monochrome[dev_nr] == 0 || monochrome[dev_nr] == 1)
2498			  ? monochrome[dev_nr] : W9968CF_MONOCHROME;
2499
2500	cam->picture.brightness = (u16)brightness[dev_nr];
2501	cam->picture.hue = (u16)hue[dev_nr];
2502	cam->picture.colour = (u16)colour[dev_nr];
2503	cam->picture.contrast = (u16)contrast[dev_nr];
2504	cam->picture.whiteness = (u16)whiteness[dev_nr];
2505	if (w9968cf_valid_palette((u16)force_palette[dev_nr])) {
2506		cam->picture.palette = (u16)force_palette[dev_nr];
2507		cam->force_palette = 1;
2508	} else {
2509		cam->force_palette = 0;
2510		if (cam->decompression == 0)
2511			cam->picture.palette = W9968CF_PALETTE_DECOMP_OFF;
2512		else if (cam->decompression == 1)
2513			cam->picture.palette = W9968CF_PALETTE_DECOMP_FORCE;
2514		else
2515			cam->picture.palette = W9968CF_PALETTE_DECOMP_ON;
2516	}
2517	cam->picture.depth = w9968cf_valid_depth(cam->picture.palette);
2518
2519	cam->force_rgb = (force_rgb[dev_nr] == 0 || force_rgb[dev_nr] == 1)
2520			 ? (u8)force_rgb[dev_nr] : W9968CF_FORCE_RGB;
2521
2522	cam->window.x = 0;
2523	cam->window.y = 0;
2524	cam->window.width = W9968CF_WIDTH;
2525	cam->window.height = W9968CF_HEIGHT;
2526	cam->window.chromakey = 0;
2527	cam->window.clipcount = 0;
2528	cam->window.flags = 0;
2529
2530	DBG(3, "%s configured with settings #%u:",
2531	    symbolic(camlist, cam->id), dev_nr)
2532
2533	DBG(3, "- Data packet size for USB isochrnous transfer: %u bytes",
2534	    wMaxPacketSize[cam->altsetting-1])
2535
2536	DBG(3, "- Number of requested video frame buffers: %u",
2537	    cam->max_buffers)
2538
2539	if (cam->double_buffer)
2540		DBG(3, "- Hardware double buffering enabled")
2541	else
2542		DBG(3, "- Hardware double buffering disabled")
2543
2544	if (cam->filter_type == 0)
2545		DBG(3, "- Video filtering disabled")
2546	else if (cam->filter_type == 1)
2547		DBG(3, "- Video filtering enabled: type 1-2-1")
2548	else if (cam->filter_type == 2)
2549		DBG(3, "- Video filtering enabled: type 2-3-6-3-2")
2550
2551	if (cam->clamping)
2552		DBG(3, "- Video data clamping (CCIR-601 format) enabled")
2553	else
2554		DBG(3, "- Video data clamping (CCIR-601 format) disabled")
2555
2556	if (cam->largeview)
2557		DBG(3, "- Large view enabled")
2558	else
2559		DBG(3, "- Large view disabled")
2560
2561	if ((cam->decompression) == 0 && (!cam->force_palette))
2562		DBG(3, "- Decompression disabled")
2563	else if ((cam->decompression) == 1 && (!cam->force_palette))
2564		DBG(3, "- Decompression forced")
2565	else if ((cam->decompression) == 2 && (!cam->force_palette))
2566		DBG(3, "- Decompression allowed")
2567
2568	if (cam->upscaling)
2569		DBG(3, "- Software image scaling enabled")
2570	else
2571		DBG(3, "- Software image scaling disabled")
2572
2573	if (cam->force_palette)
2574		DBG(3, "- Image palette forced to %s",
2575		    symbolic(v4l1_plist, cam->picture.palette))
2576
2577	if (cam->force_rgb)
2578		DBG(3, "- RGB component ordering will be used instead of BGR")
2579
2580	if (cam->auto_brt)
2581		DBG(3, "- Auto brightness enabled")
2582	else
2583		DBG(3, "- Auto brightness disabled")
2584
2585	if (cam->auto_exp)
2586		DBG(3, "- Auto exposure enabled")
2587	else
2588		DBG(3, "- Auto exposure disabled")
2589
2590	if (cam->backlight)
2591		DBG(3, "- Backlight exposure algorithm enabled")
2592	else
2593		DBG(3, "- Backlight exposure algorithm disabled")
2594
2595	if (cam->mirror)
2596		DBG(3, "- Mirror enabled")
2597	else
2598		DBG(3, "- Mirror disabled")
2599
2600	if (cam->bandfilt)
2601		DBG(3, "- Banding filter enabled")
2602	else
2603		DBG(3, "- Banding filter disabled")
2604
2605	DBG(3, "- Power lighting frequency: %u", cam->lightfreq)
2606
2607	if (cam->clockdiv == -1)
2608		DBG(3, "- Automatic clock divisor enabled")
2609	else
2610		DBG(3, "- Clock divisor: %d", cam->clockdiv)
2611
2612	if (cam->monochrome)
2613		DBG(3, "- Image sensor used as monochrome")
2614	else
2615		DBG(3, "- Image sensor not used as monochrome")
2616}
2617
2618
2619/*--------------------------------------------------------------------------
2620  If the video post-processing module is not loaded, some parameters
2621  must be overridden.
2622  --------------------------------------------------------------------------*/
2623static void w9968cf_adjust_configuration(struct w9968cf_device* cam)
2624{
2625	if (!w9968cf_vpp) {
2626		if (cam->decompression == 1) {
2627			cam->decompression = 2;
2628			DBG(2, "Video post-processing module not found: "
2629			       "'decompression' parameter forced to 2")
2630		}
2631		if (cam->upscaling) {
2632			cam->upscaling = 0;
2633			DBG(2, "Video post-processing module not found: "
2634			       "'upscaling' parameter forced to 0")
2635		}
2636		if (cam->picture.palette != VIDEO_PALETTE_UYVY) {
2637			cam->force_palette = 0;
2638			DBG(2, "Video post-processing module not found: "
2639			       "'force_palette' parameter forced to 0")
2640		}
2641		cam->picture.palette = VIDEO_PALETTE_UYVY;
2642		cam->picture.depth = w9968cf_valid_depth(cam->picture.palette);
2643	}
2644}
2645
2646
2647/*--------------------------------------------------------------------------
2648  Release the resources used by the driver.
2649  This function is called on disconnect
2650  (or on close if deallocation has been deferred)
2651  --------------------------------------------------------------------------*/
2652static void w9968cf_release_resources(struct w9968cf_device* cam)
2653{
2654	mutex_lock(&w9968cf_devlist_mutex);
2655
2656	DBG(2, "V4L device deregistered: /dev/video%d", cam->v4ldev->minor)
2657
2658	video_unregister_device(cam->v4ldev);
2659	list_del(&cam->v4llist);
2660	i2c_del_adapter(&cam->i2c_adapter);
2661	w9968cf_deallocate_memory(cam);
2662	kfree(cam->control_buffer);
2663	kfree(cam->data_buffer);
2664
2665	mutex_unlock(&w9968cf_devlist_mutex);
2666}
2667
2668
2669
2670/****************************************************************************
2671 * Video4Linux interface                                                    *
2672 ****************************************************************************/
2673
2674static int w9968cf_open(struct inode* inode, struct file* filp)
2675{
2676	struct w9968cf_device* cam;
2677	int err;
2678
2679	/* This the only safe way to prevent race conditions with disconnect */
2680	if (!down_read_trylock(&w9968cf_disconnect))
2681		return -ERESTARTSYS;
2682
2683	cam = (struct w9968cf_device*)video_get_drvdata(video_devdata(filp));
2684
2685	mutex_lock(&cam->dev_mutex);
2686
2687	if (cam->sensor == CC_UNKNOWN) {
2688		DBG(2, "No supported image sensor has been detected by the "
2689		       "'ovcamchip' module for the %s (/dev/video%d). Make "
2690		       "sure it is loaded *before* (re)connecting the camera.",
2691		    symbolic(camlist, cam->id), cam->v4ldev->minor)
2692		mutex_unlock(&cam->dev_mutex);
2693		up_read(&w9968cf_disconnect);
2694		return -ENODEV;
2695	}
2696
2697	if (cam->users) {
2698		DBG(2, "%s (/dev/video%d) has been already occupied by '%s'",
2699		    symbolic(camlist, cam->id),cam->v4ldev->minor,cam->command)
2700		if ((filp->f_flags & O_NONBLOCK)||(filp->f_flags & O_NDELAY)) {
2701			mutex_unlock(&cam->dev_mutex);
2702			up_read(&w9968cf_disconnect);
2703			return -EWOULDBLOCK;
2704		}
2705		mutex_unlock(&cam->dev_mutex);
2706		err = wait_event_interruptible_exclusive(cam->open,
2707							 cam->disconnected ||
2708							 !cam->users);
2709		if (err) {
2710			up_read(&w9968cf_disconnect);
2711			return err;
2712		}
2713		if (cam->disconnected) {
2714			up_read(&w9968cf_disconnect);
2715			return -ENODEV;
2716		}
2717		mutex_lock(&cam->dev_mutex);
2718	}
2719
2720	DBG(5, "Opening '%s', /dev/video%d ...",
2721	    symbolic(camlist, cam->id), cam->v4ldev->minor)
2722
2723	cam->streaming = 0;
2724	cam->misconfigured = 0;
2725
2726	w9968cf_adjust_configuration(cam);
2727
2728	if ((err = w9968cf_allocate_memory(cam)))
2729		goto deallocate_memory;
2730
2731	if ((err = w9968cf_init_chip(cam)))
2732		goto deallocate_memory;
2733
2734	if ((err = w9968cf_start_transfer(cam)))
2735		goto deallocate_memory;
2736
2737	filp->private_data = cam;
2738
2739	cam->users++;
2740	strcpy(cam->command, current->comm);
2741
2742	init_waitqueue_head(&cam->wait_queue);
2743
2744	DBG(5, "Video device is open")
2745
2746	mutex_unlock(&cam->dev_mutex);
2747	up_read(&w9968cf_disconnect);
2748
2749	return 0;
2750
2751deallocate_memory:
2752	w9968cf_deallocate_memory(cam);
2753	DBG(2, "Failed to open the video device")
2754	mutex_unlock(&cam->dev_mutex);
2755	up_read(&w9968cf_disconnect);
2756	return err;
2757}
2758
2759
2760static int w9968cf_release(struct inode* inode, struct file* filp)
2761{
2762	struct w9968cf_device* cam;
2763
2764	cam = (struct w9968cf_device*)video_get_drvdata(video_devdata(filp));
2765
2766	mutex_lock(&cam->dev_mutex); /* prevent disconnect() to be called */
2767
2768	w9968cf_stop_transfer(cam);
2769
2770	if (cam->disconnected) {
2771		w9968cf_release_resources(cam);
2772		mutex_unlock(&cam->dev_mutex);
2773		kfree(cam);
2774		return 0;
2775	}
2776
2777	cam->users--;
2778	w9968cf_deallocate_memory(cam);
2779	wake_up_interruptible_nr(&cam->open, 1);
2780
2781	DBG(5, "Video device closed")
2782	mutex_unlock(&cam->dev_mutex);
2783	return 0;
2784}
2785
2786
2787static ssize_t
2788w9968cf_read(struct file* filp, char __user * buf, size_t count, loff_t* f_pos)
2789{
2790	struct w9968cf_device* cam;
2791	struct w9968cf_frame_t* fr;
2792	int err = 0;
2793
2794	cam = (struct w9968cf_device*)video_get_drvdata(video_devdata(filp));
2795
2796	if (filp->f_flags & O_NONBLOCK)
2797		return -EWOULDBLOCK;
2798
2799	if (mutex_lock_interruptible(&cam->fileop_mutex))
2800		return -ERESTARTSYS;
2801
2802	if (cam->disconnected) {
2803		DBG(2, "Device not present")
2804		mutex_unlock(&cam->fileop_mutex);
2805		return -ENODEV;
2806	}
2807
2808	if (cam->misconfigured) {
2809		DBG(2, "The camera is misconfigured. Close and open it again.")
2810		mutex_unlock(&cam->fileop_mutex);
2811		return -EIO;
2812	}
2813
2814	if (!cam->frame[0].queued)
2815		w9968cf_push_frame(cam, 0);
2816
2817	if (!cam->frame[1].queued)
2818		w9968cf_push_frame(cam, 1);
2819
2820	err = wait_event_interruptible(cam->wait_queue,
2821				       cam->frame[0].status == F_READY ||
2822				       cam->frame[1].status == F_READY ||
2823				       cam->disconnected);
2824	if (err) {
2825		mutex_unlock(&cam->fileop_mutex);
2826		return err;
2827	}
2828	if (cam->disconnected) {
2829		mutex_unlock(&cam->fileop_mutex);
2830		return -ENODEV;
2831	}
2832
2833	fr = (cam->frame[0].status == F_READY) ? &cam->frame[0]:&cam->frame[1];
2834
2835	if (w9968cf_vpp)
2836		w9968cf_postprocess_frame(cam, fr);
2837
2838	if (count > fr->length)
2839		count = fr->length;
2840
2841	if (copy_to_user(buf, fr->buffer, count)) {
2842		fr->status = F_UNUSED;
2843		mutex_unlock(&cam->fileop_mutex);
2844		return -EFAULT;
2845	}
2846	*f_pos += count;
2847
2848	fr->status = F_UNUSED;
2849
2850	DBG(5, "%zu bytes read", count)
2851
2852	mutex_unlock(&cam->fileop_mutex);
2853	return count;
2854}
2855
2856
2857static int w9968cf_mmap(struct file* filp, struct vm_area_struct *vma)
2858{
2859	struct w9968cf_device* cam = (struct w9968cf_device*)
2860				     video_get_drvdata(video_devdata(filp));
2861	unsigned long vsize = vma->vm_end - vma->vm_start,
2862		      psize = cam->nbuffers * cam->frame[0].size,
2863		      start = vma->vm_start,
2864		      pos = (unsigned long)cam->frame[0].buffer,
2865		      page;
2866
2867	if (cam->disconnected) {
2868		DBG(2, "Device not present")
2869		return -ENODEV;
2870	}
2871
2872	if (cam->misconfigured) {
2873		DBG(2, "The camera is misconfigured. Close and open it again")
2874		return -EIO;
2875	}
2876
2877	PDBGG("mmapping %lu bytes...", vsize)
2878
2879	if (vsize > psize - (vma->vm_pgoff << PAGE_SHIFT))
2880		return -EINVAL;
2881
2882	while (vsize > 0) {
2883		page = vmalloc_to_pfn((void *)pos);
2884		if (remap_pfn_range(vma, start, page + vma->vm_pgoff,
2885						PAGE_SIZE, vma->vm_page_prot))
2886			return -EAGAIN;
2887		start += PAGE_SIZE;
2888		pos += PAGE_SIZE;
2889		vsize -= PAGE_SIZE;
2890	}
2891
2892	DBG(5, "mmap method successfully called")
2893	return 0;
2894}
2895
2896
2897static int
2898w9968cf_ioctl(struct inode* inode, struct file* filp,
2899	      unsigned int cmd, unsigned long arg)
2900{
2901	struct w9968cf_device* cam;
2902	int err;
2903
2904	cam = (struct w9968cf_device*)video_get_drvdata(video_devdata(filp));
2905
2906	if (mutex_lock_interruptible(&cam->fileop_mutex))
2907		return -ERESTARTSYS;
2908
2909	if (cam->disconnected) {
2910		DBG(2, "Device not present")
2911		mutex_unlock(&cam->fileop_mutex);
2912		return -ENODEV;
2913	}
2914
2915	if (cam->misconfigured) {
2916		DBG(2, "The camera is misconfigured. Close and open it again.")
2917		mutex_unlock(&cam->fileop_mutex);
2918		return -EIO;
2919	}
2920
2921	err = w9968cf_v4l_ioctl(inode, filp, cmd, (void __user *)arg);
2922
2923	mutex_unlock(&cam->fileop_mutex);
2924	return err;
2925}
2926
2927
2928static int w9968cf_v4l_ioctl(struct inode* inode, struct file* filp,
2929			     unsigned int cmd, void __user * arg)
2930{
2931	struct w9968cf_device* cam;
2932	const char* v4l1_ioctls[] = {
2933		"?", "CGAP", "GCHAN", "SCHAN", "GTUNER", "STUNER",
2934		"GPICT", "SPICT", "CCAPTURE", "GWIN", "SWIN", "GFBUF",
2935		"SFBUF", "KEY", "GFREQ", "SFREQ", "GAUDIO", "SAUDIO",
2936		"SYNC", "MCAPTURE", "GMBUF", "GUNIT", "GCAPTURE", "SCAPTURE",
2937		"SPLAYMODE", "SWRITEMODE", "GPLAYINFO", "SMICROCODE",
2938		"GVBIFMT", "SVBIFMT"
2939	};
2940
2941	#define V4L1_IOCTL(cmd) \
2942		((_IOC_NR((cmd)) < ARRAY_SIZE(v4l1_ioctls)) ? \
2943		v4l1_ioctls[_IOC_NR((cmd))] : "?")
2944
2945	cam = (struct w9968cf_device*)video_get_drvdata(video_devdata(filp));
2946
2947	switch (cmd) {
2948
2949	case VIDIOCGCAP: /* get video capability */
2950	{
2951		struct video_capability cap = {
2952			.type = VID_TYPE_CAPTURE | VID_TYPE_SCALES,
2953			.channels = 1,
2954			.audios = 0,
2955			.minwidth = cam->minwidth,
2956			.minheight = cam->minheight,
2957		};
2958		sprintf(cap.name, "W996[87]CF USB Camera #%d",
2959			cam->v4ldev->minor);
2960		cap.maxwidth = (cam->upscaling && w9968cf_vpp)
2961			       ? max((u16)W9968CF_MAX_WIDTH, cam->maxwidth)
2962				 : cam->maxwidth;
2963		cap.maxheight = (cam->upscaling && w9968cf_vpp)
2964				? max((u16)W9968CF_MAX_HEIGHT, cam->maxheight)
2965				  : cam->maxheight;
2966
2967		if (copy_to_user(arg, &cap, sizeof(cap)))
2968			return -EFAULT;
2969
2970		DBG(5, "VIDIOCGCAP successfully called")
2971		return 0;
2972	}
2973
2974	case VIDIOCGCHAN: /* get video channel informations */
2975	{
2976		struct video_channel chan;
2977		if (copy_from_user(&chan, arg, sizeof(chan)))
2978			return -EFAULT;
2979
2980		if (chan.channel != 0)
2981			return -EINVAL;
2982
2983		strcpy(chan.name, "Camera");
2984		chan.tuners = 0;
2985		chan.flags = 0;
2986		chan.type = VIDEO_TYPE_CAMERA;
2987		chan.norm = VIDEO_MODE_AUTO;
2988
2989		if (copy_to_user(arg, &chan, sizeof(chan)))
2990			return -EFAULT;
2991
2992		DBG(5, "VIDIOCGCHAN successfully called")
2993		return 0;
2994	}
2995
2996	case VIDIOCSCHAN: /* set active channel */
2997	{
2998		struct video_channel chan;
2999
3000		if (copy_from_user(&chan, arg, sizeof(chan)))
3001			return -EFAULT;
3002
3003		if (chan.channel != 0)
3004			return -EINVAL;
3005
3006		DBG(5, "VIDIOCSCHAN successfully called")
3007		return 0;
3008	}
3009
3010	case VIDIOCGPICT: /* get image properties of the picture */
3011	{
3012		if (w9968cf_sensor_get_picture(cam))
3013			return -EIO;
3014
3015		if (copy_to_user(arg, &cam->picture, sizeof(cam->picture)))
3016			return -EFAULT;
3017
3018		DBG(5, "VIDIOCGPICT successfully called")
3019		return 0;
3020	}
3021
3022	case VIDIOCSPICT: /* change picture settings */
3023	{
3024		struct video_picture pict;
3025		int err = 0;
3026
3027		if (copy_from_user(&pict, arg, sizeof(pict)))
3028			return -EFAULT;
3029
3030		if ( (cam->force_palette || !w9968cf_vpp)
3031		     && pict.palette != cam->picture.palette ) {
3032			DBG(4, "Palette %s rejected: only %s is allowed",
3033			    symbolic(v4l1_plist, pict.palette),
3034			    symbolic(v4l1_plist, cam->picture.palette))
3035			return -EINVAL;
3036		}
3037
3038		if (!w9968cf_valid_palette(pict.palette)) {
3039			DBG(4, "Palette %s not supported. VIDIOCSPICT failed",
3040			    symbolic(v4l1_plist, pict.palette))
3041			return -EINVAL;
3042		}
3043
3044		if (!cam->force_palette) {
3045		   if (cam->decompression == 0) {
3046		      if (w9968cf_need_decompression(pict.palette)) {
3047			 DBG(4, "Decompression disabled: palette %s is not "
3048				"allowed. VIDIOCSPICT failed",
3049			     symbolic(v4l1_plist, pict.palette))
3050			 return -EINVAL;
3051		      }
3052		   } else if (cam->decompression == 1) {
3053		      if (!w9968cf_need_decompression(pict.palette)) {
3054			 DBG(4, "Decompression forced: palette %s is not "
3055				"allowed. VIDIOCSPICT failed",
3056			     symbolic(v4l1_plist, pict.palette))
3057			 return -EINVAL;
3058		      }
3059		   }
3060		}
3061
3062		if (pict.depth != w9968cf_valid_depth(pict.palette)) {
3063			DBG(4, "Requested depth %u bpp is not valid for %s "
3064			       "palette: ignored and changed to %u bpp",
3065			    pict.depth, symbolic(v4l1_plist, pict.palette),
3066			    w9968cf_valid_depth(pict.palette))
3067			pict.depth = w9968cf_valid_depth(pict.palette);
3068		}
3069
3070		if (pict.palette != cam->picture.palette) {
3071			if(*cam->requested_frame
3072			   || cam->frame_current->queued) {
3073				err = wait_event_interruptible
3074				      ( cam->wait_queue,
3075					cam->disconnected ||
3076					(!*cam->requested_frame &&
3077					 !cam->frame_current->queued) );
3078				if (err)
3079					return err;
3080				if (cam->disconnected)
3081					return -ENODEV;
3082			}
3083
3084			if (w9968cf_stop_transfer(cam))
3085				goto ioctl_fail;
3086
3087			if (w9968cf_set_picture(cam, pict))
3088				goto ioctl_fail;
3089
3090			if (w9968cf_start_transfer(cam))
3091				goto ioctl_fail;
3092
3093		} else if (w9968cf_sensor_update_picture(cam, pict))
3094			return -EIO;
3095
3096
3097		DBG(5, "VIDIOCSPICT successfully called")
3098		return 0;
3099	}
3100
3101	case VIDIOCSWIN: /* set capture area */
3102	{
3103		struct video_window win;
3104		int err = 0;
3105
3106		if (copy_from_user(&win, arg, sizeof(win)))
3107			return -EFAULT;
3108
3109		DBG(6, "VIDIOCSWIN called: clipcount=%d, flags=%u, "
3110		       "x=%u, y=%u, %ux%u", win.clipcount, win.flags,
3111		    win.x, win.y, win.width, win.height)
3112
3113		if (win.clipcount != 0 || win.flags != 0)
3114			return -EINVAL;
3115
3116		if ((err = w9968cf_adjust_window_size(cam, (u16*)&win.width,
3117						      (u16*)&win.height))) {
3118			DBG(4, "Resolution not supported (%ux%u). "
3119			       "VIDIOCSWIN failed", win.width, win.height)
3120			return err;
3121		}
3122
3123		if (win.x != cam->window.x ||
3124		    win.y != cam->window.y ||
3125		    win.width != cam->window.width ||
3126		    win.height != cam->window.height) {
3127			if(*cam->requested_frame
3128			   || cam->frame_current->queued) {
3129				err = wait_event_interruptible
3130				      ( cam->wait_queue,
3131					cam->disconnected ||
3132					(!*cam->requested_frame &&
3133					 !cam->frame_current->queued) );
3134				if (err)
3135					return err;
3136				if (cam->disconnected)
3137					return -ENODEV;
3138			}
3139
3140			if (w9968cf_stop_transfer(cam))
3141				goto ioctl_fail;
3142
3143			/* This _must_ be called before set_window() */
3144			if (w9968cf_set_picture(cam, cam->picture))
3145				goto ioctl_fail;
3146
3147			if (w9968cf_set_window(cam, win))
3148				goto ioctl_fail;
3149
3150			if (w9968cf_start_transfer(cam))
3151				goto ioctl_fail;
3152		}
3153
3154		DBG(5, "VIDIOCSWIN successfully called. ")
3155		return 0;
3156	}
3157
3158	case VIDIOCGWIN: /* get current window properties */
3159	{
3160		if (copy_to_user(arg,&cam->window,sizeof(struct video_window)))
3161			return -EFAULT;
3162
3163		DBG(5, "VIDIOCGWIN successfully called")
3164		return 0;
3165	}
3166
3167	case VIDIOCGMBUF: /* request for memory (mapped) buffer */
3168	{
3169		struct video_mbuf mbuf;
3170		u8 i;
3171
3172		mbuf.size = cam->nbuffers * cam->frame[0].size;
3173		mbuf.frames = cam->nbuffers;
3174		for (i = 0; i < cam->nbuffers; i++)
3175			mbuf.offsets[i] = (unsigned long)cam->frame[i].buffer -
3176					  (unsigned long)cam->frame[0].buffer;
3177
3178		if (copy_to_user(arg, &mbuf, sizeof(mbuf)))
3179			return -EFAULT;
3180
3181		DBG(5, "VIDIOCGMBUF successfully called")
3182		return 0;
3183	}
3184
3185	case VIDIOCMCAPTURE: /* start the capture to a frame */
3186	{
3187		struct video_mmap mmap;
3188		struct w9968cf_frame_t* fr;
3189		int err = 0;
3190
3191		if (copy_from_user(&mmap, arg, sizeof(mmap)))
3192			return -EFAULT;
3193
3194		DBG(6, "VIDIOCMCAPTURE called: frame #%u, format=%s, %dx%d",
3195		    mmap.frame, symbolic(v4l1_plist, mmap.format),
3196		    mmap.width, mmap.height)
3197
3198		if (mmap.frame >= cam->nbuffers) {
3199			DBG(4, "Invalid frame number (%u). "
3200			       "VIDIOCMCAPTURE failed", mmap.frame)
3201			return -EINVAL;
3202		}
3203
3204		if (mmap.format!=cam->picture.palette &&
3205		    (cam->force_palette || !w9968cf_vpp)) {
3206			DBG(4, "Palette %s rejected: only %s is allowed",
3207			    symbolic(v4l1_plist, mmap.format),
3208			    symbolic(v4l1_plist, cam->picture.palette))
3209			return -EINVAL;
3210		}
3211
3212		if (!w9968cf_valid_palette(mmap.format)) {
3213			DBG(4, "Palette %s not supported. "
3214			       "VIDIOCMCAPTURE failed",
3215			    symbolic(v4l1_plist, mmap.format))
3216			return -EINVAL;
3217		}
3218
3219		if (!cam->force_palette) {
3220		   if (cam->decompression == 0) {
3221		      if (w9968cf_need_decompression(mmap.format)) {
3222			 DBG(4, "Decompression disabled: palette %s is not "
3223				"allowed. VIDIOCSPICT failed",
3224			     symbolic(v4l1_plist, mmap.format))
3225			 return -EINVAL;
3226		      }
3227		   } else if (cam->decompression == 1) {
3228		      if (!w9968cf_need_decompression(mmap.format)) {
3229			 DBG(4, "Decompression forced: palette %s is not "
3230				"allowed. VIDIOCSPICT failed",
3231			     symbolic(v4l1_plist, mmap.format))
3232			 return -EINVAL;
3233		      }
3234		   }
3235		}
3236
3237		if ((err = w9968cf_adjust_window_size(cam, (u16*)&mmap.width,
3238						      (u16*)&mmap.height))) {
3239			DBG(4, "Resolution not supported (%dx%d). "
3240			       "VIDIOCMCAPTURE failed",
3241			    mmap.width, mmap.height)
3242			return err;
3243		}
3244
3245		fr = &cam->frame[mmap.frame];
3246
3247		if (mmap.width  != cam->window.width ||
3248		    mmap.height != cam->window.height ||
3249		    mmap.format != cam->picture.palette) {
3250
3251			struct video_window win;
3252			struct video_picture pict;
3253
3254			if(*cam->requested_frame
3255			   || cam->frame_current->queued) {
3256				DBG(6, "VIDIOCMCAPTURE. Change settings for "
3257				       "frame #%u: %dx%d, format %s. Wait...",
3258				    mmap.frame, mmap.width, mmap.height,
3259				    symbolic(v4l1_plist, mmap.format))
3260				err = wait_event_interruptible
3261				      ( cam->wait_queue,
3262					cam->disconnected ||
3263					(!*cam->requested_frame &&
3264					 !cam->frame_current->queued) );
3265				if (err)
3266					return err;
3267				if (cam->disconnected)
3268					return -ENODEV;
3269			}
3270
3271			memcpy(&win, &cam->window, sizeof(win));
3272			memcpy(&pict, &cam->picture, sizeof(pict));
3273			win.width = mmap.width;
3274			win.height = mmap.height;
3275			pict.palette = mmap.format;
3276
3277			if (w9968cf_stop_transfer(cam))
3278				goto ioctl_fail;
3279
3280			/* This before set_window */
3281			if (w9968cf_set_picture(cam, pict))
3282				goto ioctl_fail;
3283
3284			if (w9968cf_set_window(cam, win))
3285				goto ioctl_fail;
3286
3287			if (w9968cf_start_transfer(cam))
3288				goto ioctl_fail;
3289
3290		} else 	if (fr->queued) {
3291
3292			DBG(6, "Wait until frame #%u is free", mmap.frame)
3293
3294			err = wait_event_interruptible(cam->wait_queue,
3295						       cam->disconnected ||
3296						       (!fr->queued));
3297			if (err)
3298				return err;
3299			if (cam->disconnected)
3300				return -ENODEV;
3301		}
3302
3303		w9968cf_push_frame(cam, mmap.frame);
3304		DBG(5, "VIDIOCMCAPTURE(%u): successfully called", mmap.frame)
3305		return 0;
3306	}
3307
3308	case VIDIOCSYNC: /* wait until the capture of a frame is finished */
3309	{
3310		unsigned int f_num;
3311		struct w9968cf_frame_t* fr;
3312		int err = 0;
3313
3314		if (copy_from_user(&f_num, arg, sizeof(f_num)))
3315			return -EFAULT;
3316
3317		if (f_num >= cam->nbuffers) {
3318			DBG(4, "Invalid frame number (%u). "
3319			       "VIDIOCMCAPTURE failed", f_num)
3320			return -EINVAL;
3321		}
3322
3323		DBG(6, "VIDIOCSYNC called for frame #%u", f_num)
3324
3325		fr = &cam->frame[f_num];
3326
3327		switch (fr->status) {
3328		case F_UNUSED:
3329			if (!fr->queued) {
3330				DBG(4, "VIDIOSYNC: Frame #%u not requested!",
3331				    f_num)
3332				return -EFAULT;
3333			}
3334		case F_ERROR:
3335		case F_GRABBING:
3336			err = wait_event_interruptible(cam->wait_queue,
3337						       (fr->status == F_READY)
3338						       || cam->disconnected);
3339			if (err)
3340				return err;
3341			if (cam->disconnected)
3342				return -ENODEV;
3343			break;
3344		case F_READY:
3345			break;
3346		}
3347
3348		if (w9968cf_vpp)
3349			w9968cf_postprocess_frame(cam, fr);
3350
3351		fr->status = F_UNUSED;
3352
3353		DBG(5, "VIDIOCSYNC(%u) successfully called", f_num)
3354		return 0;
3355	}
3356
3357	case VIDIOCGUNIT:/* report the unit numbers of the associated devices*/
3358	{
3359		struct video_unit unit = {
3360			.video = cam->v4ldev->minor,
3361			.vbi = VIDEO_NO_UNIT,
3362			.radio = VIDEO_NO_UNIT,
3363			.audio = VIDEO_NO_UNIT,
3364			.teletext = VIDEO_NO_UNIT,
3365		};
3366
3367		if (copy_to_user(arg, &unit, sizeof(unit)))
3368			return -EFAULT;
3369
3370		DBG(5, "VIDIOCGUNIT successfully called")
3371		return 0;
3372	}
3373
3374	case VIDIOCKEY:
3375		return 0;
3376
3377	case VIDIOCGFBUF:
3378	{
3379		if (clear_user(arg, sizeof(struct video_buffer)))
3380			return -EFAULT;
3381
3382		DBG(5, "VIDIOCGFBUF successfully called")
3383		return 0;
3384	}
3385
3386	case VIDIOCGTUNER:
3387	{
3388		struct video_tuner tuner;
3389		if (copy_from_user(&tuner, arg, sizeof(tuner)))
3390			return -EFAULT;
3391
3392		if (tuner.tuner != 0)
3393			return -EINVAL;
3394
3395		strcpy(tuner.name, "no_tuner");
3396		tuner.rangelow = 0;
3397		tuner.rangehigh = 0;
3398		tuner.flags = VIDEO_TUNER_NORM;
3399		tuner.mode = VIDEO_MODE_AUTO;
3400		tuner.signal = 0xffff;
3401
3402		if (copy_to_user(arg, &tuner, sizeof(tuner)))
3403			return -EFAULT;
3404
3405		DBG(5, "VIDIOCGTUNER successfully called")
3406		return 0;
3407	}
3408
3409	case VIDIOCSTUNER:
3410	{
3411		struct video_tuner tuner;
3412		if (copy_from_user(&tuner, arg, sizeof(tuner)))
3413			return -EFAULT;
3414
3415		if (tuner.tuner != 0)
3416			return -EINVAL;
3417
3418		if (tuner.mode != VIDEO_MODE_AUTO)
3419			return -EINVAL;
3420
3421		DBG(5, "VIDIOCSTUNER successfully called")
3422		return 0;
3423	}
3424
3425	case VIDIOCSFBUF:
3426	case VIDIOCCAPTURE:
3427	case VIDIOCGFREQ:
3428	case VIDIOCSFREQ:
3429	case VIDIOCGAUDIO:
3430	case VIDIOCSAUDIO:
3431	case VIDIOCSPLAYMODE:
3432	case VIDIOCSWRITEMODE:
3433	case VIDIOCGPLAYINFO:
3434	case VIDIOCSMICROCODE:
3435	case VIDIOCGVBIFMT:
3436	case VIDIOCSVBIFMT:
3437		DBG(4, "Unsupported V4L1 IOCtl: VIDIOC%s "
3438		       "(type 0x%01X, "
3439		       "n. 0x%01X, "
3440		       "dir. 0x%01X, "
3441		       "size 0x%02X)",
3442		    V4L1_IOCTL(cmd),
3443		    _IOC_TYPE(cmd),_IOC_NR(cmd),_IOC_DIR(cmd),_IOC_SIZE(cmd))
3444
3445		return -EINVAL;
3446
3447	default:
3448		DBG(4, "Invalid V4L1 IOCtl: VIDIOC%s "
3449		       "type 0x%01X, "
3450		       "n. 0x%01X, "
3451		       "dir. 0x%01X, "
3452		       "size 0x%02X",
3453		    V4L1_IOCTL(cmd),
3454		    _IOC_TYPE(cmd),_IOC_NR(cmd),_IOC_DIR(cmd),_IOC_SIZE(cmd))
3455
3456		return -ENOIOCTLCMD;
3457
3458	} /* end of switch */
3459
3460ioctl_fail:
3461	cam->misconfigured = 1;
3462	DBG(1, "VIDIOC%s failed because of hardware problems. "
3463	       "To use the camera, close and open it again.", V4L1_IOCTL(cmd))
3464	return -EFAULT;
3465}
3466
3467
3468static const struct file_operations w9968cf_fops = {
3469	.owner =   THIS_MODULE,
3470	.open =    w9968cf_open,
3471	.release = w9968cf_release,
3472	.read =    w9968cf_read,
3473	.ioctl =   w9968cf_ioctl,
3474	.compat_ioctl = v4l_compat_ioctl32,
3475	.mmap =    w9968cf_mmap,
3476	.llseek =  no_llseek,
3477};
3478
3479
3480
3481/****************************************************************************
3482 * USB probe and V4L registration, disconnect and id_table[] definition     *
3483 ****************************************************************************/
3484
3485static int
3486w9968cf_usb_probe(struct usb_interface* intf, const struct usb_device_id* id)
3487{
3488	struct usb_device *udev = interface_to_usbdev(intf);
3489	struct w9968cf_device* cam;
3490	int err = 0;
3491	enum w9968cf_model_id mod_id;
3492	struct list_head* ptr;
3493	u8 sc = 0; /* number of simultaneous cameras */
3494	static unsigned short dev_nr = 0; /* we are handling device number n */
3495
3496	if (le16_to_cpu(udev->descriptor.idVendor)  == winbond_id_table[0].idVendor &&
3497	    le16_to_cpu(udev->descriptor.idProduct) == winbond_id_table[0].idProduct)
3498		mod_id = W9968CF_MOD_CLVBWGP; /* see camlist[] table */
3499	else if (le16_to_cpu(udev->descriptor.idVendor)  == winbond_id_table[1].idVendor &&
3500		 le16_to_cpu(udev->descriptor.idProduct) == winbond_id_table[1].idProduct)
3501		mod_id = W9968CF_MOD_GENERIC; /* see camlist[] table */
3502	else
3503		return -ENODEV;
3504
3505	cam = (struct w9968cf_device*)
3506		  kzalloc(sizeof(struct w9968cf_device), GFP_KERNEL);
3507	if (!cam)
3508		return -ENOMEM;
3509
3510	mutex_init(&cam->dev_mutex);
3511	mutex_lock(&cam->dev_mutex);
3512
3513	cam->usbdev = udev;
3514	/* NOTE: a local copy is used to avoid possible race conditions */
3515	memcpy(&cam->dev, &udev->dev, sizeof(struct device));
3516
3517	DBG(2, "%s detected", symbolic(camlist, mod_id))
3518
3519	if (simcams > W9968CF_MAX_DEVICES)
3520		simcams = W9968CF_SIMCAMS;
3521
3522	/* How many cameras are connected ? */
3523	mutex_lock(&w9968cf_devlist_mutex);
3524	list_for_each(ptr, &w9968cf_dev_list)
3525		sc++;
3526	mutex_unlock(&w9968cf_devlist_mutex);
3527
3528	if (sc >= simcams) {
3529		DBG(2, "Device rejected: too many connected cameras "
3530		       "(max. %u)", simcams)
3531		err = -EPERM;
3532		goto fail;
3533	}
3534
3535
3536	/* Allocate 2 bytes of memory for camera control USB transfers */
3537	if (!(cam->control_buffer = kzalloc(2, GFP_KERNEL))) {
3538		DBG(1,"Couldn't allocate memory for camera control transfers")
3539		err = -ENOMEM;
3540		goto fail;
3541	}
3542
3543	/* Allocate 8 bytes of memory for USB data transfers to the FSB */
3544	if (!(cam->data_buffer = kzalloc(8, GFP_KERNEL))) {
3545		DBG(1, "Couldn't allocate memory for data "
3546		       "transfers to the FSB")
3547		err = -ENOMEM;
3548		goto fail;
3549	}
3550
3551	/* Register the V4L device */
3552	cam->v4ldev = video_device_alloc();
3553	if (!cam->v4ldev) {
3554		DBG(1, "Could not allocate memory for a V4L structure")
3555		err = -ENOMEM;
3556		goto fail;
3557	}
3558
3559	strcpy(cam->v4ldev->name, symbolic(camlist, mod_id));
3560	cam->v4ldev->owner = THIS_MODULE;
3561	cam->v4ldev->type = VID_TYPE_CAPTURE | VID_TYPE_SCALES;
3562	cam->v4ldev->hardware = VID_HARDWARE_W9968CF;
3563	cam->v4ldev->fops = &w9968cf_fops;
3564	cam->v4ldev->minor = video_nr[dev_nr];
3565	cam->v4ldev->release = video_device_release;
3566	video_set_drvdata(cam->v4ldev, cam);
3567	cam->v4ldev->dev = &cam->dev;
3568
3569	err = video_register_device(cam->v4ldev, VFL_TYPE_GRABBER,
3570				    video_nr[dev_nr]);
3571	if (err) {
3572		DBG(1, "V4L device registration failed")
3573		if (err == -ENFILE && video_nr[dev_nr] == -1)
3574			DBG(2, "Couldn't find a free /dev/videoX node")
3575		video_nr[dev_nr] = -1;
3576		dev_nr = (dev_nr < W9968CF_MAX_DEVICES-1) ? dev_nr+1 : 0;
3577		goto fail;
3578	}
3579
3580	DBG(2, "V4L device registered as /dev/video%d", cam->v4ldev->minor)
3581
3582	/* Set some basic constants */
3583	w9968cf_configure_camera(cam, udev, mod_id, dev_nr);
3584
3585	/* Add a new entry into the list of V4L registered devices */
3586	mutex_lock(&w9968cf_devlist_mutex);
3587	list_add(&cam->v4llist, &w9968cf_dev_list);
3588	mutex_unlock(&w9968cf_devlist_mutex);
3589	dev_nr = (dev_nr < W9968CF_MAX_DEVICES-1) ? dev_nr+1 : 0;
3590
3591	w9968cf_turn_on_led(cam);
3592
3593	w9968cf_i2c_init(cam);
3594
3595	usb_set_intfdata(intf, cam);
3596	mutex_unlock(&cam->dev_mutex);
3597	return 0;
3598
3599fail: /* Free unused memory */
3600	kfree(cam->control_buffer);
3601	kfree(cam->data_buffer);
3602	if (cam->v4ldev)
3603		video_device_release(cam->v4ldev);
3604	mutex_unlock(&cam->dev_mutex);
3605	kfree(cam);
3606	return err;
3607}
3608
3609
3610static void w9968cf_usb_disconnect(struct usb_interface* intf)
3611{
3612	struct w9968cf_device* cam =
3613	   (struct w9968cf_device*)usb_get_intfdata(intf);
3614
3615	down_write(&w9968cf_disconnect);
3616
3617	if (cam) {
3618		/* Prevent concurrent accesses to data */
3619		mutex_lock(&cam->dev_mutex);
3620
3621		cam->disconnected = 1;
3622
3623		DBG(2, "Disconnecting %s...", symbolic(camlist, cam->id))
3624
3625		wake_up_interruptible_all(&cam->open);
3626
3627		if (cam->users) {
3628			DBG(2, "The device is open (/dev/video%d)! "
3629			       "Process name: %s. Deregistration and memory "
3630			       "deallocation are deferred on close.",
3631			    cam->v4ldev->minor, cam->command)
3632			cam->misconfigured = 1;
3633			w9968cf_stop_transfer(cam);
3634			wake_up_interruptible(&cam->wait_queue);
3635		} else
3636			w9968cf_release_resources(cam);
3637
3638		mutex_unlock(&cam->dev_mutex);
3639
3640		if (!cam->users)
3641			kfree(cam);
3642	}
3643
3644	up_write(&w9968cf_disconnect);
3645}
3646
3647
3648static struct usb_driver w9968cf_usb_driver = {
3649	.name =       "w9968cf",
3650	.id_table =   winbond_id_table,
3651	.probe =      w9968cf_usb_probe,
3652	.disconnect = w9968cf_usb_disconnect,
3653};
3654
3655
3656
3657/****************************************************************************
3658 * Module init, exit and intermodule communication                          *
3659 ****************************************************************************/
3660
3661static int __init w9968cf_module_init(void)
3662{
3663	int err;
3664
3665	KDBG(2, W9968CF_MODULE_NAME" "W9968CF_MODULE_VERSION)
3666	KDBG(3, W9968CF_MODULE_AUTHOR)
3667
3668	if (ovmod_load)
3669		request_module("ovcamchip");
3670
3671	if ((err = usb_register(&w9968cf_usb_driver)))
3672		return err;
3673
3674	return 0;
3675}
3676
3677
3678static void __exit w9968cf_module_exit(void)
3679{
3680	/* w9968cf_usb_disconnect() will be called */
3681	usb_deregister(&w9968cf_usb_driver);
3682
3683	KDBG(2, W9968CF_MODULE_NAME" deregistered")
3684}
3685
3686
3687module_init(w9968cf_module_init);
3688module_exit(w9968cf_module_exit);
3689