Linux kernel mirror (for testing)
git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel
os
linux
1/*
2 * Linux-DVB Driver for DiBcom's DiB8000 chip (ISDB-T).
3 *
4 * Copyright (C) 2009 DiBcom (http://www.dibcom.fr/)
5 *
6 * This program is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU General Public License as
8 * published by the Free Software Foundation, version 2.
9 */
10#include <linux/kernel.h>
11#include <linux/slab.h>
12#include <linux/i2c.h>
13#include "dvb_math.h"
14
15#include "dvb_frontend.h"
16
17#include "dib8000.h"
18
19#define LAYER_ALL -1
20#define LAYER_A 1
21#define LAYER_B 2
22#define LAYER_C 3
23
24#define FE_CALLBACK_TIME_NEVER 0xffffffff
25#define MAX_NUMBER_OF_FRONTENDS 6
26
27static int debug;
28module_param(debug, int, 0644);
29MODULE_PARM_DESC(debug, "turn on debugging (default: 0)");
30
31#define dprintk(args...) do { if (debug) { printk(KERN_DEBUG "DiB8000: "); printk(args); printk("\n"); } } while (0)
32
33#define FE_STATUS_TUNE_FAILED 0
34
35struct i2c_device {
36 struct i2c_adapter *adap;
37 u8 addr;
38 u8 *i2c_write_buffer;
39 u8 *i2c_read_buffer;
40};
41
42struct dib8000_state {
43 struct dib8000_config cfg;
44
45 struct i2c_device i2c;
46
47 struct dibx000_i2c_master i2c_master;
48
49 u16 wbd_ref;
50
51 u8 current_band;
52 u32 current_bandwidth;
53 struct dibx000_agc_config *current_agc;
54 u32 timf;
55 u32 timf_default;
56
57 u8 div_force_off:1;
58 u8 div_state:1;
59 u16 div_sync_wait;
60
61 u8 agc_state;
62 u8 differential_constellation;
63 u8 diversity_onoff;
64
65 s16 ber_monitored_layer;
66 u16 gpio_dir;
67 u16 gpio_val;
68
69 u16 revision;
70 u8 isdbt_cfg_loaded;
71 enum frontend_tune_state tune_state;
72 u32 status;
73
74 struct dvb_frontend *fe[MAX_NUMBER_OF_FRONTENDS];
75
76 /* for the I2C transfer */
77 struct i2c_msg msg[2];
78 u8 i2c_write_buffer[4];
79 u8 i2c_read_buffer[2];
80};
81
82enum dib8000_power_mode {
83 DIB8000M_POWER_ALL = 0,
84 DIB8000M_POWER_INTERFACE_ONLY,
85};
86
87static u16 dib8000_i2c_read16(struct i2c_device *i2c, u16 reg)
88{
89 struct i2c_msg msg[2] = {
90 {.addr = i2c->addr >> 1, .flags = 0,
91 .buf = i2c->i2c_write_buffer, .len = 2},
92 {.addr = i2c->addr >> 1, .flags = I2C_M_RD,
93 .buf = i2c->i2c_read_buffer, .len = 2},
94 };
95
96 msg[0].buf[0] = reg >> 8;
97 msg[0].buf[1] = reg & 0xff;
98
99 if (i2c_transfer(i2c->adap, msg, 2) != 2)
100 dprintk("i2c read error on %d", reg);
101
102 return (msg[1].buf[0] << 8) | msg[1].buf[1];
103}
104
105static u16 dib8000_read_word(struct dib8000_state *state, u16 reg)
106{
107 state->i2c_write_buffer[0] = reg >> 8;
108 state->i2c_write_buffer[1] = reg & 0xff;
109
110 memset(state->msg, 0, 2 * sizeof(struct i2c_msg));
111 state->msg[0].addr = state->i2c.addr >> 1;
112 state->msg[0].flags = 0;
113 state->msg[0].buf = state->i2c_write_buffer;
114 state->msg[0].len = 2;
115 state->msg[1].addr = state->i2c.addr >> 1;
116 state->msg[1].flags = I2C_M_RD;
117 state->msg[1].buf = state->i2c_read_buffer;
118 state->msg[1].len = 2;
119
120 if (i2c_transfer(state->i2c.adap, state->msg, 2) != 2)
121 dprintk("i2c read error on %d", reg);
122
123 return (state->i2c_read_buffer[0] << 8) | state->i2c_read_buffer[1];
124}
125
126static u32 dib8000_read32(struct dib8000_state *state, u16 reg)
127{
128 u16 rw[2];
129
130 rw[0] = dib8000_read_word(state, reg + 0);
131 rw[1] = dib8000_read_word(state, reg + 1);
132
133 return ((rw[0] << 16) | (rw[1]));
134}
135
136static int dib8000_i2c_write16(struct i2c_device *i2c, u16 reg, u16 val)
137{
138 struct i2c_msg msg = {.addr = i2c->addr >> 1, .flags = 0,
139 .buf = i2c->i2c_write_buffer, .len = 4};
140 int ret = 0;
141
142 msg.buf[0] = (reg >> 8) & 0xff;
143 msg.buf[1] = reg & 0xff;
144 msg.buf[2] = (val >> 8) & 0xff;
145 msg.buf[3] = val & 0xff;
146
147 ret = i2c_transfer(i2c->adap, &msg, 1) != 1 ? -EREMOTEIO : 0;
148
149 return ret;
150}
151
152static int dib8000_write_word(struct dib8000_state *state, u16 reg, u16 val)
153{
154 state->i2c_write_buffer[0] = (reg >> 8) & 0xff;
155 state->i2c_write_buffer[1] = reg & 0xff;
156 state->i2c_write_buffer[2] = (val >> 8) & 0xff;
157 state->i2c_write_buffer[3] = val & 0xff;
158
159 memset(&state->msg[0], 0, sizeof(struct i2c_msg));
160 state->msg[0].addr = state->i2c.addr >> 1;
161 state->msg[0].flags = 0;
162 state->msg[0].buf = state->i2c_write_buffer;
163 state->msg[0].len = 4;
164
165 return i2c_transfer(state->i2c.adap, state->msg, 1) != 1 ? -EREMOTEIO : 0;
166}
167
168static const s16 coeff_2k_sb_1seg_dqpsk[8] = {
169 (769 << 5) | 0x0a, (745 << 5) | 0x03, (595 << 5) | 0x0d, (769 << 5) | 0x0a, (920 << 5) | 0x09, (784 << 5) | 0x02, (519 << 5) | 0x0c,
170 (920 << 5) | 0x09
171};
172
173static const s16 coeff_2k_sb_1seg[8] = {
174 (692 << 5) | 0x0b, (683 << 5) | 0x01, (519 << 5) | 0x09, (692 << 5) | 0x0b, 0 | 0x1f, 0 | 0x1f, 0 | 0x1f, 0 | 0x1f
175};
176
177static const s16 coeff_2k_sb_3seg_0dqpsk_1dqpsk[8] = {
178 (832 << 5) | 0x10, (912 << 5) | 0x05, (900 << 5) | 0x12, (832 << 5) | 0x10, (-931 << 5) | 0x0f, (912 << 5) | 0x04, (807 << 5) | 0x11,
179 (-931 << 5) | 0x0f
180};
181
182static const s16 coeff_2k_sb_3seg_0dqpsk[8] = {
183 (622 << 5) | 0x0c, (941 << 5) | 0x04, (796 << 5) | 0x10, (622 << 5) | 0x0c, (982 << 5) | 0x0c, (519 << 5) | 0x02, (572 << 5) | 0x0e,
184 (982 << 5) | 0x0c
185};
186
187static const s16 coeff_2k_sb_3seg_1dqpsk[8] = {
188 (699 << 5) | 0x14, (607 << 5) | 0x04, (944 << 5) | 0x13, (699 << 5) | 0x14, (-720 << 5) | 0x0d, (640 << 5) | 0x03, (866 << 5) | 0x12,
189 (-720 << 5) | 0x0d
190};
191
192static const s16 coeff_2k_sb_3seg[8] = {
193 (664 << 5) | 0x0c, (925 << 5) | 0x03, (937 << 5) | 0x10, (664 << 5) | 0x0c, (-610 << 5) | 0x0a, (697 << 5) | 0x01, (836 << 5) | 0x0e,
194 (-610 << 5) | 0x0a
195};
196
197static const s16 coeff_4k_sb_1seg_dqpsk[8] = {
198 (-955 << 5) | 0x0e, (687 << 5) | 0x04, (818 << 5) | 0x10, (-955 << 5) | 0x0e, (-922 << 5) | 0x0d, (750 << 5) | 0x03, (665 << 5) | 0x0f,
199 (-922 << 5) | 0x0d
200};
201
202static const s16 coeff_4k_sb_1seg[8] = {
203 (638 << 5) | 0x0d, (683 << 5) | 0x02, (638 << 5) | 0x0d, (638 << 5) | 0x0d, (-655 << 5) | 0x0a, (517 << 5) | 0x00, (698 << 5) | 0x0d,
204 (-655 << 5) | 0x0a
205};
206
207static const s16 coeff_4k_sb_3seg_0dqpsk_1dqpsk[8] = {
208 (-707 << 5) | 0x14, (910 << 5) | 0x06, (889 << 5) | 0x16, (-707 << 5) | 0x14, (-958 << 5) | 0x13, (993 << 5) | 0x05, (523 << 5) | 0x14,
209 (-958 << 5) | 0x13
210};
211
212static const s16 coeff_4k_sb_3seg_0dqpsk[8] = {
213 (-723 << 5) | 0x13, (910 << 5) | 0x05, (777 << 5) | 0x14, (-723 << 5) | 0x13, (-568 << 5) | 0x0f, (547 << 5) | 0x03, (696 << 5) | 0x12,
214 (-568 << 5) | 0x0f
215};
216
217static const s16 coeff_4k_sb_3seg_1dqpsk[8] = {
218 (-940 << 5) | 0x15, (607 << 5) | 0x05, (915 << 5) | 0x16, (-940 << 5) | 0x15, (-848 << 5) | 0x13, (683 << 5) | 0x04, (543 << 5) | 0x14,
219 (-848 << 5) | 0x13
220};
221
222static const s16 coeff_4k_sb_3seg[8] = {
223 (612 << 5) | 0x12, (910 << 5) | 0x04, (864 << 5) | 0x14, (612 << 5) | 0x12, (-869 << 5) | 0x13, (683 << 5) | 0x02, (869 << 5) | 0x12,
224 (-869 << 5) | 0x13
225};
226
227static const s16 coeff_8k_sb_1seg_dqpsk[8] = {
228 (-835 << 5) | 0x12, (684 << 5) | 0x05, (735 << 5) | 0x14, (-835 << 5) | 0x12, (-598 << 5) | 0x10, (781 << 5) | 0x04, (739 << 5) | 0x13,
229 (-598 << 5) | 0x10
230};
231
232static const s16 coeff_8k_sb_1seg[8] = {
233 (673 << 5) | 0x0f, (683 << 5) | 0x03, (808 << 5) | 0x12, (673 << 5) | 0x0f, (585 << 5) | 0x0f, (512 << 5) | 0x01, (780 << 5) | 0x0f,
234 (585 << 5) | 0x0f
235};
236
237static const s16 coeff_8k_sb_3seg_0dqpsk_1dqpsk[8] = {
238 (863 << 5) | 0x17, (930 << 5) | 0x07, (878 << 5) | 0x19, (863 << 5) | 0x17, (0 << 5) | 0x14, (521 << 5) | 0x05, (980 << 5) | 0x18,
239 (0 << 5) | 0x14
240};
241
242static const s16 coeff_8k_sb_3seg_0dqpsk[8] = {
243 (-924 << 5) | 0x17, (910 << 5) | 0x06, (774 << 5) | 0x17, (-924 << 5) | 0x17, (-877 << 5) | 0x15, (565 << 5) | 0x04, (553 << 5) | 0x15,
244 (-877 << 5) | 0x15
245};
246
247static const s16 coeff_8k_sb_3seg_1dqpsk[8] = {
248 (-921 << 5) | 0x19, (607 << 5) | 0x06, (881 << 5) | 0x19, (-921 << 5) | 0x19, (-921 << 5) | 0x14, (713 << 5) | 0x05, (1018 << 5) | 0x18,
249 (-921 << 5) | 0x14
250};
251
252static const s16 coeff_8k_sb_3seg[8] = {
253 (514 << 5) | 0x14, (910 << 5) | 0x05, (861 << 5) | 0x17, (514 << 5) | 0x14, (690 << 5) | 0x14, (683 << 5) | 0x03, (662 << 5) | 0x15,
254 (690 << 5) | 0x14
255};
256
257static const s16 ana_fe_coeff_3seg[24] = {
258 81, 80, 78, 74, 68, 61, 54, 45, 37, 28, 19, 11, 4, 1022, 1017, 1013, 1010, 1008, 1008, 1008, 1008, 1010, 1014, 1017
259};
260
261static const s16 ana_fe_coeff_1seg[24] = {
262 249, 226, 164, 82, 5, 981, 970, 988, 1018, 20, 31, 26, 8, 1012, 1000, 1018, 1012, 8, 15, 14, 9, 3, 1017, 1003
263};
264
265static const s16 ana_fe_coeff_13seg[24] = {
266 396, 305, 105, -51, -77, -12, 41, 31, -11, -30, -11, 14, 15, -2, -13, -7, 5, 8, 1, -6, -7, -3, 0, 1
267};
268
269static u16 fft_to_mode(struct dib8000_state *state)
270{
271 u16 mode;
272 switch (state->fe[0]->dtv_property_cache.transmission_mode) {
273 case TRANSMISSION_MODE_2K:
274 mode = 1;
275 break;
276 case TRANSMISSION_MODE_4K:
277 mode = 2;
278 break;
279 default:
280 case TRANSMISSION_MODE_AUTO:
281 case TRANSMISSION_MODE_8K:
282 mode = 3;
283 break;
284 }
285 return mode;
286}
287
288static void dib8000_set_acquisition_mode(struct dib8000_state *state)
289{
290 u16 nud = dib8000_read_word(state, 298);
291 nud |= (1 << 3) | (1 << 0);
292 dprintk("acquisition mode activated");
293 dib8000_write_word(state, 298, nud);
294}
295static int dib8000_set_output_mode(struct dvb_frontend *fe, int mode)
296{
297 struct dib8000_state *state = fe->demodulator_priv;
298
299 u16 outreg, fifo_threshold, smo_mode, sram = 0x0205; /* by default SDRAM deintlv is enabled */
300
301 outreg = 0;
302 fifo_threshold = 1792;
303 smo_mode = (dib8000_read_word(state, 299) & 0x0050) | (1 << 1);
304
305 dprintk("-I- Setting output mode for demod %p to %d",
306 &state->fe[0], mode);
307
308 switch (mode) {
309 case OUTMODE_MPEG2_PAR_GATED_CLK: // STBs with parallel gated clock
310 outreg = (1 << 10); /* 0x0400 */
311 break;
312 case OUTMODE_MPEG2_PAR_CONT_CLK: // STBs with parallel continues clock
313 outreg = (1 << 10) | (1 << 6); /* 0x0440 */
314 break;
315 case OUTMODE_MPEG2_SERIAL: // STBs with serial input
316 outreg = (1 << 10) | (2 << 6) | (0 << 1); /* 0x0482 */
317 break;
318 case OUTMODE_DIVERSITY:
319 if (state->cfg.hostbus_diversity) {
320 outreg = (1 << 10) | (4 << 6); /* 0x0500 */
321 sram &= 0xfdff;
322 } else
323 sram |= 0x0c00;
324 break;
325 case OUTMODE_MPEG2_FIFO: // e.g. USB feeding
326 smo_mode |= (3 << 1);
327 fifo_threshold = 512;
328 outreg = (1 << 10) | (5 << 6);
329 break;
330 case OUTMODE_HIGH_Z: // disable
331 outreg = 0;
332 break;
333
334 case OUTMODE_ANALOG_ADC:
335 outreg = (1 << 10) | (3 << 6);
336 dib8000_set_acquisition_mode(state);
337 break;
338
339 default:
340 dprintk("Unhandled output_mode passed to be set for demod %p",
341 &state->fe[0]);
342 return -EINVAL;
343 }
344
345 if (state->cfg.output_mpeg2_in_188_bytes)
346 smo_mode |= (1 << 5);
347
348 dib8000_write_word(state, 299, smo_mode);
349 dib8000_write_word(state, 300, fifo_threshold); /* synchronous fread */
350 dib8000_write_word(state, 1286, outreg);
351 dib8000_write_word(state, 1291, sram);
352
353 return 0;
354}
355
356static int dib8000_set_diversity_in(struct dvb_frontend *fe, int onoff)
357{
358 struct dib8000_state *state = fe->demodulator_priv;
359 u16 sync_wait = dib8000_read_word(state, 273) & 0xfff0;
360
361 if (!state->differential_constellation) {
362 dib8000_write_word(state, 272, 1 << 9); //dvsy_off_lmod4 = 1
363 dib8000_write_word(state, 273, sync_wait | (1 << 2) | 2); // sync_enable = 1; comb_mode = 2
364 } else {
365 dib8000_write_word(state, 272, 0); //dvsy_off_lmod4 = 0
366 dib8000_write_word(state, 273, sync_wait); // sync_enable = 0; comb_mode = 0
367 }
368 state->diversity_onoff = onoff;
369
370 switch (onoff) {
371 case 0: /* only use the internal way - not the diversity input */
372 dib8000_write_word(state, 270, 1);
373 dib8000_write_word(state, 271, 0);
374 break;
375 case 1: /* both ways */
376 dib8000_write_word(state, 270, 6);
377 dib8000_write_word(state, 271, 6);
378 break;
379 case 2: /* only the diversity input */
380 dib8000_write_word(state, 270, 0);
381 dib8000_write_word(state, 271, 1);
382 break;
383 }
384 return 0;
385}
386
387static void dib8000_set_power_mode(struct dib8000_state *state, enum dib8000_power_mode mode)
388{
389 /* by default everything is going to be powered off */
390 u16 reg_774 = 0x3fff, reg_775 = 0xffff, reg_776 = 0xffff,
391 reg_900 = (dib8000_read_word(state, 900) & 0xfffc) | 0x3,
392 reg_1280 = (dib8000_read_word(state, 1280) & 0x00ff) | 0xff00;
393
394 /* now, depending on the requested mode, we power on */
395 switch (mode) {
396 /* power up everything in the demod */
397 case DIB8000M_POWER_ALL:
398 reg_774 = 0x0000;
399 reg_775 = 0x0000;
400 reg_776 = 0x0000;
401 reg_900 &= 0xfffc;
402 reg_1280 &= 0x00ff;
403 break;
404 case DIB8000M_POWER_INTERFACE_ONLY:
405 reg_1280 &= 0x00ff;
406 break;
407 }
408
409 dprintk("powermode : 774 : %x ; 775 : %x; 776 : %x ; 900 : %x; 1280 : %x", reg_774, reg_775, reg_776, reg_900, reg_1280);
410 dib8000_write_word(state, 774, reg_774);
411 dib8000_write_word(state, 775, reg_775);
412 dib8000_write_word(state, 776, reg_776);
413 dib8000_write_word(state, 900, reg_900);
414 dib8000_write_word(state, 1280, reg_1280);
415}
416
417static int dib8000_set_adc_state(struct dib8000_state *state, enum dibx000_adc_states no)
418{
419 int ret = 0;
420 u16 reg_907 = dib8000_read_word(state, 907), reg_908 = dib8000_read_word(state, 908);
421
422 switch (no) {
423 case DIBX000_SLOW_ADC_ON:
424 reg_908 |= (1 << 1) | (1 << 0);
425 ret |= dib8000_write_word(state, 908, reg_908);
426 reg_908 &= ~(1 << 1);
427 break;
428
429 case DIBX000_SLOW_ADC_OFF:
430 reg_908 |= (1 << 1) | (1 << 0);
431 break;
432
433 case DIBX000_ADC_ON:
434 reg_907 &= 0x0fff;
435 reg_908 &= 0x0003;
436 break;
437
438 case DIBX000_ADC_OFF: // leave the VBG voltage on
439 reg_907 |= (1 << 14) | (1 << 13) | (1 << 12);
440 reg_908 |= (1 << 5) | (1 << 4) | (1 << 3) | (1 << 2);
441 break;
442
443 case DIBX000_VBG_ENABLE:
444 reg_907 &= ~(1 << 15);
445 break;
446
447 case DIBX000_VBG_DISABLE:
448 reg_907 |= (1 << 15);
449 break;
450
451 default:
452 break;
453 }
454
455 ret |= dib8000_write_word(state, 907, reg_907);
456 ret |= dib8000_write_word(state, 908, reg_908);
457
458 return ret;
459}
460
461static int dib8000_set_bandwidth(struct dvb_frontend *fe, u32 bw)
462{
463 struct dib8000_state *state = fe->demodulator_priv;
464 u32 timf;
465
466 if (bw == 0)
467 bw = 6000;
468
469 if (state->timf == 0) {
470 dprintk("using default timf");
471 timf = state->timf_default;
472 } else {
473 dprintk("using updated timf");
474 timf = state->timf;
475 }
476
477 dib8000_write_word(state, 29, (u16) ((timf >> 16) & 0xffff));
478 dib8000_write_word(state, 30, (u16) ((timf) & 0xffff));
479
480 return 0;
481}
482
483static int dib8000_sad_calib(struct dib8000_state *state)
484{
485/* internal */
486 dib8000_write_word(state, 923, (0 << 1) | (0 << 0));
487 dib8000_write_word(state, 924, 776); // 0.625*3.3 / 4096
488
489 /* do the calibration */
490 dib8000_write_word(state, 923, (1 << 0));
491 dib8000_write_word(state, 923, (0 << 0));
492
493 msleep(1);
494 return 0;
495}
496
497int dib8000_set_wbd_ref(struct dvb_frontend *fe, u16 value)
498{
499 struct dib8000_state *state = fe->demodulator_priv;
500 if (value > 4095)
501 value = 4095;
502 state->wbd_ref = value;
503 return dib8000_write_word(state, 106, value);
504}
505
506EXPORT_SYMBOL(dib8000_set_wbd_ref);
507static void dib8000_reset_pll_common(struct dib8000_state *state, const struct dibx000_bandwidth_config *bw)
508{
509 dprintk("ifreq: %d %x, inversion: %d", bw->ifreq, bw->ifreq, bw->ifreq >> 25);
510 dib8000_write_word(state, 23, (u16) (((bw->internal * 1000) >> 16) & 0xffff)); /* P_sec_len */
511 dib8000_write_word(state, 24, (u16) ((bw->internal * 1000) & 0xffff));
512 dib8000_write_word(state, 27, (u16) ((bw->ifreq >> 16) & 0x01ff));
513 dib8000_write_word(state, 28, (u16) (bw->ifreq & 0xffff));
514 dib8000_write_word(state, 26, (u16) ((bw->ifreq >> 25) & 0x0003));
515
516 dib8000_write_word(state, 922, bw->sad_cfg);
517}
518
519static void dib8000_reset_pll(struct dib8000_state *state)
520{
521 const struct dibx000_bandwidth_config *pll = state->cfg.pll;
522 u16 clk_cfg1;
523
524 // clk_cfg0
525 dib8000_write_word(state, 901, (pll->pll_prediv << 8) | (pll->pll_ratio << 0));
526
527 // clk_cfg1
528 clk_cfg1 = (1 << 10) | (0 << 9) | (pll->IO_CLK_en_core << 8) |
529 (pll->bypclk_div << 5) | (pll->enable_refdiv << 4) | (1 << 3) |
530 (pll->pll_range << 1) | (pll->pll_reset << 0);
531
532 dib8000_write_word(state, 902, clk_cfg1);
533 clk_cfg1 = (clk_cfg1 & 0xfff7) | (pll->pll_bypass << 3);
534 dib8000_write_word(state, 902, clk_cfg1);
535
536 dprintk("clk_cfg1: 0x%04x", clk_cfg1); /* 0x507 1 0 1 000 0 0 11 1 */
537
538 /* smpl_cfg: P_refclksel=2, P_ensmplsel=1 nodivsmpl=1 */
539 if (state->cfg.pll->ADClkSrc == 0)
540 dib8000_write_word(state, 904, (0 << 15) | (0 << 12) | (0 << 10) |
541 (pll->modulo << 8) | (pll->ADClkSrc << 7) | (0 << 1));
542 else if (state->cfg.refclksel != 0)
543 dib8000_write_word(state, 904, (0 << 15) | (1 << 12) |
544 ((state->cfg.refclksel & 0x3) << 10) | (pll->modulo << 8) |
545 (pll->ADClkSrc << 7) | (0 << 1));
546 else
547 dib8000_write_word(state, 904, (0 << 15) | (1 << 12) | (3 << 10) | (pll->modulo << 8) | (pll->ADClkSrc << 7) | (0 << 1));
548
549 dib8000_reset_pll_common(state, pll);
550}
551
552static int dib8000_reset_gpio(struct dib8000_state *st)
553{
554 /* reset the GPIOs */
555 dib8000_write_word(st, 1029, st->cfg.gpio_dir);
556 dib8000_write_word(st, 1030, st->cfg.gpio_val);
557
558 /* TODO 782 is P_gpio_od */
559
560 dib8000_write_word(st, 1032, st->cfg.gpio_pwm_pos);
561
562 dib8000_write_word(st, 1037, st->cfg.pwm_freq_div);
563 return 0;
564}
565
566static int dib8000_cfg_gpio(struct dib8000_state *st, u8 num, u8 dir, u8 val)
567{
568 st->cfg.gpio_dir = dib8000_read_word(st, 1029);
569 st->cfg.gpio_dir &= ~(1 << num); /* reset the direction bit */
570 st->cfg.gpio_dir |= (dir & 0x1) << num; /* set the new direction */
571 dib8000_write_word(st, 1029, st->cfg.gpio_dir);
572
573 st->cfg.gpio_val = dib8000_read_word(st, 1030);
574 st->cfg.gpio_val &= ~(1 << num); /* reset the direction bit */
575 st->cfg.gpio_val |= (val & 0x01) << num; /* set the new value */
576 dib8000_write_word(st, 1030, st->cfg.gpio_val);
577
578 dprintk("gpio dir: %x: gpio val: %x", st->cfg.gpio_dir, st->cfg.gpio_val);
579
580 return 0;
581}
582
583int dib8000_set_gpio(struct dvb_frontend *fe, u8 num, u8 dir, u8 val)
584{
585 struct dib8000_state *state = fe->demodulator_priv;
586 return dib8000_cfg_gpio(state, num, dir, val);
587}
588
589EXPORT_SYMBOL(dib8000_set_gpio);
590static const u16 dib8000_defaults[] = {
591 /* auto search configuration - lock0 by default waiting
592 * for cpil_lock; lock1 cpil_lock; lock2 tmcc_sync_lock */
593 3, 7,
594 0x0004,
595 0x0400,
596 0x0814,
597
598 12, 11,
599 0x001b,
600 0x7740,
601 0x005b,
602 0x8d80,
603 0x01c9,
604 0xc380,
605 0x0000,
606 0x0080,
607 0x0000,
608 0x0090,
609 0x0001,
610 0xd4c0,
611
612 /*1, 32,
613 0x6680 // P_corm_thres Lock algorithms configuration */
614
615 11, 80, /* set ADC level to -16 */
616 (1 << 13) - 825 - 117,
617 (1 << 13) - 837 - 117,
618 (1 << 13) - 811 - 117,
619 (1 << 13) - 766 - 117,
620 (1 << 13) - 737 - 117,
621 (1 << 13) - 693 - 117,
622 (1 << 13) - 648 - 117,
623 (1 << 13) - 619 - 117,
624 (1 << 13) - 575 - 117,
625 (1 << 13) - 531 - 117,
626 (1 << 13) - 501 - 117,
627
628 4, 108,
629 0,
630 0,
631 0,
632 0,
633
634 1, 175,
635 0x0410,
636 1, 179,
637 8192, // P_fft_nb_to_cut
638
639 6, 181,
640 0x2800, // P_coff_corthres_ ( 2k 4k 8k ) 0x2800
641 0x2800,
642 0x2800,
643 0x2800, // P_coff_cpilthres_ ( 2k 4k 8k ) 0x2800
644 0x2800,
645 0x2800,
646
647 2, 193,
648 0x0666, // P_pha3_thres
649 0x0000, // P_cti_use_cpe, P_cti_use_prog
650
651 2, 205,
652 0x200f, // P_cspu_regul, P_cspu_win_cut
653 0x000f, // P_des_shift_work
654
655 5, 215,
656 0x023d, // P_adp_regul_cnt
657 0x00a4, // P_adp_noise_cnt
658 0x00a4, // P_adp_regul_ext
659 0x7ff0, // P_adp_noise_ext
660 0x3ccc, // P_adp_fil
661
662 1, 230,
663 0x0000, // P_2d_byp_ti_num
664
665 1, 263,
666 0x800, //P_equal_thres_wgn
667
668 1, 268,
669 (2 << 9) | 39, // P_equal_ctrl_synchro, P_equal_speedmode
670
671 1, 270,
672 0x0001, // P_div_lock0_wait
673 1, 285,
674 0x0020, //p_fec_
675 1, 299,
676 0x0062, /* P_smo_mode, P_smo_rs_discard, P_smo_fifo_flush, P_smo_pid_parse, P_smo_error_discard */
677
678 1, 338,
679 (1 << 12) | // P_ctrl_corm_thres4pre_freq_inh=1
680 (1 << 10) |
681 (0 << 9) | /* P_ctrl_pre_freq_inh=0 */
682 (3 << 5) | /* P_ctrl_pre_freq_step=3 */
683 (1 << 0), /* P_pre_freq_win_len=1 */
684
685 1, 903,
686 (0 << 4) | 2, // P_divclksel=0 P_divbitsel=2 (was clk=3,bit=1 for MPW)
687
688 0,
689};
690
691static u16 dib8000_identify(struct i2c_device *client)
692{
693 u16 value;
694
695 //because of glitches sometimes
696 value = dib8000_i2c_read16(client, 896);
697
698 if ((value = dib8000_i2c_read16(client, 896)) != 0x01b3) {
699 dprintk("wrong Vendor ID (read=0x%x)", value);
700 return 0;
701 }
702
703 value = dib8000_i2c_read16(client, 897);
704 if (value != 0x8000 && value != 0x8001 && value != 0x8002) {
705 dprintk("wrong Device ID (%x)", value);
706 return 0;
707 }
708
709 switch (value) {
710 case 0x8000:
711 dprintk("found DiB8000A");
712 break;
713 case 0x8001:
714 dprintk("found DiB8000B");
715 break;
716 case 0x8002:
717 dprintk("found DiB8000C");
718 break;
719 }
720 return value;
721}
722
723static int dib8000_reset(struct dvb_frontend *fe)
724{
725 struct dib8000_state *state = fe->demodulator_priv;
726
727 dib8000_write_word(state, 1287, 0x0003); /* sram lead in, rdy */
728
729 if ((state->revision = dib8000_identify(&state->i2c)) == 0)
730 return -EINVAL;
731
732 if (state->revision == 0x8000)
733 dprintk("error : dib8000 MA not supported");
734
735 dibx000_reset_i2c_master(&state->i2c_master);
736
737 dib8000_set_power_mode(state, DIB8000M_POWER_ALL);
738
739 /* always leave the VBG voltage on - it consumes almost nothing but takes a long time to start */
740 dib8000_set_adc_state(state, DIBX000_VBG_ENABLE);
741
742 /* restart all parts */
743 dib8000_write_word(state, 770, 0xffff);
744 dib8000_write_word(state, 771, 0xffff);
745 dib8000_write_word(state, 772, 0xfffc);
746 dib8000_write_word(state, 898, 0x000c); // sad
747 dib8000_write_word(state, 1280, 0x004d);
748 dib8000_write_word(state, 1281, 0x000c);
749
750 dib8000_write_word(state, 770, 0x0000);
751 dib8000_write_word(state, 771, 0x0000);
752 dib8000_write_word(state, 772, 0x0000);
753 dib8000_write_word(state, 898, 0x0004); // sad
754 dib8000_write_word(state, 1280, 0x0000);
755 dib8000_write_word(state, 1281, 0x0000);
756
757 /* drives */
758 if (state->cfg.drives)
759 dib8000_write_word(state, 906, state->cfg.drives);
760 else {
761 dprintk("using standard PAD-drive-settings, please adjust settings in config-struct to be optimal.");
762 dib8000_write_word(state, 906, 0x2d98); // min drive SDRAM - not optimal - adjust
763 }
764
765 dib8000_reset_pll(state);
766
767 if (dib8000_reset_gpio(state) != 0)
768 dprintk("GPIO reset was not successful.");
769
770 if (dib8000_set_output_mode(fe, OUTMODE_HIGH_Z) != 0)
771 dprintk("OUTPUT_MODE could not be resetted.");
772
773 state->current_agc = NULL;
774
775 // P_iqc_alpha_pha, P_iqc_alpha_amp, P_iqc_dcc_alpha, ...
776 /* P_iqc_ca2 = 0; P_iqc_impnc_on = 0; P_iqc_mode = 0; */
777 if (state->cfg.pll->ifreq == 0)
778 dib8000_write_word(state, 40, 0x0755); /* P_iqc_corr_inh = 0 enable IQcorr block */
779 else
780 dib8000_write_word(state, 40, 0x1f55); /* P_iqc_corr_inh = 1 disable IQcorr block */
781
782 {
783 u16 l = 0, r;
784 const u16 *n;
785 n = dib8000_defaults;
786 l = *n++;
787 while (l) {
788 r = *n++;
789 do {
790 dib8000_write_word(state, r, *n++);
791 r++;
792 } while (--l);
793 l = *n++;
794 }
795 }
796 state->isdbt_cfg_loaded = 0;
797
798 //div_cfg override for special configs
799 if (state->cfg.div_cfg != 0)
800 dib8000_write_word(state, 903, state->cfg.div_cfg);
801
802 /* unforce divstr regardless whether i2c enumeration was done or not */
803 dib8000_write_word(state, 1285, dib8000_read_word(state, 1285) & ~(1 << 1));
804
805 dib8000_set_bandwidth(fe, 6000);
806
807 dib8000_set_adc_state(state, DIBX000_SLOW_ADC_ON);
808 dib8000_sad_calib(state);
809 dib8000_set_adc_state(state, DIBX000_SLOW_ADC_OFF);
810
811 dib8000_set_power_mode(state, DIB8000M_POWER_INTERFACE_ONLY);
812
813 return 0;
814}
815
816static void dib8000_restart_agc(struct dib8000_state *state)
817{
818 // P_restart_iqc & P_restart_agc
819 dib8000_write_word(state, 770, 0x0a00);
820 dib8000_write_word(state, 770, 0x0000);
821}
822
823static int dib8000_update_lna(struct dib8000_state *state)
824{
825 u16 dyn_gain;
826
827 if (state->cfg.update_lna) {
828 // read dyn_gain here (because it is demod-dependent and not tuner)
829 dyn_gain = dib8000_read_word(state, 390);
830
831 if (state->cfg.update_lna(state->fe[0], dyn_gain)) {
832 dib8000_restart_agc(state);
833 return 1;
834 }
835 }
836 return 0;
837}
838
839static int dib8000_set_agc_config(struct dib8000_state *state, u8 band)
840{
841 struct dibx000_agc_config *agc = NULL;
842 int i;
843 if (state->current_band == band && state->current_agc != NULL)
844 return 0;
845 state->current_band = band;
846
847 for (i = 0; i < state->cfg.agc_config_count; i++)
848 if (state->cfg.agc[i].band_caps & band) {
849 agc = &state->cfg.agc[i];
850 break;
851 }
852
853 if (agc == NULL) {
854 dprintk("no valid AGC configuration found for band 0x%02x", band);
855 return -EINVAL;
856 }
857
858 state->current_agc = agc;
859
860 /* AGC */
861 dib8000_write_word(state, 76, agc->setup);
862 dib8000_write_word(state, 77, agc->inv_gain);
863 dib8000_write_word(state, 78, agc->time_stabiliz);
864 dib8000_write_word(state, 101, (agc->alpha_level << 12) | agc->thlock);
865
866 // Demod AGC loop configuration
867 dib8000_write_word(state, 102, (agc->alpha_mant << 5) | agc->alpha_exp);
868 dib8000_write_word(state, 103, (agc->beta_mant << 6) | agc->beta_exp);
869
870 dprintk("WBD: ref: %d, sel: %d, active: %d, alpha: %d",
871 state->wbd_ref != 0 ? state->wbd_ref : agc->wbd_ref, agc->wbd_sel, !agc->perform_agc_softsplit, agc->wbd_sel);
872
873 /* AGC continued */
874 if (state->wbd_ref != 0)
875 dib8000_write_word(state, 106, state->wbd_ref);
876 else // use default
877 dib8000_write_word(state, 106, agc->wbd_ref);
878 dib8000_write_word(state, 107, (agc->wbd_alpha << 9) | (agc->perform_agc_softsplit << 8));
879 dib8000_write_word(state, 108, agc->agc1_max);
880 dib8000_write_word(state, 109, agc->agc1_min);
881 dib8000_write_word(state, 110, agc->agc2_max);
882 dib8000_write_word(state, 111, agc->agc2_min);
883 dib8000_write_word(state, 112, (agc->agc1_pt1 << 8) | agc->agc1_pt2);
884 dib8000_write_word(state, 113, (agc->agc1_slope1 << 8) | agc->agc1_slope2);
885 dib8000_write_word(state, 114, (agc->agc2_pt1 << 8) | agc->agc2_pt2);
886 dib8000_write_word(state, 115, (agc->agc2_slope1 << 8) | agc->agc2_slope2);
887
888 dib8000_write_word(state, 75, agc->agc1_pt3);
889 dib8000_write_word(state, 923, (dib8000_read_word(state, 923) & 0xffe3) | (agc->wbd_inv << 4) | (agc->wbd_sel << 2)); /*LB : 929 -> 923 */
890
891 return 0;
892}
893
894void dib8000_pwm_agc_reset(struct dvb_frontend *fe)
895{
896 struct dib8000_state *state = fe->demodulator_priv;
897 dib8000_set_adc_state(state, DIBX000_ADC_ON);
898 dib8000_set_agc_config(state, (unsigned char)(BAND_OF_FREQUENCY(fe->dtv_property_cache.frequency / 1000)));
899}
900EXPORT_SYMBOL(dib8000_pwm_agc_reset);
901
902static int dib8000_agc_soft_split(struct dib8000_state *state)
903{
904 u16 agc, split_offset;
905
906 if (!state->current_agc || !state->current_agc->perform_agc_softsplit || state->current_agc->split.max == 0)
907 return FE_CALLBACK_TIME_NEVER;
908
909 // n_agc_global
910 agc = dib8000_read_word(state, 390);
911
912 if (agc > state->current_agc->split.min_thres)
913 split_offset = state->current_agc->split.min;
914 else if (agc < state->current_agc->split.max_thres)
915 split_offset = state->current_agc->split.max;
916 else
917 split_offset = state->current_agc->split.max *
918 (agc - state->current_agc->split.min_thres) /
919 (state->current_agc->split.max_thres - state->current_agc->split.min_thres);
920
921 dprintk("AGC split_offset: %d", split_offset);
922
923 // P_agc_force_split and P_agc_split_offset
924 dib8000_write_word(state, 107, (dib8000_read_word(state, 107) & 0xff00) | split_offset);
925 return 5000;
926}
927
928static int dib8000_agc_startup(struct dvb_frontend *fe)
929{
930 struct dib8000_state *state = fe->demodulator_priv;
931 enum frontend_tune_state *tune_state = &state->tune_state;
932
933 int ret = 0;
934
935 switch (*tune_state) {
936 case CT_AGC_START:
937 // set power-up level: interf+analog+AGC
938
939 dib8000_set_adc_state(state, DIBX000_ADC_ON);
940
941 if (dib8000_set_agc_config(state, (unsigned char)(BAND_OF_FREQUENCY(fe->dtv_property_cache.frequency / 1000))) != 0) {
942 *tune_state = CT_AGC_STOP;
943 state->status = FE_STATUS_TUNE_FAILED;
944 break;
945 }
946
947 ret = 70;
948 *tune_state = CT_AGC_STEP_0;
949 break;
950
951 case CT_AGC_STEP_0:
952 //AGC initialization
953 if (state->cfg.agc_control)
954 state->cfg.agc_control(fe, 1);
955
956 dib8000_restart_agc(state);
957
958 // wait AGC rough lock time
959 ret = 50;
960 *tune_state = CT_AGC_STEP_1;
961 break;
962
963 case CT_AGC_STEP_1:
964 // wait AGC accurate lock time
965 ret = 70;
966
967 if (dib8000_update_lna(state))
968 // wait only AGC rough lock time
969 ret = 50;
970 else
971 *tune_state = CT_AGC_STEP_2;
972 break;
973
974 case CT_AGC_STEP_2:
975 dib8000_agc_soft_split(state);
976
977 if (state->cfg.agc_control)
978 state->cfg.agc_control(fe, 0);
979
980 *tune_state = CT_AGC_STOP;
981 break;
982 default:
983 ret = dib8000_agc_soft_split(state);
984 break;
985 }
986 return ret;
987
988}
989
990static const s32 lut_1000ln_mant[] =
991{
992 908, 7003, 7090, 7170, 7244, 7313, 7377, 7438, 7495, 7549, 7600
993};
994
995s32 dib8000_get_adc_power(struct dvb_frontend *fe, u8 mode)
996{
997 struct dib8000_state *state = fe->demodulator_priv;
998 u32 ix = 0, tmp_val = 0, exp = 0, mant = 0;
999 s32 val;
1000
1001 val = dib8000_read32(state, 384);
1002 if (mode) {
1003 tmp_val = val;
1004 while (tmp_val >>= 1)
1005 exp++;
1006 mant = (val * 1000 / (1<<exp));
1007 ix = (u8)((mant-1000)/100); /* index of the LUT */
1008 val = (lut_1000ln_mant[ix] + 693*(exp-20) - 6908);
1009 val = (val*256)/1000;
1010 }
1011 return val;
1012}
1013EXPORT_SYMBOL(dib8000_get_adc_power);
1014
1015static void dib8000_update_timf(struct dib8000_state *state)
1016{
1017 u32 timf = state->timf = dib8000_read32(state, 435);
1018
1019 dib8000_write_word(state, 29, (u16) (timf >> 16));
1020 dib8000_write_word(state, 30, (u16) (timf & 0xffff));
1021 dprintk("Updated timing frequency: %d (default: %d)", state->timf, state->timf_default);
1022}
1023
1024static const u16 adc_target_16dB[11] = {
1025 (1 << 13) - 825 - 117,
1026 (1 << 13) - 837 - 117,
1027 (1 << 13) - 811 - 117,
1028 (1 << 13) - 766 - 117,
1029 (1 << 13) - 737 - 117,
1030 (1 << 13) - 693 - 117,
1031 (1 << 13) - 648 - 117,
1032 (1 << 13) - 619 - 117,
1033 (1 << 13) - 575 - 117,
1034 (1 << 13) - 531 - 117,
1035 (1 << 13) - 501 - 117
1036};
1037static const u8 permu_seg[] = { 6, 5, 7, 4, 8, 3, 9, 2, 10, 1, 11, 0, 12 };
1038
1039static void dib8000_set_channel(struct dib8000_state *state, u8 seq, u8 autosearching)
1040{
1041 u16 mode, max_constellation, seg_diff_mask = 0, nbseg_diff = 0;
1042 u8 guard, crate, constellation, timeI;
1043 u16 i, coeff[4], P_cfr_left_edge = 0, P_cfr_right_edge = 0, seg_mask13 = 0x1fff; // All 13 segments enabled
1044 const s16 *ncoeff = NULL, *ana_fe;
1045 u16 tmcc_pow = 0;
1046 u16 coff_pow = 0x2800;
1047 u16 init_prbs = 0xfff;
1048 u16 ana_gain = 0;
1049
1050 if (state->ber_monitored_layer != LAYER_ALL)
1051 dib8000_write_word(state, 285, (dib8000_read_word(state, 285) & 0x60) | state->ber_monitored_layer);
1052 else
1053 dib8000_write_word(state, 285, dib8000_read_word(state, 285) & 0x60);
1054
1055 i = dib8000_read_word(state, 26) & 1; // P_dds_invspec
1056 dib8000_write_word(state, 26, state->fe[0]->dtv_property_cache.inversion^i);
1057
1058 if (state->fe[0]->dtv_property_cache.isdbt_sb_mode) {
1059 //compute new dds_freq for the seg and adjust prbs
1060 int seg_offset =
1061 state->fe[0]->dtv_property_cache.isdbt_sb_segment_idx -
1062 (state->fe[0]->dtv_property_cache.isdbt_sb_segment_count / 2) -
1063 (state->fe[0]->dtv_property_cache.isdbt_sb_segment_count % 2);
1064 int clk = state->cfg.pll->internal;
1065 u32 segtodds = ((u32) (430 << 23) / clk) << 3; // segtodds = SegBW / Fclk * pow(2,26)
1066 int dds_offset = seg_offset * segtodds;
1067 int new_dds, sub_channel;
1068 if ((state->fe[0]->dtv_property_cache.isdbt_sb_segment_count % 2) == 0)
1069 dds_offset -= (int)(segtodds / 2);
1070
1071 if (state->cfg.pll->ifreq == 0) {
1072 if ((state->fe[0]->dtv_property_cache.inversion ^ i) == 0) {
1073 dib8000_write_word(state, 26, dib8000_read_word(state, 26) | 1);
1074 new_dds = dds_offset;
1075 } else
1076 new_dds = dds_offset;
1077
1078 // We shift tuning frequency if the wanted segment is :
1079 // - the segment of center frequency with an odd total number of segments
1080 // - the segment to the left of center frequency with an even total number of segments
1081 // - the segment to the right of center frequency with an even total number of segments
1082 if ((state->fe[0]->dtv_property_cache.delivery_system == SYS_ISDBT)
1083 && (state->fe[0]->dtv_property_cache.isdbt_sb_mode == 1)
1084 && (((state->fe[0]->dtv_property_cache.isdbt_sb_segment_count % 2)
1085 && (state->fe[0]->dtv_property_cache.isdbt_sb_segment_idx ==
1086 ((state->fe[0]->dtv_property_cache.isdbt_sb_segment_count / 2) + 1)))
1087 || (((state->fe[0]->dtv_property_cache.isdbt_sb_segment_count % 2) == 0)
1088 && (state->fe[0]->dtv_property_cache.isdbt_sb_segment_idx == (state->fe[0]->dtv_property_cache.isdbt_sb_segment_count / 2)))
1089 || (((state->fe[0]->dtv_property_cache.isdbt_sb_segment_count % 2) == 0)
1090 && (state->fe[0]->dtv_property_cache.isdbt_sb_segment_idx ==
1091 ((state->fe[0]->dtv_property_cache.isdbt_sb_segment_count / 2) + 1)))
1092 )) {
1093 new_dds -= ((u32) (850 << 22) / clk) << 4; // new_dds = 850 (freq shift in KHz) / Fclk * pow(2,26)
1094 }
1095 } else {
1096 if ((state->fe[0]->dtv_property_cache.inversion ^ i) == 0)
1097 new_dds = state->cfg.pll->ifreq - dds_offset;
1098 else
1099 new_dds = state->cfg.pll->ifreq + dds_offset;
1100 }
1101 dib8000_write_word(state, 27, (u16) ((new_dds >> 16) & 0x01ff));
1102 dib8000_write_word(state, 28, (u16) (new_dds & 0xffff));
1103 if (state->fe[0]->dtv_property_cache.isdbt_sb_segment_count % 2)
1104 sub_channel = ((state->fe[0]->dtv_property_cache.isdbt_sb_subchannel + (3 * seg_offset) + 1) % 41) / 3;
1105 else
1106 sub_channel = ((state->fe[0]->dtv_property_cache.isdbt_sb_subchannel + (3 * seg_offset)) % 41) / 3;
1107 sub_channel -= 6;
1108
1109 if (state->fe[0]->dtv_property_cache.transmission_mode == TRANSMISSION_MODE_2K
1110 || state->fe[0]->dtv_property_cache.transmission_mode == TRANSMISSION_MODE_4K) {
1111 dib8000_write_word(state, 219, dib8000_read_word(state, 219) | 0x1); //adp_pass =1
1112 dib8000_write_word(state, 190, dib8000_read_word(state, 190) | (0x1 << 14)); //pha3_force_pha_shift = 1
1113 } else {
1114 dib8000_write_word(state, 219, dib8000_read_word(state, 219) & 0xfffe); //adp_pass =0
1115 dib8000_write_word(state, 190, dib8000_read_word(state, 190) & 0xbfff); //pha3_force_pha_shift = 0
1116 }
1117
1118 switch (state->fe[0]->dtv_property_cache.transmission_mode) {
1119 case TRANSMISSION_MODE_2K:
1120 switch (sub_channel) {
1121 case -6:
1122 init_prbs = 0x0;
1123 break; // 41, 0, 1
1124 case -5:
1125 init_prbs = 0x423;
1126 break; // 02~04
1127 case -4:
1128 init_prbs = 0x9;
1129 break; // 05~07
1130 case -3:
1131 init_prbs = 0x5C7;
1132 break; // 08~10
1133 case -2:
1134 init_prbs = 0x7A6;
1135 break; // 11~13
1136 case -1:
1137 init_prbs = 0x3D8;
1138 break; // 14~16
1139 case 0:
1140 init_prbs = 0x527;
1141 break; // 17~19
1142 case 1:
1143 init_prbs = 0x7FF;
1144 break; // 20~22
1145 case 2:
1146 init_prbs = 0x79B;
1147 break; // 23~25
1148 case 3:
1149 init_prbs = 0x3D6;
1150 break; // 26~28
1151 case 4:
1152 init_prbs = 0x3A2;
1153 break; // 29~31
1154 case 5:
1155 init_prbs = 0x53B;
1156 break; // 32~34
1157 case 6:
1158 init_prbs = 0x2F4;
1159 break; // 35~37
1160 default:
1161 case 7:
1162 init_prbs = 0x213;
1163 break; // 38~40
1164 }
1165 break;
1166
1167 case TRANSMISSION_MODE_4K:
1168 switch (sub_channel) {
1169 case -6:
1170 init_prbs = 0x0;
1171 break; // 41, 0, 1
1172 case -5:
1173 init_prbs = 0x208;
1174 break; // 02~04
1175 case -4:
1176 init_prbs = 0xC3;
1177 break; // 05~07
1178 case -3:
1179 init_prbs = 0x7B9;
1180 break; // 08~10
1181 case -2:
1182 init_prbs = 0x423;
1183 break; // 11~13
1184 case -1:
1185 init_prbs = 0x5C7;
1186 break; // 14~16
1187 case 0:
1188 init_prbs = 0x3D8;
1189 break; // 17~19
1190 case 1:
1191 init_prbs = 0x7FF;
1192 break; // 20~22
1193 case 2:
1194 init_prbs = 0x3D6;
1195 break; // 23~25
1196 case 3:
1197 init_prbs = 0x53B;
1198 break; // 26~28
1199 case 4:
1200 init_prbs = 0x213;
1201 break; // 29~31
1202 case 5:
1203 init_prbs = 0x29;
1204 break; // 32~34
1205 case 6:
1206 init_prbs = 0xD0;
1207 break; // 35~37
1208 default:
1209 case 7:
1210 init_prbs = 0x48E;
1211 break; // 38~40
1212 }
1213 break;
1214
1215 default:
1216 case TRANSMISSION_MODE_8K:
1217 switch (sub_channel) {
1218 case -6:
1219 init_prbs = 0x0;
1220 break; // 41, 0, 1
1221 case -5:
1222 init_prbs = 0x740;
1223 break; // 02~04
1224 case -4:
1225 init_prbs = 0x069;
1226 break; // 05~07
1227 case -3:
1228 init_prbs = 0x7DD;
1229 break; // 08~10
1230 case -2:
1231 init_prbs = 0x208;
1232 break; // 11~13
1233 case -1:
1234 init_prbs = 0x7B9;
1235 break; // 14~16
1236 case 0:
1237 init_prbs = 0x5C7;
1238 break; // 17~19
1239 case 1:
1240 init_prbs = 0x7FF;
1241 break; // 20~22
1242 case 2:
1243 init_prbs = 0x53B;
1244 break; // 23~25
1245 case 3:
1246 init_prbs = 0x29;
1247 break; // 26~28
1248 case 4:
1249 init_prbs = 0x48E;
1250 break; // 29~31
1251 case 5:
1252 init_prbs = 0x4C4;
1253 break; // 32~34
1254 case 6:
1255 init_prbs = 0x367;
1256 break; // 33~37
1257 default:
1258 case 7:
1259 init_prbs = 0x684;
1260 break; // 38~40
1261 }
1262 break;
1263 }
1264 } else {
1265 dib8000_write_word(state, 27, (u16) ((state->cfg.pll->ifreq >> 16) & 0x01ff));
1266 dib8000_write_word(state, 28, (u16) (state->cfg.pll->ifreq & 0xffff));
1267 dib8000_write_word(state, 26, (u16) ((state->cfg.pll->ifreq >> 25) & 0x0003));
1268 }
1269 /*P_mode == ?? */
1270 dib8000_write_word(state, 10, (seq << 4));
1271 // dib8000_write_word(state, 287, (dib8000_read_word(state, 287) & 0xe000) | 0x1000);
1272
1273 switch (state->fe[0]->dtv_property_cache.guard_interval) {
1274 case GUARD_INTERVAL_1_32:
1275 guard = 0;
1276 break;
1277 case GUARD_INTERVAL_1_16:
1278 guard = 1;
1279 break;
1280 case GUARD_INTERVAL_1_8:
1281 guard = 2;
1282 break;
1283 case GUARD_INTERVAL_1_4:
1284 default:
1285 guard = 3;
1286 break;
1287 }
1288
1289 dib8000_write_word(state, 1, (init_prbs << 2) | (guard & 0x3)); // ADDR 1
1290
1291 max_constellation = DQPSK;
1292 for (i = 0; i < 3; i++) {
1293 switch (state->fe[0]->dtv_property_cache.layer[i].modulation) {
1294 case DQPSK:
1295 constellation = 0;
1296 break;
1297 case QPSK:
1298 constellation = 1;
1299 break;
1300 case QAM_16:
1301 constellation = 2;
1302 break;
1303 case QAM_64:
1304 default:
1305 constellation = 3;
1306 break;
1307 }
1308
1309 switch (state->fe[0]->dtv_property_cache.layer[i].fec) {
1310 case FEC_1_2:
1311 crate = 1;
1312 break;
1313 case FEC_2_3:
1314 crate = 2;
1315 break;
1316 case FEC_3_4:
1317 crate = 3;
1318 break;
1319 case FEC_5_6:
1320 crate = 5;
1321 break;
1322 case FEC_7_8:
1323 default:
1324 crate = 7;
1325 break;
1326 }
1327
1328 if ((state->fe[0]->dtv_property_cache.layer[i].interleaving > 0) &&
1329 ((state->fe[0]->dtv_property_cache.layer[i].interleaving <= 3) ||
1330 (state->fe[0]->dtv_property_cache.layer[i].interleaving == 4 && state->fe[0]->dtv_property_cache.isdbt_sb_mode == 1))
1331 )
1332 timeI = state->fe[0]->dtv_property_cache.layer[i].interleaving;
1333 else
1334 timeI = 0;
1335 dib8000_write_word(state, 2 + i, (constellation << 10) | ((state->fe[0]->dtv_property_cache.layer[i].segment_count & 0xf) << 6) |
1336 (crate << 3) | timeI);
1337 if (state->fe[0]->dtv_property_cache.layer[i].segment_count > 0) {
1338 switch (max_constellation) {
1339 case DQPSK:
1340 case QPSK:
1341 if (state->fe[0]->dtv_property_cache.layer[i].modulation == QAM_16 ||
1342 state->fe[0]->dtv_property_cache.layer[i].modulation == QAM_64)
1343 max_constellation = state->fe[0]->dtv_property_cache.layer[i].modulation;
1344 break;
1345 case QAM_16:
1346 if (state->fe[0]->dtv_property_cache.layer[i].modulation == QAM_64)
1347 max_constellation = state->fe[0]->dtv_property_cache.layer[i].modulation;
1348 break;
1349 }
1350 }
1351 }
1352
1353 mode = fft_to_mode(state);
1354
1355 //dib8000_write_word(state, 5, 13); /*p_last_seg = 13*/
1356
1357 dib8000_write_word(state, 274, (dib8000_read_word(state, 274) & 0xffcf) |
1358 ((state->fe[0]->dtv_property_cache.isdbt_partial_reception & 1) << 5) | ((state->fe[0]->dtv_property_cache.
1359 isdbt_sb_mode & 1) << 4));
1360
1361 dprintk("mode = %d ; guard = %d", mode, state->fe[0]->dtv_property_cache.guard_interval);
1362
1363 /* signal optimization parameter */
1364
1365 if (state->fe[0]->dtv_property_cache.isdbt_partial_reception) {
1366 seg_diff_mask = (state->fe[0]->dtv_property_cache.layer[0].modulation == DQPSK) << permu_seg[0];
1367 for (i = 1; i < 3; i++)
1368 nbseg_diff +=
1369 (state->fe[0]->dtv_property_cache.layer[i].modulation == DQPSK) * state->fe[0]->dtv_property_cache.layer[i].segment_count;
1370 for (i = 0; i < nbseg_diff; i++)
1371 seg_diff_mask |= 1 << permu_seg[i + 1];
1372 } else {
1373 for (i = 0; i < 3; i++)
1374 nbseg_diff +=
1375 (state->fe[0]->dtv_property_cache.layer[i].modulation == DQPSK) * state->fe[0]->dtv_property_cache.layer[i].segment_count;
1376 for (i = 0; i < nbseg_diff; i++)
1377 seg_diff_mask |= 1 << permu_seg[i];
1378 }
1379 dprintk("nbseg_diff = %X (%d)", seg_diff_mask, seg_diff_mask);
1380
1381 state->differential_constellation = (seg_diff_mask != 0);
1382 dib8000_set_diversity_in(state->fe[0], state->diversity_onoff);
1383
1384 if (state->fe[0]->dtv_property_cache.isdbt_sb_mode == 1) {
1385 if (state->fe[0]->dtv_property_cache.isdbt_partial_reception == 1)
1386 seg_mask13 = 0x00E0;
1387 else // 1-segment
1388 seg_mask13 = 0x0040;
1389 } else
1390 seg_mask13 = 0x1fff;
1391
1392 // WRITE: Mode & Diff mask
1393 dib8000_write_word(state, 0, (mode << 13) | seg_diff_mask);
1394
1395 if ((seg_diff_mask) || (state->fe[0]->dtv_property_cache.isdbt_sb_mode))
1396 dib8000_write_word(state, 268, (dib8000_read_word(state, 268) & 0xF9FF) | 0x0200);
1397 else
1398 dib8000_write_word(state, 268, (2 << 9) | 39); //init value
1399
1400 // ---- SMALL ----
1401 // P_small_seg_diff
1402 dib8000_write_word(state, 352, seg_diff_mask); // ADDR 352
1403
1404 dib8000_write_word(state, 353, seg_mask13); // ADDR 353
1405
1406/* // P_small_narrow_band=0, P_small_last_seg=13, P_small_offset_num_car=5 */
1407
1408 // ---- SMALL ----
1409 if (state->fe[0]->dtv_property_cache.isdbt_sb_mode == 1) {
1410 switch (state->fe[0]->dtv_property_cache.transmission_mode) {
1411 case TRANSMISSION_MODE_2K:
1412 if (state->fe[0]->dtv_property_cache.isdbt_partial_reception == 0) {
1413 if (state->fe[0]->dtv_property_cache.layer[0].modulation == DQPSK)
1414 ncoeff = coeff_2k_sb_1seg_dqpsk;
1415 else // QPSK or QAM
1416 ncoeff = coeff_2k_sb_1seg;
1417 } else { // 3-segments
1418 if (state->fe[0]->dtv_property_cache.layer[0].modulation == DQPSK) {
1419 if (state->fe[0]->dtv_property_cache.layer[1].modulation == DQPSK)
1420 ncoeff = coeff_2k_sb_3seg_0dqpsk_1dqpsk;
1421 else // QPSK or QAM on external segments
1422 ncoeff = coeff_2k_sb_3seg_0dqpsk;
1423 } else { // QPSK or QAM on central segment
1424 if (state->fe[0]->dtv_property_cache.layer[1].modulation == DQPSK)
1425 ncoeff = coeff_2k_sb_3seg_1dqpsk;
1426 else // QPSK or QAM on external segments
1427 ncoeff = coeff_2k_sb_3seg;
1428 }
1429 }
1430 break;
1431
1432 case TRANSMISSION_MODE_4K:
1433 if (state->fe[0]->dtv_property_cache.isdbt_partial_reception == 0) {
1434 if (state->fe[0]->dtv_property_cache.layer[0].modulation == DQPSK)
1435 ncoeff = coeff_4k_sb_1seg_dqpsk;
1436 else // QPSK or QAM
1437 ncoeff = coeff_4k_sb_1seg;
1438 } else { // 3-segments
1439 if (state->fe[0]->dtv_property_cache.layer[0].modulation == DQPSK) {
1440 if (state->fe[0]->dtv_property_cache.layer[1].modulation == DQPSK) {
1441 ncoeff = coeff_4k_sb_3seg_0dqpsk_1dqpsk;
1442 } else { // QPSK or QAM on external segments
1443 ncoeff = coeff_4k_sb_3seg_0dqpsk;
1444 }
1445 } else { // QPSK or QAM on central segment
1446 if (state->fe[0]->dtv_property_cache.layer[1].modulation == DQPSK) {
1447 ncoeff = coeff_4k_sb_3seg_1dqpsk;
1448 } else // QPSK or QAM on external segments
1449 ncoeff = coeff_4k_sb_3seg;
1450 }
1451 }
1452 break;
1453
1454 case TRANSMISSION_MODE_AUTO:
1455 case TRANSMISSION_MODE_8K:
1456 default:
1457 if (state->fe[0]->dtv_property_cache.isdbt_partial_reception == 0) {
1458 if (state->fe[0]->dtv_property_cache.layer[0].modulation == DQPSK)
1459 ncoeff = coeff_8k_sb_1seg_dqpsk;
1460 else // QPSK or QAM
1461 ncoeff = coeff_8k_sb_1seg;
1462 } else { // 3-segments
1463 if (state->fe[0]->dtv_property_cache.layer[0].modulation == DQPSK) {
1464 if (state->fe[0]->dtv_property_cache.layer[1].modulation == DQPSK) {
1465 ncoeff = coeff_8k_sb_3seg_0dqpsk_1dqpsk;
1466 } else { // QPSK or QAM on external segments
1467 ncoeff = coeff_8k_sb_3seg_0dqpsk;
1468 }
1469 } else { // QPSK or QAM on central segment
1470 if (state->fe[0]->dtv_property_cache.layer[1].modulation == DQPSK) {
1471 ncoeff = coeff_8k_sb_3seg_1dqpsk;
1472 } else // QPSK or QAM on external segments
1473 ncoeff = coeff_8k_sb_3seg;
1474 }
1475 }
1476 break;
1477 }
1478 for (i = 0; i < 8; i++)
1479 dib8000_write_word(state, 343 + i, ncoeff[i]);
1480 }
1481
1482 // P_small_coef_ext_enable=ISDB-Tsb, P_small_narrow_band=ISDB-Tsb, P_small_last_seg=13, P_small_offset_num_car=5
1483 dib8000_write_word(state, 351,
1484 (state->fe[0]->dtv_property_cache.isdbt_sb_mode << 9) | (state->fe[0]->dtv_property_cache.isdbt_sb_mode << 8) | (13 << 4) | 5);
1485
1486 // ---- COFF ----
1487 // Carloff, the most robust
1488 if (state->fe[0]->dtv_property_cache.isdbt_sb_mode == 1) {
1489
1490 // P_coff_cpil_alpha=4, P_coff_inh=0, P_coff_cpil_winlen=64
1491 // P_coff_narrow_band=1, P_coff_square_val=1, P_coff_one_seg=~partial_rcpt, P_coff_use_tmcc=1, P_coff_use_ac=1
1492 dib8000_write_word(state, 187,
1493 (4 << 12) | (0 << 11) | (63 << 5) | (0x3 << 3) | ((~state->fe[0]->dtv_property_cache.isdbt_partial_reception & 1) << 2)
1494 | 0x3);
1495
1496/* // P_small_coef_ext_enable = 1 */
1497/* dib8000_write_word(state, 351, dib8000_read_word(state, 351) | 0x200); */
1498
1499 if (state->fe[0]->dtv_property_cache.isdbt_partial_reception == 0) {
1500
1501 // P_coff_winlen=63, P_coff_thres_lock=15, P_coff_one_seg_width= (P_mode == 3) , P_coff_one_seg_sym= (P_mode-1)
1502 if (mode == 3)
1503 dib8000_write_word(state, 180, 0x1fcf | ((mode - 1) << 14));
1504 else
1505 dib8000_write_word(state, 180, 0x0fcf | ((mode - 1) << 14));
1506 // P_ctrl_corm_thres4pre_freq_inh=1,P_ctrl_pre_freq_mode_sat=1,
1507 // P_ctrl_pre_freq_inh=0, P_ctrl_pre_freq_step = 5, P_pre_freq_win_len=4
1508 dib8000_write_word(state, 338, (1 << 12) | (1 << 10) | (0 << 9) | (5 << 5) | 4);
1509 // P_ctrl_pre_freq_win_len=16, P_ctrl_pre_freq_thres_lockin=8
1510 dib8000_write_word(state, 340, (16 << 6) | (8 << 0));
1511 // P_ctrl_pre_freq_thres_lockout=6, P_small_use_tmcc/ac/cp=1
1512 dib8000_write_word(state, 341, (6 << 3) | (1 << 2) | (1 << 1) | (1 << 0));
1513
1514 // P_coff_corthres_8k, 4k, 2k and P_coff_cpilthres_8k, 4k, 2k
1515 dib8000_write_word(state, 181, 300);
1516 dib8000_write_word(state, 182, 150);
1517 dib8000_write_word(state, 183, 80);
1518 dib8000_write_word(state, 184, 300);
1519 dib8000_write_word(state, 185, 150);
1520 dib8000_write_word(state, 186, 80);
1521 } else { // Sound Broadcasting mode 3 seg
1522 // P_coff_one_seg_sym= 1, P_coff_one_seg_width= 1, P_coff_winlen=63, P_coff_thres_lock=15
1523 /* if (mode == 3) */
1524 /* dib8000_write_word(state, 180, 0x2fca | ((0) << 14)); */
1525 /* else */
1526 /* dib8000_write_word(state, 180, 0x2fca | ((1) << 14)); */
1527 dib8000_write_word(state, 180, 0x1fcf | (1 << 14));
1528
1529 // P_ctrl_corm_thres4pre_freq_inh = 1, P_ctrl_pre_freq_mode_sat=1,
1530 // P_ctrl_pre_freq_inh=0, P_ctrl_pre_freq_step = 4, P_pre_freq_win_len=4
1531 dib8000_write_word(state, 338, (1 << 12) | (1 << 10) | (0 << 9) | (4 << 5) | 4);
1532 // P_ctrl_pre_freq_win_len=16, P_ctrl_pre_freq_thres_lockin=8
1533 dib8000_write_word(state, 340, (16 << 6) | (8 << 0));
1534 //P_ctrl_pre_freq_thres_lockout=6, P_small_use_tmcc/ac/cp=1
1535 dib8000_write_word(state, 341, (6 << 3) | (1 << 2) | (1 << 1) | (1 << 0));
1536
1537 // P_coff_corthres_8k, 4k, 2k and P_coff_cpilthres_8k, 4k, 2k
1538 dib8000_write_word(state, 181, 350);
1539 dib8000_write_word(state, 182, 300);
1540 dib8000_write_word(state, 183, 250);
1541 dib8000_write_word(state, 184, 350);
1542 dib8000_write_word(state, 185, 300);
1543 dib8000_write_word(state, 186, 250);
1544 }
1545
1546 } else if (state->isdbt_cfg_loaded == 0) { // if not Sound Broadcasting mode : put default values for 13 segments
1547 dib8000_write_word(state, 180, (16 << 6) | 9);
1548 dib8000_write_word(state, 187, (4 << 12) | (8 << 5) | 0x2);
1549 coff_pow = 0x2800;
1550 for (i = 0; i < 6; i++)
1551 dib8000_write_word(state, 181 + i, coff_pow);
1552
1553 // P_ctrl_corm_thres4pre_freq_inh=1, P_ctrl_pre_freq_mode_sat=1,
1554 // P_ctrl_pre_freq_mode_sat=1, P_ctrl_pre_freq_inh=0, P_ctrl_pre_freq_step = 3, P_pre_freq_win_len=1
1555 dib8000_write_word(state, 338, (1 << 12) | (1 << 10) | (0 << 9) | (3 << 5) | 1);
1556
1557 // P_ctrl_pre_freq_win_len=8, P_ctrl_pre_freq_thres_lockin=6
1558 dib8000_write_word(state, 340, (8 << 6) | (6 << 0));
1559 // P_ctrl_pre_freq_thres_lockout=4, P_small_use_tmcc/ac/cp=1
1560 dib8000_write_word(state, 341, (4 << 3) | (1 << 2) | (1 << 1) | (1 << 0));
1561 }
1562 // ---- FFT ----
1563 if (state->fe[0]->dtv_property_cache.isdbt_sb_mode == 1 && state->fe[0]->dtv_property_cache.isdbt_partial_reception == 0)
1564 dib8000_write_word(state, 178, 64); // P_fft_powrange=64
1565 else
1566 dib8000_write_word(state, 178, 32); // P_fft_powrange=32
1567
1568 /* make the cpil_coff_lock more robust but slower p_coff_winlen
1569 * 6bits; p_coff_thres_lock 6bits (for coff lock if needed)
1570 */
1571 /* if ( ( nbseg_diff>0)&&(nbseg_diff<13))
1572 dib8000_write_word(state, 187, (dib8000_read_word(state, 187) & 0xfffb) | (1 << 3)); */
1573
1574 dib8000_write_word(state, 189, ~seg_mask13 | seg_diff_mask); /* P_lmod4_seg_inh */
1575 dib8000_write_word(state, 192, ~seg_mask13 | seg_diff_mask); /* P_pha3_seg_inh */
1576 dib8000_write_word(state, 225, ~seg_mask13 | seg_diff_mask); /* P_tac_seg_inh */
1577 if ((!state->fe[0]->dtv_property_cache.isdbt_sb_mode) && (state->cfg.pll->ifreq == 0))
1578 dib8000_write_word(state, 266, ~seg_mask13 | seg_diff_mask | 0x40); /* P_equal_noise_seg_inh */
1579 else
1580 dib8000_write_word(state, 266, ~seg_mask13 | seg_diff_mask); /* P_equal_noise_seg_inh */
1581 dib8000_write_word(state, 287, ~seg_mask13 | 0x1000); /* P_tmcc_seg_inh */
1582 //dib8000_write_word(state, 288, ~seg_mask13 | seg_diff_mask); /* P_tmcc_seg_eq_inh */
1583 if (!autosearching)
1584 dib8000_write_word(state, 288, (~seg_mask13 | seg_diff_mask) & 0x1fff); /* P_tmcc_seg_eq_inh */
1585 else
1586 dib8000_write_word(state, 288, 0x1fff); //disable equalisation of the tmcc when autosearch to be able to find the DQPSK channels.
1587 dprintk("287 = %X (%d)", ~seg_mask13 | 0x1000, ~seg_mask13 | 0x1000);
1588
1589 dib8000_write_word(state, 211, seg_mask13 & (~seg_diff_mask)); /* P_des_seg_enabled */
1590
1591 /* offset loop parameters */
1592 if (state->fe[0]->dtv_property_cache.isdbt_sb_mode == 1) {
1593 if (state->fe[0]->dtv_property_cache.isdbt_partial_reception == 0)
1594 /* P_timf_alpha = (11-P_mode), P_corm_alpha=6, P_corm_thres=0x80 */
1595 dib8000_write_word(state, 32, ((11 - mode) << 12) | (6 << 8) | 0x40);
1596
1597 else // Sound Broadcasting mode 3 seg
1598 /* P_timf_alpha = (10-P_mode), P_corm_alpha=6, P_corm_thres=0x80 */
1599 dib8000_write_word(state, 32, ((10 - mode) << 12) | (6 << 8) | 0x60);
1600 } else
1601 // TODO in 13 seg, timf_alpha can always be the same or not ?
1602 /* P_timf_alpha = (9-P_mode, P_corm_alpha=6, P_corm_thres=0x80 */
1603 dib8000_write_word(state, 32, ((9 - mode) << 12) | (6 << 8) | 0x80);
1604
1605 if (state->fe[0]->dtv_property_cache.isdbt_sb_mode == 1) {
1606 if (state->fe[0]->dtv_property_cache.isdbt_partial_reception == 0)
1607 /* P_ctrl_pha_off_max=3 P_ctrl_sfreq_inh =0 P_ctrl_sfreq_step = (11-P_mode) */
1608 dib8000_write_word(state, 37, (3 << 5) | (0 << 4) | (10 - mode));
1609
1610 else // Sound Broadcasting mode 3 seg
1611 /* P_ctrl_pha_off_max=3 P_ctrl_sfreq_inh =0 P_ctrl_sfreq_step = (10-P_mode) */
1612 dib8000_write_word(state, 37, (3 << 5) | (0 << 4) | (9 - mode));
1613 } else
1614 /* P_ctrl_pha_off_max=3 P_ctrl_sfreq_inh =0 P_ctrl_sfreq_step = 9 */
1615 dib8000_write_word(state, 37, (3 << 5) | (0 << 4) | (8 - mode));
1616
1617 /* P_dvsy_sync_wait - reuse mode */
1618 switch (state->fe[0]->dtv_property_cache.transmission_mode) {
1619 case TRANSMISSION_MODE_8K:
1620 mode = 256;
1621 break;
1622 case TRANSMISSION_MODE_4K:
1623 mode = 128;
1624 break;
1625 default:
1626 case TRANSMISSION_MODE_2K:
1627 mode = 64;
1628 break;
1629 }
1630 if (state->cfg.diversity_delay == 0)
1631 mode = (mode * (1 << (guard)) * 3) / 2 + 48; // add 50% SFN margin + compensate for one DVSY-fifo
1632 else
1633 mode = (mode * (1 << (guard)) * 3) / 2 + state->cfg.diversity_delay; // add 50% SFN margin + compensate for DVSY-fifo
1634 mode <<= 4;
1635 dib8000_write_word(state, 273, (dib8000_read_word(state, 273) & 0x000f) | mode);
1636
1637 /* channel estimation fine configuration */
1638 switch (max_constellation) {
1639 case QAM_64:
1640 ana_gain = 0x7; // -1 : avoid def_est saturation when ADC target is -16dB
1641 coeff[0] = 0x0148; /* P_adp_regul_cnt 0.04 */
1642 coeff[1] = 0xfff0; /* P_adp_noise_cnt -0.002 */
1643 coeff[2] = 0x00a4; /* P_adp_regul_ext 0.02 */
1644 coeff[3] = 0xfff8; /* P_adp_noise_ext -0.001 */
1645 //if (!state->cfg.hostbus_diversity) //if diversity, we should prehaps use the configuration of the max_constallation -1
1646 break;
1647 case QAM_16:
1648 ana_gain = 0x7; // -1 : avoid def_est saturation when ADC target is -16dB
1649 coeff[0] = 0x023d; /* P_adp_regul_cnt 0.07 */
1650 coeff[1] = 0xffdf; /* P_adp_noise_cnt -0.004 */
1651 coeff[2] = 0x00a4; /* P_adp_regul_ext 0.02 */
1652 coeff[3] = 0xfff0; /* P_adp_noise_ext -0.002 */
1653 //if (!((state->cfg.hostbus_diversity) && (max_constellation == QAM_16)))
1654 break;
1655 default:
1656 ana_gain = 0; // 0 : goes along with ADC target at -22dB to keep good mobile performance and lock at sensitivity level
1657 coeff[0] = 0x099a; /* P_adp_regul_cnt 0.3 */
1658 coeff[1] = 0xffae; /* P_adp_noise_cnt -0.01 */
1659 coeff[2] = 0x0333; /* P_adp_regul_ext 0.1 */
1660 coeff[3] = 0xfff8; /* P_adp_noise_ext -0.002 */
1661 break;
1662 }
1663 for (mode = 0; mode < 4; mode++)
1664 dib8000_write_word(state, 215 + mode, coeff[mode]);
1665
1666 // update ana_gain depending on max constellation
1667 dib8000_write_word(state, 116, ana_gain);
1668 // update ADC target depending on ana_gain
1669 if (ana_gain) { // set -16dB ADC target for ana_gain=-1
1670 for (i = 0; i < 10; i++)
1671 dib8000_write_word(state, 80 + i, adc_target_16dB[i]);
1672 } else { // set -22dB ADC target for ana_gain=0
1673 for (i = 0; i < 10; i++)
1674 dib8000_write_word(state, 80 + i, adc_target_16dB[i] - 355);
1675 }
1676
1677 // ---- ANA_FE ----
1678 if (state->fe[0]->dtv_property_cache.isdbt_sb_mode) {
1679 if (state->fe[0]->dtv_property_cache.isdbt_partial_reception == 1)
1680 ana_fe = ana_fe_coeff_3seg;
1681 else // 1-segment
1682 ana_fe = ana_fe_coeff_1seg;
1683 } else
1684 ana_fe = ana_fe_coeff_13seg;
1685
1686 if (state->fe[0]->dtv_property_cache.isdbt_sb_mode == 1 || state->isdbt_cfg_loaded == 0)
1687 for (mode = 0; mode < 24; mode++)
1688 dib8000_write_word(state, 117 + mode, ana_fe[mode]);
1689
1690 // ---- CHAN_BLK ----
1691 for (i = 0; i < 13; i++) {
1692 if ((((~seg_diff_mask) >> i) & 1) == 1) {
1693 P_cfr_left_edge += (1 << i) * ((i == 0) || ((((seg_mask13 & (~seg_diff_mask)) >> (i - 1)) & 1) == 0));
1694 P_cfr_right_edge += (1 << i) * ((i == 12) || ((((seg_mask13 & (~seg_diff_mask)) >> (i + 1)) & 1) == 0));
1695 }
1696 }
1697 dib8000_write_word(state, 222, P_cfr_left_edge); // P_cfr_left_edge
1698 dib8000_write_word(state, 223, P_cfr_right_edge); // P_cfr_right_edge
1699 // "P_cspu_left_edge" not used => do not care
1700 // "P_cspu_right_edge" not used => do not care
1701
1702 if (state->fe[0]->dtv_property_cache.isdbt_sb_mode == 1) {
1703 dib8000_write_word(state, 228, 1); // P_2d_mode_byp=1
1704 dib8000_write_word(state, 205, dib8000_read_word(state, 205) & 0xfff0); // P_cspu_win_cut = 0
1705 if (state->fe[0]->dtv_property_cache.isdbt_partial_reception == 0
1706 && state->fe[0]->dtv_property_cache.transmission_mode == TRANSMISSION_MODE_2K) {
1707 //dib8000_write_word(state, 219, dib8000_read_word(state, 219) & 0xfffe); // P_adp_pass = 0
1708 dib8000_write_word(state, 265, 15); // P_equal_noise_sel = 15
1709 }
1710 } else if (state->isdbt_cfg_loaded == 0) {
1711 dib8000_write_word(state, 228, 0); // default value
1712 dib8000_write_word(state, 265, 31); // default value
1713 dib8000_write_word(state, 205, 0x200f); // init value
1714 }
1715 // ---- TMCC ----
1716 for (i = 0; i < 3; i++)
1717 tmcc_pow +=
1718 (((state->fe[0]->dtv_property_cache.layer[i].modulation == DQPSK) * 4 + 1) * state->fe[0]->dtv_property_cache.layer[i].segment_count);
1719 // Quantif of "P_tmcc_dec_thres_?k" is (0, 5+mode, 9);
1720 // Threshold is set at 1/4 of max power.
1721 tmcc_pow *= (1 << (9 - 2));
1722
1723 dib8000_write_word(state, 290, tmcc_pow); // P_tmcc_dec_thres_2k
1724 dib8000_write_word(state, 291, tmcc_pow); // P_tmcc_dec_thres_4k
1725 dib8000_write_word(state, 292, tmcc_pow); // P_tmcc_dec_thres_8k
1726 //dib8000_write_word(state, 287, (1 << 13) | 0x1000 );
1727 // ---- PHA3 ----
1728
1729 if (state->isdbt_cfg_loaded == 0)
1730 dib8000_write_word(state, 250, 3285); /*p_2d_hspeed_thr0 */
1731
1732 if (state->fe[0]->dtv_property_cache.isdbt_sb_mode == 1)
1733 state->isdbt_cfg_loaded = 0;
1734 else
1735 state->isdbt_cfg_loaded = 1;
1736
1737}
1738
1739static int dib8000_autosearch_start(struct dvb_frontend *fe)
1740{
1741 u8 factor;
1742 u32 value;
1743 struct dib8000_state *state = fe->demodulator_priv;
1744
1745 int slist = 0;
1746
1747 state->fe[0]->dtv_property_cache.inversion = 0;
1748 if (!state->fe[0]->dtv_property_cache.isdbt_sb_mode)
1749 state->fe[0]->dtv_property_cache.layer[0].segment_count = 13;
1750 state->fe[0]->dtv_property_cache.layer[0].modulation = QAM_64;
1751 state->fe[0]->dtv_property_cache.layer[0].fec = FEC_2_3;
1752 state->fe[0]->dtv_property_cache.layer[0].interleaving = 0;
1753
1754 //choose the right list, in sb, always do everything
1755 if (state->fe[0]->dtv_property_cache.isdbt_sb_mode) {
1756 state->fe[0]->dtv_property_cache.transmission_mode = TRANSMISSION_MODE_8K;
1757 state->fe[0]->dtv_property_cache.guard_interval = GUARD_INTERVAL_1_8;
1758 slist = 7;
1759 dib8000_write_word(state, 0, (dib8000_read_word(state, 0) & 0x9fff) | (1 << 13));
1760 } else {
1761 if (state->fe[0]->dtv_property_cache.guard_interval == GUARD_INTERVAL_AUTO) {
1762 if (state->fe[0]->dtv_property_cache.transmission_mode == TRANSMISSION_MODE_AUTO) {
1763 slist = 7;
1764 dib8000_write_word(state, 0, (dib8000_read_word(state, 0) & 0x9fff) | (1 << 13)); // P_mode = 1 to have autosearch start ok with mode2
1765 } else
1766 slist = 3;
1767 } else {
1768 if (state->fe[0]->dtv_property_cache.transmission_mode == TRANSMISSION_MODE_AUTO) {
1769 slist = 2;
1770 dib8000_write_word(state, 0, (dib8000_read_word(state, 0) & 0x9fff) | (1 << 13)); // P_mode = 1
1771 } else
1772 slist = 0;
1773 }
1774
1775 if (state->fe[0]->dtv_property_cache.transmission_mode == TRANSMISSION_MODE_AUTO)
1776 state->fe[0]->dtv_property_cache.transmission_mode = TRANSMISSION_MODE_8K;
1777 if (state->fe[0]->dtv_property_cache.guard_interval == GUARD_INTERVAL_AUTO)
1778 state->fe[0]->dtv_property_cache.guard_interval = GUARD_INTERVAL_1_8;
1779
1780 dprintk("using list for autosearch : %d", slist);
1781 dib8000_set_channel(state, (unsigned char)slist, 1);
1782 //dib8000_write_word(state, 0, (dib8000_read_word(state, 0) & 0x9fff) | (1 << 13)); // P_mode = 1
1783
1784 factor = 1;
1785
1786 //set lock_mask values
1787 dib8000_write_word(state, 6, 0x4);
1788 dib8000_write_word(state, 7, 0x8);
1789 dib8000_write_word(state, 8, 0x1000);
1790
1791 //set lock_mask wait time values
1792 value = 50 * state->cfg.pll->internal * factor;
1793 dib8000_write_word(state, 11, (u16) ((value >> 16) & 0xffff)); // lock0 wait time
1794 dib8000_write_word(state, 12, (u16) (value & 0xffff)); // lock0 wait time
1795 value = 100 * state->cfg.pll->internal * factor;
1796 dib8000_write_word(state, 13, (u16) ((value >> 16) & 0xffff)); // lock1 wait time
1797 dib8000_write_word(state, 14, (u16) (value & 0xffff)); // lock1 wait time
1798 value = 1000 * state->cfg.pll->internal * factor;
1799 dib8000_write_word(state, 15, (u16) ((value >> 16) & 0xffff)); // lock2 wait time
1800 dib8000_write_word(state, 16, (u16) (value & 0xffff)); // lock2 wait time
1801
1802 value = dib8000_read_word(state, 0);
1803 dib8000_write_word(state, 0, (u16) ((1 << 15) | value));
1804 dib8000_read_word(state, 1284); // reset the INT. n_irq_pending
1805 dib8000_write_word(state, 0, (u16) value);
1806
1807 }
1808
1809 return 0;
1810}
1811
1812static int dib8000_autosearch_irq(struct dvb_frontend *fe)
1813{
1814 struct dib8000_state *state = fe->demodulator_priv;
1815 u16 irq_pending = dib8000_read_word(state, 1284);
1816
1817 if (irq_pending & 0x1) { // failed
1818 dprintk("dib8000_autosearch_irq failed");
1819 return 1;
1820 }
1821
1822 if (irq_pending & 0x2) { // succeeded
1823 dprintk("dib8000_autosearch_irq succeeded");
1824 return 2;
1825 }
1826
1827 return 0; // still pending
1828}
1829
1830static int dib8000_tune(struct dvb_frontend *fe)
1831{
1832 struct dib8000_state *state = fe->demodulator_priv;
1833 int ret = 0;
1834 u16 value, mode = fft_to_mode(state);
1835
1836 // we are already tuned - just resuming from suspend
1837 if (state == NULL)
1838 return -EINVAL;
1839
1840 dib8000_set_bandwidth(fe, state->fe[0]->dtv_property_cache.bandwidth_hz / 1000);
1841 dib8000_set_channel(state, 0, 0);
1842
1843 // restart demod
1844 ret |= dib8000_write_word(state, 770, 0x4000);
1845 ret |= dib8000_write_word(state, 770, 0x0000);
1846 msleep(45);
1847
1848 /* P_ctrl_inh_cor=0, P_ctrl_alpha_cor=4, P_ctrl_inh_isi=0, P_ctrl_alpha_isi=3 */
1849 /* ret |= dib8000_write_word(state, 29, (0 << 9) | (4 << 5) | (0 << 4) | (3 << 0) ); workaround inh_isi stays at 1 */
1850
1851 // never achieved a lock before - wait for timfreq to update
1852 if (state->timf == 0) {
1853 if (state->fe[0]->dtv_property_cache.isdbt_sb_mode == 1) {
1854 if (state->fe[0]->dtv_property_cache.isdbt_partial_reception == 0)
1855 msleep(300);
1856 else // Sound Broadcasting mode 3 seg
1857 msleep(500);
1858 } else // 13 seg
1859 msleep(200);
1860 }
1861 if (state->fe[0]->dtv_property_cache.isdbt_sb_mode == 1) {
1862 if (state->fe[0]->dtv_property_cache.isdbt_partial_reception == 0) {
1863
1864 /* P_timf_alpha = (13-P_mode) , P_corm_alpha=6, P_corm_thres=0x40 alpha to check on board */
1865 dib8000_write_word(state, 32, ((13 - mode) << 12) | (6 << 8) | 0x40);
1866 //dib8000_write_word(state, 32, (8 << 12) | (6 << 8) | 0x80);
1867
1868 /* P_ctrl_sfreq_step= (12-P_mode) P_ctrl_sfreq_inh =0 P_ctrl_pha_off_max */
1869 ret |= dib8000_write_word(state, 37, (12 - mode) | ((5 + mode) << 5));
1870
1871 } else { // Sound Broadcasting mode 3 seg
1872
1873 /* P_timf_alpha = (12-P_mode) , P_corm_alpha=6, P_corm_thres=0x60 alpha to check on board */
1874 dib8000_write_word(state, 32, ((12 - mode) << 12) | (6 << 8) | 0x60);
1875
1876 ret |= dib8000_write_word(state, 37, (11 - mode) | ((5 + mode) << 5));
1877 }
1878
1879 } else { // 13 seg
1880 /* P_timf_alpha = 8 , P_corm_alpha=6, P_corm_thres=0x80 alpha to check on board */
1881 dib8000_write_word(state, 32, ((11 - mode) << 12) | (6 << 8) | 0x80);
1882
1883 ret |= dib8000_write_word(state, 37, (10 - mode) | ((5 + mode) << 5));
1884
1885 }
1886
1887 // we achieved a coff_cpil_lock - it's time to update the timf
1888 if ((dib8000_read_word(state, 568) >> 11) & 0x1)
1889 dib8000_update_timf(state);
1890
1891 //now that tune is finished, lock0 should lock on fec_mpeg to output this lock on MP_LOCK. It's changed in autosearch start
1892 dib8000_write_word(state, 6, 0x200);
1893
1894 if (state->revision == 0x8002) {
1895 value = dib8000_read_word(state, 903);
1896 dib8000_write_word(state, 903, value & ~(1 << 3));
1897 msleep(1);
1898 dib8000_write_word(state, 903, value | (1 << 3));
1899 }
1900
1901 return ret;
1902}
1903
1904static int dib8000_wakeup(struct dvb_frontend *fe)
1905{
1906 struct dib8000_state *state = fe->demodulator_priv;
1907 u8 index_frontend;
1908 int ret;
1909
1910 dib8000_set_power_mode(state, DIB8000M_POWER_ALL);
1911 dib8000_set_adc_state(state, DIBX000_ADC_ON);
1912 if (dib8000_set_adc_state(state, DIBX000_SLOW_ADC_ON) != 0)
1913 dprintk("could not start Slow ADC");
1914
1915 for (index_frontend = 1; (index_frontend < MAX_NUMBER_OF_FRONTENDS) && (state->fe[index_frontend] != NULL); index_frontend++) {
1916 ret = state->fe[index_frontend]->ops.init(state->fe[index_frontend]);
1917 if (ret < 0)
1918 return ret;
1919 }
1920
1921 return 0;
1922}
1923
1924static int dib8000_sleep(struct dvb_frontend *fe)
1925{
1926 struct dib8000_state *state = fe->demodulator_priv;
1927 u8 index_frontend;
1928 int ret;
1929
1930 for (index_frontend = 1; (index_frontend < MAX_NUMBER_OF_FRONTENDS) && (state->fe[index_frontend] != NULL); index_frontend++) {
1931 ret = state->fe[index_frontend]->ops.sleep(state->fe[index_frontend]);
1932 if (ret < 0)
1933 return ret;
1934 }
1935
1936 dib8000_set_output_mode(fe, OUTMODE_HIGH_Z);
1937 dib8000_set_power_mode(state, DIB8000M_POWER_INTERFACE_ONLY);
1938 return dib8000_set_adc_state(state, DIBX000_SLOW_ADC_OFF) | dib8000_set_adc_state(state, DIBX000_ADC_OFF);
1939}
1940
1941enum frontend_tune_state dib8000_get_tune_state(struct dvb_frontend *fe)
1942{
1943 struct dib8000_state *state = fe->demodulator_priv;
1944 return state->tune_state;
1945}
1946EXPORT_SYMBOL(dib8000_get_tune_state);
1947
1948int dib8000_set_tune_state(struct dvb_frontend *fe, enum frontend_tune_state tune_state)
1949{
1950 struct dib8000_state *state = fe->demodulator_priv;
1951 state->tune_state = tune_state;
1952 return 0;
1953}
1954EXPORT_SYMBOL(dib8000_set_tune_state);
1955
1956static int dib8000_get_frontend(struct dvb_frontend *fe, struct dvb_frontend_parameters *fep)
1957{
1958 struct dib8000_state *state = fe->demodulator_priv;
1959 u16 i, val = 0;
1960 fe_status_t stat;
1961 u8 index_frontend, sub_index_frontend;
1962
1963 fe->dtv_property_cache.bandwidth_hz = 6000000;
1964
1965 for (index_frontend = 1; (index_frontend < MAX_NUMBER_OF_FRONTENDS) && (state->fe[index_frontend] != NULL); index_frontend++) {
1966 state->fe[index_frontend]->ops.read_status(state->fe[index_frontend], &stat);
1967 if (stat&FE_HAS_SYNC) {
1968 dprintk("TMCC lock on the slave%i", index_frontend);
1969 /* synchronize the cache with the other frontends */
1970 state->fe[index_frontend]->ops.get_frontend(state->fe[index_frontend], fep);
1971 for (sub_index_frontend = 0; (sub_index_frontend < MAX_NUMBER_OF_FRONTENDS) && (state->fe[sub_index_frontend] != NULL); sub_index_frontend++) {
1972 if (sub_index_frontend != index_frontend) {
1973 state->fe[sub_index_frontend]->dtv_property_cache.isdbt_sb_mode = state->fe[index_frontend]->dtv_property_cache.isdbt_sb_mode;
1974 state->fe[sub_index_frontend]->dtv_property_cache.inversion = state->fe[index_frontend]->dtv_property_cache.inversion;
1975 state->fe[sub_index_frontend]->dtv_property_cache.transmission_mode = state->fe[index_frontend]->dtv_property_cache.transmission_mode;
1976 state->fe[sub_index_frontend]->dtv_property_cache.guard_interval = state->fe[index_frontend]->dtv_property_cache.guard_interval;
1977 state->fe[sub_index_frontend]->dtv_property_cache.isdbt_partial_reception = state->fe[index_frontend]->dtv_property_cache.isdbt_partial_reception;
1978 for (i = 0; i < 3; i++) {
1979 state->fe[sub_index_frontend]->dtv_property_cache.layer[i].segment_count = state->fe[index_frontend]->dtv_property_cache.layer[i].segment_count;
1980 state->fe[sub_index_frontend]->dtv_property_cache.layer[i].interleaving = state->fe[index_frontend]->dtv_property_cache.layer[i].interleaving;
1981 state->fe[sub_index_frontend]->dtv_property_cache.layer[i].fec = state->fe[index_frontend]->dtv_property_cache.layer[i].fec;
1982 state->fe[sub_index_frontend]->dtv_property_cache.layer[i].modulation = state->fe[index_frontend]->dtv_property_cache.layer[i].modulation;
1983 }
1984 }
1985 }
1986 return 0;
1987 }
1988 }
1989
1990 fe->dtv_property_cache.isdbt_sb_mode = dib8000_read_word(state, 508) & 0x1;
1991
1992 val = dib8000_read_word(state, 570);
1993 fe->dtv_property_cache.inversion = (val & 0x40) >> 6;
1994 switch ((val & 0x30) >> 4) {
1995 case 1:
1996 fe->dtv_property_cache.transmission_mode = TRANSMISSION_MODE_2K;
1997 break;
1998 case 3:
1999 default:
2000 fe->dtv_property_cache.transmission_mode = TRANSMISSION_MODE_8K;
2001 break;
2002 }
2003
2004 switch (val & 0x3) {
2005 case 0:
2006 fe->dtv_property_cache.guard_interval = GUARD_INTERVAL_1_32;
2007 dprintk("dib8000_get_frontend GI = 1/32 ");
2008 break;
2009 case 1:
2010 fe->dtv_property_cache.guard_interval = GUARD_INTERVAL_1_16;
2011 dprintk("dib8000_get_frontend GI = 1/16 ");
2012 break;
2013 case 2:
2014 dprintk("dib8000_get_frontend GI = 1/8 ");
2015 fe->dtv_property_cache.guard_interval = GUARD_INTERVAL_1_8;
2016 break;
2017 case 3:
2018 dprintk("dib8000_get_frontend GI = 1/4 ");
2019 fe->dtv_property_cache.guard_interval = GUARD_INTERVAL_1_4;
2020 break;
2021 }
2022
2023 val = dib8000_read_word(state, 505);
2024 fe->dtv_property_cache.isdbt_partial_reception = val & 1;
2025 dprintk("dib8000_get_frontend : partial_reception = %d ", fe->dtv_property_cache.isdbt_partial_reception);
2026
2027 for (i = 0; i < 3; i++) {
2028 val = dib8000_read_word(state, 493 + i);
2029 fe->dtv_property_cache.layer[i].segment_count = val & 0x0F;
2030 dprintk("dib8000_get_frontend : Layer %d segments = %d ", i, fe->dtv_property_cache.layer[i].segment_count);
2031
2032 val = dib8000_read_word(state, 499 + i);
2033 fe->dtv_property_cache.layer[i].interleaving = val & 0x3;
2034 dprintk("dib8000_get_frontend : Layer %d time_intlv = %d ", i, fe->dtv_property_cache.layer[i].interleaving);
2035
2036 val = dib8000_read_word(state, 481 + i);
2037 switch (val & 0x7) {
2038 case 1:
2039 fe->dtv_property_cache.layer[i].fec = FEC_1_2;
2040 dprintk("dib8000_get_frontend : Layer %d Code Rate = 1/2 ", i);
2041 break;
2042 case 2:
2043 fe->dtv_property_cache.layer[i].fec = FEC_2_3;
2044 dprintk("dib8000_get_frontend : Layer %d Code Rate = 2/3 ", i);
2045 break;
2046 case 3:
2047 fe->dtv_property_cache.layer[i].fec = FEC_3_4;
2048 dprintk("dib8000_get_frontend : Layer %d Code Rate = 3/4 ", i);
2049 break;
2050 case 5:
2051 fe->dtv_property_cache.layer[i].fec = FEC_5_6;
2052 dprintk("dib8000_get_frontend : Layer %d Code Rate = 5/6 ", i);
2053 break;
2054 default:
2055 fe->dtv_property_cache.layer[i].fec = FEC_7_8;
2056 dprintk("dib8000_get_frontend : Layer %d Code Rate = 7/8 ", i);
2057 break;
2058 }
2059
2060 val = dib8000_read_word(state, 487 + i);
2061 switch (val & 0x3) {
2062 case 0:
2063 dprintk("dib8000_get_frontend : Layer %d DQPSK ", i);
2064 fe->dtv_property_cache.layer[i].modulation = DQPSK;
2065 break;
2066 case 1:
2067 fe->dtv_property_cache.layer[i].modulation = QPSK;
2068 dprintk("dib8000_get_frontend : Layer %d QPSK ", i);
2069 break;
2070 case 2:
2071 fe->dtv_property_cache.layer[i].modulation = QAM_16;
2072 dprintk("dib8000_get_frontend : Layer %d QAM16 ", i);
2073 break;
2074 case 3:
2075 default:
2076 dprintk("dib8000_get_frontend : Layer %d QAM64 ", i);
2077 fe->dtv_property_cache.layer[i].modulation = QAM_64;
2078 break;
2079 }
2080 }
2081
2082 /* synchronize the cache with the other frontends */
2083 for (index_frontend = 1; (index_frontend < MAX_NUMBER_OF_FRONTENDS) && (state->fe[index_frontend] != NULL); index_frontend++) {
2084 state->fe[index_frontend]->dtv_property_cache.isdbt_sb_mode = fe->dtv_property_cache.isdbt_sb_mode;
2085 state->fe[index_frontend]->dtv_property_cache.inversion = fe->dtv_property_cache.inversion;
2086 state->fe[index_frontend]->dtv_property_cache.transmission_mode = fe->dtv_property_cache.transmission_mode;
2087 state->fe[index_frontend]->dtv_property_cache.guard_interval = fe->dtv_property_cache.guard_interval;
2088 state->fe[index_frontend]->dtv_property_cache.isdbt_partial_reception = fe->dtv_property_cache.isdbt_partial_reception;
2089 for (i = 0; i < 3; i++) {
2090 state->fe[index_frontend]->dtv_property_cache.layer[i].segment_count = fe->dtv_property_cache.layer[i].segment_count;
2091 state->fe[index_frontend]->dtv_property_cache.layer[i].interleaving = fe->dtv_property_cache.layer[i].interleaving;
2092 state->fe[index_frontend]->dtv_property_cache.layer[i].fec = fe->dtv_property_cache.layer[i].fec;
2093 state->fe[index_frontend]->dtv_property_cache.layer[i].modulation = fe->dtv_property_cache.layer[i].modulation;
2094 }
2095 }
2096 return 0;
2097}
2098
2099static int dib8000_set_frontend(struct dvb_frontend *fe, struct dvb_frontend_parameters *fep)
2100{
2101 struct dib8000_state *state = fe->demodulator_priv;
2102 u8 nbr_pending, exit_condition, index_frontend;
2103 s8 index_frontend_success = -1;
2104 int time, ret;
2105 int time_slave = FE_CALLBACK_TIME_NEVER;
2106
2107 if (state->fe[0]->dtv_property_cache.frequency == 0) {
2108 dprintk("dib8000: must at least specify frequency ");
2109 return 0;
2110 }
2111
2112 if (state->fe[0]->dtv_property_cache.bandwidth_hz == 0) {
2113 dprintk("dib8000: no bandwidth specified, set to default ");
2114 state->fe[0]->dtv_property_cache.bandwidth_hz = 6000000;
2115 }
2116
2117 for (index_frontend = 0; (index_frontend < MAX_NUMBER_OF_FRONTENDS) && (state->fe[index_frontend] != NULL); index_frontend++) {
2118 /* synchronization of the cache */
2119 state->fe[index_frontend]->dtv_property_cache.delivery_system = SYS_ISDBT;
2120 memcpy(&state->fe[index_frontend]->dtv_property_cache, &fe->dtv_property_cache, sizeof(struct dtv_frontend_properties));
2121
2122 dib8000_set_output_mode(state->fe[index_frontend], OUTMODE_HIGH_Z);
2123 if (state->fe[index_frontend]->ops.tuner_ops.set_params)
2124 state->fe[index_frontend]->ops.tuner_ops.set_params(state->fe[index_frontend], fep);
2125
2126 dib8000_set_tune_state(state->fe[index_frontend], CT_AGC_START);
2127 }
2128
2129 /* start up the AGC */
2130 do {
2131 time = dib8000_agc_startup(state->fe[0]);
2132 for (index_frontend = 1; (index_frontend < MAX_NUMBER_OF_FRONTENDS) && (state->fe[index_frontend] != NULL); index_frontend++) {
2133 time_slave = dib8000_agc_startup(state->fe[index_frontend]);
2134 if (time == FE_CALLBACK_TIME_NEVER)
2135 time = time_slave;
2136 else if ((time_slave != FE_CALLBACK_TIME_NEVER) && (time_slave > time))
2137 time = time_slave;
2138 }
2139 if (time != FE_CALLBACK_TIME_NEVER)
2140 msleep(time / 10);
2141 else
2142 break;
2143 exit_condition = 1;
2144 for (index_frontend = 0; (index_frontend < MAX_NUMBER_OF_FRONTENDS) && (state->fe[index_frontend] != NULL); index_frontend++) {
2145 if (dib8000_get_tune_state(state->fe[index_frontend]) != CT_AGC_STOP) {
2146 exit_condition = 0;
2147 break;
2148 }
2149 }
2150 } while (exit_condition == 0);
2151
2152 for (index_frontend = 0; (index_frontend < MAX_NUMBER_OF_FRONTENDS) && (state->fe[index_frontend] != NULL); index_frontend++)
2153 dib8000_set_tune_state(state->fe[index_frontend], CT_DEMOD_START);
2154
2155 if ((state->fe[0]->dtv_property_cache.delivery_system != SYS_ISDBT) ||
2156 (state->fe[0]->dtv_property_cache.inversion == INVERSION_AUTO) ||
2157 (state->fe[0]->dtv_property_cache.transmission_mode == TRANSMISSION_MODE_AUTO) ||
2158 (state->fe[0]->dtv_property_cache.guard_interval == GUARD_INTERVAL_AUTO) ||
2159 (((state->fe[0]->dtv_property_cache.isdbt_layer_enabled & (1 << 0)) != 0) &&
2160 (state->fe[0]->dtv_property_cache.layer[0].segment_count != 0xff) &&
2161 (state->fe[0]->dtv_property_cache.layer[0].segment_count != 0) &&
2162 ((state->fe[0]->dtv_property_cache.layer[0].modulation == QAM_AUTO) ||
2163 (state->fe[0]->dtv_property_cache.layer[0].fec == FEC_AUTO))) ||
2164 (((state->fe[0]->dtv_property_cache.isdbt_layer_enabled & (1 << 1)) != 0) &&
2165 (state->fe[0]->dtv_property_cache.layer[1].segment_count != 0xff) &&
2166 (state->fe[0]->dtv_property_cache.layer[1].segment_count != 0) &&
2167 ((state->fe[0]->dtv_property_cache.layer[1].modulation == QAM_AUTO) ||
2168 (state->fe[0]->dtv_property_cache.layer[1].fec == FEC_AUTO))) ||
2169 (((state->fe[0]->dtv_property_cache.isdbt_layer_enabled & (1 << 2)) != 0) &&
2170 (state->fe[0]->dtv_property_cache.layer[2].segment_count != 0xff) &&
2171 (state->fe[0]->dtv_property_cache.layer[2].segment_count != 0) &&
2172 ((state->fe[0]->dtv_property_cache.layer[2].modulation == QAM_AUTO) ||
2173 (state->fe[0]->dtv_property_cache.layer[2].fec == FEC_AUTO))) ||
2174 (((state->fe[0]->dtv_property_cache.layer[0].segment_count == 0) ||
2175 ((state->fe[0]->dtv_property_cache.isdbt_layer_enabled & (1 << 0)) == 0)) &&
2176 ((state->fe[0]->dtv_property_cache.layer[1].segment_count == 0) ||
2177 ((state->fe[0]->dtv_property_cache.isdbt_layer_enabled & (2 << 0)) == 0)) &&
2178 ((state->fe[0]->dtv_property_cache.layer[2].segment_count == 0) || ((state->fe[0]->dtv_property_cache.isdbt_layer_enabled & (3 << 0)) == 0)))) {
2179 int i = 80000;
2180 u8 found = 0;
2181 u8 tune_failed = 0;
2182
2183 for (index_frontend = 0; (index_frontend < MAX_NUMBER_OF_FRONTENDS) && (state->fe[index_frontend] != NULL); index_frontend++) {
2184 dib8000_set_bandwidth(state->fe[index_frontend], fe->dtv_property_cache.bandwidth_hz / 1000);
2185 dib8000_autosearch_start(state->fe[index_frontend]);
2186 }
2187
2188 do {
2189 msleep(20);
2190 nbr_pending = 0;
2191 exit_condition = 0; /* 0: tune pending; 1: tune failed; 2:tune success */
2192 for (index_frontend = 0; (index_frontend < MAX_NUMBER_OF_FRONTENDS) && (state->fe[index_frontend] != NULL); index_frontend++) {
2193 if (((tune_failed >> index_frontend) & 0x1) == 0) {
2194 found = dib8000_autosearch_irq(state->fe[index_frontend]);
2195 switch (found) {
2196 case 0: /* tune pending */
2197 nbr_pending++;
2198 break;
2199 case 2:
2200 dprintk("autosearch succeed on the frontend%i", index_frontend);
2201 exit_condition = 2;
2202 index_frontend_success = index_frontend;
2203 break;
2204 default:
2205 dprintk("unhandled autosearch result");
2206 case 1:
2207 dprintk("autosearch failed for the frontend%i", index_frontend);
2208 break;
2209 }
2210 }
2211 }
2212
2213 /* if all tune are done and no success, exit: tune failed */
2214 if ((nbr_pending == 0) && (exit_condition == 0))
2215 exit_condition = 1;
2216 } while ((exit_condition == 0) && i--);
2217
2218 if (exit_condition == 1) { /* tune failed */
2219 dprintk("tune failed");
2220 return 0;
2221 }
2222
2223 dprintk("tune success on frontend%i", index_frontend_success);
2224
2225 dib8000_get_frontend(fe, fep);
2226 }
2227
2228 for (index_frontend = 0, ret = 0; (ret >= 0) && (index_frontend < MAX_NUMBER_OF_FRONTENDS) && (state->fe[index_frontend] != NULL); index_frontend++)
2229 ret = dib8000_tune(state->fe[index_frontend]);
2230
2231 /* set output mode and diversity input */
2232 dib8000_set_output_mode(state->fe[0], state->cfg.output_mode);
2233 for (index_frontend = 1; (index_frontend < MAX_NUMBER_OF_FRONTENDS) && (state->fe[index_frontend] != NULL); index_frontend++) {
2234 dib8000_set_output_mode(state->fe[index_frontend], OUTMODE_DIVERSITY);
2235 dib8000_set_diversity_in(state->fe[index_frontend-1], 1);
2236 }
2237
2238 /* turn off the diversity of the last chip */
2239 dib8000_set_diversity_in(state->fe[index_frontend-1], 0);
2240
2241 return ret;
2242}
2243
2244static u16 dib8000_read_lock(struct dvb_frontend *fe)
2245{
2246 struct dib8000_state *state = fe->demodulator_priv;
2247
2248 return dib8000_read_word(state, 568);
2249}
2250
2251static int dib8000_read_status(struct dvb_frontend *fe, fe_status_t * stat)
2252{
2253 struct dib8000_state *state = fe->demodulator_priv;
2254 u16 lock_slave = 0, lock = dib8000_read_word(state, 568);
2255 u8 index_frontend;
2256
2257 for (index_frontend = 1; (index_frontend < MAX_NUMBER_OF_FRONTENDS) && (state->fe[index_frontend] != NULL); index_frontend++)
2258 lock_slave |= dib8000_read_lock(state->fe[index_frontend]);
2259
2260 *stat = 0;
2261
2262 if (((lock >> 13) & 1) || ((lock_slave >> 13) & 1))
2263 *stat |= FE_HAS_SIGNAL;
2264
2265 if (((lock >> 8) & 1) || ((lock_slave >> 8) & 1)) /* Equal */
2266 *stat |= FE_HAS_CARRIER;
2267
2268 if ((((lock >> 1) & 0xf) == 0xf) || (((lock_slave >> 1) & 0xf) == 0xf)) /* TMCC_SYNC */
2269 *stat |= FE_HAS_SYNC;
2270
2271 if ((((lock >> 12) & 1) || ((lock_slave >> 12) & 1)) && ((lock >> 5) & 7)) /* FEC MPEG */
2272 *stat |= FE_HAS_LOCK;
2273
2274 if (((lock >> 12) & 1) || ((lock_slave >> 12) & 1)) {
2275 lock = dib8000_read_word(state, 554); /* Viterbi Layer A */
2276 if (lock & 0x01)
2277 *stat |= FE_HAS_VITERBI;
2278
2279 lock = dib8000_read_word(state, 555); /* Viterbi Layer B */
2280 if (lock & 0x01)
2281 *stat |= FE_HAS_VITERBI;
2282
2283 lock = dib8000_read_word(state, 556); /* Viterbi Layer C */
2284 if (lock & 0x01)
2285 *stat |= FE_HAS_VITERBI;
2286 }
2287
2288 return 0;
2289}
2290
2291static int dib8000_read_ber(struct dvb_frontend *fe, u32 * ber)
2292{
2293 struct dib8000_state *state = fe->demodulator_priv;
2294 *ber = (dib8000_read_word(state, 560) << 16) | dib8000_read_word(state, 561); // 13 segments
2295 return 0;
2296}
2297
2298static int dib8000_read_unc_blocks(struct dvb_frontend *fe, u32 * unc)
2299{
2300 struct dib8000_state *state = fe->demodulator_priv;
2301 *unc = dib8000_read_word(state, 565); // packet error on 13 seg
2302 return 0;
2303}
2304
2305static int dib8000_read_signal_strength(struct dvb_frontend *fe, u16 * strength)
2306{
2307 struct dib8000_state *state = fe->demodulator_priv;
2308 u8 index_frontend;
2309 u16 val;
2310
2311 *strength = 0;
2312 for (index_frontend = 1; (index_frontend < MAX_NUMBER_OF_FRONTENDS) && (state->fe[index_frontend] != NULL); index_frontend++) {
2313 state->fe[index_frontend]->ops.read_signal_strength(state->fe[index_frontend], &val);
2314 if (val > 65535 - *strength)
2315 *strength = 65535;
2316 else
2317 *strength += val;
2318 }
2319
2320 val = 65535 - dib8000_read_word(state, 390);
2321 if (val > 65535 - *strength)
2322 *strength = 65535;
2323 else
2324 *strength += val;
2325 return 0;
2326}
2327
2328static u32 dib8000_get_snr(struct dvb_frontend *fe)
2329{
2330 struct dib8000_state *state = fe->demodulator_priv;
2331 u32 n, s, exp;
2332 u16 val;
2333
2334 val = dib8000_read_word(state, 542);
2335 n = (val >> 6) & 0xff;
2336 exp = (val & 0x3f);
2337 if ((exp & 0x20) != 0)
2338 exp -= 0x40;
2339 n <<= exp+16;
2340
2341 val = dib8000_read_word(state, 543);
2342 s = (val >> 6) & 0xff;
2343 exp = (val & 0x3f);
2344 if ((exp & 0x20) != 0)
2345 exp -= 0x40;
2346 s <<= exp+16;
2347
2348 if (n > 0) {
2349 u32 t = (s/n) << 16;
2350 return t + ((s << 16) - n*t) / n;
2351 }
2352 return 0xffffffff;
2353}
2354
2355static int dib8000_read_snr(struct dvb_frontend *fe, u16 * snr)
2356{
2357 struct dib8000_state *state = fe->demodulator_priv;
2358 u8 index_frontend;
2359 u32 snr_master;
2360
2361 snr_master = dib8000_get_snr(fe);
2362 for (index_frontend = 1; (index_frontend < MAX_NUMBER_OF_FRONTENDS) && (state->fe[index_frontend] != NULL); index_frontend++)
2363 snr_master += dib8000_get_snr(state->fe[index_frontend]);
2364
2365 if (snr_master != 0) {
2366 snr_master = 10*intlog10(snr_master>>16);
2367 *snr = snr_master / ((1 << 24) / 10);
2368 }
2369 else
2370 *snr = 0;
2371
2372 return 0;
2373}
2374
2375int dib8000_set_slave_frontend(struct dvb_frontend *fe, struct dvb_frontend *fe_slave)
2376{
2377 struct dib8000_state *state = fe->demodulator_priv;
2378 u8 index_frontend = 1;
2379
2380 while ((index_frontend < MAX_NUMBER_OF_FRONTENDS) && (state->fe[index_frontend] != NULL))
2381 index_frontend++;
2382 if (index_frontend < MAX_NUMBER_OF_FRONTENDS) {
2383 dprintk("set slave fe %p to index %i", fe_slave, index_frontend);
2384 state->fe[index_frontend] = fe_slave;
2385 return 0;
2386 }
2387
2388 dprintk("too many slave frontend");
2389 return -ENOMEM;
2390}
2391EXPORT_SYMBOL(dib8000_set_slave_frontend);
2392
2393int dib8000_remove_slave_frontend(struct dvb_frontend *fe)
2394{
2395 struct dib8000_state *state = fe->demodulator_priv;
2396 u8 index_frontend = 1;
2397
2398 while ((index_frontend < MAX_NUMBER_OF_FRONTENDS) && (state->fe[index_frontend] != NULL))
2399 index_frontend++;
2400 if (index_frontend != 1) {
2401 dprintk("remove slave fe %p (index %i)", state->fe[index_frontend-1], index_frontend-1);
2402 state->fe[index_frontend] = NULL;
2403 return 0;
2404 }
2405
2406 dprintk("no frontend to be removed");
2407 return -ENODEV;
2408}
2409EXPORT_SYMBOL(dib8000_remove_slave_frontend);
2410
2411struct dvb_frontend *dib8000_get_slave_frontend(struct dvb_frontend *fe, int slave_index)
2412{
2413 struct dib8000_state *state = fe->demodulator_priv;
2414
2415 if (slave_index >= MAX_NUMBER_OF_FRONTENDS)
2416 return NULL;
2417 return state->fe[slave_index];
2418}
2419EXPORT_SYMBOL(dib8000_get_slave_frontend);
2420
2421
2422int dib8000_i2c_enumeration(struct i2c_adapter *host, int no_of_demods, u8 default_addr, u8 first_addr)
2423{
2424 int k = 0, ret = 0;
2425 u8 new_addr = 0;
2426 struct i2c_device client = {.adap = host };
2427
2428 client.i2c_write_buffer = kzalloc(4 * sizeof(u8), GFP_KERNEL);
2429 if (!client.i2c_write_buffer) {
2430 dprintk("%s: not enough memory", __func__);
2431 return -ENOMEM;
2432 }
2433 client.i2c_read_buffer = kzalloc(4 * sizeof(u8), GFP_KERNEL);
2434 if (!client.i2c_read_buffer) {
2435 dprintk("%s: not enough memory", __func__);
2436 ret = -ENOMEM;
2437 goto error_memory;
2438 }
2439
2440 for (k = no_of_demods - 1; k >= 0; k--) {
2441 /* designated i2c address */
2442 new_addr = first_addr + (k << 1);
2443
2444 client.addr = new_addr;
2445 dib8000_i2c_write16(&client, 1287, 0x0003); /* sram lead in, rdy */
2446 if (dib8000_identify(&client) == 0) {
2447 dib8000_i2c_write16(&client, 1287, 0x0003); /* sram lead in, rdy */
2448 client.addr = default_addr;
2449 if (dib8000_identify(&client) == 0) {
2450 dprintk("#%d: not identified", k);
2451 ret = -EINVAL;
2452 goto error;
2453 }
2454 }
2455
2456 /* start diversity to pull_down div_str - just for i2c-enumeration */
2457 dib8000_i2c_write16(&client, 1286, (1 << 10) | (4 << 6));
2458
2459 /* set new i2c address and force divstart */
2460 dib8000_i2c_write16(&client, 1285, (new_addr << 2) | 0x2);
2461 client.addr = new_addr;
2462 dib8000_identify(&client);
2463
2464 dprintk("IC %d initialized (to i2c_address 0x%x)", k, new_addr);
2465 }
2466
2467 for (k = 0; k < no_of_demods; k++) {
2468 new_addr = first_addr | (k << 1);
2469 client.addr = new_addr;
2470
2471 // unforce divstr
2472 dib8000_i2c_write16(&client, 1285, new_addr << 2);
2473
2474 /* deactivate div - it was just for i2c-enumeration */
2475 dib8000_i2c_write16(&client, 1286, 0);
2476 }
2477
2478error:
2479 kfree(client.i2c_read_buffer);
2480error_memory:
2481 kfree(client.i2c_write_buffer);
2482
2483 return ret;
2484}
2485
2486EXPORT_SYMBOL(dib8000_i2c_enumeration);
2487static int dib8000_fe_get_tune_settings(struct dvb_frontend *fe, struct dvb_frontend_tune_settings *tune)
2488{
2489 tune->min_delay_ms = 1000;
2490 tune->step_size = 0;
2491 tune->max_drift = 0;
2492 return 0;
2493}
2494
2495static void dib8000_release(struct dvb_frontend *fe)
2496{
2497 struct dib8000_state *st = fe->demodulator_priv;
2498 u8 index_frontend;
2499
2500 for (index_frontend = 1; (index_frontend < MAX_NUMBER_OF_FRONTENDS) && (st->fe[index_frontend] != NULL); index_frontend++)
2501 dvb_frontend_detach(st->fe[index_frontend]);
2502
2503 dibx000_exit_i2c_master(&st->i2c_master);
2504 kfree(st->fe[0]);
2505 kfree(st);
2506}
2507
2508struct i2c_adapter *dib8000_get_i2c_master(struct dvb_frontend *fe, enum dibx000_i2c_interface intf, int gating)
2509{
2510 struct dib8000_state *st = fe->demodulator_priv;
2511 return dibx000_get_i2c_adapter(&st->i2c_master, intf, gating);
2512}
2513
2514EXPORT_SYMBOL(dib8000_get_i2c_master);
2515
2516int dib8000_pid_filter_ctrl(struct dvb_frontend *fe, u8 onoff)
2517{
2518 struct dib8000_state *st = fe->demodulator_priv;
2519 u16 val = dib8000_read_word(st, 299) & 0xffef;
2520 val |= (onoff & 0x1) << 4;
2521
2522 dprintk("pid filter enabled %d", onoff);
2523 return dib8000_write_word(st, 299, val);
2524}
2525EXPORT_SYMBOL(dib8000_pid_filter_ctrl);
2526
2527int dib8000_pid_filter(struct dvb_frontend *fe, u8 id, u16 pid, u8 onoff)
2528{
2529 struct dib8000_state *st = fe->demodulator_priv;
2530 dprintk("Index %x, PID %d, OnOff %d", id, pid, onoff);
2531 return dib8000_write_word(st, 305 + id, onoff ? (1 << 13) | pid : 0);
2532}
2533EXPORT_SYMBOL(dib8000_pid_filter);
2534
2535static const struct dvb_frontend_ops dib8000_ops = {
2536 .info = {
2537 .name = "DiBcom 8000 ISDB-T",
2538 .type = FE_OFDM,
2539 .frequency_min = 44250000,
2540 .frequency_max = 867250000,
2541 .frequency_stepsize = 62500,
2542 .caps = FE_CAN_INVERSION_AUTO |
2543 FE_CAN_FEC_1_2 | FE_CAN_FEC_2_3 | FE_CAN_FEC_3_4 |
2544 FE_CAN_FEC_5_6 | FE_CAN_FEC_7_8 | FE_CAN_FEC_AUTO |
2545 FE_CAN_QPSK | FE_CAN_QAM_16 | FE_CAN_QAM_64 | FE_CAN_QAM_AUTO |
2546 FE_CAN_TRANSMISSION_MODE_AUTO | FE_CAN_GUARD_INTERVAL_AUTO | FE_CAN_RECOVER | FE_CAN_HIERARCHY_AUTO,
2547 },
2548
2549 .release = dib8000_release,
2550
2551 .init = dib8000_wakeup,
2552 .sleep = dib8000_sleep,
2553
2554 .set_frontend = dib8000_set_frontend,
2555 .get_tune_settings = dib8000_fe_get_tune_settings,
2556 .get_frontend = dib8000_get_frontend,
2557
2558 .read_status = dib8000_read_status,
2559 .read_ber = dib8000_read_ber,
2560 .read_signal_strength = dib8000_read_signal_strength,
2561 .read_snr = dib8000_read_snr,
2562 .read_ucblocks = dib8000_read_unc_blocks,
2563};
2564
2565struct dvb_frontend *dib8000_attach(struct i2c_adapter *i2c_adap, u8 i2c_addr, struct dib8000_config *cfg)
2566{
2567 struct dvb_frontend *fe;
2568 struct dib8000_state *state;
2569
2570 dprintk("dib8000_attach");
2571
2572 state = kzalloc(sizeof(struct dib8000_state), GFP_KERNEL);
2573 if (state == NULL)
2574 return NULL;
2575 fe = kzalloc(sizeof(struct dvb_frontend), GFP_KERNEL);
2576 if (fe == NULL)
2577 goto error;
2578
2579 memcpy(&state->cfg, cfg, sizeof(struct dib8000_config));
2580 state->i2c.adap = i2c_adap;
2581 state->i2c.addr = i2c_addr;
2582 state->i2c.i2c_write_buffer = state->i2c_write_buffer;
2583 state->i2c.i2c_read_buffer = state->i2c_read_buffer;
2584 state->gpio_val = cfg->gpio_val;
2585 state->gpio_dir = cfg->gpio_dir;
2586
2587 /* Ensure the output mode remains at the previous default if it's
2588 * not specifically set by the caller.
2589 */
2590 if ((state->cfg.output_mode != OUTMODE_MPEG2_SERIAL) && (state->cfg.output_mode != OUTMODE_MPEG2_PAR_GATED_CLK))
2591 state->cfg.output_mode = OUTMODE_MPEG2_FIFO;
2592
2593 state->fe[0] = fe;
2594 fe->demodulator_priv = state;
2595 memcpy(&state->fe[0]->ops, &dib8000_ops, sizeof(struct dvb_frontend_ops));
2596
2597 state->timf_default = cfg->pll->timf;
2598
2599 if (dib8000_identify(&state->i2c) == 0)
2600 goto error;
2601
2602 dibx000_init_i2c_master(&state->i2c_master, DIB8000, state->i2c.adap, state->i2c.addr);
2603
2604 dib8000_reset(fe);
2605
2606 dib8000_write_word(state, 285, (dib8000_read_word(state, 285) & ~0x60) | (3 << 5)); /* ber_rs_len = 3 */
2607
2608 return fe;
2609
2610 error:
2611 kfree(state);
2612 return NULL;
2613}
2614
2615EXPORT_SYMBOL(dib8000_attach);
2616
2617MODULE_AUTHOR("Olivier Grenie <Olivier.Grenie@dibcom.fr, " "Patrick Boettcher <pboettcher@dibcom.fr>");
2618MODULE_DESCRIPTION("Driver for the DiBcom 8000 ISDB-T demodulator");
2619MODULE_LICENSE("GPL");