blob: 2b93deb857d5c15c0efbb42afdd1be0e07890740 [file] [log] [blame]
solenbergc7a8b082015-10-16 14:35:07 -07001/*
2 * Copyright (c) 2015 The WebRTC project authors. All Rights Reserved.
3 *
4 * 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.
9 */
10
11#include <list>
kwibergb25345e2016-03-12 06:10:44 -080012#include <memory>
solenbergc7a8b082015-10-16 14:35:07 -070013
kjellandera69d9732016-08-31 07:33:05 -070014#include "webrtc/api/call/audio_state.h"
solenbergc7a8b082015-10-16 14:35:07 -070015#include "webrtc/call.h"
skvlad11a9cbf2016-10-07 11:53:05 -070016#include "webrtc/logging/rtc_event_log/rtc_event_log.h"
ossu29b1a8d2016-06-13 07:34:51 -070017#include "webrtc/modules/audio_coding/codecs/mock/mock_audio_decoder_factory.h"
kwibergac9f8762016-09-30 22:29:43 -070018#include "webrtc/test/gtest.h"
Fredrik Solenberg0ccae132015-11-03 10:15:49 +010019#include "webrtc/test/mock_voice_engine.h"
solenbergc7a8b082015-10-16 14:35:07 -070020
21namespace {
22
23struct CallHelper {
ossu29b1a8d2016-06-13 07:34:51 -070024 explicit CallHelper(
25 rtc::scoped_refptr<webrtc::AudioDecoderFactory> decoder_factory = nullptr)
26 : voice_engine_(decoder_factory) {
solenberg566ef242015-11-06 15:34:49 -080027 webrtc::AudioState::Config audio_state_config;
28 audio_state_config.voice_engine = &voice_engine_;
skvlad11a9cbf2016-10-07 11:53:05 -070029 webrtc::Call::Config config(&event_log_);
solenberg566ef242015-11-06 15:34:49 -080030 config.audio_state = webrtc::AudioState::Create(audio_state_config);
solenbergc7a8b082015-10-16 14:35:07 -070031 call_.reset(webrtc::Call::Create(config));
32 }
33
34 webrtc::Call* operator->() { return call_.get(); }
solenberg7602aab2016-11-14 11:30:07 -080035 webrtc::test::MockVoiceEngine* voice_engine() { return &voice_engine_; }
solenbergc7a8b082015-10-16 14:35:07 -070036
37 private:
solenberg3a941542015-11-16 07:34:50 -080038 testing::NiceMock<webrtc::test::MockVoiceEngine> voice_engine_;
skvlad11a9cbf2016-10-07 11:53:05 -070039 webrtc::RtcEventLogNullImpl event_log_;
kwibergb25345e2016-03-12 06:10:44 -080040 std::unique_ptr<webrtc::Call> call_;
solenbergc7a8b082015-10-16 14:35:07 -070041};
42} // namespace
43
44namespace webrtc {
45
46TEST(CallTest, ConstructDestruct) {
47 CallHelper call;
48}
49
50TEST(CallTest, CreateDestroy_AudioSendStream) {
51 CallHelper call;
52 AudioSendStream::Config config(nullptr);
53 config.rtp.ssrc = 42;
54 config.voe_channel_id = 123;
55 AudioSendStream* stream = call->CreateAudioSendStream(config);
56 EXPECT_NE(stream, nullptr);
57 call->DestroyAudioSendStream(stream);
58}
59
60TEST(CallTest, CreateDestroy_AudioReceiveStream) {
ossu29b1a8d2016-06-13 07:34:51 -070061 rtc::scoped_refptr<webrtc::AudioDecoderFactory> decoder_factory(
62 new rtc::RefCountedObject<webrtc::MockAudioDecoderFactory>);
63 CallHelper call(decoder_factory);
solenbergc7a8b082015-10-16 14:35:07 -070064 AudioReceiveStream::Config config;
65 config.rtp.remote_ssrc = 42;
66 config.voe_channel_id = 123;
ossu29b1a8d2016-06-13 07:34:51 -070067 config.decoder_factory = decoder_factory;
solenbergc7a8b082015-10-16 14:35:07 -070068 AudioReceiveStream* stream = call->CreateAudioReceiveStream(config);
69 EXPECT_NE(stream, nullptr);
70 call->DestroyAudioReceiveStream(stream);
71}
72
73TEST(CallTest, CreateDestroy_AudioSendStreams) {
74 CallHelper call;
75 AudioSendStream::Config config(nullptr);
76 config.voe_channel_id = 123;
77 std::list<AudioSendStream*> streams;
78 for (int i = 0; i < 2; ++i) {
79 for (uint32_t ssrc = 0; ssrc < 1234567; ssrc += 34567) {
80 config.rtp.ssrc = ssrc;
81 AudioSendStream* stream = call->CreateAudioSendStream(config);
82 EXPECT_NE(stream, nullptr);
83 if (ssrc & 1) {
84 streams.push_back(stream);
85 } else {
86 streams.push_front(stream);
87 }
88 }
89 for (auto s : streams) {
90 call->DestroyAudioSendStream(s);
91 }
92 streams.clear();
93 }
94}
95
96TEST(CallTest, CreateDestroy_AudioReceiveStreams) {
ossu29b1a8d2016-06-13 07:34:51 -070097 rtc::scoped_refptr<webrtc::AudioDecoderFactory> decoder_factory(
98 new rtc::RefCountedObject<webrtc::MockAudioDecoderFactory>);
99 CallHelper call(decoder_factory);
solenbergc7a8b082015-10-16 14:35:07 -0700100 AudioReceiveStream::Config config;
101 config.voe_channel_id = 123;
ossu29b1a8d2016-06-13 07:34:51 -0700102 config.decoder_factory = decoder_factory;
solenbergc7a8b082015-10-16 14:35:07 -0700103 std::list<AudioReceiveStream*> streams;
104 for (int i = 0; i < 2; ++i) {
105 for (uint32_t ssrc = 0; ssrc < 1234567; ssrc += 34567) {
106 config.rtp.remote_ssrc = ssrc;
107 AudioReceiveStream* stream = call->CreateAudioReceiveStream(config);
108 EXPECT_NE(stream, nullptr);
109 if (ssrc & 1) {
110 streams.push_back(stream);
111 } else {
112 streams.push_front(stream);
113 }
114 }
115 for (auto s : streams) {
116 call->DestroyAudioReceiveStream(s);
117 }
118 streams.clear();
119 }
120}
brandtr25445d32016-10-23 23:37:14 -0700121
solenberg7602aab2016-11-14 11:30:07 -0800122TEST(CallTest, CreateDestroy_AssociateAudioSendReceiveStreams_RecvFirst) {
123 rtc::scoped_refptr<webrtc::AudioDecoderFactory> decoder_factory(
124 new rtc::RefCountedObject<webrtc::MockAudioDecoderFactory>);
125 CallHelper call(decoder_factory);
126
127 constexpr int kRecvChannelId = 101;
128
129 // Set up the mock to create a channel proxy which we know of, so that we can
130 // add our expectations to it.
131 test::MockVoEChannelProxy* recv_channel_proxy = nullptr;
132 EXPECT_CALL(*call.voice_engine(), ChannelProxyFactory(testing::_))
133 .WillRepeatedly(testing::Invoke([&](int channel_id) {
134 test::MockVoEChannelProxy* channel_proxy =
135 new testing::NiceMock<test::MockVoEChannelProxy>();
136 EXPECT_CALL(*channel_proxy, GetAudioDecoderFactory())
137 .WillRepeatedly(testing::ReturnRef(decoder_factory));
138 // If being called for the send channel, save a pointer to the channel
139 // proxy for later.
140 if (channel_id == kRecvChannelId) {
141 EXPECT_FALSE(recv_channel_proxy);
142 recv_channel_proxy = channel_proxy;
143 }
144 return channel_proxy;
145 }));
146
147 AudioReceiveStream::Config recv_config;
148 recv_config.rtp.remote_ssrc = 42;
149 recv_config.rtp.local_ssrc = 777;
150 recv_config.voe_channel_id = kRecvChannelId;
151 recv_config.decoder_factory = decoder_factory;
152 AudioReceiveStream* recv_stream = call->CreateAudioReceiveStream(recv_config);
153 EXPECT_NE(recv_stream, nullptr);
154
155 EXPECT_CALL(*recv_channel_proxy, AssociateSendChannel(testing::_)).Times(1);
156 AudioSendStream::Config send_config(nullptr);
157 send_config.rtp.ssrc = 777;
158 send_config.voe_channel_id = 123;
159 AudioSendStream* send_stream = call->CreateAudioSendStream(send_config);
160 EXPECT_NE(send_stream, nullptr);
161
162 EXPECT_CALL(*recv_channel_proxy, DisassociateSendChannel()).Times(1);
163 call->DestroyAudioSendStream(send_stream);
164
165 EXPECT_CALL(*recv_channel_proxy, DisassociateSendChannel()).Times(1);
166 call->DestroyAudioReceiveStream(recv_stream);
167}
168
169TEST(CallTest, CreateDestroy_AssociateAudioSendReceiveStreams_SendFirst) {
170 rtc::scoped_refptr<webrtc::AudioDecoderFactory> decoder_factory(
171 new rtc::RefCountedObject<webrtc::MockAudioDecoderFactory>);
172 CallHelper call(decoder_factory);
173
174 constexpr int kRecvChannelId = 101;
175
176 // Set up the mock to create a channel proxy which we know of, so that we can
177 // add our expectations to it.
178 test::MockVoEChannelProxy* recv_channel_proxy = nullptr;
179 EXPECT_CALL(*call.voice_engine(), ChannelProxyFactory(testing::_))
180 .WillRepeatedly(testing::Invoke([&](int channel_id) {
181 test::MockVoEChannelProxy* channel_proxy =
182 new testing::NiceMock<test::MockVoEChannelProxy>();
183 EXPECT_CALL(*channel_proxy, GetAudioDecoderFactory())
184 .WillRepeatedly(testing::ReturnRef(decoder_factory));
185 // If being called for the send channel, save a pointer to the channel
186 // proxy for later.
187 if (channel_id == kRecvChannelId) {
188 EXPECT_FALSE(recv_channel_proxy);
189 recv_channel_proxy = channel_proxy;
190 // We need to set this expectation here since the channel proxy is
191 // created as a side effect of CreateAudioReceiveStream().
192 EXPECT_CALL(*recv_channel_proxy,
193 AssociateSendChannel(testing::_)).Times(1);
194 }
195 return channel_proxy;
196 }));
197
198 AudioSendStream::Config send_config(nullptr);
199 send_config.rtp.ssrc = 777;
200 send_config.voe_channel_id = 123;
201 AudioSendStream* send_stream = call->CreateAudioSendStream(send_config);
202 EXPECT_NE(send_stream, nullptr);
203
204 AudioReceiveStream::Config recv_config;
205 recv_config.rtp.remote_ssrc = 42;
206 recv_config.rtp.local_ssrc = 777;
207 recv_config.voe_channel_id = kRecvChannelId;
208 recv_config.decoder_factory = decoder_factory;
209 AudioReceiveStream* recv_stream = call->CreateAudioReceiveStream(recv_config);
210 EXPECT_NE(recv_stream, nullptr);
211
212 EXPECT_CALL(*recv_channel_proxy, DisassociateSendChannel()).Times(1);
213 call->DestroyAudioReceiveStream(recv_stream);
214
215 call->DestroyAudioSendStream(send_stream);
216}
217
brandtr25445d32016-10-23 23:37:14 -0700218TEST(CallTest, CreateDestroy_FlexfecReceiveStream) {
219 CallHelper call;
220 FlexfecReceiveStream::Config config;
221 config.flexfec_payload_type = 118;
222 config.flexfec_ssrc = 38837212;
223 config.protected_media_ssrcs = {27273};
224
225 FlexfecReceiveStream* stream = call->CreateFlexfecReceiveStream(config);
226 EXPECT_NE(stream, nullptr);
227 call->DestroyFlexfecReceiveStream(stream);
228}
229
230TEST(CallTest, CreateDestroy_FlexfecReceiveStreams) {
231 CallHelper call;
232 FlexfecReceiveStream::Config config;
233 config.flexfec_payload_type = 118;
234 std::list<FlexfecReceiveStream*> streams;
235
236 for (int i = 0; i < 2; ++i) {
237 for (uint32_t ssrc = 0; ssrc < 1234567; ssrc += 34567) {
238 config.flexfec_ssrc = ssrc;
239 config.protected_media_ssrcs = {ssrc + 1};
240 FlexfecReceiveStream* stream = call->CreateFlexfecReceiveStream(config);
241 EXPECT_NE(stream, nullptr);
242 if (ssrc & 1) {
243 streams.push_back(stream);
244 } else {
245 streams.push_front(stream);
246 }
247 }
248 for (auto s : streams) {
249 call->DestroyFlexfecReceiveStream(s);
250 }
251 streams.clear();
252 }
253}
254
255TEST(CallTest, MultipleFlexfecReceiveStreamsProtectingSingleVideoStream) {
256 CallHelper call;
257 FlexfecReceiveStream::Config config;
258 config.flexfec_payload_type = 118;
259 config.protected_media_ssrcs = {1324234};
260 FlexfecReceiveStream* stream;
261 std::list<FlexfecReceiveStream*> streams;
262
263 config.flexfec_ssrc = 838383;
264 stream = call->CreateFlexfecReceiveStream(config);
265 EXPECT_NE(stream, nullptr);
266 streams.push_back(stream);
267
268 config.flexfec_ssrc = 424993;
269 stream = call->CreateFlexfecReceiveStream(config);
270 EXPECT_NE(stream, nullptr);
271 streams.push_back(stream);
272
273 config.flexfec_ssrc = 99383;
274 stream = call->CreateFlexfecReceiveStream(config);
275 EXPECT_NE(stream, nullptr);
276 streams.push_back(stream);
277
278 config.flexfec_ssrc = 5548;
279 stream = call->CreateFlexfecReceiveStream(config);
280 EXPECT_NE(stream, nullptr);
281 streams.push_back(stream);
282
283 for (auto s : streams) {
284 call->DestroyFlexfecReceiveStream(s);
285 }
286}
287
solenbergc7a8b082015-10-16 14:35:07 -0700288} // namespace webrtc