Home | History | Annotate | Download | only in filters
      1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
      2 // Use of this source code is governed by a BSD-style license that can be
      3 // found in the LICENSE file.
      4 
      5 #include "base/logging.h"
      6 #include "base/md5.h"
      7 #include "base/memory/scoped_ptr.h"
      8 #include "build/build_config.h"
      9 #include "media/base/audio_bus.h"
     10 #include "media/base/audio_hash.h"
     11 #include "media/base/decoder_buffer.h"
     12 #include "media/base/test_data_util.h"
     13 #include "media/ffmpeg/ffmpeg_common.h"
     14 #include "media/filters/audio_file_reader.h"
     15 #include "media/filters/in_memory_url_protocol.h"
     16 #include "testing/gtest/include/gtest/gtest.h"
     17 
     18 namespace media {
     19 
     20 class AudioFileReaderTest : public testing::Test {
     21  public:
     22   AudioFileReaderTest() : packet_verification_disabled_(false) {}
     23   virtual ~AudioFileReaderTest() {}
     24 
     25   void Initialize(const char* filename) {
     26     data_ = ReadTestDataFile(filename);
     27     protocol_.reset(
     28         new InMemoryUrlProtocol(data_->data(), data_->data_size(), false));
     29     reader_.reset(new AudioFileReader(protocol_.get()));
     30   }
     31 
     32   // Reads and the entire file provided to Initialize().
     33   void ReadAndVerify(const char* expected_audio_hash, int expected_frames) {
     34     scoped_ptr<AudioBus> decoded_audio_data =
     35         AudioBus::Create(reader_->channels(), reader_->GetNumberOfFrames());
     36     int actual_frames = reader_->Read(decoded_audio_data.get());
     37     ASSERT_LE(actual_frames, decoded_audio_data->frames());
     38     ASSERT_EQ(expected_frames, actual_frames);
     39 
     40     AudioHash audio_hash;
     41     audio_hash.Update(decoded_audio_data.get(), actual_frames);
     42     EXPECT_EQ(expected_audio_hash, audio_hash.ToString());
     43   }
     44 
     45   // Verify packets are consistent across demuxer runs.  Reads the first few
     46   // packets and then seeks back to the start timestamp and verifies that the
     47   // hashes match on the packets just read.
     48   void VerifyPackets() {
     49     const int kReads = 3;
     50     const int kTestPasses = 2;
     51 
     52     AVPacket packet;
     53     base::TimeDelta start_timestamp;
     54     std::vector<std::string> packet_md5_hashes_;
     55     for (int i = 0; i < kTestPasses; ++i) {
     56       for (int j = 0; j < kReads; ++j) {
     57         ASSERT_TRUE(reader_->ReadPacketForTesting(&packet));
     58 
     59         // Remove metadata from the packet data section before hashing.
     60         av_packet_split_side_data(&packet);
     61 
     62         // On the first pass save the MD5 hash of each packet, on subsequent
     63         // passes ensure it matches.
     64         const std::string md5_hash = base::MD5String(base::StringPiece(
     65             reinterpret_cast<char*>(packet.data), packet.size));
     66         if (i == 0) {
     67           packet_md5_hashes_.push_back(md5_hash);
     68           if (j == 0) {
     69             start_timestamp = ConvertFromTimeBase(
     70                 reader_->codec_context_for_testing()->time_base, packet.pts);
     71           }
     72         } else {
     73           EXPECT_EQ(packet_md5_hashes_[j], md5_hash) << "j = " << j;
     74         }
     75 
     76         av_free_packet(&packet);
     77       }
     78       ASSERT_TRUE(reader_->SeekForTesting(start_timestamp));
     79     }
     80   }
     81 
     82   void RunTest(const char* fn,
     83                const char* hash,
     84                int channels,
     85                int sample_rate,
     86                base::TimeDelta duration,
     87                int frames,
     88                int trimmed_frames) {
     89     Initialize(fn);
     90     ASSERT_TRUE(reader_->Open());
     91     EXPECT_EQ(channels, reader_->channels());
     92     EXPECT_EQ(sample_rate, reader_->sample_rate());
     93     EXPECT_EQ(duration.InMicroseconds(),
     94               reader_->GetDuration().InMicroseconds());
     95     EXPECT_EQ(frames, reader_->GetNumberOfFrames());
     96     if (!packet_verification_disabled_)
     97       ASSERT_NO_FATAL_FAILURE(VerifyPackets());
     98     ReadAndVerify(hash, trimmed_frames);
     99   }
    100 
    101   void RunTestFailingDemux(const char* fn) {
    102     Initialize(fn);
    103     EXPECT_FALSE(reader_->Open());
    104   }
    105 
    106   void RunTestFailingDecode(const char* fn) {
    107     Initialize(fn);
    108     EXPECT_TRUE(reader_->Open());
    109     scoped_ptr<AudioBus> decoded_audio_data =
    110         AudioBus::Create(reader_->channels(), reader_->GetNumberOfFrames());
    111     EXPECT_EQ(reader_->Read(decoded_audio_data.get()), 0);
    112   }
    113 
    114   void disable_packet_verification() {
    115     packet_verification_disabled_ = true;
    116   }
    117 
    118  protected:
    119   scoped_refptr<DecoderBuffer> data_;
    120   scoped_ptr<InMemoryUrlProtocol> protocol_;
    121   scoped_ptr<AudioFileReader> reader_;
    122   bool packet_verification_disabled_;
    123 
    124   DISALLOW_COPY_AND_ASSIGN(AudioFileReaderTest);
    125 };
    126 
    127 TEST_F(AudioFileReaderTest, WithoutOpen) {
    128   Initialize("bear.ogv");
    129 }
    130 
    131 TEST_F(AudioFileReaderTest, InvalidFile) {
    132   RunTestFailingDemux("ten_byte_file");
    133 }
    134 
    135 TEST_F(AudioFileReaderTest, WithVideo) {
    136   RunTest("bear.ogv",
    137           "-2.49,-0.75,0.38,1.60,0.70,-1.22,",
    138           2,
    139           44100,
    140           base::TimeDelta::FromMicroseconds(1011520),
    141           44609,
    142           44609);
    143 }
    144 
    145 TEST_F(AudioFileReaderTest, Vorbis) {
    146   RunTest("sfx.ogg",
    147           "4.36,4.81,4.84,4.45,4.61,4.63,",
    148           1,
    149           44100,
    150           base::TimeDelta::FromMicroseconds(350001),
    151           15436,
    152           15436);
    153 }
    154 
    155 TEST_F(AudioFileReaderTest, WaveU8) {
    156   RunTest("sfx_u8.wav",
    157           "-1.23,-1.57,-1.14,-0.91,-0.87,-0.07,",
    158           1,
    159           44100,
    160           base::TimeDelta::FromMicroseconds(288414),
    161           12720,
    162           12719);
    163 }
    164 
    165 TEST_F(AudioFileReaderTest, WaveS16LE) {
    166   RunTest("sfx_s16le.wav",
    167           "3.05,2.87,3.00,3.32,3.58,4.08,",
    168           1,
    169           44100,
    170           base::TimeDelta::FromMicroseconds(288414),
    171           12720,
    172           12719);
    173 }
    174 
    175 TEST_F(AudioFileReaderTest, WaveS24LE) {
    176   RunTest("sfx_s24le.wav",
    177           "3.03,2.86,2.99,3.31,3.57,4.06,",
    178           1,
    179           44100,
    180           base::TimeDelta::FromMicroseconds(288414),
    181           12720,
    182           12719);
    183 }
    184 
    185 TEST_F(AudioFileReaderTest, WaveF32LE) {
    186   RunTest("sfx_f32le.wav",
    187           "3.03,2.86,2.99,3.31,3.57,4.06,",
    188           1,
    189           44100,
    190           base::TimeDelta::FromMicroseconds(288414),
    191           12720,
    192           12719);
    193 }
    194 
    195 #if defined(USE_PROPRIETARY_CODECS)
    196 TEST_F(AudioFileReaderTest, MP3) {
    197   RunTest("sfx.mp3",
    198           "5.59,7.11,6.63,6.23,5.58,5.22,",
    199           1,
    200           44100,
    201           base::TimeDelta::FromMicroseconds(313470),
    202           13825,
    203           10496);
    204 }
    205 
    206 TEST_F(AudioFileReaderTest, CorruptMP3) {
    207   // Disable packet verification since the file is corrupt and FFmpeg does not
    208   // make any guarantees on packet consistency in this case.
    209   disable_packet_verification();
    210   RunTest("corrupt.mp3",
    211           "-4.95,-2.95,-0.44,1.16,0.31,-2.21,",
    212           1,
    213           44100,
    214           base::TimeDelta::FromMicroseconds(1018826),
    215           44931,
    216           44928);
    217 }
    218 
    219 TEST_F(AudioFileReaderTest, AAC) {
    220   RunTest("sfx.m4a",
    221           "1.81,1.66,2.32,3.27,4.46,3.36,",
    222           1,
    223           44100,
    224           base::TimeDelta::FromMicroseconds(312001),
    225           13760,
    226           13312);
    227 }
    228 
    229 TEST_F(AudioFileReaderTest, MidStreamConfigChangesFail) {
    230   RunTestFailingDecode("midstream_config_change.mp3");
    231 }
    232 #endif
    233 
    234 TEST_F(AudioFileReaderTest, VorbisInvalidChannelLayout) {
    235   RunTestFailingDemux("9ch.ogg");
    236 }
    237 
    238 TEST_F(AudioFileReaderTest, WaveValidFourChannelLayout) {
    239   RunTest("4ch.wav",
    240           "131.71,38.02,130.31,44.89,135.98,42.52,",
    241           4,
    242           44100,
    243           base::TimeDelta::FromMicroseconds(100001),
    244           4411,
    245           4410);
    246 }
    247 
    248 }  // namespace media
    249