xref: /OK3568_Linux_fs/kernel/drivers/media/tuners/tda18250.c (revision 4882a59341e53eb6f0b4789bf948001014eff981)
1*4882a593Smuzhiyun // SPDX-License-Identifier: GPL-2.0-or-later
2*4882a593Smuzhiyun /*
3*4882a593Smuzhiyun  * NXP TDA18250 silicon tuner driver
4*4882a593Smuzhiyun  *
5*4882a593Smuzhiyun  * Copyright (C) 2017 Olli Salonen <olli.salonen@iki.fi>
6*4882a593Smuzhiyun  */
7*4882a593Smuzhiyun 
8*4882a593Smuzhiyun #include "tda18250_priv.h"
9*4882a593Smuzhiyun #include <linux/regmap.h>
10*4882a593Smuzhiyun 
11*4882a593Smuzhiyun static const struct dvb_tuner_ops tda18250_ops;
12*4882a593Smuzhiyun 
tda18250_power_control(struct dvb_frontend * fe,unsigned int power_state)13*4882a593Smuzhiyun static int tda18250_power_control(struct dvb_frontend *fe,
14*4882a593Smuzhiyun 		unsigned int power_state)
15*4882a593Smuzhiyun {
16*4882a593Smuzhiyun 	struct i2c_client *client = fe->tuner_priv;
17*4882a593Smuzhiyun 	struct tda18250_dev *dev = i2c_get_clientdata(client);
18*4882a593Smuzhiyun 	int ret;
19*4882a593Smuzhiyun 	unsigned int utmp;
20*4882a593Smuzhiyun 
21*4882a593Smuzhiyun 	dev_dbg(&client->dev, "power state: %d", power_state);
22*4882a593Smuzhiyun 
23*4882a593Smuzhiyun 	switch (power_state) {
24*4882a593Smuzhiyun 	case TDA18250_POWER_NORMAL:
25*4882a593Smuzhiyun 		ret = regmap_write_bits(dev->regmap, R06_POWER2, 0x07, 0x00);
26*4882a593Smuzhiyun 		if (ret)
27*4882a593Smuzhiyun 			goto err;
28*4882a593Smuzhiyun 		ret = regmap_write_bits(dev->regmap, R25_REF, 0xc0, 0xc0);
29*4882a593Smuzhiyun 		if (ret)
30*4882a593Smuzhiyun 			goto err;
31*4882a593Smuzhiyun 		break;
32*4882a593Smuzhiyun 	case TDA18250_POWER_STANDBY:
33*4882a593Smuzhiyun 		if (dev->loopthrough) {
34*4882a593Smuzhiyun 			ret = regmap_write_bits(dev->regmap,
35*4882a593Smuzhiyun 					R25_REF, 0xc0, 0x80);
36*4882a593Smuzhiyun 			if (ret)
37*4882a593Smuzhiyun 				goto err;
38*4882a593Smuzhiyun 			ret = regmap_write_bits(dev->regmap,
39*4882a593Smuzhiyun 					R06_POWER2, 0x07, 0x02);
40*4882a593Smuzhiyun 			if (ret)
41*4882a593Smuzhiyun 				goto err;
42*4882a593Smuzhiyun 			ret = regmap_write_bits(dev->regmap,
43*4882a593Smuzhiyun 					R10_LT1, 0x80, 0x00);
44*4882a593Smuzhiyun 			if (ret)
45*4882a593Smuzhiyun 				goto err;
46*4882a593Smuzhiyun 		} else {
47*4882a593Smuzhiyun 			ret = regmap_write_bits(dev->regmap,
48*4882a593Smuzhiyun 					R25_REF, 0xc0, 0x80);
49*4882a593Smuzhiyun 			if (ret)
50*4882a593Smuzhiyun 				goto err;
51*4882a593Smuzhiyun 			ret = regmap_write_bits(dev->regmap,
52*4882a593Smuzhiyun 					R06_POWER2, 0x07, 0x01);
53*4882a593Smuzhiyun 			if (ret)
54*4882a593Smuzhiyun 				goto err;
55*4882a593Smuzhiyun 			ret = regmap_read(dev->regmap,
56*4882a593Smuzhiyun 					R0D_AGC12, &utmp);
57*4882a593Smuzhiyun 			if (ret)
58*4882a593Smuzhiyun 				goto err;
59*4882a593Smuzhiyun 			ret = regmap_write_bits(dev->regmap,
60*4882a593Smuzhiyun 					R0D_AGC12, 0x03, 0x03);
61*4882a593Smuzhiyun 			if (ret)
62*4882a593Smuzhiyun 				goto err;
63*4882a593Smuzhiyun 			ret = regmap_write_bits(dev->regmap,
64*4882a593Smuzhiyun 					R10_LT1, 0x80, 0x80);
65*4882a593Smuzhiyun 			if (ret)
66*4882a593Smuzhiyun 				goto err;
67*4882a593Smuzhiyun 			ret = regmap_write_bits(dev->regmap,
68*4882a593Smuzhiyun 					R0D_AGC12, 0x03, utmp & 0x03);
69*4882a593Smuzhiyun 			if (ret)
70*4882a593Smuzhiyun 				goto err;
71*4882a593Smuzhiyun 		}
72*4882a593Smuzhiyun 		break;
73*4882a593Smuzhiyun 	default:
74*4882a593Smuzhiyun 		ret = -EINVAL;
75*4882a593Smuzhiyun 		goto err;
76*4882a593Smuzhiyun 	}
77*4882a593Smuzhiyun 
78*4882a593Smuzhiyun 	return 0;
79*4882a593Smuzhiyun err:
80*4882a593Smuzhiyun 	return ret;
81*4882a593Smuzhiyun }
82*4882a593Smuzhiyun 
tda18250_wait_for_irq(struct dvb_frontend * fe,int maxwait,int step,u8 irq)83*4882a593Smuzhiyun static int tda18250_wait_for_irq(struct dvb_frontend *fe,
84*4882a593Smuzhiyun 		int maxwait, int step, u8 irq)
85*4882a593Smuzhiyun {
86*4882a593Smuzhiyun 	struct i2c_client *client = fe->tuner_priv;
87*4882a593Smuzhiyun 	struct tda18250_dev *dev = i2c_get_clientdata(client);
88*4882a593Smuzhiyun 	int ret;
89*4882a593Smuzhiyun 	unsigned long timeout;
90*4882a593Smuzhiyun 	bool triggered;
91*4882a593Smuzhiyun 	unsigned int utmp;
92*4882a593Smuzhiyun 
93*4882a593Smuzhiyun 	triggered = false;
94*4882a593Smuzhiyun 	timeout = jiffies + msecs_to_jiffies(maxwait);
95*4882a593Smuzhiyun 	while (!time_after(jiffies, timeout)) {
96*4882a593Smuzhiyun 		// check for the IRQ
97*4882a593Smuzhiyun 		ret = regmap_read(dev->regmap, R08_IRQ1, &utmp);
98*4882a593Smuzhiyun 		if (ret)
99*4882a593Smuzhiyun 			goto err;
100*4882a593Smuzhiyun 		if ((utmp & irq) == irq) {
101*4882a593Smuzhiyun 			triggered = true;
102*4882a593Smuzhiyun 			break;
103*4882a593Smuzhiyun 		}
104*4882a593Smuzhiyun 		msleep(step);
105*4882a593Smuzhiyun 	}
106*4882a593Smuzhiyun 
107*4882a593Smuzhiyun 	dev_dbg(&client->dev, "waited IRQ (0x%02x) %d ms, triggered: %s", irq,
108*4882a593Smuzhiyun 			jiffies_to_msecs(jiffies) -
109*4882a593Smuzhiyun 			(jiffies_to_msecs(timeout) - maxwait),
110*4882a593Smuzhiyun 			triggered ? "true" : "false");
111*4882a593Smuzhiyun 
112*4882a593Smuzhiyun 	if (!triggered)
113*4882a593Smuzhiyun 		return -ETIMEDOUT;
114*4882a593Smuzhiyun 
115*4882a593Smuzhiyun 	return 0;
116*4882a593Smuzhiyun err:
117*4882a593Smuzhiyun 	return ret;
118*4882a593Smuzhiyun }
119*4882a593Smuzhiyun 
tda18250_init(struct dvb_frontend * fe)120*4882a593Smuzhiyun static int tda18250_init(struct dvb_frontend *fe)
121*4882a593Smuzhiyun {
122*4882a593Smuzhiyun 	struct i2c_client *client = fe->tuner_priv;
123*4882a593Smuzhiyun 	struct tda18250_dev *dev = i2c_get_clientdata(client);
124*4882a593Smuzhiyun 	int ret, i;
125*4882a593Smuzhiyun 
126*4882a593Smuzhiyun 	/* default values for various regs */
127*4882a593Smuzhiyun 	static const u8 init_regs[][2] = {
128*4882a593Smuzhiyun 		{ R0C_AGC11, 0xc7 },
129*4882a593Smuzhiyun 		{ R0D_AGC12, 0x5d },
130*4882a593Smuzhiyun 		{ R0E_AGC13, 0x40 },
131*4882a593Smuzhiyun 		{ R0F_AGC14, 0x0e },
132*4882a593Smuzhiyun 		{ R10_LT1, 0x47 },
133*4882a593Smuzhiyun 		{ R11_LT2, 0x4e },
134*4882a593Smuzhiyun 		{ R12_AGC21, 0x26 },
135*4882a593Smuzhiyun 		{ R13_AGC22, 0x60 },
136*4882a593Smuzhiyun 		{ R18_AGC32, 0x37 },
137*4882a593Smuzhiyun 		{ R19_AGC33, 0x09 },
138*4882a593Smuzhiyun 		{ R1A_AGCK, 0x00 },
139*4882a593Smuzhiyun 		{ R1E_WI_FI, 0x29 },
140*4882a593Smuzhiyun 		{ R1F_RF_BPF, 0x06 },
141*4882a593Smuzhiyun 		{ R20_IR_MIX, 0xc6 },
142*4882a593Smuzhiyun 		{ R21_IF_AGC, 0x00 },
143*4882a593Smuzhiyun 		{ R2C_PS1, 0x75 },
144*4882a593Smuzhiyun 		{ R2D_PS2, 0x06 },
145*4882a593Smuzhiyun 		{ R2E_PS3, 0x07 },
146*4882a593Smuzhiyun 		{ R30_RSSI2, 0x0e },
147*4882a593Smuzhiyun 		{ R31_IRQ_CTRL, 0x00 },
148*4882a593Smuzhiyun 		{ R39_SD5, 0x00 },
149*4882a593Smuzhiyun 		{ R3B_REGU, 0x55 },
150*4882a593Smuzhiyun 		{ R3C_RCCAL1, 0xa7 },
151*4882a593Smuzhiyun 		{ R3F_IRCAL2, 0x85 },
152*4882a593Smuzhiyun 		{ R40_IRCAL3, 0x87 },
153*4882a593Smuzhiyun 		{ R41_IRCAL4, 0xc0 },
154*4882a593Smuzhiyun 		{ R43_PD1, 0x40 },
155*4882a593Smuzhiyun 		{ R44_PD2, 0xc0 },
156*4882a593Smuzhiyun 		{ R46_CPUMP, 0x0c },
157*4882a593Smuzhiyun 		{ R47_LNAPOL, 0x64 },
158*4882a593Smuzhiyun 		{ R4B_XTALOSC1, 0x30 },
159*4882a593Smuzhiyun 		{ R59_AGC2_UP2, 0x05 },
160*4882a593Smuzhiyun 		{ R5B_AGC_AUTO, 0x07 },
161*4882a593Smuzhiyun 		{ R5C_AGC_DEBUG, 0x00 },
162*4882a593Smuzhiyun 	};
163*4882a593Smuzhiyun 
164*4882a593Smuzhiyun 	/* crystal related regs depend on frequency */
165*4882a593Smuzhiyun 	static const u8 xtal_regs[][5] = {
166*4882a593Smuzhiyun 					/* reg:   4d    4e    4f    50    51 */
167*4882a593Smuzhiyun 		[TDA18250_XTAL_FREQ_16MHZ]  = { 0x3e, 0x80, 0x50, 0x00, 0x20 },
168*4882a593Smuzhiyun 		[TDA18250_XTAL_FREQ_24MHZ]  = { 0x5d, 0xc0, 0xec, 0x00, 0x18 },
169*4882a593Smuzhiyun 		[TDA18250_XTAL_FREQ_25MHZ]  = { 0x61, 0xa8, 0xec, 0x80, 0x19 },
170*4882a593Smuzhiyun 		[TDA18250_XTAL_FREQ_27MHZ]  = { 0x69, 0x78, 0x8d, 0x80, 0x1b },
171*4882a593Smuzhiyun 		[TDA18250_XTAL_FREQ_30MHZ]  = { 0x75, 0x30, 0x8f, 0x00, 0x1e },
172*4882a593Smuzhiyun 	};
173*4882a593Smuzhiyun 
174*4882a593Smuzhiyun 	dev_dbg(&client->dev, "\n");
175*4882a593Smuzhiyun 
176*4882a593Smuzhiyun 	ret = tda18250_power_control(fe, TDA18250_POWER_NORMAL);
177*4882a593Smuzhiyun 	if (ret)
178*4882a593Smuzhiyun 		goto err;
179*4882a593Smuzhiyun 
180*4882a593Smuzhiyun 	msleep(20);
181*4882a593Smuzhiyun 
182*4882a593Smuzhiyun 	if (dev->warm)
183*4882a593Smuzhiyun 		goto warm;
184*4882a593Smuzhiyun 
185*4882a593Smuzhiyun 	/* set initial register values */
186*4882a593Smuzhiyun 	for (i = 0; i < ARRAY_SIZE(init_regs); i++) {
187*4882a593Smuzhiyun 		ret = regmap_write(dev->regmap, init_regs[i][0],
188*4882a593Smuzhiyun 				init_regs[i][1]);
189*4882a593Smuzhiyun 		if (ret)
190*4882a593Smuzhiyun 			goto err;
191*4882a593Smuzhiyun 	}
192*4882a593Smuzhiyun 
193*4882a593Smuzhiyun 	/* set xtal related regs */
194*4882a593Smuzhiyun 	ret = regmap_bulk_write(dev->regmap, R4D_XTALFLX1,
195*4882a593Smuzhiyun 			xtal_regs[dev->xtal_freq], 5);
196*4882a593Smuzhiyun 	if (ret)
197*4882a593Smuzhiyun 		goto err;
198*4882a593Smuzhiyun 
199*4882a593Smuzhiyun 	ret = regmap_write_bits(dev->regmap, R10_LT1, 0x80,
200*4882a593Smuzhiyun 			dev->loopthrough ? 0x00 : 0x80);
201*4882a593Smuzhiyun 	if (ret)
202*4882a593Smuzhiyun 		goto err;
203*4882a593Smuzhiyun 
204*4882a593Smuzhiyun 	/* clear IRQ */
205*4882a593Smuzhiyun 	ret = regmap_write(dev->regmap, R0A_IRQ3, TDA18250_IRQ_HW_INIT);
206*4882a593Smuzhiyun 	if (ret)
207*4882a593Smuzhiyun 		goto err;
208*4882a593Smuzhiyun 
209*4882a593Smuzhiyun 	/* start HW init */
210*4882a593Smuzhiyun 	ret = regmap_write(dev->regmap, R2A_MSM1, 0x70);
211*4882a593Smuzhiyun 	if (ret)
212*4882a593Smuzhiyun 		goto err;
213*4882a593Smuzhiyun 
214*4882a593Smuzhiyun 	ret = regmap_write(dev->regmap, R2B_MSM2, 0x01);
215*4882a593Smuzhiyun 	if (ret)
216*4882a593Smuzhiyun 		goto err;
217*4882a593Smuzhiyun 
218*4882a593Smuzhiyun 	ret = tda18250_wait_for_irq(fe, 500, 10, TDA18250_IRQ_HW_INIT);
219*4882a593Smuzhiyun 	if (ret)
220*4882a593Smuzhiyun 		goto err;
221*4882a593Smuzhiyun 
222*4882a593Smuzhiyun 	/* tuner calibration */
223*4882a593Smuzhiyun 	ret = regmap_write(dev->regmap, R2A_MSM1, 0x02);
224*4882a593Smuzhiyun 	if (ret)
225*4882a593Smuzhiyun 		goto err;
226*4882a593Smuzhiyun 
227*4882a593Smuzhiyun 	ret = regmap_write(dev->regmap, R2B_MSM2, 0x01);
228*4882a593Smuzhiyun 	if (ret)
229*4882a593Smuzhiyun 		goto err;
230*4882a593Smuzhiyun 
231*4882a593Smuzhiyun 	ret = tda18250_wait_for_irq(fe, 500, 10, TDA18250_IRQ_CAL);
232*4882a593Smuzhiyun 	if (ret)
233*4882a593Smuzhiyun 		goto err;
234*4882a593Smuzhiyun 
235*4882a593Smuzhiyun 	dev->warm = true;
236*4882a593Smuzhiyun 
237*4882a593Smuzhiyun warm:
238*4882a593Smuzhiyun 	/* power up LNA */
239*4882a593Smuzhiyun 	ret = regmap_write_bits(dev->regmap, R0C_AGC11, 0x80, 0x00);
240*4882a593Smuzhiyun 	if (ret)
241*4882a593Smuzhiyun 		goto err;
242*4882a593Smuzhiyun 
243*4882a593Smuzhiyun 	return 0;
244*4882a593Smuzhiyun err:
245*4882a593Smuzhiyun 	dev_dbg(&client->dev, "failed=%d", ret);
246*4882a593Smuzhiyun 	return ret;
247*4882a593Smuzhiyun }
248*4882a593Smuzhiyun 
tda18250_set_agc(struct dvb_frontend * fe)249*4882a593Smuzhiyun static int tda18250_set_agc(struct dvb_frontend *fe)
250*4882a593Smuzhiyun {
251*4882a593Smuzhiyun 	struct i2c_client *client = fe->tuner_priv;
252*4882a593Smuzhiyun 	struct tda18250_dev *dev = i2c_get_clientdata(client);
253*4882a593Smuzhiyun 	struct dtv_frontend_properties *c = &fe->dtv_property_cache;
254*4882a593Smuzhiyun 	int ret;
255*4882a593Smuzhiyun 	u8 utmp, utmp2;
256*4882a593Smuzhiyun 
257*4882a593Smuzhiyun 	dev_dbg(&client->dev, "\n");
258*4882a593Smuzhiyun 
259*4882a593Smuzhiyun 	ret = regmap_write_bits(dev->regmap, R1F_RF_BPF, 0x87, 0x06);
260*4882a593Smuzhiyun 	if (ret)
261*4882a593Smuzhiyun 		goto err;
262*4882a593Smuzhiyun 
263*4882a593Smuzhiyun 	utmp = ((c->frequency < 100000000) &&
264*4882a593Smuzhiyun 			((c->delivery_system == SYS_DVBC_ANNEX_A) ||
265*4882a593Smuzhiyun 			(c->delivery_system == SYS_DVBC_ANNEX_C)) &&
266*4882a593Smuzhiyun 			(c->bandwidth_hz == 6000000)) ? 0x80 : 0x00;
267*4882a593Smuzhiyun 	ret = regmap_write(dev->regmap, R5A_H3H5, utmp);
268*4882a593Smuzhiyun 	if (ret)
269*4882a593Smuzhiyun 		goto err;
270*4882a593Smuzhiyun 
271*4882a593Smuzhiyun 	/* AGC1 */
272*4882a593Smuzhiyun 	switch (c->delivery_system) {
273*4882a593Smuzhiyun 	case SYS_ATSC:
274*4882a593Smuzhiyun 	case SYS_DVBT:
275*4882a593Smuzhiyun 	case SYS_DVBT2:
276*4882a593Smuzhiyun 		utmp = 4;
277*4882a593Smuzhiyun 		break;
278*4882a593Smuzhiyun 	default: /* DVB-C/QAM */
279*4882a593Smuzhiyun 		switch (c->bandwidth_hz) {
280*4882a593Smuzhiyun 		case 6000000:
281*4882a593Smuzhiyun 			utmp = (c->frequency < 800000000) ? 6 : 4;
282*4882a593Smuzhiyun 			break;
283*4882a593Smuzhiyun 		default: /* 7.935 and 8 MHz */
284*4882a593Smuzhiyun 			utmp = (c->frequency < 100000000) ? 2 : 3;
285*4882a593Smuzhiyun 			break;
286*4882a593Smuzhiyun 		}
287*4882a593Smuzhiyun 		break;
288*4882a593Smuzhiyun 	}
289*4882a593Smuzhiyun 
290*4882a593Smuzhiyun 	ret = regmap_write_bits(dev->regmap, R0C_AGC11, 0x07, utmp);
291*4882a593Smuzhiyun 	if (ret)
292*4882a593Smuzhiyun 		goto err;
293*4882a593Smuzhiyun 
294*4882a593Smuzhiyun 	/* AGC2 */
295*4882a593Smuzhiyun 	switch (c->delivery_system) {
296*4882a593Smuzhiyun 	case SYS_ATSC:
297*4882a593Smuzhiyun 	case SYS_DVBT:
298*4882a593Smuzhiyun 	case SYS_DVBT2:
299*4882a593Smuzhiyun 		utmp = (c->frequency < 320000000) ? 20 : 16;
300*4882a593Smuzhiyun 		utmp2 = (c->frequency < 320000000) ? 22 : 18;
301*4882a593Smuzhiyun 		break;
302*4882a593Smuzhiyun 	default: /* DVB-C/QAM */
303*4882a593Smuzhiyun 		switch (c->bandwidth_hz) {
304*4882a593Smuzhiyun 		case 6000000:
305*4882a593Smuzhiyun 			if (c->frequency < 600000000) {
306*4882a593Smuzhiyun 				utmp = 18;
307*4882a593Smuzhiyun 				utmp2 = 22;
308*4882a593Smuzhiyun 			} else if (c->frequency < 800000000) {
309*4882a593Smuzhiyun 				utmp = 16;
310*4882a593Smuzhiyun 				utmp2 = 20;
311*4882a593Smuzhiyun 			} else {
312*4882a593Smuzhiyun 				utmp = 14;
313*4882a593Smuzhiyun 				utmp2 = 16;
314*4882a593Smuzhiyun 			}
315*4882a593Smuzhiyun 			break;
316*4882a593Smuzhiyun 		default: /* 7.935 and 8 MHz */
317*4882a593Smuzhiyun 			utmp = (c->frequency < 320000000) ? 16 : 18;
318*4882a593Smuzhiyun 			utmp2 = (c->frequency < 320000000) ? 18 : 20;
319*4882a593Smuzhiyun 			break;
320*4882a593Smuzhiyun 		}
321*4882a593Smuzhiyun 		break;
322*4882a593Smuzhiyun 	}
323*4882a593Smuzhiyun 	ret = regmap_write_bits(dev->regmap, R58_AGC2_UP1, 0x1f, utmp2+8);
324*4882a593Smuzhiyun 	if (ret)
325*4882a593Smuzhiyun 		goto err;
326*4882a593Smuzhiyun 	ret = regmap_write_bits(dev->regmap, R13_AGC22, 0x1f, utmp);
327*4882a593Smuzhiyun 	if (ret)
328*4882a593Smuzhiyun 		goto err;
329*4882a593Smuzhiyun 	ret = regmap_write_bits(dev->regmap, R14_AGC23, 0x1f, utmp2);
330*4882a593Smuzhiyun 	if (ret)
331*4882a593Smuzhiyun 		goto err;
332*4882a593Smuzhiyun 
333*4882a593Smuzhiyun 	switch (c->delivery_system) {
334*4882a593Smuzhiyun 	case SYS_ATSC:
335*4882a593Smuzhiyun 	case SYS_DVBT:
336*4882a593Smuzhiyun 	case SYS_DVBT2:
337*4882a593Smuzhiyun 		utmp = 98;
338*4882a593Smuzhiyun 		break;
339*4882a593Smuzhiyun 	default: /* DVB-C/QAM */
340*4882a593Smuzhiyun 		utmp = 90;
341*4882a593Smuzhiyun 		break;
342*4882a593Smuzhiyun 	}
343*4882a593Smuzhiyun 	ret = regmap_write_bits(dev->regmap, R16_AGC25, 0xf8, utmp);
344*4882a593Smuzhiyun 	if (ret)
345*4882a593Smuzhiyun 		goto err;
346*4882a593Smuzhiyun 
347*4882a593Smuzhiyun 	ret = regmap_write_bits(dev->regmap, R12_AGC21, 0x60,
348*4882a593Smuzhiyun 			(c->frequency > 800000000) ? 0x40 : 0x20);
349*4882a593Smuzhiyun 	if (ret)
350*4882a593Smuzhiyun 		goto err;
351*4882a593Smuzhiyun 
352*4882a593Smuzhiyun 	/* AGC3 */
353*4882a593Smuzhiyun 	switch (c->delivery_system) {
354*4882a593Smuzhiyun 	case SYS_ATSC:
355*4882a593Smuzhiyun 	case SYS_DVBT:
356*4882a593Smuzhiyun 	case SYS_DVBT2:
357*4882a593Smuzhiyun 		utmp = (c->frequency < 320000000) ? 5 : 7;
358*4882a593Smuzhiyun 		utmp2 = (c->frequency < 320000000) ? 10 : 12;
359*4882a593Smuzhiyun 		break;
360*4882a593Smuzhiyun 	default: /* DVB-C/QAM */
361*4882a593Smuzhiyun 		utmp = 7;
362*4882a593Smuzhiyun 		utmp2 = 12;
363*4882a593Smuzhiyun 		break;
364*4882a593Smuzhiyun 	}
365*4882a593Smuzhiyun 	ret = regmap_write(dev->regmap, R17_AGC31, (utmp << 4) | utmp2);
366*4882a593Smuzhiyun 	if (ret)
367*4882a593Smuzhiyun 		goto err;
368*4882a593Smuzhiyun 
369*4882a593Smuzhiyun 	/* S2D */
370*4882a593Smuzhiyun 	switch (c->delivery_system) {
371*4882a593Smuzhiyun 	case SYS_ATSC:
372*4882a593Smuzhiyun 	case SYS_DVBT:
373*4882a593Smuzhiyun 	case SYS_DVBT2:
374*4882a593Smuzhiyun 		if (c->bandwidth_hz == 8000000)
375*4882a593Smuzhiyun 			utmp = 0x04;
376*4882a593Smuzhiyun 		else
377*4882a593Smuzhiyun 			utmp = (c->frequency < 320000000) ? 0x04 : 0x02;
378*4882a593Smuzhiyun 		break;
379*4882a593Smuzhiyun 	default: /* DVB-C/QAM */
380*4882a593Smuzhiyun 		if (c->bandwidth_hz == 6000000)
381*4882a593Smuzhiyun 			utmp = ((c->frequency > 172544000) &&
382*4882a593Smuzhiyun 				(c->frequency < 320000000)) ? 0x04 : 0x02;
383*4882a593Smuzhiyun 		else /* 7.935 and 8 MHz */
384*4882a593Smuzhiyun 			utmp = ((c->frequency > 320000000) &&
385*4882a593Smuzhiyun 				(c->frequency < 600000000)) ? 0x02 : 0x04;
386*4882a593Smuzhiyun 		break;
387*4882a593Smuzhiyun 	}
388*4882a593Smuzhiyun 	ret = regmap_write_bits(dev->regmap, R20_IR_MIX, 0x06, utmp);
389*4882a593Smuzhiyun 	if (ret)
390*4882a593Smuzhiyun 		goto err;
391*4882a593Smuzhiyun 
392*4882a593Smuzhiyun 	switch (c->delivery_system) {
393*4882a593Smuzhiyun 	case SYS_ATSC:
394*4882a593Smuzhiyun 	case SYS_DVBT:
395*4882a593Smuzhiyun 	case SYS_DVBT2:
396*4882a593Smuzhiyun 		utmp = 0;
397*4882a593Smuzhiyun 		break;
398*4882a593Smuzhiyun 	default: /* DVB-C/QAM */
399*4882a593Smuzhiyun 		utmp = (c->frequency < 600000000) ? 0 : 3;
400*4882a593Smuzhiyun 		break;
401*4882a593Smuzhiyun 	}
402*4882a593Smuzhiyun 	ret = regmap_write_bits(dev->regmap, R16_AGC25, 0x03, utmp);
403*4882a593Smuzhiyun 	if (ret)
404*4882a593Smuzhiyun 		goto err;
405*4882a593Smuzhiyun 
406*4882a593Smuzhiyun 	utmp = 0x09;
407*4882a593Smuzhiyun 	switch (c->delivery_system) {
408*4882a593Smuzhiyun 	case SYS_ATSC:
409*4882a593Smuzhiyun 	case SYS_DVBT:
410*4882a593Smuzhiyun 	case SYS_DVBT2:
411*4882a593Smuzhiyun 		if (c->bandwidth_hz == 8000000)
412*4882a593Smuzhiyun 			utmp = 0x0c;
413*4882a593Smuzhiyun 		break;
414*4882a593Smuzhiyun 	default: /* DVB-C/QAM */
415*4882a593Smuzhiyun 		utmp = 0x0c;
416*4882a593Smuzhiyun 		break;
417*4882a593Smuzhiyun 	}
418*4882a593Smuzhiyun 	ret = regmap_write_bits(dev->regmap, R0F_AGC14, 0x3f, utmp);
419*4882a593Smuzhiyun 	if (ret)
420*4882a593Smuzhiyun 		goto err;
421*4882a593Smuzhiyun 
422*4882a593Smuzhiyun 	return 0;
423*4882a593Smuzhiyun err:
424*4882a593Smuzhiyun 	dev_dbg(&client->dev, "failed=%d", ret);
425*4882a593Smuzhiyun 	return ret;
426*4882a593Smuzhiyun }
427*4882a593Smuzhiyun 
tda18250_pll_calc(struct dvb_frontend * fe,u8 * rdiv,u8 * ndiv,u8 * icp)428*4882a593Smuzhiyun static int tda18250_pll_calc(struct dvb_frontend *fe, u8 *rdiv,
429*4882a593Smuzhiyun 		u8 *ndiv, u8 *icp)
430*4882a593Smuzhiyun {
431*4882a593Smuzhiyun 	struct i2c_client *client = fe->tuner_priv;
432*4882a593Smuzhiyun 	struct tda18250_dev *dev = i2c_get_clientdata(client);
433*4882a593Smuzhiyun 	struct dtv_frontend_properties *c = &fe->dtv_property_cache;
434*4882a593Smuzhiyun 	int ret;
435*4882a593Smuzhiyun 	unsigned int uval, exp, lopd, scale;
436*4882a593Smuzhiyun 	unsigned long fvco;
437*4882a593Smuzhiyun 
438*4882a593Smuzhiyun 	ret = regmap_read(dev->regmap, R34_MD1, &uval);
439*4882a593Smuzhiyun 	if (ret)
440*4882a593Smuzhiyun 		goto err;
441*4882a593Smuzhiyun 
442*4882a593Smuzhiyun 	exp = (uval & 0x70) >> 4;
443*4882a593Smuzhiyun 	if (exp > 5)
444*4882a593Smuzhiyun 		exp = 0;
445*4882a593Smuzhiyun 	lopd = 1 << (exp - 1);
446*4882a593Smuzhiyun 	scale = uval & 0x0f;
447*4882a593Smuzhiyun 	fvco = lopd * scale * ((c->frequency / 1000) + dev->if_frequency);
448*4882a593Smuzhiyun 
449*4882a593Smuzhiyun 	switch (dev->xtal_freq) {
450*4882a593Smuzhiyun 	case TDA18250_XTAL_FREQ_16MHZ:
451*4882a593Smuzhiyun 		*rdiv = 1;
452*4882a593Smuzhiyun 		*ndiv = 0;
453*4882a593Smuzhiyun 		*icp = (fvco < 6622000) ? 0x05 : 0x02;
454*4882a593Smuzhiyun 	break;
455*4882a593Smuzhiyun 	case TDA18250_XTAL_FREQ_24MHZ:
456*4882a593Smuzhiyun 	case TDA18250_XTAL_FREQ_25MHZ:
457*4882a593Smuzhiyun 		*rdiv = 3;
458*4882a593Smuzhiyun 		*ndiv = 1;
459*4882a593Smuzhiyun 		*icp = (fvco < 6622000) ? 0x05 : 0x02;
460*4882a593Smuzhiyun 	break;
461*4882a593Smuzhiyun 	case TDA18250_XTAL_FREQ_27MHZ:
462*4882a593Smuzhiyun 		if (fvco < 6643000) {
463*4882a593Smuzhiyun 			*rdiv = 2;
464*4882a593Smuzhiyun 			*ndiv = 0;
465*4882a593Smuzhiyun 			*icp = 0x05;
466*4882a593Smuzhiyun 		} else if (fvco < 6811000) {
467*4882a593Smuzhiyun 			*rdiv = 2;
468*4882a593Smuzhiyun 			*ndiv = 0;
469*4882a593Smuzhiyun 			*icp = 0x06;
470*4882a593Smuzhiyun 		} else {
471*4882a593Smuzhiyun 			*rdiv = 3;
472*4882a593Smuzhiyun 			*ndiv = 1;
473*4882a593Smuzhiyun 			*icp = 0x02;
474*4882a593Smuzhiyun 		}
475*4882a593Smuzhiyun 	break;
476*4882a593Smuzhiyun 	case TDA18250_XTAL_FREQ_30MHZ:
477*4882a593Smuzhiyun 		*rdiv = 2;
478*4882a593Smuzhiyun 		*ndiv = 0;
479*4882a593Smuzhiyun 		*icp = (fvco < 6811000) ? 0x05 : 0x02;
480*4882a593Smuzhiyun 	break;
481*4882a593Smuzhiyun 	default:
482*4882a593Smuzhiyun 		return -EINVAL;
483*4882a593Smuzhiyun 	}
484*4882a593Smuzhiyun 
485*4882a593Smuzhiyun 	dev_dbg(&client->dev,
486*4882a593Smuzhiyun 			"lopd=%d scale=%u fvco=%lu, rdiv=%d ndiv=%d icp=%d",
487*4882a593Smuzhiyun 			lopd, scale, fvco, *rdiv, *ndiv, *icp);
488*4882a593Smuzhiyun 	return 0;
489*4882a593Smuzhiyun err:
490*4882a593Smuzhiyun 	return ret;
491*4882a593Smuzhiyun }
492*4882a593Smuzhiyun 
tda18250_set_params(struct dvb_frontend * fe)493*4882a593Smuzhiyun static int tda18250_set_params(struct dvb_frontend *fe)
494*4882a593Smuzhiyun {
495*4882a593Smuzhiyun 	struct i2c_client *client = fe->tuner_priv;
496*4882a593Smuzhiyun 	struct tda18250_dev *dev = i2c_get_clientdata(client);
497*4882a593Smuzhiyun 	struct dtv_frontend_properties *c = &fe->dtv_property_cache;
498*4882a593Smuzhiyun 	u32 if_khz;
499*4882a593Smuzhiyun 	int ret;
500*4882a593Smuzhiyun 	unsigned int i, j;
501*4882a593Smuzhiyun 	u8 utmp;
502*4882a593Smuzhiyun 	u8 buf[3];
503*4882a593Smuzhiyun 
504*4882a593Smuzhiyun 	#define REG      0
505*4882a593Smuzhiyun 	#define MASK     1
506*4882a593Smuzhiyun 	#define DVBT_6   2
507*4882a593Smuzhiyun 	#define DVBT_7   3
508*4882a593Smuzhiyun 	#define DVBT_8   4
509*4882a593Smuzhiyun 	#define DVBC_6   5
510*4882a593Smuzhiyun 	#define DVBC_8   6
511*4882a593Smuzhiyun 	#define ATSC     7
512*4882a593Smuzhiyun 
513*4882a593Smuzhiyun 	static const u8 delsys_params[][16] = {
514*4882a593Smuzhiyun 		[REG]    = { 0x22, 0x23, 0x24, 0x21, 0x0d, 0x0c, 0x0f, 0x14,
515*4882a593Smuzhiyun 			     0x0e, 0x12, 0x58, 0x59, 0x1a, 0x19, 0x1e, 0x30 },
516*4882a593Smuzhiyun 		[MASK]   = { 0x77, 0xff, 0xff, 0x87, 0xf0, 0x78, 0x07, 0xe0,
517*4882a593Smuzhiyun 			     0x60, 0x0f, 0x60, 0x0f, 0x33, 0x30, 0x80, 0x06 },
518*4882a593Smuzhiyun 		[DVBT_6] = { 0x51, 0x03, 0x83, 0x82, 0x40, 0x48, 0x01, 0xe0,
519*4882a593Smuzhiyun 			     0x60, 0x0f, 0x60, 0x05, 0x03, 0x10, 0x00, 0x04 },
520*4882a593Smuzhiyun 		[DVBT_7] = { 0x52, 0x03, 0x85, 0x82, 0x40, 0x48, 0x01, 0xe0,
521*4882a593Smuzhiyun 			     0x60, 0x0f, 0x60, 0x05, 0x03, 0x10, 0x00, 0x04 },
522*4882a593Smuzhiyun 		[DVBT_8] = { 0x53, 0x03, 0x87, 0x82, 0x40, 0x48, 0x06, 0xe0,
523*4882a593Smuzhiyun 			     0x60, 0x07, 0x60, 0x05, 0x03, 0x10, 0x00, 0x04 },
524*4882a593Smuzhiyun 		[DVBC_6] = { 0x32, 0x05, 0x86, 0x82, 0x50, 0x00, 0x06, 0x60,
525*4882a593Smuzhiyun 			     0x40, 0x0e, 0x60, 0x05, 0x33, 0x10, 0x00, 0x04 },
526*4882a593Smuzhiyun 		[DVBC_8] = { 0x53, 0x03, 0x88, 0x82, 0x50, 0x00, 0x06, 0x60,
527*4882a593Smuzhiyun 			     0x40, 0x0e, 0x60, 0x05, 0x33, 0x10, 0x00, 0x04 },
528*4882a593Smuzhiyun 		[ATSC]   = { 0x51, 0x03, 0x83, 0x82, 0x40, 0x48, 0x01, 0xe0,
529*4882a593Smuzhiyun 			     0x40, 0x0e, 0x60, 0x05, 0x03, 0x00, 0x80, 0x04 },
530*4882a593Smuzhiyun 	};
531*4882a593Smuzhiyun 
532*4882a593Smuzhiyun 	dev_dbg(&client->dev,
533*4882a593Smuzhiyun 			"delivery_system=%d frequency=%u bandwidth_hz=%u",
534*4882a593Smuzhiyun 			c->delivery_system, c->frequency, c->bandwidth_hz);
535*4882a593Smuzhiyun 
536*4882a593Smuzhiyun 
537*4882a593Smuzhiyun 	switch (c->delivery_system) {
538*4882a593Smuzhiyun 	case SYS_ATSC:
539*4882a593Smuzhiyun 		j = ATSC;
540*4882a593Smuzhiyun 		if_khz = dev->if_atsc;
541*4882a593Smuzhiyun 		break;
542*4882a593Smuzhiyun 	case SYS_DVBT:
543*4882a593Smuzhiyun 	case SYS_DVBT2:
544*4882a593Smuzhiyun 		if (c->bandwidth_hz == 0) {
545*4882a593Smuzhiyun 			ret = -EINVAL;
546*4882a593Smuzhiyun 			goto err;
547*4882a593Smuzhiyun 		} else if (c->bandwidth_hz <= 6000000) {
548*4882a593Smuzhiyun 			j = DVBT_6;
549*4882a593Smuzhiyun 			if_khz = dev->if_dvbt_6;
550*4882a593Smuzhiyun 		} else if (c->bandwidth_hz <= 7000000) {
551*4882a593Smuzhiyun 			j = DVBT_7;
552*4882a593Smuzhiyun 			if_khz = dev->if_dvbt_7;
553*4882a593Smuzhiyun 		} else if (c->bandwidth_hz <= 8000000) {
554*4882a593Smuzhiyun 			j = DVBT_8;
555*4882a593Smuzhiyun 			if_khz = dev->if_dvbt_8;
556*4882a593Smuzhiyun 		} else {
557*4882a593Smuzhiyun 			ret = -EINVAL;
558*4882a593Smuzhiyun 			goto err;
559*4882a593Smuzhiyun 		}
560*4882a593Smuzhiyun 		break;
561*4882a593Smuzhiyun 	case SYS_DVBC_ANNEX_A:
562*4882a593Smuzhiyun 	case SYS_DVBC_ANNEX_C:
563*4882a593Smuzhiyun 		if (c->bandwidth_hz == 0) {
564*4882a593Smuzhiyun 			ret = -EINVAL;
565*4882a593Smuzhiyun 			goto err;
566*4882a593Smuzhiyun 		} else if (c->bandwidth_hz <= 6000000) {
567*4882a593Smuzhiyun 			j = DVBC_6;
568*4882a593Smuzhiyun 			if_khz = dev->if_dvbc_6;
569*4882a593Smuzhiyun 		} else if (c->bandwidth_hz <= 8000000) {
570*4882a593Smuzhiyun 			j = DVBC_8;
571*4882a593Smuzhiyun 			if_khz = dev->if_dvbc_8;
572*4882a593Smuzhiyun 		} else {
573*4882a593Smuzhiyun 			ret = -EINVAL;
574*4882a593Smuzhiyun 			goto err;
575*4882a593Smuzhiyun 		}
576*4882a593Smuzhiyun 		break;
577*4882a593Smuzhiyun 	default:
578*4882a593Smuzhiyun 		ret = -EINVAL;
579*4882a593Smuzhiyun 		dev_err(&client->dev, "unsupported delivery system=%d",
580*4882a593Smuzhiyun 				c->delivery_system);
581*4882a593Smuzhiyun 		goto err;
582*4882a593Smuzhiyun 	}
583*4882a593Smuzhiyun 
584*4882a593Smuzhiyun 	/* set delivery system dependent registers */
585*4882a593Smuzhiyun 	for (i = 0; i < 16; i++) {
586*4882a593Smuzhiyun 		ret = regmap_write_bits(dev->regmap, delsys_params[REG][i],
587*4882a593Smuzhiyun 			 delsys_params[MASK][i],  delsys_params[j][i]);
588*4882a593Smuzhiyun 		if (ret)
589*4882a593Smuzhiyun 			goto err;
590*4882a593Smuzhiyun 	}
591*4882a593Smuzhiyun 
592*4882a593Smuzhiyun 	/* set IF if needed */
593*4882a593Smuzhiyun 	if (dev->if_frequency != if_khz) {
594*4882a593Smuzhiyun 		utmp = DIV_ROUND_CLOSEST(if_khz, 50);
595*4882a593Smuzhiyun 		ret = regmap_write(dev->regmap, R26_IF, utmp);
596*4882a593Smuzhiyun 		if (ret)
597*4882a593Smuzhiyun 			goto err;
598*4882a593Smuzhiyun 		dev->if_frequency = if_khz;
599*4882a593Smuzhiyun 		dev_dbg(&client->dev, "set IF=%u kHz", if_khz);
600*4882a593Smuzhiyun 
601*4882a593Smuzhiyun 	}
602*4882a593Smuzhiyun 
603*4882a593Smuzhiyun 	ret = tda18250_set_agc(fe);
604*4882a593Smuzhiyun 	if (ret)
605*4882a593Smuzhiyun 		goto err;
606*4882a593Smuzhiyun 
607*4882a593Smuzhiyun 	ret = regmap_write_bits(dev->regmap, R1A_AGCK, 0x03, 0x01);
608*4882a593Smuzhiyun 	if (ret)
609*4882a593Smuzhiyun 		goto err;
610*4882a593Smuzhiyun 
611*4882a593Smuzhiyun 	ret = regmap_write_bits(dev->regmap, R14_AGC23, 0x40, 0x00);
612*4882a593Smuzhiyun 	if (ret)
613*4882a593Smuzhiyun 		goto err;
614*4882a593Smuzhiyun 
615*4882a593Smuzhiyun 	/* set frequency */
616*4882a593Smuzhiyun 	buf[0] = ((c->frequency / 1000) >> 16) & 0xff;
617*4882a593Smuzhiyun 	buf[1] = ((c->frequency / 1000) >>  8) & 0xff;
618*4882a593Smuzhiyun 	buf[2] = ((c->frequency / 1000) >>  0) & 0xff;
619*4882a593Smuzhiyun 	ret = regmap_bulk_write(dev->regmap, R27_RF1, buf, 3);
620*4882a593Smuzhiyun 	if (ret)
621*4882a593Smuzhiyun 		goto err;
622*4882a593Smuzhiyun 
623*4882a593Smuzhiyun 	ret = regmap_write(dev->regmap, R0A_IRQ3, TDA18250_IRQ_TUNE);
624*4882a593Smuzhiyun 	if (ret)
625*4882a593Smuzhiyun 		goto err;
626*4882a593Smuzhiyun 
627*4882a593Smuzhiyun 	/* initial tune */
628*4882a593Smuzhiyun 	ret = regmap_write(dev->regmap, R2A_MSM1, 0x01);
629*4882a593Smuzhiyun 	if (ret)
630*4882a593Smuzhiyun 		goto err;
631*4882a593Smuzhiyun 
632*4882a593Smuzhiyun 	ret = regmap_write(dev->regmap, R2B_MSM2, 0x01);
633*4882a593Smuzhiyun 	if (ret)
634*4882a593Smuzhiyun 		goto err;
635*4882a593Smuzhiyun 
636*4882a593Smuzhiyun 	ret = tda18250_wait_for_irq(fe, 500, 10, TDA18250_IRQ_TUNE);
637*4882a593Smuzhiyun 	if (ret)
638*4882a593Smuzhiyun 		goto err;
639*4882a593Smuzhiyun 
640*4882a593Smuzhiyun 	/* calc ndiv and rdiv */
641*4882a593Smuzhiyun 	ret = tda18250_pll_calc(fe, &buf[0], &buf[1], &buf[2]);
642*4882a593Smuzhiyun 	if (ret)
643*4882a593Smuzhiyun 		goto err;
644*4882a593Smuzhiyun 
645*4882a593Smuzhiyun 	ret = regmap_write_bits(dev->regmap, R4F_XTALFLX3, 0xe0,
646*4882a593Smuzhiyun 			(buf[0] << 6) | (buf[1] << 5));
647*4882a593Smuzhiyun 	if (ret)
648*4882a593Smuzhiyun 		goto err;
649*4882a593Smuzhiyun 
650*4882a593Smuzhiyun 	/* clear IRQ */
651*4882a593Smuzhiyun 	ret = regmap_write(dev->regmap, R0A_IRQ3, TDA18250_IRQ_TUNE);
652*4882a593Smuzhiyun 	if (ret)
653*4882a593Smuzhiyun 		goto err;
654*4882a593Smuzhiyun 
655*4882a593Smuzhiyun 	ret = regmap_write_bits(dev->regmap, R46_CPUMP, 0x07, 0x00);
656*4882a593Smuzhiyun 	if (ret)
657*4882a593Smuzhiyun 		goto err;
658*4882a593Smuzhiyun 
659*4882a593Smuzhiyun 	ret = regmap_write_bits(dev->regmap, R39_SD5, 0x03, 0x00);
660*4882a593Smuzhiyun 	if (ret)
661*4882a593Smuzhiyun 		goto err;
662*4882a593Smuzhiyun 
663*4882a593Smuzhiyun 	/* tune again */
664*4882a593Smuzhiyun 	ret = regmap_write(dev->regmap, R2A_MSM1, 0x01); /* tune */
665*4882a593Smuzhiyun 	if (ret)
666*4882a593Smuzhiyun 		goto err;
667*4882a593Smuzhiyun 
668*4882a593Smuzhiyun 	ret = regmap_write(dev->regmap, R2B_MSM2, 0x01); /* go */
669*4882a593Smuzhiyun 	if (ret)
670*4882a593Smuzhiyun 		goto err;
671*4882a593Smuzhiyun 
672*4882a593Smuzhiyun 	ret = tda18250_wait_for_irq(fe, 500, 10, TDA18250_IRQ_TUNE);
673*4882a593Smuzhiyun 	if (ret)
674*4882a593Smuzhiyun 		goto err;
675*4882a593Smuzhiyun 
676*4882a593Smuzhiyun 	/* pll locking */
677*4882a593Smuzhiyun 	msleep(20);
678*4882a593Smuzhiyun 
679*4882a593Smuzhiyun 	ret = regmap_write_bits(dev->regmap, R2B_MSM2, 0x04, 0x04);
680*4882a593Smuzhiyun 	if (ret)
681*4882a593Smuzhiyun 		goto err;
682*4882a593Smuzhiyun 
683*4882a593Smuzhiyun 	msleep(20);
684*4882a593Smuzhiyun 
685*4882a593Smuzhiyun 	/* restore AGCK */
686*4882a593Smuzhiyun 	ret = regmap_write_bits(dev->regmap, R1A_AGCK, 0x03, 0x03);
687*4882a593Smuzhiyun 	if (ret)
688*4882a593Smuzhiyun 		goto err;
689*4882a593Smuzhiyun 
690*4882a593Smuzhiyun 	ret = regmap_write_bits(dev->regmap, R14_AGC23, 0x40, 0x40);
691*4882a593Smuzhiyun 	if (ret)
692*4882a593Smuzhiyun 		goto err;
693*4882a593Smuzhiyun 
694*4882a593Smuzhiyun 	/* charge pump */
695*4882a593Smuzhiyun 	ret = regmap_write_bits(dev->regmap, R46_CPUMP, 0x07, buf[2]);
696*4882a593Smuzhiyun 
697*4882a593Smuzhiyun 	return 0;
698*4882a593Smuzhiyun err:
699*4882a593Smuzhiyun 	return ret;
700*4882a593Smuzhiyun }
701*4882a593Smuzhiyun 
tda18250_get_if_frequency(struct dvb_frontend * fe,u32 * frequency)702*4882a593Smuzhiyun static int tda18250_get_if_frequency(struct dvb_frontend *fe, u32 *frequency)
703*4882a593Smuzhiyun {
704*4882a593Smuzhiyun 	struct i2c_client *client = fe->tuner_priv;
705*4882a593Smuzhiyun 	struct tda18250_dev *dev = i2c_get_clientdata(client);
706*4882a593Smuzhiyun 
707*4882a593Smuzhiyun 	*frequency = dev->if_frequency * 1000;
708*4882a593Smuzhiyun 	return 0;
709*4882a593Smuzhiyun }
710*4882a593Smuzhiyun 
tda18250_sleep(struct dvb_frontend * fe)711*4882a593Smuzhiyun static int tda18250_sleep(struct dvb_frontend *fe)
712*4882a593Smuzhiyun {
713*4882a593Smuzhiyun 	struct i2c_client *client = fe->tuner_priv;
714*4882a593Smuzhiyun 	struct tda18250_dev *dev = i2c_get_clientdata(client);
715*4882a593Smuzhiyun 	int ret;
716*4882a593Smuzhiyun 
717*4882a593Smuzhiyun 	dev_dbg(&client->dev, "\n");
718*4882a593Smuzhiyun 
719*4882a593Smuzhiyun 	/* power down LNA */
720*4882a593Smuzhiyun 	ret = regmap_write_bits(dev->regmap, R0C_AGC11, 0x80, 0x00);
721*4882a593Smuzhiyun 	if (ret)
722*4882a593Smuzhiyun 		return ret;
723*4882a593Smuzhiyun 
724*4882a593Smuzhiyun 	/* set if freq to 0 in order to make sure it's set after wake up */
725*4882a593Smuzhiyun 	dev->if_frequency = 0;
726*4882a593Smuzhiyun 
727*4882a593Smuzhiyun 	ret = tda18250_power_control(fe, TDA18250_POWER_STANDBY);
728*4882a593Smuzhiyun 	return ret;
729*4882a593Smuzhiyun }
730*4882a593Smuzhiyun 
731*4882a593Smuzhiyun static const struct dvb_tuner_ops tda18250_ops = {
732*4882a593Smuzhiyun 	.info = {
733*4882a593Smuzhiyun 		.name              = "NXP TDA18250",
734*4882a593Smuzhiyun 		.frequency_min_hz  =  42 * MHz,
735*4882a593Smuzhiyun 		.frequency_max_hz  = 870 * MHz,
736*4882a593Smuzhiyun 	},
737*4882a593Smuzhiyun 
738*4882a593Smuzhiyun 	.init = tda18250_init,
739*4882a593Smuzhiyun 	.set_params = tda18250_set_params,
740*4882a593Smuzhiyun 	.get_if_frequency = tda18250_get_if_frequency,
741*4882a593Smuzhiyun 	.sleep = tda18250_sleep,
742*4882a593Smuzhiyun };
743*4882a593Smuzhiyun 
tda18250_probe(struct i2c_client * client,const struct i2c_device_id * id)744*4882a593Smuzhiyun static int tda18250_probe(struct i2c_client *client,
745*4882a593Smuzhiyun 		const struct i2c_device_id *id)
746*4882a593Smuzhiyun {
747*4882a593Smuzhiyun 	struct tda18250_config *cfg = client->dev.platform_data;
748*4882a593Smuzhiyun 	struct dvb_frontend *fe = cfg->fe;
749*4882a593Smuzhiyun 	struct tda18250_dev *dev;
750*4882a593Smuzhiyun 	int ret;
751*4882a593Smuzhiyun 	unsigned char chip_id[3];
752*4882a593Smuzhiyun 
753*4882a593Smuzhiyun 	/* some registers are always read from HW */
754*4882a593Smuzhiyun 	static const struct regmap_range tda18250_yes_ranges[] = {
755*4882a593Smuzhiyun 		regmap_reg_range(R05_POWER1, R0B_IRQ4),
756*4882a593Smuzhiyun 		regmap_reg_range(R21_IF_AGC, R21_IF_AGC),
757*4882a593Smuzhiyun 		regmap_reg_range(R2A_MSM1, R2B_MSM2),
758*4882a593Smuzhiyun 		regmap_reg_range(R2F_RSSI1, R31_IRQ_CTRL),
759*4882a593Smuzhiyun 	};
760*4882a593Smuzhiyun 
761*4882a593Smuzhiyun 	static const struct regmap_access_table tda18250_volatile_table = {
762*4882a593Smuzhiyun 		.yes_ranges = tda18250_yes_ranges,
763*4882a593Smuzhiyun 		.n_yes_ranges = ARRAY_SIZE(tda18250_yes_ranges),
764*4882a593Smuzhiyun 	};
765*4882a593Smuzhiyun 
766*4882a593Smuzhiyun 	static const struct regmap_config tda18250_regmap_config = {
767*4882a593Smuzhiyun 		.reg_bits = 8,
768*4882a593Smuzhiyun 		.val_bits = 8,
769*4882a593Smuzhiyun 		.max_register = TDA18250_NUM_REGS - 1,
770*4882a593Smuzhiyun 		.volatile_table = &tda18250_volatile_table,
771*4882a593Smuzhiyun 	};
772*4882a593Smuzhiyun 
773*4882a593Smuzhiyun 	dev = kzalloc(sizeof(*dev), GFP_KERNEL);
774*4882a593Smuzhiyun 	if (!dev) {
775*4882a593Smuzhiyun 		ret = -ENOMEM;
776*4882a593Smuzhiyun 		goto err;
777*4882a593Smuzhiyun 	}
778*4882a593Smuzhiyun 
779*4882a593Smuzhiyun 	i2c_set_clientdata(client, dev);
780*4882a593Smuzhiyun 
781*4882a593Smuzhiyun 	dev->fe = cfg->fe;
782*4882a593Smuzhiyun 	dev->loopthrough = cfg->loopthrough;
783*4882a593Smuzhiyun 	if (cfg->xtal_freq < TDA18250_XTAL_FREQ_MAX) {
784*4882a593Smuzhiyun 		dev->xtal_freq = cfg->xtal_freq;
785*4882a593Smuzhiyun 	} else {
786*4882a593Smuzhiyun 		ret = -EINVAL;
787*4882a593Smuzhiyun 		dev_err(&client->dev, "xtal_freq invalid=%d", cfg->xtal_freq);
788*4882a593Smuzhiyun 		goto err_kfree;
789*4882a593Smuzhiyun 	}
790*4882a593Smuzhiyun 	dev->if_dvbt_6 = cfg->if_dvbt_6;
791*4882a593Smuzhiyun 	dev->if_dvbt_7 = cfg->if_dvbt_7;
792*4882a593Smuzhiyun 	dev->if_dvbt_8 = cfg->if_dvbt_8;
793*4882a593Smuzhiyun 	dev->if_dvbc_6 = cfg->if_dvbc_6;
794*4882a593Smuzhiyun 	dev->if_dvbc_8 = cfg->if_dvbc_8;
795*4882a593Smuzhiyun 	dev->if_atsc = cfg->if_atsc;
796*4882a593Smuzhiyun 
797*4882a593Smuzhiyun 	dev->if_frequency = 0;
798*4882a593Smuzhiyun 	dev->warm = false;
799*4882a593Smuzhiyun 
800*4882a593Smuzhiyun 	dev->regmap = devm_regmap_init_i2c(client, &tda18250_regmap_config);
801*4882a593Smuzhiyun 	if (IS_ERR(dev->regmap)) {
802*4882a593Smuzhiyun 		ret = PTR_ERR(dev->regmap);
803*4882a593Smuzhiyun 		goto err_kfree;
804*4882a593Smuzhiyun 	}
805*4882a593Smuzhiyun 
806*4882a593Smuzhiyun 	/* read the three chip ID registers */
807*4882a593Smuzhiyun 	regmap_bulk_read(dev->regmap, R00_ID1, &chip_id, 3);
808*4882a593Smuzhiyun 	dev_dbg(&client->dev, "chip_id=%02x:%02x:%02x",
809*4882a593Smuzhiyun 			chip_id[0], chip_id[1], chip_id[2]);
810*4882a593Smuzhiyun 
811*4882a593Smuzhiyun 	switch (chip_id[0]) {
812*4882a593Smuzhiyun 	case 0xc7:
813*4882a593Smuzhiyun 		dev->slave = false;
814*4882a593Smuzhiyun 		break;
815*4882a593Smuzhiyun 	case 0x47:
816*4882a593Smuzhiyun 		dev->slave = true;
817*4882a593Smuzhiyun 		break;
818*4882a593Smuzhiyun 	default:
819*4882a593Smuzhiyun 		ret = -ENODEV;
820*4882a593Smuzhiyun 		goto err_kfree;
821*4882a593Smuzhiyun 	}
822*4882a593Smuzhiyun 
823*4882a593Smuzhiyun 	if (chip_id[1] != 0x4a) {
824*4882a593Smuzhiyun 		ret = -ENODEV;
825*4882a593Smuzhiyun 		goto err_kfree;
826*4882a593Smuzhiyun 	}
827*4882a593Smuzhiyun 
828*4882a593Smuzhiyun 	switch (chip_id[2]) {
829*4882a593Smuzhiyun 	case 0x20:
830*4882a593Smuzhiyun 		dev_info(&client->dev,
831*4882a593Smuzhiyun 				"NXP TDA18250AHN/%s successfully identified",
832*4882a593Smuzhiyun 				dev->slave ? "S" : "M");
833*4882a593Smuzhiyun 		break;
834*4882a593Smuzhiyun 	case 0x21:
835*4882a593Smuzhiyun 		dev_info(&client->dev,
836*4882a593Smuzhiyun 				"NXP TDA18250BHN/%s successfully identified",
837*4882a593Smuzhiyun 				dev->slave ? "S" : "M");
838*4882a593Smuzhiyun 		break;
839*4882a593Smuzhiyun 	default:
840*4882a593Smuzhiyun 		ret = -ENODEV;
841*4882a593Smuzhiyun 		goto err_kfree;
842*4882a593Smuzhiyun 	}
843*4882a593Smuzhiyun 
844*4882a593Smuzhiyun 	fe->tuner_priv = client;
845*4882a593Smuzhiyun 	memcpy(&fe->ops.tuner_ops, &tda18250_ops,
846*4882a593Smuzhiyun 			sizeof(struct dvb_tuner_ops));
847*4882a593Smuzhiyun 
848*4882a593Smuzhiyun 	/* put the tuner in standby */
849*4882a593Smuzhiyun 	tda18250_power_control(fe, TDA18250_POWER_STANDBY);
850*4882a593Smuzhiyun 
851*4882a593Smuzhiyun 	return 0;
852*4882a593Smuzhiyun err_kfree:
853*4882a593Smuzhiyun 	kfree(dev);
854*4882a593Smuzhiyun err:
855*4882a593Smuzhiyun 	dev_dbg(&client->dev, "failed=%d", ret);
856*4882a593Smuzhiyun 	return ret;
857*4882a593Smuzhiyun }
858*4882a593Smuzhiyun 
tda18250_remove(struct i2c_client * client)859*4882a593Smuzhiyun static int tda18250_remove(struct i2c_client *client)
860*4882a593Smuzhiyun {
861*4882a593Smuzhiyun 	struct tda18250_dev *dev = i2c_get_clientdata(client);
862*4882a593Smuzhiyun 	struct dvb_frontend *fe = dev->fe;
863*4882a593Smuzhiyun 
864*4882a593Smuzhiyun 	dev_dbg(&client->dev, "\n");
865*4882a593Smuzhiyun 
866*4882a593Smuzhiyun 	memset(&fe->ops.tuner_ops, 0, sizeof(struct dvb_tuner_ops));
867*4882a593Smuzhiyun 	fe->tuner_priv = NULL;
868*4882a593Smuzhiyun 	kfree(dev);
869*4882a593Smuzhiyun 
870*4882a593Smuzhiyun 	return 0;
871*4882a593Smuzhiyun }
872*4882a593Smuzhiyun 
873*4882a593Smuzhiyun static const struct i2c_device_id tda18250_id_table[] = {
874*4882a593Smuzhiyun 	{"tda18250", 0},
875*4882a593Smuzhiyun 	{}
876*4882a593Smuzhiyun };
877*4882a593Smuzhiyun MODULE_DEVICE_TABLE(i2c, tda18250_id_table);
878*4882a593Smuzhiyun 
879*4882a593Smuzhiyun static struct i2c_driver tda18250_driver = {
880*4882a593Smuzhiyun 	.driver = {
881*4882a593Smuzhiyun 		.name	= "tda18250",
882*4882a593Smuzhiyun 	},
883*4882a593Smuzhiyun 	.probe		= tda18250_probe,
884*4882a593Smuzhiyun 	.remove		= tda18250_remove,
885*4882a593Smuzhiyun 	.id_table	= tda18250_id_table,
886*4882a593Smuzhiyun };
887*4882a593Smuzhiyun 
888*4882a593Smuzhiyun module_i2c_driver(tda18250_driver);
889*4882a593Smuzhiyun 
890*4882a593Smuzhiyun MODULE_DESCRIPTION("NXP TDA18250 silicon tuner driver");
891*4882a593Smuzhiyun MODULE_AUTHOR("Olli Salonen <olli.salonen@iki.fi>");
892*4882a593Smuzhiyun MODULE_LICENSE("GPL");
893