📄 umc_vc1_dec_blk_com.cpp
字号:
/* /////////////////////////////////////////////////////////////////////////////
//
// INTEL CORPORATION PROPRIETARY INFORMATION
// This software is supplied under the terms of a license agreement or
// nondisclosure agreement with Intel Corporation and may not be copied
// or disclosed except in accordance with the terms of that agreement.
// Copyright(c) 2004-2007 Intel Corporation. All Rights Reserved.
//
//
// VC-1 (VC1) decoder, block layer, common file
//
*/
#include "umc_defs.h"
#if defined (UMC_ENABLE_VC1_VIDEO_DECODER)
#include "umc_vc1_dec_seq.h"
#include "umc_vc1_dec_debug.h"
#include "umc_vc1_common_blk_order_tbl.h"
#include "umc_vc1_dec_time_statistics.h"
#include "assert.h"
#include "umc_vc1_dec_exception.h"
using namespace UMC;
using namespace UMC::VC1Exceptions;
Ipp32s DecodeSymbol(IppiBitstream* pBitstream, Ipp16s* run, Ipp16s* level,
const IppiACDecodeSet_VC1 * decodeSet,IppiEscInfo_VC1* EscInfo)
{
IppStatus ret;
Ipp32s sign = 0;
Ipp32s code = 0;
Ipp32s escape_mode = 0;
Ipp32s ESCLR = 0;
Ipp32s tmp_run = 0;
Ipp32s tmp_level = 0;
Ipp32s last = 0;
ret = ippiDecodeHuffmanOne_1u32s (&pBitstream->pBitstream,
&pBitstream->bitOffset,
&code, decodeSet->pRLTable);
//VM_ASSERT(ret == ippStsNoErr);
if (ret != ippStsNoErr)
throw vc1_exception(vld);
#ifdef VC1_DEBUG_ON
if(code == IPPVC_ESCAPE)
VM_Debug::GetInstance(VC1DebugRoutine).vm_debug_frame(-1,VC1_COEFFS,
VM_STRING("Index = ESCAPE\n"));
//else
//{
// VM_Debug::GetInstance(VC1DebugRoutine).vm_debug_frame(-1,
// VC1_COEFFS,VM_STRING("Index = %d\n"), code);
//
// VM_Debug::GetInstance(VC1DebugRoutine).vm_debug_frame(-1,
// VC1_COEFFS,VM_STRING("Offset = %d\n"), pContext->m_bitOffset);
//}
#endif
if(code != IPPVC_ESCAPE)
{
tmp_run = (code & 0X0000FF00)>>8;
tmp_level = code & 0X000000FF;
last = code >> 16;
VC1BitstreamParser::GetNBits((pBitstream->pBitstream), (pBitstream->bitOffset), 1, sign);
tmp_level = (1-(sign<<1))*tmp_level;
}
else
{
VC1BitstreamParser::GetNBits((pBitstream->pBitstream), (pBitstream->bitOffset), 1, escape_mode);
if(escape_mode == 1)
{
#ifdef VC1_DEBUG_ON
VM_Debug::GetInstance(VC1DebugRoutine).vm_debug_frame(-1,VC1_COEFFS,
VM_STRING("Index = ESCAPE Mode 1\n"));
#endif
ret = ippiDecodeHuffmanOne_1u32s ((&pBitstream->pBitstream), (&pBitstream->bitOffset), &code,
decodeSet->pRLTable);
if (ret != ippStsNoErr)
throw vc1_exception(vld);
tmp_run = (code & 0X0000FF00)>>8;
tmp_level = code & 0X000000FF;
last = code>>16;
if (last)
tmp_level = tmp_level + decodeSet->pDeltaLevelLast1[tmp_run];
else
tmp_level = tmp_level + decodeSet->pDeltaLevelLast0[tmp_run];
VC1BitstreamParser::GetNBits((pBitstream->pBitstream), (pBitstream->bitOffset), 1, sign);
tmp_level = (1-(sign<<1))*tmp_level;
}
else
{
VC1BitstreamParser::GetNBits((pBitstream->pBitstream), (pBitstream->bitOffset), 1, escape_mode);
if(escape_mode == 1)
{
#ifdef VC1_DEBUG_ON
VM_Debug::GetInstance(VC1DebugRoutine).vm_debug_frame(-1,VC1_COEFFS,
VM_STRING("Index = ESCAPE Mode 2\n"));
#endif
ret = ippiDecodeHuffmanOne_1u32s ((&pBitstream->pBitstream), (&pBitstream->bitOffset),
&code, decodeSet->pRLTable);
if (ret != ippStsNoErr)
throw vc1_exception(vld);
tmp_run = (code & 0X0000FF00)>>8;
tmp_level = code & 0X000000FF;
last = (code&0x00FF0000)>>16;
if (last)
tmp_run = tmp_run + decodeSet->pDeltaRunLast1[tmp_level] + 1;
else
tmp_run = tmp_run + decodeSet->pDeltaRunLast0[tmp_level] + 1;
VC1BitstreamParser::GetNBits((pBitstream->pBitstream), (pBitstream->bitOffset), 1, sign);
tmp_level = (1-(sign<<1))*tmp_level;
}
else
{
#ifdef VC1_DEBUG_ON
VM_Debug::GetInstance(VC1DebugRoutine).vm_debug_frame(-1,VC1_COEFFS,
VM_STRING("Index = ESCAPE Mode 3\n"));
#endif
VC1BitstreamParser::GetNBits((pBitstream->pBitstream), (pBitstream->bitOffset), 1, ESCLR);
last = ESCLR;
if (EscInfo->levelSize + EscInfo->runSize == 0)
{
if(EscInfo->bEscapeMode3Tbl == VC1_ESCAPEMODE3_Conservative)
{
VC1BitstreamParser::GetNBits((pBitstream->pBitstream), (pBitstream->bitOffset), 3, EscInfo->levelSize);
if(EscInfo->levelSize == 0)
{
VC1BitstreamParser::GetNBits((pBitstream->pBitstream), (pBitstream->bitOffset), 2, EscInfo->levelSize);
EscInfo->levelSize += 8;
}
}
else
{
Ipp32s bit_count = 1;
VC1BitstreamParser::GetNBits((pBitstream->pBitstream), (pBitstream->bitOffset), 1, EscInfo->levelSize);
while((EscInfo->levelSize == 0) && (bit_count < 6))
{
VC1BitstreamParser::GetNBits((pBitstream->pBitstream), (pBitstream->bitOffset), 1, EscInfo->levelSize);
bit_count++;
}
if(bit_count == 6 && EscInfo->levelSize == 0)
bit_count++;
EscInfo->levelSize = bit_count + 1;
}
VC1BitstreamParser::GetNBits((pBitstream->pBitstream), (pBitstream->bitOffset), 2, EscInfo->runSize);
EscInfo->runSize = 3 + EscInfo->runSize;
}
VC1BitstreamParser::GetNBits((pBitstream->pBitstream), (pBitstream->bitOffset), EscInfo->runSize, tmp_run);
VC1BitstreamParser::GetNBits((pBitstream->pBitstream), (pBitstream->bitOffset), 1, sign);
VC1BitstreamParser::GetNBits((pBitstream->pBitstream), (pBitstream->bitOffset), EscInfo->levelSize,tmp_level);
tmp_level = (1-(sign<<1))*tmp_level;
}
}
}
(*run) = (Ipp16s)tmp_run;
(*level) = (Ipp16s)tmp_level;
return last;
}
IppStatus DecodeBlockACIntra_VC1(IppiBitstream* pBitstream, Ipp16s* pDst,
const Ipp8u* pZigzagTbl, const IppiACDecodeSet_VC1 * pDecodeSet,
IppiEscInfo_VC1* pEscInfo)
{
Ipp32s last_flag = 0;
Ipp16s run = 0, level = 0;
Ipp32s curr_position = 1;
IppStatus sts = ippStsNoErr;
if((!pBitstream)||(!pDst) || (!pDecodeSet) || (!pZigzagTbl) || (!pEscInfo) || (!pBitstream->pBitstream))
//return ippStsNullPtrErr;
throw vc1_exception(internal_pipeline_error); // Global problem, no need to decode more
if((pBitstream->bitOffset < 0) || (pBitstream->bitOffset>31))
throw vc1_exception(internal_pipeline_error);// Global problem, no need to decode more
//return ippStsBitOffsetErr;
do
{
last_flag = DecodeSymbol(pBitstream, &run, &level, pDecodeSet, pEscInfo);
#ifdef VC1_DEBUG_ON
VM_Debug::GetInstance(VC1DebugRoutine).vm_debug_frame(-1,VC1_COEFFS,
VM_STRING("AC Run=%2d Level=%c%3d Last=%d\n"),
run,
(level < 0) ? '-' : '+',
(level < 0) ? -level : level,
last_flag);
#endif
if(curr_position > 64)
{
throw vc1_exception(vld);
}
curr_position = curr_position + run;
pDst[pZigzagTbl[curr_position]] = pDst[pZigzagTbl[curr_position]] + level;
curr_position++;
} while (last_flag == 0);
return sts;
}
IppStatus DecodeBlockInter8x8_VC1(IppiBitstream* pBitstream, Ipp16s* pDst,
const Ipp8u* pZigzagTbl, const IppiACDecodeSet_VC1 * pDecodeSet,
IppiEscInfo_VC1* pEscInfo, Ipp32s subBlockPattern)
{
Ipp32s last_flag = 0;
Ipp16s run = 0, level = 0;
Ipp32s curr_position = 0;
IppStatus sts = ippStsNoErr;
if((!pBitstream)||(!pDst) || (!pDecodeSet) || (!pZigzagTbl) || (!pEscInfo) || (!pBitstream->pBitstream))
//return ippStsNullPtrErr;
throw vc1_exception(internal_pipeline_error); // Global problem, no need to decode more
if((pBitstream->bitOffset < 0) || (pBitstream->bitOffset>31))
//return ippStsBitOffsetErr;
throw vc1_exception(internal_pipeline_error); // Global problem, no need to decode more
do
{
last_flag = DecodeSymbol(pBitstream, &run, &level, pDecodeSet, pEscInfo);
#ifdef VC1_DEBUG_ON
VM_Debug::GetInstance(VC1DebugRoutine).vm_debug_frame(-1,VC1_COEFFS,
VM_STRING("AC Run=%2d Level=%c%3d Last=%d\n"),
run,
(level < 0) ? '-' : '+',
(level < 0) ? -level : level,
last_flag);
#endif
if(curr_position > 64)
{
throw vc1_exception(vld);
}
curr_position = curr_position + run;
pDst[pZigzagTbl[curr_position]] = pDst[pZigzagTbl[curr_position]] + level;
curr_position++;
} while (last_flag == 0);
return sts;
}
IppStatus DecodeBlockInter4x8_VC1(IppiBitstream* pBitstream, Ipp16s* pDst,
const Ipp8u* pZigzagTbl, const IppiACDecodeSet_VC1 * pDecodeSet,
IppiEscInfo_VC1* pEscInfo, Ipp32s subBlockPattern)
{
Ipp32s last_flag = 0;
Ipp16s run = 0, level = 0;
Ipp32s curr_position = 0;
IppStatus sts = ippStsNoErr;
if((!pBitstream)||(!pDst) || (!pDecodeSet) || (!pZigzagTbl) || (!pEscInfo) || (!pBitstream->pBitstream))
//return ippStsNullPtrErr;
throw vc1_exception(internal_pipeline_error); // Global problem, no need to decode more
if((pBitstream->bitOffset < 0) || (pBitstream->bitOffset>31))
//return ippStsBitOffsetErr;
throw vc1_exception(internal_pipeline_error); // Global problem, no need to decode more
if(subBlockPattern & VC1_SBP_0)
do
{
last_flag = DecodeSymbol(pBitstream, &run, &level, pDecodeSet, pEscInfo);
#ifdef VC1_DEBUG_ON
VM_Debug::GetInstance(VC1DebugRoutine).vm_debug_frame(-1,VC1_COEFFS,
VM_STRING("AC Run=%2d Level=%c%3d Last=%d\n"),
run,
(level < 0) ? '-' : '+',
(level < 0) ? -level : level,
last_flag);
#endif
if(curr_position > 64)
{
// we can decode next MB
throw vc1_exception(vld);
}
curr_position = curr_position + run;
pDst[pZigzagTbl[curr_position]] = pDst[pZigzagTbl[curr_position]] + level;
curr_position++;
} while (last_flag == 0);
curr_position = 0;
if(subBlockPattern & VC1_SBP_1)
do
{
last_flag = DecodeSymbol(pBitstream, &run, &level, pDecodeSet, pEscInfo);
#ifdef VC1_DEBUG_ON
VM_Debug::GetInstance(VC1DebugRoutine).vm_debug_frame(-1,VC1_COEFFS,
VM_STRING("AC Run=%2d Level=%c%3d Last=%d\n"),
run,
(level < 0) ? '-' : '+',
(level < 0) ? -level : level,
last_flag);
#endif
if(curr_position > 64)
throw vc1_exception(vld);
curr_position = curr_position + run;
pDst[pZigzagTbl[curr_position + 32]] = pDst[pZigzagTbl[curr_position + 32]] + level;
curr_position++;
} while (last_flag == 0);
return sts;
}
IppStatus DecodeBlockInter8x4_VC1(IppiBitstream* pBitstream, Ipp16s* pDst,
const Ipp8u* pZigzagTbl, const IppiACDecodeSet_VC1 * pDecodeSet,
IppiEscInfo_VC1* pEscInfo, Ipp32s subBlockPattern)
{
Ipp32s last_flag = 0;
Ipp16s run = 0, level = 0;
Ipp32s curr_position = 0;
IppStatus sts = ippStsNoErr;
if((!pBitstream)||(!pDst) || (!pDecodeSet) || (!pZigzagTbl) || (!pEscInfo) || (!pBitstream->pBitstream))
//return ippStsNullPtrErr;
throw vc1_exception(internal_pipeline_error); // Global problem, no need to decode more
if((pBitstream->bitOffset < 0) || (pBitstream->bitOffset>31))
//return ippStsBitOffsetErr;
throw vc1_exception(internal_pipeline_error); // Global problem, no need to decode more
if(subBlockPattern & VC1_SBP_0)
do
{
last_flag = DecodeSymbol(pBitstream, &run, &level, pDecodeSet, pEscInfo);
#ifdef VC1_DEBUG_ON
VM_Debug::GetInstance(VC1DebugRoutine).vm_debug_frame(-1,VC1_COEFFS,
VM_STRING("AC Run=%2d Level=%c%3d Last=%d\n"),
run,
(level < 0) ? '-' : '+',
(level < 0) ? -level : level,
last_flag);
#endif
if(curr_position > 64)
{
throw vc1_exception(vld);
}
curr_position = curr_position + run;
pDst[pZigzagTbl[curr_position]] = pDst[pZigzagTbl[curr_position]] + level;
curr_position++;
} while (last_flag == 0);
curr_position = 0;
if(subBlockPattern & VC1_SBP_1)
do
{
last_flag = DecodeSymbol(pBitstream, &run, &level, pDecodeSet, pEscInfo);
#ifdef VC1_DEBUG_ON
VM_Debug::GetInstance(VC1DebugRoutine).vm_debug_frame(-1,VC1_COEFFS,
VM_STRING("AC Run=%2d Level=%c%3d Last=%d\n"),
run,
(level < 0) ? '-' : '+',
(level < 0) ? -level : level,
last_flag);
#endif
if(curr_position > 64)
{
throw vc1_exception(vld);
}
curr_position = curr_position + run;
pDst[pZigzagTbl[curr_position + 32]] = pDst[pZigzagTbl[curr_position + 32]] + level;
curr_position++;
} while (last_flag == 0);
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -