PR #20910 opened by Zhao Zhili (quink)
URL: https://code.ffmpeg.org/FFmpeg/FFmpeg/pulls/20910
Patch URL: https://code.ffmpeg.org/FFmpeg/FFmpeg/pulls/20910.patch


>From cc85c6566eb2fb93a71aa4eadc318f14a0a44710 Mon Sep 17 00:00:00 2001
From: Zhao Zhili <[email protected]>
Date: Thu, 13 Nov 2025 17:53:29 +0800
Subject: [PATCH 1/2] libavutil/frame: add aspect ratio dependent property

Mark AV_FRAME_DATA_SPHERICAL as aspect ratio dependent instead of
size dependent. After uniform scaling, the AV_FRAME_DATA_SPHERICAL
side data should be preserved.
---
 doc/APIchanges        | 3 +++
 libavutil/frame.h     | 9 +++++++++
 libavutil/side_data.c | 2 +-
 libavutil/version.h   | 2 +-
 4 files changed, 14 insertions(+), 2 deletions(-)

diff --git a/doc/APIchanges b/doc/APIchanges
index 9d128ae77b..98e693e4b1 100644
--- a/doc/APIchanges
+++ b/doc/APIchanges
@@ -2,6 +2,9 @@ The last version increases of all libraries were on 2025-03-28
 
 API changes, most recent first:
 
+2025-11-13 - xxxxxxxxxx - lavu 60.18.100 - frame.h
+  Add AV_SIDE_DATA_PROP_ASPECT_RATIO_DEPENDENT.
+
 2025-11-01 - xxxxxxxxxx - lavc 62.19.100 - avcodec.h
   Schedule AVCodecParser and av_parser_init() to use enum AVCodecID
   for codec ids on the next major version bump.
diff --git a/libavutil/frame.h b/libavutil/frame.h
index 088b24b717..dd497236c2 100644
--- a/libavutil/frame.h
+++ b/libavutil/frame.h
@@ -321,6 +321,15 @@ enum AVSideDataProps {
      * or adjusted to the new layout.
      */
     AV_SIDE_DATA_PROP_CHANNEL_DEPENDENT = (1 << 4),
+
+    /**
+     * Side data depends on the video aspect ratio. Side data with this 
property
+     * loses its meaning with non-uniform scale.
+     *
+     * @note Cropping also affects side data with this property, even when the
+     *       resulting aspect ratio matches the original input.
+     */
+    AV_SIDE_DATA_PROP_ASPECT_RATIO_DEPENDENT = (1 << 5),
 };
 
 /**
diff --git a/libavutil/side_data.c b/libavutil/side_data.c
index bbbeb70ecd..44e72c75b6 100644
--- a/libavutil/side_data.c
+++ b/libavutil/side_data.c
@@ -51,7 +51,7 @@ static const AVSideDataDescriptor sd_props[] = {
     [AV_FRAME_DATA_MASTERING_DISPLAY_METADATA]  = { "Mastering display 
metadata",                   AV_SIDE_DATA_PROP_GLOBAL | 
AV_SIDE_DATA_PROP_COLOR_DEPENDENT },
     [AV_FRAME_DATA_CONTENT_LIGHT_LEVEL]         = { "Content light level 
metadata",                 AV_SIDE_DATA_PROP_GLOBAL | 
AV_SIDE_DATA_PROP_COLOR_DEPENDENT },
     [AV_FRAME_DATA_AMBIENT_VIEWING_ENVIRONMENT] = { "Ambient viewing 
environment",                  AV_SIDE_DATA_PROP_GLOBAL },
-    [AV_FRAME_DATA_SPHERICAL]                   = { "Spherical Mapping",       
                     AV_SIDE_DATA_PROP_GLOBAL | 
AV_SIDE_DATA_PROP_SIZE_DEPENDENT },
+    [AV_FRAME_DATA_SPHERICAL]                   = { "Spherical Mapping",       
                     AV_SIDE_DATA_PROP_GLOBAL | 
AV_SIDE_DATA_PROP_ASPECT_RATIO_DEPENDENT },
     [AV_FRAME_DATA_ICC_PROFILE]                 = { "ICC profile",             
                     AV_SIDE_DATA_PROP_GLOBAL | 
AV_SIDE_DATA_PROP_COLOR_DEPENDENT },
     [AV_FRAME_DATA_EXIF]                        = { "EXIF metadata",           
                     AV_SIDE_DATA_PROP_GLOBAL },
     [AV_FRAME_DATA_SEI_UNREGISTERED]            = { "H.26[45] User Data 
Unregistered SEI message",  AV_SIDE_DATA_PROP_MULTI },
diff --git a/libavutil/version.h b/libavutil/version.h
index b16b88bfca..9dd8394b83 100644
--- a/libavutil/version.h
+++ b/libavutil/version.h
@@ -79,7 +79,7 @@
  */
 
 #define LIBAVUTIL_VERSION_MAJOR  60
