freeswitch icon indicating copy to clipboard operation
freeswitch copied to clipboard

mod_av: avformat.c lines 458-459 reference private field within AVOutputFormat

Open Korynkai opened this issue 1 year ago • 5 comments

The following code is apparently referencing a private field within the AVOutputFormat structure of libavformat, which is described as "[not] part of the public API", "may not be used outside of libavformat" and "can be changed and removed at will":

https://github.com/signalwire/freeswitch/blob/b74245d48a1f65a05e853f24e973f9b9ff35f8f5/src/mod/applications/mod_av/avformat.c#L458 https://github.com/signalwire/freeswitch/blob/b74245d48a1f65a05e853f24e973f9b9ff35f8f5/src/mod/applications/mod_av/avformat.c#L459

As described here: https://github.com/FFmpeg/FFmpeg/blob/566aa38d98f5f492995127e82ab9a516f59bf952/libavformat/avformat.h#L540

typedef struct AVOutputFormat {

...continued...

    /*****************************************************************
     * No fields below this line are part of the public API. They
     * may not be used outside of libavformat and can be changed and
     * removed at will.
     * New public fields should be added right above.
     *****************************************************************
     */
    /**
     * size of private data so that it can be allocated in the wrapper
     */
    int priv_data_size;

...continued...

} AVOutputFormat;

mod_av, as-is, causes the following error when building against FFmpeg 6.0, as this field has apparently been removed from FFmpeg 6.0:

avformat.c: In function 'mod_avformat_alloc_output_context2':
avformat.c:458:23: error: 'const struct AVOutputFormat' has no member named 'priv_data_size'
  458 |         if (s->oformat->priv_data_size > 0) {
      |                       ^~
avformat.c:459:53: error: 'const struct AVOutputFormat' has no member named 'priv_data_size'
  459 |                 s->priv_data = av_mallocz(s->oformat->priv_data_size);
      |                                                     ^~
make[4]: *** [Makefile:1026: libavmod_la-avformat.lo] Error 1

With the following patch, everything seems to build correctly:

diff -Naur freeswitch-1.10.10.pristine/src/mod/applications/mod_av/avformat.c freeswitch-1.10.10/src/mod/applications/mod_av/avformat.c
--- freeswitch-1.10.10.pristine/src/mod/applications/mod_av/avformat.c  2023-08-14 17:45:02.529331160 +0000
+++ freeswitch-1.10.10/src/mod/applications/mod_av/avformat.c   2023-08-14 23:52:55.012169884 +0000
@@ -455,8 +455,10 @@
        }
 
        s->oformat = oformat;
+#if (LIBAVFORMAT_VERSION_MAJOR < LIBAVFORMAT_N)
        if (s->oformat->priv_data_size > 0) {
                s->priv_data = av_mallocz(s->oformat->priv_data_size);
+
                if (!s->priv_data) {
                        goto nomem;
                }
@@ -468,6 +470,7 @@
        } else {
                s->priv_data = NULL;
        }
