diff options
Diffstat (limited to 'lib/rbcodec/codecs/libm4a/demux.c')
-rw-r--r-- | lib/rbcodec/codecs/libm4a/demux.c | 31 |
1 files changed, 30 insertions, 1 deletions
diff --git a/lib/rbcodec/codecs/libm4a/demux.c b/lib/rbcodec/codecs/libm4a/demux.c index 3bf46efec6..e29ecb8339 100644 --- a/lib/rbcodec/codecs/libm4a/demux.c +++ b/lib/rbcodec/codecs/libm4a/demux.c @@ -349,6 +349,7 @@ static bool read_chunk_stts(qtmovie_t *qtmovie, size_t chunk_len) static bool read_chunk_stsz(qtmovie_t *qtmovie, size_t chunk_len) { size_t size_remaining = chunk_len - 8; + uint32_t numsizes, i; /* version */ stream_read_uint8(qtmovie->stream); @@ -369,9 +370,37 @@ static bool read_chunk_stsz(qtmovie_t *qtmovie, size_t chunk_len) } size_remaining -= 4; - qtmovie->res->num_sample_byte_sizes = stream_read_uint32(qtmovie->stream); + numsizes = stream_read_uint32(qtmovie->stream); size_remaining -= 4; + /* Because this table can be really large and is only used to improve seek + * accuracy, it's optional. In that case the seek code will fall back to a + * less accurate seek method. */ + qtmovie->res->num_sample_byte_sizes = numsizes; + if (numsizes * sizeof(uint32_t) < CODEC_SIZE * 1 / 2) + qtmovie->res->sample_byte_sizes = malloc(numsizes * sizeof(uint32_t)); + else + qtmovie->res->sample_byte_sizes = NULL; + + if (qtmovie->res->sample_byte_sizes) + { + for (i = 0; i < numsizes; ++i) + { + qtmovie->res->sample_byte_sizes[i] = + stream_read_uint32(qtmovie->stream); + size_remaining -= 4; + } + + if (size_remaining) + { + DEBUGF("extra bytes after stsz\n"); + } + } + else + { + DEBUGF("stsz too large, ignoring it\n"); + } + if (size_remaining) { stream_skip(qtmovie->stream, size_remaining); |