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

📄 auto.c

📁 RTD2662板卡源代码
💻 C
📖 第 1 页 / 共 4 页
字号:
//----------------------------------------------------------------------------------------------------
// ID Code      : Auto.c No.0002
// Update Note  :
//
//----------------------------------------------------------------------------------------------------

#define __AUTO__

#include "Core\Header\Include.h"

//--------------------------------------------------
// Description  : Auto clock, phase and H,V position
// Input Value  : None
// Output Value : _ERROR_SUCCESS if succeed
//--------------------------------------------------
BYTE CAutoDoAutoConfig(void)
{
    BYTE result, phasetemp, watchdogtemp;
    CScalerRead(_WATCH_DOG_CTRL0_0C, 1, &watchdogtemp, _NON_AUTOINC);
    CScalerSetByte(_WATCH_DOG_CTRL0_0C, 0x00);

    // Save current phase
	phasetemp = stModeUserData.Phase;

    // Clear the HW auto status to prevent some un-expected event happened
    CScalerSetByte(_AUTO_ADJ_CTRL1_7D, 0x00);
    CMiscClearStatusRegister();
    result  = CAutoDoAutoPosition();

    if(result == _ERROR_SUCCESS)
    {
        result  = CAutoDoAutoClock();
        if(result == _ERROR_SUCCESS)
        {
            result  = CAutoDoAutoPhase();
            if((result == _ERROR_SUCCESS) || (result == _ERROR_PHASE))
            {
                if(result == _ERROR_PHASE)
                {
                    stModeUserData.Phase = phasetemp;
                    CAdjustPhase(stModeUserData.Phase);
                }
                result  = CAutoDoAutoPosition();
                if(result != _ERROR_SUCCESS)
                {
                    stModeUserData.HPosition = stModeInfo.IHStartPos;
                    stModeUserData.VPosition = stModeInfo.IVStartPos;
                    CAdjustHPosition();
                    CAdjustVPosition();
                }
            }
            else
            {
                // If auto phase is failed, load phase setting before auto config
                stModeUserData.Phase = phasetemp;
                CAdjustPhase(stModeUserData.Phase);
            }
        }
        else
        {
            // If auto clock is failed, load default clock setting
            stModeUserData.Clock = stModeInfo.IHTotal;
            stModeUserData.HPosition = stModeInfo.IHStartPos;
            stModeUserData.VPosition = stModeInfo.IVStartPos;
            CAdjustAdcClock(stModeUserData.Clock);
            CAdjustHPosition();
            CAdjustVPosition();
        }
    }
    else
    {
        stModeUserData.HPosition = stModeInfo.IHStartPos;
        stModeUserData.VPosition = stModeInfo.IVStartPos;
        CAdjustHPosition();
        CAdjustVPosition();
    }

    if((result == _ERROR_SUCCESS) || (result == _ERROR_ABORT))
    {

        // Save auto result
        CEepromSaveModeData(stModeInfo.ModeCurr);
        CAdjustUpdateCenterData();
        CEepromSaveCenterModeData(stModeInfo.ModeCurr);
    }       
    CScalerSetByte(_WATCH_DOG_CTRL0_0C, watchdogtemp);
    CMiscClearStatusRegister();
    return result;
}

//--------------------------------------------------
// Description  : Auto color ( white balance )
// Input Value  : None
// Output Value : _ERROR_SUCCESS if succeed
//--------------------------------------------------
BYTE CAutoDoWhiteBalance(void)
{
    BYTE result;
#if(_YPBPR_AUTO_TYPE==_NEW_TYPE)
	if(_GET_INPUT_SOURCE() == _SOURCE_YPBPR)	
		result = CAutoTuneBalanceNew();	
	else
		result = CAutoTuneBalance();
#else//_YPBPR_AUTO_TYPE==_ORIGINAL_TYPE
    result = CAutoTuneBalance();
#endif
    if(result == _ERROR_SUCCESS)
        CEepromSaveAdcData();
    else
    {
    	if(_GET_INPUT_SOURCE() == _SOURCE_VGA)
        	CEepromLoadAdcDataDefault();
        else
    	 	CEepromLoadYPbPrDataDefault();
    }
   	if(bSourceVideo())
  		CEepromSaveSystemData();
    return result;
}

