[x265] [PATCH 3/14] Added functions related to mcstf feature
Snehaa Giridharan
snehaa at multicorewareinc.com
Wed Oct 19 07:29:25 UTC 2022
>From 7c777cce9b374a31c999c960f1e794616987cb8f Mon Sep 17 00:00:00 2001
From: ashok2022 <ashok at multicorewareinc.com>
Date: Wed, 21 Sep 2022 17:48:38 +0530
Subject: [PATCH] Added functions related to mcstf feature
---
source/common/common.h | 2 +
source/common/frame.cpp | 64 ++++++++++++++++++++++++
source/common/frame.h | 12 +++++
source/common/mv.h | 2 +
source/common/piclist.cpp | 101 ++++++++++++++++++++++++++++++++++++++
source/common/piclist.h | 7 +++
source/common/picyuv.cpp | 52 ++++++++++++++++++++
source/common/picyuv.h | 2 +
source/common/slice.h | 1 +
9 files changed, 243 insertions(+)
diff --git a/source/common/common.h b/source/common/common.h
index a245c7dae..982b03d89 100644
--- a/source/common/common.h
+++ b/source/common/common.h
@@ -342,6 +342,8 @@ typedef int16_t coeff_t; // transform coefficient
#define MAX_NUM_DYN_REFINE (NUM_CU_DEPTH *
X265_REFINE_INTER_LEVELS)
#define X265_BYTE 8
+#define MAX_MCTF_TEMPORAL_WINDOW_LENGTH 8
+
namespace X265_NS {
enum { SAO_NUM_OFFSET = 4 };
diff --git a/source/common/frame.cpp b/source/common/frame.cpp
index 255882a9d..0ce301bfa 100644
--- a/source/common/frame.cpp
+++ b/source/common/frame.cpp
@@ -64,12 +64,38 @@ Frame::Frame()
m_edgeBitPlane = NULL;
m_edgeBitPic = NULL;
m_isInsideWindow = 0;
+
+ // mcstf
+ m_isSubSampled = NULL;
+ m_mcstf = NULL;
+ m_refPicCnt[0] = 0;
+ m_refPicCnt[1] = 0;
+ m_nextMCSTF = NULL;
+ m_prevMCSTF = NULL;
+
}
bool Frame::create(x265_param *param, float* quantOffsets)
{
m_fencPic = new PicYuv;
m_param = param;
+
+ if (m_param->bEnableGopBasedTemporalFilter)
+ {
+ m_mcstf = new TemporalFilter;
+ m_mcstf->init(param);
+
+ m_fencPicSubsampled2 = new PicYuv;
+ m_fencPicSubsampled4 = new PicYuv;
+
+ if (!m_fencPicSubsampled2->createScaledPicYUV(param, 2))
+ return false;
+ if (!m_fencPicSubsampled4->createScaledPicYUV(param, 4))
+ return false;
+
+ CHECKED_MALLOC_ZERO(m_isSubSampled, int, 1);
+ }
+
CHECKED_MALLOC_ZERO(m_rcData, RcStats, 1);
if (param->bCTUInfo)
@@ -151,6 +177,24 @@ fail:
return false;
}
+bool Frame::createSubSample()
+{
+
+ //m_param = param;
+
+ m_fencPicSubsampled2 = new PicYuv;
+ m_fencPicSubsampled4 = new PicYuv;
+
+ if (!m_fencPicSubsampled2->createScaledPicYUV(m_param, 2))
+ return false;
+ if (!m_fencPicSubsampled4->createScaledPicYUV(m_param, 4))
+ return false;
+ CHECKED_MALLOC_ZERO(m_isSubSampled, int, 1);
+ return true;
+fail:
+ return false;
+}
+
bool Frame::allocEncodeData(x265_param *param, const SPS& sps)
{
m_encData = new FrameData;
@@ -207,6 +251,26 @@ void Frame::destroy()
m_fencPic = NULL;
}
+ if (m_param->bEnableGopBasedTemporalFilter)
+ {
+
+ if (m_fencPicSubsampled2)
+ {
+ m_fencPicSubsampled2->destroy();
+ delete m_fencPicSubsampled2;
+ m_fencPicSubsampled2 = NULL;
+ }
+
+ if (m_fencPicSubsampled4)
+ {
+ m_fencPicSubsampled4->destroy();
+ delete m_fencPicSubsampled4;
+ m_fencPicSubsampled4 = NULL;
+ }
+ delete m_mcstf;
+ X265_FREE(m_isSubSampled);
+ }
+
if (m_reconPic)
{
m_reconPic->destroy();
diff --git a/source/common/frame.h b/source/common/frame.h
index ac1185e81..b1dd00e21 100644
--- a/source/common/frame.h
+++ b/source/common/frame.h
@@ -28,6 +28,7 @@
#include "common.h"
#include "lowres.h"
#include "threading.h"
+#include "temporalfilter.h"
namespace X265_NS {
// private namespace
@@ -84,6 +85,9 @@ public:
/* Data associated with x265_picture */
PicYuv* m_fencPic;
+ PicYuv* m_fencPicSubsampled2;
+ PicYuv* m_fencPicSubsampled4;
+
int m_poc;
int m_encodeOrder;
int64_t m_pts; // user provided
presentation time stamp
@@ -133,6 +137,13 @@ public:
bool m_classifyFrame;
int m_fieldNum;
+ /*MCSTF*/
+ TemporalFilter* m_mcstf;
+ int m_refPicCnt[2];
+ Frame* m_nextMCSTF; // PicList doubly linked
list pointers
+ Frame* m_prevMCSTF;
+ int* m_isSubSampled;
+
/* aq-mode 4 : Gaussian, edge and theta frames for edge information */
pixel* m_edgePic;
pixel* m_gaussianPic;
@@ -147,6 +158,7 @@ public:
Frame();
bool create(x265_param *param, float* quantOffsets);
+ bool createSubSample();
bool allocEncodeData(x265_param *param, const SPS& sps);
void reinit(const SPS& sps);
void destroy();
diff --git a/source/common/mv.h b/source/common/mv.h
index 191090cb9..5a8872cdd 100644
--- a/source/common/mv.h
+++ b/source/common/mv.h
@@ -105,6 +105,8 @@ public:
{
return x >= _min.x && x <= _max.x && y >= _min.y && y <= _max.y;
}
+
+ void set(int32_t _x, int32_t _y) { x = _x; y = _y; }
};
}
diff --git a/source/common/piclist.cpp b/source/common/piclist.cpp
index 91929f101..275617f6f 100644
--- a/source/common/piclist.cpp
+++ b/source/common/piclist.cpp
@@ -45,6 +45,25 @@ void PicList::pushFront(Frame& curFrame)
m_count++;
}
+void PicList::pushFrontMCSTF(Frame& curFrame)
+{
+ X265_CHECK(!curFrame.m_nextMCSTF && !curFrame.m_nextMCSTF, "piclist:
picture already in OPB list\n"); // ensure frame is not in a list
+ curFrame.m_nextMCSTF = m_start;
+ curFrame.m_prevMCSTF = NULL;
+
+ if (m_count)
+ {
+ m_start->m_prevMCSTF = &curFrame;
+ m_start = &curFrame;
+ }
+ else
+ {
+ m_start = m_end = &curFrame;
+ }
+ m_count++;
+
+}
+
void PicList::pushBack(Frame& curFrame)
{
X265_CHECK(!curFrame.m_next && !curFrame.m_prev, "piclist: picture
already in list\n"); // ensure frame is not in a list
@@ -63,6 +82,24 @@ void PicList::pushBack(Frame& curFrame)
m_count++;
}
+void PicList::pushBackMCSTF(Frame& curFrame)
+{
+ X265_CHECK(!curFrame.m_nextMCSTF && !curFrame.m_prevMCSTF, "piclist:
picture already in OPB list\n"); // ensure frame is not in a list
+ curFrame.m_nextMCSTF = NULL;
+ curFrame.m_prevMCSTF = m_end;
+
+ if (m_count)
+ {
+ m_end->m_nextMCSTF = &curFrame;
+ m_end = &curFrame;
+ }
+ else
+ {
+ m_start = m_end = &curFrame;
+ }
+ m_count++;
+}
+
Frame *PicList::popFront()
{
if (m_start)
@@ -94,6 +131,14 @@ Frame* PicList::getPOC(int poc)
return curFrame;
}
+Frame* PicList::getPOCMCSTF(int poc)
+{
+ Frame *curFrame = m_start;
+ while (curFrame && curFrame->m_poc != poc)
+ curFrame = curFrame->m_nextMCSTF;
+ return curFrame;
+}
+
Frame *PicList::popBack()
{
if (m_end)
@@ -117,6 +162,29 @@ Frame *PicList::popBack()
return NULL;
}
+Frame *PicList::popBackMCSTF()
+{
+ if (m_end)
+ {
+ Frame* temp = m_end;
+ m_count--;
+
+ if (m_count)
+ {
+ m_end = m_end->m_prevMCSTF;
+ m_end->m_nextMCSTF = NULL;
+ }
+ else
+ {
+ m_start = m_end = NULL;
+ }
+ temp->m_nextMCSTF = temp->m_prevMCSTF = NULL;
+ return temp;
+ }
+ else
+ return NULL;
+}
+
Frame* PicList::getCurFrame(void)
{
Frame *curFrame = m_start;
@@ -158,3 +226,36 @@ void PicList::remove(Frame& curFrame)
curFrame.m_next = curFrame.m_prev = NULL;
}
+
+void PicList::removeMCSTF(Frame& curFrame)
+{
+#if _DEBUG
+ Frame *tmp = m_start;
+ while (tmp && tmp != &curFrame)
+ {
+ tmp = tmp->m_nextMCSTF;
+ }
+
+ X265_CHECK(tmp == &curFrame, "framelist: pic being removed was not in
list\n"); // verify pic is in this list
+#endif
+
+ m_count--;
+ if (m_count)
+ {
+ if (m_start == &curFrame)
+ m_start = curFrame.m_nextMCSTF;
+ if (m_end == &curFrame)
+ m_end = curFrame.m_prevMCSTF;
+
+ if (curFrame.m_nextMCSTF)
+ curFrame.m_nextMCSTF->m_prevMCSTF = curFrame.m_prevMCSTF;
+ if (curFrame.m_prevMCSTF)
+ curFrame.m_prevMCSTF->m_nextMCSTF = curFrame.m_nextMCSTF;
+ }
+ else
+ {
+ m_start = m_end = NULL;
+ }
+
+ curFrame.m_nextMCSTF = curFrame.m_prevMCSTF = NULL;
+}
diff --git a/source/common/piclist.h b/source/common/piclist.h
index e1d6e714a..45023c93b 100644
--- a/source/common/piclist.h
+++ b/source/common/piclist.h
@@ -49,24 +49,31 @@ public:
/** Push picture to end of the list */
void pushBack(Frame& pic);
+ void pushBackMCSTF(Frame& pic);
/** Push picture to beginning of the list */
void pushFront(Frame& pic);
+ void pushFrontMCSTF(Frame& pic);
/** Pop picture from end of the list */
Frame* popBack();
+ Frame* popBackMCSTF();
/** Pop picture from beginning of the list */
Frame* popFront();
/** Find frame with specified POC */
Frame* getPOC(int poc);
+ /* Find next MCSTF frame with specified POC */
+ Frame* getPOCMCSTF(int poc);
/** Get the current Frame from the list **/
Frame* getCurFrame(void);
/** Remove picture from list */
void remove(Frame& pic);
+ /* Remove MCSTF picture from list */
+ void removeMCSTF(Frame& pic);
Frame* first() { return m_start; }
diff --git a/source/common/picyuv.cpp b/source/common/picyuv.cpp
index e65dbdd46..2855356b5 100644
--- a/source/common/picyuv.cpp
+++ b/source/common/picyuv.cpp
@@ -125,6 +125,58 @@ fail:
return false;
}
+/*Copy pixels from the picture buffer of a frame to picture buffer of
another frame*/
+void PicYuv::copyFromFrame(PicYuv* source)
+{
+ uint32_t numCuInHeight = (m_picHeight + m_param->maxCUSize - 1) /
m_param->maxCUSize;
+
+ int maxHeight = numCuInHeight * m_param->maxCUSize;
+ memcpy(m_picBuf[0], source->m_picBuf[0], sizeof(pixel)* m_stride *
(maxHeight + (m_lumaMarginY * 2)));
+ m_picOrg[0] = m_picBuf[0] + m_lumaMarginY * m_stride + m_lumaMarginX;
+
+ if (m_picCsp != X265_CSP_I400)
+ {
+ memcpy(m_picBuf[1], source->m_picBuf[1], sizeof(pixel)* m_strideC
* ((maxHeight >> m_vChromaShift) + (m_chromaMarginY * 2)));
+ memcpy(m_picBuf[2], source->m_picBuf[2], sizeof(pixel)* m_strideC
* ((maxHeight >> m_vChromaShift) + (m_chromaMarginY * 2)));
+
+ m_picOrg[1] = m_picBuf[1] + m_chromaMarginY * m_strideC +
m_chromaMarginX;
+ m_picOrg[2] = m_picBuf[2] + m_chromaMarginY * m_strideC +
m_chromaMarginX;
+ }
+ else
+ {
+ m_picBuf[1] = m_picBuf[2] = NULL;
+ m_picOrg[1] = m_picOrg[2] = NULL;
+ }
+}
+
+bool PicYuv::createScaledPicYUV(x265_param* param, uint8_t scaleFactor)
+{
+ m_param = param;
+ m_picWidth = m_param->sourceWidth / scaleFactor;
+ m_picHeight = m_param->sourceHeight / scaleFactor;
+
+ m_picCsp = m_param->internalCsp;
+ m_hChromaShift = CHROMA_H_SHIFT(m_picCsp);
+ m_vChromaShift = CHROMA_V_SHIFT(m_picCsp);
+
+ uint32_t numCuInWidth = (m_picWidth + param->maxCUSize - 1) /
param->maxCUSize;
+ uint32_t numCuInHeight = (m_picHeight + param->maxCUSize - 1) /
param->maxCUSize;
+
+ m_lumaMarginX = 32; // search margin for L0 and L1 ME in horizontal
direction
+ m_lumaMarginY = 32; // search margin for L0 and L1 ME in vertical
direction
+ m_stride = (numCuInWidth * param->maxCUSize) + (m_lumaMarginX << 1);
+
+ int maxHeight = numCuInHeight * param->maxCUSize;
+ CHECKED_MALLOC_ZERO(m_picBuf[0], pixel, m_stride * (maxHeight +
(m_lumaMarginY * 2)));
+ m_picOrg[0] = m_picBuf[0] + m_lumaMarginY * m_stride + m_lumaMarginX;
+ m_picBuf[1] = m_picBuf[2] = NULL;
+ m_picOrg[1] = m_picOrg[2] = NULL;
+ return true;
+
+fail:
+ return false;
+}
+
int PicYuv::getLumaBufLen(uint32_t picWidth, uint32_t picHeight, uint32_t
picCsp)
{
m_picWidth = picWidth;
diff --git a/source/common/picyuv.h b/source/common/picyuv.h
index 0b53d354d..ba448567a 100644
--- a/source/common/picyuv.h
+++ b/source/common/picyuv.h
@@ -78,11 +78,13 @@ public:
PicYuv();
bool create(x265_param* param, bool picAlloc = true, pixel *pixelbuf
= NULL);
+ bool createScaledPicYUV(x265_param* param, uint8_t scaleFactor);
bool createOffsets(const SPS& sps);
void destroy();
int getLumaBufLen(uint32_t picWidth, uint32_t picHeight, uint32_t
picCsp);
void copyFromPicture(const x265_picture&, const x265_param& param,
int padx, int pady);
+ void copyFromFrame(PicYuv* source);
intptr_t getChromaAddrOffset(uint32_t ctuAddr, uint32_t absPartIdx)
const { return m_cuOffsetC[ctuAddr] + m_buOffsetC[absPartIdx]; }
diff --git a/source/common/slice.h b/source/common/slice.h
index 9a48d39c6..c5327c198 100644
--- a/source/common/slice.h
+++ b/source/common/slice.h
@@ -363,6 +363,7 @@ public:
int m_iNumRPSInSPS;
const x265_param *m_param;
int m_fieldNum;
+ Frame* m_mcstfRefFrameList[2][MAX_MCTF_TEMPORAL_WINDOW_LENGTH];
Slice()
{
--
2.34.1.windows.1
*Thanks and Regards,*
*Snehaa.GVideo Codec Engineer,Media & AI analytics
<https://multicorewareinc.com/>*
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://mailman.videolan.org/pipermail/x265-devel/attachments/20221019/151f7de6/attachment-0001.html>
-------------- next part --------------
A non-text attachment was scrubbed...
Name: mcstf_patch_03.diff
Type: application/octet-stream
Size: 13201 bytes
Desc: not available
URL: <http://mailman.videolan.org/pipermail/x265-devel/attachments/20221019/151f7de6/attachment-0001.obj>
More information about the x265-devel
mailing list