OLD | NEW |
1 /* | 1 /* |
2 * Copyright (c) 2013 The WebRTC project authors. All Rights Reserved. | 2 * Copyright (c) 2013 The WebRTC project authors. All Rights Reserved. |
3 * | 3 * |
4 * Use of this source code is governed by a BSD-style license | 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 | 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 | 6 * tree. An additional intellectual property rights grant can be found |
7 * in the file PATENTS. All contributing project authors may | 7 * in the file PATENTS. All contributing project authors may |
8 * be found in the AUTHORS file in the root of the source tree. | 8 * be found in the AUTHORS file in the root of the source tree. |
9 */ | 9 */ |
10 | 10 |
(...skipping 17 matching lines...) Expand all Loading... |
28 | 28 |
29 const int kVideoNackListSize = 30; | 29 const int kVideoNackListSize = 30; |
30 const uint32_t kTestSsrc = 3456; | 30 const uint32_t kTestSsrc = 3456; |
31 const uint16_t kTestSequenceNumber = 2345; | 31 const uint16_t kTestSequenceNumber = 2345; |
32 const uint32_t kTestNumberOfPackets = 1350; | 32 const uint32_t kTestNumberOfPackets = 1350; |
33 const int kTestNumberOfRtxPackets = 149; | 33 const int kTestNumberOfRtxPackets = 149; |
34 const int kNumFrames = 30; | 34 const int kNumFrames = 30; |
35 const int kPayloadType = 123; | 35 const int kPayloadType = 123; |
36 const int kRtxPayloadType = 98; | 36 const int kRtxPayloadType = 98; |
37 | 37 |
38 class VerifyingRtxReceiver : public NullRtpData | 38 class VerifyingRtxReceiver : public NullRtpData { |
39 { | |
40 public: | 39 public: |
41 VerifyingRtxReceiver() {} | 40 VerifyingRtxReceiver() {} |
42 | 41 |
43 int32_t OnReceivedPayloadData( | 42 int32_t OnReceivedPayloadData( |
44 const uint8_t* data, | 43 const uint8_t* data, |
45 const size_t size, | 44 const size_t size, |
46 const webrtc::WebRtcRTPHeader* rtp_header) override { | 45 const webrtc::WebRtcRTPHeader* rtp_header) override { |
47 if (!sequence_numbers_.empty()) | 46 if (!sequence_numbers_.empty()) |
48 EXPECT_EQ(kTestSsrc, rtp_header->header.ssrc); | 47 EXPECT_EQ(kTestSsrc, rtp_header->header.ssrc); |
49 sequence_numbers_.push_back(rtp_header->header.sequenceNumber); | 48 sequence_numbers_.push_back(rtp_header->header.sequenceNumber); |
(...skipping 29 matching lines...) Expand all Loading... |
79 module_(NULL) {} | 78 module_(NULL) {} |
80 | 79 |
81 void SetSendModule(RtpRtcp* rtpRtcpModule, | 80 void SetSendModule(RtpRtcp* rtpRtcpModule, |
82 RTPPayloadRegistry* rtp_payload_registry, | 81 RTPPayloadRegistry* rtp_payload_registry, |
83 RtpReceiver* receiver) { | 82 RtpReceiver* receiver) { |
84 module_ = rtpRtcpModule; | 83 module_ = rtpRtcpModule; |
85 rtp_payload_registry_ = rtp_payload_registry; | 84 rtp_payload_registry_ = rtp_payload_registry; |
86 rtp_receiver_ = receiver; | 85 rtp_receiver_ = receiver; |
87 } | 86 } |
88 | 87 |
89 void DropEveryNthPacket(int n) { | 88 void DropEveryNthPacket(int n) { packet_loss_ = n; } |
90 packet_loss_ = n; | |
91 } | |
92 | 89 |
93 void DropConsecutivePackets(int start, int total) { | 90 void DropConsecutivePackets(int start, int total) { |
94 consecutive_drop_start_ = start; | 91 consecutive_drop_start_ = start; |
95 consecutive_drop_end_ = start + total; | 92 consecutive_drop_end_ = start + total; |
96 packet_loss_ = 0; | 93 packet_loss_ = 0; |
97 } | 94 } |
98 | 95 |
99 bool SendRtp(const uint8_t* data, | 96 bool SendRtp(const uint8_t* data, |
100 size_t len, | 97 size_t len, |
101 const PacketOptions& options) override { | 98 const PacketOptions& options) override { |
102 count_++; | 99 count_++; |
103 const unsigned char* ptr = static_cast<const unsigned char*>(data); | 100 const unsigned char* ptr = static_cast<const unsigned char*>(data); |
104 uint32_t ssrc = (ptr[8] << 24) + (ptr[9] << 16) + (ptr[10] << 8) + ptr[11]; | 101 uint32_t ssrc = (ptr[8] << 24) + (ptr[9] << 16) + (ptr[10] << 8) + ptr[11]; |
105 if (ssrc == rtx_ssrc_) count_rtx_ssrc_++; | 102 if (ssrc == rtx_ssrc_) |
| 103 count_rtx_ssrc_++; |
106 uint16_t sequence_number = (ptr[2] << 8) + ptr[3]; | 104 uint16_t sequence_number = (ptr[2] << 8) + ptr[3]; |
107 size_t packet_length = len; | 105 size_t packet_length = len; |
108 uint8_t restored_packet[1500]; | 106 uint8_t restored_packet[1500]; |
109 RTPHeader header; | 107 RTPHeader header; |
110 rtc::scoped_ptr<RtpHeaderParser> parser(RtpHeaderParser::Create()); | 108 rtc::scoped_ptr<RtpHeaderParser> parser(RtpHeaderParser::Create()); |
111 if (!parser->Parse(ptr, len, &header)) { | 109 if (!parser->Parse(ptr, len, &header)) { |
112 return false; | 110 return false; |
113 } | 111 } |
114 | 112 |
115 if (!rtp_payload_registry_->IsRtx(header)) { | 113 if (!rtp_payload_registry_->IsRtx(header)) { |
(...skipping 66 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
182 configuration.audio = false; | 180 configuration.audio = false; |
183 configuration.clock = &fake_clock; | 181 configuration.clock = &fake_clock; |
184 receive_statistics_.reset(ReceiveStatistics::Create(&fake_clock)); | 182 receive_statistics_.reset(ReceiveStatistics::Create(&fake_clock)); |
185 configuration.receive_statistics = receive_statistics_.get(); | 183 configuration.receive_statistics = receive_statistics_.get(); |
186 configuration.outgoing_transport = &transport_; | 184 configuration.outgoing_transport = &transport_; |
187 rtp_rtcp_module_ = RtpRtcp::CreateRtpRtcp(configuration); | 185 rtp_rtcp_module_ = RtpRtcp::CreateRtpRtcp(configuration); |
188 | 186 |
189 rtp_feedback_.reset(new TestRtpFeedback(rtp_rtcp_module_)); | 187 rtp_feedback_.reset(new TestRtpFeedback(rtp_rtcp_module_)); |
190 | 188 |
191 rtp_receiver_.reset(RtpReceiver::CreateVideoReceiver( | 189 rtp_receiver_.reset(RtpReceiver::CreateVideoReceiver( |
192 &fake_clock, &receiver_, rtp_feedback_.get(), | 190 &fake_clock, &receiver_, rtp_feedback_.get(), &rtp_payload_registry_)); |
193 &rtp_payload_registry_)); | |
194 | 191 |
195 rtp_rtcp_module_->SetSSRC(kTestSsrc); | 192 rtp_rtcp_module_->SetSSRC(kTestSsrc); |
196 rtp_rtcp_module_->SetRTCPStatus(RtcpMode::kCompound); | 193 rtp_rtcp_module_->SetRTCPStatus(RtcpMode::kCompound); |
197 rtp_receiver_->SetNACKStatus(kNackRtcp); | 194 rtp_receiver_->SetNACKStatus(kNackRtcp); |
198 rtp_rtcp_module_->SetStorePacketsStatus(true, 600); | 195 rtp_rtcp_module_->SetStorePacketsStatus(true, 600); |
199 EXPECT_EQ(0, rtp_rtcp_module_->SetSendingStatus(true)); | 196 EXPECT_EQ(0, rtp_rtcp_module_->SetSendingStatus(true)); |
200 rtp_rtcp_module_->SetSequenceNumber(kTestSequenceNumber); | 197 rtp_rtcp_module_->SetSequenceNumber(kTestSequenceNumber); |
201 rtp_rtcp_module_->SetStartTimestamp(111111); | 198 rtp_rtcp_module_->SetStartTimestamp(111111); |
202 | 199 |
203 transport_.SetSendModule(rtp_rtcp_module_, &rtp_payload_registry_, | 200 transport_.SetSendModule(rtp_rtcp_module_, &rtp_payload_registry_, |
204 rtp_receiver_.get()); | 201 rtp_receiver_.get()); |
205 | 202 |
206 VideoCodec video_codec; | 203 VideoCodec video_codec; |
207 memset(&video_codec, 0, sizeof(video_codec)); | 204 memset(&video_codec, 0, sizeof(video_codec)); |
208 video_codec.plType = kPayloadType; | 205 video_codec.plType = kPayloadType; |
209 memcpy(video_codec.plName, "I420", 5); | 206 memcpy(video_codec.plName, "I420", 5); |
210 | 207 |
211 EXPECT_EQ(0, rtp_rtcp_module_->RegisterSendPayload(video_codec)); | 208 EXPECT_EQ(0, rtp_rtcp_module_->RegisterSendPayload(video_codec)); |
212 rtp_rtcp_module_->SetRtxSendPayloadType(kRtxPayloadType, kPayloadType); | 209 rtp_rtcp_module_->SetRtxSendPayloadType(kRtxPayloadType, kPayloadType); |
213 EXPECT_EQ(0, rtp_receiver_->RegisterReceivePayload(video_codec.plName, | 210 EXPECT_EQ(0, rtp_receiver_->RegisterReceivePayload( |
214 video_codec.plType, | 211 video_codec.plName, video_codec.plType, 90000, 0, |
215 90000, | 212 video_codec.maxBitrate)); |
216 0, | |
217 video_codec.maxBitrate)); | |
218 rtp_payload_registry_.SetRtxPayloadType(kRtxPayloadType, kPayloadType); | 213 rtp_payload_registry_.SetRtxPayloadType(kRtxPayloadType, kPayloadType); |
219 | 214 |
220 for (size_t n = 0; n < payload_data_length; n++) { | 215 for (size_t n = 0; n < payload_data_length; n++) { |
221 payload_data[n] = n % 10; | 216 payload_data[n] = n % 10; |
222 } | 217 } |
223 } | 218 } |
224 | 219 |
225 int BuildNackList(uint16_t* nack_list) { | 220 int BuildNackList(uint16_t* nack_list) { |
226 receiver_.sequence_numbers_.sort(); | 221 receiver_.sequence_numbers_.sort(); |
227 std::list<uint16_t> missing_sequence_numbers; | 222 std::list<uint16_t> missing_sequence_numbers; |
228 std::list<uint16_t>::iterator it = | 223 std::list<uint16_t>::iterator it = receiver_.sequence_numbers_.begin(); |
229 receiver_.sequence_numbers_.begin(); | |
230 | 224 |
231 while (it != receiver_.sequence_numbers_.end()) { | 225 while (it != receiver_.sequence_numbers_.end()) { |
232 uint16_t sequence_number_1 = *it; | 226 uint16_t sequence_number_1 = *it; |
233 ++it; | 227 ++it; |
234 if (it != receiver_.sequence_numbers_.end()) { | 228 if (it != receiver_.sequence_numbers_.end()) { |
235 uint16_t sequence_number_2 = *it; | 229 uint16_t sequence_number_2 = *it; |
236 // Add all missing sequence numbers to list | 230 // Add all missing sequence numbers to list |
237 for (uint16_t i = sequence_number_1 + 1; i < sequence_number_2; | 231 for (uint16_t i = sequence_number_1 + 1; i < sequence_number_2; ++i) { |
238 ++i) { | |
239 missing_sequence_numbers.push_back(i); | 232 missing_sequence_numbers.push_back(i); |
240 } | 233 } |
241 } | 234 } |
242 } | 235 } |
243 int n = 0; | 236 int n = 0; |
244 for (it = missing_sequence_numbers.begin(); | 237 for (it = missing_sequence_numbers.begin(); |
245 it != missing_sequence_numbers.end(); ++it) { | 238 it != missing_sequence_numbers.end(); ++it) { |
246 nack_list[n++] = (*it); | 239 nack_list[n++] = (*it); |
247 } | 240 } |
248 return n; | 241 return n; |
249 } | 242 } |
250 | 243 |
251 bool ExpectedPacketsReceived() { | 244 bool ExpectedPacketsReceived() { |
252 std::list<uint16_t> received_sorted; | 245 std::list<uint16_t> received_sorted; |
253 std::copy(receiver_.sequence_numbers_.begin(), | 246 std::copy(receiver_.sequence_numbers_.begin(), |
254 receiver_.sequence_numbers_.end(), | 247 receiver_.sequence_numbers_.end(), |
255 std::back_inserter(received_sorted)); | 248 std::back_inserter(received_sorted)); |
(...skipping 30 matching lines...) Expand all Loading... |
286 | 279 |
287 void TearDown() override { delete rtp_rtcp_module_; } | 280 void TearDown() override { delete rtp_rtcp_module_; } |
288 | 281 |
289 rtc::scoped_ptr<ReceiveStatistics> receive_statistics_; | 282 rtc::scoped_ptr<ReceiveStatistics> receive_statistics_; |
290 RTPPayloadRegistry rtp_payload_registry_; | 283 RTPPayloadRegistry rtp_payload_registry_; |
291 rtc::scoped_ptr<RtpReceiver> rtp_receiver_; | 284 rtc::scoped_ptr<RtpReceiver> rtp_receiver_; |
292 RtpRtcp* rtp_rtcp_module_; | 285 RtpRtcp* rtp_rtcp_module_; |
293 rtc::scoped_ptr<TestRtpFeedback> rtp_feedback_; | 286 rtc::scoped_ptr<TestRtpFeedback> rtp_feedback_; |
294 RtxLoopBackTransport transport_; | 287 RtxLoopBackTransport transport_; |
295 VerifyingRtxReceiver receiver_; | 288 VerifyingRtxReceiver receiver_; |
296 uint8_t payload_data[65000]; | 289 uint8_t payload_data[65000]; |
297 size_t payload_data_length; | 290 size_t payload_data_length; |
298 SimulatedClock fake_clock; | 291 SimulatedClock fake_clock; |
299 }; | 292 }; |
300 | 293 |
301 TEST_F(RtpRtcpRtxNackTest, LongNackList) { | 294 TEST_F(RtpRtcpRtxNackTest, LongNackList) { |
302 const int kNumPacketsToDrop = 900; | 295 const int kNumPacketsToDrop = 900; |
303 const int kNumRequiredRtcp = 4; | 296 const int kNumRequiredRtcp = 4; |
304 uint32_t timestamp = 3000; | 297 uint32_t timestamp = 3000; |
305 uint16_t nack_list[kNumPacketsToDrop]; | 298 uint16_t nack_list[kNumPacketsToDrop]; |
306 // Disable StorePackets to be able to set a larger packet history. | 299 // Disable StorePackets to be able to set a larger packet history. |
(...skipping 26 matching lines...) Expand all Loading... |
333 } | 326 } |
334 rtp_rtcp_module_->SendNACK(nack_list, length); | 327 rtp_rtcp_module_->SendNACK(nack_list, length); |
335 EXPECT_GT(receiver_.sequence_numbers_.size(), last_receive_count); | 328 EXPECT_GT(receiver_.sequence_numbers_.size(), last_receive_count); |
336 EXPECT_TRUE(ExpectedPacketsReceived()); | 329 EXPECT_TRUE(ExpectedPacketsReceived()); |
337 } | 330 } |
338 | 331 |
339 TEST_F(RtpRtcpRtxNackTest, RtxNack) { | 332 TEST_F(RtpRtcpRtxNackTest, RtxNack) { |
340 RunRtxTest(kRtxRetransmitted, 10); | 333 RunRtxTest(kRtxRetransmitted, 10); |
341 EXPECT_EQ(kTestSequenceNumber, *(receiver_.sequence_numbers_.begin())); | 334 EXPECT_EQ(kTestSequenceNumber, *(receiver_.sequence_numbers_.begin())); |
342 EXPECT_EQ(kTestSequenceNumber + kTestNumberOfPackets - 1, | 335 EXPECT_EQ(kTestSequenceNumber + kTestNumberOfPackets - 1, |
343 *(receiver_.sequence_numbers_.rbegin())); | 336 *(receiver_.sequence_numbers_.rbegin())); |
344 EXPECT_EQ(kTestNumberOfPackets, receiver_.sequence_numbers_.size()); | 337 EXPECT_EQ(kTestNumberOfPackets, receiver_.sequence_numbers_.size()); |
345 EXPECT_EQ(kTestNumberOfRtxPackets, transport_.count_rtx_ssrc_); | 338 EXPECT_EQ(kTestNumberOfRtxPackets, transport_.count_rtx_ssrc_); |
346 EXPECT_TRUE(ExpectedPacketsReceived()); | 339 EXPECT_TRUE(ExpectedPacketsReceived()); |
347 } | 340 } |
OLD | NEW |