blob: 3b4670ea3e6c82ea0b90cf6882cf7415369720ef [file] [log] [blame]
henrike@webrtc.org79047f92014-03-06 23:46:59 +00001/*
kjellander1afca732016-02-07 20:46:45 -08002 * Copyright (c) 2008 The WebRTC project authors. All Rights Reserved.
henrike@webrtc.org79047f92014-03-06 23:46:59 +00003 *
kjellander1afca732016-02-07 20:46:45 -08004 * Use of this source code is governed by a BSD-style license
5 * that can be found in the LICENSE file in the root of the source
6 * tree. An additional intellectual property rights grant can be found
7 * in the file PATENTS. All contributing project authors may
8 * be found in the AUTHORS file in the root of the source tree.
henrike@webrtc.org79047f92014-03-06 23:46:59 +00009 */
henrike@webrtc.org28e20752013-07-10 00:45:36 +000010
kwiberg686a8ef2016-02-26 03:00:35 -080011#include <memory>
12
kjellander@webrtc.org9b8df252016-02-12 06:47:59 +010013#include "webrtc/pc/channel.h"
tfarina5237aaf2015-11-10 23:44:30 -080014#include "webrtc/base/arraysize.h"
buildbot@webrtc.orgd4e598d2014-07-29 17:36:52 +000015#include "webrtc/base/byteorder.h"
16#include "webrtc/base/gunit.h"
Fredrik Solenberg709ed672015-09-15 12:26:33 +020017#include "webrtc/call.h"
stefanba4c0e42016-02-04 04:12:24 -080018#include "webrtc/p2p/base/faketransportcontroller.h"
19#include "webrtc/test/field_trial.h"
skvlad11a9cbf2016-10-07 11:53:05 -070020#include "webrtc/logging/rtc_event_log/rtc_event_log.h"
kjellandera96e2d72016-02-04 23:52:28 -080021#include "webrtc/media/base/fakemediaengine.h"
22#include "webrtc/media/base/fakenetworkinterface.h"
23#include "webrtc/media/base/fakertp.h"
kjellanderf4752772016-03-02 05:42:30 -080024#include "webrtc/media/base/mediaconstants.h"
kjellander@webrtc.org5ad12972016-02-12 06:39:40 +010025#include "webrtc/media/engine/fakewebrtccall.h"
26#include "webrtc/media/engine/fakewebrtcvoiceengine.h"
27#include "webrtc/media/engine/webrtcvoiceengine.h"
ossu29b1a8d2016-06-13 07:34:51 -070028#include "webrtc/modules/audio_coding/codecs/builtin_audio_decoder_factory.h"
29#include "webrtc/modules/audio_coding/codecs/mock/mock_audio_decoder_factory.h"
solenbergbc37fc82016-04-04 09:54:44 -070030#include "webrtc/modules/audio_device/include/mock_audio_device.h"
solenberg059fb442016-10-26 05:12:24 -070031#include "webrtc/modules/audio_processing/include/mock_audio_processing.h"
henrike@webrtc.org28e20752013-07-10 00:45:36 +000032
solenbergbc37fc82016-04-04 09:54:44 -070033using testing::Return;
34using testing::StrictMock;
buildbot@webrtc.org150835e2014-05-06 15:54:38 +000035
Fredrik Solenberg4f4ec0a2015-10-22 10:49:27 +020036namespace {
37
deadbeef67cf2c12016-04-13 10:07:16 -070038const cricket::AudioCodec kPcmuCodec(0, "PCMU", 8000, 64000, 1);
39const cricket::AudioCodec kIsacCodec(103, "ISAC", 16000, 32000, 1);
40const cricket::AudioCodec kOpusCodec(111, "opus", 48000, 64000, 2);
41const cricket::AudioCodec kG722CodecVoE(9, "G722", 16000, 64000, 1);
42const cricket::AudioCodec kG722CodecSdp(9, "G722", 8000, 64000, 1);
deadbeef67cf2c12016-04-13 10:07:16 -070043const cricket::AudioCodec kCn8000Codec(13, "CN", 8000, 0, 1);
44const cricket::AudioCodec kCn16000Codec(105, "CN", 16000, 0, 1);
solenberg2779bab2016-11-17 04:45:19 -080045const cricket::AudioCodec
46 kTelephoneEventCodec1(106, "telephone-event", 8000, 0, 1);
47const cricket::AudioCodec
48 kTelephoneEventCodec2(107, "telephone-event", 32000, 0, 1);
49
solenberg85a04962015-10-27 03:35:21 -070050const uint32_t kSsrc1 = 0x99;
Taylor Brandstetter1a018dc2016-03-08 12:37:39 -080051const uint32_t kSsrc2 = 2;
52const uint32_t kSsrc3 = 3;
solenberg7602aab2016-11-14 11:30:07 -080053const uint32_t kSsrc4 = 0x42;
solenberg85a04962015-10-27 03:35:21 -070054const uint32_t kSsrcs4[] = { 1, 2, 3, 4 };
henrike@webrtc.org28e20752013-07-10 00:45:36 +000055
solenberg971cab02016-06-14 10:02:41 -070056constexpr int kRtpHistoryMs = 5000;
57
henrike@webrtc.org28e20752013-07-10 00:45:36 +000058class FakeVoEWrapper : public cricket::VoEWrapper {
59 public:
60 explicit FakeVoEWrapper(cricket::FakeWebRtcVoiceEngine* engine)
61 : cricket::VoEWrapper(engine, // processing
62 engine, // base
63 engine, // codec
henrike@webrtc.org28e20752013-07-10 00:45:36 +000064 engine, // hw
henrike@webrtc.org28e20752013-07-10 00:45:36 +000065 engine) { // volume
66 }
67};
skvlad11a9cbf2016-10-07 11:53:05 -070068
Fredrik Solenberg4f4ec0a2015-10-22 10:49:27 +020069} // namespace
henrike@webrtc.org28e20752013-07-10 00:45:36 +000070
solenbergff976312016-03-30 23:28:51 -070071// Tests that our stub library "works".
72TEST(WebRtcVoiceEngineTestStubLibrary, StartupShutdown) {
solenbergbc37fc82016-04-04 09:54:44 -070073 StrictMock<webrtc::test::MockAudioDeviceModule> adm;
74 EXPECT_CALL(adm, AddRef()).WillOnce(Return(0));
75 EXPECT_CALL(adm, Release()).WillOnce(Return(0));
solenberg5b5129a2016-04-08 05:35:48 -070076 EXPECT_CALL(adm, BuiltInAECIsAvailable()).WillOnce(Return(false));
77 EXPECT_CALL(adm, BuiltInAGCIsAvailable()).WillOnce(Return(false));
78 EXPECT_CALL(adm, BuiltInNSIsAvailable()).WillOnce(Return(false));
solenberg059fb442016-10-26 05:12:24 -070079 StrictMock<webrtc::test::MockAudioProcessing> apm;
80 EXPECT_CALL(apm, ApplyConfig(testing::_));
81 EXPECT_CALL(apm, SetExtraOptions(testing::_));
82 EXPECT_CALL(apm, Initialize()).WillOnce(Return(0));
83 cricket::FakeWebRtcVoiceEngine voe(&apm);
solenbergff976312016-03-30 23:28:51 -070084 EXPECT_FALSE(voe.IsInited());
85 {
ossuc54071d2016-08-17 02:45:41 -070086 cricket::WebRtcVoiceEngine engine(
87 &adm, webrtc::MockAudioDecoderFactory::CreateUnusedFactory(),
88 new FakeVoEWrapper(&voe));
solenbergff976312016-03-30 23:28:51 -070089 EXPECT_TRUE(voe.IsInited());
90 }
91 EXPECT_FALSE(voe.IsInited());
92}
93
deadbeef884f5852016-01-15 09:20:04 -080094class FakeAudioSink : public webrtc::AudioSinkInterface {
95 public:
96 void OnData(const Data& audio) override {}
97};
98
Taylor Brandstetter1a018dc2016-03-08 12:37:39 -080099class FakeAudioSource : public cricket::AudioSource {
100 void SetSink(Sink* sink) override {}
101};
102
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000103class WebRtcVoiceEngineTestFake : public testing::Test {
104 public:
stefanba4c0e42016-02-04 04:12:24 -0800105 WebRtcVoiceEngineTestFake() : WebRtcVoiceEngineTestFake("") {}
106
107 explicit WebRtcVoiceEngineTestFake(const char* field_trials)
solenberg059fb442016-10-26 05:12:24 -0700108 : call_(webrtc::Call::Config(&event_log_)), voe_(&apm_),
skvlad11a9cbf2016-10-07 11:53:05 -0700109 override_field_trials_(field_trials) {
ossuc54071d2016-08-17 02:45:41 -0700110 auto factory = webrtc::MockAudioDecoderFactory::CreateUnusedFactory();
solenbergbc37fc82016-04-04 09:54:44 -0700111 EXPECT_CALL(adm_, AddRef()).WillOnce(Return(0));
112 EXPECT_CALL(adm_, Release()).WillOnce(Return(0));
solenberg5b5129a2016-04-08 05:35:48 -0700113 EXPECT_CALL(adm_, BuiltInAECIsAvailable()).WillOnce(Return(false));
114 EXPECT_CALL(adm_, BuiltInAGCIsAvailable()).WillOnce(Return(false));
115 EXPECT_CALL(adm_, BuiltInNSIsAvailable()).WillOnce(Return(false));
solenberg059fb442016-10-26 05:12:24 -0700116 EXPECT_CALL(apm_, ApplyConfig(testing::_));
117 EXPECT_CALL(apm_, SetExtraOptions(testing::_));
118 EXPECT_CALL(apm_, Initialize()).WillOnce(Return(0));
ossuc54071d2016-08-17 02:45:41 -0700119 engine_.reset(new cricket::WebRtcVoiceEngine(&adm_, factory,
solenbergbc37fc82016-04-04 09:54:44 -0700120 new FakeVoEWrapper(&voe_)));
Fredrik Solenbergb071a192015-09-17 16:42:56 +0200121 send_parameters_.codecs.push_back(kPcmuCodec);
122 recv_parameters_.codecs.push_back(kPcmuCodec);
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000123 }
solenberg8189b022016-06-14 12:13:00 -0700124
solenbergff976312016-03-30 23:28:51 -0700125 bool SetupChannel() {
solenberg059fb442016-10-26 05:12:24 -0700126 EXPECT_CALL(apm_, ApplyConfig(testing::_));
127 EXPECT_CALL(apm_, SetExtraOptions(testing::_));
solenbergbc37fc82016-04-04 09:54:44 -0700128 channel_ = engine_->CreateChannel(&call_, cricket::MediaConfig(),
129 cricket::AudioOptions());
Jelena Marusicc28a8962015-05-29 15:05:44 +0200130 return (channel_ != nullptr);
buildbot@webrtc.org150835e2014-05-06 15:54:38 +0000131 }
solenberg8189b022016-06-14 12:13:00 -0700132
solenbergff976312016-03-30 23:28:51 -0700133 bool SetupRecvStream() {
134 if (!SetupChannel()) {
solenberg1ac56142015-10-13 03:58:19 -0700135 return false;
136 }
solenberg8189b022016-06-14 12:13:00 -0700137 return AddRecvStream(kSsrc1);
solenberg1ac56142015-10-13 03:58:19 -0700138 }
solenberg8189b022016-06-14 12:13:00 -0700139
solenbergff976312016-03-30 23:28:51 -0700140 bool SetupSendStream() {
141 if (!SetupChannel()) {
buildbot@webrtc.org150835e2014-05-06 15:54:38 +0000142 return false;
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000143 }
Taylor Brandstetter1a018dc2016-03-08 12:37:39 -0800144 if (!channel_->AddSendStream(cricket::StreamParams::CreateLegacy(kSsrc1))) {
145 return false;
146 }
solenberg059fb442016-10-26 05:12:24 -0700147 EXPECT_CALL(apm_, set_output_will_be_muted(false));
Taylor Brandstetter1a018dc2016-03-08 12:37:39 -0800148 return channel_->SetAudioSend(kSsrc1, true, nullptr, &fake_source_);
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000149 }
solenberg8189b022016-06-14 12:13:00 -0700150
151 bool AddRecvStream(uint32_t ssrc) {
152 EXPECT_TRUE(channel_);
153 return channel_->AddRecvStream(cricket::StreamParams::CreateLegacy(ssrc));
154 }
155
wu@webrtc.org9dba5252013-08-05 20:36:57 +0000156 void SetupForMultiSendStream() {
solenbergff976312016-03-30 23:28:51 -0700157 EXPECT_TRUE(SetupSendStream());
solenberg0a617e22015-10-20 15:49:38 -0700158 // Remove stream added in Setup.
solenberg3a941542015-11-16 07:34:50 -0800159 EXPECT_TRUE(call_.GetAudioSendStream(kSsrc1));
solenberg85a04962015-10-27 03:35:21 -0700160 EXPECT_TRUE(channel_->RemoveSendStream(kSsrc1));
solenberg0a617e22015-10-20 15:49:38 -0700161 // Verify the channel does not exist.
solenberg3a941542015-11-16 07:34:50 -0800162 EXPECT_FALSE(call_.GetAudioSendStream(kSsrc1));
wu@webrtc.org9dba5252013-08-05 20:36:57 +0000163 }
solenberg8189b022016-06-14 12:13:00 -0700164
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000165 void DeliverPacket(const void* data, int len) {
jbaucheec21bd2016-03-20 06:15:43 -0700166 rtc::CopyOnWriteBuffer packet(reinterpret_cast<const uint8_t*>(data), len);
buildbot@webrtc.orgd4e598d2014-07-29 17:36:52 +0000167 channel_->OnPacketReceived(&packet, rtc::PacketTime());
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000168 }
solenberg8189b022016-06-14 12:13:00 -0700169
Fredrik Solenbergaaf8ff22015-05-07 16:05:53 +0200170 void TearDown() override {
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000171 delete channel_;
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000172 }
173
Fredrik Solenbergb5727682015-12-04 15:22:19 +0100174 const cricket::FakeAudioSendStream& GetSendStream(uint32_t ssrc) {
175 const auto* send_stream = call_.GetAudioSendStream(ssrc);
176 EXPECT_TRUE(send_stream);
177 return *send_stream;
178 }
179
deadbeef884f5852016-01-15 09:20:04 -0800180 const cricket::FakeAudioReceiveStream& GetRecvStream(uint32_t ssrc) {
181 const auto* recv_stream = call_.GetAudioReceiveStream(ssrc);
182 EXPECT_TRUE(recv_stream);
183 return *recv_stream;
184 }
185
solenberg3a941542015-11-16 07:34:50 -0800186 const webrtc::AudioSendStream::Config& GetSendStreamConfig(uint32_t ssrc) {
Taylor Brandstetter1a018dc2016-03-08 12:37:39 -0800187 return GetSendStream(ssrc).GetConfig();
solenberg3a941542015-11-16 07:34:50 -0800188 }
189
solenberg7add0582015-11-20 09:59:34 -0800190 const webrtc::AudioReceiveStream::Config& GetRecvStreamConfig(uint32_t ssrc) {
Taylor Brandstetter1a018dc2016-03-08 12:37:39 -0800191 return GetRecvStream(ssrc).GetConfig();
solenberg7add0582015-11-20 09:59:34 -0800192 }
193
solenberg059fb442016-10-26 05:12:24 -0700194 void SetSend(bool enable) {
195 ASSERT_TRUE(channel_);
solenbergd53a3f92016-04-14 13:56:37 -0700196 if (enable) {
197 EXPECT_CALL(adm_, RecordingIsInitialized()).WillOnce(Return(false));
198 EXPECT_CALL(adm_, Recording()).WillOnce(Return(false));
199 EXPECT_CALL(adm_, InitRecording()).WillOnce(Return(0));
solenberg059fb442016-10-26 05:12:24 -0700200 EXPECT_CALL(apm_, ApplyConfig(testing::_));
201 EXPECT_CALL(apm_, SetExtraOptions(testing::_));
solenbergd53a3f92016-04-14 13:56:37 -0700202 }
solenberg059fb442016-10-26 05:12:24 -0700203 channel_->SetSend(enable);
204 }
205
206 void SetSendParameters(const cricket::AudioSendParameters& params) {
207 EXPECT_CALL(apm_, ApplyConfig(testing::_));
208 EXPECT_CALL(apm_, SetExtraOptions(testing::_));
209 ASSERT_TRUE(channel_);
210 EXPECT_TRUE(channel_->SetSendParameters(params));
211 }
212
minyue6b825df2016-10-31 04:08:32 -0700213 void SetAudioSend(uint32_t ssrc, bool enable, cricket::AudioSource* source,
214 const cricket::AudioOptions* options = nullptr) {
solenberg059fb442016-10-26 05:12:24 -0700215 EXPECT_CALL(apm_, set_output_will_be_muted(!enable));
216 ASSERT_TRUE(channel_);
minyue6b825df2016-10-31 04:08:32 -0700217 if (enable && options) {
218 EXPECT_CALL(apm_, ApplyConfig(testing::_));
219 EXPECT_CALL(apm_, SetExtraOptions(testing::_));
220 }
221 EXPECT_TRUE(channel_->SetAudioSend(ssrc, enable, options, source));
solenbergd53a3f92016-04-14 13:56:37 -0700222 }
223
solenbergffbbcac2016-11-17 05:25:37 -0800224 void TestInsertDtmf(uint32_t ssrc, bool caller,
225 const cricket::AudioCodec& codec) {
solenbergff976312016-03-30 23:28:51 -0700226 EXPECT_TRUE(SetupChannel());
wu@webrtc.orgcadf9042013-08-30 21:24:16 +0000227 if (caller) {
solenberg0a617e22015-10-20 15:49:38 -0700228 // If this is a caller, local description will be applied and add the
wu@webrtc.orgcadf9042013-08-30 21:24:16 +0000229 // send stream.
230 EXPECT_TRUE(channel_->AddSendStream(
231 cricket::StreamParams::CreateLegacy(kSsrc1)));
232 }
wu@webrtc.orgcadf9042013-08-30 21:24:16 +0000233
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000234 // Test we can only InsertDtmf when the other side supports telephone-event.
solenberg059fb442016-10-26 05:12:24 -0700235 SetSendParameters(send_parameters_);
236 SetSend(true);
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000237 EXPECT_FALSE(channel_->CanInsertDtmf());
solenberg1d63dd02015-12-02 12:35:09 -0800238 EXPECT_FALSE(channel_->InsertDtmf(ssrc, 1, 111));
solenbergffbbcac2016-11-17 05:25:37 -0800239 send_parameters_.codecs.push_back(codec);
solenberg059fb442016-10-26 05:12:24 -0700240 SetSendParameters(send_parameters_);
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000241 EXPECT_TRUE(channel_->CanInsertDtmf());
wu@webrtc.orgcadf9042013-08-30 21:24:16 +0000242
243 if (!caller) {
solenberg0a617e22015-10-20 15:49:38 -0700244 // If this is callee, there's no active send channel yet.
solenberg1d63dd02015-12-02 12:35:09 -0800245 EXPECT_FALSE(channel_->InsertDtmf(ssrc, 2, 123));
wu@webrtc.orgcadf9042013-08-30 21:24:16 +0000246 EXPECT_TRUE(channel_->AddSendStream(
247 cricket::StreamParams::CreateLegacy(kSsrc1)));
248 }
249
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000250 // Check we fail if the ssrc is invalid.
solenberg1d63dd02015-12-02 12:35:09 -0800251 EXPECT_FALSE(channel_->InsertDtmf(-1, 1, 111));
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000252
Fredrik Solenbergb5727682015-12-04 15:22:19 +0100253 // Test send.
254 cricket::FakeAudioSendStream::TelephoneEvent telephone_event =
255 GetSendStream(kSsrc1).GetLatestTelephoneEvent();
256 EXPECT_EQ(-1, telephone_event.payload_type);
solenberg1d63dd02015-12-02 12:35:09 -0800257 EXPECT_TRUE(channel_->InsertDtmf(ssrc, 2, 123));
Fredrik Solenbergb5727682015-12-04 15:22:19 +0100258 telephone_event = GetSendStream(kSsrc1).GetLatestTelephoneEvent();
solenbergffbbcac2016-11-17 05:25:37 -0800259 EXPECT_EQ(codec.id, telephone_event.payload_type);
260 EXPECT_EQ(codec.clockrate, telephone_event.payload_frequency);
Fredrik Solenbergb5727682015-12-04 15:22:19 +0100261 EXPECT_EQ(2, telephone_event.event_code);
262 EXPECT_EQ(123, telephone_event.duration_ms);
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000263 }
264
265 // Test that send bandwidth is set correctly.
266 // |codec| is the codec under test.
sergeyu@chromium.org4b26e2e2014-01-15 23:15:54 +0000267 // |max_bitrate| is a parameter to set to SetMaxSendBandwidth().
268 // |expected_result| is the expected result from SetMaxSendBandwidth().
269 // |expected_bitrate| is the expected audio bitrate afterward.
deadbeef80346142016-04-27 14:17:10 -0700270 void TestMaxSendBandwidth(const cricket::AudioCodec& codec,
271 int max_bitrate,
272 bool expected_result,
273 int expected_bitrate) {
Fredrik Solenbergb071a192015-09-17 16:42:56 +0200274 cricket::AudioSendParameters parameters;
275 parameters.codecs.push_back(codec);
276 parameters.max_bandwidth_bps = max_bitrate;
solenberg059fb442016-10-26 05:12:24 -0700277 if (expected_result) {
278 SetSendParameters(parameters);
279 } else {
280 EXPECT_FALSE(channel_->SetSendParameters(parameters));
281 }
minyue7a973442016-10-20 03:27:12 -0700282 EXPECT_EQ(expected_bitrate, GetCodecBitrate(kSsrc1));
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000283 }
284
skvlade0d46372016-04-07 22:59:22 -0700285 // Sets the per-stream maximum bitrate limit for the specified SSRC.
286 bool SetMaxBitrateForStream(int32_t ssrc, int bitrate) {
Taylor Brandstetterdb0cd9e2016-05-16 11:40:30 -0700287 webrtc::RtpParameters parameters = channel_->GetRtpSendParameters(ssrc);
skvlade0d46372016-04-07 22:59:22 -0700288 EXPECT_EQ(1UL, parameters.encodings.size());
289
290 parameters.encodings[0].max_bitrate_bps = bitrate;
Taylor Brandstetterdb0cd9e2016-05-16 11:40:30 -0700291 return channel_->SetRtpSendParameters(ssrc, parameters);
skvlade0d46372016-04-07 22:59:22 -0700292 }
293
solenberg059fb442016-10-26 05:12:24 -0700294 void SetGlobalMaxBitrate(const cricket::AudioCodec& codec, int bitrate) {
skvlade0d46372016-04-07 22:59:22 -0700295 cricket::AudioSendParameters send_parameters;
296 send_parameters.codecs.push_back(codec);
297 send_parameters.max_bandwidth_bps = bitrate;
solenberg059fb442016-10-26 05:12:24 -0700298 SetSendParameters(send_parameters);
skvlade0d46372016-04-07 22:59:22 -0700299 }
300
minyue7a973442016-10-20 03:27:12 -0700301 void CheckSendCodec(int32_t ssrc,
302 const char expected_name[],
303 int expected_channels,
304 int expected_bitrate) {
305 const auto& codec = GetSendStreamConfig(ssrc).send_codec_spec.codec_inst;
306 EXPECT_STREQ(expected_name, codec.plname);
307 EXPECT_EQ(expected_channels, codec.channels);
308 EXPECT_EQ(expected_bitrate, codec.rate);
309 }
310
311 int GetOpusMaxPlaybackRate(int32_t ssrc) {
312 return GetSendStreamConfig(ssrc).send_codec_spec.opus_max_playback_rate;
313 }
314
315 bool GetOpusDtx(int32_t ssrc) {
316 return GetSendStreamConfig(ssrc).send_codec_spec.enable_opus_dtx;
317 }
318
319 bool GetCodecFec(int32_t ssrc) {
320 return GetSendStreamConfig(ssrc).send_codec_spec.enable_codec_fec;
321 }
322
skvlade0d46372016-04-07 22:59:22 -0700323 int GetCodecBitrate(int32_t ssrc) {
minyue7a973442016-10-20 03:27:12 -0700324 return GetSendStreamConfig(ssrc).send_codec_spec.codec_inst.rate;
325 }
326
327 int GetCodecPacSize(int32_t ssrc) {
328 return GetSendStreamConfig(ssrc).send_codec_spec.codec_inst.pacsize;
skvlade0d46372016-04-07 22:59:22 -0700329 }
330
minyue6b825df2016-10-31 04:08:32 -0700331 const rtc::Optional<std::string>& GetAudioNetworkAdaptorConfig(int32_t ssrc) {
332 return GetSendStreamConfig(ssrc).audio_network_adaptor_config;
333 }
334
skvlade0d46372016-04-07 22:59:22 -0700335 void SetAndExpectMaxBitrate(const cricket::AudioCodec& codec,
336 int global_max,
337 int stream_max,
338 bool expected_result,
339 int expected_codec_bitrate) {
340 // Clear the bitrate limit from the previous test case.
341 EXPECT_TRUE(SetMaxBitrateForStream(kSsrc1, -1));
342
343 // Attempt to set the requested bitrate limits.
solenberg059fb442016-10-26 05:12:24 -0700344 SetGlobalMaxBitrate(codec, global_max);
skvlade0d46372016-04-07 22:59:22 -0700345 EXPECT_EQ(expected_result, SetMaxBitrateForStream(kSsrc1, stream_max));
346
347 // Verify that reading back the parameters gives results
348 // consistent with the Set() result.
349 webrtc::RtpParameters resulting_parameters =
Taylor Brandstetterdb0cd9e2016-05-16 11:40:30 -0700350 channel_->GetRtpSendParameters(kSsrc1);
skvlade0d46372016-04-07 22:59:22 -0700351 EXPECT_EQ(1UL, resulting_parameters.encodings.size());
352 EXPECT_EQ(expected_result ? stream_max : -1,
353 resulting_parameters.encodings[0].max_bitrate_bps);
354
355 // Verify that the codec settings have the expected bitrate.
356 EXPECT_EQ(expected_codec_bitrate, GetCodecBitrate(kSsrc1));
357 }
358
buildbot@webrtc.org150835e2014-05-06 15:54:38 +0000359 void TestSetSendRtpHeaderExtensions(const std::string& ext) {
solenbergff976312016-03-30 23:28:51 -0700360 EXPECT_TRUE(SetupSendStream());
wu@webrtc.org9dba5252013-08-05 20:36:57 +0000361
henrike@webrtc.org79047f92014-03-06 23:46:59 +0000362 // Ensure extensions are off by default.
solenberg3a941542015-11-16 07:34:50 -0800363 EXPECT_EQ(0u, GetSendStreamConfig(kSsrc1).rtp.extensions.size());
wu@webrtc.org9dba5252013-08-05 20:36:57 +0000364
365 // Ensure unknown extensions won't cause an error.
isheriff6f8d6862016-05-26 11:24:55 -0700366 send_parameters_.extensions.push_back(
367 webrtc::RtpExtension("urn:ietf:params:unknownextention", 1));
solenberg059fb442016-10-26 05:12:24 -0700368 SetSendParameters(send_parameters_);
solenberg3a941542015-11-16 07:34:50 -0800369 EXPECT_EQ(0u, GetSendStreamConfig(kSsrc1).rtp.extensions.size());
wu@webrtc.org9dba5252013-08-05 20:36:57 +0000370
henrike@webrtc.org79047f92014-03-06 23:46:59 +0000371 // Ensure extensions stay off with an empty list of headers.
Fredrik Solenbergb071a192015-09-17 16:42:56 +0200372 send_parameters_.extensions.clear();
solenberg059fb442016-10-26 05:12:24 -0700373 SetSendParameters(send_parameters_);
solenberg3a941542015-11-16 07:34:50 -0800374 EXPECT_EQ(0u, GetSendStreamConfig(kSsrc1).rtp.extensions.size());
wu@webrtc.org9dba5252013-08-05 20:36:57 +0000375
buildbot@webrtc.org150835e2014-05-06 15:54:38 +0000376 // Ensure extension is set properly.
377 const int id = 1;
isheriff6f8d6862016-05-26 11:24:55 -0700378 send_parameters_.extensions.push_back(webrtc::RtpExtension(ext, id));
solenberg059fb442016-10-26 05:12:24 -0700379 SetSendParameters(send_parameters_);
solenberg3a941542015-11-16 07:34:50 -0800380 EXPECT_EQ(1u, GetSendStreamConfig(kSsrc1).rtp.extensions.size());
isheriff6f8d6862016-05-26 11:24:55 -0700381 EXPECT_EQ(ext, GetSendStreamConfig(kSsrc1).rtp.extensions[0].uri);
solenberg3a941542015-11-16 07:34:50 -0800382 EXPECT_EQ(id, GetSendStreamConfig(kSsrc1).rtp.extensions[0].id);
wu@webrtc.org9dba5252013-08-05 20:36:57 +0000383
solenberg7add0582015-11-20 09:59:34 -0800384 // Ensure extension is set properly on new stream.
buildbot@webrtc.org150835e2014-05-06 15:54:38 +0000385 EXPECT_TRUE(channel_->AddSendStream(
solenberg0a617e22015-10-20 15:49:38 -0700386 cricket::StreamParams::CreateLegacy(kSsrc2)));
solenberg3a941542015-11-16 07:34:50 -0800387 EXPECT_NE(call_.GetAudioSendStream(kSsrc1),
388 call_.GetAudioSendStream(kSsrc2));
389 EXPECT_EQ(1u, GetSendStreamConfig(kSsrc2).rtp.extensions.size());
isheriff6f8d6862016-05-26 11:24:55 -0700390 EXPECT_EQ(ext, GetSendStreamConfig(kSsrc2).rtp.extensions[0].uri);
solenberg3a941542015-11-16 07:34:50 -0800391 EXPECT_EQ(id, GetSendStreamConfig(kSsrc2).rtp.extensions[0].id);
henrike@webrtc.org79047f92014-03-06 23:46:59 +0000392
393 // Ensure all extensions go back off with an empty list.
Fredrik Solenbergb071a192015-09-17 16:42:56 +0200394 send_parameters_.codecs.push_back(kPcmuCodec);
395 send_parameters_.extensions.clear();
solenberg059fb442016-10-26 05:12:24 -0700396 SetSendParameters(send_parameters_);
solenberg3a941542015-11-16 07:34:50 -0800397 EXPECT_EQ(0u, GetSendStreamConfig(kSsrc1).rtp.extensions.size());
398 EXPECT_EQ(0u, GetSendStreamConfig(kSsrc2).rtp.extensions.size());
henrike@webrtc.org79047f92014-03-06 23:46:59 +0000399 }
400
buildbot@webrtc.org150835e2014-05-06 15:54:38 +0000401 void TestSetRecvRtpHeaderExtensions(const std::string& ext) {
solenbergff976312016-03-30 23:28:51 -0700402 EXPECT_TRUE(SetupRecvStream());
henrike@webrtc.org79047f92014-03-06 23:46:59 +0000403
henrike@webrtc.org79047f92014-03-06 23:46:59 +0000404 // Ensure extensions are off by default.
solenberg7add0582015-11-20 09:59:34 -0800405 EXPECT_EQ(0u, GetRecvStreamConfig(kSsrc1).rtp.extensions.size());
henrike@webrtc.org79047f92014-03-06 23:46:59 +0000406
407 // Ensure unknown extensions won't cause an error.
isheriff6f8d6862016-05-26 11:24:55 -0700408 recv_parameters_.extensions.push_back(
409 webrtc::RtpExtension("urn:ietf:params:unknownextention", 1));
solenberg7add0582015-11-20 09:59:34 -0800410 EXPECT_TRUE(channel_->SetRecvParameters(recv_parameters_));
411 EXPECT_EQ(0u, GetRecvStreamConfig(kSsrc1).rtp.extensions.size());
henrike@webrtc.org79047f92014-03-06 23:46:59 +0000412
buildbot@webrtc.org150835e2014-05-06 15:54:38 +0000413 // Ensure extensions stay off with an empty list of headers.
solenberg7add0582015-11-20 09:59:34 -0800414 recv_parameters_.extensions.clear();
415 EXPECT_TRUE(channel_->SetRecvParameters(recv_parameters_));
416 EXPECT_EQ(0u, GetRecvStreamConfig(kSsrc1).rtp.extensions.size());
henrike@webrtc.org79047f92014-03-06 23:46:59 +0000417
buildbot@webrtc.org150835e2014-05-06 15:54:38 +0000418 // Ensure extension is set properly.
419 const int id = 2;
isheriff6f8d6862016-05-26 11:24:55 -0700420 recv_parameters_.extensions.push_back(webrtc::RtpExtension(ext, id));
solenberg7add0582015-11-20 09:59:34 -0800421 EXPECT_TRUE(channel_->SetRecvParameters(recv_parameters_));
422 EXPECT_EQ(1u, GetRecvStreamConfig(kSsrc1).rtp.extensions.size());
isheriff6f8d6862016-05-26 11:24:55 -0700423 EXPECT_EQ(ext, GetRecvStreamConfig(kSsrc1).rtp.extensions[0].uri);
solenberg7add0582015-11-20 09:59:34 -0800424 EXPECT_EQ(id, GetRecvStreamConfig(kSsrc1).rtp.extensions[0].id);
henrike@webrtc.org79047f92014-03-06 23:46:59 +0000425
solenberg7add0582015-11-20 09:59:34 -0800426 // Ensure extension is set properly on new stream.
solenberg8189b022016-06-14 12:13:00 -0700427 EXPECT_TRUE(AddRecvStream(kSsrc2));
solenberg7add0582015-11-20 09:59:34 -0800428 EXPECT_NE(call_.GetAudioReceiveStream(kSsrc1),
429 call_.GetAudioReceiveStream(kSsrc2));
430 EXPECT_EQ(1u, GetRecvStreamConfig(kSsrc2).rtp.extensions.size());
isheriff6f8d6862016-05-26 11:24:55 -0700431 EXPECT_EQ(ext, GetRecvStreamConfig(kSsrc2).rtp.extensions[0].uri);
solenberg7add0582015-11-20 09:59:34 -0800432 EXPECT_EQ(id, GetRecvStreamConfig(kSsrc2).rtp.extensions[0].id);
buildbot@webrtc.org150835e2014-05-06 15:54:38 +0000433
434 // Ensure all extensions go back off with an empty list.
solenberg7add0582015-11-20 09:59:34 -0800435 recv_parameters_.extensions.clear();
436 EXPECT_TRUE(channel_->SetRecvParameters(recv_parameters_));
437 EXPECT_EQ(0u, GetRecvStreamConfig(kSsrc1).rtp.extensions.size());
438 EXPECT_EQ(0u, GetRecvStreamConfig(kSsrc2).rtp.extensions.size());
wu@webrtc.org9dba5252013-08-05 20:36:57 +0000439 }
440
solenberg85a04962015-10-27 03:35:21 -0700441 webrtc::AudioSendStream::Stats GetAudioSendStreamStats() const {
442 webrtc::AudioSendStream::Stats stats;
443 stats.local_ssrc = 12;
444 stats.bytes_sent = 345;
445 stats.packets_sent = 678;
446 stats.packets_lost = 9012;
447 stats.fraction_lost = 34.56f;
448 stats.codec_name = "codec_name_send";
449 stats.ext_seqnum = 789;
450 stats.jitter_ms = 12;
451 stats.rtt_ms = 345;
452 stats.audio_level = 678;
453 stats.aec_quality_min = 9.01f;
454 stats.echo_delay_median_ms = 234;
455 stats.echo_delay_std_ms = 567;
456 stats.echo_return_loss = 890;
457 stats.echo_return_loss_enhancement = 1234;
ivoc8c63a822016-10-21 04:10:03 -0700458 stats.residual_echo_likelihood = 0.432f;
solenberg85a04962015-10-27 03:35:21 -0700459 stats.typing_noise_detected = true;
460 return stats;
461 }
462 void SetAudioSendStreamStats() {
463 for (auto* s : call_.GetAudioSendStreams()) {
464 s->SetStats(GetAudioSendStreamStats());
Fredrik Solenberg4f4ec0a2015-10-22 10:49:27 +0200465 }
solenberg85a04962015-10-27 03:35:21 -0700466 }
solenberg566ef242015-11-06 15:34:49 -0800467 void VerifyVoiceSenderInfo(const cricket::VoiceSenderInfo& info,
468 bool is_sending) {
solenberg85a04962015-10-27 03:35:21 -0700469 const auto stats = GetAudioSendStreamStats();
470 EXPECT_EQ(info.ssrc(), stats.local_ssrc);
471 EXPECT_EQ(info.bytes_sent, stats.bytes_sent);
472 EXPECT_EQ(info.packets_sent, stats.packets_sent);
473 EXPECT_EQ(info.packets_lost, stats.packets_lost);
474 EXPECT_EQ(info.fraction_lost, stats.fraction_lost);
475 EXPECT_EQ(info.codec_name, stats.codec_name);
476 EXPECT_EQ(info.ext_seqnum, stats.ext_seqnum);
477 EXPECT_EQ(info.jitter_ms, stats.jitter_ms);
478 EXPECT_EQ(info.rtt_ms, stats.rtt_ms);
479 EXPECT_EQ(info.audio_level, stats.audio_level);
480 EXPECT_EQ(info.aec_quality_min, stats.aec_quality_min);
481 EXPECT_EQ(info.echo_delay_median_ms, stats.echo_delay_median_ms);
482 EXPECT_EQ(info.echo_delay_std_ms, stats.echo_delay_std_ms);
483 EXPECT_EQ(info.echo_return_loss, stats.echo_return_loss);
484 EXPECT_EQ(info.echo_return_loss_enhancement,
485 stats.echo_return_loss_enhancement);
ivoc8c63a822016-10-21 04:10:03 -0700486 EXPECT_EQ(info.residual_echo_likelihood, stats.residual_echo_likelihood);
solenberg566ef242015-11-06 15:34:49 -0800487 EXPECT_EQ(info.typing_noise_detected,
488 stats.typing_noise_detected && is_sending);
solenberg85a04962015-10-27 03:35:21 -0700489 }
490
491 webrtc::AudioReceiveStream::Stats GetAudioReceiveStreamStats() const {
492 webrtc::AudioReceiveStream::Stats stats;
493 stats.remote_ssrc = 123;
494 stats.bytes_rcvd = 456;
495 stats.packets_rcvd = 768;
496 stats.packets_lost = 101;
497 stats.fraction_lost = 23.45f;
498 stats.codec_name = "codec_name_recv";
499 stats.ext_seqnum = 678;
500 stats.jitter_ms = 901;
501 stats.jitter_buffer_ms = 234;
502 stats.jitter_buffer_preferred_ms = 567;
503 stats.delay_estimate_ms = 890;
504 stats.audio_level = 1234;
505 stats.expand_rate = 5.67f;
506 stats.speech_expand_rate = 8.90f;
507 stats.secondary_decoded_rate = 1.23f;
508 stats.accelerate_rate = 4.56f;
509 stats.preemptive_expand_rate = 7.89f;
510 stats.decoding_calls_to_silence_generator = 12;
511 stats.decoding_calls_to_neteq = 345;
512 stats.decoding_normal = 67890;
513 stats.decoding_plc = 1234;
514 stats.decoding_cng = 5678;
515 stats.decoding_plc_cng = 9012;
henrik.lundin63489782016-09-20 01:47:12 -0700516 stats.decoding_muted_output = 3456;
517 stats.capture_start_ntp_time_ms = 7890;
Fredrik Solenberg4f4ec0a2015-10-22 10:49:27 +0200518 return stats;
519 }
520 void SetAudioReceiveStreamStats() {
521 for (auto* s : call_.GetAudioReceiveStreams()) {
522 s->SetStats(GetAudioReceiveStreamStats());
523 }
524 }
525 void VerifyVoiceReceiverInfo(const cricket::VoiceReceiverInfo& info) {
solenberg85a04962015-10-27 03:35:21 -0700526 const auto stats = GetAudioReceiveStreamStats();
527 EXPECT_EQ(info.ssrc(), stats.remote_ssrc);
528 EXPECT_EQ(info.bytes_rcvd, stats.bytes_rcvd);
529 EXPECT_EQ(info.packets_rcvd, stats.packets_rcvd);
530 EXPECT_EQ(info.packets_lost, stats.packets_lost);
531 EXPECT_EQ(info.fraction_lost, stats.fraction_lost);
532 EXPECT_EQ(info.codec_name, stats.codec_name);
533 EXPECT_EQ(info.ext_seqnum, stats.ext_seqnum);
534 EXPECT_EQ(info.jitter_ms, stats.jitter_ms);
535 EXPECT_EQ(info.jitter_buffer_ms, stats.jitter_buffer_ms);
Fredrik Solenberg4f4ec0a2015-10-22 10:49:27 +0200536 EXPECT_EQ(info.jitter_buffer_preferred_ms,
solenberg85a04962015-10-27 03:35:21 -0700537 stats.jitter_buffer_preferred_ms);
538 EXPECT_EQ(info.delay_estimate_ms, stats.delay_estimate_ms);
539 EXPECT_EQ(info.audio_level, stats.audio_level);
540 EXPECT_EQ(info.expand_rate, stats.expand_rate);
541 EXPECT_EQ(info.speech_expand_rate, stats.speech_expand_rate);
542 EXPECT_EQ(info.secondary_decoded_rate, stats.secondary_decoded_rate);
543 EXPECT_EQ(info.accelerate_rate, stats.accelerate_rate);
544 EXPECT_EQ(info.preemptive_expand_rate, stats.preemptive_expand_rate);
Fredrik Solenberg4f4ec0a2015-10-22 10:49:27 +0200545 EXPECT_EQ(info.decoding_calls_to_silence_generator,
solenberg85a04962015-10-27 03:35:21 -0700546 stats.decoding_calls_to_silence_generator);
547 EXPECT_EQ(info.decoding_calls_to_neteq, stats.decoding_calls_to_neteq);
548 EXPECT_EQ(info.decoding_normal, stats.decoding_normal);
549 EXPECT_EQ(info.decoding_plc, stats.decoding_plc);
550 EXPECT_EQ(info.decoding_cng, stats.decoding_cng);
551 EXPECT_EQ(info.decoding_plc_cng, stats.decoding_plc_cng);
henrik.lundin63489782016-09-20 01:47:12 -0700552 EXPECT_EQ(info.decoding_muted_output, stats.decoding_muted_output);
solenberg85a04962015-10-27 03:35:21 -0700553 EXPECT_EQ(info.capture_start_ntp_time_ms, stats.capture_start_ntp_time_ms);
Fredrik Solenberg4f4ec0a2015-10-22 10:49:27 +0200554 }
555
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000556 protected:
solenbergbc37fc82016-04-04 09:54:44 -0700557 StrictMock<webrtc::test::MockAudioDeviceModule> adm_;
solenberg059fb442016-10-26 05:12:24 -0700558 StrictMock<webrtc::test::MockAudioProcessing> apm_;
skvlad11a9cbf2016-10-07 11:53:05 -0700559 webrtc::RtcEventLogNullImpl event_log_;
Fredrik Solenberg709ed672015-09-15 12:26:33 +0200560 cricket::FakeCall call_;
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000561 cricket::FakeWebRtcVoiceEngine voe_;
solenbergbc37fc82016-04-04 09:54:44 -0700562 std::unique_ptr<cricket::WebRtcVoiceEngine> engine_;
solenbergff976312016-03-30 23:28:51 -0700563 cricket::VoiceMediaChannel* channel_ = nullptr;
Fredrik Solenbergb071a192015-09-17 16:42:56 +0200564 cricket::AudioSendParameters send_parameters_;
565 cricket::AudioRecvParameters recv_parameters_;
Taylor Brandstetter1a018dc2016-03-08 12:37:39 -0800566 FakeAudioSource fake_source_;
stefanba4c0e42016-02-04 04:12:24 -0800567 private:
568 webrtc::test::ScopedFieldTrials override_field_trials_;
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000569};
570
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000571// Tests that we can create and destroy a channel.
572TEST_F(WebRtcVoiceEngineTestFake, CreateChannel) {
solenbergff976312016-03-30 23:28:51 -0700573 EXPECT_TRUE(SetupChannel());
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000574}
575
solenberg31fec402016-05-06 02:13:12 -0700576// Test that we can add a send stream and that it has the correct defaults.
577TEST_F(WebRtcVoiceEngineTestFake, CreateSendStream) {
578 EXPECT_TRUE(SetupChannel());
579 EXPECT_TRUE(
580 channel_->AddSendStream(cricket::StreamParams::CreateLegacy(kSsrc1)));
581 const webrtc::AudioSendStream::Config& config = GetSendStreamConfig(kSsrc1);
582 EXPECT_EQ(kSsrc1, config.rtp.ssrc);
583 EXPECT_EQ("", config.rtp.c_name);
584 EXPECT_EQ(0u, config.rtp.extensions.size());
585 EXPECT_EQ(static_cast<cricket::WebRtcVoiceMediaChannel*>(channel_),
586 config.send_transport);
587}
588
589// Test that we can add a receive stream and that it has the correct defaults.
590TEST_F(WebRtcVoiceEngineTestFake, CreateRecvStream) {
591 EXPECT_TRUE(SetupChannel());
solenberg8189b022016-06-14 12:13:00 -0700592 EXPECT_TRUE(AddRecvStream(kSsrc1));
solenberg31fec402016-05-06 02:13:12 -0700593 const webrtc::AudioReceiveStream::Config& config =
594 GetRecvStreamConfig(kSsrc1);
595 EXPECT_EQ(kSsrc1, config.rtp.remote_ssrc);
596 EXPECT_EQ(0xFA17FA17, config.rtp.local_ssrc);
597 EXPECT_FALSE(config.rtp.transport_cc);
598 EXPECT_EQ(0u, config.rtp.extensions.size());
599 EXPECT_EQ(static_cast<cricket::WebRtcVoiceMediaChannel*>(channel_),
600 config.rtcp_send_transport);
601 EXPECT_EQ("", config.sync_group);
602}
603
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000604// Tests that the list of supported codecs is created properly and ordered
deadbeef67cf2c12016-04-13 10:07:16 -0700605// correctly (such that opus appears first).
ossudedfd282016-06-14 07:12:39 -0700606// TODO(ossu): This test should move into a separate builtin audio codecs
607// module.
deadbeef67cf2c12016-04-13 10:07:16 -0700608TEST_F(WebRtcVoiceEngineTestFake, CodecOrder) {
ossudedfd282016-06-14 07:12:39 -0700609 const std::vector<cricket::AudioCodec>& codecs = engine_->send_codecs();
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000610 ASSERT_FALSE(codecs.empty());
611 EXPECT_STRCASEEQ("opus", codecs[0].name.c_str());
612 EXPECT_EQ(48000, codecs[0].clockrate);
613 EXPECT_EQ(2, codecs[0].channels);
614 EXPECT_EQ(64000, codecs[0].bitrate);
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000615}
616
stefanba4c0e42016-02-04 04:12:24 -0800617TEST_F(WebRtcVoiceEngineTestFake, OpusSupportsTransportCc) {
ossudedfd282016-06-14 07:12:39 -0700618 const std::vector<cricket::AudioCodec>& codecs = engine_->send_codecs();
stefanba4c0e42016-02-04 04:12:24 -0800619 bool opus_found = false;
620 for (cricket::AudioCodec codec : codecs) {
621 if (codec.name == "opus") {
622 EXPECT_TRUE(HasTransportCc(codec));
623 opus_found = true;
624 }
625 }
626 EXPECT_TRUE(opus_found);
627}
628
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000629// Tests that we can find codecs by name or id, and that we interpret the
630// clockrate and bitrate fields properly.
631TEST_F(WebRtcVoiceEngineTestFake, FindCodec) {
632 cricket::AudioCodec codec;
633 webrtc::CodecInst codec_inst;
634 // Find PCMU with explicit clockrate and bitrate.
solenberg26c8c912015-11-27 04:00:25 -0800635 EXPECT_TRUE(cricket::WebRtcVoiceEngine::ToCodecInst(kPcmuCodec, &codec_inst));
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000636 // Find ISAC with explicit clockrate and 0 bitrate.
solenberg26c8c912015-11-27 04:00:25 -0800637 EXPECT_TRUE(cricket::WebRtcVoiceEngine::ToCodecInst(kIsacCodec, &codec_inst));
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000638 // Find telephone-event with explicit clockrate and 0 bitrate.
solenberg2779bab2016-11-17 04:45:19 -0800639 EXPECT_TRUE(cricket::WebRtcVoiceEngine::ToCodecInst(kTelephoneEventCodec1,
640 &codec_inst));
641 // Find telephone-event with explicit clockrate and 0 bitrate.
642 EXPECT_TRUE(cricket::WebRtcVoiceEngine::ToCodecInst(kTelephoneEventCodec2,
solenberg26c8c912015-11-27 04:00:25 -0800643 &codec_inst));
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000644 // Find ISAC with a different payload id.
645 codec = kIsacCodec;
646 codec.id = 127;
solenberg26c8c912015-11-27 04:00:25 -0800647 EXPECT_TRUE(cricket::WebRtcVoiceEngine::ToCodecInst(codec, &codec_inst));
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000648 EXPECT_EQ(codec.id, codec_inst.pltype);
649 // Find PCMU with a 0 clockrate.
650 codec = kPcmuCodec;
651 codec.clockrate = 0;
solenberg26c8c912015-11-27 04:00:25 -0800652 EXPECT_TRUE(cricket::WebRtcVoiceEngine::ToCodecInst(codec, &codec_inst));
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000653 EXPECT_EQ(codec.id, codec_inst.pltype);
654 EXPECT_EQ(8000, codec_inst.plfreq);
655 // Find PCMU with a 0 bitrate.
656 codec = kPcmuCodec;
657 codec.bitrate = 0;
solenberg26c8c912015-11-27 04:00:25 -0800658 EXPECT_TRUE(cricket::WebRtcVoiceEngine::ToCodecInst(codec, &codec_inst));
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000659 EXPECT_EQ(codec.id, codec_inst.pltype);
660 EXPECT_EQ(64000, codec_inst.rate);
661 // Find ISAC with an explicit bitrate.
662 codec = kIsacCodec;
663 codec.bitrate = 32000;
solenberg26c8c912015-11-27 04:00:25 -0800664 EXPECT_TRUE(cricket::WebRtcVoiceEngine::ToCodecInst(codec, &codec_inst));
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000665 EXPECT_EQ(codec.id, codec_inst.pltype);
666 EXPECT_EQ(32000, codec_inst.rate);
667}
668
669// Test that we set our inbound codecs properly, including changing PT.
670TEST_F(WebRtcVoiceEngineTestFake, SetRecvCodecs) {
solenbergff976312016-03-30 23:28:51 -0700671 EXPECT_TRUE(SetupChannel());
Fredrik Solenbergb071a192015-09-17 16:42:56 +0200672 cricket::AudioRecvParameters parameters;
673 parameters.codecs.push_back(kIsacCodec);
674 parameters.codecs.push_back(kPcmuCodec);
solenberg2779bab2016-11-17 04:45:19 -0800675 parameters.codecs.push_back(kTelephoneEventCodec1);
676 parameters.codecs.push_back(kTelephoneEventCodec2);
677 parameters.codecs[0].id = 106; // collide with existing CN 32k
Fredrik Solenbergb071a192015-09-17 16:42:56 +0200678 parameters.codecs[2].id = 126;
679 EXPECT_TRUE(channel_->SetRecvParameters(parameters));
solenberg8189b022016-06-14 12:13:00 -0700680 EXPECT_TRUE(AddRecvStream(kSsrc1));
solenberg1ac56142015-10-13 03:58:19 -0700681 int channel_num = voe_.GetLastChannel();
solenberg2779bab2016-11-17 04:45:19 -0800682
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000683 webrtc::CodecInst gcodec;
tfarina5237aaf2015-11-10 23:44:30 -0800684 rtc::strcpyn(gcodec.plname, arraysize(gcodec.plname), "ISAC");
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000685 gcodec.plfreq = 16000;
686 gcodec.channels = 1;
687 EXPECT_EQ(0, voe_.GetRecPayloadType(channel_num, gcodec));
688 EXPECT_EQ(106, gcodec.pltype);
689 EXPECT_STREQ("ISAC", gcodec.plname);
solenberg2779bab2016-11-17 04:45:19 -0800690
tfarina5237aaf2015-11-10 23:44:30 -0800691 rtc::strcpyn(gcodec.plname, arraysize(gcodec.plname), "telephone-event");
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000692 gcodec.plfreq = 8000;
693 EXPECT_EQ(0, voe_.GetRecPayloadType(channel_num, gcodec));
694 EXPECT_EQ(126, gcodec.pltype);
695 EXPECT_STREQ("telephone-event", gcodec.plname);
solenberg2779bab2016-11-17 04:45:19 -0800696
697 gcodec.plfreq = 32000;
698 EXPECT_EQ(0, voe_.GetRecPayloadType(channel_num, gcodec));
699 EXPECT_EQ(107, gcodec.pltype);
700 EXPECT_STREQ("telephone-event", gcodec.plname);
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000701}
702
703// Test that we fail to set an unknown inbound codec.
704TEST_F(WebRtcVoiceEngineTestFake, SetRecvCodecsUnsupportedCodec) {
solenbergff976312016-03-30 23:28:51 -0700705 EXPECT_TRUE(SetupChannel());
Fredrik Solenbergb071a192015-09-17 16:42:56 +0200706 cricket::AudioRecvParameters parameters;
707 parameters.codecs.push_back(kIsacCodec);
deadbeef67cf2c12016-04-13 10:07:16 -0700708 parameters.codecs.push_back(cricket::AudioCodec(127, "XYZ", 32000, 0, 1));
Fredrik Solenbergb071a192015-09-17 16:42:56 +0200709 EXPECT_FALSE(channel_->SetRecvParameters(parameters));
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000710}
711
712// Test that we fail if we have duplicate types in the inbound list.
713TEST_F(WebRtcVoiceEngineTestFake, SetRecvCodecsDuplicatePayloadType) {
solenbergff976312016-03-30 23:28:51 -0700714 EXPECT_TRUE(SetupChannel());
Fredrik Solenbergb071a192015-09-17 16:42:56 +0200715 cricket::AudioRecvParameters parameters;
716 parameters.codecs.push_back(kIsacCodec);
717 parameters.codecs.push_back(kCn16000Codec);
718 parameters.codecs[1].id = kIsacCodec.id;
719 EXPECT_FALSE(channel_->SetRecvParameters(parameters));
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000720}
721
722// Test that we can decode OPUS without stereo parameters.
723TEST_F(WebRtcVoiceEngineTestFake, SetRecvCodecsWithOpusNoStereo) {
solenbergff976312016-03-30 23:28:51 -0700724 EXPECT_TRUE(SetupChannel());
Fredrik Solenbergb071a192015-09-17 16:42:56 +0200725 cricket::AudioRecvParameters parameters;
726 parameters.codecs.push_back(kIsacCodec);
727 parameters.codecs.push_back(kPcmuCodec);
728 parameters.codecs.push_back(kOpusCodec);
729 EXPECT_TRUE(channel_->SetRecvParameters(parameters));
solenberg8189b022016-06-14 12:13:00 -0700730 EXPECT_TRUE(AddRecvStream(kSsrc1));
solenberg1ac56142015-10-13 03:58:19 -0700731 int channel_num = voe_.GetLastChannel();
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000732 webrtc::CodecInst opus;
solenberg26c8c912015-11-27 04:00:25 -0800733 cricket::WebRtcVoiceEngine::ToCodecInst(kOpusCodec, &opus);
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000734 // Even without stereo parameters, recv codecs still specify channels = 2.
735 EXPECT_EQ(2, opus.channels);
736 EXPECT_EQ(111, opus.pltype);
737 EXPECT_STREQ("opus", opus.plname);
738 opus.pltype = 0;
solenberg1ac56142015-10-13 03:58:19 -0700739 EXPECT_EQ(0, voe_.GetRecPayloadType(channel_num, opus));
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000740 EXPECT_EQ(111, opus.pltype);
741}
742
743// Test that we can decode OPUS with stereo = 0.
744TEST_F(WebRtcVoiceEngineTestFake, SetRecvCodecsWithOpus0Stereo) {
solenbergff976312016-03-30 23:28:51 -0700745 EXPECT_TRUE(SetupChannel());
Fredrik Solenbergb071a192015-09-17 16:42:56 +0200746 cricket::AudioRecvParameters parameters;
747 parameters.codecs.push_back(kIsacCodec);
748 parameters.codecs.push_back(kPcmuCodec);
749 parameters.codecs.push_back(kOpusCodec);
750 parameters.codecs[2].params["stereo"] = "0";
751 EXPECT_TRUE(channel_->SetRecvParameters(parameters));
solenberg8189b022016-06-14 12:13:00 -0700752 EXPECT_TRUE(AddRecvStream(kSsrc1));
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000753 int channel_num2 = voe_.GetLastChannel();
754 webrtc::CodecInst opus;
solenberg26c8c912015-11-27 04:00:25 -0800755 cricket::WebRtcVoiceEngine::ToCodecInst(kOpusCodec, &opus);
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000756 // Even when stereo is off, recv codecs still specify channels = 2.
757 EXPECT_EQ(2, opus.channels);
758 EXPECT_EQ(111, opus.pltype);
759 EXPECT_STREQ("opus", opus.plname);
760 opus.pltype = 0;
761 EXPECT_EQ(0, voe_.GetRecPayloadType(channel_num2, opus));
762 EXPECT_EQ(111, opus.pltype);
763}
764
765// Test that we can decode OPUS with stereo = 1.
766TEST_F(WebRtcVoiceEngineTestFake, SetRecvCodecsWithOpus1Stereo) {
solenbergff976312016-03-30 23:28:51 -0700767 EXPECT_TRUE(SetupChannel());
Fredrik Solenbergb071a192015-09-17 16:42:56 +0200768 cricket::AudioRecvParameters parameters;
769 parameters.codecs.push_back(kIsacCodec);
770 parameters.codecs.push_back(kPcmuCodec);
771 parameters.codecs.push_back(kOpusCodec);
772 parameters.codecs[2].params["stereo"] = "1";
773 EXPECT_TRUE(channel_->SetRecvParameters(parameters));
solenberg8189b022016-06-14 12:13:00 -0700774 EXPECT_TRUE(AddRecvStream(kSsrc1));
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000775 int channel_num2 = voe_.GetLastChannel();
776 webrtc::CodecInst opus;
solenberg26c8c912015-11-27 04:00:25 -0800777 cricket::WebRtcVoiceEngine::ToCodecInst(kOpusCodec, &opus);
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000778 EXPECT_EQ(2, opus.channels);
779 EXPECT_EQ(111, opus.pltype);
780 EXPECT_STREQ("opus", opus.plname);
781 opus.pltype = 0;
782 EXPECT_EQ(0, voe_.GetRecPayloadType(channel_num2, opus));
783 EXPECT_EQ(111, opus.pltype);
784}
785
786// Test that changes to recv codecs are applied to all streams.
787TEST_F(WebRtcVoiceEngineTestFake, SetRecvCodecsWithMultipleStreams) {
solenbergff976312016-03-30 23:28:51 -0700788 EXPECT_TRUE(SetupChannel());
Fredrik Solenbergb071a192015-09-17 16:42:56 +0200789 cricket::AudioRecvParameters parameters;
790 parameters.codecs.push_back(kIsacCodec);
791 parameters.codecs.push_back(kPcmuCodec);
solenberg2779bab2016-11-17 04:45:19 -0800792 parameters.codecs.push_back(kTelephoneEventCodec1);
793 parameters.codecs.push_back(kTelephoneEventCodec2);
794 parameters.codecs[0].id = 106; // collide with existing CN 32k
Fredrik Solenbergb071a192015-09-17 16:42:56 +0200795 parameters.codecs[2].id = 126;
796 EXPECT_TRUE(channel_->SetRecvParameters(parameters));
solenberg8189b022016-06-14 12:13:00 -0700797 EXPECT_TRUE(AddRecvStream(kSsrc1));
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000798 int channel_num2 = voe_.GetLastChannel();
solenberg2779bab2016-11-17 04:45:19 -0800799
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000800 webrtc::CodecInst gcodec;
tfarina5237aaf2015-11-10 23:44:30 -0800801 rtc::strcpyn(gcodec.plname, arraysize(gcodec.plname), "ISAC");
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000802 gcodec.plfreq = 16000;
803 gcodec.channels = 1;
804 EXPECT_EQ(0, voe_.GetRecPayloadType(channel_num2, gcodec));
805 EXPECT_EQ(106, gcodec.pltype);
806 EXPECT_STREQ("ISAC", gcodec.plname);
solenberg2779bab2016-11-17 04:45:19 -0800807
tfarina5237aaf2015-11-10 23:44:30 -0800808 rtc::strcpyn(gcodec.plname, arraysize(gcodec.plname), "telephone-event");
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000809 gcodec.plfreq = 8000;
810 gcodec.channels = 1;
811 EXPECT_EQ(0, voe_.GetRecPayloadType(channel_num2, gcodec));
812 EXPECT_EQ(126, gcodec.pltype);
813 EXPECT_STREQ("telephone-event", gcodec.plname);
solenberg2779bab2016-11-17 04:45:19 -0800814
815 gcodec.plfreq = 32000;
816 EXPECT_EQ(0, voe_.GetRecPayloadType(channel_num2, gcodec));
817 EXPECT_EQ(107, gcodec.pltype);
818 EXPECT_STREQ("telephone-event", gcodec.plname);
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000819}
820
821TEST_F(WebRtcVoiceEngineTestFake, SetRecvCodecsAfterAddingStreams) {
solenbergff976312016-03-30 23:28:51 -0700822 EXPECT_TRUE(SetupRecvStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +0200823 cricket::AudioRecvParameters parameters;
824 parameters.codecs.push_back(kIsacCodec);
solenberg2779bab2016-11-17 04:45:19 -0800825 parameters.codecs[0].id = 106; // collide with existing CN 32k
Fredrik Solenbergb071a192015-09-17 16:42:56 +0200826 EXPECT_TRUE(channel_->SetRecvParameters(parameters));
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000827
828 int channel_num2 = voe_.GetLastChannel();
829 webrtc::CodecInst gcodec;
tfarina5237aaf2015-11-10 23:44:30 -0800830 rtc::strcpyn(gcodec.plname, arraysize(gcodec.plname), "ISAC");
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000831 gcodec.plfreq = 16000;
832 gcodec.channels = 1;
833 EXPECT_EQ(0, voe_.GetRecPayloadType(channel_num2, gcodec));
834 EXPECT_EQ(106, gcodec.pltype);
835 EXPECT_STREQ("ISAC", gcodec.plname);
836}
837
838// Test that we can apply the same set of codecs again while playing.
839TEST_F(WebRtcVoiceEngineTestFake, SetRecvCodecsWhilePlaying) {
solenbergff976312016-03-30 23:28:51 -0700840 EXPECT_TRUE(SetupRecvStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +0200841 cricket::AudioRecvParameters parameters;
842 parameters.codecs.push_back(kIsacCodec);
843 parameters.codecs.push_back(kCn16000Codec);
844 EXPECT_TRUE(channel_->SetRecvParameters(parameters));
aleloi84ef6152016-08-04 05:28:21 -0700845 channel_->SetPlayout(true);
Fredrik Solenbergb071a192015-09-17 16:42:56 +0200846 EXPECT_TRUE(channel_->SetRecvParameters(parameters));
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000847
848 // Changing the payload type of a codec should fail.
Fredrik Solenbergb071a192015-09-17 16:42:56 +0200849 parameters.codecs[0].id = 127;
850 EXPECT_FALSE(channel_->SetRecvParameters(parameters));
aleloi84ef6152016-08-04 05:28:21 -0700851 EXPECT_TRUE(GetRecvStream(kSsrc1).started());
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000852}
853
854// Test that we can add a codec while playing.
855TEST_F(WebRtcVoiceEngineTestFake, AddRecvCodecsWhilePlaying) {
solenbergff976312016-03-30 23:28:51 -0700856 EXPECT_TRUE(SetupRecvStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +0200857 cricket::AudioRecvParameters parameters;
858 parameters.codecs.push_back(kIsacCodec);
859 parameters.codecs.push_back(kCn16000Codec);
860 EXPECT_TRUE(channel_->SetRecvParameters(parameters));
aleloi84ef6152016-08-04 05:28:21 -0700861 channel_->SetPlayout(true);
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000862
Fredrik Solenbergb071a192015-09-17 16:42:56 +0200863 parameters.codecs.push_back(kOpusCodec);
864 EXPECT_TRUE(channel_->SetRecvParameters(parameters));
aleloi84ef6152016-08-04 05:28:21 -0700865 EXPECT_TRUE(GetRecvStream(kSsrc1).started());
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000866 webrtc::CodecInst gcodec;
solenberg26c8c912015-11-27 04:00:25 -0800867 EXPECT_TRUE(cricket::WebRtcVoiceEngine::ToCodecInst(kOpusCodec, &gcodec));
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000868 EXPECT_EQ(kOpusCodec.id, gcodec.pltype);
869}
870
871TEST_F(WebRtcVoiceEngineTestFake, SetSendBandwidthAuto) {
solenbergff976312016-03-30 23:28:51 -0700872 EXPECT_TRUE(SetupSendStream());
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000873
sergeyu@chromium.org4b26e2e2014-01-15 23:15:54 +0000874 // Test that when autobw is enabled, bitrate is kept as the default
875 // value. autobw is enabled for the following tests because the target
876 // bitrate is <= 0.
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000877
878 // ISAC, default bitrate == 32000.
deadbeef80346142016-04-27 14:17:10 -0700879 TestMaxSendBandwidth(kIsacCodec, 0, true, 32000);
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000880
881 // PCMU, default bitrate == 64000.
deadbeef80346142016-04-27 14:17:10 -0700882 TestMaxSendBandwidth(kPcmuCodec, -1, true, 64000);
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000883
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000884 // opus, default bitrate == 64000.
deadbeef80346142016-04-27 14:17:10 -0700885 TestMaxSendBandwidth(kOpusCodec, -1, true, 64000);
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000886}
887
sergeyu@chromium.org4b26e2e2014-01-15 23:15:54 +0000888TEST_F(WebRtcVoiceEngineTestFake, SetMaxSendBandwidthMultiRateAsCaller) {
solenbergff976312016-03-30 23:28:51 -0700889 EXPECT_TRUE(SetupSendStream());
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000890
sergeyu@chromium.org4b26e2e2014-01-15 23:15:54 +0000891 // Test that the bitrate of a multi-rate codec is always the maximum.
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000892
893 // ISAC, default bitrate == 32000.
deadbeef80346142016-04-27 14:17:10 -0700894 TestMaxSendBandwidth(kIsacCodec, 40000, true, 40000);
895 TestMaxSendBandwidth(kIsacCodec, 16000, true, 16000);
896 // Rates above the max (56000) should be capped.
897 TestMaxSendBandwidth(kIsacCodec, 100000, true, 56000);
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000898
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000899 // opus, default bitrate == 64000.
deadbeef80346142016-04-27 14:17:10 -0700900 TestMaxSendBandwidth(kOpusCodec, 96000, true, 96000);
901 TestMaxSendBandwidth(kOpusCodec, 48000, true, 48000);
902 // Rates above the max (510000) should be capped.
903 TestMaxSendBandwidth(kOpusCodec, 600000, true, 510000);
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000904}
905
sergeyu@chromium.org4b26e2e2014-01-15 23:15:54 +0000906TEST_F(WebRtcVoiceEngineTestFake, SetMaxSendBandwidthFixedRateAsCaller) {
solenbergff976312016-03-30 23:28:51 -0700907 EXPECT_TRUE(SetupSendStream());
sergeyu@chromium.org4b26e2e2014-01-15 23:15:54 +0000908
909 // Test that we can only set a maximum bitrate for a fixed-rate codec
910 // if it's bigger than the fixed rate.
911
912 // PCMU, fixed bitrate == 64000.
deadbeef80346142016-04-27 14:17:10 -0700913 TestMaxSendBandwidth(kPcmuCodec, 0, true, 64000);
914 TestMaxSendBandwidth(kPcmuCodec, 1, false, 64000);
915 TestMaxSendBandwidth(kPcmuCodec, 128000, true, 64000);
916 TestMaxSendBandwidth(kPcmuCodec, 32000, false, 64000);
917 TestMaxSendBandwidth(kPcmuCodec, 64000, true, 64000);
918 TestMaxSendBandwidth(kPcmuCodec, 63999, false, 64000);
919 TestMaxSendBandwidth(kPcmuCodec, 64001, true, 64000);
sergeyu@chromium.org4b26e2e2014-01-15 23:15:54 +0000920}
921
922TEST_F(WebRtcVoiceEngineTestFake, SetMaxSendBandwidthMultiRateAsCallee) {
solenbergff976312016-03-30 23:28:51 -0700923 EXPECT_TRUE(SetupChannel());
Fredrik Solenbergb071a192015-09-17 16:42:56 +0200924 const int kDesiredBitrate = 128000;
925 cricket::AudioSendParameters parameters;
ossudedfd282016-06-14 07:12:39 -0700926 parameters.codecs = engine_->send_codecs();
Fredrik Solenbergb071a192015-09-17 16:42:56 +0200927 parameters.max_bandwidth_bps = kDesiredBitrate;
solenberg059fb442016-10-26 05:12:24 -0700928 SetSendParameters(parameters);
wu@webrtc.org1d1ffc92013-10-16 18:12:02 +0000929
930 EXPECT_TRUE(channel_->AddSendStream(
931 cricket::StreamParams::CreateLegacy(kSsrc1)));
932
minyue7a973442016-10-20 03:27:12 -0700933 EXPECT_EQ(kDesiredBitrate, GetCodecBitrate(kSsrc1));
wu@webrtc.org1d1ffc92013-10-16 18:12:02 +0000934}
935
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000936// Test that bitrate cannot be set for CBR codecs.
937// Bitrate is ignored if it is higher than the fixed bitrate.
938// Bitrate less then the fixed bitrate is an error.
sergeyu@chromium.org4b26e2e2014-01-15 23:15:54 +0000939TEST_F(WebRtcVoiceEngineTestFake, SetMaxSendBandwidthCbr) {
solenbergff976312016-03-30 23:28:51 -0700940 EXPECT_TRUE(SetupSendStream());
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000941
942 // PCMU, default bitrate == 64000.
solenberg059fb442016-10-26 05:12:24 -0700943 SetSendParameters(send_parameters_);
minyue7a973442016-10-20 03:27:12 -0700944 EXPECT_EQ(64000, GetCodecBitrate(kSsrc1));
Fredrik Solenbergb071a192015-09-17 16:42:56 +0200945
946 send_parameters_.max_bandwidth_bps = 128000;
solenberg059fb442016-10-26 05:12:24 -0700947 SetSendParameters(send_parameters_);
minyue7a973442016-10-20 03:27:12 -0700948 EXPECT_EQ(64000, GetCodecBitrate(kSsrc1));
Fredrik Solenbergb071a192015-09-17 16:42:56 +0200949
950 send_parameters_.max_bandwidth_bps = 128;
951 EXPECT_FALSE(channel_->SetSendParameters(send_parameters_));
minyue7a973442016-10-20 03:27:12 -0700952 EXPECT_EQ(64000, GetCodecBitrate(kSsrc1));
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000953}
954
skvlade0d46372016-04-07 22:59:22 -0700955// Test that the per-stream bitrate limit and the global
956// bitrate limit both apply.
957TEST_F(WebRtcVoiceEngineTestFake, SetMaxBitratePerStream) {
958 EXPECT_TRUE(SetupSendStream());
959
960 // opus, default bitrate == 64000.
961 SetAndExpectMaxBitrate(kOpusCodec, 0, 0, true, 64000);
962 SetAndExpectMaxBitrate(kOpusCodec, 48000, 0, true, 48000);
963 SetAndExpectMaxBitrate(kOpusCodec, 48000, 64000, true, 48000);
964 SetAndExpectMaxBitrate(kOpusCodec, 64000, 48000, true, 48000);
965
966 // CBR codecs allow both maximums to exceed the bitrate.
967 SetAndExpectMaxBitrate(kPcmuCodec, 0, 0, true, 64000);
968 SetAndExpectMaxBitrate(kPcmuCodec, 64001, 0, true, 64000);
969 SetAndExpectMaxBitrate(kPcmuCodec, 0, 64001, true, 64000);
970 SetAndExpectMaxBitrate(kPcmuCodec, 64001, 64001, true, 64000);
971
972 // CBR codecs don't allow per stream maximums to be too low.
973 SetAndExpectMaxBitrate(kPcmuCodec, 0, 63999, false, 64000);
974 SetAndExpectMaxBitrate(kPcmuCodec, 64001, 63999, false, 64000);
975}
976
977// Test that an attempt to set RtpParameters for a stream that does not exist
978// fails.
979TEST_F(WebRtcVoiceEngineTestFake, CannotSetMaxBitrateForNonexistentStream) {
980 EXPECT_TRUE(SetupChannel());
981 webrtc::RtpParameters nonexistent_parameters =
Taylor Brandstetterdb0cd9e2016-05-16 11:40:30 -0700982 channel_->GetRtpSendParameters(kSsrc1);
skvlade0d46372016-04-07 22:59:22 -0700983 EXPECT_EQ(0, nonexistent_parameters.encodings.size());
984
985 nonexistent_parameters.encodings.push_back(webrtc::RtpEncodingParameters());
Taylor Brandstetterdb0cd9e2016-05-16 11:40:30 -0700986 EXPECT_FALSE(channel_->SetRtpSendParameters(kSsrc1, nonexistent_parameters));
skvlade0d46372016-04-07 22:59:22 -0700987}
988
989TEST_F(WebRtcVoiceEngineTestFake,
Taylor Brandstetterdb0cd9e2016-05-16 11:40:30 -0700990 CannotSetRtpSendParametersWithIncorrectNumberOfEncodings) {
skvlade0d46372016-04-07 22:59:22 -0700991 // This test verifies that setting RtpParameters succeeds only if
992 // the structure contains exactly one encoding.
993 // TODO(skvlad): Update this test when we start supporting setting parameters
994 // for each encoding individually.
995
996 EXPECT_TRUE(SetupSendStream());
997 // Setting RtpParameters with no encoding is expected to fail.
998 webrtc::RtpParameters parameters;
Taylor Brandstetterdb0cd9e2016-05-16 11:40:30 -0700999 EXPECT_FALSE(channel_->SetRtpSendParameters(kSsrc1, parameters));
skvlade0d46372016-04-07 22:59:22 -07001000 // Setting RtpParameters with exactly one encoding should succeed.
1001 parameters.encodings.push_back(webrtc::RtpEncodingParameters());
Taylor Brandstetterdb0cd9e2016-05-16 11:40:30 -07001002 EXPECT_TRUE(channel_->SetRtpSendParameters(kSsrc1, parameters));
skvlade0d46372016-04-07 22:59:22 -07001003 // Two or more encodings should result in failure.
1004 parameters.encodings.push_back(webrtc::RtpEncodingParameters());
Taylor Brandstetterdb0cd9e2016-05-16 11:40:30 -07001005 EXPECT_FALSE(channel_->SetRtpSendParameters(kSsrc1, parameters));
skvlade0d46372016-04-07 22:59:22 -07001006}
1007
Taylor Brandstetter55dd7082016-05-03 13:50:11 -07001008// Test that a stream will not be sending if its encoding is made
Taylor Brandstetterdb0cd9e2016-05-16 11:40:30 -07001009// inactive through SetRtpSendParameters.
Taylor Brandstetter55dd7082016-05-03 13:50:11 -07001010TEST_F(WebRtcVoiceEngineTestFake, SetRtpParametersEncodingsActive) {
1011 EXPECT_TRUE(SetupSendStream());
solenberg059fb442016-10-26 05:12:24 -07001012 SetSend(true);
Taylor Brandstetter55dd7082016-05-03 13:50:11 -07001013 EXPECT_TRUE(GetSendStream(kSsrc1).IsSending());
1014 // Get current parameters and change "active" to false.
Taylor Brandstetterdb0cd9e2016-05-16 11:40:30 -07001015 webrtc::RtpParameters parameters = channel_->GetRtpSendParameters(kSsrc1);
Taylor Brandstetter55dd7082016-05-03 13:50:11 -07001016 ASSERT_EQ(1u, parameters.encodings.size());
1017 ASSERT_TRUE(parameters.encodings[0].active);
1018 parameters.encodings[0].active = false;
Taylor Brandstetterdb0cd9e2016-05-16 11:40:30 -07001019 EXPECT_TRUE(channel_->SetRtpSendParameters(kSsrc1, parameters));
Taylor Brandstetter55dd7082016-05-03 13:50:11 -07001020 EXPECT_FALSE(GetSendStream(kSsrc1).IsSending());
1021
1022 // Now change it back to active and verify we resume sending.
1023 parameters.encodings[0].active = true;
Taylor Brandstetterdb0cd9e2016-05-16 11:40:30 -07001024 EXPECT_TRUE(channel_->SetRtpSendParameters(kSsrc1, parameters));
Taylor Brandstetter55dd7082016-05-03 13:50:11 -07001025 EXPECT_TRUE(GetSendStream(kSsrc1).IsSending());
1026}
1027
Taylor Brandstetterdb0cd9e2016-05-16 11:40:30 -07001028// Test that SetRtpSendParameters configures the correct encoding channel for
1029// each SSRC.
skvlade0d46372016-04-07 22:59:22 -07001030TEST_F(WebRtcVoiceEngineTestFake, RtpParametersArePerStream) {
1031 SetupForMultiSendStream();
1032 // Create send streams.
1033 for (uint32_t ssrc : kSsrcs4) {
1034 EXPECT_TRUE(
1035 channel_->AddSendStream(cricket::StreamParams::CreateLegacy(ssrc)));
1036 }
1037 // Configure one stream to be limited by the stream config, another to be
1038 // limited by the global max, and the third one with no per-stream limit
1039 // (still subject to the global limit).
solenberg059fb442016-10-26 05:12:24 -07001040 SetGlobalMaxBitrate(kOpusCodec, 64000);
skvlade0d46372016-04-07 22:59:22 -07001041 EXPECT_TRUE(SetMaxBitrateForStream(kSsrcs4[0], 48000));
1042 EXPECT_TRUE(SetMaxBitrateForStream(kSsrcs4[1], 96000));
1043 EXPECT_TRUE(SetMaxBitrateForStream(kSsrcs4[2], -1));
1044
1045 EXPECT_EQ(48000, GetCodecBitrate(kSsrcs4[0]));
1046 EXPECT_EQ(64000, GetCodecBitrate(kSsrcs4[1]));
1047 EXPECT_EQ(64000, GetCodecBitrate(kSsrcs4[2]));
1048
1049 // Remove the global cap; the streams should switch to their respective
1050 // maximums (or remain unchanged if there was no other limit on them.)
solenberg059fb442016-10-26 05:12:24 -07001051 SetGlobalMaxBitrate(kOpusCodec, -1);
skvlade0d46372016-04-07 22:59:22 -07001052 EXPECT_EQ(48000, GetCodecBitrate(kSsrcs4[0]));
1053 EXPECT_EQ(96000, GetCodecBitrate(kSsrcs4[1]));
1054 EXPECT_EQ(64000, GetCodecBitrate(kSsrcs4[2]));
1055}
1056
Taylor Brandstetterdb0cd9e2016-05-16 11:40:30 -07001057// Test that GetRtpSendParameters returns the currently configured codecs.
1058TEST_F(WebRtcVoiceEngineTestFake, GetRtpSendParametersCodecs) {
Taylor Brandstetter0cd086b2016-04-20 16:23:10 -07001059 EXPECT_TRUE(SetupSendStream());
1060 cricket::AudioSendParameters parameters;
1061 parameters.codecs.push_back(kIsacCodec);
1062 parameters.codecs.push_back(kPcmuCodec);
solenberg059fb442016-10-26 05:12:24 -07001063 SetSendParameters(parameters);
Taylor Brandstetter0cd086b2016-04-20 16:23:10 -07001064
Taylor Brandstetterdb0cd9e2016-05-16 11:40:30 -07001065 webrtc::RtpParameters rtp_parameters = channel_->GetRtpSendParameters(kSsrc1);
Taylor Brandstetter0cd086b2016-04-20 16:23:10 -07001066 ASSERT_EQ(2u, rtp_parameters.codecs.size());
Taylor Brandstetterdb0cd9e2016-05-16 11:40:30 -07001067 EXPECT_EQ(kIsacCodec.ToCodecParameters(), rtp_parameters.codecs[0]);
1068 EXPECT_EQ(kPcmuCodec.ToCodecParameters(), rtp_parameters.codecs[1]);
Taylor Brandstetter0cd086b2016-04-20 16:23:10 -07001069}
1070
1071// Test that if we set/get parameters multiple times, we get the same results.
Taylor Brandstetterdb0cd9e2016-05-16 11:40:30 -07001072TEST_F(WebRtcVoiceEngineTestFake, SetAndGetRtpSendParameters) {
Taylor Brandstetter0cd086b2016-04-20 16:23:10 -07001073 EXPECT_TRUE(SetupSendStream());
1074 cricket::AudioSendParameters parameters;
1075 parameters.codecs.push_back(kIsacCodec);
1076 parameters.codecs.push_back(kPcmuCodec);
solenberg059fb442016-10-26 05:12:24 -07001077 SetSendParameters(parameters);
Taylor Brandstetter0cd086b2016-04-20 16:23:10 -07001078
Taylor Brandstetterdb0cd9e2016-05-16 11:40:30 -07001079 webrtc::RtpParameters initial_params = channel_->GetRtpSendParameters(kSsrc1);
Taylor Brandstetter0cd086b2016-04-20 16:23:10 -07001080
1081 // We should be able to set the params we just got.
Taylor Brandstetterdb0cd9e2016-05-16 11:40:30 -07001082 EXPECT_TRUE(channel_->SetRtpSendParameters(kSsrc1, initial_params));
Taylor Brandstetter0cd086b2016-04-20 16:23:10 -07001083
Taylor Brandstetterdb0cd9e2016-05-16 11:40:30 -07001084 // ... And this shouldn't change the params returned by GetRtpSendParameters.
1085 webrtc::RtpParameters new_params = channel_->GetRtpSendParameters(kSsrc1);
1086 EXPECT_EQ(initial_params, channel_->GetRtpSendParameters(kSsrc1));
1087}
1088
1089// Test that GetRtpReceiveParameters returns the currently configured codecs.
1090TEST_F(WebRtcVoiceEngineTestFake, GetRtpReceiveParametersCodecs) {
1091 EXPECT_TRUE(SetupRecvStream());
1092 cricket::AudioRecvParameters parameters;
1093 parameters.codecs.push_back(kIsacCodec);
1094 parameters.codecs.push_back(kPcmuCodec);
1095 EXPECT_TRUE(channel_->SetRecvParameters(parameters));
1096
1097 webrtc::RtpParameters rtp_parameters =
1098 channel_->GetRtpReceiveParameters(kSsrc1);
1099 ASSERT_EQ(2u, rtp_parameters.codecs.size());
1100 EXPECT_EQ(kIsacCodec.ToCodecParameters(), rtp_parameters.codecs[0]);
1101 EXPECT_EQ(kPcmuCodec.ToCodecParameters(), rtp_parameters.codecs[1]);
1102}
1103
1104// Test that if we set/get parameters multiple times, we get the same results.
1105TEST_F(WebRtcVoiceEngineTestFake, SetAndGetRtpReceiveParameters) {
1106 EXPECT_TRUE(SetupRecvStream());
1107 cricket::AudioRecvParameters parameters;
1108 parameters.codecs.push_back(kIsacCodec);
1109 parameters.codecs.push_back(kPcmuCodec);
1110 EXPECT_TRUE(channel_->SetRecvParameters(parameters));
1111
1112 webrtc::RtpParameters initial_params =
1113 channel_->GetRtpReceiveParameters(kSsrc1);
1114
1115 // We should be able to set the params we just got.
1116 EXPECT_TRUE(channel_->SetRtpReceiveParameters(kSsrc1, initial_params));
1117
1118 // ... And this shouldn't change the params returned by
1119 // GetRtpReceiveParameters.
1120 webrtc::RtpParameters new_params = channel_->GetRtpReceiveParameters(kSsrc1);
1121 EXPECT_EQ(initial_params, channel_->GetRtpReceiveParameters(kSsrc1));
Taylor Brandstetter0cd086b2016-04-20 16:23:10 -07001122}
1123
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001124// Test that we apply codecs properly.
1125TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecs) {
solenbergff976312016-03-30 23:28:51 -07001126 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001127 cricket::AudioSendParameters parameters;
1128 parameters.codecs.push_back(kIsacCodec);
1129 parameters.codecs.push_back(kPcmuCodec);
kwiberg68061362016-06-14 08:04:47 -07001130 parameters.codecs.push_back(kCn8000Codec);
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001131 parameters.codecs[0].id = 96;
1132 parameters.codecs[0].bitrate = 48000;
minyue7a973442016-10-20 03:27:12 -07001133 const int initial_num = call_.GetNumCreatedSendStreams();
solenberg059fb442016-10-26 05:12:24 -07001134 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001135 EXPECT_EQ(initial_num + 1, call_.GetNumCreatedSendStreams());
1136 const auto& send_codec_spec = GetSendStreamConfig(kSsrc1).send_codec_spec;
1137 EXPECT_EQ(96, send_codec_spec.codec_inst.pltype);
1138 EXPECT_EQ(48000, send_codec_spec.codec_inst.rate);
1139 EXPECT_STREQ("ISAC", send_codec_spec.codec_inst.plname);
1140 EXPECT_NE(send_codec_spec.codec_inst.plfreq, send_codec_spec.cng_plfreq);
1141 EXPECT_EQ(13, send_codec_spec.cng_payload_type);
1142 EXPECT_EQ(webrtc::kFreq8000Hz, send_codec_spec.cng_plfreq);
Fredrik Solenbergb5727682015-12-04 15:22:19 +01001143 EXPECT_FALSE(channel_->CanInsertDtmf());
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001144}
1145
wu@webrtc.org05e7b442014-04-01 17:44:24 +00001146// Test that VoE Channel doesn't call SetSendCodec again if same codec is tried
1147// to apply.
1148TEST_F(WebRtcVoiceEngineTestFake, DontResetSetSendCodec) {
solenbergff976312016-03-30 23:28:51 -07001149 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001150 cricket::AudioSendParameters parameters;
1151 parameters.codecs.push_back(kIsacCodec);
1152 parameters.codecs.push_back(kPcmuCodec);
kwiberg68061362016-06-14 08:04:47 -07001153 parameters.codecs.push_back(kCn8000Codec);
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001154 parameters.codecs[0].id = 96;
1155 parameters.codecs[0].bitrate = 48000;
minyue7a973442016-10-20 03:27:12 -07001156 const int initial_num = call_.GetNumCreatedSendStreams();
solenberg059fb442016-10-26 05:12:24 -07001157 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001158 EXPECT_EQ(initial_num + 1, call_.GetNumCreatedSendStreams());
wu@webrtc.org05e7b442014-04-01 17:44:24 +00001159 // Calling SetSendCodec again with same codec which is already set.
1160 // In this case media channel shouldn't send codec to VoE.
solenberg059fb442016-10-26 05:12:24 -07001161 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001162 EXPECT_EQ(initial_num + 1, call_.GetNumCreatedSendStreams());
wu@webrtc.org05e7b442014-04-01 17:44:24 +00001163}
1164
henrik.lundin@webrtc.orgf85dbce2014-11-07 12:25:00 +00001165// Verify that G722 is set with 16000 samples per second to WebRTC.
1166TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecG722) {
solenbergff976312016-03-30 23:28:51 -07001167 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001168 cricket::AudioSendParameters parameters;
1169 parameters.codecs.push_back(kG722CodecSdp);
solenberg059fb442016-10-26 05:12:24 -07001170 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001171 const auto& gcodec = GetSendStreamConfig(kSsrc1).send_codec_spec.codec_inst;
henrik.lundin@webrtc.orgf85dbce2014-11-07 12:25:00 +00001172 EXPECT_STREQ("G722", gcodec.plname);
1173 EXPECT_EQ(1, gcodec.channels);
1174 EXPECT_EQ(16000, gcodec.plfreq);
1175}
1176
henrike@webrtc.org704bf9e2014-02-27 17:52:04 +00001177// Test that if clockrate is not 48000 for opus, we fail.
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001178TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecOpusBadClockrate) {
solenbergff976312016-03-30 23:28:51 -07001179 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001180 cricket::AudioSendParameters parameters;
1181 parameters.codecs.push_back(kOpusCodec);
1182 parameters.codecs[0].bitrate = 0;
1183 parameters.codecs[0].clockrate = 50000;
1184 EXPECT_FALSE(channel_->SetSendParameters(parameters));
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001185}
1186
henrike@webrtc.org704bf9e2014-02-27 17:52:04 +00001187// Test that if channels=0 for opus, we fail.
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001188TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecOpusBad0ChannelsNoStereo) {
solenbergff976312016-03-30 23:28:51 -07001189 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001190 cricket::AudioSendParameters parameters;
1191 parameters.codecs.push_back(kOpusCodec);
1192 parameters.codecs[0].bitrate = 0;
1193 parameters.codecs[0].channels = 0;
1194 EXPECT_FALSE(channel_->SetSendParameters(parameters));
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001195}
1196
henrike@webrtc.org704bf9e2014-02-27 17:52:04 +00001197// Test that if channels=0 for opus, we fail.
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001198TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecOpusBad0Channels1Stereo) {
solenbergff976312016-03-30 23:28:51 -07001199 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001200 cricket::AudioSendParameters parameters;
1201 parameters.codecs.push_back(kOpusCodec);
1202 parameters.codecs[0].bitrate = 0;
1203 parameters.codecs[0].channels = 0;
1204 parameters.codecs[0].params["stereo"] = "1";
1205 EXPECT_FALSE(channel_->SetSendParameters(parameters));
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001206}
1207
1208// Test that if channel is 1 for opus and there's no stereo, we fail.
1209TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecOpus1ChannelNoStereo) {
solenbergff976312016-03-30 23:28:51 -07001210 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001211 cricket::AudioSendParameters parameters;
1212 parameters.codecs.push_back(kOpusCodec);
1213 parameters.codecs[0].bitrate = 0;
1214 parameters.codecs[0].channels = 1;
1215 EXPECT_FALSE(channel_->SetSendParameters(parameters));
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001216}
1217
1218// Test that if channel is 1 for opus and stereo=0, we fail.
1219TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecOpusBad1Channel0Stereo) {
solenbergff976312016-03-30 23:28:51 -07001220 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001221 cricket::AudioSendParameters parameters;
1222 parameters.codecs.push_back(kOpusCodec);
1223 parameters.codecs[0].bitrate = 0;
1224 parameters.codecs[0].channels = 1;
1225 parameters.codecs[0].params["stereo"] = "0";
1226 EXPECT_FALSE(channel_->SetSendParameters(parameters));
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001227}
1228
1229// Test that if channel is 1 for opus and stereo=1, we fail.
1230TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecOpusBad1Channel1Stereo) {
solenbergff976312016-03-30 23:28:51 -07001231 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001232 cricket::AudioSendParameters parameters;
1233 parameters.codecs.push_back(kOpusCodec);
1234 parameters.codecs[0].bitrate = 0;
1235 parameters.codecs[0].channels = 1;
1236 parameters.codecs[0].params["stereo"] = "1";
1237 EXPECT_FALSE(channel_->SetSendParameters(parameters));
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001238}
1239
1240// Test that with bitrate=0 and no stereo,
1241// channels and bitrate are 1 and 32000.
1242TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecOpusGood0BitrateNoStereo) {
solenbergff976312016-03-30 23:28:51 -07001243 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001244 cricket::AudioSendParameters parameters;
1245 parameters.codecs.push_back(kOpusCodec);
1246 parameters.codecs[0].bitrate = 0;
solenberg059fb442016-10-26 05:12:24 -07001247 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001248 CheckSendCodec(kSsrc1, "opus", 1, 32000);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001249}
1250
1251// Test that with bitrate=0 and stereo=0,
1252// channels and bitrate are 1 and 32000.
1253TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecOpusGood0Bitrate0Stereo) {
solenbergff976312016-03-30 23:28:51 -07001254 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001255 cricket::AudioSendParameters parameters;
1256 parameters.codecs.push_back(kOpusCodec);
1257 parameters.codecs[0].bitrate = 0;
1258 parameters.codecs[0].params["stereo"] = "0";
solenberg059fb442016-10-26 05:12:24 -07001259 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001260 CheckSendCodec(kSsrc1, "opus", 1, 32000);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001261}
1262
henrike@webrtc.org1e09a712013-07-26 19:17:59 +00001263// Test that with bitrate=invalid and stereo=0,
1264// channels and bitrate are 1 and 32000.
1265TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecOpusGoodXBitrate0Stereo) {
solenbergff976312016-03-30 23:28:51 -07001266 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001267 cricket::AudioSendParameters parameters;
1268 parameters.codecs.push_back(kOpusCodec);
1269 parameters.codecs[0].params["stereo"] = "0";
buildbot@webrtc.org9d446f22014-10-23 12:22:06 +00001270 // bitrate that's out of the range between 6000 and 510000 will be clamped.
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001271 parameters.codecs[0].bitrate = 5999;
solenberg059fb442016-10-26 05:12:24 -07001272 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001273 CheckSendCodec(kSsrc1, "opus", 1, 6000);
henrike@webrtc.org1e09a712013-07-26 19:17:59 +00001274
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001275 parameters.codecs[0].bitrate = 510001;
solenberg059fb442016-10-26 05:12:24 -07001276 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001277 CheckSendCodec(kSsrc1, "opus", 1, 510000);
henrike@webrtc.org1e09a712013-07-26 19:17:59 +00001278}
1279
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001280// Test that with bitrate=0 and stereo=1,
1281// channels and bitrate are 2 and 64000.
1282TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecOpusGood0Bitrate1Stereo) {
solenbergff976312016-03-30 23:28:51 -07001283 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001284 cricket::AudioSendParameters parameters;
1285 parameters.codecs.push_back(kOpusCodec);
1286 parameters.codecs[0].bitrate = 0;
1287 parameters.codecs[0].params["stereo"] = "1";
solenberg059fb442016-10-26 05:12:24 -07001288 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001289 CheckSendCodec(kSsrc1, "opus", 2, 64000);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001290}
1291
henrike@webrtc.org1e09a712013-07-26 19:17:59 +00001292// Test that with bitrate=invalid and stereo=1,
1293// channels and bitrate are 2 and 64000.
1294TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecOpusGoodXBitrate1Stereo) {
solenbergff976312016-03-30 23:28:51 -07001295 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001296 cricket::AudioSendParameters parameters;
1297 parameters.codecs.push_back(kOpusCodec);
1298 parameters.codecs[0].params["stereo"] = "1";
buildbot@webrtc.org9d446f22014-10-23 12:22:06 +00001299 // bitrate that's out of the range between 6000 and 510000 will be clamped.
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001300 parameters.codecs[0].bitrate = 5999;
solenberg059fb442016-10-26 05:12:24 -07001301 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001302 CheckSendCodec(kSsrc1, "opus", 2, 6000);
henrike@webrtc.org1e09a712013-07-26 19:17:59 +00001303
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001304 parameters.codecs[0].bitrate = 510001;
solenberg059fb442016-10-26 05:12:24 -07001305 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001306 CheckSendCodec(kSsrc1, "opus", 2, 510000);
henrike@webrtc.org1e09a712013-07-26 19:17:59 +00001307}
1308
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001309// Test that with bitrate=N and stereo unset,
1310// channels and bitrate are 1 and N.
1311TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecOpusGoodNBitrateNoStereo) {
solenbergff976312016-03-30 23:28:51 -07001312 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001313 cricket::AudioSendParameters parameters;
1314 parameters.codecs.push_back(kOpusCodec);
1315 parameters.codecs[0].bitrate = 96000;
solenberg059fb442016-10-26 05:12:24 -07001316 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001317 const auto& gcodec = GetSendStreamConfig(kSsrc1).send_codec_spec.codec_inst;
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001318 EXPECT_EQ(111, gcodec.pltype);
1319 EXPECT_EQ(96000, gcodec.rate);
1320 EXPECT_STREQ("opus", gcodec.plname);
1321 EXPECT_EQ(1, gcodec.channels);
1322 EXPECT_EQ(48000, gcodec.plfreq);
1323}
1324
1325// Test that with bitrate=N and stereo=0,
1326// channels and bitrate are 1 and N.
1327TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecOpusGoodNBitrate0Stereo) {
solenbergff976312016-03-30 23:28:51 -07001328 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001329 cricket::AudioSendParameters parameters;
1330 parameters.codecs.push_back(kOpusCodec);
1331 parameters.codecs[0].bitrate = 30000;
1332 parameters.codecs[0].params["stereo"] = "0";
solenberg059fb442016-10-26 05:12:24 -07001333 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001334 CheckSendCodec(kSsrc1, "opus", 1, 30000);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001335}
1336
1337// Test that with bitrate=N and without any parameters,
1338// channels and bitrate are 1 and N.
1339TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecOpusGoodNBitrateNoParameters) {
solenbergff976312016-03-30 23:28:51 -07001340 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001341 cricket::AudioSendParameters parameters;
1342 parameters.codecs.push_back(kOpusCodec);
1343 parameters.codecs[0].bitrate = 30000;
solenberg059fb442016-10-26 05:12:24 -07001344 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001345 CheckSendCodec(kSsrc1, "opus", 1, 30000);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001346}
1347
1348// Test that with bitrate=N and stereo=1,
1349// channels and bitrate are 2 and N.
1350TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecOpusGoodNBitrate1Stereo) {
solenbergff976312016-03-30 23:28:51 -07001351 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001352 cricket::AudioSendParameters parameters;
1353 parameters.codecs.push_back(kOpusCodec);
1354 parameters.codecs[0].bitrate = 30000;
1355 parameters.codecs[0].params["stereo"] = "1";
solenberg059fb442016-10-26 05:12:24 -07001356 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001357 CheckSendCodec(kSsrc1, "opus", 2, 30000);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001358}
1359
henrike@webrtc.org1e09a712013-07-26 19:17:59 +00001360// Test that bitrate will be overridden by the "maxaveragebitrate" parameter.
1361// Also test that the "maxaveragebitrate" can't be set to values outside the
1362// range of 6000 and 510000
1363TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecOpusMaxAverageBitrate) {
solenbergff976312016-03-30 23:28:51 -07001364 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001365 cricket::AudioSendParameters parameters;
1366 parameters.codecs.push_back(kOpusCodec);
1367 parameters.codecs[0].bitrate = 30000;
henrike@webrtc.org1e09a712013-07-26 19:17:59 +00001368 // Ignore if less than 6000.
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001369 parameters.codecs[0].params["maxaveragebitrate"] = "5999";
solenberg059fb442016-10-26 05:12:24 -07001370 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001371 EXPECT_EQ(6000, GetCodecBitrate(kSsrc1));
henrike@webrtc.org1e09a712013-07-26 19:17:59 +00001372
1373 // Ignore if larger than 510000.
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001374 parameters.codecs[0].params["maxaveragebitrate"] = "510001";
solenberg059fb442016-10-26 05:12:24 -07001375 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001376 EXPECT_EQ(510000, GetCodecBitrate(kSsrc1));
henrike@webrtc.org1e09a712013-07-26 19:17:59 +00001377
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001378 parameters.codecs[0].params["maxaveragebitrate"] = "200000";
solenberg059fb442016-10-26 05:12:24 -07001379 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001380 EXPECT_EQ(200000, GetCodecBitrate(kSsrc1));
henrike@webrtc.org1e09a712013-07-26 19:17:59 +00001381}
1382
wu@webrtc.orgcadf9042013-08-30 21:24:16 +00001383// Test that we can enable NACK with opus as caller.
1384TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecEnableNackAsCaller) {
solenbergff976312016-03-30 23:28:51 -07001385 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001386 cricket::AudioSendParameters parameters;
1387 parameters.codecs.push_back(kOpusCodec);
1388 parameters.codecs[0].AddFeedbackParam(
1389 cricket::FeedbackParam(cricket::kRtcpFbParamNack,
1390 cricket::kParamValueEmpty));
solenberg971cab02016-06-14 10:02:41 -07001391 EXPECT_EQ(0, GetSendStreamConfig(kSsrc1).rtp.nack.rtp_history_ms);
solenberg059fb442016-10-26 05:12:24 -07001392 SetSendParameters(parameters);
solenberg971cab02016-06-14 10:02:41 -07001393 EXPECT_EQ(kRtpHistoryMs, GetSendStreamConfig(kSsrc1).rtp.nack.rtp_history_ms);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001394}
1395
wu@webrtc.orgcadf9042013-08-30 21:24:16 +00001396// Test that we can enable NACK with opus as callee.
1397TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecEnableNackAsCallee) {
solenbergff976312016-03-30 23:28:51 -07001398 EXPECT_TRUE(SetupRecvStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001399 cricket::AudioSendParameters parameters;
1400 parameters.codecs.push_back(kOpusCodec);
1401 parameters.codecs[0].AddFeedbackParam(
1402 cricket::FeedbackParam(cricket::kRtcpFbParamNack,
1403 cricket::kParamValueEmpty));
solenberg8189b022016-06-14 12:13:00 -07001404 EXPECT_EQ(0, GetRecvStreamConfig(kSsrc1).rtp.nack.rtp_history_ms);
solenberg059fb442016-10-26 05:12:24 -07001405 SetSendParameters(parameters);
deadbeefb56069e2016-05-06 04:57:03 -07001406 // NACK should be enabled even with no send stream.
solenberg8189b022016-06-14 12:13:00 -07001407 EXPECT_EQ(kRtpHistoryMs, GetRecvStreamConfig(kSsrc1).rtp.nack.rtp_history_ms);
wu@webrtc.orgcadf9042013-08-30 21:24:16 +00001408
1409 EXPECT_TRUE(channel_->AddSendStream(
1410 cricket::StreamParams::CreateLegacy(kSsrc1)));
solenberg971cab02016-06-14 10:02:41 -07001411 EXPECT_EQ(kRtpHistoryMs, GetSendStreamConfig(kSsrc1).rtp.nack.rtp_history_ms);
wu@webrtc.orgcadf9042013-08-30 21:24:16 +00001412}
1413
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001414// Test that we can enable NACK on receive streams.
1415TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecEnableNackRecvStreams) {
solenbergff976312016-03-30 23:28:51 -07001416 EXPECT_TRUE(SetupSendStream());
solenberg8189b022016-06-14 12:13:00 -07001417 EXPECT_TRUE(AddRecvStream(kSsrc2));
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001418 cricket::AudioSendParameters parameters;
1419 parameters.codecs.push_back(kOpusCodec);
1420 parameters.codecs[0].AddFeedbackParam(
1421 cricket::FeedbackParam(cricket::kRtcpFbParamNack,
1422 cricket::kParamValueEmpty));
solenberg971cab02016-06-14 10:02:41 -07001423 EXPECT_EQ(0, GetSendStreamConfig(kSsrc1).rtp.nack.rtp_history_ms);
solenberg8189b022016-06-14 12:13:00 -07001424 EXPECT_EQ(0, GetRecvStreamConfig(kSsrc2).rtp.nack.rtp_history_ms);
solenberg059fb442016-10-26 05:12:24 -07001425 SetSendParameters(parameters);
solenberg971cab02016-06-14 10:02:41 -07001426 EXPECT_EQ(kRtpHistoryMs, GetSendStreamConfig(kSsrc1).rtp.nack.rtp_history_ms);
solenberg8189b022016-06-14 12:13:00 -07001427 EXPECT_EQ(kRtpHistoryMs, GetRecvStreamConfig(kSsrc2).rtp.nack.rtp_history_ms);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001428}
1429
1430// Test that we can disable NACK.
1431TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecDisableNack) {
solenbergff976312016-03-30 23:28:51 -07001432 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001433 cricket::AudioSendParameters parameters;
1434 parameters.codecs.push_back(kOpusCodec);
1435 parameters.codecs[0].AddFeedbackParam(
1436 cricket::FeedbackParam(cricket::kRtcpFbParamNack,
1437 cricket::kParamValueEmpty));
solenberg059fb442016-10-26 05:12:24 -07001438 SetSendParameters(parameters);
solenberg971cab02016-06-14 10:02:41 -07001439 EXPECT_EQ(kRtpHistoryMs, GetSendStreamConfig(kSsrc1).rtp.nack.rtp_history_ms);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001440
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001441 parameters.codecs.clear();
1442 parameters.codecs.push_back(kOpusCodec);
solenberg059fb442016-10-26 05:12:24 -07001443 SetSendParameters(parameters);
solenberg971cab02016-06-14 10:02:41 -07001444 EXPECT_EQ(0, GetSendStreamConfig(kSsrc1).rtp.nack.rtp_history_ms);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001445}
1446
1447// Test that we can disable NACK on receive streams.
1448TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecDisableNackRecvStreams) {
solenbergff976312016-03-30 23:28:51 -07001449 EXPECT_TRUE(SetupSendStream());
solenberg8189b022016-06-14 12:13:00 -07001450 EXPECT_TRUE(AddRecvStream(kSsrc2));
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001451 cricket::AudioSendParameters parameters;
1452 parameters.codecs.push_back(kOpusCodec);
1453 parameters.codecs[0].AddFeedbackParam(
1454 cricket::FeedbackParam(cricket::kRtcpFbParamNack,
1455 cricket::kParamValueEmpty));
solenberg059fb442016-10-26 05:12:24 -07001456 SetSendParameters(parameters);
solenberg971cab02016-06-14 10:02:41 -07001457 EXPECT_EQ(kRtpHistoryMs, GetSendStreamConfig(kSsrc1).rtp.nack.rtp_history_ms);
solenberg8189b022016-06-14 12:13:00 -07001458 EXPECT_EQ(kRtpHistoryMs, GetRecvStreamConfig(kSsrc2).rtp.nack.rtp_history_ms);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001459
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001460 parameters.codecs.clear();
1461 parameters.codecs.push_back(kOpusCodec);
solenberg059fb442016-10-26 05:12:24 -07001462 SetSendParameters(parameters);
solenberg971cab02016-06-14 10:02:41 -07001463 EXPECT_EQ(0, GetSendStreamConfig(kSsrc1).rtp.nack.rtp_history_ms);
solenberg8189b022016-06-14 12:13:00 -07001464 EXPECT_EQ(0, GetRecvStreamConfig(kSsrc2).rtp.nack.rtp_history_ms);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001465}
1466
1467// Test that NACK is enabled on a new receive stream.
1468TEST_F(WebRtcVoiceEngineTestFake, AddRecvStreamEnableNack) {
solenbergff976312016-03-30 23:28:51 -07001469 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001470 cricket::AudioSendParameters parameters;
1471 parameters.codecs.push_back(kIsacCodec);
1472 parameters.codecs.push_back(kCn16000Codec);
1473 parameters.codecs[0].AddFeedbackParam(
1474 cricket::FeedbackParam(cricket::kRtcpFbParamNack,
1475 cricket::kParamValueEmpty));
solenberg059fb442016-10-26 05:12:24 -07001476 SetSendParameters(parameters);
solenberg971cab02016-06-14 10:02:41 -07001477 EXPECT_EQ(kRtpHistoryMs, GetSendStreamConfig(kSsrc1).rtp.nack.rtp_history_ms);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001478
solenberg8189b022016-06-14 12:13:00 -07001479 EXPECT_TRUE(AddRecvStream(kSsrc2));
1480 EXPECT_EQ(kRtpHistoryMs, GetRecvStreamConfig(kSsrc2).rtp.nack.rtp_history_ms);
1481 EXPECT_TRUE(AddRecvStream(kSsrc3));
1482 EXPECT_EQ(kRtpHistoryMs, GetRecvStreamConfig(kSsrc3).rtp.nack.rtp_history_ms);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001483}
1484
buildbot@webrtc.orgae740dd2014-06-17 10:56:41 +00001485// Test that without useinbandfec, Opus FEC is off.
buildbot@webrtc.orgd27d9ae2014-06-19 01:56:46 +00001486TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecNoOpusFec) {
solenbergff976312016-03-30 23:28:51 -07001487 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001488 cricket::AudioSendParameters parameters;
1489 parameters.codecs.push_back(kOpusCodec);
solenberg059fb442016-10-26 05:12:24 -07001490 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001491 EXPECT_FALSE(GetCodecFec(kSsrc1));
buildbot@webrtc.orgae740dd2014-06-17 10:56:41 +00001492}
1493
1494// Test that with useinbandfec=0, Opus FEC is off.
buildbot@webrtc.orgd27d9ae2014-06-19 01:56:46 +00001495TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecOpusDisableFec) {
solenbergff976312016-03-30 23:28:51 -07001496 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001497 cricket::AudioSendParameters parameters;
1498 parameters.codecs.push_back(kOpusCodec);
1499 parameters.codecs[0].bitrate = 0;
1500 parameters.codecs[0].params["useinbandfec"] = "0";
solenberg059fb442016-10-26 05:12:24 -07001501 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001502 CheckSendCodec(kSsrc1, "opus", 1, 32000);
buildbot@webrtc.orgae740dd2014-06-17 10:56:41 +00001503}
1504
1505// Test that with useinbandfec=1, Opus FEC is on.
buildbot@webrtc.orgd27d9ae2014-06-19 01:56:46 +00001506TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecOpusEnableFec) {
solenbergff976312016-03-30 23:28:51 -07001507 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001508 cricket::AudioSendParameters parameters;
1509 parameters.codecs.push_back(kOpusCodec);
1510 parameters.codecs[0].bitrate = 0;
1511 parameters.codecs[0].params["useinbandfec"] = "1";
solenberg059fb442016-10-26 05:12:24 -07001512 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001513 EXPECT_TRUE(GetCodecFec(kSsrc1));
1514 CheckSendCodec(kSsrc1, "opus", 1, 32000);
buildbot@webrtc.orgae740dd2014-06-17 10:56:41 +00001515}
1516
1517// Test that with useinbandfec=1, stereo=1, Opus FEC is on.
buildbot@webrtc.orgd27d9ae2014-06-19 01:56:46 +00001518TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecOpusEnableFecStereo) {
solenbergff976312016-03-30 23:28:51 -07001519 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001520 cricket::AudioSendParameters parameters;
1521 parameters.codecs.push_back(kOpusCodec);
1522 parameters.codecs[0].bitrate = 0;
1523 parameters.codecs[0].params["stereo"] = "1";
1524 parameters.codecs[0].params["useinbandfec"] = "1";
solenberg059fb442016-10-26 05:12:24 -07001525 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001526 EXPECT_TRUE(GetCodecFec(kSsrc1));
1527 CheckSendCodec(kSsrc1, "opus", 2, 64000);
buildbot@webrtc.orgae740dd2014-06-17 10:56:41 +00001528}
1529
1530// Test that with non-Opus, codec FEC is off.
buildbot@webrtc.orgd27d9ae2014-06-19 01:56:46 +00001531TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecIsacNoFec) {
solenbergff976312016-03-30 23:28:51 -07001532 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001533 cricket::AudioSendParameters parameters;
1534 parameters.codecs.push_back(kIsacCodec);
solenberg059fb442016-10-26 05:12:24 -07001535 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001536 EXPECT_FALSE(GetCodecFec(kSsrc1));
buildbot@webrtc.orgae740dd2014-06-17 10:56:41 +00001537}
buildbot@webrtc.org3ffa1f92014-07-02 19:51:26 +00001538
1539// Test the with non-Opus, even if useinbandfec=1, FEC is off.
1540TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecIsacWithParamNoFec) {
solenbergff976312016-03-30 23:28:51 -07001541 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001542 cricket::AudioSendParameters parameters;
1543 parameters.codecs.push_back(kIsacCodec);
1544 parameters.codecs[0].params["useinbandfec"] = "1";
solenberg059fb442016-10-26 05:12:24 -07001545 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001546 EXPECT_FALSE(GetCodecFec(kSsrc1));
buildbot@webrtc.org3ffa1f92014-07-02 19:51:26 +00001547}
buildbot@webrtc.org5d639b32014-09-10 07:57:12 +00001548
1549// Test that Opus FEC status can be changed.
1550TEST_F(WebRtcVoiceEngineTestFake, ChangeOpusFecStatus) {
solenbergff976312016-03-30 23:28:51 -07001551 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001552 cricket::AudioSendParameters parameters;
1553 parameters.codecs.push_back(kOpusCodec);
solenberg059fb442016-10-26 05:12:24 -07001554 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001555 EXPECT_FALSE(GetCodecFec(kSsrc1));
1556
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001557 parameters.codecs[0].params["useinbandfec"] = "1";
solenberg059fb442016-10-26 05:12:24 -07001558 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001559 EXPECT_TRUE(GetCodecFec(kSsrc1));
buildbot@webrtc.org5d639b32014-09-10 07:57:12 +00001560}
1561
stefanba4c0e42016-02-04 04:12:24 -08001562TEST_F(WebRtcVoiceEngineTestFake, TransportCcCanBeEnabledAndDisabled) {
solenbergff976312016-03-30 23:28:51 -07001563 EXPECT_TRUE(SetupChannel());
stefanba4c0e42016-02-04 04:12:24 -08001564 cricket::AudioSendParameters send_parameters;
1565 send_parameters.codecs.push_back(kOpusCodec);
1566 EXPECT_TRUE(send_parameters.codecs[0].feedback_params.params().empty());
solenberg059fb442016-10-26 05:12:24 -07001567 SetSendParameters(send_parameters);
stefanba4c0e42016-02-04 04:12:24 -08001568
1569 cricket::AudioRecvParameters recv_parameters;
1570 recv_parameters.codecs.push_back(kIsacCodec);
1571 EXPECT_TRUE(channel_->SetRecvParameters(recv_parameters));
solenberg8189b022016-06-14 12:13:00 -07001572 EXPECT_TRUE(AddRecvStream(kSsrc1));
stefanba4c0e42016-02-04 04:12:24 -08001573 ASSERT_TRUE(call_.GetAudioReceiveStream(kSsrc1) != nullptr);
1574 EXPECT_FALSE(
1575 call_.GetAudioReceiveStream(kSsrc1)->GetConfig().rtp.transport_cc);
1576
ossudedfd282016-06-14 07:12:39 -07001577 send_parameters.codecs = engine_->send_codecs();
solenberg059fb442016-10-26 05:12:24 -07001578 SetSendParameters(send_parameters);
stefanba4c0e42016-02-04 04:12:24 -08001579 ASSERT_TRUE(call_.GetAudioReceiveStream(kSsrc1) != nullptr);
1580 EXPECT_TRUE(
1581 call_.GetAudioReceiveStream(kSsrc1)->GetConfig().rtp.transport_cc);
1582}
1583
buildbot@webrtc.org5d639b32014-09-10 07:57:12 +00001584// Test maxplaybackrate <= 8000 triggers Opus narrow band mode.
1585TEST_F(WebRtcVoiceEngineTestFake, SetOpusMaxPlaybackRateNb) {
solenbergff976312016-03-30 23:28:51 -07001586 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001587 cricket::AudioSendParameters parameters;
1588 parameters.codecs.push_back(kOpusCodec);
1589 parameters.codecs[0].bitrate = 0;
1590 parameters.codecs[0].SetParam(cricket::kCodecParamMaxPlaybackRate, 8000);
solenberg059fb442016-10-26 05:12:24 -07001591 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001592 EXPECT_EQ(8000, GetOpusMaxPlaybackRate(kSsrc1));
1593 EXPECT_EQ(12000, GetCodecBitrate(kSsrc1));
minyue@webrtc.org2dc6f312014-10-31 05:33:10 +00001594
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001595 parameters.codecs[0].SetParam(cricket::kCodecParamStereo, "1");
solenberg059fb442016-10-26 05:12:24 -07001596 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001597 EXPECT_EQ(24000, GetCodecBitrate(kSsrc1));
buildbot@webrtc.org5d639b32014-09-10 07:57:12 +00001598}
1599
1600// Test 8000 < maxplaybackrate <= 12000 triggers Opus medium band mode.
1601TEST_F(WebRtcVoiceEngineTestFake, SetOpusMaxPlaybackRateMb) {
solenbergff976312016-03-30 23:28:51 -07001602 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001603 cricket::AudioSendParameters parameters;
1604 parameters.codecs.push_back(kOpusCodec);
1605 parameters.codecs[0].bitrate = 0;
1606 parameters.codecs[0].SetParam(cricket::kCodecParamMaxPlaybackRate, 8001);
solenberg059fb442016-10-26 05:12:24 -07001607 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001608 EXPECT_EQ(8001, GetOpusMaxPlaybackRate(kSsrc1));
1609 EXPECT_EQ(20000, GetCodecBitrate(kSsrc1));
minyue@webrtc.org2dc6f312014-10-31 05:33:10 +00001610
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001611 parameters.codecs[0].SetParam(cricket::kCodecParamStereo, "1");
solenberg059fb442016-10-26 05:12:24 -07001612 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001613 EXPECT_EQ(40000, GetCodecBitrate(kSsrc1));
buildbot@webrtc.org5d639b32014-09-10 07:57:12 +00001614}
1615
1616// Test 12000 < maxplaybackrate <= 16000 triggers Opus wide band mode.
1617TEST_F(WebRtcVoiceEngineTestFake, SetOpusMaxPlaybackRateWb) {
solenbergff976312016-03-30 23:28:51 -07001618 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001619 cricket::AudioSendParameters parameters;
1620 parameters.codecs.push_back(kOpusCodec);
1621 parameters.codecs[0].bitrate = 0;
1622 parameters.codecs[0].SetParam(cricket::kCodecParamMaxPlaybackRate, 12001);
solenberg059fb442016-10-26 05:12:24 -07001623 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001624 EXPECT_EQ(12001, GetOpusMaxPlaybackRate(kSsrc1));
1625 EXPECT_EQ(20000, GetCodecBitrate(kSsrc1));
minyue@webrtc.org2dc6f312014-10-31 05:33:10 +00001626
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001627 parameters.codecs[0].SetParam(cricket::kCodecParamStereo, "1");
solenberg059fb442016-10-26 05:12:24 -07001628 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001629 EXPECT_EQ(40000, GetCodecBitrate(kSsrc1));
buildbot@webrtc.org5d639b32014-09-10 07:57:12 +00001630}
1631
1632// Test 16000 < maxplaybackrate <= 24000 triggers Opus super wide band mode.
1633TEST_F(WebRtcVoiceEngineTestFake, SetOpusMaxPlaybackRateSwb) {
solenbergff976312016-03-30 23:28:51 -07001634 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001635 cricket::AudioSendParameters parameters;
1636 parameters.codecs.push_back(kOpusCodec);
1637 parameters.codecs[0].bitrate = 0;
1638 parameters.codecs[0].SetParam(cricket::kCodecParamMaxPlaybackRate, 16001);
solenberg059fb442016-10-26 05:12:24 -07001639 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001640 EXPECT_EQ(16001, GetOpusMaxPlaybackRate(kSsrc1));
1641 EXPECT_EQ(32000, GetCodecBitrate(kSsrc1));
minyue@webrtc.org2dc6f312014-10-31 05:33:10 +00001642
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001643 parameters.codecs[0].SetParam(cricket::kCodecParamStereo, "1");
solenberg059fb442016-10-26 05:12:24 -07001644 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001645 EXPECT_EQ(64000, GetCodecBitrate(kSsrc1));
buildbot@webrtc.org5d639b32014-09-10 07:57:12 +00001646}
1647
1648// Test 24000 < maxplaybackrate triggers Opus full band mode.
1649TEST_F(WebRtcVoiceEngineTestFake, SetOpusMaxPlaybackRateFb) {
solenbergff976312016-03-30 23:28:51 -07001650 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001651 cricket::AudioSendParameters parameters;
1652 parameters.codecs.push_back(kOpusCodec);
1653 parameters.codecs[0].bitrate = 0;
1654 parameters.codecs[0].SetParam(cricket::kCodecParamMaxPlaybackRate, 24001);
solenberg059fb442016-10-26 05:12:24 -07001655 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001656 EXPECT_EQ(24001, GetOpusMaxPlaybackRate(kSsrc1));
1657 EXPECT_EQ(32000, GetCodecBitrate(kSsrc1));
minyue@webrtc.org2dc6f312014-10-31 05:33:10 +00001658
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001659 parameters.codecs[0].SetParam(cricket::kCodecParamStereo, "1");
solenberg059fb442016-10-26 05:12:24 -07001660 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001661 EXPECT_EQ(64000, GetCodecBitrate(kSsrc1));
buildbot@webrtc.org5d639b32014-09-10 07:57:12 +00001662}
1663
1664// Test Opus that without maxplaybackrate, default playback rate is used.
1665TEST_F(WebRtcVoiceEngineTestFake, DefaultOpusMaxPlaybackRate) {
solenbergff976312016-03-30 23:28:51 -07001666 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001667 cricket::AudioSendParameters parameters;
1668 parameters.codecs.push_back(kOpusCodec);
solenberg059fb442016-10-26 05:12:24 -07001669 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001670 EXPECT_EQ(48000, GetOpusMaxPlaybackRate(kSsrc1));
buildbot@webrtc.org5d639b32014-09-10 07:57:12 +00001671}
1672
1673// Test the with non-Opus, maxplaybackrate has no effect.
1674TEST_F(WebRtcVoiceEngineTestFake, SetNonOpusMaxPlaybackRate) {
solenbergff976312016-03-30 23:28:51 -07001675 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001676 cricket::AudioSendParameters parameters;
1677 parameters.codecs.push_back(kIsacCodec);
1678 parameters.codecs[0].SetParam(cricket::kCodecParamMaxPlaybackRate, 32000);
solenberg059fb442016-10-26 05:12:24 -07001679 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001680 EXPECT_EQ(0, GetOpusMaxPlaybackRate(kSsrc1));
buildbot@webrtc.org5d639b32014-09-10 07:57:12 +00001681}
1682
1683// Test maxplaybackrate can be set on two streams.
1684TEST_F(WebRtcVoiceEngineTestFake, SetOpusMaxPlaybackRateOnTwoStreams) {
solenbergff976312016-03-30 23:28:51 -07001685 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001686 cricket::AudioSendParameters parameters;
1687 parameters.codecs.push_back(kOpusCodec);
solenberg059fb442016-10-26 05:12:24 -07001688 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001689 EXPECT_EQ(48000, GetOpusMaxPlaybackRate(kSsrc1));
buildbot@webrtc.org5d639b32014-09-10 07:57:12 +00001690
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001691 parameters.codecs[0].SetParam(cricket::kCodecParamMaxPlaybackRate, 8000);
solenberg059fb442016-10-26 05:12:24 -07001692 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001693 EXPECT_EQ(8000, GetOpusMaxPlaybackRate(kSsrc1));
buildbot@webrtc.org5d639b32014-09-10 07:57:12 +00001694
1695 channel_->AddSendStream(cricket::StreamParams::CreateLegacy(kSsrc2));
minyue7a973442016-10-20 03:27:12 -07001696 EXPECT_EQ(8000, GetOpusMaxPlaybackRate(kSsrc2));
buildbot@webrtc.org5d639b32014-09-10 07:57:12 +00001697}
buildbot@webrtc.orgae740dd2014-06-17 10:56:41 +00001698
Minyue Li7100dcd2015-03-27 05:05:59 +01001699// Test that with usedtx=0, Opus DTX is off.
1700TEST_F(WebRtcVoiceEngineTestFake, DisableOpusDtxOnOpus) {
solenbergff976312016-03-30 23:28:51 -07001701 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001702 cricket::AudioSendParameters parameters;
1703 parameters.codecs.push_back(kOpusCodec);
1704 parameters.codecs[0].params["usedtx"] = "0";
solenberg059fb442016-10-26 05:12:24 -07001705 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001706 EXPECT_FALSE(GetOpusDtx(kSsrc1));
Minyue Li7100dcd2015-03-27 05:05:59 +01001707}
1708
1709// Test that with usedtx=1, Opus DTX is on.
1710TEST_F(WebRtcVoiceEngineTestFake, EnableOpusDtxOnOpus) {
solenbergff976312016-03-30 23:28:51 -07001711 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001712 cricket::AudioSendParameters parameters;
1713 parameters.codecs.push_back(kOpusCodec);
1714 parameters.codecs[0].params["usedtx"] = "1";
solenberg059fb442016-10-26 05:12:24 -07001715 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001716 EXPECT_TRUE(GetOpusDtx(kSsrc1));
Minyue Li7100dcd2015-03-27 05:05:59 +01001717}
1718
1719// Test that usedtx=1 works with stereo Opus.
1720TEST_F(WebRtcVoiceEngineTestFake, EnableOpusDtxOnOpusStereo) {
solenbergff976312016-03-30 23:28:51 -07001721 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001722 cricket::AudioSendParameters parameters;
1723 parameters.codecs.push_back(kOpusCodec);
1724 parameters.codecs[0].params["usedtx"] = "1";
1725 parameters.codecs[0].params["stereo"] = "1";
solenberg059fb442016-10-26 05:12:24 -07001726 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001727 EXPECT_TRUE(GetOpusDtx(kSsrc1));
Minyue Li7100dcd2015-03-27 05:05:59 +01001728}
1729
1730// Test that usedtx=1 does not work with non Opus.
1731TEST_F(WebRtcVoiceEngineTestFake, CannotEnableOpusDtxOnNonOpus) {
solenbergff976312016-03-30 23:28:51 -07001732 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001733 cricket::AudioSendParameters parameters;
1734 parameters.codecs.push_back(kIsacCodec);
1735 parameters.codecs[0].params["usedtx"] = "1";
solenberg059fb442016-10-26 05:12:24 -07001736 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001737 EXPECT_FALSE(GetOpusDtx(kSsrc1));
Minyue Li7100dcd2015-03-27 05:05:59 +01001738}
1739
minyue@webrtc.orgf9b5c1b2015-02-17 12:36:41 +00001740// Test that we can switch back and forth between Opus and ISAC with CN.
1741TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecsIsacOpusSwitching) {
solenbergff976312016-03-30 23:28:51 -07001742 EXPECT_TRUE(SetupSendStream());
minyue7a973442016-10-20 03:27:12 -07001743
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001744 cricket::AudioSendParameters opus_parameters;
1745 opus_parameters.codecs.push_back(kOpusCodec);
solenberg059fb442016-10-26 05:12:24 -07001746 SetSendParameters(opus_parameters);
minyue7a973442016-10-20 03:27:12 -07001747 {
1748 const auto& gcodec = GetSendStreamConfig(kSsrc1).send_codec_spec.codec_inst;
1749 EXPECT_EQ(111, gcodec.pltype);
1750 EXPECT_STREQ("opus", gcodec.plname);
1751 }
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001752
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001753 cricket::AudioSendParameters isac_parameters;
1754 isac_parameters.codecs.push_back(kIsacCodec);
1755 isac_parameters.codecs.push_back(kCn16000Codec);
1756 isac_parameters.codecs.push_back(kOpusCodec);
solenberg059fb442016-10-26 05:12:24 -07001757 SetSendParameters(isac_parameters);
minyue7a973442016-10-20 03:27:12 -07001758 {
1759 const auto& gcodec = GetSendStreamConfig(kSsrc1).send_codec_spec.codec_inst;
1760 EXPECT_EQ(103, gcodec.pltype);
1761 EXPECT_STREQ("ISAC", gcodec.plname);
1762 }
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001763
solenberg059fb442016-10-26 05:12:24 -07001764 SetSendParameters(opus_parameters);
minyue7a973442016-10-20 03:27:12 -07001765 {
1766 const auto& gcodec = GetSendStreamConfig(kSsrc1).send_codec_spec.codec_inst;
1767 EXPECT_EQ(111, gcodec.pltype);
1768 EXPECT_STREQ("opus", gcodec.plname);
1769 }
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001770}
1771
1772// Test that we handle various ways of specifying bitrate.
1773TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecsBitrate) {
solenbergff976312016-03-30 23:28:51 -07001774 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001775 cricket::AudioSendParameters parameters;
1776 parameters.codecs.push_back(kIsacCodec); // bitrate == 32000
solenberg059fb442016-10-26 05:12:24 -07001777 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001778 {
1779 const auto& gcodec = GetSendStreamConfig(kSsrc1).send_codec_spec.codec_inst;
1780 EXPECT_EQ(103, gcodec.pltype);
1781 EXPECT_STREQ("ISAC", gcodec.plname);
1782 EXPECT_EQ(32000, gcodec.rate);
1783 }
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001784
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001785 parameters.codecs[0].bitrate = 0; // bitrate == default
solenberg059fb442016-10-26 05:12:24 -07001786 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001787 {
1788 const auto& gcodec = GetSendStreamConfig(kSsrc1).send_codec_spec.codec_inst;
1789 EXPECT_EQ(103, gcodec.pltype);
1790 EXPECT_STREQ("ISAC", gcodec.plname);
1791 EXPECT_EQ(-1, gcodec.rate);
1792 }
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001793 parameters.codecs[0].bitrate = 28000; // bitrate == 28000
solenberg059fb442016-10-26 05:12:24 -07001794 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001795 {
1796 const auto& gcodec = GetSendStreamConfig(kSsrc1).send_codec_spec.codec_inst;
1797 EXPECT_EQ(103, gcodec.pltype);
1798 EXPECT_STREQ("ISAC", gcodec.plname);
1799 EXPECT_EQ(28000, gcodec.rate);
1800 }
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001801
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001802 parameters.codecs[0] = kPcmuCodec; // bitrate == 64000
solenberg059fb442016-10-26 05:12:24 -07001803 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001804 {
1805 const auto& gcodec = GetSendStreamConfig(kSsrc1).send_codec_spec.codec_inst;
1806 EXPECT_EQ(0, gcodec.pltype);
1807 EXPECT_STREQ("PCMU", gcodec.plname);
1808 EXPECT_EQ(64000, gcodec.rate);
1809 }
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001810
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001811 parameters.codecs[0].bitrate = 0; // bitrate == default
solenberg059fb442016-10-26 05:12:24 -07001812 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001813 {
1814 const auto& gcodec = GetSendStreamConfig(kSsrc1).send_codec_spec.codec_inst;
1815 EXPECT_EQ(0, gcodec.pltype);
1816 EXPECT_STREQ("PCMU", gcodec.plname);
1817 EXPECT_EQ(64000, gcodec.rate);
1818 }
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001819
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001820 parameters.codecs[0] = kOpusCodec;
1821 parameters.codecs[0].bitrate = 0; // bitrate == default
solenberg059fb442016-10-26 05:12:24 -07001822 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001823 {
1824 const auto& gcodec = GetSendStreamConfig(kSsrc1).send_codec_spec.codec_inst;
1825 EXPECT_EQ(111, gcodec.pltype);
1826 EXPECT_STREQ("opus", gcodec.plname);
1827 EXPECT_EQ(32000, gcodec.rate);
1828 }
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001829}
1830
Brave Yao5225dd82015-03-26 07:39:19 +08001831// Test that we could set packet size specified in kCodecParamPTime.
1832TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecsPTimeAsPacketSize) {
solenbergff976312016-03-30 23:28:51 -07001833 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001834 cricket::AudioSendParameters parameters;
1835 parameters.codecs.push_back(kOpusCodec);
1836 parameters.codecs[0].SetParam(cricket::kCodecParamPTime, 40); // Within range.
solenberg059fb442016-10-26 05:12:24 -07001837 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001838 EXPECT_EQ(1920, GetCodecPacSize(kSsrc1)); // Opus gets 40ms.
Brave Yao5225dd82015-03-26 07:39:19 +08001839
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001840 parameters.codecs[0].SetParam(cricket::kCodecParamPTime, 5); // Below range.
solenberg059fb442016-10-26 05:12:24 -07001841 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001842 EXPECT_EQ(480, GetCodecPacSize(kSsrc1)); // Opus gets 10ms.
Brave Yao5225dd82015-03-26 07:39:19 +08001843
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001844 parameters.codecs[0].SetParam(cricket::kCodecParamPTime, 80); // Beyond range.
solenberg059fb442016-10-26 05:12:24 -07001845 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001846 EXPECT_EQ(2880, GetCodecPacSize(kSsrc1)); // Opus gets 60ms.
Brave Yao5225dd82015-03-26 07:39:19 +08001847
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001848 parameters.codecs[0] = kIsacCodec; // Also try Isac, with unsupported size.
1849 parameters.codecs[0].SetParam(cricket::kCodecParamPTime, 40); // Within range.
solenberg059fb442016-10-26 05:12:24 -07001850 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001851 EXPECT_EQ(480, GetCodecPacSize(
1852 kSsrc1)); // Isac gets 30ms as the next smallest value.
Brave Yao5225dd82015-03-26 07:39:19 +08001853
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001854 parameters.codecs[0] = kG722CodecSdp; // Try G722 @8kHz as negotiated in SDP.
1855 parameters.codecs[0].SetParam(cricket::kCodecParamPTime, 40);
solenberg059fb442016-10-26 05:12:24 -07001856 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001857 EXPECT_EQ(640, GetCodecPacSize(
1858 kSsrc1)); // G722 gets 40ms @16kHz as defined in VoE.
Brave Yao5225dd82015-03-26 07:39:19 +08001859}
1860
henrike@webrtc.org704bf9e2014-02-27 17:52:04 +00001861// Test that we fail if no codecs are specified.
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001862TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecsNoCodecs) {
solenbergff976312016-03-30 23:28:51 -07001863 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001864 cricket::AudioSendParameters parameters;
1865 EXPECT_FALSE(channel_->SetSendParameters(parameters));
henrike@webrtc.org704bf9e2014-02-27 17:52:04 +00001866}
1867
1868// Test that we can set send codecs even with telephone-event codec as the first
1869// one on the list.
1870TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecsDTMFOnTop) {
solenbergff976312016-03-30 23:28:51 -07001871 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001872 cricket::AudioSendParameters parameters;
solenberg2779bab2016-11-17 04:45:19 -08001873 parameters.codecs.push_back(kTelephoneEventCodec1);
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001874 parameters.codecs.push_back(kIsacCodec);
1875 parameters.codecs.push_back(kPcmuCodec);
1876 parameters.codecs[0].id = 98; // DTMF
1877 parameters.codecs[1].id = 96;
solenberg059fb442016-10-26 05:12:24 -07001878 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001879 const auto& gcodec = GetSendStreamConfig(kSsrc1).send_codec_spec.codec_inst;
henrike@webrtc.org704bf9e2014-02-27 17:52:04 +00001880 EXPECT_EQ(96, gcodec.pltype);
1881 EXPECT_STREQ("ISAC", gcodec.plname);
Fredrik Solenbergb5727682015-12-04 15:22:19 +01001882 EXPECT_TRUE(channel_->CanInsertDtmf());
henrike@webrtc.org704bf9e2014-02-27 17:52:04 +00001883}
1884
solenberg31642aa2016-03-14 08:00:37 -07001885// Test that payload type range is limited for telephone-event codec.
1886TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecsDTMFPayloadTypeOutOfRange) {
solenbergff976312016-03-30 23:28:51 -07001887 EXPECT_TRUE(SetupSendStream());
solenberg31642aa2016-03-14 08:00:37 -07001888 cricket::AudioSendParameters parameters;
solenbergffbbcac2016-11-17 05:25:37 -08001889 parameters.codecs.push_back(kTelephoneEventCodec2);
solenberg31642aa2016-03-14 08:00:37 -07001890 parameters.codecs.push_back(kIsacCodec);
1891 parameters.codecs[0].id = 0; // DTMF
1892 parameters.codecs[1].id = 96;
solenberg059fb442016-10-26 05:12:24 -07001893 SetSendParameters(parameters);
solenberg31642aa2016-03-14 08:00:37 -07001894 EXPECT_TRUE(channel_->CanInsertDtmf());
1895 parameters.codecs[0].id = 128; // DTMF
1896 EXPECT_FALSE(channel_->SetSendParameters(parameters));
1897 EXPECT_FALSE(channel_->CanInsertDtmf());
1898 parameters.codecs[0].id = 127;
solenberg059fb442016-10-26 05:12:24 -07001899 SetSendParameters(parameters);
solenberg31642aa2016-03-14 08:00:37 -07001900 EXPECT_TRUE(channel_->CanInsertDtmf());
1901 parameters.codecs[0].id = -1; // DTMF
1902 EXPECT_FALSE(channel_->SetSendParameters(parameters));
1903 EXPECT_FALSE(channel_->CanInsertDtmf());
1904}
1905
henrike@webrtc.org704bf9e2014-02-27 17:52:04 +00001906// Test that we can set send codecs even with CN codec as the first
1907// one on the list.
1908TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecsCNOnTop) {
solenbergff976312016-03-30 23:28:51 -07001909 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001910 cricket::AudioSendParameters parameters;
1911 parameters.codecs.push_back(kCn16000Codec);
1912 parameters.codecs.push_back(kIsacCodec);
1913 parameters.codecs.push_back(kPcmuCodec);
1914 parameters.codecs[0].id = 98; // wideband CN
1915 parameters.codecs[1].id = 96;
solenberg059fb442016-10-26 05:12:24 -07001916 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001917 const auto& send_codec_spec = GetSendStreamConfig(kSsrc1).send_codec_spec;
1918 EXPECT_EQ(96, send_codec_spec.codec_inst.pltype);
1919 EXPECT_STREQ("ISAC", send_codec_spec.codec_inst.plname);
1920 EXPECT_EQ(98, send_codec_spec.cng_payload_type);
1921 EXPECT_EQ(webrtc::kFreq16000Hz, send_codec_spec.cng_plfreq);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001922}
1923
wu@webrtc.orgcadf9042013-08-30 21:24:16 +00001924// Test that we set VAD and DTMF types correctly as caller.
1925TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecsCNandDTMFAsCaller) {
solenbergff976312016-03-30 23:28:51 -07001926 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001927 cricket::AudioSendParameters parameters;
1928 parameters.codecs.push_back(kIsacCodec);
1929 parameters.codecs.push_back(kPcmuCodec);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001930 // TODO(juberti): cn 32000
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001931 parameters.codecs.push_back(kCn16000Codec);
1932 parameters.codecs.push_back(kCn8000Codec);
solenberg2779bab2016-11-17 04:45:19 -08001933 parameters.codecs.push_back(kTelephoneEventCodec1);
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001934 parameters.codecs[0].id = 96;
1935 parameters.codecs[2].id = 97; // wideband CN
1936 parameters.codecs[4].id = 98; // DTMF
solenberg059fb442016-10-26 05:12:24 -07001937 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001938 const auto& send_codec_spec = GetSendStreamConfig(kSsrc1).send_codec_spec;
1939 EXPECT_EQ(96, send_codec_spec.codec_inst.pltype);
1940 EXPECT_STREQ("ISAC", send_codec_spec.codec_inst.plname);
1941 EXPECT_EQ(1, send_codec_spec.codec_inst.channels);
1942 EXPECT_EQ(send_codec_spec.codec_inst.plfreq, send_codec_spec.cng_plfreq);
1943 EXPECT_EQ(97, send_codec_spec.cng_payload_type);
1944 EXPECT_EQ(webrtc::kFreq16000Hz, send_codec_spec.cng_plfreq);
Fredrik Solenbergb5727682015-12-04 15:22:19 +01001945 EXPECT_TRUE(channel_->CanInsertDtmf());
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001946}
1947
wu@webrtc.orgcadf9042013-08-30 21:24:16 +00001948// Test that we set VAD and DTMF types correctly as callee.
1949TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecsCNandDTMFAsCallee) {
solenbergff976312016-03-30 23:28:51 -07001950 EXPECT_TRUE(SetupChannel());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001951 cricket::AudioSendParameters parameters;
1952 parameters.codecs.push_back(kIsacCodec);
1953 parameters.codecs.push_back(kPcmuCodec);
wu@webrtc.orgcadf9042013-08-30 21:24:16 +00001954 // TODO(juberti): cn 32000
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001955 parameters.codecs.push_back(kCn16000Codec);
1956 parameters.codecs.push_back(kCn8000Codec);
solenbergffbbcac2016-11-17 05:25:37 -08001957 parameters.codecs.push_back(kTelephoneEventCodec2);
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001958 parameters.codecs[0].id = 96;
1959 parameters.codecs[2].id = 97; // wideband CN
1960 parameters.codecs[4].id = 98; // DTMF
solenberg059fb442016-10-26 05:12:24 -07001961 SetSendParameters(parameters);
wu@webrtc.orgcadf9042013-08-30 21:24:16 +00001962 EXPECT_TRUE(channel_->AddSendStream(
1963 cricket::StreamParams::CreateLegacy(kSsrc1)));
1964
minyue7a973442016-10-20 03:27:12 -07001965 const auto& send_codec_spec = GetSendStreamConfig(kSsrc1).send_codec_spec;
1966 EXPECT_EQ(96, send_codec_spec.codec_inst.pltype);
1967 EXPECT_STREQ("ISAC", send_codec_spec.codec_inst.plname);
1968 EXPECT_EQ(1, send_codec_spec.codec_inst.channels);
1969 EXPECT_EQ(send_codec_spec.codec_inst.plfreq, send_codec_spec.cng_plfreq);
1970 EXPECT_EQ(97, send_codec_spec.cng_payload_type);
1971 EXPECT_EQ(webrtc::kFreq16000Hz, send_codec_spec.cng_plfreq);
Fredrik Solenbergb5727682015-12-04 15:22:19 +01001972 EXPECT_TRUE(channel_->CanInsertDtmf());
wu@webrtc.orgcadf9042013-08-30 21:24:16 +00001973}
1974
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001975// Test that we only apply VAD if we have a CN codec that matches the
1976// send codec clockrate.
1977TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecsCNNoMatch) {
solenbergff976312016-03-30 23:28:51 -07001978 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001979 cricket::AudioSendParameters parameters;
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001980 // Set ISAC(16K) and CN(16K). VAD should be activated.
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001981 parameters.codecs.push_back(kIsacCodec);
1982 parameters.codecs.push_back(kCn16000Codec);
1983 parameters.codecs[1].id = 97;
solenberg059fb442016-10-26 05:12:24 -07001984 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001985 {
1986 const auto& send_codec_spec = GetSendStreamConfig(kSsrc1).send_codec_spec;
1987 EXPECT_STREQ("ISAC", send_codec_spec.codec_inst.plname);
1988 EXPECT_EQ(1, send_codec_spec.codec_inst.channels);
1989 EXPECT_EQ(send_codec_spec.codec_inst.plfreq, send_codec_spec.cng_plfreq);
1990 EXPECT_EQ(97, send_codec_spec.cng_payload_type);
1991 EXPECT_EQ(webrtc::kFreq16000Hz, send_codec_spec.cng_plfreq);
1992 }
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001993 // Set PCMU(8K) and CN(16K). VAD should not be activated.
Fredrik Solenbergb071a192015-09-17 16:42:56 +02001994 parameters.codecs[0] = kPcmuCodec;
solenberg059fb442016-10-26 05:12:24 -07001995 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07001996 {
1997 const auto& send_codec_spec = GetSendStreamConfig(kSsrc1).send_codec_spec;
1998 EXPECT_STREQ("PCMU", send_codec_spec.codec_inst.plname);
1999 EXPECT_NE(send_codec_spec.codec_inst.plfreq, send_codec_spec.cng_plfreq);
2000 }
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002001 // Set PCMU(8K) and CN(8K). VAD should be activated.
Fredrik Solenbergb071a192015-09-17 16:42:56 +02002002 parameters.codecs[1] = kCn8000Codec;
solenberg059fb442016-10-26 05:12:24 -07002003 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07002004 {
2005 const auto& send_codec_spec = GetSendStreamConfig(kSsrc1).send_codec_spec;
2006 EXPECT_STREQ("PCMU", send_codec_spec.codec_inst.plname);
2007 EXPECT_EQ(1, send_codec_spec.codec_inst.channels);
2008 EXPECT_EQ(send_codec_spec.codec_inst.plfreq, send_codec_spec.cng_plfreq);
2009 EXPECT_EQ(13, send_codec_spec.cng_payload_type);
2010 EXPECT_EQ(webrtc::kFreq8000Hz, send_codec_spec.cng_plfreq);
2011 }
Brave Yao5225dd82015-03-26 07:39:19 +08002012 // Set ISAC(16K) and CN(8K). VAD should not be activated.
Fredrik Solenbergb071a192015-09-17 16:42:56 +02002013 parameters.codecs[0] = kIsacCodec;
solenberg059fb442016-10-26 05:12:24 -07002014 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07002015 {
2016 const auto& send_codec_spec = GetSendStreamConfig(kSsrc1).send_codec_spec;
2017 EXPECT_STREQ("ISAC", send_codec_spec.codec_inst.plname);
2018 EXPECT_NE(send_codec_spec.codec_inst.plfreq, send_codec_spec.cng_plfreq);
2019 }
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002020}
2021
2022// Test that we perform case-insensitive matching of codec names.
2023TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecsCaseInsensitive) {
solenbergff976312016-03-30 23:28:51 -07002024 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02002025 cricket::AudioSendParameters parameters;
2026 parameters.codecs.push_back(kIsacCodec);
2027 parameters.codecs.push_back(kPcmuCodec);
2028 parameters.codecs.push_back(kCn16000Codec);
2029 parameters.codecs.push_back(kCn8000Codec);
solenberg2779bab2016-11-17 04:45:19 -08002030 parameters.codecs.push_back(kTelephoneEventCodec1);
Fredrik Solenbergb071a192015-09-17 16:42:56 +02002031 parameters.codecs[0].name = "iSaC";
2032 parameters.codecs[0].id = 96;
2033 parameters.codecs[2].id = 97; // wideband CN
2034 parameters.codecs[4].id = 98; // DTMF
solenberg059fb442016-10-26 05:12:24 -07002035 SetSendParameters(parameters);
minyue7a973442016-10-20 03:27:12 -07002036 const auto& send_codec_spec = GetSendStreamConfig(kSsrc1).send_codec_spec;
2037 EXPECT_EQ(96, send_codec_spec.codec_inst.pltype);
2038 EXPECT_STREQ("ISAC", send_codec_spec.codec_inst.plname);
2039 EXPECT_EQ(1, send_codec_spec.codec_inst.channels);
2040 EXPECT_EQ(send_codec_spec.codec_inst.plfreq, send_codec_spec.cng_plfreq);
2041 EXPECT_EQ(97, send_codec_spec.cng_payload_type);
2042 EXPECT_EQ(webrtc::kFreq16000Hz, send_codec_spec.cng_plfreq);
Fredrik Solenbergb5727682015-12-04 15:22:19 +01002043 EXPECT_TRUE(channel_->CanInsertDtmf());
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002044}
2045
stefanba4c0e42016-02-04 04:12:24 -08002046class WebRtcVoiceEngineWithSendSideBweTest : public WebRtcVoiceEngineTestFake {
2047 public:
2048 WebRtcVoiceEngineWithSendSideBweTest()
2049 : WebRtcVoiceEngineTestFake("WebRTC-Audio-SendSideBwe/Enabled/") {}
2050};
2051
2052TEST_F(WebRtcVoiceEngineWithSendSideBweTest,
2053 SupportsTransportSequenceNumberHeaderExtension) {
solenbergbc37fc82016-04-04 09:54:44 -07002054 cricket::RtpCapabilities capabilities = engine_->GetCapabilities();
stefanba4c0e42016-02-04 04:12:24 -08002055 ASSERT_FALSE(capabilities.header_extensions.empty());
isheriff6f8d6862016-05-26 11:24:55 -07002056 for (const webrtc::RtpExtension& extension : capabilities.header_extensions) {
2057 if (extension.uri == webrtc::RtpExtension::kTransportSequenceNumberUri) {
2058 EXPECT_EQ(webrtc::RtpExtension::kTransportSequenceNumberDefaultId,
stefanba4c0e42016-02-04 04:12:24 -08002059 extension.id);
2060 return;
2061 }
2062 }
2063 FAIL() << "Transport sequence number extension not in header-extension list.";
2064}
2065
buildbot@webrtc.org150835e2014-05-06 15:54:38 +00002066// Test support for audio level header extension.
2067TEST_F(WebRtcVoiceEngineTestFake, SendAudioLevelHeaderExtensions) {
isheriff6f8d6862016-05-26 11:24:55 -07002068 TestSetSendRtpHeaderExtensions(webrtc::RtpExtension::kAudioLevelUri);
henrike@webrtc.org79047f92014-03-06 23:46:59 +00002069}
buildbot@webrtc.org150835e2014-05-06 15:54:38 +00002070TEST_F(WebRtcVoiceEngineTestFake, RecvAudioLevelHeaderExtensions) {
isheriff6f8d6862016-05-26 11:24:55 -07002071 TestSetRecvRtpHeaderExtensions(webrtc::RtpExtension::kAudioLevelUri);
buildbot@webrtc.org150835e2014-05-06 15:54:38 +00002072}
henrike@webrtc.org79047f92014-03-06 23:46:59 +00002073
solenbergd4adce42016-11-17 06:26:52 -08002074// Test support for transport sequence number header extension.
2075TEST_F(WebRtcVoiceEngineTestFake, SendTransportSequenceNumberHeaderExtensions) {
2076 TestSetSendRtpHeaderExtensions(
2077 webrtc::RtpExtension::kTransportSequenceNumberUri);
buildbot@webrtc.org150835e2014-05-06 15:54:38 +00002078}
solenbergd4adce42016-11-17 06:26:52 -08002079TEST_F(WebRtcVoiceEngineTestFake, RecvTransportSequenceNumberHeaderExtensions) {
2080 TestSetRecvRtpHeaderExtensions(
2081 webrtc::RtpExtension::kTransportSequenceNumberUri);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002082}
2083
solenberg1ac56142015-10-13 03:58:19 -07002084// Test that we can create a channel and start sending on it.
2085TEST_F(WebRtcVoiceEngineTestFake, Send) {
solenbergff976312016-03-30 23:28:51 -07002086 EXPECT_TRUE(SetupSendStream());
solenberg059fb442016-10-26 05:12:24 -07002087 SetSendParameters(send_parameters_);
2088 SetSend(true);
Taylor Brandstetter1a018dc2016-03-08 12:37:39 -08002089 EXPECT_TRUE(GetSendStream(kSsrc1).IsSending());
solenberg059fb442016-10-26 05:12:24 -07002090 SetSend(false);
Taylor Brandstetter1a018dc2016-03-08 12:37:39 -08002091 EXPECT_FALSE(GetSendStream(kSsrc1).IsSending());
2092}
2093
2094// Test that a channel will send if and only if it has a source and is enabled
2095// for sending.
2096TEST_F(WebRtcVoiceEngineTestFake, SendStateWithAndWithoutSource) {
solenbergff976312016-03-30 23:28:51 -07002097 EXPECT_TRUE(SetupSendStream());
solenberg059fb442016-10-26 05:12:24 -07002098 SetSendParameters(send_parameters_);
2099 SetAudioSend(kSsrc1, true, nullptr);
2100 SetSend(true);
Taylor Brandstetter1a018dc2016-03-08 12:37:39 -08002101 EXPECT_FALSE(GetSendStream(kSsrc1).IsSending());
solenberg059fb442016-10-26 05:12:24 -07002102 SetAudioSend(kSsrc1, true, &fake_source_);
Taylor Brandstetter1a018dc2016-03-08 12:37:39 -08002103 EXPECT_TRUE(GetSendStream(kSsrc1).IsSending());
solenberg059fb442016-10-26 05:12:24 -07002104 SetAudioSend(kSsrc1, true, nullptr);
Taylor Brandstetter1a018dc2016-03-08 12:37:39 -08002105 EXPECT_FALSE(GetSendStream(kSsrc1).IsSending());
solenberg1ac56142015-10-13 03:58:19 -07002106}
2107
solenberg94218532016-06-16 10:53:22 -07002108// Test that a channel is muted/unmuted.
2109TEST_F(WebRtcVoiceEngineTestFake, SendStateMuteUnmute) {
2110 EXPECT_TRUE(SetupSendStream());
solenberg059fb442016-10-26 05:12:24 -07002111 SetSendParameters(send_parameters_);
solenberg94218532016-06-16 10:53:22 -07002112 EXPECT_FALSE(GetSendStream(kSsrc1).muted());
solenberg059fb442016-10-26 05:12:24 -07002113 SetAudioSend(kSsrc1, true, nullptr);
solenberg94218532016-06-16 10:53:22 -07002114 EXPECT_FALSE(GetSendStream(kSsrc1).muted());
solenberg059fb442016-10-26 05:12:24 -07002115 SetAudioSend(kSsrc1, false, nullptr);
solenberg94218532016-06-16 10:53:22 -07002116 EXPECT_TRUE(GetSendStream(kSsrc1).muted());
2117}
2118
solenberg6d6e7c52016-04-13 09:07:30 -07002119// Test that SetSendParameters() does not alter a stream's send state.
2120TEST_F(WebRtcVoiceEngineTestFake, SendStateWhenStreamsAreRecreated) {
2121 EXPECT_TRUE(SetupSendStream());
2122 EXPECT_FALSE(GetSendStream(kSsrc1).IsSending());
2123
2124 // Turn on sending.
solenberg059fb442016-10-26 05:12:24 -07002125 SetSend(true);
solenberg6d6e7c52016-04-13 09:07:30 -07002126 EXPECT_TRUE(GetSendStream(kSsrc1).IsSending());
2127
2128 // Changing RTP header extensions will recreate the AudioSendStream.
2129 send_parameters_.extensions.push_back(
isheriff6f8d6862016-05-26 11:24:55 -07002130 webrtc::RtpExtension(webrtc::RtpExtension::kAudioLevelUri, 12));
solenberg059fb442016-10-26 05:12:24 -07002131 SetSendParameters(send_parameters_);
solenberg6d6e7c52016-04-13 09:07:30 -07002132 EXPECT_TRUE(GetSendStream(kSsrc1).IsSending());
2133
2134 // Turn off sending.
solenberg059fb442016-10-26 05:12:24 -07002135 SetSend(false);
solenberg6d6e7c52016-04-13 09:07:30 -07002136 EXPECT_FALSE(GetSendStream(kSsrc1).IsSending());
2137
2138 // Changing RTP header extensions will recreate the AudioSendStream.
2139 send_parameters_.extensions.clear();
solenberg059fb442016-10-26 05:12:24 -07002140 SetSendParameters(send_parameters_);
solenberg6d6e7c52016-04-13 09:07:30 -07002141 EXPECT_FALSE(GetSendStream(kSsrc1).IsSending());
2142}
2143
solenberg1ac56142015-10-13 03:58:19 -07002144// Test that we can create a channel and start playing out on it.
2145TEST_F(WebRtcVoiceEngineTestFake, Playout) {
solenbergff976312016-03-30 23:28:51 -07002146 EXPECT_TRUE(SetupRecvStream());
solenberg1ac56142015-10-13 03:58:19 -07002147 EXPECT_TRUE(channel_->SetRecvParameters(recv_parameters_));
aleloi84ef6152016-08-04 05:28:21 -07002148 channel_->SetPlayout(true);
2149 EXPECT_TRUE(GetRecvStream(kSsrc1).started());
2150 channel_->SetPlayout(false);
2151 EXPECT_FALSE(GetRecvStream(kSsrc1).started());
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002152}
2153
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002154// Test that we can add and remove send streams.
2155TEST_F(WebRtcVoiceEngineTestFake, CreateAndDeleteMultipleSendStreams) {
2156 SetupForMultiSendStream();
2157
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002158 // Set the global state for sending.
solenberg059fb442016-10-26 05:12:24 -07002159 SetSend(true);
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002160
solenbergc96df772015-10-21 13:01:53 -07002161 for (uint32_t ssrc : kSsrcs4) {
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002162 EXPECT_TRUE(channel_->AddSendStream(
solenbergc96df772015-10-21 13:01:53 -07002163 cricket::StreamParams::CreateLegacy(ssrc)));
solenberg059fb442016-10-26 05:12:24 -07002164 SetAudioSend(ssrc, true, &fake_source_);
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002165 // Verify that we are in a sending state for all the created streams.
Taylor Brandstetter1a018dc2016-03-08 12:37:39 -08002166 EXPECT_TRUE(GetSendStream(ssrc).IsSending());
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002167 }
tfarina5237aaf2015-11-10 23:44:30 -08002168 EXPECT_EQ(arraysize(kSsrcs4), call_.GetAudioSendStreams().size());
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002169
solenbergc96df772015-10-21 13:01:53 -07002170 // Delete the send streams.
2171 for (uint32_t ssrc : kSsrcs4) {
2172 EXPECT_TRUE(channel_->RemoveSendStream(ssrc));
solenberg3a941542015-11-16 07:34:50 -08002173 EXPECT_FALSE(call_.GetAudioSendStream(ssrc));
solenbergc96df772015-10-21 13:01:53 -07002174 EXPECT_FALSE(channel_->RemoveSendStream(ssrc));
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002175 }
solenbergc96df772015-10-21 13:01:53 -07002176 EXPECT_EQ(0u, call_.GetAudioSendStreams().size());
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002177}
2178
2179// Test SetSendCodecs correctly configure the codecs in all send streams.
2180TEST_F(WebRtcVoiceEngineTestFake, SetSendCodecsWithMultipleSendStreams) {
2181 SetupForMultiSendStream();
2182
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002183 // Create send streams.
solenbergc96df772015-10-21 13:01:53 -07002184 for (uint32_t ssrc : kSsrcs4) {
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002185 EXPECT_TRUE(channel_->AddSendStream(
solenbergc96df772015-10-21 13:01:53 -07002186 cricket::StreamParams::CreateLegacy(ssrc)));
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002187 }
2188
Fredrik Solenbergb071a192015-09-17 16:42:56 +02002189 cricket::AudioSendParameters parameters;
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002190 // Set ISAC(16K) and CN(16K). VAD should be activated.
Fredrik Solenbergb071a192015-09-17 16:42:56 +02002191 parameters.codecs.push_back(kIsacCodec);
2192 parameters.codecs.push_back(kCn16000Codec);
2193 parameters.codecs[1].id = 97;
solenberg059fb442016-10-26 05:12:24 -07002194 SetSendParameters(parameters);
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002195
2196 // Verify ISAC and VAD are corrected configured on all send channels.
solenbergc96df772015-10-21 13:01:53 -07002197 for (uint32_t ssrc : kSsrcs4) {
minyue7a973442016-10-20 03:27:12 -07002198 ASSERT_TRUE(call_.GetAudioSendStream(ssrc) != nullptr);
2199 const auto& send_codec_spec =
2200 call_.GetAudioSendStream(ssrc)->GetConfig().send_codec_spec;
2201 EXPECT_STREQ("ISAC", send_codec_spec.codec_inst.plname);
2202 EXPECT_EQ(send_codec_spec.codec_inst.plfreq, send_codec_spec.cng_plfreq);
2203 EXPECT_EQ(1, send_codec_spec.codec_inst.channels);
2204 EXPECT_EQ(97, send_codec_spec.cng_payload_type);
2205 EXPECT_EQ(webrtc::kFreq16000Hz, send_codec_spec.cng_plfreq);
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002206 }
2207
minyue7a973442016-10-20 03:27:12 -07002208 // Change to PCMU(8K) and CN(16K).
Fredrik Solenbergb071a192015-09-17 16:42:56 +02002209 parameters.codecs[0] = kPcmuCodec;
solenberg059fb442016-10-26 05:12:24 -07002210 SetSendParameters(parameters);
solenbergc96df772015-10-21 13:01:53 -07002211 for (uint32_t ssrc : kSsrcs4) {
minyue7a973442016-10-20 03:27:12 -07002212 ASSERT_TRUE(call_.GetAudioSendStream(ssrc) != nullptr);
2213 const auto& send_codec_spec =
2214 call_.GetAudioSendStream(ssrc)->GetConfig().send_codec_spec;
2215 EXPECT_STREQ("PCMU", send_codec_spec.codec_inst.plname);
2216 EXPECT_NE(send_codec_spec.codec_inst.plfreq, send_codec_spec.cng_plfreq);
2217 EXPECT_EQ(97, send_codec_spec.cng_payload_type);
2218 EXPECT_EQ(webrtc::kFreq16000Hz, send_codec_spec.cng_plfreq);
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002219 }
2220}
2221
2222// Test we can SetSend on all send streams correctly.
2223TEST_F(WebRtcVoiceEngineTestFake, SetSendWithMultipleSendStreams) {
2224 SetupForMultiSendStream();
2225
Taylor Brandstetter1a018dc2016-03-08 12:37:39 -08002226 // Create the send channels and they should be a "not sending" date.
solenbergc96df772015-10-21 13:01:53 -07002227 for (uint32_t ssrc : kSsrcs4) {
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002228 EXPECT_TRUE(channel_->AddSendStream(
solenbergc96df772015-10-21 13:01:53 -07002229 cricket::StreamParams::CreateLegacy(ssrc)));
solenberg059fb442016-10-26 05:12:24 -07002230 SetAudioSend(ssrc, true, &fake_source_);
Taylor Brandstetter1a018dc2016-03-08 12:37:39 -08002231 EXPECT_FALSE(GetSendStream(ssrc).IsSending());
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002232 }
2233
2234 // Set the global state for starting sending.
solenberg059fb442016-10-26 05:12:24 -07002235 SetSend(true);
solenbergc96df772015-10-21 13:01:53 -07002236 for (uint32_t ssrc : kSsrcs4) {
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002237 // Verify that we are in a sending state for all the send streams.
Taylor Brandstetter1a018dc2016-03-08 12:37:39 -08002238 EXPECT_TRUE(GetSendStream(ssrc).IsSending());
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002239 }
2240
2241 // Set the global state for stopping sending.
solenberg059fb442016-10-26 05:12:24 -07002242 SetSend(false);
solenbergc96df772015-10-21 13:01:53 -07002243 for (uint32_t ssrc : kSsrcs4) {
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002244 // Verify that we are in a stop state for all the send streams.
Taylor Brandstetter1a018dc2016-03-08 12:37:39 -08002245 EXPECT_FALSE(GetSendStream(ssrc).IsSending());
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002246 }
2247}
2248
2249// Test we can set the correct statistics on all send streams.
2250TEST_F(WebRtcVoiceEngineTestFake, GetStatsWithMultipleSendStreams) {
2251 SetupForMultiSendStream();
2252
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002253 // Create send streams.
solenbergc96df772015-10-21 13:01:53 -07002254 for (uint32_t ssrc : kSsrcs4) {
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002255 EXPECT_TRUE(channel_->AddSendStream(
solenbergc96df772015-10-21 13:01:53 -07002256 cricket::StreamParams::CreateLegacy(ssrc)));
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002257 }
solenberg85a04962015-10-27 03:35:21 -07002258
buildbot@webrtc.org7e71b772014-06-13 01:14:01 +00002259 // Create a receive stream to check that none of the send streams end up in
2260 // the receive stream stats.
solenberg8189b022016-06-14 12:13:00 -07002261 EXPECT_TRUE(AddRecvStream(kSsrc2));
solenberg971cab02016-06-14 10:02:41 -07002262
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002263 // We need send codec to be set to get all stats.
solenberg059fb442016-10-26 05:12:24 -07002264 SetSendParameters(send_parameters_);
Fredrik Solenbergb071a192015-09-17 16:42:56 +02002265 EXPECT_TRUE(channel_->SetRecvParameters(recv_parameters_));
solenberg971cab02016-06-14 10:02:41 -07002266 SetAudioSendStreamStats();
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002267
solenberg85a04962015-10-27 03:35:21 -07002268 // Check stats for the added streams.
2269 {
2270 cricket::VoiceMediaInfo info;
2271 EXPECT_EQ(true, channel_->GetStats(&info));
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002272
solenberg85a04962015-10-27 03:35:21 -07002273 // We have added 4 send streams. We should see empty stats for all.
tfarina5237aaf2015-11-10 23:44:30 -08002274 EXPECT_EQ(static_cast<size_t>(arraysize(kSsrcs4)), info.senders.size());
solenberg85a04962015-10-27 03:35:21 -07002275 for (const auto& sender : info.senders) {
solenberg566ef242015-11-06 15:34:49 -08002276 VerifyVoiceSenderInfo(sender, false);
solenberg85a04962015-10-27 03:35:21 -07002277 }
2278
2279 // We have added one receive stream. We should see empty stats.
2280 EXPECT_EQ(info.receivers.size(), 1u);
2281 EXPECT_EQ(info.receivers[0].ssrc(), 0);
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002282 }
solenberg1ac56142015-10-13 03:58:19 -07002283
Fredrik Solenberg4f4ec0a2015-10-22 10:49:27 +02002284 // Remove the kSsrc2 stream. No receiver stats.
solenberg85a04962015-10-27 03:35:21 -07002285 {
2286 cricket::VoiceMediaInfo info;
2287 EXPECT_TRUE(channel_->RemoveRecvStream(kSsrc2));
2288 EXPECT_EQ(true, channel_->GetStats(&info));
tfarina5237aaf2015-11-10 23:44:30 -08002289 EXPECT_EQ(static_cast<size_t>(arraysize(kSsrcs4)), info.senders.size());
solenberg85a04962015-10-27 03:35:21 -07002290 EXPECT_EQ(0u, info.receivers.size());
2291 }
buildbot@webrtc.org7e71b772014-06-13 01:14:01 +00002292
Fredrik Solenberg4f4ec0a2015-10-22 10:49:27 +02002293 // Deliver a new packet - a default receive stream should be created and we
2294 // should see stats again.
solenberg85a04962015-10-27 03:35:21 -07002295 {
2296 cricket::VoiceMediaInfo info;
2297 DeliverPacket(kPcmuFrame, sizeof(kPcmuFrame));
2298 SetAudioReceiveStreamStats();
2299 EXPECT_EQ(true, channel_->GetStats(&info));
tfarina5237aaf2015-11-10 23:44:30 -08002300 EXPECT_EQ(static_cast<size_t>(arraysize(kSsrcs4)), info.senders.size());
solenberg85a04962015-10-27 03:35:21 -07002301 EXPECT_EQ(1u, info.receivers.size());
2302 VerifyVoiceReceiverInfo(info.receivers[0]);
2303 }
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002304}
2305
wu@webrtc.org9dba5252013-08-05 20:36:57 +00002306// Test that we can add and remove receive streams, and do proper send/playout.
2307// We can receive on multiple streams while sending one stream.
2308TEST_F(WebRtcVoiceEngineTestFake, PlayoutWithMultipleStreams) {
solenbergff976312016-03-30 23:28:51 -07002309 EXPECT_TRUE(SetupSendStream());
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002310
solenberg1ac56142015-10-13 03:58:19 -07002311 // Start playout without a receive stream.
solenberg059fb442016-10-26 05:12:24 -07002312 SetSendParameters(send_parameters_);
aleloi84ef6152016-08-04 05:28:21 -07002313 channel_->SetPlayout(true);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002314
solenberg1ac56142015-10-13 03:58:19 -07002315 // Adding another stream should enable playout on the new stream only.
solenberg8189b022016-06-14 12:13:00 -07002316 EXPECT_TRUE(AddRecvStream(kSsrc2));
solenberg059fb442016-10-26 05:12:24 -07002317 SetSend(true);
Taylor Brandstetter1a018dc2016-03-08 12:37:39 -08002318 EXPECT_TRUE(GetSendStream(kSsrc1).IsSending());
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002319
solenberg1ac56142015-10-13 03:58:19 -07002320 // Make sure only the new stream is played out.
aleloi84ef6152016-08-04 05:28:21 -07002321 EXPECT_TRUE(GetRecvStream(kSsrc2).started());
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002322
2323 // Adding yet another stream should have stream 2 and 3 enabled for playout.
solenberg8189b022016-06-14 12:13:00 -07002324 EXPECT_TRUE(AddRecvStream(kSsrc3));
aleloi84ef6152016-08-04 05:28:21 -07002325 EXPECT_TRUE(GetRecvStream(kSsrc2).started());
2326 EXPECT_TRUE(GetRecvStream(kSsrc3).started());
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002327
2328 // Stop sending.
solenberg059fb442016-10-26 05:12:24 -07002329 SetSend(false);
Taylor Brandstetter1a018dc2016-03-08 12:37:39 -08002330 EXPECT_FALSE(GetSendStream(kSsrc1).IsSending());
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002331
2332 // Stop playout.
aleloi84ef6152016-08-04 05:28:21 -07002333 channel_->SetPlayout(false);
2334 EXPECT_FALSE(GetRecvStream(kSsrc2).started());
2335 EXPECT_FALSE(GetRecvStream(kSsrc3).started());
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002336
aleloi84ef6152016-08-04 05:28:21 -07002337 // Restart playout and make sure recv streams are played out.
2338 channel_->SetPlayout(true);
2339 EXPECT_TRUE(GetRecvStream(kSsrc2).started());
2340 EXPECT_TRUE(GetRecvStream(kSsrc3).started());
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002341
aleloi84ef6152016-08-04 05:28:21 -07002342 // Now remove the recv streams.
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002343 EXPECT_TRUE(channel_->RemoveRecvStream(3));
2344 EXPECT_TRUE(channel_->RemoveRecvStream(2));
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002345}
2346
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002347// Test that we can create a channel configured for Codian bridges,
solenberg1ac56142015-10-13 03:58:19 -07002348// and start sending on it.
2349TEST_F(WebRtcVoiceEngineTestFake, CodianSend) {
solenbergff976312016-03-30 23:28:51 -07002350 EXPECT_TRUE(SetupSendStream());
solenberg246b8172015-12-08 09:50:23 -08002351 cricket::AudioOptions options_adjust_agc;
2352 options_adjust_agc.adjust_agc_delta = rtc::Optional<int>(-10);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002353 webrtc::AgcConfig agc_config;
2354 EXPECT_EQ(0, voe_.GetAgcConfig(agc_config));
2355 EXPECT_EQ(0, agc_config.targetLeveldBOv);
solenberg246b8172015-12-08 09:50:23 -08002356 send_parameters_.options = options_adjust_agc;
solenberg059fb442016-10-26 05:12:24 -07002357 SetSendParameters(send_parameters_);
2358 SetSend(true);
Taylor Brandstetter1a018dc2016-03-08 12:37:39 -08002359 EXPECT_TRUE(GetSendStream(kSsrc1).IsSending());
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002360 EXPECT_EQ(0, voe_.GetAgcConfig(agc_config));
2361 EXPECT_EQ(agc_config.targetLeveldBOv, 10); // level was attenuated
solenberg059fb442016-10-26 05:12:24 -07002362 SetSend(false);
Taylor Brandstetter1a018dc2016-03-08 12:37:39 -08002363 EXPECT_FALSE(GetSendStream(kSsrc1).IsSending());
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002364 EXPECT_EQ(0, voe_.GetAgcConfig(agc_config));
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002365}
2366
wu@webrtc.org97077a32013-10-25 21:18:33 +00002367TEST_F(WebRtcVoiceEngineTestFake, TxAgcConfigViaOptions) {
solenbergff976312016-03-30 23:28:51 -07002368 EXPECT_TRUE(SetupSendStream());
solenberg5b5129a2016-04-08 05:35:48 -07002369 EXPECT_CALL(adm_,
2370 BuiltInAGCIsAvailable()).Times(2).WillRepeatedly(Return(false));
wu@webrtc.org97077a32013-10-25 21:18:33 +00002371 webrtc::AgcConfig agc_config;
2372 EXPECT_EQ(0, voe_.GetAgcConfig(agc_config));
2373 EXPECT_EQ(0, agc_config.targetLeveldBOv);
solenberg246b8172015-12-08 09:50:23 -08002374 send_parameters_.options.tx_agc_target_dbov = rtc::Optional<uint16_t>(3);
2375 send_parameters_.options.tx_agc_digital_compression_gain =
2376 rtc::Optional<uint16_t>(9);
2377 send_parameters_.options.tx_agc_limiter = rtc::Optional<bool>(true);
2378 send_parameters_.options.auto_gain_control = rtc::Optional<bool>(true);
solenberg059fb442016-10-26 05:12:24 -07002379 SetSendParameters(send_parameters_);
wu@webrtc.org97077a32013-10-25 21:18:33 +00002380 EXPECT_EQ(0, voe_.GetAgcConfig(agc_config));
2381 EXPECT_EQ(3, agc_config.targetLeveldBOv);
2382 EXPECT_EQ(9, agc_config.digitalCompressionGaindB);
2383 EXPECT_TRUE(agc_config.limiterEnable);
2384
2385 // Check interaction with adjust_agc_delta. Both should be respected, for
2386 // backwards compatibility.
solenberg246b8172015-12-08 09:50:23 -08002387 send_parameters_.options.adjust_agc_delta = rtc::Optional<int>(-10);
solenberg059fb442016-10-26 05:12:24 -07002388 SetSendParameters(send_parameters_);
wu@webrtc.org97077a32013-10-25 21:18:33 +00002389 EXPECT_EQ(0, voe_.GetAgcConfig(agc_config));
2390 EXPECT_EQ(13, agc_config.targetLeveldBOv);
2391}
2392
wu@webrtc.org97077a32013-10-25 21:18:33 +00002393TEST_F(WebRtcVoiceEngineTestFake, SampleRatesViaOptions) {
solenbergff976312016-03-30 23:28:51 -07002394 EXPECT_TRUE(SetupSendStream());
solenberg5b5129a2016-04-08 05:35:48 -07002395 EXPECT_CALL(adm_, SetRecordingSampleRate(48000)).WillOnce(Return(0));
2396 EXPECT_CALL(adm_, SetPlayoutSampleRate(44100)).WillOnce(Return(0));
solenberg246b8172015-12-08 09:50:23 -08002397 send_parameters_.options.recording_sample_rate =
2398 rtc::Optional<uint32_t>(48000);
2399 send_parameters_.options.playout_sample_rate = rtc::Optional<uint32_t>(44100);
solenberg059fb442016-10-26 05:12:24 -07002400 SetSendParameters(send_parameters_);
wu@webrtc.org97077a32013-10-25 21:18:33 +00002401}
2402
minyue6b825df2016-10-31 04:08:32 -07002403TEST_F(WebRtcVoiceEngineTestFake, SetAudioNetworkAdaptorViaOptions) {
2404 EXPECT_TRUE(SetupSendStream());
2405 send_parameters_.options.audio_network_adaptor = rtc::Optional<bool>(true);
2406 send_parameters_.options.audio_network_adaptor_config =
2407 rtc::Optional<std::string>("1234");
2408 SetSendParameters(send_parameters_);
2409 EXPECT_EQ(send_parameters_.options.audio_network_adaptor_config,
2410 GetAudioNetworkAdaptorConfig(kSsrc1));
2411}
2412
2413TEST_F(WebRtcVoiceEngineTestFake, AudioSendResetAudioNetworkAdaptor) {
2414 EXPECT_TRUE(SetupSendStream());
2415 send_parameters_.options.audio_network_adaptor = rtc::Optional<bool>(true);
2416 send_parameters_.options.audio_network_adaptor_config =
2417 rtc::Optional<std::string>("1234");
2418 SetSendParameters(send_parameters_);
2419 EXPECT_EQ(send_parameters_.options.audio_network_adaptor_config,
2420 GetAudioNetworkAdaptorConfig(kSsrc1));
2421 const int initial_num = call_.GetNumCreatedSendStreams();
2422 cricket::AudioOptions options;
2423 options.audio_network_adaptor = rtc::Optional<bool>(false);
2424 SetAudioSend(kSsrc1, true, nullptr, &options);
2425 // AudioSendStream expected to be recreated.
2426 EXPECT_EQ(initial_num + 1, call_.GetNumCreatedSendStreams());
2427 EXPECT_EQ(rtc::Optional<std::string>(), GetAudioNetworkAdaptorConfig(kSsrc1));
2428}
2429
2430TEST_F(WebRtcVoiceEngineTestFake, AudioNetworkAdaptorNotGetOverridden) {
2431 EXPECT_TRUE(SetupSendStream());
2432 send_parameters_.options.audio_network_adaptor = rtc::Optional<bool>(true);
2433 send_parameters_.options.audio_network_adaptor_config =
2434 rtc::Optional<std::string>("1234");
2435 SetSendParameters(send_parameters_);
2436 EXPECT_EQ(send_parameters_.options.audio_network_adaptor_config,
2437 GetAudioNetworkAdaptorConfig(kSsrc1));
2438 const int initial_num = call_.GetNumCreatedSendStreams();
2439 cricket::AudioOptions options;
2440 options.audio_network_adaptor = rtc::Optional<bool>();
2441 // Unvalued |options.audio_network_adaptor|.should not reset audio network
2442 // adaptor.
2443 SetAudioSend(kSsrc1, true, nullptr, &options);
2444 // AudioSendStream not expected to be recreated.
2445 EXPECT_EQ(initial_num, call_.GetNumCreatedSendStreams());
2446 EXPECT_EQ(send_parameters_.options.audio_network_adaptor_config,
2447 GetAudioNetworkAdaptorConfig(kSsrc1));
2448}
2449
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002450// Test that we can set the outgoing SSRC properly.
solenbergff976312016-03-30 23:28:51 -07002451// SSRC is set in SetupSendStream() by calling AddSendStream.
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002452TEST_F(WebRtcVoiceEngineTestFake, SetSendSsrc) {
solenbergff976312016-03-30 23:28:51 -07002453 EXPECT_TRUE(SetupSendStream());
solenberg3a941542015-11-16 07:34:50 -08002454 EXPECT_TRUE(call_.GetAudioSendStream(kSsrc1));
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002455}
2456
2457TEST_F(WebRtcVoiceEngineTestFake, GetStats) {
2458 // Setup. We need send codec to be set to get all stats.
solenbergff976312016-03-30 23:28:51 -07002459 EXPECT_TRUE(SetupSendStream());
solenbergff976312016-03-30 23:28:51 -07002460 // SetupSendStream adds a send stream with kSsrc1, so the receive
solenberg1ac56142015-10-13 03:58:19 -07002461 // stream has to use a different SSRC.
solenberg8189b022016-06-14 12:13:00 -07002462 EXPECT_TRUE(AddRecvStream(kSsrc2));
solenberg059fb442016-10-26 05:12:24 -07002463 SetSendParameters(send_parameters_);
Fredrik Solenbergb071a192015-09-17 16:42:56 +02002464 EXPECT_TRUE(channel_->SetRecvParameters(recv_parameters_));
solenberg971cab02016-06-14 10:02:41 -07002465 SetAudioSendStreamStats();
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002466
solenberg85a04962015-10-27 03:35:21 -07002467 // Check stats for the added streams.
2468 {
2469 cricket::VoiceMediaInfo info;
2470 EXPECT_EQ(true, channel_->GetStats(&info));
2471
2472 // We have added one send stream. We should see the stats we've set.
2473 EXPECT_EQ(1u, info.senders.size());
solenberg566ef242015-11-06 15:34:49 -08002474 VerifyVoiceSenderInfo(info.senders[0], false);
solenberg85a04962015-10-27 03:35:21 -07002475 // We have added one receive stream. We should see empty stats.
2476 EXPECT_EQ(info.receivers.size(), 1u);
2477 EXPECT_EQ(info.receivers[0].ssrc(), 0);
2478 }
solenberg1ac56142015-10-13 03:58:19 -07002479
solenberg566ef242015-11-06 15:34:49 -08002480 // Start sending - this affects some reported stats.
2481 {
2482 cricket::VoiceMediaInfo info;
solenberg059fb442016-10-26 05:12:24 -07002483 SetSend(true);
solenberg566ef242015-11-06 15:34:49 -08002484 EXPECT_EQ(true, channel_->GetStats(&info));
2485 VerifyVoiceSenderInfo(info.senders[0], true);
2486 }
2487
Fredrik Solenberg4f4ec0a2015-10-22 10:49:27 +02002488 // Remove the kSsrc2 stream. No receiver stats.
solenberg85a04962015-10-27 03:35:21 -07002489 {
2490 cricket::VoiceMediaInfo info;
2491 EXPECT_TRUE(channel_->RemoveRecvStream(kSsrc2));
2492 EXPECT_EQ(true, channel_->GetStats(&info));
2493 EXPECT_EQ(1u, info.senders.size());
2494 EXPECT_EQ(0u, info.receivers.size());
2495 }
solenberg1ac56142015-10-13 03:58:19 -07002496
Fredrik Solenberg4f4ec0a2015-10-22 10:49:27 +02002497 // Deliver a new packet - a default receive stream should be created and we
2498 // should see stats again.
solenberg85a04962015-10-27 03:35:21 -07002499 {
2500 cricket::VoiceMediaInfo info;
2501 DeliverPacket(kPcmuFrame, sizeof(kPcmuFrame));
2502 SetAudioReceiveStreamStats();
2503 EXPECT_EQ(true, channel_->GetStats(&info));
2504 EXPECT_EQ(1u, info.senders.size());
2505 EXPECT_EQ(1u, info.receivers.size());
2506 VerifyVoiceReceiverInfo(info.receivers[0]);
2507 }
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002508}
2509
2510// Test that we can set the outgoing SSRC properly with multiple streams.
solenbergff976312016-03-30 23:28:51 -07002511// SSRC is set in SetupSendStream() by calling AddSendStream.
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002512TEST_F(WebRtcVoiceEngineTestFake, SetSendSsrcWithMultipleStreams) {
solenbergff976312016-03-30 23:28:51 -07002513 EXPECT_TRUE(SetupSendStream());
solenberg3a941542015-11-16 07:34:50 -08002514 EXPECT_TRUE(call_.GetAudioSendStream(kSsrc1));
solenberg8189b022016-06-14 12:13:00 -07002515 EXPECT_TRUE(AddRecvStream(kSsrc2));
solenberg7add0582015-11-20 09:59:34 -08002516 EXPECT_EQ(kSsrc1, GetRecvStreamConfig(kSsrc2).rtp.local_ssrc);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002517}
2518
2519// Test that the local SSRC is the same on sending and receiving channels if the
2520// receive channel is created before the send channel.
2521TEST_F(WebRtcVoiceEngineTestFake, SetSendSsrcAfterCreatingReceiveChannel) {
solenbergff976312016-03-30 23:28:51 -07002522 EXPECT_TRUE(SetupChannel());
solenberg4a0f7b52016-06-16 13:07:33 -07002523 EXPECT_TRUE(AddRecvStream(kSsrc2));
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002524 EXPECT_TRUE(channel_->AddSendStream(
solenberg4a0f7b52016-06-16 13:07:33 -07002525 cricket::StreamParams::CreateLegacy(kSsrc1)));
2526 EXPECT_TRUE(call_.GetAudioSendStream(kSsrc1));
2527 EXPECT_EQ(kSsrc1, GetRecvStreamConfig(kSsrc2).rtp.local_ssrc);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002528}
2529
2530// Test that we can properly receive packets.
2531TEST_F(WebRtcVoiceEngineTestFake, Recv) {
solenbergff976312016-03-30 23:28:51 -07002532 EXPECT_TRUE(SetupChannel());
solenberg8189b022016-06-14 12:13:00 -07002533 EXPECT_TRUE(AddRecvStream(1));
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002534 DeliverPacket(kPcmuFrame, sizeof(kPcmuFrame));
mflodman3d7db262016-04-29 00:57:13 -07002535
2536 EXPECT_TRUE(GetRecvStream(1).VerifyLastPacket(kPcmuFrame,
2537 sizeof(kPcmuFrame)));
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002538}
2539
2540// Test that we can properly receive packets on multiple streams.
2541TEST_F(WebRtcVoiceEngineTestFake, RecvWithMultipleStreams) {
solenbergff976312016-03-30 23:28:51 -07002542 EXPECT_TRUE(SetupChannel());
mflodman3d7db262016-04-29 00:57:13 -07002543 const uint32_t ssrc1 = 1;
2544 const uint32_t ssrc2 = 2;
2545 const uint32_t ssrc3 = 3;
solenberg8189b022016-06-14 12:13:00 -07002546 EXPECT_TRUE(AddRecvStream(ssrc1));
2547 EXPECT_TRUE(AddRecvStream(ssrc2));
2548 EXPECT_TRUE(AddRecvStream(ssrc3));
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002549 // Create packets with the right SSRCs.
mflodman3d7db262016-04-29 00:57:13 -07002550 unsigned char packets[4][sizeof(kPcmuFrame)];
tfarina5237aaf2015-11-10 23:44:30 -08002551 for (size_t i = 0; i < arraysize(packets); ++i) {
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002552 memcpy(packets[i], kPcmuFrame, sizeof(kPcmuFrame));
Peter Boström0c4e06b2015-10-07 12:23:21 +02002553 rtc::SetBE32(packets[i] + 8, static_cast<uint32_t>(i));
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002554 }
mflodman3d7db262016-04-29 00:57:13 -07002555
2556 const cricket::FakeAudioReceiveStream& s1 = GetRecvStream(ssrc1);
2557 const cricket::FakeAudioReceiveStream& s2 = GetRecvStream(ssrc2);
2558 const cricket::FakeAudioReceiveStream& s3 = GetRecvStream(ssrc3);
2559
2560 EXPECT_EQ(s1.received_packets(), 0);
2561 EXPECT_EQ(s2.received_packets(), 0);
2562 EXPECT_EQ(s3.received_packets(), 0);
solenberg7e63ef02015-11-20 00:19:43 -08002563
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002564 DeliverPacket(packets[0], sizeof(packets[0]));
mflodman3d7db262016-04-29 00:57:13 -07002565 EXPECT_EQ(s1.received_packets(), 0);
2566 EXPECT_EQ(s2.received_packets(), 0);
2567 EXPECT_EQ(s3.received_packets(), 0);
solenberg7e63ef02015-11-20 00:19:43 -08002568
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002569 DeliverPacket(packets[1], sizeof(packets[1]));
mflodman3d7db262016-04-29 00:57:13 -07002570 EXPECT_EQ(s1.received_packets(), 1);
2571 EXPECT_TRUE(s1.VerifyLastPacket(packets[1], sizeof(packets[1])));
2572 EXPECT_EQ(s2.received_packets(), 0);
2573 EXPECT_EQ(s3.received_packets(), 0);
solenberg7e63ef02015-11-20 00:19:43 -08002574
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002575 DeliverPacket(packets[2], sizeof(packets[2]));
mflodman3d7db262016-04-29 00:57:13 -07002576 EXPECT_EQ(s1.received_packets(), 1);
2577 EXPECT_EQ(s2.received_packets(), 1);
2578 EXPECT_TRUE(s2.VerifyLastPacket(packets[2], sizeof(packets[2])));
2579 EXPECT_EQ(s3.received_packets(), 0);
solenberg7e63ef02015-11-20 00:19:43 -08002580
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002581 DeliverPacket(packets[3], sizeof(packets[3]));
mflodman3d7db262016-04-29 00:57:13 -07002582 EXPECT_EQ(s1.received_packets(), 1);
2583 EXPECT_EQ(s2.received_packets(), 1);
2584 EXPECT_EQ(s3.received_packets(), 1);
2585 EXPECT_TRUE(s3.VerifyLastPacket(packets[3], sizeof(packets[3])));
solenberg7e63ef02015-11-20 00:19:43 -08002586
mflodman3d7db262016-04-29 00:57:13 -07002587 EXPECT_TRUE(channel_->RemoveRecvStream(ssrc3));
2588 EXPECT_TRUE(channel_->RemoveRecvStream(ssrc2));
2589 EXPECT_TRUE(channel_->RemoveRecvStream(ssrc1));
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002590}
2591
solenberg7e63ef02015-11-20 00:19:43 -08002592// Test that receiving on an unsignalled stream works (default channel will be
2593// created).
2594TEST_F(WebRtcVoiceEngineTestFake, RecvUnsignalled) {
solenbergff976312016-03-30 23:28:51 -07002595 EXPECT_TRUE(SetupChannel());
mflodman3d7db262016-04-29 00:57:13 -07002596 EXPECT_EQ(0, call_.GetAudioReceiveStreams().size());
2597
solenberg7e63ef02015-11-20 00:19:43 -08002598 DeliverPacket(kPcmuFrame, sizeof(kPcmuFrame));
mflodman3d7db262016-04-29 00:57:13 -07002599
2600 EXPECT_EQ(1, call_.GetAudioReceiveStreams().size());
2601 EXPECT_TRUE(GetRecvStream(1).VerifyLastPacket(kPcmuFrame,
2602 sizeof(kPcmuFrame)));
solenberg7e63ef02015-11-20 00:19:43 -08002603}
2604
2605// Test that receiving on an unsignalled stream works (default channel will be
2606// created), and that packets will be forwarded to the default channel
2607// regardless of their SSRCs.
2608TEST_F(WebRtcVoiceEngineTestFake, RecvUnsignalledWithSsrcSwitch) {
solenbergff976312016-03-30 23:28:51 -07002609 EXPECT_TRUE(SetupChannel());
mflodman3d7db262016-04-29 00:57:13 -07002610 unsigned char packet[sizeof(kPcmuFrame)];
solenberg7e63ef02015-11-20 00:19:43 -08002611 memcpy(packet, kPcmuFrame, sizeof(kPcmuFrame));
2612
mflodman3d7db262016-04-29 00:57:13 -07002613 // Note that ssrc = 0 is not supported.
2614 uint32_t ssrc = 1;
2615 for (; ssrc < 10; ++ssrc) {
solenberg7e63ef02015-11-20 00:19:43 -08002616 rtc::SetBE32(&packet[8], ssrc);
2617 DeliverPacket(packet, sizeof(packet));
mflodman3d7db262016-04-29 00:57:13 -07002618
2619 // Verify we only have one default stream.
2620 EXPECT_EQ(1, call_.GetAudioReceiveStreams().size());
2621 EXPECT_EQ(1, GetRecvStream(ssrc).received_packets());
2622 EXPECT_TRUE(GetRecvStream(ssrc).VerifyLastPacket(packet, sizeof(packet)));
solenberg7e63ef02015-11-20 00:19:43 -08002623 }
mflodman3d7db262016-04-29 00:57:13 -07002624
2625 // Sending the same ssrc again should not create a new stream.
2626 --ssrc;
2627 DeliverPacket(packet, sizeof(packet));
2628 EXPECT_EQ(1, call_.GetAudioReceiveStreams().size());
2629 EXPECT_EQ(2, GetRecvStream(ssrc).received_packets());
2630 EXPECT_TRUE(GetRecvStream(ssrc).VerifyLastPacket(packet, sizeof(packet)));
solenberg7e63ef02015-11-20 00:19:43 -08002631}
2632
2633// Test that a default channel is created even after a signalled stream has been
2634// added, and that this stream will get any packets for unknown SSRCs.
2635TEST_F(WebRtcVoiceEngineTestFake, RecvUnsignalledAfterSignalled) {
solenbergff976312016-03-30 23:28:51 -07002636 EXPECT_TRUE(SetupChannel());
mflodman3d7db262016-04-29 00:57:13 -07002637 unsigned char packet[sizeof(kPcmuFrame)];
solenberg7e63ef02015-11-20 00:19:43 -08002638 memcpy(packet, kPcmuFrame, sizeof(kPcmuFrame));
2639
2640 // Add a known stream, send packet and verify we got it.
mflodman3d7db262016-04-29 00:57:13 -07002641 const uint32_t signaled_ssrc = 1;
2642 rtc::SetBE32(&packet[8], signaled_ssrc);
solenberg8189b022016-06-14 12:13:00 -07002643 EXPECT_TRUE(AddRecvStream(signaled_ssrc));
solenberg7e63ef02015-11-20 00:19:43 -08002644 DeliverPacket(packet, sizeof(packet));
mflodman3d7db262016-04-29 00:57:13 -07002645 EXPECT_TRUE(GetRecvStream(signaled_ssrc).VerifyLastPacket(
2646 packet, sizeof(packet)));
solenberg7e63ef02015-11-20 00:19:43 -08002647
2648 // Note that the first unknown SSRC cannot be 0, because we only support
2649 // creating receive streams for SSRC!=0.
mflodman3d7db262016-04-29 00:57:13 -07002650 const uint32_t unsignaled_ssrc = 7011;
2651 rtc::SetBE32(&packet[8], unsignaled_ssrc);
solenberg7e63ef02015-11-20 00:19:43 -08002652 DeliverPacket(packet, sizeof(packet));
mflodman3d7db262016-04-29 00:57:13 -07002653 EXPECT_TRUE(GetRecvStream(unsignaled_ssrc).VerifyLastPacket(
2654 packet, sizeof(packet)));
2655 EXPECT_EQ(2, call_.GetAudioReceiveStreams().size());
2656
2657 DeliverPacket(packet, sizeof(packet));
2658 EXPECT_EQ(2, GetRecvStream(unsignaled_ssrc).received_packets());
2659
2660 rtc::SetBE32(&packet[8], signaled_ssrc);
2661 DeliverPacket(packet, sizeof(packet));
2662 EXPECT_EQ(2, GetRecvStream(signaled_ssrc).received_packets());
2663 EXPECT_EQ(2, call_.GetAudioReceiveStreams().size());
solenberg7e63ef02015-11-20 00:19:43 -08002664}
2665
solenberg0a617e22015-10-20 15:49:38 -07002666// Test that we properly handle failures to add a receive stream.
2667TEST_F(WebRtcVoiceEngineTestFake, AddRecvStreamFail) {
solenbergff976312016-03-30 23:28:51 -07002668 EXPECT_TRUE(SetupChannel());
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002669 voe_.set_fail_create_channel(true);
solenberg8189b022016-06-14 12:13:00 -07002670 EXPECT_FALSE(AddRecvStream(2));
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002671}
2672
solenberg0a617e22015-10-20 15:49:38 -07002673// Test that we properly handle failures to add a send stream.
2674TEST_F(WebRtcVoiceEngineTestFake, AddSendStreamFail) {
solenbergff976312016-03-30 23:28:51 -07002675 EXPECT_TRUE(SetupChannel());
solenberg0a617e22015-10-20 15:49:38 -07002676 voe_.set_fail_create_channel(true);
2677 EXPECT_FALSE(channel_->AddSendStream(cricket::StreamParams::CreateLegacy(2)));
2678}
2679
solenberg1ac56142015-10-13 03:58:19 -07002680// Test that AddRecvStream creates new stream.
2681TEST_F(WebRtcVoiceEngineTestFake, AddRecvStream) {
solenbergff976312016-03-30 23:28:51 -07002682 EXPECT_TRUE(SetupRecvStream());
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002683 int channel_num = voe_.GetLastChannel();
solenberg8189b022016-06-14 12:13:00 -07002684 EXPECT_TRUE(AddRecvStream(1));
solenberg1ac56142015-10-13 03:58:19 -07002685 EXPECT_NE(channel_num, voe_.GetLastChannel());
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002686}
2687
2688// Test that after adding a recv stream, we do not decode more codecs than
2689// those previously passed into SetRecvCodecs.
2690TEST_F(WebRtcVoiceEngineTestFake, AddRecvStreamUnsupportedCodec) {
solenbergff976312016-03-30 23:28:51 -07002691 EXPECT_TRUE(SetupSendStream());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02002692 cricket::AudioRecvParameters parameters;
2693 parameters.codecs.push_back(kIsacCodec);
2694 parameters.codecs.push_back(kPcmuCodec);
2695 EXPECT_TRUE(channel_->SetRecvParameters(parameters));
solenberg8189b022016-06-14 12:13:00 -07002696 EXPECT_TRUE(AddRecvStream(kSsrc1));
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002697 int channel_num2 = voe_.GetLastChannel();
2698 webrtc::CodecInst gcodec;
tfarina5237aaf2015-11-10 23:44:30 -08002699 rtc::strcpyn(gcodec.plname, arraysize(gcodec.plname), "opus");
minyue@webrtc.orgf9b5c1b2015-02-17 12:36:41 +00002700 gcodec.plfreq = 48000;
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002701 gcodec.channels = 2;
2702 EXPECT_EQ(-1, voe_.GetRecPayloadType(channel_num2, gcodec));
2703}
2704
2705// Test that we properly clean up any streams that were added, even if
2706// not explicitly removed.
2707TEST_F(WebRtcVoiceEngineTestFake, StreamCleanup) {
solenbergff976312016-03-30 23:28:51 -07002708 EXPECT_TRUE(SetupSendStream());
solenberg059fb442016-10-26 05:12:24 -07002709 SetSendParameters(send_parameters_);
solenberg8189b022016-06-14 12:13:00 -07002710 EXPECT_TRUE(AddRecvStream(1));
2711 EXPECT_TRUE(AddRecvStream(2));
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002712 EXPECT_EQ(3, voe_.GetNumChannels()); // default channel + 2 added
2713 delete channel_;
2714 channel_ = NULL;
2715 EXPECT_EQ(0, voe_.GetNumChannels());
2716}
2717
wu@webrtc.org78187522013-10-07 23:32:02 +00002718TEST_F(WebRtcVoiceEngineTestFake, TestAddRecvStreamFailWithZeroSsrc) {
solenbergff976312016-03-30 23:28:51 -07002719 EXPECT_TRUE(SetupSendStream());
solenberg8189b022016-06-14 12:13:00 -07002720 EXPECT_FALSE(AddRecvStream(0));
wu@webrtc.org78187522013-10-07 23:32:02 +00002721}
2722
2723TEST_F(WebRtcVoiceEngineTestFake, TestNoLeakingWhenAddRecvStreamFail) {
solenbergff976312016-03-30 23:28:51 -07002724 EXPECT_TRUE(SetupChannel());
solenberg8189b022016-06-14 12:13:00 -07002725 EXPECT_TRUE(AddRecvStream(1));
solenberg1ac56142015-10-13 03:58:19 -07002726 // Manually delete channel to simulate a failure.
2727 int channel = voe_.GetLastChannel();
2728 EXPECT_EQ(0, voe_.DeleteChannel(channel));
2729 // Add recv stream 2 should work.
solenberg8189b022016-06-14 12:13:00 -07002730 EXPECT_TRUE(AddRecvStream(2));
wu@webrtc.org78187522013-10-07 23:32:02 +00002731 int new_channel = voe_.GetLastChannel();
solenberg1ac56142015-10-13 03:58:19 -07002732 EXPECT_NE(channel, new_channel);
2733 // The last created channel is deleted too.
2734 EXPECT_EQ(0, voe_.DeleteChannel(new_channel));
wu@webrtc.org78187522013-10-07 23:32:02 +00002735}
2736
wu@webrtc.orgcadf9042013-08-30 21:24:16 +00002737// Test the InsertDtmf on default send stream as caller.
2738TEST_F(WebRtcVoiceEngineTestFake, InsertDtmfOnDefaultSendStreamAsCaller) {
solenbergffbbcac2016-11-17 05:25:37 -08002739 TestInsertDtmf(0, true, kTelephoneEventCodec1);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002740}
2741
wu@webrtc.orgcadf9042013-08-30 21:24:16 +00002742// Test the InsertDtmf on default send stream as callee
2743TEST_F(WebRtcVoiceEngineTestFake, InsertDtmfOnDefaultSendStreamAsCallee) {
solenbergffbbcac2016-11-17 05:25:37 -08002744 TestInsertDtmf(0, false, kTelephoneEventCodec2);
wu@webrtc.orgcadf9042013-08-30 21:24:16 +00002745}
2746
2747// Test the InsertDtmf on specified send stream as caller.
2748TEST_F(WebRtcVoiceEngineTestFake, InsertDtmfOnSendStreamAsCaller) {
solenbergffbbcac2016-11-17 05:25:37 -08002749 TestInsertDtmf(kSsrc1, true, kTelephoneEventCodec2);
wu@webrtc.orgcadf9042013-08-30 21:24:16 +00002750}
2751
2752// Test the InsertDtmf on specified send stream as callee.
2753TEST_F(WebRtcVoiceEngineTestFake, InsertDtmfOnSendStreamAsCallee) {
solenbergffbbcac2016-11-17 05:25:37 -08002754 TestInsertDtmf(kSsrc1, false, kTelephoneEventCodec1);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002755}
2756
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002757TEST_F(WebRtcVoiceEngineTestFake, SetAudioOptions) {
solenbergff976312016-03-30 23:28:51 -07002758 EXPECT_TRUE(SetupSendStream());
solenberg5b5129a2016-04-08 05:35:48 -07002759 EXPECT_CALL(adm_,
2760 BuiltInAECIsAvailable()).Times(9).WillRepeatedly(Return(false));
2761 EXPECT_CALL(adm_,
2762 BuiltInAGCIsAvailable()).Times(4).WillRepeatedly(Return(false));
2763 EXPECT_CALL(adm_,
2764 BuiltInNSIsAvailable()).Times(2).WillRepeatedly(Return(false));
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002765 bool ec_enabled;
2766 webrtc::EcModes ec_mode;
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002767 webrtc::AecmModes aecm_mode;
2768 bool cng_enabled;
2769 bool agc_enabled;
2770 webrtc::AgcModes agc_mode;
2771 webrtc::AgcConfig agc_config;
2772 bool ns_enabled;
2773 webrtc::NsModes ns_mode;
2774 bool highpass_filter_enabled;
2775 bool stereo_swapping_enabled;
2776 bool typing_detection_enabled;
2777 voe_.GetEcStatus(ec_enabled, ec_mode);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002778 voe_.GetAecmMode(aecm_mode, cng_enabled);
2779 voe_.GetAgcStatus(agc_enabled, agc_mode);
2780 voe_.GetAgcConfig(agc_config);
2781 voe_.GetNsStatus(ns_enabled, ns_mode);
2782 highpass_filter_enabled = voe_.IsHighPassFilterEnabled();
2783 stereo_swapping_enabled = voe_.IsStereoChannelSwappingEnabled();
2784 voe_.GetTypingDetectionStatus(typing_detection_enabled);
2785 EXPECT_TRUE(ec_enabled);
solenberg85a04962015-10-27 03:35:21 -07002786 EXPECT_TRUE(voe_.ec_metrics_enabled());
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002787 EXPECT_FALSE(cng_enabled);
2788 EXPECT_TRUE(agc_enabled);
2789 EXPECT_EQ(0, agc_config.targetLeveldBOv);
2790 EXPECT_TRUE(ns_enabled);
2791 EXPECT_TRUE(highpass_filter_enabled);
2792 EXPECT_FALSE(stereo_swapping_enabled);
2793 EXPECT_TRUE(typing_detection_enabled);
2794 EXPECT_EQ(ec_mode, webrtc::kEcConference);
2795 EXPECT_EQ(ns_mode, webrtc::kNsHighSuppression);
solenberg246b8172015-12-08 09:50:23 -08002796 EXPECT_EQ(50, voe_.GetNetEqCapacity());
2797 EXPECT_FALSE(voe_.GetNetEqFastAccelerate());
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002798
solenberg246b8172015-12-08 09:50:23 -08002799 // Nothing set in AudioOptions, so everything should be as default.
2800 send_parameters_.options = cricket::AudioOptions();
solenberg059fb442016-10-26 05:12:24 -07002801 SetSendParameters(send_parameters_);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002802 voe_.GetEcStatus(ec_enabled, ec_mode);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002803 voe_.GetAecmMode(aecm_mode, cng_enabled);
2804 voe_.GetAgcStatus(agc_enabled, agc_mode);
2805 voe_.GetAgcConfig(agc_config);
2806 voe_.GetNsStatus(ns_enabled, ns_mode);
2807 highpass_filter_enabled = voe_.IsHighPassFilterEnabled();
2808 stereo_swapping_enabled = voe_.IsStereoChannelSwappingEnabled();
2809 voe_.GetTypingDetectionStatus(typing_detection_enabled);
2810 EXPECT_TRUE(ec_enabled);
solenberg85a04962015-10-27 03:35:21 -07002811 EXPECT_TRUE(voe_.ec_metrics_enabled());
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002812 EXPECT_FALSE(cng_enabled);
2813 EXPECT_TRUE(agc_enabled);
2814 EXPECT_EQ(0, agc_config.targetLeveldBOv);
2815 EXPECT_TRUE(ns_enabled);
2816 EXPECT_TRUE(highpass_filter_enabled);
2817 EXPECT_FALSE(stereo_swapping_enabled);
2818 EXPECT_TRUE(typing_detection_enabled);
2819 EXPECT_EQ(ec_mode, webrtc::kEcConference);
2820 EXPECT_EQ(ns_mode, webrtc::kNsHighSuppression);
solenberg246b8172015-12-08 09:50:23 -08002821 EXPECT_EQ(50, voe_.GetNetEqCapacity());
2822 EXPECT_FALSE(voe_.GetNetEqFastAccelerate());
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002823
2824 // Turn echo cancellation off
solenberg246b8172015-12-08 09:50:23 -08002825 send_parameters_.options.echo_cancellation = rtc::Optional<bool>(false);
solenberg059fb442016-10-26 05:12:24 -07002826 SetSendParameters(send_parameters_);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002827 voe_.GetEcStatus(ec_enabled, ec_mode);
2828 EXPECT_FALSE(ec_enabled);
2829
2830 // Turn echo cancellation back on, with settings, and make sure
2831 // nothing else changed.
solenberg246b8172015-12-08 09:50:23 -08002832 send_parameters_.options.echo_cancellation = rtc::Optional<bool>(true);
solenberg059fb442016-10-26 05:12:24 -07002833 SetSendParameters(send_parameters_);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002834 voe_.GetEcStatus(ec_enabled, ec_mode);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002835 voe_.GetAecmMode(aecm_mode, cng_enabled);
2836 voe_.GetAgcStatus(agc_enabled, agc_mode);
2837 voe_.GetAgcConfig(agc_config);
2838 voe_.GetNsStatus(ns_enabled, ns_mode);
2839 highpass_filter_enabled = voe_.IsHighPassFilterEnabled();
2840 stereo_swapping_enabled = voe_.IsStereoChannelSwappingEnabled();
2841 voe_.GetTypingDetectionStatus(typing_detection_enabled);
2842 EXPECT_TRUE(ec_enabled);
solenberg85a04962015-10-27 03:35:21 -07002843 EXPECT_TRUE(voe_.ec_metrics_enabled());
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002844 EXPECT_TRUE(agc_enabled);
2845 EXPECT_EQ(0, agc_config.targetLeveldBOv);
2846 EXPECT_TRUE(ns_enabled);
2847 EXPECT_TRUE(highpass_filter_enabled);
2848 EXPECT_FALSE(stereo_swapping_enabled);
2849 EXPECT_TRUE(typing_detection_enabled);
2850 EXPECT_EQ(ec_mode, webrtc::kEcConference);
2851 EXPECT_EQ(ns_mode, webrtc::kNsHighSuppression);
2852
Bjorn Volckerbf395c12015-03-25 22:45:56 +01002853 // Turn on delay agnostic aec and make sure nothing change w.r.t. echo
2854 // control.
solenberg246b8172015-12-08 09:50:23 -08002855 send_parameters_.options.delay_agnostic_aec = rtc::Optional<bool>(true);
solenberg059fb442016-10-26 05:12:24 -07002856 SetSendParameters(send_parameters_);
Bjorn Volckerbf395c12015-03-25 22:45:56 +01002857 voe_.GetEcStatus(ec_enabled, ec_mode);
Bjorn Volckerbf395c12015-03-25 22:45:56 +01002858 voe_.GetAecmMode(aecm_mode, cng_enabled);
2859 EXPECT_TRUE(ec_enabled);
solenberg85a04962015-10-27 03:35:21 -07002860 EXPECT_TRUE(voe_.ec_metrics_enabled());
Bjorn Volckerbf395c12015-03-25 22:45:56 +01002861 EXPECT_EQ(ec_mode, webrtc::kEcConference);
2862
2863 // Turn off echo cancellation and delay agnostic aec.
solenberg246b8172015-12-08 09:50:23 -08002864 send_parameters_.options.delay_agnostic_aec = rtc::Optional<bool>(false);
2865 send_parameters_.options.extended_filter_aec = rtc::Optional<bool>(false);
2866 send_parameters_.options.echo_cancellation = rtc::Optional<bool>(false);
solenberg059fb442016-10-26 05:12:24 -07002867 SetSendParameters(send_parameters_);
Bjorn Volckerbf395c12015-03-25 22:45:56 +01002868 voe_.GetEcStatus(ec_enabled, ec_mode);
2869 EXPECT_FALSE(ec_enabled);
2870 // Turning delay agnostic aec back on should also turn on echo cancellation.
solenberg246b8172015-12-08 09:50:23 -08002871 send_parameters_.options.delay_agnostic_aec = rtc::Optional<bool>(true);
solenberg059fb442016-10-26 05:12:24 -07002872 SetSendParameters(send_parameters_);
Bjorn Volckerbf395c12015-03-25 22:45:56 +01002873 voe_.GetEcStatus(ec_enabled, ec_mode);
Bjorn Volckerbf395c12015-03-25 22:45:56 +01002874 EXPECT_TRUE(ec_enabled);
solenberg85a04962015-10-27 03:35:21 -07002875 EXPECT_TRUE(voe_.ec_metrics_enabled());
Bjorn Volckerbf395c12015-03-25 22:45:56 +01002876 EXPECT_EQ(ec_mode, webrtc::kEcConference);
2877
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002878 // Turn off AGC
solenberg246b8172015-12-08 09:50:23 -08002879 send_parameters_.options.auto_gain_control = rtc::Optional<bool>(false);
solenberg059fb442016-10-26 05:12:24 -07002880 SetSendParameters(send_parameters_);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002881 voe_.GetAgcStatus(agc_enabled, agc_mode);
2882 EXPECT_FALSE(agc_enabled);
2883
2884 // Turn AGC back on
solenberg246b8172015-12-08 09:50:23 -08002885 send_parameters_.options.auto_gain_control = rtc::Optional<bool>(true);
2886 send_parameters_.options.adjust_agc_delta = rtc::Optional<int>();
solenberg059fb442016-10-26 05:12:24 -07002887 SetSendParameters(send_parameters_);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002888 voe_.GetAgcStatus(agc_enabled, agc_mode);
2889 EXPECT_TRUE(agc_enabled);
2890 voe_.GetAgcConfig(agc_config);
2891 EXPECT_EQ(0, agc_config.targetLeveldBOv);
2892
2893 // Turn off other options (and stereo swapping on).
solenberg246b8172015-12-08 09:50:23 -08002894 send_parameters_.options.noise_suppression = rtc::Optional<bool>(false);
2895 send_parameters_.options.highpass_filter = rtc::Optional<bool>(false);
2896 send_parameters_.options.typing_detection = rtc::Optional<bool>(false);
2897 send_parameters_.options.stereo_swapping = rtc::Optional<bool>(true);
solenberg059fb442016-10-26 05:12:24 -07002898 SetSendParameters(send_parameters_);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002899 voe_.GetNsStatus(ns_enabled, ns_mode);
2900 highpass_filter_enabled = voe_.IsHighPassFilterEnabled();
2901 stereo_swapping_enabled = voe_.IsStereoChannelSwappingEnabled();
2902 voe_.GetTypingDetectionStatus(typing_detection_enabled);
2903 EXPECT_FALSE(ns_enabled);
2904 EXPECT_FALSE(highpass_filter_enabled);
2905 EXPECT_FALSE(typing_detection_enabled);
2906 EXPECT_TRUE(stereo_swapping_enabled);
2907
solenberg1ac56142015-10-13 03:58:19 -07002908 // Set options again to ensure it has no impact.
solenberg059fb442016-10-26 05:12:24 -07002909 SetSendParameters(send_parameters_);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002910 voe_.GetEcStatus(ec_enabled, ec_mode);
2911 voe_.GetNsStatus(ns_enabled, ns_mode);
2912 EXPECT_TRUE(ec_enabled);
2913 EXPECT_EQ(webrtc::kEcConference, ec_mode);
2914 EXPECT_FALSE(ns_enabled);
2915 EXPECT_EQ(webrtc::kNsHighSuppression, ns_mode);
2916}
2917
mallinath@webrtc.orga27be8e2013-09-27 23:04:10 +00002918TEST_F(WebRtcVoiceEngineTestFake, DefaultOptions) {
solenbergff976312016-03-30 23:28:51 -07002919 EXPECT_TRUE(SetupSendStream());
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002920
2921 bool ec_enabled;
2922 webrtc::EcModes ec_mode;
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002923 bool agc_enabled;
2924 webrtc::AgcModes agc_mode;
2925 bool ns_enabled;
2926 webrtc::NsModes ns_mode;
2927 bool highpass_filter_enabled;
2928 bool stereo_swapping_enabled;
2929 bool typing_detection_enabled;
2930
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002931 voe_.GetEcStatus(ec_enabled, ec_mode);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002932 voe_.GetAgcStatus(agc_enabled, agc_mode);
2933 voe_.GetNsStatus(ns_enabled, ns_mode);
2934 highpass_filter_enabled = voe_.IsHighPassFilterEnabled();
2935 stereo_swapping_enabled = voe_.IsStereoChannelSwappingEnabled();
2936 voe_.GetTypingDetectionStatus(typing_detection_enabled);
2937 EXPECT_TRUE(ec_enabled);
2938 EXPECT_TRUE(agc_enabled);
2939 EXPECT_TRUE(ns_enabled);
2940 EXPECT_TRUE(highpass_filter_enabled);
mallinath@webrtc.orga27be8e2013-09-27 23:04:10 +00002941 EXPECT_TRUE(typing_detection_enabled);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002942 EXPECT_FALSE(stereo_swapping_enabled);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002943}
2944
2945TEST_F(WebRtcVoiceEngineTestFake, InitDoesNotOverwriteDefaultAgcConfig) {
2946 webrtc::AgcConfig set_config = {0};
2947 set_config.targetLeveldBOv = 3;
2948 set_config.digitalCompressionGaindB = 9;
2949 set_config.limiterEnable = true;
2950 EXPECT_EQ(0, voe_.SetAgcConfig(set_config));
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002951
2952 webrtc::AgcConfig config = {0};
2953 EXPECT_EQ(0, voe_.GetAgcConfig(config));
2954 EXPECT_EQ(set_config.targetLeveldBOv, config.targetLeveldBOv);
2955 EXPECT_EQ(set_config.digitalCompressionGaindB,
2956 config.digitalCompressionGaindB);
2957 EXPECT_EQ(set_config.limiterEnable, config.limiterEnable);
2958}
2959
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002960TEST_F(WebRtcVoiceEngineTestFake, SetOptionOverridesViaChannels) {
solenbergff976312016-03-30 23:28:51 -07002961 EXPECT_TRUE(SetupSendStream());
solenberg5b5129a2016-04-08 05:35:48 -07002962 EXPECT_CALL(adm_,
2963 BuiltInAECIsAvailable()).Times(9).WillRepeatedly(Return(false));
2964 EXPECT_CALL(adm_,
2965 BuiltInAGCIsAvailable()).Times(9).WillRepeatedly(Return(false));
2966 EXPECT_CALL(adm_,
2967 BuiltInNSIsAvailable()).Times(9).WillRepeatedly(Return(false));
solenberg059fb442016-10-26 05:12:24 -07002968 EXPECT_CALL(adm_,
2969 RecordingIsInitialized()).Times(2).WillRepeatedly(Return(false));
2970 EXPECT_CALL(adm_, Recording()).Times(2).WillRepeatedly(Return(false));
2971 EXPECT_CALL(adm_, InitRecording()).Times(2).WillRepeatedly(Return(0));
2972 EXPECT_CALL(apm_, ApplyConfig(testing::_)).Times(10);
2973 EXPECT_CALL(apm_, SetExtraOptions(testing::_)).Times(10);
solenberg5b5129a2016-04-08 05:35:48 -07002974
kwiberg686a8ef2016-02-26 03:00:35 -08002975 std::unique_ptr<cricket::WebRtcVoiceMediaChannel> channel1(
solenbergbc37fc82016-04-04 09:54:44 -07002976 static_cast<cricket::WebRtcVoiceMediaChannel*>(engine_->CreateChannel(
nisse51542be2016-02-12 02:27:06 -08002977 &call_, cricket::MediaConfig(), cricket::AudioOptions())));
kwiberg686a8ef2016-02-26 03:00:35 -08002978 std::unique_ptr<cricket::WebRtcVoiceMediaChannel> channel2(
solenbergbc37fc82016-04-04 09:54:44 -07002979 static_cast<cricket::WebRtcVoiceMediaChannel*>(engine_->CreateChannel(
nisse51542be2016-02-12 02:27:06 -08002980 &call_, cricket::MediaConfig(), cricket::AudioOptions())));
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002981
2982 // Have to add a stream to make SetSend work.
2983 cricket::StreamParams stream1;
2984 stream1.ssrcs.push_back(1);
2985 channel1->AddSendStream(stream1);
2986 cricket::StreamParams stream2;
2987 stream2.ssrcs.push_back(2);
2988 channel2->AddSendStream(stream2);
2989
2990 // AEC and AGC and NS
Fredrik Solenbergb071a192015-09-17 16:42:56 +02002991 cricket::AudioSendParameters parameters_options_all = send_parameters_;
Karl Wibergbe579832015-11-10 22:34:18 +01002992 parameters_options_all.options.echo_cancellation = rtc::Optional<bool>(true);
2993 parameters_options_all.options.auto_gain_control = rtc::Optional<bool>(true);
2994 parameters_options_all.options.noise_suppression = rtc::Optional<bool>(true);
solenberg059fb442016-10-26 05:12:24 -07002995 EXPECT_TRUE(channel1->SetSendParameters(parameters_options_all));
Fredrik Solenbergb071a192015-09-17 16:42:56 +02002996 EXPECT_EQ(parameters_options_all.options, channel1->options());
solenberg059fb442016-10-26 05:12:24 -07002997 EXPECT_TRUE(channel2->SetSendParameters(parameters_options_all));
Fredrik Solenbergb071a192015-09-17 16:42:56 +02002998 EXPECT_EQ(parameters_options_all.options, channel2->options());
henrike@webrtc.org28e20752013-07-10 00:45:36 +00002999
3000 // unset NS
Fredrik Solenbergb071a192015-09-17 16:42:56 +02003001 cricket::AudioSendParameters parameters_options_no_ns = send_parameters_;
Karl Wibergbe579832015-11-10 22:34:18 +01003002 parameters_options_no_ns.options.noise_suppression =
3003 rtc::Optional<bool>(false);
solenberg059fb442016-10-26 05:12:24 -07003004 EXPECT_TRUE(channel1->SetSendParameters(parameters_options_no_ns));
Fredrik Solenbergb071a192015-09-17 16:42:56 +02003005 cricket::AudioOptions expected_options = parameters_options_all.options;
Karl Wibergbe579832015-11-10 22:34:18 +01003006 expected_options.echo_cancellation = rtc::Optional<bool>(true);
3007 expected_options.auto_gain_control = rtc::Optional<bool>(true);
3008 expected_options.noise_suppression = rtc::Optional<bool>(false);
solenberg66f43392015-09-09 01:36:22 -07003009 EXPECT_EQ(expected_options, channel1->options());
henrike@webrtc.org28e20752013-07-10 00:45:36 +00003010
3011 // unset AGC
Fredrik Solenbergb071a192015-09-17 16:42:56 +02003012 cricket::AudioSendParameters parameters_options_no_agc = send_parameters_;
Karl Wibergbe579832015-11-10 22:34:18 +01003013 parameters_options_no_agc.options.auto_gain_control =
3014 rtc::Optional<bool>(false);
solenberg059fb442016-10-26 05:12:24 -07003015 EXPECT_TRUE(channel2->SetSendParameters(parameters_options_no_agc));
Karl Wibergbe579832015-11-10 22:34:18 +01003016 expected_options.echo_cancellation = rtc::Optional<bool>(true);
3017 expected_options.auto_gain_control = rtc::Optional<bool>(false);
3018 expected_options.noise_suppression = rtc::Optional<bool>(true);
solenberg66f43392015-09-09 01:36:22 -07003019 EXPECT_EQ(expected_options, channel2->options());
henrike@webrtc.org28e20752013-07-10 00:45:36 +00003020
solenberg059fb442016-10-26 05:12:24 -07003021 EXPECT_TRUE(channel_->SetSendParameters(parameters_options_all));
henrike@webrtc.org28e20752013-07-10 00:45:36 +00003022 bool ec_enabled;
3023 webrtc::EcModes ec_mode;
3024 bool agc_enabled;
3025 webrtc::AgcModes agc_mode;
3026 bool ns_enabled;
3027 webrtc::NsModes ns_mode;
3028 voe_.GetEcStatus(ec_enabled, ec_mode);
3029 voe_.GetAgcStatus(agc_enabled, agc_mode);
3030 voe_.GetNsStatus(ns_enabled, ns_mode);
3031 EXPECT_TRUE(ec_enabled);
3032 EXPECT_TRUE(agc_enabled);
3033 EXPECT_TRUE(ns_enabled);
3034
solenberg059fb442016-10-26 05:12:24 -07003035 channel1->SetSend(true);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00003036 voe_.GetEcStatus(ec_enabled, ec_mode);
3037 voe_.GetAgcStatus(agc_enabled, agc_mode);
3038 voe_.GetNsStatus(ns_enabled, ns_mode);
3039 EXPECT_TRUE(ec_enabled);
3040 EXPECT_TRUE(agc_enabled);
3041 EXPECT_FALSE(ns_enabled);
3042
solenberg059fb442016-10-26 05:12:24 -07003043 channel2->SetSend(true);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00003044 voe_.GetEcStatus(ec_enabled, ec_mode);
3045 voe_.GetAgcStatus(agc_enabled, agc_mode);
3046 voe_.GetNsStatus(ns_enabled, ns_mode);
3047 EXPECT_TRUE(ec_enabled);
3048 EXPECT_FALSE(agc_enabled);
3049 EXPECT_TRUE(ns_enabled);
3050
henrike@webrtc.org28e20752013-07-10 00:45:36 +00003051 // Make sure settings take effect while we are sending.
solenberg059fb442016-10-26 05:12:24 -07003052 EXPECT_TRUE(channel_->SetSendParameters(parameters_options_all));
3053 EXPECT_CALL(apm_, ApplyConfig(testing::_));
3054 EXPECT_CALL(apm_, SetExtraOptions(testing::_));
Fredrik Solenbergb071a192015-09-17 16:42:56 +02003055 cricket::AudioSendParameters parameters_options_no_agc_nor_ns =
3056 send_parameters_;
kwiberg102c6a62015-10-30 02:47:38 -07003057 parameters_options_no_agc_nor_ns.options.auto_gain_control =
Karl Wibergbe579832015-11-10 22:34:18 +01003058 rtc::Optional<bool>(false);
kwiberg102c6a62015-10-30 02:47:38 -07003059 parameters_options_no_agc_nor_ns.options.noise_suppression =
Karl Wibergbe579832015-11-10 22:34:18 +01003060 rtc::Optional<bool>(false);
Taylor Brandstetter1a018dc2016-03-08 12:37:39 -08003061 channel2->SetSend(true);
solenberg059fb442016-10-26 05:12:24 -07003062 EXPECT_TRUE(channel2->SetSendParameters(parameters_options_no_agc_nor_ns));
Karl Wibergbe579832015-11-10 22:34:18 +01003063 expected_options.echo_cancellation = rtc::Optional<bool>(true);
3064 expected_options.auto_gain_control = rtc::Optional<bool>(false);
3065 expected_options.noise_suppression = rtc::Optional<bool>(false);
solenberg66f43392015-09-09 01:36:22 -07003066 EXPECT_EQ(expected_options, channel2->options());
henrike@webrtc.org28e20752013-07-10 00:45:36 +00003067 voe_.GetEcStatus(ec_enabled, ec_mode);
3068 voe_.GetAgcStatus(agc_enabled, agc_mode);
3069 voe_.GetNsStatus(ns_enabled, ns_mode);
3070 EXPECT_TRUE(ec_enabled);
3071 EXPECT_FALSE(agc_enabled);
3072 EXPECT_FALSE(ns_enabled);
3073}
3074
wu@webrtc.orgde305012013-10-31 15:40:38 +00003075// This test verifies DSCP settings are properly applied on voice media channel.
3076TEST_F(WebRtcVoiceEngineTestFake, TestSetDscpOptions) {
solenbergff976312016-03-30 23:28:51 -07003077 EXPECT_TRUE(SetupSendStream());
nisse51542be2016-02-12 02:27:06 -08003078 cricket::FakeNetworkInterface network_interface;
3079 cricket::MediaConfig config;
kwiberg686a8ef2016-02-26 03:00:35 -08003080 std::unique_ptr<cricket::VoiceMediaChannel> channel;
nisse51542be2016-02-12 02:27:06 -08003081
solenberg059fb442016-10-26 05:12:24 -07003082 EXPECT_CALL(apm_, ApplyConfig(testing::_)).Times(3);
3083 EXPECT_CALL(apm_, SetExtraOptions(testing::_)).Times(3);
3084
solenbergbc37fc82016-04-04 09:54:44 -07003085 channel.reset(
3086 engine_->CreateChannel(&call_, config, cricket::AudioOptions()));
nisse51542be2016-02-12 02:27:06 -08003087 channel->SetInterface(&network_interface);
3088 // Default value when DSCP is disabled should be DSCP_DEFAULT.
3089 EXPECT_EQ(rtc::DSCP_DEFAULT, network_interface.dscp());
3090
3091 config.enable_dscp = true;
solenbergbc37fc82016-04-04 09:54:44 -07003092 channel.reset(
3093 engine_->CreateChannel(&call_, config, cricket::AudioOptions()));
nisse51542be2016-02-12 02:27:06 -08003094 channel->SetInterface(&network_interface);
3095 EXPECT_EQ(rtc::DSCP_EF, network_interface.dscp());
3096
3097 // Verify that setting the option to false resets the
3098 // DiffServCodePoint.
3099 config.enable_dscp = false;
solenbergbc37fc82016-04-04 09:54:44 -07003100 channel.reset(
3101 engine_->CreateChannel(&call_, config, cricket::AudioOptions()));
nisse51542be2016-02-12 02:27:06 -08003102 channel->SetInterface(&network_interface);
3103 // Default value when DSCP is disabled should be DSCP_DEFAULT.
3104 EXPECT_EQ(rtc::DSCP_DEFAULT, network_interface.dscp());
3105
3106 channel->SetInterface(nullptr);
wu@webrtc.orgde305012013-10-31 15:40:38 +00003107}
3108
solenberg1ac56142015-10-13 03:58:19 -07003109TEST_F(WebRtcVoiceEngineTestFake, TestGetReceiveChannelId) {
solenbergff976312016-03-30 23:28:51 -07003110 EXPECT_TRUE(SetupChannel());
henrike@webrtc.org28e20752013-07-10 00:45:36 +00003111 cricket::WebRtcVoiceMediaChannel* media_channel =
3112 static_cast<cricket::WebRtcVoiceMediaChannel*>(channel_);
solenberg1ac56142015-10-13 03:58:19 -07003113 EXPECT_EQ(-1, media_channel->GetReceiveChannelId(0));
solenberg8189b022016-06-14 12:13:00 -07003114 EXPECT_TRUE(AddRecvStream(kSsrc1));
solenberg1ac56142015-10-13 03:58:19 -07003115 int channel_id = voe_.GetLastChannel();
3116 EXPECT_EQ(channel_id, media_channel->GetReceiveChannelId(kSsrc1));
3117 EXPECT_EQ(-1, media_channel->GetReceiveChannelId(kSsrc2));
solenberg8189b022016-06-14 12:13:00 -07003118 EXPECT_TRUE(AddRecvStream(kSsrc2));
solenberg1ac56142015-10-13 03:58:19 -07003119 int channel_id2 = voe_.GetLastChannel();
3120 EXPECT_EQ(channel_id2, media_channel->GetReceiveChannelId(kSsrc2));
henrike@webrtc.org28e20752013-07-10 00:45:36 +00003121}
3122
solenberg1ac56142015-10-13 03:58:19 -07003123TEST_F(WebRtcVoiceEngineTestFake, TestGetSendChannelId) {
solenbergff976312016-03-30 23:28:51 -07003124 EXPECT_TRUE(SetupChannel());
henrike@webrtc.org28e20752013-07-10 00:45:36 +00003125 cricket::WebRtcVoiceMediaChannel* media_channel =
solenberg1ac56142015-10-13 03:58:19 -07003126 static_cast<cricket::WebRtcVoiceMediaChannel*>(channel_);
3127 EXPECT_EQ(-1, media_channel->GetSendChannelId(0));
3128 EXPECT_TRUE(channel_->AddSendStream(
3129 cricket::StreamParams::CreateLegacy(kSsrc1)));
3130 int channel_id = voe_.GetLastChannel();
3131 EXPECT_EQ(channel_id, media_channel->GetSendChannelId(kSsrc1));
3132 EXPECT_EQ(-1, media_channel->GetSendChannelId(kSsrc2));
3133 EXPECT_TRUE(channel_->AddSendStream(
3134 cricket::StreamParams::CreateLegacy(kSsrc2)));
3135 int channel_id2 = voe_.GetLastChannel();
3136 EXPECT_EQ(channel_id2, media_channel->GetSendChannelId(kSsrc2));
henrike@webrtc.org28e20752013-07-10 00:45:36 +00003137}
3138
solenberg4bac9c52015-10-09 02:32:53 -07003139TEST_F(WebRtcVoiceEngineTestFake, SetOutputVolume) {
solenbergff976312016-03-30 23:28:51 -07003140 EXPECT_TRUE(SetupChannel());
solenberg4bac9c52015-10-09 02:32:53 -07003141 EXPECT_FALSE(channel_->SetOutputVolume(kSsrc2, 0.5));
henrike@webrtc.org28e20752013-07-10 00:45:36 +00003142 cricket::StreamParams stream;
3143 stream.ssrcs.push_back(kSsrc2);
3144 EXPECT_TRUE(channel_->AddRecvStream(stream));
solenberg217fb662016-06-17 08:30:54 -07003145 EXPECT_DOUBLE_EQ(1, GetRecvStream(kSsrc2).gain());
solenberg4bac9c52015-10-09 02:32:53 -07003146 EXPECT_TRUE(channel_->SetOutputVolume(kSsrc2, 3));
solenberg217fb662016-06-17 08:30:54 -07003147 EXPECT_DOUBLE_EQ(3, GetRecvStream(kSsrc2).gain());
solenberg1ac56142015-10-13 03:58:19 -07003148}
3149
3150TEST_F(WebRtcVoiceEngineTestFake, SetOutputVolumeDefaultRecvStream) {
solenbergff976312016-03-30 23:28:51 -07003151 EXPECT_TRUE(SetupChannel());
solenberg1ac56142015-10-13 03:58:19 -07003152 EXPECT_TRUE(channel_->SetOutputVolume(0, 2));
3153 DeliverPacket(kPcmuFrame, sizeof(kPcmuFrame));
solenberg217fb662016-06-17 08:30:54 -07003154 EXPECT_DOUBLE_EQ(2, GetRecvStream(1).gain());
solenberg1ac56142015-10-13 03:58:19 -07003155 EXPECT_TRUE(channel_->SetOutputVolume(0, 3));
solenberg217fb662016-06-17 08:30:54 -07003156 EXPECT_DOUBLE_EQ(3, GetRecvStream(1).gain());
3157 EXPECT_TRUE(channel_->SetOutputVolume(1, 4));
3158 EXPECT_DOUBLE_EQ(4, GetRecvStream(1).gain());
henrike@webrtc.org28e20752013-07-10 00:45:36 +00003159}
3160
pbos8fc7fa72015-07-15 08:02:58 -07003161TEST_F(WebRtcVoiceEngineTestFake, SetsSyncGroupFromSyncLabel) {
Peter Boström0c4e06b2015-10-07 12:23:21 +02003162 const uint32_t kAudioSsrc = 123;
pbos8fc7fa72015-07-15 08:02:58 -07003163 const std::string kSyncLabel = "AvSyncLabel";
3164
solenbergff976312016-03-30 23:28:51 -07003165 EXPECT_TRUE(SetupSendStream());
pbos8fc7fa72015-07-15 08:02:58 -07003166 cricket::StreamParams sp = cricket::StreamParams::CreateLegacy(kAudioSsrc);
3167 sp.sync_label = kSyncLabel;
3168 // Creating two channels to make sure that sync label is set properly for both
3169 // the default voice channel and following ones.
3170 EXPECT_TRUE(channel_->AddRecvStream(sp));
3171 sp.ssrcs[0] += 1;
3172 EXPECT_TRUE(channel_->AddRecvStream(sp));
3173
Fredrik Solenberg709ed672015-09-15 12:26:33 +02003174 ASSERT_EQ(2, call_.GetAudioReceiveStreams().size());
pbos8fc7fa72015-07-15 08:02:58 -07003175 EXPECT_EQ(kSyncLabel,
Fredrik Solenberg709ed672015-09-15 12:26:33 +02003176 call_.GetAudioReceiveStream(kAudioSsrc)->GetConfig().sync_group)
pbos8fc7fa72015-07-15 08:02:58 -07003177 << "SyncGroup should be set based on sync_label";
3178 EXPECT_EQ(kSyncLabel,
Fredrik Solenberg709ed672015-09-15 12:26:33 +02003179 call_.GetAudioReceiveStream(kAudioSsrc + 1)->GetConfig().sync_group)
pbos8fc7fa72015-07-15 08:02:58 -07003180 << "SyncGroup should be set based on sync_label";
pbos8fc7fa72015-07-15 08:02:58 -07003181}
3182
solenberg3a941542015-11-16 07:34:50 -08003183// TODO(solenberg): Remove, once recv streams are configured through Call.
3184// (This is then covered by TestSetRecvRtpHeaderExtensions.)
pbos6bb1b6e2015-07-24 07:10:18 -07003185TEST_F(WebRtcVoiceEngineTestFake, ConfiguresAudioReceiveStreamRtpExtensions) {
Fredrik Solenberg4b60c732015-05-07 14:07:48 +02003186 // Test that setting the header extensions results in the expected state
3187 // changes on an associated Call.
Peter Boström0c4e06b2015-10-07 12:23:21 +02003188 std::vector<uint32_t> ssrcs;
Fredrik Solenberg4b60c732015-05-07 14:07:48 +02003189 ssrcs.push_back(223);
3190 ssrcs.push_back(224);
3191
solenbergff976312016-03-30 23:28:51 -07003192 EXPECT_TRUE(SetupSendStream());
solenberg059fb442016-10-26 05:12:24 -07003193 SetSendParameters(send_parameters_);
Peter Boström0c4e06b2015-10-07 12:23:21 +02003194 for (uint32_t ssrc : ssrcs) {
solenberg059fb442016-10-26 05:12:24 -07003195 EXPECT_TRUE(channel_->AddRecvStream(
Fredrik Solenberg4b60c732015-05-07 14:07:48 +02003196 cricket::StreamParams::CreateLegacy(ssrc)));
3197 }
3198
Fredrik Solenberg709ed672015-09-15 12:26:33 +02003199 EXPECT_EQ(2, call_.GetAudioReceiveStreams().size());
Peter Boström0c4e06b2015-10-07 12:23:21 +02003200 for (uint32_t ssrc : ssrcs) {
Fredrik Solenberg709ed672015-09-15 12:26:33 +02003201 const auto* s = call_.GetAudioReceiveStream(ssrc);
Fredrik Solenberg4b60c732015-05-07 14:07:48 +02003202 EXPECT_NE(nullptr, s);
3203 EXPECT_EQ(0, s->GetConfig().rtp.extensions.size());
3204 }
3205
3206 // Set up receive extensions.
solenbergbc37fc82016-04-04 09:54:44 -07003207 cricket::RtpCapabilities capabilities = engine_->GetCapabilities();
Fredrik Solenbergb071a192015-09-17 16:42:56 +02003208 cricket::AudioRecvParameters recv_parameters;
Stefan Holmer9d69c3f2015-12-07 10:45:43 +01003209 recv_parameters.extensions = capabilities.header_extensions;
Fredrik Solenbergb071a192015-09-17 16:42:56 +02003210 channel_->SetRecvParameters(recv_parameters);
Fredrik Solenberg709ed672015-09-15 12:26:33 +02003211 EXPECT_EQ(2, call_.GetAudioReceiveStreams().size());
Peter Boström0c4e06b2015-10-07 12:23:21 +02003212 for (uint32_t ssrc : ssrcs) {
Fredrik Solenberg709ed672015-09-15 12:26:33 +02003213 const auto* s = call_.GetAudioReceiveStream(ssrc);
Fredrik Solenberg4b60c732015-05-07 14:07:48 +02003214 EXPECT_NE(nullptr, s);
3215 const auto& s_exts = s->GetConfig().rtp.extensions;
Stefan Holmer9d69c3f2015-12-07 10:45:43 +01003216 EXPECT_EQ(capabilities.header_extensions.size(), s_exts.size());
3217 for (const auto& e_ext : capabilities.header_extensions) {
Fredrik Solenberg4b60c732015-05-07 14:07:48 +02003218 for (const auto& s_ext : s_exts) {
3219 if (e_ext.id == s_ext.id) {
isheriff6f8d6862016-05-26 11:24:55 -07003220 EXPECT_EQ(e_ext.uri, s_ext.uri);
Fredrik Solenberg4b60c732015-05-07 14:07:48 +02003221 }
3222 }
3223 }
3224 }
3225
3226 // Disable receive extensions.
Fredrik Solenbergb071a192015-09-17 16:42:56 +02003227 channel_->SetRecvParameters(cricket::AudioRecvParameters());
Peter Boström0c4e06b2015-10-07 12:23:21 +02003228 for (uint32_t ssrc : ssrcs) {
Fredrik Solenberg709ed672015-09-15 12:26:33 +02003229 const auto* s = call_.GetAudioReceiveStream(ssrc);
Fredrik Solenberg4b60c732015-05-07 14:07:48 +02003230 EXPECT_NE(nullptr, s);
3231 EXPECT_EQ(0, s->GetConfig().rtp.extensions.size());
3232 }
Fredrik Solenberg4b60c732015-05-07 14:07:48 +02003233}
3234
3235TEST_F(WebRtcVoiceEngineTestFake, DeliverAudioPacket_Call) {
3236 // Test that packets are forwarded to the Call when configured accordingly.
Peter Boström0c4e06b2015-10-07 12:23:21 +02003237 const uint32_t kAudioSsrc = 1;
jbaucheec21bd2016-03-20 06:15:43 -07003238 rtc::CopyOnWriteBuffer kPcmuPacket(kPcmuFrame, sizeof(kPcmuFrame));
Fredrik Solenberg4b60c732015-05-07 14:07:48 +02003239 static const unsigned char kRtcp[] = {
3240 0x80, 0xc9, 0x00, 0x01, 0x00, 0x00, 0x00, 0x02,
3241 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00,
3242 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
3243 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
3244 };
jbaucheec21bd2016-03-20 06:15:43 -07003245 rtc::CopyOnWriteBuffer kRtcpPacket(kRtcp, sizeof(kRtcp));
Fredrik Solenberg4b60c732015-05-07 14:07:48 +02003246
solenbergff976312016-03-30 23:28:51 -07003247 EXPECT_TRUE(SetupSendStream());
Fredrik Solenberg4b60c732015-05-07 14:07:48 +02003248 cricket::WebRtcVoiceMediaChannel* media_channel =
3249 static_cast<cricket::WebRtcVoiceMediaChannel*>(channel_);
solenberg059fb442016-10-26 05:12:24 -07003250 SetSendParameters(send_parameters_);
Fredrik Solenberg4b60c732015-05-07 14:07:48 +02003251 EXPECT_TRUE(media_channel->AddRecvStream(
3252 cricket::StreamParams::CreateLegacy(kAudioSsrc)));
3253
Fredrik Solenberg709ed672015-09-15 12:26:33 +02003254 EXPECT_EQ(1, call_.GetAudioReceiveStreams().size());
Fredrik Solenberg4b60c732015-05-07 14:07:48 +02003255 const cricket::FakeAudioReceiveStream* s =
Fredrik Solenberg709ed672015-09-15 12:26:33 +02003256 call_.GetAudioReceiveStream(kAudioSsrc);
Fredrik Solenberg4b60c732015-05-07 14:07:48 +02003257 EXPECT_EQ(0, s->received_packets());
3258 channel_->OnPacketReceived(&kPcmuPacket, rtc::PacketTime());
3259 EXPECT_EQ(1, s->received_packets());
3260 channel_->OnRtcpReceived(&kRtcpPacket, rtc::PacketTime());
3261 EXPECT_EQ(2, s->received_packets());
Fredrik Solenberg4b60c732015-05-07 14:07:48 +02003262}
Minyue2013aec2015-05-13 14:14:42 +02003263
solenberg0a617e22015-10-20 15:49:38 -07003264// All receive channels should be associated with the first send channel,
solenberg1ac56142015-10-13 03:58:19 -07003265// since they do not send RTCP SR.
solenberg7602aab2016-11-14 11:30:07 -08003266TEST_F(WebRtcVoiceEngineTestFake, AssociateFirstSendChannel_SendCreatedFirst) {
solenbergff976312016-03-30 23:28:51 -07003267 EXPECT_TRUE(SetupSendStream());
solenberg7602aab2016-11-14 11:30:07 -08003268 EXPECT_TRUE(AddRecvStream(kSsrc2));
3269 EXPECT_EQ(kSsrc1, GetRecvStreamConfig(kSsrc2).rtp.local_ssrc);
3270 EXPECT_TRUE(channel_->AddSendStream(
3271 cricket::StreamParams::CreateLegacy(kSsrc3)));
3272 EXPECT_EQ(kSsrc1, GetRecvStreamConfig(kSsrc2).rtp.local_ssrc);
3273 EXPECT_TRUE(AddRecvStream(kSsrc4));
3274 EXPECT_EQ(kSsrc1, GetRecvStreamConfig(kSsrc4).rtp.local_ssrc);
Minyue2013aec2015-05-13 14:14:42 +02003275}
3276
solenberg7602aab2016-11-14 11:30:07 -08003277TEST_F(WebRtcVoiceEngineTestFake, AssociateFirstSendChannel_RecvCreatedFirst) {
3278 EXPECT_TRUE(SetupRecvStream());
3279 EXPECT_EQ(0xFA17FA17u, GetRecvStreamConfig(kSsrc1).rtp.local_ssrc);
3280 EXPECT_TRUE(channel_->AddSendStream(
3281 cricket::StreamParams::CreateLegacy(kSsrc2)));
3282 EXPECT_EQ(kSsrc2, GetRecvStreamConfig(kSsrc1).rtp.local_ssrc);
3283 EXPECT_TRUE(AddRecvStream(kSsrc3));
3284 EXPECT_EQ(kSsrc2, GetRecvStreamConfig(kSsrc3).rtp.local_ssrc);
3285 EXPECT_TRUE(channel_->AddSendStream(
3286 cricket::StreamParams::CreateLegacy(kSsrc4)));
3287 EXPECT_EQ(kSsrc2, GetRecvStreamConfig(kSsrc1).rtp.local_ssrc);
3288 EXPECT_EQ(kSsrc2, GetRecvStreamConfig(kSsrc3).rtp.local_ssrc);
Minyue2013aec2015-05-13 14:14:42 +02003289}
stefan658910c2015-09-03 05:48:32 -07003290
deadbeef884f5852016-01-15 09:20:04 -08003291TEST_F(WebRtcVoiceEngineTestFake, SetRawAudioSink) {
solenbergff976312016-03-30 23:28:51 -07003292 EXPECT_TRUE(SetupChannel());
kwiberg686a8ef2016-02-26 03:00:35 -08003293 std::unique_ptr<FakeAudioSink> fake_sink_1(new FakeAudioSink());
3294 std::unique_ptr<FakeAudioSink> fake_sink_2(new FakeAudioSink());
deadbeef884f5852016-01-15 09:20:04 -08003295
3296 // Setting the sink before a recv stream exists should do nothing.
3297 channel_->SetRawAudioSink(kSsrc1, std::move(fake_sink_1));
solenberg8189b022016-06-14 12:13:00 -07003298 EXPECT_TRUE(AddRecvStream(kSsrc1));
deadbeef884f5852016-01-15 09:20:04 -08003299 EXPECT_EQ(nullptr, GetRecvStream(kSsrc1).sink());
3300
3301 // Now try actually setting the sink.
3302 channel_->SetRawAudioSink(kSsrc1, std::move(fake_sink_2));
3303 EXPECT_NE(nullptr, GetRecvStream(kSsrc1).sink());
3304
3305 // Now try resetting it.
3306 channel_->SetRawAudioSink(kSsrc1, nullptr);
3307 EXPECT_EQ(nullptr, GetRecvStream(kSsrc1).sink());
3308}
3309
3310TEST_F(WebRtcVoiceEngineTestFake, SetRawAudioSinkDefaultRecvStream) {
solenbergff976312016-03-30 23:28:51 -07003311 EXPECT_TRUE(SetupChannel());
kwiberg686a8ef2016-02-26 03:00:35 -08003312 std::unique_ptr<FakeAudioSink> fake_sink_1(new FakeAudioSink());
3313 std::unique_ptr<FakeAudioSink> fake_sink_2(new FakeAudioSink());
deadbeef884f5852016-01-15 09:20:04 -08003314
3315 // Should be able to set a default sink even when no stream exists.
3316 channel_->SetRawAudioSink(0, std::move(fake_sink_1));
3317
3318 // Create default channel and ensure it's assigned the default sink.
3319 DeliverPacket(kPcmuFrame, sizeof(kPcmuFrame));
3320 EXPECT_NE(nullptr, GetRecvStream(0x01).sink());
3321
3322 // Try resetting the default sink.
3323 channel_->SetRawAudioSink(0, nullptr);
3324 EXPECT_EQ(nullptr, GetRecvStream(0x01).sink());
3325
3326 // Try setting the default sink while the default stream exists.
3327 channel_->SetRawAudioSink(0, std::move(fake_sink_2));
3328 EXPECT_NE(nullptr, GetRecvStream(0x01).sink());
3329
3330 // If we remove and add a default stream, it should get the same sink.
3331 EXPECT_TRUE(channel_->RemoveRecvStream(0x01));
3332 DeliverPacket(kPcmuFrame, sizeof(kPcmuFrame));
3333 EXPECT_NE(nullptr, GetRecvStream(0x01).sink());
3334}
3335
skvlad7a43d252016-03-22 15:32:27 -07003336// Test that, just like the video channel, the voice channel communicates the
3337// network state to the call.
3338TEST_F(WebRtcVoiceEngineTestFake, OnReadyToSendSignalsNetworkState) {
solenbergff976312016-03-30 23:28:51 -07003339 EXPECT_TRUE(SetupChannel());
skvlad7a43d252016-03-22 15:32:27 -07003340
3341 EXPECT_EQ(webrtc::kNetworkUp,
3342 call_.GetNetworkState(webrtc::MediaType::AUDIO));
3343 EXPECT_EQ(webrtc::kNetworkUp,
3344 call_.GetNetworkState(webrtc::MediaType::VIDEO));
3345
3346 channel_->OnReadyToSend(false);
3347 EXPECT_EQ(webrtc::kNetworkDown,
3348 call_.GetNetworkState(webrtc::MediaType::AUDIO));
3349 EXPECT_EQ(webrtc::kNetworkUp,
3350 call_.GetNetworkState(webrtc::MediaType::VIDEO));
3351
3352 channel_->OnReadyToSend(true);
3353 EXPECT_EQ(webrtc::kNetworkUp,
3354 call_.GetNetworkState(webrtc::MediaType::AUDIO));
3355 EXPECT_EQ(webrtc::kNetworkUp,
3356 call_.GetNetworkState(webrtc::MediaType::VIDEO));
3357}
3358
aleloi18e0b672016-10-04 02:45:47 -07003359// Test that playout is still started after changing parameters
3360TEST_F(WebRtcVoiceEngineTestFake, PreservePlayoutWhenRecreateRecvStream) {
3361 SetupRecvStream();
3362 channel_->SetPlayout(true);
3363 EXPECT_TRUE(GetRecvStream(kSsrc1).started());
3364
3365 // Changing RTP header extensions will recreate the AudioReceiveStream.
3366 cricket::AudioRecvParameters parameters;
3367 parameters.extensions.push_back(
3368 webrtc::RtpExtension(webrtc::RtpExtension::kAudioLevelUri, 12));
3369 channel_->SetRecvParameters(parameters);
3370
3371 EXPECT_TRUE(GetRecvStream(kSsrc1).started());
3372}
3373
stefan658910c2015-09-03 05:48:32 -07003374// Tests that the library initializes and shuts down properly.
3375TEST(WebRtcVoiceEngineTest, StartupShutdown) {
ossu29b1a8d2016-06-13 07:34:51 -07003376 // If the VoiceEngine wants to gather available codecs early, that's fine but
3377 // we never want it to create a decoder at this stage.
ossuc54071d2016-08-17 02:45:41 -07003378 cricket::WebRtcVoiceEngine engine(
3379 nullptr, webrtc::MockAudioDecoderFactory::CreateUnusedFactory());
skvlad11a9cbf2016-10-07 11:53:05 -07003380 webrtc::RtcEventLogNullImpl event_log;
kwiberg686a8ef2016-02-26 03:00:35 -08003381 std::unique_ptr<webrtc::Call> call(
skvlad11a9cbf2016-10-07 11:53:05 -07003382 webrtc::Call::Create(webrtc::Call::Config(&event_log)));
nisse51542be2016-02-12 02:27:06 -08003383 cricket::VoiceMediaChannel* channel = engine.CreateChannel(
3384 call.get(), cricket::MediaConfig(), cricket::AudioOptions());
stefan658910c2015-09-03 05:48:32 -07003385 EXPECT_TRUE(channel != nullptr);
3386 delete channel;
solenbergff976312016-03-30 23:28:51 -07003387}
stefan658910c2015-09-03 05:48:32 -07003388
solenbergff976312016-03-30 23:28:51 -07003389// Tests that reference counting on the external ADM is correct.
solenbergbc37fc82016-04-04 09:54:44 -07003390TEST(WebRtcVoiceEngineTest, StartupShutdownWithExternalADM) {
3391 testing::NiceMock<webrtc::test::MockAudioDeviceModule> adm;
3392 EXPECT_CALL(adm, AddRef()).Times(3).WillRepeatedly(Return(0));
3393 EXPECT_CALL(adm, Release()).Times(3).WillRepeatedly(Return(0));
solenbergff976312016-03-30 23:28:51 -07003394 {
ossuc54071d2016-08-17 02:45:41 -07003395 cricket::WebRtcVoiceEngine engine(
3396 &adm, webrtc::MockAudioDecoderFactory::CreateUnusedFactory());
skvlad11a9cbf2016-10-07 11:53:05 -07003397 webrtc::RtcEventLogNullImpl event_log;
solenbergff976312016-03-30 23:28:51 -07003398 std::unique_ptr<webrtc::Call> call(
skvlad11a9cbf2016-10-07 11:53:05 -07003399 webrtc::Call::Create(webrtc::Call::Config(&event_log)));
solenbergff976312016-03-30 23:28:51 -07003400 cricket::VoiceMediaChannel* channel = engine.CreateChannel(
3401 call.get(), cricket::MediaConfig(), cricket::AudioOptions());
3402 EXPECT_TRUE(channel != nullptr);
3403 delete channel;
3404 }
stefan658910c2015-09-03 05:48:32 -07003405}
3406
3407// Tests that the library is configured with the codecs we want.
3408TEST(WebRtcVoiceEngineTest, HasCorrectCodecs) {
ossu29b1a8d2016-06-13 07:34:51 -07003409 // TODO(ossu): These tests should move into a future "builtin audio codecs"
3410 // module.
3411
stefan658910c2015-09-03 05:48:32 -07003412 // Check codecs by name.
solenberg26c8c912015-11-27 04:00:25 -08003413 EXPECT_TRUE(cricket::WebRtcVoiceEngine::ToCodecInst(
deadbeef67cf2c12016-04-13 10:07:16 -07003414 cricket::AudioCodec(96, "OPUS", 48000, 0, 2), nullptr));
solenberg26c8c912015-11-27 04:00:25 -08003415 EXPECT_TRUE(cricket::WebRtcVoiceEngine::ToCodecInst(
deadbeef67cf2c12016-04-13 10:07:16 -07003416 cricket::AudioCodec(96, "ISAC", 16000, 0, 1), nullptr));
solenberg26c8c912015-11-27 04:00:25 -08003417 EXPECT_TRUE(cricket::WebRtcVoiceEngine::ToCodecInst(
deadbeef67cf2c12016-04-13 10:07:16 -07003418 cricket::AudioCodec(96, "ISAC", 32000, 0, 1), nullptr));
stefan658910c2015-09-03 05:48:32 -07003419 // Check that name matching is case-insensitive.
solenberg26c8c912015-11-27 04:00:25 -08003420 EXPECT_TRUE(cricket::WebRtcVoiceEngine::ToCodecInst(
deadbeef67cf2c12016-04-13 10:07:16 -07003421 cricket::AudioCodec(96, "ILBC", 8000, 0, 1), nullptr));
solenberg26c8c912015-11-27 04:00:25 -08003422 EXPECT_TRUE(cricket::WebRtcVoiceEngine::ToCodecInst(
deadbeef67cf2c12016-04-13 10:07:16 -07003423 cricket::AudioCodec(96, "iLBC", 8000, 0, 1), nullptr));
solenberg26c8c912015-11-27 04:00:25 -08003424 EXPECT_TRUE(cricket::WebRtcVoiceEngine::ToCodecInst(
deadbeef67cf2c12016-04-13 10:07:16 -07003425 cricket::AudioCodec(96, "CN", 32000, 0, 1), nullptr));
solenberg26c8c912015-11-27 04:00:25 -08003426 EXPECT_TRUE(cricket::WebRtcVoiceEngine::ToCodecInst(
deadbeef67cf2c12016-04-13 10:07:16 -07003427 cricket::AudioCodec(96, "CN", 16000, 0, 1), nullptr));
solenberg26c8c912015-11-27 04:00:25 -08003428 EXPECT_TRUE(cricket::WebRtcVoiceEngine::ToCodecInst(
deadbeef67cf2c12016-04-13 10:07:16 -07003429 cricket::AudioCodec(96, "telephone-event", 8000, 0, 1), nullptr));
solenberg2779bab2016-11-17 04:45:19 -08003430 EXPECT_TRUE(cricket::WebRtcVoiceEngine::ToCodecInst(
3431 cricket::AudioCodec(96, "telephone-event", 16000, 0, 1), nullptr));
3432 EXPECT_TRUE(cricket::WebRtcVoiceEngine::ToCodecInst(
3433 cricket::AudioCodec(96, "telephone-event", 32000, 0, 1), nullptr));
3434 EXPECT_TRUE(cricket::WebRtcVoiceEngine::ToCodecInst(
3435 cricket::AudioCodec(96, "telephone-event", 48000, 0, 1), nullptr));
stefan658910c2015-09-03 05:48:32 -07003436 // Check codecs with an id by id.
solenberg26c8c912015-11-27 04:00:25 -08003437 EXPECT_TRUE(cricket::WebRtcVoiceEngine::ToCodecInst(
deadbeef67cf2c12016-04-13 10:07:16 -07003438 cricket::AudioCodec(0, "", 8000, 0, 1), nullptr)); // PCMU
solenberg26c8c912015-11-27 04:00:25 -08003439 EXPECT_TRUE(cricket::WebRtcVoiceEngine::ToCodecInst(
deadbeef67cf2c12016-04-13 10:07:16 -07003440 cricket::AudioCodec(8, "", 8000, 0, 1), nullptr)); // PCMA
solenberg26c8c912015-11-27 04:00:25 -08003441 EXPECT_TRUE(cricket::WebRtcVoiceEngine::ToCodecInst(
deadbeef67cf2c12016-04-13 10:07:16 -07003442 cricket::AudioCodec(9, "", 8000, 0, 1), nullptr)); // G722
solenberg26c8c912015-11-27 04:00:25 -08003443 EXPECT_TRUE(cricket::WebRtcVoiceEngine::ToCodecInst(
deadbeef67cf2c12016-04-13 10:07:16 -07003444 cricket::AudioCodec(13, "", 8000, 0, 1), nullptr)); // CN
stefan658910c2015-09-03 05:48:32 -07003445 // Check sample/bitrate matching.
solenberg26c8c912015-11-27 04:00:25 -08003446 EXPECT_TRUE(cricket::WebRtcVoiceEngine::ToCodecInst(
deadbeef67cf2c12016-04-13 10:07:16 -07003447 cricket::AudioCodec(0, "PCMU", 8000, 64000, 1), nullptr));
stefan658910c2015-09-03 05:48:32 -07003448 // Check that bad codecs fail.
solenberg26c8c912015-11-27 04:00:25 -08003449 EXPECT_FALSE(cricket::WebRtcVoiceEngine::ToCodecInst(
deadbeef67cf2c12016-04-13 10:07:16 -07003450 cricket::AudioCodec(99, "ABCD", 0, 0, 1), nullptr));
solenberg26c8c912015-11-27 04:00:25 -08003451 EXPECT_FALSE(cricket::WebRtcVoiceEngine::ToCodecInst(
deadbeef67cf2c12016-04-13 10:07:16 -07003452 cricket::AudioCodec(88, "", 0, 0, 1), nullptr));
solenberg26c8c912015-11-27 04:00:25 -08003453 EXPECT_FALSE(cricket::WebRtcVoiceEngine::ToCodecInst(
deadbeef67cf2c12016-04-13 10:07:16 -07003454 cricket::AudioCodec(0, "", 0, 0, 2), nullptr));
solenberg26c8c912015-11-27 04:00:25 -08003455 EXPECT_FALSE(cricket::WebRtcVoiceEngine::ToCodecInst(
deadbeef67cf2c12016-04-13 10:07:16 -07003456 cricket::AudioCodec(0, "", 5000, 0, 1), nullptr));
solenberg26c8c912015-11-27 04:00:25 -08003457 EXPECT_FALSE(cricket::WebRtcVoiceEngine::ToCodecInst(
deadbeef67cf2c12016-04-13 10:07:16 -07003458 cricket::AudioCodec(0, "", 0, 5000, 1), nullptr));
solenberg26c8c912015-11-27 04:00:25 -08003459
stefan658910c2015-09-03 05:48:32 -07003460 // Verify the payload id of common audio codecs, including CN, ISAC, and G722.
ossuc54071d2016-08-17 02:45:41 -07003461 // TODO(ossu): Why are the payload types of codecs with non-static payload
3462 // type assignments checked here? It shouldn't really matter.
3463 cricket::WebRtcVoiceEngine engine(
3464 nullptr, webrtc::MockAudioDecoderFactory::CreateUnusedFactory());
solenberg2779bab2016-11-17 04:45:19 -08003465 for (const cricket::AudioCodec& codec : engine.send_codecs()) {
3466 if (codec.name == "CN" && codec.clockrate == 16000) {
3467 EXPECT_EQ(105, codec.id);
3468 } else if (codec.name == "CN" && codec.clockrate == 32000) {
3469 EXPECT_EQ(106, codec.id);
3470 } else if (codec.name == "ISAC" && codec.clockrate == 16000) {
3471 EXPECT_EQ(103, codec.id);
3472 } else if (codec.name == "ISAC" && codec.clockrate == 32000) {
3473 EXPECT_EQ(104, codec.id);
3474 } else if (codec.name == "G722" && codec.clockrate == 8000) {
3475 EXPECT_EQ(9, codec.id);
3476 } else if (codec.name == "telephone-event" && codec.clockrate == 8000) {
3477 EXPECT_EQ(126, codec.id);
3478 // TODO(solenberg): 16k, 32k, 48k DTMF should be dynamically assigned.
3479 // Remove these checks once both send and receive side assigns payload types
3480 // dynamically.
3481 } else if (codec.name == "telephone-event" && codec.clockrate == 16000) {
3482 EXPECT_EQ(113, codec.id);
3483 } else if (codec.name == "telephone-event" && codec.clockrate == 32000) {
3484 EXPECT_EQ(112, codec.id);
3485 } else if (codec.name == "telephone-event" && codec.clockrate == 48000) {
3486 EXPECT_EQ(110, codec.id);
3487 } else if (codec.name == "opus") {
3488 EXPECT_EQ(111, codec.id);
3489 ASSERT_TRUE(codec.params.find("minptime") != codec.params.end());
3490 EXPECT_EQ("10", codec.params.find("minptime")->second);
3491 ASSERT_TRUE(codec.params.find("useinbandfec") != codec.params.end());
3492 EXPECT_EQ("1", codec.params.find("useinbandfec")->second);
stefan658910c2015-09-03 05:48:32 -07003493 }
3494 }
stefan658910c2015-09-03 05:48:32 -07003495}
3496
3497// Tests that VoE supports at least 32 channels
3498TEST(WebRtcVoiceEngineTest, Has32Channels) {
ossuc54071d2016-08-17 02:45:41 -07003499 cricket::WebRtcVoiceEngine engine(
3500 nullptr, webrtc::MockAudioDecoderFactory::CreateUnusedFactory());
skvlad11a9cbf2016-10-07 11:53:05 -07003501 webrtc::RtcEventLogNullImpl event_log;
kwiberg686a8ef2016-02-26 03:00:35 -08003502 std::unique_ptr<webrtc::Call> call(
skvlad11a9cbf2016-10-07 11:53:05 -07003503 webrtc::Call::Create(webrtc::Call::Config(&event_log)));
stefan658910c2015-09-03 05:48:32 -07003504
3505 cricket::VoiceMediaChannel* channels[32];
3506 int num_channels = 0;
tfarina5237aaf2015-11-10 23:44:30 -08003507 while (num_channels < arraysize(channels)) {
nisse51542be2016-02-12 02:27:06 -08003508 cricket::VoiceMediaChannel* channel = engine.CreateChannel(
3509 call.get(), cricket::MediaConfig(), cricket::AudioOptions());
stefan658910c2015-09-03 05:48:32 -07003510 if (!channel)
3511 break;
stefan658910c2015-09-03 05:48:32 -07003512 channels[num_channels++] = channel;
3513 }
3514
tfarina5237aaf2015-11-10 23:44:30 -08003515 int expected = arraysize(channels);
stefan658910c2015-09-03 05:48:32 -07003516 EXPECT_EQ(expected, num_channels);
3517
3518 while (num_channels > 0) {
3519 delete channels[--num_channels];
3520 }
stefan658910c2015-09-03 05:48:32 -07003521}
3522
3523// Test that we set our preferred codecs properly.
3524TEST(WebRtcVoiceEngineTest, SetRecvCodecs) {
ossu29b1a8d2016-06-13 07:34:51 -07003525 // TODO(ossu): I'm not sure of the intent of this test. It's either:
3526 // - Check that our builtin codecs are usable by Channel.
3527 // - The codecs provided by the engine is usable by Channel.
3528 // It does not check that the codecs in the RecvParameters are actually
3529 // what we sent in - though it's probably reasonable to expect so, if
3530 // SetRecvParameters returns true.
3531 // I think it will become clear once audio decoder injection is completed.
3532 cricket::WebRtcVoiceEngine engine(
3533 nullptr, webrtc::CreateBuiltinAudioDecoderFactory());
skvlad11a9cbf2016-10-07 11:53:05 -07003534 webrtc::RtcEventLogNullImpl event_log;
kwiberg686a8ef2016-02-26 03:00:35 -08003535 std::unique_ptr<webrtc::Call> call(
skvlad11a9cbf2016-10-07 11:53:05 -07003536 webrtc::Call::Create(webrtc::Call::Config(&event_log)));
nisse51542be2016-02-12 02:27:06 -08003537 cricket::WebRtcVoiceMediaChannel channel(&engine, cricket::MediaConfig(),
3538 cricket::AudioOptions(), call.get());
Fredrik Solenbergb071a192015-09-17 16:42:56 +02003539 cricket::AudioRecvParameters parameters;
ossudedfd282016-06-14 07:12:39 -07003540 parameters.codecs = engine.recv_codecs();
Fredrik Solenbergb071a192015-09-17 16:42:56 +02003541 EXPECT_TRUE(channel.SetRecvParameters(parameters));
stefan658910c2015-09-03 05:48:32 -07003542}