From 8170f63b4f68b213df59709d4d9447029bdf3816 Mon Sep 17 00:00:00 2001 From: Stephan Raue Date: Wed, 24 Apr 2013 01:43:31 +0200 Subject: [PATCH] linux: update DVBSky patch, update kernel configs Signed-off-by: Stephan Raue --- .../patches/3.8.8/linux-210-dvbsky.patch | 5388 +++++++++-------- projects/ARCTIC_MC/linux/linux.x86_64.conf | 1 + projects/ATV/linux/linux.i386.conf | 4 +- projects/Fusion/linux/linux.i386.conf | 3 +- projects/Fusion/linux/linux.x86_64.conf | 3 +- projects/Generic/linux/linux.i386.conf | 3 +- projects/Generic_OSS/linux/linux.i386.conf | 3 +- projects/ION/linux/linux.i386.conf | 3 +- projects/ION/linux/linux.x86_64.conf | 3 +- projects/Intel/linux/linux.i386.conf | 3 +- projects/Intel/linux/linux.x86_64.conf | 3 +- projects/RPi/linux/linux.arm.conf | 1 + projects/Ultra/linux/linux.x86_64.conf | 3 +- projects/Virtual/linux/linux.i386.conf | 3 +- projects/Virtual/linux/linux.x86_64.conf | 3 +- 15 files changed, 2786 insertions(+), 2641 deletions(-) diff --git a/packages/linux/patches/3.8.8/linux-210-dvbsky.patch b/packages/linux/patches/3.8.8/linux-210-dvbsky.patch index 9e2bdf416b..28b6d412c4 100644 --- a/packages/linux/patches/3.8.8/linux-210-dvbsky.patch +++ b/packages/linux/patches/3.8.8/linux-210-dvbsky.patch @@ -1,49 +1,7 @@ -From 8d189966ad4d494c9630d2b1c41a0ff9ccaa3d0a Mon Sep 17 00:00:00 2001 -From: Stefan Saraev -Date: Tue, 26 Mar 2013 12:52:27 +0200 -Subject: [PATCH] dvbsky - ---- - drivers/media/dvb-frontends/Kconfig | 14 + - drivers/media/dvb-frontends/Makefile | 2 + - drivers/media/dvb-frontends/m88dc2800.c | 2235 ++++++++++++++++++++++++++ - drivers/media/dvb-frontends/m88dc2800.h | 43 + - drivers/media/dvb-frontends/m88ds3103.c | 1710 ++++++++++++++++++++ - drivers/media/dvb-frontends/m88ds3103.h | 53 + - drivers/media/dvb-frontends/m88ds3103_priv.h | 403 +++++ - drivers/media/pci/cx23885/Kconfig | 2 + - drivers/media/pci/cx23885/cimax2.c | 23 +- - drivers/media/pci/cx23885/cimax2.h | 4 +- - drivers/media/pci/cx23885/cx23885-cards.c | 172 ++- - drivers/media/pci/cx23885/cx23885-core.c | 6 + - drivers/media/pci/cx23885/cx23885-dvb.c | 207 ++- - drivers/media/pci/cx23885/cx23885-f300.c | 55 + - drivers/media/pci/cx23885/cx23885-f300.h | 6 + - drivers/media/pci/cx23885/cx23885-input.c | 21 + - drivers/media/pci/cx23885/cx23885.h | 9 +- - drivers/media/pci/cx88/Kconfig | 1 + - drivers/media/pci/cx88/cx88-cards.c | 22 + - drivers/media/pci/cx88/cx88-dvb.c | 85 + - drivers/media/pci/cx88/cx88-input.c | 4 + - drivers/media/pci/cx88/cx88.h | 3 +- - drivers/media/rc/keymaps/Makefile | 1 + - drivers/media/rc/keymaps/rc-dvbsky.c | 78 + - drivers/media/usb/dvb-usb/Kconfig | 1 + - drivers/media/usb/dvb-usb/dw2102.c | 280 ++++ - include/media/rc-map.h | 1 + - 27 files changed, 5384 insertions(+), 57 deletions(-) - create mode 100644 drivers/media/dvb-frontends/m88dc2800.c - create mode 100644 drivers/media/dvb-frontends/m88dc2800.h - create mode 100644 drivers/media/dvb-frontends/m88ds3103.c - create mode 100644 drivers/media/dvb-frontends/m88ds3103.h - create mode 100644 drivers/media/dvb-frontends/m88ds3103_priv.h - create mode 100644 drivers/media/rc/keymaps/rc-dvbsky.c - -diff --git a/drivers/media/dvb-frontends/Kconfig b/drivers/media/dvb-frontends/Kconfig -index e2483f9..743b4d0 100644 ---- a/drivers/media/dvb-frontends/Kconfig -+++ b/drivers/media/dvb-frontends/Kconfig -@@ -218,6 +218,20 @@ config DVB_CX24116 +diff -urN a/drivers/media/dvb-frontends/Kconfig b/drivers/media/dvb-frontends/Kconfig +--- a/drivers/media/dvb-frontends/Kconfig 2013-03-21 04:11:19.000000000 +0800 ++++ b/drivers/media/dvb-frontends/Kconfig 2013-04-23 22:14:23.000000000 +0800 +@@ -200,6 +200,20 @@ help A DVB-S/S2 tuner module. Say Y when you want to support this frontend. @@ -60,33 +18,20 @@ index e2483f9..743b4d0 100644 + default m if !MEDIA_SUBDRV_AUTOSELECT + help + A DVB-C tuner module. Say Y when you want to support this frontend. -+ ++ config DVB_SI21XX tristate "Silicon Labs SI21XX based" depends on DVB_CORE && I2C -diff --git a/drivers/media/dvb-frontends/Makefile b/drivers/media/dvb-frontends/Makefile -index b8820aa..8528900 100644 ---- a/drivers/media/dvb-frontends/Makefile -+++ b/drivers/media/dvb-frontends/Makefile -@@ -104,4 +104,6 @@ obj-$(CONFIG_DVB_RTL2830) += rtl2830.o - obj-$(CONFIG_DVB_RTL2832) += rtl2832.o - obj-$(CONFIG_DVB_M88RS2000) += m88rs2000.o - obj-$(CONFIG_DVB_AF9033) += af9033.o -+obj-$(CONFIG_DVB_M88DS3103) += m88ds3103.o -+obj-$(CONFIG_DVB_M88DC2800) += m88dc2800.o - -diff --git a/drivers/media/dvb-frontends/m88dc2800.c b/drivers/media/dvb-frontends/m88dc2800.c -new file mode 100644 -index 0000000..f48a356 ---- /dev/null -+++ b/drivers/media/dvb-frontends/m88dc2800.c -@@ -0,0 +1,2235 @@ +diff -urN a/drivers/media/dvb-frontends/m88dc2800.c b/drivers/media/dvb-frontends/m88dc2800.c +--- a/drivers/media/dvb-frontends/m88dc2800.c 1970-01-01 08:00:00.000000000 +0800 ++++ b/drivers/media/dvb-frontends/m88dc2800.c 2013-01-26 16:03:21.000000000 +0800 +@@ -0,0 +1,2124 @@ +/* + M88DC2800/M88TC2800 - DVB-C demodulator and tuner from Montage + + Copyright (C) 2012 Max nibble -+ Copyright (C) 2011 Montage Technology -+ ++ Copyright (C) 2011 Montage Technology / www.montage-tech.com ++ + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or @@ -114,28 +59,28 @@ index 0000000..f48a356 +#include "m88dc2800.h" + +struct m88dc2800_state { -+ struct i2c_adapter* i2c; -+ const struct m88dc2800_config *config; -+ struct dvb_frontend frontend; ++ struct i2c_adapter *i2c; ++ const struct m88dc2800_config *config; ++ struct dvb_frontend frontend; + u32 freq; + u32 ber; + u32 sym; + u16 qam; + u8 inverted; + u32 xtal; -+ /*tuner state*/ -+ u8 tuner_init_OK; /* Tuner initialize status */ -+ u8 tuner_dev_addr; /* Tuner device address */ -+ u32 tuner_freq; /* RF frequency to be set, unit: KHz */ -+ u16 tuner_qam; /* Reserved */ -+ u16 tuner_mode; -+ u8 tuner_bandwidth; /* Bandwidth of the channel, unit: MHz, 6/7/8 */ -+ u8 tuner_loopthrough; /* Tuner loop through switch, 0/1 */ -+ u32 tuner_crystal; /* Tuner crystal frequency, unit: KHz */ -+ u32 tuner_dac; /* Tuner DAC frequency, unit: KHz */ -+ u16 tuner_mtt; /* Tuner chip version, D1: 0x0d, E0: 0x0e, E1: 0x8e */ -+ u16 tuner_custom_cfg; -+ u32 tuner_version; /* Tuner driver version number */ ++ /* tuner state */ ++ u8 tuner_init_OK; /* Tuner initialize status */ ++ u8 tuner_dev_addr; /* Tuner device address */ ++ u32 tuner_freq; /* RF frequency to be set, unit: KHz */ ++ u16 tuner_qam; /* Reserved */ ++ u16 tuner_mode; ++ u8 tuner_bandwidth; /* Bandwidth of the channel, unit: MHz, 6/7/8 */ ++ u8 tuner_loopthrough; /* Tuner loop through switch, 0/1 */ ++ u32 tuner_crystal; /* Tuner crystal frequency, unit: KHz */ ++ u32 tuner_dac; /* Tuner DAC frequency, unit: KHz */ ++ u16 tuner_mtt; /* Tuner chip version, D1: 0x0d, E0: 0x0e, E1: 0x8e */ ++ u16 tuner_custom_cfg; ++ u32 tuner_version; /* Tuner driver version number */ + u32 tuner_time; +}; + @@ -150,25 +95,27 @@ index 0000000..f48a356 + } while (0) + + -+static int m88dc2800_i2c_write(struct m88dc2800_state *state, u8 addr, u8 *p_data, u8 len) ++static int m88dc2800_i2c_write(struct m88dc2800_state *state, u8 addr, ++ u8 * p_data, u8 len) +{ + struct i2c_msg msg = { .flags = 0 }; -+ ++ + msg.addr = addr; + msg.buf = p_data; + msg.len = len; -+ ++ + return i2c_transfer(state->i2c, &msg, 1); +} + -+static int m88dc2800_i2c_read(struct m88dc2800_state *state, u8 addr, u8 *p_data, u8 len) ++static int m88dc2800_i2c_read(struct m88dc2800_state *state, u8 addr, ++ u8 * p_data, u8 len) +{ + struct i2c_msg msg = { .flags = I2C_M_RD }; -+ ++ + msg.addr = addr; + msg.buf = p_data; + msg.len = len; -+ ++ + return i2c_transfer(state->i2c, &msg, 1); +} + @@ -179,15 +126,14 @@ index 0000000..f48a356 + u8 addr = state->config->demod_address; + int err; + -+ if (debug > 1) -+ printk("m88dc2800: %s: write reg 0x%02x, value 0x%02x\n", -+ __func__, reg, data); ++ dprintk("%s: write reg 0x%02x, value 0x%02x\n", __func__, reg, data); + + err = m88dc2800_i2c_write(state, addr, buf, 2); + + if (err != 1) { -+ printk(KERN_ERR "%s: writereg error(err == %i, reg == 0x%02x," -+ " value == 0x%02x)\n", __func__, err, reg, data); ++ printk(KERN_ERR ++ "%s: writereg error(err == %i, reg == 0x%02x," ++ " value == 0x%02x)\n", __func__, err, reg, data); + return -EIO; + } + return 0; @@ -199,1831 +145,1710 @@ index 0000000..f48a356 + u8 b0[] = { reg }; + u8 b1[] = { 0 }; + u8 addr = state->config->demod_address; -+ ++ + ret = m88dc2800_i2c_write(state, addr, b0, 1); -+ ++ + if (ret != 1) { + printk(KERN_ERR "%s: reg=0x%x (error=%d)\n", -+ __func__, reg, ret); ++ __func__, reg, ret); + return -EIO; + } -+ ++ + ret = m88dc2800_i2c_read(state, addr, b1, 1); + -+ if (debug > 1) -+ printk(KERN_INFO "m88dc2800: read reg 0x%02x, value 0x%02x\n", -+ reg, b1[0]); ++ dprintk("%s: read reg 0x%02x, value 0x%02x\n", __func__, reg, b1[0]); + return b1[0]; +} + -+static int _mt_fe_tn_set_reg(struct m88dc2800_state *state, u8 reg, u8 data) ++static int _mt_fe_tn_set_reg(struct m88dc2800_state *state, u8 reg, ++ u8 data) +{ + int ret; -+ u8 buf[2]; ++ u8 buf[2]; + u8 addr = state->tuner_dev_addr; -+ ++ + buf[1] = ReadReg(state, 0x86); + buf[1] |= 0x80; + ret = WriteReg(state, 0x86, buf[1]); -+ ++ + buf[0] = reg; + buf[1] = data; -+ ++ + ret = m88dc2800_i2c_write(state, addr, buf, 2); -+ if(ret != 1) -+ return -EIO; -+ return 0; ++ if (ret != 1) ++ return -EIO; ++ return 0; +} + -+static int _mt_fe_tn_get_reg(struct m88dc2800_state *state, u8 reg, u8 *p_data) ++static int _mt_fe_tn_get_reg(struct m88dc2800_state *state, u8 reg, ++ u8 * p_data) +{ + int ret; -+ u8 buf[2]; ++ u8 buf[2]; + u8 addr = state->tuner_dev_addr; -+ ++ + buf[1] = ReadReg(state, 0x86); + buf[1] |= 0x80; + ret = WriteReg(state, 0x86, buf[1]); -+ ++ + buf[0] = reg; + ret = m88dc2800_i2c_write(state, addr, buf, 1); -+ ++ + msleep(1); -+ ++ + buf[1] = ReadReg(state, 0x86); + buf[1] |= 0x80; + ret = WriteReg(state, 0x86, buf[1]); -+ -+ return m88dc2800_i2c_read(state, addr, p_data, 1); ++ ++ return m88dc2800_i2c_read(state, addr, p_data, 1); +} + +/* Tuner operation functions.*/ -+static int _mt_fe_tn_set_RF_front_tc2800(struct m88dc2800_state *state) -+{ -+ u32 freq_KHz = state->tuner_freq; -+ -+ if (state->tuner_mtt == 0xD1) { /* D1 */ -+ if (freq_KHz <= 123000) { -+ if (freq_KHz <= 56000) { -+ _mt_fe_tn_set_reg(state, 0x58, 0x9b); -+ _mt_fe_tn_set_reg(state, 0x59, 0x00); -+ _mt_fe_tn_set_reg(state, 0x5d, 0x00); -+ _mt_fe_tn_set_reg(state, 0x5e, 0x00); -+ }else if (freq_KHz <= 64000) { -+ _mt_fe_tn_set_reg(state, 0x58, 0x9b); -+ _mt_fe_tn_set_reg(state, 0x59, 0x10); -+ _mt_fe_tn_set_reg(state, 0x5d, 0x01); -+ _mt_fe_tn_set_reg(state, 0x5e, 0x08); -+ }else if (freq_KHz <= 72000) { -+ _mt_fe_tn_set_reg(state, 0x58, 0x9b); -+ _mt_fe_tn_set_reg(state, 0x59, 0x20); -+ _mt_fe_tn_set_reg(state, 0x5d, 0x02); -+ _mt_fe_tn_set_reg(state, 0x5e, 0x10); -+ }else if (freq_KHz <= 80000) { -+ _mt_fe_tn_set_reg(state, 0x58, 0x9b); -+ _mt_fe_tn_set_reg(state, 0x59, 0x30); -+ _mt_fe_tn_set_reg(state, 0x5d, 0x03); -+ _mt_fe_tn_set_reg(state, 0x5e, 0x18); -+ }else if (freq_KHz <= 88000) { -+ _mt_fe_tn_set_reg(state, 0x58, 0x9b); -+ _mt_fe_tn_set_reg(state, 0x59, 0x40); -+ _mt_fe_tn_set_reg(state, 0x5d, 0x04); -+ _mt_fe_tn_set_reg(state, 0x5e, 0x20); -+ }else if (freq_KHz <= 96000) { -+ _mt_fe_tn_set_reg(state, 0x58, 0x9b); -+ _mt_fe_tn_set_reg(state, 0x59, 0x50); -+ _mt_fe_tn_set_reg(state, 0x5d, 0x05); -+ _mt_fe_tn_set_reg(state, 0x5e, 0x28); -+ }else if (freq_KHz <= 104000) { -+ _mt_fe_tn_set_reg(state, 0x58, 0x9b); -+ _mt_fe_tn_set_reg(state, 0x59, 0x60); -+ _mt_fe_tn_set_reg(state, 0x5d, 0x06); -+ _mt_fe_tn_set_reg(state, 0x5e, 0x30); -+ }else { -+ _mt_fe_tn_set_reg(state, 0x58, 0x9b); -+ _mt_fe_tn_set_reg(state, 0x59, 0x70); -+ _mt_fe_tn_set_reg(state, 0x5d, 0x07); -+ _mt_fe_tn_set_reg(state, 0x5e, 0x38); -+ } -+ _mt_fe_tn_set_reg(state, 0x5a, 0x75); -+ _mt_fe_tn_set_reg(state, 0x73, 0x0c); -+ } else { /* if (freq_KHz > 112000) */ -+ _mt_fe_tn_set_reg(state, 0x58, 0x7b); -+ if (freq_KHz <= 304000) { -+ if (freq_KHz <= 136000) { -+ _mt_fe_tn_set_reg(state, 0x5e, 0x40); -+ }else if (freq_KHz <= 160000) { -+ _mt_fe_tn_set_reg(state, 0x5e, 0x48); -+ }else if (freq_KHz <= 184000) { -+ _mt_fe_tn_set_reg(state, 0x5e, 0x50); -+ }else if (freq_KHz <= 208000) { -+ _mt_fe_tn_set_reg(state, 0x5e, 0x58); -+ }else if (freq_KHz <= 232000) { -+ _mt_fe_tn_set_reg(state, 0x5e, 0x60); -+ }else if (freq_KHz <= 256000) { -+ _mt_fe_tn_set_reg(state, 0x5e, 0x68); -+ }else if (freq_KHz <= 280000) { -+ _mt_fe_tn_set_reg(state, 0x5e, 0x70); -+ }else { /*if (freq_KHz <= 304000)*/ -+ _mt_fe_tn_set_reg(state, 0x5e, 0x78); -+ } -+ if (freq_KHz <= 171000) { -+ _mt_fe_tn_set_reg(state, 0x73, 0x08); -+ }else if (freq_KHz <= 211000) { -+ _mt_fe_tn_set_reg(state, 0x73, 0x0a); -+ }else { -+ _mt_fe_tn_set_reg(state, 0x73, 0x0e); -+ } -+ }else { /* if (freq_KHz > 304000) */ -+ _mt_fe_tn_set_reg(state, 0x5e, 0x88); -+ if (freq_KHz <= 400000) { -+ _mt_fe_tn_set_reg(state, 0x73, 0x0c); -+ }else if (freq_KHz <= 450000) { -+ _mt_fe_tn_set_reg(state, 0x73, 0x09); -+ }else if (freq_KHz <= 550000) { -+ _mt_fe_tn_set_reg(state, 0x73, 0x0e); -+ }else if (freq_KHz <= 650000) { -+ _mt_fe_tn_set_reg(state, 0x73, 0x0d); -+ }else { /*if (freq_KHz > 650000) */ -+ _mt_fe_tn_set_reg(state, 0x73, 0x0e); -+ } -+ } -+ } -+ -+ if (freq_KHz > 800000) -+ _mt_fe_tn_set_reg(state, 0x87, 0x24); -+ else if (freq_KHz > 700000) -+ _mt_fe_tn_set_reg(state, 0x87, 0x34); -+ else if (freq_KHz > 500000) -+ _mt_fe_tn_set_reg(state, 0x87, 0x44); -+ else if (freq_KHz > 300000) -+ _mt_fe_tn_set_reg(state, 0x87, 0x43); -+ else if (freq_KHz > 220000) -+ _mt_fe_tn_set_reg(state, 0x87, 0x54); -+ else if (freq_KHz > 110000) -+ _mt_fe_tn_set_reg(state, 0x87, 0x14); -+ else -+ _mt_fe_tn_set_reg(state, 0x87, 0x54); -+ -+ if (freq_KHz > 600000) -+ _mt_fe_tn_set_reg(state, 0x6a, 0x53); -+ else if (freq_KHz > 500000) -+ _mt_fe_tn_set_reg(state, 0x6a, 0x57); -+ else -+ _mt_fe_tn_set_reg(state, 0x6a, 0x59); -+ -+ if (freq_KHz < 200000) { -+ _mt_fe_tn_set_reg(state, 0x20, 0x5d); -+ }else if (freq_KHz < 500000) { -+ _mt_fe_tn_set_reg(state, 0x20, 0x7d); -+ }else { -+ _mt_fe_tn_set_reg(state, 0x20, 0xfd); -+ }/* end of 0xD1 */ -+ }else if (state->tuner_mtt == 0xE1) { /* E1 */ -+ if (freq_KHz <= 112000) { /* 123MHz */ -+ if (freq_KHz <= 56000) { -+ _mt_fe_tn_set_reg(state, 0x5c, 0x01); -+ }else if (freq_KHz <= 64000) { -+ _mt_fe_tn_set_reg(state, 0x5c, 0x09); -+ }else if (freq_KHz <= 72000) { -+ _mt_fe_tn_set_reg(state, 0x5c, 0x11); -+ }else if (freq_KHz <= 80000) { -+ _mt_fe_tn_set_reg(state, 0x5c, 0x19); -+ }else if (freq_KHz <= 88000) { -+ _mt_fe_tn_set_reg(state, 0x5c, 0x21); -+ }else if (freq_KHz <= 96000) { -+ _mt_fe_tn_set_reg(state, 0x5c, 0x29); -+ }else if (freq_KHz <= 104000) { -+ _mt_fe_tn_set_reg(state, 0x5c, 0x31); -+ }else {/* if (freq_KHz <= 112000) */ -+ _mt_fe_tn_set_reg(state, 0x5c, 0x39); -+ } -+ _mt_fe_tn_set_reg(state, 0x5b, 0x30); -+ }else { /* if (freq_KHz > 112000) */ -+ if (freq_KHz <= 304000) { -+ if (freq_KHz <= 136000) { -+ _mt_fe_tn_set_reg(state, 0x5c, 0x41); -+ }else if (freq_KHz <= 160000) { -+ _mt_fe_tn_set_reg(state, 0x5c, 0x49); -+ }else if (freq_KHz <= 184000) { -+ _mt_fe_tn_set_reg(state, 0x5c, 0x51); -+ }else if (freq_KHz <= 208000) { -+ _mt_fe_tn_set_reg(state, 0x5c, 0x59); -+ }else if (freq_KHz <= 232000) { -+ _mt_fe_tn_set_reg(state, 0x5c, 0x61); -+ }else if (freq_KHz <= 256000) { -+ _mt_fe_tn_set_reg(state, 0x5c, 0x69); -+ }else if (freq_KHz <= 280000) { -+ _mt_fe_tn_set_reg(state, 0x5c, 0x71); -+ }else { /*if (freq_KHz <= 304000)*/ -+ _mt_fe_tn_set_reg(state, 0x5c, 0x79); -+ } -+ -+ if (freq_KHz <= 150000) { -+ _mt_fe_tn_set_reg(state, 0x5b, 0x28); -+ }else if (freq_KHz <= 256000) { -+ _mt_fe_tn_set_reg(state, 0x5b, 0x29); -+ }else { -+ _mt_fe_tn_set_reg(state, 0x5b, 0x2a); -+ } -+ }else { /* if (freq_KHz > 304000) */ -+ if (freq_KHz <= 400000) { -+ _mt_fe_tn_set_reg(state, 0x5c, 0x89); -+ }else if (freq_KHz <= 450000) { -+ _mt_fe_tn_set_reg(state, 0x5c, 0x91); -+ }else if (freq_KHz <= 650000) { -+ _mt_fe_tn_set_reg(state, 0x5c, 0x98); -+ }else if (freq_KHz <= 850000) { -+ _mt_fe_tn_set_reg(state, 0x5c, 0xa0); -+ }else { -+ _mt_fe_tn_set_reg(state, 0x5c, 0xa8); -+ } -+ _mt_fe_tn_set_reg(state, 0x5b, 0x08); -+ } -+ } -+ } /* end of 0xE1 */ -+ return 0; -+} -+ -+static int _mt_fe_tn_cali_PLL_tc2800(struct m88dc2800_state *state, u32 freq_KHz, u32 cali_freq_thres_div2, u32 cali_freq_thres_div3r, u32 cali_freq_thres_div3) -+{ -+ s32 N, F, MUL; -+ u8 buf, tmp, tmp2; -+ s32 M; -+ const s32 crystal_KHz = state->tuner_crystal; -+ -+ if (state->tuner_mtt == 0xD1) { -+ M = state->tuner_crystal / 4000; -+ if (freq_KHz > cali_freq_thres_div2) { -+ MUL = 4; -+ tmp = 2; -+ }else if (freq_KHz > 300000) { -+ MUL = 8; -+ tmp = 3; -+ }else if (freq_KHz > (cali_freq_thres_div2 / 2)) { -+ MUL = 8; -+ tmp = 4; -+ }else if (freq_KHz > (cali_freq_thres_div2 / 4)) { -+ MUL = 16; -+ tmp = 5; -+ }else if (freq_KHz > (cali_freq_thres_div2 / 8)) { -+ MUL = 32; -+ tmp = 6; -+ }else if (freq_KHz > (cali_freq_thres_div2 / 16)){ -+ MUL = 64; -+ tmp = 7; -+ }else { /* invalid */ -+ MUL = 0; -+ tmp = 0; -+ return 1; -+ } -+ }else if (state->tuner_mtt == 0xE1) { -+ M = state->tuner_crystal / 1000; -+ -+ _mt_fe_tn_set_reg(state, 0x30, 0xff); -+ _mt_fe_tn_set_reg(state, 0x32, 0xe0); -+ _mt_fe_tn_set_reg(state, 0x33, 0x86); -+ _mt_fe_tn_set_reg(state, 0x37, 0x70); -+ _mt_fe_tn_set_reg(state, 0x38, 0x20); -+ _mt_fe_tn_set_reg(state, 0x39, 0x18); -+ _mt_fe_tn_set_reg(state, 0x89, 0x83); -+ -+ if (freq_KHz > cali_freq_thres_div2) { -+ M = M / 4; -+ MUL = 4; -+ tmp = 2; -+ tmp2 = M + 16; /*48*/ -+ }else if (freq_KHz > cali_freq_thres_div3r) { -+ M = M / 3; -+ MUL = 6; -+ tmp = 2; -+ tmp2 = M + 32; /*32*/ -+ }else if (freq_KHz > cali_freq_thres_div3) { -+ M = M / 3; -+ MUL = 6; -+ tmp = 2; -+ tmp2 = M; /*16*/ -+ }else if (freq_KHz > 304000) { -+ M = M / 4; -+ MUL = 8; -+ tmp = 3; -+ tmp2 = M + 16; /*48*/ -+ }else if (freq_KHz > (cali_freq_thres_div2 / 2)) { -+ M = M / 4; -+ MUL = 8; -+ tmp = 4; -+ tmp2 = M + 16; /*48*/ -+ }else if (freq_KHz > (cali_freq_thres_div3r / 2)) { -+ M = M / 3; -+ MUL = 12; -+ tmp = 4; -+ tmp2 = M + 32; /*32*/ -+ }else if (freq_KHz > (cali_freq_thres_div3 / 2)) { -+ M = M / 3; -+ MUL = 12; -+ tmp = 4; -+ tmp2 = M; /*16*/ -+ }else if (freq_KHz > (cali_freq_thres_div2 / 4)) { -+ M = M / 4; -+ MUL = 16; -+ tmp = 5; -+ tmp2 = M + 16; /*48*/ -+ }else if (freq_KHz > (cali_freq_thres_div3r / 4)) { -+ M = M / 3; -+ MUL = 24; -+ tmp = 5; -+ tmp2 = M + 32; /*32*/ -+ }else if (freq_KHz > (cali_freq_thres_div3 / 4)) { -+ M = M / 3; -+ MUL = 24; -+ tmp = 5; -+ tmp2 = M; /*16*/ -+ }else if (freq_KHz > (cali_freq_thres_div2 / 8)) { -+ M = M / 4; -+ MUL = 32; -+ tmp = 6; -+ tmp2 = M + 16; /*48*/ -+ }else if (freq_KHz > (cali_freq_thres_div3r / 8)) { -+ M = M / 3; -+ MUL = 48; -+ tmp = 6; -+ tmp2 = M + 32; /*32*/ -+ }else if (freq_KHz > (cali_freq_thres_div3 / 8)) { -+ M = M / 3; -+ MUL = 48; -+ tmp = 6; -+ tmp2 = M; /*16*/ -+ }else if (freq_KHz > (cali_freq_thres_div2 / 16)) { -+ M = M / 4; -+ MUL = 64; -+ tmp = 7; -+ tmp2 = M + 16; /*48*/ -+ }else if (freq_KHz > (cali_freq_thres_div3r / 16)) { -+ M = M / 3; -+ MUL = 96; -+ tmp = 7; -+ tmp2 = M + 32; /*32*/ -+ }else if (freq_KHz > (cali_freq_thres_div3 / 16)) { -+ M = M / 3; -+ MUL = 96; -+ tmp = 7; -+ tmp2 = M; /*16*/ -+ }else { /* invalid */ -+ M = M / 4; -+ MUL = 0; -+ tmp = 0; -+ tmp2 = 48; -+ return 1; -+ } -+ -+ if (freq_KHz == 291000) { -+ M = state->tuner_crystal / 1000 / 3; -+ MUL = 12; -+ tmp = 4; -+ tmp2 = M + 32; /*32*/ -+ } -+ /* -+ if (freq_KHz == 578000) { -+ M = state->tuner_crystal / 1000 / 4; -+ MUL = 4; -+ tmp = 2; -+ tmp2 = M + 16; //48 -+ } -+ */ -+ if (freq_KHz == 690000) { -+ M = state->tuner_crystal / 1000 / 3; -+ MUL = 4; -+ tmp = 2; -+ tmp2 = M + 16; /*48*/ -+ } -+ _mt_fe_tn_get_reg(state, 0x33, &buf); -+ buf &= 0xc0; -+ buf += tmp2; -+ _mt_fe_tn_set_reg(state, 0x33, buf); -+ }else { -+ return 1; -+ } -+ -+ _mt_fe_tn_get_reg(state, 0x39, &buf); -+ buf &= 0xf8; -+ buf += tmp; -+ _mt_fe_tn_set_reg(state, 0x39, buf); -+ -+ N = (freq_KHz * MUL * M / crystal_KHz) / 2 * 2 - 256; -+ -+ buf = (N >> 8) & 0xcf; -+ if (state->tuner_mtt == 0xE1) { -+ buf |= 0x30; -+ } -+ _mt_fe_tn_set_reg(state, 0x34, buf); -+ -+ buf = N & 0xff; -+ _mt_fe_tn_set_reg(state, 0x35, buf); -+ -+ F = ((freq_KHz * MUL * M / (crystal_KHz / 1000) / 2) - (freq_KHz * MUL * M / crystal_KHz / 2 * 1000)) * 64 / 1000; -+ -+ buf = F & 0xff; -+ _mt_fe_tn_set_reg(state, 0x36, buf); -+ -+ if (F == 0) { -+ if (state->tuner_mtt == 0xD1) { -+ _mt_fe_tn_set_reg(state, 0x3d, 0xca); -+ }else if (state->tuner_mtt == 0xE1) { -+ _mt_fe_tn_set_reg(state, 0x3d, 0xfe); -+ } else { -+ return 1; -+ } -+ _mt_fe_tn_set_reg(state, 0x3e, 0x9c); -+ _mt_fe_tn_set_reg(state, 0x3f, 0x34); -+ } -+ -+ if (F > 0) { -+ if (state->tuner_mtt == 0xD1) { -+ if ((F == 32) || (F == 16) || (F == 48)) { -+ _mt_fe_tn_set_reg(state, 0x3e, 0xa4); -+ _mt_fe_tn_set_reg(state, 0x3d, 0x4a); -+ _mt_fe_tn_set_reg(state, 0x3f, 0x36); -+ }else { -+ _mt_fe_tn_set_reg(state, 0x3e, 0xa4); -+ _mt_fe_tn_set_reg(state, 0x3d, 0x4a); -+ _mt_fe_tn_set_reg(state, 0x3f, 0x36); -+ } -+ }else if (state->tuner_mtt == 0xE1) { -+ _mt_fe_tn_set_reg(state, 0x3e, 0xa4); -+ _mt_fe_tn_set_reg(state, 0x3d, 0x7e); -+ _mt_fe_tn_set_reg(state, 0x3f, 0x36); -+ _mt_fe_tn_set_reg(state, 0x89, 0x84); -+ _mt_fe_tn_get_reg(state, 0x39, &buf); -+ buf = buf & 0x1f; -+ _mt_fe_tn_set_reg(state, 0x39, buf); -+ _mt_fe_tn_get_reg(state, 0x32, &buf); -+ buf = buf | 0x02; -+ _mt_fe_tn_set_reg(state, 0x32, buf); -+ }else { -+ return 1; -+ } -+ } -+ -+ _mt_fe_tn_set_reg(state, 0x41, 0x00); -+ if (state->tuner_mtt == 0xD1) { -+ msleep(5); -+ }else if (state->tuner_mtt == 0xE1) { -+ msleep(2); -+ }else { -+ return 1; -+ } -+ _mt_fe_tn_set_reg(state, 0x41, 0x02); -+ _mt_fe_tn_set_reg(state, 0x30, 0x7f); -+ _mt_fe_tn_set_reg(state, 0x30, 0xff); -+ _mt_fe_tn_set_reg(state, 0x31, 0x80); -+ _mt_fe_tn_set_reg(state, 0x31, 0x00); -+ -+ return 0; -+} -+ -+static int _mt_fe_tn_set_PLL_freq_tc2800(struct m88dc2800_state *state) -+{ -+ u8 buf, buf1; -+ u32 freq_thres_div2_KHz, freq_thres_div3r_KHz, freq_thres_div3_KHz; -+ -+ const u32 freq_KHz = state->tuner_freq; -+ -+ if (state->tuner_mtt == 0xD1) { -+ _mt_fe_tn_set_reg(state, 0x32, 0xe1); -+ _mt_fe_tn_set_reg(state, 0x33, 0xa6); -+ _mt_fe_tn_set_reg(state, 0x37, 0x7f); -+ _mt_fe_tn_set_reg(state, 0x38, 0x20); -+ _mt_fe_tn_set_reg(state, 0x39, 0x18); -+ _mt_fe_tn_set_reg(state, 0x40, 0x40); -+ -+ freq_thres_div2_KHz = 520000; -+ _mt_fe_tn_cali_PLL_tc2800(state, freq_KHz, freq_thres_div2_KHz, 0, 0); -+ -+ msleep(5); -+ _mt_fe_tn_get_reg(state, 0x3a, &buf); -+ buf1 = buf; -+ buf = buf & 0x03; -+ buf1 = buf1 & 0x01; -+ if ((buf1 == 0) || (buf == 3)) { -+ freq_thres_div2_KHz = 420000; -+ _mt_fe_tn_cali_PLL_tc2800(state, freq_KHz, freq_thres_div2_KHz, 0, 0); -+ msleep(5); -+ -+ _mt_fe_tn_get_reg(state, 0x3a, &buf); -+ buf = buf & 0x07; -+ if (buf == 5) { -+ freq_thres_div2_KHz = 520000; -+ _mt_fe_tn_cali_PLL_tc2800(state, freq_KHz, freq_thres_div2_KHz, 0, 0); -+ msleep(5); -+ } -+ } -+ -+ _mt_fe_tn_get_reg(state, 0x38, &buf); -+ _mt_fe_tn_set_reg(state, 0x38, buf); -+ -+ _mt_fe_tn_get_reg(state, 0x32, &buf); -+ buf = buf | 0x10; -+ _mt_fe_tn_set_reg(state, 0x32, buf); -+ -+ _mt_fe_tn_set_reg(state, 0x30, 0x7f); -+ _mt_fe_tn_set_reg(state, 0x30, 0xff); -+ -+ _mt_fe_tn_get_reg(state, 0x32, &buf); -+ buf = buf & 0xdf; -+ _mt_fe_tn_set_reg(state, 0x32, buf); -+ _mt_fe_tn_set_reg(state, 0x40, 0x0); -+ -+ _mt_fe_tn_set_reg(state, 0x30, 0x7f); -+ _mt_fe_tn_set_reg(state, 0x30, 0xff); -+ _mt_fe_tn_set_reg(state, 0x31, 0x80); -+ _mt_fe_tn_set_reg(state, 0x31, 0x00); -+ msleep(5); -+ -+ _mt_fe_tn_get_reg(state, 0x39, &buf); -+ buf = buf >> 5; -+ if (buf < 5) { -+ _mt_fe_tn_get_reg(state, 0x39, &buf); -+ buf = buf | 0xa0; -+ buf = buf & 0xbf; -+ _mt_fe_tn_set_reg(state, 0x39, buf); -+ -+ _mt_fe_tn_get_reg(state, 0x32, &buf); -+ buf = buf | 0x02; -+ _mt_fe_tn_set_reg(state, 0x32, buf); -+ } -+ -+ _mt_fe_tn_get_reg(state, 0x37, &buf); -+ if (buf > 0x70) { -+ buf = 0x7f; -+ _mt_fe_tn_set_reg(state, 0x40, 0x40); -+ } -+ _mt_fe_tn_set_reg(state, 0x37, buf); -+ -+ -+ _mt_fe_tn_get_reg(state, 0x38, &buf); -+ if (buf < 0x0f) { -+ buf = (buf & 0x0f) << 2; -+ buf = buf + 0x0f; -+ _mt_fe_tn_set_reg(state, 0x37, buf); -+ }else if (buf < 0x1f) { -+ buf= buf + 0x0f; -+ _mt_fe_tn_set_reg(state, 0x37, buf); -+ } -+ -+ _mt_fe_tn_get_reg(state, 0x32, &buf); -+ buf = (buf | 0x20) & 0xef; -+ _mt_fe_tn_set_reg(state, 0x32, buf); -+ -+ _mt_fe_tn_set_reg(state, 0x41, 0x00); -+ msleep(5); -+ _mt_fe_tn_set_reg(state, 0x41, 0x02); -+ -+ }else if (state->tuner_mtt == 0xE1){ -+ freq_thres_div2_KHz = 580000; -+ freq_thres_div3r_KHz = 500000; -+ freq_thres_div3_KHz = 440000; -+ _mt_fe_tn_cali_PLL_tc2800(state, freq_KHz, freq_thres_div2_KHz, freq_thres_div3r_KHz, freq_thres_div3_KHz); -+ -+ msleep(3); -+ -+ _mt_fe_tn_get_reg(state, 0x38, &buf); -+ _mt_fe_tn_set_reg(state, 0x38, buf); -+ -+ _mt_fe_tn_set_reg(state, 0x30, 0x7f); -+ _mt_fe_tn_set_reg(state, 0x30, 0xff); -+ _mt_fe_tn_set_reg(state, 0x31, 0x80); -+ _mt_fe_tn_set_reg(state, 0x31, 0x00); -+ msleep(3); -+ _mt_fe_tn_get_reg(state, 0x38, &buf); -+ _mt_fe_tn_set_reg(state, 0x38, buf); -+ -+ _mt_fe_tn_get_reg(state, 0x32, &buf); -+ buf = buf | 0x10; -+ _mt_fe_tn_set_reg(state, 0x32, buf); -+ -+ _mt_fe_tn_set_reg(state, 0x30, 0x7f); -+ _mt_fe_tn_set_reg(state, 0x30, 0xff); -+ _mt_fe_tn_get_reg(state, 0x32, &buf); -+ buf = buf & 0xdf; -+ _mt_fe_tn_set_reg(state, 0x32, buf); -+ _mt_fe_tn_set_reg(state, 0x31, 0x80); -+ _mt_fe_tn_set_reg(state, 0x31, 0x00); -+ msleep(3); -+ -+ _mt_fe_tn_get_reg(state, 0x37, &buf); -+ _mt_fe_tn_set_reg(state, 0x37, buf); -+ /* -+ if ((freq_KHz == 802000) || (freq_KHz == 826000)) { -+ _mt_fe_tn_set_reg(state, 0x37, 0x5e); -+ } -+ */ -+ -+ _mt_fe_tn_get_reg(state, 0x32, &buf); -+ buf = (buf & 0xef) | 0x30; -+ _mt_fe_tn_set_reg(state, 0x32, buf); -+ -+ _mt_fe_tn_set_reg(state, 0x41, 0x00); -+ msleep(2); -+ _mt_fe_tn_set_reg(state, 0x41, 0x02); -+ } else { -+ return 1; -+ } -+ -+ return 0; -+} -+ -+static int _mt_fe_tn_set_BB_tc2800(struct m88dc2800_state *state) ++static int _mt_fe_tn_set_RF_front_tc2800(struct m88dc2800_state *state) +{ -+ return 0; -+} -+ -+static int _mt_fe_tn_set_appendix_tc2800(struct m88dc2800_state *state) -+{ -+ u8 buf; -+ const u32 freq_KHz = state->tuner_freq; -+ -+ if (state->tuner_mtt == 0xD1) { -+ if ((freq_KHz == 123000) || (freq_KHz == 147000) || (freq_KHz == 171000) -+ || (freq_KHz == 195000)) -+ _mt_fe_tn_set_reg(state, 0x20, 0x1b); -+ -+ if ((freq_KHz == 371000) || (freq_KHz == 419000) || (freq_KHz == 610000) -+ || (freq_KHz == 730000) || (freq_KHz == 754000) || (freq_KHz == 826000)) { -+ _mt_fe_tn_get_reg(state, 0x0d, &buf); -+ _mt_fe_tn_set_reg(state, 0x0d, (u8)(buf + 1)); -+ } -+ -+ if ((freq_KHz == 522000) || (freq_KHz == 578000) || (freq_KHz == 634000) -+ || (freq_KHz == 690000) || (freq_KHz == 834000)) { -+ _mt_fe_tn_get_reg(state, 0x0d, &buf); -+ _mt_fe_tn_set_reg(state, 0x0d, (u8)(buf - 1)); -+ } -+ } else if (state->tuner_mtt == 0xE1) { -+ _mt_fe_tn_set_reg(state, 0x20, 0xfc); -+ -+ if ((freq_KHz == 123000) || (freq_KHz == 147000) || (freq_KHz == 171000) -+ || (freq_KHz == 195000) || (freq_KHz == 219000) || (freq_KHz == 267000) -+ || (freq_KHz == 291000) || (freq_KHz == 339000) || (freq_KHz == 387000) -+ || (freq_KHz == 435000) || (freq_KHz == 482000) || (freq_KHz == 530000) -+ || (freq_KHz == 722000) -+ || ((state->tuner_custom_cfg == 1) && (freq_KHz == 315000))) { -+ _mt_fe_tn_set_reg(state, 0x20, 0x5c); -+ } -+ } -+ return 0; -+} -+ -+static int _mt_fe_tn_set_DAC_tc2800(struct m88dc2800_state *state) -+{ -+ u8 buf, tempnumber; -+ s32 N; -+ s32 f1f2number, f1, f2, delta1, Totalnum1; -+ s32 cntT, cntin, NCOI, z0, z1, z2, tmp; -+ u32 fc, fadc, fsd, f2d; -+ u32 FreqTrue108_Hz; -+ -+ s32 M = state->tuner_crystal / 4000; -+ -+/* const u8 bandwidth = state->tuner_bandwidth; */ -+ const u16 DAC_fre = 108; -+ const u32 crystal_KHz = state->tuner_crystal; -+ const u32 DACFreq_KHz = state->tuner_dac; -+ -+ const u32 freq_KHz = state->tuner_freq; -+ -+ if (state->tuner_mtt == 0xE1) { -+ _mt_fe_tn_get_reg(state, 0x33, &buf); -+ M = buf & 0x0f; -+ if (M == 0) -+ M = 6; -+ } -+ -+ _mt_fe_tn_get_reg(state, 0x34, &buf); -+ N = buf & 0x07; -+ -+ _mt_fe_tn_get_reg(state, 0x35, &buf); -+ N = (N << 8) + buf; -+ -+ -+ buf = ((N + 256) * crystal_KHz / M / DAC_fre + 500) / 1000; -+ -+ if (state->tuner_mtt == 0xE1) { -+ _mt_fe_tn_set_appendix_tc2800(state); -+ -+ if ((freq_KHz == 187000) || (freq_KHz == 195000) || (freq_KHz == 131000) -+ || (freq_KHz == 211000) || (freq_KHz == 219000) || (freq_KHz == 227000) -+ || (freq_KHz == 267000) || (freq_KHz == 299000) || (freq_KHz == 347000) -+ || (freq_KHz == 363000) || (freq_KHz == 395000) || (freq_KHz == 403000) -+ || (freq_KHz == 435000) || (freq_KHz == 482000) || (freq_KHz == 474000) -+ || (freq_KHz == 490000) || (freq_KHz == 610000) || (freq_KHz == 642000) -+ || (freq_KHz == 666000) || (freq_KHz == 722000) || (freq_KHz == 754000) -+ || (((freq_KHz == 379000) || (freq_KHz == 467000) || (freq_KHz == 762000)) -+ && (state->tuner_custom_cfg != 1))) { -+ buf = buf + 1; -+ } -+ -+ if ((freq_KHz == 123000) || (freq_KHz == 139000) || (freq_KHz == 147000) -+ || (freq_KHz == 171000) || (freq_KHz == 179000) || (freq_KHz == 203000) -+ || (freq_KHz == 235000) || (freq_KHz == 251000) || (freq_KHz == 259000) -+ || (freq_KHz == 283000) || (freq_KHz == 331000) || (freq_KHz == 363000) -+ || (freq_KHz == 371000) || (freq_KHz == 387000) || (freq_KHz == 411000) -+ || (freq_KHz == 427000) || (freq_KHz == 443000) || (freq_KHz == 451000) -+ || (freq_KHz == 459000) || (freq_KHz == 506000) || (freq_KHz == 514000) -+ || (freq_KHz == 538000) || (freq_KHz == 546000) || (freq_KHz == 554000) -+ || (freq_KHz == 562000) || (freq_KHz == 570000) || (freq_KHz == 578000) -+ || (freq_KHz == 602000) || (freq_KHz == 626000) || (freq_KHz == 658000) -+ || (freq_KHz == 690000) || (freq_KHz == 714000) || (freq_KHz == 746000) -+ || (freq_KHz == 522000) || (freq_KHz == 826000) || (freq_KHz == 155000) -+ || (freq_KHz == 530000) -+ || (((freq_KHz == 275000) || (freq_KHz == 355000)) && (state->tuner_custom_cfg != 1)) -+ || (((freq_KHz == 467000) || (freq_KHz == 762000) || (freq_KHz == 778000) -+ || (freq_KHz == 818000)) && (state->tuner_custom_cfg == 1))) { -+ buf = buf - 1; -+ } -+ } -+ -+ _mt_fe_tn_set_reg(state, 0x0e, buf); -+ _mt_fe_tn_set_reg(state, 0x0d, buf); -+ -+ f1f2number = (((DACFreq_KHz * M * buf) / crystal_KHz) << 16) / (N + 256) -+ + (((DACFreq_KHz * M * buf) % crystal_KHz) << 16) / ((N + 256) * crystal_KHz); -+ -+ -+ _mt_fe_tn_set_reg(state, 0xf1, (u8)((f1f2number & 0xff00) >> 8)); -+ _mt_fe_tn_set_reg(state, 0xf2, (u8)(f1f2number & 0x00ff)); -+ -+ FreqTrue108_Hz = (N + 256) * crystal_KHz / (M * buf) * 1000 + (((N + 256) * crystal_KHz) % (M * buf)) * 1000 / (M * buf); -+ -+ f1 = 4096; -+ fc = FreqTrue108_Hz; -+ fadc = fc / 4; -+ fsd = 27000000; -+ f2d = state->tuner_bandwidth * 1000 / 2 -150; -+ f2 = (fsd / 250) * f2d / ((fc + 500) / 1000); -+ delta1 = ((f1 - f2) << 15) / f2; -+ -+ Totalnum1 = ((f1 - f2) << 15) - delta1 * f2; -+ -+ cntT = f2; -+ cntin = Totalnum1; -+ NCOI = delta1; -+ -+ z0 = cntin; -+ z1 = cntT; -+ z2 = NCOI; -+ -+ tempnumber = (z0 & 0xff00) >> 8; -+ _mt_fe_tn_set_reg(state, 0xc9, (u8)(tempnumber & 0x0f)); -+ tempnumber = (z0 & 0xff); -+ _mt_fe_tn_set_reg(state, 0xca, tempnumber); -+ -+ tempnumber = (z1 & 0xff00) >> 8; -+ _mt_fe_tn_set_reg(state, 0xcb, tempnumber); -+ tempnumber = (z1 & 0xff); -+ _mt_fe_tn_set_reg(state, 0xcc, tempnumber); -+ -+ tempnumber = (z2 & 0xff00) >> 8; -+ _mt_fe_tn_set_reg(state, 0xcd, tempnumber); -+ tempnumber = (z2 & 0xff); -+ _mt_fe_tn_set_reg(state, 0xce, tempnumber); -+ -+ tmp = f1; -+ f1 = f2; -+ f2 = tmp / 2; -+ delta1 = ((f1 - f2) << 15) / f2; -+ Totalnum1 = ((f1 - f2) << 15) - delta1 * f2; -+ NCOI = (f1 << 15) / f2 - (1 << 15); -+ cntT = f2; -+ cntin = Totalnum1; -+ z0 = cntin; -+ z1 = cntT; -+ z2 = NCOI; -+ -+ tempnumber = (z0 & 0xff00) >> 8; -+ _mt_fe_tn_set_reg(state, 0xd9, (u8)(tempnumber & 0x0f)); -+ tempnumber = (z0 & 0xff); -+ _mt_fe_tn_set_reg(state, 0xda, tempnumber); -+ -+ tempnumber = (z1 & 0xff00) >> 8; -+ _mt_fe_tn_set_reg(state, 0xdb, tempnumber); -+ tempnumber = (z1 & 0xff); -+ _mt_fe_tn_set_reg(state, 0xdc, tempnumber); -+ -+ tempnumber = (z2 & 0xff00) >> 8; -+ _mt_fe_tn_set_reg(state, 0xdd, tempnumber); -+ tempnumber = (z2 & 0xff); -+ _mt_fe_tn_set_reg(state, 0xde, tempnumber); -+ -+ return 0; ++ u32 freq_KHz = state->tuner_freq; ++ u8 a, b, c; ++ if (state->tuner_mtt == 0xD1) { /* D1 */ ++ if (freq_KHz <= 123000) { ++ if (freq_KHz <= 56000) { ++ a = 0x00; b = 0x00; c = 0x00; ++ } else if (freq_KHz <= 64000) { ++ a = 0x10; b = 0x01; c = 0x08; ++ } else if (freq_KHz <= 72000) { ++ a = 0x20; b = 0x02; c = 0x10; ++ } else if (freq_KHz <= 80000) { ++ a = 0x30; b = 0x03; c = 0x18; ++ } else if (freq_KHz <= 88000) { ++ a = 0x40; b = 0x04; c = 0x20; ++ } else if (freq_KHz <= 96000) { ++ a = 0x50; b = 0x05; c = 0x28; ++ } else if (freq_KHz <= 104000) { ++ a = 0x60; b = 0x06; c = 0x30; ++ } else { ++ a = 0x70; b = 0x07; c = 0x38; ++ } ++ _mt_fe_tn_set_reg(state, 0x58, 0x9b); ++ _mt_fe_tn_set_reg(state, 0x59, a); ++ _mt_fe_tn_set_reg(state, 0x5d, b); ++ _mt_fe_tn_set_reg(state, 0x5e, c); ++ _mt_fe_tn_set_reg(state, 0x5a, 0x75); ++ _mt_fe_tn_set_reg(state, 0x73, 0x0c); ++ } else { /* if (freq_KHz > 112000) */ ++ _mt_fe_tn_set_reg(state, 0x58, 0x7b); ++ if (freq_KHz <= 304000) { ++ if (freq_KHz <= 136000) { ++ _mt_fe_tn_set_reg(state, 0x5e, 0x40); ++ } else if (freq_KHz <= 160000) { ++ _mt_fe_tn_set_reg(state, 0x5e, 0x48); ++ } else if (freq_KHz <= 184000) { ++ _mt_fe_tn_set_reg(state, 0x5e, 0x50); ++ } else if (freq_KHz <= 208000) { ++ _mt_fe_tn_set_reg(state, 0x5e, 0x58); ++ } else if (freq_KHz <= 232000) { ++ _mt_fe_tn_set_reg(state, 0x5e, 0x60); ++ } else if (freq_KHz <= 256000) { ++ _mt_fe_tn_set_reg(state, 0x5e, 0x68); ++ } else if (freq_KHz <= 280000) { ++ _mt_fe_tn_set_reg(state, 0x5e, 0x70); ++ } else { /* if (freq_KHz <= 304000) */ ++ _mt_fe_tn_set_reg(state, 0x5e, 0x78); ++ } ++ if (freq_KHz <= 171000) { ++ _mt_fe_tn_set_reg(state, 0x73, 0x08); ++ } else if (freq_KHz <= 211000) { ++ _mt_fe_tn_set_reg(state, 0x73, 0x0a); ++ } else { ++ _mt_fe_tn_set_reg(state, 0x73, 0x0e); ++ } ++ } else { /* if (freq_KHz > 304000) */ ++ _mt_fe_tn_set_reg(state, 0x5e, 0x88); ++ if (freq_KHz <= 400000) { ++ _mt_fe_tn_set_reg(state, 0x73, 0x0c); ++ } else if (freq_KHz <= 450000) { ++ _mt_fe_tn_set_reg(state, 0x73, 0x09); ++ } else if (freq_KHz <= 550000) { ++ _mt_fe_tn_set_reg(state, 0x73, 0x0e); ++ } else if (freq_KHz <= 650000) { ++ _mt_fe_tn_set_reg(state, 0x73, 0x0d); ++ } else { /*if (freq_KHz > 650000) */ ++ _mt_fe_tn_set_reg(state, 0x73, 0x0e); ++ } ++ } ++ } ++ if (freq_KHz > 800000) ++ _mt_fe_tn_set_reg(state, 0x87, 0x24); ++ else if (freq_KHz > 700000) ++ _mt_fe_tn_set_reg(state, 0x87, 0x34); ++ else if (freq_KHz > 500000) ++ _mt_fe_tn_set_reg(state, 0x87, 0x44); ++ else if (freq_KHz > 300000) ++ _mt_fe_tn_set_reg(state, 0x87, 0x43); ++ else if (freq_KHz > 220000) ++ _mt_fe_tn_set_reg(state, 0x87, 0x54); ++ else if (freq_KHz > 110000) ++ _mt_fe_tn_set_reg(state, 0x87, 0x14); ++ else ++ _mt_fe_tn_set_reg(state, 0x87, 0x54); ++ if (freq_KHz > 600000) ++ _mt_fe_tn_set_reg(state, 0x6a, 0x53); ++ else if (freq_KHz > 500000) ++ _mt_fe_tn_set_reg(state, 0x6a, 0x57); ++ else ++ _mt_fe_tn_set_reg(state, 0x6a, 0x59); ++ if (freq_KHz < 200000) { ++ _mt_fe_tn_set_reg(state, 0x20, 0x5d); ++ } else if (freq_KHz < 500000) { ++ _mt_fe_tn_set_reg(state, 0x20, 0x7d); ++ } else { ++ _mt_fe_tn_set_reg(state, 0x20, 0xfd); ++ } /* end of 0xD1 */ ++ } else if (state->tuner_mtt == 0xE1) { /* E1 */ ++ if (freq_KHz <= 112000) { /* 123MHz */ ++ if (freq_KHz <= 56000) { ++ _mt_fe_tn_set_reg(state, 0x5c, 0x01); ++ } else if (freq_KHz <= 64000) { ++ _mt_fe_tn_set_reg(state, 0x5c, 0x09); ++ } else if (freq_KHz <= 72000) { ++ _mt_fe_tn_set_reg(state, 0x5c, 0x11); ++ } else if (freq_KHz <= 80000) { ++ _mt_fe_tn_set_reg(state, 0x5c, 0x19); ++ } else if (freq_KHz <= 88000) { ++ _mt_fe_tn_set_reg(state, 0x5c, 0x21); ++ } else if (freq_KHz <= 96000) { ++ _mt_fe_tn_set_reg(state, 0x5c, 0x29); ++ } else if (freq_KHz <= 104000) { ++ _mt_fe_tn_set_reg(state, 0x5c, 0x31); ++ } else { /* if (freq_KHz <= 112000) */ ++ _mt_fe_tn_set_reg(state, 0x5c, 0x39); ++ } ++ _mt_fe_tn_set_reg(state, 0x5b, 0x30); ++ } else { /* if (freq_KHz > 112000) */ ++ if (freq_KHz <= 304000) { ++ if (freq_KHz <= 136000) { ++ _mt_fe_tn_set_reg(state, 0x5c, 0x41); ++ } else if (freq_KHz <= 160000) { ++ _mt_fe_tn_set_reg(state, 0x5c, 0x49); ++ } else if (freq_KHz <= 184000) { ++ _mt_fe_tn_set_reg(state, 0x5c, 0x51); ++ } else if (freq_KHz <= 208000) { ++ _mt_fe_tn_set_reg(state, 0x5c, 0x59); ++ } else if (freq_KHz <= 232000) { ++ _mt_fe_tn_set_reg(state, 0x5c, 0x61); ++ } else if (freq_KHz <= 256000) { ++ _mt_fe_tn_set_reg(state, 0x5c, 0x69); ++ } else if (freq_KHz <= 280000) { ++ _mt_fe_tn_set_reg(state, 0x5c, 0x71); ++ } else { /* if (freq_KHz <= 304000) */ ++ _mt_fe_tn_set_reg(state, 0x5c, 0x79); ++ } ++ if (freq_KHz <= 150000) { ++ _mt_fe_tn_set_reg(state, 0x5b, 0x28); ++ } else if (freq_KHz <= 256000) { ++ _mt_fe_tn_set_reg(state, 0x5b, 0x29); ++ } else { ++ _mt_fe_tn_set_reg(state, 0x5b, 0x2a); ++ } ++ } else { /* if (freq_KHz > 304000) */ ++ if (freq_KHz <= 400000) { ++ _mt_fe_tn_set_reg(state, 0x5c, 0x89); ++ } else if (freq_KHz <= 450000) { ++ _mt_fe_tn_set_reg(state, 0x5c, 0x91); ++ } else if (freq_KHz <= 650000) { ++ _mt_fe_tn_set_reg(state, 0x5c, 0x98); ++ } else if (freq_KHz <= 850000) { ++ _mt_fe_tn_set_reg(state, 0x5c, 0xa0); ++ } else { ++ _mt_fe_tn_set_reg(state, 0x5c, 0xa8); ++ } ++ _mt_fe_tn_set_reg(state, 0x5b, 0x08); ++ } ++ } ++ } /* end of 0xE1 */ ++ return 0; +} + -+static int _mt_fe_tn_preset_tc2800(struct m88dc2800_state *state) -+{ -+ if (state->tuner_mtt == 0xD1) { -+ _mt_fe_tn_set_reg(state, 0x19, 0x4a); -+ _mt_fe_tn_set_reg(state, 0x1b, 0x4b); -+ -+ _mt_fe_tn_set_reg(state, 0x04, 0x04); -+ _mt_fe_tn_set_reg(state, 0x17, 0x0d); -+ _mt_fe_tn_set_reg(state, 0x62, 0x6c); -+ _mt_fe_tn_set_reg(state, 0x63, 0xf4); -+ _mt_fe_tn_set_reg(state, 0x1f, 0x0e); -+ _mt_fe_tn_set_reg(state, 0x6b, 0xf4); -+ _mt_fe_tn_set_reg(state, 0x14, 0x01); -+ _mt_fe_tn_set_reg(state, 0x5a, 0x75); -+ _mt_fe_tn_set_reg(state, 0x66, 0x74); -+ _mt_fe_tn_set_reg(state, 0x72, 0xe0); -+ _mt_fe_tn_set_reg(state, 0x70, 0x07); -+ _mt_fe_tn_set_reg(state, 0x15, 0x7b); -+ _mt_fe_tn_set_reg(state, 0x55, 0x71); -+ -+ _mt_fe_tn_set_reg(state, 0x75, 0x55); -+ _mt_fe_tn_set_reg(state, 0x76, 0xac); -+ _mt_fe_tn_set_reg(state, 0x77, 0x6c); -+ _mt_fe_tn_set_reg(state, 0x78, 0x8b); -+ _mt_fe_tn_set_reg(state, 0x79, 0x42); -+ _mt_fe_tn_set_reg(state, 0x7a, 0xd2); -+ -+ _mt_fe_tn_set_reg(state, 0x81, 0x01); -+ _mt_fe_tn_set_reg(state, 0x82, 0x00); -+ _mt_fe_tn_set_reg(state, 0x82, 0x02); -+ _mt_fe_tn_set_reg(state, 0x82, 0x04); -+ _mt_fe_tn_set_reg(state, 0x82, 0x06); -+ _mt_fe_tn_set_reg(state, 0x82, 0x08); -+ _mt_fe_tn_set_reg(state, 0x82, 0x09); -+ _mt_fe_tn_set_reg(state, 0x82, 0x29); -+ _mt_fe_tn_set_reg(state, 0x82, 0x49); -+ _mt_fe_tn_set_reg(state, 0x82, 0x58); -+ _mt_fe_tn_set_reg(state, 0x82, 0x59); -+ _mt_fe_tn_set_reg(state, 0x82, 0x98); -+ _mt_fe_tn_set_reg(state, 0x82, 0x99); -+ -+ -+ _mt_fe_tn_set_reg(state, 0x10, 0x05); -+ _mt_fe_tn_set_reg(state, 0x10, 0x0d); -+ _mt_fe_tn_set_reg(state, 0x11, 0x95); -+ _mt_fe_tn_set_reg(state, 0x11, 0x9d); -+ -+ -+ if (state->tuner_loopthrough != 0) { -+ _mt_fe_tn_set_reg(state, 0x67, 0x25); -+ } else { -+ _mt_fe_tn_set_reg(state, 0x67, 0x05); -+ } -+ } else if (state->tuner_mtt == 0xE1) { -+ _mt_fe_tn_set_reg(state, 0x1b, 0x47); -+ if(state->tuner_mode == 0) // DVB-C -+ { -+ _mt_fe_tn_set_reg(state, 0x66, 0x74); -+ _mt_fe_tn_set_reg(state, 0x62, 0x2c); -+ _mt_fe_tn_set_reg(state, 0x63, 0x54); -+ _mt_fe_tn_set_reg(state, 0x68, 0x0b); -+ _mt_fe_tn_set_reg(state, 0x14, 0x00); -+ } -+ else // CTTB -+ { -+ _mt_fe_tn_set_reg(state, 0x66, 0x74); -+ _mt_fe_tn_set_reg(state, 0x62, 0x0c); -+ _mt_fe_tn_set_reg(state, 0x63, 0x54); -+ _mt_fe_tn_set_reg(state, 0x68, 0x0b); -+ _mt_fe_tn_set_reg(state, 0x14, 0x05); -+ } -+ _mt_fe_tn_set_reg(state, 0x6f, 0x00); -+ _mt_fe_tn_set_reg(state, 0x84, 0x04); -+ _mt_fe_tn_set_reg(state, 0x5e, 0xbe); -+ _mt_fe_tn_set_reg(state, 0x87, 0x07); -+ _mt_fe_tn_set_reg(state, 0x8a, 0x1f); -+ _mt_fe_tn_set_reg(state, 0x8b, 0x1f); -+ _mt_fe_tn_set_reg(state, 0x88, 0x30); -+ _mt_fe_tn_set_reg(state, 0x58, 0x34); -+ _mt_fe_tn_set_reg(state, 0x61, 0x8c); -+ _mt_fe_tn_set_reg(state, 0x6a, 0x42); -+ } -+ return 0; ++static int _mt_fe_tn_cali_PLL_tc2800(struct m88dc2800_state *state, ++ u32 freq_KHz, ++ u32 cali_freq_thres_div2, ++ u32 cali_freq_thres_div3r, ++ u32 cali_freq_thres_div3) ++{ ++ s32 N, F, MUL; ++ u8 buf, tmp, tmp2; ++ s32 M; ++ const s32 crystal_KHz = state->tuner_crystal; ++ if (state->tuner_mtt == 0xD1) { ++ M = state->tuner_crystal / 4000; ++ if (freq_KHz > cali_freq_thres_div2) { ++ MUL = 4; ++ tmp = 2; ++ } else if (freq_KHz > 300000) { ++ MUL = 8; ++ tmp = 3; ++ } else if (freq_KHz > (cali_freq_thres_div2 / 2)) { ++ MUL = 8; ++ tmp = 4; ++ } else if (freq_KHz > (cali_freq_thres_div2 / 4)) { ++ MUL = 16; ++ tmp = 5; ++ } else if (freq_KHz > (cali_freq_thres_div2 / 8)) { ++ MUL = 32; ++ tmp = 6; ++ } else if (freq_KHz > (cali_freq_thres_div2 / 16)) { ++ MUL = 64; ++ tmp = 7; ++ } else { /* invalid */ ++ MUL = 0; ++ tmp = 0; ++ return 1; ++ } ++ } else if (state->tuner_mtt == 0xE1) { ++ M = state->tuner_crystal / 1000; ++ _mt_fe_tn_set_reg(state, 0x30, 0xff); ++ _mt_fe_tn_set_reg(state, 0x32, 0xe0); ++ _mt_fe_tn_set_reg(state, 0x33, 0x86); ++ _mt_fe_tn_set_reg(state, 0x37, 0x70); ++ _mt_fe_tn_set_reg(state, 0x38, 0x20); ++ _mt_fe_tn_set_reg(state, 0x39, 0x18); ++ _mt_fe_tn_set_reg(state, 0x89, 0x83); ++ if (freq_KHz > cali_freq_thres_div2) { ++ M = M / 4; ++ MUL = 4; ++ tmp = 2; ++ tmp2 = M + 16; /* 48 */ ++ } else if (freq_KHz > cali_freq_thres_div3r) { ++ M = M / 3; ++ MUL = 6; ++ tmp = 2; ++ tmp2 = M + 32; /* 32 */ ++ } else if (freq_KHz > cali_freq_thres_div3) { ++ M = M / 3; ++ MUL = 6; ++ tmp = 2; ++ tmp2 = M; /* 16 */ ++ } else if (freq_KHz > 304000) { ++ M = M / 4; ++ MUL = 8; ++ tmp = 3; ++ tmp2 = M + 16; /* 48 */ ++ } else if (freq_KHz > (cali_freq_thres_div2 / 2)) { ++ M = M / 4; ++ MUL = 8; ++ tmp = 4; ++ tmp2 = M + 16; /* 48 */ ++ } else if (freq_KHz > (cali_freq_thres_div3r / 2)) { ++ M = M / 3; ++ MUL = 12; ++ tmp = 4; ++ tmp2 = M + 32; /* 32 */ ++ } else if (freq_KHz > (cali_freq_thres_div3 / 2)) { ++ M = M / 3; ++ MUL = 12; ++ tmp = 4; ++ tmp2 = M; /* 16 */ ++ } else if (freq_KHz > (cali_freq_thres_div2 / 4)) { ++ M = M / 4; ++ MUL = 16; ++ tmp = 5; ++ tmp2 = M + 16; /* 48 */ ++ } else if (freq_KHz > (cali_freq_thres_div3r / 4)) { ++ M = M / 3; ++ MUL = 24; ++ tmp = 5; ++ tmp2 = M + 32; /* 32 */ ++ } else if (freq_KHz > (cali_freq_thres_div3 / 4)) { ++ M = M / 3; ++ MUL = 24; ++ tmp = 5; ++ tmp2 = M; /* 16 */ ++ } else if (freq_KHz > (cali_freq_thres_div2 / 8)) { ++ M = M / 4; ++ MUL = 32; ++ tmp = 6; ++ tmp2 = M + 16; /* 48 */ ++ } else if (freq_KHz > (cali_freq_thres_div3r / 8)) { ++ M = M / 3; ++ MUL = 48; ++ tmp = 6; ++ tmp2 = M + 32; /* 32 */ ++ } else if (freq_KHz > (cali_freq_thres_div3 / 8)) { ++ M = M / 3; ++ MUL = 48; ++ tmp = 6; ++ tmp2 = M; /* 16 */ ++ } else if (freq_KHz > (cali_freq_thres_div2 / 16)) { ++ M = M / 4; ++ MUL = 64; ++ tmp = 7; ++ tmp2 = M + 16; /* 48 */ ++ } else if (freq_KHz > (cali_freq_thres_div3r / 16)) { ++ M = M / 3; ++ MUL = 96; ++ tmp = 7; ++ tmp2 = M + 32; /* 32 */ ++ } else if (freq_KHz > (cali_freq_thres_div3 / 16)) { ++ M = M / 3; ++ MUL = 96; ++ tmp = 7; ++ tmp2 = M; /* 16 */ ++ } else { /* invalid */ ++ M = M / 4; ++ MUL = 0; ++ tmp = 0; ++ tmp2 = 48; ++ return 1; ++ } ++ if (freq_KHz == 291000) { ++ M = state->tuner_crystal / 1000 / 3; ++ MUL = 12; ++ tmp = 4; ++ tmp2 = M + 32; /* 32 */ ++ } ++ /* ++ if (freq_KHz == 578000) { ++ M = state->tuner_crystal / 1000 / 4; ++ MUL = 4; ++ tmp = 2; ++ tmp2 = M + 16; // 48 ++ } ++ */ ++ if (freq_KHz == 690000) { ++ M = state->tuner_crystal / 1000 / 3; ++ MUL = 4; ++ tmp = 2; ++ tmp2 = M + 16; /* 48 */ ++ } ++ _mt_fe_tn_get_reg(state, 0x33, &buf); ++ buf &= 0xc0; ++ buf += tmp2; ++ _mt_fe_tn_set_reg(state, 0x33, buf); ++ } else { ++ return 1; ++ } ++ _mt_fe_tn_get_reg(state, 0x39, &buf); ++ buf &= 0xf8; ++ buf += tmp; ++ _mt_fe_tn_set_reg(state, 0x39, buf); ++ N = (freq_KHz * MUL * M / crystal_KHz) / 2 * 2 - 256; ++ buf = (N >> 8) & 0xcf; ++ if (state->tuner_mtt == 0xE1) { ++ buf |= 0x30; ++ } ++ _mt_fe_tn_set_reg(state, 0x34, buf); ++ buf = N & 0xff; ++ _mt_fe_tn_set_reg(state, 0x35, buf); ++ F = ((freq_KHz * MUL * M / (crystal_KHz / 1000) / 2) - ++ (freq_KHz * MUL * M / crystal_KHz / 2 * 1000)) * 64 / 1000; ++ buf = F & 0xff; ++ _mt_fe_tn_set_reg(state, 0x36, buf); ++ if (F == 0) { ++ if (state->tuner_mtt == 0xD1) { ++ _mt_fe_tn_set_reg(state, 0x3d, 0xca); ++ } else if (state->tuner_mtt == 0xE1) { ++ _mt_fe_tn_set_reg(state, 0x3d, 0xfe); ++ } else { ++ return 1; ++ } ++ _mt_fe_tn_set_reg(state, 0x3e, 0x9c); ++ _mt_fe_tn_set_reg(state, 0x3f, 0x34); ++ } ++ if (F > 0) { ++ if (state->tuner_mtt == 0xD1) { ++ if ((F == 32) || (F == 16) || (F == 48)) { ++ _mt_fe_tn_set_reg(state, 0x3e, 0xa4); ++ _mt_fe_tn_set_reg(state, 0x3d, 0x4a); ++ _mt_fe_tn_set_reg(state, 0x3f, 0x36); ++ } else { ++ _mt_fe_tn_set_reg(state, 0x3e, 0xa4); ++ _mt_fe_tn_set_reg(state, 0x3d, 0x4a); ++ _mt_fe_tn_set_reg(state, 0x3f, 0x36); ++ } ++ } else if (state->tuner_mtt == 0xE1) { ++ _mt_fe_tn_set_reg(state, 0x3e, 0xa4); ++ _mt_fe_tn_set_reg(state, 0x3d, 0x7e); ++ _mt_fe_tn_set_reg(state, 0x3f, 0x36); ++ _mt_fe_tn_set_reg(state, 0x89, 0x84); ++ _mt_fe_tn_get_reg(state, 0x39, &buf); ++ buf = buf & 0x1f; ++ _mt_fe_tn_set_reg(state, 0x39, buf); ++ _mt_fe_tn_get_reg(state, 0x32, &buf); ++ buf = buf | 0x02; ++ _mt_fe_tn_set_reg(state, 0x32, buf); ++ } else { ++ return 1; ++ } ++ } ++ _mt_fe_tn_set_reg(state, 0x41, 0x00); ++ if (state->tuner_mtt == 0xD1) { ++ msleep(5); ++ } else if (state->tuner_mtt == 0xE1) { ++ msleep(2); ++ } else { ++ return 1; ++ } ++ _mt_fe_tn_set_reg(state, 0x41, 0x02); ++ _mt_fe_tn_set_reg(state, 0x30, 0x7f); ++ _mt_fe_tn_set_reg(state, 0x30, 0xff); ++ _mt_fe_tn_set_reg(state, 0x31, 0x80); ++ _mt_fe_tn_set_reg(state, 0x31, 0x00); ++ ++ return 0; +} + -+static int mt_fe_tn_wakeup_tc2800(struct m88dc2800_state *state) -+{ -+ _mt_fe_tn_set_reg(state, 0x16, 0xb1); -+ _mt_fe_tn_set_reg(state, 0x09, 0x7d); -+ return 0; -+} -+ -+ -+static int mt_fe_tn_sleep_tc2800(struct m88dc2800_state *state) -+{ -+ _mt_fe_tn_set_reg(state, 0x16, 0xb0); -+ _mt_fe_tn_set_reg(state, 0x09, 0x6d); -+ return 0; -+} -+ -+static int mt_fe_tn_init_tc2800(struct m88dc2800_state *state) -+{ -+ if (state->tuner_init_OK != 1) { -+ state->tuner_dev_addr = 0x61; /* TUNER_I2C_ADDR_TC2800 */ -+ state->tuner_freq = 650000; -+ state->tuner_qam = 0; -+ state->tuner_mode = 0; // 0: DVB-C, 1: CTTB -+ -+ state->tuner_bandwidth = 8; -+ state->tuner_loopthrough = 0; -+ state->tuner_crystal = 24000; -+ state->tuner_dac = 7200; -+ state->tuner_mtt = 0x00; -+ state->tuner_custom_cfg = 0; -+ state->tuner_version = 30022; /* Driver version number */ -+ state->tuner_time = 12092611; -+ state->tuner_init_OK = 1; -+ } ++static int _mt_fe_tn_set_PLL_freq_tc2800(struct m88dc2800_state *state) ++{ ++ u8 buf, buf1; ++ u32 freq_thres_div2_KHz, freq_thres_div3r_KHz, ++ freq_thres_div3_KHz; ++ const u32 freq_KHz = state->tuner_freq; ++ if (state->tuner_mtt == 0xD1) { ++ _mt_fe_tn_set_reg(state, 0x32, 0xe1); ++ _mt_fe_tn_set_reg(state, 0x33, 0xa6); ++ _mt_fe_tn_set_reg(state, 0x37, 0x7f); ++ _mt_fe_tn_set_reg(state, 0x38, 0x20); ++ _mt_fe_tn_set_reg(state, 0x39, 0x18); ++ _mt_fe_tn_set_reg(state, 0x40, 0x40); ++ freq_thres_div2_KHz = 520000; ++ _mt_fe_tn_cali_PLL_tc2800(state, freq_KHz, ++ freq_thres_div2_KHz, 0, 0); ++ msleep(5); ++ _mt_fe_tn_get_reg(state, 0x3a, &buf); ++ buf1 = buf; ++ buf = buf & 0x03; ++ buf1 = buf1 & 0x01; ++ if ((buf1 == 0) || (buf == 3)) { ++ freq_thres_div2_KHz = 420000; ++ _mt_fe_tn_cali_PLL_tc2800(state, freq_KHz, ++ freq_thres_div2_KHz, 0, ++ 0); ++ msleep(5); ++ _mt_fe_tn_get_reg(state, 0x3a, &buf); ++ buf = buf & 0x07; ++ if (buf == 5) { ++ freq_thres_div2_KHz = 520000; ++ _mt_fe_tn_cali_PLL_tc2800(state, freq_KHz, ++ freq_thres_div2_KHz, ++ 0, 0); ++ msleep(5); ++ } ++ } ++ _mt_fe_tn_get_reg(state, 0x38, &buf); ++ _mt_fe_tn_set_reg(state, 0x38, buf); ++ _mt_fe_tn_get_reg(state, 0x32, &buf); ++ buf = buf | 0x10; ++ _mt_fe_tn_set_reg(state, 0x32, buf); ++ _mt_fe_tn_set_reg(state, 0x30, 0x7f); ++ _mt_fe_tn_set_reg(state, 0x30, 0xff); ++ _mt_fe_tn_get_reg(state, 0x32, &buf); ++ buf = buf & 0xdf; ++ _mt_fe_tn_set_reg(state, 0x32, buf); ++ _mt_fe_tn_set_reg(state, 0x40, 0x0); ++ _mt_fe_tn_set_reg(state, 0x30, 0x7f); ++ _mt_fe_tn_set_reg(state, 0x30, 0xff); ++ _mt_fe_tn_set_reg(state, 0x31, 0x80); ++ _mt_fe_tn_set_reg(state, 0x31, 0x00); ++ msleep(5); ++ _mt_fe_tn_get_reg(state, 0x39, &buf); ++ buf = buf >> 5; ++ if (buf < 5) { ++ _mt_fe_tn_get_reg(state, 0x39, &buf); ++ buf = buf | 0xa0; ++ buf = buf & 0xbf; ++ _mt_fe_tn_set_reg(state, 0x39, buf); ++ _mt_fe_tn_get_reg(state, 0x32, &buf); ++ buf = buf | 0x02; ++ _mt_fe_tn_set_reg(state, 0x32, buf); ++ } ++ _mt_fe_tn_get_reg(state, 0x37, &buf); ++ if (buf > 0x70) { ++ buf = 0x7f; ++ _mt_fe_tn_set_reg(state, 0x40, 0x40); ++ } ++ _mt_fe_tn_set_reg(state, 0x37, buf); ++ _mt_fe_tn_get_reg(state, 0x38, &buf); ++ if (buf < 0x0f) { ++ buf = (buf & 0x0f) << 2; ++ buf = buf + 0x0f; ++ _mt_fe_tn_set_reg(state, 0x37, buf); ++ } else if (buf < 0x1f) { ++ buf = buf + 0x0f; ++ _mt_fe_tn_set_reg(state, 0x37, buf); ++ } ++ _mt_fe_tn_get_reg(state, 0x32, &buf); ++ buf = (buf | 0x20) & 0xef; ++ _mt_fe_tn_set_reg(state, 0x32, buf); ++ _mt_fe_tn_set_reg(state, 0x41, 0x00); ++ msleep(5); ++ _mt_fe_tn_set_reg(state, 0x41, 0x02); ++ } else if (state->tuner_mtt == 0xE1) { ++ freq_thres_div2_KHz = 580000; ++ freq_thres_div3r_KHz = 500000; ++ freq_thres_div3_KHz = 440000; ++ _mt_fe_tn_cali_PLL_tc2800(state, freq_KHz, ++ freq_thres_div2_KHz, ++ freq_thres_div3r_KHz, ++ freq_thres_div3_KHz); ++ msleep(3); ++ _mt_fe_tn_get_reg(state, 0x38, &buf); ++ _mt_fe_tn_set_reg(state, 0x38, buf); ++ _mt_fe_tn_set_reg(state, 0x30, 0x7f); ++ _mt_fe_tn_set_reg(state, 0x30, 0xff); ++ _mt_fe_tn_set_reg(state, 0x31, 0x80); ++ _mt_fe_tn_set_reg(state, 0x31, 0x00); ++ msleep(3); ++ _mt_fe_tn_get_reg(state, 0x38, &buf); ++ _mt_fe_tn_set_reg(state, 0x38, buf); ++ _mt_fe_tn_get_reg(state, 0x32, &buf); ++ buf = buf | 0x10; ++ _mt_fe_tn_set_reg(state, 0x32, buf); ++ _mt_fe_tn_set_reg(state, 0x30, 0x7f); ++ _mt_fe_tn_set_reg(state, 0x30, 0xff); ++ _mt_fe_tn_get_reg(state, 0x32, &buf); ++ buf = buf & 0xdf; ++ _mt_fe_tn_set_reg(state, 0x32, buf); ++ _mt_fe_tn_set_reg(state, 0x31, 0x80); ++ _mt_fe_tn_set_reg(state, 0x31, 0x00); ++ msleep(3); ++ _mt_fe_tn_get_reg(state, 0x37, &buf); ++ _mt_fe_tn_set_reg(state, 0x37, buf); ++ /* ++ if ((freq_KHz == 802000) || (freq_KHz == 826000)) { ++ _mt_fe_tn_set_reg(state, 0x37, 0x5e); ++ } ++ */ ++ _mt_fe_tn_get_reg(state, 0x32, &buf); ++ buf = (buf & 0xef) | 0x30; ++ _mt_fe_tn_set_reg(state, 0x32, buf); ++ _mt_fe_tn_set_reg(state, 0x41, 0x00); ++ msleep(2); ++ _mt_fe_tn_set_reg(state, 0x41, 0x02); ++ } else { ++ return 1; ++ } ++ return 0; ++} + -+ _mt_fe_tn_set_reg(state, 0x2b, 0x46); -+ _mt_fe_tn_set_reg(state, 0x2c, 0x75); -+ -+ if (state->tuner_mtt == 0x00) { -+ u8 tmp = 0; -+ _mt_fe_tn_get_reg(state, 0x01, &tmp); -+ printk("m88dc2800: tuner id = 0x%02x ", tmp); -+ switch(tmp) { -+ case 0x0d: -+ state->tuner_mtt = 0xD1; -+ break; -+ case 0x8e: -+ default: -+ state->tuner_mtt = 0xE1; -+ break; -+ } -+ } -+ return 0; -+} -+ -+static int mt_fe_tn_set_freq_tc2800(struct m88dc2800_state *state, u32 freq_KHz) -+{ ++static int _mt_fe_tn_set_BB_tc2800(struct m88dc2800_state *state) ++{ ++ return 0; ++} ++ ++ static int _mt_fe_tn_set_appendix_tc2800(struct m88dc2800_state *state) ++ ++{ + u8 buf; -+ u8 buf1; -+ -+ mt_fe_tn_init_tc2800(state); -+ -+ state->tuner_freq = freq_KHz; ++ const u32 freq_KHz = state->tuner_freq; ++ if (state->tuner_mtt == 0xD1) { ++ if ((freq_KHz == 123000) || (freq_KHz == 147000) || ++ (freq_KHz == 171000) || (freq_KHz == 195000)) { ++ _mt_fe_tn_set_reg(state, 0x20, 0x1b); ++ } ++ if ((freq_KHz == 371000) || (freq_KHz == 419000) || ++ (freq_KHz == 610000) || (freq_KHz == 730000) || ++ (freq_KHz == 754000) || (freq_KHz == 826000)) { ++ _mt_fe_tn_get_reg(state, 0x0d, &buf); ++ _mt_fe_tn_set_reg(state, 0x0d, (u8) (buf + 1)); ++ } ++ if ((freq_KHz == 522000) || (freq_KHz == 578000) || ++ (freq_KHz == 634000) || (freq_KHz == 690000) || ++ (freq_KHz == 834000)) { ++ _mt_fe_tn_get_reg(state, 0x0d, &buf); ++ _mt_fe_tn_set_reg(state, 0x0d, (u8) (buf - 1)); ++ } ++ } else if (state->tuner_mtt == 0xE1) { ++ _mt_fe_tn_set_reg(state, 0x20, 0xfc); ++ if (freq_KHz == 123000 || freq_KHz == 147000 || ++ freq_KHz == 171000 || freq_KHz == 195000 || ++ freq_KHz == 219000 || freq_KHz == 267000 || ++ freq_KHz == 291000 || freq_KHz == 339000 || ++ freq_KHz == 387000 || freq_KHz == 435000 || ++ freq_KHz == 482000 || freq_KHz == 530000 || ++ freq_KHz == 722000 || ++ (state->tuner_custom_cfg == 1 && freq_KHz == 315000)) { ++ _mt_fe_tn_set_reg(state, 0x20, 0x5c); ++ } ++ } ++ return 0; ++} + -+ if (freq_KHz > 500000) -+ _mt_fe_tn_set_reg(state, 0x21, 0xb9); -+ else -+ _mt_fe_tn_set_reg(state, 0x21, 0x99); -+ -+ mt_fe_tn_wakeup_tc2800(state); -+ -+ _mt_fe_tn_set_reg(state, 0x05, 0x7f); -+ _mt_fe_tn_set_reg(state, 0x06, 0xf8); -+ -+ _mt_fe_tn_set_RF_front_tc2800(state); -+ _mt_fe_tn_set_PLL_freq_tc2800(state); -+ _mt_fe_tn_set_DAC_tc2800(state); -+ _mt_fe_tn_set_BB_tc2800(state); -+ _mt_fe_tn_preset_tc2800(state); -+ -+ _mt_fe_tn_set_reg(state, 0x05, 0x00); -+ _mt_fe_tn_set_reg(state, 0x06, 0x00); -+ -+ if (state->tuner_mtt == 0xD1) { -+ _mt_fe_tn_set_reg(state, 0x00, 0x01); -+ _mt_fe_tn_set_reg(state, 0x00, 0x00); -+ -+ msleep(5); -+ _mt_fe_tn_set_reg(state, 0x41, 0x00); -+ msleep(5); ++ static int _mt_fe_tn_set_DAC_tc2800(struct m88dc2800_state *state) ++{ ++ u8 buf, tempnumber; ++ s32 N; ++ s32 f1f2number, f1, f2, delta1, Totalnum1; ++ s32 cntT, cntin, NCOI, z0, z1, z2, tmp; ++ u32 fc, fadc, fsd, f2d; ++ u32 FreqTrue108_Hz; ++ s32 M = state->tuner_crystal / 4000; ++ /* const u8 bandwidth = state->tuner_bandwidth; */ ++ const u16 DAC_fre = 108; ++ const u32 crystal_KHz = state->tuner_crystal; ++ const u32 DACFreq_KHz = state->tuner_dac; ++ const u32 freq_KHz = state->tuner_freq; ++ ++ if (state->tuner_mtt == 0xE1) { ++ _mt_fe_tn_get_reg(state, 0x33, &buf); ++ M = buf & 0x0f; ++ if (M == 0) ++ M = 6; ++ } ++ _mt_fe_tn_get_reg(state, 0x34, &buf); ++ N = buf & 0x07; ++ _mt_fe_tn_get_reg(state, 0x35, &buf); ++ N = (N << 8) + buf; ++ buf = ((N + 256) * crystal_KHz / M / DAC_fre + 500) / 1000; ++ if (state->tuner_mtt == 0xE1) { ++ _mt_fe_tn_set_appendix_tc2800(state); ++ if (freq_KHz == 187000 || freq_KHz == 195000 || ++ freq_KHz == 131000 || freq_KHz == 211000 || ++ freq_KHz == 219000 || freq_KHz == 227000 || ++ freq_KHz == 267000 || freq_KHz == 299000 || ++ freq_KHz == 347000 || freq_KHz == 363000 || ++ freq_KHz == 395000 || freq_KHz == 403000 || ++ freq_KHz == 435000 || freq_KHz == 482000 || ++ freq_KHz == 474000 || freq_KHz == 490000 || ++ freq_KHz == 610000 || freq_KHz == 642000 || ++ freq_KHz == 666000 || freq_KHz == 722000 || ++ freq_KHz == 754000 || ++ ((freq_KHz == 379000 || freq_KHz == 467000 || ++ freq_KHz == 762000) && state->tuner_custom_cfg != 1)) { ++ buf = buf + 1; ++ } ++ if (freq_KHz == 123000 || freq_KHz == 139000 || ++ freq_KHz == 147000 || freq_KHz == 171000 || ++ freq_KHz == 179000 || freq_KHz == 203000 || ++ freq_KHz == 235000 || freq_KHz == 251000 || ++ freq_KHz == 259000 || freq_KHz == 283000 || ++ freq_KHz == 331000 || freq_KHz == 363000 || ++ freq_KHz == 371000 || freq_KHz == 387000 || ++ freq_KHz == 411000 || freq_KHz == 427000 || ++ freq_KHz == 443000 || freq_KHz == 451000 || ++ freq_KHz == 459000 || freq_KHz == 506000 || ++ freq_KHz == 514000 || freq_KHz == 538000 || ++ freq_KHz == 546000 || freq_KHz == 554000 || ++ freq_KHz == 562000 || freq_KHz == 570000 || ++ freq_KHz == 578000 || freq_KHz == 602000 || ++ freq_KHz == 626000 || freq_KHz == 658000 || ++ freq_KHz == 690000 || freq_KHz == 714000 || ++ freq_KHz == 746000 || freq_KHz == 522000 || ++ freq_KHz == 826000 || freq_KHz == 155000 || ++ freq_KHz == 530000 || ++ ((freq_KHz == 275000 || freq_KHz == 355000) && ++ state->tuner_custom_cfg != 1) || ++ ((freq_KHz == 467000 || freq_KHz == 762000 || ++ freq_KHz == 778000 || freq_KHz == 818000) && ++ state->tuner_custom_cfg == 1)) { ++ buf = buf - 1; ++ } ++ } ++ _mt_fe_tn_set_reg(state, 0x0e, buf); ++ _mt_fe_tn_set_reg(state, 0x0d, buf); ++ f1f2number = ++ (((DACFreq_KHz * M * buf) / crystal_KHz) << 16) / (N + 256) + ++ (((DACFreq_KHz * M * buf) % crystal_KHz) << 16) / ((N + 256) * ++ crystal_KHz); ++ _mt_fe_tn_set_reg(state, 0xf1, (f1f2number & 0xff00) >> 8); ++ _mt_fe_tn_set_reg(state, 0xf2, f1f2number & 0x00ff); ++ FreqTrue108_Hz = ++ (N + 256) * crystal_KHz / (M * buf) * 1000 + ++ (((N + 256) * crystal_KHz) % (M * buf)) * 1000 / (M * buf); ++ f1 = 4096; ++ fc = FreqTrue108_Hz; ++ fadc = fc / 4; ++ fsd = 27000000; ++ f2d = state->tuner_bandwidth * 1000 / 2 - 150; ++ f2 = (fsd / 250) * f2d / ((fc + 500) / 1000); ++ delta1 = ((f1 - f2) << 15) / f2; ++ Totalnum1 = ((f1 - f2) << 15) - delta1 * f2; ++ cntT = f2; ++ cntin = Totalnum1; ++ NCOI = delta1; ++ z0 = cntin; ++ z1 = cntT; ++ z2 = NCOI; ++ tempnumber = (z0 & 0xff00) >> 8; ++ _mt_fe_tn_set_reg(state, 0xc9, (u8) (tempnumber & 0x0f)); ++ tempnumber = (z0 & 0xff); ++ _mt_fe_tn_set_reg(state, 0xca, tempnumber); ++ tempnumber = (z1 & 0xff00) >> 8; ++ _mt_fe_tn_set_reg(state, 0xcb, tempnumber); ++ tempnumber = (z1 & 0xff); ++ _mt_fe_tn_set_reg(state, 0xcc, tempnumber); ++ tempnumber = (z2 & 0xff00) >> 8; ++ _mt_fe_tn_set_reg(state, 0xcd, tempnumber); ++ tempnumber = (z2 & 0xff); ++ _mt_fe_tn_set_reg(state, 0xce, tempnumber); ++ tmp = f1; ++ f1 = f2; ++ f2 = tmp / 2; ++ delta1 = ((f1 - f2) << 15) / f2; ++ Totalnum1 = ((f1 - f2) << 15) - delta1 * f2; ++ NCOI = (f1 << 15) / f2 - (1 << 15); ++ cntT = f2; ++ cntin = Totalnum1; ++ z0 = cntin; ++ z1 = cntT; ++ z2 = NCOI; ++ tempnumber = (z0 & 0xff00) >> 8; ++ _mt_fe_tn_set_reg(state, 0xd9, (u8) (tempnumber & 0x0f)); ++ tempnumber = (z0 & 0xff); ++ _mt_fe_tn_set_reg(state, 0xda, tempnumber); ++ tempnumber = (z1 & 0xff00) >> 8; ++ _mt_fe_tn_set_reg(state, 0xdb, tempnumber); ++ tempnumber = (z1 & 0xff); ++ _mt_fe_tn_set_reg(state, 0xdc, tempnumber); ++ tempnumber = (z2 & 0xff00) >> 8; ++ _mt_fe_tn_set_reg(state, 0xdd, tempnumber); ++ tempnumber = (z2 & 0xff); ++ _mt_fe_tn_set_reg(state, 0xde, tempnumber); ++ ++ return 0; ++} ++ ++static int _mt_fe_tn_preset_tc2800(struct m88dc2800_state *state) ++{ ++ if (state->tuner_mtt == 0xD1) { ++ _mt_fe_tn_set_reg(state, 0x19, 0x4a); ++ _mt_fe_tn_set_reg(state, 0x1b, 0x4b); ++ _mt_fe_tn_set_reg(state, 0x04, 0x04); ++ _mt_fe_tn_set_reg(state, 0x17, 0x0d); ++ _mt_fe_tn_set_reg(state, 0x62, 0x6c); ++ _mt_fe_tn_set_reg(state, 0x63, 0xf4); ++ _mt_fe_tn_set_reg(state, 0x1f, 0x0e); ++ _mt_fe_tn_set_reg(state, 0x6b, 0xf4); ++ _mt_fe_tn_set_reg(state, 0x14, 0x01); ++ _mt_fe_tn_set_reg(state, 0x5a, 0x75); ++ _mt_fe_tn_set_reg(state, 0x66, 0x74); ++ _mt_fe_tn_set_reg(state, 0x72, 0xe0); ++ _mt_fe_tn_set_reg(state, 0x70, 0x07); ++ _mt_fe_tn_set_reg(state, 0x15, 0x7b); ++ _mt_fe_tn_set_reg(state, 0x55, 0x71); ++ _mt_fe_tn_set_reg(state, 0x75, 0x55); ++ _mt_fe_tn_set_reg(state, 0x76, 0xac); ++ _mt_fe_tn_set_reg(state, 0x77, 0x6c); ++ _mt_fe_tn_set_reg(state, 0x78, 0x8b); ++ _mt_fe_tn_set_reg(state, 0x79, 0x42); ++ _mt_fe_tn_set_reg(state, 0x7a, 0xd2); ++ _mt_fe_tn_set_reg(state, 0x81, 0x01); ++ _mt_fe_tn_set_reg(state, 0x82, 0x00); ++ _mt_fe_tn_set_reg(state, 0x82, 0x02); ++ _mt_fe_tn_set_reg(state, 0x82, 0x04); ++ _mt_fe_tn_set_reg(state, 0x82, 0x06); ++ _mt_fe_tn_set_reg(state, 0x82, 0x08); ++ _mt_fe_tn_set_reg(state, 0x82, 0x09); ++ _mt_fe_tn_set_reg(state, 0x82, 0x29); ++ _mt_fe_tn_set_reg(state, 0x82, 0x49); ++ _mt_fe_tn_set_reg(state, 0x82, 0x58); ++ _mt_fe_tn_set_reg(state, 0x82, 0x59); ++ _mt_fe_tn_set_reg(state, 0x82, 0x98); ++ _mt_fe_tn_set_reg(state, 0x82, 0x99); ++ _mt_fe_tn_set_reg(state, 0x10, 0x05); ++ _mt_fe_tn_set_reg(state, 0x10, 0x0d); ++ _mt_fe_tn_set_reg(state, 0x11, 0x95); ++ _mt_fe_tn_set_reg(state, 0x11, 0x9d); ++ if (state->tuner_loopthrough != 0) { ++ _mt_fe_tn_set_reg(state, 0x67, 0x25); ++ } else { ++ _mt_fe_tn_set_reg(state, 0x67, 0x05); ++ } ++ } else if (state->tuner_mtt == 0xE1) { ++ _mt_fe_tn_set_reg(state, 0x1b, 0x47); ++ if (state->tuner_mode == 0) { /* DVB-C */ ++ _mt_fe_tn_set_reg(state, 0x66, 0x74); ++ _mt_fe_tn_set_reg(state, 0x62, 0x2c); ++ _mt_fe_tn_set_reg(state, 0x63, 0x54); ++ _mt_fe_tn_set_reg(state, 0x68, 0x0b); ++ _mt_fe_tn_set_reg(state, 0x14, 0x00); ++ } else { /* CTTB */ ++ _mt_fe_tn_set_reg(state, 0x66, 0x74); ++ _mt_fe_tn_set_reg(state, 0x62, 0x0c); ++ _mt_fe_tn_set_reg(state, 0x63, 0x54); ++ _mt_fe_tn_set_reg(state, 0x68, 0x0b); ++ _mt_fe_tn_set_reg(state, 0x14, 0x05); ++ } ++ _mt_fe_tn_set_reg(state, 0x6f, 0x00); ++ _mt_fe_tn_set_reg(state, 0x84, 0x04); ++ _mt_fe_tn_set_reg(state, 0x5e, 0xbe); ++ _mt_fe_tn_set_reg(state, 0x87, 0x07); ++ _mt_fe_tn_set_reg(state, 0x8a, 0x1f); ++ _mt_fe_tn_set_reg(state, 0x8b, 0x1f); ++ _mt_fe_tn_set_reg(state, 0x88, 0x30); ++ _mt_fe_tn_set_reg(state, 0x58, 0x34); ++ _mt_fe_tn_set_reg(state, 0x61, 0x8c); ++ _mt_fe_tn_set_reg(state, 0x6a, 0x42); ++ } ++ return 0; ++} ++ ++static int mt_fe_tn_wakeup_tc2800(struct m88dc2800_state *state) ++{ ++ _mt_fe_tn_set_reg(state, 0x16, 0xb1); ++ _mt_fe_tn_set_reg(state, 0x09, 0x7d); ++ return 0; ++} ++ ++ static int mt_fe_tn_sleep_tc2800(struct m88dc2800_state *state) ++{ ++ _mt_fe_tn_set_reg(state, 0x16, 0xb0); ++ _mt_fe_tn_set_reg(state, 0x09, 0x6d); ++ return 0; ++} ++ ++ static int mt_fe_tn_init_tc2800(struct m88dc2800_state *state) ++{ ++ if (state->tuner_init_OK != 1) { ++ state->tuner_dev_addr = 0x61; /* TUNER_I2C_ADDR_TC2800 */ ++ state->tuner_freq = 650000; ++ state->tuner_qam = 0; ++ state->tuner_mode = 0; // 0: DVB-C, 1: CTTB ++ state->tuner_bandwidth = 8; ++ state->tuner_loopthrough = 0; ++ state->tuner_crystal = 24000; ++ state->tuner_dac = 7200; ++ state->tuner_mtt = 0x00; ++ state->tuner_custom_cfg = 0; ++ state->tuner_version = 30022; /* Driver version number */ ++ state->tuner_time = 12092611; ++ state->tuner_init_OK = 1; ++ } ++ _mt_fe_tn_set_reg(state, 0x2b, 0x46); ++ _mt_fe_tn_set_reg(state, 0x2c, 0x75); ++ if (state->tuner_mtt == 0x00) { ++ u8 tmp = 0; ++ _mt_fe_tn_get_reg(state, 0x01, &tmp); ++ printk(KERN_INFO "m88dc2800: tuner id = 0x%02x ", tmp); ++ switch (tmp) { ++ case 0x0d: ++ state->tuner_mtt = 0xD1; ++ break; ++ case 0x8e: ++ default: ++ state->tuner_mtt = 0xE1; ++ break; ++ } ++ } ++ return 0; ++} ++ ++ static int mt_fe_tn_set_freq_tc2800(struct m88dc2800_state *state, ++ u32 freq_KHz) ++{ ++ u8 buf; ++ u8 buf1; ++ ++ mt_fe_tn_init_tc2800(state); ++ state->tuner_freq = freq_KHz; ++ _mt_fe_tn_set_reg(state, 0x21, freq_KHz > 500000 ? 0xb9 : 0x99); ++ mt_fe_tn_wakeup_tc2800(state); ++ _mt_fe_tn_set_reg(state, 0x05, 0x7f); ++ _mt_fe_tn_set_reg(state, 0x06, 0xf8); ++ _mt_fe_tn_set_RF_front_tc2800(state); ++ _mt_fe_tn_set_PLL_freq_tc2800(state); ++ _mt_fe_tn_set_DAC_tc2800(state); ++ _mt_fe_tn_set_BB_tc2800(state); ++ _mt_fe_tn_preset_tc2800(state); ++ _mt_fe_tn_set_reg(state, 0x05, 0x00); ++ _mt_fe_tn_set_reg(state, 0x06, 0x00); ++ if (state->tuner_mtt == 0xD1) { ++ _mt_fe_tn_set_reg(state, 0x00, 0x01); ++ _mt_fe_tn_set_reg(state, 0x00, 0x00); ++ msleep(5); ++ _mt_fe_tn_set_reg(state, 0x41, 0x00); ++ msleep(5); + _mt_fe_tn_set_reg(state, 0x41, 0x02); + -+ _mt_fe_tn_get_reg(state, 0x69, &buf1); -+ buf1 = buf1 & 0x0f; -+ -+ _mt_fe_tn_get_reg(state, 0x61, &buf); -+ buf = buf & 0x0f; -+ if (buf == 0x0c) -+ { -+ _mt_fe_tn_set_reg(state, 0x6a, 0x59); -+ } -+ -+ if(buf1 > 0x02) -+ { -+ if (freq_KHz > 600000) -+ _mt_fe_tn_set_reg(state, 0x66, 0x44); -+ else if (freq_KHz > 500000) -+ _mt_fe_tn_set_reg(state, 0x66, 0x64); -+ else -+ _mt_fe_tn_set_reg(state, 0x66, 0x74); -+ } -+ -+ if (buf1 < 0x03) -+ { -+ if (freq_KHz > 800000) -+ _mt_fe_tn_set_reg(state, 0x87, 0x64); -+ else if (freq_KHz > 600000) -+ _mt_fe_tn_set_reg(state, 0x87, 0x54); -+ else if (freq_KHz > 500000) -+ _mt_fe_tn_set_reg(state, 0x87, 0x54); -+ else if (freq_KHz > 300000) -+ _mt_fe_tn_set_reg(state, 0x87, 0x43); -+ else if (freq_KHz > 220000) -+ _mt_fe_tn_set_reg(state, 0x87, 0x54); -+ else if (freq_KHz > 110000) -+ _mt_fe_tn_set_reg(state, 0x87, 0x14); -+ else -+ _mt_fe_tn_set_reg(state, 0x87, 0x54); -+ -+ msleep(5); -+ } -+ else if (buf < 0x0c) -+ { -+ if (freq_KHz > 800000) -+ _mt_fe_tn_set_reg(state, 0x87, 0x14); -+ else if (freq_KHz >600000) -+ _mt_fe_tn_set_reg(state, 0x87, 0x14); -+ else if (freq_KHz > 500000) -+ _mt_fe_tn_set_reg(state, 0x87, 0x34); -+ else if (freq_KHz > 300000) -+ _mt_fe_tn_set_reg(state, 0x87, 0x43); -+ else if (freq_KHz > 220000) -+ _mt_fe_tn_set_reg(state, 0x87, 0x54); -+ else if (freq_KHz > 110000) -+ _mt_fe_tn_set_reg(state, 0x87, 0x14); -+ else -+ _mt_fe_tn_set_reg(state, 0x87, 0x54); -+ -+ msleep(5); -+ } -+ } else if ((state->tuner_mtt == 0xE1)) { -+ _mt_fe_tn_set_reg(state, 0x00, 0x01); -+ _mt_fe_tn_set_reg(state, 0x00, 0x00); -+ -+ msleep(20); -+ -+ _mt_fe_tn_get_reg(state, 0x32, &buf); -+ buf = (buf & 0xef) | 0x28; -+ _mt_fe_tn_set_reg(state, 0x32, buf); -+ -+ msleep(50); -+ _mt_fe_tn_get_reg(state, 0x38, &buf); -+ _mt_fe_tn_set_reg(state, 0x38, buf); -+ _mt_fe_tn_get_reg(state, 0x32, &buf); -+ buf = (buf & 0xf7)| 0x10 ; -+ _mt_fe_tn_set_reg(state, 0x32, buf); -+ -+ msleep(10); -+ -+ _mt_fe_tn_get_reg(state, 0x69, &buf); -+ buf = buf & 0x03; -+ _mt_fe_tn_set_reg(state, 0x2a, buf); -+ -+ if(buf > 0) -+ { -+ msleep(20); -+ _mt_fe_tn_get_reg(state, 0x84, &buf); -+ buf = buf & 0x1f; -+ _mt_fe_tn_set_reg(state, 0x68, 0x0a); -+ _mt_fe_tn_get_reg(state, 0x88, &buf1); -+ buf1 = buf1 & 0x1f; -+ if(buf <= buf1) -+ _mt_fe_tn_set_reg(state, 0x66, 0x44); -+ else -+ _mt_fe_tn_set_reg(state, 0x66, 0x74); -+ } -+ else -+ { -+ if (freq_KHz <= 600000) -+ { -+ _mt_fe_tn_set_reg(state, 0x68, 0x0c); -+ } -+ else -+ { -+ _mt_fe_tn_set_reg(state, 0x68, 0x0e); -+ } -+ _mt_fe_tn_set_reg(state, 0x30, 0xfb); -+ _mt_fe_tn_set_reg(state, 0x30, 0xff); -+ _mt_fe_tn_set_reg(state, 0x31, 0x04); -+ _mt_fe_tn_set_reg(state, 0x31, 0x00); -+ } -+ if(state->tuner_loopthrough != 0) { -+ _mt_fe_tn_get_reg(state, 0x28, &buf); -+ if (buf == 0) { -+ _mt_fe_tn_set_reg(state, 0x28, 0xff); -+ _mt_fe_tn_get_reg(state, 0x61, &buf); -+ buf = buf & 0x0f; -+ if(buf > 9) -+ _mt_fe_tn_set_reg(state, 0x67, 0x74); -+ else if (buf >6) -+ _mt_fe_tn_set_reg(state, 0x67, 0x64); -+ else if (buf >3) -+ _mt_fe_tn_set_reg(state, 0x67, 0x54); -+ else -+ _mt_fe_tn_set_reg(state, 0x67, 0x44); -+ } -+ } else { -+ _mt_fe_tn_set_reg(state, 0x67, 0x34); -+ } -+ } else { -+ return 1; -+ } -+ return 0; -+} -+ -+/* -+static int mt_fe_tn_set_BB_filter_band_tc2800(struct m88dc2800_state *state, u8 bandwidth) -+{ -+ u8 buf, tmp; -+ -+ _mt_fe_tn_get_reg(state, 0x53, &tmp); -+ ++ _mt_fe_tn_get_reg(state, 0x69, &buf1); ++ buf1 = buf1 & 0x0f; ++ _mt_fe_tn_get_reg(state, 0x61, &buf); ++ buf = buf & 0x0f; ++ if (buf == 0x0c) ++ _mt_fe_tn_set_reg(state, 0x6a, 0x59); ++ if (buf1 > 0x02) { ++ if (freq_KHz > 600000) ++ _mt_fe_tn_set_reg(state, 0x66, 0x44); ++ else if (freq_KHz > 500000) ++ _mt_fe_tn_set_reg(state, 0x66, 0x64); ++ else ++ _mt_fe_tn_set_reg(state, 0x66, 0x74); ++ } ++ if (buf1 < 0x03) { ++ if (freq_KHz > 800000) ++ _mt_fe_tn_set_reg(state, 0x87, 0x64); ++ else if (freq_KHz > 600000) ++ _mt_fe_tn_set_reg(state, 0x87, 0x54); ++ else if (freq_KHz > 500000) ++ _mt_fe_tn_set_reg(state, 0x87, 0x54); ++ else if (freq_KHz > 300000) ++ _mt_fe_tn_set_reg(state, 0x87, 0x43); ++ else if (freq_KHz > 220000) ++ _mt_fe_tn_set_reg(state, 0x87, 0x54); ++ else if (freq_KHz > 110000) ++ _mt_fe_tn_set_reg(state, 0x87, 0x14); ++ else ++ _mt_fe_tn_set_reg(state, 0x87, 0x54); ++ msleep(5); ++ } else if (buf < 0x0c) { ++ if (freq_KHz > 800000) ++ _mt_fe_tn_set_reg(state, 0x87, 0x14); ++ else if (freq_KHz > 600000) ++ _mt_fe_tn_set_reg(state, 0x87, 0x14); ++ else if (freq_KHz > 500000) ++ _mt_fe_tn_set_reg(state, 0x87, 0x34); ++ else if (freq_KHz > 300000) ++ _mt_fe_tn_set_reg(state, 0x87, 0x43); ++ else if (freq_KHz > 220000) ++ _mt_fe_tn_set_reg(state, 0x87, 0x54); ++ else if (freq_KHz > 110000) ++ _mt_fe_tn_set_reg(state, 0x87, 0x14); ++ else ++ _mt_fe_tn_set_reg(state, 0x87, 0x54); ++ msleep(5); ++ } ++ } else if ((state->tuner_mtt == 0xE1)) { ++ _mt_fe_tn_set_reg(state, 0x00, 0x01); ++ _mt_fe_tn_set_reg(state, 0x00, 0x00); ++ msleep(20); ++ _mt_fe_tn_get_reg(state, 0x32, &buf); ++ buf = (buf & 0xef) | 0x28; ++ _mt_fe_tn_set_reg(state, 0x32, buf); ++ msleep(50); ++ _mt_fe_tn_get_reg(state, 0x38, &buf); ++ _mt_fe_tn_set_reg(state, 0x38, buf); ++ _mt_fe_tn_get_reg(state, 0x32, &buf); ++ buf = (buf & 0xf7) | 0x10; ++ _mt_fe_tn_set_reg(state, 0x32, buf); ++ msleep(10); ++ _mt_fe_tn_get_reg(state, 0x69, &buf); ++ buf = buf & 0x03; ++ _mt_fe_tn_set_reg(state, 0x2a, buf); ++ if (buf > 0) { ++ msleep(20); ++ _mt_fe_tn_get_reg(state, 0x84, &buf); ++ buf = buf & 0x1f; ++ _mt_fe_tn_set_reg(state, 0x68, 0x0a); ++ _mt_fe_tn_get_reg(state, 0x88, &buf1); ++ buf1 = buf1 & 0x1f; ++ if (buf <= buf1) ++ _mt_fe_tn_set_reg(state, 0x66, 0x44); ++ else ++ _mt_fe_tn_set_reg(state, 0x66, 0x74); ++ } else { ++ if (freq_KHz <= 600000) ++ _mt_fe_tn_set_reg(state, 0x68, 0x0c); ++ else ++ _mt_fe_tn_set_reg(state, 0x68, 0x0e); ++ _mt_fe_tn_set_reg(state, 0x30, 0xfb); ++ _mt_fe_tn_set_reg(state, 0x30, 0xff); ++ _mt_fe_tn_set_reg(state, 0x31, 0x04); ++ _mt_fe_tn_set_reg(state, 0x31, 0x00); ++ } ++ if (state->tuner_loopthrough != 0) { ++ _mt_fe_tn_get_reg(state, 0x28, &buf); ++ if (buf == 0) { ++ _mt_fe_tn_set_reg(state, 0x28, 0xff); ++ _mt_fe_tn_get_reg(state, 0x61, &buf); ++ buf = buf & 0x0f; ++ if (buf > 9) ++ _mt_fe_tn_set_reg(state, 0x67, 0x74); ++ else if (buf > 6) ++ _mt_fe_tn_set_reg(state, 0x67, 0x64); ++ else if (buf > 3) ++ _mt_fe_tn_set_reg(state, 0x67, 0x54); ++ else ++ _mt_fe_tn_set_reg(state, 0x67, 0x44); ++ } ++ } else { ++ _mt_fe_tn_set_reg(state, 0x67, 0x34); ++ } ++ } else { ++ return 1; ++ } ++ return 0; ++} ++ ++ ++/* ++static int mt_fe_tn_set_BB_filter_band_tc2800(struct m88dc2800_state *state, ++ u8 bandwidth) ++{ ++ u8 buf, tmp; ++ ++ _mt_fe_tn_get_reg(state, 0x53, &tmp); ++ + if (bandwidth == 6) -+ buf = 0x01 << 1; ++ buf = 0x01 << 1; + else if (bandwidth == 7) -+ buf = 0x02 << 1; ++ buf = 0x02 << 1; + else if (bandwidth == 8) -+ buf = 0x04 << 1; ++ buf = 0x04 << 1; + else -+ buf = 0x04 << 1; -+ -+ tmp &= 0xf1; -+ tmp |= buf; -+ _mt_fe_tn_set_reg(state, 0x53, tmp); ++ buf = 0x04 << 1; ++ ++ tmp &= 0xf1; ++ tmp |= buf; ++ _mt_fe_tn_set_reg(state, 0x53, tmp); + state->tuner_bandwidth = bandwidth; -+ return 0; -+} -+*/ -+ -+/*static s64 mt_fe_tn_get_signal_strength_tc2800(struct m88dc2800_state *state)*/ -+static s32 mt_fe_tn_get_signal_strength_tc2800(struct m88dc2800_state *state) -+{ -+ /*s64 level = -107;*/ -+ s32 level = -107; -+ s32 tmp1, tmp2, tmp3, tmp4, tmp5, tmp6; -+ s32 val1, val2, val; -+ s32 result2, result3, result4, result5, result6; -+ s32 append; -+ u8 tmp; -+ s32 freq_KHz = (s32)state->tuner_freq; -+ -+ if (state->tuner_mtt == 0xD1) { -+ _mt_fe_tn_get_reg(state, 0x61, &tmp); -+ tmp1 = tmp & 0x0f; -+ -+ _mt_fe_tn_get_reg(state, 0x69, &tmp); -+ tmp2 = tmp & 0x0f; -+ -+ _mt_fe_tn_get_reg(state, 0x73, &tmp); -+ tmp3 = tmp & 0x07; -+ -+ _mt_fe_tn_get_reg(state, 0x7c, &tmp); -+ tmp4 = (tmp >> 4) & 0x0f; -+ -+ _mt_fe_tn_get_reg(state, 0x7b, &tmp); -+ tmp5 = tmp & 0x0f; -+ -+ _mt_fe_tn_get_reg(state, 0x7f, &tmp); -+ tmp6 = (tmp >> 5) & 0x01; -+ -+ if (tmp1 > 6) { -+ val1 = 0; -+ if (freq_KHz <= 200000) { -+ val2 = (tmp1 - 6) * 267; -+ } else if (freq_KHz <= 600000) { -+ val2 = (tmp1 - 6) * 280; -+ } else { -+ val2 = (tmp1 - 6) * 290; -+ } -+ val = val1 + val2; -+ } else { -+ if (tmp1 == 0) { -+ val1 = -550; -+ } else { -+ val1 = 0; -+ } -+ if ((tmp1 < 4) && (freq_KHz >= 506000)) { -+ val1 = -850; -+ } -+ val2 = 0; -+ val = val1 + val2; -+ } -+ -+ if (freq_KHz <= 95000) { -+ result2 = tmp2 * 289; -+ } else if (freq_KHz <= 155000) { -+ result2 = tmp2 * 278; -+ } else if (freq_KHz <= 245000) { -+ result2 = tmp2 * 267; -+ } else if (freq_KHz <= 305000) { -+ result2 = tmp2 * 256; -+ } else if (freq_KHz <= 335000) { -+ result2 = tmp2 * 244; -+ } else if (freq_KHz <= 425000) { -+ result2 = tmp2 * 233; -+ } else if (freq_KHz <= 575000) { -+ result2 = tmp2 * 222; -+ } else if (freq_KHz <= 665000) { -+ result2 = tmp2 * 211; -+ } else { -+ result2 = tmp2 * 200; -+ } -+ result3 = (6 - tmp3) * 100; -+ result4 = 300 * tmp4; -+ result5 = 50 * tmp5; -+ result6 = 300 * tmp6; -+ if (freq_KHz < 105000) { -+ append = -450; -+ } else if (freq_KHz <= 227000) { -+ append = -4 * (freq_KHz / 1000 - 100) + 150; -+ } else if (freq_KHz <= 305000) { -+ append = -4 * (freq_KHz / 1000 - 100); -+ } else if (freq_KHz <= 419000) { -+ append = 500 - 40 * (freq_KHz / 1000 - 300) / 17 + 130; -+ } else if (freq_KHz <= 640000) { -+ append = 500 - 40 * (freq_KHz / 1000 - 300) / 17; -+ } else { -+ append = -500; -+ } -+ level = append - (val + result2 + result3 + result4 + result5 + result6); -+ level /= 100; -+ } else if (state->tuner_mtt == 0xE1) { -+ _mt_fe_tn_get_reg(state, 0x61, &tmp); -+ tmp1 = tmp & 0x0f; -+ -+ _mt_fe_tn_get_reg(state, 0x84, &tmp); -+ tmp2 = tmp & 0x1f; -+ -+ _mt_fe_tn_get_reg(state, 0x69, &tmp); -+ tmp3 = tmp & 0x03; -+ -+ _mt_fe_tn_get_reg(state, 0x73, &tmp); -+ tmp4 = tmp & 0x0f; -+ -+ _mt_fe_tn_get_reg(state, 0x7c, &tmp); -+ tmp5 = (tmp >> 4) & 0x0f; -+ -+ _mt_fe_tn_get_reg(state, 0x7b, &tmp); -+ tmp6 = tmp & 0x0f; -+ -+ if (freq_KHz < 151000) { -+ result2 = (1150 - freq_KHz / 100) * 163 / 33 + 4230; -+ result3 = (1150 - freq_KHz / 100) * 115 / 33 + 1850; -+ result4 = -3676 * (freq_KHz / 1000) / 100 + 6115; -+ } else if (freq_KHz < 257000) { -+ result2 = (1540 - freq_KHz / 100) * 11 / 4 + 3870; -+ result3 = (1540 - freq_KHz / 100) * 205 / 96 + 2100; -+ result4 = -21 * freq_KHz / 1000 + 5084; -+ } else if (freq_KHz < 305000) { -+ result2 = (2620 - freq_KHz / 100) * 5 / 3 + 2770; -+ result3 = (2620 - freq_KHz / 100) * 10 / 7 + 1700; -+ result4 = 650; -+ } else if (freq_KHz < 449000) { -+ result2 = (307 - freq_KHz / 1000) * 82 / 27 + 11270; -+ result3 = (3100 - freq_KHz / 100) * 5 / 3 + 10000; -+ result4 = 134 * freq_KHz / 10000 + 11875; -+ } else { -+ result2 = (307 - freq_KHz / 1000) * 82 / 27 + 11270; -+ result3 = 8400; -+ result4 = 5300; -+ } -+ -+ if (tmp1 > 6) { -+ val1 = result2; -+ val2 = 2900; -+ val = 500; -+ } else if (tmp1 > 0) { -+ val1 = result3; -+ val2 = 2700; -+ val = 500; -+ } else { -+ val1 = result4; -+ val2 = 2700; -+ val = 400; -+ } -+ level = val1 - (val2 * tmp1 + 500 * tmp2 + 3000 * tmp3 - 500 * tmp4 + 3000 * tmp5 + val * tmp6) - 1000; -+ level /= 1000; -+ } -+ return level; -+} ++ return 0; ++} ++*/ ++ ++static s32 mt_fe_tn_get_signal_strength_tc2800(struct m88dc2800_state ++ *state) ++{ ++ s32 level = -107; ++ s32 tmp1, tmp2, tmp3, tmp4, tmp5, tmp6; ++ s32 val1, val2, val; ++ s32 result2, result3, result4, result5, result6; ++ s32 append; ++ u8 tmp; ++ s32 freq_KHz = (s32) state->tuner_freq; ++ if (state->tuner_mtt == 0xD1) { ++ _mt_fe_tn_get_reg(state, 0x61, &tmp); ++ tmp1 = tmp & 0x0f; ++ _mt_fe_tn_get_reg(state, 0x69, &tmp); ++ tmp2 = tmp & 0x0f; ++ _mt_fe_tn_get_reg(state, 0x73, &tmp); ++ tmp3 = tmp & 0x07; ++ _mt_fe_tn_get_reg(state, 0x7c, &tmp); ++ tmp4 = (tmp >> 4) & 0x0f; ++ _mt_fe_tn_get_reg(state, 0x7b, &tmp); ++ tmp5 = tmp & 0x0f; ++ _mt_fe_tn_get_reg(state, 0x7f, &tmp); ++ tmp6 = (tmp >> 5) & 0x01; ++ if (tmp1 > 6) { ++ val1 = 0; ++ if (freq_KHz <= 200000) { ++ val2 = (tmp1 - 6) * 267; ++ } else if (freq_KHz <= 600000) { ++ val2 = (tmp1 - 6) * 280; ++ } else { ++ val2 = (tmp1 - 6) * 290; ++ } ++ val = val1 + val2; ++ } else { ++ if (tmp1 == 0) { ++ val1 = -550; ++ } else { ++ val1 = 0; ++ } ++ if ((tmp1 < 4) && (freq_KHz >= 506000)) { ++ val1 = -850; ++ } ++ val2 = 0; ++ val = val1 + val2; ++ } ++ if (freq_KHz <= 95000) { ++ result2 = tmp2 * 289; ++ } else if (freq_KHz <= 155000) { ++ result2 = tmp2 * 278; ++ } else if (freq_KHz <= 245000) { ++ result2 = tmp2 * 267; ++ } else if (freq_KHz <= 305000) { ++ result2 = tmp2 * 256; ++ } else if (freq_KHz <= 335000) { ++ result2 = tmp2 * 244; ++ } else if (freq_KHz <= 425000) { ++ result2 = tmp2 * 233; ++ } else if (freq_KHz <= 575000) { ++ result2 = tmp2 * 222; ++ } else if (freq_KHz <= 665000) { ++ result2 = tmp2 * 211; ++ } else { ++ result2 = tmp2 * 200; ++ } ++ result3 = (6 - tmp3) * 100; ++ result4 = 300 * tmp4; ++ result5 = 50 * tmp5; ++ result6 = 300 * tmp6; ++ if (freq_KHz < 105000) { ++ append = -450; ++ } else if (freq_KHz <= 227000) { ++ append = -4 * (freq_KHz / 1000 - 100) + 150; ++ } else if (freq_KHz <= 305000) { ++ append = -4 * (freq_KHz / 1000 - 100); ++ } else if (freq_KHz <= 419000) { ++ append = 500 - 40 * (freq_KHz / 1000 - 300) / 17 + 130; ++ } else if (freq_KHz <= 640000) { ++ append = 500 - 40 * (freq_KHz / 1000 - 300) / 17; ++ } else { ++ append = -500; ++ } ++ level = append - (val + result2 + result3 + result4 + ++ result5 + result6); ++ level /= 100; ++ } else if (state->tuner_mtt == 0xE1) { ++ _mt_fe_tn_get_reg(state, 0x61, &tmp); ++ tmp1 = tmp & 0x0f; ++ _mt_fe_tn_get_reg(state, 0x84, &tmp); ++ tmp2 = tmp & 0x1f; ++ _mt_fe_tn_get_reg(state, 0x69, &tmp); ++ tmp3 = tmp & 0x03; ++ _mt_fe_tn_get_reg(state, 0x73, &tmp); ++ tmp4 = tmp & 0x0f; ++ _mt_fe_tn_get_reg(state, 0x7c, &tmp); ++ tmp5 = (tmp >> 4) & 0x0f; ++ _mt_fe_tn_get_reg(state, 0x7b, &tmp); ++ tmp6 = tmp & 0x0f; ++ if (freq_KHz < 151000) { ++ result2 = (1150 - freq_KHz / 100) * 163 / 33 + 4230; ++ result3 = (1150 - freq_KHz / 100) * 115 / 33 + 1850; ++ result4 = -3676 * (freq_KHz / 1000) / 100 + 6115; ++ } else if (freq_KHz < 257000) { ++ result2 = (1540 - freq_KHz / 100) * 11 / 4 + 3870; ++ result3 = (1540 - freq_KHz / 100) * 205 / 96 + 2100; ++ result4 = -21 * freq_KHz / 1000 + 5084; ++ } else if (freq_KHz < 305000) { ++ result2 = (2620 - freq_KHz / 100) * 5 / 3 + 2770; ++ result3 = (2620 - freq_KHz / 100) * 10 / 7 + 1700; ++ result4 = 650; ++ } else if (freq_KHz < 449000) { ++ result2 = (307 - freq_KHz / 1000) * 82 / 27 + 11270; ++ result3 = (3100 - freq_KHz / 100) * 5 / 3 + 10000; ++ result4 = 134 * freq_KHz / 10000 + 11875; ++ } else { ++ result2 = (307 - freq_KHz / 1000) * 82 / 27 + 11270; ++ result3 = 8400; ++ result4 = 5300; ++ } ++ if (tmp1 > 6) { ++ val1 = result2; ++ val2 = 2900; ++ val = 500; ++ } else if (tmp1 > 0) { ++ val1 = result3; ++ val2 = 2700; ++ val = 500; ++ } else { ++ val1 = result4; ++ val2 = 2700; ++ val = 400; ++ } ++ level = val1 - (val2 * tmp1 + 500 * tmp2 + 3000 * tmp3 - ++ 500 * tmp4 + 3000 * tmp5 + val * tmp6) - 1000; ++ level /= 1000; ++ } ++ return level; ++} ++ + +/* m88dc2800 operation functions */ -+u8 M88DC2000GetLock(struct m88dc2800_state *state) -+{ -+ u8 u8ret = 0; -+ -+ if (ReadReg(state, 0x80) < 0x06) { -+ if ((ReadReg(state, 0xdf)&0x80)==0x80 -+ && (ReadReg(state, 0x91)&0x23)==0x03 -+ && (ReadReg(state, 0x43)&0x08)==0x08) -+ u8ret = 1; -+ else -+ u8ret = 0; -+ } else { -+ if ((ReadReg(state, 0x85)&0x08)==0x08) -+ u8ret = 1; -+ else -+ u8ret = 0; -+ } -+ printk("%s, lock=%d\n", __func__,u8ret); -+ return u8ret; -+} -+ -+static int M88DC2000SetTsType(struct m88dc2800_state *state, u8 type) -+{ -+ u8 regC2H; -+ -+ if (type == 3) { -+ WriteReg(state, 0x84, 0x6A); -+ WriteReg(state, 0xC0, 0x43); -+ WriteReg(state, 0xE2, 0x06); -+ regC2H = ReadReg(state, 0xC2); -+ regC2H &= 0xC0; -+ regC2H |= 0x1B; -+ WriteReg(state, 0xC2, regC2H); -+ WriteReg(state, 0xC1, 0x60); /* common interface */ -+ } else if (type == 1) { -+ WriteReg(state, 0x84, 0x6A); -+ WriteReg(state, 0xC0, 0x47); /* serial format */ -+ WriteReg(state, 0xE2, 0x02); -+ regC2H = ReadReg(state, 0xC2); -+ regC2H &= 0xC7; -+ WriteReg(state, 0xC2, regC2H); -+ WriteReg(state, 0xC1, 0x00); -+ } else { -+ WriteReg(state, 0x84, 0x6C); -+ WriteReg(state, 0xC0, 0x43); /* parallel format */ -+ WriteReg(state, 0xE2, 0x06); -+ regC2H = ReadReg(state, 0xC2); -+ regC2H &= 0xC7; -+ WriteReg(state, 0xC2, regC2H); -+ WriteReg(state, 0xC1, 0x00); ++u8 M88DC2000GetLock(struct m88dc2800_state * state) ++{ ++ u8 u8ret = 0; ++ if (ReadReg(state, 0x80) < 0x06) { ++ if ((ReadReg(state, 0xdf) & 0x80) == 0x80 ++ &&(ReadReg(state, 0x91) & 0x23) == 0x03 ++ &&(ReadReg(state, 0x43) & 0x08) == 0x08) ++ u8ret = 1; ++ else ++ u8ret = 0; ++ } else { ++ if ((ReadReg(state, 0x85) & 0x08) == 0x08) ++ u8ret = 1; ++ else ++ u8ret = 0; + } -+ return 0; ++ dprintk("%s, lock=%d\n", __func__, u8ret); ++ return u8ret; +} + -+static int M88DC2000RegInitial_TC2800(struct m88dc2800_state *state) -+{ -+ u8 RegE3H, RegE4H; -+ -+ WriteReg(state, 0x00, 0x48); -+ WriteReg(state, 0x01, 0x09); -+ WriteReg(state, 0xFB, 0x0A); -+ WriteReg(state, 0xFC, 0x0B); -+ WriteReg(state, 0x02, 0x0B); -+ WriteReg(state, 0x03, 0x18); -+ WriteReg(state, 0x05, 0x0D); -+ WriteReg(state, 0x36, 0x80); -+ WriteReg(state, 0x43, 0x40); -+ WriteReg(state, 0x55, 0x7A); -+ WriteReg(state, 0x56, 0xD9); -+ WriteReg(state, 0x57, 0xDF); -+ WriteReg(state, 0x58, 0x39); -+ WriteReg(state, 0x5A, 0x00); -+ WriteReg(state, 0x5C, 0x71); -+ WriteReg(state, 0x5D, 0x23); -+ WriteReg(state, 0x86, 0x40); -+ WriteReg(state, 0xF9, 0x08); -+ WriteReg(state, 0x61, 0x40); -+ WriteReg(state, 0x62, 0x0A); -+ WriteReg(state, 0x90, 0x06); -+ WriteReg(state, 0xDE, 0x00); -+ WriteReg(state, 0xA0, 0x03); -+ WriteReg(state, 0xDF, 0x81); -+ WriteReg(state, 0xFA, 0x40); -+ WriteReg(state, 0x37, 0x10); -+ WriteReg(state, 0xF0, 0x40); -+ WriteReg(state, 0xF2, 0x9C); -+ WriteReg(state, 0xF3, 0x40); -+ -+ RegE3H = ReadReg(state, 0xE3); -+ RegE4H = ReadReg(state, 0xE4); -+ if (((RegE3H & 0xC0) == 0x00) && ((RegE4H & 0xC0) == 0x00)) { -+ WriteReg(state, 0x30, 0xFF); -+ WriteReg(state, 0x31, 0x00); -+ WriteReg(state, 0x32, 0x00); -+ WriteReg(state, 0x33, 0x00); -+ WriteReg(state, 0x35, 0x32); -+ WriteReg(state, 0x40, 0x00); -+ WriteReg(state, 0x41, 0x10); -+ WriteReg(state, 0xF1, 0x02); -+ WriteReg(state, 0xF4, 0x04); -+ WriteReg(state, 0xF5, 0x00); -+ WriteReg(state, 0x42, 0x14); -+ WriteReg(state, 0xE1, 0x25); -+ } else if (((RegE3H & 0xC0) == 0x80) && ((RegE4H & 0xC0) == 0x40)) { -+ WriteReg(state, 0x30, 0xFF); -+ WriteReg(state, 0x31, 0x00); -+ WriteReg(state, 0x32, 0x00); -+ WriteReg(state, 0x33, 0x00); -+ WriteReg(state, 0x35, 0x32); -+ WriteReg(state, 0x39, 0x00); -+ WriteReg(state, 0x3A, 0x00); -+ WriteReg(state, 0x40, 0x00); -+ WriteReg(state, 0x41, 0x10); -+ WriteReg(state, 0xF1, 0x00); -+ WriteReg(state, 0xF4, 0x00); -+ WriteReg(state, 0xF5, 0x40); -+ WriteReg(state, 0x42, 0x14); -+ WriteReg(state, 0xE1, 0x25); -+ } else if ((RegE3H == 0x80 || RegE3H == 0x81) && (RegE4H == 0x80 || RegE4H == 0x81)) { -+ WriteReg(state, 0x30, 0xFF); -+ WriteReg(state, 0x31, 0x00); -+ WriteReg(state, 0x32, 0x00); -+ WriteReg(state, 0x33, 0x00); -+ WriteReg(state, 0x35, 0x32); -+ WriteReg(state, 0x39, 0x00); -+ WriteReg(state, 0x3A, 0x00); -+ WriteReg(state, 0xF1, 0x00); -+ WriteReg(state, 0xF4, 0x00); -+ WriteReg(state, 0xF5, 0x40); -+ WriteReg(state, 0x42, 0x24); -+ WriteReg(state, 0xE1, 0x25); -+ -+ WriteReg(state, 0x92, 0x7F); -+ WriteReg(state, 0x93, 0x91); -+ WriteReg(state, 0x95, 0x00); -+ WriteReg(state, 0x2B, 0x33); -+ WriteReg(state, 0x2A, 0x2A); -+ WriteReg(state, 0x2E, 0x80); -+ WriteReg(state, 0x25, 0x25); -+ WriteReg(state, 0x2D, 0xFF); -+ WriteReg(state, 0x26, 0xFF); -+ WriteReg(state, 0x27, 0x00); -+ WriteReg(state, 0x24, 0x25); -+ WriteReg(state, 0xA4, 0xFF); -+ WriteReg(state, 0xA3, 0x0D); -+ } else { -+ WriteReg(state, 0x30, 0xFF); -+ WriteReg(state, 0x31, 0x00); -+ WriteReg(state, 0x32, 0x00); -+ WriteReg(state, 0x33, 0x00); -+ WriteReg(state, 0x35, 0x32); -+ WriteReg(state, 0x39, 0x00); -+ WriteReg(state, 0x3A, 0x00); -+ WriteReg(state, 0xF1, 0x00); -+ WriteReg(state, 0xF4, 0x00); -+ WriteReg(state, 0xF5, 0x40); -+ WriteReg(state, 0x42, 0x24); -+ WriteReg(state, 0xE1, 0x27); -+ -+ WriteReg(state, 0x92, 0x7F); -+ WriteReg(state, 0x93, 0x91); -+ WriteReg(state, 0x95, 0x00); -+ WriteReg(state, 0x2B, 0x33); -+ WriteReg(state, 0x2A, 0x2A); -+ WriteReg(state, 0x2E, 0x80); -+ WriteReg(state, 0x25, 0x25); -+ WriteReg(state, 0x2D, 0xFF); -+ WriteReg(state, 0x26, 0xFF); -+ WriteReg(state, 0x27, 0x00); -+ WriteReg(state, 0x24, 0x25); -+ WriteReg(state, 0xA4, 0xFF); -+ WriteReg(state, 0xA3, 0x10); -+ } -+ -+ WriteReg(state, 0xF6, 0x4E); -+ WriteReg(state, 0xF7, 0x20); -+ WriteReg(state, 0x89, 0x02); -+ WriteReg(state, 0x14, 0x08); -+ WriteReg(state, 0x6F, 0x0D); -+ WriteReg(state, 0x10, 0xFF); -+ WriteReg(state, 0x11, 0x00); -+ WriteReg(state, 0x12, 0x30); -+ WriteReg(state, 0x13, 0x23); -+ WriteReg(state, 0x60, 0x00); -+ WriteReg(state, 0x69, 0x00); -+ WriteReg(state, 0x6A, 0x03); -+ WriteReg(state, 0xE0, 0x75); -+ WriteReg(state, 0x8D, 0x29); -+ WriteReg(state, 0x4E, 0xD8); -+ WriteReg(state, 0x88, 0x80); -+ WriteReg(state, 0x52, 0x79); -+ WriteReg(state, 0x53, 0x03); -+ WriteReg(state, 0x59, 0x30); -+ WriteReg(state, 0x5E, 0x02); -+ WriteReg(state, 0x5F, 0x0F); -+ WriteReg(state, 0x71, 0x03); -+ WriteReg(state, 0x72, 0x12); ++static int M88DC2000SetTsType(struct m88dc2800_state *state, u8 type) ++{ ++ u8 regC2H; ++ ++ if (type == 3) { ++ WriteReg(state, 0x84, 0x6A); ++ WriteReg(state, 0xC0, 0x43); ++ WriteReg(state, 0xE2, 0x06); ++ regC2H = ReadReg(state, 0xC2); ++ regC2H &= 0xC0; ++ regC2H |= 0x1B; ++ WriteReg(state, 0xC2, regC2H); ++ WriteReg(state, 0xC1, 0x60); /* common interface */ ++ } else if (type == 1) { ++ WriteReg(state, 0x84, 0x6A); ++ WriteReg(state, 0xC0, 0x47); /* serial format */ ++ WriteReg(state, 0xE2, 0x02); ++ regC2H = ReadReg(state, 0xC2); ++ regC2H &= 0xC7; ++ WriteReg(state, 0xC2, regC2H); ++ WriteReg(state, 0xC1, 0x00); ++ } else { ++ WriteReg(state, 0x84, 0x6C); ++ WriteReg(state, 0xC0, 0x43); /* parallel format */ ++ WriteReg(state, 0xE2, 0x06); ++ regC2H = ReadReg(state, 0xC2); ++ regC2H &= 0xC7; ++ WriteReg(state, 0xC2, regC2H); ++ WriteReg(state, 0xC1, 0x00); ++ } ++ return 0; ++} ++ ++static int M88DC2000RegInitial_TC2800(struct m88dc2800_state *state) ++{ ++ u8 RegE3H, RegE4H; ++ ++ WriteReg(state, 0x00, 0x48); ++ WriteReg(state, 0x01, 0x09); ++ WriteReg(state, 0xFB, 0x0A); ++ WriteReg(state, 0xFC, 0x0B); ++ WriteReg(state, 0x02, 0x0B); ++ WriteReg(state, 0x03, 0x18); ++ WriteReg(state, 0x05, 0x0D); ++ WriteReg(state, 0x36, 0x80); ++ WriteReg(state, 0x43, 0x40); ++ WriteReg(state, 0x55, 0x7A); ++ WriteReg(state, 0x56, 0xD9); ++ WriteReg(state, 0x57, 0xDF); ++ WriteReg(state, 0x58, 0x39); ++ WriteReg(state, 0x5A, 0x00); ++ WriteReg(state, 0x5C, 0x71); ++ WriteReg(state, 0x5D, 0x23); ++ WriteReg(state, 0x86, 0x40); ++ WriteReg(state, 0xF9, 0x08); ++ WriteReg(state, 0x61, 0x40); ++ WriteReg(state, 0x62, 0x0A); ++ WriteReg(state, 0x90, 0x06); ++ WriteReg(state, 0xDE, 0x00); ++ WriteReg(state, 0xA0, 0x03); ++ WriteReg(state, 0xDF, 0x81); ++ WriteReg(state, 0xFA, 0x40); ++ WriteReg(state, 0x37, 0x10); ++ WriteReg(state, 0xF0, 0x40); ++ WriteReg(state, 0xF2, 0x9C); ++ WriteReg(state, 0xF3, 0x40); ++ RegE3H = ReadReg(state, 0xE3); ++ RegE4H = ReadReg(state, 0xE4); ++ if (((RegE3H & 0xC0) == 0x00) && ((RegE4H & 0xC0) == 0x00)) { ++ WriteReg(state, 0x30, 0xFF); ++ WriteReg(state, 0x31, 0x00); ++ WriteReg(state, 0x32, 0x00); ++ WriteReg(state, 0x33, 0x00); ++ WriteReg(state, 0x35, 0x32); ++ WriteReg(state, 0x40, 0x00); ++ WriteReg(state, 0x41, 0x10); ++ WriteReg(state, 0xF1, 0x02); ++ WriteReg(state, 0xF4, 0x04); ++ WriteReg(state, 0xF5, 0x00); ++ WriteReg(state, 0x42, 0x14); ++ WriteReg(state, 0xE1, 0x25); ++ } else if (((RegE3H & 0xC0) == 0x80) && ((RegE4H & 0xC0) == 0x40)) { ++ WriteReg(state, 0x30, 0xFF); ++ WriteReg(state, 0x31, 0x00); ++ WriteReg(state, 0x32, 0x00); ++ WriteReg(state, 0x33, 0x00); ++ WriteReg(state, 0x35, 0x32); ++ WriteReg(state, 0x39, 0x00); ++ WriteReg(state, 0x3A, 0x00); ++ WriteReg(state, 0x40, 0x00); ++ WriteReg(state, 0x41, 0x10); ++ WriteReg(state, 0xF1, 0x00); ++ WriteReg(state, 0xF4, 0x00); ++ WriteReg(state, 0xF5, 0x40); ++ WriteReg(state, 0x42, 0x14); ++ WriteReg(state, 0xE1, 0x25); ++ } else if ((RegE3H == 0x80 || RegE3H == 0x81) ++ && (RegE4H == 0x80 || RegE4H == 0x81)) { ++ WriteReg(state, 0x30, 0xFF); ++ WriteReg(state, 0x31, 0x00); ++ WriteReg(state, 0x32, 0x00); ++ WriteReg(state, 0x33, 0x00); ++ WriteReg(state, 0x35, 0x32); ++ WriteReg(state, 0x39, 0x00); ++ WriteReg(state, 0x3A, 0x00); ++ WriteReg(state, 0xF1, 0x00); ++ WriteReg(state, 0xF4, 0x00); ++ WriteReg(state, 0xF5, 0x40); ++ WriteReg(state, 0x42, 0x24); ++ WriteReg(state, 0xE1, 0x25); ++ WriteReg(state, 0x92, 0x7F); ++ WriteReg(state, 0x93, 0x91); ++ WriteReg(state, 0x95, 0x00); ++ WriteReg(state, 0x2B, 0x33); ++ WriteReg(state, 0x2A, 0x2A); ++ WriteReg(state, 0x2E, 0x80); ++ WriteReg(state, 0x25, 0x25); ++ WriteReg(state, 0x2D, 0xFF); ++ WriteReg(state, 0x26, 0xFF); ++ WriteReg(state, 0x27, 0x00); ++ WriteReg(state, 0x24, 0x25); ++ WriteReg(state, 0xA4, 0xFF); ++ WriteReg(state, 0xA3, 0x0D); ++ } else { ++ WriteReg(state, 0x30, 0xFF); ++ WriteReg(state, 0x31, 0x00); ++ WriteReg(state, 0x32, 0x00); ++ WriteReg(state, 0x33, 0x00); ++ WriteReg(state, 0x35, 0x32); ++ WriteReg(state, 0x39, 0x00); ++ WriteReg(state, 0x3A, 0x00); ++ WriteReg(state, 0xF1, 0x00); ++ WriteReg(state, 0xF4, 0x00); ++ WriteReg(state, 0xF5, 0x40); ++ WriteReg(state, 0x42, 0x24); ++ WriteReg(state, 0xE1, 0x27); ++ WriteReg(state, 0x92, 0x7F); ++ WriteReg(state, 0x93, 0x91); ++ WriteReg(state, 0x95, 0x00); ++ WriteReg(state, 0x2B, 0x33); ++ WriteReg(state, 0x2A, 0x2A); ++ WriteReg(state, 0x2E, 0x80); ++ WriteReg(state, 0x25, 0x25); ++ WriteReg(state, 0x2D, 0xFF); ++ WriteReg(state, 0x26, 0xFF); ++ WriteReg(state, 0x27, 0x00); ++ WriteReg(state, 0x24, 0x25); ++ WriteReg(state, 0xA4, 0xFF); ++ WriteReg(state, 0xA3, 0x10); ++ } ++ WriteReg(state, 0xF6, 0x4E); ++ WriteReg(state, 0xF7, 0x20); ++ WriteReg(state, 0x89, 0x02); ++ WriteReg(state, 0x14, 0x08); ++ WriteReg(state, 0x6F, 0x0D); ++ WriteReg(state, 0x10, 0xFF); ++ WriteReg(state, 0x11, 0x00); ++ WriteReg(state, 0x12, 0x30); ++ WriteReg(state, 0x13, 0x23); ++ WriteReg(state, 0x60, 0x00); ++ WriteReg(state, 0x69, 0x00); ++ WriteReg(state, 0x6A, 0x03); ++ WriteReg(state, 0xE0, 0x75); ++ WriteReg(state, 0x8D, 0x29); ++ WriteReg(state, 0x4E, 0xD8); ++ WriteReg(state, 0x88, 0x80); ++ WriteReg(state, 0x52, 0x79); ++ WriteReg(state, 0x53, 0x03); ++ WriteReg(state, 0x59, 0x30); ++ WriteReg(state, 0x5E, 0x02); ++ WriteReg(state, 0x5F, 0x0F); ++ WriteReg(state, 0x71, 0x03); ++ WriteReg(state, 0x72, 0x12); + WriteReg(state, 0x73, 0x12); -+ -+ return 0; ++ ++ return 0; +} + -+static int M88DC2000AutoTSClock_P(struct m88dc2800_state *state, u32 sym, u16 qam) -+{ -+ u32 dataRate; ++static int M88DC2000AutoTSClock_P(struct m88dc2800_state *state, u32 sym, ++ u16 qam) ++{ ++ u32 dataRate; + u8 clk_div, value; -+ printk("m88dc2800: M88DC2000AutoTSClock_P, symrate=%d qam=%d\n",sym,qam); -+ switch(qam) -+ { -+ case 16: -+ dataRate = 4; -+ break; -+ case 32: -+ dataRate = 5; -+ break; -+ case 128: -+ dataRate = 7; -+ break; -+ case 256: -+ dataRate = 8; -+ break; -+ case 64: -+ default: -+ dataRate = 6; -+ break; -+ } -+ dataRate *= sym * 105; -+ dataRate /= 800; -+ -+ if(dataRate <= 4115) -+ clk_div = 0x05; -+ else if(dataRate <= 4800) -+ clk_div = 0x04; -+ else if(dataRate <= 5760) -+ clk_div = 0x03; -+ else if(dataRate <= 7200) -+ clk_div = 0x02; -+ else if(dataRate <= 9600) -+ clk_div = 0x01; -+ else -+ clk_div = 0x00; -+ -+ value = ReadReg(state, 0xC2); -+ value &= 0xc0; -+ value |= clk_div; -+ WriteReg(state, 0xC2, value); -+ return 0; -+} -+ -+static int M88DC2000AutoTSClock_C(struct m88dc2800_state *state, u32 sym, u16 qam) -+{ -+ u32 dataRate; -+ u8 clk_div, value; -+ printk("m88dc2800: M88DC2000AutoTSClock_C, symrate=%d qam=%d\n",sym,qam); -+ switch(qam) -+ { -+ case 16: -+ dataRate = 4; -+ break; -+ case 32: -+ dataRate = 5; -+ break; -+ case 128: -+ dataRate = 7; -+ break; -+ case 256: -+ dataRate = 8; -+ break; -+ case 64: -+ default: -+ dataRate = 6; -+ break; -+ } -+ dataRate *= sym * 105; -+ dataRate /= 800; -+ -+ if(dataRate <= 4115) -+ clk_div = 0x3F; -+ else if(dataRate <= 4800) -+ clk_div = 0x36; -+ else if(dataRate <= 5760) -+ clk_div = 0x2D; -+ else if(dataRate <= 7200) -+ clk_div = 0x24; -+ else if(dataRate <= 9600) -+ clk_div = 0x1B; -+ else -+ clk_div = 0x12; -+ -+ value = ReadReg(state, 0xC2); -+ value &= 0xc0; -+ value |= clk_div; -+ WriteReg(state, 0xC2, value); -+ return 0; -+} -+ -+static int M88DC2000SetTxMode(struct m88dc2800_state *state, u8 inverted, u8 j83) -+{ -+ u8 value = 0; -+ if (inverted) -+ value |= 0x08; /* spectrum inverted */ -+ if (j83) -+ value |= 0x01; /* J83C */ -+ WriteReg(state, 0x83, value); -+ return 0; -+} -+ -+static int M88DC2000SoftReset(struct m88dc2800_state *state) -+{ -+ WriteReg(state, 0x80, 0x01); -+ WriteReg(state, 0x82, 0x00); -+ msleep(1); -+ WriteReg(state, 0x80, 0x00); -+ return 0; -+} -+ -+static int M88DC2000SetSym(struct m88dc2800_state *state, u32 sym, u32 xtal) -+{ -+ u8 value; -+ u8 reg6FH, reg12H; -+ u64 fValue; -+ u32 dwValue; -+ printk("%s, sym=%d, xtal=%d\n", __func__, sym, xtal); -+ -+ fValue = 4294967296 * (sym + 10); -+ do_div(fValue, xtal); -+/* fValue = 4294967296 * (sym + 10) / xtal; */ -+ -+ dwValue = (u32)fValue; -+ printk("%s, fvalue1=%x\n", __func__, dwValue); -+ -+ WriteReg(state, 0x58, (u8)((dwValue >> 24) & 0xff)); -+ WriteReg(state, 0x57, (u8)((dwValue >> 16) & 0xff)); -+ WriteReg(state, 0x56, (u8)((dwValue >> 8) & 0xff)); -+ WriteReg(state, 0x55, (u8)((dwValue >> 0) & 0xff)); -+ -+/* fValue = 2048 * xtal / sym; */ -+ fValue = 2048 * xtal; -+ do_div(fValue, sym); -+ -+ dwValue = (u32)fValue; -+ printk("%s, fvalue2=%x\n", __func__, dwValue); -+ WriteReg(state, 0x5D, (u8)((dwValue >> 8) & 0xff)); -+ WriteReg(state, 0x5C, (u8)((dwValue >> 0) & 0xff)); -+ -+ value = ReadReg(state, 0x5A); -+ if (((dwValue >> 16) & 0x0001) == 0) -+ value &= 0x7F; -+ else -+ value |= 0x80; -+ WriteReg(state, 0x5A, value); -+ -+ value = ReadReg(state, 0x89); -+ if (sym <= 1800) -+ value |= 0x01; -+ else -+ value &= 0xFE; -+ WriteReg(state, 0x89, value); -+ -+ if (sym >= 6700){ -+ reg6FH = 0x0D; -+ reg12H = 0x30; -+ } else if (sym >= 4000) { -+ fValue = 22 * 4096 / sym; -+ reg6FH = (u8)fValue; -+ reg12H = 0x30; -+ } else if (sym >= 2000) { -+ fValue = 14 * 4096 / sym; -+ reg6FH = (u8)fValue; -+ reg12H = 0x20; -+ } else { -+ fValue = 7 * 4096 / sym; -+ reg6FH = (u8)fValue; -+ reg12H = 0x10; -+ } -+ WriteReg(state, 0x6F, reg6FH); -+ WriteReg(state, 0x12, reg12H); -+ -+ if (((ReadReg(state, 0xE3) & 0x80) == 0x80) && ((ReadReg(state, 0xE4) & 0x80) == 0x80)) { -+ if(sym < 3000) { -+ WriteReg(state, 0x6C, 0x16); -+ WriteReg(state, 0x6D, 0x10); -+ WriteReg(state, 0x6E, 0x18); -+ } else { -+ WriteReg(state, 0x6C, 0x14); -+ WriteReg(state, 0x6D, 0x0E); -+ WriteReg(state, 0x6E, 0x36); -+ } -+ } else { -+ WriteReg(state, 0x6C, 0x16); -+ WriteReg(state, 0x6D, 0x10); -+ WriteReg(state, 0x6E, 0x18); ++ printk(KERN_INFO ++ "m88dc2800: M88DC2000AutoTSClock_P, symrate=%d qam=%d\n", ++ sym, qam); ++ switch (qam) { ++ case 16: ++ dataRate = 4; ++ break; ++ case 32: ++ dataRate = 5; ++ break; ++ case 128: ++ dataRate = 7; ++ break; ++ case 256: ++ dataRate = 8; ++ break; ++ case 64: ++ default: ++ dataRate = 6; ++ break; + } -+ return 0; ++ dataRate *= sym * 105; ++ dataRate /= 800; ++ if (dataRate <= 4115) ++ clk_div = 0x05; ++ else if (dataRate <= 4800) ++ clk_div = 0x04; ++ else if (dataRate <= 5760) ++ clk_div = 0x03; ++ else if (dataRate <= 7200) ++ clk_div = 0x02; ++ else if (dataRate <= 9600) ++ clk_div = 0x01; ++ else ++ clk_div = 0x00; ++ value = ReadReg(state, 0xC2); ++ value &= 0xc0; ++ value |= clk_div; ++ WriteReg(state, 0xC2, value); ++ return 0; +} + -+static int M88DC2000SetQAM(struct m88dc2800_state *state, u16 qam) -+{ -+ u8 reg00H, reg4AH, regC2H, reg44H, reg4CH, reg4DH, reg74H, value; -+ u8 reg8BH, reg8EH; -+ printk("%s, qam=%d\n", __func__, qam); -+ regC2H = ReadReg(state, 0xC2); -+ regC2H &= 0xF8; -+ switch(qam){ -+ case 16: /* 16 QAM */ -+ reg00H = 0x08; -+ reg4AH = 0x0F; -+ regC2H |= 0x02; -+ reg44H = 0xAA; -+ reg4CH = 0x0C; -+ reg4DH = 0xF7; -+ reg74H = 0x0E; -+ if(((ReadReg(state, 0xE3) & 0x80) == 0x80) && ((ReadReg(state, 0xE4) & 0x80) == 0x80)) { -+ reg8BH = 0x5A; -+ reg8EH = 0xBD; -+ } else { -+ reg8BH = 0x5B; -+ reg8EH = 0x9D; -+ } -+ WriteReg(state, 0x6E, 0x18); -+ break; -+ case 32: /* 32 QAM */ -+ reg00H = 0x18; -+ reg4AH = 0xFB; -+ regC2H |= 0x02; -+ reg44H = 0xAA; -+ reg4CH = 0x0C; -+ reg4DH = 0xF7; -+ reg74H = 0x0E; -+ if(((ReadReg(state, 0xE3) & 0x80) == 0x80) && ((ReadReg(state, 0xE4) & 0x80) == 0x80)) { -+ reg8BH = 0x5A; -+ reg8EH = 0xBD; -+ } else { -+ reg8BH = 0x5B; -+ reg8EH = 0x9D; -+ } -+ WriteReg(state, 0x6E, 0x18); -+ break; -+ case 64: /* 64 QAM */ -+ reg00H = 0x48; -+ reg4AH = 0xCD; -+ regC2H |= 0x02; -+ reg44H = 0xAA; -+ reg4CH = 0x0C; -+ reg4DH = 0xF7; -+ reg74H = 0x0E; -+ if(((ReadReg(state, 0xE3) & 0x80) == 0x80) && ((ReadReg(state, 0xE4) & 0x80) == 0x80)) { -+ reg8BH = 0x5A; -+ reg8EH = 0xBD; -+ } else { -+ reg8BH = 0x5B; -+ reg8EH = 0x9D; -+ } -+ break; -+ case 128: /* 128 QAM */ -+ reg00H = 0x28; -+ reg4AH = 0xFF; -+ regC2H |= 0x02; -+ reg44H = 0xA9; -+ reg4CH = 0x08; -+ reg4DH = 0xF5; -+ reg74H = 0x0E; -+ reg8BH = 0x5B; -+ reg8EH = 0x9D; -+ break; -+ case 256: /* 256 QAM */ -+ reg00H = 0x38; -+ reg4AH = 0xCD; -+ if(((ReadReg(state, 0xE3) & 0x80) == 0x80) && ((ReadReg(state, 0xE4) & 0x80) == 0x80)) { -+ regC2H |= 0x02; -+ } else { -+ regC2H |= 0x01; -+ } -+ reg44H = 0xA9; -+ reg4CH = 0x08; -+ reg4DH = 0xF5; -+ reg74H = 0x0E; -+ reg8BH = 0x5B; -+ reg8EH = 0x9D; -+ break; -+ default: /* 64 QAM */ -+ reg00H = 0x48; -+ reg4AH = 0xCD; -+ regC2H |= 0x02; -+ reg44H = 0xAA; -+ reg4CH = 0x0C; -+ reg4DH = 0xF7; -+ reg74H = 0x0E; -+ if(((ReadReg(state, 0xE3) & 0x80) == 0x80) && ((ReadReg(state, 0xE4) & 0x80) == 0x80)) { -+ reg8BH = 0x5A; -+ reg8EH = 0xBD; -+ } else { -+ reg8BH = 0x5B; -+ reg8EH = 0x9D; -+ } -+ break; -+ } -+ WriteReg(state, 0x00, reg00H); -+ -+ value = ReadReg(state, 0x88); -+ value |= 0x08; -+ WriteReg(state, 0x88, value); -+ WriteReg(state, 0x4B, 0xFF); -+ WriteReg(state, 0x4A, reg4AH); -+ value &= 0xF7; -+ WriteReg(state, 0x88, value); -+ -+ WriteReg(state, 0xC2, regC2H); -+ WriteReg(state, 0x44, reg44H); -+ WriteReg(state, 0x4C, reg4CH); -+ WriteReg(state, 0x4D, reg4DH); -+ WriteReg(state, 0x74, reg74H); -+ WriteReg(state, 0x8B, reg8BH); ++static int M88DC2000AutoTSClock_C(struct m88dc2800_state *state, u32 sym, ++ u16 qam) ++{ ++ u32 dataRate; ++ u8 clk_div, value; ++ printk(KERN_INFO ++ "m88dc2800: M88DC2000AutoTSClock_C, symrate=%d qam=%d\n", ++ sym, qam); ++ switch (qam) { ++ case 16: ++ dataRate = 4; ++ break; ++ case 32: ++ dataRate = 5; ++ break; ++ case 128: ++ dataRate = 7; ++ break; ++ case 256: ++ dataRate = 8; ++ break; ++ case 64: ++ default: ++ dataRate = 6; ++ break; ++ } ++ dataRate *= sym * 105; ++ dataRate /= 800; ++ if (dataRate <= 4115) ++ clk_div = 0x3F; ++ else if (dataRate <= 4800) ++ clk_div = 0x36; ++ else if (dataRate <= 5760) ++ clk_div = 0x2D; ++ else if (dataRate <= 7200) ++ clk_div = 0x24; ++ else if (dataRate <= 9600) ++ clk_div = 0x1B; ++ else ++ clk_div = 0x12; ++ value = ReadReg(state, 0xC2); ++ value &= 0xc0; ++ value |= clk_div; ++ WriteReg(state, 0xC2, value); ++ return 0; ++} ++ ++static int M88DC2000SetTxMode(struct m88dc2800_state *state, u8 inverted, ++ u8 j83) ++{ ++ u8 value = 0; ++ if (inverted) ++ value |= 0x08; /* spectrum inverted */ ++ if (j83) ++ value |= 0x01; /* J83C */ ++ WriteReg(state, 0x83, value); ++ return 0; ++} ++ ++static int M88DC2000SoftReset(struct m88dc2800_state *state) ++{ ++ WriteReg(state, 0x80, 0x01); ++ WriteReg(state, 0x82, 0x00); ++ msleep(1); ++ WriteReg(state, 0x80, 0x00); ++ return 0; ++} ++ ++static int M88DC2000SetSym(struct m88dc2800_state *state, u32 sym, u32 xtal) ++{ ++ u8 value; ++ u8 reg6FH, reg12H; ++ u64 fValue; ++ u32 dwValue; ++ ++ printk(KERN_INFO "%s, sym=%d, xtal=%d\n", __func__, sym, xtal); ++ fValue = 4294967296 * (sym + 10); ++ do_div(fValue, xtal); ++ ++ /* fValue = 4294967296 * (sym + 10) / xtal; */ ++ dwValue = (u32) fValue; ++ printk(KERN_INFO "%s, fvalue1=%x\n", __func__, dwValue); ++ WriteReg(state, 0x58, (u8) ((dwValue >> 24) & 0xff)); ++ WriteReg(state, 0x57, (u8) ((dwValue >> 16) & 0xff)); ++ WriteReg(state, 0x56, (u8) ((dwValue >> 8) & 0xff)); ++ WriteReg(state, 0x55, (u8) ((dwValue >> 0) & 0xff)); ++ ++ /* fValue = 2048 * xtal / sym; */ ++ fValue = 2048 * xtal; ++ do_div(fValue, sym); ++ dwValue = (u32) fValue; ++ printk(KERN_INFO "%s, fvalue2=%x\n", __func__, dwValue); ++ WriteReg(state, 0x5D, (u8) ((dwValue >> 8) & 0xff)); ++ WriteReg(state, 0x5C, (u8) ((dwValue >> 0) & 0xff)); ++ value = ReadReg(state, 0x5A); ++ if (((dwValue >> 16) & 0x0001) == 0) ++ value &= 0x7F; ++ else ++ value |= 0x80; ++ WriteReg(state, 0x5A, value); ++ value = ReadReg(state, 0x89); ++ if (sym <= 1800) ++ value |= 0x01; ++ else ++ value &= 0xFE; ++ WriteReg(state, 0x89, value); ++ if (sym >= 6700) { ++ reg6FH = 0x0D; ++ reg12H = 0x30; ++ } else if (sym >= 4000) { ++ fValue = 22 * 4096 / sym; ++ reg6FH = (u8) fValue; ++ reg12H = 0x30; ++ } else if (sym >= 2000) { ++ fValue = 14 * 4096 / sym; ++ reg6FH = (u8) fValue; ++ reg12H = 0x20; ++ } else { ++ fValue = 7 * 4096 / sym; ++ reg6FH = (u8) fValue; ++ reg12H = 0x10; ++ } ++ WriteReg(state, 0x6F, reg6FH); ++ WriteReg(state, 0x12, reg12H); ++ if (((ReadReg(state, 0xE3) & 0x80) == 0x80) ++ && ((ReadReg(state, 0xE4) & 0x80) == 0x80)) { ++ if (sym < 3000) { ++ WriteReg(state, 0x6C, 0x16); ++ WriteReg(state, 0x6D, 0x10); ++ WriteReg(state, 0x6E, 0x18); ++ } else { ++ WriteReg(state, 0x6C, 0x14); ++ WriteReg(state, 0x6D, 0x0E); ++ WriteReg(state, 0x6E, 0x36); ++ } ++ } else { ++ WriteReg(state, 0x6C, 0x16); ++ WriteReg(state, 0x6D, 0x10); ++ WriteReg(state, 0x6E, 0x18); ++ } ++ return 0; ++} ++ ++static int M88DC2000SetQAM(struct m88dc2800_state *state, u16 qam) ++{ ++ u8 reg00H, reg4AH, regC2H, reg44H, reg4CH, reg4DH, reg74H, value; ++ u8 reg8BH, reg8EH; ++ printk(KERN_INFO "%s, qam=%d\n", __func__, qam); ++ regC2H = ReadReg(state, 0xC2); ++ regC2H &= 0xF8; ++ switch (qam) { ++ case 16: /* 16 QAM */ ++ reg00H = 0x08; ++ reg4AH = 0x0F; ++ regC2H |= 0x02; ++ reg44H = 0xAA; ++ reg4CH = 0x0C; ++ reg4DH = 0xF7; ++ reg74H = 0x0E; ++ if (((ReadReg(state, 0xE3) & 0x80) == 0x80) ++ && ((ReadReg(state, 0xE4) & 0x80) == 0x80)) { ++ reg8BH = 0x5A; ++ reg8EH = 0xBD; ++ } else { ++ reg8BH = 0x5B; ++ reg8EH = 0x9D; ++ } ++ WriteReg(state, 0x6E, 0x18); ++ break; ++ case 32: /* 32 QAM */ ++ reg00H = 0x18; ++ reg4AH = 0xFB; ++ regC2H |= 0x02; ++ reg44H = 0xAA; ++ reg4CH = 0x0C; ++ reg4DH = 0xF7; ++ reg74H = 0x0E; ++ if (((ReadReg(state, 0xE3) & 0x80) == 0x80) ++ && ((ReadReg(state, 0xE4) & 0x80) == 0x80)) { ++ reg8BH = 0x5A; ++ reg8EH = 0xBD; ++ } else { ++ reg8BH = 0x5B; ++ reg8EH = 0x9D; ++ } ++ WriteReg(state, 0x6E, 0x18); ++ break; ++ case 64: /* 64 QAM */ ++ reg00H = 0x48; ++ reg4AH = 0xCD; ++ regC2H |= 0x02; ++ reg44H = 0xAA; ++ reg4CH = 0x0C; ++ reg4DH = 0xF7; ++ reg74H = 0x0E; ++ if (((ReadReg(state, 0xE3) & 0x80) == 0x80) ++ && ((ReadReg(state, 0xE4) & 0x80) == 0x80)) { ++ reg8BH = 0x5A; ++ reg8EH = 0xBD; ++ } else { ++ reg8BH = 0x5B; ++ reg8EH = 0x9D; ++ } ++ break; ++ case 128: /* 128 QAM */ ++ reg00H = 0x28; ++ reg4AH = 0xFF; ++ regC2H |= 0x02; ++ reg44H = 0xA9; ++ reg4CH = 0x08; ++ reg4DH = 0xF5; ++ reg74H = 0x0E; ++ reg8BH = 0x5B; ++ reg8EH = 0x9D; ++ break; ++ case 256: /* 256 QAM */ ++ reg00H = 0x38; ++ reg4AH = 0xCD; ++ if (((ReadReg(state, 0xE3) & 0x80) == 0x80) ++ && ((ReadReg(state, 0xE4) & 0x80) == 0x80)) { ++ regC2H |= 0x02; ++ } else { ++ regC2H |= 0x01; ++ } ++ reg44H = 0xA9; ++ reg4CH = 0x08; ++ reg4DH = 0xF5; ++ reg74H = 0x0E; ++ reg8BH = 0x5B; ++ reg8EH = 0x9D; ++ break; ++ default: /* 64 QAM */ ++ reg00H = 0x48; ++ reg4AH = 0xCD; ++ regC2H |= 0x02; ++ reg44H = 0xAA; ++ reg4CH = 0x0C; ++ reg4DH = 0xF7; ++ reg74H = 0x0E; ++ if (((ReadReg(state, 0xE3) & 0x80) == 0x80) ++ && ((ReadReg(state, 0xE4) & 0x80) == 0x80)) { ++ reg8BH = 0x5A; ++ reg8EH = 0xBD; ++ } else { ++ reg8BH = 0x5B; ++ reg8EH = 0x9D; ++ } ++ break; ++ } ++ WriteReg(state, 0x00, reg00H); ++ value = ReadReg(state, 0x88); ++ value |= 0x08; ++ WriteReg(state, 0x88, value); ++ WriteReg(state, 0x4B, 0xFF); ++ WriteReg(state, 0x4A, reg4AH); ++ value &= 0xF7; ++ WriteReg(state, 0x88, value); ++ WriteReg(state, 0xC2, regC2H); ++ WriteReg(state, 0x44, reg44H); ++ WriteReg(state, 0x4C, reg4CH); ++ WriteReg(state, 0x4D, reg4DH); ++ WriteReg(state, 0x74, reg74H); ++ WriteReg(state, 0x8B, reg8BH); + WriteReg(state, 0x8E, reg8EH); -+ return 0; ++ return 0; +} + -+static int M88DC2000WriteTuner_TC2800(struct m88dc2800_state *state, u32 freq_KHz) -+{ -+ printk("%s, freq=%d KHz\n", __func__, freq_KHz); -+ return mt_fe_tn_set_freq_tc2800(state, freq_KHz); ++static int M88DC2000WriteTuner_TC2800(struct m88dc2800_state *state, ++ u32 freq_KHz) ++{ ++ printk(KERN_INFO "%s, freq=%d KHz\n", __func__, freq_KHz); ++ return mt_fe_tn_set_freq_tc2800(state, freq_KHz); +} + +static int m88dc2800_init(struct dvb_frontend *fe) @@ -2038,12 +1863,9 @@ index 0000000..f48a356 + u8 is_annex_c, is_update; + u16 temp_qam; + s32 waiting_time; -+ struct m88dc2800_state* state = fe->demodulator_priv; -+ -+ if(c->delivery_system == SYS_DVBC_ANNEX_C) -+ is_annex_c = 1; -+ else -+ is_annex_c = 0; ++ struct m88dc2800_state *state = fe->demodulator_priv; ++ ++ is_annex_c = c->delivery_system == SYS_DVBC_ANNEX_C ? 1 : 0; + + switch (c->modulation) { + case QAM_16: @@ -2054,280 +1876,290 @@ index 0000000..f48a356 + break; + case QAM_128: + temp_qam = 128; -+ break; ++ break; + case QAM_256: + temp_qam = 256; -+ break; -+ default: /* QAM_64 */ ++ break; ++ default: /* QAM_64 */ + temp_qam = 64; + break; + } -+ -+ if(c->inversion == INVERSION_ON) -+ state->inverted = 1; -+ else -+ state->inverted = 0; + -+ printk("m88dc2800: state, freq=%d qam=%d sym=%d inverted=%d xtal=%d\n", state->freq,state->qam,state->sym,state->inverted,state->xtal); -+ printk("m88dc2800: set frequency to %d qam=%d symrate=%d annex-c=%d\n", c->frequency,temp_qam,c->symbol_rate,is_annex_c); -+ ++ state->inverted = c->inversion == INVERSION_ON ? 1 : 0; ++ ++ printk(KERN_INFO ++ "m88dc2800: state, freq=%d qam=%d sym=%d inverted=%d xtal=%d\n", ++ state->freq, state->qam, state->sym, state->inverted, ++ state->xtal); ++ printk(KERN_INFO ++ "m88dc2800: set frequency to %d qam=%d symrate=%d annex-c=%d\n", ++ c->frequency, temp_qam, c->symbol_rate, is_annex_c); ++ + is_update = 0; + WriteReg(state, 0x80, 0x01); -+ if(c->frequency != state->freq){ -+ M88DC2000WriteTuner_TC2800(state, c->frequency/1000); -+ state->freq = c->frequency; ++ if (c->frequency != state->freq) { ++ M88DC2000WriteTuner_TC2800(state, c->frequency / 1000); ++ state->freq = c->frequency; + } -+ if(c->symbol_rate != state->sym){ -+ M88DC2000SetSym(state, c->symbol_rate/1000, state->xtal); ++ if (c->symbol_rate != state->sym) { ++ M88DC2000SetSym(state, c->symbol_rate / 1000, state->xtal); + state->sym = c->symbol_rate; + is_update = 1; + } -+ if(temp_qam != state->qam){ -+ M88DC2000SetQAM(state, temp_qam); ++ if (temp_qam != state->qam) { ++ M88DC2000SetQAM(state, temp_qam); + state->qam = temp_qam; -+ is_update = 1; ++ is_update = 1; + } -+ -+ if(is_update != 0){ -+ if(state->config->ts_mode == 3) -+ M88DC2000AutoTSClock_C(state, state->sym/1000, temp_qam); ++ ++ if (is_update != 0) { ++ if (state->config->ts_mode == 3) ++ M88DC2000AutoTSClock_C(state, state->sym / 1000, ++ temp_qam); + else -+ M88DC2000AutoTSClock_P(state, state->sym/1000, temp_qam); ++ M88DC2000AutoTSClock_P(state, state->sym / 1000, ++ temp_qam); + } -+ ++ + M88DC2000SetTxMode(state, state->inverted, is_annex_c); + M88DC2000SoftReset(state); -+ if (((ReadReg(state, 0xE3) & 0x80) == 0x80) && ((ReadReg(state, 0xE4) & 0x80) == 0x80)) -+ waiting_time = 800; -+ else -+ waiting_time = 500; -+ while (waiting_time > 0) { -+ msleep(50); -+ waiting_time -= 50; -+ if (M88DC2000GetLock(state)) -+ return 0; ++ if (((ReadReg(state, 0xE3) & 0x80) == 0x80) ++ && ((ReadReg(state, 0xE4) & 0x80) == 0x80)) ++ waiting_time = 800; ++ else ++ waiting_time = 500; ++ while (waiting_time > 0) { ++ msleep(50); ++ waiting_time -= 50; ++ if (M88DC2000GetLock(state)) ++ return 0; + } -+ -+ if (state->inverted != 0) -+ state->inverted = 0; -+ else -+ state->inverted = 1; -+ M88DC2000SetTxMode(state, state->inverted, is_annex_c); -+ M88DC2000SoftReset(state); -+ if (((ReadReg(state, 0xE3) & 0x80) == 0x80) && ((ReadReg(state, 0xE4) & 0x80) == 0x80)) -+ waiting_time = 800; -+ else -+ waiting_time = 500; -+ while (waiting_time > 0) { -+ msleep(50); -+ waiting_time -= 50; -+ if (M88DC2000GetLock(state)) -+ return 0; ++ ++ state->inverted = (state->inverted != 0) ? 0 : 1; ++ M88DC2000SetTxMode(state, state->inverted, is_annex_c); ++ M88DC2000SoftReset(state); ++ if (((ReadReg(state, 0xE3) & 0x80) == 0x80) && ++ ((ReadReg(state, 0xE4) & 0x80) == 0x80)) ++ waiting_time = 800; ++ else ++ waiting_time = 500; ++ while (waiting_time > 0) { ++ msleep(50); ++ waiting_time -= 50; ++ if (M88DC2000GetLock(state)) ++ return 0; + } + return 0; +} + -+static int m88dc2800_read_status(struct dvb_frontend* fe, fe_status_t* status) ++static int m88dc2800_read_status(struct dvb_frontend *fe, ++ fe_status_t * status) +{ -+ struct m88dc2800_state* state = fe->demodulator_priv; ++ struct m88dc2800_state *state = fe->demodulator_priv; + *status = 0; -+ ++ + if (M88DC2000GetLock(state)) { -+ *status = FE_HAS_SIGNAL | FE_HAS_CARRIER -+ | FE_HAS_SYNC|FE_HAS_VITERBI | FE_HAS_LOCK; ++ *status = FE_HAS_SIGNAL | FE_HAS_CARRIER ++ |FE_HAS_SYNC | FE_HAS_VITERBI | FE_HAS_LOCK; + } + return 0; +} + -+static int m88dc2800_read_ber(struct dvb_frontend* fe, u32* ber) ++static int m88dc2800_read_ber(struct dvb_frontend *fe, u32 * ber) +{ -+ struct m88dc2800_state* state = fe->demodulator_priv; ++ struct m88dc2800_state *state = fe->demodulator_priv; + u16 tmp; + -+ if (M88DC2000GetLock(state) == 0) { ++ if (M88DC2000GetLock(state) == 0) { + state->ber = 0; -+ } else if ((ReadReg(state, 0xA0) & 0x80) != 0x80) { -+ tmp = ReadReg(state, 0xA2) << 8; -+ tmp += ReadReg(state, 0xA1); -+ state->ber = tmp; -+ WriteReg(state, 0xA0, 0x05); -+ WriteReg(state, 0xA0, 0x85); -+ } ++ } else if ((ReadReg(state, 0xA0) & 0x80) != 0x80) { ++ tmp = ReadReg(state, 0xA2) << 8; ++ tmp += ReadReg(state, 0xA1); ++ state->ber = tmp; ++ WriteReg(state, 0xA0, 0x05); ++ WriteReg(state, 0xA0, 0x85); ++ } + *ber = state->ber; + return 0; +} + -+static int m88dc2800_read_signal_strength(struct dvb_frontend* fe, u16* strength) ++static int m88dc2800_read_signal_strength(struct dvb_frontend *fe, ++ u16 * strength) +{ -+ struct m88dc2800_state* state = fe->demodulator_priv; -+ ++ struct m88dc2800_state *state = fe->demodulator_priv; + s16 tuner_strength; -+ tuner_strength = (s16)mt_fe_tn_get_signal_strength_tc2800(state); -+ -+ if(tuner_strength < -107) -+ *strength = 0; -+ else -+ *strength = tuner_strength + 107; -+ ++ ++ tuner_strength = mt_fe_tn_get_signal_strength_tc2800(state); ++ *strength = tuner_strength < -107 ? 0 : tuner_strength + 107; ++ + return 0; +} + -+static int m88dc2800_read_snr(struct dvb_frontend* fe, u16* snr) ++static int m88dc2800_read_snr(struct dvb_frontend *fe, u16 * snr) +{ -+ struct m88dc2800_state* state = fe->demodulator_priv; ++ static const u32 mes_log[] = { ++ 0, 3010, 4771, 6021, 6990, 7781, 8451, 9031, 9542, 10000, ++ 10414, 10792, 11139, 11461, 11761, 12041, 12304, 12553, 12788, ++ 13010, 13222, 13424, 13617, 13802, 13979, 14150, 14314, 14472, ++ 14624, 14771, 14914, 15052, 15185, 15315, 15441, 15563, 15682, ++ 15798, 15911, 16021, 16128, 16232, 16335, 16435, 16532, 16628, ++ 16721, 16812, 16902, 16990, 17076, 17160, 17243, 17324, 17404, ++ 17482, 17559, 17634, 17709, 17782, 17853, 17924, 17993, 18062, ++ 18129, 18195, 18261, 18325, 18388, 18451, 18513, 18573, 18633, ++ 18692, 18751, 18808, 18865, 18921, 18976, 19031 ++ }; ++ struct m88dc2800_state *state = fe->demodulator_priv; ++ u8 i; ++ u32 _snr, mse; + -+ const u32 mes_log[] = { -+ 0, 3010, 4771, 6021, 6990, 7781, 8451, 9031, 9542, 10000, -+ 10414, 10792, 11139, 11461, 11761, 12041, 12304, 12553, 12788, 13010, -+ 13222, 13424, 13617, 13802, 13979, 14150, 14314, 14472, 14624, 14771, -+ 14914, 15052, 15185, 15315, 15441, 15563, 15682, 15798, 15911, 16021, -+ 16128, 16232, 16335, 16435, 16532, 16628, 16721, 16812, 16902, 16990, -+ 17076, 17160, 17243, 17324, 17404, 17482, 17559, 17634, 17709, 17782, -+ 17853, 17924, 17993, 18062, 18129, 18195, 18261, 18325, 18388, 18451, -+ 18513, 18573, 18633, 18692, 18751, 18808, 18865, 18921, 18976, 19031 -+ }; -+ u8 i; -+ u32 _snr, mse; -+ -+ if ((ReadReg(state, 0x91)&0x23)!=0x03) { -+ *snr = 0; ++ if ((ReadReg(state, 0x91) & 0x23) != 0x03) { ++ *snr = 0; + return 0; -+ } -+ -+ mse = 0; -+ for (i=0; i<30; i++) { -+ mse += (ReadReg(state, 0x08) << 8) + ReadReg(state, 0x07); -+ } -+ mse /= 30; -+ if (mse > 80) -+ mse = 80; -+ -+ switch (state->qam) { -+ case 16: _snr = 34080; break; /* 16QAM */ -+ case 32: _snr = 37600; break; /* 32QAM */ -+ case 64: _snr = 40310; break; /* 64QAM */ -+ case 128: _snr = 43720; break; /* 128QAM */ -+ case 256: _snr = 46390; break; /* 256QAM */ -+ default: _snr = 40310; break; -+ } -+ _snr -= mes_log[mse-1]; /* C - 10*log10(MSE) */ -+ _snr /= 1000; -+ if (_snr > 0xff) -+ _snr = 0xff; -+ -+ *snr = _snr; ++ } ++ mse = 0; ++ for (i = 0; i < 30; i++) { ++ mse += (ReadReg(state, 0x08) << 8) + ReadReg(state, 0x07); ++ } ++ mse /= 30; ++ if (mse > 80) ++ mse = 80; ++ switch (state->qam) { ++ case 16: ++ _snr = 34080; ++ break; /* 16QAM */ ++ case 32: ++ _snr = 37600; ++ break; /* 32QAM */ ++ case 64: ++ _snr = 40310; ++ break; /* 64QAM */ ++ case 128: ++ _snr = 43720; ++ break; /* 128QAM */ ++ case 256: ++ _snr = 46390; ++ break; /* 256QAM */ ++ default: ++ _snr = 40310; ++ break; ++ } ++ _snr -= mes_log[mse - 1]; /* C - 10*log10(MSE) */ ++ _snr /= 1000; ++ if (_snr > 0xff) ++ _snr = 0xff; ++ *snr = _snr; + return 0; +} + -+static int m88dc2800_read_ucblocks(struct dvb_frontend* fe, u32* ucblocks) ++static int m88dc2800_read_ucblocks(struct dvb_frontend *fe, u32 * ucblocks) +{ -+ struct m88dc2800_state* state = fe->demodulator_priv; ++ struct m88dc2800_state *state = fe->demodulator_priv; + u8 u8Value; -+ ++ + u8Value = ReadReg(state, 0xdf); -+ u8Value |= 0x02; /* Hold */ ++ u8Value |= 0x02; /* Hold */ + WriteReg(state, 0xdf, u8Value); -+ ++ + *ucblocks = ReadReg(state, 0xd5); + *ucblocks = (*ucblocks << 8) | ReadReg(state, 0xd4); -+ -+ u8Value &= 0xfe; /* Clear */ ++ ++ u8Value &= 0xfe; /* Clear */ + WriteReg(state, 0xdf, u8Value); -+ u8Value &= 0xfc; /* Update */ ++ u8Value &= 0xfc; /* Update */ + u8Value |= 0x01; -+ WriteReg(state, 0xdf, u8Value); -+ ++ WriteReg(state, 0xdf, u8Value); ++ + return 0; +} + -+static int m88dc2800_sleep(struct dvb_frontend* fe) ++static int m88dc2800_sleep(struct dvb_frontend *fe) +{ -+ struct m88dc2800_state* state = fe->demodulator_priv; -+ ++ struct m88dc2800_state *state = fe->demodulator_priv; ++ + mt_fe_tn_sleep_tc2800(state); + state->freq = 0; + + return 0; +} + -+static void m88dc2800_release(struct dvb_frontend* fe) ++static void m88dc2800_release(struct dvb_frontend *fe) +{ -+ struct m88dc2800_state* state = fe->demodulator_priv; ++ struct m88dc2800_state *state = fe->demodulator_priv; + kfree(state); +} + +static struct dvb_frontend_ops m88dc2800_ops; + -+struct dvb_frontend* m88dc2800_attach(const struct m88dc2800_config* config, -+ struct i2c_adapter* i2c) ++struct dvb_frontend *m88dc2800_attach(const struct m88dc2800_config ++ *config, struct i2c_adapter *i2c) +{ -+ struct m88dc2800_state* state = NULL; ++ struct m88dc2800_state *state = NULL; + + /* allocate memory for the internal state */ + state = kzalloc(sizeof(struct m88dc2800_state), GFP_KERNEL); -+ if (state == NULL) goto error; ++ if (state == NULL) ++ goto error; + + /* setup the state */ + state->config = config; + state->i2c = i2c; + state->xtal = 28800; -+ ++ + WriteReg(state, 0x80, 0x01); -+ M88DC2000RegInitial_TC2800(state); ++ M88DC2000RegInitial_TC2800(state); + M88DC2000SetTsType(state, state->config->ts_mode); + mt_fe_tn_init_tc2800(state); -+ ++ + /* create dvb_frontend */ -+ memcpy(&state->frontend.ops, &m88dc2800_ops, sizeof(struct dvb_frontend_ops)); ++ memcpy(&state->frontend.ops, &m88dc2800_ops, ++ sizeof(struct dvb_frontend_ops)); + state->frontend.demodulator_priv = state; + return &state->frontend; + -+error: ++ error: + kfree(state); + return NULL; +} ++ +EXPORT_SYMBOL(m88dc2800_attach); + +static struct dvb_frontend_ops m88dc2800_ops = { -+ .delsys = { SYS_DVBC_ANNEX_A, SYS_DVBC_ANNEX_C }, ++ .delsys = {SYS_DVBC_ANNEX_A, SYS_DVBC_ANNEX_C}, + .info = { -+ .name = "Montage M88DC2800 DVB-C", -+ .frequency_stepsize = 62500, -+ .frequency_min = 48000000, -+ .frequency_max = 870000000, -+ .symbol_rate_min = 870000, -+ .symbol_rate_max = 9000000, -+ .caps = FE_CAN_QAM_16 | FE_CAN_QAM_32 | FE_CAN_QAM_64 | -+ FE_CAN_QAM_128 | FE_CAN_QAM_256 | -+ FE_CAN_FEC_AUTO ++ .name = "Montage M88DC2800 DVB-C", ++ .frequency_stepsize = 62500, ++ .frequency_min = 48000000, ++ .frequency_max = 870000000, ++ .symbol_rate_min = 870000, ++ .symbol_rate_max = 9000000, ++ .caps = FE_CAN_QAM_16 | FE_CAN_QAM_32 | FE_CAN_QAM_64 | ++ FE_CAN_QAM_128 | FE_CAN_QAM_256 | FE_CAN_FEC_AUTO + }, -+ + .release = m88dc2800_release, + .init = m88dc2800_init, + .sleep = m88dc2800_sleep, + .set_frontend = m88dc2800_set_parameters, -+ .read_status = m88dc2800_read_status, -+ .read_ber = m88dc2800_read_ber, -+ .read_signal_strength = m88dc2800_read_signal_strength, ++ .read_status = m88dc2800_read_status, ++ .read_ber = m88dc2800_read_ber, ++ .read_signal_strength = m88dc2800_read_signal_strength, + .read_snr = m88dc2800_read_snr, + .read_ucblocks = m88dc2800_read_ucblocks, +}; + +MODULE_DESCRIPTION("Montage DVB-C demodulator driver"); -+MODULE_AUTHOR("Max nibble"); ++MODULE_AUTHOR("Max Nibble "); +MODULE_LICENSE("GPL"); -diff --git a/drivers/media/dvb-frontends/m88dc2800.h b/drivers/media/dvb-frontends/m88dc2800.h -new file mode 100644 -index 0000000..a0a93c4 ---- /dev/null -+++ b/drivers/media/dvb-frontends/m88dc2800.h ++MODULE_VERSION("1.00"); +diff -urN a/drivers/media/dvb-frontends/m88dc2800.h b/drivers/media/dvb-frontends/m88dc2800.h +--- a/drivers/media/dvb-frontends/m88dc2800.h 1970-01-01 08:00:00.000000000 +0800 ++++ b/drivers/media/dvb-frontends/m88dc2800.h 2013-01-26 14:57:32.000000000 +0800 @@ -0,0 +1,43 @@ +/* + M88DC2800/M88TC2800 - DVB-C demodulator and tuner from Montage + -+ Copyright (C) 2012 Max nibble -+ Copyright (C) 2011 Montage Technology -+ ++ Copyright (C) 2012 Max Nibble ++ Copyright (C) 2011 Montage Technology - www.montage-tech.com ++ + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or @@ -2363,13 +2195,11 @@ index 0000000..a0a93c4 + printk(KERN_WARNING "%s: driver disabled by Kconfig\n", __func__); + return NULL; +} -+#endif // CONFIG_DVB_M88DC2800 -+#endif // M88DC2800_H -diff --git a/drivers/media/dvb-frontends/m88ds3103.c b/drivers/media/dvb-frontends/m88ds3103.c -new file mode 100644 -index 0000000..315809d ---- /dev/null -+++ b/drivers/media/dvb-frontends/m88ds3103.c ++#endif /* CONFIG_DVB_M88DC2800 */ ++#endif /* M88DC2800_H */ +diff -urN a/drivers/media/dvb-frontends/m88ds3103.c b/drivers/media/dvb-frontends/m88ds3103.c +--- a/drivers/media/dvb-frontends/m88ds3103.c 1970-01-01 08:00:00.000000000 +0800 ++++ b/drivers/media/dvb-frontends/m88ds3103.c 2013-01-30 12:33:47.000000000 +0800 @@ -0,0 +1,1710 @@ +/* + Montage Technology M88DS3103/M88TS2022 - DVBS/S2 Satellite demod/tuner driver @@ -4081,11 +3911,9 @@ index 0000000..315809d +MODULE_DESCRIPTION("DVB Frontend module for Montage DS3103/TS2022 hardware"); +MODULE_AUTHOR("Max nibble"); +MODULE_LICENSE("GPL"); -diff --git a/drivers/media/dvb-frontends/m88ds3103.h b/drivers/media/dvb-frontends/m88ds3103.h -new file mode 100644 -index 0000000..c7b690e ---- /dev/null -+++ b/drivers/media/dvb-frontends/m88ds3103.h +diff -urN a/drivers/media/dvb-frontends/m88ds3103.h b/drivers/media/dvb-frontends/m88ds3103.h +--- a/drivers/media/dvb-frontends/m88ds3103.h 1970-01-01 08:00:00.000000000 +0800 ++++ b/drivers/media/dvb-frontends/m88ds3103.h 2013-01-30 12:33:51.000000000 +0800 @@ -0,0 +1,53 @@ +/* + Montage Technology M88DS3103/M88TS2022 - DVBS/S2 Satellite demod/tuner driver @@ -4140,11 +3968,9 @@ index 0000000..c7b690e +} +#endif /* CONFIG_DVB_M88DS3103 */ +#endif /* M88DS3103_H */ -diff --git a/drivers/media/dvb-frontends/m88ds3103_priv.h b/drivers/media/dvb-frontends/m88ds3103_priv.h -new file mode 100644 -index 0000000..2838514 ---- /dev/null -+++ b/drivers/media/dvb-frontends/m88ds3103_priv.h +diff -urN a/drivers/media/dvb-frontends/m88ds3103_priv.h b/drivers/media/dvb-frontends/m88ds3103_priv.h +--- a/drivers/media/dvb-frontends/m88ds3103_priv.h 1970-01-01 08:00:00.000000000 +0800 ++++ b/drivers/media/dvb-frontends/m88ds3103_priv.h 2013-01-30 12:33:56.000000000 +0800 @@ -0,0 +1,403 @@ +/* + Montage Technology M88DS3103/M88TS2022 - DVBS/S2 Satellite demod/tuner driver @@ -4549,24 +4375,20 @@ index 0000000..2838514 +}; + +#endif /* M88DS3103_PRIV_H */ -diff --git a/drivers/media/pci/cx23885/Kconfig b/drivers/media/pci/cx23885/Kconfig -index eafa114..37690f0 100644 ---- a/drivers/media/pci/cx23885/Kconfig -+++ b/drivers/media/pci/cx23885/Kconfig -@@ -23,6 +23,8 @@ config VIDEO_CX23885 - select DVB_STB6100 if MEDIA_SUBDRV_AUTOSELECT - select DVB_STV6110 if MEDIA_SUBDRV_AUTOSELECT - select DVB_CX24116 if MEDIA_SUBDRV_AUTOSELECT -+ select DVB_M88DS3103 if MEDIA_SUBDRV_AUTOSELECT -+ select DVB_M88DC2800 if MEDIA_SUBDRV_AUTOSELECT - select DVB_STV0900 if MEDIA_SUBDRV_AUTOSELECT - select DVB_DS3000 if MEDIA_SUBDRV_AUTOSELECT - select DVB_STV0367 if MEDIA_SUBDRV_AUTOSELECT -diff --git a/drivers/media/pci/cx23885/cimax2.c b/drivers/media/pci/cx23885/cimax2.c -index 7344849..369ae7c 100644 ---- a/drivers/media/pci/cx23885/cimax2.c -+++ b/drivers/media/pci/cx23885/cimax2.c -@@ -415,7 +415,7 @@ int netup_poll_ci_slot_status(struct dvb_ca_en50221 *en50221, +diff -urN a/drivers/media/dvb-frontends/Makefile b/drivers/media/dvb-frontends/Makefile +--- a/drivers/media/dvb-frontends/Makefile 2013-03-21 04:11:19.000000000 +0800 ++++ b/drivers/media/dvb-frontends/Makefile 2013-04-23 22:15:04.000000000 +0800 +@@ -102,4 +102,5 @@ + obj-$(CONFIG_DVB_RTL2832) += rtl2832.o + obj-$(CONFIG_DVB_M88RS2000) += m88rs2000.o + obj-$(CONFIG_DVB_AF9033) += af9033.o +- ++obj-$(CONFIG_DVB_M88DS3103) += m88ds3103.o ++obj-$(CONFIG_DVB_M88DC2800) += m88dc2800.o +diff -urN a/drivers/media/pci/cx23885/cimax2.c b/drivers/media/pci/cx23885/cimax2.c +--- a/drivers/media/pci/cx23885/cimax2.c 2013-03-21 04:11:19.000000000 +0800 ++++ b/drivers/media/pci/cx23885/cimax2.c 2013-03-31 22:03:29.000000000 +0800 +@@ -415,7 +415,7 @@ return state->status; } @@ -4575,7 +4397,7 @@ index 7344849..369ae7c 100644 { struct netup_ci_state *state; u8 cimax_init[34] = { -@@ -464,6 +464,11 @@ int netup_ci_init(struct cx23885_tsport *port) +@@ -464,6 +464,11 @@ goto err; } @@ -4587,7 +4409,7 @@ index 7344849..369ae7c 100644 port->port_priv = state; switch (port->nr) { -@@ -537,3 +542,19 @@ void netup_ci_exit(struct cx23885_tsport *port) +@@ -537,3 +542,19 @@ dvb_ca_en50221_release(&state->ca); kfree(state); } @@ -4607,11 +4429,10 @@ index 7344849..369ae7c 100644 + + return 1; +} -diff --git a/drivers/media/pci/cx23885/cimax2.h b/drivers/media/pci/cx23885/cimax2.h -index 518744a..39f3db7 100644 ---- a/drivers/media/pci/cx23885/cimax2.h -+++ b/drivers/media/pci/cx23885/cimax2.h -@@ -41,7 +41,9 @@ extern int netup_ci_slot_ts_ctl(struct dvb_ca_en50221 *en50221, int slot); +diff -urN a/drivers/media/pci/cx23885/cimax2.h b/drivers/media/pci/cx23885/cimax2.h +--- a/drivers/media/pci/cx23885/cimax2.h 2013-03-21 04:11:19.000000000 +0800 ++++ b/drivers/media/pci/cx23885/cimax2.h 2013-01-30 12:34:37.000000000 +0800 +@@ -41,7 +41,9 @@ extern int netup_ci_slot_status(struct cx23885_dev *dev, u32 pci_status); extern int netup_poll_ci_slot_status(struct dvb_ca_en50221 *en50221, int slot, int open); @@ -4622,11 +4443,10 @@ index 518744a..39f3db7 100644 +extern int dvbsky_ci_slot_status(struct cx23885_dev *dev); + #endif -diff --git a/drivers/media/pci/cx23885/cx23885-cards.c b/drivers/media/pci/cx23885/cx23885-cards.c -index 6277e14..d163c41 100644 ---- a/drivers/media/pci/cx23885/cx23885-cards.c -+++ b/drivers/media/pci/cx23885/cx23885-cards.c -@@ -569,9 +569,32 @@ struct cx23885_board cx23885_boards[] = { +diff -urN a/drivers/media/pci/cx23885/cx23885-cards.c b/drivers/media/pci/cx23885/cx23885-cards.c +--- a/drivers/media/pci/cx23885/cx23885-cards.c 2013-03-21 04:11:19.000000000 +0800 ++++ b/drivers/media/pci/cx23885/cx23885-cards.c 2013-04-23 22:19:57.000000000 +0800 +@@ -569,9 +569,37 @@ .name = "TeVii S471", .portb = CX23885_MPEG_DVB, }, @@ -4655,13 +4475,18 @@ index 6277e14..d163c41 100644 + .name = "DVBSKY C2800E DVB-C CI", + .portb = CX23885_MPEG_DVB, + }, ++ [CX23885_BOARD_DVBSKY_T9580] = { ++ .name = "DVBSKY T9580", ++ .portb = CX23885_MPEG_DVB, ++ .portc = CX23885_MPEG_DVB, ++ }, + [CX23885_BOARD_PROF_8000] = { + .name = "Prof Revolution DVB-S2 8000", + .portb = CX23885_MPEG_DVB, } }; const unsigned int cx23885_bcount = ARRAY_SIZE(cx23885_boards); -@@ -785,9 +808,29 @@ struct cx23885_subid cx23885_subids[] = { +@@ -785,9 +813,33 @@ .subdevice = 0x9022, .card = CX23885_BOARD_TEVII_S471, }, { @@ -4687,6 +4512,10 @@ index 6277e14..d163c41 100644 + .subvendor = 0x4254, + .subdevice = 0x2800, + .card = CX23885_BOARD_DVBSKY_C2800E_CI, ++ }, { ++ .subvendor = 0x4254, ++ .subdevice = 0x9580, ++ .card = CX23885_BOARD_DVBSKY_T9580, + }, { + .subvendor = 0x8000, + .subdevice = 0x3034, @@ -4694,7 +4523,7 @@ index 6277e14..d163c41 100644 }, }; const unsigned int cx23885_idcount = ARRAY_SIZE(cx23885_subids); -@@ -1167,7 +1210,7 @@ void cx23885_gpio_setup(struct cx23885_dev *dev) +@@ -1167,7 +1219,7 @@ cx_set(GP0_IO, 0x00040004); break; case CX23885_BOARD_TBS_6920: @@ -4703,7 +4532,7 @@ index 6277e14..d163c41 100644 cx_write(MC417_CTL, 0x00000036); cx_write(MC417_OEN, 0x00001000); cx_set(MC417_RWD, 0x00000002); -@@ -1301,9 +1344,83 @@ void cx23885_gpio_setup(struct cx23885_dev *dev) +@@ -1301,9 +1353,84 @@ /* enable irq */ cx_write(GPIO_ISM, 0x00000000);/* INTERRUPTS active low*/ break; @@ -4714,7 +4543,8 @@ index 6277e14..d163c41 100644 + msleep(100); + cx23885_gpio_set(dev, GPIO_2); + break; -+ case CX23885_BOARD_DVBSKY_S952: ++ case CX23885_BOARD_DVBSKY_S952: ++ case CX23885_BOARD_DVBSKY_T9580: + cx_write(MC417_CTL, 0x00000037);/* enable GPIO3-18 pins */ + + cx23885_gpio_enable(dev, GPIO_2, 1); @@ -4787,7 +4617,7 @@ index 6277e14..d163c41 100644 int cx23885_ir_init(struct cx23885_dev *dev) { static struct v4l2_subdev_io_pin_config ir_rxtx_pin_cfg[] = { -@@ -1388,6 +1505,22 @@ int cx23885_ir_init(struct cx23885_dev *dev) +@@ -1388,6 +1515,23 @@ v4l2_subdev_call(dev->sd_cx25840, core, s_io_pin_config, ir_rx_pin_cfg_count, ir_rx_pin_cfg); break; @@ -4795,7 +4625,8 @@ index 6277e14..d163c41 100644 + case CX23885_BOARD_DVBSKY_S950: + case CX23885_BOARD_DVBSKY_S952: + case CX23885_BOARD_DVBSKY_S950_CI: -+ case CX23885_BOARD_DVBSKY_C2800E_CI: ++ case CX23885_BOARD_DVBSKY_C2800E_CI: ++ case CX23885_BOARD_DVBSKY_T9580: + dev->sd_ir = cx23885_find_hw(dev, CX23885_HW_AV_CORE); + if (dev->sd_ir == NULL) { + ret = -ENODEV; @@ -4810,7 +4641,7 @@ index 6277e14..d163c41 100644 case CX23885_BOARD_HAUPPAUGE_HVR1250: if (!enable_885_ir) break; -@@ -1420,6 +1553,11 @@ void cx23885_ir_fini(struct cx23885_dev *dev) +@@ -1420,6 +1564,12 @@ case CX23885_BOARD_TERRATEC_CINERGY_T_PCIE_DUAL: case CX23885_BOARD_TEVII_S470: case CX23885_BOARD_HAUPPAUGE_HVR1250: @@ -4818,11 +4649,12 @@ index 6277e14..d163c41 100644 + case CX23885_BOARD_DVBSKY_S950: + case CX23885_BOARD_DVBSKY_S952: + case CX23885_BOARD_DVBSKY_S950_CI: -+ case CX23885_BOARD_DVBSKY_C2800E_CI: ++ case CX23885_BOARD_DVBSKY_C2800E_CI: ++ case CX23885_BOARD_DVBSKY_T9580: cx23885_irq_remove(dev, PCI_MSK_AV_CORE); /* sd_ir is a duplicate pointer to the AV Core, just clear it */ dev->sd_ir = NULL; -@@ -1464,6 +1602,11 @@ void cx23885_ir_pci_int_enable(struct cx23885_dev *dev) +@@ -1464,6 +1614,12 @@ case CX23885_BOARD_TERRATEC_CINERGY_T_PCIE_DUAL: case CX23885_BOARD_TEVII_S470: case CX23885_BOARD_HAUPPAUGE_HVR1250: @@ -4830,11 +4662,12 @@ index 6277e14..d163c41 100644 + case CX23885_BOARD_DVBSKY_S950: + case CX23885_BOARD_DVBSKY_S952: + case CX23885_BOARD_DVBSKY_S950_CI: -+ case CX23885_BOARD_DVBSKY_C2800E_CI: ++ case CX23885_BOARD_DVBSKY_C2800E_CI: ++ case CX23885_BOARD_DVBSKY_T9580: if (dev->sd_ir) cx23885_irq_add_enable(dev, PCI_MSK_AV_CORE); break; -@@ -1549,6 +1692,10 @@ void cx23885_card_setup(struct cx23885_dev *dev) +@@ -1549,6 +1705,10 @@ ts1->ts_clk_en_val = 0x1; /* Enable TS_CLK */ ts1->src_sel_val = CX23885_SRC_SEL_PARALLEL_MPEG_VIDEO; break; @@ -4845,7 +4678,7 @@ index 6277e14..d163c41 100644 case CX23885_BOARD_TEVII_S470: case CX23885_BOARD_TEVII_S471: case CX23885_BOARD_DVBWORLD_2005: -@@ -1581,6 +1728,14 @@ void cx23885_card_setup(struct cx23885_dev *dev) +@@ -1581,6 +1741,22 @@ ts2->ts_clk_en_val = 0x1; /* Enable TS_CLK */ ts2->src_sel_val = CX23885_SRC_SEL_PARALLEL_MPEG_VIDEO; break; @@ -4857,10 +4690,18 @@ index 6277e14..d163c41 100644 + ts2->ts_clk_en_val = 0x1; /* Enable TS_CLK */ + ts2->src_sel_val = CX23885_SRC_SEL_PARALLEL_MPEG_VIDEO; + break; ++ case CX23885_BOARD_DVBSKY_T9580: ++ ts1->gen_ctrl_val = 0x5; /* Parallel */ ++ ts1->ts_clk_en_val = 0x1; /* Enable TS_CLK */ ++ ts1->src_sel_val = CX23885_SRC_SEL_PARALLEL_MPEG_VIDEO; ++ ts2->gen_ctrl_val = 0x8; /* Serial bus */ ++ ts2->ts_clk_en_val = 0x1; /* Enable TS_CLK */ ++ ts2->src_sel_val = CX23885_SRC_SEL_PARALLEL_MPEG_VIDEO; ++ break; case CX23885_BOARD_HAUPPAUGE_HVR1250: case CX23885_BOARD_HAUPPAUGE_HVR1500: case CX23885_BOARD_HAUPPAUGE_HVR1500Q: -@@ -1636,6 +1791,11 @@ void cx23885_card_setup(struct cx23885_dev *dev) +@@ -1636,6 +1812,12 @@ case CX23885_BOARD_MPX885: case CX23885_BOARD_MYGICA_X8507: case CX23885_BOARD_TERRATEC_CINERGY_T_PCIE_DUAL: @@ -4869,14 +4710,14 @@ index 6277e14..d163c41 100644 + case CX23885_BOARD_DVBSKY_S952: + case CX23885_BOARD_DVBSKY_S950_CI: + case CX23885_BOARD_DVBSKY_C2800E_CI: ++ case CX23885_BOARD_DVBSKY_T9580: dev->sd_cx25840 = v4l2_i2c_new_subdev(&dev->v4l2_dev, &dev->i2c_bus[2].i2c_adap, "cx25840", 0x88 >> 1, NULL); -diff --git a/drivers/media/pci/cx23885/cx23885-core.c b/drivers/media/pci/cx23885/cx23885-core.c -index f0416a6..bb8130a 100644 ---- a/drivers/media/pci/cx23885/cx23885-core.c -+++ b/drivers/media/pci/cx23885/cx23885-core.c -@@ -1909,6 +1909,10 @@ static irqreturn_t cx23885_irq(int irq, void *dev_id) +diff -urN a/drivers/media/pci/cx23885/cx23885-core.c b/drivers/media/pci/cx23885/cx23885-core.c +--- a/drivers/media/pci/cx23885/cx23885-core.c 2013-03-21 04:11:19.000000000 +0800 ++++ b/drivers/media/pci/cx23885/cx23885-core.c 2013-04-23 22:19:04.000000000 +0800 +@@ -1909,6 +1909,10 @@ (pci_status & PCI_MSK_GPIO0)) handled += altera_ci_irq(dev); @@ -4887,7 +4728,7 @@ index f0416a6..bb8130a 100644 if (ts1_status) { if (cx23885_boards[dev->board].portb == CX23885_MPEG_DVB) handled += cx23885_irq_ts(ts1, ts1_status); -@@ -2144,6 +2148,8 @@ static int cx23885_initdev(struct pci_dev *pci_dev, +@@ -2144,6 +2148,8 @@ cx23885_irq_add_enable(dev, PCI_MSK_GPIO1 | PCI_MSK_GPIO0); break; case CX23885_BOARD_NETUP_DUAL_DVB_T_C_CI_RF: @@ -4896,10 +4737,9 @@ index f0416a6..bb8130a 100644 cx23885_irq_add_enable(dev, PCI_MSK_GPIO0); break; } -diff --git a/drivers/media/pci/cx23885/cx23885-dvb.c b/drivers/media/pci/cx23885/cx23885-dvb.c -index 2f5b902..4319f35 100644 ---- a/drivers/media/pci/cx23885/cx23885-dvb.c -+++ b/drivers/media/pci/cx23885/cx23885-dvb.c +diff -urN a/drivers/media/pci/cx23885/cx23885-dvb.c b/drivers/media/pci/cx23885/cx23885-dvb.c +--- a/drivers/media/pci/cx23885/cx23885-dvb.c 2013-03-21 04:11:19.000000000 +0800 ++++ b/drivers/media/pci/cx23885/cx23885-dvb.c 2013-04-23 22:48:39.797116340 +0800 @@ -51,6 +51,8 @@ #include "stv6110.h" #include "lnbh24.h" @@ -4920,7 +4760,7 @@ index 2f5b902..4319f35 100644 #include "stb6100_cfg.h" static unsigned int debug; -@@ -492,40 +494,76 @@ static struct xc5000_config mygica_x8506_xc5000_config = { +@@ -492,42 +494,130 @@ .if_khz = 5380, }; @@ -4939,6 +4779,71 @@ index 2f5b902..4319f35 100644 - .tuner_set_frequency = stb6100_set_frequency, - .tuner_set_bandwidth = stb6100_set_bandwidth, - .tuner_get_bandwidth = stb6100_get_bandwidth, +-}; +- +-static struct stb6100_config prof_8000_stb6100_config = { +- .tuner_address = 0x60, +- .refclock = 27000000, +-}; + +-static int p8000_set_voltage(struct dvb_frontend *fe, fe_sec_voltage_t voltage) ++/* bst control */ ++int bst_set_voltage(struct dvb_frontend *fe, fe_sec_voltage_t voltage) + { + struct cx23885_tsport *port = fe->dvb->priv; + struct cx23885_dev *dev = port->dev; ++ ++ cx23885_gpio_enable(dev, GPIO_1, 1); ++ cx23885_gpio_enable(dev, GPIO_0, 1); ++ ++ switch (voltage) { ++ case SEC_VOLTAGE_13: ++ cx23885_gpio_set(dev, GPIO_1); ++ cx23885_gpio_clear(dev, GPIO_0); ++ break; ++ case SEC_VOLTAGE_18: ++ cx23885_gpio_set(dev, GPIO_1); ++ cx23885_gpio_set(dev, GPIO_0); ++ break; ++ case SEC_VOLTAGE_OFF: ++ cx23885_gpio_clear(dev, GPIO_1); ++ cx23885_gpio_clear(dev, GPIO_0); ++ break; ++ } ++ return 0; ++} + +- if (voltage == SEC_VOLTAGE_18) +- cx_write(MC417_RWD, 0x00001e00); +- else if (voltage == SEC_VOLTAGE_13) +- cx_write(MC417_RWD, 0x00001a00); +- else +- cx_write(MC417_RWD, 0x00001800); ++int dvbsky_set_voltage_sec(struct dvb_frontend *fe, fe_sec_voltage_t voltage) ++{ ++ struct cx23885_tsport *port = fe->dvb->priv; ++ struct cx23885_dev *dev = port->dev; ++ ++ cx23885_gpio_enable(dev, GPIO_12, 1); ++ cx23885_gpio_enable(dev, GPIO_13, 1); ++ ++ switch (voltage) { ++ case SEC_VOLTAGE_13: ++ cx23885_gpio_set(dev, GPIO_13); ++ cx23885_gpio_clear(dev, GPIO_12); ++ break; ++ case SEC_VOLTAGE_18: ++ cx23885_gpio_set(dev, GPIO_13); ++ cx23885_gpio_set(dev, GPIO_12); ++ break; ++ case SEC_VOLTAGE_OFF: ++ cx23885_gpio_clear(dev, GPIO_13); ++ cx23885_gpio_clear(dev, GPIO_12); ++ break; ++ } + return 0; + } + +/* bestunar single dvb-s2 */ +static struct m88ds3103_config bst_ds3103_config = { + .demod_address = 0x68, @@ -4961,34 +4866,20 @@ index 2f5b902..4319f35 100644 + .pin_ctrl = 0x82, + .ts_mode = 1, + .set_voltage = dvbsky_set_voltage_sec, - }; - --static struct stb6100_config prof_8000_stb6100_config = { -- .tuner_address = 0x60, -- .refclock = 27000000, ++}; ++ +static struct m88ds3103_config dvbsky_ds3103_ci_config = { + .demod_address = 0x68, + .ci_mode = 2, + .pin_ctrl = 0x82, + .ts_mode = 0, - }; - --static int p8000_set_voltage(struct dvb_frontend *fe, fe_sec_voltage_t voltage) --{ -- struct cx23885_tsport *port = fe->dvb->priv; -- struct cx23885_dev *dev = port->dev; ++}; ++ +static struct m88dc2800_config dvbsky_dc2800_config = { + .demod_address = 0x1c, + .ts_mode = 3, +}; - -- if (voltage == SEC_VOLTAGE_18) -- cx_write(MC417_RWD, 0x00001e00); -- else if (voltage == SEC_VOLTAGE_13) -- cx_write(MC417_RWD, 0x00001a00); -- else -- cx_write(MC417_RWD, 0x00001800); -- return 0; ++ +static struct stv090x_config prof_8000_stv090x_config = { + .device = STV0903, + .demod_mode = STV090x_SINGLE, @@ -5023,10 +4914,12 @@ index 2f5b902..4319f35 100644 + else + cx_write(MC417_RWD, 0x00001800); + return 0; - } - ++} ++ static int cx23885_dvb_set_frontend(struct dvb_frontend *fe) -@@ -1225,22 +1263,63 @@ static int dvb_register(struct cx23885_tsport *port) + { + struct dtv_frontend_properties *p = &fe->dtv_property_cache; +@@ -1225,23 +1315,79 @@ &tevii_ds3000_config, &i2c_bus->i2c_adap); break; @@ -5084,7 +4977,21 @@ index 2f5b902..4319f35 100644 + break; - fe0->dvb.frontend->ops.set_voltage = p8000_set_voltage; -- } ++ case CX23885_BOARD_DVBSKY_T9580: ++ switch (port->nr) { ++ /* port B */ ++ case 1: ++ i2c_bus = &dev->i2c_bus[1]; ++ fe0->dvb.frontend = dvb_attach(m88ds3103_attach, ++ &dvbsky_ds3103_config_pri, ++ &i2c_bus->i2c_adap); ++ break; ++ /* port C */ ++ case 2: ++ break; + } + break; ++ + case CX23885_BOARD_PROF_8000: + i2c_bus = &dev->i2c_bus[0]; + @@ -5101,10 +5008,11 @@ index 2f5b902..4319f35 100644 + + fe0->dvb.frontend->ops.set_voltage = p8000_set_voltage; + } - break; ++ break; default: printk(KERN_INFO "%s: The frontend of your DVB/ATSC card " -@@ -1289,7 +1368,7 @@ static int dvb_register(struct cx23885_tsport *port) + " isn't supported yet\n", +@@ -1289,7 +1435,7 @@ printk(KERN_INFO "NetUP Dual DVB-S2 CI card port%d MAC=%pM\n", port->nr, port->frontends.adapter.proposed_mac); @@ -5113,13 +5021,14 @@ index 2f5b902..4319f35 100644 break; } case CX23885_BOARD_NETUP_DUAL_DVB_T_C_CI_RF: { -@@ -1316,6 +1395,40 @@ static int dvb_register(struct cx23885_tsport *port) +@@ -1316,6 +1462,41 @@ memcpy(port->frontends.adapter.proposed_mac, eeprom + 0xa0, 6); break; } + case CX23885_BOARD_BST_PS8512: + case CX23885_BOARD_DVBSKY_S950: -+ case CX23885_BOARD_DVBSKY_S952:{ ++ case CX23885_BOARD_DVBSKY_S952: ++ case CX23885_BOARD_DVBSKY_T9580:{ + u8 eeprom[256]; /* 24C02 i2c eeprom */ + + if(port->nr > 2) @@ -5154,7 +5063,7 @@ index 2f5b902..4319f35 100644 } return ret; -@@ -1398,6 +1511,8 @@ int cx23885_dvb_unregister(struct cx23885_tsport *port) +@@ -1398,6 +1579,8 @@ switch (port->dev->board) { case CX23885_BOARD_NETUP_DUAL_DVBS2_CI: @@ -5163,88 +5072,35 @@ index 2f5b902..4319f35 100644 netup_ci_exit(port); break; case CX23885_BOARD_NETUP_DUAL_DVB_T_C_CI_RF: -diff --git a/drivers/media/pci/cx23885/cx23885-f300.c b/drivers/media/pci/cx23885/cx23885-f300.c -index 5444cc5..1f4bf10 100644 ---- a/drivers/media/pci/cx23885/cx23885-f300.c -+++ b/drivers/media/pci/cx23885/cx23885-f300.c -@@ -176,3 +176,58 @@ int f300_set_voltage(struct dvb_frontend *fe, fe_sec_voltage_t voltage) +diff -urN a/drivers/media/pci/cx23885/cx23885.h b/drivers/media/pci/cx23885/cx23885.h +--- a/drivers/media/pci/cx23885/cx23885.h 2013-03-21 04:11:19.000000000 +0800 ++++ b/drivers/media/pci/cx23885/cx23885.h 2013-04-23 22:18:24.000000000 +0800 +@@ -91,6 +91,12 @@ + #define CX23885_BOARD_TEVII_S471 35 + #define CX23885_BOARD_HAUPPAUGE_HVR1255_22111 36 + #define CX23885_BOARD_PROF_8000 37 ++#define CX23885_BOARD_BST_PS8512 38 ++#define CX23885_BOARD_DVBSKY_S952 39 ++#define CX23885_BOARD_DVBSKY_S950 40 ++#define CX23885_BOARD_DVBSKY_S950_CI 41 ++#define CX23885_BOARD_DVBSKY_C2800E_CI 42 ++#define CX23885_BOARD_DVBSKY_T9580 43 - return f300_xfer(fe, buf); - } -+ -+/* bst control */ -+int bst_set_voltage(struct dvb_frontend *fe, fe_sec_voltage_t voltage) -+{ -+ struct cx23885_tsport *port = fe->dvb->priv; -+ struct cx23885_dev *dev = port->dev; -+ -+ cx23885_gpio_enable(dev, GPIO_1, 1); -+ cx23885_gpio_enable(dev, GPIO_0, 1); -+ -+ switch (voltage) { -+ case SEC_VOLTAGE_13: -+ cx23885_gpio_set(dev, GPIO_1); -+ cx23885_gpio_clear(dev, GPIO_0); -+ break; -+ case SEC_VOLTAGE_18: -+ cx23885_gpio_set(dev, GPIO_1); -+ cx23885_gpio_set(dev, GPIO_0); -+ break; -+ case SEC_VOLTAGE_OFF: -+ cx23885_gpio_clear(dev, GPIO_1); -+ cx23885_gpio_clear(dev, GPIO_0); -+ break; -+ } -+ -+ -+ return 0; -+} -+ -+int dvbsky_set_voltage_sec(struct dvb_frontend *fe, fe_sec_voltage_t voltage) -+{ -+ struct cx23885_tsport *port = fe->dvb->priv; -+ struct cx23885_dev *dev = port->dev; -+ -+ cx23885_gpio_enable(dev, GPIO_12, 1); -+ cx23885_gpio_enable(dev, GPIO_13, 1); -+ -+ switch (voltage) { -+ case SEC_VOLTAGE_13: -+ cx23885_gpio_set(dev, GPIO_13); -+ cx23885_gpio_clear(dev, GPIO_12); -+ break; -+ case SEC_VOLTAGE_18: -+ cx23885_gpio_set(dev, GPIO_13); -+ cx23885_gpio_set(dev, GPIO_12); -+ break; -+ case SEC_VOLTAGE_OFF: -+ cx23885_gpio_clear(dev, GPIO_13); -+ cx23885_gpio_clear(dev, GPIO_12); -+ break; -+ } -+ -+ -+ return 0; -+} -\ No newline at end of file -diff --git a/drivers/media/pci/cx23885/cx23885-f300.h b/drivers/media/pci/cx23885/cx23885-f300.h -index e73344c..f93f37d 100644 ---- a/drivers/media/pci/cx23885/cx23885-f300.h -+++ b/drivers/media/pci/cx23885/cx23885-f300.h -@@ -1,2 +1,8 @@ -+extern int dvbsky_set_voltage_sec(struct dvb_frontend *fe, -+ fe_sec_voltage_t voltage); -+ -+extern int bst_set_voltage(struct dvb_frontend *fe, -+ fe_sec_voltage_t voltage); -+ - extern int f300_set_voltage(struct dvb_frontend *fe, - fe_sec_voltage_t voltage); -diff --git a/drivers/media/pci/cx23885/cx23885-input.c b/drivers/media/pci/cx23885/cx23885-input.c -index 4f1055a..db3366b 100644 ---- a/drivers/media/pci/cx23885/cx23885-input.c -+++ b/drivers/media/pci/cx23885/cx23885-input.c -@@ -89,6 +89,11 @@ void cx23885_input_rx_work_handler(struct cx23885_dev *dev, u32 events) + #define GPIO_0 0x00000001 + #define GPIO_1 0x00000002 +@@ -229,7 +235,7 @@ + */ + u32 clk_freq; + struct cx23885_input input[MAX_CX23885_INPUT]; +- int ci_type; /* for NetUP */ ++ int ci_type; /* 1 and 2 for NetUP, 3 for DVBSky. */ + /* Force bottom field first during DMA (888 workaround) */ + u32 force_bff; + }; +diff -urN a/drivers/media/pci/cx23885/cx23885-input.c b/drivers/media/pci/cx23885/cx23885-input.c +--- a/drivers/media/pci/cx23885/cx23885-input.c 2013-03-21 04:11:19.000000000 +0800 ++++ b/drivers/media/pci/cx23885/cx23885-input.c 2013-04-23 22:18:42.000000000 +0800 +@@ -89,6 +89,12 @@ case CX23885_BOARD_TERRATEC_CINERGY_T_PCIE_DUAL: case CX23885_BOARD_TEVII_S470: case CX23885_BOARD_HAUPPAUGE_HVR1250: @@ -5253,10 +5109,11 @@ index 4f1055a..db3366b 100644 + case CX23885_BOARD_DVBSKY_S952: + case CX23885_BOARD_DVBSKY_S950_CI: + case CX23885_BOARD_DVBSKY_C2800E_CI: ++ case CX23885_BOARD_DVBSKY_T9580: /* * The only boards we handle right now. However other boards * using the CX2388x integrated IR controller should be similar -@@ -140,6 +145,11 @@ static int cx23885_input_ir_start(struct cx23885_dev *dev) +@@ -140,6 +146,12 @@ case CX23885_BOARD_HAUPPAUGE_HVR1850: case CX23885_BOARD_HAUPPAUGE_HVR1290: case CX23885_BOARD_HAUPPAUGE_HVR1250: @@ -5264,11 +5121,12 @@ index 4f1055a..db3366b 100644 + case CX23885_BOARD_DVBSKY_S950: + case CX23885_BOARD_DVBSKY_S952: + case CX23885_BOARD_DVBSKY_S950_CI: -+ case CX23885_BOARD_DVBSKY_C2800E_CI: ++ case CX23885_BOARD_DVBSKY_C2800E_CI: ++ case CX23885_BOARD_DVBSKY_T9580: /* * The IR controller on this board only returns pulse widths. * Any other mode setting will fail to set up the device. -@@ -289,6 +299,17 @@ int cx23885_input_init(struct cx23885_dev *dev) +@@ -289,6 +301,18 @@ /* A guess at the remote */ rc_map = RC_MAP_TEVII_NEC; break; @@ -5276,7 +5134,8 @@ index 4f1055a..db3366b 100644 + case CX23885_BOARD_DVBSKY_S950: + case CX23885_BOARD_DVBSKY_S952: + case CX23885_BOARD_DVBSKY_S950_CI: -+ case CX23885_BOARD_DVBSKY_C2800E_CI: ++ case CX23885_BOARD_DVBSKY_C2800E_CI: ++ case CX23885_BOARD_DVBSKY_T9580: + /* Integrated CX2388[58] IR controller */ + driver_type = RC_DRIVER_IR_RAW; + allowed_protos = RC_BIT_ALL; @@ -5286,50 +5145,22 @@ index 4f1055a..db3366b 100644 default: return -ENODEV; } -diff --git a/drivers/media/pci/cx23885/cx23885.h b/drivers/media/pci/cx23885/cx23885.h -index 67f40d3..272dcab 100644 ---- a/drivers/media/pci/cx23885/cx23885.h -+++ b/drivers/media/pci/cx23885/cx23885.h -@@ -90,7 +90,12 @@ - #define CX23885_BOARD_TERRATEC_CINERGY_T_PCIE_DUAL 34 - #define CX23885_BOARD_TEVII_S471 35 - #define CX23885_BOARD_HAUPPAUGE_HVR1255_22111 36 --#define CX23885_BOARD_PROF_8000 37 -+#define CX23885_BOARD_BST_PS8512 37 -+#define CX23885_BOARD_DVBSKY_S952 38 -+#define CX23885_BOARD_DVBSKY_S950 39 -+#define CX23885_BOARD_DVBSKY_S950_CI 40 -+#define CX23885_BOARD_DVBSKY_C2800E_CI 41 -+#define CX23885_BOARD_PROF_8000 42 - - #define GPIO_0 0x00000001 - #define GPIO_1 0x00000002 -@@ -229,7 +234,7 @@ struct cx23885_board { - */ - u32 clk_freq; - struct cx23885_input input[MAX_CX23885_INPUT]; -- int ci_type; /* for NetUP */ -+ int ci_type; /* 1 and 2 for NetUP, 3 for DVBSky. */ - /* Force bottom field first during DMA (888 workaround) */ - u32 force_bff; - }; -diff --git a/drivers/media/pci/cx88/Kconfig b/drivers/media/pci/cx88/Kconfig -index d27fccb..04d2099 100644 ---- a/drivers/media/pci/cx88/Kconfig -+++ b/drivers/media/pci/cx88/Kconfig -@@ -57,6 +57,7 @@ config VIDEO_CX88_DVB - select DVB_ISL6421 if MEDIA_SUBDRV_AUTOSELECT - select DVB_S5H1411 if MEDIA_SUBDRV_AUTOSELECT +diff -urN a/drivers/media/pci/cx23885/Kconfig b/drivers/media/pci/cx23885/Kconfig +--- a/drivers/media/pci/cx23885/Kconfig 2013-03-21 04:11:19.000000000 +0800 ++++ b/drivers/media/pci/cx23885/Kconfig 2013-04-23 22:20:52.000000000 +0800 +@@ -23,6 +23,8 @@ + select DVB_STB6100 if MEDIA_SUBDRV_AUTOSELECT + select DVB_STV6110 if MEDIA_SUBDRV_AUTOSELECT select DVB_CX24116 if MEDIA_SUBDRV_AUTOSELECT + select DVB_M88DS3103 if MEDIA_SUBDRV_AUTOSELECT - select DVB_STV0299 if MEDIA_SUBDRV_AUTOSELECT - select DVB_STV0288 if MEDIA_SUBDRV_AUTOSELECT - select DVB_STB6000 if MEDIA_SUBDRV_AUTOSELECT -diff --git a/drivers/media/pci/cx88/cx88-cards.c b/drivers/media/pci/cx88/cx88-cards.c -index 0c25524..4989f52 100644 ---- a/drivers/media/pci/cx88/cx88-cards.c -+++ b/drivers/media/pci/cx88/cx88-cards.c -@@ -2309,6 +2309,18 @@ static const struct cx88_board cx88_boards[] = { ++ select DVB_M88DC2800 if MEDIA_SUBDRV_AUTOSELECT + select DVB_STV0900 if MEDIA_SUBDRV_AUTOSELECT + select DVB_DS3000 if MEDIA_SUBDRV_AUTOSELECT + select DVB_STV0367 if MEDIA_SUBDRV_AUTOSELECT +diff -urN a/drivers/media/pci/cx88/cx88-cards.c b/drivers/media/pci/cx88/cx88-cards.c +--- a/drivers/media/pci/cx88/cx88-cards.c 2013-03-21 04:11:19.000000000 +0800 ++++ b/drivers/media/pci/cx88/cx88-cards.c 2013-03-31 21:55:58.000000000 +0800 +@@ -2309,6 +2309,18 @@ } }, .mpeg = CX88_MPEG_DVB, }, @@ -5339,7 +5170,7 @@ index 0c25524..4989f52 100644 + .radio_type = UNSET, + .tuner_addr = ADDR_UNSET, + .radio_addr = ADDR_UNSET, -+ .input = {{ ++ .input = { { + .type = CX88_VMUX_DVB, + .vmux = 0, + } }, @@ -5348,7 +5179,7 @@ index 0c25524..4989f52 100644 }; /* ------------------------------------------------------------------ */ -@@ -2813,6 +2825,10 @@ static const struct cx88_subid cx88_subids[] = { +@@ -2813,6 +2825,10 @@ .subvendor = 0x1822, .subdevice = 0x0023, .card = CX88_BOARD_TWINHAN_VP1027_DVBS, @@ -5359,7 +5190,7 @@ index 0c25524..4989f52 100644 }, }; -@@ -3547,6 +3563,12 @@ static void cx88_card_setup(struct cx88_core *core) +@@ -3547,6 +3563,12 @@ cx_write(MO_SRST_IO, 1); msleep(100); break; @@ -5367,15 +5198,14 @@ index 0c25524..4989f52 100644 + cx_write(MO_GP1_IO, 0x808000); + msleep(100); + cx_write(MO_GP1_IO, 0x808080); -+ msleep(100); -+ break; ++ msleep(100); ++ break; } /*end switch() */ -diff --git a/drivers/media/pci/cx88/cx88-dvb.c b/drivers/media/pci/cx88/cx88-dvb.c -index 666f83b..db48d51 100644 ---- a/drivers/media/pci/cx88/cx88-dvb.c -+++ b/drivers/media/pci/cx88/cx88-dvb.c +diff -urN a/drivers/media/pci/cx88/cx88-dvb.c b/drivers/media/pci/cx88/cx88-dvb.c +--- a/drivers/media/pci/cx88/cx88-dvb.c 2013-03-21 04:11:19.000000000 +0800 ++++ b/drivers/media/pci/cx88/cx88-dvb.c 2013-01-31 10:42:51.000000000 +0800 @@ -54,6 +54,7 @@ #include "stv0288.h" #include "stb6000.h" @@ -5384,7 +5214,7 @@ index 666f83b..db48d51 100644 #include "stv0900.h" #include "stb6100.h" #include "stb6100_proc.h" -@@ -458,6 +459,56 @@ static int tevii_dvbs_set_voltage(struct dvb_frontend *fe, +@@ -458,6 +459,56 @@ return core->prev_set_voltage(fe, voltage); return 0; } @@ -5441,7 +5271,7 @@ index 666f83b..db48d51 100644 static int vp1027_set_voltage(struct dvb_frontend *fe, fe_sec_voltage_t voltage) -@@ -700,6 +751,11 @@ static struct ds3000_config tevii_ds3000_config = { +@@ -700,6 +751,11 @@ .set_ts_params = ds3000_set_ts_param, }; @@ -5453,7 +5283,7 @@ index 666f83b..db48d51 100644 static const struct stv0900_config prof_7301_stv0900_config = { .demod_address = 0x6a, /* demod_mode = 0,*/ -@@ -1470,6 +1526,35 @@ static int dvb_register(struct cx8802_dev *dev) +@@ -1470,6 +1526,35 @@ fe0->dvb.frontend->ops.set_voltage = tevii_dvbs_set_voltage; break; @@ -5489,35 +5319,10 @@ index 666f83b..db48d51 100644 case CX88_BOARD_OMICOM_SS4_PCI: case CX88_BOARD_TBS_8920: case CX88_BOARD_PROF_7300: -diff --git a/drivers/media/pci/cx88/cx88-input.c b/drivers/media/pci/cx88/cx88-input.c -index f29e18c..4de31ea 100644 ---- a/drivers/media/pci/cx88/cx88-input.c -+++ b/drivers/media/pci/cx88/cx88-input.c -@@ -419,6 +419,10 @@ int cx88_ir_init(struct cx88_core *core, struct pci_dev *pci) - rc_type = RC_BIT_NEC; - ir->sampling = 0xff00; /* address */ - break; -+ case CX88_BOARD_BST_PS8312: -+ ir_codes = RC_MAP_DVBSKY; -+ ir->sampling = 0xff00; /* address */ -+ break; - } - - if (!ir_codes) { -diff --git a/drivers/media/pci/cx88/cx88.h b/drivers/media/pci/cx88/cx88.h -index ba0dba4..58f0c11 100644 ---- a/drivers/media/pci/cx88/cx88.h -+++ b/drivers/media/pci/cx88/cx88.h -@@ -141,7 +141,7 @@ struct sram_channel { - u32 cnt1_reg; - u32 cnt2_reg; - }; --extern const struct sram_channel cx88_sram_channels[]; -+extern const struct sram_channel const cx88_sram_channels[]; - - /* ----------------------------------------------------------- */ - /* card configuration */ -@@ -238,6 +238,7 @@ extern const struct sram_channel cx88_sram_channels[]; +diff -urN a/drivers/media/pci/cx88/cx88.h b/drivers/media/pci/cx88/cx88.h +--- a/drivers/media/pci/cx88/cx88.h 2013-03-21 04:11:19.000000000 +0800 ++++ b/drivers/media/pci/cx88/cx88.h 2013-01-28 13:21:36.000000000 +0800 +@@ -238,6 +238,7 @@ #define CX88_BOARD_WINFAST_DTV1800H_XC4000 88 #define CX88_BOARD_WINFAST_TV2000_XP_GLOBAL_6F36 89 #define CX88_BOARD_WINFAST_TV2000_XP_GLOBAL_6F43 90 @@ -5525,11 +5330,35 @@ index ba0dba4..58f0c11 100644 enum cx88_itype { CX88_VMUX_COMPOSITE1 = 1, -diff --git a/drivers/media/rc/keymaps/Makefile b/drivers/media/rc/keymaps/Makefile -index ab84d66..d536fd8 100644 ---- a/drivers/media/rc/keymaps/Makefile -+++ b/drivers/media/rc/keymaps/Makefile -@@ -27,6 +27,7 @@ obj-$(CONFIG_RC_MAP) += rc-adstech-dvb-t-pci.o \ +diff -urN a/drivers/media/pci/cx88/cx88-input.c b/drivers/media/pci/cx88/cx88-input.c +--- a/drivers/media/pci/cx88/cx88-input.c 2013-03-21 04:11:19.000000000 +0800 ++++ b/drivers/media/pci/cx88/cx88-input.c 2013-01-26 14:52:03.000000000 +0800 +@@ -419,6 +419,10 @@ + rc_type = RC_BIT_NEC; + ir->sampling = 0xff00; /* address */ + break; ++ case CX88_BOARD_BST_PS8312: ++ ir_codes = RC_MAP_DVBSKY; ++ ir->sampling = 0xff00; /* address */ ++ break; + } + + if (!ir_codes) { +diff -urN a/drivers/media/pci/cx88/Kconfig b/drivers/media/pci/cx88/Kconfig +--- a/drivers/media/pci/cx88/Kconfig 2013-03-21 04:11:19.000000000 +0800 ++++ b/drivers/media/pci/cx88/Kconfig 2013-01-31 10:42:58.000000000 +0800 +@@ -57,6 +57,7 @@ + select DVB_ISL6421 if MEDIA_SUBDRV_AUTOSELECT + select DVB_S5H1411 if MEDIA_SUBDRV_AUTOSELECT + select DVB_CX24116 if MEDIA_SUBDRV_AUTOSELECT ++ select DVB_M88DS3103 if MEDIA_SUBDRV_AUTOSELECT + select DVB_STV0299 if MEDIA_SUBDRV_AUTOSELECT + select DVB_STV0288 if MEDIA_SUBDRV_AUTOSELECT + select DVB_STB6000 if MEDIA_SUBDRV_AUTOSELECT +diff -urN a/drivers/media/rc/keymaps/Makefile b/drivers/media/rc/keymaps/Makefile +--- a/drivers/media/rc/keymaps/Makefile 2013-03-21 04:11:19.000000000 +0800 ++++ b/drivers/media/rc/keymaps/Makefile 2013-03-31 22:22:13.000000000 +0800 +@@ -27,6 +27,7 @@ rc-dm1105-nec.o \ rc-dntv-live-dvb-t.o \ rc-dntv-live-dvbt-pro.o \ @@ -5537,11 +5366,9 @@ index ab84d66..d536fd8 100644 rc-em-terratec.o \ rc-encore-enltv2.o \ rc-encore-enltv.o \ -diff --git a/drivers/media/rc/keymaps/rc-dvbsky.c b/drivers/media/rc/keymaps/rc-dvbsky.c -new file mode 100644 -index 0000000..9a75cdc ---- /dev/null -+++ b/drivers/media/rc/keymaps/rc-dvbsky.c +diff -urN a/drivers/media/rc/keymaps/rc-dvbsky.c b/drivers/media/rc/keymaps/rc-dvbsky.c +--- a/drivers/media/rc/keymaps/rc-dvbsky.c 1970-01-01 08:00:00.000000000 +0800 ++++ b/drivers/media/rc/keymaps/rc-dvbsky.c 2013-01-26 14:52:49.000000000 +0800 @@ -0,0 +1,78 @@ +/* rc-dvbsky.c - Keytable for Dvbsky Remote Controllers + * @@ -5572,11 +5399,11 @@ index 0000000..9a75cdc + { 0x0006, KEY_6 }, + { 0x0007, KEY_7 }, + { 0x0008, KEY_8 }, -+ { 0x0009, KEY_9 }, ++ { 0x0009, KEY_9 }, + { 0x000a, KEY_MUTE }, + { 0x000d, KEY_OK }, + { 0x000b, KEY_STOP }, -+ { 0x000c, KEY_EXIT }, ++ { 0x000c, KEY_EXIT }, + { 0x000e, KEY_CAMERA }, /*Snap shot*/ + { 0x000f, KEY_SUBTITLE }, /*PIP*/ + { 0x0010, KEY_VOLUMEUP }, @@ -5592,9 +5419,9 @@ index 0000000..9a75cdc + { 0x0026, KEY_REWIND }, + { 0x0027, KEY_FASTFORWARD }, + { 0x0029, KEY_LAST }, -+ { 0x002b, KEY_MENU }, ++ { 0x002b, KEY_MENU }, + { 0x002c, KEY_EPG }, -+ { 0x002d, KEY_ZOOM }, ++ { 0x002d, KEY_ZOOM }, +}; + +static struct rc_map_list rc5_dvbsky_map = { @@ -5621,39 +5448,524 @@ index 0000000..9a75cdc + +MODULE_LICENSE("GPL"); +MODULE_AUTHOR("Nibble Max "); -diff --git a/drivers/media/usb/dvb-usb/Kconfig b/drivers/media/usb/dvb-usb/Kconfig -index fa0b293..60673c2 100644 ---- a/drivers/media/usb/dvb-usb/Kconfig -+++ b/drivers/media/usb/dvb-usb/Kconfig -@@ -262,6 +262,7 @@ config DVB_USB_DW2102 - select DVB_STV0288 if MEDIA_SUBDRV_AUTOSELECT - select DVB_STB6000 if MEDIA_SUBDRV_AUTOSELECT - select DVB_CX24116 if MEDIA_SUBDRV_AUTOSELECT -+ select DVB_M88DS3103 if MEDIA_SUBDRV_AUTOSELECT - select DVB_SI21XX if MEDIA_SUBDRV_AUTOSELECT - select DVB_TDA10023 if MEDIA_SUBDRV_AUTOSELECT - select DVB_MT312 if MEDIA_SUBDRV_AUTOSELECT -diff --git a/drivers/media/usb/dvb-usb/dw2102.c b/drivers/media/usb/dvb-usb/dw2102.c -index 097c186..a028166 100644 ---- a/drivers/media/usb/dvb-usb/dw2102.c -+++ b/drivers/media/usb/dvb-usb/dw2102.c -@@ -19,6 +19,7 @@ - #include "stb6000.h" - #include "eds1547.h" - #include "cx24116.h" +diff -urN a/drivers/media/usb/dvb-usb-v2/dvbsky.c b/drivers/media/usb/dvb-usb-v2/dvbsky.c +--- a/drivers/media/usb/dvb-usb-v2/dvbsky.c 1970-01-01 08:00:00.000000000 +0800 ++++ b/drivers/media/usb/dvb-usb-v2/dvbsky.c 2013-04-23 22:23:48.000000000 +0800 +@@ -0,0 +1,661 @@ ++/* ++ * Driver for DVBSky USB2.0 receiver ++ * ++ * Copyright (C) 2013 Max nibble ++ * ++ * CIMax code is copied and modified from: ++ * CIMax2(R) SP2 driver in conjunction with NetUp Dual DVB-S2 CI card ++ * Copyright (C) 2009 NetUP Inc. ++ * Copyright (C) 2009 Igor M. Liplianin ++ * Copyright (C) 2009 Abylay Ospan ++ * ++ * This program is free software; you can redistribute it and/or modify ++ * it under the terms of the GNU General Public License as published by ++ * the Free Software Foundation; either version 2 of the License, or ++ * (at your option) any later version. ++ * ++ * This program is distributed in the hope that it will be useful, ++ * but WITHOUT ANY WARRANTY; without even the implied warranty of ++ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ++ * GNU General Public License for more details. ++ * ++ * You should have received a copy of the GNU General Public License ++ * along with this program; if not, write to the Free Software ++ * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. ++ */ ++ ++#include "dvb_ca_en50221.h" ++#include "dvb_usb.h" +#include "m88ds3103.h" - #include "tda1002x.h" - #include "mt312.h" - #include "zl10039.h" -@@ -830,6 +831,39 @@ static int su3000_read_mac_address(struct dvb_usb_device *d, u8 mac[6]) - return 0; - } - -+static int dvbsky_read_mac_address(struct dvb_usb_device *d, u8 mac[6]) ++ ++static int dvbsky_debug; ++module_param(dvbsky_debug, int, 0644); ++MODULE_PARM_DESC(dvbsky_debug, "Activates dvbsky usb debugging (default:0)"); ++ ++#define DVBSKY_CI_CTL 0x04 ++#define DVBSKY_CI_RD 1 ++ ++#define dprintk(args...) \ ++ do { \ ++ if (dvbsky_debug) \ ++ printk(KERN_INFO "dvbsky_usb: " args); \ ++ } while (0) ++ ++DVB_DEFINE_MOD_OPT_ADAPTER_NR(adapter_nr); ++ ++struct dvbsky_state { ++ struct mutex stream_mutex; ++ u8 has_ci; ++ u8 ci_attached; ++ struct dvb_ca_en50221 ci; ++ unsigned long next_status_checked_time; ++ u8 ci_i2c_addr; ++ u8 current_ci_flag; ++ int ci_status; ++}; ++ ++static int dvbsky_stream_ctrl(struct dvb_usb_device *d, u8 onoff) +{ -+ int i; ++ struct dvbsky_state *state = d_to_priv(d); ++ int ret; ++ u8 obuf_pre[3] = { 0x37, 0, 0 }; ++ u8 obuf_post[3] = { 0x36, 3, 0 }; ++ dprintk("%s() -off \n", __func__); ++ mutex_lock(&state->stream_mutex); ++ ret = dvb_usbv2_generic_write(d, obuf_pre, 3); ++ if (!ret && onoff) { ++ msleep(10); ++ ret = dvb_usbv2_generic_write(d, obuf_post, 3); ++ dprintk("%s() -on \n", __func__); ++ } ++ mutex_unlock(&state->stream_mutex); ++ return ret; ++} ++ ++/* CI opertaions */ ++static int dvbsky_ci_read_i2c(struct i2c_adapter *i2c_adap, u8 addr, u8 reg, ++ u8 *buf, int len) ++{ ++ int ret; ++ struct i2c_msg msg[] = { ++ { ++ .addr = addr, ++ .flags = 0, ++ .buf = ®, ++ .len = 1 ++ }, { ++ .addr = addr, ++ .flags = I2C_M_RD, ++ .buf = buf, ++ .len = len ++ } ++ }; ++ ++ ret = i2c_transfer(i2c_adap, msg, 2); ++ ++ if (ret != 2) { ++ dprintk("%s: error, Reg = 0x%02x, Status = %d\n", __func__, reg, ret); ++ return -1; ++ } ++ return 0; ++} ++ ++static int dvbsky_ci_write_i2c(struct i2c_adapter *i2c_adap, u8 addr, u8 reg, ++ u8 *buf, int len) ++{ ++ int ret; ++ u8 buffer[len + 1]; ++ ++ struct i2c_msg msg = { ++ .addr = addr, ++ .flags = 0, ++ .buf = &buffer[0], ++ .len = len + 1 ++ }; ++ ++ buffer[0] = reg; ++ memcpy(&buffer[1], buf, len); ++ ++ ret = i2c_transfer(i2c_adap, &msg, 1); ++ ++ if (ret != 1) { ++ dprintk("%s: error, Reg=[0x%02x], Status=%d\n", __func__, reg, ret); ++ return -1; ++ } ++ return 0; ++} ++ ++static int dvbsky_ci_op_cam(struct dvb_ca_en50221 *ci, int slot, ++ u8 flag, u8 read, int addr, u8 data) ++{ ++ struct dvb_usb_device *d = ci->data; ++ struct dvbsky_state *state = d_to_priv(d); ++ u8 store; ++ int ret; ++ u8 command[4], respond[2], command_size, respond_size; ++ ++ /*dprintk("%s()\n", __func__);*/ ++ if (0 != slot) ++ return -EINVAL; ++ ++ if (state->current_ci_flag != flag) { ++ ret = dvbsky_ci_read_i2c(&d->i2c_adap, state->ci_i2c_addr, ++ 0, &store, 1); ++ if (ret != 0) ++ return ret; ++ ++ store &= ~0x0c; ++ store |= flag; ++ ++ ret = dvbsky_ci_write_i2c(&d->i2c_adap, state->ci_i2c_addr, ++ 0, &store, 1); ++ if (ret != 0) ++ return ret; ++ } ++ state->current_ci_flag = flag; ++ ++ command[1] = (u8)((addr >> 8) & 0xff); /*high part of address*/ ++ command[2] = (u8)(addr & 0xff); /*low part of address*/ ++ if (read) { ++ command[0] = 0x71; ++ command_size = 3; ++ respond_size = 2; ++ } else { ++ command[0] = 0x70; ++ command[3] = data; ++ command_size = 4; ++ respond_size = 1; ++ } ++ ret = dvb_usbv2_generic_rw(d, command, command_size, respond, respond_size); ++ ++ return (read) ? respond[1] : 0; ++} ++ ++static int dvbsky_ci_read_attribute_mem(struct dvb_ca_en50221 *ci, ++ int slot, int addr) ++{ ++ return dvbsky_ci_op_cam(ci, slot, 0, DVBSKY_CI_RD, addr, 0); ++} ++ ++static int dvbsky_ci_write_attribute_mem(struct dvb_ca_en50221 *ci, ++ int slot, int addr, u8 data) ++{ ++ return dvbsky_ci_op_cam(ci, slot, 0, 0, addr, data); ++} ++ ++static int dvbsky_ci_read_cam_ctl(struct dvb_ca_en50221 *ci, int slot, u8 addr) ++{ ++ return dvbsky_ci_op_cam(ci, slot, DVBSKY_CI_CTL, DVBSKY_CI_RD, addr, 0); ++} ++ ++static int dvbsky_ci_write_cam_ctl(struct dvb_ca_en50221 *ci, int slot, ++ u8 addr, u8 data) ++{ ++ return dvbsky_ci_op_cam(ci, slot, DVBSKY_CI_CTL, 0, addr, data); ++} ++ ++static int dvbsky_ci_slot_reset(struct dvb_ca_en50221 *ci, int slot) ++{ ++ struct dvb_usb_device *d = ci->data; ++ struct dvbsky_state *state = d_to_priv(d); ++ u8 buf = 0x80; ++ int ret; ++ dprintk("%s() slot=%d\n", __func__, slot); ++ ++ if (0 != slot) ++ return -EINVAL; ++ ++ udelay(500); ++ ret = dvbsky_ci_write_i2c(&d->i2c_adap, state->ci_i2c_addr, ++ 0, &buf, 1); ++ ++ if (ret != 0) ++ return ret; ++ ++ udelay(500); ++ ++ buf = 0x00; ++ ret = dvbsky_ci_write_i2c(&d->i2c_adap, state->ci_i2c_addr, ++ 0, &buf, 1); ++ msleep(1000); ++ dprintk("%s() slot=%d complete\n", __func__, slot); ++ return 0; ++ ++} ++ ++static int dvbsky_ci_slot_shutdown(struct dvb_ca_en50221 *ci, int slot) ++{ ++ /* not implemented */ ++ dprintk("%s()\n", __func__); ++ return 0; ++} ++ ++static int dvbsky_ci_slot_ts_enable(struct dvb_ca_en50221 *ci, int slot) ++{ ++ struct dvb_usb_device *d = ci->data; ++ struct dvbsky_state *state = d_to_priv(d); ++ u8 buf; ++ int ret; ++ ++ dprintk("%s()\n", __func__); ++ if (0 != slot) ++ return -EINVAL; ++ ++ dvbsky_ci_read_i2c(&d->i2c_adap, state->ci_i2c_addr, ++ 0, &buf, 1); ++ buf |= 0x60; ++ ++ ret = dvbsky_ci_write_i2c(&d->i2c_adap, state->ci_i2c_addr, ++ 0, &buf, 1); ++ return ret; ++} ++ ++static int dvbsky_ci_poll_slot_status(struct dvb_ca_en50221 *ci, int slot, ++ int open) ++{ ++ struct dvb_usb_device *d = ci->data; ++ struct dvbsky_state *state = d_to_priv(d); ++ int ret = 0; ++ u8 buf = 0; ++ /*dprintk("%s()\n", __func__);*/ ++ ++ /* CAM module INSERT/REMOVE processing. slow operation because of i2c ++ * transfers */ ++ if (time_after(jiffies, state->next_status_checked_time)) { ++ ret = dvbsky_ci_read_i2c(&d->i2c_adap, state->ci_i2c_addr, ++ 0, &buf, 1); ++ ++ /*dprintk("%s() status=%x\n", __func__, buf);*/ ++ ++ state->next_status_checked_time = jiffies ++ + msecs_to_jiffies(1000); ++ ++ if (ret != 0) ++ return 0; ++ ++ if (buf & 1) { ++ state->ci_status = DVB_CA_EN50221_POLL_CAM_PRESENT | ++ DVB_CA_EN50221_POLL_CAM_READY; ++ } ++ else ++ state->ci_status = 0; ++ } ++ /*dprintk("%s() ret=%x\n", __func__, state->ci_status);*/ ++ return state->ci_status; ++} ++ ++static int dvbsky_ci_init(struct dvb_usb_device *d) ++{ ++ struct dvbsky_state *state = d_to_priv(d); ++ int ret; ++ u8 cimax_init[34] = { ++ 0x00, /* module A control*/ ++ 0x00, /* auto select mask high A */ ++ 0x00, /* auto select mask low A */ ++ 0x00, /* auto select pattern high A */ ++ 0x00, /* auto select pattern low A */ ++ 0x44, /* memory access time A */ ++ 0x00, /* invert input A */ ++ 0x00, /* RFU */ ++ 0x00, /* RFU */ ++ 0x00, /* module B control*/ ++ 0x00, /* auto select mask high B */ ++ 0x00, /* auto select mask low B */ ++ 0x00, /* auto select pattern high B */ ++ 0x00, /* auto select pattern low B */ ++ 0x44, /* memory access time B */ ++ 0x00, /* invert input B */ ++ 0x00, /* RFU */ ++ 0x00, /* RFU */ ++ 0x00, /* auto select mask high Ext */ ++ 0x00, /* auto select mask low Ext */ ++ 0x00, /* auto select pattern high Ext */ ++ 0x00, /* auto select pattern low Ext */ ++ 0x00, /* RFU */ ++ 0x02, /* destination - module A */ ++ 0x01, /* power on (use it like store place) */ ++ 0x00, /* RFU */ ++ 0x00, /* int status read only */ ++ 0x00, /* Max: Disable the interrupt in USB solution.*/ ++ 0x05, /* EXTINT=active-high, INT=push-pull */ ++ 0x00, /* USCG1 */ ++ 0x04, /* ack active low */ ++ 0x00, /* LOCK = 0 */ ++ 0x22, /* serial mode, rising in, rising out, MSB first*/ ++ 0x00 /* synchronization */ ++ }; ++ dprintk("%s()\n", __func__); ++ state->current_ci_flag = 0xff; ++ state->ci_status = 0; ++ state->next_status_checked_time = jiffies + msecs_to_jiffies(1000); ++ state->ci_i2c_addr = 0x40; ++ ++ state->ci.owner = THIS_MODULE; ++ state->ci.read_attribute_mem = dvbsky_ci_read_attribute_mem; ++ state->ci.write_attribute_mem = dvbsky_ci_write_attribute_mem; ++ state->ci.read_cam_control = dvbsky_ci_read_cam_ctl; ++ state->ci.write_cam_control = dvbsky_ci_write_cam_ctl; ++ state->ci.slot_reset = dvbsky_ci_slot_reset; ++ state->ci.slot_shutdown = dvbsky_ci_slot_shutdown; ++ state->ci.slot_ts_enable = dvbsky_ci_slot_ts_enable; ++ state->ci.poll_slot_status = dvbsky_ci_poll_slot_status; ++ state->ci.data = d; ++ ++ ret = dvbsky_ci_write_i2c(&d->i2c_adap, state->ci_i2c_addr, ++ 0, &cimax_init[0], 34); ++ /* lock registers */ ++ ret |= dvbsky_ci_write_i2c(&d->i2c_adap, state->ci_i2c_addr, ++ 0x1f, &cimax_init[0x18], 1); ++ /* power on slots */ ++ ret |= dvbsky_ci_write_i2c(&d->i2c_adap, state->ci_i2c_addr, ++ 0x18, &cimax_init[0x18], 1); ++ if (0 != ret) ++ return ret; ++ ++ ret = dvb_ca_en50221_init(&d->adapter[0].dvb_adap, &state->ci, 0, 1); ++ if (ret) ++ return ret; ++ state->ci_attached = 1; ++ dprintk("%s() complete.\n", __func__); ++ return 0; ++} ++ ++static void dvbsky_ci_release(struct dvb_usb_device *d) ++{ ++ struct dvbsky_state *state = d_to_priv(d); ++ ++ /* detach CI */ ++ if (state->ci_attached) ++ dvb_ca_en50221_release(&state->ci); ++ ++ return; ++} ++ ++static int dvbsky_streaming_ctrl(struct dvb_frontend *fe, int onoff) ++{ ++ struct dvb_usb_device *d = fe_to_d(fe); ++ /*dprintk("%s() %d\n", __func__, onoff);*/ ++ return dvbsky_stream_ctrl(d, (onoff == 0) ? 0 : 1); ++} ++ ++/* GPIO */ ++static int dvbsky_gpio_ctrl(struct dvb_usb_device *d, u8 gport, u8 value) ++{ ++ u8 obuf[64], ibuf[64]; ++ obuf[0] = 0x0e; ++ obuf[1] = gport; ++ obuf[2] = value; ++ return dvb_usbv2_generic_rw(d, obuf, 3, ibuf, 1); ++} ++ ++/* I2C */ ++static int dvbsky_i2c_xfer(struct i2c_adapter *adap, struct i2c_msg msg[], ++ int num) ++{ ++ struct dvb_usb_device *d = i2c_get_adapdata(adap); ++ int ret = 0; ++ u8 ibuf[64], obuf[64]; ++ ++ if (mutex_lock_interruptible(&d->i2c_mutex) < 0) ++ return -EAGAIN; ++ ++ if (num > 2) { ++ printk(KERN_ERR "dvbsky_usb: too many i2c messages[%d] than 2.", num); ++ ret = -EOPNOTSUPP; ++ goto i2c_error; ++ } ++ ++ if(num == 1) { ++ if (msg[0].len > 60) { ++ printk(KERN_ERR "dvbsky_usb: too many i2c bytes[%d] than 60.", msg[0].len); ++ ret = -EOPNOTSUPP; ++ goto i2c_error; ++ } ++ if (msg[0].flags & I2C_M_RD) { ++ /* single read */ ++ obuf[0] = 0x09; ++ obuf[1] = 0; ++ obuf[2] = msg[0].len; ++ obuf[3] = msg[0].addr; ++ ret = dvb_usbv2_generic_rw(d, obuf, 4, ibuf, msg[0].len + 1); ++ /*dprintk("%s(): read status = %d\n", __func__, ibuf[0]);*/ ++ if (!ret) ++ memcpy(msg[0].buf, &ibuf[1], msg[0].len); ++ } else { ++ /* write */ ++ obuf[0] = 0x08; ++ obuf[1] = msg[0].addr; ++ obuf[2] = msg[0].len; ++ memcpy(&obuf[3], msg[0].buf, msg[0].len); ++ ret = dvb_usbv2_generic_rw(d, obuf, msg[0].len + 3, ibuf, 1); ++ /*dprintk("%s(): write status = %d\n", __func__, ibuf[0]);*/ ++ } ++ } else { ++ if ((msg[0].len > 60) || (msg[1].len > 60)) { ++ printk(KERN_ERR "dvbsky_usb: too many i2c bytes[w-%d][r-%d] than 60.", msg[0].len, msg[1].len); ++ ret = -EOPNOTSUPP; ++ goto i2c_error; ++ } ++ /* write then read */ ++ obuf[0] = 0x09; ++ obuf[1] = msg[0].len; ++ obuf[2] = msg[1].len; ++ obuf[3] = msg[0].addr; ++ memcpy(&obuf[4], msg[0].buf, msg[0].len); ++ ret = dvb_usbv2_generic_rw(d, obuf, msg[0].len + 4, ibuf, msg[1].len + 1); ++ /*dprintk("%s(): write then read status = %d\n", __func__, ibuf[0]);*/ ++ if (!ret) ++ memcpy(msg[1].buf, &ibuf[1], msg[1].len); ++ } ++i2c_error: ++ mutex_unlock(&d->i2c_mutex); ++ return (ret) ? ret : num; ++} ++ ++static u32 dvbsky_i2c_func(struct i2c_adapter *adapter) ++{ ++ return I2C_FUNC_I2C; ++} ++ ++static struct i2c_algorithm dvbsky_i2c_algo = { ++ .master_xfer = dvbsky_i2c_xfer, ++ .functionality = dvbsky_i2c_func, ++}; ++ ++static int dvbsky_rc_query(struct dvb_usb_device *d) ++{ ++ u32 code = 0xffff; ++ u8 obuf[2], ibuf[2], toggle; ++ int ret; ++ obuf[0] = 0x10; ++ ret = dvb_usbv2_generic_rw(d, obuf, 1, ibuf, 2); ++ if(ret == 0) ++ code = (ibuf[0] << 8) | ibuf[1]; ++ ++ if (code != 0xffff) { ++ dprintk("rc code: %x", code); ++ toggle = (code & 0x800) ? 1 : 0; ++ code &= 0x3f; ++ rc_keydown(d->rc_dev, code, toggle); ++ } ++ return 0; ++} ++ ++static int dvbsky_get_rc_config(struct dvb_usb_device *d, struct dvb_usb_rc *rc) ++{ ++ rc->allowed_protos = RC_BIT_RC5; ++ rc->query = dvbsky_rc_query; ++ rc->interval = 300; ++ return 0; ++} ++ ++static int dvbsky_sync_ctrl(struct dvb_frontend *fe) ++{ ++ struct dvb_usb_device *d = fe_to_d(fe); ++ return dvbsky_stream_ctrl(d, 1); ++} ++ ++static int dvbsky_usb_set_voltage(struct dvb_frontend *fe, fe_sec_voltage_t voltage) ++{ ++ struct dvb_usb_device *d = fe_to_d(fe); ++ u8 value; ++ ++ if (voltage == SEC_VOLTAGE_OFF) ++ value = 0; ++ else ++ value = 1; ++ return dvbsky_gpio_ctrl(d, 0x80, value); ++} ++ ++static int dvbsky_read_mac_addr(struct dvb_usb_adapter *adap, u8 mac[6]) ++{ ++ struct dvb_usb_device *d = adap_to_d(adap); + u8 obuf[] = { 0x1e, 0x00 }; -+ u8 ibuf[] = { 0 }; ++ u8 ibuf[6] = { 0 }; + struct i2c_msg msg[] = { + { + .addr = 0x51, @@ -5664,327 +5976,174 @@ index 097c186..a028166 100644 + .addr = 0x51, + .flags = I2C_M_RD, + .buf = ibuf, -+ .len = 1, ++ .len = 6, + + } + }; ++ ++ if (i2c_transfer(&d->i2c_adap, msg, 2) == 2) ++ memcpy(mac, ibuf, 6); + -+ for (i = 0; i < 6; i++) { -+ obuf[1] = i; -+ if (i2c_transfer(&d->i2c_adap, msg, 2) != 2) -+ break; -+ else -+ mac[i] = ibuf[0]; -+ -+ debug_dump(mac, 6, printk); -+ } -+ ++ printk(KERN_INFO "dvbsky_usb MAC address=%pM\n", mac); ++ + return 0; +} + - static int su3000_identify_state(struct usb_device *udev, - struct dvb_usb_device_properties *props, - struct dvb_usb_device_description **desc, -@@ -878,6 +912,43 @@ static int s660_set_voltage(struct dvb_frontend *fe, fe_sec_voltage_t voltage) - return 0; - } - -+static int bstusb_set_voltage(struct dvb_frontend *fe, fe_sec_voltage_t voltage) -+{ -+ -+ struct dvb_usb_adapter *udev_adap = -+ (struct dvb_usb_adapter *)(fe->dvb->priv); -+ -+ u8 obuf[3] = { 0xe, 0x80, 0 }; -+ u8 ibuf[] = { 0 }; -+ -+ info("US6830: %s!\n", __func__); -+ -+ if (voltage == SEC_VOLTAGE_OFF) -+ obuf[2] = 0; -+ else -+ obuf[2] = 1; -+ -+ if (dvb_usb_generic_rw(udev_adap->dev, obuf, 3, ibuf, 1, 0) < 0) -+ err("command 0x0e transfer failed."); -+ -+ return 0; -+} -+ -+static int bstusb_restart(struct dvb_frontend *fe) -+{ -+ -+ struct dvb_usb_adapter *udev_adap = -+ (struct dvb_usb_adapter *)(fe->dvb->priv); -+ -+ u8 obuf[3] = { 0x36, 3, 0 }; -+ u8 ibuf[] = { 0 }; -+ -+ if (dvb_usb_generic_rw(udev_adap->dev, obuf, 3, ibuf, 1, 0) < 0) -+ err("command 0x36 transfer failed."); -+ -+ return 0; -+} -+ - static void dw210x_led_ctrl(struct dvb_frontend *fe, int offon) - { - static u8 led_off[] = { 0 }; -@@ -983,6 +1054,24 @@ static struct ds3000_config su3000_ds3000_config = { - .ci_mode = 1, - }; - -+static struct m88ds3103_config US6830_ds3103_config = { ++static struct m88ds3103_config dvbsky_usb_ds3103_config = { + .demod_address = 0x68, + .ci_mode = 1, + .pin_ctrl = 0x83, + .ts_mode = 0, -+ .start_ctrl = bstusb_restart, -+ .set_voltage = bstusb_set_voltage, ++ .start_ctrl = dvbsky_sync_ctrl, ++ .set_voltage = dvbsky_usb_set_voltage, +}; + -+static struct m88ds3103_config US6832_ds3103_config = { -+ .demod_address = 0x68, -+ .ci_mode = 1, -+ .pin_ctrl = 0x80, -+ .ts_mode = 0, -+ .start_ctrl = bstusb_restart, -+ .set_voltage = bstusb_set_voltage, -+}; -+ - static int dw2104_frontend_attach(struct dvb_usb_adapter *d) - { - struct dvb_tuner_ops *tuner_ops = NULL; -@@ -1217,6 +1306,87 @@ static int su3000_frontend_attach(struct dvb_usb_adapter *d) - return 0; - } - -+static int US6830_frontend_attach(struct dvb_usb_adapter *d) ++static int dvbsky_s960_attach(struct dvb_usb_adapter *adap) +{ -+ u8 obuf[3] = { 0xe, 0x04, 1 }; -+ u8 ibuf[] = { 0 }; -+ -+ info("US6830: %s!\n", __func__); -+ -+ if (dvb_usb_generic_rw(d->dev, obuf, 3, ibuf, 1, 0) < 0) -+ err("command 0x0e transfer failed."); -+ -+ obuf[0] = 0xe; -+ obuf[1] = 0x83; -+ obuf[2] = 0; ++ struct dvbsky_state *state = adap_to_priv(adap); ++ struct dvb_usb_device *d = adap_to_d(adap); ++ int ret = 0; + -+ if (dvb_usb_generic_rw(d->dev, obuf, 3, ibuf, 1, 0) < 0) -+ err("command 0x0e transfer failed."); ++ dprintk("%s()\n", __func__); + ++ dvbsky_gpio_ctrl(d, 0x04, 1); ++ ++ dvbsky_gpio_ctrl(d, 0x83, 0); ++ msleep(50); ++ dvbsky_gpio_ctrl(d, 0x83, 1); + msleep(20); ++ ++ adap->fe[0] = dvb_attach(m88ds3103_attach, ++ &dvbsky_usb_ds3103_config, ++ &d->i2c_adap); ++ if (!adap->fe[0]) { ++ printk(KERN_ERR "dvbsky_s960_attach fail."); ++ ret = -ENODEV; ++ } ++ ++ state->has_ci = 0; + -+ obuf[0] = 0xe; -+ obuf[1] = 0x83; -+ obuf[2] = 1; ++ return ret; ++} + -+ if (dvb_usb_generic_rw(d->dev, obuf, 3, ibuf, 1, 0) < 0) -+ err("command 0x0e transfer failed."); ++static int dvbsky_identify_state(struct dvb_usb_device *d, const char **name) ++{ ++ return WARM; ++} + -+ obuf[0] = 0x51; ++static int dvbsky_init(struct dvb_usb_device *d) ++{ ++ struct dvbsky_state *state = d_to_priv(d); ++ int ret; + -+ if (dvb_usb_generic_rw(d->dev, obuf, 1, ibuf, 1, 0) < 0) -+ err("command 0x51 transfer failed."); -+ -+ d->fe_adap[0].fe = dvb_attach(m88ds3103_attach, &US6830_ds3103_config, -+ &d->dev->i2c_adap); -+ if (d->fe_adap[0].fe == NULL) -+ return -EIO; -+ -+ info("Attached M88DS3103!\n"); ++ /* use default interface */ ++ ret = usb_set_interface(d->udev, 0, 0); ++ if (ret) ++ return ret; + ++ mutex_init(&state->stream_mutex); ++ ++ /* attach CI */ ++ if (state->has_ci) { ++ dvbsky_gpio_ctrl(d, 0xc0, 1); ++ msleep(100); ++ dvbsky_gpio_ctrl(d, 0xc0, 0); ++ msleep(50); ++ state->ci_attached = 0; ++ ret = dvbsky_ci_init(d); ++ if (ret) ++ return ret; ++ } + return 0; +} + -+static int US6832_frontend_attach(struct dvb_usb_adapter *d) ++static void dvbsky_exit(struct dvb_usb_device *d) +{ -+ u8 obuf[3] = { 0xe, 0x04, 1 }; -+ u8 ibuf[] = { 0 }; -+ -+ info("US6832: %s!\n", __func__); -+ -+ if (dvb_usb_generic_rw(d->dev, obuf, 3, ibuf, 1, 0) < 0) -+ err("command 0x0e transfer failed."); -+ -+ obuf[0] = 0xe; -+ obuf[1] = 0x83; -+ obuf[2] = 0; -+ -+ if (dvb_usb_generic_rw(d->dev, obuf, 3, ibuf, 1, 0) < 0) -+ err("command 0x0e transfer failed."); -+ -+ msleep(20); -+ obuf[0] = 0xe; -+ obuf[1] = 0x83; -+ obuf[2] = 1; -+ -+ if (dvb_usb_generic_rw(d->dev, obuf, 3, ibuf, 1, 0) < 0) -+ err("command 0x0e transfer failed."); -+ -+ obuf[0] = 0x51; -+ -+ if (dvb_usb_generic_rw(d->dev, obuf, 1, ibuf, 1, 0) < 0) -+ err("command 0x51 transfer failed."); -+ -+ d->fe_adap[0].fe = dvb_attach(m88ds3103_attach, &US6832_ds3103_config, -+ &d->dev->i2c_adap); -+ if (d->fe_adap[0].fe == NULL) -+ return -EIO; -+ -+ info("Attached M88DS3103!\n"); -+ -+ return 0; ++ return dvbsky_ci_release(d); +} + - static int dw2102_tuner_attach(struct dvb_usb_adapter *adap) - { - dvb_attach(dvb_pll_attach, adap->fe_adap[0].fe, 0x60, -@@ -1455,6 +1625,9 @@ enum dw2102_table_entry { - TEVII_S480_1, - TEVII_S480_2, - X3M_SPC1400HD, -+ BST_US6830HD, -+ BST_US6831HD, -+ BST_US6832HD, - }; - - static struct usb_device_id dw2102_table[] = { -@@ -1474,6 +1647,9 @@ static struct usb_device_id dw2102_table[] = { - [TEVII_S480_1] = {USB_DEVICE(0x9022, USB_PID_TEVII_S480_1)}, - [TEVII_S480_2] = {USB_DEVICE(0x9022, USB_PID_TEVII_S480_2)}, - [X3M_SPC1400HD] = {USB_DEVICE(0x1f4d, 0x3100)}, -+ [BST_US6830HD] = {USB_DEVICE(0x0572, 0x6830)}, -+ [BST_US6831HD] = {USB_DEVICE(0x0572, 0x6831)}, -+ [BST_US6832HD] = {USB_DEVICE(0x0572, 0x6832)}, - { } - }; - -@@ -1883,6 +2059,106 @@ static struct dvb_usb_device_properties su3000_properties = { - } - }; - -+static struct dvb_usb_device_properties US6830_properties = { -+ .caps = DVB_USB_IS_AN_I2C_ADAPTER, -+ .usb_ctrl = DEVICE_SPECIFIC, -+ .size_of_priv = sizeof(struct su3000_state), -+ .power_ctrl = su3000_power_ctrl, -+ .num_adapters = 1, -+ .identify_state = su3000_identify_state, -+ .i2c_algo = &su3000_i2c_algo, -+ -+ .rc.legacy = { -+ .rc_map_table = rc_map_su3000_table, -+ .rc_map_size = ARRAY_SIZE(rc_map_su3000_table), -+ .rc_interval = 150, -+ .rc_query = dw2102_rc_query, -+ }, -+ -+ .read_mac_address = dvbsky_read_mac_address, ++/* DVB USB Driver stuff */ ++static struct dvb_usb_device_properties dvbsky_s960_props = { ++ .driver_name = KBUILD_MODNAME, ++ .owner = THIS_MODULE, ++ .adapter_nr = adapter_nr, ++ .size_of_priv = sizeof(struct dvbsky_state), + + .generic_bulk_ctrl_endpoint = 0x01, -+ ++ .generic_bulk_ctrl_endpoint_response = 0x81, ++ ++ .i2c_algo = &dvbsky_i2c_algo, ++ .frontend_attach = dvbsky_s960_attach, ++ .init = dvbsky_init, ++ .get_rc_config = dvbsky_get_rc_config, ++ .streaming_ctrl = dvbsky_streaming_ctrl, ++ .identify_state = dvbsky_identify_state, ++ .exit = dvbsky_exit, ++ .read_mac_address = dvbsky_read_mac_addr, ++ ++ .num_adapters = 1, + .adapter = { + { -+ .num_frontends = 1, -+ .fe = {{ -+ .streaming_ctrl = su3000_streaming_ctrl, -+ .frontend_attach = US6830_frontend_attach, -+ .stream = { -+ .type = USB_BULK, -+ .count = 8, -+ .endpoint = 0x82, -+ .u = { -+ .bulk = { -+ .buffersize = 4096, -+ } -+ } -+ } -+ }}, ++ .stream = DVB_USB_STREAM_BULK(0x82, 8, 4096), + } -+ }, -+ .num_device_descs = 2, -+ .devices = { -+ { "Bestunar US6830 HD", -+ { &dw2102_table[BST_US6830HD], NULL }, -+ { NULL }, -+ }, -+ { "Bestunar US6831 HD", -+ { &dw2102_table[BST_US6831HD], NULL }, -+ { NULL }, -+ }, + } +}; + -+static struct dvb_usb_device_properties US6832_properties = { -+ .caps = DVB_USB_IS_AN_I2C_ADAPTER, -+ .usb_ctrl = DEVICE_SPECIFIC, -+ .size_of_priv = sizeof(struct su3000_state), -+ .power_ctrl = su3000_power_ctrl, -+ .num_adapters = 1, -+ .identify_state = su3000_identify_state, -+ .i2c_algo = &su3000_i2c_algo, ++static const struct usb_device_id dvbsky_id_table[] = { ++ { DVB_USB_DEVICE(0x0572, 0x6831, ++ &dvbsky_s960_props, "DVBSky S960/S860", RC_MAP_DVBSKY) }, ++ { } ++}; ++MODULE_DEVICE_TABLE(usb, dvbsky_id_table); + -+ .rc.legacy = { -+ .rc_map_table = rc_map_su3000_table, -+ .rc_map_size = ARRAY_SIZE(rc_map_su3000_table), -+ .rc_interval = 150, -+ .rc_query = dw2102_rc_query, -+ }, -+ -+ .read_mac_address = dvbsky_read_mac_address, -+ -+ .generic_bulk_ctrl_endpoint = 0x01, -+ -+ .adapter = { -+ { -+ .num_frontends = 1, -+ .fe = {{ -+ .streaming_ctrl = su3000_streaming_ctrl, -+ .frontend_attach = US6832_frontend_attach, -+ .stream = { -+ .type = USB_BULK, -+ .count = 8, -+ .endpoint = 0x82, -+ .u = { -+ .bulk = { -+ .buffersize = 4096, -+ } -+ } -+ } -+ }}, -+ } -+ }, -+ .num_device_descs = 1, -+ .devices = { -+ { "Bestunar US6832 HD", -+ { &dw2102_table[BST_US6832HD], NULL }, -+ { NULL }, -+ }, -+ } ++static struct usb_driver dvbsky_usb_driver = { ++ .name = KBUILD_MODNAME, ++ .id_table = dvbsky_id_table, ++ .probe = dvb_usbv2_probe, ++ .disconnect = dvb_usbv2_disconnect, ++ .suspend = dvb_usbv2_suspend, ++ .resume = dvb_usbv2_resume, ++ .reset_resume = dvb_usbv2_reset_resume, ++ .no_dynamic_id = 1, ++ .soft_unbind = 1, +}; + - static int dw2102_probe(struct usb_interface *intf, - const struct usb_device_id *id) - { -@@ -1939,6 +2215,10 @@ static int dw2102_probe(struct usb_interface *intf, - 0 == dvb_usb_device_init(intf, p7500, - THIS_MODULE, NULL, adapter_nr) || - 0 == dvb_usb_device_init(intf, &su3000_properties, -+ THIS_MODULE, NULL, adapter_nr) || -+ 0 == dvb_usb_device_init(intf, &US6830_properties, -+ THIS_MODULE, NULL, adapter_nr) || -+ 0 == dvb_usb_device_init(intf, &US6832_properties, - THIS_MODULE, NULL, adapter_nr)) - return 0; ++module_usb_driver(dvbsky_usb_driver); ++ ++MODULE_AUTHOR("Max nibble "); ++MODULE_DESCRIPTION("Driver for DVBSky USB2.0"); ++MODULE_LICENSE("GPL"); +diff -urN a/drivers/media/usb/dvb-usb-v2/Kconfig b/drivers/media/usb/dvb-usb-v2/Kconfig +--- a/drivers/media/usb/dvb-usb-v2/Kconfig 2013-03-21 04:11:19.000000000 +0800 ++++ b/drivers/media/usb/dvb-usb-v2/Kconfig 2013-04-23 22:24:38.000000000 +0800 +@@ -147,3 +147,10 @@ + help + Say Y here to support the Realtek RTL28xxU DVB USB receiver. -diff --git a/include/media/rc-map.h b/include/media/rc-map.h -index 74f55a3..1817662 100644 ---- a/include/media/rc-map.h -+++ b/include/media/rc-map.h -@@ -118,6 +118,7 @@ void rc_map_init(void); ++config DVB_USB_DVBSKY ++ tristate "DVBSky USB2.0 support" ++ depends on DVB_USB_V2 ++ select DVB_M88DS3103 if MEDIA_SUBDRV_AUTOSELECT ++ help ++ Say Y here to support the USB receivers from DVBSky. ++ +diff -urN a/drivers/media/usb/dvb-usb-v2/Makefile b/drivers/media/usb/dvb-usb-v2/Makefile +--- a/drivers/media/usb/dvb-usb-v2/Makefile 2013-03-21 04:11:19.000000000 +0800 ++++ b/drivers/media/usb/dvb-usb-v2/Makefile 2013-02-17 12:03:00.000000000 +0800 +@@ -43,6 +43,9 @@ + dvb-usb-rtl28xxu-objs := rtl28xxu.o + obj-$(CONFIG_DVB_USB_RTL28XXU) += dvb-usb-rtl28xxu.o + ++dvb-usb-dvbsky-objs := dvbsky.o ++obj-$(CONFIG_DVB_USB_DVBSKY) += dvb-usb-dvbsky.o ++ + ccflags-y += -I$(srctree)/drivers/media/dvb-core + ccflags-y += -I$(srctree)/drivers/media/dvb-frontends + ccflags-y += -I$(srctree)/drivers/media/tuners +diff -urN a/include/media/rc-map.h b/include/media/rc-map.h +--- a/include/media/rc-map.h 2013-03-21 04:11:19.000000000 +0800 ++++ b/include/media/rc-map.h 2013-03-31 21:42:43.000000000 +0800 +@@ -118,6 +118,7 @@ #define RC_MAP_DM1105_NEC "rc-dm1105-nec" #define RC_MAP_DNTV_LIVE_DVBT_PRO "rc-dntv-live-dvbt-pro" #define RC_MAP_DNTV_LIVE_DVB_T "rc-dntv-live-dvb-t" @@ -5992,6 +6151,3 @@ index 74f55a3..1817662 100644 #define RC_MAP_EMPTY "rc-empty" #define RC_MAP_EM_TERRATEC "rc-em-terratec" #define RC_MAP_ENCORE_ENLTV2 "rc-encore-enltv2" --- -1.7.2.5 - diff --git a/projects/ARCTIC_MC/linux/linux.x86_64.conf b/projects/ARCTIC_MC/linux/linux.x86_64.conf index 3dbdac2e4a..6ed1ca30a3 100644 --- a/projects/ARCTIC_MC/linux/linux.x86_64.conf +++ b/projects/ARCTIC_MC/linux/linux.x86_64.conf @@ -1961,6 +1961,7 @@ CONFIG_DVB_USB_IT913X=m CONFIG_DVB_USB_LME2510=m # CONFIG_DVB_USB_MXL111SF is not set CONFIG_DVB_USB_RTL28XXU=m +CONFIG_DVB_USB_DVBSKY=m # CONFIG_DVB_TTUSB_BUDGET is not set # CONFIG_DVB_TTUSB_DEC is not set CONFIG_SMS_USB_DRV=m diff --git a/projects/ATV/linux/linux.i386.conf b/projects/ATV/linux/linux.i386.conf index 770d0db4dc..492f65aff2 100644 --- a/projects/ATV/linux/linux.i386.conf +++ b/projects/ATV/linux/linux.i386.conf @@ -1,6 +1,6 @@ # # Automatically generated file; DO NOT EDIT. -# Linux/i386 3.8.7 Kernel Configuration +# Linux/i386 3.8.8 Kernel Configuration # # CONFIG_64BIT is not set CONFIG_X86_32=y @@ -520,7 +520,6 @@ CONFIG_PCIEASPM=y CONFIG_PCIEASPM_DEFAULT=y # CONFIG_PCIEASPM_POWERSAVE is not set # CONFIG_PCIEASPM_PERFORMANCE is not set -CONFIG_PCIE_PME=y CONFIG_ARCH_SUPPORTS_MSI=y CONFIG_PCI_MSI=y # CONFIG_PCI_DEBUG is not set @@ -2025,7 +2024,6 @@ CONFIG_DVB_TUNER_CX24113=m CONFIG_DVB_TDA826X=m CONFIG_DVB_CX24116=m CONFIG_DVB_M88DS3103=m -CONFIG_DVB_SI2168=m CONFIG_DVB_SI21XX=m CONFIG_DVB_DS3000=m CONFIG_DVB_TDA10071=m diff --git a/projects/Fusion/linux/linux.i386.conf b/projects/Fusion/linux/linux.i386.conf index 6dbfd6c187..865b0b8463 100644 --- a/projects/Fusion/linux/linux.i386.conf +++ b/projects/Fusion/linux/linux.i386.conf @@ -1,6 +1,6 @@ # # Automatically generated file; DO NOT EDIT. -# Linux/i386 3.8.7 Kernel Configuration +# Linux/i386 3.8.8 Kernel Configuration # # CONFIG_64BIT is not set CONFIG_X86_32=y @@ -2318,7 +2318,6 @@ CONFIG_DVB_TUA6100=m CONFIG_DVB_CX24116=m CONFIG_DVB_M88DS3103=m CONFIG_DVB_M88DC2800=m -CONFIG_DVB_SI2168=m CONFIG_DVB_SI21XX=m CONFIG_DVB_DS3000=m CONFIG_DVB_MB86A16=m diff --git a/projects/Fusion/linux/linux.x86_64.conf b/projects/Fusion/linux/linux.x86_64.conf index 41d6a0e855..a1f25c6bcb 100644 --- a/projects/Fusion/linux/linux.x86_64.conf +++ b/projects/Fusion/linux/linux.x86_64.conf @@ -1,6 +1,6 @@ # # Automatically generated file; DO NOT EDIT. -# Linux/x86_64 3.8.7 Kernel Configuration +# Linux/x86_64 3.8.8 Kernel Configuration # CONFIG_64BIT=y CONFIG_X86_64=y @@ -2274,7 +2274,6 @@ CONFIG_DVB_TUA6100=m CONFIG_DVB_CX24116=m CONFIG_DVB_M88DS3103=m CONFIG_DVB_M88DC2800=m -CONFIG_DVB_SI2168=m CONFIG_DVB_SI21XX=m CONFIG_DVB_DS3000=m CONFIG_DVB_MB86A16=m diff --git a/projects/Generic/linux/linux.i386.conf b/projects/Generic/linux/linux.i386.conf index 22b8226e9e..8d55a58322 100644 --- a/projects/Generic/linux/linux.i386.conf +++ b/projects/Generic/linux/linux.i386.conf @@ -1,6 +1,6 @@ # # Automatically generated file; DO NOT EDIT. -# Linux/i386 3.8.7 Kernel Configuration +# Linux/i386 3.8.8 Kernel Configuration # # CONFIG_64BIT is not set CONFIG_X86_32=y @@ -2394,7 +2394,6 @@ CONFIG_DVB_TUA6100=m CONFIG_DVB_CX24116=m CONFIG_DVB_M88DS3103=m CONFIG_DVB_M88DC2800=m -CONFIG_DVB_SI2168=m CONFIG_DVB_SI21XX=m CONFIG_DVB_DS3000=m CONFIG_DVB_MB86A16=m diff --git a/projects/Generic_OSS/linux/linux.i386.conf b/projects/Generic_OSS/linux/linux.i386.conf index 57f1c6afe7..fcceb179c3 100644 --- a/projects/Generic_OSS/linux/linux.i386.conf +++ b/projects/Generic_OSS/linux/linux.i386.conf @@ -1,6 +1,6 @@ # # Automatically generated file; DO NOT EDIT. -# Linux/i386 3.8.7 Kernel Configuration +# Linux/i386 3.8.8 Kernel Configuration # # CONFIG_64BIT is not set CONFIG_X86_32=y @@ -2392,7 +2392,6 @@ CONFIG_DVB_TUA6100=m CONFIG_DVB_CX24116=m CONFIG_DVB_M88DS3103=m CONFIG_DVB_M88DC2800=m -CONFIG_DVB_SI2168=m CONFIG_DVB_SI21XX=m CONFIG_DVB_DS3000=m CONFIG_DVB_MB86A16=m diff --git a/projects/ION/linux/linux.i386.conf b/projects/ION/linux/linux.i386.conf index 97e657a453..2063be895d 100644 --- a/projects/ION/linux/linux.i386.conf +++ b/projects/ION/linux/linux.i386.conf @@ -1,6 +1,6 @@ # # Automatically generated file; DO NOT EDIT. -# Linux/i386 3.8.7 Kernel Configuration +# Linux/i386 3.8.8 Kernel Configuration # # CONFIG_64BIT is not set CONFIG_X86_32=y @@ -2313,7 +2313,6 @@ CONFIG_DVB_TUA6100=m CONFIG_DVB_CX24116=m CONFIG_DVB_M88DS3103=m CONFIG_DVB_M88DC2800=m -CONFIG_DVB_SI2168=m CONFIG_DVB_SI21XX=m CONFIG_DVB_DS3000=m CONFIG_DVB_MB86A16=m diff --git a/projects/ION/linux/linux.x86_64.conf b/projects/ION/linux/linux.x86_64.conf index 4d6272ab22..54d52f0e2b 100644 --- a/projects/ION/linux/linux.x86_64.conf +++ b/projects/ION/linux/linux.x86_64.conf @@ -1,6 +1,6 @@ # # Automatically generated file; DO NOT EDIT. -# Linux/x86_64 3.8.7 Kernel Configuration +# Linux/x86_64 3.8.8 Kernel Configuration # CONFIG_64BIT=y CONFIG_X86_64=y @@ -2252,7 +2252,6 @@ CONFIG_DVB_TUA6100=m CONFIG_DVB_CX24116=m CONFIG_DVB_M88DS3103=m CONFIG_DVB_M88DC2800=m -CONFIG_DVB_SI2168=m CONFIG_DVB_SI21XX=m CONFIG_DVB_DS3000=m CONFIG_DVB_MB86A16=m diff --git a/projects/Intel/linux/linux.i386.conf b/projects/Intel/linux/linux.i386.conf index 07ae963a21..5dd69da7d5 100644 --- a/projects/Intel/linux/linux.i386.conf +++ b/projects/Intel/linux/linux.i386.conf @@ -1,6 +1,6 @@ # # Automatically generated file; DO NOT EDIT. -# Linux/i386 3.8.7 Kernel Configuration +# Linux/i386 3.8.8 Kernel Configuration # # CONFIG_64BIT is not set CONFIG_X86_32=y @@ -2339,7 +2339,6 @@ CONFIG_DVB_TUA6100=m CONFIG_DVB_CX24116=m CONFIG_DVB_M88DS3103=m CONFIG_DVB_M88DC2800=m -CONFIG_DVB_SI2168=m CONFIG_DVB_SI21XX=m CONFIG_DVB_DS3000=m CONFIG_DVB_MB86A16=m diff --git a/projects/Intel/linux/linux.x86_64.conf b/projects/Intel/linux/linux.x86_64.conf index 315cc0e9b6..bb8ea15ecb 100644 --- a/projects/Intel/linux/linux.x86_64.conf +++ b/projects/Intel/linux/linux.x86_64.conf @@ -1,6 +1,6 @@ # # Automatically generated file; DO NOT EDIT. -# Linux/x86_64 3.8.7 Kernel Configuration +# Linux/x86_64 3.8.8 Kernel Configuration # CONFIG_64BIT=y CONFIG_X86_64=y @@ -2279,7 +2279,6 @@ CONFIG_DVB_TUA6100=m CONFIG_DVB_CX24116=m CONFIG_DVB_M88DS3103=m CONFIG_DVB_M88DC2800=m -CONFIG_DVB_SI2168=m CONFIG_DVB_SI21XX=m CONFIG_DVB_DS3000=m CONFIG_DVB_MB86A16=m diff --git a/projects/RPi/linux/linux.arm.conf b/projects/RPi/linux/linux.arm.conf index 4af0a004fe..6e9acc3095 100644 --- a/projects/RPi/linux/linux.arm.conf +++ b/projects/RPi/linux/linux.arm.conf @@ -1492,6 +1492,7 @@ CONFIG_DVB_USB_IT913X=m CONFIG_DVB_USB_LME2510=m # CONFIG_DVB_USB_MXL111SF is not set CONFIG_DVB_USB_RTL28XXU=m +CONFIG_DVB_USB_DVBSKY=m CONFIG_SMS_USB_DRV=m CONFIG_DVB_B2C2_FLEXCOP_USB=m # CONFIG_DVB_B2C2_FLEXCOP_USB_DEBUG is not set diff --git a/projects/Ultra/linux/linux.x86_64.conf b/projects/Ultra/linux/linux.x86_64.conf index f01b334989..c4faaaee57 100644 --- a/projects/Ultra/linux/linux.x86_64.conf +++ b/projects/Ultra/linux/linux.x86_64.conf @@ -1,6 +1,6 @@ # # Automatically generated file; DO NOT EDIT. -# Linux/x86_64 3.8.7 Kernel Configuration +# Linux/x86_64 3.8.8 Kernel Configuration # CONFIG_64BIT=y CONFIG_X86_64=y @@ -2097,7 +2097,6 @@ CONFIG_DVB_TUNER_CX24113=m CONFIG_DVB_TDA826X=m CONFIG_DVB_CX24116=m CONFIG_DVB_M88DS3103=m -CONFIG_DVB_SI2168=m CONFIG_DVB_SI21XX=m CONFIG_DVB_DS3000=m CONFIG_DVB_TDA10071=m diff --git a/projects/Virtual/linux/linux.i386.conf b/projects/Virtual/linux/linux.i386.conf index 9dba606643..3933a0223c 100644 --- a/projects/Virtual/linux/linux.i386.conf +++ b/projects/Virtual/linux/linux.i386.conf @@ -1,6 +1,6 @@ # # Automatically generated file; DO NOT EDIT. -# Linux/i386 3.8.7 Kernel Configuration +# Linux/i386 3.8.8 Kernel Configuration # # CONFIG_64BIT is not set CONFIG_X86_32=y @@ -2341,7 +2341,6 @@ CONFIG_DVB_TUA6100=m CONFIG_DVB_CX24116=m CONFIG_DVB_M88DS3103=m CONFIG_DVB_M88DC2800=m -CONFIG_DVB_SI2168=m CONFIG_DVB_SI21XX=m CONFIG_DVB_DS3000=m CONFIG_DVB_MB86A16=m diff --git a/projects/Virtual/linux/linux.x86_64.conf b/projects/Virtual/linux/linux.x86_64.conf index c1d3b98c45..f7b455f928 100644 --- a/projects/Virtual/linux/linux.x86_64.conf +++ b/projects/Virtual/linux/linux.x86_64.conf @@ -1,6 +1,6 @@ # # Automatically generated file; DO NOT EDIT. -# Linux/x86_64 3.8.7 Kernel Configuration +# Linux/x86_64 3.8.8 Kernel Configuration # CONFIG_64BIT=y CONFIG_X86_64=y @@ -2280,7 +2280,6 @@ CONFIG_DVB_TUA6100=m CONFIG_DVB_CX24116=m CONFIG_DVB_M88DS3103=m CONFIG_DVB_M88DC2800=m -CONFIG_DVB_SI2168=m CONFIG_DVB_SI21XX=m CONFIG_DVB_DS3000=m CONFIG_DVB_MB86A16=m