-#define LIBAVUTIL_VERSION_MINOR  17
+#define LIBAVUTIL_VERSION_MINOR  18
 #define LIBAVUTIL_VERSION_MICRO 100
 
 #define LIBAVUTIL_VERSION_INT   AV_VERSION_INT(LIBAVUTIL_VERSION_MAJOR, \
-- 
2.49.1


>From 5fcc5263e7b99a0c9d90378dcd20e58862fbcb5a Mon Sep 17 00:00:00 2001
From: Zhao Zhili <[email protected]>
Date: Thu, 13 Nov 2025 17:59:38 +0800
Subject: [PATCH 2/2] avfilter/vf_scale*: remove ASPECT_RATIO_DEPENDENT side
 data when aspect ratio changed

---
 libavfilter/vf_libplacebo.c   |  5 ++++-
 libavfilter/vf_scale.c        | 12 ++++++++----
 libavfilter/vf_scale_cuda.c   |  5 ++++-
 libavfilter/vf_scale_npp.c    |  5 ++++-
 libavfilter/vf_scale_vaapi.c  |  5 ++++-
 libavfilter/vf_scale_vt.c     |  6 ++++--
 libavfilter/vf_scale_vulkan.c |  5 ++++-
 libavfilter/vf_zscale.c       |  5 ++++-
 8 files changed, 36 insertions(+), 12 deletions(-)

diff --git a/libavfilter/vf_libplacebo.c b/libavfilter/vf_libplacebo.c
index 42501c51f2..2c4f9f4532 100644
--- a/libavfilter/vf_libplacebo.c
+++ b/libavfilter/vf_libplacebo.c
@@ -1031,8 +1031,11 @@ static int output_frame(AVFilterContext *ctx, int64_t 
pts)
         out->color_primaries = s->color_primaries;
 
     /* Strip side data if no longer relevant */
