diff options
author | Tomas Härdin <tomas.hardin@codemill.se> | 2011-12-09 17:17:33 +0100 |
---|---|---|
committer | Michael Niedermayer <michaelni@gmx.at> | 2011-12-12 18:34:37 +0100 |
commit | 8a2cb2abbf3e654837e8b940fe303315298ec59d (patch) | |
tree | f13b4189aba22bcf68f19a8de3a8cbf9c296c633 | |
parent | 0bcada9f61edbcfa749a2c9f84079c42ef2d1a59 (diff) | |
download | ffmpeg-8a2cb2abbf3e654837e8b940fe303315298ec59d.tar.gz |
mxfdec: Only sort IndexTableSegments once
Signed-off-by: Michael Niedermayer <michaelni@gmx.at>
-rw-r--r-- | libavformat/mxfdec.c | 58 |
1 files changed, 28 insertions, 30 deletions
diff --git a/libavformat/mxfdec.c b/libavformat/mxfdec.c index 9e0d4b8475..8ad59a5e1c 100644 --- a/libavformat/mxfdec.c +++ b/libavformat/mxfdec.c @@ -1103,26 +1103,15 @@ static int64_t mxf_essence_container_length(MXFContext *mxf, int body_sid) return ret; } -static int mxf_parse_index(MXFContext *mxf, int track_id, AVStream *st) +static int mxf_parse_index(MXFContext *mxf, int track_id, AVStream *st, MXFIndexTableSegment **sorted_segments, int nb_sorted_segments) { int64_t accumulated_offset = 0; - int j, k, l, ret, nb_sorted_segments; - MXFIndexTableSegment **sorted_segments = NULL; + int j, k, l, ret; int n_delta = track_id - 1; /* TrackID = 1-based stream index */ if (track_id < 1) { av_log(mxf->fc, AV_LOG_ERROR, "TrackID not positive: %i\n", track_id); - ret = AVERROR_INVALIDDATA; - goto err_out; - } - - if ((ret = mxf_get_sorted_table_segments(mxf, &nb_sorted_segments, &sorted_segments))) - goto err_out; - - if (nb_sorted_segments <= 0) { - av_log(mxf->fc, AV_LOG_WARNING, "Empty index for stream %i\n", st->index); - ret = 0; - goto err_out; + return AVERROR_INVALIDDATA; } for (j = 0; j < nb_sorted_segments; j++) { @@ -1160,8 +1149,8 @@ static int mxf_parse_index(MXFContext *mxf, int track_id, AVStream *st) if (duration <= 0) { av_log(mxf->fc, AV_LOG_WARNING, "0 duration in index for stream %i\n", st->index); - ret = 0; - goto err_out; + mxf->broken_index = 1; + return 0; } for (k = l = 0; k < duration; k++, l += index_delta) { @@ -1237,21 +1226,15 @@ static int mxf_parse_index(MXFContext *mxf, int track_id, AVStream *st) accumulated_offset += segment_size; } - av_free(sorted_segments); - return 0; - -err_out: - av_free(sorted_segments); - mxf->broken_index = 1; - return ret; } static int mxf_parse_structural_metadata(MXFContext *mxf) { MXFPackage *material_package = NULL; MXFPackage *temp_package = NULL; - int i, j, k, ret; + int i, j, k, ret, nb_sorted_segments; + MXFIndexTableSegment **sorted_segments = NULL; av_dlog(mxf->fc, "metadata sets count %d\n", mxf->metadata_sets_count); /* TODO: handle multiple material packages (OP3x) */ @@ -1264,6 +1247,12 @@ static int mxf_parse_structural_metadata(MXFContext *mxf) return -1; } + if ((ret = mxf_get_sorted_table_segments(mxf, &nb_sorted_segments, &sorted_segments)) || + nb_sorted_segments <= 0) { + av_log(mxf->fc, AV_LOG_WARNING, "broken or empty index\n"); + mxf->broken_index = 1; + } + for (i = 0; i < material_package->tracks_count; i++) { MXFPackage *source_package = NULL; MXFTrack *material_track = NULL; @@ -1309,7 +1298,8 @@ static int mxf_parse_structural_metadata(MXFContext *mxf) for (k = 0; k < source_package->tracks_count; k++) { if (!(temp_track = mxf_resolve_strong_ref(mxf, &source_package->tracks_refs[k], Track))) { av_log(mxf->fc, AV_LOG_ERROR, "could not resolve source track strong ref\n"); - return -1; + ret = -1; + goto fail_and_free; } if (temp_track->track_id == component->source_track_id) { source_track = temp_track; @@ -1326,7 +1316,8 @@ static int mxf_parse_structural_metadata(MXFContext *mxf) if (!(source_track->sequence = mxf_resolve_strong_ref(mxf, &source_track->sequence_ref, Sequence))) { av_log(mxf->fc, AV_LOG_ERROR, "could not resolve source track sequence strong ref\n"); - return -1; + ret = -1; + goto fail_and_free; } /* 0001GL00.MXF.A1.mxf_opatom.mxf has the same SourcePackageID as 0001GL.MXF.V1.mxf_opatom.mxf @@ -1339,7 +1330,8 @@ static int mxf_parse_structural_metadata(MXFContext *mxf) st = avformat_new_stream(mxf->fc, NULL); if (!st) { av_log(mxf->fc, AV_LOG_ERROR, "could not allocate stream\n"); - return -1; + ret = AVERROR(ENOMEM); + goto fail_and_free; } st->id = source_track->track_id; st->priv_data = source_track; @@ -1438,10 +1430,16 @@ static int mxf_parse_structural_metadata(MXFContext *mxf) st->need_parsing = AVSTREAM_PARSE_TIMESTAMPS; } - if ((ret = mxf_parse_index(mxf, material_track->track_id, st))) - return ret; + if (!mxf->broken_index && + (ret = mxf_parse_index(mxf, material_track->track_id, st, sorted_segments, nb_sorted_segments))) + goto fail_and_free; } - return 0; + + ret = 0; + +fail_and_free: + av_free(sorted_segments); + return ret; } static const MXFMetadataReadTableEntry mxf_metadata_read_table[] = { |