22 #include <asm/div64.h>
28 #define dprintk(args...) \
31 printk(KERN_DEBUG "atbm8830: " args); \
43 u8 buf1[] = { reg >> 8, reg & 0xFF };
45 struct i2c_msg msg1 = { .
flags = 0, .buf = buf1, .len = 2 };
46 struct i2c_msg msg2 = { .
flags = 0, .buf = buf2, .len = 1 };
48 dev_addr = priv->
config->demod_address;
53 dprintk(
"%s: reg=0x%04X, data=0x%02X\n", __func__, reg, data);
60 return (ret != 1) ? -
EIO : 0;
68 u8 buf1[] = { reg >> 8, reg & 0xFF };
70 struct i2c_msg msg1 = { .
flags = 0, .buf = buf1, .len = 2 };
73 dev_addr = priv->
config->demod_address;
79 dprintk(
"%s: error reg=0x%04x, ret=%i\n", __func__, reg, ret);
89 dprintk(
"%s: reg=0x%04X, data=0x%02X\n",
90 __func__, reg, buf2[0]);
96 static inline int atbm8830_reglatch_lock(
struct atbm_state *priv,
int lock)
107 t = (
u64)0x100000 * freq;
112 atbm8830_write_reg(priv,
REG_OSC_CLK + 1, val >> 8);
113 atbm8830_write_reg(priv,
REG_OSC_CLK + 2, val >> 16);
128 t = (
u64) 2 * 31416 * (freq - fs);
137 atbm8830_write_reg(priv,
REG_IF_FREQ+2, val >> 16);
151 if (priv->
config->zif_swap_iq)
167 *locked = (status == 1);
171 static int set_agc_config(
struct atbm_state *priv,
185 static int set_static_channel_mode(
struct atbm_state *priv)
189 for (i = 0; i < 5; i++)
190 atbm8830_write_reg(priv, 0x099B + i, 0x08);
192 atbm8830_write_reg(priv, 0x095B, 0x7F);
193 atbm8830_write_reg(priv, 0x09CB, 0x01);
194 atbm8830_write_reg(priv, 0x09CC, 0x7F);
195 atbm8830_write_reg(priv, 0x09CD, 0x7F);
196 atbm8830_write_reg(priv, 0x0E01, 0x20);
199 atbm8830_write_reg(priv, 0x0B03, 0x0A);
200 atbm8830_write_reg(priv, 0x0935, 0x10);
201 atbm8830_write_reg(priv, 0x0936, 0x08);
202 atbm8830_write_reg(priv, 0x093E, 0x08);
203 atbm8830_write_reg(priv, 0x096E, 0x06);
206 atbm8830_write_reg(priv, 0x0B09, 0x00);
208 atbm8830_write_reg(priv, 0x0B0A, 0x08);
213 static int set_ts_config(
struct atbm_state *priv)
239 set_if_freq(priv, cfg->
if_freq);
246 set_static_channel_mode(priv);
250 atbm8830_write_reg(priv, 0x000A, 0);
253 atbm8830_write_reg(priv, 0x020C, 11);
278 if (fe->
ops.tuner_ops.set_params) {
279 if (fe->
ops.i2c_gate_ctrl)
280 fe->
ops.i2c_gate_ctrl(fe, 1);
281 fe->
ops.tuner_ops.set_params(fe);
282 if (fe->
ops.i2c_gate_ctrl)
283 fe->
ops.i2c_gate_ctrl(fe, 0);
287 for (i = 0; i < 10; i++) {
290 is_locked(priv, &locked);
329 static int atbm8830_get_tune_settings(
struct dvb_frontend *fe,
347 is_locked(priv, &locked);
352 dprintk(
"%s: fe_status=0x%x\n", __func__, *fe_status);
355 dprintk(
"AGC Lock: %d\n", agc_locked);
368 atbm8830_reglatch_lock(priv, 1);
371 frame_err = t & 0x7F;
376 atbm8830_reglatch_lock(priv, 0);
378 *ber = frame_err * 100 / 32767;
380 dprintk(
"%s: ber=0x%x\n", __func__, *ber);
384 static int atbm8830_read_signal_strength(
struct dvb_frontend *fe,
u16 *signal)
391 atbm8830_reglatch_lock(priv, 1);
399 atbm8830_reglatch_lock(priv, 0);
401 dprintk(
"AGC PWM = 0x%02X\n", pwm);
404 *signal = pwm * 0x10000 / 0x400;
416 static int atbm8830_read_ucblocks(
struct dvb_frontend *fe,
u32 *ucblocks)
427 return atbm8830_write_reg(priv,
REG_I2C_GATE, enable ? 1 : 0);
433 .name =
"AltoBeam ATBM8830/8831 DMB-TH",
434 .frequency_min = 474000000,
435 .frequency_max = 858000000,
436 .frequency_stepsize = 10000,
444 .release = atbm8830_release,
446 .init = atbm8830_init,
449 .i2c_gate_ctrl = atbm8830_i2c_gate_ctrl,
451 .set_frontend = atbm8830_set_fe,
452 .get_frontend = atbm8830_get_fe,
453 .get_tune_settings = atbm8830_get_tune_settings,
455 .read_status = atbm8830_read_status,
456 .read_ber = atbm8830_read_ber,
457 .read_signal_strength = atbm8830_read_signal_strength,
458 .read_snr = atbm8830_read_snr,
459 .read_ucblocks = atbm8830_read_ucblocks,
481 if (atbm8830_read_reg(priv,
REG_CHIP_ID, &data) != 0) {
482 dprintk(
"%s atbm8830/8831 not found at i2c addr 0x%02X\n",
483 __func__, priv->
config->demod_address);
486 dprintk(
"atbm8830 chip id: 0x%02X\n", data);
494 atbm8830_i2c_gate_ctrl(&priv->
frontend, 1);
499 dprintk(
"%s() error_out\n", __func__);