-    if (out->width != ref->width || out->height != ref->height)
+    if (out->width != ref->width || out->height != ref->height) {
         changed |= AV_SIDE_DATA_PROP_SIZE_DEPENDENT;
+        if (ref->width * out->height != out->width * ref->height)
+            changed |= AV_SIDE_DATA_PROP_ASPECT_RATIO_DEPENDENT;
+    }
     if (ref->color_trc != out->color_trc || ref->color_primaries != 
out->color_primaries)
         changed |= AV_SIDE_DATA_PROP_COLOR_DEPENDENT;
     av_frame_side_data_remove_by_props(&out->side_data, &out->nb_side_data, 
changed);
diff --git a/libavfilter/vf_scale.c b/libavfilter/vf_scale.c
index 61d3ee0a0f..6f5f1cd7ac 100644
--- a/libavfilter/vf_scale.c
+++ b/libavfilter/vf_scale.c
@@ -674,8 +674,10 @@ static int config_props(AVFilterLink *outlink)
     av_freep(&flags_val);
 
     if (inlink->w != outlink->w || inlink->h != outlink->h) {
-        av_frame_side_data_remove_by_props(&outlink->side_data, 
&outlink->nb_side_data,
-                                           AV_SIDE_DATA_PROP_SIZE_DEPENDENT);
+        int prop = AV_SIDE_DATA_PROP_SIZE_DEPENDENT;
+        if (inlink->w * outlink->h != outlink->w * inlink->h)
+            prop |= AV_SIDE_DATA_PROP_ASPECT_RATIO_DEPENDENT;
+        av_frame_side_data_remove_by_props(&outlink->side_data, 
&outlink->nb_side_data, prop);
     }
 
     if (scale->in_primaries != scale->out_primaries || scale->in_transfer != 
scale->out_transfer) {
@@ -852,8 +854,10 @@ scale:
         out->color_trc = scale->out_transfer;
 
     if (out->width != in->width || out->height != in->height) {
-        av_frame_side_data_remove_by_props(&out->side_data, &out->nb_side_data,
-                                           AV_SIDE_DATA_PROP_SIZE_DEPENDENT);
+        int prop = AV_SIDE_DATA_PROP_SIZE_DEPENDENT;
+        if (in->width * out->height != out->width * in->height)
+            prop |= AV_SIDE_DATA_PROP_ASPECT_RATIO_DEPENDENT;
+        av_frame_side_data_remove_by_props(&out->side_data, 
&out->nb_side_data, prop);
     }
 
     if (in->color_primaries != out->color_primaries || in->color_trc != 
out->color_trc) {
diff --git a/libavfilter/vf_scale_cuda.c b/libavfilter/vf_scale_cuda.c
index 88a6e20610..115a0ba7e6 100644
--- a/libavfilter/vf_scale_cuda.c
+++ b/libavfilter/vf_scale_cuda.c
@@ -545,8 +545,11 @@ static int cudascale_scale(AVFilterContext *ctx, AVFrame 
*out, AVFrame *in)
         return ret;
 
     if (out->width != in->width || out->height != in->height) {
+        int prop = AV_SIDE_DATA_PROP_SIZE_DEPENDENT;
+        if (in->width * out->height != out->width * in->height)
+            prop |= AV_SIDE_DATA_PROP_ASPECT_RATIO_DEPENDENT;
         av_frame_side_data_remove_by_props(&out->side_data, &out->nb_side_data,
-                                           AV_SIDE_DATA_PROP_SIZE_DEPENDENT);
+                                           prop);
     }
 
     return 0;
diff --git a/libavfilter/vf_scale_npp.c b/libavfilter/vf_scale_npp.c
index 8e9113521c..f5e3069c2d 100644
--- a/libavfilter/vf_scale_npp.c
+++ b/libavfilter/vf_scale_npp.c
@@ -868,8 +868,11 @@ scale:
         return ret;
 
     if (out->width != in->width || out->height != in->height) {
+        int prop = AV_SIDE_DATA_PROP_SIZE_DEPENDENT;
+        if (in->width * out->height != out->width * in->height)
+            prop |= AV_SIDE_DATA_PROP_ASPECT_RATIO_DEPENDENT;
         av_frame_side_data_remove_by_props(&out->side_data, &out->nb_side_data,
-                                           AV_SIDE_DATA_PROP_SIZE_DEPENDENT);
+                                           prop);
     }
 
     return 0;
diff --git a/libavfilter/vf_scale_vaapi.c b/libavfilter/vf_scale_vaapi.c
index 1ba925afa5..951dbfe992 100644
--- a/libavfilter/vf_scale_vaapi.c
+++ b/libavfilter/vf_scale_vaapi.c
@@ -146,9 +146,12 @@ static int scale_vaapi_filter_frame(AVFilterLink *inlink, 
AVFrame *input_frame)
         goto fail;
 
     if (output_frame->width != input_frame->width || output_frame->height != 
input_frame->height) {
+        int prop = AV_SIDE_DATA_PROP_SIZE_DEPENDENT;
+        if (input_frame->width * output_frame->height != output_frame->width * 
input_frame->height)
+            prop |= AV_SIDE_DATA_PROP_ASPECT_RATIO_DEPENDENT;
         av_frame_side_data_remove_by_props(&output_frame->side_data,
                                            &output_frame->nb_side_data,
-                                           AV_SIDE_DATA_PROP_SIZE_DEPENDENT);
+                                           prop);
     }
 
     if (ctx->colour_primaries != AVCOL_PRI_UNSPECIFIED)
