[x265] [PATCH Alpha 03/10] Add compile time conditions to enable Alpha Encode

Anusuya Kumarasamy anusuya.kumarasamy at multicorewareinc.com
Mon Aug 5 10:54:38 UTC 2024


>From b6c961f9f9fa7a6a24c955798485591102581c0a Mon Sep 17 00:00:00 2001
From: Kirithika <kirithika at multicorewareinc.com>
Date: Tue, 2 Jul 2024 14:57:16 +0530
Subject: [PATCH] Add compile time conditions to enable Alpha Encode

---
 source/CMakeLists.txt      |  5 +++
 source/abrEncApp.cpp       |  4 +-
 source/common/param.cpp    |  8 ++++
 source/common/picyuv.cpp   | 90 ++++++++++++++++++++++++++++----------
 source/encoder/encoder.cpp |  2 +
 source/input/y4m.cpp       |  2 +
 source/input/yuv.cpp       |  2 +
 source/x265.h              |  4 ++
 source/x265cli.cpp         |  2 +
 source/x265cli.h           |  2 +
 10 files changed, 96 insertions(+), 25 deletions(-)

diff --git a/source/CMakeLists.txt b/source/CMakeLists.txt
index 9a215cbbf..2dcac3dc6 100755
--- a/source/CMakeLists.txt
+++ b/source/CMakeLists.txt
@@ -595,6 +595,11 @@ if(DETAILED_CU_STATS)
     add_definitions(-DDETAILED_CU_STATS)
 endif(DETAILED_CU_STATS)

+option(ENABLE_ALPHA "Enable alpha encoding in x265" OFF)
+if(ENABLE_ALPHA)
+    add_definitions(-DENABLE_ALPHA)
+endif()
+
 add_subdirectory(encoder)
 add_subdirectory(common)

diff --git a/source/abrEncApp.cpp b/source/abrEncApp.cpp
index d8b9f8e3b..96c854de6 100644
--- a/source/abrEncApp.cpp
+++ b/source/abrEncApp.cpp
@@ -1098,12 +1098,12 @@ ret:
                 memcpy(dest->planes[0], src->planes[0], src->framesize *
sizeof(char));
                 dest->planes[1] = (char*)dest->planes[0] + src->stride[0]
* src->height;
                 dest->planes[2] = (char*)dest->planes[1] + src->stride[1]
* (src->height >> x265_cli_csps[src->colorSpace].height[1]);
-
+#if ENABLE_ALPHA
                 if (m_parentEnc->m_param->bEnableAlpha)
                 {
                     dest->planes[3] = (char*)dest->planes[2] +
src->stride[2] * (src->height >> x265_cli_csps[src->colorSpace].height[2]);
                 }
-
+#endif
                 m_parentEnc->m_parent->m_picWriteCnt[m_id].incr();
             }
             else
diff --git a/source/common/param.cpp b/source/common/param.cpp
index e05e79eaf..01267b278 100755
--- a/source/common/param.cpp
+++ b/source/common/param.cpp
@@ -1448,6 +1448,7 @@ int x265_param_parse(x265_param* p, const char* name,
const char* value)
         OPT("film-grain") p->filmGrain = (char* )value;
         OPT("mcstf") p->bEnableTemporalFilter = atobool(value);
         OPT("sbrc") p->bEnableSBRC = atobool(value);
+#if ENABLE_ALPHA
         OPT("alpha")
         {
             if (atobool(value))
@@ -1456,6 +1457,7 @@ int x265_param_parse(x265_param* p, const char* name,
const char* value)
                 p->numScalableLayers = 2;
             }
         }
+#endif
         else
             return X265_PARAM_BAD_NAME;
     }
@@ -2091,7 +2093,9 @@ void x265_print_params(x265_param* param)
     TOOLOPT(param->rc.bStatWrite, "stats-write");
     TOOLOPT(param->rc.bStatRead,  "stats-read");
     TOOLOPT(param->bSingleSeiNal, "single-sei");
+#if ENABLE_ALPHA
     TOOLOPT(param->numScalableLayers > 1, "alpha");
+#endif
 #if ENABLE_HDR10_PLUS
     TOOLOPT(param->toneMapFile != NULL, "dhdr10-info");
 #endif
@@ -2356,7 +2360,9 @@ char *x265_param2string(x265_param* p, int padx, int
pady)
     if (p->filmGrain)
         s += sprintf(s, " film-grain=%s", p->filmGrain); // Film grain
