[x265] [PATCH] API: 'x265_set_analysis_data' to capture analysis information
praveen at multicorewareinc.com
praveen at multicorewareinc.com
Wed Nov 15 10:11:11 CET 2017
# HG changeset patch
# User Praveen Tiwari <praveen at multicorewareinc.com>
# Date 1510555850 -19800
# Mon Nov 13 12:20:50 2017 +0530
# Node ID 2fec493b990ee3066e5ffc853d83669955f0ee3c
# Parent dd9772385d152528201d335efbc6f75fdc43b08c
API: 'x265_set_analysis_data' to capture analysis information
diff -r dd9772385d15 -r 2fec493b990e doc/reST/api.rst
--- a/doc/reST/api.rst Tue Nov 14 11:00:09 2017 +0530
+++ b/doc/reST/api.rst Mon Nov 13 12:20:50 2017 +0530
@@ -215,6 +215,13 @@
* the encoder will wait for this copy to complete if enabled.
*/
+**x265_set_analysis_data()** may be used to recive analysis information from external application::
+
+ /* x265_set_analysis_data:
+ * set the analysis data,
+ * returns negative on error, 0 access unit were output. */
+ int x265_set_analysis_data(x265_encoder *encoder, x265_analysis_data *analysis_data, int poc, uint32_t cuBytes);
+
Pictures
========
diff -r dd9772385d15 -r 2fec493b990e source/CMakeLists.txt
--- a/source/CMakeLists.txt Tue Nov 14 11:00:09 2017 +0530
+++ b/source/CMakeLists.txt Mon Nov 13 12:20:50 2017 +0530
@@ -29,7 +29,7 @@
option(STATIC_LINK_CRT "Statically link C runtime for release builds" OFF)
mark_as_advanced(FPROFILE_USE FPROFILE_GENERATE NATIVE_BUILD)
# X265_BUILD must be incremented each time the public API is changed
-set(X265_BUILD 145)
+set(X265_BUILD 146)
configure_file("${PROJECT_SOURCE_DIR}/x265.def.in"
"${PROJECT_BINARY_DIR}/x265.def")
configure_file("${PROJECT_SOURCE_DIR}/x265_config.h.in"
diff -r dd9772385d15 -r 2fec493b990e source/encoder/api.cpp
--- a/source/encoder/api.cpp Tue Nov 14 11:00:09 2017 +0530
+++ b/source/encoder/api.cpp Mon Nov 13 12:20:50 2017 +0530
@@ -365,6 +365,18 @@
return encoder->getRefFrameList((PicYuv**)l0, (PicYuv**)l1, sliceType, poc);
}
+int x265_set_analysis_data(x265_encoder *enc, x265_analysis_data *analysis_data, int poc, uint32_t cuBytes)
+{
+ if (!enc)
+ return -1;
+
+ Encoder *encoder = static_cast<Encoder*>(enc);
+ if (!encoder->setAnalysisData(analysis_data, poc, cuBytes))
+ return 0;
+
+ return -1;
+}
+
void x265_cleanup(void)
{
BitCost::destroy();
@@ -444,6 +456,7 @@
&x265_csvlog_frame,
&x265_csvlog_encode,
&x265_dither_image,
+ &x265_set_analysis_data
};
typedef const x265_api* (*api_get_func)(int bitDepth);
diff -r dd9772385d15 -r 2fec493b990e source/encoder/encoder.cpp
--- a/source/encoder/encoder.cpp Tue Nov 14 11:00:09 2017 +0530
+++ b/source/encoder/encoder.cpp Mon Nov 13 12:20:50 2017 +0530
@@ -574,6 +574,88 @@
return 0;
}
+int Encoder::setAnalysisData(x265_analysis_data *analysis_data, int poc, uint32_t cuBytes)
+{
+ uint32_t widthInCU = (m_param->sourceWidth + m_param->maxCUSize - 1) >> m_param->maxLog2CUSize;
+ uint32_t heightInCU = (m_param->sourceHeight + m_param->maxCUSize - 1) >> m_param->maxLog2CUSize;
+
+ Frame* curFrame = m_dpb->m_picList.getPOC(poc);
+ if (curFrame != NULL)
+ {
+ curFrame->m_analysisData = (*analysis_data);
+ curFrame->m_analysisData.numCUsInFrame = widthInCU * heightInCU;
+ curFrame->m_analysisData.numPartitions = m_param->num4x4Partitions;
+ allocAnalysis(&curFrame->m_analysisData);
+ if (m_param->maxCUSize == 16)
+ {
+ if (analysis_data->sliceType == X265_TYPE_IDR || analysis_data->sliceType == X265_TYPE_I)
+ {
+ curFrame->m_analysisData.sliceType = X265_TYPE_I;
+ if (m_param->analysisReuseLevel < 2)
+ return -1;
+
+ curFrame->m_analysisData.numPartitions = m_param->num4x4Partitions;
+ size_t count = 0;
+ analysis_intra_data * currIntraData = (analysis_intra_data *)curFrame->m_analysisData.intraData;
+ analysis_intra_data * intraData = (analysis_intra_data *)analysis_data->intraData;
+ for (uint32_t d = 0; d < cuBytes; d++)
+ {
+ int bytes = curFrame->m_analysisData.numPartitions >> ((intraData)->depth[d] * 2);
+ memset(&(currIntraData)->depth[count], (intraData)->depth[d], bytes);
+ memset(&(currIntraData)->chromaModes[count], (intraData)->chromaModes[d], bytes);
+ memset(&(currIntraData)->partSizes[count], (intraData)->partSizes[d], bytes);
+ memset(&(currIntraData)->partSizes[count], (intraData)->partSizes[d], bytes);
+ count += bytes;
+ }
+ memcpy(&(currIntraData)->modes, (intraData)->modes, curFrame->m_analysisData.numPartitions * analysis_data->numCUsInFrame);
+ }
+ else
+ {
+ uint32_t numDir = analysis_data->sliceType == X265_TYPE_P ? 1 : 2;
+ if (m_param->analysisReuseLevel < 2)
+ return -1;
+
+ curFrame->m_analysisData.numPartitions = m_param->num4x4Partitions;
+ size_t count = 0;
+ analysis_inter_data * currInterData = (analysis_inter_data *)curFrame->m_analysisData.interData;
+ analysis_inter_data * interData = (analysis_inter_data *)analysis_data->interData;
+ for (uint32_t d = 0; d < cuBytes; d++)
+ {
+ int bytes = curFrame->m_analysisData.numPartitions >> ((interData)->depth[d] * 2);
+ memset(&(currInterData)->depth[count], (interData)->depth[d], bytes);
+ memset(&(currInterData)->modes[count], (interData)->modes[d], bytes);
+ if (m_param->analysisReuseLevel > 4)
+ {
+ memset(&(currInterData)->partSize[count], (interData)->partSize[d], bytes);
+ int numPU = nbPartsTable[(currInterData)->partSize[d]];
+ for (int pu = 0; pu < numPU; pu++, d++)
+ {
+ (currInterData)->mergeFlag[count + pu] = (interData)->mergeFlag[d];
+ if (m_param->analysisReuseLevel >= 7)
+ {
+ (currInterData)->interDir[count + pu] = (interData)->interDir[d];
+ for (uint32_t i = 0; i < numDir; i++)
+ {
+ (currInterData)->mvpIdx[i][count + pu] = (interData)->mvpIdx[i][d];
+ (currInterData)->refIdx[i][count + pu] = (interData)->refIdx[i][d];
+ memcpy(&(currInterData)->mv[i][count + pu], &(interData)->mv[i][d], sizeof(MV));
+ }
+ }
+ }
+ }
+ count += bytes;
+ }
+ }
+ }
+ else
+ setAnalysisDataAfterZScan(analysis_data, curFrame);
+
+ curFrame->m_copyMVType.trigger();
+ return 0;
+ }
+ return -1;
+}
+
void Encoder::destroy()
{
#if ENABLE_HDR10_PLUS
diff -r dd9772385d15 -r 2fec493b990e source/encoder/encoder.h
--- a/source/encoder/encoder.h Tue Nov 14 11:00:09 2017 +0530
+++ b/source/encoder/encoder.h Mon Nov 13 12:20:50 2017 +0530
@@ -212,6 +212,8 @@
int setAnalysisDataAfterZScan(x265_analysis_data *analysis_data, Frame* curFrame);
+ int setAnalysisData(x265_analysis_data *analysis_data, int poc, uint32_t cuBytes);
+
void getStreamHeaders(NALList& list, Entropy& sbacCoder, Bitstream& bs);
void fetchStats(x265_stats* stats, size_t statsSizeBytes);
diff -r dd9772385d15 -r 2fec493b990e source/x265.def.in
--- a/source/x265.def.in Tue Nov 14 11:00:09 2017 +0530
+++ b/source/x265.def.in Mon Nov 13 12:20:50 2017 +0530
@@ -30,3 +30,4 @@
x265_csvlog_frame
x265_csvlog_encode
x265_dither_image
+x265_set_analysis_data
diff -r dd9772385d15 -r 2fec493b990e source/x265.h
--- a/source/x265.h Tue Nov 14 11:00:09 2017 +0530
+++ b/source/x265.h Mon Nov 13 12:20:50 2017 +0530
@@ -1746,6 +1746,11 @@
* This API must be called after(poc >= lookaheadDepth + bframes + 2) condition check */
int x265_get_ref_frame_list(x265_encoder *encoder, x265_picyuv**, x265_picyuv**, int, int);
+/* x265_set_analysis_data:
+ * set the analysis data,
+ * returns negative on error, 0 access unit were output. */
+int x265_set_analysis_data(x265_encoder *encoder, x265_analysis_data *analysis_data, int poc, uint32_t cuBytes);
+
void x265_cleanup(void);
/* Open a CSV log file. On success it returns a file handle which must be passed
@@ -1819,6 +1824,7 @@
void (*csvlog_frame)(const x265_param*, const x265_picture*);
void (*csvlog_encode)(x265_encoder*, const x265_stats*, int, char**);
void (*dither_image)(x265_picture*, int, int, int16_t*, int);
+ int (*set_analysis_data)(x265_encoder *encoder, x265_analysis_data *analysis_data, int poc, uint32_t cuBytes);
/* add new pointers to the end, or increment X265_MAJOR_VERSION */
} x265_api;
More information about the x265-devel
mailing list