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

📄 umc_h264_ermb.cpp

📁 这是在PCA下的基于IPP库示例代码例子,在网上下了IPP的库之后,设置相关参数就可以编译该代码.
💻 CPP
📖 第 1 页 / 共 5 页
字号:
Ipp32u H264VideoEncoder::CEncAndRec16x16IntraMB(Ipp32u uMB){    Ipp32u  uBlock;     // block number, 0 to 23    Ipp32u  uIndex;     // block-dependent, into AI and MV arrays    Ipp32u  uOffset;        // to upper left corner of block from start of plane    Ipp32u  uMBQP;          // QP of current MB    Ipp32u  uMBType;        // current MB type    Ipp8u   uMBEdgeType;    // current MB edge type    Ipp32u  uCBP4x4;        // coded flags for all 4x4 blocks    Ipp32u  uIntraSAD;      // intra MB SAD    Ipp16s* pDCBuf;     // chroma & luma dc coeffs pointer    Ipp8u*  pPredBuf;       // prediction block pointer    Ipp16s* pDiffBuf;       // difference block pointer    Ipp16s* pTempDiffBuf;       // difference block pointer    Ipp16s* pMassDiffBuf;   // difference block pointer    Ipp16s* pQBuf;          // quantized block pointer//  Ipp16s* pDQBuf;     // dequantized block pointer    Ipp8u*  pSrcPlane;      // start of plane to encode    Ipp8u*  pRecPlane;      // start of reconstructed plane    Ipp32u  uPitch;     // buffer pitch    Ipp8u   bCoded; // coded block flag    T_NumCoeffs iNumCoeffs; // Number of nonzero coeffs after quant (negative if DC is nonzero)    Ipp8u       uLastCoeff; // Number of nonzero coeffs after quant (negative if DC is nonzero)    Ipp32u   RLE_Offset;    // Index into BlockRLE array    Ipp32u rc;    uPitch      = m_pCurrentFrame->uPitch;    uCBP4x4     = m_pCurrentFrame->pMBData[uMB].uCBP4x4;    uMBQP       = m_pCurrentFrame->pMBData[uMB].uMBQP;    uMBType     = m_pCurrentFrame->pMBData[uMB].uMBType;    uMBEdgeType = m_pCurrentFrame->pMBData[uMB].uEdgeType;    pPredBuf    = m_pCurrentFrame->pMBEncodeBuffer; // 16-byte aligned work buffer    pDiffBuf    = (Ipp16s*) (pPredBuf + 512);    pQBuf       = (Ipp16s*) (pDiffBuf + 16);//  pDQBuf      = (Ipp16s*) (pQBuf + 16);    pDCBuf      = (Ipp16s*) (pQBuf + 16);   // Used for both luma and chroma DC blocks    pMassDiffBuf = (Ipp16s*) (pDCBuf + 16);//  uIntraSAD   = rd_quant_intra[uMBQP] * 24;   // 'handicap' using reconstructed data    uIntraSAD   = 0;    //--------------------------------------------------------------------------    // encode Y plane blocks (0-15)    //--------------------------------------------------------------------------    // initialize pointers and offset    pSrcPlane = m_pCurrentFrame->m_pYPlane;    pRecPlane = m_pReconstructFrame->m_pYPlane;    uOffset = m_pCurrentFrame->pMBOffsets[uMB].uLumaOffset + m_pCurrentFrame->y_line_shift;    RLE_Offset = Y_DC_RLE;  // Used in 16x16 Intra mode only    // get AI/MV array index for first block of the MB    uIndex = m_pCurrentFrame->pMBOffsets[uMB].uFirstBlockIndex;    // for INTRA 16x16 MBs computation of luma prediction was done as    // a byproduct of sad calculation prior to this function being    // called; the predictor blocks are already at pPredBuf.    // Initialize the AC coeff flag value    m_pCurrentFrame->pMBData[uMB].uLumaAC = 0;    // compute the 4x4 luma DC transform coeffs    ippiSumsDiff16x16Blocks4x4_8u16s_C1(        pSrcPlane + uOffset,        uPitch,        pPredBuf,        16,        pDCBuf,        pMassDiffBuf);    // apply second transform on the luma DC transform coeffs    rc = ippiTransformQuantLumaDC_H264_16s_C1I(pDCBuf,pQBuf,uMBQP,&iNumCoeffs,1,        enc_single_scan[m_PicParamSet.picture_structure != FRAME_PICTURE],&uLastCoeff);    // If rc != 0, then a quantized level was out of range for coding    // with CAVLC, and this MB must be quantized more (or coded a different way)    while (rc) {    // Right now, we quantize more until all of the levels are OK        uMBQP = ++m_pCurrentFrame->pMBData[uMB].uMBQP;    // Increase by a level        rc = ippiTransformQuantLumaDC_H264_16s_C1I(pDCBuf,pQBuf,uMBQP,&iNumCoeffs,0,            enc_single_scan[m_PicParamSet.picture_structure != FRAME_PICTURE],&uLastCoeff);    }    m_pCurrentFrame->pMBData[uMB].DC16x16Coeffs = ABS(iNumCoeffs);    // insert the quantized luma double transform DC coeffs into    // RLE buffer    // record RLE info    if (m_PicParamSet.entropy_coding_mode)    {        int ctxIdxBlockCat = BLOCK_LUMA_DC_LEVELS;        ScanSignificant_CABAC(pDCBuf,ctxIdxBlockCat,16,            dec_single_scan[m_PicParamSet.picture_structure != FRAME_PICTURE],            &m_pCurrentFrame->Block_CABAC[RLE_Offset]);        bCoded = m_pCurrentFrame->Block_CABAC[RLE_Offset].uNumSigCoeffs;    }    else    {        ippiEncodeCoeffsCAVLC_H264_16s (                                            pDCBuf,                                            0,                                            dec_single_scan[m_PicParamSet.picture_structure != FRAME_PICTURE],                                            uLastCoeff,                                            &m_pCurrentFrame->Block_RLE[RLE_Offset].uTrailing_Ones,                                            &m_pCurrentFrame->Block_RLE[RLE_Offset].uTrailing_One_Signs,                                            &m_pCurrentFrame->Block_RLE[RLE_Offset].uNumCoeffs,                                            &m_pCurrentFrame->Block_RLE[RLE_Offset].uTotalZeros,                                            m_pCurrentFrame->Block_RLE[RLE_Offset].iLevels,                                            m_pCurrentFrame->Block_RLE[RLE_Offset].uRuns);        bCoded = m_pCurrentFrame->Block_RLE[RLE_Offset].uNumCoeffs;    }    //bCoded = RLE(    //          pDCBuf,     // quantized coeffs in scan order    //          16,         // number of coeffs    //          &m_pCurrentFrame->Block_RLE[RLE_Offset] // where to put RLE data    //          );    ippiTransformDequantLumaDC_H264_16s_C1I (pDCBuf, uMBQP);    // loop over all 4x4 blocks in Y plane for the MB    for (uBlock = 0; uBlock < 16; )    {        pPredBuf = m_pCurrentFrame->pMBEncodeBuffer + xoff[uBlock] + yoff[uBlock]*16;        m_pCurrentFrame->pYNumCoeffs[uIndex] = 0;        // This will be updated if the block is coded        if (m_PicParamSet.entropy_coding_mode)        {            m_pCurrentFrame->Block_CABAC[uBlock].uNumSigCoeffs = 0;        }        else        {            m_pCurrentFrame->Block_RLE[uBlock].uNumCoeffs = 0;            m_pCurrentFrame->Block_RLE[uBlock].uTrailing_Ones = 0;            m_pCurrentFrame->Block_RLE[uBlock].uTrailing_One_Signs = 0;            m_pCurrentFrame->Block_RLE[uBlock].uTotalZeros = 15;        }        // check if block is coded        bCoded = ((uCBP4x4 & CBP4x4Mask[uBlock])?(1):(0));        if (!bCoded)        {            // update reconstruct frame for the empty block            Copy4x4(                pPredBuf,               // predictor block                uPitch,                pRecPlane + uOffset);   // reconstruct frame        }        else        {   // block not declared empty, encode            // compute difference of predictor and source pels            // note: asm version does not used pDiffBuf            //       output is being passed in the mmx registers            /*            Diff4x4(                pPredBuf,               // predictor pels                pSrcPlane + uOffset,    // source pels                uPitch,                 // source pitch                pDiffBuf);              // result buffer            // forward transform, in place in iDiffBuf            // note: asm version does not used pDiffBuf            //       input and output are being passed in the mmx reg.s            ippiQuantTransformResidual_H264_16s_C1I(pDiffBuf,uMBQP,&iNumCoeffs,&uLastCoeff,(m_SliceHeader.slice_type == INTRASLICE));            */            // linear formula  pTempDiffBuf = pMassDiffBuf+ uBlock*16; or pTempDiffBuf = pMassDiffBuf+ (uBlock/4)*64+(uBlock%4)*16;            pTempDiffBuf = pMassDiffBuf+ xoff[uBlock]*4 + yoff[uBlock]*16;            ippiTransformQuantResidual_H264_16s_C1I (pTempDiffBuf,uMBQP,&iNumCoeffs,(m_SliceHeader.slice_type == INTRASLICE),                enc_single_scan[m_PicParamSet.picture_structure != FRAME_PICTURE],&uLastCoeff);            // restore luma DC transform coeff if 16x16 intra mode            // Also, saves the value of iNonEmpty for later use            // TBD: Maybe this should be part of QDQ or RLE?            m_pCurrentFrame->pMBData[uMB].uLumaAC |=                ((iNumCoeffs < -1) || (iNumCoeffs > 0));            //pDQBuf[0] = pDCBuf[block_subblock_mapping[uBlock]];            // if everything quantized to zero, skip RLE            if (!iNumCoeffs)            {                // the block is empty so it is not coded                bCoded = 0;            }            else            {                // Preserve the absolute number of coeffs.                m_pCurrentFrame->pYNumCoeffs[uIndex] = (T_NumCoeffs)((iNumCoeffs < 0) ? -(iNumCoeffs+1) : iNumCoeffs);                if (m_PicParamSet.entropy_coding_mode)                {                    int ctxIdxBlockCat = BLOCK_LUMA_AC_LEVELS;                    ScanSignificant_CABAC(pTempDiffBuf,ctxIdxBlockCat,15,                        dec_single_scan[m_PicParamSet.picture_structure != FRAME_PICTURE],                        &m_pCurrentFrame->Block_CABAC[uBlock]);                    bCoded = m_pCurrentFrame->Block_CABAC[uBlock].uNumSigCoeffs;                }                else                {                    ippiEncodeCoeffsCAVLC_H264_16s (                                                        pTempDiffBuf,//pDiffBuf,                                                        1,                                                        dec_single_scan[m_PicParamSet.picture_structure != FRAME_PICTURE],                                                        uLastCoeff,                                                        &m_pCurrentFrame->Block_RLE[uBlock].uTrailing_Ones,                                                        &m_pCurrentFrame->Block_RLE[uBlock].uTrailing_One_Signs,                                                        &m_pCurrentFrame->Block_RLE[uBlock].uNumCoeffs,                                                        &m_pCurrentFrame->Block_RLE[uBlock].uTotalZeros,                                                        m_pCurrentFrame->Block_RLE[uBlock].iLevels,                                                        m_pCurrentFrame->Block_RLE[uBlock].uRuns);                    m_pCurrentFrame->pYNumCoeffs[uIndex] = bCoded = m_pCurrentFrame->Block_RLE[uBlock].uNumCoeffs;                }                // record RLE info                //bCoded = RLE(                //          pDiffBuf,       // quantized coeffs in scan order                //          15,         // number of coeffs                //          &m_pCurrentFrame->Block_RLE[uBlock] // where to put RLE data                //          );            }            // update flags if block quantized to empty            if (!bCoded)                uCBP4x4 &= ~CBP4x4Mask[uBlock];            // If the block wasn't coded and the DC coefficient is zero            if (!bCoded && !pDCBuf[block_subblock_mapping[uBlock]])            {                // update reconstruct frame for the empty block                Copy4x4(                    pPredBuf,               // predictor block                    uPitch,                    pRecPlane + uOffset);   // reconstruct frame            }            else            {                // inverse transform for reconstruct AND...                // add inverse transformed coefficients to original predictor                // to obtain reconstructed block, store in reconstruct frame                // buffer                ippiDequantTransformResidualAndAdd_H264_16s_C1I (                    pPredBuf,                    pTempDiffBuf,//pDiffBuf,                    &pDCBuf[block_subblock_mapping[uBlock]],                    pRecPlane + uOffset,                    16,                    uPitch,                    uMBQP,                    ((iNumCoeffs < -1) || (iNumCoeffs > 0)));            }        }   // block not declared empty        // proceed to the next block        uOffset += m_EncBlockOffsetInc[uBlock];        uIndex += m_EncBlockIndexInc[uBlock];        uBlock ++;    }  // for uBlock in luma plane    //--------------------------------------------------------------------------    // encode U plane blocks (16-19) then V plane blocks (20-23)    //--------------------------------------------------------------------------    // In JVT, Chroma is Intra if any part of luma is intra.    m_pCurrentFrame->pMBData[uMB].uChromaNC = 0;    uOffset = m_pCurrentFrame->pMBOffsets[uMB].uChromaOffset + m_pCurrentFrame->uv_line_shift;    int left = m_pCurrentFrame->uMBxpos > 0; // shows whether pixels are available to the left of the MB.    int top = m_pCurrentFrame->uMBypos > 0; // shows whether pixels are available above the MB.    int available = (top<<1)|left;    // Because JVT jointly codes the Intra prediction type for both    // U and V MBs (they use the same type), we need to jointly determine    // the best type, and save the predictor values for both in the    // pPredBuf to be used below.  This is OK, since this is typically used    // as a 16x16 buffer and the U and V predictions are each 8x8 blocks.    // The 8x8 blocks are stored U above V, and the buffer pitch is 16.    AIModeSelectChromaMBs_8x8(        m_pCurrentFrame->m_pUPlane + uOffset,        m_pReconstructFrame->m_pUPlane + uOffset,        m_pCurrentFrame->m_pVPlane + uOffset,        m_pReconstructFrame->m_pVPlane + uOffset,        uPitch,        uMBEdgeType,        available,        &m_pCurrentFrame->pMBData[uMB].uChromaType,

⌨️ 快捷键说明

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