//--------------------------------------------------
// Description  : Wait auto measure process completed
// Input Value  : None
// Output Value : Return result _ERROR_INPUT, _ERROR_SUCCESS
//--------------------------------------------------
BYTE CAutoWaitFinish(void)
{
    BYTE timeoutcnt, ivsevent;
	BYTE valuetemp;//tommy add 070608

    CMiscClearStatusRegister();
    // Auto timeout
#if 1
	//{ add 070608
	//tommy liao add for prevent (ADD PC_AUTOADJUST ITEM) ERROR
	//tommy add for prevent execute funtion of (COsdMenuAutoAdjust) error
	//warning!!!!!!!!!!!!,don't delete the below function
	//warning!!!!!!!!!!!!,or if you change ,can cause serious error,can cause system error 
	CScalerRead(_AUTO_ADJ_CTRL0_7A, 1, &valuetemp, _AUTOINC);
	valuetemp = (valuetemp&0x03);
	if( valuetemp == 0x03 )
		timeoutcnt = 150;
	else
		timeoutcnt = 50;
	//warning!!!!!!!!!!!!,don't delete the up function
	//} add 070608
#else
    //tommy delete
    //timeoutcnt   = (CScalerGetBit(_AUTO_ADJ_CTRL0_7A, _BIT1 | _BIT0) == 0x03) ? 150 : 50;
#endif
    // IVS timeout
    ivsevent     = 25;

    do
    {
        CTimerDelayXms(1);
        CScalerRead(_STATUS1_03, 1, pData, _NON_AUTOINC);
        if(pData[0] & _EVENT_IVS)
        {
            CScalerSetByte(_STATUS1_03, 0x00);
            ivsevent = 25;
        }
        else
        {
            ivsevent = ivsevent - 1;
        }
        if((ivsevent == 0) || (pData[0] & (_EVENT_UNDERFLOW | _EVENT_OVERFLOW)))
        {
            return _ERROR_INPUT;
        }

        // Power off while auto config--------
//        CKeyCheckPowerKey(); cancel by weihao 940926

        if(GET_POWERSWITCH())
            return _ERROR_INPUT;
        //------------------------------------
        CScalerRead(_AUTO_ADJ_CTRL1_7D, 1, pData, _NON_AUTOINC);
    }
    while((pData[0] & 0x01) && (--timeoutcnt));

    CScalerRead(_STATUS0_02, 1, pData, _NON_AUTOINC);
    CScalerSetByte(_STATUS0_02, 0x00);

    // Return non-zero value in Data[0] if :
    // 1. IVS or IHS changed
    // 2. Auto-Phase Tracking timeout
    return ((pData[0] & 0x63) || (0 == timeoutcnt)) ? _ERROR_INPUT : _ERROR_SUCCESS;
}

//--------------------------------------------------
// Description  : Wait for IVS process
// Input Value  : ucTimes   --> frames
// Output Value : Return underflow/overflow status
//--------------------------------------------------
BYTE CAutoWaitForIVS(BYTE ucTimes)
{
    BYTE timeoutcnt;

    timeoutcnt = 25;
    CScalerSetByte(_STATUS1_03, 0x00);
   	do
    {
        CTimerDelayXms(1);
        CScalerRead(_STATUS1_03, 1, pData, _NON_AUTOINC);
        pData[0] &= (_EVENT_IVS | _EVENT_UNDERFLOW | _EVENT_OVERFLOW);
        if(((pData[0] & _EVENT_IVS) == _EVENT_IVS) && (ucTimes != 0))
        {
            CScalerSetByte(_STATUS1_03, 0x00);
            ucTimes--;
            timeoutcnt = 25;
        }
   	}
    while((ucTimes != 0) && (--timeoutcnt) && ((pData[0] & (_EVENT_UNDERFLOW | _EVENT_OVERFLOW)) == 0));

    return pData[0];
}

