tda8290.c 21.9 KB
Newer Older
L
Linus Torvalds 已提交
1
/*
2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20

   i2c tv tuner chip device driver
   controls the philips tda8290+75 tuner chip combo.

   This program is free software; you can redistribute it and/or modify
   it under the terms of the GNU General Public License as published by
   the Free Software Foundation; either version 2 of the License, or
   (at your option) any later version.

   This program is distributed in the hope that it will be useful,
   but WITHOUT ANY WARRANTY; without even the implied warranty of
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   GNU General Public License for more details.

   You should have received a copy of the GNU General Public License
   along with this program; if not, write to the Free Software
   Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/

L
Linus Torvalds 已提交
21 22 23 24 25 26 27
#include <linux/i2c.h>
#include <linux/videodev.h>
#include <linux/delay.h>
#include <media/tuner.h>

/* ---------------------------------------------------------------------- */

28 29 30 31 32 33 34 35 36 37
struct tda8290_priv {
	unsigned char tda8290_easy_mode;
	unsigned char tda827x_lpsel;
	unsigned char tda827x_addr;
	unsigned char tda827x_ver;
	unsigned int sgIF;
};

/* ---------------------------------------------------------------------- */

38 39 40 41 42 43 44 45
struct tda827x_data {
	u32 lomax;
	u8  spd;
	u8  bs;
	u8  bp;
	u8  cp;
	u8  gc3;
	u8 div1p5;
L
Linus Torvalds 已提交
46 47
};

48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79
     /* Note lomax entry is lo / 62500 */

static struct tda827x_data tda827x_analog[] = {
	{ .lomax =   992, .spd = 3, .bs = 2, .bp = 0, .cp = 0, .gc3 = 3, .div1p5 = 1}, /*  62 MHz */
	{ .lomax =  1056, .spd = 3, .bs = 3, .bp = 0, .cp = 0, .gc3 = 3, .div1p5 = 1}, /*  66 MHz */
	{ .lomax =  1216, .spd = 3, .bs = 1, .bp = 0, .cp = 0, .gc3 = 3, .div1p5 = 0}, /*  76 MHz */
	{ .lomax =  1344, .spd = 3, .bs = 2, .bp = 0, .cp = 0, .gc3 = 3, .div1p5 = 0}, /*  84 MHz */
	{ .lomax =  1488, .spd = 3, .bs = 2, .bp = 0, .cp = 0, .gc3 = 1, .div1p5 = 0}, /*  93 MHz */
	{ .lomax =  1568, .spd = 3, .bs = 3, .bp = 0, .cp = 0, .gc3 = 1, .div1p5 = 0}, /*  98 MHz */
	{ .lomax =  1744, .spd = 3, .bs = 3, .bp = 1, .cp = 0, .gc3 = 1, .div1p5 = 0}, /* 109 MHz */
	{ .lomax =  1968, .spd = 2, .bs = 2, .bp = 1, .cp = 0, .gc3 = 1, .div1p5 = 1}, /* 123 MHz */
	{ .lomax =  2128, .spd = 2, .bs = 3, .bp = 1, .cp = 0, .gc3 = 1, .div1p5 = 1}, /* 133 MHz */
	{ .lomax =  2416, .spd = 2, .bs = 1, .bp = 1, .cp = 0, .gc3 = 1, .div1p5 = 0}, /* 151 MHz */
	{ .lomax =  2464, .spd = 2, .bs = 2, .bp = 1, .cp = 0, .gc3 = 1, .div1p5 = 0}, /* 154 MHz */
	{ .lomax =  2896, .spd = 2, .bs = 2, .bp = 1, .cp = 0, .gc3 = 0, .div1p5 = 0}, /* 181 MHz */
	{ .lomax =  2960, .spd = 2, .bs = 2, .bp = 2, .cp = 0, .gc3 = 1, .div1p5 = 0}, /* 185 MHz */
	{ .lomax =  3472, .spd = 2, .bs = 3, .bp = 2, .cp = 0, .gc3 = 1, .div1p5 = 0}, /* 217 MHz */
	{ .lomax =  3904, .spd = 1, .bs = 2, .bp = 2, .cp = 0, .gc3 = 1, .div1p5 = 1}, /* 244 MHz */
	{ .lomax =  4240, .spd = 1, .bs = 3, .bp = 2, .cp = 0, .gc3 = 1, .div1p5 = 1}, /* 265 MHz */
	{ .lomax =  4832, .spd = 1, .bs = 1, .bp = 2, .cp = 0, .gc3 = 1, .div1p5 = 0}, /* 302 MHz */
	{ .lomax =  5184, .spd = 1, .bs = 2, .bp = 2, .cp = 0, .gc3 = 1, .div1p5 = 0}, /* 324 MHz */
	{ .lomax =  5920, .spd = 1, .bs = 2, .bp = 3, .cp = 0, .gc3 = 1, .div1p5 = 0}, /* 370 MHz */
	{ .lomax =  7264, .spd = 1, .bs = 3, .bp = 3, .cp = 0, .gc3 = 1, .div1p5 = 0}, /* 454 MHz */
	{ .lomax =  7888, .spd = 0, .bs = 2, .bp = 3, .cp = 0, .gc3 = 1, .div1p5 = 1}, /* 493 MHz */
	{ .lomax =  8480, .spd = 0, .bs = 3, .bp = 3, .cp = 0, .gc3 = 1, .div1p5 = 1}, /* 530 MHz */
	{ .lomax =  8864, .spd = 0, .bs = 1, .bp = 3, .cp = 0, .gc3 = 1, .div1p5 = 0}, /* 554 MHz */
	{ .lomax =  9664, .spd = 0, .bs = 1, .bp = 4, .cp = 0, .gc3 = 0, .div1p5 = 0}, /* 604 MHz */
	{ .lomax = 11088, .spd = 0, .bs = 2, .bp = 4, .cp = 0, .gc3 = 0, .div1p5 = 0}, /* 696 MHz */
	{ .lomax = 11840, .spd = 0, .bs = 2, .bp = 4, .cp = 1, .gc3 = 0, .div1p5 = 0}, /* 740 MHz */
	{ .lomax = 13120, .spd = 0, .bs = 3, .bp = 4, .cp = 0, .gc3 = 0, .div1p5 = 0}, /* 820 MHz */
	{ .lomax = 13840, .spd = 0, .bs = 3, .bp = 4, .cp = 1, .gc3 = 0, .div1p5 = 0}, /* 865 MHz */
	{ .lomax =     0, .spd = 0, .bs = 0, .bp = 0, .cp = 0, .gc3 = 0, .div1p5 = 0}  /* End      */
L
Linus Torvalds 已提交
80 81
};

82 83 84 85 86 87 88
static void tda827x_tune(struct i2c_client *c, u16 ifc, unsigned int freq)
{
	unsigned char tuner_reg[8];
	unsigned char reg2[2];
	u32 N;
	int i;
	struct tuner *t = i2c_get_clientdata(c);
89 90
	struct tda8290_priv *priv = t->priv;
	struct i2c_msg msg = {.addr = priv->tda827x_addr, .flags = 0};
L
Linus Torvalds 已提交
91

92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108
	if (t->mode == V4L2_TUNER_RADIO)
		freq = freq / 1000;

	N = freq + ifc;
	i = 0;
	while (tda827x_analog[i].lomax < N) {
		if(tda827x_analog[i + 1].lomax == 0)
			break;
		i++;
	}

	N = N << tda827x_analog[i].spd;

	tuner_reg[0] = 0;
	tuner_reg[1] = (unsigned char)(N>>8);
	tuner_reg[2] = (unsigned char) N;
	tuner_reg[3] = 0x40;
109
	tuner_reg[4] = 0x52 + (priv->tda827x_lpsel << 5);
110
	tuner_reg[5] = (tda827x_analog[i].spd   << 6) + (tda827x_analog[i].div1p5 <<5) +
111
		       (tda827x_analog[i].bs     <<3) +  tda827x_analog[i].bp;
112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146
	tuner_reg[6] = 0x8f + (tda827x_analog[i].gc3 << 4);
	tuner_reg[7] = 0x8f;

	msg.buf = tuner_reg;
	msg.len = 8;
	i2c_transfer(c->adapter, &msg, 1);

	msg.buf= reg2;
	msg.len = 2;
	reg2[0] = 0x80;
	reg2[1] = 0;
	i2c_transfer(c->adapter, &msg, 1);

	reg2[0] = 0x60;
	reg2[1] = 0xbf;
	i2c_transfer(c->adapter, &msg, 1);

	reg2[0] = 0x30;
	reg2[1] = tuner_reg[4] + 0x80;
	i2c_transfer(c->adapter, &msg, 1);

	msleep(1);
	reg2[0] = 0x30;
	reg2[1] = tuner_reg[4] + 4;
	i2c_transfer(c->adapter, &msg, 1);

	msleep(1);
	reg2[0] = 0x30;
	reg2[1] = tuner_reg[4];
	i2c_transfer(c->adapter, &msg, 1);

	msleep(550);
	reg2[0] = 0x30;
	reg2[1] = (tuner_reg[4] & 0xfc) + tda827x_analog[i].cp ;
	i2c_transfer(c->adapter, &msg, 1);
L
Linus Torvalds 已提交
147

148
	reg2[0] = 0x60;
149
	reg2[1] = 0x3f;
150 151 152 153 154 155 156 157
	i2c_transfer(c->adapter, &msg, 1);

	reg2[0] = 0x80;
	reg2[1] = 0x08;   // Vsync en
	i2c_transfer(c->adapter, &msg, 1);
}

