0001
0002
0003
0004
0005
0006
0007
0008 #include "au0828.h"
0009 #include "au0828-cards.h"
0010 #include "au8522.h"
0011 #include "media/tuner.h"
0012 #include "media/v4l2-common.h"
0013
0014 static void hvr950q_cs5340_audio(void *priv, int enable)
0015 {
0016
0017
0018 struct au0828_dev *dev = priv;
0019 if (enable == 1)
0020 au0828_set(dev, REG_000, 0x10);
0021 else
0022 au0828_clear(dev, REG_000, 0x10);
0023 }
0024
0025
0026
0027
0028
0029
0030 struct au0828_board au0828_boards[] = {
0031 [AU0828_BOARD_UNKNOWN] = {
0032 .name = "Unknown board",
0033 .tuner_type = -1U,
0034 .tuner_addr = ADDR_UNSET,
0035 },
0036 [AU0828_BOARD_HAUPPAUGE_HVR850] = {
0037 .name = "Hauppauge HVR850",
0038 .tuner_type = TUNER_XC5000,
0039 .tuner_addr = 0x61,
0040 .has_ir_i2c = 1,
0041 .has_analog = 1,
0042 .i2c_clk_divider = AU0828_I2C_CLK_250KHZ,
0043 .input = {
0044 {
0045 .type = AU0828_VMUX_TELEVISION,
0046 .vmux = AU8522_COMPOSITE_CH4_SIF,
0047 .amux = AU8522_AUDIO_SIF,
0048 },
0049 {
0050 .type = AU0828_VMUX_COMPOSITE,
0051 .vmux = AU8522_COMPOSITE_CH1,
0052 .amux = AU8522_AUDIO_NONE,
0053 .audio_setup = hvr950q_cs5340_audio,
0054 },
0055 {
0056 .type = AU0828_VMUX_SVIDEO,
0057 .vmux = AU8522_SVIDEO_CH13,
0058 .amux = AU8522_AUDIO_NONE,
0059 .audio_setup = hvr950q_cs5340_audio,
0060 },
0061 },
0062 },
0063 [AU0828_BOARD_HAUPPAUGE_HVR950Q] = {
0064 .name = "Hauppauge HVR950Q",
0065 .tuner_type = TUNER_XC5000,
0066 .tuner_addr = 0x61,
0067 .has_ir_i2c = 1,
0068 .has_analog = 1,
0069 .i2c_clk_divider = AU0828_I2C_CLK_250KHZ,
0070 .input = {
0071 {
0072 .type = AU0828_VMUX_TELEVISION,
0073 .vmux = AU8522_COMPOSITE_CH4_SIF,
0074 .amux = AU8522_AUDIO_SIF,
0075 },
0076 {
0077 .type = AU0828_VMUX_COMPOSITE,
0078 .vmux = AU8522_COMPOSITE_CH1,
0079 .amux = AU8522_AUDIO_NONE,
0080 .audio_setup = hvr950q_cs5340_audio,
0081 },
0082 {
0083 .type = AU0828_VMUX_SVIDEO,
0084 .vmux = AU8522_SVIDEO_CH13,
0085 .amux = AU8522_AUDIO_NONE,
0086 .audio_setup = hvr950q_cs5340_audio,
0087 },
0088 },
0089 },
0090 [AU0828_BOARD_HAUPPAUGE_HVR950Q_MXL] = {
0091 .name = "Hauppauge HVR950Q rev xxF8",
0092 .tuner_type = TUNER_XC5000,
0093 .tuner_addr = 0x61,
0094 .i2c_clk_divider = AU0828_I2C_CLK_250KHZ,
0095 },
0096 [AU0828_BOARD_DVICO_FUSIONHDTV7] = {
0097 .name = "DViCO FusionHDTV USB",
0098 .tuner_type = TUNER_XC5000,
0099 .tuner_addr = 0x61,
0100 .i2c_clk_divider = AU0828_I2C_CLK_250KHZ,
0101 },
0102 [AU0828_BOARD_HAUPPAUGE_WOODBURY] = {
0103 .name = "Hauppauge Woodbury",
0104 .tuner_type = TUNER_NXP_TDA18271,
0105 .tuner_addr = 0x60,
0106 .i2c_clk_divider = AU0828_I2C_CLK_250KHZ,
0107 },
0108 };
0109
0110
0111
0112
0113 int au0828_tuner_callback(void *priv, int component, int command, int arg)
0114 {
0115 struct au0828_dev *dev = priv;
0116
0117 dprintk(1, "%s()\n", __func__);
0118
0119 switch (dev->boardnr) {
0120 case AU0828_BOARD_HAUPPAUGE_HVR850:
0121 case AU0828_BOARD_HAUPPAUGE_HVR950Q:
0122 case AU0828_BOARD_HAUPPAUGE_HVR950Q_MXL:
0123 case AU0828_BOARD_DVICO_FUSIONHDTV7:
0124 if (command == 0) {
0125
0126
0127 au0828_clear(dev, REG_001, 2);
0128 mdelay(10);
0129 au0828_set(dev, REG_001, 2);
0130 mdelay(10);
0131 return 0;
0132 } else {
0133 pr_err("%s(): Unknown command.\n", __func__);
0134 return -EINVAL;
0135 }
0136 break;
0137 }
0138
0139 return 0;
0140 }
0141
0142 static void hauppauge_eeprom(struct au0828_dev *dev, u8 *eeprom_data)
0143 {
0144 struct tveeprom tv;
0145
0146 tveeprom_hauppauge_analog(&tv, eeprom_data);
0147 dev->board.tuner_type = tv.tuner_type;
0148
0149
0150 switch (tv.model) {
0151 case 72000:
0152 case 72001:
0153 case 72101:
0154 case 72201:
0155 case 72211:
0156 case 72221:
0157 case 72231:
0158 case 72241:
0159 case 72251:
0160 case 72261:
0161 case 72271:
0162 case 72281:
0163 case 72301:
0164 case 72500:
0165 break;
0166 default:
0167 pr_warn("%s: warning: unknown hauppauge model #%d\n",
0168 __func__, tv.model);
0169 break;
0170 }
0171
0172 pr_info("%s: hauppauge eeprom: model=%d\n",
0173 __func__, tv.model);
0174 }
0175
0176 void au0828_card_analog_fe_setup(struct au0828_dev *dev);
0177
0178 void au0828_card_setup(struct au0828_dev *dev)
0179 {
0180 static u8 eeprom[256];
0181
0182 dprintk(1, "%s()\n", __func__);
0183
0184 if (dev->i2c_rc == 0) {
0185 dev->i2c_client.addr = 0xa0 >> 1;
0186 tveeprom_read(&dev->i2c_client, eeprom, sizeof(eeprom));
0187 }
0188
0189 switch (dev->boardnr) {
0190 case AU0828_BOARD_HAUPPAUGE_HVR850:
0191 case AU0828_BOARD_HAUPPAUGE_HVR950Q:
0192 case AU0828_BOARD_HAUPPAUGE_HVR950Q_MXL:
0193 case AU0828_BOARD_HAUPPAUGE_WOODBURY:
0194 if (dev->i2c_rc == 0)
0195 hauppauge_eeprom(dev, eeprom+0xa0);
0196 break;
0197 }
0198
0199 au0828_card_analog_fe_setup(dev);
0200 }
0201
0202 void au0828_card_analog_fe_setup(struct au0828_dev *dev)
0203 {
0204 #ifdef CONFIG_VIDEO_AU0828_V4L2
0205 struct tuner_setup tun_setup;
0206 struct v4l2_subdev *sd;
0207 unsigned int mode_mask = T_ANALOG_TV;
0208
0209 if (AUVI_INPUT(0).type != AU0828_VMUX_UNDEFINED) {
0210
0211
0212
0213 sd = v4l2_i2c_new_subdev(&dev->v4l2_dev, &dev->i2c_adap,
0214 "au8522", 0x8e >> 1, NULL);
0215 if (sd == NULL)
0216 pr_err("analog subdev registration failed\n");
0217 }
0218
0219
0220 if (dev->board.tuner_type != TUNER_ABSENT && dev->board.has_analog) {
0221
0222 sd = v4l2_i2c_new_subdev(&dev->v4l2_dev, &dev->i2c_adap,
0223 "tuner", dev->board.tuner_addr, NULL);
0224 if (sd == NULL)
0225 pr_err("tuner subdev registration fail\n");
0226
0227 tun_setup.mode_mask = mode_mask;
0228 tun_setup.type = dev->board.tuner_type;
0229 tun_setup.addr = dev->board.tuner_addr;
0230 tun_setup.tuner_callback = au0828_tuner_callback;
0231 v4l2_device_call_all(&dev->v4l2_dev, 0, tuner, s_type_addr,
0232 &tun_setup);
0233 }
0234 #endif
0235 }
0236
0237
0238
0239
0240
0241
0242 void au0828_gpio_setup(struct au0828_dev *dev)
0243 {
0244 dprintk(1, "%s()\n", __func__);
0245
0246 switch (dev->boardnr) {
0247 case AU0828_BOARD_HAUPPAUGE_HVR850:
0248 case AU0828_BOARD_HAUPPAUGE_HVR950Q:
0249 case AU0828_BOARD_HAUPPAUGE_HVR950Q_MXL:
0250 case AU0828_BOARD_HAUPPAUGE_WOODBURY:
0251
0252
0253
0254
0255
0256
0257
0258
0259
0260
0261
0262 au0828_write(dev, REG_003, 0x02);
0263 au0828_write(dev, REG_002, 0x80 | 0x20 | 0x10);
0264
0265
0266 au0828_write(dev, REG_001, 0x0);
0267 au0828_write(dev, REG_000, 0x0);
0268 msleep(50);
0269
0270
0271 au0828_write(dev, REG_000, 0x80);
0272 msleep(50);
0273
0274
0275
0276 au0828_write(dev, REG_001, 0x02);
0277 au0828_write(dev, REG_000, 0x80 | 0x20);
0278
0279 msleep(250);
0280 break;
0281 case AU0828_BOARD_DVICO_FUSIONHDTV7:
0282
0283
0284
0285
0286
0287
0288
0289 au0828_write(dev, REG_003, 0x02);
0290 au0828_write(dev, REG_002, 0xa0);
0291 au0828_write(dev, REG_001, 0x0);
0292 au0828_write(dev, REG_000, 0x0);
0293 msleep(100);
0294
0295
0296 au0828_write(dev, REG_003, 0x02);
0297 au0828_write(dev, REG_002, 0xa0);
0298 au0828_write(dev, REG_001, 0x02);
0299 au0828_write(dev, REG_000, 0xa0);
0300 msleep(250);
0301 break;
0302 }
0303 }
0304
0305
0306 struct usb_device_id au0828_usb_id_table[] = {
0307 { USB_DEVICE(0x2040, 0x7200),
0308 .driver_info = AU0828_BOARD_HAUPPAUGE_HVR950Q },
0309 { USB_DEVICE(0x2040, 0x7240),
0310 .driver_info = AU0828_BOARD_HAUPPAUGE_HVR850 },
0311 { USB_DEVICE(0x0fe9, 0xd620),
0312 .driver_info = AU0828_BOARD_DVICO_FUSIONHDTV7 },
0313 { USB_DEVICE(0x2040, 0x7210),
0314 .driver_info = AU0828_BOARD_HAUPPAUGE_HVR950Q },
0315 { USB_DEVICE(0x2040, 0x7217),
0316 .driver_info = AU0828_BOARD_HAUPPAUGE_HVR950Q },
0317 { USB_DEVICE(0x2040, 0x721b),
0318 .driver_info = AU0828_BOARD_HAUPPAUGE_HVR950Q },
0319 { USB_DEVICE(0x2040, 0x721e),
0320 .driver_info = AU0828_BOARD_HAUPPAUGE_HVR950Q },
0321 { USB_DEVICE(0x2040, 0x721f),
0322 .driver_info = AU0828_BOARD_HAUPPAUGE_HVR950Q },
0323 { USB_DEVICE(0x2040, 0x7280),
0324 .driver_info = AU0828_BOARD_HAUPPAUGE_HVR950Q },
0325 { USB_DEVICE(0x0fd9, 0x0008),
0326 .driver_info = AU0828_BOARD_HAUPPAUGE_HVR950Q },
0327 { USB_DEVICE(0x2040, 0x7201),
0328 .driver_info = AU0828_BOARD_HAUPPAUGE_HVR950Q_MXL },
0329 { USB_DEVICE(0x2040, 0x7211),
0330 .driver_info = AU0828_BOARD_HAUPPAUGE_HVR950Q_MXL },
0331 { USB_DEVICE(0x2040, 0x7281),
0332 .driver_info = AU0828_BOARD_HAUPPAUGE_HVR950Q_MXL },
0333 { USB_DEVICE(0x05e1, 0x0480),
0334 .driver_info = AU0828_BOARD_HAUPPAUGE_WOODBURY },
0335 { USB_DEVICE(0x2040, 0x8200),
0336 .driver_info = AU0828_BOARD_HAUPPAUGE_WOODBURY },
0337 { USB_DEVICE(0x2040, 0x7260),
0338 .driver_info = AU0828_BOARD_HAUPPAUGE_HVR950Q },
0339 { USB_DEVICE(0x2040, 0x7213),
0340 .driver_info = AU0828_BOARD_HAUPPAUGE_HVR950Q },
0341 { USB_DEVICE(0x2040, 0x7270),
0342 .driver_info = AU0828_BOARD_HAUPPAUGE_HVR950Q },
0343 { },
0344 };
0345
0346 MODULE_DEVICE_TABLE(usb, au0828_usb_id_table);