blob: 882a79679dc6a9f7beadb98a2eb507428bad205c [file] [log] [blame]
Dean Anderson38f993a2008-06-26 23:15:51 -03001/*
2 * s2255drv.c - a driver for the Sensoray 2255 USB video capture device
3 *
Dean Anderson4de39f52010-03-03 19:39:19 -03004 * Copyright (C) 2007-2010 by Sensoray Company Inc.
Dean Anderson38f993a2008-06-26 23:15:51 -03005 * Dean Anderson
6 *
7 * Some video buffer code based on vivi driver:
8 *
9 * Sensoray 2255 device supports 4 simultaneous channels.
10 * The channels are not "crossbar" inputs, they are physically
11 * attached to separate video decoders.
12 *
13 * Because of USB2.0 bandwidth limitations. There is only a
14 * certain amount of data which may be transferred at one time.
15 *
16 * Example maximum bandwidth utilization:
17 *
18 * -full size, color mode YUYV or YUV422P: 2 channels at once
19 *
20 * -full or half size Grey scale: all 4 channels at once
21 *
22 * -half size, color mode YUYV or YUV422P: all 4 channels at once
23 *
24 * -full size, color mode YUYV or YUV422P 1/2 frame rate: all 4 channels
25 * at once.
26 * (TODO: Incorporate videodev2 frame rate(FR) enumeration,
27 * which is currently experimental.)
28 *
29 * This program is free software; you can redistribute it and/or modify
30 * it under the terms of the GNU General Public License as published by
31 * the Free Software Foundation; either version 2 of the License, or
32 * (at your option) any later version.
33 *
34 * This program is distributed in the hope that it will be useful,
35 * but WITHOUT ANY WARRANTY; without even the implied warranty of
36 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
37 * GNU General Public License for more details.
38 *
39 * You should have received a copy of the GNU General Public License
40 * along with this program; if not, write to the Free Software
41 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
42 */
43
44#include <linux/module.h>
45#include <linux/firmware.h>
46#include <linux/kernel.h>
47#include <linux/mutex.h>
Tejun Heo5a0e3ad2010-03-24 17:04:11 +090048#include <linux/slab.h>
Dean Anderson38f993a2008-06-26 23:15:51 -030049#include <linux/videodev2.h>
50#include <linux/version.h>
Hans Verkuilfeb75f02008-07-27 06:30:21 -030051#include <linux/mm.h>
Alexey Dobriyan405f5572009-07-11 22:08:37 +040052#include <linux/smp_lock.h>
Dean Anderson38f993a2008-06-26 23:15:51 -030053#include <media/videobuf-vmalloc.h>
54#include <media/v4l2-common.h>
Hans Verkuil35ea11f2008-07-20 08:12:02 -030055#include <media/v4l2-ioctl.h>
Dean Anderson38f993a2008-06-26 23:15:51 -030056#include <linux/vmalloc.h>
57#include <linux/usb.h>
58
59#define FIRMWARE_FILE_NAME "f2255usb.bin"
60
61
62
Dean Anderson22b88d42008-08-29 15:33:19 -030063/* default JPEG quality */
64#define S2255_DEF_JPEG_QUAL 50
Dean Anderson38f993a2008-06-26 23:15:51 -030065/* vendor request in */
66#define S2255_VR_IN 0
67/* vendor request out */
68#define S2255_VR_OUT 1
69/* firmware query */
70#define S2255_VR_FW 0x30
71/* USB endpoint number for configuring the device */
72#define S2255_CONFIG_EP 2
73/* maximum time for DSP to start responding after last FW word loaded(ms) */
Dean Anderson14d96262008-08-25 13:58:55 -030074#define S2255_DSP_BOOTTIME 800
Dean Anderson38f993a2008-06-26 23:15:51 -030075/* maximum time to wait for firmware to load (ms) */
Dean Anderson3f8d6f72008-06-30 21:28:34 -030076#define S2255_LOAD_TIMEOUT (5000 + S2255_DSP_BOOTTIME)
Dean Anderson38f993a2008-06-26 23:15:51 -030077#define S2255_DEF_BUFS 16
Dean Anderson14d96262008-08-25 13:58:55 -030078#define S2255_SETMODE_TIMEOUT 500
Dean Anderson4de39f52010-03-03 19:39:19 -030079#define S2255_VIDSTATUS_TIMEOUT 350
Dean Anderson38f993a2008-06-26 23:15:51 -030080#define MAX_CHANNELS 4
Dean Anderson3fa00602010-03-04 20:47:33 -030081#define S2255_MARKER_FRAME cpu_to_le32(0x2255DA4AL)
82#define S2255_MARKER_RESPONSE cpu_to_le32(0x2255ACACL)
83#define S2255_RESPONSE_SETMODE cpu_to_le32(0x01)
84#define S2255_RESPONSE_FW cpu_to_le32(0x10)
85#define S2255_RESPONSE_STATUS cpu_to_le32(0x20)
Dean Anderson14d96262008-08-25 13:58:55 -030086#define S2255_USB_XFER_SIZE (16 * 1024)
Dean Anderson38f993a2008-06-26 23:15:51 -030087#define MAX_CHANNELS 4
88#define MAX_PIPE_BUFFERS 1
89#define SYS_FRAMES 4
90/* maximum size is PAL full size plus room for the marker header(s) */
Dean Anderson14d96262008-08-25 13:58:55 -030091#define SYS_FRAMES_MAXSIZE (720*288*2*2 + 4096)
92#define DEF_USB_BLOCK S2255_USB_XFER_SIZE
Dean Anderson38f993a2008-06-26 23:15:51 -030093#define LINE_SZ_4CIFS_NTSC 640
94#define LINE_SZ_2CIFS_NTSC 640
95#define LINE_SZ_1CIFS_NTSC 320
96#define LINE_SZ_4CIFS_PAL 704
97#define LINE_SZ_2CIFS_PAL 704
98#define LINE_SZ_1CIFS_PAL 352
99#define NUM_LINES_4CIFS_NTSC 240
100#define NUM_LINES_2CIFS_NTSC 240
101#define NUM_LINES_1CIFS_NTSC 240
102#define NUM_LINES_4CIFS_PAL 288
103#define NUM_LINES_2CIFS_PAL 288
104#define NUM_LINES_1CIFS_PAL 288
105#define LINE_SZ_DEF 640
106#define NUM_LINES_DEF 240
107
108
109/* predefined settings */
110#define FORMAT_NTSC 1
111#define FORMAT_PAL 2
112
113#define SCALE_4CIFS 1 /* 640x480(NTSC) or 704x576(PAL) */
114#define SCALE_2CIFS 2 /* 640x240(NTSC) or 704x288(PAL) */
115#define SCALE_1CIFS 3 /* 320x240(NTSC) or 352x288(PAL) */
Dean Anderson7d853532009-05-15 14:32:04 -0300116/* SCALE_4CIFSI is the 2 fields interpolated into one */
117#define SCALE_4CIFSI 4 /* 640x480(NTSC) or 704x576(PAL) high quality */
Dean Anderson38f993a2008-06-26 23:15:51 -0300118
119#define COLOR_YUVPL 1 /* YUV planar */
120#define COLOR_YUVPK 2 /* YUV packed */
121#define COLOR_Y8 4 /* monochrome */
Dean Anderson14d96262008-08-25 13:58:55 -0300122#define COLOR_JPG 5 /* JPEG */
123#define MASK_COLOR 0xff
124#define MASK_JPG_QUALITY 0xff00
Dean Anderson38f993a2008-06-26 23:15:51 -0300125
126/* frame decimation. Not implemented by V4L yet(experimental in V4L) */
127#define FDEC_1 1 /* capture every frame. default */
128#define FDEC_2 2 /* capture every 2nd frame */
129#define FDEC_3 3 /* capture every 3rd frame */
130#define FDEC_5 5 /* capture every 5th frame */
131
132/*-------------------------------------------------------
133 * Default mode parameters.
134 *-------------------------------------------------------*/
135#define DEF_SCALE SCALE_4CIFS
136#define DEF_COLOR COLOR_YUVPL
137#define DEF_FDEC FDEC_1
138#define DEF_BRIGHT 0
139#define DEF_CONTRAST 0x5c
140#define DEF_SATURATION 0x80
141#define DEF_HUE 0
142
143/* usb config commands */
Dean Anderson3fa00602010-03-04 20:47:33 -0300144#define IN_DATA_TOKEN cpu_to_le32(0x2255c0de)
145#define CMD_2255 cpu_to_le32(0xc2255000)
146#define CMD_SET_MODE cpu_to_le32((CMD_2255 | 0x10))
147#define CMD_START cpu_to_le32((CMD_2255 | 0x20))
148#define CMD_STOP cpu_to_le32((CMD_2255 | 0x30))
149#define CMD_STATUS cpu_to_le32((CMD_2255 | 0x40))
Dean Anderson38f993a2008-06-26 23:15:51 -0300150
151struct s2255_mode {
152 u32 format; /* input video format (NTSC, PAL) */
153 u32 scale; /* output video scale */
154 u32 color; /* output video color format */
155 u32 fdec; /* frame decimation */
156 u32 bright; /* brightness */
157 u32 contrast; /* contrast */
158 u32 saturation; /* saturation */
159 u32 hue; /* hue (NTSC only)*/
160 u32 single; /* capture 1 frame at a time (!=0), continuously (==0)*/
161 u32 usb_block; /* block size. should be 4096 of DEF_USB_BLOCK */
162 u32 restart; /* if DSP requires restart */
163};
164
Dean Anderson14d96262008-08-25 13:58:55 -0300165
166#define S2255_READ_IDLE 0
167#define S2255_READ_FRAME 1
168
Dean Anderson38f993a2008-06-26 23:15:51 -0300169/* frame structure */
Dean Anderson38f993a2008-06-26 23:15:51 -0300170struct s2255_framei {
171 unsigned long size;
Dean Anderson14d96262008-08-25 13:58:55 -0300172 unsigned long ulState; /* ulState:S2255_READ_IDLE, S2255_READ_FRAME*/
Dean Anderson38f993a2008-06-26 23:15:51 -0300173 void *lpvbits; /* image data */
174 unsigned long cur_size; /* current data copied to it */
175};
176
177/* image buffer structure */
178struct s2255_bufferi {
179 unsigned long dwFrames; /* number of frames in buffer */
180 struct s2255_framei frame[SYS_FRAMES]; /* array of FRAME structures */
181};
182
183#define DEF_MODEI_NTSC_CONT {FORMAT_NTSC, DEF_SCALE, DEF_COLOR, \
184 DEF_FDEC, DEF_BRIGHT, DEF_CONTRAST, DEF_SATURATION, \
Dean Anderson3f8d6f72008-06-30 21:28:34 -0300185 DEF_HUE, 0, DEF_USB_BLOCK, 0}
Dean Anderson38f993a2008-06-26 23:15:51 -0300186
187struct s2255_dmaqueue {
188 struct list_head active;
Dean Anderson38f993a2008-06-26 23:15:51 -0300189 struct s2255_dev *dev;
190 int channel;
191};
192
193/* for firmware loading, fw_state */
194#define S2255_FW_NOTLOADED 0
195#define S2255_FW_LOADED_DSPWAIT 1
196#define S2255_FW_SUCCESS 2
197#define S2255_FW_FAILED 3
Dean Andersonf78d92c2008-07-22 14:43:27 -0300198#define S2255_FW_DISCONNECTING 4
Dean Anderson38f993a2008-06-26 23:15:51 -0300199
Harvey Harrisondeaf53e2008-11-15 01:10:14 -0300200#define S2255_FW_MARKER cpu_to_le32(0x22552f2f)
Dean Anderson14d96262008-08-25 13:58:55 -0300201/* 2255 read states */
202#define S2255_READ_IDLE 0
203#define S2255_READ_FRAME 1
Dean Anderson38f993a2008-06-26 23:15:51 -0300204struct s2255_fw {
205 int fw_loaded;
206 int fw_size;
207 struct urb *fw_urb;
208 atomic_t fw_state;
209 void *pfw_data;
210 wait_queue_head_t wait_fw;
Dean Anderson38f993a2008-06-26 23:15:51 -0300211 const struct firmware *fw;
212};
213
214struct s2255_pipeinfo {
215 u32 max_transfer_size;
216 u32 cur_transfer_size;
217 u8 *transfer_buffer;
Dean Anderson38f993a2008-06-26 23:15:51 -0300218 u32 state;
Dean Anderson38f993a2008-06-26 23:15:51 -0300219 void *stream_urb;
220 void *dev; /* back pointer to s2255_dev struct*/
221 u32 err_count;
Dean Anderson38f993a2008-06-26 23:15:51 -0300222 u32 idx;
Dean Anderson38f993a2008-06-26 23:15:51 -0300223};
224
225struct s2255_fmt; /*forward declaration */
226
227struct s2255_dev {
228 int frames;
229 int users[MAX_CHANNELS];
230 struct mutex lock;
231 struct mutex open_lock;
232 int resources[MAX_CHANNELS];
233 struct usb_device *udev;
234 struct usb_interface *interface;
235 u8 read_endpoint;
236
237 struct s2255_dmaqueue vidq[MAX_CHANNELS];
238 struct video_device *vdev[MAX_CHANNELS];
Dean Anderson38f993a2008-06-26 23:15:51 -0300239 struct timer_list timer;
240 struct s2255_fw *fw_data;
Dean Anderson38f993a2008-06-26 23:15:51 -0300241 struct s2255_pipeinfo pipes[MAX_PIPE_BUFFERS];
242 struct s2255_bufferi buffer[MAX_CHANNELS];
243 struct s2255_mode mode[MAX_CHANNELS];
Dean Anderson22b88d42008-08-29 15:33:19 -0300244 /* jpeg compression */
245 struct v4l2_jpegcompression jc[MAX_CHANNELS];
Dean Anderson7d853532009-05-15 14:32:04 -0300246 /* capture parameters (for high quality mode full size) */
247 struct v4l2_captureparm cap_parm[MAX_CHANNELS];
Dean Anderson38f993a2008-06-26 23:15:51 -0300248 const struct s2255_fmt *cur_fmt[MAX_CHANNELS];
249 int cur_frame[MAX_CHANNELS];
250 int last_frame[MAX_CHANNELS];
251 u32 cc; /* current channel */
252 int b_acquire[MAX_CHANNELS];
Dean Anderson14d96262008-08-25 13:58:55 -0300253 /* allocated image size */
Dean Anderson38f993a2008-06-26 23:15:51 -0300254 unsigned long req_image_size[MAX_CHANNELS];
Dean Anderson14d96262008-08-25 13:58:55 -0300255 /* received packet size */
256 unsigned long pkt_size[MAX_CHANNELS];
Dean Anderson38f993a2008-06-26 23:15:51 -0300257 int bad_payload[MAX_CHANNELS];
258 unsigned long frame_count[MAX_CHANNELS];
259 int frame_ready;
Dean Anderson14d96262008-08-25 13:58:55 -0300260 /* if JPEG image */
261 int jpg_size[MAX_CHANNELS];
262 /* if channel configured to default state */
263 int chn_configured[MAX_CHANNELS];
264 wait_queue_head_t wait_setmode[MAX_CHANNELS];
265 int setmode_ready[MAX_CHANNELS];
Dean Anderson4de39f52010-03-03 19:39:19 -0300266 /* video status items */
267 int vidstatus[MAX_CHANNELS];
268 wait_queue_head_t wait_vidstatus[MAX_CHANNELS];
269 int vidstatus_ready[MAX_CHANNELS];
270
Dean Anderson14d96262008-08-25 13:58:55 -0300271 int chn_ready;
Dean Anderson38f993a2008-06-26 23:15:51 -0300272 struct kref kref;
273 spinlock_t slock;
Dean Anderson4de39f52010-03-03 19:39:19 -0300274 /* dsp firmware version (f2255usb.bin) */
275 int dsp_fw_ver;
Dean Anderson38f993a2008-06-26 23:15:51 -0300276};
277#define to_s2255_dev(d) container_of(d, struct s2255_dev, kref)
278
279struct s2255_fmt {
280 char *name;
281 u32 fourcc;
282 int depth;
283};
284
285/* buffer for one video frame */
286struct s2255_buffer {
287 /* common v4l buffer stuff -- must be first */
288 struct videobuf_buffer vb;
289 const struct s2255_fmt *fmt;
290};
291
292struct s2255_fh {
293 struct s2255_dev *dev;
Dean Anderson38f993a2008-06-26 23:15:51 -0300294 const struct s2255_fmt *fmt;
295 unsigned int width;
296 unsigned int height;
297 struct videobuf_queue vb_vidq;
298 enum v4l2_buf_type type;
299 int channel;
300 /* mode below is the desired mode.
301 mode in s2255_dev is the current mode that was last set */
302 struct s2255_mode mode;
Dean Andersonf78d92c2008-07-22 14:43:27 -0300303 int resources[MAX_CHANNELS];
Dean Anderson38f993a2008-06-26 23:15:51 -0300304};
305
Dean Andersonabce21f2009-04-23 16:04:41 -0300306/* current cypress EEPROM firmware version */
307#define S2255_CUR_USB_FWVER ((3 << 8) | 6)
Dean Anderson4de39f52010-03-03 19:39:19 -0300308/* current DSP FW version */
309#define S2255_CUR_DSP_FWVER 5
310/* Need DSP version 5+ for video status feature */
311#define S2255_MIN_DSP_STATUS 5
Dean Anderson38f993a2008-06-26 23:15:51 -0300312#define S2255_MAJOR_VERSION 1
Dean Anderson3fa00602010-03-04 20:47:33 -0300313#define S2255_MINOR_VERSION 16
Dean Anderson38f993a2008-06-26 23:15:51 -0300314#define S2255_RELEASE 0
315#define S2255_VERSION KERNEL_VERSION(S2255_MAJOR_VERSION, \
316 S2255_MINOR_VERSION, \
317 S2255_RELEASE)
318
319/* vendor ids */
320#define USB_S2255_VENDOR_ID 0x1943
321#define USB_S2255_PRODUCT_ID 0x2255
322#define S2255_NORMS (V4L2_STD_PAL | V4L2_STD_NTSC)
323/* frame prefix size (sent once every frame) */
324#define PREFIX_SIZE 512
325
326/* Channels on box are in reverse order */
Dean Anderson3f8d6f72008-06-30 21:28:34 -0300327static unsigned long G_chnmap[MAX_CHANNELS] = {3, 2, 1, 0};
Dean Anderson38f993a2008-06-26 23:15:51 -0300328
Dean Anderson38f993a2008-06-26 23:15:51 -0300329static int debug;
330static int *s2255_debug = &debug;
331
332static int s2255_start_readpipe(struct s2255_dev *dev);
333static void s2255_stop_readpipe(struct s2255_dev *dev);
334static int s2255_start_acquire(struct s2255_dev *dev, unsigned long chn);
335static int s2255_stop_acquire(struct s2255_dev *dev, unsigned long chn);
336static void s2255_fillbuff(struct s2255_dev *dev, struct s2255_buffer *buf,
Dean Anderson14d96262008-08-25 13:58:55 -0300337 int chn, int jpgsize);
Dean Anderson38f993a2008-06-26 23:15:51 -0300338static int s2255_set_mode(struct s2255_dev *dev, unsigned long chn,
339 struct s2255_mode *mode);
340static int s2255_board_shutdown(struct s2255_dev *dev);
341static void s2255_exit_v4l(struct s2255_dev *dev);
Dean Anderson14d96262008-08-25 13:58:55 -0300342static void s2255_fwload_start(struct s2255_dev *dev, int reset);
343static void s2255_destroy(struct kref *kref);
344static long s2255_vendor_req(struct s2255_dev *dev, unsigned char req,
345 u16 index, u16 value, void *buf,
346 s32 buf_len, int bOut);
Dean Anderson38f993a2008-06-26 23:15:51 -0300347
Mauro Carvalho Chehabbe9ed512009-01-08 09:13:42 -0300348/* dev_err macro with driver name */
349#define S2255_DRIVER_NAME "s2255"
350#define s2255_dev_err(dev, fmt, arg...) \
351 dev_err(dev, S2255_DRIVER_NAME " - " fmt, ##arg)
352
Dean Anderson38f993a2008-06-26 23:15:51 -0300353#define dprintk(level, fmt, arg...) \
354 do { \
355 if (*s2255_debug >= (level)) { \
Mauro Carvalho Chehabbe9ed512009-01-08 09:13:42 -0300356 printk(KERN_DEBUG S2255_DRIVER_NAME \
357 ": " fmt, ##arg); \
Dean Anderson38f993a2008-06-26 23:15:51 -0300358 } \
359 } while (0)
360
Dean Anderson38f993a2008-06-26 23:15:51 -0300361static struct usb_driver s2255_driver;
362
363
364/* Declare static vars that will be used as parameters */
365static unsigned int vid_limit = 16; /* Video memory limit, in Mb */
366
367/* start video number */
368static int video_nr = -1; /* /dev/videoN, -1 for autodetect */
369
Dean Anderson3f8d6f72008-06-30 21:28:34 -0300370module_param(debug, int, 0644);
Dean Anderson38f993a2008-06-26 23:15:51 -0300371MODULE_PARM_DESC(debug, "Debug level(0-100) default 0");
Dean Anderson3f8d6f72008-06-30 21:28:34 -0300372module_param(vid_limit, int, 0644);
Dean Anderson38f993a2008-06-26 23:15:51 -0300373MODULE_PARM_DESC(vid_limit, "video memory limit(Mb)");
Dean Anderson3f8d6f72008-06-30 21:28:34 -0300374module_param(video_nr, int, 0644);
Dean Anderson38f993a2008-06-26 23:15:51 -0300375MODULE_PARM_DESC(video_nr, "start video minor(-1 default autodetect)");
376
377/* USB device table */
378static struct usb_device_id s2255_table[] = {
379 {USB_DEVICE(USB_S2255_VENDOR_ID, USB_S2255_PRODUCT_ID)},
380 { } /* Terminating entry */
381};
382MODULE_DEVICE_TABLE(usb, s2255_table);
383
384
385#define BUFFER_TIMEOUT msecs_to_jiffies(400)
386
387/* supported controls */
388static struct v4l2_queryctrl s2255_qctrl[] = {
389 {
390 .id = V4L2_CID_BRIGHTNESS,
391 .type = V4L2_CTRL_TYPE_INTEGER,
392 .name = "Brightness",
393 .minimum = -127,
394 .maximum = 128,
395 .step = 1,
396 .default_value = 0,
397 .flags = 0,
398 }, {
399 .id = V4L2_CID_CONTRAST,
400 .type = V4L2_CTRL_TYPE_INTEGER,
401 .name = "Contrast",
402 .minimum = 0,
403 .maximum = 255,
404 .step = 0x1,
405 .default_value = DEF_CONTRAST,
406 .flags = 0,
407 }, {
408 .id = V4L2_CID_SATURATION,
409 .type = V4L2_CTRL_TYPE_INTEGER,
410 .name = "Saturation",
411 .minimum = 0,
412 .maximum = 255,
413 .step = 0x1,
414 .default_value = DEF_SATURATION,
415 .flags = 0,
416 }, {
417 .id = V4L2_CID_HUE,
418 .type = V4L2_CTRL_TYPE_INTEGER,
419 .name = "Hue",
420 .minimum = 0,
421 .maximum = 255,
422 .step = 0x1,
423 .default_value = DEF_HUE,
424 .flags = 0,
425 }
426};
427
428static int qctl_regs[ARRAY_SIZE(s2255_qctrl)];
429
430/* image formats. */
431static const struct s2255_fmt formats[] = {
432 {
433 .name = "4:2:2, planar, YUV422P",
434 .fourcc = V4L2_PIX_FMT_YUV422P,
435 .depth = 16
436
437 }, {
438 .name = "4:2:2, packed, YUYV",
439 .fourcc = V4L2_PIX_FMT_YUYV,
440 .depth = 16
441
442 }, {
443 .name = "4:2:2, packed, UYVY",
444 .fourcc = V4L2_PIX_FMT_UYVY,
445 .depth = 16
446 }, {
Dean Anderson14d96262008-08-25 13:58:55 -0300447 .name = "JPG",
448 .fourcc = V4L2_PIX_FMT_JPEG,
449 .depth = 24
450 }, {
Dean Anderson38f993a2008-06-26 23:15:51 -0300451 .name = "8bpp GREY",
452 .fourcc = V4L2_PIX_FMT_GREY,
453 .depth = 8
454 }
455};
456
457static int norm_maxw(struct video_device *vdev)
458{
459 return (vdev->current_norm & V4L2_STD_NTSC) ?
460 LINE_SZ_4CIFS_NTSC : LINE_SZ_4CIFS_PAL;
461}
462
463static int norm_maxh(struct video_device *vdev)
464{
465 return (vdev->current_norm & V4L2_STD_NTSC) ?
466 (NUM_LINES_1CIFS_NTSC * 2) : (NUM_LINES_1CIFS_PAL * 2);
467}
468
469static int norm_minw(struct video_device *vdev)
470{
471 return (vdev->current_norm & V4L2_STD_NTSC) ?
472 LINE_SZ_1CIFS_NTSC : LINE_SZ_1CIFS_PAL;
473}
474
475static int norm_minh(struct video_device *vdev)
476{
477 return (vdev->current_norm & V4L2_STD_NTSC) ?
478 (NUM_LINES_1CIFS_NTSC) : (NUM_LINES_1CIFS_PAL);
479}
480
481
Dean Anderson3f8d6f72008-06-30 21:28:34 -0300482/*
483 * TODO: fixme: move YUV reordering to hardware
484 * converts 2255 planar format to yuyv or uyvy
485 */
Dean Anderson38f993a2008-06-26 23:15:51 -0300486static void planar422p_to_yuv_packed(const unsigned char *in,
487 unsigned char *out,
488 int width, int height,
489 int fmt)
490{
491 unsigned char *pY;
492 unsigned char *pCb;
493 unsigned char *pCr;
494 unsigned long size = height * width;
495 unsigned int i;
496 pY = (unsigned char *)in;
497 pCr = (unsigned char *)in + height * width;
498 pCb = (unsigned char *)in + height * width + (height * width / 2);
499 for (i = 0; i < size * 2; i += 4) {
500 out[i] = (fmt == V4L2_PIX_FMT_YUYV) ? *pY++ : *pCr++;
501 out[i + 1] = (fmt == V4L2_PIX_FMT_YUYV) ? *pCr++ : *pY++;
502 out[i + 2] = (fmt == V4L2_PIX_FMT_YUYV) ? *pY++ : *pCb++;
503 out[i + 3] = (fmt == V4L2_PIX_FMT_YUYV) ? *pCb++ : *pY++;
504 }
505 return;
506}
507
Hans Verkuild45b9b82008-09-04 03:33:43 -0300508static void s2255_reset_dsppower(struct s2255_dev *dev)
Dean Anderson14d96262008-08-25 13:58:55 -0300509{
510 s2255_vendor_req(dev, 0x40, 0x0b0b, 0x0b0b, NULL, 0, 1);
511 msleep(10);
512 s2255_vendor_req(dev, 0x50, 0x0000, 0x0000, NULL, 0, 1);
513 return;
514}
Dean Anderson38f993a2008-06-26 23:15:51 -0300515
516/* kickstarts the firmware loading. from probe
517 */
518static void s2255_timer(unsigned long user_data)
519{
520 struct s2255_fw *data = (struct s2255_fw *)user_data;
521 dprintk(100, "s2255 timer\n");
522 if (usb_submit_urb(data->fw_urb, GFP_ATOMIC) < 0) {
523 printk(KERN_ERR "s2255: can't submit urb\n");
Dean Andersonf78d92c2008-07-22 14:43:27 -0300524 atomic_set(&data->fw_state, S2255_FW_FAILED);
525 /* wake up anything waiting for the firmware */
526 wake_up(&data->wait_fw);
Dean Anderson38f993a2008-06-26 23:15:51 -0300527 return;
528 }
529}
530
Dean Anderson38f993a2008-06-26 23:15:51 -0300531
532/* this loads the firmware asynchronously.
533 Originally this was done synchroously in probe.
534 But it is better to load it asynchronously here than block
535 inside the probe function. Blocking inside probe affects boot time.
536 FW loading is triggered by the timer in the probe function
537*/
538static void s2255_fwchunk_complete(struct urb *urb)
539{
540 struct s2255_fw *data = urb->context;
541 struct usb_device *udev = urb->dev;
542 int len;
543 dprintk(100, "udev %p urb %p", udev, urb);
Dean Anderson38f993a2008-06-26 23:15:51 -0300544 if (urb->status) {
Mauro Carvalho Chehabbe9ed512009-01-08 09:13:42 -0300545 dev_err(&udev->dev, "URB failed with status %d\n", urb->status);
Dean Andersonf78d92c2008-07-22 14:43:27 -0300546 atomic_set(&data->fw_state, S2255_FW_FAILED);
547 /* wake up anything waiting for the firmware */
548 wake_up(&data->wait_fw);
Dean Anderson38f993a2008-06-26 23:15:51 -0300549 return;
550 }
551 if (data->fw_urb == NULL) {
Mauro Carvalho Chehabbe9ed512009-01-08 09:13:42 -0300552 s2255_dev_err(&udev->dev, "disconnected\n");
Dean Andersonf78d92c2008-07-22 14:43:27 -0300553 atomic_set(&data->fw_state, S2255_FW_FAILED);
554 /* wake up anything waiting for the firmware */
555 wake_up(&data->wait_fw);
Dean Anderson38f993a2008-06-26 23:15:51 -0300556 return;
557 }
558#define CHUNK_SIZE 512
559 /* all USB transfers must be done with continuous kernel memory.
560 can't allocate more than 128k in current linux kernel, so
561 upload the firmware in chunks
562 */
563 if (data->fw_loaded < data->fw_size) {
564 len = (data->fw_loaded + CHUNK_SIZE) > data->fw_size ?
565 data->fw_size % CHUNK_SIZE : CHUNK_SIZE;
566
567 if (len < CHUNK_SIZE)
568 memset(data->pfw_data, 0, CHUNK_SIZE);
569
570 dprintk(100, "completed len %d, loaded %d \n", len,
571 data->fw_loaded);
572
573 memcpy(data->pfw_data,
574 (char *) data->fw->data + data->fw_loaded, len);
575
576 usb_fill_bulk_urb(data->fw_urb, udev, usb_sndbulkpipe(udev, 2),
577 data->pfw_data, CHUNK_SIZE,
578 s2255_fwchunk_complete, data);
579 if (usb_submit_urb(data->fw_urb, GFP_ATOMIC) < 0) {
580 dev_err(&udev->dev, "failed submit URB\n");
581 atomic_set(&data->fw_state, S2255_FW_FAILED);
582 /* wake up anything waiting for the firmware */
583 wake_up(&data->wait_fw);
584 return;
585 }
586 data->fw_loaded += len;
587 } else {
Dean Anderson38f993a2008-06-26 23:15:51 -0300588 atomic_set(&data->fw_state, S2255_FW_LOADED_DSPWAIT);
Dean Anderson38f993a2008-06-26 23:15:51 -0300589 }
590 dprintk(100, "2255 complete done\n");
591 return;
592
593}
594
Dean Anderson14d96262008-08-25 13:58:55 -0300595static int s2255_got_frame(struct s2255_dev *dev, int chn, int jpgsize)
Dean Anderson38f993a2008-06-26 23:15:51 -0300596{
597 struct s2255_dmaqueue *dma_q = &dev->vidq[chn];
598 struct s2255_buffer *buf;
599 unsigned long flags = 0;
600 int rc = 0;
601 dprintk(2, "wakeup: %p channel: %d\n", &dma_q, chn);
602 spin_lock_irqsave(&dev->slock, flags);
603
604 if (list_empty(&dma_q->active)) {
605 dprintk(1, "No active queue to serve\n");
606 rc = -1;
607 goto unlock;
608 }
609 buf = list_entry(dma_q->active.next,
610 struct s2255_buffer, vb.queue);
611
Dean Anderson38f993a2008-06-26 23:15:51 -0300612 list_del(&buf->vb.queue);
613 do_gettimeofday(&buf->vb.ts);
614 dprintk(100, "[%p/%d] wakeup\n", buf, buf->vb.i);
Dean Anderson14d96262008-08-25 13:58:55 -0300615 s2255_fillbuff(dev, buf, dma_q->channel, jpgsize);
Dean Anderson38f993a2008-06-26 23:15:51 -0300616 wake_up(&buf->vb.done);
617 dprintk(2, "wakeup [buf/i] [%p/%d]\n", buf, buf->vb.i);
618unlock:
619 spin_unlock_irqrestore(&dev->slock, flags);
620 return 0;
621}
622
623
624static const struct s2255_fmt *format_by_fourcc(int fourcc)
625{
626 unsigned int i;
627
628 for (i = 0; i < ARRAY_SIZE(formats); i++) {
629 if (-1 == formats[i].fourcc)
630 continue;
631 if (formats[i].fourcc == fourcc)
632 return formats + i;
633 }
634 return NULL;
635}
636
637
638
639
640/* video buffer vmalloc implementation based partly on VIVI driver which is
641 * Copyright (c) 2006 by
642 * Mauro Carvalho Chehab <mchehab--a.t--infradead.org>
643 * Ted Walther <ted--a.t--enumera.com>
644 * John Sokol <sokol--a.t--videotechnology.com>
645 * http://v4l.videotechnology.com/
646 *
647 */
648static void s2255_fillbuff(struct s2255_dev *dev, struct s2255_buffer *buf,
Dean Anderson14d96262008-08-25 13:58:55 -0300649 int chn, int jpgsize)
Dean Anderson38f993a2008-06-26 23:15:51 -0300650{
651 int pos = 0;
652 struct timeval ts;
653 const char *tmpbuf;
654 char *vbuf = videobuf_to_vmalloc(&buf->vb);
655 unsigned long last_frame;
656 struct s2255_framei *frm;
657
658 if (!vbuf)
659 return;
660
661 last_frame = dev->last_frame[chn];
662 if (last_frame != -1) {
663 frm = &dev->buffer[chn].frame[last_frame];
664 tmpbuf =
665 (const char *)dev->buffer[chn].frame[last_frame].lpvbits;
666 switch (buf->fmt->fourcc) {
667 case V4L2_PIX_FMT_YUYV:
668 case V4L2_PIX_FMT_UYVY:
669 planar422p_to_yuv_packed((const unsigned char *)tmpbuf,
670 vbuf, buf->vb.width,
671 buf->vb.height,
672 buf->fmt->fourcc);
673 break;
674 case V4L2_PIX_FMT_GREY:
675 memcpy(vbuf, tmpbuf, buf->vb.width * buf->vb.height);
676 break;
Dean Anderson14d96262008-08-25 13:58:55 -0300677 case V4L2_PIX_FMT_JPEG:
678 buf->vb.size = jpgsize;
679 memcpy(vbuf, tmpbuf, buf->vb.size);
680 break;
Dean Anderson38f993a2008-06-26 23:15:51 -0300681 case V4L2_PIX_FMT_YUV422P:
682 memcpy(vbuf, tmpbuf,
683 buf->vb.width * buf->vb.height * 2);
684 break;
685 default:
686 printk(KERN_DEBUG "s2255: unknown format?\n");
687 }
688 dev->last_frame[chn] = -1;
Dean Anderson38f993a2008-06-26 23:15:51 -0300689 } else {
690 printk(KERN_ERR "s2255: =======no frame\n");
691 return;
692
693 }
694 dprintk(2, "s2255fill at : Buffer 0x%08lx size= %d\n",
695 (unsigned long)vbuf, pos);
696 /* tell v4l buffer was filled */
697
Dean Andersona1c45302008-09-09 12:29:56 -0300698 buf->vb.field_count = dev->frame_count[chn] * 2;
Dean Anderson38f993a2008-06-26 23:15:51 -0300699 do_gettimeofday(&ts);
700 buf->vb.ts = ts;
701 buf->vb.state = VIDEOBUF_DONE;
702}
703
704
705/* ------------------------------------------------------------------
706 Videobuf operations
707 ------------------------------------------------------------------*/
708
709static int buffer_setup(struct videobuf_queue *vq, unsigned int *count,
710 unsigned int *size)
711{
712 struct s2255_fh *fh = vq->priv_data;
713
714 *size = fh->width * fh->height * (fh->fmt->depth >> 3);
715
716 if (0 == *count)
717 *count = S2255_DEF_BUFS;
718
Dean Anderson3f8d6f72008-06-30 21:28:34 -0300719 while (*size * (*count) > vid_limit * 1024 * 1024)
Dean Anderson38f993a2008-06-26 23:15:51 -0300720 (*count)--;
721
722 return 0;
723}
724
725static void free_buffer(struct videobuf_queue *vq, struct s2255_buffer *buf)
726{
727 dprintk(4, "%s\n", __func__);
728
Dean Anderson38f993a2008-06-26 23:15:51 -0300729 videobuf_vmalloc_free(&buf->vb);
730 buf->vb.state = VIDEOBUF_NEEDS_INIT;
731}
732
733static int buffer_prepare(struct videobuf_queue *vq, struct videobuf_buffer *vb,
734 enum v4l2_field field)
735{
736 struct s2255_fh *fh = vq->priv_data;
737 struct s2255_buffer *buf = container_of(vb, struct s2255_buffer, vb);
738 int rc;
739 dprintk(4, "%s, field=%d\n", __func__, field);
740 if (fh->fmt == NULL)
741 return -EINVAL;
742
743 if ((fh->width < norm_minw(fh->dev->vdev[fh->channel])) ||
744 (fh->width > norm_maxw(fh->dev->vdev[fh->channel])) ||
745 (fh->height < norm_minh(fh->dev->vdev[fh->channel])) ||
746 (fh->height > norm_maxh(fh->dev->vdev[fh->channel]))) {
747 dprintk(4, "invalid buffer prepare\n");
748 return -EINVAL;
749 }
750
751 buf->vb.size = fh->width * fh->height * (fh->fmt->depth >> 3);
752
753 if (0 != buf->vb.baddr && buf->vb.bsize < buf->vb.size) {
754 dprintk(4, "invalid buffer prepare\n");
755 return -EINVAL;
756 }
757
758 buf->fmt = fh->fmt;
759 buf->vb.width = fh->width;
760 buf->vb.height = fh->height;
761 buf->vb.field = field;
762
763
764 if (VIDEOBUF_NEEDS_INIT == buf->vb.state) {
765 rc = videobuf_iolock(vq, &buf->vb, NULL);
766 if (rc < 0)
767 goto fail;
768 }
769
770 buf->vb.state = VIDEOBUF_PREPARED;
771 return 0;
772fail:
773 free_buffer(vq, buf);
774 return rc;
775}
776
777static void buffer_queue(struct videobuf_queue *vq, struct videobuf_buffer *vb)
778{
779 struct s2255_buffer *buf = container_of(vb, struct s2255_buffer, vb);
780 struct s2255_fh *fh = vq->priv_data;
781 struct s2255_dev *dev = fh->dev;
782 struct s2255_dmaqueue *vidq = &dev->vidq[fh->channel];
783
784 dprintk(1, "%s\n", __func__);
785
786 buf->vb.state = VIDEOBUF_QUEUED;
787 list_add_tail(&buf->vb.queue, &vidq->active);
788}
789
790static void buffer_release(struct videobuf_queue *vq,
791 struct videobuf_buffer *vb)
792{
793 struct s2255_buffer *buf = container_of(vb, struct s2255_buffer, vb);
794 struct s2255_fh *fh = vq->priv_data;
795 dprintk(4, "%s %d\n", __func__, fh->channel);
796 free_buffer(vq, buf);
797}
798
799static struct videobuf_queue_ops s2255_video_qops = {
800 .buf_setup = buffer_setup,
801 .buf_prepare = buffer_prepare,
802 .buf_queue = buffer_queue,
803 .buf_release = buffer_release,
804};
805
806
807static int res_get(struct s2255_dev *dev, struct s2255_fh *fh)
808{
809 /* is it free? */
810 mutex_lock(&dev->lock);
811 if (dev->resources[fh->channel]) {
812 /* no, someone else uses it */
813 mutex_unlock(&dev->lock);
814 return 0;
815 }
816 /* it's free, grab it */
817 dev->resources[fh->channel] = 1;
Dean Andersonf78d92c2008-07-22 14:43:27 -0300818 fh->resources[fh->channel] = 1;
819 dprintk(1, "s2255: res: get\n");
Dean Anderson38f993a2008-06-26 23:15:51 -0300820 mutex_unlock(&dev->lock);
821 return 1;
822}
823
824static int res_locked(struct s2255_dev *dev, struct s2255_fh *fh)
825{
Dean Anderson3f8d6f72008-06-30 21:28:34 -0300826 return dev->resources[fh->channel];
Dean Anderson38f993a2008-06-26 23:15:51 -0300827}
828
Dean Andersonf78d92c2008-07-22 14:43:27 -0300829static int res_check(struct s2255_fh *fh)
830{
831 return fh->resources[fh->channel];
832}
833
834
Dean Anderson38f993a2008-06-26 23:15:51 -0300835static void res_free(struct s2255_dev *dev, struct s2255_fh *fh)
836{
Dean Andersonf78d92c2008-07-22 14:43:27 -0300837 mutex_lock(&dev->lock);
Dean Anderson38f993a2008-06-26 23:15:51 -0300838 dev->resources[fh->channel] = 0;
Dean Andersonf78d92c2008-07-22 14:43:27 -0300839 fh->resources[fh->channel] = 0;
840 mutex_unlock(&dev->lock);
Dean Anderson38f993a2008-06-26 23:15:51 -0300841 dprintk(1, "res: put\n");
842}
843
844
845static int vidioc_querycap(struct file *file, void *priv,
846 struct v4l2_capability *cap)
847{
848 struct s2255_fh *fh = file->private_data;
849 struct s2255_dev *dev = fh->dev;
850 strlcpy(cap->driver, "s2255", sizeof(cap->driver));
851 strlcpy(cap->card, "s2255", sizeof(cap->card));
Thierry MERLEe22ed882009-01-20 18:19:25 -0300852 usb_make_path(dev->udev, cap->bus_info, sizeof(cap->bus_info));
Dean Anderson38f993a2008-06-26 23:15:51 -0300853 cap->version = S2255_VERSION;
854 cap->capabilities = V4L2_CAP_VIDEO_CAPTURE | V4L2_CAP_STREAMING;
855 return 0;
856}
857
858static int vidioc_enum_fmt_vid_cap(struct file *file, void *priv,
859 struct v4l2_fmtdesc *f)
860{
861 int index = 0;
862 if (f)
863 index = f->index;
864
865 if (index >= ARRAY_SIZE(formats))
866 return -EINVAL;
867
868 dprintk(4, "name %s\n", formats[index].name);
869 strlcpy(f->description, formats[index].name, sizeof(f->description));
870 f->pixelformat = formats[index].fourcc;
871 return 0;
872}
873
874static int vidioc_g_fmt_vid_cap(struct file *file, void *priv,
875 struct v4l2_format *f)
876{
877 struct s2255_fh *fh = priv;
878
879 f->fmt.pix.width = fh->width;
880 f->fmt.pix.height = fh->height;
881 f->fmt.pix.field = fh->vb_vidq.field;
882 f->fmt.pix.pixelformat = fh->fmt->fourcc;
883 f->fmt.pix.bytesperline = f->fmt.pix.width * (fh->fmt->depth >> 3);
884 f->fmt.pix.sizeimage = f->fmt.pix.height * f->fmt.pix.bytesperline;
Dean Anderson3f8d6f72008-06-30 21:28:34 -0300885 return 0;
Dean Anderson38f993a2008-06-26 23:15:51 -0300886}
887
888static int vidioc_try_fmt_vid_cap(struct file *file, void *priv,
889 struct v4l2_format *f)
890{
891 const struct s2255_fmt *fmt;
892 enum v4l2_field field;
893 int b_any_field = 0;
894 struct s2255_fh *fh = priv;
895 struct s2255_dev *dev = fh->dev;
896 int is_ntsc;
897
898 is_ntsc =
899 (dev->vdev[fh->channel]->current_norm & V4L2_STD_NTSC) ? 1 : 0;
900
901 fmt = format_by_fourcc(f->fmt.pix.pixelformat);
902
903 if (fmt == NULL)
904 return -EINVAL;
905
906 field = f->fmt.pix.field;
907 if (field == V4L2_FIELD_ANY)
908 b_any_field = 1;
909
910 dprintk(4, "try format %d \n", is_ntsc);
911 /* supports 3 sizes. see s2255drv.h */
912 dprintk(50, "width test %d, height %d\n",
913 f->fmt.pix.width, f->fmt.pix.height);
914 if (is_ntsc) {
915 /* NTSC */
916 if (f->fmt.pix.height >= NUM_LINES_1CIFS_NTSC * 2) {
917 f->fmt.pix.height = NUM_LINES_1CIFS_NTSC * 2;
918 if (b_any_field) {
919 field = V4L2_FIELD_SEQ_TB;
920 } else if (!((field == V4L2_FIELD_INTERLACED) ||
921 (field == V4L2_FIELD_SEQ_TB) ||
922 (field == V4L2_FIELD_INTERLACED_TB))) {
923 dprintk(1, "unsupported field setting\n");
924 return -EINVAL;
925 }
926 } else {
927 f->fmt.pix.height = NUM_LINES_1CIFS_NTSC;
928 if (b_any_field) {
929 field = V4L2_FIELD_TOP;
930 } else if (!((field == V4L2_FIELD_TOP) ||
931 (field == V4L2_FIELD_BOTTOM))) {
932 dprintk(1, "unsupported field setting\n");
933 return -EINVAL;
934 }
935
936 }
937 if (f->fmt.pix.width >= LINE_SZ_4CIFS_NTSC)
938 f->fmt.pix.width = LINE_SZ_4CIFS_NTSC;
939 else if (f->fmt.pix.width >= LINE_SZ_2CIFS_NTSC)
940 f->fmt.pix.width = LINE_SZ_2CIFS_NTSC;
941 else if (f->fmt.pix.width >= LINE_SZ_1CIFS_NTSC)
942 f->fmt.pix.width = LINE_SZ_1CIFS_NTSC;
943 else
944 f->fmt.pix.width = LINE_SZ_1CIFS_NTSC;
945 } else {
946 /* PAL */
947 if (f->fmt.pix.height >= NUM_LINES_1CIFS_PAL * 2) {
948 f->fmt.pix.height = NUM_LINES_1CIFS_PAL * 2;
949 if (b_any_field) {
950 field = V4L2_FIELD_SEQ_TB;
951 } else if (!((field == V4L2_FIELD_INTERLACED) ||
952 (field == V4L2_FIELD_SEQ_TB) ||
953 (field == V4L2_FIELD_INTERLACED_TB))) {
954 dprintk(1, "unsupported field setting\n");
955 return -EINVAL;
956 }
957 } else {
958 f->fmt.pix.height = NUM_LINES_1CIFS_PAL;
959 if (b_any_field) {
960 field = V4L2_FIELD_TOP;
961 } else if (!((field == V4L2_FIELD_TOP) ||
962 (field == V4L2_FIELD_BOTTOM))) {
963 dprintk(1, "unsupported field setting\n");
964 return -EINVAL;
965 }
966 }
967 if (f->fmt.pix.width >= LINE_SZ_4CIFS_PAL) {
968 dprintk(50, "pal 704\n");
969 f->fmt.pix.width = LINE_SZ_4CIFS_PAL;
970 field = V4L2_FIELD_SEQ_TB;
971 } else if (f->fmt.pix.width >= LINE_SZ_2CIFS_PAL) {
972 dprintk(50, "pal 352A\n");
973 f->fmt.pix.width = LINE_SZ_2CIFS_PAL;
974 field = V4L2_FIELD_TOP;
975 } else if (f->fmt.pix.width >= LINE_SZ_1CIFS_PAL) {
976 dprintk(50, "pal 352B\n");
977 f->fmt.pix.width = LINE_SZ_1CIFS_PAL;
978 field = V4L2_FIELD_TOP;
979 } else {
980 dprintk(50, "pal 352C\n");
981 f->fmt.pix.width = LINE_SZ_1CIFS_PAL;
982 field = V4L2_FIELD_TOP;
983 }
984 }
985
986 dprintk(50, "width %d height %d field %d \n", f->fmt.pix.width,
987 f->fmt.pix.height, f->fmt.pix.field);
988 f->fmt.pix.field = field;
989 f->fmt.pix.bytesperline = (f->fmt.pix.width * fmt->depth) >> 3;
990 f->fmt.pix.sizeimage = f->fmt.pix.height * f->fmt.pix.bytesperline;
991 return 0;
992}
993
994static int vidioc_s_fmt_vid_cap(struct file *file, void *priv,
995 struct v4l2_format *f)
996{
997 struct s2255_fh *fh = priv;
998 const struct s2255_fmt *fmt;
999 struct videobuf_queue *q = &fh->vb_vidq;
1000 int ret;
1001 int norm;
1002
1003 ret = vidioc_try_fmt_vid_cap(file, fh, f);
1004
1005 if (ret < 0)
Dean Anderson3f8d6f72008-06-30 21:28:34 -03001006 return ret;
Dean Anderson38f993a2008-06-26 23:15:51 -03001007
1008 fmt = format_by_fourcc(f->fmt.pix.pixelformat);
1009
1010 if (fmt == NULL)
1011 return -EINVAL;
1012
1013 mutex_lock(&q->vb_lock);
1014
1015 if (videobuf_queue_is_busy(&fh->vb_vidq)) {
1016 dprintk(1, "queue busy\n");
1017 ret = -EBUSY;
1018 goto out_s_fmt;
1019 }
1020
1021 if (res_locked(fh->dev, fh)) {
1022 dprintk(1, "can't change format after started\n");
1023 ret = -EBUSY;
1024 goto out_s_fmt;
1025 }
1026
1027 fh->fmt = fmt;
1028 fh->width = f->fmt.pix.width;
1029 fh->height = f->fmt.pix.height;
1030 fh->vb_vidq.field = f->fmt.pix.field;
1031 fh->type = f->type;
1032 norm = norm_minw(fh->dev->vdev[fh->channel]);
1033 if (fh->width > norm_minw(fh->dev->vdev[fh->channel])) {
Dean Anderson7d853532009-05-15 14:32:04 -03001034 if (fh->height > norm_minh(fh->dev->vdev[fh->channel])) {
1035 if (fh->dev->cap_parm[fh->channel].capturemode &
1036 V4L2_MODE_HIGHQUALITY) {
1037 fh->mode.scale = SCALE_4CIFSI;
1038 dprintk(2, "scale 4CIFSI\n");
1039 } else {
1040 fh->mode.scale = SCALE_4CIFS;
1041 dprintk(2, "scale 4CIFS\n");
1042 }
1043 } else
Dean Anderson38f993a2008-06-26 23:15:51 -03001044 fh->mode.scale = SCALE_2CIFS;
1045
1046 } else {
1047 fh->mode.scale = SCALE_1CIFS;
1048 }
1049
1050 /* color mode */
1051 switch (fh->fmt->fourcc) {
1052 case V4L2_PIX_FMT_GREY:
1053 fh->mode.color = COLOR_Y8;
1054 break;
Dean Anderson14d96262008-08-25 13:58:55 -03001055 case V4L2_PIX_FMT_JPEG:
Dean Anderson22b88d42008-08-29 15:33:19 -03001056 fh->mode.color = COLOR_JPG |
1057 (fh->dev->jc[fh->channel].quality << 8);
Dean Anderson14d96262008-08-25 13:58:55 -03001058 break;
Dean Anderson38f993a2008-06-26 23:15:51 -03001059 case V4L2_PIX_FMT_YUV422P:
1060 fh->mode.color = COLOR_YUVPL;
1061 break;
1062 case V4L2_PIX_FMT_YUYV:
1063 case V4L2_PIX_FMT_UYVY:
1064 default:
1065 fh->mode.color = COLOR_YUVPK;
1066 break;
1067 }
1068 ret = 0;
1069out_s_fmt:
1070 mutex_unlock(&q->vb_lock);
1071 return ret;
1072}
1073
1074static int vidioc_reqbufs(struct file *file, void *priv,
1075 struct v4l2_requestbuffers *p)
1076{
1077 int rc;
1078 struct s2255_fh *fh = priv;
1079 rc = videobuf_reqbufs(&fh->vb_vidq, p);
1080 return rc;
1081}
1082
1083static int vidioc_querybuf(struct file *file, void *priv, struct v4l2_buffer *p)
1084{
1085 int rc;
1086 struct s2255_fh *fh = priv;
1087 rc = videobuf_querybuf(&fh->vb_vidq, p);
1088 return rc;
1089}
1090
1091static int vidioc_qbuf(struct file *file, void *priv, struct v4l2_buffer *p)
1092{
1093 int rc;
1094 struct s2255_fh *fh = priv;
1095 rc = videobuf_qbuf(&fh->vb_vidq, p);
1096 return rc;
1097}
1098
1099static int vidioc_dqbuf(struct file *file, void *priv, struct v4l2_buffer *p)
1100{
1101 int rc;
1102 struct s2255_fh *fh = priv;
1103 rc = videobuf_dqbuf(&fh->vb_vidq, p, file->f_flags & O_NONBLOCK);
1104 return rc;
1105}
1106
1107#ifdef CONFIG_VIDEO_V4L1_COMPAT
1108static int vidioc_cgmbuf(struct file *file, void *priv, struct video_mbuf *mbuf)
1109{
1110 struct s2255_fh *fh = priv;
1111
1112 return videobuf_cgmbuf(&fh->vb_vidq, mbuf, 8);
1113}
1114#endif
1115
1116/* write to the configuration pipe, synchronously */
1117static int s2255_write_config(struct usb_device *udev, unsigned char *pbuf,
1118 int size)
1119{
1120 int pipe;
1121 int done;
1122 long retval = -1;
1123 if (udev) {
1124 pipe = usb_sndbulkpipe(udev, S2255_CONFIG_EP);
1125 retval = usb_bulk_msg(udev, pipe, pbuf, size, &done, 500);
1126 }
1127 return retval;
1128}
1129
1130static u32 get_transfer_size(struct s2255_mode *mode)
1131{
1132 int linesPerFrame = LINE_SZ_DEF;
1133 int pixelsPerLine = NUM_LINES_DEF;
1134 u32 outImageSize;
1135 u32 usbInSize;
1136 unsigned int mask_mult;
1137
1138 if (mode == NULL)
1139 return 0;
1140
1141 if (mode->format == FORMAT_NTSC) {
1142 switch (mode->scale) {
1143 case SCALE_4CIFS:
Dean Anderson7d853532009-05-15 14:32:04 -03001144 case SCALE_4CIFSI:
Dean Anderson38f993a2008-06-26 23:15:51 -03001145 linesPerFrame = NUM_LINES_4CIFS_NTSC * 2;
1146 pixelsPerLine = LINE_SZ_4CIFS_NTSC;
1147 break;
1148 case SCALE_2CIFS:
1149 linesPerFrame = NUM_LINES_2CIFS_NTSC;
1150 pixelsPerLine = LINE_SZ_2CIFS_NTSC;
1151 break;
1152 case SCALE_1CIFS:
1153 linesPerFrame = NUM_LINES_1CIFS_NTSC;
1154 pixelsPerLine = LINE_SZ_1CIFS_NTSC;
1155 break;
1156 default:
1157 break;
1158 }
1159 } else if (mode->format == FORMAT_PAL) {
1160 switch (mode->scale) {
1161 case SCALE_4CIFS:
Dean Anderson7d853532009-05-15 14:32:04 -03001162 case SCALE_4CIFSI:
Dean Anderson38f993a2008-06-26 23:15:51 -03001163 linesPerFrame = NUM_LINES_4CIFS_PAL * 2;
1164 pixelsPerLine = LINE_SZ_4CIFS_PAL;
1165 break;
1166 case SCALE_2CIFS:
1167 linesPerFrame = NUM_LINES_2CIFS_PAL;
1168 pixelsPerLine = LINE_SZ_2CIFS_PAL;
1169 break;
1170 case SCALE_1CIFS:
1171 linesPerFrame = NUM_LINES_1CIFS_PAL;
1172 pixelsPerLine = LINE_SZ_1CIFS_PAL;
1173 break;
1174 default:
1175 break;
1176 }
1177 }
1178 outImageSize = linesPerFrame * pixelsPerLine;
Dean Anderson14d96262008-08-25 13:58:55 -03001179 if ((mode->color & MASK_COLOR) != COLOR_Y8) {
Dean Anderson38f993a2008-06-26 23:15:51 -03001180 /* 2 bytes/pixel if not monochrome */
1181 outImageSize *= 2;
1182 }
1183
1184 /* total bytes to send including prefix and 4K padding;
1185 must be a multiple of USB_READ_SIZE */
1186 usbInSize = outImageSize + PREFIX_SIZE; /* always send prefix */
1187 mask_mult = 0xffffffffUL - DEF_USB_BLOCK + 1;
1188 /* if size not a multiple of USB_READ_SIZE */
1189 if (usbInSize & ~mask_mult)
1190 usbInSize = (usbInSize & mask_mult) + (DEF_USB_BLOCK);
1191 return usbInSize;
1192}
1193
1194static void dump_verify_mode(struct s2255_dev *sdev, struct s2255_mode *mode)
1195{
1196 struct device *dev = &sdev->udev->dev;
1197 dev_info(dev, "------------------------------------------------\n");
1198 dev_info(dev, "verify mode\n");
1199 dev_info(dev, "format: %d\n", mode->format);
1200 dev_info(dev, "scale: %d\n", mode->scale);
1201 dev_info(dev, "fdec: %d\n", mode->fdec);
1202 dev_info(dev, "color: %d\n", mode->color);
1203 dev_info(dev, "bright: 0x%x\n", mode->bright);
1204 dev_info(dev, "restart: 0x%x\n", mode->restart);
1205 dev_info(dev, "usb_block: 0x%x\n", mode->usb_block);
1206 dev_info(dev, "single: 0x%x\n", mode->single);
1207 dev_info(dev, "------------------------------------------------\n");
1208}
1209
1210/*
1211 * set mode is the function which controls the DSP.
1212 * the restart parameter in struct s2255_mode should be set whenever
1213 * the image size could change via color format, video system or image
1214 * size.
1215 * When the restart parameter is set, we sleep for ONE frame to allow the
1216 * DSP time to get the new frame
1217 */
1218static int s2255_set_mode(struct s2255_dev *dev, unsigned long chn,
1219 struct s2255_mode *mode)
1220{
1221 int res;
Dean Anderson3fa00602010-03-04 20:47:33 -03001222 __le32 *buffer;
Dean Anderson38f993a2008-06-26 23:15:51 -03001223 unsigned long chn_rev;
Dean Anderson14d96262008-08-25 13:58:55 -03001224 mutex_lock(&dev->lock);
Dean Anderson38f993a2008-06-26 23:15:51 -03001225 chn_rev = G_chnmap[chn];
1226 dprintk(3, "mode scale [%ld] %p %d\n", chn, mode, mode->scale);
1227 dprintk(3, "mode scale [%ld] %p %d\n", chn, &dev->mode[chn],
1228 dev->mode[chn].scale);
1229 dprintk(2, "mode contrast %x\n", mode->contrast);
1230
Dean Anderson22b88d42008-08-29 15:33:19 -03001231 /* if JPEG, set the quality */
1232 if ((mode->color & MASK_COLOR) == COLOR_JPG)
1233 mode->color = (dev->jc[chn].quality << 8) | COLOR_JPG;
1234
Dean Anderson38f993a2008-06-26 23:15:51 -03001235 /* save the mode */
1236 dev->mode[chn] = *mode;
1237 dev->req_image_size[chn] = get_transfer_size(mode);
1238 dprintk(1, "transfer size %ld\n", dev->req_image_size[chn]);
1239
1240 buffer = kzalloc(512, GFP_KERNEL);
1241 if (buffer == NULL) {
1242 dev_err(&dev->udev->dev, "out of mem\n");
Dean Anderson14d96262008-08-25 13:58:55 -03001243 mutex_unlock(&dev->lock);
Dean Anderson38f993a2008-06-26 23:15:51 -03001244 return -ENOMEM;
1245 }
1246
1247 /* set the mode */
1248 buffer[0] = IN_DATA_TOKEN;
Dean Anderson3fa00602010-03-04 20:47:33 -03001249 buffer[1] = (__le32) cpu_to_le32(chn_rev);
Dean Anderson38f993a2008-06-26 23:15:51 -03001250 buffer[2] = CMD_SET_MODE;
1251 memcpy(&buffer[3], &dev->mode[chn], sizeof(struct s2255_mode));
Dean Anderson9d63cec2009-04-20 19:07:44 -03001252 dev->setmode_ready[chn] = 0;
Dean Anderson38f993a2008-06-26 23:15:51 -03001253 res = s2255_write_config(dev->udev, (unsigned char *)buffer, 512);
1254 if (debug)
1255 dump_verify_mode(dev, mode);
1256 kfree(buffer);
1257 dprintk(1, "set mode done chn %lu, %d\n", chn, res);
1258
1259 /* wait at least 3 frames before continuing */
Dean Anderson14d96262008-08-25 13:58:55 -03001260 if (mode->restart) {
Dean Anderson14d96262008-08-25 13:58:55 -03001261 wait_event_timeout(dev->wait_setmode[chn],
1262 (dev->setmode_ready[chn] != 0),
1263 msecs_to_jiffies(S2255_SETMODE_TIMEOUT));
1264 if (dev->setmode_ready[chn] != 1) {
1265 printk(KERN_DEBUG "s2255: no set mode response\n");
1266 res = -EFAULT;
1267 }
1268 }
Dean Anderson38f993a2008-06-26 23:15:51 -03001269
1270 /* clear the restart flag */
1271 dev->mode[chn].restart = 0;
Dean Anderson14d96262008-08-25 13:58:55 -03001272 mutex_unlock(&dev->lock);
Dean Anderson38f993a2008-06-26 23:15:51 -03001273 return res;
1274}
1275
Dean Anderson4de39f52010-03-03 19:39:19 -03001276static int s2255_cmd_status(struct s2255_dev *dev, unsigned long chn,
1277 u32 *pstatus)
1278{
1279 int res;
Dean Anderson3fa00602010-03-04 20:47:33 -03001280 __le32 *buffer;
Dean Anderson4de39f52010-03-03 19:39:19 -03001281 u32 chn_rev;
1282 mutex_lock(&dev->lock);
1283 chn_rev = G_chnmap[chn];
1284 dprintk(4, "%s chan %d\n", __func__, chn_rev);
1285 buffer = kzalloc(512, GFP_KERNEL);
1286 if (buffer == NULL) {
1287 dev_err(&dev->udev->dev, "out of mem\n");
1288 mutex_unlock(&dev->lock);
1289 return -ENOMEM;
1290 }
1291 /* form the get vid status command */
1292 buffer[0] = IN_DATA_TOKEN;
Dean Anderson3fa00602010-03-04 20:47:33 -03001293 buffer[1] = (__le32) cpu_to_le32(chn_rev);
Dean Anderson4de39f52010-03-03 19:39:19 -03001294 buffer[2] = CMD_STATUS;
1295 *pstatus = 0;
1296 dev->vidstatus_ready[chn] = 0;
1297 res = s2255_write_config(dev->udev, (unsigned char *)buffer, 512);
1298 kfree(buffer);
1299 wait_event_timeout(dev->wait_vidstatus[chn],
1300 (dev->vidstatus_ready[chn] != 0),
1301 msecs_to_jiffies(S2255_VIDSTATUS_TIMEOUT));
1302 if (dev->vidstatus_ready[chn] != 1) {
1303 printk(KERN_DEBUG "s2255: no vidstatus response\n");
1304 res = -EFAULT;
1305 }
1306 *pstatus = dev->vidstatus[chn];
1307 dprintk(4, "%s, vid status %d\n", __func__, *pstatus);
1308 mutex_unlock(&dev->lock);
1309 return res;
1310}
1311
Dean Anderson38f993a2008-06-26 23:15:51 -03001312static int vidioc_streamon(struct file *file, void *priv, enum v4l2_buf_type i)
1313{
1314 int res;
1315 struct s2255_fh *fh = priv;
1316 struct s2255_dev *dev = fh->dev;
1317 struct s2255_mode *new_mode;
1318 struct s2255_mode *old_mode;
1319 int chn;
1320 int j;
1321 dprintk(4, "%s\n", __func__);
1322 if (fh->type != V4L2_BUF_TYPE_VIDEO_CAPTURE) {
1323 dev_err(&dev->udev->dev, "invalid fh type0\n");
1324 return -EINVAL;
1325 }
1326 if (i != fh->type) {
1327 dev_err(&dev->udev->dev, "invalid fh type1\n");
1328 return -EINVAL;
1329 }
1330
1331 if (!res_get(dev, fh)) {
Mauro Carvalho Chehabbe9ed512009-01-08 09:13:42 -03001332 s2255_dev_err(&dev->udev->dev, "stream busy\n");
Dean Anderson38f993a2008-06-26 23:15:51 -03001333 return -EBUSY;
1334 }
1335
1336 /* send a set mode command everytime with restart.
1337 in case we switch resolutions or other parameters */
1338 chn = fh->channel;
1339 new_mode = &fh->mode;
1340 old_mode = &fh->dev->mode[chn];
1341
1342 if (new_mode->color != old_mode->color)
1343 new_mode->restart = 1;
1344 else if (new_mode->scale != old_mode->scale)
1345 new_mode->restart = 1;
1346 else if (new_mode->format != old_mode->format)
1347 new_mode->restart = 1;
1348
1349 s2255_set_mode(dev, chn, new_mode);
1350 new_mode->restart = 0;
1351 *old_mode = *new_mode;
1352 dev->cur_fmt[chn] = fh->fmt;
1353 dprintk(1, "%s[%d]\n", __func__, chn);
1354 dev->last_frame[chn] = -1;
1355 dev->bad_payload[chn] = 0;
1356 dev->cur_frame[chn] = 0;
Dean Andersona1c45302008-09-09 12:29:56 -03001357 dev->frame_count[chn] = 0;
Dean Anderson38f993a2008-06-26 23:15:51 -03001358 for (j = 0; j < SYS_FRAMES; j++) {
Dean Anderson14d96262008-08-25 13:58:55 -03001359 dev->buffer[chn].frame[j].ulState = S2255_READ_IDLE;
Dean Anderson38f993a2008-06-26 23:15:51 -03001360 dev->buffer[chn].frame[j].cur_size = 0;
1361 }
1362 res = videobuf_streamon(&fh->vb_vidq);
1363 if (res == 0) {
1364 s2255_start_acquire(dev, chn);
1365 dev->b_acquire[chn] = 1;
1366 } else {
1367 res_free(dev, fh);
1368 }
1369 return res;
1370}
1371
1372static int vidioc_streamoff(struct file *file, void *priv, enum v4l2_buf_type i)
1373{
Dean Anderson38f993a2008-06-26 23:15:51 -03001374 struct s2255_fh *fh = priv;
1375 struct s2255_dev *dev = fh->dev;
1376
1377 dprintk(4, "%s\n, channel: %d", __func__, fh->channel);
1378 if (fh->type != V4L2_BUF_TYPE_VIDEO_CAPTURE) {
1379 printk(KERN_ERR "invalid fh type0\n");
1380 return -EINVAL;
1381 }
1382 if (i != fh->type) {
1383 printk(KERN_ERR "invalid type i\n");
1384 return -EINVAL;
1385 }
1386 s2255_stop_acquire(dev, fh->channel);
Dean Andersonb7732a32009-03-30 11:59:56 -03001387 videobuf_streamoff(&fh->vb_vidq);
Dean Anderson38f993a2008-06-26 23:15:51 -03001388 res_free(dev, fh);
Dean Andersonf78d92c2008-07-22 14:43:27 -03001389 return 0;
Dean Anderson38f993a2008-06-26 23:15:51 -03001390}
1391
1392static int vidioc_s_std(struct file *file, void *priv, v4l2_std_id *i)
1393{
1394 struct s2255_fh *fh = priv;
1395 struct s2255_mode *mode;
1396 struct videobuf_queue *q = &fh->vb_vidq;
1397 int ret = 0;
1398
1399 mutex_lock(&q->vb_lock);
1400 if (videobuf_queue_is_busy(q)) {
1401 dprintk(1, "queue busy\n");
1402 ret = -EBUSY;
1403 goto out_s_std;
1404 }
1405
1406 if (res_locked(fh->dev, fh)) {
1407 dprintk(1, "can't change standard after started\n");
1408 ret = -EBUSY;
1409 goto out_s_std;
1410 }
1411 mode = &fh->mode;
1412
1413 if (*i & V4L2_STD_NTSC) {
1414 dprintk(4, "vidioc_s_std NTSC\n");
1415 mode->format = FORMAT_NTSC;
1416 } else if (*i & V4L2_STD_PAL) {
1417 dprintk(4, "vidioc_s_std PAL\n");
1418 mode->format = FORMAT_PAL;
1419 } else {
1420 ret = -EINVAL;
1421 }
1422out_s_std:
1423 mutex_unlock(&q->vb_lock);
1424 return ret;
1425}
1426
1427/* Sensoray 2255 is a multiple channel capture device.
1428 It does not have a "crossbar" of inputs.
1429 We use one V4L device per channel. The user must
1430 be aware that certain combinations are not allowed.
1431 For instance, you cannot do full FPS on more than 2 channels(2 videodevs)
1432 at once in color(you can do full fps on 4 channels with greyscale.
1433*/
1434static int vidioc_enum_input(struct file *file, void *priv,
1435 struct v4l2_input *inp)
1436{
Dean Anderson4de39f52010-03-03 19:39:19 -03001437 struct s2255_fh *fh = priv;
1438 struct s2255_dev *dev = fh->dev;
1439 u32 status = 0;
1440
Dean Anderson38f993a2008-06-26 23:15:51 -03001441 if (inp->index != 0)
1442 return -EINVAL;
1443
1444 inp->type = V4L2_INPUT_TYPE_CAMERA;
1445 inp->std = S2255_NORMS;
Dean Anderson4de39f52010-03-03 19:39:19 -03001446 inp->status = 0;
1447 if (dev->dsp_fw_ver >= S2255_MIN_DSP_STATUS) {
1448 int rc;
1449 rc = s2255_cmd_status(dev, fh->channel, &status);
1450 dprintk(4, "s2255_cmd_status rc: %d status %x\n", rc, status);
1451 if (rc == 0)
1452 inp->status = (status & 0x01) ? 0
1453 : V4L2_IN_ST_NO_SIGNAL;
1454 }
Dean Anderson38f993a2008-06-26 23:15:51 -03001455 strlcpy(inp->name, "Camera", sizeof(inp->name));
Dean Anderson3f8d6f72008-06-30 21:28:34 -03001456 return 0;
Dean Anderson38f993a2008-06-26 23:15:51 -03001457}
1458
1459static int vidioc_g_input(struct file *file, void *priv, unsigned int *i)
1460{
1461 *i = 0;
1462 return 0;
1463}
1464static int vidioc_s_input(struct file *file, void *priv, unsigned int i)
1465{
1466 if (i > 0)
1467 return -EINVAL;
1468 return 0;
1469}
1470
1471/* --- controls ---------------------------------------------- */
1472static int vidioc_queryctrl(struct file *file, void *priv,
1473 struct v4l2_queryctrl *qc)
1474{
1475 int i;
1476
1477 for (i = 0; i < ARRAY_SIZE(s2255_qctrl); i++)
1478 if (qc->id && qc->id == s2255_qctrl[i].id) {
1479 memcpy(qc, &(s2255_qctrl[i]), sizeof(*qc));
Dean Anderson3f8d6f72008-06-30 21:28:34 -03001480 return 0;
Dean Anderson38f993a2008-06-26 23:15:51 -03001481 }
1482
1483 dprintk(4, "query_ctrl -EINVAL %d\n", qc->id);
1484 return -EINVAL;
1485}
1486
1487static int vidioc_g_ctrl(struct file *file, void *priv,
1488 struct v4l2_control *ctrl)
1489{
1490 int i;
1491
1492 for (i = 0; i < ARRAY_SIZE(s2255_qctrl); i++)
1493 if (ctrl->id == s2255_qctrl[i].id) {
1494 ctrl->value = qctl_regs[i];
Dean Anderson3f8d6f72008-06-30 21:28:34 -03001495 return 0;
Dean Anderson38f993a2008-06-26 23:15:51 -03001496 }
1497 dprintk(4, "g_ctrl -EINVAL\n");
1498
1499 return -EINVAL;
1500}
1501
1502static int vidioc_s_ctrl(struct file *file, void *priv,
1503 struct v4l2_control *ctrl)
1504{
1505 int i;
1506 struct s2255_fh *fh = priv;
1507 struct s2255_dev *dev = fh->dev;
1508 struct s2255_mode *mode;
1509 mode = &fh->mode;
1510 dprintk(4, "vidioc_s_ctrl\n");
1511 for (i = 0; i < ARRAY_SIZE(s2255_qctrl); i++) {
1512 if (ctrl->id == s2255_qctrl[i].id) {
1513 if (ctrl->value < s2255_qctrl[i].minimum ||
1514 ctrl->value > s2255_qctrl[i].maximum)
Dean Anderson3f8d6f72008-06-30 21:28:34 -03001515 return -ERANGE;
Dean Anderson38f993a2008-06-26 23:15:51 -03001516
1517 qctl_regs[i] = ctrl->value;
1518 /* update the mode to the corresponding value */
1519 switch (ctrl->id) {
1520 case V4L2_CID_BRIGHTNESS:
1521 mode->bright = ctrl->value;
1522 break;
1523 case V4L2_CID_CONTRAST:
1524 mode->contrast = ctrl->value;
1525 break;
1526 case V4L2_CID_HUE:
1527 mode->hue = ctrl->value;
1528 break;
1529 case V4L2_CID_SATURATION:
1530 mode->saturation = ctrl->value;
1531 break;
1532 }
1533 mode->restart = 0;
1534 /* set mode here. Note: stream does not need restarted.
1535 some V4L programs restart stream unnecessarily
1536 after a s_crtl.
1537 */
1538 s2255_set_mode(dev, fh->channel, mode);
1539 return 0;
1540 }
1541 }
1542 return -EINVAL;
1543}
1544
Dean Anderson22b88d42008-08-29 15:33:19 -03001545static int vidioc_g_jpegcomp(struct file *file, void *priv,
1546 struct v4l2_jpegcompression *jc)
1547{
1548 struct s2255_fh *fh = priv;
1549 struct s2255_dev *dev = fh->dev;
1550 *jc = dev->jc[fh->channel];
1551 dprintk(2, "getting jpegcompression, quality %d\n", jc->quality);
1552 return 0;
1553}
1554
1555static int vidioc_s_jpegcomp(struct file *file, void *priv,
1556 struct v4l2_jpegcompression *jc)
1557{
1558 struct s2255_fh *fh = priv;
1559 struct s2255_dev *dev = fh->dev;
1560 if (jc->quality < 0 || jc->quality > 100)
1561 return -EINVAL;
1562 dev->jc[fh->channel].quality = jc->quality;
1563 dprintk(2, "setting jpeg quality %d\n", jc->quality);
1564 return 0;
1565}
Dean Anderson7d853532009-05-15 14:32:04 -03001566
1567static int vidioc_g_parm(struct file *file, void *priv,
1568 struct v4l2_streamparm *sp)
1569{
1570 struct s2255_fh *fh = priv;
1571 struct s2255_dev *dev = fh->dev;
1572 if (sp->type != V4L2_BUF_TYPE_VIDEO_CAPTURE)
1573 return -EINVAL;
1574 sp->parm.capture.capturemode = dev->cap_parm[fh->channel].capturemode;
1575 dprintk(2, "getting parm %d\n", sp->parm.capture.capturemode);
1576 return 0;
1577}
1578
1579static int vidioc_s_parm(struct file *file, void *priv,
1580 struct v4l2_streamparm *sp)
1581{
1582 struct s2255_fh *fh = priv;
1583 struct s2255_dev *dev = fh->dev;
1584
1585 if (sp->type != V4L2_BUF_TYPE_VIDEO_CAPTURE)
1586 return -EINVAL;
1587
1588 dev->cap_parm[fh->channel].capturemode = sp->parm.capture.capturemode;
1589 dprintk(2, "setting param capture mode %d\n",
1590 sp->parm.capture.capturemode);
1591 return 0;
1592}
Hans Verkuilbec43662008-12-30 06:58:20 -03001593static int s2255_open(struct file *file)
Dean Anderson38f993a2008-06-26 23:15:51 -03001594{
Laurent Pinchart63b0d5a2009-12-10 11:44:04 -02001595 struct video_device *vdev = video_devdata(file);
1596 struct s2255_dev *dev = video_drvdata(file);
Dean Anderson38f993a2008-06-26 23:15:51 -03001597 struct s2255_fh *fh;
Laurent Pinchart63b0d5a2009-12-10 11:44:04 -02001598 enum v4l2_buf_type type = V4L2_BUF_TYPE_VIDEO_CAPTURE;
Dean Anderson38f993a2008-06-26 23:15:51 -03001599 int i = 0;
1600 int cur_channel = -1;
Dean Anderson14d96262008-08-25 13:58:55 -03001601 int state;
Laurent Pinchart50462eb2009-12-10 11:47:13 -02001602
1603 dprintk(1, "s2255: open called (dev=%s)\n",
1604 video_device_node_name(vdev));
Dean Anderson38f993a2008-06-26 23:15:51 -03001605
Hans Verkuild56dc612008-07-30 08:43:36 -03001606 lock_kernel();
Dean Anderson38f993a2008-06-26 23:15:51 -03001607
Laurent Pinchart63b0d5a2009-12-10 11:44:04 -02001608 for (i = 0; i < MAX_CHANNELS; i++) {
1609 if (dev->vdev[i] == vdev) {
1610 cur_channel = i;
1611 break;
1612 }
Dean Anderson38f993a2008-06-26 23:15:51 -03001613 }
1614
Dean Anderson14d96262008-08-25 13:58:55 -03001615 if (atomic_read(&dev->fw_data->fw_state) == S2255_FW_DISCONNECTING) {
1616 unlock_kernel();
1617 printk(KERN_INFO "disconnecting\n");
1618 return -ENODEV;
1619 }
1620 kref_get(&dev->kref);
Dean Anderson38f993a2008-06-26 23:15:51 -03001621 mutex_lock(&dev->open_lock);
1622
1623 dev->users[cur_channel]++;
Dean Andersonf78d92c2008-07-22 14:43:27 -03001624 dprintk(4, "s2255: open_handles %d\n", dev->users[cur_channel]);
Dean Anderson38f993a2008-06-26 23:15:51 -03001625
Dean Anderson14d96262008-08-25 13:58:55 -03001626 switch (atomic_read(&dev->fw_data->fw_state)) {
1627 case S2255_FW_FAILED:
Mauro Carvalho Chehabbe9ed512009-01-08 09:13:42 -03001628 s2255_dev_err(&dev->udev->dev,
1629 "firmware load failed. retrying.\n");
Dean Anderson14d96262008-08-25 13:58:55 -03001630 s2255_fwload_start(dev, 1);
Dean Anderson38f993a2008-06-26 23:15:51 -03001631 wait_event_timeout(dev->fw_data->wait_fw,
Dean Anderson14d96262008-08-25 13:58:55 -03001632 ((atomic_read(&dev->fw_data->fw_state)
1633 == S2255_FW_SUCCESS) ||
1634 (atomic_read(&dev->fw_data->fw_state)
1635 == S2255_FW_DISCONNECTING)),
Dean Anderson38f993a2008-06-26 23:15:51 -03001636 msecs_to_jiffies(S2255_LOAD_TIMEOUT));
Dean Anderson14d96262008-08-25 13:58:55 -03001637 break;
1638 case S2255_FW_NOTLOADED:
1639 case S2255_FW_LOADED_DSPWAIT:
Dean Anderson38f993a2008-06-26 23:15:51 -03001640 /* give S2255_LOAD_TIMEOUT time for firmware to load in case
1641 driver loaded and then device immediately opened */
1642 printk(KERN_INFO "%s waiting for firmware load\n", __func__);
1643 wait_event_timeout(dev->fw_data->wait_fw,
Dean Anderson14d96262008-08-25 13:58:55 -03001644 ((atomic_read(&dev->fw_data->fw_state)
1645 == S2255_FW_SUCCESS) ||
1646 (atomic_read(&dev->fw_data->fw_state)
1647 == S2255_FW_DISCONNECTING)),
1648 msecs_to_jiffies(S2255_LOAD_TIMEOUT));
1649 break;
1650 case S2255_FW_SUCCESS:
1651 default:
1652 break;
1653 }
1654 state = atomic_read(&dev->fw_data->fw_state);
1655 if (state != S2255_FW_SUCCESS) {
1656 int rc;
1657 switch (state) {
1658 case S2255_FW_FAILED:
1659 printk(KERN_INFO "2255 FW load failed. %d\n", state);
1660 rc = -ENODEV;
1661 break;
1662 case S2255_FW_DISCONNECTING:
1663 printk(KERN_INFO "%s: disconnecting\n", __func__);
1664 rc = -ENODEV;
1665 break;
1666 case S2255_FW_LOADED_DSPWAIT:
1667 case S2255_FW_NOTLOADED:
1668 printk(KERN_INFO "%s: firmware not loaded yet"
1669 "please try again later\n",
1670 __func__);
1671 rc = -EAGAIN;
1672 break;
1673 default:
1674 printk(KERN_INFO "%s: unknown state\n", __func__);
1675 rc = -EFAULT;
1676 break;
Dean Anderson38f993a2008-06-26 23:15:51 -03001677 }
Dean Anderson14d96262008-08-25 13:58:55 -03001678 dev->users[cur_channel]--;
1679 mutex_unlock(&dev->open_lock);
1680 kref_put(&dev->kref, s2255_destroy);
1681 unlock_kernel();
1682 return rc;
Dean Anderson38f993a2008-06-26 23:15:51 -03001683 }
1684
1685 /* allocate + initialize per filehandle data */
1686 fh = kzalloc(sizeof(*fh), GFP_KERNEL);
1687 if (NULL == fh) {
Dean Andersonf78d92c2008-07-22 14:43:27 -03001688 dev->users[cur_channel]--;
Dean Anderson38f993a2008-06-26 23:15:51 -03001689 mutex_unlock(&dev->open_lock);
Dean Anderson14d96262008-08-25 13:58:55 -03001690 kref_put(&dev->kref, s2255_destroy);
Hans Verkuild56dc612008-07-30 08:43:36 -03001691 unlock_kernel();
Dean Anderson38f993a2008-06-26 23:15:51 -03001692 return -ENOMEM;
1693 }
1694
1695 file->private_data = fh;
1696 fh->dev = dev;
1697 fh->type = V4L2_BUF_TYPE_VIDEO_CAPTURE;
1698 fh->mode = dev->mode[cur_channel];
1699 fh->fmt = dev->cur_fmt[cur_channel];
1700 /* default 4CIF NTSC */
1701 fh->width = LINE_SZ_4CIFS_NTSC;
1702 fh->height = NUM_LINES_4CIFS_NTSC * 2;
1703 fh->channel = cur_channel;
1704
Dean Anderson14d96262008-08-25 13:58:55 -03001705 /* configure channel to default state */
1706 if (!dev->chn_configured[cur_channel]) {
1707 s2255_set_mode(dev, cur_channel, &fh->mode);
1708 dev->chn_configured[cur_channel] = 1;
1709 }
1710
1711
Dean Anderson38f993a2008-06-26 23:15:51 -03001712 /* Put all controls at a sane state */
1713 for (i = 0; i < ARRAY_SIZE(s2255_qctrl); i++)
1714 qctl_regs[i] = s2255_qctrl[i].default_value;
1715
Laurent Pinchart50462eb2009-12-10 11:47:13 -02001716 dprintk(1, "s2255drv: open dev=%s type=%s users=%d\n",
1717 video_device_node_name(vdev), v4l2_type_names[type],
1718 dev->users[cur_channel]);
Dean Anderson38f993a2008-06-26 23:15:51 -03001719 dprintk(2, "s2255drv: open: fh=0x%08lx, dev=0x%08lx, vidq=0x%08lx\n",
1720 (unsigned long)fh, (unsigned long)dev,
1721 (unsigned long)&dev->vidq[cur_channel]);
1722 dprintk(4, "s2255drv: open: list_empty active=%d\n",
1723 list_empty(&dev->vidq[cur_channel].active));
1724
1725 videobuf_queue_vmalloc_init(&fh->vb_vidq, &s2255_video_qops,
1726 NULL, &dev->slock,
1727 fh->type,
1728 V4L2_FIELD_INTERLACED,
1729 sizeof(struct s2255_buffer), fh);
1730
Dean Anderson38f993a2008-06-26 23:15:51 -03001731 mutex_unlock(&dev->open_lock);
Hans Verkuild56dc612008-07-30 08:43:36 -03001732 unlock_kernel();
Dean Anderson38f993a2008-06-26 23:15:51 -03001733 return 0;
1734}
1735
1736
1737static unsigned int s2255_poll(struct file *file,
1738 struct poll_table_struct *wait)
1739{
1740 struct s2255_fh *fh = file->private_data;
1741 int rc;
1742 dprintk(100, "%s\n", __func__);
1743
1744 if (V4L2_BUF_TYPE_VIDEO_CAPTURE != fh->type)
1745 return POLLERR;
1746
1747 rc = videobuf_poll_stream(file, &fh->vb_vidq, wait);
1748 return rc;
1749}
1750
1751static void s2255_destroy(struct kref *kref)
1752{
1753 struct s2255_dev *dev = to_s2255_dev(kref);
Dean Anderson14d96262008-08-25 13:58:55 -03001754 int i;
Dean Anderson38f993a2008-06-26 23:15:51 -03001755 if (!dev) {
1756 printk(KERN_ERR "s2255drv: kref problem\n");
1757 return;
1758 }
Dean Andersonf78d92c2008-07-22 14:43:27 -03001759 atomic_set(&dev->fw_data->fw_state, S2255_FW_DISCONNECTING);
1760 wake_up(&dev->fw_data->wait_fw);
Dean Anderson14d96262008-08-25 13:58:55 -03001761 for (i = 0; i < MAX_CHANNELS; i++) {
1762 dev->setmode_ready[i] = 1;
1763 wake_up(&dev->wait_setmode[i]);
Dean Anderson4de39f52010-03-03 19:39:19 -03001764 dev->vidstatus_ready[i] = 1;
1765 wake_up(&dev->wait_vidstatus[i]);
Dean Anderson14d96262008-08-25 13:58:55 -03001766 }
Dean Anderson38f993a2008-06-26 23:15:51 -03001767 mutex_lock(&dev->open_lock);
Dean Anderson14d96262008-08-25 13:58:55 -03001768 /* reset the DSP so firmware can be reload next time */
1769 s2255_reset_dsppower(dev);
Dean Anderson38f993a2008-06-26 23:15:51 -03001770 s2255_exit_v4l(dev);
Dean Anderson38f993a2008-06-26 23:15:51 -03001771 /* board shutdown stops the read pipe if it is running */
1772 s2255_board_shutdown(dev);
Dean Anderson38f993a2008-06-26 23:15:51 -03001773 /* make sure firmware still not trying to load */
Dean Andersonf78d92c2008-07-22 14:43:27 -03001774 del_timer(&dev->timer); /* only started in .probe and .open */
1775
Dean Anderson38f993a2008-06-26 23:15:51 -03001776 if (dev->fw_data->fw_urb) {
1777 dprintk(2, "kill fw_urb\n");
1778 usb_kill_urb(dev->fw_data->fw_urb);
1779 usb_free_urb(dev->fw_data->fw_urb);
1780 dev->fw_data->fw_urb = NULL;
1781 }
Dean Andersonf78d92c2008-07-22 14:43:27 -03001782 if (dev->fw_data->fw)
1783 release_firmware(dev->fw_data->fw);
1784 kfree(dev->fw_data->pfw_data);
1785 kfree(dev->fw_data);
Dean Anderson38f993a2008-06-26 23:15:51 -03001786 usb_put_dev(dev->udev);
1787 dprintk(1, "%s", __func__);
Dean Anderson14d96262008-08-25 13:58:55 -03001788
Dean Anderson14d96262008-08-25 13:58:55 -03001789 mutex_unlock(&dev->open_lock);
Dean Andersonb7732a32009-03-30 11:59:56 -03001790 kfree(dev);
Dean Anderson38f993a2008-06-26 23:15:51 -03001791}
1792
Hans Verkuilbec43662008-12-30 06:58:20 -03001793static int s2255_close(struct file *file)
Dean Anderson38f993a2008-06-26 23:15:51 -03001794{
1795 struct s2255_fh *fh = file->private_data;
1796 struct s2255_dev *dev = fh->dev;
Laurent Pinchart50462eb2009-12-10 11:47:13 -02001797 struct video_device *vdev = video_devdata(file);
1798
Dean Anderson38f993a2008-06-26 23:15:51 -03001799 if (!dev)
1800 return -ENODEV;
1801
1802 mutex_lock(&dev->open_lock);
1803
Dean Andersonf78d92c2008-07-22 14:43:27 -03001804 /* turn off stream */
1805 if (res_check(fh)) {
1806 if (dev->b_acquire[fh->channel])
1807 s2255_stop_acquire(dev, fh->channel);
1808 videobuf_streamoff(&fh->vb_vidq);
1809 res_free(dev, fh);
1810 }
1811
Dean Anderson38f993a2008-06-26 23:15:51 -03001812 videobuf_mmap_free(&fh->vb_vidq);
Dean Anderson38f993a2008-06-26 23:15:51 -03001813 dev->users[fh->channel]--;
Dean Andersonf78d92c2008-07-22 14:43:27 -03001814
Dean Anderson38f993a2008-06-26 23:15:51 -03001815 mutex_unlock(&dev->open_lock);
1816
1817 kref_put(&dev->kref, s2255_destroy);
Laurent Pinchart50462eb2009-12-10 11:47:13 -02001818 dprintk(1, "s2255: close called (dev=%s, users=%d)\n",
1819 video_device_node_name(vdev), dev->users[fh->channel]);
Dean Andersonf78d92c2008-07-22 14:43:27 -03001820 kfree(fh);
Dean Anderson38f993a2008-06-26 23:15:51 -03001821 return 0;
1822}
1823
1824static int s2255_mmap_v4l(struct file *file, struct vm_area_struct *vma)
1825{
1826 struct s2255_fh *fh = file->private_data;
1827 int ret;
1828
1829 if (!fh)
1830 return -ENODEV;
1831 dprintk(4, "mmap called, vma=0x%08lx\n", (unsigned long)vma);
1832
1833 ret = videobuf_mmap_mapper(&fh->vb_vidq, vma);
1834
1835 dprintk(4, "vma start=0x%08lx, size=%ld, ret=%d\n",
1836 (unsigned long)vma->vm_start,
1837 (unsigned long)vma->vm_end - (unsigned long)vma->vm_start, ret);
1838
1839 return ret;
1840}
1841
Hans Verkuilbec43662008-12-30 06:58:20 -03001842static const struct v4l2_file_operations s2255_fops_v4l = {
Dean Anderson38f993a2008-06-26 23:15:51 -03001843 .owner = THIS_MODULE,
1844 .open = s2255_open,
1845 .release = s2255_close,
1846 .poll = s2255_poll,
1847 .ioctl = video_ioctl2, /* V4L2 ioctl handler */
Dean Anderson38f993a2008-06-26 23:15:51 -03001848 .mmap = s2255_mmap_v4l,
Dean Anderson38f993a2008-06-26 23:15:51 -03001849};
1850
Hans Verkuila3998102008-07-21 02:57:38 -03001851static const struct v4l2_ioctl_ops s2255_ioctl_ops = {
Dean Anderson38f993a2008-06-26 23:15:51 -03001852 .vidioc_querycap = vidioc_querycap,
1853 .vidioc_enum_fmt_vid_cap = vidioc_enum_fmt_vid_cap,
1854 .vidioc_g_fmt_vid_cap = vidioc_g_fmt_vid_cap,
1855 .vidioc_try_fmt_vid_cap = vidioc_try_fmt_vid_cap,
1856 .vidioc_s_fmt_vid_cap = vidioc_s_fmt_vid_cap,
1857 .vidioc_reqbufs = vidioc_reqbufs,
1858 .vidioc_querybuf = vidioc_querybuf,
1859 .vidioc_qbuf = vidioc_qbuf,
1860 .vidioc_dqbuf = vidioc_dqbuf,
1861 .vidioc_s_std = vidioc_s_std,
1862 .vidioc_enum_input = vidioc_enum_input,
1863 .vidioc_g_input = vidioc_g_input,
1864 .vidioc_s_input = vidioc_s_input,
1865 .vidioc_queryctrl = vidioc_queryctrl,
1866 .vidioc_g_ctrl = vidioc_g_ctrl,
1867 .vidioc_s_ctrl = vidioc_s_ctrl,
1868 .vidioc_streamon = vidioc_streamon,
1869 .vidioc_streamoff = vidioc_streamoff,
1870#ifdef CONFIG_VIDEO_V4L1_COMPAT
1871 .vidiocgmbuf = vidioc_cgmbuf,
1872#endif
Dean Anderson22b88d42008-08-29 15:33:19 -03001873 .vidioc_s_jpegcomp = vidioc_s_jpegcomp,
1874 .vidioc_g_jpegcomp = vidioc_g_jpegcomp,
Dean Anderson7d853532009-05-15 14:32:04 -03001875 .vidioc_s_parm = vidioc_s_parm,
1876 .vidioc_g_parm = vidioc_g_parm,
Hans Verkuila3998102008-07-21 02:57:38 -03001877};
1878
1879static struct video_device template = {
1880 .name = "s2255v",
Hans Verkuila3998102008-07-21 02:57:38 -03001881 .fops = &s2255_fops_v4l,
1882 .ioctl_ops = &s2255_ioctl_ops,
Hans Verkuila3998102008-07-21 02:57:38 -03001883 .release = video_device_release,
Dean Anderson38f993a2008-06-26 23:15:51 -03001884 .tvnorms = S2255_NORMS,
1885 .current_norm = V4L2_STD_NTSC_M,
1886};
1887
1888static int s2255_probe_v4l(struct s2255_dev *dev)
1889{
1890 int ret;
1891 int i;
1892 int cur_nr = video_nr;
1893
1894 /* initialize all video 4 linux */
Dean Anderson38f993a2008-06-26 23:15:51 -03001895 /* register 4 video devices */
1896 for (i = 0; i < MAX_CHANNELS; i++) {
1897 INIT_LIST_HEAD(&dev->vidq[i].active);
1898 dev->vidq[i].dev = dev;
1899 dev->vidq[i].channel = i;
Dean Anderson38f993a2008-06-26 23:15:51 -03001900 /* register 4 video devices */
1901 dev->vdev[i] = video_device_alloc();
1902 memcpy(dev->vdev[i], &template, sizeof(struct video_device));
Hans Verkuil5e85e732008-07-20 06:31:39 -03001903 dev->vdev[i]->parent = &dev->interface->dev;
Laurent Pinchart63b0d5a2009-12-10 11:44:04 -02001904 video_set_drvdata(dev->vdev[i], dev);
Dean Anderson38f993a2008-06-26 23:15:51 -03001905 if (video_nr == -1)
1906 ret = video_register_device(dev->vdev[i],
1907 VFL_TYPE_GRABBER,
1908 video_nr);
1909 else
1910 ret = video_register_device(dev->vdev[i],
1911 VFL_TYPE_GRABBER,
1912 cur_nr + i);
Hans Verkuil601e9442008-08-23 07:24:07 -03001913 video_set_drvdata(dev->vdev[i], dev);
Dean Anderson38f993a2008-06-26 23:15:51 -03001914
1915 if (ret != 0) {
1916 dev_err(&dev->udev->dev,
1917 "failed to register video device!\n");
1918 return ret;
1919 }
1920 }
Dean Andersonabce21f2009-04-23 16:04:41 -03001921 printk(KERN_INFO "Sensoray 2255 V4L driver Revision: %d.%d\n",
1922 S2255_MAJOR_VERSION,
1923 S2255_MINOR_VERSION);
Dean Anderson38f993a2008-06-26 23:15:51 -03001924 return ret;
1925}
1926
1927static void s2255_exit_v4l(struct s2255_dev *dev)
1928{
Dean Anderson14d96262008-08-25 13:58:55 -03001929
Dean Anderson38f993a2008-06-26 23:15:51 -03001930 int i;
Dean Anderson38f993a2008-06-26 23:15:51 -03001931 for (i = 0; i < MAX_CHANNELS; i++) {
Laurent Pinchartf0813b42009-11-27 13:57:30 -03001932 if (video_is_registered(dev->vdev[i])) {
Dean Anderson38f993a2008-06-26 23:15:51 -03001933 video_unregister_device(dev->vdev[i]);
Dean Anderson14d96262008-08-25 13:58:55 -03001934 printk(KERN_INFO "s2255 unregistered\n");
1935 } else {
Dean Anderson38f993a2008-06-26 23:15:51 -03001936 video_device_release(dev->vdev[i]);
Dean Anderson14d96262008-08-25 13:58:55 -03001937 printk(KERN_INFO "s2255 released\n");
1938 }
Dean Anderson38f993a2008-06-26 23:15:51 -03001939 }
1940}
1941
1942/* this function moves the usb stream read pipe data
1943 * into the system buffers.
1944 * returns 0 on success, EAGAIN if more data to process( call this
1945 * function again).
1946 *
1947 * Received frame structure:
Dean Anderson14d96262008-08-25 13:58:55 -03001948 * bytes 0-3: marker : 0x2255DA4AL (S2255_MARKER_FRAME)
Dean Anderson38f993a2008-06-26 23:15:51 -03001949 * bytes 4-7: channel: 0-3
1950 * bytes 8-11: payload size: size of the frame
1951 * bytes 12-payloadsize+12: frame data
1952 */
1953static int save_frame(struct s2255_dev *dev, struct s2255_pipeinfo *pipe_info)
1954{
Dean Anderson38f993a2008-06-26 23:15:51 -03001955 char *pdest;
1956 u32 offset = 0;
Dean Anderson14d96262008-08-25 13:58:55 -03001957 int bframe = 0;
Dean Anderson38f993a2008-06-26 23:15:51 -03001958 char *psrc;
1959 unsigned long copy_size;
1960 unsigned long size;
1961 s32 idx = -1;
1962 struct s2255_framei *frm;
1963 unsigned char *pdata;
Dean Anderson14d96262008-08-25 13:58:55 -03001964
Dean Anderson38f993a2008-06-26 23:15:51 -03001965 dprintk(100, "buffer to user\n");
1966
1967 idx = dev->cur_frame[dev->cc];
Dean Anderson38f993a2008-06-26 23:15:51 -03001968 frm = &dev->buffer[dev->cc].frame[idx];
1969
Dean Anderson14d96262008-08-25 13:58:55 -03001970 if (frm->ulState == S2255_READ_IDLE) {
1971 int jj;
1972 unsigned int cc;
Dean Anderson3fa00602010-03-04 20:47:33 -03001973 __le32 *pdword; /*data from dsp is little endian */
Dean Anderson14d96262008-08-25 13:58:55 -03001974 int payload;
1975 /* search for marker codes */
1976 pdata = (unsigned char *)pipe_info->transfer_buffer;
Dean Anderson3fa00602010-03-04 20:47:33 -03001977 pdword = (__le32 *)pdata;
Dean Anderson14d96262008-08-25 13:58:55 -03001978 for (jj = 0; jj < (pipe_info->cur_transfer_size - 12); jj++) {
Dean Anderson3fa00602010-03-04 20:47:33 -03001979 switch (*pdword) {
Dean Anderson14d96262008-08-25 13:58:55 -03001980 case S2255_MARKER_FRAME:
Dean Anderson14d96262008-08-25 13:58:55 -03001981 dprintk(4, "found frame marker at offset:"
1982 " %d [%x %x]\n", jj, pdata[0],
1983 pdata[1]);
1984 offset = jj + PREFIX_SIZE;
1985 bframe = 1;
1986 cc = pdword[1];
1987 if (cc >= MAX_CHANNELS) {
1988 printk(KERN_ERR
1989 "bad channel\n");
1990 return -EINVAL;
1991 }
1992 /* reverse it */
1993 dev->cc = G_chnmap[cc];
1994 payload = pdword[3];
1995 if (payload > dev->req_image_size[dev->cc]) {
1996 dev->bad_payload[dev->cc]++;
1997 /* discard the bad frame */
1998 return -EINVAL;
1999 }
2000 dev->pkt_size[dev->cc] = payload;
2001 dev->jpg_size[dev->cc] = pdword[4];
2002 break;
2003 case S2255_MARKER_RESPONSE:
Dean Anderson14d96262008-08-25 13:58:55 -03002004 pdata += DEF_USB_BLOCK;
2005 jj += DEF_USB_BLOCK;
2006 if (pdword[1] >= MAX_CHANNELS)
2007 break;
2008 cc = G_chnmap[pdword[1]];
Roel Kluinf14a2972009-10-23 07:59:42 -03002009 if (cc >= MAX_CHANNELS)
Dean Anderson14d96262008-08-25 13:58:55 -03002010 break;
2011 switch (pdword[2]) {
Dean Andersonabce21f2009-04-23 16:04:41 -03002012 case S2255_RESPONSE_SETMODE:
Dean Anderson14d96262008-08-25 13:58:55 -03002013 /* check if channel valid */
2014 /* set mode ready */
2015 dev->setmode_ready[cc] = 1;
2016 wake_up(&dev->wait_setmode[cc]);
2017 dprintk(5, "setmode ready %d\n", cc);
2018 break;
Dean Andersonabce21f2009-04-23 16:04:41 -03002019 case S2255_RESPONSE_FW:
Dean Anderson14d96262008-08-25 13:58:55 -03002020
2021 dev->chn_ready |= (1 << cc);
2022 if ((dev->chn_ready & 0x0f) != 0x0f)
2023 break;
2024 /* all channels ready */
2025 printk(KERN_INFO "s2255: fw loaded\n");
2026 atomic_set(&dev->fw_data->fw_state,
2027 S2255_FW_SUCCESS);
2028 wake_up(&dev->fw_data->wait_fw);
2029 break;
Dean Anderson4de39f52010-03-03 19:39:19 -03002030 case S2255_RESPONSE_STATUS:
2031 dev->vidstatus[cc] = pdword[3];
2032 dev->vidstatus_ready[cc] = 1;
2033 wake_up(&dev->wait_vidstatus[cc]);
2034 dprintk(5, "got vidstatus %x chan %d\n",
2035 pdword[3], cc);
2036 break;
Dean Anderson14d96262008-08-25 13:58:55 -03002037 default:
André Goddard Rosaaf901ca2009-11-14 13:09:05 -02002038 printk(KERN_INFO "s2255 unknown resp\n");
Dean Anderson14d96262008-08-25 13:58:55 -03002039 }
2040 default:
2041 pdata++;
2042 break;
2043 }
2044 if (bframe)
2045 break;
2046 } /* for */
2047 if (!bframe)
2048 return -EINVAL;
2049 }
2050
2051
2052 idx = dev->cur_frame[dev->cc];
2053 frm = &dev->buffer[dev->cc].frame[idx];
2054
2055 /* search done. now find out if should be acquiring on this channel */
2056 if (!dev->b_acquire[dev->cc]) {
2057 /* we found a frame, but this channel is turned off */
2058 frm->ulState = S2255_READ_IDLE;
2059 return -EINVAL;
2060 }
2061
2062 if (frm->ulState == S2255_READ_IDLE) {
2063 frm->ulState = S2255_READ_FRAME;
Dean Anderson38f993a2008-06-26 23:15:51 -03002064 frm->cur_size = 0;
2065 }
2066
Dean Anderson14d96262008-08-25 13:58:55 -03002067 /* skip the marker 512 bytes (and offset if out of sync) */
2068 psrc = (u8 *)pipe_info->transfer_buffer + offset;
2069
Dean Anderson38f993a2008-06-26 23:15:51 -03002070
2071 if (frm->lpvbits == NULL) {
2072 dprintk(1, "s2255 frame buffer == NULL.%p %p %d %d",
2073 frm, dev, dev->cc, idx);
2074 return -ENOMEM;
2075 }
2076
2077 pdest = frm->lpvbits + frm->cur_size;
2078
Dean Anderson14d96262008-08-25 13:58:55 -03002079 copy_size = (pipe_info->cur_transfer_size - offset);
Dean Anderson38f993a2008-06-26 23:15:51 -03002080
Dean Anderson14d96262008-08-25 13:58:55 -03002081 size = dev->pkt_size[dev->cc] - PREFIX_SIZE;
Dean Anderson38f993a2008-06-26 23:15:51 -03002082
Dean Anderson14d96262008-08-25 13:58:55 -03002083 /* sanity check on pdest */
2084 if ((copy_size + frm->cur_size) < dev->req_image_size[dev->cc])
2085 memcpy(pdest, psrc, copy_size);
Dean Anderson38f993a2008-06-26 23:15:51 -03002086
Dean Anderson38f993a2008-06-26 23:15:51 -03002087 frm->cur_size += copy_size;
Dean Anderson14d96262008-08-25 13:58:55 -03002088 dprintk(4, "cur_size size %lu size %lu \n", frm->cur_size, size);
Dean Anderson38f993a2008-06-26 23:15:51 -03002089
Dean Anderson14d96262008-08-25 13:58:55 -03002090 if (frm->cur_size >= size) {
2091
Dean Anderson38f993a2008-06-26 23:15:51 -03002092 u32 cc = dev->cc;
Dean Anderson38f993a2008-06-26 23:15:51 -03002093 dprintk(2, "****************[%d]Buffer[%d]full*************\n",
2094 cc, idx);
2095 dev->last_frame[cc] = dev->cur_frame[cc];
2096 dev->cur_frame[cc]++;
2097 /* end of system frame ring buffer, start at zero */
2098 if ((dev->cur_frame[cc] == SYS_FRAMES) ||
2099 (dev->cur_frame[cc] == dev->buffer[cc].dwFrames))
2100 dev->cur_frame[cc] = 0;
Dean Anderson14d96262008-08-25 13:58:55 -03002101 /* frame ready */
Dean Anderson38f993a2008-06-26 23:15:51 -03002102 if (dev->b_acquire[cc])
Dean Anderson14d96262008-08-25 13:58:55 -03002103 s2255_got_frame(dev, cc, dev->jpg_size[cc]);
Dean Anderson38f993a2008-06-26 23:15:51 -03002104 dev->frame_count[cc]++;
Dean Anderson14d96262008-08-25 13:58:55 -03002105 frm->ulState = S2255_READ_IDLE;
2106 frm->cur_size = 0;
2107
Dean Anderson38f993a2008-06-26 23:15:51 -03002108 }
2109 /* done successfully */
2110 return 0;
2111}
2112
2113static void s2255_read_video_callback(struct s2255_dev *dev,
2114 struct s2255_pipeinfo *pipe_info)
2115{
2116 int res;
2117 dprintk(50, "callback read video \n");
2118
2119 if (dev->cc >= MAX_CHANNELS) {
2120 dev->cc = 0;
2121 dev_err(&dev->udev->dev, "invalid channel\n");
2122 return;
2123 }
2124 /* otherwise copy to the system buffers */
2125 res = save_frame(dev, pipe_info);
Dean Anderson14d96262008-08-25 13:58:55 -03002126 if (res != 0)
2127 dprintk(4, "s2255: read callback failed\n");
Dean Anderson38f993a2008-06-26 23:15:51 -03002128
2129 dprintk(50, "callback read video done\n");
2130 return;
2131}
2132
2133static long s2255_vendor_req(struct s2255_dev *dev, unsigned char Request,
2134 u16 Index, u16 Value, void *TransferBuffer,
2135 s32 TransferBufferLength, int bOut)
2136{
2137 int r;
2138 if (!bOut) {
2139 r = usb_control_msg(dev->udev, usb_rcvctrlpipe(dev->udev, 0),
2140 Request,
2141 USB_TYPE_VENDOR | USB_RECIP_DEVICE |
2142 USB_DIR_IN,
2143 Value, Index, TransferBuffer,
2144 TransferBufferLength, HZ * 5);
2145 } else {
2146 r = usb_control_msg(dev->udev, usb_sndctrlpipe(dev->udev, 0),
2147 Request, USB_TYPE_VENDOR | USB_RECIP_DEVICE,
2148 Value, Index, TransferBuffer,
2149 TransferBufferLength, HZ * 5);
2150 }
2151 return r;
2152}
2153
2154/*
2155 * retrieve FX2 firmware version. future use.
2156 * @param dev pointer to device extension
2157 * @return -1 for fail, else returns firmware version as an int(16 bits)
2158 */
2159static int s2255_get_fx2fw(struct s2255_dev *dev)
2160{
2161 int fw;
2162 int ret;
2163 unsigned char transBuffer[64];
2164 ret = s2255_vendor_req(dev, S2255_VR_FW, 0, 0, transBuffer, 2,
2165 S2255_VR_IN);
2166 if (ret < 0)
2167 dprintk(2, "get fw error: %x\n", ret);
2168 fw = transBuffer[0] + (transBuffer[1] << 8);
2169 dprintk(2, "Get FW %x %x\n", transBuffer[0], transBuffer[1]);
2170 return fw;
2171}
2172
2173/*
2174 * Create the system ring buffer to copy frames into from the
2175 * usb read pipe.
2176 */
2177static int s2255_create_sys_buffers(struct s2255_dev *dev, unsigned long chn)
2178{
2179 unsigned long i;
2180 unsigned long reqsize;
2181 dprintk(1, "create sys buffers\n");
2182 if (chn >= MAX_CHANNELS)
2183 return -1;
2184
2185 dev->buffer[chn].dwFrames = SYS_FRAMES;
2186
2187 /* always allocate maximum size(PAL) for system buffers */
2188 reqsize = SYS_FRAMES_MAXSIZE;
2189
2190 if (reqsize > SYS_FRAMES_MAXSIZE)
2191 reqsize = SYS_FRAMES_MAXSIZE;
2192
2193 for (i = 0; i < SYS_FRAMES; i++) {
2194 /* allocate the frames */
2195 dev->buffer[chn].frame[i].lpvbits = vmalloc(reqsize);
2196
2197 dprintk(1, "valloc %p chan %lu, idx %lu, pdata %p\n",
2198 &dev->buffer[chn].frame[i], chn, i,
2199 dev->buffer[chn].frame[i].lpvbits);
2200 dev->buffer[chn].frame[i].size = reqsize;
2201 if (dev->buffer[chn].frame[i].lpvbits == NULL) {
2202 printk(KERN_INFO "out of memory. using less frames\n");
2203 dev->buffer[chn].dwFrames = i;
2204 break;
2205 }
2206 }
2207
2208 /* make sure internal states are set */
2209 for (i = 0; i < SYS_FRAMES; i++) {
2210 dev->buffer[chn].frame[i].ulState = 0;
2211 dev->buffer[chn].frame[i].cur_size = 0;
2212 }
2213
2214 dev->cur_frame[chn] = 0;
2215 dev->last_frame[chn] = -1;
2216 return 0;
2217}
2218
2219static int s2255_release_sys_buffers(struct s2255_dev *dev,
2220 unsigned long channel)
2221{
2222 unsigned long i;
2223 dprintk(1, "release sys buffers\n");
2224 for (i = 0; i < SYS_FRAMES; i++) {
2225 if (dev->buffer[channel].frame[i].lpvbits) {
2226 dprintk(1, "vfree %p\n",
2227 dev->buffer[channel].frame[i].lpvbits);
2228 vfree(dev->buffer[channel].frame[i].lpvbits);
2229 }
2230 dev->buffer[channel].frame[i].lpvbits = NULL;
2231 }
2232 return 0;
2233}
2234
2235static int s2255_board_init(struct s2255_dev *dev)
2236{
2237 int j;
2238 struct s2255_mode mode_def = DEF_MODEI_NTSC_CONT;
2239 int fw_ver;
2240 dprintk(4, "board init: %p", dev);
2241
2242 for (j = 0; j < MAX_PIPE_BUFFERS; j++) {
2243 struct s2255_pipeinfo *pipe = &dev->pipes[j];
2244
2245 memset(pipe, 0, sizeof(*pipe));
2246 pipe->dev = dev;
Dean Anderson14d96262008-08-25 13:58:55 -03002247 pipe->cur_transfer_size = S2255_USB_XFER_SIZE;
2248 pipe->max_transfer_size = S2255_USB_XFER_SIZE;
Dean Anderson38f993a2008-06-26 23:15:51 -03002249
Dean Anderson38f993a2008-06-26 23:15:51 -03002250 pipe->transfer_buffer = kzalloc(pipe->max_transfer_size,
2251 GFP_KERNEL);
2252 if (pipe->transfer_buffer == NULL) {
2253 dprintk(1, "out of memory!\n");
2254 return -ENOMEM;
2255 }
2256
2257 }
2258
2259 /* query the firmware */
2260 fw_ver = s2255_get_fx2fw(dev);
2261
Dean Andersonabce21f2009-04-23 16:04:41 -03002262 printk(KERN_INFO "2255 usb firmware version %d.%d\n",
2263 (fw_ver >> 8) & 0xff,
2264 fw_ver & 0xff);
2265
2266 if (fw_ver < S2255_CUR_USB_FWVER)
Mauro Carvalho Chehabbe9ed512009-01-08 09:13:42 -03002267 dev_err(&dev->udev->dev,
Dean Andersonabce21f2009-04-23 16:04:41 -03002268 "usb firmware not up to date %d.%d\n",
2269 (fw_ver >> 8) & 0xff,
2270 fw_ver & 0xff);
Dean Anderson38f993a2008-06-26 23:15:51 -03002271
2272 for (j = 0; j < MAX_CHANNELS; j++) {
2273 dev->b_acquire[j] = 0;
2274 dev->mode[j] = mode_def;
Dean Anderson22b88d42008-08-29 15:33:19 -03002275 dev->jc[j].quality = S2255_DEF_JPEG_QUAL;
Dean Anderson38f993a2008-06-26 23:15:51 -03002276 dev->cur_fmt[j] = &formats[0];
2277 dev->mode[j].restart = 1;
2278 dev->req_image_size[j] = get_transfer_size(&mode_def);
2279 dev->frame_count[j] = 0;
2280 /* create the system buffers */
2281 s2255_create_sys_buffers(dev, j);
2282 }
2283 /* start read pipe */
2284 s2255_start_readpipe(dev);
2285
2286 dprintk(1, "S2255: board initialized\n");
2287 return 0;
2288}
2289
2290static int s2255_board_shutdown(struct s2255_dev *dev)
2291{
2292 u32 i;
2293
2294 dprintk(1, "S2255: board shutdown: %p", dev);
2295
2296 for (i = 0; i < MAX_CHANNELS; i++) {
2297 if (dev->b_acquire[i])
2298 s2255_stop_acquire(dev, i);
2299 }
2300
2301 s2255_stop_readpipe(dev);
2302
2303 for (i = 0; i < MAX_CHANNELS; i++)
2304 s2255_release_sys_buffers(dev, i);
2305
2306 /* release transfer buffers */
2307 for (i = 0; i < MAX_PIPE_BUFFERS; i++) {
2308 struct s2255_pipeinfo *pipe = &dev->pipes[i];
2309 kfree(pipe->transfer_buffer);
2310 }
2311 return 0;
2312}
2313
2314static void read_pipe_completion(struct urb *purb)
2315{
2316 struct s2255_pipeinfo *pipe_info;
2317 struct s2255_dev *dev;
2318 int status;
2319 int pipe;
2320
2321 pipe_info = purb->context;
2322 dprintk(100, "read pipe completion %p, status %d\n", purb,
2323 purb->status);
2324 if (pipe_info == NULL) {
Mauro Carvalho Chehabbe9ed512009-01-08 09:13:42 -03002325 dev_err(&purb->dev->dev, "no context!\n");
Dean Anderson38f993a2008-06-26 23:15:51 -03002326 return;
2327 }
2328
2329 dev = pipe_info->dev;
2330 if (dev == NULL) {
Mauro Carvalho Chehabbe9ed512009-01-08 09:13:42 -03002331 dev_err(&purb->dev->dev, "no context!\n");
Dean Anderson38f993a2008-06-26 23:15:51 -03002332 return;
2333 }
2334 status = purb->status;
Dean Andersonb02064c2009-04-30 12:29:38 -03002335 /* if shutting down, do not resubmit, exit immediately */
2336 if (status == -ESHUTDOWN) {
2337 dprintk(2, "read_pipe_completion: err shutdown\n");
2338 pipe_info->err_count++;
Dean Anderson38f993a2008-06-26 23:15:51 -03002339 return;
2340 }
2341
2342 if (pipe_info->state == 0) {
2343 dprintk(2, "exiting USB pipe");
2344 return;
2345 }
2346
Dean Andersonb02064c2009-04-30 12:29:38 -03002347 if (status == 0)
2348 s2255_read_video_callback(dev, pipe_info);
2349 else {
2350 pipe_info->err_count++;
2351 dprintk(1, "s2255drv: failed URB %d\n", status);
2352 }
Dean Anderson38f993a2008-06-26 23:15:51 -03002353
Dean Anderson38f993a2008-06-26 23:15:51 -03002354 pipe = usb_rcvbulkpipe(dev->udev, dev->read_endpoint);
2355 /* reuse urb */
2356 usb_fill_bulk_urb(pipe_info->stream_urb, dev->udev,
2357 pipe,
2358 pipe_info->transfer_buffer,
2359 pipe_info->cur_transfer_size,
2360 read_pipe_completion, pipe_info);
2361
2362 if (pipe_info->state != 0) {
2363 if (usb_submit_urb(pipe_info->stream_urb, GFP_KERNEL)) {
2364 dev_err(&dev->udev->dev, "error submitting urb\n");
Dean Anderson38f993a2008-06-26 23:15:51 -03002365 }
2366 } else {
2367 dprintk(2, "read pipe complete state 0\n");
2368 }
2369 return;
2370}
2371
2372static int s2255_start_readpipe(struct s2255_dev *dev)
2373{
2374 int pipe;
2375 int retval;
2376 int i;
2377 struct s2255_pipeinfo *pipe_info = dev->pipes;
2378 pipe = usb_rcvbulkpipe(dev->udev, dev->read_endpoint);
2379 dprintk(2, "start pipe IN %d\n", dev->read_endpoint);
2380
2381 for (i = 0; i < MAX_PIPE_BUFFERS; i++) {
2382 pipe_info->state = 1;
Dean Andersonabce21f2009-04-23 16:04:41 -03002383 pipe_info->err_count = 0;
Dean Anderson38f993a2008-06-26 23:15:51 -03002384 pipe_info->stream_urb = usb_alloc_urb(0, GFP_KERNEL);
2385 if (!pipe_info->stream_urb) {
2386 dev_err(&dev->udev->dev,
Mauro Carvalho Chehabbe9ed512009-01-08 09:13:42 -03002387 "ReadStream: Unable to alloc URB\n");
Dean Anderson38f993a2008-06-26 23:15:51 -03002388 return -ENOMEM;
2389 }
2390 /* transfer buffer allocated in board_init */
2391 usb_fill_bulk_urb(pipe_info->stream_urb, dev->udev,
2392 pipe,
2393 pipe_info->transfer_buffer,
2394 pipe_info->cur_transfer_size,
2395 read_pipe_completion, pipe_info);
2396
Dean Anderson38f993a2008-06-26 23:15:51 -03002397 dprintk(4, "submitting URB %p\n", pipe_info->stream_urb);
2398 retval = usb_submit_urb(pipe_info->stream_urb, GFP_KERNEL);
2399 if (retval) {
2400 printk(KERN_ERR "s2255: start read pipe failed\n");
2401 return retval;
2402 }
2403 }
2404
2405 return 0;
2406}
2407
2408/* starts acquisition process */
2409static int s2255_start_acquire(struct s2255_dev *dev, unsigned long chn)
2410{
2411 unsigned char *buffer;
2412 int res;
2413 unsigned long chn_rev;
2414 int j;
2415 if (chn >= MAX_CHANNELS) {
2416 dprintk(2, "start acquire failed, bad channel %lu\n", chn);
2417 return -1;
2418 }
2419
2420 chn_rev = G_chnmap[chn];
2421 dprintk(1, "S2255: start acquire %lu \n", chn);
2422
2423 buffer = kzalloc(512, GFP_KERNEL);
2424 if (buffer == NULL) {
2425 dev_err(&dev->udev->dev, "out of mem\n");
2426 return -ENOMEM;
2427 }
2428
2429 dev->last_frame[chn] = -1;
2430 dev->bad_payload[chn] = 0;
2431 dev->cur_frame[chn] = 0;
2432 for (j = 0; j < SYS_FRAMES; j++) {
2433 dev->buffer[chn].frame[j].ulState = 0;
2434 dev->buffer[chn].frame[j].cur_size = 0;
2435 }
2436
2437 /* send the start command */
Dean Anderson3fa00602010-03-04 20:47:33 -03002438 *(__le32 *) buffer = IN_DATA_TOKEN;
2439 *((__le32 *) buffer + 1) = (__le32) cpu_to_le32(chn_rev);
2440 *((__le32 *) buffer + 2) = CMD_START;
Dean Anderson38f993a2008-06-26 23:15:51 -03002441 res = s2255_write_config(dev->udev, (unsigned char *)buffer, 512);
2442 if (res != 0)
2443 dev_err(&dev->udev->dev, "CMD_START error\n");
2444
2445 dprintk(2, "start acquire exit[%lu] %d \n", chn, res);
2446 kfree(buffer);
2447 return 0;
2448}
2449
2450static int s2255_stop_acquire(struct s2255_dev *dev, unsigned long chn)
2451{
2452 unsigned char *buffer;
2453 int res;
2454 unsigned long chn_rev;
Dean Anderson38f993a2008-06-26 23:15:51 -03002455 if (chn >= MAX_CHANNELS) {
2456 dprintk(2, "stop acquire failed, bad channel %lu\n", chn);
2457 return -1;
2458 }
2459 chn_rev = G_chnmap[chn];
Dean Anderson38f993a2008-06-26 23:15:51 -03002460 buffer = kzalloc(512, GFP_KERNEL);
2461 if (buffer == NULL) {
2462 dev_err(&dev->udev->dev, "out of mem\n");
2463 return -ENOMEM;
2464 }
Dean Anderson38f993a2008-06-26 23:15:51 -03002465 /* send the stop command */
2466 dprintk(4, "stop acquire %lu\n", chn);
Dean Anderson3fa00602010-03-04 20:47:33 -03002467 *(__le32 *) buffer = IN_DATA_TOKEN;
2468 *((__le32 *) buffer + 1) = (__le32) cpu_to_le32(chn_rev);
2469 *((__le32 *) buffer + 2) = CMD_STOP;
Dean Anderson38f993a2008-06-26 23:15:51 -03002470 res = s2255_write_config(dev->udev, (unsigned char *)buffer, 512);
2471
2472 if (res != 0)
2473 dev_err(&dev->udev->dev, "CMD_STOP error\n");
2474
2475 dprintk(4, "stop acquire: releasing states \n");
2476
2477 kfree(buffer);
2478 dev->b_acquire[chn] = 0;
2479
Dean Anderson14d96262008-08-25 13:58:55 -03002480 return res;
Dean Anderson38f993a2008-06-26 23:15:51 -03002481}
2482
2483static void s2255_stop_readpipe(struct s2255_dev *dev)
2484{
2485 int j;
2486
2487 if (dev == NULL) {
Mauro Carvalho Chehabbe9ed512009-01-08 09:13:42 -03002488 s2255_dev_err(&dev->udev->dev, "invalid device\n");
Dean Anderson38f993a2008-06-26 23:15:51 -03002489 return;
2490 }
2491 dprintk(4, "stop read pipe\n");
2492 for (j = 0; j < MAX_PIPE_BUFFERS; j++) {
2493 struct s2255_pipeinfo *pipe_info = &dev->pipes[j];
2494 if (pipe_info) {
2495 if (pipe_info->state == 0)
2496 continue;
2497 pipe_info->state = 0;
Dean Anderson38f993a2008-06-26 23:15:51 -03002498 }
2499 }
2500
2501 for (j = 0; j < MAX_PIPE_BUFFERS; j++) {
2502 struct s2255_pipeinfo *pipe_info = &dev->pipes[j];
2503 if (pipe_info->stream_urb) {
2504 /* cancel urb */
2505 usb_kill_urb(pipe_info->stream_urb);
2506 usb_free_urb(pipe_info->stream_urb);
2507 pipe_info->stream_urb = NULL;
2508 }
2509 }
2510 dprintk(2, "s2255 stop read pipe: %d\n", j);
2511 return;
2512}
2513
Dean Anderson14d96262008-08-25 13:58:55 -03002514static void s2255_fwload_start(struct s2255_dev *dev, int reset)
Dean Anderson38f993a2008-06-26 23:15:51 -03002515{
Dean Anderson14d96262008-08-25 13:58:55 -03002516 if (reset)
2517 s2255_reset_dsppower(dev);
Dean Anderson38f993a2008-06-26 23:15:51 -03002518 dev->fw_data->fw_size = dev->fw_data->fw->size;
2519 atomic_set(&dev->fw_data->fw_state, S2255_FW_NOTLOADED);
2520 memcpy(dev->fw_data->pfw_data,
2521 dev->fw_data->fw->data, CHUNK_SIZE);
2522 dev->fw_data->fw_loaded = CHUNK_SIZE;
2523 usb_fill_bulk_urb(dev->fw_data->fw_urb, dev->udev,
2524 usb_sndbulkpipe(dev->udev, 2),
2525 dev->fw_data->pfw_data,
2526 CHUNK_SIZE, s2255_fwchunk_complete,
2527 dev->fw_data);
2528 mod_timer(&dev->timer, jiffies + HZ);
2529}
2530
2531/* standard usb probe function */
2532static int s2255_probe(struct usb_interface *interface,
2533 const struct usb_device_id *id)
2534{
2535 struct s2255_dev *dev = NULL;
2536 struct usb_host_interface *iface_desc;
2537 struct usb_endpoint_descriptor *endpoint;
2538 int i;
2539 int retval = -ENOMEM;
Dean Anderson14d96262008-08-25 13:58:55 -03002540 __le32 *pdata;
2541 int fw_size;
Dean Anderson38f993a2008-06-26 23:15:51 -03002542
2543 dprintk(2, "s2255: probe\n");
2544
2545 /* allocate memory for our device state and initialize it to zero */
2546 dev = kzalloc(sizeof(struct s2255_dev), GFP_KERNEL);
2547 if (dev == NULL) {
Mauro Carvalho Chehabbe9ed512009-01-08 09:13:42 -03002548 s2255_dev_err(&interface->dev, "out of memory\n");
Dean Anderson38f993a2008-06-26 23:15:51 -03002549 goto error;
2550 }
2551
2552 dev->fw_data = kzalloc(sizeof(struct s2255_fw), GFP_KERNEL);
2553 if (!dev->fw_data)
2554 goto error;
2555
2556 mutex_init(&dev->lock);
2557 mutex_init(&dev->open_lock);
2558
2559 /* grab usb_device and save it */
2560 dev->udev = usb_get_dev(interface_to_usbdev(interface));
2561 if (dev->udev == NULL) {
2562 dev_err(&interface->dev, "null usb device\n");
2563 retval = -ENODEV;
2564 goto error;
2565 }
2566 kref_init(&dev->kref);
2567 dprintk(1, "dev: %p, kref: %p udev %p interface %p\n", dev, &dev->kref,
2568 dev->udev, interface);
2569 dev->interface = interface;
2570 /* set up the endpoint information */
2571 iface_desc = interface->cur_altsetting;
2572 dprintk(1, "num endpoints %d\n", iface_desc->desc.bNumEndpoints);
2573 for (i = 0; i < iface_desc->desc.bNumEndpoints; ++i) {
2574 endpoint = &iface_desc->endpoint[i].desc;
2575 if (!dev->read_endpoint && usb_endpoint_is_bulk_in(endpoint)) {
2576 /* we found the bulk in endpoint */
2577 dev->read_endpoint = endpoint->bEndpointAddress;
2578 }
2579 }
2580
2581 if (!dev->read_endpoint) {
Mauro Carvalho Chehabbe9ed512009-01-08 09:13:42 -03002582 dev_err(&interface->dev, "Could not find bulk-in endpoint\n");
Dean Anderson38f993a2008-06-26 23:15:51 -03002583 goto error;
2584 }
2585
2586 /* set intfdata */
2587 usb_set_intfdata(interface, dev);
2588
2589 dprintk(100, "after intfdata %p\n", dev);
2590
2591 init_timer(&dev->timer);
2592 dev->timer.function = s2255_timer;
2593 dev->timer.data = (unsigned long)dev->fw_data;
2594
2595 init_waitqueue_head(&dev->fw_data->wait_fw);
Dean Anderson4de39f52010-03-03 19:39:19 -03002596 for (i = 0; i < MAX_CHANNELS; i++) {
Dean Anderson14d96262008-08-25 13:58:55 -03002597 init_waitqueue_head(&dev->wait_setmode[i]);
Dean Anderson4de39f52010-03-03 19:39:19 -03002598 init_waitqueue_head(&dev->wait_vidstatus[i]);
2599 }
Dean Anderson38f993a2008-06-26 23:15:51 -03002600
2601 dev->fw_data->fw_urb = usb_alloc_urb(0, GFP_KERNEL);
2602
2603 if (!dev->fw_data->fw_urb) {
2604 dev_err(&interface->dev, "out of memory!\n");
2605 goto error;
2606 }
2607 dev->fw_data->pfw_data = kzalloc(CHUNK_SIZE, GFP_KERNEL);
2608 if (!dev->fw_data->pfw_data) {
2609 dev_err(&interface->dev, "out of memory!\n");
2610 goto error;
2611 }
2612 /* load the first chunk */
2613 if (request_firmware(&dev->fw_data->fw,
2614 FIRMWARE_FILE_NAME, &dev->udev->dev)) {
2615 printk(KERN_ERR "sensoray 2255 failed to get firmware\n");
2616 goto error;
2617 }
Dean Anderson14d96262008-08-25 13:58:55 -03002618 /* check the firmware is valid */
2619 fw_size = dev->fw_data->fw->size;
2620 pdata = (__le32 *) &dev->fw_data->fw->data[fw_size - 8];
Dean Anderson38f993a2008-06-26 23:15:51 -03002621
Dean Anderson14d96262008-08-25 13:58:55 -03002622 if (*pdata != S2255_FW_MARKER) {
2623 printk(KERN_INFO "Firmware invalid.\n");
2624 retval = -ENODEV;
2625 goto error;
2626 } else {
2627 /* make sure firmware is the latest */
2628 __le32 *pRel;
2629 pRel = (__le32 *) &dev->fw_data->fw->data[fw_size - 4];
2630 printk(KERN_INFO "s2255 dsp fw version %x\n", *pRel);
Dean Anderson4de39f52010-03-03 19:39:19 -03002631 dev->dsp_fw_ver = *pRel;
2632 if (*pRel < S2255_CUR_DSP_FWVER)
2633 printk(KERN_INFO "s2255: f2255usb.bin out of date.\n");
Dean Anderson14d96262008-08-25 13:58:55 -03002634 }
Dean Anderson38f993a2008-06-26 23:15:51 -03002635 /* loads v4l specific */
2636 s2255_probe_v4l(dev);
Dean Anderson14d96262008-08-25 13:58:55 -03002637 usb_reset_device(dev->udev);
Dean Anderson38f993a2008-06-26 23:15:51 -03002638 /* load 2255 board specific */
Dean Andersonabce21f2009-04-23 16:04:41 -03002639 retval = s2255_board_init(dev);
2640 if (retval)
2641 goto error;
Dean Anderson38f993a2008-06-26 23:15:51 -03002642
2643 dprintk(4, "before probe done %p\n", dev);
2644 spin_lock_init(&dev->slock);
2645
Dean Anderson14d96262008-08-25 13:58:55 -03002646 s2255_fwload_start(dev, 0);
Dean Anderson38f993a2008-06-26 23:15:51 -03002647 dev_info(&interface->dev, "Sensoray 2255 detected\n");
2648 return 0;
2649error:
2650 return retval;
2651}
2652
2653/* disconnect routine. when board is removed physically or with rmmod */
2654static void s2255_disconnect(struct usb_interface *interface)
2655{
2656 struct s2255_dev *dev = NULL;
Dean Anderson14d96262008-08-25 13:58:55 -03002657 int i;
Dean Anderson38f993a2008-06-26 23:15:51 -03002658 dprintk(1, "s2255: disconnect interface %p\n", interface);
2659 dev = usb_get_intfdata(interface);
Dean Anderson14d96262008-08-25 13:58:55 -03002660
2661 /*
2662 * wake up any of the timers to allow open_lock to be
2663 * acquired sooner
2664 */
2665 atomic_set(&dev->fw_data->fw_state, S2255_FW_DISCONNECTING);
2666 wake_up(&dev->fw_data->wait_fw);
2667 for (i = 0; i < MAX_CHANNELS; i++) {
2668 dev->setmode_ready[i] = 1;
2669 wake_up(&dev->wait_setmode[i]);
Dean Anderson4de39f52010-03-03 19:39:19 -03002670 dev->vidstatus_ready[i] = 1;
2671 wake_up(&dev->wait_vidstatus[i]);
Dean Anderson14d96262008-08-25 13:58:55 -03002672 }
2673
2674 mutex_lock(&dev->open_lock);
2675 usb_set_intfdata(interface, NULL);
2676 mutex_unlock(&dev->open_lock);
2677
Dean Anderson38f993a2008-06-26 23:15:51 -03002678 if (dev) {
2679 kref_put(&dev->kref, s2255_destroy);
2680 dprintk(1, "s2255drv: disconnect\n");
2681 dev_info(&interface->dev, "s2255usb now disconnected\n");
2682 }
Dean Anderson38f993a2008-06-26 23:15:51 -03002683}
2684
2685static struct usb_driver s2255_driver = {
Mauro Carvalho Chehabbe9ed512009-01-08 09:13:42 -03002686 .name = S2255_DRIVER_NAME,
Dean Anderson38f993a2008-06-26 23:15:51 -03002687 .probe = s2255_probe,
2688 .disconnect = s2255_disconnect,
2689 .id_table = s2255_table,
2690};
2691
2692static int __init usb_s2255_init(void)
2693{
2694 int result;
2695
2696 /* register this driver with the USB subsystem */
2697 result = usb_register(&s2255_driver);
2698
2699 if (result)
Mauro Carvalho Chehabbe9ed512009-01-08 09:13:42 -03002700 pr_err(KBUILD_MODNAME
2701 ": usb_register failed. Error number %d\n", result);
Dean Anderson38f993a2008-06-26 23:15:51 -03002702
2703 dprintk(2, "s2255_init: done\n");
2704 return result;
2705}
2706
2707static void __exit usb_s2255_exit(void)
2708{
2709 usb_deregister(&s2255_driver);
2710}
2711
2712module_init(usb_s2255_init);
2713module_exit(usb_s2255_exit);
2714
2715MODULE_DESCRIPTION("Sensoray 2255 Video for Linux driver");
2716MODULE_AUTHOR("Dean Anderson (Sensoray Company Inc.)");
2717MODULE_LICENSE("GPL");