15d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)// Copyright 2014 The Chromium Authors. All rights reserved.
25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be
35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// found in the LICENSE file.
45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
55d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "media/formats/mp4/box_definitions.h"
65821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
75821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/logging.h"
85d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "media/formats/mp4/es_descriptor.h"
95d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "media/formats/mp4/rcheck.h"
105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace media {
125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace mp4 {
135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FileType::FileType() {}
155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FileType::~FileType() {}
165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC FileType::BoxType() const { return FOURCC_FTYP; }
175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool FileType::Parse(BoxReader* reader) {
195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->ReadFourCC(&major_brand) && reader->Read4(&minor_version));
205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  size_t num_brands = (reader->size() - reader->pos()) / sizeof(FourCC);
215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return reader->SkipBytes(sizeof(FourCC) * num_brands);  // compatible_brands
225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)ProtectionSystemSpecificHeader::ProtectionSystemSpecificHeader() {}
255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)ProtectionSystemSpecificHeader::~ProtectionSystemSpecificHeader() {}
265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC ProtectionSystemSpecificHeader::BoxType() const { return FOURCC_PSSH; }
275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool ProtectionSystemSpecificHeader::Parse(BoxReader* reader) {
295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Validate the box's contents and hang on to the system ID.
305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  uint32 size;
315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->ReadFullBoxHeader() &&
325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->ReadVec(&system_id, 16) &&
335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->Read4(&size) &&
345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->HasBytes(size));
355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Copy the entire box, including the header, for passing to EME as initData.
375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DCHECK(raw_box.empty());
385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  raw_box.assign(reader->data(), reader->data() + reader->size());
395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return true;
405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)SampleAuxiliaryInformationOffset::SampleAuxiliaryInformationOffset() {}
435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)SampleAuxiliaryInformationOffset::~SampleAuxiliaryInformationOffset() {}
445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC SampleAuxiliaryInformationOffset::BoxType() const { return FOURCC_SAIO; }
455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool SampleAuxiliaryInformationOffset::Parse(BoxReader* reader) {
475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->ReadFullBoxHeader());
485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (reader->flags() & 1)
495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    RCHECK(reader->SkipBytes(8));
505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  uint32 count;
525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->Read4(&count) &&
535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->HasBytes(count * (reader->version() == 1 ? 8 : 4)));
545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  offsets.resize(count);
555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  for (uint32 i = 0; i < count; i++) {
575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (reader->version() == 1) {
585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      RCHECK(reader->Read8(&offsets[i]));
595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    } else {
605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      RCHECK(reader->Read4Into8(&offsets[i]));
615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return true;
645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)SampleAuxiliaryInformationSize::SampleAuxiliaryInformationSize()
675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  : default_sample_info_size(0), sample_count(0) {
685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)SampleAuxiliaryInformationSize::~SampleAuxiliaryInformationSize() {}
705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC SampleAuxiliaryInformationSize::BoxType() const { return FOURCC_SAIZ; }
715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool SampleAuxiliaryInformationSize::Parse(BoxReader* reader) {
735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->ReadFullBoxHeader());
745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (reader->flags() & 1)
755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    RCHECK(reader->SkipBytes(8));
765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->Read1(&default_sample_info_size) &&
785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->Read4(&sample_count));
795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (default_sample_info_size == 0)
805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return reader->ReadVec(&sample_info_sizes, sample_count);
815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return true;
825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)OriginalFormat::OriginalFormat() : format(FOURCC_NULL) {}
855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)OriginalFormat::~OriginalFormat() {}
865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC OriginalFormat::BoxType() const { return FOURCC_FRMA; }
875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool OriginalFormat::Parse(BoxReader* reader) {
895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return reader->ReadFourCC(&format);
905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)SchemeType::SchemeType() : type(FOURCC_NULL), version(0) {}
935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)SchemeType::~SchemeType() {}
945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC SchemeType::BoxType() const { return FOURCC_SCHM; }
955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool SchemeType::Parse(BoxReader* reader) {
975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->ReadFullBoxHeader() &&
985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->ReadFourCC(&type) &&
995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->Read4(&version));
1005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return true;
1015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TrackEncryption::TrackEncryption()
1045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  : is_encrypted(false), default_iv_size(0) {
1055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TrackEncryption::~TrackEncryption() {}
1075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC TrackEncryption::BoxType() const { return FOURCC_TENC; }
1085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool TrackEncryption::Parse(BoxReader* reader) {
1105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  uint8 flag;
1115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->ReadFullBoxHeader() &&
1125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->SkipBytes(2) &&
1135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->Read1(&flag) &&
1145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->Read1(&default_iv_size) &&
1155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->ReadVec(&default_kid, 16));
1165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  is_encrypted = (flag != 0);
1175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (is_encrypted) {
1185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    RCHECK(default_iv_size == 8 || default_iv_size == 16);
1195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
1205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    RCHECK(default_iv_size == 0);
1215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
1225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return true;
1235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)SchemeInfo::SchemeInfo() {}
1265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)SchemeInfo::~SchemeInfo() {}
1275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC SchemeInfo::BoxType() const { return FOURCC_SCHI; }
1285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool SchemeInfo::Parse(BoxReader* reader) {
1305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return reader->ScanChildren() && reader->ReadChild(&track_encryption);
1315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)ProtectionSchemeInfo::ProtectionSchemeInfo() {}
1345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)ProtectionSchemeInfo::~ProtectionSchemeInfo() {}
1355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC ProtectionSchemeInfo::BoxType() const { return FOURCC_SINF; }
1365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool ProtectionSchemeInfo::Parse(BoxReader* reader) {
1385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->ScanChildren() &&
1395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->ReadChild(&format) &&
1405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->ReadChild(&type));
1415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (type.type == FOURCC_CENC)
1425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    RCHECK(reader->ReadChild(&info));
1435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Other protection schemes are silently ignored. Since the protection scheme
1445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // type can't be determined until this box is opened, we return 'true' for
1455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // non-CENC protection scheme types. It is the parent box's responsibility to
1465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // ensure that this scheme type is a supported one.
1475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return true;
1485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)MovieHeader::MovieHeader()
1515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    : creation_time(0),
1525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      modification_time(0),
1535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      timescale(0),
1545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      duration(0),
1555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      rate(-1),
1565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      volume(-1),
1575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      next_track_id(0) {}
1585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)MovieHeader::~MovieHeader() {}
1595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC MovieHeader::BoxType() const { return FOURCC_MVHD; }
1605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool MovieHeader::Parse(BoxReader* reader) {
1625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->ReadFullBoxHeader());
1635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (reader->version() == 1) {
1655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    RCHECK(reader->Read8(&creation_time) &&
1665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)           reader->Read8(&modification_time) &&
1675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)           reader->Read4(&timescale) &&
1685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)           reader->Read8(&duration));
1695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
1705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    RCHECK(reader->Read4Into8(&creation_time) &&
1715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)           reader->Read4Into8(&modification_time) &&
1725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)           reader->Read4(&timescale) &&
1735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)           reader->Read4Into8(&duration));
1745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
1755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->Read4s(&rate) &&
1775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->Read2s(&volume) &&
1785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->SkipBytes(10) &&  // reserved
1795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->SkipBytes(36) &&  // matrix
1805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->SkipBytes(24) &&  // predefined zero
1815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->Read4(&next_track_id));
1825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return true;
1835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TrackHeader::TrackHeader()
1865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    : creation_time(0),
1875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      modification_time(0),
1885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      track_id(0),
1895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      duration(0),
1905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      layer(-1),
1915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      alternate_group(-1),
1925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      volume(-1),
1935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      width(0),
1945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      height(0) {}
1955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TrackHeader::~TrackHeader() {}
1965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC TrackHeader::BoxType() const { return FOURCC_TKHD; }
1975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool TrackHeader::Parse(BoxReader* reader) {
1995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->ReadFullBoxHeader());
2005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (reader->version() == 1) {
2015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    RCHECK(reader->Read8(&creation_time) &&
2025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)           reader->Read8(&modification_time) &&
2035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)           reader->Read4(&track_id) &&
2045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)           reader->SkipBytes(4) &&    // reserved
2055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)           reader->Read8(&duration));
2065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
2075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    RCHECK(reader->Read4Into8(&creation_time) &&
2085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)           reader->Read4Into8(&modification_time) &&
2095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)           reader->Read4(&track_id) &&
2105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)           reader->SkipBytes(4) &&   // reserved
2115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)           reader->Read4Into8(&duration));
2125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
2135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->SkipBytes(8) &&  // reserved
2155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->Read2s(&layer) &&
2165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->Read2s(&alternate_group) &&
2175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->Read2s(&volume) &&
2185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->SkipBytes(2) &&  // reserved
2195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->SkipBytes(36) &&  // matrix
2205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->Read4(&width) &&
2215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->Read4(&height));
2225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  width >>= 16;
2235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  height >>= 16;
2245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return true;
2255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
2265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)SampleDescription::SampleDescription() : type(kInvalid) {}
2285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)SampleDescription::~SampleDescription() {}
2295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC SampleDescription::BoxType() const { return FOURCC_STSD; }
2305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool SampleDescription::Parse(BoxReader* reader) {
2325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  uint32 count;
2335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->SkipBytes(4) &&
2345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->Read4(&count));
2355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  video_entries.clear();
2365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  audio_entries.clear();
2375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Note: this value is preset before scanning begins. See comments in the
2395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Parse(Media*) function.
2405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (type == kVideo) {
2415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    RCHECK(reader->ReadAllChildren(&video_entries));
2425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else if (type == kAudio) {
2435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    RCHECK(reader->ReadAllChildren(&audio_entries));
2445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
2455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return true;
2465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
2475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2485d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)SyncSample::SyncSample() : is_present(false) {}
2495d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)SyncSample::~SyncSample() {}
2505d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)FourCC SyncSample::BoxType() const { return FOURCC_STSS; }
2515d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)
2525d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)bool SyncSample::Parse(BoxReader* reader) {
2535d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  uint32 entry_count;
2545d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  RCHECK(reader->ReadFullBoxHeader() &&
2555d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)         reader->Read4(&entry_count));
2565d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)
2575d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  is_present = true;
2585d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)
259cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)  entries.resize(entry_count);
260cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)
2615d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  if (entry_count == 0)
2625d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    return true;
2635d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)
264cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)  for (size_t i = 0; i < entry_count; ++i)
265cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)    RCHECK(reader->Read4(&entries[i]));
266cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)
267cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)  return true;
268cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)}
269cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)
270cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)bool SyncSample::IsSyncSample(size_t k) const {
271cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)  // ISO/IEC 14496-12 Section 8.6.2.1 : If the sync sample box is not present,
272cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)  // every sample is a sync sample.
273cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)  if (!is_present)
274cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)    return true;
275cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)
276cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)  // ISO/IEC 14496-12  Section 8.6.2.3 : If entry_count is zero, there are no
277cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)  // sync samples within the stream.
278cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)  if (entries.size() == 0u)
2795d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    return false;
2805d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)
281cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)  for (size_t i = 0; i < entries.size(); ++i) {
282cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)    if (entries[i] == k)
283cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)      return true;
284cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)  }
2855d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)
286cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)  return false;
2875d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)}
2885d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)
2895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)SampleTable::SampleTable() {}
2905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)SampleTable::~SampleTable() {}
2915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC SampleTable::BoxType() const { return FOURCC_STBL; }
2925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool SampleTable::Parse(BoxReader* reader) {
2945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return reader->ScanChildren() &&
2955d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      reader->ReadChild(&description) &&
2965d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      reader->MaybeReadChild(&sync_sample);
2975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
2985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)EditList::EditList() {}
3005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)EditList::~EditList() {}
3015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC EditList::BoxType() const { return FOURCC_ELST; }
3025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool EditList::Parse(BoxReader* reader) {
3045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  uint32 count;
3055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->ReadFullBoxHeader() && reader->Read4(&count));
3065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (reader->version() == 1) {
3085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    RCHECK(reader->HasBytes(count * 20));
3095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
3105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    RCHECK(reader->HasBytes(count * 12));
3115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
3125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  edits.resize(count);
3135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  for (std::vector<EditListEntry>::iterator edit = edits.begin();
3155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)       edit != edits.end(); ++edit) {
3165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (reader->version() == 1) {
3175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      RCHECK(reader->Read8(&edit->segment_duration) &&
3185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)             reader->Read8s(&edit->media_time));
3195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    } else {
3205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      RCHECK(reader->Read4Into8(&edit->segment_duration) &&
3215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)             reader->Read4sInto8s(&edit->media_time));
3225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
3235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    RCHECK(reader->Read2s(&edit->media_rate_integer) &&
3245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)           reader->Read2s(&edit->media_rate_fraction));
3255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
3265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return true;
3275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
3285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)Edit::Edit() {}
3305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)Edit::~Edit() {}
3315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC Edit::BoxType() const { return FOURCC_EDTS; }
3325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool Edit::Parse(BoxReader* reader) {
3345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return reader->ScanChildren() && reader->ReadChild(&list);
3355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
3365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)HandlerReference::HandlerReference() : type(kInvalid) {}
3385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)HandlerReference::~HandlerReference() {}
3395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC HandlerReference::BoxType() const { return FOURCC_HDLR; }
3405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool HandlerReference::Parse(BoxReader* reader) {
3425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  FourCC hdlr_type;
3435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->SkipBytes(8) && reader->ReadFourCC(&hdlr_type));
3445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Note: remaining fields in box ignored
3455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (hdlr_type == FOURCC_VIDE) {
3465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    type = kVideo;
3475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else if (hdlr_type == FOURCC_SOUN) {
3485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    type = kAudio;
3495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
3505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    type = kInvalid;
3515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
3525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return true;
3535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
3545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)AVCDecoderConfigurationRecord::AVCDecoderConfigurationRecord()
3565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    : version(0),
3575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      profile_indication(0),
3585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      profile_compatibility(0),
3595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      avc_level(0),
3605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      length_size(0) {}
3615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)AVCDecoderConfigurationRecord::~AVCDecoderConfigurationRecord() {}
3635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC AVCDecoderConfigurationRecord::BoxType() const { return FOURCC_AVCC; }
3645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool AVCDecoderConfigurationRecord::Parse(BoxReader* reader) {
366010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  return ParseInternal(reader, reader->log_cb());
367010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)}
368010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
369010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)bool AVCDecoderConfigurationRecord::Parse(const uint8* data, int data_size) {
370010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  BufferReader reader(data, data_size);
371010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  return ParseInternal(&reader, LogCB());
372010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)}
373010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
374010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)bool AVCDecoderConfigurationRecord::ParseInternal(BufferReader* reader,
375010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)                                                  const LogCB& log_cb) {
3765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->Read1(&version) && version == 1 &&
3775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->Read1(&profile_indication) &&
3785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->Read1(&profile_compatibility) &&
3795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->Read1(&avc_level));
3805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  uint8 length_size_minus_one;
3825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)  RCHECK(reader->Read1(&length_size_minus_one));
3835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  length_size = (length_size_minus_one & 0x3) + 1;
3845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
385010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  RCHECK(length_size != 3); // Only values of 1, 2, and 4 are valid.
386010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
3875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  uint8 num_sps;
3885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)  RCHECK(reader->Read1(&num_sps));
3895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  num_sps &= 0x1f;
3905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  sps_list.resize(num_sps);
3925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  for (int i = 0; i < num_sps; i++) {
3935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    uint16 sps_length;
3945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    RCHECK(reader->Read2(&sps_length) &&
3955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)           reader->ReadVec(&sps_list[i], sps_length));
396010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    RCHECK(sps_list[i].size() > 4);
397010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
398010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    if (!log_cb.is_null()) {
399010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      MEDIA_LOG(log_cb) << "Video codec: avc1." << std::hex
400010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)                        << static_cast<int>(sps_list[i][1])
401010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)                        << static_cast<int>(sps_list[i][2])
402010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)                        << static_cast<int>(sps_list[i][3]);
403010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    }
4045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
4055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  uint8 num_pps;
4075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->Read1(&num_pps));
4085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  pps_list.resize(num_pps);
4105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  for (int i = 0; i < num_pps; i++) {
4115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    uint16 pps_length;
4125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    RCHECK(reader->Read2(&pps_length) &&
4135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)           reader->ReadVec(&pps_list[i], pps_length));
4145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
4155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return true;
4175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
4185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)PixelAspectRatioBox::PixelAspectRatioBox() : h_spacing(1), v_spacing(1) {}
4205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)PixelAspectRatioBox::~PixelAspectRatioBox() {}
4215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC PixelAspectRatioBox::BoxType() const { return FOURCC_PASP; }
4225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool PixelAspectRatioBox::Parse(BoxReader* reader) {
4245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->Read4(&h_spacing) &&
4255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->Read4(&v_spacing));
4265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return true;
4275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
4285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)VideoSampleEntry::VideoSampleEntry()
4305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    : format(FOURCC_NULL),
4315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      data_reference_index(0),
4325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      width(0),
4335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      height(0) {}
4345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)VideoSampleEntry::~VideoSampleEntry() {}
4365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC VideoSampleEntry::BoxType() const {
4375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DCHECK(false) << "VideoSampleEntry should be parsed according to the "
4385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                << "handler type recovered in its Media ancestor.";
4395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return FOURCC_NULL;
4405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
4415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool VideoSampleEntry::Parse(BoxReader* reader) {
4435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  format = reader->type();
4445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->SkipBytes(6) &&
4455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->Read2(&data_reference_index) &&
4465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->SkipBytes(16) &&
4475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->Read2(&width) &&
4485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->Read2(&height) &&
4495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->SkipBytes(50));
4505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->ScanChildren() &&
4525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->MaybeReadChild(&pixel_aspect));
4535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (format == FOURCC_ENCV) {
4555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // Continue scanning until a recognized protection scheme is found, or until
4565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // we run out of protection schemes.
4575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    while (sinf.type.type != FOURCC_CENC) {
4585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      if (!reader->ReadChild(&sinf))
4595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return false;
4605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
4615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
4625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4638bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  if (IsFormatValid())
4645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    RCHECK(reader->ReadChild(&avcc));
4658bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
4665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return true;
4675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
4685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4698bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)bool VideoSampleEntry::IsFormatValid() const {
4708bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  return format == FOURCC_AVC1 || format == FOURCC_AVC3 ||
4718bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)      (format == FOURCC_ENCV && (sinf.format.format == FOURCC_AVC1 ||
4728bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)                                 sinf.format.format == FOURCC_AVC3));
4738bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)}
4748bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
4755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)ElementaryStreamDescriptor::ElementaryStreamDescriptor()
4765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    : object_type(kForbidden) {}
4775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)ElementaryStreamDescriptor::~ElementaryStreamDescriptor() {}
4795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC ElementaryStreamDescriptor::BoxType() const {
4815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return FOURCC_ESDS;
4825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
4835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool ElementaryStreamDescriptor::Parse(BoxReader* reader) {
4855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::vector<uint8> data;
4865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ESDescriptor es_desc;
4875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->ReadFullBoxHeader());
4895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->ReadVec(&data, reader->size() - reader->pos()));
4905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(es_desc.Parse(data));
4915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  object_type = es_desc.object_type();
4935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
494010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  if (object_type != 0x40) {
495010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    MEDIA_LOG(reader->log_cb()) << "Audio codec: mp4a."
496010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)                                << std::hex << static_cast<int>(object_type);
497010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  }
498010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
499010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  if (es_desc.IsAAC(object_type))
500010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    RCHECK(aac.Parse(es_desc.decoder_specific_info(), reader->log_cb()));
5015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return true;
5035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
5045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)AudioSampleEntry::AudioSampleEntry()
5065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    : format(FOURCC_NULL),
5075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      data_reference_index(0),
5085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      channelcount(0),
5095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      samplesize(0),
5105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      samplerate(0) {}
5115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)AudioSampleEntry::~AudioSampleEntry() {}
5135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC AudioSampleEntry::BoxType() const {
5155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DCHECK(false) << "AudioSampleEntry should be parsed according to the "
5165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                << "handler type recovered in its Media ancestor.";
5175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return FOURCC_NULL;
5185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
5195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool AudioSampleEntry::Parse(BoxReader* reader) {
5215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  format = reader->type();
5225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->SkipBytes(6) &&
5235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->Read2(&data_reference_index) &&
5245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->SkipBytes(8) &&
5255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->Read2(&channelcount) &&
5265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->Read2(&samplesize) &&
5275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->SkipBytes(4) &&
5285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->Read4(&samplerate));
5295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Convert from 16.16 fixed point to integer
5305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  samplerate >>= 16;
5315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->ScanChildren());
5335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (format == FOURCC_ENCA) {
5345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // Continue scanning until a recognized protection scheme is found, or until
5355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // we run out of protection schemes.
5365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    while (sinf.type.type != FOURCC_CENC) {
5375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      if (!reader->ReadChild(&sinf))
5385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return false;
5395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
5405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
5415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
542c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)  // ESDS is not valid in case of EAC3.
543c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)  RCHECK(reader->MaybeReadChild(&esds));
5445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return true;
5455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
5465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)MediaHeader::MediaHeader()
5485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    : creation_time(0),
5495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      modification_time(0),
5505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      timescale(0),
5515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      duration(0) {}
5525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)MediaHeader::~MediaHeader() {}
5535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC MediaHeader::BoxType() const { return FOURCC_MDHD; }
5545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool MediaHeader::Parse(BoxReader* reader) {
5565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->ReadFullBoxHeader());
5575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (reader->version() == 1) {
5595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    RCHECK(reader->Read8(&creation_time) &&
5605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)           reader->Read8(&modification_time) &&
5615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)           reader->Read4(&timescale) &&
5625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)           reader->Read8(&duration));
5635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
5645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    RCHECK(reader->Read4Into8(&creation_time) &&
5655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)           reader->Read4Into8(&modification_time) &&
5665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)           reader->Read4(&timescale) &&
5675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)           reader->Read4Into8(&duration));
5685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
5695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Skip language information
5705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return reader->SkipBytes(4);
5715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
5725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)MediaInformation::MediaInformation() {}
5745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)MediaInformation::~MediaInformation() {}
5755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC MediaInformation::BoxType() const { return FOURCC_MINF; }
5765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool MediaInformation::Parse(BoxReader* reader) {
5785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return reader->ScanChildren() &&
5795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->ReadChild(&sample_table);
5805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
5815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)Media::Media() {}
5835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)Media::~Media() {}
5845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC Media::BoxType() const { return FOURCC_MDIA; }
5855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool Media::Parse(BoxReader* reader) {
5875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->ScanChildren() &&
5885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->ReadChild(&header) &&
5895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->ReadChild(&handler));
5905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Maddeningly, the HandlerReference box specifies how to parse the
5925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // SampleDescription box, making the latter the only box (of those that we
5935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // support) which cannot be parsed correctly on its own (or even with
5945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // information from its strict ancestor tree). We thus copy the handler type
5955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // to the sample description box *before* parsing it to provide this
5965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // information while parsing.
5975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  information.sample_table.description.type = handler.type;
5985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->ReadChild(&information));
5995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return true;
6005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
6015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)Track::Track() {}
6035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)Track::~Track() {}
6045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC Track::BoxType() const { return FOURCC_TRAK; }
6055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool Track::Parse(BoxReader* reader) {
6075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->ScanChildren() &&
6085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->ReadChild(&header) &&
6095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->ReadChild(&media) &&
6105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->MaybeReadChild(&edit));
6115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return true;
6125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
6135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)MovieExtendsHeader::MovieExtendsHeader() : fragment_duration(0) {}
6155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)MovieExtendsHeader::~MovieExtendsHeader() {}
6165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC MovieExtendsHeader::BoxType() const { return FOURCC_MEHD; }
6175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool MovieExtendsHeader::Parse(BoxReader* reader) {
6195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->ReadFullBoxHeader());
6205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (reader->version() == 1) {
6215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    RCHECK(reader->Read8(&fragment_duration));
6225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
6235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    RCHECK(reader->Read4Into8(&fragment_duration));
6245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
6255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return true;
6265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
6275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TrackExtends::TrackExtends()
6295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    : track_id(0),
6305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      default_sample_description_index(0),
6315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      default_sample_duration(0),
6325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      default_sample_size(0),
6335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      default_sample_flags(0) {}
6345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TrackExtends::~TrackExtends() {}
6355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC TrackExtends::BoxType() const { return FOURCC_TREX; }
6365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool TrackExtends::Parse(BoxReader* reader) {
6385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->ReadFullBoxHeader() &&
6395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->Read4(&track_id) &&
6405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->Read4(&default_sample_description_index) &&
6415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->Read4(&default_sample_duration) &&
6425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->Read4(&default_sample_size) &&
6435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->Read4(&default_sample_flags));
6445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return true;
6455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
6465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)MovieExtends::MovieExtends() {}
6485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)MovieExtends::~MovieExtends() {}
6495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC MovieExtends::BoxType() const { return FOURCC_MVEX; }
6505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool MovieExtends::Parse(BoxReader* reader) {
6525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  header.fragment_duration = 0;
6535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return reader->ScanChildren() &&
6545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->MaybeReadChild(&header) &&
6555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->ReadChildren(&tracks);
6565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
6575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)Movie::Movie() : fragmented(false) {}
6595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)Movie::~Movie() {}
6605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC Movie::BoxType() const { return FOURCC_MOOV; }
6615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool Movie::Parse(BoxReader* reader) {
6635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return reader->ScanChildren() &&
6645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->ReadChild(&header) &&
6655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->ReadChildren(&tracks) &&
6665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         // Media Source specific: 'mvex' required
6675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->ReadChild(&extends) &&
6685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->MaybeReadChildren(&pssh);
6695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
6705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TrackFragmentDecodeTime::TrackFragmentDecodeTime() : decode_time(0) {}
6725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TrackFragmentDecodeTime::~TrackFragmentDecodeTime() {}
6735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC TrackFragmentDecodeTime::BoxType() const { return FOURCC_TFDT; }
6745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool TrackFragmentDecodeTime::Parse(BoxReader* reader) {
6765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->ReadFullBoxHeader());
6775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (reader->version() == 1)
6785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return reader->Read8(&decode_time);
6795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  else
6805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return reader->Read4Into8(&decode_time);
6815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
6825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)MovieFragmentHeader::MovieFragmentHeader() : sequence_number(0) {}
6845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)MovieFragmentHeader::~MovieFragmentHeader() {}
6855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC MovieFragmentHeader::BoxType() const { return FOURCC_MFHD; }
6865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool MovieFragmentHeader::Parse(BoxReader* reader) {
6885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return reader->SkipBytes(4) && reader->Read4(&sequence_number);
6895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
6905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TrackFragmentHeader::TrackFragmentHeader()
6925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    : track_id(0),
6935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      sample_description_index(0),
6945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      default_sample_duration(0),
6955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      default_sample_size(0),
6965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      default_sample_flags(0),
6975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      has_default_sample_flags(false) {}
6985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TrackFragmentHeader::~TrackFragmentHeader() {}
7005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC TrackFragmentHeader::BoxType() const { return FOURCC_TFHD; }
7015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool TrackFragmentHeader::Parse(BoxReader* reader) {
7035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->ReadFullBoxHeader() && reader->Read4(&track_id));
7045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Media Source specific: reject tracks that set 'base-data-offset-present'.
7065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Although the Media Source requires that 'default-base-is-moof' (14496-12
7075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Amendment 2) be set, we omit this check as many otherwise-valid files in
7085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // the wild don't set it.
7095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  //
7105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  //  RCHECK((flags & 0x020000) && !(flags & 0x1));
7115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(!(reader->flags() & 0x1));
7125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (reader->flags() & 0x2) {
7145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    RCHECK(reader->Read4(&sample_description_index));
7155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
7165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    sample_description_index = 0;
7175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
7185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (reader->flags() & 0x8) {
7205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    RCHECK(reader->Read4(&default_sample_duration));
7215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
7225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    default_sample_duration = 0;
7235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
7245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (reader->flags() & 0x10) {
7265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    RCHECK(reader->Read4(&default_sample_size));
7275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
7285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    default_sample_size = 0;
7295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
7305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (reader->flags() & 0x20) {
7325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    RCHECK(reader->Read4(&default_sample_flags));
7335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    has_default_sample_flags = true;
7345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
7355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    has_default_sample_flags = false;
7365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
7375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return true;
7395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
7405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TrackFragmentRun::TrackFragmentRun()
7425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    : sample_count(0), data_offset(0) {}
7435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TrackFragmentRun::~TrackFragmentRun() {}
7445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC TrackFragmentRun::BoxType() const { return FOURCC_TRUN; }
7455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool TrackFragmentRun::Parse(BoxReader* reader) {
7475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->ReadFullBoxHeader() &&
7485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->Read4(&sample_count));
7495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const uint32 flags = reader->flags();
7505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool data_offset_present = (flags & 0x1) != 0;
7525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool first_sample_flags_present = (flags & 0x4) != 0;
7535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool sample_duration_present = (flags & 0x100) != 0;
7545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool sample_size_present = (flags & 0x200) != 0;
7555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool sample_flags_present = (flags & 0x400) != 0;
7565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool sample_composition_time_offsets_present = (flags & 0x800) != 0;
7575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (data_offset_present) {
7595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    RCHECK(reader->Read4(&data_offset));
7605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
7615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    data_offset = 0;
7625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
7635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)  uint32 first_sample_flags = 0;
7655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (first_sample_flags_present)
7665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    RCHECK(reader->Read4(&first_sample_flags));
7675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int fields = sample_duration_present + sample_size_present +
7695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      sample_flags_present + sample_composition_time_offsets_present;
7705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->HasBytes(fields * sample_count));
7715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (sample_duration_present)
7735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    sample_durations.resize(sample_count);
7745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (sample_size_present)
7755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    sample_sizes.resize(sample_count);
7765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (sample_flags_present)
7775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    sample_flags.resize(sample_count);
7785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (sample_composition_time_offsets_present)
7795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    sample_composition_time_offsets.resize(sample_count);
7805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  for (uint32 i = 0; i < sample_count; ++i) {
7825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (sample_duration_present)
7835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      RCHECK(reader->Read4(&sample_durations[i]));
7845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (sample_size_present)
7855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      RCHECK(reader->Read4(&sample_sizes[i]));
7865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (sample_flags_present)
7875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      RCHECK(reader->Read4(&sample_flags[i]));
7885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (sample_composition_time_offsets_present)
7895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      RCHECK(reader->Read4s(&sample_composition_time_offsets[i]));
7905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
7915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (first_sample_flags_present) {
7935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (sample_flags.size() == 0) {
7945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      sample_flags.push_back(first_sample_flags);
7955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    } else {
7965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      sample_flags[0] = first_sample_flags;
7975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
7985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
7995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return true;
8005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
8015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
802010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)SampleToGroup::SampleToGroup() : grouping_type(0), grouping_type_parameter(0) {}
803010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)SampleToGroup::~SampleToGroup() {}
804010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)FourCC SampleToGroup::BoxType() const { return FOURCC_SBGP; }
805010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
806010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)bool SampleToGroup::Parse(BoxReader* reader) {
807010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  RCHECK(reader->ReadFullBoxHeader() &&
808010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)         reader->Read4(&grouping_type));
809010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
810010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  if (reader->version() == 1)
811010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    RCHECK(reader->Read4(&grouping_type_parameter));
812010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
813010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  if (grouping_type != FOURCC_SEIG) {
814010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    DLOG(WARNING) << "SampleToGroup box with grouping_type '" << grouping_type
815010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)                  << "' is not supported.";
816010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    return true;
817010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  }
818010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
819010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  uint32 count;
820010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  RCHECK(reader->Read4(&count));
821010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  entries.resize(count);
822010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  for (uint32 i = 0; i < count; ++i) {
823010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    RCHECK(reader->Read4(&entries[i].sample_count) &&
824010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)           reader->Read4(&entries[i].group_description_index));
825010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  }
826010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  return true;
827010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)}
828010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
829010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)CencSampleEncryptionInfoEntry::CencSampleEncryptionInfoEntry()
830010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    : is_encrypted(false), iv_size(0) {}
831010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)CencSampleEncryptionInfoEntry::~CencSampleEncryptionInfoEntry() {}
832010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
833010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)SampleGroupDescription::SampleGroupDescription() : grouping_type(0) {}
834010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)SampleGroupDescription::~SampleGroupDescription() {}
835010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)FourCC SampleGroupDescription::BoxType() const { return FOURCC_SGPD; }
836010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
837010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)bool SampleGroupDescription::Parse(BoxReader* reader) {
838010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  RCHECK(reader->ReadFullBoxHeader() &&
839010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)         reader->Read4(&grouping_type));
840010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
841010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  if (grouping_type != FOURCC_SEIG) {
842010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    DLOG(WARNING) << "SampleGroupDescription box with grouping_type '"
843010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)                  << grouping_type << "' is not supported.";
844010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    return true;
845010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  }
846010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
847010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  const uint8 version = reader->version();
848010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
849010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  const size_t kKeyIdSize = 16;
850010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  const size_t kEntrySize = sizeof(uint32) + kKeyIdSize;
851010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  uint32 default_length = 0;
852010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  if (version == 1) {
853010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      RCHECK(reader->Read4(&default_length));
854010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      RCHECK(default_length == 0 || default_length >= kEntrySize);
855010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  }
856010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
857010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  uint32 count;
858010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  RCHECK(reader->Read4(&count));
859010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  entries.resize(count);
860010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  for (uint32 i = 0; i < count; ++i) {
861010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    if (version == 1) {
862010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      if (default_length == 0) {
863010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)        uint32 description_length = 0;
864010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)        RCHECK(reader->Read4(&description_length));
865010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)        RCHECK(description_length >= kEntrySize);
866010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      }
867010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    }
868010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
869010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    uint8 flag;
870010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    RCHECK(reader->SkipBytes(2) &&  // reserved.
871010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)           reader->Read1(&flag) &&
872010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)           reader->Read1(&entries[i].iv_size) &&
873010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)           reader->ReadVec(&entries[i].key_id, kKeyIdSize));
874010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
875010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    entries[i].is_encrypted = (flag != 0);
876010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    if (entries[i].is_encrypted) {
877010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      RCHECK(entries[i].iv_size == 8 || entries[i].iv_size == 16);
878010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    } else {
879010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      RCHECK(entries[i].iv_size == 0);
880010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    }
881010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  }
882010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  return true;
883010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)}
884010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
8855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TrackFragment::TrackFragment() {}
8865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TrackFragment::~TrackFragment() {}
8875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC TrackFragment::BoxType() const { return FOURCC_TRAF; }
8885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
8895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool TrackFragment::Parse(BoxReader* reader) {
890010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  RCHECK(reader->ScanChildren() &&
8915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->ReadChild(&header) &&
8925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         // Media Source specific: 'tfdt' required
8935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->ReadChild(&decode_time) &&
8945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->MaybeReadChildren(&runs) &&
8955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->MaybeReadChild(&auxiliary_offset) &&
8961e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)         reader->MaybeReadChild(&auxiliary_size) &&
897010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)         reader->MaybeReadChild(&sdtp));
898010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
899010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  // There could be multiple SampleGroupDescription and SampleToGroup boxes with
900010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  // different grouping types. For common encryption, the relevant grouping type
901010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  // is 'seig'. Continue reading until 'seig' is found, or until running out of
902010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  // child boxes.
903010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  while (sample_group_description.grouping_type != FOURCC_SEIG &&
904010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)         reader->HasChild(&sample_group_description)) {
905010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    RCHECK(reader->ReadChild(&sample_group_description));
906010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  }
907010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  while (sample_to_group.grouping_type != FOURCC_SEIG &&
908010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)         reader->HasChild(&sample_to_group)) {
909010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    RCHECK(reader->ReadChild(&sample_to_group));
910010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  }
911010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  return true;
9125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
9135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
9145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)MovieFragment::MovieFragment() {}
9155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)MovieFragment::~MovieFragment() {}
9165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)FourCC MovieFragment::BoxType() const { return FOURCC_MOOF; }
9175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
9185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool MovieFragment::Parse(BoxReader* reader) {
9195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RCHECK(reader->ScanChildren() &&
9205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->ReadChild(&header) &&
9215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->ReadChildren(&tracks) &&
9225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         reader->MaybeReadChildren(&pssh));
9235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return true;
9245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
9255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
9261e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)IndependentAndDisposableSamples::IndependentAndDisposableSamples() {}
9271e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)IndependentAndDisposableSamples::~IndependentAndDisposableSamples() {}
9281e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)FourCC IndependentAndDisposableSamples::BoxType() const { return FOURCC_SDTP; }
9291e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)
9301e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)bool IndependentAndDisposableSamples::Parse(BoxReader* reader) {
9311e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  RCHECK(reader->ReadFullBoxHeader());
9321e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  RCHECK(reader->version() == 0);
9331e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  RCHECK(reader->flags() == 0);
9341e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)
9351e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  int sample_count = reader->size() - reader->pos();
9361e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  sample_depends_on_.resize(sample_count);
9371e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  for (int i = 0; i < sample_count; ++i) {
9381e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    uint8 sample_info;
9391e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    RCHECK(reader->Read1(&sample_info));
9401e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)
9411e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    sample_depends_on_[i] =
9421e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)        static_cast<SampleDependsOn>((sample_info >> 4) & 0x3);
9431e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)
9441e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    RCHECK(sample_depends_on_[i] != kSampleDependsOnReserved);
9451e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  }
9461e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)
9471e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  return true;
9481e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)}
9491e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)
9501e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)SampleDependsOn IndependentAndDisposableSamples::sample_depends_on(
9511e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    size_t i) const {
9521e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  if (i >= sample_depends_on_.size())
9531e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)    return kSampleDependsOnUnknown;
9541e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)
9551e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)  return sample_depends_on_[i];
9561e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)}
9571e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles)
9585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}  // namespace mp4
9595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}  // namespace media
960