diff options
Diffstat (limited to 'drivers/media/dvb/frontends/stv0900_sw.c')
-rw-r--r-- | drivers/media/dvb/frontends/stv0900_sw.c | 2032 |
1 files changed, 0 insertions, 2032 deletions
diff --git a/drivers/media/dvb/frontends/stv0900_sw.c b/drivers/media/dvb/frontends/stv0900_sw.c deleted file mode 100644 index 4af20780fb9c..000000000000 --- a/drivers/media/dvb/frontends/stv0900_sw.c +++ /dev/null @@ -1,2032 +0,0 @@ -/* - * stv0900_sw.c - * - * Driver for ST STV0900 satellite demodulator IC. - * - * Copyright (C) ST Microelectronics. - * Copyright (C) 2009 NetUP Inc. - * Copyright (C) 2009 Igor M. Liplianin <liplianin@netup.ru> - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - */ - -#include "stv0900.h" -#include "stv0900_reg.h" -#include "stv0900_priv.h" - -s32 shiftx(s32 x, int demod, s32 shift) -{ - if (demod == 1) - return x - shift; - - return x; -} - -int stv0900_check_signal_presence(struct stv0900_internal *intp, - enum fe_stv0900_demod_num demod) -{ - s32 carr_offset, - agc2_integr, - max_carrier; - - int no_signal = FALSE; - - carr_offset = (stv0900_read_reg(intp, CFR2) << 8) - | stv0900_read_reg(intp, CFR1); - carr_offset = ge2comp(carr_offset, 16); - agc2_integr = (stv0900_read_reg(intp, AGC2I1) << 8) - | stv0900_read_reg(intp, AGC2I0); - max_carrier = intp->srch_range[demod] / 1000; - - max_carrier += (max_carrier / 10); - max_carrier = 65536 * (max_carrier / 2); - max_carrier /= intp->mclk / 1000; - if (max_carrier > 0x4000) - max_carrier = 0x4000; - - if ((agc2_integr > 0x2000) - || (carr_offset > (2 * max_carrier)) - || (carr_offset < (-2 * max_carrier))) - no_signal = TRUE; - - return no_signal; -} - -static void stv0900_get_sw_loop_params(struct stv0900_internal *intp, - s32 *frequency_inc, s32 *sw_timeout, - s32 *steps, - enum fe_stv0900_demod_num demod) -{ - s32 timeout, freq_inc, max_steps, srate, max_carrier; - - enum fe_stv0900_search_standard standard; - - srate = intp->symbol_rate[demod]; - max_carrier = intp->srch_range[demod] / 1000; - max_carrier += max_carrier / 10; - standard = intp->srch_standard[demod]; - - max_carrier = 65536 * (max_carrier / 2); - max_carrier /= intp->mclk / 1000; - - if (max_carrier > 0x4000) - max_carrier = 0x4000; - - freq_inc = srate; - freq_inc /= intp->mclk >> 10; - freq_inc = freq_inc << 6; - - switch (standard) { - case STV0900_SEARCH_DVBS1: - case STV0900_SEARCH_DSS: - freq_inc *= 3; - timeout = 20; - break; - case STV0900_SEARCH_DVBS2: - freq_inc *= 4; - timeout = 25; - break; - case STV0900_AUTO_SEARCH: - default: - freq_inc *= 3; - timeout = 25; - break; - } - - freq_inc /= 100; - - if ((freq_inc > max_carrier) || (freq_inc < 0)) - freq_inc = max_carrier / 2; - - timeout *= 27500; - - if (srate > 0) - timeout /= srate / 1000; - - if ((timeout > 100) || (timeout < 0)) - timeout = 100; - - max_steps = (max_carrier / freq_inc) + 1; - - if ((max_steps > 100) || (max_steps < 0)) { - max_steps = 100; - freq_inc = max_carrier / max_steps; - } - - *frequency_inc = freq_inc; - *sw_timeout = timeout; - *steps = max_steps; - -} - -static int stv0900_search_carr_sw_loop(struct stv0900_internal *intp, - s32 FreqIncr, s32 Timeout, int zigzag, - s32 MaxStep, enum fe_stv0900_demod_num demod) -{ - int no_signal, - lock = FALSE; - s32 stepCpt, - freqOffset, - max_carrier; - - max_carrier = intp->srch_range[demod] / 1000; - max_carrier += (max_carrier / 10); - - max_carrier = 65536 * (max_carrier / 2); - max_carrier /= intp->mclk / 1000; - - if (max_carrier > 0x4000) - max_carrier = 0x4000; - - if (zigzag == TRUE) - freqOffset = 0; - else - freqOffset = -max_carrier + FreqIncr; - - stepCpt = 0; - - do { - stv0900_write_reg(intp, DMDISTATE, 0x1c); - stv0900_write_reg(intp, CFRINIT1, (freqOffset / 256) & 0xff); - stv0900_write_reg(intp, CFRINIT0, freqOffset & 0xff); - stv0900_write_reg(intp, DMDISTATE, 0x18); - stv0900_write_bits(intp, ALGOSWRST, 1); - - if (intp->chip_id == 0x12) { - stv0900_write_bits(intp, RST_HWARE, 1); - stv0900_write_bits(intp, RST_HWARE, 0); - } - - if (zigzag == TRUE) { - if (freqOffset >= 0) - freqOffset = -freqOffset - 2 * FreqIncr; - else - freqOffset = -freqOffset; - } else - freqOffset += + 2 * FreqIncr; - - stepCpt++; - lock = stv0900_get_demod_lock(intp, demod, Timeout); - no_signal = stv0900_check_signal_presence(intp, demod); - - } while ((lock == FALSE) - && (no_signal == FALSE) - && ((freqOffset - FreqIncr) < max_carrier) - && ((freqOffset + FreqIncr) > -max_carrier) - && (stepCpt < MaxStep)); - - stv0900_write_bits(intp, ALGOSWRST, 0); - - return lock; -} - -static int stv0900_sw_algo(struct stv0900_internal *intp, - enum fe_stv0900_demod_num demod) -{ - int lock = FALSE, - no_signal, - zigzag; - s32 s2fw, - fqc_inc, - sft_stp_tout, - trial_cntr, - max_steps; - - stv0900_get_sw_loop_params(intp, &fqc_inc, &sft_stp_tout, - &max_steps, demod); - switch (intp->srch_standard[demod]) { - case STV0900_SEARCH_DVBS1: - case STV0900_SEARCH_DSS: - if (intp->chip_id >= 0x20) - stv0900_write_reg(intp, CARFREQ, 0x3b); - else - stv0900_write_reg(intp, CARFREQ, 0xef); - - stv0900_write_reg(intp, DMDCFGMD, 0x49); - zigzag = FALSE; - break; - case STV0900_SEARCH_DVBS2: - if (intp->chip_id >= 0x20) - stv0900_write_reg(intp, CORRELABS, 0x79); - else - stv0900_write_reg(intp, CORRELABS, 0x68); - - stv0900_write_reg(intp, DMDCFGMD, 0x89); - - zigzag = TRUE; - break; - case STV0900_AUTO_SEARCH: - default: - if (intp->chip_id >= 0x20) { - stv0900_write_reg(intp, CARFREQ, 0x3b); - stv0900_write_reg(intp, CORRELABS, 0x79); - } else { - stv0900_write_reg(intp, CARFREQ, 0xef); - stv0900_write_reg(intp, CORRELABS, 0x68); - } - - stv0900_write_reg(intp, DMDCFGMD, 0xc9); - zigzag = FALSE; - break; - } - - trial_cntr = 0; - do { - lock = stv0900_search_carr_sw_loop(intp, - fqc_inc, - sft_stp_tout, - zigzag, - max_steps, - demod); - no_signal = stv0900_check_signal_presence(intp, demod); - trial_cntr++; - if ((lock == TRUE) - || (no_signal == TRUE) - || (trial_cntr == 2)) { - - if (intp->chip_id >= 0x20) { - stv0900_write_reg(intp, CARFREQ, 0x49); - stv0900_write_reg(intp, CORRELABS, 0x9e); - } else { - stv0900_write_reg(intp, CARFREQ, 0xed); - stv0900_write_reg(intp, CORRELABS, 0x88); - } - - if ((stv0900_get_bits(intp, HEADER_MODE) == - STV0900_DVBS2_FOUND) && - (lock == TRUE)) { - msleep(sft_stp_tout); - s2fw = stv0900_get_bits(intp, FLYWHEEL_CPT); - - if (s2fw < 0xd) { - msleep(sft_stp_tout); - s2fw = stv0900_get_bits(intp, - FLYWHEEL_CPT); - } - - if (s2fw < 0xd) { - lock = FALSE; - - if (trial_cntr < 2) { - if (intp->chip_id >= 0x20) - stv0900_write_reg(intp, - CORRELABS, - 0x79); - else - stv0900_write_reg(intp, - CORRELABS, - 0x68); - - stv0900_write_reg(intp, - DMDCFGMD, - 0x89); - } - } - } - } - - } while ((lock == FALSE) - && (trial_cntr < 2) - && (no_signal == FALSE)); - - return lock; -} - -static u32 stv0900_get_symbol_rate(struct stv0900_internal *intp, - u32 mclk, - enum fe_stv0900_demod_num demod) -{ - s32 rem1, rem2, intval1, intval2, srate; - - srate = (stv0900_get_bits(intp, SYMB_FREQ3) << 24) + - (stv0900_get_bits(intp, SYMB_FREQ2) << 16) + - (stv0900_get_bits(intp, SYMB_FREQ1) << 8) + - (stv0900_get_bits(intp, SYMB_FREQ0)); - dprintk("lock: srate=%d r0=0x%x r1=0x%x r2=0x%x r3=0x%x \n", - srate, stv0900_get_bits(intp, SYMB_FREQ0), - stv0900_get_bits(intp, SYMB_FREQ1), - stv0900_get_bits(intp, SYMB_FREQ2), - stv0900_get_bits(intp, SYMB_FREQ3)); - - intval1 = (mclk) >> 16; - intval2 = (srate) >> 16; - - rem1 = (mclk) % 0x10000; - rem2 = (srate) % 0x10000; - srate = (intval1 * intval2) + - ((intval1 * rem2) >> 16) + - ((intval2 * rem1) >> 16); - - return srate; -} - -static void stv0900_set_symbol_rate(struct stv0900_internal *intp, - u32 mclk, u32 srate, - enum fe_stv0900_demod_num demod) -{ - u32 symb; - - dprintk("%s: Mclk %d, SR %d, Dmd %d\n", __func__, mclk, - srate, demod); - - if (srate > 60000000) { - symb = srate << 4; - symb /= (mclk >> 12); - } else if (srate > 6000000) { - symb = srate << 6; - symb /= (mclk >> 10); - } else { - symb = srate << 9; - symb /= (mclk >> 7); - } - - stv0900_write_reg(intp, SFRINIT1, (symb >> 8) & 0x7f); - stv0900_write_reg(intp, SFRINIT1 + 1, (symb & 0xff)); -} - -static void stv0900_set_max_symbol_rate(struct stv0900_internal *intp, - u32 mclk, u32 srate, - enum fe_stv0900_demod_num demod) -{ - u32 symb; - - srate = 105 * (srate / 100); - - if (srate > 60000000) { - symb = srate << 4; - symb /= (mclk >> 12); - } else if (srate > 6000000) { - symb = srate << 6; - symb /= (mclk >> 10); - } else { - symb = srate << 9; - symb /= (mclk >> 7); - } - - if (symb < 0x7fff) { - stv0900_write_reg(intp, SFRUP1, (symb >> 8) & 0x7f); - stv0900_write_reg(intp, SFRUP1 + 1, (symb & 0xff)); - } else { - stv0900_write_reg(intp, SFRUP1, 0x7f); - stv0900_write_reg(intp, SFRUP1 + 1, 0xff); - } -} - -static void stv0900_set_min_symbol_rate(struct stv0900_internal *intp, - u32 mclk, u32 srate, - enum fe_stv0900_demod_num demod) -{ - u32 symb; - - srate = 95 * (srate / 100); - if (srate > 60000000) { - symb = srate << 4; - symb /= (mclk >> 12); - - } else if (srate > 6000000) { - symb = srate << 6; - symb /= (mclk >> 10); - - } else { - symb = srate << 9; - symb /= (mclk >> 7); - } - - stv0900_write_reg(intp, SFRLOW1, (symb >> 8) & 0xff); - stv0900_write_reg(intp, SFRLOW1 + 1, (symb & 0xff)); -} - -static s32 stv0900_get_timing_offst(struct stv0900_internal *intp, - u32 srate, - enum fe_stv0900_demod_num demod) -{ - s32 timingoffset; - - - timingoffset = (stv0900_read_reg(intp, TMGREG2) << 16) + - (stv0900_read_reg(intp, TMGREG2 + 1) << 8) + - (stv0900_read_reg(intp, TMGREG2 + 2)); - - timingoffset = ge2comp(timingoffset, 24); - - - if (timingoffset == 0) - timingoffset = 1; - - timingoffset = ((s32)srate * 10) / ((s32)0x1000000 / timingoffset); - timingoffset /= 320; - - return timingoffset; -} - -static void stv0900_set_dvbs2_rolloff(struct stv0900_internal *intp, - enum fe_stv0900_demod_num demod) -{ - s32 rolloff; - - if (intp->chip_id == 0x10) { - stv0900_write_bits(intp, MANUALSX_ROLLOFF, 1); - rolloff = stv0900_read_reg(intp, MATSTR1) & 0x03; - stv0900_write_bits(intp, ROLLOFF_CONTROL, rolloff); - } else if (intp->chip_id <= 0x20) - stv0900_write_bits(intp, MANUALSX_ROLLOFF, 0); - else /* cut 3.0 */ - stv0900_write_bits(intp, MANUALS2_ROLLOFF, 0); -} - -static u32 stv0900_carrier_width(u32 srate, enum fe_stv0900_rolloff ro) -{ - u32 rolloff; - - switch (ro) { - case STV0900_20: - rolloff = 20; - break; - case STV0900_25: - rolloff = 25; - break; - case STV0900_35: - default: - rolloff = 35; - break; - } - - return srate + (srate * rolloff) / 100; -} - -static int stv0900_check_timing_lock(struct stv0900_internal *intp, - enum fe_stv0900_demod_num demod) -{ - int timingLock = FALSE; - s32 i, - timingcpt = 0; - u8 car_freq, - tmg_th_high, - tmg_th_low; - - car_freq = stv0900_read_reg(intp, CARFREQ); - tmg_th_high = stv0900_read_reg(intp, TMGTHRISE); - tmg_th_low = stv0900_read_reg(intp, TMGTHFALL); - stv0900_write_reg(intp, TMGTHRISE, 0x20); - stv0900_write_reg(intp, TMGTHFALL, 0x0); - stv0900_write_bits(intp, CFR_AUTOSCAN, 0); - stv0900_write_reg(intp, RTC, 0x80); - stv0900_write_reg(intp, RTCS2, 0x40); - stv0900_write_reg(intp, CARFREQ, 0x0); - stv0900_write_reg(intp, CFRINIT1, 0x0); - stv0900_write_reg(intp, CFRINIT0, 0x0); - stv0900_write_reg(intp, AGC2REF, 0x65); - stv0900_write_reg(intp, DMDISTATE, 0x18); - msleep(7); - - for (i = 0; i < 10; i++) { - if (stv0900_get_bits(intp, TMGLOCK_QUALITY) >= 2) - timingcpt++; - - msleep(1); - } - - if (timingcpt >= 3) - timingLock = TRUE; - - stv0900_write_reg(intp, AGC2REF, 0x38); - stv0900_write_reg(intp, RTC, 0x88); - stv0900_write_reg(intp, RTCS2, 0x68); - stv0900_write_reg(intp, CARFREQ, car_freq); - stv0900_write_reg(intp, TMGTHRISE, tmg_th_high); - stv0900_write_reg(intp, TMGTHFALL, tmg_th_low); - - return timingLock; -} - -static int stv0900_get_demod_cold_lock(struct dvb_frontend *fe, - s32 demod_timeout) -{ - struct stv0900_state *state = fe->demodulator_priv; - struct stv0900_internal *intp = state->internal; - enum fe_stv0900_demod_num demod = state->demod; - int lock = FALSE, - d = demod; - s32 srate, - search_range, - locktimeout, - currier_step, - nb_steps, - current_step, - direction, - tuner_freq, - timeout, - freq; - - srate = intp->symbol_rate[d]; - search_range = intp->srch_range[d]; - - if (srate >= 10000000) - locktimeout = demod_timeout / 3; - else - locktimeout = demod_timeout / 2; - - lock = stv0900_get_demod_lock(intp, d, locktimeout); - - if (lock != FALSE) - return lock; - - if (srate >= 10000000) { - if (stv0900_check_timing_lock(intp, d) == TRUE) { - stv0900_write_reg(intp, DMDISTATE, 0x1f); - stv0900_write_reg(intp, DMDISTATE, 0x15); - lock = stv0900_get_demod_lock(intp, d, demod_timeout); - } else - lock = FALSE; - - return lock; - } - - if (intp->chip_id <= 0x20) { - if (srate <= 1000000) - currier_step = 500; - else if (srate <= 4000000) - currier_step = 1000; - else if (srate <= 7000000) - currier_step = 2000; - else if (srate <= 10000000) - currier_step = 3000; - else - currier_step = 5000; - - if (srate >= 2000000) { - timeout = (demod_timeout / 3); - if (timeout > 1000) - timeout = 1000; - } else - timeout = (demod_timeout / 2); - } else { - /*cut 3.0 */ - currier_step = srate / 4000; - timeout = (demod_timeout * 3) / 4; - } - - nb_steps = ((search_range / 1000) / currier_step); - - if ((nb_steps % 2) != 0) - nb_steps += 1; - - if (nb_steps <= 0) - nb_steps = 2; - else if (nb_steps > 12) - nb_steps = 12; - - current_step = 1; - direction = 1; - - if (intp->chip_id <= 0x20) { - tuner_freq = intp->freq[d]; - intp->bw[d] = stv0900_carrier_width(intp->symbol_rate[d], - intp->rolloff) + intp->symbol_rate[d]; - } else - tuner_freq = 0; - - while ((current_step <= nb_steps) && (lock == FALSE)) { - if (direction > 0) - tuner_freq += (current_step * currier_step); - else - tuner_freq -= (current_step * currier_step); - - if (intp->chip_id <= 0x20) { - if (intp->tuner_type[d] == 3) - stv0900_set_tuner_auto(intp, tuner_freq, - intp->bw[d], demod); - else - stv0900_set_tuner(fe, tuner_freq, intp->bw[d]); - - stv0900_write_reg(intp, DMDISTATE, 0x1c); - stv0900_write_reg(intp, CFRINIT1, 0); - stv0900_write_reg(intp, CFRINIT0, 0); - stv0900_write_reg(intp, DMDISTATE, 0x1f); - stv0900_write_reg(intp, DMDISTATE, 0x15); - } else { - stv0900_write_reg(intp, DMDISTATE, 0x1c); - freq = (tuner_freq * 65536) / (intp->mclk / 1000); - stv0900_write_bits(intp, CFR_INIT1, MSB(freq)); - stv0900_write_bits(intp, CFR_INIT0, LSB(freq)); - stv0900_write_reg(intp, DMDISTATE, 0x1f); - stv0900_write_reg(intp, DMDISTATE, 0x05); - } - - lock = stv0900_get_demod_lock(intp, d, timeout); - direction *= -1; - current_step++; - } - - return lock; -} - -static void stv0900_get_lock_timeout(s32 *demod_timeout, s32 *fec_timeout, - s32 srate, - enum fe_stv0900_search_algo algo) -{ - switch (algo) { - case STV0900_BLIND_SEARCH: - if (srate <= 1500000) { - (*demod_timeout) = 1500; - (*fec_timeout) = 400; - } else if (srate <= 5000000) { - (*demod_timeout) = 1000; - (*fec_timeout) = 300; - } else { - (*demod_timeout) = 700; - (*fec_timeout) = 100; - } - - break; - case STV0900_COLD_START: - case STV0900_WARM_START: - default: - if (srate <= 1000000) { - (*demod_timeout) = 3000; - (*fec_timeout) = 1700; - } else if (srate <= 2000000) { - (*demod_timeout) = 2500; - (*fec_timeout) = 1100; - } else if (srate <= 5000000) { - (*demod_timeout) = 1000; - (*fec_timeout) = 550; - } else if (srate <= 10000000) { - (*demod_timeout) = 700; - (*fec_timeout) = 250; - } else if (srate <= 20000000) { - (*demod_timeout) = 400; - (*fec_timeout) = 130; - } else { - (*demod_timeout) = 300; - (*fec_timeout) = 100; - } - - break; - - } - - if (algo == STV0900_WARM_START) - (*demod_timeout) /= 2; -} - -static void stv0900_set_viterbi_tracq(struct stv0900_internal *intp, - enum fe_stv0900_demod_num demod) -{ - - s32 vth_reg = VTH12; - - dprintk("%s\n", __func__); - - stv0900_write_reg(intp, vth_reg++, 0xd0); - stv0900_write_reg(intp, vth_reg++, 0x7d); - stv0900_write_reg(intp, vth_reg++, 0x53); - stv0900_write_reg(intp, vth_reg++, 0x2f); - stv0900_write_reg(intp, vth_reg++, 0x24); - stv0900_write_reg(intp, vth_reg++, 0x1f); -} - -static void stv0900_set_viterbi_standard(struct stv0900_internal *intp, - enum fe_stv0900_search_standard standard, - enum fe_stv0900_fec fec, - enum fe_stv0900_demod_num demod) -{ - dprintk("%s: ViterbiStandard = ", __func__); - - switch (standard) { - case STV0900_AUTO_SEARCH: - dprintk("Auto\n"); - stv0900_write_reg(intp, FECM, 0x10); - stv0900_write_reg(intp, PRVIT, 0x3f); - break; - case STV0900_SEARCH_DVBS1: - dprintk("DVBS1\n"); - stv0900_write_reg(intp, FECM, 0x00); - switch (fec) { - case STV0900_FEC_UNKNOWN: - default: - stv0900_write_reg(intp, PRVIT, 0x2f); - break; - case STV0900_FEC_1_2: - stv0900_write_reg(intp, PRVIT, 0x01); - break; - case STV0900_FEC_2_3: - stv0900_write_reg(intp, PRVIT, 0x02); - break; - case STV0900_FEC_3_4: - stv0900_write_reg(intp, PRVIT, 0x04); - break; - case STV0900_FEC_5_6: - stv0900_write_reg(intp, PRVIT, 0x08); - break; - case STV0900_FEC_7_8: - stv0900_write_reg(intp, PRVIT, 0x20); - break; - } - - break; - case STV0900_SEARCH_DSS: - dprintk("DSS\n"); - stv0900_write_reg(intp, FECM, 0x80); - switch (fec) { - case STV0900_FEC_UNKNOWN: - default: - stv0900_write_reg(intp, PRVIT, 0x13); - break; - case STV0900_FEC_1_2: - stv0900_write_reg(intp, PRVIT, 0x01); - break; - case STV0900_FEC_2_3: - stv0900_write_reg(intp, PRVIT, 0x02); - break; - case STV0900_FEC_6_7: - stv0900_write_reg(intp, PRVIT, 0x10); - break; - } - break; - default: - break; - } -} - -static enum fe_stv0900_fec stv0900_get_vit_fec(struct stv0900_internal *intp, - enum fe_stv0900_demod_num demod) -{ - enum fe_stv0900_fec prate; - s32 rate_fld = stv0900_get_bits(intp, VIT_CURPUN); - - switch (rate_fld) { - case 13: - prate = STV0900_FEC_1_2; - break; - case 18: - prate = STV0900_FEC_2_3; - break; - case 21: - prate = STV0900_FEC_3_4; - break; - case 24: - prate = STV0900_FEC_5_6; - break; - case 25: - prate = STV0900_FEC_6_7; - break; - case 26: - prate = STV0900_FEC_7_8; - break; - default: - prate = STV0900_FEC_UNKNOWN; - break; - } - - return prate; -} - -static void stv0900_set_dvbs1_track_car_loop(struct stv0900_internal *intp, - enum fe_stv0900_demod_num demod, - u32 srate) -{ - if (intp->chip_id >= 0x30) { - if (srate >= 15000000) { - stv0900_write_reg(intp, ACLC, 0x2b); - stv0900_write_reg(intp, BCLC, 0x1a); - } else if ((srate >= 7000000) && (15000000 > srate)) { - stv0900_write_reg(intp, ACLC, 0x0c); - stv0900_write_reg(intp, BCLC, 0x1b); - } else if (srate < 7000000) { - stv0900_write_reg(intp, ACLC, 0x2c); - stv0900_write_reg(intp, BCLC, 0x1c); - } - - } else { /*cut 2.0 and 1.x*/ - stv0900_write_reg(intp, ACLC, 0x1a); - stv0900_write_reg(intp, BCLC, 0x09); - } - -} - -static void stv0900_track_optimization(struct dvb_frontend *fe) -{ - struct stv0900_state *state = fe->demodulator_priv; - struct stv0900_internal *intp = state->internal; - enum fe_stv0900_demod_num demod = state->demod; - - s32 srate, - pilots, - aclc, - freq1, - freq0, - i = 0, - timed, - timef, - blind_tun_sw = 0, - modulation; - - enum fe_stv0900_modcode foundModcod; - - dprintk("%s\n", __func__); - - srate = stv0900_get_symbol_rate(intp, intp->mclk, demod); - srate += stv0900_get_timing_offst(intp, srate, demod); - - switch (intp->result[demod].standard) { - case STV0900_DVBS1_STANDARD: - case STV0900_DSS_STANDARD: - dprintk("%s: found DVB-S or DSS\n", __func__); - if (intp->srch_standard[demod] == STV0900_AUTO_SEARCH) { - stv0900_write_bits(intp, DVBS1_ENABLE, 1); - stv0900_write_bits(intp, DVBS2_ENABLE, 0); - } - - stv0900_write_bits(intp, ROLLOFF_CONTROL, intp->rolloff); - stv0900_write_bits(intp, MANUALSX_ROLLOFF, 1); - - if (intp->chip_id < 0x30) { - stv0900_write_reg(intp, ERRCTRL1, 0x75); - break; - } - - if (stv0900_get_vit_fec(intp, demod) == STV0900_FEC_1_2) { - stv0900_write_reg(intp, GAUSSR0, 0x98); - stv0900_write_reg(intp, CCIR0, 0x18); - } else { - stv0900_write_reg(intp, GAUSSR0, 0x18); - stv0900_write_reg(intp, CCIR0, 0x18); - } - - stv0900_write_reg(intp, ERRCTRL1, 0x75); - break; - case STV0900_DVBS2_STANDARD: - dprintk("%s: found DVB-S2\n", __func__); - stv0900_write_bits(intp, DVBS1_ENABLE, 0); - stv0900_write_bits(intp, DVBS2_ENABLE, 1); - stv0900_write_reg(intp, ACLC, 0); - stv0900_write_reg(intp, BCLC, 0); - if (intp->result[demod].frame_len == STV0900_LONG_FRAME) { - foundModcod = stv0900_get_bits(intp, DEMOD_MODCOD); - pilots = stv0900_get_bits(intp, DEMOD_TYPE) & 0x01; - aclc = stv0900_get_optim_carr_loop(srate, - foundModcod, - pilots, - intp->chip_id); - if (foundModcod <= STV0900_QPSK_910) - stv0900_write_reg(intp, ACLC2S2Q, aclc); - else if (foundModcod <= STV0900_8PSK_910) { - stv0900_write_reg(intp, ACLC2S2Q, 0x2a); - stv0900_write_reg(intp, ACLC2S28, aclc); - } - - if ((intp->demod_mode == STV0900_SINGLE) && - (foundModcod > STV0900_8PSK_910)) { - if (foundModcod <= STV0900_16APSK_910) { - stv0900_write_reg(intp, ACLC2S2Q, 0x2a); - stv0900_write_reg(intp, ACLC2S216A, - aclc); - } else if (foundModcod <= STV0900_32APSK_910) { - stv0900_write_reg(intp, ACLC2S2Q, 0x2a); - stv0900_write_reg(intp, ACLC2S232A, - aclc); - } - } - - } else { - modulation = intp->result[demod].modulation; - aclc = stv0900_get_optim_short_carr_loop(srate, - modulation, intp->chip_id); - if (modulation == STV0900_QPSK) - stv0900_write_reg(intp, ACLC2S2Q, aclc); - else if (modulation == STV0900_8PSK) { - stv0900_write_reg(intp, ACLC2S2Q, 0x2a); - stv0900_write_reg(intp, ACLC2S28, aclc); - } else if (modulation == STV0900_16APSK) { - stv0900_write_reg(intp, ACLC2S2Q, 0x2a); - stv0900_write_reg(intp, ACLC2S216A, aclc); - } else if (modulation == STV0900_32APSK) { - stv0900_write_reg(intp, ACLC2S2Q, 0x2a); - stv0900_write_reg(intp, ACLC2S232A, aclc); - } - - } - - if (intp->chip_id <= 0x11) { - if (intp->demod_mode != STV0900_SINGLE) - stv0900_activate_s2_modcod(intp, demod); - - } - - stv0900_write_reg(intp, ERRCTRL1, 0x67); - break; - case STV0900_UNKNOWN_STANDARD: - default: - dprintk("%s: found unknown standard\n", __func__); - stv0900_write_bits(intp, DVBS1_ENABLE, 1); - stv0900_write_bits(intp, DVBS2_ENABLE, 1); - break; - } - - freq1 = stv0900_read_reg(intp, CFR2); - freq0 = stv0900_read_reg(intp, CFR1); - if (intp->srch_algo[demod] == STV0900_BLIND_SEARCH) { - stv0900_write_reg(intp, SFRSTEP, 0x00); - stv0900_write_bits(intp, SCAN_ENABLE, 0); - stv0900_write_bits(intp, CFR_AUTOSCAN, 0); - stv0900_write_reg(intp, TMGCFG2, 0xc1); - stv0900_set_symbol_rate(intp, intp->mclk, srate, demod); - blind_tun_sw = 1; - if (intp->result[demod].standard != STV0900_DVBS2_STANDARD) - stv0900_set_dvbs1_track_car_loop(intp, demod, srate); - - } - - if (intp->chip_id >= 0x20) { - if ((intp->srch_standard[demod] == STV0900_SEARCH_DVBS1) || - (intp->srch_standard[demod] == - STV0900_SEARCH_DSS) || - (intp->srch_standard[demod] == - STV0900_AUTO_SEARCH)) { - stv0900_write_reg(intp, VAVSRVIT, 0x0a); - stv0900_write_reg(intp, VITSCALE, 0x0); - } - } - - if (intp->chip_id < 0x20) - stv0900_write_reg(intp, CARHDR, 0x08); - - if (intp->chip_id == 0x10) - stv0900_write_reg(intp, CORRELEXP, 0x0a); - - stv0900_write_reg(intp, AGC2REF, 0x38); - - if ((intp->chip_id >= 0x20) || - (blind_tun_sw == 1) || - (intp->symbol_rate[demod] < 10000000)) { - stv0900_write_reg(intp, CFRINIT1, freq1); - stv0900_write_reg(intp, CFRINIT0, freq0); - intp->bw[demod] = stv0900_carrier_width(srate, - intp->rolloff) + 10000000; - - if ((intp->chip_id >= 0x20) || (blind_tun_sw == 1)) { - if (intp->srch_algo[demod] != STV0900_WARM_START) { - if (intp->tuner_type[demod] == 3) - stv0900_set_tuner_auto(intp, - intp->freq[demod], - intp->bw[demod], - demod); - else - stv0900_set_bandwidth(fe, - intp->bw[demod]); - } - } - - if ((intp->srch_algo[demod] == STV0900_BLIND_SEARCH) || - (intp->symbol_rate[demod] < 10000000)) - msleep(50); - else - msleep(5); - - stv0900_get_lock_timeout(&timed, &timef, srate, - STV0900_WARM_START); - - if (stv0900_get_demod_lock(intp, demod, timed / 2) == FALSE) { - stv0900_write_reg(intp, DMDISTATE, 0x1f); - stv0900_write_reg(intp, CFRINIT1, freq1); - stv0900_write_reg(intp, CFRINIT0, freq0); - stv0900_write_reg(intp, DMDISTATE, 0x18); - i = 0; - while ((stv0900_get_demod_lock(intp, - demod, - timed / 2) == FALSE) && - (i <= 2)) { - stv0900_write_reg(intp, DMDISTATE, 0x1f); - stv0900_write_reg(intp, CFRINIT1, freq1); - stv0900_write_reg(intp, CFRINIT0, freq0); - stv0900_write_reg(intp, DMDISTATE, 0x18); - i++; - } - } - - } - - if (intp->chip_id >= 0x20) - stv0900_write_reg(intp, CARFREQ, 0x49); - - if ((intp->result[demod].standard == STV0900_DVBS1_STANDARD) || - (intp->result[demod].standard == STV0900_DSS_STANDARD)) - stv0900_set_viterbi_tracq(intp, demod); - -} - -static int stv0900_get_fec_lock(struct stv0900_internal *intp, - enum fe_stv0900_demod_num demod, s32 time_out) -{ - s32 timer = 0, lock = 0; - - enum fe_stv0900_search_state dmd_state; - - dprintk("%s\n", __func__); - - dmd_state = stv0900_get_bits(intp, HEADER_MODE); - - while ((timer < time_out) && (lock == 0)) { - switch (dmd_state) { - case STV0900_SEARCH: - case STV0900_PLH_DETECTED: - default: - lock = 0; - break; - case STV0900_DVBS2_FOUND: - lock = stv0900_get_bits(intp, PKTDELIN_LOCK); - break; - case STV0900_DVBS_FOUND: - lock = stv0900_get_bits(intp, LOCKEDVIT); - break; - } - - if (lock == 0) { - msleep(10); - timer += 10; - } - } - - if (lock) - dprintk("%s: DEMOD FEC LOCK OK\n", __func__); - else - dprintk("%s: DEMOD FEC LOCK FAIL\n", __func__); - - return lock; -} - -static int stv0900_wait_for_lock(struct stv0900_internal *intp, - enum fe_stv0900_demod_num demod, - s32 dmd_timeout, s32 fec_timeout) -{ - - s32 timer = 0, lock = 0; - - dprintk("%s\n", __func__); - - lock = stv0900_get_demod_lock(intp, demod, dmd_timeout); - - if (lock) - lock = lock && stv0900_get_fec_lock(intp, demod, fec_timeout); - - if (lock) { - lock = 0; - - dprintk("%s: Timer = %d, time_out = %d\n", - __func__, timer, fec_timeout); - - while ((timer < fec_timeout) && (lock == 0)) { - lock = stv0900_get_bits(intp, TSFIFO_LINEOK); - msleep(1); - timer++; - } - } - - if (lock) - dprintk("%s: DEMOD LOCK OK\n", __func__); - else - dprintk("%s: DEMOD LOCK FAIL\n", __func__); - - if (lock) - return TRUE; - else - return FALSE; -} - -enum fe_stv0900_tracking_standard stv0900_get_standard(struct dvb_frontend *fe, - enum fe_stv0900_demod_num demod) -{ - struct stv0900_state *state = fe->demodulator_priv; - struct stv0900_internal *intp = state->internal; - enum fe_stv0900_tracking_standard fnd_standard; - - int hdr_mode = stv0900_get_bits(intp, HEADER_MODE); - - switch (hdr_mode) { - case 2: - fnd_standard = STV0900_DVBS2_STANDARD; - break; - case 3: - if (stv0900_get_bits(intp, DSS_DVB) == 1) - fnd_standard = STV0900_DSS_STANDARD; - else - fnd_standard = STV0900_DVBS1_STANDARD; - - break; - default: - fnd_standard = STV0900_UNKNOWN_STANDARD; - } - - dprintk("%s: standard %d\n", __func__, fnd_standard); - - return fnd_standard; -} - -static s32 stv0900_get_carr_freq(struct stv0900_internal *intp, u32 mclk, - enum fe_stv0900_demod_num demod) -{ - s32 derot, - rem1, - rem2, - intval1, - intval2; - - derot = (stv0900_get_bits(intp, CAR_FREQ2) << 16) + - (stv0900_get_bits(intp, CAR_FREQ1) << 8) + - (stv0900_get_bits(intp, CAR_FREQ0)); - - derot = ge2comp(derot, 24); - intval1 = mclk >> 12; - intval2 = derot >> 12; - rem1 = mclk % 0x1000; - rem2 = derot % 0x1000; - derot = (intval1 * intval2) + - ((intval1 * rem2) >> 12) + - ((intval2 * rem1) >> 12); - - return derot; -} - -static u32 stv0900_get_tuner_freq(struct dvb_frontend *fe) -{ - struct dvb_frontend_ops *frontend_ops = NULL; - struct dvb_tuner_ops *tuner_ops = NULL; - u32 freq = 0; - - if (&fe->ops) - frontend_ops = &fe->ops; - - if (&frontend_ops->tuner_ops) - tuner_ops = &frontend_ops->tuner_ops; - - if (tuner_ops->get_frequency) { - if ((tuner_ops->get_frequency(fe, &freq)) < 0) - dprintk("%s: Invalid parameter\n", __func__); - else - dprintk("%s: Frequency=%d\n", __func__, freq); - - } - - return freq; -} - -static enum -fe_stv0900_signal_type stv0900_get_signal_params(struct dvb_frontend *fe) -{ - struct stv0900_state *state = fe->demodulator_priv; - struct stv0900_internal *intp = state->internal; - enum fe_stv0900_demod_num demod = state->demod; - enum fe_stv0900_signal_type range = STV0900_OUTOFRANGE; - struct stv0900_signal_info *result = &intp->result[demod]; - s32 offsetFreq, - srate_offset; - int i = 0, - d = demod; - - u8 timing; - - msleep(5); - if (intp->srch_algo[d] == STV0900_BLIND_SEARCH) { - timing = stv0900_read_reg(intp, TMGREG2); - i = 0; - stv0900_write_reg(intp, SFRSTEP, 0x5c); - - while ((i <= 50) && (timing != 0) && (timing != 0xff)) { - timing = stv0900_read_reg(intp, TMGREG2); - msleep(5); - i += 5; - } - } - - result->standard = stv0900_get_standard(fe, d); - if (intp->tuner_type[demod] == 3) - result->frequency = stv0900_get_freq_auto(intp, d); - else - result->frequency = stv0900_get_tuner_freq(fe); - - offsetFreq = stv0900_get_carr_freq(intp, intp->mclk, d) / 1000; - result->frequency += offsetFreq; - result->symbol_rate = stv0900_get_symbol_rate(intp, intp->mclk, d); - srate_offset = stv0900_get_timing_offst(intp, result->symbol_rate, d); - result->symbol_rate += srate_offset; - result->fec = stv0900_get_vit_fec(intp, d); - result->modcode = stv0900_get_bits(intp, DEMOD_MODCOD); - result->pilot = stv0900_get_bits(intp, DEMOD_TYPE) & 0x01; - result->frame_len = ((u32)stv0900_get_bits(intp, DEMOD_TYPE)) >> 1; - result->rolloff = stv0900_get_bits(intp, ROLLOFF_STATUS); - - dprintk("%s: modcode=0x%x \n", __func__, result->modcode); - - switch (result->standard) { - case STV0900_DVBS2_STANDARD: - result->spectrum = stv0900_get_bits(intp, SPECINV_DEMOD); - if (result->modcode <= STV0900_QPSK_910) - result->modulation = STV0900_QPSK; - else if (result->modcode <= STV0900_8PSK_910) - result->modulation = STV0900_8PSK; - else if (result->modcode <= STV0900_16APSK_910) - result->modulation = STV0900_16APSK; - else if (result->modcode <= STV0900_32APSK_910) - result->modulation = STV0900_32APSK; - else - result->modulation = STV0900_UNKNOWN; - break; - case STV0900_DVBS1_STANDARD: - case STV0900_DSS_STANDARD: - result->spectrum = stv0900_get_bits(intp, IQINV); - result->modulation = STV0900_QPSK; - break; - default: - break; - } - - if ((intp->srch_algo[d] == STV0900_BLIND_SEARCH) || - (intp->symbol_rate[d] < 10000000)) { - offsetFreq = result->frequency - intp->freq[d]; - if (intp->tuner_type[demod] == 3) - intp->freq[d] = stv0900_get_freq_auto(intp, d); - else - intp->freq[d] = stv0900_get_tuner_freq(fe); - - if (ABS(offsetFreq) <= ((intp->srch_range[d] / 2000) + 500)) - range = STV0900_RANGEOK; - else if (ABS(offsetFreq) <= - (stv0900_carrier_width(result->symbol_rate, - result->rolloff) / 2000)) - range = STV0900_RANGEOK; - - } else if (ABS(offsetFreq) <= ((intp->srch_range[d] / 2000) + 500)) - range = STV0900_RANGEOK; - - dprintk("%s: range %d\n", __func__, range); - - return range; -} - -static enum -fe_stv0900_signal_type stv0900_dvbs1_acq_workaround(struct dvb_frontend *fe) -{ - struct stv0900_state *state = fe->demodulator_priv; - struct stv0900_internal *intp = state->internal; - enum fe_stv0900_demod_num demod = state->demod; - enum fe_stv0900_signal_type signal_type = STV0900_NODATA; - - s32 srate, - demod_timeout, - fec_timeout, - freq1, - freq0; - - intp->result[demod].locked = FALSE; - - if (stv0900_get_bits(intp, HEADER_MODE) == STV0900_DVBS_FOUND) { - srate = stv0900_get_symbol_rate(intp, intp->mclk, demod); - srate += stv0900_get_timing_offst(intp, srate, demod); - if (intp->srch_algo[demod] == STV0900_BLIND_SEARCH) - stv0900_set_symbol_rate(intp, intp->mclk, srate, demod); - - stv0900_get_lock_timeout(&demod_timeout, &fec_timeout, - srate, STV0900_WARM_START); - freq1 = stv0900_read_reg(intp, CFR2); - freq0 = stv0900_read_reg(intp, CFR1); - stv0900_write_bits(intp, CFR_AUTOSCAN, 0); - stv0900_write_bits(intp, SPECINV_CONTROL, - STV0900_IQ_FORCE_SWAPPED); - stv0900_write_reg(intp, DMDISTATE, 0x1c); - stv0900_write_reg(intp, CFRINIT1, freq1); - stv0900_write_reg(intp, CFRINIT0, freq0); - stv0900_write_reg(intp, DMDISTATE, 0x18); - if (stv0900_wait_for_lock(intp, demod, - demod_timeout, fec_timeout) == TRUE) { - intp->result[demod].locked = TRUE; - signal_type = stv0900_get_signal_params(fe); - stv0900_track_optimization(fe); - } else { - stv0900_write_bits(intp, SPECINV_CONTROL, - STV0900_IQ_FORCE_NORMAL); - stv0900_write_reg(intp, DMDISTATE, 0x1c); - stv0900_write_reg(intp, CFRINIT1, freq1); - stv0900_write_reg(intp, CFRINIT0, freq0); - stv0900_write_reg(intp, DMDISTATE, 0x18); - if (stv0900_wait_for_lock(intp, demod, - demod_timeout, fec_timeout) == TRUE) { - intp->result[demod].locked = TRUE; - signal_type = stv0900_get_signal_params(fe); - stv0900_track_optimization(fe); - } - - } - - } else - intp->result[demod].locked = FALSE; - - return signal_type; -} - -static u16 stv0900_blind_check_agc2_min_level(struct stv0900_internal *intp, - enum fe_stv0900_demod_num demod) -{ - u32 minagc2level = 0xffff, - agc2level, - init_freq, freq_step; - - s32 i, j, nb_steps, direction; - - dprintk("%s\n", __func__); - - stv0900_write_reg(intp, AGC2REF, 0x38); - stv0900_write_bits(intp, SCAN_ENABLE, 0); - stv0900_write_bits(intp, CFR_AUTOSCAN, 0); - - stv0900_write_bits(intp, AUTO_GUP, 1); - stv0900_write_bits(intp, AUTO_GLOW, 1); - - stv0900_write_reg(intp, DMDT0M, 0x0); - - stv0900_set_symbol_rate(intp, intp->mclk, 1000000, demod); - nb_steps = -1 + (intp->srch_range[demod] / 1000000); - nb_steps /= 2; - nb_steps = (2 * nb_steps) + 1; - - if (nb_steps < 0) - nb_steps = 1; - - direction = 1; - - freq_step = (1000000 << 8) / (intp->mclk >> 8); - - init_freq = 0; - - for (i = 0; i < nb_steps; i++) { - if (direction > 0) - init_freq = init_freq + (freq_step * i); - else - init_freq = init_freq - (freq_step * i); - - direction *= -1; - stv0900_write_reg(intp, DMDISTATE, 0x5C); - stv0900_write_reg(intp, CFRINIT1, (init_freq >> 8) & 0xff); - stv0900_write_reg(intp, CFRINIT0, init_freq & 0xff); - stv0900_write_reg(intp, DMDISTATE, 0x58); - msleep(10); - agc2level = 0; - - for (j = 0; j < 10; j++) - agc2level += (stv0900_read_reg(intp, AGC2I1) << 8) - | stv0900_read_reg(intp, AGC2I0); - - agc2level /= 10; - - if (agc2level < minagc2level) - minagc2level = agc2level; - - } - - return (u16)minagc2level; -} - -static u32 stv0900_search_srate_coarse(struct dvb_frontend *fe) -{ - struct stv0900_state *state = fe->demodulator_priv; - struct stv0900_internal *intp = state->internal; - enum fe_stv0900_demod_num demod = state->demod; - int timing_lck = FALSE; - s32 i, timingcpt = 0, - direction = 1, - nb_steps, - current_step = 0, - tuner_freq; - u32 agc2_th, - coarse_srate = 0, - agc2_integr = 0, - currier_step = 1200; - - if (intp->chip_id >= 0x30) - agc2_th = 0x2e00; - else - agc2_th = 0x1f00; - - stv0900_write_bits(intp, DEMOD_MODE, 0x1f); - stv0900_write_reg(intp, TMGCFG, 0x12); - stv0900_write_reg(intp, TMGTHRISE, 0xf0); - stv0900_write_reg(intp, TMGTHFALL, 0xe0); - stv0900_write_bits(intp, SCAN_ENABLE, 1); - stv0900_write_bits(intp, CFR_AUTOSCAN, 1); - stv0900_write_reg(intp, SFRUP1, 0x83); - stv0900_write_reg(intp, SFRUP0, 0xc0); - stv0900_write_reg(intp, SFRLOW1, 0x82); - stv0900_write_reg(intp, SFRLOW0, 0xa0); - stv0900_write_reg(intp, DMDT0M, 0x0); - stv0900_write_reg(intp, AGC2REF, 0x50); - - if (intp->chip_id >= 0x30) { - stv0900_write_reg(intp, CARFREQ, 0x99); - stv0900_write_reg(intp, SFRSTEP, 0x98); - } else if (intp->chip_id >= 0x20) { - stv0900_write_reg(intp, CARFREQ, 0x6a); - stv0900_write_reg(intp, SFRSTEP, 0x95); - } else { - stv0900_write_reg(intp, CARFREQ, 0xed); - stv0900_write_reg(intp, SFRSTEP, 0x73); - } - - if (intp->symbol_rate[demod] <= 2000000) - currier_step = 1000; - else if (intp->symbol_rate[demod] <= 5000000) - currier_step = 2000; - else if (intp->symbol_rate[demod] <= 12000000) - currier_step = 3000; - else - currier_step = 5000; - - nb_steps = -1 + ((intp->srch_range[demod] / 1000) / currier_step); - nb_steps /= 2; - nb_steps = (2 * nb_steps) + 1; - - if (nb_steps < 0) - nb_steps = 1; - else if (nb_steps > 10) { - nb_steps = 11; - currier_step = (intp->srch_range[demod] / 1000) / 10; - } - - current_step = 0; - direction = 1; - - tuner_freq = intp->freq[demod]; - - while ((timing_lck == FALSE) && (current_step < nb_steps)) { - stv0900_write_reg(intp, DMDISTATE, 0x5f); - stv0900_write_bits(intp, DEMOD_MODE, 0); - - msleep(50); - - for (i = 0; i < 10; i++) { - if (stv0900_get_bits(intp, TMGLOCK_QUALITY) >= 2) - timingcpt++; - - agc2_integr += (stv0900_read_reg(intp, AGC2I1) << 8) | - stv0900_read_reg(intp, AGC2I0); - } - - agc2_integr /= 10; - coarse_srate = stv0900_get_symbol_rate(intp, intp->mclk, demod); - current_step++; - direction *= -1; - - dprintk("lock: I2C_DEMOD_MODE_FIELD =0. Search started." - " tuner freq=%d agc2=0x%x srate_coarse=%d tmg_cpt=%d\n", - tuner_freq, agc2_integr, coarse_srate, timingcpt); - - if ((timingcpt >= 5) && - (agc2_integr < agc2_th) && - (coarse_srate < 55000000) && - (coarse_srate > 850000)) - timing_lck = TRUE; - else if (current_step < nb_steps) { - if (direction > 0) - tuner_freq += (current_step * currier_step); - else - tuner_freq -= (current_step * currier_step); - - if (intp->tuner_type[demod] == 3) - stv0900_set_tuner_auto(intp, tuner_freq, - intp->bw[demod], demod); - else - stv0900_set_tuner(fe, tuner_freq, - intp->bw[demod]); - } - } - - if (timing_lck == FALSE) - coarse_srate = 0; - else - coarse_srate = stv0900_get_symbol_rate(intp, intp->mclk, demod); - - return coarse_srate; -} - -static u32 stv0900_search_srate_fine(struct dvb_frontend *fe) -{ - struct stv0900_state *state = fe->demodulator_priv; - struct stv0900_internal *intp = state->internal; - enum fe_stv0900_demod_num demod = state->demod; - u32 coarse_srate, - coarse_freq, - symb, - symbmax, - symbmin, - symbcomp; - - coarse_srate = stv0900_get_symbol_rate(intp, intp->mclk, demod); - - if (coarse_srate > 3000000) { - symbmax = 13 * (coarse_srate / 10); - symbmax = (symbmax / 1000) * 65536; - symbmax /= (intp->mclk / 1000); - - symbmin = 10 * (coarse_srate / 13); - symbmin = (symbmin / 1000)*65536; - symbmin /= (intp->mclk / 1000); - - symb = (coarse_srate / 1000) * 65536; - symb /= (intp->mclk / 1000); - } else { - symbmax = 13 * (coarse_srate / 10); - symbmax = (symbmax / 100) * 65536; - symbmax /= (intp->mclk / 100); - - symbmin = 10 * (coarse_srate / 14); - symbmin = (symbmin / 100) * 65536; - symbmin /= (intp->mclk / 100); - - symb = (coarse_srate / 100) * 65536; - symb /= (intp->mclk / 100); - } - - symbcomp = 13 * (coarse_srate / 10); - coarse_freq = (stv0900_read_reg(intp, CFR2) << 8) - | stv0900_read_reg(intp, CFR1); - - if (symbcomp < intp->symbol_rate[demod]) - coarse_srate = 0; - else { - stv0900_write_reg(intp, DMDISTATE, 0x1f); - stv0900_write_reg(intp, TMGCFG2, 0xc1); - stv0900_write_reg(intp, TMGTHRISE, 0x20); - stv0900_write_reg(intp, TMGTHFALL, 0x00); - stv0900_write_reg(intp, TMGCFG, 0xd2); - stv0900_write_bits(intp, CFR_AUTOSCAN, 0); - stv0900_write_reg(intp, AGC2REF, 0x38); - - if (intp->chip_id >= 0x30) - stv0900_write_reg(intp, CARFREQ, 0x79); - else if (intp->chip_id >= 0x20) - stv0900_write_reg(intp, CARFREQ, 0x49); - else - stv0900_write_reg(intp, CARFREQ, 0xed); - - stv0900_write_reg(intp, SFRUP1, (symbmax >> 8) & 0x7f); - stv0900_write_reg(intp, SFRUP0, (symbmax & 0xff)); - - stv0900_write_reg(intp, SFRLOW1, (symbmin >> 8) & 0x7f); - stv0900_write_reg(intp, SFRLOW0, (symbmin & 0xff)); - - stv0900_write_reg(intp, SFRINIT1, (symb >> 8) & 0xff); - stv0900_write_reg(intp, SFRINIT0, (symb & 0xff)); - - stv0900_write_reg(intp, DMDT0M, 0x20); - stv0900_write_reg(intp, CFRINIT1, (coarse_freq >> 8) & 0xff); - stv0900_write_reg(intp, CFRINIT0, coarse_freq & 0xff); - stv0900_write_reg(intp, DMDISTATE, 0x15); - } - - return coarse_srate; -} - -static int stv0900_blind_search_algo(struct dvb_frontend *fe) -{ - struct stv0900_state *state = fe->demodulator_priv; - struct stv0900_internal *intp = state->internal; - enum fe_stv0900_demod_num demod = state->demod; - u8 k_ref_tmg, - k_ref_tmg_max, - k_ref_tmg_min; - u32 coarse_srate, - agc2_th; - int lock = FALSE, - coarse_fail = FALSE; - s32 demod_timeout = 500, - fec_timeout = 50, - fail_cpt, - i, - agc2_overflow; - u16 agc2_int; - u8 dstatus2; - - dprintk("%s\n", __func__); - - if (intp->chip_id < 0x20) { - k_ref_tmg_max = 233; - k_ref_tmg_min = 143; - } else { - k_ref_tmg_max = 110; - k_ref_tmg_min = 10; - } - - if (intp->chip_id <= 0x20) - agc2_th = STV0900_BLIND_SEARCH_AGC2_TH; - else - agc2_th = STV0900_BLIND_SEARCH_AGC2_TH_CUT30; - - agc2_int = stv0900_blind_check_agc2_min_level(intp, demod); - - dprintk("%s agc2_int=%d agc2_th=%d \n", __func__, agc2_int, agc2_th); - if (agc2_int > agc2_th) - return FALSE; - - if (intp->chip_id == 0x10) - stv0900_write_reg(intp, CORRELEXP, 0xaa); - - if (intp->chip_id < 0x20) - stv0900_write_reg(intp, CARHDR, 0x55); - else - stv0900_write_reg(intp, CARHDR, 0x20); - - if (intp->chip_id <= 0x20) - stv0900_write_reg(intp, CARCFG, 0xc4); - else - stv0900_write_reg(intp, CARCFG, 0x6); - - stv0900_write_reg(intp, RTCS2, 0x44); - - if (intp->chip_id >= 0x20) { - stv0900_write_reg(intp, EQUALCFG, 0x41); - stv0900_write_reg(intp, FFECFG, 0x41); - stv0900_write_reg(intp, VITSCALE, 0x82); - stv0900_write_reg(intp, VAVSRVIT, 0x0); - } - - k_ref_tmg = k_ref_tmg_max; - - do { - stv0900_write_reg(intp, KREFTMG, k_ref_tmg); - if (stv0900_search_srate_coarse(fe) != 0) { - coarse_srate = stv0900_search_srate_fine(fe); - - if (coarse_srate != 0) { - stv0900_get_lock_timeout(&demod_timeout, - &fec_timeout, - coarse_srate, - STV0900_BLIND_SEARCH); - lock = stv0900_get_demod_lock(intp, - demod, - demod_timeout); - } else - lock = FALSE; - } else { - fail_cpt = 0; - agc2_overflow = 0; - - for (i = 0; i < 10; i++) { - agc2_int = (stv0900_read_reg(intp, AGC2I1) << 8) - | stv0900_read_reg(intp, AGC2I0); - - if (agc2_int >= 0xff00) - agc2_overflow++; - - dstatus2 = stv0900_read_reg(intp, DSTATUS2); - - if (((dstatus2 & 0x1) == 0x1) && - ((dstatus2 >> 7) == 1)) - fail_cpt++; - } - - if ((fail_cpt > 7) || (agc2_overflow > 7)) - coarse_fail = TRUE; - - lock = FALSE; - } - k_ref_tmg -= 30; - } while ((k_ref_tmg >= k_ref_tmg_min) && - (lock == FALSE) && - (coarse_fail == FALSE)); - - return lock; -} - -static void stv0900_set_viterbi_acq(struct stv0900_internal *intp, - enum fe_stv0900_demod_num demod) -{ - s32 vth_reg = VTH12; - - dprintk("%s\n", __func__); - - stv0900_write_reg(intp, vth_reg++, 0x96); - stv0900_write_reg(intp, vth_reg++, 0x64); - stv0900_write_reg(intp, vth_reg++, 0x36); - stv0900_write_reg(intp, vth_reg++, 0x23); - stv0900_write_reg(intp, vth_reg++, 0x1e); - stv0900_write_reg(intp, vth_reg++, 0x19); -} - -static void stv0900_set_search_standard(struct stv0900_internal *intp, - enum fe_stv0900_demod_num demod) -{ - - dprintk("%s\n", __func__); - - switch (intp->srch_standard[demod]) { - case STV0900_SEARCH_DVBS1: - dprintk("Search Standard = DVBS1\n"); - break; - case STV0900_SEARCH_DSS: - dprintk("Search Standard = DSS\n"); - case STV0900_SEARCH_DVBS2: - break; - dprintk("Search Standard = DVBS2\n"); - case STV0900_AUTO_SEARCH: - default: - dprintk("Search Standard = AUTO\n"); - break; - } - - switch (intp->srch_standard[demod]) { - case STV0900_SEARCH_DVBS1: - case STV0900_SEARCH_DSS: - stv0900_write_bits(intp, DVBS1_ENABLE, 1); - stv0900_write_bits(intp, DVBS2_ENABLE, 0); - stv0900_write_bits(intp, STOP_CLKVIT, 0); - stv0900_set_dvbs1_track_car_loop(intp, - demod, - intp->symbol_rate[demod]); - stv0900_write_reg(intp, CAR2CFG, 0x22); - - stv0900_set_viterbi_acq(intp, demod); - stv0900_set_viterbi_standard(intp, - intp->srch_standard[demod], - intp->fec[demod], demod); - - break; - case STV0900_SEARCH_DVBS2: - stv0900_write_bits(intp, DVBS1_ENABLE, 0); - stv0900_write_bits(intp, DVBS2_ENABLE, 1); - stv0900_write_bits(intp, STOP_CLKVIT, 1); - stv0900_write_reg(intp, ACLC, 0x1a); - stv0900_write_reg(intp, BCLC, 0x09); - if (intp->chip_id <= 0x20) /*cut 1.x and 2.0*/ - stv0900_write_reg(intp, CAR2CFG, 0x26); - else - stv0900_write_reg(intp, CAR2CFG, 0x66); - - if (intp->demod_mode != STV0900_SINGLE) { - if (intp->chip_id <= 0x11) - stv0900_stop_all_s2_modcod(intp, demod); - else - stv0900_activate_s2_modcod(intp, demod); - - } else - stv0900_activate_s2_modcod_single(intp, demod); - - stv0900_set_viterbi_tracq(intp, demod); - - break; - case STV0900_AUTO_SEARCH: - default: - stv0900_write_bits(intp, DVBS1_ENABLE, 1); - stv0900_write_bits(intp, DVBS2_ENABLE, 1); - stv0900_write_bits(intp, STOP_CLKVIT, 0); - stv0900_write_reg(intp, ACLC, 0x1a); - stv0900_write_reg(intp, BCLC, 0x09); - stv0900_set_dvbs1_track_car_loop(intp, - demod, - intp->symbol_rate[demod]); - if (intp->chip_id <= 0x20) /*cut 1.x and 2.0*/ - stv0900_write_reg(intp, CAR2CFG, 0x26); - else - stv0900_write_reg(intp, CAR2CFG, 0x66); - - if (intp->demod_mode != STV0900_SINGLE) { - if (intp->chip_id <= 0x11) - stv0900_stop_all_s2_modcod(intp, demod); - else - stv0900_activate_s2_modcod(intp, demod); - - } else - stv0900_activate_s2_modcod_single(intp, demod); - - stv0900_set_viterbi_tracq(intp, demod); - stv0900_set_viterbi_standard(intp, - intp->srch_standard[demod], - intp->fec[demod], demod); - - break; - } -} - -enum fe_stv0900_signal_type stv0900_algo(struct dvb_frontend *fe) -{ - struct stv0900_state *state = fe->demodulator_priv; - struct stv0900_internal *intp = state->internal; - enum fe_stv0900_demod_num demod = state->demod; - - s32 demod_timeout = 500, fec_timeout = 50; - s32 aq_power, agc1_power, i; - - int lock = FALSE, low_sr = FALSE; - - enum fe_stv0900_signal_type signal_type = STV0900_NOCARRIER; - enum fe_stv0900_search_algo algo; - int no_signal = FALSE; - - dprintk("%s\n", __func__); - - algo = intp->srch_algo[demod]; - stv0900_write_bits(intp, RST_HWARE, 1); - stv0900_write_reg(intp, DMDISTATE, 0x5c); - if (intp->chip_id >= 0x20) { - if (intp->symbol_rate[demod] > 5000000) - stv0900_write_reg(intp, CORRELABS, 0x9e); - else - stv0900_write_reg(intp, CORRELABS, 0x82); - } else - stv0900_write_reg(intp, CORRELABS, 0x88); - - stv0900_get_lock_timeout(&demod_timeout, &fec_timeout, - intp->symbol_rate[demod], - intp->srch_algo[demod]); - - if (intp->srch_algo[demod] == STV0900_BLIND_SEARCH) { - intp->bw[demod] = 2 * 36000000; - - stv0900_write_reg(intp, TMGCFG2, 0xc0); - stv0900_write_reg(intp, CORRELMANT, 0x70); - - stv0900_set_symbol_rate(intp, intp->mclk, 1000000, demod); - } else { - stv0900_write_reg(intp, DMDT0M, 0x20); - stv0900_write_reg(intp, TMGCFG, 0xd2); - - if (intp->symbol_rate[demod] < 2000000) - stv0900_write_reg(intp, CORRELMANT, 0x63); - else - stv0900_write_reg(intp, CORRELMANT, 0x70); - - stv0900_write_reg(intp, AGC2REF, 0x38); - - intp->bw[demod] = - stv0900_carrier_width(intp->symbol_rate[demod], - intp->rolloff); - if (intp->chip_id >= 0x20) { - stv0900_write_reg(intp, KREFTMG, 0x5a); - - if (intp->srch_algo[demod] == STV0900_COLD_START) { - intp->bw[demod] += 10000000; - intp->bw[demod] *= 15; - intp->bw[demod] /= 10; - } else if (intp->srch_algo[demod] == STV0900_WARM_START) - intp->bw[demod] += 10000000; - - } else { - stv0900_write_reg(intp, KREFTMG, 0xc1); - intp->bw[demod] += 10000000; - intp->bw[demod] *= 15; - intp->bw[demod] /= 10; - } - - stv0900_write_reg(intp, TMGCFG2, 0xc1); - - stv0900_set_symbol_rate(intp, intp->mclk, - intp->symbol_rate[demod], demod); - stv0900_set_max_symbol_rate(intp, intp->mclk, - intp->symbol_rate[demod], demod); - stv0900_set_min_symbol_rate(intp, intp->mclk, - intp->symbol_rate[demod], demod); - if (intp->symbol_rate[demod] >= 10000000) - low_sr = FALSE; - else - low_sr = TRUE; - - } - - if (intp->tuner_type[demod] == 3) - stv0900_set_tuner_auto(intp, intp->freq[demod], - intp->bw[demod], demod); - else - stv0900_set_tuner(fe, intp->freq[demod], intp->bw[demod]); - - agc1_power = MAKEWORD(stv0900_get_bits(intp, AGCIQ_VALUE1), - stv0900_get_bits(intp, AGCIQ_VALUE0)); - - aq_power = 0; - - if (agc1_power == 0) { - for (i = 0; i < 5; i++) - aq_power += (stv0900_get_bits(intp, POWER_I) + - stv0900_get_bits(intp, POWER_Q)) / 2; - - aq_power /= 5; - } - - if ((agc1_power == 0) && (aq_power < IQPOWER_THRESHOLD)) { - intp->result[demod].locked = FALSE; - signal_type = STV0900_NOAGC1; - dprintk("%s: NO AGC1, POWERI, POWERQ\n", __func__); - } else { - stv0900_write_bits(intp, SPECINV_CONTROL, - intp->srch_iq_inv[demod]); - if (intp->chip_id <= 0x20) /*cut 2.0*/ - stv0900_write_bits(intp, MANUALSX_ROLLOFF, 1); - else /*cut 3.0*/ - stv0900_write_bits(intp, MANUALS2_ROLLOFF, 1); - - stv0900_set_search_standard(intp, demod); - - if (intp->srch_algo[demod] != STV0900_BLIND_SEARCH) - stv0900_start_search(intp, demod); - } - - if (signal_type == STV0900_NOAGC1) - return signal_type; - - if (intp->chip_id == 0x12) { - stv0900_write_bits(intp, RST_HWARE, 0); - msleep(3); - stv0900_write_bits(intp, RST_HWARE, 1); - stv0900_write_bits(intp, RST_HWARE, 0); - } - - if (algo == STV0900_BLIND_SEARCH) - lock = stv0900_blind_search_algo(fe); - else if (algo == STV0900_COLD_START) - lock = stv0900_get_demod_cold_lock(fe, demod_timeout); - else if (algo == STV0900_WARM_START) - lock = stv0900_get_demod_lock(intp, demod, demod_timeout); - - if ((lock == FALSE) && (algo == STV0900_COLD_START)) { - if (low_sr == FALSE) { - if (stv0900_check_timing_lock(intp, demod) == TRUE) - lock = stv0900_sw_algo(intp, demod); - } - } - - if (lock == TRUE) - signal_type = stv0900_get_signal_params(fe); - - if ((lock == TRUE) && (signal_type == STV0900_RANGEOK)) { - stv0900_track_optimization(fe); - if (intp->chip_id <= 0x11) { - if ((stv0900_get_standard(fe, 0) == - STV0900_DVBS1_STANDARD) && - (stv0900_get_standard(fe, 1) == - STV0900_DVBS1_STANDARD)) { - msleep(20); - stv0900_write_bits(intp, RST_HWARE, 0); - } else { - stv0900_write_bits(intp, RST_HWARE, 0); - msleep(3); - stv0900_write_bits(intp, RST_HWARE, 1); - stv0900_write_bits(intp, RST_HWARE, 0); - } - - } else if (intp->chip_id >= 0x20) { - stv0900_write_bits(intp, RST_HWARE, 0); - msleep(3); - stv0900_write_bits(intp, RST_HWARE, 1); - stv0900_write_bits(intp, RST_HWARE, 0); - } - - if (stv0900_wait_for_lock(intp, demod, - fec_timeout, fec_timeout) == TRUE) { - lock = TRUE; - intp->result[demod].locked = TRUE; - if (intp->result[demod].standard == - STV0900_DVBS2_STANDARD) { - stv0900_set_dvbs2_rolloff(intp, demod); - stv0900_write_bits(intp, RESET_UPKO_COUNT, 1); - stv0900_write_bits(intp, RESET_UPKO_COUNT, 0); - stv0900_write_reg(intp, ERRCTRL1, 0x67); - } else { - stv0900_write_reg(intp, ERRCTRL1, 0x75); - } - - stv0900_write_reg(intp, FBERCPT4, 0); - stv0900_write_reg(intp, ERRCTRL2, 0xc1); - } else { - lock = FALSE; - signal_type = STV0900_NODATA; - no_signal = stv0900_check_signal_presence(intp, demod); - - intp->result[demod].locked = FALSE; - } - } - - if ((signal_type != STV0900_NODATA) || (no_signal != FALSE)) - return signal_type; - - if (intp->chip_id > 0x11) { - intp->result[demod].locked = FALSE; - return signal_type; - } - - if ((stv0900_get_bits(intp, HEADER_MODE) == STV0900_DVBS_FOUND) && - (intp->srch_iq_inv[demod] <= STV0900_IQ_AUTO_NORMAL_FIRST)) - signal_type = stv0900_dvbs1_acq_workaround(fe); - - return signal_type; -} - |