5 #include "packager/media/formats/mp4/box_definitions.h"
9 #include "packager/base/logging.h"
10 #include "packager/media/base/bit_reader.h"
11 #include "packager/media/base/macros.h"
12 #include "packager/media/formats/mp4/box_buffer.h"
13 #include "packager/media/formats/mp4/rcheck.h"
16 const uint32_t kFourCCSize = 4;
19 const uint32_t kCencKeyIdSize = 16;
22 const uint8_t kUnityMatrix[] = {0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
23 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0,
24 0, 0, 0, 0, 0, 0, 0, 0, 0x40, 0, 0, 0};
27 const char kVideoHandlerName[] =
"VideoHandler";
28 const char kAudioHandlerName[] =
"SoundHandler";
29 const char kTextHandlerName[] =
"TextHandler";
32 const uint32_t kVideoResolution = 0x00480000;
33 const uint16_t kVideoFrameCount = 1;
34 const uint16_t kVideoDepth = 0x0018;
36 const uint32_t kCompressorNameSize = 32u;
37 const char kAvcCompressorName[] =
"\012AVC Coding";
38 const char kHevcCompressorName[] =
"\013HEVC Coding";
39 const char kVpcCompressorName[] =
"\012VPC Coding";
43 const int kCueSourceIdNotSet = -1;
47 bool IsIvSizeValid(
size_t iv_size) {
48 return iv_size == 8 || iv_size == 16;
65 const uint8_t kDdtsExtraData[] = {0xe4, 0x7c, 0, 4, 0, 0x0f, 0};
68 const uint32_t kID3v2HeaderSize = 10;
69 const char kID3v2Identifier[] =
"ID3";
70 const uint16_t kID3v2Version = 0x0400;
73 bool IsFitIn32Bits(uint64_t a) {
74 return a <= std::numeric_limits<uint32_t>::max();
77 bool IsFitIn32Bits(int64_t a) {
78 return a <= std::numeric_limits<int32_t>::max() &&
79 a >= std::numeric_limits<int32_t>::min();
82 template <
typename T1,
typename T2>
83 bool IsFitIn32Bits(T1 a1, T2 a2) {
84 return IsFitIn32Bits(a1) && IsFitIn32Bits(a2);
87 template <
typename T1,
typename T2,
typename T3>
88 bool IsFitIn32Bits(T1 a1, T2 a2, T3 a3) {
89 return IsFitIn32Bits(a1) && IsFitIn32Bits(a2) && IsFitIn32Bits(a3);
94 namespace edash_packager {
100 TrackType FourCCToTrackType(FourCC fourcc) {
113 FourCC TrackTypeToFourCC(TrackType track_type) {
114 switch (track_type) {
128 FileType::FileType() : major_brand(FOURCC_NULL), minor_version(0) {}
129 FileType::~FileType() {}
132 bool FileType::ReadWriteInternal(
BoxBuffer* buffer) {
134 buffer->ReadWriteFourCC(&major_brand) &&
135 buffer->ReadWriteUInt32(&minor_version));
138 RCHECK(buffer->
BytesLeft() %
sizeof(FourCC) == 0);
139 num_brands = buffer->
BytesLeft() /
sizeof(FourCC);
140 compatible_brands.resize(num_brands);
142 num_brands = compatible_brands.size();
144 for (
size_t i = 0; i < num_brands; ++i)
145 RCHECK(buffer->ReadWriteFourCC(&compatible_brands[i]));
149 uint32_t FileType::ComputeSizeInternal() {
150 return HeaderSize() + kFourCCSize +
sizeof(minor_version) +
151 kFourCCSize * compatible_brands.size();
156 ProtectionSystemSpecificHeader::ProtectionSystemSpecificHeader() {}
157 ProtectionSystemSpecificHeader::~ProtectionSystemSpecificHeader() {}
160 bool ProtectionSystemSpecificHeader::ReadWriteInternal(
BoxBuffer* buffer) {
164 raw_box.assign(reader->data(), reader->data() + reader->size());
166 DCHECK(!raw_box.empty());
167 buffer->
writer()->AppendVector(raw_box);
173 uint32_t ProtectionSystemSpecificHeader::ComputeSizeInternal() {
174 return raw_box.size();
177 SampleAuxiliaryInformationOffset::SampleAuxiliaryInformationOffset() {}
178 SampleAuxiliaryInformationOffset::~SampleAuxiliaryInformationOffset() {}
181 bool SampleAuxiliaryInformationOffset::ReadWriteInternal(
BoxBuffer* buffer) {
186 uint32_t count = offsets.size();
187 RCHECK(buffer->ReadWriteUInt32(&count));
188 offsets.resize(count);
190 size_t num_bytes = (version == 1) ?
sizeof(uint64_t) :
sizeof(uint32_t);
191 for (uint32_t i = 0; i < count; ++i)
196 uint32_t SampleAuxiliaryInformationOffset::ComputeSizeInternal() {
198 if (offsets.size() == 0)
200 size_t num_bytes = (version == 1) ?
sizeof(uint64_t) :
sizeof(uint32_t);
201 return HeaderSize() +
sizeof(uint32_t) + num_bytes * offsets.size();
204 SampleAuxiliaryInformationSize::SampleAuxiliaryInformationSize()
205 : default_sample_info_size(0), sample_count(0) {}
206 SampleAuxiliaryInformationSize::~SampleAuxiliaryInformationSize() {}
209 bool SampleAuxiliaryInformationSize::ReadWriteInternal(
BoxBuffer* buffer) {
214 RCHECK(buffer->ReadWriteUInt8(&default_sample_info_size) &&
215 buffer->ReadWriteUInt32(&sample_count));
216 if (default_sample_info_size == 0)
217 RCHECK(buffer->ReadWriteVector(&sample_info_sizes, sample_count));
221 uint32_t SampleAuxiliaryInformationSize::ComputeSizeInternal() {
223 if (sample_count == 0)
225 return HeaderSize() +
sizeof(default_sample_info_size) +
226 sizeof(sample_count) +
227 (default_sample_info_size == 0 ? sample_info_sizes.size() : 0);
230 SampleEncryptionEntry::SampleEncryptionEntry() {}
231 SampleEncryptionEntry::~SampleEncryptionEntry() {}
236 DCHECK(IsIvSizeValid(iv_size));
239 RCHECK(buffer->ReadWriteVector(&initialization_vector, iv_size));
241 if (!has_subsamples) {
246 uint16_t subsample_count = subsamples.size();
247 RCHECK(buffer->ReadWriteUInt16(&subsample_count));
248 RCHECK(subsample_count > 0);
249 subsamples.resize(subsample_count);
250 for (
auto& subsample : subsamples) {
251 RCHECK(buffer->ReadWriteUInt16(&subsample.clear_bytes) &&
252 buffer->ReadWriteUInt32(&subsample.cipher_bytes));
260 DCHECK(IsIvSizeValid(iv_size));
263 initialization_vector.resize(iv_size);
264 RCHECK(reader->ReadToVector(&initialization_vector, iv_size));
266 if (!has_subsamples) {
271 uint16_t subsample_count;
272 RCHECK(reader->Read2(&subsample_count));
273 RCHECK(subsample_count > 0);
274 subsamples.resize(subsample_count);
275 for (
auto& subsample : subsamples) {
276 RCHECK(reader->Read2(&subsample.clear_bytes) &&
277 reader->Read4(&subsample.cipher_bytes));
283 const uint32_t subsample_entry_size =
sizeof(uint16_t) +
sizeof(uint32_t);
284 const uint16_t subsample_count = subsamples.size();
285 return initialization_vector.size() +
286 (subsample_count > 0 ? (
sizeof(subsample_count) +
287 subsample_entry_size * subsample_count)
293 for (uint32_t i = 0; i < subsamples.size(); ++i)
294 size += subsamples[i].clear_bytes + subsamples[i].cipher_bytes;
298 SampleEncryption::SampleEncryption() : iv_size(0) {}
299 SampleEncryption::~SampleEncryption() {}
302 bool SampleEncryption::ReadWriteInternal(
BoxBuffer* buffer) {
307 if (buffer->
Reading() && iv_size == 0) {
313 if (!IsIvSizeValid(iv_size)) {
314 LOG(ERROR) <<
"IV_size can only be 8 or 16, but seeing " << iv_size;
318 uint32_t sample_count = sample_encryption_entries.size();
319 RCHECK(buffer->ReadWriteUInt32(&sample_count));
321 sample_encryption_entries.resize(sample_count);
322 for (
auto& sample_encryption_entry : sample_encryption_entries) {
323 RCHECK(sample_encryption_entry.ReadWrite(
324 iv_size, flags & kUseSubsampleEncryption, buffer));
329 uint32_t SampleEncryption::ComputeSizeInternal() {
330 const uint32_t sample_count = sample_encryption_entries.size();
331 if (sample_count == 0) {
336 DCHECK(IsIvSizeValid(iv_size));
338 if (flags & kUseSubsampleEncryption) {
339 for (
const SampleEncryptionEntry& sample_encryption_entry :
340 sample_encryption_entries) {
341 box_size += sample_encryption_entry.ComputeSize();
344 box_size += sample_count * iv_size;
351 std::vector<SampleEncryptionEntry>* sample_encryption_entries)
const {
352 DCHECK(IsIvSizeValid(iv_size));
356 uint32_t sample_count = 0;
357 RCHECK(reader.Read4(&sample_count));
359 sample_encryption_entries->resize(sample_count);
360 for (
auto& sample_encryption_entry : *sample_encryption_entries) {
361 RCHECK(sample_encryption_entry.ParseFromBuffer(
362 iv_size, flags & kUseSubsampleEncryption, &reader));
367 OriginalFormat::OriginalFormat() : format(FOURCC_NULL) {}
368 OriginalFormat::~OriginalFormat() {}
371 bool OriginalFormat::ReadWriteInternal(
BoxBuffer* buffer) {
375 uint32_t OriginalFormat::ComputeSizeInternal() {
379 SchemeType::SchemeType() : type(FOURCC_NULL), version(0) {}
380 SchemeType::~SchemeType() {}
383 bool SchemeType::ReadWriteInternal(
BoxBuffer* buffer) {
385 buffer->ReadWriteFourCC(&type) &&
386 buffer->ReadWriteUInt32(&version));
390 uint32_t SchemeType::ComputeSizeInternal() {
391 return HeaderSize() + kFourCCSize +
sizeof(version);
394 TrackEncryption::TrackEncryption()
395 : is_encrypted(false), default_iv_size(0), default_kid(16, 0) {}
396 TrackEncryption::~TrackEncryption() {}
399 bool TrackEncryption::ReadWriteInternal(
BoxBuffer* buffer) {
401 if (default_kid.size() != kCencKeyIdSize) {
402 LOG(WARNING) <<
"CENC defines key id length of " << kCencKeyIdSize
403 <<
" bytes; got " << default_kid.size()
404 <<
". Resized accordingly.";
405 default_kid.resize(kCencKeyIdSize);
409 uint8_t flag = is_encrypted ? 1 : 0;
412 buffer->ReadWriteUInt8(&flag) &&
413 buffer->ReadWriteUInt8(&default_iv_size) &&
414 buffer->ReadWriteVector(&default_kid, kCencKeyIdSize));
416 is_encrypted = (flag != 0);
418 RCHECK(default_iv_size == 8 || default_iv_size == 16);
420 RCHECK(default_iv_size == 0);
426 uint32_t TrackEncryption::ComputeSizeInternal() {
427 return HeaderSize() +
sizeof(uint32_t) + kCencKeyIdSize;
430 SchemeInfo::SchemeInfo() {}
431 SchemeInfo::~SchemeInfo() {}
434 bool SchemeInfo::ReadWriteInternal(
BoxBuffer* buffer) {
440 uint32_t SchemeInfo::ComputeSizeInternal() {
444 ProtectionSchemeInfo::ProtectionSchemeInfo() {}
445 ProtectionSchemeInfo::~ProtectionSchemeInfo() {}
448 bool ProtectionSchemeInfo::ReadWriteInternal(
BoxBuffer* buffer) {
453 if (type.type == FOURCC_CENC || type.type == FOURCC_CBC1)
462 uint32_t ProtectionSchemeInfo::ComputeSizeInternal() {
464 if (format.format == FOURCC_NULL)
470 MovieHeader::MovieHeader()
472 modification_time(0),
478 MovieHeader::~MovieHeader() {}
481 bool MovieHeader::ReadWriteInternal(
BoxBuffer* buffer) {
484 size_t num_bytes = (version == 1) ?
sizeof(uint64_t) :
sizeof(uint32_t);
487 buffer->ReadWriteUInt32(×cale) &&
490 std::vector<uint8_t> matrix(kUnityMatrix,
491 kUnityMatrix + arraysize(kUnityMatrix));
492 RCHECK(buffer->ReadWriteInt32(&rate) &&
493 buffer->ReadWriteInt16(&volume) &&
495 buffer->ReadWriteVector(&matrix, matrix.size()) &&
497 buffer->ReadWriteUInt32(&next_track_id));
501 uint32_t MovieHeader::ComputeSizeInternal() {
502 version = IsFitIn32Bits(creation_time, modification_time, duration) ? 0 : 1;
503 return HeaderSize() +
sizeof(uint32_t) * (1 + version) * 3 +
504 sizeof(timescale) +
sizeof(rate) +
sizeof(volume) +
505 sizeof(next_track_id) +
sizeof(kUnityMatrix) + 10 +
509 TrackHeader::TrackHeader()
511 modification_time(0),
519 flags = kTrackEnabled | kTrackInMovie;
521 TrackHeader::~TrackHeader() {}
524 bool TrackHeader::ReadWriteInternal(
BoxBuffer* buffer) {
527 size_t num_bytes = (version == 1) ?
sizeof(uint64_t) :
sizeof(uint32_t);
530 buffer->ReadWriteUInt32(&track_id) &&
537 volume = (width != 0 && height != 0) ? 0 : 0x100;
539 std::vector<uint8_t> matrix(kUnityMatrix,
540 kUnityMatrix + arraysize(kUnityMatrix));
542 buffer->ReadWriteInt16(&layer) &&
543 buffer->ReadWriteInt16(&alternate_group) &&
544 buffer->ReadWriteInt16(&volume) &&
546 buffer->ReadWriteVector(&matrix, matrix.size()) &&
547 buffer->ReadWriteUInt32(&width) &&
548 buffer->ReadWriteUInt32(&height));
552 uint32_t TrackHeader::ComputeSizeInternal() {
553 version = IsFitIn32Bits(creation_time, modification_time, duration) ? 0 : 1;
555 sizeof(uint32_t) * (1 + version) * 3 +
sizeof(layer) +
556 sizeof(alternate_group) +
sizeof(volume) +
sizeof(width) +
557 sizeof(height) +
sizeof(kUnityMatrix) + 14;
560 SampleDescription::SampleDescription() : type(kInvalid) {}
561 SampleDescription::~SampleDescription() {}
564 bool SampleDescription::ReadWriteInternal(
BoxBuffer* buffer) {
568 count = video_entries.size();
571 count = audio_entries.size();
574 count = text_entries.size();
577 NOTIMPLEMENTED() <<
"SampleDecryption type " << type
578 <<
" is not handled. Skipping.";
581 buffer->ReadWriteUInt32(&count));
584 BoxReader* reader = buffer->
reader();
586 video_entries.clear();
587 audio_entries.clear();
590 if (type == kVideo) {
591 RCHECK(reader->ReadAllChildren(&video_entries));
592 RCHECK(video_entries.size() == count);
593 }
else if (type == kAudio) {
594 RCHECK(reader->ReadAllChildren(&audio_entries));
595 RCHECK(audio_entries.size() == count);
596 }
else if (type == kText) {
597 RCHECK(reader->ReadAllChildren(&text_entries));
598 RCHECK(text_entries.size() == count);
601 DCHECK_LT(0u, count);
602 if (type == kVideo) {
603 for (uint32_t i = 0; i < count; ++i)
605 }
else if (type == kAudio) {
606 for (uint32_t i = 0; i < count; ++i)
608 }
else if (type == kText) {
609 for (uint32_t i = 0; i < count; ++i)
618 uint32_t SampleDescription::ComputeSizeInternal() {
619 uint32_t box_size =
HeaderSize() +
sizeof(uint32_t);
620 if (type == kVideo) {
621 for (uint32_t i = 0; i < video_entries.size(); ++i)
623 }
else if (type == kAudio) {
624 for (uint32_t i = 0; i < audio_entries.size(); ++i)
626 }
else if (type == kText) {
627 for (uint32_t i = 0; i < text_entries.size(); ++i)
633 DecodingTimeToSample::DecodingTimeToSample() {}
634 DecodingTimeToSample::~DecodingTimeToSample() {}
637 bool DecodingTimeToSample::ReadWriteInternal(
BoxBuffer* buffer) {
638 uint32_t count = decoding_time.size();
640 buffer->ReadWriteUInt32(&count));
642 decoding_time.resize(count);
643 for (uint32_t i = 0; i < count; ++i) {
644 RCHECK(buffer->ReadWriteUInt32(&decoding_time[i].sample_count) &&
645 buffer->ReadWriteUInt32(&decoding_time[i].sample_delta));
650 uint32_t DecodingTimeToSample::ComputeSizeInternal() {
652 sizeof(DecodingTime) * decoding_time.size();
655 CompositionTimeToSample::CompositionTimeToSample() {}
656 CompositionTimeToSample::~CompositionTimeToSample() {}
659 bool CompositionTimeToSample::ReadWriteInternal(
BoxBuffer* buffer) {
660 uint32_t count = composition_offset.size();
666 for (uint32_t i = 0; i < count; ++i) {
667 if (composition_offset[i].sample_offset < 0) {
675 buffer->ReadWriteUInt32(&count));
677 composition_offset.resize(count);
678 for (uint32_t i = 0; i < count; ++i) {
679 RCHECK(buffer->ReadWriteUInt32(&composition_offset[i].sample_count));
682 uint32_t sample_offset = composition_offset[i].sample_offset;
683 RCHECK(buffer->ReadWriteUInt32(&sample_offset));
684 composition_offset[i].sample_offset = sample_offset;
686 int32_t sample_offset = composition_offset[i].sample_offset;
687 RCHECK(buffer->ReadWriteInt32(&sample_offset));
688 composition_offset[i].sample_offset = sample_offset;
694 uint32_t CompositionTimeToSample::ComputeSizeInternal() {
696 if (composition_offset.empty())
701 const uint32_t kCompositionOffsetSize =
sizeof(uint32_t) * 2;
703 kCompositionOffsetSize * composition_offset.size();
706 SampleToChunk::SampleToChunk() {}
707 SampleToChunk::~SampleToChunk() {}
710 bool SampleToChunk::ReadWriteInternal(
BoxBuffer* buffer) {
711 uint32_t count = chunk_info.size();
713 buffer->ReadWriteUInt32(&count));
715 chunk_info.resize(count);
716 for (uint32_t i = 0; i < count; ++i) {
717 RCHECK(buffer->ReadWriteUInt32(&chunk_info[i].first_chunk) &&
718 buffer->ReadWriteUInt32(&chunk_info[i].samples_per_chunk) &&
719 buffer->ReadWriteUInt32(&chunk_info[i].sample_description_index));
721 RCHECK(i == 0 ? chunk_info[i].first_chunk == 1
722 : chunk_info[i].first_chunk > chunk_info[i - 1].first_chunk);
727 uint32_t SampleToChunk::ComputeSizeInternal() {
729 sizeof(ChunkInfo) * chunk_info.size();
732 SampleSize::SampleSize() : sample_size(0), sample_count(0) {}
733 SampleSize::~SampleSize() {}
736 bool SampleSize::ReadWriteInternal(
BoxBuffer* buffer) {
738 buffer->ReadWriteUInt32(&sample_size) &&
739 buffer->ReadWriteUInt32(&sample_count));
741 if (sample_size == 0) {
743 sizes.resize(sample_count);
745 DCHECK(sample_count == sizes.size());
746 for (uint32_t i = 0; i < sample_count; ++i)
747 RCHECK(buffer->ReadWriteUInt32(&sizes[i]));
752 uint32_t SampleSize::ComputeSizeInternal() {
753 return HeaderSize() +
sizeof(sample_size) +
sizeof(sample_count) +
754 (sample_size == 0 ?
sizeof(uint32_t) * sizes.size() : 0);
757 CompactSampleSize::CompactSampleSize() : field_size(0) {}
758 CompactSampleSize::~CompactSampleSize() {}
761 bool CompactSampleSize::ReadWriteInternal(
BoxBuffer* buffer) {
762 uint32_t sample_count = sizes.size();
765 buffer->ReadWriteUInt8(&field_size) &&
766 buffer->ReadWriteUInt32(&sample_count));
769 sizes.resize(sample_count + (field_size == 4 ? 1 : 0), 0);
770 switch (field_size) {
772 for (uint32_t i = 0; i < sample_count; i += 2) {
775 RCHECK(buffer->ReadWriteUInt8(&size));
776 sizes[i] = size >> 4;
777 sizes[i + 1] = size & 0x0F;
779 DCHECK_LT(sizes[i], 16u);
780 DCHECK_LT(sizes[i + 1], 16u);
781 uint8_t size = (sizes[i] << 4) | sizes[i + 1];
782 RCHECK(buffer->ReadWriteUInt8(&size));
787 for (uint32_t i = 0; i < sample_count; ++i) {
788 uint8_t size = sizes[i];
789 RCHECK(buffer->ReadWriteUInt8(&size));
794 for (uint32_t i = 0; i < sample_count; ++i) {
795 uint16_t size = sizes[i];
796 RCHECK(buffer->ReadWriteUInt16(&size));
803 sizes.resize(sample_count);
807 uint32_t CompactSampleSize::ComputeSizeInternal() {
808 return HeaderSize() +
sizeof(uint32_t) +
sizeof(uint32_t) +
809 (field_size * sizes.size() + 7) / 8;
812 ChunkOffset::ChunkOffset() {}
813 ChunkOffset::~ChunkOffset() {}
816 bool ChunkOffset::ReadWriteInternal(
BoxBuffer* buffer) {
817 uint32_t count = offsets.size();
819 buffer->ReadWriteUInt32(&count));
821 offsets.resize(count);
822 for (uint32_t i = 0; i < count; ++i)
827 uint32_t ChunkOffset::ComputeSizeInternal() {
828 return HeaderSize() +
sizeof(uint32_t) +
sizeof(uint32_t) * offsets.size();
831 ChunkLargeOffset::ChunkLargeOffset() {}
832 ChunkLargeOffset::~ChunkLargeOffset() {}
835 bool ChunkLargeOffset::ReadWriteInternal(
BoxBuffer* buffer) {
836 uint32_t count = offsets.size();
840 if (count == 0 || IsFitIn32Bits(offsets[count - 1])) {
842 stco.offsets.swap(offsets);
845 stco.offsets.swap(offsets);
851 buffer->ReadWriteUInt32(&count));
853 offsets.resize(count);
854 for (uint32_t i = 0; i < count; ++i)
855 RCHECK(buffer->ReadWriteUInt64(&offsets[i]));
859 uint32_t ChunkLargeOffset::ComputeSizeInternal() {
860 uint32_t count = offsets.size();
861 int use_large_offset =
862 (count > 0 && !IsFitIn32Bits(offsets[count - 1])) ? 1 : 0;
864 sizeof(uint32_t) * (1 + use_large_offset) * offsets.size();
867 SyncSample::SyncSample() {}
868 SyncSample::~SyncSample() {}
871 bool SyncSample::ReadWriteInternal(
BoxBuffer* buffer) {
872 uint32_t count = sample_number.size();
874 buffer->ReadWriteUInt32(&count));
876 sample_number.resize(count);
877 for (uint32_t i = 0; i < count; ++i)
878 RCHECK(buffer->ReadWriteUInt32(&sample_number[i]));
882 uint32_t SyncSample::ComputeSizeInternal() {
884 if (sample_number.empty())
887 sizeof(uint32_t) * sample_number.size();
890 SampleTable::SampleTable() {}
891 SampleTable::~SampleTable() {}
894 bool SampleTable::ReadWriteInternal(
BoxBuffer* buffer) {
910 CompactSampleSize compact_sample_size;
911 RCHECK(reader->
ReadChild(&compact_sample_size));
912 sample_size.sample_size = 0;
913 sample_size.sample_count = compact_sample_size.sizes.size();
914 sample_size.sizes.swap(compact_sample_size.sizes);
918 if (reader->
ChildExist(&chunk_large_offset)) {
919 RCHECK(reader->
ReadChild(&chunk_large_offset));
921 ChunkOffset chunk_offset;
922 RCHECK(reader->
ReadChild(&chunk_offset));
923 chunk_large_offset.offsets.swap(chunk_offset.offsets);
933 uint32_t SampleTable::ComputeSizeInternal() {
941 EditList::EditList() {}
942 EditList::~EditList() {}
945 bool EditList::ReadWriteInternal(
BoxBuffer* buffer) {
946 uint32_t count = edits.size();
950 size_t num_bytes = (version == 1) ?
sizeof(uint64_t) :
sizeof(uint32_t);
951 for (uint32_t i = 0; i < count; ++i) {
954 buffer->ReadWriteInt64NBytes(&edits[i].media_time, num_bytes) &&
955 buffer->ReadWriteInt16(&edits[i].media_rate_integer) &&
956 buffer->ReadWriteInt16(&edits[i].media_rate_fraction));
961 uint32_t EditList::ComputeSizeInternal() {
967 for (uint32_t i = 0; i < edits.size(); ++i) {
968 if (!IsFitIn32Bits(edits[i].segment_duration, edits[i].media_time)) {
974 (
sizeof(uint32_t) * (1 + version) * 2 +
sizeof(int16_t) * 2) *
982 bool Edit::ReadWriteInternal(
BoxBuffer* buffer) {
988 uint32_t Edit::ComputeSizeInternal() {
990 if (list.edits.empty())
995 HandlerReference::HandlerReference() : handler_type(FOURCC_NULL) {}
996 HandlerReference::~HandlerReference() {}
999 bool HandlerReference::ReadWriteInternal(
BoxBuffer* buffer) {
1000 std::vector<uint8_t> handler_name;
1002 switch (handler_type) {
1004 handler_name.assign(kVideoHandlerName,
1005 kVideoHandlerName + arraysize(kVideoHandlerName));
1008 handler_name.assign(kAudioHandlerName,
1009 kAudioHandlerName + arraysize(kAudioHandlerName));
1012 handler_name.assign(kTextHandlerName,
1013 kTextHandlerName + arraysize(kTextHandlerName));
1024 buffer->ReadWriteFourCC(&handler_type));
1027 buffer->ReadWriteVector(&handler_name, handler_name.size()));
1032 uint32_t HandlerReference::ComputeSizeInternal() {
1033 uint32_t box_size =
HeaderSize() + kFourCCSize + 16;
1034 switch (handler_type) {
1036 box_size +=
sizeof(kVideoHandlerName);
1039 box_size +=
sizeof(kAudioHandlerName);
1042 box_size +=
sizeof(kTextHandlerName);
1052 bool Language::ReadWrite(BoxBuffer* buffer) {
1053 if (buffer->Reading()) {
1056 std::vector<uint8_t> temp;
1057 RCHECK(buffer->ReadWriteVector(&temp, 2));
1059 BitReader bit_reader(&temp[0], 2);
1060 bit_reader.SkipBits(1);
1062 for (
int i = 0; i < 3; ++i) {
1063 CHECK(bit_reader.ReadBits(5, &language[i]));
1064 language[i] += 0x60;
1066 code.assign(language, 3);
1069 const char kUndefinedLanguage[] =
"und";
1071 code = kUndefinedLanguage;
1072 DCHECK_EQ(code.size(), 3u);
1076 for (
int i = 0; i < 3; ++i)
1077 lang |= (code[i] - 0x60) << ((2 - i) * 5);
1078 RCHECK(buffer->ReadWriteUInt16(&lang));
1083 uint32_t Language::ComputeSize()
const {
1088 bool PrivFrame::ReadWrite(BoxBuffer* buffer) {
1089 FourCC fourcc = FOURCC_PRIV;
1090 RCHECK(buffer->ReadWriteFourCC(&fourcc));
1091 if (fourcc != FOURCC_PRIV) {
1092 VLOG(1) <<
"Skip unrecognized id3 frame during read: "
1093 << FourCCToString(fourcc);
1097 uint32_t frame_size = owner.size() + 1 + value.size();
1101 DCHECK_LT(frame_size, 0x7Fu);
1103 RCHECK(buffer->ReadWriteUInt32(&frame_size) &&
1104 buffer->ReadWriteUInt16(&flags));
1106 if (buffer->Reading()) {
1108 RCHECK(buffer->ReadWriteString(&str, frame_size));
1110 size_t pos = str.find(
'\0');
1111 RCHECK(pos < str.size());
1112 owner = str.substr(0, pos);
1113 value = str.substr(pos + 1);
1116 RCHECK(buffer->ReadWriteString(&owner, owner.size()) &&
1117 buffer->ReadWriteUInt8(&byte) &&
1118 buffer->ReadWriteString(&value, value.size()));
1123 uint32_t PrivFrame::ComputeSize()
const {
1124 if (owner.empty() && value.empty())
1126 const uint32_t kFourCCSize = 4;
1127 return kFourCCSize +
sizeof(uint32_t) +
sizeof(uint16_t) + owner.size() + 1 +
1136 bool ID3v2::ReadWriteInternal(
BoxBuffer* buffer) {
1138 language.ReadWrite(buffer));
1141 std::string id3v2_identifier = kID3v2Identifier;
1142 uint16_t version = kID3v2Version;
1148 DCHECK_LT(data_size, 0x7Fu);
1150 RCHECK(buffer->
ReadWriteString(&id3v2_identifier, id3v2_identifier.size()) &&
1151 buffer->ReadWriteUInt16(&version) &&
1152 buffer->ReadWriteUInt8(&flags) &&
1153 buffer->ReadWriteUInt32(&data_size));
1159 uint32_t ID3v2::ComputeSizeInternal() {
1162 return private_frame_size == 0 ? 0 :
HeaderSize() + language.ComputeSize() +
1167 Metadata::Metadata() {}
1168 Metadata::~Metadata() {}
1174 bool Metadata::ReadWriteInternal(
BoxBuffer* buffer) {
1182 uint32_t Metadata::ComputeSizeInternal() {
1185 return id3v2_size == 0 ? 0
1189 CodecConfigurationRecord::CodecConfigurationRecord() : box_type(FOURCC_NULL) {}
1190 CodecConfigurationRecord::~CodecConfigurationRecord() {}
1197 bool CodecConfigurationRecord::ReadWriteInternal(
BoxBuffer* buffer) {
1200 RCHECK(buffer->ReadWriteVector(&data, buffer->
BytesLeft()));
1202 RCHECK(buffer->ReadWriteVector(&data, data.size()));
1207 uint32_t CodecConfigurationRecord::ComputeSizeInternal() {
1213 PixelAspectRatio::PixelAspectRatio() : h_spacing(0), v_spacing(0) {}
1214 PixelAspectRatio::~PixelAspectRatio() {}
1217 bool PixelAspectRatio::ReadWriteInternal(
BoxBuffer* buffer) {
1219 buffer->ReadWriteUInt32(&h_spacing) &&
1220 buffer->ReadWriteUInt32(&v_spacing));
1224 uint32_t PixelAspectRatio::ComputeSizeInternal() {
1226 if (h_spacing == 0 && v_spacing == 0)
1229 DCHECK(h_spacing != 0 && v_spacing != 0);
1230 return HeaderSize() +
sizeof(h_spacing) +
sizeof(v_spacing);
1233 VideoSampleEntry::VideoSampleEntry()
1234 : format(FOURCC_NULL), data_reference_index(1), width(0), height(0) {}
1236 VideoSampleEntry::~VideoSampleEntry() {}
1238 if (format == FOURCC_NULL) {
1239 LOG(ERROR) <<
"VideoSampleEntry should be parsed according to the "
1240 <<
"handler type recovered in its Media ancestor.";
1245 bool VideoSampleEntry::ReadWriteInternal(
BoxBuffer* buffer) {
1246 std::vector<uint8_t> compressor_name;
1248 DCHECK(buffer->
reader());
1249 format = buffer->
reader()->type();
1253 const FourCC actual_format = GetActualFormat();
1254 switch (actual_format) {
1256 compressor_name.assign(
1258 kAvcCompressorName + arraysize(kAvcCompressorName));
1262 compressor_name.assign(
1263 kHevcCompressorName,
1264 kHevcCompressorName + arraysize(kHevcCompressorName));
1269 compressor_name.assign(
1271 kVpcCompressorName + arraysize(kVpcCompressorName));
1274 LOG(ERROR) << FourCCToString(actual_format) <<
" is not supported.";
1277 compressor_name.resize(kCompressorNameSize);
1280 uint32_t video_resolution = kVideoResolution;
1281 uint16_t video_frame_count = kVideoFrameCount;
1282 uint16_t video_depth = kVideoDepth;
1283 int16_t predefined = -1;
1285 buffer->ReadWriteUInt16(&data_reference_index) &&
1287 buffer->ReadWriteUInt16(&width) &&
1288 buffer->ReadWriteUInt16(&height) &&
1289 buffer->ReadWriteUInt32(&video_resolution) &&
1290 buffer->ReadWriteUInt32(&video_resolution) &&
1292 buffer->ReadWriteUInt16(&video_frame_count) &&
1293 buffer->ReadWriteVector(&compressor_name, kCompressorNameSize) &&
1294 buffer->ReadWriteUInt16(&video_depth) &&
1295 buffer->ReadWriteInt16(&predefined));
1299 if (format == FOURCC_ENCV) {
1303 while (sinf.type.type != FOURCC_CENC && sinf.type.type != FOURCC_CBC1) {
1312 const FourCC actual_format = GetActualFormat();
1313 switch (actual_format) {
1315 codec_config_record.box_type = FOURCC_AVCC;
1319 codec_config_record.box_type = FOURCC_HVCC;
1324 codec_config_record.box_type = FOURCC_VPCC;
1327 LOG(ERROR) << FourCCToString(actual_format) <<
" is not supported.";
1335 uint32_t VideoSampleEntry::ComputeSizeInternal() {
1336 return HeaderSize() +
sizeof(data_reference_index) +
sizeof(width) +
1337 sizeof(height) +
sizeof(kVideoResolution) * 2 +
1338 sizeof(kVideoFrameCount) +
sizeof(kVideoDepth) +
1340 codec_config_record.
ComputeSize() + kCompressorNameSize + 6 + 4 + 16 +
1344 ElementaryStreamDescriptor::ElementaryStreamDescriptor() {}
1345 ElementaryStreamDescriptor::~ElementaryStreamDescriptor() {}
1348 bool ElementaryStreamDescriptor::ReadWriteInternal(
BoxBuffer* buffer) {
1351 std::vector<uint8_t> data;
1352 RCHECK(buffer->ReadWriteVector(&data, buffer->
BytesLeft()));
1353 RCHECK(es_descriptor.Parse(data));
1354 if (es_descriptor.
IsAAC()) {
1355 RCHECK(aac_audio_specific_config.
Parse(
1356 es_descriptor.decoder_specific_info()));
1359 DCHECK(buffer->
writer());
1360 es_descriptor.Write(buffer->
writer());
1365 uint32_t ElementaryStreamDescriptor::ComputeSizeInternal() {
1367 if (es_descriptor.object_type() == kForbidden)
1369 return HeaderSize() + es_descriptor.ComputeSize();
1372 DTSSpecific::DTSSpecific()
1373 : sampling_frequency(0),
1376 pcm_sample_depth(0) {}
1377 DTSSpecific::~DTSSpecific() {}
1380 bool DTSSpecific::ReadWriteInternal(
BoxBuffer* buffer) {
1382 buffer->ReadWriteUInt32(&sampling_frequency) &&
1383 buffer->ReadWriteUInt32(&max_bitrate) &&
1384 buffer->ReadWriteUInt32(&avg_bitrate) &&
1385 buffer->ReadWriteUInt8(&pcm_sample_depth));
1388 RCHECK(buffer->ReadWriteVector(&extra_data, buffer->
BytesLeft()));
1390 if (extra_data.empty()) {
1391 extra_data.assign(kDdtsExtraData,
1392 kDdtsExtraData +
sizeof(kDdtsExtraData));
1394 RCHECK(buffer->ReadWriteVector(&extra_data, extra_data.size()));
1399 uint32_t DTSSpecific::ComputeSizeInternal() {
1401 if (sampling_frequency == 0)
1403 return HeaderSize() +
sizeof(sampling_frequency) +
sizeof(max_bitrate) +
1404 sizeof(avg_bitrate) +
sizeof(pcm_sample_depth) +
1405 sizeof(kDdtsExtraData);
1408 AC3Specific::AC3Specific() {}
1409 AC3Specific::~AC3Specific() {}
1413 bool AC3Specific::ReadWriteInternal(
BoxBuffer* buffer) {
1415 buffer->ReadWriteVector(
1420 uint32_t AC3Specific::ComputeSizeInternal() {
1427 EC3Specific::EC3Specific() {}
1428 EC3Specific::~EC3Specific() {}
1432 bool EC3Specific::ReadWriteInternal(
BoxBuffer* buffer) {
1435 RCHECK(buffer->ReadWriteVector(&data, size));
1439 uint32_t EC3Specific::ComputeSizeInternal() {
1446 AudioSampleEntry::AudioSampleEntry()
1447 : format(FOURCC_NULL),
1448 data_reference_index(1),
1453 AudioSampleEntry::~AudioSampleEntry() {}
1456 if (format == FOURCC_NULL) {
1457 LOG(ERROR) <<
"AudioSampleEntry should be parsed according to the "
1458 <<
"handler type recovered in its Media ancestor.";
1463 bool AudioSampleEntry::ReadWriteInternal(
BoxBuffer* buffer) {
1465 DCHECK(buffer->
reader());
1466 format = buffer->
reader()->type();
1474 buffer->ReadWriteUInt16(&data_reference_index) &&
1476 buffer->ReadWriteUInt16(&channelcount) &&
1477 buffer->ReadWriteUInt16(&samplesize) &&
1479 buffer->ReadWriteUInt32(&samplerate));
1484 if (format == FOURCC_ENCA) {
1488 while (sinf.type.type != FOURCC_CENC && sinf.type.type != FOURCC_CBC1) {
1504 uint32_t AudioSampleEntry::ComputeSizeInternal() {
1505 return HeaderSize() +
sizeof(data_reference_index) +
sizeof(channelcount) +
1506 sizeof(samplesize) +
sizeof(samplerate) + sinf.
ComputeSize() +
1513 WebVTTConfigurationBox::WebVTTConfigurationBox() {}
1514 WebVTTConfigurationBox::~WebVTTConfigurationBox() {}
1520 bool WebVTTConfigurationBox::ReadWriteInternal(
BoxBuffer* buffer) {
1527 uint32_t WebVTTConfigurationBox::ComputeSizeInternal() {
1531 WebVTTSourceLabelBox::WebVTTSourceLabelBox() {}
1532 WebVTTSourceLabelBox::~WebVTTSourceLabelBox() {}
1538 bool WebVTTSourceLabelBox::ReadWriteInternal(
BoxBuffer* buffer) {
1542 : source_label.size());
1545 uint32_t WebVTTSourceLabelBox::ComputeSizeInternal() {
1546 if (source_label.empty())
1551 TextSampleEntry::TextSampleEntry() : format(FOURCC_NULL) {}
1552 TextSampleEntry::~TextSampleEntry() {}
1555 if (format == FOURCC_NULL) {
1556 LOG(ERROR) <<
"TextSampleEntry should be parsed according to the "
1557 <<
"handler type recovered in its Media ancestor.";
1562 bool TextSampleEntry::ReadWriteInternal(
BoxBuffer* buffer) {
1564 DCHECK(buffer->
reader());
1565 format = buffer->
reader()->type();
1570 buffer->ReadWriteUInt16(&data_reference_index));
1572 if (format == FOURCC_wvtt) {
1581 uint32_t TextSampleEntry::ComputeSizeInternal() {
1583 return HeaderSize() + 6 +
sizeof(data_reference_index) +
1587 MediaHeader::MediaHeader()
1588 : creation_time(0), modification_time(0), timescale(0), duration(0) {}
1589 MediaHeader::~MediaHeader() {}
1592 bool MediaHeader::ReadWriteInternal(
BoxBuffer* buffer) {
1595 uint8_t num_bytes = (version == 1) ?
sizeof(uint64_t) :
sizeof(uint32_t);
1598 buffer->ReadWriteUInt32(×cale) &&
1600 language.ReadWrite(buffer) &&
1605 uint32_t MediaHeader::ComputeSizeInternal() {
1606 version = IsFitIn32Bits(creation_time, modification_time, duration) ? 0 : 1;
1608 sizeof(uint32_t) * (1 + version) * 3 + language.ComputeSize() +
1612 VideoMediaHeader::VideoMediaHeader()
1613 : graphicsmode(0), opcolor_red(0), opcolor_green(0), opcolor_blue(0) {
1614 const uint32_t kVideoMediaHeaderFlags = 1;
1615 flags = kVideoMediaHeaderFlags;
1617 VideoMediaHeader::~VideoMediaHeader() {}
1619 bool VideoMediaHeader::ReadWriteInternal(
BoxBuffer* buffer) {
1621 buffer->ReadWriteUInt16(&graphicsmode) &&
1622 buffer->ReadWriteUInt16(&opcolor_red) &&
1623 buffer->ReadWriteUInt16(&opcolor_green) &&
1624 buffer->ReadWriteUInt16(&opcolor_blue));
1628 uint32_t VideoMediaHeader::ComputeSizeInternal() {
1629 return HeaderSize() +
sizeof(graphicsmode) +
sizeof(opcolor_red) +
1630 sizeof(opcolor_green) +
sizeof(opcolor_blue);
1633 SoundMediaHeader::SoundMediaHeader() : balance(0) {}
1634 SoundMediaHeader::~SoundMediaHeader() {}
1636 bool SoundMediaHeader::ReadWriteInternal(
BoxBuffer* buffer) {
1638 buffer->ReadWriteUInt16(&balance) &&
1643 uint32_t SoundMediaHeader::ComputeSizeInternal() {
1644 return HeaderSize() +
sizeof(balance) +
sizeof(uint16_t);
1647 SubtitleMediaHeader::SubtitleMediaHeader() {}
1648 SubtitleMediaHeader::~SubtitleMediaHeader() {}
1652 bool SubtitleMediaHeader::ReadWriteInternal(
BoxBuffer* buffer) {
1656 uint32_t SubtitleMediaHeader::ComputeSizeInternal() {
1660 DataEntryUrl::DataEntryUrl() {
1661 const uint32_t kDataEntryUrlFlags = 1;
1662 flags = kDataEntryUrlFlags;
1664 DataEntryUrl::~DataEntryUrl() {}
1666 bool DataEntryUrl::ReadWriteInternal(
BoxBuffer* buffer) {
1669 RCHECK(buffer->ReadWriteVector(&location, buffer->
BytesLeft()));
1671 RCHECK(buffer->ReadWriteVector(&location, location.size()));
1676 uint32_t DataEntryUrl::ComputeSizeInternal() {
1680 DataReference::DataReference() {
1682 data_entry.resize(1);
1684 DataReference::~DataReference() {}
1686 bool DataReference::ReadWriteInternal(
BoxBuffer* buffer) {
1687 uint32_t entry_count = data_entry.size();
1689 buffer->ReadWriteUInt32(&entry_count));
1690 data_entry.resize(entry_count);
1692 for (uint32_t i = 0; i < entry_count; ++i)
1697 uint32_t DataReference::ComputeSizeInternal() {
1698 uint32_t count = data_entry.size();
1699 uint32_t box_size =
HeaderSize() +
sizeof(count);
1700 for (uint32_t i = 0; i < count; ++i)
1705 DataInformation::DataInformation() {}
1706 DataInformation::~DataInformation() {}
1709 bool DataInformation::ReadWriteInternal(
BoxBuffer* buffer) {
1715 uint32_t DataInformation::ComputeSizeInternal() {
1719 MediaInformation::MediaInformation() {}
1720 MediaInformation::~MediaInformation() {}
1723 bool MediaInformation::ReadWriteInternal(
BoxBuffer* buffer) {
1728 switch (sample_table.description.type) {
1745 uint32_t MediaInformation::ComputeSizeInternal() {
1748 switch (sample_table.description.type) {
1768 bool Media::ReadWriteInternal(
BoxBuffer* buffer) {
1780 information.sample_table.description.type =
1781 FourCCToTrackType(handler.handler_type);
1783 handler.handler_type =
1784 TrackTypeToFourCC(information.sample_table.description.type);
1785 RCHECK(handler.handler_type != FOURCC_NULL);
1792 uint32_t Media::ComputeSizeInternal() {
1793 handler.handler_type =
1794 TrackTypeToFourCC(information.sample_table.description.type);
1803 bool Track::ReadWriteInternal(
BoxBuffer* buffer) {
1813 uint32_t Track::ComputeSizeInternal() {
1818 MovieExtendsHeader::MovieExtendsHeader() : fragment_duration(0) {}
1819 MovieExtendsHeader::~MovieExtendsHeader() {}
1822 bool MovieExtendsHeader::ReadWriteInternal(
BoxBuffer* buffer) {
1824 size_t num_bytes = (version == 1) ?
sizeof(uint64_t) :
sizeof(uint32_t);
1829 uint32_t MovieExtendsHeader::ComputeSizeInternal() {
1831 if (fragment_duration == 0)
1833 version = IsFitIn32Bits(fragment_duration) ? 0 : 1;
1834 return HeaderSize() +
sizeof(uint32_t) * (1 + version);
1837 TrackExtends::TrackExtends()
1839 default_sample_description_index(0),
1840 default_sample_duration(0),
1841 default_sample_size(0),
1842 default_sample_flags(0) {}
1843 TrackExtends::~TrackExtends() {}
1846 bool TrackExtends::ReadWriteInternal(
BoxBuffer* buffer) {
1848 buffer->ReadWriteUInt32(&track_id) &&
1849 buffer->ReadWriteUInt32(&default_sample_description_index) &&
1850 buffer->ReadWriteUInt32(&default_sample_duration) &&
1851 buffer->ReadWriteUInt32(&default_sample_size) &&
1852 buffer->ReadWriteUInt32(&default_sample_flags));
1856 uint32_t TrackExtends::ComputeSizeInternal() {
1858 sizeof(default_sample_description_index) +
1859 sizeof(default_sample_duration) +
sizeof(default_sample_size) +
1860 sizeof(default_sample_flags);
1863 MovieExtends::MovieExtends() {}
1864 MovieExtends::~MovieExtends() {}
1867 bool MovieExtends::ReadWriteInternal(
BoxBuffer* buffer) {
1872 DCHECK(buffer->
reader());
1875 for (uint32_t i = 0; i < tracks.size(); ++i)
1881 uint32_t MovieExtends::ComputeSizeInternal() {
1883 if (tracks.size() == 0)
1886 for (uint32_t i = 0; i < tracks.size(); ++i)
1895 bool Movie::ReadWriteInternal(
BoxBuffer* buffer) {
1907 for (uint32_t i = 0; i < tracks.size(); ++i)
1909 for (uint32_t i = 0; i < pssh.size(); ++i)
1915 uint32_t Movie::ComputeSizeInternal() {
1918 for (uint32_t i = 0; i < tracks.size(); ++i)
1920 for (uint32_t i = 0; i < pssh.size(); ++i)
1925 TrackFragmentDecodeTime::TrackFragmentDecodeTime() : decode_time(0) {}
1926 TrackFragmentDecodeTime::~TrackFragmentDecodeTime() {}
1929 bool TrackFragmentDecodeTime::ReadWriteInternal(
BoxBuffer* buffer) {
1931 size_t num_bytes = (version == 1) ?
sizeof(uint64_t) :
sizeof(uint32_t);
1936 uint32_t TrackFragmentDecodeTime::ComputeSizeInternal() {
1937 version = IsFitIn32Bits(decode_time) ? 0 : 1;
1938 return HeaderSize() +
sizeof(uint32_t) * (1 + version);
1941 MovieFragmentHeader::MovieFragmentHeader() : sequence_number(0) {}
1942 MovieFragmentHeader::~MovieFragmentHeader() {}
1945 bool MovieFragmentHeader::ReadWriteInternal(
BoxBuffer* buffer) {
1947 buffer->ReadWriteUInt32(&sequence_number);
1950 uint32_t MovieFragmentHeader::ComputeSizeInternal() {
1951 return HeaderSize() +
sizeof(sequence_number);
1954 TrackFragmentHeader::TrackFragmentHeader()
1956 sample_description_index(0),
1957 default_sample_duration(0),
1958 default_sample_size(0),
1959 default_sample_flags(0) {}
1961 TrackFragmentHeader::~TrackFragmentHeader() {}
1964 bool TrackFragmentHeader::ReadWriteInternal(
BoxBuffer* buffer) {
1966 buffer->ReadWriteUInt32(&track_id));
1968 if (flags & kBaseDataOffsetPresentMask) {
1973 uint64_t base_data_offset;
1974 RCHECK(buffer->ReadWriteUInt64(&base_data_offset));
1975 DLOG(WARNING) <<
"base-data-offset-present is not expected. Assumes "
1976 "default-base-is-moof.";
1979 if (flags & kSampleDescriptionIndexPresentMask) {
1980 RCHECK(buffer->ReadWriteUInt32(&sample_description_index));
1981 }
else if (buffer->
Reading()) {
1982 sample_description_index = 0;
1985 if (flags & kDefaultSampleDurationPresentMask) {
1986 RCHECK(buffer->ReadWriteUInt32(&default_sample_duration));
1987 }
else if (buffer->
Reading()) {
1988 default_sample_duration = 0;
1991 if (flags & kDefaultSampleSizePresentMask) {
1992 RCHECK(buffer->ReadWriteUInt32(&default_sample_size));
1993 }
else if (buffer->
Reading()) {
1994 default_sample_size = 0;
1997 if (flags & kDefaultSampleFlagsPresentMask)
1998 RCHECK(buffer->ReadWriteUInt32(&default_sample_flags));
2002 uint32_t TrackFragmentHeader::ComputeSizeInternal() {
2003 uint32_t box_size =
HeaderSize() +
sizeof(track_id);
2004 if (flags & kSampleDescriptionIndexPresentMask)
2005 box_size +=
sizeof(sample_description_index);
2006 if (flags & kDefaultSampleDurationPresentMask)
2007 box_size +=
sizeof(default_sample_duration);
2008 if (flags & kDefaultSampleSizePresentMask)
2009 box_size +=
sizeof(default_sample_size);
2010 if (flags & kDefaultSampleFlagsPresentMask)
2011 box_size +=
sizeof(default_sample_flags);
2015 TrackFragmentRun::TrackFragmentRun() : sample_count(0), data_offset(0) {}
2016 TrackFragmentRun::~TrackFragmentRun() {}
2019 bool TrackFragmentRun::ReadWriteInternal(
BoxBuffer* buffer) {
2025 if (flags & kSampleCompTimeOffsetsPresentMask) {
2026 for (uint32_t i = 0; i < sample_count; ++i) {
2027 if (sample_composition_time_offsets[i] < 0) {
2036 buffer->ReadWriteUInt32(&sample_count));
2038 bool data_offset_present = (flags & kDataOffsetPresentMask) != 0;
2039 bool first_sample_flags_present = (flags & kFirstSampleFlagsPresentMask) != 0;
2040 bool sample_duration_present = (flags & kSampleDurationPresentMask) != 0;
2041 bool sample_size_present = (flags & kSampleSizePresentMask) != 0;
2042 bool sample_flags_present = (flags & kSampleFlagsPresentMask) != 0;
2043 bool sample_composition_time_offsets_present =
2044 (flags & kSampleCompTimeOffsetsPresentMask) != 0;
2046 if (data_offset_present) {
2047 RCHECK(buffer->ReadWriteUInt32(&data_offset));
2058 uint32_t first_sample_flags;
2061 if (first_sample_flags_present)
2062 RCHECK(buffer->ReadWriteUInt32(&first_sample_flags));
2064 if (sample_duration_present)
2065 sample_durations.resize(sample_count);
2066 if (sample_size_present)
2067 sample_sizes.resize(sample_count);
2068 if (sample_flags_present)
2069 sample_flags.resize(sample_count);
2070 if (sample_composition_time_offsets_present)
2071 sample_composition_time_offsets.resize(sample_count);
2073 if (first_sample_flags_present) {
2074 first_sample_flags = sample_flags[0];
2075 DCHECK(sample_flags.size() == 1);
2076 RCHECK(buffer->ReadWriteUInt32(&first_sample_flags));
2079 if (sample_duration_present)
2080 DCHECK(sample_durations.size() == sample_count);
2081 if (sample_size_present)
2082 DCHECK(sample_sizes.size() == sample_count);
2083 if (sample_flags_present)
2084 DCHECK(sample_flags.size() == sample_count);
2085 if (sample_composition_time_offsets_present)
2086 DCHECK(sample_composition_time_offsets.size() == sample_count);
2089 for (uint32_t i = 0; i < sample_count; ++i) {
2090 if (sample_duration_present)
2091 RCHECK(buffer->ReadWriteUInt32(&sample_durations[i]));
2092 if (sample_size_present)
2093 RCHECK(buffer->ReadWriteUInt32(&sample_sizes[i]));
2094 if (sample_flags_present)
2095 RCHECK(buffer->ReadWriteUInt32(&sample_flags[i]));
2097 if (sample_composition_time_offsets_present) {
2099 uint32_t sample_offset = sample_composition_time_offsets[i];
2100 RCHECK(buffer->ReadWriteUInt32(&sample_offset));
2101 sample_composition_time_offsets[i] = sample_offset;
2103 int32_t sample_offset = sample_composition_time_offsets[i];
2104 RCHECK(buffer->ReadWriteInt32(&sample_offset));
2105 sample_composition_time_offsets[i] = sample_offset;
2111 if (first_sample_flags_present) {
2112 if (sample_flags.size() == 0) {
2113 sample_flags.push_back(first_sample_flags);
2115 sample_flags[0] = first_sample_flags;
2122 uint32_t TrackFragmentRun::ComputeSizeInternal() {
2123 uint32_t box_size =
HeaderSize() +
sizeof(sample_count);
2124 if (flags & kDataOffsetPresentMask)
2125 box_size +=
sizeof(data_offset);
2126 if (flags & kFirstSampleFlagsPresentMask)
2127 box_size +=
sizeof(uint32_t);
2128 uint32_t fields = (flags & kSampleDurationPresentMask ? 1 : 0) +
2129 (flags & kSampleSizePresentMask ? 1 : 0) +
2130 (flags & kSampleFlagsPresentMask ? 1 : 0) +
2131 (flags & kSampleCompTimeOffsetsPresentMask ? 1 : 0);
2132 box_size += fields *
sizeof(uint32_t) * sample_count;
2136 SampleToGroup::SampleToGroup() : grouping_type(0), grouping_type_parameter(0) {}
2137 SampleToGroup::~SampleToGroup() {}
2140 bool SampleToGroup::ReadWriteInternal(
BoxBuffer* buffer) {
2142 buffer->ReadWriteUInt32(&grouping_type));
2144 RCHECK(buffer->ReadWriteUInt32(&grouping_type_parameter));
2146 if (grouping_type != FOURCC_SEIG) {
2148 DLOG(WARNING) <<
"Sample group "
2149 << FourCCToString(static_cast<FourCC>(grouping_type))
2150 <<
" is not supported.";
2154 uint32_t count = entries.size();
2155 RCHECK(buffer->ReadWriteUInt32(&count));
2156 entries.resize(count);
2157 for (uint32_t i = 0; i < count; ++i) {
2158 RCHECK(buffer->ReadWriteUInt32(&entries[i].sample_count) &&
2159 buffer->ReadWriteUInt32(&entries[i].group_description_index));
2164 uint32_t SampleToGroup::ComputeSizeInternal() {
2166 if (entries.empty())
2168 return HeaderSize() +
sizeof(grouping_type) +
2169 (version == 1 ?
sizeof(grouping_type_parameter) : 0) +
2170 sizeof(uint32_t) + entries.size() *
sizeof(entries[0]);
2173 CencSampleEncryptionInfoEntry::CencSampleEncryptionInfoEntry()
2174 : is_encrypted(false), iv_size(0) {
2176 CencSampleEncryptionInfoEntry::~CencSampleEncryptionInfoEntry() {};
2178 SampleGroupDescription::SampleGroupDescription() : grouping_type(0) {}
2179 SampleGroupDescription::~SampleGroupDescription() {}
2182 bool SampleGroupDescription::ReadWriteInternal(
BoxBuffer* buffer) {
2184 buffer->ReadWriteUInt32(&grouping_type));
2186 if (grouping_type != FOURCC_SEIG) {
2188 DLOG(WARNING) <<
"Sample group '" << grouping_type <<
"' is not supported.";
2192 const size_t kEntrySize =
sizeof(uint32_t) + kCencKeyIdSize;
2193 uint32_t default_length = 0;
2196 RCHECK(buffer->ReadWriteUInt32(&default_length));
2197 RCHECK(default_length == 0 || default_length >= kEntrySize);
2199 default_length = kEntrySize;
2200 RCHECK(buffer->ReadWriteUInt32(&default_length));
2204 uint32_t count = entries.size();
2205 RCHECK(buffer->ReadWriteUInt32(&count));
2206 entries.resize(count);
2207 for (uint32_t i = 0; i < count; ++i) {
2209 if (buffer->
Reading() && default_length == 0) {
2210 uint32_t description_length = 0;
2211 RCHECK(buffer->ReadWriteUInt32(&description_length));
2212 RCHECK(description_length >= kEntrySize);
2217 if (entries[i].key_id.size() != kCencKeyIdSize) {
2218 LOG(WARNING) <<
"CENC defines key id length of " << kCencKeyIdSize
2219 <<
" bytes; got " << entries[i].key_id.size()
2220 <<
". Resized accordingly.";
2221 entries[i].key_id.resize(kCencKeyIdSize);
2225 uint8_t flag = entries[i].is_encrypted ? 1 : 0;
2227 buffer->ReadWriteUInt8(&flag) &&
2228 buffer->ReadWriteUInt8(&entries[i].iv_size) &&
2229 buffer->ReadWriteVector(&entries[i].key_id, kCencKeyIdSize));
2232 entries[i].is_encrypted = (flag != 0);
2233 if (entries[i].is_encrypted) {
2234 RCHECK(entries[i].iv_size == 8 || entries[i].iv_size == 16);
2236 RCHECK(entries[i].iv_size == 0);
2243 uint32_t SampleGroupDescription::ComputeSizeInternal() {
2247 if (entries.empty())
2249 const size_t kEntrySize =
sizeof(uint32_t) + kCencKeyIdSize;
2250 return HeaderSize() +
sizeof(grouping_type) +
2251 (version == 1 ?
sizeof(uint32_t) : 0) +
sizeof(uint32_t) +
2252 entries.size() * kEntrySize;
2255 TrackFragment::TrackFragment() : decode_time_absent(false) {}
2256 TrackFragment::~TrackFragment() {}
2259 bool TrackFragment::ReadWriteInternal(
BoxBuffer* buffer) {
2264 DCHECK(buffer->
reader());
2266 if (!decode_time_absent)
2274 while (sample_to_group.grouping_type != FOURCC_SEIG &&
2278 while (sample_group_description.grouping_type != FOURCC_SEIG &&
2283 if (!decode_time_absent)
2285 for (uint32_t i = 0; i < runs.size(); ++i)
2295 uint32_t TrackFragment::ComputeSizeInternal() {
2301 for (uint32_t i = 0; i < runs.size(); ++i)
2306 MovieFragment::MovieFragment() {}
2307 MovieFragment::~MovieFragment() {}
2310 bool MovieFragment::ReadWriteInternal(
BoxBuffer* buffer) {
2320 for (uint32_t i = 0; i < tracks.size(); ++i)
2322 for (uint32_t i = 0; i < pssh.size(); ++i)
2328 uint32_t MovieFragment::ComputeSizeInternal() {
2330 for (uint32_t i = 0; i < tracks.size(); ++i)
2332 for (uint32_t i = 0; i < pssh.size(); ++i)
2337 SegmentIndex::SegmentIndex()
2340 earliest_presentation_time(0),
2342 SegmentIndex::~SegmentIndex() {}
2345 bool SegmentIndex::ReadWriteInternal(
BoxBuffer* buffer) {
2347 buffer->ReadWriteUInt32(&reference_id) &&
2348 buffer->ReadWriteUInt32(×cale));
2350 size_t num_bytes = (version == 1) ?
sizeof(uint64_t) :
sizeof(uint32_t);
2355 uint16_t reference_count = references.size();
2357 buffer->ReadWriteUInt16(&reference_count));
2358 references.resize(reference_count);
2360 uint32_t reference_type_size;
2362 for (uint32_t i = 0; i < reference_count; ++i) {
2364 reference_type_size = references[i].referenced_size;
2365 if (references[i].reference_type)
2366 reference_type_size |= (1 << 31);
2367 sap = (references[i].sap_type << 28) | references[i].sap_delta_time;
2368 if (references[i].starts_with_sap)
2371 RCHECK(buffer->ReadWriteUInt32(&reference_type_size) &&
2372 buffer->ReadWriteUInt32(&references[i].subsegment_duration) &&
2373 buffer->ReadWriteUInt32(&sap));
2375 references[i].reference_type = (reference_type_size >> 31) ?
true :
false;
2376 references[i].referenced_size = reference_type_size & ~(1 << 31);
2377 references[i].starts_with_sap = (sap >> 31) ?
true :
false;
2378 references[i].sap_type =
2379 static_cast<SegmentReference::SAPType
>((sap >> 28) & 0x07);
2380 references[i].sap_delta_time = sap & ~(0xF << 28);
2386 uint32_t SegmentIndex::ComputeSizeInternal() {
2387 version = IsFitIn32Bits(earliest_presentation_time, first_offset) ? 0 : 1;
2388 return HeaderSize() +
sizeof(reference_id) +
sizeof(timescale) +
2389 sizeof(uint32_t) * (1 + version) * 2 + 2 *
sizeof(uint16_t) +
2390 3 *
sizeof(uint32_t) * references.size();
2393 MediaData::MediaData() : data_size(0) {}
2394 MediaData::~MediaData() {}
2397 bool MediaData::ReadWriteInternal(
BoxBuffer* buffer) {
2398 NOTIMPLEMENTED() <<
"Actual data is parsed and written separately.";
2402 uint32_t MediaData::ComputeSizeInternal() {
2406 CueSourceIDBox::CueSourceIDBox() : source_id(kCueSourceIdNotSet) {}
2407 CueSourceIDBox::~CueSourceIDBox() {}
2411 bool CueSourceIDBox::ReadWriteInternal(
BoxBuffer* buffer) {
2416 uint32_t CueSourceIDBox::ComputeSizeInternal() {
2417 if (source_id == kCueSourceIdNotSet)
2422 CueTimeBox::CueTimeBox() {}
2423 CueTimeBox::~CueTimeBox() {}
2429 bool CueTimeBox::ReadWriteInternal(
BoxBuffer* buffer) {
2436 uint32_t CueTimeBox::ComputeSizeInternal() {
2437 if (cue_current_time.empty())
2439 return HeaderSize() + cue_current_time.size();
2442 CueIDBox::CueIDBox() {}
2443 CueIDBox::~CueIDBox() {}
2449 bool CueIDBox::ReadWriteInternal(
BoxBuffer* buffer) {
2455 uint32_t CueIDBox::ComputeSizeInternal() {
2461 CueSettingsBox::CueSettingsBox() {}
2462 CueSettingsBox::~CueSettingsBox() {}
2468 bool CueSettingsBox::ReadWriteInternal(
BoxBuffer* buffer) {
2474 uint32_t CueSettingsBox::ComputeSizeInternal() {
2475 if (settings.empty())
2480 CuePayloadBox::CuePayloadBox() {}
2481 CuePayloadBox::~CuePayloadBox() {}
2487 bool CuePayloadBox::ReadWriteInternal(
BoxBuffer* buffer) {
2493 uint32_t CuePayloadBox::ComputeSizeInternal() {
2497 VTTEmptyCueBox::VTTEmptyCueBox() {}
2498 VTTEmptyCueBox::~VTTEmptyCueBox() {}
2504 bool VTTEmptyCueBox::ReadWriteInternal(
BoxBuffer* buffer) {
2508 uint32_t VTTEmptyCueBox::ComputeSizeInternal() {
2512 VTTAdditionalTextBox::VTTAdditionalTextBox() {}
2513 VTTAdditionalTextBox::~VTTAdditionalTextBox() {}
2519 bool VTTAdditionalTextBox::ReadWriteInternal(
BoxBuffer* buffer) {
2522 &cue_additional_text,
2526 uint32_t VTTAdditionalTextBox::ComputeSizeInternal() {
2527 return HeaderSize() + cue_additional_text.size();
2530 VTTCueBox::VTTCueBox() {}
2531 VTTCueBox::~VTTCueBox() {}
2537 bool VTTCueBox::ReadWriteInternal(
BoxBuffer* buffer) {
2548 uint32_t VTTCueBox::ComputeSizeInternal() {
uint32_t ComputeSize() const
FourCC BoxType() const override
FourCC BoxType() const override
FourCC BoxType() const override
FourCC BoxType() const override
bool ParseFromBuffer(uint8_t iv_size, bool has_subsamples, BufferReader *reader)
FourCC BoxType() const override
bool ReadWrite(uint8_t iv_size, bool has_subsamples, BoxBuffer *buffer)
uint32_t GetTotalSizeOfSubsamples() const