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