// Copyright 2014 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "cobalt/media/formats/mp4/track_run_iterator.h"

#include <memory>
#include <string>

#include "base/basictypes.h"
#include "base/logging.h"
#include "base/strings/string_split.h"
#include "cobalt/media/base/mock_media_log.h"
#include "cobalt/media/formats/mp4/box_definitions.h"
#include "cobalt/media/formats/mp4/rcheck.h"
#include "starboard/memory.h"
#include "starboard/types.h"
#include "testing/gmock/include/gmock/gmock.h"
#include "testing/gtest/include/gtest/gtest.h"

using ::testing::StrictMock;

namespace {

// The sum of the elements in a vector initialized with SumAscending,
// less the value of the last element.
const int kSumAscending1 = 45;

const int kAudioScale = 48000;
const int kVideoScale = 25;

const uint8_t kAuxInfo[] = {
    0x41, 0x54, 0x65, 0x73, 0x74, 0x49, 0x76, 0x31, 0x41, 0x54,
    0x65, 0x73, 0x74, 0x49, 0x76, 0x32, 0x00, 0x02, 0x00, 0x01,
    0x00, 0x00, 0x00, 0x02, 0x00, 0x03, 0x00, 0x00, 0x00, 0x04,
};

// Sample encryption data for two samples, one with 8 byte IV, one with 16 byte
// IV. This data is generated for testing. It should be very unlikely to see
// IV of mixed size in actual media files, though it is permitted by spec.
const uint8_t kSampleEncryptionDataWithSubsamples[] = {
    // Sample count.
    0x00, 0x00, 0x00, 0x02,
    // Sample 1: IV (8 Bytes).
    0x41, 0x54, 0x65, 0x73, 0x74, 0x49, 0x76, 0x31,
    // Sample 1: Subsample count.
    0x00, 0x01,
    // Sample 1: Subsample 1.
    0x00, 0x01, 0x00, 0x00, 0x00, 0x02,
    // Sample 2: IV (16 bytes).
    0x41, 0x54, 0x65, 0x73, 0x74, 0x49, 0x76, 0x32, 0x41, 0x42, 0x43, 0x44,
    0x45, 0x46, 0x47, 0x48,
    // Sample 2: Subsample count.
    0x00, 0x02,
    // Sample 2: Subsample 1.
    0x00, 0x01, 0x00, 0x00, 0x00, 0x02,
    // Sample 2: Subsample 2.
    0x00, 0x03, 0x00, 0x00, 0x00, 0x04,
};

const uint8_t kSampleEncryptionDataWithoutSubsamples[] = {
    // Sample count.
    0x00, 0x00, 0x00, 0x02,
    // Sample 1: IV.
    0x41, 0x54, 0x65, 0x73, 0x74, 0x49, 0x76, 0x31,
    // Sample 2: IV.
    0x41, 0x54, 0x65, 0x73, 0x74, 0x49, 0x76, 0x32,
};

// Size of these two IVs are 8 bytes. They are padded with 0 to 16 bytes.
const char kIv1[] = {
    0x41, 0x54, 0x65, 0x73, 0x74, 0x49, 0x76, 0x31,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
};
const char kIv2[] = {
    0x41, 0x54, 0x65, 0x73, 0x74, 0x49, 0x76, 0x32,
    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
};
// Size of this IV is 16 bytes.
const char kIv3[] = {
    0x41, 0x54, 0x65, 0x73, 0x74, 0x49, 0x76, 0x32,
    0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47, 0x48,
};

const uint8_t kKeyId[] = {
    0x41, 0x47, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x54,
    0x65, 0x73, 0x74, 0x4b, 0x65, 0x79, 0x49, 0x44,
};

const uint8_t kTrackCencSampleGroupKeyId[] = {
    0x46, 0x72, 0x61, 0x67, 0x53, 0x61, 0x6d, 0x70,
    0x6c, 0x65, 0x47, 0x72, 0x6f, 0x75, 0x70, 0x4b,
};

const uint8_t kFragmentCencSampleGroupKeyId[] = {
    0x6b, 0x46, 0x72, 0x61, 0x67, 0x6d, 0x65, 0x6e,
    0x74, 0x43, 0x65, 0x6e, 0x63, 0x53, 0x61, 0x6d,
};

// Sample encryption data for two samples, using constant IV (defined by 'tenc'
// or sample group entry).
const uint8_t kSampleEncryptionDataWithSubsamplesAndConstantIv[] = {
    // Sample count.
    0x00, 0x00, 0x00, 0x05,
    // Sample 1: Subsample count.
    0x00, 0x01,
    // Sample 1: Subsample 1.
    0x00, 0x01, 0x00, 0x00, 0x00, 0x02,
    // Sample 2: Subsample count.
    0x00, 0x02,
    // Sample 2: Subsample 1.
    0x00, 0x01, 0x00, 0x00, 0x00, 0x02,
    // Sample 2: Subsample 2.
    0x00, 0x03, 0x00, 0x00, 0x00, 0x04,
    // Sample 3: Subsample count.
    0x00, 0x01,
    // Sample 3: Subsample 1.
    0x00, 0x01, 0x00, 0x00, 0x00, 0x02,
    // Sample 4: Subsample count.
    0x00, 0x01,
    // Sample 4: Subsample 1.
    0x00, 0x01, 0x00, 0x00, 0x00, 0x02,
    // Sample 5: Subsample count.
    0x00, 0x01,
    // Sample 5: Subsample 1.
    0x00, 0x01, 0x00, 0x00, 0x00, 0x02,
};

// Size of these IVs are 16 bytes.
const char kIv4[] = {
    0x41, 0x54, 0x65, 0x73, 0x74, 0x49, 0x76, 0x34,
    0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47, 0x48,
};

const char kIv5[] = {
    0x41, 0x54, 0x65, 0x73, 0x74, 0x49, 0x76, 0x35,
    0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47, 0x48,
};

}  // namespace

namespace cobalt {
namespace media {
namespace mp4 {

MATCHER(ReservedValueInSampleDependencyInfo, "") {
  return CONTAINS_STRING(arg, "Reserved value used in sample dependency info.");
}

class TrackRunIteratorTest : public testing::Test {
 public:
  TrackRunIteratorTest() : media_log_(new StrictMock<MockMediaLog>()) {
    CreateMovie();
  }

 protected:
  Movie moov_;
  scoped_refptr<StrictMock<MockMediaLog>> media_log_;
  std::unique_ptr<TrackRunIterator> iter_;

