[x265-commits] [x265] lambda: [CHANGES OUTPUT] Change the distortion weights ap...

Deepthi Nandakumar deepthi at multicorewareinc.com
Fri Jun 20 03:52:44 CEST 2014


details:   http://hg.videolan.org/x265/rev/25d2c596dd28
branches:  
changeset: 7135:25d2c596dd28
user:      Deepthi Nandakumar <deepthi at multicorewareinc.com>
date:      Wed Jun 18 14:59:17 2014 +0530
description:
lambda: [CHANGES OUTPUT] Change the distortion weights applied to chroma.

Inside R-D, a single lambda is applied for both luma and chroma. To account for the different QPs,
(as defined by the standard) the chroma distortion was weighted by a factor proportional to the
difference in QPs. This patch eliminates the extra weighting given to the chroma distortion
(since it is visually less perceptible).
Subject: [x265] x265_encoder_encode: don't return 0 while flushing.

details:   http://hg.videolan.org/x265/rev/ced3a726d515
branches:  
changeset: 7136:ced3a726d515
user:      Satoshi Nakagawa <nakagawa424 at oki.com>
date:      Fri Jun 20 10:11:07 2014 +0900
description:
x265_encoder_encode: don't return 0 while flushing.
Subject: [x265] encoder: cleanup obsolete NAL data fields

details:   http://hg.videolan.org/x265/rev/aecb3b2a98c1
branches:  
changeset: 7137:aecb3b2a98c1
user:      Steve Borho <steve at borho.org>
date:      Thu Jun 19 20:36:52 2014 -0500
description:
encoder: cleanup obsolete NAL data fields
Subject: [x265] encoder: remove redundant flush argument

details:   http://hg.videolan.org/x265/rev/0b4a50730f21
branches:  
changeset: 7138:0b4a50730f21
user:      Steve Borho <steve at borho.org>
date:      Thu Jun 19 20:46:10 2014 -0500
description:
encoder: remove redundant flush argument

diffstat:

 source/Lib/TLibEncoder/TEncSearch.cpp |  10 +++++---
 source/Lib/TLibEncoder/TEncSearch.h   |   2 +-
 source/encoder/api.cpp                |   9 +++++++-
 source/encoder/encoder.cpp            |  32 ++++++-----------------------
 source/encoder/encoder.h              |   6 ++--
 source/encoder/frameencoder.cpp       |  38 +++++++++++-----------------------
 source/encoder/slicetype.cpp          |   6 ++--
 7 files changed, 41 insertions(+), 62 deletions(-)

diffs (259 lines):

diff -r dfaf67c21c32 -r 0b4a50730f21 source/Lib/TLibEncoder/TEncSearch.cpp
--- a/source/Lib/TLibEncoder/TEncSearch.cpp	Thu Jun 19 20:11:24 2014 -0500
+++ b/source/Lib/TLibEncoder/TEncSearch.cpp	Thu Jun 19 20:46:10 2014 -0500
@@ -143,15 +143,17 @@ fail:
     return false;
 }
 
-void TEncSearch::setQP(int qp, double cbWeight, double crWeight)
+void TEncSearch::setQP(int qp, int qpCb, int qpCr)
 {
     double lambda2 = x265_lambda2_tab[qp];
+    double lambdaCb = x265_lambda2_tab[qpCb];
+    double lambdaCr = x265_lambda2_tab[qpCr];
 
     m_me.setQP(qp);
-    m_trQuant->setLambdas(lambda2, lambda2 / cbWeight, lambda2 / crWeight);
+    m_trQuant->setLambdas(lambda2, lambdaCb, lambdaCr);
     m_rdCost->setLambda(lambda2, x265_lambda_tab[qp]);
-    m_rdCost->setCbDistortionWeight(cbWeight);
-    m_rdCost->setCrDistortionWeight(crWeight);
+    m_rdCost->setCbDistortionWeight(1.0);
+    m_rdCost->setCrDistortionWeight(1.0);
 }
 
 void TEncSearch::xEncSubdivCbfQT(TComDataCU* cu, uint32_t trDepth, uint32_t absPartIdx, uint32_t absPartIdxStep, uint32_t width, uint32_t height, bool bLuma, bool bChroma)
diff -r dfaf67c21c32 -r 0b4a50730f21 source/Lib/TLibEncoder/TEncSearch.h
--- a/source/Lib/TLibEncoder/TEncSearch.h	Thu Jun 19 20:11:24 2014 -0500
+++ b/source/Lib/TLibEncoder/TEncSearch.h	Thu Jun 19 20:46:10 2014 -0500
@@ -140,7 +140,7 @@ public:
 
     void setRDGoOnSbacCoder(TEncSbac* rdGoOnSbacCoder) { m_rdGoOnSbacCoder = rdGoOnSbacCoder; }
 
-    void setQP(int QP, double cbWeight, double crWeight);
+    void setQP(int qp, int qpCb, int qpCr);
 
     TEncSearch();
     virtual ~TEncSearch();
diff -r dfaf67c21c32 -r 0b4a50730f21 source/encoder/api.cpp
--- a/source/encoder/api.cpp	Thu Jun 19 20:11:24 2014 -0500
+++ b/source/encoder/api.cpp	Thu Jun 19 20:46:10 2014 -0500
@@ -100,7 +100,14 @@ int x265_encoder_encode(x265_encoder *en
         return -1;
 
     Encoder *encoder = static_cast<Encoder*>(enc);
-    int numEncoded = encoder->encode(!pic_in, pic_in, pic_out);
+    int numEncoded;
+
+    // While flushing, we cannot return 0 until the entire stream is flushed
+    do
+    {
+        numEncoded = encoder->encode(pic_in, pic_out);
+    }
+    while (numEncoded == 0 && !pic_in && encoder->m_numDelayedPic);
 
     if (pp_nal && numEncoded > 0)
     {
diff -r dfaf67c21c32 -r 0b4a50730f21 source/encoder/encoder.cpp
--- a/source/encoder/encoder.cpp	Thu Jun 19 20:11:24 2014 -0500
+++ b/source/encoder/encoder.cpp	Thu Jun 19 20:46:10 2014 -0500
@@ -60,8 +60,7 @@ Encoder::Encoder()
     m_rateControl = NULL;
     m_dpb = NULL;
     m_exportedPic = NULL;
-    m_nals = NULL;
-    m_packetData = NULL;
+    m_numDelayedPic = 0;
     m_outputCount = 0;
     m_csvfpt = NULL;
     m_param = NULL;
@@ -167,8 +166,6 @@ void Encoder::destroy()
     if (m_threadPool)
         m_threadPool->release();
 
-    X265_FREE(m_nals);
-    X265_FREE(m_packetData);
     X265_FREE(m_param->rc.statFileName);
     X265_FREE(m_param);
     if (m_csvfpt)
@@ -222,12 +219,11 @@ void Encoder::updateVbvPlan(RateControl*
 }
 
 /**
- \param   flush               force encoder to encode a frame
  \param   pic_in              input original YUV picture or NULL
  \param   pic_out             pointer to reconstructed picture struct
- \retval                      number of encoded pictures, m_nalList contains access unit
+ \retval                      1 - success, negative on error. m_nalList contains access unit
  */
-int Encoder::encode(bool flush, const x265_picture* pic_in, x265_picture *pic_out)
+int Encoder::encode(const x265_picture* pic_in, x265_picture *pic_out)
 {
     if (m_aborted)
         return -1;
@@ -292,9 +288,9 @@ int Encoder::encode(bool flush, const x2
         if (m_param->rc.aqMode || bEnableWP)
             m_rateControl->calcAdaptiveQuantFrame(pic);
         m_lookahead->addPicture(pic, pic_in->sliceType);
+        m_numDelayedPic++;
     }
-
-    if (flush)
+    else
         m_lookahead->flush();
 
     if (m_param->rc.rateControlMode == X265_RC_ABR)
@@ -320,22 +316,6 @@ int Encoder::encode(bool flush, const x2
     // accomplished when the encoder is full.
     TComPic *out = curEncoder->getEncodedPicture(m_nalList);
 
-    if (!out && flush)
-    {
-        // if the current encoder did not return an output picture and we are
-        // flushing, check all the other encoders in logical order until
-        // we find an output picture or have cycled around.  We cannot return
-        // 0 until the entire stream is flushed
-        // (can only be an issue when --frames < --frame-threads)
-        int flushed = m_curEncoder;
-        do
-        {
-            curEncoder = &m_frameEncoder[m_curEncoder];
-            m_curEncoder = (m_curEncoder + 1) % m_param->frameNumThreads;
-            out = curEncoder->getEncodedPicture(m_nalList);
-        }
-        while (!out && flushed != m_curEncoder);
-    }
     if (out)
     {
         if (pic_out)
@@ -421,6 +401,8 @@ int Encoder::encode(bool flush, const x2
         else
             m_exportedPic = out;
 
+        m_numDelayedPic--;
+
         ret = 1;
     }
 
diff -r dfaf67c21c32 -r 0b4a50730f21 source/encoder/encoder.h
--- a/source/encoder/encoder.h	Thu Jun 19 20:11:24 2014 -0500
+++ b/source/encoder/encoder.h	Thu Jun 19 20:46:10 2014 -0500
@@ -182,10 +182,10 @@ public:
     Window             m_conformanceWindow;
     Window             m_defaultDisplayWindow;
 
-    x265_nal*          m_nals;
-    char*              m_packetData;
     int                m_totalFrameThreads;
 
+    uint32_t           m_numDelayedPic;
+
     Encoder();
 
     virtual ~Encoder();
@@ -197,7 +197,7 @@ public:
     void initSPS(TComSPS *sps);
     void initPPS(TComPPS *pps);
 
-    int encode(bool bEos, const x265_picture* pic, x265_picture *pic_out);
+    int encode(const x265_picture* pic, x265_picture *pic_out);
 
     void getStreamHeaders();
 
diff -r dfaf67c21c32 -r 0b4a50730f21 source/encoder/frameencoder.cpp
--- a/source/encoder/frameencoder.cpp	Thu Jun 19 20:11:24 2014 -0500
+++ b/source/encoder/frameencoder.cpp	Thu Jun 19 20:46:10 2014 -0500
@@ -334,20 +334,14 @@ void FrameEncoder::threadMain()
 void FrameEncoder::setLambda(int qp, int row)
 {
     TComSlice*  slice = m_pic->getSlice();
-    int         chFmt = slice->getSPS()->getChromaFormatIdc();
-
-    // for RDO
-    // in RdCost there is only one lambda because the luma and chroma bits are not separated,
-    // instead we weight the distortion of chroma.
+  
     int chromaQPOffset = slice->getPPS()->getChromaCbQpOffset() + slice->getSliceQpDeltaCb();
-    int qpc = Clip3(0, MAX_MAX_QP, qp + chromaQPOffset);
-    double cbWeight = pow(2.0, (qp - g_chromaScale[chFmt][qpc]) / 3.0); // takes into account of the chroma qp mapping and chroma qp Offset
-
+    int qpCb = Clip3(0, MAX_MAX_QP, qp + chromaQPOffset);
+    
     chromaQPOffset = slice->getPPS()->getChromaCrQpOffset() + slice->getSliceQpDeltaCr();
-    qpc = Clip3(0, MAX_MAX_QP, qp + chromaQPOffset);
-    double crWeight = pow(2.0, (qp - g_chromaScale[chFmt][qpc]) / 3.0); // takes into account of the chroma qp mapping and chroma qp Offset
-
-    m_rows[row].m_search.setQP(qp, cbWeight, crWeight);
+    int qpCr = Clip3(0, MAX_MAX_QP, qp + chromaQPOffset);
+    
+    m_rows[row].m_search.setQP(qp, qpCb, qpCr);
 }
 
 void FrameEncoder::compressFrame()
@@ -356,7 +350,6 @@ void FrameEncoder::compressFrame()
     int64_t      startCompressTime = x265_mdate();
     TEncEntropy* entropyCoder      = getEntropyCoder(0);
     TComSlice*   slice             = m_pic->getSlice();
-    int          chFmt             = slice->getSPS()->getChromaFormatIdc();
     int          totalCoded        = (int)m_top->m_encodedFrameNum - 1;
 
     entropyCoder->setEntropyCoder(&m_sbacCoder, NULL);
@@ -465,20 +458,15 @@ void FrameEncoder::compressFrame()
 
     int qp = slice->getSliceQp();
 
-    // for RDO
-    // in RdCost there is only one lambda because the luma and chroma bits are not separated,
-    // instead we weight the distortion of chroma.
-    int qpc;
     int chromaQPOffset = slice->getPPS()->getChromaCbQpOffset() + slice->getSliceQpDeltaCb();
-    qpc = Clip3(0, MAX_MAX_QP, qp + chromaQPOffset);
-    double cbWeight = pow(2.0, (qp - g_chromaScale[chFmt][qpc]) / 3.0); // takes into account of the chroma qp mapping and chroma qp Offset
-
+    int qpCb = Clip3(0, MAX_MAX_QP, qp + chromaQPOffset);
+    
     chromaQPOffset = slice->getPPS()->getChromaCrQpOffset() + slice->getSliceQpDeltaCr();
-    qpc = Clip3(0, MAX_MAX_QP, qp + chromaQPOffset);
-    double crWeight = pow(2.0, (qp - g_chromaScale[chFmt][qpc]) / 3.0); // takes into account of the chroma qp mapping and chroma qp Offset
-
+    int qpCr = Clip3(0, MAX_MAX_QP, qp + chromaQPOffset);
+    
     double lambda = x265_lambda2_tab[qp];
-    double chromaLambda = lambda / crWeight;
+    /* Assuming qpCb and qpCr are the same, since SAO takes only a single chroma lambda. TODO: Check why */
+    double chromaLambda = x265_lambda2_tab[qpCb];
 
     // NOTE: set SAO lambda every Frame
     m_frameFilter.m_sao.lumaLambda = lambda;
@@ -488,7 +476,7 @@ void FrameEncoder::compressFrame()
     for (int i = 0; i < m_numRows; i++)
     {
         m_rows[i].m_search.m_me.setSourcePlane(fenc->getLumaAddr(), fenc->getStride());
-        m_rows[i].m_search.setQP(qp, cbWeight, crWeight);
+        m_rows[i].m_search.setQP(qp, qpCb, qpCr);
     }
 
     // Clip qps back to 0-51 range before encoding
diff -r dfaf67c21c32 -r 0b4a50730f21 source/encoder/slicetype.cpp
--- a/source/encoder/slicetype.cpp	Thu Jun 19 20:11:24 2014 -0500
+++ b/source/encoder/slicetype.cpp	Thu Jun 19 20:46:10 2014 -0500
@@ -141,6 +141,9 @@ void Lookahead::addPicture(TComPic *pic,
 /* Called by API thread */
 void Lookahead::flush()
 {
+    /* just in case the input queue is never allowed to fill */
+    m_bFilling = false;
+
     /* flush synchronously */
     m_inputQueueLock.acquire();
     if (!m_inputQueue.empty())
@@ -150,9 +153,6 @@ void Lookahead::flush()
     else
         m_inputQueueLock.release();
 
-    /* just in case the input queue is never allowed to fill */
-    m_bFilling = false;
-
     m_inputQueueLock.acquire();
 
     /* bFlushed indicates that an empty output queue actually means all frames


More information about the x265-commits mailing list