[x265] [PATCH 03/10] Make use of halfpel & quarterpel resolution reference frame from lookahead for mcstf

Anusuya Kumarasamy anusuya.kumarasamy at multicorewareinc.com
Mon Nov 11 14:13:25 UTC 2024


>From 0a3736655de21539cd7c302af18a46ec05c41b43 Mon Sep 17 00:00:00 2001
From: AnusuyaKumarasamy <anusuya.kumarasamy at multicorewareinc.com>
Date: Thu, 24 Oct 2024 12:57:53 +0530
Subject: [PATCH 03/10] Make use of halfpel & quarterpel resolution reference
 frame from lookahead for mcstf

---
 source/common/temporalfilter.cpp | 62 ++++++++++++++++----------------
 source/common/temporalfilter.h   |  7 ++--
 source/encoder/encoder.cpp       | 21 +++--------
 3 files changed, 40 insertions(+), 50 deletions(-)

diff --git a/source/common/temporalfilter.cpp
b/source/common/temporalfilter.cpp
index 235379b63..7c1be767e 100644
--- a/source/common/temporalfilter.cpp
+++ b/source/common/temporalfilter.cpp
@@ -194,7 +194,7 @@ fail:
 int TemporalFilter::motionErrorLumaSAD(
     pixel* src,
     int stride,
-    PicYuv *buffer,
+    pixel* buf,
     int x,
     int y,
     int dx,
@@ -205,8 +205,8 @@ int TemporalFilter::motionErrorLumaSAD(

     pixel* origOrigin = src;
     intptr_t origStride = stride;
-    pixel *buffOrigin = buffer->m_picOrg[0];
-    intptr_t buffStride = buffer->m_stride;
+    pixel *buffOrigin = buf;
+    intptr_t buffStride = stride;
     int error = 0;// dx * 10 + dy * 10;
     if (((dx | dy) & 0xF) == 0)
     {
@@ -299,7 +299,7 @@ int TemporalFilter::motionErrorLumaSAD(
 int TemporalFilter::motionErrorLumaSSD(
     pixel* src,
     int stride,
-    PicYuv *buffer,
+    pixel* buf,
     int x,
     int y,
     int dx,
@@ -310,8 +310,8 @@ int TemporalFilter::motionErrorLumaSSD(

     pixel* origOrigin = src;
     intptr_t origStride = stride;
-    pixel *buffOrigin = buffer->m_picOrg[0];
-    intptr_t buffStride = buffer->m_stride;
+    pixel *buffOrigin = buf;
+    intptr_t buffStride = stride;
     int error = 0;// dx * 10 + dy * 10;
     if (((dx | dy) & 0xF) == 0)
     {
@@ -648,7 +648,7 @@ void TemporalFilter::bilateralFilter(Frame* frame,
     }
 }

-void TemporalFilter::motionEstimationLuma(MV *mvs, uint32_t mvStride,
pixel* src,int stride, int height, int width, PicYuv *buffer, int blockSize,
+void TemporalFilter::motionEstimationLuma(MV *mvs, uint32_t mvStride,
pixel* src,int stride, int height, int width, pixel* buf, int blockSize,
     MV *previous, uint32_t prevMvStride, int factor)
 {

@@ -694,9 +694,9 @@ void TemporalFilter::motionEstimationLuma(MV *mvs,
uint32_t mvStride, pixel* src
                             MV old = previous[mvIdx];

                             if (m_useSADinME)
-                                error = motionErrorLumaSAD(src, stride,
buffer, blockX, blockY, old.x * factor, old.y * factor, blockSize,
leastError);
+                                error = motionErrorLumaSAD(src, stride,
buf, blockX, blockY, old.x * factor, old.y * factor, blockSize, leastError);
                             else
-                                error = motionErrorLumaSSD(src, stride,
buffer, blockX, blockY, old.x * factor, old.y * factor, blockSize,
leastError);
+                                error = motionErrorLumaSSD(src, stride,
buf, blockX, blockY, old.x * factor, old.y * factor, blockSize, leastError);

                             if (error < leastError)
                             {
@@ -708,9 +708,9 @@ void TemporalFilter::motionEstimationLuma(MV *mvs,
uint32_t mvStride, pixel* src
                 }

                 if (m_useSADinME)
-                    error = motionErrorLumaSAD(src, stride, buffer,
blockX, blockY, 0, 0, blockSize, leastError);
+                    error = motionErrorLumaSAD(src, stride, buf, blockX,
blockY, 0, 0, blockSize, leastError);
                 else
-                    error = motionErrorLumaSSD(src, stride, buffer,
blockX, blockY, 0, 0, blockSize, leastError);
+                    error = motionErrorLumaSSD(src, stride, buf, blockX,
blockY, 0, 0, blockSize, leastError);

                 if (error < leastError)
                 {
@@ -726,9 +726,9 @@ void TemporalFilter::motionEstimationLuma(MV *mvs,
uint32_t mvStride, pixel* src
                 for (int x2 = prevBest.x / m_motionVectorFactor - range;
x2 <= prevBest.x / m_motionVectorFactor + range; x2++)
                 {
                     if (m_useSADinME)
-                        error = motionErrorLumaSAD(src, stride, buffer,
blockX, blockY, x2 * m_motionVectorFactor, y2 * m_motionVectorFactor,
blockSize, leastError);
+                        error = motionErrorLumaSAD(src, stride, buf,
blockX, blockY, x2 * m_motionVectorFactor, y2 * m_motionVectorFactor,
blockSize, leastError);
                     else
-                        error = motionErrorLumaSSD(src, stride, buffer,
blockX, blockY, x2 * m_motionVectorFactor, y2 * m_motionVectorFactor,
blockSize, leastError);
+                        error = motionErrorLumaSSD(src, stride, buf,
blockX, blockY, x2 * m_motionVectorFactor, y2 * m_motionVectorFactor,
blockSize, leastError);
                     if (error < leastError)
                     {
                         best.set(x2 * m_motionVectorFactor, y2 *
m_motionVectorFactor);
@@ -743,9 +743,9 @@ void TemporalFilter::motionEstimationLuma(MV *mvs,
uint32_t mvStride, pixel* src
                 MV aboveMV = mvs[idx];

                 if (m_useSADinME)
-                    error = motionErrorLumaSAD(src, stride, buffer,
blockX, blockY, aboveMV.x, aboveMV.y, blockSize, leastError);
+                    error = motionErrorLumaSAD(src, stride, buf, blockX,
blockY, aboveMV.x, aboveMV.y, blockSize, leastError);
                 else
-                    error = motionErrorLumaSSD(src, stride, buffer,
blockX, blockY, aboveMV.x, aboveMV.y, blockSize, leastError);
+                    error = motionErrorLumaSSD(src, stride, buf, blockX,
blockY, aboveMV.x, aboveMV.y, blockSize, leastError);

                 if (error < leastError)
                 {
@@ -760,9 +760,9 @@ void TemporalFilter::motionEstimationLuma(MV *mvs,
uint32_t mvStride, pixel* src
                 MV leftMV = mvs[idx];

                 if (m_useSADinME)
-                    error = motionErrorLumaSAD(src, stride, buffer,
blockX, blockY, leftMV.x, leftMV.y, blockSize, leastError);
+                    error = motionErrorLumaSAD(src, stride, buf, blockX,
blockY, leftMV.x, leftMV.y, blockSize, leastError);
                 else
-                    error = motionErrorLumaSSD(src, stride, buffer,
blockX, blockY, leftMV.x, leftMV.y, blockSize, leastError);
+                    error = motionErrorLumaSSD(src, stride, buf, blockX,
blockY, leftMV.x, leftMV.y, blockSize, leastError);

                 if (error < leastError)
                 {
@@ -848,9 +848,9 @@ void TemporalFilter::motionEstimationLumaDoubleRes(MV
*mvs, uint32_t mvStride, P
                             MV old = previous[mvIdx];

                             if (m_useSADinME)
-                                error =
motionErrorLumaSAD(orig->m_picOrg[0], orig->m_stride, buffer, blockX,
blockY, old.x * factor, old.y * factor, blockSize, leastError);
+                                error =
motionErrorLumaSAD(orig->m_picOrg[0], orig->m_stride, buffer->m_picOrg[0],
blockX, blockY, old.x * factor, old.y * factor, blockSize, leastError);
                             else
-                                error =
motionErrorLumaSSD(orig->m_picOrg[0], orig->m_stride, buffer, blockX,
blockY, old.x * factor, old.y * factor, blockSize, leastError);
+                                error =
motionErrorLumaSSD(orig->m_picOrg[0], orig->m_stride, buffer->m_picOrg[0],
blockX, blockY, old.x * factor, old.y * factor, blockSize, leastError);

                             if (error < leastError)
                             {
@@ -862,9 +862,9 @@ void TemporalFilter::motionEstimationLumaDoubleRes(MV
*mvs, uint32_t mvStride, P
                 }

                 if (m_useSADinME)
-                    error = motionErrorLumaSAD(orig->m_picOrg[0],
orig->m_stride, buffer, blockX, blockY, 0, 0, blockSize, leastError);
+                    error = motionErrorLumaSAD(orig->m_picOrg[0],
orig->m_stride, buffer->m_picOrg[0], blockX, blockY, 0, 0, blockSize,
leastError);
                 else
-                    error = motionErrorLumaSSD(orig->m_picOrg[0],
orig->m_stride, buffer, blockX, blockY, 0, 0, blockSize, leastError);
+                    error = motionErrorLumaSSD(orig->m_picOrg[0],
orig->m_stride, buffer->m_picOrg[0], blockX, blockY, 0, 0, blockSize,
leastError);

                 if (error < leastError)
                 {
@@ -880,9 +880,9 @@ void TemporalFilter::motionEstimationLumaDoubleRes(MV
*mvs, uint32_t mvStride, P
                 for (int x2 = prevBest.x / m_motionVectorFactor - range;
x2 <= prevBest.x / m_motionVectorFactor + range; x2++)
                 {
                     if (m_useSADinME)
-                        error = motionErrorLumaSAD(orig->m_picOrg[0],
orig->m_stride, buffer, blockX, blockY, x2 * m_motionVectorFactor, y2 *
m_motionVectorFactor, blockSize, leastError);
+                        error = motionErrorLumaSAD(orig->m_picOrg[0],
orig->m_stride, buffer->m_picOrg[0], blockX, blockY, x2 *
m_motionVectorFactor, y2 * m_motionVectorFactor, blockSize, leastError);
                     else
-                        error = motionErrorLumaSSD(orig->m_picOrg[0],
orig->m_stride, buffer, blockX, blockY, x2 * m_motionVectorFactor, y2 *
m_motionVectorFactor, blockSize, leastError);
+                        error = motionErrorLumaSSD(orig->m_picOrg[0],
orig->m_stride, buffer->m_picOrg[0], blockX, blockY, x2 *
m_motionVectorFactor, y2 * m_motionVectorFactor, blockSize, leastError);

                     if (error < leastError)
                     {
@@ -899,9 +899,9 @@ void TemporalFilter::motionEstimationLumaDoubleRes(MV
*mvs, uint32_t mvStride, P
                 for (int x2 = prevBest.x - doubleRange; x2 <= prevBest.x +
doubleRange; x2 += 4)
                 {
                     if (m_useSADinME)
-                        error = motionErrorLumaSAD(orig->m_picOrg[0],
orig->m_stride, buffer, blockX, blockY, x2, y2, blockSize, leastError);
+                        error = motionErrorLumaSAD(orig->m_picOrg[0],
orig->m_stride, buffer->m_picOrg[0], blockX, blockY, x2, y2, blockSize,
leastError);
                     else
-                        error = motionErrorLumaSSD(orig->m_picOrg[0],
orig->m_stride, buffer, blockX, blockY, x2, y2, blockSize, leastError);
+                        error = motionErrorLumaSSD(orig->m_picOrg[0],
orig->m_stride, buffer->m_picOrg[0], blockX, blockY, x2, y2, blockSize,
leastError);

                     if (error < leastError)
                     {
@@ -918,9 +918,9 @@ void TemporalFilter::motionEstimationLumaDoubleRes(MV
*mvs, uint32_t mvStride, P
                 for (int x2 = prevBest.x - doubleRange; x2 <= prevBest.x +
doubleRange; x2++)
                 {
                     if (m_useSADinME)
-                        error = motionErrorLumaSAD(orig->m_picOrg[0],
orig->m_stride, buffer, blockX, blockY, x2, y2, blockSize, leastError);
+                        error = motionErrorLumaSAD(orig->m_picOrg[0],
orig->m_stride, buffer->m_picOrg[0], blockX, blockY, x2, y2, blockSize,
leastError);
                     else
-                        error = motionErrorLumaSSD(orig->m_picOrg[0],
orig->m_stride, buffer, blockX, blockY, x2, y2, blockSize, leastError);
+                        error = motionErrorLumaSSD(orig->m_picOrg[0],
orig->m_stride, buffer->m_picOrg[0], blockX, blockY, x2, y2, blockSize,
leastError);

                     if (error < leastError)
                     {
@@ -937,9 +937,9 @@ void TemporalFilter::motionEstimationLumaDoubleRes(MV
*mvs, uint32_t mvStride, P
                 MV aboveMV = mvs[idx];

                 if (m_useSADinME)
-                    error = motionErrorLumaSAD(orig->m_picOrg[0],
orig->m_stride, buffer, blockX, blockY, aboveMV.x, aboveMV.y, blockSize,
leastError);
+                    error = motionErrorLumaSAD(orig->m_picOrg[0],
orig->m_stride, buffer->m_picOrg[0], blockX, blockY, aboveMV.x, aboveMV.y,
blockSize, leastError);
                 else
-                    error = motionErrorLumaSSD(orig->m_picOrg[0],
orig->m_stride, buffer, blockX, blockY, aboveMV.x, aboveMV.y, blockSize,
leastError);
+                    error = motionErrorLumaSSD(orig->m_picOrg[0],
orig->m_stride, buffer->m_picOrg[0], blockX, blockY, aboveMV.x, aboveMV.y,
blockSize, leastError);

                 if (error < leastError)
                 {
@@ -954,9 +954,9 @@ void TemporalFilter::motionEstimationLumaDoubleRes(MV
*mvs, uint32_t mvStride, P
                 MV leftMV = mvs[idx];

                 if (m_useSADinME)
-                    error = motionErrorLumaSAD(orig->m_picOrg[0],
orig->m_stride, buffer, blockX, blockY, leftMV.x, leftMV.y, blockSize,
leastError);
+                    error = motionErrorLumaSAD(orig->m_picOrg[0],
orig->m_stride, buffer->m_picOrg[0], blockX, blockY, leftMV.x, leftMV.y,
blockSize, leastError);
                 else
-                    error = motionErrorLumaSSD(orig->m_picOrg[0],
orig->m_stride, buffer, blockX, blockY, leftMV.x, leftMV.y, blockSize,
leastError);
+                    error = motionErrorLumaSSD(orig->m_picOrg[0],
orig->m_stride, buffer->m_picOrg[0], blockX, blockY, leftMV.x, leftMV.y,
blockSize, leastError);

                 if (error < leastError)
                 {
diff --git a/source/common/temporalfilter.h b/source/common/temporalfilter.h
index ae60c77f8..9fe51da8c 100644
--- a/source/common/temporalfilter.h
+++ b/source/common/temporalfilter.h
@@ -104,6 +104,7 @@ namespace X265_NS {
         uint32_t   mvsStride2;
         int*       error;
         int*       noise;
+        int        poc;

         int16_t    origOffset;
         bool       isFilteredFrame;
@@ -152,7 +153,7 @@ namespace X265_NS {

         void bilateralFilter(Frame* frame, TemporalFilterRefPicInfo*
mctfRefList, double overallStrength);

-        void motionEstimationLuma(MV *mvs, uint32_t mvStride, pixel* src,
int stride, int height, int width, PicYuv *buffer, int bs,
+        void motionEstimationLuma(MV *mvs, uint32_t mvStride, pixel* src,
int stride, int height, int width, pixel* buf, int bs,
             MV *previous = 0, uint32_t prevmvStride = 0, int factor = 1);

         void motionEstimationLumaDoubleRes(MV *mvs, uint32_t mvStride,
PicYuv *orig, PicYuv *buffer, int blockSize,
@@ -160,7 +161,7 @@ namespace X265_NS {

         int motionErrorLumaSSD(pixel* src,
             int stride,
-            PicYuv *buffer,
+            pixel* buf,
             int x,
             int y,
             int dx,
@@ -170,7 +171,7 @@ namespace X265_NS {

         int motionErrorLumaSAD(pixel* src,
             int stride,
-            PicYuv *buffer,
+            pixel* buf,
             int x,
             int y,
             int dx,
diff --git a/source/encoder/encoder.cpp b/source/encoder/encoder.cpp
index 58818379a..0a0c09307 100644
--- a/source/encoder/encoder.cpp
+++ b/source/encoder/encoder.cpp
@@ -1408,6 +1408,7 @@ bool Encoder::isFilterThisframe(uint8_t
sliceTypeConfig, int curSliceType)
 inline int enqueueRefFrame(FrameEncoder* curframeEncoder, Frame*
iterFrame, Frame* curFrame, bool isPreFiltered, int16_t i)
 {
     TemporalFilterRefPicInfo* dest =
&curframeEncoder->m_mcstfRefList[curFrame->m_mcstf->m_numRef];
+    dest->poc = iterFrame->m_poc;
     dest->picBuffer = iterFrame->m_fencPic;
     dest->picBufferSubSampled2 = iterFrame->m_fencPicSubsampled2;
     dest->picBufferSubSampled4 = iterFrame->m_fencPicSubsampled4;
@@ -2510,23 +2511,11 @@ int Encoder::encode(const x265_picture* pic_in,
x265_picture* pic_out)
                 for (uint8_t i = 1; i <= frameEnc[0]->m_mcstf->m_numRef;
i++)
                 {
                     TemporalFilterRefPicInfo *ref =
&curEncoder->m_mcstfRefList[i - 1];
-                    if (!*ref->isSubsampled)
-                    {
-                        primitives.frameSubSampleLuma((const pixel
*)ref->picBuffer->m_picOrg[0], ref->picBufferSubSampled2->m_picOrg[0],
ref->picBuffer->m_stride, ref->picBufferSubSampled2->m_stride,
ref->picBufferSubSampled2->m_picWidth,
ref->picBufferSubSampled2->m_picHeight);
-
 extendPicBorder(ref->picBufferSubSampled2->m_picOrg[0],
ref->picBufferSubSampled2->m_stride, ref->picBufferSubSampled2->m_picWidth,
ref->picBufferSubSampled2->m_picHeight,
ref->picBufferSubSampled2->m_lumaMarginX,
ref->picBufferSubSampled2->m_lumaMarginY);
-                        primitives.frameSubSampleLuma((const pixel
*)ref->picBufferSubSampled2->m_picOrg[0],ref->picBufferSubSampled4->m_picOrg[0],
ref->picBufferSubSampled2->m_stride, ref->picBufferSubSampled4->m_stride,
ref->picBufferSubSampled4->m_picWidth,
ref->picBufferSubSampled4->m_picHeight);
-
 extendPicBorder(ref->picBufferSubSampled4->m_picOrg[0],
ref->picBufferSubSampled4->m_stride, ref->picBufferSubSampled4->m_picWidth,
ref->picBufferSubSampled4->m_picHeight,
ref->picBufferSubSampled4->m_lumaMarginX,
ref->picBufferSubSampled4->m_lumaMarginY);
-                        *ref->isSubsampled = true;
-                    }
-                }
-
-                for (uint8_t i = 1; i <= frameEnc[0]->m_mcstf->m_numRef;
i++)
-                {
-                    TemporalFilterRefPicInfo *ref =
&curEncoder->m_mcstfRefList[i - 1];
+                    Frame* curFrame =
m_origPicBuffer->m_mcstfPicList.getPOCMCSTF(ref->poc);

-
 curEncoder->m_frameEncTF->motionEstimationLuma(ref->mvs0, ref->mvsStride0,
frameEnc[0]->m_lowres.lowerResPlane[0], (frameEnc[0]->m_lowres.lumaStride /
2), frameEnc[0]->m_fencPicSubsampled4->m_picHeight,
frameEnc[0]->m_fencPicSubsampled4->m_picWidth, ref->picBufferSubSampled4,
16);
-
 curEncoder->m_frameEncTF->motionEstimationLuma(ref->mvs1, ref->mvsStride1,
frameEnc[0]->m_lowres.lowresPlane[0], frameEnc[0]->m_lowres.lumaStride,
frameEnc[0]->m_fencPicSubsampled2->m_picHeight,
frameEnc[0]->m_fencPicSubsampled2->m_picWidth, ref->picBufferSubSampled2,
16, ref->mvs0, ref->mvsStride0, 2);
-
 curEncoder->m_frameEncTF->motionEstimationLuma(ref->mvs2, ref->mvsStride2,
frameEnc[0]->m_fencPic->m_picOrg[0], frameEnc[0]->m_fencPic->m_stride,
frameEnc[0]->m_fencPic->m_picHeight, frameEnc[0]->m_fencPic->m_picWidth,
ref->picBuffer, 16, ref->mvs1, ref->mvsStride1, 2);
+
 curEncoder->m_frameEncTF->motionEstimationLuma(ref->mvs0, ref->mvsStride0,
frameEnc[0]->m_lowres.lowerResPlane[0], (frameEnc[0]->m_lowres.lumaStride /
2), frameEnc[0]->m_fencPicSubsampled4->m_picHeight,
frameEnc[0]->m_fencPicSubsampled4->m_picWidth,
curFrame->m_lowres.lowerResPlane[0], 16);
+
 curEncoder->m_frameEncTF->motionEstimationLuma(ref->mvs1, ref->mvsStride1,
frameEnc[0]->m_lowres.lowresPlane[0], frameEnc[0]->m_lowres.lumaStride,
frameEnc[0]->m_fencPicSubsampled2->m_picHeight,
frameEnc[0]->m_fencPicSubsampled2->m_picWidth,
curFrame->m_lowres.lowresPlane[0], 16, ref->mvs0, ref->mvsStride0, 2);
+
 curEncoder->m_frameEncTF->motionEstimationLuma(ref->mvs2, ref->mvsStride2,
frameEnc[0]->m_fencPic->m_picOrg[0], frameEnc[0]->m_fencPic->m_stride,
frameEnc[0]->m_fencPic->m_picHeight, frameEnc[0]->m_fencPic->m_picWidth,
ref->picBuffer->m_picOrg[0], 16, ref->mvs1, ref->mvsStride1, 2);

 curEncoder->m_frameEncTF->motionEstimationLumaDoubleRes(ref->mvs,
ref->mvsStride, frameEnc[0]->m_fencPic, ref->picBuffer, 8, ref->mvs2,
ref->mvsStride2, 1, ref->error);
                 }

-- 
2.36.0.windows.1
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://mailman.videolan.org/pipermail/x265-devel/attachments/20241111/f4481a4c/attachment-0001.htm>
-------------- next part --------------
A non-text attachment was scrubbed...
Name: 0003-Make-use-of-halfpel-quarterpel-resolution-reference-.patch
Type: application/octet-stream
Size: 19445 bytes
Desc: not available
URL: <http://mailman.videolan.org/pipermail/x265-devel/attachments/20241111/f4481a4c/attachment-0001.obj>


More information about the x265-devel mailing list