1 // SPDX-License-Identifier: GPL-2.0-only
2 /*
3 * vivid-ctrls.c - control support functions.
4 *
5 * Copyright 2014 Cisco Systems, Inc. and/or its affiliates. All rights reserved.
6 */
7
8 #include <linux/errno.h>
9 #include <linux/kernel.h>
10 #include <linux/videodev2.h>
11 #include <media/v4l2-event.h>
12 #include <media/v4l2-common.h>
13
14 #include "vivid-core.h"
15 #include "vivid-vid-cap.h"
16 #include "vivid-vid-out.h"
17 #include "vivid-vid-common.h"
18 #include "vivid-radio-common.h"
19 #include "vivid-osd.h"
20 #include "vivid-ctrls.h"
21
22 #define VIVID_CID_CUSTOM_BASE (V4L2_CID_USER_BASE | 0xf000)
23 #define VIVID_CID_BUTTON (VIVID_CID_CUSTOM_BASE + 0)
24 #define VIVID_CID_BOOLEAN (VIVID_CID_CUSTOM_BASE + 1)
25 #define VIVID_CID_INTEGER (VIVID_CID_CUSTOM_BASE + 2)
26 #define VIVID_CID_INTEGER64 (VIVID_CID_CUSTOM_BASE + 3)
27 #define VIVID_CID_MENU (VIVID_CID_CUSTOM_BASE + 4)
28 #define VIVID_CID_STRING (VIVID_CID_CUSTOM_BASE + 5)
29 #define VIVID_CID_BITMASK (VIVID_CID_CUSTOM_BASE + 6)
30 #define VIVID_CID_INTMENU (VIVID_CID_CUSTOM_BASE + 7)
31 #define VIVID_CID_U32_ARRAY (VIVID_CID_CUSTOM_BASE + 8)
32 #define VIVID_CID_U16_MATRIX (VIVID_CID_CUSTOM_BASE + 9)
33 #define VIVID_CID_U8_4D_ARRAY (VIVID_CID_CUSTOM_BASE + 10)
34 #define VIVID_CID_AREA (VIVID_CID_CUSTOM_BASE + 11)
35 #define VIVID_CID_RO_INTEGER (VIVID_CID_CUSTOM_BASE + 12)
36 #define VIVID_CID_U32_DYN_ARRAY (VIVID_CID_CUSTOM_BASE + 13)
37 #define VIVID_CID_U8_PIXEL_ARRAY (VIVID_CID_CUSTOM_BASE + 14)
38 #define VIVID_CID_S32_ARRAY (VIVID_CID_CUSTOM_BASE + 15)
39 #define VIVID_CID_S64_ARRAY (VIVID_CID_CUSTOM_BASE + 16)
40 #define VIVID_CID_RECT (VIVID_CID_CUSTOM_BASE + 17)
41
42 #define VIVID_CID_VIVID_BASE (0x00f00000 | 0xf000)
43 #define VIVID_CID_VIVID_CLASS (0x00f00000 | 1)
44 #define VIVID_CID_TEST_PATTERN (VIVID_CID_VIVID_BASE + 0)
45 #define VIVID_CID_OSD_TEXT_MODE (VIVID_CID_VIVID_BASE + 1)
46 #define VIVID_CID_HOR_MOVEMENT (VIVID_CID_VIVID_BASE + 2)
47 #define VIVID_CID_VERT_MOVEMENT (VIVID_CID_VIVID_BASE + 3)
48 #define VIVID_CID_SHOW_BORDER (VIVID_CID_VIVID_BASE + 4)
49 #define VIVID_CID_SHOW_SQUARE (VIVID_CID_VIVID_BASE + 5)
50 #define VIVID_CID_INSERT_SAV (VIVID_CID_VIVID_BASE + 6)
51 #define VIVID_CID_INSERT_EAV (VIVID_CID_VIVID_BASE + 7)
52 #define VIVID_CID_VBI_CAP_INTERLACED (VIVID_CID_VIVID_BASE + 8)
53 #define VIVID_CID_INSERT_HDMI_VIDEO_GUARD_BAND (VIVID_CID_VIVID_BASE + 9)
54
55 #define VIVID_CID_HFLIP (VIVID_CID_VIVID_BASE + 20)
56 #define VIVID_CID_VFLIP (VIVID_CID_VIVID_BASE + 21)
57 #define VIVID_CID_STD_ASPECT_RATIO (VIVID_CID_VIVID_BASE + 22)
58 #define VIVID_CID_DV_TIMINGS_ASPECT_RATIO (VIVID_CID_VIVID_BASE + 23)
59 #define VIVID_CID_TSTAMP_SRC (VIVID_CID_VIVID_BASE + 24)
60 #define VIVID_CID_COLORSPACE (VIVID_CID_VIVID_BASE + 25)
61 #define VIVID_CID_XFER_FUNC (VIVID_CID_VIVID_BASE + 26)
62 #define VIVID_CID_YCBCR_ENC (VIVID_CID_VIVID_BASE + 27)
63 #define VIVID_CID_QUANTIZATION (VIVID_CID_VIVID_BASE + 28)
64 #define VIVID_CID_LIMITED_RGB_RANGE (VIVID_CID_VIVID_BASE + 29)
65 #define VIVID_CID_ALPHA_MODE (VIVID_CID_VIVID_BASE + 30)
66 #define VIVID_CID_HAS_CROP_CAP (VIVID_CID_VIVID_BASE + 31)
67 #define VIVID_CID_HAS_COMPOSE_CAP (VIVID_CID_VIVID_BASE + 32)
68 #define VIVID_CID_HAS_SCALER_CAP (VIVID_CID_VIVID_BASE + 33)
69 #define VIVID_CID_HAS_CROP_OUT (VIVID_CID_VIVID_BASE + 34)
70 #define VIVID_CID_HAS_COMPOSE_OUT (VIVID_CID_VIVID_BASE + 35)
71 #define VIVID_CID_HAS_SCALER_OUT (VIVID_CID_VIVID_BASE + 36)
72 #define VIVID_CID_SEQ_WRAP (VIVID_CID_VIVID_BASE + 38)
73 #define VIVID_CID_TIME_WRAP (VIVID_CID_VIVID_BASE + 39)
74 #define VIVID_CID_MAX_EDID_BLOCKS (VIVID_CID_VIVID_BASE + 40)
75 #define VIVID_CID_PERCENTAGE_FILL (VIVID_CID_VIVID_BASE + 41)
76 #define VIVID_CID_REDUCED_FPS (VIVID_CID_VIVID_BASE + 42)
77 #define VIVID_CID_HSV_ENC (VIVID_CID_VIVID_BASE + 43)
78
79 #define VIVID_CID_STD_SIGNAL_MODE (VIVID_CID_VIVID_BASE + 60)
80 #define VIVID_CID_STANDARD (VIVID_CID_VIVID_BASE + 61)
81 #define VIVID_CID_DV_TIMINGS_SIGNAL_MODE (VIVID_CID_VIVID_BASE + 62)
82 #define VIVID_CID_DV_TIMINGS (VIVID_CID_VIVID_BASE + 63)
83 #define VIVID_CID_PERC_DROPPED (VIVID_CID_VIVID_BASE + 64)
84 #define VIVID_CID_DISCONNECT (VIVID_CID_VIVID_BASE + 65)
85 #define VIVID_CID_DQBUF_ERROR (VIVID_CID_VIVID_BASE + 66)
86 #define VIVID_CID_QUEUE_SETUP_ERROR (VIVID_CID_VIVID_BASE + 67)
87 #define VIVID_CID_BUF_PREPARE_ERROR (VIVID_CID_VIVID_BASE + 68)
88 #define VIVID_CID_START_STR_ERROR (VIVID_CID_VIVID_BASE + 69)
89 #define VIVID_CID_QUEUE_ERROR (VIVID_CID_VIVID_BASE + 70)
90 #define VIVID_CID_CLEAR_FB (VIVID_CID_VIVID_BASE + 71)
91 #define VIVID_CID_REQ_VALIDATE_ERROR (VIVID_CID_VIVID_BASE + 72)
92
93 #define VIVID_CID_RADIO_SEEK_MODE (VIVID_CID_VIVID_BASE + 90)
94 #define VIVID_CID_RADIO_SEEK_PROG_LIM (VIVID_CID_VIVID_BASE + 91)
95 #define VIVID_CID_RADIO_RX_RDS_RBDS (VIVID_CID_VIVID_BASE + 92)
96 #define VIVID_CID_RADIO_RX_RDS_BLOCKIO (VIVID_CID_VIVID_BASE + 93)
97
98 #define VIVID_CID_RADIO_TX_RDS_BLOCKIO (VIVID_CID_VIVID_BASE + 94)
99
100 #define VIVID_CID_SDR_CAP_FM_DEVIATION (VIVID_CID_VIVID_BASE + 110)
101
102 #define VIVID_CID_META_CAP_GENERATE_PTS (VIVID_CID_VIVID_BASE + 111)
103 #define VIVID_CID_META_CAP_GENERATE_SCR (VIVID_CID_VIVID_BASE + 112)
104
105 /* HDMI inputs are in the range 0-14. The next available CID is VIVID_CID_VIVID_BASE + 128 */
106 #define VIVID_CID_HDMI_IS_CONNECTED_TO_OUTPUT(input) (VIVID_CID_VIVID_BASE + 113 + (input))
107
108 /* S-Video inputs are in the range 0-15. The next available CID is VIVID_CID_VIVID_BASE + 144 */
109 #define VIVID_CID_SVID_IS_CONNECTED_TO_OUTPUT(input) (VIVID_CID_VIVID_BASE + 128 + (input))
110
111 /* General User Controls */
112
vivid_unregister_dev(bool valid,struct video_device * vdev)113 static void vivid_unregister_dev(bool valid, struct video_device *vdev)
114 {
115 if (!valid)
116 return;
117 clear_bit(V4L2_FL_REGISTERED, &vdev->flags);
118 v4l2_event_wake_all(vdev);
119 }
120
vivid_user_gen_s_ctrl(struct v4l2_ctrl * ctrl)121 static int vivid_user_gen_s_ctrl(struct v4l2_ctrl *ctrl)
122 {
123 struct vivid_dev *dev = container_of(ctrl->handler, struct vivid_dev, ctrl_hdl_user_gen);
124
125 switch (ctrl->id) {
126 case VIVID_CID_DISCONNECT:
127 v4l2_info(&dev->v4l2_dev, "disconnect\n");
128 dev->disconnect_error = true;
129 vivid_unregister_dev(dev->has_vid_cap, &dev->vid_cap_dev);
130 vivid_unregister_dev(dev->has_vid_out, &dev->vid_out_dev);
131 vivid_unregister_dev(dev->has_vbi_cap, &dev->vbi_cap_dev);
132 vivid_unregister_dev(dev->has_vbi_out, &dev->vbi_out_dev);
133 vivid_unregister_dev(dev->has_radio_rx, &dev->radio_rx_dev);
134 vivid_unregister_dev(dev->has_radio_tx, &dev->radio_tx_dev);
135 vivid_unregister_dev(dev->has_sdr_cap, &dev->sdr_cap_dev);
136 vivid_unregister_dev(dev->has_meta_cap, &dev->meta_cap_dev);
137 vivid_unregister_dev(dev->has_meta_out, &dev->meta_out_dev);
138 vivid_unregister_dev(dev->has_touch_cap, &dev->touch_cap_dev);
139 break;
140 case VIVID_CID_BUTTON:
141 dev->button_pressed = 30;
142 break;
143 }
144 return 0;
145 }
146
147 static const struct v4l2_ctrl_ops vivid_user_gen_ctrl_ops = {
148 .s_ctrl = vivid_user_gen_s_ctrl,
149 };
150
151 static const struct v4l2_ctrl_config vivid_ctrl_button = {
152 .ops = &vivid_user_gen_ctrl_ops,
153 .id = VIVID_CID_BUTTON,
154 .name = "Button",
155 .type = V4L2_CTRL_TYPE_BUTTON,
156 };
157
158 static const struct v4l2_ctrl_config vivid_ctrl_boolean = {
159 .ops = &vivid_user_gen_ctrl_ops,
160 .id = VIVID_CID_BOOLEAN,
161 .name = "Boolean",
162 .type = V4L2_CTRL_TYPE_BOOLEAN,
163 .min = 0,
164 .max = 1,
165 .step = 1,
166 .def = 1,
167 };
168
169 static const struct v4l2_ctrl_config vivid_ctrl_int32 = {
170 .ops = &vivid_user_gen_ctrl_ops,
171 .id = VIVID_CID_INTEGER,
172 .name = "Integer 32 Bits",
173 .type = V4L2_CTRL_TYPE_INTEGER,
174 .min = 0xffffffff80000000ULL,
175 .max = 0x7fffffff,
176 .step = 1,
177 };
178
179 static const struct v4l2_ctrl_config vivid_ctrl_int64 = {
180 .ops = &vivid_user_gen_ctrl_ops,
181 .id = VIVID_CID_INTEGER64,
182 .name = "Integer 64 Bits",
183 .type = V4L2_CTRL_TYPE_INTEGER64,
184 .min = 0x8000000000000000ULL,
185 .max = 0x7fffffffffffffffLL,
186 .step = 1,
187 };
188
189 static const struct v4l2_ctrl_config vivid_ctrl_u32_array = {
190 .ops = &vivid_user_gen_ctrl_ops,
191 .id = VIVID_CID_U32_ARRAY,
192 .name = "U32 1 Element Array",
193 .type = V4L2_CTRL_TYPE_U32,
194 .def = 0x18,
195 .min = 0x10,
196 .max = 0x20000,
197 .step = 1,
198 .dims = { 1 },
199 };
200
201 static const struct v4l2_ctrl_config vivid_ctrl_u32_dyn_array = {
202 .ops = &vivid_user_gen_ctrl_ops,
203 .id = VIVID_CID_U32_DYN_ARRAY,
204 .name = "U32 Dynamic Array",
205 .type = V4L2_CTRL_TYPE_U32,
206 .flags = V4L2_CTRL_FLAG_DYNAMIC_ARRAY,
207 .def = 50,
208 .min = 10,
209 .max = 90,
210 .step = 1,
211 .dims = { 100 },
212 };
213
214 static const struct v4l2_ctrl_config vivid_ctrl_u16_matrix = {
215 .ops = &vivid_user_gen_ctrl_ops,
216 .id = VIVID_CID_U16_MATRIX,
217 .name = "U16 8x16 Matrix",
218 .type = V4L2_CTRL_TYPE_U16,
219 .def = 0x18,
220 .min = 0x10,
221 .max = 0x2000,
222 .step = 1,
223 .dims = { 8, 16 },
224 };
225
226 static const struct v4l2_ctrl_config vivid_ctrl_u8_4d_array = {
227 .ops = &vivid_user_gen_ctrl_ops,
228 .id = VIVID_CID_U8_4D_ARRAY,
229 .name = "U8 2x3x4x5 Array",
230 .type = V4L2_CTRL_TYPE_U8,
231 .def = 0x18,
232 .min = 0x10,
233 .max = 0x20,
234 .step = 1,
235 .dims = { 2, 3, 4, 5 },
236 };
237
238 static const struct v4l2_ctrl_config vivid_ctrl_u8_pixel_array = {
239 .ops = &vivid_user_gen_ctrl_ops,
240 .id = VIVID_CID_U8_PIXEL_ARRAY,
241 .name = "U8 Pixel Array",
242 .type = V4L2_CTRL_TYPE_U8,
243 .def = 0x80,
244 .min = 0x00,
245 .max = 0xff,
246 .step = 1,
247 .dims = { DIV_ROUND_UP(360, PIXEL_ARRAY_DIV),
248 DIV_ROUND_UP(640, PIXEL_ARRAY_DIV) },
249 };
250
251 static const struct v4l2_ctrl_config vivid_ctrl_s32_array = {
252 .ops = &vivid_user_gen_ctrl_ops,
253 .id = VIVID_CID_S32_ARRAY,
254 .name = "S32 2 Element Array",
255 .type = V4L2_CTRL_TYPE_INTEGER,
256 .def = 2,
257 .min = -10,
258 .max = 10,
259 .step = 1,
260 .dims = { 2 },
261 };
262
263 static const struct v4l2_ctrl_config vivid_ctrl_s64_array = {
264 .ops = &vivid_user_gen_ctrl_ops,
265 .id = VIVID_CID_S64_ARRAY,
266 .name = "S64 5 Element Array",
267 .type = V4L2_CTRL_TYPE_INTEGER64,
268 .def = 4,
269 .min = -10,
270 .max = 10,
271 .step = 1,
272 .dims = { 5 },
273 };
274
275 static const char * const vivid_ctrl_menu_strings[] = {
276 "Menu Item 0 (Skipped)",
277 "Menu Item 1",
278 "Menu Item 2 (Skipped)",
279 "Menu Item 3",
280 "Menu Item 4",
281 "Menu Item 5 (Skipped)",
282 NULL,
283 };
284
285 static const struct v4l2_ctrl_config vivid_ctrl_menu = {
286 .ops = &vivid_user_gen_ctrl_ops,
287 .id = VIVID_CID_MENU,
288 .name = "Menu",
289 .type = V4L2_CTRL_TYPE_MENU,
290 .min = 1,
291 .max = 4,
292 .def = 3,
293 .menu_skip_mask = 0x04,
294 .qmenu = vivid_ctrl_menu_strings,
295 };
296
297 static const struct v4l2_ctrl_config vivid_ctrl_string = {
298 .ops = &vivid_user_gen_ctrl_ops,
299 .id = VIVID_CID_STRING,
300 .name = "String",
301 .type = V4L2_CTRL_TYPE_STRING,
302 .min = 2,
303 .max = 4,
304 .step = 1,
305 };
306
307 static const struct v4l2_ctrl_config vivid_ctrl_bitmask = {
308 .ops = &vivid_user_gen_ctrl_ops,
309 .id = VIVID_CID_BITMASK,
310 .name = "Bitmask",
311 .type = V4L2_CTRL_TYPE_BITMASK,
312 .def = 0x80002000,
313 .min = 0,
314 .max = 0x80402010,
315 .step = 0,
316 };
317
318 static const s64 vivid_ctrl_int_menu_values[] = {
319 1, 1, 2, 3, 5, 8, 13, 21, 42,
320 };
321
322 static const struct v4l2_ctrl_config vivid_ctrl_int_menu = {
323 .ops = &vivid_user_gen_ctrl_ops,
324 .id = VIVID_CID_INTMENU,
325 .name = "Integer Menu",
326 .type = V4L2_CTRL_TYPE_INTEGER_MENU,
327 .min = 1,
328 .max = 8,
329 .def = 4,
330 .menu_skip_mask = 0x02,
331 .qmenu_int = vivid_ctrl_int_menu_values,
332 };
333
334 static const struct v4l2_ctrl_config vivid_ctrl_disconnect = {
335 .ops = &vivid_user_gen_ctrl_ops,
336 .id = VIVID_CID_DISCONNECT,
337 .name = "Disconnect",
338 .type = V4L2_CTRL_TYPE_BUTTON,
339 };
340
341 static const struct v4l2_area area = {
342 .width = 1000,
343 .height = 2000,
344 };
345
346 static const struct v4l2_ctrl_config vivid_ctrl_area = {
347 .ops = &vivid_user_gen_ctrl_ops,
348 .id = VIVID_CID_AREA,
349 .name = "Area",
350 .type = V4L2_CTRL_TYPE_AREA,
351 .p_def.p_const = &area,
352 };
353
354 static const struct v4l2_ctrl_config vivid_ctrl_ro_int32 = {
355 .ops = &vivid_user_gen_ctrl_ops,
356 .id = VIVID_CID_RO_INTEGER,
357 .name = "Read-Only Integer 32 Bits",
358 .type = V4L2_CTRL_TYPE_INTEGER,
359 .flags = V4L2_CTRL_FLAG_READ_ONLY,
360 .min = 0,
361 .max = 255,
362 .step = 1,
363 };
364
365 static const struct v4l2_rect rect_def = {
366 .top = 100,
367 .left = 200,
368 .width = 300,
369 .height = 400,
370 };
371
372 static const struct v4l2_rect rect_min = {
373 .top = 0,
374 .left = 0,
375 .width = 1,
376 .height = 1,
377 };
378
379 static const struct v4l2_rect rect_max = {
380 .top = 0,
381 .left = 0,
382 .width = 1000,
383 .height = 2000,
384 };
385
386 static const struct v4l2_ctrl_config vivid_ctrl_rect = {
387 .ops = &vivid_user_gen_ctrl_ops,
388 .id = VIVID_CID_RECT,
389 .name = "Rect",
390 .type = V4L2_CTRL_TYPE_RECT,
391 .flags = V4L2_CTRL_FLAG_HAS_WHICH_MIN_MAX,
392 .p_def.p_const = &rect_def,
393 .p_min.p_const = &rect_min,
394 .p_max.p_const = &rect_max,
395 };
396
397 /* Framebuffer Controls */
398
vivid_fb_s_ctrl(struct v4l2_ctrl * ctrl)399 static int vivid_fb_s_ctrl(struct v4l2_ctrl *ctrl)
400 {
401 struct vivid_dev *dev = container_of(ctrl->handler,
402 struct vivid_dev, ctrl_hdl_fb);
403
404 switch (ctrl->id) {
405 case VIVID_CID_CLEAR_FB:
406 vivid_fb_clear(dev);
407 break;
408 }
409 return 0;
410 }
411
412 static const struct v4l2_ctrl_ops vivid_fb_ctrl_ops = {
413 .s_ctrl = vivid_fb_s_ctrl,
414 };
415
416 static const struct v4l2_ctrl_config vivid_ctrl_clear_fb = {
417 .ops = &vivid_fb_ctrl_ops,
418 .id = VIVID_CID_CLEAR_FB,
419 .name = "Clear Framebuffer",
420 .type = V4L2_CTRL_TYPE_BUTTON,
421 };
422
423
424 /* Video User Controls */
425
vivid_user_vid_g_volatile_ctrl(struct v4l2_ctrl * ctrl)426 static int vivid_user_vid_g_volatile_ctrl(struct v4l2_ctrl *ctrl)
427 {
428 struct vivid_dev *dev = container_of(ctrl->handler, struct vivid_dev, ctrl_hdl_user_vid);
429
430 switch (ctrl->id) {
431 case V4L2_CID_AUTOGAIN:
432 dev->gain->val = (jiffies_to_msecs(jiffies) / 1000) & 0xff;
433 break;
434 }
435 return 0;
436 }
437
vivid_user_vid_s_ctrl(struct v4l2_ctrl * ctrl)438 static int vivid_user_vid_s_ctrl(struct v4l2_ctrl *ctrl)
439 {
440 struct vivid_dev *dev = container_of(ctrl->handler, struct vivid_dev, ctrl_hdl_user_vid);
441
442 switch (ctrl->id) {
443 case V4L2_CID_BRIGHTNESS:
444 dev->input_brightness[dev->input] = ctrl->val - dev->input * 128;
445 tpg_s_brightness(&dev->tpg, dev->input_brightness[dev->input]);
446 break;
447 case V4L2_CID_CONTRAST:
448 tpg_s_contrast(&dev->tpg, ctrl->val);
449 break;
450 case V4L2_CID_SATURATION:
451 tpg_s_saturation(&dev->tpg, ctrl->val);
452 break;
453 case V4L2_CID_HUE:
454 tpg_s_hue(&dev->tpg, ctrl->val);
455 break;
456 case V4L2_CID_HFLIP:
457 dev->hflip = ctrl->val;
458 tpg_s_hflip(&dev->tpg, dev->sensor_hflip ^ dev->hflip);
459 break;
460 case V4L2_CID_VFLIP:
461 dev->vflip = ctrl->val;
462 tpg_s_vflip(&dev->tpg, dev->sensor_vflip ^ dev->vflip);
463 break;
464 case V4L2_CID_ALPHA_COMPONENT:
465 tpg_s_alpha_component(&dev->tpg, ctrl->val);
466 break;
467 }
468 return 0;
469 }
470
471 static const struct v4l2_ctrl_ops vivid_user_vid_ctrl_ops = {
472 .g_volatile_ctrl = vivid_user_vid_g_volatile_ctrl,
473 .s_ctrl = vivid_user_vid_s_ctrl,
474 };
475
476
477 /* Video Capture Controls */
478
vivid_update_power_present(struct vivid_dev * dev)479 static void vivid_update_power_present(struct vivid_dev *dev)
480 {
481 unsigned int i, j;
482
483 dev->power_present = 0;
484 for (i = 0, j = 0;
485 i < ARRAY_SIZE(dev->dv_timings_signal_mode); i++) {
486 if (dev->input_type[i] != HDMI)
487 continue;
488 /*
489 * If connected to TPG or HDMI output, and the signal
490 * mode is not NO_SIGNAL, then there is power present.
491 */
492 if (dev->input_is_connected_to_output[i] != 1 &&
493 dev->dv_timings_signal_mode[i] != NO_SIGNAL)
494 dev->power_present |= (1 << j);
495 j++;
496 }
497
498 __v4l2_ctrl_s_ctrl(dev->ctrl_rx_power_present,
499 dev->power_present);
500
501 v4l2_ctrl_activate(dev->ctrl_dv_timings,
502 dev->dv_timings_signal_mode[dev->input] ==
503 SELECTED_DV_TIMINGS);
504 }
505
vivid_vid_cap_s_ctrl(struct v4l2_ctrl * ctrl)506 static int vivid_vid_cap_s_ctrl(struct v4l2_ctrl *ctrl)
507 {
508 static const u32 colorspaces[] = {
509 V4L2_COLORSPACE_SMPTE170M,
510 V4L2_COLORSPACE_REC709,
511 V4L2_COLORSPACE_SRGB,
512 V4L2_COLORSPACE_OPRGB,
513 V4L2_COLORSPACE_BT2020,
514 V4L2_COLORSPACE_DCI_P3,
515 V4L2_COLORSPACE_SMPTE240M,
516 V4L2_COLORSPACE_470_SYSTEM_M,
517 V4L2_COLORSPACE_470_SYSTEM_BG,
518 };
519 struct vivid_dev *dev = container_of(ctrl->handler, struct vivid_dev, ctrl_hdl_vid_cap);
520 unsigned int i;
521 struct vivid_dev *output_inst = NULL;
522 int index = 0;
523 int hdmi_index, svid_index;
524 s32 input_index = 0;
525
526 switch (ctrl->id) {
527 case VIVID_CID_TEST_PATTERN:
528 vivid_update_quality(dev);
529 tpg_s_pattern(&dev->tpg, ctrl->val);
530 break;
531 case VIVID_CID_COLORSPACE:
532 tpg_s_colorspace(&dev->tpg, colorspaces[ctrl->val]);
533 vivid_send_source_change(dev, TV);
534 vivid_send_source_change(dev, SVID);
535 vivid_send_source_change(dev, HDMI);
536 vivid_send_source_change(dev, WEBCAM);
537 break;
538 case VIVID_CID_XFER_FUNC:
539 tpg_s_xfer_func(&dev->tpg, ctrl->val);
540 vivid_send_source_change(dev, TV);
541 vivid_send_source_change(dev, SVID);
542 vivid_send_source_change(dev, HDMI);
543 vivid_send_source_change(dev, WEBCAM);
544 break;
545 case VIVID_CID_YCBCR_ENC:
546 tpg_s_ycbcr_enc(&dev->tpg, ctrl->val);
547 vivid_send_source_change(dev, TV);
548 vivid_send_source_change(dev, SVID);
549 vivid_send_source_change(dev, HDMI);
550 vivid_send_source_change(dev, WEBCAM);
551 break;
552 case VIVID_CID_HSV_ENC:
553 tpg_s_hsv_enc(&dev->tpg, ctrl->val ? V4L2_HSV_ENC_256 :
554 V4L2_HSV_ENC_180);
555 vivid_send_source_change(dev, TV);
556 vivid_send_source_change(dev, SVID);
557 vivid_send_source_change(dev, HDMI);
558 vivid_send_source_change(dev, WEBCAM);
559 break;
560 case VIVID_CID_QUANTIZATION:
561 tpg_s_quantization(&dev->tpg, ctrl->val);
562 vivid_send_source_change(dev, TV);
563 vivid_send_source_change(dev, SVID);
564 vivid_send_source_change(dev, HDMI);
565 vivid_send_source_change(dev, WEBCAM);
566 break;
567 case V4L2_CID_DV_RX_RGB_RANGE:
568 if (!vivid_is_hdmi_cap(dev))
569 break;
570 tpg_s_rgb_range(&dev->tpg, ctrl->val);
571 break;
572 case VIVID_CID_LIMITED_RGB_RANGE:
573 tpg_s_real_rgb_range(&dev->tpg, ctrl->val ?
574 V4L2_DV_RGB_RANGE_LIMITED : V4L2_DV_RGB_RANGE_FULL);
575 break;
576 case VIVID_CID_ALPHA_MODE:
577 tpg_s_alpha_mode(&dev->tpg, ctrl->val);
578 break;
579 case VIVID_CID_HOR_MOVEMENT:
580 tpg_s_mv_hor_mode(&dev->tpg, ctrl->val);
581 break;
582 case VIVID_CID_VERT_MOVEMENT:
583 tpg_s_mv_vert_mode(&dev->tpg, ctrl->val);
584 break;
585 case VIVID_CID_OSD_TEXT_MODE:
586 dev->osd_mode = ctrl->val;
587 break;
588 case VIVID_CID_PERCENTAGE_FILL:
589 tpg_s_perc_fill(&dev->tpg, ctrl->val);
590 for (i = 0; i < MAX_VID_CAP_BUFFERS; i++)
591 dev->must_blank[i] = ctrl->val < 100;
592 break;
593 case VIVID_CID_INSERT_SAV:
594 tpg_s_insert_sav(&dev->tpg, ctrl->val);
595 break;
596 case VIVID_CID_INSERT_EAV:
597 tpg_s_insert_eav(&dev->tpg, ctrl->val);
598 break;
599 case VIVID_CID_INSERT_HDMI_VIDEO_GUARD_BAND:
600 tpg_s_insert_hdmi_video_guard_band(&dev->tpg, ctrl->val);
601 break;
602 case VIVID_CID_HFLIP:
603 dev->sensor_hflip = ctrl->val;
604 tpg_s_hflip(&dev->tpg, dev->sensor_hflip ^ dev->hflip);
605 break;
606 case VIVID_CID_VFLIP:
607 dev->sensor_vflip = ctrl->val;
608 tpg_s_vflip(&dev->tpg, dev->sensor_vflip ^ dev->vflip);
609 break;
610 case VIVID_CID_REDUCED_FPS:
611 dev->reduced_fps = ctrl->val;
612 vivid_update_format_cap(dev, true);
613 break;
614 case VIVID_CID_HAS_CROP_CAP:
615 dev->has_crop_cap = ctrl->val;
616 vivid_update_format_cap(dev, true);
617 break;
618 case VIVID_CID_HAS_COMPOSE_CAP:
619 dev->has_compose_cap = ctrl->val;
620 vivid_update_format_cap(dev, true);
621 break;
622 case VIVID_CID_HAS_SCALER_CAP:
623 dev->has_scaler_cap = ctrl->val;
624 vivid_update_format_cap(dev, true);
625 break;
626 case VIVID_CID_SHOW_BORDER:
627 tpg_s_show_border(&dev->tpg, ctrl->val);
628 break;
629 case VIVID_CID_SHOW_SQUARE:
630 tpg_s_show_square(&dev->tpg, ctrl->val);
631 break;
632 case VIVID_CID_STD_ASPECT_RATIO:
633 dev->std_aspect_ratio[dev->input] = ctrl->val;
634 tpg_s_video_aspect(&dev->tpg, vivid_get_video_aspect(dev));
635 break;
636 case VIVID_CID_DV_TIMINGS_SIGNAL_MODE:
637 dev->dv_timings_signal_mode[dev->input] =
638 dev->ctrl_dv_timings_signal_mode->val;
639 dev->query_dv_timings[dev->input] = dev->ctrl_dv_timings->val;
640 vivid_update_power_present(dev);
641 vivid_update_quality(dev);
642 vivid_send_input_source_change(dev, dev->input);
643 break;
644 case VIVID_CID_DV_TIMINGS_ASPECT_RATIO:
645 dev->dv_timings_aspect_ratio[dev->input] = ctrl->val;
646 tpg_s_video_aspect(&dev->tpg, vivid_get_video_aspect(dev));
647 break;
648 case VIVID_CID_TSTAMP_SRC:
649 dev->tstamp_src_is_soe = ctrl->val;
650 dev->vb_vid_cap_q.timestamp_flags &= ~V4L2_BUF_FLAG_TSTAMP_SRC_MASK;
651 if (dev->tstamp_src_is_soe)
652 dev->vb_vid_cap_q.timestamp_flags |= V4L2_BUF_FLAG_TSTAMP_SRC_SOE;
653 break;
654 case VIVID_CID_MAX_EDID_BLOCKS:
655 dev->edid_max_blocks = ctrl->val;
656 if (dev->edid_blocks > dev->edid_max_blocks)
657 dev->edid_blocks = dev->edid_max_blocks;
658 break;
659 case VIVID_CID_HDMI_IS_CONNECTED_TO_OUTPUT(0) ... VIVID_CID_HDMI_IS_CONNECTED_TO_OUTPUT(14):
660 hdmi_index = ctrl->id - VIVID_CID_HDMI_IS_CONNECTED_TO_OUTPUT(0);
661 output_inst = vivid_ctrl_hdmi_to_output_instance[ctrl->cur.val];
662 index = vivid_ctrl_hdmi_to_output_index[ctrl->cur.val];
663 input_index = dev->hdmi_index_to_input_index[hdmi_index];
664 dev->input_is_connected_to_output[input_index] = ctrl->val;
665
666 if (output_inst) {
667 output_inst->output_to_input_instance[index] = NULL;
668 vivid_update_outputs(output_inst);
669 cec_phys_addr_invalidate(output_inst->cec_tx_adap[index]);
670 }
671 if (ctrl->val >= FIXED_MENU_ITEMS) {
672 output_inst = vivid_ctrl_hdmi_to_output_instance[ctrl->val];
673 index = vivid_ctrl_hdmi_to_output_index[ctrl->val];
674 output_inst->output_to_input_instance[index] = dev;
675 output_inst->output_to_input_index[index] =
676 dev->hdmi_index_to_input_index[hdmi_index];
677 }
678 spin_lock(&hdmi_output_skip_mask_lock);
679 hdmi_to_output_menu_skip_mask &= ~(1ULL << ctrl->cur.val);
680 if (ctrl->val >= FIXED_MENU_ITEMS)
681 hdmi_to_output_menu_skip_mask |= 1ULL << ctrl->val;
682 spin_unlock(&hdmi_output_skip_mask_lock);
683 vivid_update_power_present(dev);
684 vivid_update_quality(dev);
685 vivid_send_input_source_change(dev, dev->hdmi_index_to_input_index[hdmi_index]);
686 if (ctrl->val < FIXED_MENU_ITEMS && ctrl->cur.val < FIXED_MENU_ITEMS)
687 break;
688 spin_lock(&hdmi_output_skip_mask_lock);
689 hdmi_input_update_outputs_mask |= 1 << dev->inst;
690 spin_unlock(&hdmi_output_skip_mask_lock);
691 queue_work(update_hdmi_ctrls_workqueue, &dev->update_hdmi_ctrl_work);
692 break;
693 case VIVID_CID_SVID_IS_CONNECTED_TO_OUTPUT(0) ... VIVID_CID_SVID_IS_CONNECTED_TO_OUTPUT(15):
694 svid_index = ctrl->id - VIVID_CID_SVID_IS_CONNECTED_TO_OUTPUT(0);
695 output_inst = vivid_ctrl_svid_to_output_instance[ctrl->cur.val];
696 index = vivid_ctrl_svid_to_output_index[ctrl->cur.val];
697 input_index = dev->svid_index_to_input_index[svid_index];
698 dev->input_is_connected_to_output[input_index] = ctrl->val;
699
700 if (output_inst)
701 output_inst->output_to_input_instance[index] = NULL;
702 if (ctrl->val >= FIXED_MENU_ITEMS) {
703 output_inst = vivid_ctrl_svid_to_output_instance[ctrl->val];
704 index = vivid_ctrl_svid_to_output_index[ctrl->val];
705 output_inst->output_to_input_instance[index] = dev;
706 output_inst->output_to_input_index[index] =
707 dev->svid_index_to_input_index[svid_index];
708 }
709 spin_lock(&svid_output_skip_mask_lock);
710 svid_to_output_menu_skip_mask &= ~(1ULL << ctrl->cur.val);
711 if (ctrl->val >= FIXED_MENU_ITEMS)
712 svid_to_output_menu_skip_mask |= 1ULL << ctrl->val;
713 spin_unlock(&svid_output_skip_mask_lock);
714 vivid_update_quality(dev);
715 vivid_send_input_source_change(dev, dev->svid_index_to_input_index[svid_index]);
716 if (ctrl->val < FIXED_MENU_ITEMS && ctrl->cur.val < FIXED_MENU_ITEMS)
717 break;
718 queue_work(update_svid_ctrls_workqueue, &dev->update_svid_ctrl_work);
719 break;
720 }
721 return 0;
722 }
723
724 static const struct v4l2_ctrl_ops vivid_vid_cap_ctrl_ops = {
725 .s_ctrl = vivid_vid_cap_s_ctrl,
726 };
727
728 static const char * const vivid_ctrl_hor_movement_strings[] = {
729 "Move Left Fast",
730 "Move Left",
731 "Move Left Slow",
732 "No Movement",
733 "Move Right Slow",
734 "Move Right",
735 "Move Right Fast",
736 NULL,
737 };
738
739 static const struct v4l2_ctrl_config vivid_ctrl_hor_movement = {
740 .ops = &vivid_vid_cap_ctrl_ops,
741 .id = VIVID_CID_HOR_MOVEMENT,
742 .name = "Horizontal Movement",
743 .type = V4L2_CTRL_TYPE_MENU,
744 .max = TPG_MOVE_POS_FAST,
745 .def = TPG_MOVE_NONE,
746 .qmenu = vivid_ctrl_hor_movement_strings,
747 };
748
749 static const char * const vivid_ctrl_vert_movement_strings[] = {
750 "Move Up Fast",
751 "Move Up",
752 "Move Up Slow",
753 "No Movement",
754 "Move Down Slow",
755 "Move Down",
756 "Move Down Fast",
757 NULL,
758 };
759
760 static const struct v4l2_ctrl_config vivid_ctrl_vert_movement = {
761 .ops = &vivid_vid_cap_ctrl_ops,
762 .id = VIVID_CID_VERT_MOVEMENT,
763 .name = "Vertical Movement",
764 .type = V4L2_CTRL_TYPE_MENU,
765 .max = TPG_MOVE_POS_FAST,
766 .def = TPG_MOVE_NONE,
767 .qmenu = vivid_ctrl_vert_movement_strings,
768 };
769
770 static const struct v4l2_ctrl_config vivid_ctrl_show_border = {
771 .ops = &vivid_vid_cap_ctrl_ops,
772 .id = VIVID_CID_SHOW_BORDER,
773 .name = "Show Border",
774 .type = V4L2_CTRL_TYPE_BOOLEAN,
775 .max = 1,
776 .step = 1,
777 };
778
779 static const struct v4l2_ctrl_config vivid_ctrl_show_square = {
780 .ops = &vivid_vid_cap_ctrl_ops,
781 .id = VIVID_CID_SHOW_SQUARE,
782 .name = "Show Square",
783 .type = V4L2_CTRL_TYPE_BOOLEAN,
784 .max = 1,
785 .step = 1,
786 };
787
788 static const char * const vivid_ctrl_osd_mode_strings[] = {
789 "All",
790 "Counters Only",
791 "None",
792 NULL,
793 };
794
795 static const struct v4l2_ctrl_config vivid_ctrl_osd_mode = {
796 .ops = &vivid_vid_cap_ctrl_ops,
797 .id = VIVID_CID_OSD_TEXT_MODE,
798 .name = "OSD Text Mode",
799 .type = V4L2_CTRL_TYPE_MENU,
800 .max = ARRAY_SIZE(vivid_ctrl_osd_mode_strings) - 2,
801 .qmenu = vivid_ctrl_osd_mode_strings,
802 };
803
804 static const struct v4l2_ctrl_config vivid_ctrl_perc_fill = {
805 .ops = &vivid_vid_cap_ctrl_ops,
806 .id = VIVID_CID_PERCENTAGE_FILL,
807 .name = "Fill Percentage of Frame",
808 .type = V4L2_CTRL_TYPE_INTEGER,
809 .min = 0,
810 .max = 100,
811 .def = 100,
812 .step = 1,
813 };
814
815 static const struct v4l2_ctrl_config vivid_ctrl_insert_sav = {
816 .ops = &vivid_vid_cap_ctrl_ops,
817 .id = VIVID_CID_INSERT_SAV,
818 .name = "Insert SAV Code in Image",
819 .type = V4L2_CTRL_TYPE_BOOLEAN,
820 .max = 1,
821 .step = 1,
822 };
823
824 static const struct v4l2_ctrl_config vivid_ctrl_insert_eav = {
825 .ops = &vivid_vid_cap_ctrl_ops,
826 .id = VIVID_CID_INSERT_EAV,
827 .name = "Insert EAV Code in Image",
828 .type = V4L2_CTRL_TYPE_BOOLEAN,
829 .max = 1,
830 .step = 1,
831 };
832
833 static const struct v4l2_ctrl_config vivid_ctrl_insert_hdmi_video_guard_band = {
834 .ops = &vivid_vid_cap_ctrl_ops,
835 .id = VIVID_CID_INSERT_HDMI_VIDEO_GUARD_BAND,
836 .name = "Insert Video Guard Band",
837 .type = V4L2_CTRL_TYPE_BOOLEAN,
838 .max = 1,
839 .step = 1,
840 };
841
842 static const struct v4l2_ctrl_config vivid_ctrl_hflip = {
843 .ops = &vivid_vid_cap_ctrl_ops,
844 .id = VIVID_CID_HFLIP,
845 .name = "Sensor Flipped Horizontally",
846 .type = V4L2_CTRL_TYPE_BOOLEAN,
847 .max = 1,
848 .step = 1,
849 };
850
851 static const struct v4l2_ctrl_config vivid_ctrl_vflip = {
852 .ops = &vivid_vid_cap_ctrl_ops,
853 .id = VIVID_CID_VFLIP,
854 .name = "Sensor Flipped Vertically",
855 .type = V4L2_CTRL_TYPE_BOOLEAN,
856 .max = 1,
857 .step = 1,
858 };
859
860 static const struct v4l2_ctrl_config vivid_ctrl_reduced_fps = {
861 .ops = &vivid_vid_cap_ctrl_ops,
862 .id = VIVID_CID_REDUCED_FPS,
863 .name = "Reduced Framerate",
864 .type = V4L2_CTRL_TYPE_BOOLEAN,
865 .max = 1,
866 .step = 1,
867 };
868
869 static const struct v4l2_ctrl_config vivid_ctrl_has_crop_cap = {
870 .ops = &vivid_vid_cap_ctrl_ops,
871 .id = VIVID_CID_HAS_CROP_CAP,
872 .name = "Enable Capture Cropping",
873 .type = V4L2_CTRL_TYPE_BOOLEAN,
874 .max = 1,
875 .def = 1,
876 .step = 1,
877 };
878
879 static const struct v4l2_ctrl_config vivid_ctrl_has_compose_cap = {
880 .ops = &vivid_vid_cap_ctrl_ops,
881 .id = VIVID_CID_HAS_COMPOSE_CAP,
882 .name = "Enable Capture Composing",
883 .type = V4L2_CTRL_TYPE_BOOLEAN,
884 .max = 1,
885 .def = 1,
886 .step = 1,
887 };
888
889 static const struct v4l2_ctrl_config vivid_ctrl_has_scaler_cap = {
890 .ops = &vivid_vid_cap_ctrl_ops,
891 .id = VIVID_CID_HAS_SCALER_CAP,
892 .name = "Enable Capture Scaler",
893 .type = V4L2_CTRL_TYPE_BOOLEAN,
894 .max = 1,
895 .def = 1,
896 .step = 1,
897 };
898
899 static const char * const vivid_ctrl_tstamp_src_strings[] = {
900 "End of Frame",
901 "Start of Exposure",
902 NULL,
903 };
904
905 static const struct v4l2_ctrl_config vivid_ctrl_tstamp_src = {
906 .ops = &vivid_vid_cap_ctrl_ops,
907 .id = VIVID_CID_TSTAMP_SRC,
908 .name = "Timestamp Source",
909 .type = V4L2_CTRL_TYPE_MENU,
910 .max = ARRAY_SIZE(vivid_ctrl_tstamp_src_strings) - 2,
911 .qmenu = vivid_ctrl_tstamp_src_strings,
912 };
913
914 static const struct v4l2_ctrl_config vivid_ctrl_std_aspect_ratio = {
915 .ops = &vivid_vid_cap_ctrl_ops,
916 .id = VIVID_CID_STD_ASPECT_RATIO,
917 .name = "Standard Aspect Ratio",
918 .type = V4L2_CTRL_TYPE_MENU,
919 .min = 1,
920 .max = 4,
921 .def = 1,
922 .qmenu = tpg_aspect_strings,
923 };
924
925 static const char * const vivid_ctrl_dv_timings_signal_mode_strings[] = {
926 "Current DV Timings",
927 "No Signal",
928 "No Lock",
929 "Out of Range",
930 "Selected DV Timings",
931 "Cycle Through All DV Timings",
932 "Custom DV Timings",
933 NULL,
934 };
935
936 static const struct v4l2_ctrl_config vivid_ctrl_dv_timings_signal_mode = {
937 .ops = &vivid_vid_cap_ctrl_ops,
938 .id = VIVID_CID_DV_TIMINGS_SIGNAL_MODE,
939 .name = "DV Timings Signal Mode",
940 .type = V4L2_CTRL_TYPE_MENU,
941 .max = 5,
942 .qmenu = vivid_ctrl_dv_timings_signal_mode_strings,
943 };
944
945 static const struct v4l2_ctrl_config vivid_ctrl_dv_timings_aspect_ratio = {
946 .ops = &vivid_vid_cap_ctrl_ops,
947 .id = VIVID_CID_DV_TIMINGS_ASPECT_RATIO,
948 .name = "DV Timings Aspect Ratio",
949 .type = V4L2_CTRL_TYPE_MENU,
950 .max = 3,
951 .qmenu = tpg_aspect_strings,
952 };
953
954 static const struct v4l2_ctrl_config vivid_ctrl_max_edid_blocks = {
955 .ops = &vivid_vid_cap_ctrl_ops,
956 .id = VIVID_CID_MAX_EDID_BLOCKS,
957 .name = "Maximum EDID Blocks",
958 .type = V4L2_CTRL_TYPE_INTEGER,
959 .min = 1,
960 .max = 256,
961 .def = 2,
962 .step = 1,
963 };
964
965 static const char * const vivid_ctrl_colorspace_strings[] = {
966 "SMPTE 170M",
967 "Rec. 709",
968 "sRGB",
969 "opRGB",
970 "BT.2020",
971 "DCI-P3",
972 "SMPTE 240M",
973 "470 System M",
974 "470 System BG",
975 NULL,
976 };
977
978 static const struct v4l2_ctrl_config vivid_ctrl_colorspace = {
979 .ops = &vivid_vid_cap_ctrl_ops,
980 .id = VIVID_CID_COLORSPACE,
981 .name = "Colorspace",
982 .type = V4L2_CTRL_TYPE_MENU,
983 .max = ARRAY_SIZE(vivid_ctrl_colorspace_strings) - 2,
984 .def = 2,
985 .qmenu = vivid_ctrl_colorspace_strings,
986 };
987
988 static const char * const vivid_ctrl_xfer_func_strings[] = {
989 "Default",
990 "Rec. 709",
991 "sRGB",
992 "opRGB",
993 "SMPTE 240M",
994 "None",
995 "DCI-P3",
996 "SMPTE 2084",
997 NULL,
998 };
999
1000 static const struct v4l2_ctrl_config vivid_ctrl_xfer_func = {
1001 .ops = &vivid_vid_cap_ctrl_ops,
1002 .id = VIVID_CID_XFER_FUNC,
1003 .name = "Transfer Function",
1004 .type = V4L2_CTRL_TYPE_MENU,
1005 .max = ARRAY_SIZE(vivid_ctrl_xfer_func_strings) - 2,
1006 .qmenu = vivid_ctrl_xfer_func_strings,
1007 };
1008
1009 static const char * const vivid_ctrl_ycbcr_enc_strings[] = {
1010 "Default",
1011 "ITU-R 601",
1012 "Rec. 709",
1013 "xvYCC 601",
1014 "xvYCC 709",
1015 "",
1016 "BT.2020",
1017 "BT.2020 Constant Luminance",
1018 "SMPTE 240M",
1019 NULL,
1020 };
1021
1022 static const struct v4l2_ctrl_config vivid_ctrl_ycbcr_enc = {
1023 .ops = &vivid_vid_cap_ctrl_ops,
1024 .id = VIVID_CID_YCBCR_ENC,
1025 .name = "Y'CbCr Encoding",
1026 .type = V4L2_CTRL_TYPE_MENU,
1027 .menu_skip_mask = 1 << 5,
1028 .max = ARRAY_SIZE(vivid_ctrl_ycbcr_enc_strings) - 2,
1029 .qmenu = vivid_ctrl_ycbcr_enc_strings,
1030 };
1031
1032 static const char * const vivid_ctrl_hsv_enc_strings[] = {
1033 "Hue 0-179",
1034 "Hue 0-256",
1035 NULL,
1036 };
1037
1038 static const struct v4l2_ctrl_config vivid_ctrl_hsv_enc = {
1039 .ops = &vivid_vid_cap_ctrl_ops,
1040 .id = VIVID_CID_HSV_ENC,
1041 .name = "HSV Encoding",
1042 .type = V4L2_CTRL_TYPE_MENU,
1043 .max = ARRAY_SIZE(vivid_ctrl_hsv_enc_strings) - 2,
1044 .qmenu = vivid_ctrl_hsv_enc_strings,
1045 };
1046
1047 static const char * const vivid_ctrl_quantization_strings[] = {
1048 "Default",
1049 "Full Range",
1050 "Limited Range",
1051 NULL,
1052 };
1053
1054 static const struct v4l2_ctrl_config vivid_ctrl_quantization = {
1055 .ops = &vivid_vid_cap_ctrl_ops,
1056 .id = VIVID_CID_QUANTIZATION,
1057 .name = "Quantization",
1058 .type = V4L2_CTRL_TYPE_MENU,
1059 .max = ARRAY_SIZE(vivid_ctrl_quantization_strings) - 2,
1060 .qmenu = vivid_ctrl_quantization_strings,
1061 };
1062
1063 static const struct v4l2_ctrl_config vivid_ctrl_alpha_mode = {
1064 .ops = &vivid_vid_cap_ctrl_ops,
1065 .id = VIVID_CID_ALPHA_MODE,
1066 .name = "Apply Alpha To Red Only",
1067 .type = V4L2_CTRL_TYPE_BOOLEAN,
1068 .max = 1,
1069 .step = 1,
1070 };
1071
1072 static const struct v4l2_ctrl_config vivid_ctrl_limited_rgb_range = {
1073 .ops = &vivid_vid_cap_ctrl_ops,
1074 .id = VIVID_CID_LIMITED_RGB_RANGE,
1075 .name = "Limited RGB Range (16-235)",
1076 .type = V4L2_CTRL_TYPE_BOOLEAN,
1077 .max = 1,
1078 .step = 1,
1079 };
1080
1081
1082 /* VBI Capture Control */
1083
vivid_vbi_cap_s_ctrl(struct v4l2_ctrl * ctrl)1084 static int vivid_vbi_cap_s_ctrl(struct v4l2_ctrl *ctrl)
1085 {
1086 struct vivid_dev *dev = container_of(ctrl->handler, struct vivid_dev, ctrl_hdl_vbi_cap);
1087
1088 switch (ctrl->id) {
1089 case VIVID_CID_VBI_CAP_INTERLACED:
1090 dev->vbi_cap_interlaced = ctrl->val;
1091 break;
1092 }
1093 return 0;
1094 }
1095
1096 static const struct v4l2_ctrl_ops vivid_vbi_cap_ctrl_ops = {
1097 .s_ctrl = vivid_vbi_cap_s_ctrl,
1098 };
1099
1100 static const struct v4l2_ctrl_config vivid_ctrl_vbi_cap_interlaced = {
1101 .ops = &vivid_vbi_cap_ctrl_ops,
1102 .id = VIVID_CID_VBI_CAP_INTERLACED,
1103 .name = "Interlaced VBI Format",
1104 .type = V4L2_CTRL_TYPE_BOOLEAN,
1105 .max = 1,
1106 .step = 1,
1107 };
1108
1109
1110 /* Video Output Controls */
1111
vivid_vid_out_s_ctrl(struct v4l2_ctrl * ctrl)1112 static int vivid_vid_out_s_ctrl(struct v4l2_ctrl *ctrl)
1113 {
1114 struct vivid_dev *dev = container_of(ctrl->handler, struct vivid_dev, ctrl_hdl_vid_out);
1115 struct v4l2_bt_timings *bt = &dev->dv_timings_out.bt;
1116
1117 switch (ctrl->id) {
1118 case VIVID_CID_HAS_CROP_OUT:
1119 dev->has_crop_out = ctrl->val;
1120 vivid_update_format_out(dev);
1121 break;
1122 case VIVID_CID_HAS_COMPOSE_OUT:
1123 dev->has_compose_out = ctrl->val;
1124 vivid_update_format_out(dev);
1125 break;
1126 case VIVID_CID_HAS_SCALER_OUT:
1127 dev->has_scaler_out = ctrl->val;
1128 vivid_update_format_out(dev);
1129 break;
1130 case V4L2_CID_DV_TX_MODE:
1131 dev->dvi_d_out = ctrl->val == V4L2_DV_TX_MODE_DVI_D;
1132 if (!vivid_is_hdmi_out(dev))
1133 break;
1134 if (!dev->dvi_d_out && (bt->flags & V4L2_DV_FL_IS_CE_VIDEO)) {
1135 if (bt->width == 720 && bt->height <= 576)
1136 dev->colorspace_out = V4L2_COLORSPACE_SMPTE170M;
1137 else
1138 dev->colorspace_out = V4L2_COLORSPACE_REC709;
1139 dev->quantization_out = V4L2_QUANTIZATION_DEFAULT;
1140 } else {
1141 dev->colorspace_out = V4L2_COLORSPACE_SRGB;
1142 dev->quantization_out = dev->dvi_d_out ?
1143 V4L2_QUANTIZATION_LIM_RANGE :
1144 V4L2_QUANTIZATION_DEFAULT;
1145 }
1146 if (vivid_output_is_connected_to(dev)) {
1147 struct vivid_dev *dev_rx = vivid_output_is_connected_to(dev);
1148
1149 vivid_send_source_change(dev_rx, HDMI);
1150 }
1151 break;
1152 }
1153 return 0;
1154 }
1155
1156 static const struct v4l2_ctrl_ops vivid_vid_out_ctrl_ops = {
1157 .s_ctrl = vivid_vid_out_s_ctrl,
1158 };
1159
1160 static const struct v4l2_ctrl_config vivid_ctrl_has_crop_out = {
1161 .ops = &vivid_vid_out_ctrl_ops,
1162 .id = VIVID_CID_HAS_CROP_OUT,
1163 .name = "Enable Output Cropping",
1164 .type = V4L2_CTRL_TYPE_BOOLEAN,
1165 .max = 1,
1166 .def = 1,
1167 .step = 1,
1168 };
1169
1170 static const struct v4l2_ctrl_config vivid_ctrl_has_compose_out = {
1171 .ops = &vivid_vid_out_ctrl_ops,
1172 .id = VIVID_CID_HAS_COMPOSE_OUT,
1173 .name = "Enable Output Composing",
1174 .type = V4L2_CTRL_TYPE_BOOLEAN,
1175 .max = 1,
1176 .def = 1,
1177 .step = 1,
1178 };
1179
1180 static const struct v4l2_ctrl_config vivid_ctrl_has_scaler_out = {
1181 .ops = &vivid_vid_out_ctrl_ops,
1182 .id = VIVID_CID_HAS_SCALER_OUT,
1183 .name = "Enable Output Scaler",
1184 .type = V4L2_CTRL_TYPE_BOOLEAN,
1185 .max = 1,
1186 .def = 1,
1187 .step = 1,
1188 };
1189
1190 /* Streaming Controls */
1191
vivid_streaming_s_ctrl(struct v4l2_ctrl * ctrl)1192 static int vivid_streaming_s_ctrl(struct v4l2_ctrl *ctrl)
1193 {
1194 struct vivid_dev *dev = container_of(ctrl->handler, struct vivid_dev, ctrl_hdl_streaming);
1195
1196 switch (ctrl->id) {
1197 case VIVID_CID_DQBUF_ERROR:
1198 dev->dqbuf_error = true;
1199 break;
1200 case VIVID_CID_PERC_DROPPED:
1201 dev->perc_dropped_buffers = ctrl->val;
1202 break;
1203 case VIVID_CID_QUEUE_SETUP_ERROR:
1204 dev->queue_setup_error = true;
1205 break;
1206 case VIVID_CID_BUF_PREPARE_ERROR:
1207 dev->buf_prepare_error = true;
1208 break;
1209 case VIVID_CID_START_STR_ERROR:
1210 dev->start_streaming_error = true;
1211 break;
1212 case VIVID_CID_REQ_VALIDATE_ERROR:
1213 dev->req_validate_error = true;
1214 break;
1215 case VIVID_CID_QUEUE_ERROR:
1216 if (vb2_start_streaming_called(&dev->vb_vid_cap_q))
1217 vb2_queue_error(&dev->vb_vid_cap_q);
1218 if (vb2_start_streaming_called(&dev->vb_vbi_cap_q))
1219 vb2_queue_error(&dev->vb_vbi_cap_q);
1220 if (vb2_start_streaming_called(&dev->vb_vid_out_q))
1221 vb2_queue_error(&dev->vb_vid_out_q);
1222 if (vb2_start_streaming_called(&dev->vb_vbi_out_q))
1223 vb2_queue_error(&dev->vb_vbi_out_q);
1224 if (vb2_start_streaming_called(&dev->vb_sdr_cap_q))
1225 vb2_queue_error(&dev->vb_sdr_cap_q);
1226 break;
1227 case VIVID_CID_SEQ_WRAP:
1228 dev->seq_wrap = ctrl->val;
1229 break;
1230 case VIVID_CID_TIME_WRAP:
1231 dev->time_wrap = ctrl->val;
1232 if (dev->time_wrap == 1)
1233 dev->time_wrap = (1ULL << 63) - NSEC_PER_SEC * 16ULL;
1234 else if (dev->time_wrap == 2)
1235 dev->time_wrap = ((1ULL << 31) - 16) * NSEC_PER_SEC;
1236 break;
1237 }
1238 return 0;
1239 }
1240
1241 static const struct v4l2_ctrl_ops vivid_streaming_ctrl_ops = {
1242 .s_ctrl = vivid_streaming_s_ctrl,
1243 };
1244
1245 static const struct v4l2_ctrl_config vivid_ctrl_dqbuf_error = {
1246 .ops = &vivid_streaming_ctrl_ops,
1247 .id = VIVID_CID_DQBUF_ERROR,
1248 .name = "Inject V4L2_BUF_FLAG_ERROR",
1249 .type = V4L2_CTRL_TYPE_BUTTON,
1250 };
1251
1252 static const struct v4l2_ctrl_config vivid_ctrl_perc_dropped = {
1253 .ops = &vivid_streaming_ctrl_ops,
1254 .id = VIVID_CID_PERC_DROPPED,
1255 .name = "Percentage of Dropped Buffers",
1256 .type = V4L2_CTRL_TYPE_INTEGER,
1257 .min = 0,
1258 .max = 100,
1259 .step = 1,
1260 };
1261
1262 static const struct v4l2_ctrl_config vivid_ctrl_queue_setup_error = {
1263 .ops = &vivid_streaming_ctrl_ops,
1264 .id = VIVID_CID_QUEUE_SETUP_ERROR,
1265 .name = "Inject VIDIOC_REQBUFS Error",
1266 .type = V4L2_CTRL_TYPE_BUTTON,
1267 };
1268
1269 static const struct v4l2_ctrl_config vivid_ctrl_buf_prepare_error = {
1270 .ops = &vivid_streaming_ctrl_ops,
1271 .id = VIVID_CID_BUF_PREPARE_ERROR,
1272 .name = "Inject VIDIOC_QBUF Error",
1273 .type = V4L2_CTRL_TYPE_BUTTON,
1274 };
1275
1276 static const struct v4l2_ctrl_config vivid_ctrl_start_streaming_error = {
1277 .ops = &vivid_streaming_ctrl_ops,
1278 .id = VIVID_CID_START_STR_ERROR,
1279 .name = "Inject VIDIOC_STREAMON Error",
1280 .type = V4L2_CTRL_TYPE_BUTTON,
1281 };
1282
1283 static const struct v4l2_ctrl_config vivid_ctrl_queue_error = {
1284 .ops = &vivid_streaming_ctrl_ops,
1285 .id = VIVID_CID_QUEUE_ERROR,
1286 .name = "Inject Fatal Streaming Error",
1287 .type = V4L2_CTRL_TYPE_BUTTON,
1288 };
1289
1290 #ifdef CONFIG_MEDIA_CONTROLLER
1291 static const struct v4l2_ctrl_config vivid_ctrl_req_validate_error = {
1292 .ops = &vivid_streaming_ctrl_ops,
1293 .id = VIVID_CID_REQ_VALIDATE_ERROR,
1294 .name = "Inject req_validate() Error",
1295 .type = V4L2_CTRL_TYPE_BUTTON,
1296 };
1297 #endif
1298
1299 static const struct v4l2_ctrl_config vivid_ctrl_seq_wrap = {
1300 .ops = &vivid_streaming_ctrl_ops,
1301 .id = VIVID_CID_SEQ_WRAP,
1302 .name = "Wrap Sequence Number",
1303 .type = V4L2_CTRL_TYPE_BOOLEAN,
1304 .max = 1,
1305 .step = 1,
1306 };
1307
1308 static const char * const vivid_ctrl_time_wrap_strings[] = {
1309 "None",
1310 "64 Bit",
1311 "32 Bit",
1312 NULL,
1313 };
1314
1315 static const struct v4l2_ctrl_config vivid_ctrl_time_wrap = {
1316 .ops = &vivid_streaming_ctrl_ops,
1317 .id = VIVID_CID_TIME_WRAP,
1318 .name = "Wrap Timestamp",
1319 .type = V4L2_CTRL_TYPE_MENU,
1320 .max = ARRAY_SIZE(vivid_ctrl_time_wrap_strings) - 2,
1321 .qmenu = vivid_ctrl_time_wrap_strings,
1322 };
1323
1324
1325 /* SDTV Capture Controls */
1326
vivid_sdtv_cap_s_ctrl(struct v4l2_ctrl * ctrl)1327 static int vivid_sdtv_cap_s_ctrl(struct v4l2_ctrl *ctrl)
1328 {
1329 struct vivid_dev *dev = container_of(ctrl->handler, struct vivid_dev, ctrl_hdl_sdtv_cap);
1330
1331 switch (ctrl->id) {
1332 case VIVID_CID_STD_SIGNAL_MODE:
1333 dev->std_signal_mode[dev->input] =
1334 dev->ctrl_std_signal_mode->val;
1335 if (dev->std_signal_mode[dev->input] == SELECTED_STD)
1336 dev->query_std[dev->input] =
1337 vivid_standard[dev->ctrl_standard->val];
1338 v4l2_ctrl_activate(dev->ctrl_standard,
1339 dev->std_signal_mode[dev->input] ==
1340 SELECTED_STD);
1341 vivid_update_quality(dev);
1342 vivid_send_source_change(dev, TV);
1343 vivid_send_source_change(dev, SVID);
1344 break;
1345 }
1346 return 0;
1347 }
1348
1349 static const struct v4l2_ctrl_ops vivid_sdtv_cap_ctrl_ops = {
1350 .s_ctrl = vivid_sdtv_cap_s_ctrl,
1351 };
1352
1353 static const char * const vivid_ctrl_std_signal_mode_strings[] = {
1354 "Current Standard",
1355 "No Signal",
1356 "No Lock",
1357 "",
1358 "Selected Standard",
1359 "Cycle Through All Standards",
1360 NULL,
1361 };
1362
1363 static const struct v4l2_ctrl_config vivid_ctrl_std_signal_mode = {
1364 .ops = &vivid_sdtv_cap_ctrl_ops,
1365 .id = VIVID_CID_STD_SIGNAL_MODE,
1366 .name = "Standard Signal Mode",
1367 .type = V4L2_CTRL_TYPE_MENU,
1368 .max = ARRAY_SIZE(vivid_ctrl_std_signal_mode_strings) - 2,
1369 .menu_skip_mask = 1 << 3,
1370 .qmenu = vivid_ctrl_std_signal_mode_strings,
1371 };
1372
1373 static const struct v4l2_ctrl_config vivid_ctrl_standard = {
1374 .ops = &vivid_sdtv_cap_ctrl_ops,
1375 .id = VIVID_CID_STANDARD,
1376 .name = "Standard",
1377 .type = V4L2_CTRL_TYPE_MENU,
1378 .max = 14,
1379 .qmenu = vivid_ctrl_standard_strings,
1380 };
1381
1382
1383
1384 /* Radio Receiver Controls */
1385
vivid_radio_rx_s_ctrl(struct v4l2_ctrl * ctrl)1386 static int vivid_radio_rx_s_ctrl(struct v4l2_ctrl *ctrl)
1387 {
1388 struct vivid_dev *dev = container_of(ctrl->handler, struct vivid_dev, ctrl_hdl_radio_rx);
1389
1390 switch (ctrl->id) {
1391 case VIVID_CID_RADIO_SEEK_MODE:
1392 dev->radio_rx_hw_seek_mode = ctrl->val;
1393 break;
1394 case VIVID_CID_RADIO_SEEK_PROG_LIM:
1395 dev->radio_rx_hw_seek_prog_lim = ctrl->val;
1396 break;
1397 case VIVID_CID_RADIO_RX_RDS_RBDS:
1398 dev->rds_gen.use_rbds = ctrl->val;
1399 break;
1400 case VIVID_CID_RADIO_RX_RDS_BLOCKIO:
1401 dev->radio_rx_rds_controls = ctrl->val;
1402 dev->radio_rx_caps &= ~V4L2_CAP_READWRITE;
1403 dev->radio_rx_rds_use_alternates = false;
1404 if (!dev->radio_rx_rds_controls) {
1405 dev->radio_rx_caps |= V4L2_CAP_READWRITE;
1406 __v4l2_ctrl_s_ctrl(dev->radio_rx_rds_pty, 0);
1407 __v4l2_ctrl_s_ctrl(dev->radio_rx_rds_ta, 0);
1408 __v4l2_ctrl_s_ctrl(dev->radio_rx_rds_tp, 0);
1409 __v4l2_ctrl_s_ctrl(dev->radio_rx_rds_ms, 0);
1410 __v4l2_ctrl_s_ctrl_string(dev->radio_rx_rds_psname, "");
1411 __v4l2_ctrl_s_ctrl_string(dev->radio_rx_rds_radiotext, "");
1412 }
1413 v4l2_ctrl_activate(dev->radio_rx_rds_pty, dev->radio_rx_rds_controls);
1414 v4l2_ctrl_activate(dev->radio_rx_rds_psname, dev->radio_rx_rds_controls);
1415 v4l2_ctrl_activate(dev->radio_rx_rds_radiotext, dev->radio_rx_rds_controls);
1416 v4l2_ctrl_activate(dev->radio_rx_rds_ta, dev->radio_rx_rds_controls);
1417 v4l2_ctrl_activate(dev->radio_rx_rds_tp, dev->radio_rx_rds_controls);
1418 v4l2_ctrl_activate(dev->radio_rx_rds_ms, dev->radio_rx_rds_controls);
1419 dev->radio_rx_dev.device_caps = dev->radio_rx_caps;
1420 break;
1421 case V4L2_CID_RDS_RECEPTION:
1422 dev->radio_rx_rds_enabled = ctrl->val;
1423 break;
1424 }
1425 return 0;
1426 }
1427
1428 static const struct v4l2_ctrl_ops vivid_radio_rx_ctrl_ops = {
1429 .s_ctrl = vivid_radio_rx_s_ctrl,
1430 };
1431
1432 static const char * const vivid_ctrl_radio_rds_mode_strings[] = {
1433 "Block I/O",
1434 "Controls",
1435 NULL,
1436 };
1437
1438 static const struct v4l2_ctrl_config vivid_ctrl_radio_rx_rds_blockio = {
1439 .ops = &vivid_radio_rx_ctrl_ops,
1440 .id = VIVID_CID_RADIO_RX_RDS_BLOCKIO,
1441 .name = "RDS Rx I/O Mode",
1442 .type = V4L2_CTRL_TYPE_MENU,
1443 .qmenu = vivid_ctrl_radio_rds_mode_strings,
1444 .max = 1,
1445 };
1446
1447 static const struct v4l2_ctrl_config vivid_ctrl_radio_rx_rds_rbds = {
1448 .ops = &vivid_radio_rx_ctrl_ops,
1449 .id = VIVID_CID_RADIO_RX_RDS_RBDS,
1450 .name = "Generate RBDS Instead of RDS",
1451 .type = V4L2_CTRL_TYPE_BOOLEAN,
1452 .max = 1,
1453 .step = 1,
1454 };
1455
1456 static const char * const vivid_ctrl_radio_hw_seek_mode_strings[] = {
1457 "Bounded",
1458 "Wrap Around",
1459 "Both",
1460 NULL,
1461 };
1462
1463 static const struct v4l2_ctrl_config vivid_ctrl_radio_hw_seek_mode = {
1464 .ops = &vivid_radio_rx_ctrl_ops,
1465 .id = VIVID_CID_RADIO_SEEK_MODE,
1466 .name = "Radio HW Seek Mode",
1467 .type = V4L2_CTRL_TYPE_MENU,
1468 .max = 2,
1469 .qmenu = vivid_ctrl_radio_hw_seek_mode_strings,
1470 };
1471
1472 static const struct v4l2_ctrl_config vivid_ctrl_radio_hw_seek_prog_lim = {
1473 .ops = &vivid_radio_rx_ctrl_ops,
1474 .id = VIVID_CID_RADIO_SEEK_PROG_LIM,
1475 .name = "Radio Programmable HW Seek",
1476 .type = V4L2_CTRL_TYPE_BOOLEAN,
1477 .max = 1,
1478 .step = 1,
1479 };
1480
1481
1482 /* Radio Transmitter Controls */
1483
vivid_radio_tx_s_ctrl(struct v4l2_ctrl * ctrl)1484 static int vivid_radio_tx_s_ctrl(struct v4l2_ctrl *ctrl)
1485 {
1486 struct vivid_dev *dev = container_of(ctrl->handler, struct vivid_dev, ctrl_hdl_radio_tx);
1487
1488 switch (ctrl->id) {
1489 case VIVID_CID_RADIO_TX_RDS_BLOCKIO:
1490 dev->radio_tx_rds_controls = ctrl->val;
1491 dev->radio_tx_caps &= ~V4L2_CAP_READWRITE;
1492 if (!dev->radio_tx_rds_controls)
1493 dev->radio_tx_caps |= V4L2_CAP_READWRITE;
1494 dev->radio_tx_dev.device_caps = dev->radio_tx_caps;
1495 break;
1496 case V4L2_CID_RDS_TX_PTY:
1497 if (dev->radio_rx_rds_controls)
1498 v4l2_ctrl_s_ctrl(dev->radio_rx_rds_pty, ctrl->val);
1499 break;
1500 case V4L2_CID_RDS_TX_PS_NAME:
1501 if (dev->radio_rx_rds_controls)
1502 v4l2_ctrl_s_ctrl_string(dev->radio_rx_rds_psname, ctrl->p_new.p_char);
1503 break;
1504 case V4L2_CID_RDS_TX_RADIO_TEXT:
1505 if (dev->radio_rx_rds_controls)
1506 v4l2_ctrl_s_ctrl_string(dev->radio_rx_rds_radiotext, ctrl->p_new.p_char);
1507 break;
1508 case V4L2_CID_RDS_TX_TRAFFIC_ANNOUNCEMENT:
1509 if (dev->radio_rx_rds_controls)
1510 v4l2_ctrl_s_ctrl(dev->radio_rx_rds_ta, ctrl->val);
1511 break;
1512 case V4L2_CID_RDS_TX_TRAFFIC_PROGRAM:
1513 if (dev->radio_rx_rds_controls)
1514 v4l2_ctrl_s_ctrl(dev->radio_rx_rds_tp, ctrl->val);
1515 break;
1516 case V4L2_CID_RDS_TX_MUSIC_SPEECH:
1517 if (dev->radio_rx_rds_controls)
1518 v4l2_ctrl_s_ctrl(dev->radio_rx_rds_ms, ctrl->val);
1519 break;
1520 }
1521 return 0;
1522 }
1523
1524 static const struct v4l2_ctrl_ops vivid_radio_tx_ctrl_ops = {
1525 .s_ctrl = vivid_radio_tx_s_ctrl,
1526 };
1527
1528 static const struct v4l2_ctrl_config vivid_ctrl_radio_tx_rds_blockio = {
1529 .ops = &vivid_radio_tx_ctrl_ops,
1530 .id = VIVID_CID_RADIO_TX_RDS_BLOCKIO,
1531 .name = "RDS Tx I/O Mode",
1532 .type = V4L2_CTRL_TYPE_MENU,
1533 .qmenu = vivid_ctrl_radio_rds_mode_strings,
1534 .max = 1,
1535 .def = 1,
1536 };
1537
1538
1539 /* SDR Capture Controls */
1540
vivid_sdr_cap_s_ctrl(struct v4l2_ctrl * ctrl)1541 static int vivid_sdr_cap_s_ctrl(struct v4l2_ctrl *ctrl)
1542 {
1543 struct vivid_dev *dev = container_of(ctrl->handler, struct vivid_dev, ctrl_hdl_sdr_cap);
1544
1545 switch (ctrl->id) {
1546 case VIVID_CID_SDR_CAP_FM_DEVIATION:
1547 dev->sdr_fm_deviation = ctrl->val;
1548 break;
1549 }
1550 return 0;
1551 }
1552
1553 static const struct v4l2_ctrl_ops vivid_sdr_cap_ctrl_ops = {
1554 .s_ctrl = vivid_sdr_cap_s_ctrl,
1555 };
1556
1557 static const struct v4l2_ctrl_config vivid_ctrl_sdr_cap_fm_deviation = {
1558 .ops = &vivid_sdr_cap_ctrl_ops,
1559 .id = VIVID_CID_SDR_CAP_FM_DEVIATION,
1560 .name = "FM Deviation",
1561 .type = V4L2_CTRL_TYPE_INTEGER,
1562 .min = 100,
1563 .max = 200000,
1564 .def = 75000,
1565 .step = 1,
1566 };
1567
1568 /* Metadata Capture Control */
1569
vivid_meta_cap_s_ctrl(struct v4l2_ctrl * ctrl)1570 static int vivid_meta_cap_s_ctrl(struct v4l2_ctrl *ctrl)
1571 {
1572 struct vivid_dev *dev = container_of(ctrl->handler, struct vivid_dev,
1573 ctrl_hdl_meta_cap);
1574
1575 switch (ctrl->id) {
1576 case VIVID_CID_META_CAP_GENERATE_PTS:
1577 dev->meta_pts = ctrl->val;
1578 break;
1579 case VIVID_CID_META_CAP_GENERATE_SCR:
1580 dev->meta_scr = ctrl->val;
1581 break;
1582 }
1583 return 0;
1584 }
1585
1586 static const struct v4l2_ctrl_ops vivid_meta_cap_ctrl_ops = {
1587 .s_ctrl = vivid_meta_cap_s_ctrl,
1588 };
1589
1590 static const struct v4l2_ctrl_config vivid_ctrl_meta_has_pts = {
1591 .ops = &vivid_meta_cap_ctrl_ops,
1592 .id = VIVID_CID_META_CAP_GENERATE_PTS,
1593 .name = "Generate PTS",
1594 .type = V4L2_CTRL_TYPE_BOOLEAN,
1595 .max = 1,
1596 .def = 1,
1597 .step = 1,
1598 };
1599
1600 static const struct v4l2_ctrl_config vivid_ctrl_meta_has_src_clk = {
1601 .ops = &vivid_meta_cap_ctrl_ops,
1602 .id = VIVID_CID_META_CAP_GENERATE_SCR,
1603 .name = "Generate SCR",
1604 .type = V4L2_CTRL_TYPE_BOOLEAN,
1605 .max = 1,
1606 .def = 1,
1607 .step = 1,
1608 };
1609
1610 static const struct v4l2_ctrl_config vivid_ctrl_class = {
1611 .ops = &vivid_user_gen_ctrl_ops,
1612 .flags = V4L2_CTRL_FLAG_READ_ONLY | V4L2_CTRL_FLAG_WRITE_ONLY,
1613 .id = VIVID_CID_VIVID_CLASS,
1614 .name = "Vivid Controls",
1615 .type = V4L2_CTRL_TYPE_CTRL_CLASS,
1616 };
1617
vivid_create_controls(struct vivid_dev * dev,bool show_ccs_cap,bool show_ccs_out,bool no_error_inj,bool has_sdtv,bool has_hdmi)1618 int vivid_create_controls(struct vivid_dev *dev, bool show_ccs_cap,
1619 bool show_ccs_out, bool no_error_inj,
1620 bool has_sdtv, bool has_hdmi)
1621 {
1622 struct v4l2_ctrl_handler *hdl_user_gen = &dev->ctrl_hdl_user_gen;
1623 struct v4l2_ctrl_handler *hdl_user_vid = &dev->ctrl_hdl_user_vid;
1624 struct v4l2_ctrl_handler *hdl_user_aud = &dev->ctrl_hdl_user_aud;
1625 struct v4l2_ctrl_handler *hdl_streaming = &dev->ctrl_hdl_streaming;
1626 struct v4l2_ctrl_handler *hdl_sdtv_cap = &dev->ctrl_hdl_sdtv_cap;
1627 struct v4l2_ctrl_handler *hdl_loop_cap = &dev->ctrl_hdl_loop_cap;
1628 struct v4l2_ctrl_handler *hdl_fb = &dev->ctrl_hdl_fb;
1629 struct v4l2_ctrl_handler *hdl_vid_cap = &dev->ctrl_hdl_vid_cap;
1630 struct v4l2_ctrl_handler *hdl_vid_out = &dev->ctrl_hdl_vid_out;
1631 struct v4l2_ctrl_handler *hdl_vbi_cap = &dev->ctrl_hdl_vbi_cap;
1632 struct v4l2_ctrl_handler *hdl_vbi_out = &dev->ctrl_hdl_vbi_out;
1633 struct v4l2_ctrl_handler *hdl_radio_rx = &dev->ctrl_hdl_radio_rx;
1634 struct v4l2_ctrl_handler *hdl_radio_tx = &dev->ctrl_hdl_radio_tx;
1635 struct v4l2_ctrl_handler *hdl_sdr_cap = &dev->ctrl_hdl_sdr_cap;
1636 struct v4l2_ctrl_handler *hdl_meta_cap = &dev->ctrl_hdl_meta_cap;
1637 struct v4l2_ctrl_handler *hdl_meta_out = &dev->ctrl_hdl_meta_out;
1638 struct v4l2_ctrl_handler *hdl_tch_cap = &dev->ctrl_hdl_touch_cap;
1639
1640 struct v4l2_ctrl_config vivid_ctrl_dv_timings = {
1641 .ops = &vivid_vid_cap_ctrl_ops,
1642 .id = VIVID_CID_DV_TIMINGS,
1643 .name = "DV Timings",
1644 .type = V4L2_CTRL_TYPE_MENU,
1645 };
1646 int i;
1647
1648 v4l2_ctrl_handler_init(hdl_user_gen, 10);
1649 v4l2_ctrl_new_custom(hdl_user_gen, &vivid_ctrl_class, NULL);
1650 v4l2_ctrl_handler_init(hdl_user_vid, 9);
1651 v4l2_ctrl_new_custom(hdl_user_vid, &vivid_ctrl_class, NULL);
1652 v4l2_ctrl_handler_init(hdl_user_aud, 2);
1653 v4l2_ctrl_new_custom(hdl_user_aud, &vivid_ctrl_class, NULL);
1654 v4l2_ctrl_handler_init(hdl_streaming, 8);
1655 v4l2_ctrl_new_custom(hdl_streaming, &vivid_ctrl_class, NULL);
1656 v4l2_ctrl_handler_init(hdl_sdtv_cap, 2);
1657 v4l2_ctrl_new_custom(hdl_sdtv_cap, &vivid_ctrl_class, NULL);
1658 v4l2_ctrl_handler_init(hdl_loop_cap, 1);
1659 v4l2_ctrl_new_custom(hdl_loop_cap, &vivid_ctrl_class, NULL);
1660 v4l2_ctrl_handler_init(hdl_fb, 1);
1661 v4l2_ctrl_new_custom(hdl_fb, &vivid_ctrl_class, NULL);
1662 v4l2_ctrl_handler_init(hdl_vid_cap, 55);
1663 v4l2_ctrl_new_custom(hdl_vid_cap, &vivid_ctrl_class, NULL);
1664 v4l2_ctrl_handler_init(hdl_vid_out, 26);
1665 if (!no_error_inj || dev->has_fb || dev->num_hdmi_outputs)
1666 v4l2_ctrl_new_custom(hdl_vid_out, &vivid_ctrl_class, NULL);
1667 v4l2_ctrl_handler_init(hdl_vbi_cap, 21);
1668 v4l2_ctrl_new_custom(hdl_vbi_cap, &vivid_ctrl_class, NULL);
1669 v4l2_ctrl_handler_init(hdl_vbi_out, 19);
1670 if (!no_error_inj)
1671 v4l2_ctrl_new_custom(hdl_vbi_out, &vivid_ctrl_class, NULL);
1672 v4l2_ctrl_handler_init(hdl_radio_rx, 17);
1673 v4l2_ctrl_new_custom(hdl_radio_rx, &vivid_ctrl_class, NULL);
1674 v4l2_ctrl_handler_init(hdl_radio_tx, 17);
1675 v4l2_ctrl_new_custom(hdl_radio_tx, &vivid_ctrl_class, NULL);
1676 v4l2_ctrl_handler_init(hdl_sdr_cap, 19);
1677 v4l2_ctrl_new_custom(hdl_sdr_cap, &vivid_ctrl_class, NULL);
1678 v4l2_ctrl_handler_init(hdl_meta_cap, 2);
1679 v4l2_ctrl_new_custom(hdl_meta_cap, &vivid_ctrl_class, NULL);
1680 v4l2_ctrl_handler_init(hdl_meta_out, 2);
1681 v4l2_ctrl_new_custom(hdl_meta_out, &vivid_ctrl_class, NULL);
1682 v4l2_ctrl_handler_init(hdl_tch_cap, 2);
1683 v4l2_ctrl_new_custom(hdl_tch_cap, &vivid_ctrl_class, NULL);
1684
1685 /* User Controls */
1686 dev->volume = v4l2_ctrl_new_std(hdl_user_aud, NULL,
1687 V4L2_CID_AUDIO_VOLUME, 0, 255, 1, 200);
1688 dev->mute = v4l2_ctrl_new_std(hdl_user_aud, NULL,
1689 V4L2_CID_AUDIO_MUTE, 0, 1, 1, 0);
1690 if (dev->has_vid_cap) {
1691 dev->brightness = v4l2_ctrl_new_std(hdl_user_vid, &vivid_user_vid_ctrl_ops,
1692 V4L2_CID_BRIGHTNESS, 0, 255, 1, 128);
1693 for (i = 0; i < MAX_INPUTS; i++)
1694 dev->input_brightness[i] = 128;
1695 dev->contrast = v4l2_ctrl_new_std(hdl_user_vid, &vivid_user_vid_ctrl_ops,
1696 V4L2_CID_CONTRAST, 0, 255, 1, 128);
1697 dev->saturation = v4l2_ctrl_new_std(hdl_user_vid, &vivid_user_vid_ctrl_ops,
1698 V4L2_CID_SATURATION, 0, 255, 1, 128);
1699 dev->hue = v4l2_ctrl_new_std(hdl_user_vid, &vivid_user_vid_ctrl_ops,
1700 V4L2_CID_HUE, -128, 128, 1, 0);
1701 v4l2_ctrl_new_std(hdl_user_vid, &vivid_user_vid_ctrl_ops,
1702 V4L2_CID_HFLIP, 0, 1, 1, 0);
1703 v4l2_ctrl_new_std(hdl_user_vid, &vivid_user_vid_ctrl_ops,
1704 V4L2_CID_VFLIP, 0, 1, 1, 0);
1705 dev->autogain = v4l2_ctrl_new_std(hdl_user_vid, &vivid_user_vid_ctrl_ops,
1706 V4L2_CID_AUTOGAIN, 0, 1, 1, 1);
1707 dev->gain = v4l2_ctrl_new_std(hdl_user_vid, &vivid_user_vid_ctrl_ops,
1708 V4L2_CID_GAIN, 0, 255, 1, 100);
1709 dev->alpha = v4l2_ctrl_new_std(hdl_user_vid, &vivid_user_vid_ctrl_ops,
1710 V4L2_CID_ALPHA_COMPONENT, 0, 255, 1, 0);
1711 }
1712 dev->button = v4l2_ctrl_new_custom(hdl_user_gen, &vivid_ctrl_button, NULL);
1713 dev->int32 = v4l2_ctrl_new_custom(hdl_user_gen, &vivid_ctrl_int32, NULL);
1714 dev->int64 = v4l2_ctrl_new_custom(hdl_user_gen, &vivid_ctrl_int64, NULL);
1715 dev->boolean = v4l2_ctrl_new_custom(hdl_user_gen, &vivid_ctrl_boolean, NULL);
1716 dev->menu = v4l2_ctrl_new_custom(hdl_user_gen, &vivid_ctrl_menu, NULL);
1717 dev->string = v4l2_ctrl_new_custom(hdl_user_gen, &vivid_ctrl_string, NULL);
1718 dev->bitmask = v4l2_ctrl_new_custom(hdl_user_gen, &vivid_ctrl_bitmask, NULL);
1719 dev->int_menu = v4l2_ctrl_new_custom(hdl_user_gen, &vivid_ctrl_int_menu, NULL);
1720 dev->ro_int32 = v4l2_ctrl_new_custom(hdl_user_gen, &vivid_ctrl_ro_int32, NULL);
1721 v4l2_ctrl_new_custom(hdl_user_gen, &vivid_ctrl_area, NULL);
1722 v4l2_ctrl_new_custom(hdl_user_gen, &vivid_ctrl_rect, NULL);
1723 v4l2_ctrl_new_custom(hdl_user_gen, &vivid_ctrl_u32_array, NULL);
1724 v4l2_ctrl_new_custom(hdl_user_gen, &vivid_ctrl_u32_dyn_array, NULL);
1725 v4l2_ctrl_new_custom(hdl_user_gen, &vivid_ctrl_u16_matrix, NULL);
1726 v4l2_ctrl_new_custom(hdl_user_gen, &vivid_ctrl_u8_4d_array, NULL);
1727 dev->pixel_array = v4l2_ctrl_new_custom(hdl_user_gen, &vivid_ctrl_u8_pixel_array, NULL);
1728 v4l2_ctrl_new_custom(hdl_user_gen, &vivid_ctrl_s32_array, NULL);
1729 v4l2_ctrl_new_custom(hdl_user_gen, &vivid_ctrl_s64_array, NULL);
1730
1731 if (dev->has_vid_cap) {
1732 /* Image Processing Controls */
1733 struct v4l2_ctrl_config vivid_ctrl_test_pattern = {
1734 .ops = &vivid_vid_cap_ctrl_ops,
1735 .id = VIVID_CID_TEST_PATTERN,
1736 .name = "Test Pattern",
1737 .type = V4L2_CTRL_TYPE_MENU,
1738 .max = TPG_PAT_NOISE,
1739 .qmenu = tpg_pattern_strings,
1740 };
1741
1742 dev->test_pattern = v4l2_ctrl_new_custom(hdl_vid_cap,
1743 &vivid_ctrl_test_pattern, NULL);
1744 v4l2_ctrl_new_custom(hdl_vid_cap, &vivid_ctrl_perc_fill, NULL);
1745 v4l2_ctrl_new_custom(hdl_vid_cap, &vivid_ctrl_hor_movement, NULL);
1746 v4l2_ctrl_new_custom(hdl_vid_cap, &vivid_ctrl_vert_movement, NULL);
1747 v4l2_ctrl_new_custom(hdl_vid_cap, &vivid_ctrl_osd_mode, NULL);
1748 v4l2_ctrl_new_custom(hdl_vid_cap, &vivid_ctrl_show_border, NULL);
1749 v4l2_ctrl_new_custom(hdl_vid_cap, &vivid_ctrl_show_square, NULL);
1750 v4l2_ctrl_new_custom(hdl_vid_cap, &vivid_ctrl_hflip, NULL);
1751 v4l2_ctrl_new_custom(hdl_vid_cap, &vivid_ctrl_vflip, NULL);
1752 v4l2_ctrl_new_custom(hdl_vid_cap, &vivid_ctrl_insert_sav, NULL);
1753 v4l2_ctrl_new_custom(hdl_vid_cap, &vivid_ctrl_insert_eav, NULL);
1754 v4l2_ctrl_new_custom(hdl_vid_cap, &vivid_ctrl_insert_hdmi_video_guard_band, NULL);
1755 v4l2_ctrl_new_custom(hdl_vid_cap, &vivid_ctrl_reduced_fps, NULL);
1756
1757 WARN_ON(dev->num_hdmi_inputs > MAX_HDMI_INPUTS);
1758 WARN_ON(dev->num_svid_inputs > MAX_SVID_INPUTS);
1759
1760 for (u8 i = 0; i < dev->num_hdmi_inputs; i++) {
1761 snprintf(dev->ctrl_hdmi_to_output_names[i],
1762 sizeof(dev->ctrl_hdmi_to_output_names[i]),
1763 "HDMI %03u-%u Is Connected To", dev->inst, i);
1764 }
1765
1766 for (u8 i = 0; i < dev->num_hdmi_inputs; i++) {
1767 struct v4l2_ctrl_config ctrl_config = {
1768 .ops = &vivid_vid_cap_ctrl_ops,
1769 .id = VIVID_CID_HDMI_IS_CONNECTED_TO_OUTPUT(i),
1770 .name = dev->ctrl_hdmi_to_output_names[i],
1771 .type = V4L2_CTRL_TYPE_MENU,
1772 .max = 1,
1773 .qmenu = (const char * const *)vivid_ctrl_hdmi_to_output_strings,
1774 };
1775 dev->ctrl_hdmi_to_output[i] = v4l2_ctrl_new_custom(hdl_vid_cap,
1776 &ctrl_config, NULL);
1777 }
1778
1779 for (u8 i = 0; i < dev->num_svid_inputs; i++) {
1780 snprintf(dev->ctrl_svid_to_output_names[i],
1781 sizeof(dev->ctrl_svid_to_output_names[i]),
1782 "S-Video %03u-%u Is Connected To", dev->inst, i);
1783 }
1784
1785 for (u8 i = 0; i < dev->num_svid_inputs; i++) {
1786 struct v4l2_ctrl_config ctrl_config = {
1787 .ops = &vivid_vid_cap_ctrl_ops,
1788 .id = VIVID_CID_SVID_IS_CONNECTED_TO_OUTPUT(i),
1789 .name = dev->ctrl_svid_to_output_names[i],
1790 .type = V4L2_CTRL_TYPE_MENU,
1791 .max = 1,
1792 .qmenu = (const char * const *)vivid_ctrl_svid_to_output_strings,
1793 };
1794 dev->ctrl_svid_to_output[i] = v4l2_ctrl_new_custom(hdl_vid_cap,
1795 &ctrl_config, NULL);
1796 }
1797
1798 if (show_ccs_cap) {
1799 dev->ctrl_has_crop_cap = v4l2_ctrl_new_custom(hdl_vid_cap,
1800 &vivid_ctrl_has_crop_cap, NULL);
1801 dev->ctrl_has_compose_cap = v4l2_ctrl_new_custom(hdl_vid_cap,
1802 &vivid_ctrl_has_compose_cap, NULL);
1803 dev->ctrl_has_scaler_cap = v4l2_ctrl_new_custom(hdl_vid_cap,
1804 &vivid_ctrl_has_scaler_cap, NULL);
1805 }
1806
1807 v4l2_ctrl_new_custom(hdl_vid_cap, &vivid_ctrl_tstamp_src, NULL);
1808 dev->colorspace = v4l2_ctrl_new_custom(hdl_vid_cap,
1809 &vivid_ctrl_colorspace, NULL);
1810 v4l2_ctrl_new_custom(hdl_vid_cap, &vivid_ctrl_xfer_func, NULL);
1811 v4l2_ctrl_new_custom(hdl_vid_cap, &vivid_ctrl_ycbcr_enc, NULL);
1812 v4l2_ctrl_new_custom(hdl_vid_cap, &vivid_ctrl_hsv_enc, NULL);
1813 v4l2_ctrl_new_custom(hdl_vid_cap, &vivid_ctrl_quantization, NULL);
1814 v4l2_ctrl_new_custom(hdl_vid_cap, &vivid_ctrl_alpha_mode, NULL);
1815 }
1816
1817 if (dev->has_vid_out && show_ccs_out) {
1818 dev->ctrl_has_crop_out = v4l2_ctrl_new_custom(hdl_vid_out,
1819 &vivid_ctrl_has_crop_out, NULL);
1820 dev->ctrl_has_compose_out = v4l2_ctrl_new_custom(hdl_vid_out,
1821 &vivid_ctrl_has_compose_out, NULL);
1822 dev->ctrl_has_scaler_out = v4l2_ctrl_new_custom(hdl_vid_out,
1823 &vivid_ctrl_has_scaler_out, NULL);
1824 }
1825
1826 /*
1827 * Testing this driver with v4l2-compliance will trigger the error
1828 * injection controls, and after that nothing will work as expected.
1829 * So we have a module option to drop these error injecting controls
1830 * allowing us to run v4l2_compliance again.
1831 */
1832 if (!no_error_inj) {
1833 v4l2_ctrl_new_custom(hdl_user_gen, &vivid_ctrl_disconnect, NULL);
1834 v4l2_ctrl_new_custom(hdl_streaming, &vivid_ctrl_dqbuf_error, NULL);
1835 v4l2_ctrl_new_custom(hdl_streaming, &vivid_ctrl_perc_dropped, NULL);
1836 v4l2_ctrl_new_custom(hdl_streaming, &vivid_ctrl_queue_setup_error, NULL);
1837 v4l2_ctrl_new_custom(hdl_streaming, &vivid_ctrl_buf_prepare_error, NULL);
1838 v4l2_ctrl_new_custom(hdl_streaming, &vivid_ctrl_start_streaming_error, NULL);
1839 v4l2_ctrl_new_custom(hdl_streaming, &vivid_ctrl_queue_error, NULL);
1840 #ifdef CONFIG_MEDIA_CONTROLLER
1841 v4l2_ctrl_new_custom(hdl_streaming, &vivid_ctrl_req_validate_error, NULL);
1842 #endif
1843 v4l2_ctrl_new_custom(hdl_streaming, &vivid_ctrl_seq_wrap, NULL);
1844 v4l2_ctrl_new_custom(hdl_streaming, &vivid_ctrl_time_wrap, NULL);
1845 }
1846
1847 if (has_sdtv && (dev->has_vid_cap || dev->has_vbi_cap)) {
1848 if (dev->has_vid_cap)
1849 v4l2_ctrl_new_custom(hdl_vid_cap, &vivid_ctrl_std_aspect_ratio, NULL);
1850 dev->ctrl_std_signal_mode = v4l2_ctrl_new_custom(hdl_sdtv_cap,
1851 &vivid_ctrl_std_signal_mode, NULL);
1852 dev->ctrl_standard = v4l2_ctrl_new_custom(hdl_sdtv_cap,
1853 &vivid_ctrl_standard, NULL);
1854 if (dev->ctrl_std_signal_mode)
1855 v4l2_ctrl_cluster(2, &dev->ctrl_std_signal_mode);
1856 if (dev->has_raw_vbi_cap)
1857 v4l2_ctrl_new_custom(hdl_vbi_cap, &vivid_ctrl_vbi_cap_interlaced, NULL);
1858 }
1859
1860 if (dev->num_hdmi_inputs) {
1861 s64 hdmi_input_mask = GENMASK(dev->num_hdmi_inputs - 1, 0);
1862
1863 dev->ctrl_dv_timings_signal_mode = v4l2_ctrl_new_custom(hdl_vid_cap,
1864 &vivid_ctrl_dv_timings_signal_mode, NULL);
1865
1866 vivid_ctrl_dv_timings.max = dev->query_dv_timings_size - 1;
1867 vivid_ctrl_dv_timings.qmenu =
1868 (const char * const *)dev->query_dv_timings_qmenu;
1869 dev->ctrl_dv_timings = v4l2_ctrl_new_custom(hdl_vid_cap,
1870 &vivid_ctrl_dv_timings, NULL);
1871 if (dev->ctrl_dv_timings_signal_mode)
1872 v4l2_ctrl_cluster(2, &dev->ctrl_dv_timings_signal_mode);
1873
1874 v4l2_ctrl_new_custom(hdl_vid_cap, &vivid_ctrl_dv_timings_aspect_ratio, NULL);
1875 v4l2_ctrl_new_custom(hdl_vid_cap, &vivid_ctrl_max_edid_blocks, NULL);
1876 dev->real_rgb_range_cap = v4l2_ctrl_new_custom(hdl_vid_cap,
1877 &vivid_ctrl_limited_rgb_range, NULL);
1878 dev->rgb_range_cap = v4l2_ctrl_new_std_menu(hdl_vid_cap,
1879 &vivid_vid_cap_ctrl_ops,
1880 V4L2_CID_DV_RX_RGB_RANGE, V4L2_DV_RGB_RANGE_FULL,
1881 0, V4L2_DV_RGB_RANGE_AUTO);
1882 dev->ctrl_rx_power_present = v4l2_ctrl_new_std(hdl_vid_cap,
1883 NULL, V4L2_CID_DV_RX_POWER_PRESENT, 0, hdmi_input_mask,
1884 0, hdmi_input_mask);
1885
1886 }
1887 if (dev->num_hdmi_outputs) {
1888 s64 hdmi_output_mask = GENMASK(dev->num_hdmi_outputs - 1, 0);
1889
1890 /*
1891 * We aren't doing anything with this at the moment, but
1892 * HDMI outputs typically have this controls.
1893 */
1894 dev->ctrl_tx_rgb_range = v4l2_ctrl_new_std_menu(hdl_vid_out, NULL,
1895 V4L2_CID_DV_TX_RGB_RANGE, V4L2_DV_RGB_RANGE_FULL,
1896 0, V4L2_DV_RGB_RANGE_AUTO);
1897 dev->ctrl_tx_mode = v4l2_ctrl_new_std_menu(hdl_vid_out, NULL,
1898 V4L2_CID_DV_TX_MODE, V4L2_DV_TX_MODE_HDMI,
1899 0, V4L2_DV_TX_MODE_HDMI);
1900 dev->ctrl_tx_hotplug = v4l2_ctrl_new_std(hdl_vid_out, NULL,
1901 V4L2_CID_DV_TX_HOTPLUG, 0, hdmi_output_mask, 0, 0);
1902 dev->ctrl_tx_rxsense = v4l2_ctrl_new_std(hdl_vid_out, NULL,
1903 V4L2_CID_DV_TX_RXSENSE, 0, hdmi_output_mask, 0, 0);
1904 dev->ctrl_tx_edid_present = v4l2_ctrl_new_std(hdl_vid_out, NULL,
1905 V4L2_CID_DV_TX_EDID_PRESENT, 0, hdmi_output_mask, 0, 0);
1906 }
1907
1908 if (dev->has_fb)
1909 v4l2_ctrl_new_custom(hdl_fb, &vivid_ctrl_clear_fb, NULL);
1910
1911 if (dev->has_radio_rx) {
1912 v4l2_ctrl_new_custom(hdl_radio_rx, &vivid_ctrl_radio_hw_seek_mode, NULL);
1913 v4l2_ctrl_new_custom(hdl_radio_rx, &vivid_ctrl_radio_hw_seek_prog_lim, NULL);
1914 v4l2_ctrl_new_custom(hdl_radio_rx, &vivid_ctrl_radio_rx_rds_blockio, NULL);
1915 v4l2_ctrl_new_custom(hdl_radio_rx, &vivid_ctrl_radio_rx_rds_rbds, NULL);
1916 v4l2_ctrl_new_std(hdl_radio_rx, &vivid_radio_rx_ctrl_ops,
1917 V4L2_CID_RDS_RECEPTION, 0, 1, 1, 1);
1918 dev->radio_rx_rds_pty = v4l2_ctrl_new_std(hdl_radio_rx,
1919 &vivid_radio_rx_ctrl_ops,
1920 V4L2_CID_RDS_RX_PTY, 0, 31, 1, 0);
1921 dev->radio_rx_rds_psname = v4l2_ctrl_new_std(hdl_radio_rx,
1922 &vivid_radio_rx_ctrl_ops,
1923 V4L2_CID_RDS_RX_PS_NAME, 0, 8, 8, 0);
1924 dev->radio_rx_rds_radiotext = v4l2_ctrl_new_std(hdl_radio_rx,
1925 &vivid_radio_rx_ctrl_ops,
1926 V4L2_CID_RDS_RX_RADIO_TEXT, 0, 64, 64, 0);
1927 dev->radio_rx_rds_ta = v4l2_ctrl_new_std(hdl_radio_rx,
1928 &vivid_radio_rx_ctrl_ops,
1929 V4L2_CID_RDS_RX_TRAFFIC_ANNOUNCEMENT, 0, 1, 1, 0);
1930 dev->radio_rx_rds_tp = v4l2_ctrl_new_std(hdl_radio_rx,
1931 &vivid_radio_rx_ctrl_ops,
1932 V4L2_CID_RDS_RX_TRAFFIC_PROGRAM, 0, 1, 1, 0);
1933 dev->radio_rx_rds_ms = v4l2_ctrl_new_std(hdl_radio_rx,
1934 &vivid_radio_rx_ctrl_ops,
1935 V4L2_CID_RDS_RX_MUSIC_SPEECH, 0, 1, 1, 1);
1936 }
1937 if (dev->has_radio_tx) {
1938 v4l2_ctrl_new_custom(hdl_radio_tx,
1939 &vivid_ctrl_radio_tx_rds_blockio, NULL);
1940 dev->radio_tx_rds_pi = v4l2_ctrl_new_std(hdl_radio_tx,
1941 &vivid_radio_tx_ctrl_ops,
1942 V4L2_CID_RDS_TX_PI, 0, 0xffff, 1, 0x8088);
1943 dev->radio_tx_rds_pty = v4l2_ctrl_new_std(hdl_radio_tx,
1944 &vivid_radio_tx_ctrl_ops,
1945 V4L2_CID_RDS_TX_PTY, 0, 31, 1, 3);
1946 dev->radio_tx_rds_psname = v4l2_ctrl_new_std(hdl_radio_tx,
1947 &vivid_radio_tx_ctrl_ops,
1948 V4L2_CID_RDS_TX_PS_NAME, 0, 8, 8, 0);
1949 if (dev->radio_tx_rds_psname)
1950 v4l2_ctrl_s_ctrl_string(dev->radio_tx_rds_psname, "VIVID-TX");
1951 dev->radio_tx_rds_radiotext = v4l2_ctrl_new_std(hdl_radio_tx,
1952 &vivid_radio_tx_ctrl_ops,
1953 V4L2_CID_RDS_TX_RADIO_TEXT, 0, 64 * 2, 64, 0);
1954 if (dev->radio_tx_rds_radiotext)
1955 v4l2_ctrl_s_ctrl_string(dev->radio_tx_rds_radiotext,
1956 "This is a VIVID default Radio Text template text, change at will");
1957 dev->radio_tx_rds_mono_stereo = v4l2_ctrl_new_std(hdl_radio_tx,
1958 &vivid_radio_tx_ctrl_ops,
1959 V4L2_CID_RDS_TX_MONO_STEREO, 0, 1, 1, 1);
1960 dev->radio_tx_rds_art_head = v4l2_ctrl_new_std(hdl_radio_tx,
1961 &vivid_radio_tx_ctrl_ops,
1962 V4L2_CID_RDS_TX_ARTIFICIAL_HEAD, 0, 1, 1, 0);
1963 dev->radio_tx_rds_compressed = v4l2_ctrl_new_std(hdl_radio_tx,
1964 &vivid_radio_tx_ctrl_ops,
1965 V4L2_CID_RDS_TX_COMPRESSED, 0, 1, 1, 0);
1966 dev->radio_tx_rds_dyn_pty = v4l2_ctrl_new_std(hdl_radio_tx,
1967 &vivid_radio_tx_ctrl_ops,
1968 V4L2_CID_RDS_TX_DYNAMIC_PTY, 0, 1, 1, 0);
1969 dev->radio_tx_rds_ta = v4l2_ctrl_new_std(hdl_radio_tx,
1970 &vivid_radio_tx_ctrl_ops,
1971 V4L2_CID_RDS_TX_TRAFFIC_ANNOUNCEMENT, 0, 1, 1, 0);
1972 dev->radio_tx_rds_tp = v4l2_ctrl_new_std(hdl_radio_tx,
1973 &vivid_radio_tx_ctrl_ops,
1974 V4L2_CID_RDS_TX_TRAFFIC_PROGRAM, 0, 1, 1, 1);
1975 dev->radio_tx_rds_ms = v4l2_ctrl_new_std(hdl_radio_tx,
1976 &vivid_radio_tx_ctrl_ops,
1977 V4L2_CID_RDS_TX_MUSIC_SPEECH, 0, 1, 1, 1);
1978 }
1979 if (dev->has_sdr_cap) {
1980 v4l2_ctrl_new_custom(hdl_sdr_cap,
1981 &vivid_ctrl_sdr_cap_fm_deviation, NULL);
1982 }
1983 if (dev->has_meta_cap) {
1984 v4l2_ctrl_new_custom(hdl_meta_cap,
1985 &vivid_ctrl_meta_has_pts, NULL);
1986 v4l2_ctrl_new_custom(hdl_meta_cap,
1987 &vivid_ctrl_meta_has_src_clk, NULL);
1988 }
1989
1990 if (hdl_user_gen->error)
1991 return hdl_user_gen->error;
1992 if (hdl_user_vid->error)
1993 return hdl_user_vid->error;
1994 if (hdl_user_aud->error)
1995 return hdl_user_aud->error;
1996 if (hdl_streaming->error)
1997 return hdl_streaming->error;
1998 if (hdl_sdr_cap->error)
1999 return hdl_sdr_cap->error;
2000 if (hdl_loop_cap->error)
2001 return hdl_loop_cap->error;
2002
2003 if (dev->autogain)
2004 v4l2_ctrl_auto_cluster(2, &dev->autogain, 0, true);
2005
2006 if (dev->has_vid_cap) {
2007 v4l2_ctrl_add_handler(hdl_vid_cap, hdl_user_gen, NULL, false);
2008 v4l2_ctrl_add_handler(hdl_vid_cap, hdl_user_vid, NULL, false);
2009 v4l2_ctrl_add_handler(hdl_vid_cap, hdl_user_aud, NULL, false);
2010 v4l2_ctrl_add_handler(hdl_vid_cap, hdl_streaming, NULL, false);
2011 v4l2_ctrl_add_handler(hdl_vid_cap, hdl_sdtv_cap, NULL, false);
2012 v4l2_ctrl_add_handler(hdl_vid_cap, hdl_loop_cap, NULL, false);
2013 v4l2_ctrl_add_handler(hdl_vid_cap, hdl_fb, NULL, false);
2014 if (hdl_vid_cap->error)
2015 return hdl_vid_cap->error;
2016 dev->vid_cap_dev.ctrl_handler = hdl_vid_cap;
2017 }
2018 if (dev->has_vid_out) {
2019 v4l2_ctrl_add_handler(hdl_vid_out, hdl_user_gen, NULL, false);
2020 v4l2_ctrl_add_handler(hdl_vid_out, hdl_user_aud, NULL, false);
2021 v4l2_ctrl_add_handler(hdl_vid_out, hdl_streaming, NULL, false);
2022 v4l2_ctrl_add_handler(hdl_vid_out, hdl_fb, NULL, false);
2023 if (hdl_vid_out->error)
2024 return hdl_vid_out->error;
2025 dev->vid_out_dev.ctrl_handler = hdl_vid_out;
2026 }
2027 if (dev->has_vbi_cap) {
2028 v4l2_ctrl_add_handler(hdl_vbi_cap, hdl_user_gen, NULL, false);
2029 v4l2_ctrl_add_handler(hdl_vbi_cap, hdl_streaming, NULL, false);
2030 v4l2_ctrl_add_handler(hdl_vbi_cap, hdl_sdtv_cap, NULL, false);
2031 v4l2_ctrl_add_handler(hdl_vbi_cap, hdl_loop_cap, NULL, false);
2032 if (hdl_vbi_cap->error)
2033 return hdl_vbi_cap->error;
2034 dev->vbi_cap_dev.ctrl_handler = hdl_vbi_cap;
2035 }
2036 if (dev->has_vbi_out) {
2037 v4l2_ctrl_add_handler(hdl_vbi_out, hdl_user_gen, NULL, false);
2038 v4l2_ctrl_add_handler(hdl_vbi_out, hdl_streaming, NULL, false);
2039 if (hdl_vbi_out->error)
2040 return hdl_vbi_out->error;
2041 dev->vbi_out_dev.ctrl_handler = hdl_vbi_out;
2042 }
2043 if (dev->has_radio_rx) {
2044 v4l2_ctrl_add_handler(hdl_radio_rx, hdl_user_gen, NULL, false);
2045 v4l2_ctrl_add_handler(hdl_radio_rx, hdl_user_aud, NULL, false);
2046 if (hdl_radio_rx->error)
2047 return hdl_radio_rx->error;
2048 dev->radio_rx_dev.ctrl_handler = hdl_radio_rx;
2049 }
2050 if (dev->has_radio_tx) {
2051 v4l2_ctrl_add_handler(hdl_radio_tx, hdl_user_gen, NULL, false);
2052 v4l2_ctrl_add_handler(hdl_radio_tx, hdl_user_aud, NULL, false);
2053 if (hdl_radio_tx->error)
2054 return hdl_radio_tx->error;
2055 dev->radio_tx_dev.ctrl_handler = hdl_radio_tx;
2056 }
2057 if (dev->has_sdr_cap) {
2058 v4l2_ctrl_add_handler(hdl_sdr_cap, hdl_user_gen, NULL, false);
2059 v4l2_ctrl_add_handler(hdl_sdr_cap, hdl_streaming, NULL, false);
2060 if (hdl_sdr_cap->error)
2061 return hdl_sdr_cap->error;
2062 dev->sdr_cap_dev.ctrl_handler = hdl_sdr_cap;
2063 }
2064 if (dev->has_meta_cap) {
2065 v4l2_ctrl_add_handler(hdl_meta_cap, hdl_user_gen, NULL, false);
2066 v4l2_ctrl_add_handler(hdl_meta_cap, hdl_streaming, NULL, false);
2067 if (hdl_meta_cap->error)
2068 return hdl_meta_cap->error;
2069 dev->meta_cap_dev.ctrl_handler = hdl_meta_cap;
2070 }
2071 if (dev->has_meta_out) {
2072 v4l2_ctrl_add_handler(hdl_meta_out, hdl_user_gen, NULL, false);
2073 v4l2_ctrl_add_handler(hdl_meta_out, hdl_streaming, NULL, false);
2074 if (hdl_meta_out->error)
2075 return hdl_meta_out->error;
2076 dev->meta_out_dev.ctrl_handler = hdl_meta_out;
2077 }
2078 if (dev->has_touch_cap) {
2079 v4l2_ctrl_add_handler(hdl_tch_cap, hdl_user_gen, NULL, false);
2080 v4l2_ctrl_add_handler(hdl_tch_cap, hdl_streaming, NULL, false);
2081 if (hdl_tch_cap->error)
2082 return hdl_tch_cap->error;
2083 dev->touch_cap_dev.ctrl_handler = hdl_tch_cap;
2084 }
2085 return 0;
2086 }
2087
vivid_free_controls(struct vivid_dev * dev)2088 void vivid_free_controls(struct vivid_dev *dev)
2089 {
2090 v4l2_ctrl_handler_free(&dev->ctrl_hdl_vid_cap);
2091 v4l2_ctrl_handler_free(&dev->ctrl_hdl_vid_out);
2092 v4l2_ctrl_handler_free(&dev->ctrl_hdl_vbi_cap);
2093 v4l2_ctrl_handler_free(&dev->ctrl_hdl_vbi_out);
2094 v4l2_ctrl_handler_free(&dev->ctrl_hdl_radio_rx);
2095 v4l2_ctrl_handler_free(&dev->ctrl_hdl_radio_tx);
2096 v4l2_ctrl_handler_free(&dev->ctrl_hdl_sdr_cap);
2097 v4l2_ctrl_handler_free(&dev->ctrl_hdl_user_gen);
2098 v4l2_ctrl_handler_free(&dev->ctrl_hdl_user_vid);
2099 v4l2_ctrl_handler_free(&dev->ctrl_hdl_user_aud);
2100 v4l2_ctrl_handler_free(&dev->ctrl_hdl_streaming);
2101 v4l2_ctrl_handler_free(&dev->ctrl_hdl_sdtv_cap);
2102 v4l2_ctrl_handler_free(&dev->ctrl_hdl_loop_cap);
2103 v4l2_ctrl_handler_free(&dev->ctrl_hdl_fb);
2104 v4l2_ctrl_handler_free(&dev->ctrl_hdl_meta_cap);
2105 v4l2_ctrl_handler_free(&dev->ctrl_hdl_meta_out);
2106 v4l2_ctrl_handler_free(&dev->ctrl_hdl_touch_cap);
2107 }
2108