+#endif
 
        if (filename) {
 #if (LIBAVCODEC_VERSION_INT < AV_VERSION_INT(58,7,100))
diff -Naur freeswitch-1.10.10.pristine/src/mod/applications/mod_av/mod_av.h freeswitch-1.10.10/src/mod/applications/mod_av/mod_av.h
--- freeswitch-1.10.10.pristine/src/mod/applications/mod_av/mod_av.h    2023-08-14 17:45:02.529331160 +0000
+++ freeswitch-1.10.10/src/mod/applications/mod_av/mod_av.h     2023-08-14 19:40:21.271938704 +0000
@@ -42,6 +42,7 @@
 
 #define LIBAVCODEC_V 59
 #define LIBAVFORMAT_V 59
+#define LIBAVFORMAT_N 60
 #define LIBAVUTIL_V 57
 
 struct mod_av_globals {

What is the purpose of referencing the priv_data_size field within the AVOutputFormat structure, and can this be averted? Can this specific conditional block be safely removed by package maintainers such as myself, as in the above patch, or will it cause some form of runtime issues or undefined behavior? I have attempted to examine this code and have not quite determined the purpose it serves.. It seems as if it is allocating the number of bytes its value indicates to the priv_data field of the allocated AVFormatContext object and then the priv_data pointer is assigned to the priv_class object within the AVOutputFormat structure, then av_opt_set_defaults() is called on the priv_data pointer if the priv_class object exists...

Can someone help me determine the purpose of this and assist in developing a patch and/or pull request that would fix this?

Korynkai avatar Aug 15 '23 01:08 Korynkai

We did video testing/recording and had no issues with this patch for now.

fx02 avatar Nov 21 '23 19:11 fx02

With FreeSWITCH v1.10.11, this patch does not solve the whole problem, compiling mod_av also throws the following errors (because warnings are treated as errors while compiling FreeSWITCH):

making all mod_av
make[4]: Entering directory '/usr/local/src/freeswitch/src/mod/applications/mod_av'
  CC       libavmod_la-mod_av.lo
  CC       libavmod_la-avformat.lo
avformat.c: In function 'add_stream':
avformat.c:626:25: error: 'ticks_per_frame' is deprecated [-Werror=deprecated-declarations]
  626 |                         c->ticks_per_frame = 2;
      |                         ^
In file included from avformat.c:37:
/usr/include/x86_64-linux-gnu/libavcodec/avcodec.h:579:9: note: declared here
  579 |     int ticks_per_frame;
      |         ^~~~~~~~~~~~~~~
avformat.c: In function 'av_file_read_video':
avformat.c:3208:17: error: 'ticks_per_frame' is deprecated [-Werror=deprecated-declarations]
 3208 |                 ticks = cp ? cp->repeat_pict + 1 : c->ticks_per_frame;
      |                 ^~~~~
/usr/include/x86_64-linux-gnu/libavcodec/avcodec.h:579:9: note: declared here
  579 |     int ticks_per_frame;
      |         ^~~~~~~~~~~~~~~
avformat.c:3214:25: error: 'ticks_per_frame' is deprecated [-Werror=deprecated-declarations]
 3214 |                         context->video_start_time, ticks, c ? c->ticks_per_frame : -1, st->time_base.num, st->time_base.den, c ? c->time_base.num : -1, c ? c->time_base.den : -1,
      |                         ^~~~~~~
/usr/include/x86_64-linux-gnu/libavcodec/avcodec.h:579:9: note: declared here
  579 |     int ticks_per_frame;
      |         ^~~~~~~~~~~~~~~
cc1: all warnings being treated as errors

tynli avatar Apr 11 '24 16:04 tynli

yes I got same error while installing freeswitch

make[4]: Entering directory '/usr/src/freeswitch/src/mod/applications/mod_av'
  CC       test/test_mod_av-test_mod_av.o
  CC       libavmod_la-mod_av.lo
  CC       libavmod_la-avformat.lo
avformat.c: In function 'mod_avformat_alloc_output_context2':
avformat.c:458:23: error: 'const struct AVOutputFormat' has no member named 'priv_data_size'
  458 |         if (s->oformat->priv_data_size > 0) {
      |                       ^~
avformat.c:459:53: error: 'const struct AVOutputFormat' has no member named 'priv_data_size'
  459 |                 s->priv_data = av_mallocz(s->oformat->priv_data_size);
      |                                                     ^~
avformat.c: In function 'add_stream':
avformat.c:624:25: error: 'ticks_per_frame' is deprecated [-Werror=deprecated-declarations]
  624 |                         c->ticks_per_frame = 2;
      |                         ^
In file included from avformat.c:37:
/usr/include/x86_64-linux-gnu/libavcodec/avcodec.h:579:9: note: declared here
  579 |     int ticks_per_frame;
      |         ^~~~~~~~~~~~~~~
avformat.c: In function 'av_file_read_video':
avformat.c:3206:17: error: 'ticks_per_frame' is deprecated [-Werror=deprecated-declarations]
 3206 |                 ticks = cp ? cp->repeat_pict + 1 : c->ticks_per_frame;
      |                 ^~~~~
/usr/include/x86_64-linux-gnu/libavcodec/avcodec.h:579:9: note: declared here
  579 |     int ticks_per_frame;
      |         ^~~~~~~~~~~~~~~
avformat.c:3212:25: error: 'ticks_per_frame' is deprecated [-Werror=deprecated-declarations]
 3212 |                         context->video_start_time, ticks, c ? c->ticks_per_frame : -1, st->time_base.num, st->time_base.den, c ? c->time_base.num : -1, c ? c->time_base.den : -1,
      |                         ^~~~~~~
/usr/include/x86_64-linux-gnu/libavcodec/avcodec.h:579:9: note: declared here
  579 |     int ticks_per_frame;
      |         ^~~~~~~~~~~~~~~
cc1: all warnings being treated as errors

fvthakor avatar May 05 '24 11:05 fvthakor

how can i get around this error? would I configure to compile against an earlier version of ffmpeg? how would i do that?

codemonkey76 avatar May 13 '24 00:05 codemonkey76

At the moment, you would need an earlier version of ffmpeg

Len-PGH avatar May 13 '24 13:05 Len-PGH