📄 mfc.c
字号:
mfcOutp32(ENC_SEQ_BIT_BUF_ADDR, oMfc.m_uStreamBufStAddr[uProcessIdx]);
mfcOutp32(ENC_SEQ_BIT_BUF_SIZE, uStreamBufSize/1024); // KB size
oMfc.m_bMbBitReport[uProcessIdx] = bMbBitReport;
oMfc.m_bSliceInfoReport[uProcessIdx] = bSliceInfoReport;
oMfc.m_bAudEnable[uProcessIdx] = bAudEnable;
oMfc.m_bSkipDisable[uProcessIdx] = bSkipDisable;
uMbBitReportBit = (oMfc.m_bMbBitReport[uProcessIdx]) ? (1<<0) : (0<<0);
uSliceInfoReportBit = (oMfc.m_bSliceInfoReport[uProcessIdx]) ? (1<<1) : (0<<1);
uAudEnableBit = (oMfc.m_bAudEnable[uProcessIdx]) ? (1<<2) : (0<<2);
uEncSeqOptionValue = uAudEnableBit | uSliceInfoReportBit | uMbBitReportBit;
mfcOutp32(ENC_SEQ_OPTION, uEncSeqOptionValue);
MFC_IssueCmd(uProcessIdx, SEQ_INIT);
stat = MFC_IsCmdFinished();
if(stat == false)
{
Disp("\n There is an error in the SEQ_INIT result\n");
return;
}
}
void MFC_IssueSeqEndCmd(u32 uRunIdx)
{
MFC_IssueCmd(uRunIdx, SEQ_END);
}
void MFC_MoveFirmwareToCodeBuf(u32 uFreeBufAddr)
{
u32 i;
u32 data;
//StopBitProcessor();
MFC_ResetIp();
// Boot code(1KB) + Codec Firmware (79KB)
for (i=0 ; i<sizeof(bit_code)/sizeof(bit_code[0]); i+=2)
{
data = (bit_code[i] << 16) | bit_code[i+1];
Outp32(uFreeBufAddr+(i-0)*2, data);
}
DbgMfc(" CODE_BUF = 0x%x\n",uFreeBufAddr);
mfcOutp32(CODE_BUF_ADDR, uFreeBufAddr); // point at boot code start addr
oMfc.m_uCodeBufEndAddr = uFreeBufAddr + (sizeof(bit_code)/sizeof(bit_code[0])-0)*2; // 80KB(PRISM) for Code and Coeff ROM table
// 512 word (Boot Code, 1KB)
for (i=0; i<512; i++)
{
data = bit_code[i];
Outp32(CODE_DN_LOAD, (i<<16) | data); // i: 13bit addr
}
}
void MFC_SetParameterBufAddr(u32 uFreeBufAddr)
{
DbgMfc(" Parameter buf = 0x%x\n",uFreeBufAddr);
oMfc.m_uParameterBufStartAddr = uFreeBufAddr;
mfcOutp32(PARA_BUF_ADDR, uFreeBufAddr);
oMfc.m_uParameterBufEndAddr = uFreeBufAddr + 8*1024; // 8KB for BIT processor parameter buffer
}
void MFC_SetStreamBufControlOption(bool isLittleEndian, bool isFlowCheckEnable)
{
u32 uRegData;
u32 uEndianMode = (isLittleEndian) ? STREAM_ENDIAN_LITTLE: STREAM_ENDIAN_BIG;
u32 uStatusCheckMode = (isFlowCheckEnable) ? BUF_STATUS_FULL_EMPTY_CHECK_BIT: BUF_STATUS_NO_CHECK_BIT;
uRegData = mfcInp32(STREAM_BUF_CTRL);
mfcOutp32(STREAM_BUF_CTRL, uRegData&~(0x03)|uStatusCheckMode|uEndianMode);
}
void MFC_SetFrameBufEndianMode(bool isLittleEndian)
{
u32 uEndianMode = (isLittleEndian) ? FRAME_MEM_ENDIAN_LITTLE : FRAME_MEM_ENDIAN_BIG;
mfcOutp32(FRAME_BUF_CTRL, uEndianMode);
}
void MFC_SetUpWorkingBuf(u32 uFreeBufAddr)
{
MFC_SetWorkBufConfig(false);
DbgMfc(" Working buf = 0x%x\n",uFreeBufAddr);
mfcOutp32(WORK_BUF_ADDR, uFreeBufAddr);
oMfc.m_uWorkingBufEndAddr = uFreeBufAddr + 1024*1024; // 1024KB for BIT processor working buffer
}
// below size unit is KB.
void MFC_SetUpWorkingBuf2(
u32 uFreeBufAddr, u32 uProcessBufSize,
u32 uDecBuf1Size, u32 uDecBuf2Size, u32 uDecBuf3Size, u32 uDecBuf4Size, u32 uDecBuf5Size,
u32 uEncBuf1Size, u32 uEncBuf2Size, u32 uEncBuf3Size, u32 uEncBuf4Size)
{
u32 uBufAddr;
MFC_SetWorkBufConfig(true);
DbgMfc(" Working buf = 0x%x\n",uFreeBufAddr);
mfcOutp32(WORK_BUF_ADDR, uFreeBufAddr);
uBufAddr = uFreeBufAddr + 78*1024;
MFC_SetProcessBufStAddr(uBufAddr);
uBufAddr += uProcessBufSize*1024;
MFC_SetDecTempBuf1StAddr(uBufAddr);
uBufAddr += uDecBuf1Size*1024;
MFC_SetDecTempBuf2StAddr(uBufAddr);
uBufAddr += uDecBuf2Size*1024;
MFC_SetDecTempBuf3StAddr(uBufAddr);
uBufAddr += uDecBuf3Size*1024;
MFC_SetDecTempBuf4StAddr(uBufAddr);
uBufAddr += uDecBuf4Size*1024;
MFC_SetDecTempBuf5StAddr(uBufAddr);
uBufAddr += uDecBuf5Size*1024;
MFC_SetEncTempBuf1StAddr(uBufAddr);
uBufAddr += uEncBuf1Size*1024;
MFC_SetEncTempBuf2StAddr(uBufAddr);
uBufAddr += uEncBuf2Size*1024;
MFC_SetEncTempBuf3StAddr(uBufAddr);
uBufAddr += uEncBuf3Size*1024;
MFC_SetEncTempBuf4StAddr(uBufAddr);
uBufAddr += uEncBuf4Size*1024;
oMfc.m_uWorkingBufEndAddr = uBufAddr;
}
// below size unit is KB.
void MFC_SetUpWorkingBuf1(u32 uFreeBufAddr, MFC_APP_TYPE eAppType)
{
u32 uBufAddr;
u32 uBufSizeArray[][10] = {
{128, 30, 15, 15, 4, 150, 0, 0, 0, 0}, // DMB decoding
{128, 36, 48, 48, 14, 608, 0, 0, 0, 0}, // Conformance decoding // total = 882 KB
{32, 36, 48, 48, 14, 16, 36, 48, 200, 256} // Conformance encoding // total = 734 KB
};
u32 uIdx =
(eAppType == DECODING_DMB) ? 0 :
(eAppType == DECODING_CONFORMANCE) ? 1 :
(eAppType == ENCODING_WITH_ALL_PARAMETERS) ? 2 : 0xff;
MFC_SetWorkBufConfig(true);
DbgMfc(" Working buf = 0x%x\n",uFreeBufAddr);
mfcOutp32(WORK_BUF_ADDR, uFreeBufAddr);
uBufAddr = uFreeBufAddr + 78*1024;
Assert(uIdx != 0xff);
MFC_SetProcessBufStAddr(uBufAddr);
uBufAddr += uBufSizeArray[uIdx][0]*1024;
MFC_SetDecTempBuf1StAddr(uBufAddr);
uBufAddr += uBufSizeArray[uIdx][1]*1024;
MFC_SetDecTempBuf2StAddr(uBufAddr);
uBufAddr += uBufSizeArray[uIdx][2]*1024;
MFC_SetDecTempBuf3StAddr(uBufAddr);
uBufAddr += uBufSizeArray[uIdx][3]*1024;
MFC_SetDecTempBuf4StAddr(uBufAddr);
uBufAddr += uBufSizeArray[uIdx][4]*1024;
MFC_SetDecTempBuf5StAddr(uBufAddr);
uBufAddr += uBufSizeArray[uIdx][5]*1024;
MFC_SetEncTempBuf1StAddr(uBufAddr);
uBufAddr += uBufSizeArray[uIdx][6]*1024;
MFC_SetEncTempBuf2StAddr(uBufAddr);
uBufAddr += uBufSizeArray[uIdx][7]*1024;
MFC_SetEncTempBuf3StAddr(uBufAddr);
uBufAddr += uBufSizeArray[uIdx][8]*1024;
MFC_SetEncTempBuf4StAddr(uBufAddr);
uBufAddr += uBufSizeArray[uIdx][9]*1024;
oMfc.m_uWorkingBufEndAddr = uBufAddr;
}
void MFC_InitBaseForProcesses(u32 uFreeBufAddr)
{
u32 uBufAddr;
MFC_SetUpWorkingBuf(uFreeBufAddr);
MFC_GetWorkingBufEndAddr(&uBufAddr);
MFC_SetParameterBufAddr(uBufAddr);
MFC_SetStreamBufControlOption(true, true); // Full/Empty check enable(true) + Little Endian(true)
MFC_SetFrameBufEndianMode(true); // Little endian (true)
MFC_SetUnmask(INT_MFC_ALL); // all interrupt enable
MFC_SetBitstreamEndFlag(false);
}
void MFC_InitBaseForProcesses2(
u32 uFreeBufAddr, u32 uProcessBufSize,
u32 uDecBuf1Size, u32 uDecBuf2Size, u32 uDecBuf3Size, u32 uDecBuf4Size, u32 uDecBuf5Size,
u32 uEncBuf1Size, u32 uEncBuf2Size, u32 uEncBuf3Size, u32 uEncBuf4Size)
{
u32 uBufAddr;
MFC_SetUpWorkingBuf2(uFreeBufAddr, uProcessBufSize,
uDecBuf1Size, uDecBuf2Size, uDecBuf3Size, uDecBuf4Size, uDecBuf5Size,
uEncBuf1Size, uEncBuf2Size, uEncBuf3Size, uEncBuf4Size);
MFC_GetWorkingBufEndAddr(&uBufAddr);
MFC_SetParameterBufAddr(uBufAddr);
MFC_SetStreamBufControlOption(true, true); // Full/Empty check enable(true) + Little Endian(true)
MFC_SetFrameBufEndianMode(true); // Little endian (true)
MFC_SetUnmask(INT_MFC_ALL); // all interrupt enable
MFC_SetBitstreamEndFlag(false);
}
void MFC_InitBaseForProcesses1(u32 uFreeBufAddr, MFC_APP_TYPE eAppType)
{
u32 uBufAddr;
MFC_SetUpWorkingBuf1(uFreeBufAddr, eAppType);
MFC_GetWorkingBufEndAddr(&uBufAddr);
MFC_SetParameterBufAddr(uBufAddr);
MFC_SetStreamBufControlOption(true, true); // Full/Empty check enable(true) + Little Endian(true)
MFC_SetFrameBufEndianMode(true); // Little endian (true)
MFC_SetUnmask(INT_MFC_ALL); // all interrupt enable
MFC_SetBitstreamEndFlag(false);
}
void MFC_WaitForReady(void)
{
u32 uRegData;
do
{
uRegData = mfcInp32(BUSY_FLAG);
} while(uRegData != 0); // 0: ready, 1: busy
}
void MFC_IssueCmd(u32 uProcessIdx, MFC_COMMAND runCmd)
{
MFC_StartIssuingCmd(uProcessIdx, runCmd);
MFC_WaitForReady();
}
void MFC_StartIssuingCmd(u32 uProcessIdx, MFC_COMMAND eCmd)
{
u32 runStd, uRunCmd;
MFC_WaitForReady();
mfcOutp32(RUN_INDEX, uProcessIdx);
runStd =
(oMfc.m_eCodecMode[uProcessIdx] == MP4_DEC) ? 0 :
(oMfc.m_eCodecMode[uProcessIdx] == MP4_ENC) ? 1 :
(oMfc.m_eCodecMode[uProcessIdx] == AVC_DEC) ? 2 :
(oMfc.m_eCodecMode[uProcessIdx] == AVC_ENC) ? 3 :
(oMfc.m_eCodecMode[uProcessIdx] == VC1_DEC) ? 4 : 0;
mfcOutp32(RUN_COD_STD, runStd);
uRunCmd =
(eCmd == SEQ_INIT) ? 1 :
(eCmd == SEQ_END) ? 2 :
(eCmd == PIC_RUN) ? 3 :
(eCmd == SET_FRAME_BUF) ? 4 :
(eCmd == ENCODE_HEADER) ? 5 :
(eCmd == ENC_PARA_SET) ? 6 :
(eCmd == DEC_PARA_SET) ? 7 :
(eCmd == GET_FW_VER) ? 0xf : 0xff;
//////////
//s/w work-around(2007.03.21)
// : write the busy flag compulsorily
// in order to remove the decoding error when mfcclk is less than pclk
mfcOutp32(BUSY_FLAG,0x1);
//////////
mfcOutp32(RUN_CMD, uRunCmd);
}
void MFC_StartBitProcessor(void)
{
DbgMfc("[ Execution Start... ]\n");
mfcOutp32(CODE_RUN, 0x1);
}
void MFC_StopBitProcessor(void)
{
mfcOutp32(CODE_RUN, 0x0);
}
void MFC_ResetProgramCounterOfBitCode(void)
{
mfcOutp32(BITS_CODE_RESET, 1);
}
void MFC_ResetIp(void)
{
mfcOutp32(SW_RESET, 0);
mfcOutp32(SW_RESET, 1);
}
void MFC_GetDecSrcFormat(u32* uWidth, u32* uHeight, float* uFrameRate)
{
u32 data;
u32 uFrameRateDiv;
u32 uFrameRateRes;
data = mfcInp32(RET_DEC_SEQ_SRC_SIZE);
*uWidth = (data >> 10) & 0x3FF;
*uHeight = (data >> 0) & 0x3FF;
data = mfcInp32(RET_DEC_SEQ_SRC_FRAME_RATE);
uFrameRateDiv = (data >> 16) & 0xffff;
uFrameRateRes = data & 0xffff;
//DbgMfc("uFrameRateDiv+1=%d, uFrameRateRes=%d\n",uFrameRateDiv+1,uFrameRateRes);
*uFrameRate = (float)uFrameRateRes / (float)(uFrameRateDiv+1);
}
void MFC_GetEncSrcSize(u32* uWidth, u32* uHeight)
{
u32 data;
data = mfcInp32(ENC_SEQ_SRC_SIZE);
*uWidth = (data >> 10) & 0x3FF;
*uHeight = (data >> 0) & 0x3FF;
}
void MFC_GetMp4Info(bool* isDataPartEn, bool* isRevVlcEn, bool* isShortVideoHeader)
{
u32 data;
data = mfcInp32(RET_DEC_SEQ_INFO);
//DbgMfc("getMp4Info()=%d\n",data);
data = data & 0x7;
if (data & 4)
{
*isShortVideoHeader = true;
*isDataPartEn = false;
*isRevVlcEn = false;
}
else
{
if (data & 1)
{
*isDataPartEn = true;
*isShortVideoHeader = false;
if (data & 2)
*isRevVlcEn = true;
else
*isRevVlcEn = false;
}
else
{
*isDataPartEn = false;
*isShortVideoHeader = false;
*isRevVlcEn = false;
}
}
}
void MFC_IsDecH263AnnexJOn(u32 runIdx, bool* bAnnexJOn)
{
if (oMfc.m_eCodecMode[runIdx] == MP4_DEC)
{
u32 uRegData;
uRegData = mfcInp32(RET_DEC_SEQ_INFO);
*bAnnexJOn = (uRegData&(1<<3)) ? true : false;
}
else
{
*bAnnexJOn = false;
}
}
void MFC_GetDecRefFrameNum(u32 uProcessIdx, u32* uRefFrameNum)
{
u32 data;
data = mfcInp32(RET_DEC_SEQ_FRAME_NEED_COUNT);
*uRefFrameNum = data & 0x1F;
oMfc.m_uRefFrameNum[uProcessIdx] = *uRefFrameNum;
}
void MFC_GetDispFrameNum(u32 uProcessIdx, u32* uDispFrameNum)
{
MFC_CODEC_MODE eMode;
u32 uNumOfFrames;
Assert(uProcessIdx < MAX_PROCESS_NUM);
eMode = oMfc.m_eCodecMode[uProcessIdx];
if (eMode == MP4_DEC || eMode == AVC_DEC || eMode == VC1_DEC)
{
uNumOfFrames = (oMfc.m_bMp4DecDeblkMode[uProcessIdx] && !oMfc.m_bAnnexJOn[uProcessIdx]) ?
oMfc.m_uRefFrameNum[uProcessIdx]+2 : oMfc.m_uRefFrameNum[uProcessIdx];
*uDispFrameNum = (oMfc.m_bDecRotEn[uProcessIdx]) ? uNumOfFrames+2 : uNumOfFrames;
}
else if (eMode == MP4_ENC || eMode == AVC_ENC)
{
*uDispFrameNum = oMfc.m_uRefFrameNum[uProcessIdx];
}
else
Assert(0);
}
void MFC_InitDecFrameBuffer(
u32 uProcessIdx,
u32 uFrameBufNum,
u32 uStride,
u32 uHeight,
u32 uFrameBuf)
{
u32 k;
u32 uBufAddr = uFrameBuf;
u32 i;
//DbgMfc("addrY=0x%x\n",addrY);
if(uStride%16!=0)
Disp("ERROR=>uStride is not multiple of 16\n");
Assert(uStride%16==0);
if(uStride>720)
Disp("ERROR=>uStride=%d(>720)\n",uStride);
Assert(uStride <= 720);
if(uHeight>576)
Disp("ERROR=>uHeight=%d(>576)\n",uHeight);
Assert(uHeight <= 576);
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -