xref: /linux/drivers/media/dvb-frontends/si21xx.c (revision 8795a739e5c72abeec51caf36b6df2b37e5720c5)
1 // SPDX-License-Identifier: GPL-2.0-or-later
2 /* DVB compliant Linux driver for the DVB-S si2109/2110 demodulator
3 *
4 * Copyright (C) 2008 Igor M. Liplianin (liplianin@me.by)
5 */
6 #include <linux/init.h>
7 #include <linux/kernel.h>
8 #include <linux/module.h>
9 #include <linux/string.h>
10 #include <linux/slab.h>
11 #include <linux/jiffies.h>
12 #include <asm/div64.h>
13 
14 #include <media/dvb_frontend.h>
15 #include "si21xx.h"
16 
17 #define	REVISION_REG			0x00
18 #define	SYSTEM_MODE_REG			0x01
19 #define	TS_CTRL_REG_1			0x02
20 #define	TS_CTRL_REG_2			0x03
21 #define	PIN_CTRL_REG_1			0x04
22 #define	PIN_CTRL_REG_2			0x05
23 #define	LOCK_STATUS_REG_1		0x0f
24 #define	LOCK_STATUS_REG_2		0x10
25 #define	ACQ_STATUS_REG			0x11
26 #define	ACQ_CTRL_REG_1			0x13
27 #define	ACQ_CTRL_REG_2			0x14
28 #define	PLL_DIVISOR_REG			0x15
29 #define	COARSE_TUNE_REG			0x16
30 #define	FINE_TUNE_REG_L			0x17
31 #define	FINE_TUNE_REG_H			0x18
32 
33 #define	ANALOG_AGC_POWER_LEVEL_REG	0x28
34 #define	CFO_ESTIMATOR_CTRL_REG_1	0x29
35 #define	CFO_ESTIMATOR_CTRL_REG_2	0x2a
36 #define	CFO_ESTIMATOR_CTRL_REG_3	0x2b
37 
38 #define	SYM_RATE_ESTIMATE_REG_L		0x31
39 #define	SYM_RATE_ESTIMATE_REG_M		0x32
40 #define	SYM_RATE_ESTIMATE_REG_H		0x33
41 
42 #define	CFO_ESTIMATOR_OFFSET_REG_L	0x36
43 #define	CFO_ESTIMATOR_OFFSET_REG_H	0x37
44 #define	CFO_ERROR_REG_L			0x38
45 #define	CFO_ERROR_REG_H			0x39
46 #define	SYM_RATE_ESTIMATOR_CTRL_REG	0x3a
47 
48 #define	SYM_RATE_REG_L			0x3f
49 #define	SYM_RATE_REG_M			0x40
50 #define	SYM_RATE_REG_H			0x41
51 #define	SYM_RATE_ESTIMATOR_MAXIMUM_REG	0x42
52 #define	SYM_RATE_ESTIMATOR_MINIMUM_REG	0x43
53 
54 #define	C_N_ESTIMATOR_CTRL_REG		0x7c
55 #define	C_N_ESTIMATOR_THRSHLD_REG	0x7d
56 #define	C_N_ESTIMATOR_LEVEL_REG_L	0x7e
57 #define	C_N_ESTIMATOR_LEVEL_REG_H	0x7f
58 
59 #define	BLIND_SCAN_CTRL_REG		0x80
60 
61 #define	LSA_CTRL_REG_1			0x8D
62 #define	SPCTRM_TILT_CORR_THRSHLD_REG	0x8f
63 #define	ONE_DB_BNDWDTH_THRSHLD_REG	0x90
64 #define	TWO_DB_BNDWDTH_THRSHLD_REG	0x91
65 #define	THREE_DB_BNDWDTH_THRSHLD_REG	0x92
66 #define	INBAND_POWER_THRSHLD_REG	0x93
67 #define	REF_NOISE_LVL_MRGN_THRSHLD_REG	0x94
68 
69 #define	VIT_SRCH_CTRL_REG_1		0xa0
70 #define	VIT_SRCH_CTRL_REG_2		0xa1
71 #define	VIT_SRCH_CTRL_REG_3		0xa2
72 #define	VIT_SRCH_STATUS_REG		0xa3
73 #define	VITERBI_BER_COUNT_REG_L		0xab
74 #define	REED_SOLOMON_CTRL_REG		0xb0
75 #define	REED_SOLOMON_ERROR_COUNT_REG_L	0xb1
76 #define	PRBS_CTRL_REG			0xb5
77 
78 #define	LNB_CTRL_REG_1			0xc0
79 #define	LNB_CTRL_REG_2			0xc1
80 #define	LNB_CTRL_REG_3			0xc2
81 #define	LNB_CTRL_REG_4			0xc3
82 #define	LNB_CTRL_STATUS_REG		0xc4
83 #define	LNB_FIFO_REGS_0			0xc5
84 #define	LNB_FIFO_REGS_1			0xc6
85 #define	LNB_FIFO_REGS_2			0xc7
86 #define	LNB_FIFO_REGS_3			0xc8
87 #define	LNB_FIFO_REGS_4			0xc9
88 #define	LNB_FIFO_REGS_5			0xca
89 #define	LNB_SUPPLY_CTRL_REG_1		0xcb
90 #define	LNB_SUPPLY_CTRL_REG_2		0xcc
91 #define	LNB_SUPPLY_CTRL_REG_3		0xcd
92 #define	LNB_SUPPLY_CTRL_REG_4		0xce
93 #define	LNB_SUPPLY_STATUS_REG		0xcf
94 
95 #define FAIL	-1
96 #define PASS	0
97 
98 #define ALLOWABLE_FS_COUNT	10
99 #define STATUS_BER		0
100 #define STATUS_UCBLOCKS		1
101 
102 static int debug;
103 #define dprintk(args...) \
104 	do { \
105 		if (debug) \
106 			printk(KERN_DEBUG "si21xx: " args); \
107 	} while (0)
108 
109 enum {
110 	ACTIVE_HIGH,
111 	ACTIVE_LOW
112 };
113 enum {
114 	BYTE_WIDE,
115 	BIT_WIDE
116 };
117 enum {
118 	CLK_GAPPED_MODE,
119 	CLK_CONTINUOUS_MODE
120 };
121 enum {
122 	RISING_EDGE,
123 	FALLING_EDGE
124 };
125 enum {
126 	MSB_FIRST,
127 	LSB_FIRST
128 };
129 enum {
130 	SERIAL,
131 	PARALLEL
132 };
133 
134 struct si21xx_state {
135 	struct i2c_adapter *i2c;
136 	const struct si21xx_config *config;
137 	struct dvb_frontend frontend;
138 	u8 initialised:1;
139 	int errmode;
140 	int fs;			/*Sampling rate of the ADC in MHz*/
141 };
142 
143 /*	register default initialization */
144 static u8 serit_sp1511lhb_inittab[] = {
145 	0x01, 0x28,	/* set i2c_inc_disable */
146 	0x20, 0x03,
147 	0x27, 0x20,
148 	0xe0, 0x45,
149 	0xe1, 0x08,
150 	0xfe, 0x01,
151 	0x01, 0x28,
152 	0x89, 0x09,
153 	0x04, 0x80,
154 	0x05, 0x01,
155 	0x06, 0x00,
156 	0x20, 0x03,
157 	0x24, 0x88,
158 	0x29, 0x09,
159 	0x2a, 0x0f,
160 	0x2c, 0x10,
161 	0x2d, 0x19,
162 	0x2e, 0x08,
163 	0x2f, 0x10,
164 	0x30, 0x19,
165 	0x34, 0x20,
166 	0x35, 0x03,
167 	0x45, 0x02,
168 	0x46, 0x45,
169 	0x47, 0xd0,
170 	0x48, 0x00,
171 	0x49, 0x40,
172 	0x4a, 0x03,
173 	0x4c, 0xfd,
174 	0x4f, 0x2e,
175 	0x50, 0x2e,
176 	0x51, 0x10,
177 	0x52, 0x10,
178 	0x56, 0x92,
179 	0x59, 0x00,
180 	0x5a, 0x2d,
181 	0x5b, 0x33,
182 	0x5c, 0x1f,
183 	0x5f, 0x76,
184 	0x62, 0xc0,
185 	0x63, 0xc0,
186 	0x64, 0xf3,
187 	0x65, 0xf3,
188 	0x79, 0x40,
189 	0x6a, 0x40,
190 	0x6b, 0x0a,
191 	0x6c, 0x80,
192 	0x6d, 0x27,
193 	0x71, 0x06,
194 	0x75, 0x60,
195 	0x78, 0x00,
196 	0x79, 0xb5,
197 	0x7c, 0x05,
198 	0x7d, 0x1a,
199 	0x87, 0x55,
200 	0x88, 0x72,
201 	0x8f, 0x08,
202 	0x90, 0xe0,
203 	0x94, 0x40,
204 	0xa0, 0x3f,
205 	0xa1, 0xc0,
206 	0xa4, 0xcc,
207 	0xa5, 0x66,
208 	0xa6, 0x66,
209 	0xa7, 0x7b,
210 	0xa8, 0x7b,
211 	0xa9, 0x7b,
212 	0xaa, 0x9a,
213 	0xed, 0x04,
214 	0xad, 0x00,
215 	0xae, 0x03,
216 	0xcc, 0xab,
217 	0x01, 0x08,
218 	0xff, 0xff
219 };
220 
221 /*	low level read/writes */
222 static int si21_writeregs(struct si21xx_state *state, u8 reg1,
223 							u8 *data, int len)
224 {
225 	int ret;
226 	u8 buf[60];/* = { reg1, data };*/
227 	struct i2c_msg msg = {
228 				.addr = state->config->demod_address,
229 				.flags = 0,
230 				.buf = buf,
231 				.len = len + 1
232 	};
233 
234 	if (len > sizeof(buf) - 1)
235 		return -EINVAL;
236 
237 	msg.buf[0] =  reg1;
238 	memcpy(msg.buf + 1, data, len);
239 
240 	ret = i2c_transfer(state->i2c, &msg, 1);
241 
242 	if (ret != 1)
243 		dprintk("%s: writereg error (reg1 == 0x%02x, data == 0x%02x, ret == %i)\n",
244 			__func__, reg1, data[0], ret);
245 
246 	return (ret != 1) ? -EREMOTEIO : 0;
247 }
248 
249 static int si21_writereg(struct si21xx_state *state, u8 reg, u8 data)
250 {
251 	int ret;
252 	u8 buf[] = { reg, data };
253 	struct i2c_msg msg = {
254 				.addr = state->config->demod_address,
255 				.flags = 0,
256 				.buf = buf,
257 				.len = 2
258 	};
259 
260 	ret = i2c_transfer(state->i2c, &msg, 1);
261 
262 	if (ret != 1)
263 		dprintk("%s: writereg error (reg == 0x%02x, data == 0x%02x, ret == %i)\n",
264 			__func__, reg, data, ret);
265 
266 	return (ret != 1) ? -EREMOTEIO : 0;
267 }
268 
269 static int si21_write(struct dvb_frontend *fe, const u8 buf[], int len)
270 {
271 	struct si21xx_state *state = fe->demodulator_priv;
272 
273 	if (len != 2)
274 		return -EINVAL;
275 
276 	return si21_writereg(state, buf[0], buf[1]);
277 }
278 
279 static u8 si21_readreg(struct si21xx_state *state, u8 reg)
280 {
281 	int ret;
282 	u8 b0[] = { reg };
283 	u8 b1[] = { 0 };
284 	struct i2c_msg msg[] = {
285 		{
286 			.addr = state->config->demod_address,
287 			.flags = 0,
288 			.buf = b0,
289 			.len = 1
290 		}, {
291 			.addr = state->config->demod_address,
292 			.flags = I2C_M_RD,
293 			.buf = b1,
294 			.len = 1
295 		}
296 	};
297 
298 	ret = i2c_transfer(state->i2c, msg, 2);
299 
300 	if (ret != 2)
301 		dprintk("%s: readreg error (reg == 0x%02x, ret == %i)\n",
302 			__func__, reg, ret);
303 
304 	return b1[0];
305 }
306 
307 static int si21_readregs(struct si21xx_state *state, u8 reg1, u8 *b, u8 len)
308 {
309 	int ret;
310 	struct i2c_msg msg[] = {
311 		{
312 			.addr = state->config->demod_address,
313 			.flags = 0,
314 			.buf = &reg1,
315 			.len = 1
316 		}, {
317 			.addr = state->config->demod_address,
318 			.flags = I2C_M_RD,
319 			.buf = b,
320 			.len = len
321 		}
322 	};
323 
324 	ret = i2c_transfer(state->i2c, msg, 2);
325 
326 	if (ret != 2)
327 		dprintk("%s: readreg error (ret == %i)\n", __func__, ret);
328 
329 	return ret == 2 ? 0 : -1;
330 }
331 
332 static int si21xx_wait_diseqc_idle(struct si21xx_state *state, int timeout)
333 {
334 	unsigned long start = jiffies;
335 
336 	dprintk("%s\n", __func__);
337 
338 	while ((si21_readreg(state, LNB_CTRL_REG_1) & 0x8) == 8) {
339 		if (jiffies - start > timeout) {
340 			dprintk("%s: timeout!!\n", __func__);
341 			return -ETIMEDOUT;
342 		}
343 		msleep(10);
344 	}
345 
346 	return 0;
347 }
348 
349 static int si21xx_set_symbolrate(struct dvb_frontend *fe, u32 srate)
350 {
351 	struct si21xx_state *state = fe->demodulator_priv;
352 	u32 sym_rate, data_rate;
353 	int i;
354 	u8 sym_rate_bytes[3];
355 
356 	dprintk("%s : srate = %i\n", __func__ , srate);
357 
358 	if ((srate < 1000000) || (srate > 45000000))
359 		return -EINVAL;
360 
361 	data_rate = srate;
362 	sym_rate = 0;
363 
364 	for (i = 0; i < 4; ++i) {
365 		sym_rate /= 100;
366 		sym_rate = sym_rate + ((data_rate % 100) * 0x800000) /
367 								state->fs;
368 		data_rate /= 100;
369 	}
370 	for (i = 0; i < 3; ++i)
371 		sym_rate_bytes[i] = (u8)((sym_rate >> (i * 8)) & 0xff);
372 
373 	si21_writeregs(state, SYM_RATE_REG_L, sym_rate_bytes, 0x03);
374 
375 	return 0;
376 }
377 
378 static int si21xx_send_diseqc_msg(struct dvb_frontend *fe,
379 					struct dvb_diseqc_master_cmd *m)
380 {
381 	struct si21xx_state *state = fe->demodulator_priv;
382 	u8 lnb_status;
383 	u8 LNB_CTRL_1;
384 	int status;
385 
386 	dprintk("%s\n", __func__);
387 
388 	status = PASS;
389 	LNB_CTRL_1 = 0;
390 
391 	status |= si21_readregs(state, LNB_CTRL_STATUS_REG, &lnb_status, 0x01);
392 	status |= si21_readregs(state, LNB_CTRL_REG_1, &lnb_status, 0x01);
393 
394 	/*fill the FIFO*/
395 	status |= si21_writeregs(state, LNB_FIFO_REGS_0, m->msg, m->msg_len);
396 
397 	LNB_CTRL_1 = (lnb_status & 0x70);
398 	LNB_CTRL_1 |= m->msg_len;
399 
400 	LNB_CTRL_1 |= 0x80;	/* begin LNB signaling */
401 
402 	status |= si21_writeregs(state, LNB_CTRL_REG_1, &LNB_CTRL_1, 0x01);
403 
404 	return status;
405 }
406 
407 static int si21xx_send_diseqc_burst(struct dvb_frontend *fe,
408 				    enum fe_sec_mini_cmd burst)
409 {
410 	struct si21xx_state *state = fe->demodulator_priv;
411 	u8 val;
412 
413 	dprintk("%s\n", __func__);
414 
415 	if (si21xx_wait_diseqc_idle(state, 100) < 0)
416 		return -ETIMEDOUT;
417 
418 	val = (0x80 | si21_readreg(state, 0xc1));
419 	if (si21_writereg(state, LNB_CTRL_REG_1,
420 			burst == SEC_MINI_A ? (val & ~0x10) : (val | 0x10)))
421 		return -EREMOTEIO;
422 
423 	if (si21xx_wait_diseqc_idle(state, 100) < 0)
424 		return -ETIMEDOUT;
425 
426 	if (si21_writereg(state, LNB_CTRL_REG_1, val))
427 		return -EREMOTEIO;
428 
429 	return 0;
430 }
431 /*	30.06.2008 */
432 static int si21xx_set_tone(struct dvb_frontend *fe, enum fe_sec_tone_mode tone)
433 {
434 	struct si21xx_state *state = fe->demodulator_priv;
435 	u8 val;
436 
437 	dprintk("%s\n", __func__);
438 	val = (0x80 | si21_readreg(state, LNB_CTRL_REG_1));
439 
440 	switch (tone) {
441 	case SEC_TONE_ON:
442 		return si21_writereg(state, LNB_CTRL_REG_1, val | 0x20);
443 
444 	case SEC_TONE_OFF:
445 		return si21_writereg(state, LNB_CTRL_REG_1, (val & ~0x20));
446 
447 	default:
448 		return -EINVAL;
449 	}
450 }
451 
452 static int si21xx_set_voltage(struct dvb_frontend *fe, enum fe_sec_voltage volt)
453 {
454 	struct si21xx_state *state = fe->demodulator_priv;
455 
456 	u8 val;
457 	dprintk("%s: %s\n", __func__,
458 		volt == SEC_VOLTAGE_13 ? "SEC_VOLTAGE_13" :
459 		volt == SEC_VOLTAGE_18 ? "SEC_VOLTAGE_18" : "??");
460 
461 
462 	val = (0x80 | si21_readreg(state, LNB_CTRL_REG_1));
463 
464 	switch (volt) {
465 	case SEC_VOLTAGE_18:
466 		return si21_writereg(state, LNB_CTRL_REG_1, val | 0x40);
467 		break;
468 	case SEC_VOLTAGE_13:
469 		return si21_writereg(state, LNB_CTRL_REG_1, (val & ~0x40));
470 		break;
471 	default:
472 		return -EINVAL;
473 	}
474 }
475 
476 static int si21xx_init(struct dvb_frontend *fe)
477 {
478 	struct si21xx_state *state = fe->demodulator_priv;
479 	int i;
480 	int status = 0;
481 	u8 reg1;
482 	u8 val;
483 	u8 reg2[2];
484 
485 	dprintk("%s\n", __func__);
486 
487 	for (i = 0; ; i += 2) {
488 		reg1 = serit_sp1511lhb_inittab[i];
489 		val = serit_sp1511lhb_inittab[i+1];
490 		if (reg1 == 0xff && val == 0xff)
491 			break;
492 		si21_writeregs(state, reg1, &val, 1);
493 	}
494 
495 	/*DVB QPSK SYSTEM MODE REG*/
496 	reg1 = 0x08;
497 	si21_writeregs(state, SYSTEM_MODE_REG, &reg1, 0x01);
498 
499 	/*transport stream config*/
500 	/*
501 	mode = PARALLEL;
502 	sdata_form = LSB_FIRST;
503 	clk_edge = FALLING_EDGE;
504 	clk_mode = CLK_GAPPED_MODE;
505 	strt_len = BYTE_WIDE;
506 	sync_pol = ACTIVE_HIGH;
507 	val_pol = ACTIVE_HIGH;
508 	err_pol = ACTIVE_HIGH;
509 	sclk_rate = 0x00;
510 	parity = 0x00 ;
511 	data_delay = 0x00;
512 	clk_delay = 0x00;
513 	pclk_smooth = 0x00;
514 	*/
515 	reg2[0] =
516 		PARALLEL + (LSB_FIRST << 1)
517 		+ (FALLING_EDGE << 2) + (CLK_GAPPED_MODE << 3)
518 		+ (BYTE_WIDE << 4) + (ACTIVE_HIGH << 5)
519 		+ (ACTIVE_HIGH << 6) + (ACTIVE_HIGH << 7);
520 
521 	reg2[1] = 0;
522 	/*	sclk_rate + (parity << 2)
523 		+ (data_delay << 3) + (clk_delay << 4)
524 		+ (pclk_smooth << 5);
525 	*/
526 	status |= si21_writeregs(state, TS_CTRL_REG_1, reg2, 0x02);
527 	if (status != 0)
528 		dprintk(" %s : TS Set Error\n", __func__);
529 
530 	return 0;
531 
532 }
533 
534 static int si21_read_status(struct dvb_frontend *fe, enum fe_status *status)
535 {
536 	struct si21xx_state *state = fe->demodulator_priv;
537 	u8 regs_read[2];
538 	u8 reg_read;
539 	u8 i;
540 	u8 lock;
541 	u8 signal = si21_readreg(state, ANALOG_AGC_POWER_LEVEL_REG);
542 
543 	si21_readregs(state, LOCK_STATUS_REG_1, regs_read, 0x02);
544 	reg_read = 0;
545 
546 	for (i = 0; i < 7; ++i)
547 		reg_read |= ((regs_read[0] >> i) & 0x01) << (6 - i);
548 
549 	lock = ((reg_read & 0x7f) | (regs_read[1] & 0x80));
550 
551 	dprintk("%s : FE_READ_STATUS : VSTATUS: 0x%02x\n", __func__, lock);
552 	*status = 0;
553 
554 	if (signal > 10)
555 		*status |= FE_HAS_SIGNAL;
556 
557 	if (lock & 0x2)
558 		*status |= FE_HAS_CARRIER;
559 
560 	if (lock & 0x20)
561 		*status |= FE_HAS_VITERBI;
562 
563 	if (lock & 0x40)
564 		*status |= FE_HAS_SYNC;
565 
566 	if ((lock & 0x7b) == 0x7b)
567 		*status |= FE_HAS_LOCK;
568 
569 	return 0;
570 }
571 
572 static int si21_read_signal_strength(struct dvb_frontend *fe, u16 *strength)
573 {
574 	struct si21xx_state *state = fe->demodulator_priv;
575 
576 	/*status = si21_readreg(state, ANALOG_AGC_POWER_LEVEL_REG,
577 						(u8*)agclevel, 0x01);*/
578 
579 	u16 signal = (3 * si21_readreg(state, 0x27) *
580 					si21_readreg(state, 0x28));
581 
582 	dprintk("%s : AGCPWR: 0x%02x%02x, signal=0x%04x\n", __func__,
583 		si21_readreg(state, 0x27),
584 		si21_readreg(state, 0x28), (int) signal);
585 
586 	signal  <<= 4;
587 	*strength = signal;
588 
589 	return 0;
590 }
591 
592 static int si21_read_ber(struct dvb_frontend *fe, u32 *ber)
593 {
594 	struct si21xx_state *state = fe->demodulator_priv;
595 
596 	dprintk("%s\n", __func__);
597 
598 	if (state->errmode != STATUS_BER)
599 		return 0;
600 
601 	*ber = (si21_readreg(state, 0x1d) << 8) |
602 				si21_readreg(state, 0x1e);
603 
604 	return 0;
605 }
606 
607 static int si21_read_snr(struct dvb_frontend *fe, u16 *snr)
608 {
609 	struct si21xx_state *state = fe->demodulator_priv;
610 
611 	s32 xsnr = 0xffff - ((si21_readreg(state, 0x24) << 8) |
612 					si21_readreg(state, 0x25));
613 	xsnr = 3 * (xsnr - 0xa100);
614 	*snr = (xsnr > 0xffff) ? 0xffff : (xsnr < 0) ? 0 : xsnr;
615 
616 	dprintk("%s\n", __func__);
617 
618 	return 0;
619 }
620 
621 static int si21_read_ucblocks(struct dvb_frontend *fe, u32 *ucblocks)
622 {
623 	struct si21xx_state *state = fe->demodulator_priv;
624 
625 	dprintk("%s\n", __func__);
626 
627 	if (state->errmode != STATUS_UCBLOCKS)
628 		*ucblocks = 0;
629 	else
630 		*ucblocks = (si21_readreg(state, 0x1d) << 8) |
631 					si21_readreg(state, 0x1e);
632 
633 	return 0;
634 }
635 
636 /*	initiates a channel acquisition sequence
637 	using the specified symbol rate and code rate */
638 static int si21xx_setacquire(struct dvb_frontend *fe, int symbrate,
639 			     enum fe_code_rate crate)
640 {
641 
642 	struct si21xx_state *state = fe->demodulator_priv;
643 	u8 coderates[] = {
644 				0x0, 0x01, 0x02, 0x04, 0x00,
645 				0x8, 0x10, 0x20, 0x00, 0x3f
646 	};
647 
648 	u8 coderate_ptr;
649 	int status;
650 	u8 start_acq = 0x80;
651 	u8 reg, regs[3];
652 
653 	dprintk("%s\n", __func__);
654 
655 	status = PASS;
656 	coderate_ptr = coderates[crate];
657 
658 	si21xx_set_symbolrate(fe, symbrate);
659 
660 	/* write code rates to use in the Viterbi search */
661 	status |= si21_writeregs(state,
662 				VIT_SRCH_CTRL_REG_1,
663 				&coderate_ptr, 0x01);
664 
665 	/* clear acq_start bit */
666 	status |= si21_readregs(state, ACQ_CTRL_REG_2, &reg, 0x01);
667 	reg &= ~start_acq;
668 	status |= si21_writeregs(state, ACQ_CTRL_REG_2, &reg, 0x01);
669 
670 	/* use new Carrier Frequency Offset Estimator (QuickLock) */
671 	regs[0] = 0xCB;
672 	regs[1] = 0x40;
673 	regs[2] = 0xCB;
674 
675 	status |= si21_writeregs(state,
676 				TWO_DB_BNDWDTH_THRSHLD_REG,
677 				&regs[0], 0x03);
678 	reg = 0x56;
679 	status |= si21_writeregs(state,
680 				LSA_CTRL_REG_1, &reg, 1);
681 	reg = 0x05;
682 	status |= si21_writeregs(state,
683 				BLIND_SCAN_CTRL_REG, &reg, 1);
684 	/* start automatic acq */
685 	status |= si21_writeregs(state,
686 				ACQ_CTRL_REG_2, &start_acq, 0x01);
687 
688 	return status;
689 }
690 
691 static int si21xx_set_frontend(struct dvb_frontend *fe)
692 {
693 	struct si21xx_state *state = fe->demodulator_priv;
694 	struct dtv_frontend_properties *c = &fe->dtv_property_cache;
695 
696 	/* freq		Channel carrier frequency in KHz (i.e. 1550000 KHz)
697 	 datarate	Channel symbol rate in Sps (i.e. 22500000 Sps)*/
698 
699 	/* in MHz */
700 	unsigned char coarse_tune_freq;
701 	int fine_tune_freq;
702 	unsigned char sample_rate = 0;
703 	/* boolean */
704 	bool inband_interferer_ind;
705 
706 	/* INTERMEDIATE VALUES */
707 	int icoarse_tune_freq; /* MHz */
708 	int ifine_tune_freq; /* MHz */
709 	unsigned int band_high;
710 	unsigned int band_low;
711 	unsigned int x1;
712 	unsigned int x2;
713 	int i;
714 	bool inband_interferer_div2[ALLOWABLE_FS_COUNT];
715 	bool inband_interferer_div4[ALLOWABLE_FS_COUNT];
716 	int status;
717 
718 	/* allowable sample rates for ADC in MHz */
719 	int afs[ALLOWABLE_FS_COUNT] = { 200, 192, 193, 194, 195,
720 					196, 204, 205, 206, 207
721 	};
722 	/* in MHz */
723 	int if_limit_high;
724 	int if_limit_low;
725 	int lnb_lo;
726 	int lnb_uncertanity;
727 
728 	int rf_freq;
729 	int data_rate;
730 	unsigned char regs[4];
731 
732 	dprintk("%s : FE_SET_FRONTEND\n", __func__);
733 
734 	if (c->delivery_system != SYS_DVBS) {
735 			dprintk("%s: unsupported delivery system selected (%d)\n",
736 				__func__, c->delivery_system);
737 			return -EOPNOTSUPP;
738 	}
739 
740 	for (i = 0; i < ALLOWABLE_FS_COUNT; ++i)
741 		inband_interferer_div2[i] = inband_interferer_div4[i] = false;
742 
743 	if_limit_high = -700000;
744 	if_limit_low = -100000;
745 	/* in MHz */
746 	lnb_lo = 0;
747 	lnb_uncertanity = 0;
748 
749 	rf_freq = 10 * c->frequency ;
750 	data_rate = c->symbol_rate / 100;
751 
752 	status = PASS;
753 
754 	band_low = (rf_freq - lnb_lo) - ((lnb_uncertanity * 200)
755 					+ (data_rate * 135)) / 200;
756 
757 	band_high = (rf_freq - lnb_lo) + ((lnb_uncertanity * 200)
758 					+ (data_rate * 135)) / 200;
759 
760 
761 	icoarse_tune_freq = 100000 *
762 				(((rf_freq - lnb_lo) -
763 					(if_limit_low + if_limit_high) / 2)
764 								/ 100000);
765 
766 	ifine_tune_freq = (rf_freq - lnb_lo) - icoarse_tune_freq ;
767 
768 	for (i = 0; i < ALLOWABLE_FS_COUNT; ++i) {
769 		x1 = ((rf_freq - lnb_lo) / (afs[i] * 2500)) *
770 					(afs[i] * 2500) + afs[i] * 2500;
771 
772 		x2 = ((rf_freq - lnb_lo) / (afs[i] * 2500)) *
773 							(afs[i] * 2500);
774 
775 		if (((band_low < x1) && (x1 < band_high)) ||
776 					((band_low < x2) && (x2 < band_high)))
777 					inband_interferer_div4[i] = true;
778 
779 	}
780 
781 	for (i = 0; i < ALLOWABLE_FS_COUNT; ++i) {
782 		x1 = ((rf_freq - lnb_lo) / (afs[i] * 5000)) *
783 					(afs[i] * 5000) + afs[i] * 5000;
784 
785 		x2 = ((rf_freq - lnb_lo) / (afs[i] * 5000)) *
786 					(afs[i] * 5000);
787 
788 		if (((band_low < x1) && (x1 < band_high)) ||
789 					((band_low < x2) && (x2 < band_high)))
790 					inband_interferer_div2[i] = true;
791 	}
792 
793 	inband_interferer_ind = true;
794 	for (i = 0; i < ALLOWABLE_FS_COUNT; ++i) {
795 		if (inband_interferer_div2[i] || inband_interferer_div4[i]) {
796 			inband_interferer_ind = false;
797 			break;
798 		}
799 	}
800 
801 	if (inband_interferer_ind) {
802 		for (i = 0; i < ALLOWABLE_FS_COUNT; ++i) {
803 			if (!inband_interferer_div2[i]) {
804 				sample_rate = (u8) afs[i];
805 				break;
806 			}
807 		}
808 	} else {
809 		for (i = 0; i < ALLOWABLE_FS_COUNT; ++i) {
810 			if ((inband_interferer_div2[i] ||
811 			     !inband_interferer_div4[i])) {
812 				sample_rate = (u8) afs[i];
813 				break;
814 			}
815 		}
816 
817 	}
818 
819 	if (sample_rate > 207 || sample_rate < 192)
820 		sample_rate = 200;
821 
822 	fine_tune_freq = ((0x4000 * (ifine_tune_freq / 10)) /
823 					((sample_rate) * 1000));
824 
825 	coarse_tune_freq = (u8)(icoarse_tune_freq / 100000);
826 
827 	regs[0] = sample_rate;
828 	regs[1] = coarse_tune_freq;
829 	regs[2] = fine_tune_freq & 0xFF;
830 	regs[3] = fine_tune_freq >> 8 & 0xFF;
831 
832 	status |= si21_writeregs(state, PLL_DIVISOR_REG, &regs[0], 0x04);
833 
834 	state->fs = sample_rate;/*ADC MHz*/
835 	si21xx_setacquire(fe, c->symbol_rate, c->fec_inner);
836 
837 	return 0;
838 }
839 
840 static int si21xx_sleep(struct dvb_frontend *fe)
841 {
842 	struct si21xx_state *state = fe->demodulator_priv;
843 	u8 regdata;
844 
845 	dprintk("%s\n", __func__);
846 
847 	si21_readregs(state, SYSTEM_MODE_REG, &regdata, 0x01);
848 	regdata |= 1 << 6;
849 	si21_writeregs(state, SYSTEM_MODE_REG, &regdata, 0x01);
850 	state->initialised = 0;
851 
852 	return 0;
853 }
854 
855 static void si21xx_release(struct dvb_frontend *fe)
856 {
857 	struct si21xx_state *state = fe->demodulator_priv;
858 
859 	dprintk("%s\n", __func__);
860 
861 	kfree(state);
862 }
863 
864 static const struct dvb_frontend_ops si21xx_ops = {
865 	.delsys = { SYS_DVBS },
866 	.info = {
867 		.name			= "SL SI21XX DVB-S",
868 		.frequency_min_hz	=  950 * MHz,
869 		.frequency_max_hz	= 2150 * MHz,
870 		.frequency_stepsize_hz	=  125 * kHz,
871 		.symbol_rate_min	= 1000000,
872 		.symbol_rate_max	= 45000000,
873 		.symbol_rate_tolerance	= 500,	/* ppm */
874 		.caps = FE_CAN_FEC_1_2 | FE_CAN_FEC_2_3 | FE_CAN_FEC_3_4 |
875 		FE_CAN_FEC_5_6 | FE_CAN_FEC_7_8 |
876 		FE_CAN_QPSK |
877 		FE_CAN_FEC_AUTO
878 	},
879 
880 	.release = si21xx_release,
881 	.init = si21xx_init,
882 	.sleep = si21xx_sleep,
883 	.write = si21_write,
884 	.read_status = si21_read_status,
885 	.read_ber = si21_read_ber,
886 	.read_signal_strength = si21_read_signal_strength,
887 	.read_snr = si21_read_snr,
888 	.read_ucblocks = si21_read_ucblocks,
889 	.diseqc_send_master_cmd = si21xx_send_diseqc_msg,
890 	.diseqc_send_burst = si21xx_send_diseqc_burst,
891 	.set_tone = si21xx_set_tone,
892 	.set_voltage = si21xx_set_voltage,
893 
894 	.set_frontend = si21xx_set_frontend,
895 };
896 
897 struct dvb_frontend *si21xx_attach(const struct si21xx_config *config,
898 						struct i2c_adapter *i2c)
899 {
900 	struct si21xx_state *state = NULL;
901 	int id;
902 
903 	dprintk("%s\n", __func__);
904 
905 	/* allocate memory for the internal state */
906 	state = kzalloc(sizeof(struct si21xx_state), GFP_KERNEL);
907 	if (state == NULL)
908 		goto error;
909 
910 	/* setup the state */
911 	state->config = config;
912 	state->i2c = i2c;
913 	state->initialised = 0;
914 	state->errmode = STATUS_BER;
915 
916 	/* check if the demod is there */
917 	id = si21_readreg(state, SYSTEM_MODE_REG);
918 	si21_writereg(state, SYSTEM_MODE_REG, id | 0x40); /* standby off */
919 	msleep(200);
920 	id = si21_readreg(state, 0x00);
921 
922 	/* register 0x00 contains:
923 		0x34 for SI2107
924 		0x24 for SI2108
925 		0x14 for SI2109
926 		0x04 for SI2110
927 	*/
928 	if (id != 0x04 && id != 0x14)
929 		goto error;
930 
931 	/* create dvb_frontend */
932 	memcpy(&state->frontend.ops, &si21xx_ops,
933 					sizeof(struct dvb_frontend_ops));
934 	state->frontend.demodulator_priv = state;
935 	return &state->frontend;
936 
937 error:
938 	kfree(state);
939 	return NULL;
940 }
941 EXPORT_SYMBOL(si21xx_attach);
942 
943 module_param(debug, int, 0644);
944 MODULE_PARM_DESC(debug, "Turn on/off frontend debugging (default:off).");
945 
946 MODULE_DESCRIPTION("SL SI21XX DVB Demodulator driver");
947 MODULE_AUTHOR("Igor M. Liplianin");
948 MODULE_LICENSE("GPL");
949