[libav-devel] [libav-commits] r3d: do not create the audio stream until we know the sample rate

Martin Storsjö martin at martin.st
Sun Dec 13 22:45:02 CET 2015


On Sat, 12 Dec 2015, Anton Khirnov  wrote:

> Module: libav
> Branch: master
> Commit: 6bf4c1d71199b92894f24db6386ed5070e590a16
>
> Author:    Anton Khirnov <anton at khirnov.net>
> Committer: Anton Khirnov <anton at khirnov.net>
> Date:      Wed Oct 21 11:22:13 2015 +0200
>
> r3d: do not create the audio stream until we know the sample rate
>
> ---
>
> libavformat/r3d.c |   37 +++++++++++++++++++++++++------------
> 1 file changed, 25 insertions(+), 12 deletions(-)

This broke fate-redcode-demux on a number of configurations

> diff --git a/libavformat/r3d.c b/libavformat/r3d.c
> index c56bdc6..fb066a6 100644
> --- a/libavformat/r3d.c
> +++ b/libavformat/r3d.c
> @@ -29,6 +29,8 @@ typedef struct R3DContext {
>     unsigned video_offsets_count;
>     unsigned *video_offsets;
>     unsigned rdvo_offset;
> +
> +    int audio_channels;
> } R3DContext;
>
> typedef struct Atom {
> @@ -52,6 +54,7 @@ static int read_atom(AVFormatContext *s, Atom *atom)
> static int r3d_read_red1(AVFormatContext *s)
> {
>     AVStream *st = avformat_new_stream(s, NULL);
> +    R3DContext *r3d = s->priv_data;
>     char filename[258];
>     int tmp;
>     int av_unused tmp2;
> @@ -89,17 +92,8 @@ static int r3d_read_red1(AVFormatContext *s)
>         st->avg_frame_rate = framerate;
>     }
>
> -    tmp = avio_r8(s->pb); // audio channels
> +    r3d->audio_channels = avio_r8(s->pb); // audio channels
>     av_log(s, AV_LOG_TRACE, "audio channels %d\n", tmp);
> -    if (tmp > 0) {
> -        AVStream *ast = avformat_new_stream(s, NULL);
> -        if (!ast)
> -            return AVERROR(ENOMEM);
> -        ast->codec->codec_type = AVMEDIA_TYPE_AUDIO;
> -        ast->codec->codec_id = AV_CODEC_ID_PCM_S32BE;
> -        ast->codec->channels = tmp;
> -        avpriv_set_pts_info(ast, 32, 1, st->time_base.den);
> -    }
>
>     avio_read(s->pb, filename, 257);
>     filename[sizeof(filename)-1] = 0;
> @@ -183,6 +177,11 @@ static int r3d_read_header(AVFormatContext *s)
>         return -1;
>     }
>
> +    /* we cannot create the audio stream now because we do not know the
> +     * sample rate */
> +    if (r3d->audio_channels)
> +        s->ctx_flags |= AVFMTCTX_NOHEADER;
> +
>     s->internal->data_offset = avio_tell(s->pb);
>     av_log(s, AV_LOG_TRACE, "data offset %#"PRIx64"\n", s->internal->data_offset);
>     if (!s->pb->seekable)
> @@ -271,13 +270,26 @@ static int r3d_read_redv(AVFormatContext *s, AVPacket *pkt, Atom *atom)
>
> static int r3d_read_reda(AVFormatContext *s, AVPacket *pkt, Atom *atom)
> {
> -    AVStream *st = s->streams[1];
> +    R3DContext *r3d = s->priv_data;
> +    AVStream *st;
>     int av_unused tmp, tmp2;
>     int samples, size;
>     int64_t pos = avio_tell(s->pb);
>     unsigned dts;
>     int ret;
>
> +    if (s->nb_streams < 2) {
> +        st = avformat_new_stream(s, NULL);
> +        if (!st)
> +            return AVERROR(ENOMEM);
> +        st->codec->codec_type = AVMEDIA_TYPE_AUDIO;
> +        st->codec->codec_id = AV_CODEC_ID_PCM_S32BE;
> +        st->codec->channels = r3d->audio_channels;
> +        avpriv_set_pts_info(st, 32, 1, s->streams[0]->time_base.den);
> +    } else {
> +        st = s->streams[1];
> +    }
> +
>     dts = avio_rb32(s->pb);
>
>     st->codec->sample_rate = avio_rb32(s->pb);
> @@ -321,6 +333,7 @@ static int r3d_read_reda(AVFormatContext *s, AVPacket *pkt, Atom *atom)
>
> static int r3d_read_packet(AVFormatContext *s, AVPacket *pkt)
> {
> +    R3DContext *r3d = s->priv_data;
>     Atom atom;
>     int err = 0;
>
> @@ -337,7 +350,7 @@ static int r3d_read_packet(AVFormatContext *s, AVPacket *pkt)
>                 return 0;
>             break;
>         case MKTAG('R','E','D','A'):
> -            if (s->nb_streams < 2)
> +            if (!r3d->audio_channels)
>                 return -1;
>             if (s->streams[1]->discard == AVDISCARD_ALL)
>                 goto skip;

In fate-redcode-demux, this dereferences s->streams[1] even if 
s->nb_streams == 1.

// Martin


More information about the libav-devel mailing list