2 mxb - v4l2 driver for the Multimedia eXtension Board
4 Copyright (C) 1998-2006 Michael Hunold <michael@mihu.de>
6 Visit http://www.mihu.de/linux/saa7146/mxb/
7 for further details about this card.
9 This program is free software; you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
11 the Free Software Foundation; either version 2 of the License, or
12 (at your option) any later version.
14 This program is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
19 You should have received a copy of the GNU General Public License
20 along with this program; if not, write to the Free Software
21 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
24 #define DEBUG_VARIABLE debug
26 #include <media/saa7146_vv.h>
27 #include <media/tuner.h>
28 #include <linux/video_decoder.h>
29 #include <media/v4l2-common.h>
30 #include <media/saa7115.h>
37 #define I2C_SAA7111 0x24
39 #define MXB_BOARD_CAN_DO_VBI(dev) (dev->revision != 0)
44 /* initial frequence the tuner will be tuned to.
45 in verden (lower saxony, germany) 4148 is a
46 channel called "phoenix" */
47 static int freq = 4148;
48 module_param(freq, int, 0644);
49 MODULE_PARM_DESC(freq, "initial frequency the tuner will be tuned to while setup");
52 module_param(debug, int, 0644);
53 MODULE_PARM_DESC(debug, "Turn on/off device debugging (default:off).");
56 enum { TUNER, AUX1, AUX3, AUX3_YC };
58 static struct v4l2_input mxb_inputs[MXB_INPUTS] = {
59 { TUNER, "Tuner", V4L2_INPUT_TYPE_TUNER, 1, 0, V4L2_STD_PAL_BG|V4L2_STD_NTSC_M, 0 },
60 { AUX1, "AUX1", V4L2_INPUT_TYPE_CAMERA, 2, 0, V4L2_STD_PAL_BG|V4L2_STD_NTSC_M, 0 },
61 { AUX3, "AUX3 Composite", V4L2_INPUT_TYPE_CAMERA, 4, 0, V4L2_STD_PAL_BG|V4L2_STD_NTSC_M, 0 },
62 { AUX3_YC, "AUX3 S-Video", V4L2_INPUT_TYPE_CAMERA, 4, 0, V4L2_STD_PAL_BG|V4L2_STD_NTSC_M, 0 },
65 /* this array holds the information, which port of the saa7146 each
66 input actually uses. the mxb uses port 0 for every input */
70 } input_port_selection[MXB_INPUTS] = {
71 { SAA7146_HPS_SOURCE_PORT_A, SAA7146_HPS_SYNC_PORT_A },
72 { SAA7146_HPS_SOURCE_PORT_A, SAA7146_HPS_SYNC_PORT_A },
73 { SAA7146_HPS_SOURCE_PORT_A, SAA7146_HPS_SYNC_PORT_A },
74 { SAA7146_HPS_SOURCE_PORT_A, SAA7146_HPS_SYNC_PORT_A },
77 /* this array holds the information of the audio source (mxb_audios),
78 which has to be switched corresponding to the video source (mxb_channels) */
79 static int video_audio_connect[MXB_INPUTS] =
82 /* these are the necessary input-output-pins for bringing one audio source
83 (see above) to the CD-output */
84 static struct tea6420_multiplex TEA6420_cd[MXB_AUDIOS+1][2] =
86 {{1,1,0},{1,1,0}}, /* Tuner */
87 {{5,1,0},{6,1,0}}, /* AUX 1 */
88 {{4,1,0},{6,1,0}}, /* AUX 2 */
89 {{3,1,0},{6,1,0}}, /* AUX 3 */
90 {{1,1,0},{3,1,0}}, /* Radio */
91 {{1,1,0},{2,1,0}}, /* CD-Rom */
92 {{6,1,0},{6,1,0}} /* Mute */
95 /* these are the necessary input-output-pins for bringing one audio source
96 (see above) to the line-output */
97 static struct tea6420_multiplex TEA6420_line[MXB_AUDIOS+1][2] =
105 {{6,3,0},{6,2,0}} /* Mute */
108 #define MAXCONTROLS 1
109 static struct v4l2_queryctrl mxb_controls[] = {
110 { V4L2_CID_AUDIO_MUTE, V4L2_CTRL_TYPE_BOOLEAN, "Mute", 0, 1, 1, 0, 0 },
115 struct video_device *video_dev;
116 struct video_device *vbi_dev;
118 struct i2c_adapter i2c_adapter;
120 struct i2c_client *saa7111a;
121 struct i2c_client *tda9840;
122 struct i2c_client *tea6415c;
123 struct i2c_client *tuner;
124 struct i2c_client *tea6420_1;
125 struct i2c_client *tea6420_2;
127 int cur_mode; /* current audio mode (mono, stereo, ...) */
128 int cur_input; /* current input */
129 int cur_mute; /* current mute status */
130 struct v4l2_frequency cur_freq; /* current frequency the tuner is tuned to */
133 static struct saa7146_extension extension;
135 static int mxb_check_clients(struct device *dev, void *data)
137 struct mxb *mxb = data;
138 struct i2c_client *client = i2c_verify_client(dev);
143 if (I2C_ADDR_TEA6420_1 == client->addr)
144 mxb->tea6420_1 = client;
145 if (I2C_ADDR_TEA6420_2 == client->addr)
146 mxb->tea6420_2 = client;
147 if (I2C_TEA6415C_2 == client->addr)
148 mxb->tea6415c = client;
149 if (I2C_ADDR_TDA9840 == client->addr)
150 mxb->tda9840 = client;
151 if (I2C_SAA7111 == client->addr)
152 mxb->saa7111a = client;
153 if (0x60 == client->addr)
159 static int mxb_probe(struct saa7146_dev* dev)
161 struct mxb* mxb = NULL;
164 result = request_module("saa7115");
166 printk("mxb: saa7111 i2c module not available.\n");
169 result = request_module("tea6420");
171 printk("mxb: tea6420 i2c module not available.\n");
174 result = request_module("tea6415c");
176 printk("mxb: tea6415c i2c module not available.\n");
179 result = request_module("tda9840");
181 printk("mxb: tda9840 i2c module not available.\n");
184 result = request_module("tuner");
186 printk("mxb: tuner i2c module not available.\n");
190 mxb = kzalloc(sizeof(struct mxb), GFP_KERNEL);
192 DEB_D(("not enough kernel memory.\n"));
196 mxb->i2c_adapter = (struct i2c_adapter) {
197 .class = I2C_CLASS_TV_ANALOG,
200 snprintf(mxb->i2c_adapter.name, sizeof(mxb->i2c_adapter.name), "mxb%d", mxb_num);
202 saa7146_i2c_adapter_prepare(dev, &mxb->i2c_adapter, SAA7146_I2C_BUS_BIT_RATE_480);
203 if(i2c_add_adapter(&mxb->i2c_adapter) < 0) {
204 DEB_S(("cannot register i2c-device. skipping.\n"));
209 /* loop through all i2c-devices on the bus and look who is there */
210 device_for_each_child(&mxb->i2c_adapter.dev, mxb, mxb_check_clients);
212 /* check if all devices are present */
213 if (!mxb->tea6420_1 || !mxb->tea6420_2 || !mxb->tea6415c ||
214 !mxb->tda9840 || !mxb->saa7111a || !mxb->tuner) {
215 printk("mxb: did not find all i2c devices. aborting\n");
216 i2c_del_adapter(&mxb->i2c_adapter);
221 /* all devices are present, probe was successful */
223 /* we store the pointer in our private data field */
229 /* some init data for the saa7740, the so-called 'sound arena module'.
230 there are no specs available, so we simply use some init values */
234 } mxb_saa7740_init[] = {
235 { 3, { 0x80, 0x00, 0x00 } },{ 3, { 0x80, 0x89, 0x00 } },
236 { 3, { 0x80, 0xb0, 0x0a } },{ 3, { 0x00, 0x00, 0x00 } },
237 { 3, { 0x49, 0x00, 0x00 } },{ 3, { 0x4a, 0x00, 0x00 } },
238 { 3, { 0x4b, 0x00, 0x00 } },{ 3, { 0x4c, 0x00, 0x00 } },
239 { 3, { 0x4d, 0x00, 0x00 } },{ 3, { 0x4e, 0x00, 0x00 } },
240 { 3, { 0x4f, 0x00, 0x00 } },{ 3, { 0x50, 0x00, 0x00 } },
241 { 3, { 0x51, 0x00, 0x00 } },{ 3, { 0x52, 0x00, 0x00 } },
242 { 3, { 0x53, 0x00, 0x00 } },{ 3, { 0x54, 0x00, 0x00 } },
243 { 3, { 0x55, 0x00, 0x00 } },{ 3, { 0x56, 0x00, 0x00 } },
244 { 3, { 0x57, 0x00, 0x00 } },{ 3, { 0x58, 0x00, 0x00 } },
245 { 3, { 0x59, 0x00, 0x00 } },{ 3, { 0x5a, 0x00, 0x00 } },
246 { 3, { 0x5b, 0x00, 0x00 } },{ 3, { 0x5c, 0x00, 0x00 } },
247 { 3, { 0x5d, 0x00, 0x00 } },{ 3, { 0x5e, 0x00, 0x00 } },
248 { 3, { 0x5f, 0x00, 0x00 } },{ 3, { 0x60, 0x00, 0x00 } },
249 { 3, { 0x61, 0x00, 0x00 } },{ 3, { 0x62, 0x00, 0x00 } },
250 { 3, { 0x63, 0x00, 0x00 } },{ 3, { 0x64, 0x00, 0x00 } },
251 { 3, { 0x65, 0x00, 0x00 } },{ 3, { 0x66, 0x00, 0x00 } },
252 { 3, { 0x67, 0x00, 0x00 } },{ 3, { 0x68, 0x00, 0x00 } },
253 { 3, { 0x69, 0x00, 0x00 } },{ 3, { 0x6a, 0x00, 0x00 } },
254 { 3, { 0x6b, 0x00, 0x00 } },{ 3, { 0x6c, 0x00, 0x00 } },
255 { 3, { 0x6d, 0x00, 0x00 } },{ 3, { 0x6e, 0x00, 0x00 } },
256 { 3, { 0x6f, 0x00, 0x00 } },{ 3, { 0x70, 0x00, 0x00 } },
257 { 3, { 0x71, 0x00, 0x00 } },{ 3, { 0x72, 0x00, 0x00 } },
258 { 3, { 0x73, 0x00, 0x00 } },{ 3, { 0x74, 0x00, 0x00 } },
259 { 3, { 0x75, 0x00, 0x00 } },{ 3, { 0x76, 0x00, 0x00 } },
260 { 3, { 0x77, 0x00, 0x00 } },{ 3, { 0x41, 0x00, 0x42 } },
261 { 3, { 0x42, 0x10, 0x42 } },{ 3, { 0x43, 0x20, 0x42 } },
262 { 3, { 0x44, 0x30, 0x42 } },{ 3, { 0x45, 0x00, 0x01 } },
263 { 3, { 0x46, 0x00, 0x01 } },{ 3, { 0x47, 0x00, 0x01 } },
264 { 3, { 0x48, 0x00, 0x01 } },
265 { 9, { 0x01, 0x03, 0xc5, 0x5c, 0x7a, 0x85, 0x01, 0x00, 0x54 } },
266 { 9, { 0x21, 0x03, 0xc5, 0x5c, 0x7a, 0x85, 0x01, 0x00, 0x54 } },
267 { 9, { 0x09, 0x0b, 0xb4, 0x6b, 0x74, 0x85, 0x95, 0x00, 0x34 } },
268 { 9, { 0x29, 0x0b, 0xb4, 0x6b, 0x74, 0x85, 0x95, 0x00, 0x34 } },
269 { 9, { 0x11, 0x17, 0x43, 0x62, 0x68, 0x89, 0xd1, 0xff, 0xb0 } },
270 { 9, { 0x31, 0x17, 0x43, 0x62, 0x68, 0x89, 0xd1, 0xff, 0xb0 } },
271 { 9, { 0x19, 0x20, 0x62, 0x51, 0x5a, 0x95, 0x19, 0x01, 0x50 } },
272 { 9, { 0x39, 0x20, 0x62, 0x51, 0x5a, 0x95, 0x19, 0x01, 0x50 } },
273 { 9, { 0x05, 0x3e, 0xd2, 0x69, 0x4e, 0x9a, 0x51, 0x00, 0xf0 } },
274 { 9, { 0x25, 0x3e, 0xd2, 0x69, 0x4e, 0x9a, 0x51, 0x00, 0xf0 } },
275 { 9, { 0x0d, 0x3d, 0xa1, 0x40, 0x7d, 0x9f, 0x29, 0xfe, 0x14 } },
276 { 9, { 0x2d, 0x3d, 0xa1, 0x40, 0x7d, 0x9f, 0x29, 0xfe, 0x14 } },
277 { 9, { 0x15, 0x73, 0xa1, 0x50, 0x5d, 0xa6, 0xf5, 0xfe, 0x38 } },
278 { 9, { 0x35, 0x73, 0xa1, 0x50, 0x5d, 0xa6, 0xf5, 0xfe, 0x38 } },
279 { 9, { 0x1d, 0xed, 0xd0, 0x68, 0x29, 0xb4, 0xe1, 0x00, 0xb8 } },
280 { 9, { 0x3d, 0xed, 0xd0, 0x68, 0x29, 0xb4, 0xe1, 0x00, 0xb8 } },
281 { 3, { 0x80, 0xb3, 0x0a } },
285 /* bring hardware to a sane state. this has to be done, just in case someone
286 wants to capture from this device before it has been properly initialized.
287 the capture engine would badly fail, because no valid signal arrives on the
288 saa7146, thus leading to timeouts and stuff. */
289 static int mxb_init_done(struct saa7146_dev* dev)
291 struct mxb* mxb = (struct mxb*)dev->ext_priv;
293 struct tuner_setup tun_setup;
294 v4l2_std_id std = V4L2_STD_PAL_BG;
295 struct v4l2_routing route;
298 struct tea6415c_multiplex vm;
300 /* select video mode in saa7111a */
301 mxb->saa7111a->driver->command(mxb->saa7111a, VIDIOC_S_STD, &std);
303 /* select tuner-output on saa7111a */
305 route.input = SAA7115_COMPOSITE0;
306 route.output = SAA7111_FMT_CCIR | SAA7111_VBI_BYPASS;
307 mxb->saa7111a->driver->command(mxb->saa7111a, VIDIOC_INT_S_VIDEO_ROUTING, &route);
309 /* select a tuner type */
310 tun_setup.mode_mask = T_ANALOG_TV;
311 tun_setup.addr = ADDR_UNSET;
312 tun_setup.type = TUNER_PHILIPS_PAL;
313 mxb->tuner->driver->command(mxb->tuner, TUNER_SET_TYPE_ADDR, &tun_setup);
314 /* tune in some frequency on tuner */
315 mxb->cur_freq.tuner = 0;
316 mxb->cur_freq.type = V4L2_TUNER_ANALOG_TV;
317 mxb->cur_freq.frequency = freq;
318 mxb->tuner->driver->command(mxb->tuner, VIDIOC_S_FREQUENCY,
321 /* set a default video standard */
322 mxb->tuner->driver->command(mxb->tuner, VIDIOC_S_STD, &std);
324 /* mute audio on tea6420s */
325 mxb->tea6420_1->driver->command(mxb->tea6420_1, TEA6420_SWITCH, &TEA6420_line[6][0]);
326 mxb->tea6420_2->driver->command(mxb->tea6420_2, TEA6420_SWITCH, &TEA6420_line[6][1]);
327 mxb->tea6420_1->driver->command(mxb->tea6420_1, TEA6420_SWITCH, &TEA6420_cd[6][0]);
328 mxb->tea6420_2->driver->command(mxb->tea6420_2, TEA6420_SWITCH, &TEA6420_cd[6][1]);
330 /* switch to tuner-channel on tea6415c*/
333 mxb->tea6415c->driver->command(mxb->tea6415c, TEA6415C_SWITCH, &vm);
335 /* select tuner-output on multicable on tea6415c*/
338 mxb->tea6415c->driver->command(mxb->tea6415c, TEA6415C_SWITCH, &vm);
340 /* the rest for mxb */
344 mxb->cur_mode = V4L2_TUNER_MODE_STEREO;
346 /* check if the saa7740 (aka 'sound arena module') is present
347 on the mxb. if so, we must initialize it. due to lack of
348 informations about the saa7740, the values were reverse
352 msg.len = mxb_saa7740_init[0].length;
353 msg.buf = &mxb_saa7740_init[0].data[0];
355 err = i2c_transfer(&mxb->i2c_adapter, &msg, 1);
357 /* the sound arena module is a pos, that's probably the reason
358 philips refuses to hand out a datasheet for the saa7740...
359 it seems to screw up the i2c bus, so we disable fast irq
360 based i2c transactions here and rely on the slow and safe
361 polling method ... */
362 extension.flags &= ~SAA7146_USE_I2C_IRQ;
364 if (-1 == mxb_saa7740_init[i].length)
367 msg.len = mxb_saa7740_init[i].length;
368 msg.buf = &mxb_saa7740_init[i].data[0];
369 err = i2c_transfer(&mxb->i2c_adapter, &msg, 1);
371 DEB_D(("failed to initialize 'sound arena module'.\n"));
375 INFO(("'sound arena module' detected.\n"));
378 /* the rest for saa7146: you should definitely set some basic values
379 for the input-port handling of the saa7146. */
381 /* ext->saa has been filled by the core driver */
383 /* some stuff is done via variables */
384 saa7146_set_hps_source_and_sync(dev, input_port_selection[mxb->cur_input].hps_source,
385 input_port_selection[mxb->cur_input].hps_sync);
387 /* some stuff is done via direct write to the registers */
389 /* this is ugly, but because of the fact that this is completely
390 hardware dependend, it should be done directly... */
391 saa7146_write(dev, DD1_STREAM_B, 0x00000000);
392 saa7146_write(dev, DD1_INIT, 0x02000200);
393 saa7146_write(dev, MC2, (MASK_09 | MASK_25 | MASK_10 | MASK_26));
398 /* interrupt-handler. this gets called when irq_mask is != 0.
399 it must clear the interrupt-bits in irq_mask it has handled */
401 void mxb_irq_bh(struct saa7146_dev* dev, u32* irq_mask)
403 struct mxb* mxb = (struct mxb*)dev->ext_priv;
407 static int vidioc_queryctrl(struct file *file, void *fh, struct v4l2_queryctrl *qc)
409 struct saa7146_dev *dev = ((struct saa7146_fh *)fh)->dev;
412 for (i = MAXCONTROLS - 1; i >= 0; i--) {
413 if (mxb_controls[i].id == qc->id) {
414 *qc = mxb_controls[i];
415 DEB_D(("VIDIOC_QUERYCTRL %d.\n", qc->id));
419 return dev->ext_vv_data->core_ops->vidioc_queryctrl(file, fh, qc);
422 static int vidioc_g_ctrl(struct file *file, void *fh, struct v4l2_control *vc)
424 struct saa7146_dev *dev = ((struct saa7146_fh *)fh)->dev;
425 struct mxb *mxb = (struct mxb *)dev->ext_priv;
428 for (i = MAXCONTROLS - 1; i >= 0; i--) {
429 if (mxb_controls[i].id == vc->id)
434 return dev->ext_vv_data->core_ops->vidioc_g_ctrl(file, fh, vc);
436 if (vc->id == V4L2_CID_AUDIO_MUTE) {
437 vc->value = mxb->cur_mute;
438 DEB_D(("VIDIOC_G_CTRL V4L2_CID_AUDIO_MUTE:%d.\n", vc->value));
442 DEB_EE(("VIDIOC_G_CTRL V4L2_CID_AUDIO_MUTE:%d.\n", vc->value));
446 static int vidioc_s_ctrl(struct file *file, void *fh, struct v4l2_control *vc)
448 struct saa7146_dev *dev = ((struct saa7146_fh *)fh)->dev;
449 struct mxb *mxb = (struct mxb *)dev->ext_priv;
452 for (i = MAXCONTROLS - 1; i >= 0; i--) {
453 if (mxb_controls[i].id == vc->id)
458 return dev->ext_vv_data->core_ops->vidioc_s_ctrl(file, fh, vc);
460 if (vc->id == V4L2_CID_AUDIO_MUTE) {
461 mxb->cur_mute = vc->value;
463 /* switch the audio-source */
464 mxb->tea6420_1->driver->command(mxb->tea6420_1, TEA6420_SWITCH,
465 &TEA6420_line[video_audio_connect[mxb->cur_input]][0]);
466 mxb->tea6420_2->driver->command(mxb->tea6420_2, TEA6420_SWITCH,
467 &TEA6420_line[video_audio_connect[mxb->cur_input]][1]);
469 mxb->tea6420_1->driver->command(mxb->tea6420_1, TEA6420_SWITCH,
470 &TEA6420_line[6][0]);
471 mxb->tea6420_2->driver->command(mxb->tea6420_2, TEA6420_SWITCH,
472 &TEA6420_line[6][1]);
474 DEB_EE(("VIDIOC_S_CTRL, V4L2_CID_AUDIO_MUTE: %d.\n", vc->value));
479 static int vidioc_enum_input(struct file *file, void *fh, struct v4l2_input *i)
481 DEB_EE(("VIDIOC_ENUMINPUT %d.\n", i->index));
482 if (i->index < 0 || i->index >= MXB_INPUTS)
484 memcpy(i, &mxb_inputs[i->index], sizeof(struct v4l2_input));
488 static int vidioc_g_input(struct file *file, void *fh, unsigned int *i)
490 struct saa7146_dev *dev = ((struct saa7146_fh *)fh)->dev;
491 struct mxb *mxb = (struct mxb *)dev->ext_priv;
494 DEB_EE(("VIDIOC_G_INPUT %d.\n", *i));
498 static int vidioc_s_input(struct file *file, void *fh, unsigned int input)
500 struct saa7146_dev *dev = ((struct saa7146_fh *)fh)->dev;
501 struct mxb *mxb = (struct mxb *)dev->ext_priv;
502 struct tea6415c_multiplex vm;
503 struct v4l2_routing route;
506 DEB_EE(("VIDIOC_S_INPUT %d.\n", input));
508 if (input < 0 || input >= MXB_INPUTS)
511 mxb->cur_input = input;
513 saa7146_set_hps_source_and_sync(dev, input_port_selection[input].hps_source,
514 input_port_selection[input].hps_sync);
516 /* prepare switching of tea6415c and saa7111a;
517 have a look at the 'background'-file for further informations */
520 i = SAA7115_COMPOSITE0;
524 if (mxb->tea6415c->driver->command(mxb->tea6415c, TEA6415C_SWITCH, &vm)) {
525 printk(KERN_ERR "VIDIOC_S_INPUT: could not address tea6415c #1\n");
528 /* connect tuner-output always to multicable */
533 /* nothing to be done here. aux3_yc is
534 directly connected to the saa711a */
538 /* nothing to be done here. aux3 is
539 directly connected to the saa711a */
540 i = SAA7115_COMPOSITE1;
543 i = SAA7115_COMPOSITE0;
549 /* switch video in tea6415c only if necessary */
553 if (mxb->tea6415c->driver->command(mxb->tea6415c, TEA6415C_SWITCH, &vm)) {
554 printk(KERN_ERR "VIDIOC_S_INPUT: could not address tea6415c #3\n");
562 /* switch video in saa7111a */
565 if (mxb->saa7111a->driver->command(mxb->saa7111a, VIDIOC_INT_S_VIDEO_ROUTING, &route))
566 printk(KERN_ERR "VIDIOC_S_INPUT: could not address saa7111a #1.\n");
568 /* switch the audio-source only if necessary */
569 if (0 == mxb->cur_mute) {
570 mxb->tea6420_1->driver->command(mxb->tea6420_1, TEA6420_SWITCH,
571 &TEA6420_line[video_audio_connect[input]][0]);
572 mxb->tea6420_2->driver->command(mxb->tea6420_2, TEA6420_SWITCH,
573 &TEA6420_line[video_audio_connect[input]][1]);
579 static int vidioc_g_tuner(struct file *file, void *fh, struct v4l2_tuner *t)
581 struct saa7146_dev *dev = ((struct saa7146_fh *)fh)->dev;
582 struct mxb *mxb = (struct mxb *)dev->ext_priv;
585 DEB_D(("VIDIOC_G_TUNER: channel %d does not have a tuner attached.\n", t->index));
589 DEB_EE(("VIDIOC_G_TUNER: %d\n", t->index));
591 memset(t, 0, sizeof(*t));
592 i2c_clients_command(&mxb->i2c_adapter, VIDIOC_G_TUNER, t);
594 strlcpy(t->name, "TV Tuner", sizeof(t->name));
595 t->type = V4L2_TUNER_ANALOG_TV;
596 t->capability = V4L2_TUNER_CAP_NORM | V4L2_TUNER_CAP_STEREO |
597 V4L2_TUNER_CAP_LANG1 | V4L2_TUNER_CAP_LANG2 | V4L2_TUNER_CAP_SAP;
598 t->audmode = mxb->cur_mode;
602 static int vidioc_s_tuner(struct file *file, void *fh, struct v4l2_tuner *t)
604 struct saa7146_dev *dev = ((struct saa7146_fh *)fh)->dev;
605 struct mxb *mxb = (struct mxb *)dev->ext_priv;
608 DEB_D(("VIDIOC_S_TUNER: channel %d does not have a tuner attached.\n", t->index));
612 mxb->cur_mode = t->audmode;
613 i2c_clients_command(&mxb->i2c_adapter, VIDIOC_S_TUNER, t);
617 static int vidioc_g_frequency(struct file *file, void *fh, struct v4l2_frequency *f)
619 struct saa7146_dev *dev = ((struct saa7146_fh *)fh)->dev;
620 struct mxb *mxb = (struct mxb *)dev->ext_priv;
622 if (mxb->cur_input) {
623 DEB_D(("VIDIOC_G_FREQ: channel %d does not have a tuner!\n",
630 DEB_EE(("VIDIOC_G_FREQ: freq:0x%08x.\n", mxb->cur_freq.frequency));
634 static int vidioc_s_frequency(struct file *file, void *fh, struct v4l2_frequency *f)
636 struct saa7146_dev *dev = ((struct saa7146_fh *)fh)->dev;
637 struct mxb *mxb = (struct mxb *)dev->ext_priv;
638 struct saa7146_vv *vv = dev->vv_data;
643 if (V4L2_TUNER_ANALOG_TV != f->type)
646 if (mxb->cur_input) {
647 DEB_D(("VIDIOC_S_FREQ: channel %d does not have a tuner!\n", mxb->cur_input));
652 DEB_EE(("VIDIOC_S_FREQUENCY: freq:0x%08x.\n", mxb->cur_freq.frequency));
654 /* tune in desired frequency */
655 mxb->tuner->driver->command(mxb->tuner, VIDIOC_S_FREQUENCY, &mxb->cur_freq);
657 /* hack: changing the frequency should invalidate the vbi-counter (=> alevt) */
658 spin_lock(&dev->slock);
659 vv->vbi_fieldcount = 0;
660 spin_unlock(&dev->slock);
665 static int vidioc_g_audio(struct file *file, void *fh, struct v4l2_audio *a)
667 struct saa7146_dev *dev = ((struct saa7146_fh *)fh)->dev;
668 struct mxb *mxb = (struct mxb *)dev->ext_priv;
670 if (a->index < 0 || a->index > MXB_INPUTS) {
671 DEB_D(("VIDIOC_G_AUDIO %d out of range.\n", a->index));
675 DEB_EE(("VIDIOC_G_AUDIO %d.\n", a->index));
676 memcpy(a, &mxb_audios[video_audio_connect[mxb->cur_input]], sizeof(struct v4l2_audio));
680 static int vidioc_s_audio(struct file *file, void *fh, struct v4l2_audio *a)
682 DEB_D(("VIDIOC_S_AUDIO %d.\n", a->index));
686 #ifdef CONFIG_VIDEO_ADV_DEBUG
687 static int vidioc_g_register(struct file *file, void *fh, struct v4l2_dbg_register *reg)
689 struct saa7146_dev *dev = ((struct saa7146_fh *)fh)->dev;
690 struct mxb *mxb = (struct mxb *)dev->ext_priv;
692 i2c_clients_command(&mxb->i2c_adapter, VIDIOC_DBG_G_REGISTER, reg);
696 static int vidioc_s_register(struct file *file, void *fh, struct v4l2_dbg_register *reg)
698 struct saa7146_dev *dev = ((struct saa7146_fh *)fh)->dev;
699 struct mxb *mxb = (struct mxb *)dev->ext_priv;
701 i2c_clients_command(&mxb->i2c_adapter, VIDIOC_DBG_S_REGISTER, reg);
706 static long vidioc_default(struct file *file, void *fh, int cmd, void *arg)
708 struct saa7146_dev *dev = ((struct saa7146_fh *)fh)->dev;
709 struct mxb *mxb = (struct mxb *)dev->ext_priv;
716 if (i < 0 || i >= MXB_AUDIOS) {
717 DEB_D(("illegal argument to MXB_S_AUDIO_CD: i:%d.\n", i));
721 DEB_EE(("MXB_S_AUDIO_CD: i:%d.\n", i));
723 mxb->tea6420_1->driver->command(mxb->tea6420_1, TEA6420_SWITCH, &TEA6420_cd[i][0]);
724 mxb->tea6420_2->driver->command(mxb->tea6420_2, TEA6420_SWITCH, &TEA6420_cd[i][1]);
728 case MXB_S_AUDIO_LINE:
732 if (i < 0 || i >= MXB_AUDIOS) {
733 DEB_D(("illegal argument to MXB_S_AUDIO_LINE: i:%d.\n", i));
737 DEB_EE(("MXB_S_AUDIO_LINE: i:%d.\n", i));
738 mxb->tea6420_1->driver->command(mxb->tea6420_1, TEA6420_SWITCH, &TEA6420_line[i][0]);
739 mxb->tea6420_2->driver->command(mxb->tea6420_2, TEA6420_SWITCH, &TEA6420_line[i][1]);
745 DEB2(printk("does not handle this ioctl.\n"));
752 static struct saa7146_ext_vv vv_data;
754 /* this function only gets called when the probing was successful */
755 static int mxb_attach(struct saa7146_dev *dev, struct saa7146_pci_extension_data *info)
757 struct mxb *mxb = (struct mxb *)dev->ext_priv;
759 DEB_EE(("dev:%p\n", dev));
761 /* checking for i2c-devices can be omitted here, because we
762 already did this in "mxb_vl42_probe" */
764 saa7146_vv_init(dev, &vv_data);
765 vv_data.ops.vidioc_queryctrl = vidioc_queryctrl;
766 vv_data.ops.vidioc_g_ctrl = vidioc_g_ctrl;
767 vv_data.ops.vidioc_s_ctrl = vidioc_s_ctrl;
768 vv_data.ops.vidioc_enum_input = vidioc_enum_input;
769 vv_data.ops.vidioc_g_input = vidioc_g_input;
770 vv_data.ops.vidioc_s_input = vidioc_s_input;
771 vv_data.ops.vidioc_g_tuner = vidioc_g_tuner;
772 vv_data.ops.vidioc_s_tuner = vidioc_s_tuner;
773 vv_data.ops.vidioc_g_frequency = vidioc_g_frequency;
774 vv_data.ops.vidioc_s_frequency = vidioc_s_frequency;
775 vv_data.ops.vidioc_g_audio = vidioc_g_audio;
776 vv_data.ops.vidioc_s_audio = vidioc_s_audio;
777 #ifdef CONFIG_VIDEO_ADV_DEBUG
778 vv_data.ops.vidioc_g_register = vidioc_g_register;
779 vv_data.ops.vidioc_s_register = vidioc_s_register;
781 vv_data.ops.vidioc_default = vidioc_default;
782 if (saa7146_register_device(&mxb->video_dev, dev, "mxb", VFL_TYPE_GRABBER)) {
783 ERR(("cannot register capture v4l2 device. skipping.\n"));
787 /* initialization stuff (vbi) (only for revision > 0 and for extensions which want it)*/
788 if (MXB_BOARD_CAN_DO_VBI(dev)) {
789 if (saa7146_register_device(&mxb->vbi_dev, dev, "mxb", VFL_TYPE_VBI)) {
790 ERR(("cannot register vbi v4l2 device. skipping.\n"));
794 i2c_use_client(mxb->tea6420_1);
795 i2c_use_client(mxb->tea6420_2);
796 i2c_use_client(mxb->tea6415c);
797 i2c_use_client(mxb->tda9840);
798 i2c_use_client(mxb->saa7111a);
799 i2c_use_client(mxb->tuner);
801 printk("mxb: found Multimedia eXtension Board #%d.\n", mxb_num);
808 static int mxb_detach(struct saa7146_dev *dev)
810 struct mxb *mxb = (struct mxb *)dev->ext_priv;
812 DEB_EE(("dev:%p\n", dev));
814 i2c_release_client(mxb->tea6420_1);
815 i2c_release_client(mxb->tea6420_2);
816 i2c_release_client(mxb->tea6415c);
817 i2c_release_client(mxb->tda9840);
818 i2c_release_client(mxb->saa7111a);
819 i2c_release_client(mxb->tuner);
821 saa7146_unregister_device(&mxb->video_dev,dev);
822 if (MXB_BOARD_CAN_DO_VBI(dev))
823 saa7146_unregister_device(&mxb->vbi_dev, dev);
824 saa7146_vv_release(dev);
828 i2c_del_adapter(&mxb->i2c_adapter);
834 static int std_callback(struct saa7146_dev *dev, struct saa7146_standard *standard)
836 struct mxb *mxb = (struct mxb *)dev->ext_priv;
840 if (V4L2_STD_PAL_I == standard->id) {
841 v4l2_std_id std = V4L2_STD_PAL_I;
843 DEB_D(("VIDIOC_S_STD: setting mxb for PAL_I.\n"));
844 /* set the 7146 gpio register -- I don't know what this does exactly */
845 saa7146_write(dev, GPIO_CTRL, 0x00404050);
846 /* unset the 7111 gpio register -- I don't know what this does exactly */
847 mxb->saa7111a->driver->command(mxb->saa7111a, VIDIOC_INT_S_GPIO, &zero);
848 mxb->tuner->driver->command(mxb->tuner, VIDIOC_S_STD, &std);
850 v4l2_std_id std = V4L2_STD_PAL_BG;
852 DEB_D(("VIDIOC_S_STD: setting mxb for PAL/NTSC/SECAM.\n"));
853 /* set the 7146 gpio register -- I don't know what this does exactly */
854 saa7146_write(dev, GPIO_CTRL, 0x00404050);
855 /* set the 7111 gpio register -- I don't know what this does exactly */
856 mxb->saa7111a->driver->command(mxb->saa7111a, VIDIOC_INT_S_GPIO, &one);
857 mxb->tuner->driver->command(mxb->tuner, VIDIOC_S_STD, &std);
862 static struct saa7146_standard standard[] = {
864 .name = "PAL-BG", .id = V4L2_STD_PAL_BG,
865 .v_offset = 0x17, .v_field = 288,
866 .h_offset = 0x14, .h_pixels = 680,
867 .v_max_out = 576, .h_max_out = 768,
869 .name = "PAL-I", .id = V4L2_STD_PAL_I,
870 .v_offset = 0x17, .v_field = 288,
871 .h_offset = 0x14, .h_pixels = 680,
872 .v_max_out = 576, .h_max_out = 768,
874 .name = "NTSC", .id = V4L2_STD_NTSC,
875 .v_offset = 0x16, .v_field = 240,
876 .h_offset = 0x06, .h_pixels = 708,
877 .v_max_out = 480, .h_max_out = 640,
879 .name = "SECAM", .id = V4L2_STD_SECAM,
880 .v_offset = 0x14, .v_field = 288,
881 .h_offset = 0x14, .h_pixels = 720,
882 .v_max_out = 576, .h_max_out = 768,
886 static struct saa7146_pci_extension_data mxb = {
887 .ext_priv = "Multimedia eXtension Board",
891 static struct pci_device_id pci_tbl[] = {
893 .vendor = PCI_VENDOR_ID_PHILIPS,
894 .device = PCI_DEVICE_ID_PHILIPS_SAA7146,
897 .driver_data = (unsigned long)&mxb,
903 MODULE_DEVICE_TABLE(pci, pci_tbl);
905 static struct saa7146_ext_vv vv_data = {
906 .inputs = MXB_INPUTS,
907 .capabilities = V4L2_CAP_TUNER | V4L2_CAP_VBI_CAPTURE,
908 .stds = &standard[0],
909 .num_stds = sizeof(standard)/sizeof(struct saa7146_standard),
910 .std_callback = &std_callback,
913 static struct saa7146_extension extension = {
914 .name = MXB_IDENTIFIER,
915 .flags = SAA7146_USE_I2C_IRQ,
917 .pci_tbl = &pci_tbl[0],
918 .module = THIS_MODULE,
921 .attach = mxb_attach,
922 .detach = mxb_detach,
928 static int __init mxb_init_module(void)
930 if (saa7146_register_extension(&extension)) {
931 DEB_S(("failed to register extension.\n"));
938 static void __exit mxb_cleanup_module(void)
940 saa7146_unregister_extension(&extension);
943 module_init(mxb_init_module);
944 module_exit(mxb_cleanup_module);
946 MODULE_DESCRIPTION("video4linux-2 driver for the Siemens-Nixdorf 'Multimedia eXtension board'");
947 MODULE_AUTHOR("Michael Hunold <michael@mihu.de>");
948 MODULE_LICENSE("GPL");