[x265] [PATCH 2 of 3] Bidir ME: new logic adapted from x264

deepthidevaki at multicorewareinc.com deepthidevaki at multicorewareinc.com
Thu Oct 3 13:14:23 CEST 2013


# HG changeset patch
# User Deepthi Devaki <deepthidevaki at multicorewareinc.com>
# Date 1380772801 -19800
# Node ID ec3a18af19a1eea20cee608956353028948faf42
# Parent  a9480c6387a56c8bcd753b37c3e44a73b18f1f25
Bidir ME: new logic adapted from x264

L0 and L1 MVs from unidir ME used for bidir MV. bidir cost is calculated from the average of references.

diff -r a9480c6387a5 -r ec3a18af19a1 source/Lib/TLibEncoder/TEncCu.cpp
--- a/source/Lib/TLibEncoder/TEncCu.cpp	Thu Oct 03 09:21:30 2013 +0530
+++ b/source/Lib/TLibEncoder/TEncCu.cpp	Thu Oct 03 09:30:01 2013 +0530
@@ -1522,7 +1522,7 @@
     outTempCU->setMergeAMP(true);
     m_tmpRecoYuv[depth]->clear();
     m_tmpResiYuv[depth]->clear();
-    m_search->predInterSearch(outTempCU, m_origYuv[depth], m_tmpPredYuv[depth], bUseMRG);
+    m_search->predInterSearch(outTempCU, m_tmpPredYuv[depth], bUseMRG);
     m_search->encodeResAndCalcRdInterCU(outTempCU, m_origYuv[depth], m_tmpPredYuv[depth], m_tmpResiYuv[depth], m_bestResiYuv[depth], m_tmpRecoYuv[depth], false);
 
     xCheckDQP(outTempCU);
diff -r a9480c6387a5 -r ec3a18af19a1 source/Lib/TLibEncoder/TEncSearch.cpp
--- a/source/Lib/TLibEncoder/TEncSearch.cpp	Thu Oct 03 09:21:30 2013 +0530
+++ b/source/Lib/TLibEncoder/TEncSearch.cpp	Thu Oct 03 09:30:01 2013 +0530
@@ -2289,7 +2289,7 @@
  * \param bUseRes
  * \returns void
  */
-void TEncSearch::predInterSearch(TComDataCU* cu, TComYuv* fencYuv, TComYuv* predYuv, bool bUseMRG)
+void TEncSearch::predInterSearch(TComDataCU* cu, TComYuv* predYuv, bool bUseMRG)
 {
     m_predYuv[0].clear();
     m_predYuv[1].clear();
@@ -2317,7 +2317,6 @@
 
     UInt partAddr;
     int  roiWidth, roiHeight;
-    int refStart, refEnd;
 
     PartSize partSize = cu->getPartitionSize(0);
     int bestBiPRefIdxL1 = 0;
@@ -2483,8 +2482,6 @@
             //  Bi-directional prediction
             if ((cu->getSlice()->isInterB()) && (cu->isBipredRestriction(partIdx) == false))
             {
-                UInt motBits[2];
-
                 mvBidir[0] = mv[0];
                 mvBidir[1] = mv[1];
                 refIdxBidir[0] = refIdx[0];
@@ -2493,111 +2490,22 @@
                 ::memcpy(mvPredBi, mvPred, sizeof(mvPred));
                 ::memcpy(mvpIdxBi, mvpIdx, sizeof(mvpIdx));
 
-                if (cu->getSlice()->getMvdL1ZeroFlag())
-                {
-                    xCopyAMVPInfo(&amvpInfo[1][bestBiPRefIdxL1], cu->getCUMvField(REF_PIC_LIST_1)->getAMVPInfo());
-                    cu->setMVPIdxSubParts(bestBiPMvpL1, REF_PIC_LIST_1, partAddr, partIdx, cu->getDepth(partAddr));
-                    mvpIdxBi[1][bestBiPRefIdxL1] = bestBiPMvpL1;
-                    mvPredBi[1][bestBiPRefIdxL1] = cu->getCUMvField(REF_PIC_LIST_1)->getAMVPInfo()->m_mvCand[bestBiPMvpL1];
-
-                    mvBidir[1] = mvPredBi[1][bestBiPRefIdxL1];
-                    refIdxBidir[1] = bestBiPRefIdxL1;
-                    cu->getCUMvField(REF_PIC_LIST_1)->setAllMv(mvBidir[1], partSize, partAddr, 0, partIdx);
-                    cu->getCUMvField(REF_PIC_LIST_1)->setAllRefIdx(refIdxBidir[1], partSize, partAddr, 0, partIdx);
-                    motionCompensation(cu, &m_predYuv[1], REF_PIC_LIST_1, partIdx);
-
-                    motBits[0] = bits[0] - mbBits[0];
-                    motBits[1] = mbBits[1];
-
-                    if (cu->getSlice()->getNumRefIdx(REF_PIC_LIST_1) > 1)
-                    {
-                        motBits[1] += bestBiPRefIdxL1 + 1;
-                        if (bestBiPRefIdxL1 == cu->getSlice()->getNumRefIdx(REF_PIC_LIST_1) - 1) motBits[1]--;
-                    }
-
-                    motBits[1] += m_mvpIdxCost[mvpIdxBi[1][bestBiPRefIdxL1]][AMVP_MAX_NUM_CANDS];
-
-                    bits[2] = mbBits[2] + motBits[0] + motBits[1];
-
-                    mvTemp[1][bestBiPRefIdxL1] = mvBidir[1];
-                }
-                else
-                {
-                    motBits[0] = bits[0] - mbBits[0];
-                    motBits[1] = bits[1] - mbBits[1];
-                    bits[2] = mbBits[2] + motBits[0] + motBits[1];
-                }
-
-                int refList = 0;
-                if (listCost[0] <= listCost[1])
-                {
-                    refList = 1;
-                }
-                else
-                {
-                    refList = 0;
-                }
-                if (!cu->getSlice()->getMvdL1ZeroFlag())
-                {
-                    cu->getCUMvField(RefPicList(1 - refList))->setAllMv(mv[1 - refList], partSize, partAddr, 0, partIdx);
-                    cu->getCUMvField(RefPicList(1 - refList))->setAllRefIdx(refIdx[1 - refList], partSize, partAddr, 0, partIdx);
-                    motionCompensation(cu, &m_predYuv[1 - refList], RefPicList(1 - refList), partIdx);
-                }
-                RefPicList  picList = (refList ? REF_PIC_LIST_1 : REF_PIC_LIST_0);
-
-                if (cu->getSlice()->getMvdL1ZeroFlag())
-                {
-                    refList = 0;
-                    picList = REF_PIC_LIST_0;
-                }
-
-                bool bChanged = false;
-
-                refStart = 0;
-                refEnd   = cu->getSlice()->getNumRefIdx(picList) - 1;
-
-                for (int refIdxTmp = refStart; refIdxTmp <= refEnd; refIdxTmp++)
-                {
-                    bitsTemp = mbBits[2] + motBits[1 - refList];
-                    if (cu->getSlice()->getNumRefIdx(picList) > 1)
-                    {
-                        bitsTemp += refIdxTmp + 1;
-                        if (refIdxTmp == cu->getSlice()->getNumRefIdx(picList) - 1) bitsTemp--;
-                    }
-                    bitsTemp += m_mvpIdxCost[mvpIdxBi[refList][refIdxTmp]][AMVP_MAX_NUM_CANDS];
-                    // call bidir ME
-                    xMotionEstimation(cu, fencYuv, partIdx, picList, &mvPredBi[refList][refIdxTmp], refIdxTmp, mvTemp[refList][refIdxTmp],
-                                      bitsTemp, costTemp);
-                    xCopyAMVPInfo(&amvpInfo[refList][refIdxTmp], cu->getCUMvField(picList)->getAMVPInfo());
-                    xCheckBestMVP(cu, picList, mvTemp[refList][refIdxTmp], mvPredBi[refList][refIdxTmp], mvpIdxBi[refList][refIdxTmp],
-                                  bitsTemp, costTemp);
-
-                    if (costTemp < costbi)
-                    {
-                        bChanged = true;
-
-                        mvBidir[refList]     = mvTemp[refList][refIdxTmp];
-                        refIdxBidir[refList] = refIdxTmp;
-
-                        costbi           = costTemp;
-                        motBits[refList] = bitsTemp - mbBits[2] - motBits[1 - refList];
-                        bits[2]          = bitsTemp;
-                    }
-                } // for loop-refIdxTmp
-
-                if (!bChanged)
-                {
-                    if (costbi <= listCost[0] && costbi <= listCost[1])
-                    {
-                        xCopyAMVPInfo(&amvpInfo[0][refIdxBidir[0]], cu->getCUMvField(REF_PIC_LIST_0)->getAMVPInfo());
-                        xCheckBestMVP(cu, REF_PIC_LIST_0, mvBidir[0], mvPredBi[0][refIdxBidir[0]], mvpIdxBi[0][refIdxBidir[0]], bits[2], costbi);
-                        if (!cu->getSlice()->getMvdL1ZeroFlag())
-                        {
-                            xCopyAMVPInfo(&amvpInfo[1][refIdxBidir[1]], cu->getCUMvField(REF_PIC_LIST_1)->getAMVPInfo());
-                            xCheckBestMVP(cu, REF_PIC_LIST_1, mvBidir[1], mvPredBi[1][refIdxBidir[1]], mvpIdxBi[1][refIdxBidir[1]], bits[2], costbi);
-                        }
-                    }
-                }
+                pixel *ref0, *ref1;
+
+                //Generate reference subpels
+                xPredInterLumaBlk(cu, cu->getSlice()->m_mref[0][refIdx[0]], partAddr, &mv[0], roiWidth, roiHeight, &m_predYuv[0]);
+                xPredInterLumaBlk(cu, cu->getSlice()->m_mref[1][refIdx[1]], partAddr, &mv[1], roiWidth, roiHeight, &m_predYuv[1]);
+
+                ref0 = m_predYuv[0].getLumaAddr(partAddr);
+                ref1 = m_predYuv[1].getLumaAddr(partAddr);
+
+                pixel avg[MAX_CU_SIZE * MAX_CU_SIZE];
+
+                int partEnum = PartitionFromSizes(roiWidth, roiHeight);
+                primitives.pixelavg_pp[partEnum](avg, roiWidth, ref0, ref1, m_predYuv[0].getStride(), m_predYuv[1].getStride());
+
+                int satdCost = primitives.satd[partEnum](pu, fenc->getStride(), avg, roiWidth);
+                costbi =  satdCost + m_rdCost->getCost(bits[0]) + m_rdCost->getCost(bits[1]);
             } // if (B_SLICE)
         } //end if bTestNormalMC
 
diff -r a9480c6387a5 -r ec3a18af19a1 source/Lib/TLibEncoder/TEncSearch.h
--- a/source/Lib/TLibEncoder/TEncSearch.h	Thu Oct 03 09:21:30 2013 +0530
+++ b/source/Lib/TLibEncoder/TEncSearch.h	Thu Oct 03 09:30:01 2013 +0530
@@ -146,7 +146,7 @@
                               TComYuv* reconYuv, UInt precalcDistC);
 
     /// encoder estimation - inter prediction (non-skip)
-    void predInterSearch(TComDataCU* cu, TComYuv* fencYuv, TComYuv* predYuv, bool bUseMRG = false);
+    void predInterSearch(TComDataCU* cu, TComYuv* predYuv, bool bUseMRG = false);
 
     /// encode residual and compute rd-cost for inter mode
     void encodeResAndCalcRdInterCU(TComDataCU* cu, TComYuv* fencYuv, TComYuv* predYuv, TShortYUV* resiYuv, TShortYUV* bestResiYuv,
diff -r a9480c6387a5 -r ec3a18af19a1 source/encoder/compress.cpp
--- a/source/encoder/compress.cpp	Thu Oct 03 09:21:30 2013 +0530
+++ b/source/encoder/compress.cpp	Thu Oct 03 09:30:01 2013 +0530
@@ -261,7 +261,7 @@
     m_tmpRecoYuv[depth]->clear();
     m_tmpResiYuv[depth]->clear();
 
-    m_search->predInterSearch(outTempCU, m_origYuv[depth], outPredYuv, bUseMRG);
+    m_search->predInterSearch(outTempCU, outPredYuv, bUseMRG);
     int part = PartitionFromSizes(outTempCU->getWidth(0), outTempCU->getHeight(0));
     outTempCU->m_totalCost = primitives.sse_pp[part](m_origYuv[depth]->getLumaAddr(), m_origYuv[depth]->getStride(),
                                                      outPredYuv->getLumaAddr(), outPredYuv->getStride());


More information about the x265-devel mailing list