[media] v4l: removal of old, obsolete ioctls
[linux-2.6/linux-acpi-2.6/ibm-acpi-2.6.git] / drivers / media / video / v4l2-ioctl.c
blob7a720745c3fad1242e30d81e4a62ab431a3d0429
1 /*
2 * Video capture interface for Linux version 2
4 * A generic framework to process V4L2 ioctl commands.
6 * This program is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU General Public License
8 * as published by the Free Software Foundation; either version
9 * 2 of the License, or (at your option) any later version.
11 * Authors: Alan Cox, <alan@lxorguk.ukuu.org.uk> (version 1)
12 * Mauro Carvalho Chehab <mchehab@infradead.org> (version 2)
15 #include <linux/module.h>
16 #include <linux/slab.h>
17 #include <linux/types.h>
18 #include <linux/kernel.h>
20 #include <linux/videodev2.h>
22 #include <media/v4l2-common.h>
23 #include <media/v4l2-ioctl.h>
24 #include <media/v4l2-ctrls.h>
25 #include <media/v4l2-fh.h>
26 #include <media/v4l2-event.h>
27 #include <media/v4l2-chip-ident.h>
29 #define dbgarg(cmd, fmt, arg...) \
30 do { \
31 if (vfd->debug & V4L2_DEBUG_IOCTL_ARG) { \
32 printk(KERN_DEBUG "%s: ", vfd->name); \
33 v4l_printk_ioctl(cmd); \
34 printk(" " fmt, ## arg); \
35 } \
36 } while (0)
38 #define dbgarg2(fmt, arg...) \
39 do { \
40 if (vfd->debug & V4L2_DEBUG_IOCTL_ARG) \
41 printk(KERN_DEBUG "%s: " fmt, vfd->name, ## arg);\
42 } while (0)
44 #define dbgarg3(fmt, arg...) \
45 do { \
46 if (vfd->debug & V4L2_DEBUG_IOCTL_ARG) \
47 printk(KERN_CONT "%s: " fmt, vfd->name, ## arg);\
48 } while (0)
50 /* Zero out the end of the struct pointed to by p. Everthing after, but
51 * not including, the specified field is cleared. */
52 #define CLEAR_AFTER_FIELD(p, field) \
53 memset((u8 *)(p) + offsetof(typeof(*(p)), field) + sizeof((p)->field), \
54 0, sizeof(*(p)) - offsetof(typeof(*(p)), field) - sizeof((p)->field))
56 struct std_descr {
57 v4l2_std_id std;
58 const char *descr;
61 static const struct std_descr standards[] = {
62 { V4L2_STD_NTSC, "NTSC" },
63 { V4L2_STD_NTSC_M, "NTSC-M" },
64 { V4L2_STD_NTSC_M_JP, "NTSC-M-JP" },
65 { V4L2_STD_NTSC_M_KR, "NTSC-M-KR" },
66 { V4L2_STD_NTSC_443, "NTSC-443" },
67 { V4L2_STD_PAL, "PAL" },
68 { V4L2_STD_PAL_BG, "PAL-BG" },
69 { V4L2_STD_PAL_B, "PAL-B" },
70 { V4L2_STD_PAL_B1, "PAL-B1" },
71 { V4L2_STD_PAL_G, "PAL-G" },
72 { V4L2_STD_PAL_H, "PAL-H" },
73 { V4L2_STD_PAL_I, "PAL-I" },
74 { V4L2_STD_PAL_DK, "PAL-DK" },
75 { V4L2_STD_PAL_D, "PAL-D" },
76 { V4L2_STD_PAL_D1, "PAL-D1" },
77 { V4L2_STD_PAL_K, "PAL-K" },
78 { V4L2_STD_PAL_M, "PAL-M" },
79 { V4L2_STD_PAL_N, "PAL-N" },
80 { V4L2_STD_PAL_Nc, "PAL-Nc" },
81 { V4L2_STD_PAL_60, "PAL-60" },
82 { V4L2_STD_SECAM, "SECAM" },
83 { V4L2_STD_SECAM_B, "SECAM-B" },
84 { V4L2_STD_SECAM_G, "SECAM-G" },
85 { V4L2_STD_SECAM_H, "SECAM-H" },
86 { V4L2_STD_SECAM_DK, "SECAM-DK" },
87 { V4L2_STD_SECAM_D, "SECAM-D" },
88 { V4L2_STD_SECAM_K, "SECAM-K" },
89 { V4L2_STD_SECAM_K1, "SECAM-K1" },
90 { V4L2_STD_SECAM_L, "SECAM-L" },
91 { V4L2_STD_SECAM_LC, "SECAM-Lc" },
92 { 0, "Unknown" }
95 /* video4linux standard ID conversion to standard name
97 const char *v4l2_norm_to_name(v4l2_std_id id)
99 u32 myid = id;
100 int i;
102 /* HACK: ppc32 architecture doesn't have __ucmpdi2 function to handle
103 64 bit comparations. So, on that architecture, with some gcc
104 variants, compilation fails. Currently, the max value is 30bit wide.
106 BUG_ON(myid != id);
108 for (i = 0; standards[i].std; i++)
109 if (myid == standards[i].std)
110 break;
111 return standards[i].descr;
113 EXPORT_SYMBOL(v4l2_norm_to_name);
115 /* Returns frame period for the given standard */
116 void v4l2_video_std_frame_period(int id, struct v4l2_fract *frameperiod)
118 if (id & V4L2_STD_525_60) {
119 frameperiod->numerator = 1001;
120 frameperiod->denominator = 30000;
121 } else {
122 frameperiod->numerator = 1;
123 frameperiod->denominator = 25;
126 EXPORT_SYMBOL(v4l2_video_std_frame_period);
128 /* Fill in the fields of a v4l2_standard structure according to the
129 'id' and 'transmission' parameters. Returns negative on error. */
130 int v4l2_video_std_construct(struct v4l2_standard *vs,
131 int id, const char *name)
133 vs->id = id;
134 v4l2_video_std_frame_period(id, &vs->frameperiod);
135 vs->framelines = (id & V4L2_STD_525_60) ? 525 : 625;
136 strlcpy(vs->name, name, sizeof(vs->name));
137 return 0;
139 EXPORT_SYMBOL(v4l2_video_std_construct);
141 /* ----------------------------------------------------------------- */
142 /* some arrays for pretty-printing debug messages of enum types */
144 const char *v4l2_field_names[] = {
145 [V4L2_FIELD_ANY] = "any",
146 [V4L2_FIELD_NONE] = "none",
147 [V4L2_FIELD_TOP] = "top",
148 [V4L2_FIELD_BOTTOM] = "bottom",
149 [V4L2_FIELD_INTERLACED] = "interlaced",
150 [V4L2_FIELD_SEQ_TB] = "seq-tb",
151 [V4L2_FIELD_SEQ_BT] = "seq-bt",
152 [V4L2_FIELD_ALTERNATE] = "alternate",
153 [V4L2_FIELD_INTERLACED_TB] = "interlaced-tb",
154 [V4L2_FIELD_INTERLACED_BT] = "interlaced-bt",
156 EXPORT_SYMBOL(v4l2_field_names);
158 const char *v4l2_type_names[] = {
159 [V4L2_BUF_TYPE_VIDEO_CAPTURE] = "vid-cap",
160 [V4L2_BUF_TYPE_VIDEO_OVERLAY] = "vid-overlay",
161 [V4L2_BUF_TYPE_VIDEO_OUTPUT] = "vid-out",
162 [V4L2_BUF_TYPE_VBI_CAPTURE] = "vbi-cap",
163 [V4L2_BUF_TYPE_VBI_OUTPUT] = "vbi-out",
164 [V4L2_BUF_TYPE_SLICED_VBI_CAPTURE] = "sliced-vbi-cap",
165 [V4L2_BUF_TYPE_SLICED_VBI_OUTPUT] = "sliced-vbi-out",
166 [V4L2_BUF_TYPE_VIDEO_OUTPUT_OVERLAY] = "vid-out-overlay",
167 [V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE] = "vid-cap-mplane",
168 [V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE] = "vid-out-mplane",
170 EXPORT_SYMBOL(v4l2_type_names);
172 static const char *v4l2_memory_names[] = {
173 [V4L2_MEMORY_MMAP] = "mmap",
174 [V4L2_MEMORY_USERPTR] = "userptr",
175 [V4L2_MEMORY_OVERLAY] = "overlay",
178 #define prt_names(a, arr) ((((a) >= 0) && ((a) < ARRAY_SIZE(arr))) ? \
179 arr[a] : "unknown")
181 /* ------------------------------------------------------------------ */
182 /* debug help functions */
183 static const char *v4l2_ioctls[] = {
184 [_IOC_NR(VIDIOC_QUERYCAP)] = "VIDIOC_QUERYCAP",
185 [_IOC_NR(VIDIOC_RESERVED)] = "VIDIOC_RESERVED",
186 [_IOC_NR(VIDIOC_ENUM_FMT)] = "VIDIOC_ENUM_FMT",
187 [_IOC_NR(VIDIOC_G_FMT)] = "VIDIOC_G_FMT",
188 [_IOC_NR(VIDIOC_S_FMT)] = "VIDIOC_S_FMT",
189 [_IOC_NR(VIDIOC_REQBUFS)] = "VIDIOC_REQBUFS",
190 [_IOC_NR(VIDIOC_QUERYBUF)] = "VIDIOC_QUERYBUF",
191 [_IOC_NR(VIDIOC_G_FBUF)] = "VIDIOC_G_FBUF",
192 [_IOC_NR(VIDIOC_S_FBUF)] = "VIDIOC_S_FBUF",
193 [_IOC_NR(VIDIOC_OVERLAY)] = "VIDIOC_OVERLAY",
194 [_IOC_NR(VIDIOC_QBUF)] = "VIDIOC_QBUF",
195 [_IOC_NR(VIDIOC_DQBUF)] = "VIDIOC_DQBUF",
196 [_IOC_NR(VIDIOC_STREAMON)] = "VIDIOC_STREAMON",
197 [_IOC_NR(VIDIOC_STREAMOFF)] = "VIDIOC_STREAMOFF",
198 [_IOC_NR(VIDIOC_G_PARM)] = "VIDIOC_G_PARM",
199 [_IOC_NR(VIDIOC_S_PARM)] = "VIDIOC_S_PARM",
200 [_IOC_NR(VIDIOC_G_STD)] = "VIDIOC_G_STD",
201 [_IOC_NR(VIDIOC_S_STD)] = "VIDIOC_S_STD",
202 [_IOC_NR(VIDIOC_ENUMSTD)] = "VIDIOC_ENUMSTD",
203 [_IOC_NR(VIDIOC_ENUMINPUT)] = "VIDIOC_ENUMINPUT",
204 [_IOC_NR(VIDIOC_G_CTRL)] = "VIDIOC_G_CTRL",
205 [_IOC_NR(VIDIOC_S_CTRL)] = "VIDIOC_S_CTRL",
206 [_IOC_NR(VIDIOC_G_TUNER)] = "VIDIOC_G_TUNER",
207 [_IOC_NR(VIDIOC_S_TUNER)] = "VIDIOC_S_TUNER",
208 [_IOC_NR(VIDIOC_G_AUDIO)] = "VIDIOC_G_AUDIO",
209 [_IOC_NR(VIDIOC_S_AUDIO)] = "VIDIOC_S_AUDIO",
210 [_IOC_NR(VIDIOC_QUERYCTRL)] = "VIDIOC_QUERYCTRL",
211 [_IOC_NR(VIDIOC_QUERYMENU)] = "VIDIOC_QUERYMENU",
212 [_IOC_NR(VIDIOC_G_INPUT)] = "VIDIOC_G_INPUT",
213 [_IOC_NR(VIDIOC_S_INPUT)] = "VIDIOC_S_INPUT",
214 [_IOC_NR(VIDIOC_G_OUTPUT)] = "VIDIOC_G_OUTPUT",
215 [_IOC_NR(VIDIOC_S_OUTPUT)] = "VIDIOC_S_OUTPUT",
216 [_IOC_NR(VIDIOC_ENUMOUTPUT)] = "VIDIOC_ENUMOUTPUT",
217 [_IOC_NR(VIDIOC_G_AUDOUT)] = "VIDIOC_G_AUDOUT",
218 [_IOC_NR(VIDIOC_S_AUDOUT)] = "VIDIOC_S_AUDOUT",
219 [_IOC_NR(VIDIOC_G_MODULATOR)] = "VIDIOC_G_MODULATOR",
220 [_IOC_NR(VIDIOC_S_MODULATOR)] = "VIDIOC_S_MODULATOR",
221 [_IOC_NR(VIDIOC_G_FREQUENCY)] = "VIDIOC_G_FREQUENCY",
222 [_IOC_NR(VIDIOC_S_FREQUENCY)] = "VIDIOC_S_FREQUENCY",
223 [_IOC_NR(VIDIOC_CROPCAP)] = "VIDIOC_CROPCAP",
224 [_IOC_NR(VIDIOC_G_CROP)] = "VIDIOC_G_CROP",
225 [_IOC_NR(VIDIOC_S_CROP)] = "VIDIOC_S_CROP",
226 [_IOC_NR(VIDIOC_G_JPEGCOMP)] = "VIDIOC_G_JPEGCOMP",
227 [_IOC_NR(VIDIOC_S_JPEGCOMP)] = "VIDIOC_S_JPEGCOMP",
228 [_IOC_NR(VIDIOC_QUERYSTD)] = "VIDIOC_QUERYSTD",
229 [_IOC_NR(VIDIOC_TRY_FMT)] = "VIDIOC_TRY_FMT",
230 [_IOC_NR(VIDIOC_ENUMAUDIO)] = "VIDIOC_ENUMAUDIO",
231 [_IOC_NR(VIDIOC_ENUMAUDOUT)] = "VIDIOC_ENUMAUDOUT",
232 [_IOC_NR(VIDIOC_G_PRIORITY)] = "VIDIOC_G_PRIORITY",
233 [_IOC_NR(VIDIOC_S_PRIORITY)] = "VIDIOC_S_PRIORITY",
234 [_IOC_NR(VIDIOC_G_SLICED_VBI_CAP)] = "VIDIOC_G_SLICED_VBI_CAP",
235 [_IOC_NR(VIDIOC_LOG_STATUS)] = "VIDIOC_LOG_STATUS",
236 [_IOC_NR(VIDIOC_G_EXT_CTRLS)] = "VIDIOC_G_EXT_CTRLS",
237 [_IOC_NR(VIDIOC_S_EXT_CTRLS)] = "VIDIOC_S_EXT_CTRLS",
238 [_IOC_NR(VIDIOC_TRY_EXT_CTRLS)] = "VIDIOC_TRY_EXT_CTRLS",
239 #if 1
240 [_IOC_NR(VIDIOC_ENUM_FRAMESIZES)] = "VIDIOC_ENUM_FRAMESIZES",
241 [_IOC_NR(VIDIOC_ENUM_FRAMEINTERVALS)] = "VIDIOC_ENUM_FRAMEINTERVALS",
242 [_IOC_NR(VIDIOC_G_ENC_INDEX)] = "VIDIOC_G_ENC_INDEX",
243 [_IOC_NR(VIDIOC_ENCODER_CMD)] = "VIDIOC_ENCODER_CMD",
244 [_IOC_NR(VIDIOC_TRY_ENCODER_CMD)] = "VIDIOC_TRY_ENCODER_CMD",
246 [_IOC_NR(VIDIOC_DBG_S_REGISTER)] = "VIDIOC_DBG_S_REGISTER",
247 [_IOC_NR(VIDIOC_DBG_G_REGISTER)] = "VIDIOC_DBG_G_REGISTER",
249 [_IOC_NR(VIDIOC_DBG_G_CHIP_IDENT)] = "VIDIOC_DBG_G_CHIP_IDENT",
250 [_IOC_NR(VIDIOC_S_HW_FREQ_SEEK)] = "VIDIOC_S_HW_FREQ_SEEK",
251 #endif
252 [_IOC_NR(VIDIOC_ENUM_DV_PRESETS)] = "VIDIOC_ENUM_DV_PRESETS",
253 [_IOC_NR(VIDIOC_S_DV_PRESET)] = "VIDIOC_S_DV_PRESET",
254 [_IOC_NR(VIDIOC_G_DV_PRESET)] = "VIDIOC_G_DV_PRESET",
255 [_IOC_NR(VIDIOC_QUERY_DV_PRESET)] = "VIDIOC_QUERY_DV_PRESET",
256 [_IOC_NR(VIDIOC_S_DV_TIMINGS)] = "VIDIOC_S_DV_TIMINGS",
257 [_IOC_NR(VIDIOC_G_DV_TIMINGS)] = "VIDIOC_G_DV_TIMINGS",
258 [_IOC_NR(VIDIOC_DQEVENT)] = "VIDIOC_DQEVENT",
259 [_IOC_NR(VIDIOC_SUBSCRIBE_EVENT)] = "VIDIOC_SUBSCRIBE_EVENT",
260 [_IOC_NR(VIDIOC_UNSUBSCRIBE_EVENT)] = "VIDIOC_UNSUBSCRIBE_EVENT",
262 #define V4L2_IOCTLS ARRAY_SIZE(v4l2_ioctls)
264 /* Common ioctl debug function. This function can be used by
265 external ioctl messages as well as internal V4L ioctl */
266 void v4l_printk_ioctl(unsigned int cmd)
268 char *dir, *type;
270 switch (_IOC_TYPE(cmd)) {
271 case 'd':
272 type = "v4l2_int";
273 break;
274 case 'V':
275 if (_IOC_NR(cmd) >= V4L2_IOCTLS) {
276 type = "v4l2";
277 break;
279 printk("%s", v4l2_ioctls[_IOC_NR(cmd)]);
280 return;
281 default:
282 type = "unknown";
285 switch (_IOC_DIR(cmd)) {
286 case _IOC_NONE: dir = "--"; break;
287 case _IOC_READ: dir = "r-"; break;
288 case _IOC_WRITE: dir = "-w"; break;
289 case _IOC_READ | _IOC_WRITE: dir = "rw"; break;
290 default: dir = "*ERR*"; break;
292 printk("%s ioctl '%c', dir=%s, #%d (0x%08x)",
293 type, _IOC_TYPE(cmd), dir, _IOC_NR(cmd), cmd);
295 EXPORT_SYMBOL(v4l_printk_ioctl);
298 * helper function -- handles userspace copying for ioctl arguments
299 * Obsolete usercopy function - Should be removed soon
301 long
302 video_usercopy(struct file *file, unsigned int cmd, unsigned long arg,
303 v4l2_kioctl func)
305 char sbuf[128];
306 void *mbuf = NULL;
307 void *parg = NULL;
308 long err = -EINVAL;
309 int is_ext_ctrl;
310 size_t ctrls_size = 0;
311 void __user *user_ptr = NULL;
313 is_ext_ctrl = (cmd == VIDIOC_S_EXT_CTRLS || cmd == VIDIOC_G_EXT_CTRLS ||
314 cmd == VIDIOC_TRY_EXT_CTRLS);
316 /* Copy arguments into temp kernel buffer */
317 switch (_IOC_DIR(cmd)) {
318 case _IOC_NONE:
319 parg = NULL;
320 break;
321 case _IOC_READ:
322 case _IOC_WRITE:
323 case (_IOC_WRITE | _IOC_READ):
324 if (_IOC_SIZE(cmd) <= sizeof(sbuf)) {
325 parg = sbuf;
326 } else {
327 /* too big to allocate from stack */
328 mbuf = kmalloc(_IOC_SIZE(cmd), GFP_KERNEL);
329 if (NULL == mbuf)
330 return -ENOMEM;
331 parg = mbuf;
334 err = -EFAULT;
335 if (_IOC_DIR(cmd) & _IOC_WRITE)
336 if (copy_from_user(parg, (void __user *)arg, _IOC_SIZE(cmd)))
337 goto out;
338 break;
340 if (is_ext_ctrl) {
341 struct v4l2_ext_controls *p = parg;
343 /* In case of an error, tell the caller that it wasn't
344 a specific control that caused it. */
345 p->error_idx = p->count;
346 user_ptr = (void __user *)p->controls;
347 if (p->count) {
348 ctrls_size = sizeof(struct v4l2_ext_control) * p->count;
349 /* Note: v4l2_ext_controls fits in sbuf[] so mbuf is still NULL. */
350 mbuf = kmalloc(ctrls_size, GFP_KERNEL);
351 err = -ENOMEM;
352 if (NULL == mbuf)
353 goto out_ext_ctrl;
354 err = -EFAULT;
355 if (copy_from_user(mbuf, user_ptr, ctrls_size))
356 goto out_ext_ctrl;
357 p->controls = mbuf;
361 /* call driver */
362 err = func(file, cmd, parg);
363 if (err == -ENOIOCTLCMD)
364 err = -EINVAL;
365 if (is_ext_ctrl) {
366 struct v4l2_ext_controls *p = parg;
368 p->controls = (void *)user_ptr;
369 if (p->count && err == 0 && copy_to_user(user_ptr, mbuf, ctrls_size))
370 err = -EFAULT;
371 goto out_ext_ctrl;
373 if (err < 0)
374 goto out;
376 out_ext_ctrl:
377 /* Copy results into user buffer */
378 switch (_IOC_DIR(cmd)) {
379 case _IOC_READ:
380 case (_IOC_WRITE | _IOC_READ):
381 if (copy_to_user((void __user *)arg, parg, _IOC_SIZE(cmd)))
382 err = -EFAULT;
383 break;
386 out:
387 kfree(mbuf);
388 return err;
390 EXPORT_SYMBOL(video_usercopy);
392 static void dbgbuf(unsigned int cmd, struct video_device *vfd,
393 struct v4l2_buffer *p)
395 struct v4l2_timecode *tc = &p->timecode;
396 struct v4l2_plane *plane;
397 int i;
399 dbgarg(cmd, "%02ld:%02d:%02d.%08ld index=%d, type=%s, "
400 "flags=0x%08d, field=%0d, sequence=%d, memory=%s\n",
401 p->timestamp.tv_sec / 3600,
402 (int)(p->timestamp.tv_sec / 60) % 60,
403 (int)(p->timestamp.tv_sec % 60),
404 (long)p->timestamp.tv_usec,
405 p->index,
406 prt_names(p->type, v4l2_type_names),
407 p->flags, p->field, p->sequence,
408 prt_names(p->memory, v4l2_memory_names));
410 if (V4L2_TYPE_IS_MULTIPLANAR(p->type) && p->m.planes) {
411 for (i = 0; i < p->length; ++i) {
412 plane = &p->m.planes[i];
413 dbgarg2("plane %d: bytesused=%d, data_offset=0x%08x "
414 "offset/userptr=0x%08lx, length=%d\n",
415 i, plane->bytesused, plane->data_offset,
416 plane->m.userptr, plane->length);
418 } else {
419 dbgarg2("bytesused=%d, offset/userptr=0x%08lx, length=%d\n",
420 p->bytesused, p->m.userptr, p->length);
423 dbgarg2("timecode=%02d:%02d:%02d type=%d, "
424 "flags=0x%08d, frames=%d, userbits=0x%08x\n",
425 tc->hours, tc->minutes, tc->seconds,
426 tc->type, tc->flags, tc->frames, *(__u32 *)tc->userbits);
429 static inline void dbgrect(struct video_device *vfd, char *s,
430 struct v4l2_rect *r)
432 dbgarg2("%sRect start at %dx%d, size=%dx%d\n", s, r->left, r->top,
433 r->width, r->height);
436 static inline void v4l_print_pix_fmt(struct video_device *vfd,
437 struct v4l2_pix_format *fmt)
439 dbgarg2("width=%d, height=%d, format=%c%c%c%c, field=%s, "
440 "bytesperline=%d sizeimage=%d, colorspace=%d\n",
441 fmt->width, fmt->height,
442 (fmt->pixelformat & 0xff),
443 (fmt->pixelformat >> 8) & 0xff,
444 (fmt->pixelformat >> 16) & 0xff,
445 (fmt->pixelformat >> 24) & 0xff,
446 prt_names(fmt->field, v4l2_field_names),
447 fmt->bytesperline, fmt->sizeimage, fmt->colorspace);
450 static inline void v4l_print_pix_fmt_mplane(struct video_device *vfd,
451 struct v4l2_pix_format_mplane *fmt)
453 int i;
455 dbgarg2("width=%d, height=%d, format=%c%c%c%c, field=%s, "
456 "colorspace=%d, num_planes=%d\n",
457 fmt->width, fmt->height,
458 (fmt->pixelformat & 0xff),
459 (fmt->pixelformat >> 8) & 0xff,
460 (fmt->pixelformat >> 16) & 0xff,
461 (fmt->pixelformat >> 24) & 0xff,
462 prt_names(fmt->field, v4l2_field_names),
463 fmt->colorspace, fmt->num_planes);
465 for (i = 0; i < fmt->num_planes; ++i)
466 dbgarg2("plane %d: bytesperline=%d sizeimage=%d\n", i,
467 fmt->plane_fmt[i].bytesperline,
468 fmt->plane_fmt[i].sizeimage);
471 static inline void v4l_print_ext_ctrls(unsigned int cmd,
472 struct video_device *vfd, struct v4l2_ext_controls *c, int show_vals)
474 __u32 i;
476 if (!(vfd->debug & V4L2_DEBUG_IOCTL_ARG))
477 return;
478 dbgarg(cmd, "");
479 printk(KERN_CONT "class=0x%x", c->ctrl_class);
480 for (i = 0; i < c->count; i++) {
481 if (show_vals && !c->controls[i].size)
482 printk(KERN_CONT " id/val=0x%x/0x%x",
483 c->controls[i].id, c->controls[i].value);
484 else
485 printk(KERN_CONT " id=0x%x,size=%u",
486 c->controls[i].id, c->controls[i].size);
488 printk(KERN_CONT "\n");
491 static inline int check_ext_ctrls(struct v4l2_ext_controls *c, int allow_priv)
493 __u32 i;
495 /* zero the reserved fields */
496 c->reserved[0] = c->reserved[1] = 0;
497 for (i = 0; i < c->count; i++)
498 c->controls[i].reserved2[0] = 0;
500 /* V4L2_CID_PRIVATE_BASE cannot be used as control class
501 when using extended controls.
502 Only when passed in through VIDIOC_G_CTRL and VIDIOC_S_CTRL
503 is it allowed for backwards compatibility.
505 if (!allow_priv && c->ctrl_class == V4L2_CID_PRIVATE_BASE)
506 return 0;
507 /* Check that all controls are from the same control class. */
508 for (i = 0; i < c->count; i++) {
509 if (V4L2_CTRL_ID2CLASS(c->controls[i].id) != c->ctrl_class) {
510 c->error_idx = i;
511 return 0;
514 return 1;
517 static int check_fmt(const struct v4l2_ioctl_ops *ops, enum v4l2_buf_type type)
519 if (ops == NULL)
520 return -EINVAL;
522 switch (type) {
523 case V4L2_BUF_TYPE_VIDEO_CAPTURE:
524 if (ops->vidioc_g_fmt_vid_cap ||
525 ops->vidioc_g_fmt_vid_cap_mplane)
526 return 0;
527 break;
528 case V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE:
529 if (ops->vidioc_g_fmt_vid_cap_mplane)
530 return 0;
531 break;
532 case V4L2_BUF_TYPE_VIDEO_OVERLAY:
533 if (ops->vidioc_g_fmt_vid_overlay)
534 return 0;
535 break;
536 case V4L2_BUF_TYPE_VIDEO_OUTPUT:
537 if (ops->vidioc_g_fmt_vid_out ||
538 ops->vidioc_g_fmt_vid_out_mplane)
539 return 0;
540 break;
541 case V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE:
542 if (ops->vidioc_g_fmt_vid_out_mplane)
543 return 0;
544 break;
545 case V4L2_BUF_TYPE_VIDEO_OUTPUT_OVERLAY:
546 if (ops->vidioc_g_fmt_vid_out_overlay)
547 return 0;
548 break;
549 case V4L2_BUF_TYPE_VBI_CAPTURE:
550 if (ops->vidioc_g_fmt_vbi_cap)
551 return 0;
552 break;
553 case V4L2_BUF_TYPE_VBI_OUTPUT:
554 if (ops->vidioc_g_fmt_vbi_out)
555 return 0;
556 break;
557 case V4L2_BUF_TYPE_SLICED_VBI_CAPTURE:
558 if (ops->vidioc_g_fmt_sliced_vbi_cap)
559 return 0;
560 break;
561 case V4L2_BUF_TYPE_SLICED_VBI_OUTPUT:
562 if (ops->vidioc_g_fmt_sliced_vbi_out)
563 return 0;
564 break;
565 case V4L2_BUF_TYPE_PRIVATE:
566 if (ops->vidioc_g_fmt_type_private)
567 return 0;
568 break;
570 return -EINVAL;
574 * fmt_sp_to_mp() - Convert a single-plane format to its multi-planar 1-plane
575 * equivalent
577 static int fmt_sp_to_mp(const struct v4l2_format *f_sp,
578 struct v4l2_format *f_mp)
580 struct v4l2_pix_format_mplane *pix_mp = &f_mp->fmt.pix_mp;
581 const struct v4l2_pix_format *pix = &f_sp->fmt.pix;
583 if (f_sp->type == V4L2_BUF_TYPE_VIDEO_CAPTURE)
584 f_mp->type = V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;
585 else if (f_sp->type == V4L2_BUF_TYPE_VIDEO_OUTPUT)
586 f_mp->type = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE;
587 else
588 return -EINVAL;
590 pix_mp->width = pix->width;
591 pix_mp->height = pix->height;
592 pix_mp->pixelformat = pix->pixelformat;
593 pix_mp->field = pix->field;
594 pix_mp->colorspace = pix->colorspace;
595 pix_mp->num_planes = 1;
596 pix_mp->plane_fmt[0].sizeimage = pix->sizeimage;
597 pix_mp->plane_fmt[0].bytesperline = pix->bytesperline;
599 return 0;
603 * fmt_mp_to_sp() - Convert a multi-planar 1-plane format to its single-planar
604 * equivalent
606 static int fmt_mp_to_sp(const struct v4l2_format *f_mp,
607 struct v4l2_format *f_sp)
609 const struct v4l2_pix_format_mplane *pix_mp = &f_mp->fmt.pix_mp;
610 struct v4l2_pix_format *pix = &f_sp->fmt.pix;
612 if (f_mp->type == V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE)
613 f_sp->type = V4L2_BUF_TYPE_VIDEO_CAPTURE;
614 else if (f_mp->type == V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE)
615 f_sp->type = V4L2_BUF_TYPE_VIDEO_OUTPUT;
616 else
617 return -EINVAL;
619 pix->width = pix_mp->width;
620 pix->height = pix_mp->height;
621 pix->pixelformat = pix_mp->pixelformat;
622 pix->field = pix_mp->field;
623 pix->colorspace = pix_mp->colorspace;
624 pix->sizeimage = pix_mp->plane_fmt[0].sizeimage;
625 pix->bytesperline = pix_mp->plane_fmt[0].bytesperline;
627 return 0;
630 static long __video_do_ioctl(struct file *file,
631 unsigned int cmd, void *arg)
633 struct video_device *vfd = video_devdata(file);
634 const struct v4l2_ioctl_ops *ops = vfd->ioctl_ops;
635 void *fh = file->private_data;
636 struct v4l2_format f_copy;
637 long ret = -EINVAL;
639 if (ops == NULL) {
640 printk(KERN_WARNING "videodev: \"%s\" has no ioctl_ops.\n",
641 vfd->name);
642 return -EINVAL;
645 if ((vfd->debug & V4L2_DEBUG_IOCTL) &&
646 !(vfd->debug & V4L2_DEBUG_IOCTL_ARG)) {
647 v4l_print_ioctl(vfd->name, cmd);
648 printk(KERN_CONT "\n");
651 switch (cmd) {
653 /* --- capabilities ------------------------------------------ */
654 case VIDIOC_QUERYCAP:
656 struct v4l2_capability *cap = (struct v4l2_capability *)arg;
658 if (!ops->vidioc_querycap)
659 break;
661 ret = ops->vidioc_querycap(file, fh, cap);
662 if (!ret)
663 dbgarg(cmd, "driver=%s, card=%s, bus=%s, "
664 "version=0x%08x, "
665 "capabilities=0x%08x\n",
666 cap->driver, cap->card, cap->bus_info,
667 cap->version,
668 cap->capabilities);
669 break;
672 /* --- priority ------------------------------------------ */
673 case VIDIOC_G_PRIORITY:
675 enum v4l2_priority *p = arg;
677 if (!ops->vidioc_g_priority)
678 break;
679 ret = ops->vidioc_g_priority(file, fh, p);
680 if (!ret)
681 dbgarg(cmd, "priority is %d\n", *p);
682 break;
684 case VIDIOC_S_PRIORITY:
686 enum v4l2_priority *p = arg;
688 if (!ops->vidioc_s_priority)
689 break;
690 dbgarg(cmd, "setting priority to %d\n", *p);
691 ret = ops->vidioc_s_priority(file, fh, *p);
692 break;
695 /* --- capture ioctls ---------------------------------------- */
696 case VIDIOC_ENUM_FMT:
698 struct v4l2_fmtdesc *f = arg;
700 switch (f->type) {
701 case V4L2_BUF_TYPE_VIDEO_CAPTURE:
702 if (ops->vidioc_enum_fmt_vid_cap)
703 ret = ops->vidioc_enum_fmt_vid_cap(file, fh, f);
704 break;
705 case V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE:
706 if (ops->vidioc_enum_fmt_vid_cap_mplane)
707 ret = ops->vidioc_enum_fmt_vid_cap_mplane(file,
708 fh, f);
709 break;
710 case V4L2_BUF_TYPE_VIDEO_OVERLAY:
711 if (ops->vidioc_enum_fmt_vid_overlay)
712 ret = ops->vidioc_enum_fmt_vid_overlay(file,
713 fh, f);
714 break;
715 case V4L2_BUF_TYPE_VIDEO_OUTPUT:
716 if (ops->vidioc_enum_fmt_vid_out)
717 ret = ops->vidioc_enum_fmt_vid_out(file, fh, f);
718 break;
719 case V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE:
720 if (ops->vidioc_enum_fmt_vid_out_mplane)
721 ret = ops->vidioc_enum_fmt_vid_out_mplane(file,
722 fh, f);
723 break;
724 case V4L2_BUF_TYPE_PRIVATE:
725 if (ops->vidioc_enum_fmt_type_private)
726 ret = ops->vidioc_enum_fmt_type_private(file,
727 fh, f);
728 break;
729 default:
730 break;
732 if (!ret)
733 dbgarg(cmd, "index=%d, type=%d, flags=%d, "
734 "pixelformat=%c%c%c%c, description='%s'\n",
735 f->index, f->type, f->flags,
736 (f->pixelformat & 0xff),
737 (f->pixelformat >> 8) & 0xff,
738 (f->pixelformat >> 16) & 0xff,
739 (f->pixelformat >> 24) & 0xff,
740 f->description);
741 break;
743 case VIDIOC_G_FMT:
745 struct v4l2_format *f = (struct v4l2_format *)arg;
747 /* FIXME: Should be one dump per type */
748 dbgarg(cmd, "type=%s\n", prt_names(f->type, v4l2_type_names));
750 switch (f->type) {
751 case V4L2_BUF_TYPE_VIDEO_CAPTURE:
752 if (ops->vidioc_g_fmt_vid_cap) {
753 ret = ops->vidioc_g_fmt_vid_cap(file, fh, f);
754 } else if (ops->vidioc_g_fmt_vid_cap_mplane) {
755 if (fmt_sp_to_mp(f, &f_copy))
756 break;
757 ret = ops->vidioc_g_fmt_vid_cap_mplane(file, fh,
758 &f_copy);
759 if (ret)
760 break;
762 /* Driver is currently in multi-planar format,
763 * we can't return it in single-planar API*/
764 if (f_copy.fmt.pix_mp.num_planes > 1) {
765 ret = -EBUSY;
766 break;
769 ret = fmt_mp_to_sp(&f_copy, f);
771 if (!ret)
772 v4l_print_pix_fmt(vfd, &f->fmt.pix);
773 break;
774 case V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE:
775 if (ops->vidioc_g_fmt_vid_cap_mplane) {
776 ret = ops->vidioc_g_fmt_vid_cap_mplane(file,
777 fh, f);
778 } else if (ops->vidioc_g_fmt_vid_cap) {
779 if (fmt_mp_to_sp(f, &f_copy))
780 break;
781 ret = ops->vidioc_g_fmt_vid_cap(file,
782 fh, &f_copy);
783 if (ret)
784 break;
786 ret = fmt_sp_to_mp(&f_copy, f);
788 if (!ret)
789 v4l_print_pix_fmt_mplane(vfd, &f->fmt.pix_mp);
790 break;
791 case V4L2_BUF_TYPE_VIDEO_OVERLAY:
792 if (ops->vidioc_g_fmt_vid_overlay)
793 ret = ops->vidioc_g_fmt_vid_overlay(file,
794 fh, f);
795 break;
796 case V4L2_BUF_TYPE_VIDEO_OUTPUT:
797 if (ops->vidioc_g_fmt_vid_out) {
798 ret = ops->vidioc_g_fmt_vid_out(file, fh, f);
799 } else if (ops->vidioc_g_fmt_vid_out_mplane) {
800 if (fmt_sp_to_mp(f, &f_copy))
801 break;
802 ret = ops->vidioc_g_fmt_vid_out_mplane(file, fh,
803 &f_copy);
804 if (ret)
805 break;
807 /* Driver is currently in multi-planar format,
808 * we can't return it in single-planar API*/
809 if (f_copy.fmt.pix_mp.num_planes > 1) {
810 ret = -EBUSY;
811 break;
814 ret = fmt_mp_to_sp(&f_copy, f);
816 if (!ret)
817 v4l_print_pix_fmt(vfd, &f->fmt.pix);
818 break;
819 case V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE:
820 if (ops->vidioc_g_fmt_vid_out_mplane) {
821 ret = ops->vidioc_g_fmt_vid_out_mplane(file,
822 fh, f);
823 } else if (ops->vidioc_g_fmt_vid_out) {
824 if (fmt_mp_to_sp(f, &f_copy))
825 break;
826 ret = ops->vidioc_g_fmt_vid_out(file,
827 fh, &f_copy);
828 if (ret)
829 break;
831 ret = fmt_sp_to_mp(&f_copy, f);
833 if (!ret)
834 v4l_print_pix_fmt_mplane(vfd, &f->fmt.pix_mp);
835 break;
836 case V4L2_BUF_TYPE_VIDEO_OUTPUT_OVERLAY:
837 if (ops->vidioc_g_fmt_vid_out_overlay)
838 ret = ops->vidioc_g_fmt_vid_out_overlay(file,
839 fh, f);
840 break;
841 case V4L2_BUF_TYPE_VBI_CAPTURE:
842 if (ops->vidioc_g_fmt_vbi_cap)
843 ret = ops->vidioc_g_fmt_vbi_cap(file, fh, f);
844 break;
845 case V4L2_BUF_TYPE_VBI_OUTPUT:
846 if (ops->vidioc_g_fmt_vbi_out)
847 ret = ops->vidioc_g_fmt_vbi_out(file, fh, f);
848 break;
849 case V4L2_BUF_TYPE_SLICED_VBI_CAPTURE:
850 if (ops->vidioc_g_fmt_sliced_vbi_cap)
851 ret = ops->vidioc_g_fmt_sliced_vbi_cap(file,
852 fh, f);
853 break;
854 case V4L2_BUF_TYPE_SLICED_VBI_OUTPUT:
855 if (ops->vidioc_g_fmt_sliced_vbi_out)
856 ret = ops->vidioc_g_fmt_sliced_vbi_out(file,
857 fh, f);
858 break;
859 case V4L2_BUF_TYPE_PRIVATE:
860 if (ops->vidioc_g_fmt_type_private)
861 ret = ops->vidioc_g_fmt_type_private(file,
862 fh, f);
863 break;
866 break;
868 case VIDIOC_S_FMT:
870 struct v4l2_format *f = (struct v4l2_format *)arg;
872 /* FIXME: Should be one dump per type */
873 dbgarg(cmd, "type=%s\n", prt_names(f->type, v4l2_type_names));
875 switch (f->type) {
876 case V4L2_BUF_TYPE_VIDEO_CAPTURE:
877 CLEAR_AFTER_FIELD(f, fmt.pix);
878 v4l_print_pix_fmt(vfd, &f->fmt.pix);
879 if (ops->vidioc_s_fmt_vid_cap) {
880 ret = ops->vidioc_s_fmt_vid_cap(file, fh, f);
881 } else if (ops->vidioc_s_fmt_vid_cap_mplane) {
882 if (fmt_sp_to_mp(f, &f_copy))
883 break;
884 ret = ops->vidioc_s_fmt_vid_cap_mplane(file, fh,
885 &f_copy);
886 if (ret)
887 break;
889 if (f_copy.fmt.pix_mp.num_planes > 1) {
890 /* Drivers shouldn't adjust from 1-plane
891 * to more than 1-plane formats */
892 ret = -EBUSY;
893 WARN_ON(1);
894 break;
897 ret = fmt_mp_to_sp(&f_copy, f);
899 break;
900 case V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE:
901 CLEAR_AFTER_FIELD(f, fmt.pix_mp);
902 v4l_print_pix_fmt_mplane(vfd, &f->fmt.pix_mp);
903 if (ops->vidioc_s_fmt_vid_cap_mplane) {
904 ret = ops->vidioc_s_fmt_vid_cap_mplane(file,
905 fh, f);
906 } else if (ops->vidioc_s_fmt_vid_cap &&
907 f->fmt.pix_mp.num_planes == 1) {
908 if (fmt_mp_to_sp(f, &f_copy))
909 break;
910 ret = ops->vidioc_s_fmt_vid_cap(file,
911 fh, &f_copy);
912 if (ret)
913 break;
915 ret = fmt_sp_to_mp(&f_copy, f);
917 break;
918 case V4L2_BUF_TYPE_VIDEO_OVERLAY:
919 CLEAR_AFTER_FIELD(f, fmt.win);
920 if (ops->vidioc_s_fmt_vid_overlay)
921 ret = ops->vidioc_s_fmt_vid_overlay(file,
922 fh, f);
923 break;
924 case V4L2_BUF_TYPE_VIDEO_OUTPUT:
925 CLEAR_AFTER_FIELD(f, fmt.pix);
926 v4l_print_pix_fmt(vfd, &f->fmt.pix);
927 if (ops->vidioc_s_fmt_vid_out) {
928 ret = ops->vidioc_s_fmt_vid_out(file, fh, f);
929 } else if (ops->vidioc_s_fmt_vid_out_mplane) {
930 if (fmt_sp_to_mp(f, &f_copy))
931 break;
932 ret = ops->vidioc_s_fmt_vid_out_mplane(file, fh,
933 &f_copy);
934 if (ret)
935 break;
937 if (f_copy.fmt.pix_mp.num_planes > 1) {
938 /* Drivers shouldn't adjust from 1-plane
939 * to more than 1-plane formats */
940 ret = -EBUSY;
941 WARN_ON(1);
942 break;
945 ret = fmt_mp_to_sp(&f_copy, f);
947 break;
948 case V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE:
949 CLEAR_AFTER_FIELD(f, fmt.pix_mp);
950 v4l_print_pix_fmt_mplane(vfd, &f->fmt.pix_mp);
951 if (ops->vidioc_s_fmt_vid_out_mplane) {
952 ret = ops->vidioc_s_fmt_vid_out_mplane(file,
953 fh, f);
954 } else if (ops->vidioc_s_fmt_vid_out &&
955 f->fmt.pix_mp.num_planes == 1) {
956 if (fmt_mp_to_sp(f, &f_copy))
957 break;
958 ret = ops->vidioc_s_fmt_vid_out(file,
959 fh, &f_copy);
960 if (ret)
961 break;
963 ret = fmt_mp_to_sp(&f_copy, f);
965 break;
966 case V4L2_BUF_TYPE_VIDEO_OUTPUT_OVERLAY:
967 CLEAR_AFTER_FIELD(f, fmt.win);
968 if (ops->vidioc_s_fmt_vid_out_overlay)
969 ret = ops->vidioc_s_fmt_vid_out_overlay(file,
970 fh, f);
971 break;
972 case V4L2_BUF_TYPE_VBI_CAPTURE:
973 CLEAR_AFTER_FIELD(f, fmt.vbi);
974 if (ops->vidioc_s_fmt_vbi_cap)
975 ret = ops->vidioc_s_fmt_vbi_cap(file, fh, f);
976 break;
977 case V4L2_BUF_TYPE_VBI_OUTPUT:
978 CLEAR_AFTER_FIELD(f, fmt.vbi);
979 if (ops->vidioc_s_fmt_vbi_out)
980 ret = ops->vidioc_s_fmt_vbi_out(file, fh, f);
981 break;
982 case V4L2_BUF_TYPE_SLICED_VBI_CAPTURE:
983 CLEAR_AFTER_FIELD(f, fmt.sliced);
984 if (ops->vidioc_s_fmt_sliced_vbi_cap)
985 ret = ops->vidioc_s_fmt_sliced_vbi_cap(file,
986 fh, f);
987 break;
988 case V4L2_BUF_TYPE_SLICED_VBI_OUTPUT:
989 CLEAR_AFTER_FIELD(f, fmt.sliced);
990 if (ops->vidioc_s_fmt_sliced_vbi_out)
991 ret = ops->vidioc_s_fmt_sliced_vbi_out(file,
992 fh, f);
993 break;
994 case V4L2_BUF_TYPE_PRIVATE:
995 /* CLEAR_AFTER_FIELD(f, fmt.raw_data); <- does nothing */
996 if (ops->vidioc_s_fmt_type_private)
997 ret = ops->vidioc_s_fmt_type_private(file,
998 fh, f);
999 break;
1001 break;
1003 case VIDIOC_TRY_FMT:
1005 struct v4l2_format *f = (struct v4l2_format *)arg;
1007 /* FIXME: Should be one dump per type */
1008 dbgarg(cmd, "type=%s\n", prt_names(f->type,
1009 v4l2_type_names));
1010 switch (f->type) {
1011 case V4L2_BUF_TYPE_VIDEO_CAPTURE:
1012 CLEAR_AFTER_FIELD(f, fmt.pix);
1013 if (ops->vidioc_try_fmt_vid_cap) {
1014 ret = ops->vidioc_try_fmt_vid_cap(file, fh, f);
1015 } else if (ops->vidioc_try_fmt_vid_cap_mplane) {
1016 if (fmt_sp_to_mp(f, &f_copy))
1017 break;
1018 ret = ops->vidioc_try_fmt_vid_cap_mplane(file,
1019 fh, &f_copy);
1020 if (ret)
1021 break;
1023 if (f_copy.fmt.pix_mp.num_planes > 1) {
1024 /* Drivers shouldn't adjust from 1-plane
1025 * to more than 1-plane formats */
1026 ret = -EBUSY;
1027 WARN_ON(1);
1028 break;
1030 ret = fmt_mp_to_sp(&f_copy, f);
1032 if (!ret)
1033 v4l_print_pix_fmt(vfd, &f->fmt.pix);
1034 break;
1035 case V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE:
1036 CLEAR_AFTER_FIELD(f, fmt.pix_mp);
1037 if (ops->vidioc_try_fmt_vid_cap_mplane) {
1038 ret = ops->vidioc_try_fmt_vid_cap_mplane(file,
1039 fh, f);
1040 } else if (ops->vidioc_try_fmt_vid_cap &&
1041 f->fmt.pix_mp.num_planes == 1) {
1042 if (fmt_mp_to_sp(f, &f_copy))
1043 break;
1044 ret = ops->vidioc_try_fmt_vid_cap(file,
1045 fh, &f_copy);
1046 if (ret)
1047 break;
1049 ret = fmt_sp_to_mp(&f_copy, f);
1051 if (!ret)
1052 v4l_print_pix_fmt_mplane(vfd, &f->fmt.pix_mp);
1053 break;
1054 case V4L2_BUF_TYPE_VIDEO_OVERLAY:
1055 CLEAR_AFTER_FIELD(f, fmt.win);
1056 if (ops->vidioc_try_fmt_vid_overlay)
1057 ret = ops->vidioc_try_fmt_vid_overlay(file,
1058 fh, f);
1059 break;
1060 case V4L2_BUF_TYPE_VIDEO_OUTPUT:
1061 CLEAR_AFTER_FIELD(f, fmt.pix);
1062 if (ops->vidioc_try_fmt_vid_out) {
1063 ret = ops->vidioc_try_fmt_vid_out(file, fh, f);
1064 } else if (ops->vidioc_try_fmt_vid_out_mplane) {
1065 if (fmt_sp_to_mp(f, &f_copy))
1066 break;
1067 ret = ops->vidioc_try_fmt_vid_out_mplane(file,
1068 fh, &f_copy);
1069 if (ret)
1070 break;
1072 if (f_copy.fmt.pix_mp.num_planes > 1) {
1073 /* Drivers shouldn't adjust from 1-plane
1074 * to more than 1-plane formats */
1075 ret = -EBUSY;
1076 WARN_ON(1);
1077 break;
1079 ret = fmt_mp_to_sp(&f_copy, f);
1081 if (!ret)
1082 v4l_print_pix_fmt(vfd, &f->fmt.pix);
1083 break;
1084 case V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE:
1085 CLEAR_AFTER_FIELD(f, fmt.pix_mp);
1086 if (ops->vidioc_try_fmt_vid_out_mplane) {
1087 ret = ops->vidioc_try_fmt_vid_out_mplane(file,
1088 fh, f);
1089 } else if (ops->vidioc_try_fmt_vid_out &&
1090 f->fmt.pix_mp.num_planes == 1) {
1091 if (fmt_mp_to_sp(f, &f_copy))
1092 break;
1093 ret = ops->vidioc_try_fmt_vid_out(file,
1094 fh, &f_copy);
1095 if (ret)
1096 break;
1098 ret = fmt_sp_to_mp(&f_copy, f);
1100 if (!ret)
1101 v4l_print_pix_fmt_mplane(vfd, &f->fmt.pix_mp);
1102 break;
1103 case V4L2_BUF_TYPE_VIDEO_OUTPUT_OVERLAY:
1104 CLEAR_AFTER_FIELD(f, fmt.win);
1105 if (ops->vidioc_try_fmt_vid_out_overlay)
1106 ret = ops->vidioc_try_fmt_vid_out_overlay(file,
1107 fh, f);
1108 break;
1109 case V4L2_BUF_TYPE_VBI_CAPTURE:
1110 CLEAR_AFTER_FIELD(f, fmt.vbi);
1111 if (ops->vidioc_try_fmt_vbi_cap)
1112 ret = ops->vidioc_try_fmt_vbi_cap(file, fh, f);
1113 break;
1114 case V4L2_BUF_TYPE_VBI_OUTPUT:
1115 CLEAR_AFTER_FIELD(f, fmt.vbi);
1116 if (ops->vidioc_try_fmt_vbi_out)
1117 ret = ops->vidioc_try_fmt_vbi_out(file, fh, f);
1118 break;
1119 case V4L2_BUF_TYPE_SLICED_VBI_CAPTURE:
1120 CLEAR_AFTER_FIELD(f, fmt.sliced);
1121 if (ops->vidioc_try_fmt_sliced_vbi_cap)
1122 ret = ops->vidioc_try_fmt_sliced_vbi_cap(file,
1123 fh, f);
1124 break;
1125 case V4L2_BUF_TYPE_SLICED_VBI_OUTPUT:
1126 CLEAR_AFTER_FIELD(f, fmt.sliced);
1127 if (ops->vidioc_try_fmt_sliced_vbi_out)
1128 ret = ops->vidioc_try_fmt_sliced_vbi_out(file,
1129 fh, f);
1130 break;
1131 case V4L2_BUF_TYPE_PRIVATE:
1132 /* CLEAR_AFTER_FIELD(f, fmt.raw_data); <- does nothing */
1133 if (ops->vidioc_try_fmt_type_private)
1134 ret = ops->vidioc_try_fmt_type_private(file,
1135 fh, f);
1136 break;
1139 break;
1141 /* FIXME: Those buf reqs could be handled here,
1142 with some changes on videobuf to allow its header to be included at
1143 videodev2.h or being merged at videodev2.
1145 case VIDIOC_REQBUFS:
1147 struct v4l2_requestbuffers *p = arg;
1149 if (!ops->vidioc_reqbufs)
1150 break;
1151 ret = check_fmt(ops, p->type);
1152 if (ret)
1153 break;
1155 if (p->type < V4L2_BUF_TYPE_PRIVATE)
1156 CLEAR_AFTER_FIELD(p, memory);
1158 ret = ops->vidioc_reqbufs(file, fh, p);
1159 dbgarg(cmd, "count=%d, type=%s, memory=%s\n",
1160 p->count,
1161 prt_names(p->type, v4l2_type_names),
1162 prt_names(p->memory, v4l2_memory_names));
1163 break;
1165 case VIDIOC_QUERYBUF:
1167 struct v4l2_buffer *p = arg;
1169 if (!ops->vidioc_querybuf)
1170 break;
1171 ret = check_fmt(ops, p->type);
1172 if (ret)
1173 break;
1175 ret = ops->vidioc_querybuf(file, fh, p);
1176 if (!ret)
1177 dbgbuf(cmd, vfd, p);
1178 break;
1180 case VIDIOC_QBUF:
1182 struct v4l2_buffer *p = arg;
1184 if (!ops->vidioc_qbuf)
1185 break;
1186 ret = check_fmt(ops, p->type);
1187 if (ret)
1188 break;
1190 ret = ops->vidioc_qbuf(file, fh, p);
1191 if (!ret)
1192 dbgbuf(cmd, vfd, p);
1193 break;
1195 case VIDIOC_DQBUF:
1197 struct v4l2_buffer *p = arg;
1199 if (!ops->vidioc_dqbuf)
1200 break;
1201 ret = check_fmt(ops, p->type);
1202 if (ret)
1203 break;
1205 ret = ops->vidioc_dqbuf(file, fh, p);
1206 if (!ret)
1207 dbgbuf(cmd, vfd, p);
1208 break;
1210 case VIDIOC_OVERLAY:
1212 int *i = arg;
1214 if (!ops->vidioc_overlay)
1215 break;
1216 dbgarg(cmd, "value=%d\n", *i);
1217 ret = ops->vidioc_overlay(file, fh, *i);
1218 break;
1220 case VIDIOC_G_FBUF:
1222 struct v4l2_framebuffer *p = arg;
1224 if (!ops->vidioc_g_fbuf)
1225 break;
1226 ret = ops->vidioc_g_fbuf(file, fh, arg);
1227 if (!ret) {
1228 dbgarg(cmd, "capability=0x%x, flags=%d, base=0x%08lx\n",
1229 p->capability, p->flags,
1230 (unsigned long)p->base);
1231 v4l_print_pix_fmt(vfd, &p->fmt);
1233 break;
1235 case VIDIOC_S_FBUF:
1237 struct v4l2_framebuffer *p = arg;
1239 if (!ops->vidioc_s_fbuf)
1240 break;
1241 dbgarg(cmd, "capability=0x%x, flags=%d, base=0x%08lx\n",
1242 p->capability, p->flags, (unsigned long)p->base);
1243 v4l_print_pix_fmt(vfd, &p->fmt);
1244 ret = ops->vidioc_s_fbuf(file, fh, arg);
1245 break;
1247 case VIDIOC_STREAMON:
1249 enum v4l2_buf_type i = *(int *)arg;
1251 if (!ops->vidioc_streamon)
1252 break;
1253 dbgarg(cmd, "type=%s\n", prt_names(i, v4l2_type_names));
1254 ret = ops->vidioc_streamon(file, fh, i);
1255 break;
1257 case VIDIOC_STREAMOFF:
1259 enum v4l2_buf_type i = *(int *)arg;
1261 if (!ops->vidioc_streamoff)
1262 break;
1263 dbgarg(cmd, "type=%s\n", prt_names(i, v4l2_type_names));
1264 ret = ops->vidioc_streamoff(file, fh, i);
1265 break;
1267 /* ---------- tv norms ---------- */
1268 case VIDIOC_ENUMSTD:
1270 struct v4l2_standard *p = arg;
1271 v4l2_std_id id = vfd->tvnorms, curr_id = 0;
1272 unsigned int index = p->index, i, j = 0;
1273 const char *descr = "";
1275 /* Return norm array in a canonical way */
1276 for (i = 0; i <= index && id; i++) {
1277 /* last std value in the standards array is 0, so this
1278 while always ends there since (id & 0) == 0. */
1279 while ((id & standards[j].std) != standards[j].std)
1280 j++;
1281 curr_id = standards[j].std;
1282 descr = standards[j].descr;
1283 j++;
1284 if (curr_id == 0)
1285 break;
1286 if (curr_id != V4L2_STD_PAL &&
1287 curr_id != V4L2_STD_SECAM &&
1288 curr_id != V4L2_STD_NTSC)
1289 id &= ~curr_id;
1291 if (i <= index)
1292 break;
1294 v4l2_video_std_construct(p, curr_id, descr);
1296 dbgarg(cmd, "index=%d, id=0x%Lx, name=%s, fps=%d/%d, "
1297 "framelines=%d\n", p->index,
1298 (unsigned long long)p->id, p->name,
1299 p->frameperiod.numerator,
1300 p->frameperiod.denominator,
1301 p->framelines);
1303 ret = 0;
1304 break;
1306 case VIDIOC_G_STD:
1308 v4l2_std_id *id = arg;
1310 ret = 0;
1311 /* Calls the specific handler */
1312 if (ops->vidioc_g_std)
1313 ret = ops->vidioc_g_std(file, fh, id);
1314 else if (vfd->current_norm)
1315 *id = vfd->current_norm;
1316 else
1317 ret = -EINVAL;
1319 if (!ret)
1320 dbgarg(cmd, "std=0x%08Lx\n", (long long unsigned)*id);
1321 break;
1323 case VIDIOC_S_STD:
1325 v4l2_std_id *id = arg, norm;
1327 dbgarg(cmd, "std=%08Lx\n", (long long unsigned)*id);
1329 norm = (*id) & vfd->tvnorms;
1330 if (vfd->tvnorms && !norm) /* Check if std is supported */
1331 break;
1333 /* Calls the specific handler */
1334 if (ops->vidioc_s_std)
1335 ret = ops->vidioc_s_std(file, fh, &norm);
1336 else
1337 ret = -EINVAL;
1339 /* Updates standard information */
1340 if (ret >= 0)
1341 vfd->current_norm = norm;
1342 break;
1344 case VIDIOC_QUERYSTD:
1346 v4l2_std_id *p = arg;
1348 if (!ops->vidioc_querystd)
1349 break;
1350 ret = ops->vidioc_querystd(file, fh, arg);
1351 if (!ret)
1352 dbgarg(cmd, "detected std=%08Lx\n",
1353 (unsigned long long)*p);
1354 break;
1356 /* ------ input switching ---------- */
1357 /* FIXME: Inputs can be handled inside videodev2 */
1358 case VIDIOC_ENUMINPUT:
1360 struct v4l2_input *p = arg;
1363 * We set the flags for CAP_PRESETS, CAP_CUSTOM_TIMINGS &
1364 * CAP_STD here based on ioctl handler provided by the
1365 * driver. If the driver doesn't support these
1366 * for a specific input, it must override these flags.
1368 if (ops->vidioc_s_std)
1369 p->capabilities |= V4L2_IN_CAP_STD;
1370 if (ops->vidioc_s_dv_preset)
1371 p->capabilities |= V4L2_IN_CAP_PRESETS;
1372 if (ops->vidioc_s_dv_timings)
1373 p->capabilities |= V4L2_IN_CAP_CUSTOM_TIMINGS;
1375 if (!ops->vidioc_enum_input)
1376 break;
1378 ret = ops->vidioc_enum_input(file, fh, p);
1379 if (!ret)
1380 dbgarg(cmd, "index=%d, name=%s, type=%d, "
1381 "audioset=%d, "
1382 "tuner=%d, std=%08Lx, status=%d\n",
1383 p->index, p->name, p->type, p->audioset,
1384 p->tuner,
1385 (unsigned long long)p->std,
1386 p->status);
1387 break;
1389 case VIDIOC_G_INPUT:
1391 unsigned int *i = arg;
1393 if (!ops->vidioc_g_input)
1394 break;
1395 ret = ops->vidioc_g_input(file, fh, i);
1396 if (!ret)
1397 dbgarg(cmd, "value=%d\n", *i);
1398 break;
1400 case VIDIOC_S_INPUT:
1402 unsigned int *i = arg;
1404 if (!ops->vidioc_s_input)
1405 break;
1406 dbgarg(cmd, "value=%d\n", *i);
1407 ret = ops->vidioc_s_input(file, fh, *i);
1408 break;
1411 /* ------ output switching ---------- */
1412 case VIDIOC_ENUMOUTPUT:
1414 struct v4l2_output *p = arg;
1416 if (!ops->vidioc_enum_output)
1417 break;
1420 * We set the flags for CAP_PRESETS, CAP_CUSTOM_TIMINGS &
1421 * CAP_STD here based on ioctl handler provided by the
1422 * driver. If the driver doesn't support these
1423 * for a specific output, it must override these flags.
1425 if (ops->vidioc_s_std)
1426 p->capabilities |= V4L2_OUT_CAP_STD;
1427 if (ops->vidioc_s_dv_preset)
1428 p->capabilities |= V4L2_OUT_CAP_PRESETS;
1429 if (ops->vidioc_s_dv_timings)
1430 p->capabilities |= V4L2_OUT_CAP_CUSTOM_TIMINGS;
1432 ret = ops->vidioc_enum_output(file, fh, p);
1433 if (!ret)
1434 dbgarg(cmd, "index=%d, name=%s, type=%d, "
1435 "audioset=0x%x, "
1436 "modulator=%d, std=0x%08Lx\n",
1437 p->index, p->name, p->type, p->audioset,
1438 p->modulator, (unsigned long long)p->std);
1439 break;
1441 case VIDIOC_G_OUTPUT:
1443 unsigned int *i = arg;
1445 if (!ops->vidioc_g_output)
1446 break;
1447 ret = ops->vidioc_g_output(file, fh, i);
1448 if (!ret)
1449 dbgarg(cmd, "value=%d\n", *i);
1450 break;
1452 case VIDIOC_S_OUTPUT:
1454 unsigned int *i = arg;
1456 if (!ops->vidioc_s_output)
1457 break;
1458 dbgarg(cmd, "value=%d\n", *i);
1459 ret = ops->vidioc_s_output(file, fh, *i);
1460 break;
1463 /* --- controls ---------------------------------------------- */
1464 case VIDIOC_QUERYCTRL:
1466 struct v4l2_queryctrl *p = arg;
1468 if (vfd->ctrl_handler)
1469 ret = v4l2_queryctrl(vfd->ctrl_handler, p);
1470 else if (ops->vidioc_queryctrl)
1471 ret = ops->vidioc_queryctrl(file, fh, p);
1472 else
1473 break;
1474 if (!ret)
1475 dbgarg(cmd, "id=0x%x, type=%d, name=%s, min/max=%d/%d, "
1476 "step=%d, default=%d, flags=0x%08x\n",
1477 p->id, p->type, p->name,
1478 p->minimum, p->maximum,
1479 p->step, p->default_value, p->flags);
1480 else
1481 dbgarg(cmd, "id=0x%x\n", p->id);
1482 break;
1484 case VIDIOC_G_CTRL:
1486 struct v4l2_control *p = arg;
1488 if (vfd->ctrl_handler)
1489 ret = v4l2_g_ctrl(vfd->ctrl_handler, p);
1490 else if (ops->vidioc_g_ctrl)
1491 ret = ops->vidioc_g_ctrl(file, fh, p);
1492 else if (ops->vidioc_g_ext_ctrls) {
1493 struct v4l2_ext_controls ctrls;
1494 struct v4l2_ext_control ctrl;
1496 ctrls.ctrl_class = V4L2_CTRL_ID2CLASS(p->id);
1497 ctrls.count = 1;
1498 ctrls.controls = &ctrl;
1499 ctrl.id = p->id;
1500 ctrl.value = p->value;
1501 if (check_ext_ctrls(&ctrls, 1)) {
1502 ret = ops->vidioc_g_ext_ctrls(file, fh, &ctrls);
1503 if (ret == 0)
1504 p->value = ctrl.value;
1506 } else
1507 break;
1508 if (!ret)
1509 dbgarg(cmd, "id=0x%x, value=%d\n", p->id, p->value);
1510 else
1511 dbgarg(cmd, "id=0x%x\n", p->id);
1512 break;
1514 case VIDIOC_S_CTRL:
1516 struct v4l2_control *p = arg;
1517 struct v4l2_ext_controls ctrls;
1518 struct v4l2_ext_control ctrl;
1520 if (!vfd->ctrl_handler &&
1521 !ops->vidioc_s_ctrl && !ops->vidioc_s_ext_ctrls)
1522 break;
1524 dbgarg(cmd, "id=0x%x, value=%d\n", p->id, p->value);
1526 if (vfd->ctrl_handler) {
1527 ret = v4l2_s_ctrl(vfd->ctrl_handler, p);
1528 break;
1530 if (ops->vidioc_s_ctrl) {
1531 ret = ops->vidioc_s_ctrl(file, fh, p);
1532 break;
1534 if (!ops->vidioc_s_ext_ctrls)
1535 break;
1537 ctrls.ctrl_class = V4L2_CTRL_ID2CLASS(p->id);
1538 ctrls.count = 1;
1539 ctrls.controls = &ctrl;
1540 ctrl.id = p->id;
1541 ctrl.value = p->value;
1542 if (check_ext_ctrls(&ctrls, 1))
1543 ret = ops->vidioc_s_ext_ctrls(file, fh, &ctrls);
1544 break;
1546 case VIDIOC_G_EXT_CTRLS:
1548 struct v4l2_ext_controls *p = arg;
1550 p->error_idx = p->count;
1551 if (vfd->ctrl_handler)
1552 ret = v4l2_g_ext_ctrls(vfd->ctrl_handler, p);
1553 else if (ops->vidioc_g_ext_ctrls && check_ext_ctrls(p, 0))
1554 ret = ops->vidioc_g_ext_ctrls(file, fh, p);
1555 else
1556 break;
1557 v4l_print_ext_ctrls(cmd, vfd, p, !ret);
1558 break;
1560 case VIDIOC_S_EXT_CTRLS:
1562 struct v4l2_ext_controls *p = arg;
1564 p->error_idx = p->count;
1565 if (!vfd->ctrl_handler && !ops->vidioc_s_ext_ctrls)
1566 break;
1567 v4l_print_ext_ctrls(cmd, vfd, p, 1);
1568 if (vfd->ctrl_handler)
1569 ret = v4l2_s_ext_ctrls(vfd->ctrl_handler, p);
1570 else if (check_ext_ctrls(p, 0))
1571 ret = ops->vidioc_s_ext_ctrls(file, fh, p);
1572 break;
1574 case VIDIOC_TRY_EXT_CTRLS:
1576 struct v4l2_ext_controls *p = arg;
1578 p->error_idx = p->count;
1579 if (!vfd->ctrl_handler && !ops->vidioc_try_ext_ctrls)
1580 break;
1581 v4l_print_ext_ctrls(cmd, vfd, p, 1);
1582 if (vfd->ctrl_handler)
1583 ret = v4l2_try_ext_ctrls(vfd->ctrl_handler, p);
1584 else if (check_ext_ctrls(p, 0))
1585 ret = ops->vidioc_try_ext_ctrls(file, fh, p);
1586 break;
1588 case VIDIOC_QUERYMENU:
1590 struct v4l2_querymenu *p = arg;
1592 if (vfd->ctrl_handler)
1593 ret = v4l2_querymenu(vfd->ctrl_handler, p);
1594 else if (ops->vidioc_querymenu)
1595 ret = ops->vidioc_querymenu(file, fh, p);
1596 else
1597 break;
1598 if (!ret)
1599 dbgarg(cmd, "id=0x%x, index=%d, name=%s\n",
1600 p->id, p->index, p->name);
1601 else
1602 dbgarg(cmd, "id=0x%x, index=%d\n",
1603 p->id, p->index);
1604 break;
1606 /* --- audio ---------------------------------------------- */
1607 case VIDIOC_ENUMAUDIO:
1609 struct v4l2_audio *p = arg;
1611 if (!ops->vidioc_enumaudio)
1612 break;
1613 ret = ops->vidioc_enumaudio(file, fh, p);
1614 if (!ret)
1615 dbgarg(cmd, "index=%d, name=%s, capability=0x%x, "
1616 "mode=0x%x\n", p->index, p->name,
1617 p->capability, p->mode);
1618 else
1619 dbgarg(cmd, "index=%d\n", p->index);
1620 break;
1622 case VIDIOC_G_AUDIO:
1624 struct v4l2_audio *p = arg;
1626 if (!ops->vidioc_g_audio)
1627 break;
1629 ret = ops->vidioc_g_audio(file, fh, p);
1630 if (!ret)
1631 dbgarg(cmd, "index=%d, name=%s, capability=0x%x, "
1632 "mode=0x%x\n", p->index,
1633 p->name, p->capability, p->mode);
1634 else
1635 dbgarg(cmd, "index=%d\n", p->index);
1636 break;
1638 case VIDIOC_S_AUDIO:
1640 struct v4l2_audio *p = arg;
1642 if (!ops->vidioc_s_audio)
1643 break;
1644 dbgarg(cmd, "index=%d, name=%s, capability=0x%x, "
1645 "mode=0x%x\n", p->index, p->name,
1646 p->capability, p->mode);
1647 ret = ops->vidioc_s_audio(file, fh, p);
1648 break;
1650 case VIDIOC_ENUMAUDOUT:
1652 struct v4l2_audioout *p = arg;
1654 if (!ops->vidioc_enumaudout)
1655 break;
1656 dbgarg(cmd, "Enum for index=%d\n", p->index);
1657 ret = ops->vidioc_enumaudout(file, fh, p);
1658 if (!ret)
1659 dbgarg2("index=%d, name=%s, capability=%d, "
1660 "mode=%d\n", p->index, p->name,
1661 p->capability, p->mode);
1662 break;
1664 case VIDIOC_G_AUDOUT:
1666 struct v4l2_audioout *p = arg;
1668 if (!ops->vidioc_g_audout)
1669 break;
1671 ret = ops->vidioc_g_audout(file, fh, p);
1672 if (!ret)
1673 dbgarg2("index=%d, name=%s, capability=%d, "
1674 "mode=%d\n", p->index, p->name,
1675 p->capability, p->mode);
1676 break;
1678 case VIDIOC_S_AUDOUT:
1680 struct v4l2_audioout *p = arg;
1682 if (!ops->vidioc_s_audout)
1683 break;
1684 dbgarg(cmd, "index=%d, name=%s, capability=%d, "
1685 "mode=%d\n", p->index, p->name,
1686 p->capability, p->mode);
1688 ret = ops->vidioc_s_audout(file, fh, p);
1689 break;
1691 case VIDIOC_G_MODULATOR:
1693 struct v4l2_modulator *p = arg;
1695 if (!ops->vidioc_g_modulator)
1696 break;
1697 ret = ops->vidioc_g_modulator(file, fh, p);
1698 if (!ret)
1699 dbgarg(cmd, "index=%d, name=%s, "
1700 "capability=%d, rangelow=%d,"
1701 " rangehigh=%d, txsubchans=%d\n",
1702 p->index, p->name, p->capability,
1703 p->rangelow, p->rangehigh,
1704 p->txsubchans);
1705 break;
1707 case VIDIOC_S_MODULATOR:
1709 struct v4l2_modulator *p = arg;
1711 if (!ops->vidioc_s_modulator)
1712 break;
1713 dbgarg(cmd, "index=%d, name=%s, capability=%d, "
1714 "rangelow=%d, rangehigh=%d, txsubchans=%d\n",
1715 p->index, p->name, p->capability, p->rangelow,
1716 p->rangehigh, p->txsubchans);
1717 ret = ops->vidioc_s_modulator(file, fh, p);
1718 break;
1720 case VIDIOC_G_CROP:
1722 struct v4l2_crop *p = arg;
1724 if (!ops->vidioc_g_crop)
1725 break;
1727 dbgarg(cmd, "type=%s\n", prt_names(p->type, v4l2_type_names));
1728 ret = ops->vidioc_g_crop(file, fh, p);
1729 if (!ret)
1730 dbgrect(vfd, "", &p->c);
1731 break;
1733 case VIDIOC_S_CROP:
1735 struct v4l2_crop *p = arg;
1737 if (!ops->vidioc_s_crop)
1738 break;
1739 dbgarg(cmd, "type=%s\n", prt_names(p->type, v4l2_type_names));
1740 dbgrect(vfd, "", &p->c);
1741 ret = ops->vidioc_s_crop(file, fh, p);
1742 break;
1744 case VIDIOC_CROPCAP:
1746 struct v4l2_cropcap *p = arg;
1748 /*FIXME: Should also show v4l2_fract pixelaspect */
1749 if (!ops->vidioc_cropcap)
1750 break;
1752 dbgarg(cmd, "type=%s\n", prt_names(p->type, v4l2_type_names));
1753 ret = ops->vidioc_cropcap(file, fh, p);
1754 if (!ret) {
1755 dbgrect(vfd, "bounds ", &p->bounds);
1756 dbgrect(vfd, "defrect ", &p->defrect);
1758 break;
1760 case VIDIOC_G_JPEGCOMP:
1762 struct v4l2_jpegcompression *p = arg;
1764 if (!ops->vidioc_g_jpegcomp)
1765 break;
1767 ret = ops->vidioc_g_jpegcomp(file, fh, p);
1768 if (!ret)
1769 dbgarg(cmd, "quality=%d, APPn=%d, "
1770 "APP_len=%d, COM_len=%d, "
1771 "jpeg_markers=%d\n",
1772 p->quality, p->APPn, p->APP_len,
1773 p->COM_len, p->jpeg_markers);
1774 break;
1776 case VIDIOC_S_JPEGCOMP:
1778 struct v4l2_jpegcompression *p = arg;
1780 if (!ops->vidioc_g_jpegcomp)
1781 break;
1782 dbgarg(cmd, "quality=%d, APPn=%d, APP_len=%d, "
1783 "COM_len=%d, jpeg_markers=%d\n",
1784 p->quality, p->APPn, p->APP_len,
1785 p->COM_len, p->jpeg_markers);
1786 ret = ops->vidioc_s_jpegcomp(file, fh, p);
1787 break;
1789 case VIDIOC_G_ENC_INDEX:
1791 struct v4l2_enc_idx *p = arg;
1793 if (!ops->vidioc_g_enc_index)
1794 break;
1795 ret = ops->vidioc_g_enc_index(file, fh, p);
1796 if (!ret)
1797 dbgarg(cmd, "entries=%d, entries_cap=%d\n",
1798 p->entries, p->entries_cap);
1799 break;
1801 case VIDIOC_ENCODER_CMD:
1803 struct v4l2_encoder_cmd *p = arg;
1805 if (!ops->vidioc_encoder_cmd)
1806 break;
1807 ret = ops->vidioc_encoder_cmd(file, fh, p);
1808 if (!ret)
1809 dbgarg(cmd, "cmd=%d, flags=%x\n", p->cmd, p->flags);
1810 break;
1812 case VIDIOC_TRY_ENCODER_CMD:
1814 struct v4l2_encoder_cmd *p = arg;
1816 if (!ops->vidioc_try_encoder_cmd)
1817 break;
1818 ret = ops->vidioc_try_encoder_cmd(file, fh, p);
1819 if (!ret)
1820 dbgarg(cmd, "cmd=%d, flags=%x\n", p->cmd, p->flags);
1821 break;
1823 case VIDIOC_G_PARM:
1825 struct v4l2_streamparm *p = arg;
1827 if (ops->vidioc_g_parm) {
1828 ret = check_fmt(ops, p->type);
1829 if (ret)
1830 break;
1831 ret = ops->vidioc_g_parm(file, fh, p);
1832 } else {
1833 v4l2_std_id std = vfd->current_norm;
1835 if (p->type != V4L2_BUF_TYPE_VIDEO_CAPTURE)
1836 break;
1838 ret = 0;
1839 if (ops->vidioc_g_std)
1840 ret = ops->vidioc_g_std(file, fh, &std);
1841 else if (std == 0)
1842 ret = -EINVAL;
1843 if (ret == 0)
1844 v4l2_video_std_frame_period(std,
1845 &p->parm.capture.timeperframe);
1848 dbgarg(cmd, "type=%d\n", p->type);
1849 break;
1851 case VIDIOC_S_PARM:
1853 struct v4l2_streamparm *p = arg;
1855 if (!ops->vidioc_s_parm)
1856 break;
1857 ret = check_fmt(ops, p->type);
1858 if (ret)
1859 break;
1861 dbgarg(cmd, "type=%d\n", p->type);
1862 ret = ops->vidioc_s_parm(file, fh, p);
1863 break;
1865 case VIDIOC_G_TUNER:
1867 struct v4l2_tuner *p = arg;
1869 if (!ops->vidioc_g_tuner)
1870 break;
1872 ret = ops->vidioc_g_tuner(file, fh, p);
1873 if (!ret)
1874 dbgarg(cmd, "index=%d, name=%s, type=%d, "
1875 "capability=0x%x, rangelow=%d, "
1876 "rangehigh=%d, signal=%d, afc=%d, "
1877 "rxsubchans=0x%x, audmode=%d\n",
1878 p->index, p->name, p->type,
1879 p->capability, p->rangelow,
1880 p->rangehigh, p->signal, p->afc,
1881 p->rxsubchans, p->audmode);
1882 break;
1884 case VIDIOC_S_TUNER:
1886 struct v4l2_tuner *p = arg;
1888 if (!ops->vidioc_s_tuner)
1889 break;
1890 dbgarg(cmd, "index=%d, name=%s, type=%d, "
1891 "capability=0x%x, rangelow=%d, "
1892 "rangehigh=%d, signal=%d, afc=%d, "
1893 "rxsubchans=0x%x, audmode=%d\n",
1894 p->index, p->name, p->type,
1895 p->capability, p->rangelow,
1896 p->rangehigh, p->signal, p->afc,
1897 p->rxsubchans, p->audmode);
1898 ret = ops->vidioc_s_tuner(file, fh, p);
1899 break;
1901 case VIDIOC_G_FREQUENCY:
1903 struct v4l2_frequency *p = arg;
1905 if (!ops->vidioc_g_frequency)
1906 break;
1908 ret = ops->vidioc_g_frequency(file, fh, p);
1909 if (!ret)
1910 dbgarg(cmd, "tuner=%d, type=%d, frequency=%d\n",
1911 p->tuner, p->type, p->frequency);
1912 break;
1914 case VIDIOC_S_FREQUENCY:
1916 struct v4l2_frequency *p = arg;
1918 if (!ops->vidioc_s_frequency)
1919 break;
1920 dbgarg(cmd, "tuner=%d, type=%d, frequency=%d\n",
1921 p->tuner, p->type, p->frequency);
1922 ret = ops->vidioc_s_frequency(file, fh, p);
1923 break;
1925 case VIDIOC_G_SLICED_VBI_CAP:
1927 struct v4l2_sliced_vbi_cap *p = arg;
1929 if (!ops->vidioc_g_sliced_vbi_cap)
1930 break;
1932 /* Clear up to type, everything after type is zerod already */
1933 memset(p, 0, offsetof(struct v4l2_sliced_vbi_cap, type));
1935 dbgarg(cmd, "type=%s\n", prt_names(p->type, v4l2_type_names));
1936 ret = ops->vidioc_g_sliced_vbi_cap(file, fh, p);
1937 if (!ret)
1938 dbgarg2("service_set=%d\n", p->service_set);
1939 break;
1941 case VIDIOC_LOG_STATUS:
1943 if (!ops->vidioc_log_status)
1944 break;
1945 ret = ops->vidioc_log_status(file, fh);
1946 break;
1948 #ifdef CONFIG_VIDEO_ADV_DEBUG
1949 case VIDIOC_DBG_G_REGISTER:
1951 struct v4l2_dbg_register *p = arg;
1953 if (ops->vidioc_g_register) {
1954 if (!capable(CAP_SYS_ADMIN))
1955 ret = -EPERM;
1956 else
1957 ret = ops->vidioc_g_register(file, fh, p);
1959 break;
1961 case VIDIOC_DBG_S_REGISTER:
1963 struct v4l2_dbg_register *p = arg;
1965 if (ops->vidioc_s_register) {
1966 if (!capable(CAP_SYS_ADMIN))
1967 ret = -EPERM;
1968 else
1969 ret = ops->vidioc_s_register(file, fh, p);
1971 break;
1973 #endif
1974 case VIDIOC_DBG_G_CHIP_IDENT:
1976 struct v4l2_dbg_chip_ident *p = arg;
1978 if (!ops->vidioc_g_chip_ident)
1979 break;
1980 p->ident = V4L2_IDENT_NONE;
1981 p->revision = 0;
1982 ret = ops->vidioc_g_chip_ident(file, fh, p);
1983 if (!ret)
1984 dbgarg(cmd, "chip_ident=%u, revision=0x%x\n", p->ident, p->revision);
1985 break;
1987 case VIDIOC_S_HW_FREQ_SEEK:
1989 struct v4l2_hw_freq_seek *p = arg;
1991 if (!ops->vidioc_s_hw_freq_seek)
1992 break;
1993 dbgarg(cmd,
1994 "tuner=%d, type=%d, seek_upward=%d, wrap_around=%d\n",
1995 p->tuner, p->type, p->seek_upward, p->wrap_around);
1996 ret = ops->vidioc_s_hw_freq_seek(file, fh, p);
1997 break;
1999 case VIDIOC_ENUM_FRAMESIZES:
2001 struct v4l2_frmsizeenum *p = arg;
2003 if (!ops->vidioc_enum_framesizes)
2004 break;
2006 ret = ops->vidioc_enum_framesizes(file, fh, p);
2007 dbgarg(cmd,
2008 "index=%d, pixelformat=%c%c%c%c, type=%d ",
2009 p->index,
2010 (p->pixel_format & 0xff),
2011 (p->pixel_format >> 8) & 0xff,
2012 (p->pixel_format >> 16) & 0xff,
2013 (p->pixel_format >> 24) & 0xff,
2014 p->type);
2015 switch (p->type) {
2016 case V4L2_FRMSIZE_TYPE_DISCRETE:
2017 dbgarg3("width = %d, height=%d\n",
2018 p->discrete.width, p->discrete.height);
2019 break;
2020 case V4L2_FRMSIZE_TYPE_STEPWISE:
2021 dbgarg3("min %dx%d, max %dx%d, step %dx%d\n",
2022 p->stepwise.min_width, p->stepwise.min_height,
2023 p->stepwise.step_width, p->stepwise.step_height,
2024 p->stepwise.max_width, p->stepwise.max_height);
2025 break;
2026 case V4L2_FRMSIZE_TYPE_CONTINUOUS:
2027 dbgarg3("continuous\n");
2028 break;
2029 default:
2030 dbgarg3("- Unknown type!\n");
2033 break;
2035 case VIDIOC_ENUM_FRAMEINTERVALS:
2037 struct v4l2_frmivalenum *p = arg;
2039 if (!ops->vidioc_enum_frameintervals)
2040 break;
2042 ret = ops->vidioc_enum_frameintervals(file, fh, p);
2043 dbgarg(cmd,
2044 "index=%d, pixelformat=%d, width=%d, height=%d, type=%d ",
2045 p->index, p->pixel_format,
2046 p->width, p->height, p->type);
2047 switch (p->type) {
2048 case V4L2_FRMIVAL_TYPE_DISCRETE:
2049 dbgarg2("fps=%d/%d\n",
2050 p->discrete.numerator,
2051 p->discrete.denominator);
2052 break;
2053 case V4L2_FRMIVAL_TYPE_STEPWISE:
2054 dbgarg2("min=%d/%d, max=%d/%d, step=%d/%d\n",
2055 p->stepwise.min.numerator,
2056 p->stepwise.min.denominator,
2057 p->stepwise.max.numerator,
2058 p->stepwise.max.denominator,
2059 p->stepwise.step.numerator,
2060 p->stepwise.step.denominator);
2061 break;
2062 case V4L2_FRMIVAL_TYPE_CONTINUOUS:
2063 dbgarg2("continuous\n");
2064 break;
2065 default:
2066 dbgarg2("- Unknown type!\n");
2068 break;
2070 case VIDIOC_ENUM_DV_PRESETS:
2072 struct v4l2_dv_enum_preset *p = arg;
2074 if (!ops->vidioc_enum_dv_presets)
2075 break;
2077 ret = ops->vidioc_enum_dv_presets(file, fh, p);
2078 if (!ret)
2079 dbgarg(cmd,
2080 "index=%d, preset=%d, name=%s, width=%d,"
2081 " height=%d ",
2082 p->index, p->preset, p->name, p->width,
2083 p->height);
2084 break;
2086 case VIDIOC_S_DV_PRESET:
2088 struct v4l2_dv_preset *p = arg;
2090 if (!ops->vidioc_s_dv_preset)
2091 break;
2093 dbgarg(cmd, "preset=%d\n", p->preset);
2094 ret = ops->vidioc_s_dv_preset(file, fh, p);
2095 break;
2097 case VIDIOC_G_DV_PRESET:
2099 struct v4l2_dv_preset *p = arg;
2101 if (!ops->vidioc_g_dv_preset)
2102 break;
2104 ret = ops->vidioc_g_dv_preset(file, fh, p);
2105 if (!ret)
2106 dbgarg(cmd, "preset=%d\n", p->preset);
2107 break;
2109 case VIDIOC_QUERY_DV_PRESET:
2111 struct v4l2_dv_preset *p = arg;
2113 if (!ops->vidioc_query_dv_preset)
2114 break;
2116 ret = ops->vidioc_query_dv_preset(file, fh, p);
2117 if (!ret)
2118 dbgarg(cmd, "preset=%d\n", p->preset);
2119 break;
2121 case VIDIOC_S_DV_TIMINGS:
2123 struct v4l2_dv_timings *p = arg;
2125 if (!ops->vidioc_s_dv_timings)
2126 break;
2128 switch (p->type) {
2129 case V4L2_DV_BT_656_1120:
2130 dbgarg2("bt-656/1120:interlaced=%d, pixelclock=%lld,"
2131 " width=%d, height=%d, polarities=%x,"
2132 " hfrontporch=%d, hsync=%d, hbackporch=%d,"
2133 " vfrontporch=%d, vsync=%d, vbackporch=%d,"
2134 " il_vfrontporch=%d, il_vsync=%d,"
2135 " il_vbackporch=%d\n",
2136 p->bt.interlaced, p->bt.pixelclock,
2137 p->bt.width, p->bt.height, p->bt.polarities,
2138 p->bt.hfrontporch, p->bt.hsync,
2139 p->bt.hbackporch, p->bt.vfrontporch,
2140 p->bt.vsync, p->bt.vbackporch,
2141 p->bt.il_vfrontporch, p->bt.il_vsync,
2142 p->bt.il_vbackporch);
2143 ret = ops->vidioc_s_dv_timings(file, fh, p);
2144 break;
2145 default:
2146 dbgarg2("Unknown type %d!\n", p->type);
2147 break;
2149 break;
2151 case VIDIOC_G_DV_TIMINGS:
2153 struct v4l2_dv_timings *p = arg;
2155 if (!ops->vidioc_g_dv_timings)
2156 break;
2158 ret = ops->vidioc_g_dv_timings(file, fh, p);
2159 if (!ret) {
2160 switch (p->type) {
2161 case V4L2_DV_BT_656_1120:
2162 dbgarg2("bt-656/1120:interlaced=%d,"
2163 " pixelclock=%lld,"
2164 " width=%d, height=%d, polarities=%x,"
2165 " hfrontporch=%d, hsync=%d,"
2166 " hbackporch=%d, vfrontporch=%d,"
2167 " vsync=%d, vbackporch=%d,"
2168 " il_vfrontporch=%d, il_vsync=%d,"
2169 " il_vbackporch=%d\n",
2170 p->bt.interlaced, p->bt.pixelclock,
2171 p->bt.width, p->bt.height,
2172 p->bt.polarities, p->bt.hfrontporch,
2173 p->bt.hsync, p->bt.hbackporch,
2174 p->bt.vfrontporch, p->bt.vsync,
2175 p->bt.vbackporch, p->bt.il_vfrontporch,
2176 p->bt.il_vsync, p->bt.il_vbackporch);
2177 break;
2178 default:
2179 dbgarg2("Unknown type %d!\n", p->type);
2180 break;
2183 break;
2185 case VIDIOC_DQEVENT:
2187 struct v4l2_event *ev = arg;
2189 if (!ops->vidioc_subscribe_event)
2190 break;
2192 ret = v4l2_event_dequeue(fh, ev, file->f_flags & O_NONBLOCK);
2193 if (ret < 0) {
2194 dbgarg(cmd, "no pending events?");
2195 break;
2197 dbgarg(cmd,
2198 "pending=%d, type=0x%8.8x, sequence=%d, "
2199 "timestamp=%lu.%9.9lu ",
2200 ev->pending, ev->type, ev->sequence,
2201 ev->timestamp.tv_sec, ev->timestamp.tv_nsec);
2202 break;
2204 case VIDIOC_SUBSCRIBE_EVENT:
2206 struct v4l2_event_subscription *sub = arg;
2208 if (!ops->vidioc_subscribe_event)
2209 break;
2211 ret = ops->vidioc_subscribe_event(fh, sub);
2212 if (ret < 0) {
2213 dbgarg(cmd, "failed, ret=%ld", ret);
2214 break;
2216 dbgarg(cmd, "type=0x%8.8x", sub->type);
2217 break;
2219 case VIDIOC_UNSUBSCRIBE_EVENT:
2221 struct v4l2_event_subscription *sub = arg;
2223 if (!ops->vidioc_unsubscribe_event)
2224 break;
2226 ret = ops->vidioc_unsubscribe_event(fh, sub);
2227 if (ret < 0) {
2228 dbgarg(cmd, "failed, ret=%ld", ret);
2229 break;
2231 dbgarg(cmd, "type=0x%8.8x", sub->type);
2232 break;
2234 default:
2236 if (!ops->vidioc_default)
2237 break;
2238 ret = ops->vidioc_default(file, fh, cmd, arg);
2239 break;
2241 } /* switch */
2243 if (vfd->debug & V4L2_DEBUG_IOCTL_ARG) {
2244 if (ret < 0) {
2245 v4l_print_ioctl(vfd->name, cmd);
2246 printk(KERN_CONT " error %ld\n", ret);
2250 return ret;
2253 /* In some cases, only a few fields are used as input, i.e. when the app sets
2254 * "index" and then the driver fills in the rest of the structure for the thing
2255 * with that index. We only need to copy up the first non-input field. */
2256 static unsigned long cmd_input_size(unsigned int cmd)
2258 /* Size of structure up to and including 'field' */
2259 #define CMDINSIZE(cmd, type, field) \
2260 case VIDIOC_##cmd: \
2261 return offsetof(struct v4l2_##type, field) + \
2262 sizeof(((struct v4l2_##type *)0)->field);
2264 switch (cmd) {
2265 CMDINSIZE(ENUM_FMT, fmtdesc, type);
2266 CMDINSIZE(G_FMT, format, type);
2267 CMDINSIZE(QUERYBUF, buffer, length);
2268 CMDINSIZE(G_PARM, streamparm, type);
2269 CMDINSIZE(ENUMSTD, standard, index);
2270 CMDINSIZE(ENUMINPUT, input, index);
2271 CMDINSIZE(G_CTRL, control, id);
2272 CMDINSIZE(G_TUNER, tuner, index);
2273 CMDINSIZE(QUERYCTRL, queryctrl, id);
2274 CMDINSIZE(QUERYMENU, querymenu, index);
2275 CMDINSIZE(ENUMOUTPUT, output, index);
2276 CMDINSIZE(G_MODULATOR, modulator, index);
2277 CMDINSIZE(G_FREQUENCY, frequency, tuner);
2278 CMDINSIZE(CROPCAP, cropcap, type);
2279 CMDINSIZE(G_CROP, crop, type);
2280 CMDINSIZE(ENUMAUDIO, audio, index);
2281 CMDINSIZE(ENUMAUDOUT, audioout, index);
2282 CMDINSIZE(ENCODER_CMD, encoder_cmd, flags);
2283 CMDINSIZE(TRY_ENCODER_CMD, encoder_cmd, flags);
2284 CMDINSIZE(G_SLICED_VBI_CAP, sliced_vbi_cap, type);
2285 CMDINSIZE(ENUM_FRAMESIZES, frmsizeenum, pixel_format);
2286 CMDINSIZE(ENUM_FRAMEINTERVALS, frmivalenum, height);
2287 default:
2288 return _IOC_SIZE(cmd);
2292 static int check_array_args(unsigned int cmd, void *parg, size_t *array_size,
2293 void * __user *user_ptr, void ***kernel_ptr)
2295 int ret = 0;
2297 switch (cmd) {
2298 case VIDIOC_QUERYBUF:
2299 case VIDIOC_QBUF:
2300 case VIDIOC_DQBUF: {
2301 struct v4l2_buffer *buf = parg;
2303 if (V4L2_TYPE_IS_MULTIPLANAR(buf->type) && buf->length > 0) {
2304 if (buf->length > VIDEO_MAX_PLANES) {
2305 ret = -EINVAL;
2306 break;
2308 *user_ptr = (void __user *)buf->m.planes;
2309 *kernel_ptr = (void **)&buf->m.planes;
2310 *array_size = sizeof(struct v4l2_plane) * buf->length;
2311 ret = 1;
2313 break;
2316 case VIDIOC_S_EXT_CTRLS:
2317 case VIDIOC_G_EXT_CTRLS:
2318 case VIDIOC_TRY_EXT_CTRLS: {
2319 struct v4l2_ext_controls *ctrls = parg;
2321 if (ctrls->count != 0) {
2322 *user_ptr = (void __user *)ctrls->controls;
2323 *kernel_ptr = (void **)&ctrls->controls;
2324 *array_size = sizeof(struct v4l2_ext_control)
2325 * ctrls->count;
2326 ret = 1;
2328 break;
2332 return ret;
2335 long video_ioctl2(struct file *file,
2336 unsigned int cmd, unsigned long arg)
2338 char sbuf[128];
2339 void *mbuf = NULL;
2340 void *parg = (void *)arg;
2341 long err = -EINVAL;
2342 bool has_array_args;
2343 size_t array_size = 0;
2344 void __user *user_ptr = NULL;
2345 void **kernel_ptr = NULL;
2347 /* Copy arguments into temp kernel buffer */
2348 if (_IOC_DIR(cmd) != _IOC_NONE) {
2349 if (_IOC_SIZE(cmd) <= sizeof(sbuf)) {
2350 parg = sbuf;
2351 } else {
2352 /* too big to allocate from stack */
2353 mbuf = kmalloc(_IOC_SIZE(cmd), GFP_KERNEL);
2354 if (NULL == mbuf)
2355 return -ENOMEM;
2356 parg = mbuf;
2359 err = -EFAULT;
2360 if (_IOC_DIR(cmd) & _IOC_WRITE) {
2361 unsigned long n = cmd_input_size(cmd);
2363 if (copy_from_user(parg, (void __user *)arg, n))
2364 goto out;
2366 /* zero out anything we don't copy from userspace */
2367 if (n < _IOC_SIZE(cmd))
2368 memset((u8 *)parg + n, 0, _IOC_SIZE(cmd) - n);
2369 } else {
2370 /* read-only ioctl */
2371 memset(parg, 0, _IOC_SIZE(cmd));
2375 err = check_array_args(cmd, parg, &array_size, &user_ptr, &kernel_ptr);
2376 if (err < 0)
2377 goto out;
2378 has_array_args = err;
2380 if (has_array_args) {
2382 * When adding new types of array args, make sure that the
2383 * parent argument to ioctl (which contains the pointer to the
2384 * array) fits into sbuf (so that mbuf will still remain
2385 * unused up to here).
2387 mbuf = kmalloc(array_size, GFP_KERNEL);
2388 err = -ENOMEM;
2389 if (NULL == mbuf)
2390 goto out_array_args;
2391 err = -EFAULT;
2392 if (copy_from_user(mbuf, user_ptr, array_size))
2393 goto out_array_args;
2394 *kernel_ptr = mbuf;
2397 /* Handles IOCTL */
2398 err = __video_do_ioctl(file, cmd, parg);
2399 if (err == -ENOIOCTLCMD)
2400 err = -EINVAL;
2402 if (has_array_args) {
2403 *kernel_ptr = user_ptr;
2404 if (copy_to_user(user_ptr, mbuf, array_size))
2405 err = -EFAULT;
2406 goto out_array_args;
2408 if (err < 0)
2409 goto out;
2411 out_array_args:
2412 /* Copy results into user buffer */
2413 switch (_IOC_DIR(cmd)) {
2414 case _IOC_READ:
2415 case (_IOC_WRITE | _IOC_READ):
2416 if (copy_to_user((void __user *)arg, parg, _IOC_SIZE(cmd)))
2417 err = -EFAULT;
2418 break;
2421 out:
2422 kfree(mbuf);
2423 return err;
2425 EXPORT_SYMBOL(video_ioctl2);