diff options
author | Thomas Kaiser <linux-dvb AT kaiser-linux.li> | 2006-04-27 20:45:20 -0400 |
---|---|---|
committer | Mauro Carvalho Chehab <mchehab@infradead.org> | 2006-06-25 00:59:46 -0400 |
commit | b8d4c235d50f8512bbc9d67730c24da3309b0307 (patch) | |
tree | 9af461a3b198bfd6856ab510044363b34a7d7be4 /drivers/media | |
parent | 21c2858235a81ce4fa1862432eb0c98d8dbdee1e (diff) |
V4L/DVB (3934): Support new dvb-ttusb-budget boards with stv0297
Added config switch to stv0297 to control i2c STOP during write behaviour.
Update frontend init in dvb-ttusb-budget.
Enable i2c STOP on other users of stv0297.
Signed-off-by: Thomas Kaiser <linux-dvb AT kaiser-linux.li>
Signed-off-by: Andrew de Quincey <adq_dvb@lidskialf.net>
Signed-off-by: Mauro Carvalho Chehab <mchehab@infradead.org>
Diffstat (limited to 'drivers/media')
-rw-r--r-- | drivers/media/dvb/frontends/stv0297.c | 49 | ||||
-rw-r--r-- | drivers/media/dvb/frontends/stv0297.h | 3 | ||||
-rw-r--r-- | drivers/media/dvb/ttpci/av7110.c | 1 | ||||
-rw-r--r-- | drivers/media/dvb/ttpci/budget-ci.c | 1 | ||||
-rw-r--r-- | drivers/media/dvb/ttusb-budget/Kconfig | 1 | ||||
-rw-r--r-- | drivers/media/dvb/ttusb-budget/dvb-ttusb-budget.c | 175 |
6 files changed, 212 insertions, 18 deletions
diff --git a/drivers/media/dvb/frontends/stv0297.c b/drivers/media/dvb/frontends/stv0297.c index c8c3b74f9958..98b95a205fd2 100644 --- a/drivers/media/dvb/frontends/stv0297.c +++ b/drivers/media/dvb/frontends/stv0297.c | |||
@@ -68,19 +68,25 @@ static int stv0297_readreg(struct stv0297_state *state, u8 reg) | |||
68 | int ret; | 68 | int ret; |
69 | u8 b0[] = { reg }; | 69 | u8 b0[] = { reg }; |
70 | u8 b1[] = { 0 }; | 70 | u8 b1[] = { 0 }; |
71 | struct i2c_msg msg[] = { {.addr = state->config->demod_address,.flags = 0,.buf = b0,.len = | 71 | struct i2c_msg msg[] = { {.addr = state->config->demod_address,.flags = 0,.buf = b0,.len = 1}, |
72 | 1}, | 72 | {.addr = state->config->demod_address,.flags = I2C_M_RD,.buf = b1,.len = 1} |
73 | {.addr = state->config->demod_address,.flags = I2C_M_RD,.buf = b1,.len = 1} | 73 | }; |
74 | }; | ||
75 | 74 | ||
76 | // this device needs a STOP between the register and data | 75 | // this device needs a STOP between the register and data |
77 | if ((ret = i2c_transfer(state->i2c, &msg[0], 1)) != 1) { | 76 | if (state->config->stop_during_read) { |
78 | dprintk("%s: readreg error (reg == 0x%02x, ret == %i)\n", __FUNCTION__, reg, ret); | 77 | if ((ret = i2c_transfer(state->i2c, &msg[0], 1)) != 1) { |
79 | return -1; | 78 | dprintk("%s: readreg error (reg == 0x%02x, ret == %i)\n", __FUNCTION__, reg, ret); |
80 | } | 79 | return -1; |
81 | if ((ret = i2c_transfer(state->i2c, &msg[1], 1)) != 1) { | 80 | } |
82 | dprintk("%s: readreg error (reg == 0x%02x, ret == %i)\n", __FUNCTION__, reg, ret); | 81 | if ((ret = i2c_transfer(state->i2c, &msg[1], 1)) != 1) { |
83 | return -1; | 82 | dprintk("%s: readreg error (reg == 0x%02x, ret == %i)\n", __FUNCTION__, reg, ret); |
83 | return -1; | ||
84 | } | ||
85 | } else { | ||
86 | if ((ret = i2c_transfer(state->i2c, msg, 2)) != 2) { | ||
87 | dprintk("%s: readreg error (reg == 0x%02x, ret == %i)\n", __FUNCTION__, reg, ret); | ||
88 | return -1; | ||
89 | } | ||
84 | } | 90 | } |
85 | 91 | ||
86 | return b1[0]; | 92 | return b1[0]; |
@@ -107,13 +113,20 @@ static int stv0297_readregs(struct stv0297_state *state, u8 reg1, u8 * b, u8 len | |||
107 | }; | 113 | }; |
108 | 114 | ||
109 | // this device needs a STOP between the register and data | 115 | // this device needs a STOP between the register and data |
110 | if ((ret = i2c_transfer(state->i2c, &msg[0], 1)) != 1) { | 116 | if (state->config->stop_during_read) { |
111 | dprintk("%s: readreg error (reg == 0x%02x, ret == %i)\n", __FUNCTION__, reg1, ret); | 117 | if ((ret = i2c_transfer(state->i2c, &msg[0], 1)) != 1) { |
112 | return -1; | 118 | dprintk("%s: readreg error (reg == 0x%02x, ret == %i)\n", __FUNCTION__, reg1, ret); |
113 | } | 119 | return -1; |
114 | if ((ret = i2c_transfer(state->i2c, &msg[1], 1)) != 1) { | 120 | } |
115 | dprintk("%s: readreg error (reg == 0x%02x, ret == %i)\n", __FUNCTION__, reg1, ret); | 121 | if ((ret = i2c_transfer(state->i2c, &msg[1], 1)) != 1) { |
116 | return -1; | 122 | dprintk("%s: readreg error (reg == 0x%02x, ret == %i)\n", __FUNCTION__, reg1, ret); |
123 | return -1; | ||
124 | } | ||
125 | } else { | ||
126 | if ((ret = i2c_transfer(state->i2c, msg, 2)) != 2) { | ||
127 | dprintk("%s: readreg error (reg == 0x%02x, ret == %i)\n", __FUNCTION__, reg1, ret); | ||
128 | return -1; | ||
129 | } | ||
117 | } | 130 | } |
118 | 131 | ||
119 | return 0; | 132 | return 0; |
diff --git a/drivers/media/dvb/frontends/stv0297.h b/drivers/media/dvb/frontends/stv0297.h index 8ff793c90038..1da5384fb985 100644 --- a/drivers/media/dvb/frontends/stv0297.h +++ b/drivers/media/dvb/frontends/stv0297.h | |||
@@ -37,6 +37,9 @@ struct stv0297_config | |||
37 | 37 | ||
38 | /* does the "inversion" need inverted? */ | 38 | /* does the "inversion" need inverted? */ |
39 | u8 invert:1; | 39 | u8 invert:1; |
40 | |||
41 | /* set to 1 if the device requires an i2c STOP during reading */ | ||
42 | u8 stop_during_read:1; | ||
40 | }; | 43 | }; |
41 | 44 | ||
42 | extern struct dvb_frontend* stv0297_attach(const struct stv0297_config* config, | 45 | extern struct dvb_frontend* stv0297_attach(const struct stv0297_config* config, |
diff --git a/drivers/media/dvb/ttpci/av7110.c b/drivers/media/dvb/ttpci/av7110.c index 1a6d7a3bf459..be0a04caf923 100644 --- a/drivers/media/dvb/ttpci/av7110.c +++ b/drivers/media/dvb/ttpci/av7110.c | |||
@@ -1859,6 +1859,7 @@ static struct stv0297_config nexusca_stv0297_config = { | |||
1859 | .demod_address = 0x1C, | 1859 | .demod_address = 0x1C, |
1860 | .inittab = nexusca_stv0297_inittab, | 1860 | .inittab = nexusca_stv0297_inittab, |
1861 | .invert = 1, | 1861 | .invert = 1, |
1862 | .stop_during_read = 1, | ||
1862 | }; | 1863 | }; |
1863 | 1864 | ||
1864 | 1865 | ||
diff --git a/drivers/media/dvb/ttpci/budget-ci.c b/drivers/media/dvb/ttpci/budget-ci.c index 145e12f9a7f6..eb03b140b05c 100644 --- a/drivers/media/dvb/ttpci/budget-ci.c +++ b/drivers/media/dvb/ttpci/budget-ci.c | |||
@@ -977,6 +977,7 @@ static struct stv0297_config dvbc_philips_tdm1316l_config = { | |||
977 | .demod_address = 0x1c, | 977 | .demod_address = 0x1c, |
978 | .inittab = dvbc_philips_tdm1316l_inittab, | 978 | .inittab = dvbc_philips_tdm1316l_inittab, |
979 | .invert = 0, | 979 | .invert = 0, |
980 | .stop_during_read = 1, | ||
980 | }; | 981 | }; |
981 | 982 | ||
982 | 983 | ||
diff --git a/drivers/media/dvb/ttusb-budget/Kconfig b/drivers/media/dvb/ttusb-budget/Kconfig index d1004e863290..92c7cdcf8981 100644 --- a/drivers/media/dvb/ttusb-budget/Kconfig +++ b/drivers/media/dvb/ttusb-budget/Kconfig | |||
@@ -6,6 +6,7 @@ config DVB_TTUSB_BUDGET | |||
6 | select DVB_VES1820 | 6 | select DVB_VES1820 |
7 | select DVB_TDA8083 | 7 | select DVB_TDA8083 |
8 | select DVB_STV0299 | 8 | select DVB_STV0299 |
9 | select DVB_STV0297 | ||
9 | select DVB_LNBP21 | 10 | select DVB_LNBP21 |
10 | help | 11 | help |
11 | Support for external USB adapters designed by Technotrend and | 12 | Support for external USB adapters designed by Technotrend and |
diff --git a/drivers/media/dvb/ttusb-budget/dvb-ttusb-budget.c b/drivers/media/dvb/ttusb-budget/dvb-ttusb-budget.c index 71581303b0ea..cf264512d36f 100644 --- a/drivers/media/dvb/ttusb-budget/dvb-ttusb-budget.c +++ b/drivers/media/dvb/ttusb-budget/dvb-ttusb-budget.c | |||
@@ -30,6 +30,7 @@ | |||
30 | #include "tda1004x.h" | 30 | #include "tda1004x.h" |
31 | #include "stv0299.h" | 31 | #include "stv0299.h" |
32 | #include "tda8083.h" | 32 | #include "tda8083.h" |
33 | #include "stv0297.h" | ||
33 | #include "lnbp21.h" | 34 | #include "lnbp21.h" |
34 | 35 | ||
35 | #include <linux/dvb/frontend.h> | 36 | #include <linux/dvb/frontend.h> |
@@ -1380,6 +1381,174 @@ static u8 read_pwm(struct ttusb* ttusb) | |||
1380 | } | 1381 | } |
1381 | 1382 | ||
1382 | 1383 | ||
1384 | static int dvbc_philips_tdm1316l_tuner_set_params(struct dvb_frontend *fe, struct dvb_frontend_parameters *params) | ||
1385 | { | ||
1386 | struct ttusb *ttusb = (struct ttusb *) fe->dvb->priv; | ||
1387 | u8 tuner_buf[5]; | ||
1388 | struct i2c_msg tuner_msg = {.addr = 0x60, | ||
1389 | .flags = 0, | ||
1390 | .buf = tuner_buf, | ||
1391 | .len = sizeof(tuner_buf) }; | ||
1392 | int tuner_frequency = 0; | ||
1393 | u8 band, cp, filter; | ||
1394 | |||
1395 | // determine charge pump | ||
1396 | tuner_frequency = params->frequency; | ||
1397 | if (tuner_frequency < 87000000) {return -EINVAL;} | ||
1398 | else if (tuner_frequency < 130000000) {cp = 3; band = 1;} | ||
1399 | else if (tuner_frequency < 160000000) {cp = 5; band = 1;} | ||
1400 | else if (tuner_frequency < 200000000) {cp = 6; band = 1;} | ||
1401 | else if (tuner_frequency < 290000000) {cp = 3; band = 2;} | ||
1402 | else if (tuner_frequency < 420000000) {cp = 5; band = 2;} | ||
1403 | else if (tuner_frequency < 480000000) {cp = 6; band = 2;} | ||
1404 | else if (tuner_frequency < 620000000) {cp = 3; band = 4;} | ||
1405 | else if (tuner_frequency < 830000000) {cp = 5; band = 4;} | ||
1406 | else if (tuner_frequency < 895000000) {cp = 7; band = 4;} | ||
1407 | else {return -EINVAL;} | ||
1408 | |||
1409 | // assume PLL filter should always be 8MHz for the moment. | ||
1410 | filter = 1; | ||
1411 | |||
1412 | // calculate divisor | ||
1413 | // (Finput + Fif)/Fref; Fif = 36125000 Hz, Fref = 62500 Hz | ||
1414 | tuner_frequency = ((params->frequency + 36125000) / 62500); | ||
1415 | |||
1416 | // setup tuner buffer | ||
1417 | tuner_buf[0] = tuner_frequency >> 8; | ||
1418 | tuner_buf[1] = tuner_frequency & 0xff; | ||
1419 | tuner_buf[2] = 0xc8; | ||
1420 | tuner_buf[3] = (cp << 5) | (filter << 3) | band; | ||
1421 | tuner_buf[4] = 0x80; | ||
1422 | |||
1423 | if (fe->ops->i2c_gate_ctrl) | ||
1424 | fe->ops->i2c_gate_ctrl(fe, 1); | ||
1425 | if (i2c_transfer(&ttusb->i2c_adap, &tuner_msg, 1) != 1) { | ||
1426 | printk("dvb-ttusb-budget: dvbc_philips_tdm1316l_pll_set Error 1\n"); | ||
1427 | return -EIO; | ||
1428 | } | ||
1429 | |||
1430 | msleep(50); | ||
1431 | |||
1432 | if (fe->ops->i2c_gate_ctrl) | ||
1433 | fe->ops->i2c_gate_ctrl(fe, 1); | ||
1434 | if (i2c_transfer(&ttusb->i2c_adap, &tuner_msg, 1) != 1) { | ||
1435 | printk("dvb-ttusb-budget: dvbc_philips_tdm1316l_pll_set Error 2\n"); | ||
1436 | return -EIO; | ||
1437 | } | ||
1438 | |||
1439 | msleep(1); | ||
1440 | |||
1441 | return 0; | ||
1442 | } | ||
1443 | |||
1444 | static u8 dvbc_philips_tdm1316l_inittab[] = { | ||
1445 | 0x80, 0x21, | ||
1446 | 0x80, 0x20, | ||
1447 | 0x81, 0x01, | ||
1448 | 0x81, 0x00, | ||
1449 | 0x00, 0x09, | ||
1450 | 0x01, 0x69, | ||
1451 | 0x03, 0x00, | ||
1452 | 0x04, 0x00, | ||
1453 | 0x07, 0x00, | ||
1454 | 0x08, 0x00, | ||
1455 | 0x20, 0x00, | ||
1456 | 0x21, 0x40, | ||
1457 | 0x22, 0x00, | ||
1458 | 0x23, 0x00, | ||
1459 | 0x24, 0x40, | ||
1460 | 0x25, 0x88, | ||
1461 | 0x30, 0xff, | ||
1462 | 0x31, 0x00, | ||
1463 | 0x32, 0xff, | ||
1464 | 0x33, 0x00, | ||
1465 | 0x34, 0x50, | ||
1466 | 0x35, 0x7f, | ||
1467 | 0x36, 0x00, | ||
1468 | 0x37, 0x20, | ||
1469 | 0x38, 0x00, | ||
1470 | 0x40, 0x1c, | ||
1471 | 0x41, 0xff, | ||
1472 | 0x42, 0x29, | ||
1473 | 0x43, 0x20, | ||
1474 | 0x44, 0xff, | ||
1475 | 0x45, 0x00, | ||
1476 | 0x46, 0x00, | ||
1477 | 0x49, 0x04, | ||
1478 | 0x4a, 0xff, | ||
1479 | 0x4b, 0x7f, | ||
1480 | 0x52, 0x30, | ||
1481 | 0x55, 0xae, | ||
1482 | 0x56, 0x47, | ||
1483 | 0x57, 0xe1, | ||
1484 | 0x58, 0x3a, | ||
1485 | 0x5a, 0x1e, | ||
1486 | 0x5b, 0x34, | ||
1487 | 0x60, 0x00, | ||
1488 | 0x63, 0x00, | ||
1489 | 0x64, 0x00, | ||
1490 | 0x65, 0x00, | ||
1491 | 0x66, 0x00, | ||
1492 | 0x67, 0x00, | ||
1493 | 0x68, 0x00, | ||
1494 | 0x69, 0x00, | ||
1495 | 0x6a, 0x02, | ||
1496 | 0x6b, 0x00, | ||
1497 | 0x70, 0xff, | ||
1498 | 0x71, 0x00, | ||
1499 | 0x72, 0x00, | ||
1500 | 0x73, 0x00, | ||
1501 | 0x74, 0x0c, | ||
1502 | 0x80, 0x00, | ||
1503 | 0x81, 0x00, | ||
1504 | 0x82, 0x00, | ||
1505 | 0x83, 0x00, | ||
1506 | 0x84, 0x04, | ||
1507 | 0x85, 0x80, | ||
1508 | 0x86, 0x24, | ||
1509 | 0x87, 0x78, | ||
1510 | 0x88, 0x00, | ||
1511 | 0x89, 0x00, | ||
1512 | 0x90, 0x01, | ||
1513 | 0x91, 0x01, | ||
1514 | 0xa0, 0x00, | ||
1515 | 0xa1, 0x00, | ||
1516 | 0xa2, 0x00, | ||
1517 | 0xb0, 0x91, | ||
1518 | 0xb1, 0x0b, | ||
1519 | 0xc0, 0x4b, | ||
1520 | 0xc1, 0x00, | ||
1521 | 0xc2, 0x00, | ||
1522 | 0xd0, 0x00, | ||
1523 | 0xd1, 0x00, | ||
1524 | 0xd2, 0x00, | ||
1525 | 0xd3, 0x00, | ||
1526 | 0xd4, 0x00, | ||
1527 | 0xd5, 0x00, | ||
1528 | 0xde, 0x00, | ||
1529 | 0xdf, 0x00, | ||
1530 | 0x61, 0x38, | ||
1531 | 0x62, 0x0a, | ||
1532 | 0x53, 0x13, | ||
1533 | 0x59, 0x08, | ||
1534 | 0x55, 0x00, | ||
1535 | 0x56, 0x40, | ||
1536 | 0x57, 0x08, | ||
1537 | 0x58, 0x3d, | ||
1538 | 0x88, 0x10, | ||
1539 | 0xa0, 0x00, | ||
1540 | 0xa0, 0x00, | ||
1541 | 0xa0, 0x00, | ||
1542 | 0xa0, 0x04, | ||
1543 | 0xff, 0xff, | ||
1544 | }; | ||
1545 | |||
1546 | static struct stv0297_config dvbc_philips_tdm1316l_config = { | ||
1547 | .demod_address = 0x1c, | ||
1548 | .inittab = dvbc_philips_tdm1316l_inittab, | ||
1549 | .invert = 0, | ||
1550 | }; | ||
1551 | |||
1383 | static void frontend_init(struct ttusb* ttusb) | 1552 | static void frontend_init(struct ttusb* ttusb) |
1384 | { | 1553 | { |
1385 | switch(le16_to_cpu(ttusb->dev->descriptor.idProduct)) { | 1554 | switch(le16_to_cpu(ttusb->dev->descriptor.idProduct)) { |
@@ -1413,6 +1582,12 @@ static void frontend_init(struct ttusb* ttusb) | |||
1413 | ttusb->fe->ops->tuner_ops.set_params = alps_tdbe2_tuner_set_params; | 1582 | ttusb->fe->ops->tuner_ops.set_params = alps_tdbe2_tuner_set_params; |
1414 | break; | 1583 | break; |
1415 | } | 1584 | } |
1585 | |||
1586 | ttusb->fe = stv0297_attach(&dvbc_philips_tdm1316l_config, &ttusb->i2c_adap); | ||
1587 | if (ttusb->fe != NULL) { | ||
1588 | ttusb->fe->ops->tuner_ops.set_params = dvbc_philips_tdm1316l_tuner_set_params; | ||
1589 | break; | ||
1590 | } | ||
1416 | break; | 1591 | break; |
1417 | 1592 | ||
1418 | case 0x1005: // Hauppauge/TT Nova-USB-t budget (tda10046/Philips td1316(tda6651tt) OR cx22700/ALPS TDMB7(??)) | 1593 | case 0x1005: // Hauppauge/TT Nova-USB-t budget (tda10046/Philips td1316(tda6651tt) OR cx22700/ALPS TDMB7(??)) |