aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--Documentation/video4linux/v4l2-framework.txt27
-rw-r--r--drivers/media/video/v4l2-dev.c14
-rw-r--r--drivers/media/video/v4l2-ioctl.c189
-rw-r--r--include/media/v4l2-dev.h11
4 files changed, 148 insertions, 93 deletions
diff --git a/Documentation/video4linux/v4l2-framework.txt b/Documentation/video4linux/v4l2-framework.txt
index fe53177f0d3c..e1e6a01d7ac6 100644
--- a/Documentation/video4linux/v4l2-framework.txt
+++ b/Documentation/video4linux/v4l2-framework.txt
@@ -580,19 +580,25 @@ allocated memory.
580You should also set these fields: 580You should also set these fields:
581 581
582- v4l2_dev: set to the v4l2_device parent device. 582- v4l2_dev: set to the v4l2_device parent device.
583
583- name: set to something descriptive and unique. 584- name: set to something descriptive and unique.
585
584- fops: set to the v4l2_file_operations struct. 586- fops: set to the v4l2_file_operations struct.
587
585- ioctl_ops: if you use the v4l2_ioctl_ops to simplify ioctl maintenance 588- ioctl_ops: if you use the v4l2_ioctl_ops to simplify ioctl maintenance
586 (highly recommended to use this and it might become compulsory in the 589 (highly recommended to use this and it might become compulsory in the
587 future!), then set this to your v4l2_ioctl_ops struct. 590 future!), then set this to your v4l2_ioctl_ops struct.
591
588- lock: leave to NULL if you want to do all the locking in the driver. 592- lock: leave to NULL if you want to do all the locking in the driver.
589 Otherwise you give it a pointer to a struct mutex_lock and before any 593 Otherwise you give it a pointer to a struct mutex_lock and before any
590 of the v4l2_file_operations is called this lock will be taken by the 594 of the v4l2_file_operations is called this lock will be taken by the
591 core and released afterwards. 595 core and released afterwards. See the next section for more details.
596
592- prio: keeps track of the priorities. Used to implement VIDIOC_G/S_PRIORITY. 597- prio: keeps track of the priorities. Used to implement VIDIOC_G/S_PRIORITY.
593 If left to NULL, then it will use the struct v4l2_prio_state in v4l2_device. 598 If left to NULL, then it will use the struct v4l2_prio_state in v4l2_device.
594 If you want to have a separate priority state per (group of) device node(s), 599 If you want to have a separate priority state per (group of) device node(s),
595 then you can point it to your own struct v4l2_prio_state. 600 then you can point it to your own struct v4l2_prio_state.
601
596- parent: you only set this if v4l2_device was registered with NULL as 602- parent: you only set this if v4l2_device was registered with NULL as
597 the parent device struct. This only happens in cases where one hardware 603 the parent device struct. This only happens in cases where one hardware
598 device has multiple PCI devices that all share the same v4l2_device core. 604 device has multiple PCI devices that all share the same v4l2_device core.
@@ -602,6 +608,7 @@ You should also set these fields:
602 (cx8802). Since the v4l2_device cannot be associated with a particular 608 (cx8802). Since the v4l2_device cannot be associated with a particular
603 PCI device it is setup without a parent device. But when the struct 609 PCI device it is setup without a parent device. But when the struct
604 video_device is setup you do know which parent PCI device to use. 610 video_device is setup you do know which parent PCI device to use.
611
605- flags: optional. Set to V4L2_FL_USE_FH_PRIO if you want to let the framework 612- flags: optional. Set to V4L2_FL_USE_FH_PRIO if you want to let the framework
606 handle the VIDIOC_G/S_PRIORITY ioctls. This requires that you use struct 613 handle the VIDIOC_G/S_PRIORITY ioctls. This requires that you use struct
607 v4l2_fh. Eventually this flag will disappear once all drivers use the core 614 v4l2_fh. Eventually this flag will disappear once all drivers use the core
@@ -634,8 +641,22 @@ v4l2_file_operations and locking
634-------------------------------- 641--------------------------------
635 642
636You can set a pointer to a mutex_lock in struct video_device. Usually this 643You can set a pointer to a mutex_lock in struct video_device. Usually this
637will be either a top-level mutex or a mutex per device node. If you want 644will be either a top-level mutex or a mutex per device node. By default this
638finer-grained locking then you have to set it to NULL and do you own locking. 645lock will be used for each file operation and ioctl, but you can disable
646locking for selected ioctls by calling:
647
648 void v4l2_dont_use_lock(struct video_device *vdev, unsigned int cmd);
649
650E.g.: v4l2_dont_use_lock(vdev, VIDIOC_DQBUF);
651
652You have to call this before you register the video_device.
653
654Particularly with USB drivers where certain commands such as setting controls
655can take a long time you may want to do your own locking for the buffer queuing
656ioctls.
657
658If you want still finer-grained locking then you have to set mutex_lock to NULL
659and do you own locking completely.
639 660
640It is up to the driver developer to decide which method to use. However, if 661It is up to the driver developer to decide which method to use. However, if
641your driver has high-latency operations (for example, changing the exposure 662your driver has high-latency operations (for example, changing the exposure
diff --git a/drivers/media/video/v4l2-dev.c b/drivers/media/video/v4l2-dev.c
index 70bec548d904..e4a9ed67bb2e 100644
--- a/drivers/media/video/v4l2-dev.c
+++ b/drivers/media/video/v4l2-dev.c
@@ -322,11 +322,19 @@ static long v4l2_ioctl(struct file *filp, unsigned int cmd, unsigned long arg)
322 int ret = -ENODEV; 322 int ret = -ENODEV;
323 323
324 if (vdev->fops->unlocked_ioctl) { 324 if (vdev->fops->unlocked_ioctl) {
325 if (vdev->lock && mutex_lock_interruptible(vdev->lock)) 325 bool locked = false;
326 return -ERESTARTSYS; 326
327 if (vdev->lock) {
328 /* always lock unless the cmd is marked as "don't use lock" */
329 locked = !v4l2_is_known_ioctl(cmd) ||
330 !test_bit(_IOC_NR(cmd), vdev->dont_use_lock);
331
332 if (locked && mutex_lock_interruptible(vdev->lock))
333 return -ERESTARTSYS;
334 }
327 if (video_is_registered(vdev)) 335 if (video_is_registered(vdev))
328 ret = vdev->fops->unlocked_ioctl(filp, cmd, arg); 336 ret = vdev->fops->unlocked_ioctl(filp, cmd, arg);
329 if (vdev->lock) 337 if (locked)
330 mutex_unlock(vdev->lock); 338 mutex_unlock(vdev->lock);
331 } else if (vdev->fops->ioctl) { 339 } else if (vdev->fops->ioctl) {
332 /* This code path is a replacement for the BKL. It is a major 340 /* This code path is a replacement for the BKL. It is a major
diff --git a/drivers/media/video/v4l2-ioctl.c b/drivers/media/video/v4l2-ioctl.c
index 5b2ec1fd2d0a..ef44b084132a 100644
--- a/drivers/media/video/v4l2-ioctl.c
+++ b/drivers/media/video/v4l2-ioctl.c
@@ -195,93 +195,106 @@ static const char *v4l2_memory_names[] = {
195 195
196/* ------------------------------------------------------------------ */ 196/* ------------------------------------------------------------------ */
197/* debug help functions */ 197/* debug help functions */
198static const char *v4l2_ioctls[] = { 198
199 [_IOC_NR(VIDIOC_QUERYCAP)] = "VIDIOC_QUERYCAP", 199struct v4l2_ioctl_info {
200 [_IOC_NR(VIDIOC_RESERVED)] = "VIDIOC_RESERVED", 200 unsigned int ioctl;
201 [_IOC_NR(VIDIOC_ENUM_FMT)] = "VIDIOC_ENUM_FMT", 201 const char * const name;
202 [_IOC_NR(VIDIOC_G_FMT)] = "VIDIOC_G_FMT", 202};
203 [_IOC_NR(VIDIOC_S_FMT)] = "VIDIOC_S_FMT", 203
204 [_IOC_NR(VIDIOC_REQBUFS)] = "VIDIOC_REQBUFS", 204#define IOCTL_INFO(_ioctl) [_IOC_NR(_ioctl)] = { \
205 [_IOC_NR(VIDIOC_QUERYBUF)] = "VIDIOC_QUERYBUF", 205 .ioctl = _ioctl, \
206 [_IOC_NR(VIDIOC_G_FBUF)] = "VIDIOC_G_FBUF", 206 .name = #_ioctl, \
207 [_IOC_NR(VIDIOC_S_FBUF)] = "VIDIOC_S_FBUF", 207}
208 [_IOC_NR(VIDIOC_OVERLAY)] = "VIDIOC_OVERLAY", 208
209 [_IOC_NR(VIDIOC_QBUF)] = "VIDIOC_QBUF", 209static struct v4l2_ioctl_info v4l2_ioctls[] = {
210 [_IOC_NR(VIDIOC_DQBUF)] = "VIDIOC_DQBUF", 210 IOCTL_INFO(VIDIOC_QUERYCAP),
211 [_IOC_NR(VIDIOC_STREAMON)] = "VIDIOC_STREAMON", 211 IOCTL_INFO(VIDIOC_ENUM_FMT),
212 [_IOC_NR(VIDIOC_STREAMOFF)] = "VIDIOC_STREAMOFF", 212 IOCTL_INFO(VIDIOC_G_FMT),
213 [_IOC_NR(VIDIOC_G_PARM)] = "VIDIOC_G_PARM", 213 IOCTL_INFO(VIDIOC_S_FMT),
214 [_IOC_NR(VIDIOC_S_PARM)] = "VIDIOC_S_PARM", 214 IOCTL_INFO(VIDIOC_REQBUFS),
215 [_IOC_NR(VIDIOC_G_STD)] = "VIDIOC_G_STD", 215 IOCTL_INFO(VIDIOC_QUERYBUF),
216 [_IOC_NR(VIDIOC_S_STD)] = "VIDIOC_S_STD", 216 IOCTL_INFO(VIDIOC_G_FBUF),
217 [_IOC_NR(VIDIOC_ENUMSTD)] = "VIDIOC_ENUMSTD", 217 IOCTL_INFO(VIDIOC_S_FBUF),
218 [_IOC_NR(VIDIOC_ENUMINPUT)] = "VIDIOC_ENUMINPUT", 218 IOCTL_INFO(VIDIOC_OVERLAY),
219 [_IOC_NR(VIDIOC_G_CTRL)] = "VIDIOC_G_CTRL", 219 IOCTL_INFO(VIDIOC_QBUF),
220 [_IOC_NR(VIDIOC_S_CTRL)] = "VIDIOC_S_CTRL", 220 IOCTL_INFO(VIDIOC_DQBUF),
221 [_IOC_NR(VIDIOC_G_TUNER)] = "VIDIOC_G_TUNER", 221 IOCTL_INFO(VIDIOC_STREAMON),
222 [_IOC_NR(VIDIOC_S_TUNER)] = "VIDIOC_S_TUNER", 222 IOCTL_INFO(VIDIOC_STREAMOFF),
223 [_IOC_NR(VIDIOC_G_AUDIO)] = "VIDIOC_G_AUDIO", 223 IOCTL_INFO(VIDIOC_G_PARM),
224 [_IOC_NR(VIDIOC_S_AUDIO)] = "VIDIOC_S_AUDIO", 224 IOCTL_INFO(VIDIOC_S_PARM),
225 [_IOC_NR(VIDIOC_QUERYCTRL)] = "VIDIOC_QUERYCTRL", 225 IOCTL_INFO(VIDIOC_G_STD),
226 [_IOC_NR(VIDIOC_QUERYMENU)] = "VIDIOC_QUERYMENU", 226 IOCTL_INFO(VIDIOC_S_STD),
227 [_IOC_NR(VIDIOC_G_INPUT)] = "VIDIOC_G_INPUT", 227 IOCTL_INFO(VIDIOC_ENUMSTD),
228 [_IOC_NR(VIDIOC_S_INPUT)] = "VIDIOC_S_INPUT", 228 IOCTL_INFO(VIDIOC_ENUMINPUT),
229 [_IOC_NR(VIDIOC_G_OUTPUT)] = "VIDIOC_G_OUTPUT", 229 IOCTL_INFO(VIDIOC_G_CTRL),
230 [_IOC_NR(VIDIOC_S_OUTPUT)] = "VIDIOC_S_OUTPUT", 230 IOCTL_INFO(VIDIOC_S_CTRL),
231 [_IOC_NR(VIDIOC_ENUMOUTPUT)] = "VIDIOC_ENUMOUTPUT", 231 IOCTL_INFO(VIDIOC_G_TUNER),
232 [_IOC_NR(VIDIOC_G_AUDOUT)] = "VIDIOC_G_AUDOUT", 232 IOCTL_INFO(VIDIOC_S_TUNER),
233 [_IOC_NR(VIDIOC_S_AUDOUT)] = "VIDIOC_S_AUDOUT", 233 IOCTL_INFO(VIDIOC_G_AUDIO),
234 [_IOC_NR(VIDIOC_G_MODULATOR)] = "VIDIOC_G_MODULATOR", 234 IOCTL_INFO(VIDIOC_S_AUDIO),
235 [_IOC_NR(VIDIOC_S_MODULATOR)] = "VIDIOC_S_MODULATOR", 235 IOCTL_INFO(VIDIOC_QUERYCTRL),
236 [_IOC_NR(VIDIOC_G_FREQUENCY)] = "VIDIOC_G_FREQUENCY", 236 IOCTL_INFO(VIDIOC_QUERYMENU),
237 [_IOC_NR(VIDIOC_S_FREQUENCY)] = "VIDIOC_S_FREQUENCY", 237 IOCTL_INFO(VIDIOC_G_INPUT),
238 [_IOC_NR(VIDIOC_CROPCAP)] = "VIDIOC_CROPCAP", 238 IOCTL_INFO(VIDIOC_S_INPUT),
239 [_IOC_NR(VIDIOC_G_CROP)] = "VIDIOC_G_CROP", 239 IOCTL_INFO(VIDIOC_G_OUTPUT),
240 [_IOC_NR(VIDIOC_S_CROP)] = "VIDIOC_S_CROP", 240 IOCTL_INFO(VIDIOC_S_OUTPUT),
241 [_IOC_NR(VIDIOC_G_SELECTION)] = "VIDIOC_G_SELECTION", 241 IOCTL_INFO(VIDIOC_ENUMOUTPUT),
242 [_IOC_NR(VIDIOC_S_SELECTION)] = "VIDIOC_S_SELECTION", 242 IOCTL_INFO(VIDIOC_G_AUDOUT),
243 [_IOC_NR(VIDIOC_G_JPEGCOMP)] = "VIDIOC_G_JPEGCOMP", 243 IOCTL_INFO(VIDIOC_S_AUDOUT),
244 [_IOC_NR(VIDIOC_S_JPEGCOMP)] = "VIDIOC_S_JPEGCOMP", 244 IOCTL_INFO(VIDIOC_G_MODULATOR),
245 [_IOC_NR(VIDIOC_QUERYSTD)] = "VIDIOC_QUERYSTD", 245 IOCTL_INFO(VIDIOC_S_MODULATOR),
246 [_IOC_NR(VIDIOC_TRY_FMT)] = "VIDIOC_TRY_FMT", 246 IOCTL_INFO(VIDIOC_G_FREQUENCY),
247 [_IOC_NR(VIDIOC_ENUMAUDIO)] = "VIDIOC_ENUMAUDIO", 247 IOCTL_INFO(VIDIOC_S_FREQUENCY),
248 [_IOC_NR(VIDIOC_ENUMAUDOUT)] = "VIDIOC_ENUMAUDOUT", 248 IOCTL_INFO(VIDIOC_CROPCAP),
249 [_IOC_NR(VIDIOC_G_PRIORITY)] = "VIDIOC_G_PRIORITY", 249 IOCTL_INFO(VIDIOC_G_CROP),
250 [_IOC_NR(VIDIOC_S_PRIORITY)] = "VIDIOC_S_PRIORITY", 250 IOCTL_INFO(VIDIOC_S_CROP),
251 [_IOC_NR(VIDIOC_G_SLICED_VBI_CAP)] = "VIDIOC_G_SLICED_VBI_CAP", 251 IOCTL_INFO(VIDIOC_G_SELECTION),
252 [_IOC_NR(VIDIOC_LOG_STATUS)] = "VIDIOC_LOG_STATUS", 252 IOCTL_INFO(VIDIOC_S_SELECTION),
253 [_IOC_NR(VIDIOC_G_EXT_CTRLS)] = "VIDIOC_G_EXT_CTRLS", 253 IOCTL_INFO(VIDIOC_G_JPEGCOMP),
254 [_IOC_NR(VIDIOC_S_EXT_CTRLS)] = "VIDIOC_S_EXT_CTRLS", 254 IOCTL_INFO(VIDIOC_S_JPEGCOMP),
255 [_IOC_NR(VIDIOC_TRY_EXT_CTRLS)] = "VIDIOC_TRY_EXT_CTRLS", 255 IOCTL_INFO(VIDIOC_QUERYSTD),
256#if 1 256 IOCTL_INFO(VIDIOC_TRY_FMT),
257 [_IOC_NR(VIDIOC_ENUM_FRAMESIZES)] = "VIDIOC_ENUM_FRAMESIZES", 257 IOCTL_INFO(VIDIOC_ENUMAUDIO),
258 [_IOC_NR(VIDIOC_ENUM_FRAMEINTERVALS)] = "VIDIOC_ENUM_FRAMEINTERVALS", 258 IOCTL_INFO(VIDIOC_ENUMAUDOUT),
259 [_IOC_NR(VIDIOC_G_ENC_INDEX)] = "VIDIOC_G_ENC_INDEX", 259 IOCTL_INFO(VIDIOC_G_PRIORITY),
260 [_IOC_NR(VIDIOC_ENCODER_CMD)] = "VIDIOC_ENCODER_CMD", 260 IOCTL_INFO(VIDIOC_S_PRIORITY),
261 [_IOC_NR(VIDIOC_TRY_ENCODER_CMD)] = "VIDIOC_TRY_ENCODER_CMD", 261 IOCTL_INFO(VIDIOC_G_SLICED_VBI_CAP),
262 262 IOCTL_INFO(VIDIOC_LOG_STATUS),
263 [_IOC_NR(VIDIOC_DECODER_CMD)] = "VIDIOC_DECODER_CMD", 263 IOCTL_INFO(VIDIOC_G_EXT_CTRLS),
264 [_IOC_NR(VIDIOC_TRY_DECODER_CMD)] = "VIDIOC_TRY_DECODER_CMD", 264 IOCTL_INFO(VIDIOC_S_EXT_CTRLS),
265 [_IOC_NR(VIDIOC_DBG_S_REGISTER)] = "VIDIOC_DBG_S_REGISTER", 265 IOCTL_INFO(VIDIOC_TRY_EXT_CTRLS),
266 [_IOC_NR(VIDIOC_DBG_G_REGISTER)] = "VIDIOC_DBG_G_REGISTER", 266 IOCTL_INFO(VIDIOC_ENUM_FRAMESIZES),
267 267 IOCTL_INFO(VIDIOC_ENUM_FRAMEINTERVALS),
268 [_IOC_NR(VIDIOC_DBG_G_CHIP_IDENT)] = "VIDIOC_DBG_G_CHIP_IDENT", 268 IOCTL_INFO(VIDIOC_G_ENC_INDEX),
269 [_IOC_NR(VIDIOC_S_HW_FREQ_SEEK)] = "VIDIOC_S_HW_FREQ_SEEK", 269 IOCTL_INFO(VIDIOC_ENCODER_CMD),
270#endif 270 IOCTL_INFO(VIDIOC_TRY_ENCODER_CMD),
271 [_IOC_NR(VIDIOC_ENUM_DV_PRESETS)] = "VIDIOC_ENUM_DV_PRESETS", 271 IOCTL_INFO(VIDIOC_DECODER_CMD),
272 [_IOC_NR(VIDIOC_S_DV_PRESET)] = "VIDIOC_S_DV_PRESET", 272 IOCTL_INFO(VIDIOC_TRY_DECODER_CMD),
273 [_IOC_NR(VIDIOC_G_DV_PRESET)] = "VIDIOC_G_DV_PRESET", 273 IOCTL_INFO(VIDIOC_DBG_S_REGISTER),
274 [_IOC_NR(VIDIOC_QUERY_DV_PRESET)] = "VIDIOC_QUERY_DV_PRESET", 274 IOCTL_INFO(VIDIOC_DBG_G_REGISTER),
275 [_IOC_NR(VIDIOC_S_DV_TIMINGS)] = "VIDIOC_S_DV_TIMINGS", 275 IOCTL_INFO(VIDIOC_DBG_G_CHIP_IDENT),
276 [_IOC_NR(VIDIOC_G_DV_TIMINGS)] = "VIDIOC_G_DV_TIMINGS", 276 IOCTL_INFO(VIDIOC_S_HW_FREQ_SEEK),
277 [_IOC_NR(VIDIOC_DQEVENT)] = "VIDIOC_DQEVENT", 277 IOCTL_INFO(VIDIOC_ENUM_DV_PRESETS),
278 [_IOC_NR(VIDIOC_SUBSCRIBE_EVENT)] = "VIDIOC_SUBSCRIBE_EVENT", 278 IOCTL_INFO(VIDIOC_S_DV_PRESET),
279 [_IOC_NR(VIDIOC_UNSUBSCRIBE_EVENT)] = "VIDIOC_UNSUBSCRIBE_EVENT", 279 IOCTL_INFO(VIDIOC_G_DV_PRESET),
280 [_IOC_NR(VIDIOC_CREATE_BUFS)] = "VIDIOC_CREATE_BUFS", 280 IOCTL_INFO(VIDIOC_QUERY_DV_PRESET),
281 [_IOC_NR(VIDIOC_PREPARE_BUF)] = "VIDIOC_PREPARE_BUF", 281 IOCTL_INFO(VIDIOC_S_DV_TIMINGS),
282 IOCTL_INFO(VIDIOC_G_DV_TIMINGS),
283 IOCTL_INFO(VIDIOC_DQEVENT),
284 IOCTL_INFO(VIDIOC_SUBSCRIBE_EVENT),
285 IOCTL_INFO(VIDIOC_UNSUBSCRIBE_EVENT),
286 IOCTL_INFO(VIDIOC_CREATE_BUFS),
287 IOCTL_INFO(VIDIOC_PREPARE_BUF),
282}; 288};
283#define V4L2_IOCTLS ARRAY_SIZE(v4l2_ioctls) 289#define V4L2_IOCTLS ARRAY_SIZE(v4l2_ioctls)
284 290
291bool v4l2_is_known_ioctl(unsigned int cmd)
292{
293 if (_IOC_NR(cmd) >= V4L2_IOCTLS)
294 return false;
295 return v4l2_ioctls[_IOC_NR(cmd)].ioctl == cmd;
296}
297
285/* Common ioctl debug function. This function can be used by 298/* Common ioctl debug function. This function can be used by
286 external ioctl messages as well as internal V4L ioctl */ 299 external ioctl messages as well as internal V4L ioctl */
287void v4l_printk_ioctl(unsigned int cmd) 300void v4l_printk_ioctl(unsigned int cmd)
@@ -297,7 +310,7 @@ void v4l_printk_ioctl(unsigned int cmd)
297 type = "v4l2"; 310 type = "v4l2";
298 break; 311 break;
299 } 312 }
300 printk("%s", v4l2_ioctls[_IOC_NR(cmd)]); 313 printk("%s", v4l2_ioctls[_IOC_NR(cmd)].name);
301 return; 314 return;
302 default: 315 default:
303 type = "unknown"; 316 type = "unknown";
@@ -1948,9 +1961,9 @@ static long __video_do_ioctl(struct file *file,
1948 vfd->v4l2_dev->name); 1961 vfd->v4l2_dev->name);
1949 break; 1962 break;
1950 } 1963 }
1951#ifdef CONFIG_VIDEO_ADV_DEBUG
1952 case VIDIOC_DBG_G_REGISTER: 1964 case VIDIOC_DBG_G_REGISTER:
1953 { 1965 {
1966#ifdef CONFIG_VIDEO_ADV_DEBUG
1954 struct v4l2_dbg_register *p = arg; 1967 struct v4l2_dbg_register *p = arg;
1955 1968
1956 if (ops->vidioc_g_register) { 1969 if (ops->vidioc_g_register) {
@@ -1959,10 +1972,12 @@ static long __video_do_ioctl(struct file *file,
1959 else 1972 else
1960 ret = ops->vidioc_g_register(file, fh, p); 1973 ret = ops->vidioc_g_register(file, fh, p);
1961 } 1974 }
1975#endif
1962 break; 1976 break;
1963 } 1977 }
1964 case VIDIOC_DBG_S_REGISTER: 1978 case VIDIOC_DBG_S_REGISTER:
1965 { 1979 {
1980#ifdef CONFIG_VIDEO_ADV_DEBUG
1966 struct v4l2_dbg_register *p = arg; 1981 struct v4l2_dbg_register *p = arg;
1967 1982
1968 if (ops->vidioc_s_register) { 1983 if (ops->vidioc_s_register) {
@@ -1971,9 +1986,9 @@ static long __video_do_ioctl(struct file *file,
1971 else 1986 else
1972 ret = ops->vidioc_s_register(file, fh, p); 1987 ret = ops->vidioc_s_register(file, fh, p);
1973 } 1988 }
1989#endif
1974 break; 1990 break;
1975 } 1991 }
1976#endif
1977 case VIDIOC_DBG_G_CHIP_IDENT: 1992 case VIDIOC_DBG_G_CHIP_IDENT:
1978 { 1993 {
1979 struct v4l2_dbg_chip_ident *p = arg; 1994 struct v4l2_dbg_chip_ident *p = arg;
diff --git a/include/media/v4l2-dev.h b/include/media/v4l2-dev.h
index 96d22215cc88..d00b9d3511f2 100644
--- a/include/media/v4l2-dev.h
+++ b/include/media/v4l2-dev.h
@@ -128,6 +128,7 @@ struct video_device
128 const struct v4l2_ioctl_ops *ioctl_ops; 128 const struct v4l2_ioctl_ops *ioctl_ops;
129 129
130 /* serialization lock */ 130 /* serialization lock */
131 DECLARE_BITMAP(dont_use_lock, BASE_VIDIOC_PRIVATE);
131 struct mutex *lock; 132 struct mutex *lock;
132}; 133};
133 134
@@ -173,6 +174,16 @@ void video_device_release(struct video_device *vdev);
173 a dubious construction at best. */ 174 a dubious construction at best. */
174void video_device_release_empty(struct video_device *vdev); 175void video_device_release_empty(struct video_device *vdev);
175 176
177/* returns true if cmd is a known V4L2 ioctl */
178bool v4l2_is_known_ioctl(unsigned int cmd);
179
180/* mark that this command shouldn't use core locking */
181static inline void v4l2_dont_use_lock(struct video_device *vdev, unsigned int cmd)
182{
183 if (_IOC_NR(cmd) < BASE_VIDIOC_PRIVATE)
184 set_bit(_IOC_NR(cmd), vdev->dont_use_lock);
185}
186
176/* helper functions to access driver private data. */ 187/* helper functions to access driver private data. */
177static inline void *video_get_drvdata(struct video_device *vdev) 188static inline void *video_get_drvdata(struct video_device *vdev)
178{ 189{