diff --git a/libavfilter/vf_scale_vt.c b/libavfilter/vf_scale_vt.c
index 3d4ba44dc6..f0ae2e12aa 100644
--- a/libavfilter/vf_scale_vt.c
+++ b/libavfilter/vf_scale_vt.c
@@ -161,8 +161,10 @@ static int scale_vt_filter_frame(AVFilterLink *link, 
AVFrame *in)
     out->crop_right = 0;
     out->crop_bottom = 0;
     if (out->width != in->width || out->height != in->height) {
-        av_frame_side_data_remove_by_props(&out->side_data, &out->nb_side_data,
-                                           AV_SIDE_DATA_PROP_SIZE_DEPENDENT);
+        int prop = AV_SIDE_DATA_PROP_SIZE_DEPENDENT;
+        if (in->width * out->height != out->width * in->height)
+            prop |= AV_SIDE_DATA_PROP_ASPECT_RATIO_DEPENDENT;
+        av_frame_side_data_remove_by_props(&out->side_data, 
&out->nb_side_data, prop);
     }
 
     av_reduce(&out->sample_aspect_ratio.num, &out->sample_aspect_ratio.den,
diff --git a/libavfilter/vf_scale_vulkan.c b/libavfilter/vf_scale_vulkan.c
index f8e069f4a4..9deeae7cf0 100644
--- a/libavfilter/vf_scale_vulkan.c
+++ b/libavfilter/vf_scale_vulkan.c
@@ -356,8 +356,11 @@ static int scale_vulkan_filter_frame(AVFilterLink *link, 
AVFrame *in)
         goto fail;
 
     if (out->width != in->width || out->height != in->height) {
+        int prop = AV_SIDE_DATA_PROP_SIZE_DEPENDENT;
+        if (in->width * out->height != out->width * in->height)
+            prop |= AV_SIDE_DATA_PROP_ASPECT_RATIO_DEPENDENT;
         av_frame_side_data_remove_by_props(&out->side_data, &out->nb_side_data,
-                                           AV_SIDE_DATA_PROP_SIZE_DEPENDENT);
+                                           prop);
     }
 
     if (s->out_range != AVCOL_RANGE_UNSPECIFIED)
diff --git a/libavfilter/vf_zscale.c b/libavfilter/vf_zscale.c
index 9ea50133c6..c90445328e 100644
--- a/libavfilter/vf_zscale.c
+++ b/libavfilter/vf_zscale.c
@@ -818,8 +818,11 @@ static int filter_frame(AVFilterLink *link, AVFrame *in)
                   (int64_t)in->sample_aspect_ratio.den * outlink->w * link->h,
                   INT_MAX);
 
-        if (out->width != in->width || out->height != in->height)
+        if (out->width != in->width || out->height != in->height) {
             changed |= AV_SIDE_DATA_PROP_SIZE_DEPENDENT;
+            if (in->width * out->height != out->width * in->height)
+                changed |= AV_SIDE_DATA_PROP_ASPECT_RATIO_DEPENDENT;
+        }
         if (out->color_trc != in->color_trc || out->color_primaries != 
in->color_primaries)
             changed |= AV_SIDE_DATA_PROP_COLOR_DEPENDENT;
         av_frame_side_data_remove_by_props(&out->side_data, 
&out->nb_side_data, changed);
-- 
2.49.1

_______________________________________________
ffmpeg-devel mailing list -- [email protected]
To unsubscribe send an email to [email protected]

Reply via email to