staticint tda18271_i2c_gate_ctrl(struct dvb_frontend *fe, int enable)
{ struct tda18271_priv *priv = fe->tuner_priv; enum tda18271_i2c_gate gate; int ret = 0;
switch (priv->gate) { case TDA18271_GATE_DIGITAL: case TDA18271_GATE_ANALOG:
gate = priv->gate; break; case TDA18271_GATE_AUTO: default: switch (priv->mode) { case TDA18271_DIGITAL:
gate = TDA18271_GATE_DIGITAL; break; case TDA18271_ANALOG: default:
gate = TDA18271_GATE_ANALOG; break;
}
}
switch (gate) { case TDA18271_GATE_ANALOG: if (fe->ops.analog_ops.i2c_gate_ctrl)
ret = fe->ops.analog_ops.i2c_gate_ctrl(fe, enable); break; case TDA18271_GATE_DIGITAL: if (fe->ops.i2c_gate_ctrl)
ret = fe->ops.i2c_gate_ctrl(fe, enable); break; default:
ret = -EINVAL; break;
}
/* read all registers */
ret = i2c_transfer(priv->i2c_props.adap, msg, 2);
tda18271_i2c_gate_ctrl(fe, 0);
if (ret != 2)
tda_err("ERROR: i2c_transfer returned: %d\n", ret);
for (i = 0; i < TDA18271_NUM_REGS; i++) { /* don't update write-only registers */ if ((i != R_EB9) &&
(i != R_EB16) &&
(i != R_EB17) &&
(i != R_EB19) &&
(i != R_EB20))
regs[i] = regdump[i];
}
if (tda18271_debug & DBG_REG)
tda18271_dump_regs(fe, 1);
return (ret == 2 ? 0 : ret);
}
staticint __tda18271_write_regs(struct dvb_frontend *fe, int idx, int len, bool lock_i2c)
{ struct tda18271_priv *priv = fe->tuner_priv; unsignedchar *regs = priv->tda18271_regs; unsignedchar buf[TDA18271_NUM_REGS + 1]; struct i2c_msg msg = { .addr = priv->i2c_props.addr, .flags = 0,
.buf = buf }; int i, ret = 1, max;
BUG_ON((len == 0) || (idx + len > sizeof(buf)));
switch (priv->small_i2c) { case TDA18271_03_BYTE_CHUNK_INIT:
max = 3; break; case TDA18271_08_BYTE_CHUNK_INIT:
max = 8; break; case TDA18271_16_BYTE_CHUNK_INIT:
max = 16; break; case TDA18271_39_BYTE_CHUNK_INIT: default:
max = 39;
}
/* *Iflock_i2cistrue,itwilltaketheI2Cbusfortda18271private *usageduringtheentirewriteops,asotherwise,badthingscould *happen. *Duringdeviceinit,severalwriteoperationswillhappen.So, *tda18271_init_regscontrolstheI2Clockdirectly, *disablinglock_i2chere.
*/ if (lock_i2c) {
tda18271_i2c_gate_ctrl(fe, 1);
i2c_lock_bus(priv->i2c_props.adap, I2C_LOCK_SEGMENT);
} while (len) { if (max > len)
max = len;
buf[0] = idx; for (i = 1; i <= max; i++)
buf[i] = regs[idx - 1 + i];
msg.len = max + 1;
/* write registers */
ret = __i2c_transfer(priv->i2c_props.adap, &msg, 1); if (ret != 1) break;
idx += max;
len -= max;
} if (lock_i2c) {
i2c_unlock_bus(priv->i2c_props.adap, I2C_LOCK_SEGMENT);
tda18271_i2c_gate_ctrl(fe, 0);
}
if (ret != 1)
tda_err("ERROR: idx = 0x%x, len = %d, i2c_transfer returned: %d\n",
idx, max, ret);
return (ret == 1 ? 0 : ret);
}
int tda18271_write_regs(struct dvb_frontend *fe, int idx, int len)
{ return __tda18271_write_regs(fe, idx, len, true);
}
int tda18271_set_standby_mode(struct dvb_frontend *fe, int sm, int sm_lt, int sm_xt)
{ struct tda18271_priv *priv = fe->tuner_priv; unsignedchar *regs = priv->tda18271_regs;
int tda18271_calc_main_pll(struct dvb_frontend *fe, u32 freq)
{ /* sets main post divider & divider bytes, but does not write them */ struct tda18271_priv *priv = fe->tuner_priv; unsignedchar *regs = priv->tda18271_regs;
u8 d, pd;
u32 div;
int ret = tda18271_lookup_pll_map(fe, MAIN_PLL, &freq, &pd, &d); if (tda_fail(ret)) goto fail;
int tda18271_calc_cal_pll(struct dvb_frontend *fe, u32 freq)
{ /* sets cal post divider & divider bytes, but does not write them */ struct tda18271_priv *priv = fe->tuner_priv; unsignedchar *regs = priv->tda18271_regs;
u8 d, pd;
u32 div;
int ret = tda18271_lookup_pll_map(fe, CAL_PLL, &freq, &pd, &d); if (tda_fail(ret)) goto fail;
int tda18271_calc_bp_filter(struct dvb_frontend *fe, u32 *freq)
{ /* sets bp filter bits, but does not write them */ struct tda18271_priv *priv = fe->tuner_priv; unsignedchar *regs = priv->tda18271_regs;
u8 val;
int ret = tda18271_lookup_map(fe, BP_FILTER, freq, &val); if (tda_fail(ret)) goto fail;
int tda18271_calc_km(struct dvb_frontend *fe, u32 *freq)
{ /* sets K & M bits, but does not write them */ struct tda18271_priv *priv = fe->tuner_priv; unsignedchar *regs = priv->tda18271_regs;
u8 val;
int ret = tda18271_lookup_map(fe, RF_CAL_KMCO, freq, &val); if (tda_fail(ret)) goto fail;
regs[R_EB13] &= ~0x7c; /* clear k & m bits */
regs[R_EB13] |= (0x7c & val);
fail: return ret;
}
int tda18271_calc_rf_band(struct dvb_frontend *fe, u32 *freq)
{ /* sets rf band bits, but does not write them */ struct tda18271_priv *priv = fe->tuner_priv; unsignedchar *regs = priv->tda18271_regs;
u8 val;
int ret = tda18271_lookup_map(fe, RF_BAND, freq, &val); if (tda_fail(ret)) goto fail;
int tda18271_calc_gain_taper(struct dvb_frontend *fe, u32 *freq)
{ /* sets gain taper bits, but does not write them */ struct tda18271_priv *priv = fe->tuner_priv; unsignedchar *regs = priv->tda18271_regs;
u8 val;
int ret = tda18271_lookup_map(fe, GAIN_TAPER, freq, &val); if (tda_fail(ret)) goto fail;
int tda18271_calc_ir_measure(struct dvb_frontend *fe, u32 *freq)
{ /* sets IR Meas bits, but does not write them */ struct tda18271_priv *priv = fe->tuner_priv; unsignedchar *regs = priv->tda18271_regs;
u8 val;
int ret = tda18271_lookup_map(fe, IR_MEASURE, freq, &val); if (tda_fail(ret)) goto fail;
int tda18271_calc_rf_cal(struct dvb_frontend *fe, u32 *freq)
{ /* sets rf cal byte (RFC_Cprog), but does not write it */ struct tda18271_priv *priv = fe->tuner_priv; unsignedchar *regs = priv->tda18271_regs;
u8 val;
int ret = tda18271_lookup_map(fe, RF_CAL, freq, &val); /* The TDA18271HD/C1 rf_cal map lookup is expected to go out of range *forfrequenciesabove61.1MHz.Inthesecases,theinternalRF *trackingfilterscalibrationmechanismisused. * *Thereisnoneedtowarntheuseraboutthis.
*/ if (ret < 0) goto fail;
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.