blob: 253ce32db00450c6baffffe46bf5d39c818bbce0 [file] [log] [blame]
danilchap1edb7ab2016-04-20 05:25:10 -07001/*
2 * Copyright (c) 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 */
Mirko Bonadei92ea95e2017-09-15 06:47:31 +020010#include "modules/rtp_rtcp/source/rtp_packet_received.h"
11#include "modules/rtp_rtcp/source/rtp_packet_to_send.h"
danilchap1edb7ab2016-04-20 05:25:10 -070012
Mirko Bonadei92ea95e2017-09-15 06:47:31 +020013#include "modules/rtp_rtcp/include/rtp_header_extension_map.h"
14#include "modules/rtp_rtcp/source/rtp_header_extensions.h"
15#include "rtc_base/random.h"
16#include "test/gmock.h"
17#include "test/gtest.h"
danilchap1edb7ab2016-04-20 05:25:10 -070018
danilchap1edb7ab2016-04-20 05:25:10 -070019namespace webrtc {
20namespace {
danilchapc547e842017-04-10 01:31:49 -070021using ::testing::ElementsAreArray;
22using ::testing::IsEmpty;
23using ::testing::make_tuple;
24
danilchap1edb7ab2016-04-20 05:25:10 -070025constexpr int8_t kPayloadType = 100;
26constexpr uint32_t kSsrc = 0x12345678;
eladalonae550e32017-05-24 08:28:13 -070027constexpr uint16_t kSeqNum = 0x1234;
28constexpr uint8_t kSeqNumFirstByte = kSeqNum >> 8;
29constexpr uint8_t kSeqNumSecondByte = kSeqNum & 0xff;
danilchap1edb7ab2016-04-20 05:25:10 -070030constexpr uint32_t kTimestamp = 0x65431278;
31constexpr uint8_t kTransmissionOffsetExtensionId = 1;
32constexpr uint8_t kAudioLevelExtensionId = 9;
erikvargae6b16192017-05-11 02:36:32 -070033constexpr uint8_t kRtpStreamIdExtensionId = 0xa;
Steve Antona3251dd2017-07-21 09:58:31 -070034constexpr uint8_t kRtpMidExtensionId = 0xb;
sprangba050a62017-08-18 02:51:12 -070035constexpr uint8_t kVideoTimingExtensionId = 0xc;
danilchap1edb7ab2016-04-20 05:25:10 -070036constexpr int32_t kTimeOffset = 0x56ce;
37constexpr bool kVoiceActive = true;
38constexpr uint8_t kAudioLevel = 0x5a;
erikvargae6b16192017-05-11 02:36:32 -070039constexpr char kStreamId[] = "streamid";
Steve Antona3251dd2017-07-21 09:58:31 -070040constexpr char kMid[] = "mid";
danilchap1edb7ab2016-04-20 05:25:10 -070041constexpr size_t kMaxPaddingSize = 224u;
danilchap07ec26d2016-06-17 04:18:54 -070042// clang-format off
danilchap1edb7ab2016-04-20 05:25:10 -070043constexpr uint8_t kMinimumPacket[] = {
eladalonae550e32017-05-24 08:28:13 -070044 0x80, kPayloadType, kSeqNumFirstByte, kSeqNumSecondByte,
danilchap1edb7ab2016-04-20 05:25:10 -070045 0x65, 0x43, 0x12, 0x78,
46 0x12, 0x34, 0x56, 0x78};
erikvargae6b16192017-05-11 02:36:32 -070047
danilchap1edb7ab2016-04-20 05:25:10 -070048constexpr uint8_t kPacketWithTO[] = {
eladalonae550e32017-05-24 08:28:13 -070049 0x90, kPayloadType, kSeqNumFirstByte, kSeqNumSecondByte,
danilchap1edb7ab2016-04-20 05:25:10 -070050 0x65, 0x43, 0x12, 0x78,
51 0x12, 0x34, 0x56, 0x78,
52 0xbe, 0xde, 0x00, 0x01,
53 0x12, 0x00, 0x56, 0xce};
54
55constexpr uint8_t kPacketWithTOAndAL[] = {
eladalonae550e32017-05-24 08:28:13 -070056 0x90, kPayloadType, kSeqNumFirstByte, kSeqNumSecondByte,
danilchap1edb7ab2016-04-20 05:25:10 -070057 0x65, 0x43, 0x12, 0x78,
58 0x12, 0x34, 0x56, 0x78,
59 0xbe, 0xde, 0x00, 0x02,
60 0x12, 0x00, 0x56, 0xce,
61 0x90, 0x80|kAudioLevel, 0x00, 0x00};
62
erikvargae6b16192017-05-11 02:36:32 -070063constexpr uint8_t kPacketWithRsid[] = {
eladalonae550e32017-05-24 08:28:13 -070064 0x90, kPayloadType, kSeqNumFirstByte, kSeqNumSecondByte,
erikvargae6b16192017-05-11 02:36:32 -070065 0x65, 0x43, 0x12, 0x78,
66 0x12, 0x34, 0x56, 0x78,
67 0xbe, 0xde, 0x00, 0x03,
68 0xa7, 's', 't', 'r',
69 'e', 'a', 'm', 'i',
70 'd' , 0x00, 0x00, 0x00};
71
Steve Antona3251dd2017-07-21 09:58:31 -070072constexpr uint8_t kPacketWithMid[] = {
73 0x90, kPayloadType, kSeqNumFirstByte, kSeqNumSecondByte,
74 0x65, 0x43, 0x12, 0x78,
75 0x12, 0x34, 0x56, 0x78,
76 0xbe, 0xde, 0x00, 0x01,
77 0xb2, 'm', 'i', 'd'};
78
danilchap1edb7ab2016-04-20 05:25:10 -070079constexpr uint32_t kCsrcs[] = {0x34567890, 0x32435465};
80constexpr uint8_t kPayload[] = {'p', 'a', 'y', 'l', 'o', 'a', 'd'};
81constexpr uint8_t kPacketPaddingSize = 8;
82constexpr uint8_t kPacket[] = {
eladalonae550e32017-05-24 08:28:13 -070083 0xb2, kPayloadType, kSeqNumFirstByte, kSeqNumSecondByte,
danilchap1edb7ab2016-04-20 05:25:10 -070084 0x65, 0x43, 0x12, 0x78,
85 0x12, 0x34, 0x56, 0x78,
86 0x34, 0x56, 0x78, 0x90,
87 0x32, 0x43, 0x54, 0x65,
88 0xbe, 0xde, 0x00, 0x01,
89 0x12, 0x00, 0x56, 0xce,
90 'p', 'a', 'y', 'l', 'o', 'a', 'd',
91 'p', 'a', 'd', 'd', 'i', 'n', 'g', kPacketPaddingSize};
danilchape565a042016-06-16 10:04:50 -070092
danilchap07ec26d2016-06-17 04:18:54 -070093constexpr uint8_t kPacketWithInvalidExtension[] = {
eladalonae550e32017-05-24 08:28:13 -070094 0x90, kPayloadType, kSeqNumFirstByte, kSeqNumSecondByte,
danilchap07ec26d2016-06-17 04:18:54 -070095 0x65, 0x43, 0x12, 0x78, // kTimestamp.
96 0x12, 0x34, 0x56, 0x78, // kSSrc.
97 0xbe, 0xde, 0x00, 0x02, // Extension block of size 2 x 32bit words.
98 (kTransmissionOffsetExtensionId << 4) | 6, // (6+1)-byte extension, but
99 'e', 'x', 't', // Transmission Offset
100 'd', 'a', 't', 'a', // expected to be 3-bytes.
sprangba050a62017-08-18 02:51:12 -0700101 'p', 'a', 'y', 'l', 'o', 'a', 'd'};
102
103constexpr uint8_t kPacketWithLegacyTimingExtension[] = {
104 0x90, kPayloadType, kSeqNumFirstByte, kSeqNumSecondByte,
105 0x65, 0x43, 0x12, 0x78, // kTimestamp.
106 0x12, 0x34, 0x56, 0x78, // kSSrc.
107 0xbe, 0xde, 0x00, 0x04, // Extension block of size 4 x 32bit words.
108 (kVideoTimingExtensionId << 4)
109 | VideoTimingExtension::kValueSizeBytes - 2, // Old format without flags.
110 0x00, 0x01, 0x00,
111 0x02, 0x00, 0x03, 0x00,
112 0x04, 0x00, 0x00, 0x00,
113 0x00, 0x00, 0x00, 0x00};
danilchap07ec26d2016-06-17 04:18:54 -0700114// clang-format on
danilchap1edb7ab2016-04-20 05:25:10 -0700115} // namespace
116
117TEST(RtpPacketTest, CreateMinimum) {
118 RtpPacketToSend packet(nullptr);
119 packet.SetPayloadType(kPayloadType);
120 packet.SetSequenceNumber(kSeqNum);
121 packet.SetTimestamp(kTimestamp);
122 packet.SetSsrc(kSsrc);
123 EXPECT_THAT(kMinimumPacket, ElementsAreArray(packet.data(), packet.size()));
124}
125
126TEST(RtpPacketTest, CreateWithExtension) {
127 RtpPacketToSend::ExtensionManager extensions;
128 extensions.Register(kRtpExtensionTransmissionTimeOffset,
129 kTransmissionOffsetExtensionId);
130 RtpPacketToSend packet(&extensions);
131 packet.SetPayloadType(kPayloadType);
132 packet.SetSequenceNumber(kSeqNum);
133 packet.SetTimestamp(kTimestamp);
134 packet.SetSsrc(kSsrc);
135 packet.SetExtension<TransmissionOffset>(kTimeOffset);
136 EXPECT_THAT(kPacketWithTO, ElementsAreArray(packet.data(), packet.size()));
137}
138
139TEST(RtpPacketTest, CreateWith2Extensions) {
140 RtpPacketToSend::ExtensionManager extensions;
141 extensions.Register(kRtpExtensionTransmissionTimeOffset,
142 kTransmissionOffsetExtensionId);
143 extensions.Register(kRtpExtensionAudioLevel, kAudioLevelExtensionId);
144 RtpPacketToSend packet(&extensions);
145 packet.SetPayloadType(kPayloadType);
146 packet.SetSequenceNumber(kSeqNum);
147 packet.SetTimestamp(kTimestamp);
148 packet.SetSsrc(kSsrc);
149 packet.SetExtension<TransmissionOffset>(kTimeOffset);
150 packet.SetExtension<AudioLevel>(kVoiceActive, kAudioLevel);
151 EXPECT_THAT(kPacketWithTOAndAL,
152 ElementsAreArray(packet.data(), packet.size()));
153}
154
erikvargae6b16192017-05-11 02:36:32 -0700155TEST(RtpPacketTest, CreateWithDynamicSizedExtensions) {
156 RtpPacketToSend::ExtensionManager extensions;
157 extensions.Register<RtpStreamId>(kRtpStreamIdExtensionId);
158 RtpPacketToSend packet(&extensions);
159 packet.SetPayloadType(kPayloadType);
160 packet.SetSequenceNumber(kSeqNum);
161 packet.SetTimestamp(kTimestamp);
162 packet.SetSsrc(kSsrc);
163 packet.SetExtension<RtpStreamId>(kStreamId);
164 EXPECT_THAT(kPacketWithRsid, ElementsAreArray(packet.data(), packet.size()));
165}
166
167TEST(RtpPacketTest, TryToCreateWithEmptyRsid) {
168 RtpPacketToSend::ExtensionManager extensions;
169 extensions.Register<RtpStreamId>(kRtpStreamIdExtensionId);
170 RtpPacketToSend packet(&extensions);
171 EXPECT_FALSE(packet.SetExtension<RtpStreamId>(""));
172}
173
174TEST(RtpPacketTest, TryToCreateWithLongRsid) {
175 RtpPacketToSend::ExtensionManager extensions;
176 constexpr char kLongStreamId[] = "LoooooooooongRsid";
177 ASSERT_EQ(strlen(kLongStreamId), 17u);
178 extensions.Register<RtpStreamId>(kRtpStreamIdExtensionId);
179 RtpPacketToSend packet(&extensions);
180 EXPECT_FALSE(packet.SetExtension<RtpStreamId>(kLongStreamId));
181}
182
Steve Antona3251dd2017-07-21 09:58:31 -0700183TEST(RtpPacketTest, TryToCreateWithEmptyMid) {
184 RtpPacketToSend::ExtensionManager extensions;
185 extensions.Register<RtpMid>(kRtpMidExtensionId);
186 RtpPacketToSend packet(&extensions);
187 EXPECT_FALSE(packet.SetExtension<RtpMid>(""));
188}
189
190TEST(RtpPacketTest, TryToCreateWithLongMid) {
191 RtpPacketToSend::ExtensionManager extensions;
192 constexpr char kLongMid[] = "LoooooooooonogMid";
193 ASSERT_EQ(strlen(kLongMid), 17u);
194 extensions.Register<RtpMid>(kRtpMidExtensionId);
195 RtpPacketToSend packet(&extensions);
196 EXPECT_FALSE(packet.SetExtension<RtpMid>(kLongMid));
197}
198
danilchap653063f2017-04-03 06:16:30 -0700199TEST(RtpPacketTest, CreateWithExtensionsWithoutManager) {
200 RtpPacketToSend packet(nullptr);
201 packet.SetPayloadType(kPayloadType);
202 packet.SetSequenceNumber(kSeqNum);
203 packet.SetTimestamp(kTimestamp);
204 packet.SetSsrc(kSsrc);
205
206 auto raw = packet.AllocateRawExtension(kTransmissionOffsetExtensionId,
207 TransmissionOffset::kValueSizeBytes);
208 EXPECT_EQ(raw.size(), TransmissionOffset::kValueSizeBytes);
209 TransmissionOffset::Write(raw.data(), kTimeOffset);
210
211 raw = packet.AllocateRawExtension(kAudioLevelExtensionId,
212 AudioLevel::kValueSizeBytes);
213 EXPECT_EQ(raw.size(), AudioLevel::kValueSizeBytes);
214 AudioLevel::Write(raw.data(), kVoiceActive, kAudioLevel);
215
216 EXPECT_THAT(kPacketWithTOAndAL,
217 ElementsAreArray(packet.data(), packet.size()));
218}
219
220TEST(RtpPacketTest, CreateWithMaxSizeHeaderExtension) {
221 const size_t kMaxExtensionSize = 16;
222 const int kId = 1;
223 const uint8_t kValue[16] = "123456789abcdef";
224
225 // Write packet with a custom extension.
226 RtpPacketToSend packet(nullptr);
227 packet.SetRawExtension(kId, kValue);
228 // Using different size for same id is not allowed.
229 EXPECT_TRUE(packet.AllocateRawExtension(kId, kMaxExtensionSize - 1).empty());
230
231 packet.SetPayloadSize(42);
232 // Rewriting allocated extension is allowed.
233 EXPECT_EQ(packet.AllocateRawExtension(kId, kMaxExtensionSize).size(),
234 kMaxExtensionSize);
235 // Adding another extension after payload is set is not allowed.
236 EXPECT_TRUE(packet.AllocateRawExtension(kId + 1, kMaxExtensionSize).empty());
237
238 // Read packet with the custom extension.
239 RtpPacketReceived parsed;
240 EXPECT_TRUE(parsed.Parse(packet.Buffer()));
241 auto read_raw = parsed.GetRawExtension(kId);
242 EXPECT_THAT(read_raw, ElementsAreArray(kValue, kMaxExtensionSize));
243}
244
danilchap1edb7ab2016-04-20 05:25:10 -0700245TEST(RtpPacketTest, SetReservedExtensionsAfterPayload) {
246 const size_t kPayloadSize = 4;
247 RtpPacketToSend::ExtensionManager extensions;
248 extensions.Register(kRtpExtensionTransmissionTimeOffset,
249 kTransmissionOffsetExtensionId);
250 extensions.Register(kRtpExtensionAudioLevel, kAudioLevelExtensionId);
251 RtpPacketToSend packet(&extensions);
252
253 EXPECT_TRUE(packet.ReserveExtension<TransmissionOffset>());
danilchap07a01b32017-03-29 07:33:13 -0700254 packet.SetPayloadSize(kPayloadSize);
danilchap1edb7ab2016-04-20 05:25:10 -0700255 // Can't set extension after payload.
256 EXPECT_FALSE(packet.SetExtension<AudioLevel>(kVoiceActive, kAudioLevel));
257 // Unless reserved.
258 EXPECT_TRUE(packet.SetExtension<TransmissionOffset>(kTimeOffset));
259}
260
261TEST(RtpPacketTest, CreatePurePadding) {
262 const size_t kPaddingSize = kMaxPaddingSize - 1;
263 RtpPacketToSend packet(nullptr, 12 + kPaddingSize);
264 packet.SetPayloadType(kPayloadType);
265 packet.SetSequenceNumber(kSeqNum);
266 packet.SetTimestamp(kTimestamp);
267 packet.SetSsrc(kSsrc);
268 Random random(0x123456789);
269
270 EXPECT_LT(packet.size(), packet.capacity());
271 EXPECT_FALSE(packet.SetPadding(kPaddingSize + 1, &random));
272 EXPECT_TRUE(packet.SetPadding(kPaddingSize, &random));
273 EXPECT_EQ(packet.size(), packet.capacity());
274}
275
276TEST(RtpPacketTest, CreateUnalignedPadding) {
277 const size_t kPayloadSize = 3; // Make padding start at unaligned address.
278 RtpPacketToSend packet(nullptr, 12 + kPayloadSize + kMaxPaddingSize);
279 packet.SetPayloadType(kPayloadType);
280 packet.SetSequenceNumber(kSeqNum);
281 packet.SetTimestamp(kTimestamp);
282 packet.SetSsrc(kSsrc);
danilchap07a01b32017-03-29 07:33:13 -0700283 packet.SetPayloadSize(kPayloadSize);
danilchap1edb7ab2016-04-20 05:25:10 -0700284 Random r(0x123456789);
285
286 EXPECT_LT(packet.size(), packet.capacity());
287 EXPECT_TRUE(packet.SetPadding(kMaxPaddingSize, &r));
288 EXPECT_EQ(packet.size(), packet.capacity());
289}
290
291TEST(RtpPacketTest, ParseMinimum) {
292 RtpPacketReceived packet;
293 EXPECT_TRUE(packet.Parse(kMinimumPacket, sizeof(kMinimumPacket)));
294 EXPECT_EQ(kPayloadType, packet.PayloadType());
295 EXPECT_EQ(kSeqNum, packet.SequenceNumber());
296 EXPECT_EQ(kTimestamp, packet.Timestamp());
297 EXPECT_EQ(kSsrc, packet.Ssrc());
298 EXPECT_EQ(0u, packet.padding_size());
299 EXPECT_EQ(0u, packet.payload_size());
300}
301
302TEST(RtpPacketTest, ParseBuffer) {
Danil Chapovalov31e4e802016-08-03 18:27:40 +0200303 rtc::CopyOnWriteBuffer unparsed(kMinimumPacket);
danilchap1edb7ab2016-04-20 05:25:10 -0700304 const uint8_t* raw = unparsed.data();
305
306 RtpPacketReceived packet;
307 EXPECT_TRUE(packet.Parse(std::move(unparsed)));
Danil Chapovalov31e4e802016-08-03 18:27:40 +0200308 EXPECT_EQ(raw, packet.data()); // Expect packet take the buffer without copy.
danilchap1edb7ab2016-04-20 05:25:10 -0700309 EXPECT_EQ(kSeqNum, packet.SequenceNumber());
310 EXPECT_EQ(kTimestamp, packet.Timestamp());
311 EXPECT_EQ(kSsrc, packet.Ssrc());
312 EXPECT_EQ(0u, packet.padding_size());
313 EXPECT_EQ(0u, packet.payload_size());
314}
315
316TEST(RtpPacketTest, ParseWithExtension) {
317 RtpPacketToSend::ExtensionManager extensions;
318 extensions.Register(kRtpExtensionTransmissionTimeOffset,
319 kTransmissionOffsetExtensionId);
320
321 RtpPacketReceived packet(&extensions);
322 EXPECT_TRUE(packet.Parse(kPacketWithTO, sizeof(kPacketWithTO)));
323 EXPECT_EQ(kPayloadType, packet.PayloadType());
324 EXPECT_EQ(kSeqNum, packet.SequenceNumber());
325 EXPECT_EQ(kTimestamp, packet.Timestamp());
326 EXPECT_EQ(kSsrc, packet.Ssrc());
327 int32_t time_offset;
328 EXPECT_TRUE(packet.GetExtension<TransmissionOffset>(&time_offset));
329 EXPECT_EQ(kTimeOffset, time_offset);
330 EXPECT_EQ(0u, packet.payload_size());
331 EXPECT_EQ(0u, packet.padding_size());
332}
333
danilchap07ec26d2016-06-17 04:18:54 -0700334TEST(RtpPacketTest, ParseWithInvalidSizedExtension) {
335 RtpPacketToSend::ExtensionManager extensions;
336 extensions.Register(kRtpExtensionTransmissionTimeOffset,
337 kTransmissionOffsetExtensionId);
338
339 RtpPacketReceived packet(&extensions);
340 EXPECT_TRUE(packet.Parse(kPacketWithInvalidExtension,
341 sizeof(kPacketWithInvalidExtension)));
342
343 // Extension should be ignored.
344 int32_t time_offset;
345 EXPECT_FALSE(packet.GetExtension<TransmissionOffset>(&time_offset));
346
347 // But shouldn't prevent reading payload.
danilchap96c15872016-11-21 01:35:29 -0800348 EXPECT_THAT(packet.payload(), ElementsAreArray(kPayload));
danilchap07ec26d2016-06-17 04:18:54 -0700349}
350
Danil Chapovalova64a2fb2016-09-12 11:41:35 +0200351TEST(RtpPacketTest, ParseWithOverSizedExtension) {
352 // clang-format off
353 const uint8_t bad_packet[] = {
eladalonae550e32017-05-24 08:28:13 -0700354 0x90, kPayloadType, kSeqNumFirstByte, kSeqNumSecondByte,
Danil Chapovalova64a2fb2016-09-12 11:41:35 +0200355 0x65, 0x43, 0x12, 0x78, // kTimestamp.
356 0x12, 0x34, 0x56, 0x78, // kSsrc.
357 0xbe, 0xde, 0x00, 0x01, // Extension of size 1x32bit word.
358 0x00, // Add a byte of padding.
359 0x12, // Extension id 1 size (2+1).
360 0xda, 0x1a // Only 2 bytes of extension payload.
361 };
362 // clang-format on
363 RtpPacketToSend::ExtensionManager extensions;
364 extensions.Register(TransmissionOffset::kId, 1);
365 RtpPacketReceived packet(&extensions);
366
367 // Parse should ignore bad extension and proceed.
368 EXPECT_TRUE(packet.Parse(bad_packet, sizeof(bad_packet)));
369 int32_t time_offset;
370 // But extracting extension should fail.
371 EXPECT_FALSE(packet.GetExtension<TransmissionOffset>(&time_offset));
372}
373
danilchap1edb7ab2016-04-20 05:25:10 -0700374TEST(RtpPacketTest, ParseWith2Extensions) {
375 RtpPacketToSend::ExtensionManager extensions;
376 extensions.Register(kRtpExtensionTransmissionTimeOffset,
377 kTransmissionOffsetExtensionId);
378 extensions.Register(kRtpExtensionAudioLevel, kAudioLevelExtensionId);
379 RtpPacketReceived packet(&extensions);
380 EXPECT_TRUE(packet.Parse(kPacketWithTOAndAL, sizeof(kPacketWithTOAndAL)));
381 int32_t time_offset;
382 EXPECT_TRUE(packet.GetExtension<TransmissionOffset>(&time_offset));
383 EXPECT_EQ(kTimeOffset, time_offset);
384 bool voice_active;
385 uint8_t audio_level;
386 EXPECT_TRUE(packet.GetExtension<AudioLevel>(&voice_active, &audio_level));
387 EXPECT_EQ(kVoiceActive, voice_active);
388 EXPECT_EQ(kAudioLevel, audio_level);
389}
390
391TEST(RtpPacketTest, ParseWithAllFeatures) {
392 RtpPacketToSend::ExtensionManager extensions;
393 extensions.Register(kRtpExtensionTransmissionTimeOffset,
394 kTransmissionOffsetExtensionId);
395 RtpPacketReceived packet(&extensions);
396 EXPECT_TRUE(packet.Parse(kPacket, sizeof(kPacket)));
397 EXPECT_EQ(kPayloadType, packet.PayloadType());
398 EXPECT_EQ(kSeqNum, packet.SequenceNumber());
399 EXPECT_EQ(kTimestamp, packet.Timestamp());
400 EXPECT_EQ(kSsrc, packet.Ssrc());
401 EXPECT_THAT(packet.Csrcs(), ElementsAreArray(kCsrcs));
danilchap96c15872016-11-21 01:35:29 -0800402 EXPECT_THAT(packet.payload(), ElementsAreArray(kPayload));
danilchap1edb7ab2016-04-20 05:25:10 -0700403 EXPECT_EQ(kPacketPaddingSize, packet.padding_size());
404 int32_t time_offset;
405 EXPECT_TRUE(packet.GetExtension<TransmissionOffset>(&time_offset));
406}
407
408TEST(RtpPacketTest, ParseWithExtensionDelayed) {
409 RtpPacketReceived packet;
410 EXPECT_TRUE(packet.Parse(kPacketWithTO, sizeof(kPacketWithTO)));
411 EXPECT_EQ(kPayloadType, packet.PayloadType());
412 EXPECT_EQ(kSeqNum, packet.SequenceNumber());
413 EXPECT_EQ(kTimestamp, packet.Timestamp());
414 EXPECT_EQ(kSsrc, packet.Ssrc());
415
416 RtpPacketToSend::ExtensionManager extensions;
417 extensions.Register(kRtpExtensionTransmissionTimeOffset,
418 kTransmissionOffsetExtensionId);
419
420 int32_t time_offset;
421 EXPECT_FALSE(packet.GetExtension<TransmissionOffset>(&time_offset));
danilchap70f39a32016-12-16 05:48:18 -0800422 packet.IdentifyExtensions(extensions);
danilchap1edb7ab2016-04-20 05:25:10 -0700423 EXPECT_TRUE(packet.GetExtension<TransmissionOffset>(&time_offset));
424 EXPECT_EQ(kTimeOffset, time_offset);
425 EXPECT_EQ(0u, packet.payload_size());
426 EXPECT_EQ(0u, packet.padding_size());
427}
428
danilchap653063f2017-04-03 06:16:30 -0700429TEST(RtpPacketTest, ParseWithoutExtensionManager) {
430 RtpPacketReceived packet;
431 EXPECT_TRUE(packet.Parse(kPacketWithTO, sizeof(kPacketWithTO)));
432
433 EXPECT_FALSE(packet.HasRawExtension(kAudioLevelExtensionId));
434 EXPECT_TRUE(packet.GetRawExtension(kAudioLevelExtensionId).empty());
435
436 EXPECT_TRUE(packet.HasRawExtension(kTransmissionOffsetExtensionId));
437
438 int32_t time_offset = 0;
439 auto raw_extension = packet.GetRawExtension(kTransmissionOffsetExtensionId);
440 EXPECT_EQ(raw_extension.size(), TransmissionOffset::kValueSizeBytes);
danilchap978504e2017-04-06 01:03:53 -0700441 EXPECT_TRUE(TransmissionOffset::Parse(raw_extension, &time_offset));
danilchap653063f2017-04-03 06:16:30 -0700442
443 EXPECT_EQ(time_offset, kTimeOffset);
444}
445
danilchapef8d7732017-04-19 02:59:48 -0700446TEST(RtpPacketTest, ParseDynamicSizeExtension) {
447 // clang-format off
448 const uint8_t kPacket1[] = {
eladalonae550e32017-05-24 08:28:13 -0700449 0x90, kPayloadType, kSeqNumFirstByte, kSeqNumSecondByte,
danilchapef8d7732017-04-19 02:59:48 -0700450 0x65, 0x43, 0x12, 0x78, // Timestamp.
451 0x12, 0x34, 0x56, 0x78, // Ssrc.
452 0xbe, 0xde, 0x00, 0x02, // Extensions block of size 2x32bit words.
453 0x21, 'H', 'D', // Extension with id = 2, size = (1+1).
454 0x12, 'r', 't', 'x', // Extension with id = 1, size = (2+1).
455 0x00}; // Extension padding.
456 const uint8_t kPacket2[] = {
eladalonae550e32017-05-24 08:28:13 -0700457 0x90, kPayloadType, kSeqNumFirstByte, kSeqNumSecondByte,
danilchapef8d7732017-04-19 02:59:48 -0700458 0x65, 0x43, 0x12, 0x78, // Timestamp.
459 0x12, 0x34, 0x56, 0x79, // Ssrc.
460 0xbe, 0xde, 0x00, 0x01, // Extensions block of size 1x32bit words.
461 0x11, 'H', 'D', // Extension with id = 1, size = (1+1).
462 0x00}; // Extension padding.
463 // clang-format on
464 RtpPacketReceived::ExtensionManager extensions;
465 extensions.Register<RtpStreamId>(1);
466 extensions.Register<RepairedRtpStreamId>(2);
467 RtpPacketReceived packet(&extensions);
468 ASSERT_TRUE(packet.Parse(kPacket1, sizeof(kPacket1)));
469
470 std::string rsid;
471 EXPECT_TRUE(packet.GetExtension<RtpStreamId>(&rsid));
472 EXPECT_EQ(rsid, "rtx");
473
474 std::string repaired_rsid;
475 EXPECT_TRUE(packet.GetExtension<RepairedRtpStreamId>(&repaired_rsid));
476 EXPECT_EQ(repaired_rsid, "HD");
477
478 // Parse another packet with RtpStreamId extension of different size.
479 ASSERT_TRUE(packet.Parse(kPacket2, sizeof(kPacket2)));
480 EXPECT_TRUE(packet.GetExtension<RtpStreamId>(&rsid));
481 EXPECT_EQ(rsid, "HD");
482 EXPECT_FALSE(packet.GetExtension<RepairedRtpStreamId>(&repaired_rsid));
483}
484
Steve Antona3251dd2017-07-21 09:58:31 -0700485TEST(RtpPacketTest, ParseWithMid) {
486 RtpPacketReceived::ExtensionManager extensions;
487 extensions.Register<RtpMid>(kRtpMidExtensionId);
488 RtpPacketReceived packet(&extensions);
489 ASSERT_TRUE(packet.Parse(kPacketWithMid, sizeof(kPacketWithMid)));
490
491 std::string mid;
492 EXPECT_TRUE(packet.GetExtension<RtpMid>(&mid));
493 EXPECT_EQ(mid, kMid);
494}
495
danilchapc547e842017-04-10 01:31:49 -0700496TEST(RtpPacketTest, RawExtensionFunctionsAcceptZeroIdAndReturnFalse) {
497 RtpPacketReceived::ExtensionManager extensions;
498 RtpPacketReceived packet(&extensions);
499 // Use ExtensionManager to set kInvalidId to 0 to demonstrate natural way for
500 // using zero value as a parameter to Packet::*RawExtension functions.
501 const int kInvalidId = extensions.GetId(TransmissionOffset::kId);
502 ASSERT_EQ(kInvalidId, 0);
503
504 ASSERT_TRUE(packet.Parse(kPacket, sizeof(kPacket)));
505
506 EXPECT_FALSE(packet.HasRawExtension(kInvalidId));
507 EXPECT_THAT(packet.GetRawExtension(kInvalidId), IsEmpty());
508 const uint8_t kExtension[] = {'e', 'x', 't'};
509 EXPECT_FALSE(packet.SetRawExtension(kInvalidId, kExtension));
510 EXPECT_THAT(packet.AllocateRawExtension(kInvalidId, 3), IsEmpty());
511}
512
sprangba050a62017-08-18 02:51:12 -0700513TEST(RtpPacketTest, CreateAndParseTimingFrameExtension) {
514 // Create a packet with video frame timing extension populated.
515 RtpPacketToSend::ExtensionManager send_extensions;
516 send_extensions.Register(kRtpExtensionVideoTiming, kVideoTimingExtensionId);
517 RtpPacketToSend send_packet(&send_extensions);
518 send_packet.SetPayloadType(kPayloadType);
519 send_packet.SetSequenceNumber(kSeqNum);
520 send_packet.SetTimestamp(kTimestamp);
521 send_packet.SetSsrc(kSsrc);
522
523 VideoSendTiming timing;
524 timing.encode_start_delta_ms = 1;
525 timing.encode_finish_delta_ms = 2;
526 timing.packetization_finish_delta_ms = 3;
527 timing.pacer_exit_delta_ms = 4;
528 timing.flags =
529 TimingFrameFlags::kTriggeredByTimer + TimingFrameFlags::kTriggeredBySize;
530
531 send_packet.SetExtension<VideoTimingExtension>(timing);
532
533 // Serialize the packet and then parse it again.
534 RtpPacketReceived::ExtensionManager extensions;
535 extensions.Register<VideoTimingExtension>(kVideoTimingExtensionId);
536 RtpPacketReceived receive_packet(&extensions);
537 EXPECT_TRUE(receive_packet.Parse(send_packet.Buffer()));
538
539 VideoSendTiming receivied_timing;
540 EXPECT_TRUE(
541 receive_packet.GetExtension<VideoTimingExtension>(&receivied_timing));
542
543 // Only check first and last timestamp (covered by other tests) plus flags.
544 EXPECT_EQ(receivied_timing.encode_start_delta_ms,
545 timing.encode_start_delta_ms);
546 EXPECT_EQ(receivied_timing.pacer_exit_delta_ms, timing.pacer_exit_delta_ms);
547 EXPECT_EQ(receivied_timing.flags, timing.flags);
548}
549
550TEST(RtpPacketTest, ParseLegacyTimingFrameExtension) {
551 // Parse the modified packet.
552 RtpPacketReceived::ExtensionManager extensions;
553 extensions.Register<VideoTimingExtension>(kVideoTimingExtensionId);
554 RtpPacketReceived packet(&extensions);
555 EXPECT_TRUE(packet.Parse(kPacketWithLegacyTimingExtension,
556 sizeof(kPacketWithLegacyTimingExtension)));
557 VideoSendTiming receivied_timing;
558 EXPECT_TRUE(packet.GetExtension<VideoTimingExtension>(&receivied_timing));
559
560 // Check first and last timestamp are still OK. Flags should now be 0.
561 EXPECT_EQ(receivied_timing.encode_start_delta_ms, 1);
562 EXPECT_EQ(receivied_timing.pacer_exit_delta_ms, 4);
563 EXPECT_EQ(receivied_timing.flags, 0);
564}
565
danilchap1edb7ab2016-04-20 05:25:10 -0700566} // namespace webrtc