aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/media/dvb/frontends
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/media/dvb/frontends')
-rw-r--r--drivers/media/dvb/frontends/Kconfig10
-rw-r--r--drivers/media/dvb/frontends/Makefile2
-rw-r--r--drivers/media/dvb/frontends/af9013.c2
-rw-r--r--drivers/media/dvb/frontends/atbm8830.c8
-rw-r--r--drivers/media/dvb/frontends/au8522_decoder.c51
-rw-r--r--drivers/media/dvb/frontends/au8522_priv.h2
-rw-r--r--drivers/media/dvb/frontends/dib7000m.c10
-rw-r--r--drivers/media/dvb/frontends/dib7000p.c10
-rw-r--r--drivers/media/dvb/frontends/ix2505v.c2
-rw-r--r--drivers/media/dvb/frontends/lgs8gxx.c11
-rw-r--r--drivers/media/dvb/frontends/mb86a20s.c615
-rw-r--r--drivers/media/dvb/frontends/mb86a20s.h52
-rw-r--r--drivers/media/dvb/frontends/s921.c548
-rw-r--r--drivers/media/dvb/frontends/s921.h47
-rw-r--r--drivers/media/dvb/frontends/s921_core.c216
-rw-r--r--drivers/media/dvb/frontends/s921_core.h114
-rw-r--r--drivers/media/dvb/frontends/s921_module.c192
-rw-r--r--drivers/media/dvb/frontends/s921_module.h49
-rw-r--r--drivers/media/dvb/frontends/stb0899_drv.c2
-rw-r--r--drivers/media/dvb/frontends/stb6100.c198
-rw-r--r--drivers/media/dvb/frontends/stv090x.c6
21 files changed, 1453 insertions, 694 deletions
diff --git a/drivers/media/dvb/frontends/Kconfig b/drivers/media/dvb/frontends/Kconfig
index 96b27016670e..ef3e43a03199 100644
--- a/drivers/media/dvb/frontends/Kconfig
+++ b/drivers/media/dvb/frontends/Kconfig
@@ -497,7 +497,7 @@ comment "ISDB-T (terrestrial) frontends"
497 depends on DVB_CORE 497 depends on DVB_CORE
498 498
499config DVB_S921 499config DVB_S921
500 tristate "Sharp S921 tuner" 500 tristate "Sharp S921 frontend"
501 depends on DVB_CORE && I2C 501 depends on DVB_CORE && I2C
502 default m if DVB_FE_CUSTOMISE 502 default m if DVB_FE_CUSTOMISE
503 help 503 help
@@ -512,6 +512,14 @@ config DVB_DIB8000
512 A driver for DiBcom's DiB8000 ISDB-T/ISDB-Tsb demodulator. 512 A driver for DiBcom's DiB8000 ISDB-T/ISDB-Tsb demodulator.
513 Say Y when you want to support this frontend. 513 Say Y when you want to support this frontend.
514 514
515config DVB_MB86A20S
516 tristate "Fujitsu mb86a20s"
517 depends on DVB_CORE && I2C
518 default m if DVB_FE_CUSTOMISE
519 help
520 A driver for Fujitsu mb86a20s ISDB-T/ISDB-Tsb demodulator.
521 Say Y when you want to support this frontend.
522
515comment "Digital terrestrial only tuners/PLL" 523comment "Digital terrestrial only tuners/PLL"
516 depends on DVB_CORE 524 depends on DVB_CORE
517 525
diff --git a/drivers/media/dvb/frontends/Makefile b/drivers/media/dvb/frontends/Makefile
index 9a31985c0dfb..b1d9525aa7e3 100644
--- a/drivers/media/dvb/frontends/Makefile
+++ b/drivers/media/dvb/frontends/Makefile
@@ -5,7 +5,6 @@
5EXTRA_CFLAGS += -Idrivers/media/dvb/dvb-core/ 5EXTRA_CFLAGS += -Idrivers/media/dvb/dvb-core/
6EXTRA_CFLAGS += -Idrivers/media/common/tuners/ 6EXTRA_CFLAGS += -Idrivers/media/common/tuners/
7 7
8s921-objs := s921_module.o s921_core.o
9stb0899-objs = stb0899_drv.o stb0899_algo.o 8stb0899-objs = stb0899_drv.o stb0899_algo.o
10stv0900-objs = stv0900_core.o stv0900_sw.o 9stv0900-objs = stv0900_core.o stv0900_sw.o
11au8522-objs = au8522_dig.o au8522_decoder.o 10au8522-objs = au8522_dig.o au8522_decoder.o
@@ -82,4 +81,5 @@ obj-$(CONFIG_DVB_ISL6423) += isl6423.o
82obj-$(CONFIG_DVB_EC100) += ec100.o 81obj-$(CONFIG_DVB_EC100) += ec100.o
83obj-$(CONFIG_DVB_DS3000) += ds3000.o 82obj-$(CONFIG_DVB_DS3000) += ds3000.o
84obj-$(CONFIG_DVB_MB86A16) += mb86a16.o 83obj-$(CONFIG_DVB_MB86A16) += mb86a16.o
84obj-$(CONFIG_DVB_MB86A20S) += mb86a20s.o
85obj-$(CONFIG_DVB_IX2505V) += ix2505v.o 85obj-$(CONFIG_DVB_IX2505V) += ix2505v.o
diff --git a/drivers/media/dvb/frontends/af9013.c b/drivers/media/dvb/frontends/af9013.c
index e2a95c07bab4..ce222055526d 100644
--- a/drivers/media/dvb/frontends/af9013.c
+++ b/drivers/media/dvb/frontends/af9013.c
@@ -964,7 +964,7 @@ error:
964static int af9013_update_signal_strength(struct dvb_frontend *fe) 964static int af9013_update_signal_strength(struct dvb_frontend *fe)
965{ 965{
966 struct af9013_state *state = fe->demodulator_priv; 966 struct af9013_state *state = fe->demodulator_priv;
967 int ret; 967 int ret = 0;
968 u8 rf_gain, if_gain; 968 u8 rf_gain, if_gain;
969 int signal_strength; 969 int signal_strength;
970 970
diff --git a/drivers/media/dvb/frontends/atbm8830.c b/drivers/media/dvb/frontends/atbm8830.c
index 43aac2f85c2e..1539ea1f81ac 100644
--- a/drivers/media/dvb/frontends/atbm8830.c
+++ b/drivers/media/dvb/frontends/atbm8830.c
@@ -50,8 +50,7 @@ static int atbm8830_write_reg(struct atbm_state *priv, u16 reg, u8 data)
50 msg2.addr = dev_addr; 50 msg2.addr = dev_addr;
51 51
52 if (debug >= 2) 52 if (debug >= 2)
53 printk(KERN_DEBUG "%s: reg=0x%04X, data=0x%02X\n", 53 dprintk("%s: reg=0x%04X, data=0x%02X\n", __func__, reg, data);
54 __func__, reg, data);
55 54
56 ret = i2c_transfer(priv->i2c, &msg1, 1); 55 ret = i2c_transfer(priv->i2c, &msg1, 1);
57 if (ret != 1) 56 if (ret != 1)
@@ -77,8 +76,7 @@ static int atbm8830_read_reg(struct atbm_state *priv, u16 reg, u8 *p_data)
77 76
78 ret = i2c_transfer(priv->i2c, &msg1, 1); 77 ret = i2c_transfer(priv->i2c, &msg1, 1);
79 if (ret != 1) { 78 if (ret != 1) {
80 dprintk(KERN_DEBUG "%s: error reg=0x%04x, ret=%i\n", 79 dprintk("%s: error reg=0x%04x, ret=%i\n", __func__, reg, ret);
81 __func__, reg, ret);
82 return -EIO; 80 return -EIO;
83 } 81 }
84 82
@@ -88,7 +86,7 @@ static int atbm8830_read_reg(struct atbm_state *priv, u16 reg, u8 *p_data)
88 86
89 *p_data = buf2[0]; 87 *p_data = buf2[0];
90 if (debug >= 2) 88 if (debug >= 2)
91 printk(KERN_DEBUG "%s: reg=0x%04X, data=0x%02X\n", 89 dprintk("%s: reg=0x%04X, data=0x%02X\n",
92 __func__, reg, buf2[0]); 90 __func__, reg, buf2[0]);
93 91
94 return 0; 92 return 0;
diff --git a/drivers/media/dvb/frontends/au8522_decoder.c b/drivers/media/dvb/frontends/au8522_decoder.c
index 6d9c5943eb3d..b537891a4cc9 100644
--- a/drivers/media/dvb/frontends/au8522_decoder.c
+++ b/drivers/media/dvb/frontends/au8522_decoder.c
@@ -278,10 +278,18 @@ static void setup_decoder_defaults(struct au8522_state *state, u8 input_mode)
278 AU8522_TVDEC_COMB_HDIF_THR2_REG06AH_CVBS); 278 AU8522_TVDEC_COMB_HDIF_THR2_REG06AH_CVBS);
279 au8522_writereg(state, AU8522_TVDEC_COMB_HDIF_THR3_REG06BH, 279 au8522_writereg(state, AU8522_TVDEC_COMB_HDIF_THR3_REG06BH,
280 AU8522_TVDEC_COMB_HDIF_THR3_REG06BH_CVBS); 280 AU8522_TVDEC_COMB_HDIF_THR3_REG06BH_CVBS);
281 au8522_writereg(state, AU8522_TVDEC_COMB_DCDIF_THR1_REG06CH, 281 if (input_mode == AU8522_INPUT_CONTROL_REG081H_SVIDEO_CH13 ||
282 AU8522_TVDEC_COMB_DCDIF_THR1_REG06CH_CVBS); 282 input_mode == AU8522_INPUT_CONTROL_REG081H_SVIDEO_CH24) {
283 au8522_writereg(state, AU8522_TVDEC_COMB_DCDIF_THR2_REG06DH, 283 au8522_writereg(state, AU8522_TVDEC_COMB_DCDIF_THR1_REG06CH,
284 AU8522_TVDEC_COMB_DCDIF_THR2_REG06DH_CVBS); 284 AU8522_TVDEC_COMB_DCDIF_THR1_REG06CH_SVIDEO);
285 au8522_writereg(state, AU8522_TVDEC_COMB_DCDIF_THR2_REG06DH,
286 AU8522_TVDEC_COMB_DCDIF_THR2_REG06DH_SVIDEO);
287 } else {
288 au8522_writereg(state, AU8522_TVDEC_COMB_DCDIF_THR1_REG06CH,
289 AU8522_TVDEC_COMB_DCDIF_THR1_REG06CH_CVBS);
290 au8522_writereg(state, AU8522_TVDEC_COMB_DCDIF_THR2_REG06DH,
291 AU8522_TVDEC_COMB_DCDIF_THR2_REG06DH_CVBS);
292 }
285 au8522_writereg(state, AU8522_TVDEC_COMB_DCDIF_THR3_REG06EH, 293 au8522_writereg(state, AU8522_TVDEC_COMB_DCDIF_THR3_REG06EH,
286 AU8522_TVDEC_COMB_DCDIF_THR3_REG06EH_CVBS); 294 AU8522_TVDEC_COMB_DCDIF_THR3_REG06EH_CVBS);
287 au8522_writereg(state, AU8522_TVDEC_UV_SEP_THR_REG06FH, 295 au8522_writereg(state, AU8522_TVDEC_UV_SEP_THR_REG06FH,
@@ -347,9 +355,11 @@ static void au8522_setup_cvbs_mode(struct au8522_state *state)
347 au8522_writereg(state, AU8522_MODULE_CLOCK_CONTROL_REG0A3H, 355 au8522_writereg(state, AU8522_MODULE_CLOCK_CONTROL_REG0A3H,
348 AU8522_MODULE_CLOCK_CONTROL_REG0A3H_CVBS); 356 AU8522_MODULE_CLOCK_CONTROL_REG0A3H_CVBS);
349 357
358 /* PGA in automatic mode */
350 au8522_writereg(state, AU8522_PGA_CONTROL_REG082H, 0x00); 359 au8522_writereg(state, AU8522_PGA_CONTROL_REG082H, 0x00);
351 au8522_writereg(state, AU8522_CLAMPING_CONTROL_REG083H, 0x0e); 360
352 au8522_writereg(state, AU8522_PGA_CONTROL_REG082H, 0x10); 361 /* Enable clamping control */
362 au8522_writereg(state, AU8522_CLAMPING_CONTROL_REG083H, 0x00);
353 363
354 au8522_writereg(state, AU8522_INPUT_CONTROL_REG081H, 364 au8522_writereg(state, AU8522_INPUT_CONTROL_REG081H,
355 AU8522_INPUT_CONTROL_REG081H_CVBS_CH1); 365 AU8522_INPUT_CONTROL_REG081H_CVBS_CH1);
@@ -366,14 +376,14 @@ static void au8522_setup_cvbs_tuner_mode(struct au8522_state *state)
366 au8522_writereg(state, AU8522_MODULE_CLOCK_CONTROL_REG0A3H, 376 au8522_writereg(state, AU8522_MODULE_CLOCK_CONTROL_REG0A3H,
367 AU8522_MODULE_CLOCK_CONTROL_REG0A3H_CVBS); 377 AU8522_MODULE_CLOCK_CONTROL_REG0A3H_CVBS);
368 378
369 /* It's not clear why they turn off the PGA before enabling the clamp 379 /* It's not clear why we have to have the PGA in automatic mode while
370 control, but the Windows trace does it so we will too... */ 380 enabling clamp control, but it's what Windows does */
371 au8522_writereg(state, AU8522_PGA_CONTROL_REG082H, 0x00); 381 au8522_writereg(state, AU8522_PGA_CONTROL_REG082H, 0x00);
372 382
373 /* Enable clamping control */ 383 /* Enable clamping control */
374 au8522_writereg(state, AU8522_CLAMPING_CONTROL_REG083H, 0x0e); 384 au8522_writereg(state, AU8522_CLAMPING_CONTROL_REG083H, 0x0e);
375 385
376 /* Turn on the PGA */ 386 /* Disable automatic PGA (since the CVBS is coming from the tuner) */
377 au8522_writereg(state, AU8522_PGA_CONTROL_REG082H, 0x10); 387 au8522_writereg(state, AU8522_PGA_CONTROL_REG082H, 0x10);
378 388
379 /* Set input mode to CVBS on channel 4 with SIF audio input enabled */ 389 /* Set input mode to CVBS on channel 4 with SIF audio input enabled */
@@ -396,7 +406,10 @@ static void au8522_setup_svideo_mode(struct au8522_state *state)
396 au8522_writereg(state, AU8522_INPUT_CONTROL_REG081H, 406 au8522_writereg(state, AU8522_INPUT_CONTROL_REG081H,
397 AU8522_INPUT_CONTROL_REG081H_SVIDEO_CH13); 407 AU8522_INPUT_CONTROL_REG081H_SVIDEO_CH13);
398 408
399 /* Disable clamping control (required for S-video) */ 409 /* PGA in automatic mode */
410 au8522_writereg(state, AU8522_PGA_CONTROL_REG082H, 0x00);
411
412 /* Enable clamping control */
400 au8522_writereg(state, AU8522_CLAMPING_CONTROL_REG083H, 0x00); 413 au8522_writereg(state, AU8522_CLAMPING_CONTROL_REG083H, 0x00);
401 414
402 setup_decoder_defaults(state, 415 setup_decoder_defaults(state,
@@ -410,29 +423,15 @@ static void au8522_setup_svideo_mode(struct au8522_state *state)
410 423
411static void disable_audio_input(struct au8522_state *state) 424static void disable_audio_input(struct au8522_state *state)
412{ 425{
413 /* This can probably be optimized */
414 au8522_writereg(state, AU8522_AUDIO_VOLUME_L_REG0F2H, 0x00); 426 au8522_writereg(state, AU8522_AUDIO_VOLUME_L_REG0F2H, 0x00);
415 au8522_writereg(state, AU8522_AUDIO_VOLUME_R_REG0F3H, 0x00); 427 au8522_writereg(state, AU8522_AUDIO_VOLUME_R_REG0F3H, 0x00);
416 au8522_writereg(state, AU8522_AUDIO_VOLUME_REG0F4H, 0x00); 428 au8522_writereg(state, AU8522_AUDIO_VOLUME_REG0F4H, 0x00);
417 au8522_writereg(state, AU8522_I2C_CONTROL_REG1_REG091H, 0x80);
418 au8522_writereg(state, AU8522_I2C_CONTROL_REG0_REG090H, 0x84);
419
420 au8522_writereg(state, AU8522_ENA_USB_REG101H, 0x00);
421 au8522_writereg(state, AU8522_AUDIO_VOLUME_L_REG0F2H, 0x7F);
422 au8522_writereg(state, AU8522_AUDIO_VOLUME_R_REG0F3H, 0x7F);
423 au8522_writereg(state, AU8522_REG0F9H, AU8522_REG0F9H_AUDIO);
424 au8522_writereg(state, AU8522_AUDIO_MODE_REG0F1H, 0x40);
425
426 au8522_writereg(state, AU8522_GPIO_DATA_REG0E2H, 0x11);
427 msleep(5);
428 au8522_writereg(state, AU8522_GPIO_DATA_REG0E2H, 0x00);
429 429
430 au8522_writereg(state, AU8522_SYSTEM_MODULE_CONTROL_1_REG0A5H, 0x04); 430 au8522_writereg(state, AU8522_SYSTEM_MODULE_CONTROL_1_REG0A5H, 0x04);
431 au8522_writereg(state, AU8522_AUDIOFREQ_REG606H, 0x03);
432 au8522_writereg(state, AU8522_I2S_CTRL_2_REG112H, 0x02); 431 au8522_writereg(state, AU8522_I2S_CTRL_2_REG112H, 0x02);
433 432
434 au8522_writereg(state, AU8522_SYSTEM_MODULE_CONTROL_0_REG0A4H, 433 au8522_writereg(state, AU8522_SYSTEM_MODULE_CONTROL_0_REG0A4H,
435 AU8522_SYSTEM_MODULE_CONTROL_0_REG0A4H_CVBS); 434 AU8522_SYSTEM_MODULE_CONTROL_0_REG0A4H_SVIDEO);
436} 435}
437 436
438/* 0=disable, 1=SIF */ 437/* 0=disable, 1=SIF */
@@ -622,7 +621,7 @@ static int au8522_queryctrl(struct v4l2_subdev *sd, struct v4l2_queryctrl *qc)
622 return v4l2_ctrl_query_fill(qc, 0, 255, 1, 621 return v4l2_ctrl_query_fill(qc, 0, 255, 1,
623 AU8522_TVDEC_CONTRAST_REG00BH_CVBS); 622 AU8522_TVDEC_CONTRAST_REG00BH_CVBS);
624 case V4L2_CID_BRIGHTNESS: 623 case V4L2_CID_BRIGHTNESS:
625 return v4l2_ctrl_query_fill(qc, 0, 255, 1, 128); 624 return v4l2_ctrl_query_fill(qc, 0, 255, 1, 109);
626 case V4L2_CID_SATURATION: 625 case V4L2_CID_SATURATION:
627 return v4l2_ctrl_query_fill(qc, 0, 255, 1, 128); 626 return v4l2_ctrl_query_fill(qc, 0, 255, 1, 128);
628 case V4L2_CID_HUE: 627 case V4L2_CID_HUE:
diff --git a/drivers/media/dvb/frontends/au8522_priv.h b/drivers/media/dvb/frontends/au8522_priv.h
index 609cf04bc312..751e17d692a9 100644
--- a/drivers/media/dvb/frontends/au8522_priv.h
+++ b/drivers/media/dvb/frontends/au8522_priv.h
@@ -397,7 +397,9 @@ void au8522_release_state(struct au8522_state *state);
397#define AU8522_TVDEC_COMB_HDIF_THR2_REG06AH_CVBS 0x0A 397#define AU8522_TVDEC_COMB_HDIF_THR2_REG06AH_CVBS 0x0A
398#define AU8522_TVDEC_COMB_HDIF_THR3_REG06BH_CVBS 0x32 398#define AU8522_TVDEC_COMB_HDIF_THR3_REG06BH_CVBS 0x32
399#define AU8522_TVDEC_COMB_DCDIF_THR1_REG06CH_CVBS 0x34 399#define AU8522_TVDEC_COMB_DCDIF_THR1_REG06CH_CVBS 0x34
400#define AU8522_TVDEC_COMB_DCDIF_THR1_REG06CH_SVIDEO 0x2a
400#define AU8522_TVDEC_COMB_DCDIF_THR2_REG06DH_CVBS 0x05 401#define AU8522_TVDEC_COMB_DCDIF_THR2_REG06DH_CVBS 0x05
402#define AU8522_TVDEC_COMB_DCDIF_THR2_REG06DH_SVIDEO 0x15
401#define AU8522_TVDEC_COMB_DCDIF_THR3_REG06EH_CVBS 0x6E 403#define AU8522_TVDEC_COMB_DCDIF_THR3_REG06EH_CVBS 0x6E
402#define AU8522_TVDEC_UV_SEP_THR_REG06FH_CVBS 0x0F 404#define AU8522_TVDEC_UV_SEP_THR_REG06FH_CVBS 0x0F
403#define AU8522_TVDEC_COMB_DC_THR1_NTSC_REG070H_CVBS 0x80 405#define AU8522_TVDEC_COMB_DC_THR1_NTSC_REG070H_CVBS 0x80
diff --git a/drivers/media/dvb/frontends/dib7000m.c b/drivers/media/dvb/frontends/dib7000m.c
index 0f09fd31cb29..c7f5ccf54aa5 100644
--- a/drivers/media/dvb/frontends/dib7000m.c
+++ b/drivers/media/dvb/frontends/dib7000m.c
@@ -805,7 +805,7 @@ static void dib7000m_set_channel(struct dib7000m_state *state, struct dvb_fronte
805 value = 0; 805 value = 0;
806 switch (ch->u.ofdm.transmission_mode) { 806 switch (ch->u.ofdm.transmission_mode) {
807 case TRANSMISSION_MODE_2K: value |= (0 << 7); break; 807 case TRANSMISSION_MODE_2K: value |= (0 << 7); break;
808 case /* 4K MODE */ 255: value |= (2 << 7); break; 808 case TRANSMISSION_MODE_4K: value |= (2 << 7); break;
809 default: 809 default:
810 case TRANSMISSION_MODE_8K: value |= (1 << 7); break; 810 case TRANSMISSION_MODE_8K: value |= (1 << 7); break;
811 } 811 }
@@ -866,7 +866,7 @@ static void dib7000m_set_channel(struct dib7000m_state *state, struct dvb_fronte
866 /* P_dvsy_sync_wait */ 866 /* P_dvsy_sync_wait */
867 switch (ch->u.ofdm.transmission_mode) { 867 switch (ch->u.ofdm.transmission_mode) {
868 case TRANSMISSION_MODE_8K: value = 256; break; 868 case TRANSMISSION_MODE_8K: value = 256; break;
869 case /* 4K MODE */ 255: value = 128; break; 869 case TRANSMISSION_MODE_4K: value = 128; break;
870 case TRANSMISSION_MODE_2K: 870 case TRANSMISSION_MODE_2K:
871 default: value = 64; break; 871 default: value = 64; break;
872 } 872 }
@@ -1020,7 +1020,7 @@ static int dib7000m_tune(struct dvb_frontend *demod, struct dvb_frontend_paramet
1020 value = (6 << 8) | 0x80; 1020 value = (6 << 8) | 0x80;
1021 switch (ch->u.ofdm.transmission_mode) { 1021 switch (ch->u.ofdm.transmission_mode) {
1022 case TRANSMISSION_MODE_2K: value |= (7 << 12); break; 1022 case TRANSMISSION_MODE_2K: value |= (7 << 12); break;
1023 case /* 4K MODE */ 255: value |= (8 << 12); break; 1023 case TRANSMISSION_MODE_4K: value |= (8 << 12); break;
1024 default: 1024 default:
1025 case TRANSMISSION_MODE_8K: value |= (9 << 12); break; 1025 case TRANSMISSION_MODE_8K: value |= (9 << 12); break;
1026 } 1026 }
@@ -1030,7 +1030,7 @@ static int dib7000m_tune(struct dvb_frontend *demod, struct dvb_frontend_paramet
1030 value = (0 << 4); 1030 value = (0 << 4);
1031 switch (ch->u.ofdm.transmission_mode) { 1031 switch (ch->u.ofdm.transmission_mode) {
1032 case TRANSMISSION_MODE_2K: value |= 0x6; break; 1032 case TRANSMISSION_MODE_2K: value |= 0x6; break;
1033 case /* 4K MODE */ 255: value |= 0x7; break; 1033 case TRANSMISSION_MODE_4K: value |= 0x7; break;
1034 default: 1034 default:
1035 case TRANSMISSION_MODE_8K: value |= 0x8; break; 1035 case TRANSMISSION_MODE_8K: value |= 0x8; break;
1036 } 1036 }
@@ -1040,7 +1040,7 @@ static int dib7000m_tune(struct dvb_frontend *demod, struct dvb_frontend_paramet
1040 value = (0 << 4); 1040 value = (0 << 4);
1041 switch (ch->u.ofdm.transmission_mode) { 1041 switch (ch->u.ofdm.transmission_mode) {
1042 case TRANSMISSION_MODE_2K: value |= 0x6; break; 1042 case TRANSMISSION_MODE_2K: value |= 0x6; break;
1043 case /* 4K MODE */ 255: value |= 0x7; break; 1043 case TRANSMISSION_MODE_4K: value |= 0x7; break;
1044 default: 1044 default:
1045 case TRANSMISSION_MODE_8K: value |= 0x8; break; 1045 case TRANSMISSION_MODE_8K: value |= 0x8; break;
1046 } 1046 }
diff --git a/drivers/media/dvb/frontends/dib7000p.c b/drivers/media/dvb/frontends/dib7000p.c
index 3aed0d433921..6aa02cb80733 100644
--- a/drivers/media/dvb/frontends/dib7000p.c
+++ b/drivers/media/dvb/frontends/dib7000p.c
@@ -717,7 +717,7 @@ static void dib7000p_set_channel(struct dib7000p_state *state, struct dvb_fronte
717 value = 0; 717 value = 0;
718 switch (ch->u.ofdm.transmission_mode) { 718 switch (ch->u.ofdm.transmission_mode) {
719 case TRANSMISSION_MODE_2K: value |= (0 << 7); break; 719 case TRANSMISSION_MODE_2K: value |= (0 << 7); break;
720 case /* 4K MODE */ 255: value |= (2 << 7); break; 720 case TRANSMISSION_MODE_4K: value |= (2 << 7); break;
721 default: 721 default:
722 case TRANSMISSION_MODE_8K: value |= (1 << 7); break; 722 case TRANSMISSION_MODE_8K: value |= (1 << 7); break;
723 } 723 }
@@ -770,7 +770,7 @@ static void dib7000p_set_channel(struct dib7000p_state *state, struct dvb_fronte
770 /* P_dvsy_sync_wait */ 770 /* P_dvsy_sync_wait */
771 switch (ch->u.ofdm.transmission_mode) { 771 switch (ch->u.ofdm.transmission_mode) {
772 case TRANSMISSION_MODE_8K: value = 256; break; 772 case TRANSMISSION_MODE_8K: value = 256; break;
773 case /* 4K MODE */ 255: value = 128; break; 773 case TRANSMISSION_MODE_4K: value = 128; break;
774 case TRANSMISSION_MODE_2K: 774 case TRANSMISSION_MODE_2K:
775 default: value = 64; break; 775 default: value = 64; break;
776 } 776 }
@@ -994,7 +994,7 @@ static int dib7000p_tune(struct dvb_frontend *demod, struct dvb_frontend_paramet
994 tmp = (6 << 8) | 0x80; 994 tmp = (6 << 8) | 0x80;
995 switch (ch->u.ofdm.transmission_mode) { 995 switch (ch->u.ofdm.transmission_mode) {
996 case TRANSMISSION_MODE_2K: tmp |= (7 << 12); break; 996 case TRANSMISSION_MODE_2K: tmp |= (7 << 12); break;
997 case /* 4K MODE */ 255: tmp |= (8 << 12); break; 997 case TRANSMISSION_MODE_4K: tmp |= (8 << 12); break;
998 default: 998 default:
999 case TRANSMISSION_MODE_8K: tmp |= (9 << 12); break; 999 case TRANSMISSION_MODE_8K: tmp |= (9 << 12); break;
1000 } 1000 }
@@ -1004,7 +1004,7 @@ static int dib7000p_tune(struct dvb_frontend *demod, struct dvb_frontend_paramet
1004 tmp = (0 << 4); 1004 tmp = (0 << 4);
1005 switch (ch->u.ofdm.transmission_mode) { 1005 switch (ch->u.ofdm.transmission_mode) {
1006 case TRANSMISSION_MODE_2K: tmp |= 0x6; break; 1006 case TRANSMISSION_MODE_2K: tmp |= 0x6; break;
1007 case /* 4K MODE */ 255: tmp |= 0x7; break; 1007 case TRANSMISSION_MODE_4K: tmp |= 0x7; break;
1008 default: 1008 default:
1009 case TRANSMISSION_MODE_8K: tmp |= 0x8; break; 1009 case TRANSMISSION_MODE_8K: tmp |= 0x8; break;
1010 } 1010 }
@@ -1014,7 +1014,7 @@ static int dib7000p_tune(struct dvb_frontend *demod, struct dvb_frontend_paramet
1014 tmp = (0 << 4); 1014 tmp = (0 << 4);
1015 switch (ch->u.ofdm.transmission_mode) { 1015 switch (ch->u.ofdm.transmission_mode) {
1016 case TRANSMISSION_MODE_2K: tmp |= 0x6; break; 1016 case TRANSMISSION_MODE_2K: tmp |= 0x6; break;
1017 case /* 4K MODE */ 255: tmp |= 0x7; break; 1017 case TRANSMISSION_MODE_4K: tmp |= 0x7; break;
1018 default: 1018 default:
1019 case TRANSMISSION_MODE_8K: tmp |= 0x8; break; 1019 case TRANSMISSION_MODE_8K: tmp |= 0x8; break;
1020 } 1020 }
diff --git a/drivers/media/dvb/frontends/ix2505v.c b/drivers/media/dvb/frontends/ix2505v.c
index 55f2eba7bc96..6360c681ded9 100644
--- a/drivers/media/dvb/frontends/ix2505v.c
+++ b/drivers/media/dvb/frontends/ix2505v.c
@@ -72,7 +72,7 @@ static int ix2505v_read_status_reg(struct ix2505v_state *state)
72 ret = i2c_transfer(state->i2c, msg, 1); 72 ret = i2c_transfer(state->i2c, msg, 1);
73 deb_i2c("Read %s ", __func__); 73 deb_i2c("Read %s ", __func__);
74 74
75 return (ret = 1) ? (int) b2[0] : -1; 75 return (ret == 1) ? (int) b2[0] : -1;
76} 76}
77 77
78static int ix2505v_write(struct ix2505v_state *state, u8 buf[], u8 count) 78static int ix2505v_write(struct ix2505v_state *state, u8 buf[], u8 count)
diff --git a/drivers/media/dvb/frontends/lgs8gxx.c b/drivers/media/dvb/frontends/lgs8gxx.c
index 0fcddc4569d2..1172b54689f8 100644
--- a/drivers/media/dvb/frontends/lgs8gxx.c
+++ b/drivers/media/dvb/frontends/lgs8gxx.c
@@ -60,13 +60,12 @@ static int lgs8gxx_write_reg(struct lgs8gxx_state *priv, u8 reg, u8 data)
60 msg.addr += 0x02; 60 msg.addr += 0x02;
61 61
62 if (debug >= 2) 62 if (debug >= 2)
63 printk(KERN_DEBUG "%s: reg=0x%02X, data=0x%02X\n", 63 dprintk("%s: reg=0x%02X, data=0x%02X\n", __func__, reg, data);
64 __func__, reg, data);
65 64
66 ret = i2c_transfer(priv->i2c, &msg, 1); 65 ret = i2c_transfer(priv->i2c, &msg, 1);
67 66
68 if (ret != 1) 67 if (ret != 1)
69 dprintk(KERN_DEBUG "%s: error reg=0x%x, data=0x%x, ret=%i\n", 68 dprintk("%s: error reg=0x%x, data=0x%x, ret=%i\n",
70 __func__, reg, data, ret); 69 __func__, reg, data, ret);
71 70
72 return (ret != 1) ? -1 : 0; 71 return (ret != 1) ? -1 : 0;
@@ -91,15 +90,13 @@ static int lgs8gxx_read_reg(struct lgs8gxx_state *priv, u8 reg, u8 *p_data)
91 90
92 ret = i2c_transfer(priv->i2c, msg, 2); 91 ret = i2c_transfer(priv->i2c, msg, 2);
93 if (ret != 2) { 92 if (ret != 2) {
94 dprintk(KERN_DEBUG "%s: error reg=0x%x, ret=%i\n", 93 dprintk("%s: error reg=0x%x, ret=%i\n", __func__, reg, ret);
95 __func__, reg, ret);
96 return -1; 94 return -1;
97 } 95 }
98 96
99 *p_data = b1[0]; 97 *p_data = b1[0];
100 if (debug >= 2) 98 if (debug >= 2)
101 printk(KERN_DEBUG "%s: reg=0x%02X, data=0x%02X\n", 99 dprintk("%s: reg=0x%02X, data=0x%02X\n", __func__, reg, b1[0]);
102 __func__, reg, b1[0]);
103 return 0; 100 return 0;
104} 101}
105 102
diff --git a/drivers/media/dvb/frontends/mb86a20s.c b/drivers/media/dvb/frontends/mb86a20s.c
new file mode 100644
index 000000000000..d3ad3e75a35a
--- /dev/null
+++ b/drivers/media/dvb/frontends/mb86a20s.c
@@ -0,0 +1,615 @@
1/*
2 * Fujitu mb86a20s ISDB-T/ISDB-Tsb Module driver
3 *
4 * Copyright (C) 2010 Mauro Carvalho Chehab <mchehab@redhat.com>
5 * Copyright (C) 2009-2010 Douglas Landgraf <dougsland@redhat.com>
6 *
7 * FIXME: Need to port to DVB v5.2 API
8 *
9 * This program is free software; you can redistribute it and/or
10 * modify it under the terms of the GNU General Public License as
11 * published by the Free Software Foundation version 2.
12 *
13 * This program is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 * General Public License for more details.
17 */
18
19#include <linux/kernel.h>
20#include <asm/div64.h>
21
22#include "dvb_frontend.h"
23#include "mb86a20s.h"
24
25static int debug = 1;
26module_param(debug, int, 0644);
27MODULE_PARM_DESC(debug, "Activates frontend debugging (default:0)");
28
29#define rc(args...) do { \
30 printk(KERN_ERR "mb86a20s: " args); \
31} while (0)
32
33#define dprintk(args...) \
34 do { \
35 if (debug) { \
36 printk(KERN_DEBUG "mb86a20s: %s: ", __func__); \
37 printk(args); \
38 } \
39 } while (0)
40
41struct mb86a20s_state {
42 struct i2c_adapter *i2c;
43 const struct mb86a20s_config *config;
44
45 struct dvb_frontend frontend;
46};
47
48struct regdata {
49 u8 reg;
50 u8 data;
51};
52
53/*
54 * Initialization sequence: Use whatevere default values that PV SBTVD
55 * does on its initialisation, obtained via USB snoop
56 */
57static struct regdata mb86a20s_init[] = {
58 { 0x70, 0x0f },
59 { 0x70, 0xff },
60 { 0x08, 0x01 },
61 { 0x09, 0x3e },
62 { 0x50, 0xd1 },
63 { 0x51, 0x22 },
64 { 0x39, 0x01 },
65 { 0x71, 0x00 },
66 { 0x28, 0x2a },
67 { 0x29, 0x00 },
68 { 0x2a, 0xff },
69 { 0x2b, 0x80 },
70 { 0x28, 0x20 },
71 { 0x29, 0x33 },
72 { 0x2a, 0xdf },
73 { 0x2b, 0xa9 },
74 { 0x3b, 0x21 },
75 { 0x3c, 0x3a },
76 { 0x01, 0x0d },
77 { 0x04, 0x08 },
78 { 0x05, 0x05 },
79 { 0x04, 0x0e },
80 { 0x05, 0x00 },
81 { 0x04, 0x0f },
82 { 0x05, 0x14 },
83 { 0x04, 0x0b },
84 { 0x05, 0x8c },
85 { 0x04, 0x00 },
86 { 0x05, 0x00 },
87 { 0x04, 0x01 },
88 { 0x05, 0x07 },
89 { 0x04, 0x02 },
90 { 0x05, 0x0f },
91 { 0x04, 0x03 },
92 { 0x05, 0xa0 },
93 { 0x04, 0x09 },
94 { 0x05, 0x00 },
95 { 0x04, 0x0a },
96 { 0x05, 0xff },
97 { 0x04, 0x27 },
98 { 0x05, 0x64 },
99 { 0x04, 0x28 },
100 { 0x05, 0x00 },
101 { 0x04, 0x1e },
102 { 0x05, 0xff },
103 { 0x04, 0x29 },
104 { 0x05, 0x0a },
105 { 0x04, 0x32 },
106 { 0x05, 0x0a },
107 { 0x04, 0x14 },
108 { 0x05, 0x02 },
109 { 0x04, 0x04 },
110 { 0x05, 0x00 },
111 { 0x04, 0x05 },
112 { 0x05, 0x22 },
113 { 0x04, 0x06 },
114 { 0x05, 0x0e },
115 { 0x04, 0x07 },
116 { 0x05, 0xd8 },
117 { 0x04, 0x12 },
118 { 0x05, 0x00 },
119 { 0x04, 0x13 },
120 { 0x05, 0xff },
121 { 0x52, 0x01 },
122 { 0x50, 0xa7 },
123 { 0x51, 0x00 },
124 { 0x50, 0xa8 },
125 { 0x51, 0xff },
126 { 0x50, 0xa9 },
127 { 0x51, 0xff },
128 { 0x50, 0xaa },
129 { 0x51, 0x00 },
130 { 0x50, 0xab },
131 { 0x51, 0xff },
132 { 0x50, 0xac },
133 { 0x51, 0xff },
134 { 0x50, 0xad },
135 { 0x51, 0x00 },
136 { 0x50, 0xae },
137 { 0x51, 0xff },
138 { 0x50, 0xaf },
139 { 0x51, 0xff },
140 { 0x5e, 0x07 },
141 { 0x50, 0xdc },
142 { 0x51, 0x01 },
143 { 0x50, 0xdd },
144 { 0x51, 0xf4 },
145 { 0x50, 0xde },
146 { 0x51, 0x01 },
147 { 0x50, 0xdf },
148 { 0x51, 0xf4 },
149 { 0x50, 0xe0 },
150 { 0x51, 0x01 },
151 { 0x50, 0xe1 },
152 { 0x51, 0xf4 },
153 { 0x50, 0xb0 },
154 { 0x51, 0x07 },
155 { 0x50, 0xb2 },
156 { 0x51, 0xff },
157 { 0x50, 0xb3 },
158 { 0x51, 0xff },
159 { 0x50, 0xb4 },
160 { 0x51, 0xff },
161 { 0x50, 0xb5 },
162 { 0x51, 0xff },
163 { 0x50, 0xb6 },
164 { 0x51, 0xff },
165 { 0x50, 0xb7 },
166 { 0x51, 0xff },
167 { 0x50, 0x50 },
168 { 0x51, 0x02 },
169 { 0x50, 0x51 },
170 { 0x51, 0x04 },
171 { 0x45, 0x04 },
172 { 0x48, 0x04 },
173 { 0x50, 0xd5 },
174 { 0x51, 0x01 }, /* Serial */
175 { 0x50, 0xd6 },
176 { 0x51, 0x1f },
177 { 0x50, 0xd2 },
178 { 0x51, 0x03 },
179 { 0x50, 0xd7 },
180 { 0x51, 0x3f },
181 { 0x1c, 0x01 },
182 { 0x28, 0x06 },
183 { 0x29, 0x00 },
184 { 0x2a, 0x00 },
185 { 0x2b, 0x03 },
186 { 0x28, 0x07 },
187 { 0x29, 0x00 },
188 { 0x2a, 0x00 },
189 { 0x2b, 0x0d },
190 { 0x28, 0x08 },
191 { 0x29, 0x00 },
192 { 0x2a, 0x00 },
193 { 0x2b, 0x02 },
194 { 0x28, 0x09 },
195 { 0x29, 0x00 },
196 { 0x2a, 0x00 },
197 { 0x2b, 0x01 },
198 { 0x28, 0x0a },
199 { 0x29, 0x00 },
200 { 0x2a, 0x00 },
201 { 0x2b, 0x21 },
202 { 0x28, 0x0b },
203 { 0x29, 0x00 },
204 { 0x2a, 0x00 },
205 { 0x2b, 0x29 },
206 { 0x28, 0x0c },
207 { 0x29, 0x00 },
208 { 0x2a, 0x00 },
209 { 0x2b, 0x16 },
210 { 0x28, 0x0d },
211 { 0x29, 0x00 },
212 { 0x2a, 0x00 },
213 { 0x2b, 0x31 },
214 { 0x28, 0x0e },
215 { 0x29, 0x00 },
216 { 0x2a, 0x00 },
217 { 0x2b, 0x0e },
218 { 0x28, 0x0f },
219 { 0x29, 0x00 },
220 { 0x2a, 0x00 },
221 { 0x2b, 0x4e },
222 { 0x28, 0x10 },
223 { 0x29, 0x00 },
224 { 0x2a, 0x00 },
225 { 0x2b, 0x46 },
226 { 0x28, 0x11 },
227 { 0x29, 0x00 },
228 { 0x2a, 0x00 },
229 { 0x2b, 0x0f },
230 { 0x28, 0x12 },
231 { 0x29, 0x00 },
232 { 0x2a, 0x00 },
233 { 0x2b, 0x56 },
234 { 0x28, 0x13 },
235 { 0x29, 0x00 },
236 { 0x2a, 0x00 },
237 { 0x2b, 0x35 },
238 { 0x28, 0x14 },
239 { 0x29, 0x00 },
240 { 0x2a, 0x01 },
241 { 0x2b, 0xbe },
242 { 0x28, 0x15 },
243 { 0x29, 0x00 },
244 { 0x2a, 0x01 },
245 { 0x2b, 0x84 },
246 { 0x28, 0x16 },
247 { 0x29, 0x00 },
248 { 0x2a, 0x03 },
249 { 0x2b, 0xee },
250 { 0x28, 0x17 },
251 { 0x29, 0x00 },
252 { 0x2a, 0x00 },
253 { 0x2b, 0x98 },
254 { 0x28, 0x18 },
255 { 0x29, 0x00 },
256 { 0x2a, 0x00 },
257 { 0x2b, 0x9f },
258 { 0x28, 0x19 },
259 { 0x29, 0x00 },
260 { 0x2a, 0x07 },
261 { 0x2b, 0xb2 },
262 { 0x28, 0x1a },
263 { 0x29, 0x00 },
264 { 0x2a, 0x06 },
265 { 0x2b, 0xc2 },
266 { 0x28, 0x1b },
267 { 0x29, 0x00 },
268 { 0x2a, 0x07 },
269 { 0x2b, 0x4a },
270 { 0x28, 0x1c },
271 { 0x29, 0x00 },
272 { 0x2a, 0x01 },
273 { 0x2b, 0xbc },
274 { 0x28, 0x1d },
275 { 0x29, 0x00 },
276 { 0x2a, 0x04 },
277 { 0x2b, 0xba },
278 { 0x28, 0x1e },
279 { 0x29, 0x00 },
280 { 0x2a, 0x06 },
281 { 0x2b, 0x14 },
282 { 0x50, 0x1e },
283 { 0x51, 0x5d },
284 { 0x50, 0x22 },
285 { 0x51, 0x00 },
286 { 0x50, 0x23 },
287 { 0x51, 0xc8 },
288 { 0x50, 0x24 },
289 { 0x51, 0x00 },
290 { 0x50, 0x25 },
291 { 0x51, 0xf0 },
292 { 0x50, 0x26 },
293 { 0x51, 0x00 },
294 { 0x50, 0x27 },
295 { 0x51, 0xc3 },
296 { 0x50, 0x39 },
297 { 0x51, 0x02 },
298 { 0x50, 0xd5 },
299 { 0x51, 0x01 },
300 { 0xd0, 0x00 },
301};
302
303static struct regdata mb86a20s_reset_reception[] = {
304 { 0x70, 0xf0 },
305 { 0x70, 0xff },
306 { 0x08, 0x01 },
307 { 0x08, 0x00 },
308};
309
310static int mb86a20s_i2c_writereg(struct mb86a20s_state *state,
311 u8 i2c_addr, int reg, int data)
312{
313 u8 buf[] = { reg, data };
314 struct i2c_msg msg = {
315 .addr = i2c_addr, .flags = 0, .buf = buf, .len = 2
316 };
317 int rc;
318
319 rc = i2c_transfer(state->i2c, &msg, 1);
320 if (rc != 1) {
321 printk("%s: writereg rcor(rc == %i, reg == 0x%02x,"
322 " data == 0x%02x)\n", __func__, rc, reg, data);
323 return rc;
324 }
325
326 return 0;
327}
328
329static int mb86a20s_i2c_writeregdata(struct mb86a20s_state *state,
330 u8 i2c_addr, struct regdata *rd, int size)
331{
332 int i, rc;
333
334 for (i = 0; i < size; i++) {
335 rc = mb86a20s_i2c_writereg(state, i2c_addr, rd[i].reg,
336 rd[i].data);
337 if (rc < 0)
338 return rc;
339 }
340 return 0;
341}
342
343static int mb86a20s_i2c_readreg(struct mb86a20s_state *state,
344 u8 i2c_addr, u8 reg)
345{
346 u8 val;
347 int rc;
348 struct i2c_msg msg[] = {
349 { .addr = i2c_addr, .flags = 0, .buf = &reg, .len = 1 },
350 { .addr = i2c_addr, .flags = I2C_M_RD, .buf = &val, .len = 1 }
351 };
352
353 rc = i2c_transfer(state->i2c, msg, 2);
354
355 if (rc != 2) {
356 rc("%s: reg=0x%x (rcor=%d)\n", __func__, reg, rc);
357 return rc;
358 }
359
360 return val;
361}
362
363#define mb86a20s_readreg(state, reg) \
364 mb86a20s_i2c_readreg(state, state->config->demod_address, reg)
365#define mb86a20s_writereg(state, reg, val) \
366 mb86a20s_i2c_writereg(state, state->config->demod_address, reg, val)
367#define mb86a20s_writeregdata(state, regdata) \
368 mb86a20s_i2c_writeregdata(state, state->config->demod_address, \
369 regdata, ARRAY_SIZE(regdata))
370
371static int mb86a20s_initfe(struct dvb_frontend *fe)
372{
373 struct mb86a20s_state *state = fe->demodulator_priv;
374 int rc;
375 u8 regD5 = 1;
376
377 dprintk("\n");
378
379 if (fe->ops.i2c_gate_ctrl)
380 fe->ops.i2c_gate_ctrl(fe, 0);
381
382 /* Initialize the frontend */
383 rc = mb86a20s_writeregdata(state, mb86a20s_init);
384 if (rc < 0)
385 return rc;
386
387 if (!state->config->is_serial) {
388 regD5 &= ~1;
389
390 rc = mb86a20s_writereg(state, 0x50, 0xd5);
391 if (rc < 0)
392 return rc;
393 rc = mb86a20s_writereg(state, 0x51, regD5);
394 if (rc < 0)
395 return rc;
396 }
397
398 if (fe->ops.i2c_gate_ctrl)
399 fe->ops.i2c_gate_ctrl(fe, 1);
400
401 return 0;
402}
403
404static int mb86a20s_read_signal_strength(struct dvb_frontend *fe, u16 *strength)
405{
406 struct mb86a20s_state *state = fe->demodulator_priv;
407 unsigned rf_max, rf_min, rf;
408 u8 val;
409
410 dprintk("\n");
411
412 if (fe->ops.i2c_gate_ctrl)
413 fe->ops.i2c_gate_ctrl(fe, 0);
414
415 /* Does a binary search to get RF strength */
416 rf_max = 0xfff;
417 rf_min = 0;
418 do {
419 rf = (rf_max + rf_min) / 2;
420 mb86a20s_writereg(state, 0x04, 0x1f);
421 mb86a20s_writereg(state, 0x05, rf >> 8);
422 mb86a20s_writereg(state, 0x04, 0x20);
423 mb86a20s_writereg(state, 0x04, rf);
424
425 val = mb86a20s_readreg(state, 0x02);
426 if (val & 0x08)
427 rf_min = (rf_max + rf_min) / 2;
428 else
429 rf_max = (rf_max + rf_min) / 2;
430 if (rf_max - rf_min < 4) {
431 *strength = (((rf_max + rf_min) / 2) * 65535) / 4095;
432 break;
433 }
434 } while (1);
435
436 dprintk("signal strength = %d\n", *strength);
437
438 if (fe->ops.i2c_gate_ctrl)
439 fe->ops.i2c_gate_ctrl(fe, 1);
440
441 return 0;
442}
443
444static int mb86a20s_read_status(struct dvb_frontend *fe, fe_status_t *status)
445{
446 struct mb86a20s_state *state = fe->demodulator_priv;
447 u8 val;
448
449 dprintk("\n");
450 *status = 0;
451
452 if (fe->ops.i2c_gate_ctrl)
453 fe->ops.i2c_gate_ctrl(fe, 0);
454 val = mb86a20s_readreg(state, 0x0a) & 0xf;
455 if (fe->ops.i2c_gate_ctrl)
456 fe->ops.i2c_gate_ctrl(fe, 1);
457
458 if (val >= 2)
459 *status |= FE_HAS_SIGNAL;
460
461 if (val >= 4)
462 *status |= FE_HAS_CARRIER;
463
464 if (val >= 5)
465 *status |= FE_HAS_VITERBI;
466
467 if (val >= 7)
468 *status |= FE_HAS_SYNC;
469
470 if (val >= 8) /* Maybe 9? */
471 *status |= FE_HAS_LOCK;
472
473 dprintk("val = %d, status = 0x%02x\n", val, *status);
474
475 return 0;
476}
477
478static int mb86a20s_set_frontend(struct dvb_frontend *fe,
479 struct dvb_frontend_parameters *p)
480{
481 struct mb86a20s_state *state = fe->demodulator_priv;
482 int rc;
483
484 dprintk("\n");
485
486 if (fe->ops.i2c_gate_ctrl)
487 fe->ops.i2c_gate_ctrl(fe, 1);
488 fe->ops.tuner_ops.set_params(fe, p);
489
490 if (fe->ops.i2c_gate_ctrl)
491 fe->ops.i2c_gate_ctrl(fe, 0);
492 rc = mb86a20s_writeregdata(state, mb86a20s_reset_reception);
493 if (fe->ops.i2c_gate_ctrl)
494 fe->ops.i2c_gate_ctrl(fe, 1);
495
496 return rc;
497}
498
499static int mb86a20s_get_frontend(struct dvb_frontend *fe,
500 struct dvb_frontend_parameters *p)
501{
502
503 /* FIXME: For now, it does nothing */
504
505 fe->dtv_property_cache.bandwidth_hz = 6000000;
506 fe->dtv_property_cache.transmission_mode = TRANSMISSION_MODE_AUTO;
507 fe->dtv_property_cache.guard_interval = GUARD_INTERVAL_AUTO;
508 fe->dtv_property_cache.isdbt_partial_reception = 0;
509
510 return 0;
511}
512
513static int mb86a20s_tune(struct dvb_frontend *fe,
514 struct dvb_frontend_parameters *params,
515 unsigned int mode_flags,
516 unsigned int *delay,
517 fe_status_t *status)
518{
519 int rc = 0;
520
521 dprintk("\n");
522
523 if (params != NULL)
524 rc = mb86a20s_set_frontend(fe, params);
525
526 if (!(mode_flags & FE_TUNE_MODE_ONESHOT))
527 mb86a20s_read_status(fe, status);
528
529 return rc;
530}
531
532static void mb86a20s_release(struct dvb_frontend *fe)
533{
534 struct mb86a20s_state *state = fe->demodulator_priv;
535
536 dprintk("\n");
537
538 kfree(state);
539}
540
541static struct dvb_frontend_ops mb86a20s_ops;
542
543struct dvb_frontend *mb86a20s_attach(const struct mb86a20s_config *config,
544 struct i2c_adapter *i2c)
545{
546 u8 rev;
547
548 /* allocate memory for the internal state */
549 struct mb86a20s_state *state =
550 kzalloc(sizeof(struct mb86a20s_state), GFP_KERNEL);
551
552 dprintk("\n");
553 if (state == NULL) {
554 rc("Unable to kzalloc\n");
555 goto error;
556 }
557
558 /* setup the state */
559 state->config = config;
560 state->i2c = i2c;
561
562 /* create dvb_frontend */
563 memcpy(&state->frontend.ops, &mb86a20s_ops,
564 sizeof(struct dvb_frontend_ops));
565 state->frontend.demodulator_priv = state;
566
567 /* Check if it is a mb86a20s frontend */
568 rev = mb86a20s_readreg(state, 0);
569
570 if (rev == 0x13) {
571 printk(KERN_INFO "Detected a Fujitsu mb86a20s frontend\n");
572 } else {
573 printk(KERN_ERR "Frontend revision %d is unknown - aborting.\n",
574 rev);
575 goto error;
576 }
577
578 return &state->frontend;
579
580error:
581 kfree(state);
582 return NULL;
583}
584EXPORT_SYMBOL(mb86a20s_attach);
585
586static struct dvb_frontend_ops mb86a20s_ops = {
587 /* Use dib8000 values per default */
588 .info = {
589 .name = "Fujitsu mb86A20s",
590 .type = FE_OFDM,
591 .caps = FE_CAN_INVERSION_AUTO | FE_CAN_RECOVER |
592 FE_CAN_FEC_1_2 | FE_CAN_FEC_2_3 | FE_CAN_FEC_3_4 |
593 FE_CAN_FEC_5_6 | FE_CAN_FEC_7_8 | FE_CAN_FEC_AUTO |
594 FE_CAN_QPSK | FE_CAN_QAM_16 | FE_CAN_QAM_64 |
595 FE_CAN_TRANSMISSION_MODE_AUTO | FE_CAN_QAM_AUTO |
596 FE_CAN_GUARD_INTERVAL_AUTO | FE_CAN_HIERARCHY_AUTO,
597 /* Actually, those values depend on the used tuner */
598 .frequency_min = 45000000,
599 .frequency_max = 864000000,
600 .frequency_stepsize = 62500,
601 },
602
603 .release = mb86a20s_release,
604
605 .init = mb86a20s_initfe,
606 .set_frontend = mb86a20s_set_frontend,
607 .get_frontend = mb86a20s_get_frontend,
608 .read_status = mb86a20s_read_status,
609 .read_signal_strength = mb86a20s_read_signal_strength,
610 .tune = mb86a20s_tune,
611};
612
613MODULE_DESCRIPTION("DVB Frontend module for Fujitsu mb86A20s hardware");
614MODULE_AUTHOR("Mauro Carvalho Chehab <mchehab@redhat.com>");
615MODULE_LICENSE("GPL");
diff --git a/drivers/media/dvb/frontends/mb86a20s.h b/drivers/media/dvb/frontends/mb86a20s.h
new file mode 100644
index 000000000000..bf22e77888b9
--- /dev/null
+++ b/drivers/media/dvb/frontends/mb86a20s.h
@@ -0,0 +1,52 @@
1/*
2 * Fujitsu mb86a20s driver
3 *
4 * Copyright (C) 2010 Mauro Carvalho Chehab <mchehab@redhat.com>
5 *
6 * This program is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU General Public License as
8 * published by the Free Software Foundation version 2.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 * General Public License for more details.
14 */
15
16#ifndef MB86A20S_H
17#define MB86A20S_H
18
19#include <linux/dvb/frontend.h>
20
21/**
22 * struct mb86a20s_config - Define the per-device attributes of the frontend
23 *
24 * @demod_address: the demodulator's i2c address
25 */
26
27struct mb86a20s_config {
28 u8 demod_address;
29 bool is_serial;
30};
31
32#if defined(CONFIG_DVB_MB86A20S) || (defined(CONFIG_DVB_MB86A20S_MODULE) \
33 && defined(MODULE))
34extern struct dvb_frontend *mb86a20s_attach(const struct mb86a20s_config *config,
35 struct i2c_adapter *i2c);
36extern struct i2c_adapter *mb86a20s_get_tuner_i2c_adapter(struct dvb_frontend *);
37#else
38static inline struct dvb_frontend *mb86a20s_attach(
39 const struct mb86a20s_config *config, struct i2c_adapter *i2c)
40{
41 printk(KERN_WARNING "%s: driver disabled by Kconfig\n", __func__);
42 return NULL;
43}
44static struct i2c_adapter *
45 mb86a20s_get_tuner_i2c_adapter(struct dvb_frontend *fe)
46{
47 printk(KERN_WARNING "%s: driver disabled by Kconfig\n", __func__);
48 return NULL;
49}
50#endif
51
52#endif /* MB86A20S */
diff --git a/drivers/media/dvb/frontends/s921.c b/drivers/media/dvb/frontends/s921.c
new file mode 100644
index 000000000000..ca0103d5f148
--- /dev/null
+++ b/drivers/media/dvb/frontends/s921.c
@@ -0,0 +1,548 @@
1/*
2 * Sharp VA3A5JZ921 One Seg Broadcast Module driver
3 * This device is labeled as just S. 921 at the top of the frontend can
4 *
5 * Copyright (C) 2009-2010 Mauro Carvalho Chehab <mchehab@redhat.com>
6 * Copyright (C) 2009-2010 Douglas Landgraf <dougsland@redhat.com>
7 *
8 * Developed for Leadership SBTVD 1seg device sold in Brazil
9 *
10 * Frontend module based on cx24123 driver, getting some info from
11 * the old s921 driver.
12 *
13 * FIXME: Need to port to DVB v5.2 API
14 *
15 * This program is free software; you can redistribute it and/or
16 * modify it under the terms of the GNU General Public License as
17 * published by the Free Software Foundation version 2.
18 *
19 * This program is distributed in the hope that it will be useful,
20 * but WITHOUT ANY WARRANTY; without even the implied warranty of
21 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
22 * General Public License for more details.
23 */
24
25#include <linux/kernel.h>
26#include <asm/div64.h>
27
28#include "dvb_frontend.h"
29#include "s921.h"
30
31static int debug = 1;
32module_param(debug, int, 0644);
33MODULE_PARM_DESC(debug, "Activates frontend debugging (default:0)");
34
35#define rc(args...) do { \
36 printk(KERN_ERR "s921: " args); \
37} while (0)
38
39#define dprintk(args...) \
40 do { \
41 if (debug) { \
42 printk(KERN_DEBUG "s921: %s: ", __func__); \
43 printk(args); \
44 } \
45 } while (0)
46
47struct s921_state {
48 struct i2c_adapter *i2c;
49 const struct s921_config *config;
50
51 struct dvb_frontend frontend;
52
53 /* The Demod can't easily provide these, we cache them */
54 u32 currentfreq;
55};
56
57/*
58 * Various tuner defaults need to be established for a given frequency kHz.
59 * fixme: The bounds on the bands do not match the doc in real life.
60 * fixme: Some of them have been moved, other might need adjustment.
61 */
62static struct s921_bandselect_val {
63 u32 freq_low;
64 u8 band_reg;
65} s921_bandselect[] = {
66 { 0, 0x7b },
67 { 485140000, 0x5b },
68 { 515140000, 0x3b },
69 { 545140000, 0x1b },
70 { 599140000, 0xfb },
71 { 623140000, 0xdb },
72 { 659140000, 0xbb },
73 { 713140000, 0x9b },
74};
75
76struct regdata {
77 u8 reg;
78 u8 data;
79};
80
81static struct regdata s921_init[] = {
82 { 0x01, 0x80 }, /* Probably, a reset sequence */
83 { 0x01, 0x40 },
84 { 0x01, 0x80 },
85 { 0x01, 0x40 },
86
87 { 0x02, 0x00 },
88 { 0x03, 0x40 },
89 { 0x04, 0x01 },
90 { 0x05, 0x00 },
91 { 0x06, 0x00 },
92 { 0x07, 0x00 },
93 { 0x08, 0x00 },
94 { 0x09, 0x00 },
95 { 0x0a, 0x00 },
96 { 0x0b, 0x5a },
97 { 0x0c, 0x00 },
98 { 0x0d, 0x00 },
99 { 0x0f, 0x00 },
100 { 0x13, 0x1b },
101 { 0x14, 0x80 },
102 { 0x15, 0x40 },
103 { 0x17, 0x70 },
104 { 0x18, 0x01 },
105 { 0x19, 0x12 },
106 { 0x1a, 0x01 },
107 { 0x1b, 0x12 },
108 { 0x1c, 0xa0 },
109 { 0x1d, 0x00 },
110 { 0x1e, 0x0a },
111 { 0x1f, 0x08 },
112 { 0x20, 0x40 },
113 { 0x21, 0xff },
114 { 0x22, 0x4c },
115 { 0x23, 0x4e },
116 { 0x24, 0x4c },
117 { 0x25, 0x00 },
118 { 0x26, 0x00 },
119 { 0x27, 0xf4 },
120 { 0x28, 0x60 },
121 { 0x29, 0x88 },
122 { 0x2a, 0x40 },
123 { 0x2b, 0x40 },
124 { 0x2c, 0xff },
125 { 0x2d, 0x00 },
126 { 0x2e, 0xff },
127 { 0x2f, 0x00 },
128 { 0x30, 0x20 },
129 { 0x31, 0x06 },
130 { 0x32, 0x0c },
131 { 0x34, 0x0f },
132 { 0x37, 0xfe },
133 { 0x38, 0x00 },
134 { 0x39, 0x63 },
135 { 0x3a, 0x10 },
136 { 0x3b, 0x10 },
137 { 0x47, 0x00 },
138 { 0x49, 0xe5 },
139 { 0x4b, 0x00 },
140 { 0x50, 0xc0 },
141 { 0x52, 0x20 },
142 { 0x54, 0x5a },
143 { 0x55, 0x5b },
144 { 0x56, 0x40 },
145 { 0x57, 0x70 },
146 { 0x5c, 0x50 },
147 { 0x5d, 0x00 },
148 { 0x62, 0x17 },
149 { 0x63, 0x2f },
150 { 0x64, 0x6f },
151 { 0x68, 0x00 },
152 { 0x69, 0x89 },
153 { 0x6a, 0x00 },
154 { 0x6b, 0x00 },
155 { 0x6c, 0x00 },
156 { 0x6d, 0x00 },
157 { 0x6e, 0x00 },
158 { 0x70, 0x10 },
159 { 0x71, 0x00 },
160 { 0x75, 0x00 },
161 { 0x76, 0x30 },
162 { 0x77, 0x01 },
163 { 0xaf, 0x00 },
164 { 0xb0, 0xa0 },
165 { 0xb2, 0x3d },
166 { 0xb3, 0x25 },
167 { 0xb4, 0x8b },
168 { 0xb5, 0x4b },
169 { 0xb6, 0x3f },
170 { 0xb7, 0xff },
171 { 0xb8, 0xff },
172 { 0xb9, 0xfc },
173 { 0xba, 0x00 },
174 { 0xbb, 0x00 },
175 { 0xbc, 0x00 },
176 { 0xd0, 0x30 },
177 { 0xe4, 0x84 },
178 { 0xf0, 0x48 },
179 { 0xf1, 0x19 },
180 { 0xf2, 0x5a },
181 { 0xf3, 0x8e },
182 { 0xf4, 0x2d },
183 { 0xf5, 0x07 },
184 { 0xf6, 0x5a },
185 { 0xf7, 0xba },
186 { 0xf8, 0xd7 },
187};
188
189static struct regdata s921_prefreq[] = {
190 { 0x47, 0x60 },
191 { 0x68, 0x00 },
192 { 0x69, 0x89 },
193 { 0xf0, 0x48 },
194 { 0xf1, 0x19 },
195};
196
197static struct regdata s921_postfreq[] = {
198 { 0xf5, 0xae },
199 { 0xf6, 0xb7 },
200 { 0xf7, 0xba },
201 { 0xf8, 0xd7 },
202 { 0x68, 0x0a },
203 { 0x69, 0x09 },
204};
205
206static int s921_i2c_writereg(struct s921_state *state,
207 u8 i2c_addr, int reg, int data)
208{
209 u8 buf[] = { reg, data };
210 struct i2c_msg msg = {
211 .addr = i2c_addr, .flags = 0, .buf = buf, .len = 2
212 };
213 int rc;
214
215 rc = i2c_transfer(state->i2c, &msg, 1);
216 if (rc != 1) {
217 printk("%s: writereg rcor(rc == %i, reg == 0x%02x,"
218 " data == 0x%02x)\n", __func__, rc, reg, data);
219 return rc;
220 }
221
222 return 0;
223}
224
225static int s921_i2c_writeregdata(struct s921_state *state, u8 i2c_addr,
226 struct regdata *rd, int size)
227{
228 int i, rc;
229
230 for (i = 0; i < size; i++) {
231 rc = s921_i2c_writereg(state, i2c_addr, rd[i].reg, rd[i].data);
232 if (rc < 0)
233 return rc;
234 }
235 return 0;
236}
237
238static int s921_i2c_readreg(struct s921_state *state, u8 i2c_addr, u8 reg)
239{
240 u8 val;
241 int rc;
242 struct i2c_msg msg[] = {
243 { .addr = i2c_addr, .flags = 0, .buf = &reg, .len = 1 },
244 { .addr = i2c_addr, .flags = I2C_M_RD, .buf = &val, .len = 1 }
245 };
246
247 rc = i2c_transfer(state->i2c, msg, 2);
248
249 if (rc != 2) {
250 rc("%s: reg=0x%x (rcor=%d)\n", __func__, reg, rc);
251 return rc;
252 }
253
254 return val;
255}
256
257#define s921_readreg(state, reg) \
258 s921_i2c_readreg(state, state->config->demod_address, reg)
259#define s921_writereg(state, reg, val) \
260 s921_i2c_writereg(state, state->config->demod_address, reg, val)
261#define s921_writeregdata(state, regdata) \
262 s921_i2c_writeregdata(state, state->config->demod_address, \
263 regdata, ARRAY_SIZE(regdata))
264
265static int s921_pll_tune(struct dvb_frontend *fe,
266 struct dvb_frontend_parameters *p)
267{
268 struct s921_state *state = fe->demodulator_priv;
269 int band, rc, i;
270 unsigned long f_offset;
271 u8 f_switch;
272 u64 offset;
273
274 dprintk("frequency=%i\n", p->frequency);
275
276 for (band = 0; band < ARRAY_SIZE(s921_bandselect); band++)
277 if (p->frequency < s921_bandselect[band].freq_low)
278 break;
279 band--;
280
281 if (band < 0) {
282 rc("%s: frequency out of range\n", __func__);
283 return -EINVAL;
284 }
285
286 f_switch = s921_bandselect[band].band_reg;
287
288 offset = ((u64)p->frequency) * 258;
289 do_div(offset, 6000000);
290 f_offset = ((unsigned long)offset) + 2321;
291
292 rc = s921_writeregdata(state, s921_prefreq);
293 if (rc < 0)
294 return rc;
295
296 rc = s921_writereg(state, 0xf2, (f_offset >> 8) & 0xff);
297 if (rc < 0)
298 return rc;
299
300 rc = s921_writereg(state, 0xf3, f_offset & 0xff);
301 if (rc < 0)
302 return rc;
303
304 rc = s921_writereg(state, 0xf4, f_switch);
305 if (rc < 0)
306 return rc;
307
308 rc = s921_writeregdata(state, s921_postfreq);
309 if (rc < 0)
310 return rc;
311
312 for (i = 0 ; i < 6; i++) {
313 rc = s921_readreg(state, 0x80);
314 dprintk("status 0x80: %02x\n", rc);
315 }
316 rc = s921_writereg(state, 0x01, 0x40);
317 if (rc < 0)
318 return rc;
319
320 rc = s921_readreg(state, 0x01);
321 dprintk("status 0x01: %02x\n", rc);
322
323 rc = s921_readreg(state, 0x80);
324 dprintk("status 0x80: %02x\n", rc);
325
326 rc = s921_readreg(state, 0x80);
327 dprintk("status 0x80: %02x\n", rc);
328
329 rc = s921_readreg(state, 0x32);
330 dprintk("status 0x32: %02x\n", rc);
331
332 dprintk("pll tune band=%d, pll=%d\n", f_switch, (int)f_offset);
333
334 return 0;
335}
336
337static int s921_initfe(struct dvb_frontend *fe)
338{
339 struct s921_state *state = fe->demodulator_priv;
340 int rc;
341
342 dprintk("\n");
343
344 rc = s921_writeregdata(state, s921_init);
345 if (rc < 0)
346 return rc;
347
348 return 0;
349}
350
351static int s921_read_status(struct dvb_frontend *fe, fe_status_t *status)
352{
353 struct s921_state *state = fe->demodulator_priv;
354 int regstatus, rc;
355
356 *status = 0;
357
358 rc = s921_readreg(state, 0x81);
359 if (rc < 0)
360 return rc;
361
362 regstatus = rc << 8;
363
364 rc = s921_readreg(state, 0x82);
365 if (rc < 0)
366 return rc;
367
368 regstatus |= rc;
369
370 dprintk("status = %04x\n", regstatus);
371
372 /* Full Sync - We don't know what each bit means on regs 0x81/0x82 */
373 if ((regstatus & 0xff) == 0x40) {
374 *status = FE_HAS_SIGNAL |
375 FE_HAS_CARRIER |
376 FE_HAS_VITERBI |
377 FE_HAS_SYNC |
378 FE_HAS_LOCK;
379 } else if (regstatus & 0x40) {
380 /* This is close to Full Sync, but not enough to get useful info */
381 *status = FE_HAS_SIGNAL |
382 FE_HAS_CARRIER |
383 FE_HAS_VITERBI |
384 FE_HAS_SYNC;
385 }
386
387 return 0;
388}
389
390static int s921_read_signal_strength(struct dvb_frontend *fe, u16 *strength)
391{
392 fe_status_t status;
393 struct s921_state *state = fe->demodulator_priv;
394 int rc;
395
396 /* FIXME: Use the proper register for it... 0x80? */
397 rc = s921_read_status(fe, &status);
398 if (rc < 0)
399 return rc;
400
401 *strength = (status & FE_HAS_LOCK) ? 0xffff : 0;
402
403 dprintk("strength = 0x%04x\n", *strength);
404
405 rc = s921_readreg(state, 0x01);
406 dprintk("status 0x01: %02x\n", rc);
407
408 rc = s921_readreg(state, 0x80);
409 dprintk("status 0x80: %02x\n", rc);
410
411 rc = s921_readreg(state, 0x32);
412 dprintk("status 0x32: %02x\n", rc);
413
414 return 0;
415}
416
417static int s921_set_frontend(struct dvb_frontend *fe,
418 struct dvb_frontend_parameters *p)
419{
420 struct s921_state *state = fe->demodulator_priv;
421 int rc;
422
423 dprintk("\n");
424
425 /* FIXME: We don't know how to use non-auto mode */
426
427 rc = s921_pll_tune(fe, p);
428 if (rc < 0)
429 return rc;
430
431 state->currentfreq = p->frequency;
432
433 return 0;
434}
435
436static int s921_get_frontend(struct dvb_frontend *fe,
437 struct dvb_frontend_parameters *p)
438{
439 struct s921_state *state = fe->demodulator_priv;
440
441 /* FIXME: Probably it is possible to get it from regs f1 and f2 */
442 p->frequency = state->currentfreq;
443
444 return 0;
445}
446
447static int s921_tune(struct dvb_frontend *fe,
448 struct dvb_frontend_parameters *params,
449 unsigned int mode_flags,
450 unsigned int *delay,
451 fe_status_t *status)
452{
453 int rc = 0;
454
455 dprintk("\n");
456
457 if (params != NULL)
458 rc = s921_set_frontend(fe, params);
459
460 if (!(mode_flags & FE_TUNE_MODE_ONESHOT))
461 s921_read_status(fe, status);
462
463 return rc;
464}
465
466static int s921_get_algo(struct dvb_frontend *fe)
467{
468 return 1; /* FE_ALGO_HW */
469}
470
471static void s921_release(struct dvb_frontend *fe)
472{
473 struct s921_state *state = fe->demodulator_priv;
474
475 dprintk("\n");
476 kfree(state);
477}
478
479static struct dvb_frontend_ops s921_ops;
480
481struct dvb_frontend *s921_attach(const struct s921_config *config,
482 struct i2c_adapter *i2c)
483{
484 /* allocate memory for the internal state */
485 struct s921_state *state =
486 kzalloc(sizeof(struct s921_state), GFP_KERNEL);
487
488 dprintk("\n");
489 if (state == NULL) {
490 rc("Unable to kzalloc\n");
491 goto rcor;
492 }
493
494 /* setup the state */
495 state->config = config;
496 state->i2c = i2c;
497
498 /* create dvb_frontend */
499 memcpy(&state->frontend.ops, &s921_ops,
500 sizeof(struct dvb_frontend_ops));
501 state->frontend.demodulator_priv = state;
502
503 return &state->frontend;
504
505rcor:
506 kfree(state);
507
508 return NULL;
509}
510EXPORT_SYMBOL(s921_attach);
511
512static struct dvb_frontend_ops s921_ops = {
513 /* Use dib8000 values per default */
514 .info = {
515 .name = "Sharp S921",
516 .type = FE_OFDM,
517 .frequency_min = 470000000,
518 /*
519 * Max should be 770MHz instead, according with Sharp docs,
520 * but Leadership doc says it works up to 806 MHz. This is
521 * required to get channel 69, used in Brazil
522 */
523 .frequency_max = 806000000,
524 .frequency_tolerance = 0,
525 .caps = FE_CAN_INVERSION_AUTO |
526 FE_CAN_FEC_1_2 | FE_CAN_FEC_2_3 | FE_CAN_FEC_3_4 |
527 FE_CAN_FEC_5_6 | FE_CAN_FEC_7_8 | FE_CAN_FEC_AUTO |
528 FE_CAN_QPSK | FE_CAN_QAM_16 | FE_CAN_QAM_64 |
529 FE_CAN_QAM_AUTO | FE_CAN_TRANSMISSION_MODE_AUTO |
530 FE_CAN_GUARD_INTERVAL_AUTO | FE_CAN_RECOVER |
531 FE_CAN_HIERARCHY_AUTO,
532 },
533
534 .release = s921_release,
535
536 .init = s921_initfe,
537 .set_frontend = s921_set_frontend,
538 .get_frontend = s921_get_frontend,
539 .read_status = s921_read_status,
540 .read_signal_strength = s921_read_signal_strength,
541 .tune = s921_tune,
542 .get_frontend_algo = s921_get_algo,
543};
544
545MODULE_DESCRIPTION("DVB Frontend module for Sharp S921 hardware");
546MODULE_AUTHOR("Mauro Carvalho Chehab <mchehab@redhat.com>");
547MODULE_AUTHOR("Douglas Landgraf <dougsland@redhat.com>");
548MODULE_LICENSE("GPL");
diff --git a/drivers/media/dvb/frontends/s921.h b/drivers/media/dvb/frontends/s921.h
new file mode 100644
index 000000000000..f220d8299c81
--- /dev/null
+++ b/drivers/media/dvb/frontends/s921.h
@@ -0,0 +1,47 @@
1/*
2 * Sharp s921 driver
3 *
4 * Copyright (C) 2009 Mauro Carvalho Chehab <mchehab@redhat.com>
5 * Copyright (C) 2009 Douglas Landgraf <dougsland@redhat.com>
6 *
7 * This program is free software; you can redistribute it and/or
8 * modify it under the terms of the GNU General Public License as
9 * published by the Free Software Foundation version 2.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * General Public License for more details.
15 */
16
17#ifndef S921_H
18#define S921_H
19
20#include <linux/dvb/frontend.h>
21
22struct s921_config {
23 /* the demodulator's i2c address */
24 u8 demod_address;
25};
26
27#if defined(CONFIG_DVB_S921) || (defined(CONFIG_DVB_S921_MODULE) \
28 && defined(MODULE))
29extern struct dvb_frontend *s921_attach(const struct s921_config *config,
30 struct i2c_adapter *i2c);
31extern struct i2c_adapter *s921_get_tuner_i2c_adapter(struct dvb_frontend *);
32#else
33static inline struct dvb_frontend *s921_attach(
34 const struct s921_config *config, struct i2c_adapter *i2c)
35{
36 printk(KERN_WARNING "%s: driver disabled by Kconfig\n", __func__);
37 return NULL;
38}
39static struct i2c_adapter *
40 s921_get_tuner_i2c_adapter(struct dvb_frontend *fe)
41{
42 printk(KERN_WARNING "%s: driver disabled by Kconfig\n", __func__);
43 return NULL;
44}
45#endif
46
47#endif /* S921_H */
diff --git a/drivers/media/dvb/frontends/s921_core.c b/drivers/media/dvb/frontends/s921_core.c
deleted file mode 100644
index 974b52be9aea..000000000000
--- a/drivers/media/dvb/frontends/s921_core.c
+++ /dev/null
@@ -1,216 +0,0 @@
1/*
2 * Driver for Sharp s921 driver
3 *
4 * Copyright (C) 2008 Markus Rechberger <mrechberger@sundtek.de>
5 *
6 */
7
8
9#include <linux/kernel.h>
10#include <linux/module.h>
11#include <linux/delay.h>
12#include "s921_core.h"
13
14static int s921_isdb_init(struct s921_isdb_t *dev);
15static int s921_isdb_set_parameters(struct s921_isdb_t *dev, struct s921_isdb_t_transmission_mode_params *params);
16static int s921_isdb_tune(struct s921_isdb_t *dev, struct s921_isdb_t_tune_params *params);
17static int s921_isdb_get_status(struct s921_isdb_t *dev, void *data);
18
19static u8 init_table[]={ 0x01, 0x40, 0x02, 0x00, 0x03, 0x40, 0x04, 0x01,
20 0x05, 0x00, 0x06, 0x00, 0x07, 0x00, 0x08, 0x00,
21 0x09, 0x00, 0x0a, 0x00, 0x0b, 0x5a, 0x0c, 0x00,
22 0x0d, 0x00, 0x0f, 0x00, 0x13, 0x1b, 0x14, 0x80,
23 0x15, 0x40, 0x17, 0x70, 0x18, 0x01, 0x19, 0x12,
24 0x1a, 0x01, 0x1b, 0x12, 0x1c, 0xa0, 0x1d, 0x00,
25 0x1e, 0x0a, 0x1f, 0x08, 0x20, 0x40, 0x21, 0xff,
26 0x22, 0x4c, 0x23, 0x4e, 0x24, 0x4c, 0x25, 0x00,
27 0x26, 0x00, 0x27, 0xf4, 0x28, 0x60, 0x29, 0x88,
28 0x2a, 0x40, 0x2b, 0x40, 0x2c, 0xff, 0x2d, 0x00,
29 0x2e, 0xff, 0x2f, 0x00, 0x30, 0x20, 0x31, 0x06,
30 0x32, 0x0c, 0x34, 0x0f, 0x37, 0xfe, 0x38, 0x00,
31 0x39, 0x63, 0x3a, 0x10, 0x3b, 0x10, 0x47, 0x00,
32 0x49, 0xe5, 0x4b, 0x00, 0x50, 0xc0, 0x52, 0x20,
33 0x54, 0x5a, 0x55, 0x5b, 0x56, 0x40, 0x57, 0x70,
34 0x5c, 0x50, 0x5d, 0x00, 0x62, 0x17, 0x63, 0x2f,
35 0x64, 0x6f, 0x68, 0x00, 0x69, 0x89, 0x6a, 0x00,
36 0x6b, 0x00, 0x6c, 0x00, 0x6d, 0x00, 0x6e, 0x00,
37 0x70, 0x00, 0x71, 0x00, 0x75, 0x00, 0x76, 0x30,
38 0x77, 0x01, 0xaf, 0x00, 0xb0, 0xa0, 0xb2, 0x3d,
39 0xb3, 0x25, 0xb4, 0x8b, 0xb5, 0x4b, 0xb6, 0x3f,
40 0xb7, 0xff, 0xb8, 0xff, 0xb9, 0xfc, 0xba, 0x00,
41 0xbb, 0x00, 0xbc, 0x00, 0xd0, 0x30, 0xe4, 0x84,
42 0xf0, 0x48, 0xf1, 0x19, 0xf2, 0x5a, 0xf3, 0x8e,
43 0xf4, 0x2d, 0xf5, 0x07, 0xf6, 0x5a, 0xf7, 0xba,
44 0xf8, 0xd7 };
45
46static u8 c_table[]={ 0x58, 0x8a, 0x7b, 0x59, 0x8c, 0x7b, 0x5a, 0x8e, 0x5b,
47 0x5b, 0x90, 0x5b, 0x5c, 0x92, 0x5b, 0x5d, 0x94, 0x5b,
48 0x5e, 0x96, 0x5b, 0x5f, 0x98, 0x3b, 0x60, 0x9a, 0x3b,
49 0x61, 0x9c, 0x3b, 0x62, 0x9e, 0x3b, 0x63, 0xa0, 0x3b,
50 0x64, 0xa2, 0x1b, 0x65, 0xa4, 0x1b, 0x66, 0xa6, 0x1b,
51 0x67, 0xa8, 0x1b, 0x68, 0xaa, 0x1b, 0x69, 0xac, 0x1b,
52 0x6a, 0xae, 0x1b, 0x6b, 0xb0, 0x1b, 0x6c, 0xb2, 0x1b,
53 0x6d, 0xb4, 0xfb, 0x6e, 0xb6, 0xfb, 0x6f, 0xb8, 0xfb,
54 0x70, 0xba, 0xfb, 0x71, 0xbc, 0xdb, 0x72, 0xbe, 0xdb,
55 0x73, 0xc0, 0xdb, 0x74, 0xc2, 0xdb, 0x75, 0xc4, 0xdb,
56 0x76, 0xc6, 0xdb, 0x77, 0xc8, 0xbb, 0x78, 0xca, 0xbb,
57 0x79, 0xcc, 0xbb, 0x7a, 0xce, 0xbb, 0x7b, 0xd0, 0xbb,
58 0x7c, 0xd2, 0xbb, 0x7d, 0xd4, 0xbb, 0x7e, 0xd6, 0xbb,
59 0x7f, 0xd8, 0xbb, 0x80, 0xda, 0x9b, 0x81, 0xdc, 0x9b,
60 0x82, 0xde, 0x9b, 0x83, 0xe0, 0x9b, 0x84, 0xe2, 0x9b,
61 0x85, 0xe4, 0x9b, 0x86, 0xe6, 0x9b, 0x87, 0xe8, 0x9b,
62 0x88, 0xea, 0x9b, 0x89, 0xec, 0x9b };
63
64int s921_isdb_cmd(struct s921_isdb_t *dev, u32 cmd, void *data) {
65 switch(cmd) {
66 case ISDB_T_CMD_INIT:
67 s921_isdb_init(dev);
68 break;
69 case ISDB_T_CMD_SET_PARAM:
70 s921_isdb_set_parameters(dev, data);
71 break;
72 case ISDB_T_CMD_TUNE:
73 s921_isdb_tune(dev, data);
74 break;
75 case ISDB_T_CMD_GET_STATUS:
76 s921_isdb_get_status(dev, data);
77 break;
78 default:
79 printk("unhandled command\n");
80 return -EINVAL;
81 }
82 return 0;
83}
84
85static int s921_isdb_init(struct s921_isdb_t *dev) {
86 unsigned int i;
87 unsigned int ret;
88 printk("isdb_init\n");
89 for (i = 0; i < sizeof(init_table); i+=2) {
90 ret = dev->i2c_write(dev->priv_dev, init_table[i], init_table[i+1]);
91 if (ret != 0) {
92 printk("i2c write failed\n");
93 return ret;
94 }
95 }
96 return 0;
97}
98
99static int s921_isdb_set_parameters(struct s921_isdb_t *dev, struct s921_isdb_t_transmission_mode_params *params) {
100
101 int ret;
102 /* auto is sufficient for now, lateron this should be reflected in an extra interface */
103
104
105
106 ret = dev->i2c_write(dev->priv_dev, 0xb0, 0xa0); //mod_b2);
107 ret = dev->i2c_write(dev->priv_dev, 0xb2, 0x3d); //mod_b2);
108
109 if (ret < 0)
110 return -EINVAL;
111
112 ret = dev->i2c_write(dev->priv_dev, 0xb3, 0x25); //mod_b3);
113 if (ret < 0)
114 return -EINVAL;
115
116 ret = dev->i2c_write(dev->priv_dev, 0xb4, 0x8b); //mod_b4);
117 if (ret < 0)
118 return -EINVAL;
119
120 ret = dev->i2c_write(dev->priv_dev, 0xb5, 0x4b); //mod_b5);
121 if (ret < 0)
122 return -EINVAL;
123
124 ret = dev->i2c_write(dev->priv_dev, 0xb6, 0x3f); //mod_b6);
125 if (ret < 0)
126 return -EINVAL;
127
128 ret = dev->i2c_write(dev->priv_dev, 0xb7, 0x3f); //mod_b7);
129 if (ret < 0)
130 return -EINVAL;
131
132 return E_OK;
133}
134
135static int s921_isdb_tune(struct s921_isdb_t *dev, struct s921_isdb_t_tune_params *params) {
136
137 int ret;
138 int index;
139
140 index = (params->frequency - 473143000)/6000000;
141
142 if (index > 48) {
143 return -EINVAL;
144 }
145
146 dev->i2c_write(dev->priv_dev, 0x47, 0x60);
147
148 ret = dev->i2c_write(dev->priv_dev, 0x68, 0x00);
149 if (ret < 0)
150 return -EINVAL;
151
152 ret = dev->i2c_write(dev->priv_dev, 0x69, 0x89);
153 if (ret < 0)
154 return -EINVAL;
155
156 ret = dev->i2c_write(dev->priv_dev, 0xf0, 0x48);
157 if (ret < 0)
158 return -EINVAL;
159
160 ret = dev->i2c_write(dev->priv_dev, 0xf1, 0x19);
161 if (ret < 0)
162 return -EINVAL;
163
164 ret = dev->i2c_write(dev->priv_dev, 0xf2, c_table[index*3]);
165 if (ret < 0)
166 return -EINVAL;
167
168 ret = dev->i2c_write(dev->priv_dev, 0xf3, c_table[index*3+1]);
169 if (ret < 0)
170 return -EINVAL;
171
172 ret = dev->i2c_write(dev->priv_dev, 0xf4, c_table[index*3+2]);
173 if (ret < 0)
174 return -EINVAL;
175
176 ret = dev->i2c_write(dev->priv_dev, 0xf5, 0xae);
177 if (ret < 0)
178 return -EINVAL;
179
180 ret = dev->i2c_write(dev->priv_dev, 0xf6, 0xb7);
181 if (ret < 0)
182 return -EINVAL;
183
184 ret = dev->i2c_write(dev->priv_dev, 0xf7, 0xba);
185 if (ret < 0)
186 return -EINVAL;
187
188 ret = dev->i2c_write(dev->priv_dev, 0xf8, 0xd7);
189 if (ret < 0)
190 return -EINVAL;
191
192 ret = dev->i2c_write(dev->priv_dev, 0x68, 0x0a);
193 if (ret < 0)
194 return -EINVAL;
195
196 ret = dev->i2c_write(dev->priv_dev, 0x69, 0x09);
197 if (ret < 0)
198 return -EINVAL;
199
200 dev->i2c_write(dev->priv_dev, 0x01, 0x40);
201 return 0;
202}
203
204static int s921_isdb_get_status(struct s921_isdb_t *dev, void *data) {
205 unsigned int *ret = (unsigned int*)data;
206 u8 ifagc_dt;
207 u8 rfagc_dt;
208
209 mdelay(10);
210 ifagc_dt = dev->i2c_read(dev->priv_dev, 0x81);
211 rfagc_dt = dev->i2c_read(dev->priv_dev, 0x82);
212 if (rfagc_dt == 0x40) {
213 *ret = 1;
214 }
215 return 0;
216}
diff --git a/drivers/media/dvb/frontends/s921_core.h b/drivers/media/dvb/frontends/s921_core.h
deleted file mode 100644
index de2f10a44e72..000000000000
--- a/drivers/media/dvb/frontends/s921_core.h
+++ /dev/null
@@ -1,114 +0,0 @@
1#ifndef _S921_CORE_H
2#define _S921_CORE_H
3//#define u8 unsigned int
4//#define u32 unsigned int
5
6
7
8//#define EINVAL -1
9#define E_OK 0
10
11struct s921_isdb_t {
12 void *priv_dev;
13 int (*i2c_write)(void *dev, u8 reg, u8 val);
14 int (*i2c_read)(void *dev, u8 reg);
15};
16
17#define ISDB_T_CMD_INIT 0
18#define ISDB_T_CMD_SET_PARAM 1
19#define ISDB_T_CMD_TUNE 2
20#define ISDB_T_CMD_GET_STATUS 3
21
22struct s921_isdb_t_tune_params {
23 u32 frequency;
24};
25
26struct s921_isdb_t_status {
27};
28
29struct s921_isdb_t_transmission_mode_params {
30 u8 mode;
31 u8 layer_a_mode;
32#define ISDB_T_LA_MODE_1 0
33#define ISDB_T_LA_MODE_2 1
34#define ISDB_T_LA_MODE_3 2
35 u8 layer_a_carrier_modulation;
36#define ISDB_T_LA_CM_DQPSK 0
37#define ISDB_T_LA_CM_QPSK 1
38#define ISDB_T_LA_CM_16QAM 2
39#define ISDB_T_LA_CM_64QAM 3
40#define ISDB_T_LA_CM_NOLAYER 4
41 u8 layer_a_code_rate;
42#define ISDB_T_LA_CR_1_2 0
43#define ISDB_T_LA_CR_2_3 1
44#define ISDB_T_LA_CR_3_4 2
45#define ISDB_T_LA_CR_5_6 4
46#define ISDB_T_LA_CR_7_8 8
47#define ISDB_T_LA_CR_NOLAYER 16
48 u8 layer_a_time_interleave;
49#define ISDB_T_LA_TI_0 0
50#define ISDB_T_LA_TI_1 1
51#define ISDB_T_LA_TI_2 2
52#define ISDB_T_LA_TI_4 4
53#define ISDB_T_LA_TI_8 8
54#define ISDB_T_LA_TI_16 16
55#define ISDB_T_LA_TI_32 32
56 u8 layer_a_nseg;
57
58 u8 layer_b_mode;
59#define ISDB_T_LB_MODE_1 0
60#define ISDB_T_LB_MODE_2 1
61#define ISDB_T_LB_MODE_3 2
62 u8 layer_b_carrier_modulation;
63#define ISDB_T_LB_CM_DQPSK 0
64#define ISDB_T_LB_CM_QPSK 1
65#define ISDB_T_LB_CM_16QAM 2
66#define ISDB_T_LB_CM_64QAM 3
67#define ISDB_T_LB_CM_NOLAYER 4
68 u8 layer_b_code_rate;
69#define ISDB_T_LB_CR_1_2 0
70#define ISDB_T_LB_CR_2_3 1
71#define ISDB_T_LB_CR_3_4 2
72#define ISDB_T_LB_CR_5_6 4
73#define ISDB_T_LB_CR_7_8 8
74#define ISDB_T_LB_CR_NOLAYER 16
75 u8 layer_b_time_interleave;
76#define ISDB_T_LB_TI_0 0
77#define ISDB_T_LB_TI_1 1
78#define ISDB_T_LB_TI_2 2
79#define ISDB_T_LB_TI_4 4
80#define ISDB_T_LB_TI_8 8
81#define ISDB_T_LB_TI_16 16
82#define ISDB_T_LB_TI_32 32
83 u8 layer_b_nseg;
84
85 u8 layer_c_mode;
86#define ISDB_T_LC_MODE_1 0
87#define ISDB_T_LC_MODE_2 1
88#define ISDB_T_LC_MODE_3 2
89 u8 layer_c_carrier_modulation;
90#define ISDB_T_LC_CM_DQPSK 0
91#define ISDB_T_LC_CM_QPSK 1
92#define ISDB_T_LC_CM_16QAM 2
93#define ISDB_T_LC_CM_64QAM 3
94#define ISDB_T_LC_CM_NOLAYER 4
95 u8 layer_c_code_rate;
96#define ISDB_T_LC_CR_1_2 0
97#define ISDB_T_LC_CR_2_3 1
98#define ISDB_T_LC_CR_3_4 2
99#define ISDB_T_LC_CR_5_6 4
100#define ISDB_T_LC_CR_7_8 8
101#define ISDB_T_LC_CR_NOLAYER 16
102 u8 layer_c_time_interleave;
103#define ISDB_T_LC_TI_0 0
104#define ISDB_T_LC_TI_1 1
105#define ISDB_T_LC_TI_2 2
106#define ISDB_T_LC_TI_4 4
107#define ISDB_T_LC_TI_8 8
108#define ISDB_T_LC_TI_16 16
109#define ISDB_T_LC_TI_32 32
110 u8 layer_c_nseg;
111};
112
113int s921_isdb_cmd(struct s921_isdb_t *dev, u32 cmd, void *data);
114#endif
diff --git a/drivers/media/dvb/frontends/s921_module.c b/drivers/media/dvb/frontends/s921_module.c
deleted file mode 100644
index 0eefff61cc50..000000000000
--- a/drivers/media/dvb/frontends/s921_module.c
+++ /dev/null
@@ -1,192 +0,0 @@
1/*
2 * Driver for Sharp s921 driver
3 *
4 * Copyright (C) 2008 Markus Rechberger <mrechberger@sundtek.de>
5 *
6 * All rights reserved.
7 *
8 */
9
10#include <linux/kernel.h>
11#include <linux/module.h>
12#include <linux/slab.h>
13#include <linux/delay.h>
14#include "dvb_frontend.h"
15#include "s921_module.h"
16#include "s921_core.h"
17
18static unsigned int debug = 0;
19module_param(debug, int, 0644);
20MODULE_PARM_DESC(debug,"s921 debugging (default off)");
21
22#define dprintk(fmt, args...) if (debug) do {\
23 printk("s921 debug: " fmt, ##args); } while (0)
24
25struct s921_state
26{
27 struct dvb_frontend frontend;
28 fe_modulation_t current_modulation;
29 __u32 snr;
30 __u32 current_frequency;
31 __u8 addr;
32 struct s921_isdb_t dev;
33 struct i2c_adapter *i2c;
34};
35
36static int s921_set_parameters(struct dvb_frontend *fe, struct dvb_frontend_parameters *param) {
37 struct s921_state *state = (struct s921_state *)fe->demodulator_priv;
38 struct s921_isdb_t_transmission_mode_params params;
39 struct s921_isdb_t_tune_params tune_params;
40
41 tune_params.frequency = param->frequency;
42 s921_isdb_cmd(&state->dev, ISDB_T_CMD_SET_PARAM, &params);
43 s921_isdb_cmd(&state->dev, ISDB_T_CMD_TUNE, &tune_params);
44 mdelay(100);
45 return 0;
46}
47
48static int s921_init(struct dvb_frontend *fe) {
49 printk("s921 init\n");
50 return 0;
51}
52
53static int s921_sleep(struct dvb_frontend *fe) {
54 printk("s921 sleep\n");
55 return 0;
56}
57
58static int s921_read_status(struct dvb_frontend *fe, fe_status_t *status)
59{
60 struct s921_state *state = (struct s921_state *)fe->demodulator_priv;
61 unsigned int ret;
62 mdelay(5);
63 s921_isdb_cmd(&state->dev, ISDB_T_CMD_GET_STATUS, &ret);
64 *status = 0;
65
66 printk("status: %02x\n", ret);
67 if (ret == 1) {
68 *status |= FE_HAS_CARRIER;
69 *status |= FE_HAS_VITERBI;
70 *status |= FE_HAS_LOCK;
71 *status |= FE_HAS_SYNC;
72 *status |= FE_HAS_SIGNAL;
73 }
74
75 return 0;
76}
77
78static int s921_read_ber(struct dvb_frontend *fe, __u32 *ber)
79{
80 dprintk("read ber\n");
81 return 0;
82}
83
84static int s921_read_snr(struct dvb_frontend *fe, __u16 *snr)
85{
86 dprintk("read snr\n");
87 return 0;
88}
89
90static int s921_read_ucblocks(struct dvb_frontend *fe, __u32 *ucblocks)
91{
92 dprintk("read ucblocks\n");
93 return 0;
94}
95
96static void s921_release(struct dvb_frontend *fe)
97{
98 struct s921_state *state = (struct s921_state *)fe->demodulator_priv;
99 kfree(state);
100}
101
102static struct dvb_frontend_ops demod_s921={
103 .info = {
104 .name = "SHARP S921",
105 .type = FE_OFDM,
106 .frequency_min = 473143000,
107 .frequency_max = 767143000,
108 .frequency_stepsize = 6000000,
109 .frequency_tolerance = 0,
110 .caps = FE_CAN_FEC_1_2 | FE_CAN_FEC_2_3 |
111 FE_CAN_FEC_3_4 | FE_CAN_FEC_5_6 | FE_CAN_FEC_7_8 |
112 FE_CAN_FEC_AUTO |
113 FE_CAN_QPSK | FE_CAN_QAM_16 | FE_CAN_QAM_64 | FE_CAN_QAM_AUTO |
114 FE_CAN_TRANSMISSION_MODE_AUTO | FE_CAN_GUARD_INTERVAL_AUTO |
115 FE_CAN_HIERARCHY_AUTO | FE_CAN_RECOVER |
116 FE_CAN_MUTE_TS
117 },
118 .init = s921_init,
119 .sleep = s921_sleep,
120 .set_frontend = s921_set_parameters,
121 .read_snr = s921_read_snr,
122 .read_ber = s921_read_ber,
123 .read_status = s921_read_status,
124 .read_ucblocks = s921_read_ucblocks,
125 .release = s921_release,
126};
127
128static int s921_write(void *dev, u8 reg, u8 val) {
129 struct s921_state *state = dev;
130 char buf[2]={reg,val};
131 int err;
132 struct i2c_msg i2cmsgs = {
133 .addr = state->addr,
134 .flags = 0,
135 .len = 2,
136 .buf = buf
137 };
138
139 if((err = i2c_transfer(state->i2c, &i2cmsgs, 1))<0) {
140 printk("%s i2c_transfer error %d\n", __func__, err);
141 if (err < 0)
142 return err;
143 else
144 return -EREMOTEIO;
145 }
146
147 return 0;
148}
149
150static int s921_read(void *dev, u8 reg) {
151 struct s921_state *state = dev;
152 u8 b1;
153 int ret;
154 struct i2c_msg msg[2] = { { .addr = state->addr,
155 .flags = 0,
156 .buf = &reg, .len = 1 },
157 { .addr = state->addr,
158 .flags = I2C_M_RD,
159 .buf = &b1, .len = 1 } };
160
161 ret = i2c_transfer(state->i2c, msg, 2);
162 if (ret != 2)
163 return ret;
164 return b1;
165}
166
167struct dvb_frontend* s921_attach(const struct s921_config *config,
168 struct i2c_adapter *i2c)
169{
170
171 struct s921_state *state;
172 state = kzalloc(sizeof(struct s921_state), GFP_KERNEL);
173 if (state == NULL)
174 return NULL;
175
176 state->addr = config->i2c_address;
177 state->i2c = i2c;
178 state->dev.i2c_write = &s921_write;
179 state->dev.i2c_read = &s921_read;
180 state->dev.priv_dev = state;
181
182 s921_isdb_cmd(&state->dev, ISDB_T_CMD_INIT, NULL);
183
184 memcpy(&state->frontend.ops, &demod_s921, sizeof(struct dvb_frontend_ops));
185 state->frontend.demodulator_priv = state;
186 return &state->frontend;
187}
188
189EXPORT_SYMBOL_GPL(s921_attach);
190MODULE_AUTHOR("Markus Rechberger <mrechberger@empiatech.com>");
191MODULE_DESCRIPTION("Sharp S921 ISDB-T 1Seg");
192MODULE_LICENSE("GPL");
diff --git a/drivers/media/dvb/frontends/s921_module.h b/drivers/media/dvb/frontends/s921_module.h
deleted file mode 100644
index 78660424ba95..000000000000
--- a/drivers/media/dvb/frontends/s921_module.h
+++ /dev/null
@@ -1,49 +0,0 @@
1/*
2 * Driver for DVB-T s921 demodulator
3 *
4 * Copyright (C) 2008 Markus Rechberger <mrechberger@sundtek.de>
5 *
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
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 *
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.=
20 */
21
22#ifndef S921_MODULE_H
23#define S921_MODULE_H
24
25#include <linux/dvb/frontend.h>
26#include "s921_core.h"
27
28int s921_isdb_init(struct s921_isdb_t *dev);
29int s921_isdb_cmd(struct s921_isdb_t *dev, u32 cmd, void *data);
30
31struct s921_config
32{
33 /* demodulator's I2C address */
34 u8 i2c_address;
35};
36
37#if defined(CONFIG_DVB_S921) || (defined(CONFIG_DVB_S921_MODULE) && defined(MODULE))
38extern struct dvb_frontend* s921_attach(const struct s921_config *config,
39 struct i2c_adapter *i2c);
40#else
41static inline struct dvb_frontend* s921_attach(const struct s921_config *config,
42 struct i2c_adapter *i2c)
43{
44 printk(KERN_WARNING "%s: driver disabled by Kconfig\n", __func__);
45 return NULL;
46}
47#endif /* CONFIG_DVB_S921 */
48
49#endif /* S921_H */
diff --git a/drivers/media/dvb/frontends/stb0899_drv.c b/drivers/media/dvb/frontends/stb0899_drv.c
index 8e38fcee564e..37a222d9ddb3 100644
--- a/drivers/media/dvb/frontends/stb0899_drv.c
+++ b/drivers/media/dvb/frontends/stb0899_drv.c
@@ -714,7 +714,7 @@ static int stb0899_send_diseqc_msg(struct dvb_frontend *fe, struct dvb_diseqc_ma
714 reg = stb0899_read_reg(state, STB0899_DISCNTRL1); 714 reg = stb0899_read_reg(state, STB0899_DISCNTRL1);
715 STB0899_SETFIELD_VAL(DISPRECHARGE, reg, 0); 715 STB0899_SETFIELD_VAL(DISPRECHARGE, reg, 0);
716 stb0899_write_reg(state, STB0899_DISCNTRL1, reg); 716 stb0899_write_reg(state, STB0899_DISCNTRL1, reg);
717 717 msleep(100);
718 return 0; 718 return 0;
719} 719}
720 720
diff --git a/drivers/media/dvb/frontends/stb6100.c b/drivers/media/dvb/frontends/stb6100.c
index 80a9e4cba631..64673b8b64a2 100644
--- a/drivers/media/dvb/frontends/stb6100.c
+++ b/drivers/media/dvb/frontends/stb6100.c
@@ -51,7 +51,7 @@ module_param(verbose, int, 0644);
51 if (x > y) \ 51 if (x > y) \
52 printk(format, ##arg); \ 52 printk(format, ##arg); \
53 } \ 53 } \
54} while(0) 54} while (0)
55 55
56struct stb6100_lkup { 56struct stb6100_lkup {
57 u32 val_low; 57 u32 val_low;
@@ -117,7 +117,10 @@ static const struct stb6100_regmask stb6100_template[] = {
117 [STB6100_TEST3] = { 0x00, 0xde }, 117 [STB6100_TEST3] = { 0x00, 0xde },
118}; 118};
119 119
120static void stb6100_normalise_regs(u8 regs[]) 120/*
121 * Currently unused. Some boards might need it in the future
122 */
123static inline void stb6100_normalise_regs(u8 regs[])
121{ 124{
122 int i; 125 int i;
123 126
@@ -157,13 +160,25 @@ static int stb6100_read_reg(struct stb6100_state *state, u8 reg)
157 u8 regs[STB6100_NUMREGS]; 160 u8 regs[STB6100_NUMREGS];
158 int rc; 161 int rc;
159 162
163 struct i2c_msg msg = {
164 .addr = state->config->tuner_address + reg,
165 .flags = I2C_M_RD,
166 .buf = regs,
167 .len = 1
168 };
169
170 rc = i2c_transfer(state->i2c, &msg, 1);
171
160 if (unlikely(reg >= STB6100_NUMREGS)) { 172 if (unlikely(reg >= STB6100_NUMREGS)) {
161 dprintk(verbose, FE_ERROR, 1, "Invalid register offset 0x%x", reg); 173 dprintk(verbose, FE_ERROR, 1, "Invalid register offset 0x%x", reg);
162 return -EINVAL; 174 return -EINVAL;
163 } 175 }
164 if ((rc = stb6100_read_regs(state, regs)) < 0) 176 if (unlikely(verbose > FE_DEBUG)) {
165 return rc; 177 dprintk(verbose, FE_DEBUG, 1, " Read from 0x%02x", state->config->tuner_address);
166 return (unsigned int)regs[reg]; 178 dprintk(verbose, FE_DEBUG, 1, " %s: 0x%02x", stb6100_regnames[reg], regs[0]);
179 }
180
181 return (unsigned int)regs[0];
167} 182}
168 183
169static int stb6100_write_reg_range(struct stb6100_state *state, u8 buf[], int start, int len) 184static int stb6100_write_reg_range(struct stb6100_state *state, u8 buf[], int start, int len)
@@ -211,20 +226,17 @@ static int stb6100_write_reg(struct stb6100_state *state, u8 reg, u8 data)
211 return stb6100_write_reg_range(state, &data, reg, 1); 226 return stb6100_write_reg_range(state, &data, reg, 1);
212} 227}
213 228
214static int stb6100_write_regs(struct stb6100_state *state, u8 regs[])
215{
216 stb6100_normalise_regs(regs);
217 return stb6100_write_reg_range(state, &regs[1], 1, STB6100_NUMREGS - 1);
218}
219 229
220static int stb6100_get_status(struct dvb_frontend *fe, u32 *status) 230static int stb6100_get_status(struct dvb_frontend *fe, u32 *status)
221{ 231{
222 int rc; 232 int rc;
223 struct stb6100_state *state = fe->tuner_priv; 233 struct stb6100_state *state = fe->tuner_priv;
224 234
225 if ((rc = stb6100_read_reg(state, STB6100_LD)) < 0) 235 rc = stb6100_read_reg(state, STB6100_LD);
236 if (rc < 0) {
237 dprintk(verbose, FE_ERROR, 1, "%s failed", __func__);
226 return rc; 238 return rc;
227 239 }
228 return (rc & STB6100_LD_LOCK) ? TUNER_STATUS_LOCKED : 0; 240 return (rc & STB6100_LD_LOCK) ? TUNER_STATUS_LOCKED : 0;
229} 241}
230 242
@@ -234,7 +246,8 @@ static int stb6100_get_bandwidth(struct dvb_frontend *fe, u32 *bandwidth)
234 u8 f; 246 u8 f;
235 struct stb6100_state *state = fe->tuner_priv; 247 struct stb6100_state *state = fe->tuner_priv;
236 248
237 if ((rc = stb6100_read_reg(state, STB6100_F)) < 0) 249 rc = stb6100_read_reg(state, STB6100_F);
250 if (rc < 0)
238 return rc; 251 return rc;
239 f = rc & STB6100_F_F; 252 f = rc & STB6100_F_F;
240 253
@@ -265,14 +278,21 @@ static int stb6100_set_bandwidth(struct dvb_frontend *fe, u32 bandwidth)
265 /* Turn on LPF bandwidth setting clock control, 278 /* Turn on LPF bandwidth setting clock control,
266 * set bandwidth, wait 10ms, turn off. 279 * set bandwidth, wait 10ms, turn off.
267 */ 280 */
268 if ((rc = stb6100_write_reg(state, STB6100_FCCK, 0x0d | STB6100_FCCK_FCCK)) < 0) 281 rc = stb6100_write_reg(state, STB6100_FCCK, 0x0d | STB6100_FCCK_FCCK);
282 if (rc < 0)
269 return rc; 283 return rc;
270 if ((rc = stb6100_write_reg(state, STB6100_F, 0xc0 | tmp)) < 0) 284 rc = stb6100_write_reg(state, STB6100_F, 0xc0 | tmp);
285 if (rc < 0)
271 return rc; 286 return rc;
272 msleep(1); 287
273 if ((rc = stb6100_write_reg(state, STB6100_FCCK, 0x0d)) < 0) 288 msleep(5); /* This is dangerous as another (related) thread may start */
289
290 rc = stb6100_write_reg(state, STB6100_FCCK, 0x0d);
291 if (rc < 0)
274 return rc; 292 return rc;
275 293
294 msleep(10); /* This is dangerous as another (related) thread may start */
295
276 return 0; 296 return 0;
277} 297}
278 298
@@ -284,7 +304,8 @@ static int stb6100_get_frequency(struct dvb_frontend *fe, u32 *frequency)
284 struct stb6100_state *state = fe->tuner_priv; 304 struct stb6100_state *state = fe->tuner_priv;
285 u8 regs[STB6100_NUMREGS]; 305 u8 regs[STB6100_NUMREGS];
286 306
287 if ((rc = stb6100_read_regs(state, regs)) < 0) 307 rc = stb6100_read_regs(state, regs);
308 if (rc < 0)
288 return rc; 309 return rc;
289 310
290 odiv = (regs[STB6100_VCO] & STB6100_VCO_ODIV) >> STB6100_VCO_ODIV_SHIFT; 311 odiv = (regs[STB6100_VCO] & STB6100_VCO_ODIV) >> STB6100_VCO_ODIV_SHIFT;
@@ -312,8 +333,7 @@ static int stb6100_set_frequency(struct dvb_frontend *fe, u32 frequency)
312 u8 regs[STB6100_NUMREGS]; 333 u8 regs[STB6100_NUMREGS];
313 u8 g, psd2, odiv; 334 u8 g, psd2, odiv;
314 335
315 if ((rc = stb6100_read_regs(state, regs)) < 0) 336 dprintk(verbose, FE_DEBUG, 1, "Version 2010-8-14 13:51");
316 return rc;
317 337
318 if (fe->ops.get_frontend) { 338 if (fe->ops.get_frontend) {
319 dprintk(verbose, FE_DEBUG, 1, "Get frontend parameters"); 339 dprintk(verbose, FE_DEBUG, 1, "Get frontend parameters");
@@ -321,96 +341,140 @@ static int stb6100_set_frequency(struct dvb_frontend *fe, u32 frequency)
321 } 341 }
322 srate = p.u.qpsk.symbol_rate; 342 srate = p.u.qpsk.symbol_rate;
323 343
324 regs[STB6100_DLB] = 0xdc; 344 /* Set up tuner cleanly, LPF calibration on */
325 /* Disable LPEN */ 345 rc = stb6100_write_reg(state, STB6100_FCCK, 0x4d | STB6100_FCCK_FCCK);
326 regs[STB6100_LPEN] &= ~STB6100_LPEN_LPEN; /* PLL Loop disabled */ 346 if (rc < 0)
347 return rc; /* allow LPF calibration */
327 348
328 if ((rc = stb6100_write_regs(state, regs)) < 0) 349 /* PLL Loop disabled, bias on, VCO on, synth on */
350 regs[STB6100_LPEN] = 0xeb;
351 rc = stb6100_write_reg(state, STB6100_LPEN, regs[STB6100_LPEN]);
352 if (rc < 0)
329 return rc; 353 return rc;
330 354
331 /* Baseband gain. */ 355 /* Program the registers with their data values */
332 if (srate >= 15000000)
333 g = 9; // +4 dB
334 else if (srate >= 5000000)
335 g = 11; // +8 dB
336 else
337 g = 14; // +14 dB
338
339 regs[STB6100_G] = (regs[STB6100_G] & ~STB6100_G_G) | g;
340 regs[STB6100_G] &= ~STB6100_G_GCT; /* mask GCT */
341 regs[STB6100_G] |= (1 << 5); /* 2Vp-p Mode */
342 356
343 /* VCO divide ratio (LO divide ratio, VCO prescaler enable). */ 357 /* VCO divide ratio (LO divide ratio, VCO prescaler enable). */
344 if (frequency <= 1075000) 358 if (frequency <= 1075000)
345 odiv = 1; 359 odiv = 1;
346 else 360 else
347 odiv = 0; 361 odiv = 0;
348 regs[STB6100_VCO] = (regs[STB6100_VCO] & ~STB6100_VCO_ODIV) | (odiv << STB6100_VCO_ODIV_SHIFT);
349 362
350 if ((frequency > 1075000) && (frequency <= 1325000)) 363 /* VCO enabled, seach clock off as per LL3.7, 3.4.1 */
351 psd2 = 0; 364 regs[STB6100_VCO] = 0xe0 | (odiv << STB6100_VCO_ODIV_SHIFT);
352 else
353 psd2 = 1;
354 regs[STB6100_K] = (regs[STB6100_K] & ~STB6100_K_PSD2) | (psd2 << STB6100_K_PSD2_SHIFT);
355 365
356 /* OSM */ 366 /* OSM */
357 for (ptr = lkup; 367 for (ptr = lkup;
358 (ptr->val_high != 0) && !CHKRANGE(frequency, ptr->val_low, ptr->val_high); 368 (ptr->val_high != 0) && !CHKRANGE(frequency, ptr->val_low, ptr->val_high);
359 ptr++); 369 ptr++);
370
360 if (ptr->val_high == 0) { 371 if (ptr->val_high == 0) {
361 printk(KERN_ERR "%s: frequency out of range: %u kHz\n", __func__, frequency); 372 printk(KERN_ERR "%s: frequency out of range: %u kHz\n", __func__, frequency);
362 return -EINVAL; 373 return -EINVAL;
363 } 374 }
364 regs[STB6100_VCO] = (regs[STB6100_VCO] & ~STB6100_VCO_OSM) | ptr->reg; 375 regs[STB6100_VCO] = (regs[STB6100_VCO] & ~STB6100_VCO_OSM) | ptr->reg;
376 rc = stb6100_write_reg(state, STB6100_VCO, regs[STB6100_VCO]);
377 if (rc < 0)
378 return rc;
365 379
380 if ((frequency > 1075000) && (frequency <= 1325000))
381 psd2 = 0;
382 else
383 psd2 = 1;
366 /* F(VCO) = F(LO) * (ODIV == 0 ? 2 : 4) */ 384 /* F(VCO) = F(LO) * (ODIV == 0 ? 2 : 4) */
367 fvco = frequency << (1 + odiv); 385 fvco = frequency << (1 + odiv);
368 /* N(I) = floor(f(VCO) / (f(XTAL) * (PSD2 ? 2 : 1))) */ 386 /* N(I) = floor(f(VCO) / (f(XTAL) * (PSD2 ? 2 : 1))) */
369 nint = fvco / (state->reference << psd2); 387 nint = fvco / (state->reference << psd2);
370 /* N(F) = round(f(VCO) / f(XTAL) * (PSD2 ? 2 : 1) - N(I)) * 2 ^ 9 */ 388 /* N(F) = round(f(VCO) / f(XTAL) * (PSD2 ? 2 : 1) - N(I)) * 2 ^ 9 */
371 nfrac = DIV_ROUND_CLOSEST((fvco - (nint * state->reference << psd2)) 389 nfrac = DIV_ROUND_CLOSEST((fvco - (nint * state->reference << psd2))
372 << (9 - psd2), 390 << (9 - psd2), state->reference);
373 state->reference); 391
392 /* NI */
393 regs[STB6100_NI] = nint;
394 rc = stb6100_write_reg(state, STB6100_NI, regs[STB6100_NI]);
395 if (rc < 0)
396 return rc;
397
398 /* NF */
399 regs[STB6100_NF_LSB] = nfrac;
400 rc = stb6100_write_reg(state, STB6100_NF_LSB, regs[STB6100_NF_LSB]);
401 if (rc < 0)
402 return rc;
403
404 /* K */
405 regs[STB6100_K] = (0x38 & ~STB6100_K_PSD2) | (psd2 << STB6100_K_PSD2_SHIFT);
406 regs[STB6100_K] = (regs[STB6100_K] & ~STB6100_K_NF_MSB) | ((nfrac >> 8) & STB6100_K_NF_MSB);
407 rc = stb6100_write_reg(state, STB6100_K, regs[STB6100_K]);
408 if (rc < 0)
409 return rc;
410
411 /* G Baseband gain. */
412 if (srate >= 15000000)
413 g = 9; /* +4 dB */
414 else if (srate >= 5000000)
415 g = 11; /* +8 dB */
416 else
417 g = 14; /* +14 dB */
418
419 regs[STB6100_G] = (0x10 & ~STB6100_G_G) | g;
420 regs[STB6100_G] &= ~STB6100_G_GCT; /* mask GCT */
421 regs[STB6100_G] |= (1 << 5); /* 2Vp-p Mode */
422 rc = stb6100_write_reg(state, STB6100_G, regs[STB6100_G]);
423 if (rc < 0)
424 return rc;
425
426 /* F we don't write as it is set up in BW set */
427
428 /* DLB set DC servo loop BW to 160Hz (LLA 3.8 / 2.1) */
429 regs[STB6100_DLB] = 0xcc;
430 rc = stb6100_write_reg(state, STB6100_DLB, regs[STB6100_DLB]);
431 if (rc < 0)
432 return rc;
433
374 dprintk(verbose, FE_DEBUG, 1, 434 dprintk(verbose, FE_DEBUG, 1,
375 "frequency = %u, srate = %u, g = %u, odiv = %u, psd2 = %u, fxtal = %u, osm = %u, fvco = %u, N(I) = %u, N(F) = %u", 435 "frequency = %u, srate = %u, g = %u, odiv = %u, psd2 = %u, fxtal = %u, osm = %u, fvco = %u, N(I) = %u, N(F) = %u",
376 frequency, srate, (unsigned int)g, (unsigned int)odiv, 436 frequency, srate, (unsigned int)g, (unsigned int)odiv,
377 (unsigned int)psd2, state->reference, 437 (unsigned int)psd2, state->reference,
378 ptr->reg, fvco, nint, nfrac); 438 ptr->reg, fvco, nint, nfrac);
379 regs[STB6100_NI] = nint;
380 regs[STB6100_NF_LSB] = nfrac;
381 regs[STB6100_K] = (regs[STB6100_K] & ~STB6100_K_NF_MSB) | ((nfrac >> 8) & STB6100_K_NF_MSB);
382 regs[STB6100_VCO] |= STB6100_VCO_OSCH; /* VCO search enabled */
383 regs[STB6100_VCO] |= STB6100_VCO_OCK; /* VCO search clock off */
384 regs[STB6100_FCCK] |= STB6100_FCCK_FCCK; /* LPF BW setting clock enabled */
385 regs[STB6100_LPEN] &= ~STB6100_LPEN_LPEN; /* PLL loop disabled */
386 /* Power up. */
387 regs[STB6100_LPEN] |= STB6100_LPEN_SYNP | STB6100_LPEN_OSCP | STB6100_LPEN_BEN;
388 439
389 msleep(2); 440 /* Set up the test registers */
390 if ((rc = stb6100_write_regs(state, regs)) < 0) 441 regs[STB6100_TEST1] = 0x8f;
442 rc = stb6100_write_reg(state, STB6100_TEST1, regs[STB6100_TEST1]);
443 if (rc < 0)
444 return rc;
445 regs[STB6100_TEST3] = 0xde;
446 rc = stb6100_write_reg(state, STB6100_TEST3, regs[STB6100_TEST3]);
447 if (rc < 0)
391 return rc; 448 return rc;
392 449
393 msleep(2); 450 /* Bring up tuner according to LLA 3.7 3.4.1, step 2 */
394 regs[STB6100_LPEN] |= STB6100_LPEN_LPEN; /* PLL loop enabled */ 451 regs[STB6100_LPEN] = 0xfb; /* PLL Loop enabled, bias on, VCO on, synth on */
395 if ((rc = stb6100_write_reg(state, STB6100_LPEN, regs[STB6100_LPEN])) < 0) 452 rc = stb6100_write_reg(state, STB6100_LPEN, regs[STB6100_LPEN]);
453 if (rc < 0)
396 return rc; 454 return rc;
397 455
456 msleep(2);
457
458 /* Bring up tuner according to LLA 3.7 3.4.1, step 3 */
398 regs[STB6100_VCO] &= ~STB6100_VCO_OCK; /* VCO fast search */ 459 regs[STB6100_VCO] &= ~STB6100_VCO_OCK; /* VCO fast search */
399 if ((rc = stb6100_write_reg(state, STB6100_VCO, regs[STB6100_VCO])) < 0) 460 rc = stb6100_write_reg(state, STB6100_VCO, regs[STB6100_VCO]);
461 if (rc < 0)
400 return rc; 462 return rc;
401 463
402 msleep(10); /* wait for LO to lock */ 464 msleep(10); /* This is dangerous as another (related) thread may start */ /* wait for LO to lock */
465
403 regs[STB6100_VCO] &= ~STB6100_VCO_OSCH; /* vco search disabled */ 466 regs[STB6100_VCO] &= ~STB6100_VCO_OSCH; /* vco search disabled */
404 regs[STB6100_VCO] |= STB6100_VCO_OCK; /* search clock off */ 467 regs[STB6100_VCO] |= STB6100_VCO_OCK; /* search clock off */
405 if ((rc = stb6100_write_reg(state, STB6100_VCO, regs[STB6100_VCO])) < 0) 468 rc = stb6100_write_reg(state, STB6100_VCO, regs[STB6100_VCO]);
406 return rc; 469 if (rc < 0)
407 regs[STB6100_FCCK] &= ~STB6100_FCCK_FCCK; /* LPF BW clock disabled */
408 stb6100_normalise_regs(regs);
409 if ((rc = stb6100_write_reg_range(state, &regs[1], 1, STB6100_NUMREGS - 3)) < 0)
410 return rc; 470 return rc;
411 471
412 msleep(100); 472 rc = stb6100_write_reg(state, STB6100_FCCK, 0x0d);
473 if (rc < 0)
474 return rc; /* Stop LPF calibration */
413 475
476 msleep(10); /* This is dangerous as another (related) thread may start */
477 /* wait for stabilisation, (should not be necessary) */
414 return 0; 478 return 0;
415} 479}
416 480
@@ -433,8 +497,8 @@ static int stb6100_init(struct dvb_frontend *fe)
433 state->bandwidth = status->bandwidth * 1000; /* Hz */ 497 state->bandwidth = status->bandwidth * 1000; /* Hz */
434 state->reference = status->refclock / 1000; /* kHz */ 498 state->reference = status->refclock / 1000; /* kHz */
435 499
436 /* Set default bandwidth. */ 500 /* Set default bandwidth. Modified, PN 13-May-10 */
437 return stb6100_set_bandwidth(fe, state->bandwidth); 501 return 0;
438} 502}
439 503
440static int stb6100_get_state(struct dvb_frontend *fe, 504static int stb6100_get_state(struct dvb_frontend *fe,
diff --git a/drivers/media/dvb/frontends/stv090x.c b/drivers/media/dvb/frontends/stv090x.c
index 425e7a43ae19..4e0fc2c8a41c 100644
--- a/drivers/media/dvb/frontends/stv090x.c
+++ b/drivers/media/dvb/frontends/stv090x.c
@@ -1483,8 +1483,8 @@ static int stv090x_start_search(struct stv090x_state *state)
1483 if (STV090x_WRITE_DEMOD(state, FFECFG, 0x41) < 0) 1483 if (STV090x_WRITE_DEMOD(state, FFECFG, 0x41) < 0)
1484 goto err; 1484 goto err;
1485 1485
1486 if ((state->search_mode == STV090x_DVBS1) || 1486 if ((state->search_mode == STV090x_SEARCH_DVBS1) ||
1487 (state->search_mode == STV090x_DSS) || 1487 (state->search_mode == STV090x_SEARCH_DSS) ||
1488 (state->search_mode == STV090x_SEARCH_AUTO)) { 1488 (state->search_mode == STV090x_SEARCH_AUTO)) {
1489 1489
1490 if (STV090x_WRITE_DEMOD(state, VITSCALE, 0x82) < 0) 1490 if (STV090x_WRITE_DEMOD(state, VITSCALE, 0x82) < 0)
@@ -2940,7 +2940,7 @@ static int stv090x_optimize_track(struct stv090x_state *state)
2940 STV090x_WRITE_DEMOD(state, ERRCTRL1, 0x67); /* PER */ 2940 STV090x_WRITE_DEMOD(state, ERRCTRL1, 0x67); /* PER */
2941 break; 2941 break;
2942 2942
2943 case STV090x_UNKNOWN: 2943 case STV090x_ERROR:
2944 default: 2944 default:
2945 reg = STV090x_READ_DEMOD(state, DMDCFGMD); 2945 reg = STV090x_READ_DEMOD(state, DMDCFGMD);
2946 STV090x_SETFIELD_Px(reg, DVBS1_ENABLE_FIELD, 1); 2946 STV090x_SETFIELD_Px(reg, DVBS1_ENABLE_FIELD, 1);