diff options
Diffstat (limited to 'drivers/media/video/v4l2-common.c')
-rw-r--r-- | drivers/media/video/v4l2-common.c | 265 |
1 files changed, 104 insertions, 161 deletions
diff --git a/drivers/media/video/v4l2-common.c b/drivers/media/video/v4l2-common.c index b8f2be8d5c0e..1da8cb836cb6 100644 --- a/drivers/media/video/v4l2-common.c +++ b/drivers/media/video/v4l2-common.c | |||
@@ -334,6 +334,12 @@ const char **v4l2_ctrl_get_menu(u32 id) | |||
334 | "Aperture Priority Mode", | 334 | "Aperture Priority Mode", |
335 | NULL | 335 | NULL |
336 | }; | 336 | }; |
337 | static const char *colorfx[] = { | ||
338 | "None", | ||
339 | "Black & White", | ||
340 | "Sepia", | ||
341 | NULL | ||
342 | }; | ||
337 | 343 | ||
338 | switch (id) { | 344 | switch (id) { |
339 | case V4L2_CID_MPEG_AUDIO_SAMPLING_FREQ: | 345 | case V4L2_CID_MPEG_AUDIO_SAMPLING_FREQ: |
@@ -370,6 +376,8 @@ const char **v4l2_ctrl_get_menu(u32 id) | |||
370 | return camera_power_line_frequency; | 376 | return camera_power_line_frequency; |
371 | case V4L2_CID_EXPOSURE_AUTO: | 377 | case V4L2_CID_EXPOSURE_AUTO: |
372 | return camera_exposure_auto; | 378 | return camera_exposure_auto; |
379 | case V4L2_CID_COLORFX: | ||
380 | return colorfx; | ||
373 | default: | 381 | default: |
374 | return NULL; | 382 | return NULL; |
375 | } | 383 | } |
@@ -382,16 +390,16 @@ const char *v4l2_ctrl_get_name(u32 id) | |||
382 | switch (id) { | 390 | switch (id) { |
383 | /* USER controls */ | 391 | /* USER controls */ |
384 | case V4L2_CID_USER_CLASS: return "User Controls"; | 392 | case V4L2_CID_USER_CLASS: return "User Controls"; |
393 | case V4L2_CID_BRIGHTNESS: return "Brightness"; | ||
394 | case V4L2_CID_CONTRAST: return "Contrast"; | ||
395 | case V4L2_CID_SATURATION: return "Saturation"; | ||
396 | case V4L2_CID_HUE: return "Hue"; | ||
385 | case V4L2_CID_AUDIO_VOLUME: return "Volume"; | 397 | case V4L2_CID_AUDIO_VOLUME: return "Volume"; |
386 | case V4L2_CID_AUDIO_MUTE: return "Mute"; | ||
387 | case V4L2_CID_AUDIO_BALANCE: return "Balance"; | 398 | case V4L2_CID_AUDIO_BALANCE: return "Balance"; |
388 | case V4L2_CID_AUDIO_BASS: return "Bass"; | 399 | case V4L2_CID_AUDIO_BASS: return "Bass"; |
389 | case V4L2_CID_AUDIO_TREBLE: return "Treble"; | 400 | case V4L2_CID_AUDIO_TREBLE: return "Treble"; |
401 | case V4L2_CID_AUDIO_MUTE: return "Mute"; | ||
390 | case V4L2_CID_AUDIO_LOUDNESS: return "Loudness"; | 402 | case V4L2_CID_AUDIO_LOUDNESS: return "Loudness"; |
391 | case V4L2_CID_BRIGHTNESS: return "Brightness"; | ||
392 | case V4L2_CID_CONTRAST: return "Contrast"; | ||
393 | case V4L2_CID_SATURATION: return "Saturation"; | ||
394 | case V4L2_CID_HUE: return "Hue"; | ||
395 | case V4L2_CID_BLACK_LEVEL: return "Black Level"; | 403 | case V4L2_CID_BLACK_LEVEL: return "Black Level"; |
396 | case V4L2_CID_AUTO_WHITE_BALANCE: return "White Balance, Automatic"; | 404 | case V4L2_CID_AUTO_WHITE_BALANCE: return "White Balance, Automatic"; |
397 | case V4L2_CID_DO_WHITE_BALANCE: return "Do White Balance"; | 405 | case V4L2_CID_DO_WHITE_BALANCE: return "Do White Balance"; |
@@ -412,6 +420,7 @@ const char *v4l2_ctrl_get_name(u32 id) | |||
412 | case V4L2_CID_BACKLIGHT_COMPENSATION: return "Backlight Compensation"; | 420 | case V4L2_CID_BACKLIGHT_COMPENSATION: return "Backlight Compensation"; |
413 | case V4L2_CID_CHROMA_AGC: return "Chroma AGC"; | 421 | case V4L2_CID_CHROMA_AGC: return "Chroma AGC"; |
414 | case V4L2_CID_COLOR_KILLER: return "Color Killer"; | 422 | case V4L2_CID_COLOR_KILLER: return "Color Killer"; |
423 | case V4L2_CID_COLORFX: return "Color Effects"; | ||
415 | 424 | ||
416 | /* MPEG controls */ | 425 | /* MPEG controls */ |
417 | case V4L2_CID_MPEG_CLASS: return "MPEG Encoder Controls"; | 426 | case V4L2_CID_MPEG_CLASS: return "MPEG Encoder Controls"; |
@@ -490,16 +499,25 @@ int v4l2_ctrl_query_fill(struct v4l2_queryctrl *qctrl, s32 min, s32 max, s32 ste | |||
490 | case V4L2_CID_HFLIP: | 499 | case V4L2_CID_HFLIP: |
491 | case V4L2_CID_VFLIP: | 500 | case V4L2_CID_VFLIP: |
492 | case V4L2_CID_HUE_AUTO: | 501 | case V4L2_CID_HUE_AUTO: |
502 | case V4L2_CID_CHROMA_AGC: | ||
503 | case V4L2_CID_COLOR_KILLER: | ||
493 | case V4L2_CID_MPEG_AUDIO_MUTE: | 504 | case V4L2_CID_MPEG_AUDIO_MUTE: |
494 | case V4L2_CID_MPEG_VIDEO_MUTE: | 505 | case V4L2_CID_MPEG_VIDEO_MUTE: |
495 | case V4L2_CID_MPEG_VIDEO_GOP_CLOSURE: | 506 | case V4L2_CID_MPEG_VIDEO_GOP_CLOSURE: |
496 | case V4L2_CID_MPEG_VIDEO_PULLDOWN: | 507 | case V4L2_CID_MPEG_VIDEO_PULLDOWN: |
497 | case V4L2_CID_EXPOSURE_AUTO_PRIORITY: | 508 | case V4L2_CID_EXPOSURE_AUTO_PRIORITY: |
509 | case V4L2_CID_FOCUS_AUTO: | ||
498 | case V4L2_CID_PRIVACY: | 510 | case V4L2_CID_PRIVACY: |
499 | qctrl->type = V4L2_CTRL_TYPE_BOOLEAN; | 511 | qctrl->type = V4L2_CTRL_TYPE_BOOLEAN; |
500 | min = 0; | 512 | min = 0; |
501 | max = step = 1; | 513 | max = step = 1; |
502 | break; | 514 | break; |
515 | case V4L2_CID_PAN_RESET: | ||
516 | case V4L2_CID_TILT_RESET: | ||
517 | qctrl->type = V4L2_CTRL_TYPE_BUTTON; | ||
518 | qctrl->flags |= V4L2_CTRL_FLAG_WRITE_ONLY; | ||
519 | min = max = step = def = 0; | ||
520 | break; | ||
503 | case V4L2_CID_POWER_LINE_FREQUENCY: | 521 | case V4L2_CID_POWER_LINE_FREQUENCY: |
504 | case V4L2_CID_MPEG_AUDIO_SAMPLING_FREQ: | 522 | case V4L2_CID_MPEG_AUDIO_SAMPLING_FREQ: |
505 | case V4L2_CID_MPEG_AUDIO_ENCODING: | 523 | case V4L2_CID_MPEG_AUDIO_ENCODING: |
@@ -517,6 +535,7 @@ int v4l2_ctrl_query_fill(struct v4l2_queryctrl *qctrl, s32 min, s32 max, s32 ste | |||
517 | case V4L2_CID_MPEG_STREAM_TYPE: | 535 | case V4L2_CID_MPEG_STREAM_TYPE: |
518 | case V4L2_CID_MPEG_STREAM_VBI_FMT: | 536 | case V4L2_CID_MPEG_STREAM_VBI_FMT: |
519 | case V4L2_CID_EXPOSURE_AUTO: | 537 | case V4L2_CID_EXPOSURE_AUTO: |
538 | case V4L2_CID_COLORFX: | ||
520 | qctrl->type = V4L2_CTRL_TYPE_MENU; | 539 | qctrl->type = V4L2_CTRL_TYPE_MENU; |
521 | step = 1; | 540 | step = 1; |
522 | break; | 541 | break; |
@@ -547,161 +566,29 @@ int v4l2_ctrl_query_fill(struct v4l2_queryctrl *qctrl, s32 min, s32 max, s32 ste | |||
547 | case V4L2_CID_CONTRAST: | 566 | case V4L2_CID_CONTRAST: |
548 | case V4L2_CID_SATURATION: | 567 | case V4L2_CID_SATURATION: |
549 | case V4L2_CID_HUE: | 568 | case V4L2_CID_HUE: |
569 | case V4L2_CID_RED_BALANCE: | ||
570 | case V4L2_CID_BLUE_BALANCE: | ||
571 | case V4L2_CID_GAMMA: | ||
572 | case V4L2_CID_SHARPNESS: | ||
550 | qctrl->flags |= V4L2_CTRL_FLAG_SLIDER; | 573 | qctrl->flags |= V4L2_CTRL_FLAG_SLIDER; |
551 | break; | 574 | break; |
575 | case V4L2_CID_PAN_RELATIVE: | ||
576 | case V4L2_CID_TILT_RELATIVE: | ||
577 | case V4L2_CID_FOCUS_RELATIVE: | ||
578 | case V4L2_CID_ZOOM_RELATIVE: | ||
579 | qctrl->flags |= V4L2_CTRL_FLAG_WRITE_ONLY; | ||
580 | break; | ||
552 | } | 581 | } |
553 | qctrl->minimum = min; | 582 | qctrl->minimum = min; |
554 | qctrl->maximum = max; | 583 | qctrl->maximum = max; |
555 | qctrl->step = step; | 584 | qctrl->step = step; |
556 | qctrl->default_value = def; | 585 | qctrl->default_value = def; |
557 | qctrl->reserved[0] = qctrl->reserved[1] = 0; | 586 | qctrl->reserved[0] = qctrl->reserved[1] = 0; |
558 | snprintf(qctrl->name, sizeof(qctrl->name), name); | 587 | strlcpy(qctrl->name, name, sizeof(qctrl->name)); |
559 | return 0; | 588 | return 0; |
560 | } | 589 | } |
561 | EXPORT_SYMBOL(v4l2_ctrl_query_fill); | 590 | EXPORT_SYMBOL(v4l2_ctrl_query_fill); |
562 | 591 | ||
563 | /* Fill in a struct v4l2_queryctrl with standard values based on | ||
564 | the control ID. */ | ||
565 | int v4l2_ctrl_query_fill_std(struct v4l2_queryctrl *qctrl) | ||
566 | { | ||
567 | switch (qctrl->id) { | ||
568 | /* USER controls */ | ||
569 | case V4L2_CID_USER_CLASS: | ||
570 | case V4L2_CID_MPEG_CLASS: | ||
571 | return v4l2_ctrl_query_fill(qctrl, 0, 0, 0, 0); | ||
572 | case V4L2_CID_AUDIO_VOLUME: | ||
573 | return v4l2_ctrl_query_fill(qctrl, 0, 65535, 65535 / 100, 58880); | ||
574 | case V4L2_CID_AUDIO_MUTE: | ||
575 | case V4L2_CID_AUDIO_LOUDNESS: | ||
576 | return v4l2_ctrl_query_fill(qctrl, 0, 1, 1, 0); | ||
577 | case V4L2_CID_AUDIO_BALANCE: | ||
578 | case V4L2_CID_AUDIO_BASS: | ||
579 | case V4L2_CID_AUDIO_TREBLE: | ||
580 | return v4l2_ctrl_query_fill(qctrl, 0, 65535, 65535 / 100, 32768); | ||
581 | case V4L2_CID_BRIGHTNESS: | ||
582 | return v4l2_ctrl_query_fill(qctrl, 0, 255, 1, 128); | ||
583 | case V4L2_CID_CONTRAST: | ||
584 | case V4L2_CID_SATURATION: | ||
585 | return v4l2_ctrl_query_fill(qctrl, 0, 127, 1, 64); | ||
586 | case V4L2_CID_HUE: | ||
587 | return v4l2_ctrl_query_fill(qctrl, -128, 127, 1, 0); | ||
588 | |||
589 | /* MPEG controls */ | ||
590 | case V4L2_CID_MPEG_AUDIO_SAMPLING_FREQ: | ||
591 | return v4l2_ctrl_query_fill(qctrl, | ||
592 | V4L2_MPEG_AUDIO_SAMPLING_FREQ_44100, | ||
593 | V4L2_MPEG_AUDIO_SAMPLING_FREQ_32000, 1, | ||
594 | V4L2_MPEG_AUDIO_SAMPLING_FREQ_48000); | ||
595 | case V4L2_CID_MPEG_AUDIO_ENCODING: | ||
596 | return v4l2_ctrl_query_fill(qctrl, | ||
597 | V4L2_MPEG_AUDIO_ENCODING_LAYER_1, | ||
598 | V4L2_MPEG_AUDIO_ENCODING_AC3, 1, | ||
599 | V4L2_MPEG_AUDIO_ENCODING_LAYER_2); | ||
600 | case V4L2_CID_MPEG_AUDIO_L1_BITRATE: | ||
601 | return v4l2_ctrl_query_fill(qctrl, | ||
602 | V4L2_MPEG_AUDIO_L1_BITRATE_32K, | ||
603 | V4L2_MPEG_AUDIO_L1_BITRATE_448K, 1, | ||
604 | V4L2_MPEG_AUDIO_L1_BITRATE_256K); | ||
605 | case V4L2_CID_MPEG_AUDIO_L2_BITRATE: | ||
606 | return v4l2_ctrl_query_fill(qctrl, | ||
607 | V4L2_MPEG_AUDIO_L2_BITRATE_32K, | ||
608 | V4L2_MPEG_AUDIO_L2_BITRATE_384K, 1, | ||
609 | V4L2_MPEG_AUDIO_L2_BITRATE_224K); | ||
610 | case V4L2_CID_MPEG_AUDIO_L3_BITRATE: | ||
611 | return v4l2_ctrl_query_fill(qctrl, | ||
612 | V4L2_MPEG_AUDIO_L3_BITRATE_32K, | ||
613 | V4L2_MPEG_AUDIO_L3_BITRATE_320K, 1, | ||
614 | V4L2_MPEG_AUDIO_L3_BITRATE_192K); | ||
615 | case V4L2_CID_MPEG_AUDIO_AAC_BITRATE: | ||
616 | return v4l2_ctrl_query_fill(qctrl, 0, 6400, 1, 3200000); | ||
617 | case V4L2_CID_MPEG_AUDIO_AC3_BITRATE: | ||
618 | return v4l2_ctrl_query_fill(qctrl, | ||
619 | V4L2_MPEG_AUDIO_AC3_BITRATE_32K, | ||
620 | V4L2_MPEG_AUDIO_AC3_BITRATE_640K, 1, | ||
621 | V4L2_MPEG_AUDIO_AC3_BITRATE_384K); | ||
622 | case V4L2_CID_MPEG_AUDIO_MODE: | ||
623 | return v4l2_ctrl_query_fill(qctrl, | ||
624 | V4L2_MPEG_AUDIO_MODE_STEREO, | ||
625 | V4L2_MPEG_AUDIO_MODE_MONO, 1, | ||
626 | V4L2_MPEG_AUDIO_MODE_STEREO); | ||
627 | case V4L2_CID_MPEG_AUDIO_MODE_EXTENSION: | ||
628 | return v4l2_ctrl_query_fill(qctrl, | ||
629 | V4L2_MPEG_AUDIO_MODE_EXTENSION_BOUND_4, | ||
630 | V4L2_MPEG_AUDIO_MODE_EXTENSION_BOUND_16, 1, | ||
631 | V4L2_MPEG_AUDIO_MODE_EXTENSION_BOUND_4); | ||
632 | case V4L2_CID_MPEG_AUDIO_EMPHASIS: | ||
633 | return v4l2_ctrl_query_fill(qctrl, | ||
634 | V4L2_MPEG_AUDIO_EMPHASIS_NONE, | ||
635 | V4L2_MPEG_AUDIO_EMPHASIS_CCITT_J17, 1, | ||
636 | V4L2_MPEG_AUDIO_EMPHASIS_NONE); | ||
637 | case V4L2_CID_MPEG_AUDIO_CRC: | ||
638 | return v4l2_ctrl_query_fill(qctrl, | ||
639 | V4L2_MPEG_AUDIO_CRC_NONE, | ||
640 | V4L2_MPEG_AUDIO_CRC_CRC16, 1, | ||
641 | V4L2_MPEG_AUDIO_CRC_NONE); | ||
642 | case V4L2_CID_MPEG_AUDIO_MUTE: | ||
643 | return v4l2_ctrl_query_fill(qctrl, 0, 1, 1, 0); | ||
644 | case V4L2_CID_MPEG_VIDEO_ENCODING: | ||
645 | return v4l2_ctrl_query_fill(qctrl, | ||
646 | V4L2_MPEG_VIDEO_ENCODING_MPEG_1, | ||
647 | V4L2_MPEG_VIDEO_ENCODING_MPEG_4_AVC, 1, | ||
648 | V4L2_MPEG_VIDEO_ENCODING_MPEG_2); | ||
649 | case V4L2_CID_MPEG_VIDEO_ASPECT: | ||
650 | return v4l2_ctrl_query_fill(qctrl, | ||
651 | V4L2_MPEG_VIDEO_ASPECT_1x1, | ||
652 | V4L2_MPEG_VIDEO_ASPECT_221x100, 1, | ||
653 | V4L2_MPEG_VIDEO_ASPECT_4x3); | ||
654 | case V4L2_CID_MPEG_VIDEO_B_FRAMES: | ||
655 | return v4l2_ctrl_query_fill(qctrl, 0, 33, 1, 2); | ||
656 | case V4L2_CID_MPEG_VIDEO_GOP_SIZE: | ||
657 | return v4l2_ctrl_query_fill(qctrl, 1, 34, 1, 12); | ||
658 | case V4L2_CID_MPEG_VIDEO_GOP_CLOSURE: | ||
659 | return v4l2_ctrl_query_fill(qctrl, 0, 1, 1, 1); | ||
660 | case V4L2_CID_MPEG_VIDEO_PULLDOWN: | ||
661 | return v4l2_ctrl_query_fill(qctrl, 0, 1, 1, 0); | ||
662 | case V4L2_CID_MPEG_VIDEO_BITRATE_MODE: | ||
663 | return v4l2_ctrl_query_fill(qctrl, | ||
664 | V4L2_MPEG_VIDEO_BITRATE_MODE_VBR, | ||
665 | V4L2_MPEG_VIDEO_BITRATE_MODE_CBR, 1, | ||
666 | V4L2_MPEG_VIDEO_BITRATE_MODE_VBR); | ||
667 | case V4L2_CID_MPEG_VIDEO_BITRATE: | ||
668 | return v4l2_ctrl_query_fill(qctrl, 0, 27000000, 1, 6000000); | ||
669 | case V4L2_CID_MPEG_VIDEO_BITRATE_PEAK: | ||
670 | return v4l2_ctrl_query_fill(qctrl, 0, 27000000, 1, 8000000); | ||
671 | case V4L2_CID_MPEG_VIDEO_TEMPORAL_DECIMATION: | ||
672 | return v4l2_ctrl_query_fill(qctrl, 0, 255, 1, 0); | ||
673 | case V4L2_CID_MPEG_VIDEO_MUTE: | ||
674 | return v4l2_ctrl_query_fill(qctrl, 0, 1, 1, 0); | ||
675 | case V4L2_CID_MPEG_VIDEO_MUTE_YUV: /* Init YUV (really YCbCr) to black */ | ||
676 | return v4l2_ctrl_query_fill(qctrl, 0, 0xffffff, 1, 0x008080); | ||
677 | case V4L2_CID_MPEG_STREAM_TYPE: | ||
678 | return v4l2_ctrl_query_fill(qctrl, | ||
679 | V4L2_MPEG_STREAM_TYPE_MPEG2_PS, | ||
680 | V4L2_MPEG_STREAM_TYPE_MPEG2_SVCD, 1, | ||
681 | V4L2_MPEG_STREAM_TYPE_MPEG2_PS); | ||
682 | case V4L2_CID_MPEG_STREAM_PID_PMT: | ||
683 | return v4l2_ctrl_query_fill(qctrl, 0, (1 << 14) - 1, 1, 16); | ||
684 | case V4L2_CID_MPEG_STREAM_PID_AUDIO: | ||
685 | return v4l2_ctrl_query_fill(qctrl, 0, (1 << 14) - 1, 1, 260); | ||
686 | case V4L2_CID_MPEG_STREAM_PID_VIDEO: | ||
687 | return v4l2_ctrl_query_fill(qctrl, 0, (1 << 14) - 1, 1, 256); | ||
688 | case V4L2_CID_MPEG_STREAM_PID_PCR: | ||
689 | return v4l2_ctrl_query_fill(qctrl, 0, (1 << 14) - 1, 1, 259); | ||
690 | case V4L2_CID_MPEG_STREAM_PES_ID_AUDIO: | ||
691 | return v4l2_ctrl_query_fill(qctrl, 0, 255, 1, 0); | ||
692 | case V4L2_CID_MPEG_STREAM_PES_ID_VIDEO: | ||
693 | return v4l2_ctrl_query_fill(qctrl, 0, 255, 1, 0); | ||
694 | case V4L2_CID_MPEG_STREAM_VBI_FMT: | ||
695 | return v4l2_ctrl_query_fill(qctrl, | ||
696 | V4L2_MPEG_STREAM_VBI_FMT_NONE, | ||
697 | V4L2_MPEG_STREAM_VBI_FMT_IVTV, 1, | ||
698 | V4L2_MPEG_STREAM_VBI_FMT_NONE); | ||
699 | default: | ||
700 | return -EINVAL; | ||
701 | } | ||
702 | } | ||
703 | EXPORT_SYMBOL(v4l2_ctrl_query_fill_std); | ||
704 | |||
705 | /* Fill in a struct v4l2_querymenu based on the struct v4l2_queryctrl and | 592 | /* Fill in a struct v4l2_querymenu based on the struct v4l2_queryctrl and |
706 | the menu. The qctrl pointer may be NULL, in which case it is ignored. | 593 | the menu. The qctrl pointer may be NULL, in which case it is ignored. |
707 | If menu_items is NULL, then the menu items are retrieved using | 594 | If menu_items is NULL, then the menu items are retrieved using |
@@ -720,7 +607,7 @@ int v4l2_ctrl_query_menu(struct v4l2_querymenu *qmenu, struct v4l2_queryctrl *qc | |||
720 | for (i = 0; i < qmenu->index && menu_items[i]; i++) ; | 607 | for (i = 0; i < qmenu->index && menu_items[i]; i++) ; |
721 | if (menu_items[i] == NULL || menu_items[i][0] == '\0') | 608 | if (menu_items[i] == NULL || menu_items[i][0] == '\0') |
722 | return -EINVAL; | 609 | return -EINVAL; |
723 | snprintf(qmenu->name, sizeof(qmenu->name), menu_items[qmenu->index]); | 610 | strlcpy(qmenu->name, menu_items[qmenu->index], sizeof(qmenu->name)); |
724 | return 0; | 611 | return 0; |
725 | } | 612 | } |
726 | EXPORT_SYMBOL(v4l2_ctrl_query_menu); | 613 | EXPORT_SYMBOL(v4l2_ctrl_query_menu); |
@@ -737,8 +624,8 @@ int v4l2_ctrl_query_menu_valid_items(struct v4l2_querymenu *qmenu, const u32 *id | |||
737 | return -EINVAL; | 624 | return -EINVAL; |
738 | while (*ids != V4L2_CTRL_MENU_IDS_END) { | 625 | while (*ids != V4L2_CTRL_MENU_IDS_END) { |
739 | if (*ids++ == qmenu->index) { | 626 | if (*ids++ == qmenu->index) { |
740 | snprintf(qmenu->name, sizeof(qmenu->name), | 627 | strlcpy(qmenu->name, menu_items[qmenu->index], |
741 | menu_items[qmenu->index]); | 628 | sizeof(qmenu->name)); |
742 | return 0; | 629 | return 0; |
743 | } | 630 | } |
744 | } | 631 | } |
@@ -749,7 +636,7 @@ EXPORT_SYMBOL(v4l2_ctrl_query_menu_valid_items); | |||
749 | /* ctrl_classes points to an array of u32 pointers, the last element is | 636 | /* ctrl_classes points to an array of u32 pointers, the last element is |
750 | a NULL pointer. Each u32 array is a 0-terminated array of control IDs. | 637 | a NULL pointer. Each u32 array is a 0-terminated array of control IDs. |
751 | Each array must be sorted low to high and belong to the same control | 638 | Each array must be sorted low to high and belong to the same control |
752 | class. The array of u32 pointer must also be sorted, from low class IDs | 639 | class. The array of u32 pointers must also be sorted, from low class IDs |
753 | to high class IDs. | 640 | to high class IDs. |
754 | 641 | ||
755 | This function returns the first ID that follows after the given ID. | 642 | This function returns the first ID that follows after the given ID. |
@@ -910,10 +797,10 @@ struct v4l2_subdev *v4l2_i2c_new_subdev(struct i2c_adapter *adapter, | |||
910 | struct i2c_board_info info; | 797 | struct i2c_board_info info; |
911 | 798 | ||
912 | BUG_ON(!dev); | 799 | BUG_ON(!dev); |
913 | #ifdef MODULE | 800 | |
914 | if (module_name) | 801 | if (module_name) |
915 | request_module(module_name); | 802 | request_module(module_name); |
916 | #endif | 803 | |
917 | /* Setup the i2c board info with the device type and | 804 | /* Setup the i2c board info with the device type and |
918 | the device address. */ | 805 | the device address. */ |
919 | memset(&info, 0, sizeof(info)); | 806 | memset(&info, 0, sizeof(info)); |
@@ -927,11 +814,11 @@ struct v4l2_subdev *v4l2_i2c_new_subdev(struct i2c_adapter *adapter, | |||
927 | We need better support from the kernel so that we | 814 | We need better support from the kernel so that we |
928 | can easily wait for the load to finish. */ | 815 | can easily wait for the load to finish. */ |
929 | if (client == NULL || client->driver == NULL) | 816 | if (client == NULL || client->driver == NULL) |
930 | return NULL; | 817 | goto error; |
931 | 818 | ||
932 | /* Lock the module so we can safely get the v4l2_subdev pointer */ | 819 | /* Lock the module so we can safely get the v4l2_subdev pointer */ |
933 | if (!try_module_get(client->driver->driver.owner)) | 820 | if (!try_module_get(client->driver->driver.owner)) |
934 | return NULL; | 821 | goto error; |
935 | sd = i2c_get_clientdata(client); | 822 | sd = i2c_get_clientdata(client); |
936 | 823 | ||
937 | /* Register with the v4l2_device which increases the module's | 824 | /* Register with the v4l2_device which increases the module's |
@@ -940,8 +827,13 @@ struct v4l2_subdev *v4l2_i2c_new_subdev(struct i2c_adapter *adapter, | |||
940 | sd = NULL; | 827 | sd = NULL; |
941 | /* Decrease the module use count to match the first try_module_get. */ | 828 | /* Decrease the module use count to match the first try_module_get. */ |
942 | module_put(client->driver->driver.owner); | 829 | module_put(client->driver->driver.owner); |
943 | return sd; | ||
944 | 830 | ||
831 | error: | ||
832 | /* If we have a client but no subdev, then something went wrong and | ||
833 | we must unregister the client. */ | ||
834 | if (client && sd == NULL) | ||
835 | i2c_unregister_device(client); | ||
836 | return sd; | ||
945 | } | 837 | } |
946 | EXPORT_SYMBOL_GPL(v4l2_i2c_new_subdev); | 838 | EXPORT_SYMBOL_GPL(v4l2_i2c_new_subdev); |
947 | 839 | ||
@@ -958,10 +850,10 @@ struct v4l2_subdev *v4l2_i2c_new_probed_subdev(struct i2c_adapter *adapter, | |||
958 | struct i2c_board_info info; | 850 | struct i2c_board_info info; |
959 | 851 | ||
960 | BUG_ON(!dev); | 852 | BUG_ON(!dev); |
961 | #ifdef MODULE | 853 | |
962 | if (module_name) | 854 | if (module_name) |
963 | request_module(module_name); | 855 | request_module(module_name); |
964 | #endif | 856 | |
965 | /* Setup the i2c board info with the device type and | 857 | /* Setup the i2c board info with the device type and |
966 | the device address. */ | 858 | the device address. */ |
967 | memset(&info, 0, sizeof(info)); | 859 | memset(&info, 0, sizeof(info)); |
@@ -974,11 +866,11 @@ struct v4l2_subdev *v4l2_i2c_new_probed_subdev(struct i2c_adapter *adapter, | |||
974 | We need better support from the kernel so that we | 866 | We need better support from the kernel so that we |
975 | can easily wait for the load to finish. */ | 867 | can easily wait for the load to finish. */ |
976 | if (client == NULL || client->driver == NULL) | 868 | if (client == NULL || client->driver == NULL) |
977 | return NULL; | 869 | goto error; |
978 | 870 | ||
979 | /* Lock the module so we can safely get the v4l2_subdev pointer */ | 871 | /* Lock the module so we can safely get the v4l2_subdev pointer */ |
980 | if (!try_module_get(client->driver->driver.owner)) | 872 | if (!try_module_get(client->driver->driver.owner)) |
981 | return NULL; | 873 | goto error; |
982 | sd = i2c_get_clientdata(client); | 874 | sd = i2c_get_clientdata(client); |
983 | 875 | ||
984 | /* Register with the v4l2_device which increases the module's | 876 | /* Register with the v4l2_device which increases the module's |
@@ -987,8 +879,59 @@ struct v4l2_subdev *v4l2_i2c_new_probed_subdev(struct i2c_adapter *adapter, | |||
987 | sd = NULL; | 879 | sd = NULL; |
988 | /* Decrease the module use count to match the first try_module_get. */ | 880 | /* Decrease the module use count to match the first try_module_get. */ |
989 | module_put(client->driver->driver.owner); | 881 | module_put(client->driver->driver.owner); |
882 | |||
883 | error: | ||
884 | /* If we have a client but no subdev, then something went wrong and | ||
885 | we must unregister the client. */ | ||
886 | if (client && sd == NULL) | ||
887 | i2c_unregister_device(client); | ||
990 | return sd; | 888 | return sd; |
991 | } | 889 | } |
992 | EXPORT_SYMBOL_GPL(v4l2_i2c_new_probed_subdev); | 890 | EXPORT_SYMBOL_GPL(v4l2_i2c_new_probed_subdev); |
993 | 891 | ||
892 | /* Return i2c client address of v4l2_subdev. */ | ||
893 | unsigned short v4l2_i2c_subdev_addr(struct v4l2_subdev *sd) | ||
894 | { | ||
895 | struct i2c_client *client = v4l2_get_subdevdata(sd); | ||
896 | |||
897 | return client ? client->addr : I2C_CLIENT_END; | ||
898 | } | ||
899 | EXPORT_SYMBOL_GPL(v4l2_i2c_subdev_addr); | ||
900 | |||
901 | /* Return a list of I2C tuner addresses to probe. Use only if the tuner | ||
902 | addresses are unknown. */ | ||
903 | const unsigned short *v4l2_i2c_tuner_addrs(enum v4l2_i2c_tuner_type type) | ||
904 | { | ||
905 | static const unsigned short radio_addrs[] = { | ||
906 | #if defined(CONFIG_MEDIA_TUNER_TEA5761) || defined(CONFIG_MEDIA_TUNER_TEA5761_MODULE) | ||
907 | 0x10, | ||
908 | #endif | ||
909 | 0x60, | ||
910 | I2C_CLIENT_END | ||
911 | }; | ||
912 | static const unsigned short demod_addrs[] = { | ||
913 | 0x42, 0x43, 0x4a, 0x4b, | ||
914 | I2C_CLIENT_END | ||
915 | }; | ||
916 | static const unsigned short tv_addrs[] = { | ||
917 | 0x42, 0x43, 0x4a, 0x4b, /* tda8290 */ | ||
918 | 0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67, | ||
919 | 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f, | ||
920 | I2C_CLIENT_END | ||
921 | }; | ||
922 | |||
923 | switch (type) { | ||
924 | case ADDRS_RADIO: | ||
925 | return radio_addrs; | ||
926 | case ADDRS_DEMOD: | ||
927 | return demod_addrs; | ||
928 | case ADDRS_TV: | ||
929 | return tv_addrs; | ||
930 | case ADDRS_TV_WITH_DEMOD: | ||
931 | return tv_addrs + 4; | ||
932 | } | ||
933 | return NULL; | ||
934 | } | ||
935 | EXPORT_SYMBOL_GPL(v4l2_i2c_tuner_addrs); | ||
936 | |||
994 | #endif | 937 | #endif |