📄 dcf_api.c
字号:
/* STV0297 noise estimation must be filtered. The used filter is:
Estimation(n) = 63/64*Estimation(n-1) + 1/64*NoiseEstimation */
for(i=0; i<100; i++)
{
dcf_get_noise_accumulator(pNim, &u16Temp);
pNim->cne_mean = (pNim->cne_mean * 63 + (signed long)(u16Temp)) >> 6;
}
n32ComputedMean = pNim->cne_mean - pNim->cne_offset;
n32CurrentMean = gn32ST0CN[u8ModType][0];
n8D = 1;
while(n8D < 40)
{
n32OldMean = n32CurrentMean;
n32CurrentMean = gn32ST0CN[u8ModType][n8D];
if(n32CurrentMean <= n32ComputedMean)
{
break;
}
else
{
n8D++;
}
}
pNim->cne = n8D;
return(True);
}
/*****************************************************************************/
/* FUNCTION: dcf_get_qam_size */
/* */
/* PARAMETERS: pNim - pointer to DCF_NIM struct. */
/* */
/* DESCRIPTION: The function gets the QAM mode */
/* by reading the MODE_SELECT bits of EQU_0 register. */
/* */
/* RETURNS: True if successful, False if unsuccessful. */
/* */
/* CONTEXT: Must be called from a non-interrupt context. */
/* */
/*****************************************************************************/
bool dcf_get_qam_size (DCF_NIM *pNim)
{
unsigned char u8RegData;
bool bRetVal;
/* Get QAM size */
bRetVal = DCF_RegRead(pNim, gDemReg[ST0_RID_EQU_0].addr, 1,
(unsigned char*)&u8RegData, DCF_DEMOD_I2C);
if(bRetVal == False)
return(False);
gDemReg[ST0_RID_EQU_0].value = u8RegData;
u8RegData = ((gDemReg[ST0_RID_EQU_0].value & 0x70) >> 4);
/* save QAM size to DCF struct */
pNim->mod_type = u8RegData;
return(True);
}
/*****************************************************************************/
/* FUNCTION: dcf_get_noise_accumulator */
/* */
/* PARAMETERS: pNim - pointer to DCF_NIM struct. */
/* puData - the pointer to the return data. */
/* */
/* DESCRIPTION: The function gets the 16-bit noise estimation accumulator */
/* by reading the EQU_7 & EQU_8 registers. */
/* */
/* RETURNS: True if successful, False if unsuccessful. */
/* */
/* CONTEXT: Must be called from a non-interrupt context. */
/* */
/*****************************************************************************/
bool dcf_get_noise_accumulator(DCF_NIM *pNim, unsigned short *pu16Data)
{
unsigned short u16Temp;
unsigned char u8RegData;
bool bRetVal;
/* sanity check */
if(pNim == NULL)
return(False);
/* read ST0_RID_EQU_7 */
bRetVal = DCF_RegRead(pNim, gDemReg[ST0_RID_EQU_7].addr, 1,
&u8RegData, DCF_DEMOD_I2C);
if(bRetVal == False)
return(False);
gDemReg[ST0_RID_EQU_7].value = u8RegData;
u16Temp = (unsigned short)(u8RegData);
/* read ST0_RID_EQU_8 */
bRetVal = DCF_RegRead(pNim, gDemReg[ST0_RID_EQU_8].addr, 1,
&u8RegData, DCF_DEMOD_I2C);
if(bRetVal == False)
return(False);
gDemReg[ST0_RID_EQU_8].value = u8RegData;
u16Temp = u16Temp + ((unsigned short)(u8RegData << 8));
*pu16Data = u16Temp;
return(True);
}
/*****************************************************************************/
/* FUNCTION: dcf_get_bert */
/* */
/* PARAMETERS: pNim - pointer to DCF_NIM struct. */
/* */
/* DESCRIPTION: The function calculates the current BER. */
/* */
/* RETURNS: True if successful, False if unsuccessful. */
/* */
/* CONTEXT: Must be called from a non-interrupt context. */
/* */
/*****************************************************************************/
bool dcf_get_bert(DCF_NIM *pNim)
{
/* sanity check */
if(pNim == NULL)
return(False);
if(pNim->bert_wait == 0)
{
/* start the BERT */
DCF_DRIVER_Start_BERT(pNim);
pNim->bert_wait = 1;
}
else
{
/* check whether the BERT is stoped. */
DCF_DRIVER_Get_Bert_Status(pNim, &(pNim->bert_status));
if((pNim->bert_status & 0x80) == 0x00)
{
/* get the BER error counter */
/* ber(dividen/divisor) is stored in pNim */
DCF_DRIVER_Get_BER_Error(pNim);
pNim->bert_wait = 0;
}
}
return(True);
}
/*****************************************************************************/
/* FUNCTION: dcf_get_strength */
/* */
/* PARAMETERS: pNim - pointer to DCF_NIM struct. */
/* */
/* DESCRIPTION: The function calculates the current BER. */
/* */
/* RETURNS: True if successful, False if unsuccessful. */
/* */
/* CONTEXT: Must be called from a non-interrupt context. */
/* */
/*****************************************************************************/
bool dcf_get_strength(DCF_NIM *pNim)
{
/* sanity check */
if(pNim == NULL)
return(False);
/* get the current WBAGC agc2sd value. */
DCF_DRIVER_WBAGC_Get_Agc2Sd(pNim, &(pNim->agc2_sd));
/* according to the WBAGC agc2sd value, to estimate the signal strength. */
if(pNim->agc2_sd <= 460) /* > 75 dBuV --- strong signal */
{
pNim->signal_strength = 255;
}
else if(pNim->agc2_sd <= 520) /* > 35 dBuV --- 255 to 75 */
{
pNim->signal_strength = 255 - (pNim->agc2_sd - 460) * 3;
}
else if(pNim->agc2_sd < 670) /* < 35 dBuV --- weak signal */
{
pNim->signal_strength = 75 - ((pNim->agc2_sd - 520) >> 1);
}
else if(pNim->agc2_sd >= 670) /* no signal or very weak signal */
{
pNim->signal_strength = 0;
}
return(True);
}
/*****************************************************************************/
/* FUNCTION: dcf_init_statics */
/* */
/* PARAMETERS: pNim - pointer to DCF_NIM struct. */
/* */
/* DESCRIPTION: The function get the parameters of the current tuning. */
/* */
/* RETURNS: True if successful, False if unsuccessful. */
/* */
/* CONTEXT: Must be called from a non-interrupt context. */
/* */
/*****************************************************************************/
bool dcf_init_statics(DCF_NIM *pNim)
{
/* sanity check */
if(pNim == NULL)
return(False);
/* start the block counts */
DCF_DRIVER_Start_CT(pNim);
pNim->cne = 0;
pNim->bert_wait = 0;
return (True);
}
/*****************************************************************************/
/* FUNCTION: dcf_set_outputformat */
/* */
/* PARAMETERS: pNim - pointer to DCF_NIM struct. */
/* pTsOutFormat - pointer to OUTFORMAT struct */
/* */
/* DESCRIPTION: The function re-initializes THOMSON Cable Front-End DCF8722 */
/* */
/* RETURNS: True if successful, False if unsuccessful. */
/* */
/* CONTEXT: Must be called from a non-interrupt context. */
/* */
/*****************************************************************************/
bool dcf_set_outputformat(DCF_NIM *pNim, DCF_TS_OUT *pTsOutFormat)
{
unsigned char u8RegData;
bool bRetVal;
/* sanity check */
if((pNim == NULL) || (pTsOutFormat == NULL))
return(False);
/* verify/set the output mode */
switch(pTsOutFormat->TsOutMode)
{
case DCF_PARALLEL_OUT:
{
/* set 0xC0[2] to 0 if parallel */
gDemReg[ST0_RID_OUTFORMAT_0].value = gDemReg[ST0_RID_OUTFORMAT_0].value & 0xFB;
break;
}
case DCF_SERIAL_OUT:
{
/* set 0xC0[2] to 1 if serial */
gDemReg[ST0_RID_OUTFORMAT_0].value = gDemReg[ST0_RID_OUTFORMAT_0].value | 0x04;
break;
}
case DCF_OUTMODE_UNDEF:
default:
{
/* passed parameter was invalid, flag and bail */
return(False);
break;
}
} /* switch(... */
/* set clock polarity */
switch(pTsOutFormat->TsClkPar)
{
case DCF_FALLING_EDGE:
{
/* set 0xC0[4] to 0 if falling edge */
gDemReg[ST0_RID_OUTFORMAT_0].value = gDemReg[ST0_RID_OUTFORMAT_0].value & 0xEF;
break;
}
case DCF_RISING_EDGE:
{
/* set 0xC0[4] to 1 if rising edge */
gDemReg[ST0_RID_OUTFORMAT_0].value = gDemReg[ST0_RID_OUTFORMAT_0].value | 0x10;
break;
}
case DCF_CLKPAR_UNDEF:
default:
{
/* passed parameter was invalid, flag and bail */
return(False);
break;
}
} /* switch(... */
/* set clock gating */
switch(pTsOutFormat->TsClkGatting)
{
case DCF_CLK_GATTING_OFF:
{
/* set 0xC0[3] to 1 if continuous clock */
gDemReg[ST0_RID_OUTFORMAT_0].value = gDemReg[ST0_RID_OUTFORMAT_0].value | 0x08;
break;
}
case DCF_CLK_GATTING_ON:
{
/* set 0xC0[3] to 0 if uncontinuous clock */
gDemReg[ST0_RID_OUTFORMAT_0].value = gDemReg[ST0_RID_OUTFORMAT_0].value & 0xF7;
break;
}
case DCF_CLKGATTING_UNDEF:
default:
{
/* passed parameter was invalid, flag and bail */
return(False);
break;
}
} /* switch(... */
/* set MPEG TEI */
switch(pTsOutFormat->TsTei)
{
case DCF_TS_TEI_ON:
{
/* set 0xC0[2] to 1 if TEI mode */
gDemReg[ST0_RID_OUTFORMAT_0].value = gDemReg[ST0_RID_OUTFORMAT_0].value | 0x02;
break;
}
case DCF_TS_TEI_OFF:
{
/* set 0xC0[2] to 0 if not TEI mode */
gDemReg[ST0_RID_OUTFORMAT_0].value = gDemReg[ST0_RID_OUTFORMAT_0].value & 0xFD;
break;
}
case DCF_CLKGATTING_UNDEF:
default:
{
/* passed parameter was invalid, flag and bail */
return(False);
break;
}
} /* switch(... */
/* OUT format is set */
u8RegData = gDemReg[ST0_RID_OUTFORMAT_0].value;
/*debug_out(TL_ALWAYS, "DCF: 0xC0=%2X\n", u8RegData);*/
gDemReg[ST0_RID_OUTFORMAT_0].start = gDemReg[ST0_RID_OUTFORMAT_0].value;
bRetVal = DCF_RegWrite(pNim, gDemReg[ST0_RID_OUTFORMAT_0].addr, 1, &u8RegData, DCF_DEMOD_I2C);
return(bRetVal);
}
/*****************************************************************************/
/* FUNCTION: dcf_init_acq */
/* */
/* PARAMETERS: pNim - pointer to DCF_NIM struct. */
/* pTsOutFormat - pointer to OUTFORMAT struct */
/* */
/* DESCRIPTION: The function re-initializes THOMSON Cable Front-End DCF8722 */
/* */
/* RETURNS: True if successful, False if unsuccessful. */
/* */
/* CONTEXT: Must be called from a non-interrupt context. */
/* */
/*****************************************************************************/
bool dcf_init_acq(DCF_NIM *pNim)
{
/* sanity check */
if(pNim == NULL)
return(False);
/* initialization */
pNim->symbol_rate = 0;
pNim->pll_frequency = pNim->freq_ideal;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -