linux/drivers/media/video/uvc/uvc_ctrl.c
<<
>>
Prefs
   1/*
   2 *      uvc_ctrl.c  --  USB Video Class driver - Controls
   3 *
   4 *      Copyright (C) 2005-2010
   5 *          Laurent Pinchart (laurent.pinchart@ideasonboard.com)
   6 *
   7 *      This program is free software; you can redistribute it and/or modify
   8 *      it under the terms of the GNU General Public License as published by
   9 *      the Free Software Foundation; either version 2 of the License, or
  10 *      (at your option) any later version.
  11 *
  12 */
  13
  14#include <linux/kernel.h>
  15#include <linux/list.h>
  16#include <linux/module.h>
  17#include <linux/slab.h>
  18#include <linux/uaccess.h>
  19#include <linux/usb.h>
  20#include <linux/videodev2.h>
  21#include <linux/vmalloc.h>
  22#include <linux/wait.h>
  23#include <linux/atomic.h>
  24
  25#include "uvcvideo.h"
  26
  27#define UVC_CTRL_DATA_CURRENT   0
  28#define UVC_CTRL_DATA_BACKUP    1
  29#define UVC_CTRL_DATA_MIN       2
  30#define UVC_CTRL_DATA_MAX       3
  31#define UVC_CTRL_DATA_RES       4
  32#define UVC_CTRL_DATA_DEF       5
  33#define UVC_CTRL_DATA_LAST      6
  34
  35/* ------------------------------------------------------------------------
  36 * Controls
  37 */
  38
  39static struct uvc_control_info uvc_ctrls[] = {
  40        {
  41                .entity         = UVC_GUID_UVC_PROCESSING,
  42                .selector       = UVC_PU_BRIGHTNESS_CONTROL,
  43                .index          = 0,
  44                .size           = 2,
  45                .flags          = UVC_CTRL_FLAG_SET_CUR
  46                                | UVC_CTRL_FLAG_GET_RANGE
  47                                | UVC_CTRL_FLAG_RESTORE,
  48        },
  49        {
  50                .entity         = UVC_GUID_UVC_PROCESSING,
  51                .selector       = UVC_PU_CONTRAST_CONTROL,
  52                .index          = 1,
  53                .size           = 2,
  54                .flags          = UVC_CTRL_FLAG_SET_CUR
  55                                | UVC_CTRL_FLAG_GET_RANGE
  56                                | UVC_CTRL_FLAG_RESTORE,
  57        },
  58        {
  59                .entity         = UVC_GUID_UVC_PROCESSING,
  60                .selector       = UVC_PU_HUE_CONTROL,
  61                .index          = 2,
  62                .size           = 2,
  63                .flags          = UVC_CTRL_FLAG_SET_CUR
  64                                | UVC_CTRL_FLAG_GET_RANGE
  65                                | UVC_CTRL_FLAG_RESTORE
  66                                | UVC_CTRL_FLAG_AUTO_UPDATE,
  67        },
  68        {
  69                .entity         = UVC_GUID_UVC_PROCESSING,
  70                .selector       = UVC_PU_SATURATION_CONTROL,
  71                .index          = 3,
  72                .size           = 2,
  73                .flags          = UVC_CTRL_FLAG_SET_CUR
  74                                | UVC_CTRL_FLAG_GET_RANGE
  75                                | UVC_CTRL_FLAG_RESTORE,
  76        },
  77        {
  78                .entity         = UVC_GUID_UVC_PROCESSING,
  79                .selector       = UVC_PU_SHARPNESS_CONTROL,
  80                .index          = 4,
  81                .size           = 2,
  82                .flags          = UVC_CTRL_FLAG_SET_CUR
  83                                | UVC_CTRL_FLAG_GET_RANGE
  84                                | UVC_CTRL_FLAG_RESTORE,
  85        },
  86        {
  87                .entity         = UVC_GUID_UVC_PROCESSING,
  88                .selector       = UVC_PU_GAMMA_CONTROL,
  89                .index          = 5,
  90                .size           = 2,
  91                .flags          = UVC_CTRL_FLAG_SET_CUR
  92                                | UVC_CTRL_FLAG_GET_RANGE
  93                                | UVC_CTRL_FLAG_RESTORE,
  94        },
  95        {
  96                .entity         = UVC_GUID_UVC_PROCESSING,
  97                .selector       = UVC_PU_WHITE_BALANCE_TEMPERATURE_CONTROL,
  98                .index          = 6,
  99                .size           = 2,
 100                .flags          = UVC_CTRL_FLAG_SET_CUR
 101                                | UVC_CTRL_FLAG_GET_RANGE
 102                                | UVC_CTRL_FLAG_RESTORE
 103                                | UVC_CTRL_FLAG_AUTO_UPDATE,
 104        },
 105        {
 106                .entity         = UVC_GUID_UVC_PROCESSING,
 107                .selector       = UVC_PU_WHITE_BALANCE_COMPONENT_CONTROL,
 108                .index          = 7,
 109                .size           = 4,
 110                .flags          = UVC_CTRL_FLAG_SET_CUR
 111                                | UVC_CTRL_FLAG_GET_RANGE
 112                                | UVC_CTRL_FLAG_RESTORE
 113                                | UVC_CTRL_FLAG_AUTO_UPDATE,
 114        },
 115        {
 116                .entity         = UVC_GUID_UVC_PROCESSING,
 117                .selector       = UVC_PU_BACKLIGHT_COMPENSATION_CONTROL,
 118                .index          = 8,
 119                .size           = 2,
 120                .flags          = UVC_CTRL_FLAG_SET_CUR
 121                                | UVC_CTRL_FLAG_GET_RANGE
 122                                | UVC_CTRL_FLAG_RESTORE,
 123        },
 124        {
 125                .entity         = UVC_GUID_UVC_PROCESSING,
 126                .selector       = UVC_PU_GAIN_CONTROL,
 127                .index          = 9,
 128                .size           = 2,
 129                .flags          = UVC_CTRL_FLAG_SET_CUR
 130                                | UVC_CTRL_FLAG_GET_RANGE
 131                                | UVC_CTRL_FLAG_RESTORE,
 132        },
 133        {
 134                .entity         = UVC_GUID_UVC_PROCESSING,
 135                .selector       = UVC_PU_POWER_LINE_FREQUENCY_CONTROL,
 136                .index          = 10,
 137                .size           = 1,
 138                .flags          = UVC_CTRL_FLAG_SET_CUR | UVC_CTRL_FLAG_GET_CUR
 139                                | UVC_CTRL_FLAG_GET_DEF | UVC_CTRL_FLAG_RESTORE,
 140        },
 141        {
 142                .entity         = UVC_GUID_UVC_PROCESSING,
 143                .selector       = UVC_PU_HUE_AUTO_CONTROL,
 144                .index          = 11,
 145                .size           = 1,
 146                .flags          = UVC_CTRL_FLAG_SET_CUR | UVC_CTRL_FLAG_GET_CUR
 147                                | UVC_CTRL_FLAG_GET_DEF | UVC_CTRL_FLAG_RESTORE,
 148        },
 149        {
 150                .entity         = UVC_GUID_UVC_PROCESSING,
 151                .selector       = UVC_PU_WHITE_BALANCE_TEMPERATURE_AUTO_CONTROL,
 152                .index          = 12,
 153                .size           = 1,
 154                .flags          = UVC_CTRL_FLAG_SET_CUR | UVC_CTRL_FLAG_GET_CUR
 155                                | UVC_CTRL_FLAG_GET_DEF | UVC_CTRL_FLAG_RESTORE,
 156        },
 157        {
 158                .entity         = UVC_GUID_UVC_PROCESSING,
 159                .selector       = UVC_PU_WHITE_BALANCE_COMPONENT_AUTO_CONTROL,
 160                .index          = 13,
 161                .size           = 1,
 162                .flags          = UVC_CTRL_FLAG_SET_CUR | UVC_CTRL_FLAG_GET_CUR
 163                                | UVC_CTRL_FLAG_GET_DEF | UVC_CTRL_FLAG_RESTORE,
 164        },
 165        {
 166                .entity         = UVC_GUID_UVC_PROCESSING,
 167                .selector       = UVC_PU_DIGITAL_MULTIPLIER_CONTROL,
 168                .index          = 14,
 169                .size           = 2,
 170                .flags          = UVC_CTRL_FLAG_SET_CUR
 171                                | UVC_CTRL_FLAG_GET_RANGE
 172                                | UVC_CTRL_FLAG_RESTORE,
 173        },
 174        {
 175                .entity         = UVC_GUID_UVC_PROCESSING,
 176                .selector       = UVC_PU_DIGITAL_MULTIPLIER_LIMIT_CONTROL,
 177                .index          = 15,
 178                .size           = 2,
 179                .flags          = UVC_CTRL_FLAG_SET_CUR
 180                                | UVC_CTRL_FLAG_GET_RANGE
 181                                | UVC_CTRL_FLAG_RESTORE,
 182        },
 183        {
 184                .entity         = UVC_GUID_UVC_PROCESSING,
 185                .selector       = UVC_PU_ANALOG_VIDEO_STANDARD_CONTROL,
 186                .index          = 16,
 187                .size           = 1,
 188                .flags          = UVC_CTRL_FLAG_GET_CUR,
 189        },
 190        {
 191                .entity         = UVC_GUID_UVC_PROCESSING,
 192                .selector       = UVC_PU_ANALOG_LOCK_STATUS_CONTROL,
 193                .index          = 17,
 194                .size           = 1,
 195                .flags          = UVC_CTRL_FLAG_GET_CUR,
 196        },
 197        {
 198                .entity         = UVC_GUID_UVC_CAMERA,
 199                .selector       = UVC_CT_SCANNING_MODE_CONTROL,
 200                .index          = 0,
 201                .size           = 1,
 202                .flags          = UVC_CTRL_FLAG_SET_CUR | UVC_CTRL_FLAG_GET_CUR
 203                                | UVC_CTRL_FLAG_RESTORE,
 204        },
 205        {
 206                .entity         = UVC_GUID_UVC_CAMERA,
 207                .selector       = UVC_CT_AE_MODE_CONTROL,
 208                .index          = 1,
 209                .size           = 1,
 210                .flags          = UVC_CTRL_FLAG_SET_CUR | UVC_CTRL_FLAG_GET_CUR
 211                                | UVC_CTRL_FLAG_GET_DEF | UVC_CTRL_FLAG_GET_RES
 212                                | UVC_CTRL_FLAG_RESTORE,
 213        },
 214        {
 215                .entity         = UVC_GUID_UVC_CAMERA,
 216                .selector       = UVC_CT_AE_PRIORITY_CONTROL,
 217                .index          = 2,
 218                .size           = 1,
 219                .flags          = UVC_CTRL_FLAG_SET_CUR | UVC_CTRL_FLAG_GET_CUR
 220                                | UVC_CTRL_FLAG_RESTORE,
 221        },
 222        {
 223                .entity         = UVC_GUID_UVC_CAMERA,
 224                .selector       = UVC_CT_EXPOSURE_TIME_ABSOLUTE_CONTROL,
 225                .index          = 3,
 226                .size           = 4,
 227                .flags          = UVC_CTRL_FLAG_SET_CUR
 228                                | UVC_CTRL_FLAG_GET_RANGE
 229                                | UVC_CTRL_FLAG_RESTORE,
 230        },
 231        {
 232                .entity         = UVC_GUID_UVC_CAMERA,
 233                .selector       = UVC_CT_EXPOSURE_TIME_RELATIVE_CONTROL,
 234                .index          = 4,
 235                .size           = 1,
 236                .flags          = UVC_CTRL_FLAG_SET_CUR | UVC_CTRL_FLAG_RESTORE,
 237        },
 238        {
 239                .entity         = UVC_GUID_UVC_CAMERA,
 240                .selector       = UVC_CT_FOCUS_ABSOLUTE_CONTROL,
 241                .index          = 5,
 242                .size           = 2,
 243                .flags          = UVC_CTRL_FLAG_SET_CUR
 244                                | UVC_CTRL_FLAG_GET_RANGE
 245                                | UVC_CTRL_FLAG_RESTORE
 246                                | UVC_CTRL_FLAG_AUTO_UPDATE,
 247        },
 248        {
 249                .entity         = UVC_GUID_UVC_CAMERA,
 250                .selector       = UVC_CT_FOCUS_RELATIVE_CONTROL,
 251                .index          = 6,
 252                .size           = 2,
 253                .flags          = UVC_CTRL_FLAG_SET_CUR | UVC_CTRL_FLAG_GET_MIN
 254                                | UVC_CTRL_FLAG_GET_MAX | UVC_CTRL_FLAG_GET_RES
 255                                | UVC_CTRL_FLAG_GET_DEF
 256                                | UVC_CTRL_FLAG_AUTO_UPDATE,
 257        },
 258        {
 259                .entity         = UVC_GUID_UVC_CAMERA,
 260                .selector       = UVC_CT_IRIS_ABSOLUTE_CONTROL,
 261                .index          = 7,
 262                .size           = 2,
 263                .flags          = UVC_CTRL_FLAG_SET_CUR
 264                                | UVC_CTRL_FLAG_GET_RANGE
 265                                | UVC_CTRL_FLAG_RESTORE
 266                                | UVC_CTRL_FLAG_AUTO_UPDATE,
 267        },
 268        {
 269                .entity         = UVC_GUID_UVC_CAMERA,
 270                .selector       = UVC_CT_IRIS_RELATIVE_CONTROL,
 271                .index          = 8,
 272                .size           = 1,
 273                .flags          = UVC_CTRL_FLAG_SET_CUR
 274                                | UVC_CTRL_FLAG_AUTO_UPDATE,
 275        },
 276        {
 277                .entity         = UVC_GUID_UVC_CAMERA,
 278                .selector       = UVC_CT_ZOOM_ABSOLUTE_CONTROL,
 279                .index          = 9,
 280                .size           = 2,
 281                .flags          = UVC_CTRL_FLAG_SET_CUR
 282                                | UVC_CTRL_FLAG_GET_RANGE
 283                                | UVC_CTRL_FLAG_RESTORE
 284                                | UVC_CTRL_FLAG_AUTO_UPDATE,
 285        },
 286        {
 287                .entity         = UVC_GUID_UVC_CAMERA,
 288                .selector       = UVC_CT_ZOOM_RELATIVE_CONTROL,
 289                .index          = 10,
 290                .size           = 3,
 291                .flags          = UVC_CTRL_FLAG_SET_CUR | UVC_CTRL_FLAG_GET_MIN
 292                                | UVC_CTRL_FLAG_GET_MAX | UVC_CTRL_FLAG_GET_RES
 293                                | UVC_CTRL_FLAG_GET_DEF
 294                                | UVC_CTRL_FLAG_AUTO_UPDATE,
 295        },
 296        {
 297                .entity         = UVC_GUID_UVC_CAMERA,
 298                .selector       = UVC_CT_PANTILT_ABSOLUTE_CONTROL,
 299                .index          = 11,
 300                .size           = 8,
 301                .flags          = UVC_CTRL_FLAG_SET_CUR
 302                                | UVC_CTRL_FLAG_GET_RANGE
 303                                | UVC_CTRL_FLAG_RESTORE
 304                                | UVC_CTRL_FLAG_AUTO_UPDATE,
 305        },
 306        {
 307                .entity         = UVC_GUID_UVC_CAMERA,
 308                .selector       = UVC_CT_PANTILT_RELATIVE_CONTROL,
 309                .index          = 12,
 310                .size           = 4,
 311                .flags          = UVC_CTRL_FLAG_SET_CUR | UVC_CTRL_FLAG_GET_MIN
 312                                | UVC_CTRL_FLAG_GET_MAX | UVC_CTRL_FLAG_GET_RES
 313                                | UVC_CTRL_FLAG_GET_DEF
 314                                | UVC_CTRL_FLAG_AUTO_UPDATE,
 315        },
 316        {
 317                .entity         = UVC_GUID_UVC_CAMERA,
 318                .selector       = UVC_CT_ROLL_ABSOLUTE_CONTROL,
 319                .index          = 13,
 320                .size           = 2,
 321                .flags          = UVC_CTRL_FLAG_SET_CUR
 322                                | UVC_CTRL_FLAG_GET_RANGE
 323                                | UVC_CTRL_FLAG_RESTORE
 324                                | UVC_CTRL_FLAG_AUTO_UPDATE,
 325        },
 326        {
 327                .entity         = UVC_GUID_UVC_CAMERA,
 328                .selector       = UVC_CT_ROLL_RELATIVE_CONTROL,
 329                .index          = 14,
 330                .size           = 2,
 331                .flags          = UVC_CTRL_FLAG_SET_CUR | UVC_CTRL_FLAG_GET_MIN
 332                                | UVC_CTRL_FLAG_GET_MAX | UVC_CTRL_FLAG_GET_RES
 333                                | UVC_CTRL_FLAG_GET_DEF
 334                                | UVC_CTRL_FLAG_AUTO_UPDATE,
 335        },
 336        {
 337                .entity         = UVC_GUID_UVC_CAMERA,
 338                .selector       = UVC_CT_FOCUS_AUTO_CONTROL,
 339                .index          = 17,
 340                .size           = 1,
 341                .flags          = UVC_CTRL_FLAG_SET_CUR | UVC_CTRL_FLAG_GET_CUR
 342                                | UVC_CTRL_FLAG_GET_DEF | UVC_CTRL_FLAG_RESTORE,
 343        },
 344        {
 345                .entity         = UVC_GUID_UVC_CAMERA,
 346                .selector       = UVC_CT_PRIVACY_CONTROL,
 347                .index          = 18,
 348                .size           = 1,
 349                .flags          = UVC_CTRL_FLAG_SET_CUR | UVC_CTRL_FLAG_GET_CUR
 350                                | UVC_CTRL_FLAG_RESTORE
 351                                | UVC_CTRL_FLAG_AUTO_UPDATE,
 352        },
 353};
 354
 355static struct uvc_menu_info power_line_frequency_controls[] = {
 356        { 0, "Disabled" },
 357        { 1, "50 Hz" },
 358        { 2, "60 Hz" },
 359};
 360
 361static struct uvc_menu_info exposure_auto_controls[] = {
 362        { 2, "Auto Mode" },
 363        { 1, "Manual Mode" },
 364        { 4, "Shutter Priority Mode" },
 365        { 8, "Aperture Priority Mode" },
 366};
 367
 368static __s32 uvc_ctrl_get_zoom(struct uvc_control_mapping *mapping,
 369        __u8 query, const __u8 *data)
 370{
 371        __s8 zoom = (__s8)data[0];
 372
 373        switch (query) {
 374        case UVC_GET_CUR:
 375                return (zoom == 0) ? 0 : (zoom > 0 ? data[2] : -data[2]);
 376
 377        case UVC_GET_MIN:
 378        case UVC_GET_MAX:
 379        case UVC_GET_RES:
 380        case UVC_GET_DEF:
 381        default:
 382                return data[2];
 383        }
 384}
 385
 386static void uvc_ctrl_set_zoom(struct uvc_control_mapping *mapping,
 387        __s32 value, __u8 *data)
 388{
 389        data[0] = value == 0 ? 0 : (value > 0) ? 1 : 0xff;
 390        data[2] = min((int)abs(value), 0xff);
 391}
 392
 393static struct uvc_control_mapping uvc_ctrl_mappings[] = {
 394        {
 395                .id             = V4L2_CID_BRIGHTNESS,
 396                .name           = "Brightness",
 397                .entity         = UVC_GUID_UVC_PROCESSING,
 398                .selector       = UVC_PU_BRIGHTNESS_CONTROL,
 399                .size           = 16,
 400                .offset         = 0,
 401                .v4l2_type      = V4L2_CTRL_TYPE_INTEGER,
 402                .data_type      = UVC_CTRL_DATA_TYPE_SIGNED,
 403        },
 404        {
 405                .id             = V4L2_CID_CONTRAST,
 406                .name           = "Contrast",
 407                .entity         = UVC_GUID_UVC_PROCESSING,
 408                .selector       = UVC_PU_CONTRAST_CONTROL,
 409                .size           = 16,
 410                .offset         = 0,
 411                .v4l2_type      = V4L2_CTRL_TYPE_INTEGER,
 412                .data_type      = UVC_CTRL_DATA_TYPE_UNSIGNED,
 413        },
 414        {
 415                .id             = V4L2_CID_HUE,
 416                .name           = "Hue",
 417                .entity         = UVC_GUID_UVC_PROCESSING,
 418                .selector       = UVC_PU_HUE_CONTROL,
 419                .size           = 16,
 420                .offset         = 0,
 421                .v4l2_type      = V4L2_CTRL_TYPE_INTEGER,
 422                .data_type      = UVC_CTRL_DATA_TYPE_SIGNED,
 423        },
 424        {
 425                .id             = V4L2_CID_SATURATION,
 426                .name           = "Saturation",
 427                .entity         = UVC_GUID_UVC_PROCESSING,
 428                .selector       = UVC_PU_SATURATION_CONTROL,
 429                .size           = 16,
 430                .offset         = 0,
 431                .v4l2_type      = V4L2_CTRL_TYPE_INTEGER,
 432                .data_type      = UVC_CTRL_DATA_TYPE_UNSIGNED,
 433        },
 434        {
 435                .id             = V4L2_CID_SHARPNESS,
 436                .name           = "Sharpness",
 437                .entity         = UVC_GUID_UVC_PROCESSING,
 438                .selector       = UVC_PU_SHARPNESS_CONTROL,
 439                .size           = 16,
 440                .offset         = 0,
 441                .v4l2_type      = V4L2_CTRL_TYPE_INTEGER,
 442                .data_type      = UVC_CTRL_DATA_TYPE_UNSIGNED,
 443        },
 444        {
 445                .id             = V4L2_CID_GAMMA,
 446                .name           = "Gamma",
 447                .entity         = UVC_GUID_UVC_PROCESSING,
 448                .selector       = UVC_PU_GAMMA_CONTROL,
 449                .size           = 16,
 450                .offset         = 0,
 451                .v4l2_type      = V4L2_CTRL_TYPE_INTEGER,
 452                .data_type      = UVC_CTRL_DATA_TYPE_UNSIGNED,
 453        },
 454        {
 455                .id             = V4L2_CID_BACKLIGHT_COMPENSATION,
 456                .name           = "Backlight Compensation",
 457                .entity         = UVC_GUID_UVC_PROCESSING,
 458                .selector       = UVC_PU_BACKLIGHT_COMPENSATION_CONTROL,
 459                .size           = 16,
 460                .offset         = 0,
 461                .v4l2_type      = V4L2_CTRL_TYPE_INTEGER,
 462                .data_type      = UVC_CTRL_DATA_TYPE_UNSIGNED,
 463        },
 464        {
 465                .id             = V4L2_CID_GAIN,
 466                .name           = "Gain",
 467                .entity         = UVC_GUID_UVC_PROCESSING,
 468                .selector       = UVC_PU_GAIN_CONTROL,
 469                .size           = 16,
 470                .offset         = 0,
 471                .v4l2_type      = V4L2_CTRL_TYPE_INTEGER,
 472                .data_type      = UVC_CTRL_DATA_TYPE_UNSIGNED,
 473        },
 474        {
 475                .id             = V4L2_CID_POWER_LINE_FREQUENCY,
 476                .name           = "Power Line Frequency",
 477                .entity         = UVC_GUID_UVC_PROCESSING,
 478                .selector       = UVC_PU_POWER_LINE_FREQUENCY_CONTROL,
 479                .size           = 2,
 480                .offset         = 0,
 481                .v4l2_type      = V4L2_CTRL_TYPE_MENU,
 482                .data_type      = UVC_CTRL_DATA_TYPE_ENUM,
 483                .menu_info      = power_line_frequency_controls,
 484                .menu_count     = ARRAY_SIZE(power_line_frequency_controls),
 485        },
 486        {
 487                .id             = V4L2_CID_HUE_AUTO,
 488                .name           = "Hue, Auto",
 489                .entity         = UVC_GUID_UVC_PROCESSING,
 490                .selector       = UVC_PU_HUE_AUTO_CONTROL,
 491                .size           = 1,
 492                .offset         = 0,
 493                .v4l2_type      = V4L2_CTRL_TYPE_BOOLEAN,
 494                .data_type      = UVC_CTRL_DATA_TYPE_BOOLEAN,
 495        },
 496        {
 497                .id             = V4L2_CID_EXPOSURE_AUTO,
 498                .name           = "Exposure, Auto",
 499                .entity         = UVC_GUID_UVC_CAMERA,
 500                .selector       = UVC_CT_AE_MODE_CONTROL,
 501                .size           = 4,
 502                .offset         = 0,
 503                .v4l2_type      = V4L2_CTRL_TYPE_MENU,
 504                .data_type      = UVC_CTRL_DATA_TYPE_BITMASK,
 505                .menu_info      = exposure_auto_controls,
 506                .menu_count     = ARRAY_SIZE(exposure_auto_controls),
 507        },
 508        {
 509                .id             = V4L2_CID_EXPOSURE_AUTO_PRIORITY,
 510                .name           = "Exposure, Auto Priority",
 511                .entity         = UVC_GUID_UVC_CAMERA,
 512                .selector       = UVC_CT_AE_PRIORITY_CONTROL,
 513                .size           = 1,
 514                .offset         = 0,
 515                .v4l2_type      = V4L2_CTRL_TYPE_BOOLEAN,
 516                .data_type      = UVC_CTRL_DATA_TYPE_BOOLEAN,
 517        },
 518        {
 519                .id             = V4L2_CID_EXPOSURE_ABSOLUTE,
 520                .name           = "Exposure (Absolute)",
 521                .entity         = UVC_GUID_UVC_CAMERA,
 522                .selector       = UVC_CT_EXPOSURE_TIME_ABSOLUTE_CONTROL,
 523                .size           = 32,
 524                .offset         = 0,
 525                .v4l2_type      = V4L2_CTRL_TYPE_INTEGER,
 526                .data_type      = UVC_CTRL_DATA_TYPE_UNSIGNED,
 527        },
 528        {
 529                .id             = V4L2_CID_AUTO_WHITE_BALANCE,
 530                .name           = "White Balance Temperature, Auto",
 531                .entity         = UVC_GUID_UVC_PROCESSING,
 532                .selector       = UVC_PU_WHITE_BALANCE_TEMPERATURE_AUTO_CONTROL,
 533                .size           = 1,
 534                .offset         = 0,
 535                .v4l2_type      = V4L2_CTRL_TYPE_BOOLEAN,
 536                .data_type      = UVC_CTRL_DATA_TYPE_BOOLEAN,
 537        },
 538        {
 539                .id             = V4L2_CID_WHITE_BALANCE_TEMPERATURE,
 540                .name           = "White Balance Temperature",
 541                .entity         = UVC_GUID_UVC_PROCESSING,
 542                .selector       = UVC_PU_WHITE_BALANCE_TEMPERATURE_CONTROL,
 543                .size           = 16,
 544                .offset         = 0,
 545                .v4l2_type      = V4L2_CTRL_TYPE_INTEGER,
 546                .data_type      = UVC_CTRL_DATA_TYPE_UNSIGNED,
 547        },
 548        {
 549                .id             = V4L2_CID_AUTO_WHITE_BALANCE,
 550                .name           = "White Balance Component, Auto",
 551                .entity         = UVC_GUID_UVC_PROCESSING,
 552                .selector       = UVC_PU_WHITE_BALANCE_COMPONENT_AUTO_CONTROL,
 553                .size           = 1,
 554                .offset         = 0,
 555                .v4l2_type      = V4L2_CTRL_TYPE_BOOLEAN,
 556                .data_type      = UVC_CTRL_DATA_TYPE_BOOLEAN,
 557        },
 558        {
 559                .id             = V4L2_CID_BLUE_BALANCE,
 560                .name           = "White Balance Blue Component",
 561                .entity         = UVC_GUID_UVC_PROCESSING,
 562                .selector       = UVC_PU_WHITE_BALANCE_COMPONENT_CONTROL,
 563                .size           = 16,
 564                .offset         = 0,
 565                .v4l2_type      = V4L2_CTRL_TYPE_INTEGER,
 566                .data_type      = UVC_CTRL_DATA_TYPE_SIGNED,
 567        },
 568        {
 569                .id             = V4L2_CID_RED_BALANCE,
 570                .name           = "White Balance Red Component",
 571                .entity         = UVC_GUID_UVC_PROCESSING,
 572                .selector       = UVC_PU_WHITE_BALANCE_COMPONENT_CONTROL,
 573                .size           = 16,
 574                .offset         = 16,
 575                .v4l2_type      = V4L2_CTRL_TYPE_INTEGER,
 576                .data_type      = UVC_CTRL_DATA_TYPE_SIGNED,
 577        },
 578        {
 579                .id             = V4L2_CID_FOCUS_ABSOLUTE,
 580                .name           = "Focus (absolute)",
 581                .entity         = UVC_GUID_UVC_CAMERA,
 582                .selector       = UVC_CT_FOCUS_ABSOLUTE_CONTROL,
 583                .size           = 16,
 584                .offset         = 0,
 585                .v4l2_type      = V4L2_CTRL_TYPE_INTEGER,
 586                .data_type      = UVC_CTRL_DATA_TYPE_UNSIGNED,
 587        },
 588        {
 589                .id             = V4L2_CID_FOCUS_AUTO,
 590                .name           = "Focus, Auto",
 591                .entity         = UVC_GUID_UVC_CAMERA,
 592                .selector       = UVC_CT_FOCUS_AUTO_CONTROL,
 593                .size           = 1,
 594                .offset         = 0,
 595                .v4l2_type      = V4L2_CTRL_TYPE_BOOLEAN,
 596                .data_type      = UVC_CTRL_DATA_TYPE_BOOLEAN,
 597        },
 598        {
 599                .id             = V4L2_CID_IRIS_ABSOLUTE,
 600                .name           = "Iris, Absolute",
 601                .entity         = UVC_GUID_UVC_CAMERA,
 602                .selector       = UVC_CT_IRIS_ABSOLUTE_CONTROL,
 603                .size           = 16,
 604                .offset         = 0,
 605                .v4l2_type      = V4L2_CTRL_TYPE_INTEGER,
 606                .data_type      = UVC_CTRL_DATA_TYPE_UNSIGNED,
 607        },
 608        {
 609                .id             = V4L2_CID_IRIS_RELATIVE,
 610                .name           = "Iris, Relative",
 611                .entity         = UVC_GUID_UVC_CAMERA,
 612                .selector       = UVC_CT_IRIS_RELATIVE_CONTROL,
 613                .size           = 8,
 614                .offset         = 0,
 615                .v4l2_type      = V4L2_CTRL_TYPE_INTEGER,
 616                .data_type      = UVC_CTRL_DATA_TYPE_SIGNED,
 617        },
 618        {
 619                .id             = V4L2_CID_ZOOM_ABSOLUTE,
 620                .name           = "Zoom, Absolute",
 621                .entity         = UVC_GUID_UVC_CAMERA,
 622                .selector       = UVC_CT_ZOOM_ABSOLUTE_CONTROL,
 623                .size           = 16,
 624                .offset         = 0,
 625                .v4l2_type      = V4L2_CTRL_TYPE_INTEGER,
 626                .data_type      = UVC_CTRL_DATA_TYPE_UNSIGNED,
 627        },
 628        {
 629                .id             = V4L2_CID_ZOOM_CONTINUOUS,
 630                .name           = "Zoom, Continuous",
 631                .entity         = UVC_GUID_UVC_CAMERA,
 632                .selector       = UVC_CT_ZOOM_RELATIVE_CONTROL,
 633                .size           = 0,
 634                .offset         = 0,
 635                .v4l2_type      = V4L2_CTRL_TYPE_INTEGER,
 636                .data_type      = UVC_CTRL_DATA_TYPE_SIGNED,
 637                .get            = uvc_ctrl_get_zoom,
 638                .set            = uvc_ctrl_set_zoom,
 639        },
 640        {
 641                .id             = V4L2_CID_PAN_ABSOLUTE,
 642                .name           = "Pan (Absolute)",
 643                .entity         = UVC_GUID_UVC_CAMERA,
 644                .selector       = UVC_CT_PANTILT_ABSOLUTE_CONTROL,
 645                .size           = 32,
 646                .offset         = 0,
 647                .v4l2_type      = V4L2_CTRL_TYPE_INTEGER,
 648                .data_type      = UVC_CTRL_DATA_TYPE_UNSIGNED,
 649        },
 650        {
 651                .id             = V4L2_CID_TILT_ABSOLUTE,
 652                .name           = "Tilt (Absolute)",
 653                .entity         = UVC_GUID_UVC_CAMERA,
 654                .selector       = UVC_CT_PANTILT_ABSOLUTE_CONTROL,
 655                .size           = 32,
 656                .offset         = 32,
 657                .v4l2_type      = V4L2_CTRL_TYPE_INTEGER,
 658                .data_type      = UVC_CTRL_DATA_TYPE_UNSIGNED,
 659        },
 660        {
 661                .id             = V4L2_CID_PRIVACY,
 662                .name           = "Privacy",
 663                .entity         = UVC_GUID_UVC_CAMERA,
 664                .selector       = UVC_CT_PRIVACY_CONTROL,
 665                .size           = 1,
 666                .offset         = 0,
 667                .v4l2_type      = V4L2_CTRL_TYPE_BOOLEAN,
 668                .data_type      = UVC_CTRL_DATA_TYPE_BOOLEAN,
 669        },
 670};
 671
 672/* ------------------------------------------------------------------------
 673 * Utility functions
 674 */
 675
 676static inline __u8 *uvc_ctrl_data(struct uvc_control *ctrl, int id)
 677{
 678        return ctrl->uvc_data + id * ctrl->info.size;
 679}
 680
 681static inline int uvc_test_bit(const __u8 *data, int bit)
 682{
 683        return (data[bit >> 3] >> (bit & 7)) & 1;
 684}
 685
 686static inline void uvc_clear_bit(__u8 *data, int bit)
 687{
 688        data[bit >> 3] &= ~(1 << (bit & 7));
 689}
 690
 691/* Extract the bit string specified by mapping->offset and mapping->size
 692 * from the little-endian data stored at 'data' and return the result as
 693 * a signed 32bit integer. Sign extension will be performed if the mapping
 694 * references a signed data type.
 695 */
 696static __s32 uvc_get_le_value(struct uvc_control_mapping *mapping,
 697        __u8 query, const __u8 *data)
 698{
 699        int bits = mapping->size;
 700        int offset = mapping->offset;
 701        __s32 value = 0;
 702        __u8 mask;
 703
 704        data += offset / 8;
 705        offset &= 7;
 706        mask = ((1LL << bits) - 1) << offset;
 707
 708        for (; bits > 0; data++) {
 709                __u8 byte = *data & mask;
 710                value |= offset > 0 ? (byte >> offset) : (byte << (-offset));
 711                bits -= 8 - (offset > 0 ? offset : 0);
 712                offset -= 8;
 713                mask = (1 << bits) - 1;
 714        }
 715
 716        /* Sign-extend the value if needed. */
 717        if (mapping->data_type == UVC_CTRL_DATA_TYPE_SIGNED)
 718                value |= -(value & (1 << (mapping->size - 1)));
 719
 720        return value;
 721}
 722
 723/* Set the bit string specified by mapping->offset and mapping->size
 724 * in the little-endian data stored at 'data' to the value 'value'.
 725 */
 726static void uvc_set_le_value(struct uvc_control_mapping *mapping,
 727        __s32 value, __u8 *data)
 728{
 729        int bits = mapping->size;
 730        int offset = mapping->offset;
 731        __u8 mask;
 732
 733        /* According to the v4l2 spec, writing any value to a button control
 734         * should result in the action belonging to the button control being
 735         * triggered. UVC devices however want to see a 1 written -> override
 736         * value.
 737         */
 738        if (mapping->v4l2_type == V4L2_CTRL_TYPE_BUTTON)
 739                value = -1;
 740
 741        data += offset / 8;
 742        offset &= 7;
 743
 744        for (; bits > 0; data++) {
 745                mask = ((1LL << bits) - 1) << offset;
 746                *data = (*data & ~mask) | ((value << offset) & mask);
 747                value >>= offset ? offset : 8;
 748                bits -= 8 - offset;
 749                offset = 0;
 750        }
 751}
 752
 753/* ------------------------------------------------------------------------
 754 * Terminal and unit management
 755 */
 756
 757static const __u8 uvc_processing_guid[16] = UVC_GUID_UVC_PROCESSING;
 758static const __u8 uvc_camera_guid[16] = UVC_GUID_UVC_CAMERA;
 759static const __u8 uvc_media_transport_input_guid[16] =
 760        UVC_GUID_UVC_MEDIA_TRANSPORT_INPUT;
 761
 762static int uvc_entity_match_guid(const struct uvc_entity *entity,
 763        const __u8 guid[16])
 764{
 765        switch (UVC_ENTITY_TYPE(entity)) {
 766        case UVC_ITT_CAMERA:
 767                return memcmp(uvc_camera_guid, guid, 16) == 0;
 768
 769        case UVC_ITT_MEDIA_TRANSPORT_INPUT:
 770                return memcmp(uvc_media_transport_input_guid, guid, 16) == 0;
 771
 772        case UVC_VC_PROCESSING_UNIT:
 773                return memcmp(uvc_processing_guid, guid, 16) == 0;
 774
 775        case UVC_VC_EXTENSION_UNIT:
 776                return memcmp(entity->extension.guidExtensionCode,
 777                              guid, 16) == 0;
 778
 779        default:
 780                return 0;
 781        }
 782}
 783
 784/* ------------------------------------------------------------------------
 785 * UVC Controls
 786 */
 787
 788static void __uvc_find_control(struct uvc_entity *entity, __u32 v4l2_id,
 789        struct uvc_control_mapping **mapping, struct uvc_control **control,
 790        int next)
 791{
 792        struct uvc_control *ctrl;
 793        struct uvc_control_mapping *map;
 794        unsigned int i;
 795
 796        if (entity == NULL)
 797                return;
 798
 799        for (i = 0; i < entity->ncontrols; ++i) {
 800                ctrl = &entity->controls[i];
 801                if (!ctrl->initialized)
 802                        continue;
 803
 804                list_for_each_entry(map, &ctrl->info.mappings, list) {
 805                        if ((map->id == v4l2_id) && !next) {
 806                                *control = ctrl;
 807                                *mapping = map;
 808                                return;
 809                        }
 810
 811                        if ((*mapping == NULL || (*mapping)->id > map->id) &&
 812                            (map->id > v4l2_id) && next) {
 813                                *control = ctrl;
 814                                *mapping = map;
 815                        }
 816                }
 817        }
 818}
 819
 820static struct uvc_control *uvc_find_control(struct uvc_video_chain *chain,
 821        __u32 v4l2_id, struct uvc_control_mapping **mapping)
 822{
 823        struct uvc_control *ctrl = NULL;
 824        struct uvc_entity *entity;
 825        int next = v4l2_id & V4L2_CTRL_FLAG_NEXT_CTRL;
 826
 827        *mapping = NULL;
 828
 829        /* Mask the query flags. */
 830        v4l2_id &= V4L2_CTRL_ID_MASK;
 831
 832        /* Find the control. */
 833        list_for_each_entry(entity, &chain->entities, chain) {
 834                __uvc_find_control(entity, v4l2_id, mapping, &ctrl, next);
 835                if (ctrl && !next)
 836                        return ctrl;
 837        }
 838
 839        if (ctrl == NULL && !next)
 840                uvc_trace(UVC_TRACE_CONTROL, "Control 0x%08x not found.\n",
 841                                v4l2_id);
 842
 843        return ctrl;
 844}
 845
 846static int uvc_ctrl_populate_cache(struct uvc_video_chain *chain,
 847        struct uvc_control *ctrl)
 848{
 849        int ret;
 850
 851        if (ctrl->info.flags & UVC_CTRL_FLAG_GET_DEF) {
 852                ret = uvc_query_ctrl(chain->dev, UVC_GET_DEF, ctrl->entity->id,
 853                                     chain->dev->intfnum, ctrl->info.selector,
 854                                     uvc_ctrl_data(ctrl, UVC_CTRL_DATA_DEF),
 855                                     ctrl->info.size);
 856                if (ret < 0)
 857                        return ret;
 858        }
 859
 860        if (ctrl->info.flags & UVC_CTRL_FLAG_GET_MIN) {
 861                ret = uvc_query_ctrl(chain->dev, UVC_GET_MIN, ctrl->entity->id,
 862                                     chain->dev->intfnum, ctrl->info.selector,
 863                                     uvc_ctrl_data(ctrl, UVC_CTRL_DATA_MIN),
 864                                     ctrl->info.size);
 865                if (ret < 0)
 866                        return ret;
 867        }
 868        if (ctrl->info.flags & UVC_CTRL_FLAG_GET_MAX) {
 869                ret = uvc_query_ctrl(chain->dev, UVC_GET_MAX, ctrl->entity->id,
 870                                     chain->dev->intfnum, ctrl->info.selector,
 871                                     uvc_ctrl_data(ctrl, UVC_CTRL_DATA_MAX),
 872                                     ctrl->info.size);
 873                if (ret < 0)
 874                        return ret;
 875        }
 876        if (ctrl->info.flags & UVC_CTRL_FLAG_GET_RES) {
 877                ret = uvc_query_ctrl(chain->dev, UVC_GET_RES, ctrl->entity->id,
 878                                     chain->dev->intfnum, ctrl->info.selector,
 879                                     uvc_ctrl_data(ctrl, UVC_CTRL_DATA_RES),
 880                                     ctrl->info.size);
 881                if (ret < 0)
 882                        return ret;
 883        }
 884
 885        ctrl->cached = 1;
 886        return 0;
 887}
 888
 889int uvc_query_v4l2_ctrl(struct uvc_video_chain *chain,
 890        struct v4l2_queryctrl *v4l2_ctrl)
 891{
 892        struct uvc_control *ctrl;
 893        struct uvc_control_mapping *mapping;
 894        struct uvc_menu_info *menu;
 895        unsigned int i;
 896        int ret;
 897
 898        ret = mutex_lock_interruptible(&chain->ctrl_mutex);
 899        if (ret < 0)
 900                return -ERESTARTSYS;
 901
 902        ctrl = uvc_find_control(chain, v4l2_ctrl->id, &mapping);
 903        if (ctrl == NULL) {
 904                ret = -EINVAL;
 905                goto done;
 906        }
 907
 908        memset(v4l2_ctrl, 0, sizeof *v4l2_ctrl);
 909        v4l2_ctrl->id = mapping->id;
 910        v4l2_ctrl->type = mapping->v4l2_type;
 911        strlcpy(v4l2_ctrl->name, mapping->name, sizeof v4l2_ctrl->name);
 912        v4l2_ctrl->flags = 0;
 913
 914        if (!(ctrl->info.flags & UVC_CTRL_FLAG_GET_CUR))
 915                v4l2_ctrl->flags |= V4L2_CTRL_FLAG_WRITE_ONLY;
 916        if (!(ctrl->info.flags & UVC_CTRL_FLAG_SET_CUR))
 917                v4l2_ctrl->flags |= V4L2_CTRL_FLAG_READ_ONLY;
 918
 919        if (!ctrl->cached) {
 920                ret = uvc_ctrl_populate_cache(chain, ctrl);
 921                if (ret < 0)
 922                        goto done;
 923        }
 924
 925        if (ctrl->info.flags & UVC_CTRL_FLAG_GET_DEF) {
 926                v4l2_ctrl->default_value = mapping->get(mapping, UVC_GET_DEF,
 927                                uvc_ctrl_data(ctrl, UVC_CTRL_DATA_DEF));
 928        }
 929
 930        switch (mapping->v4l2_type) {
 931        case V4L2_CTRL_TYPE_MENU:
 932                v4l2_ctrl->minimum = 0;
 933                v4l2_ctrl->maximum = mapping->menu_count - 1;
 934                v4l2_ctrl->step = 1;
 935
 936                menu = mapping->menu_info;
 937                for (i = 0; i < mapping->menu_count; ++i, ++menu) {
 938                        if (menu->value == v4l2_ctrl->default_value) {
 939                                v4l2_ctrl->default_value = i;
 940                                break;
 941                        }
 942                }
 943
 944                goto done;
 945
 946        case V4L2_CTRL_TYPE_BOOLEAN:
 947                v4l2_ctrl->minimum = 0;
 948                v4l2_ctrl->maximum = 1;
 949                v4l2_ctrl->step = 1;
 950                goto done;
 951
 952        case V4L2_CTRL_TYPE_BUTTON:
 953                v4l2_ctrl->minimum = 0;
 954                v4l2_ctrl->maximum = 0;
 955                v4l2_ctrl->step = 0;
 956                goto done;
 957
 958        default:
 959                break;
 960        }
 961
 962        if (ctrl->info.flags & UVC_CTRL_FLAG_GET_MIN)
 963                v4l2_ctrl->minimum = mapping->get(mapping, UVC_GET_MIN,
 964                                     uvc_ctrl_data(ctrl, UVC_CTRL_DATA_MIN));
 965
 966        if (ctrl->info.flags & UVC_CTRL_FLAG_GET_MAX)
 967                v4l2_ctrl->maximum = mapping->get(mapping, UVC_GET_MAX,
 968                                     uvc_ctrl_data(ctrl, UVC_CTRL_DATA_MAX));
 969
 970        if (ctrl->info.flags & UVC_CTRL_FLAG_GET_RES)
 971                v4l2_ctrl->step = mapping->get(mapping, UVC_GET_RES,
 972                                  uvc_ctrl_data(ctrl, UVC_CTRL_DATA_RES));
 973
 974done:
 975        mutex_unlock(&chain->ctrl_mutex);
 976        return ret;
 977}
 978
 979/*
 980 * Mapping V4L2 controls to UVC controls can be straighforward if done well.
 981 * Most of the UVC controls exist in V4L2, and can be mapped directly. Some
 982 * must be grouped (for instance the Red Balance, Blue Balance and Do White
 983 * Balance V4L2 controls use the White Balance Component UVC control) or
 984 * otherwise translated. The approach we take here is to use a translation
 985 * table for the controls that can be mapped directly, and handle the others
 986 * manually.
 987 */
 988int uvc_query_v4l2_menu(struct uvc_video_chain *chain,
 989        struct v4l2_querymenu *query_menu)
 990{
 991        struct uvc_menu_info *menu_info;
 992        struct uvc_control_mapping *mapping;
 993        struct uvc_control *ctrl;
 994        u32 index = query_menu->index;
 995        u32 id = query_menu->id;
 996        int ret;
 997
 998        memset(query_menu, 0, sizeof(*query_menu));
 999        query_menu->id = id;
1000        query_menu->index = index;
1001
1002        ret = mutex_lock_interruptible(&chain->ctrl_mutex);
1003        if (ret < 0)
1004                return -ERESTARTSYS;
1005
1006        ctrl = uvc_find_control(chain, query_menu->id, &mapping);
1007        if (ctrl == NULL || mapping->v4l2_type != V4L2_CTRL_TYPE_MENU) {
1008                ret = -EINVAL;
1009                goto done;
1010        }
1011
1012        if (query_menu->index >= mapping->menu_count) {
1013                ret = -EINVAL;
1014                goto done;
1015        }
1016
1017        menu_info = &mapping->menu_info[query_menu->index];
1018
1019        if (ctrl->info.flags & UVC_CTRL_FLAG_GET_RES) {
1020                s32 bitmap;
1021
1022                if (!ctrl->cached) {
1023                        ret = uvc_ctrl_populate_cache(chain, ctrl);
1024                        if (ret < 0)
1025                                goto done;
1026                }
1027
1028                bitmap = mapping->get(mapping, UVC_GET_RES,
1029                                      uvc_ctrl_data(ctrl, UVC_CTRL_DATA_RES));
1030                if (!(bitmap & menu_info->value)) {
1031                        ret = -EINVAL;
1032                        goto done;
1033                }
1034        }
1035
1036        strlcpy(query_menu->name, menu_info->name, sizeof query_menu->name);
1037
1038done:
1039        mutex_unlock(&chain->ctrl_mutex);
1040        return ret;
1041}
1042
1043
1044/* --------------------------------------------------------------------------
1045 * Control transactions
1046 *
1047 * To make extended set operations as atomic as the hardware allows, controls
1048 * are handled using begin/commit/rollback operations.
1049 *
1050 * At the beginning of a set request, uvc_ctrl_begin should be called to
1051 * initialize the request. This function acquires the control lock.
1052 *
1053 * When setting a control, the new value is stored in the control data field
1054 * at position UVC_CTRL_DATA_CURRENT. The control is then marked as dirty for
1055 * later processing. If the UVC and V4L2 control sizes differ, the current
1056 * value is loaded from the hardware before storing the new value in the data
1057 * field.
1058 *
1059 * After processing all controls in the transaction, uvc_ctrl_commit or
1060 * uvc_ctrl_rollback must be called to apply the pending changes to the
1061 * hardware or revert them. When applying changes, all controls marked as
1062 * dirty will be modified in the UVC device, and the dirty flag will be
1063 * cleared. When reverting controls, the control data field
1064 * UVC_CTRL_DATA_CURRENT is reverted to its previous value
1065 * (UVC_CTRL_DATA_BACKUP) for all dirty controls. Both functions release the
1066 * control lock.
1067 */
1068int uvc_ctrl_begin(struct uvc_video_chain *chain)
1069{
1070        return mutex_lock_interruptible(&chain->ctrl_mutex) ? -ERESTARTSYS : 0;
1071}
1072
1073static int uvc_ctrl_commit_entity(struct uvc_device *dev,
1074        struct uvc_entity *entity, int rollback)
1075{
1076        struct uvc_control *ctrl;
1077        unsigned int i;
1078        int ret;
1079
1080        if (entity == NULL)
1081                return 0;
1082
1083        for (i = 0; i < entity->ncontrols; ++i) {
1084                ctrl = &entity->controls[i];
1085                if (!ctrl->initialized)
1086                        continue;
1087
1088                /* Reset the loaded flag for auto-update controls that were
1089                 * marked as loaded in uvc_ctrl_get/uvc_ctrl_set to prevent
1090                 * uvc_ctrl_get from using the cached value.
1091                 */
1092                if (ctrl->info.flags & UVC_CTRL_FLAG_AUTO_UPDATE)
1093                        ctrl->loaded = 0;
1094
1095                if (!ctrl->dirty)
1096                        continue;
1097
1098                if (!rollback)
1099                        ret = uvc_query_ctrl(dev, UVC_SET_CUR, ctrl->entity->id,
1100                                dev->intfnum, ctrl->info.selector,
1101                                uvc_ctrl_data(ctrl, UVC_CTRL_DATA_CURRENT),
1102                                ctrl->info.size);
1103                else
1104                        ret = 0;
1105
1106                if (rollback || ret < 0)
1107                        memcpy(uvc_ctrl_data(ctrl, UVC_CTRL_DATA_CURRENT),
1108                               uvc_ctrl_data(ctrl, UVC_CTRL_DATA_BACKUP),
1109                               ctrl->info.size);
1110
1111                ctrl->dirty = 0;
1112
1113                if (ret < 0)
1114                        return ret;
1115        }
1116
1117        return 0;
1118}
1119
1120int __uvc_ctrl_commit(struct uvc_video_chain *chain, int rollback)
1121{
1122        struct uvc_entity *entity;
1123        int ret = 0;
1124
1125        /* Find the control. */
1126        list_for_each_entry(entity, &chain->entities, chain) {
1127                ret = uvc_ctrl_commit_entity(chain->dev, entity, rollback);
1128                if (ret < 0)
1129                        goto done;
1130        }
1131
1132done:
1133        mutex_unlock(&chain->ctrl_mutex);
1134        return ret;
1135}
1136
1137int uvc_ctrl_get(struct uvc_video_chain *chain,
1138        struct v4l2_ext_control *xctrl)
1139{
1140        struct uvc_control *ctrl;
1141        struct uvc_control_mapping *mapping;
1142        struct uvc_menu_info *menu;
1143        unsigned int i;
1144        int ret;
1145
1146        ctrl = uvc_find_control(chain, xctrl->id, &mapping);
1147        if (ctrl == NULL || (ctrl->info.flags & UVC_CTRL_FLAG_GET_CUR) == 0)
1148                return -EINVAL;
1149
1150        if (!ctrl->loaded) {
1151                ret = uvc_query_ctrl(chain->dev, UVC_GET_CUR, ctrl->entity->id,
1152                                chain->dev->intfnum, ctrl->info.selector,
1153                                uvc_ctrl_data(ctrl, UVC_CTRL_DATA_CURRENT),
1154                                ctrl->info.size);
1155                if (ret < 0)
1156                        return ret;
1157
1158                ctrl->loaded = 1;
1159        }
1160
1161        xctrl->value = mapping->get(mapping, UVC_GET_CUR,
1162                uvc_ctrl_data(ctrl, UVC_CTRL_DATA_CURRENT));
1163
1164        if (mapping->v4l2_type == V4L2_CTRL_TYPE_MENU) {
1165                menu = mapping->menu_info;
1166                for (i = 0; i < mapping->menu_count; ++i, ++menu) {
1167                        if (menu->value == xctrl->value) {
1168                                xctrl->value = i;
1169                                break;
1170                        }
1171                }
1172        }
1173
1174        return 0;
1175}
1176
1177int uvc_ctrl_set(struct uvc_video_chain *chain,
1178        struct v4l2_ext_control *xctrl)
1179{
1180        struct uvc_control *ctrl;
1181        struct uvc_control_mapping *mapping;
1182        s32 value;
1183        u32 step;
1184        s32 min;
1185        s32 max;
1186        int ret;
1187
1188        ctrl = uvc_find_control(chain, xctrl->id, &mapping);
1189        if (ctrl == NULL || (ctrl->info.flags & UVC_CTRL_FLAG_SET_CUR) == 0)
1190                return -EINVAL;
1191
1192        /* Clamp out of range values. */
1193        switch (mapping->v4l2_type) {
1194        case V4L2_CTRL_TYPE_INTEGER:
1195                if (!ctrl->cached) {
1196                        ret = uvc_ctrl_populate_cache(chain, ctrl);
1197                        if (ret < 0)
1198                                return ret;
1199                }
1200
1201                min = mapping->get(mapping, UVC_GET_MIN,
1202                                   uvc_ctrl_data(ctrl, UVC_CTRL_DATA_MIN));
1203                max = mapping->get(mapping, UVC_GET_MAX,
1204                                   uvc_ctrl_data(ctrl, UVC_CTRL_DATA_MAX));
1205                step = mapping->get(mapping, UVC_GET_RES,
1206                                    uvc_ctrl_data(ctrl, UVC_CTRL_DATA_RES));
1207                if (step == 0)
1208                        step = 1;
1209
1210                xctrl->value = min + (xctrl->value - min + step/2) / step * step;
1211                xctrl->value = clamp(xctrl->value, min, max);
1212                value = xctrl->value;
1213                break;
1214
1215        case V4L2_CTRL_TYPE_BOOLEAN:
1216                xctrl->value = clamp(xctrl->value, 0, 1);
1217                value = xctrl->value;
1218                break;
1219
1220        case V4L2_CTRL_TYPE_MENU:
1221                if (xctrl->value < 0 || xctrl->value >= mapping->menu_count)
1222                        return -ERANGE;
1223                value = mapping->menu_info[xctrl->value].value;
1224
1225                /* Valid menu indices are reported by the GET_RES request for
1226                 * UVC controls that support it.
1227                 */
1228                if (ctrl->info.flags & UVC_CTRL_FLAG_GET_RES) {
1229                        if (!ctrl->cached) {
1230                                ret = uvc_ctrl_populate_cache(chain, ctrl);
1231                                if (ret < 0)
1232                                        return ret;
1233                        }
1234
1235                        step = mapping->get(mapping, UVC_GET_RES,
1236                                        uvc_ctrl_data(ctrl, UVC_CTRL_DATA_RES));
1237                        if (!(step & value))
1238                                return -ERANGE;
1239                }
1240
1241                break;
1242
1243        default:
1244                value = xctrl->value;
1245                break;
1246        }
1247
1248        /* If the mapping doesn't span the whole UVC control, the current value
1249         * needs to be loaded from the device to perform the read-modify-write
1250         * operation.
1251         */
1252        if (!ctrl->loaded && (ctrl->info.size * 8) != mapping->size) {
1253                if ((ctrl->info.flags & UVC_CTRL_FLAG_GET_CUR) == 0) {
1254                        memset(uvc_ctrl_data(ctrl, UVC_CTRL_DATA_CURRENT),
1255                                0, ctrl->info.size);
1256                } else {
1257                        ret = uvc_query_ctrl(chain->dev, UVC_GET_CUR,
1258                                ctrl->entity->id, chain->dev->intfnum,
1259                                ctrl->info.selector,
1260                                uvc_ctrl_data(ctrl, UVC_CTRL_DATA_CURRENT),
1261                                ctrl->info.size);
1262                        if (ret < 0)
1263                                return ret;
1264                }
1265
1266                ctrl->loaded = 1;
1267        }
1268
1269        /* Backup the current value in case we need to rollback later. */
1270        if (!ctrl->dirty) {
1271                memcpy(uvc_ctrl_data(ctrl, UVC_CTRL_DATA_BACKUP),
1272                       uvc_ctrl_data(ctrl, UVC_CTRL_DATA_CURRENT),
1273                       ctrl->info.size);
1274        }
1275
1276        mapping->set(mapping, value,
1277                uvc_ctrl_data(ctrl, UVC_CTRL_DATA_CURRENT));
1278
1279        ctrl->dirty = 1;
1280        ctrl->modified = 1;
1281        return 0;
1282}
1283
1284/* --------------------------------------------------------------------------
1285 * Dynamic controls
1286 */
1287
1288static void uvc_ctrl_fixup_xu_info(struct uvc_device *dev,
1289        const struct uvc_control *ctrl, struct uvc_control_info *info)
1290{
1291        struct uvc_ctrl_fixup {
1292                struct usb_device_id id;
1293                u8 entity;
1294                u8 selector;
1295                u8 flags;
1296        };
1297
1298        static const struct uvc_ctrl_fixup fixups[] = {
1299                { { USB_DEVICE(0x046d, 0x08c2) }, 9, 1,
1300                        UVC_CTRL_FLAG_GET_MIN | UVC_CTRL_FLAG_GET_MAX |
1301                        UVC_CTRL_FLAG_GET_DEF | UVC_CTRL_FLAG_SET_CUR |
1302                        UVC_CTRL_FLAG_AUTO_UPDATE },
1303                { { USB_DEVICE(0x046d, 0x08cc) }, 9, 1,
1304                        UVC_CTRL_FLAG_GET_MIN | UVC_CTRL_FLAG_GET_MAX |
1305                        UVC_CTRL_FLAG_GET_DEF | UVC_CTRL_FLAG_SET_CUR |
1306                        UVC_CTRL_FLAG_AUTO_UPDATE },
1307                { { USB_DEVICE(0x046d, 0x0994) }, 9, 1,
1308                        UVC_CTRL_FLAG_GET_MIN | UVC_CTRL_FLAG_GET_MAX |
1309                        UVC_CTRL_FLAG_GET_DEF | UVC_CTRL_FLAG_SET_CUR |
1310                        UVC_CTRL_FLAG_AUTO_UPDATE },
1311        };
1312
1313        unsigned int i;
1314
1315        for (i = 0; i < ARRAY_SIZE(fixups); ++i) {
1316                if (!usb_match_one_id(dev->intf, &fixups[i].id))
1317                        continue;
1318
1319                if (fixups[i].entity == ctrl->entity->id &&
1320                    fixups[i].selector == info->selector) {
1321                        info->flags = fixups[i].flags;
1322                        return;
1323                }
1324        }
1325}
1326
1327/*
1328 * Query control information (size and flags) for XU controls.
1329 */
1330static int uvc_ctrl_fill_xu_info(struct uvc_device *dev,
1331        const struct uvc_control *ctrl, struct uvc_control_info *info)
1332{
1333        u8 *data;
1334        int ret;
1335
1336        data = kmalloc(2, GFP_KERNEL);
1337        if (data == NULL)
1338                return -ENOMEM;
1339
1340        memcpy(info->entity, ctrl->entity->extension.guidExtensionCode,
1341               sizeof(info->entity));
1342        info->index = ctrl->index;
1343        info->selector = ctrl->index + 1;
1344
1345        /* Query and verify the control length (GET_LEN) */
1346        ret = uvc_query_ctrl(dev, UVC_GET_LEN, ctrl->entity->id, dev->intfnum,
1347                             info->selector, data, 2);
1348        if (ret < 0) {
1349                uvc_trace(UVC_TRACE_CONTROL,
1350                          "GET_LEN failed on control %pUl/%u (%d).\n",
1351                           info->entity, info->selector, ret);
1352                goto done;
1353        }
1354
1355        info->size = le16_to_cpup((__le16 *)data);
1356
1357        /* Query the control information (GET_INFO) */
1358        ret = uvc_query_ctrl(dev, UVC_GET_INFO, ctrl->entity->id, dev->intfnum,
1359                             info->selector, data, 1);
1360        if (ret < 0) {
1361                uvc_trace(UVC_TRACE_CONTROL,
1362                          "GET_INFO failed on control %pUl/%u (%d).\n",
1363                          info->entity, info->selector, ret);
1364                goto done;
1365        }
1366
1367        info->flags = UVC_CTRL_FLAG_GET_MIN | UVC_CTRL_FLAG_GET_MAX
1368                    | UVC_CTRL_FLAG_GET_RES | UVC_CTRL_FLAG_GET_DEF
1369                    | (data[0] & UVC_CONTROL_CAP_GET ?
1370                       UVC_CTRL_FLAG_GET_CUR : 0)
1371                    | (data[0] & UVC_CONTROL_CAP_SET ?
1372                       UVC_CTRL_FLAG_SET_CUR : 0)
1373                    | (data[0] & UVC_CONTROL_CAP_AUTOUPDATE ?
1374                       UVC_CTRL_FLAG_AUTO_UPDATE : 0);
1375
1376        uvc_ctrl_fixup_xu_info(dev, ctrl, info);
1377
1378        uvc_trace(UVC_TRACE_CONTROL, "XU control %pUl/%u queried: len %u, "
1379                  "flags { get %u set %u auto %u }.\n",
1380                  info->entity, info->selector, info->size,
1381                  (info->flags & UVC_CTRL_FLAG_GET_CUR) ? 1 : 0,
1382                  (info->flags & UVC_CTRL_FLAG_SET_CUR) ? 1 : 0,
1383                  (info->flags & UVC_CTRL_FLAG_AUTO_UPDATE) ? 1 : 0);
1384
1385done:
1386        kfree(data);
1387        return ret;
1388}
1389
1390static int uvc_ctrl_add_info(struct uvc_device *dev, struct uvc_control *ctrl,
1391        const struct uvc_control_info *info);
1392
1393static int uvc_ctrl_init_xu_ctrl(struct uvc_device *dev,
1394        struct uvc_control *ctrl)
1395{
1396        struct uvc_control_info info;
1397        int ret;
1398
1399        if (ctrl->initialized)
1400                return 0;
1401
1402        ret = uvc_ctrl_fill_xu_info(dev, ctrl, &info);
1403        if (ret < 0)
1404                return ret;
1405
1406        ret = uvc_ctrl_add_info(dev, ctrl, &info);
1407        if (ret < 0)
1408                uvc_trace(UVC_TRACE_CONTROL, "Failed to initialize control "
1409                          "%pUl/%u on device %s entity %u\n", info.entity,
1410                          info.selector, dev->udev->devpath, ctrl->entity->id);
1411
1412        return ret;
1413}
1414
1415int uvc_xu_ctrl_query(struct uvc_video_chain *chain,
1416        struct uvc_xu_control_query *xqry)
1417{
1418        struct uvc_entity *entity;
1419        struct uvc_control *ctrl;
1420        unsigned int i, found = 0;
1421        __u32 reqflags;
1422        __u16 size;
1423        __u8 *data = NULL;
1424        int ret;
1425
1426        /* Find the extension unit. */
1427        list_for_each_entry(entity, &chain->entities, chain) {
1428                if (UVC_ENTITY_TYPE(entity) == UVC_VC_EXTENSION_UNIT &&
1429                    entity->id == xqry->unit)
1430                        break;
1431        }
1432
1433        if (entity->id != xqry->unit) {
1434                uvc_trace(UVC_TRACE_CONTROL, "Extension unit %u not found.\n",
1435                        xqry->unit);
1436                return -ENOENT;
1437        }
1438
1439        /* Find the control and perform delayed initialization if needed. */
1440        for (i = 0; i < entity->ncontrols; ++i) {
1441                ctrl = &entity->controls[i];
1442                if (ctrl->index == xqry->selector - 1) {
1443                        found = 1;
1444                        break;
1445                }
1446        }
1447
1448        if (!found) {
1449                uvc_trace(UVC_TRACE_CONTROL, "Control %pUl/%u not found.\n",
1450                        entity->extension.guidExtensionCode, xqry->selector);
1451                return -ENOENT;
1452        }
1453
1454        if (mutex_lock_interruptible(&chain->ctrl_mutex))
1455                return -ERESTARTSYS;
1456
1457        ret = uvc_ctrl_init_xu_ctrl(chain->dev, ctrl);
1458        if (ret < 0) {
1459                ret = -ENOENT;
1460                goto done;
1461        }
1462
1463        /* Validate the required buffer size and flags for the request */
1464        reqflags = 0;
1465        size = ctrl->info.size;
1466
1467        switch (xqry->query) {
1468        case UVC_GET_CUR:
1469                reqflags = UVC_CTRL_FLAG_GET_CUR;
1470                break;
1471        case UVC_GET_MIN:
1472                reqflags = UVC_CTRL_FLAG_GET_MIN;
1473                break;
1474        case UVC_GET_MAX:
1475                reqflags = UVC_CTRL_FLAG_GET_MAX;
1476                break;
1477        case UVC_GET_DEF:
1478                reqflags = UVC_CTRL_FLAG_GET_DEF;
1479                break;
1480        case UVC_GET_RES:
1481                reqflags = UVC_CTRL_FLAG_GET_RES;
1482                break;
1483        case UVC_SET_CUR:
1484                reqflags = UVC_CTRL_FLAG_SET_CUR;
1485                break;
1486        case UVC_GET_LEN:
1487                size = 2;
1488                break;
1489        case UVC_GET_INFO:
1490                size = 1;
1491                break;
1492        default:
1493                ret = -EINVAL;
1494                goto done;
1495        }
1496
1497        if (size != xqry->size) {
1498                ret = -ENOBUFS;
1499                goto done;
1500        }
1501
1502        if (reqflags && !(ctrl->info.flags & reqflags)) {
1503                ret = -EBADRQC;
1504                goto done;
1505        }
1506
1507        data = kmalloc(size, GFP_KERNEL);
1508        if (data == NULL) {
1509                ret = -ENOMEM;
1510                goto done;
1511        }
1512
1513        if (xqry->query == UVC_SET_CUR &&
1514            copy_from_user(data, xqry->data, size)) {
1515                ret = -EFAULT;
1516                goto done;
1517        }
1518
1519        ret = uvc_query_ctrl(chain->dev, xqry->query, xqry->unit,
1520                             chain->dev->intfnum, xqry->selector, data, size);
1521        if (ret < 0)
1522                goto done;
1523
1524        if (xqry->query != UVC_SET_CUR &&
1525            copy_to_user(xqry->data, data, size))
1526                ret = -EFAULT;
1527done:
1528        kfree(data);
1529        mutex_unlock(&chain->ctrl_mutex);
1530        return ret;
1531}
1532
1533/* --------------------------------------------------------------------------
1534 * Suspend/resume
1535 */
1536
1537/*
1538 * Restore control values after resume, skipping controls that haven't been
1539 * changed.
1540 *
1541 * TODO
1542 * - Don't restore modified controls that are back to their default value.
1543 * - Handle restore order (Auto-Exposure Mode should be restored before
1544 *   Exposure Time).
1545 */
1546int uvc_ctrl_resume_device(struct uvc_device *dev)
1547{
1548        struct uvc_control *ctrl;
1549        struct uvc_entity *entity;
1550        unsigned int i;
1551        int ret;
1552
1553        /* Walk the entities list and restore controls when possible. */
1554        list_for_each_entry(entity, &dev->entities, list) {
1555
1556                for (i = 0; i < entity->ncontrols; ++i) {
1557                        ctrl = &entity->controls[i];
1558
1559                        if (!ctrl->initialized || !ctrl->modified ||
1560                            (ctrl->info.flags & UVC_CTRL_FLAG_RESTORE) == 0)
1561                                continue;
1562
1563                        printk(KERN_INFO "restoring control %pUl/%u/%u\n",
1564                                ctrl->info.entity, ctrl->info.index,
1565                                ctrl->info.selector);
1566                        ctrl->dirty = 1;
1567                }
1568
1569                ret = uvc_ctrl_commit_entity(dev, entity, 0);
1570                if (ret < 0)
1571                        return ret;
1572        }
1573
1574        return 0;
1575}
1576
1577/* --------------------------------------------------------------------------
1578 * Control and mapping handling
1579 */
1580
1581/*
1582 * Add control information to a given control.
1583 */
1584static int uvc_ctrl_add_info(struct uvc_device *dev, struct uvc_control *ctrl,
1585        const struct uvc_control_info *info)
1586{
1587        int ret = 0;
1588
1589        memcpy(&ctrl->info, info, sizeof(*info));
1590        INIT_LIST_HEAD(&ctrl->info.mappings);
1591
1592        /* Allocate an array to save control values (cur, def, max, etc.) */
1593        ctrl->uvc_data = kzalloc(ctrl->info.size * UVC_CTRL_DATA_LAST + 1,
1594                                 GFP_KERNEL);
1595        if (ctrl->uvc_data == NULL) {
1596                ret = -ENOMEM;
1597                goto done;
1598        }
1599
1600        ctrl->initialized = 1;
1601
1602        uvc_trace(UVC_TRACE_CONTROL, "Added control %pUl/%u to device %s "
1603                "entity %u\n", ctrl->info.entity, ctrl->info.selector,
1604                dev->udev->devpath, ctrl->entity->id);
1605
1606done:
1607        if (ret < 0)
1608                kfree(ctrl->uvc_data);
1609        return ret;
1610}
1611
1612/*
1613 * Add a control mapping to a given control.
1614 */
1615static int __uvc_ctrl_add_mapping(struct uvc_device *dev,
1616        struct uvc_control *ctrl, const struct uvc_control_mapping *mapping)
1617{
1618        struct uvc_control_mapping *map;
1619        unsigned int size;
1620
1621        /* Most mappings come from static kernel data and need to be duplicated.
1622         * Mappings that come from userspace will be unnecessarily duplicated,
1623         * this could be optimized.
1624         */
1625        map = kmemdup(mapping, sizeof(*mapping), GFP_KERNEL);
1626        if (map == NULL)
1627                return -ENOMEM;
1628
1629        size = sizeof(*mapping->menu_info) * mapping->menu_count;
1630        map->menu_info = kmemdup(mapping->menu_info, size, GFP_KERNEL);
1631        if (map->menu_info == NULL) {
1632                kfree(map);
1633                return -ENOMEM;
1634        }
1635
1636        if (map->get == NULL)
1637                map->get = uvc_get_le_value;
1638        if (map->set == NULL)
1639                map->set = uvc_set_le_value;
1640
1641        map->ctrl = &ctrl->info;
1642        list_add_tail(&map->list, &ctrl->info.mappings);
1643        uvc_trace(UVC_TRACE_CONTROL,
1644                "Adding mapping '%s' to control %pUl/%u.\n",
1645                map->name, ctrl->info.entity, ctrl->info.selector);
1646
1647        return 0;
1648}
1649
1650int uvc_ctrl_add_mapping(struct uvc_video_chain *chain,
1651        const struct uvc_control_mapping *mapping)
1652{
1653        struct uvc_device *dev = chain->dev;
1654        struct uvc_control_mapping *map;
1655        struct uvc_entity *entity;
1656        struct uvc_control *ctrl;
1657        int found = 0;
1658        int ret;
1659
1660        if (mapping->id & ~V4L2_CTRL_ID_MASK) {
1661                uvc_trace(UVC_TRACE_CONTROL, "Can't add mapping '%s', control "
1662                        "id 0x%08x is invalid.\n", mapping->name,
1663                        mapping->id);
1664                return -EINVAL;
1665        }
1666
1667        /* Search for the matching (GUID/CS) control on the current chain */
1668        list_for_each_entry(entity, &chain->entities, chain) {
1669                unsigned int i;
1670
1671                if (UVC_ENTITY_TYPE(entity) != UVC_VC_EXTENSION_UNIT ||
1672                    !uvc_entity_match_guid(entity, mapping->entity))
1673                        continue;
1674
1675                for (i = 0; i < entity->ncontrols; ++i) {
1676                        ctrl = &entity->controls[i];
1677                        if (ctrl->index == mapping->selector - 1) {
1678                                found = 1;
1679                                break;
1680                        }
1681                }
1682
1683                if (found)
1684                        break;
1685        }
1686        if (!found)
1687                return -ENOENT;
1688
1689        if (mutex_lock_interruptible(&chain->ctrl_mutex))
1690                return -ERESTARTSYS;
1691
1692        /* Perform delayed initialization of XU controls */
1693        ret = uvc_ctrl_init_xu_ctrl(dev, ctrl);
1694        if (ret < 0) {
1695                ret = -ENOENT;
1696                goto done;
1697        }
1698
1699        list_for_each_entry(map, &ctrl->info.mappings, list) {
1700                if (mapping->id == map->id) {
1701                        uvc_trace(UVC_TRACE_CONTROL, "Can't add mapping '%s', "
1702                                "control id 0x%08x already exists.\n",
1703                                mapping->name, mapping->id);
1704                        ret = -EEXIST;
1705                        goto done;
1706                }
1707        }
1708
1709        /* Prevent excess memory consumption */
1710        if (atomic_inc_return(&dev->nmappings) > UVC_MAX_CONTROL_MAPPINGS) {
1711                atomic_dec(&dev->nmappings);
1712                uvc_trace(UVC_TRACE_CONTROL, "Can't add mapping '%s', maximum "
1713                        "mappings count (%u) exceeded.\n", mapping->name,
1714                        UVC_MAX_CONTROL_MAPPINGS);
1715                ret = -ENOMEM;
1716                goto done;
1717        }
1718
1719        ret = __uvc_ctrl_add_mapping(dev, ctrl, mapping);
1720        if (ret < 0)
1721                atomic_dec(&dev->nmappings);
1722
1723done:
1724        mutex_unlock(&chain->ctrl_mutex);
1725        return ret;
1726}
1727
1728/*
1729 * Prune an entity of its bogus controls using a blacklist. Bogus controls
1730 * are currently the ones that crash the camera or unconditionally return an
1731 * error when queried.
1732 */
1733static void uvc_ctrl_prune_entity(struct uvc_device *dev,
1734        struct uvc_entity *entity)
1735{
1736        struct uvc_ctrl_blacklist {
1737                struct usb_device_id id;
1738                u8 index;
1739        };
1740
1741        static const struct uvc_ctrl_blacklist processing_blacklist[] = {
1742                { { USB_DEVICE(0x13d3, 0x509b) }, 9 }, /* Gain */
1743                { { USB_DEVICE(0x1c4f, 0x3000) }, 6 }, /* WB Temperature */
1744                { { USB_DEVICE(0x5986, 0x0241) }, 2 }, /* Hue */
1745        };
1746        static const struct uvc_ctrl_blacklist camera_blacklist[] = {
1747                { { USB_DEVICE(0x06f8, 0x3005) }, 9 }, /* Zoom, Absolute */
1748        };
1749
1750        const struct uvc_ctrl_blacklist *blacklist;
1751        unsigned int size;
1752        unsigned int count;
1753        unsigned int i;
1754        u8 *controls;
1755
1756        switch (UVC_ENTITY_TYPE(entity)) {
1757        case UVC_VC_PROCESSING_UNIT:
1758                blacklist = processing_blacklist;
1759                count = ARRAY_SIZE(processing_blacklist);
1760                controls = entity->processing.bmControls;
1761                size = entity->processing.bControlSize;
1762                break;
1763
1764        case UVC_ITT_CAMERA:
1765                blacklist = camera_blacklist;
1766                count = ARRAY_SIZE(camera_blacklist);
1767                controls = entity->camera.bmControls;
1768                size = entity->camera.bControlSize;
1769                break;
1770
1771        default:
1772                return;
1773        }
1774
1775        for (i = 0; i < count; ++i) {
1776                if (!usb_match_one_id(dev->intf, &blacklist[i].id))
1777                        continue;
1778
1779                if (blacklist[i].index >= 8 * size ||
1780                    !uvc_test_bit(controls, blacklist[i].index))
1781                        continue;
1782
1783                uvc_trace(UVC_TRACE_CONTROL, "%u/%u control is black listed, "
1784                        "removing it.\n", entity->id, blacklist[i].index);
1785
1786                uvc_clear_bit(controls, blacklist[i].index);
1787        }
1788}
1789
1790/*
1791 * Add control information and hardcoded stock control mappings to the given
1792 * device.
1793 */
1794static void uvc_ctrl_init_ctrl(struct uvc_device *dev, struct uvc_control *ctrl)
1795{
1796        const struct uvc_control_info *info = uvc_ctrls;
1797        const struct uvc_control_info *iend = info + ARRAY_SIZE(uvc_ctrls);
1798        const struct uvc_control_mapping *mapping = uvc_ctrl_mappings;
1799        const struct uvc_control_mapping *mend =
1800                mapping + ARRAY_SIZE(uvc_ctrl_mappings);
1801
1802        /* XU controls initialization requires querying the device for control
1803         * information. As some buggy UVC devices will crash when queried
1804         * repeatedly in a tight loop, delay XU controls initialization until
1805         * first use.
1806         */
1807        if (UVC_ENTITY_TYPE(ctrl->entity) == UVC_VC_EXTENSION_UNIT)
1808                return;
1809
1810        for (; info < iend; ++info) {
1811                if (uvc_entity_match_guid(ctrl->entity, info->entity) &&
1812                    ctrl->index == info->index) {
1813                        uvc_ctrl_add_info(dev, ctrl, info);
1814                        break;
1815                 }
1816        }
1817
1818        if (!ctrl->initialized)
1819                return;
1820
1821        for (; mapping < mend; ++mapping) {
1822                if (uvc_entity_match_guid(ctrl->entity, mapping->entity) &&
1823                    ctrl->info.selector == mapping->selector)
1824                        __uvc_ctrl_add_mapping(dev, ctrl, mapping);
1825        }
1826}
1827
1828/*
1829 * Initialize device controls.
1830 */
1831int uvc_ctrl_init_device(struct uvc_device *dev)
1832{
1833        struct uvc_entity *entity;
1834        unsigned int i;
1835
1836        /* Walk the entities list and instantiate controls */
1837        list_for_each_entry(entity, &dev->entities, list) {
1838                struct uvc_control *ctrl;
1839                unsigned int bControlSize = 0, ncontrols = 0;
1840                __u8 *bmControls = NULL;
1841
1842                if (UVC_ENTITY_TYPE(entity) == UVC_VC_EXTENSION_UNIT) {
1843                        bmControls = entity->extension.bmControls;
1844                        bControlSize = entity->extension.bControlSize;
1845                } else if (UVC_ENTITY_TYPE(entity) == UVC_VC_PROCESSING_UNIT) {
1846                        bmControls = entity->processing.bmControls;
1847                        bControlSize = entity->processing.bControlSize;
1848                } else if (UVC_ENTITY_TYPE(entity) == UVC_ITT_CAMERA) {
1849                        bmControls = entity->camera.bmControls;
1850                        bControlSize = entity->camera.bControlSize;
1851                }
1852
1853                /* Remove bogus/blacklisted controls */
1854                uvc_ctrl_prune_entity(dev, entity);
1855
1856                /* Count supported controls and allocate the controls array */
1857                for (i = 0; i < bControlSize; ++i)
1858                        ncontrols += hweight8(bmControls[i]);
1859                if (ncontrols == 0)
1860                        continue;
1861
1862                entity->controls = kzalloc(ncontrols * sizeof(*ctrl),
1863                                           GFP_KERNEL);
1864                if (entity->controls == NULL)
1865                        return -ENOMEM;
1866                entity->ncontrols = ncontrols;
1867
1868                /* Initialize all supported controls */
1869                ctrl = entity->controls;
1870                for (i = 0; i < bControlSize * 8; ++i) {
1871                        if (uvc_test_bit(bmControls, i) == 0)
1872                                continue;
1873
1874                        ctrl->entity = entity;
1875                        ctrl->index = i;
1876
1877                        uvc_ctrl_init_ctrl(dev, ctrl);
1878                        ctrl++;
1879                }
1880        }
1881
1882        return 0;
1883}
1884
1885/*
1886 * Cleanup device controls.
1887 */
1888static void uvc_ctrl_cleanup_mappings(struct uvc_device *dev,
1889        struct uvc_control *ctrl)
1890{
1891        struct uvc_control_mapping *mapping, *nm;
1892
1893        list_for_each_entry_safe(mapping, nm, &ctrl->info.mappings, list) {
1894                list_del(&mapping->list);
1895                kfree(mapping->menu_info);
1896                kfree(mapping);
1897        }
1898}
1899
1900void uvc_ctrl_cleanup_device(struct uvc_device *dev)
1901{
1902        struct uvc_entity *entity;
1903        unsigned int i;
1904
1905        /* Free controls and control mappings for all entities. */
1906        list_for_each_entry(entity, &dev->entities, list) {
1907                for (i = 0; i < entity->ncontrols; ++i) {
1908                        struct uvc_control *ctrl = &entity->controls[i];
1909
1910                        if (!ctrl->initialized)
1911                                continue;
1912
1913                        uvc_ctrl_cleanup_mappings(dev, ctrl);
1914                        kfree(ctrl->uvc_data);
1915                }
1916
1917                kfree(entity->controls);
1918        }
1919}
1920