characteristics model filename
     BOOL(p->bEnableTemporalFilter, "mcstf");
+#if ENABLE_ALPHA
     BOOL(p->bEnableAlpha, "alpha");
+#endif
     BOOL(p->bEnableSBRC, "sbrc");
 #undef BOOL
     return buf;
@@ -2878,8 +2884,10 @@ void x265_copy_params(x265_param* dst, x265_param*
src)
     dst->confWinRightOffset = src->confWinRightOffset;
     dst->confWinBottomOffset = src->confWinBottomOffset;
     dst->bliveVBV2pass = src->bliveVBV2pass;
+#if ENABLE_ALPHA
     dst->bEnableAlpha = src->bEnableAlpha;
     dst->numScalableLayers = src->numScalableLayers;
+#endif

     if (src->videoSignalTypePreset) dst->videoSignalTypePreset =
strdup(src->videoSignalTypePreset);
     else dst->videoSignalTypePreset = NULL;
diff --git a/source/common/picyuv.cpp b/source/common/picyuv.cpp
index 8e0b44455..bd5690d3e 100644
--- a/source/common/picyuv.cpp
+++ b/source/common/picyuv.cpp
@@ -354,6 +354,7 @@ void PicYuv::copyFromPicture(const x265_picture& pic,
const x265_param& param, i
                     }
                 }
             }
+#if ENABLE_ALPHA
             if (!isBase && param.bEnableAlpha)
             {
                 pixel* aPixel = m_picOrg[0];
@@ -379,48 +380,91 @@ void PicYuv::copyFromPicture(const x265_picture& pic,
const x265_param& param, i
                     vPixel += m_strideC;
                 }
             }
+#endif
         }
 #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];