//--------------------------------------------------
// Description  : Measure position H
// Input Value  : ucNoiseMarginH    --> Noise margin for H
// Output Value : Measure status
//--------------------------------------------------
BYTE CAutoMeasurePositionH(BYTE ucNoiseMarginH)
{
    WORD lbound, rbound;

    rbound  = stModeUserData.Clock;                                               // Totol Clock Number
    lbound  = (DWORD)rbound * stModeInfo.IHSyncPulseCount / stModeInfo.IHCount;   // Clock number in HSYNC pulse
    CScalerSetBit(_VGIP_HV_DELAY_1E, 0x0f, 0x50);
    rbound  = (rbound + _MEASURE_HDEALY) - 2;
    rbound  = rbound - 32;
    lbound  = (lbound + 20 + _MEASURE_HDEALY) < stModeInfo.IHStartPos ? (lbound + 20 + _MEASURE_HDEALY) : 0x0001;
    lbound  = (lbound > 32) ? (lbound - 32) : 0x0001;
    ucNoiseMarginH  &= 0xfc;
    pData[0]    = ((lbound >> 4) & 0x70) | (HIBYTE(rbound) & 0x0f);
    pData[1]    = (LOBYTE(lbound));
    pData[2]    = (LOBYTE(rbound));
    CScalerWrite(_H_BOUNDARY_H_70, 3, pData, _AUTOINC);
    pData[0]    = ucNoiseMarginH;
    pData[1]    = ucNoiseMarginH;
    pData[2]    = ucNoiseMarginH;
    pData[3]    = 0x00;
    pData[4]    = 0x00;
    pData[5]    = 0x00;
    pData[6]    = 0x00;
    pData[7]    = 0x01;
    CScalerWrite(_RED_NOISE_MARGIN_76, 8, pData, _AUTOINC);
    pData[0]    = CAutoWaitFinish();
    if(pData[0] != _ERROR_SUCCESS)
		return pData[0];
    CScalerRead(_H_START_END_H_81, 3, &pData[8], _AUTOINC);
    usHStartPos = (((WORD)(pData[8] & 0xf0 ) << 4) | (WORD)pData[9]) + 32;
    usHEndPos   = (((WORD)(pData[8] & 0x0f ) << 8) | (WORD)pData[10]) + 32;
    return _ERROR_SUCCESS;
}

//--------------------------------------------------
// Description  : Measure position V
// Input Value  : ucNoiseMarginV    --> Noise margin for V
// Output Value : Measure status
//--------------------------------------------------
BYTE CAutoMeasurePositionV(BYTE ucNoiseMarginV)
{
    WORD lbound, rbound;

    rbound  = stModeUserData.Clock;                                               // Totol Clock Number
    lbound  = (DWORD)rbound * stModeInfo.IHSyncPulseCount / stModeInfo.IHCount;   // Clock number in HSYNC pulse
    CScalerSetBit(_VGIP_HV_DELAY_1E, 0x0f, 0x50);
    rbound  = (rbound + _MEASURE_HDEALY) - 2;
    rbound  = rbound - 32;
    lbound  = (lbound + 20 + _MEASURE_HDEALY) < stModeInfo.IHStartPos ? (lbound + 20 + _MEASURE_HDEALY) : 0x0001;
    lbound  = (lbound > 32) ? (lbound - 32) : 0x0001;
    ucNoiseMarginV  &= 0xfc;
    pData[0]    = ((lbound >> 4) & 0x70) | (HIBYTE(rbound) & 0x0f);
    pData[1]    = (LOBYTE(lbound));
    pData[2]    = (LOBYTE(rbound));
    pData[3]    = (HIBYTE(stModeInfo.IVTotal - 1 + 3) & 0x0f);
    pData[4]    = (0x02);
    pData[5]    = (LOBYTE(stModeInfo.IVTotal - 1 + 3));
    CScalerWrite(_H_BOUNDARY_H_70, 6, pData, _AUTOINC);
    pData[0]    = ucNoiseMarginV;
    pData[1]    = ucNoiseMarginV;
    pData[2]    = ucNoiseMarginV;
    pData[3]    = 0x00;
    pData[4]    = 0x00;
    pData[5]    = 0x00;
    pData[6]    = 0x00;
    pData[7]    = 0x01;
    CScalerWrite(_RED_NOISE_MARGIN_76, 8, pData, _AUTOINC);
    pData[0]    = CAutoWaitFinish();
    if(pData[0] != _ERROR_SUCCESS)
		return pData[0];
    CScalerRead(_V_START_END_H_7E, 3, &pData[8], _AUTOINC);
    usVStartPos = (((WORD)(pData[8] & 0xf0 ) << 4) | (WORD)pData[9]) + 3;
    usVEndPos   = (((WORD)(pData[8] & 0x0f ) << 8) | (WORD)pData[10]) + 3;
    // Check all black
    if(usVEndPos == 0x0000)
		return  _ERROR_ABORT;
    // Update auto-tracking window vertical range
    pData[0]    = (pData[8] & 0x7f);
    pData[1]    = pData[9];
    pData[2]    = pData[10];
    CScalerWrite(_V_BOUNDARY_H_73, 3, pData, _AUTOINC);
    return _ERROR_SUCCESS;
}

//--------------------------------------------------
// Description  : Auto phase search function
// Input Value  :
// Output Value :
//--------------------------------------------------
DWORD CAutoPhaseSearch(BYTE ucSelColor, BYTE ucSelStep, BYTE ucSelStepNum, BYTE ucSelStepStart, BYTE *ucPhaseResult)
{
    DWORD maxsum;
    BYTE  count, best;

    CScalerSetByte(_AUTO_ADJ_CTRL1_7D, 0x00);
    CScalerSetBit(_AUTO_ADJ_CTRL0_7A, ~(_BIT1 | _BIT0), ucSelColor & 0x03);
    // Issac : Because H/W auto phase search may cause underflow at start and stop,
    //         frame-sync watch-dog must be disabled.
    //CAdjustDisableWatchDog(_WD_ALL);

    if(((DWORD)stModeInfo.IHFreq * stModeInfo.IHTotal / 1000) < 530){
        ucSelStep += 1;
        ucSelStepStart *= 2;
        CScalerPageSelect(_PAGE1);
        if (ucSelStepStart >= 64)
			CScalerSetBit(_P1_MIX_B0, ~_BIT1, _BIT1);
    }
    CScalerSetByte(_HW_AUTO_PHASE_CTRL0_7B, (ucSelStep & 0x07) | (((ucSelStepNum - 1) & 0x1f) << 3));
    CScalerSetByte(_HW_AUTO_PHASE_CTRL1_7C, 0x00 | (ucSelStepStart & 0x3f));
    ucSelStep   = (0x01 << ucSelStep);
    ucSelColor  = ucSelStepStart + (ucSelStepNum) * ucSelStep;
    count       = ucSelStepStart;
    maxsum      = 0;
    best        = 0;
    // Issac : Using Wait_For_Event(EVENT_IVS) instead of Wait_For_IVS().
    //         Because H/W auto phase search may cause underflow at start and stop.
    //         Wait_For_Event() will not check underflow/overflow.
    CScalerSetByte(_AUTO_ADJ_CTRL1_7D, 0x7b);
    CAutoWaitForIVS(1);
    do
    {
        if(CAutoWaitForIVS(((CScalerGetBit(_AUTO_ADJ_CTRL0_7A, _BIT1 | _BIT0) == 0x03) ? 3 : 1)) & (_EVENT_UNDERFLOW | _EVENT_OVERFLOW))
        {
        	CScalerSetByte(_AUTO_ADJ_CTRL1_7D, 0x00);
	 		CScalerPageSelect(_PAGE1);
			CScalerSetBit(_P1_MIX_B0, ~_BIT1, 0x00);
			return 0xffffffff;
        }
        CScalerRead(_AUTO_PHASE_3_84, 3, pData, _AUTOINC);
        pData[3]    = 0;
        if(((DWORD *)pData)[0] > maxsum)
        {
            maxsum  = ((DWORD *)pData)[0];
            best    = count;
        }
        count += ucSelStep;
    }
    while(count < ucSelColor);
    CScalerSetByte(_AUTO_ADJ_CTRL1_7D, 0x00);
    CScalerPageSelect(_PAGE1);

	CScalerSetBit(_P1_MIX_B0, ~_BIT1, 0x00);
		
    CTimerWaitForEvent(_EVENT_IVS);
    pData[0] = CAutoWaitFinish();
    if(pData[0] != _ERROR_SUCCESS)
		return 0xffffffff;
    if(((DWORD)stModeInfo.IHFreq * stModeInfo.IHTotal / 1000) < 530)
    {
        *ucPhaseResult = best / 2;
    }
    else
    {
    	*ucPhaseResult = best;
    }
    return maxsum;
}

//--------------------------------------------------
// Description  : Get phase SOD information
// Input Value  : ucColor   --> Color we measure
// Output Value : Measure status
//--------------------------------------------------
BYTE CAutoReadPhaseInfo(BYTE ucColor)
{
    CScalerSetBit(_AUTO_ADJ_CTRL0_7A, ~(_BIT1 | _BIT0), ucColor & 0x03);
    CScalerSetByte(_AUTO_ADJ_CTRL1_7D, 0x3b);
    pData[0] = CAutoWaitFinish();
    if(_ERROR_SUCCESS != pData[0])
		return pData[0];
    CScalerRead(_AUTO_PHASE_3_84, 4, pData, _AUTOINC);
    return _ERROR_SUCCESS;
}

//--------------------------------------------------
// Description  : Auto clock process
// Input Value  : None
// Output Value : Measure status
//--------------------------------------------------
BYTE CAutoDoAutoClock(void)
{
    BYTE    result, phase;
    WORD    count, delta, stop;
    DWORD   maxval;

    stModeUserData.Clock = stModeInfo.IHTotal;
    stModeUserData.Clock &= 0xfffc;
    CAdjustAdcClock(stModeUserData.Clock);
    result  = CAutoMeasurePositionV(_MIN_NOISE_MARGIN);
    if(result != _ERROR_SUCCESS)
		return result;
    delta   = (stModeInfo.IHTotal - stModeInfo.IHWidth * 8 / 10) / 2;
    stop    = 0;
    count   = 10;
    do
    {
        // Measure Horizontal Start/End
        //result      = CAutoMeasurePositionH(_MIN_NOISE_MARGIN + 0x10);
		result      = CAutoMeasurePositionH(_MIN_NOISE_MARGIN + 0x30);
        if(result != _ERROR_SUCCESS)
			return result;
        usHEndPos   = usHEndPos + 1 - usHStartPos;
        if(usHEndPos < stModeInfo.IHWidth)
        {
            if((stModeInfo.IHWidth - usHEndPos) >= (2 * delta))
            {
                stop    = 1;
            }
            else
            {
                usHStartPos = (DWORD)(stModeInfo.IHWidth - usHEndPos) * (stModeUserData.Clock)
                            / (DWORD)stModeInfo.IHWidth;

                if(usHStartPos <= 2)    break;
                usHStartPos = (usHStartPos + 2) & 0xfffc;
                //if((usHStartPos + stModeUserData.Clock - stModeInfo.IHTotal) > usDelta)
                if((usHStartPos + stModeUserData.Clock) > (delta + stModeInfo.IHTotal))
                {
                    stop    = 1;
                }
                else
                {
                    stModeUserData.Clock += usHStartPos;
                }
            }
        }
        else
        {
            if((usHEndPos - stModeInfo.IHWidth) >= (2 * delta))
            {
                stop    = 1;
            }
            else
            {

⌨️ 快捷键说明

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