[x265] [PATCH 4 of 4] rdlevel: implement rdlevel 1

deepthidevaki at multicorewareinc.com deepthidevaki at multicorewareinc.com
Tue Dec 10 13:14:26 CET 2013


# HG changeset patch
# User Deepthi Devaki <deepthidevaki at multicorewareinc.com>
# Date 1386677520 -19800
# Node ID 6ff91e0034ea8c295f9248cbaafee7a109add435
# Parent  f9ebf328eb5a319a9bf0e25313c6317e917a5aca
rdlevel: implement rdlevel 1

At each depth, dct, quant, iquant, idct is done on best mode. No RD done during TU selection. Recon is generated for intra prediction in neighbouring quadtree is not broken

diff -r f9ebf328eb5a -r 6ff91e0034ea source/Lib/TLibEncoder/TEncSearch.cpp
--- a/source/Lib/TLibEncoder/TEncSearch.cpp	Tue Dec 10 17:40:42 2013 +0530
+++ b/source/Lib/TLibEncoder/TEncSearch.cpp	Tue Dec 10 17:42:00 2013 +0530
@@ -3259,6 +3259,38 @@
     cu->setQPSubParts(qpBest, 0, cu->getDepth(0));
 }
 
+void TEncSearch::generateCoeffRecon(TComDataCU* cu, TComYuv* fencYuv, TComYuv* predYuv, TShortYUV* resiYuv, TComYuv* reconYuv, bool skipRes)
+{
+    if (skipRes && cu->getPredictionMode(0) == MODE_INTER && cu->getMergeFlag(0) && cu->getPartitionSize(0) == SIZE_2Nx2N)
+    {
+        predYuv->copyToPartYuv(reconYuv, 0);
+        cu->setCbfSubParts(0, TEXT_LUMA, 0, 0, cu->getDepth(0));
+        cu->setCbfSubParts(0, TEXT_CHROMA_U, 0, 0, cu->getDepth(0));
+        cu->setCbfSubParts(0, TEXT_CHROMA_V, 0, 0, cu->getDepth(0));
+        return;
+    }
+    if (cu->getPredictionMode(0) == MODE_INTER)
+    {
+        residualTransformQuantInter(cu, 0, 0, resiYuv, cu->getDepth(0), true);
+        xSetResidualQTData(cu, 0, 0, NULL, cu->getDepth(0), false);
+        uint32_t width  = cu->getWidth(0);
+        xSetResidualQTData(cu, 0, 0, resiYuv, cu->getDepth(0), true);
+        reconYuv->addClip(predYuv, resiYuv, 0, width);
+
+        if (cu->getMergeFlag(0) && cu->getPartitionSize(0) == SIZE_2Nx2N && cu->getQtRootCbf(0) == 0)
+        {
+            cu->setSkipFlagSubParts(true, 0, cu->getDepth(0));
+        }
+    }
+    else if (cu->getPredictionMode(0) == MODE_INTRA)
+    {
+        uint32_t initTrDepth = cu->getPartitionSize(0) == SIZE_2Nx2N ? 0 : 1;
+        residualTransformQuantIntra(cu, initTrDepth, 0, true, fencYuv, predYuv, resiYuv, reconYuv);
+        getBestIntraModeChroma(cu, fencYuv, predYuv);
+        residualQTIntrachroma(cu, 0, 0, fencYuv, predYuv, resiYuv, reconYuv);
+    }
+}
+
 #if _MSC_VER
 #pragma warning(disable: 4701) // potentially uninitialized local variable
 #endif
diff -r f9ebf328eb5a -r 6ff91e0034ea source/Lib/TLibEncoder/TEncSearch.h
--- a/source/Lib/TLibEncoder/TEncSearch.h	Tue Dec 10 17:40:42 2013 +0530
+++ b/source/Lib/TLibEncoder/TEncSearch.h	Tue Dec 10 17:42:00 2013 +0530
@@ -170,6 +170,7 @@
                              uint64_t& dRDCost);
     void xSetIntraResultQT(TComDataCU* cu, uint32_t trDepth, uint32_t absPartIdx, bool bLumaOnly, TComYuv* reconYuv);
 
+    void generateCoeffRecon(TComDataCU* cu, TComYuv* fencYuv, TComYuv* predYuv, TShortYUV* resiYuv, TComYuv* reconYuv, bool skipRes);
     // -------------------------------------------------------------------------------------------------------------------
     // compute symbol bits
     // -------------------------------------------------------------------------------------------------------------------
diff -r f9ebf328eb5a -r 6ff91e0034ea source/encoder/compress.cpp
--- a/source/encoder/compress.cpp	Tue Dec 10 17:40:42 2013 +0530
+++ b/source/encoder/compress.cpp	Tue Dec 10 17:42:00 2013 +0530
@@ -290,6 +290,8 @@
     outTempCU->setInterDirSubParts(interDirNeighbours[bestMergeCand], 0, 0, depth);
     outTempCU->getCUMvField(REF_PIC_LIST_0)->setAllMvField(mvFieldNeighbours[0 + 2 * bestMergeCand], SIZE_2Nx2N, 0, 0);
     outTempCU->getCUMvField(REF_PIC_LIST_1)->setAllMvField(mvFieldNeighbours[1 + 2 * bestMergeCand], SIZE_2Nx2N, 0, 0);
+    outTempCU->m_totalBits = outBestCU->m_totalBits;
+    outTempCU->m_totalDistortion = outBestCU->m_totalDistortion;
     if (m_cfg->param.rdLevel > 2)
     {
         //calculate the motion compensation for chroma for the best mode selected
@@ -491,7 +493,6 @@
 
                     m_search->encodeResAndCalcRdInterCU(outBestCU, m_origYuv[depth], m_bestPredYuv[depth], m_tmpResiYuv[depth],
                                                         m_bestResiYuv[depth], m_bestRecoYuv[depth], false);
-                    xCheckDQP(outBestCU);
                 }
                 if (m_bestMergeCU[depth]->m_totalCost < outBestCU->m_totalCost)
                 {
@@ -563,49 +564,82 @@
                         m_search->motionCompensation(outBestCU, m_bestPredYuv[depth], REF_PIC_LIST_X, partIdx, false, true);
                     }
 
-                    m_search->encodeResAndCalcRdInterCU(outBestCU, m_origYuv[depth], m_bestPredYuv[depth], m_tmpResiYuv[depth],
-                                                        m_bestResiYuv[depth], m_bestRecoYuv[depth], false);
-                    xCheckDQP(outBestCU);
+                    if (m_cfg->param.rdLevel == 2)
+                    {
+                        m_search->encodeResAndCalcRdInterCU(outBestCU, m_origYuv[depth], m_bestPredYuv[depth], m_tmpResiYuv[depth],
+                                                            m_bestResiYuv[depth], m_bestRecoYuv[depth], false);
+                    }
+                    else if (m_cfg->param.rdLevel <= 1)
+                    {
+                        m_tmpResiYuv[depth]->subtract(m_origYuv[depth], m_bestPredYuv[depth], 0, outBestCU->getWidth(0));
+                        m_search->generateCoeffRecon(outBestCU, m_origYuv[depth], m_bestPredYuv[depth], m_tmpResiYuv[depth], m_bestRecoYuv[depth], false);
+                    }
                 }
                 else
                 {
-                    xEncodeIntraInInter(outBestCU, m_origYuv[depth], m_bestPredYuv[depth], m_tmpResiYuv[depth],  m_bestRecoYuv[depth]);
+                    if (m_cfg->param.rdLevel == 2)
+                        xEncodeIntraInInter(outBestCU, m_origYuv[depth], m_bestPredYuv[depth], m_tmpResiYuv[depth],  m_bestRecoYuv[depth]);
+                    else if (m_cfg->param.rdLevel == 1)
+                    {
+                        m_search->generateCoeffRecon(outBestCU, m_origYuv[depth], m_bestPredYuv[depth], m_tmpResiYuv[depth], m_bestRecoYuv[depth], false);
+                    }
                 }
                 //Check Merge-skip
-                if (!(outBestCU->getPredictionMode(0) == MODE_INTER && outBestCU->getPartitionSize(0) == SIZE_2Nx2N && outBestCU->getMergeFlag(0)))
+                if (m_cfg->param.rdLevel <= 2)
                 {
-                    int numPart = m_mergeCU[depth]->getNumPartInter();
-                    for (int partIdx = 0; partIdx < numPart; partIdx++)
+                    if (!(outBestCU->getPredictionMode(0) == MODE_INTER && outBestCU->getPartitionSize(0) == SIZE_2Nx2N && outBestCU->getMergeFlag(0)))
                     {
-                        m_search->motionCompensation(m_mergeCU[depth], bestMergePred, REF_PIC_LIST_X, partIdx, false, true);
+                        int numPart = m_mergeCU[depth]->getNumPartInter();
+                        for (int partIdx = 0; partIdx < numPart; partIdx++)
+                        {
+                            m_search->motionCompensation(m_mergeCU[depth], bestMergePred, REF_PIC_LIST_X, partIdx, false, true);
+                        }
                     }
-                }
 
-                m_search->encodeResAndCalcRdInterCU(m_mergeCU[depth], m_origYuv[depth], bestMergePred, m_tmpResiYuv[depth],
-                                                    m_bestResiYuv[depth], m_tmpRecoYuv[depth], true);
+                    if (m_cfg->param.rdLevel == 2)
+                    {
+                        m_search->encodeResAndCalcRdInterCU(m_mergeCU[depth], m_origYuv[depth], bestMergePred, m_tmpResiYuv[depth],
+                                                            m_bestResiYuv[depth], m_tmpRecoYuv[depth], true);
 
-                if (m_mergeCU[depth]->m_totalCost < outBestCU->m_totalCost)
-                {
-                    outBestCU = m_mergeCU[depth];
-                    tempYuv = m_bestRecoYuv[depth];
-                    m_bestRecoYuv[depth] = m_tmpRecoYuv[depth];
-                    m_tmpRecoYuv[depth] = tempYuv;
-                    if (bestMergePred != m_bestPredYuv[depth])
+                        if (m_mergeCU[depth]->m_totalCost < outBestCU->m_totalCost)
+                        {
+                            outBestCU = m_mergeCU[depth];
+                            tempYuv = m_bestRecoYuv[depth];
+                            m_bestRecoYuv[depth] = m_tmpRecoYuv[depth];
+                            m_tmpRecoYuv[depth] = tempYuv;
+                            if (bestMergePred != m_bestPredYuv[depth])
+                            {
+                                bestMergePred->copyPartToPartYuv(m_bestPredYuv[depth], 0, outBestCU->getWidth(0), outBestCU->getHeight(0));
+                            }
+                        }
+                    }
+                    else if (m_cfg->param.rdLevel <= 1)
                     {
-                        bestMergePred->copyPartToPartYuv(m_bestPredYuv[depth], 0, outBestCU->getWidth(0), outBestCU->getHeight(0));
+                        uint32_t threshold[4] = { 20000, 6000, 1600, 500 };
+                        if (m_mergeCU[depth]->m_totalDistortion < threshold[depth])
+                        {
+                            m_mergeCU[depth]->setSkipFlagSubParts(true, 0, depth);
+                            m_search->generateCoeffRecon(m_mergeCU[depth], m_origYuv[depth], bestMergePred, m_tmpResiYuv[depth], m_bestRecoYuv[depth], true);
+                            outBestCU = m_mergeCU[depth];
+                        }
                     }
                 }
             }
+            
+            xCheckDQP(outBestCU);
             /* Disable recursive analysis for whole CUs temporarily */
             if ((outBestCU != 0) && (outBestCU->isSkipped(0)))
                 bSubBranch = false;
             else
                 bSubBranch = true;
 
-            m_entropyCoder->resetBits();
-            m_entropyCoder->encodeSplitFlag(outBestCU, 0, depth, true);
-            outBestCU->m_totalBits += m_entropyCoder->getNumberOfWrittenBits(); // split bits
-            outBestCU->m_totalCost  = m_rdCost->calcRdCost(outBestCU->m_totalDistortion, outBestCU->m_totalBits);
+            if (m_cfg->param.rdLevel > 1)
+            {
+                m_entropyCoder->resetBits();
+                m_entropyCoder->encodeSplitFlag(outBestCU, 0, depth, true);
+                outBestCU->m_totalBits += m_entropyCoder->getNumberOfWrittenBits(); // split bits
+                outBestCU->m_totalCost  = m_rdCost->calcRdCost(outBestCU->m_totalDistortion, outBestCU->m_totalBits);
+            }
         }
         else if (!(bSliceEnd && bInsidePicture))
         {


More information about the x265-devel mailing list