dib3000mb.c (23283B)
1// SPDX-License-Identifier: GPL-2.0-only 2/* 3 * Frontend driver for mobile DVB-T demodulator DiBcom 3000M-B 4 * DiBcom (http://www.dibcom.fr/) 5 * 6 * Copyright (C) 2004-5 Patrick Boettcher (patrick.boettcher@posteo.de) 7 * 8 * based on GPL code from DibCom, which has 9 * 10 * Copyright (C) 2004 Amaury Demol for DiBcom 11 * 12 * Acknowledgements 13 * 14 * Amaury Demol from DiBcom for providing specs and driver 15 * sources, on which this driver (and the dvb-dibusb) are based. 16 * 17 * see Documentation/driver-api/media/drivers/dvb-usb.rst for more information 18 */ 19 20#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt 21 22#include <linux/kernel.h> 23#include <linux/module.h> 24#include <linux/init.h> 25#include <linux/delay.h> 26#include <linux/string.h> 27#include <linux/slab.h> 28 29#include <media/dvb_frontend.h> 30 31#include "dib3000.h" 32#include "dib3000mb_priv.h" 33 34/* Version information */ 35#define DRIVER_VERSION "0.1" 36#define DRIVER_DESC "DiBcom 3000M-B DVB-T demodulator" 37#define DRIVER_AUTHOR "Patrick Boettcher, patrick.boettcher@posteo.de" 38 39static int debug; 40module_param(debug, int, 0644); 41MODULE_PARM_DESC(debug, "set debugging level (1=info,2=xfer,4=setfe,8=getfe (|-able))."); 42 43#define deb_info(args...) dprintk(0x01, args) 44#define deb_i2c(args...) dprintk(0x02, args) 45#define deb_srch(args...) dprintk(0x04, args) 46#define deb_info(args...) dprintk(0x01, args) 47#define deb_xfer(args...) dprintk(0x02, args) 48#define deb_setf(args...) dprintk(0x04, args) 49#define deb_getf(args...) dprintk(0x08, args) 50 51static int dib3000_read_reg(struct dib3000_state *state, u16 reg) 52{ 53 u8 wb[] = { ((reg >> 8) | 0x80) & 0xff, reg & 0xff }; 54 u8 rb[2]; 55 struct i2c_msg msg[] = { 56 { .addr = state->config.demod_address, .flags = 0, .buf = wb, .len = 2 }, 57 { .addr = state->config.demod_address, .flags = I2C_M_RD, .buf = rb, .len = 2 }, 58 }; 59 60 if (i2c_transfer(state->i2c, msg, 2) != 2) 61 deb_i2c("i2c read error\n"); 62 63 deb_i2c("reading i2c bus (reg: %5d 0x%04x, val: %5d 0x%04x)\n",reg,reg, 64 (rb[0] << 8) | rb[1],(rb[0] << 8) | rb[1]); 65 66 return (rb[0] << 8) | rb[1]; 67} 68 69static int dib3000_write_reg(struct dib3000_state *state, u16 reg, u16 val) 70{ 71 u8 b[] = { 72 (reg >> 8) & 0xff, reg & 0xff, 73 (val >> 8) & 0xff, val & 0xff, 74 }; 75 struct i2c_msg msg[] = { 76 { .addr = state->config.demod_address, .flags = 0, .buf = b, .len = 4 } 77 }; 78 deb_i2c("writing i2c bus (reg: %5d 0x%04x, val: %5d 0x%04x)\n",reg,reg,val,val); 79 80 return i2c_transfer(state->i2c,msg, 1) != 1 ? -EREMOTEIO : 0; 81} 82 83static int dib3000_search_status(u16 irq,u16 lock) 84{ 85 if (irq & 0x02) { 86 if (lock & 0x01) { 87 deb_srch("auto search succeeded\n"); 88 return 1; // auto search succeeded 89 } else { 90 deb_srch("auto search not successful\n"); 91 return 0; // auto search failed 92 } 93 } else if (irq & 0x01) { 94 deb_srch("auto search failed\n"); 95 return 0; // auto search failed 96 } 97 return -1; // try again 98} 99 100/* for auto search */ 101static u16 dib3000_seq[2][2][2] = /* fft,gua, inv */ 102 { /* fft */ 103 { /* gua */ 104 { 0, 1 }, /* 0 0 { 0,1 } */ 105 { 3, 9 }, /* 0 1 { 0,1 } */ 106 }, 107 { 108 { 2, 5 }, /* 1 0 { 0,1 } */ 109 { 6, 11 }, /* 1 1 { 0,1 } */ 110 } 111 }; 112 113static int dib3000mb_get_frontend(struct dvb_frontend* fe, 114 struct dtv_frontend_properties *c); 115 116static int dib3000mb_set_frontend(struct dvb_frontend *fe, int tuner) 117{ 118 struct dib3000_state* state = fe->demodulator_priv; 119 struct dtv_frontend_properties *c = &fe->dtv_property_cache; 120 enum fe_code_rate fe_cr = FEC_NONE; 121 int search_state, seq; 122 123 if (tuner && fe->ops.tuner_ops.set_params) { 124 fe->ops.tuner_ops.set_params(fe); 125 if (fe->ops.i2c_gate_ctrl) fe->ops.i2c_gate_ctrl(fe, 0); 126 127 switch (c->bandwidth_hz) { 128 case 8000000: 129 wr_foreach(dib3000mb_reg_timing_freq, dib3000mb_timing_freq[2]); 130 wr_foreach(dib3000mb_reg_bandwidth, dib3000mb_bandwidth_8mhz); 131 break; 132 case 7000000: 133 wr_foreach(dib3000mb_reg_timing_freq, dib3000mb_timing_freq[1]); 134 wr_foreach(dib3000mb_reg_bandwidth, dib3000mb_bandwidth_7mhz); 135 break; 136 case 6000000: 137 wr_foreach(dib3000mb_reg_timing_freq, dib3000mb_timing_freq[0]); 138 wr_foreach(dib3000mb_reg_bandwidth, dib3000mb_bandwidth_6mhz); 139 break; 140 case 0: 141 return -EOPNOTSUPP; 142 default: 143 pr_err("unknown bandwidth value.\n"); 144 return -EINVAL; 145 } 146 deb_setf("bandwidth: %d MHZ\n", c->bandwidth_hz / 1000000); 147 } 148 wr(DIB3000MB_REG_LOCK1_MASK, DIB3000MB_LOCK1_SEARCH_4); 149 150 switch (c->transmission_mode) { 151 case TRANSMISSION_MODE_2K: 152 deb_setf("transmission mode: 2k\n"); 153 wr(DIB3000MB_REG_FFT, DIB3000_TRANSMISSION_MODE_2K); 154 break; 155 case TRANSMISSION_MODE_8K: 156 deb_setf("transmission mode: 8k\n"); 157 wr(DIB3000MB_REG_FFT, DIB3000_TRANSMISSION_MODE_8K); 158 break; 159 case TRANSMISSION_MODE_AUTO: 160 deb_setf("transmission mode: auto\n"); 161 break; 162 default: 163 return -EINVAL; 164 } 165 166 switch (c->guard_interval) { 167 case GUARD_INTERVAL_1_32: 168 deb_setf("guard 1_32\n"); 169 wr(DIB3000MB_REG_GUARD_TIME, DIB3000_GUARD_TIME_1_32); 170 break; 171 case GUARD_INTERVAL_1_16: 172 deb_setf("guard 1_16\n"); 173 wr(DIB3000MB_REG_GUARD_TIME, DIB3000_GUARD_TIME_1_16); 174 break; 175 case GUARD_INTERVAL_1_8: 176 deb_setf("guard 1_8\n"); 177 wr(DIB3000MB_REG_GUARD_TIME, DIB3000_GUARD_TIME_1_8); 178 break; 179 case GUARD_INTERVAL_1_4: 180 deb_setf("guard 1_4\n"); 181 wr(DIB3000MB_REG_GUARD_TIME, DIB3000_GUARD_TIME_1_4); 182 break; 183 case GUARD_INTERVAL_AUTO: 184 deb_setf("guard auto\n"); 185 break; 186 default: 187 return -EINVAL; 188 } 189 190 switch (c->inversion) { 191 case INVERSION_OFF: 192 deb_setf("inversion off\n"); 193 wr(DIB3000MB_REG_DDS_INV, DIB3000_DDS_INVERSION_OFF); 194 break; 195 case INVERSION_AUTO: 196 deb_setf("inversion auto\n"); 197 break; 198 case INVERSION_ON: 199 deb_setf("inversion on\n"); 200 wr(DIB3000MB_REG_DDS_INV, DIB3000_DDS_INVERSION_ON); 201 break; 202 default: 203 return -EINVAL; 204 } 205 206 switch (c->modulation) { 207 case QPSK: 208 deb_setf("modulation: qpsk\n"); 209 wr(DIB3000MB_REG_QAM, DIB3000_CONSTELLATION_QPSK); 210 break; 211 case QAM_16: 212 deb_setf("modulation: qam16\n"); 213 wr(DIB3000MB_REG_QAM, DIB3000_CONSTELLATION_16QAM); 214 break; 215 case QAM_64: 216 deb_setf("modulation: qam64\n"); 217 wr(DIB3000MB_REG_QAM, DIB3000_CONSTELLATION_64QAM); 218 break; 219 case QAM_AUTO: 220 break; 221 default: 222 return -EINVAL; 223 } 224 switch (c->hierarchy) { 225 case HIERARCHY_NONE: 226 deb_setf("hierarchy: none\n"); 227 fallthrough; 228 case HIERARCHY_1: 229 deb_setf("hierarchy: alpha=1\n"); 230 wr(DIB3000MB_REG_VIT_ALPHA, DIB3000_ALPHA_1); 231 break; 232 case HIERARCHY_2: 233 deb_setf("hierarchy: alpha=2\n"); 234 wr(DIB3000MB_REG_VIT_ALPHA, DIB3000_ALPHA_2); 235 break; 236 case HIERARCHY_4: 237 deb_setf("hierarchy: alpha=4\n"); 238 wr(DIB3000MB_REG_VIT_ALPHA, DIB3000_ALPHA_4); 239 break; 240 case HIERARCHY_AUTO: 241 deb_setf("hierarchy: alpha=auto\n"); 242 break; 243 default: 244 return -EINVAL; 245 } 246 247 if (c->hierarchy == HIERARCHY_NONE) { 248 wr(DIB3000MB_REG_VIT_HRCH, DIB3000_HRCH_OFF); 249 wr(DIB3000MB_REG_VIT_HP, DIB3000_SELECT_HP); 250 fe_cr = c->code_rate_HP; 251 } else if (c->hierarchy != HIERARCHY_AUTO) { 252 wr(DIB3000MB_REG_VIT_HRCH, DIB3000_HRCH_ON); 253 wr(DIB3000MB_REG_VIT_HP, DIB3000_SELECT_LP); 254 fe_cr = c->code_rate_LP; 255 } 256 switch (fe_cr) { 257 case FEC_1_2: 258 deb_setf("fec: 1_2\n"); 259 wr(DIB3000MB_REG_VIT_CODE_RATE, DIB3000_FEC_1_2); 260 break; 261 case FEC_2_3: 262 deb_setf("fec: 2_3\n"); 263 wr(DIB3000MB_REG_VIT_CODE_RATE, DIB3000_FEC_2_3); 264 break; 265 case FEC_3_4: 266 deb_setf("fec: 3_4\n"); 267 wr(DIB3000MB_REG_VIT_CODE_RATE, DIB3000_FEC_3_4); 268 break; 269 case FEC_5_6: 270 deb_setf("fec: 5_6\n"); 271 wr(DIB3000MB_REG_VIT_CODE_RATE, DIB3000_FEC_5_6); 272 break; 273 case FEC_7_8: 274 deb_setf("fec: 7_8\n"); 275 wr(DIB3000MB_REG_VIT_CODE_RATE, DIB3000_FEC_7_8); 276 break; 277 case FEC_NONE: 278 deb_setf("fec: none\n"); 279 break; 280 case FEC_AUTO: 281 deb_setf("fec: auto\n"); 282 break; 283 default: 284 return -EINVAL; 285 } 286 287 seq = dib3000_seq 288 [c->transmission_mode == TRANSMISSION_MODE_AUTO] 289 [c->guard_interval == GUARD_INTERVAL_AUTO] 290 [c->inversion == INVERSION_AUTO]; 291 292 deb_setf("seq? %d\n", seq); 293 294 wr(DIB3000MB_REG_SEQ, seq); 295 296 wr(DIB3000MB_REG_ISI, seq ? DIB3000MB_ISI_INHIBIT : DIB3000MB_ISI_ACTIVATE); 297 298 if (c->transmission_mode == TRANSMISSION_MODE_2K) { 299 if (c->guard_interval == GUARD_INTERVAL_1_8) { 300 wr(DIB3000MB_REG_SYNC_IMPROVEMENT, DIB3000MB_SYNC_IMPROVE_2K_1_8); 301 } else { 302 wr(DIB3000MB_REG_SYNC_IMPROVEMENT, DIB3000MB_SYNC_IMPROVE_DEFAULT); 303 } 304 305 wr(DIB3000MB_REG_UNK_121, DIB3000MB_UNK_121_2K); 306 } else { 307 wr(DIB3000MB_REG_UNK_121, DIB3000MB_UNK_121_DEFAULT); 308 } 309 310 wr(DIB3000MB_REG_MOBILE_ALGO, DIB3000MB_MOBILE_ALGO_OFF); 311 wr(DIB3000MB_REG_MOBILE_MODE_QAM, DIB3000MB_MOBILE_MODE_QAM_OFF); 312 wr(DIB3000MB_REG_MOBILE_MODE, DIB3000MB_MOBILE_MODE_OFF); 313 314 wr_foreach(dib3000mb_reg_agc_bandwidth, dib3000mb_agc_bandwidth_high); 315 316 wr(DIB3000MB_REG_ISI, DIB3000MB_ISI_ACTIVATE); 317 318 wr(DIB3000MB_REG_RESTART, DIB3000MB_RESTART_AGC + DIB3000MB_RESTART_CTRL); 319 wr(DIB3000MB_REG_RESTART, DIB3000MB_RESTART_OFF); 320 321 /* wait for AGC lock */ 322 msleep(70); 323 324 wr_foreach(dib3000mb_reg_agc_bandwidth, dib3000mb_agc_bandwidth_low); 325 326 /* something has to be auto searched */ 327 if (c->modulation == QAM_AUTO || 328 c->hierarchy == HIERARCHY_AUTO || 329 fe_cr == FEC_AUTO || 330 c->inversion == INVERSION_AUTO) { 331 int as_count=0; 332 333 deb_setf("autosearch enabled.\n"); 334 335 wr(DIB3000MB_REG_ISI, DIB3000MB_ISI_INHIBIT); 336 337 wr(DIB3000MB_REG_RESTART, DIB3000MB_RESTART_AUTO_SEARCH); 338 wr(DIB3000MB_REG_RESTART, DIB3000MB_RESTART_OFF); 339 340 while ((search_state = 341 dib3000_search_status( 342 rd(DIB3000MB_REG_AS_IRQ_PENDING), 343 rd(DIB3000MB_REG_LOCK2_VALUE))) < 0 && as_count++ < 100) 344 msleep(1); 345 346 deb_setf("search_state after autosearch %d after %d checks\n", 347 search_state, as_count); 348 349 if (search_state == 1) { 350 if (dib3000mb_get_frontend(fe, c) == 0) { 351 deb_setf("reading tuning data from frontend succeeded.\n"); 352 return dib3000mb_set_frontend(fe, 0); 353 } 354 } 355 356 } else { 357 wr(DIB3000MB_REG_RESTART, DIB3000MB_RESTART_CTRL); 358 wr(DIB3000MB_REG_RESTART, DIB3000MB_RESTART_OFF); 359 } 360 361 return 0; 362} 363 364static int dib3000mb_fe_init(struct dvb_frontend* fe, int mobile_mode) 365{ 366 struct dib3000_state* state = fe->demodulator_priv; 367 368 deb_info("dib3000mb is getting up.\n"); 369 wr(DIB3000MB_REG_POWER_CONTROL, DIB3000MB_POWER_UP); 370 371 wr(DIB3000MB_REG_RESTART, DIB3000MB_RESTART_AGC); 372 373 wr(DIB3000MB_REG_RESET_DEVICE, DIB3000MB_RESET_DEVICE); 374 wr(DIB3000MB_REG_RESET_DEVICE, DIB3000MB_RESET_DEVICE_RST); 375 376 wr(DIB3000MB_REG_CLOCK, DIB3000MB_CLOCK_DEFAULT); 377 378 wr(DIB3000MB_REG_ELECT_OUT_MODE, DIB3000MB_ELECT_OUT_MODE_ON); 379 380 wr(DIB3000MB_REG_DDS_FREQ_MSB, DIB3000MB_DDS_FREQ_MSB); 381 wr(DIB3000MB_REG_DDS_FREQ_LSB, DIB3000MB_DDS_FREQ_LSB); 382 383 wr_foreach(dib3000mb_reg_timing_freq, dib3000mb_timing_freq[2]); 384 385 wr_foreach(dib3000mb_reg_impulse_noise, 386 dib3000mb_impulse_noise_values[DIB3000MB_IMPNOISE_OFF]); 387 388 wr_foreach(dib3000mb_reg_agc_gain, dib3000mb_default_agc_gain); 389 390 wr(DIB3000MB_REG_PHASE_NOISE, DIB3000MB_PHASE_NOISE_DEFAULT); 391 392 wr_foreach(dib3000mb_reg_phase_noise, dib3000mb_default_noise_phase); 393 394 wr_foreach(dib3000mb_reg_lock_duration, dib3000mb_default_lock_duration); 395 396 wr_foreach(dib3000mb_reg_agc_bandwidth, dib3000mb_agc_bandwidth_low); 397 398 wr(DIB3000MB_REG_LOCK0_MASK, DIB3000MB_LOCK0_DEFAULT); 399 wr(DIB3000MB_REG_LOCK1_MASK, DIB3000MB_LOCK1_SEARCH_4); 400 wr(DIB3000MB_REG_LOCK2_MASK, DIB3000MB_LOCK2_DEFAULT); 401 wr(DIB3000MB_REG_SEQ, dib3000_seq[1][1][1]); 402 403 wr_foreach(dib3000mb_reg_bandwidth, dib3000mb_bandwidth_8mhz); 404 405 wr(DIB3000MB_REG_UNK_68, DIB3000MB_UNK_68); 406 wr(DIB3000MB_REG_UNK_69, DIB3000MB_UNK_69); 407 wr(DIB3000MB_REG_UNK_71, DIB3000MB_UNK_71); 408 wr(DIB3000MB_REG_UNK_77, DIB3000MB_UNK_77); 409 wr(DIB3000MB_REG_UNK_78, DIB3000MB_UNK_78); 410 wr(DIB3000MB_REG_ISI, DIB3000MB_ISI_INHIBIT); 411 wr(DIB3000MB_REG_UNK_92, DIB3000MB_UNK_92); 412 wr(DIB3000MB_REG_UNK_96, DIB3000MB_UNK_96); 413 wr(DIB3000MB_REG_UNK_97, DIB3000MB_UNK_97); 414 wr(DIB3000MB_REG_UNK_106, DIB3000MB_UNK_106); 415 wr(DIB3000MB_REG_UNK_107, DIB3000MB_UNK_107); 416 wr(DIB3000MB_REG_UNK_108, DIB3000MB_UNK_108); 417 wr(DIB3000MB_REG_UNK_122, DIB3000MB_UNK_122); 418 wr(DIB3000MB_REG_MOBILE_MODE_QAM, DIB3000MB_MOBILE_MODE_QAM_OFF); 419 wr(DIB3000MB_REG_BERLEN, DIB3000MB_BERLEN_DEFAULT); 420 421 wr_foreach(dib3000mb_reg_filter_coeffs, dib3000mb_filter_coeffs); 422 423 wr(DIB3000MB_REG_MOBILE_ALGO, DIB3000MB_MOBILE_ALGO_ON); 424 wr(DIB3000MB_REG_MULTI_DEMOD_MSB, DIB3000MB_MULTI_DEMOD_MSB); 425 wr(DIB3000MB_REG_MULTI_DEMOD_LSB, DIB3000MB_MULTI_DEMOD_LSB); 426 427 wr(DIB3000MB_REG_OUTPUT_MODE, DIB3000MB_OUTPUT_MODE_SLAVE); 428 429 wr(DIB3000MB_REG_FIFO_142, DIB3000MB_FIFO_142); 430 wr(DIB3000MB_REG_MPEG2_OUT_MODE, DIB3000MB_MPEG2_OUT_MODE_188); 431 wr(DIB3000MB_REG_PID_PARSE, DIB3000MB_PID_PARSE_ACTIVATE); 432 wr(DIB3000MB_REG_FIFO, DIB3000MB_FIFO_INHIBIT); 433 wr(DIB3000MB_REG_FIFO_146, DIB3000MB_FIFO_146); 434 wr(DIB3000MB_REG_FIFO_147, DIB3000MB_FIFO_147); 435 436 wr(DIB3000MB_REG_DATA_IN_DIVERSITY, DIB3000MB_DATA_DIVERSITY_IN_OFF); 437 438 return 0; 439} 440 441static int dib3000mb_get_frontend(struct dvb_frontend* fe, 442 struct dtv_frontend_properties *c) 443{ 444 struct dib3000_state* state = fe->demodulator_priv; 445 enum fe_code_rate *cr; 446 u16 tps_val; 447 int inv_test1,inv_test2; 448 u32 dds_val, threshold = 0x800000; 449 450 if (!rd(DIB3000MB_REG_TPS_LOCK)) 451 return 0; 452 453 dds_val = ((rd(DIB3000MB_REG_DDS_VALUE_MSB) & 0xff) << 16) + rd(DIB3000MB_REG_DDS_VALUE_LSB); 454 deb_getf("DDS_VAL: %x %x %x\n", dds_val, rd(DIB3000MB_REG_DDS_VALUE_MSB), rd(DIB3000MB_REG_DDS_VALUE_LSB)); 455 if (dds_val < threshold) 456 inv_test1 = 0; 457 else if (dds_val == threshold) 458 inv_test1 = 1; 459 else 460 inv_test1 = 2; 461 462 dds_val = ((rd(DIB3000MB_REG_DDS_FREQ_MSB) & 0xff) << 16) + rd(DIB3000MB_REG_DDS_FREQ_LSB); 463 deb_getf("DDS_FREQ: %x %x %x\n", dds_val, rd(DIB3000MB_REG_DDS_FREQ_MSB), rd(DIB3000MB_REG_DDS_FREQ_LSB)); 464 if (dds_val < threshold) 465 inv_test2 = 0; 466 else if (dds_val == threshold) 467 inv_test2 = 1; 468 else 469 inv_test2 = 2; 470 471 c->inversion = 472 ((inv_test2 == 2) && (inv_test1==1 || inv_test1==0)) || 473 ((inv_test2 == 0) && (inv_test1==1 || inv_test1==2)) ? 474 INVERSION_ON : INVERSION_OFF; 475 476 deb_getf("inversion %d %d, %d\n", inv_test2, inv_test1, c->inversion); 477 478 switch ((tps_val = rd(DIB3000MB_REG_TPS_QAM))) { 479 case DIB3000_CONSTELLATION_QPSK: 480 deb_getf("QPSK\n"); 481 c->modulation = QPSK; 482 break; 483 case DIB3000_CONSTELLATION_16QAM: 484 deb_getf("QAM16\n"); 485 c->modulation = QAM_16; 486 break; 487 case DIB3000_CONSTELLATION_64QAM: 488 deb_getf("QAM64\n"); 489 c->modulation = QAM_64; 490 break; 491 default: 492 pr_err("Unexpected constellation returned by TPS (%d)\n", tps_val); 493 break; 494 } 495 deb_getf("TPS: %d\n", tps_val); 496 497 if (rd(DIB3000MB_REG_TPS_HRCH)) { 498 deb_getf("HRCH ON\n"); 499 cr = &c->code_rate_LP; 500 c->code_rate_HP = FEC_NONE; 501 switch ((tps_val = rd(DIB3000MB_REG_TPS_VIT_ALPHA))) { 502 case DIB3000_ALPHA_0: 503 deb_getf("HIERARCHY_NONE\n"); 504 c->hierarchy = HIERARCHY_NONE; 505 break; 506 case DIB3000_ALPHA_1: 507 deb_getf("HIERARCHY_1\n"); 508 c->hierarchy = HIERARCHY_1; 509 break; 510 case DIB3000_ALPHA_2: 511 deb_getf("HIERARCHY_2\n"); 512 c->hierarchy = HIERARCHY_2; 513 break; 514 case DIB3000_ALPHA_4: 515 deb_getf("HIERARCHY_4\n"); 516 c->hierarchy = HIERARCHY_4; 517 break; 518 default: 519 pr_err("Unexpected ALPHA value returned by TPS (%d)\n", tps_val); 520 break; 521 } 522 deb_getf("TPS: %d\n", tps_val); 523 524 tps_val = rd(DIB3000MB_REG_TPS_CODE_RATE_LP); 525 } else { 526 deb_getf("HRCH OFF\n"); 527 cr = &c->code_rate_HP; 528 c->code_rate_LP = FEC_NONE; 529 c->hierarchy = HIERARCHY_NONE; 530 531 tps_val = rd(DIB3000MB_REG_TPS_CODE_RATE_HP); 532 } 533 534 switch (tps_val) { 535 case DIB3000_FEC_1_2: 536 deb_getf("FEC_1_2\n"); 537 *cr = FEC_1_2; 538 break; 539 case DIB3000_FEC_2_3: 540 deb_getf("FEC_2_3\n"); 541 *cr = FEC_2_3; 542 break; 543 case DIB3000_FEC_3_4: 544 deb_getf("FEC_3_4\n"); 545 *cr = FEC_3_4; 546 break; 547 case DIB3000_FEC_5_6: 548 deb_getf("FEC_5_6\n"); 549 *cr = FEC_4_5; 550 break; 551 case DIB3000_FEC_7_8: 552 deb_getf("FEC_7_8\n"); 553 *cr = FEC_7_8; 554 break; 555 default: 556 pr_err("Unexpected FEC returned by TPS (%d)\n", tps_val); 557 break; 558 } 559 deb_getf("TPS: %d\n",tps_val); 560 561 switch ((tps_val = rd(DIB3000MB_REG_TPS_GUARD_TIME))) { 562 case DIB3000_GUARD_TIME_1_32: 563 deb_getf("GUARD_INTERVAL_1_32\n"); 564 c->guard_interval = GUARD_INTERVAL_1_32; 565 break; 566 case DIB3000_GUARD_TIME_1_16: 567 deb_getf("GUARD_INTERVAL_1_16\n"); 568 c->guard_interval = GUARD_INTERVAL_1_16; 569 break; 570 case DIB3000_GUARD_TIME_1_8: 571 deb_getf("GUARD_INTERVAL_1_8\n"); 572 c->guard_interval = GUARD_INTERVAL_1_8; 573 break; 574 case DIB3000_GUARD_TIME_1_4: 575 deb_getf("GUARD_INTERVAL_1_4\n"); 576 c->guard_interval = GUARD_INTERVAL_1_4; 577 break; 578 default: 579 pr_err("Unexpected Guard Time returned by TPS (%d)\n", tps_val); 580 break; 581 } 582 deb_getf("TPS: %d\n", tps_val); 583 584 switch ((tps_val = rd(DIB3000MB_REG_TPS_FFT))) { 585 case DIB3000_TRANSMISSION_MODE_2K: 586 deb_getf("TRANSMISSION_MODE_2K\n"); 587 c->transmission_mode = TRANSMISSION_MODE_2K; 588 break; 589 case DIB3000_TRANSMISSION_MODE_8K: 590 deb_getf("TRANSMISSION_MODE_8K\n"); 591 c->transmission_mode = TRANSMISSION_MODE_8K; 592 break; 593 default: 594 pr_err("unexpected transmission mode return by TPS (%d)\n", tps_val); 595 break; 596 } 597 deb_getf("TPS: %d\n", tps_val); 598 599 return 0; 600} 601 602static int dib3000mb_read_status(struct dvb_frontend *fe, 603 enum fe_status *stat) 604{ 605 struct dib3000_state* state = fe->demodulator_priv; 606 607 *stat = 0; 608 609 if (rd(DIB3000MB_REG_AGC_LOCK)) 610 *stat |= FE_HAS_SIGNAL; 611 if (rd(DIB3000MB_REG_CARRIER_LOCK)) 612 *stat |= FE_HAS_CARRIER; 613 if (rd(DIB3000MB_REG_VIT_LCK)) 614 *stat |= FE_HAS_VITERBI; 615 if (rd(DIB3000MB_REG_TS_SYNC_LOCK)) 616 *stat |= (FE_HAS_SYNC | FE_HAS_LOCK); 617 618 deb_getf("actual status is %2x\n",*stat); 619 620 deb_getf("autoval: tps: %d, qam: %d, hrch: %d, alpha: %d, hp: %d, lp: %d, guard: %d, fft: %d cell: %d\n", 621 rd(DIB3000MB_REG_TPS_LOCK), 622 rd(DIB3000MB_REG_TPS_QAM), 623 rd(DIB3000MB_REG_TPS_HRCH), 624 rd(DIB3000MB_REG_TPS_VIT_ALPHA), 625 rd(DIB3000MB_REG_TPS_CODE_RATE_HP), 626 rd(DIB3000MB_REG_TPS_CODE_RATE_LP), 627 rd(DIB3000MB_REG_TPS_GUARD_TIME), 628 rd(DIB3000MB_REG_TPS_FFT), 629 rd(DIB3000MB_REG_TPS_CELL_ID)); 630 631 //*stat = FE_HAS_SIGNAL | FE_HAS_CARRIER | FE_HAS_VITERBI | FE_HAS_SYNC | FE_HAS_LOCK; 632 return 0; 633} 634 635static int dib3000mb_read_ber(struct dvb_frontend* fe, u32 *ber) 636{ 637 struct dib3000_state* state = fe->demodulator_priv; 638 639 *ber = ((rd(DIB3000MB_REG_BER_MSB) << 16) | rd(DIB3000MB_REG_BER_LSB)); 640 return 0; 641} 642 643/* see dib3000-watch dvb-apps for exact calcuations of signal_strength and snr */ 644static int dib3000mb_read_signal_strength(struct dvb_frontend* fe, u16 *strength) 645{ 646 struct dib3000_state* state = fe->demodulator_priv; 647 648 *strength = rd(DIB3000MB_REG_SIGNAL_POWER) * 0xffff / 0x170; 649 return 0; 650} 651 652static int dib3000mb_read_snr(struct dvb_frontend* fe, u16 *snr) 653{ 654 struct dib3000_state* state = fe->demodulator_priv; 655 short sigpow = rd(DIB3000MB_REG_SIGNAL_POWER); 656 int icipow = ((rd(DIB3000MB_REG_NOISE_POWER_MSB) & 0xff) << 16) | 657 rd(DIB3000MB_REG_NOISE_POWER_LSB); 658 *snr = (sigpow << 8) / ((icipow > 0) ? icipow : 1); 659 return 0; 660} 661 662static int dib3000mb_read_unc_blocks(struct dvb_frontend* fe, u32 *unc) 663{ 664 struct dib3000_state* state = fe->demodulator_priv; 665 666 *unc = rd(DIB3000MB_REG_PACKET_ERROR_RATE); 667 return 0; 668} 669 670static int dib3000mb_sleep(struct dvb_frontend* fe) 671{ 672 struct dib3000_state* state = fe->demodulator_priv; 673 deb_info("dib3000mb is going to bed.\n"); 674 wr(DIB3000MB_REG_POWER_CONTROL, DIB3000MB_POWER_DOWN); 675 return 0; 676} 677 678static int dib3000mb_fe_get_tune_settings(struct dvb_frontend* fe, struct dvb_frontend_tune_settings *tune) 679{ 680 tune->min_delay_ms = 800; 681 return 0; 682} 683 684static int dib3000mb_fe_init_nonmobile(struct dvb_frontend* fe) 685{ 686 return dib3000mb_fe_init(fe, 0); 687} 688 689static int dib3000mb_set_frontend_and_tuner(struct dvb_frontend *fe) 690{ 691 return dib3000mb_set_frontend(fe, 1); 692} 693 694static void dib3000mb_release(struct dvb_frontend* fe) 695{ 696 struct dib3000_state *state = fe->demodulator_priv; 697 kfree(state); 698} 699 700/* pid filter and transfer stuff */ 701static int dib3000mb_pid_control(struct dvb_frontend *fe,int index, int pid,int onoff) 702{ 703 struct dib3000_state *state = fe->demodulator_priv; 704 pid = (onoff ? pid | DIB3000_ACTIVATE_PID_FILTERING : 0); 705 wr(index+DIB3000MB_REG_FIRST_PID,pid); 706 return 0; 707} 708 709static int dib3000mb_fifo_control(struct dvb_frontend *fe, int onoff) 710{ 711 struct dib3000_state *state = fe->demodulator_priv; 712 713 deb_xfer("%s fifo\n",onoff ? "enabling" : "disabling"); 714 if (onoff) { 715 wr(DIB3000MB_REG_FIFO, DIB3000MB_FIFO_ACTIVATE); 716 } else { 717 wr(DIB3000MB_REG_FIFO, DIB3000MB_FIFO_INHIBIT); 718 } 719 return 0; 720} 721 722static int dib3000mb_pid_parse(struct dvb_frontend *fe, int onoff) 723{ 724 struct dib3000_state *state = fe->demodulator_priv; 725 deb_xfer("%s pid parsing\n",onoff ? "enabling" : "disabling"); 726 wr(DIB3000MB_REG_PID_PARSE,onoff); 727 return 0; 728} 729 730static int dib3000mb_tuner_pass_ctrl(struct dvb_frontend *fe, int onoff, u8 pll_addr) 731{ 732 struct dib3000_state *state = fe->demodulator_priv; 733 if (onoff) { 734 wr(DIB3000MB_REG_TUNER, DIB3000_TUNER_WRITE_ENABLE(pll_addr)); 735 } else { 736 wr(DIB3000MB_REG_TUNER, DIB3000_TUNER_WRITE_DISABLE(pll_addr)); 737 } 738 return 0; 739} 740 741static const struct dvb_frontend_ops dib3000mb_ops; 742 743struct dvb_frontend* dib3000mb_attach(const struct dib3000_config* config, 744 struct i2c_adapter* i2c, struct dib_fe_xfer_ops *xfer_ops) 745{ 746 struct dib3000_state* state = NULL; 747 748 /* allocate memory for the internal state */ 749 state = kzalloc(sizeof(struct dib3000_state), GFP_KERNEL); 750 if (state == NULL) 751 goto error; 752 753 /* setup the state */ 754 state->i2c = i2c; 755 memcpy(&state->config,config,sizeof(struct dib3000_config)); 756 757 /* check for the correct demod */ 758 if (rd(DIB3000_REG_MANUFACTOR_ID) != DIB3000_I2C_ID_DIBCOM) 759 goto error; 760 761 if (rd(DIB3000_REG_DEVICE_ID) != DIB3000MB_DEVICE_ID) 762 goto error; 763 764 /* create dvb_frontend */ 765 memcpy(&state->frontend.ops, &dib3000mb_ops, sizeof(struct dvb_frontend_ops)); 766 state->frontend.demodulator_priv = state; 767 768 /* set the xfer operations */ 769 xfer_ops->pid_parse = dib3000mb_pid_parse; 770 xfer_ops->fifo_ctrl = dib3000mb_fifo_control; 771 xfer_ops->pid_ctrl = dib3000mb_pid_control; 772 xfer_ops->tuner_pass_ctrl = dib3000mb_tuner_pass_ctrl; 773 774 return &state->frontend; 775 776error: 777 kfree(state); 778 return NULL; 779} 780 781static const struct dvb_frontend_ops dib3000mb_ops = { 782 .delsys = { SYS_DVBT }, 783 .info = { 784 .name = "DiBcom 3000M-B DVB-T", 785 .frequency_min_hz = 44250 * kHz, 786 .frequency_max_hz = 867250 * kHz, 787 .frequency_stepsize_hz = 62500, 788 .caps = FE_CAN_INVERSION_AUTO | 789 FE_CAN_FEC_1_2 | FE_CAN_FEC_2_3 | FE_CAN_FEC_3_4 | 790 FE_CAN_FEC_5_6 | FE_CAN_FEC_7_8 | FE_CAN_FEC_AUTO | 791 FE_CAN_QPSK | FE_CAN_QAM_16 | FE_CAN_QAM_64 | FE_CAN_QAM_AUTO | 792 FE_CAN_TRANSMISSION_MODE_AUTO | 793 FE_CAN_GUARD_INTERVAL_AUTO | 794 FE_CAN_RECOVER | 795 FE_CAN_HIERARCHY_AUTO, 796 }, 797 798 .release = dib3000mb_release, 799 800 .init = dib3000mb_fe_init_nonmobile, 801 .sleep = dib3000mb_sleep, 802 803 .set_frontend = dib3000mb_set_frontend_and_tuner, 804 .get_frontend = dib3000mb_get_frontend, 805 .get_tune_settings = dib3000mb_fe_get_tune_settings, 806 807 .read_status = dib3000mb_read_status, 808 .read_ber = dib3000mb_read_ber, 809 .read_signal_strength = dib3000mb_read_signal_strength, 810 .read_snr = dib3000mb_read_snr, 811 .read_ucblocks = dib3000mb_read_unc_blocks, 812}; 813 814MODULE_AUTHOR(DRIVER_AUTHOR); 815MODULE_DESCRIPTION(DRIVER_DESC); 816MODULE_LICENSE("GPL"); 817 818EXPORT_SYMBOL(dib3000mb_attach);