📄 umc_h264_aic.cpp
字号:
}*/
dstPtr++;
srcPtr++;
}
/*
*pCopyDst = *(pCopyDst + 1)= *pCopySrc; // 4 bytes left & right block
if( m_PicParamSet.chroma_format_idc == 3 ){
*(pCopyDst+2) = *(pCopyDst + 3)=*pCopyDst;
}
*/
pCopySrc += sizeof(PixType);
pCopyDst += 4*sizeof(PixType); // pitch is 16*sizeof(PixType)
}
}
break;
case PRED8x8_DC:
for (plane=0; plane<2; plane++) {
// top row
pPred = plane ? pVPredBuf : pUPredBuf;
// Copy 8 rows
pCopySrc = (Ipp32u *)&uDCPred[plane][0]; // Rewrite for 16 bits.
pCopyDst = (Ipp32u *)pPred;
for (i=0; i<num_rows; i++)
{
Ipp32u *srcPtr = pCopySrc;
Ipp32u *dstPtr = pCopyDst;
for(Ipp32s j = 0; j < sizeof(PixType); j++) {
*dstPtr = *srcPtr;
*(dstPtr + sizeof(PixType)) = *(srcPtr + 4*sizeof(PixType));
/*if(m_PicParamSet.chroma_format_idc == 3) {
*(dstPtr + 2*sizeof(PixType)) = 0;
*(dstPtr + 3*sizeof(PixType)) = 0;
}*/
dstPtr++;
srcPtr++;
}
if((i & 0x03) == 0x03) pCopySrc += 5*sizeof(PixType);
else pCopySrc += sizeof(PixType);
pCopyDst += 4*sizeof(PixType);
}
/**pCopyDst = *pCopySrc; // 4 bytes left block
*(pCopyDst + 1) = *(pCopySrc+4); // 4 bytes right block (adds 16 bytes)
// if( m_PicParamSet.chroma_format_idc == 3 ){
// *(pCopyDst + 2) = 0; //*(pCopySrc+8); // 4 bytes left block
// *(pCopyDst + 3) = 0; //*(pCopySrc+12); // 4 bytes right block
// }
*/
}
break;
case PRED8x8_PLANAR:
// nothing to do, planar prediction already filled PredBuf
break;
default:
VM_ASSERT( 0 /*Can't find the best intra prediction 8x8!!!*/);
break;
}
*pMode = (Ipp8u)Best8x8Type;
return uSmallestSAD;
} // C_AIModeSelectChromaMBs_8x8
////////////////////////////////////////////////////////////////////////////////
//
// PlanarPredictLuma [This function conforms with the JVT FCD, but the #if 0'd
// version above is probably correct.]
//
// Find the planar prediction for this 16x16 MB, store at pPredBuf.
//
// Uses 15 pels from the reconstructed macroblock above and 15 pels from the
// reconstructed macroblock to the left and 1 pel from the macroblock to the NW
// to form a 16x16 prediction macroblock.
//
// L0,a0 a1 a2 a3 a4 a5 a6 a7 -- a9 a10 a11 a12 a13 a14 a15 a16
// L1 x x x x x x x x x x x x x x x x
// L2 x x x x x x x x x x x x x x x x
// ...
// L7 x x x x x x x x x x x x x x x x
// -- x x x x x x x x x x x x x x x x
// L9 x x x x x x x x x x x x x x x x
// ...
// L16 x x x x x x x x x x x x x x x x
//
// Above predictors are a0..a7 & a9..a16, left predictors are L0..L7 & L9..L15,
// x indicates pels to be predicted.
//
// 1. Obtain weighted sum of differences of above predictors:
// H = 8*(a16-a0) + 7*(a15-a1) + 6*(a14-a2) + ... + 1*(a9-a7)
// 2. Obtain weighted sum of differences of left predictors:
// V = 8*(L16-L0) + 7*(L15-L1) + 6*(L14-L2) + ... + 1*(L9-L7)
// 3. Calculate a,b,c terms (level, horiz slope factor, vert slope factor):
// a = (a16 + L16) *16
// b = (5*H + 32) >> 6
// c = (5*V + 32) >> 6
// 4. Use a,b,c to calculate a predictor at each x,y of the 16x16 macroblock,
// where x is horizontal index and y is vertical index:
// pred = ((a + (i-7)*b + (j-7)*c) + 16)>>5
//
// Note this function will reference pels above and to the left of the
// current macroblock so should not be called at top or left picture edge.
//
////////////////////////////////////////////////////////////////////////////////
template <class PixType, class CoeffsType>
void H264CoreEncoder<PixType,CoeffsType>::PlanarPredictLuma(PixType* pBlock, // pointer to upper left pel of block
Ipp32u uPitch, // of reference plane
PixType *pPredBuf)
{
PixType ap[17], lp[17];
Ipp32s iH;
Ipp32s iV;
Ipp32s x, y;
Ipp32s a,b,c;
Ipp32s temp;
PixType max_pix_value = (1<<m_PicParamSet.bit_depth_luma) - 1;
for (x=0;x<17;x++) {
ap[x]=(pBlock-Ipp32s(uPitch)-1)[x];
lp[x]=(pBlock+Ipp32s(uPitch)*(x-1))[-1];
}
iH = 0;
iV = 0;
for (x=1; x<=8; x++)
{
iH += x*(ap[8+x] - ap[8-x]);
iV += x*(lp[8+x] - lp[8-x]);
}
a = (ap[16] + lp[16])*16;
b = (5*iH + 32)>>6;
c = (5*iV + 32)>>6;
for (y=0; y<16; y++)
for (x=0; x<16; x++)
{
temp= (a+(x-7)*b+(y-7)*c+16)>>5;
temp= (temp>max_pix_value)?max_pix_value:temp;
temp= (temp<0)?0:temp;
pPredBuf[x + y*16]=(PixType) temp;
}
} // C_PlanarPredictLuma
////////////////////////////////////////////////////////////////////////////////
//
// PlanarPredictChroma [This function conforms with the JVT FCD, but the #if 0'd
// version above is probably correct.]
//
// Find the planar prediction for this 8x8 MB, store at pPredBuf.
//
// Uses 7 pels from the reconstructed macroblock above and 7 pels from the
// reconstructed macroblock to the left and 1 pel from the macroblock to the NW
// to form a 8x8 prediction macroblock.
//
// L0,a0 a1 a2 a3 -- a5 a6 a7 a8
// L1 x x x x x x x x
// L2 x x x x x x x x
// L3 x x x x x x x x
// -- x x x x x x x x
// L5 x x x x x x x x
// L6 x x x x x x x x
// L7 x x x x x x x x
// L8 x x x x x x x x
//
// Above predictors are a0..a3 & a5..a8, left predictors are L0..L3 & L5..L8,
// x indicates pels to be predicted.
//
// 1. Obtain weighted sum of differences of above predictors:
// H = 4*(a8-a0) + 3*(a7-a1) + 2*(a6-a2) + 1*(a5-a3)
// 2. Obtain weighted sum of differences of left predictors:
// V = 4*(L8-L0) + 3*(L7-L1) + 2*(L6-L2) + 1*(L5-L3)
// 3. Calculate a,b,c terms (level, horiz slope factor, vert slope factor):
// a = (a8 + L8) *16
// b = (17*H + 16) >> 5
// c = (17*V + 16) >> 5
// 4. Use a,b,c to calculate a predictor at each i, j of the 8x8 macroblock,
// where x is horizontal index and y is vertical index:
// pred = ((a + (i-3)*b + (j-3)*c) + 16)>>5
//
// Note this function will reference pels above and to the left of the
// current macroblock so should not be called at top or left picture edge.
//
////////////////////////////////////////////////////////////////////////////////
template <class PixType, class CoeffsType>
void H264CoreEncoder<PixType,CoeffsType>::PlanarPredictChroma(PixType* pBlock, // pointer to upper left pel of block
Ipp32u uPitch, // of reference plane
PixType *pPredBuf)
{
PixType ap[17], lp[17];
Ipp32s iH;
Ipp32s iV;
Ipp32s i, j;
Ipp32s a,b,c;
Ipp32s temp;
Ipp32s xCF,yCF;
Ipp32s bit_depth = m_SeqParamSet.bit_depth_chroma;
PixType max_pix_value = (1<<bit_depth) - 1;
xCF = 4*(m_PicParamSet.chroma_format_idc == 3);
yCF = 4*(m_PicParamSet.chroma_format_idc != 1);
for (i=0;i<(9+(xCF<<1));i++)
ap[i]=(pBlock-Ipp32s(uPitch)-1)[i];
for (i=0;i<(9+(yCF<<1));i++)
lp[i]=(pBlock+Ipp32s(uPitch)*(i-1))[-1];
iH = 0;
iV = 0;
for (i=1; i<= 4; i++){
iH += i*(ap[4+xCF+i] - ap[4+xCF-i]);
iV += i*(lp[4+yCF+i] - lp[4+yCF-i]);
}
for( i=5; i<= 4+xCF; i++ )
iH += i*(ap[4+xCF+i] - ap[4+xCF-i]);
for( i=5; i<= 4+yCF; i++ )
iV += i*(lp[4+yCF+i] - lp[4+yCF-i]);
a = (ap[8+(xCF<<1)] + lp[8+(yCF<<1)])*16;
b = ((34-29*(m_PicParamSet.chroma_format_idc == 3))*iH + 32)>>6;
c = ((34-29*(m_PicParamSet.chroma_format_idc != 1))*iV + 32)>>6;
for (j=0; j<(8+(yCF<<1)); j++)
for (i=0; i<(8+(xCF<<1)); i++)
{
temp= (a+(i-3-xCF)*b+(j-3-yCF)*c+16)>>5;
temp= (temp>max_pix_value)? max_pix_value:temp;
temp= (temp<0)?0:temp;
pPredBuf[i + j*16]=(PixType) temp;
}
} // C_PlanarPredictChroma
////////////////////////////////////////////////////////////////////////////////
// AdvancedIntraModeSelectOneMacroblock
//
// Main function to drive advanced intra mode select for one macroblock.
////////////////////////////////////////////////////////////////////////////////
template <class PixType, class CoeffsType>
void H264CoreEncoder<PixType,CoeffsType>::AdvancedIntraModeSelectOneMacroblock8x8(
H264EncoderThreadPrivateSlice<PixType, CoeffsType> *curr_slice,
Ipp32u uMB, // which MB
Ipp32u uBestSAD, //Best previous SAD
Ipp32u *puAIMBSAD) // return total MB SAD here
{
H264CurrentMacroblockDescriptor<PixType, CoeffsType>& cur_mb = curr_slice->m_cur_mb;
// All 9 intra modes are checked. Since we treat all 4x4 blocks before
// coding/decoding the prediction may not be based on decoded pixels (except
// for some of the blocks). Therefore original pixel data are used for
// prediction in this assessment of intra coding. This will result in
// too good prediction.
// To compensate for this the SAD for intra is given a 'handicap'
// depending on QP. Notice: Original data is used for prediction only
// in mode selection. When real coding is performed, prediction is made
// from decoded data
//Ipp32u uMBQP = curr_slice->m_cur_mb.LocalMacroblockInfo->QP;
*puAIMBSAD = 0;//rd_quant_intra[uMBQP]; //TODO ADB
// pointer to upper left pel of first block
PixType *pBlock = cur_mb.mbPtr;
PixType *rBlock = m_pReconstructFrame->m_pYPlane + m_pMBOffsets[uMB].uLumaOffset[m_is_cur_pic_afrm][curr_slice->m_is_cur_mb_field];
Ipp32s uBlock;
if( m_Analyse & ANALYSE_RD_OPT ){
curr_slice->fakeBitstream->CopyContext_CABAC(*(curr_slice->m_pbitstream));
curr_slice->fakeBitstream->SaveContext_CABAC();
}
// loop over all 4 8x8 blocks in the MB
for (uBlock = 0; uBlock < 4; uBlock++)
{
PixType *pPredBuf = NULL;
if (curr_slice->m_use_transform_for_intra_decision)
pPredBuf = cur_mb.mb8x8.prediction + xoff[4*uBlock] + yoff[4*uBlock]*16;
// CPU-dependent call to block level mode select
if( m_Analyse & ANALYSE_RD_OPT && pPredBuf ){
*puAIMBSAD += Intra8x8SelectRD(
curr_slice,
pBlock, // source block
rBlock, // no reference block yet, use source for ref.
uBlock,
curr_slice->m_cur_mb.intra_types,
pPredBuf); // no return of predictor pels
}else{
*puAIMBSAD += AIModeSelectOneMB_8x8(
curr_slice,
pBlock, // source block
rBlock, // no reference block yet, use source for ref.
uBlock,
curr_slice->m_cur_mb.intra_types,
pPredBuf); // no return of predictor pels
}
if( *puAIMBSAD > uBestSAD ) return; //Don't count anymore because previous SAD is better.
pBlock += m_EncBlockOffsetInc[curr_slice->m_is_cur_mb_fi
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -