⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 stb6000drv.c

📁 QPSK Tuner details, for conexant chipset.
💻 C
字号:
#include "CSHDI_typedef.h"
#include "cs_qpsk.h"
#include "cs_i2c.h"
#include "STB6000drv.h"
// BY SFG
#include "cs_os.h"
#include "csqpskcfg.h"
#include "Allcommand.h"
#include "cs_assert.h"
//end
#define STB6000_R		0x04
#define FREQ_REF		4000000		//Hz
#define TUNELIMIT_LOW	900000		// KHz
#define TUNELIMIT_HIGH	2200000		// KHz
#define BANDFREQREF	125000

#define STB6000ADDR		0xc0

extern BYTE g_bLinkICType[MAX_TUNER_NUM];
static HCSHANDLE hSTB6000I2C[MAX_TUNER_NUM];
//ADD BY SFG FOR COMPILER
#ifdef STV0299_SUPPORT
extern CSQPSK_Error_t STV0299EnableTunerI2C ( CSHDITunerIndex bTunerIndex );
extern CSQPSK_Error_t STV0299DisableTunerI2C (CSHDITunerIndex bTunerIndex);
#endif
#ifdef STV0288_SUPPORT
extern CSQPSK_Error_t STV0288EnableTunerI2C ( CSHDITunerIndex bTunerIndex );
extern CSQPSK_Error_t STV0288DisableTunerI2C (CSHDITunerIndex bTunerIndex);
#endif
//add end

static CSQPSK_Error_t DemodEnableTunerI2C(CSHDITunerIndex bTunerIndex)
{
	#ifdef STV0299_SUPPORT
	if (g_bLinkICType[bTunerIndex] == STV_0299)
	{
		return STV0299EnableTunerI2C (bTunerIndex);
	}
	#endif
	#ifdef STV0288_SUPPORT	
	if (g_bLinkICType[bTunerIndex] == STV_0288)
	{
		
		return STV0288EnableTunerI2C (bTunerIndex);
	}
	#endif
	
	CSTRACE(ERROR_LEVEL, "[HDIQPSK]DemodEnableTunerI2C error \r\n");
	
	return CSQPSK_FAILURE;

}
static CSQPSK_Error_t DemodDisableTunerI2C(CSHDITunerIndex bTunerIndex)
{
	#ifdef STV0299_SUPPORT
	if (g_bLinkICType[bTunerIndex] == STV_0299)
	{
		return STV0299DisableTunerI2C (bTunerIndex);
	}
	#endif
	#ifdef STV0288_SUPPORT			
	if (g_bLinkICType[bTunerIndex] == STV_0288)
	{
		return STV0288DisableTunerI2C (bTunerIndex);
	}
	#endif
	CSTRACE(ERROR_LEVEL, "[HDIQPSK]DemodDisableTunerI2C error \r\n");

	return CSQPSK_FAILURE;
}
CSQPSK_Error_t STB6000Init( CSHDITunerIndex bTunerIndex )
{
	hSTB6000I2C[bTunerIndex] = 0;
	
	if( CSI2COpen(bTunerIndex,STB6000ADDR,&hSTB6000I2C[bTunerIndex]) != CSI2C_SUCCESS )
	{
		return CSQPSK_I2C_ERROR;
	}
	return CSQPSK_SUCCESS;
}

CSQPSK_Error_t STB6000Term( CSHDITunerIndex bTunerIndex )
{
	int ErrorCode;
	
	ErrorCode = CSI2CClose(hSTB6000I2C[bTunerIndex]);
	if ( ErrorCode != CSI2C_SUCCESS)
	{
		return CSQPSK_I2C_ERROR;
	}
	return CSQPSK_SUCCESS;

}

CSQPSK_Error_t STB6000GetFreq(CSHDITunerIndex bTunerIndex,DWORD *dwTuneFreq )
{
	int nRet = CSI2C_SUCCESS;		
	int nRetry = 5;
	int i;
	BYTE pbValue[6];
	BYTE bStartAddr;
	DWORD dwDiv,swallow,nbsteps,stepsize,f_ref=FREQ_REF;
	DWORD dwTmp;
	BYTE ucTmp;

	CSASSERT(NULL!=dwTuneFreq);
	if(NULL==dwTuneFreq) 
		return CSQPSK_FAILURE;
	CSASSERT(0!=hSTB6000I2C[bTunerIndex]);
	if(0==hSTB6000I2C[bTunerIndex]) 
		return CSQPSK_FAILURE;
	if ( CSI2CRequestBus_inner(bTunerIndex, CSHDI_TIMEOUT_INFINITY) == CSI2C_SUCCESS )
	{
		for ( i=0; i<nRetry; i++ )
		{
			bStartAddr = 0x00;
			DemodEnableTunerI2C(bTunerIndex);
			//nRet |= CSI2CWriteWithoutStop( hSTB6000I2C[bTunerIndex], &bStartAddr, 1 ) ;
			nRet |= CSI2CReadWithStop(hSTB6000I2C[bTunerIndex],  pbValue, 5)	;
			DemodDisableTunerI2C(bTunerIndex);			
			
			if ( nRet == CSI2C_SUCCESS )
			{
				//CSTRACE( INFO_LEVEL, "[STB6000GetFreq]reg value (%x),(%x),(%x),(%x),(%x) \n",pbValue[0],pbValue[1],pbValue[2],pbValue[3],pbValue[4]);
				break;					
			}
			else
			{
				CSTRACE( INFO_LEVEL, "[STB6000GetFreq]CSI2CWriteWithStop Error1(%d)\n",i);
				CSSleep(2);
			}
		}
		CSI2CReleaseBus_inner(bTunerIndex);
		
	}
	if (nRet != CSI2C_SUCCESS)
	{
			//sttbx_Print("[STB6000GetPLLStatus]I2C Read Error\n");
			return CSQPSK_I2C_ERROR;
	}
	if(0 == (pbValue[0]&0x01))  //pll lock ?
		*dwTuneFreq = 0xffffffff; 
	else
	{//pll lock 
	dwDiv  =(DWORD)pbValue[2];
	dwDiv =	(dwDiv<<1) + (DWORD)(pbValue[3]>>7);
							
	swallow =  pbValue[3]&0x1f;
	nbsteps = dwDiv*16 + (DWORD)swallow;	/* N x P + A ; P=16*/			
	stepsize =  2*(f_ref /  (pbValue[4]&0x3f)); /* 2 x Fr / R */
	*dwTuneFreq = (nbsteps * (stepsize>>( ((pbValue[1]>>4)&0x01)+1)))/1000; /* 2 x Fr x (PxN + A)/R */  //Khz
//	*dwTuneFreq = (nbsteps * (stepsize>>( (pbValue[1]>>4)&0x01+1))) ; /* 2 x Fr x (PxN + A)/R */  //hz
	}
	return CSQPSK_SUCCESS;

}


CSQPSK_Error_t STB6000SetFreq(CSHDITunerIndex bTunerIndex,DWORD dwTuneFreq, DWORD dwSymbolRate)
{
	int nRet = 0;		
	int nResult = 0;
	int nRetry = 8;
	int nPLLStatus;
	int i;
	BYTE pbValue[12];
	BYTE bFCL;
	BYTE bF;
	BYTE bODIV = 0;
	BYTE bOSM;
	BYTE bLPEN;
	BYTE bOSCH;
	BYTE bOCK;
	//sfg BYTE bK;
	//sfg BYTE bR;

	DWORD dwFrequency;
	DWORD dwStepSize;
	DWORD dwNBSteps;
	DWORD dwDivider; 
	DWORD dwSWAllow;

	//CSTRACE(ERROR_LEVEL,"[qpsk]stb6000 tuner setup freq=%d\n",dwTuneFreq);
		
#if 0 // SR 2 BW
	dwSymbolRate =dwSymbolRate *128 /100;
#endif
	if(dwSymbolRate != 0)
	{
		if((dwSymbolRate/2) > 26000) 
			bF = 31;		
		else
			bF = (dwSymbolRate/2)/1000 + 5; 		
	}
	else
	{
		bF = 0x0f;
	}

	if ( dwTuneFreq < 1076000 )
	{
		bODIV = 1;
	}
	else
	{
		bODIV = 0;
	}

	if ( dwTuneFreq < 1000000 )
	{
		bOSM = 0xA;
	}
	else if ( dwTuneFreq < 1076000 )
	{
		bOSM = 0xC;
	}
	else if ( dwTuneFreq < 1200000 )
	{
		bOSM = 0x0;
	}
	else if ( dwTuneFreq < 1300000 )
	{
		bOSM = 0x1;
	}
	else if ( dwTuneFreq < 1370000 )
	{
		bOSM = 0x2;
	}
	else if ( dwTuneFreq < 1470000 )
	{
		bOSM = 0x4;
	}
	else if ( dwTuneFreq < 1530000 )
	{
		bOSM = 0x5;
	}
	else if ( dwTuneFreq < 1650000 )
	{
		bOSM = 0x6;
	}
	else if ( dwTuneFreq < 1800000 )
	{
		bOSM = 0x8;
	}
	else if ( dwTuneFreq < 1950000 )
	{
		bOSM = 0xA;
	}
	else //if ( dwTuneFreq <= 2150000 )
	{
		bOSM = 0xC;
	}
	
	dwFrequency = dwTuneFreq<<(bODIV+1);
	dwStepSize =  2*(FREQ_REF / STB6000_R); /* 2 x Fr / R */
	dwNBSteps = (dwFrequency * 100) / (dwStepSize / 10);
	dwDivider = dwNBSteps / 16; /* 32 */
	dwSWAllow = dwNBSteps % 16; /* 32 */
	
	bLPEN = 0;	//PLL Loop Disable
	bOSCH = 1;	// VCO search enable
	bOCK = 1;	//VCO search clock is set to medium
	bFCL = 0;	//FCL_CLK = Fref / 1

	pbValue[0] = 0x01;	// sub register addr
	pbValue[1] = ((bOSCH&0x01)<<7) | ((bOCK&0x03)<<5) | ((bODIV&0x01)<<4) | (bOSM&0x0f);	//VCO
	pbValue[2] = (dwDivider>>1)&0xff;	//N
	pbValue[3] = ((dwDivider&0x01)<<7) | 0x60 |(dwSWAllow&0x1F);	//A
	pbValue[4] = 0x04;//K_R
	pbValue[5] = 0x07;//G
	pbValue[6] = 0x80 | (bF&0x1f); //F  0x8f;//
	pbValue[7] = 0xd8 | (bFCL&0x07);
	pbValue[8] = 0xd6;
	pbValue[9] = 0x56;
	pbValue[10] = 0xeb | ((bLPEN&0x01)<<4); //LPEN
	pbValue[11] = 0x0f;

	if ( CSI2CRequestBus_inner(bTunerIndex, CSHDI_TIMEOUT_INFINITY) == CSI2C_SUCCESS )
	{
		for ( i=0; i<nRetry; i++ )
		{
			DemodEnableTunerI2C(bTunerIndex);
			nRet = CSI2CWriteWithStop ( hSTB6000I2C[bTunerIndex], pbValue, 12 ) ;
			DemodDisableTunerI2C(bTunerIndex);			
		
			if ( nRet == CSI2C_SUCCESS )
			{
				break;					
			}
			else
			{
				CSTRACE( INFO_LEVEL, "[STB6000SetFreq]CSI2CWriteWithStop Error1(%d)\n",i);
			}
		}
		
		if ( nRet != CSI2C_SUCCESS )
		{
				nResult++;
		}

		CSI2CReleaseBus_inner(bTunerIndex);
	}
	

	bLPEN = 1;	// PLL Loop Enable
	pbValue[0] = 0x0a;
	pbValue[1] = 0xeb | ((bLPEN&0x01)<<4); //LPEN

	if ( CSI2CRequestBus_inner(bTunerIndex, CSHDI_TIMEOUT_INFINITY) == CSI2C_SUCCESS )
	{
		for ( i=0; i<nRetry; i++ )
		{
			DemodEnableTunerI2C(bTunerIndex);
			nRet = CSI2CWriteWithStop ( hSTB6000I2C[bTunerIndex], pbValue, 2 ) ;
			DemodDisableTunerI2C(bTunerIndex);			
		
			if ( nRet == CSI2C_SUCCESS )
			{
				break;					
			}
			else
			{
				CSTRACE( INFO_LEVEL, "[STB6000SetFreq]CSI2CWriteWithStop Error2(%d)\n",i);
			}
		}

		if ( nRet != CSI2C_SUCCESS )
		{
			nResult++;
		}
		
		CSI2CReleaseBus_inner(bTunerIndex);
	}

	CSSleep(20);	

	bOSCH = 0;	// VCO Search Disable 
	bOCK = 3;	// VCO Search Clock is set to low
	bFCL = 7;	// FCL_CLK is off
	pbValue[0] = 0x01;
	pbValue[1] = ((bOSCH&0x01)<<7) | ((bOCK&0x03)<<5) | ((bODIV&0x01)<<4) | (bOSM&0x0f);	//VCO
	pbValue[7] = 0xd8 | (bFCL&0x07);

	if ( CSI2CRequestBus_inner(bTunerIndex, CSHDI_TIMEOUT_INFINITY) == CSI2C_SUCCESS )
	{
		for ( i=0; i<nRetry; i++ )
		{
			DemodEnableTunerI2C(bTunerIndex);
			nRet = CSI2CWriteWithStop ( hSTB6000I2C[bTunerIndex], pbValue, 8 ) ;
			DemodDisableTunerI2C(bTunerIndex);			
		
			if ( nRet == CSI2C_SUCCESS )
			{
				break;					
			}
			else
			{
				CSTRACE( INFO_LEVEL, "[STB6000SetFreq]CSI2CWriteWithStop Error3(%d)\n",i);
			}
		}

		if ( nRet != CSI2C_SUCCESS )
		{
			nResult++;
		}
		
		CSI2CReleaseBus_inner(bTunerIndex);
	}
	if ( nResult == 0 )
	{
		return CSQPSK_SUCCESS;
	}
	else
	{
		return CSQPSK_I2C_ERROR;
	}

}


CSQPSK_Error_t STB6000GetPLLStatus ( CSHDITunerIndex bTunerIndex, int *pnPllLock )
{
	BYTE bStatus;
	int i;
	int nRetry = 8;
	int nRet;

	if ( CSI2CRequestBus_inner(bTunerIndex, CSHDI_TIMEOUT_INFINITY) == CSI2C_SUCCESS )
	{
		for ( i=0; i<nRetry; i++ )
		{
			DemodEnableTunerI2C(bTunerIndex);
			nRet = CSI2CReadWithStop ( hSTB6000I2C[bTunerIndex], &bStatus, 1) ;
			DemodDisableTunerI2C(bTunerIndex);			
		
			if ( nRet == CSI2C_SUCCESS )
			{
				break;					
			}
			else
			{
				CSTRACE( INFO_LEVEL, "[STB6000SetFreq]CSI2CReadWithStop Error1(%d)\n",i);
			}
		}

		CSI2CReleaseBus_inner(bTunerIndex);
		
		if (nRet != CSI2C_SUCCESS)
		{
			//sttbx_Print("[STB6000GetPLLStatus]I2C Read Error\n");
			return CSQPSK_I2C_ERROR;
		}

		if (( bStatus & 0x01 ) == 0x01 )
		{			
			//sttbx_Print("[STB6000SetFreq]lock!\n");
			*pnPllLock = TRUE;
		}
		else
		{
			//sttbx_Print("[STB6000SetFreq]not lock!\n");
			*pnPllLock = FALSE;
		}
		
		return CSQPSK_SUCCESS;
	}
	else
	{
		return CSQPSK_FAILURE;
	}
}	
CSQPSK_Error_t STB6000WrtReg(CSHDITunerIndex bTunerIndex,BYTE bStartIdx,BYTE *pbValue,BYTE len)
{
	int nRet,i;
	BYTE szBuffer[13];

	if(len>13) len =12;
	szBuffer[0] = bStartIdx;
	for(i=0;i<len;i++)
		szBuffer[1+i]= *(pbValue+i);
	if ( CSI2CRequestBus_inner(bTunerIndex, CSHDI_TIMEOUT_INFINITY) == CSI2C_SUCCESS )
		{
			DemodEnableTunerI2C(bTunerIndex);
			nRet = CSI2CWriteWithStop ( hSTB6000I2C[bTunerIndex], szBuffer, len+1 ) ;
			DemodDisableTunerI2C(bTunerIndex);			
			
			if ( nRet != CSI2C_SUCCESS )
			{
				CSTRACE( INFO_LEVEL, "[STB6000SetFreq]CSI2CWriteWithStop Error1(%d)\n",i);
			}
			CSI2CReleaseBus_inner(bTunerIndex);
		}
	return nRet;
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -