3127 lines · c
1// SPDX-License-Identifier: GPL-2.0-or-later2/*3 cx231xx_avcore.c - driver for Conexant Cx23100/101/1024 USB video capture devices5 6 Copyright (C) 2008 <srinivasa.deevi at conexant dot com>7 8 This program contains the specific code to control the avdecoder chip and9 other related usb control functions for cx231xx based chipset.10 11 */12 13#include "cx231xx.h"14#include <linux/init.h>15#include <linux/list.h>16#include <linux/module.h>17#include <linux/kernel.h>18#include <linux/bitmap.h>19#include <linux/i2c.h>20#include <linux/mm.h>21#include <linux/mutex.h>22#include <media/tuner.h>23 24#include <media/v4l2-common.h>25#include <media/v4l2-ioctl.h>26 27#include "cx231xx-dif.h"28 29#define TUNER_MODE_FM_RADIO 030/******************************************************************************31 -: BLOCK ARRANGEMENT :-32 I2S block ----------------------|33 [I2S audio] |34 |35 Analog Front End --> Direct IF -|-> Cx25840 --> Audio36 [video & audio] | [Audio]37 |38 |-> Cx25840 --> Video39 [Video]40 41*******************************************************************************/42/******************************************************************************43 * VERVE REGISTER *44 * *45 ******************************************************************************/46static int verve_write_byte(struct cx231xx *dev, u8 saddr, u8 data)47{48 return cx231xx_write_i2c_data(dev, VERVE_I2C_ADDRESS,49 saddr, 1, data, 1);50}51 52static int verve_read_byte(struct cx231xx *dev, u8 saddr, u8 *data)53{54 int status;55 u32 temp = 0;56 57 status = cx231xx_read_i2c_data(dev, VERVE_I2C_ADDRESS,58 saddr, 1, &temp, 1);59 *data = (u8) temp;60 return status;61}62void initGPIO(struct cx231xx *dev)63{64 u32 _gpio_direction = 0;65 u32 value = 0;66 u8 val = 0;67 68 _gpio_direction = _gpio_direction & 0xFC0003FF;69 _gpio_direction = _gpio_direction | 0x03FDFC00;70 cx231xx_send_gpio_cmd(dev, _gpio_direction, (u8 *)&value, 4, 0, 0);71 72 verve_read_byte(dev, 0x07, &val);73 dev_dbg(dev->dev, "verve_read_byte address0x07=0x%x\n", val);74 verve_write_byte(dev, 0x07, 0xF4);75 verve_read_byte(dev, 0x07, &val);76 dev_dbg(dev->dev, "verve_read_byte address0x07=0x%x\n", val);77 78 cx231xx_capture_start(dev, 1, Vbi);79 80 cx231xx_mode_register(dev, EP_MODE_SET, 0x0500FE00);81 cx231xx_mode_register(dev, GBULK_BIT_EN, 0xFFFDFFFF);82 83}84void uninitGPIO(struct cx231xx *dev)85{86 u8 value[4] = { 0, 0, 0, 0 };87 88 cx231xx_capture_start(dev, 0, Vbi);89 verve_write_byte(dev, 0x07, 0x14);90 cx231xx_write_ctrl_reg(dev, VRT_SET_REGISTER,91 0x68, value, 4);92}93 94/******************************************************************************95 * A F E - B L O C K C O N T R O L functions *96 * [ANALOG FRONT END] *97 ******************************************************************************/98static int afe_write_byte(struct cx231xx *dev, u16 saddr, u8 data)99{100 return cx231xx_write_i2c_data(dev, AFE_DEVICE_ADDRESS,101 saddr, 2, data, 1);102}103 104static int afe_read_byte(struct cx231xx *dev, u16 saddr, u8 *data)105{106 int status;107 u32 temp = 0;108 109 status = cx231xx_read_i2c_data(dev, AFE_DEVICE_ADDRESS,110 saddr, 2, &temp, 1);111 *data = (u8) temp;112 return status;113}114 115int cx231xx_afe_init_super_block(struct cx231xx *dev, u32 ref_count)116{117 int status = 0;118 u8 temp = 0;119 u8 afe_power_status = 0;120 int i = 0;121 122 /* super block initialize */123 temp = (u8) (ref_count & 0xff);124 status = afe_write_byte(dev, SUP_BLK_TUNE2, temp);125 if (status < 0)126 return status;127 128 status = afe_read_byte(dev, SUP_BLK_TUNE2, &afe_power_status);129 if (status < 0)130 return status;131 132 temp = (u8) ((ref_count & 0x300) >> 8);133 temp |= 0x40;134 status = afe_write_byte(dev, SUP_BLK_TUNE1, temp);135 if (status < 0)136 return status;137 138 status = afe_write_byte(dev, SUP_BLK_PLL2, 0x0f);139 if (status < 0)140 return status;141 142 /* enable pll */143 while (afe_power_status != 0x18) {144 status = afe_write_byte(dev, SUP_BLK_PWRDN, 0x18);145 if (status < 0) {146 dev_dbg(dev->dev,147 "%s: Init Super Block failed in send cmd\n",148 __func__);149 break;150 }151 152 status = afe_read_byte(dev, SUP_BLK_PWRDN, &afe_power_status);153 afe_power_status &= 0xff;154 if (status < 0) {155 dev_dbg(dev->dev,156 "%s: Init Super Block failed in receive cmd\n",157 __func__);158 break;159 }160 i++;161 if (i == 10) {162 dev_dbg(dev->dev,163 "%s: Init Super Block force break in loop !!!!\n",164 __func__);165 status = -1;166 break;167 }168 }169 170 if (status < 0)171 return status;172 173 /* start tuning filter */174 status = afe_write_byte(dev, SUP_BLK_TUNE3, 0x40);175 if (status < 0)176 return status;177 178 msleep(5);179 180 /* exit tuning */181 status = afe_write_byte(dev, SUP_BLK_TUNE3, 0x00);182 183 return status;184}185 186int cx231xx_afe_init_channels(struct cx231xx *dev)187{188 int status = 0;189 190 /* power up all 3 channels, clear pd_buffer */191 status = afe_write_byte(dev, ADC_PWRDN_CLAMP_CH1, 0x00);192 status = afe_write_byte(dev, ADC_PWRDN_CLAMP_CH2, 0x00);193 status = afe_write_byte(dev, ADC_PWRDN_CLAMP_CH3, 0x00);194 195 /* Enable quantizer calibration */196 status = afe_write_byte(dev, ADC_COM_QUANT, 0x02);197 198 /* channel initialize, force modulator (fb) reset */199 status = afe_write_byte(dev, ADC_FB_FRCRST_CH1, 0x17);200 status = afe_write_byte(dev, ADC_FB_FRCRST_CH2, 0x17);201 status = afe_write_byte(dev, ADC_FB_FRCRST_CH3, 0x17);202 203 /* start quantilizer calibration */204 status = afe_write_byte(dev, ADC_CAL_ATEST_CH1, 0x10);205 status = afe_write_byte(dev, ADC_CAL_ATEST_CH2, 0x10);206 status = afe_write_byte(dev, ADC_CAL_ATEST_CH3, 0x10);207 msleep(5);208 209 /* exit modulator (fb) reset */210 status = afe_write_byte(dev, ADC_FB_FRCRST_CH1, 0x07);211 status = afe_write_byte(dev, ADC_FB_FRCRST_CH2, 0x07);212 status = afe_write_byte(dev, ADC_FB_FRCRST_CH3, 0x07);213 214 /* enable the pre_clamp in each channel for single-ended input */215 status = afe_write_byte(dev, ADC_NTF_PRECLMP_EN_CH1, 0xf0);216 status = afe_write_byte(dev, ADC_NTF_PRECLMP_EN_CH2, 0xf0);217 status = afe_write_byte(dev, ADC_NTF_PRECLMP_EN_CH3, 0xf0);218 219 /* use diode instead of resistor, so set term_en to 0, res_en to 0 */220 status = cx231xx_reg_mask_write(dev, AFE_DEVICE_ADDRESS, 8,221 ADC_QGAIN_RES_TRM_CH1, 3, 7, 0x00);222 status = cx231xx_reg_mask_write(dev, AFE_DEVICE_ADDRESS, 8,223 ADC_QGAIN_RES_TRM_CH2, 3, 7, 0x00);224 status = cx231xx_reg_mask_write(dev, AFE_DEVICE_ADDRESS, 8,225 ADC_QGAIN_RES_TRM_CH3, 3, 7, 0x00);226 227 /* dynamic element matching off */228 status = afe_write_byte(dev, ADC_DCSERVO_DEM_CH1, 0x03);229 status = afe_write_byte(dev, ADC_DCSERVO_DEM_CH2, 0x03);230 status = afe_write_byte(dev, ADC_DCSERVO_DEM_CH3, 0x03);231 232 return status;233}234 235int cx231xx_afe_setup_AFE_for_baseband(struct cx231xx *dev)236{237 u8 c_value = 0;238 int status = 0;239 240 status = afe_read_byte(dev, ADC_PWRDN_CLAMP_CH2, &c_value);241 c_value &= (~(0x50));242 status = afe_write_byte(dev, ADC_PWRDN_CLAMP_CH2, c_value);243 244 return status;245}246 247/*248 The Analog Front End in Cx231xx has 3 channels. These249 channels are used to share between different inputs250 like tuner, s-video and composite inputs.251 252 channel 1 ----- pin 1 to pin4(in reg is 1-4)253 channel 2 ----- pin 5 to pin8(in reg is 5-8)254 channel 3 ----- pin 9 to pin 12(in reg is 9-11)255*/256int cx231xx_afe_set_input_mux(struct cx231xx *dev, u32 input_mux)257{258 u8 ch1_setting = (u8) input_mux;259 u8 ch2_setting = (u8) (input_mux >> 8);260 u8 ch3_setting = (u8) (input_mux >> 16);261 int status = 0;262 u8 value = 0;263 264 if (ch1_setting != 0) {265 status = afe_read_byte(dev, ADC_INPUT_CH1, &value);266 value &= ~INPUT_SEL_MASK;267 value |= (ch1_setting - 1) << 4;268 value &= 0xff;269 status = afe_write_byte(dev, ADC_INPUT_CH1, value);270 }271 272 if (ch2_setting != 0) {273 status = afe_read_byte(dev, ADC_INPUT_CH2, &value);274 value &= ~INPUT_SEL_MASK;275 value |= (ch2_setting - 1) << 4;276 value &= 0xff;277 status = afe_write_byte(dev, ADC_INPUT_CH2, value);278 }279 280 /* For ch3_setting, the value to put in the register is281 7 less than the input number */282 if (ch3_setting != 0) {283 status = afe_read_byte(dev, ADC_INPUT_CH3, &value);284 value &= ~INPUT_SEL_MASK;285 value |= (ch3_setting - 1) << 4;286 value &= 0xff;287 status = afe_write_byte(dev, ADC_INPUT_CH3, value);288 }289 290 return status;291}292 293int cx231xx_afe_set_mode(struct cx231xx *dev, enum AFE_MODE mode)294{295 int status = 0;296 297 /*298 * FIXME: We need to implement the AFE code for LOW IF and for HI IF.299 * Currently, only baseband works.300 */301 302 switch (mode) {303 case AFE_MODE_LOW_IF:304 cx231xx_Setup_AFE_for_LowIF(dev);305 break;306 case AFE_MODE_BASEBAND:307 status = cx231xx_afe_setup_AFE_for_baseband(dev);308 break;309 case AFE_MODE_EU_HI_IF:310 /* SetupAFEforEuHiIF(); */311 break;312 case AFE_MODE_US_HI_IF:313 /* SetupAFEforUsHiIF(); */314 break;315 case AFE_MODE_JAPAN_HI_IF:316 /* SetupAFEforJapanHiIF(); */317 break;318 }319 320 if ((mode != dev->afe_mode) &&321 (dev->video_input == CX231XX_VMUX_TELEVISION))322 status = cx231xx_afe_adjust_ref_count(dev,323 CX231XX_VMUX_TELEVISION);324 325 dev->afe_mode = mode;326 327 return status;328}329 330int cx231xx_afe_update_power_control(struct cx231xx *dev,331 enum AV_MODE avmode)332{333 u8 afe_power_status = 0;334 int status = 0;335 336 switch (dev->model) {337 case CX231XX_BOARD_CNXT_CARRAERA:338 case CX231XX_BOARD_CNXT_RDE_250:339 case CX231XX_BOARD_CNXT_SHELBY:340 case CX231XX_BOARD_CNXT_RDU_250:341 case CX231XX_BOARD_CNXT_RDE_253S:342 case CX231XX_BOARD_CNXT_RDU_253S:343 case CX231XX_BOARD_CNXT_VIDEO_GRABBER:344 case CX231XX_BOARD_HAUPPAUGE_EXETER:345 case CX231XX_BOARD_HAUPPAUGE_930C_HD_1113xx:346 case CX231XX_BOARD_HAUPPAUGE_USBLIVE2:347 case CX231XX_BOARD_PV_PLAYTV_USB_HYBRID:348 case CX231XX_BOARD_HAUPPAUGE_USB2_FM_PAL:349 case CX231XX_BOARD_HAUPPAUGE_USB2_FM_NTSC:350 case CX231XX_BOARD_OTG102:351 if (avmode == POLARIS_AVMODE_ANALOGT_TV) {352 while (afe_power_status != (FLD_PWRDN_TUNING_BIAS |353 FLD_PWRDN_ENABLE_PLL)) {354 status = afe_write_byte(dev, SUP_BLK_PWRDN,355 FLD_PWRDN_TUNING_BIAS |356 FLD_PWRDN_ENABLE_PLL);357 status |= afe_read_byte(dev, SUP_BLK_PWRDN,358 &afe_power_status);359 if (status < 0)360 break;361 }362 363 status = afe_write_byte(dev, ADC_PWRDN_CLAMP_CH1,364 0x00);365 status |= afe_write_byte(dev, ADC_PWRDN_CLAMP_CH2,366 0x00);367 status |= afe_write_byte(dev, ADC_PWRDN_CLAMP_CH3,368 0x00);369 } else if (avmode == POLARIS_AVMODE_DIGITAL) {370 status = afe_write_byte(dev, ADC_PWRDN_CLAMP_CH1,371 0x70);372 status |= afe_write_byte(dev, ADC_PWRDN_CLAMP_CH2,373 0x70);374 status |= afe_write_byte(dev, ADC_PWRDN_CLAMP_CH3,375 0x70);376 377 status |= afe_read_byte(dev, SUP_BLK_PWRDN,378 &afe_power_status);379 afe_power_status |= FLD_PWRDN_PD_BANDGAP |380 FLD_PWRDN_PD_BIAS |381 FLD_PWRDN_PD_TUNECK;382 status |= afe_write_byte(dev, SUP_BLK_PWRDN,383 afe_power_status);384 } else if (avmode == POLARIS_AVMODE_ENXTERNAL_AV) {385 while (afe_power_status != (FLD_PWRDN_TUNING_BIAS |386 FLD_PWRDN_ENABLE_PLL)) {387 status = afe_write_byte(dev, SUP_BLK_PWRDN,388 FLD_PWRDN_TUNING_BIAS |389 FLD_PWRDN_ENABLE_PLL);390 status |= afe_read_byte(dev, SUP_BLK_PWRDN,391 &afe_power_status);392 if (status < 0)393 break;394 }395 396 status |= afe_write_byte(dev, ADC_PWRDN_CLAMP_CH1,397 0x00);398 status |= afe_write_byte(dev, ADC_PWRDN_CLAMP_CH2,399 0x00);400 status |= afe_write_byte(dev, ADC_PWRDN_CLAMP_CH3,401 0x00);402 } else {403 dev_dbg(dev->dev, "Invalid AV mode input\n");404 status = -1;405 }406 break;407 default:408 if (avmode == POLARIS_AVMODE_ANALOGT_TV) {409 while (afe_power_status != (FLD_PWRDN_TUNING_BIAS |410 FLD_PWRDN_ENABLE_PLL)) {411 status = afe_write_byte(dev, SUP_BLK_PWRDN,412 FLD_PWRDN_TUNING_BIAS |413 FLD_PWRDN_ENABLE_PLL);414 status |= afe_read_byte(dev, SUP_BLK_PWRDN,415 &afe_power_status);416 if (status < 0)417 break;418 }419 420 status |= afe_write_byte(dev, ADC_PWRDN_CLAMP_CH1,421 0x40);422 status |= afe_write_byte(dev, ADC_PWRDN_CLAMP_CH2,423 0x40);424 status |= afe_write_byte(dev, ADC_PWRDN_CLAMP_CH3,425 0x00);426 } else if (avmode == POLARIS_AVMODE_DIGITAL) {427 status = afe_write_byte(dev, ADC_PWRDN_CLAMP_CH1,428 0x70);429 status |= afe_write_byte(dev, ADC_PWRDN_CLAMP_CH2,430 0x70);431 status |= afe_write_byte(dev, ADC_PWRDN_CLAMP_CH3,432 0x70);433 434 status |= afe_read_byte(dev, SUP_BLK_PWRDN,435 &afe_power_status);436 afe_power_status |= FLD_PWRDN_PD_BANDGAP |437 FLD_PWRDN_PD_BIAS |438 FLD_PWRDN_PD_TUNECK;439 status |= afe_write_byte(dev, SUP_BLK_PWRDN,440 afe_power_status);441 } else if (avmode == POLARIS_AVMODE_ENXTERNAL_AV) {442 while (afe_power_status != (FLD_PWRDN_TUNING_BIAS |443 FLD_PWRDN_ENABLE_PLL)) {444 status = afe_write_byte(dev, SUP_BLK_PWRDN,445 FLD_PWRDN_TUNING_BIAS |446 FLD_PWRDN_ENABLE_PLL);447 status |= afe_read_byte(dev, SUP_BLK_PWRDN,448 &afe_power_status);449 if (status < 0)450 break;451 }452 453 status |= afe_write_byte(dev, ADC_PWRDN_CLAMP_CH1,454 0x00);455 status |= afe_write_byte(dev, ADC_PWRDN_CLAMP_CH2,456 0x00);457 status |= afe_write_byte(dev, ADC_PWRDN_CLAMP_CH3,458 0x40);459 } else {460 dev_dbg(dev->dev, "Invalid AV mode input\n");461 status = -1;462 }463 } /* switch */464 465 return status;466}467 468int cx231xx_afe_adjust_ref_count(struct cx231xx *dev, u32 video_input)469{470 u8 input_mode = 0;471 u8 ntf_mode = 0;472 int status = 0;473 474 dev->video_input = video_input;475 476 if (video_input == CX231XX_VMUX_TELEVISION) {477 status = afe_read_byte(dev, ADC_INPUT_CH3, &input_mode);478 status = afe_read_byte(dev, ADC_NTF_PRECLMP_EN_CH3,479 &ntf_mode);480 } else {481 status = afe_read_byte(dev, ADC_INPUT_CH1, &input_mode);482 status = afe_read_byte(dev, ADC_NTF_PRECLMP_EN_CH1,483 &ntf_mode);484 }485 486 input_mode = (ntf_mode & 0x3) | ((input_mode & 0x6) << 1);487 488 switch (input_mode) {489 case SINGLE_ENDED:490 dev->afe_ref_count = 0x23C;491 break;492 case LOW_IF:493 dev->afe_ref_count = 0x24C;494 break;495 case EU_IF:496 dev->afe_ref_count = 0x258;497 break;498 case US_IF:499 dev->afe_ref_count = 0x260;500 break;501 default:502 break;503 }504 505 status = cx231xx_afe_init_super_block(dev, dev->afe_ref_count);506 507 return status;508}509 510/******************************************************************************511 * V I D E O / A U D I O D E C O D E R C O N T R O L functions *512 ******************************************************************************/513static int vid_blk_write_byte(struct cx231xx *dev, u16 saddr, u8 data)514{515 return cx231xx_write_i2c_data(dev, VID_BLK_I2C_ADDRESS,516 saddr, 2, data, 1);517}518 519static int vid_blk_read_byte(struct cx231xx *dev, u16 saddr, u8 *data)520{521 int status;522 u32 temp = 0;523 524 status = cx231xx_read_i2c_data(dev, VID_BLK_I2C_ADDRESS,525 saddr, 2, &temp, 1);526 *data = (u8) temp;527 return status;528}529 530static int vid_blk_write_word(struct cx231xx *dev, u16 saddr, u32 data)531{532 return cx231xx_write_i2c_data(dev, VID_BLK_I2C_ADDRESS,533 saddr, 2, data, 4);534}535 536static int vid_blk_read_word(struct cx231xx *dev, u16 saddr, u32 *data)537{538 return cx231xx_read_i2c_data(dev, VID_BLK_I2C_ADDRESS,539 saddr, 2, data, 4);540}541int cx231xx_check_fw(struct cx231xx *dev)542{543 u8 temp = 0;544 int status = 0;545 status = vid_blk_read_byte(dev, DL_CTL_ADDRESS_LOW, &temp);546 if (status < 0)547 return status;548 else549 return temp;550 551}552 553int cx231xx_set_video_input_mux(struct cx231xx *dev, u8 input)554{555 int status = 0;556 557 switch (INPUT(input)->type) {558 case CX231XX_VMUX_COMPOSITE1:559 case CX231XX_VMUX_SVIDEO:560 if ((dev->current_pcb_config.type == USB_BUS_POWER) &&561 (dev->power_mode != POLARIS_AVMODE_ENXTERNAL_AV)) {562 /* External AV */563 status = cx231xx_set_power_mode(dev,564 POLARIS_AVMODE_ENXTERNAL_AV);565 if (status < 0) {566 dev_err(dev->dev,567 "%s: Failed to set Power - errCode [%d]!\n",568 __func__, status);569 return status;570 }571 }572 status = cx231xx_set_decoder_video_input(dev,573 INPUT(input)->type,574 INPUT(input)->vmux);575 break;576 case CX231XX_VMUX_TELEVISION:577 case CX231XX_VMUX_CABLE:578 if ((dev->current_pcb_config.type == USB_BUS_POWER) &&579 (dev->power_mode != POLARIS_AVMODE_ANALOGT_TV)) {580 /* Tuner */581 status = cx231xx_set_power_mode(dev,582 POLARIS_AVMODE_ANALOGT_TV);583 if (status < 0) {584 dev_err(dev->dev,585 "%s: Failed to set Power - errCode [%d]!\n",586 __func__, status);587 return status;588 }589 }590 switch (dev->model) { /* i2c device tuners */591 case CX231XX_BOARD_HAUPPAUGE_930C_HD_1114xx:592 case CX231XX_BOARD_HAUPPAUGE_935C:593 case CX231XX_BOARD_HAUPPAUGE_955Q:594 case CX231XX_BOARD_HAUPPAUGE_975:595 case CX231XX_BOARD_EVROMEDIA_FULL_HYBRID_FULLHD:596 status = cx231xx_set_decoder_video_input(dev,597 CX231XX_VMUX_TELEVISION,598 INPUT(input)->vmux);599 break;600 default:601 if (dev->tuner_type == TUNER_NXP_TDA18271)602 status = cx231xx_set_decoder_video_input(dev,603 CX231XX_VMUX_TELEVISION,604 INPUT(input)->vmux);605 else606 status = cx231xx_set_decoder_video_input(dev,607 CX231XX_VMUX_COMPOSITE1,608 INPUT(input)->vmux);609 break;610 }611 612 break;613 default:614 dev_err(dev->dev, "%s: Unknown Input %d !\n",615 __func__, INPUT(input)->type);616 break;617 }618 619 /* save the selection */620 dev->video_input = input;621 622 return status;623}624 625int cx231xx_set_decoder_video_input(struct cx231xx *dev,626 u8 pin_type, u8 input)627{628 int status = 0;629 u32 value = 0;630 631 if (pin_type != dev->video_input) {632 status = cx231xx_afe_adjust_ref_count(dev, pin_type);633 if (status < 0) {634 dev_err(dev->dev,635 "%s: adjust_ref_count :Failed to set AFE input mux - errCode [%d]!\n",636 __func__, status);637 return status;638 }639 }640 641 /* call afe block to set video inputs */642 status = cx231xx_afe_set_input_mux(dev, input);643 if (status < 0) {644 dev_err(dev->dev,645 "%s: set_input_mux :Failed to set AFE input mux - errCode [%d]!\n",646 __func__, status);647 return status;648 }649 650 switch (pin_type) {651 case CX231XX_VMUX_COMPOSITE1:652 status = vid_blk_read_word(dev, AFE_CTRL, &value);653 value |= (0 << 13) | (1 << 4);654 value &= ~(1 << 5);655 656 /* set [24:23] [22:15] to 0 */657 value &= (~(0x1ff8000));658 /* set FUNC_MODE[24:23] = 2 IF_MOD[22:15] = 0 */659 value |= 0x1000000;660 status = vid_blk_write_word(dev, AFE_CTRL, value);661 662 status = vid_blk_read_word(dev, OUT_CTRL1, &value);663 value |= (1 << 7);664 status = vid_blk_write_word(dev, OUT_CTRL1, value);665 666 /* Set output mode */667 status = cx231xx_read_modify_write_i2c_dword(dev,668 VID_BLK_I2C_ADDRESS,669 OUT_CTRL1,670 FLD_OUT_MODE,671 dev->board.output_mode);672 673 /* Tell DIF object to go to baseband mode */674 status = cx231xx_dif_set_standard(dev, DIF_USE_BASEBAND);675 if (status < 0) {676 dev_err(dev->dev,677 "%s: cx231xx_dif set to By pass mode- errCode [%d]!\n",678 __func__, status);679 return status;680 }681 682 /* Read the DFE_CTRL1 register */683 status = vid_blk_read_word(dev, DFE_CTRL1, &value);684 685 /* enable the VBI_GATE_EN */686 value |= FLD_VBI_GATE_EN;687 688 /* Enable the auto-VGA enable */689 value |= FLD_VGA_AUTO_EN;690 691 /* Write it back */692 status = vid_blk_write_word(dev, DFE_CTRL1, value);693 694 /* Disable auto config of registers */695 status = cx231xx_read_modify_write_i2c_dword(dev,696 VID_BLK_I2C_ADDRESS,697 MODE_CTRL, FLD_ACFG_DIS,698 cx231xx_set_field(FLD_ACFG_DIS, 1));699 700 /* Set CVBS input mode */701 status = cx231xx_read_modify_write_i2c_dword(dev,702 VID_BLK_I2C_ADDRESS,703 MODE_CTRL, FLD_INPUT_MODE,704 cx231xx_set_field(FLD_INPUT_MODE, INPUT_MODE_CVBS_0));705 break;706 case CX231XX_VMUX_SVIDEO:707 /* Disable the use of DIF */708 709 status = vid_blk_read_word(dev, AFE_CTRL, &value);710 711 /* set [24:23] [22:15] to 0 */712 value &= (~(0x1ff8000));713 /* set FUNC_MODE[24:23] = 2714 IF_MOD[22:15] = 0 DCR_BYP_CH2[4:4] = 1; */715 value |= 0x1000010;716 status = vid_blk_write_word(dev, AFE_CTRL, value);717 718 /* Tell DIF object to go to baseband mode */719 status = cx231xx_dif_set_standard(dev, DIF_USE_BASEBAND);720 if (status < 0) {721 dev_err(dev->dev,722 "%s: cx231xx_dif set to By pass mode- errCode [%d]!\n",723 __func__, status);724 return status;725 }726 727 /* Read the DFE_CTRL1 register */728 status = vid_blk_read_word(dev, DFE_CTRL1, &value);729 730 /* enable the VBI_GATE_EN */731 value |= FLD_VBI_GATE_EN;732 733 /* Enable the auto-VGA enable */734 value |= FLD_VGA_AUTO_EN;735 736 /* Write it back */737 status = vid_blk_write_word(dev, DFE_CTRL1, value);738 739 /* Disable auto config of registers */740 status = cx231xx_read_modify_write_i2c_dword(dev,741 VID_BLK_I2C_ADDRESS,742 MODE_CTRL, FLD_ACFG_DIS,743 cx231xx_set_field(FLD_ACFG_DIS, 1));744 745 /* Set YC input mode */746 status = cx231xx_read_modify_write_i2c_dword(dev,747 VID_BLK_I2C_ADDRESS,748 MODE_CTRL,749 FLD_INPUT_MODE,750 cx231xx_set_field(FLD_INPUT_MODE, INPUT_MODE_YC_1));751 752 /* Chroma to ADC2 */753 status = vid_blk_read_word(dev, AFE_CTRL, &value);754 value |= FLD_CHROMA_IN_SEL; /* set the chroma in select */755 756 /* Clear VGA_SEL_CH2 and VGA_SEL_CH3 (bits 7 and 8)757 This sets them to use video758 rather than audio. Only one of the two will be in use. */759 value &= ~(FLD_VGA_SEL_CH2 | FLD_VGA_SEL_CH3);760 761 status = vid_blk_write_word(dev, AFE_CTRL, value);762 763 status = cx231xx_afe_set_mode(dev, AFE_MODE_BASEBAND);764 break;765 case CX231XX_VMUX_TELEVISION:766 case CX231XX_VMUX_CABLE:767 default:768 /* TODO: Test if this is also needed for xc2028/xc3028 */769 if (dev->board.tuner_type == TUNER_XC5000) {770 /* Disable the use of DIF */771 772 status = vid_blk_read_word(dev, AFE_CTRL, &value);773 value |= (0 << 13) | (1 << 4);774 value &= ~(1 << 5);775 776 /* set [24:23] [22:15] to 0 */777 value &= (~(0x1FF8000));778 /* set FUNC_MODE[24:23] = 2 IF_MOD[22:15] = 0 */779 value |= 0x1000000;780 status = vid_blk_write_word(dev, AFE_CTRL, value);781 782 status = vid_blk_read_word(dev, OUT_CTRL1, &value);783 value |= (1 << 7);784 status = vid_blk_write_word(dev, OUT_CTRL1, value);785 786 /* Set output mode */787 status = cx231xx_read_modify_write_i2c_dword(dev,788 VID_BLK_I2C_ADDRESS,789 OUT_CTRL1, FLD_OUT_MODE,790 dev->board.output_mode);791 792 /* Tell DIF object to go to baseband mode */793 status = cx231xx_dif_set_standard(dev,794 DIF_USE_BASEBAND);795 if (status < 0) {796 dev_err(dev->dev,797 "%s: cx231xx_dif set to By pass mode- errCode [%d]!\n",798 __func__, status);799 return status;800 }801 802 /* Read the DFE_CTRL1 register */803 status = vid_blk_read_word(dev, DFE_CTRL1, &value);804 805 /* enable the VBI_GATE_EN */806 value |= FLD_VBI_GATE_EN;807 808 /* Enable the auto-VGA enable */809 value |= FLD_VGA_AUTO_EN;810 811 /* Write it back */812 status = vid_blk_write_word(dev, DFE_CTRL1, value);813 814 /* Disable auto config of registers */815 status = cx231xx_read_modify_write_i2c_dword(dev,816 VID_BLK_I2C_ADDRESS,817 MODE_CTRL, FLD_ACFG_DIS,818 cx231xx_set_field(FLD_ACFG_DIS, 1));819 820 /* Set CVBS input mode */821 status = cx231xx_read_modify_write_i2c_dword(dev,822 VID_BLK_I2C_ADDRESS,823 MODE_CTRL, FLD_INPUT_MODE,824 cx231xx_set_field(FLD_INPUT_MODE,825 INPUT_MODE_CVBS_0));826 } else {827 /* Enable the DIF for the tuner */828 829 /* Reinitialize the DIF */830 status = cx231xx_dif_set_standard(dev, dev->norm);831 if (status < 0) {832 dev_err(dev->dev,833 "%s: cx231xx_dif set to By pass mode- errCode [%d]!\n",834 __func__, status);835 return status;836 }837 838 /* Make sure bypass is cleared */839 status = vid_blk_read_word(dev, DIF_MISC_CTRL, &value);840 841 /* Clear the bypass bit */842 value &= ~FLD_DIF_DIF_BYPASS;843 844 /* Enable the use of the DIF block */845 status = vid_blk_write_word(dev, DIF_MISC_CTRL, value);846 847 /* Read the DFE_CTRL1 register */848 status = vid_blk_read_word(dev, DFE_CTRL1, &value);849 850 /* Disable the VBI_GATE_EN */851 value &= ~FLD_VBI_GATE_EN;852 853 /* Enable the auto-VGA enable, AGC, and854 set the skip count to 2 */855 value |= FLD_VGA_AUTO_EN | FLD_AGC_AUTO_EN | 0x00200000;856 857 /* Write it back */858 status = vid_blk_write_word(dev, DFE_CTRL1, value);859 860 /* Wait until AGC locks up */861 msleep(1);862 863 /* Disable the auto-VGA enable AGC */864 value &= ~(FLD_VGA_AUTO_EN);865 866 /* Write it back */867 status = vid_blk_write_word(dev, DFE_CTRL1, value);868 869 /* Enable Polaris B0 AGC output */870 status = vid_blk_read_word(dev, PIN_CTRL, &value);871 value |= (FLD_OEF_AGC_RF) |872 (FLD_OEF_AGC_IFVGA) |873 (FLD_OEF_AGC_IF);874 status = vid_blk_write_word(dev, PIN_CTRL, value);875 876 /* Set output mode */877 status = cx231xx_read_modify_write_i2c_dword(dev,878 VID_BLK_I2C_ADDRESS,879 OUT_CTRL1, FLD_OUT_MODE,880 dev->board.output_mode);881 882 /* Disable auto config of registers */883 status = cx231xx_read_modify_write_i2c_dword(dev,884 VID_BLK_I2C_ADDRESS,885 MODE_CTRL, FLD_ACFG_DIS,886 cx231xx_set_field(FLD_ACFG_DIS, 1));887 888 /* Set CVBS input mode */889 status = cx231xx_read_modify_write_i2c_dword(dev,890 VID_BLK_I2C_ADDRESS,891 MODE_CTRL, FLD_INPUT_MODE,892 cx231xx_set_field(FLD_INPUT_MODE,893 INPUT_MODE_CVBS_0));894 895 /* Set some bits in AFE_CTRL so that channel 2 or 3896 * is ready to receive audio */897 /* Clear clamp for channels 2 and 3 (bit 16-17) */898 /* Clear droop comp (bit 19-20) */899 /* Set VGA_SEL (for audio control) (bit 7-8) */900 status = vid_blk_read_word(dev, AFE_CTRL, &value);901 902 /*Set Func mode:01-DIF 10-baseband 11-YUV*/903 value &= (~(FLD_FUNC_MODE));904 value |= 0x800000;905 906 value |= FLD_VGA_SEL_CH3 | FLD_VGA_SEL_CH2;907 908 status = vid_blk_write_word(dev, AFE_CTRL, value);909 910 if (dev->tuner_type == TUNER_NXP_TDA18271) {911 status = vid_blk_read_word(dev, PIN_CTRL,912 &value);913 status = vid_blk_write_word(dev, PIN_CTRL,914 (value & 0xFFFFFFEF));915 }916 917 break;918 919 }920 break;921 }922 923 /* Set raw VBI mode */924 status = cx231xx_read_modify_write_i2c_dword(dev,925 VID_BLK_I2C_ADDRESS,926 OUT_CTRL1, FLD_VBIHACTRAW_EN,927 cx231xx_set_field(FLD_VBIHACTRAW_EN, 1));928 929 status = vid_blk_read_word(dev, OUT_CTRL1, &value);930 if (value & 0x02) {931 value |= (1 << 19);932 status = vid_blk_write_word(dev, OUT_CTRL1, value);933 }934 935 return status;936}937 938void cx231xx_enable656(struct cx231xx *dev)939{940 u8 temp = 0;941 /*enable TS1 data[0:7] as output to export 656*/942 943 vid_blk_write_byte(dev, TS1_PIN_CTL0, 0xFF);944 945 /*enable TS1 clock as output to export 656*/946 947 vid_blk_read_byte(dev, TS1_PIN_CTL1, &temp);948 temp = temp|0x04;949 950 vid_blk_write_byte(dev, TS1_PIN_CTL1, temp);951}952EXPORT_SYMBOL_GPL(cx231xx_enable656);953 954void cx231xx_disable656(struct cx231xx *dev)955{956 u8 temp = 0;957 958 vid_blk_write_byte(dev, TS1_PIN_CTL0, 0x00);959 960 vid_blk_read_byte(dev, TS1_PIN_CTL1, &temp);961 temp = temp&0xFB;962 963 vid_blk_write_byte(dev, TS1_PIN_CTL1, temp);964}965EXPORT_SYMBOL_GPL(cx231xx_disable656);966 967/*968 * Handle any video-mode specific overrides that are different969 * on a per video standards basis after touching the MODE_CTRL970 * register which resets many values for autodetect971 */972int cx231xx_do_mode_ctrl_overrides(struct cx231xx *dev)973{974 int status = 0;975 976 dev_dbg(dev->dev, "%s: 0x%x\n",977 __func__, (unsigned int)dev->norm);978 979 /* Change the DFE_CTRL3 bp_percent to fix flagging */980 status = vid_blk_write_word(dev, DFE_CTRL3, 0xCD3F0280);981 982 if (dev->norm & (V4L2_STD_NTSC | V4L2_STD_PAL_M)) {983 dev_dbg(dev->dev, "%s: NTSC\n", __func__);984 985 /* Move the close caption lines out of active video,986 adjust the active video start point */987 status = cx231xx_read_modify_write_i2c_dword(dev,988 VID_BLK_I2C_ADDRESS,989 VERT_TIM_CTRL,990 FLD_VBLANK_CNT, 0x18);991 status = cx231xx_read_modify_write_i2c_dword(dev,992 VID_BLK_I2C_ADDRESS,993 VERT_TIM_CTRL,994 FLD_VACTIVE_CNT,995 0x1E7000);996 status = cx231xx_read_modify_write_i2c_dword(dev,997 VID_BLK_I2C_ADDRESS,998 VERT_TIM_CTRL,999 FLD_V656BLANK_CNT,1000 0x1C000000);1001 1002 status = cx231xx_read_modify_write_i2c_dword(dev,1003 VID_BLK_I2C_ADDRESS,1004 HORIZ_TIM_CTRL,1005 FLD_HBLANK_CNT,1006 cx231xx_set_field1007 (FLD_HBLANK_CNT, 0x79));1008 1009 } else if (dev->norm & V4L2_STD_SECAM) {1010 dev_dbg(dev->dev, "%s: SECAM\n", __func__);1011 status = cx231xx_read_modify_write_i2c_dword(dev,1012 VID_BLK_I2C_ADDRESS,1013 VERT_TIM_CTRL,1014 FLD_VBLANK_CNT, 0x20);1015 status = cx231xx_read_modify_write_i2c_dword(dev,1016 VID_BLK_I2C_ADDRESS,1017 VERT_TIM_CTRL,1018 FLD_VACTIVE_CNT,1019 cx231xx_set_field1020 (FLD_VACTIVE_CNT,1021 0x244));1022 status = cx231xx_read_modify_write_i2c_dword(dev,1023 VID_BLK_I2C_ADDRESS,1024 VERT_TIM_CTRL,1025 FLD_V656BLANK_CNT,1026 cx231xx_set_field1027 (FLD_V656BLANK_CNT,1028 0x24));1029 /* Adjust the active video horizontal start point */1030 status = cx231xx_read_modify_write_i2c_dword(dev,1031 VID_BLK_I2C_ADDRESS,1032 HORIZ_TIM_CTRL,1033 FLD_HBLANK_CNT,1034 cx231xx_set_field1035 (FLD_HBLANK_CNT, 0x85));1036 } else {1037 dev_dbg(dev->dev, "%s: PAL\n", __func__);1038 status = cx231xx_read_modify_write_i2c_dword(dev,1039 VID_BLK_I2C_ADDRESS,1040 VERT_TIM_CTRL,1041 FLD_VBLANK_CNT, 0x20);1042 status = cx231xx_read_modify_write_i2c_dword(dev,1043 VID_BLK_I2C_ADDRESS,1044 VERT_TIM_CTRL,1045 FLD_VACTIVE_CNT,1046 cx231xx_set_field1047 (FLD_VACTIVE_CNT,1048 0x244));1049 status = cx231xx_read_modify_write_i2c_dword(dev,1050 VID_BLK_I2C_ADDRESS,1051 VERT_TIM_CTRL,1052 FLD_V656BLANK_CNT,1053 cx231xx_set_field1054 (FLD_V656BLANK_CNT,1055 0x24));1056 /* Adjust the active video horizontal start point */1057 status = cx231xx_read_modify_write_i2c_dword(dev,1058 VID_BLK_I2C_ADDRESS,1059 HORIZ_TIM_CTRL,1060 FLD_HBLANK_CNT,1061 cx231xx_set_field1062 (FLD_HBLANK_CNT, 0x85));1063 1064 }1065 1066 return status;1067}1068 1069int cx231xx_unmute_audio(struct cx231xx *dev)1070{1071 return vid_blk_write_byte(dev, PATH1_VOL_CTL, 0x24);1072}1073EXPORT_SYMBOL_GPL(cx231xx_unmute_audio);1074 1075static int stopAudioFirmware(struct cx231xx *dev)1076{1077 return vid_blk_write_byte(dev, DL_CTL_CONTROL, 0x03);1078}1079 1080static int restartAudioFirmware(struct cx231xx *dev)1081{1082 return vid_blk_write_byte(dev, DL_CTL_CONTROL, 0x13);1083}1084 1085int cx231xx_set_audio_input(struct cx231xx *dev, u8 input)1086{1087 int status = 0;1088 enum AUDIO_INPUT ainput = AUDIO_INPUT_LINE;1089 1090 switch (INPUT(input)->amux) {1091 case CX231XX_AMUX_VIDEO:1092 ainput = AUDIO_INPUT_TUNER_TV;1093 break;1094 case CX231XX_AMUX_LINE_IN:1095 status = cx231xx_i2s_blk_set_audio_input(dev, input);1096 ainput = AUDIO_INPUT_LINE;1097 break;1098 default:1099 break;1100 }1101 1102 status = cx231xx_set_audio_decoder_input(dev, ainput);1103 1104 return status;1105}1106 1107int cx231xx_set_audio_decoder_input(struct cx231xx *dev,1108 enum AUDIO_INPUT audio_input)1109{1110 u32 dwval;1111 int status;1112 u8 gen_ctrl;1113 u32 value = 0;1114 1115 /* Put it in soft reset */1116 status = vid_blk_read_byte(dev, GENERAL_CTL, &gen_ctrl);1117 gen_ctrl |= 1;1118 status = vid_blk_write_byte(dev, GENERAL_CTL, gen_ctrl);1119 1120 switch (audio_input) {1121 case AUDIO_INPUT_LINE:1122 /* setup AUD_IO control from Merlin paralle output */1123 value = cx231xx_set_field(FLD_AUD_CHAN1_SRC,1124 AUD_CHAN_SRC_PARALLEL);1125 status = vid_blk_write_word(dev, AUD_IO_CTRL, value);1126 1127 /* setup input to Merlin, SRC2 connect to AC971128 bypass upsample-by-2, slave mode, sony mode, left justify1129 adr 091c, dat 01000000 */1130 status = vid_blk_read_word(dev, AC97_CTL, &dwval);1131 1132 status = vid_blk_write_word(dev, AC97_CTL,1133 (dwval | FLD_AC97_UP2X_BYPASS));1134 1135 /* select the parallel1 and SRC3 */1136 status = vid_blk_write_word(dev, BAND_OUT_SEL,1137 cx231xx_set_field(FLD_SRC3_IN_SEL, 0x0) |1138 cx231xx_set_field(FLD_SRC3_CLK_SEL, 0x0) |1139 cx231xx_set_field(FLD_PARALLEL1_SRC_SEL, 0x0));1140 1141 /* unmute all, AC97 in, independence mode1142 adr 08d0, data 0x00063073 */1143 status = vid_blk_write_word(dev, DL_CTL, 0x3000001);1144 status = vid_blk_write_word(dev, PATH1_CTL1, 0x00063073);1145 1146 /* set AVC maximum threshold, adr 08d4, dat ffff0024 */1147 status = vid_blk_read_word(dev, PATH1_VOL_CTL, &dwval);1148 status = vid_blk_write_word(dev, PATH1_VOL_CTL,1149 (dwval | FLD_PATH1_AVC_THRESHOLD));1150 1151 /* set SC maximum threshold, adr 08ec, dat ffffb3a3 */1152 status = vid_blk_read_word(dev, PATH1_SC_CTL, &dwval);1153 status = vid_blk_write_word(dev, PATH1_SC_CTL,1154 (dwval | FLD_PATH1_SC_THRESHOLD));1155 break;1156 1157 case AUDIO_INPUT_TUNER_TV:1158 default:1159 status = stopAudioFirmware(dev);1160 /* Setup SRC sources and clocks */1161 status = vid_blk_write_word(dev, BAND_OUT_SEL,1162 cx231xx_set_field(FLD_SRC6_IN_SEL, 0x00) |1163 cx231xx_set_field(FLD_SRC6_CLK_SEL, 0x01) |1164 cx231xx_set_field(FLD_SRC5_IN_SEL, 0x00) |1165 cx231xx_set_field(FLD_SRC5_CLK_SEL, 0x02) |1166 cx231xx_set_field(FLD_SRC4_IN_SEL, 0x02) |1167 cx231xx_set_field(FLD_SRC4_CLK_SEL, 0x03) |1168 cx231xx_set_field(FLD_SRC3_IN_SEL, 0x00) |1169 cx231xx_set_field(FLD_SRC3_CLK_SEL, 0x00) |1170 cx231xx_set_field(FLD_BASEBAND_BYPASS_CTL, 0x00) |1171 cx231xx_set_field(FLD_AC97_SRC_SEL, 0x03) |1172 cx231xx_set_field(FLD_I2S_SRC_SEL, 0x00) |1173 cx231xx_set_field(FLD_PARALLEL2_SRC_SEL, 0x02) |1174 cx231xx_set_field(FLD_PARALLEL1_SRC_SEL, 0x01));1175 1176 /* Setup the AUD_IO control */1177 status = vid_blk_write_word(dev, AUD_IO_CTRL,1178 cx231xx_set_field(FLD_I2S_PORT_DIR, 0x00) |1179 cx231xx_set_field(FLD_I2S_OUT_SRC, 0x00) |1180 cx231xx_set_field(FLD_AUD_CHAN3_SRC, 0x00) |1181 cx231xx_set_field(FLD_AUD_CHAN2_SRC, 0x00) |1182 cx231xx_set_field(FLD_AUD_CHAN1_SRC, 0x03));1183 1184 status = vid_blk_write_word(dev, PATH1_CTL1, 0x1F063870);1185 1186 /* setAudioStandard(_audio_standard); */1187 status = vid_blk_write_word(dev, PATH1_CTL1, 0x00063870);1188 1189 status = restartAudioFirmware(dev);1190 1191 switch (dev->board.tuner_type) {1192 case TUNER_XC5000:1193 /* SIF passthrough at 28.6363 MHz sample rate */1194 status = cx231xx_read_modify_write_i2c_dword(dev,1195 VID_BLK_I2C_ADDRESS,1196 CHIP_CTRL,1197 FLD_SIF_EN,1198 cx231xx_set_field(FLD_SIF_EN, 1));1199 break;1200 case TUNER_NXP_TDA18271:1201 /* Normal mode: SIF passthrough at 14.32 MHz */1202 status = cx231xx_read_modify_write_i2c_dword(dev,1203 VID_BLK_I2C_ADDRESS,1204 CHIP_CTRL,1205 FLD_SIF_EN,1206 cx231xx_set_field(FLD_SIF_EN, 0));1207 break;1208 default:1209 switch (dev->model) { /* i2c device tuners */1210 case CX231XX_BOARD_HAUPPAUGE_930C_HD_1114xx:1211 case CX231XX_BOARD_HAUPPAUGE_935C:1212 case CX231XX_BOARD_HAUPPAUGE_955Q:1213 case CX231XX_BOARD_HAUPPAUGE_975:1214 case CX231XX_BOARD_EVROMEDIA_FULL_HYBRID_FULLHD:1215 /* TODO: Normal mode: SIF passthrough at 14.32 MHz?? */1216 break;1217 default:1218 /* This is just a casual suggestion to people adding1219 new boards in case they use a tuner type we don't1220 currently know about */1221 dev_info(dev->dev,1222 "Unknown tuner type configuring SIF");1223 break;1224 }1225 }1226 break;1227 1228 case AUDIO_INPUT_TUNER_FM:1229 /* use SIF for FM radio1230 setupFM();1231 setAudioStandard(_audio_standard);1232 */1233 break;1234 1235 case AUDIO_INPUT_MUTE:1236 status = vid_blk_write_word(dev, PATH1_CTL1, 0x1F011012);1237 break;1238 }1239 1240 /* Take it out of soft reset */1241 status = vid_blk_read_byte(dev, GENERAL_CTL, &gen_ctrl);1242 gen_ctrl &= ~1;1243 status = vid_blk_write_byte(dev, GENERAL_CTL, gen_ctrl);1244 1245 return status;1246}1247 1248/******************************************************************************1249 * C H I P Specific C O N T R O L functions *1250 ******************************************************************************/1251int cx231xx_init_ctrl_pin_status(struct cx231xx *dev)1252{1253 u32 value;1254 int status = 0;1255 1256 status = vid_blk_read_word(dev, PIN_CTRL, &value);1257 value |= (~dev->board.ctl_pin_status_mask);1258 status = vid_blk_write_word(dev, PIN_CTRL, value);1259 1260 return status;1261}1262 1263int cx231xx_set_agc_analog_digital_mux_select(struct cx231xx *dev,1264 u8 analog_or_digital)1265{1266 int status;1267 1268 /* first set the direction to output */1269 status = cx231xx_set_gpio_direction(dev,1270 dev->board.1271 agc_analog_digital_select_gpio, 1);1272 1273 /* 0 - demod ; 1 - Analog mode */1274 status = cx231xx_set_gpio_value(dev,1275 dev->board.agc_analog_digital_select_gpio,1276 analog_or_digital);1277 1278 if (status < 0)1279 return status;1280 1281 return 0;1282}1283 1284int cx231xx_enable_i2c_port_3(struct cx231xx *dev, bool is_port_3)1285{1286 u8 value[4] = { 0, 0, 0, 0 };1287 int status = 0;1288 bool current_is_port_3;1289 1290 /*1291 * Should this code check dev->port_3_switch_enabled first1292 * to skip unnecessary reading of the register?1293 * If yes, the flag dev->port_3_switch_enabled must be initialized1294 * correctly.1295 */1296 1297 status = cx231xx_read_ctrl_reg(dev, VRT_GET_REGISTER,1298 PWR_CTL_EN, value, 4);1299 if (status < 0)1300 return status;1301 1302 current_is_port_3 = value[0] & I2C_DEMOD_EN ? true : false;1303 1304 /* Just return, if already using the right port */1305 if (current_is_port_3 == is_port_3)1306 return 0;1307 1308 if (is_port_3)1309 value[0] |= I2C_DEMOD_EN;1310 else1311 value[0] &= ~I2C_DEMOD_EN;1312 1313 status = cx231xx_write_ctrl_reg(dev, VRT_SET_REGISTER,1314 PWR_CTL_EN, value, 4);1315 1316 /* remember status of the switch for usage in is_tuner */1317 if (status >= 0)1318 dev->port_3_switch_enabled = is_port_3;1319 1320 return status;1321 1322}1323EXPORT_SYMBOL_GPL(cx231xx_enable_i2c_port_3);1324 1325void update_HH_register_after_set_DIF(struct cx231xx *dev)1326{1327/*1328 u8 status = 0;1329 u32 value = 0;1330 1331 vid_blk_write_word(dev, PIN_CTRL, 0xA0FFF82F);1332 vid_blk_write_word(dev, DIF_MISC_CTRL, 0x0A203F11);1333 vid_blk_write_word(dev, DIF_SRC_PHASE_INC, 0x1BEFBF06);1334 1335 status = vid_blk_read_word(dev, AFE_CTRL_C2HH_SRC_CTRL, &value);1336 vid_blk_write_word(dev, AFE_CTRL_C2HH_SRC_CTRL, 0x4485D390);1337 status = vid_blk_read_word(dev, AFE_CTRL_C2HH_SRC_CTRL, &value);1338*/1339}1340 1341void cx231xx_dump_HH_reg(struct cx231xx *dev)1342{1343 u32 value = 0;1344 u16 i = 0;1345 1346 value = 0x45005390;1347 vid_blk_write_word(dev, 0x104, value);1348 1349 for (i = 0x100; i < 0x140; i++) {1350 vid_blk_read_word(dev, i, &value);1351 dev_dbg(dev->dev, "reg0x%x=0x%x\n", i, value);1352 i = i+3;1353 }1354 1355 for (i = 0x300; i < 0x400; i++) {1356 vid_blk_read_word(dev, i, &value);1357 dev_dbg(dev->dev, "reg0x%x=0x%x\n", i, value);1358 i = i+3;1359 }1360 1361 for (i = 0x400; i < 0x440; i++) {1362 vid_blk_read_word(dev, i, &value);1363 dev_dbg(dev->dev, "reg0x%x=0x%x\n", i, value);1364 i = i+3;1365 }1366 1367 vid_blk_read_word(dev, AFE_CTRL_C2HH_SRC_CTRL, &value);1368 dev_dbg(dev->dev, "AFE_CTRL_C2HH_SRC_CTRL=0x%x\n", value);1369 vid_blk_write_word(dev, AFE_CTRL_C2HH_SRC_CTRL, 0x4485D390);1370 vid_blk_read_word(dev, AFE_CTRL_C2HH_SRC_CTRL, &value);1371 dev_dbg(dev->dev, "AFE_CTRL_C2HH_SRC_CTRL=0x%x\n", value);1372}1373 1374#if 01375static void cx231xx_dump_SC_reg(struct cx231xx *dev)1376{1377 u8 value[4] = { 0, 0, 0, 0 };1378 dev_dbg(dev->dev, "%s!\n", __func__);1379 1380 cx231xx_read_ctrl_reg(dev, VRT_GET_REGISTER, BOARD_CFG_STAT,1381 value, 4);1382 dev_dbg(dev->dev,1383 "reg0x%x=0x%x 0x%x 0x%x 0x%x\n", BOARD_CFG_STAT, value[0],1384 value[1], value[2], value[3]);1385 cx231xx_read_ctrl_reg(dev, VRT_GET_REGISTER, TS_MODE_REG,1386 value, 4);1387 dev_dbg(dev->dev,1388 "reg0x%x=0x%x 0x%x 0x%x 0x%x\n", TS_MODE_REG, value[0],1389 value[1], value[2], value[3]);1390 cx231xx_read_ctrl_reg(dev, VRT_GET_REGISTER, TS1_CFG_REG,1391 value, 4);1392 dev_dbg(dev->dev,1393 "reg0x%x=0x%x 0x%x 0x%x 0x%x\n", TS1_CFG_REG, value[0],1394 value[1], value[2], value[3]);1395 cx231xx_read_ctrl_reg(dev, VRT_GET_REGISTER, TS1_LENGTH_REG,1396 value, 4);1397 dev_dbg(dev->dev,1398 "reg0x%x=0x%x 0x%x 0x%x 0x%x\n", TS1_LENGTH_REG, value[0],1399 value[1], value[2], value[3]);1400 1401 cx231xx_read_ctrl_reg(dev, VRT_GET_REGISTER, TS2_CFG_REG,1402 value, 4);1403 dev_dbg(dev->dev,1404 "reg0x%x=0x%x 0x%x 0x%x 0x%x\n", TS2_CFG_REG, value[0],1405 value[1], value[2], value[3]);1406 cx231xx_read_ctrl_reg(dev, VRT_GET_REGISTER, TS2_LENGTH_REG,1407 value, 4);1408 dev_dbg(dev->dev,1409 "reg0x%x=0x%x 0x%x 0x%x 0x%x\n", TS2_LENGTH_REG, value[0],1410 value[1], value[2], value[3]);1411 cx231xx_read_ctrl_reg(dev, VRT_GET_REGISTER, EP_MODE_SET,1412 value, 4);1413 dev_dbg(dev->dev,1414 "reg0x%x=0x%x 0x%x 0x%x 0x%x\n", EP_MODE_SET, value[0],1415 value[1], value[2], value[3]);1416 cx231xx_read_ctrl_reg(dev, VRT_GET_REGISTER, CIR_PWR_PTN1,1417 value, 4);1418 dev_dbg(dev->dev,1419 "reg0x%x=0x%x 0x%x 0x%x 0x%x\n", CIR_PWR_PTN1, value[0],1420 value[1], value[2], value[3]);1421 1422 cx231xx_read_ctrl_reg(dev, VRT_GET_REGISTER, CIR_PWR_PTN2,1423 value, 4);1424 dev_dbg(dev->dev,1425 "reg0x%x=0x%x 0x%x 0x%x 0x%x\n", CIR_PWR_PTN2, value[0],1426 value[1], value[2], value[3]);1427 cx231xx_read_ctrl_reg(dev, VRT_GET_REGISTER, CIR_PWR_PTN3,1428 value, 4);1429 dev_dbg(dev->dev,1430 "reg0x%x=0x%x 0x%x 0x%x 0x%x\n", CIR_PWR_PTN3, value[0],1431 value[1], value[2], value[3]);1432 cx231xx_read_ctrl_reg(dev, VRT_GET_REGISTER, CIR_PWR_MASK0,1433 value, 4);1434 dev_dbg(dev->dev,1435 "reg0x%x=0x%x 0x%x 0x%x 0x%x\n", CIR_PWR_MASK0, value[0],1436 value[1], value[2], value[3]);1437 cx231xx_read_ctrl_reg(dev, VRT_GET_REGISTER, CIR_PWR_MASK1,1438 value, 4);1439 dev_dbg(dev->dev,1440 "reg0x%x=0x%x 0x%x 0x%x 0x%x\n", CIR_PWR_MASK1, value[0],1441 value[1], value[2], value[3]);1442 1443 cx231xx_read_ctrl_reg(dev, VRT_GET_REGISTER, CIR_PWR_MASK2,1444 value, 4);1445 dev_dbg(dev->dev,1446 "reg0x%x=0x%x 0x%x 0x%x 0x%x\n", CIR_PWR_MASK2, value[0],1447 value[1], value[2], value[3]);1448 cx231xx_read_ctrl_reg(dev, VRT_GET_REGISTER, CIR_GAIN,1449 value, 4);1450 dev_dbg(dev->dev,1451 "reg0x%x=0x%x 0x%x 0x%x 0x%x\n", CIR_GAIN, value[0],1452 value[1], value[2], value[3]);1453 cx231xx_read_ctrl_reg(dev, VRT_GET_REGISTER, CIR_CAR_REG,1454 value, 4);1455 dev_dbg(dev->dev,1456 "reg0x%x=0x%x 0x%x 0x%x 0x%x\n", CIR_CAR_REG, value[0],1457 value[1], value[2], value[3]);1458 cx231xx_read_ctrl_reg(dev, VRT_GET_REGISTER, CIR_OT_CFG1,1459 value, 4);1460 dev_dbg(dev->dev,1461 "reg0x%x=0x%x 0x%x 0x%x 0x%x\n", CIR_OT_CFG1, value[0],1462 value[1], value[2], value[3]);1463 1464 cx231xx_read_ctrl_reg(dev, VRT_GET_REGISTER, CIR_OT_CFG2,1465 value, 4);1466 dev_dbg(dev->dev,1467 "reg0x%x=0x%x 0x%x 0x%x 0x%x\n", CIR_OT_CFG2, value[0],1468 value[1], value[2], value[3]);1469 cx231xx_read_ctrl_reg(dev, VRT_GET_REGISTER, PWR_CTL_EN,1470 value, 4);1471 dev_dbg(dev->dev,1472 "reg0x%x=0x%x 0x%x 0x%x 0x%x\n", PWR_CTL_EN, value[0],1473 value[1], value[2], value[3]);1474}1475#endif1476 1477void cx231xx_Setup_AFE_for_LowIF(struct cx231xx *dev)1478 1479{1480 u8 value = 0;1481 1482 afe_read_byte(dev, ADC_STATUS2_CH3, &value);1483 value = (value & 0xFE)|0x01;1484 afe_write_byte(dev, ADC_STATUS2_CH3, value);1485 1486 afe_read_byte(dev, ADC_STATUS2_CH3, &value);1487 value = (value & 0xFE)|0x00;1488 afe_write_byte(dev, ADC_STATUS2_CH3, value);1489 1490 1491/*1492 config colibri to lo-if mode1493 1494 FIXME: ntf_mode = 2'b00 by default. But set 0x1 would reduce1495 the diff IF input by half,1496 1497 for low-if agc defect1498*/1499 1500 afe_read_byte(dev, ADC_NTF_PRECLMP_EN_CH3, &value);1501 value = (value & 0xFC)|0x00;1502 afe_write_byte(dev, ADC_NTF_PRECLMP_EN_CH3, value);1503 1504 afe_read_byte(dev, ADC_INPUT_CH3, &value);1505 value = (value & 0xF9)|0x02;1506 afe_write_byte(dev, ADC_INPUT_CH3, value);1507 1508 afe_read_byte(dev, ADC_FB_FRCRST_CH3, &value);1509 value = (value & 0xFB)|0x04;1510 afe_write_byte(dev, ADC_FB_FRCRST_CH3, value);1511 1512 afe_read_byte(dev, ADC_DCSERVO_DEM_CH3, &value);1513 value = (value & 0xFC)|0x03;1514 afe_write_byte(dev, ADC_DCSERVO_DEM_CH3, value);1515 1516 afe_read_byte(dev, ADC_CTRL_DAC1_CH3, &value);1517 value = (value & 0xFB)|0x04;1518 afe_write_byte(dev, ADC_CTRL_DAC1_CH3, value);1519 1520 afe_read_byte(dev, ADC_CTRL_DAC23_CH3, &value);1521 value = (value & 0xF8)|0x06;1522 afe_write_byte(dev, ADC_CTRL_DAC23_CH3, value);1523 1524 afe_read_byte(dev, ADC_CTRL_DAC23_CH3, &value);1525 value = (value & 0x8F)|0x40;1526 afe_write_byte(dev, ADC_CTRL_DAC23_CH3, value);1527 1528 afe_read_byte(dev, ADC_PWRDN_CLAMP_CH3, &value);1529 value = (value & 0xDF)|0x20;1530 afe_write_byte(dev, ADC_PWRDN_CLAMP_CH3, value);1531}1532 1533void cx231xx_set_Colibri_For_LowIF(struct cx231xx *dev, u32 if_freq,1534 u8 spectral_invert, u32 mode)1535{1536 u32 colibri_carrier_offset = 0;1537 u32 func_mode = 0x01; /* Device has a DIF if this function is called */1538 u32 standard = 0;1539 u8 value[4] = { 0, 0, 0, 0 };1540 1541 dev_dbg(dev->dev, "Enter cx231xx_set_Colibri_For_LowIF()\n");1542 value[0] = (u8) 0x6F;1543 value[1] = (u8) 0x6F;1544 value[2] = (u8) 0x6F;1545 value[3] = (u8) 0x6F;1546 cx231xx_write_ctrl_reg(dev, VRT_SET_REGISTER,1547 PWR_CTL_EN, value, 4);1548 1549 /*Set colibri for low IF*/1550 cx231xx_afe_set_mode(dev, AFE_MODE_LOW_IF);1551 1552 /* Set C2HH for low IF operation.*/1553 standard = dev->norm;1554 cx231xx_dif_configure_C2HH_for_low_IF(dev, dev->active_mode,1555 func_mode, standard);1556 1557 /* Get colibri offsets.*/1558 colibri_carrier_offset = cx231xx_Get_Colibri_CarrierOffset(mode,1559 standard);1560 1561 dev_dbg(dev->dev, "colibri_carrier_offset=%d, standard=0x%x\n",1562 colibri_carrier_offset, standard);1563 1564 /* Set the band Pass filter for DIF*/1565 cx231xx_set_DIF_bandpass(dev, (if_freq+colibri_carrier_offset),1566 spectral_invert, mode);1567}1568 1569u32 cx231xx_Get_Colibri_CarrierOffset(u32 mode, u32 standerd)1570{1571 u32 colibri_carrier_offset = 0;1572 1573 if (mode == TUNER_MODE_FM_RADIO) {1574 colibri_carrier_offset = 1100000;1575 } else if (standerd & (V4L2_STD_MN | V4L2_STD_NTSC_M_JP)) {1576 colibri_carrier_offset = 4832000; /*4.83MHz */1577 } else if (standerd & (V4L2_STD_PAL_B | V4L2_STD_PAL_G)) {1578 colibri_carrier_offset = 2700000; /*2.70MHz */1579 } else if (standerd & (V4L2_STD_PAL_D | V4L2_STD_PAL_I1580 | V4L2_STD_SECAM)) {1581 colibri_carrier_offset = 2100000; /*2.10MHz */1582 }1583 1584 return colibri_carrier_offset;1585}1586 1587void cx231xx_set_DIF_bandpass(struct cx231xx *dev, u32 if_freq,1588 u8 spectral_invert, u32 mode)1589{1590 unsigned long pll_freq_word;1591 u32 dif_misc_ctrl_value = 0;1592 u64 pll_freq_u64 = 0;1593 u32 i = 0;1594 1595 dev_dbg(dev->dev, "if_freq=%d;spectral_invert=0x%x;mode=0x%x\n",1596 if_freq, spectral_invert, mode);1597 1598 1599 if (mode == TUNER_MODE_FM_RADIO) {1600 pll_freq_word = 0x905A1CAC;1601 vid_blk_write_word(dev, DIF_PLL_FREQ_WORD, pll_freq_word);1602 1603 } else /*KSPROPERTY_TUNER_MODE_TV*/{1604 /* Calculate the PLL frequency word based on the adjusted if_freq*/1605 pll_freq_word = if_freq;1606 pll_freq_u64 = (u64)pll_freq_word << 28L;1607 do_div(pll_freq_u64, 50000000);1608 pll_freq_word = (u32)pll_freq_u64;1609 /*pll_freq_word = 0x3463497;*/1610 vid_blk_write_word(dev, DIF_PLL_FREQ_WORD, pll_freq_word);1611 1612 if (spectral_invert) {1613 if_freq -= 400000;1614 /* Enable Spectral Invert*/1615 vid_blk_read_word(dev, DIF_MISC_CTRL,1616 &dif_misc_ctrl_value);1617 dif_misc_ctrl_value = dif_misc_ctrl_value | 0x00200000;1618 vid_blk_write_word(dev, DIF_MISC_CTRL,1619 dif_misc_ctrl_value);1620 } else {1621 if_freq += 400000;1622 /* Disable Spectral Invert*/1623 vid_blk_read_word(dev, DIF_MISC_CTRL,1624 &dif_misc_ctrl_value);1625 dif_misc_ctrl_value = dif_misc_ctrl_value & 0xFFDFFFFF;1626 vid_blk_write_word(dev, DIF_MISC_CTRL,1627 dif_misc_ctrl_value);1628 }1629 1630 if_freq = (if_freq / 100000) * 100000;1631 1632 if (if_freq < 3000000)1633 if_freq = 3000000;1634 1635 if (if_freq > 16000000)1636 if_freq = 16000000;1637 }1638 1639 dev_dbg(dev->dev, "Enter IF=%zu\n", ARRAY_SIZE(Dif_set_array));1640 for (i = 0; i < ARRAY_SIZE(Dif_set_array); i++) {1641 if (Dif_set_array[i].if_freq == if_freq) {1642 vid_blk_write_word(dev,1643 Dif_set_array[i].register_address, Dif_set_array[i].value);1644 }1645 }1646}1647 1648/******************************************************************************1649 * D I F - B L O C K C O N T R O L functions *1650 ******************************************************************************/1651int cx231xx_dif_configure_C2HH_for_low_IF(struct cx231xx *dev, u32 mode,1652 u32 function_mode, u32 standard)1653{1654 int status = 0;1655 1656 1657 if (mode == V4L2_TUNER_RADIO) {1658 /* C2HH */1659 /* lo if big signal */1660 status = cx231xx_reg_mask_write(dev,1661 VID_BLK_I2C_ADDRESS, 32,1662 AFE_CTRL_C2HH_SRC_CTRL, 30, 31, 0x1);1663 /* FUNC_MODE = DIF */1664 status = cx231xx_reg_mask_write(dev,1665 VID_BLK_I2C_ADDRESS, 32,1666 AFE_CTRL_C2HH_SRC_CTRL, 23, 24, function_mode);1667 /* IF_MODE */1668 status = cx231xx_reg_mask_write(dev,1669 VID_BLK_I2C_ADDRESS, 32,1670 AFE_CTRL_C2HH_SRC_CTRL, 15, 22, 0xFF);1671 /* no inv */1672 status = cx231xx_reg_mask_write(dev,1673 VID_BLK_I2C_ADDRESS, 32,1674 AFE_CTRL_C2HH_SRC_CTRL, 9, 9, 0x1);1675 } else if (standard != DIF_USE_BASEBAND) {1676 if (standard & V4L2_STD_MN) {1677 /* lo if big signal */1678 status = cx231xx_reg_mask_write(dev,1679 VID_BLK_I2C_ADDRESS, 32,1680 AFE_CTRL_C2HH_SRC_CTRL, 30, 31, 0x1);1681 /* FUNC_MODE = DIF */1682 status = cx231xx_reg_mask_write(dev,1683 VID_BLK_I2C_ADDRESS, 32,1684 AFE_CTRL_C2HH_SRC_CTRL, 23, 24,1685 function_mode);1686 /* IF_MODE */1687 status = cx231xx_reg_mask_write(dev,1688 VID_BLK_I2C_ADDRESS, 32,1689 AFE_CTRL_C2HH_SRC_CTRL, 15, 22, 0xb);1690 /* no inv */1691 status = cx231xx_reg_mask_write(dev,1692 VID_BLK_I2C_ADDRESS, 32,1693 AFE_CTRL_C2HH_SRC_CTRL, 9, 9, 0x1);1694 /* 0x124, AUD_CHAN1_SRC = 0x3 */1695 status = cx231xx_reg_mask_write(dev,1696 VID_BLK_I2C_ADDRESS, 32,1697 AUD_IO_CTRL, 0, 31, 0x00000003);1698 } else if ((standard == V4L2_STD_PAL_I) |1699 (standard & V4L2_STD_PAL_D) |1700 (standard & V4L2_STD_SECAM)) {1701 /* C2HH setup */1702 /* lo if big signal */1703 status = cx231xx_reg_mask_write(dev,1704 VID_BLK_I2C_ADDRESS, 32,1705 AFE_CTRL_C2HH_SRC_CTRL, 30, 31, 0x1);1706 /* FUNC_MODE = DIF */1707 status = cx231xx_reg_mask_write(dev,1708 VID_BLK_I2C_ADDRESS, 32,1709 AFE_CTRL_C2HH_SRC_CTRL, 23, 24,1710 function_mode);1711 /* IF_MODE */1712 status = cx231xx_reg_mask_write(dev,1713 VID_BLK_I2C_ADDRESS, 32,1714 AFE_CTRL_C2HH_SRC_CTRL, 15, 22, 0xF);1715 /* no inv */1716 status = cx231xx_reg_mask_write(dev,1717 VID_BLK_I2C_ADDRESS, 32,1718 AFE_CTRL_C2HH_SRC_CTRL, 9, 9, 0x1);1719 } else {1720 /* default PAL BG */1721 /* C2HH setup */1722 /* lo if big signal */1723 status = cx231xx_reg_mask_write(dev,1724 VID_BLK_I2C_ADDRESS, 32,1725 AFE_CTRL_C2HH_SRC_CTRL, 30, 31, 0x1);1726 /* FUNC_MODE = DIF */1727 status = cx231xx_reg_mask_write(dev,1728 VID_BLK_I2C_ADDRESS, 32,1729 AFE_CTRL_C2HH_SRC_CTRL, 23, 24,1730 function_mode);1731 /* IF_MODE */1732 status = cx231xx_reg_mask_write(dev,1733 VID_BLK_I2C_ADDRESS, 32,1734 AFE_CTRL_C2HH_SRC_CTRL, 15, 22, 0xE);1735 /* no inv */1736 status = cx231xx_reg_mask_write(dev,1737 VID_BLK_I2C_ADDRESS, 32,1738 AFE_CTRL_C2HH_SRC_CTRL, 9, 9, 0x1);1739 }1740 }1741 1742 return status;1743}1744 1745int cx231xx_dif_set_standard(struct cx231xx *dev, u32 standard)1746{1747 int status = 0;1748 u32 dif_misc_ctrl_value = 0;1749 u32 func_mode = 0;1750 1751 dev_dbg(dev->dev, "%s: setStandard to %x\n", __func__, standard);1752 1753 status = vid_blk_read_word(dev, DIF_MISC_CTRL, &dif_misc_ctrl_value);1754 if (standard != DIF_USE_BASEBAND)1755 dev->norm = standard;1756 1757 switch (dev->model) {1758 case CX231XX_BOARD_CNXT_CARRAERA:1759 case CX231XX_BOARD_CNXT_RDE_250:1760 case CX231XX_BOARD_CNXT_SHELBY:1761 case CX231XX_BOARD_CNXT_RDU_250:1762 case CX231XX_BOARD_CNXT_VIDEO_GRABBER:1763 case CX231XX_BOARD_HAUPPAUGE_EXETER:1764 case CX231XX_BOARD_OTG102:1765 func_mode = 0x03;1766 break;1767 case CX231XX_BOARD_CNXT_RDE_253S:1768 case CX231XX_BOARD_CNXT_RDU_253S:1769 case CX231XX_BOARD_HAUPPAUGE_USB2_FM_PAL:1770 case CX231XX_BOARD_HAUPPAUGE_USB2_FM_NTSC:1771 func_mode = 0x01;1772 break;1773 default:1774 func_mode = 0x01;1775 }1776 1777 status = cx231xx_dif_configure_C2HH_for_low_IF(dev, dev->active_mode,1778 func_mode, standard);1779 1780 if (standard == DIF_USE_BASEBAND) { /* base band */1781 /* There is a different SRC_PHASE_INC value1782 for baseband vs. DIF */1783 status = vid_blk_write_word(dev, DIF_SRC_PHASE_INC, 0xDF7DF83);1784 status = vid_blk_read_word(dev, DIF_MISC_CTRL,1785 &dif_misc_ctrl_value);1786 dif_misc_ctrl_value |= FLD_DIF_DIF_BYPASS;1787 status = vid_blk_write_word(dev, DIF_MISC_CTRL,1788 dif_misc_ctrl_value);1789 } else if (standard & V4L2_STD_PAL_D) {1790 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1791 DIF_PLL_CTRL, 0, 31, 0x6503bc0c);1792 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1793 DIF_PLL_CTRL1, 0, 31, 0xbd038c85);1794 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1795 DIF_PLL_CTRL2, 0, 31, 0x1db4640a);1796 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1797 DIF_PLL_CTRL3, 0, 31, 0x00008800);1798 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1799 DIF_AGC_IF_REF, 0, 31, 0x444C1380);1800 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1801 DIF_AGC_CTRL_IF, 0, 31, 0xDA302600);1802 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1803 DIF_AGC_CTRL_INT, 0, 31, 0xDA261700);1804 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1805 DIF_AGC_CTRL_RF, 0, 31, 0xDA262600);1806 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1807 DIF_AGC_IF_INT_CURRENT, 0, 31,1808 0x26001700);1809 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1810 DIF_AGC_RF_CURRENT, 0, 31,1811 0x00002660);1812 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1813 DIF_VIDEO_AGC_CTRL, 0, 31,1814 0x72500800);1815 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1816 DIF_VID_AUD_OVERRIDE, 0, 31,1817 0x27000100);1818 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1819 DIF_AV_SEP_CTRL, 0, 31, 0x3F3934EA);1820 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1821 DIF_COMP_FLT_CTRL, 0, 31,1822 0x00000000);1823 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1824 DIF_SRC_PHASE_INC, 0, 31,1825 0x1befbf06);1826 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1827 DIF_SRC_GAIN_CONTROL, 0, 31,1828 0x000035e8);1829 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1830 DIF_RPT_VARIANCE, 0, 31, 0x00000000);1831 /* Save the Spec Inversion value */1832 dif_misc_ctrl_value &= FLD_DIF_SPEC_INV;1833 dif_misc_ctrl_value |= 0x3a023F11;1834 } else if (standard & V4L2_STD_PAL_I) {1835 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1836 DIF_PLL_CTRL, 0, 31, 0x6503bc0c);1837 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1838 DIF_PLL_CTRL1, 0, 31, 0xbd038c85);1839 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1840 DIF_PLL_CTRL2, 0, 31, 0x1db4640a);1841 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1842 DIF_PLL_CTRL3, 0, 31, 0x00008800);1843 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1844 DIF_AGC_IF_REF, 0, 31, 0x444C1380);1845 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1846 DIF_AGC_CTRL_IF, 0, 31, 0xDA302600);1847 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1848 DIF_AGC_CTRL_INT, 0, 31, 0xDA261700);1849 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1850 DIF_AGC_CTRL_RF, 0, 31, 0xDA262600);1851 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1852 DIF_AGC_IF_INT_CURRENT, 0, 31,1853 0x26001700);1854 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1855 DIF_AGC_RF_CURRENT, 0, 31,1856 0x00002660);1857 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1858 DIF_VIDEO_AGC_CTRL, 0, 31,1859 0x72500800);1860 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1861 DIF_VID_AUD_OVERRIDE, 0, 31,1862 0x27000100);1863 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1864 DIF_AV_SEP_CTRL, 0, 31, 0x5F39A934);1865 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1866 DIF_COMP_FLT_CTRL, 0, 31,1867 0x00000000);1868 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1869 DIF_SRC_PHASE_INC, 0, 31,1870 0x1befbf06);1871 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1872 DIF_SRC_GAIN_CONTROL, 0, 31,1873 0x000035e8);1874 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1875 DIF_RPT_VARIANCE, 0, 31, 0x00000000);1876 /* Save the Spec Inversion value */1877 dif_misc_ctrl_value &= FLD_DIF_SPEC_INV;1878 dif_misc_ctrl_value |= 0x3a033F11;1879 } else if (standard & V4L2_STD_PAL_M) {1880 /* improved Low Frequency Phase Noise */1881 status = vid_blk_write_word(dev, DIF_PLL_CTRL, 0xFF01FF0C);1882 status = vid_blk_write_word(dev, DIF_PLL_CTRL1, 0xbd038c85);1883 status = vid_blk_write_word(dev, DIF_PLL_CTRL2, 0x1db4640a);1884 status = vid_blk_write_word(dev, DIF_PLL_CTRL3, 0x00008800);1885 status = vid_blk_write_word(dev, DIF_AGC_IF_REF, 0x444C1380);1886 status = vid_blk_write_word(dev, DIF_AGC_IF_INT_CURRENT,1887 0x26001700);1888 status = vid_blk_write_word(dev, DIF_AGC_RF_CURRENT,1889 0x00002660);1890 status = vid_blk_write_word(dev, DIF_VIDEO_AGC_CTRL,1891 0x72500800);1892 status = vid_blk_write_word(dev, DIF_VID_AUD_OVERRIDE,1893 0x27000100);1894 status = vid_blk_write_word(dev, DIF_AV_SEP_CTRL, 0x012c405d);1895 status = vid_blk_write_word(dev, DIF_COMP_FLT_CTRL,1896 0x009f50c1);1897 status = vid_blk_write_word(dev, DIF_SRC_PHASE_INC,1898 0x1befbf06);1899 status = vid_blk_write_word(dev, DIF_SRC_GAIN_CONTROL,1900 0x000035e8);1901 status = vid_blk_write_word(dev, DIF_SOFT_RST_CTRL_REVB,1902 0x00000000);1903 /* Save the Spec Inversion value */1904 dif_misc_ctrl_value &= FLD_DIF_SPEC_INV;1905 dif_misc_ctrl_value |= 0x3A0A3F10;1906 } else if (standard & (V4L2_STD_PAL_N | V4L2_STD_PAL_Nc)) {1907 /* improved Low Frequency Phase Noise */1908 status = vid_blk_write_word(dev, DIF_PLL_CTRL, 0xFF01FF0C);1909 status = vid_blk_write_word(dev, DIF_PLL_CTRL1, 0xbd038c85);1910 status = vid_blk_write_word(dev, DIF_PLL_CTRL2, 0x1db4640a);1911 status = vid_blk_write_word(dev, DIF_PLL_CTRL3, 0x00008800);1912 status = vid_blk_write_word(dev, DIF_AGC_IF_REF, 0x444C1380);1913 status = vid_blk_write_word(dev, DIF_AGC_IF_INT_CURRENT,1914 0x26001700);1915 status = vid_blk_write_word(dev, DIF_AGC_RF_CURRENT,1916 0x00002660);1917 status = vid_blk_write_word(dev, DIF_VIDEO_AGC_CTRL,1918 0x72500800);1919 status = vid_blk_write_word(dev, DIF_VID_AUD_OVERRIDE,1920 0x27000100);1921 status = vid_blk_write_word(dev, DIF_AV_SEP_CTRL,1922 0x012c405d);1923 status = vid_blk_write_word(dev, DIF_COMP_FLT_CTRL,1924 0x009f50c1);1925 status = vid_blk_write_word(dev, DIF_SRC_PHASE_INC,1926 0x1befbf06);1927 status = vid_blk_write_word(dev, DIF_SRC_GAIN_CONTROL,1928 0x000035e8);1929 status = vid_blk_write_word(dev, DIF_SOFT_RST_CTRL_REVB,1930 0x00000000);1931 /* Save the Spec Inversion value */1932 dif_misc_ctrl_value &= FLD_DIF_SPEC_INV;1933 dif_misc_ctrl_value = 0x3A093F10;1934 } else if (standard &1935 (V4L2_STD_SECAM_B | V4L2_STD_SECAM_D | V4L2_STD_SECAM_G |1936 V4L2_STD_SECAM_K | V4L2_STD_SECAM_K1)) {1937 1938 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1939 DIF_PLL_CTRL, 0, 31, 0x6503bc0c);1940 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1941 DIF_PLL_CTRL1, 0, 31, 0xbd038c85);1942 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1943 DIF_PLL_CTRL2, 0, 31, 0x1db4640a);1944 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1945 DIF_PLL_CTRL3, 0, 31, 0x00008800);1946 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1947 DIF_AGC_IF_REF, 0, 31, 0x888C0380);1948 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1949 DIF_AGC_CTRL_IF, 0, 31, 0xe0262600);1950 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1951 DIF_AGC_CTRL_INT, 0, 31, 0xc2171700);1952 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1953 DIF_AGC_CTRL_RF, 0, 31, 0xc2262600);1954 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1955 DIF_AGC_IF_INT_CURRENT, 0, 31,1956 0x26001700);1957 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1958 DIF_AGC_RF_CURRENT, 0, 31,1959 0x00002660);1960 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1961 DIF_VID_AUD_OVERRIDE, 0, 31,1962 0x27000100);1963 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1964 DIF_AV_SEP_CTRL, 0, 31, 0x3F3530ec);1965 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1966 DIF_COMP_FLT_CTRL, 0, 31,1967 0x00000000);1968 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1969 DIF_SRC_PHASE_INC, 0, 31,1970 0x1befbf06);1971 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1972 DIF_SRC_GAIN_CONTROL, 0, 31,1973 0x000035e8);1974 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1975 DIF_RPT_VARIANCE, 0, 31, 0x00000000);1976 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1977 DIF_VIDEO_AGC_CTRL, 0, 31,1978 0xf4000000);1979 1980 /* Save the Spec Inversion value */1981 dif_misc_ctrl_value &= FLD_DIF_SPEC_INV;1982 dif_misc_ctrl_value |= 0x3a023F11;1983 } else if (standard & (V4L2_STD_SECAM_L | V4L2_STD_SECAM_LC)) {1984 /* Is it SECAM_L1? */1985 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1986 DIF_PLL_CTRL, 0, 31, 0x6503bc0c);1987 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1988 DIF_PLL_CTRL1, 0, 31, 0xbd038c85);1989 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1990 DIF_PLL_CTRL2, 0, 31, 0x1db4640a);1991 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1992 DIF_PLL_CTRL3, 0, 31, 0x00008800);1993 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1994 DIF_AGC_IF_REF, 0, 31, 0x888C0380);1995 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1996 DIF_AGC_CTRL_IF, 0, 31, 0xe0262600);1997 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,1998 DIF_AGC_CTRL_INT, 0, 31, 0xc2171700);1999 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,2000 DIF_AGC_CTRL_RF, 0, 31, 0xc2262600);2001 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,2002 DIF_AGC_IF_INT_CURRENT, 0, 31,2003 0x26001700);2004 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,2005 DIF_AGC_RF_CURRENT, 0, 31,2006 0x00002660);2007 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,2008 DIF_VID_AUD_OVERRIDE, 0, 31,2009 0x27000100);2010 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,2011 DIF_AV_SEP_CTRL, 0, 31, 0x3F3530ec);2012 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,2013 DIF_COMP_FLT_CTRL, 0, 31,2014 0x00000000);2015 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,2016 DIF_SRC_PHASE_INC, 0, 31,2017 0x1befbf06);2018 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,2019 DIF_SRC_GAIN_CONTROL, 0, 31,2020 0x000035e8);2021 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,2022 DIF_RPT_VARIANCE, 0, 31, 0x00000000);2023 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,2024 DIF_VIDEO_AGC_CTRL, 0, 31,2025 0xf2560000);2026 2027 /* Save the Spec Inversion value */2028 dif_misc_ctrl_value &= FLD_DIF_SPEC_INV;2029 dif_misc_ctrl_value |= 0x3a023F11;2030 2031 } else if (standard & V4L2_STD_NTSC_M) {2032 /* V4L2_STD_NTSC_M (75 IRE Setup) Or2033 V4L2_STD_NTSC_M_JP (Japan, 0 IRE Setup) */2034 2035 /* For NTSC the centre frequency of video coming out of2036 sidewinder is around 7.1MHz or 3.6MHz depending on the2037 spectral inversion. so for a non spectrally inverted channel2038 the pll freq word is 0x03420c492039 */2040 2041 status = vid_blk_write_word(dev, DIF_PLL_CTRL, 0x6503BC0C);2042 status = vid_blk_write_word(dev, DIF_PLL_CTRL1, 0xBD038C85);2043 status = vid_blk_write_word(dev, DIF_PLL_CTRL2, 0x1DB4640A);2044 status = vid_blk_write_word(dev, DIF_PLL_CTRL3, 0x00008800);2045 status = vid_blk_write_word(dev, DIF_AGC_IF_REF, 0x444C0380);2046 status = vid_blk_write_word(dev, DIF_AGC_IF_INT_CURRENT,2047 0x26001700);2048 status = vid_blk_write_word(dev, DIF_AGC_RF_CURRENT,2049 0x00002660);2050 status = vid_blk_write_word(dev, DIF_VIDEO_AGC_CTRL,2051 0x04000800);2052 status = vid_blk_write_word(dev, DIF_VID_AUD_OVERRIDE,2053 0x27000100);2054 status = vid_blk_write_word(dev, DIF_AV_SEP_CTRL, 0x01296e1f);2055 2056 status = vid_blk_write_word(dev, DIF_COMP_FLT_CTRL,2057 0x009f50c1);2058 status = vid_blk_write_word(dev, DIF_SRC_PHASE_INC,2059 0x1befbf06);2060 status = vid_blk_write_word(dev, DIF_SRC_GAIN_CONTROL,2061 0x000035e8);2062 2063 status = vid_blk_write_word(dev, DIF_AGC_CTRL_IF, 0xC2262600);2064 status = vid_blk_write_word(dev, DIF_AGC_CTRL_INT,2065 0xC2262600);2066 status = vid_blk_write_word(dev, DIF_AGC_CTRL_RF, 0xC2262600);2067 2068 /* Save the Spec Inversion value */2069 dif_misc_ctrl_value &= FLD_DIF_SPEC_INV;2070 dif_misc_ctrl_value |= 0x3a003F10;2071 } else {2072 /* default PAL BG */2073 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,2074 DIF_PLL_CTRL, 0, 31, 0x6503bc0c);2075 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,2076 DIF_PLL_CTRL1, 0, 31, 0xbd038c85);2077 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,2078 DIF_PLL_CTRL2, 0, 31, 0x1db4640a);2079 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,2080 DIF_PLL_CTRL3, 0, 31, 0x00008800);2081 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,2082 DIF_AGC_IF_REF, 0, 31, 0x444C1380);2083 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,2084 DIF_AGC_CTRL_IF, 0, 31, 0xDA302600);2085 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,2086 DIF_AGC_CTRL_INT, 0, 31, 0xDA261700);2087 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,2088 DIF_AGC_CTRL_RF, 0, 31, 0xDA262600);2089 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,2090 DIF_AGC_IF_INT_CURRENT, 0, 31,2091 0x26001700);2092 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,2093 DIF_AGC_RF_CURRENT, 0, 31,2094 0x00002660);2095 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,2096 DIF_VIDEO_AGC_CTRL, 0, 31,2097 0x72500800);2098 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,2099 DIF_VID_AUD_OVERRIDE, 0, 31,2100 0x27000100);2101 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,2102 DIF_AV_SEP_CTRL, 0, 31, 0x3F3530EC);2103 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,2104 DIF_COMP_FLT_CTRL, 0, 31,2105 0x00A653A8);2106 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,2107 DIF_SRC_PHASE_INC, 0, 31,2108 0x1befbf06);2109 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,2110 DIF_SRC_GAIN_CONTROL, 0, 31,2111 0x000035e8);2112 status = cx231xx_reg_mask_write(dev, VID_BLK_I2C_ADDRESS, 32,2113 DIF_RPT_VARIANCE, 0, 31, 0x00000000);2114 /* Save the Spec Inversion value */2115 dif_misc_ctrl_value &= FLD_DIF_SPEC_INV;2116 dif_misc_ctrl_value |= 0x3a013F11;2117 }2118 2119 /* The AGC values should be the same for all standards,2120 AUD_SRC_SEL[19] should always be disabled */2121 dif_misc_ctrl_value &= ~FLD_DIF_AUD_SRC_SEL;2122 2123 /* It is still possible to get Set Standard calls even when we2124 are in FM mode.2125 This is done to override the value for FM. */2126 if (dev->active_mode == V4L2_TUNER_RADIO)2127 dif_misc_ctrl_value = 0x7a080000;2128 2129 /* Write the calculated value for misc ontrol register */2130 status = vid_blk_write_word(dev, DIF_MISC_CTRL, dif_misc_ctrl_value);2131 2132 return status;2133}2134 2135int cx231xx_tuner_pre_channel_change(struct cx231xx *dev)2136{2137 int status = 0;2138 u32 dwval;2139 2140 /* Set the RF and IF k_agc values to 3 */2141 status = vid_blk_read_word(dev, DIF_AGC_IF_REF, &dwval);2142 dwval &= ~(FLD_DIF_K_AGC_RF | FLD_DIF_K_AGC_IF);2143 dwval |= 0x33000000;2144 2145 status = vid_blk_write_word(dev, DIF_AGC_IF_REF, dwval);2146 2147 return status;2148}2149 2150int cx231xx_tuner_post_channel_change(struct cx231xx *dev)2151{2152 int status = 0;2153 u32 dwval;2154 dev_dbg(dev->dev, "%s: dev->tuner_type =0%d\n",2155 __func__, dev->tuner_type);2156 /* Set the RF and IF k_agc values to 4 for PAL/NTSC and 8 for2157 * SECAM L/B/D standards */2158 status = vid_blk_read_word(dev, DIF_AGC_IF_REF, &dwval);2159 dwval &= ~(FLD_DIF_K_AGC_RF | FLD_DIF_K_AGC_IF);2160 2161 if (dev->norm & (V4L2_STD_SECAM_L | V4L2_STD_SECAM_B |2162 V4L2_STD_SECAM_D)) {2163 if (dev->tuner_type == TUNER_NXP_TDA18271) {2164 dwval &= ~FLD_DIF_IF_REF;2165 dwval |= 0x88000300;2166 } else2167 dwval |= 0x88000000;2168 } else {2169 if (dev->tuner_type == TUNER_NXP_TDA18271) {2170 dwval &= ~FLD_DIF_IF_REF;2171 dwval |= 0xCC000300;2172 } else2173 dwval |= 0x44000000;2174 }2175 2176 status = vid_blk_write_word(dev, DIF_AGC_IF_REF, dwval);2177 2178 return status == sizeof(dwval) ? 0 : -EIO;2179}2180 2181/******************************************************************************2182 * I 2 S - B L O C K C O N T R O L functions *2183 ******************************************************************************/2184int cx231xx_i2s_blk_initialize(struct cx231xx *dev)2185{2186 int status = 0;2187 u32 value;2188 2189 status = cx231xx_read_i2c_data(dev, I2S_BLK_DEVICE_ADDRESS,2190 CH_PWR_CTRL1, 1, &value, 1);2191 /* enables clock to delta-sigma and decimation filter */2192 value |= 0x80;2193 status = cx231xx_write_i2c_data(dev, I2S_BLK_DEVICE_ADDRESS,2194 CH_PWR_CTRL1, 1, value, 1);2195 /* power up all channel */2196 status = cx231xx_write_i2c_data(dev, I2S_BLK_DEVICE_ADDRESS,2197 CH_PWR_CTRL2, 1, 0x00, 1);2198 2199 return status;2200}2201 2202int cx231xx_i2s_blk_update_power_control(struct cx231xx *dev,2203 enum AV_MODE avmode)2204{2205 int status = 0;2206 u32 value = 0;2207 2208 if (avmode != POLARIS_AVMODE_ENXTERNAL_AV) {2209 status = cx231xx_read_i2c_data(dev, I2S_BLK_DEVICE_ADDRESS,2210 CH_PWR_CTRL2, 1, &value, 1);2211 value |= 0xfe;2212 status = cx231xx_write_i2c_data(dev, I2S_BLK_DEVICE_ADDRESS,2213 CH_PWR_CTRL2, 1, value, 1);2214 } else {2215 status = cx231xx_write_i2c_data(dev, I2S_BLK_DEVICE_ADDRESS,2216 CH_PWR_CTRL2, 1, 0x00, 1);2217 }2218 2219 return status;2220}2221 2222/* set i2s_blk for audio input types */2223int cx231xx_i2s_blk_set_audio_input(struct cx231xx *dev, u8 audio_input)2224{2225 int status = 0;2226 2227 switch (audio_input) {2228 case CX231XX_AMUX_LINE_IN:2229 status = cx231xx_write_i2c_data(dev, I2S_BLK_DEVICE_ADDRESS,2230 CH_PWR_CTRL2, 1, 0x00, 1);2231 status = cx231xx_write_i2c_data(dev, I2S_BLK_DEVICE_ADDRESS,2232 CH_PWR_CTRL1, 1, 0x80, 1);2233 break;2234 case CX231XX_AMUX_VIDEO:2235 default:2236 break;2237 }2238 2239 dev->ctl_ainput = audio_input;2240 2241 return status;2242}2243 2244/******************************************************************************2245 * P O W E R C O N T R O L functions *2246 ******************************************************************************/2247int cx231xx_set_power_mode(struct cx231xx *dev, enum AV_MODE mode)2248{2249 u8 value[4] = { 0, 0, 0, 0 };2250 u32 tmp = 0;2251 int status = 0;2252 2253 if (dev->power_mode != mode)2254 dev->power_mode = mode;2255 else {2256 dev_dbg(dev->dev, "%s: mode = %d, No Change req.\n",2257 __func__, mode);2258 return 0;2259 }2260 2261 status = cx231xx_read_ctrl_reg(dev, VRT_GET_REGISTER, PWR_CTL_EN, value,2262 4);2263 if (status < 0)2264 return status;2265 2266 tmp = le32_to_cpu(*((__le32 *) value));2267 2268 switch (mode) {2269 case POLARIS_AVMODE_ENXTERNAL_AV:2270 2271 tmp &= (~PWR_MODE_MASK);2272 2273 tmp |= PWR_AV_EN;2274 value[0] = (u8) tmp;2275 value[1] = (u8) (tmp >> 8);2276 value[2] = (u8) (tmp >> 16);2277 value[3] = (u8) (tmp >> 24);2278 status = cx231xx_write_ctrl_reg(dev, VRT_SET_REGISTER,2279 PWR_CTL_EN, value, 4);2280 msleep(PWR_SLEEP_INTERVAL);2281 2282 tmp |= PWR_ISO_EN;2283 value[0] = (u8) tmp;2284 value[1] = (u8) (tmp >> 8);2285 value[2] = (u8) (tmp >> 16);2286 value[3] = (u8) (tmp >> 24);2287 status =2288 cx231xx_write_ctrl_reg(dev, VRT_SET_REGISTER, PWR_CTL_EN,2289 value, 4);2290 msleep(PWR_SLEEP_INTERVAL);2291 2292 tmp |= POLARIS_AVMODE_ENXTERNAL_AV;2293 value[0] = (u8) tmp;2294 value[1] = (u8) (tmp >> 8);2295 value[2] = (u8) (tmp >> 16);2296 value[3] = (u8) (tmp >> 24);2297 status = cx231xx_write_ctrl_reg(dev, VRT_SET_REGISTER,2298 PWR_CTL_EN, value, 4);2299 2300 /* reset state of xceive tuner */2301 dev->xc_fw_load_done = 0;2302 break;2303 2304 case POLARIS_AVMODE_ANALOGT_TV:2305 2306 tmp |= PWR_DEMOD_EN;2307 value[0] = (u8) tmp;2308 value[1] = (u8) (tmp >> 8);2309 value[2] = (u8) (tmp >> 16);2310 value[3] = (u8) (tmp >> 24);2311 status = cx231xx_write_ctrl_reg(dev, VRT_SET_REGISTER,2312 PWR_CTL_EN, value, 4);2313 msleep(PWR_SLEEP_INTERVAL);2314 2315 if (!(tmp & PWR_TUNER_EN)) {2316 tmp |= (PWR_TUNER_EN);2317 value[0] = (u8) tmp;2318 value[1] = (u8) (tmp >> 8);2319 value[2] = (u8) (tmp >> 16);2320 value[3] = (u8) (tmp >> 24);2321 status = cx231xx_write_ctrl_reg(dev, VRT_SET_REGISTER,2322 PWR_CTL_EN, value, 4);2323 msleep(PWR_SLEEP_INTERVAL);2324 }2325 2326 if (!(tmp & PWR_AV_EN)) {2327 tmp |= PWR_AV_EN;2328 value[0] = (u8) tmp;2329 value[1] = (u8) (tmp >> 8);2330 value[2] = (u8) (tmp >> 16);2331 value[3] = (u8) (tmp >> 24);2332 status = cx231xx_write_ctrl_reg(dev, VRT_SET_REGISTER,2333 PWR_CTL_EN, value, 4);2334 msleep(PWR_SLEEP_INTERVAL);2335 }2336 if (!(tmp & PWR_ISO_EN)) {2337 tmp |= PWR_ISO_EN;2338 value[0] = (u8) tmp;2339 value[1] = (u8) (tmp >> 8);2340 value[2] = (u8) (tmp >> 16);2341 value[3] = (u8) (tmp >> 24);2342 status = cx231xx_write_ctrl_reg(dev, VRT_SET_REGISTER,2343 PWR_CTL_EN, value, 4);2344 msleep(PWR_SLEEP_INTERVAL);2345 }2346 2347 if (!(tmp & POLARIS_AVMODE_ANALOGT_TV)) {2348 tmp |= POLARIS_AVMODE_ANALOGT_TV;2349 value[0] = (u8) tmp;2350 value[1] = (u8) (tmp >> 8);2351 value[2] = (u8) (tmp >> 16);2352 value[3] = (u8) (tmp >> 24);2353 status = cx231xx_write_ctrl_reg(dev, VRT_SET_REGISTER,2354 PWR_CTL_EN, value, 4);2355 msleep(PWR_SLEEP_INTERVAL);2356 }2357 2358 if (dev->board.tuner_type != TUNER_ABSENT) {2359 /* reset the Tuner */2360 if (dev->board.tuner_gpio)2361 cx231xx_gpio_set(dev, dev->board.tuner_gpio);2362 2363 if (dev->cx231xx_reset_analog_tuner)2364 dev->cx231xx_reset_analog_tuner(dev);2365 }2366 2367 break;2368 2369 case POLARIS_AVMODE_DIGITAL:2370 if (!(tmp & PWR_TUNER_EN)) {2371 tmp |= (PWR_TUNER_EN);2372 value[0] = (u8) tmp;2373 value[1] = (u8) (tmp >> 8);2374 value[2] = (u8) (tmp >> 16);2375 value[3] = (u8) (tmp >> 24);2376 status = cx231xx_write_ctrl_reg(dev, VRT_SET_REGISTER,2377 PWR_CTL_EN, value, 4);2378 msleep(PWR_SLEEP_INTERVAL);2379 }2380 if (!(tmp & PWR_AV_EN)) {2381 tmp |= PWR_AV_EN;2382 value[0] = (u8) tmp;2383 value[1] = (u8) (tmp >> 8);2384 value[2] = (u8) (tmp >> 16);2385 value[3] = (u8) (tmp >> 24);2386 status = cx231xx_write_ctrl_reg(dev, VRT_SET_REGISTER,2387 PWR_CTL_EN, value, 4);2388 msleep(PWR_SLEEP_INTERVAL);2389 }2390 if (!(tmp & PWR_ISO_EN)) {2391 tmp |= PWR_ISO_EN;2392 value[0] = (u8) tmp;2393 value[1] = (u8) (tmp >> 8);2394 value[2] = (u8) (tmp >> 16);2395 value[3] = (u8) (tmp >> 24);2396 status = cx231xx_write_ctrl_reg(dev, VRT_SET_REGISTER,2397 PWR_CTL_EN, value, 4);2398 msleep(PWR_SLEEP_INTERVAL);2399 }2400 2401 tmp &= (~PWR_AV_MODE);2402 tmp |= POLARIS_AVMODE_DIGITAL;2403 value[0] = (u8) tmp;2404 value[1] = (u8) (tmp >> 8);2405 value[2] = (u8) (tmp >> 16);2406 value[3] = (u8) (tmp >> 24);2407 status = cx231xx_write_ctrl_reg(dev, VRT_SET_REGISTER,2408 PWR_CTL_EN, value, 4);2409 msleep(PWR_SLEEP_INTERVAL);2410 2411 if (!(tmp & PWR_DEMOD_EN)) {2412 tmp |= PWR_DEMOD_EN;2413 value[0] = (u8) tmp;2414 value[1] = (u8) (tmp >> 8);2415 value[2] = (u8) (tmp >> 16);2416 value[3] = (u8) (tmp >> 24);2417 status = cx231xx_write_ctrl_reg(dev, VRT_SET_REGISTER,2418 PWR_CTL_EN, value, 4);2419 msleep(PWR_SLEEP_INTERVAL);2420 }2421 2422 if (dev->board.tuner_type != TUNER_ABSENT) {2423 /* reset the Tuner */2424 if (dev->board.tuner_gpio)2425 cx231xx_gpio_set(dev, dev->board.tuner_gpio);2426 2427 if (dev->cx231xx_reset_analog_tuner)2428 dev->cx231xx_reset_analog_tuner(dev);2429 }2430 break;2431 2432 default:2433 break;2434 }2435 2436 msleep(PWR_SLEEP_INTERVAL);2437 2438 /* For power saving, only enable Pwr_resetout_n2439 when digital TV is selected. */2440 if (mode == POLARIS_AVMODE_DIGITAL) {2441 tmp |= PWR_RESETOUT_EN;2442 value[0] = (u8) tmp;2443 value[1] = (u8) (tmp >> 8);2444 value[2] = (u8) (tmp >> 16);2445 value[3] = (u8) (tmp >> 24);2446 status = cx231xx_write_ctrl_reg(dev, VRT_SET_REGISTER,2447 PWR_CTL_EN, value, 4);2448 msleep(PWR_SLEEP_INTERVAL);2449 }2450 2451 /* update power control for afe */2452 status = cx231xx_afe_update_power_control(dev, mode);2453 2454 /* update power control for i2s_blk */2455 status = cx231xx_i2s_blk_update_power_control(dev, mode);2456 2457 status = cx231xx_read_ctrl_reg(dev, VRT_GET_REGISTER, PWR_CTL_EN, value,2458 4);2459 2460 return status;2461}2462 2463int cx231xx_power_suspend(struct cx231xx *dev)2464{2465 u8 value[4] = { 0, 0, 0, 0 };2466 u32 tmp = 0;2467 int status = 0;2468 2469 status = cx231xx_read_ctrl_reg(dev, VRT_GET_REGISTER, PWR_CTL_EN,2470 value, 4);2471 if (status > 0)2472 return status;2473 2474 tmp = le32_to_cpu(*((__le32 *) value));2475 tmp &= (~PWR_MODE_MASK);2476 2477 value[0] = (u8) tmp;2478 value[1] = (u8) (tmp >> 8);2479 value[2] = (u8) (tmp >> 16);2480 value[3] = (u8) (tmp >> 24);2481 status = cx231xx_write_ctrl_reg(dev, VRT_SET_REGISTER, PWR_CTL_EN,2482 value, 4);2483 2484 return status;2485}2486 2487/******************************************************************************2488 * S T R E A M C O N T R O L functions *2489 ******************************************************************************/2490int cx231xx_start_stream(struct cx231xx *dev, u32 ep_mask)2491{2492 u8 value[4] = { 0x0, 0x0, 0x0, 0x0 };2493 u32 tmp = 0;2494 int status = 0;2495 2496 dev_dbg(dev->dev, "%s: ep_mask = %x\n", __func__, ep_mask);2497 status = cx231xx_read_ctrl_reg(dev, VRT_GET_REGISTER, EP_MODE_SET,2498 value, 4);2499 if (status < 0)2500 return status;2501 2502 tmp = le32_to_cpu(*((__le32 *) value));2503 tmp |= ep_mask;2504 value[0] = (u8) tmp;2505 value[1] = (u8) (tmp >> 8);2506 value[2] = (u8) (tmp >> 16);2507 value[3] = (u8) (tmp >> 24);2508 2509 status = cx231xx_write_ctrl_reg(dev, VRT_SET_REGISTER, EP_MODE_SET,2510 value, 4);2511 2512 return status;2513}2514 2515int cx231xx_stop_stream(struct cx231xx *dev, u32 ep_mask)2516{2517 u8 value[4] = { 0x0, 0x0, 0x0, 0x0 };2518 u32 tmp = 0;2519 int status = 0;2520 2521 dev_dbg(dev->dev, "%s: ep_mask = %x\n", __func__, ep_mask);2522 status =2523 cx231xx_read_ctrl_reg(dev, VRT_GET_REGISTER, EP_MODE_SET, value, 4);2524 if (status < 0)2525 return status;2526 2527 tmp = le32_to_cpu(*((__le32 *) value));2528 tmp &= (~ep_mask);2529 value[0] = (u8) tmp;2530 value[1] = (u8) (tmp >> 8);2531 value[2] = (u8) (tmp >> 16);2532 value[3] = (u8) (tmp >> 24);2533 2534 status = cx231xx_write_ctrl_reg(dev, VRT_SET_REGISTER, EP_MODE_SET,2535 value, 4);2536 2537 return status;2538}2539 2540int cx231xx_initialize_stream_xfer(struct cx231xx *dev, u32 media_type)2541{2542 int status = 0;2543 u32 value = 0;2544 u8 val[4] = { 0, 0, 0, 0 };2545 2546 if (dev->udev->speed == USB_SPEED_HIGH) {2547 switch (media_type) {2548 case Audio:2549 dev_dbg(dev->dev,2550 "%s: Audio enter HANC\n", __func__);2551 status =2552 cx231xx_mode_register(dev, TS_MODE_REG, 0x9300);2553 break;2554 2555 case Vbi:2556 dev_dbg(dev->dev,2557 "%s: set vanc registers\n", __func__);2558 status = cx231xx_mode_register(dev, TS_MODE_REG, 0x300);2559 break;2560 2561 case Sliced_cc:2562 dev_dbg(dev->dev,2563 "%s: set hanc registers\n", __func__);2564 status =2565 cx231xx_mode_register(dev, TS_MODE_REG, 0x1300);2566 break;2567 2568 case Raw_Video:2569 dev_dbg(dev->dev,2570 "%s: set video registers\n", __func__);2571 status = cx231xx_mode_register(dev, TS_MODE_REG, 0x100);2572 break;2573 2574 case TS1_serial_mode:2575 dev_dbg(dev->dev,2576 "%s: set ts1 registers", __func__);2577 2578 if (dev->board.has_417) {2579 dev_dbg(dev->dev,2580 "%s: MPEG\n", __func__);2581 value &= 0xFFFFFFFC;2582 value |= 0x3;2583 2584 status = cx231xx_mode_register(dev,2585 TS_MODE_REG, value);2586 2587 val[0] = 0x04;2588 val[1] = 0xA3;2589 val[2] = 0x3B;2590 val[3] = 0x00;2591 status = cx231xx_write_ctrl_reg(dev,2592 VRT_SET_REGISTER,2593 TS1_CFG_REG, val, 4);2594 2595 val[0] = 0x00;2596 val[1] = 0x08;2597 val[2] = 0x00;2598 val[3] = 0x08;2599 status = cx231xx_write_ctrl_reg(dev,2600 VRT_SET_REGISTER,2601 TS1_LENGTH_REG, val, 4);2602 } else {2603 dev_dbg(dev->dev, "%s: BDA\n", __func__);2604 status = cx231xx_mode_register(dev,2605 TS_MODE_REG, 0x101);2606 status = cx231xx_mode_register(dev,2607 TS1_CFG_REG, 0x010);2608 }2609 break;2610 2611 case TS1_parallel_mode:2612 dev_dbg(dev->dev,2613 "%s: set ts1 parallel mode registers\n",2614 __func__);2615 status = cx231xx_mode_register(dev, TS_MODE_REG, 0x100);2616 status = cx231xx_mode_register(dev, TS1_CFG_REG, 0x400);2617 break;2618 }2619 } else {2620 status = cx231xx_mode_register(dev, TS_MODE_REG, 0x101);2621 }2622 2623 return status;2624}2625 2626int cx231xx_capture_start(struct cx231xx *dev, int start, u8 media_type)2627{2628 int rc = -1;2629 u32 ep_mask = -1;2630 struct pcb_config *pcb_config;2631 2632 /* get EP for media type */2633 pcb_config = (struct pcb_config *)&dev->current_pcb_config;2634 2635 if (pcb_config->config_num) {2636 switch (media_type) {2637 case Raw_Video:2638 ep_mask = ENABLE_EP4; /* ep4 [00:1000] */2639 break;2640 case Audio:2641 ep_mask = ENABLE_EP3; /* ep3 [00:0100] */2642 break;2643 case Vbi:2644 ep_mask = ENABLE_EP5; /* ep5 [01:0000] */2645 break;2646 case Sliced_cc:2647 ep_mask = ENABLE_EP6; /* ep6 [10:0000] */2648 break;2649 case TS1_serial_mode:2650 case TS1_parallel_mode:2651 ep_mask = ENABLE_EP1; /* ep1 [00:0001] */2652 break;2653 case TS2:2654 ep_mask = ENABLE_EP2; /* ep2 [00:0010] */2655 break;2656 }2657 }2658 2659 if (start) {2660 rc = cx231xx_initialize_stream_xfer(dev, media_type);2661 2662 if (rc < 0)2663 return rc;2664 2665 /* enable video capture */2666 if (ep_mask > 0)2667 rc = cx231xx_start_stream(dev, ep_mask);2668 } else {2669 /* disable video capture */2670 if (ep_mask > 0)2671 rc = cx231xx_stop_stream(dev, ep_mask);2672 }2673 2674 return rc;2675}2676EXPORT_SYMBOL_GPL(cx231xx_capture_start);2677 2678/*****************************************************************************2679* G P I O B I T control functions *2680******************************************************************************/2681static int cx231xx_set_gpio_bit(struct cx231xx *dev, u32 gpio_bit, u32 gpio_val)2682{2683 int status = 0;2684 2685 gpio_val = (__force u32)cpu_to_le32(gpio_val);2686 status = cx231xx_send_gpio_cmd(dev, gpio_bit, (u8 *)&gpio_val, 4, 0, 0);2687 2688 return status;2689}2690 2691static int cx231xx_get_gpio_bit(struct cx231xx *dev, u32 gpio_bit, u32 *gpio_val)2692{2693 __le32 tmp;2694 int status = 0;2695 2696 status = cx231xx_send_gpio_cmd(dev, gpio_bit, (u8 *)&tmp, 4, 0, 1);2697 *gpio_val = le32_to_cpu(tmp);2698 2699 return status;2700}2701 2702/*2703* cx231xx_set_gpio_direction2704* Sets the direction of the GPIO pin to input or output2705*2706* Parameters :2707* pin_number : The GPIO Pin number to program the direction for2708* from 0 to 312709* pin_value : The Direction of the GPIO Pin under reference.2710* 0 = Input direction2711* 1 = Output direction2712*/2713int cx231xx_set_gpio_direction(struct cx231xx *dev,2714 int pin_number, int pin_value)2715{2716 int status = 0;2717 u32 value = 0;2718 2719 /* Check for valid pin_number - if 32 , bail out */2720 if (pin_number >= 32)2721 return -EINVAL;2722 2723 /* input */2724 if (pin_value == 0)2725 value = dev->gpio_dir & (~(1 << pin_number)); /* clear */2726 else2727 value = dev->gpio_dir | (1 << pin_number);2728 2729 status = cx231xx_set_gpio_bit(dev, value, dev->gpio_val);2730 2731 /* cache the value for future */2732 dev->gpio_dir = value;2733 2734 return status;2735}2736 2737/*2738* cx231xx_set_gpio_value2739* Sets the value of the GPIO pin to Logic high or low. The Pin under2740* reference should ALREADY BE SET IN OUTPUT MODE !!!!!!!!!2741*2742* Parameters :2743* pin_number : The GPIO Pin number to program the direction for2744* pin_value : The value of the GPIO Pin under reference.2745* 0 = set it to 02746* 1 = set it to 12747*/2748int cx231xx_set_gpio_value(struct cx231xx *dev, int pin_number, int pin_value)2749{2750 int status = 0;2751 u32 value = 0;2752 2753 /* Check for valid pin_number - if 0xFF , bail out */2754 if (pin_number >= 32)2755 return -EINVAL;2756 2757 /* first do a sanity check - if the Pin is not output, make it output */2758 if ((dev->gpio_dir & (1 << pin_number)) == 0x00) {2759 /* It was in input mode */2760 value = dev->gpio_dir | (1 << pin_number);2761 dev->gpio_dir = value;2762 status = cx231xx_set_gpio_bit(dev, dev->gpio_dir,2763 dev->gpio_val);2764 value = 0;2765 }2766 2767 if (pin_value == 0)2768 value = dev->gpio_val & (~(1 << pin_number));2769 else2770 value = dev->gpio_val | (1 << pin_number);2771 2772 /* store the value */2773 dev->gpio_val = value;2774 2775 /* toggle bit0 of GP_IO */2776 status = cx231xx_set_gpio_bit(dev, dev->gpio_dir, dev->gpio_val);2777 2778 return status;2779}2780 2781/*****************************************************************************2782* G P I O I2C related functions *2783******************************************************************************/2784int cx231xx_gpio_i2c_start(struct cx231xx *dev)2785{2786 int status = 0;2787 2788 /* set SCL to output 1 ; set SDA to output 1 */2789 dev->gpio_dir |= 1 << dev->board.tuner_scl_gpio;2790 dev->gpio_dir |= 1 << dev->board.tuner_sda_gpio;2791 dev->gpio_val |= 1 << dev->board.tuner_scl_gpio;2792 dev->gpio_val |= 1 << dev->board.tuner_sda_gpio;2793 2794 status = cx231xx_set_gpio_bit(dev, dev->gpio_dir, dev->gpio_val);2795 if (status < 0)2796 return -EINVAL;2797 2798 /* set SCL to output 1; set SDA to output 0 */2799 dev->gpio_val |= 1 << dev->board.tuner_scl_gpio;2800 dev->gpio_val &= ~(1 << dev->board.tuner_sda_gpio);2801 2802 status = cx231xx_set_gpio_bit(dev, dev->gpio_dir, dev->gpio_val);2803 if (status < 0)2804 return -EINVAL;2805 2806 /* set SCL to output 0; set SDA to output 0 */2807 dev->gpio_val &= ~(1 << dev->board.tuner_scl_gpio);2808 dev->gpio_val &= ~(1 << dev->board.tuner_sda_gpio);2809 2810 status = cx231xx_set_gpio_bit(dev, dev->gpio_dir, dev->gpio_val);2811 if (status < 0)2812 return -EINVAL;2813 2814 return status;2815}2816 2817int cx231xx_gpio_i2c_end(struct cx231xx *dev)2818{2819 int status = 0;2820 2821 /* set SCL to output 0; set SDA to output 0 */2822 dev->gpio_dir |= 1 << dev->board.tuner_scl_gpio;2823 dev->gpio_dir |= 1 << dev->board.tuner_sda_gpio;2824 2825 dev->gpio_val &= ~(1 << dev->board.tuner_scl_gpio);2826 dev->gpio_val &= ~(1 << dev->board.tuner_sda_gpio);2827 2828 status = cx231xx_set_gpio_bit(dev, dev->gpio_dir, dev->gpio_val);2829 if (status < 0)2830 return -EINVAL;2831 2832 /* set SCL to output 1; set SDA to output 0 */2833 dev->gpio_val |= 1 << dev->board.tuner_scl_gpio;2834 dev->gpio_val &= ~(1 << dev->board.tuner_sda_gpio);2835 2836 status = cx231xx_set_gpio_bit(dev, dev->gpio_dir, dev->gpio_val);2837 if (status < 0)2838 return -EINVAL;2839 2840 /* set SCL to input ,release SCL cable control2841 set SDA to input ,release SDA cable control */2842 dev->gpio_dir &= ~(1 << dev->board.tuner_scl_gpio);2843 dev->gpio_dir &= ~(1 << dev->board.tuner_sda_gpio);2844 2845 status =2846 cx231xx_set_gpio_bit(dev, dev->gpio_dir, dev->gpio_val);2847 if (status < 0)2848 return -EINVAL;2849 2850 return status;2851}2852 2853int cx231xx_gpio_i2c_write_byte(struct cx231xx *dev, u8 data)2854{2855 int status = 0;2856 u8 i;2857 2858 /* set SCL to output ; set SDA to output */2859 dev->gpio_dir |= 1 << dev->board.tuner_scl_gpio;2860 dev->gpio_dir |= 1 << dev->board.tuner_sda_gpio;2861 2862 for (i = 0; i < 8; i++) {2863 if (((data << i) & 0x80) == 0) {2864 /* set SCL to output 0; set SDA to output 0 */2865 dev->gpio_val &= ~(1 << dev->board.tuner_scl_gpio);2866 dev->gpio_val &= ~(1 << dev->board.tuner_sda_gpio);2867 status = cx231xx_set_gpio_bit(dev, dev->gpio_dir,2868 dev->gpio_val);2869 2870 /* set SCL to output 1; set SDA to output 0 */2871 dev->gpio_val |= 1 << dev->board.tuner_scl_gpio;2872 status = cx231xx_set_gpio_bit(dev, dev->gpio_dir,2873 dev->gpio_val);2874 2875 /* set SCL to output 0; set SDA to output 0 */2876 dev->gpio_val &= ~(1 << dev->board.tuner_scl_gpio);2877 status = cx231xx_set_gpio_bit(dev, dev->gpio_dir,2878 dev->gpio_val);2879 } else {2880 /* set SCL to output 0; set SDA to output 1 */2881 dev->gpio_val &= ~(1 << dev->board.tuner_scl_gpio);2882 dev->gpio_val |= 1 << dev->board.tuner_sda_gpio;2883 status = cx231xx_set_gpio_bit(dev, dev->gpio_dir,2884 dev->gpio_val);2885 2886 /* set SCL to output 1; set SDA to output 1 */2887 dev->gpio_val |= 1 << dev->board.tuner_scl_gpio;2888 status = cx231xx_set_gpio_bit(dev, dev->gpio_dir,2889 dev->gpio_val);2890 2891 /* set SCL to output 0; set SDA to output 1 */2892 dev->gpio_val &= ~(1 << dev->board.tuner_scl_gpio);2893 status = cx231xx_set_gpio_bit(dev, dev->gpio_dir,2894 dev->gpio_val);2895 }2896 }2897 return status;2898}2899 2900int cx231xx_gpio_i2c_read_byte(struct cx231xx *dev, u8 *buf)2901{2902 u8 value = 0;2903 int status = 0;2904 u32 gpio_logic_value = 0;2905 u8 i;2906 2907 /* read byte */2908 for (i = 0; i < 8; i++) { /* send write I2c addr */2909 2910 /* set SCL to output 0; set SDA to input */2911 dev->gpio_val &= ~(1 << dev->board.tuner_scl_gpio);2912 status = cx231xx_set_gpio_bit(dev, dev->gpio_dir,2913 dev->gpio_val);2914 2915 /* set SCL to output 1; set SDA to input */2916 dev->gpio_val |= 1 << dev->board.tuner_scl_gpio;2917 status = cx231xx_set_gpio_bit(dev, dev->gpio_dir,2918 dev->gpio_val);2919 2920 /* get SDA data bit */2921 gpio_logic_value = dev->gpio_val;2922 status = cx231xx_get_gpio_bit(dev, dev->gpio_dir,2923 &dev->gpio_val);2924 if ((dev->gpio_val & (1 << dev->board.tuner_sda_gpio)) != 0)2925 value |= (1 << (8 - i - 1));2926 2927 dev->gpio_val = gpio_logic_value;2928 }2929 2930 /* set SCL to output 0,finish the read latest SCL signal.2931 !!!set SDA to input, never to modify SDA direction at2932 the same times */2933 dev->gpio_val &= ~(1 << dev->board.tuner_scl_gpio);2934 status = cx231xx_set_gpio_bit(dev, dev->gpio_dir, dev->gpio_val);2935 2936 /* store the value */2937 *buf = value & 0xff;2938 2939 return status;2940}2941 2942int cx231xx_gpio_i2c_read_ack(struct cx231xx *dev)2943{2944 int status = 0;2945 u32 gpio_logic_value = 0;2946 int nCnt = 10;2947 int nInit = nCnt;2948 2949 /* clock stretch; set SCL to input; set SDA to input;2950 get SCL value till SCL = 1 */2951 dev->gpio_dir &= ~(1 << dev->board.tuner_sda_gpio);2952 dev->gpio_dir &= ~(1 << dev->board.tuner_scl_gpio);2953 2954 gpio_logic_value = dev->gpio_val;2955 status = cx231xx_set_gpio_bit(dev, dev->gpio_dir, dev->gpio_val);2956 2957 do {2958 msleep(2);2959 status = cx231xx_get_gpio_bit(dev, dev->gpio_dir,2960 &dev->gpio_val);2961 nCnt--;2962 } while (((dev->gpio_val &2963 (1 << dev->board.tuner_scl_gpio)) == 0) &&2964 (nCnt > 0));2965 2966 if (nCnt == 0)2967 dev_dbg(dev->dev,2968 "No ACK after %d msec -GPIO I2C failed!",2969 nInit * 10);2970 2971 /*2972 * readAck2973 * through clock stretch, slave has given a SCL signal,2974 * so the SDA data can be directly read.2975 */2976 status = cx231xx_get_gpio_bit(dev, dev->gpio_dir, &dev->gpio_val);2977 2978 if ((dev->gpio_val & 1 << dev->board.tuner_sda_gpio) == 0) {2979 dev->gpio_val = gpio_logic_value;2980 dev->gpio_val &= ~(1 << dev->board.tuner_sda_gpio);2981 status = 0;2982 } else {2983 dev->gpio_val = gpio_logic_value;2984 dev->gpio_val |= (1 << dev->board.tuner_sda_gpio);2985 }2986 2987 /* read SDA end, set the SCL to output 0, after this operation,2988 SDA direction can be changed. */2989 dev->gpio_val = gpio_logic_value;2990 dev->gpio_dir |= (1 << dev->board.tuner_scl_gpio);2991 dev->gpio_val &= ~(1 << dev->board.tuner_scl_gpio);2992 status = cx231xx_set_gpio_bit(dev, dev->gpio_dir, dev->gpio_val);2993 2994 return status;2995}2996 2997int cx231xx_gpio_i2c_write_ack(struct cx231xx *dev)2998{2999 int status = 0;3000 3001 /* set SDA to output */3002 dev->gpio_dir |= 1 << dev->board.tuner_sda_gpio;3003 status = cx231xx_set_gpio_bit(dev, dev->gpio_dir, dev->gpio_val);3004 3005 /* set SCL = 0 (output); set SDA = 0 (output) */3006 dev->gpio_val &= ~(1 << dev->board.tuner_sda_gpio);3007 dev->gpio_val &= ~(1 << dev->board.tuner_scl_gpio);3008 status = cx231xx_set_gpio_bit(dev, dev->gpio_dir, dev->gpio_val);3009 3010 /* set SCL = 1 (output); set SDA = 0 (output) */3011 dev->gpio_val |= 1 << dev->board.tuner_scl_gpio;3012 status = cx231xx_set_gpio_bit(dev, dev->gpio_dir, dev->gpio_val);3013 3014 /* set SCL = 0 (output); set SDA = 0 (output) */3015 dev->gpio_val &= ~(1 << dev->board.tuner_scl_gpio);3016 status = cx231xx_set_gpio_bit(dev, dev->gpio_dir, dev->gpio_val);3017 3018 /* set SDA to input,and then the slave will read data from SDA. */3019 dev->gpio_dir &= ~(1 << dev->board.tuner_sda_gpio);3020 status = cx231xx_set_gpio_bit(dev, dev->gpio_dir, dev->gpio_val);3021 3022 return status;3023}3024 3025int cx231xx_gpio_i2c_write_nak(struct cx231xx *dev)3026{3027 int status = 0;3028 3029 /* set scl to output ; set sda to input */3030 dev->gpio_dir |= 1 << dev->board.tuner_scl_gpio;3031 dev->gpio_dir &= ~(1 << dev->board.tuner_sda_gpio);3032 status = cx231xx_set_gpio_bit(dev, dev->gpio_dir, dev->gpio_val);3033 3034 /* set scl to output 0; set sda to input */3035 dev->gpio_val &= ~(1 << dev->board.tuner_scl_gpio);3036 status = cx231xx_set_gpio_bit(dev, dev->gpio_dir, dev->gpio_val);3037 3038 /* set scl to output 1; set sda to input */3039 dev->gpio_val |= 1 << dev->board.tuner_scl_gpio;3040 status = cx231xx_set_gpio_bit(dev, dev->gpio_dir, dev->gpio_val);3041 3042 return status;3043}3044 3045/*****************************************************************************3046* G P I O I2C related functions *3047******************************************************************************/3048/* cx231xx_gpio_i2c_read3049 * Function to read data from gpio based I2C interface3050 */3051int cx231xx_gpio_i2c_read(struct cx231xx *dev, u8 dev_addr, u8 *buf, u8 len)3052{3053 int status = 0;3054 int i = 0;3055 3056 /* get the lock */3057 mutex_lock(&dev->gpio_i2c_lock);3058 3059 /* start */3060 status = cx231xx_gpio_i2c_start(dev);3061 3062 /* write dev_addr */3063 status = cx231xx_gpio_i2c_write_byte(dev, (dev_addr << 1) + 1);3064 3065 /* readAck */3066 status = cx231xx_gpio_i2c_read_ack(dev);3067 3068 /* read data */3069 for (i = 0; i < len; i++) {3070 /* read data */3071 buf[i] = 0;3072 status = cx231xx_gpio_i2c_read_byte(dev, &buf[i]);3073 3074 if ((i + 1) != len) {3075 /* only do write ack if we more length */3076 status = cx231xx_gpio_i2c_write_ack(dev);3077 }3078 }3079 3080 /* write NAK - inform reads are complete */3081 status = cx231xx_gpio_i2c_write_nak(dev);3082 3083 /* write end */3084 status = cx231xx_gpio_i2c_end(dev);3085 3086 /* release the lock */3087 mutex_unlock(&dev->gpio_i2c_lock);3088 3089 return status;3090}3091 3092/* cx231xx_gpio_i2c_write3093 * Function to write data to gpio based I2C interface3094 */3095int cx231xx_gpio_i2c_write(struct cx231xx *dev, u8 dev_addr, u8 *buf, u8 len)3096{3097 int i = 0;3098 3099 /* get the lock */3100 mutex_lock(&dev->gpio_i2c_lock);3101 3102 /* start */3103 cx231xx_gpio_i2c_start(dev);3104 3105 /* write dev_addr */3106 cx231xx_gpio_i2c_write_byte(dev, dev_addr << 1);3107 3108 /* read Ack */3109 cx231xx_gpio_i2c_read_ack(dev);3110 3111 for (i = 0; i < len; i++) {3112 /* Write data */3113 cx231xx_gpio_i2c_write_byte(dev, buf[i]);3114 3115 /* read Ack */3116 cx231xx_gpio_i2c_read_ack(dev);3117 }3118 3119 /* write End */3120 cx231xx_gpio_i2c_end(dev);3121 3122 /* release the lock */3123 mutex_unlock(&dev->gpio_i2c_lock);3124 3125 return 0;3126}3127