aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/media/dvb/frontends/tda10048.c
diff options
context:
space:
mode:
authorSteven Toth <stoth@kernellabs.com>2009-05-15 20:01:57 -0400
committerMauro Carvalho Chehab <mchehab@redhat.com>2009-06-16 17:21:13 -0400
commit9e08199770f28b92e5a85052e8c16cde94f9a2c9 (patch)
tree326535e36ede6c96f0e23466975f8db3915e726e /drivers/media/dvb/frontends/tda10048.c
parent6ecdf92d211fb37a905fce5d0a8668c831764abc (diff)
V4L/DVB (11854): TDA10048: Ensure the I/F changes during DVB-T 6/7/8 bandwidth changes.
TDA10048: Ensure the I/F changes during DVB-T 6/7/8 bandwidth changes. Signed-off-by: Steven Toth <stoth@kernellabs.com> Signed-off-by: Mauro Carvalho Chehab <mchehab@redhat.com>
Diffstat (limited to 'drivers/media/dvb/frontends/tda10048.c')
-rw-r--r--drivers/media/dvb/frontends/tda10048.c184
1 files changed, 123 insertions, 61 deletions
diff --git a/drivers/media/dvb/frontends/tda10048.c b/drivers/media/dvb/frontends/tda10048.c
index 11be4697cb3d..6707832bdcab 100644
--- a/drivers/media/dvb/frontends/tda10048.c
+++ b/drivers/media/dvb/frontends/tda10048.c
@@ -1,7 +1,7 @@
1/* 1/*
2 NXP TDA10048HN DVB OFDM demodulator driver 2 NXP TDA10048HN DVB OFDM demodulator driver
3 3
4 Copyright (C) 2008 Steven Toth <stoth@linuxtv.org> 4 Copyright (C) 2009 Steven Toth <stoth@kernellabs.com>
5 5
6 This program is free software; you can redistribute it and/or modify 6 This program is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by 7 it under the terms of the GNU General Public License as published by
@@ -139,8 +139,8 @@ struct tda10048_state {
139 139
140 struct i2c_adapter *i2c; 140 struct i2c_adapter *i2c;
141 141
142 /* configuration settings */ 142 /* We'll cache and update the attach config settings */
143 const struct tda10048_config *config; 143 struct tda10048_config config;
144 struct dvb_frontend frontend; 144 struct dvb_frontend frontend;
145 145
146 int fwloaded; 146 int fwloaded;
@@ -202,12 +202,24 @@ static struct init_tab {
202 { TDA10048_CONF_C4_2, 0x04 }, 202 { TDA10048_CONF_C4_2, 0x04 },
203}; 203};
204 204
205static struct pll_tab {
206 u32 clk_freq_khz;
207 u32 if_freq_khz;
208 u8 m, n, p;
209} pll_tab[] = {
210 { TDA10048_CLK_4000, TDA10048_IF_36130, 10, 0, 0 },
211 { TDA10048_CLK_16000, TDA10048_IF_4300, 10, 3, 0 },
212 { TDA10048_CLK_16000, TDA10048_IF_4000, 10, 3, 0 },
213 { TDA10048_CLK_16000, TDA10048_IF_36130, 10, 3, 0 },
214};
215
205static int tda10048_writereg(struct tda10048_state *state, u8 reg, u8 data) 216static int tda10048_writereg(struct tda10048_state *state, u8 reg, u8 data)
206{ 217{
218 struct tda10048_config *config = &state->config;
207 int ret; 219 int ret;
208 u8 buf[] = { reg, data }; 220 u8 buf[] = { reg, data };
209 struct i2c_msg msg = { 221 struct i2c_msg msg = {
210 .addr = state->config->demod_address, 222 .addr = config->demod_address,
211 .flags = 0, .buf = buf, .len = 2 }; 223 .flags = 0, .buf = buf, .len = 2 };
212 224
213 dprintk(2, "%s(reg = 0x%02x, data = 0x%02x)\n", __func__, reg, data); 225 dprintk(2, "%s(reg = 0x%02x, data = 0x%02x)\n", __func__, reg, data);
@@ -222,13 +234,14 @@ static int tda10048_writereg(struct tda10048_state *state, u8 reg, u8 data)
222 234
223static u8 tda10048_readreg(struct tda10048_state *state, u8 reg) 235static u8 tda10048_readreg(struct tda10048_state *state, u8 reg)
224{ 236{
237 struct tda10048_config *config = &state->config;
225 int ret; 238 int ret;
226 u8 b0[] = { reg }; 239 u8 b0[] = { reg };
227 u8 b1[] = { 0 }; 240 u8 b1[] = { 0 };
228 struct i2c_msg msg[] = { 241 struct i2c_msg msg[] = {
229 { .addr = state->config->demod_address, 242 { .addr = config->demod_address,
230 .flags = 0, .buf = b0, .len = 1 }, 243 .flags = 0, .buf = b0, .len = 1 },
231 { .addr = state->config->demod_address, 244 { .addr = config->demod_address,
232 .flags = I2C_M_RD, .buf = b1, .len = 1 } }; 245 .flags = I2C_M_RD, .buf = b1, .len = 1 } };
233 246
234 dprintk(2, "%s(reg = 0x%02x)\n", __func__, reg); 247 dprintk(2, "%s(reg = 0x%02x)\n", __func__, reg);
@@ -245,6 +258,7 @@ static u8 tda10048_readreg(struct tda10048_state *state, u8 reg)
245static int tda10048_writeregbulk(struct tda10048_state *state, u8 reg, 258static int tda10048_writeregbulk(struct tda10048_state *state, u8 reg,
246 const u8 *data, u16 len) 259 const u8 *data, u16 len)
247{ 260{
261 struct tda10048_config *config = &state->config;
248 int ret = -EREMOTEIO; 262 int ret = -EREMOTEIO;
249 struct i2c_msg msg; 263 struct i2c_msg msg;
250 u8 *buf; 264 u8 *buf;
@@ -260,7 +274,7 @@ static int tda10048_writeregbulk(struct tda10048_state *state, u8 reg,
260 *buf = reg; 274 *buf = reg;
261 memcpy(buf + 1, data, len); 275 memcpy(buf + 1, data, len);
262 276
263 msg.addr = state->config->demod_address; 277 msg.addr = config->demod_address;
264 msg.flags = 0; 278 msg.flags = 0;
265 msg.buf = buf; 279 msg.buf = buf;
266 msg.len = len + 1; 280 msg.len = len + 1;
@@ -411,47 +425,47 @@ static int tda10048_set_bandwidth(struct dvb_frontend *fe,
411 return 0; 425 return 0;
412} 426}
413 427
414static int tda10048_set_pll(struct dvb_frontend *fe) 428static int tda10048_set_if(struct dvb_frontend *fe, enum fe_bandwidth bw)
415{ 429{
416 struct tda10048_state *state = fe->demodulator_priv; 430 struct tda10048_state *state = fe->demodulator_priv;
417 int ret = 0; 431 struct tda10048_config *config = &state->config;
432 int i;
433 u32 if_freq_khz;
418 434
419 dprintk(1, "%s()\n", __func__); 435 dprintk(1, "%s(bw = %d)\n", __func__, bw);
420 436
421 if ((state->config->clk_freq_khz == TDA10048_CLK_4000) && 437 /* based on target bandwidth and clk we calculate pll factors */
422 (state->config->if_freq_khz == TDA10048_IF_36130)) { 438 switch (bw) {
423 state->freq_if_hz = TDA10048_IF_36130 * 1000; 439 case BANDWIDTH_6_MHZ:
424 state->xtal_hz = TDA10048_CLK_4000 * 1000; 440 if_freq_khz = config->dtv6_if_freq_khz;
425 state->pll_mfactor = 10; 441 break;
426 state->pll_nfactor = 0; 442 case BANDWIDTH_7_MHZ:
427 state->pll_pfactor = 0; 443 if_freq_khz = config->dtv7_if_freq_khz;
428 } else 444 break;
429 if ((state->config->clk_freq_khz == TDA10048_CLK_16000) && 445 case BANDWIDTH_8_MHZ:
430 (state->config->if_freq_khz == TDA10048_IF_4300)) { 446 if_freq_khz = config->dtv8_if_freq_khz;
431 state->freq_if_hz = TDA10048_IF_4300 * 1000; 447 break;
432 state->xtal_hz = TDA10048_CLK_16000 * 1000; 448 default:
433 state->pll_mfactor = 10; 449 printk(KERN_ERR "%s() no default\n", __func__);
434 state->pll_nfactor = 3; 450 return -EINVAL;
435 state->pll_pfactor = 0; 451 }
436 } else 452
437 if ((state->config->clk_freq_khz == TDA10048_CLK_16000) && 453 for (i = 0; i < ARRAY_SIZE(pll_tab); i++) {
438 (state->config->if_freq_khz == TDA10048_IF_4000)) { 454 if ((pll_tab[i].clk_freq_khz == config->clk_freq_khz) &&
439 state->freq_if_hz = TDA10048_IF_4000 * 1000; 455 (pll_tab[i].if_freq_khz == if_freq_khz)) {
440 state->xtal_hz = TDA10048_CLK_16000 * 1000; 456
441 state->pll_mfactor = 10; 457 state->freq_if_hz = pll_tab[i].if_freq_khz * 1000;
442 state->pll_nfactor = 3; 458 state->xtal_hz = pll_tab[i].clk_freq_khz * 1000;
443 state->pll_pfactor = 0; 459 state->pll_mfactor = pll_tab[i].m;
444 } else 460 state->pll_nfactor = pll_tab[i].n;
445 if ((state->config->clk_freq_khz == TDA10048_CLK_16000) && 461 state->pll_pfactor = pll_tab[i].p;
446 (state->config->if_freq_khz == TDA10048_IF_36130)) { 462 break;
447 state->freq_if_hz = TDA10048_IF_36130 * 1000; 463 }
448 state->xtal_hz = TDA10048_CLK_16000 * 1000; 464 }
449 state->pll_mfactor = 10; 465 if (i == ARRAY_SIZE(pll_tab)) {
450 state->pll_nfactor = 3; 466 printk(KERN_ERR "%s() Incorrect attach settings\n",
451 state->pll_pfactor = 0; 467 __func__);
452 } else { 468 return -EINVAL;
453 printk(KERN_ERR "%s() Incorrect attach settings\n", __func__);
454 ret = -EINVAL;
455 } 469 }
456 470
457 dprintk(1, "- freq_if_hz = %d\n", state->freq_if_hz); 471 dprintk(1, "- freq_if_hz = %d\n", state->freq_if_hz);
@@ -466,22 +480,21 @@ static int tda10048_set_pll(struct dvb_frontend *fe)
466 state->sample_freq /= (state->pll_pfactor + 4); 480 state->sample_freq /= (state->pll_pfactor + 4);
467 dprintk(1, "- sample_freq = %d\n", state->sample_freq); 481 dprintk(1, "- sample_freq = %d\n", state->sample_freq);
468 482
469 tda10048_set_phy2(fe, state->sample_freq, 483 /* Update the I/F */
470 state->config->if_freq_khz * 1000); 484 tda10048_set_phy2(fe, state->sample_freq, state->freq_if_hz);
471 tda10048_set_wref(fe, state->sample_freq, state->bandwidth);
472 tda10048_set_invwref(fe, state->sample_freq, state->bandwidth);
473 485
474 return ret; 486 return 0;
475} 487}
476 488
477static int tda10048_firmware_upload(struct dvb_frontend *fe) 489static int tda10048_firmware_upload(struct dvb_frontend *fe)
478{ 490{
479 struct tda10048_state *state = fe->demodulator_priv; 491 struct tda10048_state *state = fe->demodulator_priv;
492 struct tda10048_config *config = &state->config;
480 const struct firmware *fw; 493 const struct firmware *fw;
481 int ret; 494 int ret;
482 int pos = 0; 495 int pos = 0;
483 int cnt; 496 int cnt;
484 u8 wlen = state->config->fwbulkwritelen; 497 u8 wlen = config->fwbulkwritelen;
485 498
486 if ((wlen != TDA10048_BULKWRITE_200) && (wlen != TDA10048_BULKWRITE_50)) 499 if ((wlen != TDA10048_BULKWRITE_200) && (wlen != TDA10048_BULKWRITE_50))
487 wlen = TDA10048_BULKWRITE_200; 500 wlen = TDA10048_BULKWRITE_200;
@@ -687,9 +700,10 @@ static int tda10048_get_tps(struct tda10048_state *state,
687static int tda10048_i2c_gate_ctrl(struct dvb_frontend *fe, int enable) 700static int tda10048_i2c_gate_ctrl(struct dvb_frontend *fe, int enable)
688{ 701{
689 struct tda10048_state *state = fe->demodulator_priv; 702 struct tda10048_state *state = fe->demodulator_priv;
703 struct tda10048_config *config = &state->config;
690 dprintk(1, "%s(%d)\n", __func__, enable); 704 dprintk(1, "%s(%d)\n", __func__, enable);
691 705
692 if (state->config->disable_gate_access) 706 if (config->disable_gate_access)
693 return 0; 707 return 0;
694 708
695 if (enable) 709 if (enable)
@@ -729,8 +743,11 @@ static int tda10048_set_frontend(struct dvb_frontend *fe,
729 743
730 dprintk(1, "%s(frequency=%d)\n", __func__, p->frequency); 744 dprintk(1, "%s(frequency=%d)\n", __func__, p->frequency);
731 745
732 if (p->u.ofdm.bandwidth != state->bandwidth) 746 /* Update the I/F pll's if the bandwidth changes */
747 if (p->u.ofdm.bandwidth != state->bandwidth) {
748 tda10048_set_if(fe, p->u.ofdm.bandwidth);
733 tda10048_set_bandwidth(fe, p->u.ofdm.bandwidth); 749 tda10048_set_bandwidth(fe, p->u.ofdm.bandwidth);
750 }
734 751
735 if (fe->ops.tuner_ops.set_params) { 752 if (fe->ops.tuner_ops.set_params) {
736 753
@@ -753,6 +770,7 @@ static int tda10048_set_frontend(struct dvb_frontend *fe,
753static int tda10048_init(struct dvb_frontend *fe) 770static int tda10048_init(struct dvb_frontend *fe)
754{ 771{
755 struct tda10048_state *state = fe->demodulator_priv; 772 struct tda10048_state *state = fe->demodulator_priv;
773 struct tda10048_config *config = &state->config;
756 int ret = 0, i; 774 int ret = 0, i;
757 775
758 dprintk(1, "%s()\n", __func__); 776 dprintk(1, "%s()\n", __func__);
@@ -765,15 +783,13 @@ static int tda10048_init(struct dvb_frontend *fe)
765 ret = tda10048_firmware_upload(fe); 783 ret = tda10048_firmware_upload(fe);
766 784
767 /* Set either serial or parallel */ 785 /* Set either serial or parallel */
768 tda10048_output_mode(fe, state->config->output_mode); 786 tda10048_output_mode(fe, config->output_mode);
769 787
770 /* Set inversion */ 788 /* Set inversion */
771 tda10048_set_inversion(fe, state->config->inversion); 789 tda10048_set_inversion(fe, config->inversion);
772 790
773 /* Establish default PLL values */ 791 /* Establish default RF values */
774 tda10048_set_pll(fe); 792 tda10048_set_if(fe, BANDWIDTH_8_MHZ);
775
776 /* Establish default bandwidth */
777 tda10048_set_bandwidth(fe, BANDWIDTH_8_MHZ); 793 tda10048_set_bandwidth(fe, BANDWIDTH_8_MHZ);
778 794
779 /* Ensure we leave the gate closed */ 795 /* Ensure we leave the gate closed */
@@ -1027,6 +1043,45 @@ static void tda10048_release(struct dvb_frontend *fe)
1027 kfree(state); 1043 kfree(state);
1028} 1044}
1029 1045
1046static void tda10048_establish_defaults(struct dvb_frontend *fe)
1047{
1048 struct tda10048_state *state = fe->demodulator_priv;
1049 struct tda10048_config *config = &state->config;
1050
1051 /* Validate/default the config */
1052 if (config->dtv6_if_freq_khz == 0) {
1053 config->dtv6_if_freq_khz = TDA10048_IF_4300;
1054 printk(KERN_WARNING "%s() tda10048_config.dtv6_if_freq_khz "
1055 "is not set (defaulting to %d)\n",
1056 __func__,
1057 config->dtv6_if_freq_khz);
1058 }
1059
1060 if (config->dtv7_if_freq_khz == 0) {
1061 config->dtv7_if_freq_khz = TDA10048_IF_4300;
1062 printk(KERN_WARNING "%s() tda10048_config.dtv7_if_freq_khz "
1063 "is not set (defaulting to %d)\n",
1064 __func__,
1065 config->dtv7_if_freq_khz);
1066 }
1067
1068 if (config->dtv8_if_freq_khz == 0) {
1069 config->dtv8_if_freq_khz = TDA10048_IF_4300;
1070 printk(KERN_WARNING "%s() tda10048_config.dtv8_if_freq_khz "
1071 "is not set (defaulting to %d)\n",
1072 __func__,
1073 config->dtv8_if_freq_khz);
1074 }
1075
1076 if (config->clk_freq_khz == 0) {
1077 config->clk_freq_khz = TDA10048_CLK_16000;
1078 printk(KERN_WARNING "%s() tda10048_config.clk_freq_khz "
1079 "is not set (defaulting to %d)\n",
1080 __func__,
1081 config->clk_freq_khz);
1082 }
1083}
1084
1030static struct dvb_frontend_ops tda10048_ops; 1085static struct dvb_frontend_ops tda10048_ops;
1031 1086
1032struct dvb_frontend *tda10048_attach(const struct tda10048_config *config, 1087struct dvb_frontend *tda10048_attach(const struct tda10048_config *config,
@@ -1041,8 +1096,8 @@ struct dvb_frontend *tda10048_attach(const struct tda10048_config *config,
1041 if (state == NULL) 1096 if (state == NULL)
1042 goto error; 1097 goto error;
1043 1098
1044 /* setup the state */ 1099 /* setup the state and clone the config */
1045 state->config = config; 1100 memcpy(&state->config, config, sizeof(*config));
1046 state->i2c = i2c; 1101 state->i2c = i2c;
1047 state->fwloaded = 0; 1102 state->fwloaded = 0;
1048 state->bandwidth = BANDWIDTH_8_MHZ; 1103 state->bandwidth = BANDWIDTH_8_MHZ;
@@ -1056,8 +1111,15 @@ struct dvb_frontend *tda10048_attach(const struct tda10048_config *config,
1056 sizeof(struct dvb_frontend_ops)); 1111 sizeof(struct dvb_frontend_ops));
1057 state->frontend.demodulator_priv = state; 1112 state->frontend.demodulator_priv = state;
1058 1113
1114 /* Establish any defaults the the user didn't pass */
1115 tda10048_establish_defaults(&state->frontend);
1116
1059 /* Set the xtal and freq defaults */ 1117 /* Set the xtal and freq defaults */
1060 if (tda10048_set_pll(&state->frontend) != 0) 1118 if (tda10048_set_if(&state->frontend, BANDWIDTH_8_MHZ) != 0)
1119 goto error;
1120
1121 /* Default bandwidth */
1122 if (tda10048_set_bandwidth(&state->frontend, BANDWIDTH_8_MHZ) != 0)
1061 goto error; 1123 goto error;
1062 1124
1063 /* Leave the gate closed */ 1125 /* Leave the gate closed */