}
const MDIA_CHUNK_HANDLERS: &[TrackChunkHandler] = &[
- TrackChunkHandler { ctype: mktag!(b"mdhd"), parse: skip_chunk },
+ TrackChunkHandler { ctype: mktag!(b"mdhd"), parse: read_mdhd },
TrackChunkHandler { ctype: mktag!(b"hdlr"), parse: read_hdlr },
TrackChunkHandler { ctype: mktag!(b"minf"), parse: read_minf },
];
+fn read_mdhd(track: &mut Track, br: &mut ByteReader, size: u64) -> DemuxerResult<u64> {
+ const KNOWN_MDHD_SIZE: u64 = 24;
+ validate!(size >= KNOWN_MDHD_SIZE);
+ let version = br.read_byte()?;
+ validate!(version == 0);
+ let flags = br.read_u24be()?;
+ validate!(flags == 0);
+ let _ctime = br.read_u32be()?;
+ let _mtime = br.read_u32be()?;
+ track.tb_den = br.read_u32be()?;
+ validate!(track.tb_den != 0);
+ track.duration = br.read_u32be()?;
+ let _language = br.read_u16be()?;
+ let _quality = br.read_u16be()?;
+
+ Ok(KNOWN_MDHD_SIZE)
+}
+
fn read_hdlr(track: &mut Track, br: &mut ByteReader, size: u64) -> DemuxerResult<u64> {
const KNOWN_HDLR_SIZE: u64 = 24;
validate!(size >= KNOWN_HDLR_SIZE);
let format = if depth > 8 { RGB24_FORMAT } else { PAL8_FORMAT };
let mut vhdr = NAVideoInfo::new(width, height, false, format);
vhdr.bits = depth as u8;
+ //skip various common atoms
+ while br.tell() - start_pos + 4 < size {
+ let mut buf = [0u8; 8];
+ br.peek_buf(&mut buf)?;
+ let tsize = read_u32be(&buf).unwrap() as usize;
+ let tag = &buf[4..8];
+ validate!(tsize >= 8);
+ match tag {
+ b"pasp" | b"clap" => {
+ br.read_skip(tsize)?;
+ },
+ _ => break,
+ };
+ }
let edata = if br.tell() - start_pos + 4 < size {
-//todo skip various common atoms
let edata_size = br.read_u32be()? as usize;
validate!(edata_size >= 4);
let mut buf = vec![0; edata_size - 4];
if let Some(ref mut stream) = track.stream {
let tb_den = stream.tb_den;
let (tb_num, tb_den) = reduce_timebase(tb_num * stream.tb_num, tb_den);
- stream.duration /= u64::from(stream.tb_den / tb_den);
+ stream.duration /= u64::from(track.tb_div);
stream.tb_num = tb_num;
stream.tb_den = tb_den;
track.tb_num = tb_num;
track.tb_den = tb_den;
+ track.duration /= track.tb_div;
}
} else {
track.time_to_sample.truncate(0);