Back to home page

OSCL-LXR

 
 

    


0001 // SPDX-License-Identifier: GPL-2.0-only
0002 /*
0003  * Driver for DiBcom DiB3000MC/P-demodulator.
0004  *
0005  * Copyright (C) 2004-7 DiBcom (http://www.dibcom.fr/)
0006  * Copyright (C) 2004-5 Patrick Boettcher (patrick.boettcher@posteo.de)
0007  *
0008  * This code is partially based on the previous dib3000mc.c .
0009  */
0010 
0011 #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
0012 
0013 #include <linux/kernel.h>
0014 #include <linux/slab.h>
0015 #include <linux/i2c.h>
0016 
0017 #include <media/dvb_frontend.h>
0018 
0019 #include "dib3000mc.h"
0020 
0021 static int debug;
0022 module_param(debug, int, 0644);
0023 MODULE_PARM_DESC(debug, "turn on debugging (default: 0)");
0024 
0025 static int buggy_sfn_workaround;
0026 module_param(buggy_sfn_workaround, int, 0644);
0027 MODULE_PARM_DESC(buggy_sfn_workaround, "Enable work-around for buggy SFNs (default: 0)");
0028 
0029 #define dprintk(fmt, arg...) do {                   \
0030     if (debug)                          \
0031         printk(KERN_DEBUG pr_fmt("%s: " fmt),           \
0032                __func__, ##arg);                \
0033 } while (0)
0034 
0035 struct dib3000mc_state {
0036     struct dvb_frontend demod;
0037     struct dib3000mc_config *cfg;
0038 
0039     u8 i2c_addr;
0040     struct i2c_adapter *i2c_adap;
0041 
0042     struct dibx000_i2c_master i2c_master;
0043 
0044     u32 timf;
0045 
0046     u32 current_bandwidth;
0047 
0048     u16 dev_id;
0049 
0050     u8 sfn_workaround_active :1;
0051 };
0052 
0053 static u16 dib3000mc_read_word(struct dib3000mc_state *state, u16 reg)
0054 {
0055     struct i2c_msg msg[2] = {
0056         { .addr = state->i2c_addr >> 1, .flags = 0,        .len = 2 },
0057         { .addr = state->i2c_addr >> 1, .flags = I2C_M_RD, .len = 2 },
0058     };
0059     u16 word;
0060     u8 *b;
0061 
0062     b = kmalloc(4, GFP_KERNEL);
0063     if (!b)
0064         return 0;
0065 
0066     b[0] = (reg >> 8) | 0x80;
0067     b[1] = reg;
0068     b[2] = 0;
0069     b[3] = 0;
0070 
0071     msg[0].buf = b;
0072     msg[1].buf = b + 2;
0073 
0074     if (i2c_transfer(state->i2c_adap, msg, 2) != 2)
0075         dprintk("i2c read error on %d\n",reg);
0076 
0077     word = (b[2] << 8) | b[3];
0078     kfree(b);
0079 
0080     return word;
0081 }
0082 
0083 static int dib3000mc_write_word(struct dib3000mc_state *state, u16 reg, u16 val)
0084 {
0085     struct i2c_msg msg = {
0086         .addr = state->i2c_addr >> 1, .flags = 0, .len = 4
0087     };
0088     int rc;
0089     u8 *b;
0090 
0091     b = kmalloc(4, GFP_KERNEL);
0092     if (!b)
0093         return -ENOMEM;
0094 
0095     b[0] = reg >> 8;
0096     b[1] = reg;
0097     b[2] = val >> 8;
0098     b[3] = val;
0099 
0100     msg.buf = b;
0101 
0102     rc = i2c_transfer(state->i2c_adap, &msg, 1) != 1 ? -EREMOTEIO : 0;
0103     kfree(b);
0104 
0105     return rc;
0106 }
0107 
0108 static int dib3000mc_identify(struct dib3000mc_state *state)
0109 {
0110     u16 value;
0111     if ((value = dib3000mc_read_word(state, 1025)) != 0x01b3) {
0112         dprintk("-E-  DiB3000MC/P: wrong Vendor ID (read=0x%x)\n",value);
0113         return -EREMOTEIO;
0114     }
0115 
0116     value = dib3000mc_read_word(state, 1026);
0117     if (value != 0x3001 && value != 0x3002) {
0118         dprintk("-E-  DiB3000MC/P: wrong Device ID (%x)\n",value);
0119         return -EREMOTEIO;
0120     }
0121     state->dev_id = value;
0122 
0123     dprintk("-I-  found DiB3000MC/P: %x\n",state->dev_id);
0124 
0125     return 0;
0126 }
0127 
0128 static int dib3000mc_set_timing(struct dib3000mc_state *state, s16 nfft, u32 bw, u8 update_offset)
0129 {
0130     u32 timf;
0131 
0132     if (state->timf == 0) {
0133         timf = 1384402; // default value for 8MHz
0134         if (update_offset)
0135             msleep(200); // first time we do an update
0136     } else
0137         timf = state->timf;
0138 
0139     timf *= (bw / 1000);
0140 
0141     if (update_offset) {
0142         s16 tim_offs = dib3000mc_read_word(state, 416);
0143 
0144         if (tim_offs &  0x2000)
0145             tim_offs -= 0x4000;
0146 
0147         if (nfft == TRANSMISSION_MODE_2K)
0148             tim_offs *= 4;
0149 
0150         timf += tim_offs;
0151         state->timf = timf / (bw / 1000);
0152     }
0153 
0154     dprintk("timf: %d\n", timf);
0155 
0156     dib3000mc_write_word(state, 23, (u16) (timf >> 16));
0157     dib3000mc_write_word(state, 24, (u16) (timf      ) & 0xffff);
0158 
0159     return 0;
0160 }
0161 
0162 static int dib3000mc_setup_pwm_state(struct dib3000mc_state *state)
0163 {
0164     u16 reg_51, reg_52 = state->cfg->agc->setup & 0xfefb;
0165     if (state->cfg->pwm3_inversion) {
0166         reg_51 =  (2 << 14) | (0 << 10) | (7 << 6) | (2 << 2) | (2 << 0);
0167         reg_52 |= (1 << 2);
0168     } else {
0169         reg_51 = (2 << 14) | (4 << 10) | (7 << 6) | (2 << 2) | (2 << 0);
0170         reg_52 |= (1 << 8);
0171     }
0172     dib3000mc_write_word(state, 51, reg_51);
0173     dib3000mc_write_word(state, 52, reg_52);
0174 
0175     if (state->cfg->use_pwm3)
0176         dib3000mc_write_word(state, 245, (1 << 3) | (1 << 0));
0177     else
0178         dib3000mc_write_word(state, 245, 0);
0179 
0180     dib3000mc_write_word(state, 1040, 0x3);
0181     return 0;
0182 }
0183 
0184 static int dib3000mc_set_output_mode(struct dib3000mc_state *state, int mode)
0185 {
0186     int    ret = 0;
0187     u16 fifo_threshold = 1792;
0188     u16 outreg = 0;
0189     u16 outmode = 0;
0190     u16 elecout = 1;
0191     u16 smo_reg = dib3000mc_read_word(state, 206) & 0x0010; /* keep the pid_parse bit */
0192 
0193     dprintk("-I-  Setting output mode for demod %p to %d\n",
0194             &state->demod, mode);
0195 
0196     switch (mode) {
0197         case OUTMODE_HIGH_Z:  // disable
0198             elecout = 0;
0199             break;
0200         case OUTMODE_MPEG2_PAR_GATED_CLK:   // STBs with parallel gated clock
0201             outmode = 0;
0202             break;
0203         case OUTMODE_MPEG2_PAR_CONT_CLK:    // STBs with parallel continues clock
0204             outmode = 1;
0205             break;
0206         case OUTMODE_MPEG2_SERIAL:          // STBs with serial input
0207             outmode = 2;
0208             break;
0209         case OUTMODE_MPEG2_FIFO:            // e.g. USB feeding
0210             elecout = 3;
0211             /*ADDR @ 206 :
0212             P_smo_error_discard  [1;6:6] = 0
0213             P_smo_rs_discard     [1;5:5] = 0
0214             P_smo_pid_parse      [1;4:4] = 0
0215             P_smo_fifo_flush     [1;3:3] = 0
0216             P_smo_mode           [2;2:1] = 11
0217             P_smo_ovf_prot       [1;0:0] = 0
0218             */
0219             smo_reg |= 3 << 1;
0220             fifo_threshold = 512;
0221             outmode = 5;
0222             break;
0223         case OUTMODE_DIVERSITY:
0224             outmode = 4;
0225             elecout = 1;
0226             break;
0227         default:
0228             dprintk("Unhandled output_mode passed to be set for demod %p\n",&state->demod);
0229             outmode = 0;
0230             break;
0231     }
0232 
0233     if ((state->cfg->output_mpeg2_in_188_bytes))
0234         smo_reg |= (1 << 5); // P_smo_rs_discard     [1;5:5] = 1
0235 
0236     outreg = dib3000mc_read_word(state, 244) & 0x07FF;
0237     outreg |= (outmode << 11);
0238     ret |= dib3000mc_write_word(state,  244, outreg);
0239     ret |= dib3000mc_write_word(state,  206, smo_reg);   /*smo_ mode*/
0240     ret |= dib3000mc_write_word(state,  207, fifo_threshold); /* synchronous fread */
0241     ret |= dib3000mc_write_word(state, 1040, elecout);         /* P_out_cfg */
0242     return ret;
0243 }
0244 
0245 static int dib3000mc_set_bandwidth(struct dib3000mc_state *state, u32 bw)
0246 {
0247     u16 bw_cfg[6] = { 0 };
0248     u16 imp_bw_cfg[3] = { 0 };
0249     u16 reg;
0250 
0251 /* settings here are for 27.7MHz */
0252     switch (bw) {
0253         case 8000:
0254             bw_cfg[0] = 0x0019; bw_cfg[1] = 0x5c30; bw_cfg[2] = 0x0054; bw_cfg[3] = 0x88a0; bw_cfg[4] = 0x01a6; bw_cfg[5] = 0xab20;
0255             imp_bw_cfg[0] = 0x04db; imp_bw_cfg[1] = 0x00db; imp_bw_cfg[2] = 0x00b7;
0256             break;
0257 
0258         case 7000:
0259             bw_cfg[0] = 0x001c; bw_cfg[1] = 0xfba5; bw_cfg[2] = 0x0060; bw_cfg[3] = 0x9c25; bw_cfg[4] = 0x01e3; bw_cfg[5] = 0x0cb7;
0260             imp_bw_cfg[0] = 0x04c0; imp_bw_cfg[1] = 0x00c0; imp_bw_cfg[2] = 0x00a0;
0261             break;
0262 
0263         case 6000:
0264             bw_cfg[0] = 0x0021; bw_cfg[1] = 0xd040; bw_cfg[2] = 0x0070; bw_cfg[3] = 0xb62b; bw_cfg[4] = 0x0233; bw_cfg[5] = 0x8ed5;
0265             imp_bw_cfg[0] = 0x04a5; imp_bw_cfg[1] = 0x00a5; imp_bw_cfg[2] = 0x0089;
0266             break;
0267 
0268         case 5000:
0269             bw_cfg[0] = 0x0028; bw_cfg[1] = 0x9380; bw_cfg[2] = 0x0087; bw_cfg[3] = 0x4100; bw_cfg[4] = 0x02a4; bw_cfg[5] = 0x4500;
0270             imp_bw_cfg[0] = 0x0489; imp_bw_cfg[1] = 0x0089; imp_bw_cfg[2] = 0x0072;
0271             break;
0272 
0273         default: return -EINVAL;
0274     }
0275 
0276     for (reg = 6; reg < 12; reg++)
0277         dib3000mc_write_word(state, reg, bw_cfg[reg - 6]);
0278     dib3000mc_write_word(state, 12, 0x0000);
0279     dib3000mc_write_word(state, 13, 0x03e8);
0280     dib3000mc_write_word(state, 14, 0x0000);
0281     dib3000mc_write_word(state, 15, 0x03f2);
0282     dib3000mc_write_word(state, 16, 0x0001);
0283     dib3000mc_write_word(state, 17, 0xb0d0);
0284     // P_sec_len
0285     dib3000mc_write_word(state, 18, 0x0393);
0286     dib3000mc_write_word(state, 19, 0x8700);
0287 
0288     for (reg = 55; reg < 58; reg++)
0289         dib3000mc_write_word(state, reg, imp_bw_cfg[reg - 55]);
0290 
0291     // Timing configuration
0292     dib3000mc_set_timing(state, TRANSMISSION_MODE_2K, bw, 0);
0293 
0294     return 0;
0295 }
0296 
0297 static u16 impulse_noise_val[29] =
0298 
0299 {
0300     0x38, 0x6d9, 0x3f28, 0x7a7, 0x3a74, 0x196, 0x32a, 0x48c, 0x3ffe, 0x7f3,
0301     0x2d94, 0x76, 0x53d, 0x3ff8, 0x7e3, 0x3320, 0x76, 0x5b3, 0x3feb, 0x7d2,
0302     0x365e, 0x76, 0x48c, 0x3ffe, 0x5b3, 0x3feb, 0x76, 0x0000, 0xd
0303 };
0304 
0305 static void dib3000mc_set_impulse_noise(struct dib3000mc_state *state, u8 mode, s16 nfft)
0306 {
0307     u16 i;
0308     for (i = 58; i < 87; i++)
0309         dib3000mc_write_word(state, i, impulse_noise_val[i-58]);
0310 
0311     if (nfft == TRANSMISSION_MODE_8K) {
0312         dib3000mc_write_word(state, 58, 0x3b);
0313         dib3000mc_write_word(state, 84, 0x00);
0314         dib3000mc_write_word(state, 85, 0x8200);
0315     }
0316 
0317     dib3000mc_write_word(state, 34, 0x1294);
0318     dib3000mc_write_word(state, 35, 0x1ff8);
0319     if (mode == 1)
0320         dib3000mc_write_word(state, 55, dib3000mc_read_word(state, 55) | (1 << 10));
0321 }
0322 
0323 static int dib3000mc_init(struct dvb_frontend *demod)
0324 {
0325     struct dib3000mc_state *state = demod->demodulator_priv;
0326     struct dibx000_agc_config *agc = state->cfg->agc;
0327 
0328     // Restart Configuration
0329     dib3000mc_write_word(state, 1027, 0x8000);
0330     dib3000mc_write_word(state, 1027, 0x0000);
0331 
0332     // power up the demod + mobility configuration
0333     dib3000mc_write_word(state, 140, 0x0000);
0334     dib3000mc_write_word(state, 1031, 0);
0335 
0336     if (state->cfg->mobile_mode) {
0337         dib3000mc_write_word(state, 139,  0x0000);
0338         dib3000mc_write_word(state, 141,  0x0000);
0339         dib3000mc_write_word(state, 175,  0x0002);
0340         dib3000mc_write_word(state, 1032, 0x0000);
0341     } else {
0342         dib3000mc_write_word(state, 139,  0x0001);
0343         dib3000mc_write_word(state, 141,  0x0000);
0344         dib3000mc_write_word(state, 175,  0x0000);
0345         dib3000mc_write_word(state, 1032, 0x012C);
0346     }
0347     dib3000mc_write_word(state, 1033, 0x0000);
0348 
0349     // P_clk_cfg
0350     dib3000mc_write_word(state, 1037, 0x3130);
0351 
0352     // other configurations
0353 
0354     // P_ctrl_sfreq
0355     dib3000mc_write_word(state, 33, (5 << 0));
0356     dib3000mc_write_word(state, 88, (1 << 10) | (0x10 << 0));
0357 
0358     // Phase noise control
0359     // P_fft_phacor_inh, P_fft_phacor_cpe, P_fft_powrange
0360     dib3000mc_write_word(state, 99, (1 << 9) | (0x20 << 0));
0361 
0362     if (state->cfg->phase_noise_mode == 0)
0363         dib3000mc_write_word(state, 111, 0x00);
0364     else
0365         dib3000mc_write_word(state, 111, 0x02);
0366 
0367     // P_agc_global
0368     dib3000mc_write_word(state, 50, 0x8000);
0369 
0370     // agc setup misc
0371     dib3000mc_setup_pwm_state(state);
0372 
0373     // P_agc_counter_lock
0374     dib3000mc_write_word(state, 53, 0x87);
0375     // P_agc_counter_unlock
0376     dib3000mc_write_word(state, 54, 0x87);
0377 
0378     /* agc */
0379     dib3000mc_write_word(state, 36, state->cfg->max_time);
0380     dib3000mc_write_word(state, 37, (state->cfg->agc_command1 << 13) | (state->cfg->agc_command2 << 12) | (0x1d << 0));
0381     dib3000mc_write_word(state, 38, state->cfg->pwm3_value);
0382     dib3000mc_write_word(state, 39, state->cfg->ln_adc_level);
0383 
0384     // set_agc_loop_Bw
0385     dib3000mc_write_word(state, 40, 0x0179);
0386     dib3000mc_write_word(state, 41, 0x03f0);
0387 
0388     dib3000mc_write_word(state, 42, agc->agc1_max);
0389     dib3000mc_write_word(state, 43, agc->agc1_min);
0390     dib3000mc_write_word(state, 44, agc->agc2_max);
0391     dib3000mc_write_word(state, 45, agc->agc2_min);
0392     dib3000mc_write_word(state, 46, (agc->agc1_pt1 << 8) | agc->agc1_pt2);
0393     dib3000mc_write_word(state, 47, (agc->agc1_slope1 << 8) | agc->agc1_slope2);
0394     dib3000mc_write_word(state, 48, (agc->agc2_pt1 << 8) | agc->agc2_pt2);
0395     dib3000mc_write_word(state, 49, (agc->agc2_slope1 << 8) | agc->agc2_slope2);
0396 
0397 // Begin: TimeOut registers
0398     // P_pha3_thres
0399     dib3000mc_write_word(state, 110, 3277);
0400     // P_timf_alpha = 6, P_corm_alpha = 6, P_corm_thres = 0x80
0401     dib3000mc_write_word(state,  26, 0x6680);
0402     // lock_mask0
0403     dib3000mc_write_word(state, 1, 4);
0404     // lock_mask1
0405     dib3000mc_write_word(state, 2, 4);
0406     // lock_mask2
0407     dib3000mc_write_word(state, 3, 0x1000);
0408     // P_search_maxtrial=1
0409     dib3000mc_write_word(state, 5, 1);
0410 
0411     dib3000mc_set_bandwidth(state, 8000);
0412 
0413     // div_lock_mask
0414     dib3000mc_write_word(state,  4, 0x814);
0415 
0416     dib3000mc_write_word(state, 21, (1 << 9) | 0x164);
0417     dib3000mc_write_word(state, 22, 0x463d);
0418 
0419     // Spurious rm cfg
0420     // P_cspu_regul, P_cspu_win_cut
0421     dib3000mc_write_word(state, 120, 0x200f);
0422     // P_adp_selec_monit
0423     dib3000mc_write_word(state, 134, 0);
0424 
0425     // Fec cfg
0426     dib3000mc_write_word(state, 195, 0x10);
0427 
0428     // diversity register: P_dvsy_sync_wait..
0429     dib3000mc_write_word(state, 180, 0x2FF0);
0430 
0431     // Impulse noise configuration
0432     dib3000mc_set_impulse_noise(state, 0, TRANSMISSION_MODE_8K);
0433 
0434     // output mode set-up
0435     dib3000mc_set_output_mode(state, OUTMODE_HIGH_Z);
0436 
0437     /* close the i2c-gate */
0438     dib3000mc_write_word(state, 769, (1 << 7) );
0439 
0440     return 0;
0441 }
0442 
0443 static int dib3000mc_sleep(struct dvb_frontend *demod)
0444 {
0445     struct dib3000mc_state *state = demod->demodulator_priv;
0446 
0447     dib3000mc_write_word(state, 1031, 0xFFFF);
0448     dib3000mc_write_word(state, 1032, 0xFFFF);
0449     dib3000mc_write_word(state, 1033, 0xFFF0);
0450 
0451     return 0;
0452 }
0453 
0454 static void dib3000mc_set_adp_cfg(struct dib3000mc_state *state, s16 qam)
0455 {
0456     u16 cfg[4] = { 0 },reg;
0457     switch (qam) {
0458         case QPSK:
0459             cfg[0] = 0x099a; cfg[1] = 0x7fae; cfg[2] = 0x0333; cfg[3] = 0x7ff0;
0460             break;
0461         case QAM_16:
0462             cfg[0] = 0x023d; cfg[1] = 0x7fdf; cfg[2] = 0x00a4; cfg[3] = 0x7ff0;
0463             break;
0464         case QAM_64:
0465             cfg[0] = 0x0148; cfg[1] = 0x7ff0; cfg[2] = 0x00a4; cfg[3] = 0x7ff8;
0466             break;
0467     }
0468     for (reg = 129; reg < 133; reg++)
0469         dib3000mc_write_word(state, reg, cfg[reg - 129]);
0470 }
0471 
0472 static void dib3000mc_set_channel_cfg(struct dib3000mc_state *state,
0473                       struct dtv_frontend_properties *ch, u16 seq)
0474 {
0475     u16 value;
0476     u32 bw = BANDWIDTH_TO_KHZ(ch->bandwidth_hz);
0477 
0478     dib3000mc_set_bandwidth(state, bw);
0479     dib3000mc_set_timing(state, ch->transmission_mode, bw, 0);
0480 
0481 #if 1
0482     dib3000mc_write_word(state, 100, (16 << 6) + 9);
0483 #else
0484     if (boost)
0485         dib3000mc_write_word(state, 100, (11 << 6) + 6);
0486     else
0487         dib3000mc_write_word(state, 100, (16 << 6) + 9);
0488 #endif
0489 
0490     dib3000mc_write_word(state, 1027, 0x0800);
0491     dib3000mc_write_word(state, 1027, 0x0000);
0492 
0493     //Default cfg isi offset adp
0494     dib3000mc_write_word(state, 26,  0x6680);
0495     dib3000mc_write_word(state, 29,  0x1273);
0496     dib3000mc_write_word(state, 33,       5);
0497     dib3000mc_set_adp_cfg(state, QAM_16);
0498     dib3000mc_write_word(state, 133,  15564);
0499 
0500     dib3000mc_write_word(state, 12 , 0x0);
0501     dib3000mc_write_word(state, 13 , 0x3e8);
0502     dib3000mc_write_word(state, 14 , 0x0);
0503     dib3000mc_write_word(state, 15 , 0x3f2);
0504 
0505     dib3000mc_write_word(state, 93,0);
0506     dib3000mc_write_word(state, 94,0);
0507     dib3000mc_write_word(state, 95,0);
0508     dib3000mc_write_word(state, 96,0);
0509     dib3000mc_write_word(state, 97,0);
0510     dib3000mc_write_word(state, 98,0);
0511 
0512     dib3000mc_set_impulse_noise(state, 0, ch->transmission_mode);
0513 
0514     value = 0;
0515     switch (ch->transmission_mode) {
0516         case TRANSMISSION_MODE_2K: value |= (0 << 7); break;
0517         default:
0518         case TRANSMISSION_MODE_8K: value |= (1 << 7); break;
0519     }
0520     switch (ch->guard_interval) {
0521         case GUARD_INTERVAL_1_32: value |= (0 << 5); break;
0522         case GUARD_INTERVAL_1_16: value |= (1 << 5); break;
0523         case GUARD_INTERVAL_1_4:  value |= (3 << 5); break;
0524         default:
0525         case GUARD_INTERVAL_1_8:  value |= (2 << 5); break;
0526     }
0527     switch (ch->modulation) {
0528         case QPSK:  value |= (0 << 3); break;
0529         case QAM_16: value |= (1 << 3); break;
0530         default:
0531         case QAM_64: value |= (2 << 3); break;
0532     }
0533     switch (HIERARCHY_1) {
0534         case HIERARCHY_2: value |= 2; break;
0535         case HIERARCHY_4: value |= 4; break;
0536         default:
0537         case HIERARCHY_1: value |= 1; break;
0538     }
0539     dib3000mc_write_word(state, 0, value);
0540     dib3000mc_write_word(state, 5, (1 << 8) | ((seq & 0xf) << 4));
0541 
0542     value = 0;
0543     if (ch->hierarchy == 1)
0544         value |= (1 << 4);
0545     if (1 == 1)
0546         value |= 1;
0547     switch ((ch->hierarchy == 0 || 1 == 1) ? ch->code_rate_HP : ch->code_rate_LP) {
0548         case FEC_2_3: value |= (2 << 1); break;
0549         case FEC_3_4: value |= (3 << 1); break;
0550         case FEC_5_6: value |= (5 << 1); break;
0551         case FEC_7_8: value |= (7 << 1); break;
0552         default:
0553         case FEC_1_2: value |= (1 << 1); break;
0554     }
0555     dib3000mc_write_word(state, 181, value);
0556 
0557     // diversity synchro delay add 50% SFN margin
0558     switch (ch->transmission_mode) {
0559         case TRANSMISSION_MODE_8K: value = 256; break;
0560         case TRANSMISSION_MODE_2K:
0561         default: value = 64; break;
0562     }
0563     switch (ch->guard_interval) {
0564         case GUARD_INTERVAL_1_16: value *= 2; break;
0565         case GUARD_INTERVAL_1_8:  value *= 4; break;
0566         case GUARD_INTERVAL_1_4:  value *= 8; break;
0567         default:
0568         case GUARD_INTERVAL_1_32: value *= 1; break;
0569     }
0570     value <<= 4;
0571     value |= dib3000mc_read_word(state, 180) & 0x000f;
0572     dib3000mc_write_word(state, 180, value);
0573 
0574     // restart demod
0575     value = dib3000mc_read_word(state, 0);
0576     dib3000mc_write_word(state, 0, value | (1 << 9));
0577     dib3000mc_write_word(state, 0, value);
0578 
0579     msleep(30);
0580 
0581     dib3000mc_set_impulse_noise(state, state->cfg->impulse_noise_mode, ch->transmission_mode);
0582 }
0583 
0584 static int dib3000mc_autosearch_start(struct dvb_frontend *demod)
0585 {
0586     struct dtv_frontend_properties *chan = &demod->dtv_property_cache;
0587     struct dib3000mc_state *state = demod->demodulator_priv;
0588     u16 reg;
0589 //  u32 val;
0590     struct dtv_frontend_properties schan;
0591 
0592     schan = *chan;
0593 
0594     /* TODO what is that ? */
0595 
0596     /* a channel for autosearch */
0597     schan.transmission_mode = TRANSMISSION_MODE_8K;
0598     schan.guard_interval = GUARD_INTERVAL_1_32;
0599     schan.modulation = QAM_64;
0600     schan.code_rate_HP = FEC_2_3;
0601     schan.code_rate_LP = FEC_2_3;
0602     schan.hierarchy = 0;
0603 
0604     dib3000mc_set_channel_cfg(state, &schan, 11);
0605 
0606     reg = dib3000mc_read_word(state, 0);
0607     dib3000mc_write_word(state, 0, reg | (1 << 8));
0608     dib3000mc_read_word(state, 511);
0609     dib3000mc_write_word(state, 0, reg);
0610 
0611     return 0;
0612 }
0613 
0614 static int dib3000mc_autosearch_is_irq(struct dvb_frontend *demod)
0615 {
0616     struct dib3000mc_state *state = demod->demodulator_priv;
0617     u16 irq_pending = dib3000mc_read_word(state, 511);
0618 
0619     if (irq_pending & 0x1) // failed
0620         return 1;
0621 
0622     if (irq_pending & 0x2) // succeeded
0623         return 2;
0624 
0625     return 0; // still pending
0626 }
0627 
0628 static int dib3000mc_tune(struct dvb_frontend *demod)
0629 {
0630     struct dtv_frontend_properties *ch = &demod->dtv_property_cache;
0631     struct dib3000mc_state *state = demod->demodulator_priv;
0632 
0633     // ** configure demod **
0634     dib3000mc_set_channel_cfg(state, ch, 0);
0635 
0636     // activates isi
0637     if (state->sfn_workaround_active) {
0638         dprintk("SFN workaround is active\n");
0639         dib3000mc_write_word(state, 29, 0x1273);
0640         dib3000mc_write_word(state, 108, 0x4000); // P_pha3_force_pha_shift
0641     } else {
0642         dib3000mc_write_word(state, 29, 0x1073);
0643         dib3000mc_write_word(state, 108, 0x0000); // P_pha3_force_pha_shift
0644     }
0645 
0646     dib3000mc_set_adp_cfg(state, (u8)ch->modulation);
0647     if (ch->transmission_mode == TRANSMISSION_MODE_8K) {
0648         dib3000mc_write_word(state, 26, 38528);
0649         dib3000mc_write_word(state, 33, 8);
0650     } else {
0651         dib3000mc_write_word(state, 26, 30336);
0652         dib3000mc_write_word(state, 33, 6);
0653     }
0654 
0655     if (dib3000mc_read_word(state, 509) & 0x80)
0656         dib3000mc_set_timing(state, ch->transmission_mode,
0657                      BANDWIDTH_TO_KHZ(ch->bandwidth_hz), 1);
0658 
0659     return 0;
0660 }
0661 
0662 struct i2c_adapter * dib3000mc_get_tuner_i2c_master(struct dvb_frontend *demod, int gating)
0663 {
0664     struct dib3000mc_state *st = demod->demodulator_priv;
0665     return dibx000_get_i2c_adapter(&st->i2c_master, DIBX000_I2C_INTERFACE_TUNER, gating);
0666 }
0667 
0668 EXPORT_SYMBOL(dib3000mc_get_tuner_i2c_master);
0669 
0670 static int dib3000mc_get_frontend(struct dvb_frontend* fe,
0671                   struct dtv_frontend_properties *fep)
0672 {
0673     struct dib3000mc_state *state = fe->demodulator_priv;
0674     u16 tps = dib3000mc_read_word(state,458);
0675 
0676     fep->inversion = INVERSION_AUTO;
0677 
0678     fep->bandwidth_hz = state->current_bandwidth;
0679 
0680     switch ((tps >> 8) & 0x1) {
0681         case 0: fep->transmission_mode = TRANSMISSION_MODE_2K; break;
0682         case 1: fep->transmission_mode = TRANSMISSION_MODE_8K; break;
0683     }
0684 
0685     switch (tps & 0x3) {
0686         case 0: fep->guard_interval = GUARD_INTERVAL_1_32; break;
0687         case 1: fep->guard_interval = GUARD_INTERVAL_1_16; break;
0688         case 2: fep->guard_interval = GUARD_INTERVAL_1_8; break;
0689         case 3: fep->guard_interval = GUARD_INTERVAL_1_4; break;
0690     }
0691 
0692     switch ((tps >> 13) & 0x3) {
0693         case 0: fep->modulation = QPSK; break;
0694         case 1: fep->modulation = QAM_16; break;
0695         case 2:
0696         default: fep->modulation = QAM_64; break;
0697     }
0698 
0699     /* as long as the frontend_param structure is fixed for hierarchical transmission I refuse to use it */
0700     /* (tps >> 12) & 0x1 == hrch is used, (tps >> 9) & 0x7 == alpha */
0701 
0702     fep->hierarchy = HIERARCHY_NONE;
0703     switch ((tps >> 5) & 0x7) {
0704         case 1: fep->code_rate_HP = FEC_1_2; break;
0705         case 2: fep->code_rate_HP = FEC_2_3; break;
0706         case 3: fep->code_rate_HP = FEC_3_4; break;
0707         case 5: fep->code_rate_HP = FEC_5_6; break;
0708         case 7:
0709         default: fep->code_rate_HP = FEC_7_8; break;
0710 
0711     }
0712 
0713     switch ((tps >> 2) & 0x7) {
0714         case 1: fep->code_rate_LP = FEC_1_2; break;
0715         case 2: fep->code_rate_LP = FEC_2_3; break;
0716         case 3: fep->code_rate_LP = FEC_3_4; break;
0717         case 5: fep->code_rate_LP = FEC_5_6; break;
0718         case 7:
0719         default: fep->code_rate_LP = FEC_7_8; break;
0720     }
0721 
0722     return 0;
0723 }
0724 
0725 static int dib3000mc_set_frontend(struct dvb_frontend *fe)
0726 {
0727     struct dtv_frontend_properties *fep = &fe->dtv_property_cache;
0728     struct dib3000mc_state *state = fe->demodulator_priv;
0729     int ret;
0730 
0731     dib3000mc_set_output_mode(state, OUTMODE_HIGH_Z);
0732 
0733     state->current_bandwidth = fep->bandwidth_hz;
0734     dib3000mc_set_bandwidth(state, BANDWIDTH_TO_KHZ(fep->bandwidth_hz));
0735 
0736     /* maybe the parameter has been changed */
0737     state->sfn_workaround_active = buggy_sfn_workaround;
0738 
0739     if (fe->ops.tuner_ops.set_params) {
0740         fe->ops.tuner_ops.set_params(fe);
0741         msleep(100);
0742     }
0743 
0744     if (fep->transmission_mode  == TRANSMISSION_MODE_AUTO ||
0745         fep->guard_interval == GUARD_INTERVAL_AUTO ||
0746         fep->modulation     == QAM_AUTO ||
0747         fep->code_rate_HP   == FEC_AUTO) {
0748         int i = 1000, found;
0749 
0750         dib3000mc_autosearch_start(fe);
0751         do {
0752             msleep(1);
0753             found = dib3000mc_autosearch_is_irq(fe);
0754         } while (found == 0 && i--);
0755 
0756         dprintk("autosearch returns: %d\n",found);
0757         if (found == 0 || found == 1)
0758             return 0; // no channel found
0759 
0760         dib3000mc_get_frontend(fe, fep);
0761     }
0762 
0763     ret = dib3000mc_tune(fe);
0764 
0765     /* make this a config parameter */
0766     dib3000mc_set_output_mode(state, OUTMODE_MPEG2_FIFO);
0767     return ret;
0768 }
0769 
0770 static int dib3000mc_read_status(struct dvb_frontend *fe, enum fe_status *stat)
0771 {
0772     struct dib3000mc_state *state = fe->demodulator_priv;
0773     u16 lock = dib3000mc_read_word(state, 509);
0774 
0775     *stat = 0;
0776 
0777     if (lock & 0x8000)
0778         *stat |= FE_HAS_SIGNAL;
0779     if (lock & 0x3000)
0780         *stat |= FE_HAS_CARRIER;
0781     if (lock & 0x0100)
0782         *stat |= FE_HAS_VITERBI;
0783     if (lock & 0x0010)
0784         *stat |= FE_HAS_SYNC;
0785     if (lock & 0x0008)
0786         *stat |= FE_HAS_LOCK;
0787 
0788     return 0;
0789 }
0790 
0791 static int dib3000mc_read_ber(struct dvb_frontend *fe, u32 *ber)
0792 {
0793     struct dib3000mc_state *state = fe->demodulator_priv;
0794     *ber = (dib3000mc_read_word(state, 500) << 16) | dib3000mc_read_word(state, 501);
0795     return 0;
0796 }
0797 
0798 static int dib3000mc_read_unc_blocks(struct dvb_frontend *fe, u32 *unc)
0799 {
0800     struct dib3000mc_state *state = fe->demodulator_priv;
0801     *unc = dib3000mc_read_word(state, 508);
0802     return 0;
0803 }
0804 
0805 static int dib3000mc_read_signal_strength(struct dvb_frontend *fe, u16 *strength)
0806 {
0807     struct dib3000mc_state *state = fe->demodulator_priv;
0808     u16 val = dib3000mc_read_word(state, 392);
0809     *strength = 65535 - val;
0810     return 0;
0811 }
0812 
0813 static int dib3000mc_read_snr(struct dvb_frontend* fe, u16 *snr)
0814 {
0815     *snr = 0x0000;
0816     return 0;
0817 }
0818 
0819 static int dib3000mc_fe_get_tune_settings(struct dvb_frontend* fe, struct dvb_frontend_tune_settings *tune)
0820 {
0821     tune->min_delay_ms = 1000;
0822     return 0;
0823 }
0824 
0825 static void dib3000mc_release(struct dvb_frontend *fe)
0826 {
0827     struct dib3000mc_state *state = fe->demodulator_priv;
0828     dibx000_exit_i2c_master(&state->i2c_master);
0829     kfree(state);
0830 }
0831 
0832 int dib3000mc_pid_control(struct dvb_frontend *fe, int index, int pid,int onoff)
0833 {
0834     struct dib3000mc_state *state = fe->demodulator_priv;
0835     dib3000mc_write_word(state, 212 + index,  onoff ? (1 << 13) | pid : 0);
0836     return 0;
0837 }
0838 EXPORT_SYMBOL(dib3000mc_pid_control);
0839 
0840 int dib3000mc_pid_parse(struct dvb_frontend *fe, int onoff)
0841 {
0842     struct dib3000mc_state *state = fe->demodulator_priv;
0843     u16 tmp = dib3000mc_read_word(state, 206) & ~(1 << 4);
0844     tmp |= (onoff << 4);
0845     return dib3000mc_write_word(state, 206, tmp);
0846 }
0847 EXPORT_SYMBOL(dib3000mc_pid_parse);
0848 
0849 void dib3000mc_set_config(struct dvb_frontend *fe, struct dib3000mc_config *cfg)
0850 {
0851     struct dib3000mc_state *state = fe->demodulator_priv;
0852     state->cfg = cfg;
0853 }
0854 EXPORT_SYMBOL(dib3000mc_set_config);
0855 
0856 int dib3000mc_i2c_enumeration(struct i2c_adapter *i2c, int no_of_demods, u8 default_addr, struct dib3000mc_config cfg[])
0857 {
0858     struct dib3000mc_state *dmcst;
0859     int k;
0860     u8 new_addr;
0861 
0862     static const u8 DIB3000MC_I2C_ADDRESS[] = { 20, 22, 24, 26 };
0863 
0864     dmcst = kzalloc(sizeof(struct dib3000mc_state), GFP_KERNEL);
0865     if (dmcst == NULL)
0866         return -ENOMEM;
0867 
0868     dmcst->i2c_adap = i2c;
0869 
0870     for (k = no_of_demods-1; k >= 0; k--) {
0871         dmcst->cfg = &cfg[k];
0872 
0873         /* designated i2c address */
0874         new_addr          = DIB3000MC_I2C_ADDRESS[k];
0875         dmcst->i2c_addr = new_addr;
0876         if (dib3000mc_identify(dmcst) != 0) {
0877             dmcst->i2c_addr = default_addr;
0878             if (dib3000mc_identify(dmcst) != 0) {
0879                 dprintk("-E-  DiB3000P/MC #%d: not identified\n", k);
0880                 kfree(dmcst);
0881                 return -ENODEV;
0882             }
0883         }
0884 
0885         dib3000mc_set_output_mode(dmcst, OUTMODE_MPEG2_PAR_CONT_CLK);
0886 
0887         // set new i2c address and force divstr (Bit 1) to value 0 (Bit 0)
0888         dib3000mc_write_word(dmcst, 1024, (new_addr << 3) | 0x1);
0889         dmcst->i2c_addr = new_addr;
0890     }
0891 
0892     for (k = 0; k < no_of_demods; k++) {
0893         dmcst->cfg = &cfg[k];
0894         dmcst->i2c_addr = DIB3000MC_I2C_ADDRESS[k];
0895 
0896         dib3000mc_write_word(dmcst, 1024, dmcst->i2c_addr << 3);
0897 
0898         /* turn off data output */
0899         dib3000mc_set_output_mode(dmcst, OUTMODE_HIGH_Z);
0900     }
0901 
0902     kfree(dmcst);
0903     return 0;
0904 }
0905 EXPORT_SYMBOL(dib3000mc_i2c_enumeration);
0906 
0907 static const struct dvb_frontend_ops dib3000mc_ops;
0908 
0909 struct dvb_frontend * dib3000mc_attach(struct i2c_adapter *i2c_adap, u8 i2c_addr, struct dib3000mc_config *cfg)
0910 {
0911     struct dvb_frontend *demod;
0912     struct dib3000mc_state *st;
0913     st = kzalloc(sizeof(struct dib3000mc_state), GFP_KERNEL);
0914     if (st == NULL)
0915         return NULL;
0916 
0917     st->cfg = cfg;
0918     st->i2c_adap = i2c_adap;
0919     st->i2c_addr = i2c_addr;
0920 
0921     demod                   = &st->demod;
0922     demod->demodulator_priv = st;
0923     memcpy(&st->demod.ops, &dib3000mc_ops, sizeof(struct dvb_frontend_ops));
0924 
0925     if (dib3000mc_identify(st) != 0)
0926         goto error;
0927 
0928     dibx000_init_i2c_master(&st->i2c_master, DIB3000MC, st->i2c_adap, st->i2c_addr);
0929 
0930     dib3000mc_write_word(st, 1037, 0x3130);
0931 
0932     return demod;
0933 
0934 error:
0935     kfree(st);
0936     return NULL;
0937 }
0938 EXPORT_SYMBOL(dib3000mc_attach);
0939 
0940 static const struct dvb_frontend_ops dib3000mc_ops = {
0941     .delsys = { SYS_DVBT },
0942     .info = {
0943         .name = "DiBcom 3000MC/P",
0944         .frequency_min_hz      =  44250 * kHz,
0945         .frequency_max_hz      = 867250 * kHz,
0946         .frequency_stepsize_hz = 62500,
0947         .caps = FE_CAN_INVERSION_AUTO |
0948             FE_CAN_FEC_1_2 | FE_CAN_FEC_2_3 | FE_CAN_FEC_3_4 |
0949             FE_CAN_FEC_5_6 | FE_CAN_FEC_7_8 | FE_CAN_FEC_AUTO |
0950             FE_CAN_QPSK | FE_CAN_QAM_16 | FE_CAN_QAM_64 | FE_CAN_QAM_AUTO |
0951             FE_CAN_TRANSMISSION_MODE_AUTO |
0952             FE_CAN_GUARD_INTERVAL_AUTO |
0953             FE_CAN_RECOVER |
0954             FE_CAN_HIERARCHY_AUTO,
0955     },
0956 
0957     .release              = dib3000mc_release,
0958 
0959     .init                 = dib3000mc_init,
0960     .sleep                = dib3000mc_sleep,
0961 
0962     .set_frontend         = dib3000mc_set_frontend,
0963     .get_tune_settings    = dib3000mc_fe_get_tune_settings,
0964     .get_frontend         = dib3000mc_get_frontend,
0965 
0966     .read_status          = dib3000mc_read_status,
0967     .read_ber             = dib3000mc_read_ber,
0968     .read_signal_strength = dib3000mc_read_signal_strength,
0969     .read_snr             = dib3000mc_read_snr,
0970     .read_ucblocks        = dib3000mc_read_unc_blocks,
0971 };
0972 
0973 MODULE_AUTHOR("Patrick Boettcher <patrick.boettcher@posteo.de>");
0974 MODULE_DESCRIPTION("Driver for the DiBcom 3000MC/P COFDM demodulator");
0975 MODULE_LICENSE("GPL");