Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(358)

Side by Side Diff: webrtc/modules/rtp_rtcp/source/rtp_rtcp_impl_unittest.cc

Issue 2960363002: Implement RTP keepalive in native stack. (Closed)
Patch Set: Cleanup Created 3 years, 5 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
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 35 matching lines...) Expand 10 before | Expand all | Expand 10 after
46 46
47 void OnRttUpdate(int64_t rtt_ms) override { rtt_ms_ = rtt_ms; } 47 void OnRttUpdate(int64_t rtt_ms) override { rtt_ms_ = rtt_ms; }
48 int64_t LastProcessedRtt() const override { return rtt_ms_; } 48 int64_t LastProcessedRtt() const override { return rtt_ms_; }
49 int64_t rtt_ms_; 49 int64_t rtt_ms_;
50 }; 50 };
51 51
52 class SendTransport : public Transport, 52 class SendTransport : public Transport,
53 public RtpData { 53 public RtpData {
54 public: 54 public:
55 SendTransport() 55 SendTransport()
56 : receiver_(NULL), 56 : receiver_(nullptr),
57 clock_(NULL), 57 clock_(nullptr),
58 delay_ms_(0), 58 delay_ms_(0),
59 rtp_packets_sent_(0) { 59 rtp_packets_sent_(0),
60 } 60 keepalive_payload_type_(0),
61 num_keepalive_sent_(0) {}
61 62
62 void SetRtpRtcpModule(ModuleRtpRtcpImpl* receiver) { 63 void SetRtpRtcpModule(ModuleRtpRtcpImpl* receiver) {
63 receiver_ = receiver; 64 receiver_ = receiver;
64 } 65 }
65 void SimulateNetworkDelay(int64_t delay_ms, SimulatedClock* clock) { 66 void SimulateNetworkDelay(int64_t delay_ms, SimulatedClock* clock) {
66 clock_ = clock; 67 clock_ = clock;
67 delay_ms_ = delay_ms; 68 delay_ms_ = delay_ms;
68 } 69 }
69 bool SendRtp(const uint8_t* data, 70 bool SendRtp(const uint8_t* data,
70 size_t len, 71 size_t len,
71 const PacketOptions& options) override { 72 const PacketOptions& options) override {
72 RTPHeader header; 73 RTPHeader header;
73 std::unique_ptr<RtpHeaderParser> parser(RtpHeaderParser::Create()); 74 std::unique_ptr<RtpHeaderParser> parser(RtpHeaderParser::Create());
74 EXPECT_TRUE(parser->Parse(static_cast<const uint8_t*>(data), len, &header)); 75 EXPECT_TRUE(parser->Parse(static_cast<const uint8_t*>(data), len, &header));
75 ++rtp_packets_sent_; 76 ++rtp_packets_sent_;
77 if (header.payloadType == keepalive_payload_type_)
78 ++num_keepalive_sent_;
76 last_rtp_header_ = header; 79 last_rtp_header_ = header;
77 return true; 80 return true;
78 } 81 }
79 bool SendRtcp(const uint8_t* data, size_t len) override { 82 bool SendRtcp(const uint8_t* data, size_t len) override {
80 test::RtcpPacketParser parser; 83 test::RtcpPacketParser parser;
81 parser.Parse(data, len); 84 parser.Parse(data, len);
82 last_nack_list_ = parser.nack()->packet_ids(); 85 last_nack_list_ = parser.nack()->packet_ids();
83 86
84 if (clock_) { 87 if (clock_) {
85 clock_->AdvanceTimeMilliseconds(delay_ms_); 88 clock_->AdvanceTimeMilliseconds(delay_ms_);
86 } 89 }
87 EXPECT_TRUE(receiver_); 90 EXPECT_TRUE(receiver_);
88 EXPECT_EQ(0, receiver_->IncomingRtcpPacket(data, len)); 91 EXPECT_EQ(0, receiver_->IncomingRtcpPacket(data, len));
89 return true; 92 return true;
90 } 93 }
91 int32_t OnReceivedPayloadData(const uint8_t* payload_data, 94 int32_t OnReceivedPayloadData(const uint8_t* payload_data,
92 size_t payload_size, 95 size_t payload_size,
93 const WebRtcRTPHeader* rtp_header) override { 96 const WebRtcRTPHeader* rtp_header) override {
94 return 0; 97 return 0;
95 } 98 }
99 void SetKeepalivePayloadType(uint8_t payload_type) {
100 keepalive_payload_type_ = payload_type;
101 }
102 size_t NumKeepaliveSent() { return num_keepalive_sent_; }
96 ModuleRtpRtcpImpl* receiver_; 103 ModuleRtpRtcpImpl* receiver_;
97 SimulatedClock* clock_; 104 SimulatedClock* clock_;
98 int64_t delay_ms_; 105 int64_t delay_ms_;
99 int rtp_packets_sent_; 106 int rtp_packets_sent_;
100 RTPHeader last_rtp_header_; 107 RTPHeader last_rtp_header_;
101 std::vector<uint16_t> last_nack_list_; 108 std::vector<uint16_t> last_nack_list_;
109 uint8_t keepalive_payload_type_;
110 size_t num_keepalive_sent_;
102 }; 111 };
103 112
104 class RtpRtcpModule : public RtcpPacketTypeCounterObserver { 113 class RtpRtcpModule : public RtcpPacketTypeCounterObserver {
105 public: 114 public:
106 explicit RtpRtcpModule(SimulatedClock* clock) 115 explicit RtpRtcpModule(SimulatedClock* clock)
107 : receive_statistics_(ReceiveStatistics::Create(clock)), 116 : receive_statistics_(ReceiveStatistics::Create(clock)),
108 remote_ssrc_(0), 117 remote_ssrc_(0),
109 retransmission_rate_limiter_(clock, kMaxRttMs) { 118 retransmission_rate_limiter_(clock, kMaxRttMs),
110 RtpRtcp::Configuration config; 119 clock_(clock) {
111 config.audio = false; 120 CreateModuleImpl();
112 config.clock = clock;
113 config.outgoing_transport = &transport_;
114 config.receive_statistics = receive_statistics_.get();
115 config.rtcp_packet_type_counter_observer = this;
116 config.rtt_stats = &rtt_stats_;
117 config.retransmission_rate_limiter = &retransmission_rate_limiter_;
118
119 impl_.reset(new ModuleRtpRtcpImpl(config));
120 impl_->SetRTCPStatus(RtcpMode::kCompound);
121
122 transport_.SimulateNetworkDelay(kOneWayNetworkDelayMs, clock); 121 transport_.SimulateNetworkDelay(kOneWayNetworkDelayMs, clock);
123 } 122 }
124 123
125 RtcpPacketTypeCounter packets_sent_; 124 RtcpPacketTypeCounter packets_sent_;
126 RtcpPacketTypeCounter packets_received_; 125 RtcpPacketTypeCounter packets_received_;
127 std::unique_ptr<ReceiveStatistics> receive_statistics_; 126 std::unique_ptr<ReceiveStatistics> receive_statistics_;
128 SendTransport transport_; 127 SendTransport transport_;
129 RtcpRttStatsTestImpl rtt_stats_; 128 RtcpRttStatsTestImpl rtt_stats_;
130 std::unique_ptr<ModuleRtpRtcpImpl> impl_; 129 std::unique_ptr<ModuleRtpRtcpImpl> impl_;
131 uint32_t remote_ssrc_; 130 uint32_t remote_ssrc_;
132 RateLimiter retransmission_rate_limiter_; 131 RateLimiter retransmission_rate_limiter_;
132 RtpKeepAliveConfig keepalive_config_;
133 133
134 void SetRemoteSsrc(uint32_t ssrc) { 134 void SetRemoteSsrc(uint32_t ssrc) {
135 remote_ssrc_ = ssrc; 135 remote_ssrc_ = ssrc;
136 impl_->SetRemoteSSRC(ssrc); 136 impl_->SetRemoteSSRC(ssrc);
137 } 137 }
138 138
139 void RtcpPacketTypesCounterUpdated( 139 void RtcpPacketTypesCounterUpdated(
140 uint32_t ssrc, 140 uint32_t ssrc,
141 const RtcpPacketTypeCounter& packet_counter) override { 141 const RtcpPacketTypeCounter& packet_counter) override {
142 counter_map_[ssrc] = packet_counter; 142 counter_map_[ssrc] = packet_counter;
(...skipping 10 matching lines...) Expand all
153 } 153 }
154 int RtpSent() { 154 int RtpSent() {
155 return transport_.rtp_packets_sent_; 155 return transport_.rtp_packets_sent_;
156 } 156 }
157 uint16_t LastRtpSequenceNumber() { 157 uint16_t LastRtpSequenceNumber() {
158 return transport_.last_rtp_header_.sequenceNumber; 158 return transport_.last_rtp_header_.sequenceNumber;
159 } 159 }
160 std::vector<uint16_t> LastNackListSent() { 160 std::vector<uint16_t> LastNackListSent() {
161 return transport_.last_nack_list_; 161 return transport_.last_nack_list_;
162 } 162 }
163 void SetKeepaliveConfigAndReset(const RtpKeepAliveConfig& config) {
164 keepalive_config_ = config;
165 // Need to create a new module impl, since it's configured at creation.
166 CreateModuleImpl();
167 transport_.SetKeepalivePayloadType(config.payload_type);
168 }
163 169
164 private: 170 private:
171 void CreateModuleImpl() {
172 RtpRtcp::Configuration config;
173 config.audio = false;
174 config.clock = clock_;
175 config.outgoing_transport = &transport_;
176 config.receive_statistics = receive_statistics_.get();
177 config.rtcp_packet_type_counter_observer = this;
178 config.rtt_stats = &rtt_stats_;
179 config.retransmission_rate_limiter = &retransmission_rate_limiter_;
180 config.keepalive_config = keepalive_config_;
181
182 impl_.reset(new ModuleRtpRtcpImpl(config));
183 impl_->SetRTCPStatus(RtcpMode::kCompound);
184 }
185
186 SimulatedClock* const clock_;
165 std::map<uint32_t, RtcpPacketTypeCounter> counter_map_; 187 std::map<uint32_t, RtcpPacketTypeCounter> counter_map_;
166 }; 188 };
167 } // namespace 189 } // namespace
168 190
169 class RtpRtcpImplTest : public ::testing::Test { 191 class RtpRtcpImplTest : public ::testing::Test {
170 protected: 192 protected:
171 RtpRtcpImplTest() 193 RtpRtcpImplTest()
172 : clock_(133590000000000), 194 : clock_(133590000000000), sender_(&clock_), receiver_(&clock_) {}
173 sender_(&clock_), 195
174 receiver_(&clock_) { 196 void SetUp() override {
175 // Send module. 197 // Send module.
176 sender_.impl_->SetSSRC(kSenderSsrc); 198 sender_.impl_->SetSSRC(kSenderSsrc);
177 EXPECT_EQ(0, sender_.impl_->SetSendingStatus(true)); 199 EXPECT_EQ(0, sender_.impl_->SetSendingStatus(true));
178 sender_.impl_->SetSendingMediaStatus(true); 200 sender_.impl_->SetSendingMediaStatus(true);
179 sender_.SetRemoteSsrc(kReceiverSsrc); 201 sender_.SetRemoteSsrc(kReceiverSsrc);
180 sender_.impl_->SetSequenceNumber(kSequenceNumber); 202 sender_.impl_->SetSequenceNumber(kSequenceNumber);
181 sender_.impl_->SetStorePacketsStatus(true, 100); 203 sender_.impl_->SetStorePacketsStatus(true, 100);
182 204
183 memset(&codec_, 0, sizeof(VideoCodec)); 205 memset(&codec_, 0, sizeof(VideoCodec));
184 codec_.plType = 100; 206 codec_.plType = 100;
185 strncpy(codec_.plName, "VP8", 3); 207 strncpy(codec_.plName, "VP8", 3);
186 codec_.width = 320; 208 codec_.width = 320;
187 codec_.height = 180; 209 codec_.height = 180;
188 EXPECT_EQ(0, sender_.impl_->RegisterSendPayload(codec_)); 210 EXPECT_EQ(0, sender_.impl_->RegisterSendPayload(codec_));
189 211
190 // Receive module. 212 // Receive module.
191 EXPECT_EQ(0, receiver_.impl_->SetSendingStatus(false)); 213 EXPECT_EQ(0, receiver_.impl_->SetSendingStatus(false));
192 receiver_.impl_->SetSendingMediaStatus(false); 214 receiver_.impl_->SetSendingMediaStatus(false);
193 receiver_.impl_->SetSSRC(kReceiverSsrc); 215 receiver_.impl_->SetSSRC(kReceiverSsrc);
194 receiver_.SetRemoteSsrc(kSenderSsrc); 216 receiver_.SetRemoteSsrc(kSenderSsrc);
195 // Transport settings. 217 // Transport settings.
196 sender_.transport_.SetRtpRtcpModule(receiver_.impl_.get()); 218 sender_.transport_.SetRtpRtcpModule(receiver_.impl_.get());
197 receiver_.transport_.SetRtpRtcpModule(sender_.impl_.get()); 219 receiver_.transport_.SetRtpRtcpModule(sender_.impl_.get());
198 } 220 }
221
199 SimulatedClock clock_; 222 SimulatedClock clock_;
200 RtpRtcpModule sender_; 223 RtpRtcpModule sender_;
201 RtpRtcpModule receiver_; 224 RtpRtcpModule receiver_;
202 VideoCodec codec_; 225 VideoCodec codec_;
203 226
204 void SendFrame(const RtpRtcpModule* module, uint8_t tid) { 227 void SendFrame(const RtpRtcpModule* module, uint8_t tid) {
205 RTPVideoHeaderVP8 vp8_header = {}; 228 RTPVideoHeaderVP8 vp8_header = {};
206 vp8_header.temporalIdx = tid; 229 vp8_header.temporalIdx = tid;
207 RTPVideoHeader rtp_video_header; 230 RTPVideoHeader rtp_video_header;
208 rtp_video_header.width = codec_.width; 231 rtp_video_header.width = codec_.width;
(...skipping 351 matching lines...) Expand 10 before | Expand all | Expand 10 after
560 EXPECT_EQ(8U, receiver_.RtcpSent().nack_requests); 583 EXPECT_EQ(8U, receiver_.RtcpSent().nack_requests);
561 EXPECT_EQ(6U, receiver_.RtcpSent().unique_nack_requests); 584 EXPECT_EQ(6U, receiver_.RtcpSent().unique_nack_requests);
562 EXPECT_THAT(receiver_.LastNackListSent(), ElementsAre(11, 18, 20, 21)); 585 EXPECT_THAT(receiver_.LastNackListSent(), ElementsAre(11, 18, 20, 21));
563 586
564 // Send module receives the request. 587 // Send module receives the request.
565 EXPECT_EQ(2U, sender_.RtcpReceived().nack_packets); 588 EXPECT_EQ(2U, sender_.RtcpReceived().nack_packets);
566 EXPECT_EQ(8U, sender_.RtcpReceived().nack_requests); 589 EXPECT_EQ(8U, sender_.RtcpReceived().nack_requests);
567 EXPECT_EQ(6U, sender_.RtcpReceived().unique_nack_requests); 590 EXPECT_EQ(6U, sender_.RtcpReceived().unique_nack_requests);
568 EXPECT_EQ(75, sender_.RtcpReceived().UniqueNackRequestsInPercent()); 591 EXPECT_EQ(75, sender_.RtcpReceived().UniqueNackRequestsInPercent());
569 } 592 }
593
594 TEST_F(RtpRtcpImplTest, SendsKeepaliveAfterTimout) {
595 const int kTimeoutMs = 1500;
596
597 RtpKeepAliveConfig config;
598 config.timeout_interval_ms = kTimeoutMs;
599
600 // Recreate sender impl with new configuration, and redo setup.
601 sender_.SetKeepaliveConfigAndReset(config);
602 SetUp();
603
604 // Initial process call.
605 sender_.impl_->Process();
606 EXPECT_EQ(0U, sender_.transport_.NumKeepaliveSent());
607
608 // After one time, a single keep-alive packet should be sent.
609 clock_.AdvanceTimeMilliseconds(kTimeoutMs);
610 sender_.impl_->Process();
611 EXPECT_EQ(1U, sender_.transport_.NumKeepaliveSent());
612
613 // Process for the same timestamp again, no new packet should be sent.
614 sender_.impl_->Process();
615 EXPECT_EQ(1U, sender_.transport_.NumKeepaliveSent());
616
617 // Move ahead to the last ms before a keep-alive is expected, no action.
618 clock_.AdvanceTimeMilliseconds(kTimeoutMs - 1);
619 sender_.impl_->Process();
620 EXPECT_EQ(1U, sender_.transport_.NumKeepaliveSent());
621
622 // Move the final ms, timeout relative last KA. Should create new keep-alive.
623 clock_.AdvanceTimeMilliseconds(1);
624 sender_.impl_->Process();
625 EXPECT_EQ(2U, sender_.transport_.NumKeepaliveSent());
626
627 // Move ahead to the last ms before Christmas.
628 clock_.AdvanceTimeMilliseconds(kTimeoutMs - 1);
629 sender_.impl_->Process();
630 EXPECT_EQ(2U, sender_.transport_.NumKeepaliveSent());
631
632 // Send actual payload data, no keep-alive expected.
633 SendFrame(&sender_, 0);
634 sender_.impl_->Process();
635 EXPECT_EQ(2U, sender_.transport_.NumKeepaliveSent());
636
637 // Move ahead as far as possible again, timeout now relative payload. No KA.
638 clock_.AdvanceTimeMilliseconds(kTimeoutMs - 1);
639 sender_.impl_->Process();
640 EXPECT_EQ(2U, sender_.transport_.NumKeepaliveSent());
641
642 // Timeout relative payload, send new keep-alive.
643 clock_.AdvanceTimeMilliseconds(1);
644 sender_.impl_->Process();
645 EXPECT_EQ(3U, sender_.transport_.NumKeepaliveSent());
646 }
570 } // namespace webrtc 647 } // namespace webrtc
OLDNEW
« no previous file with comments | « webrtc/modules/rtp_rtcp/source/rtp_rtcp_impl.cc ('k') | webrtc/modules/rtp_rtcp/source/rtp_sender.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698