static void tda827x_agcf(struct i2c_client *c)
L
Linus Torvalds 已提交
158
{
159
	struct tuner *t = i2c_get_clientdata(c);
160
	struct tda8290_priv *priv = t->priv;
161
	unsigned char data[] = {0x80, 0x0c};
162
	struct i2c_msg msg = {.addr = priv->tda827x_addr, .buf = data,
163 164
			      .flags = 0, .len = 2};
	i2c_transfer(c->adapter, &msg, 1);
L
Linus Torvalds 已提交
165 166 167 168
}

/* ---------------------------------------------------------------------- */

169 170 171 172 173 174 175
struct tda827xa_data {
	u32 lomax;
	u8  svco;
	u8  spd;
	u8  scr;
	u8  sbs;
	u8  gc3;
L
Linus Torvalds 已提交
176 177
};

178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204
static struct tda827xa_data tda827xa_analog[] = {
	{ .lomax =   910, .svco = 3, .spd = 4, .scr = 0, .sbs = 0, .gc3 = 3},  /*  56.875 MHz */
	{ .lomax =  1076, .svco = 0, .spd = 3, .scr = 0, .sbs = 0, .gc3 = 3},  /*  67.25 MHz */
	{ .lomax =  1300, .svco = 1, .spd = 3, .scr = 0, .sbs = 0, .gc3 = 3},  /*  81.25 MHz */
	{ .lomax =  1560, .svco = 2, .spd = 3, .scr = 0, .sbs = 0, .gc3 = 3},  /*  97.5  MHz */
	{ .lomax =  1820, .svco = 3, .spd = 3, .scr = 0, .sbs = 1, .gc3 = 1},  /* 113.75 MHz */
	{ .lomax =  2152, .svco = 0, .spd = 2, .scr = 0, .sbs = 1, .gc3 = 1},  /* 134.5 MHz */
	{ .lomax =  2464, .svco = 1, .spd = 2, .scr = 0, .sbs = 1, .gc3 = 1},  /* 154   MHz */
	{ .lomax =  2600, .svco = 1, .spd = 2, .scr = 0, .sbs = 1, .gc3 = 1},  /* 162.5 MHz */
	{ .lomax =  2928, .svco = 2, .spd = 2, .scr = 0, .sbs = 1, .gc3 = 1},  /* 183   MHz */
	{ .lomax =  3120, .svco = 2, .spd = 2, .scr = 0, .sbs = 2, .gc3 = 1},  /* 195   MHz */
	{ .lomax =  3640, .svco = 3, .spd = 2, .scr = 0, .sbs = 2, .gc3 = 3},  /* 227.5 MHz */
	{ .lomax =  4304, .svco = 0, .spd = 1, .scr = 0, .sbs = 2, .gc3 = 3},  /* 269   MHz */
	{ .lomax =  5200, .svco = 1, .spd = 1, .scr = 0, .sbs = 2, .gc3 = 1},  /* 325   MHz */
	{ .lomax =  6240, .svco = 2, .spd = 1, .scr = 0, .sbs = 3, .gc3 = 3},  /* 390   MHz */
	{ .lomax =  7280, .svco = 3, .spd = 1, .scr = 0, .sbs = 3, .gc3 = 3},  /* 455   MHz */
	{ .lomax =  8320, .svco = 0, .spd = 0, .scr = 0, .sbs = 3, .gc3 = 1},  /* 520   MHz */
	{ .lomax =  8608, .svco = 0, .spd = 0, .scr = 1, .sbs = 3, .gc3 = 1},  /* 538   MHz */
	{ .lomax =  8864, .svco = 1, .spd = 0, .scr = 0, .sbs = 3, .gc3 = 1},  /* 554   MHz */
	{ .lomax =  9920, .svco = 1, .spd = 0, .scr = 0, .sbs = 4, .gc3 = 0},  /* 620   MHz */
	{ .lomax = 10400, .svco = 1, .spd = 0, .scr = 1, .sbs = 4, .gc3 = 0},  /* 650   MHz */
	{ .lomax = 11200, .svco = 2, .spd = 0, .scr = 0, .sbs = 4, .gc3 = 0},  /* 700   MHz */
	{ .lomax = 12480, .svco = 2, .spd = 0, .scr = 1, .sbs = 4, .gc3 = 0},  /* 780   MHz */
	{ .lomax = 13120, .svco = 3, .spd = 0, .scr = 0, .sbs = 4, .gc3 = 0},  /* 820   MHz */
	{ .lomax = 13920, .svco = 3, .spd = 0, .scr = 1, .sbs = 4, .gc3 = 0},  /* 870   MHz */
	{ .lomax = 14576, .svco = 3, .spd = 0, .scr = 2, .sbs = 4, .gc3 = 0},  /* 911   MHz */
	{ .lomax =     0, .svco = 0, .spd = 0, .scr = 0, .sbs = 0, .gc3 = 0}   /* End */
L
Linus Torvalds 已提交
205 206
};

207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225
static void tda827xa_lna_gain(struct i2c_client *c, int high)
{
	struct tuner *t = i2c_get_clientdata(c);
	unsigned char buf[] = {0x22, 0x01};
	int arg;
	struct i2c_msg msg = {.addr = c->addr, .flags = 0, .buf = buf, .len = sizeof(buf)};
	if (t->config) {
		if (high)
			tuner_dbg("setting LNA to high gain\n");
		else
			tuner_dbg("setting LNA to low gain\n");
	}
	switch (t->config) {
	case 0: /* no LNA */
		break;
	case 1: /* switch is GPIO 0 of tda8290 */
	case 2:
		/* turn Vsync on */
		if (t->std & V4L2_STD_MN)
226
			arg = 1;
227
		else
228 229 230
			arg = 0;
		if (t->tuner_callback)
			t->tuner_callback(c->adapter->algo_data, 1, arg);
231 232 233 234 235 236
		buf[1] = high ? 0 : 1;
		if (t->config == 2)
			buf[1] = high ? 1 : 0;
		i2c_transfer(c->adapter, &msg, 1);
		break;
	case 3: /* switch with GPIO of saa713x */
237 238
		if (t->tuner_callback)
			t->tuner_callback(c->adapter->algo_data, 0, high);
239 240 241 242
		break;
	}
}

243 244
static void tda827xa_tune(struct i2c_client *c, u16 ifc, unsigned int freq)
{
245
	unsigned char tuner_reg[11];
246 247 248
	u32 N;
	int i;
	struct tuner *t = i2c_get_clientdata(c);
249 250
	struct tda8290_priv *priv = t->priv;
	struct i2c_msg msg = {.addr = priv->tda827x_addr, .flags = 0, .buf = tuner_reg};
251 252 253

	tda827xa_lna_gain( c, 1);
	msleep(10);
L
Linus Torvalds 已提交
254

255 256
	if (t->mode == V4L2_TUNER_RADIO)
		freq = freq / 1000;
L
Linus Torvalds 已提交
257

258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273
	N = freq + ifc;
	i = 0;
	while (tda827xa_analog[i].lomax < N) {
		if(tda827xa_analog[i + 1].lomax == 0)
			break;
		i++;
	}

	N = N << tda827xa_analog[i].spd;

	tuner_reg[0] = 0;
	tuner_reg[1] = (unsigned char)(N>>8);
	tuner_reg[2] = (unsigned char) N;
	tuner_reg[3] = 0;
	tuner_reg[4] = 0x16;
	tuner_reg[5] = (tda827xa_analog[i].spd << 5) + (tda827xa_analog[i].svco << 3) +
274
			tda827xa_analog[i].sbs;
275
	tuner_reg[6] = 0x8b + (tda827xa_analog[i].gc3 << 4);
276
	tuner_reg[7] = 0x1c;
277 278
	tuner_reg[8] = 4;
	tuner_reg[9] = 0x20;
279 280 281
	tuner_reg[10] = 0x00;
	msg.len = 11;
	i2c_transfer(c->adapter, &msg, 1);
282

283 284 285 286
	tuner_reg[0] = 0x90;
	tuner_reg[1] = 0xff;
	tuner_reg[2] = 0xe0;
	tuner_reg[3] = 0;
287
	tuner_reg[4] = 0x99 + (priv->tda827x_lpsel << 1);
288
	msg.len = 5;
289 290
	i2c_transfer(c->adapter, &msg, 1);

291 292
	tuner_reg[0] = 0xa0;
	tuner_reg[1] = 0xc0;
293 294 295
	msg.len = 2;
	i2c_transfer(c->adapter, &msg, 1);

296 297
	tuner_reg[0] = 0x30;
	tuner_reg[1] = 0x10 + tda827xa_analog[i].scr;
298 299
	i2c_transfer(c->adapter, &msg, 1);

300 301 302 303 304 305 306 307 308 309 310
	msg.flags = I2C_M_RD;
	i2c_transfer(c->adapter, &msg, 1);
	msg.flags = 0;
	tuner_reg[1] >>= 4;
	tuner_dbg("AGC2 gain is: %d\n", tuner_reg[1]);
	if (tuner_reg[1] < 1)
		tda827xa_lna_gain( c, 0);

	msleep(100);
	tuner_reg[0] = 0x60;
	tuner_reg[1] = 0x3c;
311 312
	i2c_transfer(c->adapter, &msg, 1);

313 314 315
	msleep(163);
	tuner_reg[0] = 0x50;
	tuner_reg[1] = 0x8f + (tda827xa_analog[i].gc3 << 4);
316 317
	i2c_transfer(c->adapter, &msg, 1);

318 319
	tuner_reg[0] = 0x80;
	tuner_reg[1] = 0x28;
320 321
	i2c_transfer(c->adapter, &msg, 1);

322 323
	tuner_reg[0] = 0xb0;
	tuner_reg[1] = 0x01;
324
	i2c_transfer(c->adapter, &msg, 1);
325

326
	tuner_reg[0] = 0xc0;
327
	tuner_reg[1] = 0x19 + (priv->tda827x_lpsel << 1);
328 329 330 331
	i2c_transfer(c->adapter, &msg, 1);
}

static void tda827xa_agcf(struct i2c_client *c)
L
Linus Torvalds 已提交
332 333
{
	struct tuner *t = i2c_get_clientdata(c);
334
	struct tda8290_priv *priv = t->priv;
335
	unsigned char data[] = {0x80, 0x2c};
336
	struct i2c_msg msg = {.addr = priv->tda827x_addr, .buf = data,
337 338 339
			      .flags = 0, .len = 2};
	i2c_transfer(c->adapter, &msg, 1);
}
L
Linus Torvalds 已提交
340

341
/*---------------------------------------------------------------------*/
L
Linus Torvalds 已提交
342

343 344 345
static void tda8290_i2c_bridge(struct i2c_client *c, int close)
{
	unsigned char  enable[2] = { 0x21, 0xC0 };
346
	unsigned char disable[2] = { 0x21, 0x00 };
347 348 349 350 351 352 353 354 355 356
	unsigned char *msg;
	if(close) {
		msg = enable;
		i2c_master_send(c, msg, 2);
		/* let the bridge stabilize */
		msleep(20);
	} else {
		msg = disable;
		i2c_master_send(c, msg, 2);
	}
L
Linus Torvalds 已提交
357 358
}

359 360 361
/*---------------------------------------------------------------------*/

static int tda8290_tune(struct i2c_client *c, u16 ifc, unsigned int freq)
L
Linus Torvalds 已提交
362
{
363
	struct tuner *t = i2c_get_clientdata(c);
364
	struct tda8290_priv *priv = t->priv;
365
	unsigned char soft_reset[]  = { 0x00, 0x00 };
366
	unsigned char easy_mode[]   = { 0x01, priv->tda8290_easy_mode };
367
	unsigned char expert_mode[] = { 0x01, 0x80 };
368
	unsigned char agc_out_on[]  = { 0x02, 0x00 };
369 370 371 372 373 374 375 376 377 378 379 380 381 382 383
	unsigned char gainset_off[] = { 0x28, 0x14 };
	unsigned char if_agc_spd[]  = { 0x0f, 0x88 };
	unsigned char adc_head_6[]  = { 0x05, 0x04 };
	unsigned char adc_head_9[]  = { 0x05, 0x02 };
	unsigned char adc_head_12[] = { 0x05, 0x01 };
	unsigned char pll_bw_nom[]  = { 0x0d, 0x47 };
	unsigned char pll_bw_low[]  = { 0x0d, 0x27 };
	unsigned char gainset_2[]   = { 0x28, 0x64 };
	unsigned char agc_rst_on[]  = { 0x0e, 0x0b };
	unsigned char agc_rst_off[] = { 0x0e, 0x09 };
	unsigned char if_agc_set[]  = { 0x0f, 0x81 };
	unsigned char addr_adc_sat  = 0x1a;
	unsigned char addr_agc_stat = 0x1d;
	unsigned char addr_pll_stat = 0x1b;
	unsigned char adc_sat, agc_stat,
384
		      pll_stat;
385
	int i;
386

387
	tuner_dbg("tda827xa config is 0x%02x\n", t->config);
388
	i2c_master_send(c, easy_mode, 2);
389
	i2c_master_send(c, agc_out_on, 2);
390 391 392
	i2c_master_send(c, soft_reset, 2);
	msleep(1);

393
	expert_mode[1] = priv->tda8290_easy_mode + 0x80;
394 395 396
	i2c_master_send(c, expert_mode, 2);
	i2c_master_send(c, gainset_off, 2);
	i2c_master_send(c, if_agc_spd, 2);
397
	if (priv->tda8290_easy_mode & 0x60)
398 399 400 401 402 403
		i2c_master_send(c, adc_head_9, 2);
	else
		i2c_master_send(c, adc_head_6, 2);
	i2c_master_send(c, pll_bw_nom, 2);

	tda8290_i2c_bridge(c, 1);
404
	if (priv->tda827x_ver != 0)
405 406 407
		tda827xa_tune(c, ifc, freq);
	else
		tda827x_tune(c, ifc, freq);
408 409 410 411 412 413 414 415 416 417 418 419 420 421 422
	for (i = 0; i < 3; i++) {
		i2c_master_send(c, &addr_pll_stat, 1);
		i2c_master_recv(c, &pll_stat, 1);
		if (pll_stat & 0x80) {
			i2c_master_send(c, &addr_adc_sat, 1);
			i2c_master_recv(c, &adc_sat, 1);
			i2c_master_send(c, &addr_agc_stat, 1);
			i2c_master_recv(c, &agc_stat, 1);
			tuner_dbg("tda8290 is locked, AGC: %d\n", agc_stat);
			break;
		} else {
			tuner_dbg("tda8290 not locked, no signal?\n");
			msleep(100);
		}
	}
423
	/* adjust headroom resp. gain */
424 425 426
	if ((agc_stat > 115) || (!(pll_stat & 0x80) && (adc_sat < 20))) {
		tuner_dbg("adjust gain, step 1. Agc: %d, ADC stat: %d, lock: %d\n",
			   agc_stat, adc_sat, pll_stat & 0x80);
427 428 429 430 431 432 433
		i2c_master_send(c, gainset_2, 2);
		msleep(100);
		i2c_master_send(c, &addr_agc_stat, 1);
		i2c_master_recv(c, &agc_stat, 1);
		i2c_master_send(c, &addr_pll_stat, 1);
		i2c_master_recv(c, &pll_stat, 1);
		if ((agc_stat > 115) || !(pll_stat & 0x80)) {
434 435
			tuner_dbg("adjust gain, step 2. Agc: %d, lock: %d\n",
				   agc_stat, pll_stat & 0x80);
436
			if (priv->tda827x_ver != 0)
437 438 439 440 441 442 443 444 445 446 447 448 449 450 451 452
				tda827xa_agcf(c);
			else
				tda827x_agcf(c);
			msleep(100);
			i2c_master_send(c, &addr_agc_stat, 1);
			i2c_master_recv(c, &agc_stat, 1);
			i2c_master_send(c, &addr_pll_stat, 1);
			i2c_master_recv(c, &pll_stat, 1);
			if((agc_stat > 115) || !(pll_stat & 0x80)) {
				tuner_dbg("adjust gain, step 3. Agc: %d\n", agc_stat);
				i2c_master_send(c, adc_head_12, 2);
				i2c_master_send(c, pll_bw_low, 2);
				msleep(100);
			}
		}
	}
L
Linus Torvalds 已提交
453

454
	/* l/ l' deadlock? */
455
	if(priv->tda8290_easy_mode & 0x60) {
456 457 458 459 460
		i2c_master_send(c, &addr_adc_sat, 1);
		i2c_master_recv(c, &adc_sat, 1);
		i2c_master_send(c, &addr_pll_stat, 1);
		i2c_master_recv(c, &pll_stat, 1);
		if ((adc_sat > 20) || !(pll_stat & 0x80)) {
461
			tuner_dbg("trying to resolve SECAM L deadlock\n");
462 463 464 465 466
			i2c_master_send(c, agc_rst_on, 2);
			msleep(40);
			i2c_master_send(c, agc_rst_off, 2);
		}
	}
467

468 469 470
	tda8290_i2c_bridge(c, 0);
	i2c_master_send(c, if_agc_set, 2);
	return 0;
L
Linus Torvalds 已提交
471 472
}

473 474
/*---------------------------------------------------------------------*/

L
Linus Torvalds 已提交
475 476
static void set_audio(struct tuner *t)
{
477
	struct tda8290_priv *priv = t->priv;
478
	char* mode;
L
Linus Torvalds 已提交
479

480
	priv->tda827x_lpsel = 0;
481
	if (t->std & V4L2_STD_MN) {
482 483 484
		priv->sgIF = 92;
		priv->tda8290_easy_mode = 0x01;
		priv->tda827x_lpsel = 1;
485
		mode = "MN";
486
	} else if (t->std & V4L2_STD_B) {
487 488
		priv->sgIF = 108;
		priv->tda8290_easy_mode = 0x02;
489
		mode = "B";
490
	} else if (t->std & V4L2_STD_GH) {
491 492
		priv->sgIF = 124;
		priv->tda8290_easy_mode = 0x04;
493
		mode = "GH";
494
	} else if (t->std & V4L2_STD_PAL_I) {
495 496
		priv->sgIF = 124;
		priv->tda8290_easy_mode = 0x08;
497
		mode = "I";
498
	} else if (t->std & V4L2_STD_DK) {
499 500
		priv->sgIF = 124;
		priv->tda8290_easy_mode = 0x10;
501
		mode = "DK";
502
	} else if (t->std & V4L2_STD_SECAM_L) {
503 504
		priv->sgIF = 124;
		priv->tda8290_easy_mode = 0x20;
505
		mode = "L";
506
	} else if (t->std & V4L2_STD_SECAM_LC) {
507 508
		priv->sgIF = 20;
		priv->tda8290_easy_mode = 0x40;
509
		mode = "LC";
510
	} else {
511 512
		priv->sgIF = 124;
		priv->tda8290_easy_mode = 0x10;
513
		mode = "xx";
514
	}
515
	tuner_dbg("setting tda8290 to system %s\n", mode);
L
Linus Torvalds 已提交
516 517 518 519 520
}

static void set_tv_freq(struct i2c_client *c, unsigned int freq)
{
	struct tuner *t = i2c_get_clientdata(c);
521
	struct tda8290_priv *priv = t->priv;
L
Linus Torvalds 已提交
522 523

	set_audio(t);
524
	tda8290_tune(c, priv->sgIF, freq);
L
Linus Torvalds 已提交
525 526 527 528
}

static void set_radio_freq(struct i2c_client *c, unsigned int freq)
{
529 530
	/* if frequency is 5.5 MHz */
	tda8290_tune(c, 88, freq);
L
Linus Torvalds 已提交
531 532 533 534 535 536 537 538 539 540 541 542
}

static int has_signal(struct i2c_client *c)
{
	unsigned char i2c_get_afc[1] = { 0x1B };
	unsigned char afc = 0;

	i2c_master_send(c, i2c_get_afc, ARRAY_SIZE(i2c_get_afc));
	i2c_master_recv(c, &afc, 1);
	return (afc & 0x80)? 65535:0;
}

543 544
/*---------------------------------------------------------------------*/

545 546
static void standby(struct i2c_client *c)
{
547
	struct tuner *t = i2c_get_clientdata(c);
548
	struct tda8290_priv *priv = t->priv;
549 550
	unsigned char cb1[] = { 0x30, 0xD0 };
	unsigned char tda8290_standby[] = { 0x00, 0x02 };
551
	unsigned char tda8290_agc_tri[] = { 0x02, 0x20 };
552
	struct i2c_msg msg = {.addr = priv->tda827x_addr, .flags=0, .buf=cb1, .len = 2};
553 554

	tda8290_i2c_bridge(c, 1);
555
	if (priv->tda827x_ver != 0)
556 557 558
		cb1[1] = 0x90;
	i2c_transfer(c->adapter, &msg, 1);
	tda8290_i2c_bridge(c, 0);
559
	i2c_master_send(c, tda8290_agc_tri, 2);
560
	i2c_master_send(c, tda8290_standby, 2);
561 562
}

563 564 565

static void tda8290_init_if(struct i2c_client *c)
{
566
	struct tuner *t = i2c_get_clientdata(c);
567
	unsigned char set_VS[] = { 0x30, 0x6F };
568
	unsigned char set_GP00_CF[] = { 0x20, 0x01 };
569 570
	unsigned char set_GP01_CF[] = { 0x20, 0x0B };

571 572 573 574
	if ((t->config == 1) || (t->config == 2))
		i2c_master_send(c, set_GP00_CF, 2);
	else
		i2c_master_send(c, set_GP01_CF, 2);
575 576 577 578
	i2c_master_send(c, set_VS, 2);
}

static void tda8290_init_tuner(struct i2c_client *c)
L
Linus Torvalds 已提交
579 580
{
	struct tuner *t = i2c_get_clientdata(c);
581
	struct tda8290_priv *priv = t->priv;
582
	unsigned char tda8275_init[]  = { 0x00, 0x00, 0x00, 0x40, 0xdC, 0x04, 0xAf,
583
					  0x3F, 0x2A, 0x04, 0xFF, 0x00, 0x00, 0x40 };
584
	unsigned char tda8275a_init[] = { 0x00, 0x00, 0x00, 0x00, 0xdC, 0x05, 0x8b,
585
					  0x0c, 0x04, 0x20, 0xFF, 0x00, 0x00, 0x4b };
586
	struct i2c_msg msg = {.addr = priv->tda827x_addr, .flags=0,
587
			      .buf=tda8275_init, .len = 14};
588
	if (priv->tda827x_ver != 0)
589 590 591 592 593 594 595 596
		msg.buf = tda8275a_init;

	tda8290_i2c_bridge(c, 1);
	i2c_transfer(c->adapter, &msg, 1);
	tda8290_i2c_bridge(c, 0);
}

/*---------------------------------------------------------------------*/
L
Linus Torvalds 已提交
597

598 599 600 601 602 603 604 605
static void tda8290_release(struct i2c_client *c)
{
	struct tuner *t = i2c_get_clientdata(c);

	kfree(t->priv);
	t->priv = NULL;
}

606 607
int tda8290_init(struct i2c_client *c)
{
608
	struct tda8290_priv *priv = NULL;
609 610 611 612 613 614
	struct tuner *t = i2c_get_clientdata(c);
	u8 data;
	int i, ret, tuners_found;
	u32 tuner_addrs;
	struct i2c_msg msg = {.flags=I2C_M_RD, .buf=&data, .len = 1};

615 616 617 618 619
	priv = kzalloc(sizeof(struct tda8290_priv), GFP_KERNEL);
	if (priv == NULL)
		return -ENOMEM;
	t->priv = priv;

620 621 622 623 624 625 626 627 628 629 630 631 632 633 634 635 636 637 638 639 640 641 642 643 644 645 646 647
	tda8290_i2c_bridge(c, 1);
	/* probe for tuner chip */
	tuners_found = 0;
	tuner_addrs = 0;
	for (i=0x60; i<= 0x63; i++) {
		msg.addr = i;
		ret = i2c_transfer(c->adapter, &msg, 1);
		if (ret == 1) {
			tuners_found++;
			tuner_addrs = (tuner_addrs << 8) + i;
		}
	}
	/* if there is more than one tuner, we expect the right one is
	   behind the bridge and we choose the highest address that doesn't
	   give a response now
	 */
	tda8290_i2c_bridge(c, 0);
	if(tuners_found > 1)
		for (i = 0; i < tuners_found; i++) {
			msg.addr = tuner_addrs  & 0xff;
			ret = i2c_transfer(c->adapter, &msg, 1);
			if(ret == 1)
				tuner_addrs = tuner_addrs >> 8;
			else
				break;
		}
	if (tuner_addrs == 0) {
		tuner_addrs = 0x61;
648
		tuner_info ("could not clearly identify tuner address, defaulting to %x\n",
649
			     tuner_addrs);
650 651 652 653
	} else {
		tuner_addrs = tuner_addrs & 0xff;
		tuner_info ("setting tuner address to %x\n", tuner_addrs);
	}
654
	priv->tda827x_addr = tuner_addrs;
655 656 657 658 659 660 661 662
	msg.addr = tuner_addrs;

	tda8290_i2c_bridge(c, 1);
	ret = i2c_transfer(c->adapter, &msg, 1);
	if( ret != 1)
		tuner_warn ("TDA827x access failed!\n");
	if ((data & 0x3c) == 0) {
		strlcpy(c->name, "tda8290+75", sizeof(c->name));
663
		priv->tda827x_ver = 0;
664 665
	} else {
		strlcpy(c->name, "tda8290+75a", sizeof(c->name));
666
		priv->tda827x_ver = 2;
667
	}
668
	tuner_info("type set to %s\n", c->name);
669

670 671 672 673 674
	t->ops.set_tv_freq    = set_tv_freq;
	t->ops.set_radio_freq = set_radio_freq;
	t->ops.has_signal = has_signal;
	t->ops.standby = standby;
	t->ops.release = tda8290_release;
675
	priv->tda827x_lpsel = 0;
676
	t->mode = V4L2_TUNER_ANALOG_TV;
L
Linus Torvalds 已提交
677

678 679
	tda8290_init_tuner(c);
	tda8290_init_if(c);
L
Linus Torvalds 已提交
680 681 682
	return 0;
}

683 684
int tda8290_probe(struct i2c_client *c)
{
685 686 687 688
	unsigned char soft_reset[]   = { 0x00, 0x00 };
	unsigned char easy_mode_b[]  = { 0x01, 0x02 };
	unsigned char easy_mode_g[]  = { 0x01, 0x04 };
	unsigned char restore_9886[] = { 0x00, 0xd6, 0x30 };
689 690 691 692 693 694 695 696 697 698 699 700 701 702 703 704
	unsigned char addr_dto_lsb = 0x07;
	unsigned char data;

	i2c_master_send(c, easy_mode_b, 2);
	i2c_master_send(c, soft_reset, 2);
	i2c_master_send(c, &addr_dto_lsb, 1);
	i2c_master_recv(c, &data, 1);
	if (data == 0) {
		i2c_master_send(c, easy_mode_g, 2);
		i2c_master_send(c, soft_reset, 2);
		i2c_master_send(c, &addr_dto_lsb, 1);
		i2c_master_recv(c, &data, 1);
		if (data == 0x7b) {
			return 0;
		}
	}
705
	i2c_master_send(c, restore_9886, 3);
706 707 708
	return -1;
}

L
Linus Torvalds 已提交
709 710 711 712 713 714 715
/*
 * Overrides for Emacs so that we follow Linus's tabbing style.
 * ---------------------------------------------------------------------------
 * Local variables:
 * c-basic-offset: 8
 * End:
 */