Commit 09e74c42 authored by acolwell@chromium.org's avatar acolwell@chromium.org

Fix channel layout reporting for implicit signalling of AAC parametric stereo


BUG=226642
TEST=AACTest_TestImplicitSBR_ChannelConfig0,AACTest_TestImplicitSBR_ChannelConfig1


Review URL: https://chromiumcodereview.appspot.com/13648007

git-svn-id: svn://svn.chromium.org/chrome/trunk/src@192498 0039d316-1c4b-4281-b951-d872f2087c98
parent bc596c90
......@@ -19,7 +19,7 @@ static const int kFrequencyMap[] = {
namespace media {
static ChannelLayout GetChannelLayout(uint8 channel_config) {
static ChannelLayout ConvertChannelConfigToLayout(uint8 channel_config) {
switch (channel_config) {
case 1:
return CHANNEL_LAYOUT_MONO;
......@@ -130,9 +130,9 @@ bool AAC::Parse(const std::vector<uint8>& data) {
// When Parametric Stereo is on, mono will be played as stereo.
if (ps_present && channel_config_ == 1)
channel_layout_ = GetChannelLayout(2);
channel_layout_ = CHANNEL_LAYOUT_STEREO;
else
channel_layout_ = GetChannelLayout(channel_config_);
channel_layout_ = ConvertChannelConfigToLayout(channel_config_);
return frequency_ != 0 && channel_layout_ != CHANNEL_LAYOUT_UNSUPPORTED &&
profile_ >= 1 && profile_ <= 4 && frequency_index_ != 0xf &&
......@@ -154,7 +154,13 @@ int AAC::GetOutputSamplesPerSecond(bool sbr_in_mimetype) const {
return std::min(2 * frequency_, 48000);
}
ChannelLayout AAC::channel_layout() const {
ChannelLayout AAC::GetChannelLayout(bool sbr_in_mimetype) const {
// Check for implicit signalling of HE-AAC and indicate stereo output
// if the mono channel configuration is signalled.
// See ISO-14496-3 Section 1.6.6.1.2 for details about this special casing.
if (sbr_in_mimetype && channel_config_ == 1)
return CHANNEL_LAYOUT_STEREO;
return channel_layout_;
}
......
......@@ -38,7 +38,13 @@ class MEDIA_EXPORT AAC {
// Returns the samples_per_second value that should used in an
// AudioDecoderConfig.
int GetOutputSamplesPerSecond(bool sbr_in_mimetype) const;
ChannelLayout channel_layout() const;
// Gets the channel layout for the AAC stream.
// |sbr_in_mimetype| should be set to true if the SBR mode is
// signalled in the mimetype. (ie mp4a.40.5 in the codecs parameter).
// Returns the channel_layout value that should used in an
// AudioDecoderConfig.
ChannelLayout GetChannelLayout(bool sbr_in_mimetype) const;
// This function converts a raw AAC frame into an AAC frame with an ADTS
// header. On success, the function returns true and stores the converted data
......
......@@ -19,7 +19,7 @@ TEST(AACTest, BasicProfileTest) {
EXPECT_TRUE(aac.Parse(data));
EXPECT_EQ(aac.GetOutputSamplesPerSecond(false), 44100);
EXPECT_EQ(aac.channel_layout(), CHANNEL_LAYOUT_STEREO);
EXPECT_EQ(aac.GetChannelLayout(false), CHANNEL_LAYOUT_STEREO);
}
TEST(AACTest, ExtensionTest) {
......@@ -32,10 +32,33 @@ TEST(AACTest, ExtensionTest) {
EXPECT_TRUE(aac.Parse(data));
EXPECT_EQ(aac.GetOutputSamplesPerSecond(false), 48000);
EXPECT_EQ(aac.GetOutputSamplesPerSecond(true), 48000);
EXPECT_EQ(aac.channel_layout(), CHANNEL_LAYOUT_STEREO);
EXPECT_EQ(aac.GetChannelLayout(false), CHANNEL_LAYOUT_STEREO);
}
TEST(AACTest, TestImplicitSBR) {
// Test implicit SBR with mono channel config.
// Mono channel layout should only be reported if SBR is not
// specified. Otherwise stereo should be reported.
// See ISO-14496-3 Section 1.6.6.1.2 for details about this special casing.
TEST(AACTest, TestImplicitSBR_ChannelConfig0) {
AAC aac;
uint8 buffer[] = {0x13, 0x08};
std::vector<uint8> data;
data.assign(buffer, buffer + sizeof(buffer));
EXPECT_TRUE(aac.Parse(data));
// Test w/o implict SBR.
EXPECT_EQ(aac.GetOutputSamplesPerSecond(false), 24000);
EXPECT_EQ(aac.GetChannelLayout(false), CHANNEL_LAYOUT_MONO);
// Test implicit SBR.
EXPECT_EQ(aac.GetOutputSamplesPerSecond(true), 48000);
EXPECT_EQ(aac.GetChannelLayout(true), CHANNEL_LAYOUT_STEREO);
}
// Tests implicit SBR with a stereo channel config.
TEST(AACTest, TestImplicitSBR_ChannelConfig1) {
AAC aac;
uint8 buffer[] = {0x13, 0x10};
std::vector<uint8> data;
......@@ -43,9 +66,14 @@ TEST(AACTest, TestImplicitSBR) {
data.assign(buffer, buffer + sizeof(buffer));
EXPECT_TRUE(aac.Parse(data));
// Test w/o implict SBR.
EXPECT_EQ(aac.GetOutputSamplesPerSecond(false), 24000);
EXPECT_EQ(aac.GetChannelLayout(false), CHANNEL_LAYOUT_STEREO);
// Test implicit SBR.
EXPECT_EQ(aac.GetOutputSamplesPerSecond(true), 48000);
EXPECT_EQ(aac.channel_layout(), CHANNEL_LAYOUT_STEREO);
EXPECT_EQ(aac.GetChannelLayout(true), CHANNEL_LAYOUT_STEREO);
}
TEST(AACTest, SixChannelTest) {
......@@ -57,7 +85,7 @@ TEST(AACTest, SixChannelTest) {
EXPECT_TRUE(aac.Parse(data));
EXPECT_EQ(aac.GetOutputSamplesPerSecond(false), 48000);
EXPECT_EQ(aac.channel_layout(), CHANNEL_LAYOUT_5_1);
EXPECT_EQ(aac.GetChannelLayout(false), CHANNEL_LAYOUT_5_1);
}
TEST(AACTest, DataTooShortTest) {
......
......@@ -237,7 +237,7 @@ bool MP4StreamParser::ParseMoov(BoxReader* reader) {
is_audio_track_encrypted_ = entry.sinf.info.track_encryption.is_encrypted;
DVLOG(1) << "is_audio_track_encrypted_: " << is_audio_track_encrypted_;
audio_config.Initialize(kCodecAAC, sample_format,
aac.channel_layout(),
aac.GetChannelLayout(has_sbr_),
aac.GetOutputSamplesPerSecond(has_sbr_),
NULL, 0, is_audio_track_encrypted_, false);
has_audio_ = true;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment