📄 mstar.c
字号:
#endif
{
if( (SIG_NONE == g_VdInfo.ucVideoSystem)
||(0 ==(g_VdInfo.wVideoStatus&VD_HSYNC_LOCKED)))
return FALSE;
}
return TRUE;
}
void SetOutputTimingAndWindow( BYTE ucOutputTimingCtl )
{
// Get input sync info
if( IsSrcHasSignal() || (ucOutputTimingCtl&OUTPUT_SNOW) ) // Has signal or snow
{
GetInputSignalHV();
}
else // No signal or Freerun
{
g_InOutCtl.inOutVFreq = 60;
if( g_InOutCtl.inOutVFreq == 50 )
{
g_InOutCtl.inHFreq = 15625;
g_InOutCtl.inVTotal = 625;
}
else // 60 Hz
{
g_InOutCtl.inHFreq = 15734;
g_InOutCtl.inVTotal = 525;
}
g_InOutCtl.inHPeriod = MST_CLOCK_HZ/g_InOutCtl.inHFreq;
}
msProgWindow( ucOutputTimingCtl );
msSetOutputTiming( ucOutputTimingCtl ); // This function must after msProgWindow()
#if (PANEL_TYPE>=PanelSHARP08_DT) //for digital panel only
if(ucOutputTimingCtl&OUTPUT_SNOW) // Has signal or snow
msWriteRegsTbl(tTVSnowModeTbl);
#endif
}
void msSetScaler(void)
{
#if (!WidePanel)
msLoadModeIndexTBL(tModeIndexTbl);
#else
BYTE ucBank;
WORD ulNewHsize,uwInput_H_Resol,uwTemp;
DWORD ulH_Scaling_Factor, ulTemp;
ucBank = msReadByte(BK0_00_REGBK); // store bank
msWriteByte( BK0_00_REGBK, REG_BANK_SCALER); // bank 1
if (g_VideoSetting.Scaling==Scaling_Full)
{
#if VGA_ENABLE
if(IsVGAInUse())
SetScalingRatio( g_InOutCtl.bInterlace );
else
#endif
SetScalingRatio( 1 );
msWriteWord(BK0_49_SIHST_H, PanelHStart); // horizontal DE start
msWriteWord(BK0_43_HFDEST_H, PanelHStart); // horizontal DE start
msWriteWord(BK0_4D_SIHEND_H, (PanelHStart + PanelWidth - 1)); // Image H end
msWriteWord(BK0_47_HFDEEND_H, (PanelHStart+ PanelWidth - 1)); // horizontal DE end
msLoadModeIndexTBL(tModeIndexTbl);
//printMsg("test 169");
}
else
{
msWriteByte(BK0_38_NLDTI, 0x00); // Disable Nonlinear scaling function
//ulNewHsize=PANEL_DOT_HEIGHT;//X*4/3=>4:3,X/3=>3dot in 1 pixel
//ulNewHsize=ulNewHsize*PanelHeight;
//ulNewHsize=ulNewHsize/PANEL_DOT_WIDTH;
//ulNewHsize=(ulNewHsize*SCAL_RATIO_NUMERATOR)/(SCAL_RATIO_DENOMINATOR*3);
ulNewHsize=PanelWidth*3/4;
uwInput_H_Resol = msReadWord(BK0_0C_SPRHDC_H);//Get Input H resolution
//New start point
uwTemp = PanelHStart+ (PanelWidth- ulNewHsize )/2;
msWriteWord(BK0_49_SIHST_H,uwTemp);//new Start //BK0_48_SIHST_L, BK0_49_SIHST_H
msWriteWord(BK0_43_HFDEST_H,uwTemp);
// New end point
msWriteWord(BK0_4D_SIHEND_H,uwTemp+ulNewHsize);//new End //BK0_4C_SIHEND_L, BK0_4D_SIHEND_H
msWriteWord(BK0_47_HFDEEND_H,uwTemp+ulNewHsize);
// Get new scaling factor
ulH_Scaling_Factor = (DWORD)ulNewHsize <<20 ;
ulTemp = (DWORD)uwInput_H_Resol*(SCAL_CUTOFF_RESOL - SCAL_CUTOFF_H_PER);
ulH_Scaling_Factor /= (ulTemp/SCAL_CUTOFF_RESOL);
// Mask the front and back block
// msWriteWord(BK0_5D_FRAME_COLOR_2,0);//BK0_5C_FRAME_COLOR_1, BK0_5D_FRAME_COLOR_2
ulH_Scaling_Factor += 0xC00;//0xc00 get from fine tune
msWriteWord(BK0_31_SRH_M,(unsigned int)(ulH_Scaling_Factor&0xFFF000) );//BK0_30_SRH_L,BK0_31_SRH_M
msWriteByte(BK0_32_SRH_H,(unsigned char)((ulH_Scaling_Factor&0x0F0000)>>16)+0xC0);
//printMsg("test 43");
}
msWriteByte( BK0_00_REGBK, ucBank); // bank 1
#endif
}
void msSetLineBufferClock( BYTE ucModeIdx, BYTE ucOutputClock )
{
BYTE ucInputClock;
BYTE ucBank;
BYTE ucBk0_36_val = 0; // Use default clock
ucInputClock = ((float)GetStdModeHTotal(ucModeIdx)*GetStdModeHFreq(ucModeIdx))/10000;
#ifndef D800480PANEL
if( ucInputClock > 50 )
ucBk0_36_val = 0x80; // Using input clock
else
#endif
ucInputClock = 50;
if( ucOutputClock > ucInputClock )
ucBk0_36_val = 0x40; // Using output clock
ucBank = msReadByte( BK0_00_REGBK);
msWriteByte( BK0_00_REGBK, 0 );
msWriteByteMask( BK0_36_VDSUSG, ucBk0_36_val, 0xC0 );
msWriteByte( BK0_00_REGBK, ucBank );
}
void msSetOutputFreeRunClock( BYTE ucVFreq )
{
BYTE ucBank = msReadByte( BK0_00_REGBK);
msWriteByte( BK0_00_REGBK, REG_BANK_SCALER);
#if PANEL_ANALOG_TCON
if( ucVFreq != 60 )
msWrite3Bytes( BK0_27_OPL_SET2, PANEL_FREE_RUN_DCLK_FACTOR*60/ucVFreq/3 );
else
msWrite3Bytes( BK0_27_OPL_SET2, PANEL_FREE_RUN_DCLK_FACTOR/3 );
#else
if( ucVFreq != 60 )
msWrite3Bytes( BK0_27_OPL_SET2, PANEL_FREE_RUN_DCLK_FACTOR*60/ucVFreq );
else
msWrite3Bytes( BK0_27_OPL_SET2, PANEL_FREE_RUN_DCLK_FACTOR );
#endif
msSetLineBufferClock( MD_720x480_60I, PANEL_FREE_RUN_DCLK/1000000);
msWriteByte( BK0_00_REGBK, ucBank );
}
void SetOutputClock( BYTE ucOutputTimingCtl )
{
//printf("\r\nmsSetOutputClock(%x)", ucOutputTimingCtl);
WatchDogClear();
if( ucOutputTimingCtl&OUTPUT_FREERUN )
{
msSetOutputFreeRunClock( 60 );
}
else
{
msLCDSetClock();
}
WatchDogClear();
}
void msLCDSetClock(void)
{
BYTE ucBank;
XDATA WORD wInputHPeriod; // horizontal period
XDATA WORD wOutputClock;
XDATA DWORD dwClockFactor; // clock factor
wInputHPeriod = g_InOutCtl.inHPeriod;
ucBank = msReadByte( BK0_00_REGBK);
msWriteByte( BK0_00_REGBK, REG_BANK_SCALER );
if( IsVGAInUse() )
{
// get more accurate horzontal total for output
if( wInputHPeriod > (MST_H_PERIOD_MASK / 16) ) // check overflow
{
wInputHPeriod = wInputHPeriod * 16;
}
else // general
{
WORD wVSyncTime; // VSync time
msWriteBit( BK0_E8_HSTOL, 1, _BIT6 ); // enable 16 line to calculate hsync period
wVSyncTime = ((WORD)msCalculateVSyncTime() * 3);
Delay1ms(wVSyncTime); // delay for stable
wInputHPeriod = msGetHorizontalPeriod();
if (abs((wInputHPeriod / 16) - g_wHorizontalPeriod) > 5)
wInputHPeriod = g_wHorizontalPeriod * 16;
msWriteBit( BK0_E8_HSTOL, 0, _BIT6 ); // recovry one line to calculate hsync period
Delay1ms(wVSyncTime);
}
}
else
{
wInputHPeriod *= 16;
}
// Cal output clock
{
// if expansion, chip will assume output clock is faster than input clock,
#if 1//(SCALING_FORMULA)
wOutputClock = (((float)PanelMinHTotal * (PanelHeight-1) * MST_CLOCK_KHZ * 16) + 500) /
((float)wInputHPeriod * (g_WindowInfo.V_CapSize-1) * 1000);
#else
wOutputClock = (((float)PanelMinHTotal * (PanelHeight) * MST_CLOCK_KHZ * 16) + 500) /
((float)wInputHPeriod * (g_WindowInfo.V_CapSize) * 1000);
#endif
if( g_InOutCtl.bInterlace )
{
wOutputClock *= 2;
}
}
#if 1//(SCALING_FORMULA)
dwClockFactor = ((float)wInputHPeriod*(g_WindowInfo.V_CapSize-1)*524288ul*PANEL_MASTER_PLL_DIVIDER)/
((float)PanelMinHTotal*(PanelHeight-1)*16);
#else
dwClockFactor = ((float)wInputHPeriod*(g_WindowInfo.V_CapSize)*524288ul*PANEL_MASTER_PLL_DIVIDER)/
((float)PanelMinHTotal*(PanelHeight)*16);
#endif
if( g_InOutCtl.bInterlace )
{
dwClockFactor /= 2;
}
#if (PANEL_ANALOG_TCON)
dwClockFactor /= 3;
#endif
printf("\r\nDclk %dMhz", (DClkFactor+dwClockFactor/2)/dwClockFactor/2);
msWrite3Bytes( BK0_27_OPL_SET2, dwClockFactor );
msSetLineBufferClock( g_ucSrcModeIndex, wOutputClock );
msWriteByte( BK0_00_REGBK, ucBank );
}
#if(ENABLE_MONITOR_VTOTAL)
XDATA WORD g_wMsMonitorVTotal_OriginalVCapsize;
XDATA WORD g_wMsMonitorVTotal_LastVTotal;
XDATA WORD g_wMsMonitorVTotal_VTotalChangeCnt;
void msMonitorVTotal( BYTE ucFlag )
{
BYTE ucBank;
WORD wCurVTotal;
bit bVTotalChange = 0;
ucBank = msReadByte( BK0_00_REGBK);
msWriteByte( BK0_00_REGBK, REG_BANK_SCALER);
wCurVTotal = msVDGetVTotal();
if( ucFlag&1 ) // Reset
{
g_wMsMonitorVTotal_OriginalVCapsize = msReadWord( BK0_0A_SPRVDC_H);
g_wMsMonitorVTotal_VTotalChangeCnt = 0;
g_wMsMonitorVTotal_LastVTotal = 0;
bVTotalChange = 1;
}
else
{
if( wCurVTotal != g_wMsMonitorVTotal_LastVTotal )
{
g_wMsMonitorVTotal_VTotalChangeCnt ++;
if( g_wMsMonitorVTotal_VTotalChangeCnt >= 5 )
{
bVTotalChange = 1;
g_wMsMonitorVTotal_VTotalChangeCnt = 0;
}
}
else
{
g_wMsMonitorVTotal_VTotalChangeCnt = 0;
}
}
if( bVTotalChange )
{
WORD wCurVCapsize;
wCurVCapsize = msReadWord( BK0_0A_SPRVDC_H);
if( (wCurVCapsize + V_CAP_SIZE_SAFE_RANGE) > wCurVTotal )
{
msWriteWord( BK0_0A_SPRVDC_H, (wCurVTotal-V_CAP_SIZE_SAFE_RANGE) );
}
else
{
if( ( g_wMsMonitorVTotal_OriginalVCapsize != wCurVCapsize )
&&( (g_wMsMonitorVTotal_OriginalVCapsize+V_CAP_SIZE_SAFE_RANGE) <= wCurVTotal))
{
msWriteWord( BK0_0A_SPRVDC_H, g_wMsMonitorVTotal_OriginalVCapsize );
}
}
g_wMsMonitorVTotal_LastVTotal = wCurVTotal;
}
msWriteByte( BK0_00_REGBK, ucBank );
}
#endif
#if(ENABLE_CHECK_AUTO_H_TOTAL)
WORD msCalculateVFreqX10( WORD wHFreq, WORD wVTotal )
{
return ((((DWORD)wHFreq * 1000) + (wVTotal / 2)) / wVTotal); // Hz
}
void msCheckBK0_57_Value(BOOL ResetIndex)
{
bit bCurAutoHTotalOn ;
bit bCurSyncStable = 0;
BYTE ucBank;
if( !g_bEnableAutoHTotal ||!IsSrcHasSignal())
{
bCurAutoHTotalOn=ResetIndex;
ucBank=msReadByte(BK0_00_REGBK);
msWriteByte(BK0_00_REGBK, REG_BANK_SCALER);
if( msReadByte( BK0_57_OSCTRL1)&_BIT1 )
bCurAutoHTotalOn = 1;
if( (msVDGetSyncStatus()&VD_HSYNC_LOCKED)
&&(msVDCheckScalerStatus(0) == 0)
&&(msDSP_Std_GetNoiseMag()<0xE0)
)
bCurSyncStable = 1;
if( bCurAutoHTotalOn )
{
g_ucCheckSyncCounter = 0;
g_ucSyncStableCounter = 0;
if( !bCurSyncStable )
{
msWriteBit( BK0_57_OSCTRL1, 0, _BIT1 ); // Turn off auto h total
if( (g_VdInfo.ucVideoSystem==SIG_NTSC)||(g_VdInfo.ucVideoSystem==SIG_NTSC_443))
msWriteWord(BK0_55_HDTOT_H,NtscHTotal); // output htotal
else if(g_VdInfo.ucVideoSystem==SIG_NONE)
msWriteWord(BK0_55_HDTOT_H, FreeRunHTotal);
else
msWriteWord(BK0_55_HDTOT_H, PalHTotal); // output htotal
//printf("\r\nTurn off auto H:Noise=%x", msDSP_Std_GetNoiseMag());
}
}
else // Current auto h total is off
{
if( g_ucCheckSyncCounter < 20 )
{
g_ucCheckSyncCounter ++;
if( bCurSyncStable )
{
g_ucSyncStableCounter ++;
if( (g_ucCheckSyncCounter == 20) && (g_ucSyncStableCounter == 20) )
{
// Turn on auto h total
msWriteBit( BK0_57_OSCTRL1, 1, _BIT1 );
//printf("\r\nTurn on auto H:Noise=%x", msDSP_Std_GetNoiseMag());
}
}
else
{
g_ucCheckSyncCounter = 0;
g_ucSyncStableCounter = 0;
}
}
else// if( g_ucCheckSyncCounter == 10 )
{
g_ucCheckSyncCounter = 0;
g_ucSyncStableCounter = 0;
}
}
msWriteByte(BK0_00_REGBK, ucBank);
}
else
{
msWriteBit( BK0_57_OSCTRL1, 1, _BIT1 );
g_ucCheckSyncCounter = 0;
g_ucSyncStableCounter = 0;
}
}
#endif
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -