aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorHans Verkuil <hverkuil@xs4all.nl>2006-03-19 10:35:57 -0500
committerMauro Carvalho Chehab <mchehab@infradead.org>2006-03-24 14:26:57 -0500
commit2474ed444b475614ef795523076be7cc8437ae00 (patch)
tree87808b3c7ff145b63a638e6e42ffce9db7db1b8c
parent49965a80a4c4f5cbe15fb3bb1f8f8b0ec4ef02bc (diff)
V4L/DVB (3582): Implement correct msp3400 input/output routing
- implement VIDIOC_INT_S_AUDIO_ROUTING for msp3400 and tvaudio - use the new command in bttv, pvrusb2 and em28xx. - remove the now obsolete MSP_SET_MATRIX from msp3400 (yeah!) - remove the obsolete VIDIOC_S_AUDIO from msp3400. Signed-off-by: Hans Verkuil <hverkuil@xs4all.nl> Signed-off-by: Mauro Carvalho Chehab <mchehab@infradead.org>
-rw-r--r--drivers/media/video/bt8xx/bttv-driver.c52
-rw-r--r--drivers/media/video/em28xx/em28xx-cards.c8
-rw-r--r--drivers/media/video/em28xx/em28xx-video.c8
-rw-r--r--drivers/media/video/msp3400-driver.c67
-rw-r--r--drivers/media/video/msp3400-driver.h4
-rw-r--r--drivers/media/video/msp3400-kthreads.c111
-rw-r--r--drivers/media/video/tvaudio.c24
-rw-r--r--drivers/media/video/v4l2-common.c13
-rw-r--r--include/media/msp3400.h5
-rw-r--r--include/media/v4l2-common.h8
10 files changed, 181 insertions, 119 deletions
diff --git a/drivers/media/video/bt8xx/bttv-driver.c b/drivers/media/video/bt8xx/bttv-driver.c
index be567ec9e145..80e4a7406ac2 100644
--- a/drivers/media/video/bt8xx/bttv-driver.c
+++ b/drivers/media/video/bt8xx/bttv-driver.c
@@ -37,6 +37,7 @@
37#include "bttvp.h" 37#include "bttvp.h"
38#include <media/v4l2-common.h> 38#include <media/v4l2-common.h>
39#include <media/tvaudio.h> 39#include <media/tvaudio.h>
40#include <media/msp3400.h>
40 41
41#include <linux/dma-mapping.h> 42#include <linux/dma-mapping.h>
42 43
@@ -934,11 +935,9 @@ static int
934audio_mux(struct bttv *btv, int input, int mute) 935audio_mux(struct bttv *btv, int input, int mute)
935{ 936{
936 int gpio_val, signal; 937 int gpio_val, signal;
937 struct v4l2_audio aud_input;
938 struct v4l2_control ctrl; 938 struct v4l2_control ctrl;
939 struct i2c_client *c; 939 struct i2c_client *c;
940 940
941 memset(&aud_input, 0, sizeof(aud_input));
942 gpio_inout(bttv_tvcards[btv->c.type].gpiomask, 941 gpio_inout(bttv_tvcards[btv->c.type].gpiomask,
943 bttv_tvcards[btv->c.type].gpiomask); 942 bttv_tvcards[btv->c.type].gpiomask);
944 signal = btread(BT848_DSTATUS) & BT848_DSTATUS_HLOC; 943 signal = btread(BT848_DSTATUS) & BT848_DSTATUS_HLOC;
@@ -953,7 +952,6 @@ audio_mux(struct bttv *btv, int input, int mute)
953 gpio_val = bttv_tvcards[btv->c.type].gpiomute; 952 gpio_val = bttv_tvcards[btv->c.type].gpiomute;
954 else 953 else
955 gpio_val = bttv_tvcards[btv->c.type].gpiomux[input]; 954 gpio_val = bttv_tvcards[btv->c.type].gpiomux[input];
956 aud_input.index = btv->audio;
957 955
958 gpio_bits(bttv_tvcards[btv->c.type].gpiomask, gpio_val); 956 gpio_bits(bttv_tvcards[btv->c.type].gpiomask, gpio_val);
959 if (bttv_gpio) 957 if (bttv_gpio)
@@ -962,15 +960,51 @@ audio_mux(struct bttv *btv, int input, int mute)
962 return 0; 960 return 0;
963 961
964 ctrl.id = V4L2_CID_AUDIO_MUTE; 962 ctrl.id = V4L2_CID_AUDIO_MUTE;
965 /* take automute into account, just btv->mute is not enough */ 963 ctrl.value = btv->mute;
966 ctrl.value = mute;
967 bttv_call_i2c_clients(btv, VIDIOC_S_CTRL, &ctrl); 964 bttv_call_i2c_clients(btv, VIDIOC_S_CTRL, &ctrl);
968 c = btv->i2c_msp34xx_client; 965 c = btv->i2c_msp34xx_client;
969 if (c) 966 if (c) {
970 c->driver->command(c, VIDIOC_S_AUDIO, &aud_input); 967 struct v4l2_routing route;
968
969 /* Note: the inputs tuner/radio/extern/intern are translated
970 to msp routings. This assumes common behavior for all msp3400
971 based TV cards. When this assumption fails, then the
972 specific MSP routing must be added to the card table.
973 For now this is sufficient. */
974 switch (input) {
975 case TVAUDIO_INPUT_RADIO:
976 route.input = MSP_INPUT(MSP_IN_SCART_2, MSP_IN_TUNER_1,
977 MSP_DSP_OUT_SCART, MSP_DSP_OUT_SCART);
978 break;
979 case TVAUDIO_INPUT_EXTERN:
980 route.input = MSP_INPUT(MSP_IN_SCART_1, MSP_IN_TUNER_1,
981 MSP_DSP_OUT_SCART, MSP_DSP_OUT_SCART);
982 break;
983 case TVAUDIO_INPUT_INTERN:
984 /* Yes, this is the same input as for RADIO. I doubt
985 if this is ever used. The only board with an INTERN
986 input is the BTTV_BOARD_AVERMEDIA98. I wonder how
987 that was tested. My guess is that the whole INTERN
988 input does not work. */
989 route.input = MSP_INPUT(MSP_IN_SCART_2, MSP_IN_TUNER_1,
990 MSP_DSP_OUT_SCART, MSP_DSP_OUT_SCART);
991 break;
992 case TVAUDIO_INPUT_TUNER:
993 default:
994 route.input = MSP_INPUT_DEFAULT;
995 break;
996 }
997 route.output = MSP_OUTPUT_DEFAULT;
998 c->driver->command(c, VIDIOC_INT_S_AUDIO_ROUTING, &route);
999 }
971 c = btv->i2c_tvaudio_client; 1000 c = btv->i2c_tvaudio_client;
972 if (c) 1001 if (c) {
973 c->driver->command(c, VIDIOC_S_AUDIO, &aud_input); 1002 struct v4l2_routing route;
1003
1004 route.input = input;
1005 route.output = 0;
1006 c->driver->command(c, VIDIOC_INT_S_AUDIO_ROUTING, &route);
1007 }
974 return 0; 1008 return 0;
975} 1009}
976 1010
diff --git a/drivers/media/video/em28xx/em28xx-cards.c b/drivers/media/video/em28xx/em28xx-cards.c
index 2d68a27417eb..f62fd706b45a 100644
--- a/drivers/media/video/em28xx/em28xx-cards.c
+++ b/drivers/media/video/em28xx/em28xx-cards.c
@@ -28,8 +28,9 @@
28#include <linux/i2c.h> 28#include <linux/i2c.h>
29#include <linux/usb.h> 29#include <linux/usb.h>
30#include <media/tuner.h> 30#include <media/tuner.h>
31#include <media/audiochip.h> 31#include <media/msp3400.h>
32#include <media/tveeprom.h> 32#include <media/tveeprom.h>
33#include <media/audiochip.h>
33#include <media/v4l2-common.h> 34#include <media/v4l2-common.h>
34 35
35#include "em28xx.h" 36#include "em28xx.h"
@@ -146,11 +147,12 @@ struct em28xx_board em28xx_boards[] = {
146 .input = {{ 147 .input = {{
147 .type = EM28XX_VMUX_TELEVISION, 148 .type = EM28XX_VMUX_TELEVISION,
148 .vmux = 0, 149 .vmux = 0,
149 .amux = 6, 150 .amux = MSP_INPUT_DEFAULT,
150 },{ 151 },{
151 .type = EM28XX_VMUX_SVIDEO, 152 .type = EM28XX_VMUX_SVIDEO,
152 .vmux = 2, 153 .vmux = 2,
153 .amux = 1, 154 .amux = MSP_INPUT(MSP_IN_SCART_1, MSP_IN_TUNER_1,
155 MSP_DSP_OUT_SCART, MSP_DSP_OUT_SCART),
154 }}, 156 }},
155 }, 157 },
156 [EM2820_BOARD_MSI_VOX_USB_2] = { 158 [EM2820_BOARD_MSI_VOX_USB_2] = {
diff --git a/drivers/media/video/em28xx/em28xx-video.c b/drivers/media/video/em28xx/em28xx-video.c
index 780342f7b239..dfba33d0fa61 100644
--- a/drivers/media/video/em28xx/em28xx-video.c
+++ b/drivers/media/video/em28xx/em28xx-video.c
@@ -38,6 +38,7 @@
38#include "em28xx.h" 38#include "em28xx.h"
39#include <media/tuner.h> 39#include <media/tuner.h>
40#include <media/v4l2-common.h> 40#include <media/v4l2-common.h>
41#include <media/msp3400.h>
41 42
42#define DRIVER_AUTHOR "Ludovico Cavedon <cavedon@sssup.it>, " \ 43#define DRIVER_AUTHOR "Ludovico Cavedon <cavedon@sssup.it>, " \
43 "Markus Rechberger <mrechberger@gmail.com>, " \ 44 "Markus Rechberger <mrechberger@gmail.com>, " \
@@ -216,9 +217,14 @@ static void video_mux(struct em28xx *dev, int index)
216 em28xx_videodbg("Setting input index=%d, vmux=%d, amux=%d\n",index,input,dev->ctl_ainput); 217 em28xx_videodbg("Setting input index=%d, vmux=%d, amux=%d\n",index,input,dev->ctl_ainput);
217 218
218 if (dev->has_msp34xx) { 219 if (dev->has_msp34xx) {
220 struct v4l2_routing route;
221
219 if (dev->i2s_speed) 222 if (dev->i2s_speed)
220 em28xx_i2c_call_clients(dev, VIDIOC_INT_I2S_CLOCK_FREQ, &dev->i2s_speed); 223 em28xx_i2c_call_clients(dev, VIDIOC_INT_I2S_CLOCK_FREQ, &dev->i2s_speed);
221 em28xx_i2c_call_clients(dev, VIDIOC_S_AUDIO, &dev->ctl_ainput); 224 route.input = dev->ctl_ainput;
225 route.output = MSP_OUTPUT(MSP_OUT_SCART1_DA);
226 /* Note: this is msp3400 specific */
227 em28xx_i2c_call_clients(dev, VIDIOC_INT_S_AUDIO_ROUTING, &route);
222 ainput = EM28XX_AUDIO_SRC_TUNER; 228 ainput = EM28XX_AUDIO_SRC_TUNER;
223 em28xx_audio_source(dev, ainput); 229 em28xx_audio_source(dev, ainput);
224 } else { 230 } else {
diff --git a/drivers/media/video/msp3400-driver.c b/drivers/media/video/msp3400-driver.c
index 04250284ff1e..8ba1c960388a 100644
--- a/drivers/media/video/msp3400-driver.c
+++ b/drivers/media/video/msp3400-driver.c
@@ -555,7 +555,6 @@ static int msp_set_ctrl(struct i2c_client *client, struct v4l2_control *ctrl)
555static int msp_command(struct i2c_client *client, unsigned int cmd, void *arg) 555static int msp_command(struct i2c_client *client, unsigned int cmd, void *arg)
556{ 556{
557 struct msp_state *state = i2c_get_clientdata(client); 557 struct msp_state *state = i2c_get_clientdata(client);
558 int scart = -1;
559 558
560 if (msp_debug >= 2) 559 if (msp_debug >= 2)
561 v4l_i2c_print_ioctl(client, cmd); 560 v4l_i2c_print_ioctl(client, cmd);
@@ -660,15 +659,6 @@ static int msp_command(struct i2c_client *client, unsigned int cmd, void *arg)
660 break; 659 break;
661 } 660 }
662 661
663 /* msp34xx specific */
664 case MSP_SET_MATRIX:
665 {
666 struct msp_matrix *mspm = arg;
667
668 msp_set_scart(client, mspm->input - 1, mspm->output);
669 break;
670 }
671
672 /* --- v4l2 ioctls --- */ 662 /* --- v4l2 ioctls --- */
673 case VIDIOC_S_STD: 663 case VIDIOC_S_STD:
674 { 664 {
@@ -682,36 +672,38 @@ static int msp_command(struct i2c_client *client, unsigned int cmd, void *arg)
682 return 0; 672 return 0;
683 } 673 }
684 674
685 case VIDIOC_S_AUDIO: 675 case VIDIOC_INT_G_AUDIO_ROUTING:
686 { 676 {
687 struct v4l2_audio *sarg = arg; 677 struct v4l2_routing *rt = arg;
688 678
689 switch (sarg->index) { 679 *rt = state->routing;
690 case TVAUDIO_INPUT_RADIO: 680 break;
691 /* Hauppauge uses IN2 for the radio */ 681 }
692 state->mode = MSP_MODE_FM_RADIO; 682
693 scart = SCART_IN2; 683 case VIDIOC_INT_S_AUDIO_ROUTING:
694 break; 684 {
695 case TVAUDIO_INPUT_EXTERN: 685 struct v4l2_routing *rt = arg;
696 /* IN1 is often used for external input ... */ 686 int tuner = (rt->input >> 3) & 1;
697 state->mode = MSP_MODE_EXTERN; 687 int old_tuner = (state->routing.input >> 3) & 1;
698 scart = SCART_IN1; 688 int sc_in = rt->input & 0x7;
699 break; 689 int sc1_out = rt->output & 0xf;
700 case TVAUDIO_INPUT_INTERN: 690 int sc2_out = (rt->output >> 4) & 0xf;
701 /* ... sometimes it is IN2 through ;) */ 691 u16 val;
702 state->mode = MSP_MODE_EXTERN; 692
703 scart = SCART_IN2; 693 state->routing = *rt;
704 break; 694 if (state->opmode == OPMODE_AUTOSELECT) {
705 case TVAUDIO_INPUT_TUNER: 695 val = msp_read_dem(client, 0x30) & ~0x100;
706 state->mode = -1; 696 msp_write_dem(client, 0x30, val | (tuner ? 0x100 : 0));
707 break; 697 } else {
708 } 698 val = msp_read_dem(client, 0xbb) & ~0x100;
709 if (scart >= 0) { 699 msp_write_dem(client, 0xbb, val | (tuner ? 0x100 : 0));
710 state->rxsubchans = V4L2_TUNER_SUB_STEREO;
711 msp_set_scart(client, scart, 0);
712 } 700 }
701 msp_set_scart(client, sc_in, 0);
702 msp_set_scart(client, sc1_out, 1);
703 msp_set_scart(client, sc2_out, 2);
713 msp_set_audmode(client); 704 msp_set_audmode(client);
714 msp_wake_thread(client); 705 if (tuner != old_tuner)
706 msp_wake_thread(client);
715 break; 707 break;
716 } 708 }
717 709
@@ -941,6 +933,9 @@ static int msp_attach(struct i2c_adapter *adapter, int address, int kind)
941 state->muted = 0; 933 state->muted = 0;
942 state->i2s_mode = 0; 934 state->i2s_mode = 0;
943 init_waitqueue_head(&state->wq); 935 init_waitqueue_head(&state->wq);
936 /* These are the reset input/output positions */
937 state->routing.input = MSP_INPUT_DEFAULT;
938 state->routing.output = MSP_OUTPUT_DEFAULT;
944 939
945 state->rev1 = msp_read_dsp(client, 0x1e); 940 state->rev1 = msp_read_dsp(client, 0x1e);
946 if (state->rev1 != -1) 941 if (state->rev1 != -1)
diff --git a/drivers/media/video/msp3400-driver.h b/drivers/media/video/msp3400-driver.h
index 04821ebfe04a..1940748bb633 100644
--- a/drivers/media/video/msp3400-driver.h
+++ b/drivers/media/video/msp3400-driver.h
@@ -4,6 +4,8 @@
4#ifndef MSP3400_DRIVER_H 4#ifndef MSP3400_DRIVER_H
5#define MSP3400_DRIVER_H 5#define MSP3400_DRIVER_H
6 6
7#include <media/msp3400.h>
8
7/* ---------------------------------------------------------------------- */ 9/* ---------------------------------------------------------------------- */
8 10
9/* This macro is allowed for *constants* only, gcc must calculate it 11/* This macro is allowed for *constants* only, gcc must calculate it
@@ -72,7 +74,7 @@ struct msp_state {
72 int i2s_mode; 74 int i2s_mode;
73 int main, second; /* sound carrier */ 75 int main, second; /* sound carrier */
74 int input; 76 int input;
75 int source; /* see msp34xxg_set_source */ 77 struct v4l2_routing routing;
76 78
77 /* v4l2 */ 79 /* v4l2 */
78 int audmode; 80 int audmode;
diff --git a/drivers/media/video/msp3400-kthreads.c b/drivers/media/video/msp3400-kthreads.c
index 9ee8dc216d7f..1c794c3b9f21 100644
--- a/drivers/media/video/msp3400-kthreads.c
+++ b/drivers/media/video/msp3400-kthreads.c
@@ -187,13 +187,14 @@ void msp3400c_set_mode(struct i2c_client *client, int mode)
187{ 187{
188 struct msp_state *state = i2c_get_clientdata(client); 188 struct msp_state *state = i2c_get_clientdata(client);
189 struct msp3400c_init_data_dem *data = &msp3400c_init_data[mode]; 189 struct msp3400c_init_data_dem *data = &msp3400c_init_data[mode];
190 int tuner = (state->routing.input >> 3) & 1;
190 int i; 191 int i;
191 192
192 v4l_dbg(1, msp_debug, client, "set_mode: %d\n", mode); 193 v4l_dbg(1, msp_debug, client, "set_mode: %d\n", mode);
193 state->mode = mode; 194 state->mode = mode;
194 state->rxsubchans = V4L2_TUNER_SUB_MONO; 195 state->rxsubchans = V4L2_TUNER_SUB_MONO;
195 196
196 msp_write_dem(client, 0x00bb, data->ad_cv); 197 msp_write_dem(client, 0x00bb, data->ad_cv | (tuner ? 0x100 : 0));
197 198
198 for (i = 5; i >= 0; i--) /* fir 1 */ 199 for (i = 5; i >= 0; i--) /* fir 1 */
199 msp_write_dem(client, 0x0001, data->fir1[i]); 200 msp_write_dem(client, 0x0001, data->fir1[i]);
@@ -783,34 +784,6 @@ int msp3410d_thread(void *data)
783 * struct msp: only norm, acb and source are really used in this mode 784 * struct msp: only norm, acb and source are really used in this mode
784 */ 785 */
785 786
786/* set the same 'source' for the loudspeaker, scart and quasi-peak detector
787 * the value for source is the same as bit 15:8 of DSP registers 0x08,
788 * 0x0a and 0x0c: 0=mono, 1=stereo or A|B, 2=SCART, 3=stereo or A, 4=stereo or B
789 */
790static void msp34xxg_set_source(struct i2c_client *client, int source)
791{
792 struct msp_state *state = i2c_get_clientdata(client);
793
794 /* fix matrix mode to stereo and let the msp choose what
795 * to output according to 'source', as recommended
796 * for MONO (source==0) downmixing set bit[7:0] to 0x30
797 */
798 int value = (source & 0x07) << 8 | (source == 0 ? 0x30 : 0x20);
799
800 v4l_dbg(1, msp_debug, client, "set source to %d (0x%x)\n", source, value);
801 msp_set_source(client, value);
802 /*
803 * set identification threshold. Personally, I
804 * I set it to a higher value that the default
805 * of 0x190 to ignore noisy stereo signals.
806 * this needs tuning. (recommended range 0x00a0-0x03c0)
807 * 0x7f0 = forced mono mode
808 */
809 /* a2 threshold for stereo/bilingual */
810 msp_write_dem(client, 0x22, msp_stereo_thresh);
811 state->source = source;
812}
813
814static int msp34xxg_modus(struct i2c_client *client) 787static int msp34xxg_modus(struct i2c_client *client)
815{ 788{
816 struct msp_state *state = i2c_get_clientdata(client); 789 struct msp_state *state = i2c_get_clientdata(client);
@@ -843,10 +816,65 @@ static int msp34xxg_modus(struct i2c_client *client)
843 return 0x0001; 816 return 0x0001;
844} 817}
845 818
819static void msp34xxg_set_source(struct i2c_client *client, u16 reg, int in)
820 {
821 struct msp_state *state = i2c_get_clientdata(client);
822 int source, matrix;
823
824 switch (state->audmode) {
825 case V4L2_TUNER_MODE_MONO:
826 source = 0; /* mono only */
827 matrix = 0x30;
828 break;
829 case V4L2_TUNER_MODE_LANG1:
830 source = 3; /* stereo or A */
831 matrix = 0x00;
832 break;
833 case V4L2_TUNER_MODE_LANG2:
834 source = 4; /* stereo or B */
835 matrix = 0x10;
836 break;
837 case V4L2_TUNER_MODE_STEREO:
838 default:
839 source = 1; /* stereo or A|B */
840 matrix = 0x20;
841 break;
842 }
843
844 if (in == MSP_DSP_OUT_TUNER)
845 source = (source << 8) | 0x20;
846 /* the msp34x2g puts the MAIN_AVC, MAIN and AUX sources in 12, 13, 14
847 instead of 11, 12, 13. So we add one for that msp version. */
848 else if (in >= MSP_DSP_OUT_MAIN_AVC && state->has_dolby_pro_logic)
849 source = ((in + 1) << 8) | matrix;
850 else
851 source = (in << 8) | matrix;
852
853 v4l_dbg(1, msp_debug, client, "set source to %d (0x%x) for output %02x\n",
854 in, source, reg);
855 msp_write_dsp(client, reg, source);
856}
857
858static void msp34xxg_set_sources(struct i2c_client *client)
859{
860 struct msp_state *state = i2c_get_clientdata(client);
861 u32 in = state->routing.input;
862
863 msp34xxg_set_source(client, 0x0008, (in >> 4) & 0xf);
864 /* quasi-peak detector is set to same input as the loudspeaker (MAIN) */
865 msp34xxg_set_source(client, 0x000c, (in >> 4) & 0xf);
866 msp34xxg_set_source(client, 0x0009, (in >> 8) & 0xf);
867 msp34xxg_set_source(client, 0x000a, (in >> 12) & 0xf);
868 if (state->has_scart23_in_scart2_out)
869 msp34xxg_set_source(client, 0x0041, (in >> 16) & 0xf);
870 msp34xxg_set_source(client, 0x000b, (in >> 20) & 0xf);
871}
872
846/* (re-)initialize the msp34xxg */ 873/* (re-)initialize the msp34xxg */
847static void msp34xxg_reset(struct i2c_client *client) 874static void msp34xxg_reset(struct i2c_client *client)
848{ 875{
849 struct msp_state *state = i2c_get_clientdata(client); 876 struct msp_state *state = i2c_get_clientdata(client);
877 int tuner = (state->routing.input >> 3) & 1;
850 int modus; 878 int modus;
851 879
852 /* initialize std to 1 (autodetect) to signal that no standard is 880 /* initialize std to 1 (autodetect) to signal that no standard is
@@ -864,11 +892,12 @@ static void msp34xxg_reset(struct i2c_client *client)
864 892
865 /* step-by-step initialisation, as described in the manual */ 893 /* step-by-step initialisation, as described in the manual */
866 modus = msp34xxg_modus(client); 894 modus = msp34xxg_modus(client);
895 modus |= tuner ? 0x100 : 0;
867 msp_write_dem(client, 0x30, modus); 896 msp_write_dem(client, 0x30, modus);
868 897
869 /* write the dsps that may have an influence on 898 /* write the dsps that may have an influence on
870 standard/audio autodetection right now */ 899 standard/audio autodetection right now */
871 msp34xxg_set_source(client, state->source); 900 msp34xxg_set_sources(client);
872 901
873 msp_write_dsp(client, 0x0d, 0x1900); /* scart */ 902 msp_write_dsp(client, 0x0d, 0x1900); /* scart */
874 msp_write_dsp(client, 0x0e, 0x3000); /* FM */ 903 msp_write_dsp(client, 0x0e, 0x3000); /* FM */
@@ -896,7 +925,6 @@ int msp34xxg_thread(void *data)
896 925
897 v4l_dbg(1, msp_debug, client, "msp34xxg daemon started\n"); 926 v4l_dbg(1, msp_debug, client, "msp34xxg daemon started\n");
898 927
899 state->source = 1; /* default */
900 for (;;) { 928 for (;;) {
901 v4l_dbg(2, msp_debug, client, "msp34xxg thread: sleep\n"); 929 v4l_dbg(2, msp_debug, client, "msp34xxg thread: sleep\n");
902 msp_sleep(state, -1); 930 msp_sleep(state, -1);
@@ -993,7 +1021,6 @@ static int msp34xxg_detect_stereo(struct i2c_client *client)
993static void msp34xxg_set_audmode(struct i2c_client *client) 1021static void msp34xxg_set_audmode(struct i2c_client *client)
994{ 1022{
995 struct msp_state *state = i2c_get_clientdata(client); 1023 struct msp_state *state = i2c_get_clientdata(client);
996 int source;
997 1024
998 if (state->std == 0x20) { 1025 if (state->std == 0x20) {
999 if ((state->rxsubchans & V4L2_TUNER_SUB_SAP) && 1026 if ((state->rxsubchans & V4L2_TUNER_SUB_SAP) &&
@@ -1005,25 +1032,7 @@ static void msp34xxg_set_audmode(struct i2c_client *client)
1005 } 1032 }
1006 } 1033 }
1007 1034
1008 switch (state->audmode) { 1035 msp34xxg_set_sources(client);
1009 case V4L2_TUNER_MODE_MONO:
1010 source = 0; /* mono only */
1011 break;
1012 case V4L2_TUNER_MODE_STEREO:
1013 source = 1; /* stereo or A|B, see comment in msp34xxg_get_v4l2_stereo() */
1014 /* problem: that could also mean 2 (scart input) */
1015 break;
1016 case V4L2_TUNER_MODE_LANG1:
1017 source = 3; /* stereo or A */
1018 break;
1019 case V4L2_TUNER_MODE_LANG2:
1020 source = 4; /* stereo or B */
1021 break;
1022 default:
1023 source = 1;
1024 break;
1025 }
1026 msp34xxg_set_source(client, source);
1027} 1036}
1028 1037
1029void msp_set_audmode(struct i2c_client *client) 1038void msp_set_audmode(struct i2c_client *client)
diff --git a/drivers/media/video/tvaudio.c b/drivers/media/video/tvaudio.c
index 15fd55ff69ca..4e6d030d83c0 100644
--- a/drivers/media/video/tvaudio.c
+++ b/drivers/media/video/tvaudio.c
@@ -1682,6 +1682,30 @@ static int chip_command(struct i2c_client *client,
1682 case VIDIOC_S_CTRL: 1682 case VIDIOC_S_CTRL:
1683 return tvaudio_set_ctrl(chip, arg); 1683 return tvaudio_set_ctrl(chip, arg);
1684 1684
1685 case VIDIOC_INT_G_AUDIO_ROUTING:
1686 {
1687 struct v4l2_routing *rt = arg;
1688
1689 rt->input = chip->input;
1690 rt->output = 0;
1691 break;
1692 }
1693
1694 case VIDIOC_INT_S_AUDIO_ROUTING:
1695 {
1696 struct v4l2_routing *rt = arg;
1697
1698 if (!(desc->flags & CHIP_HAS_INPUTSEL) || rt->input >= 4)
1699 return -EINVAL;
1700 /* There are four inputs: tuner, radio, extern and intern. */
1701 chip->input = rt->input;
1702 if (chip->muted)
1703 break;
1704 chip_write_masked(chip, desc->inputreg,
1705 desc->inputmap[chip->input], desc->inputmask);
1706 break;
1707 }
1708
1685 case VIDIOC_S_AUDIO: 1709 case VIDIOC_S_AUDIO:
1686 { 1710 {
1687 struct v4l2_audio *sarg = arg; 1711 struct v4l2_audio *sarg = arg;
diff --git a/drivers/media/video/v4l2-common.c b/drivers/media/video/v4l2-common.c
index d1234d781e16..6824ee045fe6 100644
--- a/drivers/media/video/v4l2-common.c
+++ b/drivers/media/video/v4l2-common.c
@@ -312,7 +312,6 @@ static const char *v4l2_int_ioctls[] = {
312 [_IOC_NR(DECODER_DUMP)] = "DECODER_DUMP", 312 [_IOC_NR(DECODER_DUMP)] = "DECODER_DUMP",
313#endif 313#endif
314 [_IOC_NR(AUDC_SET_RADIO)] = "AUDC_SET_RADIO", 314 [_IOC_NR(AUDC_SET_RADIO)] = "AUDC_SET_RADIO",
315 [_IOC_NR(MSP_SET_MATRIX)] = "MSP_SET_MATRIX",
316 315
317 [_IOC_NR(TUNER_SET_TYPE_ADDR)] = "TUNER_SET_TYPE_ADDR", 316 [_IOC_NR(TUNER_SET_TYPE_ADDR)] = "TUNER_SET_TYPE_ADDR",
318 [_IOC_NR(TUNER_SET_STANDBY)] = "TUNER_SET_STANDBY", 317 [_IOC_NR(TUNER_SET_STANDBY)] = "TUNER_SET_STANDBY",
@@ -431,12 +430,6 @@ void v4l_printk_ioctl_arg(char *s,unsigned int cmd, void *arg)
431 printk ("%s: value=%d\n", s, *p); 430 printk ("%s: value=%d\n", s, *p);
432 break; 431 break;
433 } 432 }
434 case MSP_SET_MATRIX:
435 {
436 struct msp_matrix *p=arg;
437 printk ("%s: input=%d, output=%d\n", s, p->input, p->output);
438 break;
439 }
440 case VIDIOC_G_AUDIO: 433 case VIDIOC_G_AUDIO:
441 case VIDIOC_S_AUDIO: 434 case VIDIOC_S_AUDIO:
442 case VIDIOC_ENUMAUDIO: 435 case VIDIOC_ENUMAUDIO:
@@ -465,7 +458,7 @@ void v4l_printk_ioctl_arg(char *s,unsigned int cmd, void *arg)
465 struct v4l2_buffer *p=arg; 458 struct v4l2_buffer *p=arg;
466 struct v4l2_timecode *tc=&p->timecode; 459 struct v4l2_timecode *tc=&p->timecode;
467 printk ("%s: %02ld:%02d:%02d.%08ld index=%d, type=%s, " 460 printk ("%s: %02ld:%02d:%02d.%08ld index=%d, type=%s, "
468 "bytesused=%d, flags=0x%08d, " 461 "bytesused=%d, flags=0x%08x, "
469 "field=%0d, sequence=%d, memory=%s, offset/userptr=0x%08lx\n", 462 "field=%0d, sequence=%d, memory=%s, offset/userptr=0x%08lx\n",
470 s, 463 s,
471 (p->timestamp.tv_sec/3600), 464 (p->timestamp.tv_sec/3600),
@@ -479,7 +472,7 @@ void v4l_printk_ioctl_arg(char *s,unsigned int cmd, void *arg)
479 prt_names(p->memory,v4l2_memory_names), 472 prt_names(p->memory,v4l2_memory_names),
480 p->m.userptr); 473 p->m.userptr);
481 printk ("%s: timecode= %02d:%02d:%02d type=%d, " 474 printk ("%s: timecode= %02d:%02d:%02d type=%d, "
482 "flags=0x%08d, frames=%d, userbits=0x%p", 475 "flags=0x%08x, frames=%d, userbits=0x%08p\n",
483 s,tc->hours,tc->minutes,tc->seconds, 476 s,tc->hours,tc->minutes,tc->seconds,
484 tc->type, tc->flags, tc->frames, tc->userbits); 477 tc->type, tc->flags, tc->frames, tc->userbits);
485 break; 478 break;
@@ -665,7 +658,7 @@ void v4l_printk_ioctl_arg(char *s,unsigned int cmd, void *arg)
665 case VIDIOC_INT_G_VIDEO_ROUTING: 658 case VIDIOC_INT_G_VIDEO_ROUTING:
666 { 659 {
667 struct v4l2_routing *p=arg; 660 struct v4l2_routing *p=arg;
668 printk ("%s: input=%d, output=%d\n", s, p->input, p->output); 661 printk ("%s: input=0x%x, output=0x%x\n", s, p->input, p->output);
669 break; 662 break;
670 } 663 }
671 case VIDIOC_G_SLICED_VBI_CAP: 664 case VIDIOC_G_SLICED_VBI_CAP:
diff --git a/include/media/msp3400.h b/include/media/msp3400.h
index 26e26585273f..0be61a021d45 100644
--- a/include/media/msp3400.h
+++ b/include/media/msp3400.h
@@ -145,9 +145,14 @@
145 MSP_DSP_TO_SCART1(sc_i2s_src) | \ 145 MSP_DSP_TO_SCART1(sc_i2s_src) | \
146 MSP_DSP_TO_SCART2(sc_i2s_src) | \ 146 MSP_DSP_TO_SCART2(sc_i2s_src) | \
147 MSP_DSP_TO_I2S(sc_i2s_src)) 147 MSP_DSP_TO_I2S(sc_i2s_src))
148#define MSP_INPUT_DEFAULT MSP_INPUT(MSP_IN_SCART_1, MSP_IN_TUNER_1, \
149 MSP_DSP_OUT_TUNER, MSP_DSP_OUT_TUNER)
148#define MSP_OUTPUT(sc) \ 150#define MSP_OUTPUT(sc) \
149 (MSP_OUT_TO_SCART1(sc) | \ 151 (MSP_OUT_TO_SCART1(sc) | \
150 MSP_OUT_TO_SCART2(sc)) 152 MSP_OUT_TO_SCART2(sc))
153/* This equals the RESET position of the msp3400 ACB register */
154#define MSP_OUTPUT_DEFAULT (MSP_OUT_TO_SCART1(MSP_OUT_SCART3) | \
155 MSP_OUT_TO_SCART2(MSP_OUT_SCART1_DA))
151 156
152/* Tuner inputs vs. msp version */ 157/* Tuner inputs vs. msp version */
153/* Chip TUNER_1 TUNER_2 158/* Chip TUNER_1 TUNER_2
diff --git a/include/media/v4l2-common.h b/include/media/v4l2-common.h
index 07130474a0df..642520acdfa7 100644
--- a/include/media/v4l2-common.h
+++ b/include/media/v4l2-common.h
@@ -123,14 +123,6 @@ enum v4l2_chip_ident {
123/* v4l device was opened in Radio mode, to be replaced by VIDIOC_INT_S_TUNER_MODE */ 123/* v4l device was opened in Radio mode, to be replaced by VIDIOC_INT_S_TUNER_MODE */
124#define AUDC_SET_RADIO _IO('d',88) 124#define AUDC_SET_RADIO _IO('d',88)
125 125
126/* msp3400 ioctl: will be removed in the near future, to be replaced by
127 VIDIOC_INT_S_AUDIO_ROUTING. */
128struct msp_matrix {
129 int input;
130 int output;
131};
132#define MSP_SET_MATRIX _IOW('m',17,struct msp_matrix)
133
134/* tuner ioctls */ 126/* tuner ioctls */
135 127
136/* Sets tuner type and its I2C addr */ 128/* Sets tuner type and its I2C addr */