  void CreateMovie() {
    moov_.header.timescale = 1000;
    moov_.tracks.resize(3);
    moov_.extends.tracks.resize(2);
    moov_.tracks[0].header.track_id = 1;
    moov_.tracks[0].media.header.timescale = kAudioScale;
    SampleDescription& desc1 =
        moov_.tracks[0].media.information.sample_table.description;
    AudioSampleEntry aud_desc;
    aud_desc.format = FOURCC_MP4A;
    aud_desc.sinf.info.track_encryption.is_encrypted = false;
    desc1.type = kAudio;
    desc1.audio_entries.push_back(aud_desc);
    moov_.extends.tracks[0].track_id = 1;
    moov_.extends.tracks[0].default_sample_description_index = 1;
    moov_.tracks[1].header.track_id = 2;
    moov_.tracks[1].media.header.timescale = kVideoScale;
    SampleDescription& desc2 =
        moov_.tracks[1].media.information.sample_table.description;
    VideoSampleEntry vid_desc;
    vid_desc.format = FOURCC_AVC1;
    vid_desc.sinf.info.track_encryption.is_encrypted = false;
    desc2.type = kVideo;
    desc2.video_entries.push_back(vid_desc);
    moov_.extends.tracks[1].track_id = 2;
    moov_.extends.tracks[1].default_sample_description_index = 1;

    moov_.tracks[2].header.track_id = 3;
    moov_.tracks[2].media.information.sample_table.description.type = kHint;
  }

  uint32_t ToSampleFlags(const std::string& str) {
    CHECK_EQ(str.length(), 2u);

    SampleDependsOn sample_depends_on = kSampleDependsOnReserved;
    bool is_non_sync_sample = false;
    switch (str[0]) {
      case 'U':
        sample_depends_on = kSampleDependsOnUnknown;
        break;
      case 'O':
        sample_depends_on = kSampleDependsOnOthers;
        break;
      case 'N':
        sample_depends_on = kSampleDependsOnNoOther;
        break;
      case 'R':
        sample_depends_on = kSampleDependsOnReserved;
        break;
      default:
        CHECK(false) << "Invalid sample dependency character '" << str[0]
                     << "'";
        break;
    }

    switch (str[1]) {
      case 'S':
        is_non_sync_sample = false;
        break;
      case 'N':
        is_non_sync_sample = true;
        break;
      default:
        CHECK(false) << "Invalid sync sample character '" << str[1] << "'";
        break;
    }
    uint32_t flags = static_cast<uint32_t>(sample_depends_on) << 24;
    if (is_non_sync_sample) flags |= kSampleIsNonSyncSample;
    return flags;
  }

  void SetFlagsOnSamples(const std::string& sample_info,
                         TrackFragmentRun* trun) {
    // US - SampleDependsOnUnknown & IsSyncSample
    // UN - SampleDependsOnUnknown & IsNonSyncSample
    // OS - SampleDependsOnOthers & IsSyncSample
    // ON - SampleDependsOnOthers & IsNonSyncSample
    // NS - SampleDependsOnNoOthers & IsSyncSample
    // NN - SampleDependsOnNoOthers & IsNonSyncSample
    std::vector<std::string> flags_data = base::SplitString(
        sample_info, " ", base::TRIM_WHITESPACE, base::SPLIT_WANT_ALL);

    if (flags_data.size() == 1u) {
      // Simulates the first_sample_flags_present set scenario,
      // where only one sample_flag value is set and the default
      // flags are used for everything else.
      ASSERT_GE(trun->sample_count, flags_data.size());
    } else {
      ASSERT_EQ(trun->sample_count, flags_data.size());
    }

    trun->sample_flags.resize(flags_data.size());
    for (size_t i = 0; i < flags_data.size(); i++)
      trun->sample_flags[i] = ToSampleFlags(flags_data[i]);
  }

  std::string KeyframeAndRAPInfo(TrackRunIterator* iter) {
    CHECK(iter->IsRunValid());
    std::stringstream ss;
    ss << iter->track_id();

    while (iter->IsSampleValid()) {
      ss << " " << (iter->is_keyframe() ? "K" : "P");
      iter->AdvanceSample();
    }

    return ss.str();
  }

  MovieFragment CreateFragment() {
    MovieFragment moof;
    moof.tracks.resize(2);
    moof.tracks[0].decode_time.decode_time = 0;
    moof.tracks[0].header.track_id = 1;
    moof.tracks[0].header.has_default_sample_flags = true;
    moof.tracks[0].header.default_sample_flags = ToSampleFlags("US");
    moof.tracks[0].header.default_sample_duration = 1024;
    moof.tracks[0].header.default_sample_size = 4;
    moof.tracks[0].runs.resize(2);
    moof.tracks[0].runs[0].sample_count = 10;
    moof.tracks[0].runs[0].data_offset = 100;
    SetAscending(&moof.tracks[0].runs[0].sample_sizes);

    moof.tracks[0].runs[1].sample_count = 10;
    moof.tracks[0].runs[1].data_offset = 10000;

    moof.tracks[1].header.track_id = 2;
    moof.tracks[1].header.has_default_sample_flags = false;
    moof.tracks[1].decode_time.decode_time = 10;
    moof.tracks[1].runs.resize(1);
    moof.tracks[1].runs[0].sample_count = 10;
    moof.tracks[1].runs[0].data_offset = 200;
    SetAscending(&moof.tracks[1].runs[0].sample_sizes);
    SetAscending(&moof.tracks[1].runs[0].sample_durations);
    SetFlagsOnSamples("US UN UN UN UN UN UN UN UN UN", &moof.tracks[1].runs[0]);

    return moof;
  }

  ProtectionSchemeInfo* GetProtectionSchemeInfoForTrack(Track* track) {
    SampleDescription* stsd =
        &track->media.information.sample_table.description;
    ProtectionSchemeInfo* sinf;
    if (!stsd->video_entries.empty()) {
      sinf = &stsd->video_entries[0].sinf;
    } else {
      sinf = &stsd->audio_entries[0].sinf;
    }
    return sinf;
  }

  // Update the first sample description of a Track to indicate CENC encryption
  void AddEncryption(Track* track) {
    ProtectionSchemeInfo* sinf = GetProtectionSchemeInfoForTrack(track);
    sinf->type.type = FOURCC_CENC;
    sinf->info.track_encryption.is_encrypted = true;
    sinf->info.track_encryption.default_iv_size = 8;
    sinf->info.track_encryption.default_kid.assign(kKeyId,
                                                   kKeyId + arraysize(kKeyId));
  }

