bcm27xx: add support for linux v5.15
[openwrt/staging/chunkeey.git] / target / linux / bcm27xx / patches-5.15 / 950-0171-v4l2-Add-a-Greyworld-AWB-mode.patch
1 From 8b666c067e3a52f960e0e6112451596d8b1c672f Mon Sep 17 00:00:00 2001
2 From: Dave Stevenson <dave.stevenson@raspberrypi.org>
3 Date: Fri, 6 Sep 2019 15:04:51 +0100
4 Subject: [PATCH] v4l2: Add a Greyworld AWB mode.
5
6 Adds a simple greyworld white balance preset, mainly for use
7 with cameras without an IR filter (eg Raspberry Pi NoIR)
8
9 Signed-off-by: Dave Stevenson <dave.stevenson@raspberrypi.org>
10 ---
11 drivers/media/v4l2-core/v4l2-ctrls.c | 5036 ++++++++++++++++++++++++++
12 include/uapi/linux/v4l2-controls.h | 1 +
13 2 files changed, 5037 insertions(+)
14 create mode 100644 drivers/media/v4l2-core/v4l2-ctrls.c
15
16 --- /dev/null
17 +++ b/drivers/media/v4l2-core/v4l2-ctrls.c
18 @@ -0,0 +1,5036 @@
19 +// SPDX-License-Identifier: GPL-2.0-or-later
20 +/*
21 + V4L2 controls framework implementation.
22 +
23 + Copyright (C) 2010 Hans Verkuil <hverkuil@xs4all.nl>
24 +
25 + */
26 +
27 +#define pr_fmt(fmt) "v4l2-ctrls: " fmt
28 +
29 +#include <linux/ctype.h>
30 +#include <linux/export.h>
31 +#include <linux/mm.h>
32 +#include <linux/slab.h>
33 +#include <media/v4l2-ctrls.h>
34 +#include <media/v4l2-dev.h>
35 +#include <media/v4l2-device.h>
36 +#include <media/v4l2-event.h>
37 +#include <media/v4l2-fwnode.h>
38 +#include <media/v4l2-ioctl.h>
39 +
40 +#define dprintk(vdev, fmt, arg...) do { \
41 + if (!WARN_ON(!(vdev)) && ((vdev)->dev_debug & V4L2_DEV_DEBUG_CTRL)) \
42 + printk(KERN_DEBUG pr_fmt("%s: %s: " fmt), \
43 + __func__, video_device_node_name(vdev), ##arg); \
44 +} while (0)
45 +
46 +#define has_op(master, op) \
47 + (master->ops && master->ops->op)
48 +#define call_op(master, op) \
49 + (has_op(master, op) ? master->ops->op(master) : 0)
50 +
51 +static const union v4l2_ctrl_ptr ptr_null;
52 +
53 +/* Internal temporary helper struct, one for each v4l2_ext_control */
54 +struct v4l2_ctrl_helper {
55 + /* Pointer to the control reference of the master control */
56 + struct v4l2_ctrl_ref *mref;
57 + /* The control ref corresponding to the v4l2_ext_control ID field. */
58 + struct v4l2_ctrl_ref *ref;
59 + /* v4l2_ext_control index of the next control belonging to the
60 + same cluster, or 0 if there isn't any. */
61 + u32 next;
62 +};
63 +
64 +/* Small helper function to determine if the autocluster is set to manual
65 + mode. */
66 +static bool is_cur_manual(const struct v4l2_ctrl *master)
67 +{
68 + return master->is_auto && master->cur.val == master->manual_mode_value;
69 +}
70 +
71 +/* Same as above, but this checks the against the new value instead of the
72 + current value. */
73 +static bool is_new_manual(const struct v4l2_ctrl *master)
74 +{
75 + return master->is_auto && master->val == master->manual_mode_value;
76 +}
77 +
78 +/* Returns NULL or a character pointer array containing the menu for
79 + the given control ID. The pointer array ends with a NULL pointer.
80 + An empty string signifies a menu entry that is invalid. This allows
81 + drivers to disable certain options if it is not supported. */
82 +const char * const *v4l2_ctrl_get_menu(u32 id)
83 +{
84 + static const char * const mpeg_audio_sampling_freq[] = {
85 + "44.1 kHz",
86 + "48 kHz",
87 + "32 kHz",
88 + NULL
89 + };
90 + static const char * const mpeg_audio_encoding[] = {
91 + "MPEG-1/2 Layer I",
92 + "MPEG-1/2 Layer II",
93 + "MPEG-1/2 Layer III",
94 + "MPEG-2/4 AAC",
95 + "AC-3",
96 + NULL
97 + };
98 + static const char * const mpeg_audio_l1_bitrate[] = {
99 + "32 kbps",
100 + "64 kbps",
101 + "96 kbps",
102 + "128 kbps",
103 + "160 kbps",
104 + "192 kbps",
105 + "224 kbps",
106 + "256 kbps",
107 + "288 kbps",
108 + "320 kbps",
109 + "352 kbps",
110 + "384 kbps",
111 + "416 kbps",
112 + "448 kbps",
113 + NULL
114 + };
115 + static const char * const mpeg_audio_l2_bitrate[] = {
116 + "32 kbps",
117 + "48 kbps",
118 + "56 kbps",
119 + "64 kbps",
120 + "80 kbps",
121 + "96 kbps",
122 + "112 kbps",
123 + "128 kbps",
124 + "160 kbps",
125 + "192 kbps",
126 + "224 kbps",
127 + "256 kbps",
128 + "320 kbps",
129 + "384 kbps",
130 + NULL
131 + };
132 + static const char * const mpeg_audio_l3_bitrate[] = {
133 + "32 kbps",
134 + "40 kbps",
135 + "48 kbps",
136 + "56 kbps",
137 + "64 kbps",
138 + "80 kbps",
139 + "96 kbps",
140 + "112 kbps",
141 + "128 kbps",
142 + "160 kbps",
143 + "192 kbps",
144 + "224 kbps",
145 + "256 kbps",
146 + "320 kbps",
147 + NULL
148 + };
149 + static const char * const mpeg_audio_ac3_bitrate[] = {
150 + "32 kbps",
151 + "40 kbps",
152 + "48 kbps",
153 + "56 kbps",
154 + "64 kbps",
155 + "80 kbps",
156 + "96 kbps",
157 + "112 kbps",
158 + "128 kbps",
159 + "160 kbps",
160 + "192 kbps",
161 + "224 kbps",
162 + "256 kbps",
163 + "320 kbps",
164 + "384 kbps",
165 + "448 kbps",
166 + "512 kbps",
167 + "576 kbps",
168 + "640 kbps",
169 + NULL
170 + };
171 + static const char * const mpeg_audio_mode[] = {
172 + "Stereo",
173 + "Joint Stereo",
174 + "Dual",
175 + "Mono",
176 + NULL
177 + };
178 + static const char * const mpeg_audio_mode_extension[] = {
179 + "Bound 4",
180 + "Bound 8",
181 + "Bound 12",
182 + "Bound 16",
183 + NULL
184 + };
185 + static const char * const mpeg_audio_emphasis[] = {
186 + "No Emphasis",
187 + "50/15 us",
188 + "CCITT J17",
189 + NULL
190 + };
191 + static const char * const mpeg_audio_crc[] = {
192 + "No CRC",
193 + "16-bit CRC",
194 + NULL
195 + };
196 + static const char * const mpeg_audio_dec_playback[] = {
197 + "Auto",
198 + "Stereo",
199 + "Left",
200 + "Right",
201 + "Mono",
202 + "Swapped Stereo",
203 + NULL
204 + };
205 + static const char * const mpeg_video_encoding[] = {
206 + "MPEG-1",
207 + "MPEG-2",
208 + "MPEG-4 AVC",
209 + NULL
210 + };
211 + static const char * const mpeg_video_aspect[] = {
212 + "1x1",
213 + "4x3",
214 + "16x9",
215 + "2.21x1",
216 + NULL
217 + };
218 + static const char * const mpeg_video_bitrate_mode[] = {
219 + "Variable Bitrate",
220 + "Constant Bitrate",
221 + "Constant Quality",
222 + NULL
223 + };
224 + static const char * const mpeg_stream_type[] = {
225 + "MPEG-2 Program Stream",
226 + "MPEG-2 Transport Stream",
227 + "MPEG-1 System Stream",
228 + "MPEG-2 DVD-compatible Stream",
229 + "MPEG-1 VCD-compatible Stream",
230 + "MPEG-2 SVCD-compatible Stream",
231 + NULL
232 + };
233 + static const char * const mpeg_stream_vbi_fmt[] = {
234 + "No VBI",
235 + "Private Packet, IVTV Format",
236 + NULL
237 + };
238 + static const char * const camera_power_line_frequency[] = {
239 + "Disabled",
240 + "50 Hz",
241 + "60 Hz",
242 + "Auto",
243 + NULL
244 + };
245 + static const char * const camera_exposure_auto[] = {
246 + "Auto Mode",
247 + "Manual Mode",
248 + "Shutter Priority Mode",
249 + "Aperture Priority Mode",
250 + NULL
251 + };
252 + static const char * const camera_exposure_metering[] = {
253 + "Average",
254 + "Center Weighted",
255 + "Spot",
256 + "Matrix",
257 + NULL
258 + };
259 + static const char * const camera_auto_focus_range[] = {
260 + "Auto",
261 + "Normal",
262 + "Macro",
263 + "Infinity",
264 + NULL
265 + };
266 + static const char * const colorfx[] = {
267 + "None",
268 + "Black & White",
269 + "Sepia",
270 + "Negative",
271 + "Emboss",
272 + "Sketch",
273 + "Sky Blue",
274 + "Grass Green",
275 + "Skin Whiten",
276 + "Vivid",
277 + "Aqua",
278 + "Art Freeze",
279 + "Silhouette",
280 + "Solarization",
281 + "Antique",
282 + "Set Cb/Cr",
283 + NULL
284 + };
285 + static const char * const auto_n_preset_white_balance[] = {
286 + "Manual",
287 + "Auto",
288 + "Incandescent",
289 + "Fluorescent",
290 + "Fluorescent H",
291 + "Horizon",
292 + "Daylight",
293 + "Flash",
294 + "Cloudy",
295 + "Shade",
296 + "Greyworld",
297 + NULL,
298 + };
299 + static const char * const camera_iso_sensitivity_auto[] = {
300 + "Manual",
301 + "Auto",
302 + NULL
303 + };
304 + static const char * const scene_mode[] = {
305 + "None",
306 + "Backlight",
307 + "Beach/Snow",
308 + "Candle Light",
309 + "Dusk/Dawn",
310 + "Fall Colors",
311 + "Fireworks",
312 + "Landscape",
313 + "Night",
314 + "Party/Indoor",
315 + "Portrait",
316 + "Sports",
317 + "Sunset",
318 + "Text",
319 + NULL
320 + };
321 + static const char * const tune_emphasis[] = {
322 + "None",
323 + "50 Microseconds",
324 + "75 Microseconds",
325 + NULL,
326 + };
327 + static const char * const header_mode[] = {
328 + "Separate Buffer",
329 + "Joined With 1st Frame",
330 + NULL,
331 + };
332 + static const char * const multi_slice[] = {
333 + "Single",
334 + "Max Macroblocks",
335 + "Max Bytes",
336 + NULL,
337 + };
338 + static const char * const entropy_mode[] = {
339 + "CAVLC",
340 + "CABAC",
341 + NULL,
342 + };
343 + static const char * const mpeg_h264_level[] = {
344 + "1",
345 + "1b",
346 + "1.1",
347 + "1.2",
348 + "1.3",
349 + "2",
350 + "2.1",
351 + "2.2",
352 + "3",
353 + "3.1",
354 + "3.2",
355 + "4",
356 + "4.1",
357 + "4.2",
358 + "5",
359 + "5.1",
360 + "5.2",
361 + "6.0",
362 + "6.1",
363 + "6.2",
364 + NULL,
365 + };
366 + static const char * const h264_loop_filter[] = {
367 + "Enabled",
368 + "Disabled",
369 + "Disabled at Slice Boundary",
370 + NULL,
371 + };
372 + static const char * const h264_profile[] = {
373 + "Baseline",
374 + "Constrained Baseline",
375 + "Main",
376 + "Extended",
377 + "High",
378 + "High 10",
379 + "High 422",
380 + "High 444 Predictive",
381 + "High 10 Intra",
382 + "High 422 Intra",
383 + "High 444 Intra",
384 + "CAVLC 444 Intra",
385 + "Scalable Baseline",
386 + "Scalable High",
387 + "Scalable High Intra",
388 + "Stereo High",
389 + "Multiview High",
390 + "Constrained High",
391 + NULL,
392 + };
393 + static const char * const vui_sar_idc[] = {
394 + "Unspecified",
395 + "1:1",
396 + "12:11",
397 + "10:11",
398 + "16:11",
399 + "40:33",
400 + "24:11",
401 + "20:11",
402 + "32:11",
403 + "80:33",
404 + "18:11",
405 + "15:11",
406 + "64:33",
407 + "160:99",
408 + "4:3",
409 + "3:2",
410 + "2:1",
411 + "Extended SAR",
412 + NULL,
413 + };
414 + static const char * const h264_fp_arrangement_type[] = {
415 + "Checkerboard",
416 + "Column",
417 + "Row",
418 + "Side by Side",
419 + "Top Bottom",
420 + "Temporal",
421 + NULL,
422 + };
423 + static const char * const h264_fmo_map_type[] = {
424 + "Interleaved Slices",
425 + "Scattered Slices",
426 + "Foreground with Leftover",
427 + "Box Out",
428 + "Raster Scan",
429 + "Wipe Scan",
430 + "Explicit",
431 + NULL,
432 + };
433 + static const char * const h264_decode_mode[] = {
434 + "Slice-Based",
435 + "Frame-Based",
436 + NULL,
437 + };
438 + static const char * const h264_start_code[] = {
439 + "No Start Code",
440 + "Annex B Start Code",
441 + NULL,
442 + };
443 + static const char * const h264_hierarchical_coding_type[] = {
444 + "Hier Coding B",
445 + "Hier Coding P",
446 + NULL,
447 + };
448 + static const char * const mpeg_mpeg2_level[] = {
449 + "Low",
450 + "Main",
451 + "High 1440",
452 + "High",
453 + NULL,
454 + };
455 + static const char * const mpeg2_profile[] = {
456 + "Simple",
457 + "Main",
458 + "SNR Scalable",
459 + "Spatially Scalable",
460 + "High",
461 + NULL,
462 + };
463 + static const char * const mpeg_mpeg4_level[] = {
464 + "0",
465 + "0b",
466 + "1",
467 + "2",
468 + "3",
469 + "3b",
470 + "4",
471 + "5",
472 + NULL,
473 + };
474 + static const char * const mpeg4_profile[] = {
475 + "Simple",
476 + "Advanced Simple",
477 + "Core",
478 + "Simple Scalable",
479 + "Advanced Coding Efficiency",
480 + NULL,
481 + };
482 +
483 + static const char * const vpx_golden_frame_sel[] = {
484 + "Use Previous Frame",
485 + "Use Previous Specific Frame",
486 + NULL,
487 + };
488 + static const char * const vp8_profile[] = {
489 + "0",
490 + "1",
491 + "2",
492 + "3",
493 + NULL,
494 + };
495 + static const char * const vp9_profile[] = {
496 + "0",
497 + "1",
498 + "2",
499 + "3",
500 + NULL,
501 + };
502 + static const char * const vp9_level[] = {
503 + "1",
504 + "1.1",
505 + "2",
506 + "2.1",
507 + "3",
508 + "3.1",
509 + "4",
510 + "4.1",
511 + "5",
512 + "5.1",
513 + "5.2",
514 + "6",
515 + "6.1",
516 + "6.2",
517 + NULL,
518 + };
519 +
520 + static const char * const flash_led_mode[] = {
521 + "Off",
522 + "Flash",
523 + "Torch",
524 + NULL,
525 + };
526 + static const char * const flash_strobe_source[] = {
527 + "Software",
528 + "External",
529 + NULL,
530 + };
531 +
532 + static const char * const jpeg_chroma_subsampling[] = {
533 + "4:4:4",
534 + "4:2:2",
535 + "4:2:0",
536 + "4:1:1",
537 + "4:1:0",
538 + "Gray",
539 + NULL,
540 + };
541 + static const char * const dv_tx_mode[] = {
542 + "DVI-D",
543 + "HDMI",
544 + NULL,
545 + };
546 + static const char * const dv_rgb_range[] = {
547 + "Automatic",
548 + "RGB Limited Range (16-235)",
549 + "RGB Full Range (0-255)",
550 + NULL,
551 + };
552 + static const char * const dv_it_content_type[] = {
553 + "Graphics",
554 + "Photo",
555 + "Cinema",
556 + "Game",
557 + "No IT Content",
558 + NULL,
559 + };
560 + static const char * const detect_md_mode[] = {
561 + "Disabled",
562 + "Global",
563 + "Threshold Grid",
564 + "Region Grid",
565 + NULL,
566 + };
567 +
568 + static const char * const hevc_profile[] = {
569 + "Main",
570 + "Main Still Picture",
571 + "Main 10",
572 + NULL,
573 + };
574 + static const char * const hevc_level[] = {
575 + "1",
576 + "2",
577 + "2.1",
578 + "3",
579 + "3.1",
580 + "4",
581 + "4.1",
582 + "5",
583 + "5.1",
584 + "5.2",
585 + "6",
586 + "6.1",
587 + "6.2",
588 + NULL,
589 + };
590 + static const char * const hevc_hierarchial_coding_type[] = {
591 + "B",
592 + "P",
593 + NULL,
594 + };
595 + static const char * const hevc_refresh_type[] = {
596 + "None",
597 + "CRA",
598 + "IDR",
599 + NULL,
600 + };
601 + static const char * const hevc_size_of_length_field[] = {
602 + "0",
603 + "1",
604 + "2",
605 + "4",
606 + NULL,
607 + };
608 + static const char * const hevc_tier[] = {
609 + "Main",
610 + "High",
611 + NULL,
612 + };
613 + static const char * const hevc_loop_filter_mode[] = {
614 + "Disabled",
615 + "Enabled",
616 + "Disabled at slice boundary",
617 + "NULL",
618 + };
619 + static const char * const hevc_decode_mode[] = {
620 + "Slice-Based",
621 + "Frame-Based",
622 + NULL,
623 + };
624 + static const char * const hevc_start_code[] = {
625 + "No Start Code",
626 + "Annex B Start Code",
627 + NULL,
628 + };
629 + static const char * const camera_orientation[] = {
630 + "Front",
631 + "Back",
632 + "External",
633 + NULL,
634 + };
635 + static const char * const mpeg_video_frame_skip[] = {
636 + "Disabled",
637 + "Level Limit",
638 + "VBV/CPB Limit",
639 + NULL,
640 + };
641 +
642 + switch (id) {
643 + case V4L2_CID_MPEG_AUDIO_SAMPLING_FREQ:
644 + return mpeg_audio_sampling_freq;
645 + case V4L2_CID_MPEG_AUDIO_ENCODING:
646 + return mpeg_audio_encoding;
647 + case V4L2_CID_MPEG_AUDIO_L1_BITRATE:
648 + return mpeg_audio_l1_bitrate;
649 + case V4L2_CID_MPEG_AUDIO_L2_BITRATE:
650 + return mpeg_audio_l2_bitrate;
651 + case V4L2_CID_MPEG_AUDIO_L3_BITRATE:
652 + return mpeg_audio_l3_bitrate;
653 + case V4L2_CID_MPEG_AUDIO_AC3_BITRATE:
654 + return mpeg_audio_ac3_bitrate;
655 + case V4L2_CID_MPEG_AUDIO_MODE:
656 + return mpeg_audio_mode;
657 + case V4L2_CID_MPEG_AUDIO_MODE_EXTENSION:
658 + return mpeg_audio_mode_extension;
659 + case V4L2_CID_MPEG_AUDIO_EMPHASIS:
660 + return mpeg_audio_emphasis;
661 + case V4L2_CID_MPEG_AUDIO_CRC:
662 + return mpeg_audio_crc;
663 + case V4L2_CID_MPEG_AUDIO_DEC_PLAYBACK:
664 + case V4L2_CID_MPEG_AUDIO_DEC_MULTILINGUAL_PLAYBACK:
665 + return mpeg_audio_dec_playback;
666 + case V4L2_CID_MPEG_VIDEO_ENCODING:
667 + return mpeg_video_encoding;
668 + case V4L2_CID_MPEG_VIDEO_ASPECT:
669 + return mpeg_video_aspect;
670 + case V4L2_CID_MPEG_VIDEO_BITRATE_MODE:
671 + return mpeg_video_bitrate_mode;
672 + case V4L2_CID_MPEG_STREAM_TYPE:
673 + return mpeg_stream_type;
674 + case V4L2_CID_MPEG_STREAM_VBI_FMT:
675 + return mpeg_stream_vbi_fmt;
676 + case V4L2_CID_POWER_LINE_FREQUENCY:
677 + return camera_power_line_frequency;
678 + case V4L2_CID_EXPOSURE_AUTO:
679 + return camera_exposure_auto;
680 + case V4L2_CID_EXPOSURE_METERING:
681 + return camera_exposure_metering;
682 + case V4L2_CID_AUTO_FOCUS_RANGE:
683 + return camera_auto_focus_range;
684 + case V4L2_CID_COLORFX:
685 + return colorfx;
686 + case V4L2_CID_AUTO_N_PRESET_WHITE_BALANCE:
687 + return auto_n_preset_white_balance;
688 + case V4L2_CID_ISO_SENSITIVITY_AUTO:
689 + return camera_iso_sensitivity_auto;
690 + case V4L2_CID_SCENE_MODE:
691 + return scene_mode;
692 + case V4L2_CID_TUNE_PREEMPHASIS:
693 + return tune_emphasis;
694 + case V4L2_CID_TUNE_DEEMPHASIS:
695 + return tune_emphasis;
696 + case V4L2_CID_FLASH_LED_MODE:
697 + return flash_led_mode;
698 + case V4L2_CID_FLASH_STROBE_SOURCE:
699 + return flash_strobe_source;
700 + case V4L2_CID_MPEG_VIDEO_HEADER_MODE:
701 + return header_mode;
702 + case V4L2_CID_MPEG_VIDEO_FRAME_SKIP_MODE:
703 + return mpeg_video_frame_skip;
704 + case V4L2_CID_MPEG_VIDEO_MULTI_SLICE_MODE:
705 + return multi_slice;
706 + case V4L2_CID_MPEG_VIDEO_H264_ENTROPY_MODE:
707 + return entropy_mode;
708 + case V4L2_CID_MPEG_VIDEO_H264_LEVEL:
709 + return mpeg_h264_level;
710 + case V4L2_CID_MPEG_VIDEO_H264_LOOP_FILTER_MODE:
711 + return h264_loop_filter;
712 + case V4L2_CID_MPEG_VIDEO_H264_PROFILE:
713 + return h264_profile;
714 + case V4L2_CID_MPEG_VIDEO_H264_VUI_SAR_IDC:
715 + return vui_sar_idc;
716 + case V4L2_CID_MPEG_VIDEO_H264_SEI_FP_ARRANGEMENT_TYPE:
717 + return h264_fp_arrangement_type;
718 + case V4L2_CID_MPEG_VIDEO_H264_FMO_MAP_TYPE:
719 + return h264_fmo_map_type;
720 + case V4L2_CID_STATELESS_H264_DECODE_MODE:
721 + return h264_decode_mode;
722 + case V4L2_CID_STATELESS_H264_START_CODE:
723 + return h264_start_code;
724 + case V4L2_CID_MPEG_VIDEO_H264_HIERARCHICAL_CODING_TYPE:
725 + return h264_hierarchical_coding_type;
726 + case V4L2_CID_MPEG_VIDEO_MPEG2_LEVEL:
727 + return mpeg_mpeg2_level;
728 + case V4L2_CID_MPEG_VIDEO_MPEG2_PROFILE:
729 + return mpeg2_profile;
730 + case V4L2_CID_MPEG_VIDEO_MPEG4_LEVEL:
731 + return mpeg_mpeg4_level;
732 + case V4L2_CID_MPEG_VIDEO_MPEG4_PROFILE:
733 + return mpeg4_profile;
734 + case V4L2_CID_MPEG_VIDEO_VPX_GOLDEN_FRAME_SEL:
735 + return vpx_golden_frame_sel;
736 + case V4L2_CID_MPEG_VIDEO_VP8_PROFILE:
737 + return vp8_profile;
738 + case V4L2_CID_MPEG_VIDEO_VP9_PROFILE:
739 + return vp9_profile;
740 + case V4L2_CID_MPEG_VIDEO_VP9_LEVEL:
741 + return vp9_level;
742 + case V4L2_CID_JPEG_CHROMA_SUBSAMPLING:
743 + return jpeg_chroma_subsampling;
744 + case V4L2_CID_DV_TX_MODE:
745 + return dv_tx_mode;
746 + case V4L2_CID_DV_TX_RGB_RANGE:
747 + case V4L2_CID_DV_RX_RGB_RANGE:
748 + return dv_rgb_range;
749 + case V4L2_CID_DV_TX_IT_CONTENT_TYPE:
750 + case V4L2_CID_DV_RX_IT_CONTENT_TYPE:
751 + return dv_it_content_type;
752 + case V4L2_CID_DETECT_MD_MODE:
753 + return detect_md_mode;
754 + case V4L2_CID_MPEG_VIDEO_HEVC_PROFILE:
755 + return hevc_profile;
756 + case V4L2_CID_MPEG_VIDEO_HEVC_LEVEL:
757 + return hevc_level;
758 + case V4L2_CID_MPEG_VIDEO_HEVC_HIER_CODING_TYPE:
759 + return hevc_hierarchial_coding_type;
760 + case V4L2_CID_MPEG_VIDEO_HEVC_REFRESH_TYPE:
761 + return hevc_refresh_type;
762 + case V4L2_CID_MPEG_VIDEO_HEVC_SIZE_OF_LENGTH_FIELD:
763 + return hevc_size_of_length_field;
764 + case V4L2_CID_MPEG_VIDEO_HEVC_TIER:
765 + return hevc_tier;
766 + case V4L2_CID_MPEG_VIDEO_HEVC_LOOP_FILTER_MODE:
767 + return hevc_loop_filter_mode;
768 + case V4L2_CID_MPEG_VIDEO_HEVC_DECODE_MODE:
769 + return hevc_decode_mode;
770 + case V4L2_CID_MPEG_VIDEO_HEVC_START_CODE:
771 + return hevc_start_code;
772 + case V4L2_CID_CAMERA_ORIENTATION:
773 + return camera_orientation;
774 + default:
775 + return NULL;
776 + }
777 +}
778 +EXPORT_SYMBOL(v4l2_ctrl_get_menu);
779 +
780 +#define __v4l2_qmenu_int_len(arr, len) ({ *(len) = ARRAY_SIZE(arr); arr; })
781 +/*
782 + * Returns NULL or an s64 type array containing the menu for given
783 + * control ID. The total number of the menu items is returned in @len.
784 + */
785 +const s64 *v4l2_ctrl_get_int_menu(u32 id, u32 *len)
786 +{
787 + static const s64 qmenu_int_vpx_num_partitions[] = {
788 + 1, 2, 4, 8,
789 + };
790 +
791 + static const s64 qmenu_int_vpx_num_ref_frames[] = {
792 + 1, 2, 3,
793 + };
794 +
795 + switch (id) {
796 + case V4L2_CID_MPEG_VIDEO_VPX_NUM_PARTITIONS:
797 + return __v4l2_qmenu_int_len(qmenu_int_vpx_num_partitions, len);
798 + case V4L2_CID_MPEG_VIDEO_VPX_NUM_REF_FRAMES:
799 + return __v4l2_qmenu_int_len(qmenu_int_vpx_num_ref_frames, len);
800 + default:
801 + *len = 0;
802 + return NULL;
803 + }
804 +}
805 +EXPORT_SYMBOL(v4l2_ctrl_get_int_menu);
806 +
807 +/* Return the control name. */
808 +const char *v4l2_ctrl_get_name(u32 id)
809 +{
810 + switch (id) {
811 + /* USER controls */
812 + /* Keep the order of the 'case's the same as in v4l2-controls.h! */
813 + case V4L2_CID_USER_CLASS: return "User Controls";
814 + case V4L2_CID_BRIGHTNESS: return "Brightness";
815 + case V4L2_CID_CONTRAST: return "Contrast";
816 + case V4L2_CID_SATURATION: return "Saturation";
817 + case V4L2_CID_HUE: return "Hue";
818 + case V4L2_CID_AUDIO_VOLUME: return "Volume";
819 + case V4L2_CID_AUDIO_BALANCE: return "Balance";
820 + case V4L2_CID_AUDIO_BASS: return "Bass";
821 + case V4L2_CID_AUDIO_TREBLE: return "Treble";
822 + case V4L2_CID_AUDIO_MUTE: return "Mute";
823 + case V4L2_CID_AUDIO_LOUDNESS: return "Loudness";
824 + case V4L2_CID_BLACK_LEVEL: return "Black Level";
825 + case V4L2_CID_AUTO_WHITE_BALANCE: return "White Balance, Automatic";
826 + case V4L2_CID_DO_WHITE_BALANCE: return "Do White Balance";
827 + case V4L2_CID_RED_BALANCE: return "Red Balance";
828 + case V4L2_CID_BLUE_BALANCE: return "Blue Balance";
829 + case V4L2_CID_GAMMA: return "Gamma";
830 + case V4L2_CID_EXPOSURE: return "Exposure";
831 + case V4L2_CID_AUTOGAIN: return "Gain, Automatic";
832 + case V4L2_CID_GAIN: return "Gain";
833 + case V4L2_CID_HFLIP: return "Horizontal Flip";
834 + case V4L2_CID_VFLIP: return "Vertical Flip";
835 + case V4L2_CID_POWER_LINE_FREQUENCY: return "Power Line Frequency";
836 + case V4L2_CID_HUE_AUTO: return "Hue, Automatic";
837 + case V4L2_CID_WHITE_BALANCE_TEMPERATURE: return "White Balance Temperature";
838 + case V4L2_CID_SHARPNESS: return "Sharpness";
839 + case V4L2_CID_BACKLIGHT_COMPENSATION: return "Backlight Compensation";
840 + case V4L2_CID_CHROMA_AGC: return "Chroma AGC";
841 + case V4L2_CID_COLOR_KILLER: return "Color Killer";
842 + case V4L2_CID_COLORFX: return "Color Effects";
843 + case V4L2_CID_AUTOBRIGHTNESS: return "Brightness, Automatic";
844 + case V4L2_CID_BAND_STOP_FILTER: return "Band-Stop Filter";
845 + case V4L2_CID_ROTATE: return "Rotate";
846 + case V4L2_CID_BG_COLOR: return "Background Color";
847 + case V4L2_CID_CHROMA_GAIN: return "Chroma Gain";
848 + case V4L2_CID_ILLUMINATORS_1: return "Illuminator 1";
849 + case V4L2_CID_ILLUMINATORS_2: return "Illuminator 2";
850 + case V4L2_CID_MIN_BUFFERS_FOR_CAPTURE: return "Min Number of Capture Buffers";
851 + case V4L2_CID_MIN_BUFFERS_FOR_OUTPUT: return "Min Number of Output Buffers";
852 + case V4L2_CID_ALPHA_COMPONENT: return "Alpha Component";
853 + case V4L2_CID_COLORFX_CBCR: return "Color Effects, CbCr";
854 +
855 + /* Codec controls */
856 + /* The MPEG controls are applicable to all codec controls
857 + * and the 'MPEG' part of the define is historical */
858 + /* Keep the order of the 'case's the same as in videodev2.h! */
859 + case V4L2_CID_CODEC_CLASS: return "Codec Controls";
860 + case V4L2_CID_MPEG_STREAM_TYPE: return "Stream Type";
861 + case V4L2_CID_MPEG_STREAM_PID_PMT: return "Stream PMT Program ID";
862 + case V4L2_CID_MPEG_STREAM_PID_AUDIO: return "Stream Audio Program ID";
863 + case V4L2_CID_MPEG_STREAM_PID_VIDEO: return "Stream Video Program ID";
864 + case V4L2_CID_MPEG_STREAM_PID_PCR: return "Stream PCR Program ID";
865 + case V4L2_CID_MPEG_STREAM_PES_ID_AUDIO: return "Stream PES Audio ID";
866 + case V4L2_CID_MPEG_STREAM_PES_ID_VIDEO: return "Stream PES Video ID";
867 + case V4L2_CID_MPEG_STREAM_VBI_FMT: return "Stream VBI Format";
868 + case V4L2_CID_MPEG_AUDIO_SAMPLING_FREQ: return "Audio Sampling Frequency";
869 + case V4L2_CID_MPEG_AUDIO_ENCODING: return "Audio Encoding";
870 + case V4L2_CID_MPEG_AUDIO_L1_BITRATE: return "Audio Layer I Bitrate";
871 + case V4L2_CID_MPEG_AUDIO_L2_BITRATE: return "Audio Layer II Bitrate";
872 + case V4L2_CID_MPEG_AUDIO_L3_BITRATE: return "Audio Layer III Bitrate";
873 + case V4L2_CID_MPEG_AUDIO_MODE: return "Audio Stereo Mode";
874 + case V4L2_CID_MPEG_AUDIO_MODE_EXTENSION: return "Audio Stereo Mode Extension";
875 + case V4L2_CID_MPEG_AUDIO_EMPHASIS: return "Audio Emphasis";
876 + case V4L2_CID_MPEG_AUDIO_CRC: return "Audio CRC";
877 + case V4L2_CID_MPEG_AUDIO_MUTE: return "Audio Mute";
878 + case V4L2_CID_MPEG_AUDIO_AAC_BITRATE: return "Audio AAC Bitrate";
879 + case V4L2_CID_MPEG_AUDIO_AC3_BITRATE: return "Audio AC-3 Bitrate";
880 + case V4L2_CID_MPEG_AUDIO_DEC_PLAYBACK: return "Audio Playback";
881 + case V4L2_CID_MPEG_AUDIO_DEC_MULTILINGUAL_PLAYBACK: return "Audio Multilingual Playback";
882 + case V4L2_CID_MPEG_VIDEO_ENCODING: return "Video Encoding";
883 + case V4L2_CID_MPEG_VIDEO_ASPECT: return "Video Aspect";
884 + case V4L2_CID_MPEG_VIDEO_B_FRAMES: return "Video B Frames";
885 + case V4L2_CID_MPEG_VIDEO_GOP_SIZE: return "Video GOP Size";
886 + case V4L2_CID_MPEG_VIDEO_GOP_CLOSURE: return "Video GOP Closure";
887 + case V4L2_CID_MPEG_VIDEO_PULLDOWN: return "Video Pulldown";
888 + case V4L2_CID_MPEG_VIDEO_BITRATE_MODE: return "Video Bitrate Mode";
889 + case V4L2_CID_MPEG_VIDEO_CONSTANT_QUALITY: return "Constant Quality";
890 + case V4L2_CID_MPEG_VIDEO_BITRATE: return "Video Bitrate";
891 + case V4L2_CID_MPEG_VIDEO_BITRATE_PEAK: return "Video Peak Bitrate";
892 + case V4L2_CID_MPEG_VIDEO_TEMPORAL_DECIMATION: return "Video Temporal Decimation";
893 + case V4L2_CID_MPEG_VIDEO_MUTE: return "Video Mute";
894 + case V4L2_CID_MPEG_VIDEO_MUTE_YUV: return "Video Mute YUV";
895 + case V4L2_CID_MPEG_VIDEO_DECODER_SLICE_INTERFACE: return "Decoder Slice Interface";
896 + case V4L2_CID_MPEG_VIDEO_DECODER_MPEG4_DEBLOCK_FILTER: return "MPEG4 Loop Filter Enable";
897 + case V4L2_CID_MPEG_VIDEO_CYCLIC_INTRA_REFRESH_MB: return "Number of Intra Refresh MBs";
898 + case V4L2_CID_MPEG_VIDEO_FRAME_RC_ENABLE: return "Frame Level Rate Control Enable";
899 + case V4L2_CID_MPEG_VIDEO_MB_RC_ENABLE: return "H264 MB Level Rate Control";
900 + case V4L2_CID_MPEG_VIDEO_HEADER_MODE: return "Sequence Header Mode";
901 + case V4L2_CID_MPEG_VIDEO_MAX_REF_PIC: return "Max Number of Reference Pics";
902 + case V4L2_CID_MPEG_VIDEO_FRAME_SKIP_MODE: return "Frame Skip Mode";
903 + case V4L2_CID_MPEG_VIDEO_DEC_DISPLAY_DELAY: return "Display Delay";
904 + case V4L2_CID_MPEG_VIDEO_DEC_DISPLAY_DELAY_ENABLE: return "Display Delay Enable";
905 + case V4L2_CID_MPEG_VIDEO_AU_DELIMITER: return "Generate Access Unit Delimiters";
906 + case V4L2_CID_MPEG_VIDEO_H263_I_FRAME_QP: return "H263 I-Frame QP Value";
907 + case V4L2_CID_MPEG_VIDEO_H263_P_FRAME_QP: return "H263 P-Frame QP Value";
908 + case V4L2_CID_MPEG_VIDEO_H263_B_FRAME_QP: return "H263 B-Frame QP Value";
909 + case V4L2_CID_MPEG_VIDEO_H263_MIN_QP: return "H263 Minimum QP Value";
910 + case V4L2_CID_MPEG_VIDEO_H263_MAX_QP: return "H263 Maximum QP Value";
911 + case V4L2_CID_MPEG_VIDEO_H264_I_FRAME_QP: return "H264 I-Frame QP Value";
912 + case V4L2_CID_MPEG_VIDEO_H264_P_FRAME_QP: return "H264 P-Frame QP Value";
913 + case V4L2_CID_MPEG_VIDEO_H264_B_FRAME_QP: return "H264 B-Frame QP Value";
914 + case V4L2_CID_MPEG_VIDEO_H264_MAX_QP: return "H264 Maximum QP Value";
915 + case V4L2_CID_MPEG_VIDEO_H264_MIN_QP: return "H264 Minimum QP Value";
916 + case V4L2_CID_MPEG_VIDEO_H264_8X8_TRANSFORM: return "H264 8x8 Transform Enable";
917 + case V4L2_CID_MPEG_VIDEO_H264_CPB_SIZE: return "H264 CPB Buffer Size";
918 + case V4L2_CID_MPEG_VIDEO_H264_ENTROPY_MODE: return "H264 Entropy Mode";
919 + case V4L2_CID_MPEG_VIDEO_H264_I_PERIOD: return "H264 I-Frame Period";
920 + case V4L2_CID_MPEG_VIDEO_H264_LEVEL: return "H264 Level";
921 + case V4L2_CID_MPEG_VIDEO_H264_LOOP_FILTER_ALPHA: return "H264 Loop Filter Alpha Offset";
922 + case V4L2_CID_MPEG_VIDEO_H264_LOOP_FILTER_BETA: return "H264 Loop Filter Beta Offset";
923 + case V4L2_CID_MPEG_VIDEO_H264_LOOP_FILTER_MODE: return "H264 Loop Filter Mode";
924 + case V4L2_CID_MPEG_VIDEO_H264_PROFILE: return "H264 Profile";
925 + case V4L2_CID_MPEG_VIDEO_H264_VUI_EXT_SAR_HEIGHT: return "Vertical Size of SAR";
926 + case V4L2_CID_MPEG_VIDEO_H264_VUI_EXT_SAR_WIDTH: return "Horizontal Size of SAR";
927 + case V4L2_CID_MPEG_VIDEO_H264_VUI_SAR_ENABLE: return "Aspect Ratio VUI Enable";
928 + case V4L2_CID_MPEG_VIDEO_H264_VUI_SAR_IDC: return "VUI Aspect Ratio IDC";
929 + case V4L2_CID_MPEG_VIDEO_H264_SEI_FRAME_PACKING: return "H264 Enable Frame Packing SEI";
930 + case V4L2_CID_MPEG_VIDEO_H264_SEI_FP_CURRENT_FRAME_0: return "H264 Set Curr. Frame as Frame0";
931 + case V4L2_CID_MPEG_VIDEO_H264_SEI_FP_ARRANGEMENT_TYPE: return "H264 FP Arrangement Type";
932 + case V4L2_CID_MPEG_VIDEO_H264_FMO: return "H264 Flexible MB Ordering";
933 + case V4L2_CID_MPEG_VIDEO_H264_FMO_MAP_TYPE: return "H264 Map Type for FMO";
934 + case V4L2_CID_MPEG_VIDEO_H264_FMO_SLICE_GROUP: return "H264 FMO Number of Slice Groups";
935 + case V4L2_CID_MPEG_VIDEO_H264_FMO_CHANGE_DIRECTION: return "H264 FMO Direction of Change";
936 + case V4L2_CID_MPEG_VIDEO_H264_FMO_CHANGE_RATE: return "H264 FMO Size of 1st Slice Grp";
937 + case V4L2_CID_MPEG_VIDEO_H264_FMO_RUN_LENGTH: return "H264 FMO No. of Consecutive MBs";
938 + case V4L2_CID_MPEG_VIDEO_H264_ASO: return "H264 Arbitrary Slice Ordering";
939 + case V4L2_CID_MPEG_VIDEO_H264_ASO_SLICE_ORDER: return "H264 ASO Slice Order";
940 + case V4L2_CID_MPEG_VIDEO_H264_HIERARCHICAL_CODING: return "Enable H264 Hierarchical Coding";
941 + case V4L2_CID_MPEG_VIDEO_H264_HIERARCHICAL_CODING_TYPE: return "H264 Hierarchical Coding Type";
942 + case V4L2_CID_MPEG_VIDEO_H264_HIERARCHICAL_CODING_LAYER:return "H264 Number of HC Layers";
943 + case V4L2_CID_MPEG_VIDEO_H264_HIERARCHICAL_CODING_LAYER_QP:
944 + return "H264 Set QP Value for HC Layers";
945 + case V4L2_CID_MPEG_VIDEO_H264_CONSTRAINED_INTRA_PREDICTION:
946 + return "H264 Constrained Intra Pred";
947 + case V4L2_CID_MPEG_VIDEO_H264_CHROMA_QP_INDEX_OFFSET: return "H264 Chroma QP Index Offset";
948 + case V4L2_CID_MPEG_VIDEO_H264_I_FRAME_MIN_QP: return "H264 I-Frame Minimum QP Value";
949 + case V4L2_CID_MPEG_VIDEO_H264_I_FRAME_MAX_QP: return "H264 I-Frame Maximum QP Value";
950 + case V4L2_CID_MPEG_VIDEO_H264_P_FRAME_MIN_QP: return "H264 P-Frame Minimum QP Value";
951 + case V4L2_CID_MPEG_VIDEO_H264_P_FRAME_MAX_QP: return "H264 P-Frame Maximum QP Value";
952 + case V4L2_CID_MPEG_VIDEO_H264_B_FRAME_MIN_QP: return "H264 B-Frame Minimum QP Value";
953 + case V4L2_CID_MPEG_VIDEO_H264_B_FRAME_MAX_QP: return "H264 B-Frame Maximum QP Value";
954 + case V4L2_CID_MPEG_VIDEO_H264_HIER_CODING_L0_BR: return "H264 Hierarchical Lay 0 Bitrate";
955 + case V4L2_CID_MPEG_VIDEO_H264_HIER_CODING_L1_BR: return "H264 Hierarchical Lay 1 Bitrate";
956 + case V4L2_CID_MPEG_VIDEO_H264_HIER_CODING_L2_BR: return "H264 Hierarchical Lay 2 Bitrate";
957 + case V4L2_CID_MPEG_VIDEO_H264_HIER_CODING_L3_BR: return "H264 Hierarchical Lay 3 Bitrate";
958 + case V4L2_CID_MPEG_VIDEO_H264_HIER_CODING_L4_BR: return "H264 Hierarchical Lay 4 Bitrate";
959 + case V4L2_CID_MPEG_VIDEO_H264_HIER_CODING_L5_BR: return "H264 Hierarchical Lay 5 Bitrate";
960 + case V4L2_CID_MPEG_VIDEO_H264_HIER_CODING_L6_BR: return "H264 Hierarchical Lay 6 Bitrate";
961 + case V4L2_CID_MPEG_VIDEO_MPEG2_LEVEL: return "MPEG2 Level";
962 + case V4L2_CID_MPEG_VIDEO_MPEG2_PROFILE: return "MPEG2 Profile";
963 + case V4L2_CID_MPEG_VIDEO_MPEG4_I_FRAME_QP: return "MPEG4 I-Frame QP Value";
964 + case V4L2_CID_MPEG_VIDEO_MPEG4_P_FRAME_QP: return "MPEG4 P-Frame QP Value";
965 + case V4L2_CID_MPEG_VIDEO_MPEG4_B_FRAME_QP: return "MPEG4 B-Frame QP Value";
966 + case V4L2_CID_MPEG_VIDEO_MPEG4_MIN_QP: return "MPEG4 Minimum QP Value";
967 + case V4L2_CID_MPEG_VIDEO_MPEG4_MAX_QP: return "MPEG4 Maximum QP Value";
968 + case V4L2_CID_MPEG_VIDEO_MPEG4_LEVEL: return "MPEG4 Level";
969 + case V4L2_CID_MPEG_VIDEO_MPEG4_PROFILE: return "MPEG4 Profile";
970 + case V4L2_CID_MPEG_VIDEO_MPEG4_QPEL: return "Quarter Pixel Search Enable";
971 + case V4L2_CID_MPEG_VIDEO_MULTI_SLICE_MAX_BYTES: return "Maximum Bytes in a Slice";
972 + case V4L2_CID_MPEG_VIDEO_MULTI_SLICE_MAX_MB: return "Number of MBs in a Slice";
973 + case V4L2_CID_MPEG_VIDEO_MULTI_SLICE_MODE: return "Slice Partitioning Method";
974 + case V4L2_CID_MPEG_VIDEO_VBV_SIZE: return "VBV Buffer Size";
975 + case V4L2_CID_MPEG_VIDEO_DEC_PTS: return "Video Decoder PTS";
976 + case V4L2_CID_MPEG_VIDEO_DEC_FRAME: return "Video Decoder Frame Count";
977 + case V4L2_CID_MPEG_VIDEO_DEC_CONCEAL_COLOR: return "Video Decoder Conceal Color";
978 + case V4L2_CID_MPEG_VIDEO_VBV_DELAY: return "Initial Delay for VBV Control";
979 + case V4L2_CID_MPEG_VIDEO_MV_H_SEARCH_RANGE: return "Horizontal MV Search Range";
980 + case V4L2_CID_MPEG_VIDEO_MV_V_SEARCH_RANGE: return "Vertical MV Search Range";
981 + case V4L2_CID_MPEG_VIDEO_REPEAT_SEQ_HEADER: return "Repeat Sequence Header";
982 + case V4L2_CID_MPEG_VIDEO_FORCE_KEY_FRAME: return "Force Key Frame";
983 + case V4L2_CID_MPEG_VIDEO_BASELAYER_PRIORITY_ID: return "Base Layer Priority ID";
984 + case V4L2_CID_MPEG_VIDEO_LTR_COUNT: return "LTR Count";
985 + case V4L2_CID_MPEG_VIDEO_FRAME_LTR_INDEX: return "Frame LTR Index";
986 + case V4L2_CID_MPEG_VIDEO_USE_LTR_FRAMES: return "Use LTR Frames";
987 + case V4L2_CID_MPEG_VIDEO_MPEG2_SLICE_PARAMS: return "MPEG-2 Slice Parameters";
988 + case V4L2_CID_MPEG_VIDEO_MPEG2_QUANTIZATION: return "MPEG-2 Quantization Matrices";
989 + case V4L2_CID_FWHT_I_FRAME_QP: return "FWHT I-Frame QP Value";
990 + case V4L2_CID_FWHT_P_FRAME_QP: return "FWHT P-Frame QP Value";
991 +
992 + /* VPX controls */
993 + case V4L2_CID_MPEG_VIDEO_VPX_NUM_PARTITIONS: return "VPX Number of Partitions";
994 + case V4L2_CID_MPEG_VIDEO_VPX_IMD_DISABLE_4X4: return "VPX Intra Mode Decision Disable";
995 + case V4L2_CID_MPEG_VIDEO_VPX_NUM_REF_FRAMES: return "VPX No. of Refs for P Frame";
996 + case V4L2_CID_MPEG_VIDEO_VPX_FILTER_LEVEL: return "VPX Loop Filter Level Range";
997 + case V4L2_CID_MPEG_VIDEO_VPX_FILTER_SHARPNESS: return "VPX Deblocking Effect Control";
998 + case V4L2_CID_MPEG_VIDEO_VPX_GOLDEN_FRAME_REF_PERIOD: return "VPX Golden Frame Refresh Period";
999 + case V4L2_CID_MPEG_VIDEO_VPX_GOLDEN_FRAME_SEL: return "VPX Golden Frame Indicator";
1000 + case V4L2_CID_MPEG_VIDEO_VPX_MIN_QP: return "VPX Minimum QP Value";
1001 + case V4L2_CID_MPEG_VIDEO_VPX_MAX_QP: return "VPX Maximum QP Value";
1002 + case V4L2_CID_MPEG_VIDEO_VPX_I_FRAME_QP: return "VPX I-Frame QP Value";
1003 + case V4L2_CID_MPEG_VIDEO_VPX_P_FRAME_QP: return "VPX P-Frame QP Value";
1004 + case V4L2_CID_MPEG_VIDEO_VP8_PROFILE: return "VP8 Profile";
1005 + case V4L2_CID_MPEG_VIDEO_VP9_PROFILE: return "VP9 Profile";
1006 + case V4L2_CID_MPEG_VIDEO_VP9_LEVEL: return "VP9 Level";
1007 +
1008 + /* HEVC controls */
1009 + case V4L2_CID_MPEG_VIDEO_HEVC_I_FRAME_QP: return "HEVC I-Frame QP Value";
1010 + case V4L2_CID_MPEG_VIDEO_HEVC_P_FRAME_QP: return "HEVC P-Frame QP Value";
1011 + case V4L2_CID_MPEG_VIDEO_HEVC_B_FRAME_QP: return "HEVC B-Frame QP Value";
1012 + case V4L2_CID_MPEG_VIDEO_HEVC_MIN_QP: return "HEVC Minimum QP Value";
1013 + case V4L2_CID_MPEG_VIDEO_HEVC_MAX_QP: return "HEVC Maximum QP Value";
1014 + case V4L2_CID_MPEG_VIDEO_HEVC_I_FRAME_MIN_QP: return "HEVC I-Frame Minimum QP Value";
1015 + case V4L2_CID_MPEG_VIDEO_HEVC_I_FRAME_MAX_QP: return "HEVC I-Frame Maximum QP Value";
1016 + case V4L2_CID_MPEG_VIDEO_HEVC_P_FRAME_MIN_QP: return "HEVC P-Frame Minimum QP Value";
1017 + case V4L2_CID_MPEG_VIDEO_HEVC_P_FRAME_MAX_QP: return "HEVC P-Frame Maximum QP Value";
1018 + case V4L2_CID_MPEG_VIDEO_HEVC_B_FRAME_MIN_QP: return "HEVC B-Frame Minimum QP Value";
1019 + case V4L2_CID_MPEG_VIDEO_HEVC_B_FRAME_MAX_QP: return "HEVC B-Frame Maximum QP Value";
1020 + case V4L2_CID_MPEG_VIDEO_HEVC_PROFILE: return "HEVC Profile";
1021 + case V4L2_CID_MPEG_VIDEO_HEVC_LEVEL: return "HEVC Level";
1022 + case V4L2_CID_MPEG_VIDEO_HEVC_TIER: return "HEVC Tier";
1023 + case V4L2_CID_MPEG_VIDEO_HEVC_FRAME_RATE_RESOLUTION: return "HEVC Frame Rate Resolution";
1024 + case V4L2_CID_MPEG_VIDEO_HEVC_MAX_PARTITION_DEPTH: return "HEVC Maximum Coding Unit Depth";
1025 + case V4L2_CID_MPEG_VIDEO_HEVC_REFRESH_TYPE: return "HEVC Refresh Type";
1026 + case V4L2_CID_MPEG_VIDEO_HEVC_CONST_INTRA_PRED: return "HEVC Constant Intra Prediction";
1027 + case V4L2_CID_MPEG_VIDEO_HEVC_LOSSLESS_CU: return "HEVC Lossless Encoding";
1028 + case V4L2_CID_MPEG_VIDEO_HEVC_WAVEFRONT: return "HEVC Wavefront";
1029 + case V4L2_CID_MPEG_VIDEO_HEVC_LOOP_FILTER_MODE: return "HEVC Loop Filter";
1030 + case V4L2_CID_MPEG_VIDEO_HEVC_HIER_QP: return "HEVC QP Values";
1031 + case V4L2_CID_MPEG_VIDEO_HEVC_HIER_CODING_TYPE: return "HEVC Hierarchical Coding Type";
1032 + case V4L2_CID_MPEG_VIDEO_HEVC_HIER_CODING_LAYER: return "HEVC Hierarchical Coding Layer";
1033 + case V4L2_CID_MPEG_VIDEO_HEVC_HIER_CODING_L0_QP: return "HEVC Hierarchical Layer 0 QP";
1034 + case V4L2_CID_MPEG_VIDEO_HEVC_HIER_CODING_L1_QP: return "HEVC Hierarchical Layer 1 QP";
1035 + case V4L2_CID_MPEG_VIDEO_HEVC_HIER_CODING_L2_QP: return "HEVC Hierarchical Layer 2 QP";
1036 + case V4L2_CID_MPEG_VIDEO_HEVC_HIER_CODING_L3_QP: return "HEVC Hierarchical Layer 3 QP";
1037 + case V4L2_CID_MPEG_VIDEO_HEVC_HIER_CODING_L4_QP: return "HEVC Hierarchical Layer 4 QP";
1038 + case V4L2_CID_MPEG_VIDEO_HEVC_HIER_CODING_L5_QP: return "HEVC Hierarchical Layer 5 QP";
1039 + case V4L2_CID_MPEG_VIDEO_HEVC_HIER_CODING_L6_QP: return "HEVC Hierarchical Layer 6 QP";
1040 + case V4L2_CID_MPEG_VIDEO_HEVC_HIER_CODING_L0_BR: return "HEVC Hierarchical Lay 0 BitRate";
1041 + case V4L2_CID_MPEG_VIDEO_HEVC_HIER_CODING_L1_BR: return "HEVC Hierarchical Lay 1 BitRate";
1042 + case V4L2_CID_MPEG_VIDEO_HEVC_HIER_CODING_L2_BR: return "HEVC Hierarchical Lay 2 BitRate";
1043 + case V4L2_CID_MPEG_VIDEO_HEVC_HIER_CODING_L3_BR: return "HEVC Hierarchical Lay 3 BitRate";
1044 + case V4L2_CID_MPEG_VIDEO_HEVC_HIER_CODING_L4_BR: return "HEVC Hierarchical Lay 4 BitRate";
1045 + case V4L2_CID_MPEG_VIDEO_HEVC_HIER_CODING_L5_BR: return "HEVC Hierarchical Lay 5 BitRate";
1046 + case V4L2_CID_MPEG_VIDEO_HEVC_HIER_CODING_L6_BR: return "HEVC Hierarchical Lay 6 BitRate";
1047 + case V4L2_CID_MPEG_VIDEO_HEVC_GENERAL_PB: return "HEVC General PB";
1048 + case V4L2_CID_MPEG_VIDEO_HEVC_TEMPORAL_ID: return "HEVC Temporal ID";
1049 + case V4L2_CID_MPEG_VIDEO_HEVC_STRONG_SMOOTHING: return "HEVC Strong Intra Smoothing";
1050 + case V4L2_CID_MPEG_VIDEO_HEVC_INTRA_PU_SPLIT: return "HEVC Intra PU Split";
1051 + case V4L2_CID_MPEG_VIDEO_HEVC_TMV_PREDICTION: return "HEVC TMV Prediction";
1052 + case V4L2_CID_MPEG_VIDEO_HEVC_MAX_NUM_MERGE_MV_MINUS1: return "HEVC Max Num of Candidate MVs";
1053 + case V4L2_CID_MPEG_VIDEO_HEVC_WITHOUT_STARTCODE: return "HEVC ENC Without Startcode";
1054 + case V4L2_CID_MPEG_VIDEO_HEVC_REFRESH_PERIOD: return "HEVC Num of I-Frame b/w 2 IDR";
1055 + case V4L2_CID_MPEG_VIDEO_HEVC_LF_BETA_OFFSET_DIV2: return "HEVC Loop Filter Beta Offset";
1056 + case V4L2_CID_MPEG_VIDEO_HEVC_LF_TC_OFFSET_DIV2: return "HEVC Loop Filter TC Offset";
1057 + case V4L2_CID_MPEG_VIDEO_HEVC_SIZE_OF_LENGTH_FIELD: return "HEVC Size of Length Field";
1058 + case V4L2_CID_MPEG_VIDEO_REF_NUMBER_FOR_PFRAMES: return "Reference Frames for a P-Frame";
1059 + case V4L2_CID_MPEG_VIDEO_PREPEND_SPSPPS_TO_IDR: return "Prepend SPS and PPS to IDR";
1060 + case V4L2_CID_MPEG_VIDEO_HEVC_SPS: return "HEVC Sequence Parameter Set";
1061 + case V4L2_CID_MPEG_VIDEO_HEVC_PPS: return "HEVC Picture Parameter Set";
1062 + case V4L2_CID_MPEG_VIDEO_HEVC_SLICE_PARAMS: return "HEVC Slice Parameters";
1063 + case V4L2_CID_MPEG_VIDEO_HEVC_DECODE_MODE: return "HEVC Decode Mode";
1064 + case V4L2_CID_MPEG_VIDEO_HEVC_START_CODE: return "HEVC Start Code";
1065 +
1066 + /* CAMERA controls */
1067 + /* Keep the order of the 'case's the same as in v4l2-controls.h! */
1068 + case V4L2_CID_CAMERA_CLASS: return "Camera Controls";
1069 + case V4L2_CID_EXPOSURE_AUTO: return "Auto Exposure";
1070 + case V4L2_CID_EXPOSURE_ABSOLUTE: return "Exposure Time, Absolute";
1071 + case V4L2_CID_EXPOSURE_AUTO_PRIORITY: return "Exposure, Dynamic Framerate";
1072 + case V4L2_CID_PAN_RELATIVE: return "Pan, Relative";
1073 + case V4L2_CID_TILT_RELATIVE: return "Tilt, Relative";
1074 + case V4L2_CID_PAN_RESET: return "Pan, Reset";
1075 + case V4L2_CID_TILT_RESET: return "Tilt, Reset";
1076 + case V4L2_CID_PAN_ABSOLUTE: return "Pan, Absolute";
1077 + case V4L2_CID_TILT_ABSOLUTE: return "Tilt, Absolute";
1078 + case V4L2_CID_FOCUS_ABSOLUTE: return "Focus, Absolute";
1079 + case V4L2_CID_FOCUS_RELATIVE: return "Focus, Relative";
1080 + case V4L2_CID_FOCUS_AUTO: return "Focus, Automatic Continuous";
1081 + case V4L2_CID_ZOOM_ABSOLUTE: return "Zoom, Absolute";
1082 + case V4L2_CID_ZOOM_RELATIVE: return "Zoom, Relative";
1083 + case V4L2_CID_ZOOM_CONTINUOUS: return "Zoom, Continuous";
1084 + case V4L2_CID_PRIVACY: return "Privacy";
1085 + case V4L2_CID_IRIS_ABSOLUTE: return "Iris, Absolute";
1086 + case V4L2_CID_IRIS_RELATIVE: return "Iris, Relative";
1087 + case V4L2_CID_AUTO_EXPOSURE_BIAS: return "Auto Exposure, Bias";
1088 + case V4L2_CID_AUTO_N_PRESET_WHITE_BALANCE: return "White Balance, Auto & Preset";
1089 + case V4L2_CID_WIDE_DYNAMIC_RANGE: return "Wide Dynamic Range";
1090 + case V4L2_CID_IMAGE_STABILIZATION: return "Image Stabilization";
1091 + case V4L2_CID_ISO_SENSITIVITY: return "ISO Sensitivity";
1092 + case V4L2_CID_ISO_SENSITIVITY_AUTO: return "ISO Sensitivity, Auto";
1093 + case V4L2_CID_EXPOSURE_METERING: return "Exposure, Metering Mode";
1094 + case V4L2_CID_SCENE_MODE: return "Scene Mode";
1095 + case V4L2_CID_3A_LOCK: return "3A Lock";
1096 + case V4L2_CID_AUTO_FOCUS_START: return "Auto Focus, Start";
1097 + case V4L2_CID_AUTO_FOCUS_STOP: return "Auto Focus, Stop";
1098 + case V4L2_CID_AUTO_FOCUS_STATUS: return "Auto Focus, Status";
1099 + case V4L2_CID_AUTO_FOCUS_RANGE: return "Auto Focus, Range";
1100 + case V4L2_CID_PAN_SPEED: return "Pan, Speed";
1101 + case V4L2_CID_TILT_SPEED: return "Tilt, Speed";
1102 + case V4L2_CID_UNIT_CELL_SIZE: return "Unit Cell Size";
1103 + case V4L2_CID_CAMERA_ORIENTATION: return "Camera Orientation";
1104 + case V4L2_CID_CAMERA_SENSOR_ROTATION: return "Camera Sensor Rotation";
1105 +
1106 + /* FM Radio Modulator controls */
1107 + /* Keep the order of the 'case's the same as in v4l2-controls.h! */
1108 + case V4L2_CID_FM_TX_CLASS: return "FM Radio Modulator Controls";
1109 + case V4L2_CID_RDS_TX_DEVIATION: return "RDS Signal Deviation";
1110 + case V4L2_CID_RDS_TX_PI: return "RDS Program ID";
1111 + case V4L2_CID_RDS_TX_PTY: return "RDS Program Type";
1112 + case V4L2_CID_RDS_TX_PS_NAME: return "RDS PS Name";
1113 + case V4L2_CID_RDS_TX_RADIO_TEXT: return "RDS Radio Text";
1114 + case V4L2_CID_RDS_TX_MONO_STEREO: return "RDS Stereo";
1115 + case V4L2_CID_RDS_TX_ARTIFICIAL_HEAD: return "RDS Artificial Head";
1116 + case V4L2_CID_RDS_TX_COMPRESSED: return "RDS Compressed";
1117 + case V4L2_CID_RDS_TX_DYNAMIC_PTY: return "RDS Dynamic PTY";
1118 + case V4L2_CID_RDS_TX_TRAFFIC_ANNOUNCEMENT: return "RDS Traffic Announcement";
1119 + case V4L2_CID_RDS_TX_TRAFFIC_PROGRAM: return "RDS Traffic Program";
1120 + case V4L2_CID_RDS_TX_MUSIC_SPEECH: return "RDS Music";
1121 + case V4L2_CID_RDS_TX_ALT_FREQS_ENABLE: return "RDS Enable Alt Frequencies";
1122 + case V4L2_CID_RDS_TX_ALT_FREQS: return "RDS Alternate Frequencies";
1123 + case V4L2_CID_AUDIO_LIMITER_ENABLED: return "Audio Limiter Feature Enabled";
1124 + case V4L2_CID_AUDIO_LIMITER_RELEASE_TIME: return "Audio Limiter Release Time";
1125 + case V4L2_CID_AUDIO_LIMITER_DEVIATION: return "Audio Limiter Deviation";
1126 + case V4L2_CID_AUDIO_COMPRESSION_ENABLED: return "Audio Compression Enabled";
1127 + case V4L2_CID_AUDIO_COMPRESSION_GAIN: return "Audio Compression Gain";
1128 + case V4L2_CID_AUDIO_COMPRESSION_THRESHOLD: return "Audio Compression Threshold";
1129 + case V4L2_CID_AUDIO_COMPRESSION_ATTACK_TIME: return "Audio Compression Attack Time";
1130 + case V4L2_CID_AUDIO_COMPRESSION_RELEASE_TIME: return "Audio Compression Release Time";
1131 + case V4L2_CID_PILOT_TONE_ENABLED: return "Pilot Tone Feature Enabled";
1132 + case V4L2_CID_PILOT_TONE_DEVIATION: return "Pilot Tone Deviation";
1133 + case V4L2_CID_PILOT_TONE_FREQUENCY: return "Pilot Tone Frequency";
1134 + case V4L2_CID_TUNE_PREEMPHASIS: return "Pre-Emphasis";
1135 + case V4L2_CID_TUNE_POWER_LEVEL: return "Tune Power Level";
1136 + case V4L2_CID_TUNE_ANTENNA_CAPACITOR: return "Tune Antenna Capacitor";
1137 +
1138 + /* Flash controls */
1139 + /* Keep the order of the 'case's the same as in v4l2-controls.h! */
1140 + case V4L2_CID_FLASH_CLASS: return "Flash Controls";
1141 + case V4L2_CID_FLASH_LED_MODE: return "LED Mode";
1142 + case V4L2_CID_FLASH_STROBE_SOURCE: return "Strobe Source";
1143 + case V4L2_CID_FLASH_STROBE: return "Strobe";
1144 + case V4L2_CID_FLASH_STROBE_STOP: return "Stop Strobe";
1145 + case V4L2_CID_FLASH_STROBE_STATUS: return "Strobe Status";
1146 + case V4L2_CID_FLASH_TIMEOUT: return "Strobe Timeout";
1147 + case V4L2_CID_FLASH_INTENSITY: return "Intensity, Flash Mode";
1148 + case V4L2_CID_FLASH_TORCH_INTENSITY: return "Intensity, Torch Mode";
1149 + case V4L2_CID_FLASH_INDICATOR_INTENSITY: return "Intensity, Indicator";
1150 + case V4L2_CID_FLASH_FAULT: return "Faults";
1151 + case V4L2_CID_FLASH_CHARGE: return "Charge";
1152 + case V4L2_CID_FLASH_READY: return "Ready to Strobe";
1153 +
1154 + /* JPEG encoder controls */
1155 + /* Keep the order of the 'case's the same as in v4l2-controls.h! */
1156 + case V4L2_CID_JPEG_CLASS: return "JPEG Compression Controls";
1157 + case V4L2_CID_JPEG_CHROMA_SUBSAMPLING: return "Chroma Subsampling";
1158 + case V4L2_CID_JPEG_RESTART_INTERVAL: return "Restart Interval";
1159 + case V4L2_CID_JPEG_COMPRESSION_QUALITY: return "Compression Quality";
1160 + case V4L2_CID_JPEG_ACTIVE_MARKER: return "Active Markers";
1161 +
1162 + /* Image source controls */
1163 + /* Keep the order of the 'case's the same as in v4l2-controls.h! */
1164 + case V4L2_CID_IMAGE_SOURCE_CLASS: return "Image Source Controls";
1165 + case V4L2_CID_VBLANK: return "Vertical Blanking";
1166 + case V4L2_CID_HBLANK: return "Horizontal Blanking";
1167 + case V4L2_CID_ANALOGUE_GAIN: return "Analogue Gain";
1168 + case V4L2_CID_TEST_PATTERN_RED: return "Red Pixel Value";
1169 + case V4L2_CID_TEST_PATTERN_GREENR: return "Green (Red) Pixel Value";
1170 + case V4L2_CID_TEST_PATTERN_BLUE: return "Blue Pixel Value";
1171 + case V4L2_CID_TEST_PATTERN_GREENB: return "Green (Blue) Pixel Value";
1172 +
1173 + /* Image processing controls */
1174 + /* Keep the order of the 'case's the same as in v4l2-controls.h! */
1175 + case V4L2_CID_IMAGE_PROC_CLASS: return "Image Processing Controls";
1176 + case V4L2_CID_LINK_FREQ: return "Link Frequency";
1177 + case V4L2_CID_PIXEL_RATE: return "Pixel Rate";
1178 + case V4L2_CID_TEST_PATTERN: return "Test Pattern";
1179 + case V4L2_CID_DEINTERLACING_MODE: return "Deinterlacing Mode";
1180 + case V4L2_CID_DIGITAL_GAIN: return "Digital Gain";
1181 +
1182 + /* DV controls */
1183 + /* Keep the order of the 'case's the same as in v4l2-controls.h! */
1184 + case V4L2_CID_DV_CLASS: return "Digital Video Controls";
1185 + case V4L2_CID_DV_TX_HOTPLUG: return "Hotplug Present";
1186 + case V4L2_CID_DV_TX_RXSENSE: return "RxSense Present";
1187 + case V4L2_CID_DV_TX_EDID_PRESENT: return "EDID Present";
1188 + case V4L2_CID_DV_TX_MODE: return "Transmit Mode";
1189 + case V4L2_CID_DV_TX_RGB_RANGE: return "Tx RGB Quantization Range";
1190 + case V4L2_CID_DV_TX_IT_CONTENT_TYPE: return "Tx IT Content Type";
1191 + case V4L2_CID_DV_RX_POWER_PRESENT: return "Power Present";
1192 + case V4L2_CID_DV_RX_RGB_RANGE: return "Rx RGB Quantization Range";
1193 + case V4L2_CID_DV_RX_IT_CONTENT_TYPE: return "Rx IT Content Type";
1194 +
1195 + case V4L2_CID_FM_RX_CLASS: return "FM Radio Receiver Controls";
1196 + case V4L2_CID_TUNE_DEEMPHASIS: return "De-Emphasis";
1197 + case V4L2_CID_RDS_RECEPTION: return "RDS Reception";
1198 + case V4L2_CID_RF_TUNER_CLASS: return "RF Tuner Controls";
1199 + case V4L2_CID_RF_TUNER_RF_GAIN: return "RF Gain";
1200 + case V4L2_CID_RF_TUNER_LNA_GAIN_AUTO: return "LNA Gain, Auto";
1201 + case V4L2_CID_RF_TUNER_LNA_GAIN: return "LNA Gain";
1202 + case V4L2_CID_RF_TUNER_MIXER_GAIN_AUTO: return "Mixer Gain, Auto";
1203 + case V4L2_CID_RF_TUNER_MIXER_GAIN: return "Mixer Gain";
1204 + case V4L2_CID_RF_TUNER_IF_GAIN_AUTO: return "IF Gain, Auto";
1205 + case V4L2_CID_RF_TUNER_IF_GAIN: return "IF Gain";
1206 + case V4L2_CID_RF_TUNER_BANDWIDTH_AUTO: return "Bandwidth, Auto";
1207 + case V4L2_CID_RF_TUNER_BANDWIDTH: return "Bandwidth";
1208 + case V4L2_CID_RF_TUNER_PLL_LOCK: return "PLL Lock";
1209 + case V4L2_CID_RDS_RX_PTY: return "RDS Program Type";
1210 + case V4L2_CID_RDS_RX_PS_NAME: return "RDS PS Name";
1211 + case V4L2_CID_RDS_RX_RADIO_TEXT: return "RDS Radio Text";
1212 + case V4L2_CID_RDS_RX_TRAFFIC_ANNOUNCEMENT: return "RDS Traffic Announcement";
1213 + case V4L2_CID_RDS_RX_TRAFFIC_PROGRAM: return "RDS Traffic Program";
1214 + case V4L2_CID_RDS_RX_MUSIC_SPEECH: return "RDS Music";
1215 +
1216 + /* Detection controls */
1217 + /* Keep the order of the 'case's the same as in v4l2-controls.h! */
1218 + case V4L2_CID_DETECT_CLASS: return "Detection Controls";
1219 + case V4L2_CID_DETECT_MD_MODE: return "Motion Detection Mode";
1220 + case V4L2_CID_DETECT_MD_GLOBAL_THRESHOLD: return "MD Global Threshold";
1221 + case V4L2_CID_DETECT_MD_THRESHOLD_GRID: return "MD Threshold Grid";
1222 + case V4L2_CID_DETECT_MD_REGION_GRID: return "MD Region Grid";
1223 +
1224 + /* Stateless Codec controls */
1225 + /* Keep the order of the 'case's the same as in v4l2-controls.h! */
1226 + case V4L2_CID_CODEC_STATELESS_CLASS: return "Stateless Codec Controls";
1227 + case V4L2_CID_STATELESS_H264_DECODE_MODE: return "H264 Decode Mode";
1228 + case V4L2_CID_STATELESS_H264_START_CODE: return "H264 Start Code";
1229 + case V4L2_CID_STATELESS_H264_SPS: return "H264 Sequence Parameter Set";
1230 + case V4L2_CID_STATELESS_H264_PPS: return "H264 Picture Parameter Set";
1231 + case V4L2_CID_STATELESS_H264_SCALING_MATRIX: return "H264 Scaling Matrix";
1232 + case V4L2_CID_STATELESS_H264_PRED_WEIGHTS: return "H264 Prediction Weight Table";
1233 + case V4L2_CID_STATELESS_H264_SLICE_PARAMS: return "H264 Slice Parameters";
1234 + case V4L2_CID_STATELESS_H264_DECODE_PARAMS: return "H264 Decode Parameters";
1235 + case V4L2_CID_STATELESS_FWHT_PARAMS: return "FWHT Stateless Parameters";
1236 + case V4L2_CID_STATELESS_VP8_FRAME: return "VP8 Frame Parameters";
1237 +
1238 + /* Colorimetry controls */
1239 + /* Keep the order of the 'case's the same as in v4l2-controls.h! */
1240 + case V4L2_CID_COLORIMETRY_CLASS: return "Colorimetry Controls";
1241 + case V4L2_CID_COLORIMETRY_HDR10_CLL_INFO: return "HDR10 Content Light Info";
1242 + case V4L2_CID_COLORIMETRY_HDR10_MASTERING_DISPLAY: return "HDR10 Mastering Display";
1243 + default:
1244 + return NULL;
1245 + }
1246 +}
1247 +EXPORT_SYMBOL(v4l2_ctrl_get_name);
1248 +
1249 +void v4l2_ctrl_fill(u32 id, const char **name, enum v4l2_ctrl_type *type,
1250 + s64 *min, s64 *max, u64 *step, s64 *def, u32 *flags)
1251 +{
1252 + *name = v4l2_ctrl_get_name(id);
1253 + *flags = 0;
1254 +
1255 + switch (id) {
1256 + case V4L2_CID_AUDIO_MUTE:
1257 + case V4L2_CID_AUDIO_LOUDNESS:
1258 + case V4L2_CID_AUTO_WHITE_BALANCE:
1259 + case V4L2_CID_AUTOGAIN:
1260 + case V4L2_CID_HFLIP:
1261 + case V4L2_CID_VFLIP:
1262 + case V4L2_CID_HUE_AUTO:
1263 + case V4L2_CID_CHROMA_AGC:
1264 + case V4L2_CID_COLOR_KILLER:
1265 + case V4L2_CID_AUTOBRIGHTNESS:
1266 + case V4L2_CID_MPEG_AUDIO_MUTE:
1267 + case V4L2_CID_MPEG_VIDEO_MUTE:
1268 + case V4L2_CID_MPEG_VIDEO_GOP_CLOSURE:
1269 + case V4L2_CID_MPEG_VIDEO_PULLDOWN:
1270 + case V4L2_CID_EXPOSURE_AUTO_PRIORITY:
1271 + case V4L2_CID_FOCUS_AUTO:
1272 + case V4L2_CID_PRIVACY:
1273 + case V4L2_CID_AUDIO_LIMITER_ENABLED:
1274 + case V4L2_CID_AUDIO_COMPRESSION_ENABLED:
1275 + case V4L2_CID_PILOT_TONE_ENABLED:
1276 + case V4L2_CID_ILLUMINATORS_1:
1277 + case V4L2_CID_ILLUMINATORS_2:
1278 + case V4L2_CID_FLASH_STROBE_STATUS:
1279 + case V4L2_CID_FLASH_CHARGE:
1280 + case V4L2_CID_FLASH_READY:
1281 + case V4L2_CID_MPEG_VIDEO_DECODER_MPEG4_DEBLOCK_FILTER:
1282 + case V4L2_CID_MPEG_VIDEO_DECODER_SLICE_INTERFACE:
1283 + case V4L2_CID_MPEG_VIDEO_DEC_DISPLAY_DELAY_ENABLE:
1284 + case V4L2_CID_MPEG_VIDEO_FRAME_RC_ENABLE:
1285 + case V4L2_CID_MPEG_VIDEO_MB_RC_ENABLE:
1286 + case V4L2_CID_MPEG_VIDEO_H264_8X8_TRANSFORM:
1287 + case V4L2_CID_MPEG_VIDEO_H264_VUI_SAR_ENABLE:
1288 + case V4L2_CID_MPEG_VIDEO_MPEG4_QPEL:
1289 + case V4L2_CID_MPEG_VIDEO_REPEAT_SEQ_HEADER:
1290 + case V4L2_CID_MPEG_VIDEO_AU_DELIMITER:
1291 + case V4L2_CID_WIDE_DYNAMIC_RANGE:
1292 + case V4L2_CID_IMAGE_STABILIZATION:
1293 + case V4L2_CID_RDS_RECEPTION:
1294 + case V4L2_CID_RF_TUNER_LNA_GAIN_AUTO:
1295 + case V4L2_CID_RF_TUNER_MIXER_GAIN_AUTO:
1296 + case V4L2_CID_RF_TUNER_IF_GAIN_AUTO:
1297 + case V4L2_CID_RF_TUNER_BANDWIDTH_AUTO:
1298 + case V4L2_CID_RF_TUNER_PLL_LOCK:
1299 + case V4L2_CID_RDS_TX_MONO_STEREO:
1300 + case V4L2_CID_RDS_TX_ARTIFICIAL_HEAD:
1301 + case V4L2_CID_RDS_TX_COMPRESSED:
1302 + case V4L2_CID_RDS_TX_DYNAMIC_PTY:
1303 + case V4L2_CID_RDS_TX_TRAFFIC_ANNOUNCEMENT:
1304 + case V4L2_CID_RDS_TX_TRAFFIC_PROGRAM:
1305 + case V4L2_CID_RDS_TX_MUSIC_SPEECH:
1306 + case V4L2_CID_RDS_TX_ALT_FREQS_ENABLE:
1307 + case V4L2_CID_RDS_RX_TRAFFIC_ANNOUNCEMENT:
1308 + case V4L2_CID_RDS_RX_TRAFFIC_PROGRAM:
1309 + case V4L2_CID_RDS_RX_MUSIC_SPEECH:
1310 + *type = V4L2_CTRL_TYPE_BOOLEAN;
1311 + *min = 0;
1312 + *max = *step = 1;
1313 + break;
1314 + case V4L2_CID_ROTATE:
1315 + *type = V4L2_CTRL_TYPE_INTEGER;
1316 + *flags |= V4L2_CTRL_FLAG_MODIFY_LAYOUT;
1317 + break;
1318 + case V4L2_CID_MPEG_VIDEO_MV_H_SEARCH_RANGE:
1319 + case V4L2_CID_MPEG_VIDEO_MV_V_SEARCH_RANGE:
1320 + case V4L2_CID_MPEG_VIDEO_DEC_DISPLAY_DELAY:
1321 + *type = V4L2_CTRL_TYPE_INTEGER;
1322 + break;
1323 + case V4L2_CID_MPEG_VIDEO_LTR_COUNT:
1324 + *type = V4L2_CTRL_TYPE_INTEGER;
1325 + break;
1326 + case V4L2_CID_MPEG_VIDEO_FRAME_LTR_INDEX:
1327 + *type = V4L2_CTRL_TYPE_INTEGER;
1328 + *flags |= V4L2_CTRL_FLAG_EXECUTE_ON_WRITE;
1329 + break;
1330 + case V4L2_CID_MPEG_VIDEO_USE_LTR_FRAMES:
1331 + *type = V4L2_CTRL_TYPE_BITMASK;
1332 + *flags |= V4L2_CTRL_FLAG_EXECUTE_ON_WRITE;
1333 + break;
1334 + case V4L2_CID_MPEG_VIDEO_FORCE_KEY_FRAME:
1335 + case V4L2_CID_PAN_RESET:
1336 + case V4L2_CID_TILT_RESET:
1337 + case V4L2_CID_FLASH_STROBE:
1338 + case V4L2_CID_FLASH_STROBE_STOP:
1339 + case V4L2_CID_AUTO_FOCUS_START:
1340 + case V4L2_CID_AUTO_FOCUS_STOP:
1341 + case V4L2_CID_DO_WHITE_BALANCE:
1342 + *type = V4L2_CTRL_TYPE_BUTTON;
1343 + *flags |= V4L2_CTRL_FLAG_WRITE_ONLY |
1344 + V4L2_CTRL_FLAG_EXECUTE_ON_WRITE;
1345 + *min = *max = *step = *def = 0;
1346 + break;
1347 + case V4L2_CID_POWER_LINE_FREQUENCY:
1348 + case V4L2_CID_MPEG_AUDIO_SAMPLING_FREQ:
1349 + case V4L2_CID_MPEG_AUDIO_ENCODING:
1350 + case V4L2_CID_MPEG_AUDIO_L1_BITRATE:
1351 + case V4L2_CID_MPEG_AUDIO_L2_BITRATE:
1352 + case V4L2_CID_MPEG_AUDIO_L3_BITRATE:
1353 + case V4L2_CID_MPEG_AUDIO_AC3_BITRATE:
1354 + case V4L2_CID_MPEG_AUDIO_MODE:
1355 + case V4L2_CID_MPEG_AUDIO_MODE_EXTENSION:
1356 + case V4L2_CID_MPEG_AUDIO_EMPHASIS:
1357 + case V4L2_CID_MPEG_AUDIO_CRC:
1358 + case V4L2_CID_MPEG_AUDIO_DEC_PLAYBACK:
1359 + case V4L2_CID_MPEG_AUDIO_DEC_MULTILINGUAL_PLAYBACK:
1360 + case V4L2_CID_MPEG_VIDEO_ENCODING:
1361 + case V4L2_CID_MPEG_VIDEO_ASPECT:
1362 + case V4L2_CID_MPEG_VIDEO_BITRATE_MODE:
1363 + case V4L2_CID_MPEG_STREAM_TYPE:
1364 + case V4L2_CID_MPEG_STREAM_VBI_FMT:
1365 + case V4L2_CID_EXPOSURE_AUTO:
1366 + case V4L2_CID_AUTO_FOCUS_RANGE:
1367 + case V4L2_CID_COLORFX:
1368 + case V4L2_CID_AUTO_N_PRESET_WHITE_BALANCE:
1369 + case V4L2_CID_TUNE_PREEMPHASIS:
1370 + case V4L2_CID_FLASH_LED_MODE:
1371 + case V4L2_CID_FLASH_STROBE_SOURCE:
1372 + case V4L2_CID_MPEG_VIDEO_HEADER_MODE:
1373 + case V4L2_CID_MPEG_VIDEO_FRAME_SKIP_MODE:
1374 + case V4L2_CID_MPEG_VIDEO_MULTI_SLICE_MODE:
1375 + case V4L2_CID_MPEG_VIDEO_H264_ENTROPY_MODE:
1376 + case V4L2_CID_MPEG_VIDEO_H264_LEVEL:
1377 + case V4L2_CID_MPEG_VIDEO_H264_LOOP_FILTER_MODE:
1378 + case V4L2_CID_MPEG_VIDEO_H264_PROFILE:
1379 + case V4L2_CID_MPEG_VIDEO_H264_VUI_SAR_IDC:
1380 + case V4L2_CID_MPEG_VIDEO_H264_SEI_FP_ARRANGEMENT_TYPE:
1381 + case V4L2_CID_MPEG_VIDEO_H264_FMO_MAP_TYPE:
1382 + case V4L2_CID_MPEG_VIDEO_H264_HIERARCHICAL_CODING_TYPE:
1383 + case V4L2_CID_MPEG_VIDEO_MPEG2_LEVEL:
1384 + case V4L2_CID_MPEG_VIDEO_MPEG2_PROFILE:
1385 + case V4L2_CID_MPEG_VIDEO_MPEG4_LEVEL:
1386 + case V4L2_CID_MPEG_VIDEO_MPEG4_PROFILE:
1387 + case V4L2_CID_JPEG_CHROMA_SUBSAMPLING:
1388 + case V4L2_CID_ISO_SENSITIVITY_AUTO:
1389 + case V4L2_CID_EXPOSURE_METERING:
1390 + case V4L2_CID_SCENE_MODE:
1391 + case V4L2_CID_DV_TX_MODE:
1392 + case V4L2_CID_DV_TX_RGB_RANGE:
1393 + case V4L2_CID_DV_TX_IT_CONTENT_TYPE:
1394 + case V4L2_CID_DV_RX_RGB_RANGE:
1395 + case V4L2_CID_DV_RX_IT_CONTENT_TYPE:
1396 + case V4L2_CID_TEST_PATTERN:
1397 + case V4L2_CID_DEINTERLACING_MODE:
1398 + case V4L2_CID_TUNE_DEEMPHASIS:
1399 + case V4L2_CID_MPEG_VIDEO_VPX_GOLDEN_FRAME_SEL:
1400 + case V4L2_CID_MPEG_VIDEO_VP8_PROFILE:
1401 + case V4L2_CID_MPEG_VIDEO_VP9_PROFILE:
1402 + case V4L2_CID_MPEG_VIDEO_VP9_LEVEL:
1403 + case V4L2_CID_DETECT_MD_MODE:
1404 + case V4L2_CID_MPEG_VIDEO_HEVC_PROFILE:
1405 + case V4L2_CID_MPEG_VIDEO_HEVC_LEVEL:
1406 + case V4L2_CID_MPEG_VIDEO_HEVC_HIER_CODING_TYPE:
1407 + case V4L2_CID_MPEG_VIDEO_HEVC_REFRESH_TYPE:
1408 + case V4L2_CID_MPEG_VIDEO_HEVC_SIZE_OF_LENGTH_FIELD:
1409 + case V4L2_CID_MPEG_VIDEO_HEVC_TIER:
1410 + case V4L2_CID_MPEG_VIDEO_HEVC_LOOP_FILTER_MODE:
1411 + case V4L2_CID_MPEG_VIDEO_HEVC_DECODE_MODE:
1412 + case V4L2_CID_MPEG_VIDEO_HEVC_START_CODE:
1413 + case V4L2_CID_STATELESS_H264_DECODE_MODE:
1414 + case V4L2_CID_STATELESS_H264_START_CODE:
1415 + case V4L2_CID_CAMERA_ORIENTATION:
1416 + *type = V4L2_CTRL_TYPE_MENU;
1417 + break;
1418 + case V4L2_CID_LINK_FREQ:
1419 + *type = V4L2_CTRL_TYPE_INTEGER_MENU;
1420 + break;
1421 + case V4L2_CID_RDS_TX_PS_NAME:
1422 + case V4L2_CID_RDS_TX_RADIO_TEXT:
1423 + case V4L2_CID_RDS_RX_PS_NAME:
1424 + case V4L2_CID_RDS_RX_RADIO_TEXT:
1425 + *type = V4L2_CTRL_TYPE_STRING;
1426 + break;
1427 + case V4L2_CID_ISO_SENSITIVITY:
1428 + case V4L2_CID_AUTO_EXPOSURE_BIAS:
1429 + case V4L2_CID_MPEG_VIDEO_VPX_NUM_PARTITIONS:
1430 + case V4L2_CID_MPEG_VIDEO_VPX_NUM_REF_FRAMES:
1431 + *type = V4L2_CTRL_TYPE_INTEGER_MENU;
1432 + break;
1433 + case V4L2_CID_USER_CLASS:
1434 + case V4L2_CID_CAMERA_CLASS:
1435 + case V4L2_CID_CODEC_CLASS:
1436 + case V4L2_CID_FM_TX_CLASS:
1437 + case V4L2_CID_FLASH_CLASS:
1438 + case V4L2_CID_JPEG_CLASS:
1439 + case V4L2_CID_IMAGE_SOURCE_CLASS:
1440 + case V4L2_CID_IMAGE_PROC_CLASS:
1441 + case V4L2_CID_DV_CLASS:
1442 + case V4L2_CID_FM_RX_CLASS:
1443 + case V4L2_CID_RF_TUNER_CLASS:
1444 + case V4L2_CID_DETECT_CLASS:
1445 + case V4L2_CID_CODEC_STATELESS_CLASS:
1446 + case V4L2_CID_COLORIMETRY_CLASS:
1447 + *type = V4L2_CTRL_TYPE_CTRL_CLASS;
1448 + /* You can neither read nor write these */
1449 + *flags |= V4L2_CTRL_FLAG_READ_ONLY | V4L2_CTRL_FLAG_WRITE_ONLY;
1450 + *min = *max = *step = *def = 0;
1451 + break;
1452 + case V4L2_CID_BG_COLOR:
1453 + *type = V4L2_CTRL_TYPE_INTEGER;
1454 + *step = 1;
1455 + *min = 0;
1456 + /* Max is calculated as RGB888 that is 2^24 */
1457 + *max = 0xFFFFFF;
1458 + break;
1459 + case V4L2_CID_FLASH_FAULT:
1460 + case V4L2_CID_JPEG_ACTIVE_MARKER:
1461 + case V4L2_CID_3A_LOCK:
1462 + case V4L2_CID_AUTO_FOCUS_STATUS:
1463 + case V4L2_CID_DV_TX_HOTPLUG:
1464 + case V4L2_CID_DV_TX_RXSENSE:
1465 + case V4L2_CID_DV_TX_EDID_PRESENT:
1466 + case V4L2_CID_DV_RX_POWER_PRESENT:
1467 + *type = V4L2_CTRL_TYPE_BITMASK;
1468 + break;
1469 + case V4L2_CID_MIN_BUFFERS_FOR_CAPTURE:
1470 + case V4L2_CID_MIN_BUFFERS_FOR_OUTPUT:
1471 + *type = V4L2_CTRL_TYPE_INTEGER;
1472 + *flags |= V4L2_CTRL_FLAG_READ_ONLY;
1473 + break;
1474 + case V4L2_CID_MPEG_VIDEO_DEC_PTS:
1475 + *type = V4L2_CTRL_TYPE_INTEGER64;
1476 + *flags |= V4L2_CTRL_FLAG_VOLATILE | V4L2_CTRL_FLAG_READ_ONLY;
1477 + *min = *def = 0;
1478 + *max = 0x1ffffffffLL;
1479 + *step = 1;
1480 + break;
1481 + case V4L2_CID_MPEG_VIDEO_DEC_FRAME:
1482 + *type = V4L2_CTRL_TYPE_INTEGER64;
1483 + *flags |= V4L2_CTRL_FLAG_VOLATILE | V4L2_CTRL_FLAG_READ_ONLY;
1484 + *min = *def = 0;
1485 + *max = 0x7fffffffffffffffLL;
1486 + *step = 1;
1487 + break;
1488 + case V4L2_CID_MPEG_VIDEO_DEC_CONCEAL_COLOR:
1489 + *type = V4L2_CTRL_TYPE_INTEGER64;
1490 + *min = 0;
1491 + /* default for 8 bit black, luma is 16, chroma is 128 */
1492 + *def = 0x8000800010LL;
1493 + *max = 0xffffffffffffLL;
1494 + *step = 1;
1495 + break;
1496 + case V4L2_CID_PIXEL_RATE:
1497 + *type = V4L2_CTRL_TYPE_INTEGER64;
1498 + *flags |= V4L2_CTRL_FLAG_READ_ONLY;
1499 + break;
1500 + case V4L2_CID_DETECT_MD_REGION_GRID:
1501 + *type = V4L2_CTRL_TYPE_U8;
1502 + break;
1503 + case V4L2_CID_DETECT_MD_THRESHOLD_GRID:
1504 + *type = V4L2_CTRL_TYPE_U16;
1505 + break;
1506 + case V4L2_CID_RDS_TX_ALT_FREQS:
1507 + *type = V4L2_CTRL_TYPE_U32;
1508 + break;
1509 + case V4L2_CID_MPEG_VIDEO_MPEG2_SLICE_PARAMS:
1510 + *type = V4L2_CTRL_TYPE_MPEG2_SLICE_PARAMS;
1511 + break;
1512 + case V4L2_CID_MPEG_VIDEO_MPEG2_QUANTIZATION:
1513 + *type = V4L2_CTRL_TYPE_MPEG2_QUANTIZATION;
1514 + break;
1515 + case V4L2_CID_STATELESS_FWHT_PARAMS:
1516 + *type = V4L2_CTRL_TYPE_FWHT_PARAMS;
1517 + break;
1518 + case V4L2_CID_STATELESS_H264_SPS:
1519 + *type = V4L2_CTRL_TYPE_H264_SPS;
1520 + break;
1521 + case V4L2_CID_STATELESS_H264_PPS:
1522 + *type = V4L2_CTRL_TYPE_H264_PPS;
1523 + break;
1524 + case V4L2_CID_STATELESS_H264_SCALING_MATRIX:
1525 + *type = V4L2_CTRL_TYPE_H264_SCALING_MATRIX;
1526 + break;
1527 + case V4L2_CID_STATELESS_H264_SLICE_PARAMS:
1528 + *type = V4L2_CTRL_TYPE_H264_SLICE_PARAMS;
1529 + break;
1530 + case V4L2_CID_STATELESS_H264_DECODE_PARAMS:
1531 + *type = V4L2_CTRL_TYPE_H264_DECODE_PARAMS;
1532 + break;
1533 + case V4L2_CID_STATELESS_H264_PRED_WEIGHTS:
1534 + *type = V4L2_CTRL_TYPE_H264_PRED_WEIGHTS;
1535 + break;
1536 + case V4L2_CID_STATELESS_VP8_FRAME:
1537 + *type = V4L2_CTRL_TYPE_VP8_FRAME;
1538 + break;
1539 + case V4L2_CID_MPEG_VIDEO_HEVC_SPS:
1540 + *type = V4L2_CTRL_TYPE_HEVC_SPS;
1541 + break;
1542 + case V4L2_CID_MPEG_VIDEO_HEVC_PPS:
1543 + *type = V4L2_CTRL_TYPE_HEVC_PPS;
1544 + break;
1545 + case V4L2_CID_MPEG_VIDEO_HEVC_SLICE_PARAMS:
1546 + *type = V4L2_CTRL_TYPE_HEVC_SLICE_PARAMS;
1547 + break;
1548 + case V4L2_CID_UNIT_CELL_SIZE:
1549 + *type = V4L2_CTRL_TYPE_AREA;
1550 + *flags |= V4L2_CTRL_FLAG_READ_ONLY;
1551 + break;
1552 + case V4L2_CID_COLORIMETRY_HDR10_CLL_INFO:
1553 + *type = V4L2_CTRL_TYPE_HDR10_CLL_INFO;
1554 + break;
1555 + case V4L2_CID_COLORIMETRY_HDR10_MASTERING_DISPLAY:
1556 + *type = V4L2_CTRL_TYPE_HDR10_MASTERING_DISPLAY;
1557 + break;
1558 + default:
1559 + *type = V4L2_CTRL_TYPE_INTEGER;
1560 + break;
1561 + }
1562 + switch (id) {
1563 + case V4L2_CID_MPEG_AUDIO_ENCODING:
1564 + case V4L2_CID_MPEG_AUDIO_MODE:
1565 + case V4L2_CID_MPEG_VIDEO_BITRATE_MODE:
1566 + case V4L2_CID_MPEG_VIDEO_B_FRAMES:
1567 + case V4L2_CID_MPEG_STREAM_TYPE:
1568 + *flags |= V4L2_CTRL_FLAG_UPDATE;
1569 + break;
1570 + case V4L2_CID_AUDIO_VOLUME:
1571 + case V4L2_CID_AUDIO_BALANCE:
1572 + case V4L2_CID_AUDIO_BASS:
1573 + case V4L2_CID_AUDIO_TREBLE:
1574 + case V4L2_CID_BRIGHTNESS:
1575 + case V4L2_CID_CONTRAST:
1576 + case V4L2_CID_SATURATION:
1577 + case V4L2_CID_HUE:
1578 + case V4L2_CID_RED_BALANCE:
1579 + case V4L2_CID_BLUE_BALANCE:
1580 + case V4L2_CID_GAMMA:
1581 + case V4L2_CID_SHARPNESS:
1582 + case V4L2_CID_CHROMA_GAIN:
1583 + case V4L2_CID_RDS_TX_DEVIATION:
1584 + case V4L2_CID_AUDIO_LIMITER_RELEASE_TIME:
1585 + case V4L2_CID_AUDIO_LIMITER_DEVIATION:
1586 + case V4L2_CID_AUDIO_COMPRESSION_GAIN:
1587 + case V4L2_CID_AUDIO_COMPRESSION_THRESHOLD:
1588 + case V4L2_CID_AUDIO_COMPRESSION_ATTACK_TIME:
1589 + case V4L2_CID_AUDIO_COMPRESSION_RELEASE_TIME:
1590 + case V4L2_CID_PILOT_TONE_DEVIATION:
1591 + case V4L2_CID_PILOT_TONE_FREQUENCY:
1592 + case V4L2_CID_TUNE_POWER_LEVEL:
1593 + case V4L2_CID_TUNE_ANTENNA_CAPACITOR:
1594 + case V4L2_CID_RF_TUNER_RF_GAIN:
1595 + case V4L2_CID_RF_TUNER_LNA_GAIN:
1596 + case V4L2_CID_RF_TUNER_MIXER_GAIN:
1597 + case V4L2_CID_RF_TUNER_IF_GAIN:
1598 + case V4L2_CID_RF_TUNER_BANDWIDTH:
1599 + case V4L2_CID_DETECT_MD_GLOBAL_THRESHOLD:
1600 + *flags |= V4L2_CTRL_FLAG_SLIDER;
1601 + break;
1602 + case V4L2_CID_PAN_RELATIVE:
1603 + case V4L2_CID_TILT_RELATIVE:
1604 + case V4L2_CID_FOCUS_RELATIVE:
1605 + case V4L2_CID_IRIS_RELATIVE:
1606 + case V4L2_CID_ZOOM_RELATIVE:
1607 + *flags |= V4L2_CTRL_FLAG_WRITE_ONLY |
1608 + V4L2_CTRL_FLAG_EXECUTE_ON_WRITE;
1609 + break;
1610 + case V4L2_CID_FLASH_STROBE_STATUS:
1611 + case V4L2_CID_AUTO_FOCUS_STATUS:
1612 + case V4L2_CID_FLASH_READY:
1613 + case V4L2_CID_DV_TX_HOTPLUG:
1614 + case V4L2_CID_DV_TX_RXSENSE:
1615 + case V4L2_CID_DV_TX_EDID_PRESENT:
1616 + case V4L2_CID_DV_RX_POWER_PRESENT:
1617 + case V4L2_CID_DV_RX_IT_CONTENT_TYPE:
1618 + case V4L2_CID_RDS_RX_PTY:
1619 + case V4L2_CID_RDS_RX_PS_NAME:
1620 + case V4L2_CID_RDS_RX_RADIO_TEXT:
1621 + case V4L2_CID_RDS_RX_TRAFFIC_ANNOUNCEMENT:
1622 + case V4L2_CID_RDS_RX_TRAFFIC_PROGRAM:
1623 + case V4L2_CID_RDS_RX_MUSIC_SPEECH:
1624 + case V4L2_CID_CAMERA_ORIENTATION:
1625 + case V4L2_CID_CAMERA_SENSOR_ROTATION:
1626 + *flags |= V4L2_CTRL_FLAG_READ_ONLY;
1627 + break;
1628 + case V4L2_CID_RF_TUNER_PLL_LOCK:
1629 + *flags |= V4L2_CTRL_FLAG_VOLATILE;
1630 + break;
1631 + }
1632 +}
1633 +EXPORT_SYMBOL(v4l2_ctrl_fill);
1634 +
1635 +static u32 user_flags(const struct v4l2_ctrl *ctrl)
1636 +{
1637 + u32 flags = ctrl->flags;
1638 +
1639 + if (ctrl->is_ptr)
1640 + flags |= V4L2_CTRL_FLAG_HAS_PAYLOAD;
1641 +
1642 + return flags;
1643 +}
1644 +
1645 +static void fill_event(struct v4l2_event *ev, struct v4l2_ctrl *ctrl, u32 changes)
1646 +{
1647 + memset(ev, 0, sizeof(*ev));
1648 + ev->type = V4L2_EVENT_CTRL;
1649 + ev->id = ctrl->id;
1650 + ev->u.ctrl.changes = changes;
1651 + ev->u.ctrl.type = ctrl->type;
1652 + ev->u.ctrl.flags = user_flags(ctrl);
1653 + if (ctrl->is_ptr)
1654 + ev->u.ctrl.value64 = 0;
1655 + else
1656 + ev->u.ctrl.value64 = *ctrl->p_cur.p_s64;
1657 + ev->u.ctrl.minimum = ctrl->minimum;
1658 + ev->u.ctrl.maximum = ctrl->maximum;
1659 + if (ctrl->type == V4L2_CTRL_TYPE_MENU
1660 + || ctrl->type == V4L2_CTRL_TYPE_INTEGER_MENU)
1661 + ev->u.ctrl.step = 1;
1662 + else
1663 + ev->u.ctrl.step = ctrl->step;
1664 + ev->u.ctrl.default_value = ctrl->default_value;
1665 +}
1666 +
1667 +static void send_event(struct v4l2_fh *fh, struct v4l2_ctrl *ctrl, u32 changes)
1668 +{
1669 + struct v4l2_event ev;
1670 + struct v4l2_subscribed_event *sev;
1671 +
1672 + if (list_empty(&ctrl->ev_subs))
1673 + return;
1674 + fill_event(&ev, ctrl, changes);
1675 +
1676 + list_for_each_entry(sev, &ctrl->ev_subs, node)
1677 + if (sev->fh != fh ||
1678 + (sev->flags & V4L2_EVENT_SUB_FL_ALLOW_FEEDBACK))
1679 + v4l2_event_queue_fh(sev->fh, &ev);
1680 +}
1681 +
1682 +static bool std_equal(const struct v4l2_ctrl *ctrl, u32 idx,
1683 + union v4l2_ctrl_ptr ptr1,
1684 + union v4l2_ctrl_ptr ptr2)
1685 +{
1686 + switch (ctrl->type) {
1687 + case V4L2_CTRL_TYPE_BUTTON:
1688 + return false;
1689 + case V4L2_CTRL_TYPE_STRING:
1690 + idx *= ctrl->elem_size;
1691 + /* strings are always 0-terminated */
1692 + return !strcmp(ptr1.p_char + idx, ptr2.p_char + idx);
1693 + case V4L2_CTRL_TYPE_INTEGER64:
1694 + return ptr1.p_s64[idx] == ptr2.p_s64[idx];
1695 + case V4L2_CTRL_TYPE_U8:
1696 + return ptr1.p_u8[idx] == ptr2.p_u8[idx];
1697 + case V4L2_CTRL_TYPE_U16:
1698 + return ptr1.p_u16[idx] == ptr2.p_u16[idx];
1699 + case V4L2_CTRL_TYPE_U32:
1700 + return ptr1.p_u32[idx] == ptr2.p_u32[idx];
1701 + default:
1702 + if (ctrl->is_int)
1703 + return ptr1.p_s32[idx] == ptr2.p_s32[idx];
1704 + idx *= ctrl->elem_size;
1705 + return !memcmp(ptr1.p_const + idx, ptr2.p_const + idx,
1706 + ctrl->elem_size);
1707 + }
1708 +}
1709 +
1710 +static void std_init_compound(const struct v4l2_ctrl *ctrl, u32 idx,
1711 + union v4l2_ctrl_ptr ptr)
1712 +{
1713 + struct v4l2_ctrl_mpeg2_slice_params *p_mpeg2_slice_params;
1714 + struct v4l2_ctrl_vp8_frame *p_vp8_frame;
1715 + struct v4l2_ctrl_fwht_params *p_fwht_params;
1716 + void *p = ptr.p + idx * ctrl->elem_size;
1717 +
1718 + if (ctrl->p_def.p_const)
1719 + memcpy(p, ctrl->p_def.p_const, ctrl->elem_size);
1720 + else
1721 + memset(p, 0, ctrl->elem_size);
1722 +
1723 + /*
1724 + * The cast is needed to get rid of a gcc warning complaining that
1725 + * V4L2_CTRL_TYPE_MPEG2_SLICE_PARAMS is not part of the
1726 + * v4l2_ctrl_type enum.
1727 + */
1728 + switch ((u32)ctrl->type) {
1729 + case V4L2_CTRL_TYPE_MPEG2_SLICE_PARAMS:
1730 + p_mpeg2_slice_params = p;
1731 + /* 4:2:0 */
1732 + p_mpeg2_slice_params->sequence.chroma_format = 1;
1733 + /* interlaced top field */
1734 + p_mpeg2_slice_params->picture.picture_structure = 1;
1735 + p_mpeg2_slice_params->picture.picture_coding_type =
1736 + V4L2_MPEG2_PICTURE_CODING_TYPE_I;
1737 + break;
1738 + case V4L2_CTRL_TYPE_VP8_FRAME:
1739 + p_vp8_frame = p;
1740 + p_vp8_frame->num_dct_parts = 1;
1741 + break;
1742 + case V4L2_CTRL_TYPE_FWHT_PARAMS:
1743 + p_fwht_params = p;
1744 + p_fwht_params->version = V4L2_FWHT_VERSION;
1745 + p_fwht_params->width = 1280;
1746 + p_fwht_params->height = 720;
1747 + p_fwht_params->flags = V4L2_FWHT_FL_PIXENC_YUV |
1748 + (2 << V4L2_FWHT_FL_COMPONENTS_NUM_OFFSET);
1749 + break;
1750 + }
1751 +}
1752 +
1753 +static void std_init(const struct v4l2_ctrl *ctrl, u32 idx,
1754 + union v4l2_ctrl_ptr ptr)
1755 +{
1756 + switch (ctrl->type) {
1757 + case V4L2_CTRL_TYPE_STRING:
1758 + idx *= ctrl->elem_size;
1759 + memset(ptr.p_char + idx, ' ', ctrl->minimum);
1760 + ptr.p_char[idx + ctrl->minimum] = '\0';
1761 + break;
1762 + case V4L2_CTRL_TYPE_INTEGER64:
1763 + ptr.p_s64[idx] = ctrl->default_value;
1764 + break;
1765 + case V4L2_CTRL_TYPE_INTEGER:
1766 + case V4L2_CTRL_TYPE_INTEGER_MENU:
1767 + case V4L2_CTRL_TYPE_MENU:
1768 + case V4L2_CTRL_TYPE_BITMASK:
1769 + case V4L2_CTRL_TYPE_BOOLEAN:
1770 + ptr.p_s32[idx] = ctrl->default_value;
1771 + break;
1772 + case V4L2_CTRL_TYPE_BUTTON:
1773 + case V4L2_CTRL_TYPE_CTRL_CLASS:
1774 + ptr.p_s32[idx] = 0;
1775 + break;
1776 + case V4L2_CTRL_TYPE_U8:
1777 + ptr.p_u8[idx] = ctrl->default_value;
1778 + break;
1779 + case V4L2_CTRL_TYPE_U16:
1780 + ptr.p_u16[idx] = ctrl->default_value;
1781 + break;
1782 + case V4L2_CTRL_TYPE_U32:
1783 + ptr.p_u32[idx] = ctrl->default_value;
1784 + break;
1785 + default:
1786 + std_init_compound(ctrl, idx, ptr);
1787 + break;
1788 + }
1789 +}
1790 +
1791 +static void std_log(const struct v4l2_ctrl *ctrl)
1792 +{
1793 + union v4l2_ctrl_ptr ptr = ctrl->p_cur;
1794 +
1795 + if (ctrl->is_array) {
1796 + unsigned i;
1797 +
1798 + for (i = 0; i < ctrl->nr_of_dims; i++)
1799 + pr_cont("[%u]", ctrl->dims[i]);
1800 + pr_cont(" ");
1801 + }
1802 +
1803 + switch (ctrl->type) {
1804 + case V4L2_CTRL_TYPE_INTEGER:
1805 + pr_cont("%d", *ptr.p_s32);
1806 + break;
1807 + case V4L2_CTRL_TYPE_BOOLEAN:
1808 + pr_cont("%s", *ptr.p_s32 ? "true" : "false");
1809 + break;
1810 + case V4L2_CTRL_TYPE_MENU:
1811 + pr_cont("%s", ctrl->qmenu[*ptr.p_s32]);
1812 + break;
1813 + case V4L2_CTRL_TYPE_INTEGER_MENU:
1814 + pr_cont("%lld", ctrl->qmenu_int[*ptr.p_s32]);
1815 + break;
1816 + case V4L2_CTRL_TYPE_BITMASK:
1817 + pr_cont("0x%08x", *ptr.p_s32);
1818 + break;
1819 + case V4L2_CTRL_TYPE_INTEGER64:
1820 + pr_cont("%lld", *ptr.p_s64);
1821 + break;
1822 + case V4L2_CTRL_TYPE_STRING:
1823 + pr_cont("%s", ptr.p_char);
1824 + break;
1825 + case V4L2_CTRL_TYPE_U8:
1826 + pr_cont("%u", (unsigned)*ptr.p_u8);
1827 + break;
1828 + case V4L2_CTRL_TYPE_U16:
1829 + pr_cont("%u", (unsigned)*ptr.p_u16);
1830 + break;
1831 + case V4L2_CTRL_TYPE_U32:
1832 + pr_cont("%u", (unsigned)*ptr.p_u32);
1833 + break;
1834 + case V4L2_CTRL_TYPE_H264_SPS:
1835 + pr_cont("H264_SPS");
1836 + break;
1837 + case V4L2_CTRL_TYPE_H264_PPS:
1838 + pr_cont("H264_PPS");
1839 + break;
1840 + case V4L2_CTRL_TYPE_H264_SCALING_MATRIX:
1841 + pr_cont("H264_SCALING_MATRIX");
1842 + break;
1843 + case V4L2_CTRL_TYPE_H264_SLICE_PARAMS:
1844 + pr_cont("H264_SLICE_PARAMS");
1845 + break;
1846 + case V4L2_CTRL_TYPE_H264_DECODE_PARAMS:
1847 + pr_cont("H264_DECODE_PARAMS");
1848 + break;
1849 + case V4L2_CTRL_TYPE_H264_PRED_WEIGHTS:
1850 + pr_cont("H264_PRED_WEIGHTS");
1851 + break;
1852 + case V4L2_CTRL_TYPE_FWHT_PARAMS:
1853 + pr_cont("FWHT_PARAMS");
1854 + break;
1855 + case V4L2_CTRL_TYPE_VP8_FRAME:
1856 + pr_cont("VP8_FRAME");
1857 + break;
1858 + case V4L2_CTRL_TYPE_HDR10_CLL_INFO:
1859 + pr_cont("HDR10_CLL_INFO");
1860 + break;
1861 + case V4L2_CTRL_TYPE_HDR10_MASTERING_DISPLAY:
1862 + pr_cont("HDR10_MASTERING_DISPLAY");
1863 + break;
1864 + default:
1865 + pr_cont("unknown type %d", ctrl->type);
1866 + break;
1867 + }
1868 +}
1869 +
1870 +/*
1871 + * Round towards the closest legal value. Be careful when we are
1872 + * close to the maximum range of the control type to prevent
1873 + * wrap-arounds.
1874 + */
1875 +#define ROUND_TO_RANGE(val, offset_type, ctrl) \
1876 +({ \
1877 + offset_type offset; \
1878 + if ((ctrl)->maximum >= 0 && \
1879 + val >= (ctrl)->maximum - (s32)((ctrl)->step / 2)) \
1880 + val = (ctrl)->maximum; \
1881 + else \
1882 + val += (s32)((ctrl)->step / 2); \
1883 + val = clamp_t(typeof(val), val, \
1884 + (ctrl)->minimum, (ctrl)->maximum); \
1885 + offset = (val) - (ctrl)->minimum; \
1886 + offset = (ctrl)->step * (offset / (u32)(ctrl)->step); \
1887 + val = (ctrl)->minimum + offset; \
1888 + 0; \
1889 +})
1890 +
1891 +/* Validate a new control */
1892 +
1893 +#define zero_padding(s) \
1894 + memset(&(s).padding, 0, sizeof((s).padding))
1895 +#define zero_reserved(s) \
1896 + memset(&(s).reserved, 0, sizeof((s).reserved))
1897 +
1898 +/*
1899 + * Compound controls validation requires setting unused fields/flags to zero
1900 + * in order to properly detect unchanged controls with std_equal's memcmp.
1901 + */
1902 +static int std_validate_compound(const struct v4l2_ctrl *ctrl, u32 idx,
1903 + union v4l2_ctrl_ptr ptr)
1904 +{
1905 + struct v4l2_ctrl_mpeg2_slice_params *p_mpeg2_slice_params;
1906 + struct v4l2_ctrl_vp8_frame *p_vp8_frame;
1907 + struct v4l2_ctrl_fwht_params *p_fwht_params;
1908 + struct v4l2_ctrl_h264_sps *p_h264_sps;
1909 + struct v4l2_ctrl_h264_pps *p_h264_pps;
1910 + struct v4l2_ctrl_h264_pred_weights *p_h264_pred_weights;
1911 + struct v4l2_ctrl_h264_slice_params *p_h264_slice_params;
1912 + struct v4l2_ctrl_h264_decode_params *p_h264_dec_params;
1913 + struct v4l2_ctrl_hevc_sps *p_hevc_sps;
1914 + struct v4l2_ctrl_hevc_pps *p_hevc_pps;
1915 + struct v4l2_ctrl_hevc_slice_params *p_hevc_slice_params;
1916 + struct v4l2_ctrl_hdr10_mastering_display *p_hdr10_mastering;
1917 + struct v4l2_area *area;
1918 + void *p = ptr.p + idx * ctrl->elem_size;
1919 + unsigned int i;
1920 +
1921 + switch ((u32)ctrl->type) {
1922 + case V4L2_CTRL_TYPE_MPEG2_SLICE_PARAMS:
1923 + p_mpeg2_slice_params = p;
1924 +
1925 + switch (p_mpeg2_slice_params->sequence.chroma_format) {
1926 + case 1: /* 4:2:0 */
1927 + case 2: /* 4:2:2 */
1928 + case 3: /* 4:4:4 */
1929 + break;
1930 + default:
1931 + return -EINVAL;
1932 + }
1933 +
1934 + switch (p_mpeg2_slice_params->picture.intra_dc_precision) {
1935 + case 0: /* 8 bits */
1936 + case 1: /* 9 bits */
1937 + case 2: /* 10 bits */
1938 + case 3: /* 11 bits */
1939 + break;
1940 + default:
1941 + return -EINVAL;
1942 + }
1943 +
1944 + switch (p_mpeg2_slice_params->picture.picture_structure) {
1945 + case 1: /* interlaced top field */
1946 + case 2: /* interlaced bottom field */
1947 + case 3: /* progressive */
1948 + break;
1949 + default:
1950 + return -EINVAL;
1951 + }
1952 +
1953 + switch (p_mpeg2_slice_params->picture.picture_coding_type) {
1954 + case V4L2_MPEG2_PICTURE_CODING_TYPE_I:
1955 + case V4L2_MPEG2_PICTURE_CODING_TYPE_P:
1956 + case V4L2_MPEG2_PICTURE_CODING_TYPE_B:
1957 + break;
1958 + default:
1959 + return -EINVAL;
1960 + }
1961 +
1962 + break;
1963 +
1964 + case V4L2_CTRL_TYPE_MPEG2_QUANTIZATION:
1965 + break;
1966 +
1967 + case V4L2_CTRL_TYPE_FWHT_PARAMS:
1968 + p_fwht_params = p;
1969 + if (p_fwht_params->version < V4L2_FWHT_VERSION)
1970 + return -EINVAL;
1971 + if (!p_fwht_params->width || !p_fwht_params->height)
1972 + return -EINVAL;
1973 + break;
1974 +
1975 + case V4L2_CTRL_TYPE_H264_SPS:
1976 + p_h264_sps = p;
1977 +
1978 + /* Some syntax elements are only conditionally valid */
1979 + if (p_h264_sps->pic_order_cnt_type != 0) {
1980 + p_h264_sps->log2_max_pic_order_cnt_lsb_minus4 = 0;
1981 + } else if (p_h264_sps->pic_order_cnt_type != 1) {
1982 + p_h264_sps->num_ref_frames_in_pic_order_cnt_cycle = 0;
1983 + p_h264_sps->offset_for_non_ref_pic = 0;
1984 + p_h264_sps->offset_for_top_to_bottom_field = 0;
1985 + memset(&p_h264_sps->offset_for_ref_frame, 0,
1986 + sizeof(p_h264_sps->offset_for_ref_frame));
1987 + }
1988 +
1989 + if (!V4L2_H264_SPS_HAS_CHROMA_FORMAT(p_h264_sps)) {
1990 + p_h264_sps->chroma_format_idc = 1;
1991 + p_h264_sps->bit_depth_luma_minus8 = 0;
1992 + p_h264_sps->bit_depth_chroma_minus8 = 0;
1993 +
1994 + p_h264_sps->flags &=
1995 + ~V4L2_H264_SPS_FLAG_QPPRIME_Y_ZERO_TRANSFORM_BYPASS;
1996 +
1997 + if (p_h264_sps->chroma_format_idc < 3)
1998 + p_h264_sps->flags &=
1999 + ~V4L2_H264_SPS_FLAG_SEPARATE_COLOUR_PLANE;
2000 + }
2001 +
2002 + if (p_h264_sps->flags & V4L2_H264_SPS_FLAG_FRAME_MBS_ONLY)
2003 + p_h264_sps->flags &=
2004 + ~V4L2_H264_SPS_FLAG_MB_ADAPTIVE_FRAME_FIELD;
2005 +
2006 + /*
2007 + * Chroma 4:2:2 format require at least High 4:2:2 profile.
2008 + *
2009 + * The H264 specification and well-known parser implementations
2010 + * use profile-idc values directly, as that is clearer and
2011 + * less ambiguous. We do the same here.
2012 + */
2013 + if (p_h264_sps->profile_idc < 122 &&
2014 + p_h264_sps->chroma_format_idc > 1)
2015 + return -EINVAL;
2016 + /* Chroma 4:4:4 format require at least High 4:2:2 profile */
2017 + if (p_h264_sps->profile_idc < 244 &&
2018 + p_h264_sps->chroma_format_idc > 2)
2019 + return -EINVAL;
2020 + if (p_h264_sps->chroma_format_idc > 3)
2021 + return -EINVAL;
2022 +
2023 + if (p_h264_sps->bit_depth_luma_minus8 > 6)
2024 + return -EINVAL;
2025 + if (p_h264_sps->bit_depth_chroma_minus8 > 6)
2026 + return -EINVAL;
2027 + if (p_h264_sps->log2_max_frame_num_minus4 > 12)
2028 + return -EINVAL;
2029 + if (p_h264_sps->pic_order_cnt_type > 2)
2030 + return -EINVAL;
2031 + if (p_h264_sps->log2_max_pic_order_cnt_lsb_minus4 > 12)
2032 + return -EINVAL;
2033 + if (p_h264_sps->max_num_ref_frames > V4L2_H264_REF_LIST_LEN)
2034 + return -EINVAL;
2035 + break;
2036 +
2037 + case V4L2_CTRL_TYPE_H264_PPS:
2038 + p_h264_pps = p;
2039 +
2040 + if (p_h264_pps->num_slice_groups_minus1 > 7)
2041 + return -EINVAL;
2042 + if (p_h264_pps->num_ref_idx_l0_default_active_minus1 >
2043 + (V4L2_H264_REF_LIST_LEN - 1))
2044 + return -EINVAL;
2045 + if (p_h264_pps->num_ref_idx_l1_default_active_minus1 >
2046 + (V4L2_H264_REF_LIST_LEN - 1))
2047 + return -EINVAL;
2048 + if (p_h264_pps->weighted_bipred_idc > 2)
2049 + return -EINVAL;
2050 + /*
2051 + * pic_init_qp_minus26 shall be in the range of
2052 + * -(26 + QpBdOffset_y) to +25, inclusive,
2053 + * where QpBdOffset_y is 6 * bit_depth_luma_minus8
2054 + */
2055 + if (p_h264_pps->pic_init_qp_minus26 < -62 ||
2056 + p_h264_pps->pic_init_qp_minus26 > 25)
2057 + return -EINVAL;
2058 + if (p_h264_pps->pic_init_qs_minus26 < -26 ||
2059 + p_h264_pps->pic_init_qs_minus26 > 25)
2060 + return -EINVAL;
2061 + if (p_h264_pps->chroma_qp_index_offset < -12 ||
2062 + p_h264_pps->chroma_qp_index_offset > 12)
2063 + return -EINVAL;
2064 + if (p_h264_pps->second_chroma_qp_index_offset < -12 ||
2065 + p_h264_pps->second_chroma_qp_index_offset > 12)
2066 + return -EINVAL;
2067 + break;
2068 +
2069 + case V4L2_CTRL_TYPE_H264_SCALING_MATRIX:
2070 + break;
2071 +
2072 + case V4L2_CTRL_TYPE_H264_PRED_WEIGHTS:
2073 + p_h264_pred_weights = p;
2074 +
2075 + if (p_h264_pred_weights->luma_log2_weight_denom > 7)
2076 + return -EINVAL;
2077 + if (p_h264_pred_weights->chroma_log2_weight_denom > 7)
2078 + return -EINVAL;
2079 + break;
2080 +
2081 + case V4L2_CTRL_TYPE_H264_SLICE_PARAMS:
2082 + p_h264_slice_params = p;
2083 +
2084 + if (p_h264_slice_params->slice_type != V4L2_H264_SLICE_TYPE_B)
2085 + p_h264_slice_params->flags &=
2086 + ~V4L2_H264_SLICE_FLAG_DIRECT_SPATIAL_MV_PRED;
2087 +
2088 + if (p_h264_slice_params->colour_plane_id > 2)
2089 + return -EINVAL;
2090 + if (p_h264_slice_params->cabac_init_idc > 2)
2091 + return -EINVAL;
2092 + if (p_h264_slice_params->disable_deblocking_filter_idc > 2)
2093 + return -EINVAL;
2094 + if (p_h264_slice_params->slice_alpha_c0_offset_div2 < -6 ||
2095 + p_h264_slice_params->slice_alpha_c0_offset_div2 > 6)
2096 + return -EINVAL;
2097 + if (p_h264_slice_params->slice_beta_offset_div2 < -6 ||
2098 + p_h264_slice_params->slice_beta_offset_div2 > 6)
2099 + return -EINVAL;
2100 +
2101 + if (p_h264_slice_params->slice_type == V4L2_H264_SLICE_TYPE_I ||
2102 + p_h264_slice_params->slice_type == V4L2_H264_SLICE_TYPE_SI)
2103 + p_h264_slice_params->num_ref_idx_l0_active_minus1 = 0;
2104 + if (p_h264_slice_params->slice_type != V4L2_H264_SLICE_TYPE_B)
2105 + p_h264_slice_params->num_ref_idx_l1_active_minus1 = 0;
2106 +
2107 + if (p_h264_slice_params->num_ref_idx_l0_active_minus1 >
2108 + (V4L2_H264_REF_LIST_LEN - 1))
2109 + return -EINVAL;
2110 + if (p_h264_slice_params->num_ref_idx_l1_active_minus1 >
2111 + (V4L2_H264_REF_LIST_LEN - 1))
2112 + return -EINVAL;
2113 + zero_reserved(*p_h264_slice_params);
2114 + break;
2115 +
2116 + case V4L2_CTRL_TYPE_H264_DECODE_PARAMS:
2117 + p_h264_dec_params = p;
2118 +
2119 + if (p_h264_dec_params->nal_ref_idc > 3)
2120 + return -EINVAL;
2121 + for (i = 0; i < V4L2_H264_NUM_DPB_ENTRIES; i++) {
2122 + struct v4l2_h264_dpb_entry *dpb_entry =
2123 + &p_h264_dec_params->dpb[i];
2124 +
2125 + zero_reserved(*dpb_entry);
2126 + }
2127 + zero_reserved(*p_h264_dec_params);
2128 + break;
2129 +
2130 + case V4L2_CTRL_TYPE_VP8_FRAME:
2131 + p_vp8_frame = p;
2132 +
2133 + switch (p_vp8_frame->num_dct_parts) {
2134 + case 1:
2135 + case 2:
2136 + case 4:
2137 + case 8:
2138 + break;
2139 + default:
2140 + return -EINVAL;
2141 + }
2142 + zero_padding(p_vp8_frame->segment);
2143 + zero_padding(p_vp8_frame->lf);
2144 + zero_padding(p_vp8_frame->quant);
2145 + zero_padding(p_vp8_frame->entropy);
2146 + zero_padding(p_vp8_frame->coder_state);
2147 + break;
2148 +
2149 + case V4L2_CTRL_TYPE_HEVC_SPS:
2150 + p_hevc_sps = p;
2151 +
2152 + if (!(p_hevc_sps->flags & V4L2_HEVC_SPS_FLAG_PCM_ENABLED)) {
2153 + p_hevc_sps->pcm_sample_bit_depth_luma_minus1 = 0;
2154 + p_hevc_sps->pcm_sample_bit_depth_chroma_minus1 = 0;
2155 + p_hevc_sps->log2_min_pcm_luma_coding_block_size_minus3 = 0;
2156 + p_hevc_sps->log2_diff_max_min_pcm_luma_coding_block_size = 0;
2157 + }
2158 +
2159 + if (!(p_hevc_sps->flags &
2160 + V4L2_HEVC_SPS_FLAG_LONG_TERM_REF_PICS_PRESENT))
2161 + p_hevc_sps->num_long_term_ref_pics_sps = 0;
2162 + break;
2163 +
2164 + case V4L2_CTRL_TYPE_HEVC_PPS:
2165 + p_hevc_pps = p;
2166 +
2167 + if (!(p_hevc_pps->flags &
2168 + V4L2_HEVC_PPS_FLAG_CU_QP_DELTA_ENABLED))
2169 + p_hevc_pps->diff_cu_qp_delta_depth = 0;
2170 +
2171 + if (!(p_hevc_pps->flags & V4L2_HEVC_PPS_FLAG_TILES_ENABLED)) {
2172 + p_hevc_pps->num_tile_columns_minus1 = 0;
2173 + p_hevc_pps->num_tile_rows_minus1 = 0;
2174 + memset(&p_hevc_pps->column_width_minus1, 0,
2175 + sizeof(p_hevc_pps->column_width_minus1));
2176 + memset(&p_hevc_pps->row_height_minus1, 0,
2177 + sizeof(p_hevc_pps->row_height_minus1));
2178 +
2179 + p_hevc_pps->flags &=
2180 + ~V4L2_HEVC_PPS_FLAG_LOOP_FILTER_ACROSS_TILES_ENABLED;
2181 + }
2182 +
2183 + if (p_hevc_pps->flags &
2184 + V4L2_HEVC_PPS_FLAG_PPS_DISABLE_DEBLOCKING_FILTER) {
2185 + p_hevc_pps->pps_beta_offset_div2 = 0;
2186 + p_hevc_pps->pps_tc_offset_div2 = 0;
2187 + }
2188 +
2189 + zero_padding(*p_hevc_pps);
2190 + break;
2191 +
2192 + case V4L2_CTRL_TYPE_HEVC_SLICE_PARAMS:
2193 + p_hevc_slice_params = p;
2194 +
2195 + if (p_hevc_slice_params->num_active_dpb_entries >
2196 + V4L2_HEVC_DPB_ENTRIES_NUM_MAX)
2197 + return -EINVAL;
2198 +
2199 + zero_padding(p_hevc_slice_params->pred_weight_table);
2200 +
2201 + for (i = 0; i < p_hevc_slice_params->num_active_dpb_entries;
2202 + i++) {
2203 + struct v4l2_hevc_dpb_entry *dpb_entry =
2204 + &p_hevc_slice_params->dpb[i];
2205 +
2206 + zero_padding(*dpb_entry);
2207 + }
2208 +
2209 + zero_padding(*p_hevc_slice_params);
2210 + break;
2211 +
2212 + case V4L2_CTRL_TYPE_HDR10_CLL_INFO:
2213 + break;
2214 +
2215 + case V4L2_CTRL_TYPE_HDR10_MASTERING_DISPLAY:
2216 + p_hdr10_mastering = p;
2217 +
2218 + for (i = 0; i < 3; ++i) {
2219 + if (p_hdr10_mastering->display_primaries_x[i] <
2220 + V4L2_HDR10_MASTERING_PRIMARIES_X_LOW ||
2221 + p_hdr10_mastering->display_primaries_x[i] >
2222 + V4L2_HDR10_MASTERING_PRIMARIES_X_HIGH ||
2223 + p_hdr10_mastering->display_primaries_y[i] <
2224 + V4L2_HDR10_MASTERING_PRIMARIES_Y_LOW ||
2225 + p_hdr10_mastering->display_primaries_y[i] >
2226 + V4L2_HDR10_MASTERING_PRIMARIES_Y_HIGH)
2227 + return -EINVAL;
2228 + }
2229 +
2230 + if (p_hdr10_mastering->white_point_x <
2231 + V4L2_HDR10_MASTERING_WHITE_POINT_X_LOW ||
2232 + p_hdr10_mastering->white_point_x >
2233 + V4L2_HDR10_MASTERING_WHITE_POINT_X_HIGH ||
2234 + p_hdr10_mastering->white_point_y <
2235 + V4L2_HDR10_MASTERING_WHITE_POINT_Y_LOW ||
2236 + p_hdr10_mastering->white_point_y >
2237 + V4L2_HDR10_MASTERING_WHITE_POINT_Y_HIGH)
2238 + return -EINVAL;
2239 +
2240 + if (p_hdr10_mastering->max_display_mastering_luminance <
2241 + V4L2_HDR10_MASTERING_MAX_LUMA_LOW ||
2242 + p_hdr10_mastering->max_display_mastering_luminance >
2243 + V4L2_HDR10_MASTERING_MAX_LUMA_HIGH ||
2244 + p_hdr10_mastering->min_display_mastering_luminance <
2245 + V4L2_HDR10_MASTERING_MIN_LUMA_LOW ||
2246 + p_hdr10_mastering->min_display_mastering_luminance >
2247 + V4L2_HDR10_MASTERING_MIN_LUMA_HIGH)
2248 + return -EINVAL;
2249 +
2250 + /* The following restriction comes from ITU-T Rec. H.265 spec */
2251 + if (p_hdr10_mastering->max_display_mastering_luminance ==
2252 + V4L2_HDR10_MASTERING_MAX_LUMA_LOW &&
2253 + p_hdr10_mastering->min_display_mastering_luminance ==
2254 + V4L2_HDR10_MASTERING_MIN_LUMA_HIGH)
2255 + return -EINVAL;
2256 +
2257 + break;
2258 +
2259 + case V4L2_CTRL_TYPE_AREA:
2260 + area = p;
2261 + if (!area->width || !area->height)
2262 + return -EINVAL;
2263 + break;
2264 +
2265 + default:
2266 + return -EINVAL;
2267 + }
2268 +
2269 + return 0;
2270 +}
2271 +
2272 +static int std_validate(const struct v4l2_ctrl *ctrl, u32 idx,
2273 + union v4l2_ctrl_ptr ptr)
2274 +{
2275 + size_t len;
2276 + u64 offset;
2277 + s64 val;
2278 +
2279 + switch ((u32)ctrl->type) {
2280 + case V4L2_CTRL_TYPE_INTEGER:
2281 + return ROUND_TO_RANGE(ptr.p_s32[idx], u32, ctrl);
2282 + case V4L2_CTRL_TYPE_INTEGER64:
2283 + /*
2284 + * We can't use the ROUND_TO_RANGE define here due to
2285 + * the u64 divide that needs special care.
2286 + */
2287 + val = ptr.p_s64[idx];
2288 + if (ctrl->maximum >= 0 && val >= ctrl->maximum - (s64)(ctrl->step / 2))
2289 + val = ctrl->maximum;
2290 + else
2291 + val += (s64)(ctrl->step / 2);
2292 + val = clamp_t(s64, val, ctrl->minimum, ctrl->maximum);
2293 + offset = val - ctrl->minimum;
2294 + do_div(offset, ctrl->step);
2295 + ptr.p_s64[idx] = ctrl->minimum + offset * ctrl->step;
2296 + return 0;
2297 + case V4L2_CTRL_TYPE_U8:
2298 + return ROUND_TO_RANGE(ptr.p_u8[idx], u8, ctrl);
2299 + case V4L2_CTRL_TYPE_U16:
2300 + return ROUND_TO_RANGE(ptr.p_u16[idx], u16, ctrl);
2301 + case V4L2_CTRL_TYPE_U32:
2302 + return ROUND_TO_RANGE(ptr.p_u32[idx], u32, ctrl);
2303 +
2304 + case V4L2_CTRL_TYPE_BOOLEAN:
2305 + ptr.p_s32[idx] = !!ptr.p_s32[idx];
2306 + return 0;
2307 +
2308 + case V4L2_CTRL_TYPE_MENU:
2309 + case V4L2_CTRL_TYPE_INTEGER_MENU:
2310 + if (ptr.p_s32[idx] < ctrl->minimum || ptr.p_s32[idx] > ctrl->maximum)
2311 + return -ERANGE;
2312 + if (ptr.p_s32[idx] < BITS_PER_LONG_LONG &&
2313 + (ctrl->menu_skip_mask & BIT_ULL(ptr.p_s32[idx])))
2314 + return -EINVAL;
2315 + if (ctrl->type == V4L2_CTRL_TYPE_MENU &&
2316 + ctrl->qmenu[ptr.p_s32[idx]][0] == '\0')
2317 + return -EINVAL;
2318 + return 0;
2319 +
2320 + case V4L2_CTRL_TYPE_BITMASK:
2321 + ptr.p_s32[idx] &= ctrl->maximum;
2322 + return 0;
2323 +
2324 + case V4L2_CTRL_TYPE_BUTTON:
2325 + case V4L2_CTRL_TYPE_CTRL_CLASS:
2326 + ptr.p_s32[idx] = 0;
2327 + return 0;
2328 +
2329 + case V4L2_CTRL_TYPE_STRING:
2330 + idx *= ctrl->elem_size;
2331 + len = strlen(ptr.p_char + idx);
2332 + if (len < ctrl->minimum)
2333 + return -ERANGE;
2334 + if ((len - (u32)ctrl->minimum) % (u32)ctrl->step)
2335 + return -ERANGE;
2336 + return 0;
2337 +
2338 + default:
2339 + return std_validate_compound(ctrl, idx, ptr);
2340 + }
2341 +}
2342 +
2343 +static const struct v4l2_ctrl_type_ops std_type_ops = {
2344 + .equal = std_equal,
2345 + .init = std_init,
2346 + .log = std_log,
2347 + .validate = std_validate,
2348 +};
2349 +
2350 +/* Helper function: copy the given control value back to the caller */
2351 +static int ptr_to_user(struct v4l2_ext_control *c,
2352 + struct v4l2_ctrl *ctrl,
2353 + union v4l2_ctrl_ptr ptr)
2354 +{
2355 + u32 len;
2356 +
2357 + if (ctrl->is_ptr && !ctrl->is_string)
2358 + return copy_to_user(c->ptr, ptr.p_const, c->size) ?
2359 + -EFAULT : 0;
2360 +
2361 + switch (ctrl->type) {
2362 + case V4L2_CTRL_TYPE_STRING:
2363 + len = strlen(ptr.p_char);
2364 + if (c->size < len + 1) {
2365 + c->size = ctrl->elem_size;
2366 + return -ENOSPC;
2367 + }
2368 + return copy_to_user(c->string, ptr.p_char, len + 1) ?
2369 + -EFAULT : 0;
2370 + case V4L2_CTRL_TYPE_INTEGER64:
2371 + c->value64 = *ptr.p_s64;
2372 + break;
2373 + default:
2374 + c->value = *ptr.p_s32;
2375 + break;
2376 + }
2377 + return 0;
2378 +}
2379 +
2380 +/* Helper function: copy the current control value back to the caller */
2381 +static int cur_to_user(struct v4l2_ext_control *c,
2382 + struct v4l2_ctrl *ctrl)
2383 +{
2384 + return ptr_to_user(c, ctrl, ctrl->p_cur);
2385 +}
2386 +
2387 +/* Helper function: copy the new control value back to the caller */
2388 +static int new_to_user(struct v4l2_ext_control *c,
2389 + struct v4l2_ctrl *ctrl)
2390 +{
2391 + return ptr_to_user(c, ctrl, ctrl->p_new);
2392 +}
2393 +
2394 +/* Helper function: copy the request value back to the caller */
2395 +static int req_to_user(struct v4l2_ext_control *c,
2396 + struct v4l2_ctrl_ref *ref)
2397 +{
2398 + return ptr_to_user(c, ref->ctrl, ref->p_req);
2399 +}
2400 +
2401 +/* Helper function: copy the initial control value back to the caller */
2402 +static int def_to_user(struct v4l2_ext_control *c, struct v4l2_ctrl *ctrl)
2403 +{
2404 + int idx;
2405 +
2406 + for (idx = 0; idx < ctrl->elems; idx++)
2407 + ctrl->type_ops->init(ctrl, idx, ctrl->p_new);
2408 +
2409 + return ptr_to_user(c, ctrl, ctrl->p_new);
2410 +}
2411 +
2412 +/* Helper function: copy the caller-provider value to the given control value */
2413 +static int user_to_ptr(struct v4l2_ext_control *c,
2414 + struct v4l2_ctrl *ctrl,
2415 + union v4l2_ctrl_ptr ptr)
2416 +{
2417 + int ret;
2418 + u32 size;
2419 +
2420 + ctrl->is_new = 1;
2421 + if (ctrl->is_ptr && !ctrl->is_string) {
2422 + unsigned idx;
2423 +
2424 + ret = copy_from_user(ptr.p, c->ptr, c->size) ? -EFAULT : 0;
2425 + if (ret || !ctrl->is_array)
2426 + return ret;
2427 + for (idx = c->size / ctrl->elem_size; idx < ctrl->elems; idx++)
2428 + ctrl->type_ops->init(ctrl, idx, ptr);
2429 + return 0;
2430 + }
2431 +
2432 + switch (ctrl->type) {
2433 + case V4L2_CTRL_TYPE_INTEGER64:
2434 + *ptr.p_s64 = c->value64;
2435 + break;
2436 + case V4L2_CTRL_TYPE_STRING:
2437 + size = c->size;
2438 + if (size == 0)
2439 + return -ERANGE;
2440 + if (size > ctrl->maximum + 1)
2441 + size = ctrl->maximum + 1;
2442 + ret = copy_from_user(ptr.p_char, c->string, size) ? -EFAULT : 0;
2443 + if (!ret) {
2444 + char last = ptr.p_char[size - 1];
2445 +
2446 + ptr.p_char[size - 1] = 0;
2447 + /* If the string was longer than ctrl->maximum,
2448 + then return an error. */
2449 + if (strlen(ptr.p_char) == ctrl->maximum && last)
2450 + return -ERANGE;
2451 + }
2452 + return ret;
2453 + default:
2454 + *ptr.p_s32 = c->value;
2455 + break;
2456 + }
2457 + return 0;
2458 +}
2459 +
2460 +/* Helper function: copy the caller-provider value as the new control value */
2461 +static int user_to_new(struct v4l2_ext_control *c,
2462 + struct v4l2_ctrl *ctrl)
2463 +{
2464 + return user_to_ptr(c, ctrl, ctrl->p_new);
2465 +}
2466 +
2467 +/* Copy the one value to another. */
2468 +static void ptr_to_ptr(struct v4l2_ctrl *ctrl,
2469 + union v4l2_ctrl_ptr from, union v4l2_ctrl_ptr to)
2470 +{
2471 + if (ctrl == NULL)
2472 + return;
2473 + memcpy(to.p, from.p_const, ctrl->elems * ctrl->elem_size);
2474 +}
2475 +
2476 +/* Copy the new value to the current value. */
2477 +static void new_to_cur(struct v4l2_fh *fh, struct v4l2_ctrl *ctrl, u32 ch_flags)
2478 +{
2479 + bool changed;
2480 +
2481 + if (ctrl == NULL)
2482 + return;
2483 +
2484 + /* has_changed is set by cluster_changed */
2485 + changed = ctrl->has_changed;
2486 + if (changed)
2487 + ptr_to_ptr(ctrl, ctrl->p_new, ctrl->p_cur);
2488 +
2489 + if (ch_flags & V4L2_EVENT_CTRL_CH_FLAGS) {
2490 + /* Note: CH_FLAGS is only set for auto clusters. */
2491 + ctrl->flags &=
2492 + ~(V4L2_CTRL_FLAG_INACTIVE | V4L2_CTRL_FLAG_VOLATILE);
2493 + if (!is_cur_manual(ctrl->cluster[0])) {
2494 + ctrl->flags |= V4L2_CTRL_FLAG_INACTIVE;
2495 + if (ctrl->cluster[0]->has_volatiles)
2496 + ctrl->flags |= V4L2_CTRL_FLAG_VOLATILE;
2497 + }
2498 + fh = NULL;
2499 + }
2500 + if (changed || ch_flags) {
2501 + /* If a control was changed that was not one of the controls
2502 + modified by the application, then send the event to all. */
2503 + if (!ctrl->is_new)
2504 + fh = NULL;
2505 + send_event(fh, ctrl,
2506 + (changed ? V4L2_EVENT_CTRL_CH_VALUE : 0) | ch_flags);
2507 + if (ctrl->call_notify && changed && ctrl->handler->notify)
2508 + ctrl->handler->notify(ctrl, ctrl->handler->notify_priv);
2509 + }
2510 +}
2511 +
2512 +/* Copy the current value to the new value */
2513 +static void cur_to_new(struct v4l2_ctrl *ctrl)
2514 +{
2515 + if (ctrl == NULL)
2516 + return;
2517 + ptr_to_ptr(ctrl, ctrl->p_cur, ctrl->p_new);
2518 +}
2519 +
2520 +/* Copy the new value to the request value */
2521 +static void new_to_req(struct v4l2_ctrl_ref *ref)
2522 +{
2523 + if (!ref)
2524 + return;
2525 + ptr_to_ptr(ref->ctrl, ref->ctrl->p_new, ref->p_req);
2526 + ref->valid_p_req = true;
2527 +}
2528 +
2529 +/* Copy the current value to the request value */
2530 +static void cur_to_req(struct v4l2_ctrl_ref *ref)
2531 +{
2532 + if (!ref)
2533 + return;
2534 + ptr_to_ptr(ref->ctrl, ref->ctrl->p_cur, ref->p_req);
2535 + ref->valid_p_req = true;
2536 +}
2537 +
2538 +/* Copy the request value to the new value */
2539 +static void req_to_new(struct v4l2_ctrl_ref *ref)
2540 +{
2541 + if (!ref)
2542 + return;
2543 + if (ref->valid_p_req)
2544 + ptr_to_ptr(ref->ctrl, ref->p_req, ref->ctrl->p_new);
2545 + else
2546 + ptr_to_ptr(ref->ctrl, ref->ctrl->p_cur, ref->ctrl->p_new);
2547 +}
2548 +
2549 +/* Return non-zero if one or more of the controls in the cluster has a new
2550 + value that differs from the current value. */
2551 +static int cluster_changed(struct v4l2_ctrl *master)
2552 +{
2553 + bool changed = false;
2554 + unsigned idx;
2555 + int i;
2556 +
2557 + for (i = 0; i < master->ncontrols; i++) {
2558 + struct v4l2_ctrl *ctrl = master->cluster[i];
2559 + bool ctrl_changed = false;
2560 +
2561 + if (ctrl == NULL)
2562 + continue;
2563 +
2564 + if (ctrl->flags & V4L2_CTRL_FLAG_EXECUTE_ON_WRITE)
2565 + changed = ctrl_changed = true;
2566 +
2567 + /*
2568 + * Set has_changed to false to avoid generating
2569 + * the event V4L2_EVENT_CTRL_CH_VALUE
2570 + */
2571 + if (ctrl->flags & V4L2_CTRL_FLAG_VOLATILE) {
2572 + ctrl->has_changed = false;
2573 + continue;
2574 + }
2575 +
2576 + for (idx = 0; !ctrl_changed && idx < ctrl->elems; idx++)
2577 + ctrl_changed = !ctrl->type_ops->equal(ctrl, idx,
2578 + ctrl->p_cur, ctrl->p_new);
2579 + ctrl->has_changed = ctrl_changed;
2580 + changed |= ctrl->has_changed;
2581 + }
2582 + return changed;
2583 +}
2584 +
2585 +/* Control range checking */
2586 +static int check_range(enum v4l2_ctrl_type type,
2587 + s64 min, s64 max, u64 step, s64 def)
2588 +{
2589 + switch (type) {
2590 + case V4L2_CTRL_TYPE_BOOLEAN:
2591 + if (step != 1 || max > 1 || min < 0)
2592 + return -ERANGE;
2593 + fallthrough;
2594 + case V4L2_CTRL_TYPE_U8:
2595 + case V4L2_CTRL_TYPE_U16:
2596 + case V4L2_CTRL_TYPE_U32:
2597 + case V4L2_CTRL_TYPE_INTEGER:
2598 + case V4L2_CTRL_TYPE_INTEGER64:
2599 + if (step == 0 || min > max || def < min || def > max)
2600 + return -ERANGE;
2601 + return 0;
2602 + case V4L2_CTRL_TYPE_BITMASK:
2603 + if (step || min || !max || (def & ~max))
2604 + return -ERANGE;
2605 + return 0;
2606 + case V4L2_CTRL_TYPE_MENU:
2607 + case V4L2_CTRL_TYPE_INTEGER_MENU:
2608 + if (min > max || def < min || def > max)
2609 + return -ERANGE;
2610 + /* Note: step == menu_skip_mask for menu controls.
2611 + So here we check if the default value is masked out. */
2612 + if (step && ((1 << def) & step))
2613 + return -EINVAL;
2614 + return 0;
2615 + case V4L2_CTRL_TYPE_STRING:
2616 + if (min > max || min < 0 || step < 1 || def)
2617 + return -ERANGE;
2618 + return 0;
2619 + default:
2620 + return 0;
2621 + }
2622 +}
2623 +
2624 +/* Validate a new control */
2625 +static int validate_new(const struct v4l2_ctrl *ctrl, union v4l2_ctrl_ptr p_new)
2626 +{
2627 + unsigned idx;
2628 + int err = 0;
2629 +
2630 + for (idx = 0; !err && idx < ctrl->elems; idx++)
2631 + err = ctrl->type_ops->validate(ctrl, idx, p_new);
2632 + return err;
2633 +}
2634 +
2635 +static inline u32 node2id(struct list_head *node)
2636 +{
2637 + return list_entry(node, struct v4l2_ctrl_ref, node)->ctrl->id;
2638 +}
2639 +
2640 +/* Set the handler's error code if it wasn't set earlier already */
2641 +static inline int handler_set_err(struct v4l2_ctrl_handler *hdl, int err)
2642 +{
2643 + if (hdl->error == 0)
2644 + hdl->error = err;
2645 + return err;
2646 +}
2647 +
2648 +/* Initialize the handler */
2649 +int v4l2_ctrl_handler_init_class(struct v4l2_ctrl_handler *hdl,
2650 + unsigned nr_of_controls_hint,
2651 + struct lock_class_key *key, const char *name)
2652 +{
2653 + mutex_init(&hdl->_lock);
2654 + hdl->lock = &hdl->_lock;
2655 + lockdep_set_class_and_name(hdl->lock, key, name);
2656 + INIT_LIST_HEAD(&hdl->ctrls);
2657 + INIT_LIST_HEAD(&hdl->ctrl_refs);
2658 + INIT_LIST_HEAD(&hdl->requests);
2659 + INIT_LIST_HEAD(&hdl->requests_queued);
2660 + hdl->request_is_queued = false;
2661 + hdl->nr_of_buckets = 1 + nr_of_controls_hint / 8;
2662 + hdl->buckets = kvmalloc_array(hdl->nr_of_buckets,
2663 + sizeof(hdl->buckets[0]),
2664 + GFP_KERNEL | __GFP_ZERO);
2665 + hdl->error = hdl->buckets ? 0 : -ENOMEM;
2666 + media_request_object_init(&hdl->req_obj);
2667 + return hdl->error;
2668 +}
2669 +EXPORT_SYMBOL(v4l2_ctrl_handler_init_class);
2670 +
2671 +/* Free all controls and control refs */
2672 +void v4l2_ctrl_handler_free(struct v4l2_ctrl_handler *hdl)
2673 +{
2674 + struct v4l2_ctrl_ref *ref, *next_ref;
2675 + struct v4l2_ctrl *ctrl, *next_ctrl;
2676 + struct v4l2_subscribed_event *sev, *next_sev;
2677 +
2678 + if (hdl == NULL || hdl->buckets == NULL)
2679 + return;
2680 +
2681 + /*
2682 + * If the main handler is freed and it is used by handler objects in
2683 + * outstanding requests, then unbind and put those objects before
2684 + * freeing the main handler.
2685 + *
2686 + * The main handler can be identified by having a NULL ops pointer in
2687 + * the request object.
2688 + */
2689 + if (!hdl->req_obj.ops && !list_empty(&hdl->requests)) {
2690 + struct v4l2_ctrl_handler *req, *next_req;
2691 +
2692 + list_for_each_entry_safe(req, next_req, &hdl->requests, requests) {
2693 + media_request_object_unbind(&req->req_obj);
2694 + media_request_object_put(&req->req_obj);
2695 + }
2696 + }
2697 + mutex_lock(hdl->lock);
2698 + /* Free all nodes */
2699 + list_for_each_entry_safe(ref, next_ref, &hdl->ctrl_refs, node) {
2700 + list_del(&ref->node);
2701 + kfree(ref);
2702 + }
2703 + /* Free all controls owned by the handler */
2704 + list_for_each_entry_safe(ctrl, next_ctrl, &hdl->ctrls, node) {
2705 + list_del(&ctrl->node);
2706 + list_for_each_entry_safe(sev, next_sev, &ctrl->ev_subs, node)
2707 + list_del(&sev->node);
2708 + kvfree(ctrl);
2709 + }
2710 + kvfree(hdl->buckets);
2711 + hdl->buckets = NULL;
2712 + hdl->cached = NULL;
2713 + hdl->error = 0;
2714 + mutex_unlock(hdl->lock);
2715 + mutex_destroy(&hdl->_lock);
2716 +}
2717 +EXPORT_SYMBOL(v4l2_ctrl_handler_free);
2718 +
2719 +/* For backwards compatibility: V4L2_CID_PRIVATE_BASE should no longer
2720 + be used except in G_CTRL, S_CTRL, QUERYCTRL and QUERYMENU when dealing
2721 + with applications that do not use the NEXT_CTRL flag.
2722 +
2723 + We just find the n-th private user control. It's O(N), but that should not
2724 + be an issue in this particular case. */
2725 +static struct v4l2_ctrl_ref *find_private_ref(
2726 + struct v4l2_ctrl_handler *hdl, u32 id)
2727 +{
2728 + struct v4l2_ctrl_ref *ref;
2729 +
2730 + id -= V4L2_CID_PRIVATE_BASE;
2731 + list_for_each_entry(ref, &hdl->ctrl_refs, node) {
2732 + /* Search for private user controls that are compatible with
2733 + VIDIOC_G/S_CTRL. */
2734 + if (V4L2_CTRL_ID2WHICH(ref->ctrl->id) == V4L2_CTRL_CLASS_USER &&
2735 + V4L2_CTRL_DRIVER_PRIV(ref->ctrl->id)) {
2736 + if (!ref->ctrl->is_int)
2737 + continue;
2738 + if (id == 0)
2739 + return ref;
2740 + id--;
2741 + }
2742 + }
2743 + return NULL;
2744 +}
2745 +
2746 +/* Find a control with the given ID. */
2747 +static struct v4l2_ctrl_ref *find_ref(struct v4l2_ctrl_handler *hdl, u32 id)
2748 +{
2749 + struct v4l2_ctrl_ref *ref;
2750 + int bucket;
2751 +
2752 + id &= V4L2_CTRL_ID_MASK;
2753 +
2754 + /* Old-style private controls need special handling */
2755 + if (id >= V4L2_CID_PRIVATE_BASE)
2756 + return find_private_ref(hdl, id);
2757 + bucket = id % hdl->nr_of_buckets;
2758 +
2759 + /* Simple optimization: cache the last control found */
2760 + if (hdl->cached && hdl->cached->ctrl->id == id)
2761 + return hdl->cached;
2762 +
2763 + /* Not in cache, search the hash */
2764 + ref = hdl->buckets ? hdl->buckets[bucket] : NULL;
2765 + while (ref && ref->ctrl->id != id)
2766 + ref = ref->next;
2767 +
2768 + if (ref)
2769 + hdl->cached = ref; /* cache it! */
2770 + return ref;
2771 +}
2772 +
2773 +/* Find a control with the given ID. Take the handler's lock first. */
2774 +static struct v4l2_ctrl_ref *find_ref_lock(
2775 + struct v4l2_ctrl_handler *hdl, u32 id)
2776 +{
2777 + struct v4l2_ctrl_ref *ref = NULL;
2778 +
2779 + if (hdl) {
2780 + mutex_lock(hdl->lock);
2781 + ref = find_ref(hdl, id);
2782 + mutex_unlock(hdl->lock);
2783 + }
2784 + return ref;
2785 +}
2786 +
2787 +/* Find a control with the given ID. */
2788 +struct v4l2_ctrl *v4l2_ctrl_find(struct v4l2_ctrl_handler *hdl, u32 id)
2789 +{
2790 + struct v4l2_ctrl_ref *ref = find_ref_lock(hdl, id);
2791 +
2792 + return ref ? ref->ctrl : NULL;
2793 +}
2794 +EXPORT_SYMBOL(v4l2_ctrl_find);
2795 +
2796 +/* Allocate a new v4l2_ctrl_ref and hook it into the handler. */
2797 +static int handler_new_ref(struct v4l2_ctrl_handler *hdl,
2798 + struct v4l2_ctrl *ctrl,
2799 + struct v4l2_ctrl_ref **ctrl_ref,
2800 + bool from_other_dev, bool allocate_req)
2801 +{
2802 + struct v4l2_ctrl_ref *ref;
2803 + struct v4l2_ctrl_ref *new_ref;
2804 + u32 id = ctrl->id;
2805 + u32 class_ctrl = V4L2_CTRL_ID2WHICH(id) | 1;
2806 + int bucket = id % hdl->nr_of_buckets; /* which bucket to use */
2807 + unsigned int size_extra_req = 0;
2808 +
2809 + if (ctrl_ref)
2810 + *ctrl_ref = NULL;
2811 +
2812 + /*
2813 + * Automatically add the control class if it is not yet present and
2814 + * the new control is not a compound control.
2815 + */
2816 + if (ctrl->type < V4L2_CTRL_COMPOUND_TYPES &&
2817 + id != class_ctrl && find_ref_lock(hdl, class_ctrl) == NULL)
2818 + if (!v4l2_ctrl_new_std(hdl, NULL, class_ctrl, 0, 0, 0, 0))
2819 + return hdl->error;
2820 +
2821 + if (hdl->error)
2822 + return hdl->error;
2823 +
2824 + if (allocate_req)
2825 + size_extra_req = ctrl->elems * ctrl->elem_size;
2826 + new_ref = kzalloc(sizeof(*new_ref) + size_extra_req, GFP_KERNEL);
2827 + if (!new_ref)
2828 + return handler_set_err(hdl, -ENOMEM);
2829 + new_ref->ctrl = ctrl;
2830 + new_ref->from_other_dev = from_other_dev;
2831 + if (size_extra_req)
2832 + new_ref->p_req.p = &new_ref[1];
2833 +
2834 + INIT_LIST_HEAD(&new_ref->node);
2835 +
2836 + mutex_lock(hdl->lock);
2837 +
2838 + /* Add immediately at the end of the list if the list is empty, or if
2839 + the last element in the list has a lower ID.
2840 + This ensures that when elements are added in ascending order the
2841 + insertion is an O(1) operation. */
2842 + if (list_empty(&hdl->ctrl_refs) || id > node2id(hdl->ctrl_refs.prev)) {
2843 + list_add_tail(&new_ref->node, &hdl->ctrl_refs);
2844 + goto insert_in_hash;
2845 + }
2846 +
2847 + /* Find insert position in sorted list */
2848 + list_for_each_entry(ref, &hdl->ctrl_refs, node) {
2849 + if (ref->ctrl->id < id)
2850 + continue;
2851 + /* Don't add duplicates */
2852 + if (ref->ctrl->id == id) {
2853 + kfree(new_ref);
2854 + goto unlock;
2855 + }
2856 + list_add(&new_ref->node, ref->node.prev);
2857 + break;
2858 + }
2859 +
2860 +insert_in_hash:
2861 + /* Insert the control node in the hash */
2862 + new_ref->next = hdl->buckets[bucket];
2863 + hdl->buckets[bucket] = new_ref;
2864 + if (ctrl_ref)
2865 + *ctrl_ref = new_ref;
2866 + if (ctrl->handler == hdl) {
2867 + /* By default each control starts in a cluster of its own.
2868 + * new_ref->ctrl is basically a cluster array with one
2869 + * element, so that's perfect to use as the cluster pointer.
2870 + * But only do this for the handler that owns the control.
2871 + */
2872 + ctrl->cluster = &new_ref->ctrl;
2873 + ctrl->ncontrols = 1;
2874 + }
2875 +
2876 +unlock:
2877 + mutex_unlock(hdl->lock);
2878 + return 0;
2879 +}
2880 +
2881 +/* Add a new control */
2882 +static struct v4l2_ctrl *v4l2_ctrl_new(struct v4l2_ctrl_handler *hdl,
2883 + const struct v4l2_ctrl_ops *ops,
2884 + const struct v4l2_ctrl_type_ops *type_ops,
2885 + u32 id, const char *name, enum v4l2_ctrl_type type,
2886 + s64 min, s64 max, u64 step, s64 def,
2887 + const u32 dims[V4L2_CTRL_MAX_DIMS], u32 elem_size,
2888 + u32 flags, const char * const *qmenu,
2889 + const s64 *qmenu_int, const union v4l2_ctrl_ptr p_def,
2890 + void *priv)
2891 +{
2892 + struct v4l2_ctrl *ctrl;
2893 + unsigned sz_extra;
2894 + unsigned nr_of_dims = 0;
2895 + unsigned elems = 1;
2896 + bool is_array;
2897 + unsigned tot_ctrl_size;
2898 + unsigned idx;
2899 + void *data;
2900 + int err;
2901 +
2902 + if (hdl->error)
2903 + return NULL;
2904 +
2905 + while (dims && dims[nr_of_dims]) {
2906 + elems *= dims[nr_of_dims];
2907 + nr_of_dims++;
2908 + if (nr_of_dims == V4L2_CTRL_MAX_DIMS)
2909 + break;
2910 + }
2911 + is_array = nr_of_dims > 0;
2912 +
2913 + /* Prefill elem_size for all types handled by std_type_ops */
2914 + switch ((u32)type) {
2915 + case V4L2_CTRL_TYPE_INTEGER64:
2916 + elem_size = sizeof(s64);
2917 + break;
2918 + case V4L2_CTRL_TYPE_STRING:
2919 + elem_size = max + 1;
2920 + break;
2921 + case V4L2_CTRL_TYPE_U8:
2922 + elem_size = sizeof(u8);
2923 + break;
2924 + case V4L2_CTRL_TYPE_U16:
2925 + elem_size = sizeof(u16);
2926 + break;
2927 + case V4L2_CTRL_TYPE_U32:
2928 + elem_size = sizeof(u32);
2929 + break;
2930 + case V4L2_CTRL_TYPE_MPEG2_SLICE_PARAMS:
2931 + elem_size = sizeof(struct v4l2_ctrl_mpeg2_slice_params);
2932 + break;
2933 + case V4L2_CTRL_TYPE_MPEG2_QUANTIZATION:
2934 + elem_size = sizeof(struct v4l2_ctrl_mpeg2_quantization);
2935 + break;
2936 + case V4L2_CTRL_TYPE_FWHT_PARAMS:
2937 + elem_size = sizeof(struct v4l2_ctrl_fwht_params);
2938 + break;
2939 + case V4L2_CTRL_TYPE_H264_SPS:
2940 + elem_size = sizeof(struct v4l2_ctrl_h264_sps);
2941 + break;
2942 + case V4L2_CTRL_TYPE_H264_PPS:
2943 + elem_size = sizeof(struct v4l2_ctrl_h264_pps);
2944 + break;
2945 + case V4L2_CTRL_TYPE_H264_SCALING_MATRIX:
2946 + elem_size = sizeof(struct v4l2_ctrl_h264_scaling_matrix);
2947 + break;
2948 + case V4L2_CTRL_TYPE_H264_SLICE_PARAMS:
2949 + elem_size = sizeof(struct v4l2_ctrl_h264_slice_params);
2950 + break;
2951 + case V4L2_CTRL_TYPE_H264_DECODE_PARAMS:
2952 + elem_size = sizeof(struct v4l2_ctrl_h264_decode_params);
2953 + break;
2954 + case V4L2_CTRL_TYPE_H264_PRED_WEIGHTS:
2955 + elem_size = sizeof(struct v4l2_ctrl_h264_pred_weights);
2956 + break;
2957 + case V4L2_CTRL_TYPE_VP8_FRAME:
2958 + elem_size = sizeof(struct v4l2_ctrl_vp8_frame);
2959 + break;
2960 + case V4L2_CTRL_TYPE_HEVC_SPS:
2961 + elem_size = sizeof(struct v4l2_ctrl_hevc_sps);
2962 + break;
2963 + case V4L2_CTRL_TYPE_HEVC_PPS:
2964 + elem_size = sizeof(struct v4l2_ctrl_hevc_pps);
2965 + break;
2966 + case V4L2_CTRL_TYPE_HEVC_SLICE_PARAMS:
2967 + elem_size = sizeof(struct v4l2_ctrl_hevc_slice_params);
2968 + break;
2969 + case V4L2_CTRL_TYPE_HDR10_CLL_INFO:
2970 + elem_size = sizeof(struct v4l2_ctrl_hdr10_cll_info);
2971 + break;
2972 + case V4L2_CTRL_TYPE_HDR10_MASTERING_DISPLAY:
2973 + elem_size = sizeof(struct v4l2_ctrl_hdr10_mastering_display);
2974 + break;
2975 + case V4L2_CTRL_TYPE_AREA:
2976 + elem_size = sizeof(struct v4l2_area);
2977 + break;
2978 + default:
2979 + if (type < V4L2_CTRL_COMPOUND_TYPES)
2980 + elem_size = sizeof(s32);
2981 + break;
2982 + }
2983 + tot_ctrl_size = elem_size * elems;
2984 +
2985 + /* Sanity checks */
2986 + if (id == 0 || name == NULL || !elem_size ||
2987 + id >= V4L2_CID_PRIVATE_BASE ||
2988 + (type == V4L2_CTRL_TYPE_MENU && qmenu == NULL) ||
2989 + (type == V4L2_CTRL_TYPE_INTEGER_MENU && qmenu_int == NULL)) {
2990 + handler_set_err(hdl, -ERANGE);
2991 + return NULL;
2992 + }
2993 + err = check_range(type, min, max, step, def);
2994 + if (err) {
2995 + handler_set_err(hdl, err);
2996 + return NULL;
2997 + }
2998 + if (is_array &&
2999 + (type == V4L2_CTRL_TYPE_BUTTON ||
3000 + type == V4L2_CTRL_TYPE_CTRL_CLASS)) {
3001 + handler_set_err(hdl, -EINVAL);
3002 + return NULL;
3003 + }
3004 +
3005 + sz_extra = 0;
3006 + if (type == V4L2_CTRL_TYPE_BUTTON)
3007 + flags |= V4L2_CTRL_FLAG_WRITE_ONLY |
3008 + V4L2_CTRL_FLAG_EXECUTE_ON_WRITE;
3009 + else if (type == V4L2_CTRL_TYPE_CTRL_CLASS)
3010 + flags |= V4L2_CTRL_FLAG_READ_ONLY;
3011 + else if (type == V4L2_CTRL_TYPE_INTEGER64 ||
3012 + type == V4L2_CTRL_TYPE_STRING ||
3013 + type >= V4L2_CTRL_COMPOUND_TYPES ||
3014 + is_array)
3015 + sz_extra += 2 * tot_ctrl_size;
3016 +
3017 + if (type >= V4L2_CTRL_COMPOUND_TYPES && p_def.p_const)
3018 + sz_extra += elem_size;
3019 +
3020 + ctrl = kvzalloc(sizeof(*ctrl) + sz_extra, GFP_KERNEL);
3021 + if (ctrl == NULL) {
3022 + handler_set_err(hdl, -ENOMEM);
3023 + return NULL;
3024 + }
3025 +
3026 + INIT_LIST_HEAD(&ctrl->node);
3027 + INIT_LIST_HEAD(&ctrl->ev_subs);
3028 + ctrl->handler = hdl;
3029 + ctrl->ops = ops;
3030 + ctrl->type_ops = type_ops ? type_ops : &std_type_ops;
3031 + ctrl->id = id;
3032 + ctrl->name = name;
3033 + ctrl->type = type;
3034 + ctrl->flags = flags;
3035 + ctrl->minimum = min;
3036 + ctrl->maximum = max;
3037 + ctrl->step = step;
3038 + ctrl->default_value = def;
3039 + ctrl->is_string = !is_array && type == V4L2_CTRL_TYPE_STRING;
3040 + ctrl->is_ptr = is_array || type >= V4L2_CTRL_COMPOUND_TYPES || ctrl->is_string;
3041 + ctrl->is_int = !ctrl->is_ptr && type != V4L2_CTRL_TYPE_INTEGER64;
3042 + ctrl->is_array = is_array;
3043 + ctrl->elems = elems;
3044 + ctrl->nr_of_dims = nr_of_dims;
3045 + if (nr_of_dims)
3046 + memcpy(ctrl->dims, dims, nr_of_dims * sizeof(dims[0]));
3047 + ctrl->elem_size = elem_size;
3048 + if (type == V4L2_CTRL_TYPE_MENU)
3049 + ctrl->qmenu = qmenu;
3050 + else if (type == V4L2_CTRL_TYPE_INTEGER_MENU)
3051 + ctrl->qmenu_int = qmenu_int;
3052 + ctrl->priv = priv;
3053 + ctrl->cur.val = ctrl->val = def;
3054 + data = &ctrl[1];
3055 +
3056 + if (!ctrl->is_int) {
3057 + ctrl->p_new.p = data;
3058 + ctrl->p_cur.p = data + tot_ctrl_size;
3059 + } else {
3060 + ctrl->p_new.p = &ctrl->val;
3061 + ctrl->p_cur.p = &ctrl->cur.val;
3062 + }
3063 +
3064 + if (type >= V4L2_CTRL_COMPOUND_TYPES && p_def.p_const) {
3065 + ctrl->p_def.p = ctrl->p_cur.p + tot_ctrl_size;
3066 + memcpy(ctrl->p_def.p, p_def.p_const, elem_size);
3067 + }
3068 +
3069 + for (idx = 0; idx < elems; idx++) {
3070 + ctrl->type_ops->init(ctrl, idx, ctrl->p_cur);
3071 + ctrl->type_ops->init(ctrl, idx, ctrl->p_new);
3072 + }
3073 +
3074 + if (handler_new_ref(hdl, ctrl, NULL, false, false)) {
3075 + kvfree(ctrl);
3076 + return NULL;
3077 + }
3078 + mutex_lock(hdl->lock);
3079 + list_add_tail(&ctrl->node, &hdl->ctrls);
3080 + mutex_unlock(hdl->lock);
3081 + return ctrl;
3082 +}
3083 +
3084 +struct v4l2_ctrl *v4l2_ctrl_new_custom(struct v4l2_ctrl_handler *hdl,
3085 + const struct v4l2_ctrl_config *cfg, void *priv)
3086 +{
3087 + bool is_menu;
3088 + struct v4l2_ctrl *ctrl;
3089 + const char *name = cfg->name;
3090 + const char * const *qmenu = cfg->qmenu;
3091 + const s64 *qmenu_int = cfg->qmenu_int;
3092 + enum v4l2_ctrl_type type = cfg->type;
3093 + u32 flags = cfg->flags;
3094 + s64 min = cfg->min;
3095 + s64 max = cfg->max;
3096 + u64 step = cfg->step;
3097 + s64 def = cfg->def;
3098 +
3099 + if (name == NULL)
3100 + v4l2_ctrl_fill(cfg->id, &name, &type, &min, &max, &step,
3101 + &def, &flags);
3102 +
3103 + is_menu = (type == V4L2_CTRL_TYPE_MENU ||
3104 + type == V4L2_CTRL_TYPE_INTEGER_MENU);
3105 + if (is_menu)
3106 + WARN_ON(step);
3107 + else
3108 + WARN_ON(cfg->menu_skip_mask);
3109 + if (type == V4L2_CTRL_TYPE_MENU && !qmenu) {
3110 + qmenu = v4l2_ctrl_get_menu(cfg->id);
3111 + } else if (type == V4L2_CTRL_TYPE_INTEGER_MENU && !qmenu_int) {
3112 + handler_set_err(hdl, -EINVAL);
3113 + return NULL;
3114 + }
3115 +
3116 + ctrl = v4l2_ctrl_new(hdl, cfg->ops, cfg->type_ops, cfg->id, name,
3117 + type, min, max,
3118 + is_menu ? cfg->menu_skip_mask : step, def,
3119 + cfg->dims, cfg->elem_size,
3120 + flags, qmenu, qmenu_int, cfg->p_def, priv);
3121 + if (ctrl)
3122 + ctrl->is_private = cfg->is_private;
3123 + return ctrl;
3124 +}
3125 +EXPORT_SYMBOL(v4l2_ctrl_new_custom);
3126 +
3127 +/* Helper function for standard non-menu controls */
3128 +struct v4l2_ctrl *v4l2_ctrl_new_std(struct v4l2_ctrl_handler *hdl,
3129 + const struct v4l2_ctrl_ops *ops,
3130 + u32 id, s64 min, s64 max, u64 step, s64 def)
3131 +{
3132 + const char *name;
3133 + enum v4l2_ctrl_type type;
3134 + u32 flags;
3135 +
3136 + v4l2_ctrl_fill(id, &name, &type, &min, &max, &step, &def, &flags);
3137 + if (type == V4L2_CTRL_TYPE_MENU ||
3138 + type == V4L2_CTRL_TYPE_INTEGER_MENU ||
3139 + type >= V4L2_CTRL_COMPOUND_TYPES) {
3140 + handler_set_err(hdl, -EINVAL);
3141 + return NULL;
3142 + }
3143 + return v4l2_ctrl_new(hdl, ops, NULL, id, name, type,
3144 + min, max, step, def, NULL, 0,
3145 + flags, NULL, NULL, ptr_null, NULL);
3146 +}
3147 +EXPORT_SYMBOL(v4l2_ctrl_new_std);
3148 +
3149 +/* Helper function for standard menu controls */
3150 +struct v4l2_ctrl *v4l2_ctrl_new_std_menu(struct v4l2_ctrl_handler *hdl,
3151 + const struct v4l2_ctrl_ops *ops,
3152 + u32 id, u8 _max, u64 mask, u8 _def)
3153 +{
3154 + const char * const *qmenu = NULL;
3155 + const s64 *qmenu_int = NULL;
3156 + unsigned int qmenu_int_len = 0;
3157 + const char *name;
3158 + enum v4l2_ctrl_type type;
3159 + s64 min;
3160 + s64 max = _max;
3161 + s64 def = _def;
3162 + u64 step;
3163 + u32 flags;
3164 +
3165 + v4l2_ctrl_fill(id, &name, &type, &min, &max, &step, &def, &flags);
3166 +
3167 + if (type == V4L2_CTRL_TYPE_MENU)
3168 + qmenu = v4l2_ctrl_get_menu(id);
3169 + else if (type == V4L2_CTRL_TYPE_INTEGER_MENU)
3170 + qmenu_int = v4l2_ctrl_get_int_menu(id, &qmenu_int_len);
3171 +
3172 + if ((!qmenu && !qmenu_int) || (qmenu_int && max > qmenu_int_len)) {
3173 + handler_set_err(hdl, -EINVAL);
3174 + return NULL;
3175 + }
3176 + return v4l2_ctrl_new(hdl, ops, NULL, id, name, type,
3177 + 0, max, mask, def, NULL, 0,
3178 + flags, qmenu, qmenu_int, ptr_null, NULL);
3179 +}
3180 +EXPORT_SYMBOL(v4l2_ctrl_new_std_menu);
3181 +
3182 +/* Helper function for standard menu controls with driver defined menu */
3183 +struct v4l2_ctrl *v4l2_ctrl_new_std_menu_items(struct v4l2_ctrl_handler *hdl,
3184 + const struct v4l2_ctrl_ops *ops, u32 id, u8 _max,
3185 + u64 mask, u8 _def, const char * const *qmenu)
3186 +{
3187 + enum v4l2_ctrl_type type;
3188 + const char *name;
3189 + u32 flags;
3190 + u64 step;
3191 + s64 min;
3192 + s64 max = _max;
3193 + s64 def = _def;
3194 +
3195 + /* v4l2_ctrl_new_std_menu_items() should only be called for
3196 + * standard controls without a standard menu.
3197 + */
3198 + if (v4l2_ctrl_get_menu(id)) {
3199 + handler_set_err(hdl, -EINVAL);
3200 + return NULL;
3201 + }
3202 +
3203 + v4l2_ctrl_fill(id, &name, &type, &min, &max, &step, &def, &flags);
3204 + if (type != V4L2_CTRL_TYPE_MENU || qmenu == NULL) {
3205 + handler_set_err(hdl, -EINVAL);
3206 + return NULL;
3207 + }
3208 + return v4l2_ctrl_new(hdl, ops, NULL, id, name, type,
3209 + 0, max, mask, def, NULL, 0,
3210 + flags, qmenu, NULL, ptr_null, NULL);
3211 +
3212 +}
3213 +EXPORT_SYMBOL(v4l2_ctrl_new_std_menu_items);
3214 +
3215 +/* Helper function for standard compound controls */
3216 +struct v4l2_ctrl *v4l2_ctrl_new_std_compound(struct v4l2_ctrl_handler *hdl,
3217 + const struct v4l2_ctrl_ops *ops, u32 id,
3218 + const union v4l2_ctrl_ptr p_def)
3219 +{
3220 + const char *name;
3221 + enum v4l2_ctrl_type type;
3222 + u32 flags;
3223 + s64 min, max, step, def;
3224 +
3225 + v4l2_ctrl_fill(id, &name, &type, &min, &max, &step, &def, &flags);
3226 + if (type < V4L2_CTRL_COMPOUND_TYPES) {
3227 + handler_set_err(hdl, -EINVAL);
3228 + return NULL;
3229 + }
3230 + return v4l2_ctrl_new(hdl, ops, NULL, id, name, type,
3231 + min, max, step, def, NULL, 0,
3232 + flags, NULL, NULL, p_def, NULL);
3233 +}
3234 +EXPORT_SYMBOL(v4l2_ctrl_new_std_compound);
3235 +
3236 +/* Helper function for standard integer menu controls */
3237 +struct v4l2_ctrl *v4l2_ctrl_new_int_menu(struct v4l2_ctrl_handler *hdl,
3238 + const struct v4l2_ctrl_ops *ops,
3239 + u32 id, u8 _max, u8 _def, const s64 *qmenu_int)
3240 +{
3241 + const char *name;
3242 + enum v4l2_ctrl_type type;
3243 + s64 min;
3244 + u64 step;
3245 + s64 max = _max;
3246 + s64 def = _def;
3247 + u32 flags;
3248 +
3249 + v4l2_ctrl_fill(id, &name, &type, &min, &max, &step, &def, &flags);
3250 + if (type != V4L2_CTRL_TYPE_INTEGER_MENU) {
3251 + handler_set_err(hdl, -EINVAL);
3252 + return NULL;
3253 + }
3254 + return v4l2_ctrl_new(hdl, ops, NULL, id, name, type,
3255 + 0, max, 0, def, NULL, 0,
3256 + flags, NULL, qmenu_int, ptr_null, NULL);
3257 +}
3258 +EXPORT_SYMBOL(v4l2_ctrl_new_int_menu);
3259 +
3260 +/* Add the controls from another handler to our own. */
3261 +int v4l2_ctrl_add_handler(struct v4l2_ctrl_handler *hdl,
3262 + struct v4l2_ctrl_handler *add,
3263 + bool (*filter)(const struct v4l2_ctrl *ctrl),
3264 + bool from_other_dev)
3265 +{
3266 + struct v4l2_ctrl_ref *ref;
3267 + int ret = 0;
3268 +
3269 + /* Do nothing if either handler is NULL or if they are the same */
3270 + if (!hdl || !add || hdl == add)
3271 + return 0;
3272 + if (hdl->error)
3273 + return hdl->error;
3274 + mutex_lock(add->lock);
3275 + list_for_each_entry(ref, &add->ctrl_refs, node) {
3276 + struct v4l2_ctrl *ctrl = ref->ctrl;
3277 +
3278 + /* Skip handler-private controls. */
3279 + if (ctrl->is_private)
3280 + continue;
3281 + /* And control classes */
3282 + if (ctrl->type == V4L2_CTRL_TYPE_CTRL_CLASS)
3283 + continue;
3284 + /* Filter any unwanted controls */
3285 + if (filter && !filter(ctrl))
3286 + continue;
3287 + ret = handler_new_ref(hdl, ctrl, NULL, from_other_dev, false);
3288 + if (ret)
3289 + break;
3290 + }
3291 + mutex_unlock(add->lock);
3292 + return ret;
3293 +}
3294 +EXPORT_SYMBOL(v4l2_ctrl_add_handler);
3295 +
3296 +bool v4l2_ctrl_radio_filter(const struct v4l2_ctrl *ctrl)
3297 +{
3298 + if (V4L2_CTRL_ID2WHICH(ctrl->id) == V4L2_CTRL_CLASS_FM_TX)
3299 + return true;
3300 + if (V4L2_CTRL_ID2WHICH(ctrl->id) == V4L2_CTRL_CLASS_FM_RX)
3301 + return true;
3302 + switch (ctrl->id) {
3303 + case V4L2_CID_AUDIO_MUTE:
3304 + case V4L2_CID_AUDIO_VOLUME:
3305 + case V4L2_CID_AUDIO_BALANCE:
3306 + case V4L2_CID_AUDIO_BASS:
3307 + case V4L2_CID_AUDIO_TREBLE:
3308 + case V4L2_CID_AUDIO_LOUDNESS:
3309 + return true;
3310 + default:
3311 + break;
3312 + }
3313 + return false;
3314 +}
3315 +EXPORT_SYMBOL(v4l2_ctrl_radio_filter);
3316 +
3317 +/* Cluster controls */
3318 +void v4l2_ctrl_cluster(unsigned ncontrols, struct v4l2_ctrl **controls)
3319 +{
3320 + bool has_volatiles = false;
3321 + int i;
3322 +
3323 + /* The first control is the master control and it must not be NULL */
3324 + if (WARN_ON(ncontrols == 0 || controls[0] == NULL))
3325 + return;
3326 +
3327 + for (i = 0; i < ncontrols; i++) {
3328 + if (controls[i]) {
3329 + controls[i]->cluster = controls;
3330 + controls[i]->ncontrols = ncontrols;
3331 + if (controls[i]->flags & V4L2_CTRL_FLAG_VOLATILE)
3332 + has_volatiles = true;
3333 + }
3334 + }
3335 + controls[0]->has_volatiles = has_volatiles;
3336 +}
3337 +EXPORT_SYMBOL(v4l2_ctrl_cluster);
3338 +
3339 +void v4l2_ctrl_auto_cluster(unsigned ncontrols, struct v4l2_ctrl **controls,
3340 + u8 manual_val, bool set_volatile)
3341 +{
3342 + struct v4l2_ctrl *master = controls[0];
3343 + u32 flag = 0;
3344 + int i;
3345 +
3346 + v4l2_ctrl_cluster(ncontrols, controls);
3347 + WARN_ON(ncontrols <= 1);
3348 + WARN_ON(manual_val < master->minimum || manual_val > master->maximum);
3349 + WARN_ON(set_volatile && !has_op(master, g_volatile_ctrl));
3350 + master->is_auto = true;
3351 + master->has_volatiles = set_volatile;
3352 + master->manual_mode_value = manual_val;
3353 + master->flags |= V4L2_CTRL_FLAG_UPDATE;
3354 +
3355 + if (!is_cur_manual(master))
3356 + flag = V4L2_CTRL_FLAG_INACTIVE |
3357 + (set_volatile ? V4L2_CTRL_FLAG_VOLATILE : 0);
3358 +
3359 + for (i = 1; i < ncontrols; i++)
3360 + if (controls[i])
3361 + controls[i]->flags |= flag;
3362 +}
3363 +EXPORT_SYMBOL(v4l2_ctrl_auto_cluster);
3364 +
3365 +/* Activate/deactivate a control. */
3366 +void v4l2_ctrl_activate(struct v4l2_ctrl *ctrl, bool active)
3367 +{
3368 + /* invert since the actual flag is called 'inactive' */
3369 + bool inactive = !active;
3370 + bool old;
3371 +
3372 + if (ctrl == NULL)
3373 + return;
3374 +
3375 + if (inactive)
3376 + /* set V4L2_CTRL_FLAG_INACTIVE */
3377 + old = test_and_set_bit(4, &ctrl->flags);
3378 + else
3379 + /* clear V4L2_CTRL_FLAG_INACTIVE */
3380 + old = test_and_clear_bit(4, &ctrl->flags);
3381 + if (old != inactive)
3382 + send_event(NULL, ctrl, V4L2_EVENT_CTRL_CH_FLAGS);
3383 +}
3384 +EXPORT_SYMBOL(v4l2_ctrl_activate);
3385 +
3386 +void __v4l2_ctrl_grab(struct v4l2_ctrl *ctrl, bool grabbed)
3387 +{
3388 + bool old;
3389 +
3390 + if (ctrl == NULL)
3391 + return;
3392 +
3393 + lockdep_assert_held(ctrl->handler->lock);
3394 +
3395 + if (grabbed)
3396 + /* set V4L2_CTRL_FLAG_GRABBED */
3397 + old = test_and_set_bit(1, &ctrl->flags);
3398 + else
3399 + /* clear V4L2_CTRL_FLAG_GRABBED */
3400 + old = test_and_clear_bit(1, &ctrl->flags);
3401 + if (old != grabbed)
3402 + send_event(NULL, ctrl, V4L2_EVENT_CTRL_CH_FLAGS);
3403 +}
3404 +EXPORT_SYMBOL(__v4l2_ctrl_grab);
3405 +
3406 +/* Log the control name and value */
3407 +static void log_ctrl(const struct v4l2_ctrl *ctrl,
3408 + const char *prefix, const char *colon)
3409 +{
3410 + if (ctrl->flags & (V4L2_CTRL_FLAG_DISABLED | V4L2_CTRL_FLAG_WRITE_ONLY))
3411 + return;
3412 + if (ctrl->type == V4L2_CTRL_TYPE_CTRL_CLASS)
3413 + return;
3414 +
3415 + pr_info("%s%s%s: ", prefix, colon, ctrl->name);
3416 +
3417 + ctrl->type_ops->log(ctrl);
3418 +
3419 + if (ctrl->flags & (V4L2_CTRL_FLAG_INACTIVE |
3420 + V4L2_CTRL_FLAG_GRABBED |
3421 + V4L2_CTRL_FLAG_VOLATILE)) {
3422 + if (ctrl->flags & V4L2_CTRL_FLAG_INACTIVE)
3423 + pr_cont(" inactive");
3424 + if (ctrl->flags & V4L2_CTRL_FLAG_GRABBED)
3425 + pr_cont(" grabbed");
3426 + if (ctrl->flags & V4L2_CTRL_FLAG_VOLATILE)
3427 + pr_cont(" volatile");
3428 + }
3429 + pr_cont("\n");
3430 +}
3431 +
3432 +/* Log all controls owned by the handler */
3433 +void v4l2_ctrl_handler_log_status(struct v4l2_ctrl_handler *hdl,
3434 + const char *prefix)
3435 +{
3436 + struct v4l2_ctrl *ctrl;
3437 + const char *colon = "";
3438 + int len;
3439 +
3440 + if (hdl == NULL)
3441 + return;
3442 + if (prefix == NULL)
3443 + prefix = "";
3444 + len = strlen(prefix);
3445 + if (len && prefix[len - 1] != ' ')
3446 + colon = ": ";
3447 + mutex_lock(hdl->lock);
3448 + list_for_each_entry(ctrl, &hdl->ctrls, node)
3449 + if (!(ctrl->flags & V4L2_CTRL_FLAG_DISABLED))
3450 + log_ctrl(ctrl, prefix, colon);
3451 + mutex_unlock(hdl->lock);
3452 +}
3453 +EXPORT_SYMBOL(v4l2_ctrl_handler_log_status);
3454 +
3455 +int v4l2_ctrl_subdev_log_status(struct v4l2_subdev *sd)
3456 +{
3457 + v4l2_ctrl_handler_log_status(sd->ctrl_handler, sd->name);
3458 + return 0;
3459 +}
3460 +EXPORT_SYMBOL(v4l2_ctrl_subdev_log_status);
3461 +
3462 +/* Call s_ctrl for all controls owned by the handler */
3463 +int __v4l2_ctrl_handler_setup(struct v4l2_ctrl_handler *hdl)
3464 +{
3465 + struct v4l2_ctrl *ctrl;
3466 + int ret = 0;
3467 +
3468 + if (hdl == NULL)
3469 + return 0;
3470 +
3471 + lockdep_assert_held(hdl->lock);
3472 +
3473 + list_for_each_entry(ctrl, &hdl->ctrls, node)
3474 + ctrl->done = false;
3475 +
3476 + list_for_each_entry(ctrl, &hdl->ctrls, node) {
3477 + struct v4l2_ctrl *master = ctrl->cluster[0];
3478 + int i;
3479 +
3480 + /* Skip if this control was already handled by a cluster. */
3481 + /* Skip button controls and read-only controls. */
3482 + if (ctrl->done || ctrl->type == V4L2_CTRL_TYPE_BUTTON ||
3483 + (ctrl->flags & V4L2_CTRL_FLAG_READ_ONLY))
3484 + continue;
3485 +
3486 + for (i = 0; i < master->ncontrols; i++) {
3487 + if (master->cluster[i]) {
3488 + cur_to_new(master->cluster[i]);
3489 + master->cluster[i]->is_new = 1;
3490 + master->cluster[i]->done = true;
3491 + }
3492 + }
3493 + ret = call_op(master, s_ctrl);
3494 + if (ret)
3495 + break;
3496 + }
3497 +
3498 + return ret;
3499 +}
3500 +EXPORT_SYMBOL_GPL(__v4l2_ctrl_handler_setup);
3501 +
3502 +int v4l2_ctrl_handler_setup(struct v4l2_ctrl_handler *hdl)
3503 +{
3504 + int ret;
3505 +
3506 + if (hdl == NULL)
3507 + return 0;
3508 +
3509 + mutex_lock(hdl->lock);
3510 + ret = __v4l2_ctrl_handler_setup(hdl);
3511 + mutex_unlock(hdl->lock);
3512 +
3513 + return ret;
3514 +}
3515 +EXPORT_SYMBOL(v4l2_ctrl_handler_setup);
3516 +
3517 +/* Implement VIDIOC_QUERY_EXT_CTRL */
3518 +int v4l2_query_ext_ctrl(struct v4l2_ctrl_handler *hdl, struct v4l2_query_ext_ctrl *qc)
3519 +{
3520 + const unsigned next_flags = V4L2_CTRL_FLAG_NEXT_CTRL | V4L2_CTRL_FLAG_NEXT_COMPOUND;
3521 + u32 id = qc->id & V4L2_CTRL_ID_MASK;
3522 + struct v4l2_ctrl_ref *ref;
3523 + struct v4l2_ctrl *ctrl;
3524 +
3525 + if (hdl == NULL)
3526 + return -EINVAL;
3527 +
3528 + mutex_lock(hdl->lock);
3529 +
3530 + /* Try to find it */
3531 + ref = find_ref(hdl, id);
3532 +
3533 + if ((qc->id & next_flags) && !list_empty(&hdl->ctrl_refs)) {
3534 + bool is_compound;
3535 + /* Match any control that is not hidden */
3536 + unsigned mask = 1;
3537 + bool match = false;
3538 +
3539 + if ((qc->id & next_flags) == V4L2_CTRL_FLAG_NEXT_COMPOUND) {
3540 + /* Match any hidden control */
3541 + match = true;
3542 + } else if ((qc->id & next_flags) == next_flags) {
3543 + /* Match any control, compound or not */
3544 + mask = 0;
3545 + }
3546 +
3547 + /* Find the next control with ID > qc->id */
3548 +
3549 + /* Did we reach the end of the control list? */
3550 + if (id >= node2id(hdl->ctrl_refs.prev)) {
3551 + ref = NULL; /* Yes, so there is no next control */
3552 + } else if (ref) {
3553 + /* We found a control with the given ID, so just get
3554 + the next valid one in the list. */
3555 + list_for_each_entry_continue(ref, &hdl->ctrl_refs, node) {
3556 + is_compound = ref->ctrl->is_array ||
3557 + ref->ctrl->type >= V4L2_CTRL_COMPOUND_TYPES;
3558 + if (id < ref->ctrl->id &&
3559 + (is_compound & mask) == match)
3560 + break;
3561 + }
3562 + if (&ref->node == &hdl->ctrl_refs)
3563 + ref = NULL;
3564 + } else {
3565 + /* No control with the given ID exists, so start
3566 + searching for the next largest ID. We know there
3567 + is one, otherwise the first 'if' above would have
3568 + been true. */
3569 + list_for_each_entry(ref, &hdl->ctrl_refs, node) {
3570 + is_compound = ref->ctrl->is_array ||
3571 + ref->ctrl->type >= V4L2_CTRL_COMPOUND_TYPES;
3572 + if (id < ref->ctrl->id &&
3573 + (is_compound & mask) == match)
3574 + break;
3575 + }
3576 + if (&ref->node == &hdl->ctrl_refs)
3577 + ref = NULL;
3578 + }
3579 + }
3580 + mutex_unlock(hdl->lock);
3581 +
3582 + if (!ref)
3583 + return -EINVAL;
3584 +
3585 + ctrl = ref->ctrl;
3586 + memset(qc, 0, sizeof(*qc));
3587 + if (id >= V4L2_CID_PRIVATE_BASE)
3588 + qc->id = id;
3589 + else
3590 + qc->id = ctrl->id;
3591 + strscpy(qc->name, ctrl->name, sizeof(qc->name));
3592 + qc->flags = user_flags(ctrl);
3593 + qc->type = ctrl->type;
3594 + qc->elem_size = ctrl->elem_size;
3595 + qc->elems = ctrl->elems;
3596 + qc->nr_of_dims = ctrl->nr_of_dims;
3597 + memcpy(qc->dims, ctrl->dims, qc->nr_of_dims * sizeof(qc->dims[0]));
3598 + qc->minimum = ctrl->minimum;
3599 + qc->maximum = ctrl->maximum;
3600 + qc->default_value = ctrl->default_value;
3601 + if (ctrl->type == V4L2_CTRL_TYPE_MENU
3602 + || ctrl->type == V4L2_CTRL_TYPE_INTEGER_MENU)
3603 + qc->step = 1;
3604 + else
3605 + qc->step = ctrl->step;
3606 + return 0;
3607 +}
3608 +EXPORT_SYMBOL(v4l2_query_ext_ctrl);
3609 +
3610 +/* Implement VIDIOC_QUERYCTRL */
3611 +int v4l2_queryctrl(struct v4l2_ctrl_handler *hdl, struct v4l2_queryctrl *qc)
3612 +{
3613 + struct v4l2_query_ext_ctrl qec = { qc->id };
3614 + int rc;
3615 +
3616 + rc = v4l2_query_ext_ctrl(hdl, &qec);
3617 + if (rc)
3618 + return rc;
3619 +
3620 + qc->id = qec.id;
3621 + qc->type = qec.type;
3622 + qc->flags = qec.flags;
3623 + strscpy(qc->name, qec.name, sizeof(qc->name));
3624 + switch (qc->type) {
3625 + case V4L2_CTRL_TYPE_INTEGER:
3626 + case V4L2_CTRL_TYPE_BOOLEAN:
3627 + case V4L2_CTRL_TYPE_MENU:
3628 + case V4L2_CTRL_TYPE_INTEGER_MENU:
3629 + case V4L2_CTRL_TYPE_STRING:
3630 + case V4L2_CTRL_TYPE_BITMASK:
3631 + qc->minimum = qec.minimum;
3632 + qc->maximum = qec.maximum;
3633 + qc->step = qec.step;
3634 + qc->default_value = qec.default_value;
3635 + break;
3636 + default:
3637 + qc->minimum = 0;
3638 + qc->maximum = 0;
3639 + qc->step = 0;
3640 + qc->default_value = 0;
3641 + break;
3642 + }
3643 + return 0;
3644 +}
3645 +EXPORT_SYMBOL(v4l2_queryctrl);
3646 +
3647 +/* Implement VIDIOC_QUERYMENU */
3648 +int v4l2_querymenu(struct v4l2_ctrl_handler *hdl, struct v4l2_querymenu *qm)
3649 +{
3650 + struct v4l2_ctrl *ctrl;
3651 + u32 i = qm->index;
3652 +
3653 + ctrl = v4l2_ctrl_find(hdl, qm->id);
3654 + if (!ctrl)
3655 + return -EINVAL;
3656 +
3657 + qm->reserved = 0;
3658 + /* Sanity checks */
3659 + switch (ctrl->type) {
3660 + case V4L2_CTRL_TYPE_MENU:
3661 + if (ctrl->qmenu == NULL)
3662 + return -EINVAL;
3663 + break;
3664 + case V4L2_CTRL_TYPE_INTEGER_MENU:
3665 + if (ctrl->qmenu_int == NULL)
3666 + return -EINVAL;
3667 + break;
3668 + default:
3669 + return -EINVAL;
3670 + }
3671 +
3672 + if (i < ctrl->minimum || i > ctrl->maximum)
3673 + return -EINVAL;
3674 +
3675 + /* Use mask to see if this menu item should be skipped */
3676 + if (ctrl->menu_skip_mask & (1ULL << i))
3677 + return -EINVAL;
3678 + /* Empty menu items should also be skipped */
3679 + if (ctrl->type == V4L2_CTRL_TYPE_MENU) {
3680 + if (ctrl->qmenu[i] == NULL || ctrl->qmenu[i][0] == '\0')
3681 + return -EINVAL;
3682 + strscpy(qm->name, ctrl->qmenu[i], sizeof(qm->name));
3683 + } else {
3684 + qm->value = ctrl->qmenu_int[i];
3685 + }
3686 + return 0;
3687 +}
3688 +EXPORT_SYMBOL(v4l2_querymenu);
3689 +
3690 +static int v4l2_ctrl_request_clone(struct v4l2_ctrl_handler *hdl,
3691 + const struct v4l2_ctrl_handler *from)
3692 +{
3693 + struct v4l2_ctrl_ref *ref;
3694 + int err = 0;
3695 +
3696 + if (WARN_ON(!hdl || hdl == from))
3697 + return -EINVAL;
3698 +
3699 + if (hdl->error)
3700 + return hdl->error;
3701 +
3702 + WARN_ON(hdl->lock != &hdl->_lock);
3703 +
3704 + mutex_lock(from->lock);
3705 + list_for_each_entry(ref, &from->ctrl_refs, node) {
3706 + struct v4l2_ctrl *ctrl = ref->ctrl;
3707 + struct v4l2_ctrl_ref *new_ref;
3708 +
3709 + /* Skip refs inherited from other devices */
3710 + if (ref->from_other_dev)
3711 + continue;
3712 + err = handler_new_ref(hdl, ctrl, &new_ref, false, true);
3713 + if (err)
3714 + break;
3715 + }
3716 + mutex_unlock(from->lock);
3717 + return err;
3718 +}
3719 +
3720 +static void v4l2_ctrl_request_queue(struct media_request_object *obj)
3721 +{
3722 + struct v4l2_ctrl_handler *hdl =
3723 + container_of(obj, struct v4l2_ctrl_handler, req_obj);
3724 + struct v4l2_ctrl_handler *main_hdl = obj->priv;
3725 +
3726 + mutex_lock(main_hdl->lock);
3727 + list_add_tail(&hdl->requests_queued, &main_hdl->requests_queued);
3728 + hdl->request_is_queued = true;
3729 + mutex_unlock(main_hdl->lock);
3730 +}
3731 +
3732 +static void v4l2_ctrl_request_unbind(struct media_request_object *obj)
3733 +{
3734 + struct v4l2_ctrl_handler *hdl =
3735 + container_of(obj, struct v4l2_ctrl_handler, req_obj);
3736 + struct v4l2_ctrl_handler *main_hdl = obj->priv;
3737 +
3738 + mutex_lock(main_hdl->lock);
3739 + list_del_init(&hdl->requests);
3740 + if (hdl->request_is_queued) {
3741 + list_del_init(&hdl->requests_queued);
3742 + hdl->request_is_queued = false;
3743 + }
3744 + mutex_unlock(main_hdl->lock);
3745 +}
3746 +
3747 +static void v4l2_ctrl_request_release(struct media_request_object *obj)
3748 +{
3749 + struct v4l2_ctrl_handler *hdl =
3750 + container_of(obj, struct v4l2_ctrl_handler, req_obj);
3751 +
3752 + v4l2_ctrl_handler_free(hdl);
3753 + kfree(hdl);
3754 +}
3755 +
3756 +static const struct media_request_object_ops req_ops = {
3757 + .queue = v4l2_ctrl_request_queue,
3758 + .unbind = v4l2_ctrl_request_unbind,
3759 + .release = v4l2_ctrl_request_release,
3760 +};
3761 +
3762 +struct v4l2_ctrl_handler *v4l2_ctrl_request_hdl_find(struct media_request *req,
3763 + struct v4l2_ctrl_handler *parent)
3764 +{
3765 + struct media_request_object *obj;
3766 +
3767 + if (WARN_ON(req->state != MEDIA_REQUEST_STATE_VALIDATING &&
3768 + req->state != MEDIA_REQUEST_STATE_QUEUED))
3769 + return NULL;
3770 +
3771 + obj = media_request_object_find(req, &req_ops, parent);
3772 + if (obj)
3773 + return container_of(obj, struct v4l2_ctrl_handler, req_obj);
3774 + return NULL;
3775 +}
3776 +EXPORT_SYMBOL_GPL(v4l2_ctrl_request_hdl_find);
3777 +
3778 +struct v4l2_ctrl *
3779 +v4l2_ctrl_request_hdl_ctrl_find(struct v4l2_ctrl_handler *hdl, u32 id)
3780 +{
3781 + struct v4l2_ctrl_ref *ref = find_ref_lock(hdl, id);
3782 +
3783 + return (ref && ref->valid_p_req) ? ref->ctrl : NULL;
3784 +}
3785 +EXPORT_SYMBOL_GPL(v4l2_ctrl_request_hdl_ctrl_find);
3786 +
3787 +static int v4l2_ctrl_request_bind(struct media_request *req,
3788 + struct v4l2_ctrl_handler *hdl,
3789 + struct v4l2_ctrl_handler *from)
3790 +{
3791 + int ret;
3792 +
3793 + ret = v4l2_ctrl_request_clone(hdl, from);
3794 +
3795 + if (!ret) {
3796 + ret = media_request_object_bind(req, &req_ops,
3797 + from, false, &hdl->req_obj);
3798 + if (!ret) {
3799 + mutex_lock(from->lock);
3800 + list_add_tail(&hdl->requests, &from->requests);
3801 + mutex_unlock(from->lock);
3802 + }
3803 + }
3804 + return ret;
3805 +}
3806 +
3807 +/* Some general notes on the atomic requirements of VIDIOC_G/TRY/S_EXT_CTRLS:
3808 +
3809 + It is not a fully atomic operation, just best-effort only. After all, if
3810 + multiple controls have to be set through multiple i2c writes (for example)
3811 + then some initial writes may succeed while others fail. Thus leaving the
3812 + system in an inconsistent state. The question is how much effort you are
3813 + willing to spend on trying to make something atomic that really isn't.
3814 +
3815 + From the point of view of an application the main requirement is that
3816 + when you call VIDIOC_S_EXT_CTRLS and some values are invalid then an
3817 + error should be returned without actually affecting any controls.
3818 +
3819 + If all the values are correct, then it is acceptable to just give up
3820 + in case of low-level errors.
3821 +
3822 + It is important though that the application can tell when only a partial
3823 + configuration was done. The way we do that is through the error_idx field
3824 + of struct v4l2_ext_controls: if that is equal to the count field then no
3825 + controls were affected. Otherwise all controls before that index were
3826 + successful in performing their 'get' or 'set' operation, the control at
3827 + the given index failed, and you don't know what happened with the controls
3828 + after the failed one. Since if they were part of a control cluster they
3829 + could have been successfully processed (if a cluster member was encountered
3830 + at index < error_idx), they could have failed (if a cluster member was at
3831 + error_idx), or they may not have been processed yet (if the first cluster
3832 + member appeared after error_idx).
3833 +
3834 + It is all fairly theoretical, though. In practice all you can do is to
3835 + bail out. If error_idx == count, then it is an application bug. If
3836 + error_idx < count then it is only an application bug if the error code was
3837 + EBUSY. That usually means that something started streaming just when you
3838 + tried to set the controls. In all other cases it is a driver/hardware
3839 + problem and all you can do is to retry or bail out.
3840 +
3841 + Note that these rules do not apply to VIDIOC_TRY_EXT_CTRLS: since that
3842 + never modifies controls the error_idx is just set to whatever control
3843 + has an invalid value.
3844 + */
3845 +
3846 +/* Prepare for the extended g/s/try functions.
3847 + Find the controls in the control array and do some basic checks. */
3848 +static int prepare_ext_ctrls(struct v4l2_ctrl_handler *hdl,
3849 + struct v4l2_ext_controls *cs,
3850 + struct v4l2_ctrl_helper *helpers,
3851 + struct video_device *vdev,
3852 + bool get)
3853 +{
3854 + struct v4l2_ctrl_helper *h;
3855 + bool have_clusters = false;
3856 + u32 i;
3857 +
3858 + for (i = 0, h = helpers; i < cs->count; i++, h++) {
3859 + struct v4l2_ext_control *c = &cs->controls[i];
3860 + struct v4l2_ctrl_ref *ref;
3861 + struct v4l2_ctrl *ctrl;
3862 + u32 id = c->id & V4L2_CTRL_ID_MASK;
3863 +
3864 + cs->error_idx = i;
3865 +
3866 + if (cs->which &&
3867 + cs->which != V4L2_CTRL_WHICH_DEF_VAL &&
3868 + cs->which != V4L2_CTRL_WHICH_REQUEST_VAL &&
3869 + V4L2_CTRL_ID2WHICH(id) != cs->which) {
3870 + dprintk(vdev,
3871 + "invalid which 0x%x or control id 0x%x\n",
3872 + cs->which, id);
3873 + return -EINVAL;
3874 + }
3875 +
3876 + /* Old-style private controls are not allowed for
3877 + extended controls */
3878 + if (id >= V4L2_CID_PRIVATE_BASE) {
3879 + dprintk(vdev,
3880 + "old-style private controls not allowed\n");
3881 + return -EINVAL;
3882 + }
3883 + ref = find_ref_lock(hdl, id);
3884 + if (ref == NULL) {
3885 + dprintk(vdev, "cannot find control id 0x%x\n", id);
3886 + return -EINVAL;
3887 + }
3888 + h->ref = ref;
3889 + ctrl = ref->ctrl;
3890 + if (ctrl->flags & V4L2_CTRL_FLAG_DISABLED) {
3891 + dprintk(vdev, "control id 0x%x is disabled\n", id);
3892 + return -EINVAL;
3893 + }
3894 +
3895 + if (ctrl->cluster[0]->ncontrols > 1)
3896 + have_clusters = true;
3897 + if (ctrl->cluster[0] != ctrl)
3898 + ref = find_ref_lock(hdl, ctrl->cluster[0]->id);
3899 + if (ctrl->is_ptr && !ctrl->is_string) {
3900 + unsigned tot_size = ctrl->elems * ctrl->elem_size;
3901 +
3902 + if (c->size < tot_size) {
3903 + /*
3904 + * In the get case the application first
3905 + * queries to obtain the size of the control.
3906 + */
3907 + if (get) {
3908 + c->size = tot_size;
3909 + return -ENOSPC;
3910 + }
3911 + dprintk(vdev,
3912 + "pointer control id 0x%x size too small, %d bytes but %d bytes needed\n",
3913 + id, c->size, tot_size);
3914 + return -EFAULT;
3915 + }
3916 + c->size = tot_size;
3917 + }
3918 + /* Store the ref to the master control of the cluster */
3919 + h->mref = ref;
3920 + /* Initially set next to 0, meaning that there is no other
3921 + control in this helper array belonging to the same
3922 + cluster */
3923 + h->next = 0;
3924 + }
3925 +
3926 + /* We are done if there were no controls that belong to a multi-
3927 + control cluster. */
3928 + if (!have_clusters)
3929 + return 0;
3930 +
3931 + /* The code below figures out in O(n) time which controls in the list
3932 + belong to the same cluster. */
3933 +
3934 + /* This has to be done with the handler lock taken. */
3935 + mutex_lock(hdl->lock);
3936 +
3937 + /* First zero the helper field in the master control references */
3938 + for (i = 0; i < cs->count; i++)
3939 + helpers[i].mref->helper = NULL;
3940 + for (i = 0, h = helpers; i < cs->count; i++, h++) {
3941 + struct v4l2_ctrl_ref *mref = h->mref;
3942 +
3943 + /* If the mref->helper is set, then it points to an earlier
3944 + helper that belongs to the same cluster. */
3945 + if (mref->helper) {
3946 + /* Set the next field of mref->helper to the current
3947 + index: this means that that earlier helper now
3948 + points to the next helper in the same cluster. */
3949 + mref->helper->next = i;
3950 + /* mref should be set only for the first helper in the
3951 + cluster, clear the others. */
3952 + h->mref = NULL;
3953 + }
3954 + /* Point the mref helper to the current helper struct. */
3955 + mref->helper = h;
3956 + }
3957 + mutex_unlock(hdl->lock);
3958 + return 0;
3959 +}
3960 +
3961 +/* Handles the corner case where cs->count == 0. It checks whether the
3962 + specified control class exists. If that class ID is 0, then it checks
3963 + whether there are any controls at all. */
3964 +static int class_check(struct v4l2_ctrl_handler *hdl, u32 which)
3965 +{
3966 + if (which == 0 || which == V4L2_CTRL_WHICH_DEF_VAL ||
3967 + which == V4L2_CTRL_WHICH_REQUEST_VAL)
3968 + return 0;
3969 + return find_ref_lock(hdl, which | 1) ? 0 : -EINVAL;
3970 +}
3971 +
3972 +/*
3973 + * Get extended controls. Allocates the helpers array if needed.
3974 + *
3975 + * Note that v4l2_g_ext_ctrls_common() with 'which' set to
3976 + * V4L2_CTRL_WHICH_REQUEST_VAL is only called if the request was
3977 + * completed, and in that case valid_p_req is true for all controls.
3978 + */
3979 +static int v4l2_g_ext_ctrls_common(struct v4l2_ctrl_handler *hdl,
3980 + struct v4l2_ext_controls *cs,
3981 + struct video_device *vdev)
3982 +{
3983 + struct v4l2_ctrl_helper helper[4];
3984 + struct v4l2_ctrl_helper *helpers = helper;
3985 + int ret;
3986 + int i, j;
3987 + bool is_default, is_request;
3988 +
3989 + is_default = (cs->which == V4L2_CTRL_WHICH_DEF_VAL);
3990 + is_request = (cs->which == V4L2_CTRL_WHICH_REQUEST_VAL);
3991 +
3992 + cs->error_idx = cs->count;
3993 + cs->which = V4L2_CTRL_ID2WHICH(cs->which);
3994 +
3995 + if (hdl == NULL)
3996 + return -EINVAL;
3997 +
3998 + if (cs->count == 0)
3999 + return class_check(hdl, cs->which);
4000 +
4001 + if (cs->count > ARRAY_SIZE(helper)) {
4002 + helpers = kvmalloc_array(cs->count, sizeof(helper[0]),
4003 + GFP_KERNEL);
4004 + if (helpers == NULL)
4005 + return -ENOMEM;
4006 + }
4007 +
4008 + ret = prepare_ext_ctrls(hdl, cs, helpers, vdev, true);
4009 + cs->error_idx = cs->count;
4010 +
4011 + for (i = 0; !ret && i < cs->count; i++)
4012 + if (helpers[i].ref->ctrl->flags & V4L2_CTRL_FLAG_WRITE_ONLY)
4013 + ret = -EACCES;
4014 +
4015 + for (i = 0; !ret && i < cs->count; i++) {
4016 + struct v4l2_ctrl *master;
4017 + bool is_volatile = false;
4018 + u32 idx = i;
4019 +
4020 + if (helpers[i].mref == NULL)
4021 + continue;
4022 +
4023 + master = helpers[i].mref->ctrl;
4024 + cs->error_idx = i;
4025 +
4026 + v4l2_ctrl_lock(master);
4027 +
4028 + /*
4029 + * g_volatile_ctrl will update the new control values.
4030 + * This makes no sense for V4L2_CTRL_WHICH_DEF_VAL and
4031 + * V4L2_CTRL_WHICH_REQUEST_VAL. In the case of requests
4032 + * it is v4l2_ctrl_request_complete() that copies the
4033 + * volatile controls at the time of request completion
4034 + * to the request, so you don't want to do that again.
4035 + */
4036 + if (!is_default && !is_request &&
4037 + ((master->flags & V4L2_CTRL_FLAG_VOLATILE) ||
4038 + (master->has_volatiles && !is_cur_manual(master)))) {
4039 + for (j = 0; j < master->ncontrols; j++)
4040 + cur_to_new(master->cluster[j]);
4041 + ret = call_op(master, g_volatile_ctrl);
4042 + is_volatile = true;
4043 + }
4044 +
4045 + if (ret) {
4046 + v4l2_ctrl_unlock(master);
4047 + break;
4048 + }
4049 +
4050 + /*
4051 + * Copy the default value (if is_default is true), the
4052 + * request value (if is_request is true and p_req is valid),
4053 + * the new volatile value (if is_volatile is true) or the
4054 + * current value.
4055 + */
4056 + do {
4057 + struct v4l2_ctrl_ref *ref = helpers[idx].ref;
4058 +
4059 + if (is_default)
4060 + ret = def_to_user(cs->controls + idx, ref->ctrl);
4061 + else if (is_request && ref->valid_p_req)
4062 + ret = req_to_user(cs->controls + idx, ref);
4063 + else if (is_volatile)
4064 + ret = new_to_user(cs->controls + idx, ref->ctrl);
4065 + else
4066 + ret = cur_to_user(cs->controls + idx, ref->ctrl);
4067 + idx = helpers[idx].next;
4068 + } while (!ret && idx);
4069 +
4070 + v4l2_ctrl_unlock(master);
4071 + }
4072 +
4073 + if (cs->count > ARRAY_SIZE(helper))
4074 + kvfree(helpers);
4075 + return ret;
4076 +}
4077 +
4078 +static struct media_request_object *
4079 +v4l2_ctrls_find_req_obj(struct v4l2_ctrl_handler *hdl,
4080 + struct media_request *req, bool set)
4081 +{
4082 + struct media_request_object *obj;
4083 + struct v4l2_ctrl_handler *new_hdl;
4084 + int ret;
4085 +
4086 + if (IS_ERR(req))
4087 + return ERR_CAST(req);
4088 +
4089 + if (set && WARN_ON(req->state != MEDIA_REQUEST_STATE_UPDATING))
4090 + return ERR_PTR(-EBUSY);
4091 +
4092 + obj = media_request_object_find(req, &req_ops, hdl);
4093 + if (obj)
4094 + return obj;
4095 + if (!set)
4096 + return ERR_PTR(-ENOENT);
4097 +
4098 + new_hdl = kzalloc(sizeof(*new_hdl), GFP_KERNEL);
4099 + if (!new_hdl)
4100 + return ERR_PTR(-ENOMEM);
4101 +
4102 + obj = &new_hdl->req_obj;
4103 + ret = v4l2_ctrl_handler_init(new_hdl, (hdl->nr_of_buckets - 1) * 8);
4104 + if (!ret)
4105 + ret = v4l2_ctrl_request_bind(req, new_hdl, hdl);
4106 + if (ret) {
4107 + kfree(new_hdl);
4108 +
4109 + return ERR_PTR(ret);
4110 + }
4111 +
4112 + media_request_object_get(obj);
4113 + return obj;
4114 +}
4115 +
4116 +int v4l2_g_ext_ctrls(struct v4l2_ctrl_handler *hdl, struct video_device *vdev,
4117 + struct media_device *mdev, struct v4l2_ext_controls *cs)
4118 +{
4119 + struct media_request_object *obj = NULL;
4120 + struct media_request *req = NULL;
4121 + int ret;
4122 +
4123 + if (cs->which == V4L2_CTRL_WHICH_REQUEST_VAL) {
4124 + if (!mdev || cs->request_fd < 0)
4125 + return -EINVAL;
4126 +
4127 + req = media_request_get_by_fd(mdev, cs->request_fd);
4128 + if (IS_ERR(req))
4129 + return PTR_ERR(req);
4130 +
4131 + if (req->state != MEDIA_REQUEST_STATE_COMPLETE) {
4132 + media_request_put(req);
4133 + return -EACCES;
4134 + }
4135 +
4136 + ret = media_request_lock_for_access(req);
4137 + if (ret) {
4138 + media_request_put(req);
4139 + return ret;
4140 + }
4141 +
4142 + obj = v4l2_ctrls_find_req_obj(hdl, req, false);
4143 + if (IS_ERR(obj)) {
4144 + media_request_unlock_for_access(req);
4145 + media_request_put(req);
4146 + return PTR_ERR(obj);
4147 + }
4148 +
4149 + hdl = container_of(obj, struct v4l2_ctrl_handler,
4150 + req_obj);
4151 + }
4152 +
4153 + ret = v4l2_g_ext_ctrls_common(hdl, cs, vdev);
4154 +
4155 + if (obj) {
4156 + media_request_unlock_for_access(req);
4157 + media_request_object_put(obj);
4158 + media_request_put(req);
4159 + }
4160 + return ret;
4161 +}
4162 +EXPORT_SYMBOL(v4l2_g_ext_ctrls);
4163 +
4164 +/* Helper function to get a single control */
4165 +static int get_ctrl(struct v4l2_ctrl *ctrl, struct v4l2_ext_control *c)
4166 +{
4167 + struct v4l2_ctrl *master = ctrl->cluster[0];
4168 + int ret = 0;
4169 + int i;
4170 +
4171 + /* Compound controls are not supported. The new_to_user() and
4172 + * cur_to_user() calls below would need to be modified not to access
4173 + * userspace memory when called from get_ctrl().
4174 + */
4175 + if (!ctrl->is_int && ctrl->type != V4L2_CTRL_TYPE_INTEGER64)
4176 + return -EINVAL;
4177 +
4178 + if (ctrl->flags & V4L2_CTRL_FLAG_WRITE_ONLY)
4179 + return -EACCES;
4180 +
4181 + v4l2_ctrl_lock(master);
4182 + /* g_volatile_ctrl will update the current control values */
4183 + if (ctrl->flags & V4L2_CTRL_FLAG_VOLATILE) {
4184 + for (i = 0; i < master->ncontrols; i++)
4185 + cur_to_new(master->cluster[i]);
4186 + ret = call_op(master, g_volatile_ctrl);
4187 + new_to_user(c, ctrl);
4188 + } else {
4189 + cur_to_user(c, ctrl);
4190 + }
4191 + v4l2_ctrl_unlock(master);
4192 + return ret;
4193 +}
4194 +
4195 +int v4l2_g_ctrl(struct v4l2_ctrl_handler *hdl, struct v4l2_control *control)
4196 +{
4197 + struct v4l2_ctrl *ctrl = v4l2_ctrl_find(hdl, control->id);
4198 + struct v4l2_ext_control c;
4199 + int ret;
4200 +
4201 + if (ctrl == NULL || !ctrl->is_int)
4202 + return -EINVAL;
4203 + ret = get_ctrl(ctrl, &c);
4204 + control->value = c.value;
4205 + return ret;
4206 +}
4207 +EXPORT_SYMBOL(v4l2_g_ctrl);
4208 +
4209 +s32 v4l2_ctrl_g_ctrl(struct v4l2_ctrl *ctrl)
4210 +{
4211 + struct v4l2_ext_control c;
4212 +
4213 + /* It's a driver bug if this happens. */
4214 + if (WARN_ON(!ctrl->is_int))
4215 + return 0;
4216 + c.value = 0;
4217 + get_ctrl(ctrl, &c);
4218 + return c.value;
4219 +}
4220 +EXPORT_SYMBOL(v4l2_ctrl_g_ctrl);
4221 +
4222 +s64 v4l2_ctrl_g_ctrl_int64(struct v4l2_ctrl *ctrl)
4223 +{
4224 + struct v4l2_ext_control c;
4225 +
4226 + /* It's a driver bug if this happens. */
4227 + if (WARN_ON(ctrl->is_ptr || ctrl->type != V4L2_CTRL_TYPE_INTEGER64))
4228 + return 0;
4229 + c.value64 = 0;
4230 + get_ctrl(ctrl, &c);
4231 + return c.value64;
4232 +}
4233 +EXPORT_SYMBOL(v4l2_ctrl_g_ctrl_int64);
4234 +
4235 +
4236 +/* Core function that calls try/s_ctrl and ensures that the new value is
4237 + copied to the current value on a set.
4238 + Must be called with ctrl->handler->lock held. */
4239 +static int try_or_set_cluster(struct v4l2_fh *fh, struct v4l2_ctrl *master,
4240 + bool set, u32 ch_flags)
4241 +{
4242 + bool update_flag;
4243 + int ret;
4244 + int i;
4245 +
4246 + /* Go through the cluster and either validate the new value or
4247 + (if no new value was set), copy the current value to the new
4248 + value, ensuring a consistent view for the control ops when
4249 + called. */
4250 + for (i = 0; i < master->ncontrols; i++) {
4251 + struct v4l2_ctrl *ctrl = master->cluster[i];
4252 +
4253 + if (ctrl == NULL)
4254 + continue;
4255 +
4256 + if (!ctrl->is_new) {
4257 + cur_to_new(ctrl);
4258 + continue;
4259 + }
4260 + /* Check again: it may have changed since the
4261 + previous check in try_or_set_ext_ctrls(). */
4262 + if (set && (ctrl->flags & V4L2_CTRL_FLAG_GRABBED))
4263 + return -EBUSY;
4264 + }
4265 +
4266 + ret = call_op(master, try_ctrl);
4267 +
4268 + /* Don't set if there is no change */
4269 + if (ret || !set || !cluster_changed(master))
4270 + return ret;
4271 + ret = call_op(master, s_ctrl);
4272 + if (ret)
4273 + return ret;
4274 +
4275 + /* If OK, then make the new values permanent. */
4276 + update_flag = is_cur_manual(master) != is_new_manual(master);
4277 +
4278 + for (i = 0; i < master->ncontrols; i++) {
4279 + /*
4280 + * If we switch from auto to manual mode, and this cluster
4281 + * contains volatile controls, then all non-master controls
4282 + * have to be marked as changed. The 'new' value contains
4283 + * the volatile value (obtained by update_from_auto_cluster),
4284 + * which now has to become the current value.
4285 + */
4286 + if (i && update_flag && is_new_manual(master) &&
4287 + master->has_volatiles && master->cluster[i])
4288 + master->cluster[i]->has_changed = true;
4289 +
4290 + new_to_cur(fh, master->cluster[i], ch_flags |
4291 + ((update_flag && i > 0) ? V4L2_EVENT_CTRL_CH_FLAGS : 0));
4292 + }
4293 + return 0;
4294 +}
4295 +
4296 +/* Validate controls. */
4297 +static int validate_ctrls(struct v4l2_ext_controls *cs,
4298 + struct v4l2_ctrl_helper *helpers,
4299 + struct video_device *vdev,
4300 + bool set)
4301 +{
4302 + unsigned i;
4303 + int ret = 0;
4304 +
4305 + cs->error_idx = cs->count;
4306 + for (i = 0; i < cs->count; i++) {
4307 + struct v4l2_ctrl *ctrl = helpers[i].ref->ctrl;
4308 + union v4l2_ctrl_ptr p_new;
4309 +
4310 + cs->error_idx = i;
4311 +
4312 + if (ctrl->flags & V4L2_CTRL_FLAG_READ_ONLY) {
4313 + dprintk(vdev,
4314 + "control id 0x%x is read-only\n",
4315 + ctrl->id);
4316 + return -EACCES;
4317 + }
4318 + /* This test is also done in try_set_control_cluster() which
4319 + is called in atomic context, so that has the final say,
4320 + but it makes sense to do an up-front check as well. Once
4321 + an error occurs in try_set_control_cluster() some other
4322 + controls may have been set already and we want to do a
4323 + best-effort to avoid that. */
4324 + if (set && (ctrl->flags & V4L2_CTRL_FLAG_GRABBED)) {
4325 + dprintk(vdev,
4326 + "control id 0x%x is grabbed, cannot set\n",
4327 + ctrl->id);
4328 + return -EBUSY;
4329 + }
4330 + /*
4331 + * Skip validation for now if the payload needs to be copied
4332 + * from userspace into kernelspace. We'll validate those later.
4333 + */
4334 + if (ctrl->is_ptr)
4335 + continue;
4336 + if (ctrl->type == V4L2_CTRL_TYPE_INTEGER64)
4337 + p_new.p_s64 = &cs->controls[i].value64;
4338 + else
4339 + p_new.p_s32 = &cs->controls[i].value;
4340 + ret = validate_new(ctrl, p_new);
4341 + if (ret)
4342 + return ret;
4343 + }
4344 + return 0;
4345 +}
4346 +
4347 +/* Obtain the current volatile values of an autocluster and mark them
4348 + as new. */
4349 +static void update_from_auto_cluster(struct v4l2_ctrl *master)
4350 +{
4351 + int i;
4352 +
4353 + for (i = 1; i < master->ncontrols; i++)
4354 + cur_to_new(master->cluster[i]);
4355 + if (!call_op(master, g_volatile_ctrl))
4356 + for (i = 1; i < master->ncontrols; i++)
4357 + if (master->cluster[i])
4358 + master->cluster[i]->is_new = 1;
4359 +}
4360 +
4361 +/* Try or try-and-set controls */
4362 +static int try_set_ext_ctrls_common(struct v4l2_fh *fh,
4363 + struct v4l2_ctrl_handler *hdl,
4364 + struct v4l2_ext_controls *cs,
4365 + struct video_device *vdev, bool set)
4366 +{
4367 + struct v4l2_ctrl_helper helper[4];
4368 + struct v4l2_ctrl_helper *helpers = helper;
4369 + unsigned i, j;
4370 + int ret;
4371 +
4372 + cs->error_idx = cs->count;
4373 +
4374 + /* Default value cannot be changed */
4375 + if (cs->which == V4L2_CTRL_WHICH_DEF_VAL) {
4376 + dprintk(vdev, "%s: cannot change default value\n",
4377 + video_device_node_name(vdev));
4378 + return -EINVAL;
4379 + }
4380 +
4381 + cs->which = V4L2_CTRL_ID2WHICH(cs->which);
4382 +
4383 + if (hdl == NULL) {
4384 + dprintk(vdev, "%s: invalid null control handler\n",
4385 + video_device_node_name(vdev));
4386 + return -EINVAL;
4387 + }
4388 +
4389 + if (cs->count == 0)
4390 + return class_check(hdl, cs->which);
4391 +
4392 + if (cs->count > ARRAY_SIZE(helper)) {
4393 + helpers = kvmalloc_array(cs->count, sizeof(helper[0]),
4394 + GFP_KERNEL);
4395 + if (!helpers)
4396 + return -ENOMEM;
4397 + }
4398 + ret = prepare_ext_ctrls(hdl, cs, helpers, vdev, false);
4399 + if (!ret)
4400 + ret = validate_ctrls(cs, helpers, vdev, set);
4401 + if (ret && set)
4402 + cs->error_idx = cs->count;
4403 + for (i = 0; !ret && i < cs->count; i++) {
4404 + struct v4l2_ctrl *master;
4405 + u32 idx = i;
4406 +
4407 + if (helpers[i].mref == NULL)
4408 + continue;
4409 +
4410 + cs->error_idx = i;
4411 + master = helpers[i].mref->ctrl;
4412 + v4l2_ctrl_lock(master);
4413 +
4414 + /* Reset the 'is_new' flags of the cluster */
4415 + for (j = 0; j < master->ncontrols; j++)
4416 + if (master->cluster[j])
4417 + master->cluster[j]->is_new = 0;
4418 +
4419 + /* For volatile autoclusters that are currently in auto mode
4420 + we need to discover if it will be set to manual mode.
4421 + If so, then we have to copy the current volatile values
4422 + first since those will become the new manual values (which
4423 + may be overwritten by explicit new values from this set
4424 + of controls). */
4425 + if (master->is_auto && master->has_volatiles &&
4426 + !is_cur_manual(master)) {
4427 + /* Pick an initial non-manual value */
4428 + s32 new_auto_val = master->manual_mode_value + 1;
4429 + u32 tmp_idx = idx;
4430 +
4431 + do {
4432 + /* Check if the auto control is part of the
4433 + list, and remember the new value. */
4434 + if (helpers[tmp_idx].ref->ctrl == master)
4435 + new_auto_val = cs->controls[tmp_idx].value;
4436 + tmp_idx = helpers[tmp_idx].next;
4437 + } while (tmp_idx);
4438 + /* If the new value == the manual value, then copy
4439 + the current volatile values. */
4440 + if (new_auto_val == master->manual_mode_value)
4441 + update_from_auto_cluster(master);
4442 + }
4443 +
4444 + /* Copy the new caller-supplied control values.
4445 + user_to_new() sets 'is_new' to 1. */
4446 + do {
4447 + struct v4l2_ctrl *ctrl = helpers[idx].ref->ctrl;
4448 +
4449 + ret = user_to_new(cs->controls + idx, ctrl);
4450 + if (!ret && ctrl->is_ptr) {
4451 + ret = validate_new(ctrl, ctrl->p_new);
4452 + if (ret)
4453 + dprintk(vdev,
4454 + "failed to validate control %s (%d)\n",
4455 + v4l2_ctrl_get_name(ctrl->id), ret);
4456 + }
4457 + idx = helpers[idx].next;
4458 + } while (!ret && idx);
4459 +
4460 + if (!ret)
4461 + ret = try_or_set_cluster(fh, master,
4462 + !hdl->req_obj.req && set, 0);
4463 + if (!ret && hdl->req_obj.req && set) {
4464 + for (j = 0; j < master->ncontrols; j++) {
4465 + struct v4l2_ctrl_ref *ref =
4466 + find_ref(hdl, master->cluster[j]->id);
4467 +
4468 + new_to_req(ref);
4469 + }
4470 + }
4471 +
4472 + /* Copy the new values back to userspace. */
4473 + if (!ret) {
4474 + idx = i;
4475 + do {
4476 + ret = new_to_user(cs->controls + idx,
4477 + helpers[idx].ref->ctrl);
4478 + idx = helpers[idx].next;
4479 + } while (!ret && idx);
4480 + }
4481 + v4l2_ctrl_unlock(master);
4482 + }
4483 +
4484 + if (cs->count > ARRAY_SIZE(helper))
4485 + kvfree(helpers);
4486 + return ret;
4487 +}
4488 +
4489 +static int try_set_ext_ctrls(struct v4l2_fh *fh,
4490 + struct v4l2_ctrl_handler *hdl,
4491 + struct video_device *vdev,
4492 + struct media_device *mdev,
4493 + struct v4l2_ext_controls *cs, bool set)
4494 +{
4495 + struct media_request_object *obj = NULL;
4496 + struct media_request *req = NULL;
4497 + int ret;
4498 +
4499 + if (cs->which == V4L2_CTRL_WHICH_REQUEST_VAL) {
4500 + if (!mdev) {
4501 + dprintk(vdev, "%s: missing media device\n",
4502 + video_device_node_name(vdev));
4503 + return -EINVAL;
4504 + }
4505 +
4506 + if (cs->request_fd < 0) {
4507 + dprintk(vdev, "%s: invalid request fd %d\n",
4508 + video_device_node_name(vdev), cs->request_fd);
4509 + return -EINVAL;
4510 + }
4511 +
4512 + req = media_request_get_by_fd(mdev, cs->request_fd);
4513 + if (IS_ERR(req)) {
4514 + dprintk(vdev, "%s: cannot find request fd %d\n",
4515 + video_device_node_name(vdev), cs->request_fd);
4516 + return PTR_ERR(req);
4517 + }
4518 +
4519 + ret = media_request_lock_for_update(req);
4520 + if (ret) {
4521 + dprintk(vdev, "%s: cannot lock request fd %d\n",
4522 + video_device_node_name(vdev), cs->request_fd);
4523 + media_request_put(req);
4524 + return ret;
4525 + }
4526 +
4527 + obj = v4l2_ctrls_find_req_obj(hdl, req, set);
4528 + if (IS_ERR(obj)) {
4529 + dprintk(vdev,
4530 + "%s: cannot find request object for request fd %d\n",
4531 + video_device_node_name(vdev),
4532 + cs->request_fd);
4533 + media_request_unlock_for_update(req);
4534 + media_request_put(req);
4535 + return PTR_ERR(obj);
4536 + }
4537 + hdl = container_of(obj, struct v4l2_ctrl_handler,
4538 + req_obj);
4539 + }
4540 +
4541 + ret = try_set_ext_ctrls_common(fh, hdl, cs, vdev, set);
4542 + if (ret)
4543 + dprintk(vdev,
4544 + "%s: try_set_ext_ctrls_common failed (%d)\n",
4545 + video_device_node_name(vdev), ret);
4546 +
4547 + if (obj) {
4548 + media_request_unlock_for_update(req);
4549 + media_request_object_put(obj);
4550 + media_request_put(req);
4551 + }
4552 +
4553 + return ret;
4554 +}
4555 +
4556 +int v4l2_try_ext_ctrls(struct v4l2_ctrl_handler *hdl,
4557 + struct video_device *vdev,
4558 + struct media_device *mdev,
4559 + struct v4l2_ext_controls *cs)
4560 +{
4561 + return try_set_ext_ctrls(NULL, hdl, vdev, mdev, cs, false);
4562 +}
4563 +EXPORT_SYMBOL(v4l2_try_ext_ctrls);
4564 +
4565 +int v4l2_s_ext_ctrls(struct v4l2_fh *fh,
4566 + struct v4l2_ctrl_handler *hdl,
4567 + struct video_device *vdev,
4568 + struct media_device *mdev,
4569 + struct v4l2_ext_controls *cs)
4570 +{
4571 + return try_set_ext_ctrls(fh, hdl, vdev, mdev, cs, true);
4572 +}
4573 +EXPORT_SYMBOL(v4l2_s_ext_ctrls);
4574 +
4575 +/* Helper function for VIDIOC_S_CTRL compatibility */
4576 +static int set_ctrl(struct v4l2_fh *fh, struct v4l2_ctrl *ctrl, u32 ch_flags)
4577 +{
4578 + struct v4l2_ctrl *master = ctrl->cluster[0];
4579 + int ret;
4580 + int i;
4581 +
4582 + /* Reset the 'is_new' flags of the cluster */
4583 + for (i = 0; i < master->ncontrols; i++)
4584 + if (master->cluster[i])
4585 + master->cluster[i]->is_new = 0;
4586 +
4587 + ret = validate_new(ctrl, ctrl->p_new);
4588 + if (ret)
4589 + return ret;
4590 +
4591 + /* For autoclusters with volatiles that are switched from auto to
4592 + manual mode we have to update the current volatile values since
4593 + those will become the initial manual values after such a switch. */
4594 + if (master->is_auto && master->has_volatiles && ctrl == master &&
4595 + !is_cur_manual(master) && ctrl->val == master->manual_mode_value)
4596 + update_from_auto_cluster(master);
4597 +
4598 + ctrl->is_new = 1;
4599 + return try_or_set_cluster(fh, master, true, ch_flags);
4600 +}
4601 +
4602 +/* Helper function for VIDIOC_S_CTRL compatibility */
4603 +static int set_ctrl_lock(struct v4l2_fh *fh, struct v4l2_ctrl *ctrl,
4604 + struct v4l2_ext_control *c)
4605 +{
4606 + int ret;
4607 +
4608 + v4l2_ctrl_lock(ctrl);
4609 + user_to_new(c, ctrl);
4610 + ret = set_ctrl(fh, ctrl, 0);
4611 + if (!ret)
4612 + cur_to_user(c, ctrl);
4613 + v4l2_ctrl_unlock(ctrl);
4614 + return ret;
4615 +}
4616 +
4617 +int v4l2_s_ctrl(struct v4l2_fh *fh, struct v4l2_ctrl_handler *hdl,
4618 + struct v4l2_control *control)
4619 +{
4620 + struct v4l2_ctrl *ctrl = v4l2_ctrl_find(hdl, control->id);
4621 + struct v4l2_ext_control c = { control->id };
4622 + int ret;
4623 +
4624 + if (ctrl == NULL || !ctrl->is_int)
4625 + return -EINVAL;
4626 +
4627 + if (ctrl->flags & V4L2_CTRL_FLAG_READ_ONLY)
4628 + return -EACCES;
4629 +
4630 + c.value = control->value;
4631 + ret = set_ctrl_lock(fh, ctrl, &c);
4632 + control->value = c.value;
4633 + return ret;
4634 +}
4635 +EXPORT_SYMBOL(v4l2_s_ctrl);
4636 +
4637 +int __v4l2_ctrl_s_ctrl(struct v4l2_ctrl *ctrl, s32 val)
4638 +{
4639 + lockdep_assert_held(ctrl->handler->lock);
4640 +
4641 + /* It's a driver bug if this happens. */
4642 + if (WARN_ON(!ctrl->is_int))
4643 + return -EINVAL;
4644 + ctrl->val = val;
4645 + return set_ctrl(NULL, ctrl, 0);
4646 +}
4647 +EXPORT_SYMBOL(__v4l2_ctrl_s_ctrl);
4648 +
4649 +int __v4l2_ctrl_s_ctrl_int64(struct v4l2_ctrl *ctrl, s64 val)
4650 +{
4651 + lockdep_assert_held(ctrl->handler->lock);
4652 +
4653 + /* It's a driver bug if this happens. */
4654 + if (WARN_ON(ctrl->is_ptr || ctrl->type != V4L2_CTRL_TYPE_INTEGER64))
4655 + return -EINVAL;
4656 + *ctrl->p_new.p_s64 = val;
4657 + return set_ctrl(NULL, ctrl, 0);
4658 +}
4659 +EXPORT_SYMBOL(__v4l2_ctrl_s_ctrl_int64);
4660 +
4661 +int __v4l2_ctrl_s_ctrl_string(struct v4l2_ctrl *ctrl, const char *s)
4662 +{
4663 + lockdep_assert_held(ctrl->handler->lock);
4664 +
4665 + /* It's a driver bug if this happens. */
4666 + if (WARN_ON(ctrl->type != V4L2_CTRL_TYPE_STRING))
4667 + return -EINVAL;
4668 + strscpy(ctrl->p_new.p_char, s, ctrl->maximum + 1);
4669 + return set_ctrl(NULL, ctrl, 0);
4670 +}
4671 +EXPORT_SYMBOL(__v4l2_ctrl_s_ctrl_string);
4672 +
4673 +int __v4l2_ctrl_s_ctrl_compound(struct v4l2_ctrl *ctrl,
4674 + enum v4l2_ctrl_type type, const void *p)
4675 +{
4676 + lockdep_assert_held(ctrl->handler->lock);
4677 +
4678 + /* It's a driver bug if this happens. */
4679 + if (WARN_ON(ctrl->type != type))
4680 + return -EINVAL;
4681 + memcpy(ctrl->p_new.p, p, ctrl->elems * ctrl->elem_size);
4682 + return set_ctrl(NULL, ctrl, 0);
4683 +}
4684 +EXPORT_SYMBOL(__v4l2_ctrl_s_ctrl_compound);
4685 +
4686 +void v4l2_ctrl_request_complete(struct media_request *req,
4687 + struct v4l2_ctrl_handler *main_hdl)
4688 +{
4689 + struct media_request_object *obj;
4690 + struct v4l2_ctrl_handler *hdl;
4691 + struct v4l2_ctrl_ref *ref;
4692 +
4693 + if (!req || !main_hdl)
4694 + return;
4695 +
4696 + /*
4697 + * Note that it is valid if nothing was found. It means
4698 + * that this request doesn't have any controls and so just
4699 + * wants to leave the controls unchanged.
4700 + */
4701 + obj = media_request_object_find(req, &req_ops, main_hdl);
4702 + if (!obj)
4703 + return;
4704 + hdl = container_of(obj, struct v4l2_ctrl_handler, req_obj);
4705 +
4706 + list_for_each_entry(ref, &hdl->ctrl_refs, node) {
4707 + struct v4l2_ctrl *ctrl = ref->ctrl;
4708 + struct v4l2_ctrl *master = ctrl->cluster[0];
4709 + unsigned int i;
4710 +
4711 + if (ctrl->flags & V4L2_CTRL_FLAG_VOLATILE) {
4712 + v4l2_ctrl_lock(master);
4713 + /* g_volatile_ctrl will update the current control values */
4714 + for (i = 0; i < master->ncontrols; i++)
4715 + cur_to_new(master->cluster[i]);
4716 + call_op(master, g_volatile_ctrl);
4717 + new_to_req(ref);
4718 + v4l2_ctrl_unlock(master);
4719 + continue;
4720 + }
4721 + if (ref->valid_p_req)
4722 + continue;
4723 +
4724 + /* Copy the current control value into the request */
4725 + v4l2_ctrl_lock(ctrl);
4726 + cur_to_req(ref);
4727 + v4l2_ctrl_unlock(ctrl);
4728 + }
4729 +
4730 + mutex_lock(main_hdl->lock);
4731 + WARN_ON(!hdl->request_is_queued);
4732 + list_del_init(&hdl->requests_queued);
4733 + hdl->request_is_queued = false;
4734 + mutex_unlock(main_hdl->lock);
4735 + media_request_object_complete(obj);
4736 + media_request_object_put(obj);
4737 +}
4738 +EXPORT_SYMBOL(v4l2_ctrl_request_complete);
4739 +
4740 +int v4l2_ctrl_request_setup(struct media_request *req,
4741 + struct v4l2_ctrl_handler *main_hdl)
4742 +{
4743 + struct media_request_object *obj;
4744 + struct v4l2_ctrl_handler *hdl;
4745 + struct v4l2_ctrl_ref *ref;
4746 + int ret = 0;
4747 +
4748 + if (!req || !main_hdl)
4749 + return 0;
4750 +
4751 + if (WARN_ON(req->state != MEDIA_REQUEST_STATE_QUEUED))
4752 + return -EBUSY;
4753 +
4754 + /*
4755 + * Note that it is valid if nothing was found. It means
4756 + * that this request doesn't have any controls and so just
4757 + * wants to leave the controls unchanged.
4758 + */
4759 + obj = media_request_object_find(req, &req_ops, main_hdl);
4760 + if (!obj)
4761 + return 0;
4762 + if (obj->completed) {
4763 + media_request_object_put(obj);
4764 + return -EBUSY;
4765 + }
4766 + hdl = container_of(obj, struct v4l2_ctrl_handler, req_obj);
4767 +
4768 + list_for_each_entry(ref, &hdl->ctrl_refs, node)
4769 + ref->req_done = false;
4770 +
4771 + list_for_each_entry(ref, &hdl->ctrl_refs, node) {
4772 + struct v4l2_ctrl *ctrl = ref->ctrl;
4773 + struct v4l2_ctrl *master = ctrl->cluster[0];
4774 + bool have_new_data = false;
4775 + int i;
4776 +
4777 + /*
4778 + * Skip if this control was already handled by a cluster.
4779 + * Skip button controls and read-only controls.
4780 + */
4781 + if (ref->req_done || (ctrl->flags & V4L2_CTRL_FLAG_READ_ONLY))
4782 + continue;
4783 +
4784 + v4l2_ctrl_lock(master);
4785 + for (i = 0; i < master->ncontrols; i++) {
4786 + if (master->cluster[i]) {
4787 + struct v4l2_ctrl_ref *r =
4788 + find_ref(hdl, master->cluster[i]->id);
4789 +
4790 + if (r->valid_p_req) {
4791 + have_new_data = true;
4792 + break;
4793 + }
4794 + }
4795 + }
4796 + if (!have_new_data) {
4797 + v4l2_ctrl_unlock(master);
4798 + continue;
4799 + }
4800 +
4801 + for (i = 0; i < master->ncontrols; i++) {
4802 + if (master->cluster[i]) {
4803 + struct v4l2_ctrl_ref *r =
4804 + find_ref(hdl, master->cluster[i]->id);
4805 +
4806 + req_to_new(r);
4807 + master->cluster[i]->is_new = 1;
4808 + r->req_done = true;
4809 + }
4810 + }
4811 + /*
4812 + * For volatile autoclusters that are currently in auto mode
4813 + * we need to discover if it will be set to manual mode.
4814 + * If so, then we have to copy the current volatile values
4815 + * first since those will become the new manual values (which
4816 + * may be overwritten by explicit new values from this set
4817 + * of controls).
4818 + */
4819 + if (master->is_auto && master->has_volatiles &&
4820 + !is_cur_manual(master)) {
4821 + s32 new_auto_val = *master->p_new.p_s32;
4822 +
4823 + /*
4824 + * If the new value == the manual value, then copy
4825 + * the current volatile values.
4826 + */
4827 + if (new_auto_val == master->manual_mode_value)
4828 + update_from_auto_cluster(master);
4829 + }
4830 +
4831 + ret = try_or_set_cluster(NULL, master, true, 0);
4832 + v4l2_ctrl_unlock(master);
4833 +
4834 + if (ret)
4835 + break;
4836 + }
4837 +
4838 + media_request_object_put(obj);
4839 + return ret;
4840 +}
4841 +EXPORT_SYMBOL(v4l2_ctrl_request_setup);
4842 +
4843 +void v4l2_ctrl_notify(struct v4l2_ctrl *ctrl, v4l2_ctrl_notify_fnc notify, void *priv)
4844 +{
4845 + if (ctrl == NULL)
4846 + return;
4847 + if (notify == NULL) {
4848 + ctrl->call_notify = 0;
4849 + return;
4850 + }
4851 + if (WARN_ON(ctrl->handler->notify && ctrl->handler->notify != notify))
4852 + return;
4853 + ctrl->handler->notify = notify;
4854 + ctrl->handler->notify_priv = priv;
4855 + ctrl->call_notify = 1;
4856 +}
4857 +EXPORT_SYMBOL(v4l2_ctrl_notify);
4858 +
4859 +int __v4l2_ctrl_modify_range(struct v4l2_ctrl *ctrl,
4860 + s64 min, s64 max, u64 step, s64 def)
4861 +{
4862 + bool value_changed;
4863 + bool range_changed = false;
4864 + int ret;
4865 +
4866 + lockdep_assert_held(ctrl->handler->lock);
4867 +
4868 + switch (ctrl->type) {
4869 + case V4L2_CTRL_TYPE_INTEGER:
4870 + case V4L2_CTRL_TYPE_INTEGER64:
4871 + case V4L2_CTRL_TYPE_BOOLEAN:
4872 + case V4L2_CTRL_TYPE_MENU:
4873 + case V4L2_CTRL_TYPE_INTEGER_MENU:
4874 + case V4L2_CTRL_TYPE_BITMASK:
4875 + case V4L2_CTRL_TYPE_U8:
4876 + case V4L2_CTRL_TYPE_U16:
4877 + case V4L2_CTRL_TYPE_U32:
4878 + if (ctrl->is_array)
4879 + return -EINVAL;
4880 + ret = check_range(ctrl->type, min, max, step, def);
4881 + if (ret)
4882 + return ret;
4883 + break;
4884 + default:
4885 + return -EINVAL;
4886 + }
4887 + if ((ctrl->minimum != min) || (ctrl->maximum != max) ||
4888 + (ctrl->step != step) || ctrl->default_value != def) {
4889 + range_changed = true;
4890 + ctrl->minimum = min;
4891 + ctrl->maximum = max;
4892 + ctrl->step = step;
4893 + ctrl->default_value = def;
4894 + }
4895 + cur_to_new(ctrl);
4896 + if (validate_new(ctrl, ctrl->p_new)) {
4897 + if (ctrl->type == V4L2_CTRL_TYPE_INTEGER64)
4898 + *ctrl->p_new.p_s64 = def;
4899 + else
4900 + *ctrl->p_new.p_s32 = def;
4901 + }
4902 +
4903 + if (ctrl->type == V4L2_CTRL_TYPE_INTEGER64)
4904 + value_changed = *ctrl->p_new.p_s64 != *ctrl->p_cur.p_s64;
4905 + else
4906 + value_changed = *ctrl->p_new.p_s32 != *ctrl->p_cur.p_s32;
4907 + if (value_changed)
4908 + ret = set_ctrl(NULL, ctrl, V4L2_EVENT_CTRL_CH_RANGE);
4909 + else if (range_changed)
4910 + send_event(NULL, ctrl, V4L2_EVENT_CTRL_CH_RANGE);
4911 + return ret;
4912 +}
4913 +EXPORT_SYMBOL(__v4l2_ctrl_modify_range);
4914 +
4915 +static int v4l2_ctrl_add_event(struct v4l2_subscribed_event *sev, unsigned elems)
4916 +{
4917 + struct v4l2_ctrl *ctrl = v4l2_ctrl_find(sev->fh->ctrl_handler, sev->id);
4918 +
4919 + if (ctrl == NULL)
4920 + return -EINVAL;
4921 +
4922 + v4l2_ctrl_lock(ctrl);
4923 + list_add_tail(&sev->node, &ctrl->ev_subs);
4924 + if (ctrl->type != V4L2_CTRL_TYPE_CTRL_CLASS &&
4925 + (sev->flags & V4L2_EVENT_SUB_FL_SEND_INITIAL)) {
4926 + struct v4l2_event ev;
4927 + u32 changes = V4L2_EVENT_CTRL_CH_FLAGS;
4928 +
4929 + if (!(ctrl->flags & V4L2_CTRL_FLAG_WRITE_ONLY))
4930 + changes |= V4L2_EVENT_CTRL_CH_VALUE;
4931 + fill_event(&ev, ctrl, changes);
4932 + /* Mark the queue as active, allowing this initial
4933 + event to be accepted. */
4934 + sev->elems = elems;
4935 + v4l2_event_queue_fh(sev->fh, &ev);
4936 + }
4937 + v4l2_ctrl_unlock(ctrl);
4938 + return 0;
4939 +}
4940 +
4941 +static void v4l2_ctrl_del_event(struct v4l2_subscribed_event *sev)
4942 +{
4943 + struct v4l2_ctrl *ctrl = v4l2_ctrl_find(sev->fh->ctrl_handler, sev->id);
4944 +
4945 + if (ctrl == NULL)
4946 + return;
4947 +
4948 + v4l2_ctrl_lock(ctrl);
4949 + list_del(&sev->node);
4950 + v4l2_ctrl_unlock(ctrl);
4951 +}
4952 +
4953 +void v4l2_ctrl_replace(struct v4l2_event *old, const struct v4l2_event *new)
4954 +{
4955 + u32 old_changes = old->u.ctrl.changes;
4956 +
4957 + old->u.ctrl = new->u.ctrl;
4958 + old->u.ctrl.changes |= old_changes;
4959 +}
4960 +EXPORT_SYMBOL(v4l2_ctrl_replace);
4961 +
4962 +void v4l2_ctrl_merge(const struct v4l2_event *old, struct v4l2_event *new)
4963 +{
4964 + new->u.ctrl.changes |= old->u.ctrl.changes;
4965 +}
4966 +EXPORT_SYMBOL(v4l2_ctrl_merge);
4967 +
4968 +const struct v4l2_subscribed_event_ops v4l2_ctrl_sub_ev_ops = {
4969 + .add = v4l2_ctrl_add_event,
4970 + .del = v4l2_ctrl_del_event,
4971 + .replace = v4l2_ctrl_replace,
4972 + .merge = v4l2_ctrl_merge,
4973 +};
4974 +EXPORT_SYMBOL(v4l2_ctrl_sub_ev_ops);
4975 +
4976 +int v4l2_ctrl_log_status(struct file *file, void *fh)
4977 +{
4978 + struct video_device *vfd = video_devdata(file);
4979 + struct v4l2_fh *vfh = file->private_data;
4980 +
4981 + if (test_bit(V4L2_FL_USES_V4L2_FH, &vfd->flags) && vfd->v4l2_dev)
4982 + v4l2_ctrl_handler_log_status(vfh->ctrl_handler,
4983 + vfd->v4l2_dev->name);
4984 + return 0;
4985 +}
4986 +EXPORT_SYMBOL(v4l2_ctrl_log_status);
4987 +
4988 +int v4l2_ctrl_subscribe_event(struct v4l2_fh *fh,
4989 + const struct v4l2_event_subscription *sub)
4990 +{
4991 + if (sub->type == V4L2_EVENT_CTRL)
4992 + return v4l2_event_subscribe(fh, sub, 0, &v4l2_ctrl_sub_ev_ops);
4993 + return -EINVAL;
4994 +}
4995 +EXPORT_SYMBOL(v4l2_ctrl_subscribe_event);
4996 +
4997 +int v4l2_ctrl_subdev_subscribe_event(struct v4l2_subdev *sd, struct v4l2_fh *fh,
4998 + struct v4l2_event_subscription *sub)
4999 +{
5000 + if (!sd->ctrl_handler)
5001 + return -EINVAL;
5002 + return v4l2_ctrl_subscribe_event(fh, sub);
5003 +}
5004 +EXPORT_SYMBOL(v4l2_ctrl_subdev_subscribe_event);
5005 +
5006 +__poll_t v4l2_ctrl_poll(struct file *file, struct poll_table_struct *wait)
5007 +{
5008 + struct v4l2_fh *fh = file->private_data;
5009 +
5010 + poll_wait(file, &fh->wait, wait);
5011 + if (v4l2_event_pending(fh))
5012 + return EPOLLPRI;
5013 + return 0;
5014 +}
5015 +EXPORT_SYMBOL(v4l2_ctrl_poll);
5016 +
5017 +int v4l2_ctrl_new_fwnode_properties(struct v4l2_ctrl_handler *hdl,
5018 + const struct v4l2_ctrl_ops *ctrl_ops,
5019 + const struct v4l2_fwnode_device_properties *p)
5020 +{
5021 + if (p->orientation != V4L2_FWNODE_PROPERTY_UNSET) {
5022 + u32 orientation_ctrl;
5023 +
5024 + switch (p->orientation) {
5025 + case V4L2_FWNODE_ORIENTATION_FRONT:
5026 + orientation_ctrl = V4L2_CAMERA_ORIENTATION_FRONT;
5027 + break;
5028 + case V4L2_FWNODE_ORIENTATION_BACK:
5029 + orientation_ctrl = V4L2_CAMERA_ORIENTATION_BACK;
5030 + break;
5031 + case V4L2_FWNODE_ORIENTATION_EXTERNAL:
5032 + orientation_ctrl = V4L2_CAMERA_ORIENTATION_EXTERNAL;
5033 + break;
5034 + default:
5035 + return -EINVAL;
5036 + }
5037 + if (!v4l2_ctrl_new_std_menu(hdl, ctrl_ops,
5038 + V4L2_CID_CAMERA_ORIENTATION,
5039 + V4L2_CAMERA_ORIENTATION_EXTERNAL, 0,
5040 + orientation_ctrl))
5041 + return hdl->error;
5042 + }
5043 +
5044 + if (p->rotation != V4L2_FWNODE_PROPERTY_UNSET) {
5045 + if (!v4l2_ctrl_new_std(hdl, ctrl_ops,
5046 + V4L2_CID_CAMERA_SENSOR_ROTATION,
5047 + p->rotation, p->rotation, 1,
5048 + p->rotation))
5049 + return hdl->error;
5050 + }
5051 +
5052 + return hdl->error;
5053 +}
5054 +EXPORT_SYMBOL(v4l2_ctrl_new_fwnode_properties);
5055 --- a/include/uapi/linux/v4l2-controls.h
5056 +++ b/include/uapi/linux/v4l2-controls.h
5057 @@ -926,6 +926,7 @@ enum v4l2_auto_n_preset_white_balance {
5058 V4L2_WHITE_BALANCE_FLASH = 7,
5059 V4L2_WHITE_BALANCE_CLOUDY = 8,
5060 V4L2_WHITE_BALANCE_SHADE = 9,
5061 + V4L2_WHITE_BALANCE_GREYWORLD = 10,
5062 };
5063
5064 #define V4L2_CID_WIDE_DYNAMIC_RANGE (V4L2_CID_CAMERA_CLASS_BASE+21)