[x265] [PATCH] rd: determine CU complexity to skip analysis of higher depths
kavitha at multicorewareinc.com
kavitha at multicorewareinc.com
Thu Jun 16 10:29:39 CEST 2016
# HG changeset patch
# User Kavitha Sampath <kavitha at multicorewareinc.com>
# Date 1466062058 -19800
# Thu Jun 16 12:57:38 2016 +0530
# Node ID 0d3fe50466f995ad519e20d1dc7ab7ec6920db00
# Parent 78ffb67a844e3e76facf18c52790f1bd544754d6
rd: determine CU complexity to skip analysis of higher depths
Complexity check is performed for RD level 2 of 4K videos
diff -r 78ffb67a844e -r 0d3fe50466f9 source/encoder/analysis.cpp
--- a/source/encoder/analysis.cpp Fri Jun 10 15:53:28 2016 +0530
+++ b/source/encoder/analysis.cpp Thu Jun 16 12:57:38 2016 +0530
@@ -74,6 +74,7 @@
{
m_reuseInterDataCTU = NULL;
m_reuseRef = NULL;
+ m_is4k = false;
}
bool Analysis::create(ThreadLocalData *tld)
{
@@ -105,6 +106,8 @@
md.pred[j].fencYuv = &md.fencYuv;
}
}
+ if (m_param->sourceWidth >= 3840)
+ m_is4k = true;
return ok;
}
@@ -944,8 +947,13 @@
if (md.bestMode && m_param->bEnableRecursionSkip)
{
skipRecursion = md.bestMode->cu.isSkipped(0);
- if (mightSplit && depth && depth >= minDepth && !skipRecursion)
- skipRecursion = recursionDepthCheck(parentCTU, cuGeom, *md.bestMode);
+ if (mightSplit && depth >= minDepth && !skipRecursion)
+ {
+ if (depth)
+ skipRecursion = recursionDepthCheck(parentCTU, cuGeom, *md.bestMode);
+ if (m_is4k && !skipRecursion && m_param->rdLevel == 2 && md.fencYuv.m_size != MAX_CU_SIZE)
+ skipRecursion = complexityCheckCU(*md.bestMode);
+ }
}
/* Step 2. Evaluate each of the 4 split sub-blocks in series */
@@ -2593,6 +2601,30 @@
return false;
}
+bool Analysis::complexityCheckCU(const Mode& bestMode)
+{
+ uint32_t mean = 0;
+ uint32_t homo = 0;
+ uint32_t cuSize = bestMode.fencYuv->m_size;
+ for (uint32_t y = 0; y < cuSize; y++) {
+ for (uint32_t x = 0; x < cuSize; x++) {
+ mean += (bestMode.fencYuv->m_buf[0][y * cuSize + x]);
+ }
+ }
+ mean = mean / (cuSize * cuSize);
+ for (uint32_t y = 0 ; y < cuSize; y++){
+ for (uint32_t x = 0 ; x < cuSize; x++){
+ homo += abs(int(bestMode.fencYuv->m_buf[0][y * cuSize + x] - mean));
+ }
+ }
+ homo = homo / (cuSize * cuSize);
+
+ if (homo < (.1 * mean))
+ return true;
+
+ return false;
+}
+
int Analysis::calculateQpforCuSize(const CUData& ctu, const CUGeom& cuGeom, double baseQp)
{
FrameData& curEncData = *m_frame->m_encData;
diff -r 78ffb67a844e -r 0d3fe50466f9 source/encoder/analysis.h
--- a/source/encoder/analysis.h Fri Jun 10 15:53:28 2016 +0530
+++ b/source/encoder/analysis.h Thu Jun 16 12:57:38 2016 +0530
@@ -108,6 +108,7 @@
ModeDepth m_modeDepth[NUM_CU_DEPTH];
bool m_bTryLossless;
bool m_bChromaSa8d;
+ bool m_is4k;
Analysis();
@@ -160,6 +161,7 @@
/* work-avoidance heuristics for RD levels < 5 */
uint32_t topSkipMinDepth(const CUData& parentCTU, const CUGeom& cuGeom);
bool recursionDepthCheck(const CUData& parentCTU, const CUGeom& cuGeom, const Mode& bestMode);
+ bool complexityCheckCU(const Mode& bestMode);
/* generate residual and recon pixels for an entire CTU recursively (RD0) */
void encodeResidue(const CUData& parentCTU, const CUGeom& cuGeom);
More information about the x265-devel
mailing list