+            if (isBase)
+            {
+                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];
+                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 (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)
+                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);
+                    }
+                }
+            }
+#if ENABLE_ALPHA
+            if (!isBase && param.bEnableAlpha)
             {
-                pixel *uPixel = m_picOrg[1];
-                pixel *vPixel = m_picOrg[2];
+                /* 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 *uShort = (uint16_t*)pic.planes[1];
-                uint16_t *vShort = (uint16_t*)pic.planes[2];
+                uint16_t* yShort = (uint16_t*)pic.planes[3];

                 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];
+
+                    for (int r = 0; r < height >> m_vChromaShift; r++)
+                    {
+                        for (int c = 0; c < (width >> m_hChromaShift); c++)
+                        {
+                            uPixel[c] = ((1 << X265_DEPTH) >> 1);
+                            vPixel[c] = ((1 << X265_DEPTH) >> 1);
+                        }
+                        uPixel += m_strideC;
+                        vPixel += m_strideC;
+                    }
                 }
             }
+#endif
         }
     }
     else
diff --git a/source/encoder/encoder.cpp b/source/encoder/encoder.cpp
index dc09be6dc..ef6c5f64a 100644
--- a/source/encoder/encoder.cpp
+++ b/source/encoder/encoder.cpp
@@ -1359,8 +1359,10 @@ void Encoder::copyPicture(x265_picture *dest, const
x265_picture *src)
     memcpy(dest->planes[0], src->planes[0], src->framesize * sizeof(char));
     dest->planes[1] = (char*)dest->planes[0] + src->stride[0] *
src->height;
     dest->planes[2] = (char*)dest->planes[1] + src->stride[1] *
(src->height >> x265_cli_csps[src->colorSpace].height[1]);
+#if ENABLE_ALPHA
     if(m_param->bEnableAlpha)
         dest->planes[3] = (char*)dest->planes[2] + src->stride[2] *
(src->height >> x265_cli_csps[src->colorSpace].height[2]);
+#endif
 }

 bool Encoder::isFilterThisframe(uint8_t sliceTypeConfig, int curSliceType)
diff --git a/source/input/y4m.cpp b/source/input/y4m.cpp
index eedbf991c..0fe0cc43e 100644
--- a/source/input/y4m.cpp
+++ b/source/input/y4m.cpp
@@ -397,11 +397,13 @@ bool Y4MInput::readPicture(x265_picture& pic)
         pic.planes[0] = buf[read % QUEUE_SIZE];
         pic.planes[1] = (char*)pic.planes[0] + pic.stride[0] * height;
         pic.planes[2] = (char*)pic.planes[1] + pic.stride[1] * (height >>
x265_cli_csps[colorSpace].height[1]);
+#if ENABLE_ALPHA
         if (alphaAvailable)
         {
             pic.stride[3] = pic.stride[0] >>
x265_cli_csps[colorSpace].width[3];
             pic.planes[3] = (char*)pic.planes[2] + pic.stride[2] * (height
>> x265_cli_csps[colorSpace].height[2]);
         }
+#endif
         readCount.incr();
         return true;
     }
diff --git a/source/input/yuv.cpp b/source/input/yuv.cpp
index 670dae1ab..878075ec8 100644
--- a/source/input/yuv.cpp
+++ b/source/input/yuv.cpp
@@ -212,11 +212,13 @@ bool YUVInput::readPicture(x265_picture& pic)
         pic.planes[0] = buf[read % QUEUE_SIZE];
         pic.planes[1] = (char*)pic.planes[0] + pic.stride[0] * height;
         pic.planes[2] = (char*)pic.planes[1] + pic.stride[1] * (height >>
x265_cli_csps[colorSpace].height[1]);
+#if ENABLE_ALPHA
         if (alphaAvailable)
         {
             pic.stride[3] = pic.stride[0] >>
x265_cli_csps[colorSpace].width[3];
             pic.planes[3] = (char*)pic.planes[2] + pic.stride[2] * (height
>> x265_cli_csps[colorSpace].height[2]);
         }
+#endif
         readCount.incr();
         return true;
     }
diff --git a/source/x265.h b/source/x265.h
index 48ec30bc7..e994ea3e2 100644
--- a/source/x265.h
+++ b/source/x265.h
@@ -623,7 +623,11 @@ typedef enum
 #define X265_MAX_GOP_LENGTH 16
 #define MAX_T_LAYERS 7

+#if ENABLE_ALPHA
 #define MAX_SCALABLE_LAYERS     2
+#else
+#define MAX_SCALABLE_LAYERS     1
+#endif

 #define X265_IPRATIO_STRENGTH   1.43

diff --git a/source/x265cli.cpp b/source/x265cli.cpp
index ce7af9533..070011cf0 100755
--- a/source/x265cli.cpp
+++ b/source/x265cli.cpp
@@ -374,7 +374,9 @@ namespace X265_NS {
         H0("   --[no-]frame-dup              Enable Frame duplication.
Default %s\n", OPT(param->bEnableFrameDuplication));
         H0("   --dup-threshold <integer>     PSNR threshold for Frame
duplication. Default %d\n", param->dupThreshold);
         H0("   --[no-]mcstf                  Enable GOP based temporal
filter. Default %d\n", param->bEnableTemporalFilter);
+#if ENABLE_ALPHA
         H0("   --alpha                       Enable alpha channel support.
Default %d\n", param->bEnableAlpha);
+#endif
 #ifdef SVT_HEVC
         H0("   --[no]svt                     Enable SVT HEVC encoder
%s\n", OPT(param->bEnableSvtHevc));
         H0("   --[no-]svt-hme                Enable Hierarchial motion
estimation(HME) in SVT HEVC encoder \n");
diff --git a/source/x265cli.h b/source/x265cli.h
index b4e91a137..9bdaba0f3 100644
--- a/source/x265cli.h
+++ b/source/x265cli.h
@@ -358,7 +358,9 @@ static const struct option long_options[] =
     { "dup-threshold", required_argument, NULL, 0 },
     { "mcstf",                 no_argument, NULL, 0 },
     { "no-mcstf",              no_argument, NULL, 0 },
+#if ENABLE_ALPHA
     { "alpha",                 no_argument, NULL, 0 },
+#endif
 #ifdef SVT_HEVC
     { "svt",     no_argument, NULL, 0 },
     { "no-svt",  no_argument, NULL, 0 },
-- 
2.36.0.windows.1
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://mailman.videolan.org/pipermail/x265-devel/attachments/20240805/3531cc33/attachment-0001.htm>
-------------- next part --------------
A non-text attachment was scrubbed...
Name: 0003-Add-compile-time-conditions-to-enable-Alpha-Encode.patch
Type: application/octet-stream
Size: 14595 bytes
Desc: not available
URL: <http://mailman.videolan.org/pipermail/x265-devel/attachments/20240805/3531cc33/attachment-0001.obj>


More information about the x265-devel mailing list