  // Add SampleGroupDescription Box to track level sample table and to
  // fragment. Populate SampleToGroup Box from input array.
  void AddCencSampleGroup(Track* track, TrackFragment* frag,
                          const SampleToGroupEntry* sample_to_group_entries,
                          size_t num_entries) {
    auto& track_cenc_group =
        track->media.information.sample_table.sample_group_description;
    track_cenc_group.grouping_type = FOURCC_SEIG;
    track_cenc_group.entries.resize(1);
    track_cenc_group.entries[0].is_encrypted = true;
    track_cenc_group.entries[0].iv_size = 8;
    track_cenc_group.entries[0].key_id.assign(
        kTrackCencSampleGroupKeyId,
        kTrackCencSampleGroupKeyId + arraysize(kTrackCencSampleGroupKeyId));

    frag->sample_group_description.grouping_type = FOURCC_SEIG;
    frag->sample_group_description.entries.resize(3);
    frag->sample_group_description.entries[0].is_encrypted = false;
    frag->sample_group_description.entries[0].iv_size = 0;
    frag->sample_group_description.entries[1].is_encrypted = true;
    frag->sample_group_description.entries[1].iv_size = 8;
    frag->sample_group_description.entries[1].key_id.assign(
        kFragmentCencSampleGroupKeyId,
        kFragmentCencSampleGroupKeyId +
            arraysize(kFragmentCencSampleGroupKeyId));
    frag->sample_group_description.entries[2].is_encrypted = true;
    frag->sample_group_description.entries[2].iv_size = 16;
    frag->sample_group_description.entries[2].key_id.assign(
        kKeyId, kKeyId + arraysize(kKeyId));

    frag->sample_to_group.grouping_type = FOURCC_SEIG;
    frag->sample_to_group.entries.assign(sample_to_group_entries,
                                         sample_to_group_entries + num_entries);
  }

  // Add aux info covering the first track run to a TrackFragment, and update
  // the run to ensure it matches length and subsample information.
  void AddAuxInfoHeaders(int offset, TrackFragment* frag) {
    frag->auxiliary_offset.offsets.push_back(offset);
    frag->auxiliary_size.sample_count = 2;
    frag->auxiliary_size.sample_info_sizes.push_back(8);
    frag->auxiliary_size.sample_info_sizes.push_back(22);
    frag->runs[0].sample_count = 2;
    frag->runs[0].sample_sizes[1] = 10;
  }

  void AddSampleEncryption(uint8_t use_subsample_flag, TrackFragment* frag) {
    frag->sample_encryption.use_subsample_encryption = use_subsample_flag;
    if (use_subsample_flag) {
      frag->sample_encryption.sample_encryption_data.assign(
          kSampleEncryptionDataWithSubsamples,
          kSampleEncryptionDataWithSubsamples +
              arraysize(kSampleEncryptionDataWithSubsamples));
    } else {
      frag->sample_encryption.sample_encryption_data.assign(
          kSampleEncryptionDataWithoutSubsamples,
          kSampleEncryptionDataWithoutSubsamples +
              arraysize(kSampleEncryptionDataWithoutSubsamples));
    }

    // Update sample sizes and aux info header.
    frag->runs.resize(1);
    frag->runs[0].sample_count = 2;
    frag->auxiliary_offset.offsets.push_back(0);
    frag->auxiliary_size.sample_count = 2;
    if (use_subsample_flag) {
      // Update sample sizes to match with subsample entries above.
      frag->runs[0].sample_sizes[0] = 3;
      frag->runs[0].sample_sizes[1] = 10;
      // Set aux info header.
      frag->auxiliary_size.sample_info_sizes.push_back(16);
      frag->auxiliary_size.sample_info_sizes.push_back(30);
    } else {
      frag->auxiliary_size.default_sample_info_size = 8;
    }
  }

  // Update the first sample description of a Track to indicate CBCS encryption
  // with a constant IV and pattern.
  void AddEncryptionCbcs(Track* track) {
    ProtectionSchemeInfo* sinf = GetProtectionSchemeInfoForTrack(track);
    sinf->type.type = FOURCC_CBCS;
    sinf->info.track_encryption.is_encrypted = true;
    sinf->info.track_encryption.default_iv_size = 0;
    sinf->info.track_encryption.default_crypt_byte_block = 1;
    sinf->info.track_encryption.default_skip_byte_block = 9;
    sinf->info.track_encryption.default_constant_iv_size = 16;
    SbMemoryCopy(sinf->info.track_encryption.default_constant_iv, kIv3, 16);
    sinf->info.track_encryption.default_kid.assign(kKeyId,
                                                   kKeyId + arraysize(kKeyId));
  }

  void AddConstantIvsToCencSampleGroup(Track* track, TrackFragment* frag) {
    auto& track_cenc_group =
        track->media.information.sample_table.sample_group_description;
    track_cenc_group.entries[0].iv_size = 0;
    track_cenc_group.entries[0].crypt_byte_block = 1;
    track_cenc_group.entries[0].skip_byte_block = 9;
    track_cenc_group.entries[0].constant_iv_size = 16;
    SbMemoryCopy(track_cenc_group.entries[0].constant_iv, kIv4, 16);

    frag->sample_group_description.entries[1].iv_size = 0;
    frag->sample_group_description.entries[1].crypt_byte_block = 1;
    frag->sample_group_description.entries[1].skip_byte_block = 9;
    frag->sample_group_description.entries[1].constant_iv_size = 16;
    SbMemoryCopy(frag->sample_group_description.entries[1].constant_iv, kIv5,
                 16);
    frag->sample_group_description.entries[2].iv_size = 0;
    frag->sample_group_description.entries[2].crypt_byte_block = 1;
    frag->sample_group_description.entries[2].skip_byte_block = 9;
    frag->sample_group_description.entries[2].constant_iv_size = 16;
    SbMemoryCopy(frag->sample_group_description.entries[2].constant_iv, kIv5,
                 16);
  }

  void AddSampleEncryptionCbcs(TrackFragment* frag) {
    frag->sample_encryption.use_subsample_encryption = true;
    frag->sample_encryption.sample_encryption_data.assign(
        kSampleEncryptionDataWithSubsamplesAndConstantIv,
        kSampleEncryptionDataWithSubsamplesAndConstantIv +
            arraysize(kSampleEncryptionDataWithSubsamplesAndConstantIv));

    // Update sample sizes and aux info header.
    frag->runs.resize(1);
    frag->runs[0].sample_count = 5;
    frag->auxiliary_offset.offsets.push_back(0);
    frag->auxiliary_size.sample_count = 5;
    // Update sample sizes to match with subsample entries above.
    frag->runs[0].sample_sizes[0] = 3;
    frag->runs[0].sample_sizes[1] = 10;
    frag->runs[0].sample_sizes[2] = 3;
    frag->runs[0].sample_sizes[3] = 3;
    frag->runs[0].sample_sizes[4] = 3;
    // Set aux info header.
    frag->auxiliary_size.sample_info_sizes.push_back(16);
    frag->auxiliary_size.sample_info_sizes.push_back(30);
    frag->auxiliary_size.sample_info_sizes.push_back(16);
    frag->auxiliary_size.sample_info_sizes.push_back(16);
    frag->auxiliary_size.sample_info_sizes.push_back(16);
  }

  bool InitMoofWithArbitraryAuxInfo(MovieFragment* moof) {
    // Add aux info header (equal sized aux info for every sample).
    for (uint32_t i = 0; i < moof->tracks.size(); ++i) {
      moof->tracks[i].auxiliary_offset.offsets.push_back(50);
      moof->tracks[i].auxiliary_size.sample_count = 10;
      moof->tracks[i].auxiliary_size.default_sample_info_size = 8;
    }

    // We don't care about the actual data in aux.
    std::vector<uint8_t> aux_info(1000);
    return iter_->Init(*moof) &&
           iter_->CacheAuxInfo(&aux_info[0], aux_info.size());
  }

  void SetAscending(std::vector<uint32_t>* vec) {
    vec->resize(10);
    for (size_t i = 0; i < vec->size(); i++) (*vec)[i] = i + 1;
  }
};

TEST_F(TrackRunIteratorTest, NoRunsTest) {
  iter_.reset(new TrackRunIterator(&moov_, media_log_));
  ASSERT_TRUE(iter_->Init(MovieFragment()));
  EXPECT_FALSE(iter_->IsRunValid());
  EXPECT_FALSE(iter_->IsSampleValid());
}

TEST_F(TrackRunIteratorTest, BasicOperationTest) {
  iter_.reset(new TrackRunIterator(&moov_, media_log_));
  MovieFragment moof = CreateFragment();

  // Test that runs are sorted correctly, and that properties of the initial
  // sample of the first run are correct
  ASSERT_TRUE(iter_->Init(moof));
  EXPECT_TRUE(iter_->IsRunValid());
  EXPECT_FALSE(iter_->is_encrypted());
  EXPECT_EQ(iter_->track_id(), 1u);
  EXPECT_EQ(iter_->sample_offset(), 100);
  EXPECT_EQ(iter_->sample_size(), 1);
  EXPECT_EQ(iter_->dts(), DecodeTimestampFromRational(0, kAudioScale));
  EXPECT_EQ(iter_->cts(), TimeDeltaFromRational(0, kAudioScale));
  EXPECT_EQ(iter_->duration(), TimeDeltaFromRational(1024, kAudioScale));
  EXPECT_TRUE(iter_->is_keyframe());

  // Advance to the last sample in the current run, and test its properties
  for (int i = 0; i < 9; i++) iter_->AdvanceSample();
  EXPECT_EQ(iter_->track_id(), 1u);
  EXPECT_EQ(iter_->sample_offset(), 100 + kSumAscending1);
  EXPECT_EQ(iter_->sample_size(), 10);
  EXPECT_EQ(iter_->dts(), DecodeTimestampFromRational(1024 * 9, kAudioScale));
  EXPECT_EQ(iter_->duration(), TimeDeltaFromRational(1024, kAudioScale));
  EXPECT_TRUE(iter_->is_keyframe());

  // Test end-of-run
  iter_->AdvanceSample();
  EXPECT_FALSE(iter_->IsSampleValid());

  // Test last sample of next run
  iter_->AdvanceRun();
  EXPECT_TRUE(iter_->is_keyframe());
  for (int i = 0; i < 9; i++) iter_->AdvanceSample();
  EXPECT_EQ(iter_->track_id(), 2u);
  EXPECT_EQ(iter_->sample_offset(), 200 + kSumAscending1);
  EXPECT_EQ(iter_->sample_size(), 10);
  int64_t base_dts = kSumAscending1 + moof.tracks[1].decode_time.decode_time;
  EXPECT_EQ(iter_->dts(), DecodeTimestampFromRational(base_dts, kVideoScale));
  EXPECT_EQ(iter_->duration(), TimeDeltaFromRational(10, kVideoScale));
  EXPECT_FALSE(iter_->is_keyframe());

  // Test final run
  iter_->AdvanceRun();
  EXPECT_EQ(iter_->track_id(), 1u);
  EXPECT_EQ(iter_->dts(), DecodeTimestampFromRational(1024 * 10, kAudioScale));
  iter_->AdvanceSample();
  EXPECT_EQ(moof.tracks[0].runs[1].data_offset +
                moof.tracks[0].header.default_sample_size,
            iter_->sample_offset());
  iter_->AdvanceRun();
  EXPECT_FALSE(iter_->IsRunValid());
}

TEST_F(TrackRunIteratorTest, TrackExtendsDefaultsTest) {
  moov_.extends.tracks[0].default_sample_duration = 50;
  moov_.extends.tracks[0].default_sample_size = 3;
  moov_.extends.tracks[0].default_sample_flags = ToSampleFlags("UN");
  iter_.reset(new TrackRunIterator(&moov_, media_log_));
  MovieFragment moof = CreateFragment();
  moof.tracks[0].header.has_default_sample_flags = false;
  moof.tracks[0].header.default_sample_size = 0;
  moof.tracks[0].header.default_sample_duration = 0;
  moof.tracks[0].runs[0].sample_sizes.clear();
  ASSERT_TRUE(iter_->Init(moof));
  iter_->AdvanceSample();
  EXPECT_FALSE(iter_->is_keyframe());
  EXPECT_EQ(iter_->sample_size(), 3);
  EXPECT_EQ(iter_->sample_offset(), moof.tracks[0].runs[0].data_offset + 3);
  EXPECT_EQ(iter_->duration(), TimeDeltaFromRational(50, kAudioScale));
  EXPECT_EQ(iter_->dts(), DecodeTimestampFromRational(50, kAudioScale));
}

TEST_F(TrackRunIteratorTest, FirstSampleFlagTest) {
  // Ensure that keyframes are flagged correctly in the face of BMFF boxes which
  // explicitly specify the flags for the first sample in a run and rely on
  // defaults for all subsequent samples
  iter_.reset(new TrackRunIterator(&moov_, media_log_));
  MovieFragment moof = CreateFragment();
  moof.tracks[1].header.has_default_sample_flags = true;
  moof.tracks[1].header.default_sample_flags = ToSampleFlags("UN");
  SetFlagsOnSamples("US", &moof.tracks[1].runs[0]);

  ASSERT_TRUE(iter_->Init(moof));
  EXPECT_EQ("1 K K K K K K K K K K", KeyframeAndRAPInfo(iter_.get()));

  iter_->AdvanceRun();
  EXPECT_EQ("2 K P P P P P P P P P", KeyframeAndRAPInfo(iter_.get()));
}

// Verify that parsing fails if a reserved value is in the sample flags.
TEST_F(TrackRunIteratorTest, SampleInfoTest_ReservedInSampleFlags) {
  EXPECT_MEDIA_LOG(ReservedValueInSampleDependencyInfo());
  iter_.reset(new TrackRunIterator(&moov_, media_log_));
  MovieFragment moof = CreateFragment();
  // Change the "depends on" field on one of the samples to a
  // reserved value.
  moof.tracks[1].runs[0].sample_flags[0] = ToSampleFlags("RS");
  ASSERT_FALSE(iter_->Init(moof));
}

// Verify that parsing fails if a reserved value is in the default sample flags.
TEST_F(TrackRunIteratorTest, SampleInfoTest_ReservedInDefaultSampleFlags) {
  EXPECT_MEDIA_LOG(ReservedValueInSampleDependencyInfo());
  iter_.reset(new TrackRunIterator(&moov_, media_log_));
  MovieFragment moof = CreateFragment();
  // Set the default flag to contain a reserved "depends on" value.
  moof.tracks[0].header.default_sample_flags = ToSampleFlags("RN");
  ASSERT_FALSE(iter_->Init(moof));
}

TEST_F(TrackRunIteratorTest, ReorderingTest) {
  // Test frame reordering and edit list support. The frames have the following
  // decode timestamps:
  //
  //   0ms 40ms   120ms     240ms
  //   | 0 | 1  - | 2  -  - |
  //
  // ...and these composition timestamps, after edit list adjustment:
  //
  //   0ms 40ms       160ms  240ms
  //   | 0 | 2  -  -  | 1 - |

  // Create an edit list with one entry, with an initial start time of 80ms
  // (that is, 2 / kVideoTimescale) and a duration of zero (which is treated as
  // infinite according to 14496-12:2012). This will cause the first 80ms of the
  // media timeline - which will be empty, due to CTS biasing - to be discarded.
  iter_.reset(new TrackRunIterator(&moov_, media_log_));
  EditListEntry entry;
  entry.segment_duration = 0;
  entry.media_time = 2;
  entry.media_rate_integer = 1;
  entry.media_rate_fraction = 0;
  moov_.tracks[1].edit.list.edits.push_back(entry);

  // Add CTS offsets. Without bias, the CTS offsets for the first three frames
  // would simply be [0, 3, -2]. Since CTS offsets should be non-negative for
  // maximum compatibility, these values are biased up to [2, 5, 0], and the
  // extra 80ms is removed via the edit list.
  MovieFragment moof = CreateFragment();
  std::vector<int32_t>& cts_offsets =
      moof.tracks[1].runs[0].sample_composition_time_offsets;
  cts_offsets.resize(10);
  cts_offsets[0] = 2;
  cts_offsets[1] = 5;
  cts_offsets[2] = 0;
  moof.tracks[1].decode_time.decode_time = 0;

  ASSERT_TRUE(iter_->Init(moof));
  iter_->AdvanceRun();
  EXPECT_EQ(iter_->dts(), DecodeTimestampFromRational(0, kVideoScale));
  EXPECT_EQ(iter_->cts(), TimeDeltaFromRational(0, kVideoScale));
  EXPECT_EQ(iter_->duration(), TimeDeltaFromRational(1, kVideoScale));
  iter_->AdvanceSample();
  EXPECT_EQ(iter_->dts(), DecodeTimestampFromRational(1, kVideoScale));
  EXPECT_EQ(iter_->cts(), TimeDeltaFromRational(4, kVideoScale));
  EXPECT_EQ(iter_->duration(), TimeDeltaFromRational(2, kVideoScale));
  iter_->AdvanceSample();
  EXPECT_EQ(iter_->dts(), DecodeTimestampFromRational(3, kVideoScale));
  EXPECT_EQ(iter_->cts(), TimeDeltaFromRational(1, kVideoScale));
  EXPECT_EQ(iter_->duration(), TimeDeltaFromRational(3, kVideoScale));
}

TEST_F(TrackRunIteratorTest, IgnoreUnknownAuxInfoTest) {
  iter_.reset(new TrackRunIterator(&moov_, media_log_));
  MovieFragment moof = CreateFragment();
  moof.tracks[1].auxiliary_offset.offsets.push_back(50);
  moof.tracks[1].auxiliary_size.default_sample_info_size = 2;
  moof.tracks[1].auxiliary_size.sample_count = 2;
  moof.tracks[1].runs[0].sample_count = 2;
  ASSERT_TRUE(iter_->Init(moof));
  iter_->AdvanceRun();
  EXPECT_FALSE(iter_->AuxInfoNeedsToBeCached());
}

TEST_F(TrackRunIteratorTest,
       DecryptConfigTestWithSampleEncryptionAndNoSubsample) {
  AddEncryption(&moov_.tracks[1]);
  iter_.reset(new TrackRunIterator(&moov_, media_log_));

  MovieFragment moof = CreateFragment();
  AddSampleEncryption(!SampleEncryption::kUseSubsampleEncryption,
                      &moof.tracks[1]);

  ASSERT_TRUE(iter_->Init(moof));
  // The run for track 2 will be the second, which is parsed according to
  // data_offset.
  iter_->AdvanceRun();
  EXPECT_EQ(iter_->track_id(), 2u);

  EXPECT_TRUE(iter_->is_encrypted());
  // No need to cache aux info as it is already available in SampleEncryption.
  EXPECT_FALSE(iter_->AuxInfoNeedsToBeCached());
  EXPECT_EQ(iter_->aux_info_size(), 0);
  EXPECT_EQ(iter_->sample_offset(), 200);
  EXPECT_EQ(iter_->GetMaxClearOffset(), moof.tracks[1].runs[0].data_offset);
  std::unique_ptr<DecryptConfig> config = iter_->GetDecryptConfig();
  EXPECT_EQ(
      std::string(reinterpret_cast<const char*>(kKeyId), arraysize(kKeyId)),
      config->key_id());
  EXPECT_EQ(std::string(reinterpret_cast<const char*>(kIv1), arraysize(kIv1)),
            config->iv());
  EXPECT_EQ(config->subsamples().size(), 0u);
  iter_->AdvanceSample();
  config = iter_->GetDecryptConfig();
  EXPECT_EQ(std::string(reinterpret_cast<const char*>(kIv2), arraysize(kIv2)),
            config->iv());
  EXPECT_EQ(config->subsamples().size(), 0u);
}

TEST_F(TrackRunIteratorTest,
       DecryptConfigTestWithSampleEncryptionAndSubsample) {
  AddEncryption(&moov_.tracks[1]);
  iter_.reset(new TrackRunIterator(&moov_, media_log_));

  MovieFragment moof = CreateFragment();
  AddSampleEncryption(SampleEncryption::kUseSubsampleEncryption,
                      &moof.tracks[1]);
  const SampleToGroupEntry kSampleToGroupTable[] = {
      // Associated with the second entry in SampleGroupDescription Box.
      // With Iv size 8 bytes.
      {1, SampleToGroupEntry::kFragmentGroupDescriptionIndexBase + 2},
      // Associated with the third entry in SampleGroupDescription Box.
      // With Iv size 16 bytes.
      {1, SampleToGroupEntry::kFragmentGroupDescriptionIndexBase + 3}};
  AddCencSampleGroup(&moov_.tracks[1], &moof.tracks[1], kSampleToGroupTable,
                     arraysize(kSampleToGroupTable));

  ASSERT_TRUE(iter_->Init(moof));
  // The run for track 2 will be the second, which is parsed according to
  // data_offset.
  iter_->AdvanceRun();
  EXPECT_EQ(iter_->track_id(), 2u);

  EXPECT_TRUE(iter_->is_encrypted());
  // No need to cache aux info as it is already available in SampleEncryption.
  EXPECT_FALSE(iter_->AuxInfoNeedsToBeCached());
  EXPECT_EQ(iter_->aux_info_size(), 0);
  EXPECT_EQ(iter_->sample_offset(), 200);
  EXPECT_EQ(iter_->GetMaxClearOffset(), moof.tracks[1].runs[0].data_offset);
  std::unique_ptr<DecryptConfig> config = iter_->GetDecryptConfig();
  EXPECT_EQ(std::string(reinterpret_cast<const char*>(kIv1), arraysize(kIv1)),
            config->iv());
  EXPECT_EQ(config->subsamples().size(), 1u);
  EXPECT_EQ(config->subsamples()[0].clear_bytes, 1u);
  EXPECT_EQ(config->subsamples()[0].cypher_bytes, 2u);
  iter_->AdvanceSample();
  config = iter_->GetDecryptConfig();
  EXPECT_EQ(std::string(reinterpret_cast<const char*>(kIv3), arraysize(kIv3)),
            config->iv());
  EXPECT_EQ(config->subsamples().size(), 2u);
  EXPECT_EQ(config->subsamples()[0].clear_bytes, 1u);
  EXPECT_EQ(config->subsamples()[0].cypher_bytes, 2u);
  EXPECT_EQ(config->subsamples()[1].clear_bytes, 3u);
  EXPECT_EQ(config->subsamples()[1].cypher_bytes, 4u);
}

TEST_F(TrackRunIteratorTest, DecryptConfigTestWithAuxInfo) {
  AddEncryption(&moov_.tracks[1]);
  iter_.reset(new TrackRunIterator(&moov_, media_log_));

  MovieFragment moof = CreateFragment();
  AddAuxInfoHeaders(50, &moof.tracks[1]);

  ASSERT_TRUE(iter_->Init(moof));

  // The run for track 2 will be first, since its aux info offset is the first
  // element in the file.
  EXPECT_EQ(iter_->track_id(), 2u);
  EXPECT_TRUE(iter_->is_encrypted());
  ASSERT_TRUE(iter_->AuxInfoNeedsToBeCached());
  EXPECT_EQ(static_cast<uint32_t>(iter_->aux_info_size()), arraysize(kAuxInfo));
  EXPECT_EQ(iter_->aux_info_offset(), 50);
  EXPECT_EQ(iter_->GetMaxClearOffset(), 50);
  EXPECT_FALSE(iter_->CacheAuxInfo(NULL, 0));
  EXPECT_FALSE(iter_->CacheAuxInfo(kAuxInfo, 3));
  EXPECT_TRUE(iter_->AuxInfoNeedsToBeCached());
  EXPECT_TRUE(iter_->CacheAuxInfo(kAuxInfo, arraysize(kAuxInfo)));
  EXPECT_FALSE(iter_->AuxInfoNeedsToBeCached());
  EXPECT_EQ(iter_->sample_offset(), 200);
  EXPECT_EQ(iter_->GetMaxClearOffset(), moof.tracks[0].runs[0].data_offset);
  std::unique_ptr<DecryptConfig> config = iter_->GetDecryptConfig();
  EXPECT_EQ(
      std::string(reinterpret_cast<const char*>(kKeyId), arraysize(kKeyId)),
      config->key_id());
  EXPECT_EQ(std::string(reinterpret_cast<const char*>(kIv1), arraysize(kIv1)),
            config->iv());
  EXPECT_TRUE(config->subsamples().empty());
  iter_->AdvanceSample();
  config = iter_->GetDecryptConfig();
  EXPECT_EQ(config->subsamples().size(), 2u);
  EXPECT_EQ(config->subsamples()[0].clear_bytes, 1u);
  EXPECT_EQ(config->subsamples()[1].cypher_bytes, 4u);
}

TEST_F(TrackRunIteratorTest, CencSampleGroupTest) {
  MovieFragment moof = CreateFragment();

  const SampleToGroupEntry kSampleToGroupTable[] = {
      // Associated with the second entry in SampleGroupDescription Box.
      {1, SampleToGroupEntry::kFragmentGroupDescriptionIndexBase + 2},
      // Associated with the first entry in SampleGroupDescription Box.
      {1, SampleToGroupEntry::kFragmentGroupDescriptionIndexBase + 1}};
  AddCencSampleGroup(&moov_.tracks[0], &moof.tracks[0], kSampleToGroupTable,
                     arraysize(kSampleToGroupTable));

  iter_.reset(new TrackRunIterator(&moov_, media_log_));
  ASSERT_TRUE(InitMoofWithArbitraryAuxInfo(&moof));

  std::string cenc_sample_group_key_id(
      kFragmentCencSampleGroupKeyId,
      kFragmentCencSampleGroupKeyId + arraysize(kFragmentCencSampleGroupKeyId));
  // The first sample is encrypted and the second sample is unencrypted.
  EXPECT_TRUE(iter_->is_encrypted());
  EXPECT_EQ(cenc_sample_group_key_id, iter_->GetDecryptConfig()->key_id());
  iter_->AdvanceSample();
  EXPECT_FALSE(iter_->is_encrypted());
}

TEST_F(TrackRunIteratorTest, CencSampleGroupWithTrackEncryptionBoxTest) {
  // Add TrackEncryption Box.
  AddEncryption(&moov_.tracks[0]);

  MovieFragment moof = CreateFragment();

  const SampleToGroupEntry kSampleToGroupTable[] = {
      // Associated with the 2nd entry in fragment SampleGroupDescription Box.
      {2, SampleToGroupEntry::kFragmentGroupDescriptionIndexBase + 2},
      // Associated with the default values specified in TrackEncryption Box.
      {1, 0},
      // Associated with the 1st entry in fragment SampleGroupDescription Box.
      {3, SampleToGroupEntry::kFragmentGroupDescriptionIndexBase + 1},
      // Associated with the 1st entry in track SampleGroupDescription Box.
      {2, 1}};
  AddCencSampleGroup(&moov_.tracks[0], &moof.tracks[0], kSampleToGroupTable,
                     arraysize(kSampleToGroupTable));

  iter_.reset(new TrackRunIterator(&moov_, media_log_));
  ASSERT_TRUE(InitMoofWithArbitraryAuxInfo(&moof));

  std::string track_encryption_key_id(kKeyId, kKeyId + arraysize(kKeyId));
  std::string track_cenc_sample_group_key_id(
      kTrackCencSampleGroupKeyId,
      kTrackCencSampleGroupKeyId + arraysize(kTrackCencSampleGroupKeyId));
  std::string fragment_cenc_sample_group_key_id(
      kFragmentCencSampleGroupKeyId,
      kFragmentCencSampleGroupKeyId + arraysize(kFragmentCencSampleGroupKeyId));

  for (size_t i = 0; i < kSampleToGroupTable[0].sample_count; ++i) {
    EXPECT_TRUE(iter_->is_encrypted());
    EXPECT_EQ(fragment_cenc_sample_group_key_id,
              iter_->GetDecryptConfig()->key_id());
    iter_->AdvanceSample();
  }

  for (size_t i = 0; i < kSampleToGroupTable[1].sample_count; ++i) {
    EXPECT_TRUE(iter_->is_encrypted());
    EXPECT_EQ(track_encryption_key_id, iter_->GetDecryptConfig()->key_id());
    iter_->AdvanceSample();
  }

  for (size_t i = 0; i < kSampleToGroupTable[2].sample_count; ++i) {
    EXPECT_FALSE(iter_->is_encrypted());
    iter_->AdvanceSample();
  }

  for (size_t i = 0; i < kSampleToGroupTable[3].sample_count; ++i) {
    EXPECT_TRUE(iter_->is_encrypted());
    EXPECT_EQ(track_cenc_sample_group_key_id,
              iter_->GetDecryptConfig()->key_id());
    iter_->AdvanceSample();
  }

  // The remaining samples should be associated with the default values
  // specified in TrackEncryption Box.
  EXPECT_TRUE(iter_->is_encrypted());
  EXPECT_EQ(track_encryption_key_id, iter_->GetDecryptConfig()->key_id());
}

// It is legal for aux info blocks to be shared among multiple formats.
TEST_F(TrackRunIteratorTest, SharedAuxInfoTest) {
  AddEncryption(&moov_.tracks[0]);
  AddEncryption(&moov_.tracks[1]);
  iter_.reset(new TrackRunIterator(&moov_, media_log_));

  MovieFragment moof = CreateFragment();
  moof.tracks[0].runs.resize(1);
  AddAuxInfoHeaders(50, &moof.tracks[0]);
  AddAuxInfoHeaders(50, &moof.tracks[1]);
  moof.tracks[0].auxiliary_size.default_sample_info_size = 8;

  ASSERT_TRUE(iter_->Init(moof));
  EXPECT_EQ(iter_->track_id(), 1u);
  EXPECT_EQ(iter_->aux_info_offset(), 50);
  EXPECT_TRUE(iter_->CacheAuxInfo(kAuxInfo, arraysize(kAuxInfo)));
  std::unique_ptr<DecryptConfig> config = iter_->GetDecryptConfig();
  ASSERT_EQ(arraysize(kIv1), config->iv().size());
  EXPECT_TRUE(!SbMemoryCompare(kIv1, config->iv().data(), config->iv().size()));
  iter_->AdvanceSample();
  EXPECT_EQ(iter_->GetMaxClearOffset(), 50);
  iter_->AdvanceRun();
  EXPECT_EQ(iter_->GetMaxClearOffset(), 50);
  EXPECT_EQ(iter_->aux_info_offset(), 50);
  EXPECT_TRUE(iter_->CacheAuxInfo(kAuxInfo, arraysize(kAuxInfo)));
  EXPECT_EQ(iter_->GetMaxClearOffset(), 200);
  ASSERT_EQ(arraysize(kIv1), config->iv().size());
  EXPECT_TRUE(!SbMemoryCompare(kIv1, config->iv().data(), config->iv().size()));
  iter_->AdvanceSample();
  EXPECT_EQ(iter_->GetMaxClearOffset(), 201);
}

// Sensible files are expected to place auxiliary information for a run
// immediately before the main data for that run. Alternative schemes are
// possible, however, including the somewhat reasonable behavior of placing all
// aux info at the head of the 'mdat' box together, and the completely
// unreasonable behavior demonstrated here:
//  byte 50: track 2, run 1 aux info
//  byte 100: track 1, run 1 data
//  byte 200: track 2, run 1 data
//  byte 201: track 1, run 2 aux info (*inside* track 2, run 1 data)
//  byte 10000: track 1, run 2 data
//  byte 20000: track 1, run 1 aux info
TEST_F(TrackRunIteratorTest, UnexpectedOrderingTest) {
  AddEncryption(&moov_.tracks[0]);
  AddEncryption(&moov_.tracks[1]);
  iter_.reset(new TrackRunIterator(&moov_, media_log_));

  MovieFragment moof = CreateFragment();
  AddAuxInfoHeaders(20000, &moof.tracks[0]);
  moof.tracks[0].auxiliary_offset.offsets.push_back(201);
  moof.tracks[0].auxiliary_size.sample_count += 2;
  moof.tracks[0].auxiliary_size.default_sample_info_size = 8;
  moof.tracks[0].runs[1].sample_count = 2;
  AddAuxInfoHeaders(50, &moof.tracks[1]);
  moof.tracks[1].runs[0].sample_sizes[0] = 5;

  ASSERT_TRUE(iter_->Init(moof));
  EXPECT_EQ(iter_->track_id(), 2u);
  EXPECT_EQ(iter_->aux_info_offset(), 50);
  EXPECT_EQ(iter_->sample_offset(), 200);
  EXPECT_TRUE(iter_->CacheAuxInfo(kAuxInfo, arraysize(kAuxInfo)));
  EXPECT_EQ(iter_->GetMaxClearOffset(), 100);
  iter_->AdvanceRun();
  EXPECT_EQ(iter_->track_id(), 1u);
  EXPECT_EQ(iter_->aux_info_offset(), 20000);
  EXPECT_EQ(iter_->sample_offset(), 100);
  EXPECT_TRUE(iter_->CacheAuxInfo(kAuxInfo, arraysize(kAuxInfo)));
  EXPECT_EQ(iter_->GetMaxClearOffset(), 100);
  iter_->AdvanceSample();
  EXPECT_EQ(iter_->GetMaxClearOffset(), 101);
  iter_->AdvanceRun();
  EXPECT_EQ(iter_->track_id(), 1u);
  EXPECT_EQ(iter_->aux_info_offset(), 201);
  EXPECT_EQ(iter_->sample_offset(), 10000);
  EXPECT_EQ(iter_->GetMaxClearOffset(), 201);
  EXPECT_TRUE(iter_->CacheAuxInfo(kAuxInfo, arraysize(kAuxInfo)));
  EXPECT_EQ(iter_->GetMaxClearOffset(), 10000);
}

TEST_F(TrackRunIteratorTest, KeyFrameFlagCombinations) {
  // Setup both audio and video tracks to each have 6 samples covering all the
  // combinations of mp4 "sync sample" and "depends on" relationships.
  MovieFragment moof = CreateFragment();
  moof.tracks[0].runs.resize(1);
  moof.tracks[1].runs.resize(1);
  moof.tracks[0].runs[0].sample_count = 6;
  moof.tracks[1].runs[0].sample_count = 6;
  SetFlagsOnSamples("US UN OS ON NS NN", &moof.tracks[0].runs[0]);
  SetFlagsOnSamples("US UN OS ON NS NN", &moof.tracks[1].runs[0]);
  iter_.reset(new TrackRunIterator(&moov_, media_log_));

  ASSERT_TRUE(iter_->Init(moof));
  EXPECT_TRUE(iter_->IsRunValid());

  // Keyframes should be marked according to downstream's expectations that
  // keyframes serve as points of random access for seeking.

  // For audio, any sync sample should be marked as a key frame. Whether a
  // sample "depends on" other samples is not considered. Unlike video samples,
  // audio samples are often marked as depending on other samples but are still
  // workable for random access. While we allow for parsing of audio samples
  // that are non-sync samples, we generally expect all audio samples to be sync
  // samples and downstream will log and discard any non-sync audio samples.
  EXPECT_EQ("1 K P K P K P", KeyframeAndRAPInfo(iter_.get()));

  iter_->AdvanceRun();

  // For video, any key frame should be both a sync sample and have no known
  // dependents. Ideally, a video sync sample should always be marked as having
  // no dependents, but we occasionally encounter media where all samples are
  // marked "sync" and we must rely on combining the two flags to pick out the
  // true key frames. See http://crbug.com/310712 and http://crbug.com/507916.
  // Reliably knowing the keyframes for video is also critical to SPS PPS
  // insertion.
  EXPECT_EQ("2 K P P P K P", KeyframeAndRAPInfo(iter_.get()));
}

TEST_F(TrackRunIteratorTest, DecryptConfigTestWithConstantIvNoAuxInfo) {
  AddEncryptionCbcs(&moov_.tracks[1]);
  iter_.reset(new TrackRunIterator(&moov_, media_log_));

  MovieFragment moof = CreateFragment();

  ASSERT_TRUE(iter_->Init(moof));

  // The run for track 2 will be the second.
  iter_->AdvanceRun();
  EXPECT_EQ(iter_->track_id(), 2u);
  EXPECT_TRUE(iter_->is_encrypted());
  ASSERT_FALSE(iter_->AuxInfoNeedsToBeCached());
  EXPECT_EQ(iter_->sample_offset(), 200);
  std::unique_ptr<DecryptConfig> config = iter_->GetDecryptConfig();
  EXPECT_EQ(
      std::string(reinterpret_cast<const char*>(kKeyId), arraysize(kKeyId)),
      config->key_id());
  EXPECT_EQ(std::string(reinterpret_cast<const char*>(kIv3), arraysize(kIv3)),
            config->iv());
  EXPECT_TRUE(config->subsamples().empty());
  iter_->AdvanceSample();
  config = iter_->GetDecryptConfig();
  EXPECT_EQ(
      std::string(reinterpret_cast<const char*>(kKeyId), arraysize(kKeyId)),
      config->key_id());
  EXPECT_EQ(std::string(reinterpret_cast<const char*>(kIv3), arraysize(kIv3)),
            config->iv());
  EXPECT_TRUE(config->subsamples().empty());
}

TEST_F(TrackRunIteratorTest, DecryptConfigTestWithSampleGroupsAndConstantIv) {
  // Add TrackEncryption Box.
  AddEncryptionCbcs(&moov_.tracks[1]);

  MovieFragment moof = CreateFragment();
  AddSampleEncryptionCbcs(&moof.tracks[1]);

  const SampleToGroupEntry kSampleToGroupTable[] = {
      // Associated with the 2nd entry in fragment SampleGroupDescription Box.
      {1, SampleToGroupEntry::kFragmentGroupDescriptionIndexBase + 2},
      // Associated with the default values specified in TrackEncryption Box.
      {1, 0},
      // Associated with the 1st entry in fragment SampleGroupDescription Box.
      {1, SampleToGroupEntry::kFragmentGroupDescriptionIndexBase + 1},
      // Associated with the 1st entry in track SampleGroupDescription Box.
      {1, 1}};
  AddCencSampleGroup(&moov_.tracks[1], &moof.tracks[1], kSampleToGroupTable,
                     arraysize(kSampleToGroupTable));
  AddConstantIvsToCencSampleGroup(&moov_.tracks[1], &moof.tracks[1]);
  iter_.reset(new TrackRunIterator(&moov_, media_log_));
  ASSERT_TRUE(iter_->Init(moof));

  // The run for track 2 will be the second.
  iter_->AdvanceRun();

  std::string track_encryption_iv(kIv3, kIv3 + arraysize(kIv3));
  std::string track_cenc_sample_group_iv(kIv4, kIv4 + arraysize(kIv4));
  std::string fragment_cenc_sample_group_iv(kIv5, kIv5 + arraysize(kIv5));

  for (size_t i = 0; i < kSampleToGroupTable[0].sample_count; ++i) {
    EXPECT_TRUE(iter_->is_encrypted());
    EXPECT_EQ(fragment_cenc_sample_group_iv, iter_->GetDecryptConfig()->iv());
    iter_->AdvanceSample();
  }

  for (size_t i = 0; i < kSampleToGroupTable[1].sample_count; ++i) {
    EXPECT_TRUE(iter_->is_encrypted());
    EXPECT_EQ(track_encryption_iv, iter_->GetDecryptConfig()->iv());
    iter_->AdvanceSample();
  }

  for (size_t i = 0; i < kSampleToGroupTable[2].sample_count; ++i) {
    EXPECT_FALSE(iter_->is_encrypted());
    iter_->AdvanceSample();
  }

  for (size_t i = 0; i < kSampleToGroupTable[3].sample_count; ++i) {
    EXPECT_TRUE(iter_->is_encrypted());
    EXPECT_EQ(track_cenc_sample_group_iv, iter_->GetDecryptConfig()->iv());
    iter_->AdvanceSample();
  }

  // The remaining samples should be associated with the default values
  // specified in TrackEncryption Box.
  EXPECT_TRUE(iter_->is_encrypted());
  EXPECT_EQ(track_encryption_iv, iter_->GetDecryptConfig()->iv());
}

}  // namespace mp4
}  // namespace media
}  // namespace cobalt
