[x265-commits] [x265] Add CLI option to enable or disable picture copy to inter...
Kavitha Sampath
kavitha at multicorewareinc.com
Thu Nov 16 01:03:03 CET 2017
details: http://hg.videolan.org/x265/rev/dd9772385d15
branches:
changeset: 11917:dd9772385d15
user: Kavitha Sampath <kavitha at multicorewareinc.com>
date: Tue Nov 14 11:00:09 2017 +0530
description:
Add CLI option to enable or disable picture copy to internal frame buffer
diffstat:
doc/reST/cli.rst | 12 ++++++
source/CMakeLists.txt | 2 +-
source/common/frame.cpp | 5 +-
source/common/param.cpp | 3 +
source/common/picyuv.cpp | 96 +++++++++++++++++++++++++++--------------------
source/common/picyuv.h | 2 +-
source/x265.h | 3 +
source/x265cli.h | 3 +
8 files changed, 81 insertions(+), 45 deletions(-)
diffs (281 lines):
diff -r 6ac1b12bcde9 -r dd9772385d15 doc/reST/cli.rst
--- a/doc/reST/cli.rst Fri Nov 10 19:02:48 2017 +0530
+++ b/doc/reST/cli.rst Tue Nov 14 11:00:09 2017 +0530
@@ -399,6 +399,18 @@ Performance Options
Default: 1 slice per frame. **Experimental feature**
+.. option:: --copy-pic, --no-copy-pic
+
+ Allow encoder to copy input x265 pictures to internal frame buffers. When disabled,
+ x265 will not make an internal copy of the input picture and will work with the
+ application's buffers. While this allows for deeper integration, it is the responsbility
+ of the application to (a) ensure that the allocated picture has extra space for padding
+ that will be done by the library, and (b) the buffers aren't recycled until the library
+ has completed encoding this frame (which can be figured out by tracking NALs output by x265)
+
+ Default: enabled
+
+
Input/Output File Options
=========================
diff -r 6ac1b12bcde9 -r dd9772385d15 source/CMakeLists.txt
--- a/source/CMakeLists.txt Fri Nov 10 19:02:48 2017 +0530
+++ b/source/CMakeLists.txt Tue Nov 14 11:00:09 2017 +0530
@@ -29,7 +29,7 @@ option(NATIVE_BUILD "Target the build CP
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 144)
+set(X265_BUILD 145)
configure_file("${PROJECT_SOURCE_DIR}/x265.def.in"
"${PROJECT_BINARY_DIR}/x265.def")
configure_file("${PROJECT_SOURCE_DIR}/x265_config.h.in"
diff -r 6ac1b12bcde9 -r dd9772385d15 source/common/frame.cpp
--- a/source/common/frame.cpp Fri Nov 10 19:02:48 2017 +0530
+++ b/source/common/frame.cpp Tue Nov 14 11:00:09 2017 +0530
@@ -85,7 +85,7 @@ bool Frame::create(x265_param *param, fl
m_analysis2Pass.analysisFramedata = NULL;
}
- if (m_fencPic->create(param) && m_lowres.create(m_fencPic, param->bframes, !!param->rc.aqMode || !!param->bAQMotion, param->rc.qgSize))
+ if (m_fencPic->create(param, !!m_param->bCopyPicToFrame) && m_lowres.create(m_fencPic, param->bframes, !!param->rc.aqMode || !!param->bAQMotion, param->rc.qgSize))
{
X265_CHECK((m_reconColCount == NULL), "m_reconColCount was initialized");
m_numRows = (m_fencPic->m_picHeight + param->maxCUSize - 1) / param->maxCUSize;
@@ -158,7 +158,8 @@ void Frame::destroy()
if (m_fencPic)
{
- m_fencPic->destroy();
+ if (m_param->bCopyPicToFrame)
+ m_fencPic->destroy();
delete m_fencPic;
m_fencPic = NULL;
}
diff -r 6ac1b12bcde9 -r dd9772385d15 source/common/param.cpp
--- a/source/common/param.cpp Fri Nov 10 19:02:48 2017 +0530
+++ b/source/common/param.cpp Tue Nov 14 11:00:09 2017 +0530
@@ -290,6 +290,7 @@ void x265_param_default(x265_param* para
param->csvfpt = NULL;
param->forceFlush = 0;
param->bDisableLookahead = 0;
+ param->bCopyPicToFrame = 1;
/* DCT Approximations */
param->bLowPassDct = 0;
@@ -987,6 +988,7 @@ int x265_param_parse(x265_param* p, cons
OPT("lowpass-dct") p->bLowPassDct = atobool(value);
OPT("vbv-end") p->vbvBufferEnd = atof(value);
OPT("vbv-end-fr-adj") p->vbvEndFrameAdjust = atof(value);
+ OPT("copy-pic") p->bCopyPicToFrame = atobool(value);
OPT("refine-mv-type")
{
if (strcmp(strdup(value), "avc") == 0)
@@ -1718,6 +1720,7 @@ char *x265_param2string(x265_param* p, i
s += sprintf(s, " ctu-info=%d", p->bCTUInfo);
BOOL(p->bLowPassDct, "lowpass-dct");
s += sprintf(s, " refine-mv-type=%d", p->bMVType);
+ s += sprintf(s, " copy-pic=%d", p->bCopyPicToFrame);
#undef BOOL
return buf;
}
diff -r 6ac1b12bcde9 -r dd9772385d15 source/common/picyuv.cpp
--- a/source/common/picyuv.cpp Fri Nov 10 19:02:48 2017 +0530
+++ b/source/common/picyuv.cpp Tue Nov 14 11:00:09 2017 +0530
@@ -69,7 +69,7 @@ PicYuv::PicYuv()
m_vChromaShift = 0;
}
-bool PicYuv::create(x265_param* param, pixel *pixelbuf)
+bool PicYuv::create(x265_param* param, bool picAlloc, pixel *pixelbuf)
{
m_param = param;
uint32_t picWidth = m_param->sourceWidth;
@@ -93,8 +93,11 @@ bool PicYuv::create(x265_param* param, p
m_picOrg[0] = pixelbuf;
else
{
- CHECKED_MALLOC(m_picBuf[0], pixel, m_stride * (maxHeight + (m_lumaMarginY * 2)));
- m_picOrg[0] = m_picBuf[0] + m_lumaMarginY * m_stride + m_lumaMarginX;
+ if (picAlloc)
+ {
+ CHECKED_MALLOC(m_picBuf[0], pixel, m_stride * (maxHeight + (m_lumaMarginY * 2)));
+ m_picOrg[0] = m_picBuf[0] + m_lumaMarginY * m_stride + m_lumaMarginX;
+ }
}
if (picCsp != X265_CSP_I400)
@@ -102,12 +105,14 @@ bool PicYuv::create(x265_param* param, p
m_chromaMarginX = m_lumaMarginX; // keep 16-byte alignment for chroma CTUs
m_chromaMarginY = m_lumaMarginY >> m_vChromaShift;
m_strideC = ((numCuInWidth * m_param->maxCUSize) >> m_hChromaShift) + (m_chromaMarginX * 2);
+ if (picAlloc)
+ {
+ CHECKED_MALLOC(m_picBuf[1], pixel, m_strideC * ((maxHeight >> m_vChromaShift) + (m_chromaMarginY * 2)));
+ CHECKED_MALLOC(m_picBuf[2], pixel, m_strideC * ((maxHeight >> m_vChromaShift) + (m_chromaMarginY * 2)));
- CHECKED_MALLOC(m_picBuf[1], pixel, m_strideC * ((maxHeight >> m_vChromaShift) + (m_chromaMarginY * 2)));
- CHECKED_MALLOC(m_picBuf[2], 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;
+ 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
{
@@ -236,8 +241,10 @@ void PicYuv::copyFromPicture(const x265_
uint64_t crSum;
lumaSum = cbSum = crSum = 0;
- if (pic.bitDepth == 8)
+ if (m_param->bCopyPicToFrame)
{
+ if (pic.bitDepth == 8)
+ {
#if (X265_DEPTH > 8)
{
pixel *yPixel = m_picOrg[0];
@@ -260,7 +267,7 @@ void PicYuv::copyFromPicture(const x265_
}
}
#else /* Case for (X265_DEPTH == 8) */
- // TODO: Does we need this path? may merge into above in future
+ // TODO: Does we need this path? may merge into above in future
{
pixel *yPixel = m_picOrg[0];
uint8_t *yChar = (uint8_t*)pic.planes[0];
@@ -294,47 +301,54 @@ void PicYuv::copyFromPicture(const x265_
}
}
#endif /* (X265_DEPTH > 8) */
- }
- else /* pic.bitDepth > 8 */
- {
- /* defensive programming, mask off bits that are supposed to be zero */
- uint16_t mask = (1 << X265_DEPTH) - 1;
- int shift = abs(pic.bitDepth - X265_DEPTH);
- pixel *yPixel = m_picOrg[0];
+ }
+ else /* pic.bitDepth > 8 */
+ {
+ /* defensive programming, mask off bits that are supposed to be zero */
+ uint16_t mask = (1 << X265_DEPTH) - 1;
+ int shift = abs(pic.bitDepth - X265_DEPTH);
+ pixel *yPixel = m_picOrg[0];
- uint16_t *yShort = (uint16_t*)pic.planes[0];
-
- if (pic.bitDepth > X265_DEPTH)
- {
- /* shift right and mask pixels to final size */
- primitives.planecopy_sp(yShort, pic.stride[0] / sizeof(*yShort), yPixel, m_stride, width, height, shift, mask);
- }
- else /* Case for (pic.bitDepth <= X265_DEPTH) */
- {
- /* shift left and mask pixels to final size */
- primitives.planecopy_sp_shl(yShort, pic.stride[0] / sizeof(*yShort), yPixel, m_stride, width, height, shift, mask);
- }
-
- if (param.internalCsp != X265_CSP_I400)
- {
- pixel *uPixel = m_picOrg[1];
- pixel *vPixel = m_picOrg[2];
-
- uint16_t *uShort = (uint16_t*)pic.planes[1];
- uint16_t *vShort = (uint16_t*)pic.planes[2];
+ uint16_t *yShort = (uint16_t*)pic.planes[0];
if (pic.bitDepth > X265_DEPTH)
{
- primitives.planecopy_sp(uShort, pic.stride[1] / sizeof(*uShort), uPixel, m_strideC, width >> m_hChromaShift, height >> m_vChromaShift, shift, mask);
- primitives.planecopy_sp(vShort, pic.stride[2] / sizeof(*vShort), vPixel, m_strideC, width >> m_hChromaShift, height >> m_vChromaShift, shift, mask);
+ /* shift right and mask pixels to final size */
+ primitives.planecopy_sp(yShort, pic.stride[0] / sizeof(*yShort), yPixel, m_stride, width, height, shift, mask);
}
else /* Case for (pic.bitDepth <= X265_DEPTH) */
{
- primitives.planecopy_sp_shl(uShort, pic.stride[1] / sizeof(*uShort), uPixel, m_strideC, width >> m_hChromaShift, height >> m_vChromaShift, shift, mask);
- primitives.planecopy_sp_shl(vShort, pic.stride[2] / sizeof(*vShort), vPixel, m_strideC, width >> m_hChromaShift, height >> m_vChromaShift, shift, mask);
+ /* shift left and mask pixels to final size */
+ primitives.planecopy_sp_shl(yShort, pic.stride[0] / sizeof(*yShort), yPixel, m_stride, width, height, shift, mask);
+ }
+
+ if (param.internalCsp != X265_CSP_I400)
+ {
+ pixel *uPixel = m_picOrg[1];
+ pixel *vPixel = m_picOrg[2];
+
+ uint16_t *uShort = (uint16_t*)pic.planes[1];
+ uint16_t *vShort = (uint16_t*)pic.planes[2];
+
+ if (pic.bitDepth > X265_DEPTH)
+ {
+ primitives.planecopy_sp(uShort, pic.stride[1] / sizeof(*uShort), uPixel, m_strideC, width >> m_hChromaShift, height >> m_vChromaShift, shift, mask);
+ primitives.planecopy_sp(vShort, pic.stride[2] / sizeof(*vShort), vPixel, m_strideC, width >> m_hChromaShift, height >> m_vChromaShift, shift, mask);
+ }
+ else /* Case for (pic.bitDepth <= X265_DEPTH) */
+ {
+ primitives.planecopy_sp_shl(uShort, pic.stride[1] / sizeof(*uShort), uPixel, m_strideC, width >> m_hChromaShift, height >> m_vChromaShift, shift, mask);
+ primitives.planecopy_sp_shl(vShort, pic.stride[2] / sizeof(*vShort), vPixel, m_strideC, width >> m_hChromaShift, height >> m_vChromaShift, shift, mask);
+ }
}
}
}
+ else
+ {
+ m_picOrg[0] = (pixel*)pic.planes[0];
+ m_picOrg[1] = (pixel*)pic.planes[1];
+ m_picOrg[2] = (pixel*)pic.planes[2];
+ }
pixel *Y = m_picOrg[0];
pixel *U = m_picOrg[1];
diff -r 6ac1b12bcde9 -r dd9772385d15 source/common/picyuv.h
--- a/source/common/picyuv.h Fri Nov 10 19:02:48 2017 +0530
+++ b/source/common/picyuv.h Tue Nov 14 11:00:09 2017 +0530
@@ -76,7 +76,7 @@ public:
PicYuv();
- bool create(x265_param* param, pixel *pixelbuf = NULL);
+ bool create(x265_param* param, bool picAlloc = true, pixel *pixelbuf = NULL);
bool createOffsets(const SPS& sps);
void destroy();
int getLumaBufLen(uint32_t picWidth, uint32_t picHeight, uint32_t picCsp);
diff -r 6ac1b12bcde9 -r dd9772385d15 source/x265.h
--- a/source/x265.h Fri Nov 10 19:02:48 2017 +0530
+++ b/source/x265.h Tue Nov 14 11:00:09 2017 +0530
@@ -1531,6 +1531,9 @@ typedef struct x265_param
/* Reuse MV information obtained through API */
int bMVType;
+
+ /* Allow the encoder to have a copy of the planes of x265_picture in Frame */
+ int bCopyPicToFrame;
} x265_param;
/* x265_param_alloc:
diff -r 6ac1b12bcde9 -r dd9772385d15 source/x265cli.h
--- a/source/x265cli.h Fri Nov 10 19:02:48 2017 +0530
+++ b/source/x265cli.h Tue Nov 14 11:00:09 2017 +0530
@@ -286,6 +286,8 @@ static const struct option long_options[
{ "no-splitrd-skip", no_argument, NULL, 0 },
{ "lowpass-dct", no_argument, NULL, 0 },
{ "refine-mv-type", required_argument, NULL, 0 },
+ { "copy-pic", no_argument, NULL, 0 },
+ { "no-copy-pic", no_argument, NULL, 0 },
{ 0, 0, 0, 0 },
{ 0, 0, 0, 0 },
{ 0, 0, 0, 0 },
@@ -339,6 +341,7 @@ static void showHelp(x265_param *param)
H0(" --seek <integer> First frame to encode\n");
H1(" --[no-]interlace <bff|tff> Indicate input pictures are interlace fields in temporal order. Default progressive\n");
H1(" --dither Enable dither if downscaling to 8 bit pixels. Default disabled\n");
+ H0(" --[no-]copy-pic Copy buffers of input picture in frame. Default %s\n", OPT(param->bCopyPicToFrame));
H0("\nQuality reporting metrics:\n");
H0(" --[no-]ssim Enable reporting SSIM metric scores. Default %s\n", OPT(param->bEnableSsim));
H0(" --[no-]psnr Enable reporting PSNR metric scores. Default %s\n", OPT(param->bEnablePsnr));
More information about the x265-commits
mailing list