📄 drv0299.c
字号:
For each authorized inner code, the Viterbi search time is calculated,
and the results are cumulated in ViterbiSearch.
*/
DSS_Mode = (STTUNER_IOREG_FieldExtractVal(R0299_FECMVal, F0299_FECMODE) == 0x04);
for(loop = 0; loop < 5; loop++)
{
if ( ((Er >> loop)& 0x01) == 0x01 )
{
switch(loop)
{
case 0: /* inner code 1/2 */
InnerCode = 2000; /* 2.0 */
break;
case 1: /* inner code 2/3 */
InnerCode = 1500; /* 1.5 */
break;
case 2: /* inner code 3/4 */
InnerCode = 1333; /* 1.333 */
break;
case 3: /* inner code 5/6 */
InnerCode = 1200; /* 1.2 */
break;
case 4: /* inner code 7/8 */
InnerCode = 1143; /* 1.143 */
break;
}
if(!DSS_Mode)
Tviterbi +=(int)((PhaseNumberDVB[loop]*averaging[Sn]*InnerCode)/SymbolRate);
else
Tviterbi +=(int)((PhaseNumberDSS[loop]*averaging[Sn]*InnerCode)/SymbolRate);
if(HigherRate < InnerCode) HigherRate = InnerCode;
}
} /* for(loop) */
/* time out calculation (TimeOut) This value indicates the maximum duration of the synchro word research. */
TimeOut = (int)((HigherRate * 16384L * ((long)To + 1))/(2*SymbolRate)); /* cast To to long (eliminate compiler warning --SFS */
/* Hysteresis duration (Hysteresis) */
THysteresis = (int)((HigherRate * 26112L * ((long)Hy +1))/(2*SymbolRate)); /* 26112= 16*204*8 bits */ /* cast Hy to long (eliminate compiler warning --SFS */
/* a guard time of 1 mS is added */
return (1 + Tviterbi + TimeOut + THysteresis);
}
#endif
#ifndef STTUNER_MINIDRIVER
/*----------------------------------------------------
FUNCTION InitParams
ACTION Set Params fields that are never changed during search algorithm
PARAMS IN NONE
PARAMS OUT NONE
RETURN NONE
------------------------------------------------------*/
void Drv0299_InitParams(STTUNER_IOREG_DeviceMap_t *DeviceMap, IOARCH_Handle_t IOHandle, D0299_StateBlock_t *StateBlock)
{
#ifdef STTUNER_DEBUG_MODULE_SATDRV_DRV0299
const char *identity = "STTUNER drv0299.c Drv0299_InitParams()";
#endif
int stdby, dirclk, k, m, p, m1, betaagc1, agc2coef, MasterClock;
U8 rcr[2],agcr[2],agc1c;
/* Read registers (in burst mode) */
STTUNER_IOREG_GetContigousRegisters(DeviceMap, IOHandle, R0299_RCR, 2,rcr); /* Read RCR and MCR registers */
agc1c = (DeviceMap, IOHandle, R0299_AGC1C); /* Read AGC1C register */
STTUNER_IOREG_GetContigousRegisters(DeviceMap, IOHandle, R0299_AGC1R, 2,agcr); /* Read AGC1R and AGC2O registers */
/* Get fields values */
stdby = STTUNER_IOREG_FieldExtractVal(rcr[1], F0299_STDBY);
dirclk = STTUNER_IOREG_FieldExtractVal(rcr[0], F0299_DIRCLK);
k = STTUNER_IOREG_FieldExtractVal(rcr[0], F0299_K);
m = STTUNER_IOREG_FieldExtractVal(rcr[0], F0299_M);
p = STTUNER_IOREG_FieldExtractVal(rcr[1], F0299_P);
m1 = STTUNER_IOREG_FieldExtractVal(agcr[0], F0299_AGC1_REF);
betaagc1 = STTUNER_IOREG_FieldExtractVal(agc1c, F0299_BETA_AGC1);
agc2coef = STTUNER_IOREG_FieldExtractVal(agcr[1], F0299_AGC2COEF);
/* Initial calculations */ /* cast to match parameter type --SFS */
MasterClock = (int)Reg0299_CalcMasterClkFrequency(DeviceMap, stdby, dirclk, k, m, p);
#ifdef STTUNER_DEBUG_MODULE_SATDRV_DRV0299
STTBX_Print(("%s MasterClock = %d, Mclk = %d\n", identity, MasterClock, MasterClock/65536L));
#endif
StateBlock->Params.Tagc1 = (int)( Reg0299_CalcAGC1TimeConstant(m1, MasterClock, betaagc1)/ 20L); /* cast to match parameter type --SFS */
StateBlock->Params.Tagc2 = (int)( Reg0299_CalcAGC2TimeConstant(agc2coef, m1, MasterClock) / 1000000L); /* cast to match parameter type --SFS */
StateBlock->Params.MasterClock = MasterClock;
StateBlock->Params.Mclk = MasterClock/65536L;
StateBlock->Params.RollOff = Reg0299_GetRollOff(DeviceMap, IOHandle);
/* Added defensive check against Mclk == 0 to avoid potential
divide by zero exceptions throughout the code. In practice
Mclk should never equal zero - if it does, something
seriously bad has happened! In the event that Mclk is
zero at this point we reset it to 1 to ensure
driver computations involving Mclk do not produce
exceptions.
*/
if (StateBlock->Params.Mclk == 0) StateBlock->Params.Mclk = 1; /* Serious error - reset to avoid exceptions */
}
#endif
#ifndef STTUNER_MINIDRIVER
/*----------------------------------------------------
FUNCTION InitSearch
ACTION Set Params fields that are used by the search algorithm
PARAMS IN Frequency => Frequency used to start zig zag
SymbolRate => searched symbol rate
SearchRange => Range of the search
DerotStep => Size of derotator's steps used in the carrier search (in per thousand of symbol frequency)
PARAMS OUT NONE
RETURN NONE
------------------------------------------------------*/
void Drv0299_InitSearch(STTUNER_tuner_instance_t *TunerInstance, D0299_StateBlock_t *StateBlock, int Frequency, int SymbolRate, int SearchRange, int DerotStep)
{
U32 BandWidth;
ST_ErrorCode_t Error;
TUNER_Status_t TunerStatus;
/* Obtain current tuner status */
Error = (TunerInstance->Driver->tuner_GetStatus)(TunerInstance->DrvHandle, &TunerStatus);
/* Select closest bandwidth for tuner */ /* cast to U32 type to match function argument & eliminate compiler warning --SFS */
Error = (TunerInstance->Driver->tuner_SetBandWidth)( TunerInstance->DrvHandle,
(U32)( Drv0299_CarrierWidth(SymbolRate, StateBlock->Params.RollOff) /1000 + 12000),/* set bandwidth some more to optimize scanning->GNBvd26185*/
&BandWidth);
StateBlock->Params.Frequency = Frequency;
StateBlock->Params.SymbolRate = SymbolRate;
if(SearchRange < 10000000)
{
StateBlock->Params.SearchRange = 10000000;
}
else
{
StateBlock->Params.SearchRange = SearchRange;
}
StateBlock->Params.DerotPercent = DerotStep;
StateBlock->Params.TunerBW = (long)BandWidth * 1000; /* cast from U32 to long to eliminate compiler warning --SFS */
StateBlock->Params.TunerStep = (long)TunerStatus.TunerStep;
StateBlock->Params.TunerIF = (long)TunerStatus.IntermediateFrequency;
StateBlock->Params.TunerIQSense = (long)TunerStatus.IQSense;
StateBlock->Result.SignalType = E299_NOAGC1;
StateBlock->Result.Frequency = 0;
StateBlock->Result.SymbolRate = 0;
}
#endif
#ifdef STTUNER_MINIDRIVER
/*----------------------------------------------------
FUNCTION SearchTiming
ACTION Perform an Fs/2 zig zag to found timing
PARAMS IN NONE
PARAMS OUT NONE
RETURN E299_NOTIMING if no valid timing had been found, E299_TIMINGOK otherwise
------------------------------------------------------*/
D0299_SignalType_t Drv0299_SearchTiming(D0299_SearchParams_t *Params)
{
short int DerotStep;
short int DerotMin,DerotMax;
short int DerotFreq = 0;
short int LastDerotFreq = 0;
short int NextLoop = 2;
int index = 0;
U8 nsbuffer[5];
Params->State = E299_NOTIMING;
Params->Direction = 1;
/* timing loop computation & symbol rate optimisation */
DerotMin = (short int) (((-(long)(Params->SubRange))/ 2L + Params->FreqOffset) / Params->Mclk); /* introduce 14 MHz derotator offset */
DerotMax = (short int) ((Params->SubRange/2L + Params->FreqOffset)/Params->Mclk);
DerotStep = (short int)( (Params->SymbolRate/2L) / Params->Mclk ); /* cast to eliminate compiler warning --SFS */
do
{
if (Drv0299_CheckTiming(Params) != E299_TIMINGOK)
{
index++;
LastDerotFreq = DerotFreq;
DerotFreq = DerotFreq + ( (int)Params->TunerIQSense * index * Params->Direction * DerotStep); /* Compute the next derotator position for the zig zag */
if((DerotFreq < DerotMin) || (DerotFreq > DerotMax))
NextLoop--;
if(NextLoop)
{
nsbuffer[1] = MAC0299_LSB(DerotFreq);
nsbuffer[0] = MAC0299_MSB(DerotFreq);
STTUNER_IODIRECT_ReadWrite(STTUNER_IO_SA_WRITE, R0299_CFRM, 0, 0, nsbuffer,2, FALSE);
}
}
Params->Direction = -Params->Direction; /* Change the zigzag direction */
}
while((Params->State != E299_TIMINGOK) && NextLoop); /* do..while */
if(Params->State == E299_TIMINGOK)
{
STTUNER_IODIRECT_ReadWrite(STTUNER_IO_SA_READ, R0299_CFRM, 0, 0, nsbuffer, 2, FALSE);
/* Multiply DerotFreq with IQ wiring sense of tuner & Demod */
Params->DerotFreq = (short int)Params->TunerIQSense * (short int)MAC0299_MAKEWORD( nsbuffer[0],nsbuffer[1] );
}
else
{
Params->DerotFreq = LastDerotFreq;
}
return(Params->State);
}
#endif
#ifdef STTUNER_MINIDRIVER
/*----------------------------------------------------
FUNCTION SearchCarrier
ACTION Search a QPSK carrier with the derotator
PARAMS IN
PARAMS OUT NONE
RETURN E299_NOCARRIER if no carrier had been found, E299_CARRIEROK otherwise
------------------------------------------------------*/
D0299_SignalType_t Drv0299_SearchCarrier(D0299_SearchParams_t *Params)
{
short int DerotMin,DerotMax;
short int DerotFreq = 0;
short int LastDerotFreq = 0;
short int NextLoop = 2;
int index = 0;
U8 nsbuffer[5], Data;
Params->State = E299_NOCARRIER;
Params->Direction = 1;
DerotMin = (short int) (((-(long)(Params->SubRange))/ 2L + Params->FreqOffset) / Params->Mclk); /* introduce 14 MHz derotator offset */
DerotMax = (short int) ((Params->SubRange/2L + Params->FreqOffset)/Params->Mclk);
DerotFreq = Params->DerotFreq;
Data = 1;
STTUNER_IODIRECT_ReadWrite(STTUNER_IO_SA_WRITE, R0299_CFD, F0299_CFD_ALGO, F0299_CFD_ALGO_L, &Data, 1, FALSE);
do
{
if(Drv0299_CheckCarrier(Params) == E299_NOCARRIER)
{
index++;
LastDerotFreq = DerotFreq;
DerotFreq = DerotFreq + ( (int)Params->TunerIQSense * index * Params->Direction * Params->DerotStep); /* Compute the next derotator position for the zig zag */
if((DerotFreq < DerotMin) || (DerotFreq > DerotMax))
NextLoop--;
if(NextLoop)
{
Data = 1;
STTUNER_IODIRECT_ReadWrite(STTUNER_IO_SA_WRITE, R0299_CFD, F0299_CFD_ALGO, F0299_CFD_ALGO_L, &Data, 1, FALSE);
nsbuffer[1] = MAC0299_LSB(DerotFreq);
nsbuffer[0] = MAC0299_MSB(DerotFreq);
STTUNER_IODIRECT_ReadWrite(STTUNER_IO_SA_WRITE, R0299_CFRM, 0, 0, nsbuffer, 2, FALSE);
}
}
Params->Direction = -Params->Direction; /* Change the zig-zag direction */
}
while((Params->State != E299_CARRIEROK) && NextLoop);
if(Params->State == E299_CARRIEROK)
{
STTUNER_IODIRECT_ReadWrite(STTUNER_IO_SA_READ, R0299_CFRM, 0, 0, nsbuffer, 2, FALSE);
/* Multiply DerotFreq with IQ wiring sense of tuner & Demod */
Params->DerotFreq = (short int)Params->TunerIQSense * (short int)MAC0299_MAKEWORD( nsbuffer[0],nsbuffer[1] );
}
else
{
Params->DerotFreq = LastDerotFreq;
}
return(Params->State);
}
#endif
#ifndef STTUNER_MINIDRIVER
/*----------------------------------------------------
FUNCTION SearchTiming
ACTION Perform an Fs/2 zig zag to found timing
PARAMS IN NONE
PARAMS OUT NONE
RETURN E299_NOTIMING if no valid timing had been found, E299_TIMINGOK otherwise
------------------------------------------------------*/
D0299_SignalType_t Drv0299_SearchTiming(STTUNER_IOREG_DeviceMap_t *DeviceMap, IOARCH_Handle_t IOHandle, D0299_SearchParams_t *Params, D0299_Searchresult_t *Result, STTUNER_Handle_t TopLevelHandle)
{
short int DerotStep;
short int DerotMin,DerotMax;
short int DerotFreq = 0;
short int LastDerotFreq = 0;
short int NextLoop = 2;
int index = 0;
U8 sfrm[2];
STTUNER_InstanceDbase_t *Inst;
STTUNER_tuner_instance_t *TunerInstance;
/* top level public instance data */
Inst = STTUNER_GetDrvInst();
/* get the tuner instance for this driver from the top level handle */
TunerInstance = &Inst[TopLevelHandle].Sat.Tuner;
Params->State = E299_NOTIMING;
Params->Direction = 1;
/* timing loop computation & symbol rate optimisation */
DerotMin = (short int) (((-(long)(Params->SubRange))/ 2L + Params->FreqOffset) / Params->Mclk); /* introduce 14 MHz derotator offset */
DerotMax = (short int) ((Params->SubRange/2L + Params->FreqOffset)/Params->Mclk);
DerotStep = (short int)( (Params->SymbolRate/2L) / Params->Mclk ); /* cast to eliminate compiler warning --SFS */
do
{
/* Try the terminate check here */
if(Inst[TopLevelHandle].ForceSearchTerminate==TRUE)
break;
if (Drv0299_CheckTiming(DeviceMap, IOHandle, Params) != E299_TIMINGOK)
{
index++;
LastDerotFreq = DerotFreq;
DerotFreq = DerotFreq + ( (int)Params->TunerIQSense * index * Params->Direction * DerotStep); /* Compute the next derotator position for the zig zag */
if((DerotFreq < DerotMin) || (DerotFreq > DerotMax))
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -