OLD | NEW |
| (Empty) |
1 /* | |
2 * Copyright 2016 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 "webrtc/api/trackmediainfomap.h" | |
12 | |
13 #include <initializer_list> | |
14 #include <memory> | |
15 #include <utility> | |
16 #include <vector> | |
17 | |
18 #include "webrtc/api/audiotrack.h" | |
19 #include "webrtc/api/rtpreceiverinterface.h" | |
20 #include "webrtc/api/rtpsenderinterface.h" | |
21 #include "webrtc/api/test/mock_rtpreceiver.h" | |
22 #include "webrtc/api/test/mock_rtpsender.h" | |
23 #include "webrtc/api/test/fakevideotracksource.h" | |
24 #include "webrtc/api/videotrack.h" | |
25 #include "webrtc/base/refcount.h" | |
26 #include "webrtc/media/base/mediachannel.h" | |
27 #include "webrtc/test/gtest.h" | |
28 | |
29 namespace webrtc { | |
30 | |
31 namespace { | |
32 | |
33 RtpParameters CreateRtpParametersWithSsrcs( | |
34 std::initializer_list<uint32_t> ssrcs) { | |
35 RtpParameters params; | |
36 for (uint32_t ssrc : ssrcs) { | |
37 RtpEncodingParameters encoding_params; | |
38 encoding_params.ssrc = rtc::Optional<uint32_t>(ssrc); | |
39 params.encodings.push_back(encoding_params); | |
40 } | |
41 return params; | |
42 } | |
43 | |
44 rtc::scoped_refptr<MockRtpSender> CreateMockRtpSender( | |
45 cricket::MediaType media_type, std::initializer_list<uint32_t> ssrcs, | |
46 rtc::scoped_refptr<MediaStreamTrackInterface> track) { | |
47 uint32_t first_ssrc; | |
48 if (ssrcs.size()) { | |
49 first_ssrc = *ssrcs.begin(); | |
50 } else { | |
51 first_ssrc = 0; | |
52 } | |
53 rtc::scoped_refptr<MockRtpSender> sender( | |
54 new rtc::RefCountedObject<MockRtpSender>()); | |
55 EXPECT_CALL(*sender, track()).WillRepeatedly(testing::Return(track)); | |
56 EXPECT_CALL(*sender, ssrc()).WillRepeatedly(testing::Return(first_ssrc)); | |
57 EXPECT_CALL(*sender, media_type()).WillRepeatedly(testing::Return( | |
58 media_type)); | |
59 EXPECT_CALL(*sender, GetParameters()).WillRepeatedly(testing::Return( | |
60 CreateRtpParametersWithSsrcs(ssrcs))); | |
61 return sender; | |
62 } | |
63 | |
64 rtc::scoped_refptr<MockRtpReceiver> CreateMockRtpReceiver( | |
65 cricket::MediaType media_type, std::initializer_list<uint32_t> ssrcs, | |
66 rtc::scoped_refptr<MediaStreamTrackInterface> track) { | |
67 rtc::scoped_refptr<MockRtpReceiver> receiver( | |
68 new rtc::RefCountedObject<MockRtpReceiver>()); | |
69 EXPECT_CALL(*receiver, track()).WillRepeatedly(testing::Return(track)); | |
70 EXPECT_CALL(*receiver, media_type()).WillRepeatedly(testing::Return( | |
71 media_type)); | |
72 EXPECT_CALL(*receiver, GetParameters()).WillRepeatedly(testing::Return( | |
73 CreateRtpParametersWithSsrcs(ssrcs))); | |
74 return receiver; | |
75 } | |
76 | |
77 class TrackMediaInfoMapTest : public testing::Test { | |
78 public: | |
79 TrackMediaInfoMapTest() | |
80 : voice_media_info_(new cricket::VoiceMediaInfo()), | |
81 video_media_info_(new cricket::VideoMediaInfo()), | |
82 local_audio_track_(AudioTrack::Create("LocalAudioTrack", nullptr)), | |
83 remote_audio_track_(AudioTrack::Create("RemoteAudioTrack", nullptr)), | |
84 local_video_track_( | |
85 VideoTrack::Create("LocalVideoTrack", | |
86 FakeVideoTrackSource::Create(false))), | |
87 remote_video_track_( | |
88 VideoTrack::Create("RemoteVideoTrack", | |
89 FakeVideoTrackSource::Create(false))) { | |
90 } | |
91 | |
92 ~TrackMediaInfoMapTest() { | |
93 // If we have a map the ownership has been passed to the map, only delete if | |
94 // |CreateMap| has not been called. | |
95 if (!map_) { | |
96 delete voice_media_info_; | |
97 delete video_media_info_; | |
98 } | |
99 } | |
100 | |
101 void AddRtpSenderWithSsrcs(std::initializer_list<uint32_t> ssrcs, | |
102 MediaStreamTrackInterface* local_track) { | |
103 rtc::scoped_refptr<MockRtpSender> rtp_sender = CreateMockRtpSender( | |
104 local_track->kind() == MediaStreamTrackInterface::kAudioKind ? | |
105 cricket::MEDIA_TYPE_AUDIO : cricket::MEDIA_TYPE_VIDEO, | |
106 ssrcs, local_track); | |
107 rtp_senders_.push_back(rtp_sender); | |
108 | |
109 if (local_track->kind() == MediaStreamTrackInterface::kAudioKind) { | |
110 cricket::VoiceSenderInfo voice_sender_info; | |
111 size_t i = 0; | |
112 for (uint32_t ssrc : ssrcs) { | |
113 voice_sender_info.local_stats.push_back(cricket::SsrcSenderInfo()); | |
114 voice_sender_info.local_stats[i++].ssrc = ssrc; | |
115 } | |
116 voice_media_info_->senders.push_back(voice_sender_info); | |
117 } else { | |
118 cricket::VideoSenderInfo video_sender_info; | |
119 size_t i = 0; | |
120 for (uint32_t ssrc : ssrcs) { | |
121 video_sender_info.local_stats.push_back(cricket::SsrcSenderInfo()); | |
122 video_sender_info.local_stats[i++].ssrc = ssrc; | |
123 } | |
124 video_media_info_->senders.push_back(video_sender_info); | |
125 } | |
126 } | |
127 | |
128 void AddRtpReceiverWithSsrcs(std::initializer_list<uint32_t> ssrcs, | |
129 MediaStreamTrackInterface* remote_track) { | |
130 rtc::scoped_refptr<MockRtpReceiver> rtp_receiver = CreateMockRtpReceiver( | |
131 remote_track->kind() == MediaStreamTrackInterface::kAudioKind ? | |
132 cricket::MEDIA_TYPE_AUDIO : cricket::MEDIA_TYPE_VIDEO, | |
133 ssrcs, remote_track); | |
134 rtp_receivers_.push_back(rtp_receiver); | |
135 | |
136 if (remote_track->kind() == MediaStreamTrackInterface::kAudioKind) { | |
137 cricket::VoiceReceiverInfo voice_receiver_info; | |
138 size_t i = 0; | |
139 for (uint32_t ssrc : ssrcs) { | |
140 voice_receiver_info.local_stats.push_back(cricket::SsrcReceiverInfo()); | |
141 voice_receiver_info.local_stats[i++].ssrc = ssrc; | |
142 } | |
143 voice_media_info_->receivers.push_back(voice_receiver_info); | |
144 } else { | |
145 cricket::VideoReceiverInfo video_receiver_info; | |
146 size_t i = 0; | |
147 for (uint32_t ssrc : ssrcs) { | |
148 video_receiver_info.local_stats.push_back(cricket::SsrcReceiverInfo()); | |
149 video_receiver_info.local_stats[i++].ssrc = ssrc; | |
150 } | |
151 video_media_info_->receivers.push_back(video_receiver_info); | |
152 } | |
153 } | |
154 | |
155 void CreateMap() { | |
156 RTC_DCHECK(!map_); | |
157 map_.reset(new TrackMediaInfoMap( | |
158 std::unique_ptr<cricket::VoiceMediaInfo>(voice_media_info_), | |
159 std::unique_ptr<cricket::VideoMediaInfo>(video_media_info_), | |
160 rtp_senders_, | |
161 rtp_receivers_)); | |
162 } | |
163 | |
164 protected: | |
165 cricket::VoiceMediaInfo* voice_media_info_; | |
166 cricket::VideoMediaInfo* video_media_info_; | |
167 std::vector<rtc::scoped_refptr<RtpSenderInterface>> rtp_senders_; | |
168 std::vector<rtc::scoped_refptr<RtpReceiverInterface>> rtp_receivers_; | |
169 std::unique_ptr<TrackMediaInfoMap> map_; | |
170 rtc::scoped_refptr<AudioTrack> local_audio_track_; | |
171 rtc::scoped_refptr<AudioTrack> remote_audio_track_; | |
172 rtc::scoped_refptr<VideoTrack> local_video_track_; | |
173 rtc::scoped_refptr<VideoTrack> remote_video_track_; | |
174 }; | |
175 | |
176 } // namespace | |
177 | |
178 TEST_F(TrackMediaInfoMapTest, SingleSenderReceiverPerTrackWithOneSsrc) { | |
179 AddRtpSenderWithSsrcs({ 1 }, local_audio_track_); | |
180 AddRtpReceiverWithSsrcs({ 2 }, remote_audio_track_); | |
181 AddRtpSenderWithSsrcs({ 3 }, local_video_track_); | |
182 AddRtpReceiverWithSsrcs({ 4 }, remote_video_track_); | |
183 CreateMap(); | |
184 | |
185 // Local audio track <-> RTP audio sender | |
186 ASSERT_TRUE(map_->GetVoiceSenderInfos(*local_audio_track_)); | |
187 EXPECT_EQ(*map_->GetVoiceSenderInfos(*local_audio_track_), | |
188 std::vector<cricket::VoiceSenderInfo*>({ | |
189 &voice_media_info_->senders[0] })); | |
190 EXPECT_EQ(map_->GetAudioTrack(voice_media_info_->senders[0]), | |
191 local_audio_track_.get()); | |
192 | |
193 // Remote audio track <-> RTP audio receiver | |
194 EXPECT_EQ(map_->GetVoiceReceiverInfo(*remote_audio_track_), | |
195 &voice_media_info_->receivers[0]); | |
196 EXPECT_EQ(map_->GetAudioTrack(voice_media_info_->receivers[0]), | |
197 remote_audio_track_.get()); | |
198 | |
199 // Local video track <-> RTP video sender | |
200 ASSERT_TRUE(map_->GetVideoSenderInfos(*local_video_track_)); | |
201 EXPECT_EQ(*map_->GetVideoSenderInfos(*local_video_track_), | |
202 std::vector<cricket::VideoSenderInfo*>({ | |
203 &video_media_info_->senders[0] })); | |
204 EXPECT_EQ(map_->GetVideoTrack(video_media_info_->senders[0]), | |
205 local_video_track_.get()); | |
206 | |
207 // Remote video track <-> RTP video receiver | |
208 EXPECT_EQ(map_->GetVideoReceiverInfo(*remote_video_track_), | |
209 &video_media_info_->receivers[0]); | |
210 EXPECT_EQ(map_->GetVideoTrack(video_media_info_->receivers[0]), | |
211 remote_video_track_.get()); | |
212 } | |
213 | |
214 TEST_F(TrackMediaInfoMapTest, SingleSenderReceiverPerTrackWithMissingSsrc) { | |
215 AddRtpSenderWithSsrcs({}, local_audio_track_); | |
216 AddRtpSenderWithSsrcs({}, local_video_track_); | |
217 AddRtpReceiverWithSsrcs({}, remote_audio_track_); | |
218 AddRtpReceiverWithSsrcs({}, remote_video_track_); | |
219 CreateMap(); | |
220 | |
221 EXPECT_FALSE(map_->GetVoiceSenderInfos(*local_audio_track_)); | |
222 EXPECT_FALSE(map_->GetVideoSenderInfos(*local_video_track_)); | |
223 EXPECT_FALSE(map_->GetVoiceReceiverInfo(*remote_audio_track_)); | |
224 EXPECT_FALSE(map_->GetVideoReceiverInfo(*remote_video_track_)); | |
225 } | |
226 | |
227 TEST_F(TrackMediaInfoMapTest, | |
228 SingleSenderReceiverPerTrackWithAudioAndVideoUseSameSsrc) { | |
229 AddRtpSenderWithSsrcs({ 1 }, local_audio_track_); | |
230 AddRtpReceiverWithSsrcs({ 2 }, remote_audio_track_); | |
231 AddRtpSenderWithSsrcs({ 1 }, local_video_track_); | |
232 AddRtpReceiverWithSsrcs({ 2 }, remote_video_track_); | |
233 CreateMap(); | |
234 | |
235 // Local audio track <-> RTP audio sender | |
236 ASSERT_TRUE(map_->GetVoiceSenderInfos(*local_audio_track_)); | |
237 EXPECT_EQ(*map_->GetVoiceSenderInfos(*local_audio_track_), | |
238 std::vector<cricket::VoiceSenderInfo*>({ | |
239 &voice_media_info_->senders[0] })); | |
240 EXPECT_EQ(map_->GetAudioTrack(voice_media_info_->senders[0]), | |
241 local_audio_track_.get()); | |
242 | |
243 // Remote audio track <-> RTP audio receiver | |
244 EXPECT_EQ(map_->GetVoiceReceiverInfo(*remote_audio_track_), | |
245 &voice_media_info_->receivers[0]); | |
246 EXPECT_EQ(map_->GetAudioTrack(voice_media_info_->receivers[0]), | |
247 remote_audio_track_.get()); | |
248 | |
249 // Local video track <-> RTP video sender | |
250 ASSERT_TRUE(map_->GetVideoSenderInfos(*local_video_track_)); | |
251 EXPECT_EQ(*map_->GetVideoSenderInfos(*local_video_track_), | |
252 std::vector<cricket::VideoSenderInfo*>({ | |
253 &video_media_info_->senders[0] })); | |
254 EXPECT_EQ(map_->GetVideoTrack(video_media_info_->senders[0]), | |
255 local_video_track_.get()); | |
256 | |
257 // Remote video track <-> RTP video receiver | |
258 EXPECT_EQ(map_->GetVideoReceiverInfo(*remote_video_track_), | |
259 &video_media_info_->receivers[0]); | |
260 EXPECT_EQ(map_->GetVideoTrack(video_media_info_->receivers[0]), | |
261 remote_video_track_.get()); | |
262 } | |
263 | |
264 TEST_F(TrackMediaInfoMapTest, SingleMultiSsrcSenderPerTrack) { | |
265 AddRtpSenderWithSsrcs({ 1, 2 }, local_audio_track_); | |
266 AddRtpSenderWithSsrcs({ 3, 4 }, local_video_track_); | |
267 CreateMap(); | |
268 | |
269 // Local audio track <-> RTP audio senders | |
270 ASSERT_TRUE(map_->GetVoiceSenderInfos(*local_audio_track_)); | |
271 EXPECT_EQ(*map_->GetVoiceSenderInfos(*local_audio_track_), | |
272 std::vector<cricket::VoiceSenderInfo*>({ | |
273 &voice_media_info_->senders[0] })); | |
274 EXPECT_EQ(map_->GetAudioTrack(voice_media_info_->senders[0]), | |
275 local_audio_track_.get()); | |
276 | |
277 // Local video track <-> RTP video senders | |
278 ASSERT_TRUE(map_->GetVideoSenderInfos(*local_video_track_)); | |
279 EXPECT_EQ(*map_->GetVideoSenderInfos(*local_video_track_), | |
280 std::vector<cricket::VideoSenderInfo*>({ | |
281 &video_media_info_->senders[0] })); | |
282 EXPECT_EQ(map_->GetVideoTrack(video_media_info_->senders[0]), | |
283 local_video_track_.get()); | |
284 } | |
285 | |
286 TEST_F(TrackMediaInfoMapTest, MultipleOneSsrcSendersPerTrack) { | |
287 AddRtpSenderWithSsrcs({ 1 }, local_audio_track_); | |
288 AddRtpSenderWithSsrcs({ 2 }, local_audio_track_); | |
289 AddRtpSenderWithSsrcs({ 3 }, local_video_track_); | |
290 AddRtpSenderWithSsrcs({ 4 }, local_video_track_); | |
291 CreateMap(); | |
292 | |
293 // Local audio track <-> RTP audio senders | |
294 ASSERT_TRUE(map_->GetVoiceSenderInfos(*local_audio_track_)); | |
295 EXPECT_EQ(*map_->GetVoiceSenderInfos(*local_audio_track_), | |
296 std::vector<cricket::VoiceSenderInfo*>({ | |
297 &voice_media_info_->senders[0], | |
298 &voice_media_info_->senders[1] })); | |
299 EXPECT_EQ(map_->GetAudioTrack(voice_media_info_->senders[0]), | |
300 local_audio_track_.get()); | |
301 EXPECT_EQ(map_->GetAudioTrack(voice_media_info_->senders[1]), | |
302 local_audio_track_.get()); | |
303 | |
304 // Local video track <-> RTP video senders | |
305 ASSERT_TRUE(map_->GetVideoSenderInfos(*local_video_track_)); | |
306 EXPECT_EQ(*map_->GetVideoSenderInfos(*local_video_track_), | |
307 std::vector<cricket::VideoSenderInfo*>({ | |
308 &video_media_info_->senders[0], | |
309 &video_media_info_->senders[1] })); | |
310 EXPECT_EQ(map_->GetVideoTrack(video_media_info_->senders[0]), | |
311 local_video_track_.get()); | |
312 EXPECT_EQ(map_->GetVideoTrack(video_media_info_->senders[1]), | |
313 local_video_track_.get()); | |
314 } | |
315 | |
316 TEST_F(TrackMediaInfoMapTest, MultipleMultiSsrcSendersPerTrack) { | |
317 AddRtpSenderWithSsrcs({ 1, 2 }, local_audio_track_); | |
318 AddRtpSenderWithSsrcs({ 3, 4 }, local_audio_track_); | |
319 AddRtpSenderWithSsrcs({ 5, 6 }, local_video_track_); | |
320 AddRtpSenderWithSsrcs({ 7, 8 }, local_video_track_); | |
321 CreateMap(); | |
322 | |
323 // Local audio track <-> RTP audio senders | |
324 ASSERT_TRUE(map_->GetVoiceSenderInfos(*local_audio_track_)); | |
325 EXPECT_EQ(*map_->GetVoiceSenderInfos(*local_audio_track_), | |
326 std::vector<cricket::VoiceSenderInfo*>({ | |
327 &voice_media_info_->senders[0], | |
328 &voice_media_info_->senders[1] })); | |
329 EXPECT_EQ(map_->GetAudioTrack(voice_media_info_->senders[0]), | |
330 local_audio_track_.get()); | |
331 EXPECT_EQ(map_->GetAudioTrack(voice_media_info_->senders[1]), | |
332 local_audio_track_.get()); | |
333 | |
334 // Local video track <-> RTP video senders | |
335 ASSERT_TRUE(map_->GetVideoSenderInfos(*local_video_track_)); | |
336 EXPECT_EQ(*map_->GetVideoSenderInfos(*local_video_track_), | |
337 std::vector<cricket::VideoSenderInfo*>({ | |
338 &video_media_info_->senders[0], | |
339 &video_media_info_->senders[1] })); | |
340 EXPECT_EQ(map_->GetVideoTrack(video_media_info_->senders[0]), | |
341 local_video_track_.get()); | |
342 EXPECT_EQ(map_->GetVideoTrack(video_media_info_->senders[1]), | |
343 local_video_track_.get()); | |
344 } | |
345 | |
346 // Death tests. | |
347 // Disabled on Android because death tests misbehave on Android, see | |
348 // base/test/gtest_util.h. | |
349 #if RTC_DCHECK_IS_ON && GTEST_HAS_DEATH_TEST && !defined(WEBRTC_ANDROID) | |
350 | |
351 class TrackMediaInfoMapDeathTest : public TrackMediaInfoMapTest { | |
352 }; | |
353 | |
354 TEST_F(TrackMediaInfoMapDeathTest, MultipleOneSsrcReceiversPerTrack) { | |
355 AddRtpReceiverWithSsrcs({ 1 }, remote_audio_track_); | |
356 AddRtpReceiverWithSsrcs({ 2 }, remote_audio_track_); | |
357 AddRtpReceiverWithSsrcs({ 3 }, remote_video_track_); | |
358 AddRtpReceiverWithSsrcs({ 4 }, remote_video_track_); | |
359 EXPECT_DEATH(CreateMap(), ""); | |
360 } | |
361 | |
362 TEST_F(TrackMediaInfoMapDeathTest, MultipleMultiSsrcReceiversPerTrack) { | |
363 AddRtpReceiverWithSsrcs({ 1, 2 }, remote_audio_track_); | |
364 AddRtpReceiverWithSsrcs({ 3, 4 }, remote_audio_track_); | |
365 AddRtpReceiverWithSsrcs({ 5, 6 }, remote_video_track_); | |
366 AddRtpReceiverWithSsrcs({ 7, 8 }, remote_video_track_); | |
367 EXPECT_DEATH(CreateMap(), ""); | |
368 } | |
369 | |
370 TEST_F(TrackMediaInfoMapDeathTest, | |
371 SingleSenderReceiverPerTrackWithSsrcNotUnique) { | |
372 AddRtpSenderWithSsrcs({ 1 }, local_audio_track_); | |
373 AddRtpReceiverWithSsrcs({ 1 }, remote_audio_track_); | |
374 AddRtpSenderWithSsrcs({ 2 }, local_video_track_); | |
375 AddRtpReceiverWithSsrcs({ 2 }, remote_video_track_); | |
376 EXPECT_DEATH(CreateMap(), ""); | |
377 } | |
378 | |
379 #endif // RTC_DCHECK_IS_ON && GTEST_HAS_DEATH_TEST && !defined(WEBRTC_ANDROID) | |
380 | |
381 } // namespace webrtc | |
OLD | NEW |