aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/media/common/tuners
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/media/common/tuners')
-rw-r--r--drivers/media/common/tuners/Kconfig207
-rw-r--r--drivers/media/common/tuners/Makefile32
-rw-r--r--drivers/media/common/tuners/max2165.c441
-rw-r--r--drivers/media/common/tuners/max2165.h48
-rw-r--r--drivers/media/common/tuners/max2165_priv.h60
-rw-r--r--drivers/media/common/tuners/mc44s803.c372
-rw-r--r--drivers/media/common/tuners/mc44s803.h46
-rw-r--r--drivers/media/common/tuners/mc44s803_priv.h208
-rw-r--r--drivers/media/common/tuners/mt2060.c404
-rw-r--r--drivers/media/common/tuners/mt2060.h43
-rw-r--r--drivers/media/common/tuners/mt2060_priv.h105
-rw-r--r--drivers/media/common/tuners/mt20xx.c672
-rw-r--r--drivers/media/common/tuners/mt20xx.h37
-rw-r--r--drivers/media/common/tuners/mt2131.c315
-rw-r--r--drivers/media/common/tuners/mt2131.h54
-rw-r--r--drivers/media/common/tuners/mt2131_priv.h49
-rw-r--r--drivers/media/common/tuners/mt2266.c352
-rw-r--r--drivers/media/common/tuners/mt2266.h37
-rw-r--r--drivers/media/common/tuners/mxl5005s.c4118
-rw-r--r--drivers/media/common/tuners/mxl5005s.h135
-rw-r--r--drivers/media/common/tuners/mxl5007t.c883
-rw-r--r--drivers/media/common/tuners/mxl5007t.h104
-rw-r--r--drivers/media/common/tuners/qt1010.c483
-rw-r--r--drivers/media/common/tuners/qt1010.h53
-rw-r--r--drivers/media/common/tuners/qt1010_priv.h105
-rw-r--r--drivers/media/common/tuners/tda18212.c265
-rw-r--r--drivers/media/common/tuners/tda18212.h48
-rw-r--r--drivers/media/common/tuners/tda18212_priv.h44
-rw-r--r--drivers/media/common/tuners/tda18218.c334
-rw-r--r--drivers/media/common/tuners/tda18218.h45
-rw-r--r--drivers/media/common/tuners/tda18218_priv.h106
-rw-r--r--drivers/media/common/tuners/tda18271-common.c685
-rw-r--r--drivers/media/common/tuners/tda18271-fe.c1346
-rw-r--r--drivers/media/common/tuners/tda18271-maps.c1313
-rw-r--r--drivers/media/common/tuners/tda18271-priv.h237
-rw-r--r--drivers/media/common/tuners/tda18271.h133
-rw-r--r--drivers/media/common/tuners/tda827x.c913
-rw-r--r--drivers/media/common/tuners/tda827x.h68
-rw-r--r--drivers/media/common/tuners/tda8290.c874
-rw-r--r--drivers/media/common/tuners/tda8290.h56
-rw-r--r--drivers/media/common/tuners/tda9887.c717
-rw-r--r--drivers/media/common/tuners/tda9887.h38
-rw-r--r--drivers/media/common/tuners/tea5761.c348
-rw-r--r--drivers/media/common/tuners/tea5761.h47
-rw-r--r--drivers/media/common/tuners/tea5767.c475
-rw-r--r--drivers/media/common/tuners/tea5767.h66
-rw-r--r--drivers/media/common/tuners/tuner-i2c.h182
-rw-r--r--drivers/media/common/tuners/tuner-simple.c1131
-rw-r--r--drivers/media/common/tuners/tuner-simple.h39
-rw-r--r--drivers/media/common/tuners/tuner-types.c1878
-rw-r--r--drivers/media/common/tuners/tuner-xc2028-types.h141
-rw-r--r--drivers/media/common/tuners/tuner-xc2028.c1356
-rw-r--r--drivers/media/common/tuners/tuner-xc2028.h71
-rw-r--r--drivers/media/common/tuners/xc4000.c1691
-rw-r--r--drivers/media/common/tuners/xc4000.h67
-rw-r--r--drivers/media/common/tuners/xc5000.c1201
-rw-r--r--drivers/media/common/tuners/xc5000.h68
57 files changed, 25346 insertions, 0 deletions
diff --git a/drivers/media/common/tuners/Kconfig b/drivers/media/common/tuners/Kconfig
new file mode 100644
index 00000000000..996302ae210
--- /dev/null
+++ b/drivers/media/common/tuners/Kconfig
@@ -0,0 +1,207 @@
1config MEDIA_ATTACH
2 bool "Load and attach frontend and tuner driver modules as needed"
3 depends on VIDEO_MEDIA
4 depends on MODULES
5 help
6 Remove the static dependency of DVB card drivers on all
7 frontend modules for all possible card variants. Instead,
8 allow the card drivers to only load the frontend modules
9 they require.
10
11 Also, tuner module will automatically load a tuner driver
12 when needed, for analog mode.
13
14 This saves several KBytes of memory.
15
16 Note: You will need module-init-tools v3.2 or later for this feature.
17
18 If unsure say Y.
19
20config MEDIA_TUNER
21 tristate
22 default VIDEO_MEDIA && I2C
23 depends on VIDEO_MEDIA && I2C
24 select MEDIA_TUNER_XC2028 if !MEDIA_TUNER_CUSTOMISE
25 select MEDIA_TUNER_XC5000 if !MEDIA_TUNER_CUSTOMISE
26 select MEDIA_TUNER_XC4000 if !MEDIA_TUNER_CUSTOMISE
27 select MEDIA_TUNER_MT20XX if !MEDIA_TUNER_CUSTOMISE
28 select MEDIA_TUNER_TDA8290 if !MEDIA_TUNER_CUSTOMISE
29 select MEDIA_TUNER_TEA5761 if !MEDIA_TUNER_CUSTOMISE
30 select MEDIA_TUNER_TEA5767 if !MEDIA_TUNER_CUSTOMISE
31 select MEDIA_TUNER_SIMPLE if !MEDIA_TUNER_CUSTOMISE
32 select MEDIA_TUNER_TDA9887 if !MEDIA_TUNER_CUSTOMISE
33 select MEDIA_TUNER_MC44S803 if !MEDIA_TUNER_CUSTOMISE
34
35config MEDIA_TUNER_CUSTOMISE
36 bool "Customize analog and hybrid tuner modules to build"
37 depends on MEDIA_TUNER
38 default y if EXPERT
39 help
40 This allows the user to deselect tuner drivers unnecessary
41 for their hardware from the build. Use this option with care
42 as deselecting tuner drivers which are in fact necessary will
43 result in V4L/DVB devices which cannot be tuned due to lack of
44 driver support
45
46 If unsure say N.
47
48menu "Customize TV tuners"
49 visible if MEDIA_TUNER_CUSTOMISE
50
51config MEDIA_TUNER_SIMPLE
52 tristate "Simple tuner support"
53 depends on VIDEO_MEDIA && I2C
54 select MEDIA_TUNER_TDA9887
55 default m if MEDIA_TUNER_CUSTOMISE
56 help
57 Say Y here to include support for various simple tuners.
58
59config MEDIA_TUNER_TDA8290
60 tristate "TDA 8290/8295 + 8275(a)/18271 tuner combo"
61 depends on VIDEO_MEDIA && I2C
62 select MEDIA_TUNER_TDA827X
63 select MEDIA_TUNER_TDA18271
64 default m if MEDIA_TUNER_CUSTOMISE
65 help
66 Say Y here to include support for Philips TDA8290+8275(a) tuner.
67
68config MEDIA_TUNER_TDA827X
69 tristate "Philips TDA827X silicon tuner"
70 depends on VIDEO_MEDIA && I2C
71 default m if MEDIA_TUNER_CUSTOMISE
72 help
73 A DVB-T silicon tuner module. Say Y when you want to support this tuner.
74
75config MEDIA_TUNER_TDA18271
76 tristate "NXP TDA18271 silicon tuner"
77 depends on VIDEO_MEDIA && I2C
78 default m if MEDIA_TUNER_CUSTOMISE
79 help
80 A silicon tuner module. Say Y when you want to support this tuner.
81
82config MEDIA_TUNER_TDA9887
83 tristate "TDA 9885/6/7 analog IF demodulator"
84 depends on VIDEO_MEDIA && I2C
85 default m if MEDIA_TUNER_CUSTOMISE
86 help
87 Say Y here to include support for Philips TDA9885/6/7
88 analog IF demodulator.
89
90config MEDIA_TUNER_TEA5761
91 tristate "TEA 5761 radio tuner (EXPERIMENTAL)"
92 depends on VIDEO_MEDIA && I2C
93 depends on EXPERIMENTAL
94 default m if MEDIA_TUNER_CUSTOMISE
95 help
96 Say Y here to include support for the Philips TEA5761 radio tuner.
97
98config MEDIA_TUNER_TEA5767
99 tristate "TEA 5767 radio tuner"
100 depends on VIDEO_MEDIA && I2C
101 default m if MEDIA_TUNER_CUSTOMISE
102 help
103 Say Y here to include support for the Philips TEA5767 radio tuner.
104
105config MEDIA_TUNER_MT20XX
106 tristate "Microtune 2032 / 2050 tuners"
107 depends on VIDEO_MEDIA && I2C
108 default m if MEDIA_TUNER_CUSTOMISE
109 help
110 Say Y here to include support for the MT2032 / MT2050 tuner.
111
112config MEDIA_TUNER_MT2060
113 tristate "Microtune MT2060 silicon IF tuner"
114 depends on VIDEO_MEDIA && I2C
115 default m if MEDIA_TUNER_CUSTOMISE
116 help
117 A driver for the silicon IF tuner MT2060 from Microtune.
118
119config MEDIA_TUNER_MT2266
120 tristate "Microtune MT2266 silicon tuner"
121 depends on VIDEO_MEDIA && I2C
122 default m if MEDIA_TUNER_CUSTOMISE
123 help
124 A driver for the silicon baseband tuner MT2266 from Microtune.
125
126config MEDIA_TUNER_MT2131
127 tristate "Microtune MT2131 silicon tuner"
128 depends on VIDEO_MEDIA && I2C
129 default m if MEDIA_TUNER_CUSTOMISE
130 help
131 A driver for the silicon baseband tuner MT2131 from Microtune.
132
133config MEDIA_TUNER_QT1010
134 tristate "Quantek QT1010 silicon tuner"
135 depends on VIDEO_MEDIA && I2C
136 default m if MEDIA_TUNER_CUSTOMISE
137 help
138 A driver for the silicon tuner QT1010 from Quantek.
139
140config MEDIA_TUNER_XC2028
141 tristate "XCeive xc2028/xc3028 tuners"
142 depends on VIDEO_MEDIA && I2C
143 default m if MEDIA_TUNER_CUSTOMISE
144 help
145 Say Y here to include support for the xc2028/xc3028 tuners.
146
147config MEDIA_TUNER_XC5000
148 tristate "Xceive XC5000 silicon tuner"
149 depends on VIDEO_MEDIA && I2C
150 default m if MEDIA_TUNER_CUSTOMISE
151 help
152 A driver for the silicon tuner XC5000 from Xceive.
153 This device is only used inside a SiP called together with a
154 demodulator for now.
155
156config MEDIA_TUNER_XC4000
157 tristate "Xceive XC4000 silicon tuner"
158 depends on VIDEO_MEDIA && I2C
159 default m if MEDIA_TUNER_CUSTOMISE
160 help
161 A driver for the silicon tuner XC4000 from Xceive.
162 This device is only used inside a SiP called together with a
163 demodulator for now.
164
165config MEDIA_TUNER_MXL5005S
166 tristate "MaxLinear MSL5005S silicon tuner"
167 depends on VIDEO_MEDIA && I2C
168 default m if MEDIA_TUNER_CUSTOMISE
169 help
170 A driver for the silicon tuner MXL5005S from MaxLinear.
171
172config MEDIA_TUNER_MXL5007T
173 tristate "MaxLinear MxL5007T silicon tuner"
174 depends on VIDEO_MEDIA && I2C
175 default m if MEDIA_TUNER_CUSTOMISE
176 help
177 A driver for the silicon tuner MxL5007T from MaxLinear.
178
179config MEDIA_TUNER_MC44S803
180 tristate "Freescale MC44S803 Low Power CMOS Broadband tuners"
181 depends on VIDEO_MEDIA && I2C
182 default m if MEDIA_TUNER_CUSTOMISE
183 help
184 Say Y here to support the Freescale MC44S803 based tuners
185
186config MEDIA_TUNER_MAX2165
187 tristate "Maxim MAX2165 silicon tuner"
188 depends on VIDEO_MEDIA && I2C
189 default m if MEDIA_TUNER_CUSTOMISE
190 help
191 A driver for the silicon tuner MAX2165 from Maxim.
192
193config MEDIA_TUNER_TDA18218
194 tristate "NXP TDA18218 silicon tuner"
195 depends on VIDEO_MEDIA && I2C
196 default m if MEDIA_TUNER_CUSTOMISE
197 help
198 NXP TDA18218 silicon tuner driver.
199
200config MEDIA_TUNER_TDA18212
201 tristate "NXP TDA18212 silicon tuner"
202 depends on VIDEO_MEDIA && I2C
203 default m if MEDIA_TUNER_CUSTOMISE
204 help
205 NXP TDA18212 silicon tuner driver.
206
207endmenu
diff --git a/drivers/media/common/tuners/Makefile b/drivers/media/common/tuners/Makefile
new file mode 100644
index 00000000000..20d24fca2cf
--- /dev/null
+++ b/drivers/media/common/tuners/Makefile
@@ -0,0 +1,32 @@
1#
2# Makefile for common V4L/DVB tuners
3#
4
5tda18271-objs := tda18271-maps.o tda18271-common.o tda18271-fe.o
6
7obj-$(CONFIG_MEDIA_TUNER_XC2028) += tuner-xc2028.o
8obj-$(CONFIG_MEDIA_TUNER_SIMPLE) += tuner-simple.o
9# tuner-types will be merged into tuner-simple, in the future
10obj-$(CONFIG_MEDIA_TUNER_SIMPLE) += tuner-types.o
11obj-$(CONFIG_MEDIA_TUNER_MT20XX) += mt20xx.o
12obj-$(CONFIG_MEDIA_TUNER_TDA8290) += tda8290.o
13obj-$(CONFIG_MEDIA_TUNER_TEA5767) += tea5767.o
14obj-$(CONFIG_MEDIA_TUNER_TEA5761) += tea5761.o
15obj-$(CONFIG_MEDIA_TUNER_TDA9887) += tda9887.o
16obj-$(CONFIG_MEDIA_TUNER_TDA827X) += tda827x.o
17obj-$(CONFIG_MEDIA_TUNER_TDA18271) += tda18271.o
18obj-$(CONFIG_MEDIA_TUNER_XC5000) += xc5000.o
19obj-$(CONFIG_MEDIA_TUNER_XC4000) += xc4000.o
20obj-$(CONFIG_MEDIA_TUNER_MT2060) += mt2060.o
21obj-$(CONFIG_MEDIA_TUNER_MT2266) += mt2266.o
22obj-$(CONFIG_MEDIA_TUNER_QT1010) += qt1010.o
23obj-$(CONFIG_MEDIA_TUNER_MT2131) += mt2131.o
24obj-$(CONFIG_MEDIA_TUNER_MXL5005S) += mxl5005s.o
25obj-$(CONFIG_MEDIA_TUNER_MXL5007T) += mxl5007t.o
26obj-$(CONFIG_MEDIA_TUNER_MC44S803) += mc44s803.o
27obj-$(CONFIG_MEDIA_TUNER_MAX2165) += max2165.o
28obj-$(CONFIG_MEDIA_TUNER_TDA18218) += tda18218.o
29obj-$(CONFIG_MEDIA_TUNER_TDA18212) += tda18212.o
30
31EXTRA_CFLAGS += -Idrivers/media/dvb/dvb-core
32EXTRA_CFLAGS += -Idrivers/media/dvb/frontends
diff --git a/drivers/media/common/tuners/max2165.c b/drivers/media/common/tuners/max2165.c
new file mode 100644
index 00000000000..9883617b786
--- /dev/null
+++ b/drivers/media/common/tuners/max2165.c
@@ -0,0 +1,441 @@
1/*
2 * Driver for Maxim MAX2165 silicon tuner
3 *
4 * Copyright (c) 2009 David T. L. Wong <davidtlwong@gmail.com>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 *
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
20 */
21
22#include <linux/module.h>
23#include <linux/moduleparam.h>
24#include <linux/videodev2.h>
25#include <linux/delay.h>
26#include <linux/dvb/frontend.h>
27#include <linux/i2c.h>
28#include <linux/slab.h>
29
30#include "dvb_frontend.h"
31
32#include "max2165.h"
33#include "max2165_priv.h"
34#include "tuner-i2c.h"
35
36#define dprintk(args...) \
37 do { \
38 if (debug) \
39 printk(KERN_DEBUG "max2165: " args); \
40 } while (0)
41
42static int debug;
43module_param(debug, int, 0644);
44MODULE_PARM_DESC(debug, "Turn on/off debugging (default:off).");
45
46static int max2165_write_reg(struct max2165_priv *priv, u8 reg, u8 data)
47{
48 int ret;
49 u8 buf[] = { reg, data };
50 struct i2c_msg msg = { .flags = 0, .buf = buf, .len = 2 };
51
52 msg.addr = priv->config->i2c_address;
53
54 if (debug >= 2)
55 dprintk("%s: reg=0x%02X, data=0x%02X\n", __func__, reg, data);
56
57 ret = i2c_transfer(priv->i2c, &msg, 1);
58
59 if (ret != 1)
60 dprintk("%s: error reg=0x%x, data=0x%x, ret=%i\n",
61 __func__, reg, data, ret);
62
63 return (ret != 1) ? -EIO : 0;
64}
65
66static int max2165_read_reg(struct max2165_priv *priv, u8 reg, u8 *p_data)
67{
68 int ret;
69 u8 dev_addr = priv->config->i2c_address;
70
71 u8 b0[] = { reg };
72 u8 b1[] = { 0 };
73 struct i2c_msg msg[] = {
74 { .addr = dev_addr, .flags = 0, .buf = b0, .len = 1 },
75 { .addr = dev_addr, .flags = I2C_M_RD, .buf = b1, .len = 1 },
76 };
77
78 ret = i2c_transfer(priv->i2c, msg, 2);
79 if (ret != 2) {
80 dprintk("%s: error reg=0x%x, ret=%i\n", __func__, reg, ret);
81 return -EIO;
82 }
83
84 *p_data = b1[0];
85 if (debug >= 2)
86 dprintk("%s: reg=0x%02X, data=0x%02X\n",
87 __func__, reg, b1[0]);
88 return 0;
89}
90
91static int max2165_mask_write_reg(struct max2165_priv *priv, u8 reg,
92 u8 mask, u8 data)
93{
94 int ret;
95 u8 v;
96
97 data &= mask;
98 ret = max2165_read_reg(priv, reg, &v);
99 if (ret != 0)
100 return ret;
101 v &= ~mask;
102 v |= data;
103 ret = max2165_write_reg(priv, reg, v);
104
105 return ret;
106}
107
108static int max2165_read_rom_table(struct max2165_priv *priv)
109{
110 u8 dat[3];
111 int i;
112
113 for (i = 0; i < 3; i++) {
114 max2165_write_reg(priv, REG_ROM_TABLE_ADDR, i + 1);
115 max2165_read_reg(priv, REG_ROM_TABLE_DATA, &dat[i]);
116 }
117
118 priv->tf_ntch_low_cfg = dat[0] >> 4;
119 priv->tf_ntch_hi_cfg = dat[0] & 0x0F;
120 priv->tf_balun_low_ref = dat[1] & 0x0F;
121 priv->tf_balun_hi_ref = dat[1] >> 4;
122 priv->bb_filter_7mhz_cfg = dat[2] & 0x0F;
123 priv->bb_filter_8mhz_cfg = dat[2] >> 4;
124
125 dprintk("tf_ntch_low_cfg = 0x%X\n", priv->tf_ntch_low_cfg);
126 dprintk("tf_ntch_hi_cfg = 0x%X\n", priv->tf_ntch_hi_cfg);
127 dprintk("tf_balun_low_ref = 0x%X\n", priv->tf_balun_low_ref);
128 dprintk("tf_balun_hi_ref = 0x%X\n", priv->tf_balun_hi_ref);
129 dprintk("bb_filter_7mhz_cfg = 0x%X\n", priv->bb_filter_7mhz_cfg);
130 dprintk("bb_filter_8mhz_cfg = 0x%X\n", priv->bb_filter_8mhz_cfg);
131
132 return 0;
133}
134
135static int max2165_set_osc(struct max2165_priv *priv, u8 osc /*MHz*/)
136{
137 u8 v;
138
139 v = (osc / 2);
140 if (v == 2)
141 v = 0x7;
142 else
143 v -= 8;
144
145 max2165_mask_write_reg(priv, REG_PLL_CFG, 0x07, v);
146
147 return 0;
148}
149
150static int max2165_set_bandwidth(struct max2165_priv *priv, u32 bw)
151{
152 u8 val;
153
154 if (bw == BANDWIDTH_8_MHZ)
155 val = priv->bb_filter_8mhz_cfg;
156 else
157 val = priv->bb_filter_7mhz_cfg;
158
159 max2165_mask_write_reg(priv, REG_BASEBAND_CTRL, 0xF0, val << 4);
160
161 return 0;
162}
163
164int fixpt_div32(u32 dividend, u32 divisor, u32 *quotient, u32 *fraction)
165{
166 u32 remainder;
167 u32 q, f = 0;
168 int i;
169
170 if (0 == divisor)
171 return -1;
172
173 q = dividend / divisor;
174 remainder = dividend - q * divisor;
175
176 for (i = 0; i < 31; i++) {
177 remainder <<= 1;
178 if (remainder >= divisor) {
179 f += 1;
180 remainder -= divisor;
181 }
182 f <<= 1;
183 }
184
185 *quotient = q;
186 *fraction = f;
187
188 return 0;
189}
190
191static int max2165_set_rf(struct max2165_priv *priv, u32 freq)
192{
193 u8 tf;
194 u8 tf_ntch;
195 u32 t;
196 u32 quotient, fraction;
197
198 /* Set PLL divider according to RF frequency */
199 fixpt_div32(freq / 1000, priv->config->osc_clk * 1000,
200 &quotient, &fraction);
201
202 /* 20-bit fraction */
203 fraction >>= 12;
204
205 max2165_write_reg(priv, REG_NDIV_INT, quotient);
206 max2165_mask_write_reg(priv, REG_NDIV_FRAC2, 0x0F, fraction >> 16);
207 max2165_write_reg(priv, REG_NDIV_FRAC1, fraction >> 8);
208 max2165_write_reg(priv, REG_NDIV_FRAC0, fraction);
209
210 /* Norch Filter */
211 tf_ntch = (freq < 725000000) ?
212 priv->tf_ntch_low_cfg : priv->tf_ntch_hi_cfg;
213
214 /* Tracking filter balun */
215 t = priv->tf_balun_low_ref;
216 t += (priv->tf_balun_hi_ref - priv->tf_balun_low_ref)
217 * (freq / 1000 - 470000) / (780000 - 470000);
218
219 tf = t;
220 dprintk("tf = %X\n", tf);
221 tf |= tf_ntch << 4;
222
223 max2165_write_reg(priv, REG_TRACK_FILTER, tf);
224
225 return 0;
226}
227
228static void max2165_debug_status(struct max2165_priv *priv)
229{
230 u8 status, autotune;
231 u8 auto_vco_success, auto_vco_active;
232 u8 pll_locked;
233 u8 dc_offset_low, dc_offset_hi;
234 u8 signal_lv_over_threshold;
235 u8 vco, vco_sub_band, adc;
236
237 max2165_read_reg(priv, REG_STATUS, &status);
238 max2165_read_reg(priv, REG_AUTOTUNE, &autotune);
239
240 auto_vco_success = (status >> 6) & 0x01;
241 auto_vco_active = (status >> 5) & 0x01;
242 pll_locked = (status >> 4) & 0x01;
243 dc_offset_low = (status >> 3) & 0x01;
244 dc_offset_hi = (status >> 2) & 0x01;
245 signal_lv_over_threshold = status & 0x01;
246
247 vco = autotune >> 6;
248 vco_sub_band = (autotune >> 3) & 0x7;
249 adc = autotune & 0x7;
250
251 dprintk("auto VCO active: %d, auto VCO success: %d\n",
252 auto_vco_active, auto_vco_success);
253 dprintk("PLL locked: %d\n", pll_locked);
254 dprintk("DC offset low: %d, DC offset high: %d\n",
255 dc_offset_low, dc_offset_hi);
256 dprintk("Signal lvl over threshold: %d\n", signal_lv_over_threshold);
257 dprintk("VCO: %d, VCO Sub-band: %d, ADC: %d\n", vco, vco_sub_band, adc);
258}
259
260static int max2165_set_params(struct dvb_frontend *fe,
261 struct dvb_frontend_parameters *params)
262{
263 struct max2165_priv *priv = fe->tuner_priv;
264 int ret;
265
266 dprintk("%s() frequency=%d (Hz)\n", __func__, params->frequency);
267 if (fe->ops.info.type == FE_ATSC) {
268 return -EINVAL;
269 } else if (fe->ops.info.type == FE_OFDM) {
270 dprintk("%s() OFDM\n", __func__);
271 switch (params->u.ofdm.bandwidth) {
272 case BANDWIDTH_6_MHZ:
273 return -EINVAL;
274 case BANDWIDTH_7_MHZ:
275 case BANDWIDTH_8_MHZ:
276 priv->frequency = params->frequency;
277 priv->bandwidth = params->u.ofdm.bandwidth;
278 break;
279 default:
280 printk(KERN_ERR "MAX2165 bandwidth not set!\n");
281 return -EINVAL;
282 }
283 } else {
284 printk(KERN_ERR "MAX2165 modulation type not supported!\n");
285 return -EINVAL;
286 }
287
288 dprintk("%s() frequency=%d\n", __func__, priv->frequency);
289
290 if (fe->ops.i2c_gate_ctrl)
291 fe->ops.i2c_gate_ctrl(fe, 1);
292 max2165_set_bandwidth(priv, priv->bandwidth);
293 ret = max2165_set_rf(priv, priv->frequency);
294 mdelay(50);
295 max2165_debug_status(priv);
296 if (fe->ops.i2c_gate_ctrl)
297 fe->ops.i2c_gate_ctrl(fe, 0);
298
299 if (ret != 0)
300 return -EREMOTEIO;
301
302 return 0;
303}
304
305static int max2165_get_frequency(struct dvb_frontend *fe, u32 *freq)
306{
307 struct max2165_priv *priv = fe->tuner_priv;
308 dprintk("%s()\n", __func__);
309 *freq = priv->frequency;
310 return 0;
311}
312
313static int max2165_get_bandwidth(struct dvb_frontend *fe, u32 *bw)
314{
315 struct max2165_priv *priv = fe->tuner_priv;
316 dprintk("%s()\n", __func__);
317
318 *bw = priv->bandwidth;
319 return 0;
320}
321
322static int max2165_get_status(struct dvb_frontend *fe, u32 *status)
323{
324 struct max2165_priv *priv = fe->tuner_priv;
325 u16 lock_status = 0;
326
327 dprintk("%s()\n", __func__);
328
329 if (fe->ops.i2c_gate_ctrl)
330 fe->ops.i2c_gate_ctrl(fe, 1);
331
332 max2165_debug_status(priv);
333 *status = lock_status;
334
335 if (fe->ops.i2c_gate_ctrl)
336 fe->ops.i2c_gate_ctrl(fe, 0);
337
338 return 0;
339}
340
341static int max2165_sleep(struct dvb_frontend *fe)
342{
343 dprintk("%s()\n", __func__);
344 return 0;
345}
346
347static int max2165_init(struct dvb_frontend *fe)
348{
349 struct max2165_priv *priv = fe->tuner_priv;
350 dprintk("%s()\n", __func__);
351
352 if (fe->ops.i2c_gate_ctrl)
353 fe->ops.i2c_gate_ctrl(fe, 1);
354
355 /* Setup initial values */
356 /* Fractional Mode on */
357 max2165_write_reg(priv, REG_NDIV_FRAC2, 0x18);
358 /* LNA on */
359 max2165_write_reg(priv, REG_LNA, 0x01);
360 max2165_write_reg(priv, REG_PLL_CFG, 0x7A);
361 max2165_write_reg(priv, REG_TEST, 0x08);
362 max2165_write_reg(priv, REG_SHUTDOWN, 0x40);
363 max2165_write_reg(priv, REG_VCO_CTRL, 0x84);
364 max2165_write_reg(priv, REG_BASEBAND_CTRL, 0xC3);
365 max2165_write_reg(priv, REG_DC_OFFSET_CTRL, 0x75);
366 max2165_write_reg(priv, REG_DC_OFFSET_DAC, 0x00);
367 max2165_write_reg(priv, REG_ROM_TABLE_ADDR, 0x00);
368
369 max2165_set_osc(priv, priv->config->osc_clk);
370
371 max2165_read_rom_table(priv);
372
373 max2165_set_bandwidth(priv, BANDWIDTH_8_MHZ);
374
375 if (fe->ops.i2c_gate_ctrl)
376 fe->ops.i2c_gate_ctrl(fe, 0);
377
378 return 0;
379}
380
381static int max2165_release(struct dvb_frontend *fe)
382{
383 struct max2165_priv *priv = fe->tuner_priv;
384 dprintk("%s()\n", __func__);
385
386 kfree(priv);
387 fe->tuner_priv = NULL;
388
389 return 0;
390}
391
392static const struct dvb_tuner_ops max2165_tuner_ops = {
393 .info = {
394 .name = "Maxim MAX2165",
395 .frequency_min = 470000000,
396 .frequency_max = 780000000,
397 .frequency_step = 50000,
398 },
399
400 .release = max2165_release,
401 .init = max2165_init,
402 .sleep = max2165_sleep,
403
404 .set_params = max2165_set_params,
405 .set_analog_params = NULL,
406 .get_frequency = max2165_get_frequency,
407 .get_bandwidth = max2165_get_bandwidth,
408 .get_status = max2165_get_status
409};
410
411struct dvb_frontend *max2165_attach(struct dvb_frontend *fe,
412 struct i2c_adapter *i2c,
413 struct max2165_config *cfg)
414{
415 struct max2165_priv *priv = NULL;
416
417 dprintk("%s(%d-%04x)\n", __func__,
418 i2c ? i2c_adapter_id(i2c) : -1,
419 cfg ? cfg->i2c_address : -1);
420
421 priv = kzalloc(sizeof(struct max2165_priv), GFP_KERNEL);
422 if (priv == NULL)
423 return NULL;
424
425 memcpy(&fe->ops.tuner_ops, &max2165_tuner_ops,
426 sizeof(struct dvb_tuner_ops));
427
428 priv->config = cfg;
429 priv->i2c = i2c;
430 fe->tuner_priv = priv;
431
432 max2165_init(fe);
433 max2165_debug_status(priv);
434
435 return fe;
436}
437EXPORT_SYMBOL(max2165_attach);
438
439MODULE_AUTHOR("David T. L. Wong <davidtlwong@gmail.com>");
440MODULE_DESCRIPTION("Maxim MAX2165 silicon tuner driver");
441MODULE_LICENSE("GPL");
diff --git a/drivers/media/common/tuners/max2165.h b/drivers/media/common/tuners/max2165.h
new file mode 100644
index 00000000000..c063c36a93d
--- /dev/null
+++ b/drivers/media/common/tuners/max2165.h
@@ -0,0 +1,48 @@
1/*
2 * Driver for Maxim MAX2165 silicon tuner
3 *
4 * Copyright (c) 2009 David T. L. Wong <davidtlwong@gmail.com>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 *
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
20 */
21
22#ifndef __MAX2165_H__
23#define __MAX2165_H__
24
25struct dvb_frontend;
26struct i2c_adapter;
27
28struct max2165_config {
29 u8 i2c_address;
30 u8 osc_clk; /* in MHz, selectable values: 4,16,18,20,22,24,26,28 */
31};
32
33#if defined(CONFIG_MEDIA_TUNER_MAX2165) || \
34 (defined(CONFIG_MEDIA_TUNER_MAX2165_MODULE) && defined(MODULE))
35extern struct dvb_frontend *max2165_attach(struct dvb_frontend *fe,
36 struct i2c_adapter *i2c,
37 struct max2165_config *cfg);
38#else
39static inline struct dvb_frontend *max2165_attach(struct dvb_frontend *fe,
40 struct i2c_adapter *i2c,
41 struct max2165_config *cfg)
42{
43 printk(KERN_WARNING "%s: driver disabled by Kconfig\n", __func__);
44 return NULL;
45}
46#endif
47
48#endif
diff --git a/drivers/media/common/tuners/max2165_priv.h b/drivers/media/common/tuners/max2165_priv.h
new file mode 100644
index 00000000000..91bbe021a08
--- /dev/null
+++ b/drivers/media/common/tuners/max2165_priv.h
@@ -0,0 +1,60 @@
1/*
2 * Driver for Maxim MAX2165 silicon tuner
3 *
4 * Copyright (c) 2009 David T. L. Wong <davidtlwong@gmail.com>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 *
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
20 */
21
22#ifndef __MAX2165_PRIV_H__
23#define __MAX2165_PRIV_H__
24
25#define REG_NDIV_INT 0x00
26#define REG_NDIV_FRAC2 0x01
27#define REG_NDIV_FRAC1 0x02
28#define REG_NDIV_FRAC0 0x03
29#define REG_TRACK_FILTER 0x04
30#define REG_LNA 0x05
31#define REG_PLL_CFG 0x06
32#define REG_TEST 0x07
33#define REG_SHUTDOWN 0x08
34#define REG_VCO_CTRL 0x09
35#define REG_BASEBAND_CTRL 0x0A
36#define REG_DC_OFFSET_CTRL 0x0B
37#define REG_DC_OFFSET_DAC 0x0C
38#define REG_ROM_TABLE_ADDR 0x0D
39
40/* Read Only Registers */
41#define REG_ROM_TABLE_DATA 0x10
42#define REG_STATUS 0x11
43#define REG_AUTOTUNE 0x12
44
45struct max2165_priv {
46 struct max2165_config *config;
47 struct i2c_adapter *i2c;
48
49 u32 frequency;
50 u32 bandwidth;
51
52 u8 tf_ntch_low_cfg;
53 u8 tf_ntch_hi_cfg;
54 u8 tf_balun_low_ref;
55 u8 tf_balun_hi_ref;
56 u8 bb_filter_7mhz_cfg;
57 u8 bb_filter_8mhz_cfg;
58};
59
60#endif
diff --git a/drivers/media/common/tuners/mc44s803.c b/drivers/media/common/tuners/mc44s803.c
new file mode 100644
index 00000000000..fe5c4b8d83e
--- /dev/null
+++ b/drivers/media/common/tuners/mc44s803.c
@@ -0,0 +1,372 @@
1/*
2 * Driver for Freescale MC44S803 Low Power CMOS Broadband Tuner
3 *
4 * Copyright (c) 2009 Jochen Friedrich <jochen@scram.de>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 *
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.=
20 */
21
22#include <linux/module.h>
23#include <linux/delay.h>
24#include <linux/dvb/frontend.h>
25#include <linux/i2c.h>
26#include <linux/slab.h>
27
28#include "dvb_frontend.h"
29
30#include "mc44s803.h"
31#include "mc44s803_priv.h"
32
33#define mc_printk(level, format, arg...) \
34 printk(level "mc44s803: " format , ## arg)
35
36/* Writes a single register */
37static int mc44s803_writereg(struct mc44s803_priv *priv, u32 val)
38{
39 u8 buf[3];
40 struct i2c_msg msg = {
41 .addr = priv->cfg->i2c_address, .flags = 0, .buf = buf, .len = 3
42 };
43
44 buf[0] = (val & 0xff0000) >> 16;
45 buf[1] = (val & 0xff00) >> 8;
46 buf[2] = (val & 0xff);
47
48 if (i2c_transfer(priv->i2c, &msg, 1) != 1) {
49 mc_printk(KERN_WARNING, "I2C write failed\n");
50 return -EREMOTEIO;
51 }
52 return 0;
53}
54
55/* Reads a single register */
56static int mc44s803_readreg(struct mc44s803_priv *priv, u8 reg, u32 *val)
57{
58 u32 wval;
59 u8 buf[3];
60 int ret;
61 struct i2c_msg msg[] = {
62 { .addr = priv->cfg->i2c_address, .flags = I2C_M_RD,
63 .buf = buf, .len = 3 },
64 };
65
66 wval = MC44S803_REG_SM(MC44S803_REG_DATAREG, MC44S803_ADDR) |
67 MC44S803_REG_SM(reg, MC44S803_D);
68
69 ret = mc44s803_writereg(priv, wval);
70 if (ret)
71 return ret;
72
73 if (i2c_transfer(priv->i2c, msg, 1) != 1) {
74 mc_printk(KERN_WARNING, "I2C read failed\n");
75 return -EREMOTEIO;
76 }
77
78 *val = (buf[0] << 16) | (buf[1] << 8) | buf[2];
79
80 return 0;
81}
82
83static int mc44s803_release(struct dvb_frontend *fe)
84{
85 struct mc44s803_priv *priv = fe->tuner_priv;
86
87 fe->tuner_priv = NULL;
88 kfree(priv);
89
90 return 0;
91}
92
93static int mc44s803_init(struct dvb_frontend *fe)
94{
95 struct mc44s803_priv *priv = fe->tuner_priv;
96 u32 val;
97 int err;
98
99 if (fe->ops.i2c_gate_ctrl)
100 fe->ops.i2c_gate_ctrl(fe, 1);
101
102/* Reset chip */
103 val = MC44S803_REG_SM(MC44S803_REG_RESET, MC44S803_ADDR) |
104 MC44S803_REG_SM(1, MC44S803_RS);
105
106 err = mc44s803_writereg(priv, val);
107 if (err)
108 goto exit;
109
110 val = MC44S803_REG_SM(MC44S803_REG_RESET, MC44S803_ADDR);
111
112 err = mc44s803_writereg(priv, val);
113 if (err)
114 goto exit;
115
116/* Power Up and Start Osc */
117
118 val = MC44S803_REG_SM(MC44S803_REG_REFOSC, MC44S803_ADDR) |
119 MC44S803_REG_SM(0xC0, MC44S803_REFOSC) |
120 MC44S803_REG_SM(1, MC44S803_OSCSEL);
121
122 err = mc44s803_writereg(priv, val);
123 if (err)
124 goto exit;
125
126 val = MC44S803_REG_SM(MC44S803_REG_POWER, MC44S803_ADDR) |
127 MC44S803_REG_SM(0x200, MC44S803_POWER);
128
129 err = mc44s803_writereg(priv, val);
130 if (err)
131 goto exit;
132
133 msleep(10);
134
135 val = MC44S803_REG_SM(MC44S803_REG_REFOSC, MC44S803_ADDR) |
136 MC44S803_REG_SM(0x40, MC44S803_REFOSC) |
137 MC44S803_REG_SM(1, MC44S803_OSCSEL);
138
139 err = mc44s803_writereg(priv, val);
140 if (err)
141 goto exit;
142
143 msleep(20);
144
145/* Setup Mixer */
146
147 val = MC44S803_REG_SM(MC44S803_REG_MIXER, MC44S803_ADDR) |
148 MC44S803_REG_SM(1, MC44S803_TRI_STATE) |
149 MC44S803_REG_SM(0x7F, MC44S803_MIXER_RES);
150
151 err = mc44s803_writereg(priv, val);
152 if (err)
153 goto exit;
154
155/* Setup Cirquit Adjust */
156
157 val = MC44S803_REG_SM(MC44S803_REG_CIRCADJ, MC44S803_ADDR) |
158 MC44S803_REG_SM(1, MC44S803_G1) |
159 MC44S803_REG_SM(1, MC44S803_G3) |
160 MC44S803_REG_SM(0x3, MC44S803_CIRCADJ_RES) |
161 MC44S803_REG_SM(1, MC44S803_G6) |
162 MC44S803_REG_SM(priv->cfg->dig_out, MC44S803_S1) |
163 MC44S803_REG_SM(0x3, MC44S803_LP) |
164 MC44S803_REG_SM(1, MC44S803_CLRF) |
165 MC44S803_REG_SM(1, MC44S803_CLIF);
166
167 err = mc44s803_writereg(priv, val);
168 if (err)
169 goto exit;
170
171 val = MC44S803_REG_SM(MC44S803_REG_CIRCADJ, MC44S803_ADDR) |
172 MC44S803_REG_SM(1, MC44S803_G1) |
173 MC44S803_REG_SM(1, MC44S803_G3) |
174 MC44S803_REG_SM(0x3, MC44S803_CIRCADJ_RES) |
175 MC44S803_REG_SM(1, MC44S803_G6) |
176 MC44S803_REG_SM(priv->cfg->dig_out, MC44S803_S1) |
177 MC44S803_REG_SM(0x3, MC44S803_LP);
178
179 err = mc44s803_writereg(priv, val);
180 if (err)
181 goto exit;
182
183/* Setup Digtune */
184
185 val = MC44S803_REG_SM(MC44S803_REG_DIGTUNE, MC44S803_ADDR) |
186 MC44S803_REG_SM(3, MC44S803_XOD);
187
188 err = mc44s803_writereg(priv, val);
189 if (err)
190 goto exit;
191
192/* Setup AGC */
193
194 val = MC44S803_REG_SM(MC44S803_REG_LNAAGC, MC44S803_ADDR) |
195 MC44S803_REG_SM(1, MC44S803_AT1) |
196 MC44S803_REG_SM(1, MC44S803_AT2) |
197 MC44S803_REG_SM(1, MC44S803_AGC_AN_DIG) |
198 MC44S803_REG_SM(1, MC44S803_AGC_READ_EN) |
199 MC44S803_REG_SM(1, MC44S803_LNA0);
200
201 err = mc44s803_writereg(priv, val);
202 if (err)
203 goto exit;
204
205 if (fe->ops.i2c_gate_ctrl)
206 fe->ops.i2c_gate_ctrl(fe, 0);
207 return 0;
208
209exit:
210 if (fe->ops.i2c_gate_ctrl)
211 fe->ops.i2c_gate_ctrl(fe, 0);
212
213 mc_printk(KERN_WARNING, "I/O Error\n");
214 return err;
215}
216
217static int mc44s803_set_params(struct dvb_frontend *fe,
218 struct dvb_frontend_parameters *params)
219{
220 struct mc44s803_priv *priv = fe->tuner_priv;
221 u32 r1, r2, n1, n2, lo1, lo2, freq, val;
222 int err;
223
224 priv->frequency = params->frequency;
225
226 r1 = MC44S803_OSC / 1000000;
227 r2 = MC44S803_OSC / 100000;
228
229 n1 = (params->frequency + MC44S803_IF1 + 500000) / 1000000;
230 freq = MC44S803_OSC / r1 * n1;
231 lo1 = ((60 * n1) + (r1 / 2)) / r1;
232 freq = freq - params->frequency;
233
234 n2 = (freq - MC44S803_IF2 + 50000) / 100000;
235 lo2 = ((60 * n2) + (r2 / 2)) / r2;
236
237 if (fe->ops.i2c_gate_ctrl)
238 fe->ops.i2c_gate_ctrl(fe, 1);
239
240 val = MC44S803_REG_SM(MC44S803_REG_REFDIV, MC44S803_ADDR) |
241 MC44S803_REG_SM(r1-1, MC44S803_R1) |
242 MC44S803_REG_SM(r2-1, MC44S803_R2) |
243 MC44S803_REG_SM(1, MC44S803_REFBUF_EN);
244
245 err = mc44s803_writereg(priv, val);
246 if (err)
247 goto exit;
248
249 val = MC44S803_REG_SM(MC44S803_REG_LO1, MC44S803_ADDR) |
250 MC44S803_REG_SM(n1-2, MC44S803_LO1);
251
252 err = mc44s803_writereg(priv, val);
253 if (err)
254 goto exit;
255
256 val = MC44S803_REG_SM(MC44S803_REG_LO2, MC44S803_ADDR) |
257 MC44S803_REG_SM(n2-2, MC44S803_LO2);
258
259 err = mc44s803_writereg(priv, val);
260 if (err)
261 goto exit;
262
263 val = MC44S803_REG_SM(MC44S803_REG_DIGTUNE, MC44S803_ADDR) |
264 MC44S803_REG_SM(1, MC44S803_DA) |
265 MC44S803_REG_SM(lo1, MC44S803_LO_REF) |
266 MC44S803_REG_SM(1, MC44S803_AT);
267
268 err = mc44s803_writereg(priv, val);
269 if (err)
270 goto exit;
271
272 val = MC44S803_REG_SM(MC44S803_REG_DIGTUNE, MC44S803_ADDR) |
273 MC44S803_REG_SM(2, MC44S803_DA) |
274 MC44S803_REG_SM(lo2, MC44S803_LO_REF) |
275 MC44S803_REG_SM(1, MC44S803_AT);
276
277 err = mc44s803_writereg(priv, val);
278 if (err)
279 goto exit;
280
281 if (fe->ops.i2c_gate_ctrl)
282 fe->ops.i2c_gate_ctrl(fe, 0);
283
284 return 0;
285
286exit:
287 if (fe->ops.i2c_gate_ctrl)
288 fe->ops.i2c_gate_ctrl(fe, 0);
289
290 mc_printk(KERN_WARNING, "I/O Error\n");
291 return err;
292}
293
294static int mc44s803_get_frequency(struct dvb_frontend *fe, u32 *frequency)
295{
296 struct mc44s803_priv *priv = fe->tuner_priv;
297 *frequency = priv->frequency;
298 return 0;
299}
300
301static const struct dvb_tuner_ops mc44s803_tuner_ops = {
302 .info = {
303 .name = "Freescale MC44S803",
304 .frequency_min = 48000000,
305 .frequency_max = 1000000000,
306 .frequency_step = 100000,
307 },
308
309 .release = mc44s803_release,
310 .init = mc44s803_init,
311 .set_params = mc44s803_set_params,
312 .get_frequency = mc44s803_get_frequency
313};
314
315/* This functions tries to identify a MC44S803 tuner by reading the ID
316 register. This is hasty. */
317struct dvb_frontend *mc44s803_attach(struct dvb_frontend *fe,
318 struct i2c_adapter *i2c, struct mc44s803_config *cfg)
319{
320 struct mc44s803_priv *priv;
321 u32 reg;
322 u8 id;
323 int ret;
324
325 reg = 0;
326
327 priv = kzalloc(sizeof(struct mc44s803_priv), GFP_KERNEL);
328 if (priv == NULL)
329 return NULL;
330
331 priv->cfg = cfg;
332 priv->i2c = i2c;
333 priv->fe = fe;
334
335 if (fe->ops.i2c_gate_ctrl)
336 fe->ops.i2c_gate_ctrl(fe, 1); /* open i2c_gate */
337
338 ret = mc44s803_readreg(priv, MC44S803_REG_ID, &reg);
339 if (ret)
340 goto error;
341
342 id = MC44S803_REG_MS(reg, MC44S803_ID);
343
344 if (id != 0x14) {
345 mc_printk(KERN_ERR, "unsupported ID "
346 "(%x should be 0x14)\n", id);
347 goto error;
348 }
349
350 mc_printk(KERN_INFO, "successfully identified (ID = %x)\n", id);
351 memcpy(&fe->ops.tuner_ops, &mc44s803_tuner_ops,
352 sizeof(struct dvb_tuner_ops));
353
354 fe->tuner_priv = priv;
355
356 if (fe->ops.i2c_gate_ctrl)
357 fe->ops.i2c_gate_ctrl(fe, 0); /* close i2c_gate */
358
359 return fe;
360
361error:
362 if (fe->ops.i2c_gate_ctrl)
363 fe->ops.i2c_gate_ctrl(fe, 0); /* close i2c_gate */
364
365 kfree(priv);
366 return NULL;
367}
368EXPORT_SYMBOL(mc44s803_attach);
369
370MODULE_AUTHOR("Jochen Friedrich");
371MODULE_DESCRIPTION("Freescale MC44S803 silicon tuner driver");
372MODULE_LICENSE("GPL");
diff --git a/drivers/media/common/tuners/mc44s803.h b/drivers/media/common/tuners/mc44s803.h
new file mode 100644
index 00000000000..34f3892d3f6
--- /dev/null
+++ b/drivers/media/common/tuners/mc44s803.h
@@ -0,0 +1,46 @@
1/*
2 * Driver for Freescale MC44S803 Low Power CMOS Broadband Tuner
3 *
4 * Copyright (c) 2009 Jochen Friedrich <jochen@scram.de>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 *
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.=
20 */
21
22#ifndef MC44S803_H
23#define MC44S803_H
24
25struct dvb_frontend;
26struct i2c_adapter;
27
28struct mc44s803_config {
29 u8 i2c_address;
30 u8 dig_out;
31};
32
33#if defined(CONFIG_MEDIA_TUNER_MC44S803) || \
34 (defined(CONFIG_MEDIA_TUNER_MC44S803_MODULE) && defined(MODULE))
35extern struct dvb_frontend *mc44s803_attach(struct dvb_frontend *fe,
36 struct i2c_adapter *i2c, struct mc44s803_config *cfg);
37#else
38static inline struct dvb_frontend *mc44s803_attach(struct dvb_frontend *fe,
39 struct i2c_adapter *i2c, struct mc44s803_config *cfg)
40{
41 printk(KERN_WARNING "%s: driver disabled by Kconfig\n", __func__);
42 return NULL;
43}
44#endif /* CONFIG_MEDIA_TUNER_MC44S803 */
45
46#endif
diff --git a/drivers/media/common/tuners/mc44s803_priv.h b/drivers/media/common/tuners/mc44s803_priv.h
new file mode 100644
index 00000000000..14a92780906
--- /dev/null
+++ b/drivers/media/common/tuners/mc44s803_priv.h
@@ -0,0 +1,208 @@
1/*
2 * Driver for Freescale MC44S803 Low Power CMOS Broadband Tuner
3 *
4 * Copyright (c) 2009 Jochen Friedrich <jochen@scram.de>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 *
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.=
20 */
21
22#ifndef MC44S803_PRIV_H
23#define MC44S803_PRIV_H
24
25/* This driver is based on the information available in the datasheet
26 http://www.freescale.com/files/rf_if/doc/data_sheet/MC44S803.pdf
27
28 SPI or I2C Address : 0xc0-0xc6
29
30 Reg.No | Function
31 -------------------------------------------
32 00 | Power Down
33 01 | Reference Oszillator
34 02 | Reference Dividers
35 03 | Mixer and Reference Buffer
36 04 | Reset/Serial Out
37 05 | LO 1
38 06 | LO 2
39 07 | Circuit Adjust
40 08 | Test
41 09 | Digital Tune
42 0A | LNA AGC
43 0B | Data Register Address
44 0C | Regulator Test
45 0D | VCO Test
46 0E | LNA Gain/Input Power
47 0F | ID Bits
48
49*/
50
51#define MC44S803_OSC 26000000 /* 26 MHz */
52#define MC44S803_IF1 1086000000 /* 1086 MHz */
53#define MC44S803_IF2 36125000 /* 36.125 MHz */
54
55#define MC44S803_REG_POWER 0
56#define MC44S803_REG_REFOSC 1
57#define MC44S803_REG_REFDIV 2
58#define MC44S803_REG_MIXER 3
59#define MC44S803_REG_RESET 4
60#define MC44S803_REG_LO1 5
61#define MC44S803_REG_LO2 6
62#define MC44S803_REG_CIRCADJ 7
63#define MC44S803_REG_TEST 8
64#define MC44S803_REG_DIGTUNE 9
65#define MC44S803_REG_LNAAGC 0x0A
66#define MC44S803_REG_DATAREG 0x0B
67#define MC44S803_REG_REGTEST 0x0C
68#define MC44S803_REG_VCOTEST 0x0D
69#define MC44S803_REG_LNAGAIN 0x0E
70#define MC44S803_REG_ID 0x0F
71
72/* Register definitions */
73#define MC44S803_ADDR 0x0F
74#define MC44S803_ADDR_S 0
75/* REG_POWER */
76#define MC44S803_POWER 0xFFFFF0
77#define MC44S803_POWER_S 4
78/* REG_REFOSC */
79#define MC44S803_REFOSC 0x1FF0
80#define MC44S803_REFOSC_S 4
81#define MC44S803_OSCSEL 0x2000
82#define MC44S803_OSCSEL_S 13
83/* REG_REFDIV */
84#define MC44S803_R2 0x1FF0
85#define MC44S803_R2_S 4
86#define MC44S803_REFBUF_EN 0x2000
87#define MC44S803_REFBUF_EN_S 13
88#define MC44S803_R1 0x7C000
89#define MC44S803_R1_S 14
90/* REG_MIXER */
91#define MC44S803_R3 0x70
92#define MC44S803_R3_S 4
93#define MC44S803_MUX3 0x80
94#define MC44S803_MUX3_S 7
95#define MC44S803_MUX4 0x100
96#define MC44S803_MUX4_S 8
97#define MC44S803_OSC_SCR 0x200
98#define MC44S803_OSC_SCR_S 9
99#define MC44S803_TRI_STATE 0x400
100#define MC44S803_TRI_STATE_S 10
101#define MC44S803_BUF_GAIN 0x800
102#define MC44S803_BUF_GAIN_S 11
103#define MC44S803_BUF_IO 0x1000
104#define MC44S803_BUF_IO_S 12
105#define MC44S803_MIXER_RES 0xFE000
106#define MC44S803_MIXER_RES_S 13
107/* REG_RESET */
108#define MC44S803_RS 0x10
109#define MC44S803_RS_S 4
110#define MC44S803_SO 0x20
111#define MC44S803_SO_S 5
112/* REG_LO1 */
113#define MC44S803_LO1 0xFFF0
114#define MC44S803_LO1_S 4
115/* REG_LO2 */
116#define MC44S803_LO2 0x7FFF0
117#define MC44S803_LO2_S 4
118/* REG_CIRCADJ */
119#define MC44S803_G1 0x20
120#define MC44S803_G1_S 5
121#define MC44S803_G3 0x80
122#define MC44S803_G3_S 7
123#define MC44S803_CIRCADJ_RES 0x300
124#define MC44S803_CIRCADJ_RES_S 8
125#define MC44S803_G6 0x400
126#define MC44S803_G6_S 10
127#define MC44S803_G7 0x800
128#define MC44S803_G7_S 11
129#define MC44S803_S1 0x1000
130#define MC44S803_S1_S 12
131#define MC44S803_LP 0x7E000
132#define MC44S803_LP_S 13
133#define MC44S803_CLRF 0x80000
134#define MC44S803_CLRF_S 19
135#define MC44S803_CLIF 0x100000
136#define MC44S803_CLIF_S 20
137/* REG_TEST */
138/* REG_DIGTUNE */
139#define MC44S803_DA 0xF0
140#define MC44S803_DA_S 4
141#define MC44S803_XOD 0x300
142#define MC44S803_XOD_S 8
143#define MC44S803_RST 0x10000
144#define MC44S803_RST_S 16
145#define MC44S803_LO_REF 0x1FFF00
146#define MC44S803_LO_REF_S 8
147#define MC44S803_AT 0x200000
148#define MC44S803_AT_S 21
149#define MC44S803_MT 0x400000
150#define MC44S803_MT_S 22
151/* REG_LNAAGC */
152#define MC44S803_G 0x3F0
153#define MC44S803_G_S 4
154#define MC44S803_AT1 0x400
155#define MC44S803_AT1_S 10
156#define MC44S803_AT2 0x800
157#define MC44S803_AT2_S 11
158#define MC44S803_HL_GR_EN 0x8000
159#define MC44S803_HL_GR_EN_S 15
160#define MC44S803_AGC_AN_DIG 0x10000
161#define MC44S803_AGC_AN_DIG_S 16
162#define MC44S803_ATTEN_EN 0x20000
163#define MC44S803_ATTEN_EN_S 17
164#define MC44S803_AGC_READ_EN 0x40000
165#define MC44S803_AGC_READ_EN_S 18
166#define MC44S803_LNA0 0x80000
167#define MC44S803_LNA0_S 19
168#define MC44S803_AGC_SEL 0x100000
169#define MC44S803_AGC_SEL_S 20
170#define MC44S803_AT0 0x200000
171#define MC44S803_AT0_S 21
172#define MC44S803_B 0xC00000
173#define MC44S803_B_S 22
174/* REG_DATAREG */
175#define MC44S803_D 0xF0
176#define MC44S803_D_S 4
177/* REG_REGTEST */
178/* REG_VCOTEST */
179/* REG_LNAGAIN */
180#define MC44S803_IF_PWR 0x700
181#define MC44S803_IF_PWR_S 8
182#define MC44S803_RF_PWR 0x3800
183#define MC44S803_RF_PWR_S 11
184#define MC44S803_LNA_GAIN 0xFC000
185#define MC44S803_LNA_GAIN_S 14
186/* REG_ID */
187#define MC44S803_ID 0x3E00
188#define MC44S803_ID_S 9
189
190/* Some macros to read/write fields */
191
192/* First shift, then mask */
193#define MC44S803_REG_SM(_val, _reg) \
194 (((_val) << _reg##_S) & (_reg))
195
196/* First mask, then shift */
197#define MC44S803_REG_MS(_val, _reg) \
198 (((_val) & (_reg)) >> _reg##_S)
199
200struct mc44s803_priv {
201 struct mc44s803_config *cfg;
202 struct i2c_adapter *i2c;
203 struct dvb_frontend *fe;
204
205 u32 frequency;
206};
207
208#endif
diff --git a/drivers/media/common/tuners/mt2060.c b/drivers/media/common/tuners/mt2060.c
new file mode 100644
index 00000000000..2d0e7689c6a
--- /dev/null
+++ b/drivers/media/common/tuners/mt2060.c
@@ -0,0 +1,404 @@
1/*
2 * Driver for Microtune MT2060 "Single chip dual conversion broadband tuner"
3 *
4 * Copyright (c) 2006 Olivier DANET <odanet@caramail.com>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 *
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.=
20 */
21
22/* In that file, frequencies are expressed in kiloHertz to avoid 32 bits overflows */
23
24#include <linux/module.h>
25#include <linux/delay.h>
26#include <linux/dvb/frontend.h>
27#include <linux/i2c.h>
28#include <linux/slab.h>
29
30#include "dvb_frontend.h"
31
32#include "mt2060.h"
33#include "mt2060_priv.h"
34
35static int debug;
36module_param(debug, int, 0644);
37MODULE_PARM_DESC(debug, "Turn on/off debugging (default:off).");
38
39#define dprintk(args...) do { if (debug) {printk(KERN_DEBUG "MT2060: " args); printk("\n"); }} while (0)
40
41// Reads a single register
42static int mt2060_readreg(struct mt2060_priv *priv, u8 reg, u8 *val)
43{
44 struct i2c_msg msg[2] = {
45 { .addr = priv->cfg->i2c_address, .flags = 0, .buf = &reg, .len = 1 },
46 { .addr = priv->cfg->i2c_address, .flags = I2C_M_RD, .buf = val, .len = 1 },
47 };
48
49 if (i2c_transfer(priv->i2c, msg, 2) != 2) {
50 printk(KERN_WARNING "mt2060 I2C read failed\n");
51 return -EREMOTEIO;
52 }
53 return 0;
54}
55
56// Writes a single register
57static int mt2060_writereg(struct mt2060_priv *priv, u8 reg, u8 val)
58{
59 u8 buf[2] = { reg, val };
60 struct i2c_msg msg = {
61 .addr = priv->cfg->i2c_address, .flags = 0, .buf = buf, .len = 2
62 };
63
64 if (i2c_transfer(priv->i2c, &msg, 1) != 1) {
65 printk(KERN_WARNING "mt2060 I2C write failed\n");
66 return -EREMOTEIO;
67 }
68 return 0;
69}
70
71// Writes a set of consecutive registers
72static int mt2060_writeregs(struct mt2060_priv *priv,u8 *buf, u8 len)
73{
74 struct i2c_msg msg = {
75 .addr = priv->cfg->i2c_address, .flags = 0, .buf = buf, .len = len
76 };
77 if (i2c_transfer(priv->i2c, &msg, 1) != 1) {
78 printk(KERN_WARNING "mt2060 I2C write failed (len=%i)\n",(int)len);
79 return -EREMOTEIO;
80 }
81 return 0;
82}
83
84// Initialisation sequences
85// LNABAND=3, NUM1=0x3C, DIV1=0x74, NUM2=0x1080, DIV2=0x49
86static u8 mt2060_config1[] = {
87 REG_LO1C1,
88 0x3F, 0x74, 0x00, 0x08, 0x93
89};
90
91// FMCG=2, GP2=0, GP1=0
92static u8 mt2060_config2[] = {
93 REG_MISC_CTRL,
94 0x20, 0x1E, 0x30, 0xff, 0x80, 0xff, 0x00, 0x2c, 0x42
95};
96
97// VGAG=3, V1CSE=1
98
99#ifdef MT2060_SPURCHECK
100/* The function below calculates the frequency offset between the output frequency if2
101 and the closer cross modulation subcarrier between lo1 and lo2 up to the tenth harmonic */
102static int mt2060_spurcalc(u32 lo1,u32 lo2,u32 if2)
103{
104 int I,J;
105 int dia,diamin,diff;
106 diamin=1000000;
107 for (I = 1; I < 10; I++) {
108 J = ((2*I*lo1)/lo2+1)/2;
109 diff = I*(int)lo1-J*(int)lo2;
110 if (diff < 0) diff=-diff;
111 dia = (diff-(int)if2);
112 if (dia < 0) dia=-dia;
113 if (diamin > dia) diamin=dia;
114 }
115 return diamin;
116}
117
118#define BANDWIDTH 4000 // kHz
119
120/* Calculates the frequency offset to add to avoid spurs. Returns 0 if no offset is needed */
121static int mt2060_spurcheck(u32 lo1,u32 lo2,u32 if2)
122{
123 u32 Spur,Sp1,Sp2;
124 int I,J;
125 I=0;
126 J=1000;
127
128 Spur=mt2060_spurcalc(lo1,lo2,if2);
129 if (Spur < BANDWIDTH) {
130 /* Potential spurs detected */
131 dprintk("Spurs before : f_lo1: %d f_lo2: %d (kHz)",
132 (int)lo1,(int)lo2);
133 I=1000;
134 Sp1 = mt2060_spurcalc(lo1+I,lo2+I,if2);
135 Sp2 = mt2060_spurcalc(lo1-I,lo2-I,if2);
136
137 if (Sp1 < Sp2) {
138 J=-J; I=-I; Spur=Sp2;
139 } else
140 Spur=Sp1;
141
142 while (Spur < BANDWIDTH) {
143 I += J;
144 Spur = mt2060_spurcalc(lo1+I,lo2+I,if2);
145 }
146 dprintk("Spurs after : f_lo1: %d f_lo2: %d (kHz)",
147 (int)(lo1+I),(int)(lo2+I));
148 }
149 return I;
150}
151#endif
152
153#define IF2 36150 // IF2 frequency = 36.150 MHz
154#define FREF 16000 // Quartz oscillator 16 MHz
155
156static int mt2060_set_params(struct dvb_frontend *fe, struct dvb_frontend_parameters *params)
157{
158 struct mt2060_priv *priv;
159 int ret=0;
160 int i=0;
161 u32 freq;
162 u8 lnaband;
163 u32 f_lo1,f_lo2;
164 u32 div1,num1,div2,num2;
165 u8 b[8];
166 u32 if1;
167
168 priv = fe->tuner_priv;
169
170 if1 = priv->if1_freq;
171 b[0] = REG_LO1B1;
172 b[1] = 0xFF;
173
174 if (fe->ops.i2c_gate_ctrl)
175 fe->ops.i2c_gate_ctrl(fe, 1); /* open i2c_gate */
176
177 mt2060_writeregs(priv,b,2);
178
179 freq = params->frequency / 1000; // Hz -> kHz
180 priv->bandwidth = (fe->ops.info.type == FE_OFDM) ? params->u.ofdm.bandwidth : 0;
181
182 f_lo1 = freq + if1 * 1000;
183 f_lo1 = (f_lo1 / 250) * 250;
184 f_lo2 = f_lo1 - freq - IF2;
185 // From the Comtech datasheet, the step used is 50kHz. The tuner chip could be more precise
186 f_lo2 = ((f_lo2 + 25) / 50) * 50;
187 priv->frequency = (f_lo1 - f_lo2 - IF2) * 1000,
188
189#ifdef MT2060_SPURCHECK
190 // LO-related spurs detection and correction
191 num1 = mt2060_spurcheck(f_lo1,f_lo2,IF2);
192 f_lo1 += num1;
193 f_lo2 += num1;
194#endif
195 //Frequency LO1 = 16MHz * (DIV1 + NUM1/64 )
196 num1 = f_lo1 / (FREF / 64);
197 div1 = num1 / 64;
198 num1 &= 0x3f;
199
200 // Frequency LO2 = 16MHz * (DIV2 + NUM2/8192 )
201 num2 = f_lo2 * 64 / (FREF / 128);
202 div2 = num2 / 8192;
203 num2 &= 0x1fff;
204
205 if (freq <= 95000) lnaband = 0xB0; else
206 if (freq <= 180000) lnaband = 0xA0; else
207 if (freq <= 260000) lnaband = 0x90; else
208 if (freq <= 335000) lnaband = 0x80; else
209 if (freq <= 425000) lnaband = 0x70; else
210 if (freq <= 480000) lnaband = 0x60; else
211 if (freq <= 570000) lnaband = 0x50; else
212 if (freq <= 645000) lnaband = 0x40; else
213 if (freq <= 730000) lnaband = 0x30; else
214 if (freq <= 810000) lnaband = 0x20; else lnaband = 0x10;
215
216 b[0] = REG_LO1C1;
217 b[1] = lnaband | ((num1 >>2) & 0x0F);
218 b[2] = div1;
219 b[3] = (num2 & 0x0F) | ((num1 & 3) << 4);
220 b[4] = num2 >> 4;
221 b[5] = ((num2 >>12) & 1) | (div2 << 1);
222
223 dprintk("IF1: %dMHz",(int)if1);
224 dprintk("PLL freq=%dkHz f_lo1=%dkHz f_lo2=%dkHz",(int)freq,(int)f_lo1,(int)f_lo2);
225 dprintk("PLL div1=%d num1=%d div2=%d num2=%d",(int)div1,(int)num1,(int)div2,(int)num2);
226 dprintk("PLL [1..5]: %2x %2x %2x %2x %2x",(int)b[1],(int)b[2],(int)b[3],(int)b[4],(int)b[5]);
227
228 mt2060_writeregs(priv,b,6);
229
230 //Waits for pll lock or timeout
231 i = 0;
232 do {
233 mt2060_readreg(priv,REG_LO_STATUS,b);
234 if ((b[0] & 0x88)==0x88)
235 break;
236 msleep(4);
237 i++;
238 } while (i<10);
239
240 if (fe->ops.i2c_gate_ctrl)
241 fe->ops.i2c_gate_ctrl(fe, 0); /* close i2c_gate */
242
243 return ret;
244}
245
246static void mt2060_calibrate(struct mt2060_priv *priv)
247{
248 u8 b = 0;
249 int i = 0;
250
251 if (mt2060_writeregs(priv,mt2060_config1,sizeof(mt2060_config1)))
252 return;
253 if (mt2060_writeregs(priv,mt2060_config2,sizeof(mt2060_config2)))
254 return;
255
256 /* initialize the clock output */
257 mt2060_writereg(priv, REG_VGAG, (priv->cfg->clock_out << 6) | 0x30);
258
259 do {
260 b |= (1 << 6); // FM1SS;
261 mt2060_writereg(priv, REG_LO2C1,b);
262 msleep(20);
263
264 if (i == 0) {
265 b |= (1 << 7); // FM1CA;
266 mt2060_writereg(priv, REG_LO2C1,b);
267 b &= ~(1 << 7); // FM1CA;
268 msleep(20);
269 }
270
271 b &= ~(1 << 6); // FM1SS
272 mt2060_writereg(priv, REG_LO2C1,b);
273
274 msleep(20);
275 i++;
276 } while (i < 9);
277
278 i = 0;
279 while (i++ < 10 && mt2060_readreg(priv, REG_MISC_STAT, &b) == 0 && (b & (1 << 6)) == 0)
280 msleep(20);
281
282 if (i <= 10) {
283 mt2060_readreg(priv, REG_FM_FREQ, &priv->fmfreq); // now find out, what is fmreq used for :)
284 dprintk("calibration was successful: %d", (int)priv->fmfreq);
285 } else
286 dprintk("FMCAL timed out");
287}
288
289static int mt2060_get_frequency(struct dvb_frontend *fe, u32 *frequency)
290{
291 struct mt2060_priv *priv = fe->tuner_priv;
292 *frequency = priv->frequency;
293 return 0;
294}
295
296static int mt2060_get_bandwidth(struct dvb_frontend *fe, u32 *bandwidth)
297{
298 struct mt2060_priv *priv = fe->tuner_priv;
299 *bandwidth = priv->bandwidth;
300 return 0;
301}
302
303static int mt2060_init(struct dvb_frontend *fe)
304{
305 struct mt2060_priv *priv = fe->tuner_priv;
306 int ret;
307
308 if (fe->ops.i2c_gate_ctrl)
309 fe->ops.i2c_gate_ctrl(fe, 1); /* open i2c_gate */
310
311 ret = mt2060_writereg(priv, REG_VGAG,
312 (priv->cfg->clock_out << 6) | 0x33);
313
314 if (fe->ops.i2c_gate_ctrl)
315 fe->ops.i2c_gate_ctrl(fe, 0); /* close i2c_gate */
316
317 return ret;
318}
319
320static int mt2060_sleep(struct dvb_frontend *fe)
321{
322 struct mt2060_priv *priv = fe->tuner_priv;
323 int ret;
324
325 if (fe->ops.i2c_gate_ctrl)
326 fe->ops.i2c_gate_ctrl(fe, 1); /* open i2c_gate */
327
328 ret = mt2060_writereg(priv, REG_VGAG,
329 (priv->cfg->clock_out << 6) | 0x30);
330
331 if (fe->ops.i2c_gate_ctrl)
332 fe->ops.i2c_gate_ctrl(fe, 0); /* close i2c_gate */
333
334 return ret;
335}
336
337static int mt2060_release(struct dvb_frontend *fe)
338{
339 kfree(fe->tuner_priv);
340 fe->tuner_priv = NULL;
341 return 0;
342}
343
344static const struct dvb_tuner_ops mt2060_tuner_ops = {
345 .info = {
346 .name = "Microtune MT2060",
347 .frequency_min = 48000000,
348 .frequency_max = 860000000,
349 .frequency_step = 50000,
350 },
351
352 .release = mt2060_release,
353
354 .init = mt2060_init,
355 .sleep = mt2060_sleep,
356
357 .set_params = mt2060_set_params,
358 .get_frequency = mt2060_get_frequency,
359 .get_bandwidth = mt2060_get_bandwidth
360};
361
362/* This functions tries to identify a MT2060 tuner by reading the PART/REV register. This is hasty. */
363struct dvb_frontend * mt2060_attach(struct dvb_frontend *fe, struct i2c_adapter *i2c, struct mt2060_config *cfg, u16 if1)
364{
365 struct mt2060_priv *priv = NULL;
366 u8 id = 0;
367
368 priv = kzalloc(sizeof(struct mt2060_priv), GFP_KERNEL);
369 if (priv == NULL)
370 return NULL;
371
372 priv->cfg = cfg;
373 priv->i2c = i2c;
374 priv->if1_freq = if1;
375
376 if (fe->ops.i2c_gate_ctrl)
377 fe->ops.i2c_gate_ctrl(fe, 1); /* open i2c_gate */
378
379 if (mt2060_readreg(priv,REG_PART_REV,&id) != 0) {
380 kfree(priv);
381 return NULL;
382 }
383
384 if (id != PART_REV) {
385 kfree(priv);
386 return NULL;
387 }
388 printk(KERN_INFO "MT2060: successfully identified (IF1 = %d)\n", if1);
389 memcpy(&fe->ops.tuner_ops, &mt2060_tuner_ops, sizeof(struct dvb_tuner_ops));
390
391 fe->tuner_priv = priv;
392
393 mt2060_calibrate(priv);
394
395 if (fe->ops.i2c_gate_ctrl)
396 fe->ops.i2c_gate_ctrl(fe, 0); /* close i2c_gate */
397
398 return fe;
399}
400EXPORT_SYMBOL(mt2060_attach);
401
402MODULE_AUTHOR("Olivier DANET");
403MODULE_DESCRIPTION("Microtune MT2060 silicon tuner driver");
404MODULE_LICENSE("GPL");
diff --git a/drivers/media/common/tuners/mt2060.h b/drivers/media/common/tuners/mt2060.h
new file mode 100644
index 00000000000..cb60caffb6b
--- /dev/null
+++ b/drivers/media/common/tuners/mt2060.h
@@ -0,0 +1,43 @@
1/*
2 * Driver for Microtune MT2060 "Single chip dual conversion broadband tuner"
3 *
4 * Copyright (c) 2006 Olivier DANET <odanet@caramail.com>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 *
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.=
20 */
21
22#ifndef MT2060_H
23#define MT2060_H
24
25struct dvb_frontend;
26struct i2c_adapter;
27
28struct mt2060_config {
29 u8 i2c_address;
30 u8 clock_out; /* 0 = off, 1 = CLK/4, 2 = CLK/2, 3 = CLK/1 */
31};
32
33#if defined(CONFIG_MEDIA_TUNER_MT2060) || (defined(CONFIG_MEDIA_TUNER_MT2060_MODULE) && defined(MODULE))
34extern struct dvb_frontend * mt2060_attach(struct dvb_frontend *fe, struct i2c_adapter *i2c, struct mt2060_config *cfg, u16 if1);
35#else
36static inline struct dvb_frontend * mt2060_attach(struct dvb_frontend *fe, struct i2c_adapter *i2c, struct mt2060_config *cfg, u16 if1)
37{
38 printk(KERN_WARNING "%s: driver disabled by Kconfig\n", __func__);
39 return NULL;
40}
41#endif // CONFIG_MEDIA_TUNER_MT2060
42
43#endif
diff --git a/drivers/media/common/tuners/mt2060_priv.h b/drivers/media/common/tuners/mt2060_priv.h
new file mode 100644
index 00000000000..5eaccdefd0b
--- /dev/null
+++ b/drivers/media/common/tuners/mt2060_priv.h
@@ -0,0 +1,105 @@
1/*
2 * Driver for Microtune MT2060 "Single chip dual conversion broadband tuner"
3 *
4 * Copyright (c) 2006 Olivier DANET <odanet@caramail.com>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 *
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.=
20 */
21
22#ifndef MT2060_PRIV_H
23#define MT2060_PRIV_H
24
25// Uncomment the #define below to enable spurs checking. The results where quite unconvincing.
26// #define MT2060_SPURCHECK
27
28/* This driver is based on the information available in the datasheet of the
29 "Comtech SDVBT-3K6M" tuner ( K1000737843.pdf ) which features the MT2060 register map :
30
31 I2C Address : 0x60
32
33 Reg.No | B7 | B6 | B5 | B4 | B3 | B2 | B1 | B0 | ( defaults )
34 --------------------------------------------------------------------------------
35 00 | [ PART ] | [ REV ] | R = 0x63
36 01 | [ LNABAND ] | [ NUM1(5:2) ] | RW = 0x3F
37 02 | [ DIV1 ] | RW = 0x74
38 03 | FM1CA | FM1SS | [ NUM1(1:0) ] | [ NUM2(3:0) ] | RW = 0x00
39 04 | NUM2(11:4) ] | RW = 0x08
40 05 | [ DIV2 ] |NUM2(12)| RW = 0x93
41 06 | L1LK | [ TAD1 ] | L2LK | [ TAD2 ] | R
42 07 | [ FMF ] | R
43 08 | ? | FMCAL | ? | ? | ? | ? | ? | TEMP | R
44 09 | 0 | 0 | [ FMGC ] | 0 | GP02 | GP01 | 0 | RW = 0x20
45 0A | ??
46 0B | 0 | 0 | 1 | 1 | 0 | 0 | [ VGAG ] | RW = 0x30
47 0C | V1CSE | 1 | 1 | 1 | 1 | 1 | 1 | 1 | RW = 0xFF
48 0D | 1 | 0 | [ V1CS ] | RW = 0xB0
49 0E | ??
50 0F | ??
51 10 | ??
52 11 | [ LOTO ] | 0 | 0 | 1 | 0 | RW = 0x42
53
54 PART : Part code : 6 for MT2060
55 REV : Revision code : 3 for current revision
56 LNABAND : Input frequency range : ( See code for details )
57 NUM1 / DIV1 / NUM2 / DIV2 : Frequencies programming ( See code for details )
58 FM1CA : Calibration Start Bit
59 FM1SS : Calibration Single Step bit
60 L1LK : LO1 Lock Detect
61 TAD1 : Tune Line ADC ( ? )
62 L2LK : LO2 Lock Detect
63 TAD2 : Tune Line ADC ( ? )
64 FMF : Estimated first IF Center frequency Offset ( ? )
65 FM1CAL : Calibration done bit
66 TEMP : On chip temperature sensor
67 FMCG : Mixer 1 Cap Gain ( ? )
68 GP01 / GP02 : Programmable digital outputs. Unconnected pins ?
69 V1CSE : LO1 VCO Automatic Capacitor Select Enable ( ? )
70 V1CS : LO1 Capacitor Selection Value ( ? )
71 LOTO : LO Timeout ( ? )
72 VGAG : Tuner Output gain
73*/
74
75#define I2C_ADDRESS 0x60
76
77#define REG_PART_REV 0
78#define REG_LO1C1 1
79#define REG_LO1C2 2
80#define REG_LO2C1 3
81#define REG_LO2C2 4
82#define REG_LO2C3 5
83#define REG_LO_STATUS 6
84#define REG_FM_FREQ 7
85#define REG_MISC_STAT 8
86#define REG_MISC_CTRL 9
87#define REG_RESERVED_A 0x0A
88#define REG_VGAG 0x0B
89#define REG_LO1B1 0x0C
90#define REG_LO1B2 0x0D
91#define REG_LOTO 0x11
92
93#define PART_REV 0x63 // The current driver works only with PART=6 and REV=3 chips
94
95struct mt2060_priv {
96 struct mt2060_config *cfg;
97 struct i2c_adapter *i2c;
98
99 u32 frequency;
100 u32 bandwidth;
101 u16 if1_freq;
102 u8 fmfreq;
103};
104
105#endif
diff --git a/drivers/media/common/tuners/mt20xx.c b/drivers/media/common/tuners/mt20xx.c
new file mode 100644
index 00000000000..d0e70e10a71
--- /dev/null
+++ b/drivers/media/common/tuners/mt20xx.c
@@ -0,0 +1,672 @@
1/*
2 * i2c tv tuner chip device driver
3 * controls microtune tuners, mt2032 + mt2050 at the moment.
4 *
5 * This "mt20xx" module was split apart from the original "tuner" module.
6 */
7#include <linux/delay.h>
8#include <linux/i2c.h>
9#include <linux/slab.h>
10#include <linux/videodev2.h>
11#include "tuner-i2c.h"
12#include "mt20xx.h"
13
14static int debug;
15module_param(debug, int, 0644);
16MODULE_PARM_DESC(debug, "enable verbose debug messages");
17
18/* ---------------------------------------------------------------------- */
19
20static unsigned int optimize_vco = 1;
21module_param(optimize_vco, int, 0644);
22
23static unsigned int tv_antenna = 1;
24module_param(tv_antenna, int, 0644);
25
26static unsigned int radio_antenna;
27module_param(radio_antenna, int, 0644);
28
29/* ---------------------------------------------------------------------- */
30
31#define MT2032 0x04
32#define MT2030 0x06
33#define MT2040 0x07
34#define MT2050 0x42
35
36static char *microtune_part[] = {
37 [ MT2030 ] = "MT2030",
38 [ MT2032 ] = "MT2032",
39 [ MT2040 ] = "MT2040",
40 [ MT2050 ] = "MT2050",
41};
42
43struct microtune_priv {
44 struct tuner_i2c_props i2c_props;
45
46 unsigned int xogc;
47 //unsigned int radio_if2;
48
49 u32 frequency;
50};
51
52static int microtune_release(struct dvb_frontend *fe)
53{
54 kfree(fe->tuner_priv);
55 fe->tuner_priv = NULL;
56
57 return 0;
58}
59
60static int microtune_get_frequency(struct dvb_frontend *fe, u32 *frequency)
61{
62 struct microtune_priv *priv = fe->tuner_priv;
63 *frequency = priv->frequency;
64 return 0;
65}
66
67// IsSpurInBand()?
68static int mt2032_spurcheck(struct dvb_frontend *fe,
69 int f1, int f2, int spectrum_from,int spectrum_to)
70{
71 struct microtune_priv *priv = fe->tuner_priv;
72 int n1=1,n2,f;
73
74 f1=f1/1000; //scale to kHz to avoid 32bit overflows
75 f2=f2/1000;
76 spectrum_from/=1000;
77 spectrum_to/=1000;
78
79 tuner_dbg("spurcheck f1=%d f2=%d from=%d to=%d\n",
80 f1,f2,spectrum_from,spectrum_to);
81
82 do {
83 n2=-n1;
84 f=n1*(f1-f2);
85 do {
86 n2--;
87 f=f-f2;
88 tuner_dbg("spurtest n1=%d n2=%d ftest=%d\n",n1,n2,f);
89
90 if( (f>spectrum_from) && (f<spectrum_to))
91 tuner_dbg("mt2032 spurcheck triggered: %d\n",n1);
92 } while ( (f>(f2-spectrum_to)) || (n2>-5));
93 n1++;
94 } while (n1<5);
95
96 return 1;
97}
98
99static int mt2032_compute_freq(struct dvb_frontend *fe,
100 unsigned int rfin,
101 unsigned int if1, unsigned int if2,
102 unsigned int spectrum_from,
103 unsigned int spectrum_to,
104 unsigned char *buf,
105 int *ret_sel,
106 unsigned int xogc) //all in Hz
107{
108 struct microtune_priv *priv = fe->tuner_priv;
109 unsigned int fref,lo1,lo1n,lo1a,s,sel,lo1freq, desired_lo1,
110 desired_lo2,lo2,lo2n,lo2a,lo2num,lo2freq;
111
112 fref= 5250 *1000; //5.25MHz
113 desired_lo1=rfin+if1;
114
115 lo1=(2*(desired_lo1/1000)+(fref/1000)) / (2*fref/1000);
116 lo1n=lo1/8;
117 lo1a=lo1-(lo1n*8);
118
119 s=rfin/1000/1000+1090;
120
121 if(optimize_vco) {
122 if(s>1890) sel=0;
123 else if(s>1720) sel=1;
124 else if(s>1530) sel=2;
125 else if(s>1370) sel=3;
126 else sel=4; // >1090
127 }
128 else {
129 if(s>1790) sel=0; // <1958
130 else if(s>1617) sel=1;
131 else if(s>1449) sel=2;
132 else if(s>1291) sel=3;
133 else sel=4; // >1090
134 }
135 *ret_sel=sel;
136
137 lo1freq=(lo1a+8*lo1n)*fref;
138
139 tuner_dbg("mt2032: rfin=%d lo1=%d lo1n=%d lo1a=%d sel=%d, lo1freq=%d\n",
140 rfin,lo1,lo1n,lo1a,sel,lo1freq);
141
142 desired_lo2=lo1freq-rfin-if2;
143 lo2=(desired_lo2)/fref;
144 lo2n=lo2/8;
145 lo2a=lo2-(lo2n*8);
146 lo2num=((desired_lo2/1000)%(fref/1000))* 3780/(fref/1000); //scale to fit in 32bit arith
147 lo2freq=(lo2a+8*lo2n)*fref + lo2num*(fref/1000)/3780*1000;
148
149 tuner_dbg("mt2032: rfin=%d lo2=%d lo2n=%d lo2a=%d num=%d lo2freq=%d\n",
150 rfin,lo2,lo2n,lo2a,lo2num,lo2freq);
151
152 if (lo1a > 7 || lo1n < 17 || lo1n > 48 || lo2a > 7 || lo2n < 17 ||
153 lo2n > 30) {
154 tuner_info("mt2032: frequency parameters out of range: %d %d %d %d\n",
155 lo1a, lo1n, lo2a,lo2n);
156 return(-1);
157 }
158
159 mt2032_spurcheck(fe, lo1freq, desired_lo2, spectrum_from, spectrum_to);
160 // should recalculate lo1 (one step up/down)
161
162 // set up MT2032 register map for transfer over i2c
163 buf[0]=lo1n-1;
164 buf[1]=lo1a | (sel<<4);
165 buf[2]=0x86; // LOGC
166 buf[3]=0x0f; //reserved
167 buf[4]=0x1f;
168 buf[5]=(lo2n-1) | (lo2a<<5);
169 if(rfin >400*1000*1000)
170 buf[6]=0xe4;
171 else
172 buf[6]=0xf4; // set PKEN per rev 1.2
173 buf[7]=8+xogc;
174 buf[8]=0xc3; //reserved
175 buf[9]=0x4e; //reserved
176 buf[10]=0xec; //reserved
177 buf[11]=(lo2num&0xff);
178 buf[12]=(lo2num>>8) |0x80; // Lo2RST
179
180 return 0;
181}
182
183static int mt2032_check_lo_lock(struct dvb_frontend *fe)
184{
185 struct microtune_priv *priv = fe->tuner_priv;
186 int try,lock=0;
187 unsigned char buf[2];
188
189 for(try=0;try<10;try++) {
190 buf[0]=0x0e;
191 tuner_i2c_xfer_send(&priv->i2c_props,buf,1);
192 tuner_i2c_xfer_recv(&priv->i2c_props,buf,1);
193 tuner_dbg("mt2032 Reg.E=0x%02x\n",buf[0]);
194 lock=buf[0] &0x06;
195
196 if (lock==6)
197 break;
198
199 tuner_dbg("mt2032: pll wait 1ms for lock (0x%2x)\n",buf[0]);
200 udelay(1000);
201 }
202 return lock;
203}
204
205static int mt2032_optimize_vco(struct dvb_frontend *fe,int sel,int lock)
206{
207 struct microtune_priv *priv = fe->tuner_priv;
208 unsigned char buf[2];
209 int tad1;
210
211 buf[0]=0x0f;
212 tuner_i2c_xfer_send(&priv->i2c_props,buf,1);
213 tuner_i2c_xfer_recv(&priv->i2c_props,buf,1);
214 tuner_dbg("mt2032 Reg.F=0x%02x\n",buf[0]);
215 tad1=buf[0]&0x07;
216
217 if(tad1 ==0) return lock;
218 if(tad1 ==1) return lock;
219
220 if(tad1==2) {
221 if(sel==0)
222 return lock;
223 else sel--;
224 }
225 else {
226 if(sel<4)
227 sel++;
228 else
229 return lock;
230 }
231
232 tuner_dbg("mt2032 optimize_vco: sel=%d\n",sel);
233
234 buf[0]=0x0f;
235 buf[1]=sel;
236 tuner_i2c_xfer_send(&priv->i2c_props,buf,2);
237 lock=mt2032_check_lo_lock(fe);
238 return lock;
239}
240
241
242static void mt2032_set_if_freq(struct dvb_frontend *fe, unsigned int rfin,
243 unsigned int if1, unsigned int if2,
244 unsigned int from, unsigned int to)
245{
246 unsigned char buf[21];
247 int lint_try,ret,sel,lock=0;
248 struct microtune_priv *priv = fe->tuner_priv;
249
250 tuner_dbg("mt2032_set_if_freq rfin=%d if1=%d if2=%d from=%d to=%d\n",
251 rfin,if1,if2,from,to);
252
253 buf[0]=0;
254 ret=tuner_i2c_xfer_send(&priv->i2c_props,buf,1);
255 tuner_i2c_xfer_recv(&priv->i2c_props,buf,21);
256
257 buf[0]=0;
258 ret=mt2032_compute_freq(fe,rfin,if1,if2,from,to,&buf[1],&sel,priv->xogc);
259 if (ret<0)
260 return;
261
262 // send only the relevant registers per Rev. 1.2
263 buf[0]=0;
264 ret=tuner_i2c_xfer_send(&priv->i2c_props,buf,4);
265 buf[5]=5;
266 ret=tuner_i2c_xfer_send(&priv->i2c_props,buf+5,4);
267 buf[11]=11;
268 ret=tuner_i2c_xfer_send(&priv->i2c_props,buf+11,3);
269 if(ret!=3)
270 tuner_warn("i2c i/o error: rc == %d (should be 3)\n",ret);
271
272 // wait for PLLs to lock (per manual), retry LINT if not.
273 for(lint_try=0; lint_try<2; lint_try++) {
274 lock=mt2032_check_lo_lock(fe);
275
276 if(optimize_vco)
277 lock=mt2032_optimize_vco(fe,sel,lock);
278 if(lock==6) break;
279
280 tuner_dbg("mt2032: re-init PLLs by LINT\n");
281 buf[0]=7;
282 buf[1]=0x80 +8+priv->xogc; // set LINT to re-init PLLs
283 tuner_i2c_xfer_send(&priv->i2c_props,buf,2);
284 mdelay(10);
285 buf[1]=8+priv->xogc;
286 tuner_i2c_xfer_send(&priv->i2c_props,buf,2);
287 }
288
289 if (lock!=6)
290 tuner_warn("MT2032 Fatal Error: PLLs didn't lock.\n");
291
292 buf[0]=2;
293 buf[1]=0x20; // LOGC for optimal phase noise
294 ret=tuner_i2c_xfer_send(&priv->i2c_props,buf,2);
295 if (ret!=2)
296 tuner_warn("i2c i/o error: rc == %d (should be 2)\n",ret);
297}
298
299
300static int mt2032_set_tv_freq(struct dvb_frontend *fe,
301 struct analog_parameters *params)
302{
303 int if2,from,to;
304
305 // signal bandwidth and picture carrier
306 if (params->std & V4L2_STD_525_60) {
307 // NTSC
308 from = 40750*1000;
309 to = 46750*1000;
310 if2 = 45750*1000;
311 } else {
312 // PAL
313 from = 32900*1000;
314 to = 39900*1000;
315 if2 = 38900*1000;
316 }
317
318 mt2032_set_if_freq(fe, params->frequency*62500,
319 1090*1000*1000, if2, from, to);
320
321 return 0;
322}
323
324static int mt2032_set_radio_freq(struct dvb_frontend *fe,
325 struct analog_parameters *params)
326{
327 struct microtune_priv *priv = fe->tuner_priv;
328 int if2;
329
330 if (params->std & V4L2_STD_525_60) {
331 tuner_dbg("pinnacle ntsc\n");
332 if2 = 41300 * 1000;
333 } else {
334 tuner_dbg("pinnacle pal\n");
335 if2 = 33300 * 1000;
336 }
337
338 // per Manual for FM tuning: first if center freq. 1085 MHz
339 mt2032_set_if_freq(fe, params->frequency * 125 / 2,
340 1085*1000*1000,if2,if2,if2);
341
342 return 0;
343}
344
345static int mt2032_set_params(struct dvb_frontend *fe,
346 struct analog_parameters *params)
347{
348 struct microtune_priv *priv = fe->tuner_priv;
349 int ret = -EINVAL;
350
351 switch (params->mode) {
352 case V4L2_TUNER_RADIO:
353 ret = mt2032_set_radio_freq(fe, params);
354 priv->frequency = params->frequency * 125 / 2;
355 break;
356 case V4L2_TUNER_ANALOG_TV:
357 case V4L2_TUNER_DIGITAL_TV:
358 ret = mt2032_set_tv_freq(fe, params);
359 priv->frequency = params->frequency * 62500;
360 break;
361 }
362
363 return ret;
364}
365
366static struct dvb_tuner_ops mt2032_tuner_ops = {
367 .set_analog_params = mt2032_set_params,
368 .release = microtune_release,
369 .get_frequency = microtune_get_frequency,
370};
371
372// Initialization as described in "MT203x Programming Procedures", Rev 1.2, Feb.2001
373static int mt2032_init(struct dvb_frontend *fe)
374{
375 struct microtune_priv *priv = fe->tuner_priv;
376 unsigned char buf[21];
377 int ret,xogc,xok=0;
378
379 // Initialize Registers per spec.
380 buf[1]=2; // Index to register 2
381 buf[2]=0xff;
382 buf[3]=0x0f;
383 buf[4]=0x1f;
384 ret=tuner_i2c_xfer_send(&priv->i2c_props,buf+1,4);
385
386 buf[5]=6; // Index register 6
387 buf[6]=0xe4;
388 buf[7]=0x8f;
389 buf[8]=0xc3;
390 buf[9]=0x4e;
391 buf[10]=0xec;
392 ret=tuner_i2c_xfer_send(&priv->i2c_props,buf+5,6);
393
394 buf[12]=13; // Index register 13
395 buf[13]=0x32;
396 ret=tuner_i2c_xfer_send(&priv->i2c_props,buf+12,2);
397
398 // Adjust XOGC (register 7), wait for XOK
399 xogc=7;
400 do {
401 tuner_dbg("mt2032: xogc = 0x%02x\n",xogc&0x07);
402 mdelay(10);
403 buf[0]=0x0e;
404 tuner_i2c_xfer_send(&priv->i2c_props,buf,1);
405 tuner_i2c_xfer_recv(&priv->i2c_props,buf,1);
406 xok=buf[0]&0x01;
407 tuner_dbg("mt2032: xok = 0x%02x\n",xok);
408 if (xok == 1) break;
409
410 xogc--;
411 tuner_dbg("mt2032: xogc = 0x%02x\n",xogc&0x07);
412 if (xogc == 3) {
413 xogc=4; // min. 4 per spec
414 break;
415 }
416 buf[0]=0x07;
417 buf[1]=0x88 + xogc;
418 ret=tuner_i2c_xfer_send(&priv->i2c_props,buf,2);
419 if (ret!=2)
420 tuner_warn("i2c i/o error: rc == %d (should be 2)\n",ret);
421 } while (xok != 1 );
422 priv->xogc=xogc;
423
424 memcpy(&fe->ops.tuner_ops, &mt2032_tuner_ops, sizeof(struct dvb_tuner_ops));
425
426 return(1);
427}
428
429static void mt2050_set_antenna(struct dvb_frontend *fe, unsigned char antenna)
430{
431 struct microtune_priv *priv = fe->tuner_priv;
432 unsigned char buf[2];
433 int ret;
434
435 buf[0] = 6;
436 buf[1] = antenna ? 0x11 : 0x10;
437 ret=tuner_i2c_xfer_send(&priv->i2c_props,buf,2);
438 tuner_dbg("mt2050: enabled antenna connector %d\n", antenna);
439}
440
441static void mt2050_set_if_freq(struct dvb_frontend *fe,unsigned int freq, unsigned int if2)
442{
443 struct microtune_priv *priv = fe->tuner_priv;
444 unsigned int if1=1218*1000*1000;
445 unsigned int f_lo1,f_lo2,lo1,lo2,f_lo1_modulo,f_lo2_modulo,num1,num2,div1a,div1b,div2a,div2b;
446 int ret;
447 unsigned char buf[6];
448
449 tuner_dbg("mt2050_set_if_freq freq=%d if1=%d if2=%d\n",
450 freq,if1,if2);
451
452 f_lo1=freq+if1;
453 f_lo1=(f_lo1/1000000)*1000000;
454
455 f_lo2=f_lo1-freq-if2;
456 f_lo2=(f_lo2/50000)*50000;
457
458 lo1=f_lo1/4000000;
459 lo2=f_lo2/4000000;
460
461 f_lo1_modulo= f_lo1-(lo1*4000000);
462 f_lo2_modulo= f_lo2-(lo2*4000000);
463
464 num1=4*f_lo1_modulo/4000000;
465 num2=4096*(f_lo2_modulo/1000)/4000;
466
467 // todo spurchecks
468
469 div1a=(lo1/12)-1;
470 div1b=lo1-(div1a+1)*12;
471
472 div2a=(lo2/8)-1;
473 div2b=lo2-(div2a+1)*8;
474
475 if (debug > 1) {
476 tuner_dbg("lo1 lo2 = %d %d\n", lo1, lo2);
477 tuner_dbg("num1 num2 div1a div1b div2a div2b= %x %x %x %x %x %x\n",
478 num1,num2,div1a,div1b,div2a,div2b);
479 }
480
481 buf[0]=1;
482 buf[1]= 4*div1b + num1;
483 if(freq<275*1000*1000) buf[1] = buf[1]|0x80;
484
485 buf[2]=div1a;
486 buf[3]=32*div2b + num2/256;
487 buf[4]=num2-(num2/256)*256;
488 buf[5]=div2a;
489 if(num2!=0) buf[5]=buf[5]|0x40;
490
491 if (debug > 1) {
492 int i;
493 tuner_dbg("bufs is: ");
494 for(i=0;i<6;i++)
495 printk("%x ",buf[i]);
496 printk("\n");
497 }
498
499 ret=tuner_i2c_xfer_send(&priv->i2c_props,buf,6);
500 if (ret!=6)
501 tuner_warn("i2c i/o error: rc == %d (should be 6)\n",ret);
502}
503
504static int mt2050_set_tv_freq(struct dvb_frontend *fe,
505 struct analog_parameters *params)
506{
507 unsigned int if2;
508
509 if (params->std & V4L2_STD_525_60) {
510 // NTSC
511 if2 = 45750*1000;
512 } else {
513 // PAL
514 if2 = 38900*1000;
515 }
516 if (V4L2_TUNER_DIGITAL_TV == params->mode) {
517 // DVB (pinnacle 300i)
518 if2 = 36150*1000;
519 }
520 mt2050_set_if_freq(fe, params->frequency*62500, if2);
521 mt2050_set_antenna(fe, tv_antenna);
522
523 return 0;
524}
525
526static int mt2050_set_radio_freq(struct dvb_frontend *fe,
527 struct analog_parameters *params)
528{
529 struct microtune_priv *priv = fe->tuner_priv;
530 int if2;
531
532 if (params->std & V4L2_STD_525_60) {
533 tuner_dbg("pinnacle ntsc\n");
534 if2 = 41300 * 1000;
535 } else {
536 tuner_dbg("pinnacle pal\n");
537 if2 = 33300 * 1000;
538 }
539
540 mt2050_set_if_freq(fe, params->frequency * 125 / 2, if2);
541 mt2050_set_antenna(fe, radio_antenna);
542
543 return 0;
544}
545
546static int mt2050_set_params(struct dvb_frontend *fe,
547 struct analog_parameters *params)
548{
549 struct microtune_priv *priv = fe->tuner_priv;
550 int ret = -EINVAL;
551
552 switch (params->mode) {
553 case V4L2_TUNER_RADIO:
554 ret = mt2050_set_radio_freq(fe, params);
555 priv->frequency = params->frequency * 125 / 2;
556 break;
557 case V4L2_TUNER_ANALOG_TV:
558 case V4L2_TUNER_DIGITAL_TV:
559 ret = mt2050_set_tv_freq(fe, params);
560 priv->frequency = params->frequency * 62500;
561 break;
562 }
563
564 return ret;
565}
566
567static struct dvb_tuner_ops mt2050_tuner_ops = {
568 .set_analog_params = mt2050_set_params,
569 .release = microtune_release,
570 .get_frequency = microtune_get_frequency,
571};
572
573static int mt2050_init(struct dvb_frontend *fe)
574{
575 struct microtune_priv *priv = fe->tuner_priv;
576 unsigned char buf[2];
577 int ret;
578
579 buf[0]=6;
580 buf[1]=0x10;
581 ret=tuner_i2c_xfer_send(&priv->i2c_props,buf,2); // power
582
583 buf[0]=0x0f;
584 buf[1]=0x0f;
585 ret=tuner_i2c_xfer_send(&priv->i2c_props,buf,2); // m1lo
586
587 buf[0]=0x0d;
588 ret=tuner_i2c_xfer_send(&priv->i2c_props,buf,1);
589 tuner_i2c_xfer_recv(&priv->i2c_props,buf,1);
590
591 tuner_dbg("mt2050: sro is %x\n",buf[0]);
592
593 memcpy(&fe->ops.tuner_ops, &mt2050_tuner_ops, sizeof(struct dvb_tuner_ops));
594
595 return 0;
596}
597
598struct dvb_frontend *microtune_attach(struct dvb_frontend *fe,
599 struct i2c_adapter* i2c_adap,
600 u8 i2c_addr)
601{
602 struct microtune_priv *priv = NULL;
603 char *name;
604 unsigned char buf[21];
605 int company_code;
606
607 priv = kzalloc(sizeof(struct microtune_priv), GFP_KERNEL);
608 if (priv == NULL)
609 return NULL;
610 fe->tuner_priv = priv;
611
612 priv->i2c_props.addr = i2c_addr;
613 priv->i2c_props.adap = i2c_adap;
614 priv->i2c_props.name = "mt20xx";
615
616 //priv->radio_if2 = 10700 * 1000; /* 10.7MHz - FM radio */
617
618 memset(buf,0,sizeof(buf));
619
620 name = "unknown";
621
622 tuner_i2c_xfer_send(&priv->i2c_props,buf,1);
623 tuner_i2c_xfer_recv(&priv->i2c_props,buf,21);
624 if (debug) {
625 int i;
626 tuner_dbg("MT20xx hexdump:");
627 for(i=0;i<21;i++) {
628 printk(" %02x",buf[i]);
629 if(((i+1)%8)==0) printk(" ");
630 }
631 printk("\n");
632 }
633 company_code = buf[0x11] << 8 | buf[0x12];
634 tuner_info("microtune: companycode=%04x part=%02x rev=%02x\n",
635 company_code,buf[0x13],buf[0x14]);
636
637
638 if (buf[0x13] < ARRAY_SIZE(microtune_part) &&
639 NULL != microtune_part[buf[0x13]])
640 name = microtune_part[buf[0x13]];
641 switch (buf[0x13]) {
642 case MT2032:
643 mt2032_init(fe);
644 break;
645 case MT2050:
646 mt2050_init(fe);
647 break;
648 default:
649 tuner_info("microtune %s found, not (yet?) supported, sorry :-/\n",
650 name);
651 return NULL;
652 }
653
654 strlcpy(fe->ops.tuner_ops.info.name, name,
655 sizeof(fe->ops.tuner_ops.info.name));
656 tuner_info("microtune %s found, OK\n",name);
657 return fe;
658}
659
660EXPORT_SYMBOL_GPL(microtune_attach);
661
662MODULE_DESCRIPTION("Microtune tuner driver");
663MODULE_AUTHOR("Ralph Metzler, Gerd Knorr, Gunther Mayer");
664MODULE_LICENSE("GPL");
665
666/*
667 * Overrides for Emacs so that we follow Linus's tabbing style.
668 * ---------------------------------------------------------------------------
669 * Local variables:
670 * c-basic-offset: 8
671 * End:
672 */
diff --git a/drivers/media/common/tuners/mt20xx.h b/drivers/media/common/tuners/mt20xx.h
new file mode 100644
index 00000000000..259553a2490
--- /dev/null
+++ b/drivers/media/common/tuners/mt20xx.h
@@ -0,0 +1,37 @@
1/*
2 This program is free software; you can redistribute it and/or modify
3 it under the terms of the GNU General Public License as published by
4 the Free Software Foundation; either version 2 of the License, or
5 (at your option) any later version.
6
7 This program is distributed in the hope that it will be useful,
8 but WITHOUT ANY WARRANTY; without even the implied warranty of
9 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10 GNU General Public License for more details.
11
12 You should have received a copy of the GNU General Public License
13 along with this program; if not, write to the Free Software
14 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
15*/
16
17#ifndef __MT20XX_H__
18#define __MT20XX_H__
19
20#include <linux/i2c.h>
21#include "dvb_frontend.h"
22
23#if defined(CONFIG_MEDIA_TUNER_MT20XX) || (defined(CONFIG_MEDIA_TUNER_MT20XX_MODULE) && defined(MODULE))
24extern struct dvb_frontend *microtune_attach(struct dvb_frontend *fe,
25 struct i2c_adapter* i2c_adap,
26 u8 i2c_addr);
27#else
28static inline struct dvb_frontend *microtune_attach(struct dvb_frontend *fe,
29 struct i2c_adapter* i2c_adap,
30 u8 i2c_addr)
31{
32 printk(KERN_WARNING "%s: driver disabled by Kconfig\n", __func__);
33 return NULL;
34}
35#endif
36
37#endif /* __MT20XX_H__ */
diff --git a/drivers/media/common/tuners/mt2131.c b/drivers/media/common/tuners/mt2131.c
new file mode 100644
index 00000000000..a4f830bb25d
--- /dev/null
+++ b/drivers/media/common/tuners/mt2131.c
@@ -0,0 +1,315 @@
1/*
2 * Driver for Microtune MT2131 "QAM/8VSB single chip tuner"
3 *
4 * Copyright (c) 2006 Steven Toth <stoth@linuxtv.org>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 *
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
20 */
21
22#include <linux/module.h>
23#include <linux/delay.h>
24#include <linux/dvb/frontend.h>
25#include <linux/i2c.h>
26#include <linux/slab.h>
27
28#include "dvb_frontend.h"
29
30#include "mt2131.h"
31#include "mt2131_priv.h"
32
33static int debug;
34module_param(debug, int, 0644);
35MODULE_PARM_DESC(debug, "Turn on/off debugging (default:off).");
36
37#define dprintk(level,fmt, arg...) if (debug >= level) \
38 printk(KERN_INFO "%s: " fmt, "mt2131", ## arg)
39
40static u8 mt2131_config1[] = {
41 0x01,
42 0x50, 0x00, 0x50, 0x80, 0x00, 0x49, 0xfa, 0x88,
43 0x08, 0x77, 0x41, 0x04, 0x00, 0x00, 0x00, 0x32,
44 0x7f, 0xda, 0x4c, 0x00, 0x10, 0xaa, 0x78, 0x80,
45 0xff, 0x68, 0xa0, 0xff, 0xdd, 0x00, 0x00
46};
47
48static u8 mt2131_config2[] = {
49 0x10,
50 0x7f, 0xc8, 0x0a, 0x5f, 0x00, 0x04
51};
52
53static int mt2131_readreg(struct mt2131_priv *priv, u8 reg, u8 *val)
54{
55 struct i2c_msg msg[2] = {
56 { .addr = priv->cfg->i2c_address, .flags = 0,
57 .buf = &reg, .len = 1 },
58 { .addr = priv->cfg->i2c_address, .flags = I2C_M_RD,
59 .buf = val, .len = 1 },
60 };
61
62 if (i2c_transfer(priv->i2c, msg, 2) != 2) {
63 printk(KERN_WARNING "mt2131 I2C read failed\n");
64 return -EREMOTEIO;
65 }
66 return 0;
67}
68
69static int mt2131_writereg(struct mt2131_priv *priv, u8 reg, u8 val)
70{
71 u8 buf[2] = { reg, val };
72 struct i2c_msg msg = { .addr = priv->cfg->i2c_address, .flags = 0,
73 .buf = buf, .len = 2 };
74
75 if (i2c_transfer(priv->i2c, &msg, 1) != 1) {
76 printk(KERN_WARNING "mt2131 I2C write failed\n");
77 return -EREMOTEIO;
78 }
79 return 0;
80}
81
82static int mt2131_writeregs(struct mt2131_priv *priv,u8 *buf, u8 len)
83{
84 struct i2c_msg msg = { .addr = priv->cfg->i2c_address,
85 .flags = 0, .buf = buf, .len = len };
86
87 if (i2c_transfer(priv->i2c, &msg, 1) != 1) {
88 printk(KERN_WARNING "mt2131 I2C write failed (len=%i)\n",
89 (int)len);
90 return -EREMOTEIO;
91 }
92 return 0;
93}
94
95static int mt2131_set_params(struct dvb_frontend *fe,
96 struct dvb_frontend_parameters *params)
97{
98 struct mt2131_priv *priv;
99 int ret=0, i;
100 u32 freq;
101 u8 if_band_center;
102 u32 f_lo1, f_lo2;
103 u32 div1, num1, div2, num2;
104 u8 b[8];
105 u8 lockval = 0;
106
107 priv = fe->tuner_priv;
108 if (fe->ops.info.type == FE_OFDM)
109 priv->bandwidth = params->u.ofdm.bandwidth;
110 else
111 priv->bandwidth = 0;
112
113 freq = params->frequency / 1000; // Hz -> kHz
114 dprintk(1, "%s() freq=%d\n", __func__, freq);
115
116 f_lo1 = freq + MT2131_IF1 * 1000;
117 f_lo1 = (f_lo1 / 250) * 250;
118 f_lo2 = f_lo1 - freq - MT2131_IF2;
119
120 priv->frequency = (f_lo1 - f_lo2 - MT2131_IF2) * 1000;
121
122 /* Frequency LO1 = 16MHz * (DIV1 + NUM1/8192 ) */
123 num1 = f_lo1 * 64 / (MT2131_FREF / 128);
124 div1 = num1 / 8192;
125 num1 &= 0x1fff;
126
127 /* Frequency LO2 = 16MHz * (DIV2 + NUM2/8192 ) */
128 num2 = f_lo2 * 64 / (MT2131_FREF / 128);
129 div2 = num2 / 8192;
130 num2 &= 0x1fff;
131
132 if (freq <= 82500) if_band_center = 0x00; else
133 if (freq <= 137500) if_band_center = 0x01; else
134 if (freq <= 192500) if_band_center = 0x02; else
135 if (freq <= 247500) if_band_center = 0x03; else
136 if (freq <= 302500) if_band_center = 0x04; else
137 if (freq <= 357500) if_band_center = 0x05; else
138 if (freq <= 412500) if_band_center = 0x06; else
139 if (freq <= 467500) if_band_center = 0x07; else
140 if (freq <= 522500) if_band_center = 0x08; else
141 if (freq <= 577500) if_band_center = 0x09; else
142 if (freq <= 632500) if_band_center = 0x0A; else
143 if (freq <= 687500) if_band_center = 0x0B; else
144 if (freq <= 742500) if_band_center = 0x0C; else
145 if (freq <= 797500) if_band_center = 0x0D; else
146 if (freq <= 852500) if_band_center = 0x0E; else
147 if (freq <= 907500) if_band_center = 0x0F; else
148 if (freq <= 962500) if_band_center = 0x10; else
149 if (freq <= 1017500) if_band_center = 0x11; else
150 if (freq <= 1072500) if_band_center = 0x12; else if_band_center = 0x13;
151
152 b[0] = 1;
153 b[1] = (num1 >> 5) & 0xFF;
154 b[2] = (num1 & 0x1F);
155 b[3] = div1;
156 b[4] = (num2 >> 5) & 0xFF;
157 b[5] = num2 & 0x1F;
158 b[6] = div2;
159
160 dprintk(1, "IF1: %dMHz IF2: %dMHz\n", MT2131_IF1, MT2131_IF2);
161 dprintk(1, "PLL freq=%dkHz band=%d\n", (int)freq, (int)if_band_center);
162 dprintk(1, "PLL f_lo1=%dkHz f_lo2=%dkHz\n", (int)f_lo1, (int)f_lo2);
163 dprintk(1, "PLL div1=%d num1=%d div2=%d num2=%d\n",
164 (int)div1, (int)num1, (int)div2, (int)num2);
165 dprintk(1, "PLL [1..6]: %2x %2x %2x %2x %2x %2x\n",
166 (int)b[1], (int)b[2], (int)b[3], (int)b[4], (int)b[5],
167 (int)b[6]);
168
169 ret = mt2131_writeregs(priv,b,7);
170 if (ret < 0)
171 return ret;
172
173 mt2131_writereg(priv, 0x0b, if_band_center);
174
175 /* Wait for lock */
176 i = 0;
177 do {
178 mt2131_readreg(priv, 0x08, &lockval);
179 if ((lockval & 0x88) == 0x88)
180 break;
181 msleep(4);
182 i++;
183 } while (i < 10);
184
185 return ret;
186}
187
188static int mt2131_get_frequency(struct dvb_frontend *fe, u32 *frequency)
189{
190 struct mt2131_priv *priv = fe->tuner_priv;
191 dprintk(1, "%s()\n", __func__);
192 *frequency = priv->frequency;
193 return 0;
194}
195
196static int mt2131_get_bandwidth(struct dvb_frontend *fe, u32 *bandwidth)
197{
198 struct mt2131_priv *priv = fe->tuner_priv;
199 dprintk(1, "%s()\n", __func__);
200 *bandwidth = priv->bandwidth;
201 return 0;
202}
203
204static int mt2131_get_status(struct dvb_frontend *fe, u32 *status)
205{
206 struct mt2131_priv *priv = fe->tuner_priv;
207 u8 lock_status = 0;
208 u8 afc_status = 0;
209
210 *status = 0;
211
212 mt2131_readreg(priv, 0x08, &lock_status);
213 if ((lock_status & 0x88) == 0x88)
214 *status = TUNER_STATUS_LOCKED;
215
216 mt2131_readreg(priv, 0x09, &afc_status);
217 dprintk(1, "%s() - LO Status = 0x%x, AFC Status = 0x%x\n",
218 __func__, lock_status, afc_status);
219
220 return 0;
221}
222
223static int mt2131_init(struct dvb_frontend *fe)
224{
225 struct mt2131_priv *priv = fe->tuner_priv;
226 int ret;
227 dprintk(1, "%s()\n", __func__);
228
229 if ((ret = mt2131_writeregs(priv, mt2131_config1,
230 sizeof(mt2131_config1))) < 0)
231 return ret;
232
233 mt2131_writereg(priv, 0x0b, 0x09);
234 mt2131_writereg(priv, 0x15, 0x47);
235 mt2131_writereg(priv, 0x07, 0xf2);
236 mt2131_writereg(priv, 0x0b, 0x01);
237
238 if ((ret = mt2131_writeregs(priv, mt2131_config2,
239 sizeof(mt2131_config2))) < 0)
240 return ret;
241
242 return ret;
243}
244
245static int mt2131_release(struct dvb_frontend *fe)
246{
247 dprintk(1, "%s()\n", __func__);
248 kfree(fe->tuner_priv);
249 fe->tuner_priv = NULL;
250 return 0;
251}
252
253static const struct dvb_tuner_ops mt2131_tuner_ops = {
254 .info = {
255 .name = "Microtune MT2131",
256 .frequency_min = 48000000,
257 .frequency_max = 860000000,
258 .frequency_step = 50000,
259 },
260
261 .release = mt2131_release,
262 .init = mt2131_init,
263
264 .set_params = mt2131_set_params,
265 .get_frequency = mt2131_get_frequency,
266 .get_bandwidth = mt2131_get_bandwidth,
267 .get_status = mt2131_get_status
268};
269
270struct dvb_frontend * mt2131_attach(struct dvb_frontend *fe,
271 struct i2c_adapter *i2c,
272 struct mt2131_config *cfg, u16 if1)
273{
274 struct mt2131_priv *priv = NULL;
275 u8 id = 0;
276
277 dprintk(1, "%s()\n", __func__);
278
279 priv = kzalloc(sizeof(struct mt2131_priv), GFP_KERNEL);
280 if (priv == NULL)
281 return NULL;
282
283 priv->cfg = cfg;
284 priv->bandwidth = 6000000; /* 6MHz */
285 priv->i2c = i2c;
286
287 if (mt2131_readreg(priv, 0, &id) != 0) {
288 kfree(priv);
289 return NULL;
290 }
291 if ( (id != 0x3E) && (id != 0x3F) ) {
292 printk(KERN_ERR "MT2131: Device not found at addr 0x%02x\n",
293 cfg->i2c_address);
294 kfree(priv);
295 return NULL;
296 }
297
298 printk(KERN_INFO "MT2131: successfully identified at address 0x%02x\n",
299 cfg->i2c_address);
300 memcpy(&fe->ops.tuner_ops, &mt2131_tuner_ops,
301 sizeof(struct dvb_tuner_ops));
302
303 fe->tuner_priv = priv;
304 return fe;
305}
306EXPORT_SYMBOL(mt2131_attach);
307
308MODULE_AUTHOR("Steven Toth");
309MODULE_DESCRIPTION("Microtune MT2131 silicon tuner driver");
310MODULE_LICENSE("GPL");
311
312/*
313 * Local variables:
314 * c-basic-offset: 8
315 */
diff --git a/drivers/media/common/tuners/mt2131.h b/drivers/media/common/tuners/mt2131.h
new file mode 100644
index 00000000000..6632de640df
--- /dev/null
+++ b/drivers/media/common/tuners/mt2131.h
@@ -0,0 +1,54 @@
1/*
2 * Driver for Microtune MT2131 "QAM/8VSB single chip tuner"
3 *
4 * Copyright (c) 2006 Steven Toth <stoth@linuxtv.org>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 *
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
20 */
21
22#ifndef __MT2131_H__
23#define __MT2131_H__
24
25struct dvb_frontend;
26struct i2c_adapter;
27
28struct mt2131_config {
29 u8 i2c_address;
30 u8 clock_out; /* 0 = off, 1 = CLK/4, 2 = CLK/2, 3 = CLK/1 */
31};
32
33#if defined(CONFIG_MEDIA_TUNER_MT2131) || (defined(CONFIG_MEDIA_TUNER_MT2131_MODULE) && defined(MODULE))
34extern struct dvb_frontend* mt2131_attach(struct dvb_frontend *fe,
35 struct i2c_adapter *i2c,
36 struct mt2131_config *cfg,
37 u16 if1);
38#else
39static inline struct dvb_frontend* mt2131_attach(struct dvb_frontend *fe,
40 struct i2c_adapter *i2c,
41 struct mt2131_config *cfg,
42 u16 if1)
43{
44 printk(KERN_WARNING "%s: driver disabled by Kconfig\n", __func__);
45 return NULL;
46}
47#endif /* CONFIG_MEDIA_TUNER_MT2131 */
48
49#endif /* __MT2131_H__ */
50
51/*
52 * Local variables:
53 * c-basic-offset: 8
54 */
diff --git a/drivers/media/common/tuners/mt2131_priv.h b/drivers/media/common/tuners/mt2131_priv.h
new file mode 100644
index 00000000000..4e05a67e88c
--- /dev/null
+++ b/drivers/media/common/tuners/mt2131_priv.h
@@ -0,0 +1,49 @@
1/*
2 * Driver for Microtune MT2131 "QAM/8VSB single chip tuner"
3 *
4 * Copyright (c) 2006 Steven Toth <stoth@linuxtv.org>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 *
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
20 */
21
22#ifndef __MT2131_PRIV_H__
23#define __MT2131_PRIV_H__
24
25/* Regs */
26#define MT2131_PWR 0x07
27#define MT2131_UPC_1 0x0b
28#define MT2131_AGC_RL 0x10
29#define MT2131_MISC_2 0x15
30
31/* frequency values in KHz */
32#define MT2131_IF1 1220
33#define MT2131_IF2 44000
34#define MT2131_FREF 16000
35
36struct mt2131_priv {
37 struct mt2131_config *cfg;
38 struct i2c_adapter *i2c;
39
40 u32 frequency;
41 u32 bandwidth;
42};
43
44#endif /* __MT2131_PRIV_H__ */
45
46/*
47 * Local variables:
48 * c-basic-offset: 8
49 */
diff --git a/drivers/media/common/tuners/mt2266.c b/drivers/media/common/tuners/mt2266.c
new file mode 100644
index 00000000000..25a8ea342c4
--- /dev/null
+++ b/drivers/media/common/tuners/mt2266.c
@@ -0,0 +1,352 @@
1/*
2 * Driver for Microtune MT2266 "Direct conversion low power broadband tuner"
3 *
4 * Copyright (c) 2007 Olivier DANET <odanet@caramail.com>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 */
16
17#include <linux/module.h>
18#include <linux/delay.h>
19#include <linux/dvb/frontend.h>
20#include <linux/i2c.h>
21#include <linux/slab.h>
22
23#include "dvb_frontend.h"
24#include "mt2266.h"
25
26#define I2C_ADDRESS 0x60
27
28#define REG_PART_REV 0
29#define REG_TUNE 1
30#define REG_BAND 6
31#define REG_BANDWIDTH 8
32#define REG_LOCK 0x12
33
34#define PART_REV 0x85
35
36struct mt2266_priv {
37 struct mt2266_config *cfg;
38 struct i2c_adapter *i2c;
39
40 u32 frequency;
41 u32 bandwidth;
42 u8 band;
43};
44
45#define MT2266_VHF 1
46#define MT2266_UHF 0
47
48/* Here, frequencies are expressed in kiloHertz to avoid 32 bits overflows */
49
50static int debug;
51module_param(debug, int, 0644);
52MODULE_PARM_DESC(debug, "Turn on/off debugging (default:off).");
53
54#define dprintk(args...) do { if (debug) {printk(KERN_DEBUG "MT2266: " args); printk("\n"); }} while (0)
55
56// Reads a single register
57static int mt2266_readreg(struct mt2266_priv *priv, u8 reg, u8 *val)
58{
59 struct i2c_msg msg[2] = {
60 { .addr = priv->cfg->i2c_address, .flags = 0, .buf = &reg, .len = 1 },
61 { .addr = priv->cfg->i2c_address, .flags = I2C_M_RD, .buf = val, .len = 1 },
62 };
63 if (i2c_transfer(priv->i2c, msg, 2) != 2) {
64 printk(KERN_WARNING "MT2266 I2C read failed\n");
65 return -EREMOTEIO;
66 }
67 return 0;
68}
69
70// Writes a single register
71static int mt2266_writereg(struct mt2266_priv *priv, u8 reg, u8 val)
72{
73 u8 buf[2] = { reg, val };
74 struct i2c_msg msg = {
75 .addr = priv->cfg->i2c_address, .flags = 0, .buf = buf, .len = 2
76 };
77 if (i2c_transfer(priv->i2c, &msg, 1) != 1) {
78 printk(KERN_WARNING "MT2266 I2C write failed\n");
79 return -EREMOTEIO;
80 }
81 return 0;
82}
83
84// Writes a set of consecutive registers
85static int mt2266_writeregs(struct mt2266_priv *priv,u8 *buf, u8 len)
86{
87 struct i2c_msg msg = {
88 .addr = priv->cfg->i2c_address, .flags = 0, .buf = buf, .len = len
89 };
90 if (i2c_transfer(priv->i2c, &msg, 1) != 1) {
91 printk(KERN_WARNING "MT2266 I2C write failed (len=%i)\n",(int)len);
92 return -EREMOTEIO;
93 }
94 return 0;
95}
96
97// Initialisation sequences
98static u8 mt2266_init1[] = { REG_TUNE, 0x00, 0x00, 0x28,
99 0x00, 0x52, 0x99, 0x3f };
100
101static u8 mt2266_init2[] = {
102 0x17, 0x6d, 0x71, 0x61, 0xc0, 0xbf, 0xff, 0xdc, 0x00, 0x0a, 0xd4,
103 0x03, 0x64, 0x64, 0x64, 0x64, 0x22, 0xaa, 0xf2, 0x1e, 0x80, 0x14,
104 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x7f, 0x5e, 0x3f, 0xff, 0xff,
105 0xff, 0x00, 0x77, 0x0f, 0x2d
106};
107
108static u8 mt2266_init_8mhz[] = { REG_BANDWIDTH, 0x22, 0x22, 0x22, 0x22,
109 0x22, 0x22, 0x22, 0x22 };
110
111static u8 mt2266_init_7mhz[] = { REG_BANDWIDTH, 0x32, 0x32, 0x32, 0x32,
112 0x32, 0x32, 0x32, 0x32 };
113
114static u8 mt2266_init_6mhz[] = { REG_BANDWIDTH, 0xa7, 0xa7, 0xa7, 0xa7,
115 0xa7, 0xa7, 0xa7, 0xa7 };
116
117static u8 mt2266_uhf[] = { 0x1d, 0xdc, 0x00, 0x0a, 0xd4, 0x03, 0x64, 0x64,
118 0x64, 0x64, 0x22, 0xaa, 0xf2, 0x1e, 0x80, 0x14 };
119
120static u8 mt2266_vhf[] = { 0x1d, 0xfe, 0x00, 0x00, 0xb4, 0x03, 0xa5, 0xa5,
121 0xa5, 0xa5, 0x82, 0xaa, 0xf1, 0x17, 0x80, 0x1f };
122
123#define FREF 30000 // Quartz oscillator 30 MHz
124
125static int mt2266_set_params(struct dvb_frontend *fe, struct dvb_frontend_parameters *params)
126{
127 struct mt2266_priv *priv;
128 int ret=0;
129 u32 freq;
130 u32 tune;
131 u8 lnaband;
132 u8 b[10];
133 int i;
134 u8 band;
135
136 priv = fe->tuner_priv;
137
138 freq = params->frequency / 1000; // Hz -> kHz
139 if (freq < 470000 && freq > 230000)
140 return -EINVAL; /* Gap between VHF and UHF bands */
141 priv->bandwidth = (fe->ops.info.type == FE_OFDM) ? params->u.ofdm.bandwidth : 0;
142 priv->frequency = freq * 1000;
143
144 tune = 2 * freq * (8192/16) / (FREF/16);
145 band = (freq < 300000) ? MT2266_VHF : MT2266_UHF;
146 if (band == MT2266_VHF)
147 tune *= 2;
148
149 switch (params->u.ofdm.bandwidth) {
150 case BANDWIDTH_6_MHZ:
151 mt2266_writeregs(priv, mt2266_init_6mhz,
152 sizeof(mt2266_init_6mhz));
153 break;
154 case BANDWIDTH_7_MHZ:
155 mt2266_writeregs(priv, mt2266_init_7mhz,
156 sizeof(mt2266_init_7mhz));
157 break;
158 case BANDWIDTH_8_MHZ:
159 default:
160 mt2266_writeregs(priv, mt2266_init_8mhz,
161 sizeof(mt2266_init_8mhz));
162 break;
163 }
164
165 if (band == MT2266_VHF && priv->band == MT2266_UHF) {
166 dprintk("Switch from UHF to VHF");
167 mt2266_writereg(priv, 0x05, 0x04);
168 mt2266_writereg(priv, 0x19, 0x61);
169 mt2266_writeregs(priv, mt2266_vhf, sizeof(mt2266_vhf));
170 } else if (band == MT2266_UHF && priv->band == MT2266_VHF) {
171 dprintk("Switch from VHF to UHF");
172 mt2266_writereg(priv, 0x05, 0x52);
173 mt2266_writereg(priv, 0x19, 0x61);
174 mt2266_writeregs(priv, mt2266_uhf, sizeof(mt2266_uhf));
175 }
176 msleep(10);
177
178 if (freq <= 495000)
179 lnaband = 0xEE;
180 else if (freq <= 525000)
181 lnaband = 0xDD;
182 else if (freq <= 550000)
183 lnaband = 0xCC;
184 else if (freq <= 580000)
185 lnaband = 0xBB;
186 else if (freq <= 605000)
187 lnaband = 0xAA;
188 else if (freq <= 630000)
189 lnaband = 0x99;
190 else if (freq <= 655000)
191 lnaband = 0x88;
192 else if (freq <= 685000)
193 lnaband = 0x77;
194 else if (freq <= 710000)
195 lnaband = 0x66;
196 else if (freq <= 735000)
197 lnaband = 0x55;
198 else if (freq <= 765000)
199 lnaband = 0x44;
200 else if (freq <= 802000)
201 lnaband = 0x33;
202 else if (freq <= 840000)
203 lnaband = 0x22;
204 else
205 lnaband = 0x11;
206
207 b[0] = REG_TUNE;
208 b[1] = (tune >> 8) & 0x1F;
209 b[2] = tune & 0xFF;
210 b[3] = tune >> 13;
211 mt2266_writeregs(priv,b,4);
212
213 dprintk("set_parms: tune=%d band=%d %s",
214 (int) tune, (int) lnaband,
215 (band == MT2266_UHF) ? "UHF" : "VHF");
216 dprintk("set_parms: [1..3]: %2x %2x %2x",
217 (int) b[1], (int) b[2], (int)b[3]);
218
219 if (band == MT2266_UHF) {
220 b[0] = 0x05;
221 b[1] = (priv->band == MT2266_VHF) ? 0x52 : 0x62;
222 b[2] = lnaband;
223 mt2266_writeregs(priv, b, 3);
224 }
225
226 /* Wait for pll lock or timeout */
227 i = 0;
228 do {
229 mt2266_readreg(priv,REG_LOCK,b);
230 if (b[0] & 0x40)
231 break;
232 msleep(10);
233 i++;
234 } while (i<10);
235 dprintk("Lock when i=%i",(int)i);
236
237 if (band == MT2266_UHF && priv->band == MT2266_VHF)
238 mt2266_writereg(priv, 0x05, 0x62);
239
240 priv->band = band;
241
242 return ret;
243}
244
245static void mt2266_calibrate(struct mt2266_priv *priv)
246{
247 mt2266_writereg(priv, 0x11, 0x03);
248 mt2266_writereg(priv, 0x11, 0x01);
249 mt2266_writeregs(priv, mt2266_init1, sizeof(mt2266_init1));
250 mt2266_writeregs(priv, mt2266_init2, sizeof(mt2266_init2));
251 mt2266_writereg(priv, 0x33, 0x5e);
252 mt2266_writereg(priv, 0x10, 0x10);
253 mt2266_writereg(priv, 0x10, 0x00);
254 mt2266_writeregs(priv, mt2266_init_8mhz, sizeof(mt2266_init_8mhz));
255 msleep(25);
256 mt2266_writereg(priv, 0x17, 0x6d);
257 mt2266_writereg(priv, 0x1c, 0x00);
258 msleep(75);
259 mt2266_writereg(priv, 0x17, 0x6d);
260 mt2266_writereg(priv, 0x1c, 0xff);
261}
262
263static int mt2266_get_frequency(struct dvb_frontend *fe, u32 *frequency)
264{
265 struct mt2266_priv *priv = fe->tuner_priv;
266 *frequency = priv->frequency;
267 return 0;
268}
269
270static int mt2266_get_bandwidth(struct dvb_frontend *fe, u32 *bandwidth)
271{
272 struct mt2266_priv *priv = fe->tuner_priv;
273 *bandwidth = priv->bandwidth;
274 return 0;
275}
276
277static int mt2266_init(struct dvb_frontend *fe)
278{
279 int ret;
280 struct mt2266_priv *priv = fe->tuner_priv;
281 ret = mt2266_writereg(priv, 0x17, 0x6d);
282 if (ret < 0)
283 return ret;
284 ret = mt2266_writereg(priv, 0x1c, 0xff);
285 if (ret < 0)
286 return ret;
287 return 0;
288}
289
290static int mt2266_sleep(struct dvb_frontend *fe)
291{
292 struct mt2266_priv *priv = fe->tuner_priv;
293 mt2266_writereg(priv, 0x17, 0x6d);
294 mt2266_writereg(priv, 0x1c, 0x00);
295 return 0;
296}
297
298static int mt2266_release(struct dvb_frontend *fe)
299{
300 kfree(fe->tuner_priv);
301 fe->tuner_priv = NULL;
302 return 0;
303}
304
305static const struct dvb_tuner_ops mt2266_tuner_ops = {
306 .info = {
307 .name = "Microtune MT2266",
308 .frequency_min = 174000000,
309 .frequency_max = 862000000,
310 .frequency_step = 50000,
311 },
312 .release = mt2266_release,
313 .init = mt2266_init,
314 .sleep = mt2266_sleep,
315 .set_params = mt2266_set_params,
316 .get_frequency = mt2266_get_frequency,
317 .get_bandwidth = mt2266_get_bandwidth
318};
319
320struct dvb_frontend * mt2266_attach(struct dvb_frontend *fe, struct i2c_adapter *i2c, struct mt2266_config *cfg)
321{
322 struct mt2266_priv *priv = NULL;
323 u8 id = 0;
324
325 priv = kzalloc(sizeof(struct mt2266_priv), GFP_KERNEL);
326 if (priv == NULL)
327 return NULL;
328
329 priv->cfg = cfg;
330 priv->i2c = i2c;
331 priv->band = MT2266_UHF;
332
333 if (mt2266_readreg(priv, 0, &id)) {
334 kfree(priv);
335 return NULL;
336 }
337 if (id != PART_REV) {
338 kfree(priv);
339 return NULL;
340 }
341 printk(KERN_INFO "MT2266: successfully identified\n");
342 memcpy(&fe->ops.tuner_ops, &mt2266_tuner_ops, sizeof(struct dvb_tuner_ops));
343
344 fe->tuner_priv = priv;
345 mt2266_calibrate(priv);
346 return fe;
347}
348EXPORT_SYMBOL(mt2266_attach);
349
350MODULE_AUTHOR("Olivier DANET");
351MODULE_DESCRIPTION("Microtune MT2266 silicon tuner driver");
352MODULE_LICENSE("GPL");
diff --git a/drivers/media/common/tuners/mt2266.h b/drivers/media/common/tuners/mt2266.h
new file mode 100644
index 00000000000..4d083882d04
--- /dev/null
+++ b/drivers/media/common/tuners/mt2266.h
@@ -0,0 +1,37 @@
1/*
2 * Driver for Microtune MT2266 "Direct conversion low power broadband tuner"
3 *
4 * Copyright (c) 2007 Olivier DANET <odanet@caramail.com>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 */
16
17#ifndef MT2266_H
18#define MT2266_H
19
20struct dvb_frontend;
21struct i2c_adapter;
22
23struct mt2266_config {
24 u8 i2c_address;
25};
26
27#if defined(CONFIG_MEDIA_TUNER_MT2266) || (defined(CONFIG_MEDIA_TUNER_MT2266_MODULE) && defined(MODULE))
28extern struct dvb_frontend * mt2266_attach(struct dvb_frontend *fe, struct i2c_adapter *i2c, struct mt2266_config *cfg);
29#else
30static inline struct dvb_frontend * mt2266_attach(struct dvb_frontend *fe, struct i2c_adapter *i2c, struct mt2266_config *cfg)
31{
32 printk(KERN_WARNING "%s: driver disabled by Kconfig\n", __func__);
33 return NULL;
34}
35#endif // CONFIG_MEDIA_TUNER_MT2266
36
37#endif
diff --git a/drivers/media/common/tuners/mxl5005s.c b/drivers/media/common/tuners/mxl5005s.c
new file mode 100644
index 00000000000..56fe75c94de
--- /dev/null
+++ b/drivers/media/common/tuners/mxl5005s.c
@@ -0,0 +1,4118 @@
1/*
2 MaxLinear MXL5005S VSB/QAM/DVBT tuner driver
3
4 Copyright (C) 2008 MaxLinear
5 Copyright (C) 2006 Steven Toth <stoth@linuxtv.org>
6 Functions:
7 mxl5005s_reset()
8 mxl5005s_writereg()
9 mxl5005s_writeregs()
10 mxl5005s_init()
11 mxl5005s_reconfigure()
12 mxl5005s_AssignTunerMode()
13 mxl5005s_set_params()
14 mxl5005s_get_frequency()
15 mxl5005s_get_bandwidth()
16 mxl5005s_release()
17 mxl5005s_attach()
18
19 Copyright (C) 2008 Realtek
20 Copyright (C) 2008 Jan Hoogenraad
21 Functions:
22 mxl5005s_SetRfFreqHz()
23
24 This program is free software; you can redistribute it and/or modify
25 it under the terms of the GNU General Public License as published by
26 the Free Software Foundation; either version 2 of the License, or
27 (at your option) any later version.
28
29 This program is distributed in the hope that it will be useful,
30 but WITHOUT ANY WARRANTY; without even the implied warranty of
31 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
32 GNU General Public License for more details.
33
34 You should have received a copy of the GNU General Public License
35 along with this program; if not, write to the Free Software
36 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
37
38*/
39
40/*
41 History of this driver (Steven Toth):
42 I was given a public release of a linux driver that included
43 support for the MaxLinear MXL5005S silicon tuner. Analysis of
44 the tuner driver showed clearly three things.
45
46 1. The tuner driver didn't support the LinuxTV tuner API
47 so the code Realtek added had to be removed.
48
49 2. A significant amount of the driver is reference driver code
50 from MaxLinear, I felt it was important to identify and
51 preserve this.
52
53 3. New code has to be added to interface correctly with the
54 LinuxTV API, as a regular kernel module.
55
56 Other than the reference driver enum's, I've clearly marked
57 sections of the code and retained the copyright of the
58 respective owners.
59*/
60#include <linux/kernel.h>
61#include <linux/init.h>
62#include <linux/module.h>
63#include <linux/string.h>
64#include <linux/slab.h>
65#include <linux/delay.h>
66#include "dvb_frontend.h"
67#include "mxl5005s.h"
68
69static int debug;
70
71#define dprintk(level, arg...) do { \
72 if (level <= debug) \
73 printk(arg); \
74 } while (0)
75
76#define TUNER_REGS_NUM 104
77#define INITCTRL_NUM 40
78
79#ifdef _MXL_PRODUCTION
80#define CHCTRL_NUM 39
81#else
82#define CHCTRL_NUM 36
83#endif
84
85#define MXLCTRL_NUM 189
86#define MASTER_CONTROL_ADDR 9
87
88/* Enumeration of Master Control Register State */
89enum master_control_state {
90 MC_LOAD_START = 1,
91 MC_POWER_DOWN,
92 MC_SYNTH_RESET,
93 MC_SEQ_OFF
94};
95
96/* Enumeration of MXL5005 Tuner Modulation Type */
97enum {
98 MXL_DEFAULT_MODULATION = 0,
99 MXL_DVBT,
100 MXL_ATSC,
101 MXL_QAM,
102 MXL_ANALOG_CABLE,
103 MXL_ANALOG_OTA
104};
105
106/* MXL5005 Tuner Register Struct */
107struct TunerReg {
108 u16 Reg_Num; /* Tuner Register Address */
109 u16 Reg_Val; /* Current sw programmed value waiting to be written */
110};
111
112enum {
113 /* Initialization Control Names */
114 DN_IQTN_AMP_CUT = 1, /* 1 */
115 BB_MODE, /* 2 */
116 BB_BUF, /* 3 */
117 BB_BUF_OA, /* 4 */
118 BB_ALPF_BANDSELECT, /* 5 */
119 BB_IQSWAP, /* 6 */
120 BB_DLPF_BANDSEL, /* 7 */
121 RFSYN_CHP_GAIN, /* 8 */
122 RFSYN_EN_CHP_HIGAIN, /* 9 */
123 AGC_IF, /* 10 */
124 AGC_RF, /* 11 */
125 IF_DIVVAL, /* 12 */
126 IF_VCO_BIAS, /* 13 */
127 CHCAL_INT_MOD_IF, /* 14 */
128 CHCAL_FRAC_MOD_IF, /* 15 */
129 DRV_RES_SEL, /* 16 */
130 I_DRIVER, /* 17 */
131 EN_AAF, /* 18 */
132 EN_3P, /* 19 */
133 EN_AUX_3P, /* 20 */
134 SEL_AAF_BAND, /* 21 */
135 SEQ_ENCLK16_CLK_OUT, /* 22 */
136 SEQ_SEL4_16B, /* 23 */
137 XTAL_CAPSELECT, /* 24 */
138 IF_SEL_DBL, /* 25 */
139 RFSYN_R_DIV, /* 26 */
140 SEQ_EXTSYNTHCALIF, /* 27 */
141 SEQ_EXTDCCAL, /* 28 */
142 AGC_EN_RSSI, /* 29 */
143 RFA_ENCLKRFAGC, /* 30 */
144 RFA_RSSI_REFH, /* 31 */
145 RFA_RSSI_REF, /* 32 */
146 RFA_RSSI_REFL, /* 33 */
147 RFA_FLR, /* 34 */
148 RFA_CEIL, /* 35 */
149 SEQ_EXTIQFSMPULSE, /* 36 */
150 OVERRIDE_1, /* 37 */
151 BB_INITSTATE_DLPF_TUNE, /* 38 */
152 TG_R_DIV, /* 39 */
153 EN_CHP_LIN_B, /* 40 */
154
155 /* Channel Change Control Names */
156 DN_POLY = 51, /* 51 */
157 DN_RFGAIN, /* 52 */
158 DN_CAP_RFLPF, /* 53 */
159 DN_EN_VHFUHFBAR, /* 54 */
160 DN_GAIN_ADJUST, /* 55 */
161 DN_IQTNBUF_AMP, /* 56 */
162 DN_IQTNGNBFBIAS_BST, /* 57 */
163 RFSYN_EN_OUTMUX, /* 58 */
164 RFSYN_SEL_VCO_OUT, /* 59 */
165 RFSYN_SEL_VCO_HI, /* 60 */
166 RFSYN_SEL_DIVM, /* 61 */
167 RFSYN_RF_DIV_BIAS, /* 62 */
168 DN_SEL_FREQ, /* 63 */
169 RFSYN_VCO_BIAS, /* 64 */
170 CHCAL_INT_MOD_RF, /* 65 */
171 CHCAL_FRAC_MOD_RF, /* 66 */
172 RFSYN_LPF_R, /* 67 */
173 CHCAL_EN_INT_RF, /* 68 */
174 TG_LO_DIVVAL, /* 69 */
175 TG_LO_SELVAL, /* 70 */
176 TG_DIV_VAL, /* 71 */
177 TG_VCO_BIAS, /* 72 */
178 SEQ_EXTPOWERUP, /* 73 */
179 OVERRIDE_2, /* 74 */
180 OVERRIDE_3, /* 75 */
181 OVERRIDE_4, /* 76 */
182 SEQ_FSM_PULSE, /* 77 */
183 GPIO_4B, /* 78 */
184 GPIO_3B, /* 79 */
185 GPIO_4, /* 80 */
186 GPIO_3, /* 81 */
187 GPIO_1B, /* 82 */
188 DAC_A_ENABLE, /* 83 */
189 DAC_B_ENABLE, /* 84 */
190 DAC_DIN_A, /* 85 */
191 DAC_DIN_B, /* 86 */
192#ifdef _MXL_PRODUCTION
193 RFSYN_EN_DIV, /* 87 */
194 RFSYN_DIVM, /* 88 */
195 DN_BYPASS_AGC_I2C /* 89 */
196#endif
197};
198
199/*
200 * The following context is source code provided by MaxLinear.
201 * MaxLinear source code - Common_MXL.h (?)
202 */
203
204/* Constants */
205#define MXL5005S_REG_WRITING_TABLE_LEN_MAX 104
206#define MXL5005S_LATCH_BYTE 0xfe
207
208/* Register address, MSB, and LSB */
209#define MXL5005S_BB_IQSWAP_ADDR 59
210#define MXL5005S_BB_IQSWAP_MSB 0
211#define MXL5005S_BB_IQSWAP_LSB 0
212
213#define MXL5005S_BB_DLPF_BANDSEL_ADDR 53
214#define MXL5005S_BB_DLPF_BANDSEL_MSB 4
215#define MXL5005S_BB_DLPF_BANDSEL_LSB 3
216
217/* Standard modes */
218enum {
219 MXL5005S_STANDARD_DVBT,
220 MXL5005S_STANDARD_ATSC,
221};
222#define MXL5005S_STANDARD_MODE_NUM 2
223
224/* Bandwidth modes */
225enum {
226 MXL5005S_BANDWIDTH_6MHZ = 6000000,
227 MXL5005S_BANDWIDTH_7MHZ = 7000000,
228 MXL5005S_BANDWIDTH_8MHZ = 8000000,
229};
230#define MXL5005S_BANDWIDTH_MODE_NUM 3
231
232/* MXL5005 Tuner Control Struct */
233struct TunerControl {
234 u16 Ctrl_Num; /* Control Number */
235 u16 size; /* Number of bits to represent Value */
236 u16 addr[25]; /* Array of Tuner Register Address for each bit pos */
237 u16 bit[25]; /* Array of bit pos in Reg Addr for each bit pos */
238 u16 val[25]; /* Binary representation of Value */
239};
240
241/* MXL5005 Tuner Struct */
242struct mxl5005s_state {
243 u8 Mode; /* 0: Analog Mode ; 1: Digital Mode */
244 u8 IF_Mode; /* for Analog Mode, 0: zero IF; 1: low IF */
245 u32 Chan_Bandwidth; /* filter channel bandwidth (6, 7, 8) */
246 u32 IF_OUT; /* Desired IF Out Frequency */
247 u16 IF_OUT_LOAD; /* IF Out Load Resistor (200/300 Ohms) */
248 u32 RF_IN; /* RF Input Frequency */
249 u32 Fxtal; /* XTAL Frequency */
250 u8 AGC_Mode; /* AGC Mode 0: Dual AGC; 1: Single AGC */
251 u16 TOP; /* Value: take over point */
252 u8 CLOCK_OUT; /* 0: turn off clk out; 1: turn on clock out */
253 u8 DIV_OUT; /* 4MHz or 16MHz */
254 u8 CAPSELECT; /* 0: disable On-Chip pulling cap; 1: enable */
255 u8 EN_RSSI; /* 0: disable RSSI; 1: enable RSSI */
256
257 /* Modulation Type; */
258 /* 0 - Default; 1 - DVB-T; 2 - ATSC; 3 - QAM; 4 - Analog Cable */
259 u8 Mod_Type;
260
261 /* Tracking Filter Type */
262 /* 0 - Default; 1 - Off; 2 - Type C; 3 - Type C-H */
263 u8 TF_Type;
264
265 /* Calculated Settings */
266 u32 RF_LO; /* Synth RF LO Frequency */
267 u32 IF_LO; /* Synth IF LO Frequency */
268 u32 TG_LO; /* Synth TG_LO Frequency */
269
270 /* Pointers to ControlName Arrays */
271 u16 Init_Ctrl_Num; /* Number of INIT Control Names */
272 struct TunerControl
273 Init_Ctrl[INITCTRL_NUM]; /* INIT Control Names Array Pointer */
274
275 u16 CH_Ctrl_Num; /* Number of CH Control Names */
276 struct TunerControl
277 CH_Ctrl[CHCTRL_NUM]; /* CH Control Name Array Pointer */
278
279 u16 MXL_Ctrl_Num; /* Number of MXL Control Names */
280 struct TunerControl
281 MXL_Ctrl[MXLCTRL_NUM]; /* MXL Control Name Array Pointer */
282
283 /* Pointer to Tuner Register Array */
284 u16 TunerRegs_Num; /* Number of Tuner Registers */
285 struct TunerReg
286 TunerRegs[TUNER_REGS_NUM]; /* Tuner Register Array Pointer */
287
288 /* Linux driver framework specific */
289 struct mxl5005s_config *config;
290 struct dvb_frontend *frontend;
291 struct i2c_adapter *i2c;
292
293 /* Cache values */
294 u32 current_mode;
295
296};
297
298static u16 MXL_GetMasterControl(u8 *MasterReg, int state);
299static u16 MXL_ControlWrite(struct dvb_frontend *fe, u16 ControlNum, u32 value);
300static u16 MXL_ControlRead(struct dvb_frontend *fe, u16 controlNum, u32 *value);
301static void MXL_RegWriteBit(struct dvb_frontend *fe, u8 address, u8 bit,
302 u8 bitVal);
303static u16 MXL_GetCHRegister(struct dvb_frontend *fe, u8 *RegNum,
304 u8 *RegVal, int *count);
305static u32 MXL_Ceiling(u32 value, u32 resolution);
306static u16 MXL_RegRead(struct dvb_frontend *fe, u8 RegNum, u8 *RegVal);
307static u16 MXL_ControlWrite_Group(struct dvb_frontend *fe, u16 controlNum,
308 u32 value, u16 controlGroup);
309static u16 MXL_SetGPIO(struct dvb_frontend *fe, u8 GPIO_Num, u8 GPIO_Val);
310static u16 MXL_GetInitRegister(struct dvb_frontend *fe, u8 *RegNum,
311 u8 *RegVal, int *count);
312static u32 MXL_GetXtalInt(u32 Xtal_Freq);
313static u16 MXL_TuneRF(struct dvb_frontend *fe, u32 RF_Freq);
314static void MXL_SynthIFLO_Calc(struct dvb_frontend *fe);
315static void MXL_SynthRFTGLO_Calc(struct dvb_frontend *fe);
316static u16 MXL_GetCHRegister_ZeroIF(struct dvb_frontend *fe, u8 *RegNum,
317 u8 *RegVal, int *count);
318static int mxl5005s_writeregs(struct dvb_frontend *fe, u8 *addrtable,
319 u8 *datatable, u8 len);
320static u16 MXL_IFSynthInit(struct dvb_frontend *fe);
321static int mxl5005s_AssignTunerMode(struct dvb_frontend *fe, u32 mod_type,
322 u32 bandwidth);
323static int mxl5005s_reconfigure(struct dvb_frontend *fe, u32 mod_type,
324 u32 bandwidth);
325
326/* ----------------------------------------------------------------
327 * Begin: Custom code salvaged from the Realtek driver.
328 * Copyright (C) 2008 Realtek
329 * Copyright (C) 2008 Jan Hoogenraad
330 * This code is placed under the terms of the GNU General Public License
331 *
332 * Released by Realtek under GPLv2.
333 * Thanks to Realtek for a lot of support we received !
334 *
335 * Revision: 080314 - original version
336 */
337
338static int mxl5005s_SetRfFreqHz(struct dvb_frontend *fe, unsigned long RfFreqHz)
339{
340 struct mxl5005s_state *state = fe->tuner_priv;
341 unsigned char AddrTable[MXL5005S_REG_WRITING_TABLE_LEN_MAX];
342 unsigned char ByteTable[MXL5005S_REG_WRITING_TABLE_LEN_MAX];
343 int TableLen;
344
345 u32 IfDivval = 0;
346 unsigned char MasterControlByte;
347
348 dprintk(1, "%s() freq=%ld\n", __func__, RfFreqHz);
349
350 /* Set MxL5005S tuner RF frequency according to example code. */
351
352 /* Tuner RF frequency setting stage 0 */
353 MXL_GetMasterControl(ByteTable, MC_SYNTH_RESET);
354 AddrTable[0] = MASTER_CONTROL_ADDR;
355 ByteTable[0] |= state->config->AgcMasterByte;
356
357 mxl5005s_writeregs(fe, AddrTable, ByteTable, 1);
358
359 /* Tuner RF frequency setting stage 1 */
360 MXL_TuneRF(fe, RfFreqHz);
361
362 MXL_ControlRead(fe, IF_DIVVAL, &IfDivval);
363
364 MXL_ControlWrite(fe, SEQ_FSM_PULSE, 0);
365 MXL_ControlWrite(fe, SEQ_EXTPOWERUP, 1);
366 MXL_ControlWrite(fe, IF_DIVVAL, 8);
367 MXL_GetCHRegister(fe, AddrTable, ByteTable, &TableLen);
368
369 MXL_GetMasterControl(&MasterControlByte, MC_LOAD_START);
370 AddrTable[TableLen] = MASTER_CONTROL_ADDR ;
371 ByteTable[TableLen] = MasterControlByte |
372 state->config->AgcMasterByte;
373 TableLen += 1;
374
375 mxl5005s_writeregs(fe, AddrTable, ByteTable, TableLen);
376
377 /* Wait 30 ms. */
378 msleep(150);
379
380 /* Tuner RF frequency setting stage 2 */
381 MXL_ControlWrite(fe, SEQ_FSM_PULSE, 1);
382 MXL_ControlWrite(fe, IF_DIVVAL, IfDivval);
383 MXL_GetCHRegister_ZeroIF(fe, AddrTable, ByteTable, &TableLen);
384
385 MXL_GetMasterControl(&MasterControlByte, MC_LOAD_START);
386 AddrTable[TableLen] = MASTER_CONTROL_ADDR ;
387 ByteTable[TableLen] = MasterControlByte |
388 state->config->AgcMasterByte ;
389 TableLen += 1;
390
391 mxl5005s_writeregs(fe, AddrTable, ByteTable, TableLen);
392
393 msleep(100);
394
395 return 0;
396}
397/* End: Custom code taken from the Realtek driver */
398
399/* ----------------------------------------------------------------
400 * Begin: Reference driver code found in the Realtek driver.
401 * Copyright (C) 2008 MaxLinear
402 */
403static u16 MXL5005_RegisterInit(struct dvb_frontend *fe)
404{
405 struct mxl5005s_state *state = fe->tuner_priv;
406 state->TunerRegs_Num = TUNER_REGS_NUM ;
407
408 state->TunerRegs[0].Reg_Num = 9 ;
409 state->TunerRegs[0].Reg_Val = 0x40 ;
410
411 state->TunerRegs[1].Reg_Num = 11 ;
412 state->TunerRegs[1].Reg_Val = 0x19 ;
413
414 state->TunerRegs[2].Reg_Num = 12 ;
415 state->TunerRegs[2].Reg_Val = 0x60 ;
416
417 state->TunerRegs[3].Reg_Num = 13 ;
418 state->TunerRegs[3].Reg_Val = 0x00 ;
419
420 state->TunerRegs[4].Reg_Num = 14 ;
421 state->TunerRegs[4].Reg_Val = 0x00 ;
422
423 state->TunerRegs[5].Reg_Num = 15 ;
424 state->TunerRegs[5].Reg_Val = 0xC0 ;
425
426 state->TunerRegs[6].Reg_Num = 16 ;
427 state->TunerRegs[6].Reg_Val = 0x00 ;
428
429 state->TunerRegs[7].Reg_Num = 17 ;
430 state->TunerRegs[7].Reg_Val = 0x00 ;
431
432 state->TunerRegs[8].Reg_Num = 18 ;
433 state->TunerRegs[8].Reg_Val = 0x00 ;
434
435 state->TunerRegs[9].Reg_Num = 19 ;
436 state->TunerRegs[9].Reg_Val = 0x34 ;
437
438 state->TunerRegs[10].Reg_Num = 21 ;
439 state->TunerRegs[10].Reg_Val = 0x00 ;
440
441 state->TunerRegs[11].Reg_Num = 22 ;
442 state->TunerRegs[11].Reg_Val = 0x6B ;
443
444 state->TunerRegs[12].Reg_Num = 23 ;
445 state->TunerRegs[12].Reg_Val = 0x35 ;
446
447 state->TunerRegs[13].Reg_Num = 24 ;
448 state->TunerRegs[13].Reg_Val = 0x70 ;
449
450 state->TunerRegs[14].Reg_Num = 25 ;
451 state->TunerRegs[14].Reg_Val = 0x3E ;
452
453 state->TunerRegs[15].Reg_Num = 26 ;
454 state->TunerRegs[15].Reg_Val = 0x82 ;
455
456 state->TunerRegs[16].Reg_Num = 31 ;
457 state->TunerRegs[16].Reg_Val = 0x00 ;
458
459 state->TunerRegs[17].Reg_Num = 32 ;
460 state->TunerRegs[17].Reg_Val = 0x40 ;
461
462 state->TunerRegs[18].Reg_Num = 33 ;
463 state->TunerRegs[18].Reg_Val = 0x53 ;
464
465 state->TunerRegs[19].Reg_Num = 34 ;
466 state->TunerRegs[19].Reg_Val = 0x81 ;
467
468 state->TunerRegs[20].Reg_Num = 35 ;
469 state->TunerRegs[20].Reg_Val = 0xC9 ;
470
471 state->TunerRegs[21].Reg_Num = 36 ;
472 state->TunerRegs[21].Reg_Val = 0x01 ;
473
474 state->TunerRegs[22].Reg_Num = 37 ;
475 state->TunerRegs[22].Reg_Val = 0x00 ;
476
477 state->TunerRegs[23].Reg_Num = 41 ;
478 state->TunerRegs[23].Reg_Val = 0x00 ;
479
480 state->TunerRegs[24].Reg_Num = 42 ;
481 state->TunerRegs[24].Reg_Val = 0xF8 ;
482
483 state->TunerRegs[25].Reg_Num = 43 ;
484 state->TunerRegs[25].Reg_Val = 0x43 ;
485
486 state->TunerRegs[26].Reg_Num = 44 ;
487 state->TunerRegs[26].Reg_Val = 0x20 ;
488
489 state->TunerRegs[27].Reg_Num = 45 ;
490 state->TunerRegs[27].Reg_Val = 0x80 ;
491
492 state->TunerRegs[28].Reg_Num = 46 ;
493 state->TunerRegs[28].Reg_Val = 0x88 ;
494
495 state->TunerRegs[29].Reg_Num = 47 ;
496 state->TunerRegs[29].Reg_Val = 0x86 ;
497
498 state->TunerRegs[30].Reg_Num = 48 ;
499 state->TunerRegs[30].Reg_Val = 0x00 ;
500
501 state->TunerRegs[31].Reg_Num = 49 ;
502 state->TunerRegs[31].Reg_Val = 0x00 ;
503
504 state->TunerRegs[32].Reg_Num = 53 ;
505 state->TunerRegs[32].Reg_Val = 0x94 ;
506
507 state->TunerRegs[33].Reg_Num = 54 ;
508 state->TunerRegs[33].Reg_Val = 0xFA ;
509
510 state->TunerRegs[34].Reg_Num = 55 ;
511 state->TunerRegs[34].Reg_Val = 0x92 ;
512
513 state->TunerRegs[35].Reg_Num = 56 ;
514 state->TunerRegs[35].Reg_Val = 0x80 ;
515
516 state->TunerRegs[36].Reg_Num = 57 ;
517 state->TunerRegs[36].Reg_Val = 0x41 ;
518
519 state->TunerRegs[37].Reg_Num = 58 ;
520 state->TunerRegs[37].Reg_Val = 0xDB ;
521
522 state->TunerRegs[38].Reg_Num = 59 ;
523 state->TunerRegs[38].Reg_Val = 0x00 ;
524
525 state->TunerRegs[39].Reg_Num = 60 ;
526 state->TunerRegs[39].Reg_Val = 0x00 ;
527
528 state->TunerRegs[40].Reg_Num = 61 ;
529 state->TunerRegs[40].Reg_Val = 0x00 ;
530
531 state->TunerRegs[41].Reg_Num = 62 ;
532 state->TunerRegs[41].Reg_Val = 0x00 ;
533
534 state->TunerRegs[42].Reg_Num = 65 ;
535 state->TunerRegs[42].Reg_Val = 0xF8 ;
536
537 state->TunerRegs[43].Reg_Num = 66 ;
538 state->TunerRegs[43].Reg_Val = 0xE4 ;
539
540 state->TunerRegs[44].Reg_Num = 67 ;
541 state->TunerRegs[44].Reg_Val = 0x90 ;
542
543 state->TunerRegs[45].Reg_Num = 68 ;
544 state->TunerRegs[45].Reg_Val = 0xC0 ;
545
546 state->TunerRegs[46].Reg_Num = 69 ;
547 state->TunerRegs[46].Reg_Val = 0x01 ;
548
549 state->TunerRegs[47].Reg_Num = 70 ;
550 state->TunerRegs[47].Reg_Val = 0x50 ;
551
552 state->TunerRegs[48].Reg_Num = 71 ;
553 state->TunerRegs[48].Reg_Val = 0x06 ;
554
555 state->TunerRegs[49].Reg_Num = 72 ;
556 state->TunerRegs[49].Reg_Val = 0x00 ;
557
558 state->TunerRegs[50].Reg_Num = 73 ;
559 state->TunerRegs[50].Reg_Val = 0x20 ;
560
561 state->TunerRegs[51].Reg_Num = 76 ;
562 state->TunerRegs[51].Reg_Val = 0xBB ;
563
564 state->TunerRegs[52].Reg_Num = 77 ;
565 state->TunerRegs[52].Reg_Val = 0x13 ;
566
567 state->TunerRegs[53].Reg_Num = 81 ;
568 state->TunerRegs[53].Reg_Val = 0x04 ;
569
570 state->TunerRegs[54].Reg_Num = 82 ;
571 state->TunerRegs[54].Reg_Val = 0x75 ;
572
573 state->TunerRegs[55].Reg_Num = 83 ;
574 state->TunerRegs[55].Reg_Val = 0x00 ;
575
576 state->TunerRegs[56].Reg_Num = 84 ;
577 state->TunerRegs[56].Reg_Val = 0x00 ;
578
579 state->TunerRegs[57].Reg_Num = 85 ;
580 state->TunerRegs[57].Reg_Val = 0x00 ;
581
582 state->TunerRegs[58].Reg_Num = 91 ;
583 state->TunerRegs[58].Reg_Val = 0x70 ;
584
585 state->TunerRegs[59].Reg_Num = 92 ;
586 state->TunerRegs[59].Reg_Val = 0x00 ;
587
588 state->TunerRegs[60].Reg_Num = 93 ;
589 state->TunerRegs[60].Reg_Val = 0x00 ;
590
591 state->TunerRegs[61].Reg_Num = 94 ;
592 state->TunerRegs[61].Reg_Val = 0x00 ;
593
594 state->TunerRegs[62].Reg_Num = 95 ;
595 state->TunerRegs[62].Reg_Val = 0x0C ;
596
597 state->TunerRegs[63].Reg_Num = 96 ;
598 state->TunerRegs[63].Reg_Val = 0x00 ;
599
600 state->TunerRegs[64].Reg_Num = 97 ;
601 state->TunerRegs[64].Reg_Val = 0x00 ;
602
603 state->TunerRegs[65].Reg_Num = 98 ;
604 state->TunerRegs[65].Reg_Val = 0xE2 ;
605
606 state->TunerRegs[66].Reg_Num = 99 ;
607 state->TunerRegs[66].Reg_Val = 0x00 ;
608
609 state->TunerRegs[67].Reg_Num = 100 ;
610 state->TunerRegs[67].Reg_Val = 0x00 ;
611
612 state->TunerRegs[68].Reg_Num = 101 ;
613 state->TunerRegs[68].Reg_Val = 0x12 ;
614
615 state->TunerRegs[69].Reg_Num = 102 ;
616 state->TunerRegs[69].Reg_Val = 0x80 ;
617
618 state->TunerRegs[70].Reg_Num = 103 ;
619 state->TunerRegs[70].Reg_Val = 0x32 ;
620
621 state->TunerRegs[71].Reg_Num = 104 ;
622 state->TunerRegs[71].Reg_Val = 0xB4 ;
623
624 state->TunerRegs[72].Reg_Num = 105 ;
625 state->TunerRegs[72].Reg_Val = 0x60 ;
626
627 state->TunerRegs[73].Reg_Num = 106 ;
628 state->TunerRegs[73].Reg_Val = 0x83 ;
629
630 state->TunerRegs[74].Reg_Num = 107 ;
631 state->TunerRegs[74].Reg_Val = 0x84 ;
632
633 state->TunerRegs[75].Reg_Num = 108 ;
634 state->TunerRegs[75].Reg_Val = 0x9C ;
635
636 state->TunerRegs[76].Reg_Num = 109 ;
637 state->TunerRegs[76].Reg_Val = 0x02 ;
638
639 state->TunerRegs[77].Reg_Num = 110 ;
640 state->TunerRegs[77].Reg_Val = 0x81 ;
641
642 state->TunerRegs[78].Reg_Num = 111 ;
643 state->TunerRegs[78].Reg_Val = 0xC0 ;
644
645 state->TunerRegs[79].Reg_Num = 112 ;
646 state->TunerRegs[79].Reg_Val = 0x10 ;
647
648 state->TunerRegs[80].Reg_Num = 131 ;
649 state->TunerRegs[80].Reg_Val = 0x8A ;
650
651 state->TunerRegs[81].Reg_Num = 132 ;
652 state->TunerRegs[81].Reg_Val = 0x10 ;
653
654 state->TunerRegs[82].Reg_Num = 133 ;
655 state->TunerRegs[82].Reg_Val = 0x24 ;
656
657 state->TunerRegs[83].Reg_Num = 134 ;
658 state->TunerRegs[83].Reg_Val = 0x00 ;
659
660 state->TunerRegs[84].Reg_Num = 135 ;
661 state->TunerRegs[84].Reg_Val = 0x00 ;
662
663 state->TunerRegs[85].Reg_Num = 136 ;
664 state->TunerRegs[85].Reg_Val = 0x7E ;
665
666 state->TunerRegs[86].Reg_Num = 137 ;
667 state->TunerRegs[86].Reg_Val = 0x40 ;
668
669 state->TunerRegs[87].Reg_Num = 138 ;
670 state->TunerRegs[87].Reg_Val = 0x38 ;
671
672 state->TunerRegs[88].Reg_Num = 146 ;
673 state->TunerRegs[88].Reg_Val = 0xF6 ;
674
675 state->TunerRegs[89].Reg_Num = 147 ;
676 state->TunerRegs[89].Reg_Val = 0x1A ;
677
678 state->TunerRegs[90].Reg_Num = 148 ;
679 state->TunerRegs[90].Reg_Val = 0x62 ;
680
681 state->TunerRegs[91].Reg_Num = 149 ;
682 state->TunerRegs[91].Reg_Val = 0x33 ;
683
684 state->TunerRegs[92].Reg_Num = 150 ;
685 state->TunerRegs[92].Reg_Val = 0x80 ;
686
687 state->TunerRegs[93].Reg_Num = 156 ;
688 state->TunerRegs[93].Reg_Val = 0x56 ;
689
690 state->TunerRegs[94].Reg_Num = 157 ;
691 state->TunerRegs[94].Reg_Val = 0x17 ;
692
693 state->TunerRegs[95].Reg_Num = 158 ;
694 state->TunerRegs[95].Reg_Val = 0xA9 ;
695
696 state->TunerRegs[96].Reg_Num = 159 ;
697 state->TunerRegs[96].Reg_Val = 0x00 ;
698
699 state->TunerRegs[97].Reg_Num = 160 ;
700 state->TunerRegs[97].Reg_Val = 0x00 ;
701
702 state->TunerRegs[98].Reg_Num = 161 ;
703 state->TunerRegs[98].Reg_Val = 0x00 ;
704
705 state->TunerRegs[99].Reg_Num = 162 ;
706 state->TunerRegs[99].Reg_Val = 0x40 ;
707
708 state->TunerRegs[100].Reg_Num = 166 ;
709 state->TunerRegs[100].Reg_Val = 0xAE ;
710
711 state->TunerRegs[101].Reg_Num = 167 ;
712 state->TunerRegs[101].Reg_Val = 0x1B ;
713
714 state->TunerRegs[102].Reg_Num = 168 ;
715 state->TunerRegs[102].Reg_Val = 0xF2 ;
716
717 state->TunerRegs[103].Reg_Num = 195 ;
718 state->TunerRegs[103].Reg_Val = 0x00 ;
719
720 return 0 ;
721}
722
723static u16 MXL5005_ControlInit(struct dvb_frontend *fe)
724{
725 struct mxl5005s_state *state = fe->tuner_priv;
726 state->Init_Ctrl_Num = INITCTRL_NUM;
727
728 state->Init_Ctrl[0].Ctrl_Num = DN_IQTN_AMP_CUT ;
729 state->Init_Ctrl[0].size = 1 ;
730 state->Init_Ctrl[0].addr[0] = 73;
731 state->Init_Ctrl[0].bit[0] = 7;
732 state->Init_Ctrl[0].val[0] = 0;
733
734 state->Init_Ctrl[1].Ctrl_Num = BB_MODE ;
735 state->Init_Ctrl[1].size = 1 ;
736 state->Init_Ctrl[1].addr[0] = 53;
737 state->Init_Ctrl[1].bit[0] = 2;
738 state->Init_Ctrl[1].val[0] = 1;
739
740 state->Init_Ctrl[2].Ctrl_Num = BB_BUF ;
741 state->Init_Ctrl[2].size = 2 ;
742 state->Init_Ctrl[2].addr[0] = 53;
743 state->Init_Ctrl[2].bit[0] = 1;
744 state->Init_Ctrl[2].val[0] = 0;
745 state->Init_Ctrl[2].addr[1] = 57;
746 state->Init_Ctrl[2].bit[1] = 0;
747 state->Init_Ctrl[2].val[1] = 1;
748
749 state->Init_Ctrl[3].Ctrl_Num = BB_BUF_OA ;
750 state->Init_Ctrl[3].size = 1 ;
751 state->Init_Ctrl[3].addr[0] = 53;
752 state->Init_Ctrl[3].bit[0] = 0;
753 state->Init_Ctrl[3].val[0] = 0;
754
755 state->Init_Ctrl[4].Ctrl_Num = BB_ALPF_BANDSELECT ;
756 state->Init_Ctrl[4].size = 3 ;
757 state->Init_Ctrl[4].addr[0] = 53;
758 state->Init_Ctrl[4].bit[0] = 5;
759 state->Init_Ctrl[4].val[0] = 0;
760 state->Init_Ctrl[4].addr[1] = 53;
761 state->Init_Ctrl[4].bit[1] = 6;
762 state->Init_Ctrl[4].val[1] = 0;
763 state->Init_Ctrl[4].addr[2] = 53;
764 state->Init_Ctrl[4].bit[2] = 7;
765 state->Init_Ctrl[4].val[2] = 1;
766
767 state->Init_Ctrl[5].Ctrl_Num = BB_IQSWAP ;
768 state->Init_Ctrl[5].size = 1 ;
769 state->Init_Ctrl[5].addr[0] = 59;
770 state->Init_Ctrl[5].bit[0] = 0;
771 state->Init_Ctrl[5].val[0] = 0;
772
773 state->Init_Ctrl[6].Ctrl_Num = BB_DLPF_BANDSEL ;
774 state->Init_Ctrl[6].size = 2 ;
775 state->Init_Ctrl[6].addr[0] = 53;
776 state->Init_Ctrl[6].bit[0] = 3;
777 state->Init_Ctrl[6].val[0] = 0;
778 state->Init_Ctrl[6].addr[1] = 53;
779 state->Init_Ctrl[6].bit[1] = 4;
780 state->Init_Ctrl[6].val[1] = 1;
781
782 state->Init_Ctrl[7].Ctrl_Num = RFSYN_CHP_GAIN ;
783 state->Init_Ctrl[7].size = 4 ;
784 state->Init_Ctrl[7].addr[0] = 22;
785 state->Init_Ctrl[7].bit[0] = 4;
786 state->Init_Ctrl[7].val[0] = 0;
787 state->Init_Ctrl[7].addr[1] = 22;
788 state->Init_Ctrl[7].bit[1] = 5;
789 state->Init_Ctrl[7].val[1] = 1;
790 state->Init_Ctrl[7].addr[2] = 22;
791 state->Init_Ctrl[7].bit[2] = 6;
792 state->Init_Ctrl[7].val[2] = 1;
793 state->Init_Ctrl[7].addr[3] = 22;
794 state->Init_Ctrl[7].bit[3] = 7;
795 state->Init_Ctrl[7].val[3] = 0;
796
797 state->Init_Ctrl[8].Ctrl_Num = RFSYN_EN_CHP_HIGAIN ;
798 state->Init_Ctrl[8].size = 1 ;
799 state->Init_Ctrl[8].addr[0] = 22;
800 state->Init_Ctrl[8].bit[0] = 2;
801 state->Init_Ctrl[8].val[0] = 0;
802
803 state->Init_Ctrl[9].Ctrl_Num = AGC_IF ;
804 state->Init_Ctrl[9].size = 4 ;
805 state->Init_Ctrl[9].addr[0] = 76;
806 state->Init_Ctrl[9].bit[0] = 0;
807 state->Init_Ctrl[9].val[0] = 1;
808 state->Init_Ctrl[9].addr[1] = 76;
809 state->Init_Ctrl[9].bit[1] = 1;
810 state->Init_Ctrl[9].val[1] = 1;
811 state->Init_Ctrl[9].addr[2] = 76;
812 state->Init_Ctrl[9].bit[2] = 2;
813 state->Init_Ctrl[9].val[2] = 0;
814 state->Init_Ctrl[9].addr[3] = 76;
815 state->Init_Ctrl[9].bit[3] = 3;
816 state->Init_Ctrl[9].val[3] = 1;
817
818 state->Init_Ctrl[10].Ctrl_Num = AGC_RF ;
819 state->Init_Ctrl[10].size = 4 ;
820 state->Init_Ctrl[10].addr[0] = 76;
821 state->Init_Ctrl[10].bit[0] = 4;
822 state->Init_Ctrl[10].val[0] = 1;
823 state->Init_Ctrl[10].addr[1] = 76;
824 state->Init_Ctrl[10].bit[1] = 5;
825 state->Init_Ctrl[10].val[1] = 1;
826 state->Init_Ctrl[10].addr[2] = 76;
827 state->Init_Ctrl[10].bit[2] = 6;
828 state->Init_Ctrl[10].val[2] = 0;
829 state->Init_Ctrl[10].addr[3] = 76;
830 state->Init_Ctrl[10].bit[3] = 7;
831 state->Init_Ctrl[10].val[3] = 1;
832
833 state->Init_Ctrl[11].Ctrl_Num = IF_DIVVAL ;
834 state->Init_Ctrl[11].size = 5 ;
835 state->Init_Ctrl[11].addr[0] = 43;
836 state->Init_Ctrl[11].bit[0] = 3;
837 state->Init_Ctrl[11].val[0] = 0;
838 state->Init_Ctrl[11].addr[1] = 43;
839 state->Init_Ctrl[11].bit[1] = 4;
840 state->Init_Ctrl[11].val[1] = 0;
841 state->Init_Ctrl[11].addr[2] = 43;
842 state->Init_Ctrl[11].bit[2] = 5;
843 state->Init_Ctrl[11].val[2] = 0;
844 state->Init_Ctrl[11].addr[3] = 43;
845 state->Init_Ctrl[11].bit[3] = 6;
846 state->Init_Ctrl[11].val[3] = 1;
847 state->Init_Ctrl[11].addr[4] = 43;
848 state->Init_Ctrl[11].bit[4] = 7;
849 state->Init_Ctrl[11].val[4] = 0;
850
851 state->Init_Ctrl[12].Ctrl_Num = IF_VCO_BIAS ;
852 state->Init_Ctrl[12].size = 6 ;
853 state->Init_Ctrl[12].addr[0] = 44;
854 state->Init_Ctrl[12].bit[0] = 2;
855 state->Init_Ctrl[12].val[0] = 0;
856 state->Init_Ctrl[12].addr[1] = 44;
857 state->Init_Ctrl[12].bit[1] = 3;
858 state->Init_Ctrl[12].val[1] = 0;
859 state->Init_Ctrl[12].addr[2] = 44;
860 state->Init_Ctrl[12].bit[2] = 4;
861 state->Init_Ctrl[12].val[2] = 0;
862 state->Init_Ctrl[12].addr[3] = 44;
863 state->Init_Ctrl[12].bit[3] = 5;
864 state->Init_Ctrl[12].val[3] = 1;
865 state->Init_Ctrl[12].addr[4] = 44;
866 state->Init_Ctrl[12].bit[4] = 6;
867 state->Init_Ctrl[12].val[4] = 0;
868 state->Init_Ctrl[12].addr[5] = 44;
869 state->Init_Ctrl[12].bit[5] = 7;
870 state->Init_Ctrl[12].val[5] = 0;
871
872 state->Init_Ctrl[13].Ctrl_Num = CHCAL_INT_MOD_IF ;
873 state->Init_Ctrl[13].size = 7 ;
874 state->Init_Ctrl[13].addr[0] = 11;
875 state->Init_Ctrl[13].bit[0] = 0;
876 state->Init_Ctrl[13].val[0] = 1;
877 state->Init_Ctrl[13].addr[1] = 11;
878 state->Init_Ctrl[13].bit[1] = 1;
879 state->Init_Ctrl[13].val[1] = 0;
880 state->Init_Ctrl[13].addr[2] = 11;
881 state->Init_Ctrl[13].bit[2] = 2;
882 state->Init_Ctrl[13].val[2] = 0;
883 state->Init_Ctrl[13].addr[3] = 11;
884 state->Init_Ctrl[13].bit[3] = 3;
885 state->Init_Ctrl[13].val[3] = 1;
886 state->Init_Ctrl[13].addr[4] = 11;
887 state->Init_Ctrl[13].bit[4] = 4;
888 state->Init_Ctrl[13].val[4] = 1;
889 state->Init_Ctrl[13].addr[5] = 11;
890 state->Init_Ctrl[13].bit[5] = 5;
891 state->Init_Ctrl[13].val[5] = 0;
892 state->Init_Ctrl[13].addr[6] = 11;
893 state->Init_Ctrl[13].bit[6] = 6;
894 state->Init_Ctrl[13].val[6] = 0;
895
896 state->Init_Ctrl[14].Ctrl_Num = CHCAL_FRAC_MOD_IF ;
897 state->Init_Ctrl[14].size = 16 ;
898 state->Init_Ctrl[14].addr[0] = 13;
899 state->Init_Ctrl[14].bit[0] = 0;
900 state->Init_Ctrl[14].val[0] = 0;
901 state->Init_Ctrl[14].addr[1] = 13;
902 state->Init_Ctrl[14].bit[1] = 1;
903 state->Init_Ctrl[14].val[1] = 0;
904 state->Init_Ctrl[14].addr[2] = 13;
905 state->Init_Ctrl[14].bit[2] = 2;
906 state->Init_Ctrl[14].val[2] = 0;
907 state->Init_Ctrl[14].addr[3] = 13;
908 state->Init_Ctrl[14].bit[3] = 3;
909 state->Init_Ctrl[14].val[3] = 0;
910 state->Init_Ctrl[14].addr[4] = 13;
911 state->Init_Ctrl[14].bit[4] = 4;
912 state->Init_Ctrl[14].val[4] = 0;
913 state->Init_Ctrl[14].addr[5] = 13;
914 state->Init_Ctrl[14].bit[5] = 5;
915 state->Init_Ctrl[14].val[5] = 0;
916 state->Init_Ctrl[14].addr[6] = 13;
917 state->Init_Ctrl[14].bit[6] = 6;
918 state->Init_Ctrl[14].val[6] = 0;
919 state->Init_Ctrl[14].addr[7] = 13;
920 state->Init_Ctrl[14].bit[7] = 7;
921 state->Init_Ctrl[14].val[7] = 0;
922 state->Init_Ctrl[14].addr[8] = 12;
923 state->Init_Ctrl[14].bit[8] = 0;
924 state->Init_Ctrl[14].val[8] = 0;
925 state->Init_Ctrl[14].addr[9] = 12;
926 state->Init_Ctrl[14].bit[9] = 1;
927 state->Init_Ctrl[14].val[9] = 0;
928 state->Init_Ctrl[14].addr[10] = 12;
929 state->Init_Ctrl[14].bit[10] = 2;
930 state->Init_Ctrl[14].val[10] = 0;
931 state->Init_Ctrl[14].addr[11] = 12;
932 state->Init_Ctrl[14].bit[11] = 3;
933 state->Init_Ctrl[14].val[11] = 0;
934 state->Init_Ctrl[14].addr[12] = 12;
935 state->Init_Ctrl[14].bit[12] = 4;
936 state->Init_Ctrl[14].val[12] = 0;
937 state->Init_Ctrl[14].addr[13] = 12;
938 state->Init_Ctrl[14].bit[13] = 5;
939 state->Init_Ctrl[14].val[13] = 1;
940 state->Init_Ctrl[14].addr[14] = 12;
941 state->Init_Ctrl[14].bit[14] = 6;
942 state->Init_Ctrl[14].val[14] = 1;
943 state->Init_Ctrl[14].addr[15] = 12;
944 state->Init_Ctrl[14].bit[15] = 7;
945 state->Init_Ctrl[14].val[15] = 0;
946
947 state->Init_Ctrl[15].Ctrl_Num = DRV_RES_SEL ;
948 state->Init_Ctrl[15].size = 3 ;
949 state->Init_Ctrl[15].addr[0] = 147;
950 state->Init_Ctrl[15].bit[0] = 2;
951 state->Init_Ctrl[15].val[0] = 0;
952 state->Init_Ctrl[15].addr[1] = 147;
953 state->Init_Ctrl[15].bit[1] = 3;
954 state->Init_Ctrl[15].val[1] = 1;
955 state->Init_Ctrl[15].addr[2] = 147;
956 state->Init_Ctrl[15].bit[2] = 4;
957 state->Init_Ctrl[15].val[2] = 1;
958
959 state->Init_Ctrl[16].Ctrl_Num = I_DRIVER ;
960 state->Init_Ctrl[16].size = 2 ;
961 state->Init_Ctrl[16].addr[0] = 147;
962 state->Init_Ctrl[16].bit[0] = 0;
963 state->Init_Ctrl[16].val[0] = 0;
964 state->Init_Ctrl[16].addr[1] = 147;
965 state->Init_Ctrl[16].bit[1] = 1;
966 state->Init_Ctrl[16].val[1] = 1;
967
968 state->Init_Ctrl[17].Ctrl_Num = EN_AAF ;
969 state->Init_Ctrl[17].size = 1 ;
970 state->Init_Ctrl[17].addr[0] = 147;
971 state->Init_Ctrl[17].bit[0] = 7;
972 state->Init_Ctrl[17].val[0] = 0;
973
974 state->Init_Ctrl[18].Ctrl_Num = EN_3P ;
975 state->Init_Ctrl[18].size = 1 ;
976 state->Init_Ctrl[18].addr[0] = 147;
977 state->Init_Ctrl[18].bit[0] = 6;
978 state->Init_Ctrl[18].val[0] = 0;
979
980 state->Init_Ctrl[19].Ctrl_Num = EN_AUX_3P ;
981 state->Init_Ctrl[19].size = 1 ;
982 state->Init_Ctrl[19].addr[0] = 156;
983 state->Init_Ctrl[19].bit[0] = 0;
984 state->Init_Ctrl[19].val[0] = 0;
985
986 state->Init_Ctrl[20].Ctrl_Num = SEL_AAF_BAND ;
987 state->Init_Ctrl[20].size = 1 ;
988 state->Init_Ctrl[20].addr[0] = 147;
989 state->Init_Ctrl[20].bit[0] = 5;
990 state->Init_Ctrl[20].val[0] = 0;
991
992 state->Init_Ctrl[21].Ctrl_Num = SEQ_ENCLK16_CLK_OUT ;
993 state->Init_Ctrl[21].size = 1 ;
994 state->Init_Ctrl[21].addr[0] = 137;
995 state->Init_Ctrl[21].bit[0] = 4;
996 state->Init_Ctrl[21].val[0] = 0;
997
998 state->Init_Ctrl[22].Ctrl_Num = SEQ_SEL4_16B ;
999 state->Init_Ctrl[22].size = 1 ;
1000 state->Init_Ctrl[22].addr[0] = 137;
1001 state->Init_Ctrl[22].bit[0] = 7;
1002 state->Init_Ctrl[22].val[0] = 0;
1003
1004 state->Init_Ctrl[23].Ctrl_Num = XTAL_CAPSELECT ;
1005 state->Init_Ctrl[23].size = 1 ;
1006 state->Init_Ctrl[23].addr[0] = 91;
1007 state->Init_Ctrl[23].bit[0] = 5;
1008 state->Init_Ctrl[23].val[0] = 1;
1009
1010 state->Init_Ctrl[24].Ctrl_Num = IF_SEL_DBL ;
1011 state->Init_Ctrl[24].size = 1 ;
1012 state->Init_Ctrl[24].addr[0] = 43;
1013 state->Init_Ctrl[24].bit[0] = 0;
1014 state->Init_Ctrl[24].val[0] = 1;
1015
1016 state->Init_Ctrl[25].Ctrl_Num = RFSYN_R_DIV ;
1017 state->Init_Ctrl[25].size = 2 ;
1018 state->Init_Ctrl[25].addr[0] = 22;
1019 state->Init_Ctrl[25].bit[0] = 0;
1020 state->Init_Ctrl[25].val[0] = 1;
1021 state->Init_Ctrl[25].addr[1] = 22;
1022 state->Init_Ctrl[25].bit[1] = 1;
1023 state->Init_Ctrl[25].val[1] = 1;
1024
1025 state->Init_Ctrl[26].Ctrl_Num = SEQ_EXTSYNTHCALIF ;
1026 state->Init_Ctrl[26].size = 1 ;
1027 state->Init_Ctrl[26].addr[0] = 134;
1028 state->Init_Ctrl[26].bit[0] = 2;
1029 state->Init_Ctrl[26].val[0] = 0;
1030
1031 state->Init_Ctrl[27].Ctrl_Num = SEQ_EXTDCCAL ;
1032 state->Init_Ctrl[27].size = 1 ;
1033 state->Init_Ctrl[27].addr[0] = 137;
1034 state->Init_Ctrl[27].bit[0] = 3;
1035 state->Init_Ctrl[27].val[0] = 0;
1036
1037 state->Init_Ctrl[28].Ctrl_Num = AGC_EN_RSSI ;
1038 state->Init_Ctrl[28].size = 1 ;
1039 state->Init_Ctrl[28].addr[0] = 77;
1040 state->Init_Ctrl[28].bit[0] = 7;
1041 state->Init_Ctrl[28].val[0] = 0;
1042
1043 state->Init_Ctrl[29].Ctrl_Num = RFA_ENCLKRFAGC ;
1044 state->Init_Ctrl[29].size = 1 ;
1045 state->Init_Ctrl[29].addr[0] = 166;
1046 state->Init_Ctrl[29].bit[0] = 7;
1047 state->Init_Ctrl[29].val[0] = 1;
1048
1049 state->Init_Ctrl[30].Ctrl_Num = RFA_RSSI_REFH ;
1050 state->Init_Ctrl[30].size = 3 ;
1051 state->Init_Ctrl[30].addr[0] = 166;
1052 state->Init_Ctrl[30].bit[0] = 0;
1053 state->Init_Ctrl[30].val[0] = 0;
1054 state->Init_Ctrl[30].addr[1] = 166;
1055 state->Init_Ctrl[30].bit[1] = 1;
1056 state->Init_Ctrl[30].val[1] = 1;
1057 state->Init_Ctrl[30].addr[2] = 166;
1058 state->Init_Ctrl[30].bit[2] = 2;
1059 state->Init_Ctrl[30].val[2] = 1;
1060
1061 state->Init_Ctrl[31].Ctrl_Num = RFA_RSSI_REF ;
1062 state->Init_Ctrl[31].size = 3 ;
1063 state->Init_Ctrl[31].addr[0] = 166;
1064 state->Init_Ctrl[31].bit[0] = 3;
1065 state->Init_Ctrl[31].val[0] = 1;
1066 state->Init_Ctrl[31].addr[1] = 166;
1067 state->Init_Ctrl[31].bit[1] = 4;
1068 state->Init_Ctrl[31].val[1] = 0;
1069 state->Init_Ctrl[31].addr[2] = 166;
1070 state->Init_Ctrl[31].bit[2] = 5;
1071 state->Init_Ctrl[31].val[2] = 1;
1072
1073 state->Init_Ctrl[32].Ctrl_Num = RFA_RSSI_REFL ;
1074 state->Init_Ctrl[32].size = 3 ;
1075 state->Init_Ctrl[32].addr[0] = 167;
1076 state->Init_Ctrl[32].bit[0] = 0;
1077 state->Init_Ctrl[32].val[0] = 1;
1078 state->Init_Ctrl[32].addr[1] = 167;
1079 state->Init_Ctrl[32].bit[1] = 1;
1080 state->Init_Ctrl[32].val[1] = 1;
1081 state->Init_Ctrl[32].addr[2] = 167;
1082 state->Init_Ctrl[32].bit[2] = 2;
1083 state->Init_Ctrl[32].val[2] = 0;
1084
1085 state->Init_Ctrl[33].Ctrl_Num = RFA_FLR ;
1086 state->Init_Ctrl[33].size = 4 ;
1087 state->Init_Ctrl[33].addr[0] = 168;
1088 state->Init_Ctrl[33].bit[0] = 0;
1089 state->Init_Ctrl[33].val[0] = 0;
1090 state->Init_Ctrl[33].addr[1] = 168;
1091 state->Init_Ctrl[33].bit[1] = 1;
1092 state->Init_Ctrl[33].val[1] = 1;
1093 state->Init_Ctrl[33].addr[2] = 168;
1094 state->Init_Ctrl[33].bit[2] = 2;
1095 state->Init_Ctrl[33].val[2] = 0;
1096 state->Init_Ctrl[33].addr[3] = 168;
1097 state->Init_Ctrl[33].bit[3] = 3;
1098 state->Init_Ctrl[33].val[3] = 0;
1099
1100 state->Init_Ctrl[34].Ctrl_Num = RFA_CEIL ;
1101 state->Init_Ctrl[34].size = 4 ;
1102 state->Init_Ctrl[34].addr[0] = 168;
1103 state->Init_Ctrl[34].bit[0] = 4;
1104 state->Init_Ctrl[34].val[0] = 1;
1105 state->Init_Ctrl[34].addr[1] = 168;
1106 state->Init_Ctrl[34].bit[1] = 5;
1107 state->Init_Ctrl[34].val[1] = 1;
1108 state->Init_Ctrl[34].addr[2] = 168;
1109 state->Init_Ctrl[34].bit[2] = 6;
1110 state->Init_Ctrl[34].val[2] = 1;
1111 state->Init_Ctrl[34].addr[3] = 168;
1112 state->Init_Ctrl[34].bit[3] = 7;
1113 state->Init_Ctrl[34].val[3] = 1;
1114
1115 state->Init_Ctrl[35].Ctrl_Num = SEQ_EXTIQFSMPULSE ;
1116 state->Init_Ctrl[35].size = 1 ;
1117 state->Init_Ctrl[35].addr[0] = 135;
1118 state->Init_Ctrl[35].bit[0] = 0;
1119 state->Init_Ctrl[35].val[0] = 0;
1120
1121 state->Init_Ctrl[36].Ctrl_Num = OVERRIDE_1 ;
1122 state->Init_Ctrl[36].size = 1 ;
1123 state->Init_Ctrl[36].addr[0] = 56;
1124 state->Init_Ctrl[36].bit[0] = 3;
1125 state->Init_Ctrl[36].val[0] = 0;
1126
1127 state->Init_Ctrl[37].Ctrl_Num = BB_INITSTATE_DLPF_TUNE ;
1128 state->Init_Ctrl[37].size = 7 ;
1129 state->Init_Ctrl[37].addr[0] = 59;
1130 state->Init_Ctrl[37].bit[0] = 1;
1131 state->Init_Ctrl[37].val[0] = 0;
1132 state->Init_Ctrl[37].addr[1] = 59;
1133 state->Init_Ctrl[37].bit[1] = 2;
1134 state->Init_Ctrl[37].val[1] = 0;
1135 state->Init_Ctrl[37].addr[2] = 59;
1136 state->Init_Ctrl[37].bit[2] = 3;
1137 state->Init_Ctrl[37].val[2] = 0;
1138 state->Init_Ctrl[37].addr[3] = 59;
1139 state->Init_Ctrl[37].bit[3] = 4;
1140 state->Init_Ctrl[37].val[3] = 0;
1141 state->Init_Ctrl[37].addr[4] = 59;
1142 state->Init_Ctrl[37].bit[4] = 5;
1143 state->Init_Ctrl[37].val[4] = 0;
1144 state->Init_Ctrl[37].addr[5] = 59;
1145 state->Init_Ctrl[37].bit[5] = 6;
1146 state->Init_Ctrl[37].val[5] = 0;
1147 state->Init_Ctrl[37].addr[6] = 59;
1148 state->Init_Ctrl[37].bit[6] = 7;
1149 state->Init_Ctrl[37].val[6] = 0;
1150
1151 state->Init_Ctrl[38].Ctrl_Num = TG_R_DIV ;
1152 state->Init_Ctrl[38].size = 6 ;
1153 state->Init_Ctrl[38].addr[0] = 32;
1154 state->Init_Ctrl[38].bit[0] = 2;
1155 state->Init_Ctrl[38].val[0] = 0;
1156 state->Init_Ctrl[38].addr[1] = 32;
1157 state->Init_Ctrl[38].bit[1] = 3;
1158 state->Init_Ctrl[38].val[1] = 0;
1159 state->Init_Ctrl[38].addr[2] = 32;
1160 state->Init_Ctrl[38].bit[2] = 4;
1161 state->Init_Ctrl[38].val[2] = 0;
1162 state->Init_Ctrl[38].addr[3] = 32;
1163 state->Init_Ctrl[38].bit[3] = 5;
1164 state->Init_Ctrl[38].val[3] = 0;
1165 state->Init_Ctrl[38].addr[4] = 32;
1166 state->Init_Ctrl[38].bit[4] = 6;
1167 state->Init_Ctrl[38].val[4] = 1;
1168 state->Init_Ctrl[38].addr[5] = 32;
1169 state->Init_Ctrl[38].bit[5] = 7;
1170 state->Init_Ctrl[38].val[5] = 0;
1171
1172 state->Init_Ctrl[39].Ctrl_Num = EN_CHP_LIN_B ;
1173 state->Init_Ctrl[39].size = 1 ;
1174 state->Init_Ctrl[39].addr[0] = 25;
1175 state->Init_Ctrl[39].bit[0] = 3;
1176 state->Init_Ctrl[39].val[0] = 1;
1177
1178
1179 state->CH_Ctrl_Num = CHCTRL_NUM ;
1180
1181 state->CH_Ctrl[0].Ctrl_Num = DN_POLY ;
1182 state->CH_Ctrl[0].size = 2 ;
1183 state->CH_Ctrl[0].addr[0] = 68;
1184 state->CH_Ctrl[0].bit[0] = 6;
1185 state->CH_Ctrl[0].val[0] = 1;
1186 state->CH_Ctrl[0].addr[1] = 68;
1187 state->CH_Ctrl[0].bit[1] = 7;
1188 state->CH_Ctrl[0].val[1] = 1;
1189
1190 state->CH_Ctrl[1].Ctrl_Num = DN_RFGAIN ;
1191 state->CH_Ctrl[1].size = 2 ;
1192 state->CH_Ctrl[1].addr[0] = 70;
1193 state->CH_Ctrl[1].bit[0] = 6;
1194 state->CH_Ctrl[1].val[0] = 1;
1195 state->CH_Ctrl[1].addr[1] = 70;
1196 state->CH_Ctrl[1].bit[1] = 7;
1197 state->CH_Ctrl[1].val[1] = 0;
1198
1199 state->CH_Ctrl[2].Ctrl_Num = DN_CAP_RFLPF ;
1200 state->CH_Ctrl[2].size = 9 ;
1201 state->CH_Ctrl[2].addr[0] = 69;
1202 state->CH_Ctrl[2].bit[0] = 5;
1203 state->CH_Ctrl[2].val[0] = 0;
1204 state->CH_Ctrl[2].addr[1] = 69;
1205 state->CH_Ctrl[2].bit[1] = 6;
1206 state->CH_Ctrl[2].val[1] = 0;
1207 state->CH_Ctrl[2].addr[2] = 69;
1208 state->CH_Ctrl[2].bit[2] = 7;
1209 state->CH_Ctrl[2].val[2] = 0;
1210 state->CH_Ctrl[2].addr[3] = 68;
1211 state->CH_Ctrl[2].bit[3] = 0;
1212 state->CH_Ctrl[2].val[3] = 0;
1213 state->CH_Ctrl[2].addr[4] = 68;
1214 state->CH_Ctrl[2].bit[4] = 1;
1215 state->CH_Ctrl[2].val[4] = 0;
1216 state->CH_Ctrl[2].addr[5] = 68;
1217 state->CH_Ctrl[2].bit[5] = 2;
1218 state->CH_Ctrl[2].val[5] = 0;
1219 state->CH_Ctrl[2].addr[6] = 68;
1220 state->CH_Ctrl[2].bit[6] = 3;
1221 state->CH_Ctrl[2].val[6] = 0;
1222 state->CH_Ctrl[2].addr[7] = 68;
1223 state->CH_Ctrl[2].bit[7] = 4;
1224 state->CH_Ctrl[2].val[7] = 0;
1225 state->CH_Ctrl[2].addr[8] = 68;
1226 state->CH_Ctrl[2].bit[8] = 5;
1227 state->CH_Ctrl[2].val[8] = 0;
1228
1229 state->CH_Ctrl[3].Ctrl_Num = DN_EN_VHFUHFBAR ;
1230 state->CH_Ctrl[3].size = 1 ;
1231 state->CH_Ctrl[3].addr[0] = 70;
1232 state->CH_Ctrl[3].bit[0] = 5;
1233 state->CH_Ctrl[3].val[0] = 0;
1234
1235 state->CH_Ctrl[4].Ctrl_Num = DN_GAIN_ADJUST ;
1236 state->CH_Ctrl[4].size = 3 ;
1237 state->CH_Ctrl[4].addr[0] = 73;
1238 state->CH_Ctrl[4].bit[0] = 4;
1239 state->CH_Ctrl[4].val[0] = 0;
1240 state->CH_Ctrl[4].addr[1] = 73;
1241 state->CH_Ctrl[4].bit[1] = 5;
1242 state->CH_Ctrl[4].val[1] = 1;
1243 state->CH_Ctrl[4].addr[2] = 73;
1244 state->CH_Ctrl[4].bit[2] = 6;
1245 state->CH_Ctrl[4].val[2] = 0;
1246
1247 state->CH_Ctrl[5].Ctrl_Num = DN_IQTNBUF_AMP ;
1248 state->CH_Ctrl[5].size = 4 ;
1249 state->CH_Ctrl[5].addr[0] = 70;
1250 state->CH_Ctrl[5].bit[0] = 0;
1251 state->CH_Ctrl[5].val[0] = 0;
1252 state->CH_Ctrl[5].addr[1] = 70;
1253 state->CH_Ctrl[5].bit[1] = 1;
1254 state->CH_Ctrl[5].val[1] = 0;
1255 state->CH_Ctrl[5].addr[2] = 70;
1256 state->CH_Ctrl[5].bit[2] = 2;
1257 state->CH_Ctrl[5].val[2] = 0;
1258 state->CH_Ctrl[5].addr[3] = 70;
1259 state->CH_Ctrl[5].bit[3] = 3;
1260 state->CH_Ctrl[5].val[3] = 0;
1261
1262 state->CH_Ctrl[6].Ctrl_Num = DN_IQTNGNBFBIAS_BST ;
1263 state->CH_Ctrl[6].size = 1 ;
1264 state->CH_Ctrl[6].addr[0] = 70;
1265 state->CH_Ctrl[6].bit[0] = 4;
1266 state->CH_Ctrl[6].val[0] = 1;
1267
1268 state->CH_Ctrl[7].Ctrl_Num = RFSYN_EN_OUTMUX ;
1269 state->CH_Ctrl[7].size = 1 ;
1270 state->CH_Ctrl[7].addr[0] = 111;
1271 state->CH_Ctrl[7].bit[0] = 4;
1272 state->CH_Ctrl[7].val[0] = 0;
1273
1274 state->CH_Ctrl[8].Ctrl_Num = RFSYN_SEL_VCO_OUT ;
1275 state->CH_Ctrl[8].size = 1 ;
1276 state->CH_Ctrl[8].addr[0] = 111;
1277 state->CH_Ctrl[8].bit[0] = 7;
1278 state->CH_Ctrl[8].val[0] = 1;
1279
1280 state->CH_Ctrl[9].Ctrl_Num = RFSYN_SEL_VCO_HI ;
1281 state->CH_Ctrl[9].size = 1 ;
1282 state->CH_Ctrl[9].addr[0] = 111;
1283 state->CH_Ctrl[9].bit[0] = 6;
1284 state->CH_Ctrl[9].val[0] = 1;
1285
1286 state->CH_Ctrl[10].Ctrl_Num = RFSYN_SEL_DIVM ;
1287 state->CH_Ctrl[10].size = 1 ;
1288 state->CH_Ctrl[10].addr[0] = 111;
1289 state->CH_Ctrl[10].bit[0] = 5;
1290 state->CH_Ctrl[10].val[0] = 0;
1291
1292 state->CH_Ctrl[11].Ctrl_Num = RFSYN_RF_DIV_BIAS ;
1293 state->CH_Ctrl[11].size = 2 ;
1294 state->CH_Ctrl[11].addr[0] = 110;
1295 state->CH_Ctrl[11].bit[0] = 0;
1296 state->CH_Ctrl[11].val[0] = 1;
1297 state->CH_Ctrl[11].addr[1] = 110;
1298 state->CH_Ctrl[11].bit[1] = 1;
1299 state->CH_Ctrl[11].val[1] = 0;
1300
1301 state->CH_Ctrl[12].Ctrl_Num = DN_SEL_FREQ ;
1302 state->CH_Ctrl[12].size = 3 ;
1303 state->CH_Ctrl[12].addr[0] = 69;
1304 state->CH_Ctrl[12].bit[0] = 2;
1305 state->CH_Ctrl[12].val[0] = 0;
1306 state->CH_Ctrl[12].addr[1] = 69;
1307 state->CH_Ctrl[12].bit[1] = 3;
1308 state->CH_Ctrl[12].val[1] = 0;
1309 state->CH_Ctrl[12].addr[2] = 69;
1310 state->CH_Ctrl[12].bit[2] = 4;
1311 state->CH_Ctrl[12].val[2] = 0;
1312
1313 state->CH_Ctrl[13].Ctrl_Num = RFSYN_VCO_BIAS ;
1314 state->CH_Ctrl[13].size = 6 ;
1315 state->CH_Ctrl[13].addr[0] = 110;
1316 state->CH_Ctrl[13].bit[0] = 2;
1317 state->CH_Ctrl[13].val[0] = 0;
1318 state->CH_Ctrl[13].addr[1] = 110;
1319 state->CH_Ctrl[13].bit[1] = 3;
1320 state->CH_Ctrl[13].val[1] = 0;
1321 state->CH_Ctrl[13].addr[2] = 110;
1322 state->CH_Ctrl[13].bit[2] = 4;
1323 state->CH_Ctrl[13].val[2] = 0;
1324 state->CH_Ctrl[13].addr[3] = 110;
1325 state->CH_Ctrl[13].bit[3] = 5;
1326 state->CH_Ctrl[13].val[3] = 0;
1327 state->CH_Ctrl[13].addr[4] = 110;
1328 state->CH_Ctrl[13].bit[4] = 6;
1329 state->CH_Ctrl[13].val[4] = 0;
1330 state->CH_Ctrl[13].addr[5] = 110;
1331 state->CH_Ctrl[13].bit[5] = 7;
1332 state->CH_Ctrl[13].val[5] = 1;
1333
1334 state->CH_Ctrl[14].Ctrl_Num = CHCAL_INT_MOD_RF ;
1335 state->CH_Ctrl[14].size = 7 ;
1336 state->CH_Ctrl[14].addr[0] = 14;
1337 state->CH_Ctrl[14].bit[0] = 0;
1338 state->CH_Ctrl[14].val[0] = 0;
1339 state->CH_Ctrl[14].addr[1] = 14;
1340 state->CH_Ctrl[14].bit[1] = 1;
1341 state->CH_Ctrl[14].val[1] = 0;
1342 state->CH_Ctrl[14].addr[2] = 14;
1343 state->CH_Ctrl[14].bit[2] = 2;
1344 state->CH_Ctrl[14].val[2] = 0;
1345 state->CH_Ctrl[14].addr[3] = 14;
1346 state->CH_Ctrl[14].bit[3] = 3;
1347 state->CH_Ctrl[14].val[3] = 0;
1348 state->CH_Ctrl[14].addr[4] = 14;
1349 state->CH_Ctrl[14].bit[4] = 4;
1350 state->CH_Ctrl[14].val[4] = 0;
1351 state->CH_Ctrl[14].addr[5] = 14;
1352 state->CH_Ctrl[14].bit[5] = 5;
1353 state->CH_Ctrl[14].val[5] = 0;
1354 state->CH_Ctrl[14].addr[6] = 14;
1355 state->CH_Ctrl[14].bit[6] = 6;
1356 state->CH_Ctrl[14].val[6] = 0;
1357
1358 state->CH_Ctrl[15].Ctrl_Num = CHCAL_FRAC_MOD_RF ;
1359 state->CH_Ctrl[15].size = 18 ;
1360 state->CH_Ctrl[15].addr[0] = 17;
1361 state->CH_Ctrl[15].bit[0] = 6;
1362 state->CH_Ctrl[15].val[0] = 0;
1363 state->CH_Ctrl[15].addr[1] = 17;
1364 state->CH_Ctrl[15].bit[1] = 7;
1365 state->CH_Ctrl[15].val[1] = 0;
1366 state->CH_Ctrl[15].addr[2] = 16;
1367 state->CH_Ctrl[15].bit[2] = 0;
1368 state->CH_Ctrl[15].val[2] = 0;
1369 state->CH_Ctrl[15].addr[3] = 16;
1370 state->CH_Ctrl[15].bit[3] = 1;
1371 state->CH_Ctrl[15].val[3] = 0;
1372 state->CH_Ctrl[15].addr[4] = 16;
1373 state->CH_Ctrl[15].bit[4] = 2;
1374 state->CH_Ctrl[15].val[4] = 0;
1375 state->CH_Ctrl[15].addr[5] = 16;
1376 state->CH_Ctrl[15].bit[5] = 3;
1377 state->CH_Ctrl[15].val[5] = 0;
1378 state->CH_Ctrl[15].addr[6] = 16;
1379 state->CH_Ctrl[15].bit[6] = 4;
1380 state->CH_Ctrl[15].val[6] = 0;
1381 state->CH_Ctrl[15].addr[7] = 16;
1382 state->CH_Ctrl[15].bit[7] = 5;
1383 state->CH_Ctrl[15].val[7] = 0;
1384 state->CH_Ctrl[15].addr[8] = 16;
1385 state->CH_Ctrl[15].bit[8] = 6;
1386 state->CH_Ctrl[15].val[8] = 0;
1387 state->CH_Ctrl[15].addr[9] = 16;
1388 state->CH_Ctrl[15].bit[9] = 7;
1389 state->CH_Ctrl[15].val[9] = 0;
1390 state->CH_Ctrl[15].addr[10] = 15;
1391 state->CH_Ctrl[15].bit[10] = 0;
1392 state->CH_Ctrl[15].val[10] = 0;
1393 state->CH_Ctrl[15].addr[11] = 15;
1394 state->CH_Ctrl[15].bit[11] = 1;
1395 state->CH_Ctrl[15].val[11] = 0;
1396 state->CH_Ctrl[15].addr[12] = 15;
1397 state->CH_Ctrl[15].bit[12] = 2;
1398 state->CH_Ctrl[15].val[12] = 0;
1399 state->CH_Ctrl[15].addr[13] = 15;
1400 state->CH_Ctrl[15].bit[13] = 3;
1401 state->CH_Ctrl[15].val[13] = 0;
1402 state->CH_Ctrl[15].addr[14] = 15;
1403 state->CH_Ctrl[15].bit[14] = 4;
1404 state->CH_Ctrl[15].val[14] = 0;
1405 state->CH_Ctrl[15].addr[15] = 15;
1406 state->CH_Ctrl[15].bit[15] = 5;
1407 state->CH_Ctrl[15].val[15] = 0;
1408 state->CH_Ctrl[15].addr[16] = 15;
1409 state->CH_Ctrl[15].bit[16] = 6;
1410 state->CH_Ctrl[15].val[16] = 1;
1411 state->CH_Ctrl[15].addr[17] = 15;
1412 state->CH_Ctrl[15].bit[17] = 7;
1413 state->CH_Ctrl[15].val[17] = 1;
1414
1415 state->CH_Ctrl[16].Ctrl_Num = RFSYN_LPF_R ;
1416 state->CH_Ctrl[16].size = 5 ;
1417 state->CH_Ctrl[16].addr[0] = 112;
1418 state->CH_Ctrl[16].bit[0] = 0;
1419 state->CH_Ctrl[16].val[0] = 0;
1420 state->CH_Ctrl[16].addr[1] = 112;
1421 state->CH_Ctrl[16].bit[1] = 1;
1422 state->CH_Ctrl[16].val[1] = 0;
1423 state->CH_Ctrl[16].addr[2] = 112;
1424 state->CH_Ctrl[16].bit[2] = 2;
1425 state->CH_Ctrl[16].val[2] = 0;
1426 state->CH_Ctrl[16].addr[3] = 112;
1427 state->CH_Ctrl[16].bit[3] = 3;
1428 state->CH_Ctrl[16].val[3] = 0;
1429 state->CH_Ctrl[16].addr[4] = 112;
1430 state->CH_Ctrl[16].bit[4] = 4;
1431 state->CH_Ctrl[16].val[4] = 1;
1432
1433 state->CH_Ctrl[17].Ctrl_Num = CHCAL_EN_INT_RF ;
1434 state->CH_Ctrl[17].size = 1 ;
1435 state->CH_Ctrl[17].addr[0] = 14;
1436 state->CH_Ctrl[17].bit[0] = 7;
1437 state->CH_Ctrl[17].val[0] = 0;
1438
1439 state->CH_Ctrl[18].Ctrl_Num = TG_LO_DIVVAL ;
1440 state->CH_Ctrl[18].size = 4 ;
1441 state->CH_Ctrl[18].addr[0] = 107;
1442 state->CH_Ctrl[18].bit[0] = 3;
1443 state->CH_Ctrl[18].val[0] = 0;
1444 state->CH_Ctrl[18].addr[1] = 107;
1445 state->CH_Ctrl[18].bit[1] = 4;
1446 state->CH_Ctrl[18].val[1] = 0;
1447 state->CH_Ctrl[18].addr[2] = 107;
1448 state->CH_Ctrl[18].bit[2] = 5;
1449 state->CH_Ctrl[18].val[2] = 0;
1450 state->CH_Ctrl[18].addr[3] = 107;
1451 state->CH_Ctrl[18].bit[3] = 6;
1452 state->CH_Ctrl[18].val[3] = 0;
1453
1454 state->CH_Ctrl[19].Ctrl_Num = TG_LO_SELVAL ;
1455 state->CH_Ctrl[19].size = 3 ;
1456 state->CH_Ctrl[19].addr[0] = 107;
1457 state->CH_Ctrl[19].bit[0] = 7;
1458 state->CH_Ctrl[19].val[0] = 1;
1459 state->CH_Ctrl[19].addr[1] = 106;
1460 state->CH_Ctrl[19].bit[1] = 0;
1461 state->CH_Ctrl[19].val[1] = 1;
1462 state->CH_Ctrl[19].addr[2] = 106;
1463 state->CH_Ctrl[19].bit[2] = 1;
1464 state->CH_Ctrl[19].val[2] = 1;
1465
1466 state->CH_Ctrl[20].Ctrl_Num = TG_DIV_VAL ;
1467 state->CH_Ctrl[20].size = 11 ;
1468 state->CH_Ctrl[20].addr[0] = 109;
1469 state->CH_Ctrl[20].bit[0] = 2;
1470 state->CH_Ctrl[20].val[0] = 0;
1471 state->CH_Ctrl[20].addr[1] = 109;
1472 state->CH_Ctrl[20].bit[1] = 3;
1473 state->CH_Ctrl[20].val[1] = 0;
1474 state->CH_Ctrl[20].addr[2] = 109;
1475 state->CH_Ctrl[20].bit[2] = 4;
1476 state->CH_Ctrl[20].val[2] = 0;
1477 state->CH_Ctrl[20].addr[3] = 109;
1478 state->CH_Ctrl[20].bit[3] = 5;
1479 state->CH_Ctrl[20].val[3] = 0;
1480 state->CH_Ctrl[20].addr[4] = 109;
1481 state->CH_Ctrl[20].bit[4] = 6;
1482 state->CH_Ctrl[20].val[4] = 0;
1483 state->CH_Ctrl[20].addr[5] = 109;
1484 state->CH_Ctrl[20].bit[5] = 7;
1485 state->CH_Ctrl[20].val[5] = 0;
1486 state->CH_Ctrl[20].addr[6] = 108;
1487 state->CH_Ctrl[20].bit[6] = 0;
1488 state->CH_Ctrl[20].val[6] = 0;
1489 state->CH_Ctrl[20].addr[7] = 108;
1490 state->CH_Ctrl[20].bit[7] = 1;
1491 state->CH_Ctrl[20].val[7] = 0;
1492 state->CH_Ctrl[20].addr[8] = 108;
1493 state->CH_Ctrl[20].bit[8] = 2;
1494 state->CH_Ctrl[20].val[8] = 1;
1495 state->CH_Ctrl[20].addr[9] = 108;
1496 state->CH_Ctrl[20].bit[9] = 3;
1497 state->CH_Ctrl[20].val[9] = 1;
1498 state->CH_Ctrl[20].addr[10] = 108;
1499 state->CH_Ctrl[20].bit[10] = 4;
1500 state->CH_Ctrl[20].val[10] = 1;
1501
1502 state->CH_Ctrl[21].Ctrl_Num = TG_VCO_BIAS ;
1503 state->CH_Ctrl[21].size = 6 ;
1504 state->CH_Ctrl[21].addr[0] = 106;
1505 state->CH_Ctrl[21].bit[0] = 2;
1506 state->CH_Ctrl[21].val[0] = 0;
1507 state->CH_Ctrl[21].addr[1] = 106;
1508 state->CH_Ctrl[21].bit[1] = 3;
1509 state->CH_Ctrl[21].val[1] = 0;
1510 state->CH_Ctrl[21].addr[2] = 106;
1511 state->CH_Ctrl[21].bit[2] = 4;
1512 state->CH_Ctrl[21].val[2] = 0;
1513 state->CH_Ctrl[21].addr[3] = 106;
1514 state->CH_Ctrl[21].bit[3] = 5;
1515 state->CH_Ctrl[21].val[3] = 0;
1516 state->CH_Ctrl[21].addr[4] = 106;
1517 state->CH_Ctrl[21].bit[4] = 6;
1518 state->CH_Ctrl[21].val[4] = 0;
1519 state->CH_Ctrl[21].addr[5] = 106;
1520 state->CH_Ctrl[21].bit[5] = 7;
1521 state->CH_Ctrl[21].val[5] = 1;
1522
1523 state->CH_Ctrl[22].Ctrl_Num = SEQ_EXTPOWERUP ;
1524 state->CH_Ctrl[22].size = 1 ;
1525 state->CH_Ctrl[22].addr[0] = 138;
1526 state->CH_Ctrl[22].bit[0] = 4;
1527 state->CH_Ctrl[22].val[0] = 1;
1528
1529 state->CH_Ctrl[23].Ctrl_Num = OVERRIDE_2 ;
1530 state->CH_Ctrl[23].size = 1 ;
1531 state->CH_Ctrl[23].addr[0] = 17;
1532 state->CH_Ctrl[23].bit[0] = 5;
1533 state->CH_Ctrl[23].val[0] = 0;
1534
1535 state->CH_Ctrl[24].Ctrl_Num = OVERRIDE_3 ;
1536 state->CH_Ctrl[24].size = 1 ;
1537 state->CH_Ctrl[24].addr[0] = 111;
1538 state->CH_Ctrl[24].bit[0] = 3;
1539 state->CH_Ctrl[24].val[0] = 0;
1540
1541 state->CH_Ctrl[25].Ctrl_Num = OVERRIDE_4 ;
1542 state->CH_Ctrl[25].size = 1 ;
1543 state->CH_Ctrl[25].addr[0] = 112;
1544 state->CH_Ctrl[25].bit[0] = 7;
1545 state->CH_Ctrl[25].val[0] = 0;
1546
1547 state->CH_Ctrl[26].Ctrl_Num = SEQ_FSM_PULSE ;
1548 state->CH_Ctrl[26].size = 1 ;
1549 state->CH_Ctrl[26].addr[0] = 136;
1550 state->CH_Ctrl[26].bit[0] = 7;
1551 state->CH_Ctrl[26].val[0] = 0;
1552
1553 state->CH_Ctrl[27].Ctrl_Num = GPIO_4B ;
1554 state->CH_Ctrl[27].size = 1 ;
1555 state->CH_Ctrl[27].addr[0] = 149;
1556 state->CH_Ctrl[27].bit[0] = 7;
1557 state->CH_Ctrl[27].val[0] = 0;
1558
1559 state->CH_Ctrl[28].Ctrl_Num = GPIO_3B ;
1560 state->CH_Ctrl[28].size = 1 ;
1561 state->CH_Ctrl[28].addr[0] = 149;
1562 state->CH_Ctrl[28].bit[0] = 6;
1563 state->CH_Ctrl[28].val[0] = 0;
1564
1565 state->CH_Ctrl[29].Ctrl_Num = GPIO_4 ;
1566 state->CH_Ctrl[29].size = 1 ;
1567 state->CH_Ctrl[29].addr[0] = 149;
1568 state->CH_Ctrl[29].bit[0] = 5;
1569 state->CH_Ctrl[29].val[0] = 1;
1570
1571 state->CH_Ctrl[30].Ctrl_Num = GPIO_3 ;
1572 state->CH_Ctrl[30].size = 1 ;
1573 state->CH_Ctrl[30].addr[0] = 149;
1574 state->CH_Ctrl[30].bit[0] = 4;
1575 state->CH_Ctrl[30].val[0] = 1;
1576
1577 state->CH_Ctrl[31].Ctrl_Num = GPIO_1B ;
1578 state->CH_Ctrl[31].size = 1 ;
1579 state->CH_Ctrl[31].addr[0] = 149;
1580 state->CH_Ctrl[31].bit[0] = 3;
1581 state->CH_Ctrl[31].val[0] = 0;
1582
1583 state->CH_Ctrl[32].Ctrl_Num = DAC_A_ENABLE ;
1584 state->CH_Ctrl[32].size = 1 ;
1585 state->CH_Ctrl[32].addr[0] = 93;
1586 state->CH_Ctrl[32].bit[0] = 1;
1587 state->CH_Ctrl[32].val[0] = 0;
1588
1589 state->CH_Ctrl[33].Ctrl_Num = DAC_B_ENABLE ;
1590 state->CH_Ctrl[33].size = 1 ;
1591 state->CH_Ctrl[33].addr[0] = 93;
1592 state->CH_Ctrl[33].bit[0] = 0;
1593 state->CH_Ctrl[33].val[0] = 0;
1594
1595 state->CH_Ctrl[34].Ctrl_Num = DAC_DIN_A ;
1596 state->CH_Ctrl[34].size = 6 ;
1597 state->CH_Ctrl[34].addr[0] = 92;
1598 state->CH_Ctrl[34].bit[0] = 2;
1599 state->CH_Ctrl[34].val[0] = 0;
1600 state->CH_Ctrl[34].addr[1] = 92;
1601 state->CH_Ctrl[34].bit[1] = 3;
1602 state->CH_Ctrl[34].val[1] = 0;
1603 state->CH_Ctrl[34].addr[2] = 92;
1604 state->CH_Ctrl[34].bit[2] = 4;
1605 state->CH_Ctrl[34].val[2] = 0;
1606 state->CH_Ctrl[34].addr[3] = 92;
1607 state->CH_Ctrl[34].bit[3] = 5;
1608 state->CH_Ctrl[34].val[3] = 0;
1609 state->CH_Ctrl[34].addr[4] = 92;
1610 state->CH_Ctrl[34].bit[4] = 6;
1611 state->CH_Ctrl[34].val[4] = 0;
1612 state->CH_Ctrl[34].addr[5] = 92;
1613 state->CH_Ctrl[34].bit[5] = 7;
1614 state->CH_Ctrl[34].val[5] = 0;
1615
1616 state->CH_Ctrl[35].Ctrl_Num = DAC_DIN_B ;
1617 state->CH_Ctrl[35].size = 6 ;
1618 state->CH_Ctrl[35].addr[0] = 93;
1619 state->CH_Ctrl[35].bit[0] = 2;
1620 state->CH_Ctrl[35].val[0] = 0;
1621 state->CH_Ctrl[35].addr[1] = 93;
1622 state->CH_Ctrl[35].bit[1] = 3;
1623 state->CH_Ctrl[35].val[1] = 0;
1624 state->CH_Ctrl[35].addr[2] = 93;
1625 state->CH_Ctrl[35].bit[2] = 4;
1626 state->CH_Ctrl[35].val[2] = 0;
1627 state->CH_Ctrl[35].addr[3] = 93;
1628 state->CH_Ctrl[35].bit[3] = 5;
1629 state->CH_Ctrl[35].val[3] = 0;
1630 state->CH_Ctrl[35].addr[4] = 93;
1631 state->CH_Ctrl[35].bit[4] = 6;
1632 state->CH_Ctrl[35].val[4] = 0;
1633 state->CH_Ctrl[35].addr[5] = 93;
1634 state->CH_Ctrl[35].bit[5] = 7;
1635 state->CH_Ctrl[35].val[5] = 0;
1636
1637#ifdef _MXL_PRODUCTION
1638 state->CH_Ctrl[36].Ctrl_Num = RFSYN_EN_DIV ;
1639 state->CH_Ctrl[36].size = 1 ;
1640 state->CH_Ctrl[36].addr[0] = 109;
1641 state->CH_Ctrl[36].bit[0] = 1;
1642 state->CH_Ctrl[36].val[0] = 1;
1643
1644 state->CH_Ctrl[37].Ctrl_Num = RFSYN_DIVM ;
1645 state->CH_Ctrl[37].size = 2 ;
1646 state->CH_Ctrl[37].addr[0] = 112;
1647 state->CH_Ctrl[37].bit[0] = 5;
1648 state->CH_Ctrl[37].val[0] = 0;
1649 state->CH_Ctrl[37].addr[1] = 112;
1650 state->CH_Ctrl[37].bit[1] = 6;
1651 state->CH_Ctrl[37].val[1] = 0;
1652
1653 state->CH_Ctrl[38].Ctrl_Num = DN_BYPASS_AGC_I2C ;
1654 state->CH_Ctrl[38].size = 1 ;
1655 state->CH_Ctrl[38].addr[0] = 65;
1656 state->CH_Ctrl[38].bit[0] = 1;
1657 state->CH_Ctrl[38].val[0] = 0;
1658#endif
1659
1660 return 0 ;
1661}
1662
1663static void InitTunerControls(struct dvb_frontend *fe)
1664{
1665 MXL5005_RegisterInit(fe);
1666 MXL5005_ControlInit(fe);
1667#ifdef _MXL_INTERNAL
1668 MXL5005_MXLControlInit(fe);
1669#endif
1670}
1671
1672static u16 MXL5005_TunerConfig(struct dvb_frontend *fe,
1673 u8 Mode, /* 0: Analog Mode ; 1: Digital Mode */
1674 u8 IF_mode, /* for Analog Mode, 0: zero IF; 1: low IF */
1675 u32 Bandwidth, /* filter channel bandwidth (6, 7, 8) */
1676 u32 IF_out, /* Desired IF Out Frequency */
1677 u32 Fxtal, /* XTAL Frequency */
1678 u8 AGC_Mode, /* AGC Mode - Dual AGC: 0, Single AGC: 1 */
1679 u16 TOP, /* 0: Dual AGC; Value: take over point */
1680 u16 IF_OUT_LOAD, /* IF Out Load Resistor (200 / 300 Ohms) */
1681 u8 CLOCK_OUT, /* 0: turn off clk out; 1: turn on clock out */
1682 u8 DIV_OUT, /* 0: Div-1; 1: Div-4 */
1683 u8 CAPSELECT, /* 0: disable On-Chip pulling cap; 1: enable */
1684 u8 EN_RSSI, /* 0: disable RSSI; 1: enable RSSI */
1685
1686 /* Modulation Type; */
1687 /* 0 - Default; 1 - DVB-T; 2 - ATSC; 3 - QAM; 4 - Analog Cable */
1688 u8 Mod_Type,
1689
1690 /* Tracking Filter */
1691 /* 0 - Default; 1 - Off; 2 - Type C; 3 - Type C-H */
1692 u8 TF_Type
1693 )
1694{
1695 struct mxl5005s_state *state = fe->tuner_priv;
1696 u16 status = 0;
1697
1698 state->Mode = Mode;
1699 state->IF_Mode = IF_mode;
1700 state->Chan_Bandwidth = Bandwidth;
1701 state->IF_OUT = IF_out;
1702 state->Fxtal = Fxtal;
1703 state->AGC_Mode = AGC_Mode;
1704 state->TOP = TOP;
1705 state->IF_OUT_LOAD = IF_OUT_LOAD;
1706 state->CLOCK_OUT = CLOCK_OUT;
1707 state->DIV_OUT = DIV_OUT;
1708 state->CAPSELECT = CAPSELECT;
1709 state->EN_RSSI = EN_RSSI;
1710 state->Mod_Type = Mod_Type;
1711 state->TF_Type = TF_Type;
1712
1713 /* Initialize all the controls and registers */
1714 InitTunerControls(fe);
1715
1716 /* Synthesizer LO frequency calculation */
1717 MXL_SynthIFLO_Calc(fe);
1718
1719 return status;
1720}
1721
1722static void MXL_SynthIFLO_Calc(struct dvb_frontend *fe)
1723{
1724 struct mxl5005s_state *state = fe->tuner_priv;
1725 if (state->Mode == 1) /* Digital Mode */
1726 state->IF_LO = state->IF_OUT;
1727 else /* Analog Mode */ {
1728 if (state->IF_Mode == 0) /* Analog Zero IF mode */
1729 state->IF_LO = state->IF_OUT + 400000;
1730 else /* Analog Low IF mode */
1731 state->IF_LO = state->IF_OUT + state->Chan_Bandwidth/2;
1732 }
1733}
1734
1735static void MXL_SynthRFTGLO_Calc(struct dvb_frontend *fe)
1736{
1737 struct mxl5005s_state *state = fe->tuner_priv;
1738
1739 if (state->Mode == 1) /* Digital Mode */ {
1740 /* remove 20.48MHz setting for 2.6.10 */
1741 state->RF_LO = state->RF_IN;
1742 /* change for 2.6.6 */
1743 state->TG_LO = state->RF_IN - 750000;
1744 } else /* Analog Mode */ {
1745 if (state->IF_Mode == 0) /* Analog Zero IF mode */ {
1746 state->RF_LO = state->RF_IN - 400000;
1747 state->TG_LO = state->RF_IN - 1750000;
1748 } else /* Analog Low IF mode */ {
1749 state->RF_LO = state->RF_IN - state->Chan_Bandwidth/2;
1750 state->TG_LO = state->RF_IN -
1751 state->Chan_Bandwidth + 500000;
1752 }
1753 }
1754}
1755
1756static u16 MXL_OverwriteICDefault(struct dvb_frontend *fe)
1757{
1758 u16 status = 0;
1759
1760 status += MXL_ControlWrite(fe, OVERRIDE_1, 1);
1761 status += MXL_ControlWrite(fe, OVERRIDE_2, 1);
1762 status += MXL_ControlWrite(fe, OVERRIDE_3, 1);
1763 status += MXL_ControlWrite(fe, OVERRIDE_4, 1);
1764
1765 return status;
1766}
1767
1768static u16 MXL_BlockInit(struct dvb_frontend *fe)
1769{
1770 struct mxl5005s_state *state = fe->tuner_priv;
1771 u16 status = 0;
1772
1773 status += MXL_OverwriteICDefault(fe);
1774
1775 /* Downconverter Control Dig Ana */
1776 status += MXL_ControlWrite(fe, DN_IQTN_AMP_CUT, state->Mode ? 1 : 0);
1777
1778 /* Filter Control Dig Ana */
1779 status += MXL_ControlWrite(fe, BB_MODE, state->Mode ? 0 : 1);
1780 status += MXL_ControlWrite(fe, BB_BUF, state->Mode ? 3 : 2);
1781 status += MXL_ControlWrite(fe, BB_BUF_OA, state->Mode ? 1 : 0);
1782 status += MXL_ControlWrite(fe, BB_IQSWAP, state->Mode ? 0 : 1);
1783 status += MXL_ControlWrite(fe, BB_INITSTATE_DLPF_TUNE, 0);
1784
1785 /* Initialize Low-Pass Filter */
1786 if (state->Mode) { /* Digital Mode */
1787 switch (state->Chan_Bandwidth) {
1788 case 8000000:
1789 status += MXL_ControlWrite(fe, BB_DLPF_BANDSEL, 0);
1790 break;
1791 case 7000000:
1792 status += MXL_ControlWrite(fe, BB_DLPF_BANDSEL, 2);
1793 break;
1794 case 6000000:
1795 status += MXL_ControlWrite(fe,
1796 BB_DLPF_BANDSEL, 3);
1797 break;
1798 }
1799 } else { /* Analog Mode */
1800 switch (state->Chan_Bandwidth) {
1801 case 8000000: /* Low Zero */
1802 status += MXL_ControlWrite(fe, BB_ALPF_BANDSELECT,
1803 (state->IF_Mode ? 0 : 3));
1804 break;
1805 case 7000000:
1806 status += MXL_ControlWrite(fe, BB_ALPF_BANDSELECT,
1807 (state->IF_Mode ? 1 : 4));
1808 break;
1809 case 6000000:
1810 status += MXL_ControlWrite(fe, BB_ALPF_BANDSELECT,
1811 (state->IF_Mode ? 2 : 5));
1812 break;
1813 }
1814 }
1815
1816 /* Charge Pump Control Dig Ana */
1817 status += MXL_ControlWrite(fe, RFSYN_CHP_GAIN, state->Mode ? 5 : 8);
1818 status += MXL_ControlWrite(fe,
1819 RFSYN_EN_CHP_HIGAIN, state->Mode ? 1 : 1);
1820 status += MXL_ControlWrite(fe, EN_CHP_LIN_B, state->Mode ? 0 : 0);
1821
1822 /* AGC TOP Control */
1823 if (state->AGC_Mode == 0) /* Dual AGC */ {
1824 status += MXL_ControlWrite(fe, AGC_IF, 15);
1825 status += MXL_ControlWrite(fe, AGC_RF, 15);
1826 } else /* Single AGC Mode Dig Ana */
1827 status += MXL_ControlWrite(fe, AGC_RF, state->Mode ? 15 : 12);
1828
1829 if (state->TOP == 55) /* TOP == 5.5 */
1830 status += MXL_ControlWrite(fe, AGC_IF, 0x0);
1831
1832 if (state->TOP == 72) /* TOP == 7.2 */
1833 status += MXL_ControlWrite(fe, AGC_IF, 0x1);
1834
1835 if (state->TOP == 92) /* TOP == 9.2 */
1836 status += MXL_ControlWrite(fe, AGC_IF, 0x2);
1837
1838 if (state->TOP == 110) /* TOP == 11.0 */
1839 status += MXL_ControlWrite(fe, AGC_IF, 0x3);
1840
1841 if (state->TOP == 129) /* TOP == 12.9 */
1842 status += MXL_ControlWrite(fe, AGC_IF, 0x4);
1843
1844 if (state->TOP == 147) /* TOP == 14.7 */
1845 status += MXL_ControlWrite(fe, AGC_IF, 0x5);
1846
1847 if (state->TOP == 168) /* TOP == 16.8 */
1848 status += MXL_ControlWrite(fe, AGC_IF, 0x6);
1849
1850 if (state->TOP == 194) /* TOP == 19.4 */
1851 status += MXL_ControlWrite(fe, AGC_IF, 0x7);
1852
1853 if (state->TOP == 212) /* TOP == 21.2 */
1854 status += MXL_ControlWrite(fe, AGC_IF, 0x9);
1855
1856 if (state->TOP == 232) /* TOP == 23.2 */
1857 status += MXL_ControlWrite(fe, AGC_IF, 0xA);
1858
1859 if (state->TOP == 252) /* TOP == 25.2 */
1860 status += MXL_ControlWrite(fe, AGC_IF, 0xB);
1861
1862 if (state->TOP == 271) /* TOP == 27.1 */
1863 status += MXL_ControlWrite(fe, AGC_IF, 0xC);
1864
1865 if (state->TOP == 292) /* TOP == 29.2 */
1866 status += MXL_ControlWrite(fe, AGC_IF, 0xD);
1867
1868 if (state->TOP == 317) /* TOP == 31.7 */
1869 status += MXL_ControlWrite(fe, AGC_IF, 0xE);
1870
1871 if (state->TOP == 349) /* TOP == 34.9 */
1872 status += MXL_ControlWrite(fe, AGC_IF, 0xF);
1873
1874 /* IF Synthesizer Control */
1875 status += MXL_IFSynthInit(fe);
1876
1877 /* IF UpConverter Control */
1878 if (state->IF_OUT_LOAD == 200) {
1879 status += MXL_ControlWrite(fe, DRV_RES_SEL, 6);
1880 status += MXL_ControlWrite(fe, I_DRIVER, 2);
1881 }
1882 if (state->IF_OUT_LOAD == 300) {
1883 status += MXL_ControlWrite(fe, DRV_RES_SEL, 4);
1884 status += MXL_ControlWrite(fe, I_DRIVER, 1);
1885 }
1886
1887 /* Anti-Alias Filtering Control
1888 * initialise Anti-Aliasing Filter
1889 */
1890 if (state->Mode) { /* Digital Mode */
1891 if (state->IF_OUT >= 4000000UL && state->IF_OUT <= 6280000UL) {
1892 status += MXL_ControlWrite(fe, EN_AAF, 1);
1893 status += MXL_ControlWrite(fe, EN_3P, 1);
1894 status += MXL_ControlWrite(fe, EN_AUX_3P, 1);
1895 status += MXL_ControlWrite(fe, SEL_AAF_BAND, 0);
1896 }
1897 if ((state->IF_OUT == 36125000UL) ||
1898 (state->IF_OUT == 36150000UL)) {
1899 status += MXL_ControlWrite(fe, EN_AAF, 1);
1900 status += MXL_ControlWrite(fe, EN_3P, 1);
1901 status += MXL_ControlWrite(fe, EN_AUX_3P, 1);
1902 status += MXL_ControlWrite(fe, SEL_AAF_BAND, 1);
1903 }
1904 if (state->IF_OUT > 36150000UL) {
1905 status += MXL_ControlWrite(fe, EN_AAF, 0);
1906 status += MXL_ControlWrite(fe, EN_3P, 1);
1907 status += MXL_ControlWrite(fe, EN_AUX_3P, 1);
1908 status += MXL_ControlWrite(fe, SEL_AAF_BAND, 1);
1909 }
1910 } else { /* Analog Mode */
1911 if (state->IF_OUT >= 4000000UL && state->IF_OUT <= 5000000UL) {
1912 status += MXL_ControlWrite(fe, EN_AAF, 1);
1913 status += MXL_ControlWrite(fe, EN_3P, 1);
1914 status += MXL_ControlWrite(fe, EN_AUX_3P, 1);
1915 status += MXL_ControlWrite(fe, SEL_AAF_BAND, 0);
1916 }
1917 if (state->IF_OUT > 5000000UL) {
1918 status += MXL_ControlWrite(fe, EN_AAF, 0);
1919 status += MXL_ControlWrite(fe, EN_3P, 0);
1920 status += MXL_ControlWrite(fe, EN_AUX_3P, 0);
1921 status += MXL_ControlWrite(fe, SEL_AAF_BAND, 0);
1922 }
1923 }
1924
1925 /* Demod Clock Out */
1926 if (state->CLOCK_OUT)
1927 status += MXL_ControlWrite(fe, SEQ_ENCLK16_CLK_OUT, 1);
1928 else
1929 status += MXL_ControlWrite(fe, SEQ_ENCLK16_CLK_OUT, 0);
1930
1931 if (state->DIV_OUT == 1)
1932 status += MXL_ControlWrite(fe, SEQ_SEL4_16B, 1);
1933 if (state->DIV_OUT == 0)
1934 status += MXL_ControlWrite(fe, SEQ_SEL4_16B, 0);
1935
1936 /* Crystal Control */
1937 if (state->CAPSELECT)
1938 status += MXL_ControlWrite(fe, XTAL_CAPSELECT, 1);
1939 else
1940 status += MXL_ControlWrite(fe, XTAL_CAPSELECT, 0);
1941
1942 if (state->Fxtal >= 12000000UL && state->Fxtal <= 16000000UL)
1943 status += MXL_ControlWrite(fe, IF_SEL_DBL, 1);
1944 if (state->Fxtal > 16000000UL && state->Fxtal <= 32000000UL)
1945 status += MXL_ControlWrite(fe, IF_SEL_DBL, 0);
1946
1947 if (state->Fxtal >= 12000000UL && state->Fxtal <= 22000000UL)
1948 status += MXL_ControlWrite(fe, RFSYN_R_DIV, 3);
1949 if (state->Fxtal > 22000000UL && state->Fxtal <= 32000000UL)
1950 status += MXL_ControlWrite(fe, RFSYN_R_DIV, 0);
1951
1952 /* Misc Controls */
1953 if (state->Mode == 0 && state->IF_Mode == 1) /* Analog LowIF mode */
1954 status += MXL_ControlWrite(fe, SEQ_EXTIQFSMPULSE, 0);
1955 else
1956 status += MXL_ControlWrite(fe, SEQ_EXTIQFSMPULSE, 1);
1957
1958 /* status += MXL_ControlRead(fe, IF_DIVVAL, &IF_DIVVAL_Val); */
1959
1960 /* Set TG_R_DIV */
1961 status += MXL_ControlWrite(fe, TG_R_DIV,
1962 MXL_Ceiling(state->Fxtal, 1000000));
1963
1964 /* Apply Default value to BB_INITSTATE_DLPF_TUNE */
1965
1966 /* RSSI Control */
1967 if (state->EN_RSSI) {
1968 status += MXL_ControlWrite(fe, SEQ_EXTSYNTHCALIF, 1);
1969 status += MXL_ControlWrite(fe, SEQ_EXTDCCAL, 1);
1970 status += MXL_ControlWrite(fe, AGC_EN_RSSI, 1);
1971 status += MXL_ControlWrite(fe, RFA_ENCLKRFAGC, 1);
1972
1973 /* RSSI reference point */
1974 status += MXL_ControlWrite(fe, RFA_RSSI_REF, 2);
1975 status += MXL_ControlWrite(fe, RFA_RSSI_REFH, 3);
1976 status += MXL_ControlWrite(fe, RFA_RSSI_REFL, 1);
1977
1978 /* TOP point */
1979 status += MXL_ControlWrite(fe, RFA_FLR, 0);
1980 status += MXL_ControlWrite(fe, RFA_CEIL, 12);
1981 }
1982
1983 /* Modulation type bit settings
1984 * Override the control values preset
1985 */
1986 if (state->Mod_Type == MXL_DVBT) /* DVB-T Mode */ {
1987 state->AGC_Mode = 1; /* Single AGC Mode */
1988
1989 /* Enable RSSI */
1990 status += MXL_ControlWrite(fe, SEQ_EXTSYNTHCALIF, 1);
1991 status += MXL_ControlWrite(fe, SEQ_EXTDCCAL, 1);
1992 status += MXL_ControlWrite(fe, AGC_EN_RSSI, 1);
1993 status += MXL_ControlWrite(fe, RFA_ENCLKRFAGC, 1);
1994
1995 /* RSSI reference point */
1996 status += MXL_ControlWrite(fe, RFA_RSSI_REF, 3);
1997 status += MXL_ControlWrite(fe, RFA_RSSI_REFH, 5);
1998 status += MXL_ControlWrite(fe, RFA_RSSI_REFL, 1);
1999
2000 /* TOP point */
2001 status += MXL_ControlWrite(fe, RFA_FLR, 2);
2002 status += MXL_ControlWrite(fe, RFA_CEIL, 13);
2003 if (state->IF_OUT <= 6280000UL) /* Low IF */
2004 status += MXL_ControlWrite(fe, BB_IQSWAP, 0);
2005 else /* High IF */
2006 status += MXL_ControlWrite(fe, BB_IQSWAP, 1);
2007
2008 }
2009 if (state->Mod_Type == MXL_ATSC) /* ATSC Mode */ {
2010 state->AGC_Mode = 1; /* Single AGC Mode */
2011
2012 /* Enable RSSI */
2013 status += MXL_ControlWrite(fe, SEQ_EXTSYNTHCALIF, 1);
2014 status += MXL_ControlWrite(fe, SEQ_EXTDCCAL, 1);
2015 status += MXL_ControlWrite(fe, AGC_EN_RSSI, 1);
2016 status += MXL_ControlWrite(fe, RFA_ENCLKRFAGC, 1);
2017
2018 /* RSSI reference point */
2019 status += MXL_ControlWrite(fe, RFA_RSSI_REF, 2);
2020 status += MXL_ControlWrite(fe, RFA_RSSI_REFH, 4);
2021 status += MXL_ControlWrite(fe, RFA_RSSI_REFL, 1);
2022
2023 /* TOP point */
2024 status += MXL_ControlWrite(fe, RFA_FLR, 2);
2025 status += MXL_ControlWrite(fe, RFA_CEIL, 13);
2026 status += MXL_ControlWrite(fe, BB_INITSTATE_DLPF_TUNE, 1);
2027 /* Low Zero */
2028 status += MXL_ControlWrite(fe, RFSYN_CHP_GAIN, 5);
2029
2030 if (state->IF_OUT <= 6280000UL) /* Low IF */
2031 status += MXL_ControlWrite(fe, BB_IQSWAP, 0);
2032 else /* High IF */
2033 status += MXL_ControlWrite(fe, BB_IQSWAP, 1);
2034 }
2035 if (state->Mod_Type == MXL_QAM) /* QAM Mode */ {
2036 state->Mode = MXL_DIGITAL_MODE;
2037
2038 /* state->AGC_Mode = 1; */ /* Single AGC Mode */
2039
2040 /* Disable RSSI */ /* change here for v2.6.5 */
2041 status += MXL_ControlWrite(fe, SEQ_EXTSYNTHCALIF, 1);
2042 status += MXL_ControlWrite(fe, SEQ_EXTDCCAL, 1);
2043 status += MXL_ControlWrite(fe, AGC_EN_RSSI, 0);
2044 status += MXL_ControlWrite(fe, RFA_ENCLKRFAGC, 1);
2045
2046 /* RSSI reference point */
2047 status += MXL_ControlWrite(fe, RFA_RSSI_REFH, 5);
2048 status += MXL_ControlWrite(fe, RFA_RSSI_REF, 3);
2049 status += MXL_ControlWrite(fe, RFA_RSSI_REFL, 2);
2050 /* change here for v2.6.5 */
2051 status += MXL_ControlWrite(fe, RFSYN_CHP_GAIN, 3);
2052
2053 if (state->IF_OUT <= 6280000UL) /* Low IF */
2054 status += MXL_ControlWrite(fe, BB_IQSWAP, 0);
2055 else /* High IF */
2056 status += MXL_ControlWrite(fe, BB_IQSWAP, 1);
2057 status += MXL_ControlWrite(fe, RFSYN_CHP_GAIN, 2);
2058
2059 }
2060 if (state->Mod_Type == MXL_ANALOG_CABLE) {
2061 /* Analog Cable Mode */
2062 /* state->Mode = MXL_DIGITAL_MODE; */
2063
2064 state->AGC_Mode = 1; /* Single AGC Mode */
2065
2066 /* Disable RSSI */
2067 status += MXL_ControlWrite(fe, SEQ_EXTSYNTHCALIF, 1);
2068 status += MXL_ControlWrite(fe, SEQ_EXTDCCAL, 1);
2069 status += MXL_ControlWrite(fe, AGC_EN_RSSI, 0);
2070 status += MXL_ControlWrite(fe, RFA_ENCLKRFAGC, 1);
2071 /* change for 2.6.3 */
2072 status += MXL_ControlWrite(fe, AGC_IF, 1);
2073 status += MXL_ControlWrite(fe, AGC_RF, 15);
2074 status += MXL_ControlWrite(fe, BB_IQSWAP, 1);
2075 }
2076
2077 if (state->Mod_Type == MXL_ANALOG_OTA) {
2078 /* Analog OTA Terrestrial mode add for 2.6.7 */
2079 /* state->Mode = MXL_ANALOG_MODE; */
2080
2081 /* Enable RSSI */
2082 status += MXL_ControlWrite(fe, SEQ_EXTSYNTHCALIF, 1);
2083 status += MXL_ControlWrite(fe, SEQ_EXTDCCAL, 1);
2084 status += MXL_ControlWrite(fe, AGC_EN_RSSI, 1);
2085 status += MXL_ControlWrite(fe, RFA_ENCLKRFAGC, 1);
2086
2087 /* RSSI reference point */
2088 status += MXL_ControlWrite(fe, RFA_RSSI_REFH, 5);
2089 status += MXL_ControlWrite(fe, RFA_RSSI_REF, 3);
2090 status += MXL_ControlWrite(fe, RFA_RSSI_REFL, 2);
2091 status += MXL_ControlWrite(fe, RFSYN_CHP_GAIN, 3);
2092 status += MXL_ControlWrite(fe, BB_IQSWAP, 1);
2093 }
2094
2095 /* RSSI disable */
2096 if (state->EN_RSSI == 0) {
2097 status += MXL_ControlWrite(fe, SEQ_EXTSYNTHCALIF, 1);
2098 status += MXL_ControlWrite(fe, SEQ_EXTDCCAL, 1);
2099 status += MXL_ControlWrite(fe, AGC_EN_RSSI, 0);
2100 status += MXL_ControlWrite(fe, RFA_ENCLKRFAGC, 1);
2101 }
2102
2103 return status;
2104}
2105
2106static u16 MXL_IFSynthInit(struct dvb_frontend *fe)
2107{
2108 struct mxl5005s_state *state = fe->tuner_priv;
2109 u16 status = 0 ;
2110 u32 Fref = 0 ;
2111 u32 Kdbl, intModVal ;
2112 u32 fracModVal ;
2113 Kdbl = 2 ;
2114
2115 if (state->Fxtal >= 12000000UL && state->Fxtal <= 16000000UL)
2116 Kdbl = 2 ;
2117 if (state->Fxtal > 16000000UL && state->Fxtal <= 32000000UL)
2118 Kdbl = 1 ;
2119
2120 /* IF Synthesizer Control */
2121 if (state->Mode == 0 && state->IF_Mode == 1) /* Analog Low IF mode */ {
2122 if (state->IF_LO == 41000000UL) {
2123 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x08);
2124 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x0C);
2125 Fref = 328000000UL ;
2126 }
2127 if (state->IF_LO == 47000000UL) {
2128 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x08);
2129 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x08);
2130 Fref = 376000000UL ;
2131 }
2132 if (state->IF_LO == 54000000UL) {
2133 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x10);
2134 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x0C);
2135 Fref = 324000000UL ;
2136 }
2137 if (state->IF_LO == 60000000UL) {
2138 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x10);
2139 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x08);
2140 Fref = 360000000UL ;
2141 }
2142 if (state->IF_LO == 39250000UL) {
2143 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x08);
2144 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x0C);
2145 Fref = 314000000UL ;
2146 }
2147 if (state->IF_LO == 39650000UL) {
2148 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x08);
2149 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x0C);
2150 Fref = 317200000UL ;
2151 }
2152 if (state->IF_LO == 40150000UL) {
2153 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x08);
2154 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x0C);
2155 Fref = 321200000UL ;
2156 }
2157 if (state->IF_LO == 40650000UL) {
2158 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x08);
2159 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x0C);
2160 Fref = 325200000UL ;
2161 }
2162 }
2163
2164 if (state->Mode || (state->Mode == 0 && state->IF_Mode == 0)) {
2165 if (state->IF_LO == 57000000UL) {
2166 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x10);
2167 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x08);
2168 Fref = 342000000UL ;
2169 }
2170 if (state->IF_LO == 44000000UL) {
2171 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x08);
2172 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x08);
2173 Fref = 352000000UL ;
2174 }
2175 if (state->IF_LO == 43750000UL) {
2176 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x08);
2177 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x08);
2178 Fref = 350000000UL ;
2179 }
2180 if (state->IF_LO == 36650000UL) {
2181 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x04);
2182 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x08);
2183 Fref = 366500000UL ;
2184 }
2185 if (state->IF_LO == 36150000UL) {
2186 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x04);
2187 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x08);
2188 Fref = 361500000UL ;
2189 }
2190 if (state->IF_LO == 36000000UL) {
2191 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x04);
2192 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x08);
2193 Fref = 360000000UL ;
2194 }
2195 if (state->IF_LO == 35250000UL) {
2196 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x04);
2197 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x08);
2198 Fref = 352500000UL ;
2199 }
2200 if (state->IF_LO == 34750000UL) {
2201 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x04);
2202 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x08);
2203 Fref = 347500000UL ;
2204 }
2205 if (state->IF_LO == 6280000UL) {
2206 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x07);
2207 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x08);
2208 Fref = 376800000UL ;
2209 }
2210 if (state->IF_LO == 5000000UL) {
2211 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x09);
2212 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x08);
2213 Fref = 360000000UL ;
2214 }
2215 if (state->IF_LO == 4500000UL) {
2216 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x06);
2217 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x08);
2218 Fref = 360000000UL ;
2219 }
2220 if (state->IF_LO == 4570000UL) {
2221 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x06);
2222 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x08);
2223 Fref = 365600000UL ;
2224 }
2225 if (state->IF_LO == 4000000UL) {
2226 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x05);
2227 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x08);
2228 Fref = 360000000UL ;
2229 }
2230 if (state->IF_LO == 57400000UL) {
2231 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x10);
2232 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x08);
2233 Fref = 344400000UL ;
2234 }
2235 if (state->IF_LO == 44400000UL) {
2236 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x08);
2237 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x08);
2238 Fref = 355200000UL ;
2239 }
2240 if (state->IF_LO == 44150000UL) {
2241 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x08);
2242 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x08);
2243 Fref = 353200000UL ;
2244 }
2245 if (state->IF_LO == 37050000UL) {
2246 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x04);
2247 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x08);
2248 Fref = 370500000UL ;
2249 }
2250 if (state->IF_LO == 36550000UL) {
2251 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x04);
2252 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x08);
2253 Fref = 365500000UL ;
2254 }
2255 if (state->IF_LO == 36125000UL) {
2256 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x04);
2257 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x08);
2258 Fref = 361250000UL ;
2259 }
2260 if (state->IF_LO == 6000000UL) {
2261 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x07);
2262 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x08);
2263 Fref = 360000000UL ;
2264 }
2265 if (state->IF_LO == 5400000UL) {
2266 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x07);
2267 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x0C);
2268 Fref = 324000000UL ;
2269 }
2270 if (state->IF_LO == 5380000UL) {
2271 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x07);
2272 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x0C);
2273 Fref = 322800000UL ;
2274 }
2275 if (state->IF_LO == 5200000UL) {
2276 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x09);
2277 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x08);
2278 Fref = 374400000UL ;
2279 }
2280 if (state->IF_LO == 4900000UL) {
2281 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x09);
2282 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x08);
2283 Fref = 352800000UL ;
2284 }
2285 if (state->IF_LO == 4400000UL) {
2286 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x06);
2287 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x08);
2288 Fref = 352000000UL ;
2289 }
2290 if (state->IF_LO == 4063000UL) /* add for 2.6.8 */ {
2291 status += MXL_ControlWrite(fe, IF_DIVVAL, 0x05);
2292 status += MXL_ControlWrite(fe, IF_VCO_BIAS, 0x08);
2293 Fref = 365670000UL ;
2294 }
2295 }
2296 /* CHCAL_INT_MOD_IF */
2297 /* CHCAL_FRAC_MOD_IF */
2298 intModVal = Fref / (state->Fxtal * Kdbl/2);
2299 status += MXL_ControlWrite(fe, CHCAL_INT_MOD_IF, intModVal);
2300
2301 fracModVal = (2<<15)*(Fref/1000 - (state->Fxtal/1000 * Kdbl/2) *
2302 intModVal);
2303
2304 fracModVal = fracModVal / ((state->Fxtal * Kdbl/2)/1000);
2305 status += MXL_ControlWrite(fe, CHCAL_FRAC_MOD_IF, fracModVal);
2306
2307 return status ;
2308}
2309
2310static u32 MXL_GetXtalInt(u32 Xtal_Freq)
2311{
2312 if ((Xtal_Freq % 1000000) == 0)
2313 return (Xtal_Freq / 10000);
2314 else
2315 return (((Xtal_Freq / 1000000) + 1)*100);
2316}
2317
2318static u16 MXL_TuneRF(struct dvb_frontend *fe, u32 RF_Freq)
2319{
2320 struct mxl5005s_state *state = fe->tuner_priv;
2321 u16 status = 0;
2322 u32 divider_val, E3, E4, E5, E5A;
2323 u32 Fmax, Fmin, FmaxBin, FminBin;
2324 u32 Kdbl_RF = 2;
2325 u32 tg_divval;
2326 u32 tg_lo;
2327 u32 Xtal_Int;
2328
2329 u32 Fref_TG;
2330 u32 Fvco;
2331
2332 Xtal_Int = MXL_GetXtalInt(state->Fxtal);
2333
2334 state->RF_IN = RF_Freq;
2335
2336 MXL_SynthRFTGLO_Calc(fe);
2337
2338 if (state->Fxtal >= 12000000UL && state->Fxtal <= 22000000UL)
2339 Kdbl_RF = 2;
2340 if (state->Fxtal > 22000000 && state->Fxtal <= 32000000)
2341 Kdbl_RF = 1;
2342
2343 /* Downconverter Controls
2344 * Look-Up Table Implementation for:
2345 * DN_POLY
2346 * DN_RFGAIN
2347 * DN_CAP_RFLPF
2348 * DN_EN_VHFUHFBAR
2349 * DN_GAIN_ADJUST
2350 * Change the boundary reference from RF_IN to RF_LO
2351 */
2352 if (state->RF_LO < 40000000UL)
2353 return -1;
2354
2355 if (state->RF_LO >= 40000000UL && state->RF_LO <= 75000000UL) {
2356 status += MXL_ControlWrite(fe, DN_POLY, 2);
2357 status += MXL_ControlWrite(fe, DN_RFGAIN, 3);
2358 status += MXL_ControlWrite(fe, DN_CAP_RFLPF, 423);
2359 status += MXL_ControlWrite(fe, DN_EN_VHFUHFBAR, 1);
2360 status += MXL_ControlWrite(fe, DN_GAIN_ADJUST, 1);
2361 }
2362 if (state->RF_LO > 75000000UL && state->RF_LO <= 100000000UL) {
2363 status += MXL_ControlWrite(fe, DN_POLY, 3);
2364 status += MXL_ControlWrite(fe, DN_RFGAIN, 3);
2365 status += MXL_ControlWrite(fe, DN_CAP_RFLPF, 222);
2366 status += MXL_ControlWrite(fe, DN_EN_VHFUHFBAR, 1);
2367 status += MXL_ControlWrite(fe, DN_GAIN_ADJUST, 1);
2368 }
2369 if (state->RF_LO > 100000000UL && state->RF_LO <= 150000000UL) {
2370 status += MXL_ControlWrite(fe, DN_POLY, 3);
2371 status += MXL_ControlWrite(fe, DN_RFGAIN, 3);
2372 status += MXL_ControlWrite(fe, DN_CAP_RFLPF, 147);
2373 status += MXL_ControlWrite(fe, DN_EN_VHFUHFBAR, 1);
2374 status += MXL_ControlWrite(fe, DN_GAIN_ADJUST, 2);
2375 }
2376 if (state->RF_LO > 150000000UL && state->RF_LO <= 200000000UL) {
2377 status += MXL_ControlWrite(fe, DN_POLY, 3);
2378 status += MXL_ControlWrite(fe, DN_RFGAIN, 3);
2379 status += MXL_ControlWrite(fe, DN_CAP_RFLPF, 9);
2380 status += MXL_ControlWrite(fe, DN_EN_VHFUHFBAR, 1);
2381 status += MXL_ControlWrite(fe, DN_GAIN_ADJUST, 2);
2382 }
2383 if (state->RF_LO > 200000000UL && state->RF_LO <= 300000000UL) {
2384 status += MXL_ControlWrite(fe, DN_POLY, 3);
2385 status += MXL_ControlWrite(fe, DN_RFGAIN, 3);
2386 status += MXL_ControlWrite(fe, DN_CAP_RFLPF, 0);
2387 status += MXL_ControlWrite(fe, DN_EN_VHFUHFBAR, 1);
2388 status += MXL_ControlWrite(fe, DN_GAIN_ADJUST, 3);
2389 }
2390 if (state->RF_LO > 300000000UL && state->RF_LO <= 650000000UL) {
2391 status += MXL_ControlWrite(fe, DN_POLY, 3);
2392 status += MXL_ControlWrite(fe, DN_RFGAIN, 1);
2393 status += MXL_ControlWrite(fe, DN_CAP_RFLPF, 0);
2394 status += MXL_ControlWrite(fe, DN_EN_VHFUHFBAR, 0);
2395 status += MXL_ControlWrite(fe, DN_GAIN_ADJUST, 3);
2396 }
2397 if (state->RF_LO > 650000000UL && state->RF_LO <= 900000000UL) {
2398 status += MXL_ControlWrite(fe, DN_POLY, 3);
2399 status += MXL_ControlWrite(fe, DN_RFGAIN, 2);
2400 status += MXL_ControlWrite(fe, DN_CAP_RFLPF, 0);
2401 status += MXL_ControlWrite(fe, DN_EN_VHFUHFBAR, 0);
2402 status += MXL_ControlWrite(fe, DN_GAIN_ADJUST, 3);
2403 }
2404 if (state->RF_LO > 900000000UL)
2405 return -1;
2406
2407 /* DN_IQTNBUF_AMP */
2408 /* DN_IQTNGNBFBIAS_BST */
2409 if (state->RF_LO >= 40000000UL && state->RF_LO <= 75000000UL) {
2410 status += MXL_ControlWrite(fe, DN_IQTNBUF_AMP, 1);
2411 status += MXL_ControlWrite(fe, DN_IQTNGNBFBIAS_BST, 0);
2412 }
2413 if (state->RF_LO > 75000000UL && state->RF_LO <= 100000000UL) {
2414 status += MXL_ControlWrite(fe, DN_IQTNBUF_AMP, 1);
2415 status += MXL_ControlWrite(fe, DN_IQTNGNBFBIAS_BST, 0);
2416 }
2417 if (state->RF_LO > 100000000UL && state->RF_LO <= 150000000UL) {
2418 status += MXL_ControlWrite(fe, DN_IQTNBUF_AMP, 1);
2419 status += MXL_ControlWrite(fe, DN_IQTNGNBFBIAS_BST, 0);
2420 }
2421 if (state->RF_LO > 150000000UL && state->RF_LO <= 200000000UL) {
2422 status += MXL_ControlWrite(fe, DN_IQTNBUF_AMP, 1);
2423 status += MXL_ControlWrite(fe, DN_IQTNGNBFBIAS_BST, 0);
2424 }
2425 if (state->RF_LO > 200000000UL && state->RF_LO <= 300000000UL) {
2426 status += MXL_ControlWrite(fe, DN_IQTNBUF_AMP, 1);
2427 status += MXL_ControlWrite(fe, DN_IQTNGNBFBIAS_BST, 0);
2428 }
2429 if (state->RF_LO > 300000000UL && state->RF_LO <= 400000000UL) {
2430 status += MXL_ControlWrite(fe, DN_IQTNBUF_AMP, 1);
2431 status += MXL_ControlWrite(fe, DN_IQTNGNBFBIAS_BST, 0);
2432 }
2433 if (state->RF_LO > 400000000UL && state->RF_LO <= 450000000UL) {
2434 status += MXL_ControlWrite(fe, DN_IQTNBUF_AMP, 1);
2435 status += MXL_ControlWrite(fe, DN_IQTNGNBFBIAS_BST, 0);
2436 }
2437 if (state->RF_LO > 450000000UL && state->RF_LO <= 500000000UL) {
2438 status += MXL_ControlWrite(fe, DN_IQTNBUF_AMP, 1);
2439 status += MXL_ControlWrite(fe, DN_IQTNGNBFBIAS_BST, 0);
2440 }
2441 if (state->RF_LO > 500000000UL && state->RF_LO <= 550000000UL) {
2442 status += MXL_ControlWrite(fe, DN_IQTNBUF_AMP, 1);
2443 status += MXL_ControlWrite(fe, DN_IQTNGNBFBIAS_BST, 0);
2444 }
2445 if (state->RF_LO > 550000000UL && state->RF_LO <= 600000000UL) {
2446 status += MXL_ControlWrite(fe, DN_IQTNBUF_AMP, 1);
2447 status += MXL_ControlWrite(fe, DN_IQTNGNBFBIAS_BST, 0);
2448 }
2449 if (state->RF_LO > 600000000UL && state->RF_LO <= 650000000UL) {
2450 status += MXL_ControlWrite(fe, DN_IQTNBUF_AMP, 1);
2451 status += MXL_ControlWrite(fe, DN_IQTNGNBFBIAS_BST, 0);
2452 }
2453 if (state->RF_LO > 650000000UL && state->RF_LO <= 700000000UL) {
2454 status += MXL_ControlWrite(fe, DN_IQTNBUF_AMP, 1);
2455 status += MXL_ControlWrite(fe, DN_IQTNGNBFBIAS_BST, 0);
2456 }
2457 if (state->RF_LO > 700000000UL && state->RF_LO <= 750000000UL) {
2458 status += MXL_ControlWrite(fe, DN_IQTNBUF_AMP, 1);
2459 status += MXL_ControlWrite(fe, DN_IQTNGNBFBIAS_BST, 0);
2460 }
2461 if (state->RF_LO > 750000000UL && state->RF_LO <= 800000000UL) {
2462 status += MXL_ControlWrite(fe, DN_IQTNBUF_AMP, 1);
2463 status += MXL_ControlWrite(fe, DN_IQTNGNBFBIAS_BST, 0);
2464 }
2465 if (state->RF_LO > 800000000UL && state->RF_LO <= 850000000UL) {
2466 status += MXL_ControlWrite(fe, DN_IQTNBUF_AMP, 10);
2467 status += MXL_ControlWrite(fe, DN_IQTNGNBFBIAS_BST, 1);
2468 }
2469 if (state->RF_LO > 850000000UL && state->RF_LO <= 900000000UL) {
2470 status += MXL_ControlWrite(fe, DN_IQTNBUF_AMP, 10);
2471 status += MXL_ControlWrite(fe, DN_IQTNGNBFBIAS_BST, 1);
2472 }
2473
2474 /*
2475 * Set RF Synth and LO Path Control
2476 *
2477 * Look-Up table implementation for:
2478 * RFSYN_EN_OUTMUX
2479 * RFSYN_SEL_VCO_OUT
2480 * RFSYN_SEL_VCO_HI
2481 * RFSYN_SEL_DIVM
2482 * RFSYN_RF_DIV_BIAS
2483 * DN_SEL_FREQ
2484 *
2485 * Set divider_val, Fmax, Fmix to use in Equations
2486 */
2487 FminBin = 28000000UL ;
2488 FmaxBin = 42500000UL ;
2489 if (state->RF_LO >= 40000000UL && state->RF_LO <= FmaxBin) {
2490 status += MXL_ControlWrite(fe, RFSYN_EN_OUTMUX, 1);
2491 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_OUT, 0);
2492 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_HI, 0);
2493 status += MXL_ControlWrite(fe, RFSYN_SEL_DIVM, 0);
2494 status += MXL_ControlWrite(fe, RFSYN_RF_DIV_BIAS, 1);
2495 status += MXL_ControlWrite(fe, DN_SEL_FREQ, 1);
2496 divider_val = 64 ;
2497 Fmax = FmaxBin ;
2498 Fmin = FminBin ;
2499 }
2500 FminBin = 42500000UL ;
2501 FmaxBin = 56000000UL ;
2502 if (state->RF_LO > FminBin && state->RF_LO <= FmaxBin) {
2503 status += MXL_ControlWrite(fe, RFSYN_EN_OUTMUX, 1);
2504 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_OUT, 0);
2505 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_HI, 1);
2506 status += MXL_ControlWrite(fe, RFSYN_SEL_DIVM, 0);
2507 status += MXL_ControlWrite(fe, RFSYN_RF_DIV_BIAS, 1);
2508 status += MXL_ControlWrite(fe, DN_SEL_FREQ, 1);
2509 divider_val = 64 ;
2510 Fmax = FmaxBin ;
2511 Fmin = FminBin ;
2512 }
2513 FminBin = 56000000UL ;
2514 FmaxBin = 85000000UL ;
2515 if (state->RF_LO > FminBin && state->RF_LO <= FmaxBin) {
2516 status += MXL_ControlWrite(fe, RFSYN_EN_OUTMUX, 0);
2517 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_OUT, 1);
2518 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_HI, 0);
2519 status += MXL_ControlWrite(fe, RFSYN_SEL_DIVM, 0);
2520 status += MXL_ControlWrite(fe, RFSYN_RF_DIV_BIAS, 1);
2521 status += MXL_ControlWrite(fe, DN_SEL_FREQ, 1);
2522 divider_val = 32 ;
2523 Fmax = FmaxBin ;
2524 Fmin = FminBin ;
2525 }
2526 FminBin = 85000000UL ;
2527 FmaxBin = 112000000UL ;
2528 if (state->RF_LO > FminBin && state->RF_LO <= FmaxBin) {
2529 status += MXL_ControlWrite(fe, RFSYN_EN_OUTMUX, 0);
2530 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_OUT, 1);
2531 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_HI, 1);
2532 status += MXL_ControlWrite(fe, RFSYN_SEL_DIVM, 0);
2533 status += MXL_ControlWrite(fe, RFSYN_RF_DIV_BIAS, 1);
2534 status += MXL_ControlWrite(fe, DN_SEL_FREQ, 1);
2535 divider_val = 32 ;
2536 Fmax = FmaxBin ;
2537 Fmin = FminBin ;
2538 }
2539 FminBin = 112000000UL ;
2540 FmaxBin = 170000000UL ;
2541 if (state->RF_LO > FminBin && state->RF_LO <= FmaxBin) {
2542 status += MXL_ControlWrite(fe, RFSYN_EN_OUTMUX, 0);
2543 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_OUT, 1);
2544 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_HI, 0);
2545 status += MXL_ControlWrite(fe, RFSYN_SEL_DIVM, 0);
2546 status += MXL_ControlWrite(fe, RFSYN_RF_DIV_BIAS, 1);
2547 status += MXL_ControlWrite(fe, DN_SEL_FREQ, 2);
2548 divider_val = 16 ;
2549 Fmax = FmaxBin ;
2550 Fmin = FminBin ;
2551 }
2552 FminBin = 170000000UL ;
2553 FmaxBin = 225000000UL ;
2554 if (state->RF_LO > FminBin && state->RF_LO <= FmaxBin) {
2555 status += MXL_ControlWrite(fe, RFSYN_EN_OUTMUX, 0);
2556 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_OUT, 1);
2557 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_HI, 1);
2558 status += MXL_ControlWrite(fe, RFSYN_SEL_DIVM, 0);
2559 status += MXL_ControlWrite(fe, RFSYN_RF_DIV_BIAS, 1);
2560 status += MXL_ControlWrite(fe, DN_SEL_FREQ, 2);
2561 divider_val = 16 ;
2562 Fmax = FmaxBin ;
2563 Fmin = FminBin ;
2564 }
2565 FminBin = 225000000UL ;
2566 FmaxBin = 300000000UL ;
2567 if (state->RF_LO > FminBin && state->RF_LO <= FmaxBin) {
2568 status += MXL_ControlWrite(fe, RFSYN_EN_OUTMUX, 0);
2569 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_OUT, 1);
2570 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_HI, 0);
2571 status += MXL_ControlWrite(fe, RFSYN_SEL_DIVM, 0);
2572 status += MXL_ControlWrite(fe, RFSYN_RF_DIV_BIAS, 1);
2573 status += MXL_ControlWrite(fe, DN_SEL_FREQ, 4);
2574 divider_val = 8 ;
2575 Fmax = 340000000UL ;
2576 Fmin = FminBin ;
2577 }
2578 FminBin = 300000000UL ;
2579 FmaxBin = 340000000UL ;
2580 if (state->RF_LO > FminBin && state->RF_LO <= FmaxBin) {
2581 status += MXL_ControlWrite(fe, RFSYN_EN_OUTMUX, 1);
2582 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_OUT, 0);
2583 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_HI, 0);
2584 status += MXL_ControlWrite(fe, RFSYN_SEL_DIVM, 0);
2585 status += MXL_ControlWrite(fe, RFSYN_RF_DIV_BIAS, 1);
2586 status += MXL_ControlWrite(fe, DN_SEL_FREQ, 0);
2587 divider_val = 8 ;
2588 Fmax = FmaxBin ;
2589 Fmin = 225000000UL ;
2590 }
2591 FminBin = 340000000UL ;
2592 FmaxBin = 450000000UL ;
2593 if (state->RF_LO > FminBin && state->RF_LO <= FmaxBin) {
2594 status += MXL_ControlWrite(fe, RFSYN_EN_OUTMUX, 1);
2595 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_OUT, 0);
2596 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_HI, 1);
2597 status += MXL_ControlWrite(fe, RFSYN_SEL_DIVM, 0);
2598 status += MXL_ControlWrite(fe, RFSYN_RF_DIV_BIAS, 2);
2599 status += MXL_ControlWrite(fe, DN_SEL_FREQ, 0);
2600 divider_val = 8 ;
2601 Fmax = FmaxBin ;
2602 Fmin = FminBin ;
2603 }
2604 FminBin = 450000000UL ;
2605 FmaxBin = 680000000UL ;
2606 if (state->RF_LO > FminBin && state->RF_LO <= FmaxBin) {
2607 status += MXL_ControlWrite(fe, RFSYN_EN_OUTMUX, 0);
2608 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_OUT, 1);
2609 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_HI, 0);
2610 status += MXL_ControlWrite(fe, RFSYN_SEL_DIVM, 1);
2611 status += MXL_ControlWrite(fe, RFSYN_RF_DIV_BIAS, 1);
2612 status += MXL_ControlWrite(fe, DN_SEL_FREQ, 0);
2613 divider_val = 4 ;
2614 Fmax = FmaxBin ;
2615 Fmin = FminBin ;
2616 }
2617 FminBin = 680000000UL ;
2618 FmaxBin = 900000000UL ;
2619 if (state->RF_LO > FminBin && state->RF_LO <= FmaxBin) {
2620 status += MXL_ControlWrite(fe, RFSYN_EN_OUTMUX, 0);
2621 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_OUT, 1);
2622 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_HI, 1);
2623 status += MXL_ControlWrite(fe, RFSYN_SEL_DIVM, 1);
2624 status += MXL_ControlWrite(fe, RFSYN_RF_DIV_BIAS, 1);
2625 status += MXL_ControlWrite(fe, DN_SEL_FREQ, 0);
2626 divider_val = 4 ;
2627 Fmax = FmaxBin ;
2628 Fmin = FminBin ;
2629 }
2630
2631 /* CHCAL_INT_MOD_RF
2632 * CHCAL_FRAC_MOD_RF
2633 * RFSYN_LPF_R
2634 * CHCAL_EN_INT_RF
2635 */
2636 /* Equation E3 RFSYN_VCO_BIAS */
2637 E3 = (((Fmax-state->RF_LO)/1000)*32)/((Fmax-Fmin)/1000) + 8 ;
2638 status += MXL_ControlWrite(fe, RFSYN_VCO_BIAS, E3);
2639
2640 /* Equation E4 CHCAL_INT_MOD_RF */
2641 E4 = (state->RF_LO*divider_val/1000)/(2*state->Fxtal*Kdbl_RF/1000);
2642 MXL_ControlWrite(fe, CHCAL_INT_MOD_RF, E4);
2643
2644 /* Equation E5 CHCAL_FRAC_MOD_RF CHCAL_EN_INT_RF */
2645 E5 = ((2<<17)*(state->RF_LO/10000*divider_val -
2646 (E4*(2*state->Fxtal*Kdbl_RF)/10000))) /
2647 (2*state->Fxtal*Kdbl_RF/10000);
2648
2649 status += MXL_ControlWrite(fe, CHCAL_FRAC_MOD_RF, E5);
2650
2651 /* Equation E5A RFSYN_LPF_R */
2652 E5A = (((Fmax - state->RF_LO)/1000)*4/((Fmax-Fmin)/1000)) + 1 ;
2653 status += MXL_ControlWrite(fe, RFSYN_LPF_R, E5A);
2654
2655 /* Euqation E5B CHCAL_EN_INIT_RF */
2656 status += MXL_ControlWrite(fe, CHCAL_EN_INT_RF, ((E5 == 0) ? 1 : 0));
2657 /*if (E5 == 0)
2658 * status += MXL_ControlWrite(fe, CHCAL_EN_INT_RF, 1);
2659 *else
2660 * status += MXL_ControlWrite(fe, CHCAL_FRAC_MOD_RF, E5);
2661 */
2662
2663 /*
2664 * Set TG Synth
2665 *
2666 * Look-Up table implementation for:
2667 * TG_LO_DIVVAL
2668 * TG_LO_SELVAL
2669 *
2670 * Set divider_val, Fmax, Fmix to use in Equations
2671 */
2672 if (state->TG_LO < 33000000UL)
2673 return -1;
2674
2675 FminBin = 33000000UL ;
2676 FmaxBin = 50000000UL ;
2677 if (state->TG_LO >= FminBin && state->TG_LO <= FmaxBin) {
2678 status += MXL_ControlWrite(fe, TG_LO_DIVVAL, 0x6);
2679 status += MXL_ControlWrite(fe, TG_LO_SELVAL, 0x0);
2680 divider_val = 36 ;
2681 Fmax = FmaxBin ;
2682 Fmin = FminBin ;
2683 }
2684 FminBin = 50000000UL ;
2685 FmaxBin = 67000000UL ;
2686 if (state->TG_LO > FminBin && state->TG_LO <= FmaxBin) {
2687 status += MXL_ControlWrite(fe, TG_LO_DIVVAL, 0x1);
2688 status += MXL_ControlWrite(fe, TG_LO_SELVAL, 0x0);
2689 divider_val = 24 ;
2690 Fmax = FmaxBin ;
2691 Fmin = FminBin ;
2692 }
2693 FminBin = 67000000UL ;
2694 FmaxBin = 100000000UL ;
2695 if (state->TG_LO > FminBin && state->TG_LO <= FmaxBin) {
2696 status += MXL_ControlWrite(fe, TG_LO_DIVVAL, 0xC);
2697 status += MXL_ControlWrite(fe, TG_LO_SELVAL, 0x2);
2698 divider_val = 18 ;
2699 Fmax = FmaxBin ;
2700 Fmin = FminBin ;
2701 }
2702 FminBin = 100000000UL ;
2703 FmaxBin = 150000000UL ;
2704 if (state->TG_LO > FminBin && state->TG_LO <= FmaxBin) {
2705 status += MXL_ControlWrite(fe, TG_LO_DIVVAL, 0x8);
2706 status += MXL_ControlWrite(fe, TG_LO_SELVAL, 0x2);
2707 divider_val = 12 ;
2708 Fmax = FmaxBin ;
2709 Fmin = FminBin ;
2710 }
2711 FminBin = 150000000UL ;
2712 FmaxBin = 200000000UL ;
2713 if (state->TG_LO > FminBin && state->TG_LO <= FmaxBin) {
2714 status += MXL_ControlWrite(fe, TG_LO_DIVVAL, 0x0);
2715 status += MXL_ControlWrite(fe, TG_LO_SELVAL, 0x2);
2716 divider_val = 8 ;
2717 Fmax = FmaxBin ;
2718 Fmin = FminBin ;
2719 }
2720 FminBin = 200000000UL ;
2721 FmaxBin = 300000000UL ;
2722 if (state->TG_LO > FminBin && state->TG_LO <= FmaxBin) {
2723 status += MXL_ControlWrite(fe, TG_LO_DIVVAL, 0x8);
2724 status += MXL_ControlWrite(fe, TG_LO_SELVAL, 0x3);
2725 divider_val = 6 ;
2726 Fmax = FmaxBin ;
2727 Fmin = FminBin ;
2728 }
2729 FminBin = 300000000UL ;
2730 FmaxBin = 400000000UL ;
2731 if (state->TG_LO > FminBin && state->TG_LO <= FmaxBin) {
2732 status += MXL_ControlWrite(fe, TG_LO_DIVVAL, 0x0);
2733 status += MXL_ControlWrite(fe, TG_LO_SELVAL, 0x3);
2734 divider_val = 4 ;
2735 Fmax = FmaxBin ;
2736 Fmin = FminBin ;
2737 }
2738 FminBin = 400000000UL ;
2739 FmaxBin = 600000000UL ;
2740 if (state->TG_LO > FminBin && state->TG_LO <= FmaxBin) {
2741 status += MXL_ControlWrite(fe, TG_LO_DIVVAL, 0x8);
2742 status += MXL_ControlWrite(fe, TG_LO_SELVAL, 0x7);
2743 divider_val = 3 ;
2744 Fmax = FmaxBin ;
2745 Fmin = FminBin ;
2746 }
2747 FminBin = 600000000UL ;
2748 FmaxBin = 900000000UL ;
2749 if (state->TG_LO > FminBin && state->TG_LO <= FmaxBin) {
2750 status += MXL_ControlWrite(fe, TG_LO_DIVVAL, 0x0);
2751 status += MXL_ControlWrite(fe, TG_LO_SELVAL, 0x7);
2752 divider_val = 2 ;
2753 Fmax = FmaxBin ;
2754 Fmin = FminBin ;
2755 }
2756
2757 /* TG_DIV_VAL */
2758 tg_divval = (state->TG_LO*divider_val/100000) *
2759 (MXL_Ceiling(state->Fxtal, 1000000) * 100) /
2760 (state->Fxtal/1000);
2761
2762 status += MXL_ControlWrite(fe, TG_DIV_VAL, tg_divval);
2763
2764 if (state->TG_LO > 600000000UL)
2765 status += MXL_ControlWrite(fe, TG_DIV_VAL, tg_divval + 1);
2766
2767 Fmax = 1800000000UL ;
2768 Fmin = 1200000000UL ;
2769
2770 /* prevent overflow of 32 bit unsigned integer, use
2771 * following equation. Edit for v2.6.4
2772 */
2773 /* Fref_TF = Fref_TG * 1000 */
2774 Fref_TG = (state->Fxtal/1000) / MXL_Ceiling(state->Fxtal, 1000000);
2775
2776 /* Fvco = Fvco/10 */
2777 Fvco = (state->TG_LO/10000) * divider_val * Fref_TG;
2778
2779 tg_lo = (((Fmax/10 - Fvco)/100)*32) / ((Fmax-Fmin)/1000)+8;
2780
2781 /* below equation is same as above but much harder to debug.
2782 * tg_lo = ( ((Fmax/10000 * Xtal_Int)/100) -
2783 * ((state->TG_LO/10000)*divider_val *
2784 * (state->Fxtal/10000)/100) )*32/((Fmax-Fmin)/10000 *
2785 * Xtal_Int/100) + 8;
2786 */
2787
2788 status += MXL_ControlWrite(fe, TG_VCO_BIAS , tg_lo);
2789
2790 /* add for 2.6.5 Special setting for QAM */
2791 if (state->Mod_Type == MXL_QAM) {
2792 if (state->config->qam_gain != 0)
2793 status += MXL_ControlWrite(fe, RFSYN_CHP_GAIN,
2794 state->config->qam_gain);
2795 else if (state->RF_IN < 680000000)
2796 status += MXL_ControlWrite(fe, RFSYN_CHP_GAIN, 3);
2797 else
2798 status += MXL_ControlWrite(fe, RFSYN_CHP_GAIN, 2);
2799 }
2800
2801 /* Off Chip Tracking Filter Control */
2802 if (state->TF_Type == MXL_TF_OFF) {
2803 /* Tracking Filter Off State; turn off all the banks */
2804 status += MXL_ControlWrite(fe, DAC_A_ENABLE, 0);
2805 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
2806 status += MXL_SetGPIO(fe, 3, 1); /* Bank1 Off */
2807 status += MXL_SetGPIO(fe, 1, 1); /* Bank2 Off */
2808 status += MXL_SetGPIO(fe, 4, 1); /* Bank3 Off */
2809 }
2810
2811 if (state->TF_Type == MXL_TF_C) /* Tracking Filter type C */ {
2812 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 1);
2813 status += MXL_ControlWrite(fe, DAC_DIN_A, 0);
2814
2815 if (state->RF_IN >= 43000000 && state->RF_IN < 150000000) {
2816 status += MXL_ControlWrite(fe, DAC_A_ENABLE, 0);
2817 status += MXL_ControlWrite(fe, DAC_DIN_B, 0);
2818 status += MXL_SetGPIO(fe, 3, 0);
2819 status += MXL_SetGPIO(fe, 1, 1);
2820 status += MXL_SetGPIO(fe, 4, 1);
2821 }
2822 if (state->RF_IN >= 150000000 && state->RF_IN < 280000000) {
2823 status += MXL_ControlWrite(fe, DAC_A_ENABLE, 0);
2824 status += MXL_ControlWrite(fe, DAC_DIN_B, 0);
2825 status += MXL_SetGPIO(fe, 3, 1);
2826 status += MXL_SetGPIO(fe, 1, 0);
2827 status += MXL_SetGPIO(fe, 4, 1);
2828 }
2829 if (state->RF_IN >= 280000000 && state->RF_IN < 360000000) {
2830 status += MXL_ControlWrite(fe, DAC_A_ENABLE, 0);
2831 status += MXL_ControlWrite(fe, DAC_DIN_B, 0);
2832 status += MXL_SetGPIO(fe, 3, 1);
2833 status += MXL_SetGPIO(fe, 1, 0);
2834 status += MXL_SetGPIO(fe, 4, 0);
2835 }
2836 if (state->RF_IN >= 360000000 && state->RF_IN < 560000000) {
2837 status += MXL_ControlWrite(fe, DAC_A_ENABLE, 0);
2838 status += MXL_ControlWrite(fe, DAC_DIN_B, 0);
2839 status += MXL_SetGPIO(fe, 3, 1);
2840 status += MXL_SetGPIO(fe, 1, 1);
2841 status += MXL_SetGPIO(fe, 4, 0);
2842 }
2843 if (state->RF_IN >= 560000000 && state->RF_IN < 580000000) {
2844 status += MXL_ControlWrite(fe, DAC_A_ENABLE, 1);
2845 status += MXL_ControlWrite(fe, DAC_DIN_B, 29);
2846 status += MXL_SetGPIO(fe, 3, 1);
2847 status += MXL_SetGPIO(fe, 1, 1);
2848 status += MXL_SetGPIO(fe, 4, 0);
2849 }
2850 if (state->RF_IN >= 580000000 && state->RF_IN < 630000000) {
2851 status += MXL_ControlWrite(fe, DAC_A_ENABLE, 1);
2852 status += MXL_ControlWrite(fe, DAC_DIN_B, 0);
2853 status += MXL_SetGPIO(fe, 3, 1);
2854 status += MXL_SetGPIO(fe, 1, 1);
2855 status += MXL_SetGPIO(fe, 4, 0);
2856 }
2857 if (state->RF_IN >= 630000000 && state->RF_IN < 700000000) {
2858 status += MXL_ControlWrite(fe, DAC_A_ENABLE, 1);
2859 status += MXL_ControlWrite(fe, DAC_DIN_B, 16);
2860 status += MXL_SetGPIO(fe, 3, 1);
2861 status += MXL_SetGPIO(fe, 1, 1);
2862 status += MXL_SetGPIO(fe, 4, 1);
2863 }
2864 if (state->RF_IN >= 700000000 && state->RF_IN < 760000000) {
2865 status += MXL_ControlWrite(fe, DAC_A_ENABLE, 1);
2866 status += MXL_ControlWrite(fe, DAC_DIN_B, 7);
2867 status += MXL_SetGPIO(fe, 3, 1);
2868 status += MXL_SetGPIO(fe, 1, 1);
2869 status += MXL_SetGPIO(fe, 4, 1);
2870 }
2871 if (state->RF_IN >= 760000000 && state->RF_IN <= 900000000) {
2872 status += MXL_ControlWrite(fe, DAC_A_ENABLE, 1);
2873 status += MXL_ControlWrite(fe, DAC_DIN_B, 0);
2874 status += MXL_SetGPIO(fe, 3, 1);
2875 status += MXL_SetGPIO(fe, 1, 1);
2876 status += MXL_SetGPIO(fe, 4, 1);
2877 }
2878 }
2879
2880 if (state->TF_Type == MXL_TF_C_H) {
2881
2882 /* Tracking Filter type C-H for Hauppauge only */
2883 status += MXL_ControlWrite(fe, DAC_DIN_A, 0);
2884
2885 if (state->RF_IN >= 43000000 && state->RF_IN < 150000000) {
2886 status += MXL_ControlWrite(fe, DAC_A_ENABLE, 0);
2887 status += MXL_SetGPIO(fe, 4, 0);
2888 status += MXL_SetGPIO(fe, 3, 1);
2889 status += MXL_SetGPIO(fe, 1, 1);
2890 }
2891 if (state->RF_IN >= 150000000 && state->RF_IN < 280000000) {
2892 status += MXL_ControlWrite(fe, DAC_A_ENABLE, 0);
2893 status += MXL_SetGPIO(fe, 4, 1);
2894 status += MXL_SetGPIO(fe, 3, 0);
2895 status += MXL_SetGPIO(fe, 1, 1);
2896 }
2897 if (state->RF_IN >= 280000000 && state->RF_IN < 360000000) {
2898 status += MXL_ControlWrite(fe, DAC_A_ENABLE, 0);
2899 status += MXL_SetGPIO(fe, 4, 1);
2900 status += MXL_SetGPIO(fe, 3, 0);
2901 status += MXL_SetGPIO(fe, 1, 0);
2902 }
2903 if (state->RF_IN >= 360000000 && state->RF_IN < 560000000) {
2904 status += MXL_ControlWrite(fe, DAC_A_ENABLE, 0);
2905 status += MXL_SetGPIO(fe, 4, 1);
2906 status += MXL_SetGPIO(fe, 3, 1);
2907 status += MXL_SetGPIO(fe, 1, 0);
2908 }
2909 if (state->RF_IN >= 560000000 && state->RF_IN < 580000000) {
2910 status += MXL_ControlWrite(fe, DAC_A_ENABLE, 1);
2911 status += MXL_SetGPIO(fe, 4, 1);
2912 status += MXL_SetGPIO(fe, 3, 1);
2913 status += MXL_SetGPIO(fe, 1, 0);
2914 }
2915 if (state->RF_IN >= 580000000 && state->RF_IN < 630000000) {
2916 status += MXL_ControlWrite(fe, DAC_A_ENABLE, 1);
2917 status += MXL_SetGPIO(fe, 4, 1);
2918 status += MXL_SetGPIO(fe, 3, 1);
2919 status += MXL_SetGPIO(fe, 1, 0);
2920 }
2921 if (state->RF_IN >= 630000000 && state->RF_IN < 700000000) {
2922 status += MXL_ControlWrite(fe, DAC_A_ENABLE, 1);
2923 status += MXL_SetGPIO(fe, 4, 1);
2924 status += MXL_SetGPIO(fe, 3, 1);
2925 status += MXL_SetGPIO(fe, 1, 1);
2926 }
2927 if (state->RF_IN >= 700000000 && state->RF_IN < 760000000) {
2928 status += MXL_ControlWrite(fe, DAC_A_ENABLE, 1);
2929 status += MXL_SetGPIO(fe, 4, 1);
2930 status += MXL_SetGPIO(fe, 3, 1);
2931 status += MXL_SetGPIO(fe, 1, 1);
2932 }
2933 if (state->RF_IN >= 760000000 && state->RF_IN <= 900000000) {
2934 status += MXL_ControlWrite(fe, DAC_A_ENABLE, 1);
2935 status += MXL_SetGPIO(fe, 4, 1);
2936 status += MXL_SetGPIO(fe, 3, 1);
2937 status += MXL_SetGPIO(fe, 1, 1);
2938 }
2939 }
2940
2941 if (state->TF_Type == MXL_TF_D) { /* Tracking Filter type D */
2942
2943 status += MXL_ControlWrite(fe, DAC_DIN_B, 0);
2944
2945 if (state->RF_IN >= 43000000 && state->RF_IN < 174000000) {
2946 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
2947 status += MXL_SetGPIO(fe, 4, 0);
2948 status += MXL_SetGPIO(fe, 1, 1);
2949 status += MXL_SetGPIO(fe, 3, 1);
2950 }
2951 if (state->RF_IN >= 174000000 && state->RF_IN < 250000000) {
2952 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
2953 status += MXL_SetGPIO(fe, 4, 0);
2954 status += MXL_SetGPIO(fe, 1, 0);
2955 status += MXL_SetGPIO(fe, 3, 1);
2956 }
2957 if (state->RF_IN >= 250000000 && state->RF_IN < 310000000) {
2958 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
2959 status += MXL_SetGPIO(fe, 4, 1);
2960 status += MXL_SetGPIO(fe, 1, 0);
2961 status += MXL_SetGPIO(fe, 3, 1);
2962 }
2963 if (state->RF_IN >= 310000000 && state->RF_IN < 360000000) {
2964 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
2965 status += MXL_SetGPIO(fe, 4, 1);
2966 status += MXL_SetGPIO(fe, 1, 0);
2967 status += MXL_SetGPIO(fe, 3, 0);
2968 }
2969 if (state->RF_IN >= 360000000 && state->RF_IN < 470000000) {
2970 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
2971 status += MXL_SetGPIO(fe, 4, 1);
2972 status += MXL_SetGPIO(fe, 1, 1);
2973 status += MXL_SetGPIO(fe, 3, 0);
2974 }
2975 if (state->RF_IN >= 470000000 && state->RF_IN < 640000000) {
2976 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 1);
2977 status += MXL_SetGPIO(fe, 4, 1);
2978 status += MXL_SetGPIO(fe, 1, 1);
2979 status += MXL_SetGPIO(fe, 3, 0);
2980 }
2981 if (state->RF_IN >= 640000000 && state->RF_IN <= 900000000) {
2982 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 1);
2983 status += MXL_SetGPIO(fe, 4, 1);
2984 status += MXL_SetGPIO(fe, 1, 1);
2985 status += MXL_SetGPIO(fe, 3, 1);
2986 }
2987 }
2988
2989 if (state->TF_Type == MXL_TF_D_L) {
2990
2991 /* Tracking Filter type D-L for Lumanate ONLY change 2.6.3 */
2992 status += MXL_ControlWrite(fe, DAC_DIN_A, 0);
2993
2994 /* if UHF and terrestrial => Turn off Tracking Filter */
2995 if (state->RF_IN >= 471000000 &&
2996 (state->RF_IN - 471000000)%6000000 != 0) {
2997 /* Turn off all the banks */
2998 status += MXL_SetGPIO(fe, 3, 1);
2999 status += MXL_SetGPIO(fe, 1, 1);
3000 status += MXL_SetGPIO(fe, 4, 1);
3001 status += MXL_ControlWrite(fe, DAC_A_ENABLE, 0);
3002 status += MXL_ControlWrite(fe, AGC_IF, 10);
3003 } else {
3004 /* if VHF or cable => Turn on Tracking Filter */
3005 if (state->RF_IN >= 43000000 &&
3006 state->RF_IN < 140000000) {
3007
3008 status += MXL_ControlWrite(fe, DAC_A_ENABLE, 0);
3009 status += MXL_SetGPIO(fe, 4, 1);
3010 status += MXL_SetGPIO(fe, 1, 1);
3011 status += MXL_SetGPIO(fe, 3, 0);
3012 }
3013 if (state->RF_IN >= 140000000 &&
3014 state->RF_IN < 240000000) {
3015 status += MXL_ControlWrite(fe, DAC_A_ENABLE, 0);
3016 status += MXL_SetGPIO(fe, 4, 1);
3017 status += MXL_SetGPIO(fe, 1, 0);
3018 status += MXL_SetGPIO(fe, 3, 0);
3019 }
3020 if (state->RF_IN >= 240000000 &&
3021 state->RF_IN < 340000000) {
3022 status += MXL_ControlWrite(fe, DAC_A_ENABLE, 0);
3023 status += MXL_SetGPIO(fe, 4, 0);
3024 status += MXL_SetGPIO(fe, 1, 1);
3025 status += MXL_SetGPIO(fe, 3, 0);
3026 }
3027 if (state->RF_IN >= 340000000 &&
3028 state->RF_IN < 430000000) {
3029 status += MXL_ControlWrite(fe, DAC_A_ENABLE, 0);
3030 status += MXL_SetGPIO(fe, 4, 0);
3031 status += MXL_SetGPIO(fe, 1, 0);
3032 status += MXL_SetGPIO(fe, 3, 1);
3033 }
3034 if (state->RF_IN >= 430000000 &&
3035 state->RF_IN < 470000000) {
3036 status += MXL_ControlWrite(fe, DAC_A_ENABLE, 1);
3037 status += MXL_SetGPIO(fe, 4, 1);
3038 status += MXL_SetGPIO(fe, 1, 0);
3039 status += MXL_SetGPIO(fe, 3, 1);
3040 }
3041 if (state->RF_IN >= 470000000 &&
3042 state->RF_IN < 570000000) {
3043 status += MXL_ControlWrite(fe, DAC_A_ENABLE, 1);
3044 status += MXL_SetGPIO(fe, 4, 0);
3045 status += MXL_SetGPIO(fe, 1, 0);
3046 status += MXL_SetGPIO(fe, 3, 1);
3047 }
3048 if (state->RF_IN >= 570000000 &&
3049 state->RF_IN < 620000000) {
3050 status += MXL_ControlWrite(fe, DAC_A_ENABLE, 0);
3051 status += MXL_SetGPIO(fe, 4, 0);
3052 status += MXL_SetGPIO(fe, 1, 1);
3053 status += MXL_SetGPIO(fe, 3, 1);
3054 }
3055 if (state->RF_IN >= 620000000 &&
3056 state->RF_IN < 760000000) {
3057 status += MXL_ControlWrite(fe, DAC_A_ENABLE, 1);
3058 status += MXL_SetGPIO(fe, 4, 0);
3059 status += MXL_SetGPIO(fe, 1, 1);
3060 status += MXL_SetGPIO(fe, 3, 1);
3061 }
3062 if (state->RF_IN >= 760000000 &&
3063 state->RF_IN <= 900000000) {
3064 status += MXL_ControlWrite(fe, DAC_A_ENABLE, 1);
3065 status += MXL_SetGPIO(fe, 4, 1);
3066 status += MXL_SetGPIO(fe, 1, 1);
3067 status += MXL_SetGPIO(fe, 3, 1);
3068 }
3069 }
3070 }
3071
3072 if (state->TF_Type == MXL_TF_E) /* Tracking Filter type E */ {
3073
3074 status += MXL_ControlWrite(fe, DAC_DIN_B, 0);
3075
3076 if (state->RF_IN >= 43000000 && state->RF_IN < 174000000) {
3077 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
3078 status += MXL_SetGPIO(fe, 4, 0);
3079 status += MXL_SetGPIO(fe, 1, 1);
3080 status += MXL_SetGPIO(fe, 3, 1);
3081 }
3082 if (state->RF_IN >= 174000000 && state->RF_IN < 250000000) {
3083 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
3084 status += MXL_SetGPIO(fe, 4, 0);
3085 status += MXL_SetGPIO(fe, 1, 0);
3086 status += MXL_SetGPIO(fe, 3, 1);
3087 }
3088 if (state->RF_IN >= 250000000 && state->RF_IN < 310000000) {
3089 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
3090 status += MXL_SetGPIO(fe, 4, 1);
3091 status += MXL_SetGPIO(fe, 1, 0);
3092 status += MXL_SetGPIO(fe, 3, 1);
3093 }
3094 if (state->RF_IN >= 310000000 && state->RF_IN < 360000000) {
3095 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
3096 status += MXL_SetGPIO(fe, 4, 1);
3097 status += MXL_SetGPIO(fe, 1, 0);
3098 status += MXL_SetGPIO(fe, 3, 0);
3099 }
3100 if (state->RF_IN >= 360000000 && state->RF_IN < 470000000) {
3101 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
3102 status += MXL_SetGPIO(fe, 4, 1);
3103 status += MXL_SetGPIO(fe, 1, 1);
3104 status += MXL_SetGPIO(fe, 3, 0);
3105 }
3106 if (state->RF_IN >= 470000000 && state->RF_IN < 640000000) {
3107 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 1);
3108 status += MXL_SetGPIO(fe, 4, 1);
3109 status += MXL_SetGPIO(fe, 1, 1);
3110 status += MXL_SetGPIO(fe, 3, 0);
3111 }
3112 if (state->RF_IN >= 640000000 && state->RF_IN <= 900000000) {
3113 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 1);
3114 status += MXL_SetGPIO(fe, 4, 1);
3115 status += MXL_SetGPIO(fe, 1, 1);
3116 status += MXL_SetGPIO(fe, 3, 1);
3117 }
3118 }
3119
3120 if (state->TF_Type == MXL_TF_F) {
3121
3122 /* Tracking Filter type F */
3123 status += MXL_ControlWrite(fe, DAC_DIN_B, 0);
3124
3125 if (state->RF_IN >= 43000000 && state->RF_IN < 160000000) {
3126 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
3127 status += MXL_SetGPIO(fe, 4, 0);
3128 status += MXL_SetGPIO(fe, 1, 1);
3129 status += MXL_SetGPIO(fe, 3, 1);
3130 }
3131 if (state->RF_IN >= 160000000 && state->RF_IN < 210000000) {
3132 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
3133 status += MXL_SetGPIO(fe, 4, 0);
3134 status += MXL_SetGPIO(fe, 1, 0);
3135 status += MXL_SetGPIO(fe, 3, 1);
3136 }
3137 if (state->RF_IN >= 210000000 && state->RF_IN < 300000000) {
3138 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
3139 status += MXL_SetGPIO(fe, 4, 1);
3140 status += MXL_SetGPIO(fe, 1, 0);
3141 status += MXL_SetGPIO(fe, 3, 1);
3142 }
3143 if (state->RF_IN >= 300000000 && state->RF_IN < 390000000) {
3144 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
3145 status += MXL_SetGPIO(fe, 4, 1);
3146 status += MXL_SetGPIO(fe, 1, 0);
3147 status += MXL_SetGPIO(fe, 3, 0);
3148 }
3149 if (state->RF_IN >= 390000000 && state->RF_IN < 515000000) {
3150 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
3151 status += MXL_SetGPIO(fe, 4, 1);
3152 status += MXL_SetGPIO(fe, 1, 1);
3153 status += MXL_SetGPIO(fe, 3, 0);
3154 }
3155 if (state->RF_IN >= 515000000 && state->RF_IN < 650000000) {
3156 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 1);
3157 status += MXL_SetGPIO(fe, 4, 1);
3158 status += MXL_SetGPIO(fe, 1, 1);
3159 status += MXL_SetGPIO(fe, 3, 0);
3160 }
3161 if (state->RF_IN >= 650000000 && state->RF_IN <= 900000000) {
3162 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 1);
3163 status += MXL_SetGPIO(fe, 4, 1);
3164 status += MXL_SetGPIO(fe, 1, 1);
3165 status += MXL_SetGPIO(fe, 3, 1);
3166 }
3167 }
3168
3169 if (state->TF_Type == MXL_TF_E_2) {
3170
3171 /* Tracking Filter type E_2 */
3172 status += MXL_ControlWrite(fe, DAC_DIN_B, 0);
3173
3174 if (state->RF_IN >= 43000000 && state->RF_IN < 174000000) {
3175 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
3176 status += MXL_SetGPIO(fe, 4, 0);
3177 status += MXL_SetGPIO(fe, 1, 1);
3178 status += MXL_SetGPIO(fe, 3, 1);
3179 }
3180 if (state->RF_IN >= 174000000 && state->RF_IN < 250000000) {
3181 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
3182 status += MXL_SetGPIO(fe, 4, 0);
3183 status += MXL_SetGPIO(fe, 1, 0);
3184 status += MXL_SetGPIO(fe, 3, 1);
3185 }
3186 if (state->RF_IN >= 250000000 && state->RF_IN < 350000000) {
3187 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
3188 status += MXL_SetGPIO(fe, 4, 1);
3189 status += MXL_SetGPIO(fe, 1, 0);
3190 status += MXL_SetGPIO(fe, 3, 1);
3191 }
3192 if (state->RF_IN >= 350000000 && state->RF_IN < 400000000) {
3193 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
3194 status += MXL_SetGPIO(fe, 4, 1);
3195 status += MXL_SetGPIO(fe, 1, 0);
3196 status += MXL_SetGPIO(fe, 3, 0);
3197 }
3198 if (state->RF_IN >= 400000000 && state->RF_IN < 570000000) {
3199 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
3200 status += MXL_SetGPIO(fe, 4, 1);
3201 status += MXL_SetGPIO(fe, 1, 1);
3202 status += MXL_SetGPIO(fe, 3, 0);
3203 }
3204 if (state->RF_IN >= 570000000 && state->RF_IN < 770000000) {
3205 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 1);
3206 status += MXL_SetGPIO(fe, 4, 1);
3207 status += MXL_SetGPIO(fe, 1, 1);
3208 status += MXL_SetGPIO(fe, 3, 0);
3209 }
3210 if (state->RF_IN >= 770000000 && state->RF_IN <= 900000000) {
3211 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 1);
3212 status += MXL_SetGPIO(fe, 4, 1);
3213 status += MXL_SetGPIO(fe, 1, 1);
3214 status += MXL_SetGPIO(fe, 3, 1);
3215 }
3216 }
3217
3218 if (state->TF_Type == MXL_TF_G) {
3219
3220 /* Tracking Filter type G add for v2.6.8 */
3221 status += MXL_ControlWrite(fe, DAC_DIN_B, 0);
3222
3223 if (state->RF_IN >= 50000000 && state->RF_IN < 190000000) {
3224
3225 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
3226 status += MXL_SetGPIO(fe, 4, 0);
3227 status += MXL_SetGPIO(fe, 1, 1);
3228 status += MXL_SetGPIO(fe, 3, 1);
3229 }
3230 if (state->RF_IN >= 190000000 && state->RF_IN < 280000000) {
3231 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
3232 status += MXL_SetGPIO(fe, 4, 0);
3233 status += MXL_SetGPIO(fe, 1, 0);
3234 status += MXL_SetGPIO(fe, 3, 1);
3235 }
3236 if (state->RF_IN >= 280000000 && state->RF_IN < 350000000) {
3237 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
3238 status += MXL_SetGPIO(fe, 4, 1);
3239 status += MXL_SetGPIO(fe, 1, 0);
3240 status += MXL_SetGPIO(fe, 3, 1);
3241 }
3242 if (state->RF_IN >= 350000000 && state->RF_IN < 400000000) {
3243 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
3244 status += MXL_SetGPIO(fe, 4, 1);
3245 status += MXL_SetGPIO(fe, 1, 0);
3246 status += MXL_SetGPIO(fe, 3, 0);
3247 }
3248 if (state->RF_IN >= 400000000 && state->RF_IN < 470000000) {
3249 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 1);
3250 status += MXL_SetGPIO(fe, 4, 1);
3251 status += MXL_SetGPIO(fe, 1, 0);
3252 status += MXL_SetGPIO(fe, 3, 1);
3253 }
3254 if (state->RF_IN >= 470000000 && state->RF_IN < 640000000) {
3255 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
3256 status += MXL_SetGPIO(fe, 4, 1);
3257 status += MXL_SetGPIO(fe, 1, 1);
3258 status += MXL_SetGPIO(fe, 3, 0);
3259 }
3260 if (state->RF_IN >= 640000000 && state->RF_IN < 820000000) {
3261 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 1);
3262 status += MXL_SetGPIO(fe, 4, 1);
3263 status += MXL_SetGPIO(fe, 1, 1);
3264 status += MXL_SetGPIO(fe, 3, 0);
3265 }
3266 if (state->RF_IN >= 820000000 && state->RF_IN <= 900000000) {
3267 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 1);
3268 status += MXL_SetGPIO(fe, 4, 1);
3269 status += MXL_SetGPIO(fe, 1, 1);
3270 status += MXL_SetGPIO(fe, 3, 1);
3271 }
3272 }
3273
3274 if (state->TF_Type == MXL_TF_E_NA) {
3275
3276 /* Tracking Filter type E-NA for Empia ONLY change for 2.6.8 */
3277 status += MXL_ControlWrite(fe, DAC_DIN_B, 0);
3278
3279 /* if UHF and terrestrial=> Turn off Tracking Filter */
3280 if (state->RF_IN >= 471000000 &&
3281 (state->RF_IN - 471000000)%6000000 != 0) {
3282
3283 /* Turn off all the banks */
3284 status += MXL_SetGPIO(fe, 3, 1);
3285 status += MXL_SetGPIO(fe, 1, 1);
3286 status += MXL_SetGPIO(fe, 4, 1);
3287 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
3288
3289 /* 2.6.12 Turn on RSSI */
3290 status += MXL_ControlWrite(fe, SEQ_EXTSYNTHCALIF, 1);
3291 status += MXL_ControlWrite(fe, SEQ_EXTDCCAL, 1);
3292 status += MXL_ControlWrite(fe, AGC_EN_RSSI, 1);
3293 status += MXL_ControlWrite(fe, RFA_ENCLKRFAGC, 1);
3294
3295 /* RSSI reference point */
3296 status += MXL_ControlWrite(fe, RFA_RSSI_REFH, 5);
3297 status += MXL_ControlWrite(fe, RFA_RSSI_REF, 3);
3298 status += MXL_ControlWrite(fe, RFA_RSSI_REFL, 2);
3299
3300 /* following parameter is from analog OTA mode,
3301 * can be change to seek better performance */
3302 status += MXL_ControlWrite(fe, RFSYN_CHP_GAIN, 3);
3303 } else {
3304 /* if VHF or Cable => Turn on Tracking Filter */
3305
3306 /* 2.6.12 Turn off RSSI */
3307 status += MXL_ControlWrite(fe, AGC_EN_RSSI, 0);
3308
3309 /* change back from above condition */
3310 status += MXL_ControlWrite(fe, RFSYN_CHP_GAIN, 5);
3311
3312
3313 if (state->RF_IN >= 43000000 && state->RF_IN < 174000000) {
3314
3315 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
3316 status += MXL_SetGPIO(fe, 4, 0);
3317 status += MXL_SetGPIO(fe, 1, 1);
3318 status += MXL_SetGPIO(fe, 3, 1);
3319 }
3320 if (state->RF_IN >= 174000000 && state->RF_IN < 250000000) {
3321 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
3322 status += MXL_SetGPIO(fe, 4, 0);
3323 status += MXL_SetGPIO(fe, 1, 0);
3324 status += MXL_SetGPIO(fe, 3, 1);
3325 }
3326 if (state->RF_IN >= 250000000 && state->RF_IN < 350000000) {
3327 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
3328 status += MXL_SetGPIO(fe, 4, 1);
3329 status += MXL_SetGPIO(fe, 1, 0);
3330 status += MXL_SetGPIO(fe, 3, 1);
3331 }
3332 if (state->RF_IN >= 350000000 && state->RF_IN < 400000000) {
3333 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
3334 status += MXL_SetGPIO(fe, 4, 1);
3335 status += MXL_SetGPIO(fe, 1, 0);
3336 status += MXL_SetGPIO(fe, 3, 0);
3337 }
3338 if (state->RF_IN >= 400000000 && state->RF_IN < 570000000) {
3339 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 0);
3340 status += MXL_SetGPIO(fe, 4, 1);
3341 status += MXL_SetGPIO(fe, 1, 1);
3342 status += MXL_SetGPIO(fe, 3, 0);
3343 }
3344 if (state->RF_IN >= 570000000 && state->RF_IN < 770000000) {
3345 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 1);
3346 status += MXL_SetGPIO(fe, 4, 1);
3347 status += MXL_SetGPIO(fe, 1, 1);
3348 status += MXL_SetGPIO(fe, 3, 0);
3349 }
3350 if (state->RF_IN >= 770000000 && state->RF_IN <= 900000000) {
3351 status += MXL_ControlWrite(fe, DAC_B_ENABLE, 1);
3352 status += MXL_SetGPIO(fe, 4, 1);
3353 status += MXL_SetGPIO(fe, 1, 1);
3354 status += MXL_SetGPIO(fe, 3, 1);
3355 }
3356 }
3357 }
3358 return status ;
3359}
3360
3361static u16 MXL_SetGPIO(struct dvb_frontend *fe, u8 GPIO_Num, u8 GPIO_Val)
3362{
3363 u16 status = 0;
3364
3365 if (GPIO_Num == 1)
3366 status += MXL_ControlWrite(fe, GPIO_1B, GPIO_Val ? 0 : 1);
3367
3368 /* GPIO2 is not available */
3369
3370 if (GPIO_Num == 3) {
3371 if (GPIO_Val == 1) {
3372 status += MXL_ControlWrite(fe, GPIO_3, 0);
3373 status += MXL_ControlWrite(fe, GPIO_3B, 0);
3374 }
3375 if (GPIO_Val == 0) {
3376 status += MXL_ControlWrite(fe, GPIO_3, 1);
3377 status += MXL_ControlWrite(fe, GPIO_3B, 1);
3378 }
3379 if (GPIO_Val == 3) { /* tri-state */
3380 status += MXL_ControlWrite(fe, GPIO_3, 0);
3381 status += MXL_ControlWrite(fe, GPIO_3B, 1);
3382 }
3383 }
3384 if (GPIO_Num == 4) {
3385 if (GPIO_Val == 1) {
3386 status += MXL_ControlWrite(fe, GPIO_4, 0);
3387 status += MXL_ControlWrite(fe, GPIO_4B, 0);
3388 }
3389 if (GPIO_Val == 0) {
3390 status += MXL_ControlWrite(fe, GPIO_4, 1);
3391 status += MXL_ControlWrite(fe, GPIO_4B, 1);
3392 }
3393 if (GPIO_Val == 3) { /* tri-state */
3394 status += MXL_ControlWrite(fe, GPIO_4, 0);
3395 status += MXL_ControlWrite(fe, GPIO_4B, 1);
3396 }
3397 }
3398
3399 return status;
3400}
3401
3402static u16 MXL_ControlWrite(struct dvb_frontend *fe, u16 ControlNum, u32 value)
3403{
3404 u16 status = 0;
3405
3406 /* Will write ALL Matching Control Name */
3407 /* Write Matching INIT Control */
3408 status += MXL_ControlWrite_Group(fe, ControlNum, value, 1);
3409 /* Write Matching CH Control */
3410 status += MXL_ControlWrite_Group(fe, ControlNum, value, 2);
3411#ifdef _MXL_INTERNAL
3412 /* Write Matching MXL Control */
3413 status += MXL_ControlWrite_Group(fe, ControlNum, value, 3);
3414#endif
3415 return status;
3416}
3417
3418static u16 MXL_ControlWrite_Group(struct dvb_frontend *fe, u16 controlNum,
3419 u32 value, u16 controlGroup)
3420{
3421 struct mxl5005s_state *state = fe->tuner_priv;
3422 u16 i, j, k;
3423 u32 highLimit;
3424 u32 ctrlVal;
3425
3426 if (controlGroup == 1) /* Initial Control */ {
3427
3428 for (i = 0; i < state->Init_Ctrl_Num; i++) {
3429
3430 if (controlNum == state->Init_Ctrl[i].Ctrl_Num) {
3431
3432 highLimit = 1 << state->Init_Ctrl[i].size;
3433 if (value < highLimit) {
3434 for (j = 0; j < state->Init_Ctrl[i].size; j++) {
3435 state->Init_Ctrl[i].val[j] = (u8)((value >> j) & 0x01);
3436 MXL_RegWriteBit(fe, (u8)(state->Init_Ctrl[i].addr[j]),
3437 (u8)(state->Init_Ctrl[i].bit[j]),
3438 (u8)((value>>j) & 0x01));
3439 }
3440 ctrlVal = 0;
3441 for (k = 0; k < state->Init_Ctrl[i].size; k++)
3442 ctrlVal += state->Init_Ctrl[i].val[k] * (1 << k);
3443 } else
3444 return -1;
3445 }
3446 }
3447 }
3448 if (controlGroup == 2) /* Chan change Control */ {
3449
3450 for (i = 0; i < state->CH_Ctrl_Num; i++) {
3451
3452 if (controlNum == state->CH_Ctrl[i].Ctrl_Num) {
3453
3454 highLimit = 1 << state->CH_Ctrl[i].size;
3455 if (value < highLimit) {
3456 for (j = 0; j < state->CH_Ctrl[i].size; j++) {
3457 state->CH_Ctrl[i].val[j] = (u8)((value >> j) & 0x01);
3458 MXL_RegWriteBit(fe, (u8)(state->CH_Ctrl[i].addr[j]),
3459 (u8)(state->CH_Ctrl[i].bit[j]),
3460 (u8)((value>>j) & 0x01));
3461 }
3462 ctrlVal = 0;
3463 for (k = 0; k < state->CH_Ctrl[i].size; k++)
3464 ctrlVal += state->CH_Ctrl[i].val[k] * (1 << k);
3465 } else
3466 return -1;
3467 }
3468 }
3469 }
3470#ifdef _MXL_INTERNAL
3471 if (controlGroup == 3) /* Maxlinear Control */ {
3472
3473 for (i = 0; i < state->MXL_Ctrl_Num; i++) {
3474
3475 if (controlNum == state->MXL_Ctrl[i].Ctrl_Num) {
3476
3477 highLimit = (1 << state->MXL_Ctrl[i].size);
3478 if (value < highLimit) {
3479 for (j = 0; j < state->MXL_Ctrl[i].size; j++) {
3480 state->MXL_Ctrl[i].val[j] = (u8)((value >> j) & 0x01);
3481 MXL_RegWriteBit(fe, (u8)(state->MXL_Ctrl[i].addr[j]),
3482 (u8)(state->MXL_Ctrl[i].bit[j]),
3483 (u8)((value>>j) & 0x01));
3484 }
3485 ctrlVal = 0;
3486 for (k = 0; k < state->MXL_Ctrl[i].size; k++)
3487 ctrlVal += state->
3488 MXL_Ctrl[i].val[k] *
3489 (1 << k);
3490 } else
3491 return -1;
3492 }
3493 }
3494 }
3495#endif
3496 return 0 ; /* successful return */
3497}
3498
3499static u16 MXL_RegRead(struct dvb_frontend *fe, u8 RegNum, u8 *RegVal)
3500{
3501 struct mxl5005s_state *state = fe->tuner_priv;
3502 int i ;
3503
3504 for (i = 0; i < 104; i++) {
3505 if (RegNum == state->TunerRegs[i].Reg_Num) {
3506 *RegVal = (u8)(state->TunerRegs[i].Reg_Val);
3507 return 0;
3508 }
3509 }
3510
3511 return 1;
3512}
3513
3514static u16 MXL_ControlRead(struct dvb_frontend *fe, u16 controlNum, u32 *value)
3515{
3516 struct mxl5005s_state *state = fe->tuner_priv;
3517 u32 ctrlVal ;
3518 u16 i, k ;
3519
3520 for (i = 0; i < state->Init_Ctrl_Num ; i++) {
3521
3522 if (controlNum == state->Init_Ctrl[i].Ctrl_Num) {
3523
3524 ctrlVal = 0;
3525 for (k = 0; k < state->Init_Ctrl[i].size; k++)
3526 ctrlVal += state->Init_Ctrl[i].val[k] * (1<<k);
3527 *value = ctrlVal;
3528 return 0;
3529 }
3530 }
3531
3532 for (i = 0; i < state->CH_Ctrl_Num ; i++) {
3533
3534 if (controlNum == state->CH_Ctrl[i].Ctrl_Num) {
3535
3536 ctrlVal = 0;
3537 for (k = 0; k < state->CH_Ctrl[i].size; k++)
3538 ctrlVal += state->CH_Ctrl[i].val[k] * (1 << k);
3539 *value = ctrlVal;
3540 return 0;
3541
3542 }
3543 }
3544
3545#ifdef _MXL_INTERNAL
3546 for (i = 0; i < state->MXL_Ctrl_Num ; i++) {
3547
3548 if (controlNum == state->MXL_Ctrl[i].Ctrl_Num) {
3549
3550 ctrlVal = 0;
3551 for (k = 0; k < state->MXL_Ctrl[i].size; k++)
3552 ctrlVal += state->MXL_Ctrl[i].val[k] * (1<<k);
3553 *value = ctrlVal;
3554 return 0;
3555
3556 }
3557 }
3558#endif
3559 return 1;
3560}
3561
3562static void MXL_RegWriteBit(struct dvb_frontend *fe, u8 address, u8 bit,
3563 u8 bitVal)
3564{
3565 struct mxl5005s_state *state = fe->tuner_priv;
3566 int i ;
3567
3568 const u8 AND_MAP[8] = {
3569 0xFE, 0xFD, 0xFB, 0xF7,
3570 0xEF, 0xDF, 0xBF, 0x7F } ;
3571
3572 const u8 OR_MAP[8] = {
3573 0x01, 0x02, 0x04, 0x08,
3574 0x10, 0x20, 0x40, 0x80 } ;
3575
3576 for (i = 0; i < state->TunerRegs_Num; i++) {
3577 if (state->TunerRegs[i].Reg_Num == address) {
3578 if (bitVal)
3579 state->TunerRegs[i].Reg_Val |= OR_MAP[bit];
3580 else
3581 state->TunerRegs[i].Reg_Val &= AND_MAP[bit];
3582 break ;
3583 }
3584 }
3585}
3586
3587static u32 MXL_Ceiling(u32 value, u32 resolution)
3588{
3589 return value / resolution + (value % resolution > 0 ? 1 : 0);
3590}
3591
3592/* Retrieve the Initialzation Registers */
3593static u16 MXL_GetInitRegister(struct dvb_frontend *fe, u8 *RegNum,
3594 u8 *RegVal, int *count)
3595{
3596 u16 status = 0;
3597 int i ;
3598
3599 u8 RegAddr[] = {
3600 11, 12, 13, 22, 32, 43, 44, 53, 56, 59, 73,
3601 76, 77, 91, 134, 135, 137, 147,
3602 156, 166, 167, 168, 25 };
3603
3604 *count = ARRAY_SIZE(RegAddr);
3605
3606 status += MXL_BlockInit(fe);
3607
3608 for (i = 0 ; i < *count; i++) {
3609 RegNum[i] = RegAddr[i];
3610 status += MXL_RegRead(fe, RegNum[i], &RegVal[i]);
3611 }
3612
3613 return status;
3614}
3615
3616static u16 MXL_GetCHRegister(struct dvb_frontend *fe, u8 *RegNum, u8 *RegVal,
3617 int *count)
3618{
3619 u16 status = 0;
3620 int i ;
3621
3622/* add 77, 166, 167, 168 register for 2.6.12 */
3623#ifdef _MXL_PRODUCTION
3624 u8 RegAddr[] = {14, 15, 16, 17, 22, 43, 65, 68, 69, 70, 73, 92, 93, 106,
3625 107, 108, 109, 110, 111, 112, 136, 138, 149, 77, 166, 167, 168 } ;
3626#else
3627 u8 RegAddr[] = {14, 15, 16, 17, 22, 43, 68, 69, 70, 73, 92, 93, 106,
3628 107, 108, 109, 110, 111, 112, 136, 138, 149, 77, 166, 167, 168 } ;
3629 /*
3630 u8 RegAddr[171];
3631 for (i = 0; i <= 170; i++)
3632 RegAddr[i] = i;
3633 */
3634#endif
3635
3636 *count = ARRAY_SIZE(RegAddr);
3637
3638 for (i = 0 ; i < *count; i++) {
3639 RegNum[i] = RegAddr[i];
3640 status += MXL_RegRead(fe, RegNum[i], &RegVal[i]);
3641 }
3642
3643 return status;
3644}
3645
3646static u16 MXL_GetCHRegister_ZeroIF(struct dvb_frontend *fe, u8 *RegNum,
3647 u8 *RegVal, int *count)
3648{
3649 u16 status = 0;
3650 int i;
3651
3652 u8 RegAddr[] = {43, 136};
3653
3654 *count = ARRAY_SIZE(RegAddr);
3655
3656 for (i = 0; i < *count; i++) {
3657 RegNum[i] = RegAddr[i];
3658 status += MXL_RegRead(fe, RegNum[i], &RegVal[i]);
3659 }
3660
3661 return status;
3662}
3663
3664static u16 MXL_GetMasterControl(u8 *MasterReg, int state)
3665{
3666 if (state == 1) /* Load_Start */
3667 *MasterReg = 0xF3;
3668 if (state == 2) /* Power_Down */
3669 *MasterReg = 0x41;
3670 if (state == 3) /* Synth_Reset */
3671 *MasterReg = 0xB1;
3672 if (state == 4) /* Seq_Off */
3673 *MasterReg = 0xF1;
3674
3675 return 0;
3676}
3677
3678#ifdef _MXL_PRODUCTION
3679static u16 MXL_VCORange_Test(struct dvb_frontend *fe, int VCO_Range)
3680{
3681 struct mxl5005s_state *state = fe->tuner_priv;
3682 u16 status = 0 ;
3683
3684 if (VCO_Range == 1) {
3685 status += MXL_ControlWrite(fe, RFSYN_EN_DIV, 1);
3686 status += MXL_ControlWrite(fe, RFSYN_EN_OUTMUX, 0);
3687 status += MXL_ControlWrite(fe, RFSYN_SEL_DIVM, 0);
3688 status += MXL_ControlWrite(fe, RFSYN_DIVM, 1);
3689 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_OUT, 1);
3690 status += MXL_ControlWrite(fe, RFSYN_RF_DIV_BIAS, 1);
3691 status += MXL_ControlWrite(fe, DN_SEL_FREQ, 0);
3692 if (state->Mode == 0 && state->IF_Mode == 1) {
3693 /* Analog Low IF Mode */
3694 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_HI, 1);
3695 status += MXL_ControlWrite(fe, RFSYN_VCO_BIAS, 8);
3696 status += MXL_ControlWrite(fe, CHCAL_INT_MOD_RF, 56);
3697 status += MXL_ControlWrite(fe,
3698 CHCAL_FRAC_MOD_RF, 180224);
3699 }
3700 if (state->Mode == 0 && state->IF_Mode == 0) {
3701 /* Analog Zero IF Mode */
3702 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_HI, 1);
3703 status += MXL_ControlWrite(fe, RFSYN_VCO_BIAS, 8);
3704 status += MXL_ControlWrite(fe, CHCAL_INT_MOD_RF, 56);
3705 status += MXL_ControlWrite(fe,
3706 CHCAL_FRAC_MOD_RF, 222822);
3707 }
3708 if (state->Mode == 1) /* Digital Mode */ {
3709 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_HI, 1);
3710 status += MXL_ControlWrite(fe, RFSYN_VCO_BIAS, 8);
3711 status += MXL_ControlWrite(fe, CHCAL_INT_MOD_RF, 56);
3712 status += MXL_ControlWrite(fe,
3713 CHCAL_FRAC_MOD_RF, 229376);
3714 }
3715 }
3716
3717 if (VCO_Range == 2) {
3718 status += MXL_ControlWrite(fe, RFSYN_EN_DIV, 1);
3719 status += MXL_ControlWrite(fe, RFSYN_EN_OUTMUX, 0);
3720 status += MXL_ControlWrite(fe, RFSYN_SEL_DIVM, 0);
3721 status += MXL_ControlWrite(fe, RFSYN_DIVM, 1);
3722 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_OUT, 1);
3723 status += MXL_ControlWrite(fe, RFSYN_RF_DIV_BIAS, 1);
3724 status += MXL_ControlWrite(fe, DN_SEL_FREQ, 0);
3725 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_HI, 1);
3726 status += MXL_ControlWrite(fe, RFSYN_VCO_BIAS, 40);
3727 status += MXL_ControlWrite(fe, CHCAL_INT_MOD_RF, 41);
3728 if (state->Mode == 0 && state->IF_Mode == 1) {
3729 /* Analog Low IF Mode */
3730 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_HI, 1);
3731 status += MXL_ControlWrite(fe, RFSYN_VCO_BIAS, 40);
3732 status += MXL_ControlWrite(fe, CHCAL_INT_MOD_RF, 42);
3733 status += MXL_ControlWrite(fe,
3734 CHCAL_FRAC_MOD_RF, 206438);
3735 }
3736 if (state->Mode == 0 && state->IF_Mode == 0) {
3737 /* Analog Zero IF Mode */
3738 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_HI, 1);
3739 status += MXL_ControlWrite(fe, RFSYN_VCO_BIAS, 40);
3740 status += MXL_ControlWrite(fe, CHCAL_INT_MOD_RF, 42);
3741 status += MXL_ControlWrite(fe,
3742 CHCAL_FRAC_MOD_RF, 206438);
3743 }
3744 if (state->Mode == 1) /* Digital Mode */ {
3745 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_HI, 1);
3746 status += MXL_ControlWrite(fe, RFSYN_VCO_BIAS, 40);
3747 status += MXL_ControlWrite(fe, CHCAL_INT_MOD_RF, 41);
3748 status += MXL_ControlWrite(fe,
3749 CHCAL_FRAC_MOD_RF, 16384);
3750 }
3751 }
3752
3753 if (VCO_Range == 3) {
3754 status += MXL_ControlWrite(fe, RFSYN_EN_DIV, 1);
3755 status += MXL_ControlWrite(fe, RFSYN_EN_OUTMUX, 0);
3756 status += MXL_ControlWrite(fe, RFSYN_SEL_DIVM, 0);
3757 status += MXL_ControlWrite(fe, RFSYN_DIVM, 1);
3758 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_OUT, 1);
3759 status += MXL_ControlWrite(fe, RFSYN_RF_DIV_BIAS, 1);
3760 status += MXL_ControlWrite(fe, DN_SEL_FREQ, 0);
3761 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_HI, 0);
3762 status += MXL_ControlWrite(fe, RFSYN_VCO_BIAS, 8);
3763 status += MXL_ControlWrite(fe, CHCAL_INT_MOD_RF, 42);
3764 if (state->Mode == 0 && state->IF_Mode == 1) {
3765 /* Analog Low IF Mode */
3766 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_HI, 0);
3767 status += MXL_ControlWrite(fe, RFSYN_VCO_BIAS, 8);
3768 status += MXL_ControlWrite(fe, CHCAL_INT_MOD_RF, 44);
3769 status += MXL_ControlWrite(fe,
3770 CHCAL_FRAC_MOD_RF, 173670);
3771 }
3772 if (state->Mode == 0 && state->IF_Mode == 0) {
3773 /* Analog Zero IF Mode */
3774 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_HI, 0);
3775 status += MXL_ControlWrite(fe, RFSYN_VCO_BIAS, 8);
3776 status += MXL_ControlWrite(fe, CHCAL_INT_MOD_RF, 44);
3777 status += MXL_ControlWrite(fe,
3778 CHCAL_FRAC_MOD_RF, 173670);
3779 }
3780 if (state->Mode == 1) /* Digital Mode */ {
3781 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_HI, 0);
3782 status += MXL_ControlWrite(fe, RFSYN_VCO_BIAS, 8);
3783 status += MXL_ControlWrite(fe, CHCAL_INT_MOD_RF, 42);
3784 status += MXL_ControlWrite(fe,
3785 CHCAL_FRAC_MOD_RF, 245760);
3786 }
3787 }
3788
3789 if (VCO_Range == 4) {
3790 status += MXL_ControlWrite(fe, RFSYN_EN_DIV, 1);
3791 status += MXL_ControlWrite(fe, RFSYN_EN_OUTMUX, 0);
3792 status += MXL_ControlWrite(fe, RFSYN_SEL_DIVM, 0);
3793 status += MXL_ControlWrite(fe, RFSYN_DIVM, 1);
3794 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_OUT, 1);
3795 status += MXL_ControlWrite(fe, RFSYN_RF_DIV_BIAS, 1);
3796 status += MXL_ControlWrite(fe, DN_SEL_FREQ, 0);
3797 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_HI, 0);
3798 status += MXL_ControlWrite(fe, RFSYN_VCO_BIAS, 40);
3799 status += MXL_ControlWrite(fe, CHCAL_INT_MOD_RF, 27);
3800 if (state->Mode == 0 && state->IF_Mode == 1) {
3801 /* Analog Low IF Mode */
3802 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_HI, 0);
3803 status += MXL_ControlWrite(fe, RFSYN_VCO_BIAS, 40);
3804 status += MXL_ControlWrite(fe, CHCAL_INT_MOD_RF, 27);
3805 status += MXL_ControlWrite(fe,
3806 CHCAL_FRAC_MOD_RF, 206438);
3807 }
3808 if (state->Mode == 0 && state->IF_Mode == 0) {
3809 /* Analog Zero IF Mode */
3810 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_HI, 0);
3811 status += MXL_ControlWrite(fe, RFSYN_VCO_BIAS, 40);
3812 status += MXL_ControlWrite(fe, CHCAL_INT_MOD_RF, 27);
3813 status += MXL_ControlWrite(fe,
3814 CHCAL_FRAC_MOD_RF, 206438);
3815 }
3816 if (state->Mode == 1) /* Digital Mode */ {
3817 status += MXL_ControlWrite(fe, RFSYN_SEL_VCO_HI, 0);
3818 status += MXL_ControlWrite(fe, RFSYN_VCO_BIAS, 40);
3819 status += MXL_ControlWrite(fe, CHCAL_INT_MOD_RF, 27);
3820 status += MXL_ControlWrite(fe,
3821 CHCAL_FRAC_MOD_RF, 212992);
3822 }
3823 }
3824
3825 return status;
3826}
3827
3828static u16 MXL_Hystersis_Test(struct dvb_frontend *fe, int Hystersis)
3829{
3830 struct mxl5005s_state *state = fe->tuner_priv;
3831 u16 status = 0;
3832
3833 if (Hystersis == 1)
3834 status += MXL_ControlWrite(fe, DN_BYPASS_AGC_I2C, 1);
3835
3836 return status;
3837}
3838#endif
3839/* End: Reference driver code found in the Realtek driver that
3840 * is copyright MaxLinear */
3841
3842/* ----------------------------------------------------------------
3843 * Begin: Everything after here is new code to adapt the
3844 * proprietary Realtek driver into a Linux API tuner.
3845 * Copyright (C) 2008 Steven Toth <stoth@linuxtv.org>
3846 */
3847static int mxl5005s_reset(struct dvb_frontend *fe)
3848{
3849 struct mxl5005s_state *state = fe->tuner_priv;
3850 int ret = 0;
3851
3852 u8 buf[2] = { 0xff, 0x00 };
3853 struct i2c_msg msg = { .addr = state->config->i2c_address, .flags = 0,
3854 .buf = buf, .len = 2 };
3855
3856 dprintk(2, "%s()\n", __func__);
3857
3858 if (fe->ops.i2c_gate_ctrl)
3859 fe->ops.i2c_gate_ctrl(fe, 1);
3860
3861 if (i2c_transfer(state->i2c, &msg, 1) != 1) {
3862 printk(KERN_WARNING "mxl5005s I2C reset failed\n");
3863 ret = -EREMOTEIO;
3864 }
3865
3866 if (fe->ops.i2c_gate_ctrl)
3867 fe->ops.i2c_gate_ctrl(fe, 0);
3868
3869 return ret;
3870}
3871
3872/* Write a single byte to a single reg, latch the value if required by
3873 * following the transaction with the latch byte.
3874 */
3875static int mxl5005s_writereg(struct dvb_frontend *fe, u8 reg, u8 val, int latch)
3876{
3877 struct mxl5005s_state *state = fe->tuner_priv;
3878 u8 buf[3] = { reg, val, MXL5005S_LATCH_BYTE };
3879 struct i2c_msg msg = { .addr = state->config->i2c_address, .flags = 0,
3880 .buf = buf, .len = 3 };
3881
3882 if (latch == 0)
3883 msg.len = 2;
3884
3885 dprintk(2, "%s(0x%x, 0x%x, 0x%x)\n", __func__, reg, val, msg.addr);
3886
3887 if (i2c_transfer(state->i2c, &msg, 1) != 1) {
3888 printk(KERN_WARNING "mxl5005s I2C write failed\n");
3889 return -EREMOTEIO;
3890 }
3891 return 0;
3892}
3893
3894static int mxl5005s_writeregs(struct dvb_frontend *fe, u8 *addrtable,
3895 u8 *datatable, u8 len)
3896{
3897 int ret = 0, i;
3898
3899 if (fe->ops.i2c_gate_ctrl)
3900 fe->ops.i2c_gate_ctrl(fe, 1);
3901
3902 for (i = 0 ; i < len-1; i++) {
3903 ret = mxl5005s_writereg(fe, addrtable[i], datatable[i], 0);
3904 if (ret < 0)
3905 break;
3906 }
3907
3908 ret = mxl5005s_writereg(fe, addrtable[i], datatable[i], 1);
3909
3910 if (fe->ops.i2c_gate_ctrl)
3911 fe->ops.i2c_gate_ctrl(fe, 0);
3912
3913 return ret;
3914}
3915
3916static int mxl5005s_init(struct dvb_frontend *fe)
3917{
3918 struct mxl5005s_state *state = fe->tuner_priv;
3919
3920 dprintk(1, "%s()\n", __func__);
3921 state->current_mode = MXL_QAM;
3922 return mxl5005s_reconfigure(fe, MXL_QAM, MXL5005S_BANDWIDTH_6MHZ);
3923}
3924
3925static int mxl5005s_reconfigure(struct dvb_frontend *fe, u32 mod_type,
3926 u32 bandwidth)
3927{
3928 struct mxl5005s_state *state = fe->tuner_priv;
3929
3930 u8 AddrTable[MXL5005S_REG_WRITING_TABLE_LEN_MAX];
3931 u8 ByteTable[MXL5005S_REG_WRITING_TABLE_LEN_MAX];
3932 int TableLen;
3933
3934 dprintk(1, "%s(type=%d, bw=%d)\n", __func__, mod_type, bandwidth);
3935
3936 mxl5005s_reset(fe);
3937
3938 /* Tuner initialization stage 0 */
3939 MXL_GetMasterControl(ByteTable, MC_SYNTH_RESET);
3940 AddrTable[0] = MASTER_CONTROL_ADDR;
3941 ByteTable[0] |= state->config->AgcMasterByte;
3942
3943 mxl5005s_writeregs(fe, AddrTable, ByteTable, 1);
3944
3945 mxl5005s_AssignTunerMode(fe, mod_type, bandwidth);
3946
3947 /* Tuner initialization stage 1 */
3948 MXL_GetInitRegister(fe, AddrTable, ByteTable, &TableLen);
3949
3950 mxl5005s_writeregs(fe, AddrTable, ByteTable, TableLen);
3951
3952 return 0;
3953}
3954
3955static int mxl5005s_AssignTunerMode(struct dvb_frontend *fe, u32 mod_type,
3956 u32 bandwidth)
3957{
3958 struct mxl5005s_state *state = fe->tuner_priv;
3959 struct mxl5005s_config *c = state->config;
3960
3961 InitTunerControls(fe);
3962
3963 /* Set MxL5005S parameters. */
3964 MXL5005_TunerConfig(
3965 fe,
3966 c->mod_mode,
3967 c->if_mode,
3968 bandwidth,
3969 c->if_freq,
3970 c->xtal_freq,
3971 c->agc_mode,
3972 c->top,
3973 c->output_load,
3974 c->clock_out,
3975 c->div_out,
3976 c->cap_select,
3977 c->rssi_enable,
3978 mod_type,
3979 c->tracking_filter);
3980
3981 return 0;
3982}
3983
3984static int mxl5005s_set_params(struct dvb_frontend *fe,
3985 struct dvb_frontend_parameters *params)
3986{
3987 struct mxl5005s_state *state = fe->tuner_priv;
3988 u32 req_mode, req_bw = 0;
3989 int ret;
3990
3991 dprintk(1, "%s()\n", __func__);
3992
3993 if (fe->ops.info.type == FE_ATSC) {
3994 switch (params->u.vsb.modulation) {
3995 case VSB_8:
3996 req_mode = MXL_ATSC; break;
3997 default:
3998 case QAM_64:
3999 case QAM_256:
4000 case QAM_AUTO:
4001 req_mode = MXL_QAM; break;
4002 }
4003 } else
4004 req_mode = MXL_DVBT;
4005
4006 /* Change tuner for new modulation type if reqd */
4007 if (req_mode != state->current_mode) {
4008 switch (req_mode) {
4009 case MXL_ATSC:
4010 case MXL_QAM:
4011 req_bw = MXL5005S_BANDWIDTH_6MHZ;
4012 break;
4013 case MXL_DVBT:
4014 default:
4015 /* Assume DVB-T */
4016 switch (params->u.ofdm.bandwidth) {
4017 case BANDWIDTH_6_MHZ:
4018 req_bw = MXL5005S_BANDWIDTH_6MHZ;
4019 break;
4020 case BANDWIDTH_7_MHZ:
4021 req_bw = MXL5005S_BANDWIDTH_7MHZ;
4022 break;
4023 case BANDWIDTH_AUTO:
4024 case BANDWIDTH_8_MHZ:
4025 req_bw = MXL5005S_BANDWIDTH_8MHZ;
4026 break;
4027 default:
4028 return -EINVAL;
4029 }
4030 }
4031
4032 state->current_mode = req_mode;
4033 ret = mxl5005s_reconfigure(fe, req_mode, req_bw);
4034
4035 } else
4036 ret = 0;
4037
4038 if (ret == 0) {
4039 dprintk(1, "%s() freq=%d\n", __func__, params->frequency);
4040 ret = mxl5005s_SetRfFreqHz(fe, params->frequency);
4041 }
4042
4043 return ret;
4044}
4045
4046static int mxl5005s_get_frequency(struct dvb_frontend *fe, u32 *frequency)
4047{
4048 struct mxl5005s_state *state = fe->tuner_priv;
4049 dprintk(1, "%s()\n", __func__);
4050
4051 *frequency = state->RF_IN;
4052
4053 return 0;
4054}
4055
4056static int mxl5005s_get_bandwidth(struct dvb_frontend *fe, u32 *bandwidth)
4057{
4058 struct mxl5005s_state *state = fe->tuner_priv;
4059 dprintk(1, "%s()\n", __func__);
4060
4061 *bandwidth = state->Chan_Bandwidth;
4062
4063 return 0;
4064}
4065
4066static int mxl5005s_release(struct dvb_frontend *fe)
4067{
4068 dprintk(1, "%s()\n", __func__);
4069 kfree(fe->tuner_priv);
4070 fe->tuner_priv = NULL;
4071 return 0;
4072}
4073
4074static const struct dvb_tuner_ops mxl5005s_tuner_ops = {
4075 .info = {
4076 .name = "MaxLinear MXL5005S",
4077 .frequency_min = 48000000,
4078 .frequency_max = 860000000,
4079 .frequency_step = 50000,
4080 },
4081
4082 .release = mxl5005s_release,
4083 .init = mxl5005s_init,
4084
4085 .set_params = mxl5005s_set_params,
4086 .get_frequency = mxl5005s_get_frequency,
4087 .get_bandwidth = mxl5005s_get_bandwidth,
4088};
4089
4090struct dvb_frontend *mxl5005s_attach(struct dvb_frontend *fe,
4091 struct i2c_adapter *i2c,
4092 struct mxl5005s_config *config)
4093{
4094 struct mxl5005s_state *state = NULL;
4095 dprintk(1, "%s()\n", __func__);
4096
4097 state = kzalloc(sizeof(struct mxl5005s_state), GFP_KERNEL);
4098 if (state == NULL)
4099 return NULL;
4100
4101 state->frontend = fe;
4102 state->config = config;
4103 state->i2c = i2c;
4104
4105 printk(KERN_INFO "MXL5005S: Attached at address 0x%02x\n",
4106 config->i2c_address);
4107
4108 memcpy(&fe->ops.tuner_ops, &mxl5005s_tuner_ops,
4109 sizeof(struct dvb_tuner_ops));
4110
4111 fe->tuner_priv = state;
4112 return fe;
4113}
4114EXPORT_SYMBOL(mxl5005s_attach);
4115
4116MODULE_DESCRIPTION("MaxLinear MXL5005S silicon tuner driver");
4117MODULE_AUTHOR("Steven Toth");
4118MODULE_LICENSE("GPL");
diff --git a/drivers/media/common/tuners/mxl5005s.h b/drivers/media/common/tuners/mxl5005s.h
new file mode 100644
index 00000000000..fc8a1ffc53b
--- /dev/null
+++ b/drivers/media/common/tuners/mxl5005s.h
@@ -0,0 +1,135 @@
1/*
2 MaxLinear MXL5005S VSB/QAM/DVBT tuner driver
3
4 Copyright (C) 2008 MaxLinear
5 Copyright (C) 2008 Steven Toth <stoth@linuxtv.org>
6
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2 of the License, or
10 (at your option) any later version.
11
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
16
17 You should have received a copy of the GNU General Public License
18 along with this program; if not, write to the Free Software
19 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
20
21*/
22
23#ifndef __MXL5005S_H
24#define __MXL5005S_H
25
26#include <linux/i2c.h>
27#include "dvb_frontend.h"
28
29struct mxl5005s_config {
30
31 /* 7 bit i2c address */
32 u8 i2c_address;
33
34#define IF_FREQ_4570000HZ 4570000
35#define IF_FREQ_4571429HZ 4571429
36#define IF_FREQ_5380000HZ 5380000
37#define IF_FREQ_36000000HZ 36000000
38#define IF_FREQ_36125000HZ 36125000
39#define IF_FREQ_36166667HZ 36166667
40#define IF_FREQ_44000000HZ 44000000
41 u32 if_freq;
42
43#define CRYSTAL_FREQ_4000000HZ 4000000
44#define CRYSTAL_FREQ_16000000HZ 16000000
45#define CRYSTAL_FREQ_25000000HZ 25000000
46#define CRYSTAL_FREQ_28800000HZ 28800000
47 u32 xtal_freq;
48
49#define MXL_DUAL_AGC 0
50#define MXL_SINGLE_AGC 1
51 u8 agc_mode;
52
53#define MXL_TF_DEFAULT 0
54#define MXL_TF_OFF 1
55#define MXL_TF_C 2
56#define MXL_TF_C_H 3
57#define MXL_TF_D 4
58#define MXL_TF_D_L 5
59#define MXL_TF_E 6
60#define MXL_TF_F 7
61#define MXL_TF_E_2 8
62#define MXL_TF_E_NA 9
63#define MXL_TF_G 10
64 u8 tracking_filter;
65
66#define MXL_RSSI_DISABLE 0
67#define MXL_RSSI_ENABLE 1
68 u8 rssi_enable;
69
70#define MXL_CAP_SEL_DISABLE 0
71#define MXL_CAP_SEL_ENABLE 1
72 u8 cap_select;
73
74#define MXL_DIV_OUT_1 0
75#define MXL_DIV_OUT_4 1
76 u8 div_out;
77
78#define MXL_CLOCK_OUT_DISABLE 0
79#define MXL_CLOCK_OUT_ENABLE 1
80 u8 clock_out;
81
82#define MXL5005S_IF_OUTPUT_LOAD_200_OHM 200
83#define MXL5005S_IF_OUTPUT_LOAD_300_OHM 300
84 u32 output_load;
85
86#define MXL5005S_TOP_5P5 55
87#define MXL5005S_TOP_7P2 72
88#define MXL5005S_TOP_9P2 92
89#define MXL5005S_TOP_11P0 110
90#define MXL5005S_TOP_12P9 129
91#define MXL5005S_TOP_14P7 147
92#define MXL5005S_TOP_16P8 168
93#define MXL5005S_TOP_19P4 194
94#define MXL5005S_TOP_21P2 212
95#define MXL5005S_TOP_23P2 232
96#define MXL5005S_TOP_25P2 252
97#define MXL5005S_TOP_27P1 271
98#define MXL5005S_TOP_29P2 292
99#define MXL5005S_TOP_31P7 317
100#define MXL5005S_TOP_34P9 349
101 u32 top;
102
103#define MXL_ANALOG_MODE 0
104#define MXL_DIGITAL_MODE 1
105 u8 mod_mode;
106
107#define MXL_ZERO_IF 0
108#define MXL_LOW_IF 1
109 u8 if_mode;
110
111 /* Some boards need to override the built-in logic for determining
112 the gain when in QAM mode (the HVR-1600 is one such case) */
113 u8 qam_gain;
114
115 /* Stuff I don't know what to do with */
116 u8 AgcMasterByte;
117};
118
119#if defined(CONFIG_MEDIA_TUNER_MXL5005S) || \
120 (defined(CONFIG_MEDIA_TUNER_MXL5005S_MODULE) && defined(MODULE))
121extern struct dvb_frontend *mxl5005s_attach(struct dvb_frontend *fe,
122 struct i2c_adapter *i2c,
123 struct mxl5005s_config *config);
124#else
125static inline struct dvb_frontend *mxl5005s_attach(struct dvb_frontend *fe,
126 struct i2c_adapter *i2c,
127 struct mxl5005s_config *config)
128{
129 printk(KERN_WARNING "%s: driver disabled by Kconfig\n", __func__);
130 return NULL;
131}
132#endif /* CONFIG_DVB_TUNER_MXL5005S */
133
134#endif /* __MXL5005S_H */
135
diff --git a/drivers/media/common/tuners/mxl5007t.c b/drivers/media/common/tuners/mxl5007t.c
new file mode 100644
index 00000000000..7eb1bf75cd0
--- /dev/null
+++ b/drivers/media/common/tuners/mxl5007t.c
@@ -0,0 +1,883 @@
1/*
2 * mxl5007t.c - driver for the MaxLinear MxL5007T silicon tuner
3 *
4 * Copyright (C) 2008, 2009 Michael Krufky <mkrufky@linuxtv.org>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, write to the Free Software
18 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
19 */
20
21#include <linux/i2c.h>
22#include <linux/types.h>
23#include <linux/videodev2.h>
24#include "tuner-i2c.h"
25#include "mxl5007t.h"
26
27static DEFINE_MUTEX(mxl5007t_list_mutex);
28static LIST_HEAD(hybrid_tuner_instance_list);
29
30static int mxl5007t_debug;
31module_param_named(debug, mxl5007t_debug, int, 0644);
32MODULE_PARM_DESC(debug, "set debug level");
33
34/* ------------------------------------------------------------------------- */
35
36#define mxl_printk(kern, fmt, arg...) \
37 printk(kern "%s: " fmt "\n", __func__, ##arg)
38
39#define mxl_err(fmt, arg...) \
40 mxl_printk(KERN_ERR, "%d: " fmt, __LINE__, ##arg)
41
42#define mxl_warn(fmt, arg...) \
43 mxl_printk(KERN_WARNING, fmt, ##arg)
44
45#define mxl_info(fmt, arg...) \
46 mxl_printk(KERN_INFO, fmt, ##arg)
47
48#define mxl_debug(fmt, arg...) \
49({ \
50 if (mxl5007t_debug) \
51 mxl_printk(KERN_DEBUG, fmt, ##arg); \
52})
53
54#define mxl_fail(ret) \
55({ \
56 int __ret; \
57 __ret = (ret < 0); \
58 if (__ret) \
59 mxl_printk(KERN_ERR, "error %d on line %d", \
60 ret, __LINE__); \
61 __ret; \
62})
63
64/* ------------------------------------------------------------------------- */
65
66#define MHz 1000000
67
68enum mxl5007t_mode {
69 MxL_MODE_ISDBT = 0,
70 MxL_MODE_DVBT = 1,
71 MxL_MODE_ATSC = 2,
72 MxL_MODE_CABLE = 0x10,
73};
74
75enum mxl5007t_chip_version {
76 MxL_UNKNOWN_ID = 0x00,
77 MxL_5007_V1_F1 = 0x11,
78 MxL_5007_V1_F2 = 0x12,
79 MxL_5007_V4 = 0x14,
80 MxL_5007_V2_100_F1 = 0x21,
81 MxL_5007_V2_100_F2 = 0x22,
82 MxL_5007_V2_200_F1 = 0x23,
83 MxL_5007_V2_200_F2 = 0x24,
84};
85
86struct reg_pair_t {
87 u8 reg;
88 u8 val;
89};
90
91/* ------------------------------------------------------------------------- */
92
93static struct reg_pair_t init_tab[] = {
94 { 0x02, 0x06 },
95 { 0x03, 0x48 },
96 { 0x05, 0x04 },
97 { 0x06, 0x10 },
98 { 0x2e, 0x15 }, /* OVERRIDE */
99 { 0x30, 0x10 }, /* OVERRIDE */
100 { 0x45, 0x58 }, /* OVERRIDE */
101 { 0x48, 0x19 }, /* OVERRIDE */
102 { 0x52, 0x03 }, /* OVERRIDE */
103 { 0x53, 0x44 }, /* OVERRIDE */
104 { 0x6a, 0x4b }, /* OVERRIDE */
105 { 0x76, 0x00 }, /* OVERRIDE */
106 { 0x78, 0x18 }, /* OVERRIDE */
107 { 0x7a, 0x17 }, /* OVERRIDE */
108 { 0x85, 0x06 }, /* OVERRIDE */
109 { 0x01, 0x01 }, /* TOP_MASTER_ENABLE */
110 { 0, 0 }
111};
112
113static struct reg_pair_t init_tab_cable[] = {
114 { 0x02, 0x06 },
115 { 0x03, 0x48 },
116 { 0x05, 0x04 },
117 { 0x06, 0x10 },
118 { 0x09, 0x3f },
119 { 0x0a, 0x3f },
120 { 0x0b, 0x3f },
121 { 0x2e, 0x15 }, /* OVERRIDE */
122 { 0x30, 0x10 }, /* OVERRIDE */
123 { 0x45, 0x58 }, /* OVERRIDE */
124 { 0x48, 0x19 }, /* OVERRIDE */
125 { 0x52, 0x03 }, /* OVERRIDE */
126 { 0x53, 0x44 }, /* OVERRIDE */
127 { 0x6a, 0x4b }, /* OVERRIDE */
128 { 0x76, 0x00 }, /* OVERRIDE */
129 { 0x78, 0x18 }, /* OVERRIDE */
130 { 0x7a, 0x17 }, /* OVERRIDE */
131 { 0x85, 0x06 }, /* OVERRIDE */
132 { 0x01, 0x01 }, /* TOP_MASTER_ENABLE */
133 { 0, 0 }
134};
135
136/* ------------------------------------------------------------------------- */
137
138static struct reg_pair_t reg_pair_rftune[] = {
139 { 0x0f, 0x00 }, /* abort tune */
140 { 0x0c, 0x15 },
141 { 0x0d, 0x40 },
142 { 0x0e, 0x0e },
143 { 0x1f, 0x87 }, /* OVERRIDE */
144 { 0x20, 0x1f }, /* OVERRIDE */
145 { 0x21, 0x87 }, /* OVERRIDE */
146 { 0x22, 0x1f }, /* OVERRIDE */
147 { 0x80, 0x01 }, /* freq dependent */
148 { 0x0f, 0x01 }, /* start tune */
149 { 0, 0 }
150};
151
152/* ------------------------------------------------------------------------- */
153
154struct mxl5007t_state {
155 struct list_head hybrid_tuner_instance_list;
156 struct tuner_i2c_props i2c_props;
157
158 struct mutex lock;
159
160 struct mxl5007t_config *config;
161
162 enum mxl5007t_chip_version chip_id;
163
164 struct reg_pair_t tab_init[ARRAY_SIZE(init_tab)];
165 struct reg_pair_t tab_init_cable[ARRAY_SIZE(init_tab_cable)];
166 struct reg_pair_t tab_rftune[ARRAY_SIZE(reg_pair_rftune)];
167
168 u32 frequency;
169 u32 bandwidth;
170};
171
172/* ------------------------------------------------------------------------- */
173
174/* called by _init and _rftun to manipulate the register arrays */
175
176static void set_reg_bits(struct reg_pair_t *reg_pair, u8 reg, u8 mask, u8 val)
177{
178 unsigned int i = 0;
179
180 while (reg_pair[i].reg || reg_pair[i].val) {
181 if (reg_pair[i].reg == reg) {
182 reg_pair[i].val &= ~mask;
183 reg_pair[i].val |= val;
184 }
185 i++;
186
187 }
188 return;
189}
190
191static void copy_reg_bits(struct reg_pair_t *reg_pair1,
192 struct reg_pair_t *reg_pair2)
193{
194 unsigned int i, j;
195
196 i = j = 0;
197
198 while (reg_pair1[i].reg || reg_pair1[i].val) {
199 while (reg_pair2[j].reg || reg_pair2[j].val) {
200 if (reg_pair1[i].reg != reg_pair2[j].reg) {
201 j++;
202 continue;
203 }
204 reg_pair2[j].val = reg_pair1[i].val;
205 break;
206 }
207 i++;
208 }
209 return;
210}
211
212/* ------------------------------------------------------------------------- */
213
214static void mxl5007t_set_mode_bits(struct mxl5007t_state *state,
215 enum mxl5007t_mode mode,
216 s32 if_diff_out_level)
217{
218 switch (mode) {
219 case MxL_MODE_ATSC:
220 set_reg_bits(state->tab_init, 0x06, 0x1f, 0x12);
221 break;
222 case MxL_MODE_DVBT:
223 set_reg_bits(state->tab_init, 0x06, 0x1f, 0x11);
224 break;
225 case MxL_MODE_ISDBT:
226 set_reg_bits(state->tab_init, 0x06, 0x1f, 0x10);
227 break;
228 case MxL_MODE_CABLE:
229 set_reg_bits(state->tab_init_cable, 0x09, 0xff, 0xc1);
230 set_reg_bits(state->tab_init_cable, 0x0a, 0xff,
231 8 - if_diff_out_level);
232 set_reg_bits(state->tab_init_cable, 0x0b, 0xff, 0x17);
233 break;
234 default:
235 mxl_fail(-EINVAL);
236 }
237 return;
238}
239
240static void mxl5007t_set_if_freq_bits(struct mxl5007t_state *state,
241 enum mxl5007t_if_freq if_freq,
242 int invert_if)
243{
244 u8 val;
245
246 switch (if_freq) {
247 case MxL_IF_4_MHZ:
248 val = 0x00;
249 break;
250 case MxL_IF_4_5_MHZ:
251 val = 0x02;
252 break;
253 case MxL_IF_4_57_MHZ:
254 val = 0x03;
255 break;
256 case MxL_IF_5_MHZ:
257 val = 0x04;
258 break;
259 case MxL_IF_5_38_MHZ:
260 val = 0x05;
261 break;
262 case MxL_IF_6_MHZ:
263 val = 0x06;
264 break;
265 case MxL_IF_6_28_MHZ:
266 val = 0x07;
267 break;
268 case MxL_IF_9_1915_MHZ:
269 val = 0x08;
270 break;
271 case MxL_IF_35_25_MHZ:
272 val = 0x09;
273 break;
274 case MxL_IF_36_15_MHZ:
275 val = 0x0a;
276 break;
277 case MxL_IF_44_MHZ:
278 val = 0x0b;
279 break;
280 default:
281 mxl_fail(-EINVAL);
282 return;
283 }
284 set_reg_bits(state->tab_init, 0x02, 0x0f, val);
285
286 /* set inverted IF or normal IF */
287 set_reg_bits(state->tab_init, 0x02, 0x10, invert_if ? 0x10 : 0x00);
288
289 return;
290}
291
292static void mxl5007t_set_xtal_freq_bits(struct mxl5007t_state *state,
293 enum mxl5007t_xtal_freq xtal_freq)
294{
295 switch (xtal_freq) {
296 case MxL_XTAL_16_MHZ:
297 /* select xtal freq & ref freq */
298 set_reg_bits(state->tab_init, 0x03, 0xf0, 0x00);
299 set_reg_bits(state->tab_init, 0x05, 0x0f, 0x00);
300 break;
301 case MxL_XTAL_20_MHZ:
302 set_reg_bits(state->tab_init, 0x03, 0xf0, 0x10);
303 set_reg_bits(state->tab_init, 0x05, 0x0f, 0x01);
304 break;
305 case MxL_XTAL_20_25_MHZ:
306 set_reg_bits(state->tab_init, 0x03, 0xf0, 0x20);
307 set_reg_bits(state->tab_init, 0x05, 0x0f, 0x02);
308 break;
309 case MxL_XTAL_20_48_MHZ:
310 set_reg_bits(state->tab_init, 0x03, 0xf0, 0x30);
311 set_reg_bits(state->tab_init, 0x05, 0x0f, 0x03);
312 break;
313 case MxL_XTAL_24_MHZ:
314 set_reg_bits(state->tab_init, 0x03, 0xf0, 0x40);
315 set_reg_bits(state->tab_init, 0x05, 0x0f, 0x04);
316 break;
317 case MxL_XTAL_25_MHZ:
318 set_reg_bits(state->tab_init, 0x03, 0xf0, 0x50);
319 set_reg_bits(state->tab_init, 0x05, 0x0f, 0x05);
320 break;
321 case MxL_XTAL_25_14_MHZ:
322 set_reg_bits(state->tab_init, 0x03, 0xf0, 0x60);
323 set_reg_bits(state->tab_init, 0x05, 0x0f, 0x06);
324 break;
325 case MxL_XTAL_27_MHZ:
326 set_reg_bits(state->tab_init, 0x03, 0xf0, 0x70);
327 set_reg_bits(state->tab_init, 0x05, 0x0f, 0x07);
328 break;
329 case MxL_XTAL_28_8_MHZ:
330 set_reg_bits(state->tab_init, 0x03, 0xf0, 0x80);
331 set_reg_bits(state->tab_init, 0x05, 0x0f, 0x08);
332 break;
333 case MxL_XTAL_32_MHZ:
334 set_reg_bits(state->tab_init, 0x03, 0xf0, 0x90);
335 set_reg_bits(state->tab_init, 0x05, 0x0f, 0x09);
336 break;
337 case MxL_XTAL_40_MHZ:
338 set_reg_bits(state->tab_init, 0x03, 0xf0, 0xa0);
339 set_reg_bits(state->tab_init, 0x05, 0x0f, 0x0a);
340 break;
341 case MxL_XTAL_44_MHZ:
342 set_reg_bits(state->tab_init, 0x03, 0xf0, 0xb0);
343 set_reg_bits(state->tab_init, 0x05, 0x0f, 0x0b);
344 break;
345 case MxL_XTAL_48_MHZ:
346 set_reg_bits(state->tab_init, 0x03, 0xf0, 0xc0);
347 set_reg_bits(state->tab_init, 0x05, 0x0f, 0x0c);
348 break;
349 case MxL_XTAL_49_3811_MHZ:
350 set_reg_bits(state->tab_init, 0x03, 0xf0, 0xd0);
351 set_reg_bits(state->tab_init, 0x05, 0x0f, 0x0d);
352 break;
353 default:
354 mxl_fail(-EINVAL);
355 return;
356 }
357
358 return;
359}
360
361static struct reg_pair_t *mxl5007t_calc_init_regs(struct mxl5007t_state *state,
362 enum mxl5007t_mode mode)
363{
364 struct mxl5007t_config *cfg = state->config;
365
366 memcpy(&state->tab_init, &init_tab, sizeof(init_tab));
367 memcpy(&state->tab_init_cable, &init_tab_cable, sizeof(init_tab_cable));
368
369 mxl5007t_set_mode_bits(state, mode, cfg->if_diff_out_level);
370 mxl5007t_set_if_freq_bits(state, cfg->if_freq_hz, cfg->invert_if);
371 mxl5007t_set_xtal_freq_bits(state, cfg->xtal_freq_hz);
372
373 set_reg_bits(state->tab_init, 0x04, 0x01, cfg->loop_thru_enable);
374 set_reg_bits(state->tab_init, 0x03, 0x08, cfg->clk_out_enable << 3);
375 set_reg_bits(state->tab_init, 0x03, 0x07, cfg->clk_out_amp);
376
377 if (mode >= MxL_MODE_CABLE) {
378 copy_reg_bits(state->tab_init, state->tab_init_cable);
379 return state->tab_init_cable;
380 } else
381 return state->tab_init;
382}
383
384/* ------------------------------------------------------------------------- */
385
386enum mxl5007t_bw_mhz {
387 MxL_BW_6MHz = 6,
388 MxL_BW_7MHz = 7,
389 MxL_BW_8MHz = 8,
390};
391
392static void mxl5007t_set_bw_bits(struct mxl5007t_state *state,
393 enum mxl5007t_bw_mhz bw)
394{
395 u8 val;
396
397 switch (bw) {
398 case MxL_BW_6MHz:
399 val = 0x15; /* set DIG_MODEINDEX, DIG_MODEINDEX_A,
400 * and DIG_MODEINDEX_CSF */
401 break;
402 case MxL_BW_7MHz:
403 val = 0x2a;
404 break;
405 case MxL_BW_8MHz:
406 val = 0x3f;
407 break;
408 default:
409 mxl_fail(-EINVAL);
410 return;
411 }
412 set_reg_bits(state->tab_rftune, 0x0c, 0x3f, val);
413
414 return;
415}
416
417static struct
418reg_pair_t *mxl5007t_calc_rf_tune_regs(struct mxl5007t_state *state,
419 u32 rf_freq, enum mxl5007t_bw_mhz bw)
420{
421 u32 dig_rf_freq = 0;
422 u32 temp;
423 u32 frac_divider = 1000000;
424 unsigned int i;
425
426 memcpy(&state->tab_rftune, &reg_pair_rftune, sizeof(reg_pair_rftune));
427
428 mxl5007t_set_bw_bits(state, bw);
429
430 /* Convert RF frequency into 16 bits =>
431 * 10 bit integer (MHz) + 6 bit fraction */
432 dig_rf_freq = rf_freq / MHz;
433
434 temp = rf_freq % MHz;
435
436 for (i = 0; i < 6; i++) {
437 dig_rf_freq <<= 1;
438 frac_divider /= 2;
439 if (temp > frac_divider) {
440 temp -= frac_divider;
441 dig_rf_freq++;
442 }
443 }
444
445 /* add to have shift center point by 7.8124 kHz */
446 if (temp > 7812)
447 dig_rf_freq++;
448
449 set_reg_bits(state->tab_rftune, 0x0d, 0xff, (u8) dig_rf_freq);
450 set_reg_bits(state->tab_rftune, 0x0e, 0xff, (u8) (dig_rf_freq >> 8));
451
452 if (rf_freq >= 333000000)
453 set_reg_bits(state->tab_rftune, 0x80, 0x40, 0x40);
454
455 return state->tab_rftune;
456}
457
458/* ------------------------------------------------------------------------- */
459
460static int mxl5007t_write_reg(struct mxl5007t_state *state, u8 reg, u8 val)
461{
462 u8 buf[] = { reg, val };
463 struct i2c_msg msg = { .addr = state->i2c_props.addr, .flags = 0,
464 .buf = buf, .len = 2 };
465 int ret;
466
467 ret = i2c_transfer(state->i2c_props.adap, &msg, 1);
468 if (ret != 1) {
469 mxl_err("failed!");
470 return -EREMOTEIO;
471 }
472 return 0;
473}
474
475static int mxl5007t_write_regs(struct mxl5007t_state *state,
476 struct reg_pair_t *reg_pair)
477{
478 unsigned int i = 0;
479 int ret = 0;
480
481 while ((ret == 0) && (reg_pair[i].reg || reg_pair[i].val)) {
482 ret = mxl5007t_write_reg(state,
483 reg_pair[i].reg, reg_pair[i].val);
484 i++;
485 }
486 return ret;
487}
488
489static int mxl5007t_read_reg(struct mxl5007t_state *state, u8 reg, u8 *val)
490{
491 struct i2c_msg msg[] = {
492 { .addr = state->i2c_props.addr, .flags = 0,
493 .buf = &reg, .len = 1 },
494 { .addr = state->i2c_props.addr, .flags = I2C_M_RD,
495 .buf = val, .len = 1 },
496 };
497 int ret;
498
499 ret = i2c_transfer(state->i2c_props.adap, msg, 2);
500 if (ret != 2) {
501 mxl_err("failed!");
502 return -EREMOTEIO;
503 }
504 return 0;
505}
506
507static int mxl5007t_soft_reset(struct mxl5007t_state *state)
508{
509 u8 d = 0xff;
510 struct i2c_msg msg = {
511 .addr = state->i2c_props.addr, .flags = 0,
512 .buf = &d, .len = 1
513 };
514 int ret = i2c_transfer(state->i2c_props.adap, &msg, 1);
515
516 if (ret != 1) {
517 mxl_err("failed!");
518 return -EREMOTEIO;
519 }
520 return 0;
521}
522
523static int mxl5007t_tuner_init(struct mxl5007t_state *state,
524 enum mxl5007t_mode mode)
525{
526 struct reg_pair_t *init_regs;
527 int ret;
528
529 ret = mxl5007t_soft_reset(state);
530 if (mxl_fail(ret))
531 goto fail;
532
533 /* calculate initialization reg array */
534 init_regs = mxl5007t_calc_init_regs(state, mode);
535
536 ret = mxl5007t_write_regs(state, init_regs);
537 if (mxl_fail(ret))
538 goto fail;
539 mdelay(1);
540fail:
541 return ret;
542}
543
544static int mxl5007t_tuner_rf_tune(struct mxl5007t_state *state, u32 rf_freq_hz,
545 enum mxl5007t_bw_mhz bw)
546{
547 struct reg_pair_t *rf_tune_regs;
548 int ret;
549
550 /* calculate channel change reg array */
551 rf_tune_regs = mxl5007t_calc_rf_tune_regs(state, rf_freq_hz, bw);
552
553 ret = mxl5007t_write_regs(state, rf_tune_regs);
554 if (mxl_fail(ret))
555 goto fail;
556 msleep(3);
557fail:
558 return ret;
559}
560
561/* ------------------------------------------------------------------------- */
562
563static int mxl5007t_synth_lock_status(struct mxl5007t_state *state,
564 int *rf_locked, int *ref_locked)
565{
566 u8 d;
567 int ret;
568
569 *rf_locked = 0;
570 *ref_locked = 0;
571
572 ret = mxl5007t_read_reg(state, 0xd8, &d);
573 if (mxl_fail(ret))
574 goto fail;
575
576 if ((d & 0x0c) == 0x0c)
577 *rf_locked = 1;
578
579 if ((d & 0x03) == 0x03)
580 *ref_locked = 1;
581fail:
582 return ret;
583}
584
585/* ------------------------------------------------------------------------- */
586
587static int mxl5007t_get_status(struct dvb_frontend *fe, u32 *status)
588{
589 struct mxl5007t_state *state = fe->tuner_priv;
590 int rf_locked, ref_locked, ret;
591
592 *status = 0;
593
594 if (fe->ops.i2c_gate_ctrl)
595 fe->ops.i2c_gate_ctrl(fe, 1);
596
597 ret = mxl5007t_synth_lock_status(state, &rf_locked, &ref_locked);
598 if (mxl_fail(ret))
599 goto fail;
600 mxl_debug("%s%s", rf_locked ? "rf locked " : "",
601 ref_locked ? "ref locked" : "");
602
603 if ((rf_locked) || (ref_locked))
604 *status |= TUNER_STATUS_LOCKED;
605fail:
606 if (fe->ops.i2c_gate_ctrl)
607 fe->ops.i2c_gate_ctrl(fe, 0);
608
609 return ret;
610}
611
612/* ------------------------------------------------------------------------- */
613
614static int mxl5007t_set_params(struct dvb_frontend *fe,
615 struct dvb_frontend_parameters *params)
616{
617 struct mxl5007t_state *state = fe->tuner_priv;
618 enum mxl5007t_bw_mhz bw;
619 enum mxl5007t_mode mode;
620 int ret;
621 u32 freq = params->frequency;
622
623 if (fe->ops.info.type == FE_ATSC) {
624 switch (params->u.vsb.modulation) {
625 case VSB_8:
626 case VSB_16:
627 mode = MxL_MODE_ATSC;
628 break;
629 case QAM_64:
630 case QAM_256:
631 mode = MxL_MODE_CABLE;
632 break;
633 default:
634 mxl_err("modulation not set!");
635 return -EINVAL;
636 }
637 bw = MxL_BW_6MHz;
638 } else if (fe->ops.info.type == FE_OFDM) {
639 switch (params->u.ofdm.bandwidth) {
640 case BANDWIDTH_6_MHZ:
641 bw = MxL_BW_6MHz;
642 break;
643 case BANDWIDTH_7_MHZ:
644 bw = MxL_BW_7MHz;
645 break;
646 case BANDWIDTH_8_MHZ:
647 bw = MxL_BW_8MHz;
648 break;
649 default:
650 mxl_err("bandwidth not set!");
651 return -EINVAL;
652 }
653 mode = MxL_MODE_DVBT;
654 } else {
655 mxl_err("modulation type not supported!");
656 return -EINVAL;
657 }
658
659 if (fe->ops.i2c_gate_ctrl)
660 fe->ops.i2c_gate_ctrl(fe, 1);
661
662 mutex_lock(&state->lock);
663
664 ret = mxl5007t_tuner_init(state, mode);
665 if (mxl_fail(ret))
666 goto fail;
667
668 ret = mxl5007t_tuner_rf_tune(state, freq, bw);
669 if (mxl_fail(ret))
670 goto fail;
671
672 state->frequency = freq;
673 state->bandwidth = (fe->ops.info.type == FE_OFDM) ?
674 params->u.ofdm.bandwidth : 0;
675fail:
676 mutex_unlock(&state->lock);
677
678 if (fe->ops.i2c_gate_ctrl)
679 fe->ops.i2c_gate_ctrl(fe, 0);
680
681 return ret;
682}
683
684/* ------------------------------------------------------------------------- */
685
686static int mxl5007t_init(struct dvb_frontend *fe)
687{
688 struct mxl5007t_state *state = fe->tuner_priv;
689 int ret;
690
691 if (fe->ops.i2c_gate_ctrl)
692 fe->ops.i2c_gate_ctrl(fe, 1);
693
694 /* wake from standby */
695 ret = mxl5007t_write_reg(state, 0x01, 0x01);
696 mxl_fail(ret);
697
698 if (fe->ops.i2c_gate_ctrl)
699 fe->ops.i2c_gate_ctrl(fe, 0);
700
701 return ret;
702}
703
704static int mxl5007t_sleep(struct dvb_frontend *fe)
705{
706 struct mxl5007t_state *state = fe->tuner_priv;
707 int ret;
708
709 if (fe->ops.i2c_gate_ctrl)
710 fe->ops.i2c_gate_ctrl(fe, 1);
711
712 /* enter standby mode */
713 ret = mxl5007t_write_reg(state, 0x01, 0x00);
714 mxl_fail(ret);
715 ret = mxl5007t_write_reg(state, 0x0f, 0x00);
716 mxl_fail(ret);
717
718 if (fe->ops.i2c_gate_ctrl)
719 fe->ops.i2c_gate_ctrl(fe, 0);
720
721 return ret;
722}
723
724/* ------------------------------------------------------------------------- */
725
726static int mxl5007t_get_frequency(struct dvb_frontend *fe, u32 *frequency)
727{
728 struct mxl5007t_state *state = fe->tuner_priv;
729 *frequency = state->frequency;
730 return 0;
731}
732
733static int mxl5007t_get_bandwidth(struct dvb_frontend *fe, u32 *bandwidth)
734{
735 struct mxl5007t_state *state = fe->tuner_priv;
736 *bandwidth = state->bandwidth;
737 return 0;
738}
739
740static int mxl5007t_release(struct dvb_frontend *fe)
741{
742 struct mxl5007t_state *state = fe->tuner_priv;
743
744 mutex_lock(&mxl5007t_list_mutex);
745
746 if (state)
747 hybrid_tuner_release_state(state);
748
749 mutex_unlock(&mxl5007t_list_mutex);
750
751 fe->tuner_priv = NULL;
752
753 return 0;
754}
755
756/* ------------------------------------------------------------------------- */
757
758static struct dvb_tuner_ops mxl5007t_tuner_ops = {
759 .info = {
760 .name = "MaxLinear MxL5007T",
761 },
762 .init = mxl5007t_init,
763 .sleep = mxl5007t_sleep,
764 .set_params = mxl5007t_set_params,
765 .get_status = mxl5007t_get_status,
766 .get_frequency = mxl5007t_get_frequency,
767 .get_bandwidth = mxl5007t_get_bandwidth,
768 .release = mxl5007t_release,
769};
770
771static int mxl5007t_get_chip_id(struct mxl5007t_state *state)
772{
773 char *name;
774 int ret;
775 u8 id;
776
777 ret = mxl5007t_read_reg(state, 0xd9, &id);
778 if (mxl_fail(ret))
779 goto fail;
780
781 switch (id) {
782 case MxL_5007_V1_F1:
783 name = "MxL5007.v1.f1";
784 break;
785 case MxL_5007_V1_F2:
786 name = "MxL5007.v1.f2";
787 break;
788 case MxL_5007_V2_100_F1:
789 name = "MxL5007.v2.100.f1";
790 break;
791 case MxL_5007_V2_100_F2:
792 name = "MxL5007.v2.100.f2";
793 break;
794 case MxL_5007_V2_200_F1:
795 name = "MxL5007.v2.200.f1";
796 break;
797 case MxL_5007_V2_200_F2:
798 name = "MxL5007.v2.200.f2";
799 break;
800 case MxL_5007_V4:
801 name = "MxL5007T.v4";
802 break;
803 default:
804 name = "MxL5007T";
805 printk(KERN_WARNING "%s: unknown rev (%02x)\n", __func__, id);
806 id = MxL_UNKNOWN_ID;
807 }
808 state->chip_id = id;
809 mxl_info("%s detected @ %d-%04x", name,
810 i2c_adapter_id(state->i2c_props.adap),
811 state->i2c_props.addr);
812 return 0;
813fail:
814 mxl_warn("unable to identify device @ %d-%04x",
815 i2c_adapter_id(state->i2c_props.adap),
816 state->i2c_props.addr);
817
818 state->chip_id = MxL_UNKNOWN_ID;
819 return ret;
820}
821
822struct dvb_frontend *mxl5007t_attach(struct dvb_frontend *fe,
823 struct i2c_adapter *i2c, u8 addr,
824 struct mxl5007t_config *cfg)
825{
826 struct mxl5007t_state *state = NULL;
827 int instance, ret;
828
829 mutex_lock(&mxl5007t_list_mutex);
830 instance = hybrid_tuner_request_state(struct mxl5007t_state, state,
831 hybrid_tuner_instance_list,
832 i2c, addr, "mxl5007t");
833 switch (instance) {
834 case 0:
835 goto fail;
836 case 1:
837 /* new tuner instance */
838 state->config = cfg;
839
840 mutex_init(&state->lock);
841
842 if (fe->ops.i2c_gate_ctrl)
843 fe->ops.i2c_gate_ctrl(fe, 1);
844
845 ret = mxl5007t_get_chip_id(state);
846
847 if (fe->ops.i2c_gate_ctrl)
848 fe->ops.i2c_gate_ctrl(fe, 0);
849
850 /* check return value of mxl5007t_get_chip_id */
851 if (mxl_fail(ret))
852 goto fail;
853 break;
854 default:
855 /* existing tuner instance */
856 break;
857 }
858 fe->tuner_priv = state;
859 mutex_unlock(&mxl5007t_list_mutex);
860
861 memcpy(&fe->ops.tuner_ops, &mxl5007t_tuner_ops,
862 sizeof(struct dvb_tuner_ops));
863
864 return fe;
865fail:
866 mutex_unlock(&mxl5007t_list_mutex);
867
868 mxl5007t_release(fe);
869 return NULL;
870}
871EXPORT_SYMBOL_GPL(mxl5007t_attach);
872MODULE_DESCRIPTION("MaxLinear MxL5007T Silicon IC tuner driver");
873MODULE_AUTHOR("Michael Krufky <mkrufky@linuxtv.org>");
874MODULE_LICENSE("GPL");
875MODULE_VERSION("0.2");
876
877/*
878 * Overrides for Emacs so that we follow Linus's tabbing style.
879 * ---------------------------------------------------------------------------
880 * Local variables:
881 * c-basic-offset: 8
882 * End:
883 */
diff --git a/drivers/media/common/tuners/mxl5007t.h b/drivers/media/common/tuners/mxl5007t.h
new file mode 100644
index 00000000000..aa3eea0b526
--- /dev/null
+++ b/drivers/media/common/tuners/mxl5007t.h
@@ -0,0 +1,104 @@
1/*
2 * mxl5007t.h - driver for the MaxLinear MxL5007T silicon tuner
3 *
4 * Copyright (C) 2008 Michael Krufky <mkrufky@linuxtv.org>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, write to the Free Software
18 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
19 */
20
21#ifndef __MXL5007T_H__
22#define __MXL5007T_H__
23
24#include "dvb_frontend.h"
25
26/* ------------------------------------------------------------------------- */
27
28enum mxl5007t_if_freq {
29 MxL_IF_4_MHZ, /* 4000000 */
30 MxL_IF_4_5_MHZ, /* 4500000 */
31 MxL_IF_4_57_MHZ, /* 4570000 */
32 MxL_IF_5_MHZ, /* 5000000 */
33 MxL_IF_5_38_MHZ, /* 5380000 */
34 MxL_IF_6_MHZ, /* 6000000 */
35 MxL_IF_6_28_MHZ, /* 6280000 */
36 MxL_IF_9_1915_MHZ, /* 9191500 */
37 MxL_IF_35_25_MHZ, /* 35250000 */
38 MxL_IF_36_15_MHZ, /* 36150000 */
39 MxL_IF_44_MHZ, /* 44000000 */
40};
41
42enum mxl5007t_xtal_freq {
43 MxL_XTAL_16_MHZ, /* 16000000 */
44 MxL_XTAL_20_MHZ, /* 20000000 */
45 MxL_XTAL_20_25_MHZ, /* 20250000 */
46 MxL_XTAL_20_48_MHZ, /* 20480000 */
47 MxL_XTAL_24_MHZ, /* 24000000 */
48 MxL_XTAL_25_MHZ, /* 25000000 */
49 MxL_XTAL_25_14_MHZ, /* 25140000 */
50 MxL_XTAL_27_MHZ, /* 27000000 */
51 MxL_XTAL_28_8_MHZ, /* 28800000 */
52 MxL_XTAL_32_MHZ, /* 32000000 */
53 MxL_XTAL_40_MHZ, /* 40000000 */
54 MxL_XTAL_44_MHZ, /* 44000000 */
55 MxL_XTAL_48_MHZ, /* 48000000 */
56 MxL_XTAL_49_3811_MHZ, /* 49381100 */
57};
58
59enum mxl5007t_clkout_amp {
60 MxL_CLKOUT_AMP_0_94V = 0,
61 MxL_CLKOUT_AMP_0_53V = 1,
62 MxL_CLKOUT_AMP_0_37V = 2,
63 MxL_CLKOUT_AMP_0_28V = 3,
64 MxL_CLKOUT_AMP_0_23V = 4,
65 MxL_CLKOUT_AMP_0_20V = 5,
66 MxL_CLKOUT_AMP_0_17V = 6,
67 MxL_CLKOUT_AMP_0_15V = 7,
68};
69
70struct mxl5007t_config {
71 s32 if_diff_out_level;
72 enum mxl5007t_clkout_amp clk_out_amp;
73 enum mxl5007t_xtal_freq xtal_freq_hz;
74 enum mxl5007t_if_freq if_freq_hz;
75 unsigned int invert_if:1;
76 unsigned int loop_thru_enable:1;
77 unsigned int clk_out_enable:1;
78};
79
80#if defined(CONFIG_MEDIA_TUNER_MXL5007T) || (defined(CONFIG_MEDIA_TUNER_MXL5007T_MODULE) && defined(MODULE))
81extern struct dvb_frontend *mxl5007t_attach(struct dvb_frontend *fe,
82 struct i2c_adapter *i2c, u8 addr,
83 struct mxl5007t_config *cfg);
84#else
85static inline struct dvb_frontend *mxl5007t_attach(struct dvb_frontend *fe,
86 struct i2c_adapter *i2c,
87 u8 addr,
88 struct mxl5007t_config *cfg)
89{
90 printk(KERN_WARNING "%s: driver disabled by Kconfig\n", __func__);
91 return NULL;
92}
93#endif
94
95#endif /* __MXL5007T_H__ */
96
97/*
98 * Overrides for Emacs so that we follow Linus's tabbing style.
99 * ---------------------------------------------------------------------------
100 * Local variables:
101 * c-basic-offset: 8
102 * End:
103 */
104
diff --git a/drivers/media/common/tuners/qt1010.c b/drivers/media/common/tuners/qt1010.c
new file mode 100644
index 00000000000..9f5dba244cb
--- /dev/null
+++ b/drivers/media/common/tuners/qt1010.c
@@ -0,0 +1,483 @@
1/*
2 * Driver for Quantek QT1010 silicon tuner
3 *
4 * Copyright (C) 2006 Antti Palosaari <crope@iki.fi>
5 * Aapo Tahkola <aet@rasterburn.org>
6 *
7 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation; either version 2 of the License, or
10 * (at your option) any later version.
11 *
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
20 */
21#include "qt1010.h"
22#include "qt1010_priv.h"
23
24static int debug;
25module_param(debug, int, 0644);
26MODULE_PARM_DESC(debug, "Turn on/off debugging (default:off).");
27
28#define dprintk(args...) \
29 do { \
30 if (debug) printk(KERN_DEBUG "QT1010: " args); \
31 } while (0)
32
33/* read single register */
34static int qt1010_readreg(struct qt1010_priv *priv, u8 reg, u8 *val)
35{
36 struct i2c_msg msg[2] = {
37 { .addr = priv->cfg->i2c_address,
38 .flags = 0, .buf = &reg, .len = 1 },
39 { .addr = priv->cfg->i2c_address,
40 .flags = I2C_M_RD, .buf = val, .len = 1 },
41 };
42
43 if (i2c_transfer(priv->i2c, msg, 2) != 2) {
44 printk(KERN_WARNING "qt1010 I2C read failed\n");
45 return -EREMOTEIO;
46 }
47 return 0;
48}
49
50/* write single register */
51static int qt1010_writereg(struct qt1010_priv *priv, u8 reg, u8 val)
52{
53 u8 buf[2] = { reg, val };
54 struct i2c_msg msg = { .addr = priv->cfg->i2c_address,
55 .flags = 0, .buf = buf, .len = 2 };
56
57 if (i2c_transfer(priv->i2c, &msg, 1) != 1) {
58 printk(KERN_WARNING "qt1010 I2C write failed\n");
59 return -EREMOTEIO;
60 }
61 return 0;
62}
63
64/* dump all registers */
65static void qt1010_dump_regs(struct qt1010_priv *priv)
66{
67 u8 reg, val;
68
69 for (reg = 0; ; reg++) {
70 if (reg % 16 == 0) {
71 if (reg)
72 printk(KERN_CONT "\n");
73 printk(KERN_DEBUG "%02x:", reg);
74 }
75 if (qt1010_readreg(priv, reg, &val) == 0)
76 printk(KERN_CONT " %02x", val);
77 else
78 printk(KERN_CONT " --");
79 if (reg == 0x2f)
80 break;
81 }
82 printk(KERN_CONT "\n");
83}
84
85static int qt1010_set_params(struct dvb_frontend *fe,
86 struct dvb_frontend_parameters *params)
87{
88 struct qt1010_priv *priv;
89 int err;
90 u32 freq, div, mod1, mod2;
91 u8 i, tmpval, reg05;
92 qt1010_i2c_oper_t rd[48] = {
93 { QT1010_WR, 0x01, 0x80 },
94 { QT1010_WR, 0x02, 0x3f },
95 { QT1010_WR, 0x05, 0xff }, /* 02 c write */
96 { QT1010_WR, 0x06, 0x44 },
97 { QT1010_WR, 0x07, 0xff }, /* 04 c write */
98 { QT1010_WR, 0x08, 0x08 },
99 { QT1010_WR, 0x09, 0xff }, /* 06 c write */
100 { QT1010_WR, 0x0a, 0xff }, /* 07 c write */
101 { QT1010_WR, 0x0b, 0xff }, /* 08 c write */
102 { QT1010_WR, 0x0c, 0xe1 },
103 { QT1010_WR, 0x1a, 0xff }, /* 10 c write */
104 { QT1010_WR, 0x1b, 0x00 },
105 { QT1010_WR, 0x1c, 0x89 },
106 { QT1010_WR, 0x11, 0xff }, /* 13 c write */
107 { QT1010_WR, 0x12, 0xff }, /* 14 c write */
108 { QT1010_WR, 0x22, 0xff }, /* 15 c write */
109 { QT1010_WR, 0x1e, 0x00 },
110 { QT1010_WR, 0x1e, 0xd0 },
111 { QT1010_RD, 0x22, 0xff }, /* 16 c read */
112 { QT1010_WR, 0x1e, 0x00 },
113 { QT1010_RD, 0x05, 0xff }, /* 20 c read */
114 { QT1010_RD, 0x22, 0xff }, /* 21 c read */
115 { QT1010_WR, 0x23, 0xd0 },
116 { QT1010_WR, 0x1e, 0x00 },
117 { QT1010_WR, 0x1e, 0xe0 },
118 { QT1010_RD, 0x23, 0xff }, /* 25 c read */
119 { QT1010_RD, 0x23, 0xff }, /* 26 c read */
120 { QT1010_WR, 0x1e, 0x00 },
121 { QT1010_WR, 0x24, 0xd0 },
122 { QT1010_WR, 0x1e, 0x00 },
123 { QT1010_WR, 0x1e, 0xf0 },
124 { QT1010_RD, 0x24, 0xff }, /* 31 c read */
125 { QT1010_WR, 0x1e, 0x00 },
126 { QT1010_WR, 0x14, 0x7f },
127 { QT1010_WR, 0x15, 0x7f },
128 { QT1010_WR, 0x05, 0xff }, /* 35 c write */
129 { QT1010_WR, 0x06, 0x00 },
130 { QT1010_WR, 0x15, 0x1f },
131 { QT1010_WR, 0x16, 0xff },
132 { QT1010_WR, 0x18, 0xff },
133 { QT1010_WR, 0x1f, 0xff }, /* 40 c write */
134 { QT1010_WR, 0x20, 0xff }, /* 41 c write */
135 { QT1010_WR, 0x21, 0x53 },
136 { QT1010_WR, 0x25, 0xff }, /* 43 c write */
137 { QT1010_WR, 0x26, 0x15 },
138 { QT1010_WR, 0x00, 0xff }, /* 45 c write */
139 { QT1010_WR, 0x02, 0x00 },
140 { QT1010_WR, 0x01, 0x00 }
141 };
142
143#define FREQ1 32000000 /* 32 MHz */
144#define FREQ2 4000000 /* 4 MHz Quartz oscillator in the stick? */
145
146 priv = fe->tuner_priv;
147 freq = params->frequency;
148 div = (freq + QT1010_OFFSET) / QT1010_STEP;
149 freq = (div * QT1010_STEP) - QT1010_OFFSET;
150 mod1 = (freq + QT1010_OFFSET) % FREQ1;
151 mod2 = (freq + QT1010_OFFSET) % FREQ2;
152 priv->bandwidth =
153 (fe->ops.info.type == FE_OFDM) ? params->u.ofdm.bandwidth : 0;
154 priv->frequency = freq;
155
156 if (fe->ops.i2c_gate_ctrl)
157 fe->ops.i2c_gate_ctrl(fe, 1); /* open i2c_gate */
158
159 /* reg 05 base value */
160 if (freq < 290000000) reg05 = 0x14; /* 290 MHz */
161 else if (freq < 610000000) reg05 = 0x34; /* 610 MHz */
162 else if (freq < 802000000) reg05 = 0x54; /* 802 MHz */
163 else reg05 = 0x74;
164
165 /* 0x5 */
166 rd[2].val = reg05;
167
168 /* 07 - set frequency: 32 MHz scale */
169 rd[4].val = (freq + QT1010_OFFSET) / FREQ1;
170
171 /* 09 - changes every 8/24 MHz */
172 if (mod1 < 8000000) rd[6].val = 0x1d;
173 else rd[6].val = 0x1c;
174
175 /* 0a - set frequency: 4 MHz scale (max 28 MHz) */
176 if (mod1 < 1*FREQ2) rd[7].val = 0x09; /* +0 MHz */
177 else if (mod1 < 2*FREQ2) rd[7].val = 0x08; /* +4 MHz */
178 else if (mod1 < 3*FREQ2) rd[7].val = 0x0f; /* +8 MHz */
179 else if (mod1 < 4*FREQ2) rd[7].val = 0x0e; /* +12 MHz */
180 else if (mod1 < 5*FREQ2) rd[7].val = 0x0d; /* +16 MHz */
181 else if (mod1 < 6*FREQ2) rd[7].val = 0x0c; /* +20 MHz */
182 else if (mod1 < 7*FREQ2) rd[7].val = 0x0b; /* +24 MHz */
183 else rd[7].val = 0x0a; /* +28 MHz */
184
185 /* 0b - changes every 2/2 MHz */
186 if (mod2 < 2000000) rd[8].val = 0x45;
187 else rd[8].val = 0x44;
188
189 /* 1a - set frequency: 125 kHz scale (max 3875 kHz)*/
190 tmpval = 0x78; /* byte, overflows intentionally */
191 rd[10].val = tmpval-((mod2/QT1010_STEP)*0x08);
192
193 /* 11 */
194 rd[13].val = 0xfd; /* TODO: correct value calculation */
195
196 /* 12 */
197 rd[14].val = 0x91; /* TODO: correct value calculation */
198
199 /* 22 */
200 if (freq < 450000000) rd[15].val = 0xd0; /* 450 MHz */
201 else if (freq < 482000000) rd[15].val = 0xd1; /* 482 MHz */
202 else if (freq < 514000000) rd[15].val = 0xd4; /* 514 MHz */
203 else if (freq < 546000000) rd[15].val = 0xd7; /* 546 MHz */
204 else if (freq < 610000000) rd[15].val = 0xda; /* 610 MHz */
205 else rd[15].val = 0xd0;
206
207 /* 05 */
208 rd[35].val = (reg05 & 0xf0);
209
210 /* 1f */
211 if (mod1 < 8000000) tmpval = 0x00;
212 else if (mod1 < 12000000) tmpval = 0x01;
213 else if (mod1 < 16000000) tmpval = 0x02;
214 else if (mod1 < 24000000) tmpval = 0x03;
215 else if (mod1 < 28000000) tmpval = 0x04;
216 else tmpval = 0x05;
217 rd[40].val = (priv->reg1f_init_val + 0x0e + tmpval);
218
219 /* 20 */
220 if (mod1 < 8000000) tmpval = 0x00;
221 else if (mod1 < 12000000) tmpval = 0x01;
222 else if (mod1 < 20000000) tmpval = 0x02;
223 else if (mod1 < 24000000) tmpval = 0x03;
224 else if (mod1 < 28000000) tmpval = 0x04;
225 else tmpval = 0x05;
226 rd[41].val = (priv->reg20_init_val + 0x0d + tmpval);
227
228 /* 25 */
229 rd[43].val = priv->reg25_init_val;
230
231 /* 00 */
232 rd[45].val = 0x92; /* TODO: correct value calculation */
233
234 dprintk("freq:%u 05:%02x 07:%02x 09:%02x 0a:%02x 0b:%02x " \
235 "1a:%02x 11:%02x 12:%02x 22:%02x 05:%02x 1f:%02x " \
236 "20:%02x 25:%02x 00:%02x", \
237 freq, rd[2].val, rd[4].val, rd[6].val, rd[7].val, rd[8].val, \
238 rd[10].val, rd[13].val, rd[14].val, rd[15].val, rd[35].val, \
239 rd[40].val, rd[41].val, rd[43].val, rd[45].val);
240
241 for (i = 0; i < ARRAY_SIZE(rd); i++) {
242 if (rd[i].oper == QT1010_WR) {
243 err = qt1010_writereg(priv, rd[i].reg, rd[i].val);
244 } else { /* read is required to proper locking */
245 err = qt1010_readreg(priv, rd[i].reg, &tmpval);
246 }
247 if (err) return err;
248 }
249
250 if (debug)
251 qt1010_dump_regs(priv);
252
253 if (fe->ops.i2c_gate_ctrl)
254 fe->ops.i2c_gate_ctrl(fe, 0); /* close i2c_gate */
255
256 return 0;
257}
258
259static int qt1010_init_meas1(struct qt1010_priv *priv,
260 u8 oper, u8 reg, u8 reg_init_val, u8 *retval)
261{
262 u8 i, val1, val2;
263 int err;
264
265 qt1010_i2c_oper_t i2c_data[] = {
266 { QT1010_WR, reg, reg_init_val },
267 { QT1010_WR, 0x1e, 0x00 },
268 { QT1010_WR, 0x1e, oper },
269 { QT1010_RD, reg, 0xff }
270 };
271
272 for (i = 0; i < ARRAY_SIZE(i2c_data); i++) {
273 if (i2c_data[i].oper == QT1010_WR) {
274 err = qt1010_writereg(priv, i2c_data[i].reg,
275 i2c_data[i].val);
276 } else {
277 err = qt1010_readreg(priv, i2c_data[i].reg, &val2);
278 }
279 if (err) return err;
280 }
281
282 do {
283 val1 = val2;
284 err = qt1010_readreg(priv, reg, &val2);
285 if (err) return err;
286 dprintk("compare reg:%02x %02x %02x", reg, val1, val2);
287 } while (val1 != val2);
288 *retval = val1;
289
290 return qt1010_writereg(priv, 0x1e, 0x00);
291}
292
293static u8 qt1010_init_meas2(struct qt1010_priv *priv,
294 u8 reg_init_val, u8 *retval)
295{
296 u8 i, val;
297 int err;
298 qt1010_i2c_oper_t i2c_data[] = {
299 { QT1010_WR, 0x07, reg_init_val },
300 { QT1010_WR, 0x22, 0xd0 },
301 { QT1010_WR, 0x1e, 0x00 },
302 { QT1010_WR, 0x1e, 0xd0 },
303 { QT1010_RD, 0x22, 0xff },
304 { QT1010_WR, 0x1e, 0x00 },
305 { QT1010_WR, 0x22, 0xff }
306 };
307 for (i = 0; i < ARRAY_SIZE(i2c_data); i++) {
308 if (i2c_data[i].oper == QT1010_WR) {
309 err = qt1010_writereg(priv, i2c_data[i].reg,
310 i2c_data[i].val);
311 } else {
312 err = qt1010_readreg(priv, i2c_data[i].reg, &val);
313 }
314 if (err) return err;
315 }
316 *retval = val;
317 return 0;
318}
319
320static int qt1010_init(struct dvb_frontend *fe)
321{
322 struct qt1010_priv *priv = fe->tuner_priv;
323 struct dvb_frontend_parameters params;
324 int err = 0;
325 u8 i, tmpval, *valptr = NULL;
326
327 qt1010_i2c_oper_t i2c_data[] = {
328 { QT1010_WR, 0x01, 0x80 },
329 { QT1010_WR, 0x0d, 0x84 },
330 { QT1010_WR, 0x0e, 0xb7 },
331 { QT1010_WR, 0x2a, 0x23 },
332 { QT1010_WR, 0x2c, 0xdc },
333 { QT1010_M1, 0x25, 0x40 }, /* get reg 25 init value */
334 { QT1010_M1, 0x81, 0xff }, /* get reg 25 init value */
335 { QT1010_WR, 0x2b, 0x70 },
336 { QT1010_WR, 0x2a, 0x23 },
337 { QT1010_M1, 0x26, 0x08 },
338 { QT1010_M1, 0x82, 0xff },
339 { QT1010_WR, 0x05, 0x14 },
340 { QT1010_WR, 0x06, 0x44 },
341 { QT1010_WR, 0x07, 0x28 },
342 { QT1010_WR, 0x08, 0x0b },
343 { QT1010_WR, 0x11, 0xfd },
344 { QT1010_M1, 0x22, 0x0d },
345 { QT1010_M1, 0xd0, 0xff },
346 { QT1010_WR, 0x06, 0x40 },
347 { QT1010_WR, 0x16, 0xf0 },
348 { QT1010_WR, 0x02, 0x38 },
349 { QT1010_WR, 0x03, 0x18 },
350 { QT1010_WR, 0x20, 0xe0 },
351 { QT1010_M1, 0x1f, 0x20 }, /* get reg 1f init value */
352 { QT1010_M1, 0x84, 0xff }, /* get reg 1f init value */
353 { QT1010_RD, 0x20, 0x20 }, /* get reg 20 init value */
354 { QT1010_WR, 0x03, 0x19 },
355 { QT1010_WR, 0x02, 0x3f },
356 { QT1010_WR, 0x21, 0x53 },
357 { QT1010_RD, 0x21, 0xff },
358 { QT1010_WR, 0x11, 0xfd },
359 { QT1010_WR, 0x05, 0x34 },
360 { QT1010_WR, 0x06, 0x44 },
361 { QT1010_WR, 0x08, 0x08 }
362 };
363
364 if (fe->ops.i2c_gate_ctrl)
365 fe->ops.i2c_gate_ctrl(fe, 1); /* open i2c_gate */
366
367 for (i = 0; i < ARRAY_SIZE(i2c_data); i++) {
368 switch (i2c_data[i].oper) {
369 case QT1010_WR:
370 err = qt1010_writereg(priv, i2c_data[i].reg,
371 i2c_data[i].val);
372 break;
373 case QT1010_RD:
374 if (i2c_data[i].val == 0x20)
375 valptr = &priv->reg20_init_val;
376 else
377 valptr = &tmpval;
378 err = qt1010_readreg(priv, i2c_data[i].reg, valptr);
379 break;
380 case QT1010_M1:
381 if (i2c_data[i].val == 0x25)
382 valptr = &priv->reg25_init_val;
383 else if (i2c_data[i].val == 0x1f)
384 valptr = &priv->reg1f_init_val;
385 else
386 valptr = &tmpval;
387 err = qt1010_init_meas1(priv, i2c_data[i+1].reg,
388 i2c_data[i].reg,
389 i2c_data[i].val, valptr);
390 i++;
391 break;
392 }
393 if (err) return err;
394 }
395
396 for (i = 0x31; i < 0x3a; i++) /* 0x31 - 0x39 */
397 if ((err = qt1010_init_meas2(priv, i, &tmpval)))
398 return err;
399
400 params.frequency = 545000000; /* Sigmatek DVB-110 545000000 */
401 /* MSI Megasky 580 GL861 533000000 */
402 return qt1010_set_params(fe, &params);
403}
404
405static int qt1010_release(struct dvb_frontend *fe)
406{
407 kfree(fe->tuner_priv);
408 fe->tuner_priv = NULL;
409 return 0;
410}
411
412static int qt1010_get_frequency(struct dvb_frontend *fe, u32 *frequency)
413{
414 struct qt1010_priv *priv = fe->tuner_priv;
415 *frequency = priv->frequency;
416 return 0;
417}
418
419static int qt1010_get_bandwidth(struct dvb_frontend *fe, u32 *bandwidth)
420{
421 struct qt1010_priv *priv = fe->tuner_priv;
422 *bandwidth = priv->bandwidth;
423 return 0;
424}
425
426static const struct dvb_tuner_ops qt1010_tuner_ops = {
427 .info = {
428 .name = "Quantek QT1010",
429 .frequency_min = QT1010_MIN_FREQ,
430 .frequency_max = QT1010_MAX_FREQ,
431 .frequency_step = QT1010_STEP,
432 },
433
434 .release = qt1010_release,
435 .init = qt1010_init,
436 /* TODO: implement sleep */
437
438 .set_params = qt1010_set_params,
439 .get_frequency = qt1010_get_frequency,
440 .get_bandwidth = qt1010_get_bandwidth
441};
442
443struct dvb_frontend * qt1010_attach(struct dvb_frontend *fe,
444 struct i2c_adapter *i2c,
445 struct qt1010_config *cfg)
446{
447 struct qt1010_priv *priv = NULL;
448 u8 id;
449
450 priv = kzalloc(sizeof(struct qt1010_priv), GFP_KERNEL);
451 if (priv == NULL)
452 return NULL;
453
454 priv->cfg = cfg;
455 priv->i2c = i2c;
456
457 if (fe->ops.i2c_gate_ctrl)
458 fe->ops.i2c_gate_ctrl(fe, 1); /* open i2c_gate */
459
460
461 /* Try to detect tuner chip. Probably this is not correct register. */
462 if (qt1010_readreg(priv, 0x29, &id) != 0 || (id != 0x39)) {
463 kfree(priv);
464 return NULL;
465 }
466
467 if (fe->ops.i2c_gate_ctrl)
468 fe->ops.i2c_gate_ctrl(fe, 0); /* close i2c_gate */
469
470 printk(KERN_INFO "Quantek QT1010 successfully identified.\n");
471 memcpy(&fe->ops.tuner_ops, &qt1010_tuner_ops,
472 sizeof(struct dvb_tuner_ops));
473
474 fe->tuner_priv = priv;
475 return fe;
476}
477EXPORT_SYMBOL(qt1010_attach);
478
479MODULE_DESCRIPTION("Quantek QT1010 silicon tuner driver");
480MODULE_AUTHOR("Antti Palosaari <crope@iki.fi>");
481MODULE_AUTHOR("Aapo Tahkola <aet@rasterburn.org>");
482MODULE_VERSION("0.1");
483MODULE_LICENSE("GPL");
diff --git a/drivers/media/common/tuners/qt1010.h b/drivers/media/common/tuners/qt1010.h
new file mode 100644
index 00000000000..807fb7b6146
--- /dev/null
+++ b/drivers/media/common/tuners/qt1010.h
@@ -0,0 +1,53 @@
1/*
2 * Driver for Quantek QT1010 silicon tuner
3 *
4 * Copyright (C) 2006 Antti Palosaari <crope@iki.fi>
5 * Aapo Tahkola <aet@rasterburn.org>
6 *
7 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation; either version 2 of the License, or
10 * (at your option) any later version.
11 *
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
20 */
21
22#ifndef QT1010_H
23#define QT1010_H
24
25#include "dvb_frontend.h"
26
27struct qt1010_config {
28 u8 i2c_address;
29};
30
31/**
32 * Attach a qt1010 tuner to the supplied frontend structure.
33 *
34 * @param fe frontend to attach to
35 * @param i2c i2c adapter to use
36 * @param cfg tuner hw based configuration
37 * @return fe pointer on success, NULL on failure
38 */
39#if defined(CONFIG_MEDIA_TUNER_QT1010) || (defined(CONFIG_MEDIA_TUNER_QT1010_MODULE) && defined(MODULE))
40extern struct dvb_frontend *qt1010_attach(struct dvb_frontend *fe,
41 struct i2c_adapter *i2c,
42 struct qt1010_config *cfg);
43#else
44static inline struct dvb_frontend *qt1010_attach(struct dvb_frontend *fe,
45 struct i2c_adapter *i2c,
46 struct qt1010_config *cfg)
47{
48 printk(KERN_WARNING "%s: driver disabled by Kconfig\n", __func__);
49 return NULL;
50}
51#endif // CONFIG_MEDIA_TUNER_QT1010
52
53#endif
diff --git a/drivers/media/common/tuners/qt1010_priv.h b/drivers/media/common/tuners/qt1010_priv.h
new file mode 100644
index 00000000000..090cf475f09
--- /dev/null
+++ b/drivers/media/common/tuners/qt1010_priv.h
@@ -0,0 +1,105 @@
1/*
2 * Driver for Quantek QT1010 silicon tuner
3 *
4 * Copyright (C) 2006 Antti Palosaari <crope@iki.fi>
5 * Aapo Tahkola <aet@rasterburn.org>
6 *
7 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation; either version 2 of the License, or
10 * (at your option) any later version.
11 *
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
20 */
21
22#ifndef QT1010_PRIV_H
23#define QT1010_PRIV_H
24
25/*
26reg def meaning
27=== === =======
2800 00 ?
2901 a0 ? operation start/stop; start=80, stop=00
3002 00 ?
3103 19 ?
3204 00 ?
3305 00 ? maybe band selection
3406 00 ?
3507 2b set frequency: 32 MHz scale, n*32 MHz
3608 0b ?
3709 10 ? changes every 8/24 MHz; values 1d/1c
380a 08 set frequency: 4 MHz scale, n*4 MHz
390b 41 ? changes every 2/2 MHz; values 45/45
400c e1 ?
410d 94 ?
420e b6 ?
430f 2c ?
4410 10 ?
4511 f1 ? maybe device specified adjustment
4612 11 ? maybe device specified adjustment
4713 3f ?
4814 1f ?
4915 3f ?
5016 ff ?
5117 ff ?
5218 f7 ?
5319 80 ?
541a d0 set frequency: 125 kHz scale, n*125 kHz
551b 00 ?
561c 89 ?
571d 00 ?
581e 00 ? looks like operation register; write cmd here, read result from 1f-26
591f 20 ? chip initialization
6020 e0 ? chip initialization
6121 20 ?
6222 d0 ?
6323 d0 ?
6424 d0 ?
6525 40 ? chip initialization
6626 08 ?
6727 29 ?
6828 55 ?
6929 39 ?
702a 13 ?
712b 01 ?
722c ea ?
732d 00 ?
742e 00 ? not used?
752f 00 ? not used?
76*/
77
78#define QT1010_STEP 125000 /* 125 kHz used by Windows drivers,
79 hw could be more precise but we don't
80 know how to use */
81#define QT1010_MIN_FREQ 48000000 /* 48 MHz */
82#define QT1010_MAX_FREQ 860000000 /* 860 MHz */
83#define QT1010_OFFSET 1246000000 /* 1246 MHz */
84
85#define QT1010_WR 0
86#define QT1010_RD 1
87#define QT1010_M1 3
88
89typedef struct {
90 u8 oper, reg, val;
91} qt1010_i2c_oper_t;
92
93struct qt1010_priv {
94 struct qt1010_config *cfg;
95 struct i2c_adapter *i2c;
96
97 u8 reg1f_init_val;
98 u8 reg20_init_val;
99 u8 reg25_init_val;
100
101 u32 frequency;
102 u32 bandwidth;
103};
104
105#endif
diff --git a/drivers/media/common/tuners/tda18212.c b/drivers/media/common/tuners/tda18212.c
new file mode 100644
index 00000000000..1f1db20d46b
--- /dev/null
+++ b/drivers/media/common/tuners/tda18212.c
@@ -0,0 +1,265 @@
1/*
2 * NXP TDA18212HN silicon tuner driver
3 *
4 * Copyright (C) 2011 Antti Palosaari <crope@iki.fi>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License along
17 * with this program; if not, write to the Free Software Foundation, Inc.,
18 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
19 */
20
21#include "tda18212_priv.h"
22
23static int debug;
24module_param(debug, int, 0644);
25MODULE_PARM_DESC(debug, "Turn on/off debugging (default:off).");
26
27/* write multiple registers */
28static int tda18212_wr_regs(struct tda18212_priv *priv, u8 reg, u8 *val,
29 int len)
30{
31 int ret;
32 u8 buf[len+1];
33 struct i2c_msg msg[1] = {
34 {
35 .addr = priv->cfg->i2c_address,
36 .flags = 0,
37 .len = sizeof(buf),
38 .buf = buf,
39 }
40 };
41
42 buf[0] = reg;
43 memcpy(&buf[1], val, len);
44
45 ret = i2c_transfer(priv->i2c, msg, 1);
46 if (ret == 1) {
47 ret = 0;
48 } else {
49 warn("i2c wr failed ret:%d reg:%02x len:%d", ret, reg, len);
50 ret = -EREMOTEIO;
51 }
52 return ret;
53}
54
55/* read multiple registers */
56static int tda18212_rd_regs(struct tda18212_priv *priv, u8 reg, u8 *val,
57 int len)
58{
59 int ret;
60 u8 buf[len];
61 struct i2c_msg msg[2] = {
62 {
63 .addr = priv->cfg->i2c_address,
64 .flags = 0,
65 .len = 1,
66 .buf = &reg,
67 }, {
68 .addr = priv->cfg->i2c_address,
69 .flags = I2C_M_RD,
70 .len = sizeof(buf),
71 .buf = buf,
72 }
73 };
74
75 ret = i2c_transfer(priv->i2c, msg, 2);
76 if (ret == 2) {
77 memcpy(val, buf, len);
78 ret = 0;
79 } else {
80 warn("i2c rd failed ret:%d reg:%02x len:%d", ret, reg, len);
81 ret = -EREMOTEIO;
82 }
83
84 return ret;
85}
86
87/* write single register */
88static int tda18212_wr_reg(struct tda18212_priv *priv, u8 reg, u8 val)
89{
90 return tda18212_wr_regs(priv, reg, &val, 1);
91}
92
93/* read single register */
94static int tda18212_rd_reg(struct tda18212_priv *priv, u8 reg, u8 *val)
95{
96 return tda18212_rd_regs(priv, reg, val, 1);
97}
98
99#if 0 /* keep, useful when developing driver */
100static void tda18212_dump_regs(struct tda18212_priv *priv)
101{
102 int i;
103 u8 buf[256];
104
105 #define TDA18212_RD_LEN 32
106 for (i = 0; i < sizeof(buf); i += TDA18212_RD_LEN)
107 tda18212_rd_regs(priv, i, &buf[i], TDA18212_RD_LEN);
108
109 print_hex_dump(KERN_INFO, "", DUMP_PREFIX_OFFSET, 32, 1, buf,
110 sizeof(buf), true);
111
112 return;
113}
114#endif
115
116static int tda18212_set_params(struct dvb_frontend *fe,
117 struct dvb_frontend_parameters *p)
118{
119 struct tda18212_priv *priv = fe->tuner_priv;
120 struct dtv_frontend_properties *c = &fe->dtv_property_cache;
121 int ret, i;
122 u32 if_khz;
123 u8 buf[9];
124 static const u8 bw_params[][3] = {
125 /* 0f 13 23 */
126 { 0xb3, 0x20, 0x03 }, /* DVB-T 6 MHz */
127 { 0xb3, 0x31, 0x01 }, /* DVB-T 7 MHz */
128 { 0xb3, 0x22, 0x01 }, /* DVB-T 8 MHz */
129 { 0x92, 0x53, 0x03 }, /* DVB-C */
130 };
131
132 dbg("%s: delsys=%d RF=%d BW=%d", __func__,
133 c->delivery_system, c->frequency, c->bandwidth_hz);
134
135 if (fe->ops.i2c_gate_ctrl)
136 fe->ops.i2c_gate_ctrl(fe, 1); /* open I2C-gate */
137
138 switch (c->delivery_system) {
139 case SYS_DVBT:
140 switch (c->bandwidth_hz) {
141 case 6000000:
142 if_khz = priv->cfg->if_dvbt_6;
143 i = 0;
144 break;
145 case 7000000:
146 if_khz = priv->cfg->if_dvbt_7;
147 i = 1;
148 break;
149 case 8000000:
150 if_khz = priv->cfg->if_dvbt_8;
151 i = 2;
152 break;
153 default:
154 ret = -EINVAL;
155 goto error;
156 }
157 break;
158 case SYS_DVBC_ANNEX_AC:
159 if_khz = priv->cfg->if_dvbc;
160 i = 3;
161 break;
162 default:
163 ret = -EINVAL;
164 goto error;
165 }
166
167 ret = tda18212_wr_reg(priv, 0x23, bw_params[i][2]);
168 if (ret)
169 goto error;
170
171 ret = tda18212_wr_reg(priv, 0x06, 0x00);
172 if (ret)
173 goto error;
174
175 ret = tda18212_wr_reg(priv, 0x0f, bw_params[i][0]);
176 if (ret)
177 goto error;
178
179 buf[0] = 0x02;
180 buf[1] = bw_params[i][1];
181 buf[2] = 0x03; /* default value */
182 buf[3] = if_khz / 50;
183 buf[4] = ((c->frequency / 1000) >> 16) & 0xff;
184 buf[5] = ((c->frequency / 1000) >> 8) & 0xff;
185 buf[6] = ((c->frequency / 1000) >> 0) & 0xff;
186 buf[7] = 0xc1;
187 buf[8] = 0x01;
188 ret = tda18212_wr_regs(priv, 0x12, buf, sizeof(buf));
189 if (ret)
190 goto error;
191
192exit:
193 if (fe->ops.i2c_gate_ctrl)
194 fe->ops.i2c_gate_ctrl(fe, 0); /* close I2C-gate */
195
196 return ret;
197
198error:
199 dbg("%s: failed:%d", __func__, ret);
200 goto exit;
201}
202
203static int tda18212_release(struct dvb_frontend *fe)
204{
205 kfree(fe->tuner_priv);
206 fe->tuner_priv = NULL;
207 return 0;
208}
209
210static const struct dvb_tuner_ops tda18212_tuner_ops = {
211 .info = {
212 .name = "NXP TDA18212",
213
214 .frequency_min = 48000000,
215 .frequency_max = 864000000,
216 .frequency_step = 1000,
217 },
218
219 .release = tda18212_release,
220
221 .set_params = tda18212_set_params,
222};
223
224struct dvb_frontend *tda18212_attach(struct dvb_frontend *fe,
225 struct i2c_adapter *i2c, struct tda18212_config *cfg)
226{
227 struct tda18212_priv *priv = NULL;
228 int ret;
229 u8 val;
230
231 priv = kzalloc(sizeof(struct tda18212_priv), GFP_KERNEL);
232 if (priv == NULL)
233 return NULL;
234
235 priv->cfg = cfg;
236 priv->i2c = i2c;
237 fe->tuner_priv = priv;
238
239 if (fe->ops.i2c_gate_ctrl)
240 fe->ops.i2c_gate_ctrl(fe, 1); /* open I2C-gate */
241
242 /* check if the tuner is there */
243 ret = tda18212_rd_reg(priv, 0x00, &val);
244
245 if (fe->ops.i2c_gate_ctrl)
246 fe->ops.i2c_gate_ctrl(fe, 0); /* close I2C-gate */
247
248 dbg("%s: ret:%d chip ID:%02x", __func__, ret, val);
249 if (ret || val != 0xc7) {
250 kfree(priv);
251 return NULL;
252 }
253
254 info("NXP TDA18212HN successfully identified.");
255
256 memcpy(&fe->ops.tuner_ops, &tda18212_tuner_ops,
257 sizeof(struct dvb_tuner_ops));
258
259 return fe;
260}
261EXPORT_SYMBOL(tda18212_attach);
262
263MODULE_DESCRIPTION("NXP TDA18212HN silicon tuner driver");
264MODULE_AUTHOR("Antti Palosaari <crope@iki.fi>");
265MODULE_LICENSE("GPL");
diff --git a/drivers/media/common/tuners/tda18212.h b/drivers/media/common/tuners/tda18212.h
new file mode 100644
index 00000000000..83b497f59e1
--- /dev/null
+++ b/drivers/media/common/tuners/tda18212.h
@@ -0,0 +1,48 @@
1/*
2 * NXP TDA18212HN silicon tuner driver
3 *
4 * Copyright (C) 2011 Antti Palosaari <crope@iki.fi>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License along
17 * with this program; if not, write to the Free Software Foundation, Inc.,
18 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
19 */
20
21#ifndef TDA18212_H
22#define TDA18212_H
23
24#include "dvb_frontend.h"
25
26struct tda18212_config {
27 u8 i2c_address;
28
29 u16 if_dvbt_6;
30 u16 if_dvbt_7;
31 u16 if_dvbt_8;
32 u16 if_dvbc;
33};
34
35#if defined(CONFIG_MEDIA_TUNER_TDA18212) || \
36 (defined(CONFIG_MEDIA_TUNER_TDA18212_MODULE) && defined(MODULE))
37extern struct dvb_frontend *tda18212_attach(struct dvb_frontend *fe,
38 struct i2c_adapter *i2c, struct tda18212_config *cfg);
39#else
40static inline struct dvb_frontend *tda18212_attach(struct dvb_frontend *fe,
41 struct i2c_adapter *i2c, struct tda18212_config *cfg)
42{
43 printk(KERN_WARNING "%s: driver disabled by Kconfig\n", __func__);
44 return NULL;
45}
46#endif
47
48#endif
diff --git a/drivers/media/common/tuners/tda18212_priv.h b/drivers/media/common/tuners/tda18212_priv.h
new file mode 100644
index 00000000000..9adff9356b7
--- /dev/null
+++ b/drivers/media/common/tuners/tda18212_priv.h
@@ -0,0 +1,44 @@
1/*
2 * NXP TDA18212HN silicon tuner driver
3 *
4 * Copyright (C) 2011 Antti Palosaari <crope@iki.fi>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License along
17 * with this program; if not, write to the Free Software Foundation, Inc.,
18 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
19 */
20
21#ifndef TDA18212_PRIV_H
22#define TDA18212_PRIV_H
23
24#include "tda18212.h"
25
26#define LOG_PREFIX "tda18212"
27
28#undef dbg
29#define dbg(f, arg...) \
30 if (debug) \
31 printk(KERN_INFO LOG_PREFIX": " f "\n" , ## arg)
32#undef err
33#define err(f, arg...) printk(KERN_ERR LOG_PREFIX": " f "\n" , ## arg)
34#undef info
35#define info(f, arg...) printk(KERN_INFO LOG_PREFIX": " f "\n" , ## arg)
36#undef warn
37#define warn(f, arg...) printk(KERN_WARNING LOG_PREFIX": " f "\n" , ## arg)
38
39struct tda18212_priv {
40 struct tda18212_config *cfg;
41 struct i2c_adapter *i2c;
42};
43
44#endif
diff --git a/drivers/media/common/tuners/tda18218.c b/drivers/media/common/tuners/tda18218.c
new file mode 100644
index 00000000000..aacfe2387e2
--- /dev/null
+++ b/drivers/media/common/tuners/tda18218.c
@@ -0,0 +1,334 @@
1/*
2 * NXP TDA18218HN silicon tuner driver
3 *
4 * Copyright (C) 2010 Antti Palosaari <crope@iki.fi>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, write to the Free Software
18 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
19 */
20
21#include "tda18218.h"
22#include "tda18218_priv.h"
23
24static int debug;
25module_param(debug, int, 0644);
26MODULE_PARM_DESC(debug, "Turn on/off debugging (default:off).");
27
28/* write multiple registers */
29static int tda18218_wr_regs(struct tda18218_priv *priv, u8 reg, u8 *val, u8 len)
30{
31 int ret = 0;
32 u8 buf[1+len], quotient, remainder, i, msg_len, msg_len_max;
33 struct i2c_msg msg[1] = {
34 {
35 .addr = priv->cfg->i2c_address,
36 .flags = 0,
37 .buf = buf,
38 }
39 };
40
41 msg_len_max = priv->cfg->i2c_wr_max - 1;
42 quotient = len / msg_len_max;
43 remainder = len % msg_len_max;
44 msg_len = msg_len_max;
45 for (i = 0; (i <= quotient && remainder); i++) {
46 if (i == quotient) /* set len of the last msg */
47 msg_len = remainder;
48
49 msg[0].len = msg_len + 1;
50 buf[0] = reg + i * msg_len_max;
51 memcpy(&buf[1], &val[i * msg_len_max], msg_len);
52
53 ret = i2c_transfer(priv->i2c, msg, 1);
54 if (ret != 1)
55 break;
56 }
57
58 if (ret == 1) {
59 ret = 0;
60 } else {
61 warn("i2c wr failed ret:%d reg:%02x len:%d", ret, reg, len);
62 ret = -EREMOTEIO;
63 }
64
65 return ret;
66}
67
68/* read multiple registers */
69static int tda18218_rd_regs(struct tda18218_priv *priv, u8 reg, u8 *val, u8 len)
70{
71 int ret;
72 u8 buf[reg+len]; /* we must start read always from reg 0x00 */
73 struct i2c_msg msg[2] = {
74 {
75 .addr = priv->cfg->i2c_address,
76 .flags = 0,
77 .len = 1,
78 .buf = "\x00",
79 }, {
80 .addr = priv->cfg->i2c_address,
81 .flags = I2C_M_RD,
82 .len = sizeof(buf),
83 .buf = buf,
84 }
85 };
86
87 ret = i2c_transfer(priv->i2c, msg, 2);
88 if (ret == 2) {
89 memcpy(val, &buf[reg], len);
90 ret = 0;
91 } else {
92 warn("i2c rd failed ret:%d reg:%02x len:%d", ret, reg, len);
93 ret = -EREMOTEIO;
94 }
95
96 return ret;
97}
98
99/* write single register */
100static int tda18218_wr_reg(struct tda18218_priv *priv, u8 reg, u8 val)
101{
102 return tda18218_wr_regs(priv, reg, &val, 1);
103}
104
105/* read single register */
106
107static int tda18218_rd_reg(struct tda18218_priv *priv, u8 reg, u8 *val)
108{
109 return tda18218_rd_regs(priv, reg, val, 1);
110}
111
112static int tda18218_set_params(struct dvb_frontend *fe,
113 struct dvb_frontend_parameters *params)
114{
115 struct tda18218_priv *priv = fe->tuner_priv;
116 int ret;
117 u8 buf[3], i, BP_Filter, LP_Fc;
118 u32 LO_Frac;
119 /* TODO: find out correct AGC algorithm */
120 u8 agc[][2] = {
121 { R20_AGC11, 0x60 },
122 { R23_AGC21, 0x02 },
123 { R20_AGC11, 0xa0 },
124 { R23_AGC21, 0x09 },
125 { R20_AGC11, 0xe0 },
126 { R23_AGC21, 0x0c },
127 { R20_AGC11, 0x40 },
128 { R23_AGC21, 0x01 },
129 { R20_AGC11, 0x80 },
130 { R23_AGC21, 0x08 },
131 { R20_AGC11, 0xc0 },
132 { R23_AGC21, 0x0b },
133 { R24_AGC22, 0x1c },
134 { R24_AGC22, 0x0c },
135 };
136
137 if (fe->ops.i2c_gate_ctrl)
138 fe->ops.i2c_gate_ctrl(fe, 1); /* open I2C-gate */
139
140 /* low-pass filter cut-off frequency */
141 switch (params->u.ofdm.bandwidth) {
142 case BANDWIDTH_6_MHZ:
143 LP_Fc = 0;
144 LO_Frac = params->frequency + 4000000;
145 break;
146 case BANDWIDTH_7_MHZ:
147 LP_Fc = 1;
148 LO_Frac = params->frequency + 3500000;
149 break;
150 case BANDWIDTH_8_MHZ:
151 default:
152 LP_Fc = 2;
153 LO_Frac = params->frequency + 4000000;
154 break;
155 }
156
157 /* band-pass filter */
158 if (LO_Frac < 188000000)
159 BP_Filter = 3;
160 else if (LO_Frac < 253000000)
161 BP_Filter = 4;
162 else if (LO_Frac < 343000000)
163 BP_Filter = 5;
164 else
165 BP_Filter = 6;
166
167 buf[0] = (priv->regs[R1A_IF1] & ~7) | BP_Filter; /* BP_Filter */
168 buf[1] = (priv->regs[R1B_IF2] & ~3) | LP_Fc; /* LP_Fc */
169 buf[2] = priv->regs[R1C_AGC2B];
170 ret = tda18218_wr_regs(priv, R1A_IF1, buf, 3);
171 if (ret)
172 goto error;
173
174 buf[0] = (LO_Frac / 1000) >> 12; /* LO_Frac_0 */
175 buf[1] = (LO_Frac / 1000) >> 4; /* LO_Frac_1 */
176 buf[2] = (LO_Frac / 1000) << 4 |
177 (priv->regs[R0C_MD5] & 0x0f); /* LO_Frac_2 */
178 ret = tda18218_wr_regs(priv, R0A_MD3, buf, 3);
179 if (ret)
180 goto error;
181
182 buf[0] = priv->regs[R0F_MD8] | (1 << 6); /* Freq_prog_Start */
183 ret = tda18218_wr_regs(priv, R0F_MD8, buf, 1);
184 if (ret)
185 goto error;
186
187 buf[0] = priv->regs[R0F_MD8] & ~(1 << 6); /* Freq_prog_Start */
188 ret = tda18218_wr_regs(priv, R0F_MD8, buf, 1);
189 if (ret)
190 goto error;
191
192 /* trigger AGC */
193 for (i = 0; i < ARRAY_SIZE(agc); i++) {
194 ret = tda18218_wr_reg(priv, agc[i][0], agc[i][1]);
195 if (ret)
196 goto error;
197 }
198
199error:
200 if (fe->ops.i2c_gate_ctrl)
201 fe->ops.i2c_gate_ctrl(fe, 0); /* close I2C-gate */
202
203 if (ret)
204 dbg("%s: failed ret:%d", __func__, ret);
205
206 return ret;
207}
208
209static int tda18218_sleep(struct dvb_frontend *fe)
210{
211 struct tda18218_priv *priv = fe->tuner_priv;
212 int ret;
213
214 if (fe->ops.i2c_gate_ctrl)
215 fe->ops.i2c_gate_ctrl(fe, 1); /* open I2C-gate */
216
217 /* standby */
218 ret = tda18218_wr_reg(priv, R17_PD1, priv->regs[R17_PD1] | (1 << 0));
219
220 if (fe->ops.i2c_gate_ctrl)
221 fe->ops.i2c_gate_ctrl(fe, 0); /* close I2C-gate */
222
223 if (ret)
224 dbg("%s: failed ret:%d", __func__, ret);
225
226 return ret;
227}
228
229static int tda18218_init(struct dvb_frontend *fe)
230{
231 struct tda18218_priv *priv = fe->tuner_priv;
232 int ret;
233
234 /* TODO: calibrations */
235
236 if (fe->ops.i2c_gate_ctrl)
237 fe->ops.i2c_gate_ctrl(fe, 1); /* open I2C-gate */
238
239 ret = tda18218_wr_regs(priv, R00_ID, priv->regs, TDA18218_NUM_REGS);
240
241 if (fe->ops.i2c_gate_ctrl)
242 fe->ops.i2c_gate_ctrl(fe, 0); /* close I2C-gate */
243
244 if (ret)
245 dbg("%s: failed ret:%d", __func__, ret);
246
247 return ret;
248}
249
250static int tda18218_release(struct dvb_frontend *fe)
251{
252 kfree(fe->tuner_priv);
253 fe->tuner_priv = NULL;
254 return 0;
255}
256
257static const struct dvb_tuner_ops tda18218_tuner_ops = {
258 .info = {
259 .name = "NXP TDA18218",
260
261 .frequency_min = 174000000,
262 .frequency_max = 864000000,
263 .frequency_step = 1000,
264 },
265
266 .release = tda18218_release,
267 .init = tda18218_init,
268 .sleep = tda18218_sleep,
269
270 .set_params = tda18218_set_params,
271};
272
273struct dvb_frontend *tda18218_attach(struct dvb_frontend *fe,
274 struct i2c_adapter *i2c, struct tda18218_config *cfg)
275{
276 struct tda18218_priv *priv = NULL;
277 u8 val;
278 int ret;
279 /* chip default registers values */
280 static u8 def_regs[] = {
281 0xc0, 0x88, 0x00, 0x8e, 0x03, 0x00, 0x00, 0xd0, 0x00, 0x40,
282 0x00, 0x00, 0x07, 0xff, 0x84, 0x09, 0x00, 0x13, 0x00, 0x00,
283 0x01, 0x84, 0x09, 0xf0, 0x19, 0x0a, 0x8e, 0x69, 0x98, 0x01,
284 0x00, 0x58, 0x10, 0x40, 0x8c, 0x00, 0x0c, 0x48, 0x85, 0xc9,
285 0xa7, 0x00, 0x00, 0x00, 0x30, 0x81, 0x80, 0x00, 0x39, 0x00,
286 0x8a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xf6, 0xf6
287 };
288
289 priv = kzalloc(sizeof(struct tda18218_priv), GFP_KERNEL);
290 if (priv == NULL)
291 return NULL;
292
293 priv->cfg = cfg;
294 priv->i2c = i2c;
295 fe->tuner_priv = priv;
296
297 if (fe->ops.i2c_gate_ctrl)
298 fe->ops.i2c_gate_ctrl(fe, 1); /* open I2C-gate */
299
300 /* check if the tuner is there */
301 ret = tda18218_rd_reg(priv, R00_ID, &val);
302 dbg("%s: ret:%d chip ID:%02x", __func__, ret, val);
303 if (ret || val != def_regs[R00_ID]) {
304 kfree(priv);
305 return NULL;
306 }
307
308 info("NXP TDA18218HN successfully identified.");
309
310 memcpy(&fe->ops.tuner_ops, &tda18218_tuner_ops,
311 sizeof(struct dvb_tuner_ops));
312 memcpy(priv->regs, def_regs, sizeof(def_regs));
313
314 /* loop-through enabled chip default register values */
315 if (priv->cfg->loop_through) {
316 priv->regs[R17_PD1] = 0xb0;
317 priv->regs[R18_PD2] = 0x59;
318 }
319
320 /* standby */
321 ret = tda18218_wr_reg(priv, R17_PD1, priv->regs[R17_PD1] | (1 << 0));
322 if (ret)
323 dbg("%s: failed ret:%d", __func__, ret);
324
325 if (fe->ops.i2c_gate_ctrl)
326 fe->ops.i2c_gate_ctrl(fe, 0); /* close I2C-gate */
327
328 return fe;
329}
330EXPORT_SYMBOL(tda18218_attach);
331
332MODULE_DESCRIPTION("NXP TDA18218HN silicon tuner driver");
333MODULE_AUTHOR("Antti Palosaari <crope@iki.fi>");
334MODULE_LICENSE("GPL");
diff --git a/drivers/media/common/tuners/tda18218.h b/drivers/media/common/tuners/tda18218.h
new file mode 100644
index 00000000000..b4180d18002
--- /dev/null
+++ b/drivers/media/common/tuners/tda18218.h
@@ -0,0 +1,45 @@
1/*
2 * NXP TDA18218HN silicon tuner driver
3 *
4 * Copyright (C) 2010 Antti Palosaari <crope@iki.fi>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, write to the Free Software
18 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
19 */
20
21#ifndef TDA18218_H
22#define TDA18218_H
23
24#include "dvb_frontend.h"
25
26struct tda18218_config {
27 u8 i2c_address;
28 u8 i2c_wr_max;
29 u8 loop_through:1;
30};
31
32#if defined(CONFIG_MEDIA_TUNER_TDA18218) || \
33 (defined(CONFIG_MEDIA_TUNER_TDA18218_MODULE) && defined(MODULE))
34extern struct dvb_frontend *tda18218_attach(struct dvb_frontend *fe,
35 struct i2c_adapter *i2c, struct tda18218_config *cfg);
36#else
37static inline struct dvb_frontend *tda18218_attach(struct dvb_frontend *fe,
38 struct i2c_adapter *i2c, struct tda18218_config *cfg)
39{
40 printk(KERN_WARNING "%s: driver disabled by Kconfig\n", __func__);
41 return NULL;
42}
43#endif
44
45#endif
diff --git a/drivers/media/common/tuners/tda18218_priv.h b/drivers/media/common/tuners/tda18218_priv.h
new file mode 100644
index 00000000000..904e5365c78
--- /dev/null
+++ b/drivers/media/common/tuners/tda18218_priv.h
@@ -0,0 +1,106 @@
1/*
2 * NXP TDA18218HN silicon tuner driver
3 *
4 * Copyright (C) 2010 Antti Palosaari <crope@iki.fi>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, write to the Free Software
18 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
19 */
20
21#ifndef TDA18218_PRIV_H
22#define TDA18218_PRIV_H
23
24#define LOG_PREFIX "tda18218"
25
26#undef dbg
27#define dbg(f, arg...) \
28 if (debug) \
29 printk(KERN_DEBUG LOG_PREFIX": " f "\n" , ## arg)
30#undef err
31#define err(f, arg...) printk(KERN_ERR LOG_PREFIX": " f "\n" , ## arg)
32#undef info
33#define info(f, arg...) printk(KERN_INFO LOG_PREFIX": " f "\n" , ## arg)
34#undef warn
35#define warn(f, arg...) printk(KERN_WARNING LOG_PREFIX": " f "\n" , ## arg)
36
37#define R00_ID 0x00 /* ID byte */
38#define R01_R1 0x01 /* Read byte 1 */
39#define R02_R2 0x02 /* Read byte 2 */
40#define R03_R3 0x03 /* Read byte 3 */
41#define R04_R4 0x04 /* Read byte 4 */
42#define R05_R5 0x05 /* Read byte 5 */
43#define R06_R6 0x06 /* Read byte 6 */
44#define R07_MD1 0x07 /* Main divider byte 1 */
45#define R08_PSM1 0x08 /* PSM byte 1 */
46#define R09_MD2 0x09 /* Main divider byte 2 */
47#define R0A_MD3 0x0a /* Main divider byte 1 */
48#define R0B_MD4 0x0b /* Main divider byte 4 */
49#define R0C_MD5 0x0c /* Main divider byte 5 */
50#define R0D_MD6 0x0d /* Main divider byte 6 */
51#define R0E_MD7 0x0e /* Main divider byte 7 */
52#define R0F_MD8 0x0f /* Main divider byte 8 */
53#define R10_CD1 0x10 /* Call divider byte 1 */
54#define R11_CD2 0x11 /* Call divider byte 2 */
55#define R12_CD3 0x12 /* Call divider byte 3 */
56#define R13_CD4 0x13 /* Call divider byte 4 */
57#define R14_CD5 0x14 /* Call divider byte 5 */
58#define R15_CD6 0x15 /* Call divider byte 6 */
59#define R16_CD7 0x16 /* Call divider byte 7 */
60#define R17_PD1 0x17 /* Power-down byte 1 */
61#define R18_PD2 0x18 /* Power-down byte 2 */
62#define R19_XTOUT 0x19 /* XTOUT byte */
63#define R1A_IF1 0x1a /* IF byte 1 */
64#define R1B_IF2 0x1b /* IF byte 2 */
65#define R1C_AGC2B 0x1c /* AGC2b byte */
66#define R1D_PSM2 0x1d /* PSM byte 2 */
67#define R1E_PSM3 0x1e /* PSM byte 3 */
68#define R1F_PSM4 0x1f /* PSM byte 4 */
69#define R20_AGC11 0x20 /* AGC1 byte 1 */
70#define R21_AGC12 0x21 /* AGC1 byte 2 */
71#define R22_AGC13 0x22 /* AGC1 byte 3 */
72#define R23_AGC21 0x23 /* AGC2 byte 1 */
73#define R24_AGC22 0x24 /* AGC2 byte 2 */
74#define R25_AAGC 0x25 /* Analog AGC byte */
75#define R26_RC 0x26 /* RC byte */
76#define R27_RSSI 0x27 /* RSSI byte */
77#define R28_IRCAL1 0x28 /* IR CAL byte 1 */
78#define R29_IRCAL2 0x29 /* IR CAL byte 2 */
79#define R2A_IRCAL3 0x2a /* IR CAL byte 3 */
80#define R2B_IRCAL4 0x2b /* IR CAL byte 4 */
81#define R2C_RFCAL1 0x2c /* RF CAL byte 1 */
82#define R2D_RFCAL2 0x2d /* RF CAL byte 2 */
83#define R2E_RFCAL3 0x2e /* RF CAL byte 3 */
84#define R2F_RFCAL4 0x2f /* RF CAL byte 4 */
85#define R30_RFCAL5 0x30 /* RF CAL byte 5 */
86#define R31_RFCAL6 0x31 /* RF CAL byte 6 */
87#define R32_RFCAL7 0x32 /* RF CAL byte 7 */
88#define R33_RFCAL8 0x33 /* RF CAL byte 8 */
89#define R34_RFCAL9 0x34 /* RF CAL byte 9 */
90#define R35_RFCAL10 0x35 /* RF CAL byte 10 */
91#define R36_RFCALRAM1 0x36 /* RF CAL RAM byte 1 */
92#define R37_RFCALRAM2 0x37 /* RF CAL RAM byte 2 */
93#define R38_MARGIN 0x38 /* Margin byte */
94#define R39_FMAX1 0x39 /* Fmax byte 1 */
95#define R3A_FMAX2 0x3a /* Fmax byte 2 */
96
97#define TDA18218_NUM_REGS 59
98
99struct tda18218_priv {
100 struct tda18218_config *cfg;
101 struct i2c_adapter *i2c;
102
103 u8 regs[TDA18218_NUM_REGS];
104};
105
106#endif
diff --git a/drivers/media/common/tuners/tda18271-common.c b/drivers/media/common/tuners/tda18271-common.c
new file mode 100644
index 00000000000..aae40e52af5
--- /dev/null
+++ b/drivers/media/common/tuners/tda18271-common.c
@@ -0,0 +1,685 @@
1/*
2 tda18271-common.c - driver for the Philips / NXP TDA18271 silicon tuner
3
4 Copyright (C) 2007, 2008 Michael Krufky <mkrufky@linuxtv.org>
5
6 This program is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 2 of the License, or
9 (at your option) any later version.
10
11 This program is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
15
16 You should have received a copy of the GNU General Public License
17 along with this program; if not, write to the Free Software
18 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
19*/
20
21#include "tda18271-priv.h"
22
23static int tda18271_i2c_gate_ctrl(struct dvb_frontend *fe, int enable)
24{
25 struct tda18271_priv *priv = fe->tuner_priv;
26 enum tda18271_i2c_gate gate;
27 int ret = 0;
28
29 switch (priv->gate) {
30 case TDA18271_GATE_DIGITAL:
31 case TDA18271_GATE_ANALOG:
32 gate = priv->gate;
33 break;
34 case TDA18271_GATE_AUTO:
35 default:
36 switch (priv->mode) {
37 case TDA18271_DIGITAL:
38 gate = TDA18271_GATE_DIGITAL;
39 break;
40 case TDA18271_ANALOG:
41 default:
42 gate = TDA18271_GATE_ANALOG;
43 break;
44 }
45 }
46
47 switch (gate) {
48 case TDA18271_GATE_ANALOG:
49 if (fe->ops.analog_ops.i2c_gate_ctrl)
50 ret = fe->ops.analog_ops.i2c_gate_ctrl(fe, enable);
51 break;
52 case TDA18271_GATE_DIGITAL:
53 if (fe->ops.i2c_gate_ctrl)
54 ret = fe->ops.i2c_gate_ctrl(fe, enable);
55 break;
56 default:
57 ret = -EINVAL;
58 break;
59 }
60
61 return ret;
62};
63
64/*---------------------------------------------------------------------*/
65
66static void tda18271_dump_regs(struct dvb_frontend *fe, int extended)
67{
68 struct tda18271_priv *priv = fe->tuner_priv;
69 unsigned char *regs = priv->tda18271_regs;
70
71 tda_reg("=== TDA18271 REG DUMP ===\n");
72 tda_reg("ID_BYTE = 0x%02x\n", 0xff & regs[R_ID]);
73 tda_reg("THERMO_BYTE = 0x%02x\n", 0xff & regs[R_TM]);
74 tda_reg("POWER_LEVEL_BYTE = 0x%02x\n", 0xff & regs[R_PL]);
75 tda_reg("EASY_PROG_BYTE_1 = 0x%02x\n", 0xff & regs[R_EP1]);
76 tda_reg("EASY_PROG_BYTE_2 = 0x%02x\n", 0xff & regs[R_EP2]);
77 tda_reg("EASY_PROG_BYTE_3 = 0x%02x\n", 0xff & regs[R_EP3]);
78 tda_reg("EASY_PROG_BYTE_4 = 0x%02x\n", 0xff & regs[R_EP4]);
79 tda_reg("EASY_PROG_BYTE_5 = 0x%02x\n", 0xff & regs[R_EP5]);
80 tda_reg("CAL_POST_DIV_BYTE = 0x%02x\n", 0xff & regs[R_CPD]);
81 tda_reg("CAL_DIV_BYTE_1 = 0x%02x\n", 0xff & regs[R_CD1]);
82 tda_reg("CAL_DIV_BYTE_2 = 0x%02x\n", 0xff & regs[R_CD2]);
83 tda_reg("CAL_DIV_BYTE_3 = 0x%02x\n", 0xff & regs[R_CD3]);
84 tda_reg("MAIN_POST_DIV_BYTE = 0x%02x\n", 0xff & regs[R_MPD]);
85 tda_reg("MAIN_DIV_BYTE_1 = 0x%02x\n", 0xff & regs[R_MD1]);
86 tda_reg("MAIN_DIV_BYTE_2 = 0x%02x\n", 0xff & regs[R_MD2]);
87 tda_reg("MAIN_DIV_BYTE_3 = 0x%02x\n", 0xff & regs[R_MD3]);
88
89 /* only dump extended regs if DBG_ADV is set */
90 if (!(tda18271_debug & DBG_ADV))
91 return;
92
93 /* W indicates write-only registers.
94 * Register dump for write-only registers shows last value written. */
95
96 tda_reg("EXTENDED_BYTE_1 = 0x%02x\n", 0xff & regs[R_EB1]);
97 tda_reg("EXTENDED_BYTE_2 = 0x%02x\n", 0xff & regs[R_EB2]);
98 tda_reg("EXTENDED_BYTE_3 = 0x%02x\n", 0xff & regs[R_EB3]);
99 tda_reg("EXTENDED_BYTE_4 = 0x%02x\n", 0xff & regs[R_EB4]);
100 tda_reg("EXTENDED_BYTE_5 = 0x%02x\n", 0xff & regs[R_EB5]);
101 tda_reg("EXTENDED_BYTE_6 = 0x%02x\n", 0xff & regs[R_EB6]);
102 tda_reg("EXTENDED_BYTE_7 = 0x%02x\n", 0xff & regs[R_EB7]);
103 tda_reg("EXTENDED_BYTE_8 = 0x%02x\n", 0xff & regs[R_EB8]);
104 tda_reg("EXTENDED_BYTE_9 W = 0x%02x\n", 0xff & regs[R_EB9]);
105 tda_reg("EXTENDED_BYTE_10 = 0x%02x\n", 0xff & regs[R_EB10]);
106 tda_reg("EXTENDED_BYTE_11 = 0x%02x\n", 0xff & regs[R_EB11]);
107 tda_reg("EXTENDED_BYTE_12 = 0x%02x\n", 0xff & regs[R_EB12]);
108 tda_reg("EXTENDED_BYTE_13 = 0x%02x\n", 0xff & regs[R_EB13]);
109 tda_reg("EXTENDED_BYTE_14 = 0x%02x\n", 0xff & regs[R_EB14]);
110 tda_reg("EXTENDED_BYTE_15 = 0x%02x\n", 0xff & regs[R_EB15]);
111 tda_reg("EXTENDED_BYTE_16 W = 0x%02x\n", 0xff & regs[R_EB16]);
112 tda_reg("EXTENDED_BYTE_17 W = 0x%02x\n", 0xff & regs[R_EB17]);
113 tda_reg("EXTENDED_BYTE_18 = 0x%02x\n", 0xff & regs[R_EB18]);
114 tda_reg("EXTENDED_BYTE_19 W = 0x%02x\n", 0xff & regs[R_EB19]);
115 tda_reg("EXTENDED_BYTE_20 W = 0x%02x\n", 0xff & regs[R_EB20]);
116 tda_reg("EXTENDED_BYTE_21 = 0x%02x\n", 0xff & regs[R_EB21]);
117 tda_reg("EXTENDED_BYTE_22 = 0x%02x\n", 0xff & regs[R_EB22]);
118 tda_reg("EXTENDED_BYTE_23 = 0x%02x\n", 0xff & regs[R_EB23]);
119}
120
121int tda18271_read_regs(struct dvb_frontend *fe)
122{
123 struct tda18271_priv *priv = fe->tuner_priv;
124 unsigned char *regs = priv->tda18271_regs;
125 unsigned char buf = 0x00;
126 int ret;
127 struct i2c_msg msg[] = {
128 { .addr = priv->i2c_props.addr, .flags = 0,
129 .buf = &buf, .len = 1 },
130 { .addr = priv->i2c_props.addr, .flags = I2C_M_RD,
131 .buf = regs, .len = 16 }
132 };
133
134 tda18271_i2c_gate_ctrl(fe, 1);
135
136 /* read all registers */
137 ret = i2c_transfer(priv->i2c_props.adap, msg, 2);
138
139 tda18271_i2c_gate_ctrl(fe, 0);
140
141 if (ret != 2)
142 tda_err("ERROR: i2c_transfer returned: %d\n", ret);
143
144 if (tda18271_debug & DBG_REG)
145 tda18271_dump_regs(fe, 0);
146
147 return (ret == 2 ? 0 : ret);
148}
149
150int tda18271_read_extended(struct dvb_frontend *fe)
151{
152 struct tda18271_priv *priv = fe->tuner_priv;
153 unsigned char *regs = priv->tda18271_regs;
154 unsigned char regdump[TDA18271_NUM_REGS];
155 unsigned char buf = 0x00;
156 int ret, i;
157 struct i2c_msg msg[] = {
158 { .addr = priv->i2c_props.addr, .flags = 0,
159 .buf = &buf, .len = 1 },
160 { .addr = priv->i2c_props.addr, .flags = I2C_M_RD,
161 .buf = regdump, .len = TDA18271_NUM_REGS }
162 };
163
164 tda18271_i2c_gate_ctrl(fe, 1);
165
166 /* read all registers */
167 ret = i2c_transfer(priv->i2c_props.adap, msg, 2);
168
169 tda18271_i2c_gate_ctrl(fe, 0);
170
171 if (ret != 2)
172 tda_err("ERROR: i2c_transfer returned: %d\n", ret);
173
174 for (i = 0; i < TDA18271_NUM_REGS; i++) {
175 /* don't update write-only registers */
176 if ((i != R_EB9) &&
177 (i != R_EB16) &&
178 (i != R_EB17) &&
179 (i != R_EB19) &&
180 (i != R_EB20))
181 regs[i] = regdump[i];
182 }
183
184 if (tda18271_debug & DBG_REG)
185 tda18271_dump_regs(fe, 1);
186
187 return (ret == 2 ? 0 : ret);
188}
189
190int tda18271_write_regs(struct dvb_frontend *fe, int idx, int len)
191{
192 struct tda18271_priv *priv = fe->tuner_priv;
193 unsigned char *regs = priv->tda18271_regs;
194 unsigned char buf[TDA18271_NUM_REGS + 1];
195 struct i2c_msg msg = { .addr = priv->i2c_props.addr, .flags = 0,
196 .buf = buf };
197 int i, ret = 1, max;
198
199 BUG_ON((len == 0) || (idx + len > sizeof(buf)));
200
201
202 switch (priv->small_i2c) {
203 case TDA18271_03_BYTE_CHUNK_INIT:
204 max = 3;
205 break;
206 case TDA18271_08_BYTE_CHUNK_INIT:
207 max = 8;
208 break;
209 case TDA18271_16_BYTE_CHUNK_INIT:
210 max = 16;
211 break;
212 case TDA18271_39_BYTE_CHUNK_INIT:
213 default:
214 max = 39;
215 }
216
217 tda18271_i2c_gate_ctrl(fe, 1);
218 while (len) {
219 if (max > len)
220 max = len;
221
222 buf[0] = idx;
223 for (i = 1; i <= max; i++)
224 buf[i] = regs[idx - 1 + i];
225
226 msg.len = max + 1;
227
228 /* write registers */
229 ret = i2c_transfer(priv->i2c_props.adap, &msg, 1);
230 if (ret != 1)
231 break;
232
233 idx += max;
234 len -= max;
235 }
236 tda18271_i2c_gate_ctrl(fe, 0);
237
238 if (ret != 1)
239 tda_err("ERROR: idx = 0x%x, len = %d, "
240 "i2c_transfer returned: %d\n", idx, max, ret);
241
242 return (ret == 1 ? 0 : ret);
243}
244
245/*---------------------------------------------------------------------*/
246
247int tda18271_charge_pump_source(struct dvb_frontend *fe,
248 enum tda18271_pll pll, int force)
249{
250 struct tda18271_priv *priv = fe->tuner_priv;
251 unsigned char *regs = priv->tda18271_regs;
252
253 int r_cp = (pll == TDA18271_CAL_PLL) ? R_EB7 : R_EB4;
254
255 regs[r_cp] &= ~0x20;
256 regs[r_cp] |= ((force & 1) << 5);
257
258 return tda18271_write_regs(fe, r_cp, 1);
259}
260
261int tda18271_init_regs(struct dvb_frontend *fe)
262{
263 struct tda18271_priv *priv = fe->tuner_priv;
264 unsigned char *regs = priv->tda18271_regs;
265
266 tda_dbg("initializing registers for device @ %d-%04x\n",
267 i2c_adapter_id(priv->i2c_props.adap),
268 priv->i2c_props.addr);
269
270 /* initialize registers */
271 switch (priv->id) {
272 case TDA18271HDC1:
273 regs[R_ID] = 0x83;
274 break;
275 case TDA18271HDC2:
276 regs[R_ID] = 0x84;
277 break;
278 };
279
280 regs[R_TM] = 0x08;
281 regs[R_PL] = 0x80;
282 regs[R_EP1] = 0xc6;
283 regs[R_EP2] = 0xdf;
284 regs[R_EP3] = 0x16;
285 regs[R_EP4] = 0x60;
286 regs[R_EP5] = 0x80;
287 regs[R_CPD] = 0x80;
288 regs[R_CD1] = 0x00;
289 regs[R_CD2] = 0x00;
290 regs[R_CD3] = 0x00;
291 regs[R_MPD] = 0x00;
292 regs[R_MD1] = 0x00;
293 regs[R_MD2] = 0x00;
294 regs[R_MD3] = 0x00;
295
296 switch (priv->id) {
297 case TDA18271HDC1:
298 regs[R_EB1] = 0xff;
299 break;
300 case TDA18271HDC2:
301 regs[R_EB1] = 0xfc;
302 break;
303 };
304
305 regs[R_EB2] = 0x01;
306 regs[R_EB3] = 0x84;
307 regs[R_EB4] = 0x41;
308 regs[R_EB5] = 0x01;
309 regs[R_EB6] = 0x84;
310 regs[R_EB7] = 0x40;
311 regs[R_EB8] = 0x07;
312 regs[R_EB9] = 0x00;
313 regs[R_EB10] = 0x00;
314 regs[R_EB11] = 0x96;
315
316 switch (priv->id) {
317 case TDA18271HDC1:
318 regs[R_EB12] = 0x0f;
319 break;
320 case TDA18271HDC2:
321 regs[R_EB12] = 0x33;
322 break;
323 };
324
325 regs[R_EB13] = 0xc1;
326 regs[R_EB14] = 0x00;
327 regs[R_EB15] = 0x8f;
328 regs[R_EB16] = 0x00;
329 regs[R_EB17] = 0x00;
330
331 switch (priv->id) {
332 case TDA18271HDC1:
333 regs[R_EB18] = 0x00;
334 break;
335 case TDA18271HDC2:
336 regs[R_EB18] = 0x8c;
337 break;
338 };
339
340 regs[R_EB19] = 0x00;
341 regs[R_EB20] = 0x20;
342
343 switch (priv->id) {
344 case TDA18271HDC1:
345 regs[R_EB21] = 0x33;
346 break;
347 case TDA18271HDC2:
348 regs[R_EB21] = 0xb3;
349 break;
350 };
351
352 regs[R_EB22] = 0x48;
353 regs[R_EB23] = 0xb0;
354
355 tda18271_write_regs(fe, 0x00, TDA18271_NUM_REGS);
356
357 /* setup agc1 gain */
358 regs[R_EB17] = 0x00;
359 tda18271_write_regs(fe, R_EB17, 1);
360 regs[R_EB17] = 0x03;
361 tda18271_write_regs(fe, R_EB17, 1);
362 regs[R_EB17] = 0x43;
363 tda18271_write_regs(fe, R_EB17, 1);
364 regs[R_EB17] = 0x4c;
365 tda18271_write_regs(fe, R_EB17, 1);
366
367 /* setup agc2 gain */
368 if ((priv->id) == TDA18271HDC1) {
369 regs[R_EB20] = 0xa0;
370 tda18271_write_regs(fe, R_EB20, 1);
371 regs[R_EB20] = 0xa7;
372 tda18271_write_regs(fe, R_EB20, 1);
373 regs[R_EB20] = 0xe7;
374 tda18271_write_regs(fe, R_EB20, 1);
375 regs[R_EB20] = 0xec;
376 tda18271_write_regs(fe, R_EB20, 1);
377 }
378
379 /* image rejection calibration */
380
381 /* low-band */
382 regs[R_EP3] = 0x1f;
383 regs[R_EP4] = 0x66;
384 regs[R_EP5] = 0x81;
385 regs[R_CPD] = 0xcc;
386 regs[R_CD1] = 0x6c;
387 regs[R_CD2] = 0x00;
388 regs[R_CD3] = 0x00;
389 regs[R_MPD] = 0xcd;
390 regs[R_MD1] = 0x77;
391 regs[R_MD2] = 0x08;
392 regs[R_MD3] = 0x00;
393
394 tda18271_write_regs(fe, R_EP3, 11);
395
396 if ((priv->id) == TDA18271HDC2) {
397 /* main pll cp source on */
398 tda18271_charge_pump_source(fe, TDA18271_MAIN_PLL, 1);
399 msleep(1);
400
401 /* main pll cp source off */
402 tda18271_charge_pump_source(fe, TDA18271_MAIN_PLL, 0);
403 }
404
405 msleep(5); /* pll locking */
406
407 /* launch detector */
408 tda18271_write_regs(fe, R_EP1, 1);
409 msleep(5); /* wanted low measurement */
410
411 regs[R_EP5] = 0x85;
412 regs[R_CPD] = 0xcb;
413 regs[R_CD1] = 0x66;
414 regs[R_CD2] = 0x70;
415
416 tda18271_write_regs(fe, R_EP3, 7);
417 msleep(5); /* pll locking */
418
419 /* launch optimization algorithm */
420 tda18271_write_regs(fe, R_EP2, 1);
421 msleep(30); /* image low optimization completion */
422
423 /* mid-band */
424 regs[R_EP5] = 0x82;
425 regs[R_CPD] = 0xa8;
426 regs[R_CD2] = 0x00;
427 regs[R_MPD] = 0xa9;
428 regs[R_MD1] = 0x73;
429 regs[R_MD2] = 0x1a;
430
431 tda18271_write_regs(fe, R_EP3, 11);
432 msleep(5); /* pll locking */
433
434 /* launch detector */
435 tda18271_write_regs(fe, R_EP1, 1);
436 msleep(5); /* wanted mid measurement */
437
438 regs[R_EP5] = 0x86;
439 regs[R_CPD] = 0xa8;
440 regs[R_CD1] = 0x66;
441 regs[R_CD2] = 0xa0;
442
443 tda18271_write_regs(fe, R_EP3, 7);
444 msleep(5); /* pll locking */
445
446 /* launch optimization algorithm */
447 tda18271_write_regs(fe, R_EP2, 1);
448 msleep(30); /* image mid optimization completion */
449
450 /* high-band */
451 regs[R_EP5] = 0x83;
452 regs[R_CPD] = 0x98;
453 regs[R_CD1] = 0x65;
454 regs[R_CD2] = 0x00;
455 regs[R_MPD] = 0x99;
456 regs[R_MD1] = 0x71;
457 regs[R_MD2] = 0xcd;
458
459 tda18271_write_regs(fe, R_EP3, 11);
460 msleep(5); /* pll locking */
461
462 /* launch detector */
463 tda18271_write_regs(fe, R_EP1, 1);
464 msleep(5); /* wanted high measurement */
465
466 regs[R_EP5] = 0x87;
467 regs[R_CD1] = 0x65;
468 regs[R_CD2] = 0x50;
469
470 tda18271_write_regs(fe, R_EP3, 7);
471 msleep(5); /* pll locking */
472
473 /* launch optimization algorithm */
474 tda18271_write_regs(fe, R_EP2, 1);
475 msleep(30); /* image high optimization completion */
476
477 /* return to normal mode */
478 regs[R_EP4] = 0x64;
479 tda18271_write_regs(fe, R_EP4, 1);
480
481 /* synchronize */
482 tda18271_write_regs(fe, R_EP1, 1);
483
484 return 0;
485}
486
487/*---------------------------------------------------------------------*/
488
489/*
490 * Standby modes, EP3 [7:5]
491 *
492 * | SM || SM_LT || SM_XT || mode description
493 * |=====\\=======\\=======\\===================================
494 * | 0 || 0 || 0 || normal mode
495 * |-----||-------||-------||-----------------------------------
496 * | || || || standby mode w/ slave tuner output
497 * | 1 || 0 || 0 || & loop thru & xtal oscillator on
498 * |-----||-------||-------||-----------------------------------
499 * | 1 || 1 || 0 || standby mode w/ xtal oscillator on
500 * |-----||-------||-------||-----------------------------------
501 * | 1 || 1 || 1 || power off
502 *
503 */
504
505int tda18271_set_standby_mode(struct dvb_frontend *fe,
506 int sm, int sm_lt, int sm_xt)
507{
508 struct tda18271_priv *priv = fe->tuner_priv;
509 unsigned char *regs = priv->tda18271_regs;
510
511 if (tda18271_debug & DBG_ADV)
512 tda_dbg("sm = %d, sm_lt = %d, sm_xt = %d\n", sm, sm_lt, sm_xt);
513
514 regs[R_EP3] &= ~0xe0; /* clear sm, sm_lt, sm_xt */
515 regs[R_EP3] |= (sm ? (1 << 7) : 0) |
516 (sm_lt ? (1 << 6) : 0) |
517 (sm_xt ? (1 << 5) : 0);
518
519 return tda18271_write_regs(fe, R_EP3, 1);
520}
521
522/*---------------------------------------------------------------------*/
523
524int tda18271_calc_main_pll(struct dvb_frontend *fe, u32 freq)
525{
526 /* sets main post divider & divider bytes, but does not write them */
527 struct tda18271_priv *priv = fe->tuner_priv;
528 unsigned char *regs = priv->tda18271_regs;
529 u8 d, pd;
530 u32 div;
531
532 int ret = tda18271_lookup_pll_map(fe, MAIN_PLL, &freq, &pd, &d);
533 if (tda_fail(ret))
534 goto fail;
535
536 regs[R_MPD] = (0x7f & pd);
537
538 div = ((d * (freq / 1000)) << 7) / 125;
539
540 regs[R_MD1] = 0x7f & (div >> 16);
541 regs[R_MD2] = 0xff & (div >> 8);
542 regs[R_MD3] = 0xff & div;
543fail:
544 return ret;
545}
546
547int tda18271_calc_cal_pll(struct dvb_frontend *fe, u32 freq)
548{
549 /* sets cal post divider & divider bytes, but does not write them */
550 struct tda18271_priv *priv = fe->tuner_priv;
551 unsigned char *regs = priv->tda18271_regs;
552 u8 d, pd;
553 u32 div;
554
555 int ret = tda18271_lookup_pll_map(fe, CAL_PLL, &freq, &pd, &d);
556 if (tda_fail(ret))
557 goto fail;
558
559 regs[R_CPD] = pd;
560
561 div = ((d * (freq / 1000)) << 7) / 125;
562
563 regs[R_CD1] = 0x7f & (div >> 16);
564 regs[R_CD2] = 0xff & (div >> 8);
565 regs[R_CD3] = 0xff & div;
566fail:
567 return ret;
568}
569
570/*---------------------------------------------------------------------*/
571
572int tda18271_calc_bp_filter(struct dvb_frontend *fe, u32 *freq)
573{
574 /* sets bp filter bits, but does not write them */
575 struct tda18271_priv *priv = fe->tuner_priv;
576 unsigned char *regs = priv->tda18271_regs;
577 u8 val;
578
579 int ret = tda18271_lookup_map(fe, BP_FILTER, freq, &val);
580 if (tda_fail(ret))
581 goto fail;
582
583 regs[R_EP1] &= ~0x07; /* clear bp filter bits */
584 regs[R_EP1] |= (0x07 & val);
585fail:
586 return ret;
587}
588
589int tda18271_calc_km(struct dvb_frontend *fe, u32 *freq)
590{
591 /* sets K & M bits, but does not write them */
592 struct tda18271_priv *priv = fe->tuner_priv;
593 unsigned char *regs = priv->tda18271_regs;
594 u8 val;
595
596 int ret = tda18271_lookup_map(fe, RF_CAL_KMCO, freq, &val);
597 if (tda_fail(ret))
598 goto fail;
599
600 regs[R_EB13] &= ~0x7c; /* clear k & m bits */
601 regs[R_EB13] |= (0x7c & val);
602fail:
603 return ret;
604}
605
606int tda18271_calc_rf_band(struct dvb_frontend *fe, u32 *freq)
607{
608 /* sets rf band bits, but does not write them */
609 struct tda18271_priv *priv = fe->tuner_priv;
610 unsigned char *regs = priv->tda18271_regs;
611 u8 val;
612
613 int ret = tda18271_lookup_map(fe, RF_BAND, freq, &val);
614 if (tda_fail(ret))
615 goto fail;
616
617 regs[R_EP2] &= ~0xe0; /* clear rf band bits */
618 regs[R_EP2] |= (0xe0 & (val << 5));
619fail:
620 return ret;
621}
622
623int tda18271_calc_gain_taper(struct dvb_frontend *fe, u32 *freq)
624{
625 /* sets gain taper bits, but does not write them */
626 struct tda18271_priv *priv = fe->tuner_priv;
627 unsigned char *regs = priv->tda18271_regs;
628 u8 val;
629
630 int ret = tda18271_lookup_map(fe, GAIN_TAPER, freq, &val);
631 if (tda_fail(ret))
632 goto fail;
633
634 regs[R_EP2] &= ~0x1f; /* clear gain taper bits */
635 regs[R_EP2] |= (0x1f & val);
636fail:
637 return ret;
638}
639
640int tda18271_calc_ir_measure(struct dvb_frontend *fe, u32 *freq)
641{
642 /* sets IR Meas bits, but does not write them */
643 struct tda18271_priv *priv = fe->tuner_priv;
644 unsigned char *regs = priv->tda18271_regs;
645 u8 val;
646
647 int ret = tda18271_lookup_map(fe, IR_MEASURE, freq, &val);
648 if (tda_fail(ret))
649 goto fail;
650
651 regs[R_EP5] &= ~0x07;
652 regs[R_EP5] |= (0x07 & val);
653fail:
654 return ret;
655}
656
657int tda18271_calc_rf_cal(struct dvb_frontend *fe, u32 *freq)
658{
659 /* sets rf cal byte (RFC_Cprog), but does not write it */
660 struct tda18271_priv *priv = fe->tuner_priv;
661 unsigned char *regs = priv->tda18271_regs;
662 u8 val;
663
664 int ret = tda18271_lookup_map(fe, RF_CAL, freq, &val);
665 /* The TDA18271HD/C1 rf_cal map lookup is expected to go out of range
666 * for frequencies above 61.1 MHz. In these cases, the internal RF
667 * tracking filters calibration mechanism is used.
668 *
669 * There is no need to warn the user about this.
670 */
671 if (ret < 0)
672 goto fail;
673
674 regs[R_EB14] = val;
675fail:
676 return ret;
677}
678
679/*
680 * Overrides for Emacs so that we follow Linus's tabbing style.
681 * ---------------------------------------------------------------------------
682 * Local variables:
683 * c-basic-offset: 8
684 * End:
685 */
diff --git a/drivers/media/common/tuners/tda18271-fe.c b/drivers/media/common/tuners/tda18271-fe.c
new file mode 100644
index 00000000000..57022e88e33
--- /dev/null
+++ b/drivers/media/common/tuners/tda18271-fe.c
@@ -0,0 +1,1346 @@
1/*
2 tda18271-fe.c - driver for the Philips / NXP TDA18271 silicon tuner
3
4 Copyright (C) 2007, 2008 Michael Krufky <mkrufky@linuxtv.org>
5
6 This program is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 2 of the License, or
9 (at your option) any later version.
10
11 This program is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
15
16 You should have received a copy of the GNU General Public License
17 along with this program; if not, write to the Free Software
18 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
19*/
20
21#include <linux/delay.h>
22#include <linux/videodev2.h>
23#include "tda18271-priv.h"
24
25int tda18271_debug;
26module_param_named(debug, tda18271_debug, int, 0644);
27MODULE_PARM_DESC(debug, "set debug level "
28 "(info=1, map=2, reg=4, adv=8, cal=16 (or-able))");
29
30static int tda18271_cal_on_startup = -1;
31module_param_named(cal, tda18271_cal_on_startup, int, 0644);
32MODULE_PARM_DESC(cal, "perform RF tracking filter calibration on startup");
33
34static DEFINE_MUTEX(tda18271_list_mutex);
35static LIST_HEAD(hybrid_tuner_instance_list);
36
37/*---------------------------------------------------------------------*/
38
39static int tda18271_toggle_output(struct dvb_frontend *fe, int standby)
40{
41 struct tda18271_priv *priv = fe->tuner_priv;
42
43 int ret = tda18271_set_standby_mode(fe, standby ? 1 : 0,
44 priv->output_opt & TDA18271_OUTPUT_LT_OFF ? 1 : 0,
45 priv->output_opt & TDA18271_OUTPUT_XT_OFF ? 1 : 0);
46
47 if (tda_fail(ret))
48 goto fail;
49
50 tda_dbg("%s mode: xtal oscillator %s, slave tuner loop thru %s\n",
51 standby ? "standby" : "active",
52 priv->output_opt & TDA18271_OUTPUT_XT_OFF ? "off" : "on",
53 priv->output_opt & TDA18271_OUTPUT_LT_OFF ? "off" : "on");
54fail:
55 return ret;
56}
57
58/*---------------------------------------------------------------------*/
59
60static inline int charge_pump_source(struct dvb_frontend *fe, int force)
61{
62 struct tda18271_priv *priv = fe->tuner_priv;
63 return tda18271_charge_pump_source(fe,
64 (priv->role == TDA18271_SLAVE) ?
65 TDA18271_CAL_PLL :
66 TDA18271_MAIN_PLL, force);
67}
68
69static inline void tda18271_set_if_notch(struct dvb_frontend *fe)
70{
71 struct tda18271_priv *priv = fe->tuner_priv;
72 unsigned char *regs = priv->tda18271_regs;
73
74 switch (priv->mode) {
75 case TDA18271_ANALOG:
76 regs[R_MPD] &= ~0x80; /* IF notch = 0 */
77 break;
78 case TDA18271_DIGITAL:
79 regs[R_MPD] |= 0x80; /* IF notch = 1 */
80 break;
81 }
82}
83
84static int tda18271_channel_configuration(struct dvb_frontend *fe,
85 struct tda18271_std_map_item *map,
86 u32 freq, u32 bw)
87{
88 struct tda18271_priv *priv = fe->tuner_priv;
89 unsigned char *regs = priv->tda18271_regs;
90 int ret;
91 u32 N;
92
93 /* update TV broadcast parameters */
94
95 /* set standard */
96 regs[R_EP3] &= ~0x1f; /* clear std bits */
97 regs[R_EP3] |= (map->agc_mode << 3) | map->std;
98
99 if (priv->id == TDA18271HDC2) {
100 /* set rfagc to high speed mode */
101 regs[R_EP3] &= ~0x04;
102 }
103
104 /* set cal mode to normal */
105 regs[R_EP4] &= ~0x03;
106
107 /* update IF output level */
108 regs[R_EP4] &= ~0x1c; /* clear if level bits */
109 regs[R_EP4] |= (map->if_lvl << 2);
110
111 /* update FM_RFn */
112 regs[R_EP4] &= ~0x80;
113 regs[R_EP4] |= map->fm_rfn << 7;
114
115 /* update rf top / if top */
116 regs[R_EB22] = 0x00;
117 regs[R_EB22] |= map->rfagc_top;
118 ret = tda18271_write_regs(fe, R_EB22, 1);
119 if (tda_fail(ret))
120 goto fail;
121
122 /* --------------------------------------------------------------- */
123
124 /* disable Power Level Indicator */
125 regs[R_EP1] |= 0x40;
126
127 /* make sure thermometer is off */
128 regs[R_TM] &= ~0x10;
129
130 /* frequency dependent parameters */
131
132 tda18271_calc_ir_measure(fe, &freq);
133
134 tda18271_calc_bp_filter(fe, &freq);
135
136 tda18271_calc_rf_band(fe, &freq);
137
138 tda18271_calc_gain_taper(fe, &freq);
139
140 /* --------------------------------------------------------------- */
141
142 /* dual tuner and agc1 extra configuration */
143
144 switch (priv->role) {
145 case TDA18271_MASTER:
146 regs[R_EB1] |= 0x04; /* main vco */
147 break;
148 case TDA18271_SLAVE:
149 regs[R_EB1] &= ~0x04; /* cal vco */
150 break;
151 }
152
153 /* agc1 always active */
154 regs[R_EB1] &= ~0x02;
155
156 /* agc1 has priority on agc2 */
157 regs[R_EB1] &= ~0x01;
158
159 ret = tda18271_write_regs(fe, R_EB1, 1);
160 if (tda_fail(ret))
161 goto fail;
162
163 /* --------------------------------------------------------------- */
164
165 N = map->if_freq * 1000 + freq;
166
167 switch (priv->role) {
168 case TDA18271_MASTER:
169 tda18271_calc_main_pll(fe, N);
170 tda18271_set_if_notch(fe);
171 tda18271_write_regs(fe, R_MPD, 4);
172 break;
173 case TDA18271_SLAVE:
174 tda18271_calc_cal_pll(fe, N);
175 tda18271_write_regs(fe, R_CPD, 4);
176
177 regs[R_MPD] = regs[R_CPD] & 0x7f;
178 tda18271_set_if_notch(fe);
179 tda18271_write_regs(fe, R_MPD, 1);
180 break;
181 }
182
183 ret = tda18271_write_regs(fe, R_TM, 7);
184 if (tda_fail(ret))
185 goto fail;
186
187 /* force charge pump source */
188 charge_pump_source(fe, 1);
189
190 msleep(1);
191
192 /* return pll to normal operation */
193 charge_pump_source(fe, 0);
194
195 msleep(20);
196
197 if (priv->id == TDA18271HDC2) {
198 /* set rfagc to normal speed mode */
199 if (map->fm_rfn)
200 regs[R_EP3] &= ~0x04;
201 else
202 regs[R_EP3] |= 0x04;
203 ret = tda18271_write_regs(fe, R_EP3, 1);
204 }
205fail:
206 return ret;
207}
208
209static int tda18271_read_thermometer(struct dvb_frontend *fe)
210{
211 struct tda18271_priv *priv = fe->tuner_priv;
212 unsigned char *regs = priv->tda18271_regs;
213 int tm;
214
215 /* switch thermometer on */
216 regs[R_TM] |= 0x10;
217 tda18271_write_regs(fe, R_TM, 1);
218
219 /* read thermometer info */
220 tda18271_read_regs(fe);
221
222 if ((((regs[R_TM] & 0x0f) == 0x00) && ((regs[R_TM] & 0x20) == 0x20)) ||
223 (((regs[R_TM] & 0x0f) == 0x08) && ((regs[R_TM] & 0x20) == 0x00))) {
224
225 if ((regs[R_TM] & 0x20) == 0x20)
226 regs[R_TM] &= ~0x20;
227 else
228 regs[R_TM] |= 0x20;
229
230 tda18271_write_regs(fe, R_TM, 1);
231
232 msleep(10); /* temperature sensing */
233
234 /* read thermometer info */
235 tda18271_read_regs(fe);
236 }
237
238 tm = tda18271_lookup_thermometer(fe);
239
240 /* switch thermometer off */
241 regs[R_TM] &= ~0x10;
242 tda18271_write_regs(fe, R_TM, 1);
243
244 /* set CAL mode to normal */
245 regs[R_EP4] &= ~0x03;
246 tda18271_write_regs(fe, R_EP4, 1);
247
248 return tm;
249}
250
251/* ------------------------------------------------------------------ */
252
253static int tda18271c2_rf_tracking_filters_correction(struct dvb_frontend *fe,
254 u32 freq)
255{
256 struct tda18271_priv *priv = fe->tuner_priv;
257 struct tda18271_rf_tracking_filter_cal *map = priv->rf_cal_state;
258 unsigned char *regs = priv->tda18271_regs;
259 int i, ret;
260 u8 tm_current, dc_over_dt, rf_tab;
261 s32 rfcal_comp, approx;
262
263 /* power up */
264 ret = tda18271_set_standby_mode(fe, 0, 0, 0);
265 if (tda_fail(ret))
266 goto fail;
267
268 /* read die current temperature */
269 tm_current = tda18271_read_thermometer(fe);
270
271 /* frequency dependent parameters */
272
273 tda18271_calc_rf_cal(fe, &freq);
274 rf_tab = regs[R_EB14];
275
276 i = tda18271_lookup_rf_band(fe, &freq, NULL);
277 if (tda_fail(i))
278 return i;
279
280 if ((0 == map[i].rf3) || (freq / 1000 < map[i].rf2)) {
281 approx = map[i].rf_a1 * (s32)(freq / 1000 - map[i].rf1) +
282 map[i].rf_b1 + rf_tab;
283 } else {
284 approx = map[i].rf_a2 * (s32)(freq / 1000 - map[i].rf2) +
285 map[i].rf_b2 + rf_tab;
286 }
287
288 if (approx < 0)
289 approx = 0;
290 if (approx > 255)
291 approx = 255;
292
293 tda18271_lookup_map(fe, RF_CAL_DC_OVER_DT, &freq, &dc_over_dt);
294
295 /* calculate temperature compensation */
296 rfcal_comp = dc_over_dt * (s32)(tm_current - priv->tm_rfcal) / 1000;
297
298 regs[R_EB14] = (unsigned char)(approx + rfcal_comp);
299 ret = tda18271_write_regs(fe, R_EB14, 1);
300fail:
301 return ret;
302}
303
304static int tda18271_por(struct dvb_frontend *fe)
305{
306 struct tda18271_priv *priv = fe->tuner_priv;
307 unsigned char *regs = priv->tda18271_regs;
308 int ret;
309
310 /* power up detector 1 */
311 regs[R_EB12] &= ~0x20;
312 ret = tda18271_write_regs(fe, R_EB12, 1);
313 if (tda_fail(ret))
314 goto fail;
315
316 regs[R_EB18] &= ~0x80; /* turn agc1 loop on */
317 regs[R_EB18] &= ~0x03; /* set agc1_gain to 6 dB */
318 ret = tda18271_write_regs(fe, R_EB18, 1);
319 if (tda_fail(ret))
320 goto fail;
321
322 regs[R_EB21] |= 0x03; /* set agc2_gain to -6 dB */
323
324 /* POR mode */
325 ret = tda18271_set_standby_mode(fe, 1, 0, 0);
326 if (tda_fail(ret))
327 goto fail;
328
329 /* disable 1.5 MHz low pass filter */
330 regs[R_EB23] &= ~0x04; /* forcelp_fc2_en = 0 */
331 regs[R_EB23] &= ~0x02; /* XXX: lp_fc[2] = 0 */
332 ret = tda18271_write_regs(fe, R_EB21, 3);
333fail:
334 return ret;
335}
336
337static int tda18271_calibrate_rf(struct dvb_frontend *fe, u32 freq)
338{
339 struct tda18271_priv *priv = fe->tuner_priv;
340 unsigned char *regs = priv->tda18271_regs;
341 u32 N;
342
343 /* set CAL mode to normal */
344 regs[R_EP4] &= ~0x03;
345 tda18271_write_regs(fe, R_EP4, 1);
346
347 /* switch off agc1 */
348 regs[R_EP3] |= 0x40; /* sm_lt = 1 */
349
350 regs[R_EB18] |= 0x03; /* set agc1_gain to 15 dB */
351 tda18271_write_regs(fe, R_EB18, 1);
352
353 /* frequency dependent parameters */
354
355 tda18271_calc_bp_filter(fe, &freq);
356 tda18271_calc_gain_taper(fe, &freq);
357 tda18271_calc_rf_band(fe, &freq);
358 tda18271_calc_km(fe, &freq);
359
360 tda18271_write_regs(fe, R_EP1, 3);
361 tda18271_write_regs(fe, R_EB13, 1);
362
363 /* main pll charge pump source */
364 tda18271_charge_pump_source(fe, TDA18271_MAIN_PLL, 1);
365
366 /* cal pll charge pump source */
367 tda18271_charge_pump_source(fe, TDA18271_CAL_PLL, 1);
368
369 /* force dcdc converter to 0 V */
370 regs[R_EB14] = 0x00;
371 tda18271_write_regs(fe, R_EB14, 1);
372
373 /* disable plls lock */
374 regs[R_EB20] &= ~0x20;
375 tda18271_write_regs(fe, R_EB20, 1);
376
377 /* set CAL mode to RF tracking filter calibration */
378 regs[R_EP4] |= 0x03;
379 tda18271_write_regs(fe, R_EP4, 2);
380
381 /* --------------------------------------------------------------- */
382
383 /* set the internal calibration signal */
384 N = freq;
385
386 tda18271_calc_cal_pll(fe, N);
387 tda18271_write_regs(fe, R_CPD, 4);
388
389 /* downconvert internal calibration */
390 N += 1000000;
391
392 tda18271_calc_main_pll(fe, N);
393 tda18271_write_regs(fe, R_MPD, 4);
394
395 msleep(5);
396
397 tda18271_write_regs(fe, R_EP2, 1);
398 tda18271_write_regs(fe, R_EP1, 1);
399 tda18271_write_regs(fe, R_EP2, 1);
400 tda18271_write_regs(fe, R_EP1, 1);
401
402 /* --------------------------------------------------------------- */
403
404 /* normal operation for the main pll */
405 tda18271_charge_pump_source(fe, TDA18271_MAIN_PLL, 0);
406
407 /* normal operation for the cal pll */
408 tda18271_charge_pump_source(fe, TDA18271_CAL_PLL, 0);
409
410 msleep(10); /* plls locking */
411
412 /* launch the rf tracking filters calibration */
413 regs[R_EB20] |= 0x20;
414 tda18271_write_regs(fe, R_EB20, 1);
415
416 msleep(60); /* calibration */
417
418 /* --------------------------------------------------------------- */
419
420 /* set CAL mode to normal */
421 regs[R_EP4] &= ~0x03;
422
423 /* switch on agc1 */
424 regs[R_EP3] &= ~0x40; /* sm_lt = 0 */
425
426 regs[R_EB18] &= ~0x03; /* set agc1_gain to 6 dB */
427 tda18271_write_regs(fe, R_EB18, 1);
428
429 tda18271_write_regs(fe, R_EP3, 2);
430
431 /* synchronization */
432 tda18271_write_regs(fe, R_EP1, 1);
433
434 /* get calibration result */
435 tda18271_read_extended(fe);
436
437 return regs[R_EB14];
438}
439
440static int tda18271_powerscan(struct dvb_frontend *fe,
441 u32 *freq_in, u32 *freq_out)
442{
443 struct tda18271_priv *priv = fe->tuner_priv;
444 unsigned char *regs = priv->tda18271_regs;
445 int sgn, bcal, count, wait, ret;
446 u8 cid_target;
447 u16 count_limit;
448 u32 freq;
449
450 freq = *freq_in;
451
452 tda18271_calc_rf_band(fe, &freq);
453 tda18271_calc_rf_cal(fe, &freq);
454 tda18271_calc_gain_taper(fe, &freq);
455 tda18271_lookup_cid_target(fe, &freq, &cid_target, &count_limit);
456
457 tda18271_write_regs(fe, R_EP2, 1);
458 tda18271_write_regs(fe, R_EB14, 1);
459
460 /* downconvert frequency */
461 freq += 1000000;
462
463 tda18271_calc_main_pll(fe, freq);
464 tda18271_write_regs(fe, R_MPD, 4);
465
466 msleep(5); /* pll locking */
467
468 /* detection mode */
469 regs[R_EP4] &= ~0x03;
470 regs[R_EP4] |= 0x01;
471 tda18271_write_regs(fe, R_EP4, 1);
472
473 /* launch power detection measurement */
474 tda18271_write_regs(fe, R_EP2, 1);
475
476 /* read power detection info, stored in EB10 */
477 ret = tda18271_read_extended(fe);
478 if (tda_fail(ret))
479 return ret;
480
481 /* algorithm initialization */
482 sgn = 1;
483 *freq_out = *freq_in;
484 bcal = 0;
485 count = 0;
486 wait = false;
487
488 while ((regs[R_EB10] & 0x3f) < cid_target) {
489 /* downconvert updated freq to 1 MHz */
490 freq = *freq_in + (sgn * count) + 1000000;
491
492 tda18271_calc_main_pll(fe, freq);
493 tda18271_write_regs(fe, R_MPD, 4);
494
495 if (wait) {
496 msleep(5); /* pll locking */
497 wait = false;
498 } else
499 udelay(100); /* pll locking */
500
501 /* launch power detection measurement */
502 tda18271_write_regs(fe, R_EP2, 1);
503
504 /* read power detection info, stored in EB10 */
505 ret = tda18271_read_extended(fe);
506 if (tda_fail(ret))
507 return ret;
508
509 count += 200;
510
511 if (count <= count_limit)
512 continue;
513
514 if (sgn <= 0)
515 break;
516
517 sgn = -1 * sgn;
518 count = 200;
519 wait = true;
520 }
521
522 if ((regs[R_EB10] & 0x3f) >= cid_target) {
523 bcal = 1;
524 *freq_out = freq - 1000000;
525 } else
526 bcal = 0;
527
528 tda_cal("bcal = %d, freq_in = %d, freq_out = %d (freq = %d)\n",
529 bcal, *freq_in, *freq_out, freq);
530
531 return bcal;
532}
533
534static int tda18271_powerscan_init(struct dvb_frontend *fe)
535{
536 struct tda18271_priv *priv = fe->tuner_priv;
537 unsigned char *regs = priv->tda18271_regs;
538 int ret;
539
540 /* set standard to digital */
541 regs[R_EP3] &= ~0x1f; /* clear std bits */
542 regs[R_EP3] |= 0x12;
543
544 /* set cal mode to normal */
545 regs[R_EP4] &= ~0x03;
546
547 /* update IF output level */
548 regs[R_EP4] &= ~0x1c; /* clear if level bits */
549
550 ret = tda18271_write_regs(fe, R_EP3, 2);
551 if (tda_fail(ret))
552 goto fail;
553
554 regs[R_EB18] &= ~0x03; /* set agc1_gain to 6 dB */
555 ret = tda18271_write_regs(fe, R_EB18, 1);
556 if (tda_fail(ret))
557 goto fail;
558
559 regs[R_EB21] &= ~0x03; /* set agc2_gain to -15 dB */
560
561 /* 1.5 MHz low pass filter */
562 regs[R_EB23] |= 0x04; /* forcelp_fc2_en = 1 */
563 regs[R_EB23] |= 0x02; /* lp_fc[2] = 1 */
564
565 ret = tda18271_write_regs(fe, R_EB21, 3);
566fail:
567 return ret;
568}
569
570static int tda18271_rf_tracking_filters_init(struct dvb_frontend *fe, u32 freq)
571{
572 struct tda18271_priv *priv = fe->tuner_priv;
573 struct tda18271_rf_tracking_filter_cal *map = priv->rf_cal_state;
574 unsigned char *regs = priv->tda18271_regs;
575 int bcal, rf, i;
576 s32 divisor, dividend;
577#define RF1 0
578#define RF2 1
579#define RF3 2
580 u32 rf_default[3];
581 u32 rf_freq[3];
582 s32 prog_cal[3];
583 s32 prog_tab[3];
584
585 i = tda18271_lookup_rf_band(fe, &freq, NULL);
586
587 if (tda_fail(i))
588 return i;
589
590 rf_default[RF1] = 1000 * map[i].rf1_def;
591 rf_default[RF2] = 1000 * map[i].rf2_def;
592 rf_default[RF3] = 1000 * map[i].rf3_def;
593
594 for (rf = RF1; rf <= RF3; rf++) {
595 if (0 == rf_default[rf])
596 return 0;
597 tda_cal("freq = %d, rf = %d\n", freq, rf);
598
599 /* look for optimized calibration frequency */
600 bcal = tda18271_powerscan(fe, &rf_default[rf], &rf_freq[rf]);
601 if (tda_fail(bcal))
602 return bcal;
603
604 tda18271_calc_rf_cal(fe, &rf_freq[rf]);
605 prog_tab[rf] = (s32)regs[R_EB14];
606
607 if (1 == bcal)
608 prog_cal[rf] =
609 (s32)tda18271_calibrate_rf(fe, rf_freq[rf]);
610 else
611 prog_cal[rf] = prog_tab[rf];
612
613 switch (rf) {
614 case RF1:
615 map[i].rf_a1 = 0;
616 map[i].rf_b1 = (prog_cal[RF1] - prog_tab[RF1]);
617 map[i].rf1 = rf_freq[RF1] / 1000;
618 break;
619 case RF2:
620 dividend = (prog_cal[RF2] - prog_tab[RF2] -
621 prog_cal[RF1] + prog_tab[RF1]);
622 divisor = (s32)(rf_freq[RF2] - rf_freq[RF1]) / 1000;
623 map[i].rf_a1 = (dividend / divisor);
624 map[i].rf2 = rf_freq[RF2] / 1000;
625 break;
626 case RF3:
627 dividend = (prog_cal[RF3] - prog_tab[RF3] -
628 prog_cal[RF2] + prog_tab[RF2]);
629 divisor = (s32)(rf_freq[RF3] - rf_freq[RF2]) / 1000;
630 map[i].rf_a2 = (dividend / divisor);
631 map[i].rf_b2 = (prog_cal[RF2] - prog_tab[RF2]);
632 map[i].rf3 = rf_freq[RF3] / 1000;
633 break;
634 default:
635 BUG();
636 }
637 }
638
639 return 0;
640}
641
642static int tda18271_calc_rf_filter_curve(struct dvb_frontend *fe)
643{
644 struct tda18271_priv *priv = fe->tuner_priv;
645 unsigned int i;
646 int ret;
647
648 tda_info("tda18271: performing RF tracking filter calibration\n");
649
650 /* wait for die temperature stabilization */
651 msleep(200);
652
653 ret = tda18271_powerscan_init(fe);
654 if (tda_fail(ret))
655 goto fail;
656
657 /* rf band calibration */
658 for (i = 0; priv->rf_cal_state[i].rfmax != 0; i++) {
659 ret =
660 tda18271_rf_tracking_filters_init(fe, 1000 *
661 priv->rf_cal_state[i].rfmax);
662 if (tda_fail(ret))
663 goto fail;
664 }
665
666 priv->tm_rfcal = tda18271_read_thermometer(fe);
667fail:
668 return ret;
669}
670
671/* ------------------------------------------------------------------ */
672
673static int tda18271c2_rf_cal_init(struct dvb_frontend *fe)
674{
675 struct tda18271_priv *priv = fe->tuner_priv;
676 unsigned char *regs = priv->tda18271_regs;
677 int ret;
678
679 /* test RF_CAL_OK to see if we need init */
680 if ((regs[R_EP1] & 0x10) == 0)
681 priv->cal_initialized = false;
682
683 if (priv->cal_initialized)
684 return 0;
685
686 ret = tda18271_calc_rf_filter_curve(fe);
687 if (tda_fail(ret))
688 goto fail;
689
690 ret = tda18271_por(fe);
691 if (tda_fail(ret))
692 goto fail;
693
694 tda_info("tda18271: RF tracking filter calibration complete\n");
695
696 priv->cal_initialized = true;
697 goto end;
698fail:
699 tda_info("tda18271: RF tracking filter calibration failed!\n");
700end:
701 return ret;
702}
703
704static int tda18271c1_rf_tracking_filter_calibration(struct dvb_frontend *fe,
705 u32 freq, u32 bw)
706{
707 struct tda18271_priv *priv = fe->tuner_priv;
708 unsigned char *regs = priv->tda18271_regs;
709 int ret;
710 u32 N = 0;
711
712 /* calculate bp filter */
713 tda18271_calc_bp_filter(fe, &freq);
714 tda18271_write_regs(fe, R_EP1, 1);
715
716 regs[R_EB4] &= 0x07;
717 regs[R_EB4] |= 0x60;
718 tda18271_write_regs(fe, R_EB4, 1);
719
720 regs[R_EB7] = 0x60;
721 tda18271_write_regs(fe, R_EB7, 1);
722
723 regs[R_EB14] = 0x00;
724 tda18271_write_regs(fe, R_EB14, 1);
725
726 regs[R_EB20] = 0xcc;
727 tda18271_write_regs(fe, R_EB20, 1);
728
729 /* set cal mode to RF tracking filter calibration */
730 regs[R_EP4] |= 0x03;
731
732 /* calculate cal pll */
733
734 switch (priv->mode) {
735 case TDA18271_ANALOG:
736 N = freq - 1250000;
737 break;
738 case TDA18271_DIGITAL:
739 N = freq + bw / 2;
740 break;
741 }
742
743 tda18271_calc_cal_pll(fe, N);
744
745 /* calculate main pll */
746
747 switch (priv->mode) {
748 case TDA18271_ANALOG:
749 N = freq - 250000;
750 break;
751 case TDA18271_DIGITAL:
752 N = freq + bw / 2 + 1000000;
753 break;
754 }
755
756 tda18271_calc_main_pll(fe, N);
757
758 ret = tda18271_write_regs(fe, R_EP3, 11);
759 if (tda_fail(ret))
760 return ret;
761
762 msleep(5); /* RF tracking filter calibration initialization */
763
764 /* search for K,M,CO for RF calibration */
765 tda18271_calc_km(fe, &freq);
766 tda18271_write_regs(fe, R_EB13, 1);
767
768 /* search for rf band */
769 tda18271_calc_rf_band(fe, &freq);
770
771 /* search for gain taper */
772 tda18271_calc_gain_taper(fe, &freq);
773
774 tda18271_write_regs(fe, R_EP2, 1);
775 tda18271_write_regs(fe, R_EP1, 1);
776 tda18271_write_regs(fe, R_EP2, 1);
777 tda18271_write_regs(fe, R_EP1, 1);
778
779 regs[R_EB4] &= 0x07;
780 regs[R_EB4] |= 0x40;
781 tda18271_write_regs(fe, R_EB4, 1);
782
783 regs[R_EB7] = 0x40;
784 tda18271_write_regs(fe, R_EB7, 1);
785 msleep(10); /* pll locking */
786
787 regs[R_EB20] = 0xec;
788 tda18271_write_regs(fe, R_EB20, 1);
789 msleep(60); /* RF tracking filter calibration completion */
790
791 regs[R_EP4] &= ~0x03; /* set cal mode to normal */
792 tda18271_write_regs(fe, R_EP4, 1);
793
794 tda18271_write_regs(fe, R_EP1, 1);
795
796 /* RF tracking filter correction for VHF_Low band */
797 if (0 == tda18271_calc_rf_cal(fe, &freq))
798 tda18271_write_regs(fe, R_EB14, 1);
799
800 return 0;
801}
802
803/* ------------------------------------------------------------------ */
804
805static int tda18271_ir_cal_init(struct dvb_frontend *fe)
806{
807 struct tda18271_priv *priv = fe->tuner_priv;
808 unsigned char *regs = priv->tda18271_regs;
809 int ret;
810
811 ret = tda18271_read_regs(fe);
812 if (tda_fail(ret))
813 goto fail;
814
815 /* test IR_CAL_OK to see if we need init */
816 if ((regs[R_EP1] & 0x08) == 0)
817 ret = tda18271_init_regs(fe);
818fail:
819 return ret;
820}
821
822static int tda18271_init(struct dvb_frontend *fe)
823{
824 struct tda18271_priv *priv = fe->tuner_priv;
825 int ret;
826
827 mutex_lock(&priv->lock);
828
829 /* full power up */
830 ret = tda18271_set_standby_mode(fe, 0, 0, 0);
831 if (tda_fail(ret))
832 goto fail;
833
834 /* initialization */
835 ret = tda18271_ir_cal_init(fe);
836 if (tda_fail(ret))
837 goto fail;
838
839 if (priv->id == TDA18271HDC2)
840 tda18271c2_rf_cal_init(fe);
841fail:
842 mutex_unlock(&priv->lock);
843
844 return ret;
845}
846
847static int tda18271_sleep(struct dvb_frontend *fe)
848{
849 struct tda18271_priv *priv = fe->tuner_priv;
850 int ret;
851
852 mutex_lock(&priv->lock);
853
854 /* enter standby mode, with required output features enabled */
855 ret = tda18271_toggle_output(fe, 1);
856
857 mutex_unlock(&priv->lock);
858
859 return ret;
860}
861
862/* ------------------------------------------------------------------ */
863
864static int tda18271_agc(struct dvb_frontend *fe)
865{
866 struct tda18271_priv *priv = fe->tuner_priv;
867 int ret = 0;
868
869 switch (priv->config) {
870 case 0:
871 /* no external agc configuration required */
872 if (tda18271_debug & DBG_ADV)
873 tda_dbg("no agc configuration provided\n");
874 break;
875 case 3:
876 /* switch with GPIO of saa713x */
877 tda_dbg("invoking callback\n");
878 if (fe->callback)
879 ret = fe->callback(priv->i2c_props.adap->algo_data,
880 DVB_FRONTEND_COMPONENT_TUNER,
881 TDA18271_CALLBACK_CMD_AGC_ENABLE,
882 priv->mode);
883 break;
884 case 1:
885 case 2:
886 default:
887 /* n/a - currently not supported */
888 tda_err("unsupported configuration: %d\n", priv->config);
889 ret = -EINVAL;
890 break;
891 }
892 return ret;
893}
894
895static int tda18271_tune(struct dvb_frontend *fe,
896 struct tda18271_std_map_item *map, u32 freq, u32 bw)
897{
898 struct tda18271_priv *priv = fe->tuner_priv;
899 int ret;
900
901 tda_dbg("freq = %d, ifc = %d, bw = %d, agc_mode = %d, std = %d\n",
902 freq, map->if_freq, bw, map->agc_mode, map->std);
903
904 ret = tda18271_agc(fe);
905 if (tda_fail(ret))
906 tda_warn("failed to configure agc\n");
907
908 ret = tda18271_init(fe);
909 if (tda_fail(ret))
910 goto fail;
911
912 mutex_lock(&priv->lock);
913
914 switch (priv->id) {
915 case TDA18271HDC1:
916 tda18271c1_rf_tracking_filter_calibration(fe, freq, bw);
917 break;
918 case TDA18271HDC2:
919 tda18271c2_rf_tracking_filters_correction(fe, freq);
920 break;
921 }
922 ret = tda18271_channel_configuration(fe, map, freq, bw);
923
924 mutex_unlock(&priv->lock);
925fail:
926 return ret;
927}
928
929/* ------------------------------------------------------------------ */
930
931static int tda18271_set_params(struct dvb_frontend *fe,
932 struct dvb_frontend_parameters *params)
933{
934 struct tda18271_priv *priv = fe->tuner_priv;
935 struct tda18271_std_map *std_map = &priv->std;
936 struct tda18271_std_map_item *map;
937 int ret;
938 u32 bw, freq = params->frequency;
939
940 priv->mode = TDA18271_DIGITAL;
941
942 if (fe->ops.info.type == FE_ATSC) {
943 switch (params->u.vsb.modulation) {
944 case VSB_8:
945 case VSB_16:
946 map = &std_map->atsc_6;
947 break;
948 case QAM_64:
949 case QAM_256:
950 map = &std_map->qam_6;
951 break;
952 default:
953 tda_warn("modulation not set!\n");
954 return -EINVAL;
955 }
956#if 0
957 /* userspace request is already center adjusted */
958 freq += 1750000; /* Adjust to center (+1.75MHZ) */
959#endif
960 bw = 6000000;
961 } else if (fe->ops.info.type == FE_OFDM) {
962 switch (params->u.ofdm.bandwidth) {
963 case BANDWIDTH_6_MHZ:
964 bw = 6000000;
965 map = &std_map->dvbt_6;
966 break;
967 case BANDWIDTH_7_MHZ:
968 bw = 7000000;
969 map = &std_map->dvbt_7;
970 break;
971 case BANDWIDTH_8_MHZ:
972 bw = 8000000;
973 map = &std_map->dvbt_8;
974 break;
975 default:
976 tda_warn("bandwidth not set!\n");
977 return -EINVAL;
978 }
979 } else if (fe->ops.info.type == FE_QAM) {
980 /* DVB-C */
981 map = &std_map->qam_8;
982 bw = 8000000;
983 } else {
984 tda_warn("modulation type not supported!\n");
985 return -EINVAL;
986 }
987
988 /* When tuning digital, the analog demod must be tri-stated */
989 if (fe->ops.analog_ops.standby)
990 fe->ops.analog_ops.standby(fe);
991
992 ret = tda18271_tune(fe, map, freq, bw);
993
994 if (tda_fail(ret))
995 goto fail;
996
997 priv->frequency = freq;
998 priv->bandwidth = (fe->ops.info.type == FE_OFDM) ?
999 params->u.ofdm.bandwidth : 0;
1000fail:
1001 return ret;
1002}
1003
1004static int tda18271_set_analog_params(struct dvb_frontend *fe,
1005 struct analog_parameters *params)
1006{
1007 struct tda18271_priv *priv = fe->tuner_priv;
1008 struct tda18271_std_map *std_map = &priv->std;
1009 struct tda18271_std_map_item *map;
1010 char *mode;
1011 int ret;
1012 u32 freq = params->frequency * 125 *
1013 ((params->mode == V4L2_TUNER_RADIO) ? 1 : 1000) / 2;
1014
1015 priv->mode = TDA18271_ANALOG;
1016
1017 if (params->mode == V4L2_TUNER_RADIO) {
1018 map = &std_map->fm_radio;
1019 mode = "fm";
1020 } else if (params->std & V4L2_STD_MN) {
1021 map = &std_map->atv_mn;
1022 mode = "MN";
1023 } else if (params->std & V4L2_STD_B) {
1024 map = &std_map->atv_b;
1025 mode = "B";
1026 } else if (params->std & V4L2_STD_GH) {
1027 map = &std_map->atv_gh;
1028 mode = "GH";
1029 } else if (params->std & V4L2_STD_PAL_I) {
1030 map = &std_map->atv_i;
1031 mode = "I";
1032 } else if (params->std & V4L2_STD_DK) {
1033 map = &std_map->atv_dk;
1034 mode = "DK";
1035 } else if (params->std & V4L2_STD_SECAM_L) {
1036 map = &std_map->atv_l;
1037 mode = "L";
1038 } else if (params->std & V4L2_STD_SECAM_LC) {
1039 map = &std_map->atv_lc;
1040 mode = "L'";
1041 } else {
1042 map = &std_map->atv_i;
1043 mode = "xx";
1044 }
1045
1046 tda_dbg("setting tda18271 to system %s\n", mode);
1047
1048 ret = tda18271_tune(fe, map, freq, 0);
1049
1050 if (tda_fail(ret))
1051 goto fail;
1052
1053 priv->frequency = freq;
1054 priv->bandwidth = 0;
1055fail:
1056 return ret;
1057}
1058
1059static int tda18271_release(struct dvb_frontend *fe)
1060{
1061 struct tda18271_priv *priv = fe->tuner_priv;
1062
1063 mutex_lock(&tda18271_list_mutex);
1064
1065 if (priv)
1066 hybrid_tuner_release_state(priv);
1067
1068 mutex_unlock(&tda18271_list_mutex);
1069
1070 fe->tuner_priv = NULL;
1071
1072 return 0;
1073}
1074
1075static int tda18271_get_frequency(struct dvb_frontend *fe, u32 *frequency)
1076{
1077 struct tda18271_priv *priv = fe->tuner_priv;
1078 *frequency = priv->frequency;
1079 return 0;
1080}
1081
1082static int tda18271_get_bandwidth(struct dvb_frontend *fe, u32 *bandwidth)
1083{
1084 struct tda18271_priv *priv = fe->tuner_priv;
1085 *bandwidth = priv->bandwidth;
1086 return 0;
1087}
1088
1089/* ------------------------------------------------------------------ */
1090
1091#define tda18271_update_std(std_cfg, name) do { \
1092 if (map->std_cfg.if_freq + \
1093 map->std_cfg.agc_mode + map->std_cfg.std + \
1094 map->std_cfg.if_lvl + map->std_cfg.rfagc_top > 0) { \
1095 tda_dbg("Using custom std config for %s\n", name); \
1096 memcpy(&std->std_cfg, &map->std_cfg, \
1097 sizeof(struct tda18271_std_map_item)); \
1098 } } while (0)
1099
1100#define tda18271_dump_std_item(std_cfg, name) do { \
1101 tda_dbg("(%s) if_freq = %d, agc_mode = %d, std = %d, " \
1102 "if_lvl = %d, rfagc_top = 0x%02x\n", \
1103 name, std->std_cfg.if_freq, \
1104 std->std_cfg.agc_mode, std->std_cfg.std, \
1105 std->std_cfg.if_lvl, std->std_cfg.rfagc_top); \
1106 } while (0)
1107
1108static int tda18271_dump_std_map(struct dvb_frontend *fe)
1109{
1110 struct tda18271_priv *priv = fe->tuner_priv;
1111 struct tda18271_std_map *std = &priv->std;
1112
1113 tda_dbg("========== STANDARD MAP SETTINGS ==========\n");
1114 tda18271_dump_std_item(fm_radio, " fm ");
1115 tda18271_dump_std_item(atv_b, "atv b ");
1116 tda18271_dump_std_item(atv_dk, "atv dk");
1117 tda18271_dump_std_item(atv_gh, "atv gh");
1118 tda18271_dump_std_item(atv_i, "atv i ");
1119 tda18271_dump_std_item(atv_l, "atv l ");
1120 tda18271_dump_std_item(atv_lc, "atv l'");
1121 tda18271_dump_std_item(atv_mn, "atv mn");
1122 tda18271_dump_std_item(atsc_6, "atsc 6");
1123 tda18271_dump_std_item(dvbt_6, "dvbt 6");
1124 tda18271_dump_std_item(dvbt_7, "dvbt 7");
1125 tda18271_dump_std_item(dvbt_8, "dvbt 8");
1126 tda18271_dump_std_item(qam_6, "qam 6 ");
1127 tda18271_dump_std_item(qam_8, "qam 8 ");
1128
1129 return 0;
1130}
1131
1132static int tda18271_update_std_map(struct dvb_frontend *fe,
1133 struct tda18271_std_map *map)
1134{
1135 struct tda18271_priv *priv = fe->tuner_priv;
1136 struct tda18271_std_map *std = &priv->std;
1137
1138 if (!map)
1139 return -EINVAL;
1140
1141 tda18271_update_std(fm_radio, "fm");
1142 tda18271_update_std(atv_b, "atv b");
1143 tda18271_update_std(atv_dk, "atv dk");
1144 tda18271_update_std(atv_gh, "atv gh");
1145 tda18271_update_std(atv_i, "atv i");
1146 tda18271_update_std(atv_l, "atv l");
1147 tda18271_update_std(atv_lc, "atv l'");
1148 tda18271_update_std(atv_mn, "atv mn");
1149 tda18271_update_std(atsc_6, "atsc 6");
1150 tda18271_update_std(dvbt_6, "dvbt 6");
1151 tda18271_update_std(dvbt_7, "dvbt 7");
1152 tda18271_update_std(dvbt_8, "dvbt 8");
1153 tda18271_update_std(qam_6, "qam 6");
1154 tda18271_update_std(qam_8, "qam 8");
1155
1156 return 0;
1157}
1158
1159static int tda18271_get_id(struct dvb_frontend *fe)
1160{
1161 struct tda18271_priv *priv = fe->tuner_priv;
1162 unsigned char *regs = priv->tda18271_regs;
1163 char *name;
1164
1165 mutex_lock(&priv->lock);
1166 tda18271_read_regs(fe);
1167 mutex_unlock(&priv->lock);
1168
1169 switch (regs[R_ID] & 0x7f) {
1170 case 3:
1171 name = "TDA18271HD/C1";
1172 priv->id = TDA18271HDC1;
1173 break;
1174 case 4:
1175 name = "TDA18271HD/C2";
1176 priv->id = TDA18271HDC2;
1177 break;
1178 default:
1179 tda_info("Unknown device (%i) detected @ %d-%04x, device not supported.\n",
1180 regs[R_ID], i2c_adapter_id(priv->i2c_props.adap),
1181 priv->i2c_props.addr);
1182 return -EINVAL;
1183 }
1184
1185 tda_info("%s detected @ %d-%04x\n", name,
1186 i2c_adapter_id(priv->i2c_props.adap), priv->i2c_props.addr);
1187
1188 return 0;
1189}
1190
1191static int tda18271_setup_configuration(struct dvb_frontend *fe,
1192 struct tda18271_config *cfg)
1193{
1194 struct tda18271_priv *priv = fe->tuner_priv;
1195
1196 priv->gate = (cfg) ? cfg->gate : TDA18271_GATE_AUTO;
1197 priv->role = (cfg) ? cfg->role : TDA18271_MASTER;
1198 priv->config = (cfg) ? cfg->config : 0;
1199 priv->small_i2c = (cfg) ?
1200 cfg->small_i2c : TDA18271_39_BYTE_CHUNK_INIT;
1201 priv->output_opt = (cfg) ?
1202 cfg->output_opt : TDA18271_OUTPUT_LT_XT_ON;
1203
1204 return 0;
1205}
1206
1207static inline int tda18271_need_cal_on_startup(struct tda18271_config *cfg)
1208{
1209 /* tda18271_cal_on_startup == -1 when cal module option is unset */
1210 return ((tda18271_cal_on_startup == -1) ?
1211 /* honor configuration setting */
1212 ((cfg) && (cfg->rf_cal_on_startup)) :
1213 /* module option overrides configuration setting */
1214 (tda18271_cal_on_startup)) ? 1 : 0;
1215}
1216
1217static int tda18271_set_config(struct dvb_frontend *fe, void *priv_cfg)
1218{
1219 struct tda18271_config *cfg = (struct tda18271_config *) priv_cfg;
1220
1221 tda18271_setup_configuration(fe, cfg);
1222
1223 if (tda18271_need_cal_on_startup(cfg))
1224 tda18271_init(fe);
1225
1226 /* override default std map with values in config struct */
1227 if ((cfg) && (cfg->std_map))
1228 tda18271_update_std_map(fe, cfg->std_map);
1229
1230 return 0;
1231}
1232
1233static struct dvb_tuner_ops tda18271_tuner_ops = {
1234 .info = {
1235 .name = "NXP TDA18271HD",
1236 .frequency_min = 45000000,
1237 .frequency_max = 864000000,
1238 .frequency_step = 62500
1239 },
1240 .init = tda18271_init,
1241 .sleep = tda18271_sleep,
1242 .set_params = tda18271_set_params,
1243 .set_analog_params = tda18271_set_analog_params,
1244 .release = tda18271_release,
1245 .set_config = tda18271_set_config,
1246 .get_frequency = tda18271_get_frequency,
1247 .get_bandwidth = tda18271_get_bandwidth,
1248};
1249
1250struct dvb_frontend *tda18271_attach(struct dvb_frontend *fe, u8 addr,
1251 struct i2c_adapter *i2c,
1252 struct tda18271_config *cfg)
1253{
1254 struct tda18271_priv *priv = NULL;
1255 int instance, ret;
1256
1257 mutex_lock(&tda18271_list_mutex);
1258
1259 instance = hybrid_tuner_request_state(struct tda18271_priv, priv,
1260 hybrid_tuner_instance_list,
1261 i2c, addr, "tda18271");
1262 switch (instance) {
1263 case 0:
1264 goto fail;
1265 case 1:
1266 /* new tuner instance */
1267 fe->tuner_priv = priv;
1268
1269 tda18271_setup_configuration(fe, cfg);
1270
1271 priv->cal_initialized = false;
1272 mutex_init(&priv->lock);
1273
1274 ret = tda18271_get_id(fe);
1275 if (tda_fail(ret))
1276 goto fail;
1277
1278 ret = tda18271_assign_map_layout(fe);
1279 if (tda_fail(ret))
1280 goto fail;
1281
1282 mutex_lock(&priv->lock);
1283 tda18271_init_regs(fe);
1284
1285 if ((tda18271_need_cal_on_startup(cfg)) &&
1286 (priv->id == TDA18271HDC2))
1287 tda18271c2_rf_cal_init(fe);
1288
1289 mutex_unlock(&priv->lock);
1290 break;
1291 default:
1292 /* existing tuner instance */
1293 fe->tuner_priv = priv;
1294
1295 /* allow dvb driver to override configuration settings */
1296 if (cfg) {
1297 if (cfg->gate != TDA18271_GATE_ANALOG)
1298 priv->gate = cfg->gate;
1299 if (cfg->role)
1300 priv->role = cfg->role;
1301 if (cfg->config)
1302 priv->config = cfg->config;
1303 if (cfg->small_i2c)
1304 priv->small_i2c = cfg->small_i2c;
1305 if (cfg->output_opt)
1306 priv->output_opt = cfg->output_opt;
1307 if (cfg->std_map)
1308 tda18271_update_std_map(fe, cfg->std_map);
1309 }
1310 if (tda18271_need_cal_on_startup(cfg))
1311 tda18271_init(fe);
1312 break;
1313 }
1314
1315 /* override default std map with values in config struct */
1316 if ((cfg) && (cfg->std_map))
1317 tda18271_update_std_map(fe, cfg->std_map);
1318
1319 mutex_unlock(&tda18271_list_mutex);
1320
1321 memcpy(&fe->ops.tuner_ops, &tda18271_tuner_ops,
1322 sizeof(struct dvb_tuner_ops));
1323
1324 if (tda18271_debug & (DBG_MAP | DBG_ADV))
1325 tda18271_dump_std_map(fe);
1326
1327 return fe;
1328fail:
1329 mutex_unlock(&tda18271_list_mutex);
1330
1331 tda18271_release(fe);
1332 return NULL;
1333}
1334EXPORT_SYMBOL_GPL(tda18271_attach);
1335MODULE_DESCRIPTION("NXP TDA18271HD analog / digital tuner driver");
1336MODULE_AUTHOR("Michael Krufky <mkrufky@linuxtv.org>");
1337MODULE_LICENSE("GPL");
1338MODULE_VERSION("0.4");
1339
1340/*
1341 * Overrides for Emacs so that we follow Linus's tabbing style.
1342 * ---------------------------------------------------------------------------
1343 * Local variables:
1344 * c-basic-offset: 8
1345 * End:
1346 */
diff --git a/drivers/media/common/tuners/tda18271-maps.c b/drivers/media/common/tuners/tda18271-maps.c
new file mode 100644
index 00000000000..3d5b6ab7e33
--- /dev/null
+++ b/drivers/media/common/tuners/tda18271-maps.c
@@ -0,0 +1,1313 @@
1/*
2 tda18271-maps.c - driver for the Philips / NXP TDA18271 silicon tuner
3
4 Copyright (C) 2007, 2008 Michael Krufky <mkrufky@linuxtv.org>
5
6 This program is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 2 of the License, or
9 (at your option) any later version.
10
11 This program is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
15
16 You should have received a copy of the GNU General Public License
17 along with this program; if not, write to the Free Software
18 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
19*/
20
21#include "tda18271-priv.h"
22
23struct tda18271_pll_map {
24 u32 lomax;
25 u8 pd; /* post div */
26 u8 d; /* div */
27};
28
29struct tda18271_map {
30 u32 rfmax;
31 u8 val;
32};
33
34/*---------------------------------------------------------------------*/
35
36static struct tda18271_pll_map tda18271c1_main_pll[] = {
37 { .lomax = 32000, .pd = 0x5f, .d = 0xf0 },
38 { .lomax = 35000, .pd = 0x5e, .d = 0xe0 },
39 { .lomax = 37000, .pd = 0x5d, .d = 0xd0 },
40 { .lomax = 41000, .pd = 0x5c, .d = 0xc0 },
41 { .lomax = 44000, .pd = 0x5b, .d = 0xb0 },
42 { .lomax = 49000, .pd = 0x5a, .d = 0xa0 },
43 { .lomax = 54000, .pd = 0x59, .d = 0x90 },
44 { .lomax = 61000, .pd = 0x58, .d = 0x80 },
45 { .lomax = 65000, .pd = 0x4f, .d = 0x78 },
46 { .lomax = 70000, .pd = 0x4e, .d = 0x70 },
47 { .lomax = 75000, .pd = 0x4d, .d = 0x68 },
48 { .lomax = 82000, .pd = 0x4c, .d = 0x60 },
49 { .lomax = 89000, .pd = 0x4b, .d = 0x58 },
50 { .lomax = 98000, .pd = 0x4a, .d = 0x50 },
51 { .lomax = 109000, .pd = 0x49, .d = 0x48 },
52 { .lomax = 123000, .pd = 0x48, .d = 0x40 },
53 { .lomax = 131000, .pd = 0x3f, .d = 0x3c },
54 { .lomax = 141000, .pd = 0x3e, .d = 0x38 },
55 { .lomax = 151000, .pd = 0x3d, .d = 0x34 },
56 { .lomax = 164000, .pd = 0x3c, .d = 0x30 },
57 { .lomax = 179000, .pd = 0x3b, .d = 0x2c },
58 { .lomax = 197000, .pd = 0x3a, .d = 0x28 },
59 { .lomax = 219000, .pd = 0x39, .d = 0x24 },
60 { .lomax = 246000, .pd = 0x38, .d = 0x20 },
61 { .lomax = 263000, .pd = 0x2f, .d = 0x1e },
62 { .lomax = 282000, .pd = 0x2e, .d = 0x1c },
63 { .lomax = 303000, .pd = 0x2d, .d = 0x1a },
64 { .lomax = 329000, .pd = 0x2c, .d = 0x18 },
65 { .lomax = 359000, .pd = 0x2b, .d = 0x16 },
66 { .lomax = 395000, .pd = 0x2a, .d = 0x14 },
67 { .lomax = 438000, .pd = 0x29, .d = 0x12 },
68 { .lomax = 493000, .pd = 0x28, .d = 0x10 },
69 { .lomax = 526000, .pd = 0x1f, .d = 0x0f },
70 { .lomax = 564000, .pd = 0x1e, .d = 0x0e },
71 { .lomax = 607000, .pd = 0x1d, .d = 0x0d },
72 { .lomax = 658000, .pd = 0x1c, .d = 0x0c },
73 { .lomax = 718000, .pd = 0x1b, .d = 0x0b },
74 { .lomax = 790000, .pd = 0x1a, .d = 0x0a },
75 { .lomax = 877000, .pd = 0x19, .d = 0x09 },
76 { .lomax = 987000, .pd = 0x18, .d = 0x08 },
77 { .lomax = 0, .pd = 0x00, .d = 0x00 }, /* end */
78};
79
80static struct tda18271_pll_map tda18271c2_main_pll[] = {
81 { .lomax = 33125, .pd = 0x57, .d = 0xf0 },
82 { .lomax = 35500, .pd = 0x56, .d = 0xe0 },
83 { .lomax = 38188, .pd = 0x55, .d = 0xd0 },
84 { .lomax = 41375, .pd = 0x54, .d = 0xc0 },
85 { .lomax = 45125, .pd = 0x53, .d = 0xb0 },
86 { .lomax = 49688, .pd = 0x52, .d = 0xa0 },
87 { .lomax = 55188, .pd = 0x51, .d = 0x90 },
88 { .lomax = 62125, .pd = 0x50, .d = 0x80 },
89 { .lomax = 66250, .pd = 0x47, .d = 0x78 },
90 { .lomax = 71000, .pd = 0x46, .d = 0x70 },
91 { .lomax = 76375, .pd = 0x45, .d = 0x68 },
92 { .lomax = 82750, .pd = 0x44, .d = 0x60 },
93 { .lomax = 90250, .pd = 0x43, .d = 0x58 },
94 { .lomax = 99375, .pd = 0x42, .d = 0x50 },
95 { .lomax = 110375, .pd = 0x41, .d = 0x48 },
96 { .lomax = 124250, .pd = 0x40, .d = 0x40 },
97 { .lomax = 132500, .pd = 0x37, .d = 0x3c },
98 { .lomax = 142000, .pd = 0x36, .d = 0x38 },
99 { .lomax = 152750, .pd = 0x35, .d = 0x34 },
100 { .lomax = 165500, .pd = 0x34, .d = 0x30 },
101 { .lomax = 180500, .pd = 0x33, .d = 0x2c },
102 { .lomax = 198750, .pd = 0x32, .d = 0x28 },
103 { .lomax = 220750, .pd = 0x31, .d = 0x24 },
104 { .lomax = 248500, .pd = 0x30, .d = 0x20 },
105 { .lomax = 265000, .pd = 0x27, .d = 0x1e },
106 { .lomax = 284000, .pd = 0x26, .d = 0x1c },
107 { .lomax = 305500, .pd = 0x25, .d = 0x1a },
108 { .lomax = 331000, .pd = 0x24, .d = 0x18 },
109 { .lomax = 361000, .pd = 0x23, .d = 0x16 },
110 { .lomax = 397500, .pd = 0x22, .d = 0x14 },
111 { .lomax = 441500, .pd = 0x21, .d = 0x12 },
112 { .lomax = 497000, .pd = 0x20, .d = 0x10 },
113 { .lomax = 530000, .pd = 0x17, .d = 0x0f },
114 { .lomax = 568000, .pd = 0x16, .d = 0x0e },
115 { .lomax = 611000, .pd = 0x15, .d = 0x0d },
116 { .lomax = 662000, .pd = 0x14, .d = 0x0c },
117 { .lomax = 722000, .pd = 0x13, .d = 0x0b },
118 { .lomax = 795000, .pd = 0x12, .d = 0x0a },
119 { .lomax = 883000, .pd = 0x11, .d = 0x09 },
120 { .lomax = 994000, .pd = 0x10, .d = 0x08 },
121 { .lomax = 0, .pd = 0x00, .d = 0x00 }, /* end */
122};
123
124static struct tda18271_pll_map tda18271c1_cal_pll[] = {
125 { .lomax = 33000, .pd = 0xdd, .d = 0xd0 },
126 { .lomax = 36000, .pd = 0xdc, .d = 0xc0 },
127 { .lomax = 40000, .pd = 0xdb, .d = 0xb0 },
128 { .lomax = 44000, .pd = 0xda, .d = 0xa0 },
129 { .lomax = 49000, .pd = 0xd9, .d = 0x90 },
130 { .lomax = 55000, .pd = 0xd8, .d = 0x80 },
131 { .lomax = 63000, .pd = 0xd3, .d = 0x70 },
132 { .lomax = 67000, .pd = 0xcd, .d = 0x68 },
133 { .lomax = 73000, .pd = 0xcc, .d = 0x60 },
134 { .lomax = 80000, .pd = 0xcb, .d = 0x58 },
135 { .lomax = 88000, .pd = 0xca, .d = 0x50 },
136 { .lomax = 98000, .pd = 0xc9, .d = 0x48 },
137 { .lomax = 110000, .pd = 0xc8, .d = 0x40 },
138 { .lomax = 126000, .pd = 0xc3, .d = 0x38 },
139 { .lomax = 135000, .pd = 0xbd, .d = 0x34 },
140 { .lomax = 147000, .pd = 0xbc, .d = 0x30 },
141 { .lomax = 160000, .pd = 0xbb, .d = 0x2c },
142 { .lomax = 176000, .pd = 0xba, .d = 0x28 },
143 { .lomax = 196000, .pd = 0xb9, .d = 0x24 },
144 { .lomax = 220000, .pd = 0xb8, .d = 0x20 },
145 { .lomax = 252000, .pd = 0xb3, .d = 0x1c },
146 { .lomax = 271000, .pd = 0xad, .d = 0x1a },
147 { .lomax = 294000, .pd = 0xac, .d = 0x18 },
148 { .lomax = 321000, .pd = 0xab, .d = 0x16 },
149 { .lomax = 353000, .pd = 0xaa, .d = 0x14 },
150 { .lomax = 392000, .pd = 0xa9, .d = 0x12 },
151 { .lomax = 441000, .pd = 0xa8, .d = 0x10 },
152 { .lomax = 505000, .pd = 0xa3, .d = 0x0e },
153 { .lomax = 543000, .pd = 0x9d, .d = 0x0d },
154 { .lomax = 589000, .pd = 0x9c, .d = 0x0c },
155 { .lomax = 642000, .pd = 0x9b, .d = 0x0b },
156 { .lomax = 707000, .pd = 0x9a, .d = 0x0a },
157 { .lomax = 785000, .pd = 0x99, .d = 0x09 },
158 { .lomax = 883000, .pd = 0x98, .d = 0x08 },
159 { .lomax = 1010000, .pd = 0x93, .d = 0x07 },
160 { .lomax = 0, .pd = 0x00, .d = 0x00 }, /* end */
161};
162
163static struct tda18271_pll_map tda18271c2_cal_pll[] = {
164 { .lomax = 33813, .pd = 0xdd, .d = 0xd0 },
165 { .lomax = 36625, .pd = 0xdc, .d = 0xc0 },
166 { .lomax = 39938, .pd = 0xdb, .d = 0xb0 },
167 { .lomax = 43938, .pd = 0xda, .d = 0xa0 },
168 { .lomax = 48813, .pd = 0xd9, .d = 0x90 },
169 { .lomax = 54938, .pd = 0xd8, .d = 0x80 },
170 { .lomax = 62813, .pd = 0xd3, .d = 0x70 },
171 { .lomax = 67625, .pd = 0xcd, .d = 0x68 },
172 { .lomax = 73250, .pd = 0xcc, .d = 0x60 },
173 { .lomax = 79875, .pd = 0xcb, .d = 0x58 },
174 { .lomax = 87875, .pd = 0xca, .d = 0x50 },
175 { .lomax = 97625, .pd = 0xc9, .d = 0x48 },
176 { .lomax = 109875, .pd = 0xc8, .d = 0x40 },
177 { .lomax = 125625, .pd = 0xc3, .d = 0x38 },
178 { .lomax = 135250, .pd = 0xbd, .d = 0x34 },
179 { .lomax = 146500, .pd = 0xbc, .d = 0x30 },
180 { .lomax = 159750, .pd = 0xbb, .d = 0x2c },
181 { .lomax = 175750, .pd = 0xba, .d = 0x28 },
182 { .lomax = 195250, .pd = 0xb9, .d = 0x24 },
183 { .lomax = 219750, .pd = 0xb8, .d = 0x20 },
184 { .lomax = 251250, .pd = 0xb3, .d = 0x1c },
185 { .lomax = 270500, .pd = 0xad, .d = 0x1a },
186 { .lomax = 293000, .pd = 0xac, .d = 0x18 },
187 { .lomax = 319500, .pd = 0xab, .d = 0x16 },
188 { .lomax = 351500, .pd = 0xaa, .d = 0x14 },
189 { .lomax = 390500, .pd = 0xa9, .d = 0x12 },
190 { .lomax = 439500, .pd = 0xa8, .d = 0x10 },
191 { .lomax = 502500, .pd = 0xa3, .d = 0x0e },
192 { .lomax = 541000, .pd = 0x9d, .d = 0x0d },
193 { .lomax = 586000, .pd = 0x9c, .d = 0x0c },
194 { .lomax = 639000, .pd = 0x9b, .d = 0x0b },
195 { .lomax = 703000, .pd = 0x9a, .d = 0x0a },
196 { .lomax = 781000, .pd = 0x99, .d = 0x09 },
197 { .lomax = 879000, .pd = 0x98, .d = 0x08 },
198 { .lomax = 0, .pd = 0x00, .d = 0x00 }, /* end */
199};
200
201static struct tda18271_map tda18271_bp_filter[] = {
202 { .rfmax = 62000, .val = 0x00 },
203 { .rfmax = 84000, .val = 0x01 },
204 { .rfmax = 100000, .val = 0x02 },
205 { .rfmax = 140000, .val = 0x03 },
206 { .rfmax = 170000, .val = 0x04 },
207 { .rfmax = 180000, .val = 0x05 },
208 { .rfmax = 865000, .val = 0x06 },
209 { .rfmax = 0, .val = 0x00 }, /* end */
210};
211
212static struct tda18271_map tda18271c1_km[] = {
213 { .rfmax = 61100, .val = 0x74 },
214 { .rfmax = 350000, .val = 0x40 },
215 { .rfmax = 720000, .val = 0x30 },
216 { .rfmax = 865000, .val = 0x40 },
217 { .rfmax = 0, .val = 0x00 }, /* end */
218};
219
220static struct tda18271_map tda18271c2_km[] = {
221 { .rfmax = 47900, .val = 0x38 },
222 { .rfmax = 61100, .val = 0x44 },
223 { .rfmax = 350000, .val = 0x30 },
224 { .rfmax = 720000, .val = 0x24 },
225 { .rfmax = 865000, .val = 0x3c },
226 { .rfmax = 0, .val = 0x00 }, /* end */
227};
228
229static struct tda18271_map tda18271_rf_band[] = {
230 { .rfmax = 47900, .val = 0x00 },
231 { .rfmax = 61100, .val = 0x01 },
232 { .rfmax = 152600, .val = 0x02 },
233 { .rfmax = 164700, .val = 0x03 },
234 { .rfmax = 203500, .val = 0x04 },
235 { .rfmax = 457800, .val = 0x05 },
236 { .rfmax = 865000, .val = 0x06 },
237 { .rfmax = 0, .val = 0x00 }, /* end */
238};
239
240static struct tda18271_map tda18271_gain_taper[] = {
241 { .rfmax = 45400, .val = 0x1f },
242 { .rfmax = 45800, .val = 0x1e },
243 { .rfmax = 46200, .val = 0x1d },
244 { .rfmax = 46700, .val = 0x1c },
245 { .rfmax = 47100, .val = 0x1b },
246 { .rfmax = 47500, .val = 0x1a },
247 { .rfmax = 47900, .val = 0x19 },
248 { .rfmax = 49600, .val = 0x17 },
249 { .rfmax = 51200, .val = 0x16 },
250 { .rfmax = 52900, .val = 0x15 },
251 { .rfmax = 54500, .val = 0x14 },
252 { .rfmax = 56200, .val = 0x13 },
253 { .rfmax = 57800, .val = 0x12 },
254 { .rfmax = 59500, .val = 0x11 },
255 { .rfmax = 61100, .val = 0x10 },
256 { .rfmax = 67600, .val = 0x0d },
257 { .rfmax = 74200, .val = 0x0c },
258 { .rfmax = 80700, .val = 0x0b },
259 { .rfmax = 87200, .val = 0x0a },
260 { .rfmax = 93800, .val = 0x09 },
261 { .rfmax = 100300, .val = 0x08 },
262 { .rfmax = 106900, .val = 0x07 },
263 { .rfmax = 113400, .val = 0x06 },
264 { .rfmax = 119900, .val = 0x05 },
265 { .rfmax = 126500, .val = 0x04 },
266 { .rfmax = 133000, .val = 0x03 },
267 { .rfmax = 139500, .val = 0x02 },
268 { .rfmax = 146100, .val = 0x01 },
269 { .rfmax = 152600, .val = 0x00 },
270 { .rfmax = 154300, .val = 0x1f },
271 { .rfmax = 156100, .val = 0x1e },
272 { .rfmax = 157800, .val = 0x1d },
273 { .rfmax = 159500, .val = 0x1c },
274 { .rfmax = 161200, .val = 0x1b },
275 { .rfmax = 163000, .val = 0x1a },
276 { .rfmax = 164700, .val = 0x19 },
277 { .rfmax = 170200, .val = 0x17 },
278 { .rfmax = 175800, .val = 0x16 },
279 { .rfmax = 181300, .val = 0x15 },
280 { .rfmax = 186900, .val = 0x14 },
281 { .rfmax = 192400, .val = 0x13 },
282 { .rfmax = 198000, .val = 0x12 },
283 { .rfmax = 203500, .val = 0x11 },
284 { .rfmax = 216200, .val = 0x14 },
285 { .rfmax = 228900, .val = 0x13 },
286 { .rfmax = 241600, .val = 0x12 },
287 { .rfmax = 254400, .val = 0x11 },
288 { .rfmax = 267100, .val = 0x10 },
289 { .rfmax = 279800, .val = 0x0f },
290 { .rfmax = 292500, .val = 0x0e },
291 { .rfmax = 305200, .val = 0x0d },
292 { .rfmax = 317900, .val = 0x0c },
293 { .rfmax = 330700, .val = 0x0b },
294 { .rfmax = 343400, .val = 0x0a },
295 { .rfmax = 356100, .val = 0x09 },
296 { .rfmax = 368800, .val = 0x08 },
297 { .rfmax = 381500, .val = 0x07 },
298 { .rfmax = 394200, .val = 0x06 },
299 { .rfmax = 406900, .val = 0x05 },
300 { .rfmax = 419700, .val = 0x04 },
301 { .rfmax = 432400, .val = 0x03 },
302 { .rfmax = 445100, .val = 0x02 },
303 { .rfmax = 457800, .val = 0x01 },
304 { .rfmax = 476300, .val = 0x19 },
305 { .rfmax = 494800, .val = 0x18 },
306 { .rfmax = 513300, .val = 0x17 },
307 { .rfmax = 531800, .val = 0x16 },
308 { .rfmax = 550300, .val = 0x15 },
309 { .rfmax = 568900, .val = 0x14 },
310 { .rfmax = 587400, .val = 0x13 },
311 { .rfmax = 605900, .val = 0x12 },
312 { .rfmax = 624400, .val = 0x11 },
313 { .rfmax = 642900, .val = 0x10 },
314 { .rfmax = 661400, .val = 0x0f },
315 { .rfmax = 679900, .val = 0x0e },
316 { .rfmax = 698400, .val = 0x0d },
317 { .rfmax = 716900, .val = 0x0c },
318 { .rfmax = 735400, .val = 0x0b },
319 { .rfmax = 753900, .val = 0x0a },
320 { .rfmax = 772500, .val = 0x09 },
321 { .rfmax = 791000, .val = 0x08 },
322 { .rfmax = 809500, .val = 0x07 },
323 { .rfmax = 828000, .val = 0x06 },
324 { .rfmax = 846500, .val = 0x05 },
325 { .rfmax = 865000, .val = 0x04 },
326 { .rfmax = 0, .val = 0x00 }, /* end */
327};
328
329static struct tda18271_map tda18271c1_rf_cal[] = {
330 { .rfmax = 41000, .val = 0x1e },
331 { .rfmax = 43000, .val = 0x30 },
332 { .rfmax = 45000, .val = 0x43 },
333 { .rfmax = 46000, .val = 0x4d },
334 { .rfmax = 47000, .val = 0x54 },
335 { .rfmax = 47900, .val = 0x64 },
336 { .rfmax = 49100, .val = 0x20 },
337 { .rfmax = 50000, .val = 0x22 },
338 { .rfmax = 51000, .val = 0x2a },
339 { .rfmax = 53000, .val = 0x32 },
340 { .rfmax = 55000, .val = 0x35 },
341 { .rfmax = 56000, .val = 0x3c },
342 { .rfmax = 57000, .val = 0x3f },
343 { .rfmax = 58000, .val = 0x48 },
344 { .rfmax = 59000, .val = 0x4d },
345 { .rfmax = 60000, .val = 0x58 },
346 { .rfmax = 61100, .val = 0x5f },
347 { .rfmax = 0, .val = 0x00 }, /* end */
348};
349
350static struct tda18271_map tda18271c2_rf_cal[] = {
351 { .rfmax = 41000, .val = 0x0f },
352 { .rfmax = 43000, .val = 0x1c },
353 { .rfmax = 45000, .val = 0x2f },
354 { .rfmax = 46000, .val = 0x39 },
355 { .rfmax = 47000, .val = 0x40 },
356 { .rfmax = 47900, .val = 0x50 },
357 { .rfmax = 49100, .val = 0x16 },
358 { .rfmax = 50000, .val = 0x18 },
359 { .rfmax = 51000, .val = 0x20 },
360 { .rfmax = 53000, .val = 0x28 },
361 { .rfmax = 55000, .val = 0x2b },
362 { .rfmax = 56000, .val = 0x32 },
363 { .rfmax = 57000, .val = 0x35 },
364 { .rfmax = 58000, .val = 0x3e },
365 { .rfmax = 59000, .val = 0x43 },
366 { .rfmax = 60000, .val = 0x4e },
367 { .rfmax = 61100, .val = 0x55 },
368 { .rfmax = 63000, .val = 0x0f },
369 { .rfmax = 64000, .val = 0x11 },
370 { .rfmax = 65000, .val = 0x12 },
371 { .rfmax = 66000, .val = 0x15 },
372 { .rfmax = 67000, .val = 0x16 },
373 { .rfmax = 68000, .val = 0x17 },
374 { .rfmax = 70000, .val = 0x19 },
375 { .rfmax = 71000, .val = 0x1c },
376 { .rfmax = 72000, .val = 0x1d },
377 { .rfmax = 73000, .val = 0x1f },
378 { .rfmax = 74000, .val = 0x20 },
379 { .rfmax = 75000, .val = 0x21 },
380 { .rfmax = 76000, .val = 0x24 },
381 { .rfmax = 77000, .val = 0x25 },
382 { .rfmax = 78000, .val = 0x27 },
383 { .rfmax = 80000, .val = 0x28 },
384 { .rfmax = 81000, .val = 0x29 },
385 { .rfmax = 82000, .val = 0x2d },
386 { .rfmax = 83000, .val = 0x2e },
387 { .rfmax = 84000, .val = 0x2f },
388 { .rfmax = 85000, .val = 0x31 },
389 { .rfmax = 86000, .val = 0x33 },
390 { .rfmax = 87000, .val = 0x34 },
391 { .rfmax = 88000, .val = 0x35 },
392 { .rfmax = 89000, .val = 0x37 },
393 { .rfmax = 90000, .val = 0x38 },
394 { .rfmax = 91000, .val = 0x39 },
395 { .rfmax = 93000, .val = 0x3c },
396 { .rfmax = 94000, .val = 0x3e },
397 { .rfmax = 95000, .val = 0x3f },
398 { .rfmax = 96000, .val = 0x40 },
399 { .rfmax = 97000, .val = 0x42 },
400 { .rfmax = 99000, .val = 0x45 },
401 { .rfmax = 100000, .val = 0x46 },
402 { .rfmax = 102000, .val = 0x48 },
403 { .rfmax = 103000, .val = 0x4a },
404 { .rfmax = 105000, .val = 0x4d },
405 { .rfmax = 106000, .val = 0x4e },
406 { .rfmax = 107000, .val = 0x50 },
407 { .rfmax = 108000, .val = 0x51 },
408 { .rfmax = 110000, .val = 0x54 },
409 { .rfmax = 111000, .val = 0x56 },
410 { .rfmax = 112000, .val = 0x57 },
411 { .rfmax = 113000, .val = 0x58 },
412 { .rfmax = 114000, .val = 0x59 },
413 { .rfmax = 115000, .val = 0x5c },
414 { .rfmax = 116000, .val = 0x5d },
415 { .rfmax = 117000, .val = 0x5f },
416 { .rfmax = 119000, .val = 0x60 },
417 { .rfmax = 120000, .val = 0x64 },
418 { .rfmax = 121000, .val = 0x65 },
419 { .rfmax = 122000, .val = 0x66 },
420 { .rfmax = 123000, .val = 0x68 },
421 { .rfmax = 124000, .val = 0x69 },
422 { .rfmax = 125000, .val = 0x6c },
423 { .rfmax = 126000, .val = 0x6d },
424 { .rfmax = 127000, .val = 0x6e },
425 { .rfmax = 128000, .val = 0x70 },
426 { .rfmax = 129000, .val = 0x71 },
427 { .rfmax = 130000, .val = 0x75 },
428 { .rfmax = 131000, .val = 0x77 },
429 { .rfmax = 132000, .val = 0x78 },
430 { .rfmax = 133000, .val = 0x7b },
431 { .rfmax = 134000, .val = 0x7e },
432 { .rfmax = 135000, .val = 0x81 },
433 { .rfmax = 136000, .val = 0x82 },
434 { .rfmax = 137000, .val = 0x87 },
435 { .rfmax = 138000, .val = 0x88 },
436 { .rfmax = 139000, .val = 0x8d },
437 { .rfmax = 140000, .val = 0x8e },
438 { .rfmax = 141000, .val = 0x91 },
439 { .rfmax = 142000, .val = 0x95 },
440 { .rfmax = 143000, .val = 0x9a },
441 { .rfmax = 144000, .val = 0x9d },
442 { .rfmax = 145000, .val = 0xa1 },
443 { .rfmax = 146000, .val = 0xa2 },
444 { .rfmax = 147000, .val = 0xa4 },
445 { .rfmax = 148000, .val = 0xa9 },
446 { .rfmax = 149000, .val = 0xae },
447 { .rfmax = 150000, .val = 0xb0 },
448 { .rfmax = 151000, .val = 0xb1 },
449 { .rfmax = 152000, .val = 0xb7 },
450 { .rfmax = 152600, .val = 0xbd },
451 { .rfmax = 154000, .val = 0x20 },
452 { .rfmax = 155000, .val = 0x22 },
453 { .rfmax = 156000, .val = 0x24 },
454 { .rfmax = 157000, .val = 0x25 },
455 { .rfmax = 158000, .val = 0x27 },
456 { .rfmax = 159000, .val = 0x29 },
457 { .rfmax = 160000, .val = 0x2c },
458 { .rfmax = 161000, .val = 0x2d },
459 { .rfmax = 163000, .val = 0x2e },
460 { .rfmax = 164000, .val = 0x2f },
461 { .rfmax = 164700, .val = 0x30 },
462 { .rfmax = 166000, .val = 0x11 },
463 { .rfmax = 167000, .val = 0x12 },
464 { .rfmax = 168000, .val = 0x13 },
465 { .rfmax = 169000, .val = 0x14 },
466 { .rfmax = 170000, .val = 0x15 },
467 { .rfmax = 172000, .val = 0x16 },
468 { .rfmax = 173000, .val = 0x17 },
469 { .rfmax = 174000, .val = 0x18 },
470 { .rfmax = 175000, .val = 0x1a },
471 { .rfmax = 176000, .val = 0x1b },
472 { .rfmax = 178000, .val = 0x1d },
473 { .rfmax = 179000, .val = 0x1e },
474 { .rfmax = 180000, .val = 0x1f },
475 { .rfmax = 181000, .val = 0x20 },
476 { .rfmax = 182000, .val = 0x21 },
477 { .rfmax = 183000, .val = 0x22 },
478 { .rfmax = 184000, .val = 0x24 },
479 { .rfmax = 185000, .val = 0x25 },
480 { .rfmax = 186000, .val = 0x26 },
481 { .rfmax = 187000, .val = 0x27 },
482 { .rfmax = 188000, .val = 0x29 },
483 { .rfmax = 189000, .val = 0x2a },
484 { .rfmax = 190000, .val = 0x2c },
485 { .rfmax = 191000, .val = 0x2d },
486 { .rfmax = 192000, .val = 0x2e },
487 { .rfmax = 193000, .val = 0x2f },
488 { .rfmax = 194000, .val = 0x30 },
489 { .rfmax = 195000, .val = 0x33 },
490 { .rfmax = 196000, .val = 0x35 },
491 { .rfmax = 198000, .val = 0x36 },
492 { .rfmax = 200000, .val = 0x38 },
493 { .rfmax = 201000, .val = 0x3c },
494 { .rfmax = 202000, .val = 0x3d },
495 { .rfmax = 203500, .val = 0x3e },
496 { .rfmax = 206000, .val = 0x0e },
497 { .rfmax = 208000, .val = 0x0f },
498 { .rfmax = 212000, .val = 0x10 },
499 { .rfmax = 216000, .val = 0x11 },
500 { .rfmax = 217000, .val = 0x12 },
501 { .rfmax = 218000, .val = 0x13 },
502 { .rfmax = 220000, .val = 0x14 },
503 { .rfmax = 222000, .val = 0x15 },
504 { .rfmax = 225000, .val = 0x16 },
505 { .rfmax = 228000, .val = 0x17 },
506 { .rfmax = 231000, .val = 0x18 },
507 { .rfmax = 234000, .val = 0x19 },
508 { .rfmax = 235000, .val = 0x1a },
509 { .rfmax = 236000, .val = 0x1b },
510 { .rfmax = 237000, .val = 0x1c },
511 { .rfmax = 240000, .val = 0x1d },
512 { .rfmax = 242000, .val = 0x1e },
513 { .rfmax = 244000, .val = 0x1f },
514 { .rfmax = 247000, .val = 0x20 },
515 { .rfmax = 249000, .val = 0x21 },
516 { .rfmax = 252000, .val = 0x22 },
517 { .rfmax = 253000, .val = 0x23 },
518 { .rfmax = 254000, .val = 0x24 },
519 { .rfmax = 256000, .val = 0x25 },
520 { .rfmax = 259000, .val = 0x26 },
521 { .rfmax = 262000, .val = 0x27 },
522 { .rfmax = 264000, .val = 0x28 },
523 { .rfmax = 267000, .val = 0x29 },
524 { .rfmax = 269000, .val = 0x2a },
525 { .rfmax = 271000, .val = 0x2b },
526 { .rfmax = 273000, .val = 0x2c },
527 { .rfmax = 275000, .val = 0x2d },
528 { .rfmax = 277000, .val = 0x2e },
529 { .rfmax = 279000, .val = 0x2f },
530 { .rfmax = 282000, .val = 0x30 },
531 { .rfmax = 284000, .val = 0x31 },
532 { .rfmax = 286000, .val = 0x32 },
533 { .rfmax = 287000, .val = 0x33 },
534 { .rfmax = 290000, .val = 0x34 },
535 { .rfmax = 293000, .val = 0x35 },
536 { .rfmax = 295000, .val = 0x36 },
537 { .rfmax = 297000, .val = 0x37 },
538 { .rfmax = 300000, .val = 0x38 },
539 { .rfmax = 303000, .val = 0x39 },
540 { .rfmax = 305000, .val = 0x3a },
541 { .rfmax = 306000, .val = 0x3b },
542 { .rfmax = 307000, .val = 0x3c },
543 { .rfmax = 310000, .val = 0x3d },
544 { .rfmax = 312000, .val = 0x3e },
545 { .rfmax = 315000, .val = 0x3f },
546 { .rfmax = 318000, .val = 0x40 },
547 { .rfmax = 320000, .val = 0x41 },
548 { .rfmax = 323000, .val = 0x42 },
549 { .rfmax = 324000, .val = 0x43 },
550 { .rfmax = 325000, .val = 0x44 },
551 { .rfmax = 327000, .val = 0x45 },
552 { .rfmax = 331000, .val = 0x46 },
553 { .rfmax = 334000, .val = 0x47 },
554 { .rfmax = 337000, .val = 0x48 },
555 { .rfmax = 339000, .val = 0x49 },
556 { .rfmax = 340000, .val = 0x4a },
557 { .rfmax = 341000, .val = 0x4b },
558 { .rfmax = 343000, .val = 0x4c },
559 { .rfmax = 345000, .val = 0x4d },
560 { .rfmax = 349000, .val = 0x4e },
561 { .rfmax = 352000, .val = 0x4f },
562 { .rfmax = 353000, .val = 0x50 },
563 { .rfmax = 355000, .val = 0x51 },
564 { .rfmax = 357000, .val = 0x52 },
565 { .rfmax = 359000, .val = 0x53 },
566 { .rfmax = 361000, .val = 0x54 },
567 { .rfmax = 362000, .val = 0x55 },
568 { .rfmax = 364000, .val = 0x56 },
569 { .rfmax = 368000, .val = 0x57 },
570 { .rfmax = 370000, .val = 0x58 },
571 { .rfmax = 372000, .val = 0x59 },
572 { .rfmax = 375000, .val = 0x5a },
573 { .rfmax = 376000, .val = 0x5b },
574 { .rfmax = 377000, .val = 0x5c },
575 { .rfmax = 379000, .val = 0x5d },
576 { .rfmax = 382000, .val = 0x5e },
577 { .rfmax = 384000, .val = 0x5f },
578 { .rfmax = 385000, .val = 0x60 },
579 { .rfmax = 386000, .val = 0x61 },
580 { .rfmax = 388000, .val = 0x62 },
581 { .rfmax = 390000, .val = 0x63 },
582 { .rfmax = 393000, .val = 0x64 },
583 { .rfmax = 394000, .val = 0x65 },
584 { .rfmax = 396000, .val = 0x66 },
585 { .rfmax = 397000, .val = 0x67 },
586 { .rfmax = 398000, .val = 0x68 },
587 { .rfmax = 400000, .val = 0x69 },
588 { .rfmax = 402000, .val = 0x6a },
589 { .rfmax = 403000, .val = 0x6b },
590 { .rfmax = 407000, .val = 0x6c },
591 { .rfmax = 408000, .val = 0x6d },
592 { .rfmax = 409000, .val = 0x6e },
593 { .rfmax = 410000, .val = 0x6f },
594 { .rfmax = 411000, .val = 0x70 },
595 { .rfmax = 412000, .val = 0x71 },
596 { .rfmax = 413000, .val = 0x72 },
597 { .rfmax = 414000, .val = 0x73 },
598 { .rfmax = 417000, .val = 0x74 },
599 { .rfmax = 418000, .val = 0x75 },
600 { .rfmax = 420000, .val = 0x76 },
601 { .rfmax = 422000, .val = 0x77 },
602 { .rfmax = 423000, .val = 0x78 },
603 { .rfmax = 424000, .val = 0x79 },
604 { .rfmax = 427000, .val = 0x7a },
605 { .rfmax = 428000, .val = 0x7b },
606 { .rfmax = 429000, .val = 0x7d },
607 { .rfmax = 432000, .val = 0x7f },
608 { .rfmax = 434000, .val = 0x80 },
609 { .rfmax = 435000, .val = 0x81 },
610 { .rfmax = 436000, .val = 0x83 },
611 { .rfmax = 437000, .val = 0x84 },
612 { .rfmax = 438000, .val = 0x85 },
613 { .rfmax = 439000, .val = 0x86 },
614 { .rfmax = 440000, .val = 0x87 },
615 { .rfmax = 441000, .val = 0x88 },
616 { .rfmax = 442000, .val = 0x89 },
617 { .rfmax = 445000, .val = 0x8a },
618 { .rfmax = 446000, .val = 0x8b },
619 { .rfmax = 447000, .val = 0x8c },
620 { .rfmax = 448000, .val = 0x8e },
621 { .rfmax = 449000, .val = 0x8f },
622 { .rfmax = 450000, .val = 0x90 },
623 { .rfmax = 452000, .val = 0x91 },
624 { .rfmax = 453000, .val = 0x93 },
625 { .rfmax = 454000, .val = 0x94 },
626 { .rfmax = 456000, .val = 0x96 },
627 { .rfmax = 457800, .val = 0x98 },
628 { .rfmax = 461000, .val = 0x11 },
629 { .rfmax = 468000, .val = 0x12 },
630 { .rfmax = 472000, .val = 0x13 },
631 { .rfmax = 473000, .val = 0x14 },
632 { .rfmax = 474000, .val = 0x15 },
633 { .rfmax = 481000, .val = 0x16 },
634 { .rfmax = 486000, .val = 0x17 },
635 { .rfmax = 491000, .val = 0x18 },
636 { .rfmax = 498000, .val = 0x19 },
637 { .rfmax = 499000, .val = 0x1a },
638 { .rfmax = 501000, .val = 0x1b },
639 { .rfmax = 506000, .val = 0x1c },
640 { .rfmax = 511000, .val = 0x1d },
641 { .rfmax = 516000, .val = 0x1e },
642 { .rfmax = 520000, .val = 0x1f },
643 { .rfmax = 521000, .val = 0x20 },
644 { .rfmax = 525000, .val = 0x21 },
645 { .rfmax = 529000, .val = 0x22 },
646 { .rfmax = 533000, .val = 0x23 },
647 { .rfmax = 539000, .val = 0x24 },
648 { .rfmax = 541000, .val = 0x25 },
649 { .rfmax = 547000, .val = 0x26 },
650 { .rfmax = 549000, .val = 0x27 },
651 { .rfmax = 551000, .val = 0x28 },
652 { .rfmax = 556000, .val = 0x29 },
653 { .rfmax = 561000, .val = 0x2a },
654 { .rfmax = 563000, .val = 0x2b },
655 { .rfmax = 565000, .val = 0x2c },
656 { .rfmax = 569000, .val = 0x2d },
657 { .rfmax = 571000, .val = 0x2e },
658 { .rfmax = 577000, .val = 0x2f },
659 { .rfmax = 580000, .val = 0x30 },
660 { .rfmax = 582000, .val = 0x31 },
661 { .rfmax = 584000, .val = 0x32 },
662 { .rfmax = 588000, .val = 0x33 },
663 { .rfmax = 591000, .val = 0x34 },
664 { .rfmax = 596000, .val = 0x35 },
665 { .rfmax = 598000, .val = 0x36 },
666 { .rfmax = 603000, .val = 0x37 },
667 { .rfmax = 604000, .val = 0x38 },
668 { .rfmax = 606000, .val = 0x39 },
669 { .rfmax = 612000, .val = 0x3a },
670 { .rfmax = 615000, .val = 0x3b },
671 { .rfmax = 617000, .val = 0x3c },
672 { .rfmax = 621000, .val = 0x3d },
673 { .rfmax = 622000, .val = 0x3e },
674 { .rfmax = 625000, .val = 0x3f },
675 { .rfmax = 632000, .val = 0x40 },
676 { .rfmax = 633000, .val = 0x41 },
677 { .rfmax = 634000, .val = 0x42 },
678 { .rfmax = 642000, .val = 0x43 },
679 { .rfmax = 643000, .val = 0x44 },
680 { .rfmax = 647000, .val = 0x45 },
681 { .rfmax = 650000, .val = 0x46 },
682 { .rfmax = 652000, .val = 0x47 },
683 { .rfmax = 657000, .val = 0x48 },
684 { .rfmax = 661000, .val = 0x49 },
685 { .rfmax = 662000, .val = 0x4a },
686 { .rfmax = 665000, .val = 0x4b },
687 { .rfmax = 667000, .val = 0x4c },
688 { .rfmax = 670000, .val = 0x4d },
689 { .rfmax = 673000, .val = 0x4e },
690 { .rfmax = 676000, .val = 0x4f },
691 { .rfmax = 677000, .val = 0x50 },
692 { .rfmax = 681000, .val = 0x51 },
693 { .rfmax = 683000, .val = 0x52 },
694 { .rfmax = 686000, .val = 0x53 },
695 { .rfmax = 688000, .val = 0x54 },
696 { .rfmax = 689000, .val = 0x55 },
697 { .rfmax = 691000, .val = 0x56 },
698 { .rfmax = 695000, .val = 0x57 },
699 { .rfmax = 698000, .val = 0x58 },
700 { .rfmax = 703000, .val = 0x59 },
701 { .rfmax = 704000, .val = 0x5a },
702 { .rfmax = 705000, .val = 0x5b },
703 { .rfmax = 707000, .val = 0x5c },
704 { .rfmax = 710000, .val = 0x5d },
705 { .rfmax = 712000, .val = 0x5e },
706 { .rfmax = 717000, .val = 0x5f },
707 { .rfmax = 718000, .val = 0x60 },
708 { .rfmax = 721000, .val = 0x61 },
709 { .rfmax = 722000, .val = 0x62 },
710 { .rfmax = 723000, .val = 0x63 },
711 { .rfmax = 725000, .val = 0x64 },
712 { .rfmax = 727000, .val = 0x65 },
713 { .rfmax = 730000, .val = 0x66 },
714 { .rfmax = 732000, .val = 0x67 },
715 { .rfmax = 735000, .val = 0x68 },
716 { .rfmax = 740000, .val = 0x69 },
717 { .rfmax = 741000, .val = 0x6a },
718 { .rfmax = 742000, .val = 0x6b },
719 { .rfmax = 743000, .val = 0x6c },
720 { .rfmax = 745000, .val = 0x6d },
721 { .rfmax = 747000, .val = 0x6e },
722 { .rfmax = 748000, .val = 0x6f },
723 { .rfmax = 750000, .val = 0x70 },
724 { .rfmax = 752000, .val = 0x71 },
725 { .rfmax = 754000, .val = 0x72 },
726 { .rfmax = 757000, .val = 0x73 },
727 { .rfmax = 758000, .val = 0x74 },
728 { .rfmax = 760000, .val = 0x75 },
729 { .rfmax = 763000, .val = 0x76 },
730 { .rfmax = 764000, .val = 0x77 },
731 { .rfmax = 766000, .val = 0x78 },
732 { .rfmax = 767000, .val = 0x79 },
733 { .rfmax = 768000, .val = 0x7a },
734 { .rfmax = 773000, .val = 0x7b },
735 { .rfmax = 774000, .val = 0x7c },
736 { .rfmax = 776000, .val = 0x7d },
737 { .rfmax = 777000, .val = 0x7e },
738 { .rfmax = 778000, .val = 0x7f },
739 { .rfmax = 779000, .val = 0x80 },
740 { .rfmax = 781000, .val = 0x81 },
741 { .rfmax = 783000, .val = 0x82 },
742 { .rfmax = 784000, .val = 0x83 },
743 { .rfmax = 785000, .val = 0x84 },
744 { .rfmax = 786000, .val = 0x85 },
745 { .rfmax = 793000, .val = 0x86 },
746 { .rfmax = 794000, .val = 0x87 },
747 { .rfmax = 795000, .val = 0x88 },
748 { .rfmax = 797000, .val = 0x89 },
749 { .rfmax = 799000, .val = 0x8a },
750 { .rfmax = 801000, .val = 0x8b },
751 { .rfmax = 802000, .val = 0x8c },
752 { .rfmax = 803000, .val = 0x8d },
753 { .rfmax = 804000, .val = 0x8e },
754 { .rfmax = 810000, .val = 0x90 },
755 { .rfmax = 811000, .val = 0x91 },
756 { .rfmax = 812000, .val = 0x92 },
757 { .rfmax = 814000, .val = 0x93 },
758 { .rfmax = 816000, .val = 0x94 },
759 { .rfmax = 817000, .val = 0x96 },
760 { .rfmax = 818000, .val = 0x97 },
761 { .rfmax = 820000, .val = 0x98 },
762 { .rfmax = 821000, .val = 0x99 },
763 { .rfmax = 822000, .val = 0x9a },
764 { .rfmax = 828000, .val = 0x9b },
765 { .rfmax = 829000, .val = 0x9d },
766 { .rfmax = 830000, .val = 0x9f },
767 { .rfmax = 831000, .val = 0xa0 },
768 { .rfmax = 833000, .val = 0xa1 },
769 { .rfmax = 835000, .val = 0xa2 },
770 { .rfmax = 836000, .val = 0xa3 },
771 { .rfmax = 837000, .val = 0xa4 },
772 { .rfmax = 838000, .val = 0xa6 },
773 { .rfmax = 840000, .val = 0xa8 },
774 { .rfmax = 842000, .val = 0xa9 },
775 { .rfmax = 845000, .val = 0xaa },
776 { .rfmax = 846000, .val = 0xab },
777 { .rfmax = 847000, .val = 0xad },
778 { .rfmax = 848000, .val = 0xae },
779 { .rfmax = 852000, .val = 0xaf },
780 { .rfmax = 853000, .val = 0xb0 },
781 { .rfmax = 858000, .val = 0xb1 },
782 { .rfmax = 860000, .val = 0xb2 },
783 { .rfmax = 861000, .val = 0xb3 },
784 { .rfmax = 862000, .val = 0xb4 },
785 { .rfmax = 863000, .val = 0xb6 },
786 { .rfmax = 864000, .val = 0xb8 },
787 { .rfmax = 865000, .val = 0xb9 },
788 { .rfmax = 0, .val = 0x00 }, /* end */
789};
790
791static struct tda18271_map tda18271_ir_measure[] = {
792 { .rfmax = 30000, .val = 4 },
793 { .rfmax = 200000, .val = 5 },
794 { .rfmax = 600000, .val = 6 },
795 { .rfmax = 865000, .val = 7 },
796 { .rfmax = 0, .val = 0 }, /* end */
797};
798
799static struct tda18271_map tda18271_rf_cal_dc_over_dt[] = {
800 { .rfmax = 47900, .val = 0x00 },
801 { .rfmax = 55000, .val = 0x00 },
802 { .rfmax = 61100, .val = 0x0a },
803 { .rfmax = 64000, .val = 0x0a },
804 { .rfmax = 82000, .val = 0x14 },
805 { .rfmax = 84000, .val = 0x19 },
806 { .rfmax = 119000, .val = 0x1c },
807 { .rfmax = 124000, .val = 0x20 },
808 { .rfmax = 129000, .val = 0x2a },
809 { .rfmax = 134000, .val = 0x32 },
810 { .rfmax = 139000, .val = 0x39 },
811 { .rfmax = 144000, .val = 0x3e },
812 { .rfmax = 149000, .val = 0x3f },
813 { .rfmax = 152600, .val = 0x40 },
814 { .rfmax = 154000, .val = 0x40 },
815 { .rfmax = 164700, .val = 0x41 },
816 { .rfmax = 203500, .val = 0x32 },
817 { .rfmax = 353000, .val = 0x19 },
818 { .rfmax = 356000, .val = 0x1a },
819 { .rfmax = 359000, .val = 0x1b },
820 { .rfmax = 363000, .val = 0x1c },
821 { .rfmax = 366000, .val = 0x1d },
822 { .rfmax = 369000, .val = 0x1e },
823 { .rfmax = 373000, .val = 0x1f },
824 { .rfmax = 376000, .val = 0x20 },
825 { .rfmax = 379000, .val = 0x21 },
826 { .rfmax = 383000, .val = 0x22 },
827 { .rfmax = 386000, .val = 0x23 },
828 { .rfmax = 389000, .val = 0x24 },
829 { .rfmax = 393000, .val = 0x25 },
830 { .rfmax = 396000, .val = 0x26 },
831 { .rfmax = 399000, .val = 0x27 },
832 { .rfmax = 402000, .val = 0x28 },
833 { .rfmax = 404000, .val = 0x29 },
834 { .rfmax = 407000, .val = 0x2a },
835 { .rfmax = 409000, .val = 0x2b },
836 { .rfmax = 412000, .val = 0x2c },
837 { .rfmax = 414000, .val = 0x2d },
838 { .rfmax = 417000, .val = 0x2e },
839 { .rfmax = 419000, .val = 0x2f },
840 { .rfmax = 422000, .val = 0x30 },
841 { .rfmax = 424000, .val = 0x31 },
842 { .rfmax = 427000, .val = 0x32 },
843 { .rfmax = 429000, .val = 0x33 },
844 { .rfmax = 432000, .val = 0x34 },
845 { .rfmax = 434000, .val = 0x35 },
846 { .rfmax = 437000, .val = 0x36 },
847 { .rfmax = 439000, .val = 0x37 },
848 { .rfmax = 442000, .val = 0x38 },
849 { .rfmax = 444000, .val = 0x39 },
850 { .rfmax = 447000, .val = 0x3a },
851 { .rfmax = 449000, .val = 0x3b },
852 { .rfmax = 457800, .val = 0x3c },
853 { .rfmax = 465000, .val = 0x0f },
854 { .rfmax = 477000, .val = 0x12 },
855 { .rfmax = 483000, .val = 0x14 },
856 { .rfmax = 502000, .val = 0x19 },
857 { .rfmax = 508000, .val = 0x1b },
858 { .rfmax = 519000, .val = 0x1c },
859 { .rfmax = 522000, .val = 0x1d },
860 { .rfmax = 524000, .val = 0x1e },
861 { .rfmax = 534000, .val = 0x1f },
862 { .rfmax = 549000, .val = 0x20 },
863 { .rfmax = 554000, .val = 0x22 },
864 { .rfmax = 584000, .val = 0x24 },
865 { .rfmax = 589000, .val = 0x26 },
866 { .rfmax = 658000, .val = 0x27 },
867 { .rfmax = 664000, .val = 0x2c },
868 { .rfmax = 669000, .val = 0x2d },
869 { .rfmax = 699000, .val = 0x2e },
870 { .rfmax = 704000, .val = 0x30 },
871 { .rfmax = 709000, .val = 0x31 },
872 { .rfmax = 714000, .val = 0x32 },
873 { .rfmax = 724000, .val = 0x33 },
874 { .rfmax = 729000, .val = 0x36 },
875 { .rfmax = 739000, .val = 0x38 },
876 { .rfmax = 744000, .val = 0x39 },
877 { .rfmax = 749000, .val = 0x3b },
878 { .rfmax = 754000, .val = 0x3c },
879 { .rfmax = 759000, .val = 0x3d },
880 { .rfmax = 764000, .val = 0x3e },
881 { .rfmax = 769000, .val = 0x3f },
882 { .rfmax = 774000, .val = 0x40 },
883 { .rfmax = 779000, .val = 0x41 },
884 { .rfmax = 784000, .val = 0x43 },
885 { .rfmax = 789000, .val = 0x46 },
886 { .rfmax = 794000, .val = 0x48 },
887 { .rfmax = 799000, .val = 0x4b },
888 { .rfmax = 804000, .val = 0x4f },
889 { .rfmax = 809000, .val = 0x54 },
890 { .rfmax = 814000, .val = 0x59 },
891 { .rfmax = 819000, .val = 0x5d },
892 { .rfmax = 824000, .val = 0x61 },
893 { .rfmax = 829000, .val = 0x68 },
894 { .rfmax = 834000, .val = 0x6e },
895 { .rfmax = 839000, .val = 0x75 },
896 { .rfmax = 844000, .val = 0x7e },
897 { .rfmax = 849000, .val = 0x82 },
898 { .rfmax = 854000, .val = 0x84 },
899 { .rfmax = 859000, .val = 0x8f },
900 { .rfmax = 865000, .val = 0x9a },
901 { .rfmax = 0, .val = 0x00 }, /* end */
902};
903
904/*---------------------------------------------------------------------*/
905
906struct tda18271_thermo_map {
907 u8 d;
908 u8 r0;
909 u8 r1;
910};
911
912static struct tda18271_thermo_map tda18271_thermometer[] = {
913 { .d = 0x00, .r0 = 60, .r1 = 92 },
914 { .d = 0x01, .r0 = 62, .r1 = 94 },
915 { .d = 0x02, .r0 = 66, .r1 = 98 },
916 { .d = 0x03, .r0 = 64, .r1 = 96 },
917 { .d = 0x04, .r0 = 74, .r1 = 106 },
918 { .d = 0x05, .r0 = 72, .r1 = 104 },
919 { .d = 0x06, .r0 = 68, .r1 = 100 },
920 { .d = 0x07, .r0 = 70, .r1 = 102 },
921 { .d = 0x08, .r0 = 90, .r1 = 122 },
922 { .d = 0x09, .r0 = 88, .r1 = 120 },
923 { .d = 0x0a, .r0 = 84, .r1 = 116 },
924 { .d = 0x0b, .r0 = 86, .r1 = 118 },
925 { .d = 0x0c, .r0 = 76, .r1 = 108 },
926 { .d = 0x0d, .r0 = 78, .r1 = 110 },
927 { .d = 0x0e, .r0 = 82, .r1 = 114 },
928 { .d = 0x0f, .r0 = 80, .r1 = 112 },
929 { .d = 0x00, .r0 = 0, .r1 = 0 }, /* end */
930};
931
932int tda18271_lookup_thermometer(struct dvb_frontend *fe)
933{
934 struct tda18271_priv *priv = fe->tuner_priv;
935 unsigned char *regs = priv->tda18271_regs;
936 int val, i = 0;
937
938 while (tda18271_thermometer[i].d < (regs[R_TM] & 0x0f)) {
939 if (tda18271_thermometer[i + 1].d == 0)
940 break;
941 i++;
942 }
943
944 if ((regs[R_TM] & 0x20) == 0x20)
945 val = tda18271_thermometer[i].r1;
946 else
947 val = tda18271_thermometer[i].r0;
948
949 tda_map("(%d) tm = %d\n", i, val);
950
951 return val;
952}
953
954/*---------------------------------------------------------------------*/
955
956struct tda18271_cid_target_map {
957 u32 rfmax;
958 u8 target;
959 u16 limit;
960};
961
962static struct tda18271_cid_target_map tda18271_cid_target[] = {
963 { .rfmax = 46000, .target = 0x04, .limit = 1800 },
964 { .rfmax = 52200, .target = 0x0a, .limit = 1500 },
965 { .rfmax = 70100, .target = 0x01, .limit = 4000 },
966 { .rfmax = 136800, .target = 0x18, .limit = 4000 },
967 { .rfmax = 156700, .target = 0x18, .limit = 4000 },
968 { .rfmax = 186250, .target = 0x0a, .limit = 4000 },
969 { .rfmax = 230000, .target = 0x0a, .limit = 4000 },
970 { .rfmax = 345000, .target = 0x18, .limit = 4000 },
971 { .rfmax = 426000, .target = 0x0e, .limit = 4000 },
972 { .rfmax = 489500, .target = 0x1e, .limit = 4000 },
973 { .rfmax = 697500, .target = 0x32, .limit = 4000 },
974 { .rfmax = 842000, .target = 0x3a, .limit = 4000 },
975 { .rfmax = 0, .target = 0x00, .limit = 0 }, /* end */
976};
977
978int tda18271_lookup_cid_target(struct dvb_frontend *fe,
979 u32 *freq, u8 *cid_target, u16 *count_limit)
980{
981 struct tda18271_priv *priv = fe->tuner_priv;
982 int i = 0;
983
984 while ((tda18271_cid_target[i].rfmax * 1000) < *freq) {
985 if (tda18271_cid_target[i + 1].rfmax == 0)
986 break;
987 i++;
988 }
989 *cid_target = tda18271_cid_target[i].target;
990 *count_limit = tda18271_cid_target[i].limit;
991
992 tda_map("(%d) cid_target = %02x, count_limit = %d\n", i,
993 tda18271_cid_target[i].target, tda18271_cid_target[i].limit);
994
995 return 0;
996}
997
998/*---------------------------------------------------------------------*/
999
1000static struct tda18271_rf_tracking_filter_cal tda18271_rf_band_template[] = {
1001 { .rfmax = 47900, .rfband = 0x00,
1002 .rf1_def = 46000, .rf2_def = 0, .rf3_def = 0 },
1003 { .rfmax = 61100, .rfband = 0x01,
1004 .rf1_def = 52200, .rf2_def = 0, .rf3_def = 0 },
1005 { .rfmax = 152600, .rfband = 0x02,
1006 .rf1_def = 70100, .rf2_def = 136800, .rf3_def = 0 },
1007 { .rfmax = 164700, .rfband = 0x03,
1008 .rf1_def = 156700, .rf2_def = 0, .rf3_def = 0 },
1009 { .rfmax = 203500, .rfband = 0x04,
1010 .rf1_def = 186250, .rf2_def = 0, .rf3_def = 0 },
1011 { .rfmax = 457800, .rfband = 0x05,
1012 .rf1_def = 230000, .rf2_def = 345000, .rf3_def = 426000 },
1013 { .rfmax = 865000, .rfband = 0x06,
1014 .rf1_def = 489500, .rf2_def = 697500, .rf3_def = 842000 },
1015 { .rfmax = 0, .rfband = 0x00,
1016 .rf1_def = 0, .rf2_def = 0, .rf3_def = 0 }, /* end */
1017};
1018
1019int tda18271_lookup_rf_band(struct dvb_frontend *fe, u32 *freq, u8 *rf_band)
1020{
1021 struct tda18271_priv *priv = fe->tuner_priv;
1022 struct tda18271_rf_tracking_filter_cal *map = priv->rf_cal_state;
1023 int i = 0;
1024
1025 while ((map[i].rfmax * 1000) < *freq) {
1026 if (tda18271_debug & DBG_ADV)
1027 tda_map("(%d) rfmax = %d < freq = %d, "
1028 "rf1_def = %d, rf2_def = %d, rf3_def = %d, "
1029 "rf1 = %d, rf2 = %d, rf3 = %d, "
1030 "rf_a1 = %d, rf_a2 = %d, "
1031 "rf_b1 = %d, rf_b2 = %d\n",
1032 i, map[i].rfmax * 1000, *freq,
1033 map[i].rf1_def, map[i].rf2_def, map[i].rf3_def,
1034 map[i].rf1, map[i].rf2, map[i].rf3,
1035 map[i].rf_a1, map[i].rf_a2,
1036 map[i].rf_b1, map[i].rf_b2);
1037 if (map[i].rfmax == 0)
1038 return -EINVAL;
1039 i++;
1040 }
1041 if (rf_band)
1042 *rf_band = map[i].rfband;
1043
1044 tda_map("(%d) rf_band = %02x\n", i, map[i].rfband);
1045
1046 return i;
1047}
1048
1049/*---------------------------------------------------------------------*/
1050
1051struct tda18271_map_layout {
1052 struct tda18271_pll_map *main_pll;
1053 struct tda18271_pll_map *cal_pll;
1054
1055 struct tda18271_map *rf_cal;
1056 struct tda18271_map *rf_cal_kmco;
1057 struct tda18271_map *rf_cal_dc_over_dt;
1058
1059 struct tda18271_map *bp_filter;
1060 struct tda18271_map *rf_band;
1061 struct tda18271_map *gain_taper;
1062 struct tda18271_map *ir_measure;
1063};
1064
1065/*---------------------------------------------------------------------*/
1066
1067int tda18271_lookup_pll_map(struct dvb_frontend *fe,
1068 enum tda18271_map_type map_type,
1069 u32 *freq, u8 *post_div, u8 *div)
1070{
1071 struct tda18271_priv *priv = fe->tuner_priv;
1072 struct tda18271_pll_map *map = NULL;
1073 unsigned int i = 0;
1074 char *map_name;
1075 int ret = 0;
1076
1077 BUG_ON(!priv->maps);
1078
1079 switch (map_type) {
1080 case MAIN_PLL:
1081 map = priv->maps->main_pll;
1082 map_name = "main_pll";
1083 break;
1084 case CAL_PLL:
1085 map = priv->maps->cal_pll;
1086 map_name = "cal_pll";
1087 break;
1088 default:
1089 /* we should never get here */
1090 map_name = "undefined";
1091 break;
1092 }
1093
1094 if (!map) {
1095 tda_warn("%s map is not set!\n", map_name);
1096 ret = -EINVAL;
1097 goto fail;
1098 }
1099
1100 while ((map[i].lomax * 1000) < *freq) {
1101 if (map[i + 1].lomax == 0) {
1102 tda_map("%s: frequency (%d) out of range\n",
1103 map_name, *freq);
1104 ret = -ERANGE;
1105 break;
1106 }
1107 i++;
1108 }
1109 *post_div = map[i].pd;
1110 *div = map[i].d;
1111
1112 tda_map("(%d) %s: post div = 0x%02x, div = 0x%02x\n",
1113 i, map_name, *post_div, *div);
1114fail:
1115 return ret;
1116}
1117
1118int tda18271_lookup_map(struct dvb_frontend *fe,
1119 enum tda18271_map_type map_type,
1120 u32 *freq, u8 *val)
1121{
1122 struct tda18271_priv *priv = fe->tuner_priv;
1123 struct tda18271_map *map = NULL;
1124 unsigned int i = 0;
1125 char *map_name;
1126 int ret = 0;
1127
1128 BUG_ON(!priv->maps);
1129
1130 switch (map_type) {
1131 case BP_FILTER:
1132 map = priv->maps->bp_filter;
1133 map_name = "bp_filter";
1134 break;
1135 case RF_CAL_KMCO:
1136 map = priv->maps->rf_cal_kmco;
1137 map_name = "km";
1138 break;
1139 case RF_BAND:
1140 map = priv->maps->rf_band;
1141 map_name = "rf_band";
1142 break;
1143 case GAIN_TAPER:
1144 map = priv->maps->gain_taper;
1145 map_name = "gain_taper";
1146 break;
1147 case RF_CAL:
1148 map = priv->maps->rf_cal;
1149 map_name = "rf_cal";
1150 break;
1151 case IR_MEASURE:
1152 map = priv->maps->ir_measure;
1153 map_name = "ir_measure";
1154 break;
1155 case RF_CAL_DC_OVER_DT:
1156 map = priv->maps->rf_cal_dc_over_dt;
1157 map_name = "rf_cal_dc_over_dt";
1158 break;
1159 default:
1160 /* we should never get here */
1161 map_name = "undefined";
1162 break;
1163 }
1164
1165 if (!map) {
1166 tda_warn("%s map is not set!\n", map_name);
1167 ret = -EINVAL;
1168 goto fail;
1169 }
1170
1171 while ((map[i].rfmax * 1000) < *freq) {
1172 if (map[i + 1].rfmax == 0) {
1173 tda_map("%s: frequency (%d) out of range\n",
1174 map_name, *freq);
1175 ret = -ERANGE;
1176 break;
1177 }
1178 i++;
1179 }
1180 *val = map[i].val;
1181
1182 tda_map("(%d) %s: 0x%02x\n", i, map_name, *val);
1183fail:
1184 return ret;
1185}
1186
1187/*---------------------------------------------------------------------*/
1188
1189static struct tda18271_std_map tda18271c1_std_map = {
1190 .fm_radio = { .if_freq = 1250, .fm_rfn = 1, .agc_mode = 3, .std = 0,
1191 .if_lvl = 0, .rfagc_top = 0x2c, }, /* EP3[4:0] 0x18 */
1192 .atv_b = { .if_freq = 6750, .fm_rfn = 0, .agc_mode = 1, .std = 6,
1193 .if_lvl = 0, .rfagc_top = 0x2c, }, /* EP3[4:0] 0x0e */
1194 .atv_dk = { .if_freq = 7750, .fm_rfn = 0, .agc_mode = 1, .std = 7,
1195 .if_lvl = 0, .rfagc_top = 0x2c, }, /* EP3[4:0] 0x0f */
1196 .atv_gh = { .if_freq = 7750, .fm_rfn = 0, .agc_mode = 1, .std = 7,
1197 .if_lvl = 0, .rfagc_top = 0x2c, }, /* EP3[4:0] 0x0f */
1198 .atv_i = { .if_freq = 7750, .fm_rfn = 0, .agc_mode = 1, .std = 7,
1199 .if_lvl = 0, .rfagc_top = 0x2c, }, /* EP3[4:0] 0x0f */
1200 .atv_l = { .if_freq = 7750, .fm_rfn = 0, .agc_mode = 1, .std = 7,
1201 .if_lvl = 0, .rfagc_top = 0x2c, }, /* EP3[4:0] 0x0f */
1202 .atv_lc = { .if_freq = 1250, .fm_rfn = 0, .agc_mode = 1, .std = 7,
1203 .if_lvl = 0, .rfagc_top = 0x2c, }, /* EP3[4:0] 0x0f */
1204 .atv_mn = { .if_freq = 5750, .fm_rfn = 0, .agc_mode = 1, .std = 5,
1205 .if_lvl = 0, .rfagc_top = 0x2c, }, /* EP3[4:0] 0x0d */
1206 .atsc_6 = { .if_freq = 3250, .fm_rfn = 0, .agc_mode = 3, .std = 4,
1207 .if_lvl = 1, .rfagc_top = 0x37, }, /* EP3[4:0] 0x1c */
1208 .dvbt_6 = { .if_freq = 3300, .fm_rfn = 0, .agc_mode = 3, .std = 4,
1209 .if_lvl = 1, .rfagc_top = 0x37, }, /* EP3[4:0] 0x1c */
1210 .dvbt_7 = { .if_freq = 3800, .fm_rfn = 0, .agc_mode = 3, .std = 5,
1211 .if_lvl = 1, .rfagc_top = 0x37, }, /* EP3[4:0] 0x1d */
1212 .dvbt_8 = { .if_freq = 4300, .fm_rfn = 0, .agc_mode = 3, .std = 6,
1213 .if_lvl = 1, .rfagc_top = 0x37, }, /* EP3[4:0] 0x1e */
1214 .qam_6 = { .if_freq = 4000, .fm_rfn = 0, .agc_mode = 3, .std = 5,
1215 .if_lvl = 1, .rfagc_top = 0x37, }, /* EP3[4:0] 0x1d */
1216 .qam_8 = { .if_freq = 5000, .fm_rfn = 0, .agc_mode = 3, .std = 7,
1217 .if_lvl = 1, .rfagc_top = 0x37, }, /* EP3[4:0] 0x1f */
1218};
1219
1220static struct tda18271_std_map tda18271c2_std_map = {
1221 .fm_radio = { .if_freq = 1250, .fm_rfn = 1, .agc_mode = 3, .std = 0,
1222 .if_lvl = 0, .rfagc_top = 0x2c, }, /* EP3[4:0] 0x18 */
1223 .atv_b = { .if_freq = 6000, .fm_rfn = 0, .agc_mode = 1, .std = 5,
1224 .if_lvl = 0, .rfagc_top = 0x2c, }, /* EP3[4:0] 0x0d */
1225 .atv_dk = { .if_freq = 6900, .fm_rfn = 0, .agc_mode = 1, .std = 6,
1226 .if_lvl = 0, .rfagc_top = 0x2c, }, /* EP3[4:0] 0x0e */
1227 .atv_gh = { .if_freq = 7100, .fm_rfn = 0, .agc_mode = 1, .std = 6,
1228 .if_lvl = 0, .rfagc_top = 0x2c, }, /* EP3[4:0] 0x0e */
1229 .atv_i = { .if_freq = 7250, .fm_rfn = 0, .agc_mode = 1, .std = 6,
1230 .if_lvl = 0, .rfagc_top = 0x2c, }, /* EP3[4:0] 0x0e */
1231 .atv_l = { .if_freq = 6900, .fm_rfn = 0, .agc_mode = 1, .std = 6,
1232 .if_lvl = 0, .rfagc_top = 0x2c, }, /* EP3[4:0] 0x0e */
1233 .atv_lc = { .if_freq = 1250, .fm_rfn = 0, .agc_mode = 1, .std = 6,
1234 .if_lvl = 0, .rfagc_top = 0x2c, }, /* EP3[4:0] 0x0e */
1235 .atv_mn = { .if_freq = 5400, .fm_rfn = 0, .agc_mode = 1, .std = 4,
1236 .if_lvl = 0, .rfagc_top = 0x2c, }, /* EP3[4:0] 0x0c */
1237 .atsc_6 = { .if_freq = 3250, .fm_rfn = 0, .agc_mode = 3, .std = 4,
1238 .if_lvl = 1, .rfagc_top = 0x37, }, /* EP3[4:0] 0x1c */
1239 .dvbt_6 = { .if_freq = 3300, .fm_rfn = 0, .agc_mode = 3, .std = 4,
1240 .if_lvl = 1, .rfagc_top = 0x37, }, /* EP3[4:0] 0x1c */
1241 .dvbt_7 = { .if_freq = 3500, .fm_rfn = 0, .agc_mode = 3, .std = 4,
1242 .if_lvl = 1, .rfagc_top = 0x37, }, /* EP3[4:0] 0x1c */
1243 .dvbt_8 = { .if_freq = 4000, .fm_rfn = 0, .agc_mode = 3, .std = 5,
1244 .if_lvl = 1, .rfagc_top = 0x37, }, /* EP3[4:0] 0x1d */
1245 .qam_6 = { .if_freq = 4000, .fm_rfn = 0, .agc_mode = 3, .std = 5,
1246 .if_lvl = 1, .rfagc_top = 0x37, }, /* EP3[4:0] 0x1d */
1247 .qam_8 = { .if_freq = 5000, .fm_rfn = 0, .agc_mode = 3, .std = 7,
1248 .if_lvl = 1, .rfagc_top = 0x37, }, /* EP3[4:0] 0x1f */
1249};
1250
1251/*---------------------------------------------------------------------*/
1252
1253static struct tda18271_map_layout tda18271c1_map_layout = {
1254 .main_pll = tda18271c1_main_pll,
1255 .cal_pll = tda18271c1_cal_pll,
1256
1257 .rf_cal = tda18271c1_rf_cal,
1258 .rf_cal_kmco = tda18271c1_km,
1259
1260 .bp_filter = tda18271_bp_filter,
1261 .rf_band = tda18271_rf_band,
1262 .gain_taper = tda18271_gain_taper,
1263 .ir_measure = tda18271_ir_measure,
1264};
1265
1266static struct tda18271_map_layout tda18271c2_map_layout = {
1267 .main_pll = tda18271c2_main_pll,
1268 .cal_pll = tda18271c2_cal_pll,
1269
1270 .rf_cal = tda18271c2_rf_cal,
1271 .rf_cal_kmco = tda18271c2_km,
1272
1273 .rf_cal_dc_over_dt = tda18271_rf_cal_dc_over_dt,
1274
1275 .bp_filter = tda18271_bp_filter,
1276 .rf_band = tda18271_rf_band,
1277 .gain_taper = tda18271_gain_taper,
1278 .ir_measure = tda18271_ir_measure,
1279};
1280
1281int tda18271_assign_map_layout(struct dvb_frontend *fe)
1282{
1283 struct tda18271_priv *priv = fe->tuner_priv;
1284 int ret = 0;
1285
1286 switch (priv->id) {
1287 case TDA18271HDC1:
1288 priv->maps = &tda18271c1_map_layout;
1289 memcpy(&priv->std, &tda18271c1_std_map,
1290 sizeof(struct tda18271_std_map));
1291 break;
1292 case TDA18271HDC2:
1293 priv->maps = &tda18271c2_map_layout;
1294 memcpy(&priv->std, &tda18271c2_std_map,
1295 sizeof(struct tda18271_std_map));
1296 break;
1297 default:
1298 ret = -EINVAL;
1299 break;
1300 }
1301 memcpy(priv->rf_cal_state, &tda18271_rf_band_template,
1302 sizeof(tda18271_rf_band_template));
1303
1304 return ret;
1305}
1306
1307/*
1308 * Overrides for Emacs so that we follow Linus's tabbing style.
1309 * ---------------------------------------------------------------------------
1310 * Local variables:
1311 * c-basic-offset: 8
1312 * End:
1313 */
diff --git a/drivers/media/common/tuners/tda18271-priv.h b/drivers/media/common/tuners/tda18271-priv.h
new file mode 100644
index 00000000000..9589ab0576d
--- /dev/null
+++ b/drivers/media/common/tuners/tda18271-priv.h
@@ -0,0 +1,237 @@
1/*
2 tda18271-priv.h - private header for the NXP TDA18271 silicon tuner
3
4 Copyright (C) 2007, 2008 Michael Krufky <mkrufky@linuxtv.org>
5
6 This program is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 2 of the License, or
9 (at your option) any later version.
10
11 This program is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
15
16 You should have received a copy of the GNU General Public License
17 along with this program; if not, write to the Free Software
18 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
19*/
20
21#ifndef __TDA18271_PRIV_H__
22#define __TDA18271_PRIV_H__
23
24#include <linux/kernel.h>
25#include <linux/types.h>
26#include <linux/mutex.h>
27#include "tuner-i2c.h"
28#include "tda18271.h"
29
30#define R_ID 0x00 /* ID byte */
31#define R_TM 0x01 /* Thermo byte */
32#define R_PL 0x02 /* Power level byte */
33#define R_EP1 0x03 /* Easy Prog byte 1 */
34#define R_EP2 0x04 /* Easy Prog byte 2 */
35#define R_EP3 0x05 /* Easy Prog byte 3 */
36#define R_EP4 0x06 /* Easy Prog byte 4 */
37#define R_EP5 0x07 /* Easy Prog byte 5 */
38#define R_CPD 0x08 /* Cal Post-Divider byte */
39#define R_CD1 0x09 /* Cal Divider byte 1 */
40#define R_CD2 0x0a /* Cal Divider byte 2 */
41#define R_CD3 0x0b /* Cal Divider byte 3 */
42#define R_MPD 0x0c /* Main Post-Divider byte */
43#define R_MD1 0x0d /* Main Divider byte 1 */
44#define R_MD2 0x0e /* Main Divider byte 2 */
45#define R_MD3 0x0f /* Main Divider byte 3 */
46#define R_EB1 0x10 /* Extended byte 1 */
47#define R_EB2 0x11 /* Extended byte 2 */
48#define R_EB3 0x12 /* Extended byte 3 */
49#define R_EB4 0x13 /* Extended byte 4 */
50#define R_EB5 0x14 /* Extended byte 5 */
51#define R_EB6 0x15 /* Extended byte 6 */
52#define R_EB7 0x16 /* Extended byte 7 */
53#define R_EB8 0x17 /* Extended byte 8 */
54#define R_EB9 0x18 /* Extended byte 9 */
55#define R_EB10 0x19 /* Extended byte 10 */
56#define R_EB11 0x1a /* Extended byte 11 */
57#define R_EB12 0x1b /* Extended byte 12 */
58#define R_EB13 0x1c /* Extended byte 13 */
59#define R_EB14 0x1d /* Extended byte 14 */
60#define R_EB15 0x1e /* Extended byte 15 */
61#define R_EB16 0x1f /* Extended byte 16 */
62#define R_EB17 0x20 /* Extended byte 17 */
63#define R_EB18 0x21 /* Extended byte 18 */
64#define R_EB19 0x22 /* Extended byte 19 */
65#define R_EB20 0x23 /* Extended byte 20 */
66#define R_EB21 0x24 /* Extended byte 21 */
67#define R_EB22 0x25 /* Extended byte 22 */
68#define R_EB23 0x26 /* Extended byte 23 */
69
70#define TDA18271_NUM_REGS 39
71
72/*---------------------------------------------------------------------*/
73
74struct tda18271_rf_tracking_filter_cal {
75 u32 rfmax;
76 u8 rfband;
77 u32 rf1_def;
78 u32 rf2_def;
79 u32 rf3_def;
80 u32 rf1;
81 u32 rf2;
82 u32 rf3;
83 s32 rf_a1;
84 s32 rf_b1;
85 s32 rf_a2;
86 s32 rf_b2;
87};
88
89enum tda18271_pll {
90 TDA18271_MAIN_PLL,
91 TDA18271_CAL_PLL,
92};
93
94struct tda18271_map_layout;
95
96enum tda18271_ver {
97 TDA18271HDC1,
98 TDA18271HDC2,
99};
100
101struct tda18271_priv {
102 unsigned char tda18271_regs[TDA18271_NUM_REGS];
103
104 struct list_head hybrid_tuner_instance_list;
105 struct tuner_i2c_props i2c_props;
106
107 enum tda18271_mode mode;
108 enum tda18271_role role;
109 enum tda18271_i2c_gate gate;
110 enum tda18271_ver id;
111 enum tda18271_output_options output_opt;
112 enum tda18271_small_i2c small_i2c;
113
114 unsigned int config; /* interface to saa713x / tda829x */
115 unsigned int cal_initialized:1;
116
117 u8 tm_rfcal;
118
119 struct tda18271_map_layout *maps;
120 struct tda18271_std_map std;
121 struct tda18271_rf_tracking_filter_cal rf_cal_state[8];
122
123 struct mutex lock;
124
125 u32 frequency;
126 u32 bandwidth;
127};
128
129/*---------------------------------------------------------------------*/
130
131extern int tda18271_debug;
132
133#define DBG_INFO 1
134#define DBG_MAP 2
135#define DBG_REG 4
136#define DBG_ADV 8
137#define DBG_CAL 16
138
139#define tda_printk(st, kern, fmt, arg...) do {\
140 if (st) { \
141 struct tda18271_priv *state = st; \
142 printk(kern "%s: [%d-%04x|%s] " fmt, __func__, \
143 i2c_adapter_id(state->i2c_props.adap), \
144 state->i2c_props.addr, \
145 (state->role == TDA18271_MASTER) \
146 ? "M" : "S", ##arg); \
147 } else \
148 printk(kern "%s: " fmt, __func__, ##arg); \
149} while (0)
150
151#define tda_dprintk(st, lvl, fmt, arg...) do {\
152 if (tda18271_debug & lvl) \
153 tda_printk(st, KERN_DEBUG, fmt, ##arg); } while (0)
154
155#define tda_info(fmt, arg...) printk(KERN_INFO fmt, ##arg)
156#define tda_warn(fmt, arg...) tda_printk(priv, KERN_WARNING, fmt, ##arg)
157#define tda_err(fmt, arg...) tda_printk(priv, KERN_ERR, fmt, ##arg)
158#define tda_dbg(fmt, arg...) tda_dprintk(priv, DBG_INFO, fmt, ##arg)
159#define tda_map(fmt, arg...) tda_dprintk(priv, DBG_MAP, fmt, ##arg)
160#define tda_reg(fmt, arg...) tda_dprintk(priv, DBG_REG, fmt, ##arg)
161#define tda_cal(fmt, arg...) tda_dprintk(priv, DBG_CAL, fmt, ##arg)
162
163#define tda_fail(ret) \
164({ \
165 int __ret; \
166 __ret = (ret < 0); \
167 if (__ret) \
168 tda_printk(priv, KERN_ERR, \
169 "error %d on line %d\n", ret, __LINE__); \
170 __ret; \
171})
172
173/*---------------------------------------------------------------------*/
174
175enum tda18271_map_type {
176 /* tda18271_pll_map */
177 MAIN_PLL,
178 CAL_PLL,
179 /* tda18271_map */
180 RF_CAL,
181 RF_CAL_KMCO,
182 RF_CAL_DC_OVER_DT,
183 BP_FILTER,
184 RF_BAND,
185 GAIN_TAPER,
186 IR_MEASURE,
187};
188
189extern int tda18271_lookup_pll_map(struct dvb_frontend *fe,
190 enum tda18271_map_type map_type,
191 u32 *freq, u8 *post_div, u8 *div);
192extern int tda18271_lookup_map(struct dvb_frontend *fe,
193 enum tda18271_map_type map_type,
194 u32 *freq, u8 *val);
195
196extern int tda18271_lookup_thermometer(struct dvb_frontend *fe);
197
198extern int tda18271_lookup_rf_band(struct dvb_frontend *fe,
199 u32 *freq, u8 *rf_band);
200
201extern int tda18271_lookup_cid_target(struct dvb_frontend *fe,
202 u32 *freq, u8 *cid_target,
203 u16 *count_limit);
204
205extern int tda18271_assign_map_layout(struct dvb_frontend *fe);
206
207/*---------------------------------------------------------------------*/
208
209extern int tda18271_read_regs(struct dvb_frontend *fe);
210extern int tda18271_read_extended(struct dvb_frontend *fe);
211extern int tda18271_write_regs(struct dvb_frontend *fe, int idx, int len);
212extern int tda18271_init_regs(struct dvb_frontend *fe);
213
214extern int tda18271_charge_pump_source(struct dvb_frontend *fe,
215 enum tda18271_pll pll, int force);
216extern int tda18271_set_standby_mode(struct dvb_frontend *fe,
217 int sm, int sm_lt, int sm_xt);
218
219extern int tda18271_calc_main_pll(struct dvb_frontend *fe, u32 freq);
220extern int tda18271_calc_cal_pll(struct dvb_frontend *fe, u32 freq);
221
222extern int tda18271_calc_bp_filter(struct dvb_frontend *fe, u32 *freq);
223extern int tda18271_calc_km(struct dvb_frontend *fe, u32 *freq);
224extern int tda18271_calc_rf_band(struct dvb_frontend *fe, u32 *freq);
225extern int tda18271_calc_gain_taper(struct dvb_frontend *fe, u32 *freq);
226extern int tda18271_calc_ir_measure(struct dvb_frontend *fe, u32 *freq);
227extern int tda18271_calc_rf_cal(struct dvb_frontend *fe, u32 *freq);
228
229#endif /* __TDA18271_PRIV_H__ */
230
231/*
232 * Overrides for Emacs so that we follow Linus's tabbing style.
233 * ---------------------------------------------------------------------------
234 * Local variables:
235 * c-basic-offset: 8
236 * End:
237 */
diff --git a/drivers/media/common/tuners/tda18271.h b/drivers/media/common/tuners/tda18271.h
new file mode 100644
index 00000000000..50cfa8cebb9
--- /dev/null
+++ b/drivers/media/common/tuners/tda18271.h
@@ -0,0 +1,133 @@
1/*
2 tda18271.h - header for the Philips / NXP TDA18271 silicon tuner
3
4 Copyright (C) 2007, 2008 Michael Krufky <mkrufky@linuxtv.org>
5
6 This program is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 2 of the License, or
9 (at your option) any later version.
10
11 This program is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
15
16 You should have received a copy of the GNU General Public License
17 along with this program; if not, write to the Free Software
18 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
19*/
20
21#ifndef __TDA18271_H__
22#define __TDA18271_H__
23
24#include <linux/i2c.h>
25#include "dvb_frontend.h"
26
27struct tda18271_std_map_item {
28 u16 if_freq;
29
30 /* EP3[4:3] */
31 unsigned int agc_mode:2;
32 /* EP3[2:0] */
33 unsigned int std:3;
34 /* EP4[7] */
35 unsigned int fm_rfn:1;
36 /* EP4[4:2] */
37 unsigned int if_lvl:3;
38 /* EB22[6:0] */
39 unsigned int rfagc_top:7;
40};
41
42struct tda18271_std_map {
43 struct tda18271_std_map_item fm_radio;
44 struct tda18271_std_map_item atv_b;
45 struct tda18271_std_map_item atv_dk;
46 struct tda18271_std_map_item atv_gh;
47 struct tda18271_std_map_item atv_i;
48 struct tda18271_std_map_item atv_l;
49 struct tda18271_std_map_item atv_lc;
50 struct tda18271_std_map_item atv_mn;
51 struct tda18271_std_map_item atsc_6;
52 struct tda18271_std_map_item dvbt_6;
53 struct tda18271_std_map_item dvbt_7;
54 struct tda18271_std_map_item dvbt_8;
55 struct tda18271_std_map_item qam_6;
56 struct tda18271_std_map_item qam_8;
57};
58
59enum tda18271_role {
60 TDA18271_MASTER = 0,
61 TDA18271_SLAVE,
62};
63
64enum tda18271_i2c_gate {
65 TDA18271_GATE_AUTO = 0,
66 TDA18271_GATE_ANALOG,
67 TDA18271_GATE_DIGITAL,
68};
69
70enum tda18271_output_options {
71 /* slave tuner output & loop thru & xtal oscillator always on */
72 TDA18271_OUTPUT_LT_XT_ON = 0,
73
74 /* slave tuner output loop thru off */
75 TDA18271_OUTPUT_LT_OFF = 1,
76
77 /* xtal oscillator off */
78 TDA18271_OUTPUT_XT_OFF = 2,
79};
80
81enum tda18271_small_i2c {
82 TDA18271_39_BYTE_CHUNK_INIT = 0,
83 TDA18271_16_BYTE_CHUNK_INIT = 16,
84 TDA18271_08_BYTE_CHUNK_INIT = 8,
85 TDA18271_03_BYTE_CHUNK_INIT = 3,
86};
87
88struct tda18271_config {
89 /* override default if freq / std settings (optional) */
90 struct tda18271_std_map *std_map;
91
92 /* master / slave tuner: master uses main pll, slave uses cal pll */
93 enum tda18271_role role;
94
95 /* use i2c gate provided by analog or digital demod */
96 enum tda18271_i2c_gate gate;
97
98 /* output options that can be disabled */
99 enum tda18271_output_options output_opt;
100
101 /* some i2c providers can't write all 39 registers at once */
102 enum tda18271_small_i2c small_i2c;
103
104 /* force rf tracking filter calibration on startup */
105 unsigned int rf_cal_on_startup:1;
106
107 /* interface to saa713x / tda829x */
108 unsigned int config;
109};
110
111#define TDA18271_CALLBACK_CMD_AGC_ENABLE 0
112
113enum tda18271_mode {
114 TDA18271_ANALOG = 0,
115 TDA18271_DIGITAL,
116};
117
118#if defined(CONFIG_MEDIA_TUNER_TDA18271) || (defined(CONFIG_MEDIA_TUNER_TDA18271_MODULE) && defined(MODULE))
119extern struct dvb_frontend *tda18271_attach(struct dvb_frontend *fe, u8 addr,
120 struct i2c_adapter *i2c,
121 struct tda18271_config *cfg);
122#else
123static inline struct dvb_frontend *tda18271_attach(struct dvb_frontend *fe,
124 u8 addr,
125 struct i2c_adapter *i2c,
126 struct tda18271_config *cfg)
127{
128 printk(KERN_WARNING "%s: driver disabled by Kconfig\n", __func__);
129 return NULL;
130}
131#endif
132
133#endif /* __TDA18271_H__ */
diff --git a/drivers/media/common/tuners/tda827x.c b/drivers/media/common/tuners/tda827x.c
new file mode 100644
index 00000000000..b21b6ea68b2
--- /dev/null
+++ b/drivers/media/common/tuners/tda827x.c
@@ -0,0 +1,913 @@
1/*
2 *
3 * (c) 2005 Hartmut Hackmann
4 * (c) 2007 Michael Krufky
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, write to the Free Software
18 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
19 */
20
21#include <linux/module.h>
22#include <linux/slab.h>
23#include <asm/types.h>
24#include <linux/dvb/frontend.h>
25#include <linux/videodev2.h>
26
27#include "tda827x.h"
28
29static int debug;
30module_param(debug, int, 0644);
31MODULE_PARM_DESC(debug, "Turn on/off frontend debugging (default:off).");
32
33#define dprintk(args...) \
34 do { \
35 if (debug) printk(KERN_DEBUG "tda827x: " args); \
36 } while (0)
37
38struct tda827x_priv {
39 int i2c_addr;
40 struct i2c_adapter *i2c_adap;
41 struct tda827x_config *cfg;
42
43 unsigned int sgIF;
44 unsigned char lpsel;
45
46 u32 frequency;
47 u32 bandwidth;
48};
49
50static void tda827x_set_std(struct dvb_frontend *fe,
51 struct analog_parameters *params)
52{
53 struct tda827x_priv *priv = fe->tuner_priv;
54 char *mode;
55
56 priv->lpsel = 0;
57 if (params->std & V4L2_STD_MN) {
58 priv->sgIF = 92;
59 priv->lpsel = 1;
60 mode = "MN";
61 } else if (params->std & V4L2_STD_B) {
62 priv->sgIF = 108;
63 mode = "B";
64 } else if (params->std & V4L2_STD_GH) {
65 priv->sgIF = 124;
66 mode = "GH";
67 } else if (params->std & V4L2_STD_PAL_I) {
68 priv->sgIF = 124;
69 mode = "I";
70 } else if (params->std & V4L2_STD_DK) {
71 priv->sgIF = 124;
72 mode = "DK";
73 } else if (params->std & V4L2_STD_SECAM_L) {
74 priv->sgIF = 124;
75 mode = "L";
76 } else if (params->std & V4L2_STD_SECAM_LC) {
77 priv->sgIF = 20;
78 mode = "LC";
79 } else {
80 priv->sgIF = 124;
81 mode = "xx";
82 }
83
84 if (params->mode == V4L2_TUNER_RADIO) {
85 priv->sgIF = 88; /* if frequency is 5.5 MHz */
86 dprintk("setting tda827x to radio FM\n");
87 } else
88 dprintk("setting tda827x to system %s\n", mode);
89}
90
91
92/* ------------------------------------------------------------------ */
93
94struct tda827x_data {
95 u32 lomax;
96 u8 spd;
97 u8 bs;
98 u8 bp;
99 u8 cp;
100 u8 gc3;
101 u8 div1p5;
102};
103
104static const struct tda827x_data tda827x_table[] = {
105 { .lomax = 62000000, .spd = 3, .bs = 2, .bp = 0, .cp = 0, .gc3 = 3, .div1p5 = 1},
106 { .lomax = 66000000, .spd = 3, .bs = 3, .bp = 0, .cp = 0, .gc3 = 3, .div1p5 = 1},
107 { .lomax = 76000000, .spd = 3, .bs = 1, .bp = 0, .cp = 0, .gc3 = 3, .div1p5 = 0},
108 { .lomax = 84000000, .spd = 3, .bs = 2, .bp = 0, .cp = 0, .gc3 = 3, .div1p5 = 0},
109 { .lomax = 93000000, .spd = 3, .bs = 2, .bp = 0, .cp = 0, .gc3 = 1, .div1p5 = 0},
110 { .lomax = 98000000, .spd = 3, .bs = 3, .bp = 0, .cp = 0, .gc3 = 1, .div1p5 = 0},
111 { .lomax = 109000000, .spd = 3, .bs = 3, .bp = 1, .cp = 0, .gc3 = 1, .div1p5 = 0},
112 { .lomax = 123000000, .spd = 2, .bs = 2, .bp = 1, .cp = 0, .gc3 = 1, .div1p5 = 1},
113 { .lomax = 133000000, .spd = 2, .bs = 3, .bp = 1, .cp = 0, .gc3 = 1, .div1p5 = 1},
114 { .lomax = 151000000, .spd = 2, .bs = 1, .bp = 1, .cp = 0, .gc3 = 1, .div1p5 = 0},
115 { .lomax = 154000000, .spd = 2, .bs = 2, .bp = 1, .cp = 0, .gc3 = 1, .div1p5 = 0},
116 { .lomax = 181000000, .spd = 2, .bs = 2, .bp = 1, .cp = 0, .gc3 = 0, .div1p5 = 0},
117 { .lomax = 185000000, .spd = 2, .bs = 2, .bp = 2, .cp = 0, .gc3 = 1, .div1p5 = 0},
118 { .lomax = 217000000, .spd = 2, .bs = 3, .bp = 2, .cp = 0, .gc3 = 1, .div1p5 = 0},
119 { .lomax = 244000000, .spd = 1, .bs = 2, .bp = 2, .cp = 0, .gc3 = 1, .div1p5 = 1},
120 { .lomax = 265000000, .spd = 1, .bs = 3, .bp = 2, .cp = 0, .gc3 = 1, .div1p5 = 1},
121 { .lomax = 302000000, .spd = 1, .bs = 1, .bp = 2, .cp = 0, .gc3 = 1, .div1p5 = 0},
122 { .lomax = 324000000, .spd = 1, .bs = 2, .bp = 2, .cp = 0, .gc3 = 1, .div1p5 = 0},
123 { .lomax = 370000000, .spd = 1, .bs = 2, .bp = 3, .cp = 0, .gc3 = 1, .div1p5 = 0},
124 { .lomax = 454000000, .spd = 1, .bs = 3, .bp = 3, .cp = 0, .gc3 = 1, .div1p5 = 0},
125 { .lomax = 493000000, .spd = 0, .bs = 2, .bp = 3, .cp = 0, .gc3 = 1, .div1p5 = 1},
126 { .lomax = 530000000, .spd = 0, .bs = 3, .bp = 3, .cp = 0, .gc3 = 1, .div1p5 = 1},
127 { .lomax = 554000000, .spd = 0, .bs = 1, .bp = 3, .cp = 0, .gc3 = 1, .div1p5 = 0},
128 { .lomax = 604000000, .spd = 0, .bs = 1, .bp = 4, .cp = 0, .gc3 = 0, .div1p5 = 0},
129 { .lomax = 696000000, .spd = 0, .bs = 2, .bp = 4, .cp = 0, .gc3 = 0, .div1p5 = 0},
130 { .lomax = 740000000, .spd = 0, .bs = 2, .bp = 4, .cp = 1, .gc3 = 0, .div1p5 = 0},
131 { .lomax = 820000000, .spd = 0, .bs = 3, .bp = 4, .cp = 0, .gc3 = 0, .div1p5 = 0},
132 { .lomax = 865000000, .spd = 0, .bs = 3, .bp = 4, .cp = 1, .gc3 = 0, .div1p5 = 0},
133 { .lomax = 0, .spd = 0, .bs = 0, .bp = 0, .cp = 0, .gc3 = 0, .div1p5 = 0}
134};
135
136static int tuner_transfer(struct dvb_frontend *fe,
137 struct i2c_msg *msg,
138 const int size)
139{
140 int rc;
141 struct tda827x_priv *priv = fe->tuner_priv;
142
143 if (fe->ops.i2c_gate_ctrl)
144 fe->ops.i2c_gate_ctrl(fe, 1);
145 rc = i2c_transfer(priv->i2c_adap, msg, size);
146 if (fe->ops.i2c_gate_ctrl)
147 fe->ops.i2c_gate_ctrl(fe, 0);
148
149 if (rc >= 0 && rc != size)
150 return -EIO;
151
152 return rc;
153}
154
155static int tda827xo_set_params(struct dvb_frontend *fe,
156 struct dvb_frontend_parameters *params)
157{
158 struct tda827x_priv *priv = fe->tuner_priv;
159 u8 buf[14];
160 int rc;
161
162 struct i2c_msg msg = { .addr = priv->i2c_addr, .flags = 0,
163 .buf = buf, .len = sizeof(buf) };
164 int i, tuner_freq, if_freq;
165 u32 N;
166
167 dprintk("%s:\n", __func__);
168 switch (params->u.ofdm.bandwidth) {
169 case BANDWIDTH_6_MHZ:
170 if_freq = 4000000;
171 break;
172 case BANDWIDTH_7_MHZ:
173 if_freq = 4500000;
174 break;
175 default: /* 8 MHz or Auto */
176 if_freq = 5000000;
177 break;
178 }
179 tuner_freq = params->frequency + if_freq;
180
181 i = 0;
182 while (tda827x_table[i].lomax < tuner_freq) {
183 if (tda827x_table[i + 1].lomax == 0)
184 break;
185 i++;
186 }
187
188 N = ((tuner_freq + 125000) / 250000) << (tda827x_table[i].spd + 2);
189 buf[0] = 0;
190 buf[1] = (N>>8) | 0x40;
191 buf[2] = N & 0xff;
192 buf[3] = 0;
193 buf[4] = 0x52;
194 buf[5] = (tda827x_table[i].spd << 6) + (tda827x_table[i].div1p5 << 5) +
195 (tda827x_table[i].bs << 3) +
196 tda827x_table[i].bp;
197 buf[6] = (tda827x_table[i].gc3 << 4) + 0x8f;
198 buf[7] = 0xbf;
199 buf[8] = 0x2a;
200 buf[9] = 0x05;
201 buf[10] = 0xff;
202 buf[11] = 0x00;
203 buf[12] = 0x00;
204 buf[13] = 0x40;
205
206 msg.len = 14;
207 rc = tuner_transfer(fe, &msg, 1);
208 if (rc < 0)
209 goto err;
210
211 msleep(500);
212 /* correct CP value */
213 buf[0] = 0x30;
214 buf[1] = 0x50 + tda827x_table[i].cp;
215 msg.len = 2;
216
217 rc = tuner_transfer(fe, &msg, 1);
218 if (rc < 0)
219 goto err;
220
221 priv->frequency = params->frequency;
222 priv->bandwidth = (fe->ops.info.type == FE_OFDM) ? params->u.ofdm.bandwidth : 0;
223
224 return 0;
225
226err:
227 printk(KERN_ERR "%s: could not write to tuner at addr: 0x%02x\n",
228 __func__, priv->i2c_addr << 1);
229 return rc;
230}
231
232static int tda827xo_sleep(struct dvb_frontend *fe)
233{
234 struct tda827x_priv *priv = fe->tuner_priv;
235 static u8 buf[] = { 0x30, 0xd0 };
236 struct i2c_msg msg = { .addr = priv->i2c_addr, .flags = 0,
237 .buf = buf, .len = sizeof(buf) };
238
239 dprintk("%s:\n", __func__);
240 tuner_transfer(fe, &msg, 1);
241
242 if (priv->cfg && priv->cfg->sleep)
243 priv->cfg->sleep(fe);
244
245 return 0;
246}
247
248/* ------------------------------------------------------------------ */
249
250static int tda827xo_set_analog_params(struct dvb_frontend *fe,
251 struct analog_parameters *params)
252{
253 unsigned char tuner_reg[8];
254 unsigned char reg2[2];
255 u32 N;
256 int i;
257 struct tda827x_priv *priv = fe->tuner_priv;
258 struct i2c_msg msg = { .addr = priv->i2c_addr, .flags = 0 };
259 unsigned int freq = params->frequency;
260
261 tda827x_set_std(fe, params);
262
263 if (params->mode == V4L2_TUNER_RADIO)
264 freq = freq / 1000;
265
266 N = freq + priv->sgIF;
267
268 i = 0;
269 while (tda827x_table[i].lomax < N * 62500) {
270 if (tda827x_table[i + 1].lomax == 0)
271 break;
272 i++;
273 }
274
275 N = N << tda827x_table[i].spd;
276
277 tuner_reg[0] = 0;
278 tuner_reg[1] = (unsigned char)(N>>8);
279 tuner_reg[2] = (unsigned char) N;
280 tuner_reg[3] = 0x40;
281 tuner_reg[4] = 0x52 + (priv->lpsel << 5);
282 tuner_reg[5] = (tda827x_table[i].spd << 6) +
283 (tda827x_table[i].div1p5 << 5) +
284 (tda827x_table[i].bs << 3) + tda827x_table[i].bp;
285 tuner_reg[6] = 0x8f + (tda827x_table[i].gc3 << 4);
286 tuner_reg[7] = 0x8f;
287
288 msg.buf = tuner_reg;
289 msg.len = 8;
290 tuner_transfer(fe, &msg, 1);
291
292 msg.buf = reg2;
293 msg.len = 2;
294 reg2[0] = 0x80;
295 reg2[1] = 0;
296 tuner_transfer(fe, &msg, 1);
297
298 reg2[0] = 0x60;
299 reg2[1] = 0xbf;
300 tuner_transfer(fe, &msg, 1);
301
302 reg2[0] = 0x30;
303 reg2[1] = tuner_reg[4] + 0x80;
304 tuner_transfer(fe, &msg, 1);
305
306 msleep(1);
307 reg2[0] = 0x30;
308 reg2[1] = tuner_reg[4] + 4;
309 tuner_transfer(fe, &msg, 1);
310
311 msleep(1);
312 reg2[0] = 0x30;
313 reg2[1] = tuner_reg[4];
314 tuner_transfer(fe, &msg, 1);
315
316 msleep(550);
317 reg2[0] = 0x30;
318 reg2[1] = (tuner_reg[4] & 0xfc) + tda827x_table[i].cp;
319 tuner_transfer(fe, &msg, 1);
320
321 reg2[0] = 0x60;
322 reg2[1] = 0x3f;
323 tuner_transfer(fe, &msg, 1);
324
325 reg2[0] = 0x80;
326 reg2[1] = 0x08; /* Vsync en */
327 tuner_transfer(fe, &msg, 1);
328
329 priv->frequency = params->frequency;
330
331 return 0;
332}
333
334static void tda827xo_agcf(struct dvb_frontend *fe)
335{
336 struct tda827x_priv *priv = fe->tuner_priv;
337 unsigned char data[] = { 0x80, 0x0c };
338 struct i2c_msg msg = { .addr = priv->i2c_addr, .flags = 0,
339 .buf = data, .len = 2};
340
341 tuner_transfer(fe, &msg, 1);
342}
343
344/* ------------------------------------------------------------------ */
345
346struct tda827xa_data {
347 u32 lomax;
348 u8 svco;
349 u8 spd;
350 u8 scr;
351 u8 sbs;
352 u8 gc3;
353};
354
355static struct tda827xa_data tda827xa_dvbt[] = {
356 { .lomax = 56875000, .svco = 3, .spd = 4, .scr = 0, .sbs = 0, .gc3 = 1},
357 { .lomax = 67250000, .svco = 0, .spd = 3, .scr = 0, .sbs = 0, .gc3 = 1},
358 { .lomax = 81250000, .svco = 1, .spd = 3, .scr = 0, .sbs = 0, .gc3 = 1},
359 { .lomax = 97500000, .svco = 2, .spd = 3, .scr = 0, .sbs = 0, .gc3 = 1},
360 { .lomax = 113750000, .svco = 3, .spd = 3, .scr = 0, .sbs = 1, .gc3 = 1},
361 { .lomax = 134500000, .svco = 0, .spd = 2, .scr = 0, .sbs = 1, .gc3 = 1},
362 { .lomax = 154000000, .svco = 1, .spd = 2, .scr = 0, .sbs = 1, .gc3 = 1},
363 { .lomax = 162500000, .svco = 1, .spd = 2, .scr = 0, .sbs = 1, .gc3 = 1},
364 { .lomax = 183000000, .svco = 2, .spd = 2, .scr = 0, .sbs = 1, .gc3 = 1},
365 { .lomax = 195000000, .svco = 2, .spd = 2, .scr = 0, .sbs = 2, .gc3 = 1},
366 { .lomax = 227500000, .svco = 3, .spd = 2, .scr = 0, .sbs = 2, .gc3 = 1},
367 { .lomax = 269000000, .svco = 0, .spd = 1, .scr = 0, .sbs = 2, .gc3 = 1},
368 { .lomax = 290000000, .svco = 1, .spd = 1, .scr = 0, .sbs = 2, .gc3 = 1},
369 { .lomax = 325000000, .svco = 1, .spd = 1, .scr = 0, .sbs = 3, .gc3 = 1},
370 { .lomax = 390000000, .svco = 2, .spd = 1, .scr = 0, .sbs = 3, .gc3 = 1},
371 { .lomax = 455000000, .svco = 3, .spd = 1, .scr = 0, .sbs = 3, .gc3 = 1},
372 { .lomax = 520000000, .svco = 0, .spd = 0, .scr = 0, .sbs = 3, .gc3 = 1},
373 { .lomax = 538000000, .svco = 0, .spd = 0, .scr = 1, .sbs = 3, .gc3 = 1},
374 { .lomax = 550000000, .svco = 1, .spd = 0, .scr = 0, .sbs = 3, .gc3 = 1},
375 { .lomax = 620000000, .svco = 1, .spd = 0, .scr = 0, .sbs = 4, .gc3 = 0},
376 { .lomax = 650000000, .svco = 1, .spd = 0, .scr = 1, .sbs = 4, .gc3 = 0},
377 { .lomax = 700000000, .svco = 2, .spd = 0, .scr = 0, .sbs = 4, .gc3 = 0},
378 { .lomax = 780000000, .svco = 2, .spd = 0, .scr = 1, .sbs = 4, .gc3 = 0},
379 { .lomax = 820000000, .svco = 3, .spd = 0, .scr = 0, .sbs = 4, .gc3 = 0},
380 { .lomax = 870000000, .svco = 3, .spd = 0, .scr = 1, .sbs = 4, .gc3 = 0},
381 { .lomax = 911000000, .svco = 3, .spd = 0, .scr = 2, .sbs = 4, .gc3 = 0},
382 { .lomax = 0, .svco = 0, .spd = 0, .scr = 0, .sbs = 0, .gc3 = 0}
383};
384
385static struct tda827xa_data tda827xa_dvbc[] = {
386 { .lomax = 50125000, .svco = 2, .spd = 4, .scr = 2, .sbs = 0, .gc3 = 3},
387 { .lomax = 58500000, .svco = 3, .spd = 4, .scr = 2, .sbs = 0, .gc3 = 3},
388 { .lomax = 69250000, .svco = 0, .spd = 3, .scr = 2, .sbs = 0, .gc3 = 3},
389 { .lomax = 83625000, .svco = 1, .spd = 3, .scr = 2, .sbs = 0, .gc3 = 3},
390 { .lomax = 97500000, .svco = 2, .spd = 3, .scr = 2, .sbs = 0, .gc3 = 3},
391 { .lomax = 100250000, .svco = 2, .spd = 3, .scr = 2, .sbs = 1, .gc3 = 1},
392 { .lomax = 117000000, .svco = 3, .spd = 3, .scr = 2, .sbs = 1, .gc3 = 1},
393 { .lomax = 138500000, .svco = 0, .spd = 2, .scr = 2, .sbs = 1, .gc3 = 1},
394 { .lomax = 167250000, .svco = 1, .spd = 2, .scr = 2, .sbs = 1, .gc3 = 1},
395 { .lomax = 187000000, .svco = 2, .spd = 2, .scr = 2, .sbs = 1, .gc3 = 1},
396 { .lomax = 200500000, .svco = 2, .spd = 2, .scr = 2, .sbs = 2, .gc3 = 1},
397 { .lomax = 234000000, .svco = 3, .spd = 2, .scr = 2, .sbs = 2, .gc3 = 3},
398 { .lomax = 277000000, .svco = 0, .spd = 1, .scr = 2, .sbs = 2, .gc3 = 3},
399 { .lomax = 325000000, .svco = 1, .spd = 1, .scr = 2, .sbs = 2, .gc3 = 1},
400 { .lomax = 334500000, .svco = 1, .spd = 1, .scr = 2, .sbs = 3, .gc3 = 3},
401 { .lomax = 401000000, .svco = 2, .spd = 1, .scr = 2, .sbs = 3, .gc3 = 3},
402 { .lomax = 468000000, .svco = 3, .spd = 1, .scr = 2, .sbs = 3, .gc3 = 1},
403 { .lomax = 535000000, .svco = 0, .spd = 0, .scr = 1, .sbs = 3, .gc3 = 1},
404 { .lomax = 554000000, .svco = 0, .spd = 0, .scr = 2, .sbs = 3, .gc3 = 1},
405 { .lomax = 638000000, .svco = 1, .spd = 0, .scr = 1, .sbs = 4, .gc3 = 1},
406 { .lomax = 669000000, .svco = 1, .spd = 0, .scr = 2, .sbs = 4, .gc3 = 1},
407 { .lomax = 720000000, .svco = 2, .spd = 0, .scr = 1, .sbs = 4, .gc3 = 1},
408 { .lomax = 802000000, .svco = 2, .spd = 0, .scr = 2, .sbs = 4, .gc3 = 1},
409 { .lomax = 835000000, .svco = 3, .spd = 0, .scr = 1, .sbs = 4, .gc3 = 1},
410 { .lomax = 885000000, .svco = 3, .spd = 0, .scr = 1, .sbs = 4, .gc3 = 1},
411 { .lomax = 911000000, .svco = 3, .spd = 0, .scr = 2, .sbs = 4, .gc3 = 1},
412 { .lomax = 0, .svco = 0, .spd = 0, .scr = 0, .sbs = 0, .gc3 = 0}
413};
414
415static struct tda827xa_data tda827xa_analog[] = {
416 { .lomax = 56875000, .svco = 3, .spd = 4, .scr = 0, .sbs = 0, .gc3 = 3},
417 { .lomax = 67250000, .svco = 0, .spd = 3, .scr = 0, .sbs = 0, .gc3 = 3},
418 { .lomax = 81250000, .svco = 1, .spd = 3, .scr = 0, .sbs = 0, .gc3 = 3},
419 { .lomax = 97500000, .svco = 2, .spd = 3, .scr = 0, .sbs = 0, .gc3 = 3},
420 { .lomax = 113750000, .svco = 3, .spd = 3, .scr = 0, .sbs = 1, .gc3 = 1},
421 { .lomax = 134500000, .svco = 0, .spd = 2, .scr = 0, .sbs = 1, .gc3 = 1},
422 { .lomax = 154000000, .svco = 1, .spd = 2, .scr = 0, .sbs = 1, .gc3 = 1},
423 { .lomax = 162500000, .svco = 1, .spd = 2, .scr = 0, .sbs = 1, .gc3 = 1},
424 { .lomax = 183000000, .svco = 2, .spd = 2, .scr = 0, .sbs = 1, .gc3 = 1},
425 { .lomax = 195000000, .svco = 2, .spd = 2, .scr = 0, .sbs = 2, .gc3 = 1},
426 { .lomax = 227500000, .svco = 3, .spd = 2, .scr = 0, .sbs = 2, .gc3 = 3},
427 { .lomax = 269000000, .svco = 0, .spd = 1, .scr = 0, .sbs = 2, .gc3 = 3},
428 { .lomax = 325000000, .svco = 1, .spd = 1, .scr = 0, .sbs = 2, .gc3 = 1},
429 { .lomax = 390000000, .svco = 2, .spd = 1, .scr = 0, .sbs = 3, .gc3 = 3},
430 { .lomax = 455000000, .svco = 3, .spd = 1, .scr = 0, .sbs = 3, .gc3 = 3},
431 { .lomax = 520000000, .svco = 0, .spd = 0, .scr = 0, .sbs = 3, .gc3 = 1},
432 { .lomax = 538000000, .svco = 0, .spd = 0, .scr = 1, .sbs = 3, .gc3 = 1},
433 { .lomax = 554000000, .svco = 1, .spd = 0, .scr = 0, .sbs = 3, .gc3 = 1},
434 { .lomax = 620000000, .svco = 1, .spd = 0, .scr = 0, .sbs = 4, .gc3 = 0},
435 { .lomax = 650000000, .svco = 1, .spd = 0, .scr = 1, .sbs = 4, .gc3 = 0},
436 { .lomax = 700000000, .svco = 2, .spd = 0, .scr = 0, .sbs = 4, .gc3 = 0},
437 { .lomax = 780000000, .svco = 2, .spd = 0, .scr = 1, .sbs = 4, .gc3 = 0},
438 { .lomax = 820000000, .svco = 3, .spd = 0, .scr = 0, .sbs = 4, .gc3 = 0},
439 { .lomax = 870000000, .svco = 3, .spd = 0, .scr = 1, .sbs = 4, .gc3 = 0},
440 { .lomax = 911000000, .svco = 3, .spd = 0, .scr = 2, .sbs = 4, .gc3 = 0},
441 { .lomax = 0, .svco = 0, .spd = 0, .scr = 0, .sbs = 0, .gc3 = 0}
442};
443
444static int tda827xa_sleep(struct dvb_frontend *fe)
445{
446 struct tda827x_priv *priv = fe->tuner_priv;
447 static u8 buf[] = { 0x30, 0x90 };
448 struct i2c_msg msg = { .addr = priv->i2c_addr, .flags = 0,
449 .buf = buf, .len = sizeof(buf) };
450
451 dprintk("%s:\n", __func__);
452
453 tuner_transfer(fe, &msg, 1);
454
455 if (priv->cfg && priv->cfg->sleep)
456 priv->cfg->sleep(fe);
457
458 return 0;
459}
460
461static void tda827xa_lna_gain(struct dvb_frontend *fe, int high,
462 struct analog_parameters *params)
463{
464 struct tda827x_priv *priv = fe->tuner_priv;
465 unsigned char buf[] = {0x22, 0x01};
466 int arg;
467 int gp_func;
468 struct i2c_msg msg = { .flags = 0, .buf = buf, .len = sizeof(buf) };
469
470 if (NULL == priv->cfg) {
471 dprintk("tda827x_config not defined, cannot set LNA gain!\n");
472 return;
473 }
474 msg.addr = priv->cfg->switch_addr;
475 if (priv->cfg->config) {
476 if (high)
477 dprintk("setting LNA to high gain\n");
478 else
479 dprintk("setting LNA to low gain\n");
480 }
481 switch (priv->cfg->config) {
482 case 0: /* no LNA */
483 break;
484 case 1: /* switch is GPIO 0 of tda8290 */
485 case 2:
486 if (params == NULL) {
487 gp_func = 0;
488 arg = 0;
489 } else {
490 /* turn Vsync on */
491 gp_func = 1;
492 if (params->std & V4L2_STD_MN)
493 arg = 1;
494 else
495 arg = 0;
496 }
497 if (fe->callback)
498 fe->callback(priv->i2c_adap->algo_data,
499 DVB_FRONTEND_COMPONENT_TUNER,
500 gp_func, arg);
501 buf[1] = high ? 0 : 1;
502 if (priv->cfg->config == 2)
503 buf[1] = high ? 1 : 0;
504 tuner_transfer(fe, &msg, 1);
505 break;
506 case 3: /* switch with GPIO of saa713x */
507 if (fe->callback)
508 fe->callback(priv->i2c_adap->algo_data,
509 DVB_FRONTEND_COMPONENT_TUNER, 0, high);
510 break;
511 }
512}
513
514static int tda827xa_set_params(struct dvb_frontend *fe,
515 struct dvb_frontend_parameters *params)
516{
517 struct tda827x_priv *priv = fe->tuner_priv;
518 struct tda827xa_data *frequency_map = tda827xa_dvbt;
519 u8 buf[11];
520
521 struct i2c_msg msg = { .addr = priv->i2c_addr, .flags = 0,
522 .buf = buf, .len = sizeof(buf) };
523
524 int i, tuner_freq, if_freq, rc;
525 u32 N;
526
527 dprintk("%s:\n", __func__);
528
529 tda827xa_lna_gain(fe, 1, NULL);
530 msleep(20);
531
532 switch (params->u.ofdm.bandwidth) {
533 case BANDWIDTH_6_MHZ:
534 if_freq = 4000000;
535 break;
536 case BANDWIDTH_7_MHZ:
537 if_freq = 4500000;
538 break;
539 default: /* 8 MHz or Auto */
540 if_freq = 5000000;
541 break;
542 }
543 tuner_freq = params->frequency + if_freq;
544
545 if (fe->ops.info.type == FE_QAM) {
546 dprintk("%s select tda827xa_dvbc\n", __func__);
547 frequency_map = tda827xa_dvbc;
548 }
549
550 i = 0;
551 while (frequency_map[i].lomax < tuner_freq) {
552 if (frequency_map[i + 1].lomax == 0)
553 break;
554 i++;
555 }
556
557 N = ((tuner_freq + 31250) / 62500) << frequency_map[i].spd;
558 buf[0] = 0; // subaddress
559 buf[1] = N >> 8;
560 buf[2] = N & 0xff;
561 buf[3] = 0;
562 buf[4] = 0x16;
563 buf[5] = (frequency_map[i].spd << 5) + (frequency_map[i].svco << 3) +
564 frequency_map[i].sbs;
565 buf[6] = 0x4b + (frequency_map[i].gc3 << 4);
566 buf[7] = 0x1c;
567 buf[8] = 0x06;
568 buf[9] = 0x24;
569 buf[10] = 0x00;
570 msg.len = 11;
571 rc = tuner_transfer(fe, &msg, 1);
572 if (rc < 0)
573 goto err;
574
575 buf[0] = 0x90;
576 buf[1] = 0xff;
577 buf[2] = 0x60;
578 buf[3] = 0x00;
579 buf[4] = 0x59; // lpsel, for 6MHz + 2
580 msg.len = 5;
581 rc = tuner_transfer(fe, &msg, 1);
582 if (rc < 0)
583 goto err;
584
585 buf[0] = 0xa0;
586 buf[1] = 0x40;
587 msg.len = 2;
588 rc = tuner_transfer(fe, &msg, 1);
589 if (rc < 0)
590 goto err;
591
592 msleep(11);
593 msg.flags = I2C_M_RD;
594 rc = tuner_transfer(fe, &msg, 1);
595 if (rc < 0)
596 goto err;
597 msg.flags = 0;
598
599 buf[1] >>= 4;
600 dprintk("tda8275a AGC2 gain is: %d\n", buf[1]);
601 if ((buf[1]) < 2) {
602 tda827xa_lna_gain(fe, 0, NULL);
603 buf[0] = 0x60;
604 buf[1] = 0x0c;
605 rc = tuner_transfer(fe, &msg, 1);
606 if (rc < 0)
607 goto err;
608 }
609
610 buf[0] = 0xc0;
611 buf[1] = 0x99; // lpsel, for 6MHz + 2
612 rc = tuner_transfer(fe, &msg, 1);
613 if (rc < 0)
614 goto err;
615
616 buf[0] = 0x60;
617 buf[1] = 0x3c;
618 rc = tuner_transfer(fe, &msg, 1);
619 if (rc < 0)
620 goto err;
621
622 /* correct CP value */
623 buf[0] = 0x30;
624 buf[1] = 0x10 + frequency_map[i].scr;
625 rc = tuner_transfer(fe, &msg, 1);
626 if (rc < 0)
627 goto err;
628
629 msleep(163);
630 buf[0] = 0xc0;
631 buf[1] = 0x39; // lpsel, for 6MHz + 2
632 rc = tuner_transfer(fe, &msg, 1);
633 if (rc < 0)
634 goto err;
635
636 msleep(3);
637 /* freeze AGC1 */
638 buf[0] = 0x50;
639 buf[1] = 0x4f + (frequency_map[i].gc3 << 4);
640 rc = tuner_transfer(fe, &msg, 1);
641 if (rc < 0)
642 goto err;
643
644 priv->frequency = params->frequency;
645 priv->bandwidth = (fe->ops.info.type == FE_OFDM) ? params->u.ofdm.bandwidth : 0;
646
647
648 return 0;
649
650err:
651 printk(KERN_ERR "%s: could not write to tuner at addr: 0x%02x\n",
652 __func__, priv->i2c_addr << 1);
653 return rc;
654}
655
656
657static int tda827xa_set_analog_params(struct dvb_frontend *fe,
658 struct analog_parameters *params)
659{
660 unsigned char tuner_reg[11];
661 u32 N;
662 int i;
663 struct tda827x_priv *priv = fe->tuner_priv;
664 struct i2c_msg msg = { .addr = priv->i2c_addr, .flags = 0,
665 .buf = tuner_reg, .len = sizeof(tuner_reg) };
666 unsigned int freq = params->frequency;
667
668 tda827x_set_std(fe, params);
669
670 tda827xa_lna_gain(fe, 1, params);
671 msleep(10);
672
673 if (params->mode == V4L2_TUNER_RADIO)
674 freq = freq / 1000;
675
676 N = freq + priv->sgIF;
677
678 i = 0;
679 while (tda827xa_analog[i].lomax < N * 62500) {
680 if (tda827xa_analog[i + 1].lomax == 0)
681 break;
682 i++;
683 }
684
685 N = N << tda827xa_analog[i].spd;
686
687 tuner_reg[0] = 0;
688 tuner_reg[1] = (unsigned char)(N>>8);
689 tuner_reg[2] = (unsigned char) N;
690 tuner_reg[3] = 0;
691 tuner_reg[4] = 0x16;
692 tuner_reg[5] = (tda827xa_analog[i].spd << 5) +
693 (tda827xa_analog[i].svco << 3) +
694 tda827xa_analog[i].sbs;
695 tuner_reg[6] = 0x8b + (tda827xa_analog[i].gc3 << 4);
696 tuner_reg[7] = 0x1c;
697 tuner_reg[8] = 4;
698 tuner_reg[9] = 0x20;
699 tuner_reg[10] = 0x00;
700 msg.len = 11;
701 tuner_transfer(fe, &msg, 1);
702
703 tuner_reg[0] = 0x90;
704 tuner_reg[1] = 0xff;
705 tuner_reg[2] = 0xe0;
706 tuner_reg[3] = 0;
707 tuner_reg[4] = 0x99 + (priv->lpsel << 1);
708 msg.len = 5;
709 tuner_transfer(fe, &msg, 1);
710
711 tuner_reg[0] = 0xa0;
712 tuner_reg[1] = 0xc0;
713 msg.len = 2;
714 tuner_transfer(fe, &msg, 1);
715
716 tuner_reg[0] = 0x30;
717 tuner_reg[1] = 0x10 + tda827xa_analog[i].scr;
718 tuner_transfer(fe, &msg, 1);
719
720 msg.flags = I2C_M_RD;
721 tuner_transfer(fe, &msg, 1);
722 msg.flags = 0;
723 tuner_reg[1] >>= 4;
724 dprintk("AGC2 gain is: %d\n", tuner_reg[1]);
725 if (tuner_reg[1] < 1)
726 tda827xa_lna_gain(fe, 0, params);
727
728 msleep(100);
729 tuner_reg[0] = 0x60;
730 tuner_reg[1] = 0x3c;
731 tuner_transfer(fe, &msg, 1);
732
733 msleep(163);
734 tuner_reg[0] = 0x50;
735 tuner_reg[1] = 0x8f + (tda827xa_analog[i].gc3 << 4);
736 tuner_transfer(fe, &msg, 1);
737
738 tuner_reg[0] = 0x80;
739 tuner_reg[1] = 0x28;
740 tuner_transfer(fe, &msg, 1);
741
742 tuner_reg[0] = 0xb0;
743 tuner_reg[1] = 0x01;
744 tuner_transfer(fe, &msg, 1);
745
746 tuner_reg[0] = 0xc0;
747 tuner_reg[1] = 0x19 + (priv->lpsel << 1);
748 tuner_transfer(fe, &msg, 1);
749
750 priv->frequency = params->frequency;
751
752 return 0;
753}
754
755static void tda827xa_agcf(struct dvb_frontend *fe)
756{
757 struct tda827x_priv *priv = fe->tuner_priv;
758 unsigned char data[] = {0x80, 0x2c};
759 struct i2c_msg msg = {.addr = priv->i2c_addr, .flags = 0,
760 .buf = data, .len = 2};
761 tuner_transfer(fe, &msg, 1);
762}
763
764/* ------------------------------------------------------------------ */
765
766static int tda827x_release(struct dvb_frontend *fe)
767{
768 kfree(fe->tuner_priv);
769 fe->tuner_priv = NULL;
770 return 0;
771}
772
773static int tda827x_get_frequency(struct dvb_frontend *fe, u32 *frequency)
774{
775 struct tda827x_priv *priv = fe->tuner_priv;
776 *frequency = priv->frequency;
777 return 0;
778}
779
780static int tda827x_get_bandwidth(struct dvb_frontend *fe, u32 *bandwidth)
781{
782 struct tda827x_priv *priv = fe->tuner_priv;
783 *bandwidth = priv->bandwidth;
784 return 0;
785}
786
787static int tda827x_init(struct dvb_frontend *fe)
788{
789 struct tda827x_priv *priv = fe->tuner_priv;
790 dprintk("%s:\n", __func__);
791 if (priv->cfg && priv->cfg->init)
792 priv->cfg->init(fe);
793
794 return 0;
795}
796
797static int tda827x_probe_version(struct dvb_frontend *fe);
798
799static int tda827x_initial_init(struct dvb_frontend *fe)
800{
801 int ret;
802 ret = tda827x_probe_version(fe);
803 if (ret)
804 return ret;
805 return fe->ops.tuner_ops.init(fe);
806}
807
808static int tda827x_initial_sleep(struct dvb_frontend *fe)
809{
810 int ret;
811 ret = tda827x_probe_version(fe);
812 if (ret)
813 return ret;
814 return fe->ops.tuner_ops.sleep(fe);
815}
816
817static struct dvb_tuner_ops tda827xo_tuner_ops = {
818 .info = {
819 .name = "Philips TDA827X",
820 .frequency_min = 55000000,
821 .frequency_max = 860000000,
822 .frequency_step = 250000
823 },
824 .release = tda827x_release,
825 .init = tda827x_initial_init,
826 .sleep = tda827x_initial_sleep,
827 .set_params = tda827xo_set_params,
828 .set_analog_params = tda827xo_set_analog_params,
829 .get_frequency = tda827x_get_frequency,
830 .get_bandwidth = tda827x_get_bandwidth,
831};
832
833static struct dvb_tuner_ops tda827xa_tuner_ops = {
834 .info = {
835 .name = "Philips TDA827XA",
836 .frequency_min = 44000000,
837 .frequency_max = 906000000,
838 .frequency_step = 62500
839 },
840 .release = tda827x_release,
841 .init = tda827x_init,
842 .sleep = tda827xa_sleep,
843 .set_params = tda827xa_set_params,
844 .set_analog_params = tda827xa_set_analog_params,
845 .get_frequency = tda827x_get_frequency,
846 .get_bandwidth = tda827x_get_bandwidth,
847};
848
849static int tda827x_probe_version(struct dvb_frontend *fe)
850{
851 u8 data;
852 int rc;
853 struct tda827x_priv *priv = fe->tuner_priv;
854 struct i2c_msg msg = { .addr = priv->i2c_addr, .flags = I2C_M_RD,
855 .buf = &data, .len = 1 };
856
857 rc = tuner_transfer(fe, &msg, 1);
858
859 if (rc < 0) {
860 printk("%s: could not read from tuner at addr: 0x%02x\n",
861 __func__, msg.addr << 1);
862 return rc;
863 }
864 if ((data & 0x3c) == 0) {
865 dprintk("tda827x tuner found\n");
866 fe->ops.tuner_ops.init = tda827x_init;
867 fe->ops.tuner_ops.sleep = tda827xo_sleep;
868 if (priv->cfg)
869 priv->cfg->agcf = tda827xo_agcf;
870 } else {
871 dprintk("tda827xa tuner found\n");
872 memcpy(&fe->ops.tuner_ops, &tda827xa_tuner_ops, sizeof(struct dvb_tuner_ops));
873 if (priv->cfg)
874 priv->cfg->agcf = tda827xa_agcf;
875 }
876 return 0;
877}
878
879struct dvb_frontend *tda827x_attach(struct dvb_frontend *fe, int addr,
880 struct i2c_adapter *i2c,
881 struct tda827x_config *cfg)
882{
883 struct tda827x_priv *priv = NULL;
884
885 dprintk("%s:\n", __func__);
886 priv = kzalloc(sizeof(struct tda827x_priv), GFP_KERNEL);
887 if (priv == NULL)
888 return NULL;
889
890 priv->i2c_addr = addr;
891 priv->i2c_adap = i2c;
892 priv->cfg = cfg;
893 memcpy(&fe->ops.tuner_ops, &tda827xo_tuner_ops, sizeof(struct dvb_tuner_ops));
894 fe->tuner_priv = priv;
895
896 dprintk("type set to %s\n", fe->ops.tuner_ops.info.name);
897
898 return fe;
899}
900EXPORT_SYMBOL_GPL(tda827x_attach);
901
902MODULE_DESCRIPTION("DVB TDA827x driver");
903MODULE_AUTHOR("Hartmut Hackmann <hartmut.hackmann@t-online.de>");
904MODULE_AUTHOR("Michael Krufky <mkrufky@linuxtv.org>");
905MODULE_LICENSE("GPL");
906
907/*
908 * Overrides for Emacs so that we follow Linus's tabbing style.
909 * ---------------------------------------------------------------------------
910 * Local variables:
911 * c-basic-offset: 8
912 * End:
913 */
diff --git a/drivers/media/common/tuners/tda827x.h b/drivers/media/common/tuners/tda827x.h
new file mode 100644
index 00000000000..7d72ce0a0c2
--- /dev/null
+++ b/drivers/media/common/tuners/tda827x.h
@@ -0,0 +1,68 @@
1 /*
2 DVB Driver for Philips tda827x / tda827xa Silicon tuners
3
4 (c) 2005 Hartmut Hackmann
5 (c) 2007 Michael Krufky
6
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2 of the License, or
10 (at your option) any later version.
11
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15
16 GNU General Public License for more details.
17
18 You should have received a copy of the GNU General Public License
19 along with this program; if not, write to the Free Software
20 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
21
22 */
23
24#ifndef __DVB_TDA827X_H__
25#define __DVB_TDA827X_H__
26
27#include <linux/i2c.h>
28#include "dvb_frontend.h"
29
30struct tda827x_config
31{
32 /* saa7134 - provided callbacks */
33 int (*init) (struct dvb_frontend *fe);
34 int (*sleep) (struct dvb_frontend *fe);
35
36 /* interface to tda829x driver */
37 unsigned int config;
38 int switch_addr;
39
40 void (*agcf)(struct dvb_frontend *fe);
41};
42
43
44/**
45 * Attach a tda827x tuner to the supplied frontend structure.
46 *
47 * @param fe Frontend to attach to.
48 * @param addr i2c address of the tuner.
49 * @param i2c i2c adapter to use.
50 * @param cfg optional callback function pointers.
51 * @return FE pointer on success, NULL on failure.
52 */
53#if defined(CONFIG_MEDIA_TUNER_TDA827X) || (defined(CONFIG_MEDIA_TUNER_TDA827X_MODULE) && defined(MODULE))
54extern struct dvb_frontend* tda827x_attach(struct dvb_frontend *fe, int addr,
55 struct i2c_adapter *i2c,
56 struct tda827x_config *cfg);
57#else
58static inline struct dvb_frontend* tda827x_attach(struct dvb_frontend *fe,
59 int addr,
60 struct i2c_adapter *i2c,
61 struct tda827x_config *cfg)
62{
63 printk(KERN_WARNING "%s: driver disabled by Kconfig\n", __func__);
64 return NULL;
65}
66#endif // CONFIG_MEDIA_TUNER_TDA827X
67
68#endif // __DVB_TDA827X_H__
diff --git a/drivers/media/common/tuners/tda8290.c b/drivers/media/common/tuners/tda8290.c
new file mode 100644
index 00000000000..8c4852114ee
--- /dev/null
+++ b/drivers/media/common/tuners/tda8290.c
@@ -0,0 +1,874 @@
1/*
2
3 i2c tv tuner chip device driver
4 controls the philips tda8290+75 tuner chip combo.
5
6 This program is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 2 of the License, or
9 (at your option) any later version.
10
11 This program is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
15
16 You should have received a copy of the GNU General Public License
17 along with this program; if not, write to the Free Software
18 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
19
20 This "tda8290" module was split apart from the original "tuner" module.
21*/
22
23#include <linux/i2c.h>
24#include <linux/slab.h>
25#include <linux/delay.h>
26#include <linux/videodev2.h>
27#include "tuner-i2c.h"
28#include "tda8290.h"
29#include "tda827x.h"
30#include "tda18271.h"
31
32static int debug;
33module_param(debug, int, 0644);
34MODULE_PARM_DESC(debug, "enable verbose debug messages");
35
36static int deemphasis_50;
37module_param(deemphasis_50, int, 0644);
38MODULE_PARM_DESC(deemphasis_50, "0 - 75us deemphasis; 1 - 50us deemphasis");
39
40/* ---------------------------------------------------------------------- */
41
42struct tda8290_priv {
43 struct tuner_i2c_props i2c_props;
44
45 unsigned char tda8290_easy_mode;
46
47 unsigned char tda827x_addr;
48
49 unsigned char ver;
50#define TDA8290 1
51#define TDA8295 2
52#define TDA8275 4
53#define TDA8275A 8
54#define TDA18271 16
55
56 struct tda827x_config cfg;
57};
58
59/*---------------------------------------------------------------------*/
60
61static int tda8290_i2c_bridge(struct dvb_frontend *fe, int close)
62{
63 struct tda8290_priv *priv = fe->analog_demod_priv;
64
65 unsigned char enable[2] = { 0x21, 0xC0 };
66 unsigned char disable[2] = { 0x21, 0x00 };
67 unsigned char *msg;
68
69 if (close) {
70 msg = enable;
71 tuner_i2c_xfer_send(&priv->i2c_props, msg, 2);
72 /* let the bridge stabilize */
73 msleep(20);
74 } else {
75 msg = disable;
76 tuner_i2c_xfer_send(&priv->i2c_props, msg, 2);
77 }
78
79 return 0;
80}
81
82static int tda8295_i2c_bridge(struct dvb_frontend *fe, int close)
83{
84 struct tda8290_priv *priv = fe->analog_demod_priv;
85
86 unsigned char enable[2] = { 0x45, 0xc1 };
87 unsigned char disable[2] = { 0x46, 0x00 };
88 unsigned char buf[3] = { 0x45, 0x01, 0x00 };
89 unsigned char *msg;
90
91 if (close) {
92 msg = enable;
93 tuner_i2c_xfer_send(&priv->i2c_props, msg, 2);
94 /* let the bridge stabilize */
95 msleep(20);
96 } else {
97 msg = disable;
98 tuner_i2c_xfer_send_recv(&priv->i2c_props, msg, 1, &msg[1], 1);
99
100 buf[2] = msg[1];
101 buf[2] &= ~0x04;
102 tuner_i2c_xfer_send(&priv->i2c_props, buf, 3);
103 msleep(5);
104
105 msg[1] |= 0x04;
106 tuner_i2c_xfer_send(&priv->i2c_props, msg, 2);
107 }
108
109 return 0;
110}
111
112/*---------------------------------------------------------------------*/
113
114static void set_audio(struct dvb_frontend *fe,
115 struct analog_parameters *params)
116{
117 struct tda8290_priv *priv = fe->analog_demod_priv;
118 char* mode;
119
120 if (params->std & V4L2_STD_MN) {
121 priv->tda8290_easy_mode = 0x01;
122 mode = "MN";
123 } else if (params->std & V4L2_STD_B) {
124 priv->tda8290_easy_mode = 0x02;
125 mode = "B";
126 } else if (params->std & V4L2_STD_GH) {
127 priv->tda8290_easy_mode = 0x04;
128 mode = "GH";
129 } else if (params->std & V4L2_STD_PAL_I) {
130 priv->tda8290_easy_mode = 0x08;
131 mode = "I";
132 } else if (params->std & V4L2_STD_DK) {
133 priv->tda8290_easy_mode = 0x10;
134 mode = "DK";
135 } else if (params->std & V4L2_STD_SECAM_L) {
136 priv->tda8290_easy_mode = 0x20;
137 mode = "L";
138 } else if (params->std & V4L2_STD_SECAM_LC) {
139 priv->tda8290_easy_mode = 0x40;
140 mode = "LC";
141 } else {
142 priv->tda8290_easy_mode = 0x10;
143 mode = "xx";
144 }
145
146 if (params->mode == V4L2_TUNER_RADIO) {
147 /* Set TDA8295 to FM radio; Start TDA8290 with MN values */
148 priv->tda8290_easy_mode = (priv->ver & TDA8295) ? 0x80 : 0x01;
149 tuner_dbg("setting to radio FM\n");
150 } else {
151 tuner_dbg("setting tda829x to system %s\n", mode);
152 }
153}
154
155static struct {
156 unsigned char seq[2];
157} fm_mode[] = {
158 { { 0x01, 0x81} }, /* Put device into expert mode */
159 { { 0x03, 0x48} }, /* Disable NOTCH and VIDEO filters */
160 { { 0x04, 0x04} }, /* Disable color carrier filter (SSIF) */
161 { { 0x05, 0x04} }, /* ADC headroom */
162 { { 0x06, 0x10} }, /* group delay flat */
163
164 { { 0x07, 0x00} }, /* use the same radio DTO values as a tda8295 */
165 { { 0x08, 0x00} },
166 { { 0x09, 0x80} },
167 { { 0x0a, 0xda} },
168 { { 0x0b, 0x4b} },
169 { { 0x0c, 0x68} },
170
171 { { 0x0d, 0x00} }, /* PLL off, no video carrier detect */
172 { { 0x14, 0x00} }, /* disable auto mute if no video */
173};
174
175static void tda8290_set_params(struct dvb_frontend *fe,
176 struct analog_parameters *params)
177{
178 struct tda8290_priv *priv = fe->analog_demod_priv;
179
180 unsigned char soft_reset[] = { 0x00, 0x00 };
181 unsigned char easy_mode[] = { 0x01, priv->tda8290_easy_mode };
182 unsigned char expert_mode[] = { 0x01, 0x80 };
183 unsigned char agc_out_on[] = { 0x02, 0x00 };
184 unsigned char gainset_off[] = { 0x28, 0x14 };
185 unsigned char if_agc_spd[] = { 0x0f, 0x88 };
186 unsigned char adc_head_6[] = { 0x05, 0x04 };
187 unsigned char adc_head_9[] = { 0x05, 0x02 };
188 unsigned char adc_head_12[] = { 0x05, 0x01 };
189 unsigned char pll_bw_nom[] = { 0x0d, 0x47 };
190 unsigned char pll_bw_low[] = { 0x0d, 0x27 };
191 unsigned char gainset_2[] = { 0x28, 0x64 };
192 unsigned char agc_rst_on[] = { 0x0e, 0x0b };
193 unsigned char agc_rst_off[] = { 0x0e, 0x09 };
194 unsigned char if_agc_set[] = { 0x0f, 0x81 };
195 unsigned char addr_adc_sat = 0x1a;
196 unsigned char addr_agc_stat = 0x1d;
197 unsigned char addr_pll_stat = 0x1b;
198 unsigned char adc_sat, agc_stat,
199 pll_stat;
200 int i;
201
202 set_audio(fe, params);
203
204 if (priv->cfg.config)
205 tuner_dbg("tda827xa config is 0x%02x\n", priv->cfg.config);
206 tuner_i2c_xfer_send(&priv->i2c_props, easy_mode, 2);
207 tuner_i2c_xfer_send(&priv->i2c_props, agc_out_on, 2);
208 tuner_i2c_xfer_send(&priv->i2c_props, soft_reset, 2);
209 msleep(1);
210
211 if (params->mode == V4L2_TUNER_RADIO) {
212 unsigned char deemphasis[] = { 0x13, 1 };
213
214 /* FIXME: allow using a different deemphasis */
215
216 if (deemphasis_50)
217 deemphasis[1] = 2;
218
219 for (i = 0; i < ARRAY_SIZE(fm_mode); i++)
220 tuner_i2c_xfer_send(&priv->i2c_props, fm_mode[i].seq, 2);
221
222 tuner_i2c_xfer_send(&priv->i2c_props, deemphasis, 2);
223 } else {
224 expert_mode[1] = priv->tda8290_easy_mode + 0x80;
225 tuner_i2c_xfer_send(&priv->i2c_props, expert_mode, 2);
226 tuner_i2c_xfer_send(&priv->i2c_props, gainset_off, 2);
227 tuner_i2c_xfer_send(&priv->i2c_props, if_agc_spd, 2);
228 if (priv->tda8290_easy_mode & 0x60)
229 tuner_i2c_xfer_send(&priv->i2c_props, adc_head_9, 2);
230 else
231 tuner_i2c_xfer_send(&priv->i2c_props, adc_head_6, 2);
232 tuner_i2c_xfer_send(&priv->i2c_props, pll_bw_nom, 2);
233 }
234
235
236 tda8290_i2c_bridge(fe, 1);
237
238 if (fe->ops.tuner_ops.set_analog_params)
239 fe->ops.tuner_ops.set_analog_params(fe, params);
240
241 for (i = 0; i < 3; i++) {
242 tuner_i2c_xfer_send_recv(&priv->i2c_props,
243 &addr_pll_stat, 1, &pll_stat, 1);
244 if (pll_stat & 0x80) {
245 tuner_i2c_xfer_send_recv(&priv->i2c_props,
246 &addr_adc_sat, 1,
247 &adc_sat, 1);
248 tuner_i2c_xfer_send_recv(&priv->i2c_props,
249 &addr_agc_stat, 1,
250 &agc_stat, 1);
251 tuner_dbg("tda8290 is locked, AGC: %d\n", agc_stat);
252 break;
253 } else {
254 tuner_dbg("tda8290 not locked, no signal?\n");
255 msleep(100);
256 }
257 }
258 /* adjust headroom resp. gain */
259 if ((agc_stat > 115) || (!(pll_stat & 0x80) && (adc_sat < 20))) {
260 tuner_dbg("adjust gain, step 1. Agc: %d, ADC stat: %d, lock: %d\n",
261 agc_stat, adc_sat, pll_stat & 0x80);
262 tuner_i2c_xfer_send(&priv->i2c_props, gainset_2, 2);
263 msleep(100);
264 tuner_i2c_xfer_send_recv(&priv->i2c_props,
265 &addr_agc_stat, 1, &agc_stat, 1);
266 tuner_i2c_xfer_send_recv(&priv->i2c_props,
267 &addr_pll_stat, 1, &pll_stat, 1);
268 if ((agc_stat > 115) || !(pll_stat & 0x80)) {
269 tuner_dbg("adjust gain, step 2. Agc: %d, lock: %d\n",
270 agc_stat, pll_stat & 0x80);
271 if (priv->cfg.agcf)
272 priv->cfg.agcf(fe);
273 msleep(100);
274 tuner_i2c_xfer_send_recv(&priv->i2c_props,
275 &addr_agc_stat, 1,
276 &agc_stat, 1);
277 tuner_i2c_xfer_send_recv(&priv->i2c_props,
278 &addr_pll_stat, 1,
279 &pll_stat, 1);
280 if((agc_stat > 115) || !(pll_stat & 0x80)) {
281 tuner_dbg("adjust gain, step 3. Agc: %d\n", agc_stat);
282 tuner_i2c_xfer_send(&priv->i2c_props, adc_head_12, 2);
283 tuner_i2c_xfer_send(&priv->i2c_props, pll_bw_low, 2);
284 msleep(100);
285 }
286 }
287 }
288
289 /* l/ l' deadlock? */
290 if(priv->tda8290_easy_mode & 0x60) {
291 tuner_i2c_xfer_send_recv(&priv->i2c_props,
292 &addr_adc_sat, 1,
293 &adc_sat, 1);
294 tuner_i2c_xfer_send_recv(&priv->i2c_props,
295 &addr_pll_stat, 1,
296 &pll_stat, 1);
297 if ((adc_sat > 20) || !(pll_stat & 0x80)) {
298 tuner_dbg("trying to resolve SECAM L deadlock\n");
299 tuner_i2c_xfer_send(&priv->i2c_props, agc_rst_on, 2);
300 msleep(40);
301 tuner_i2c_xfer_send(&priv->i2c_props, agc_rst_off, 2);
302 }
303 }
304
305 tda8290_i2c_bridge(fe, 0);
306 tuner_i2c_xfer_send(&priv->i2c_props, if_agc_set, 2);
307}
308
309/*---------------------------------------------------------------------*/
310
311static void tda8295_power(struct dvb_frontend *fe, int enable)
312{
313 struct tda8290_priv *priv = fe->analog_demod_priv;
314 unsigned char buf[] = { 0x30, 0x00 }; /* clb_stdbt */
315
316 tuner_i2c_xfer_send_recv(&priv->i2c_props, &buf[0], 1, &buf[1], 1);
317
318 if (enable)
319 buf[1] = 0x01;
320 else
321 buf[1] = 0x03;
322
323 tuner_i2c_xfer_send(&priv->i2c_props, buf, 2);
324}
325
326static void tda8295_set_easy_mode(struct dvb_frontend *fe, int enable)
327{
328 struct tda8290_priv *priv = fe->analog_demod_priv;
329 unsigned char buf[] = { 0x01, 0x00 };
330
331 tuner_i2c_xfer_send_recv(&priv->i2c_props, &buf[0], 1, &buf[1], 1);
332
333 if (enable)
334 buf[1] = 0x01; /* rising edge sets regs 0x02 - 0x23 */
335 else
336 buf[1] = 0x00; /* reset active bit */
337
338 tuner_i2c_xfer_send(&priv->i2c_props, buf, 2);
339}
340
341static void tda8295_set_video_std(struct dvb_frontend *fe)
342{
343 struct tda8290_priv *priv = fe->analog_demod_priv;
344 unsigned char buf[] = { 0x00, priv->tda8290_easy_mode };
345
346 tuner_i2c_xfer_send(&priv->i2c_props, buf, 2);
347
348 tda8295_set_easy_mode(fe, 1);
349 msleep(20);
350 tda8295_set_easy_mode(fe, 0);
351}
352
353/*---------------------------------------------------------------------*/
354
355static void tda8295_agc1_out(struct dvb_frontend *fe, int enable)
356{
357 struct tda8290_priv *priv = fe->analog_demod_priv;
358 unsigned char buf[] = { 0x02, 0x00 }; /* DIV_FUNC */
359
360 tuner_i2c_xfer_send_recv(&priv->i2c_props, &buf[0], 1, &buf[1], 1);
361
362 if (enable)
363 buf[1] &= ~0x40;
364 else
365 buf[1] |= 0x40;
366
367 tuner_i2c_xfer_send(&priv->i2c_props, buf, 2);
368}
369
370static void tda8295_agc2_out(struct dvb_frontend *fe, int enable)
371{
372 struct tda8290_priv *priv = fe->analog_demod_priv;
373 unsigned char set_gpio_cf[] = { 0x44, 0x00 };
374 unsigned char set_gpio_val[] = { 0x46, 0x00 };
375
376 tuner_i2c_xfer_send_recv(&priv->i2c_props,
377 &set_gpio_cf[0], 1, &set_gpio_cf[1], 1);
378 tuner_i2c_xfer_send_recv(&priv->i2c_props,
379 &set_gpio_val[0], 1, &set_gpio_val[1], 1);
380
381 set_gpio_cf[1] &= 0xf0; /* clear GPIO_0 bits 3-0 */
382
383 if (enable) {
384 set_gpio_cf[1] |= 0x01; /* config GPIO_0 as Open Drain Out */
385 set_gpio_val[1] &= 0xfe; /* set GPIO_0 pin low */
386 }
387 tuner_i2c_xfer_send(&priv->i2c_props, set_gpio_cf, 2);
388 tuner_i2c_xfer_send(&priv->i2c_props, set_gpio_val, 2);
389}
390
391static int tda8295_has_signal(struct dvb_frontend *fe)
392{
393 struct tda8290_priv *priv = fe->analog_demod_priv;
394
395 unsigned char hvpll_stat = 0x26;
396 unsigned char ret;
397
398 tuner_i2c_xfer_send_recv(&priv->i2c_props, &hvpll_stat, 1, &ret, 1);
399 return (ret & 0x01) ? 65535 : 0;
400}
401
402/*---------------------------------------------------------------------*/
403
404static void tda8295_set_params(struct dvb_frontend *fe,
405 struct analog_parameters *params)
406{
407 struct tda8290_priv *priv = fe->analog_demod_priv;
408
409 unsigned char blanking_mode[] = { 0x1d, 0x00 };
410
411 set_audio(fe, params);
412
413 tuner_dbg("%s: freq = %d\n", __func__, params->frequency);
414
415 tda8295_power(fe, 1);
416 tda8295_agc1_out(fe, 1);
417
418 tuner_i2c_xfer_send_recv(&priv->i2c_props,
419 &blanking_mode[0], 1, &blanking_mode[1], 1);
420
421 tda8295_set_video_std(fe);
422
423 blanking_mode[1] = 0x03;
424 tuner_i2c_xfer_send(&priv->i2c_props, blanking_mode, 2);
425 msleep(20);
426
427 tda8295_i2c_bridge(fe, 1);
428
429 if (fe->ops.tuner_ops.set_analog_params)
430 fe->ops.tuner_ops.set_analog_params(fe, params);
431
432 if (priv->cfg.agcf)
433 priv->cfg.agcf(fe);
434
435 if (tda8295_has_signal(fe))
436 tuner_dbg("tda8295 is locked\n");
437 else
438 tuner_dbg("tda8295 not locked, no signal?\n");
439
440 tda8295_i2c_bridge(fe, 0);
441}
442
443/*---------------------------------------------------------------------*/
444
445static int tda8290_has_signal(struct dvb_frontend *fe)
446{
447 struct tda8290_priv *priv = fe->analog_demod_priv;
448
449 unsigned char i2c_get_afc[1] = { 0x1B };
450 unsigned char afc = 0;
451
452 tuner_i2c_xfer_send_recv(&priv->i2c_props,
453 i2c_get_afc, ARRAY_SIZE(i2c_get_afc), &afc, 1);
454 return (afc & 0x80)? 65535:0;
455}
456
457/*---------------------------------------------------------------------*/
458
459static void tda8290_standby(struct dvb_frontend *fe)
460{
461 struct tda8290_priv *priv = fe->analog_demod_priv;
462
463 unsigned char cb1[] = { 0x30, 0xD0 };
464 unsigned char tda8290_standby[] = { 0x00, 0x02 };
465 unsigned char tda8290_agc_tri[] = { 0x02, 0x20 };
466 struct i2c_msg msg = {.addr = priv->tda827x_addr, .flags=0, .buf=cb1, .len = 2};
467
468 tda8290_i2c_bridge(fe, 1);
469 if (priv->ver & TDA8275A)
470 cb1[1] = 0x90;
471 i2c_transfer(priv->i2c_props.adap, &msg, 1);
472 tda8290_i2c_bridge(fe, 0);
473 tuner_i2c_xfer_send(&priv->i2c_props, tda8290_agc_tri, 2);
474 tuner_i2c_xfer_send(&priv->i2c_props, tda8290_standby, 2);
475}
476
477static void tda8295_standby(struct dvb_frontend *fe)
478{
479 tda8295_agc1_out(fe, 0); /* Put AGC in tri-state */
480
481 tda8295_power(fe, 0);
482}
483
484static void tda8290_init_if(struct dvb_frontend *fe)
485{
486 struct tda8290_priv *priv = fe->analog_demod_priv;
487
488 unsigned char set_VS[] = { 0x30, 0x6F };
489 unsigned char set_GP00_CF[] = { 0x20, 0x01 };
490 unsigned char set_GP01_CF[] = { 0x20, 0x0B };
491
492 if ((priv->cfg.config == 1) || (priv->cfg.config == 2))
493 tuner_i2c_xfer_send(&priv->i2c_props, set_GP00_CF, 2);
494 else
495 tuner_i2c_xfer_send(&priv->i2c_props, set_GP01_CF, 2);
496 tuner_i2c_xfer_send(&priv->i2c_props, set_VS, 2);
497}
498
499static void tda8295_init_if(struct dvb_frontend *fe)
500{
501 struct tda8290_priv *priv = fe->analog_demod_priv;
502
503 static unsigned char set_adc_ctl[] = { 0x33, 0x14 };
504 static unsigned char set_adc_ctl2[] = { 0x34, 0x00 };
505 static unsigned char set_pll_reg6[] = { 0x3e, 0x63 };
506 static unsigned char set_pll_reg0[] = { 0x38, 0x23 };
507 static unsigned char set_pll_reg7[] = { 0x3f, 0x01 };
508 static unsigned char set_pll_reg10[] = { 0x42, 0x61 };
509 static unsigned char set_gpio_reg0[] = { 0x44, 0x0b };
510
511 tda8295_power(fe, 1);
512
513 tda8295_set_easy_mode(fe, 0);
514 tda8295_set_video_std(fe);
515
516 tuner_i2c_xfer_send(&priv->i2c_props, set_adc_ctl, 2);
517 tuner_i2c_xfer_send(&priv->i2c_props, set_adc_ctl2, 2);
518 tuner_i2c_xfer_send(&priv->i2c_props, set_pll_reg6, 2);
519 tuner_i2c_xfer_send(&priv->i2c_props, set_pll_reg0, 2);
520 tuner_i2c_xfer_send(&priv->i2c_props, set_pll_reg7, 2);
521 tuner_i2c_xfer_send(&priv->i2c_props, set_pll_reg10, 2);
522 tuner_i2c_xfer_send(&priv->i2c_props, set_gpio_reg0, 2);
523
524 tda8295_agc1_out(fe, 0);
525 tda8295_agc2_out(fe, 0);
526}
527
528static void tda8290_init_tuner(struct dvb_frontend *fe)
529{
530 struct tda8290_priv *priv = fe->analog_demod_priv;
531 unsigned char tda8275_init[] = { 0x00, 0x00, 0x00, 0x40, 0xdC, 0x04, 0xAf,
532 0x3F, 0x2A, 0x04, 0xFF, 0x00, 0x00, 0x40 };
533 unsigned char tda8275a_init[] = { 0x00, 0x00, 0x00, 0x00, 0xdC, 0x05, 0x8b,
534 0x0c, 0x04, 0x20, 0xFF, 0x00, 0x00, 0x4b };
535 struct i2c_msg msg = {.addr = priv->tda827x_addr, .flags=0,
536 .buf=tda8275_init, .len = 14};
537 if (priv->ver & TDA8275A)
538 msg.buf = tda8275a_init;
539
540 tda8290_i2c_bridge(fe, 1);
541 i2c_transfer(priv->i2c_props.adap, &msg, 1);
542 tda8290_i2c_bridge(fe, 0);
543}
544
545/*---------------------------------------------------------------------*/
546
547static void tda829x_release(struct dvb_frontend *fe)
548{
549 struct tda8290_priv *priv = fe->analog_demod_priv;
550
551 /* only try to release the tuner if we've
552 * attached it from within this module */
553 if (priv->ver & (TDA18271 | TDA8275 | TDA8275A))
554 if (fe->ops.tuner_ops.release)
555 fe->ops.tuner_ops.release(fe);
556
557 kfree(fe->analog_demod_priv);
558 fe->analog_demod_priv = NULL;
559}
560
561static struct tda18271_config tda829x_tda18271_config = {
562 .gate = TDA18271_GATE_ANALOG,
563};
564
565static int tda829x_find_tuner(struct dvb_frontend *fe)
566{
567 struct tda8290_priv *priv = fe->analog_demod_priv;
568 struct analog_demod_ops *analog_ops = &fe->ops.analog_ops;
569 int i, ret, tuners_found;
570 u32 tuner_addrs;
571 u8 data;
572 struct i2c_msg msg = { .flags = I2C_M_RD, .buf = &data, .len = 1 };
573
574 if (!analog_ops->i2c_gate_ctrl) {
575 printk(KERN_ERR "tda8290: no gate control were provided!\n");
576
577 return -EINVAL;
578 }
579
580 analog_ops->i2c_gate_ctrl(fe, 1);
581
582 /* probe for tuner chip */
583 tuners_found = 0;
584 tuner_addrs = 0;
585 for (i = 0x60; i <= 0x63; i++) {
586 msg.addr = i;
587 ret = i2c_transfer(priv->i2c_props.adap, &msg, 1);
588 if (ret == 1) {
589 tuners_found++;
590 tuner_addrs = (tuner_addrs << 8) + i;
591 }
592 }
593 /* if there is more than one tuner, we expect the right one is
594 behind the bridge and we choose the highest address that doesn't
595 give a response now
596 */
597
598 analog_ops->i2c_gate_ctrl(fe, 0);
599
600 if (tuners_found > 1)
601 for (i = 0; i < tuners_found; i++) {
602 msg.addr = tuner_addrs & 0xff;
603 ret = i2c_transfer(priv->i2c_props.adap, &msg, 1);
604 if (ret == 1)
605 tuner_addrs = tuner_addrs >> 8;
606 else
607 break;
608 }
609
610 if (tuner_addrs == 0) {
611 tuner_addrs = 0x60;
612 tuner_info("could not clearly identify tuner address, "
613 "defaulting to %x\n", tuner_addrs);
614 } else {
615 tuner_addrs = tuner_addrs & 0xff;
616 tuner_info("setting tuner address to %x\n", tuner_addrs);
617 }
618 priv->tda827x_addr = tuner_addrs;
619 msg.addr = tuner_addrs;
620
621 analog_ops->i2c_gate_ctrl(fe, 1);
622 ret = i2c_transfer(priv->i2c_props.adap, &msg, 1);
623
624 if (ret != 1) {
625 tuner_warn("tuner access failed!\n");
626 analog_ops->i2c_gate_ctrl(fe, 0);
627 return -EREMOTEIO;
628 }
629
630 if ((data == 0x83) || (data == 0x84)) {
631 priv->ver |= TDA18271;
632 tda829x_tda18271_config.config = priv->cfg.config;
633 dvb_attach(tda18271_attach, fe, priv->tda827x_addr,
634 priv->i2c_props.adap, &tda829x_tda18271_config);
635 } else {
636 if ((data & 0x3c) == 0)
637 priv->ver |= TDA8275;
638 else
639 priv->ver |= TDA8275A;
640
641 dvb_attach(tda827x_attach, fe, priv->tda827x_addr,
642 priv->i2c_props.adap, &priv->cfg);
643 priv->cfg.switch_addr = priv->i2c_props.addr;
644 }
645 if (fe->ops.tuner_ops.init)
646 fe->ops.tuner_ops.init(fe);
647
648 if (fe->ops.tuner_ops.sleep)
649 fe->ops.tuner_ops.sleep(fe);
650
651 analog_ops->i2c_gate_ctrl(fe, 0);
652
653 return 0;
654}
655
656static int tda8290_probe(struct tuner_i2c_props *i2c_props)
657{
658#define TDA8290_ID 0x89
659 u8 reg = 0x1f, id;
660 struct i2c_msg msg_read[] = {
661 { .addr = i2c_props->addr, .flags = 0, .len = 1, .buf = &reg },
662 { .addr = i2c_props->addr, .flags = I2C_M_RD, .len = 1, .buf = &id },
663 };
664
665 /* detect tda8290 */
666 if (i2c_transfer(i2c_props->adap, msg_read, 2) != 2) {
667 printk(KERN_WARNING "%s: couldn't read register 0x%02x\n",
668 __func__, reg);
669 return -ENODEV;
670 }
671
672 if (id == TDA8290_ID) {
673 if (debug)
674 printk(KERN_DEBUG "%s: tda8290 detected @ %d-%04x\n",
675 __func__, i2c_adapter_id(i2c_props->adap),
676 i2c_props->addr);
677 return 0;
678 }
679 return -ENODEV;
680}
681
682static int tda8295_probe(struct tuner_i2c_props *i2c_props)
683{
684#define TDA8295_ID 0x8a
685#define TDA8295C2_ID 0x8b
686 u8 reg = 0x2f, id;
687 struct i2c_msg msg_read[] = {
688 { .addr = i2c_props->addr, .flags = 0, .len = 1, .buf = &reg },
689 { .addr = i2c_props->addr, .flags = I2C_M_RD, .len = 1, .buf = &id },
690 };
691
692 /* detect tda8295 */
693 if (i2c_transfer(i2c_props->adap, msg_read, 2) != 2) {
694 printk(KERN_WARNING "%s: couldn't read register 0x%02x\n",
695 __func__, reg);
696 return -ENODEV;
697 }
698
699 if ((id & 0xfe) == TDA8295_ID) {
700 if (debug)
701 printk(KERN_DEBUG "%s: %s detected @ %d-%04x\n",
702 __func__, (id == TDA8295_ID) ?
703 "tda8295c1" : "tda8295c2",
704 i2c_adapter_id(i2c_props->adap),
705 i2c_props->addr);
706 return 0;
707 }
708
709 return -ENODEV;
710}
711
712static struct analog_demod_ops tda8290_ops = {
713 .set_params = tda8290_set_params,
714 .has_signal = tda8290_has_signal,
715 .standby = tda8290_standby,
716 .release = tda829x_release,
717 .i2c_gate_ctrl = tda8290_i2c_bridge,
718};
719
720static struct analog_demod_ops tda8295_ops = {
721 .set_params = tda8295_set_params,
722 .has_signal = tda8295_has_signal,
723 .standby = tda8295_standby,
724 .release = tda829x_release,
725 .i2c_gate_ctrl = tda8295_i2c_bridge,
726};
727
728struct dvb_frontend *tda829x_attach(struct dvb_frontend *fe,
729 struct i2c_adapter *i2c_adap, u8 i2c_addr,
730 struct tda829x_config *cfg)
731{
732 struct tda8290_priv *priv = NULL;
733 char *name;
734
735 priv = kzalloc(sizeof(struct tda8290_priv), GFP_KERNEL);
736 if (priv == NULL)
737 return NULL;
738 fe->analog_demod_priv = priv;
739
740 priv->i2c_props.addr = i2c_addr;
741 priv->i2c_props.adap = i2c_adap;
742 priv->i2c_props.name = "tda829x";
743 if (cfg)
744 priv->cfg.config = cfg->lna_cfg;
745
746 if (tda8290_probe(&priv->i2c_props) == 0) {
747 priv->ver = TDA8290;
748 memcpy(&fe->ops.analog_ops, &tda8290_ops,
749 sizeof(struct analog_demod_ops));
750 }
751
752 if (tda8295_probe(&priv->i2c_props) == 0) {
753 priv->ver = TDA8295;
754 memcpy(&fe->ops.analog_ops, &tda8295_ops,
755 sizeof(struct analog_demod_ops));
756 }
757
758 if (!(cfg) || (TDA829X_PROBE_TUNER == cfg->probe_tuner)) {
759 tda8295_power(fe, 1);
760 if (tda829x_find_tuner(fe) < 0)
761 goto fail;
762 }
763
764 switch (priv->ver) {
765 case TDA8290:
766 name = "tda8290";
767 break;
768 case TDA8295:
769 name = "tda8295";
770 break;
771 case TDA8290 | TDA8275:
772 name = "tda8290+75";
773 break;
774 case TDA8295 | TDA8275:
775 name = "tda8295+75";
776 break;
777 case TDA8290 | TDA8275A:
778 name = "tda8290+75a";
779 break;
780 case TDA8295 | TDA8275A:
781 name = "tda8295+75a";
782 break;
783 case TDA8290 | TDA18271:
784 name = "tda8290+18271";
785 break;
786 case TDA8295 | TDA18271:
787 name = "tda8295+18271";
788 break;
789 default:
790 goto fail;
791 }
792 tuner_info("type set to %s\n", name);
793
794 fe->ops.analog_ops.info.name = name;
795
796 if (priv->ver & TDA8290) {
797 if (priv->ver & (TDA8275 | TDA8275A))
798 tda8290_init_tuner(fe);
799 tda8290_init_if(fe);
800 } else if (priv->ver & TDA8295)
801 tda8295_init_if(fe);
802
803 return fe;
804
805fail:
806 memset(&fe->ops.analog_ops, 0, sizeof(struct analog_demod_ops));
807
808 tda829x_release(fe);
809 return NULL;
810}
811EXPORT_SYMBOL_GPL(tda829x_attach);
812
813int tda829x_probe(struct i2c_adapter *i2c_adap, u8 i2c_addr)
814{
815 struct tuner_i2c_props i2c_props = {
816 .adap = i2c_adap,
817 .addr = i2c_addr,
818 };
819
820 unsigned char soft_reset[] = { 0x00, 0x00 };
821 unsigned char easy_mode_b[] = { 0x01, 0x02 };
822 unsigned char easy_mode_g[] = { 0x01, 0x04 };
823 unsigned char restore_9886[] = { 0x00, 0xd6, 0x30 };
824 unsigned char addr_dto_lsb = 0x07;
825 unsigned char data;
826#define PROBE_BUFFER_SIZE 8
827 unsigned char buf[PROBE_BUFFER_SIZE];
828 int i;
829
830 /* rule out tda9887, which would return the same byte repeatedly */
831 tuner_i2c_xfer_send_recv(&i2c_props,
832 soft_reset, 1, buf, PROBE_BUFFER_SIZE);
833 for (i = 1; i < PROBE_BUFFER_SIZE; i++) {
834 if (buf[i] != buf[0])
835 break;
836 }
837
838 /* all bytes are equal, not a tda829x - probably a tda9887 */
839 if (i == PROBE_BUFFER_SIZE)
840 return -ENODEV;
841
842 if ((tda8290_probe(&i2c_props) == 0) ||
843 (tda8295_probe(&i2c_props) == 0))
844 return 0;
845
846 /* fall back to old probing method */
847 tuner_i2c_xfer_send(&i2c_props, easy_mode_b, 2);
848 tuner_i2c_xfer_send(&i2c_props, soft_reset, 2);
849 tuner_i2c_xfer_send_recv(&i2c_props, &addr_dto_lsb, 1, &data, 1);
850 if (data == 0) {
851 tuner_i2c_xfer_send(&i2c_props, easy_mode_g, 2);
852 tuner_i2c_xfer_send(&i2c_props, soft_reset, 2);
853 tuner_i2c_xfer_send_recv(&i2c_props,
854 &addr_dto_lsb, 1, &data, 1);
855 if (data == 0x7b) {
856 return 0;
857 }
858 }
859 tuner_i2c_xfer_send(&i2c_props, restore_9886, 3);
860 return -ENODEV;
861}
862EXPORT_SYMBOL_GPL(tda829x_probe);
863
864MODULE_DESCRIPTION("Philips/NXP TDA8290/TDA8295 analog IF demodulator driver");
865MODULE_AUTHOR("Gerd Knorr, Hartmut Hackmann, Michael Krufky");
866MODULE_LICENSE("GPL");
867
868/*
869 * Overrides for Emacs so that we follow Linus's tabbing style.
870 * ---------------------------------------------------------------------------
871 * Local variables:
872 * c-basic-offset: 8
873 * End:
874 */
diff --git a/drivers/media/common/tuners/tda8290.h b/drivers/media/common/tuners/tda8290.h
new file mode 100644
index 00000000000..7e288b26fcc
--- /dev/null
+++ b/drivers/media/common/tuners/tda8290.h
@@ -0,0 +1,56 @@
1/*
2 This program is free software; you can redistribute it and/or modify
3 it under the terms of the GNU General Public License as published by
4 the Free Software Foundation; either version 2 of the License, or
5 (at your option) any later version.
6
7 This program is distributed in the hope that it will be useful,
8 but WITHOUT ANY WARRANTY; without even the implied warranty of
9 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10 GNU General Public License for more details.
11
12 You should have received a copy of the GNU General Public License
13 along with this program; if not, write to the Free Software
14 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
15*/
16
17#ifndef __TDA8290_H__
18#define __TDA8290_H__
19
20#include <linux/i2c.h>
21#include "dvb_frontend.h"
22
23struct tda829x_config {
24 unsigned int lna_cfg;
25
26 unsigned int probe_tuner:1;
27#define TDA829X_PROBE_TUNER 0
28#define TDA829X_DONT_PROBE 1
29};
30
31#if defined(CONFIG_MEDIA_TUNER_TDA8290) || (defined(CONFIG_MEDIA_TUNER_TDA8290_MODULE) && defined(MODULE))
32extern int tda829x_probe(struct i2c_adapter *i2c_adap, u8 i2c_addr);
33
34extern struct dvb_frontend *tda829x_attach(struct dvb_frontend *fe,
35 struct i2c_adapter *i2c_adap,
36 u8 i2c_addr,
37 struct tda829x_config *cfg);
38#else
39static inline int tda829x_probe(struct i2c_adapter *i2c_adap, u8 i2c_addr)
40{
41 printk(KERN_WARNING "%s: driver disabled by Kconfig\n", __func__);
42 return -EINVAL;
43}
44
45static inline struct dvb_frontend *tda829x_attach(struct dvb_frontend *fe,
46 struct i2c_adapter *i2c_adap,
47 u8 i2c_addr,
48 struct tda829x_config *cfg)
49{
50 printk(KERN_INFO "%s: not probed - driver disabled by Kconfig\n",
51 __func__);
52 return NULL;
53}
54#endif
55
56#endif /* __TDA8290_H__ */
diff --git a/drivers/media/common/tuners/tda9887.c b/drivers/media/common/tuners/tda9887.c
new file mode 100644
index 00000000000..cdb645d5743
--- /dev/null
+++ b/drivers/media/common/tuners/tda9887.c
@@ -0,0 +1,717 @@
1#include <linux/module.h>
2#include <linux/kernel.h>
3#include <linux/i2c.h>
4#include <linux/types.h>
5#include <linux/init.h>
6#include <linux/errno.h>
7#include <linux/delay.h>
8#include <linux/videodev2.h>
9#include <media/v4l2-common.h>
10#include <media/tuner.h>
11#include "tuner-i2c.h"
12#include "tda9887.h"
13
14
15/* Chips:
16 TDA9885 (PAL, NTSC)
17 TDA9886 (PAL, SECAM, NTSC)
18 TDA9887 (PAL, SECAM, NTSC, FM Radio)
19
20 Used as part of several tuners
21*/
22
23static int debug;
24module_param(debug, int, 0644);
25MODULE_PARM_DESC(debug, "enable verbose debug messages");
26
27static DEFINE_MUTEX(tda9887_list_mutex);
28static LIST_HEAD(hybrid_tuner_instance_list);
29
30struct tda9887_priv {
31 struct tuner_i2c_props i2c_props;
32 struct list_head hybrid_tuner_instance_list;
33
34 unsigned char data[4];
35 unsigned int config;
36 unsigned int mode;
37 unsigned int audmode;
38 v4l2_std_id std;
39
40 bool standby;
41};
42
43/* ---------------------------------------------------------------------- */
44
45#define UNSET (-1U)
46
47struct tvnorm {
48 v4l2_std_id std;
49 char *name;
50 unsigned char b;
51 unsigned char c;
52 unsigned char e;
53};
54
55/* ---------------------------------------------------------------------- */
56
57//
58// TDA defines
59//
60
61//// first reg (b)
62#define cVideoTrapBypassOFF 0x00 // bit b0
63#define cVideoTrapBypassON 0x01 // bit b0
64
65#define cAutoMuteFmInactive 0x00 // bit b1
66#define cAutoMuteFmActive 0x02 // bit b1
67
68#define cIntercarrier 0x00 // bit b2
69#define cQSS 0x04 // bit b2
70
71#define cPositiveAmTV 0x00 // bit b3:4
72#define cFmRadio 0x08 // bit b3:4
73#define cNegativeFmTV 0x10 // bit b3:4
74
75
76#define cForcedMuteAudioON 0x20 // bit b5
77#define cForcedMuteAudioOFF 0x00 // bit b5
78
79#define cOutputPort1Active 0x00 // bit b6
80#define cOutputPort1Inactive 0x40 // bit b6
81
82#define cOutputPort2Active 0x00 // bit b7
83#define cOutputPort2Inactive 0x80 // bit b7
84
85
86//// second reg (c)
87#define cDeemphasisOFF 0x00 // bit c5
88#define cDeemphasisON 0x20 // bit c5
89
90#define cDeemphasis75 0x00 // bit c6
91#define cDeemphasis50 0x40 // bit c6
92
93#define cAudioGain0 0x00 // bit c7
94#define cAudioGain6 0x80 // bit c7
95
96#define cTopMask 0x1f // bit c0:4
97#define cTopDefault 0x10 // bit c0:4
98
99//// third reg (e)
100#define cAudioIF_4_5 0x00 // bit e0:1
101#define cAudioIF_5_5 0x01 // bit e0:1
102#define cAudioIF_6_0 0x02 // bit e0:1
103#define cAudioIF_6_5 0x03 // bit e0:1
104
105
106#define cVideoIFMask 0x1c // bit e2:4
107/* Video IF selection in TV Mode (bit B3=0) */
108#define cVideoIF_58_75 0x00 // bit e2:4
109#define cVideoIF_45_75 0x04 // bit e2:4
110#define cVideoIF_38_90 0x08 // bit e2:4
111#define cVideoIF_38_00 0x0C // bit e2:4
112#define cVideoIF_33_90 0x10 // bit e2:4
113#define cVideoIF_33_40 0x14 // bit e2:4
114#define cRadioIF_45_75 0x18 // bit e2:4
115#define cRadioIF_38_90 0x1C // bit e2:4
116
117/* IF1 selection in Radio Mode (bit B3=1) */
118#define cRadioIF_33_30 0x00 // bit e2,4 (also 0x10,0x14)
119#define cRadioIF_41_30 0x04 // bit e2,4
120
121/* Output of AFC pin in radio mode when bit E7=1 */
122#define cRadioAGC_SIF 0x00 // bit e3
123#define cRadioAGC_FM 0x08 // bit e3
124
125#define cTunerGainNormal 0x00 // bit e5
126#define cTunerGainLow 0x20 // bit e5
127
128#define cGating_18 0x00 // bit e6
129#define cGating_36 0x40 // bit e6
130
131#define cAgcOutON 0x80 // bit e7
132#define cAgcOutOFF 0x00 // bit e7
133
134/* ---------------------------------------------------------------------- */
135
136static struct tvnorm tvnorms[] = {
137 {
138 .std = V4L2_STD_PAL_BG | V4L2_STD_PAL_H | V4L2_STD_PAL_N,
139 .name = "PAL-BGHN",
140 .b = ( cNegativeFmTV |
141 cQSS ),
142 .c = ( cDeemphasisON |
143 cDeemphasis50 |
144 cTopDefault),
145 .e = ( cGating_36 |
146 cAudioIF_5_5 |
147 cVideoIF_38_90 ),
148 },{
149 .std = V4L2_STD_PAL_I,
150 .name = "PAL-I",
151 .b = ( cNegativeFmTV |
152 cQSS ),
153 .c = ( cDeemphasisON |
154 cDeemphasis50 |
155 cTopDefault),
156 .e = ( cGating_36 |
157 cAudioIF_6_0 |
158 cVideoIF_38_90 ),
159 },{
160 .std = V4L2_STD_PAL_DK,
161 .name = "PAL-DK",
162 .b = ( cNegativeFmTV |
163 cQSS ),
164 .c = ( cDeemphasisON |
165 cDeemphasis50 |
166 cTopDefault),
167 .e = ( cGating_36 |
168 cAudioIF_6_5 |
169 cVideoIF_38_90 ),
170 },{
171 .std = V4L2_STD_PAL_M | V4L2_STD_PAL_Nc,
172 .name = "PAL-M/Nc",
173 .b = ( cNegativeFmTV |
174 cQSS ),
175 .c = ( cDeemphasisON |
176 cDeemphasis75 |
177 cTopDefault),
178 .e = ( cGating_36 |
179 cAudioIF_4_5 |
180 cVideoIF_45_75 ),
181 },{
182 .std = V4L2_STD_SECAM_B | V4L2_STD_SECAM_G | V4L2_STD_SECAM_H,
183 .name = "SECAM-BGH",
184 .b = ( cNegativeFmTV |
185 cQSS ),
186 .c = ( cTopDefault),
187 .e = ( cAudioIF_5_5 |
188 cVideoIF_38_90 ),
189 },{
190 .std = V4L2_STD_SECAM_L,
191 .name = "SECAM-L",
192 .b = ( cPositiveAmTV |
193 cQSS ),
194 .c = ( cTopDefault),
195 .e = ( cGating_36 |
196 cAudioIF_6_5 |
197 cVideoIF_38_90 ),
198 },{
199 .std = V4L2_STD_SECAM_LC,
200 .name = "SECAM-L'",
201 .b = ( cOutputPort2Inactive |
202 cPositiveAmTV |
203 cQSS ),
204 .c = ( cTopDefault),
205 .e = ( cGating_36 |
206 cAudioIF_6_5 |
207 cVideoIF_33_90 ),
208 },{
209 .std = V4L2_STD_SECAM_DK,
210 .name = "SECAM-DK",
211 .b = ( cNegativeFmTV |
212 cQSS ),
213 .c = ( cDeemphasisON |
214 cDeemphasis50 |
215 cTopDefault),
216 .e = ( cGating_36 |
217 cAudioIF_6_5 |
218 cVideoIF_38_90 ),
219 },{
220 .std = V4L2_STD_NTSC_M | V4L2_STD_NTSC_M_KR,
221 .name = "NTSC-M",
222 .b = ( cNegativeFmTV |
223 cQSS ),
224 .c = ( cDeemphasisON |
225 cDeemphasis75 |
226 cTopDefault),
227 .e = ( cGating_36 |
228 cAudioIF_4_5 |
229 cVideoIF_45_75 ),
230 },{
231 .std = V4L2_STD_NTSC_M_JP,
232 .name = "NTSC-M-JP",
233 .b = ( cNegativeFmTV |
234 cQSS ),
235 .c = ( cDeemphasisON |
236 cDeemphasis50 |
237 cTopDefault),
238 .e = ( cGating_36 |
239 cAudioIF_4_5 |
240 cVideoIF_58_75 ),
241 }
242};
243
244static struct tvnorm radio_stereo = {
245 .name = "Radio Stereo",
246 .b = ( cFmRadio |
247 cQSS ),
248 .c = ( cDeemphasisOFF |
249 cAudioGain6 |
250 cTopDefault),
251 .e = ( cTunerGainLow |
252 cAudioIF_5_5 |
253 cRadioIF_38_90 ),
254};
255
256static struct tvnorm radio_mono = {
257 .name = "Radio Mono",
258 .b = ( cFmRadio |
259 cQSS ),
260 .c = ( cDeemphasisON |
261 cDeemphasis75 |
262 cTopDefault),
263 .e = ( cTunerGainLow |
264 cAudioIF_5_5 |
265 cRadioIF_38_90 ),
266};
267
268/* ---------------------------------------------------------------------- */
269
270static void dump_read_message(struct dvb_frontend *fe, unsigned char *buf)
271{
272 struct tda9887_priv *priv = fe->analog_demod_priv;
273
274 static char *afc[16] = {
275 "- 12.5 kHz",
276 "- 37.5 kHz",
277 "- 62.5 kHz",
278 "- 87.5 kHz",
279 "-112.5 kHz",
280 "-137.5 kHz",
281 "-162.5 kHz",
282 "-187.5 kHz [min]",
283 "+187.5 kHz [max]",
284 "+162.5 kHz",
285 "+137.5 kHz",
286 "+112.5 kHz",
287 "+ 87.5 kHz",
288 "+ 62.5 kHz",
289 "+ 37.5 kHz",
290 "+ 12.5 kHz",
291 };
292 tuner_info("read: 0x%2x\n", buf[0]);
293 tuner_info(" after power on : %s\n", (buf[0] & 0x01) ? "yes" : "no");
294 tuner_info(" afc : %s\n", afc[(buf[0] >> 1) & 0x0f]);
295 tuner_info(" fmif level : %s\n", (buf[0] & 0x20) ? "high" : "low");
296 tuner_info(" afc window : %s\n", (buf[0] & 0x40) ? "in" : "out");
297 tuner_info(" vfi level : %s\n", (buf[0] & 0x80) ? "high" : "low");
298}
299
300static void dump_write_message(struct dvb_frontend *fe, unsigned char *buf)
301{
302 struct tda9887_priv *priv = fe->analog_demod_priv;
303
304 static char *sound[4] = {
305 "AM/TV",
306 "FM/radio",
307 "FM/TV",
308 "FM/radio"
309 };
310 static char *adjust[32] = {
311 "-16", "-15", "-14", "-13", "-12", "-11", "-10", "-9",
312 "-8", "-7", "-6", "-5", "-4", "-3", "-2", "-1",
313 "0", "+1", "+2", "+3", "+4", "+5", "+6", "+7",
314 "+8", "+9", "+10", "+11", "+12", "+13", "+14", "+15"
315 };
316 static char *deemph[4] = {
317 "no", "no", "75", "50"
318 };
319 static char *carrier[4] = {
320 "4.5 MHz",
321 "5.5 MHz",
322 "6.0 MHz",
323 "6.5 MHz / AM"
324 };
325 static char *vif[8] = {
326 "58.75 MHz",
327 "45.75 MHz",
328 "38.9 MHz",
329 "38.0 MHz",
330 "33.9 MHz",
331 "33.4 MHz",
332 "45.75 MHz + pin13",
333 "38.9 MHz + pin13",
334 };
335 static char *rif[4] = {
336 "44 MHz",
337 "52 MHz",
338 "52 MHz",
339 "44 MHz",
340 };
341
342 tuner_info("write: byte B 0x%02x\n", buf[1]);
343 tuner_info(" B0 video mode : %s\n",
344 (buf[1] & 0x01) ? "video trap" : "sound trap");
345 tuner_info(" B1 auto mute fm : %s\n",
346 (buf[1] & 0x02) ? "yes" : "no");
347 tuner_info(" B2 carrier mode : %s\n",
348 (buf[1] & 0x04) ? "QSS" : "Intercarrier");
349 tuner_info(" B3-4 tv sound/radio : %s\n",
350 sound[(buf[1] & 0x18) >> 3]);
351 tuner_info(" B5 force mute audio: %s\n",
352 (buf[1] & 0x20) ? "yes" : "no");
353 tuner_info(" B6 output port 1 : %s\n",
354 (buf[1] & 0x40) ? "high (inactive)" : "low (active)");
355 tuner_info(" B7 output port 2 : %s\n",
356 (buf[1] & 0x80) ? "high (inactive)" : "low (active)");
357
358 tuner_info("write: byte C 0x%02x\n", buf[2]);
359 tuner_info(" C0-4 top adjustment : %s dB\n",
360 adjust[buf[2] & 0x1f]);
361 tuner_info(" C5-6 de-emphasis : %s\n",
362 deemph[(buf[2] & 0x60) >> 5]);
363 tuner_info(" C7 audio gain : %s\n",
364 (buf[2] & 0x80) ? "-6" : "0");
365
366 tuner_info("write: byte E 0x%02x\n", buf[3]);
367 tuner_info(" E0-1 sound carrier : %s\n",
368 carrier[(buf[3] & 0x03)]);
369 tuner_info(" E6 l pll gating : %s\n",
370 (buf[3] & 0x40) ? "36" : "13");
371
372 if (buf[1] & 0x08) {
373 /* radio */
374 tuner_info(" E2-4 video if : %s\n",
375 rif[(buf[3] & 0x0c) >> 2]);
376 tuner_info(" E7 vif agc output : %s\n",
377 (buf[3] & 0x80)
378 ? ((buf[3] & 0x10) ? "fm-agc radio" :
379 "sif-agc radio")
380 : "fm radio carrier afc");
381 } else {
382 /* video */
383 tuner_info(" E2-4 video if : %s\n",
384 vif[(buf[3] & 0x1c) >> 2]);
385 tuner_info(" E5 tuner gain : %s\n",
386 (buf[3] & 0x80)
387 ? ((buf[3] & 0x20) ? "external" : "normal")
388 : ((buf[3] & 0x20) ? "minimum" : "normal"));
389 tuner_info(" E7 vif agc output : %s\n",
390 (buf[3] & 0x80) ? ((buf[3] & 0x20)
391 ? "pin3 port, pin22 vif agc out"
392 : "pin22 port, pin3 vif acg ext in")
393 : "pin3+pin22 port");
394 }
395 tuner_info("--\n");
396}
397
398/* ---------------------------------------------------------------------- */
399
400static int tda9887_set_tvnorm(struct dvb_frontend *fe)
401{
402 struct tda9887_priv *priv = fe->analog_demod_priv;
403 struct tvnorm *norm = NULL;
404 char *buf = priv->data;
405 int i;
406
407 if (priv->mode == V4L2_TUNER_RADIO) {
408 if (priv->audmode == V4L2_TUNER_MODE_MONO)
409 norm = &radio_mono;
410 else
411 norm = &radio_stereo;
412 } else {
413 for (i = 0; i < ARRAY_SIZE(tvnorms); i++) {
414 if (tvnorms[i].std & priv->std) {
415 norm = tvnorms+i;
416 break;
417 }
418 }
419 }
420 if (NULL == norm) {
421 tuner_dbg("Unsupported tvnorm entry - audio muted\n");
422 return -1;
423 }
424
425 tuner_dbg("configure for: %s\n", norm->name);
426 buf[1] = norm->b;
427 buf[2] = norm->c;
428 buf[3] = norm->e;
429 return 0;
430}
431
432static unsigned int port1 = UNSET;
433static unsigned int port2 = UNSET;
434static unsigned int qss = UNSET;
435static unsigned int adjust = UNSET;
436
437module_param(port1, int, 0644);
438module_param(port2, int, 0644);
439module_param(qss, int, 0644);
440module_param(adjust, int, 0644);
441
442static int tda9887_set_insmod(struct dvb_frontend *fe)
443{
444 struct tda9887_priv *priv = fe->analog_demod_priv;
445 char *buf = priv->data;
446
447 if (UNSET != port1) {
448 if (port1)
449 buf[1] |= cOutputPort1Inactive;
450 else
451 buf[1] &= ~cOutputPort1Inactive;
452 }
453 if (UNSET != port2) {
454 if (port2)
455 buf[1] |= cOutputPort2Inactive;
456 else
457 buf[1] &= ~cOutputPort2Inactive;
458 }
459
460 if (UNSET != qss) {
461 if (qss)
462 buf[1] |= cQSS;
463 else
464 buf[1] &= ~cQSS;
465 }
466
467 if (adjust < 0x20) {
468 buf[2] &= ~cTopMask;
469 buf[2] |= adjust;
470 }
471 return 0;
472}
473
474static int tda9887_do_config(struct dvb_frontend *fe)
475{
476 struct tda9887_priv *priv = fe->analog_demod_priv;
477 char *buf = priv->data;
478
479 if (priv->config & TDA9887_PORT1_ACTIVE)
480 buf[1] &= ~cOutputPort1Inactive;
481 if (priv->config & TDA9887_PORT1_INACTIVE)
482 buf[1] |= cOutputPort1Inactive;
483 if (priv->config & TDA9887_PORT2_ACTIVE)
484 buf[1] &= ~cOutputPort2Inactive;
485 if (priv->config & TDA9887_PORT2_INACTIVE)
486 buf[1] |= cOutputPort2Inactive;
487
488 if (priv->config & TDA9887_QSS)
489 buf[1] |= cQSS;
490 if (priv->config & TDA9887_INTERCARRIER)
491 buf[1] &= ~cQSS;
492
493 if (priv->config & TDA9887_AUTOMUTE)
494 buf[1] |= cAutoMuteFmActive;
495 if (priv->config & TDA9887_DEEMPHASIS_MASK) {
496 buf[2] &= ~0x60;
497 switch (priv->config & TDA9887_DEEMPHASIS_MASK) {
498 case TDA9887_DEEMPHASIS_NONE:
499 buf[2] |= cDeemphasisOFF;
500 break;
501 case TDA9887_DEEMPHASIS_50:
502 buf[2] |= cDeemphasisON | cDeemphasis50;
503 break;
504 case TDA9887_DEEMPHASIS_75:
505 buf[2] |= cDeemphasisON | cDeemphasis75;
506 break;
507 }
508 }
509 if (priv->config & TDA9887_TOP_SET) {
510 buf[2] &= ~cTopMask;
511 buf[2] |= (priv->config >> 8) & cTopMask;
512 }
513 if ((priv->config & TDA9887_INTERCARRIER_NTSC) &&
514 (priv->std & V4L2_STD_NTSC))
515 buf[1] &= ~cQSS;
516 if (priv->config & TDA9887_GATING_18)
517 buf[3] &= ~cGating_36;
518
519 if (priv->mode == V4L2_TUNER_RADIO) {
520 if (priv->config & TDA9887_RIF_41_3) {
521 buf[3] &= ~cVideoIFMask;
522 buf[3] |= cRadioIF_41_30;
523 }
524 if (priv->config & TDA9887_GAIN_NORMAL)
525 buf[3] &= ~cTunerGainLow;
526 }
527
528 return 0;
529}
530
531/* ---------------------------------------------------------------------- */
532
533static int tda9887_status(struct dvb_frontend *fe)
534{
535 struct tda9887_priv *priv = fe->analog_demod_priv;
536 unsigned char buf[1];
537 int rc;
538
539 memset(buf,0,sizeof(buf));
540 if (1 != (rc = tuner_i2c_xfer_recv(&priv->i2c_props,buf,1)))
541 tuner_info("i2c i/o error: rc == %d (should be 1)\n", rc);
542 dump_read_message(fe, buf);
543 return 0;
544}
545
546static void tda9887_configure(struct dvb_frontend *fe)
547{
548 struct tda9887_priv *priv = fe->analog_demod_priv;
549 int rc;
550
551 memset(priv->data,0,sizeof(priv->data));
552 tda9887_set_tvnorm(fe);
553
554 /* A note on the port settings:
555 These settings tend to depend on the specifics of the board.
556 By default they are set to inactive (bit value 1) by this driver,
557 overwriting any changes made by the tvnorm. This means that it
558 is the responsibility of the module using the tda9887 to set
559 these values in case of changes in the tvnorm.
560 In many cases port 2 should be made active (0) when selecting
561 SECAM-L, and port 2 should remain inactive (1) for SECAM-L'.
562
563 For the other standards the tda9887 application note says that
564 the ports should be set to active (0), but, again, that may
565 differ depending on the precise hardware configuration.
566 */
567 priv->data[1] |= cOutputPort1Inactive;
568 priv->data[1] |= cOutputPort2Inactive;
569
570 tda9887_do_config(fe);
571 tda9887_set_insmod(fe);
572
573 if (priv->standby)
574 priv->data[1] |= cForcedMuteAudioON;
575
576 tuner_dbg("writing: b=0x%02x c=0x%02x e=0x%02x\n",
577 priv->data[1], priv->data[2], priv->data[3]);
578 if (debug > 1)
579 dump_write_message(fe, priv->data);
580
581 if (4 != (rc = tuner_i2c_xfer_send(&priv->i2c_props,priv->data,4)))
582 tuner_info("i2c i/o error: rc == %d (should be 4)\n", rc);
583
584 if (debug > 2) {
585 msleep_interruptible(1000);
586 tda9887_status(fe);
587 }
588}
589
590/* ---------------------------------------------------------------------- */
591
592static void tda9887_tuner_status(struct dvb_frontend *fe)
593{
594 struct tda9887_priv *priv = fe->analog_demod_priv;
595 tuner_info("Data bytes: b=0x%02x c=0x%02x e=0x%02x\n",
596 priv->data[1], priv->data[2], priv->data[3]);
597}
598
599static int tda9887_get_afc(struct dvb_frontend *fe)
600{
601 struct tda9887_priv *priv = fe->analog_demod_priv;
602 static int AFC_BITS_2_kHz[] = {
603 -12500, -37500, -62500, -97500,
604 -112500, -137500, -162500, -187500,
605 187500, 162500, 137500, 112500,
606 97500 , 62500, 37500 , 12500
607 };
608 int afc=0;
609 __u8 reg = 0;
610
611 if (1 == tuner_i2c_xfer_recv(&priv->i2c_props,&reg,1))
612 afc = AFC_BITS_2_kHz[(reg>>1)&0x0f];
613
614 return afc;
615}
616
617static void tda9887_standby(struct dvb_frontend *fe)
618{
619 struct tda9887_priv *priv = fe->analog_demod_priv;
620
621 priv->standby = true;
622
623 tda9887_configure(fe);
624}
625
626static void tda9887_set_params(struct dvb_frontend *fe,
627 struct analog_parameters *params)
628{
629 struct tda9887_priv *priv = fe->analog_demod_priv;
630
631 priv->standby = false;
632 priv->mode = params->mode;
633 priv->audmode = params->audmode;
634 priv->std = params->std;
635 tda9887_configure(fe);
636}
637
638static int tda9887_set_config(struct dvb_frontend *fe, void *priv_cfg)
639{
640 struct tda9887_priv *priv = fe->analog_demod_priv;
641
642 priv->config = *(unsigned int *)priv_cfg;
643 tda9887_configure(fe);
644
645 return 0;
646}
647
648static void tda9887_release(struct dvb_frontend *fe)
649{
650 struct tda9887_priv *priv = fe->analog_demod_priv;
651
652 mutex_lock(&tda9887_list_mutex);
653
654 if (priv)
655 hybrid_tuner_release_state(priv);
656
657 mutex_unlock(&tda9887_list_mutex);
658
659 fe->analog_demod_priv = NULL;
660}
661
662static struct analog_demod_ops tda9887_ops = {
663 .info = {
664 .name = "tda9887",
665 },
666 .set_params = tda9887_set_params,
667 .standby = tda9887_standby,
668 .tuner_status = tda9887_tuner_status,
669 .get_afc = tda9887_get_afc,
670 .release = tda9887_release,
671 .set_config = tda9887_set_config,
672};
673
674struct dvb_frontend *tda9887_attach(struct dvb_frontend *fe,
675 struct i2c_adapter *i2c_adap,
676 u8 i2c_addr)
677{
678 struct tda9887_priv *priv = NULL;
679 int instance;
680
681 mutex_lock(&tda9887_list_mutex);
682
683 instance = hybrid_tuner_request_state(struct tda9887_priv, priv,
684 hybrid_tuner_instance_list,
685 i2c_adap, i2c_addr, "tda9887");
686 switch (instance) {
687 case 0:
688 mutex_unlock(&tda9887_list_mutex);
689 return NULL;
690 case 1:
691 fe->analog_demod_priv = priv;
692 priv->standby = true;
693 tuner_info("tda988[5/6/7] found\n");
694 break;
695 default:
696 fe->analog_demod_priv = priv;
697 break;
698 }
699
700 mutex_unlock(&tda9887_list_mutex);
701
702 memcpy(&fe->ops.analog_ops, &tda9887_ops,
703 sizeof(struct analog_demod_ops));
704
705 return fe;
706}
707EXPORT_SYMBOL_GPL(tda9887_attach);
708
709MODULE_LICENSE("GPL");
710
711/*
712 * Overrides for Emacs so that we follow Linus's tabbing style.
713 * ---------------------------------------------------------------------------
714 * Local variables:
715 * c-basic-offset: 8
716 * End:
717 */
diff --git a/drivers/media/common/tuners/tda9887.h b/drivers/media/common/tuners/tda9887.h
new file mode 100644
index 00000000000..acc419e8c4f
--- /dev/null
+++ b/drivers/media/common/tuners/tda9887.h
@@ -0,0 +1,38 @@
1/*
2 This program is free software; you can redistribute it and/or modify
3 it under the terms of the GNU General Public License as published by
4 the Free Software Foundation; either version 2 of the License, or
5 (at your option) any later version.
6
7 This program is distributed in the hope that it will be useful,
8 but WITHOUT ANY WARRANTY; without even the implied warranty of
9 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10 GNU General Public License for more details.
11
12 You should have received a copy of the GNU General Public License
13 along with this program; if not, write to the Free Software
14 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
15*/
16
17#ifndef __TDA9887_H__
18#define __TDA9887_H__
19
20#include <linux/i2c.h>
21#include "dvb_frontend.h"
22
23/* ------------------------------------------------------------------------ */
24#if defined(CONFIG_MEDIA_TUNER_TDA9887) || (defined(CONFIG_MEDIA_TUNER_TDA9887_MODULE) && defined(MODULE))
25extern struct dvb_frontend *tda9887_attach(struct dvb_frontend *fe,
26 struct i2c_adapter *i2c_adap,
27 u8 i2c_addr);
28#else
29static inline struct dvb_frontend *tda9887_attach(struct dvb_frontend *fe,
30 struct i2c_adapter *i2c_adap,
31 u8 i2c_addr)
32{
33 printk(KERN_WARNING "%s: driver disabled by Kconfig\n", __func__);
34 return NULL;
35}
36#endif
37
38#endif /* __TDA9887_H__ */
diff --git a/drivers/media/common/tuners/tea5761.c b/drivers/media/common/tuners/tea5761.c
new file mode 100644
index 00000000000..bf78cb9fc52
--- /dev/null
+++ b/drivers/media/common/tuners/tea5761.c
@@ -0,0 +1,348 @@
1/*
2 * For Philips TEA5761 FM Chip
3 * I2C address is allways 0x20 (0x10 at 7-bit mode).
4 *
5 * Copyright (c) 2005-2007 Mauro Carvalho Chehab (mchehab@infradead.org)
6 * This code is placed under the terms of the GNUv2 General Public License
7 *
8 */
9
10#include <linux/i2c.h>
11#include <linux/slab.h>
12#include <linux/delay.h>
13#include <linux/videodev2.h>
14#include <media/tuner.h>
15#include "tuner-i2c.h"
16#include "tea5761.h"
17
18static int debug;
19module_param(debug, int, 0644);
20MODULE_PARM_DESC(debug, "enable verbose debug messages");
21
22struct tea5761_priv {
23 struct tuner_i2c_props i2c_props;
24
25 u32 frequency;
26 bool standby;
27};
28
29/*****************************************************************************/
30
31/***************************
32 * TEA5761HN I2C registers *
33 ***************************/
34
35/* INTREG - Read: bytes 0 and 1 / Write: byte 0 */
36
37 /* first byte for reading */
38#define TEA5761_INTREG_IFFLAG 0x10
39#define TEA5761_INTREG_LEVFLAG 0x8
40#define TEA5761_INTREG_FRRFLAG 0x2
41#define TEA5761_INTREG_BLFLAG 0x1
42
43 /* second byte for reading / byte for writing */
44#define TEA5761_INTREG_IFMSK 0x10
45#define TEA5761_INTREG_LEVMSK 0x8
46#define TEA5761_INTREG_FRMSK 0x2
47#define TEA5761_INTREG_BLMSK 0x1
48
49/* FRQSET - Read: bytes 2 and 3 / Write: byte 1 and 2 */
50
51 /* First byte */
52#define TEA5761_FRQSET_SEARCH_UP 0x80 /* 1=Station search from botton to up */
53#define TEA5761_FRQSET_SEARCH_MODE 0x40 /* 1=Search mode */
54
55 /* Bits 0-5 for divider MSB */
56
57 /* Second byte */
58 /* Bits 0-7 for divider LSB */
59
60/* TNCTRL - Read: bytes 4 and 5 / Write: Bytes 3 and 4 */
61
62 /* first byte */
63
64#define TEA5761_TNCTRL_PUPD_0 0x40 /* Power UP/Power Down MSB */
65#define TEA5761_TNCTRL_BLIM 0X20 /* 1= Japan Frequencies, 0= European frequencies */
66#define TEA5761_TNCTRL_SWPM 0x10 /* 1= software port is FRRFLAG */
67#define TEA5761_TNCTRL_IFCTC 0x08 /* 1= IF count time 15.02 ms, 0= IF count time 2.02 ms */
68#define TEA5761_TNCTRL_AFM 0x04
69#define TEA5761_TNCTRL_SMUTE 0x02 /* 1= Soft mute */
70#define TEA5761_TNCTRL_SNC 0x01
71
72 /* second byte */
73
74#define TEA5761_TNCTRL_MU 0x80 /* 1=Hard mute */
75#define TEA5761_TNCTRL_SSL_1 0x40
76#define TEA5761_TNCTRL_SSL_0 0x20
77#define TEA5761_TNCTRL_HLSI 0x10
78#define TEA5761_TNCTRL_MST 0x08 /* 1 = mono */
79#define TEA5761_TNCTRL_SWP 0x04
80#define TEA5761_TNCTRL_DTC 0x02 /* 1 = deemphasis 50 us, 0 = deemphasis 75 us */
81#define TEA5761_TNCTRL_AHLSI 0x01
82
83/* FRQCHECK - Read: bytes 6 and 7 */
84 /* First byte */
85
86 /* Bits 0-5 for divider MSB */
87
88 /* Second byte */
89 /* Bits 0-7 for divider LSB */
90
91/* TUNCHECK - Read: bytes 8 and 9 */
92
93 /* First byte */
94#define TEA5761_TUNCHECK_IF_MASK 0x7e /* IF count */
95#define TEA5761_TUNCHECK_TUNTO 0x01
96
97 /* Second byte */
98#define TEA5761_TUNCHECK_LEV_MASK 0xf0 /* Level Count */
99#define TEA5761_TUNCHECK_LD 0x08
100#define TEA5761_TUNCHECK_STEREO 0x04
101
102/* TESTREG - Read: bytes 10 and 11 / Write: bytes 5 and 6 */
103
104 /* All zero = no test mode */
105
106/* MANID - Read: bytes 12 and 13 */
107
108 /* First byte - should be 0x10 */
109#define TEA5767_MANID_VERSION_MASK 0xf0 /* Version = 1 */
110#define TEA5767_MANID_ID_MSB_MASK 0x0f /* Manufacurer ID - should be 0 */
111
112 /* Second byte - Should be 0x2b */
113
114#define TEA5767_MANID_ID_LSB_MASK 0xfe /* Manufacturer ID - should be 0x15 */
115#define TEA5767_MANID_IDAV 0x01 /* 1 = Chip has ID, 0 = Chip has no ID */
116
117/* Chip ID - Read: bytes 14 and 15 */
118
119 /* First byte - should be 0x57 */
120
121 /* Second byte - should be 0x61 */
122
123/*****************************************************************************/
124
125#define FREQ_OFFSET 0 /* for TEA5767, it is 700 to give the right freq */
126static void tea5761_status_dump(unsigned char *buffer)
127{
128 unsigned int div, frq;
129
130 div = ((buffer[2] & 0x3f) << 8) | buffer[3];
131
132 frq = 1000 * (div * 32768 / 1000 + FREQ_OFFSET + 225) / 4; /* Freq in KHz */
133
134 printk(KERN_INFO "tea5761: Frequency %d.%03d KHz (divider = 0x%04x)\n",
135 frq / 1000, frq % 1000, div);
136}
137
138/* Freq should be specifyed at 62.5 Hz */
139static int __set_radio_freq(struct dvb_frontend *fe,
140 unsigned int freq,
141 bool mono)
142{
143 struct tea5761_priv *priv = fe->tuner_priv;
144 unsigned int frq = freq;
145 unsigned char buffer[7] = {0, 0, 0, 0, 0, 0, 0 };
146 unsigned div;
147 int rc;
148
149 tuner_dbg("radio freq counter %d\n", frq);
150
151 if (priv->standby) {
152 tuner_dbg("TEA5761 set to standby mode\n");
153 buffer[5] |= TEA5761_TNCTRL_MU;
154 } else {
155 buffer[4] |= TEA5761_TNCTRL_PUPD_0;
156 }
157
158
159 if (mono) {
160 tuner_dbg("TEA5761 set to mono\n");
161 buffer[5] |= TEA5761_TNCTRL_MST;
162 } else {
163 tuner_dbg("TEA5761 set to stereo\n");
164 }
165
166 div = (1000 * (frq * 4 / 16 + 700 + 225) ) >> 15;
167 buffer[1] = (div >> 8) & 0x3f;
168 buffer[2] = div & 0xff;
169
170 if (debug)
171 tea5761_status_dump(buffer);
172
173 if (7 != (rc = tuner_i2c_xfer_send(&priv->i2c_props, buffer, 7)))
174 tuner_warn("i2c i/o error: rc == %d (should be 5)\n", rc);
175
176 priv->frequency = frq * 125 / 2;
177
178 return 0;
179}
180
181static int set_radio_freq(struct dvb_frontend *fe,
182 struct analog_parameters *params)
183{
184 struct tea5761_priv *priv = fe->analog_demod_priv;
185
186 priv->standby = false;
187
188 return __set_radio_freq(fe, params->frequency,
189 params->audmode == V4L2_TUNER_MODE_MONO);
190}
191
192static int set_radio_sleep(struct dvb_frontend *fe)
193{
194 struct tea5761_priv *priv = fe->analog_demod_priv;
195
196 priv->standby = true;
197
198 return __set_radio_freq(fe, priv->frequency, false);
199}
200
201static int tea5761_read_status(struct dvb_frontend *fe, char *buffer)
202{
203 struct tea5761_priv *priv = fe->tuner_priv;
204 int rc;
205
206 memset(buffer, 0, 16);
207 if (16 != (rc = tuner_i2c_xfer_recv(&priv->i2c_props, buffer, 16))) {
208 tuner_warn("i2c i/o error: rc == %d (should be 16)\n", rc);
209 return -EREMOTEIO;
210 }
211
212 return 0;
213}
214
215static inline int tea5761_signal(struct dvb_frontend *fe, const char *buffer)
216{
217 struct tea5761_priv *priv = fe->tuner_priv;
218
219 int signal = ((buffer[9] & TEA5761_TUNCHECK_LEV_MASK) << (13 - 4));
220
221 tuner_dbg("Signal strength: %d\n", signal);
222
223 return signal;
224}
225
226static inline int tea5761_stereo(struct dvb_frontend *fe, const char *buffer)
227{
228 struct tea5761_priv *priv = fe->tuner_priv;
229
230 int stereo = buffer[9] & TEA5761_TUNCHECK_STEREO;
231
232 tuner_dbg("Radio ST GET = %02x\n", stereo);
233
234 return (stereo ? V4L2_TUNER_SUB_STEREO : 0);
235}
236
237static int tea5761_get_status(struct dvb_frontend *fe, u32 *status)
238{
239 unsigned char buffer[16];
240
241 *status = 0;
242
243 if (0 == tea5761_read_status(fe, buffer)) {
244 if (tea5761_signal(fe, buffer))
245 *status = TUNER_STATUS_LOCKED;
246 if (tea5761_stereo(fe, buffer))
247 *status |= TUNER_STATUS_STEREO;
248 }
249
250 return 0;
251}
252
253static int tea5761_get_rf_strength(struct dvb_frontend *fe, u16 *strength)
254{
255 unsigned char buffer[16];
256
257 *strength = 0;
258
259 if (0 == tea5761_read_status(fe, buffer))
260 *strength = tea5761_signal(fe, buffer);
261
262 return 0;
263}
264
265int tea5761_autodetection(struct i2c_adapter* i2c_adap, u8 i2c_addr)
266{
267 unsigned char buffer[16];
268 int rc;
269 struct tuner_i2c_props i2c = { .adap = i2c_adap, .addr = i2c_addr };
270
271 if (16 != (rc = tuner_i2c_xfer_recv(&i2c, buffer, 16))) {
272 printk(KERN_WARNING "it is not a TEA5761. Received %i chars.\n", rc);
273 return -EINVAL;
274 }
275
276 if ((buffer[13] != 0x2b) || (buffer[14] != 0x57) || (buffer[15] != 0x061)) {
277 printk(KERN_WARNING "Manufacturer ID= 0x%02x, Chip ID = %02x%02x."
278 " It is not a TEA5761\n",
279 buffer[13], buffer[14], buffer[15]);
280 return -EINVAL;
281 }
282 printk(KERN_WARNING "tea5761: TEA%02x%02x detected. "
283 "Manufacturer ID= 0x%02x\n",
284 buffer[14], buffer[15], buffer[13]);
285
286 return 0;
287}
288
289static int tea5761_release(struct dvb_frontend *fe)
290{
291 kfree(fe->tuner_priv);
292 fe->tuner_priv = NULL;
293
294 return 0;
295}
296
297static int tea5761_get_frequency(struct dvb_frontend *fe, u32 *frequency)
298{
299 struct tea5761_priv *priv = fe->tuner_priv;
300 *frequency = priv->frequency;
301 return 0;
302}
303
304static struct dvb_tuner_ops tea5761_tuner_ops = {
305 .info = {
306 .name = "tea5761", // Philips TEA5761HN FM Radio
307 },
308 .set_analog_params = set_radio_freq,
309 .sleep = set_radio_sleep,
310 .release = tea5761_release,
311 .get_frequency = tea5761_get_frequency,
312 .get_status = tea5761_get_status,
313 .get_rf_strength = tea5761_get_rf_strength,
314};
315
316struct dvb_frontend *tea5761_attach(struct dvb_frontend *fe,
317 struct i2c_adapter* i2c_adap,
318 u8 i2c_addr)
319{
320 struct tea5761_priv *priv = NULL;
321
322 if (tea5761_autodetection(i2c_adap, i2c_addr) != 0)
323 return NULL;
324
325 priv = kzalloc(sizeof(struct tea5761_priv), GFP_KERNEL);
326 if (priv == NULL)
327 return NULL;
328 fe->tuner_priv = priv;
329
330 priv->i2c_props.addr = i2c_addr;
331 priv->i2c_props.adap = i2c_adap;
332 priv->i2c_props.name = "tea5761";
333
334 memcpy(&fe->ops.tuner_ops, &tea5761_tuner_ops,
335 sizeof(struct dvb_tuner_ops));
336
337 tuner_info("type set to %s\n", "Philips TEA5761HN FM Radio");
338
339 return fe;
340}
341
342
343EXPORT_SYMBOL_GPL(tea5761_attach);
344EXPORT_SYMBOL_GPL(tea5761_autodetection);
345
346MODULE_DESCRIPTION("Philips TEA5761 FM tuner driver");
347MODULE_AUTHOR("Mauro Carvalho Chehab <mchehab@infradead.org>");
348MODULE_LICENSE("GPL");
diff --git a/drivers/media/common/tuners/tea5761.h b/drivers/media/common/tuners/tea5761.h
new file mode 100644
index 00000000000..2e2ff82c95a
--- /dev/null
+++ b/drivers/media/common/tuners/tea5761.h
@@ -0,0 +1,47 @@
1/*
2 This program is free software; you can redistribute it and/or modify
3 it under the terms of the GNU General Public License as published by
4 the Free Software Foundation; either version 2 of the License, or
5 (at your option) any later version.
6
7 This program is distributed in the hope that it will be useful,
8 but WITHOUT ANY WARRANTY; without even the implied warranty of
9 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10 GNU General Public License for more details.
11
12 You should have received a copy of the GNU General Public License
13 along with this program; if not, write to the Free Software
14 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
15*/
16
17#ifndef __TEA5761_H__
18#define __TEA5761_H__
19
20#include <linux/i2c.h>
21#include "dvb_frontend.h"
22
23#if defined(CONFIG_MEDIA_TUNER_TEA5761) || (defined(CONFIG_MEDIA_TUNER_TEA5761_MODULE) && defined(MODULE))
24extern int tea5761_autodetection(struct i2c_adapter* i2c_adap, u8 i2c_addr);
25
26extern struct dvb_frontend *tea5761_attach(struct dvb_frontend *fe,
27 struct i2c_adapter* i2c_adap,
28 u8 i2c_addr);
29#else
30static inline int tea5761_autodetection(struct i2c_adapter* i2c_adap,
31 u8 i2c_addr)
32{
33 printk(KERN_INFO "%s: not probed - driver disabled by Kconfig\n",
34 __func__);
35 return -EINVAL;
36}
37
38static inline struct dvb_frontend *tea5761_attach(struct dvb_frontend *fe,
39 struct i2c_adapter* i2c_adap,
40 u8 i2c_addr)
41{
42 printk(KERN_WARNING "%s: driver disabled by Kconfig\n", __func__);
43 return NULL;
44}
45#endif
46
47#endif /* __TEA5761_H__ */
diff --git a/drivers/media/common/tuners/tea5767.c b/drivers/media/common/tuners/tea5767.c
new file mode 100644
index 00000000000..36e85d81acb
--- /dev/null
+++ b/drivers/media/common/tuners/tea5767.c
@@ -0,0 +1,475 @@
1/*
2 * For Philips TEA5767 FM Chip used on some TV Cards like Prolink Pixelview
3 * I2C address is allways 0xC0.
4 *
5 *
6 * Copyright (c) 2005 Mauro Carvalho Chehab (mchehab@infradead.org)
7 * This code is placed under the terms of the GNU General Public License
8 *
9 * tea5767 autodetection thanks to Torsten Seeboth and Atsushi Nakagawa
10 * from their contributions on DScaler.
11 */
12
13#include <linux/i2c.h>
14#include <linux/slab.h>
15#include <linux/delay.h>
16#include <linux/videodev2.h>
17#include "tuner-i2c.h"
18#include "tea5767.h"
19
20static int debug;
21module_param(debug, int, 0644);
22MODULE_PARM_DESC(debug, "enable verbose debug messages");
23
24/*****************************************************************************/
25
26struct tea5767_priv {
27 struct tuner_i2c_props i2c_props;
28 u32 frequency;
29 struct tea5767_ctrl ctrl;
30};
31
32/*****************************************************************************/
33
34/******************************
35 * Write mode register values *
36 ******************************/
37
38/* First register */
39#define TEA5767_MUTE 0x80 /* Mutes output */
40#define TEA5767_SEARCH 0x40 /* Activates station search */
41/* Bits 0-5 for divider MSB */
42
43/* Second register */
44/* Bits 0-7 for divider LSB */
45
46/* Third register */
47
48/* Station search from botton to up */
49#define TEA5767_SEARCH_UP 0x80
50
51/* Searches with ADC output = 10 */
52#define TEA5767_SRCH_HIGH_LVL 0x60
53
54/* Searches with ADC output = 10 */
55#define TEA5767_SRCH_MID_LVL 0x40
56
57/* Searches with ADC output = 5 */
58#define TEA5767_SRCH_LOW_LVL 0x20
59
60/* if on, div=4*(Frf+Fif)/Fref otherwise, div=4*(Frf-Fif)/Freq) */
61#define TEA5767_HIGH_LO_INJECT 0x10
62
63/* Disable stereo */
64#define TEA5767_MONO 0x08
65
66/* Disable right channel and turns to mono */
67#define TEA5767_MUTE_RIGHT 0x04
68
69/* Disable left channel and turns to mono */
70#define TEA5767_MUTE_LEFT 0x02
71
72#define TEA5767_PORT1_HIGH 0x01
73
74/* Fourth register */
75#define TEA5767_PORT2_HIGH 0x80
76/* Chips stops working. Only I2C bus remains on */
77#define TEA5767_STDBY 0x40
78
79/* Japan freq (76-108 MHz. If disabled, 87.5-108 MHz */
80#define TEA5767_JAPAN_BAND 0x20
81
82/* Unselected means 32.768 KHz freq as reference. Otherwise Xtal at 13 MHz */
83#define TEA5767_XTAL_32768 0x10
84
85/* Cuts weak signals */
86#define TEA5767_SOFT_MUTE 0x08
87
88/* Activates high cut control */
89#define TEA5767_HIGH_CUT_CTRL 0x04
90
91/* Activates stereo noise control */
92#define TEA5767_ST_NOISE_CTL 0x02
93
94/* If activate PORT 1 indicates SEARCH or else it is used as PORT1 */
95#define TEA5767_SRCH_IND 0x01
96
97/* Fifth register */
98
99/* By activating, it will use Xtal at 13 MHz as reference for divider */
100#define TEA5767_PLLREF_ENABLE 0x80
101
102/* By activating, deemphasis=50, or else, deemphasis of 50us */
103#define TEA5767_DEEMPH_75 0X40
104
105/*****************************
106 * Read mode register values *
107 *****************************/
108
109/* First register */
110#define TEA5767_READY_FLAG_MASK 0x80
111#define TEA5767_BAND_LIMIT_MASK 0X40
112/* Bits 0-5 for divider MSB after search or preset */
113
114/* Second register */
115/* Bits 0-7 for divider LSB after search or preset */
116
117/* Third register */
118#define TEA5767_STEREO_MASK 0x80
119#define TEA5767_IF_CNTR_MASK 0x7f
120
121/* Fourth register */
122#define TEA5767_ADC_LEVEL_MASK 0xf0
123
124/* should be 0 */
125#define TEA5767_CHIP_ID_MASK 0x0f
126
127/* Fifth register */
128/* Reserved for future extensions */
129#define TEA5767_RESERVED_MASK 0xff
130
131/*****************************************************************************/
132
133static void tea5767_status_dump(struct tea5767_priv *priv,
134 unsigned char *buffer)
135{
136 unsigned int div, frq;
137
138 if (TEA5767_READY_FLAG_MASK & buffer[0])
139 tuner_info("Ready Flag ON\n");
140 else
141 tuner_info("Ready Flag OFF\n");
142
143 if (TEA5767_BAND_LIMIT_MASK & buffer[0])
144 tuner_info("Tuner at band limit\n");
145 else
146 tuner_info("Tuner not at band limit\n");
147
148 div = ((buffer[0] & 0x3f) << 8) | buffer[1];
149
150 switch (priv->ctrl.xtal_freq) {
151 case TEA5767_HIGH_LO_13MHz:
152 frq = (div * 50000 - 700000 - 225000) / 4; /* Freq in KHz */
153 break;
154 case TEA5767_LOW_LO_13MHz:
155 frq = (div * 50000 + 700000 + 225000) / 4; /* Freq in KHz */
156 break;
157 case TEA5767_LOW_LO_32768:
158 frq = (div * 32768 + 700000 + 225000) / 4; /* Freq in KHz */
159 break;
160 case TEA5767_HIGH_LO_32768:
161 default:
162 frq = (div * 32768 - 700000 - 225000) / 4; /* Freq in KHz */
163 break;
164 }
165 buffer[0] = (div >> 8) & 0x3f;
166 buffer[1] = div & 0xff;
167
168 tuner_info("Frequency %d.%03d KHz (divider = 0x%04x)\n",
169 frq / 1000, frq % 1000, div);
170
171 if (TEA5767_STEREO_MASK & buffer[2])
172 tuner_info("Stereo\n");
173 else
174 tuner_info("Mono\n");
175
176 tuner_info("IF Counter = %d\n", buffer[2] & TEA5767_IF_CNTR_MASK);
177
178 tuner_info("ADC Level = %d\n",
179 (buffer[3] & TEA5767_ADC_LEVEL_MASK) >> 4);
180
181 tuner_info("Chip ID = %d\n", (buffer[3] & TEA5767_CHIP_ID_MASK));
182
183 tuner_info("Reserved = 0x%02x\n",
184 (buffer[4] & TEA5767_RESERVED_MASK));
185}
186
187/* Freq should be specifyed at 62.5 Hz */
188static int set_radio_freq(struct dvb_frontend *fe,
189 struct analog_parameters *params)
190{
191 struct tea5767_priv *priv = fe->tuner_priv;
192 unsigned int frq = params->frequency;
193 unsigned char buffer[5];
194 unsigned div;
195 int rc;
196
197 tuner_dbg("radio freq = %d.%03d MHz\n", frq/16000,(frq/16)%1000);
198
199 buffer[2] = 0;
200
201 if (priv->ctrl.port1)
202 buffer[2] |= TEA5767_PORT1_HIGH;
203
204 if (params->audmode == V4L2_TUNER_MODE_MONO) {
205 tuner_dbg("TEA5767 set to mono\n");
206 buffer[2] |= TEA5767_MONO;
207 } else {
208 tuner_dbg("TEA5767 set to stereo\n");
209 }
210
211
212 buffer[3] = 0;
213
214 if (priv->ctrl.port2)
215 buffer[3] |= TEA5767_PORT2_HIGH;
216
217 if (priv->ctrl.high_cut)
218 buffer[3] |= TEA5767_HIGH_CUT_CTRL;
219
220 if (priv->ctrl.st_noise)
221 buffer[3] |= TEA5767_ST_NOISE_CTL;
222
223 if (priv->ctrl.soft_mute)
224 buffer[3] |= TEA5767_SOFT_MUTE;
225
226 if (priv->ctrl.japan_band)
227 buffer[3] |= TEA5767_JAPAN_BAND;
228
229 buffer[4] = 0;
230
231 if (priv->ctrl.deemph_75)
232 buffer[4] |= TEA5767_DEEMPH_75;
233
234 if (priv->ctrl.pllref)
235 buffer[4] |= TEA5767_PLLREF_ENABLE;
236
237
238 /* Rounds freq to next decimal value - for 62.5 KHz step */
239 /* frq = 20*(frq/16)+radio_frq[frq%16]; */
240
241 switch (priv->ctrl.xtal_freq) {
242 case TEA5767_HIGH_LO_13MHz:
243 tuner_dbg("radio HIGH LO inject xtal @ 13 MHz\n");
244 buffer[2] |= TEA5767_HIGH_LO_INJECT;
245 div = (frq * (4000 / 16) + 700000 + 225000 + 25000) / 50000;
246 break;
247 case TEA5767_LOW_LO_13MHz:
248 tuner_dbg("radio LOW LO inject xtal @ 13 MHz\n");
249
250 div = (frq * (4000 / 16) - 700000 - 225000 + 25000) / 50000;
251 break;
252 case TEA5767_LOW_LO_32768:
253 tuner_dbg("radio LOW LO inject xtal @ 32,768 MHz\n");
254 buffer[3] |= TEA5767_XTAL_32768;
255 /* const 700=4000*175 Khz - to adjust freq to right value */
256 div = ((frq * (4000 / 16) - 700000 - 225000) + 16384) >> 15;
257 break;
258 case TEA5767_HIGH_LO_32768:
259 default:
260 tuner_dbg("radio HIGH LO inject xtal @ 32,768 MHz\n");
261
262 buffer[2] |= TEA5767_HIGH_LO_INJECT;
263 buffer[3] |= TEA5767_XTAL_32768;
264 div = ((frq * (4000 / 16) + 700000 + 225000) + 16384) >> 15;
265 break;
266 }
267 buffer[0] = (div >> 8) & 0x3f;
268 buffer[1] = div & 0xff;
269
270 if (5 != (rc = tuner_i2c_xfer_send(&priv->i2c_props, buffer, 5)))
271 tuner_warn("i2c i/o error: rc == %d (should be 5)\n", rc);
272
273 if (debug) {
274 if (5 != (rc = tuner_i2c_xfer_recv(&priv->i2c_props, buffer, 5)))
275 tuner_warn("i2c i/o error: rc == %d (should be 5)\n", rc);
276 else
277 tea5767_status_dump(priv, buffer);
278 }
279
280 priv->frequency = frq * 125 / 2;
281
282 return 0;
283}
284
285static int tea5767_read_status(struct dvb_frontend *fe, char *buffer)
286{
287 struct tea5767_priv *priv = fe->tuner_priv;
288 int rc;
289
290 memset(buffer, 0, 5);
291 if (5 != (rc = tuner_i2c_xfer_recv(&priv->i2c_props, buffer, 5))) {
292 tuner_warn("i2c i/o error: rc == %d (should be 5)\n", rc);
293 return -EREMOTEIO;
294 }
295
296 return 0;
297}
298
299static inline int tea5767_signal(struct dvb_frontend *fe, const char *buffer)
300{
301 struct tea5767_priv *priv = fe->tuner_priv;
302
303 int signal = ((buffer[3] & TEA5767_ADC_LEVEL_MASK) << 8);
304
305 tuner_dbg("Signal strength: %d\n", signal);
306
307 return signal;
308}
309
310static inline int tea5767_stereo(struct dvb_frontend *fe, const char *buffer)
311{
312 struct tea5767_priv *priv = fe->tuner_priv;
313
314 int stereo = buffer[2] & TEA5767_STEREO_MASK;
315
316 tuner_dbg("Radio ST GET = %02x\n", stereo);
317
318 return (stereo ? V4L2_TUNER_SUB_STEREO : 0);
319}
320
321static int tea5767_get_status(struct dvb_frontend *fe, u32 *status)
322{
323 unsigned char buffer[5];
324
325 *status = 0;
326
327 if (0 == tea5767_read_status(fe, buffer)) {
328 if (tea5767_signal(fe, buffer))
329 *status = TUNER_STATUS_LOCKED;
330 if (tea5767_stereo(fe, buffer))
331 *status |= TUNER_STATUS_STEREO;
332 }
333
334 return 0;
335}
336
337static int tea5767_get_rf_strength(struct dvb_frontend *fe, u16 *strength)
338{
339 unsigned char buffer[5];
340
341 *strength = 0;
342
343 if (0 == tea5767_read_status(fe, buffer))
344 *strength = tea5767_signal(fe, buffer);
345
346 return 0;
347}
348
349static int tea5767_standby(struct dvb_frontend *fe)
350{
351 unsigned char buffer[5];
352 struct tea5767_priv *priv = fe->tuner_priv;
353 unsigned div, rc;
354
355 div = (87500 * 4 + 700 + 225 + 25) / 50; /* Set frequency to 87.5 MHz */
356 buffer[0] = (div >> 8) & 0x3f;
357 buffer[1] = div & 0xff;
358 buffer[2] = TEA5767_PORT1_HIGH;
359 buffer[3] = TEA5767_PORT2_HIGH | TEA5767_HIGH_CUT_CTRL |
360 TEA5767_ST_NOISE_CTL | TEA5767_JAPAN_BAND | TEA5767_STDBY;
361 buffer[4] = 0;
362
363 if (5 != (rc = tuner_i2c_xfer_send(&priv->i2c_props, buffer, 5)))
364 tuner_warn("i2c i/o error: rc == %d (should be 5)\n", rc);
365
366 return 0;
367}
368
369int tea5767_autodetection(struct i2c_adapter* i2c_adap, u8 i2c_addr)
370{
371 struct tuner_i2c_props i2c = { .adap = i2c_adap, .addr = i2c_addr };
372 unsigned char buffer[7] = { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff };
373 int rc;
374
375 if ((rc = tuner_i2c_xfer_recv(&i2c, buffer, 7))< 5) {
376 printk(KERN_WARNING "It is not a TEA5767. Received %i bytes.\n", rc);
377 return -EINVAL;
378 }
379
380 /* If all bytes are the same then it's a TV tuner and not a tea5767 */
381 if (buffer[0] == buffer[1] && buffer[0] == buffer[2] &&
382 buffer[0] == buffer[3] && buffer[0] == buffer[4]) {
383 printk(KERN_WARNING "All bytes are equal. It is not a TEA5767\n");
384 return -EINVAL;
385 }
386
387 /* Status bytes:
388 * Byte 4: bit 3:1 : CI (Chip Identification) == 0
389 * bit 0 : internally set to 0
390 * Byte 5: bit 7:0 : == 0
391 */
392 if (((buffer[3] & 0x0f) != 0x00) || (buffer[4] != 0x00)) {
393 printk(KERN_WARNING "Chip ID is not zero. It is not a TEA5767\n");
394 return -EINVAL;
395 }
396
397
398 return 0;
399}
400
401static int tea5767_release(struct dvb_frontend *fe)
402{
403 kfree(fe->tuner_priv);
404 fe->tuner_priv = NULL;
405
406 return 0;
407}
408
409static int tea5767_get_frequency(struct dvb_frontend *fe, u32 *frequency)
410{
411 struct tea5767_priv *priv = fe->tuner_priv;
412 *frequency = priv->frequency;
413
414 return 0;
415}
416
417static int tea5767_set_config (struct dvb_frontend *fe, void *priv_cfg)
418{
419 struct tea5767_priv *priv = fe->tuner_priv;
420
421 memcpy(&priv->ctrl, priv_cfg, sizeof(priv->ctrl));
422
423 return 0;
424}
425
426static struct dvb_tuner_ops tea5767_tuner_ops = {
427 .info = {
428 .name = "tea5767", // Philips TEA5767HN FM Radio
429 },
430
431 .set_analog_params = set_radio_freq,
432 .set_config = tea5767_set_config,
433 .sleep = tea5767_standby,
434 .release = tea5767_release,
435 .get_frequency = tea5767_get_frequency,
436 .get_status = tea5767_get_status,
437 .get_rf_strength = tea5767_get_rf_strength,
438};
439
440struct dvb_frontend *tea5767_attach(struct dvb_frontend *fe,
441 struct i2c_adapter* i2c_adap,
442 u8 i2c_addr)
443{
444 struct tea5767_priv *priv = NULL;
445
446 priv = kzalloc(sizeof(struct tea5767_priv), GFP_KERNEL);
447 if (priv == NULL)
448 return NULL;
449 fe->tuner_priv = priv;
450
451 priv->i2c_props.addr = i2c_addr;
452 priv->i2c_props.adap = i2c_adap;
453 priv->i2c_props.name = "tea5767";
454
455 priv->ctrl.xtal_freq = TEA5767_HIGH_LO_32768;
456 priv->ctrl.port1 = 1;
457 priv->ctrl.port2 = 1;
458 priv->ctrl.high_cut = 1;
459 priv->ctrl.st_noise = 1;
460 priv->ctrl.japan_band = 1;
461
462 memcpy(&fe->ops.tuner_ops, &tea5767_tuner_ops,
463 sizeof(struct dvb_tuner_ops));
464
465 tuner_info("type set to %s\n", "Philips TEA5767HN FM Radio");
466
467 return fe;
468}
469
470EXPORT_SYMBOL_GPL(tea5767_attach);
471EXPORT_SYMBOL_GPL(tea5767_autodetection);
472
473MODULE_DESCRIPTION("Philips TEA5767 FM tuner driver");
474MODULE_AUTHOR("Mauro Carvalho Chehab <mchehab@infradead.org>");
475MODULE_LICENSE("GPL");
diff --git a/drivers/media/common/tuners/tea5767.h b/drivers/media/common/tuners/tea5767.h
new file mode 100644
index 00000000000..d30ab1b483d
--- /dev/null
+++ b/drivers/media/common/tuners/tea5767.h
@@ -0,0 +1,66 @@
1/*
2 This program is free software; you can redistribute it and/or modify
3 it under the terms of the GNU General Public License as published by
4 the Free Software Foundation; either version 2 of the License, or
5 (at your option) any later version.
6
7 This program is distributed in the hope that it will be useful,
8 but WITHOUT ANY WARRANTY; without even the implied warranty of
9 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10 GNU General Public License for more details.
11
12 You should have received a copy of the GNU General Public License
13 along with this program; if not, write to the Free Software
14 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
15*/
16
17#ifndef __TEA5767_H__
18#define __TEA5767_H__
19
20#include <linux/i2c.h>
21#include "dvb_frontend.h"
22
23enum tea5767_xtal {
24 TEA5767_LOW_LO_32768 = 0,
25 TEA5767_HIGH_LO_32768 = 1,
26 TEA5767_LOW_LO_13MHz = 2,
27 TEA5767_HIGH_LO_13MHz = 3,
28};
29
30struct tea5767_ctrl {
31 unsigned int port1:1;
32 unsigned int port2:1;
33 unsigned int high_cut:1;
34 unsigned int st_noise:1;
35 unsigned int soft_mute:1;
36 unsigned int japan_band:1;
37 unsigned int deemph_75:1;
38 unsigned int pllref:1;
39 enum tea5767_xtal xtal_freq;
40};
41
42#if defined(CONFIG_MEDIA_TUNER_TEA5767) || (defined(CONFIG_MEDIA_TUNER_TEA5767_MODULE) && defined(MODULE))
43extern int tea5767_autodetection(struct i2c_adapter* i2c_adap, u8 i2c_addr);
44
45extern struct dvb_frontend *tea5767_attach(struct dvb_frontend *fe,
46 struct i2c_adapter* i2c_adap,
47 u8 i2c_addr);
48#else
49static inline int tea5767_autodetection(struct i2c_adapter* i2c_adap,
50 u8 i2c_addr)
51{
52 printk(KERN_INFO "%s: not probed - driver disabled by Kconfig\n",
53 __func__);
54 return -EINVAL;
55}
56
57static inline struct dvb_frontend *tea5767_attach(struct dvb_frontend *fe,
58 struct i2c_adapter* i2c_adap,
59 u8 i2c_addr)
60{
61 printk(KERN_WARNING "%s: driver disabled by Kconfig\n", __func__);
62 return NULL;
63}
64#endif
65
66#endif /* __TEA5767_H__ */
diff --git a/drivers/media/common/tuners/tuner-i2c.h b/drivers/media/common/tuners/tuner-i2c.h
new file mode 100644
index 00000000000..18f005634c6
--- /dev/null
+++ b/drivers/media/common/tuners/tuner-i2c.h
@@ -0,0 +1,182 @@
1/*
2 tuner-i2c.h - i2c interface for different tuners
3
4 Copyright (C) 2007 Michael Krufky (mkrufky@linuxtv.org)
5
6 This program is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 2 of the License, or
9 (at your option) any later version.
10
11 This program is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
15
16 You should have received a copy of the GNU General Public License
17 along with this program; if not, write to the Free Software
18 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
19*/
20
21#ifndef __TUNER_I2C_H__
22#define __TUNER_I2C_H__
23
24#include <linux/i2c.h>
25#include <linux/slab.h>
26
27struct tuner_i2c_props {
28 u8 addr;
29 struct i2c_adapter *adap;
30
31 /* used for tuner instance management */
32 int count;
33 char *name;
34};
35
36static inline int tuner_i2c_xfer_send(struct tuner_i2c_props *props, char *buf, int len)
37{
38 struct i2c_msg msg = { .addr = props->addr, .flags = 0,
39 .buf = buf, .len = len };
40 int ret = i2c_transfer(props->adap, &msg, 1);
41
42 return (ret == 1) ? len : ret;
43}
44
45static inline int tuner_i2c_xfer_recv(struct tuner_i2c_props *props, char *buf, int len)
46{
47 struct i2c_msg msg = { .addr = props->addr, .flags = I2C_M_RD,
48 .buf = buf, .len = len };
49 int ret = i2c_transfer(props->adap, &msg, 1);
50
51 return (ret == 1) ? len : ret;
52}
53
54static inline int tuner_i2c_xfer_send_recv(struct tuner_i2c_props *props,
55 char *obuf, int olen,
56 char *ibuf, int ilen)
57{
58 struct i2c_msg msg[2] = { { .addr = props->addr, .flags = 0,
59 .buf = obuf, .len = olen },
60 { .addr = props->addr, .flags = I2C_M_RD,
61 .buf = ibuf, .len = ilen } };
62 int ret = i2c_transfer(props->adap, msg, 2);
63
64 return (ret == 2) ? ilen : ret;
65}
66
67/* Callers must declare as a global for the module:
68 *
69 * static LIST_HEAD(hybrid_tuner_instance_list);
70 *
71 * hybrid_tuner_instance_list should be the third argument
72 * passed into hybrid_tuner_request_state().
73 *
74 * state structure must contain the following:
75 *
76 * struct list_head hybrid_tuner_instance_list;
77 * struct tuner_i2c_props i2c_props;
78 *
79 * hybrid_tuner_instance_list (both within state structure and globally)
80 * is only required if the driver is using hybrid_tuner_request_state
81 * and hybrid_tuner_release_state to manage state sharing between
82 * multiple instances of hybrid tuners.
83 */
84
85#define tuner_printk(kernlvl, i2cprops, fmt, arg...) do { \
86 printk(kernlvl "%s %d-%04x: " fmt, i2cprops.name, \
87 i2cprops.adap ? \
88 i2c_adapter_id(i2cprops.adap) : -1, \
89 i2cprops.addr, ##arg); \
90 } while (0)
91
92/* TO DO: convert all callers of these macros to pass in
93 * struct tuner_i2c_props, then remove the macro wrappers */
94
95#define __tuner_warn(i2cprops, fmt, arg...) do { \
96 tuner_printk(KERN_WARNING, i2cprops, fmt, ##arg); \
97 } while (0)
98
99#define __tuner_info(i2cprops, fmt, arg...) do { \
100 tuner_printk(KERN_INFO, i2cprops, fmt, ##arg); \
101 } while (0)
102
103#define __tuner_err(i2cprops, fmt, arg...) do { \
104 tuner_printk(KERN_ERR, i2cprops, fmt, ##arg); \
105 } while (0)
106
107#define __tuner_dbg(i2cprops, fmt, arg...) do { \
108 if ((debug)) \
109 tuner_printk(KERN_DEBUG, i2cprops, fmt, ##arg); \
110 } while (0)
111
112#define tuner_warn(fmt, arg...) __tuner_warn(priv->i2c_props, fmt, ##arg)
113#define tuner_info(fmt, arg...) __tuner_info(priv->i2c_props, fmt, ##arg)
114#define tuner_err(fmt, arg...) __tuner_err(priv->i2c_props, fmt, ##arg)
115#define tuner_dbg(fmt, arg...) __tuner_dbg(priv->i2c_props, fmt, ##arg)
116
117/****************************************************************************/
118
119/* The return value of hybrid_tuner_request_state indicates the number of
120 * instances using this tuner object.
121 *
122 * 0 - no instances, indicates an error - kzalloc must have failed
123 *
124 * 1 - one instance, indicates that the tuner object was created successfully
125 *
126 * 2 (or more) instances, indicates that an existing tuner object was found
127 */
128
129#define hybrid_tuner_request_state(type, state, list, i2cadap, i2caddr, devname)\
130({ \
131 int __ret = 0; \
132 list_for_each_entry(state, &list, hybrid_tuner_instance_list) { \
133 if (((i2cadap) && (state->i2c_props.adap)) && \
134 ((i2c_adapter_id(state->i2c_props.adap) == \
135 i2c_adapter_id(i2cadap)) && \
136 (i2caddr == state->i2c_props.addr))) { \
137 __tuner_info(state->i2c_props, \
138 "attaching existing instance\n"); \
139 state->i2c_props.count++; \
140 __ret = state->i2c_props.count; \
141 break; \
142 } \
143 } \
144 if (0 == __ret) { \
145 state = kzalloc(sizeof(type), GFP_KERNEL); \
146 if (NULL == state) \
147 goto __fail; \
148 state->i2c_props.addr = i2caddr; \
149 state->i2c_props.adap = i2cadap; \
150 state->i2c_props.name = devname; \
151 __tuner_info(state->i2c_props, \
152 "creating new instance\n"); \
153 list_add_tail(&state->hybrid_tuner_instance_list, &list);\
154 state->i2c_props.count++; \
155 __ret = state->i2c_props.count; \
156 } \
157__fail: \
158 __ret; \
159})
160
161#define hybrid_tuner_release_state(state) \
162({ \
163 int __ret; \
164 state->i2c_props.count--; \
165 __ret = state->i2c_props.count; \
166 if (!state->i2c_props.count) { \
167 __tuner_info(state->i2c_props, "destroying instance\n");\
168 list_del(&state->hybrid_tuner_instance_list); \
169 kfree(state); \
170 } \
171 __ret; \
172})
173
174#define hybrid_tuner_report_instance_count(state) \
175({ \
176 int __ret = 0; \
177 if (state) \
178 __ret = state->i2c_props.count; \
179 __ret; \
180})
181
182#endif /* __TUNER_I2C_H__ */
diff --git a/drivers/media/common/tuners/tuner-simple.c b/drivers/media/common/tuners/tuner-simple.c
new file mode 100644
index 00000000000..f8ee29e6059
--- /dev/null
+++ b/drivers/media/common/tuners/tuner-simple.c
@@ -0,0 +1,1131 @@
1/*
2 * i2c tv tuner chip device driver
3 * controls all those simple 4-control-bytes style tuners.
4 *
5 * This "tuner-simple" module was split apart from the original "tuner" module.
6 */
7#include <linux/delay.h>
8#include <linux/i2c.h>
9#include <linux/videodev2.h>
10#include <media/tuner.h>
11#include <media/v4l2-common.h>
12#include <media/tuner-types.h>
13#include "tuner-i2c.h"
14#include "tuner-simple.h"
15
16static int debug;
17module_param(debug, int, 0644);
18MODULE_PARM_DESC(debug, "enable verbose debug messages");
19
20#define TUNER_SIMPLE_MAX 64
21static unsigned int simple_devcount;
22
23static int offset;
24module_param(offset, int, 0664);
25MODULE_PARM_DESC(offset, "Allows to specify an offset for tuner");
26
27static unsigned int atv_input[TUNER_SIMPLE_MAX] = \
28 { [0 ... (TUNER_SIMPLE_MAX-1)] = 0 };
29static unsigned int dtv_input[TUNER_SIMPLE_MAX] = \
30 { [0 ... (TUNER_SIMPLE_MAX-1)] = 0 };
31module_param_array(atv_input, int, NULL, 0644);
32module_param_array(dtv_input, int, NULL, 0644);
33MODULE_PARM_DESC(atv_input, "specify atv rf input, 0 for autoselect");
34MODULE_PARM_DESC(dtv_input, "specify dtv rf input, 0 for autoselect");
35
36/* ---------------------------------------------------------------------- */
37
38/* tv standard selection for Temic 4046 FM5
39 this value takes the low bits of control byte 2
40 from datasheet Rev.01, Feb.00
41 standard BG I L L2 D
42 picture IF 38.9 38.9 38.9 33.95 38.9
43 sound 1 33.4 32.9 32.4 40.45 32.4
44 sound 2 33.16
45 NICAM 33.05 32.348 33.05 33.05
46 */
47#define TEMIC_SET_PAL_I 0x05
48#define TEMIC_SET_PAL_DK 0x09
49#define TEMIC_SET_PAL_L 0x0a /* SECAM ? */
50#define TEMIC_SET_PAL_L2 0x0b /* change IF ! */
51#define TEMIC_SET_PAL_BG 0x0c
52
53/* tv tuner system standard selection for Philips FQ1216ME
54 this value takes the low bits of control byte 2
55 from datasheet "1999 Nov 16" (supersedes "1999 Mar 23")
56 standard BG DK I L L`
57 picture carrier 38.90 38.90 38.90 38.90 33.95
58 colour 34.47 34.47 34.47 34.47 38.38
59 sound 1 33.40 32.40 32.90 32.40 40.45
60 sound 2 33.16 - - - -
61 NICAM 33.05 33.05 32.35 33.05 39.80
62 */
63#define PHILIPS_SET_PAL_I 0x01 /* Bit 2 always zero !*/
64#define PHILIPS_SET_PAL_BGDK 0x09
65#define PHILIPS_SET_PAL_L2 0x0a
66#define PHILIPS_SET_PAL_L 0x0b
67
68/* system switching for Philips FI1216MF MK2
69 from datasheet "1996 Jul 09",
70 standard BG L L'
71 picture carrier 38.90 38.90 33.95
72 colour 34.47 34.37 38.38
73 sound 1 33.40 32.40 40.45
74 sound 2 33.16 - -
75 NICAM 33.05 33.05 39.80
76 */
77#define PHILIPS_MF_SET_STD_BG 0x01 /* Bit 2 must be zero, Bit 3 is system output */
78#define PHILIPS_MF_SET_STD_L 0x03 /* Used on Secam France */
79#define PHILIPS_MF_SET_STD_LC 0x02 /* Used on SECAM L' */
80
81/* Control byte */
82
83#define TUNER_RATIO_MASK 0x06 /* Bit cb1:cb2 */
84#define TUNER_RATIO_SELECT_50 0x00
85#define TUNER_RATIO_SELECT_32 0x02
86#define TUNER_RATIO_SELECT_166 0x04
87#define TUNER_RATIO_SELECT_62 0x06
88
89#define TUNER_CHARGE_PUMP 0x40 /* Bit cb6 */
90
91/* Status byte */
92
93#define TUNER_POR 0x80
94#define TUNER_FL 0x40
95#define TUNER_MODE 0x38
96#define TUNER_AFC 0x07
97#define TUNER_SIGNAL 0x07
98#define TUNER_STEREO 0x10
99
100#define TUNER_PLL_LOCKED 0x40
101#define TUNER_STEREO_MK3 0x04
102
103static DEFINE_MUTEX(tuner_simple_list_mutex);
104static LIST_HEAD(hybrid_tuner_instance_list);
105
106struct tuner_simple_priv {
107 unsigned int nr;
108 u16 last_div;
109
110 struct tuner_i2c_props i2c_props;
111 struct list_head hybrid_tuner_instance_list;
112
113 unsigned int type;
114 struct tunertype *tun;
115
116 u32 frequency;
117 u32 bandwidth;
118};
119
120/* ---------------------------------------------------------------------- */
121
122static int tuner_read_status(struct dvb_frontend *fe)
123{
124 struct tuner_simple_priv *priv = fe->tuner_priv;
125 unsigned char byte;
126
127 if (1 != tuner_i2c_xfer_recv(&priv->i2c_props, &byte, 1))
128 return 0;
129
130 return byte;
131}
132
133static inline int tuner_signal(const int status)
134{
135 return (status & TUNER_SIGNAL) << 13;
136}
137
138static inline int tuner_stereo(const int type, const int status)
139{
140 switch (type) {
141 case TUNER_PHILIPS_FM1216ME_MK3:
142 case TUNER_PHILIPS_FM1236_MK3:
143 case TUNER_PHILIPS_FM1256_IH3:
144 case TUNER_LG_NTSC_TAPE:
145 case TUNER_TCL_MF02GIP_5N:
146 return ((status & TUNER_SIGNAL) == TUNER_STEREO_MK3);
147 case TUNER_PHILIPS_FM1216MK5:
148 return status | TUNER_STEREO;
149 default:
150 return status & TUNER_STEREO;
151 }
152}
153
154static inline int tuner_islocked(const int status)
155{
156 return (status & TUNER_FL);
157}
158
159static inline int tuner_afcstatus(const int status)
160{
161 return (status & TUNER_AFC) - 2;
162}
163
164
165static int simple_get_status(struct dvb_frontend *fe, u32 *status)
166{
167 struct tuner_simple_priv *priv = fe->tuner_priv;
168 int tuner_status;
169
170 if (priv->i2c_props.adap == NULL)
171 return -EINVAL;
172
173 tuner_status = tuner_read_status(fe);
174
175 *status = 0;
176
177 if (tuner_islocked(tuner_status))
178 *status = TUNER_STATUS_LOCKED;
179 if (tuner_stereo(priv->type, tuner_status))
180 *status |= TUNER_STATUS_STEREO;
181
182 tuner_dbg("AFC Status: %d\n", tuner_afcstatus(tuner_status));
183
184 return 0;
185}
186
187static int simple_get_rf_strength(struct dvb_frontend *fe, u16 *strength)
188{
189 struct tuner_simple_priv *priv = fe->tuner_priv;
190 int signal;
191
192 if (priv->i2c_props.adap == NULL)
193 return -EINVAL;
194
195 signal = tuner_signal(tuner_read_status(fe));
196
197 *strength = signal;
198
199 tuner_dbg("Signal strength: %d\n", signal);
200
201 return 0;
202}
203
204/* ---------------------------------------------------------------------- */
205
206static inline char *tuner_param_name(enum param_type type)
207{
208 char *name;
209
210 switch (type) {
211 case TUNER_PARAM_TYPE_RADIO:
212 name = "radio";
213 break;
214 case TUNER_PARAM_TYPE_PAL:
215 name = "pal";
216 break;
217 case TUNER_PARAM_TYPE_SECAM:
218 name = "secam";
219 break;
220 case TUNER_PARAM_TYPE_NTSC:
221 name = "ntsc";
222 break;
223 case TUNER_PARAM_TYPE_DIGITAL:
224 name = "digital";
225 break;
226 default:
227 name = "unknown";
228 break;
229 }
230 return name;
231}
232
233static struct tuner_params *simple_tuner_params(struct dvb_frontend *fe,
234 enum param_type desired_type)
235{
236 struct tuner_simple_priv *priv = fe->tuner_priv;
237 struct tunertype *tun = priv->tun;
238 int i;
239
240 for (i = 0; i < tun->count; i++)
241 if (desired_type == tun->params[i].type)
242 break;
243
244 /* use default tuner params if desired_type not available */
245 if (i == tun->count) {
246 tuner_dbg("desired params (%s) undefined for tuner %d\n",
247 tuner_param_name(desired_type), priv->type);
248 i = 0;
249 }
250
251 tuner_dbg("using tuner params #%d (%s)\n", i,
252 tuner_param_name(tun->params[i].type));
253
254 return &tun->params[i];
255}
256
257static int simple_config_lookup(struct dvb_frontend *fe,
258 struct tuner_params *t_params,
259 unsigned *frequency, u8 *config, u8 *cb)
260{
261 struct tuner_simple_priv *priv = fe->tuner_priv;
262 int i;
263
264 for (i = 0; i < t_params->count; i++) {
265 if (*frequency > t_params->ranges[i].limit)
266 continue;
267 break;
268 }
269 if (i == t_params->count) {
270 tuner_dbg("frequency out of range (%d > %d)\n",
271 *frequency, t_params->ranges[i - 1].limit);
272 *frequency = t_params->ranges[--i].limit;
273 }
274 *config = t_params->ranges[i].config;
275 *cb = t_params->ranges[i].cb;
276
277 tuner_dbg("freq = %d.%02d (%d), range = %d, "
278 "config = 0x%02x, cb = 0x%02x\n",
279 *frequency / 16, *frequency % 16 * 100 / 16, *frequency,
280 i, *config, *cb);
281
282 return i;
283}
284
285/* ---------------------------------------------------------------------- */
286
287static void simple_set_rf_input(struct dvb_frontend *fe,
288 u8 *config, u8 *cb, unsigned int rf)
289{
290 struct tuner_simple_priv *priv = fe->tuner_priv;
291
292 switch (priv->type) {
293 case TUNER_PHILIPS_TUV1236D:
294 switch (rf) {
295 case 1:
296 *cb |= 0x08;
297 break;
298 default:
299 *cb &= ~0x08;
300 break;
301 }
302 break;
303 case TUNER_PHILIPS_FCV1236D:
304 switch (rf) {
305 case 1:
306 *cb |= 0x01;
307 break;
308 default:
309 *cb &= ~0x01;
310 break;
311 }
312 break;
313 default:
314 break;
315 }
316}
317
318static int simple_std_setup(struct dvb_frontend *fe,
319 struct analog_parameters *params,
320 u8 *config, u8 *cb)
321{
322 struct tuner_simple_priv *priv = fe->tuner_priv;
323 int rc;
324
325 /* tv norm specific stuff for multi-norm tuners */
326 switch (priv->type) {
327 case TUNER_PHILIPS_SECAM: /* FI1216MF */
328 /* 0x01 -> ??? no change ??? */
329 /* 0x02 -> PAL BDGHI / SECAM L */
330 /* 0x04 -> ??? PAL others / SECAM others ??? */
331 *cb &= ~0x03;
332 if (params->std & V4L2_STD_SECAM_L)
333 /* also valid for V4L2_STD_SECAM */
334 *cb |= PHILIPS_MF_SET_STD_L;
335 else if (params->std & V4L2_STD_SECAM_LC)
336 *cb |= PHILIPS_MF_SET_STD_LC;
337 else /* V4L2_STD_B|V4L2_STD_GH */
338 *cb |= PHILIPS_MF_SET_STD_BG;
339 break;
340
341 case TUNER_TEMIC_4046FM5:
342 *cb &= ~0x0f;
343
344 if (params->std & V4L2_STD_PAL_BG) {
345 *cb |= TEMIC_SET_PAL_BG;
346
347 } else if (params->std & V4L2_STD_PAL_I) {
348 *cb |= TEMIC_SET_PAL_I;
349
350 } else if (params->std & V4L2_STD_PAL_DK) {
351 *cb |= TEMIC_SET_PAL_DK;
352
353 } else if (params->std & V4L2_STD_SECAM_L) {
354 *cb |= TEMIC_SET_PAL_L;
355
356 }
357 break;
358
359 case TUNER_PHILIPS_FQ1216ME:
360 *cb &= ~0x0f;
361
362 if (params->std & (V4L2_STD_PAL_BG|V4L2_STD_PAL_DK)) {
363 *cb |= PHILIPS_SET_PAL_BGDK;
364
365 } else if (params->std & V4L2_STD_PAL_I) {
366 *cb |= PHILIPS_SET_PAL_I;
367
368 } else if (params->std & V4L2_STD_SECAM_L) {
369 *cb |= PHILIPS_SET_PAL_L;
370
371 }
372 break;
373
374 case TUNER_PHILIPS_FCV1236D:
375 /* 0x00 -> ATSC antenna input 1 */
376 /* 0x01 -> ATSC antenna input 2 */
377 /* 0x02 -> NTSC antenna input 1 */
378 /* 0x03 -> NTSC antenna input 2 */
379 *cb &= ~0x03;
380 if (!(params->std & V4L2_STD_ATSC))
381 *cb |= 2;
382 break;
383
384 case TUNER_MICROTUNE_4042FI5:
385 /* Set the charge pump for fast tuning */
386 *config |= TUNER_CHARGE_PUMP;
387 break;
388
389 case TUNER_PHILIPS_TUV1236D:
390 {
391 struct tuner_i2c_props i2c = priv->i2c_props;
392 /* 0x40 -> ATSC antenna input 1 */
393 /* 0x48 -> ATSC antenna input 2 */
394 /* 0x00 -> NTSC antenna input 1 */
395 /* 0x08 -> NTSC antenna input 2 */
396 u8 buffer[4] = { 0x14, 0x00, 0x17, 0x00};
397 *cb &= ~0x40;
398 if (params->std & V4L2_STD_ATSC) {
399 *cb |= 0x40;
400 buffer[1] = 0x04;
401 }
402 /* set to the correct mode (analog or digital) */
403 i2c.addr = 0x0a;
404 rc = tuner_i2c_xfer_send(&i2c, &buffer[0], 2);
405 if (2 != rc)
406 tuner_warn("i2c i/o error: rc == %d "
407 "(should be 2)\n", rc);
408 rc = tuner_i2c_xfer_send(&i2c, &buffer[2], 2);
409 if (2 != rc)
410 tuner_warn("i2c i/o error: rc == %d "
411 "(should be 2)\n", rc);
412 break;
413 }
414 }
415 if (atv_input[priv->nr])
416 simple_set_rf_input(fe, config, cb, atv_input[priv->nr]);
417
418 return 0;
419}
420
421static int simple_set_aux_byte(struct dvb_frontend *fe, u8 config, u8 aux)
422{
423 struct tuner_simple_priv *priv = fe->tuner_priv;
424 int rc;
425 u8 buffer[2];
426
427 buffer[0] = (config & ~0x38) | 0x18;
428 buffer[1] = aux;
429
430 tuner_dbg("setting aux byte: 0x%02x 0x%02x\n", buffer[0], buffer[1]);
431
432 rc = tuner_i2c_xfer_send(&priv->i2c_props, buffer, 2);
433 if (2 != rc)
434 tuner_warn("i2c i/o error: rc == %d (should be 2)\n", rc);
435
436 return rc == 2 ? 0 : rc;
437}
438
439static int simple_post_tune(struct dvb_frontend *fe, u8 *buffer,
440 u16 div, u8 config, u8 cb)
441{
442 struct tuner_simple_priv *priv = fe->tuner_priv;
443 int rc;
444
445 switch (priv->type) {
446 case TUNER_LG_TDVS_H06XF:
447 simple_set_aux_byte(fe, config, 0x20);
448 break;
449 case TUNER_PHILIPS_FQ1216LME_MK3:
450 simple_set_aux_byte(fe, config, 0x60); /* External AGC */
451 break;
452 case TUNER_MICROTUNE_4042FI5:
453 {
454 /* FIXME - this may also work for other tuners */
455 unsigned long timeout = jiffies + msecs_to_jiffies(1);
456 u8 status_byte = 0;
457
458 /* Wait until the PLL locks */
459 for (;;) {
460 if (time_after(jiffies, timeout))
461 return 0;
462 rc = tuner_i2c_xfer_recv(&priv->i2c_props,
463 &status_byte, 1);
464 if (1 != rc) {
465 tuner_warn("i2c i/o read error: rc == %d "
466 "(should be 1)\n", rc);
467 break;
468 }
469 if (status_byte & TUNER_PLL_LOCKED)
470 break;
471 udelay(10);
472 }
473
474 /* Set the charge pump for optimized phase noise figure */
475 config &= ~TUNER_CHARGE_PUMP;
476 buffer[0] = (div>>8) & 0x7f;
477 buffer[1] = div & 0xff;
478 buffer[2] = config;
479 buffer[3] = cb;
480 tuner_dbg("tv 0x%02x 0x%02x 0x%02x 0x%02x\n",
481 buffer[0], buffer[1], buffer[2], buffer[3]);
482
483 rc = tuner_i2c_xfer_send(&priv->i2c_props, buffer, 4);
484 if (4 != rc)
485 tuner_warn("i2c i/o error: rc == %d "
486 "(should be 4)\n", rc);
487 break;
488 }
489 }
490
491 return 0;
492}
493
494static int simple_radio_bandswitch(struct dvb_frontend *fe, u8 *buffer)
495{
496 struct tuner_simple_priv *priv = fe->tuner_priv;
497
498 switch (priv->type) {
499 case TUNER_TENA_9533_DI:
500 case TUNER_YMEC_TVF_5533MF:
501 tuner_dbg("This tuner doesn't have FM. "
502 "Most cards have a TEA5767 for FM\n");
503 return 0;
504 case TUNER_PHILIPS_FM1216ME_MK3:
505 case TUNER_PHILIPS_FM1236_MK3:
506 case TUNER_PHILIPS_FMD1216ME_MK3:
507 case TUNER_PHILIPS_FMD1216MEX_MK3:
508 case TUNER_LG_NTSC_TAPE:
509 case TUNER_PHILIPS_FM1256_IH3:
510 case TUNER_TCL_MF02GIP_5N:
511 buffer[3] = 0x19;
512 break;
513 case TUNER_PHILIPS_FM1216MK5:
514 buffer[2] = 0x88;
515 buffer[3] = 0x09;
516 break;
517 case TUNER_TNF_5335MF:
518 buffer[3] = 0x11;
519 break;
520 case TUNER_LG_PAL_FM:
521 buffer[3] = 0xa5;
522 break;
523 case TUNER_THOMSON_DTT761X:
524 buffer[3] = 0x39;
525 break;
526 case TUNER_PHILIPS_FQ1216LME_MK3:
527 case TUNER_PHILIPS_FQ1236_MK5:
528 tuner_err("This tuner doesn't have FM\n");
529 /* Set the low band for sanity, since it covers 88-108 MHz */
530 buffer[3] = 0x01;
531 break;
532 case TUNER_MICROTUNE_4049FM5:
533 default:
534 buffer[3] = 0xa4;
535 break;
536 }
537
538 return 0;
539}
540
541/* ---------------------------------------------------------------------- */
542
543static int simple_set_tv_freq(struct dvb_frontend *fe,
544 struct analog_parameters *params)
545{
546 struct tuner_simple_priv *priv = fe->tuner_priv;
547 u8 config, cb;
548 u16 div;
549 u8 buffer[4];
550 int rc, IFPCoff, i;
551 enum param_type desired_type;
552 struct tuner_params *t_params;
553
554 /* IFPCoff = Video Intermediate Frequency - Vif:
555 940 =16*58.75 NTSC/J (Japan)
556 732 =16*45.75 M/N STD
557 704 =16*44 ATSC (at DVB code)
558 632 =16*39.50 I U.K.
559 622.4=16*38.90 B/G D/K I, L STD
560 592 =16*37.00 D China
561 590 =16.36.875 B Australia
562 543.2=16*33.95 L' STD
563 171.2=16*10.70 FM Radio (at set_radio_freq)
564 */
565
566 if (params->std == V4L2_STD_NTSC_M_JP) {
567 IFPCoff = 940;
568 desired_type = TUNER_PARAM_TYPE_NTSC;
569 } else if ((params->std & V4L2_STD_MN) &&
570 !(params->std & ~V4L2_STD_MN)) {
571 IFPCoff = 732;
572 desired_type = TUNER_PARAM_TYPE_NTSC;
573 } else if (params->std == V4L2_STD_SECAM_LC) {
574 IFPCoff = 543;
575 desired_type = TUNER_PARAM_TYPE_SECAM;
576 } else {
577 IFPCoff = 623;
578 desired_type = TUNER_PARAM_TYPE_PAL;
579 }
580
581 t_params = simple_tuner_params(fe, desired_type);
582
583 i = simple_config_lookup(fe, t_params, &params->frequency,
584 &config, &cb);
585
586 div = params->frequency + IFPCoff + offset;
587
588 tuner_dbg("Freq= %d.%02d MHz, V_IF=%d.%02d MHz, "
589 "Offset=%d.%02d MHz, div=%0d\n",
590 params->frequency / 16, params->frequency % 16 * 100 / 16,
591 IFPCoff / 16, IFPCoff % 16 * 100 / 16,
592 offset / 16, offset % 16 * 100 / 16, div);
593
594 /* tv norm specific stuff for multi-norm tuners */
595 simple_std_setup(fe, params, &config, &cb);
596
597 if (t_params->cb_first_if_lower_freq && div < priv->last_div) {
598 buffer[0] = config;
599 buffer[1] = cb;
600 buffer[2] = (div>>8) & 0x7f;
601 buffer[3] = div & 0xff;
602 } else {
603 buffer[0] = (div>>8) & 0x7f;
604 buffer[1] = div & 0xff;
605 buffer[2] = config;
606 buffer[3] = cb;
607 }
608 priv->last_div = div;
609 if (t_params->has_tda9887) {
610 struct v4l2_priv_tun_config tda9887_cfg;
611 int tda_config = 0;
612 int is_secam_l = (params->std & (V4L2_STD_SECAM_L |
613 V4L2_STD_SECAM_LC)) &&
614 !(params->std & ~(V4L2_STD_SECAM_L |
615 V4L2_STD_SECAM_LC));
616
617 tda9887_cfg.tuner = TUNER_TDA9887;
618 tda9887_cfg.priv = &tda_config;
619
620 if (params->std == V4L2_STD_SECAM_LC) {
621 if (t_params->port1_active ^ t_params->port1_invert_for_secam_lc)
622 tda_config |= TDA9887_PORT1_ACTIVE;
623 if (t_params->port2_active ^ t_params->port2_invert_for_secam_lc)
624 tda_config |= TDA9887_PORT2_ACTIVE;
625 } else {
626 if (t_params->port1_active)
627 tda_config |= TDA9887_PORT1_ACTIVE;
628 if (t_params->port2_active)
629 tda_config |= TDA9887_PORT2_ACTIVE;
630 }
631 if (t_params->intercarrier_mode)
632 tda_config |= TDA9887_INTERCARRIER;
633 if (is_secam_l) {
634 if (i == 0 && t_params->default_top_secam_low)
635 tda_config |= TDA9887_TOP(t_params->default_top_secam_low);
636 else if (i == 1 && t_params->default_top_secam_mid)
637 tda_config |= TDA9887_TOP(t_params->default_top_secam_mid);
638 else if (t_params->default_top_secam_high)
639 tda_config |= TDA9887_TOP(t_params->default_top_secam_high);
640 } else {
641 if (i == 0 && t_params->default_top_low)
642 tda_config |= TDA9887_TOP(t_params->default_top_low);
643 else if (i == 1 && t_params->default_top_mid)
644 tda_config |= TDA9887_TOP(t_params->default_top_mid);
645 else if (t_params->default_top_high)
646 tda_config |= TDA9887_TOP(t_params->default_top_high);
647 }
648 if (t_params->default_pll_gating_18)
649 tda_config |= TDA9887_GATING_18;
650 i2c_clients_command(priv->i2c_props.adap, TUNER_SET_CONFIG,
651 &tda9887_cfg);
652 }
653 tuner_dbg("tv 0x%02x 0x%02x 0x%02x 0x%02x\n",
654 buffer[0], buffer[1], buffer[2], buffer[3]);
655
656 rc = tuner_i2c_xfer_send(&priv->i2c_props, buffer, 4);
657 if (4 != rc)
658 tuner_warn("i2c i/o error: rc == %d (should be 4)\n", rc);
659
660 simple_post_tune(fe, &buffer[0], div, config, cb);
661
662 return 0;
663}
664
665static int simple_set_radio_freq(struct dvb_frontend *fe,
666 struct analog_parameters *params)
667{
668 struct tunertype *tun;
669 struct tuner_simple_priv *priv = fe->tuner_priv;
670 u8 buffer[4];
671 u16 div;
672 int rc, j;
673 struct tuner_params *t_params;
674 unsigned int freq = params->frequency;
675
676 tun = priv->tun;
677
678 for (j = tun->count-1; j > 0; j--)
679 if (tun->params[j].type == TUNER_PARAM_TYPE_RADIO)
680 break;
681 /* default t_params (j=0) will be used if desired type wasn't found */
682 t_params = &tun->params[j];
683
684 /* Select Radio 1st IF used */
685 switch (t_params->radio_if) {
686 case 0: /* 10.7 MHz */
687 freq += (unsigned int)(10.7*16000);
688 break;
689 case 1: /* 33.3 MHz */
690 freq += (unsigned int)(33.3*16000);
691 break;
692 case 2: /* 41.3 MHz */
693 freq += (unsigned int)(41.3*16000);
694 break;
695 default:
696 tuner_warn("Unsupported radio_if value %d\n",
697 t_params->radio_if);
698 return 0;
699 }
700
701 buffer[2] = (t_params->ranges[0].config & ~TUNER_RATIO_MASK) |
702 TUNER_RATIO_SELECT_50; /* 50 kHz step */
703
704 /* Bandswitch byte */
705 simple_radio_bandswitch(fe, &buffer[0]);
706
707 /* Convert from 1/16 kHz V4L steps to 1/20 MHz (=50 kHz) PLL steps
708 freq * (1 Mhz / 16000 V4L steps) * (20 PLL steps / 1 MHz) =
709 freq * (1/800) */
710 div = (freq + 400) / 800;
711
712 if (t_params->cb_first_if_lower_freq && div < priv->last_div) {
713 buffer[0] = buffer[2];
714 buffer[1] = buffer[3];
715 buffer[2] = (div>>8) & 0x7f;
716 buffer[3] = div & 0xff;
717 } else {
718 buffer[0] = (div>>8) & 0x7f;
719 buffer[1] = div & 0xff;
720 }
721
722 tuner_dbg("radio 0x%02x 0x%02x 0x%02x 0x%02x\n",
723 buffer[0], buffer[1], buffer[2], buffer[3]);
724 priv->last_div = div;
725
726 if (t_params->has_tda9887) {
727 int config = 0;
728 struct v4l2_priv_tun_config tda9887_cfg;
729
730 tda9887_cfg.tuner = TUNER_TDA9887;
731 tda9887_cfg.priv = &config;
732
733 if (t_params->port1_active &&
734 !t_params->port1_fm_high_sensitivity)
735 config |= TDA9887_PORT1_ACTIVE;
736 if (t_params->port2_active &&
737 !t_params->port2_fm_high_sensitivity)
738 config |= TDA9887_PORT2_ACTIVE;
739 if (t_params->intercarrier_mode)
740 config |= TDA9887_INTERCARRIER;
741/* if (t_params->port1_set_for_fm_mono)
742 config &= ~TDA9887_PORT1_ACTIVE;*/
743 if (t_params->fm_gain_normal)
744 config |= TDA9887_GAIN_NORMAL;
745 if (t_params->radio_if == 2)
746 config |= TDA9887_RIF_41_3;
747 i2c_clients_command(priv->i2c_props.adap, TUNER_SET_CONFIG,
748 &tda9887_cfg);
749 }
750 rc = tuner_i2c_xfer_send(&priv->i2c_props, buffer, 4);
751 if (4 != rc)
752 tuner_warn("i2c i/o error: rc == %d (should be 4)\n", rc);
753
754 return 0;
755}
756
757static int simple_set_params(struct dvb_frontend *fe,
758 struct analog_parameters *params)
759{
760 struct tuner_simple_priv *priv = fe->tuner_priv;
761 int ret = -EINVAL;
762
763 if (priv->i2c_props.adap == NULL)
764 return -EINVAL;
765
766 switch (params->mode) {
767 case V4L2_TUNER_RADIO:
768 ret = simple_set_radio_freq(fe, params);
769 priv->frequency = params->frequency * 125 / 2;
770 break;
771 case V4L2_TUNER_ANALOG_TV:
772 case V4L2_TUNER_DIGITAL_TV:
773 ret = simple_set_tv_freq(fe, params);
774 priv->frequency = params->frequency * 62500;
775 break;
776 }
777 priv->bandwidth = 0;
778
779 return ret;
780}
781
782static void simple_set_dvb(struct dvb_frontend *fe, u8 *buf,
783 const struct dvb_frontend_parameters *params)
784{
785 struct tuner_simple_priv *priv = fe->tuner_priv;
786
787 switch (priv->type) {
788 case TUNER_PHILIPS_FMD1216ME_MK3:
789 case TUNER_PHILIPS_FMD1216MEX_MK3:
790 if (params->u.ofdm.bandwidth == BANDWIDTH_8_MHZ &&
791 params->frequency >= 158870000)
792 buf[3] |= 0x08;
793 break;
794 case TUNER_PHILIPS_TD1316:
795 /* determine band */
796 buf[3] |= (params->frequency < 161000000) ? 1 :
797 (params->frequency < 444000000) ? 2 : 4;
798
799 /* setup PLL filter */
800 if (params->u.ofdm.bandwidth == BANDWIDTH_8_MHZ)
801 buf[3] |= 1 << 3;
802 break;
803 case TUNER_PHILIPS_TUV1236D:
804 case TUNER_PHILIPS_FCV1236D:
805 {
806 unsigned int new_rf;
807
808 if (dtv_input[priv->nr])
809 new_rf = dtv_input[priv->nr];
810 else
811 switch (params->u.vsb.modulation) {
812 case QAM_64:
813 case QAM_256:
814 new_rf = 1;
815 break;
816 case VSB_8:
817 default:
818 new_rf = 0;
819 break;
820 }
821 simple_set_rf_input(fe, &buf[2], &buf[3], new_rf);
822 break;
823 }
824 default:
825 break;
826 }
827}
828
829static u32 simple_dvb_configure(struct dvb_frontend *fe, u8 *buf,
830 const struct dvb_frontend_parameters *params)
831{
832 /* This function returns the tuned frequency on success, 0 on error */
833 struct tuner_simple_priv *priv = fe->tuner_priv;
834 struct tunertype *tun = priv->tun;
835 static struct tuner_params *t_params;
836 u8 config, cb;
837 u32 div;
838 int ret;
839 unsigned frequency = params->frequency / 62500;
840
841 if (!tun->stepsize) {
842 /* tuner-core was loaded before the digital tuner was
843 * configured and somehow picked the wrong tuner type */
844 tuner_err("attempt to treat tuner %d (%s) as digital tuner "
845 "without stepsize defined.\n",
846 priv->type, priv->tun->name);
847 return 0; /* failure */
848 }
849
850 t_params = simple_tuner_params(fe, TUNER_PARAM_TYPE_DIGITAL);
851 ret = simple_config_lookup(fe, t_params, &frequency, &config, &cb);
852 if (ret < 0)
853 return 0; /* failure */
854
855 div = ((frequency + t_params->iffreq) * 62500 + offset +
856 tun->stepsize/2) / tun->stepsize;
857
858 buf[0] = div >> 8;
859 buf[1] = div & 0xff;
860 buf[2] = config;
861 buf[3] = cb;
862
863 simple_set_dvb(fe, buf, params);
864
865 tuner_dbg("%s: div=%d | buf=0x%02x,0x%02x,0x%02x,0x%02x\n",
866 tun->name, div, buf[0], buf[1], buf[2], buf[3]);
867
868 /* calculate the frequency we set it to */
869 return (div * tun->stepsize) - t_params->iffreq;
870}
871
872static int simple_dvb_calc_regs(struct dvb_frontend *fe,
873 struct dvb_frontend_parameters *params,
874 u8 *buf, int buf_len)
875{
876 struct tuner_simple_priv *priv = fe->tuner_priv;
877 u32 frequency;
878
879 if (buf_len < 5)
880 return -EINVAL;
881
882 frequency = simple_dvb_configure(fe, buf+1, params);
883 if (frequency == 0)
884 return -EINVAL;
885
886 buf[0] = priv->i2c_props.addr;
887
888 priv->frequency = frequency;
889 priv->bandwidth = (fe->ops.info.type == FE_OFDM) ?
890 params->u.ofdm.bandwidth : 0;
891
892 return 5;
893}
894
895static int simple_dvb_set_params(struct dvb_frontend *fe,
896 struct dvb_frontend_parameters *params)
897{
898 struct tuner_simple_priv *priv = fe->tuner_priv;
899 u32 prev_freq, prev_bw;
900 int ret;
901 u8 buf[5];
902
903 if (priv->i2c_props.adap == NULL)
904 return -EINVAL;
905
906 prev_freq = priv->frequency;
907 prev_bw = priv->bandwidth;
908
909 ret = simple_dvb_calc_regs(fe, params, buf, 5);
910 if (ret != 5)
911 goto fail;
912
913 /* put analog demod in standby when tuning digital */
914 if (fe->ops.analog_ops.standby)
915 fe->ops.analog_ops.standby(fe);
916
917 if (fe->ops.i2c_gate_ctrl)
918 fe->ops.i2c_gate_ctrl(fe, 1);
919
920 /* buf[0] contains the i2c address, but *
921 * we already have it in i2c_props.addr */
922 ret = tuner_i2c_xfer_send(&priv->i2c_props, buf+1, 4);
923 if (ret != 4)
924 goto fail;
925
926 return 0;
927fail:
928 /* calc_regs sets frequency and bandwidth. if we failed, unset them */
929 priv->frequency = prev_freq;
930 priv->bandwidth = prev_bw;
931
932 return ret;
933}
934
935static int simple_init(struct dvb_frontend *fe)
936{
937 struct tuner_simple_priv *priv = fe->tuner_priv;
938
939 if (priv->i2c_props.adap == NULL)
940 return -EINVAL;
941
942 if (priv->tun->initdata) {
943 int ret;
944
945 if (fe->ops.i2c_gate_ctrl)
946 fe->ops.i2c_gate_ctrl(fe, 1);
947
948 ret = tuner_i2c_xfer_send(&priv->i2c_props,
949 priv->tun->initdata + 1,
950 priv->tun->initdata[0]);
951 if (ret != priv->tun->initdata[0])
952 return ret;
953 }
954
955 return 0;
956}
957
958static int simple_sleep(struct dvb_frontend *fe)
959{
960 struct tuner_simple_priv *priv = fe->tuner_priv;
961
962 if (priv->i2c_props.adap == NULL)
963 return -EINVAL;
964
965 if (priv->tun->sleepdata) {
966 int ret;
967
968 if (fe->ops.i2c_gate_ctrl)
969 fe->ops.i2c_gate_ctrl(fe, 1);
970
971 ret = tuner_i2c_xfer_send(&priv->i2c_props,
972 priv->tun->sleepdata + 1,
973 priv->tun->sleepdata[0]);
974 if (ret != priv->tun->sleepdata[0])
975 return ret;
976 }
977
978 return 0;
979}
980
981static int simple_release(struct dvb_frontend *fe)
982{
983 struct tuner_simple_priv *priv = fe->tuner_priv;
984
985 mutex_lock(&tuner_simple_list_mutex);
986
987 if (priv)
988 hybrid_tuner_release_state(priv);
989
990 mutex_unlock(&tuner_simple_list_mutex);
991
992 fe->tuner_priv = NULL;
993
994 return 0;
995}
996
997static int simple_get_frequency(struct dvb_frontend *fe, u32 *frequency)
998{
999 struct tuner_simple_priv *priv = fe->tuner_priv;
1000 *frequency = priv->frequency;
1001 return 0;
1002}
1003
1004static int simple_get_bandwidth(struct dvb_frontend *fe, u32 *bandwidth)
1005{
1006 struct tuner_simple_priv *priv = fe->tuner_priv;
1007 *bandwidth = priv->bandwidth;
1008 return 0;
1009}
1010
1011static struct dvb_tuner_ops simple_tuner_ops = {
1012 .init = simple_init,
1013 .sleep = simple_sleep,
1014 .set_analog_params = simple_set_params,
1015 .set_params = simple_dvb_set_params,
1016 .calc_regs = simple_dvb_calc_regs,
1017 .release = simple_release,
1018 .get_frequency = simple_get_frequency,
1019 .get_bandwidth = simple_get_bandwidth,
1020 .get_status = simple_get_status,
1021 .get_rf_strength = simple_get_rf_strength,
1022};
1023
1024struct dvb_frontend *simple_tuner_attach(struct dvb_frontend *fe,
1025 struct i2c_adapter *i2c_adap,
1026 u8 i2c_addr,
1027 unsigned int type)
1028{
1029 struct tuner_simple_priv *priv = NULL;
1030 int instance;
1031
1032 if (type >= tuner_count) {
1033 printk(KERN_WARNING "%s: invalid tuner type: %d (max: %d)\n",
1034 __func__, type, tuner_count-1);
1035 return NULL;
1036 }
1037
1038 /* If i2c_adap is set, check that the tuner is at the correct address.
1039 * Otherwise, if i2c_adap is NULL, the tuner will be programmed directly
1040 * by the digital demod via calc_regs.
1041 */
1042 if (i2c_adap != NULL) {
1043 u8 b[1];
1044 struct i2c_msg msg = {
1045 .addr = i2c_addr, .flags = I2C_M_RD,
1046 .buf = b, .len = 1,
1047 };
1048
1049 if (fe->ops.i2c_gate_ctrl)
1050 fe->ops.i2c_gate_ctrl(fe, 1);
1051
1052 if (1 != i2c_transfer(i2c_adap, &msg, 1))
1053 printk(KERN_WARNING "tuner-simple %d-%04x: "
1054 "unable to probe %s, proceeding anyway.",
1055 i2c_adapter_id(i2c_adap), i2c_addr,
1056 tuners[type].name);
1057
1058 if (fe->ops.i2c_gate_ctrl)
1059 fe->ops.i2c_gate_ctrl(fe, 0);
1060 }
1061
1062 mutex_lock(&tuner_simple_list_mutex);
1063
1064 instance = hybrid_tuner_request_state(struct tuner_simple_priv, priv,
1065 hybrid_tuner_instance_list,
1066 i2c_adap, i2c_addr,
1067 "tuner-simple");
1068 switch (instance) {
1069 case 0:
1070 mutex_unlock(&tuner_simple_list_mutex);
1071 return NULL;
1072 case 1:
1073 fe->tuner_priv = priv;
1074
1075 priv->type = type;
1076 priv->tun = &tuners[type];
1077 priv->nr = simple_devcount++;
1078 break;
1079 default:
1080 fe->tuner_priv = priv;
1081 break;
1082 }
1083
1084 mutex_unlock(&tuner_simple_list_mutex);
1085
1086 memcpy(&fe->ops.tuner_ops, &simple_tuner_ops,
1087 sizeof(struct dvb_tuner_ops));
1088
1089 if (type != priv->type)
1090 tuner_warn("couldn't set type to %d. Using %d (%s) instead\n",
1091 type, priv->type, priv->tun->name);
1092 else
1093 tuner_info("type set to %d (%s)\n",
1094 priv->type, priv->tun->name);
1095
1096 if ((debug) || ((atv_input[priv->nr] > 0) ||
1097 (dtv_input[priv->nr] > 0))) {
1098 if (0 == atv_input[priv->nr])
1099 tuner_info("tuner %d atv rf input will be "
1100 "autoselected\n", priv->nr);
1101 else
1102 tuner_info("tuner %d atv rf input will be "
1103 "set to input %d (insmod option)\n",
1104 priv->nr, atv_input[priv->nr]);
1105 if (0 == dtv_input[priv->nr])
1106 tuner_info("tuner %d dtv rf input will be "
1107 "autoselected\n", priv->nr);
1108 else
1109 tuner_info("tuner %d dtv rf input will be "
1110 "set to input %d (insmod option)\n",
1111 priv->nr, dtv_input[priv->nr]);
1112 }
1113
1114 strlcpy(fe->ops.tuner_ops.info.name, priv->tun->name,
1115 sizeof(fe->ops.tuner_ops.info.name));
1116
1117 return fe;
1118}
1119EXPORT_SYMBOL_GPL(simple_tuner_attach);
1120
1121MODULE_DESCRIPTION("Simple 4-control-bytes style tuner driver");
1122MODULE_AUTHOR("Ralph Metzler, Gerd Knorr, Gunther Mayer");
1123MODULE_LICENSE("GPL");
1124
1125/*
1126 * Overrides for Emacs so that we follow Linus's tabbing style.
1127 * ---------------------------------------------------------------------------
1128 * Local variables:
1129 * c-basic-offset: 8
1130 * End:
1131 */
diff --git a/drivers/media/common/tuners/tuner-simple.h b/drivers/media/common/tuners/tuner-simple.h
new file mode 100644
index 00000000000..381fa5d35a9
--- /dev/null
+++ b/drivers/media/common/tuners/tuner-simple.h
@@ -0,0 +1,39 @@
1/*
2 This program is free software; you can redistribute it and/or modify
3 it under the terms of the GNU General Public License as published by
4 the Free Software Foundation; either version 2 of the License, or
5 (at your option) any later version.
6
7 This program is distributed in the hope that it will be useful,
8 but WITHOUT ANY WARRANTY; without even the implied warranty of
9 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10 GNU General Public License for more details.
11
12 You should have received a copy of the GNU General Public License
13 along with this program; if not, write to the Free Software
14 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
15*/
16
17#ifndef __TUNER_SIMPLE_H__
18#define __TUNER_SIMPLE_H__
19
20#include <linux/i2c.h>
21#include "dvb_frontend.h"
22
23#if defined(CONFIG_MEDIA_TUNER_SIMPLE) || (defined(CONFIG_MEDIA_TUNER_SIMPLE_MODULE) && defined(MODULE))
24extern struct dvb_frontend *simple_tuner_attach(struct dvb_frontend *fe,
25 struct i2c_adapter *i2c_adap,
26 u8 i2c_addr,
27 unsigned int type);
28#else
29static inline struct dvb_frontend *simple_tuner_attach(struct dvb_frontend *fe,
30 struct i2c_adapter *i2c_adap,
31 u8 i2c_addr,
32 unsigned int type)
33{
34 printk(KERN_WARNING "%s: driver disabled by Kconfig\n", __func__);
35 return NULL;
36}
37#endif
38
39#endif /* __TUNER_SIMPLE_H__ */
diff --git a/drivers/media/common/tuners/tuner-types.c b/drivers/media/common/tuners/tuner-types.c
new file mode 100644
index 00000000000..94a603a6084
--- /dev/null
+++ b/drivers/media/common/tuners/tuner-types.c
@@ -0,0 +1,1878 @@
1/*
2 *
3 * i2c tv tuner chip device type database.
4 *
5 */
6
7#include <linux/i2c.h>
8#include <media/tuner.h>
9#include <media/tuner-types.h>
10
11/* ---------------------------------------------------------------------- */
12
13/*
14 * The floats in the tuner struct are computed at compile time
15 * by gcc and cast back to integers. Thus we don't violate the
16 * "no float in kernel" rule.
17 *
18 * A tuner_range may be referenced by multiple tuner_params structs.
19 * There are many duplicates in here. Reusing tuner_range structs,
20 * rather than defining new ones for each tuner, will cut down on
21 * memory usage, and is preferred when possible.
22 *
23 * Each tuner_params array may contain one or more elements, one
24 * for each video standard.
25 *
26 * FIXME: tuner_params struct contains an element, tda988x. We must
27 * set this for all tuners that contain a tda988x chip, and then we
28 * can remove this setting from the various card structs.
29 *
30 * FIXME: Right now, all tuners are using the first tuner_params[]
31 * array element for analog mode. In the future, we will be merging
32 * similar tuner definitions together, such that each tuner definition
33 * will have a tuner_params struct for each available video standard.
34 * At that point, the tuner_params[] array element will be chosen
35 * based on the video standard in use.
36 */
37
38/* The following was taken from dvb-pll.c: */
39
40/* Set AGC TOP value to 103 dBuV:
41 * 0x80 = Control Byte
42 * 0x40 = 250 uA charge pump (irrelevant)
43 * 0x18 = Aux Byte to follow
44 * 0x06 = 64.5 kHz divider (irrelevant)
45 * 0x01 = Disable Vt (aka sleep)
46 *
47 * 0x00 = AGC Time constant 2s Iagc = 300 nA (vs 0x80 = 9 nA)
48 * 0x50 = AGC Take over point = 103 dBuV
49 */
50static u8 tua603x_agc103[] = { 2, 0x80|0x40|0x18|0x06|0x01, 0x00|0x50 };
51
52/* 0x04 = 166.67 kHz divider
53 *
54 * 0x80 = AGC Time constant 50ms Iagc = 9 uA
55 * 0x20 = AGC Take over point = 112 dBuV
56 */
57static u8 tua603x_agc112[] = { 2, 0x80|0x40|0x18|0x04|0x01, 0x80|0x20 };
58
59/* 0-9 */
60/* ------------ TUNER_TEMIC_PAL - TEMIC PAL ------------ */
61
62static struct tuner_range tuner_temic_pal_ranges[] = {
63 { 16 * 140.25 /*MHz*/, 0x8e, 0x02, },
64 { 16 * 463.25 /*MHz*/, 0x8e, 0x04, },
65 { 16 * 999.99 , 0x8e, 0x01, },
66};
67
68static struct tuner_params tuner_temic_pal_params[] = {
69 {
70 .type = TUNER_PARAM_TYPE_PAL,
71 .ranges = tuner_temic_pal_ranges,
72 .count = ARRAY_SIZE(tuner_temic_pal_ranges),
73 },
74};
75
76/* ------------ TUNER_PHILIPS_PAL_I - Philips PAL_I ------------ */
77
78static struct tuner_range tuner_philips_pal_i_ranges[] = {
79 { 16 * 140.25 /*MHz*/, 0x8e, 0xa0, },
80 { 16 * 463.25 /*MHz*/, 0x8e, 0x90, },
81 { 16 * 999.99 , 0x8e, 0x30, },
82};
83
84static struct tuner_params tuner_philips_pal_i_params[] = {
85 {
86 .type = TUNER_PARAM_TYPE_PAL,
87 .ranges = tuner_philips_pal_i_ranges,
88 .count = ARRAY_SIZE(tuner_philips_pal_i_ranges),
89 },
90};
91
92/* ------------ TUNER_PHILIPS_NTSC - Philips NTSC ------------ */
93
94static struct tuner_range tuner_philips_ntsc_ranges[] = {
95 { 16 * 157.25 /*MHz*/, 0x8e, 0xa0, },
96 { 16 * 451.25 /*MHz*/, 0x8e, 0x90, },
97 { 16 * 999.99 , 0x8e, 0x30, },
98};
99
100static struct tuner_params tuner_philips_ntsc_params[] = {
101 {
102 .type = TUNER_PARAM_TYPE_NTSC,
103 .ranges = tuner_philips_ntsc_ranges,
104 .count = ARRAY_SIZE(tuner_philips_ntsc_ranges),
105 .cb_first_if_lower_freq = 1,
106 },
107};
108
109/* ------------ TUNER_PHILIPS_SECAM - Philips SECAM ------------ */
110
111static struct tuner_range tuner_philips_secam_ranges[] = {
112 { 16 * 168.25 /*MHz*/, 0x8e, 0xa7, },
113 { 16 * 447.25 /*MHz*/, 0x8e, 0x97, },
114 { 16 * 999.99 , 0x8e, 0x37, },
115};
116
117static struct tuner_params tuner_philips_secam_params[] = {
118 {
119 .type = TUNER_PARAM_TYPE_SECAM,
120 .ranges = tuner_philips_secam_ranges,
121 .count = ARRAY_SIZE(tuner_philips_secam_ranges),
122 .cb_first_if_lower_freq = 1,
123 },
124};
125
126/* ------------ TUNER_PHILIPS_PAL - Philips PAL ------------ */
127
128static struct tuner_range tuner_philips_pal_ranges[] = {
129 { 16 * 168.25 /*MHz*/, 0x8e, 0xa0, },
130 { 16 * 447.25 /*MHz*/, 0x8e, 0x90, },
131 { 16 * 999.99 , 0x8e, 0x30, },
132};
133
134static struct tuner_params tuner_philips_pal_params[] = {
135 {
136 .type = TUNER_PARAM_TYPE_PAL,
137 .ranges = tuner_philips_pal_ranges,
138 .count = ARRAY_SIZE(tuner_philips_pal_ranges),
139 .cb_first_if_lower_freq = 1,
140 },
141};
142
143/* ------------ TUNER_TEMIC_NTSC - TEMIC NTSC ------------ */
144
145static struct tuner_range tuner_temic_ntsc_ranges[] = {
146 { 16 * 157.25 /*MHz*/, 0x8e, 0x02, },
147 { 16 * 463.25 /*MHz*/, 0x8e, 0x04, },
148 { 16 * 999.99 , 0x8e, 0x01, },
149};
150
151static struct tuner_params tuner_temic_ntsc_params[] = {
152 {
153 .type = TUNER_PARAM_TYPE_NTSC,
154 .ranges = tuner_temic_ntsc_ranges,
155 .count = ARRAY_SIZE(tuner_temic_ntsc_ranges),
156 },
157};
158
159/* ------------ TUNER_TEMIC_PAL_I - TEMIC PAL_I ------------ */
160
161static struct tuner_range tuner_temic_pal_i_ranges[] = {
162 { 16 * 170.00 /*MHz*/, 0x8e, 0x02, },
163 { 16 * 450.00 /*MHz*/, 0x8e, 0x04, },
164 { 16 * 999.99 , 0x8e, 0x01, },
165};
166
167static struct tuner_params tuner_temic_pal_i_params[] = {
168 {
169 .type = TUNER_PARAM_TYPE_PAL,
170 .ranges = tuner_temic_pal_i_ranges,
171 .count = ARRAY_SIZE(tuner_temic_pal_i_ranges),
172 },
173};
174
175/* ------------ TUNER_TEMIC_4036FY5_NTSC - TEMIC NTSC ------------ */
176
177static struct tuner_range tuner_temic_4036fy5_ntsc_ranges[] = {
178 { 16 * 157.25 /*MHz*/, 0x8e, 0xa0, },
179 { 16 * 463.25 /*MHz*/, 0x8e, 0x90, },
180 { 16 * 999.99 , 0x8e, 0x30, },
181};
182
183static struct tuner_params tuner_temic_4036fy5_ntsc_params[] = {
184 {
185 .type = TUNER_PARAM_TYPE_NTSC,
186 .ranges = tuner_temic_4036fy5_ntsc_ranges,
187 .count = ARRAY_SIZE(tuner_temic_4036fy5_ntsc_ranges),
188 },
189};
190
191/* ------------ TUNER_ALPS_TSBH1_NTSC - TEMIC NTSC ------------ */
192
193static struct tuner_range tuner_alps_tsb_1_ranges[] = {
194 { 16 * 137.25 /*MHz*/, 0x8e, 0x01, },
195 { 16 * 385.25 /*MHz*/, 0x8e, 0x02, },
196 { 16 * 999.99 , 0x8e, 0x08, },
197};
198
199static struct tuner_params tuner_alps_tsbh1_ntsc_params[] = {
200 {
201 .type = TUNER_PARAM_TYPE_NTSC,
202 .ranges = tuner_alps_tsb_1_ranges,
203 .count = ARRAY_SIZE(tuner_alps_tsb_1_ranges),
204 },
205};
206
207/* 10-19 */
208/* ------------ TUNER_ALPS_TSBE1_PAL - TEMIC PAL ------------ */
209
210static struct tuner_params tuner_alps_tsb_1_params[] = {
211 {
212 .type = TUNER_PARAM_TYPE_PAL,
213 .ranges = tuner_alps_tsb_1_ranges,
214 .count = ARRAY_SIZE(tuner_alps_tsb_1_ranges),
215 },
216};
217
218/* ------------ TUNER_ALPS_TSBB5_PAL_I - Alps PAL_I ------------ */
219
220static struct tuner_range tuner_alps_tsb_5_pal_ranges[] = {
221 { 16 * 133.25 /*MHz*/, 0x8e, 0x01, },
222 { 16 * 351.25 /*MHz*/, 0x8e, 0x02, },
223 { 16 * 999.99 , 0x8e, 0x08, },
224};
225
226static struct tuner_params tuner_alps_tsbb5_params[] = {
227 {
228 .type = TUNER_PARAM_TYPE_PAL,
229 .ranges = tuner_alps_tsb_5_pal_ranges,
230 .count = ARRAY_SIZE(tuner_alps_tsb_5_pal_ranges),
231 },
232};
233
234/* ------------ TUNER_ALPS_TSBE5_PAL - Alps PAL ------------ */
235
236static struct tuner_params tuner_alps_tsbe5_params[] = {
237 {
238 .type = TUNER_PARAM_TYPE_PAL,
239 .ranges = tuner_alps_tsb_5_pal_ranges,
240 .count = ARRAY_SIZE(tuner_alps_tsb_5_pal_ranges),
241 },
242};
243
244/* ------------ TUNER_ALPS_TSBC5_PAL - Alps PAL ------------ */
245
246static struct tuner_params tuner_alps_tsbc5_params[] = {
247 {
248 .type = TUNER_PARAM_TYPE_PAL,
249 .ranges = tuner_alps_tsb_5_pal_ranges,
250 .count = ARRAY_SIZE(tuner_alps_tsb_5_pal_ranges),
251 },
252};
253
254/* ------------ TUNER_TEMIC_4006FH5_PAL - TEMIC PAL ------------ */
255
256static struct tuner_range tuner_lg_pal_ranges[] = {
257 { 16 * 170.00 /*MHz*/, 0x8e, 0xa0, },
258 { 16 * 450.00 /*MHz*/, 0x8e, 0x90, },
259 { 16 * 999.99 , 0x8e, 0x30, },
260};
261
262static struct tuner_params tuner_temic_4006fh5_params[] = {
263 {
264 .type = TUNER_PARAM_TYPE_PAL,
265 .ranges = tuner_lg_pal_ranges,
266 .count = ARRAY_SIZE(tuner_lg_pal_ranges),
267 },
268};
269
270/* ------------ TUNER_ALPS_TSHC6_NTSC - Alps NTSC ------------ */
271
272static struct tuner_range tuner_alps_tshc6_ntsc_ranges[] = {
273 { 16 * 137.25 /*MHz*/, 0x8e, 0x14, },
274 { 16 * 385.25 /*MHz*/, 0x8e, 0x12, },
275 { 16 * 999.99 , 0x8e, 0x11, },
276};
277
278static struct tuner_params tuner_alps_tshc6_params[] = {
279 {
280 .type = TUNER_PARAM_TYPE_NTSC,
281 .ranges = tuner_alps_tshc6_ntsc_ranges,
282 .count = ARRAY_SIZE(tuner_alps_tshc6_ntsc_ranges),
283 },
284};
285
286/* ------------ TUNER_TEMIC_PAL_DK - TEMIC PAL ------------ */
287
288static struct tuner_range tuner_temic_pal_dk_ranges[] = {
289 { 16 * 168.25 /*MHz*/, 0x8e, 0xa0, },
290 { 16 * 456.25 /*MHz*/, 0x8e, 0x90, },
291 { 16 * 999.99 , 0x8e, 0x30, },
292};
293
294static struct tuner_params tuner_temic_pal_dk_params[] = {
295 {
296 .type = TUNER_PARAM_TYPE_PAL,
297 .ranges = tuner_temic_pal_dk_ranges,
298 .count = ARRAY_SIZE(tuner_temic_pal_dk_ranges),
299 },
300};
301
302/* ------------ TUNER_PHILIPS_NTSC_M - Philips NTSC ------------ */
303
304static struct tuner_range tuner_philips_ntsc_m_ranges[] = {
305 { 16 * 160.00 /*MHz*/, 0x8e, 0xa0, },
306 { 16 * 454.00 /*MHz*/, 0x8e, 0x90, },
307 { 16 * 999.99 , 0x8e, 0x30, },
308};
309
310static struct tuner_params tuner_philips_ntsc_m_params[] = {
311 {
312 .type = TUNER_PARAM_TYPE_NTSC,
313 .ranges = tuner_philips_ntsc_m_ranges,
314 .count = ARRAY_SIZE(tuner_philips_ntsc_m_ranges),
315 },
316};
317
318/* ------------ TUNER_TEMIC_4066FY5_PAL_I - TEMIC PAL_I ------------ */
319
320static struct tuner_range tuner_temic_40x6f_5_pal_ranges[] = {
321 { 16 * 169.00 /*MHz*/, 0x8e, 0xa0, },
322 { 16 * 454.00 /*MHz*/, 0x8e, 0x90, },
323 { 16 * 999.99 , 0x8e, 0x30, },
324};
325
326static struct tuner_params tuner_temic_4066fy5_pal_i_params[] = {
327 {
328 .type = TUNER_PARAM_TYPE_PAL,
329 .ranges = tuner_temic_40x6f_5_pal_ranges,
330 .count = ARRAY_SIZE(tuner_temic_40x6f_5_pal_ranges),
331 },
332};
333
334/* ------------ TUNER_TEMIC_4006FN5_MULTI_PAL - TEMIC PAL ------------ */
335
336static struct tuner_params tuner_temic_4006fn5_multi_params[] = {
337 {
338 .type = TUNER_PARAM_TYPE_PAL,
339 .ranges = tuner_temic_40x6f_5_pal_ranges,
340 .count = ARRAY_SIZE(tuner_temic_40x6f_5_pal_ranges),
341 },
342};
343
344/* 20-29 */
345/* ------------ TUNER_TEMIC_4009FR5_PAL - TEMIC PAL ------------ */
346
347static struct tuner_range tuner_temic_4009f_5_pal_ranges[] = {
348 { 16 * 141.00 /*MHz*/, 0x8e, 0xa0, },
349 { 16 * 464.00 /*MHz*/, 0x8e, 0x90, },
350 { 16 * 999.99 , 0x8e, 0x30, },
351};
352
353static struct tuner_params tuner_temic_4009f_5_params[] = {
354 {
355 .type = TUNER_PARAM_TYPE_PAL,
356 .ranges = tuner_temic_4009f_5_pal_ranges,
357 .count = ARRAY_SIZE(tuner_temic_4009f_5_pal_ranges),
358 },
359};
360
361/* ------------ TUNER_TEMIC_4039FR5_NTSC - TEMIC NTSC ------------ */
362
363static struct tuner_range tuner_temic_4x3x_f_5_ntsc_ranges[] = {
364 { 16 * 158.00 /*MHz*/, 0x8e, 0xa0, },
365 { 16 * 453.00 /*MHz*/, 0x8e, 0x90, },
366 { 16 * 999.99 , 0x8e, 0x30, },
367};
368
369static struct tuner_params tuner_temic_4039fr5_params[] = {
370 {
371 .type = TUNER_PARAM_TYPE_NTSC,
372 .ranges = tuner_temic_4x3x_f_5_ntsc_ranges,
373 .count = ARRAY_SIZE(tuner_temic_4x3x_f_5_ntsc_ranges),
374 },
375};
376
377/* ------------ TUNER_TEMIC_4046FM5 - TEMIC PAL ------------ */
378
379static struct tuner_params tuner_temic_4046fm5_params[] = {
380 {
381 .type = TUNER_PARAM_TYPE_PAL,
382 .ranges = tuner_temic_40x6f_5_pal_ranges,
383 .count = ARRAY_SIZE(tuner_temic_40x6f_5_pal_ranges),
384 },
385};
386
387/* ------------ TUNER_PHILIPS_PAL_DK - Philips PAL ------------ */
388
389static struct tuner_params tuner_philips_pal_dk_params[] = {
390 {
391 .type = TUNER_PARAM_TYPE_PAL,
392 .ranges = tuner_lg_pal_ranges,
393 .count = ARRAY_SIZE(tuner_lg_pal_ranges),
394 },
395};
396
397/* ------------ TUNER_PHILIPS_FQ1216ME - Philips PAL ------------ */
398
399static struct tuner_params tuner_philips_fq1216me_params[] = {
400 {
401 .type = TUNER_PARAM_TYPE_PAL,
402 .ranges = tuner_lg_pal_ranges,
403 .count = ARRAY_SIZE(tuner_lg_pal_ranges),
404 .has_tda9887 = 1,
405 .port1_active = 1,
406 .port2_active = 1,
407 .port2_invert_for_secam_lc = 1,
408 },
409};
410
411/* ------------ TUNER_LG_PAL_I_FM - LGINNOTEK PAL_I ------------ */
412
413static struct tuner_params tuner_lg_pal_i_fm_params[] = {
414 {
415 .type = TUNER_PARAM_TYPE_PAL,
416 .ranges = tuner_lg_pal_ranges,
417 .count = ARRAY_SIZE(tuner_lg_pal_ranges),
418 },
419};
420
421/* ------------ TUNER_LG_PAL_I - LGINNOTEK PAL_I ------------ */
422
423static struct tuner_params tuner_lg_pal_i_params[] = {
424 {
425 .type = TUNER_PARAM_TYPE_PAL,
426 .ranges = tuner_lg_pal_ranges,
427 .count = ARRAY_SIZE(tuner_lg_pal_ranges),
428 },
429};
430
431/* ------------ TUNER_LG_NTSC_FM - LGINNOTEK NTSC ------------ */
432
433static struct tuner_range tuner_lg_ntsc_fm_ranges[] = {
434 { 16 * 210.00 /*MHz*/, 0x8e, 0xa0, },
435 { 16 * 497.00 /*MHz*/, 0x8e, 0x90, },
436 { 16 * 999.99 , 0x8e, 0x30, },
437};
438
439static struct tuner_params tuner_lg_ntsc_fm_params[] = {
440 {
441 .type = TUNER_PARAM_TYPE_NTSC,
442 .ranges = tuner_lg_ntsc_fm_ranges,
443 .count = ARRAY_SIZE(tuner_lg_ntsc_fm_ranges),
444 },
445};
446
447/* ------------ TUNER_LG_PAL_FM - LGINNOTEK PAL ------------ */
448
449static struct tuner_params tuner_lg_pal_fm_params[] = {
450 {
451 .type = TUNER_PARAM_TYPE_PAL,
452 .ranges = tuner_lg_pal_ranges,
453 .count = ARRAY_SIZE(tuner_lg_pal_ranges),
454 },
455};
456
457/* ------------ TUNER_LG_PAL - LGINNOTEK PAL ------------ */
458
459static struct tuner_params tuner_lg_pal_params[] = {
460 {
461 .type = TUNER_PARAM_TYPE_PAL,
462 .ranges = tuner_lg_pal_ranges,
463 .count = ARRAY_SIZE(tuner_lg_pal_ranges),
464 },
465};
466
467/* 30-39 */
468/* ------------ TUNER_TEMIC_4009FN5_MULTI_PAL_FM - TEMIC PAL ------------ */
469
470static struct tuner_params tuner_temic_4009_fn5_multi_pal_fm_params[] = {
471 {
472 .type = TUNER_PARAM_TYPE_PAL,
473 .ranges = tuner_temic_4009f_5_pal_ranges,
474 .count = ARRAY_SIZE(tuner_temic_4009f_5_pal_ranges),
475 },
476};
477
478/* ------------ TUNER_SHARP_2U5JF5540_NTSC - SHARP NTSC ------------ */
479
480static struct tuner_range tuner_sharp_2u5jf5540_ntsc_ranges[] = {
481 { 16 * 137.25 /*MHz*/, 0x8e, 0x01, },
482 { 16 * 317.25 /*MHz*/, 0x8e, 0x02, },
483 { 16 * 999.99 , 0x8e, 0x08, },
484};
485
486static struct tuner_params tuner_sharp_2u5jf5540_params[] = {
487 {
488 .type = TUNER_PARAM_TYPE_NTSC,
489 .ranges = tuner_sharp_2u5jf5540_ntsc_ranges,
490 .count = ARRAY_SIZE(tuner_sharp_2u5jf5540_ntsc_ranges),
491 },
492};
493
494/* ------------ TUNER_Samsung_PAL_TCPM9091PD27 - Samsung PAL ------------ */
495
496static struct tuner_range tuner_samsung_pal_tcpm9091pd27_ranges[] = {
497 { 16 * 169 /*MHz*/, 0x8e, 0xa0, },
498 { 16 * 464 /*MHz*/, 0x8e, 0x90, },
499 { 16 * 999.99 , 0x8e, 0x30, },
500};
501
502static struct tuner_params tuner_samsung_pal_tcpm9091pd27_params[] = {
503 {
504 .type = TUNER_PARAM_TYPE_PAL,
505 .ranges = tuner_samsung_pal_tcpm9091pd27_ranges,
506 .count = ARRAY_SIZE(tuner_samsung_pal_tcpm9091pd27_ranges),
507 },
508};
509
510/* ------------ TUNER_TEMIC_4106FH5 - TEMIC PAL ------------ */
511
512static struct tuner_params tuner_temic_4106fh5_params[] = {
513 {
514 .type = TUNER_PARAM_TYPE_PAL,
515 .ranges = tuner_temic_4009f_5_pal_ranges,
516 .count = ARRAY_SIZE(tuner_temic_4009f_5_pal_ranges),
517 },
518};
519
520/* ------------ TUNER_TEMIC_4012FY5 - TEMIC PAL ------------ */
521
522static struct tuner_params tuner_temic_4012fy5_params[] = {
523 {
524 .type = TUNER_PARAM_TYPE_PAL,
525 .ranges = tuner_temic_pal_ranges,
526 .count = ARRAY_SIZE(tuner_temic_pal_ranges),
527 },
528};
529
530/* ------------ TUNER_TEMIC_4136FY5 - TEMIC NTSC ------------ */
531
532static struct tuner_params tuner_temic_4136_fy5_params[] = {
533 {
534 .type = TUNER_PARAM_TYPE_NTSC,
535 .ranges = tuner_temic_4x3x_f_5_ntsc_ranges,
536 .count = ARRAY_SIZE(tuner_temic_4x3x_f_5_ntsc_ranges),
537 },
538};
539
540/* ------------ TUNER_LG_PAL_NEW_TAPC - LGINNOTEK PAL ------------ */
541
542static struct tuner_range tuner_lg_new_tapc_ranges[] = {
543 { 16 * 170.00 /*MHz*/, 0x8e, 0x01, },
544 { 16 * 450.00 /*MHz*/, 0x8e, 0x02, },
545 { 16 * 999.99 , 0x8e, 0x08, },
546};
547
548static struct tuner_params tuner_lg_pal_new_tapc_params[] = {
549 {
550 .type = TUNER_PARAM_TYPE_PAL,
551 .ranges = tuner_lg_new_tapc_ranges,
552 .count = ARRAY_SIZE(tuner_lg_new_tapc_ranges),
553 },
554};
555
556/* ------------ TUNER_PHILIPS_FM1216ME_MK3 - Philips PAL ------------ */
557
558static struct tuner_range tuner_fm1216me_mk3_pal_ranges[] = {
559 { 16 * 158.00 /*MHz*/, 0x8e, 0x01, },
560 { 16 * 442.00 /*MHz*/, 0x8e, 0x02, },
561 { 16 * 999.99 , 0x8e, 0x04, },
562};
563
564static struct tuner_params tuner_fm1216me_mk3_params[] = {
565 {
566 .type = TUNER_PARAM_TYPE_PAL,
567 .ranges = tuner_fm1216me_mk3_pal_ranges,
568 .count = ARRAY_SIZE(tuner_fm1216me_mk3_pal_ranges),
569 .cb_first_if_lower_freq = 1,
570 .has_tda9887 = 1,
571 .port1_active = 1,
572 .port2_active = 1,
573 .port2_invert_for_secam_lc = 1,
574 .port1_fm_high_sensitivity = 1,
575 .default_top_mid = -2,
576 .default_top_secam_mid = -2,
577 .default_top_secam_high = -2,
578 },
579};
580
581/* ------------ TUNER_PHILIPS_FM1216MK5 - Philips PAL ------------ */
582
583static struct tuner_range tuner_fm1216mk5_pal_ranges[] = {
584 { 16 * 158.00 /*MHz*/, 0xce, 0x01, },
585 { 16 * 441.00 /*MHz*/, 0xce, 0x02, },
586 { 16 * 864.00 , 0xce, 0x04, },
587};
588
589static struct tuner_params tuner_fm1216mk5_params[] = {
590 {
591 .type = TUNER_PARAM_TYPE_PAL,
592 .ranges = tuner_fm1216mk5_pal_ranges,
593 .count = ARRAY_SIZE(tuner_fm1216mk5_pal_ranges),
594 .cb_first_if_lower_freq = 1,
595 .has_tda9887 = 1,
596 .port1_active = 1,
597 .port2_active = 1,
598 .port2_invert_for_secam_lc = 1,
599 .port1_fm_high_sensitivity = 1,
600 .default_top_mid = -2,
601 .default_top_secam_mid = -2,
602 .default_top_secam_high = -2,
603 },
604};
605
606/* ------------ TUNER_LG_NTSC_NEW_TAPC - LGINNOTEK NTSC ------------ */
607
608static struct tuner_params tuner_lg_ntsc_new_tapc_params[] = {
609 {
610 .type = TUNER_PARAM_TYPE_NTSC,
611 .ranges = tuner_lg_new_tapc_ranges,
612 .count = ARRAY_SIZE(tuner_lg_new_tapc_ranges),
613 },
614};
615
616/* 40-49 */
617/* ------------ TUNER_HITACHI_NTSC - HITACHI NTSC ------------ */
618
619static struct tuner_params tuner_hitachi_ntsc_params[] = {
620 {
621 .type = TUNER_PARAM_TYPE_NTSC,
622 .ranges = tuner_lg_new_tapc_ranges,
623 .count = ARRAY_SIZE(tuner_lg_new_tapc_ranges),
624 },
625};
626
627/* ------------ TUNER_PHILIPS_PAL_MK - Philips PAL ------------ */
628
629static struct tuner_range tuner_philips_pal_mk_pal_ranges[] = {
630 { 16 * 140.25 /*MHz*/, 0x8e, 0x01, },
631 { 16 * 463.25 /*MHz*/, 0x8e, 0xc2, },
632 { 16 * 999.99 , 0x8e, 0xcf, },
633};
634
635static struct tuner_params tuner_philips_pal_mk_params[] = {
636 {
637 .type = TUNER_PARAM_TYPE_PAL,
638 .ranges = tuner_philips_pal_mk_pal_ranges,
639 .count = ARRAY_SIZE(tuner_philips_pal_mk_pal_ranges),
640 },
641};
642
643/* ---- TUNER_PHILIPS_FCV1236D - Philips FCV1236D (ATSC/NTSC) ---- */
644
645static struct tuner_range tuner_philips_fcv1236d_ntsc_ranges[] = {
646 { 16 * 157.25 /*MHz*/, 0x8e, 0xa2, },
647 { 16 * 451.25 /*MHz*/, 0x8e, 0x92, },
648 { 16 * 999.99 , 0x8e, 0x32, },
649};
650
651static struct tuner_range tuner_philips_fcv1236d_atsc_ranges[] = {
652 { 16 * 159.00 /*MHz*/, 0x8e, 0xa0, },
653 { 16 * 453.00 /*MHz*/, 0x8e, 0x90, },
654 { 16 * 999.99 , 0x8e, 0x30, },
655};
656
657static struct tuner_params tuner_philips_fcv1236d_params[] = {
658 {
659 .type = TUNER_PARAM_TYPE_NTSC,
660 .ranges = tuner_philips_fcv1236d_ntsc_ranges,
661 .count = ARRAY_SIZE(tuner_philips_fcv1236d_ntsc_ranges),
662 },
663 {
664 .type = TUNER_PARAM_TYPE_DIGITAL,
665 .ranges = tuner_philips_fcv1236d_atsc_ranges,
666 .count = ARRAY_SIZE(tuner_philips_fcv1236d_atsc_ranges),
667 .iffreq = 16 * 44.00,
668 },
669};
670
671/* ------------ TUNER_PHILIPS_FM1236_MK3 - Philips NTSC ------------ */
672
673static struct tuner_range tuner_fm1236_mk3_ntsc_ranges[] = {
674 { 16 * 160.00 /*MHz*/, 0x8e, 0x01, },
675 { 16 * 442.00 /*MHz*/, 0x8e, 0x02, },
676 { 16 * 999.99 , 0x8e, 0x04, },
677};
678
679static struct tuner_params tuner_fm1236_mk3_params[] = {
680 {
681 .type = TUNER_PARAM_TYPE_NTSC,
682 .ranges = tuner_fm1236_mk3_ntsc_ranges,
683 .count = ARRAY_SIZE(tuner_fm1236_mk3_ntsc_ranges),
684 .cb_first_if_lower_freq = 1,
685 .has_tda9887 = 1,
686 .port1_active = 1,
687 .port2_active = 1,
688 .port1_fm_high_sensitivity = 1,
689 },
690};
691
692/* ------------ TUNER_PHILIPS_4IN1 - Philips NTSC ------------ */
693
694static struct tuner_params tuner_philips_4in1_params[] = {
695 {
696 .type = TUNER_PARAM_TYPE_NTSC,
697 .ranges = tuner_fm1236_mk3_ntsc_ranges,
698 .count = ARRAY_SIZE(tuner_fm1236_mk3_ntsc_ranges),
699 },
700};
701
702/* ------------ TUNER_MICROTUNE_4049FM5 - Microtune PAL ------------ */
703
704static struct tuner_params tuner_microtune_4049_fm5_params[] = {
705 {
706 .type = TUNER_PARAM_TYPE_PAL,
707 .ranges = tuner_temic_4009f_5_pal_ranges,
708 .count = ARRAY_SIZE(tuner_temic_4009f_5_pal_ranges),
709 .has_tda9887 = 1,
710 .port1_invert_for_secam_lc = 1,
711 .default_pll_gating_18 = 1,
712 .fm_gain_normal=1,
713 .radio_if = 1, /* 33.3 MHz */
714 },
715};
716
717/* ------------ TUNER_PANASONIC_VP27 - Panasonic NTSC ------------ */
718
719static struct tuner_range tuner_panasonic_vp27_ntsc_ranges[] = {
720 { 16 * 160.00 /*MHz*/, 0xce, 0x01, },
721 { 16 * 454.00 /*MHz*/, 0xce, 0x02, },
722 { 16 * 999.99 , 0xce, 0x08, },
723};
724
725static struct tuner_params tuner_panasonic_vp27_params[] = {
726 {
727 .type = TUNER_PARAM_TYPE_NTSC,
728 .ranges = tuner_panasonic_vp27_ntsc_ranges,
729 .count = ARRAY_SIZE(tuner_panasonic_vp27_ntsc_ranges),
730 .has_tda9887 = 1,
731 .intercarrier_mode = 1,
732 .default_top_low = -3,
733 .default_top_mid = -3,
734 .default_top_high = -3,
735 },
736};
737
738/* ------------ TUNER_TNF_8831BGFF - Philips PAL ------------ */
739
740static struct tuner_range tuner_tnf_8831bgff_pal_ranges[] = {
741 { 16 * 161.25 /*MHz*/, 0x8e, 0xa0, },
742 { 16 * 463.25 /*MHz*/, 0x8e, 0x90, },
743 { 16 * 999.99 , 0x8e, 0x30, },
744};
745
746static struct tuner_params tuner_tnf_8831bgff_params[] = {
747 {
748 .type = TUNER_PARAM_TYPE_PAL,
749 .ranges = tuner_tnf_8831bgff_pal_ranges,
750 .count = ARRAY_SIZE(tuner_tnf_8831bgff_pal_ranges),
751 },
752};
753
754/* ------------ TUNER_MICROTUNE_4042FI5 - Microtune NTSC ------------ */
755
756static struct tuner_range tuner_microtune_4042fi5_ntsc_ranges[] = {
757 { 16 * 162.00 /*MHz*/, 0x8e, 0xa2, },
758 { 16 * 457.00 /*MHz*/, 0x8e, 0x94, },
759 { 16 * 999.99 , 0x8e, 0x31, },
760};
761
762static struct tuner_range tuner_microtune_4042fi5_atsc_ranges[] = {
763 { 16 * 162.00 /*MHz*/, 0x8e, 0xa1, },
764 { 16 * 457.00 /*MHz*/, 0x8e, 0x91, },
765 { 16 * 999.99 , 0x8e, 0x31, },
766};
767
768static struct tuner_params tuner_microtune_4042fi5_params[] = {
769 {
770 .type = TUNER_PARAM_TYPE_NTSC,
771 .ranges = tuner_microtune_4042fi5_ntsc_ranges,
772 .count = ARRAY_SIZE(tuner_microtune_4042fi5_ntsc_ranges),
773 },
774 {
775 .type = TUNER_PARAM_TYPE_DIGITAL,
776 .ranges = tuner_microtune_4042fi5_atsc_ranges,
777 .count = ARRAY_SIZE(tuner_microtune_4042fi5_atsc_ranges),
778 .iffreq = 16 * 44.00 /*MHz*/,
779 },
780};
781
782/* 50-59 */
783/* ------------ TUNER_TCL_2002N - TCL NTSC ------------ */
784
785static struct tuner_range tuner_tcl_2002n_ntsc_ranges[] = {
786 { 16 * 172.00 /*MHz*/, 0x8e, 0x01, },
787 { 16 * 448.00 /*MHz*/, 0x8e, 0x02, },
788 { 16 * 999.99 , 0x8e, 0x08, },
789};
790
791static struct tuner_params tuner_tcl_2002n_params[] = {
792 {
793 .type = TUNER_PARAM_TYPE_NTSC,
794 .ranges = tuner_tcl_2002n_ntsc_ranges,
795 .count = ARRAY_SIZE(tuner_tcl_2002n_ntsc_ranges),
796 .cb_first_if_lower_freq = 1,
797 },
798};
799
800/* ------------ TUNER_PHILIPS_FM1256_IH3 - Philips PAL ------------ */
801
802static struct tuner_params tuner_philips_fm1256_ih3_params[] = {
803 {
804 .type = TUNER_PARAM_TYPE_PAL,
805 .ranges = tuner_fm1236_mk3_ntsc_ranges,
806 .count = ARRAY_SIZE(tuner_fm1236_mk3_ntsc_ranges),
807 .radio_if = 1, /* 33.3 MHz */
808 },
809};
810
811/* ------------ TUNER_THOMSON_DTT7610 - THOMSON ATSC ------------ */
812
813/* single range used for both ntsc and atsc */
814static struct tuner_range tuner_thomson_dtt7610_ntsc_ranges[] = {
815 { 16 * 157.25 /*MHz*/, 0x8e, 0x39, },
816 { 16 * 454.00 /*MHz*/, 0x8e, 0x3a, },
817 { 16 * 999.99 , 0x8e, 0x3c, },
818};
819
820static struct tuner_params tuner_thomson_dtt7610_params[] = {
821 {
822 .type = TUNER_PARAM_TYPE_NTSC,
823 .ranges = tuner_thomson_dtt7610_ntsc_ranges,
824 .count = ARRAY_SIZE(tuner_thomson_dtt7610_ntsc_ranges),
825 },
826 {
827 .type = TUNER_PARAM_TYPE_DIGITAL,
828 .ranges = tuner_thomson_dtt7610_ntsc_ranges,
829 .count = ARRAY_SIZE(tuner_thomson_dtt7610_ntsc_ranges),
830 .iffreq = 16 * 44.00 /*MHz*/,
831 },
832};
833
834/* ------------ TUNER_PHILIPS_FQ1286 - Philips NTSC ------------ */
835
836static struct tuner_range tuner_philips_fq1286_ntsc_ranges[] = {
837 { 16 * 160.00 /*MHz*/, 0x8e, 0x41, },
838 { 16 * 454.00 /*MHz*/, 0x8e, 0x42, },
839 { 16 * 999.99 , 0x8e, 0x04, },
840};
841
842static struct tuner_params tuner_philips_fq1286_params[] = {
843 {
844 .type = TUNER_PARAM_TYPE_NTSC,
845 .ranges = tuner_philips_fq1286_ntsc_ranges,
846 .count = ARRAY_SIZE(tuner_philips_fq1286_ntsc_ranges),
847 },
848};
849
850/* ------------ TUNER_TCL_2002MB - TCL PAL ------------ */
851
852static struct tuner_range tuner_tcl_2002mb_pal_ranges[] = {
853 { 16 * 170.00 /*MHz*/, 0xce, 0x01, },
854 { 16 * 450.00 /*MHz*/, 0xce, 0x02, },
855 { 16 * 999.99 , 0xce, 0x08, },
856};
857
858static struct tuner_params tuner_tcl_2002mb_params[] = {
859 {
860 .type = TUNER_PARAM_TYPE_PAL,
861 .ranges = tuner_tcl_2002mb_pal_ranges,
862 .count = ARRAY_SIZE(tuner_tcl_2002mb_pal_ranges),
863 },
864};
865
866/* ------------ TUNER_PHILIPS_FQ1216AME_MK4 - Philips PAL ------------ */
867
868static struct tuner_range tuner_philips_fq12_6a___mk4_pal_ranges[] = {
869 { 16 * 160.00 /*MHz*/, 0xce, 0x01, },
870 { 16 * 442.00 /*MHz*/, 0xce, 0x02, },
871 { 16 * 999.99 , 0xce, 0x04, },
872};
873
874static struct tuner_params tuner_philips_fq1216ame_mk4_params[] = {
875 {
876 .type = TUNER_PARAM_TYPE_PAL,
877 .ranges = tuner_philips_fq12_6a___mk4_pal_ranges,
878 .count = ARRAY_SIZE(tuner_philips_fq12_6a___mk4_pal_ranges),
879 .has_tda9887 = 1,
880 .port1_active = 1,
881 .port2_invert_for_secam_lc = 1,
882 .default_top_mid = -2,
883 .default_top_secam_low = -2,
884 .default_top_secam_mid = -2,
885 .default_top_secam_high = -2,
886 },
887};
888
889/* ------------ TUNER_PHILIPS_FQ1236A_MK4 - Philips NTSC ------------ */
890
891static struct tuner_params tuner_philips_fq1236a_mk4_params[] = {
892 {
893 .type = TUNER_PARAM_TYPE_NTSC,
894 .ranges = tuner_fm1236_mk3_ntsc_ranges,
895 .count = ARRAY_SIZE(tuner_fm1236_mk3_ntsc_ranges),
896 },
897};
898
899/* ------------ TUNER_YMEC_TVF_8531MF - Philips NTSC ------------ */
900
901static struct tuner_params tuner_ymec_tvf_8531mf_params[] = {
902 {
903 .type = TUNER_PARAM_TYPE_NTSC,
904 .ranges = tuner_philips_ntsc_m_ranges,
905 .count = ARRAY_SIZE(tuner_philips_ntsc_m_ranges),
906 },
907};
908
909/* ------------ TUNER_YMEC_TVF_5533MF - Philips NTSC ------------ */
910
911static struct tuner_range tuner_ymec_tvf_5533mf_ntsc_ranges[] = {
912 { 16 * 160.00 /*MHz*/, 0x8e, 0x01, },
913 { 16 * 454.00 /*MHz*/, 0x8e, 0x02, },
914 { 16 * 999.99 , 0x8e, 0x04, },
915};
916
917static struct tuner_params tuner_ymec_tvf_5533mf_params[] = {
918 {
919 .type = TUNER_PARAM_TYPE_NTSC,
920 .ranges = tuner_ymec_tvf_5533mf_ntsc_ranges,
921 .count = ARRAY_SIZE(tuner_ymec_tvf_5533mf_ntsc_ranges),
922 },
923};
924
925/* 60-69 */
926/* ------------ TUNER_THOMSON_DTT761X - THOMSON ATSC ------------ */
927/* DTT 7611 7611A 7612 7613 7613A 7614 7615 7615A */
928
929static struct tuner_range tuner_thomson_dtt761x_ntsc_ranges[] = {
930 { 16 * 145.25 /*MHz*/, 0x8e, 0x39, },
931 { 16 * 415.25 /*MHz*/, 0x8e, 0x3a, },
932 { 16 * 999.99 , 0x8e, 0x3c, },
933};
934
935static struct tuner_range tuner_thomson_dtt761x_atsc_ranges[] = {
936 { 16 * 147.00 /*MHz*/, 0x8e, 0x39, },
937 { 16 * 417.00 /*MHz*/, 0x8e, 0x3a, },
938 { 16 * 999.99 , 0x8e, 0x3c, },
939};
940
941static struct tuner_params tuner_thomson_dtt761x_params[] = {
942 {
943 .type = TUNER_PARAM_TYPE_NTSC,
944 .ranges = tuner_thomson_dtt761x_ntsc_ranges,
945 .count = ARRAY_SIZE(tuner_thomson_dtt761x_ntsc_ranges),
946 .has_tda9887 = 1,
947 .fm_gain_normal = 1,
948 .radio_if = 2, /* 41.3 MHz */
949 },
950 {
951 .type = TUNER_PARAM_TYPE_DIGITAL,
952 .ranges = tuner_thomson_dtt761x_atsc_ranges,
953 .count = ARRAY_SIZE(tuner_thomson_dtt761x_atsc_ranges),
954 .iffreq = 16 * 44.00, /*MHz*/
955 },
956};
957
958/* ------------ TUNER_TENA_9533_DI - Philips PAL ------------ */
959
960static struct tuner_range tuner_tena_9533_di_pal_ranges[] = {
961 { 16 * 160.25 /*MHz*/, 0x8e, 0x01, },
962 { 16 * 464.25 /*MHz*/, 0x8e, 0x02, },
963 { 16 * 999.99 , 0x8e, 0x04, },
964};
965
966static struct tuner_params tuner_tena_9533_di_params[] = {
967 {
968 .type = TUNER_PARAM_TYPE_PAL,
969 .ranges = tuner_tena_9533_di_pal_ranges,
970 .count = ARRAY_SIZE(tuner_tena_9533_di_pal_ranges),
971 },
972};
973
974/* ------------ TUNER_TENA_TNF_5337 - Tena tnf5337MFD STD M/N ------------ */
975
976static struct tuner_range tuner_tena_tnf_5337_ntsc_ranges[] = {
977 { 16 * 166.25 /*MHz*/, 0x86, 0x01, },
978 { 16 * 466.25 /*MHz*/, 0x86, 0x02, },
979 { 16 * 999.99 , 0x86, 0x08, },
980};
981
982static struct tuner_params tuner_tena_tnf_5337_params[] = {
983 {
984 .type = TUNER_PARAM_TYPE_NTSC,
985 .ranges = tuner_tena_tnf_5337_ntsc_ranges,
986 .count = ARRAY_SIZE(tuner_tena_tnf_5337_ntsc_ranges),
987 },
988};
989
990/* ------------ TUNER_PHILIPS_FMD1216ME(X)_MK3 - Philips PAL ------------ */
991
992static struct tuner_range tuner_philips_fmd1216me_mk3_pal_ranges[] = {
993 { 16 * 160.00 /*MHz*/, 0x86, 0x51, },
994 { 16 * 442.00 /*MHz*/, 0x86, 0x52, },
995 { 16 * 999.99 , 0x86, 0x54, },
996};
997
998static struct tuner_range tuner_philips_fmd1216me_mk3_dvb_ranges[] = {
999 { 16 * 143.87 /*MHz*/, 0xbc, 0x41 },
1000 { 16 * 158.87 /*MHz*/, 0xf4, 0x41 },
1001 { 16 * 329.87 /*MHz*/, 0xbc, 0x42 },
1002 { 16 * 441.87 /*MHz*/, 0xf4, 0x42 },
1003 { 16 * 625.87 /*MHz*/, 0xbc, 0x44 },
1004 { 16 * 803.87 /*MHz*/, 0xf4, 0x44 },
1005 { 16 * 999.99 , 0xfc, 0x44 },
1006};
1007
1008static struct tuner_params tuner_philips_fmd1216me_mk3_params[] = {
1009 {
1010 .type = TUNER_PARAM_TYPE_PAL,
1011 .ranges = tuner_philips_fmd1216me_mk3_pal_ranges,
1012 .count = ARRAY_SIZE(tuner_philips_fmd1216me_mk3_pal_ranges),
1013 .has_tda9887 = 1,
1014 .port1_active = 1,
1015 .port2_active = 1,
1016 .port2_fm_high_sensitivity = 1,
1017 .port2_invert_for_secam_lc = 1,
1018 .port1_set_for_fm_mono = 1,
1019 },
1020 {
1021 .type = TUNER_PARAM_TYPE_DIGITAL,
1022 .ranges = tuner_philips_fmd1216me_mk3_dvb_ranges,
1023 .count = ARRAY_SIZE(tuner_philips_fmd1216me_mk3_dvb_ranges),
1024 .iffreq = 16 * 36.125, /*MHz*/
1025 },
1026};
1027
1028static struct tuner_params tuner_philips_fmd1216mex_mk3_params[] = {
1029 {
1030 .type = TUNER_PARAM_TYPE_PAL,
1031 .ranges = tuner_philips_fmd1216me_mk3_pal_ranges,
1032 .count = ARRAY_SIZE(tuner_philips_fmd1216me_mk3_pal_ranges),
1033 .has_tda9887 = 1,
1034 .port1_active = 1,
1035 .port2_active = 1,
1036 .port2_fm_high_sensitivity = 1,
1037 .port2_invert_for_secam_lc = 1,
1038 .port1_set_for_fm_mono = 1,
1039 .radio_if = 1,
1040 .fm_gain_normal = 1,
1041 },
1042 {
1043 .type = TUNER_PARAM_TYPE_DIGITAL,
1044 .ranges = tuner_philips_fmd1216me_mk3_dvb_ranges,
1045 .count = ARRAY_SIZE(tuner_philips_fmd1216me_mk3_dvb_ranges),
1046 .iffreq = 16 * 36.125, /*MHz*/
1047 },
1048};
1049
1050/* ------ TUNER_LG_TDVS_H06XF - LG INNOTEK / INFINEON ATSC ----- */
1051
1052static struct tuner_range tuner_tua6034_ntsc_ranges[] = {
1053 { 16 * 165.00 /*MHz*/, 0x8e, 0x01 },
1054 { 16 * 450.00 /*MHz*/, 0x8e, 0x02 },
1055 { 16 * 999.99 , 0x8e, 0x04 },
1056};
1057
1058static struct tuner_range tuner_tua6034_atsc_ranges[] = {
1059 { 16 * 165.00 /*MHz*/, 0xce, 0x01 },
1060 { 16 * 450.00 /*MHz*/, 0xce, 0x02 },
1061 { 16 * 999.99 , 0xce, 0x04 },
1062};
1063
1064static struct tuner_params tuner_lg_tdvs_h06xf_params[] = {
1065 {
1066 .type = TUNER_PARAM_TYPE_NTSC,
1067 .ranges = tuner_tua6034_ntsc_ranges,
1068 .count = ARRAY_SIZE(tuner_tua6034_ntsc_ranges),
1069 },
1070 {
1071 .type = TUNER_PARAM_TYPE_DIGITAL,
1072 .ranges = tuner_tua6034_atsc_ranges,
1073 .count = ARRAY_SIZE(tuner_tua6034_atsc_ranges),
1074 .iffreq = 16 * 44.00,
1075 },
1076};
1077
1078/* ------------ TUNER_YMEC_TVF66T5_B_DFF - Philips PAL ------------ */
1079
1080static struct tuner_range tuner_ymec_tvf66t5_b_dff_pal_ranges[] = {
1081 { 16 * 160.25 /*MHz*/, 0x8e, 0x01, },
1082 { 16 * 464.25 /*MHz*/, 0x8e, 0x02, },
1083 { 16 * 999.99 , 0x8e, 0x08, },
1084};
1085
1086static struct tuner_params tuner_ymec_tvf66t5_b_dff_params[] = {
1087 {
1088 .type = TUNER_PARAM_TYPE_PAL,
1089 .ranges = tuner_ymec_tvf66t5_b_dff_pal_ranges,
1090 .count = ARRAY_SIZE(tuner_ymec_tvf66t5_b_dff_pal_ranges),
1091 },
1092};
1093
1094/* ------------ TUNER_LG_NTSC_TALN_MINI - LGINNOTEK NTSC ------------ */
1095
1096static struct tuner_range tuner_lg_taln_ntsc_ranges[] = {
1097 { 16 * 137.25 /*MHz*/, 0x8e, 0x01, },
1098 { 16 * 373.25 /*MHz*/, 0x8e, 0x02, },
1099 { 16 * 999.99 , 0x8e, 0x08, },
1100};
1101
1102static struct tuner_range tuner_lg_taln_pal_secam_ranges[] = {
1103 { 16 * 150.00 /*MHz*/, 0x8e, 0x01, },
1104 { 16 * 425.00 /*MHz*/, 0x8e, 0x02, },
1105 { 16 * 999.99 , 0x8e, 0x08, },
1106};
1107
1108static struct tuner_params tuner_lg_taln_params[] = {
1109 {
1110 .type = TUNER_PARAM_TYPE_NTSC,
1111 .ranges = tuner_lg_taln_ntsc_ranges,
1112 .count = ARRAY_SIZE(tuner_lg_taln_ntsc_ranges),
1113 },{
1114 .type = TUNER_PARAM_TYPE_PAL,
1115 .ranges = tuner_lg_taln_pal_secam_ranges,
1116 .count = ARRAY_SIZE(tuner_lg_taln_pal_secam_ranges),
1117 },
1118};
1119
1120/* ------------ TUNER_PHILIPS_TD1316 - Philips PAL ------------ */
1121
1122static struct tuner_range tuner_philips_td1316_pal_ranges[] = {
1123 { 16 * 160.00 /*MHz*/, 0xc8, 0xa1, },
1124 { 16 * 442.00 /*MHz*/, 0xc8, 0xa2, },
1125 { 16 * 999.99 , 0xc8, 0xa4, },
1126};
1127
1128static struct tuner_range tuner_philips_td1316_dvb_ranges[] = {
1129 { 16 * 93.834 /*MHz*/, 0xca, 0x60, },
1130 { 16 * 123.834 /*MHz*/, 0xca, 0xa0, },
1131 { 16 * 163.834 /*MHz*/, 0xca, 0xc0, },
1132 { 16 * 253.834 /*MHz*/, 0xca, 0x60, },
1133 { 16 * 383.834 /*MHz*/, 0xca, 0xa0, },
1134 { 16 * 443.834 /*MHz*/, 0xca, 0xc0, },
1135 { 16 * 583.834 /*MHz*/, 0xca, 0x60, },
1136 { 16 * 793.834 /*MHz*/, 0xca, 0xa0, },
1137 { 16 * 999.999 , 0xca, 0xe0, },
1138};
1139
1140static struct tuner_params tuner_philips_td1316_params[] = {
1141 {
1142 .type = TUNER_PARAM_TYPE_PAL,
1143 .ranges = tuner_philips_td1316_pal_ranges,
1144 .count = ARRAY_SIZE(tuner_philips_td1316_pal_ranges),
1145 },
1146 {
1147 .type = TUNER_PARAM_TYPE_DIGITAL,
1148 .ranges = tuner_philips_td1316_dvb_ranges,
1149 .count = ARRAY_SIZE(tuner_philips_td1316_dvb_ranges),
1150 .iffreq = 16 * 36.166667 /*MHz*/,
1151 },
1152};
1153
1154/* ------------ TUNER_PHILIPS_TUV1236D - Philips ATSC ------------ */
1155
1156static struct tuner_range tuner_tuv1236d_ntsc_ranges[] = {
1157 { 16 * 157.25 /*MHz*/, 0xce, 0x01, },
1158 { 16 * 454.00 /*MHz*/, 0xce, 0x02, },
1159 { 16 * 999.99 , 0xce, 0x04, },
1160};
1161
1162static struct tuner_range tuner_tuv1236d_atsc_ranges[] = {
1163 { 16 * 157.25 /*MHz*/, 0xc6, 0x41, },
1164 { 16 * 454.00 /*MHz*/, 0xc6, 0x42, },
1165 { 16 * 999.99 , 0xc6, 0x44, },
1166};
1167
1168static struct tuner_params tuner_tuv1236d_params[] = {
1169 {
1170 .type = TUNER_PARAM_TYPE_NTSC,
1171 .ranges = tuner_tuv1236d_ntsc_ranges,
1172 .count = ARRAY_SIZE(tuner_tuv1236d_ntsc_ranges),
1173 },
1174 {
1175 .type = TUNER_PARAM_TYPE_DIGITAL,
1176 .ranges = tuner_tuv1236d_atsc_ranges,
1177 .count = ARRAY_SIZE(tuner_tuv1236d_atsc_ranges),
1178 .iffreq = 16 * 44.00,
1179 },
1180};
1181
1182/* ------------ TUNER_TNF_xxx5 - Texas Instruments--------- */
1183/* This is known to work with Tenna TVF58t5-MFF and TVF5835 MFF
1184 * but it is expected to work also with other Tenna/Ymec
1185 * models based on TI SN 761677 chip on both PAL and NTSC
1186 */
1187
1188static struct tuner_range tuner_tnf_5335_d_if_pal_ranges[] = {
1189 { 16 * 168.25 /*MHz*/, 0x8e, 0x01, },
1190 { 16 * 471.25 /*MHz*/, 0x8e, 0x02, },
1191 { 16 * 999.99 , 0x8e, 0x08, },
1192};
1193
1194static struct tuner_range tuner_tnf_5335mf_ntsc_ranges[] = {
1195 { 16 * 169.25 /*MHz*/, 0x8e, 0x01, },
1196 { 16 * 469.25 /*MHz*/, 0x8e, 0x02, },
1197 { 16 * 999.99 , 0x8e, 0x08, },
1198};
1199
1200static struct tuner_params tuner_tnf_5335mf_params[] = {
1201 {
1202 .type = TUNER_PARAM_TYPE_NTSC,
1203 .ranges = tuner_tnf_5335mf_ntsc_ranges,
1204 .count = ARRAY_SIZE(tuner_tnf_5335mf_ntsc_ranges),
1205 },
1206 {
1207 .type = TUNER_PARAM_TYPE_PAL,
1208 .ranges = tuner_tnf_5335_d_if_pal_ranges,
1209 .count = ARRAY_SIZE(tuner_tnf_5335_d_if_pal_ranges),
1210 },
1211};
1212
1213/* 70-79 */
1214/* ------------ TUNER_SAMSUNG_TCPN_2121P30A - Samsung NTSC ------------ */
1215
1216/* '+ 4' turns on the Low Noise Amplifier */
1217static struct tuner_range tuner_samsung_tcpn_2121p30a_ntsc_ranges[] = {
1218 { 16 * 130.00 /*MHz*/, 0xce, 0x01 + 4, },
1219 { 16 * 364.50 /*MHz*/, 0xce, 0x02 + 4, },
1220 { 16 * 999.99 , 0xce, 0x08 + 4, },
1221};
1222
1223static struct tuner_params tuner_samsung_tcpn_2121p30a_params[] = {
1224 {
1225 .type = TUNER_PARAM_TYPE_NTSC,
1226 .ranges = tuner_samsung_tcpn_2121p30a_ntsc_ranges,
1227 .count = ARRAY_SIZE(tuner_samsung_tcpn_2121p30a_ntsc_ranges),
1228 },
1229};
1230
1231/* ------------ TUNER_THOMSON_FE6600 - DViCO Hybrid PAL ------------ */
1232
1233static struct tuner_range tuner_thomson_fe6600_pal_ranges[] = {
1234 { 16 * 160.00 /*MHz*/, 0xfe, 0x11, },
1235 { 16 * 442.00 /*MHz*/, 0xf6, 0x12, },
1236 { 16 * 999.99 , 0xf6, 0x18, },
1237};
1238
1239static struct tuner_range tuner_thomson_fe6600_dvb_ranges[] = {
1240 { 16 * 250.00 /*MHz*/, 0xb4, 0x12, },
1241 { 16 * 455.00 /*MHz*/, 0xfe, 0x11, },
1242 { 16 * 775.50 /*MHz*/, 0xbc, 0x18, },
1243 { 16 * 999.99 , 0xf4, 0x18, },
1244};
1245
1246static struct tuner_params tuner_thomson_fe6600_params[] = {
1247 {
1248 .type = TUNER_PARAM_TYPE_PAL,
1249 .ranges = tuner_thomson_fe6600_pal_ranges,
1250 .count = ARRAY_SIZE(tuner_thomson_fe6600_pal_ranges),
1251 },
1252 {
1253 .type = TUNER_PARAM_TYPE_DIGITAL,
1254 .ranges = tuner_thomson_fe6600_dvb_ranges,
1255 .count = ARRAY_SIZE(tuner_thomson_fe6600_dvb_ranges),
1256 .iffreq = 16 * 36.125 /*MHz*/,
1257 },
1258};
1259
1260/* ------------ TUNER_SAMSUNG_TCPG_6121P30A - Samsung PAL ------------ */
1261
1262/* '+ 4' turns on the Low Noise Amplifier */
1263static struct tuner_range tuner_samsung_tcpg_6121p30a_pal_ranges[] = {
1264 { 16 * 146.25 /*MHz*/, 0xce, 0x01 + 4, },
1265 { 16 * 428.50 /*MHz*/, 0xce, 0x02 + 4, },
1266 { 16 * 999.99 , 0xce, 0x08 + 4, },
1267};
1268
1269static struct tuner_params tuner_samsung_tcpg_6121p30a_params[] = {
1270 {
1271 .type = TUNER_PARAM_TYPE_PAL,
1272 .ranges = tuner_samsung_tcpg_6121p30a_pal_ranges,
1273 .count = ARRAY_SIZE(tuner_samsung_tcpg_6121p30a_pal_ranges),
1274 .has_tda9887 = 1,
1275 .port1_active = 1,
1276 .port2_active = 1,
1277 .port2_invert_for_secam_lc = 1,
1278 },
1279};
1280
1281/* ------------ TUNER_TCL_MF02GIP-5N-E - TCL MF02GIP-5N ------------ */
1282
1283static struct tuner_range tuner_tcl_mf02gip_5n_ntsc_ranges[] = {
1284 { 16 * 172.00 /*MHz*/, 0x8e, 0x01, },
1285 { 16 * 448.00 /*MHz*/, 0x8e, 0x02, },
1286 { 16 * 999.99 , 0x8e, 0x04, },
1287};
1288
1289static struct tuner_params tuner_tcl_mf02gip_5n_params[] = {
1290 {
1291 .type = TUNER_PARAM_TYPE_NTSC,
1292 .ranges = tuner_tcl_mf02gip_5n_ntsc_ranges,
1293 .count = ARRAY_SIZE(tuner_tcl_mf02gip_5n_ntsc_ranges),
1294 .cb_first_if_lower_freq = 1,
1295 },
1296};
1297
1298/* 80-89 */
1299/* --------- TUNER_PHILIPS_FQ1216LME_MK3 -- active loopthrough, no FM ------- */
1300
1301static struct tuner_params tuner_fq1216lme_mk3_params[] = {
1302 {
1303 .type = TUNER_PARAM_TYPE_PAL,
1304 .ranges = tuner_fm1216me_mk3_pal_ranges,
1305 .count = ARRAY_SIZE(tuner_fm1216me_mk3_pal_ranges),
1306 .cb_first_if_lower_freq = 1, /* not specified, but safe to do */
1307 .has_tda9887 = 1, /* TDA9886 */
1308 .port1_active = 1,
1309 .port2_active = 1,
1310 .port2_invert_for_secam_lc = 1,
1311 .default_top_low = 4,
1312 .default_top_mid = 4,
1313 .default_top_high = 4,
1314 .default_top_secam_low = 4,
1315 .default_top_secam_mid = 4,
1316 .default_top_secam_high = 4,
1317 },
1318};
1319
1320/* ----- TUNER_PARTSNIC_PTI_5NF05 - Partsnic (Daewoo) PTI-5NF05 NTSC ----- */
1321
1322static struct tuner_range tuner_partsnic_pti_5nf05_ranges[] = {
1323 /* The datasheet specified channel ranges and the bandswitch byte */
1324 /* The control byte value of 0x8e is just a guess */
1325 { 16 * 133.25 /*MHz*/, 0x8e, 0x01, }, /* Channels 2 - B */
1326 { 16 * 367.25 /*MHz*/, 0x8e, 0x02, }, /* Channels C - W+11 */
1327 { 16 * 999.99 , 0x8e, 0x08, }, /* Channels W+12 - 69 */
1328};
1329
1330static struct tuner_params tuner_partsnic_pti_5nf05_params[] = {
1331 {
1332 .type = TUNER_PARAM_TYPE_NTSC,
1333 .ranges = tuner_partsnic_pti_5nf05_ranges,
1334 .count = ARRAY_SIZE(tuner_partsnic_pti_5nf05_ranges),
1335 .cb_first_if_lower_freq = 1, /* not specified but safe to do */
1336 },
1337};
1338
1339/* --------- TUNER_PHILIPS_CU1216L - DVB-C NIM ------------------------- */
1340
1341static struct tuner_range tuner_cu1216l_ranges[] = {
1342 { 16 * 160.25 /*MHz*/, 0xce, 0x01 },
1343 { 16 * 444.25 /*MHz*/, 0xce, 0x02 },
1344 { 16 * 999.99 , 0xce, 0x04 },
1345};
1346
1347static struct tuner_params tuner_philips_cu1216l_params[] = {
1348 {
1349 .type = TUNER_PARAM_TYPE_DIGITAL,
1350 .ranges = tuner_cu1216l_ranges,
1351 .count = ARRAY_SIZE(tuner_cu1216l_ranges),
1352 .iffreq = 16 * 36.125, /*MHz*/
1353 },
1354};
1355
1356/* ---------------------- TUNER_SONY_BTF_PXN01Z ------------------------ */
1357
1358static struct tuner_range tuner_sony_btf_pxn01z_ranges[] = {
1359 { 16 * 137.25 /*MHz*/, 0x8e, 0x01, },
1360 { 16 * 367.25 /*MHz*/, 0x8e, 0x02, },
1361 { 16 * 999.99 , 0x8e, 0x04, },
1362};
1363
1364static struct tuner_params tuner_sony_btf_pxn01z_params[] = {
1365 {
1366 .type = TUNER_PARAM_TYPE_NTSC,
1367 .ranges = tuner_sony_btf_pxn01z_ranges,
1368 .count = ARRAY_SIZE(tuner_sony_btf_pxn01z_ranges),
1369 },
1370};
1371
1372/* ------------ TUNER_PHILIPS_FQ1236_MK5 - Philips NTSC ------------ */
1373
1374static struct tuner_params tuner_philips_fq1236_mk5_params[] = {
1375 {
1376 .type = TUNER_PARAM_TYPE_NTSC,
1377 .ranges = tuner_fm1236_mk3_ntsc_ranges,
1378 .count = ARRAY_SIZE(tuner_fm1236_mk3_ntsc_ranges),
1379 .has_tda9887 = 1, /* TDA9885, no FM radio */
1380 },
1381};
1382
1383/* --------------------------------------------------------------------- */
1384
1385struct tunertype tuners[] = {
1386 /* 0-9 */
1387 [TUNER_TEMIC_PAL] = { /* TEMIC PAL */
1388 .name = "Temic PAL (4002 FH5)",
1389 .params = tuner_temic_pal_params,
1390 .count = ARRAY_SIZE(tuner_temic_pal_params),
1391 },
1392 [TUNER_PHILIPS_PAL_I] = { /* Philips PAL_I */
1393 .name = "Philips PAL_I (FI1246 and compatibles)",
1394 .params = tuner_philips_pal_i_params,
1395 .count = ARRAY_SIZE(tuner_philips_pal_i_params),
1396 },
1397 [TUNER_PHILIPS_NTSC] = { /* Philips NTSC */
1398 .name = "Philips NTSC (FI1236,FM1236 and compatibles)",
1399 .params = tuner_philips_ntsc_params,
1400 .count = ARRAY_SIZE(tuner_philips_ntsc_params),
1401 },
1402 [TUNER_PHILIPS_SECAM] = { /* Philips SECAM */
1403 .name = "Philips (SECAM+PAL_BG) (FI1216MF, FM1216MF, FR1216MF)",
1404 .params = tuner_philips_secam_params,
1405 .count = ARRAY_SIZE(tuner_philips_secam_params),
1406 },
1407 [TUNER_ABSENT] = { /* Tuner Absent */
1408 .name = "NoTuner",
1409 },
1410 [TUNER_PHILIPS_PAL] = { /* Philips PAL */
1411 .name = "Philips PAL_BG (FI1216 and compatibles)",
1412 .params = tuner_philips_pal_params,
1413 .count = ARRAY_SIZE(tuner_philips_pal_params),
1414 },
1415 [TUNER_TEMIC_NTSC] = { /* TEMIC NTSC */
1416 .name = "Temic NTSC (4032 FY5)",
1417 .params = tuner_temic_ntsc_params,
1418 .count = ARRAY_SIZE(tuner_temic_ntsc_params),
1419 },
1420 [TUNER_TEMIC_PAL_I] = { /* TEMIC PAL_I */
1421 .name = "Temic PAL_I (4062 FY5)",
1422 .params = tuner_temic_pal_i_params,
1423 .count = ARRAY_SIZE(tuner_temic_pal_i_params),
1424 },
1425 [TUNER_TEMIC_4036FY5_NTSC] = { /* TEMIC NTSC */
1426 .name = "Temic NTSC (4036 FY5)",
1427 .params = tuner_temic_4036fy5_ntsc_params,
1428 .count = ARRAY_SIZE(tuner_temic_4036fy5_ntsc_params),
1429 },
1430 [TUNER_ALPS_TSBH1_NTSC] = { /* TEMIC NTSC */
1431 .name = "Alps HSBH1",
1432 .params = tuner_alps_tsbh1_ntsc_params,
1433 .count = ARRAY_SIZE(tuner_alps_tsbh1_ntsc_params),
1434 },
1435
1436 /* 10-19 */
1437 [TUNER_ALPS_TSBE1_PAL] = { /* TEMIC PAL */
1438 .name = "Alps TSBE1",
1439 .params = tuner_alps_tsb_1_params,
1440 .count = ARRAY_SIZE(tuner_alps_tsb_1_params),
1441 },
1442 [TUNER_ALPS_TSBB5_PAL_I] = { /* Alps PAL_I */
1443 .name = "Alps TSBB5",
1444 .params = tuner_alps_tsbb5_params,
1445 .count = ARRAY_SIZE(tuner_alps_tsbb5_params),
1446 },
1447 [TUNER_ALPS_TSBE5_PAL] = { /* Alps PAL */
1448 .name = "Alps TSBE5",
1449 .params = tuner_alps_tsbe5_params,
1450 .count = ARRAY_SIZE(tuner_alps_tsbe5_params),
1451 },
1452 [TUNER_ALPS_TSBC5_PAL] = { /* Alps PAL */
1453 .name = "Alps TSBC5",
1454 .params = tuner_alps_tsbc5_params,
1455 .count = ARRAY_SIZE(tuner_alps_tsbc5_params),
1456 },
1457 [TUNER_TEMIC_4006FH5_PAL] = { /* TEMIC PAL */
1458 .name = "Temic PAL_BG (4006FH5)",
1459 .params = tuner_temic_4006fh5_params,
1460 .count = ARRAY_SIZE(tuner_temic_4006fh5_params),
1461 },
1462 [TUNER_ALPS_TSHC6_NTSC] = { /* Alps NTSC */
1463 .name = "Alps TSCH6",
1464 .params = tuner_alps_tshc6_params,
1465 .count = ARRAY_SIZE(tuner_alps_tshc6_params),
1466 },
1467 [TUNER_TEMIC_PAL_DK] = { /* TEMIC PAL */
1468 .name = "Temic PAL_DK (4016 FY5)",
1469 .params = tuner_temic_pal_dk_params,
1470 .count = ARRAY_SIZE(tuner_temic_pal_dk_params),
1471 },
1472 [TUNER_PHILIPS_NTSC_M] = { /* Philips NTSC */
1473 .name = "Philips NTSC_M (MK2)",
1474 .params = tuner_philips_ntsc_m_params,
1475 .count = ARRAY_SIZE(tuner_philips_ntsc_m_params),
1476 },
1477 [TUNER_TEMIC_4066FY5_PAL_I] = { /* TEMIC PAL_I */
1478 .name = "Temic PAL_I (4066 FY5)",
1479 .params = tuner_temic_4066fy5_pal_i_params,
1480 .count = ARRAY_SIZE(tuner_temic_4066fy5_pal_i_params),
1481 },
1482 [TUNER_TEMIC_4006FN5_MULTI_PAL] = { /* TEMIC PAL */
1483 .name = "Temic PAL* auto (4006 FN5)",
1484 .params = tuner_temic_4006fn5_multi_params,
1485 .count = ARRAY_SIZE(tuner_temic_4006fn5_multi_params),
1486 },
1487
1488 /* 20-29 */
1489 [TUNER_TEMIC_4009FR5_PAL] = { /* TEMIC PAL */
1490 .name = "Temic PAL_BG (4009 FR5) or PAL_I (4069 FR5)",
1491 .params = tuner_temic_4009f_5_params,
1492 .count = ARRAY_SIZE(tuner_temic_4009f_5_params),
1493 },
1494 [TUNER_TEMIC_4039FR5_NTSC] = { /* TEMIC NTSC */
1495 .name = "Temic NTSC (4039 FR5)",
1496 .params = tuner_temic_4039fr5_params,
1497 .count = ARRAY_SIZE(tuner_temic_4039fr5_params),
1498 },
1499 [TUNER_TEMIC_4046FM5] = { /* TEMIC PAL */
1500 .name = "Temic PAL/SECAM multi (4046 FM5)",
1501 .params = tuner_temic_4046fm5_params,
1502 .count = ARRAY_SIZE(tuner_temic_4046fm5_params),
1503 },
1504 [TUNER_PHILIPS_PAL_DK] = { /* Philips PAL */
1505 .name = "Philips PAL_DK (FI1256 and compatibles)",
1506 .params = tuner_philips_pal_dk_params,
1507 .count = ARRAY_SIZE(tuner_philips_pal_dk_params),
1508 },
1509 [TUNER_PHILIPS_FQ1216ME] = { /* Philips PAL */
1510 .name = "Philips PAL/SECAM multi (FQ1216ME)",
1511 .params = tuner_philips_fq1216me_params,
1512 .count = ARRAY_SIZE(tuner_philips_fq1216me_params),
1513 },
1514 [TUNER_LG_PAL_I_FM] = { /* LGINNOTEK PAL_I */
1515 .name = "LG PAL_I+FM (TAPC-I001D)",
1516 .params = tuner_lg_pal_i_fm_params,
1517 .count = ARRAY_SIZE(tuner_lg_pal_i_fm_params),
1518 },
1519 [TUNER_LG_PAL_I] = { /* LGINNOTEK PAL_I */
1520 .name = "LG PAL_I (TAPC-I701D)",
1521 .params = tuner_lg_pal_i_params,
1522 .count = ARRAY_SIZE(tuner_lg_pal_i_params),
1523 },
1524 [TUNER_LG_NTSC_FM] = { /* LGINNOTEK NTSC */
1525 .name = "LG NTSC+FM (TPI8NSR01F)",
1526 .params = tuner_lg_ntsc_fm_params,
1527 .count = ARRAY_SIZE(tuner_lg_ntsc_fm_params),
1528 },
1529 [TUNER_LG_PAL_FM] = { /* LGINNOTEK PAL */
1530 .name = "LG PAL_BG+FM (TPI8PSB01D)",
1531 .params = tuner_lg_pal_fm_params,
1532 .count = ARRAY_SIZE(tuner_lg_pal_fm_params),
1533 },
1534 [TUNER_LG_PAL] = { /* LGINNOTEK PAL */
1535 .name = "LG PAL_BG (TPI8PSB11D)",
1536 .params = tuner_lg_pal_params,
1537 .count = ARRAY_SIZE(tuner_lg_pal_params),
1538 },
1539
1540 /* 30-39 */
1541 [TUNER_TEMIC_4009FN5_MULTI_PAL_FM] = { /* TEMIC PAL */
1542 .name = "Temic PAL* auto + FM (4009 FN5)",
1543 .params = tuner_temic_4009_fn5_multi_pal_fm_params,
1544 .count = ARRAY_SIZE(tuner_temic_4009_fn5_multi_pal_fm_params),
1545 },
1546 [TUNER_SHARP_2U5JF5540_NTSC] = { /* SHARP NTSC */
1547 .name = "SHARP NTSC_JP (2U5JF5540)",
1548 .params = tuner_sharp_2u5jf5540_params,
1549 .count = ARRAY_SIZE(tuner_sharp_2u5jf5540_params),
1550 },
1551 [TUNER_Samsung_PAL_TCPM9091PD27] = { /* Samsung PAL */
1552 .name = "Samsung PAL TCPM9091PD27",
1553 .params = tuner_samsung_pal_tcpm9091pd27_params,
1554 .count = ARRAY_SIZE(tuner_samsung_pal_tcpm9091pd27_params),
1555 },
1556 [TUNER_MT2032] = { /* Microtune PAL|NTSC */
1557 .name = "MT20xx universal",
1558 /* see mt20xx.c for details */ },
1559 [TUNER_TEMIC_4106FH5] = { /* TEMIC PAL */
1560 .name = "Temic PAL_BG (4106 FH5)",
1561 .params = tuner_temic_4106fh5_params,
1562 .count = ARRAY_SIZE(tuner_temic_4106fh5_params),
1563 },
1564 [TUNER_TEMIC_4012FY5] = { /* TEMIC PAL */
1565 .name = "Temic PAL_DK/SECAM_L (4012 FY5)",
1566 .params = tuner_temic_4012fy5_params,
1567 .count = ARRAY_SIZE(tuner_temic_4012fy5_params),
1568 },
1569 [TUNER_TEMIC_4136FY5] = { /* TEMIC NTSC */
1570 .name = "Temic NTSC (4136 FY5)",
1571 .params = tuner_temic_4136_fy5_params,
1572 .count = ARRAY_SIZE(tuner_temic_4136_fy5_params),
1573 },
1574 [TUNER_LG_PAL_NEW_TAPC] = { /* LGINNOTEK PAL */
1575 .name = "LG PAL (newer TAPC series)",
1576 .params = tuner_lg_pal_new_tapc_params,
1577 .count = ARRAY_SIZE(tuner_lg_pal_new_tapc_params),
1578 },
1579 [TUNER_PHILIPS_FM1216ME_MK3] = { /* Philips PAL */
1580 .name = "Philips PAL/SECAM multi (FM1216ME MK3)",
1581 .params = tuner_fm1216me_mk3_params,
1582 .count = ARRAY_SIZE(tuner_fm1216me_mk3_params),
1583 },
1584 [TUNER_LG_NTSC_NEW_TAPC] = { /* LGINNOTEK NTSC */
1585 .name = "LG NTSC (newer TAPC series)",
1586 .params = tuner_lg_ntsc_new_tapc_params,
1587 .count = ARRAY_SIZE(tuner_lg_ntsc_new_tapc_params),
1588 },
1589
1590 /* 40-49 */
1591 [TUNER_HITACHI_NTSC] = { /* HITACHI NTSC */
1592 .name = "HITACHI V7-J180AT",
1593 .params = tuner_hitachi_ntsc_params,
1594 .count = ARRAY_SIZE(tuner_hitachi_ntsc_params),
1595 },
1596 [TUNER_PHILIPS_PAL_MK] = { /* Philips PAL */
1597 .name = "Philips PAL_MK (FI1216 MK)",
1598 .params = tuner_philips_pal_mk_params,
1599 .count = ARRAY_SIZE(tuner_philips_pal_mk_params),
1600 },
1601 [TUNER_PHILIPS_FCV1236D] = { /* Philips ATSC */
1602 .name = "Philips FCV1236D ATSC/NTSC dual in",
1603 .params = tuner_philips_fcv1236d_params,
1604 .count = ARRAY_SIZE(tuner_philips_fcv1236d_params),
1605 .min = 16 * 53.00,
1606 .max = 16 * 803.00,
1607 .stepsize = 62500,
1608 },
1609 [TUNER_PHILIPS_FM1236_MK3] = { /* Philips NTSC */
1610 .name = "Philips NTSC MK3 (FM1236MK3 or FM1236/F)",
1611 .params = tuner_fm1236_mk3_params,
1612 .count = ARRAY_SIZE(tuner_fm1236_mk3_params),
1613 },
1614 [TUNER_PHILIPS_4IN1] = { /* Philips NTSC */
1615 .name = "Philips 4 in 1 (ATI TV Wonder Pro/Conexant)",
1616 .params = tuner_philips_4in1_params,
1617 .count = ARRAY_SIZE(tuner_philips_4in1_params),
1618 },
1619 [TUNER_MICROTUNE_4049FM5] = { /* Microtune PAL */
1620 .name = "Microtune 4049 FM5",
1621 .params = tuner_microtune_4049_fm5_params,
1622 .count = ARRAY_SIZE(tuner_microtune_4049_fm5_params),
1623 },
1624 [TUNER_PANASONIC_VP27] = { /* Panasonic NTSC */
1625 .name = "Panasonic VP27s/ENGE4324D",
1626 .params = tuner_panasonic_vp27_params,
1627 .count = ARRAY_SIZE(tuner_panasonic_vp27_params),
1628 },
1629 [TUNER_LG_NTSC_TAPE] = { /* LGINNOTEK NTSC */
1630 .name = "LG NTSC (TAPE series)",
1631 .params = tuner_fm1236_mk3_params,
1632 .count = ARRAY_SIZE(tuner_fm1236_mk3_params),
1633 },
1634 [TUNER_TNF_8831BGFF] = { /* Philips PAL */
1635 .name = "Tenna TNF 8831 BGFF)",
1636 .params = tuner_tnf_8831bgff_params,
1637 .count = ARRAY_SIZE(tuner_tnf_8831bgff_params),
1638 },
1639 [TUNER_MICROTUNE_4042FI5] = { /* Microtune NTSC */
1640 .name = "Microtune 4042 FI5 ATSC/NTSC dual in",
1641 .params = tuner_microtune_4042fi5_params,
1642 .count = ARRAY_SIZE(tuner_microtune_4042fi5_params),
1643 .min = 16 * 57.00,
1644 .max = 16 * 858.00,
1645 .stepsize = 62500,
1646 },
1647
1648 /* 50-59 */
1649 [TUNER_TCL_2002N] = { /* TCL NTSC */
1650 .name = "TCL 2002N",
1651 .params = tuner_tcl_2002n_params,
1652 .count = ARRAY_SIZE(tuner_tcl_2002n_params),
1653 },
1654 [TUNER_PHILIPS_FM1256_IH3] = { /* Philips PAL */
1655 .name = "Philips PAL/SECAM_D (FM 1256 I-H3)",
1656 .params = tuner_philips_fm1256_ih3_params,
1657 .count = ARRAY_SIZE(tuner_philips_fm1256_ih3_params),
1658 },
1659 [TUNER_THOMSON_DTT7610] = { /* THOMSON ATSC */
1660 .name = "Thomson DTT 7610 (ATSC/NTSC)",
1661 .params = tuner_thomson_dtt7610_params,
1662 .count = ARRAY_SIZE(tuner_thomson_dtt7610_params),
1663 .min = 16 * 44.00,
1664 .max = 16 * 958.00,
1665 .stepsize = 62500,
1666 },
1667 [TUNER_PHILIPS_FQ1286] = { /* Philips NTSC */
1668 .name = "Philips FQ1286",
1669 .params = tuner_philips_fq1286_params,
1670 .count = ARRAY_SIZE(tuner_philips_fq1286_params),
1671 },
1672 [TUNER_PHILIPS_TDA8290] = { /* Philips PAL|NTSC */
1673 .name = "Philips/NXP TDA 8290/8295 + 8275/8275A/18271",
1674 /* see tda8290.c for details */ },
1675 [TUNER_TCL_2002MB] = { /* TCL PAL */
1676 .name = "TCL 2002MB",
1677 .params = tuner_tcl_2002mb_params,
1678 .count = ARRAY_SIZE(tuner_tcl_2002mb_params),
1679 },
1680 [TUNER_PHILIPS_FQ1216AME_MK4] = { /* Philips PAL */
1681 .name = "Philips PAL/SECAM multi (FQ1216AME MK4)",
1682 .params = tuner_philips_fq1216ame_mk4_params,
1683 .count = ARRAY_SIZE(tuner_philips_fq1216ame_mk4_params),
1684 },
1685 [TUNER_PHILIPS_FQ1236A_MK4] = { /* Philips NTSC */
1686 .name = "Philips FQ1236A MK4",
1687 .params = tuner_philips_fq1236a_mk4_params,
1688 .count = ARRAY_SIZE(tuner_philips_fq1236a_mk4_params),
1689 },
1690 [TUNER_YMEC_TVF_8531MF] = { /* Philips NTSC */
1691 .name = "Ymec TVision TVF-8531MF/8831MF/8731MF",
1692 .params = tuner_ymec_tvf_8531mf_params,
1693 .count = ARRAY_SIZE(tuner_ymec_tvf_8531mf_params),
1694 },
1695 [TUNER_YMEC_TVF_5533MF] = { /* Philips NTSC */
1696 .name = "Ymec TVision TVF-5533MF",
1697 .params = tuner_ymec_tvf_5533mf_params,
1698 .count = ARRAY_SIZE(tuner_ymec_tvf_5533mf_params),
1699 },
1700
1701 /* 60-69 */
1702 [TUNER_THOMSON_DTT761X] = { /* THOMSON ATSC */
1703 /* DTT 7611 7611A 7612 7613 7613A 7614 7615 7615A */
1704 .name = "Thomson DTT 761X (ATSC/NTSC)",
1705 .params = tuner_thomson_dtt761x_params,
1706 .count = ARRAY_SIZE(tuner_thomson_dtt761x_params),
1707 .min = 16 * 57.00,
1708 .max = 16 * 863.00,
1709 .stepsize = 62500,
1710 .initdata = tua603x_agc103,
1711 },
1712 [TUNER_TENA_9533_DI] = { /* Philips PAL */
1713 .name = "Tena TNF9533-D/IF/TNF9533-B/DF",
1714 .params = tuner_tena_9533_di_params,
1715 .count = ARRAY_SIZE(tuner_tena_9533_di_params),
1716 },
1717 [TUNER_TEA5767] = { /* Philips RADIO */
1718 .name = "Philips TEA5767HN FM Radio",
1719 /* see tea5767.c for details */
1720 },
1721 [TUNER_PHILIPS_FMD1216ME_MK3] = { /* Philips PAL */
1722 .name = "Philips FMD1216ME MK3 Hybrid Tuner",
1723 .params = tuner_philips_fmd1216me_mk3_params,
1724 .count = ARRAY_SIZE(tuner_philips_fmd1216me_mk3_params),
1725 .min = 16 * 50.87,
1726 .max = 16 * 858.00,
1727 .stepsize = 166667,
1728 .initdata = tua603x_agc112,
1729 .sleepdata = (u8[]){ 4, 0x9c, 0x60, 0x85, 0x54 },
1730 },
1731 [TUNER_LG_TDVS_H06XF] = { /* LGINNOTEK ATSC */
1732 .name = "LG TDVS-H06xF", /* H061F, H062F & H064F */
1733 .params = tuner_lg_tdvs_h06xf_params,
1734 .count = ARRAY_SIZE(tuner_lg_tdvs_h06xf_params),
1735 .min = 16 * 54.00,
1736 .max = 16 * 863.00,
1737 .stepsize = 62500,
1738 .initdata = tua603x_agc103,
1739 },
1740 [TUNER_YMEC_TVF66T5_B_DFF] = { /* Philips PAL */
1741 .name = "Ymec TVF66T5-B/DFF",
1742 .params = tuner_ymec_tvf66t5_b_dff_params,
1743 .count = ARRAY_SIZE(tuner_ymec_tvf66t5_b_dff_params),
1744 },
1745 [TUNER_LG_TALN] = { /* LGINNOTEK NTSC / PAL / SECAM */
1746 .name = "LG TALN series",
1747 .params = tuner_lg_taln_params,
1748 .count = ARRAY_SIZE(tuner_lg_taln_params),
1749 },
1750 [TUNER_PHILIPS_TD1316] = { /* Philips PAL */
1751 .name = "Philips TD1316 Hybrid Tuner",
1752 .params = tuner_philips_td1316_params,
1753 .count = ARRAY_SIZE(tuner_philips_td1316_params),
1754 .min = 16 * 87.00,
1755 .max = 16 * 895.00,
1756 .stepsize = 166667,
1757 },
1758 [TUNER_PHILIPS_TUV1236D] = { /* Philips ATSC */
1759 .name = "Philips TUV1236D ATSC/NTSC dual in",
1760 .params = tuner_tuv1236d_params,
1761 .count = ARRAY_SIZE(tuner_tuv1236d_params),
1762 .min = 16 * 54.00,
1763 .max = 16 * 864.00,
1764 .stepsize = 62500,
1765 },
1766 [TUNER_TNF_5335MF] = { /* Tenna PAL/NTSC */
1767 .name = "Tena TNF 5335 and similar models",
1768 .params = tuner_tnf_5335mf_params,
1769 .count = ARRAY_SIZE(tuner_tnf_5335mf_params),
1770 },
1771
1772 /* 70-79 */
1773 [TUNER_SAMSUNG_TCPN_2121P30A] = { /* Samsung NTSC */
1774 .name = "Samsung TCPN 2121P30A",
1775 .params = tuner_samsung_tcpn_2121p30a_params,
1776 .count = ARRAY_SIZE(tuner_samsung_tcpn_2121p30a_params),
1777 },
1778 [TUNER_XC2028] = { /* Xceive 2028 */
1779 .name = "Xceive xc2028/xc3028 tuner",
1780 /* see tuner-xc2028.c for details */
1781 },
1782 [TUNER_THOMSON_FE6600] = { /* Thomson PAL / DVB-T */
1783 .name = "Thomson FE6600",
1784 .params = tuner_thomson_fe6600_params,
1785 .count = ARRAY_SIZE(tuner_thomson_fe6600_params),
1786 .min = 16 * 44.25,
1787 .max = 16 * 858.00,
1788 .stepsize = 166667,
1789 },
1790 [TUNER_SAMSUNG_TCPG_6121P30A] = { /* Samsung PAL */
1791 .name = "Samsung TCPG 6121P30A",
1792 .params = tuner_samsung_tcpg_6121p30a_params,
1793 .count = ARRAY_SIZE(tuner_samsung_tcpg_6121p30a_params),
1794 },
1795 [TUNER_TDA9887] = { /* Philips TDA 9887 IF PLL Demodulator.
1796 This chip is part of some modern tuners */
1797 .name = "Philips TDA988[5,6,7] IF PLL Demodulator",
1798 /* see tda9887.c for details */
1799 },
1800 [TUNER_TEA5761] = { /* Philips RADIO */
1801 .name = "Philips TEA5761 FM Radio",
1802 /* see tea5767.c for details */
1803 },
1804 [TUNER_XC5000] = { /* Xceive 5000 */
1805 .name = "Xceive 5000 tuner",
1806 /* see xc5000.c for details */
1807 },
1808 [TUNER_XC4000] = { /* Xceive 4000 */
1809 .name = "Xceive 4000 tuner",
1810 /* see xc4000.c for details */
1811 },
1812 [TUNER_TCL_MF02GIP_5N] = { /* TCL tuner MF02GIP-5N-E */
1813 .name = "TCL tuner MF02GIP-5N-E",
1814 .params = tuner_tcl_mf02gip_5n_params,
1815 .count = ARRAY_SIZE(tuner_tcl_mf02gip_5n_params),
1816 },
1817 [TUNER_PHILIPS_FMD1216MEX_MK3] = { /* Philips PAL */
1818 .name = "Philips FMD1216MEX MK3 Hybrid Tuner",
1819 .params = tuner_philips_fmd1216mex_mk3_params,
1820 .count = ARRAY_SIZE(tuner_philips_fmd1216mex_mk3_params),
1821 .min = 16 * 50.87,
1822 .max = 16 * 858.00,
1823 .stepsize = 166667,
1824 .initdata = tua603x_agc112,
1825 .sleepdata = (u8[]){ 4, 0x9c, 0x60, 0x85, 0x54 },
1826 },
1827 [TUNER_PHILIPS_FM1216MK5] = { /* Philips PAL */
1828 .name = "Philips PAL/SECAM multi (FM1216 MK5)",
1829 .params = tuner_fm1216mk5_params,
1830 .count = ARRAY_SIZE(tuner_fm1216mk5_params),
1831 },
1832
1833 /* 80-89 */
1834 [TUNER_PHILIPS_FQ1216LME_MK3] = { /* PAL/SECAM, Loop-thru, no FM */
1835 .name = "Philips FQ1216LME MK3 PAL/SECAM w/active loopthrough",
1836 .params = tuner_fq1216lme_mk3_params,
1837 .count = ARRAY_SIZE(tuner_fq1216lme_mk3_params),
1838 },
1839
1840 [TUNER_PARTSNIC_PTI_5NF05] = {
1841 .name = "Partsnic (Daewoo) PTI-5NF05",
1842 .params = tuner_partsnic_pti_5nf05_params,
1843 .count = ARRAY_SIZE(tuner_partsnic_pti_5nf05_params),
1844 },
1845 [TUNER_PHILIPS_CU1216L] = {
1846 .name = "Philips CU1216L",
1847 .params = tuner_philips_cu1216l_params,
1848 .count = ARRAY_SIZE(tuner_philips_cu1216l_params),
1849 .stepsize = 62500,
1850 },
1851 [TUNER_NXP_TDA18271] = {
1852 .name = "NXP TDA18271",
1853 /* see tda18271-fe.c for details */
1854 },
1855 [TUNER_SONY_BTF_PXN01Z] = {
1856 .name = "Sony BTF-Pxn01Z",
1857 .params = tuner_sony_btf_pxn01z_params,
1858 .count = ARRAY_SIZE(tuner_sony_btf_pxn01z_params),
1859 },
1860 [TUNER_PHILIPS_FQ1236_MK5] = { /* NTSC, TDA9885, no FM radio */
1861 .name = "Philips FQ1236 MK5",
1862 .params = tuner_philips_fq1236_mk5_params,
1863 .count = ARRAY_SIZE(tuner_philips_fq1236_mk5_params),
1864 },
1865 [TUNER_TENA_TNF_5337] = { /* Tena 5337 MFD */
1866 .name = "Tena TNF5337 MFD",
1867 .params = tuner_tena_tnf_5337_params,
1868 .count = ARRAY_SIZE(tuner_tena_tnf_5337_params),
1869 },
1870};
1871EXPORT_SYMBOL(tuners);
1872
1873unsigned const int tuner_count = ARRAY_SIZE(tuners);
1874EXPORT_SYMBOL(tuner_count);
1875
1876MODULE_DESCRIPTION("Simple tuner device type database");
1877MODULE_AUTHOR("Ralph Metzler, Gerd Knorr, Gunther Mayer");
1878MODULE_LICENSE("GPL");
diff --git a/drivers/media/common/tuners/tuner-xc2028-types.h b/drivers/media/common/tuners/tuner-xc2028-types.h
new file mode 100644
index 00000000000..74dc46a71f6
--- /dev/null
+++ b/drivers/media/common/tuners/tuner-xc2028-types.h
@@ -0,0 +1,141 @@
1/* tuner-xc2028_types
2 *
3 * This file includes internal tipes to be used inside tuner-xc2028.
4 * Shouldn't be included outside tuner-xc2028
5 *
6 * Copyright (c) 2007-2008 Mauro Carvalho Chehab (mchehab@infradead.org)
7 * This code is placed under the terms of the GNU General Public License v2
8 */
9
10/* xc3028 firmware types */
11
12/* BASE firmware should be loaded before any other firmware */
13#define BASE (1<<0)
14#define BASE_TYPES (BASE|F8MHZ|MTS|FM|INPUT1|INPUT2|INIT1)
15
16/* F8MHZ marks BASE firmwares for 8 MHz Bandwidth */
17#define F8MHZ (1<<1)
18
19/* Multichannel Television Sound (MTS)
20 Those firmwares are capable of using xc2038 DSP to decode audio and
21 produce a baseband audio output on some pins of the chip.
22 There are MTS firmwares for the most used video standards. It should be
23 required to use MTS firmwares, depending on the way audio is routed into
24 the bridge chip
25 */
26#define MTS (1<<2)
27
28/* FIXME: I have no idea what's the difference between
29 D2620 and D2633 firmwares
30 */
31#define D2620 (1<<3)
32#define D2633 (1<<4)
33
34/* DTV firmwares for 6, 7 and 8 MHz
35 DTV6 - 6MHz - ATSC/DVB-C/DVB-T/ISDB-T/DOCSIS
36 DTV8 - 8MHz - DVB-C/DVB-T
37 */
38#define DTV6 (1 << 5)
39#define QAM (1 << 6)
40#define DTV7 (1<<7)
41#define DTV78 (1<<8)
42#define DTV8 (1<<9)
43
44#define DTV_TYPES (D2620|D2633|DTV6|QAM|DTV7|DTV78|DTV8|ATSC)
45
46/* There's a FM | BASE firmware + FM specific firmware (std=0) */
47#define FM (1<<10)
48
49#define STD_SPECIFIC_TYPES (MTS|FM|LCD|NOGD)
50
51/* Applies only for FM firmware
52 Makes it use RF input 1 (pin #2) instead of input 2 (pin #4)
53 */
54#define INPUT1 (1<<11)
55
56
57/* LCD firmwares exist only for MTS STD/MN (PAL or NTSC/M)
58 and for non-MTS STD/MN (PAL, NTSC/M or NTSC/Kr)
59 There are variants both with and without NOGD
60 Those firmwares produce better result with LCD displays
61 */
62#define LCD (1<<12)
63
64/* NOGD firmwares exist only for MTS STD/MN (PAL or NTSC/M)
65 and for non-MTS STD/MN (PAL, NTSC/M or NTSC/Kr)
66 The NOGD firmwares don't have group delay compensation filter
67 */
68#define NOGD (1<<13)
69
70/* Old firmwares were broken into init0 and init1 */
71#define INIT1 (1<<14)
72
73/* SCODE firmware selects particular behaviours */
74#define MONO (1 << 15)
75#define ATSC (1 << 16)
76#define IF (1 << 17)
77#define LG60 (1 << 18)
78#define ATI638 (1 << 19)
79#define OREN538 (1 << 20)
80#define OREN36 (1 << 21)
81#define TOYOTA388 (1 << 22)
82#define TOYOTA794 (1 << 23)
83#define DIBCOM52 (1 << 24)
84#define ZARLINK456 (1 << 25)
85#define CHINA (1 << 26)
86#define F6MHZ (1 << 27)
87#define INPUT2 (1 << 28)
88#define SCODE (1 << 29)
89
90/* This flag identifies that the scode table has a new format */
91#define HAS_IF (1 << 30)
92
93/* There are different scode tables for MTS and non-MTS.
94 The MTS firmwares support mono only
95 */
96#define SCODE_TYPES (SCODE | MTS)
97
98
99/* Newer types not defined on videodev2.h.
100 The original idea were to move all those types to videodev2.h, but
101 it seemed overkill, since, with the exception of SECAM/K3, the other
102 types seem to be autodetected.
103 It is not clear where secam/k3 is used, nor we have a feedback of this
104 working or being autodetected by the standard secam firmware.
105 */
106
107#define V4L2_STD_SECAM_K3 (0x04000000)
108
109/* Audio types */
110
111#define V4L2_STD_A2_A (1LL<<32)
112#define V4L2_STD_A2_B (1LL<<33)
113#define V4L2_STD_NICAM_A (1LL<<34)
114#define V4L2_STD_NICAM_B (1LL<<35)
115#define V4L2_STD_AM (1LL<<36)
116#define V4L2_STD_BTSC (1LL<<37)
117#define V4L2_STD_EIAJ (1LL<<38)
118
119#define V4L2_STD_A2 (V4L2_STD_A2_A | V4L2_STD_A2_B)
120#define V4L2_STD_NICAM (V4L2_STD_NICAM_A | V4L2_STD_NICAM_B)
121
122/* To preserve backward compatibilty,
123 (std & V4L2_STD_AUDIO) = 0 means that ALL audio stds are supported
124 */
125
126#define V4L2_STD_AUDIO (V4L2_STD_A2 | \
127 V4L2_STD_NICAM | \
128 V4L2_STD_AM | \
129 V4L2_STD_BTSC | \
130 V4L2_STD_EIAJ)
131
132/* Used standards with audio restrictions */
133
134#define V4L2_STD_PAL_BG_A2_A (V4L2_STD_PAL_BG | V4L2_STD_A2_A)
135#define V4L2_STD_PAL_BG_A2_B (V4L2_STD_PAL_BG | V4L2_STD_A2_B)
136#define V4L2_STD_PAL_BG_NICAM_A (V4L2_STD_PAL_BG | V4L2_STD_NICAM_A)
137#define V4L2_STD_PAL_BG_NICAM_B (V4L2_STD_PAL_BG | V4L2_STD_NICAM_B)
138#define V4L2_STD_PAL_DK_A2 (V4L2_STD_PAL_DK | V4L2_STD_A2)
139#define V4L2_STD_PAL_DK_NICAM (V4L2_STD_PAL_DK | V4L2_STD_NICAM)
140#define V4L2_STD_SECAM_L_NICAM (V4L2_STD_SECAM_L | V4L2_STD_NICAM)
141#define V4L2_STD_SECAM_L_AM (V4L2_STD_SECAM_L | V4L2_STD_AM)
diff --git a/drivers/media/common/tuners/tuner-xc2028.c b/drivers/media/common/tuners/tuner-xc2028.c
new file mode 100644
index 00000000000..16fba6b5961
--- /dev/null
+++ b/drivers/media/common/tuners/tuner-xc2028.c
@@ -0,0 +1,1356 @@
1/* tuner-xc2028
2 *
3 * Copyright (c) 2007-2008 Mauro Carvalho Chehab (mchehab@infradead.org)
4 *
5 * Copyright (c) 2007 Michel Ludwig (michel.ludwig@gmail.com)
6 * - frontend interface
7 *
8 * This code is placed under the terms of the GNU General Public License v2
9 */
10
11#include <linux/i2c.h>
12#include <asm/div64.h>
13#include <linux/firmware.h>
14#include <linux/videodev2.h>
15#include <linux/delay.h>
16#include <media/tuner.h>
17#include <linux/mutex.h>
18#include <linux/slab.h>
19#include <asm/unaligned.h>
20#include "tuner-i2c.h"
21#include "tuner-xc2028.h"
22#include "tuner-xc2028-types.h"
23
24#include <linux/dvb/frontend.h>
25#include "dvb_frontend.h"
26
27
28static int debug;
29module_param(debug, int, 0644);
30MODULE_PARM_DESC(debug, "enable verbose debug messages");
31
32static int no_poweroff;
33module_param(no_poweroff, int, 0644);
34MODULE_PARM_DESC(no_poweroff, "0 (default) powers device off when not used.\n"
35 "1 keep device energized and with tuner ready all the times.\n"
36 " Faster, but consumes more power and keeps the device hotter\n");
37
38static char audio_std[8];
39module_param_string(audio_std, audio_std, sizeof(audio_std), 0);
40MODULE_PARM_DESC(audio_std,
41 "Audio standard. XC3028 audio decoder explicitly "
42 "needs to know what audio\n"
43 "standard is needed for some video standards with audio A2 or NICAM.\n"
44 "The valid values are:\n"
45 "A2\n"
46 "A2/A\n"
47 "A2/B\n"
48 "NICAM\n"
49 "NICAM/A\n"
50 "NICAM/B\n");
51
52static char firmware_name[30];
53module_param_string(firmware_name, firmware_name, sizeof(firmware_name), 0);
54MODULE_PARM_DESC(firmware_name, "Firmware file name. Allows overriding the "
55 "default firmware name\n");
56
57static LIST_HEAD(hybrid_tuner_instance_list);
58static DEFINE_MUTEX(xc2028_list_mutex);
59
60/* struct for storing firmware table */
61struct firmware_description {
62 unsigned int type;
63 v4l2_std_id id;
64 __u16 int_freq;
65 unsigned char *ptr;
66 unsigned int size;
67};
68
69struct firmware_properties {
70 unsigned int type;
71 v4l2_std_id id;
72 v4l2_std_id std_req;
73 __u16 int_freq;
74 unsigned int scode_table;
75 int scode_nr;
76};
77
78struct xc2028_data {
79 struct list_head hybrid_tuner_instance_list;
80 struct tuner_i2c_props i2c_props;
81 __u32 frequency;
82
83 struct firmware_description *firm;
84 int firm_size;
85 __u16 firm_version;
86
87 __u16 hwmodel;
88 __u16 hwvers;
89
90 struct xc2028_ctrl ctrl;
91
92 struct firmware_properties cur_fw;
93
94 struct mutex lock;
95};
96
97#define i2c_send(priv, buf, size) ({ \
98 int _rc; \
99 _rc = tuner_i2c_xfer_send(&priv->i2c_props, buf, size); \
100 if (size != _rc) \
101 tuner_info("i2c output error: rc = %d (should be %d)\n",\
102 _rc, (int)size); \
103 if (priv->ctrl.msleep) \
104 msleep(priv->ctrl.msleep); \
105 _rc; \
106})
107
108#define i2c_rcv(priv, buf, size) ({ \
109 int _rc; \
110 _rc = tuner_i2c_xfer_recv(&priv->i2c_props, buf, size); \
111 if (size != _rc) \
112 tuner_err("i2c input error: rc = %d (should be %d)\n", \
113 _rc, (int)size); \
114 _rc; \
115})
116
117#define i2c_send_recv(priv, obuf, osize, ibuf, isize) ({ \
118 int _rc; \
119 _rc = tuner_i2c_xfer_send_recv(&priv->i2c_props, obuf, osize, \
120 ibuf, isize); \
121 if (isize != _rc) \
122 tuner_err("i2c input error: rc = %d (should be %d)\n", \
123 _rc, (int)isize); \
124 if (priv->ctrl.msleep) \
125 msleep(priv->ctrl.msleep); \
126 _rc; \
127})
128
129#define send_seq(priv, data...) ({ \
130 static u8 _val[] = data; \
131 int _rc; \
132 if (sizeof(_val) != \
133 (_rc = tuner_i2c_xfer_send(&priv->i2c_props, \
134 _val, sizeof(_val)))) { \
135 tuner_err("Error on line %d: %d\n", __LINE__, _rc); \
136 } else if (priv->ctrl.msleep) \
137 msleep(priv->ctrl.msleep); \
138 _rc; \
139})
140
141static int xc2028_get_reg(struct xc2028_data *priv, u16 reg, u16 *val)
142{
143 unsigned char buf[2];
144 unsigned char ibuf[2];
145
146 tuner_dbg("%s %04x called\n", __func__, reg);
147
148 buf[0] = reg >> 8;
149 buf[1] = (unsigned char) reg;
150
151 if (i2c_send_recv(priv, buf, 2, ibuf, 2) != 2)
152 return -EIO;
153
154 *val = (ibuf[1]) | (ibuf[0] << 8);
155 return 0;
156}
157
158#define dump_firm_type(t) dump_firm_type_and_int_freq(t, 0)
159static void dump_firm_type_and_int_freq(unsigned int type, u16 int_freq)
160{
161 if (type & BASE)
162 printk("BASE ");
163 if (type & INIT1)
164 printk("INIT1 ");
165 if (type & F8MHZ)
166 printk("F8MHZ ");
167 if (type & MTS)
168 printk("MTS ");
169 if (type & D2620)
170 printk("D2620 ");
171 if (type & D2633)
172 printk("D2633 ");
173 if (type & DTV6)
174 printk("DTV6 ");
175 if (type & QAM)
176 printk("QAM ");
177 if (type & DTV7)
178 printk("DTV7 ");
179 if (type & DTV78)
180 printk("DTV78 ");
181 if (type & DTV8)
182 printk("DTV8 ");
183 if (type & FM)
184 printk("FM ");
185 if (type & INPUT1)
186 printk("INPUT1 ");
187 if (type & LCD)
188 printk("LCD ");
189 if (type & NOGD)
190 printk("NOGD ");
191 if (type & MONO)
192 printk("MONO ");
193 if (type & ATSC)
194 printk("ATSC ");
195 if (type & IF)
196 printk("IF ");
197 if (type & LG60)
198 printk("LG60 ");
199 if (type & ATI638)
200 printk("ATI638 ");
201 if (type & OREN538)
202 printk("OREN538 ");
203 if (type & OREN36)
204 printk("OREN36 ");
205 if (type & TOYOTA388)
206 printk("TOYOTA388 ");
207 if (type & TOYOTA794)
208 printk("TOYOTA794 ");
209 if (type & DIBCOM52)
210 printk("DIBCOM52 ");
211 if (type & ZARLINK456)
212 printk("ZARLINK456 ");
213 if (type & CHINA)
214 printk("CHINA ");
215 if (type & F6MHZ)
216 printk("F6MHZ ");
217 if (type & INPUT2)
218 printk("INPUT2 ");
219 if (type & SCODE)
220 printk("SCODE ");
221 if (type & HAS_IF)
222 printk("HAS_IF_%d ", int_freq);
223}
224
225static v4l2_std_id parse_audio_std_option(void)
226{
227 if (strcasecmp(audio_std, "A2") == 0)
228 return V4L2_STD_A2;
229 if (strcasecmp(audio_std, "A2/A") == 0)
230 return V4L2_STD_A2_A;
231 if (strcasecmp(audio_std, "A2/B") == 0)
232 return V4L2_STD_A2_B;
233 if (strcasecmp(audio_std, "NICAM") == 0)
234 return V4L2_STD_NICAM;
235 if (strcasecmp(audio_std, "NICAM/A") == 0)
236 return V4L2_STD_NICAM_A;
237 if (strcasecmp(audio_std, "NICAM/B") == 0)
238 return V4L2_STD_NICAM_B;
239
240 return 0;
241}
242
243static void free_firmware(struct xc2028_data *priv)
244{
245 int i;
246 tuner_dbg("%s called\n", __func__);
247
248 if (!priv->firm)
249 return;
250
251 for (i = 0; i < priv->firm_size; i++)
252 kfree(priv->firm[i].ptr);
253
254 kfree(priv->firm);
255
256 priv->firm = NULL;
257 priv->firm_size = 0;
258
259 memset(&priv->cur_fw, 0, sizeof(priv->cur_fw));
260}
261
262static int load_all_firmwares(struct dvb_frontend *fe)
263{
264 struct xc2028_data *priv = fe->tuner_priv;
265 const struct firmware *fw = NULL;
266 const unsigned char *p, *endp;
267 int rc = 0;
268 int n, n_array;
269 char name[33];
270 char *fname;
271
272 tuner_dbg("%s called\n", __func__);
273
274 if (!firmware_name[0])
275 fname = priv->ctrl.fname;
276 else
277 fname = firmware_name;
278
279 tuner_dbg("Reading firmware %s\n", fname);
280 rc = request_firmware(&fw, fname, priv->i2c_props.adap->dev.parent);
281 if (rc < 0) {
282 if (rc == -ENOENT)
283 tuner_err("Error: firmware %s not found.\n",
284 fname);
285 else
286 tuner_err("Error %d while requesting firmware %s \n",
287 rc, fname);
288
289 return rc;
290 }
291 p = fw->data;
292 endp = p + fw->size;
293
294 if (fw->size < sizeof(name) - 1 + 2 + 2) {
295 tuner_err("Error: firmware file %s has invalid size!\n",
296 fname);
297 goto corrupt;
298 }
299
300 memcpy(name, p, sizeof(name) - 1);
301 name[sizeof(name) - 1] = 0;
302 p += sizeof(name) - 1;
303
304 priv->firm_version = get_unaligned_le16(p);
305 p += 2;
306
307 n_array = get_unaligned_le16(p);
308 p += 2;
309
310 tuner_info("Loading %d firmware images from %s, type: %s, ver %d.%d\n",
311 n_array, fname, name,
312 priv->firm_version >> 8, priv->firm_version & 0xff);
313
314 priv->firm = kzalloc(sizeof(*priv->firm) * n_array, GFP_KERNEL);
315 if (priv->firm == NULL) {
316 tuner_err("Not enough memory to load firmware file.\n");
317 rc = -ENOMEM;
318 goto err;
319 }
320 priv->firm_size = n_array;
321
322 n = -1;
323 while (p < endp) {
324 __u32 type, size;
325 v4l2_std_id id;
326 __u16 int_freq = 0;
327
328 n++;
329 if (n >= n_array) {
330 tuner_err("More firmware images in file than "
331 "were expected!\n");
332 goto corrupt;
333 }
334
335 /* Checks if there's enough bytes to read */
336 if (endp - p < sizeof(type) + sizeof(id) + sizeof(size))
337 goto header;
338
339 type = get_unaligned_le32(p);
340 p += sizeof(type);
341
342 id = get_unaligned_le64(p);
343 p += sizeof(id);
344
345 if (type & HAS_IF) {
346 int_freq = get_unaligned_le16(p);
347 p += sizeof(int_freq);
348 if (endp - p < sizeof(size))
349 goto header;
350 }
351
352 size = get_unaligned_le32(p);
353 p += sizeof(size);
354
355 if (!size || size > endp - p) {
356 tuner_err("Firmware type ");
357 dump_firm_type(type);
358 printk("(%x), id %llx is corrupted "
359 "(size=%d, expected %d)\n",
360 type, (unsigned long long)id,
361 (unsigned)(endp - p), size);
362 goto corrupt;
363 }
364
365 priv->firm[n].ptr = kzalloc(size, GFP_KERNEL);
366 if (priv->firm[n].ptr == NULL) {
367 tuner_err("Not enough memory to load firmware file.\n");
368 rc = -ENOMEM;
369 goto err;
370 }
371 tuner_dbg("Reading firmware type ");
372 if (debug) {
373 dump_firm_type_and_int_freq(type, int_freq);
374 printk("(%x), id %llx, size=%d.\n",
375 type, (unsigned long long)id, size);
376 }
377
378 memcpy(priv->firm[n].ptr, p, size);
379 priv->firm[n].type = type;
380 priv->firm[n].id = id;
381 priv->firm[n].size = size;
382 priv->firm[n].int_freq = int_freq;
383
384 p += size;
385 }
386
387 if (n + 1 != priv->firm_size) {
388 tuner_err("Firmware file is incomplete!\n");
389 goto corrupt;
390 }
391
392 goto done;
393
394header:
395 tuner_err("Firmware header is incomplete!\n");
396corrupt:
397 rc = -EINVAL;
398 tuner_err("Error: firmware file is corrupted!\n");
399
400err:
401 tuner_info("Releasing partially loaded firmware file.\n");
402 free_firmware(priv);
403
404done:
405 release_firmware(fw);
406 if (rc == 0)
407 tuner_dbg("Firmware files loaded.\n");
408
409 return rc;
410}
411
412static int seek_firmware(struct dvb_frontend *fe, unsigned int type,
413 v4l2_std_id *id)
414{
415 struct xc2028_data *priv = fe->tuner_priv;
416 int i, best_i = -1, best_nr_matches = 0;
417 unsigned int type_mask = 0;
418
419 tuner_dbg("%s called, want type=", __func__);
420 if (debug) {
421 dump_firm_type(type);
422 printk("(%x), id %016llx.\n", type, (unsigned long long)*id);
423 }
424
425 if (!priv->firm) {
426 tuner_err("Error! firmware not loaded\n");
427 return -EINVAL;
428 }
429
430 if (((type & ~SCODE) == 0) && (*id == 0))
431 *id = V4L2_STD_PAL;
432
433 if (type & BASE)
434 type_mask = BASE_TYPES;
435 else if (type & SCODE) {
436 type &= SCODE_TYPES;
437 type_mask = SCODE_TYPES & ~HAS_IF;
438 } else if (type & DTV_TYPES)
439 type_mask = DTV_TYPES;
440 else if (type & STD_SPECIFIC_TYPES)
441 type_mask = STD_SPECIFIC_TYPES;
442
443 type &= type_mask;
444
445 if (!(type & SCODE))
446 type_mask = ~0;
447
448 /* Seek for exact match */
449 for (i = 0; i < priv->firm_size; i++) {
450 if ((type == (priv->firm[i].type & type_mask)) &&
451 (*id == priv->firm[i].id))
452 goto found;
453 }
454
455 /* Seek for generic video standard match */
456 for (i = 0; i < priv->firm_size; i++) {
457 v4l2_std_id match_mask;
458 int nr_matches;
459
460 if (type != (priv->firm[i].type & type_mask))
461 continue;
462
463 match_mask = *id & priv->firm[i].id;
464 if (!match_mask)
465 continue;
466
467 if ((*id & match_mask) == *id)
468 goto found; /* Supports all the requested standards */
469
470 nr_matches = hweight64(match_mask);
471 if (nr_matches > best_nr_matches) {
472 best_nr_matches = nr_matches;
473 best_i = i;
474 }
475 }
476
477 if (best_nr_matches > 0) {
478 tuner_dbg("Selecting best matching firmware (%d bits) for "
479 "type=", best_nr_matches);
480 dump_firm_type(type);
481 printk("(%x), id %016llx:\n", type, (unsigned long long)*id);
482 i = best_i;
483 goto found;
484 }
485
486 /*FIXME: Would make sense to seek for type "hint" match ? */
487
488 i = -ENOENT;
489 goto ret;
490
491found:
492 *id = priv->firm[i].id;
493
494ret:
495 tuner_dbg("%s firmware for type=", (i < 0) ? "Can't find" : "Found");
496 if (debug) {
497 dump_firm_type(type);
498 printk("(%x), id %016llx.\n", type, (unsigned long long)*id);
499 }
500 return i;
501}
502
503static inline int do_tuner_callback(struct dvb_frontend *fe, int cmd, int arg)
504{
505 struct xc2028_data *priv = fe->tuner_priv;
506
507 /* analog side (tuner-core) uses i2c_adap->algo_data.
508 * digital side is not guaranteed to have algo_data defined.
509 *
510 * digital side will always have fe->dvb defined.
511 * analog side (tuner-core) doesn't (yet) define fe->dvb.
512 */
513
514 return (!fe->callback) ? -EINVAL :
515 fe->callback(((fe->dvb) && (fe->dvb->priv)) ?
516 fe->dvb->priv : priv->i2c_props.adap->algo_data,
517 DVB_FRONTEND_COMPONENT_TUNER, cmd, arg);
518}
519
520static int load_firmware(struct dvb_frontend *fe, unsigned int type,
521 v4l2_std_id *id)
522{
523 struct xc2028_data *priv = fe->tuner_priv;
524 int pos, rc;
525 unsigned char *p, *endp, buf[priv->ctrl.max_len];
526
527 tuner_dbg("%s called\n", __func__);
528
529 pos = seek_firmware(fe, type, id);
530 if (pos < 0)
531 return pos;
532
533 tuner_info("Loading firmware for type=");
534 dump_firm_type(priv->firm[pos].type);
535 printk("(%x), id %016llx.\n", priv->firm[pos].type,
536 (unsigned long long)*id);
537
538 p = priv->firm[pos].ptr;
539 endp = p + priv->firm[pos].size;
540
541 while (p < endp) {
542 __u16 size;
543
544 /* Checks if there's enough bytes to read */
545 if (p + sizeof(size) > endp) {
546 tuner_err("Firmware chunk size is wrong\n");
547 return -EINVAL;
548 }
549
550 size = le16_to_cpu(*(__u16 *) p);
551 p += sizeof(size);
552
553 if (size == 0xffff)
554 return 0;
555
556 if (!size) {
557 /* Special callback command received */
558 rc = do_tuner_callback(fe, XC2028_TUNER_RESET, 0);
559 if (rc < 0) {
560 tuner_err("Error at RESET code %d\n",
561 (*p) & 0x7f);
562 return -EINVAL;
563 }
564 continue;
565 }
566 if (size >= 0xff00) {
567 switch (size) {
568 case 0xff00:
569 rc = do_tuner_callback(fe, XC2028_RESET_CLK, 0);
570 if (rc < 0) {
571 tuner_err("Error at RESET code %d\n",
572 (*p) & 0x7f);
573 return -EINVAL;
574 }
575 break;
576 default:
577 tuner_info("Invalid RESET code %d\n",
578 size & 0x7f);
579 return -EINVAL;
580
581 }
582 continue;
583 }
584
585 /* Checks for a sleep command */
586 if (size & 0x8000) {
587 msleep(size & 0x7fff);
588 continue;
589 }
590
591 if ((size + p > endp)) {
592 tuner_err("missing bytes: need %d, have %d\n",
593 size, (int)(endp - p));
594 return -EINVAL;
595 }
596
597 buf[0] = *p;
598 p++;
599 size--;
600
601 /* Sends message chunks */
602 while (size > 0) {
603 int len = (size < priv->ctrl.max_len - 1) ?
604 size : priv->ctrl.max_len - 1;
605
606 memcpy(buf + 1, p, len);
607
608 rc = i2c_send(priv, buf, len + 1);
609 if (rc < 0) {
610 tuner_err("%d returned from send\n", rc);
611 return -EINVAL;
612 }
613
614 p += len;
615 size -= len;
616 }
617 }
618 return 0;
619}
620
621static int load_scode(struct dvb_frontend *fe, unsigned int type,
622 v4l2_std_id *id, __u16 int_freq, int scode)
623{
624 struct xc2028_data *priv = fe->tuner_priv;
625 int pos, rc;
626 unsigned char *p;
627
628 tuner_dbg("%s called\n", __func__);
629
630 if (!int_freq) {
631 pos = seek_firmware(fe, type, id);
632 if (pos < 0)
633 return pos;
634 } else {
635 for (pos = 0; pos < priv->firm_size; pos++) {
636 if ((priv->firm[pos].int_freq == int_freq) &&
637 (priv->firm[pos].type & HAS_IF))
638 break;
639 }
640 if (pos == priv->firm_size)
641 return -ENOENT;
642 }
643
644 p = priv->firm[pos].ptr;
645
646 if (priv->firm[pos].type & HAS_IF) {
647 if (priv->firm[pos].size != 12 * 16 || scode >= 16)
648 return -EINVAL;
649 p += 12 * scode;
650 } else {
651 /* 16 SCODE entries per file; each SCODE entry is 12 bytes and
652 * has a 2-byte size header in the firmware format. */
653 if (priv->firm[pos].size != 14 * 16 || scode >= 16 ||
654 le16_to_cpu(*(__u16 *)(p + 14 * scode)) != 12)
655 return -EINVAL;
656 p += 14 * scode + 2;
657 }
658
659 tuner_info("Loading SCODE for type=");
660 dump_firm_type_and_int_freq(priv->firm[pos].type,
661 priv->firm[pos].int_freq);
662 printk("(%x), id %016llx.\n", priv->firm[pos].type,
663 (unsigned long long)*id);
664
665 if (priv->firm_version < 0x0202)
666 rc = send_seq(priv, {0x20, 0x00, 0x00, 0x00});
667 else
668 rc = send_seq(priv, {0xa0, 0x00, 0x00, 0x00});
669 if (rc < 0)
670 return -EIO;
671
672 rc = i2c_send(priv, p, 12);
673 if (rc < 0)
674 return -EIO;
675
676 rc = send_seq(priv, {0x00, 0x8c});
677 if (rc < 0)
678 return -EIO;
679
680 return 0;
681}
682
683static int check_firmware(struct dvb_frontend *fe, unsigned int type,
684 v4l2_std_id std, __u16 int_freq)
685{
686 struct xc2028_data *priv = fe->tuner_priv;
687 struct firmware_properties new_fw;
688 int rc = 0, retry_count = 0;
689 u16 version, hwmodel;
690 v4l2_std_id std0;
691
692 tuner_dbg("%s called\n", __func__);
693
694 if (!priv->firm) {
695 if (!priv->ctrl.fname) {
696 tuner_info("xc2028/3028 firmware name not set!\n");
697 return -EINVAL;
698 }
699
700 rc = load_all_firmwares(fe);
701 if (rc < 0)
702 return rc;
703 }
704
705 if (priv->ctrl.mts && !(type & FM))
706 type |= MTS;
707
708retry:
709 new_fw.type = type;
710 new_fw.id = std;
711 new_fw.std_req = std;
712 new_fw.scode_table = SCODE | priv->ctrl.scode_table;
713 new_fw.scode_nr = 0;
714 new_fw.int_freq = int_freq;
715
716 tuner_dbg("checking firmware, user requested type=");
717 if (debug) {
718 dump_firm_type(new_fw.type);
719 printk("(%x), id %016llx, ", new_fw.type,
720 (unsigned long long)new_fw.std_req);
721 if (!int_freq) {
722 printk("scode_tbl ");
723 dump_firm_type(priv->ctrl.scode_table);
724 printk("(%x), ", priv->ctrl.scode_table);
725 } else
726 printk("int_freq %d, ", new_fw.int_freq);
727 printk("scode_nr %d\n", new_fw.scode_nr);
728 }
729
730 /* No need to reload base firmware if it matches */
731 if (((BASE | new_fw.type) & BASE_TYPES) ==
732 (priv->cur_fw.type & BASE_TYPES)) {
733 tuner_dbg("BASE firmware not changed.\n");
734 goto skip_base;
735 }
736
737 /* Updating BASE - forget about all currently loaded firmware */
738 memset(&priv->cur_fw, 0, sizeof(priv->cur_fw));
739
740 /* Reset is needed before loading firmware */
741 rc = do_tuner_callback(fe, XC2028_TUNER_RESET, 0);
742 if (rc < 0)
743 goto fail;
744
745 /* BASE firmwares are all std0 */
746 std0 = 0;
747 rc = load_firmware(fe, BASE | new_fw.type, &std0);
748 if (rc < 0) {
749 tuner_err("Error %d while loading base firmware\n",
750 rc);
751 goto fail;
752 }
753
754 /* Load INIT1, if needed */
755 tuner_dbg("Load init1 firmware, if exists\n");
756
757 rc = load_firmware(fe, BASE | INIT1 | new_fw.type, &std0);
758 if (rc == -ENOENT)
759 rc = load_firmware(fe, (BASE | INIT1 | new_fw.type) & ~F8MHZ,
760 &std0);
761 if (rc < 0 && rc != -ENOENT) {
762 tuner_err("Error %d while loading init1 firmware\n",
763 rc);
764 goto fail;
765 }
766
767skip_base:
768 /*
769 * No need to reload standard specific firmware if base firmware
770 * was not reloaded and requested video standards have not changed.
771 */
772 if (priv->cur_fw.type == (BASE | new_fw.type) &&
773 priv->cur_fw.std_req == std) {
774 tuner_dbg("Std-specific firmware already loaded.\n");
775 goto skip_std_specific;
776 }
777
778 /* Reloading std-specific firmware forces a SCODE update */
779 priv->cur_fw.scode_table = 0;
780
781 rc = load_firmware(fe, new_fw.type, &new_fw.id);
782 if (rc == -ENOENT)
783 rc = load_firmware(fe, new_fw.type & ~F8MHZ, &new_fw.id);
784
785 if (rc < 0)
786 goto fail;
787
788skip_std_specific:
789 if (priv->cur_fw.scode_table == new_fw.scode_table &&
790 priv->cur_fw.scode_nr == new_fw.scode_nr) {
791 tuner_dbg("SCODE firmware already loaded.\n");
792 goto check_device;
793 }
794
795 if (new_fw.type & FM)
796 goto check_device;
797
798 /* Load SCODE firmware, if exists */
799 tuner_dbg("Trying to load scode %d\n", new_fw.scode_nr);
800
801 rc = load_scode(fe, new_fw.type | new_fw.scode_table, &new_fw.id,
802 new_fw.int_freq, new_fw.scode_nr);
803
804check_device:
805 if (xc2028_get_reg(priv, 0x0004, &version) < 0 ||
806 xc2028_get_reg(priv, 0x0008, &hwmodel) < 0) {
807 tuner_err("Unable to read tuner registers.\n");
808 goto fail;
809 }
810
811 tuner_dbg("Device is Xceive %d version %d.%d, "
812 "firmware version %d.%d\n",
813 hwmodel, (version & 0xf000) >> 12, (version & 0xf00) >> 8,
814 (version & 0xf0) >> 4, version & 0xf);
815
816
817 if (priv->ctrl.read_not_reliable)
818 goto read_not_reliable;
819
820 /* Check firmware version against what we downloaded. */
821 if (priv->firm_version != ((version & 0xf0) << 4 | (version & 0x0f))) {
822 if (!priv->ctrl.read_not_reliable) {
823 tuner_err("Incorrect readback of firmware version.\n");
824 goto fail;
825 } else {
826 tuner_err("Returned an incorrect version. However, "
827 "read is not reliable enough. Ignoring it.\n");
828 hwmodel = 3028;
829 }
830 }
831
832 /* Check that the tuner hardware model remains consistent over time. */
833 if (priv->hwmodel == 0 && (hwmodel == 2028 || hwmodel == 3028)) {
834 priv->hwmodel = hwmodel;
835 priv->hwvers = version & 0xff00;
836 } else if (priv->hwmodel == 0 || priv->hwmodel != hwmodel ||
837 priv->hwvers != (version & 0xff00)) {
838 tuner_err("Read invalid device hardware information - tuner "
839 "hung?\n");
840 goto fail;
841 }
842
843read_not_reliable:
844 memcpy(&priv->cur_fw, &new_fw, sizeof(priv->cur_fw));
845
846 /*
847 * By setting BASE in cur_fw.type only after successfully loading all
848 * firmwares, we can:
849 * 1. Identify that BASE firmware with type=0 has been loaded;
850 * 2. Tell whether BASE firmware was just changed the next time through.
851 */
852 priv->cur_fw.type |= BASE;
853
854 return 0;
855
856fail:
857 memset(&priv->cur_fw, 0, sizeof(priv->cur_fw));
858 if (retry_count < 8) {
859 msleep(50);
860 retry_count++;
861 tuner_dbg("Retrying firmware load\n");
862 goto retry;
863 }
864
865 if (rc == -ENOENT)
866 rc = -EINVAL;
867 return rc;
868}
869
870static int xc2028_signal(struct dvb_frontend *fe, u16 *strength)
871{
872 struct xc2028_data *priv = fe->tuner_priv;
873 u16 frq_lock, signal = 0;
874 int rc;
875
876 tuner_dbg("%s called\n", __func__);
877
878 mutex_lock(&priv->lock);
879
880 /* Sync Lock Indicator */
881 rc = xc2028_get_reg(priv, 0x0002, &frq_lock);
882 if (rc < 0)
883 goto ret;
884
885 /* Frequency is locked */
886 if (frq_lock == 1)
887 signal = 32768;
888
889 /* Get SNR of the video signal */
890 rc = xc2028_get_reg(priv, 0x0040, &signal);
891 if (rc < 0)
892 goto ret;
893
894 /* Use both frq_lock and signal to generate the result */
895 signal = signal || ((signal & 0x07) << 12);
896
897ret:
898 mutex_unlock(&priv->lock);
899
900 *strength = signal;
901
902 tuner_dbg("signal strength is %d\n", signal);
903
904 return rc;
905}
906
907#define DIV 15625
908
909static int generic_set_freq(struct dvb_frontend *fe, u32 freq /* in HZ */,
910 enum v4l2_tuner_type new_type,
911 unsigned int type,
912 v4l2_std_id std,
913 u16 int_freq)
914{
915 struct xc2028_data *priv = fe->tuner_priv;
916 int rc = -EINVAL;
917 unsigned char buf[4];
918 u32 div, offset = 0;
919
920 tuner_dbg("%s called\n", __func__);
921
922 mutex_lock(&priv->lock);
923
924 tuner_dbg("should set frequency %d kHz\n", freq / 1000);
925
926 if (check_firmware(fe, type, std, int_freq) < 0)
927 goto ret;
928
929 /* On some cases xc2028 can disable video output, if
930 * very weak signals are received. By sending a soft
931 * reset, this is re-enabled. So, it is better to always
932 * send a soft reset before changing channels, to be sure
933 * that xc2028 will be in a safe state.
934 * Maybe this might also be needed for DTV.
935 */
936 if (new_type == V4L2_TUNER_ANALOG_TV) {
937 rc = send_seq(priv, {0x00, 0x00});
938
939 /* Analog modes require offset = 0 */
940 } else {
941 /*
942 * Digital modes require an offset to adjust to the
943 * proper frequency. The offset depends on what
944 * firmware version is used.
945 */
946
947 /*
948 * Adjust to the center frequency. This is calculated by the
949 * formula: offset = 1.25MHz - BW/2
950 * For DTV 7/8, the firmware uses BW = 8000, so it needs a
951 * further adjustment to get the frequency center on VHF
952 */
953 if (priv->cur_fw.type & DTV6)
954 offset = 1750000;
955 else if (priv->cur_fw.type & DTV7)
956 offset = 2250000;
957 else /* DTV8 or DTV78 */
958 offset = 2750000;
959 if ((priv->cur_fw.type & DTV78) && freq < 470000000)
960 offset -= 500000;
961
962 /*
963 * xc3028 additional "magic"
964 * Depending on the firmware version, it needs some adjustments
965 * to properly centralize the frequency. This seems to be
966 * needed to compensate the SCODE table adjustments made by
967 * newer firmwares
968 */
969
970#if 1
971 /*
972 * The proper adjustment would be to do it at s-code table.
973 * However, this didn't work, as reported by
974 * Robert Lowery <rglowery@exemail.com.au>
975 */
976
977 if (priv->cur_fw.type & DTV7)
978 offset += 500000;
979
980#else
981 /*
982 * Still need tests for XC3028L (firmware 3.2 or upper)
983 * So, for now, let's just comment the per-firmware
984 * version of this change. Reports with xc3028l working
985 * with and without the lines bellow are welcome
986 */
987
988 if (priv->firm_version < 0x0302) {
989 if (priv->cur_fw.type & DTV7)
990 offset += 500000;
991 } else {
992 if (priv->cur_fw.type & DTV7)
993 offset -= 300000;
994 else if (type != ATSC) /* DVB @6MHz, DTV 8 and DTV 7/8 */
995 offset += 200000;
996 }
997#endif
998 }
999
1000 div = (freq - offset + DIV / 2) / DIV;
1001
1002 /* CMD= Set frequency */
1003 if (priv->firm_version < 0x0202)
1004 rc = send_seq(priv, {0x00, 0x02, 0x00, 0x00});
1005 else
1006 rc = send_seq(priv, {0x80, 0x02, 0x00, 0x00});
1007 if (rc < 0)
1008 goto ret;
1009
1010 /* Return code shouldn't be checked.
1011 The reset CLK is needed only with tm6000.
1012 Driver should work fine even if this fails.
1013 */
1014 if (priv->ctrl.msleep)
1015 msleep(priv->ctrl.msleep);
1016 do_tuner_callback(fe, XC2028_RESET_CLK, 1);
1017
1018 msleep(10);
1019
1020 buf[0] = 0xff & (div >> 24);
1021 buf[1] = 0xff & (div >> 16);
1022 buf[2] = 0xff & (div >> 8);
1023 buf[3] = 0xff & (div);
1024
1025 rc = i2c_send(priv, buf, sizeof(buf));
1026 if (rc < 0)
1027 goto ret;
1028 msleep(100);
1029
1030 priv->frequency = freq;
1031
1032 tuner_dbg("divisor= %02x %02x %02x %02x (freq=%d.%03d)\n",
1033 buf[0], buf[1], buf[2], buf[3],
1034 freq / 1000000, (freq % 1000000) / 1000);
1035
1036 rc = 0;
1037
1038ret:
1039 mutex_unlock(&priv->lock);
1040
1041 return rc;
1042}
1043
1044static int xc2028_set_analog_freq(struct dvb_frontend *fe,
1045 struct analog_parameters *p)
1046{
1047 struct xc2028_data *priv = fe->tuner_priv;
1048 unsigned int type=0;
1049
1050 tuner_dbg("%s called\n", __func__);
1051
1052 if (p->mode == V4L2_TUNER_RADIO) {
1053 type |= FM;
1054 if (priv->ctrl.input1)
1055 type |= INPUT1;
1056 return generic_set_freq(fe, (625l * p->frequency) / 10,
1057 V4L2_TUNER_RADIO, type, 0, 0);
1058 }
1059
1060 /* if std is not defined, choose one */
1061 if (!p->std)
1062 p->std = V4L2_STD_MN;
1063
1064 /* PAL/M, PAL/N, PAL/Nc and NTSC variants should use 6MHz firmware */
1065 if (!(p->std & V4L2_STD_MN))
1066 type |= F8MHZ;
1067
1068 /* Add audio hack to std mask */
1069 p->std |= parse_audio_std_option();
1070
1071 return generic_set_freq(fe, 62500l * p->frequency,
1072 V4L2_TUNER_ANALOG_TV, type, p->std, 0);
1073}
1074
1075static int xc2028_set_params(struct dvb_frontend *fe,
1076 struct dvb_frontend_parameters *p)
1077{
1078 struct xc2028_data *priv = fe->tuner_priv;
1079 unsigned int type=0;
1080 fe_bandwidth_t bw = BANDWIDTH_8_MHZ;
1081 u16 demod = 0;
1082
1083 tuner_dbg("%s called\n", __func__);
1084
1085 switch(fe->ops.info.type) {
1086 case FE_OFDM:
1087 bw = p->u.ofdm.bandwidth;
1088 /*
1089 * The only countries with 6MHz seem to be Taiwan/Uruguay.
1090 * Both seem to require QAM firmware for OFDM decoding
1091 * Tested in Taiwan by Terry Wu <terrywu2009@gmail.com>
1092 */
1093 if (bw == BANDWIDTH_6_MHZ)
1094 type |= QAM;
1095 break;
1096 case FE_ATSC:
1097 bw = BANDWIDTH_6_MHZ;
1098 /* The only ATSC firmware (at least on v2.7) is D2633 */
1099 type |= ATSC | D2633;
1100 break;
1101 /* DVB-S and pure QAM (FE_QAM) are not supported */
1102 default:
1103 return -EINVAL;
1104 }
1105
1106 switch (bw) {
1107 case BANDWIDTH_8_MHZ:
1108 if (p->frequency < 470000000)
1109 priv->ctrl.vhfbw7 = 0;
1110 else
1111 priv->ctrl.uhfbw8 = 1;
1112 type |= (priv->ctrl.vhfbw7 && priv->ctrl.uhfbw8) ? DTV78 : DTV8;
1113 type |= F8MHZ;
1114 break;
1115 case BANDWIDTH_7_MHZ:
1116 if (p->frequency < 470000000)
1117 priv->ctrl.vhfbw7 = 1;
1118 else
1119 priv->ctrl.uhfbw8 = 0;
1120 type |= (priv->ctrl.vhfbw7 && priv->ctrl.uhfbw8) ? DTV78 : DTV7;
1121 type |= F8MHZ;
1122 break;
1123 case BANDWIDTH_6_MHZ:
1124 type |= DTV6;
1125 priv->ctrl.vhfbw7 = 0;
1126 priv->ctrl.uhfbw8 = 0;
1127 break;
1128 default:
1129 tuner_err("error: bandwidth not supported.\n");
1130 };
1131
1132 /*
1133 Selects between D2633 or D2620 firmware.
1134 It doesn't make sense for ATSC, since it should be D2633 on all cases
1135 */
1136 if (fe->ops.info.type != FE_ATSC) {
1137 switch (priv->ctrl.type) {
1138 case XC2028_D2633:
1139 type |= D2633;
1140 break;
1141 case XC2028_D2620:
1142 type |= D2620;
1143 break;
1144 case XC2028_AUTO:
1145 default:
1146 /* Zarlink seems to need D2633 */
1147 if (priv->ctrl.demod == XC3028_FE_ZARLINK456)
1148 type |= D2633;
1149 else
1150 type |= D2620;
1151 }
1152 }
1153
1154 /* All S-code tables need a 200kHz shift */
1155 if (priv->ctrl.demod) {
1156 demod = priv->ctrl.demod;
1157
1158 /*
1159 * Newer firmwares require a 200 kHz offset only for ATSC
1160 */
1161 if (type == ATSC || priv->firm_version < 0x0302)
1162 demod += 200;
1163 /*
1164 * The DTV7 S-code table needs a 700 kHz shift.
1165 *
1166 * DTV7 is only used in Australia. Germany or Italy may also
1167 * use this firmware after initialization, but a tune to a UHF
1168 * channel should then cause DTV78 to be used.
1169 *
1170 * Unfortunately, on real-field tests, the s-code offset
1171 * didn't work as expected, as reported by
1172 * Robert Lowery <rglowery@exemail.com.au>
1173 */
1174 }
1175
1176 return generic_set_freq(fe, p->frequency,
1177 V4L2_TUNER_DIGITAL_TV, type, 0, demod);
1178}
1179
1180static int xc2028_sleep(struct dvb_frontend *fe)
1181{
1182 struct xc2028_data *priv = fe->tuner_priv;
1183 int rc = 0;
1184
1185 /* Avoid firmware reload on slow devices or if PM disabled */
1186 if (no_poweroff || priv->ctrl.disable_power_mgmt)
1187 return 0;
1188
1189 tuner_dbg("Putting xc2028/3028 into poweroff mode.\n");
1190 if (debug > 1) {
1191 tuner_dbg("Printing sleep stack trace:\n");
1192 dump_stack();
1193 }
1194
1195 mutex_lock(&priv->lock);
1196
1197 if (priv->firm_version < 0x0202)
1198 rc = send_seq(priv, {0x00, 0x08, 0x00, 0x00});
1199 else
1200 rc = send_seq(priv, {0x80, 0x08, 0x00, 0x00});
1201
1202 priv->cur_fw.type = 0; /* need firmware reload */
1203
1204 mutex_unlock(&priv->lock);
1205
1206 return rc;
1207}
1208
1209static int xc2028_dvb_release(struct dvb_frontend *fe)
1210{
1211 struct xc2028_data *priv = fe->tuner_priv;
1212
1213 tuner_dbg("%s called\n", __func__);
1214
1215 mutex_lock(&xc2028_list_mutex);
1216
1217 /* only perform final cleanup if this is the last instance */
1218 if (hybrid_tuner_report_instance_count(priv) == 1) {
1219 kfree(priv->ctrl.fname);
1220 free_firmware(priv);
1221 }
1222
1223 if (priv)
1224 hybrid_tuner_release_state(priv);
1225
1226 mutex_unlock(&xc2028_list_mutex);
1227
1228 fe->tuner_priv = NULL;
1229
1230 return 0;
1231}
1232
1233static int xc2028_get_frequency(struct dvb_frontend *fe, u32 *frequency)
1234{
1235 struct xc2028_data *priv = fe->tuner_priv;
1236
1237 tuner_dbg("%s called\n", __func__);
1238
1239 *frequency = priv->frequency;
1240
1241 return 0;
1242}
1243
1244static int xc2028_set_config(struct dvb_frontend *fe, void *priv_cfg)
1245{
1246 struct xc2028_data *priv = fe->tuner_priv;
1247 struct xc2028_ctrl *p = priv_cfg;
1248 int rc = 0;
1249
1250 tuner_dbg("%s called\n", __func__);
1251
1252 mutex_lock(&priv->lock);
1253
1254 memcpy(&priv->ctrl, p, sizeof(priv->ctrl));
1255 if (priv->ctrl.max_len < 9)
1256 priv->ctrl.max_len = 13;
1257
1258 if (p->fname) {
1259 if (priv->ctrl.fname && strcmp(p->fname, priv->ctrl.fname)) {
1260 kfree(priv->ctrl.fname);
1261 free_firmware(priv);
1262 }
1263
1264 priv->ctrl.fname = kstrdup(p->fname, GFP_KERNEL);
1265 if (priv->ctrl.fname == NULL)
1266 rc = -ENOMEM;
1267 }
1268
1269 mutex_unlock(&priv->lock);
1270
1271 return rc;
1272}
1273
1274static const struct dvb_tuner_ops xc2028_dvb_tuner_ops = {
1275 .info = {
1276 .name = "Xceive XC3028",
1277 .frequency_min = 42000000,
1278 .frequency_max = 864000000,
1279 .frequency_step = 50000,
1280 },
1281
1282 .set_config = xc2028_set_config,
1283 .set_analog_params = xc2028_set_analog_freq,
1284 .release = xc2028_dvb_release,
1285 .get_frequency = xc2028_get_frequency,
1286 .get_rf_strength = xc2028_signal,
1287 .set_params = xc2028_set_params,
1288 .sleep = xc2028_sleep,
1289};
1290
1291struct dvb_frontend *xc2028_attach(struct dvb_frontend *fe,
1292 struct xc2028_config *cfg)
1293{
1294 struct xc2028_data *priv;
1295 int instance;
1296
1297 if (debug)
1298 printk(KERN_DEBUG "xc2028: Xcv2028/3028 init called!\n");
1299
1300 if (NULL == cfg)
1301 return NULL;
1302
1303 if (!fe) {
1304 printk(KERN_ERR "xc2028: No frontend!\n");
1305 return NULL;
1306 }
1307
1308 mutex_lock(&xc2028_list_mutex);
1309
1310 instance = hybrid_tuner_request_state(struct xc2028_data, priv,
1311 hybrid_tuner_instance_list,
1312 cfg->i2c_adap, cfg->i2c_addr,
1313 "xc2028");
1314 switch (instance) {
1315 case 0:
1316 /* memory allocation failure */
1317 goto fail;
1318 break;
1319 case 1:
1320 /* new tuner instance */
1321 priv->ctrl.max_len = 13;
1322
1323 mutex_init(&priv->lock);
1324
1325 fe->tuner_priv = priv;
1326 break;
1327 case 2:
1328 /* existing tuner instance */
1329 fe->tuner_priv = priv;
1330 break;
1331 }
1332
1333 memcpy(&fe->ops.tuner_ops, &xc2028_dvb_tuner_ops,
1334 sizeof(xc2028_dvb_tuner_ops));
1335
1336 tuner_info("type set to %s\n", "XCeive xc2028/xc3028 tuner");
1337
1338 if (cfg->ctrl)
1339 xc2028_set_config(fe, cfg->ctrl);
1340
1341 mutex_unlock(&xc2028_list_mutex);
1342
1343 return fe;
1344fail:
1345 mutex_unlock(&xc2028_list_mutex);
1346
1347 xc2028_dvb_release(fe);
1348 return NULL;
1349}
1350
1351EXPORT_SYMBOL(xc2028_attach);
1352
1353MODULE_DESCRIPTION("Xceive xc2028/xc3028 tuner driver");
1354MODULE_AUTHOR("Michel Ludwig <michel.ludwig@gmail.com>");
1355MODULE_AUTHOR("Mauro Carvalho Chehab <mchehab@infradead.org>");
1356MODULE_LICENSE("GPL");
diff --git a/drivers/media/common/tuners/tuner-xc2028.h b/drivers/media/common/tuners/tuner-xc2028.h
new file mode 100644
index 00000000000..9778c96a500
--- /dev/null
+++ b/drivers/media/common/tuners/tuner-xc2028.h
@@ -0,0 +1,71 @@
1/* tuner-xc2028
2 *
3 * Copyright (c) 2007-2008 Mauro Carvalho Chehab (mchehab@infradead.org)
4 * This code is placed under the terms of the GNU General Public License v2
5 */
6
7#ifndef __TUNER_XC2028_H__
8#define __TUNER_XC2028_H__
9
10#include "dvb_frontend.h"
11
12#define XC2028_DEFAULT_FIRMWARE "xc3028-v27.fw"
13#define XC3028L_DEFAULT_FIRMWARE "xc3028L-v36.fw"
14
15/* Dmoduler IF (kHz) */
16#define XC3028_FE_DEFAULT 0 /* Don't load SCODE */
17#define XC3028_FE_LG60 6000
18#define XC3028_FE_ATI638 6380
19#define XC3028_FE_OREN538 5380
20#define XC3028_FE_OREN36 3600
21#define XC3028_FE_TOYOTA388 3880
22#define XC3028_FE_TOYOTA794 7940
23#define XC3028_FE_DIBCOM52 5200
24#define XC3028_FE_ZARLINK456 4560
25#define XC3028_FE_CHINA 5200
26
27enum firmware_type {
28 XC2028_AUTO = 0, /* By default, auto-detects */
29 XC2028_D2633,
30 XC2028_D2620,
31};
32
33struct xc2028_ctrl {
34 char *fname;
35 int max_len;
36 int msleep;
37 unsigned int scode_table;
38 unsigned int mts :1;
39 unsigned int input1:1;
40 unsigned int vhfbw7:1;
41 unsigned int uhfbw8:1;
42 unsigned int disable_power_mgmt:1;
43 unsigned int read_not_reliable:1;
44 unsigned int demod;
45 enum firmware_type type:2;
46};
47
48struct xc2028_config {
49 struct i2c_adapter *i2c_adap;
50 u8 i2c_addr;
51 struct xc2028_ctrl *ctrl;
52};
53
54/* xc2028 commands for callback */
55#define XC2028_TUNER_RESET 0
56#define XC2028_RESET_CLK 1
57
58#if defined(CONFIG_MEDIA_TUNER_XC2028) || (defined(CONFIG_MEDIA_TUNER_XC2028_MODULE) && defined(MODULE))
59extern struct dvb_frontend *xc2028_attach(struct dvb_frontend *fe,
60 struct xc2028_config *cfg);
61#else
62static inline struct dvb_frontend *xc2028_attach(struct dvb_frontend *fe,
63 struct xc2028_config *cfg)
64{
65 printk(KERN_INFO "%s: not probed - driver disabled by Kconfig\n",
66 __func__);
67 return NULL;
68}
69#endif
70
71#endif /* __TUNER_XC2028_H__ */
diff --git a/drivers/media/common/tuners/xc4000.c b/drivers/media/common/tuners/xc4000.c
new file mode 100644
index 00000000000..634f4d9b6c6
--- /dev/null
+++ b/drivers/media/common/tuners/xc4000.c
@@ -0,0 +1,1691 @@
1/*
2 * Driver for Xceive XC4000 "QAM/8VSB single chip tuner"
3 *
4 * Copyright (c) 2007 Xceive Corporation
5 * Copyright (c) 2007 Steven Toth <stoth@linuxtv.org>
6 * Copyright (c) 2009 Devin Heitmueller <dheitmueller@kernellabs.com>
7 * Copyright (c) 2009 Davide Ferri <d.ferri@zero11.it>
8 * Copyright (c) 2010 Istvan Varga <istvan_v@mailbox.hu>
9 *
10 * This program is free software; you can redistribute it and/or modify
11 * it under the terms of the GNU General Public License as published by
12 * the Free Software Foundation; either version 2 of the License, or
13 * (at your option) any later version.
14 *
15 * This program is distributed in the hope that it will be useful,
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 * GNU General Public License for more details.
19 *
20 * You should have received a copy of the GNU General Public License
21 * along with this program; if not, write to the Free Software
22 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
23 */
24
25#include <linux/module.h>
26#include <linux/moduleparam.h>
27#include <linux/videodev2.h>
28#include <linux/delay.h>
29#include <linux/dvb/frontend.h>
30#include <linux/i2c.h>
31#include <linux/mutex.h>
32#include <asm/unaligned.h>
33
34#include "dvb_frontend.h"
35
36#include "xc4000.h"
37#include "tuner-i2c.h"
38#include "tuner-xc2028-types.h"
39
40static int debug;
41module_param(debug, int, 0644);
42MODULE_PARM_DESC(debug, "Debugging level (0 to 2, default: 0 (off)).");
43
44static int no_poweroff;
45module_param(no_poweroff, int, 0644);
46MODULE_PARM_DESC(no_poweroff, "Power management (1: disabled, 2: enabled, "
47 "0 (default): use device-specific default mode).");
48
49static int audio_std;
50module_param(audio_std, int, 0644);
51MODULE_PARM_DESC(audio_std, "Audio standard. XC4000 audio decoder explicitly "
52 "needs to know what audio standard is needed for some video standards "
53 "with audio A2 or NICAM. The valid settings are a sum of:\n"
54 " 1: use NICAM/B or A2/B instead of NICAM/A or A2/A\n"
55 " 2: use A2 instead of NICAM or BTSC\n"
56 " 4: use SECAM/K3 instead of K1\n"
57 " 8: use PAL-D/K audio for SECAM-D/K\n"
58 "16: use FM radio input 1 instead of input 2\n"
59 "32: use mono audio (the lower three bits are ignored)");
60
61static char firmware_name[30];
62module_param_string(firmware_name, firmware_name, sizeof(firmware_name), 0);
63MODULE_PARM_DESC(firmware_name, "Firmware file name. Allows overriding the "
64 "default firmware name.");
65
66static DEFINE_MUTEX(xc4000_list_mutex);
67static LIST_HEAD(hybrid_tuner_instance_list);
68
69#define dprintk(level, fmt, arg...) if (debug >= level) \
70 printk(KERN_INFO "%s: " fmt, "xc4000", ## arg)
71
72/* struct for storing firmware table */
73struct firmware_description {
74 unsigned int type;
75 v4l2_std_id id;
76 __u16 int_freq;
77 unsigned char *ptr;
78 unsigned int size;
79};
80
81struct firmware_properties {
82 unsigned int type;
83 v4l2_std_id id;
84 v4l2_std_id std_req;
85 __u16 int_freq;
86 unsigned int scode_table;
87 int scode_nr;
88};
89
90struct xc4000_priv {
91 struct tuner_i2c_props i2c_props;
92 struct list_head hybrid_tuner_instance_list;
93 struct firmware_description *firm;
94 int firm_size;
95 u32 if_khz;
96 u32 freq_hz;
97 u32 bandwidth;
98 u8 video_standard;
99 u8 rf_mode;
100 u8 default_pm;
101 u8 dvb_amplitude;
102 u8 set_smoothedcvbs;
103 u8 ignore_i2c_write_errors;
104 __u16 firm_version;
105 struct firmware_properties cur_fw;
106 __u16 hwmodel;
107 __u16 hwvers;
108 struct mutex lock;
109};
110
111#define XC4000_AUDIO_STD_B 1
112#define XC4000_AUDIO_STD_A2 2
113#define XC4000_AUDIO_STD_K3 4
114#define XC4000_AUDIO_STD_L 8
115#define XC4000_AUDIO_STD_INPUT1 16
116#define XC4000_AUDIO_STD_MONO 32
117
118#define XC4000_DEFAULT_FIRMWARE "dvb-fe-xc4000-1.4.fw"
119
120/* Misc Defines */
121#define MAX_TV_STANDARD 24
122#define XC_MAX_I2C_WRITE_LENGTH 64
123#define XC_POWERED_DOWN 0x80000000U
124
125/* Signal Types */
126#define XC_RF_MODE_AIR 0
127#define XC_RF_MODE_CABLE 1
128
129/* Product id */
130#define XC_PRODUCT_ID_FW_NOT_LOADED 0x2000
131#define XC_PRODUCT_ID_XC4000 0x0FA0
132#define XC_PRODUCT_ID_XC4100 0x1004
133
134/* Registers (Write-only) */
135#define XREG_INIT 0x00
136#define XREG_VIDEO_MODE 0x01
137#define XREG_AUDIO_MODE 0x02
138#define XREG_RF_FREQ 0x03
139#define XREG_D_CODE 0x04
140#define XREG_DIRECTSITTING_MODE 0x05
141#define XREG_SEEK_MODE 0x06
142#define XREG_POWER_DOWN 0x08
143#define XREG_SIGNALSOURCE 0x0A
144#define XREG_SMOOTHEDCVBS 0x0E
145#define XREG_AMPLITUDE 0x10
146
147/* Registers (Read-only) */
148#define XREG_ADC_ENV 0x00
149#define XREG_QUALITY 0x01
150#define XREG_FRAME_LINES 0x02
151#define XREG_HSYNC_FREQ 0x03
152#define XREG_LOCK 0x04
153#define XREG_FREQ_ERROR 0x05
154#define XREG_SNR 0x06
155#define XREG_VERSION 0x07
156#define XREG_PRODUCT_ID 0x08
157
158/*
159 Basic firmware description. This will remain with
160 the driver for documentation purposes.
161
162 This represents an I2C firmware file encoded as a
163 string of unsigned char. Format is as follows:
164
165 char[0 ]=len0_MSB -> len = len_MSB * 256 + len_LSB
166 char[1 ]=len0_LSB -> length of first write transaction
167 char[2 ]=data0 -> first byte to be sent
168 char[3 ]=data1
169 char[4 ]=data2
170 char[ ]=...
171 char[M ]=dataN -> last byte to be sent
172 char[M+1]=len1_MSB -> len = len_MSB * 256 + len_LSB
173 char[M+2]=len1_LSB -> length of second write transaction
174 char[M+3]=data0
175 char[M+4]=data1
176 ...
177 etc.
178
179 The [len] value should be interpreted as follows:
180
181 len= len_MSB _ len_LSB
182 len=1111_1111_1111_1111 : End of I2C_SEQUENCE
183 len=0000_0000_0000_0000 : Reset command: Do hardware reset
184 len=0NNN_NNNN_NNNN_NNNN : Normal transaction: number of bytes = {1:32767)
185 len=1WWW_WWWW_WWWW_WWWW : Wait command: wait for {1:32767} ms
186
187 For the RESET and WAIT commands, the two following bytes will contain
188 immediately the length of the following transaction.
189*/
190
191struct XC_TV_STANDARD {
192 const char *Name;
193 u16 audio_mode;
194 u16 video_mode;
195 u16 int_freq;
196};
197
198/* Tuner standards */
199#define XC4000_MN_NTSC_PAL_BTSC 0
200#define XC4000_MN_NTSC_PAL_A2 1
201#define XC4000_MN_NTSC_PAL_EIAJ 2
202#define XC4000_MN_NTSC_PAL_Mono 3
203#define XC4000_BG_PAL_A2 4
204#define XC4000_BG_PAL_NICAM 5
205#define XC4000_BG_PAL_MONO 6
206#define XC4000_I_PAL_NICAM 7
207#define XC4000_I_PAL_NICAM_MONO 8
208#define XC4000_DK_PAL_A2 9
209#define XC4000_DK_PAL_NICAM 10
210#define XC4000_DK_PAL_MONO 11
211#define XC4000_DK_SECAM_A2DK1 12
212#define XC4000_DK_SECAM_A2LDK3 13
213#define XC4000_DK_SECAM_A2MONO 14
214#define XC4000_DK_SECAM_NICAM 15
215#define XC4000_L_SECAM_NICAM 16
216#define XC4000_LC_SECAM_NICAM 17
217#define XC4000_DTV6 18
218#define XC4000_DTV8 19
219#define XC4000_DTV7_8 20
220#define XC4000_DTV7 21
221#define XC4000_FM_Radio_INPUT2 22
222#define XC4000_FM_Radio_INPUT1 23
223
224static struct XC_TV_STANDARD xc4000_standard[MAX_TV_STANDARD] = {
225 {"M/N-NTSC/PAL-BTSC", 0x0000, 0x80A0, 4500},
226 {"M/N-NTSC/PAL-A2", 0x0000, 0x80A0, 4600},
227 {"M/N-NTSC/PAL-EIAJ", 0x0040, 0x80A0, 4500},
228 {"M/N-NTSC/PAL-Mono", 0x0078, 0x80A0, 4500},
229 {"B/G-PAL-A2", 0x0000, 0x8159, 5640},
230 {"B/G-PAL-NICAM", 0x0004, 0x8159, 5740},
231 {"B/G-PAL-MONO", 0x0078, 0x8159, 5500},
232 {"I-PAL-NICAM", 0x0080, 0x8049, 6240},
233 {"I-PAL-NICAM-MONO", 0x0078, 0x8049, 6000},
234 {"D/K-PAL-A2", 0x0000, 0x8049, 6380},
235 {"D/K-PAL-NICAM", 0x0080, 0x8049, 6200},
236 {"D/K-PAL-MONO", 0x0078, 0x8049, 6500},
237 {"D/K-SECAM-A2 DK1", 0x0000, 0x8049, 6340},
238 {"D/K-SECAM-A2 L/DK3", 0x0000, 0x8049, 6000},
239 {"D/K-SECAM-A2 MONO", 0x0078, 0x8049, 6500},
240 {"D/K-SECAM-NICAM", 0x0080, 0x8049, 6200},
241 {"L-SECAM-NICAM", 0x8080, 0x0009, 6200},
242 {"L'-SECAM-NICAM", 0x8080, 0x4009, 6200},
243 {"DTV6", 0x00C0, 0x8002, 0},
244 {"DTV8", 0x00C0, 0x800B, 0},
245 {"DTV7/8", 0x00C0, 0x801B, 0},
246 {"DTV7", 0x00C0, 0x8007, 0},
247 {"FM Radio-INPUT2", 0x0008, 0x9800, 10700},
248 {"FM Radio-INPUT1", 0x0008, 0x9000, 10700}
249};
250
251static int xc4000_readreg(struct xc4000_priv *priv, u16 reg, u16 *val);
252static int xc4000_tuner_reset(struct dvb_frontend *fe);
253static void xc_debug_dump(struct xc4000_priv *priv);
254
255static int xc_send_i2c_data(struct xc4000_priv *priv, u8 *buf, int len)
256{
257 struct i2c_msg msg = { .addr = priv->i2c_props.addr,
258 .flags = 0, .buf = buf, .len = len };
259 if (i2c_transfer(priv->i2c_props.adap, &msg, 1) != 1) {
260 if (priv->ignore_i2c_write_errors == 0) {
261 printk(KERN_ERR "xc4000: I2C write failed (len=%i)\n",
262 len);
263 if (len == 4) {
264 printk(KERN_ERR "bytes %02x %02x %02x %02x\n", buf[0],
265 buf[1], buf[2], buf[3]);
266 }
267 return -EREMOTEIO;
268 }
269 }
270 return 0;
271}
272
273static int xc4000_tuner_reset(struct dvb_frontend *fe)
274{
275 struct xc4000_priv *priv = fe->tuner_priv;
276 int ret;
277
278 dprintk(1, "%s()\n", __func__);
279
280 if (fe->callback) {
281 ret = fe->callback(((fe->dvb) && (fe->dvb->priv)) ?
282 fe->dvb->priv :
283 priv->i2c_props.adap->algo_data,
284 DVB_FRONTEND_COMPONENT_TUNER,
285 XC4000_TUNER_RESET, 0);
286 if (ret) {
287 printk(KERN_ERR "xc4000: reset failed\n");
288 return -EREMOTEIO;
289 }
290 } else {
291 printk(KERN_ERR "xc4000: no tuner reset callback function, "
292 "fatal\n");
293 return -EINVAL;
294 }
295 return 0;
296}
297
298static int xc_write_reg(struct xc4000_priv *priv, u16 regAddr, u16 i2cData)
299{
300 u8 buf[4];
301 int result;
302
303 buf[0] = (regAddr >> 8) & 0xFF;
304 buf[1] = regAddr & 0xFF;
305 buf[2] = (i2cData >> 8) & 0xFF;
306 buf[3] = i2cData & 0xFF;
307 result = xc_send_i2c_data(priv, buf, 4);
308
309 return result;
310}
311
312static int xc_load_i2c_sequence(struct dvb_frontend *fe, const u8 *i2c_sequence)
313{
314 struct xc4000_priv *priv = fe->tuner_priv;
315
316 int i, nbytes_to_send, result;
317 unsigned int len, pos, index;
318 u8 buf[XC_MAX_I2C_WRITE_LENGTH];
319
320 index = 0;
321 while ((i2c_sequence[index] != 0xFF) ||
322 (i2c_sequence[index + 1] != 0xFF)) {
323 len = i2c_sequence[index] * 256 + i2c_sequence[index+1];
324 if (len == 0x0000) {
325 /* RESET command */
326 /* NOTE: this is ignored, as the reset callback was */
327 /* already called by check_firmware() */
328 index += 2;
329 } else if (len & 0x8000) {
330 /* WAIT command */
331 msleep(len & 0x7FFF);
332 index += 2;
333 } else {
334 /* Send i2c data whilst ensuring individual transactions
335 * do not exceed XC_MAX_I2C_WRITE_LENGTH bytes.
336 */
337 index += 2;
338 buf[0] = i2c_sequence[index];
339 buf[1] = i2c_sequence[index + 1];
340 pos = 2;
341 while (pos < len) {
342 if ((len - pos) > XC_MAX_I2C_WRITE_LENGTH - 2)
343 nbytes_to_send =
344 XC_MAX_I2C_WRITE_LENGTH;
345 else
346 nbytes_to_send = (len - pos + 2);
347 for (i = 2; i < nbytes_to_send; i++) {
348 buf[i] = i2c_sequence[index + pos +
349 i - 2];
350 }
351 result = xc_send_i2c_data(priv, buf,
352 nbytes_to_send);
353
354 if (result != 0)
355 return result;
356
357 pos += nbytes_to_send - 2;
358 }
359 index += len;
360 }
361 }
362 return 0;
363}
364
365static int xc_set_tv_standard(struct xc4000_priv *priv,
366 u16 video_mode, u16 audio_mode)
367{
368 int ret;
369 dprintk(1, "%s(0x%04x,0x%04x)\n", __func__, video_mode, audio_mode);
370 dprintk(1, "%s() Standard = %s\n",
371 __func__,
372 xc4000_standard[priv->video_standard].Name);
373
374 /* Don't complain when the request fails because of i2c stretching */
375 priv->ignore_i2c_write_errors = 1;
376
377 ret = xc_write_reg(priv, XREG_VIDEO_MODE, video_mode);
378 if (ret == 0)
379 ret = xc_write_reg(priv, XREG_AUDIO_MODE, audio_mode);
380
381 priv->ignore_i2c_write_errors = 0;
382
383 return ret;
384}
385
386static int xc_set_signal_source(struct xc4000_priv *priv, u16 rf_mode)
387{
388 dprintk(1, "%s(%d) Source = %s\n", __func__, rf_mode,
389 rf_mode == XC_RF_MODE_AIR ? "ANTENNA" : "CABLE");
390
391 if ((rf_mode != XC_RF_MODE_AIR) && (rf_mode != XC_RF_MODE_CABLE)) {
392 rf_mode = XC_RF_MODE_CABLE;
393 printk(KERN_ERR
394 "%s(), Invalid mode, defaulting to CABLE",
395 __func__);
396 }
397 return xc_write_reg(priv, XREG_SIGNALSOURCE, rf_mode);
398}
399
400static const struct dvb_tuner_ops xc4000_tuner_ops;
401
402static int xc_set_rf_frequency(struct xc4000_priv *priv, u32 freq_hz)
403{
404 u16 freq_code;
405
406 dprintk(1, "%s(%u)\n", __func__, freq_hz);
407
408 if ((freq_hz > xc4000_tuner_ops.info.frequency_max) ||
409 (freq_hz < xc4000_tuner_ops.info.frequency_min))
410 return -EINVAL;
411
412 freq_code = (u16)(freq_hz / 15625);
413
414 /* WAS: Starting in firmware version 1.1.44, Xceive recommends using the
415 FINERFREQ for all normal tuning (the doc indicates reg 0x03 should
416 only be used for fast scanning for channel lock) */
417 /* WAS: XREG_FINERFREQ */
418 return xc_write_reg(priv, XREG_RF_FREQ, freq_code);
419}
420
421static int xc_get_adc_envelope(struct xc4000_priv *priv, u16 *adc_envelope)
422{
423 return xc4000_readreg(priv, XREG_ADC_ENV, adc_envelope);
424}
425
426static int xc_get_frequency_error(struct xc4000_priv *priv, u32 *freq_error_hz)
427{
428 int result;
429 u16 regData;
430 u32 tmp;
431
432 result = xc4000_readreg(priv, XREG_FREQ_ERROR, &regData);
433 if (result != 0)
434 return result;
435
436 tmp = (u32)regData & 0xFFFFU;
437 tmp = (tmp < 0x8000U ? tmp : 0x10000U - tmp);
438 (*freq_error_hz) = tmp * 15625;
439 return result;
440}
441
442static int xc_get_lock_status(struct xc4000_priv *priv, u16 *lock_status)
443{
444 return xc4000_readreg(priv, XREG_LOCK, lock_status);
445}
446
447static int xc_get_version(struct xc4000_priv *priv,
448 u8 *hw_majorversion, u8 *hw_minorversion,
449 u8 *fw_majorversion, u8 *fw_minorversion)
450{
451 u16 data;
452 int result;
453
454 result = xc4000_readreg(priv, XREG_VERSION, &data);
455 if (result != 0)
456 return result;
457
458 (*hw_majorversion) = (data >> 12) & 0x0F;
459 (*hw_minorversion) = (data >> 8) & 0x0F;
460 (*fw_majorversion) = (data >> 4) & 0x0F;
461 (*fw_minorversion) = data & 0x0F;
462
463 return 0;
464}
465
466static int xc_get_hsync_freq(struct xc4000_priv *priv, u32 *hsync_freq_hz)
467{
468 u16 regData;
469 int result;
470
471 result = xc4000_readreg(priv, XREG_HSYNC_FREQ, &regData);
472 if (result != 0)
473 return result;
474
475 (*hsync_freq_hz) = ((regData & 0x0fff) * 763)/100;
476 return result;
477}
478
479static int xc_get_frame_lines(struct xc4000_priv *priv, u16 *frame_lines)
480{
481 return xc4000_readreg(priv, XREG_FRAME_LINES, frame_lines);
482}
483
484static int xc_get_quality(struct xc4000_priv *priv, u16 *quality)
485{
486 return xc4000_readreg(priv, XREG_QUALITY, quality);
487}
488
489static u16 xc_wait_for_lock(struct xc4000_priv *priv)
490{
491 u16 lock_state = 0;
492 int watchdog_count = 40;
493
494 while ((lock_state == 0) && (watchdog_count > 0)) {
495 xc_get_lock_status(priv, &lock_state);
496 if (lock_state != 1) {
497 msleep(5);
498 watchdog_count--;
499 }
500 }
501 return lock_state;
502}
503
504static int xc_tune_channel(struct xc4000_priv *priv, u32 freq_hz)
505{
506 int found = 1;
507 int result;
508
509 dprintk(1, "%s(%u)\n", __func__, freq_hz);
510
511 /* Don't complain when the request fails because of i2c stretching */
512 priv->ignore_i2c_write_errors = 1;
513 result = xc_set_rf_frequency(priv, freq_hz);
514 priv->ignore_i2c_write_errors = 0;
515
516 if (result != 0)
517 return 0;
518
519 /* wait for lock only in analog TV mode */
520 if ((priv->cur_fw.type & (FM | DTV6 | DTV7 | DTV78 | DTV8)) == 0) {
521 if (xc_wait_for_lock(priv) != 1)
522 found = 0;
523 }
524
525 /* Wait for stats to stabilize.
526 * Frame Lines needs two frame times after initial lock
527 * before it is valid.
528 */
529 msleep(debug ? 100 : 10);
530
531 if (debug)
532 xc_debug_dump(priv);
533
534 return found;
535}
536
537static int xc4000_readreg(struct xc4000_priv *priv, u16 reg, u16 *val)
538{
539 u8 buf[2] = { reg >> 8, reg & 0xff };
540 u8 bval[2] = { 0, 0 };
541 struct i2c_msg msg[2] = {
542 { .addr = priv->i2c_props.addr,
543 .flags = 0, .buf = &buf[0], .len = 2 },
544 { .addr = priv->i2c_props.addr,
545 .flags = I2C_M_RD, .buf = &bval[0], .len = 2 },
546 };
547
548 if (i2c_transfer(priv->i2c_props.adap, msg, 2) != 2) {
549 printk(KERN_ERR "xc4000: I2C read failed\n");
550 return -EREMOTEIO;
551 }
552
553 *val = (bval[0] << 8) | bval[1];
554 return 0;
555}
556
557#define dump_firm_type(t) dump_firm_type_and_int_freq(t, 0)
558static void dump_firm_type_and_int_freq(unsigned int type, u16 int_freq)
559{
560 if (type & BASE)
561 printk(KERN_CONT "BASE ");
562 if (type & INIT1)
563 printk(KERN_CONT "INIT1 ");
564 if (type & F8MHZ)
565 printk(KERN_CONT "F8MHZ ");
566 if (type & MTS)
567 printk(KERN_CONT "MTS ");
568 if (type & D2620)
569 printk(KERN_CONT "D2620 ");
570 if (type & D2633)
571 printk(KERN_CONT "D2633 ");
572 if (type & DTV6)
573 printk(KERN_CONT "DTV6 ");
574 if (type & QAM)
575 printk(KERN_CONT "QAM ");
576 if (type & DTV7)
577 printk(KERN_CONT "DTV7 ");
578 if (type & DTV78)
579 printk(KERN_CONT "DTV78 ");
580 if (type & DTV8)
581 printk(KERN_CONT "DTV8 ");
582 if (type & FM)
583 printk(KERN_CONT "FM ");
584 if (type & INPUT1)
585 printk(KERN_CONT "INPUT1 ");
586 if (type & LCD)
587 printk(KERN_CONT "LCD ");
588 if (type & NOGD)
589 printk(KERN_CONT "NOGD ");
590 if (type & MONO)
591 printk(KERN_CONT "MONO ");
592 if (type & ATSC)
593 printk(KERN_CONT "ATSC ");
594 if (type & IF)
595 printk(KERN_CONT "IF ");
596 if (type & LG60)
597 printk(KERN_CONT "LG60 ");
598 if (type & ATI638)
599 printk(KERN_CONT "ATI638 ");
600 if (type & OREN538)
601 printk(KERN_CONT "OREN538 ");
602 if (type & OREN36)
603 printk(KERN_CONT "OREN36 ");
604 if (type & TOYOTA388)
605 printk(KERN_CONT "TOYOTA388 ");
606 if (type & TOYOTA794)
607 printk(KERN_CONT "TOYOTA794 ");
608 if (type & DIBCOM52)
609 printk(KERN_CONT "DIBCOM52 ");
610 if (type & ZARLINK456)
611 printk(KERN_CONT "ZARLINK456 ");
612 if (type & CHINA)
613 printk(KERN_CONT "CHINA ");
614 if (type & F6MHZ)
615 printk(KERN_CONT "F6MHZ ");
616 if (type & INPUT2)
617 printk(KERN_CONT "INPUT2 ");
618 if (type & SCODE)
619 printk(KERN_CONT "SCODE ");
620 if (type & HAS_IF)
621 printk(KERN_CONT "HAS_IF_%d ", int_freq);
622}
623
624static int seek_firmware(struct dvb_frontend *fe, unsigned int type,
625 v4l2_std_id *id)
626{
627 struct xc4000_priv *priv = fe->tuner_priv;
628 int i, best_i = -1;
629 unsigned int best_nr_diffs = 255U;
630
631 if (!priv->firm) {
632 printk(KERN_ERR "Error! firmware not loaded\n");
633 return -EINVAL;
634 }
635
636 if (((type & ~SCODE) == 0) && (*id == 0))
637 *id = V4L2_STD_PAL;
638
639 /* Seek for generic video standard match */
640 for (i = 0; i < priv->firm_size; i++) {
641 v4l2_std_id id_diff_mask =
642 (priv->firm[i].id ^ (*id)) & (*id);
643 unsigned int type_diff_mask =
644 (priv->firm[i].type ^ type)
645 & (BASE_TYPES | DTV_TYPES | LCD | NOGD | MONO | SCODE);
646 unsigned int nr_diffs;
647
648 if (type_diff_mask
649 & (BASE | INIT1 | FM | DTV6 | DTV7 | DTV78 | DTV8 | SCODE))
650 continue;
651
652 nr_diffs = hweight64(id_diff_mask) + hweight32(type_diff_mask);
653 if (!nr_diffs) /* Supports all the requested standards */
654 goto found;
655
656 if (nr_diffs < best_nr_diffs) {
657 best_nr_diffs = nr_diffs;
658 best_i = i;
659 }
660 }
661
662 /* FIXME: Would make sense to seek for type "hint" match ? */
663 if (best_i < 0) {
664 i = -ENOENT;
665 goto ret;
666 }
667
668 if (best_nr_diffs > 0U) {
669 printk(KERN_WARNING
670 "Selecting best matching firmware (%u bits differ) for "
671 "type=(%x), id %016llx:\n",
672 best_nr_diffs, type, (unsigned long long)*id);
673 i = best_i;
674 }
675
676found:
677 *id = priv->firm[i].id;
678
679ret:
680 if (debug) {
681 printk(KERN_DEBUG "%s firmware for type=",
682 (i < 0) ? "Can't find" : "Found");
683 dump_firm_type(type);
684 printk(KERN_DEBUG "(%x), id %016llx.\n", type, (unsigned long long)*id);
685 }
686 return i;
687}
688
689static int load_firmware(struct dvb_frontend *fe, unsigned int type,
690 v4l2_std_id *id)
691{
692 struct xc4000_priv *priv = fe->tuner_priv;
693 int pos, rc;
694 unsigned char *p;
695
696 pos = seek_firmware(fe, type, id);
697 if (pos < 0)
698 return pos;
699
700 p = priv->firm[pos].ptr;
701
702 /* Don't complain when the request fails because of i2c stretching */
703 priv->ignore_i2c_write_errors = 1;
704
705 rc = xc_load_i2c_sequence(fe, p);
706
707 priv->ignore_i2c_write_errors = 0;
708
709 return rc;
710}
711
712static int xc4000_fwupload(struct dvb_frontend *fe)
713{
714 struct xc4000_priv *priv = fe->tuner_priv;
715 const struct firmware *fw = NULL;
716 const unsigned char *p, *endp;
717 int rc = 0;
718 int n, n_array;
719 char name[33];
720 const char *fname;
721
722 if (firmware_name[0] != '\0')
723 fname = firmware_name;
724 else
725 fname = XC4000_DEFAULT_FIRMWARE;
726
727 dprintk(1, "Reading firmware %s\n", fname);
728 rc = request_firmware(&fw, fname, priv->i2c_props.adap->dev.parent);
729 if (rc < 0) {
730 if (rc == -ENOENT)
731 printk(KERN_ERR "Error: firmware %s not found.\n", fname);
732 else
733 printk(KERN_ERR "Error %d while requesting firmware %s\n",
734 rc, fname);
735
736 return rc;
737 }
738 p = fw->data;
739 endp = p + fw->size;
740
741 if (fw->size < sizeof(name) - 1 + 2 + 2) {
742 printk(KERN_ERR "Error: firmware file %s has invalid size!\n",
743 fname);
744 goto corrupt;
745 }
746
747 memcpy(name, p, sizeof(name) - 1);
748 name[sizeof(name) - 1] = '\0';
749 p += sizeof(name) - 1;
750
751 priv->firm_version = get_unaligned_le16(p);
752 p += 2;
753
754 n_array = get_unaligned_le16(p);
755 p += 2;
756
757 dprintk(1, "Loading %d firmware images from %s, type: %s, ver %d.%d\n",
758 n_array, fname, name,
759 priv->firm_version >> 8, priv->firm_version & 0xff);
760
761 priv->firm = kzalloc(sizeof(*priv->firm) * n_array, GFP_KERNEL);
762 if (priv->firm == NULL) {
763 printk(KERN_ERR "Not enough memory to load firmware file.\n");
764 rc = -ENOMEM;
765 goto done;
766 }
767 priv->firm_size = n_array;
768
769 n = -1;
770 while (p < endp) {
771 __u32 type, size;
772 v4l2_std_id id;
773 __u16 int_freq = 0;
774
775 n++;
776 if (n >= n_array) {
777 printk(KERN_ERR "More firmware images in file than "
778 "were expected!\n");
779 goto corrupt;
780 }
781
782 /* Checks if there's enough bytes to read */
783 if (endp - p < sizeof(type) + sizeof(id) + sizeof(size))
784 goto header;
785
786 type = get_unaligned_le32(p);
787 p += sizeof(type);
788
789 id = get_unaligned_le64(p);
790 p += sizeof(id);
791
792 if (type & HAS_IF) {
793 int_freq = get_unaligned_le16(p);
794 p += sizeof(int_freq);
795 if (endp - p < sizeof(size))
796 goto header;
797 }
798
799 size = get_unaligned_le32(p);
800 p += sizeof(size);
801
802 if (!size || size > endp - p) {
803 printk(KERN_ERR "Firmware type (%x), id %llx is corrupted (size=%d, expected %d)\n",
804 type, (unsigned long long)id,
805 (unsigned)(endp - p), size);
806 goto corrupt;
807 }
808
809 priv->firm[n].ptr = kzalloc(size, GFP_KERNEL);
810 if (priv->firm[n].ptr == NULL) {
811 printk(KERN_ERR "Not enough memory to load firmware file.\n");
812 rc = -ENOMEM;
813 goto done;
814 }
815
816 if (debug) {
817 printk(KERN_DEBUG "Reading firmware type ");
818 dump_firm_type_and_int_freq(type, int_freq);
819 printk(KERN_DEBUG "(%x), id %llx, size=%d.\n",
820 type, (unsigned long long)id, size);
821 }
822
823 memcpy(priv->firm[n].ptr, p, size);
824 priv->firm[n].type = type;
825 priv->firm[n].id = id;
826 priv->firm[n].size = size;
827 priv->firm[n].int_freq = int_freq;
828
829 p += size;
830 }
831
832 if (n + 1 != priv->firm_size) {
833 printk(KERN_ERR "Firmware file is incomplete!\n");
834 goto corrupt;
835 }
836
837 goto done;
838
839header:
840 printk(KERN_ERR "Firmware header is incomplete!\n");
841corrupt:
842 rc = -EINVAL;
843 printk(KERN_ERR "Error: firmware file is corrupted!\n");
844
845done:
846 release_firmware(fw);
847 if (rc == 0)
848 dprintk(1, "Firmware files loaded.\n");
849
850 return rc;
851}
852
853static int load_scode(struct dvb_frontend *fe, unsigned int type,
854 v4l2_std_id *id, __u16 int_freq, int scode)
855{
856 struct xc4000_priv *priv = fe->tuner_priv;
857 int pos, rc;
858 unsigned char *p;
859 u8 scode_buf[13];
860 u8 indirect_mode[5];
861
862 dprintk(1, "%s called int_freq=%d\n", __func__, int_freq);
863
864 if (!int_freq) {
865 pos = seek_firmware(fe, type, id);
866 if (pos < 0)
867 return pos;
868 } else {
869 for (pos = 0; pos < priv->firm_size; pos++) {
870 if ((priv->firm[pos].int_freq == int_freq) &&
871 (priv->firm[pos].type & HAS_IF))
872 break;
873 }
874 if (pos == priv->firm_size)
875 return -ENOENT;
876 }
877
878 p = priv->firm[pos].ptr;
879
880 if (priv->firm[pos].size != 12 * 16 || scode >= 16)
881 return -EINVAL;
882 p += 12 * scode;
883
884 if (debug) {
885 tuner_info("Loading SCODE for type=");
886 dump_firm_type_and_int_freq(priv->firm[pos].type,
887 priv->firm[pos].int_freq);
888 printk(KERN_CONT "(%x), id %016llx.\n", priv->firm[pos].type,
889 (unsigned long long)*id);
890 }
891
892 scode_buf[0] = 0x00;
893 memcpy(&scode_buf[1], p, 12);
894
895 /* Enter direct-mode */
896 rc = xc_write_reg(priv, XREG_DIRECTSITTING_MODE, 0);
897 if (rc < 0) {
898 printk(KERN_ERR "failed to put device into direct mode!\n");
899 return -EIO;
900 }
901
902 rc = xc_send_i2c_data(priv, scode_buf, 13);
903 if (rc != 0) {
904 /* Even if the send failed, make sure we set back to indirect
905 mode */
906 printk(KERN_ERR "Failed to set scode %d\n", rc);
907 }
908
909 /* Switch back to indirect-mode */
910 memset(indirect_mode, 0, sizeof(indirect_mode));
911 indirect_mode[4] = 0x88;
912 xc_send_i2c_data(priv, indirect_mode, sizeof(indirect_mode));
913 msleep(10);
914
915 return 0;
916}
917
918static int check_firmware(struct dvb_frontend *fe, unsigned int type,
919 v4l2_std_id std, __u16 int_freq)
920{
921 struct xc4000_priv *priv = fe->tuner_priv;
922 struct firmware_properties new_fw;
923 int rc = 0, is_retry = 0;
924 u16 hwmodel;
925 v4l2_std_id std0;
926 u8 hw_major, hw_minor, fw_major, fw_minor;
927
928 dprintk(1, "%s called\n", __func__);
929
930 if (!priv->firm) {
931 rc = xc4000_fwupload(fe);
932 if (rc < 0)
933 return rc;
934 }
935
936retry:
937 new_fw.type = type;
938 new_fw.id = std;
939 new_fw.std_req = std;
940 new_fw.scode_table = SCODE;
941 new_fw.scode_nr = 0;
942 new_fw.int_freq = int_freq;
943
944 dprintk(1, "checking firmware, user requested type=");
945 if (debug) {
946 dump_firm_type(new_fw.type);
947 printk(KERN_CONT "(%x), id %016llx, ", new_fw.type,
948 (unsigned long long)new_fw.std_req);
949 if (!int_freq)
950 printk(KERN_CONT "scode_tbl ");
951 else
952 printk(KERN_CONT "int_freq %d, ", new_fw.int_freq);
953 printk(KERN_CONT "scode_nr %d\n", new_fw.scode_nr);
954 }
955
956 /* No need to reload base firmware if it matches */
957 if (priv->cur_fw.type & BASE) {
958 dprintk(1, "BASE firmware not changed.\n");
959 goto skip_base;
960 }
961
962 /* Updating BASE - forget about all currently loaded firmware */
963 memset(&priv->cur_fw, 0, sizeof(priv->cur_fw));
964
965 /* Reset is needed before loading firmware */
966 rc = xc4000_tuner_reset(fe);
967 if (rc < 0)
968 goto fail;
969
970 /* BASE firmwares are all std0 */
971 std0 = 0;
972 rc = load_firmware(fe, BASE, &std0);
973 if (rc < 0) {
974 printk(KERN_ERR "Error %d while loading base firmware\n", rc);
975 goto fail;
976 }
977
978 /* Load INIT1, if needed */
979 dprintk(1, "Load init1 firmware, if exists\n");
980
981 rc = load_firmware(fe, BASE | INIT1, &std0);
982 if (rc == -ENOENT)
983 rc = load_firmware(fe, BASE | INIT1, &std0);
984 if (rc < 0 && rc != -ENOENT) {
985 tuner_err("Error %d while loading init1 firmware\n",
986 rc);
987 goto fail;
988 }
989
990skip_base:
991 /*
992 * No need to reload standard specific firmware if base firmware
993 * was not reloaded and requested video standards have not changed.
994 */
995 if (priv->cur_fw.type == (BASE | new_fw.type) &&
996 priv->cur_fw.std_req == std) {
997 dprintk(1, "Std-specific firmware already loaded.\n");
998 goto skip_std_specific;
999 }
1000
1001 /* Reloading std-specific firmware forces a SCODE update */
1002 priv->cur_fw.scode_table = 0;
1003
1004 /* Load the standard firmware */
1005 rc = load_firmware(fe, new_fw.type, &new_fw.id);
1006
1007 if (rc < 0)
1008 goto fail;
1009
1010skip_std_specific:
1011 if (priv->cur_fw.scode_table == new_fw.scode_table &&
1012 priv->cur_fw.scode_nr == new_fw.scode_nr) {
1013 dprintk(1, "SCODE firmware already loaded.\n");
1014 goto check_device;
1015 }
1016
1017 /* Load SCODE firmware, if exists */
1018 rc = load_scode(fe, new_fw.type | new_fw.scode_table, &new_fw.id,
1019 new_fw.int_freq, new_fw.scode_nr);
1020 if (rc != 0)
1021 dprintk(1, "load scode failed %d\n", rc);
1022
1023check_device:
1024 rc = xc4000_readreg(priv, XREG_PRODUCT_ID, &hwmodel);
1025
1026 if (xc_get_version(priv, &hw_major, &hw_minor, &fw_major,
1027 &fw_minor) != 0) {
1028 printk(KERN_ERR "Unable to read tuner registers.\n");
1029 goto fail;
1030 }
1031
1032 dprintk(1, "Device is Xceive %d version %d.%d, "
1033 "firmware version %d.%d\n",
1034 hwmodel, hw_major, hw_minor, fw_major, fw_minor);
1035
1036 /* Check firmware version against what we downloaded. */
1037 if (priv->firm_version != ((fw_major << 8) | fw_minor)) {
1038 printk(KERN_WARNING
1039 "Incorrect readback of firmware version %d.%d.\n",
1040 fw_major, fw_minor);
1041 goto fail;
1042 }
1043
1044 /* Check that the tuner hardware model remains consistent over time. */
1045 if (priv->hwmodel == 0 &&
1046 (hwmodel == XC_PRODUCT_ID_XC4000 ||
1047 hwmodel == XC_PRODUCT_ID_XC4100)) {
1048 priv->hwmodel = hwmodel;
1049 priv->hwvers = (hw_major << 8) | hw_minor;
1050 } else if (priv->hwmodel == 0 || priv->hwmodel != hwmodel ||
1051 priv->hwvers != ((hw_major << 8) | hw_minor)) {
1052 printk(KERN_WARNING
1053 "Read invalid device hardware information - tuner "
1054 "hung?\n");
1055 goto fail;
1056 }
1057
1058 memcpy(&priv->cur_fw, &new_fw, sizeof(priv->cur_fw));
1059
1060 /*
1061 * By setting BASE in cur_fw.type only after successfully loading all
1062 * firmwares, we can:
1063 * 1. Identify that BASE firmware with type=0 has been loaded;
1064 * 2. Tell whether BASE firmware was just changed the next time through.
1065 */
1066 priv->cur_fw.type |= BASE;
1067
1068 return 0;
1069
1070fail:
1071 memset(&priv->cur_fw, 0, sizeof(priv->cur_fw));
1072 if (!is_retry) {
1073 msleep(50);
1074 is_retry = 1;
1075 dprintk(1, "Retrying firmware load\n");
1076 goto retry;
1077 }
1078
1079 if (rc == -ENOENT)
1080 rc = -EINVAL;
1081 return rc;
1082}
1083
1084static void xc_debug_dump(struct xc4000_priv *priv)
1085{
1086 u16 adc_envelope;
1087 u32 freq_error_hz = 0;
1088 u16 lock_status;
1089 u32 hsync_freq_hz = 0;
1090 u16 frame_lines;
1091 u16 quality;
1092 u8 hw_majorversion = 0, hw_minorversion = 0;
1093 u8 fw_majorversion = 0, fw_minorversion = 0;
1094
1095 xc_get_adc_envelope(priv, &adc_envelope);
1096 dprintk(1, "*** ADC envelope (0-1023) = %d\n", adc_envelope);
1097
1098 xc_get_frequency_error(priv, &freq_error_hz);
1099 dprintk(1, "*** Frequency error = %d Hz\n", freq_error_hz);
1100
1101 xc_get_lock_status(priv, &lock_status);
1102 dprintk(1, "*** Lock status (0-Wait, 1-Locked, 2-No-signal) = %d\n",
1103 lock_status);
1104
1105 xc_get_version(priv, &hw_majorversion, &hw_minorversion,
1106 &fw_majorversion, &fw_minorversion);
1107 dprintk(1, "*** HW: V%02x.%02x, FW: V%02x.%02x\n",
1108 hw_majorversion, hw_minorversion,
1109 fw_majorversion, fw_minorversion);
1110
1111 if (priv->video_standard < XC4000_DTV6) {
1112 xc_get_hsync_freq(priv, &hsync_freq_hz);
1113 dprintk(1, "*** Horizontal sync frequency = %d Hz\n",
1114 hsync_freq_hz);
1115
1116 xc_get_frame_lines(priv, &frame_lines);
1117 dprintk(1, "*** Frame lines = %d\n", frame_lines);
1118 }
1119
1120 xc_get_quality(priv, &quality);
1121 dprintk(1, "*** Quality (0:<8dB, 7:>56dB) = %d\n", quality);
1122}
1123
1124static int xc4000_set_params(struct dvb_frontend *fe,
1125 struct dvb_frontend_parameters *params)
1126{
1127 struct xc4000_priv *priv = fe->tuner_priv;
1128 unsigned int type;
1129 int ret = -EREMOTEIO;
1130
1131 dprintk(1, "%s() frequency=%d (Hz)\n", __func__, params->frequency);
1132
1133 mutex_lock(&priv->lock);
1134
1135 if (fe->ops.info.type == FE_ATSC) {
1136 dprintk(1, "%s() ATSC\n", __func__);
1137 switch (params->u.vsb.modulation) {
1138 case VSB_8:
1139 case VSB_16:
1140 dprintk(1, "%s() VSB modulation\n", __func__);
1141 priv->rf_mode = XC_RF_MODE_AIR;
1142 priv->freq_hz = params->frequency - 1750000;
1143 priv->bandwidth = BANDWIDTH_6_MHZ;
1144 priv->video_standard = XC4000_DTV6;
1145 type = DTV6;
1146 break;
1147 case QAM_64:
1148 case QAM_256:
1149 case QAM_AUTO:
1150 dprintk(1, "%s() QAM modulation\n", __func__);
1151 priv->rf_mode = XC_RF_MODE_CABLE;
1152 priv->freq_hz = params->frequency - 1750000;
1153 priv->bandwidth = BANDWIDTH_6_MHZ;
1154 priv->video_standard = XC4000_DTV6;
1155 type = DTV6;
1156 break;
1157 default:
1158 ret = -EINVAL;
1159 goto fail;
1160 }
1161 } else if (fe->ops.info.type == FE_OFDM) {
1162 dprintk(1, "%s() OFDM\n", __func__);
1163 switch (params->u.ofdm.bandwidth) {
1164 case BANDWIDTH_6_MHZ:
1165 priv->bandwidth = BANDWIDTH_6_MHZ;
1166 priv->video_standard = XC4000_DTV6;
1167 priv->freq_hz = params->frequency - 1750000;
1168 type = DTV6;
1169 break;
1170 case BANDWIDTH_7_MHZ:
1171 priv->bandwidth = BANDWIDTH_7_MHZ;
1172 priv->video_standard = XC4000_DTV7;
1173 priv->freq_hz = params->frequency - 2250000;
1174 type = DTV7;
1175 break;
1176 case BANDWIDTH_8_MHZ:
1177 priv->bandwidth = BANDWIDTH_8_MHZ;
1178 priv->video_standard = XC4000_DTV8;
1179 priv->freq_hz = params->frequency - 2750000;
1180 type = DTV8;
1181 break;
1182 case BANDWIDTH_AUTO:
1183 if (params->frequency < 400000000) {
1184 priv->bandwidth = BANDWIDTH_7_MHZ;
1185 priv->freq_hz = params->frequency - 2250000;
1186 } else {
1187 priv->bandwidth = BANDWIDTH_8_MHZ;
1188 priv->freq_hz = params->frequency - 2750000;
1189 }
1190 priv->video_standard = XC4000_DTV7_8;
1191 type = DTV78;
1192 break;
1193 default:
1194 printk(KERN_ERR "xc4000 bandwidth not set!\n");
1195 ret = -EINVAL;
1196 goto fail;
1197 }
1198 priv->rf_mode = XC_RF_MODE_AIR;
1199 } else {
1200 printk(KERN_ERR "xc4000 modulation type not supported!\n");
1201 ret = -EINVAL;
1202 goto fail;
1203 }
1204
1205 dprintk(1, "%s() frequency=%d (compensated)\n",
1206 __func__, priv->freq_hz);
1207
1208 /* Make sure the correct firmware type is loaded */
1209 if (check_firmware(fe, type, 0, priv->if_khz) != 0)
1210 goto fail;
1211
1212 ret = xc_set_signal_source(priv, priv->rf_mode);
1213 if (ret != 0) {
1214 printk(KERN_ERR "xc4000: xc_set_signal_source(%d) failed\n",
1215 priv->rf_mode);
1216 goto fail;
1217 } else {
1218 u16 video_mode, audio_mode;
1219 video_mode = xc4000_standard[priv->video_standard].video_mode;
1220 audio_mode = xc4000_standard[priv->video_standard].audio_mode;
1221 if (type == DTV6 && priv->firm_version != 0x0102)
1222 video_mode |= 0x0001;
1223 ret = xc_set_tv_standard(priv, video_mode, audio_mode);
1224 if (ret != 0) {
1225 printk(KERN_ERR "xc4000: xc_set_tv_standard failed\n");
1226 /* DJH - do not return when it fails... */
1227 /* goto fail; */
1228 }
1229 }
1230
1231 if (xc_write_reg(priv, XREG_D_CODE, 0) == 0)
1232 ret = 0;
1233 if (priv->dvb_amplitude != 0) {
1234 if (xc_write_reg(priv, XREG_AMPLITUDE,
1235 (priv->firm_version != 0x0102 ||
1236 priv->dvb_amplitude != 134 ?
1237 priv->dvb_amplitude : 132)) != 0)
1238 ret = -EREMOTEIO;
1239 }
1240 if (priv->set_smoothedcvbs != 0) {
1241 if (xc_write_reg(priv, XREG_SMOOTHEDCVBS, 1) != 0)
1242 ret = -EREMOTEIO;
1243 }
1244 if (ret != 0) {
1245 printk(KERN_ERR "xc4000: setting registers failed\n");
1246 /* goto fail; */
1247 }
1248
1249 xc_tune_channel(priv, priv->freq_hz);
1250
1251 ret = 0;
1252
1253fail:
1254 mutex_unlock(&priv->lock);
1255
1256 return ret;
1257}
1258
1259static int xc4000_set_analog_params(struct dvb_frontend *fe,
1260 struct analog_parameters *params)
1261{
1262 struct xc4000_priv *priv = fe->tuner_priv;
1263 unsigned int type = 0;
1264 int ret = -EREMOTEIO;
1265
1266 if (params->mode == V4L2_TUNER_RADIO) {
1267 dprintk(1, "%s() frequency=%d (in units of 62.5Hz)\n",
1268 __func__, params->frequency);
1269
1270 mutex_lock(&priv->lock);
1271
1272 params->std = 0;
1273 priv->freq_hz = params->frequency * 125L / 2;
1274
1275 if (audio_std & XC4000_AUDIO_STD_INPUT1) {
1276 priv->video_standard = XC4000_FM_Radio_INPUT1;
1277 type = FM | INPUT1;
1278 } else {
1279 priv->video_standard = XC4000_FM_Radio_INPUT2;
1280 type = FM | INPUT2;
1281 }
1282
1283 goto tune_channel;
1284 }
1285
1286 dprintk(1, "%s() frequency=%d (in units of 62.5khz)\n",
1287 __func__, params->frequency);
1288
1289 mutex_lock(&priv->lock);
1290
1291 /* params->frequency is in units of 62.5khz */
1292 priv->freq_hz = params->frequency * 62500;
1293
1294 params->std &= V4L2_STD_ALL;
1295 /* if std is not defined, choose one */
1296 if (!params->std)
1297 params->std = V4L2_STD_PAL_BG;
1298
1299 if (audio_std & XC4000_AUDIO_STD_MONO)
1300 type = MONO;
1301
1302 if (params->std & V4L2_STD_MN) {
1303 params->std = V4L2_STD_MN;
1304 if (audio_std & XC4000_AUDIO_STD_MONO) {
1305 priv->video_standard = XC4000_MN_NTSC_PAL_Mono;
1306 } else if (audio_std & XC4000_AUDIO_STD_A2) {
1307 params->std |= V4L2_STD_A2;
1308 priv->video_standard = XC4000_MN_NTSC_PAL_A2;
1309 } else {
1310 params->std |= V4L2_STD_BTSC;
1311 priv->video_standard = XC4000_MN_NTSC_PAL_BTSC;
1312 }
1313 goto tune_channel;
1314 }
1315
1316 if (params->std & V4L2_STD_PAL_BG) {
1317 params->std = V4L2_STD_PAL_BG;
1318 if (audio_std & XC4000_AUDIO_STD_MONO) {
1319 priv->video_standard = XC4000_BG_PAL_MONO;
1320 } else if (!(audio_std & XC4000_AUDIO_STD_A2)) {
1321 if (!(audio_std & XC4000_AUDIO_STD_B)) {
1322 params->std |= V4L2_STD_NICAM_A;
1323 priv->video_standard = XC4000_BG_PAL_NICAM;
1324 } else {
1325 params->std |= V4L2_STD_NICAM_B;
1326 priv->video_standard = XC4000_BG_PAL_NICAM;
1327 }
1328 } else {
1329 if (!(audio_std & XC4000_AUDIO_STD_B)) {
1330 params->std |= V4L2_STD_A2_A;
1331 priv->video_standard = XC4000_BG_PAL_A2;
1332 } else {
1333 params->std |= V4L2_STD_A2_B;
1334 priv->video_standard = XC4000_BG_PAL_A2;
1335 }
1336 }
1337 goto tune_channel;
1338 }
1339
1340 if (params->std & V4L2_STD_PAL_I) {
1341 /* default to NICAM audio standard */
1342 params->std = V4L2_STD_PAL_I | V4L2_STD_NICAM;
1343 if (audio_std & XC4000_AUDIO_STD_MONO)
1344 priv->video_standard = XC4000_I_PAL_NICAM_MONO;
1345 else
1346 priv->video_standard = XC4000_I_PAL_NICAM;
1347 goto tune_channel;
1348 }
1349
1350 if (params->std & V4L2_STD_PAL_DK) {
1351 params->std = V4L2_STD_PAL_DK;
1352 if (audio_std & XC4000_AUDIO_STD_MONO) {
1353 priv->video_standard = XC4000_DK_PAL_MONO;
1354 } else if (audio_std & XC4000_AUDIO_STD_A2) {
1355 params->std |= V4L2_STD_A2;
1356 priv->video_standard = XC4000_DK_PAL_A2;
1357 } else {
1358 params->std |= V4L2_STD_NICAM;
1359 priv->video_standard = XC4000_DK_PAL_NICAM;
1360 }
1361 goto tune_channel;
1362 }
1363
1364 if (params->std & V4L2_STD_SECAM_DK) {
1365 /* default to A2 audio standard */
1366 params->std = V4L2_STD_SECAM_DK | V4L2_STD_A2;
1367 if (audio_std & XC4000_AUDIO_STD_L) {
1368 type = 0;
1369 priv->video_standard = XC4000_DK_SECAM_NICAM;
1370 } else if (audio_std & XC4000_AUDIO_STD_MONO) {
1371 priv->video_standard = XC4000_DK_SECAM_A2MONO;
1372 } else if (audio_std & XC4000_AUDIO_STD_K3) {
1373 params->std |= V4L2_STD_SECAM_K3;
1374 priv->video_standard = XC4000_DK_SECAM_A2LDK3;
1375 } else {
1376 priv->video_standard = XC4000_DK_SECAM_A2DK1;
1377 }
1378 goto tune_channel;
1379 }
1380
1381 if (params->std & V4L2_STD_SECAM_L) {
1382 /* default to NICAM audio standard */
1383 type = 0;
1384 params->std = V4L2_STD_SECAM_L | V4L2_STD_NICAM;
1385 priv->video_standard = XC4000_L_SECAM_NICAM;
1386 goto tune_channel;
1387 }
1388
1389 if (params->std & V4L2_STD_SECAM_LC) {
1390 /* default to NICAM audio standard */
1391 type = 0;
1392 params->std = V4L2_STD_SECAM_LC | V4L2_STD_NICAM;
1393 priv->video_standard = XC4000_LC_SECAM_NICAM;
1394 goto tune_channel;
1395 }
1396
1397tune_channel:
1398 /* FIXME: it could be air. */
1399 priv->rf_mode = XC_RF_MODE_CABLE;
1400
1401 if (check_firmware(fe, type, params->std,
1402 xc4000_standard[priv->video_standard].int_freq) != 0)
1403 goto fail;
1404
1405 ret = xc_set_signal_source(priv, priv->rf_mode);
1406 if (ret != 0) {
1407 printk(KERN_ERR
1408 "xc4000: xc_set_signal_source(%d) failed\n",
1409 priv->rf_mode);
1410 goto fail;
1411 } else {
1412 u16 video_mode, audio_mode;
1413 video_mode = xc4000_standard[priv->video_standard].video_mode;
1414 audio_mode = xc4000_standard[priv->video_standard].audio_mode;
1415 if (priv->video_standard < XC4000_BG_PAL_A2) {
1416 if (type & NOGD)
1417 video_mode &= 0xFF7F;
1418 } else if (priv->video_standard < XC4000_I_PAL_NICAM) {
1419 if (priv->firm_version == 0x0102)
1420 video_mode &= 0xFEFF;
1421 if (audio_std & XC4000_AUDIO_STD_B)
1422 video_mode |= 0x0080;
1423 }
1424 ret = xc_set_tv_standard(priv, video_mode, audio_mode);
1425 if (ret != 0) {
1426 printk(KERN_ERR "xc4000: xc_set_tv_standard failed\n");
1427 goto fail;
1428 }
1429 }
1430
1431 if (xc_write_reg(priv, XREG_D_CODE, 0) == 0)
1432 ret = 0;
1433 if (xc_write_reg(priv, XREG_AMPLITUDE, 1) != 0)
1434 ret = -EREMOTEIO;
1435 if (priv->set_smoothedcvbs != 0) {
1436 if (xc_write_reg(priv, XREG_SMOOTHEDCVBS, 1) != 0)
1437 ret = -EREMOTEIO;
1438 }
1439 if (ret != 0) {
1440 printk(KERN_ERR "xc4000: setting registers failed\n");
1441 goto fail;
1442 }
1443
1444 xc_tune_channel(priv, priv->freq_hz);
1445
1446 ret = 0;
1447
1448fail:
1449 mutex_unlock(&priv->lock);
1450
1451 return ret;
1452}
1453
1454static int xc4000_get_frequency(struct dvb_frontend *fe, u32 *freq)
1455{
1456 struct xc4000_priv *priv = fe->tuner_priv;
1457
1458 *freq = priv->freq_hz;
1459
1460 if (debug) {
1461 mutex_lock(&priv->lock);
1462 if ((priv->cur_fw.type
1463 & (BASE | FM | DTV6 | DTV7 | DTV78 | DTV8)) == BASE) {
1464 u16 snr = 0;
1465 if (xc4000_readreg(priv, XREG_SNR, &snr) == 0) {
1466 mutex_unlock(&priv->lock);
1467 dprintk(1, "%s() freq = %u, SNR = %d\n",
1468 __func__, *freq, snr);
1469 return 0;
1470 }
1471 }
1472 mutex_unlock(&priv->lock);
1473 }
1474
1475 dprintk(1, "%s()\n", __func__);
1476
1477 return 0;
1478}
1479
1480static int xc4000_get_bandwidth(struct dvb_frontend *fe, u32 *bw)
1481{
1482 struct xc4000_priv *priv = fe->tuner_priv;
1483 dprintk(1, "%s()\n", __func__);
1484
1485 *bw = priv->bandwidth;
1486 return 0;
1487}
1488
1489static int xc4000_get_status(struct dvb_frontend *fe, u32 *status)
1490{
1491 struct xc4000_priv *priv = fe->tuner_priv;
1492 u16 lock_status = 0;
1493
1494 mutex_lock(&priv->lock);
1495
1496 if (priv->cur_fw.type & BASE)
1497 xc_get_lock_status(priv, &lock_status);
1498
1499 *status = (lock_status == 1 ?
1500 TUNER_STATUS_LOCKED | TUNER_STATUS_STEREO : 0);
1501 if (priv->cur_fw.type & (DTV6 | DTV7 | DTV78 | DTV8))
1502 *status &= (~TUNER_STATUS_STEREO);
1503
1504 mutex_unlock(&priv->lock);
1505
1506 dprintk(2, "%s() lock_status = %d\n", __func__, lock_status);
1507
1508 return 0;
1509}
1510
1511static int xc4000_sleep(struct dvb_frontend *fe)
1512{
1513 struct xc4000_priv *priv = fe->tuner_priv;
1514 int ret = 0;
1515
1516 dprintk(1, "%s()\n", __func__);
1517
1518 mutex_lock(&priv->lock);
1519
1520 /* Avoid firmware reload on slow devices */
1521 if ((no_poweroff == 2 ||
1522 (no_poweroff == 0 && priv->default_pm != 0)) &&
1523 (priv->cur_fw.type & BASE) != 0) {
1524 /* force reset and firmware reload */
1525 priv->cur_fw.type = XC_POWERED_DOWN;
1526
1527 if (xc_write_reg(priv, XREG_POWER_DOWN, 0) != 0) {
1528 printk(KERN_ERR
1529 "xc4000: %s() unable to shutdown tuner\n",
1530 __func__);
1531 ret = -EREMOTEIO;
1532 }
1533 msleep(20);
1534 }
1535
1536 mutex_unlock(&priv->lock);
1537
1538 return ret;
1539}
1540
1541static int xc4000_init(struct dvb_frontend *fe)
1542{
1543 dprintk(1, "%s()\n", __func__);
1544
1545 return 0;
1546}
1547
1548static int xc4000_release(struct dvb_frontend *fe)
1549{
1550 struct xc4000_priv *priv = fe->tuner_priv;
1551
1552 dprintk(1, "%s()\n", __func__);
1553
1554 mutex_lock(&xc4000_list_mutex);
1555
1556 if (priv)
1557 hybrid_tuner_release_state(priv);
1558
1559 mutex_unlock(&xc4000_list_mutex);
1560
1561 fe->tuner_priv = NULL;
1562
1563 return 0;
1564}
1565
1566static const struct dvb_tuner_ops xc4000_tuner_ops = {
1567 .info = {
1568 .name = "Xceive XC4000",
1569 .frequency_min = 1000000,
1570 .frequency_max = 1023000000,
1571 .frequency_step = 50000,
1572 },
1573
1574 .release = xc4000_release,
1575 .init = xc4000_init,
1576 .sleep = xc4000_sleep,
1577
1578 .set_params = xc4000_set_params,
1579 .set_analog_params = xc4000_set_analog_params,
1580 .get_frequency = xc4000_get_frequency,
1581 .get_bandwidth = xc4000_get_bandwidth,
1582 .get_status = xc4000_get_status
1583};
1584
1585struct dvb_frontend *xc4000_attach(struct dvb_frontend *fe,
1586 struct i2c_adapter *i2c,
1587 struct xc4000_config *cfg)
1588{
1589 struct xc4000_priv *priv = NULL;
1590 int instance;
1591 u16 id = 0;
1592
1593 dprintk(1, "%s(%d-%04x)\n", __func__,
1594 i2c ? i2c_adapter_id(i2c) : -1,
1595 cfg ? cfg->i2c_address : -1);
1596
1597 mutex_lock(&xc4000_list_mutex);
1598
1599 instance = hybrid_tuner_request_state(struct xc4000_priv, priv,
1600 hybrid_tuner_instance_list,
1601 i2c, cfg->i2c_address, "xc4000");
1602 switch (instance) {
1603 case 0:
1604 goto fail;
1605 break;
1606 case 1:
1607 /* new tuner instance */
1608 priv->bandwidth = BANDWIDTH_6_MHZ;
1609 /* set default configuration */
1610 priv->if_khz = 4560;
1611 priv->default_pm = 0;
1612 priv->dvb_amplitude = 134;
1613 priv->set_smoothedcvbs = 1;
1614 mutex_init(&priv->lock);
1615 fe->tuner_priv = priv;
1616 break;
1617 default:
1618 /* existing tuner instance */
1619 fe->tuner_priv = priv;
1620 break;
1621 }
1622
1623 if (cfg->if_khz != 0) {
1624 /* copy configuration if provided by the caller */
1625 priv->if_khz = cfg->if_khz;
1626 priv->default_pm = cfg->default_pm;
1627 priv->dvb_amplitude = cfg->dvb_amplitude;
1628 priv->set_smoothedcvbs = cfg->set_smoothedcvbs;
1629 }
1630
1631 /* Check if firmware has been loaded. It is possible that another
1632 instance of the driver has loaded the firmware.
1633 */
1634
1635 if (instance == 1) {
1636 if (xc4000_readreg(priv, XREG_PRODUCT_ID, &id) != 0)
1637 goto fail;
1638 } else {
1639 id = ((priv->cur_fw.type & BASE) != 0 ?
1640 priv->hwmodel : XC_PRODUCT_ID_FW_NOT_LOADED);
1641 }
1642
1643 switch (id) {
1644 case XC_PRODUCT_ID_XC4000:
1645 case XC_PRODUCT_ID_XC4100:
1646 printk(KERN_INFO
1647 "xc4000: Successfully identified at address 0x%02x\n",
1648 cfg->i2c_address);
1649 printk(KERN_INFO
1650 "xc4000: Firmware has been loaded previously\n");
1651 break;
1652 case XC_PRODUCT_ID_FW_NOT_LOADED:
1653 printk(KERN_INFO
1654 "xc4000: Successfully identified at address 0x%02x\n",
1655 cfg->i2c_address);
1656 printk(KERN_INFO
1657 "xc4000: Firmware has not been loaded previously\n");
1658 break;
1659 default:
1660 printk(KERN_ERR
1661 "xc4000: Device not found at addr 0x%02x (0x%x)\n",
1662 cfg->i2c_address, id);
1663 goto fail;
1664 }
1665
1666 mutex_unlock(&xc4000_list_mutex);
1667
1668 memcpy(&fe->ops.tuner_ops, &xc4000_tuner_ops,
1669 sizeof(struct dvb_tuner_ops));
1670
1671 if (instance == 1) {
1672 int ret;
1673 mutex_lock(&priv->lock);
1674 ret = xc4000_fwupload(fe);
1675 mutex_unlock(&priv->lock);
1676 if (ret != 0)
1677 goto fail2;
1678 }
1679
1680 return fe;
1681fail:
1682 mutex_unlock(&xc4000_list_mutex);
1683fail2:
1684 xc4000_release(fe);
1685 return NULL;
1686}
1687EXPORT_SYMBOL(xc4000_attach);
1688
1689MODULE_AUTHOR("Steven Toth, Davide Ferri");
1690MODULE_DESCRIPTION("Xceive xc4000 silicon tuner driver");
1691MODULE_LICENSE("GPL");
diff --git a/drivers/media/common/tuners/xc4000.h b/drivers/media/common/tuners/xc4000.h
new file mode 100644
index 00000000000..e6a44d151cb
--- /dev/null
+++ b/drivers/media/common/tuners/xc4000.h
@@ -0,0 +1,67 @@
1/*
2 * Driver for Xceive XC4000 "QAM/8VSB single chip tuner"
3 *
4 * Copyright (c) 2007 Steven Toth <stoth@linuxtv.org>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 *
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
20 */
21
22#ifndef __XC4000_H__
23#define __XC4000_H__
24
25#include <linux/firmware.h>
26
27struct dvb_frontend;
28struct i2c_adapter;
29
30struct xc4000_config {
31 u8 i2c_address;
32 /* if non-zero, power management is enabled by default */
33 u8 default_pm;
34 /* value to be written to XREG_AMPLITUDE in DVB-T mode (0: no write) */
35 u8 dvb_amplitude;
36 /* if non-zero, register 0x0E is set to filter analog TV video output */
37 u8 set_smoothedcvbs;
38 /* IF for DVB-T */
39 u32 if_khz;
40};
41
42/* xc4000 callback command */
43#define XC4000_TUNER_RESET 0
44
45/* For each bridge framework, when it attaches either analog or digital,
46 * it has to store a reference back to its _core equivalent structure,
47 * so that it can service the hardware by steering gpio's etc.
48 * Each bridge implementation is different so cast devptr accordingly.
49 * The xc4000 driver cares not for this value, other than ensuring
50 * it's passed back to a bridge during tuner_callback().
51 */
52
53#if defined(CONFIG_MEDIA_TUNER_XC4000) || (defined(CONFIG_MEDIA_TUNER_XC4000_MODULE) && defined(MODULE))
54extern struct dvb_frontend *xc4000_attach(struct dvb_frontend *fe,
55 struct i2c_adapter *i2c,
56 struct xc4000_config *cfg);
57#else
58static inline struct dvb_frontend *xc4000_attach(struct dvb_frontend *fe,
59 struct i2c_adapter *i2c,
60 struct xc4000_config *cfg)
61{
62 printk(KERN_WARNING "%s: driver disabled by Kconfig\n", __func__);
63 return NULL;
64}
65#endif
66
67#endif
diff --git a/drivers/media/common/tuners/xc5000.c b/drivers/media/common/tuners/xc5000.c
new file mode 100644
index 00000000000..aa1b2e844d3
--- /dev/null
+++ b/drivers/media/common/tuners/xc5000.c
@@ -0,0 +1,1201 @@
1/*
2 * Driver for Xceive XC5000 "QAM/8VSB single chip tuner"
3 *
4 * Copyright (c) 2007 Xceive Corporation
5 * Copyright (c) 2007 Steven Toth <stoth@linuxtv.org>
6 * Copyright (c) 2009 Devin Heitmueller <dheitmueller@kernellabs.com>
7 *
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License as published by
10 * the Free Software Foundation; either version 2 of the License, or
11 * (at your option) any later version.
12 *
13 * This program is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 *
17 * GNU General Public License for more details.
18 *
19 * You should have received a copy of the GNU General Public License
20 * along with this program; if not, write to the Free Software
21 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
22 */
23
24#include <linux/module.h>
25#include <linux/moduleparam.h>
26#include <linux/videodev2.h>
27#include <linux/delay.h>
28#include <linux/dvb/frontend.h>
29#include <linux/i2c.h>
30
31#include "dvb_frontend.h"
32
33#include "xc5000.h"
34#include "tuner-i2c.h"
35
36static int debug;
37module_param(debug, int, 0644);
38MODULE_PARM_DESC(debug, "Turn on/off debugging (default:off).");
39
40static int no_poweroff;
41module_param(no_poweroff, int, 0644);
42MODULE_PARM_DESC(no_poweroff, "0 (default) powers device off when not used.\n"
43 "\t\t1 keep device energized and with tuner ready all the times.\n"
44 "\t\tFaster, but consumes more power and keeps the device hotter");
45
46static DEFINE_MUTEX(xc5000_list_mutex);
47static LIST_HEAD(hybrid_tuner_instance_list);
48
49#define dprintk(level, fmt, arg...) if (debug >= level) \
50 printk(KERN_INFO "%s: " fmt, "xc5000", ## arg)
51
52#define XC5000_DEFAULT_FIRMWARE "dvb-fe-xc5000-1.6.114.fw"
53#define XC5000_DEFAULT_FIRMWARE_SIZE 12401
54
55struct xc5000_priv {
56 struct tuner_i2c_props i2c_props;
57 struct list_head hybrid_tuner_instance_list;
58
59 u32 if_khz;
60 u32 freq_hz;
61 u32 bandwidth;
62 u8 video_standard;
63 u8 rf_mode;
64 u8 radio_input;
65};
66
67/* Misc Defines */
68#define MAX_TV_STANDARD 24
69#define XC_MAX_I2C_WRITE_LENGTH 64
70
71/* Signal Types */
72#define XC_RF_MODE_AIR 0
73#define XC_RF_MODE_CABLE 1
74
75/* Result codes */
76#define XC_RESULT_SUCCESS 0
77#define XC_RESULT_RESET_FAILURE 1
78#define XC_RESULT_I2C_WRITE_FAILURE 2
79#define XC_RESULT_I2C_READ_FAILURE 3
80#define XC_RESULT_OUT_OF_RANGE 5
81
82/* Product id */
83#define XC_PRODUCT_ID_FW_NOT_LOADED 0x2000
84#define XC_PRODUCT_ID_FW_LOADED 0x1388
85
86/* Registers */
87#define XREG_INIT 0x00
88#define XREG_VIDEO_MODE 0x01
89#define XREG_AUDIO_MODE 0x02
90#define XREG_RF_FREQ 0x03
91#define XREG_D_CODE 0x04
92#define XREG_IF_OUT 0x05
93#define XREG_SEEK_MODE 0x07
94#define XREG_POWER_DOWN 0x0A /* Obsolete */
95/* Set the output amplitude - SIF for analog, DTVP/DTVN for digital */
96#define XREG_OUTPUT_AMP 0x0B
97#define XREG_SIGNALSOURCE 0x0D /* 0=Air, 1=Cable */
98#define XREG_SMOOTHEDCVBS 0x0E
99#define XREG_XTALFREQ 0x0F
100#define XREG_FINERFREQ 0x10
101#define XREG_DDIMODE 0x11
102
103#define XREG_ADC_ENV 0x00
104#define XREG_QUALITY 0x01
105#define XREG_FRAME_LINES 0x02
106#define XREG_HSYNC_FREQ 0x03
107#define XREG_LOCK 0x04
108#define XREG_FREQ_ERROR 0x05
109#define XREG_SNR 0x06
110#define XREG_VERSION 0x07
111#define XREG_PRODUCT_ID 0x08
112#define XREG_BUSY 0x09
113#define XREG_BUILD 0x0D
114
115/*
116 Basic firmware description. This will remain with
117 the driver for documentation purposes.
118
119 This represents an I2C firmware file encoded as a
120 string of unsigned char. Format is as follows:
121
122 char[0 ]=len0_MSB -> len = len_MSB * 256 + len_LSB
123 char[1 ]=len0_LSB -> length of first write transaction
124 char[2 ]=data0 -> first byte to be sent
125 char[3 ]=data1
126 char[4 ]=data2
127 char[ ]=...
128 char[M ]=dataN -> last byte to be sent
129 char[M+1]=len1_MSB -> len = len_MSB * 256 + len_LSB
130 char[M+2]=len1_LSB -> length of second write transaction
131 char[M+3]=data0
132 char[M+4]=data1
133 ...
134 etc.
135
136 The [len] value should be interpreted as follows:
137
138 len= len_MSB _ len_LSB
139 len=1111_1111_1111_1111 : End of I2C_SEQUENCE
140 len=0000_0000_0000_0000 : Reset command: Do hardware reset
141 len=0NNN_NNNN_NNNN_NNNN : Normal transaction: number of bytes = {1:32767)
142 len=1WWW_WWWW_WWWW_WWWW : Wait command: wait for {1:32767} ms
143
144 For the RESET and WAIT commands, the two following bytes will contain
145 immediately the length of the following transaction.
146
147*/
148struct XC_TV_STANDARD {
149 char *Name;
150 u16 AudioMode;
151 u16 VideoMode;
152};
153
154/* Tuner standards */
155#define MN_NTSC_PAL_BTSC 0
156#define MN_NTSC_PAL_A2 1
157#define MN_NTSC_PAL_EIAJ 2
158#define MN_NTSC_PAL_Mono 3
159#define BG_PAL_A2 4
160#define BG_PAL_NICAM 5
161#define BG_PAL_MONO 6
162#define I_PAL_NICAM 7
163#define I_PAL_NICAM_MONO 8
164#define DK_PAL_A2 9
165#define DK_PAL_NICAM 10
166#define DK_PAL_MONO 11
167#define DK_SECAM_A2DK1 12
168#define DK_SECAM_A2LDK3 13
169#define DK_SECAM_A2MONO 14
170#define L_SECAM_NICAM 15
171#define LC_SECAM_NICAM 16
172#define DTV6 17
173#define DTV8 18
174#define DTV7_8 19
175#define DTV7 20
176#define FM_Radio_INPUT2 21
177#define FM_Radio_INPUT1 22
178#define FM_Radio_INPUT1_MONO 23
179
180static struct XC_TV_STANDARD XC5000_Standard[MAX_TV_STANDARD] = {
181 {"M/N-NTSC/PAL-BTSC", 0x0400, 0x8020},
182 {"M/N-NTSC/PAL-A2", 0x0600, 0x8020},
183 {"M/N-NTSC/PAL-EIAJ", 0x0440, 0x8020},
184 {"M/N-NTSC/PAL-Mono", 0x0478, 0x8020},
185 {"B/G-PAL-A2", 0x0A00, 0x8049},
186 {"B/G-PAL-NICAM", 0x0C04, 0x8049},
187 {"B/G-PAL-MONO", 0x0878, 0x8059},
188 {"I-PAL-NICAM", 0x1080, 0x8009},
189 {"I-PAL-NICAM-MONO", 0x0E78, 0x8009},
190 {"D/K-PAL-A2", 0x1600, 0x8009},
191 {"D/K-PAL-NICAM", 0x0E80, 0x8009},
192 {"D/K-PAL-MONO", 0x1478, 0x8009},
193 {"D/K-SECAM-A2 DK1", 0x1200, 0x8009},
194 {"D/K-SECAM-A2 L/DK3", 0x0E00, 0x8009},
195 {"D/K-SECAM-A2 MONO", 0x1478, 0x8009},
196 {"L-SECAM-NICAM", 0x8E82, 0x0009},
197 {"L'-SECAM-NICAM", 0x8E82, 0x4009},
198 {"DTV6", 0x00C0, 0x8002},
199 {"DTV8", 0x00C0, 0x800B},
200 {"DTV7/8", 0x00C0, 0x801B},
201 {"DTV7", 0x00C0, 0x8007},
202 {"FM Radio-INPUT2", 0x9802, 0x9002},
203 {"FM Radio-INPUT1", 0x0208, 0x9002},
204 {"FM Radio-INPUT1_MONO", 0x0278, 0x9002}
205};
206
207static int xc_load_fw_and_init_tuner(struct dvb_frontend *fe);
208static int xc5000_is_firmware_loaded(struct dvb_frontend *fe);
209static int xc5000_readreg(struct xc5000_priv *priv, u16 reg, u16 *val);
210static int xc5000_TunerReset(struct dvb_frontend *fe);
211
212static int xc_send_i2c_data(struct xc5000_priv *priv, u8 *buf, int len)
213{
214 struct i2c_msg msg = { .addr = priv->i2c_props.addr,
215 .flags = 0, .buf = buf, .len = len };
216
217 if (i2c_transfer(priv->i2c_props.adap, &msg, 1) != 1) {
218 printk(KERN_ERR "xc5000: I2C write failed (len=%i)\n", len);
219 return XC_RESULT_I2C_WRITE_FAILURE;
220 }
221 return XC_RESULT_SUCCESS;
222}
223
224#if 0
225/* This routine is never used because the only time we read data from the
226 i2c bus is when we read registers, and we want that to be an atomic i2c
227 transaction in case we are on a multi-master bus */
228static int xc_read_i2c_data(struct xc5000_priv *priv, u8 *buf, int len)
229{
230 struct i2c_msg msg = { .addr = priv->i2c_props.addr,
231 .flags = I2C_M_RD, .buf = buf, .len = len };
232
233 if (i2c_transfer(priv->i2c_props.adap, &msg, 1) != 1) {
234 printk(KERN_ERR "xc5000 I2C read failed (len=%i)\n", len);
235 return -EREMOTEIO;
236 }
237 return 0;
238}
239#endif
240
241static int xc5000_readreg(struct xc5000_priv *priv, u16 reg, u16 *val)
242{
243 u8 buf[2] = { reg >> 8, reg & 0xff };
244 u8 bval[2] = { 0, 0 };
245 struct i2c_msg msg[2] = {
246 { .addr = priv->i2c_props.addr,
247 .flags = 0, .buf = &buf[0], .len = 2 },
248 { .addr = priv->i2c_props.addr,
249 .flags = I2C_M_RD, .buf = &bval[0], .len = 2 },
250 };
251
252 if (i2c_transfer(priv->i2c_props.adap, msg, 2) != 2) {
253 printk(KERN_WARNING "xc5000: I2C read failed\n");
254 return -EREMOTEIO;
255 }
256
257 *val = (bval[0] << 8) | bval[1];
258 return XC_RESULT_SUCCESS;
259}
260
261static void xc_wait(int wait_ms)
262{
263 msleep(wait_ms);
264}
265
266static int xc5000_TunerReset(struct dvb_frontend *fe)
267{
268 struct xc5000_priv *priv = fe->tuner_priv;
269 int ret;
270
271 dprintk(1, "%s()\n", __func__);
272
273 if (fe->callback) {
274 ret = fe->callback(((fe->dvb) && (fe->dvb->priv)) ?
275 fe->dvb->priv :
276 priv->i2c_props.adap->algo_data,
277 DVB_FRONTEND_COMPONENT_TUNER,
278 XC5000_TUNER_RESET, 0);
279 if (ret) {
280 printk(KERN_ERR "xc5000: reset failed\n");
281 return XC_RESULT_RESET_FAILURE;
282 }
283 } else {
284 printk(KERN_ERR "xc5000: no tuner reset callback function, fatal\n");
285 return XC_RESULT_RESET_FAILURE;
286 }
287 return XC_RESULT_SUCCESS;
288}
289
290static int xc_write_reg(struct xc5000_priv *priv, u16 regAddr, u16 i2cData)
291{
292 u8 buf[4];
293 int WatchDogTimer = 100;
294 int result;
295
296 buf[0] = (regAddr >> 8) & 0xFF;
297 buf[1] = regAddr & 0xFF;
298 buf[2] = (i2cData >> 8) & 0xFF;
299 buf[3] = i2cData & 0xFF;
300 result = xc_send_i2c_data(priv, buf, 4);
301 if (result == XC_RESULT_SUCCESS) {
302 /* wait for busy flag to clear */
303 while ((WatchDogTimer > 0) && (result == XC_RESULT_SUCCESS)) {
304 result = xc5000_readreg(priv, XREG_BUSY, (u16 *)buf);
305 if (result == XC_RESULT_SUCCESS) {
306 if ((buf[0] == 0) && (buf[1] == 0)) {
307 /* busy flag cleared */
308 break;
309 } else {
310 xc_wait(5); /* wait 5 ms */
311 WatchDogTimer--;
312 }
313 }
314 }
315 }
316 if (WatchDogTimer < 0)
317 result = XC_RESULT_I2C_WRITE_FAILURE;
318
319 return result;
320}
321
322static int xc_load_i2c_sequence(struct dvb_frontend *fe, const u8 *i2c_sequence)
323{
324 struct xc5000_priv *priv = fe->tuner_priv;
325
326 int i, nbytes_to_send, result;
327 unsigned int len, pos, index;
328 u8 buf[XC_MAX_I2C_WRITE_LENGTH];
329
330 index = 0;
331 while ((i2c_sequence[index] != 0xFF) ||
332 (i2c_sequence[index + 1] != 0xFF)) {
333 len = i2c_sequence[index] * 256 + i2c_sequence[index+1];
334 if (len == 0x0000) {
335 /* RESET command */
336 result = xc5000_TunerReset(fe);
337 index += 2;
338 if (result != XC_RESULT_SUCCESS)
339 return result;
340 } else if (len & 0x8000) {
341 /* WAIT command */
342 xc_wait(len & 0x7FFF);
343 index += 2;
344 } else {
345 /* Send i2c data whilst ensuring individual transactions
346 * do not exceed XC_MAX_I2C_WRITE_LENGTH bytes.
347 */
348 index += 2;
349 buf[0] = i2c_sequence[index];
350 buf[1] = i2c_sequence[index + 1];
351 pos = 2;
352 while (pos < len) {
353 if ((len - pos) > XC_MAX_I2C_WRITE_LENGTH - 2)
354 nbytes_to_send =
355 XC_MAX_I2C_WRITE_LENGTH;
356 else
357 nbytes_to_send = (len - pos + 2);
358 for (i = 2; i < nbytes_to_send; i++) {
359 buf[i] = i2c_sequence[index + pos +
360 i - 2];
361 }
362 result = xc_send_i2c_data(priv, buf,
363 nbytes_to_send);
364
365 if (result != XC_RESULT_SUCCESS)
366 return result;
367
368 pos += nbytes_to_send - 2;
369 }
370 index += len;
371 }
372 }
373 return XC_RESULT_SUCCESS;
374}
375
376static int xc_initialize(struct xc5000_priv *priv)
377{
378 dprintk(1, "%s()\n", __func__);
379 return xc_write_reg(priv, XREG_INIT, 0);
380}
381
382static int xc_SetTVStandard(struct xc5000_priv *priv,
383 u16 VideoMode, u16 AudioMode)
384{
385 int ret;
386 dprintk(1, "%s(0x%04x,0x%04x)\n", __func__, VideoMode, AudioMode);
387 dprintk(1, "%s() Standard = %s\n",
388 __func__,
389 XC5000_Standard[priv->video_standard].Name);
390
391 ret = xc_write_reg(priv, XREG_VIDEO_MODE, VideoMode);
392 if (ret == XC_RESULT_SUCCESS)
393 ret = xc_write_reg(priv, XREG_AUDIO_MODE, AudioMode);
394
395 return ret;
396}
397
398static int xc_SetSignalSource(struct xc5000_priv *priv, u16 rf_mode)
399{
400 dprintk(1, "%s(%d) Source = %s\n", __func__, rf_mode,
401 rf_mode == XC_RF_MODE_AIR ? "ANTENNA" : "CABLE");
402
403 if ((rf_mode != XC_RF_MODE_AIR) && (rf_mode != XC_RF_MODE_CABLE)) {
404 rf_mode = XC_RF_MODE_CABLE;
405 printk(KERN_ERR
406 "%s(), Invalid mode, defaulting to CABLE",
407 __func__);
408 }
409 return xc_write_reg(priv, XREG_SIGNALSOURCE, rf_mode);
410}
411
412static const struct dvb_tuner_ops xc5000_tuner_ops;
413
414static int xc_set_RF_frequency(struct xc5000_priv *priv, u32 freq_hz)
415{
416 u16 freq_code;
417
418 dprintk(1, "%s(%u)\n", __func__, freq_hz);
419
420 if ((freq_hz > xc5000_tuner_ops.info.frequency_max) ||
421 (freq_hz < xc5000_tuner_ops.info.frequency_min))
422 return XC_RESULT_OUT_OF_RANGE;
423
424 freq_code = (u16)(freq_hz / 15625);
425
426 /* Starting in firmware version 1.1.44, Xceive recommends using the
427 FINERFREQ for all normal tuning (the doc indicates reg 0x03 should
428 only be used for fast scanning for channel lock) */
429 return xc_write_reg(priv, XREG_FINERFREQ, freq_code);
430}
431
432
433static int xc_set_IF_frequency(struct xc5000_priv *priv, u32 freq_khz)
434{
435 u32 freq_code = (freq_khz * 1024)/1000;
436 dprintk(1, "%s(freq_khz = %d) freq_code = 0x%x\n",
437 __func__, freq_khz, freq_code);
438
439 return xc_write_reg(priv, XREG_IF_OUT, freq_code);
440}
441
442
443static int xc_get_ADC_Envelope(struct xc5000_priv *priv, u16 *adc_envelope)
444{
445 return xc5000_readreg(priv, XREG_ADC_ENV, adc_envelope);
446}
447
448static int xc_get_frequency_error(struct xc5000_priv *priv, u32 *freq_error_hz)
449{
450 int result;
451 u16 regData;
452 u32 tmp;
453
454 result = xc5000_readreg(priv, XREG_FREQ_ERROR, &regData);
455 if (result != XC_RESULT_SUCCESS)
456 return result;
457
458 tmp = (u32)regData;
459 (*freq_error_hz) = (tmp * 15625) / 1000;
460 return result;
461}
462
463static int xc_get_lock_status(struct xc5000_priv *priv, u16 *lock_status)
464{
465 return xc5000_readreg(priv, XREG_LOCK, lock_status);
466}
467
468static int xc_get_version(struct xc5000_priv *priv,
469 u8 *hw_majorversion, u8 *hw_minorversion,
470 u8 *fw_majorversion, u8 *fw_minorversion)
471{
472 u16 data;
473 int result;
474
475 result = xc5000_readreg(priv, XREG_VERSION, &data);
476 if (result != XC_RESULT_SUCCESS)
477 return result;
478
479 (*hw_majorversion) = (data >> 12) & 0x0F;
480 (*hw_minorversion) = (data >> 8) & 0x0F;
481 (*fw_majorversion) = (data >> 4) & 0x0F;
482 (*fw_minorversion) = data & 0x0F;
483
484 return 0;
485}
486
487static int xc_get_buildversion(struct xc5000_priv *priv, u16 *buildrev)
488{
489 return xc5000_readreg(priv, XREG_BUILD, buildrev);
490}
491
492static int xc_get_hsync_freq(struct xc5000_priv *priv, u32 *hsync_freq_hz)
493{
494 u16 regData;
495 int result;
496
497 result = xc5000_readreg(priv, XREG_HSYNC_FREQ, &regData);
498 if (result != XC_RESULT_SUCCESS)
499 return result;
500
501 (*hsync_freq_hz) = ((regData & 0x0fff) * 763)/100;
502 return result;
503}
504
505static int xc_get_frame_lines(struct xc5000_priv *priv, u16 *frame_lines)
506{
507 return xc5000_readreg(priv, XREG_FRAME_LINES, frame_lines);
508}
509
510static int xc_get_quality(struct xc5000_priv *priv, u16 *quality)
511{
512 return xc5000_readreg(priv, XREG_QUALITY, quality);
513}
514
515static u16 WaitForLock(struct xc5000_priv *priv)
516{
517 u16 lockState = 0;
518 int watchDogCount = 40;
519
520 while ((lockState == 0) && (watchDogCount > 0)) {
521 xc_get_lock_status(priv, &lockState);
522 if (lockState != 1) {
523 xc_wait(5);
524 watchDogCount--;
525 }
526 }
527 return lockState;
528}
529
530#define XC_TUNE_ANALOG 0
531#define XC_TUNE_DIGITAL 1
532static int xc_tune_channel(struct xc5000_priv *priv, u32 freq_hz, int mode)
533{
534 int found = 0;
535
536 dprintk(1, "%s(%u)\n", __func__, freq_hz);
537
538 if (xc_set_RF_frequency(priv, freq_hz) != XC_RESULT_SUCCESS)
539 return 0;
540
541 if (mode == XC_TUNE_ANALOG) {
542 if (WaitForLock(priv) == 1)
543 found = 1;
544 }
545
546 return found;
547}
548
549
550static int xc5000_fwupload(struct dvb_frontend *fe)
551{
552 struct xc5000_priv *priv = fe->tuner_priv;
553 const struct firmware *fw;
554 int ret;
555
556 /* request the firmware, this will block and timeout */
557 printk(KERN_INFO "xc5000: waiting for firmware upload (%s)...\n",
558 XC5000_DEFAULT_FIRMWARE);
559
560 ret = request_firmware(&fw, XC5000_DEFAULT_FIRMWARE,
561 priv->i2c_props.adap->dev.parent);
562 if (ret) {
563 printk(KERN_ERR "xc5000: Upload failed. (file not found?)\n");
564 ret = XC_RESULT_RESET_FAILURE;
565 goto out;
566 } else {
567 printk(KERN_DEBUG "xc5000: firmware read %Zu bytes.\n",
568 fw->size);
569 ret = XC_RESULT_SUCCESS;
570 }
571
572 if (fw->size != XC5000_DEFAULT_FIRMWARE_SIZE) {
573 printk(KERN_ERR "xc5000: firmware incorrect size\n");
574 ret = XC_RESULT_RESET_FAILURE;
575 } else {
576 printk(KERN_INFO "xc5000: firmware uploading...\n");
577 ret = xc_load_i2c_sequence(fe, fw->data);
578 printk(KERN_INFO "xc5000: firmware upload complete...\n");
579 }
580
581out:
582 release_firmware(fw);
583 return ret;
584}
585
586static void xc_debug_dump(struct xc5000_priv *priv)
587{
588 u16 adc_envelope;
589 u32 freq_error_hz = 0;
590 u16 lock_status;
591 u32 hsync_freq_hz = 0;
592 u16 frame_lines;
593 u16 quality;
594 u8 hw_majorversion = 0, hw_minorversion = 0;
595 u8 fw_majorversion = 0, fw_minorversion = 0;
596 u16 fw_buildversion = 0;
597
598 /* Wait for stats to stabilize.
599 * Frame Lines needs two frame times after initial lock
600 * before it is valid.
601 */
602 xc_wait(100);
603
604 xc_get_ADC_Envelope(priv, &adc_envelope);
605 dprintk(1, "*** ADC envelope (0-1023) = %d\n", adc_envelope);
606
607 xc_get_frequency_error(priv, &freq_error_hz);
608 dprintk(1, "*** Frequency error = %d Hz\n", freq_error_hz);
609
610 xc_get_lock_status(priv, &lock_status);
611 dprintk(1, "*** Lock status (0-Wait, 1-Locked, 2-No-signal) = %d\n",
612 lock_status);
613
614 xc_get_version(priv, &hw_majorversion, &hw_minorversion,
615 &fw_majorversion, &fw_minorversion);
616 xc_get_buildversion(priv, &fw_buildversion);
617 dprintk(1, "*** HW: V%02x.%02x, FW: V%02x.%02x.%04x\n",
618 hw_majorversion, hw_minorversion,
619 fw_majorversion, fw_minorversion, fw_buildversion);
620
621 xc_get_hsync_freq(priv, &hsync_freq_hz);
622 dprintk(1, "*** Horizontal sync frequency = %d Hz\n", hsync_freq_hz);
623
624 xc_get_frame_lines(priv, &frame_lines);
625 dprintk(1, "*** Frame lines = %d\n", frame_lines);
626
627 xc_get_quality(priv, &quality);
628 dprintk(1, "*** Quality (0:<8dB, 7:>56dB) = %d\n", quality);
629}
630
631/*
632 * As defined on EN 300 429, the DVB-C roll-off factor is 0.15.
633 * So, the amount of the needed bandwith is given by:
634 * Bw = Symbol_rate * (1 + 0.15)
635 * As such, the maximum symbol rate supported by 6 MHz is given by:
636 * max_symbol_rate = 6 MHz / 1.15 = 5217391 Bauds
637 */
638#define MAX_SYMBOL_RATE_6MHz 5217391
639
640static int xc5000_set_params(struct dvb_frontend *fe,
641 struct dvb_frontend_parameters *params)
642{
643 struct xc5000_priv *priv = fe->tuner_priv;
644 int ret;
645
646 if (xc5000_is_firmware_loaded(fe) != XC_RESULT_SUCCESS) {
647 if (xc_load_fw_and_init_tuner(fe) != XC_RESULT_SUCCESS) {
648 dprintk(1, "Unable to load firmware and init tuner\n");
649 return -EINVAL;
650 }
651 }
652
653 dprintk(1, "%s() frequency=%d (Hz)\n", __func__, params->frequency);
654
655 if (fe->ops.info.type == FE_ATSC) {
656 dprintk(1, "%s() ATSC\n", __func__);
657 switch (params->u.vsb.modulation) {
658 case VSB_8:
659 case VSB_16:
660 dprintk(1, "%s() VSB modulation\n", __func__);
661 priv->rf_mode = XC_RF_MODE_AIR;
662 priv->freq_hz = params->frequency - 1750000;
663 priv->bandwidth = BANDWIDTH_6_MHZ;
664 priv->video_standard = DTV6;
665 break;
666 case QAM_64:
667 case QAM_256:
668 case QAM_AUTO:
669 dprintk(1, "%s() QAM modulation\n", __func__);
670 priv->rf_mode = XC_RF_MODE_CABLE;
671 priv->freq_hz = params->frequency - 1750000;
672 priv->bandwidth = BANDWIDTH_6_MHZ;
673 priv->video_standard = DTV6;
674 break;
675 default:
676 return -EINVAL;
677 }
678 } else if (fe->ops.info.type == FE_OFDM) {
679 dprintk(1, "%s() OFDM\n", __func__);
680 switch (params->u.ofdm.bandwidth) {
681 case BANDWIDTH_6_MHZ:
682 priv->bandwidth = BANDWIDTH_6_MHZ;
683 priv->video_standard = DTV6;
684 priv->freq_hz = params->frequency - 1750000;
685 break;
686 case BANDWIDTH_7_MHZ:
687 printk(KERN_ERR "xc5000 bandwidth 7MHz not supported\n");
688 return -EINVAL;
689 case BANDWIDTH_8_MHZ:
690 priv->bandwidth = BANDWIDTH_8_MHZ;
691 priv->video_standard = DTV8;
692 priv->freq_hz = params->frequency - 2750000;
693 break;
694 default:
695 printk(KERN_ERR "xc5000 bandwidth not set!\n");
696 return -EINVAL;
697 }
698 priv->rf_mode = XC_RF_MODE_AIR;
699 } else if (fe->ops.info.type == FE_QAM) {
700 switch (params->u.qam.modulation) {
701 case QAM_256:
702 case QAM_AUTO:
703 case QAM_16:
704 case QAM_32:
705 case QAM_64:
706 case QAM_128:
707 dprintk(1, "%s() QAM modulation\n", __func__);
708 priv->rf_mode = XC_RF_MODE_CABLE;
709 /*
710 * Using a 8MHz bandwidth sometimes fail
711 * with 6MHz-spaced channels, due to inter-carrier
712 * interference. So, use DTV6 firmware
713 */
714 if (params->u.qam.symbol_rate <= MAX_SYMBOL_RATE_6MHz) {
715 priv->bandwidth = BANDWIDTH_6_MHZ;
716 priv->video_standard = DTV6;
717 priv->freq_hz = params->frequency - 1750000;
718 } else {
719 priv->bandwidth = BANDWIDTH_8_MHZ;
720 priv->video_standard = DTV7_8;
721 priv->freq_hz = params->frequency - 2750000;
722 }
723 break;
724 default:
725 dprintk(1, "%s() Unsupported QAM type\n", __func__);
726 return -EINVAL;
727 }
728 } else {
729 printk(KERN_ERR "xc5000 modulation type not supported!\n");
730 return -EINVAL;
731 }
732
733 dprintk(1, "%s() frequency=%d (compensated)\n",
734 __func__, priv->freq_hz);
735
736 ret = xc_SetSignalSource(priv, priv->rf_mode);
737 if (ret != XC_RESULT_SUCCESS) {
738 printk(KERN_ERR
739 "xc5000: xc_SetSignalSource(%d) failed\n",
740 priv->rf_mode);
741 return -EREMOTEIO;
742 }
743
744 ret = xc_SetTVStandard(priv,
745 XC5000_Standard[priv->video_standard].VideoMode,
746 XC5000_Standard[priv->video_standard].AudioMode);
747 if (ret != XC_RESULT_SUCCESS) {
748 printk(KERN_ERR "xc5000: xc_SetTVStandard failed\n");
749 return -EREMOTEIO;
750 }
751
752 ret = xc_set_IF_frequency(priv, priv->if_khz);
753 if (ret != XC_RESULT_SUCCESS) {
754 printk(KERN_ERR "xc5000: xc_Set_IF_frequency(%d) failed\n",
755 priv->if_khz);
756 return -EIO;
757 }
758
759 xc_write_reg(priv, XREG_OUTPUT_AMP, 0x8a);
760
761 xc_tune_channel(priv, priv->freq_hz, XC_TUNE_DIGITAL);
762
763 if (debug)
764 xc_debug_dump(priv);
765
766 return 0;
767}
768
769static int xc5000_is_firmware_loaded(struct dvb_frontend *fe)
770{
771 struct xc5000_priv *priv = fe->tuner_priv;
772 int ret;
773 u16 id;
774
775 ret = xc5000_readreg(priv, XREG_PRODUCT_ID, &id);
776 if (ret == XC_RESULT_SUCCESS) {
777 if (id == XC_PRODUCT_ID_FW_NOT_LOADED)
778 ret = XC_RESULT_RESET_FAILURE;
779 else
780 ret = XC_RESULT_SUCCESS;
781 }
782
783 dprintk(1, "%s() returns %s id = 0x%x\n", __func__,
784 ret == XC_RESULT_SUCCESS ? "True" : "False", id);
785 return ret;
786}
787
788static int xc5000_set_tv_freq(struct dvb_frontend *fe,
789 struct analog_parameters *params)
790{
791 struct xc5000_priv *priv = fe->tuner_priv;
792 int ret;
793
794 dprintk(1, "%s() frequency=%d (in units of 62.5khz)\n",
795 __func__, params->frequency);
796
797 /* Fix me: it could be air. */
798 priv->rf_mode = params->mode;
799 if (params->mode > XC_RF_MODE_CABLE)
800 priv->rf_mode = XC_RF_MODE_CABLE;
801
802 /* params->frequency is in units of 62.5khz */
803 priv->freq_hz = params->frequency * 62500;
804
805 /* FIX ME: Some video standards may have several possible audio
806 standards. We simply default to one of them here.
807 */
808 if (params->std & V4L2_STD_MN) {
809 /* default to BTSC audio standard */
810 priv->video_standard = MN_NTSC_PAL_BTSC;
811 goto tune_channel;
812 }
813
814 if (params->std & V4L2_STD_PAL_BG) {
815 /* default to NICAM audio standard */
816 priv->video_standard = BG_PAL_NICAM;
817 goto tune_channel;
818 }
819
820 if (params->std & V4L2_STD_PAL_I) {
821 /* default to NICAM audio standard */
822 priv->video_standard = I_PAL_NICAM;
823 goto tune_channel;
824 }
825
826 if (params->std & V4L2_STD_PAL_DK) {
827 /* default to NICAM audio standard */
828 priv->video_standard = DK_PAL_NICAM;
829 goto tune_channel;
830 }
831
832 if (params->std & V4L2_STD_SECAM_DK) {
833 /* default to A2 DK1 audio standard */
834 priv->video_standard = DK_SECAM_A2DK1;
835 goto tune_channel;
836 }
837
838 if (params->std & V4L2_STD_SECAM_L) {
839 priv->video_standard = L_SECAM_NICAM;
840 goto tune_channel;
841 }
842
843 if (params->std & V4L2_STD_SECAM_LC) {
844 priv->video_standard = LC_SECAM_NICAM;
845 goto tune_channel;
846 }
847
848tune_channel:
849 ret = xc_SetSignalSource(priv, priv->rf_mode);
850 if (ret != XC_RESULT_SUCCESS) {
851 printk(KERN_ERR
852 "xc5000: xc_SetSignalSource(%d) failed\n",
853 priv->rf_mode);
854 return -EREMOTEIO;
855 }
856
857 ret = xc_SetTVStandard(priv,
858 XC5000_Standard[priv->video_standard].VideoMode,
859 XC5000_Standard[priv->video_standard].AudioMode);
860 if (ret != XC_RESULT_SUCCESS) {
861 printk(KERN_ERR "xc5000: xc_SetTVStandard failed\n");
862 return -EREMOTEIO;
863 }
864
865 xc_write_reg(priv, XREG_OUTPUT_AMP, 0x09);
866
867 xc_tune_channel(priv, priv->freq_hz, XC_TUNE_ANALOG);
868
869 if (debug)
870 xc_debug_dump(priv);
871
872 return 0;
873}
874
875static int xc5000_set_radio_freq(struct dvb_frontend *fe,
876 struct analog_parameters *params)
877{
878 struct xc5000_priv *priv = fe->tuner_priv;
879 int ret = -EINVAL;
880 u8 radio_input;
881
882 dprintk(1, "%s() frequency=%d (in units of khz)\n",
883 __func__, params->frequency);
884
885 if (priv->radio_input == XC5000_RADIO_NOT_CONFIGURED) {
886 dprintk(1, "%s() radio input not configured\n", __func__);
887 return -EINVAL;
888 }
889
890 if (priv->radio_input == XC5000_RADIO_FM1)
891 radio_input = FM_Radio_INPUT1;
892 else if (priv->radio_input == XC5000_RADIO_FM2)
893 radio_input = FM_Radio_INPUT2;
894 else if (priv->radio_input == XC5000_RADIO_FM1_MONO)
895 radio_input = FM_Radio_INPUT1_MONO;
896 else {
897 dprintk(1, "%s() unknown radio input %d\n", __func__,
898 priv->radio_input);
899 return -EINVAL;
900 }
901
902 priv->freq_hz = params->frequency * 125 / 2;
903
904 priv->rf_mode = XC_RF_MODE_AIR;
905
906 ret = xc_SetTVStandard(priv, XC5000_Standard[radio_input].VideoMode,
907 XC5000_Standard[radio_input].AudioMode);
908
909 if (ret != XC_RESULT_SUCCESS) {
910 printk(KERN_ERR "xc5000: xc_SetTVStandard failed\n");
911 return -EREMOTEIO;
912 }
913
914 ret = xc_SetSignalSource(priv, priv->rf_mode);
915 if (ret != XC_RESULT_SUCCESS) {
916 printk(KERN_ERR
917 "xc5000: xc_SetSignalSource(%d) failed\n",
918 priv->rf_mode);
919 return -EREMOTEIO;
920 }
921
922 if ((priv->radio_input == XC5000_RADIO_FM1) ||
923 (priv->radio_input == XC5000_RADIO_FM2))
924 xc_write_reg(priv, XREG_OUTPUT_AMP, 0x09);
925 else if (priv->radio_input == XC5000_RADIO_FM1_MONO)
926 xc_write_reg(priv, XREG_OUTPUT_AMP, 0x06);
927
928 xc_tune_channel(priv, priv->freq_hz, XC_TUNE_ANALOG);
929
930 return 0;
931}
932
933static int xc5000_set_analog_params(struct dvb_frontend *fe,
934 struct analog_parameters *params)
935{
936 struct xc5000_priv *priv = fe->tuner_priv;
937 int ret = -EINVAL;
938
939 if (priv->i2c_props.adap == NULL)
940 return -EINVAL;
941
942 if (xc5000_is_firmware_loaded(fe) != XC_RESULT_SUCCESS) {
943 if (xc_load_fw_and_init_tuner(fe) != XC_RESULT_SUCCESS) {
944 dprintk(1, "Unable to load firmware and init tuner\n");
945 return -EINVAL;
946 }
947 }
948
949 switch (params->mode) {
950 case V4L2_TUNER_RADIO:
951 ret = xc5000_set_radio_freq(fe, params);
952 break;
953 case V4L2_TUNER_ANALOG_TV:
954 case V4L2_TUNER_DIGITAL_TV:
955 ret = xc5000_set_tv_freq(fe, params);
956 break;
957 }
958
959 return ret;
960}
961
962
963static int xc5000_get_frequency(struct dvb_frontend *fe, u32 *freq)
964{
965 struct xc5000_priv *priv = fe->tuner_priv;
966 dprintk(1, "%s()\n", __func__);
967 *freq = priv->freq_hz;
968 return 0;
969}
970
971static int xc5000_get_bandwidth(struct dvb_frontend *fe, u32 *bw)
972{
973 struct xc5000_priv *priv = fe->tuner_priv;
974 dprintk(1, "%s()\n", __func__);
975
976 *bw = priv->bandwidth;
977 return 0;
978}
979
980static int xc5000_get_status(struct dvb_frontend *fe, u32 *status)
981{
982 struct xc5000_priv *priv = fe->tuner_priv;
983 u16 lock_status = 0;
984
985 xc_get_lock_status(priv, &lock_status);
986
987 dprintk(1, "%s() lock_status = 0x%08x\n", __func__, lock_status);
988
989 *status = lock_status;
990
991 return 0;
992}
993
994static int xc_load_fw_and_init_tuner(struct dvb_frontend *fe)
995{
996 struct xc5000_priv *priv = fe->tuner_priv;
997 int ret = 0;
998
999 if (xc5000_is_firmware_loaded(fe) != XC_RESULT_SUCCESS) {
1000 ret = xc5000_fwupload(fe);
1001 if (ret != XC_RESULT_SUCCESS)
1002 return ret;
1003 }
1004
1005 /* Start the tuner self-calibration process */
1006 ret |= xc_initialize(priv);
1007
1008 /* Wait for calibration to complete.
1009 * We could continue but XC5000 will clock stretch subsequent
1010 * I2C transactions until calibration is complete. This way we
1011 * don't have to rely on clock stretching working.
1012 */
1013 xc_wait(100);
1014
1015 /* Default to "CABLE" mode */
1016 ret |= xc_write_reg(priv, XREG_SIGNALSOURCE, XC_RF_MODE_CABLE);
1017
1018 return ret;
1019}
1020
1021static int xc5000_sleep(struct dvb_frontend *fe)
1022{
1023 int ret;
1024
1025 dprintk(1, "%s()\n", __func__);
1026
1027 /* Avoid firmware reload on slow devices */
1028 if (no_poweroff)
1029 return 0;
1030
1031 /* According to Xceive technical support, the "powerdown" register
1032 was removed in newer versions of the firmware. The "supported"
1033 way to sleep the tuner is to pull the reset pin low for 10ms */
1034 ret = xc5000_TunerReset(fe);
1035 if (ret != XC_RESULT_SUCCESS) {
1036 printk(KERN_ERR
1037 "xc5000: %s() unable to shutdown tuner\n",
1038 __func__);
1039 return -EREMOTEIO;
1040 } else
1041 return XC_RESULT_SUCCESS;
1042}
1043
1044static int xc5000_init(struct dvb_frontend *fe)
1045{
1046 struct xc5000_priv *priv = fe->tuner_priv;
1047 dprintk(1, "%s()\n", __func__);
1048
1049 if (xc_load_fw_and_init_tuner(fe) != XC_RESULT_SUCCESS) {
1050 printk(KERN_ERR "xc5000: Unable to initialise tuner\n");
1051 return -EREMOTEIO;
1052 }
1053
1054 if (debug)
1055 xc_debug_dump(priv);
1056
1057 return 0;
1058}
1059
1060static int xc5000_release(struct dvb_frontend *fe)
1061{
1062 struct xc5000_priv *priv = fe->tuner_priv;
1063
1064 dprintk(1, "%s()\n", __func__);
1065
1066 mutex_lock(&xc5000_list_mutex);
1067
1068 if (priv)
1069 hybrid_tuner_release_state(priv);
1070
1071 mutex_unlock(&xc5000_list_mutex);
1072
1073 fe->tuner_priv = NULL;
1074
1075 return 0;
1076}
1077
1078static int xc5000_set_config(struct dvb_frontend *fe, void *priv_cfg)
1079{
1080 struct xc5000_priv *priv = fe->tuner_priv;
1081 struct xc5000_config *p = priv_cfg;
1082
1083 dprintk(1, "%s()\n", __func__);
1084
1085 if (p->if_khz)
1086 priv->if_khz = p->if_khz;
1087
1088 if (p->radio_input)
1089 priv->radio_input = p->radio_input;
1090
1091 return 0;
1092}
1093
1094
1095static const struct dvb_tuner_ops xc5000_tuner_ops = {
1096 .info = {
1097 .name = "Xceive XC5000",
1098 .frequency_min = 1000000,
1099 .frequency_max = 1023000000,
1100 .frequency_step = 50000,
1101 },
1102
1103 .release = xc5000_release,
1104 .init = xc5000_init,
1105 .sleep = xc5000_sleep,
1106
1107 .set_config = xc5000_set_config,
1108 .set_params = xc5000_set_params,
1109 .set_analog_params = xc5000_set_analog_params,
1110 .get_frequency = xc5000_get_frequency,
1111 .get_bandwidth = xc5000_get_bandwidth,
1112 .get_status = xc5000_get_status
1113};
1114
1115struct dvb_frontend *xc5000_attach(struct dvb_frontend *fe,
1116 struct i2c_adapter *i2c,
1117 const struct xc5000_config *cfg)
1118{
1119 struct xc5000_priv *priv = NULL;
1120 int instance;
1121 u16 id = 0;
1122
1123 dprintk(1, "%s(%d-%04x)\n", __func__,
1124 i2c ? i2c_adapter_id(i2c) : -1,
1125 cfg ? cfg->i2c_address : -1);
1126
1127 mutex_lock(&xc5000_list_mutex);
1128
1129 instance = hybrid_tuner_request_state(struct xc5000_priv, priv,
1130 hybrid_tuner_instance_list,
1131 i2c, cfg->i2c_address, "xc5000");
1132 switch (instance) {
1133 case 0:
1134 goto fail;
1135 break;
1136 case 1:
1137 /* new tuner instance */
1138 priv->bandwidth = BANDWIDTH_6_MHZ;
1139 fe->tuner_priv = priv;
1140 break;
1141 default:
1142 /* existing tuner instance */
1143 fe->tuner_priv = priv;
1144 break;
1145 }
1146
1147 if (priv->if_khz == 0) {
1148 /* If the IF hasn't been set yet, use the value provided by
1149 the caller (occurs in hybrid devices where the analog
1150 call to xc5000_attach occurs before the digital side) */
1151 priv->if_khz = cfg->if_khz;
1152 }
1153
1154 if (priv->radio_input == 0)
1155 priv->radio_input = cfg->radio_input;
1156
1157 /* Check if firmware has been loaded. It is possible that another
1158 instance of the driver has loaded the firmware.
1159 */
1160 if (xc5000_readreg(priv, XREG_PRODUCT_ID, &id) != XC_RESULT_SUCCESS)
1161 goto fail;
1162
1163 switch (id) {
1164 case XC_PRODUCT_ID_FW_LOADED:
1165 printk(KERN_INFO
1166 "xc5000: Successfully identified at address 0x%02x\n",
1167 cfg->i2c_address);
1168 printk(KERN_INFO
1169 "xc5000: Firmware has been loaded previously\n");
1170 break;
1171 case XC_PRODUCT_ID_FW_NOT_LOADED:
1172 printk(KERN_INFO
1173 "xc5000: Successfully identified at address 0x%02x\n",
1174 cfg->i2c_address);
1175 printk(KERN_INFO
1176 "xc5000: Firmware has not been loaded previously\n");
1177 break;
1178 default:
1179 printk(KERN_ERR
1180 "xc5000: Device not found at addr 0x%02x (0x%x)\n",
1181 cfg->i2c_address, id);
1182 goto fail;
1183 }
1184
1185 mutex_unlock(&xc5000_list_mutex);
1186
1187 memcpy(&fe->ops.tuner_ops, &xc5000_tuner_ops,
1188 sizeof(struct dvb_tuner_ops));
1189
1190 return fe;
1191fail:
1192 mutex_unlock(&xc5000_list_mutex);
1193
1194 xc5000_release(fe);
1195 return NULL;
1196}
1197EXPORT_SYMBOL(xc5000_attach);
1198
1199MODULE_AUTHOR("Steven Toth");
1200MODULE_DESCRIPTION("Xceive xc5000 silicon tuner driver");
1201MODULE_LICENSE("GPL");
diff --git a/drivers/media/common/tuners/xc5000.h b/drivers/media/common/tuners/xc5000.h
new file mode 100644
index 00000000000..e2957451b53
--- /dev/null
+++ b/drivers/media/common/tuners/xc5000.h
@@ -0,0 +1,68 @@
1/*
2 * Driver for Xceive XC5000 "QAM/8VSB single chip tuner"
3 *
4 * Copyright (c) 2007 Steven Toth <stoth@linuxtv.org>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 *
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
20 */
21
22#ifndef __XC5000_H__
23#define __XC5000_H__
24
25#include <linux/firmware.h>
26
27struct dvb_frontend;
28struct i2c_adapter;
29
30struct xc5000_config {
31 u8 i2c_address;
32 u32 if_khz;
33 u8 radio_input;
34};
35
36/* xc5000 callback command */
37#define XC5000_TUNER_RESET 0
38
39/* Possible Radio inputs */
40#define XC5000_RADIO_NOT_CONFIGURED 0
41#define XC5000_RADIO_FM1 1
42#define XC5000_RADIO_FM2 2
43#define XC5000_RADIO_FM1_MONO 3
44
45/* For each bridge framework, when it attaches either analog or digital,
46 * it has to store a reference back to its _core equivalent structure,
47 * so that it can service the hardware by steering gpio's etc.
48 * Each bridge implementation is different so cast devptr accordingly.
49 * The xc5000 driver cares not for this value, other than ensuring
50 * it's passed back to a bridge during tuner_callback().
51 */
52
53#if defined(CONFIG_MEDIA_TUNER_XC5000) || \
54 (defined(CONFIG_MEDIA_TUNER_XC5000_MODULE) && defined(MODULE))
55extern struct dvb_frontend *xc5000_attach(struct dvb_frontend *fe,
56 struct i2c_adapter *i2c,
57 const struct xc5000_config *cfg);
58#else
59static inline struct dvb_frontend *xc5000_attach(struct dvb_frontend *fe,
60 struct i2c_adapter *i2c,
61 const struct xc5000_config *cfg)
62{
63 printk(KERN_WARNING "%s: driver disabled by Kconfig\n", __func__);
64 return NULL;
65}
66#endif
67
68#endif