1 /* 2 * Support for LG2160 - ATSC/MH 3 * 4 * Copyright (C) 2010 Michael Krufky <mkrufky@linuxtv.org> 5 * 6 * This program is free software; you can redistribute it and/or modify 7 * it under the terms of the GNU General Public License as published by 8 * the Free Software Foundation; either version 2 of the License, or 9 * (at your option) any later version. 10 * 11 * This program is distributed in the hope that it will be useful, 12 * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 * GNU General Public License for more details. 15 * 16 */ 17 18 #include <linux/jiffies.h> 19 #include <linux/dvb/frontend.h> 20 #include "lg2160.h" 21 22 static int debug; 23 module_param(debug, int, 0644); 24 MODULE_PARM_DESC(debug, "set debug level (info=1, reg=2 (or-able))"); 25 26 #define DBG_INFO 1 27 #define DBG_REG 2 28 29 #define lg_printk(kern, fmt, arg...) \ 30 printk(kern "%s: " fmt, __func__, ##arg) 31 32 #define lg_info(fmt, arg...) printk(KERN_INFO "lg2160: " fmt, ##arg) 33 #define lg_warn(fmt, arg...) lg_printk(KERN_WARNING, fmt, ##arg) 34 #define lg_err(fmt, arg...) lg_printk(KERN_ERR, fmt, ##arg) 35 #define lg_dbg(fmt, arg...) if (debug & DBG_INFO) \ 36 lg_printk(KERN_DEBUG, fmt, ##arg) 37 #define lg_reg(fmt, arg...) if (debug & DBG_REG) \ 38 lg_printk(KERN_DEBUG, fmt, ##arg) 39 40 #define lg_fail(ret) \ 41 ({ \ 42 int __ret; \ 43 __ret = (ret < 0); \ 44 if (__ret) \ 45 lg_err("error %d on line %d\n", ret, __LINE__); \ 46 __ret; \ 47 }) 48 49 struct lg216x_state { 50 struct i2c_adapter *i2c_adap; 51 const struct lg2160_config *cfg; 52 53 struct dvb_frontend frontend; 54 55 u32 current_frequency; 56 u8 parade_id; 57 u8 fic_ver; 58 unsigned int last_reset; 59 }; 60 61 /* ------------------------------------------------------------------------ */ 62 63 static int lg216x_write_reg(struct lg216x_state *state, u16 reg, u8 val) 64 { 65 int ret; 66 u8 buf[] = { reg >> 8, reg & 0xff, val }; 67 struct i2c_msg msg = { 68 .addr = state->cfg->i2c_addr, .flags = 0, 69 .buf = buf, .len = 3, 70 }; 71 72 lg_reg("reg: 0x%04x, val: 0x%02x\n", reg, val); 73 74 ret = i2c_transfer(state->i2c_adap, &msg, 1); 75 76 if (ret != 1) { 77 lg_err("error (addr %02x %02x <- %02x, err = %i)\n", 78 msg.buf[0], msg.buf[1], msg.buf[2], ret); 79 if (ret < 0) 80 return ret; 81 else 82 return -EREMOTEIO; 83 } 84 return 0; 85 } 86 87 static int lg216x_read_reg(struct lg216x_state *state, u16 reg, u8 *val) 88 { 89 int ret; 90 u8 reg_buf[] = { reg >> 8, reg & 0xff }; 91 struct i2c_msg msg[] = { 92 { .addr = state->cfg->i2c_addr, 93 .flags = 0, .buf = reg_buf, .len = 2 }, 94 { .addr = state->cfg->i2c_addr, 95 .flags = I2C_M_RD, .buf = val, .len = 1 }, 96 }; 97 98 lg_reg("reg: 0x%04x\n", reg); 99 100 ret = i2c_transfer(state->i2c_adap, msg, 2); 101 102 if (ret != 2) { 103 lg_err("error (addr %02x reg %04x error (ret == %i)\n", 104 state->cfg->i2c_addr, reg, ret); 105 if (ret < 0) 106 return ret; 107 else 108 return -EREMOTEIO; 109 } 110 return 0; 111 } 112 113 struct lg216x_reg { 114 u16 reg; 115 u8 val; 116 }; 117 118 static int lg216x_write_regs(struct lg216x_state *state, 119 struct lg216x_reg *regs, int len) 120 { 121 int i, ret; 122 123 lg_reg("writing %d registers...\n", len); 124 125 for (i = 0; i < len; i++) { 126 ret = lg216x_write_reg(state, regs[i].reg, regs[i].val); 127 if (lg_fail(ret)) 128 return ret; 129 } 130 return 0; 131 } 132 133 static int lg216x_set_reg_bit(struct lg216x_state *state, 134 u16 reg, int bit, int onoff) 135 { 136 u8 val; 137 int ret; 138 139 lg_reg("reg: 0x%04x, bit: %d, level: %d\n", reg, bit, onoff); 140 141 ret = lg216x_read_reg(state, reg, &val); 142 if (lg_fail(ret)) 143 goto fail; 144 145 val &= ~(1 << bit); 146 val |= (onoff & 1) << bit; 147 148 ret = lg216x_write_reg(state, reg, val); 149 lg_fail(ret); 150 fail: 151 return ret; 152 } 153 154 /* ------------------------------------------------------------------------ */ 155 156 static int lg216x_i2c_gate_ctrl(struct dvb_frontend *fe, int enable) 157 { 158 struct lg216x_state *state = fe->demodulator_priv; 159 int ret; 160 161 if (state->cfg->deny_i2c_rptr) 162 return 0; 163 164 lg_dbg("(%d)\n", enable); 165 166 ret = lg216x_set_reg_bit(state, 0x0000, 0, enable ? 0 : 1); 167 168 msleep(1); 169 170 return ret; 171 } 172 173 static int lg216x_soft_reset(struct lg216x_state *state) 174 { 175 int ret; 176 177 lg_dbg("\n"); 178 179 ret = lg216x_write_reg(state, 0x0002, 0x00); 180 if (lg_fail(ret)) 181 goto fail; 182 183 msleep(20); 184 ret = lg216x_write_reg(state, 0x0002, 0x01); 185 if (lg_fail(ret)) 186 goto fail; 187 188 state->last_reset = jiffies_to_msecs(jiffies); 189 fail: 190 return ret; 191 } 192 193 static int lg216x_initialize(struct lg216x_state *state) 194 { 195 int ret; 196 197 static struct lg216x_reg lg2160_init[] = { 198 #if 0 199 { .reg = 0x0015, .val = 0xe6 }, 200 #else 201 { .reg = 0x0015, .val = 0xf7 }, 202 { .reg = 0x001b, .val = 0x52 }, 203 { .reg = 0x0208, .val = 0x00 }, 204 { .reg = 0x0209, .val = 0x82 }, 205 { .reg = 0x0210, .val = 0xf9 }, 206 { .reg = 0x020a, .val = 0x00 }, 207 { .reg = 0x020b, .val = 0x82 }, 208 { .reg = 0x020d, .val = 0x28 }, 209 { .reg = 0x020f, .val = 0x14 }, 210 #endif 211 }; 212 213 static struct lg216x_reg lg2161_init[] = { 214 { .reg = 0x0000, .val = 0x41 }, 215 { .reg = 0x0001, .val = 0xfb }, 216 { .reg = 0x0216, .val = 0x00 }, 217 { .reg = 0x0219, .val = 0x00 }, 218 { .reg = 0x021b, .val = 0x55 }, 219 { .reg = 0x0606, .val = 0x0a }, 220 }; 221 222 switch (state->cfg->lg_chip) { 223 case LG2160: 224 ret = lg216x_write_regs(state, 225 lg2160_init, ARRAY_SIZE(lg2160_init)); 226 break; 227 case LG2161: 228 ret = lg216x_write_regs(state, 229 lg2161_init, ARRAY_SIZE(lg2161_init)); 230 break; 231 default: 232 ret = -EINVAL; 233 break; 234 } 235 if (lg_fail(ret)) 236 goto fail; 237 238 ret = lg216x_soft_reset(state); 239 lg_fail(ret); 240 fail: 241 return ret; 242 } 243 244 /* ------------------------------------------------------------------------ */ 245 246 static int lg216x_set_if(struct lg216x_state *state) 247 { 248 u8 val; 249 int ret; 250 251 lg_dbg("%d KHz\n", state->cfg->if_khz); 252 253 ret = lg216x_read_reg(state, 0x0132, &val); 254 if (lg_fail(ret)) 255 goto fail; 256 257 val &= 0xfb; 258 val |= (0 == state->cfg->if_khz) ? 0x04 : 0x00; 259 260 ret = lg216x_write_reg(state, 0x0132, val); 261 lg_fail(ret); 262 263 /* if NOT zero IF, 6 MHz is the default */ 264 fail: 265 return ret; 266 } 267 268 /* ------------------------------------------------------------------------ */ 269 270 static int lg2160_agc_fix(struct lg216x_state *state, 271 int if_agc_fix, int rf_agc_fix) 272 { 273 u8 val; 274 int ret; 275 276 ret = lg216x_read_reg(state, 0x0100, &val); 277 if (lg_fail(ret)) 278 goto fail; 279 280 val &= 0xf3; 281 val |= (if_agc_fix) ? 0x08 : 0x00; 282 val |= (rf_agc_fix) ? 0x04 : 0x00; 283 284 ret = lg216x_write_reg(state, 0x0100, val); 285 lg_fail(ret); 286 fail: 287 return ret; 288 } 289 290 #if 0 291 static int lg2160_agc_freeze(struct lg216x_state *state, 292 int if_agc_freeze, int rf_agc_freeze) 293 { 294 u8 val; 295 int ret; 296 297 ret = lg216x_read_reg(state, 0x0100, &val); 298 if (lg_fail(ret)) 299 goto fail; 300 301 val &= 0xcf; 302 val |= (if_agc_freeze) ? 0x20 : 0x00; 303 val |= (rf_agc_freeze) ? 0x10 : 0x00; 304 305 ret = lg216x_write_reg(state, 0x0100, val); 306 lg_fail(ret); 307 fail: 308 return ret; 309 } 310 #endif 311 312 static int lg2160_agc_polarity(struct lg216x_state *state, 313 int if_agc_polarity, int rf_agc_polarity) 314 { 315 u8 val; 316 int ret; 317 318 ret = lg216x_read_reg(state, 0x0100, &val); 319 if (lg_fail(ret)) 320 goto fail; 321 322 val &= 0xfc; 323 val |= (if_agc_polarity) ? 0x02 : 0x00; 324 val |= (rf_agc_polarity) ? 0x01 : 0x00; 325 326 ret = lg216x_write_reg(state, 0x0100, val); 327 lg_fail(ret); 328 fail: 329 return ret; 330 } 331 332 static int lg2160_tuner_pwr_save_polarity(struct lg216x_state *state, 333 int polarity) 334 { 335 u8 val; 336 int ret; 337 338 ret = lg216x_read_reg(state, 0x0008, &val); 339 if (lg_fail(ret)) 340 goto fail; 341 342 val &= 0xfe; 343 val |= (polarity) ? 0x01 : 0x00; 344 345 ret = lg216x_write_reg(state, 0x0008, val); 346 lg_fail(ret); 347 fail: 348 return ret; 349 } 350 351 static int lg2160_spectrum_polarity(struct lg216x_state *state, 352 int inverted) 353 { 354 u8 val; 355 int ret; 356 357 ret = lg216x_read_reg(state, 0x0132, &val); 358 if (lg_fail(ret)) 359 goto fail; 360 361 val &= 0xfd; 362 val |= (inverted) ? 0x02 : 0x00; 363 364 ret = lg216x_write_reg(state, 0x0132, val); 365 lg_fail(ret); 366 fail: 367 return lg216x_soft_reset(state); 368 } 369 370 static int lg2160_tuner_pwr_save(struct lg216x_state *state, int onoff) 371 { 372 u8 val; 373 int ret; 374 375 ret = lg216x_read_reg(state, 0x0007, &val); 376 if (lg_fail(ret)) 377 goto fail; 378 379 val &= 0xbf; 380 val |= (onoff) ? 0x40 : 0x00; 381 382 ret = lg216x_write_reg(state, 0x0007, val); 383 lg_fail(ret); 384 fail: 385 return ret; 386 } 387 388 static int lg216x_set_parade(struct lg216x_state *state, int id) 389 { 390 int ret; 391 392 ret = lg216x_write_reg(state, 0x013e, id & 0x7f); 393 if (lg_fail(ret)) 394 goto fail; 395 396 state->parade_id = id & 0x7f; 397 fail: 398 return ret; 399 } 400 401 static int lg216x_set_ensemble(struct lg216x_state *state, int id) 402 { 403 int ret; 404 u16 reg; 405 u8 val; 406 407 switch (state->cfg->lg_chip) { 408 case LG2160: 409 reg = 0x0400; 410 break; 411 case LG2161: 412 default: 413 reg = 0x0500; 414 break; 415 } 416 417 ret = lg216x_read_reg(state, reg, &val); 418 if (lg_fail(ret)) 419 goto fail; 420 421 val &= 0xfe; 422 val |= (id) ? 0x01 : 0x00; 423 424 ret = lg216x_write_reg(state, reg, val); 425 lg_fail(ret); 426 fail: 427 return ret; 428 } 429 430 static int lg2160_set_spi_clock(struct lg216x_state *state) 431 { 432 u8 val; 433 int ret; 434 435 ret = lg216x_read_reg(state, 0x0014, &val); 436 if (lg_fail(ret)) 437 goto fail; 438 439 val &= 0xf3; 440 val |= (state->cfg->spi_clock << 2); 441 442 ret = lg216x_write_reg(state, 0x0014, val); 443 lg_fail(ret); 444 fail: 445 return ret; 446 } 447 448 static int lg2161_set_output_interface(struct lg216x_state *state) 449 { 450 u8 val; 451 int ret; 452 453 ret = lg216x_read_reg(state, 0x0014, &val); 454 if (lg_fail(ret)) 455 goto fail; 456 457 val &= ~0x07; 458 val |= state->cfg->output_if; /* FIXME: needs sanity check */ 459 460 ret = lg216x_write_reg(state, 0x0014, val); 461 lg_fail(ret); 462 fail: 463 return ret; 464 } 465 466 static int lg216x_enable_fic(struct lg216x_state *state, int onoff) 467 { 468 int ret; 469 470 ret = lg216x_write_reg(state, 0x0017, 0x23); 471 if (lg_fail(ret)) 472 goto fail; 473 474 ret = lg216x_write_reg(state, 0x0016, 0xfc); 475 if (lg_fail(ret)) 476 goto fail; 477 478 switch (state->cfg->lg_chip) { 479 case LG2160: 480 ret = lg216x_write_reg(state, 0x0016, 481 0xfc | ((onoff) ? 0x02 : 0x00)); 482 break; 483 case LG2161: 484 ret = lg216x_write_reg(state, 0x0016, (onoff) ? 0x10 : 0x00); 485 break; 486 } 487 if (lg_fail(ret)) 488 goto fail; 489 490 ret = lg216x_initialize(state); 491 if (lg_fail(ret)) 492 goto fail; 493 494 if (onoff) { 495 ret = lg216x_write_reg(state, 0x0017, 0x03); 496 lg_fail(ret); 497 } 498 fail: 499 return ret; 500 } 501 502 /* ------------------------------------------------------------------------ */ 503 504 static int lg216x_get_fic_version(struct lg216x_state *state, u8 *ficver) 505 { 506 u8 val; 507 int ret; 508 509 *ficver = 0xff; /* invalid value */ 510 511 ret = lg216x_read_reg(state, 0x0128, &val); 512 if (lg_fail(ret)) 513 goto fail; 514 515 *ficver = (val >> 3) & 0x1f; 516 fail: 517 return ret; 518 } 519 520 #if 0 521 static int lg2160_get_parade_id(struct lg216x_state *state, u8 *id) 522 { 523 u8 val; 524 int ret; 525 526 *id = 0xff; /* invalid value */ 527 528 ret = lg216x_read_reg(state, 0x0123, &val); 529 if (lg_fail(ret)) 530 goto fail; 531 532 *id = val & 0x7f; 533 fail: 534 return ret; 535 } 536 #endif 537 538 static int lg216x_get_nog(struct lg216x_state *state, u8 *nog) 539 { 540 u8 val; 541 int ret; 542 543 *nog = 0xff; /* invalid value */ 544 545 ret = lg216x_read_reg(state, 0x0124, &val); 546 if (lg_fail(ret)) 547 goto fail; 548 549 *nog = ((val >> 4) & 0x07) + 1; 550 fail: 551 return ret; 552 } 553 554 static int lg216x_get_tnog(struct lg216x_state *state, u8 *tnog) 555 { 556 u8 val; 557 int ret; 558 559 *tnog = 0xff; /* invalid value */ 560 561 ret = lg216x_read_reg(state, 0x0125, &val); 562 if (lg_fail(ret)) 563 goto fail; 564 565 *tnog = val & 0x1f; 566 fail: 567 return ret; 568 } 569 570 static int lg216x_get_sgn(struct lg216x_state *state, u8 *sgn) 571 { 572 u8 val; 573 int ret; 574 575 *sgn = 0xff; /* invalid value */ 576 577 ret = lg216x_read_reg(state, 0x0124, &val); 578 if (lg_fail(ret)) 579 goto fail; 580 581 *sgn = val & 0x0f; 582 fail: 583 return ret; 584 } 585 586 static int lg216x_get_prc(struct lg216x_state *state, u8 *prc) 587 { 588 u8 val; 589 int ret; 590 591 *prc = 0xff; /* invalid value */ 592 593 ret = lg216x_read_reg(state, 0x0125, &val); 594 if (lg_fail(ret)) 595 goto fail; 596 597 *prc = ((val >> 5) & 0x07) + 1; 598 fail: 599 return ret; 600 } 601 602 /* ------------------------------------------------------------------------ */ 603 604 static int lg216x_get_rs_frame_mode(struct lg216x_state *state, 605 enum atscmh_rs_frame_mode *rs_framemode) 606 { 607 u8 val; 608 int ret; 609 610 switch (state->cfg->lg_chip) { 611 case LG2160: 612 ret = lg216x_read_reg(state, 0x0410, &val); 613 break; 614 case LG2161: 615 ret = lg216x_read_reg(state, 0x0513, &val); 616 break; 617 default: 618 ret = -EINVAL; 619 } 620 if (lg_fail(ret)) 621 goto fail; 622 623 switch ((val >> 4) & 0x03) { 624 #if 1 625 default: 626 #endif 627 case 0x00: 628 *rs_framemode = ATSCMH_RSFRAME_PRI_ONLY; 629 break; 630 case 0x01: 631 *rs_framemode = ATSCMH_RSFRAME_PRI_SEC; 632 break; 633 #if 0 634 default: 635 *rs_framemode = ATSCMH_RSFRAME_RES; 636 break; 637 #endif 638 } 639 fail: 640 return ret; 641 } 642 643 static 644 int lg216x_get_rs_frame_ensemble(struct lg216x_state *state, 645 enum atscmh_rs_frame_ensemble *rs_frame_ens) 646 { 647 u8 val; 648 int ret; 649 650 switch (state->cfg->lg_chip) { 651 case LG2160: 652 ret = lg216x_read_reg(state, 0x0400, &val); 653 break; 654 case LG2161: 655 ret = lg216x_read_reg(state, 0x0500, &val); 656 break; 657 default: 658 ret = -EINVAL; 659 } 660 if (lg_fail(ret)) 661 goto fail; 662 663 val &= 0x01; 664 *rs_frame_ens = (enum atscmh_rs_frame_ensemble) val; 665 fail: 666 return ret; 667 } 668 669 static int lg216x_get_rs_code_mode(struct lg216x_state *state, 670 enum atscmh_rs_code_mode *rs_code_pri, 671 enum atscmh_rs_code_mode *rs_code_sec) 672 { 673 u8 val; 674 int ret; 675 676 switch (state->cfg->lg_chip) { 677 case LG2160: 678 ret = lg216x_read_reg(state, 0x0410, &val); 679 break; 680 case LG2161: 681 ret = lg216x_read_reg(state, 0x0513, &val); 682 break; 683 default: 684 ret = -EINVAL; 685 } 686 if (lg_fail(ret)) 687 goto fail; 688 689 *rs_code_pri = (enum atscmh_rs_code_mode) ((val >> 2) & 0x03); 690 *rs_code_sec = (enum atscmh_rs_code_mode) (val & 0x03); 691 fail: 692 return ret; 693 } 694 695 static int lg216x_get_sccc_block_mode(struct lg216x_state *state, 696 enum atscmh_sccc_block_mode *sccc_block) 697 { 698 u8 val; 699 int ret; 700 701 switch (state->cfg->lg_chip) { 702 case LG2160: 703 ret = lg216x_read_reg(state, 0x0315, &val); 704 break; 705 case LG2161: 706 ret = lg216x_read_reg(state, 0x0511, &val); 707 break; 708 default: 709 ret = -EINVAL; 710 } 711 if (lg_fail(ret)) 712 goto fail; 713 714 switch (val & 0x03) { 715 case 0x00: 716 *sccc_block = ATSCMH_SCCC_BLK_SEP; 717 break; 718 case 0x01: 719 *sccc_block = ATSCMH_SCCC_BLK_COMB; 720 break; 721 default: 722 *sccc_block = ATSCMH_SCCC_BLK_RES; 723 break; 724 } 725 fail: 726 return ret; 727 } 728 729 static int lg216x_get_sccc_code_mode(struct lg216x_state *state, 730 enum atscmh_sccc_code_mode *mode_a, 731 enum atscmh_sccc_code_mode *mode_b, 732 enum atscmh_sccc_code_mode *mode_c, 733 enum atscmh_sccc_code_mode *mode_d) 734 { 735 u8 val; 736 int ret; 737 738 switch (state->cfg->lg_chip) { 739 case LG2160: 740 ret = lg216x_read_reg(state, 0x0316, &val); 741 break; 742 case LG2161: 743 ret = lg216x_read_reg(state, 0x0512, &val); 744 break; 745 default: 746 ret = -EINVAL; 747 } 748 if (lg_fail(ret)) 749 goto fail; 750 751 switch ((val >> 6) & 0x03) { 752 case 0x00: 753 *mode_a = ATSCMH_SCCC_CODE_HLF; 754 break; 755 case 0x01: 756 *mode_a = ATSCMH_SCCC_CODE_QTR; 757 break; 758 default: 759 *mode_a = ATSCMH_SCCC_CODE_RES; 760 break; 761 } 762 763 switch ((val >> 4) & 0x03) { 764 case 0x00: 765 *mode_b = ATSCMH_SCCC_CODE_HLF; 766 break; 767 case 0x01: 768 *mode_b = ATSCMH_SCCC_CODE_QTR; 769 break; 770 default: 771 *mode_b = ATSCMH_SCCC_CODE_RES; 772 break; 773 } 774 775 switch ((val >> 2) & 0x03) { 776 case 0x00: 777 *mode_c = ATSCMH_SCCC_CODE_HLF; 778 break; 779 case 0x01: 780 *mode_c = ATSCMH_SCCC_CODE_QTR; 781 break; 782 default: 783 *mode_c = ATSCMH_SCCC_CODE_RES; 784 break; 785 } 786 787 switch (val & 0x03) { 788 case 0x00: 789 *mode_d = ATSCMH_SCCC_CODE_HLF; 790 break; 791 case 0x01: 792 *mode_d = ATSCMH_SCCC_CODE_QTR; 793 break; 794 default: 795 *mode_d = ATSCMH_SCCC_CODE_RES; 796 break; 797 } 798 fail: 799 return ret; 800 } 801 802 /* ------------------------------------------------------------------------ */ 803 804 #if 0 805 static int lg216x_read_fic_err_count(struct lg216x_state *state, u8 *err) 806 { 807 u8 fic_err; 808 int ret; 809 810 *err = 0; 811 812 switch (state->cfg->lg_chip) { 813 case LG2160: 814 ret = lg216x_read_reg(state, 0x0012, &fic_err); 815 break; 816 case LG2161: 817 ret = lg216x_read_reg(state, 0x001e, &fic_err); 818 break; 819 } 820 if (lg_fail(ret)) 821 goto fail; 822 823 *err = fic_err; 824 fail: 825 return ret; 826 } 827 828 static int lg2160_read_crc_err_count(struct lg216x_state *state, u16 *err) 829 { 830 u8 crc_err1, crc_err2; 831 int ret; 832 833 *err = 0; 834 835 ret = lg216x_read_reg(state, 0x0411, &crc_err1); 836 if (lg_fail(ret)) 837 goto fail; 838 839 ret = lg216x_read_reg(state, 0x0412, &crc_err2); 840 if (lg_fail(ret)) 841 goto fail; 842 843 *err = (u16)(((crc_err2 & 0x0f) << 8) | crc_err1); 844 fail: 845 return ret; 846 } 847 848 static int lg2161_read_crc_err_count(struct lg216x_state *state, u16 *err) 849 { 850 u8 crc_err; 851 int ret; 852 853 *err = 0; 854 855 ret = lg216x_read_reg(state, 0x0612, &crc_err); 856 if (lg_fail(ret)) 857 goto fail; 858 859 *err = (u16)crc_err; 860 fail: 861 return ret; 862 } 863 864 static int lg216x_read_crc_err_count(struct lg216x_state *state, u16 *err) 865 { 866 int ret; 867 switch (state->cfg->lg_chip) { 868 case LG2160: 869 ret = lg2160_read_crc_err_count(state, err); 870 break; 871 case LG2161: 872 ret = lg2161_read_crc_err_count(state, err); 873 break; 874 default: 875 ret = -EINVAL; 876 break; 877 } 878 return ret; 879 } 880 881 static int lg2160_read_rs_err_count(struct lg216x_state *state, u16 *err) 882 { 883 u8 rs_err1, rs_err2; 884 int ret; 885 886 *err = 0; 887 888 ret = lg216x_read_reg(state, 0x0413, &rs_err1); 889 if (lg_fail(ret)) 890 goto fail; 891 892 ret = lg216x_read_reg(state, 0x0414, &rs_err2); 893 if (lg_fail(ret)) 894 goto fail; 895 896 *err = (u16)(((rs_err2 & 0x0f) << 8) | rs_err1); 897 fail: 898 return ret; 899 } 900 901 static int lg2161_read_rs_err_count(struct lg216x_state *state, u16 *err) 902 { 903 u8 rs_err1, rs_err2; 904 int ret; 905 906 *err = 0; 907 908 ret = lg216x_read_reg(state, 0x0613, &rs_err1); 909 if (lg_fail(ret)) 910 goto fail; 911 912 ret = lg216x_read_reg(state, 0x0614, &rs_err2); 913 if (lg_fail(ret)) 914 goto fail; 915 916 *err = (u16)((rs_err1 << 8) | rs_err2); 917 fail: 918 return ret; 919 } 920 921 static int lg216x_read_rs_err_count(struct lg216x_state *state, u16 *err) 922 { 923 int ret; 924 switch (state->cfg->lg_chip) { 925 case LG2160: 926 ret = lg2160_read_rs_err_count(state, err); 927 break; 928 case LG2161: 929 ret = lg2161_read_rs_err_count(state, err); 930 break; 931 default: 932 ret = -EINVAL; 933 break; 934 } 935 return ret; 936 } 937 #endif 938 939 /* ------------------------------------------------------------------------ */ 940 941 static int lg216x_get_frontend(struct dvb_frontend *fe, 942 struct dtv_frontend_properties *c) 943 { 944 struct lg216x_state *state = fe->demodulator_priv; 945 int ret; 946 947 lg_dbg("\n"); 948 949 c->modulation = VSB_8; 950 c->frequency = state->current_frequency; 951 c->delivery_system = SYS_ATSCMH; 952 953 ret = lg216x_get_fic_version(state, 954 &c->atscmh_fic_ver); 955 if (lg_fail(ret)) 956 goto fail; 957 if (state->fic_ver != c->atscmh_fic_ver) { 958 state->fic_ver = c->atscmh_fic_ver; 959 960 #if 0 961 ret = lg2160_get_parade_id(state, 962 &c->atscmh_parade_id); 963 if (lg_fail(ret)) 964 goto fail; 965 /* #else */ 966 c->atscmh_parade_id = state->parade_id; 967 #endif 968 ret = lg216x_get_nog(state, 969 &c->atscmh_nog); 970 if (lg_fail(ret)) 971 goto fail; 972 ret = lg216x_get_tnog(state, 973 &c->atscmh_tnog); 974 if (lg_fail(ret)) 975 goto fail; 976 ret = lg216x_get_sgn(state, 977 &c->atscmh_sgn); 978 if (lg_fail(ret)) 979 goto fail; 980 ret = lg216x_get_prc(state, 981 &c->atscmh_prc); 982 if (lg_fail(ret)) 983 goto fail; 984 985 ret = lg216x_get_rs_frame_mode(state, 986 (enum atscmh_rs_frame_mode *) 987 &c->atscmh_rs_frame_mode); 988 if (lg_fail(ret)) 989 goto fail; 990 ret = lg216x_get_rs_frame_ensemble(state, 991 (enum atscmh_rs_frame_ensemble *) 992 &c->atscmh_rs_frame_ensemble); 993 if (lg_fail(ret)) 994 goto fail; 995 ret = lg216x_get_rs_code_mode(state, 996 (enum atscmh_rs_code_mode *) 997 &c->atscmh_rs_code_mode_pri, 998 (enum atscmh_rs_code_mode *) 999 &c->atscmh_rs_code_mode_sec); 1000 if (lg_fail(ret)) 1001 goto fail; 1002 ret = lg216x_get_sccc_block_mode(state, 1003 (enum atscmh_sccc_block_mode *) 1004 &c->atscmh_sccc_block_mode); 1005 if (lg_fail(ret)) 1006 goto fail; 1007 ret = lg216x_get_sccc_code_mode(state, 1008 (enum atscmh_sccc_code_mode *) 1009 &c->atscmh_sccc_code_mode_a, 1010 (enum atscmh_sccc_code_mode *) 1011 &c->atscmh_sccc_code_mode_b, 1012 (enum atscmh_sccc_code_mode *) 1013 &c->atscmh_sccc_code_mode_c, 1014 (enum atscmh_sccc_code_mode *) 1015 &c->atscmh_sccc_code_mode_d); 1016 if (lg_fail(ret)) 1017 goto fail; 1018 } 1019 #if 0 1020 ret = lg216x_read_fic_err_count(state, 1021 (u8 *)&c->atscmh_fic_err); 1022 if (lg_fail(ret)) 1023 goto fail; 1024 ret = lg216x_read_crc_err_count(state, 1025 &c->atscmh_crc_err); 1026 if (lg_fail(ret)) 1027 goto fail; 1028 ret = lg216x_read_rs_err_count(state, 1029 &c->atscmh_rs_err); 1030 if (lg_fail(ret)) 1031 goto fail; 1032 1033 switch (state->cfg->lg_chip) { 1034 case LG2160: 1035 if (((c->atscmh_rs_err >= 240) && 1036 (c->atscmh_crc_err >= 240)) && 1037 ((jiffies_to_msecs(jiffies) - state->last_reset) > 6000)) 1038 ret = lg216x_soft_reset(state); 1039 break; 1040 case LG2161: 1041 /* no fix needed here (as far as we know) */ 1042 ret = 0; 1043 break; 1044 } 1045 lg_fail(ret); 1046 #endif 1047 fail: 1048 return ret; 1049 } 1050 1051 static int lg2160_set_frontend(struct dvb_frontend *fe) 1052 { 1053 struct lg216x_state *state = fe->demodulator_priv; 1054 struct dtv_frontend_properties *c = &fe->dtv_property_cache; 1055 int ret; 1056 1057 lg_dbg("(%d)\n", fe->dtv_property_cache.frequency); 1058 1059 if (fe->ops.tuner_ops.set_params) { 1060 ret = fe->ops.tuner_ops.set_params(fe); 1061 if (fe->ops.i2c_gate_ctrl) 1062 fe->ops.i2c_gate_ctrl(fe, 0); 1063 if (lg_fail(ret)) 1064 goto fail; 1065 state->current_frequency = fe->dtv_property_cache.frequency; 1066 } 1067 1068 ret = lg2160_agc_fix(state, 0, 0); 1069 if (lg_fail(ret)) 1070 goto fail; 1071 ret = lg2160_agc_polarity(state, 0, 0); 1072 if (lg_fail(ret)) 1073 goto fail; 1074 ret = lg2160_tuner_pwr_save_polarity(state, 1); 1075 if (lg_fail(ret)) 1076 goto fail; 1077 ret = lg216x_set_if(state); 1078 if (lg_fail(ret)) 1079 goto fail; 1080 ret = lg2160_spectrum_polarity(state, state->cfg->spectral_inversion); 1081 if (lg_fail(ret)) 1082 goto fail; 1083 1084 /* be tuned before this point */ 1085 ret = lg216x_soft_reset(state); 1086 if (lg_fail(ret)) 1087 goto fail; 1088 1089 ret = lg2160_tuner_pwr_save(state, 0); 1090 if (lg_fail(ret)) 1091 goto fail; 1092 1093 switch (state->cfg->lg_chip) { 1094 case LG2160: 1095 ret = lg2160_set_spi_clock(state); 1096 if (lg_fail(ret)) 1097 goto fail; 1098 break; 1099 case LG2161: 1100 ret = lg2161_set_output_interface(state); 1101 if (lg_fail(ret)) 1102 goto fail; 1103 break; 1104 } 1105 1106 ret = lg216x_set_parade(state, fe->dtv_property_cache.atscmh_parade_id); 1107 if (lg_fail(ret)) 1108 goto fail; 1109 1110 ret = lg216x_set_ensemble(state, 1111 fe->dtv_property_cache.atscmh_rs_frame_ensemble); 1112 if (lg_fail(ret)) 1113 goto fail; 1114 1115 ret = lg216x_initialize(state); 1116 if (lg_fail(ret)) 1117 goto fail; 1118 1119 ret = lg216x_enable_fic(state, 1); 1120 lg_fail(ret); 1121 1122 lg216x_get_frontend(fe, c); 1123 fail: 1124 return ret; 1125 } 1126 1127 /* ------------------------------------------------------------------------ */ 1128 1129 static int lg2160_read_lock_status(struct lg216x_state *state, 1130 int *acq_lock, int *sync_lock) 1131 { 1132 u8 val; 1133 int ret; 1134 1135 *acq_lock = 0; 1136 *sync_lock = 0; 1137 1138 ret = lg216x_read_reg(state, 0x011b, &val); 1139 if (lg_fail(ret)) 1140 goto fail; 1141 1142 *sync_lock = (val & 0x20) ? 0 : 1; 1143 *acq_lock = (val & 0x40) ? 0 : 1; 1144 fail: 1145 return ret; 1146 } 1147 1148 #ifdef USE_LG2161_LOCK_BITS 1149 static int lg2161_read_lock_status(struct lg216x_state *state, 1150 int *acq_lock, int *sync_lock) 1151 { 1152 u8 val; 1153 int ret; 1154 1155 *acq_lock = 0; 1156 *sync_lock = 0; 1157 1158 ret = lg216x_read_reg(state, 0x0304, &val); 1159 if (lg_fail(ret)) 1160 goto fail; 1161 1162 *sync_lock = (val & 0x80) ? 0 : 1; 1163 1164 ret = lg216x_read_reg(state, 0x011b, &val); 1165 if (lg_fail(ret)) 1166 goto fail; 1167 1168 *acq_lock = (val & 0x40) ? 0 : 1; 1169 fail: 1170 return ret; 1171 } 1172 #endif 1173 1174 static int lg216x_read_lock_status(struct lg216x_state *state, 1175 int *acq_lock, int *sync_lock) 1176 { 1177 #ifdef USE_LG2161_LOCK_BITS 1178 int ret; 1179 switch (state->cfg->lg_chip) { 1180 case LG2160: 1181 ret = lg2160_read_lock_status(state, acq_lock, sync_lock); 1182 break; 1183 case LG2161: 1184 ret = lg2161_read_lock_status(state, acq_lock, sync_lock); 1185 break; 1186 default: 1187 ret = -EINVAL; 1188 break; 1189 } 1190 return ret; 1191 #else 1192 return lg2160_read_lock_status(state, acq_lock, sync_lock); 1193 #endif 1194 } 1195 1196 static int lg216x_read_status(struct dvb_frontend *fe, enum fe_status *status) 1197 { 1198 struct lg216x_state *state = fe->demodulator_priv; 1199 int ret, acq_lock, sync_lock; 1200 1201 *status = 0; 1202 1203 ret = lg216x_read_lock_status(state, &acq_lock, &sync_lock); 1204 if (lg_fail(ret)) 1205 goto fail; 1206 1207 lg_dbg("%s%s\n", 1208 acq_lock ? "SIGNALEXIST " : "", 1209 sync_lock ? "SYNCLOCK" : ""); 1210 1211 if (acq_lock) 1212 *status |= FE_HAS_SIGNAL; 1213 if (sync_lock) 1214 *status |= FE_HAS_SYNC; 1215 1216 if (*status) 1217 *status |= FE_HAS_CARRIER | FE_HAS_VITERBI | FE_HAS_LOCK; 1218 1219 fail: 1220 return ret; 1221 } 1222 1223 /* ------------------------------------------------------------------------ */ 1224 1225 static int lg2160_read_snr(struct dvb_frontend *fe, u16 *snr) 1226 { 1227 struct lg216x_state *state = fe->demodulator_priv; 1228 u8 snr1, snr2; 1229 int ret; 1230 1231 *snr = 0; 1232 1233 ret = lg216x_read_reg(state, 0x0202, &snr1); 1234 if (lg_fail(ret)) 1235 goto fail; 1236 1237 ret = lg216x_read_reg(state, 0x0203, &snr2); 1238 if (lg_fail(ret)) 1239 goto fail; 1240 1241 if ((snr1 == 0xba) || (snr2 == 0xdf)) 1242 *snr = 0; 1243 else 1244 #if 1 1245 *snr = ((snr1 >> 4) * 100) + ((snr1 & 0x0f) * 10) + (snr2 >> 4); 1246 #else /* BCD */ 1247 *snr = (snr2 | (snr1 << 8)); 1248 #endif 1249 fail: 1250 return ret; 1251 } 1252 1253 static int lg2161_read_snr(struct dvb_frontend *fe, u16 *snr) 1254 { 1255 struct lg216x_state *state = fe->demodulator_priv; 1256 u8 snr1, snr2; 1257 int ret; 1258 1259 *snr = 0; 1260 1261 ret = lg216x_read_reg(state, 0x0302, &snr1); 1262 if (lg_fail(ret)) 1263 goto fail; 1264 1265 ret = lg216x_read_reg(state, 0x0303, &snr2); 1266 if (lg_fail(ret)) 1267 goto fail; 1268 1269 if ((snr1 == 0xba) || (snr2 == 0xfd)) 1270 *snr = 0; 1271 else 1272 1273 *snr = ((snr1 >> 4) * 100) + ((snr1 & 0x0f) * 10) + (snr2 & 0x0f); 1274 fail: 1275 return ret; 1276 } 1277 1278 static int lg216x_read_signal_strength(struct dvb_frontend *fe, 1279 u16 *strength) 1280 { 1281 #if 0 1282 /* borrowed from lgdt330x.c 1283 * 1284 * Calculate strength from SNR up to 35dB 1285 * Even though the SNR can go higher than 35dB, 1286 * there is some comfort factor in having a range of 1287 * strong signals that can show at 100% 1288 */ 1289 struct lg216x_state *state = fe->demodulator_priv; 1290 u16 snr; 1291 int ret; 1292 #endif 1293 *strength = 0; 1294 #if 0 1295 ret = fe->ops.read_snr(fe, &snr); 1296 if (lg_fail(ret)) 1297 goto fail; 1298 /* Rather than use the 8.8 value snr, use state->snr which is 8.24 */ 1299 /* scale the range 0 - 35*2^24 into 0 - 65535 */ 1300 if (state->snr >= 8960 * 0x10000) 1301 *strength = 0xffff; 1302 else 1303 *strength = state->snr / 8960; 1304 fail: 1305 return ret; 1306 #else 1307 return 0; 1308 #endif 1309 } 1310 1311 /* ------------------------------------------------------------------------ */ 1312 1313 static int lg216x_read_ucblocks(struct dvb_frontend *fe, u32 *ucblocks) 1314 { 1315 #if 0 1316 struct lg216x_state *state = fe->demodulator_priv; 1317 int ret; 1318 1319 ret = lg216x_read_rs_err_count(state, 1320 &fe->dtv_property_cache.atscmh_rs_err); 1321 if (lg_fail(ret)) 1322 goto fail; 1323 1324 *ucblocks = fe->dtv_property_cache.atscmh_rs_err; 1325 fail: 1326 #else 1327 *ucblocks = 0; 1328 #endif 1329 return 0; 1330 } 1331 1332 static int lg216x_get_tune_settings(struct dvb_frontend *fe, 1333 struct dvb_frontend_tune_settings 1334 *fe_tune_settings) 1335 { 1336 fe_tune_settings->min_delay_ms = 500; 1337 lg_dbg("\n"); 1338 return 0; 1339 } 1340 1341 static void lg216x_release(struct dvb_frontend *fe) 1342 { 1343 struct lg216x_state *state = fe->demodulator_priv; 1344 lg_dbg("\n"); 1345 kfree(state); 1346 } 1347 1348 static const struct dvb_frontend_ops lg2160_ops = { 1349 .delsys = { SYS_ATSCMH }, 1350 .info = { 1351 .name = "LG Electronics LG2160 ATSC/MH Frontend", 1352 .frequency_min_hz = 54 * MHz, 1353 .frequency_max_hz = 858 * MHz, 1354 .frequency_stepsize_hz = 62500, 1355 }, 1356 .i2c_gate_ctrl = lg216x_i2c_gate_ctrl, 1357 #if 0 1358 .init = lg216x_init, 1359 .sleep = lg216x_sleep, 1360 #endif 1361 .set_frontend = lg2160_set_frontend, 1362 .get_frontend = lg216x_get_frontend, 1363 .get_tune_settings = lg216x_get_tune_settings, 1364 .read_status = lg216x_read_status, 1365 #if 0 1366 .read_ber = lg216x_read_ber, 1367 #endif 1368 .read_signal_strength = lg216x_read_signal_strength, 1369 .read_snr = lg2160_read_snr, 1370 .read_ucblocks = lg216x_read_ucblocks, 1371 .release = lg216x_release, 1372 }; 1373 1374 static const struct dvb_frontend_ops lg2161_ops = { 1375 .delsys = { SYS_ATSCMH }, 1376 .info = { 1377 .name = "LG Electronics LG2161 ATSC/MH Frontend", 1378 .frequency_min_hz = 54 * MHz, 1379 .frequency_max_hz = 858 * MHz, 1380 .frequency_stepsize_hz = 62500, 1381 }, 1382 .i2c_gate_ctrl = lg216x_i2c_gate_ctrl, 1383 #if 0 1384 .init = lg216x_init, 1385 .sleep = lg216x_sleep, 1386 #endif 1387 .set_frontend = lg2160_set_frontend, 1388 .get_frontend = lg216x_get_frontend, 1389 .get_tune_settings = lg216x_get_tune_settings, 1390 .read_status = lg216x_read_status, 1391 #if 0 1392 .read_ber = lg216x_read_ber, 1393 #endif 1394 .read_signal_strength = lg216x_read_signal_strength, 1395 .read_snr = lg2161_read_snr, 1396 .read_ucblocks = lg216x_read_ucblocks, 1397 .release = lg216x_release, 1398 }; 1399 1400 struct dvb_frontend *lg2160_attach(const struct lg2160_config *config, 1401 struct i2c_adapter *i2c_adap) 1402 { 1403 struct lg216x_state *state = NULL; 1404 1405 lg_dbg("(%d-%04x)\n", 1406 i2c_adap ? i2c_adapter_id(i2c_adap) : 0, 1407 config ? config->i2c_addr : 0); 1408 1409 state = kzalloc(sizeof(struct lg216x_state), GFP_KERNEL); 1410 if (!state) 1411 return NULL; 1412 1413 state->cfg = config; 1414 state->i2c_adap = i2c_adap; 1415 state->fic_ver = 0xff; 1416 state->parade_id = 0xff; 1417 1418 switch (config->lg_chip) { 1419 default: 1420 lg_warn("invalid chip requested, defaulting to LG2160"); 1421 /* fall-thru */ 1422 case LG2160: 1423 memcpy(&state->frontend.ops, &lg2160_ops, 1424 sizeof(struct dvb_frontend_ops)); 1425 break; 1426 case LG2161: 1427 memcpy(&state->frontend.ops, &lg2161_ops, 1428 sizeof(struct dvb_frontend_ops)); 1429 break; 1430 } 1431 1432 state->frontend.demodulator_priv = state; 1433 state->current_frequency = -1; 1434 /* parade 1 by default */ 1435 state->frontend.dtv_property_cache.atscmh_parade_id = 1; 1436 1437 return &state->frontend; 1438 } 1439 EXPORT_SYMBOL(lg2160_attach); 1440 1441 MODULE_DESCRIPTION("LG Electronics LG216x ATSC/MH Demodulator Driver"); 1442 MODULE_AUTHOR("Michael Krufky <mkrufky@linuxtv.org>"); 1443 MODULE_LICENSE("GPL"); 1444 MODULE_VERSION("0.3"); 1445