session_info_unittest.cc (17257B)
1 /* 2 * Copyright (c) 2012 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 "modules/video_coding/deprecated/session_info.h" 12 13 #include <cstdint> 14 #include <cstring> 15 16 #include "api/video/video_codec_type.h" 17 #include "api/video/video_frame_type.h" 18 #include "modules/video_coding/deprecated/packet.h" 19 #include "test/gtest.h" 20 21 namespace webrtc { 22 23 class TestSessionInfo : public ::testing::Test { 24 protected: 25 void SetUp() override { 26 memset(packet_buffer_, 0, sizeof(packet_buffer_)); 27 memset(frame_buffer_, 0, sizeof(frame_buffer_)); 28 session_.Reset(); 29 packet_.video_header.frame_type = VideoFrameType::kVideoFrameDelta; 30 packet_.sizeBytes = packet_buffer_size(); 31 packet_.dataPtr = packet_buffer_; 32 packet_.seqNum = 0; 33 packet_.timestamp = 0; 34 frame_data.rtt_ms = 0; 35 frame_data.rolling_average_packets_per_frame = -1; 36 } 37 38 void FillPacket(uint8_t start_value) { 39 for (size_t i = 0; i < packet_buffer_size(); ++i) 40 packet_buffer_[i] = start_value + i; 41 } 42 43 void VerifyPacket(uint8_t* start_ptr, uint8_t start_value) { 44 for (size_t j = 0; j < packet_buffer_size(); ++j) { 45 ASSERT_EQ(start_value + j, start_ptr[j]); 46 } 47 } 48 49 size_t packet_buffer_size() const { 50 return sizeof(packet_buffer_) / sizeof(packet_buffer_[0]); 51 } 52 size_t frame_buffer_size() const { 53 return sizeof(frame_buffer_) / sizeof(frame_buffer_[0]); 54 } 55 56 enum { kPacketBufferSize = 10 }; 57 58 uint8_t packet_buffer_[kPacketBufferSize]; 59 uint8_t frame_buffer_[10 * kPacketBufferSize]; 60 61 VCMSessionInfo session_; 62 VCMPacket packet_; 63 FrameData frame_data; 64 }; 65 66 class TestNalUnits : public TestSessionInfo { 67 protected: 68 void SetUp() override { 69 TestSessionInfo::SetUp(); 70 packet_.video_header.codec = kVideoCodecVP8; 71 } 72 73 bool VerifyNalu(int offset, int packets_expected, int start_value) { 74 EXPECT_GE(session_.SessionLength(), 75 packets_expected * packet_buffer_size()); 76 for (int i = 0; i < packets_expected; ++i) { 77 int packet_index = (offset + i) * packet_buffer_size(); 78 VerifyPacket(frame_buffer_ + packet_index, start_value + i); 79 } 80 return true; 81 } 82 }; 83 84 class TestNackList : public TestSessionInfo { 85 protected: 86 static const size_t kMaxSeqNumListLength = 30; 87 88 void SetUp() override { 89 TestSessionInfo::SetUp(); 90 seq_num_list_length_ = 0; 91 memset(seq_num_list_, 0, sizeof(seq_num_list_)); 92 } 93 94 void BuildSeqNumList(uint16_t low, uint16_t high) { 95 size_t i = 0; 96 while (low != high + 1) { 97 EXPECT_LT(i, kMaxSeqNumListLength); 98 if (i >= kMaxSeqNumListLength) { 99 seq_num_list_length_ = kMaxSeqNumListLength; 100 return; 101 } 102 seq_num_list_[i] = low; 103 low++; 104 i++; 105 } 106 seq_num_list_length_ = i; 107 } 108 109 void VerifyAll(int value) { 110 for (int i = 0; i < seq_num_list_length_; ++i) 111 EXPECT_EQ(seq_num_list_[i], value); 112 } 113 114 int seq_num_list_[kMaxSeqNumListLength]; 115 int seq_num_list_length_; 116 }; 117 118 TEST_F(TestSessionInfo, TestSimpleAPIs) { 119 packet_.video_header.is_first_packet_in_frame = true; 120 packet_.seqNum = 0xFFFE; 121 packet_.sizeBytes = packet_buffer_size(); 122 packet_.video_header.frame_type = VideoFrameType::kVideoFrameKey; 123 FillPacket(0); 124 EXPECT_EQ(packet_buffer_size(), static_cast<size_t>(session_.InsertPacket( 125 packet_, frame_buffer_, frame_data))); 126 EXPECT_FALSE(session_.HaveLastPacket()); 127 EXPECT_EQ(VideoFrameType::kVideoFrameKey, session_.FrameType()); 128 129 packet_.video_header.is_first_packet_in_frame = false; 130 packet_.markerBit = true; 131 packet_.seqNum += 1; 132 EXPECT_EQ(packet_buffer_size(), static_cast<size_t>(session_.InsertPacket( 133 packet_, frame_buffer_, frame_data))); 134 EXPECT_TRUE(session_.HaveLastPacket()); 135 EXPECT_EQ(packet_.seqNum, session_.HighSequenceNumber()); 136 EXPECT_EQ(0xFFFE, session_.LowSequenceNumber()); 137 138 // Insert empty packet which will be the new high sequence number. 139 // To make things more difficult we will make sure to have a wrap here. 140 packet_.video_header.is_first_packet_in_frame = false; 141 packet_.markerBit = true; 142 packet_.seqNum = 2; 143 packet_.sizeBytes = 0; 144 packet_.video_header.frame_type = VideoFrameType::kEmptyFrame; 145 EXPECT_EQ(0, session_.InsertPacket(packet_, frame_buffer_, frame_data)); 146 EXPECT_EQ(packet_.seqNum, session_.HighSequenceNumber()); 147 } 148 149 TEST_F(TestSessionInfo, NormalOperation) { 150 packet_.seqNum = 0xFFFF; 151 packet_.video_header.is_first_packet_in_frame = true; 152 packet_.markerBit = false; 153 FillPacket(0); 154 EXPECT_EQ(packet_buffer_size(), static_cast<size_t>(session_.InsertPacket( 155 packet_, frame_buffer_, frame_data))); 156 157 packet_.video_header.is_first_packet_in_frame = false; 158 for (int i = 1; i < 9; ++i) { 159 packet_.seqNum += 1; 160 FillPacket(i); 161 ASSERT_EQ(packet_buffer_size(), static_cast<size_t>(session_.InsertPacket( 162 packet_, frame_buffer_, frame_data))); 163 } 164 165 packet_.seqNum += 1; 166 packet_.markerBit = true; 167 FillPacket(9); 168 EXPECT_EQ(packet_buffer_size(), static_cast<size_t>(session_.InsertPacket( 169 packet_, frame_buffer_, frame_data))); 170 171 EXPECT_EQ(10 * packet_buffer_size(), session_.SessionLength()); 172 for (int i = 0; i < 10; ++i) { 173 SCOPED_TRACE("Calling VerifyPacket"); 174 VerifyPacket(frame_buffer_ + i * packet_buffer_size(), i); 175 } 176 } 177 178 TEST_F(TestSessionInfo, OutOfBoundsPackets1PacketFrame) { 179 packet_.seqNum = 0x0001; 180 packet_.video_header.is_first_packet_in_frame = true; 181 packet_.markerBit = true; 182 FillPacket(1); 183 EXPECT_EQ(packet_buffer_size(), static_cast<size_t>(session_.InsertPacket( 184 packet_, frame_buffer_, frame_data))); 185 186 packet_.seqNum = 0x0004; 187 packet_.video_header.is_first_packet_in_frame = true; 188 packet_.markerBit = true; 189 FillPacket(1); 190 EXPECT_EQ(-3, session_.InsertPacket(packet_, frame_buffer_, frame_data)); 191 packet_.seqNum = 0x0000; 192 packet_.video_header.is_first_packet_in_frame = false; 193 packet_.markerBit = false; 194 FillPacket(1); 195 EXPECT_EQ(-3, session_.InsertPacket(packet_, frame_buffer_, frame_data)); 196 } 197 198 TEST_F(TestSessionInfo, SetMarkerBitOnce) { 199 packet_.seqNum = 0x0005; 200 packet_.video_header.is_first_packet_in_frame = false; 201 packet_.markerBit = true; 202 FillPacket(1); 203 EXPECT_EQ(packet_buffer_size(), static_cast<size_t>(session_.InsertPacket( 204 packet_, frame_buffer_, frame_data))); 205 ++packet_.seqNum; 206 packet_.video_header.is_first_packet_in_frame = true; 207 packet_.markerBit = true; 208 FillPacket(1); 209 EXPECT_EQ(-3, session_.InsertPacket(packet_, frame_buffer_, frame_data)); 210 } 211 212 TEST_F(TestSessionInfo, OutOfBoundsPacketsBase) { 213 // Allow packets in the range 5-6. 214 packet_.seqNum = 0x0005; 215 packet_.video_header.is_first_packet_in_frame = true; 216 packet_.markerBit = false; 217 FillPacket(1); 218 EXPECT_EQ(packet_buffer_size(), static_cast<size_t>(session_.InsertPacket( 219 packet_, frame_buffer_, frame_data))); 220 // Insert an older packet with a first packet set. 221 packet_.seqNum = 0x0004; 222 packet_.video_header.is_first_packet_in_frame = true; 223 packet_.markerBit = true; 224 FillPacket(1); 225 EXPECT_EQ(-3, session_.InsertPacket(packet_, frame_buffer_, frame_data)); 226 packet_.seqNum = 0x0006; 227 packet_.video_header.is_first_packet_in_frame = true; 228 packet_.markerBit = true; 229 FillPacket(1); 230 EXPECT_EQ(packet_buffer_size(), static_cast<size_t>(session_.InsertPacket( 231 packet_, frame_buffer_, frame_data))); 232 packet_.seqNum = 0x0008; 233 packet_.video_header.is_first_packet_in_frame = false; 234 packet_.markerBit = true; 235 FillPacket(1); 236 EXPECT_EQ(-3, session_.InsertPacket(packet_, frame_buffer_, frame_data)); 237 } 238 239 TEST_F(TestSessionInfo, OutOfBoundsPacketsWrap) { 240 packet_.seqNum = 0xFFFE; 241 packet_.video_header.is_first_packet_in_frame = true; 242 packet_.markerBit = false; 243 FillPacket(1); 244 EXPECT_EQ(packet_buffer_size(), static_cast<size_t>(session_.InsertPacket( 245 packet_, frame_buffer_, frame_data))); 246 247 packet_.seqNum = 0x0004; 248 packet_.video_header.is_first_packet_in_frame = false; 249 packet_.markerBit = true; 250 FillPacket(1); 251 EXPECT_EQ(packet_buffer_size(), static_cast<size_t>(session_.InsertPacket( 252 packet_, frame_buffer_, frame_data))); 253 packet_.seqNum = 0x0002; 254 packet_.video_header.is_first_packet_in_frame = false; 255 packet_.markerBit = false; 256 FillPacket(1); 257 ASSERT_EQ(packet_buffer_size(), static_cast<size_t>(session_.InsertPacket( 258 packet_, frame_buffer_, frame_data))); 259 packet_.seqNum = 0xFFF0; 260 packet_.video_header.is_first_packet_in_frame = false; 261 packet_.markerBit = false; 262 FillPacket(1); 263 EXPECT_EQ(-3, session_.InsertPacket(packet_, frame_buffer_, frame_data)); 264 packet_.seqNum = 0x0006; 265 packet_.video_header.is_first_packet_in_frame = false; 266 packet_.markerBit = false; 267 FillPacket(1); 268 EXPECT_EQ(-3, session_.InsertPacket(packet_, frame_buffer_, frame_data)); 269 } 270 271 TEST_F(TestSessionInfo, OutOfBoundsOutOfOrder) { 272 // Insert out of bound regular packets, and then the first and last packet. 273 // Verify that correct bounds are maintained. 274 packet_.seqNum = 0x0003; 275 packet_.video_header.is_first_packet_in_frame = false; 276 packet_.markerBit = false; 277 FillPacket(1); 278 EXPECT_EQ(packet_buffer_size(), static_cast<size_t>(session_.InsertPacket( 279 packet_, frame_buffer_, frame_data))); 280 // Insert an older packet with a first packet set. 281 packet_.seqNum = 0x0005; 282 packet_.video_header.is_first_packet_in_frame = true; 283 packet_.markerBit = false; 284 FillPacket(1); 285 EXPECT_EQ(packet_buffer_size(), static_cast<size_t>(session_.InsertPacket( 286 packet_, frame_buffer_, frame_data))); 287 packet_.seqNum = 0x0004; 288 packet_.video_header.is_first_packet_in_frame = false; 289 packet_.markerBit = false; 290 FillPacket(1); 291 EXPECT_EQ(-3, session_.InsertPacket(packet_, frame_buffer_, frame_data)); 292 packet_.seqNum = 0x0010; 293 packet_.video_header.is_first_packet_in_frame = false; 294 packet_.markerBit = false; 295 FillPacket(1); 296 EXPECT_EQ(packet_buffer_size(), static_cast<size_t>(session_.InsertPacket( 297 packet_, frame_buffer_, frame_data))); 298 packet_.seqNum = 0x0008; 299 packet_.video_header.is_first_packet_in_frame = false; 300 packet_.markerBit = true; 301 FillPacket(1); 302 EXPECT_EQ(packet_buffer_size(), static_cast<size_t>(session_.InsertPacket( 303 packet_, frame_buffer_, frame_data))); 304 305 packet_.seqNum = 0x0009; 306 packet_.video_header.is_first_packet_in_frame = false; 307 packet_.markerBit = false; 308 FillPacket(1); 309 EXPECT_EQ(-3, session_.InsertPacket(packet_, frame_buffer_, frame_data)); 310 } 311 312 TEST_F(TestNalUnits, OnlyReceivedEmptyPacket) { 313 packet_.video_header.is_first_packet_in_frame = false; 314 packet_.completeNALU = kNaluComplete; 315 packet_.video_header.frame_type = VideoFrameType::kEmptyFrame; 316 packet_.sizeBytes = 0; 317 packet_.seqNum = 0; 318 packet_.markerBit = false; 319 EXPECT_EQ(0, session_.InsertPacket(packet_, frame_buffer_, frame_data)); 320 321 EXPECT_EQ(0U, session_.MakeDecodable()); 322 EXPECT_EQ(0U, session_.SessionLength()); 323 } 324 325 TEST_F(TestNalUnits, OneIsolatedNaluLoss) { 326 packet_.video_header.is_first_packet_in_frame = true; 327 packet_.completeNALU = kNaluComplete; 328 packet_.seqNum = 0; 329 packet_.markerBit = false; 330 FillPacket(0); 331 EXPECT_EQ(packet_buffer_size(), static_cast<size_t>(session_.InsertPacket( 332 packet_, frame_buffer_, frame_data))); 333 334 packet_.video_header.is_first_packet_in_frame = false; 335 packet_.completeNALU = kNaluComplete; 336 packet_.seqNum += 2; 337 packet_.markerBit = true; 338 FillPacket(2); 339 EXPECT_EQ(packet_buffer_size(), static_cast<size_t>(session_.InsertPacket( 340 packet_, frame_buffer_, frame_data))); 341 342 EXPECT_EQ(0U, session_.MakeDecodable()); 343 EXPECT_EQ(2 * packet_buffer_size(), session_.SessionLength()); 344 SCOPED_TRACE("Calling VerifyNalu"); 345 EXPECT_TRUE(VerifyNalu(0, 1, 0)); 346 SCOPED_TRACE("Calling VerifyNalu"); 347 EXPECT_TRUE(VerifyNalu(1, 1, 2)); 348 } 349 350 TEST_F(TestNalUnits, LossInMiddleOfNalu) { 351 packet_.video_header.is_first_packet_in_frame = true; 352 packet_.completeNALU = kNaluComplete; 353 packet_.seqNum = 0; 354 packet_.markerBit = false; 355 FillPacket(0); 356 EXPECT_EQ(packet_buffer_size(), static_cast<size_t>(session_.InsertPacket( 357 packet_, frame_buffer_, frame_data))); 358 359 packet_.video_header.is_first_packet_in_frame = false; 360 packet_.completeNALU = kNaluEnd; 361 packet_.seqNum += 2; 362 packet_.markerBit = true; 363 FillPacket(2); 364 EXPECT_EQ(packet_buffer_size(), static_cast<size_t>(session_.InsertPacket( 365 packet_, frame_buffer_, frame_data))); 366 367 EXPECT_EQ(packet_buffer_size(), session_.MakeDecodable()); 368 EXPECT_EQ(packet_buffer_size(), session_.SessionLength()); 369 SCOPED_TRACE("Calling VerifyNalu"); 370 EXPECT_TRUE(VerifyNalu(0, 1, 0)); 371 } 372 373 TEST_F(TestNalUnits, StartAndEndOfLastNalUnitLost) { 374 packet_.video_header.is_first_packet_in_frame = true; 375 packet_.completeNALU = kNaluComplete; 376 packet_.seqNum = 0; 377 packet_.markerBit = false; 378 FillPacket(0); 379 EXPECT_EQ(packet_buffer_size(), static_cast<size_t>(session_.InsertPacket( 380 packet_, frame_buffer_, frame_data))); 381 382 packet_.video_header.is_first_packet_in_frame = false; 383 packet_.completeNALU = kNaluIncomplete; 384 packet_.seqNum += 2; 385 packet_.markerBit = false; 386 FillPacket(1); 387 EXPECT_EQ(packet_buffer_size(), static_cast<size_t>(session_.InsertPacket( 388 packet_, frame_buffer_, frame_data))); 389 390 EXPECT_EQ(packet_buffer_size(), session_.MakeDecodable()); 391 EXPECT_EQ(packet_buffer_size(), session_.SessionLength()); 392 SCOPED_TRACE("Calling VerifyNalu"); 393 EXPECT_TRUE(VerifyNalu(0, 1, 0)); 394 } 395 396 TEST_F(TestNalUnits, ReorderWrapNoLoss) { 397 packet_.seqNum = 0xFFFF; 398 packet_.video_header.is_first_packet_in_frame = false; 399 packet_.completeNALU = kNaluIncomplete; 400 packet_.seqNum += 1; 401 packet_.markerBit = false; 402 FillPacket(1); 403 EXPECT_EQ(packet_buffer_size(), static_cast<size_t>(session_.InsertPacket( 404 packet_, frame_buffer_, frame_data))); 405 406 packet_.video_header.is_first_packet_in_frame = true; 407 packet_.completeNALU = kNaluComplete; 408 packet_.seqNum -= 1; 409 packet_.markerBit = false; 410 FillPacket(0); 411 EXPECT_EQ(packet_buffer_size(), static_cast<size_t>(session_.InsertPacket( 412 packet_, frame_buffer_, frame_data))); 413 414 packet_.video_header.is_first_packet_in_frame = false; 415 packet_.completeNALU = kNaluEnd; 416 packet_.seqNum += 2; 417 packet_.markerBit = true; 418 FillPacket(2); 419 EXPECT_EQ(packet_buffer_size(), static_cast<size_t>(session_.InsertPacket( 420 packet_, frame_buffer_, frame_data))); 421 422 EXPECT_EQ(0U, session_.MakeDecodable()); 423 EXPECT_EQ(3 * packet_buffer_size(), session_.SessionLength()); 424 SCOPED_TRACE("Calling VerifyNalu"); 425 EXPECT_TRUE(VerifyNalu(0, 1, 0)); 426 } 427 428 TEST_F(TestNalUnits, WrapLosses) { 429 packet_.seqNum = 0xFFFF; 430 packet_.video_header.is_first_packet_in_frame = false; 431 packet_.completeNALU = kNaluIncomplete; 432 packet_.markerBit = false; 433 FillPacket(1); 434 EXPECT_EQ(packet_buffer_size(), static_cast<size_t>(session_.InsertPacket( 435 packet_, frame_buffer_, frame_data))); 436 437 packet_.video_header.is_first_packet_in_frame = false; 438 packet_.completeNALU = kNaluEnd; 439 packet_.seqNum += 2; 440 packet_.markerBit = true; 441 FillPacket(2); 442 EXPECT_EQ(packet_buffer_size(), static_cast<size_t>(session_.InsertPacket( 443 packet_, frame_buffer_, frame_data))); 444 445 EXPECT_EQ(2 * packet_buffer_size(), session_.MakeDecodable()); 446 EXPECT_EQ(0U, session_.SessionLength()); 447 } 448 449 TEST_F(TestNalUnits, ReorderWrapLosses) { 450 packet_.seqNum = 0xFFFF; 451 452 packet_.video_header.is_first_packet_in_frame = false; 453 packet_.completeNALU = kNaluEnd; 454 packet_.seqNum += 2; 455 packet_.markerBit = true; 456 FillPacket(2); 457 EXPECT_EQ(packet_buffer_size(), static_cast<size_t>(session_.InsertPacket( 458 packet_, frame_buffer_, frame_data))); 459 460 packet_.seqNum -= 2; 461 packet_.video_header.is_first_packet_in_frame = false; 462 packet_.completeNALU = kNaluIncomplete; 463 packet_.markerBit = false; 464 FillPacket(1); 465 EXPECT_EQ(packet_buffer_size(), static_cast<size_t>(session_.InsertPacket( 466 packet_, frame_buffer_, frame_data))); 467 468 EXPECT_EQ(2 * packet_buffer_size(), session_.MakeDecodable()); 469 EXPECT_EQ(0U, session_.SessionLength()); 470 } 471 472 } // namespace webrtc