Home | History | Annotate | Download | only in source
      1 /*
      2  *  Copyright (c) 2015 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 <vector>
     12 
     13 #include "testing/gmock/include/gmock/gmock.h"
     14 #include "testing/gtest/include/gtest/gtest.h"
     15 #include "webrtc/modules/rtp_rtcp/source/rtp_format_vp9.h"
     16 #include "webrtc/typedefs.h"
     17 
     18 namespace webrtc {
     19 namespace {
     20 void VerifyHeader(const RTPVideoHeaderVP9& expected,
     21                   const RTPVideoHeaderVP9& actual) {
     22   EXPECT_EQ(expected.inter_layer_predicted, actual.inter_layer_predicted);
     23   EXPECT_EQ(expected.inter_pic_predicted, actual.inter_pic_predicted);
     24   EXPECT_EQ(expected.flexible_mode, actual.flexible_mode);
     25   EXPECT_EQ(expected.beginning_of_frame, actual.beginning_of_frame);
     26   EXPECT_EQ(expected.end_of_frame, actual.end_of_frame);
     27   EXPECT_EQ(expected.ss_data_available, actual.ss_data_available);
     28   EXPECT_EQ(expected.picture_id, actual.picture_id);
     29   EXPECT_EQ(expected.max_picture_id, actual.max_picture_id);
     30   EXPECT_EQ(expected.temporal_idx, actual.temporal_idx);
     31   EXPECT_EQ(expected.spatial_idx == kNoSpatialIdx ? 0 : expected.spatial_idx,
     32       actual.spatial_idx);
     33   EXPECT_EQ(expected.gof_idx, actual.gof_idx);
     34   EXPECT_EQ(expected.tl0_pic_idx, actual.tl0_pic_idx);
     35   EXPECT_EQ(expected.temporal_up_switch, actual.temporal_up_switch);
     36 
     37   EXPECT_EQ(expected.num_ref_pics, actual.num_ref_pics);
     38   for (uint8_t i = 0; i < expected.num_ref_pics; ++i) {
     39     EXPECT_EQ(expected.pid_diff[i], actual.pid_diff[i]);
     40     EXPECT_EQ(expected.ref_picture_id[i], actual.ref_picture_id[i]);
     41   }
     42   if (expected.ss_data_available) {
     43     EXPECT_EQ(expected.spatial_layer_resolution_present,
     44               actual.spatial_layer_resolution_present);
     45     EXPECT_EQ(expected.num_spatial_layers, actual.num_spatial_layers);
     46     if (expected.spatial_layer_resolution_present) {
     47       for (size_t i = 0; i < expected.num_spatial_layers; i++) {
     48         EXPECT_EQ(expected.width[i], actual.width[i]);
     49         EXPECT_EQ(expected.height[i], actual.height[i]);
     50       }
     51     }
     52     EXPECT_EQ(expected.gof.num_frames_in_gof, actual.gof.num_frames_in_gof);
     53     for (size_t i = 0; i < expected.gof.num_frames_in_gof; i++) {
     54       EXPECT_EQ(expected.gof.temporal_up_switch[i],
     55                 actual.gof.temporal_up_switch[i]);
     56       EXPECT_EQ(expected.gof.temporal_idx[i], actual.gof.temporal_idx[i]);
     57       EXPECT_EQ(expected.gof.num_ref_pics[i], actual.gof.num_ref_pics[i]);
     58       for (uint8_t j = 0; j < expected.gof.num_ref_pics[i]; j++) {
     59         EXPECT_EQ(expected.gof.pid_diff[i][j], actual.gof.pid_diff[i][j]);
     60       }
     61     }
     62   }
     63 }
     64 
     65 void VerifyPayload(const RtpDepacketizer::ParsedPayload& parsed,
     66                    const uint8_t* payload,
     67                    size_t payload_length) {
     68   EXPECT_EQ(payload, parsed.payload);
     69   EXPECT_EQ(payload_length, parsed.payload_length);
     70   EXPECT_THAT(std::vector<uint8_t>(parsed.payload,
     71                                    parsed.payload + parsed.payload_length),
     72               ::testing::ElementsAreArray(payload, payload_length));
     73 }
     74 
     75 void ParseAndCheckPacket(const uint8_t* packet,
     76                          const RTPVideoHeaderVP9& expected,
     77                          size_t expected_hdr_length,
     78                          size_t expected_length) {
     79   rtc::scoped_ptr<RtpDepacketizer> depacketizer(new RtpDepacketizerVp9());
     80   RtpDepacketizer::ParsedPayload parsed;
     81   ASSERT_TRUE(depacketizer->Parse(&parsed, packet, expected_length));
     82   EXPECT_EQ(kRtpVideoVp9, parsed.type.Video.codec);
     83   VerifyHeader(expected, parsed.type.Video.codecHeader.VP9);
     84   const size_t kExpectedPayloadLength = expected_length - expected_hdr_length;
     85   VerifyPayload(parsed, packet + expected_hdr_length, kExpectedPayloadLength);
     86 }
     87 }  // namespace
     88 
     89 // Payload descriptor for flexible mode
     90 //        0 1 2 3 4 5 6 7
     91 //        +-+-+-+-+-+-+-+-+
     92 //        |I|P|L|F|B|E|V|-| (REQUIRED)
     93 //        +-+-+-+-+-+-+-+-+
     94 //   I:   |M| PICTURE ID  | (RECOMMENDED)
     95 //        +-+-+-+-+-+-+-+-+
     96 //   M:   | EXTENDED PID  | (RECOMMENDED)
     97 //        +-+-+-+-+-+-+-+-+
     98 //   L:   |  T  |U|  S  |D| (CONDITIONALLY RECOMMENDED)
     99 //        +-+-+-+-+-+-+-+-+                             -|
    100 //   P,F: | P_DIFF      |N| (CONDITIONALLY RECOMMENDED)  . up to 3 times
    101 //        +-+-+-+-+-+-+-+-+                             -|
    102 //   V:   | SS            |
    103 //        | ..            |
    104 //        +-+-+-+-+-+-+-+-+
    105 //
    106 // Payload descriptor for non-flexible mode
    107 //        0 1 2 3 4 5 6 7
    108 //        +-+-+-+-+-+-+-+-+
    109 //        |I|P|L|F|B|E|V|-| (REQUIRED)
    110 //        +-+-+-+-+-+-+-+-+
    111 //   I:   |M| PICTURE ID  | (RECOMMENDED)
    112 //        +-+-+-+-+-+-+-+-+
    113 //   M:   | EXTENDED PID  | (RECOMMENDED)
    114 //        +-+-+-+-+-+-+-+-+
    115 //   L:   |  T  |U|  S  |D| (CONDITIONALLY RECOMMENDED)
    116 //        +-+-+-+-+-+-+-+-+
    117 //        |   TL0PICIDX   | (CONDITIONALLY REQUIRED)
    118 //        +-+-+-+-+-+-+-+-+
    119 //   V:   | SS            |
    120 //        | ..            |
    121 //        +-+-+-+-+-+-+-+-+
    122 
    123 class RtpPacketizerVp9Test : public ::testing::Test {
    124  protected:
    125   RtpPacketizerVp9Test() {}
    126   virtual void SetUp() {
    127     expected_.InitRTPVideoHeaderVP9();
    128   }
    129 
    130   rtc::scoped_ptr<uint8_t[]> packet_;
    131   rtc::scoped_ptr<uint8_t[]> payload_;
    132   size_t payload_size_;
    133   size_t payload_pos_;
    134   RTPVideoHeaderVP9 expected_;
    135   rtc::scoped_ptr<RtpPacketizerVp9> packetizer_;
    136 
    137   void Init(size_t payload_size, size_t packet_size) {
    138     payload_.reset(new uint8_t[payload_size]);
    139     memset(payload_.get(), 7, payload_size);
    140     payload_size_ = payload_size;
    141     payload_pos_ = 0;
    142     packetizer_.reset(new RtpPacketizerVp9(expected_, packet_size));
    143     packetizer_->SetPayloadData(payload_.get(), payload_size_, NULL);
    144 
    145     const int kMaxPayloadDescriptorLength = 100;
    146     packet_.reset(new uint8_t[payload_size_ + kMaxPayloadDescriptorLength]);
    147   }
    148 
    149   void CheckPayload(const uint8_t* packet,
    150                     size_t start_pos,
    151                     size_t end_pos,
    152                     bool last) {
    153     for (size_t i = start_pos; i < end_pos; ++i) {
    154       EXPECT_EQ(packet[i], payload_[payload_pos_++]);
    155     }
    156     EXPECT_EQ(last, payload_pos_ == payload_size_);
    157   }
    158 
    159   void CreateParseAndCheckPackets(const size_t* expected_hdr_sizes,
    160                                   const size_t* expected_sizes,
    161                                   size_t expected_num_packets) {
    162     ASSERT_TRUE(packetizer_.get() != NULL);
    163     size_t length = 0;
    164     bool last = false;
    165     if (expected_num_packets == 0) {
    166       EXPECT_FALSE(packetizer_->NextPacket(packet_.get(), &length, &last));
    167       return;
    168     }
    169     for (size_t i = 0; i < expected_num_packets; ++i) {
    170       EXPECT_TRUE(packetizer_->NextPacket(packet_.get(), &length, &last));
    171       EXPECT_EQ(expected_sizes[i], length);
    172       RTPVideoHeaderVP9 hdr = expected_;
    173       hdr.beginning_of_frame = (i == 0);
    174       hdr.end_of_frame = last;
    175       ParseAndCheckPacket(packet_.get(), hdr, expected_hdr_sizes[i], length);
    176       CheckPayload(packet_.get(), expected_hdr_sizes[i], length, last);
    177     }
    178     EXPECT_TRUE(last);
    179   }
    180 };
    181 
    182 TEST_F(RtpPacketizerVp9Test, TestEqualSizedMode_OnePacket) {
    183   const size_t kFrameSize = 25;
    184   const size_t kPacketSize = 26;
    185   Init(kFrameSize, kPacketSize);
    186 
    187   // One packet:
    188   // I:0, P:0, L:0, F:0, B:1, E:1, V:0  (1hdr + 25 payload)
    189   const size_t kExpectedHdrSizes[] = {1};
    190   const size_t kExpectedSizes[] = {26};
    191   const size_t kExpectedNum = GTEST_ARRAY_SIZE_(kExpectedSizes);
    192   CreateParseAndCheckPackets(kExpectedHdrSizes, kExpectedSizes, kExpectedNum);
    193 }
    194 
    195 TEST_F(RtpPacketizerVp9Test, TestEqualSizedMode_TwoPackets) {
    196   const size_t kFrameSize = 27;
    197   const size_t kPacketSize = 27;
    198   Init(kFrameSize, kPacketSize);
    199 
    200   // Two packets:
    201   // I:0, P:0, L:0, F:0, B:1, E:0, V:0  (1hdr + 14 payload)
    202   // I:0, P:0, L:0, F:0, B:0, E:1, V:0  (1hdr + 13 payload)
    203   const size_t kExpectedHdrSizes[] = {1, 1};
    204   const size_t kExpectedSizes[] = {15, 14};
    205   const size_t kExpectedNum = GTEST_ARRAY_SIZE_(kExpectedSizes);
    206   CreateParseAndCheckPackets(kExpectedHdrSizes, kExpectedSizes, kExpectedNum);
    207 }
    208 
    209 TEST_F(RtpPacketizerVp9Test, TestTooShortBufferToFitPayload) {
    210   const size_t kFrameSize = 1;
    211   const size_t kPacketSize = 1;
    212   Init(kFrameSize, kPacketSize);  // 1hdr + 1 payload
    213 
    214   const size_t kExpectedNum = 0;
    215   CreateParseAndCheckPackets(NULL, NULL, kExpectedNum);
    216 }
    217 
    218 TEST_F(RtpPacketizerVp9Test, TestOneBytePictureId) {
    219   const size_t kFrameSize = 30;
    220   const size_t kPacketSize = 12;
    221 
    222   expected_.picture_id = kMaxOneBytePictureId;   // 2 byte payload descriptor
    223   expected_.max_picture_id = kMaxOneBytePictureId;
    224   Init(kFrameSize, kPacketSize);
    225 
    226   // Three packets:
    227   // I:1, P:0, L:0, F:0, B:1, E:0, V:0 (2hdr + 10 payload)
    228   // I:1, P:0, L:0, F:0, B:0, E:0, V:0 (2hdr + 10 payload)
    229   // I:1, P:0, L:0, F:0, B:0, E:1, V:0 (2hdr + 10 payload)
    230   const size_t kExpectedHdrSizes[] = {2, 2, 2};
    231   const size_t kExpectedSizes[] = {12, 12, 12};
    232   const size_t kExpectedNum = GTEST_ARRAY_SIZE_(kExpectedSizes);
    233   CreateParseAndCheckPackets(kExpectedHdrSizes, kExpectedSizes, kExpectedNum);
    234 }
    235 
    236 TEST_F(RtpPacketizerVp9Test, TestTwoBytePictureId) {
    237   const size_t kFrameSize = 31;
    238   const size_t kPacketSize = 13;
    239 
    240   expected_.picture_id = kMaxTwoBytePictureId;  // 3 byte payload descriptor
    241   Init(kFrameSize, kPacketSize);
    242 
    243   // Four packets:
    244   // I:1, P:0, L:0, F:0, B:1, E:0, V:0 (3hdr + 8 payload)
    245   // I:1, P:0, L:0, F:0, B:0, E:0, V:0 (3hdr + 8 payload)
    246   // I:1, P:0, L:0, F:0, B:0, E:0, V:0 (3hdr + 8 payload)
    247   // I:1, P:0, L:0, F:0, B:0, E:1, V:0 (3hdr + 7 payload)
    248   const size_t kExpectedHdrSizes[] = {3, 3, 3, 3};
    249   const size_t kExpectedSizes[] = {11, 11, 11, 10};
    250   const size_t kExpectedNum = GTEST_ARRAY_SIZE_(kExpectedSizes);
    251   CreateParseAndCheckPackets(kExpectedHdrSizes, kExpectedSizes, kExpectedNum);
    252 }
    253 
    254 TEST_F(RtpPacketizerVp9Test, TestLayerInfoWithNonFlexibleMode) {
    255   const size_t kFrameSize = 30;
    256   const size_t kPacketSize = 25;
    257 
    258   expected_.temporal_idx = 3;
    259   expected_.temporal_up_switch = true;  // U
    260   expected_.num_spatial_layers = 3;
    261   expected_.spatial_idx = 2;
    262   expected_.inter_layer_predicted = true;  // D
    263   expected_.tl0_pic_idx = 117;
    264   Init(kFrameSize, kPacketSize);
    265 
    266   // Two packets:
    267   //    | I:0, P:0, L:1, F:0, B:1, E:0, V:0 | (3hdr + 15 payload)
    268   // L: | T:3, U:1, S:2, D:1 | TL0PICIDX:117 |
    269   //    | I:0, P:0, L:1, F:0, B:0, E:1, V:0 | (3hdr + 15 payload)
    270   // L: | T:3, U:1, S:2, D:1 | TL0PICIDX:117 |
    271   const size_t kExpectedHdrSizes[] = {3, 3};
    272   const size_t kExpectedSizes[] = {18, 18};
    273   const size_t kExpectedNum = GTEST_ARRAY_SIZE_(kExpectedSizes);
    274   CreateParseAndCheckPackets(kExpectedHdrSizes, kExpectedSizes, kExpectedNum);
    275 }
    276 
    277 TEST_F(RtpPacketizerVp9Test, TestLayerInfoWithFlexibleMode) {
    278   const size_t kFrameSize = 21;
    279   const size_t kPacketSize = 23;
    280 
    281   expected_.flexible_mode = true;
    282   expected_.temporal_idx = 3;
    283   expected_.temporal_up_switch = true;  // U
    284   expected_.num_spatial_layers = 3;
    285   expected_.spatial_idx = 2;
    286   expected_.inter_layer_predicted = false;  // D
    287   Init(kFrameSize, kPacketSize);
    288 
    289   // One packet:
    290   // I:0, P:0, L:1, F:1, B:1, E:1, V:0 (2hdr + 21 payload)
    291   // L:   T:3, U:1, S:2, D:0
    292   const size_t kExpectedHdrSizes[] = {2};
    293   const size_t kExpectedSizes[] = {23};
    294   const size_t kExpectedNum = GTEST_ARRAY_SIZE_(kExpectedSizes);
    295   CreateParseAndCheckPackets(kExpectedHdrSizes, kExpectedSizes, kExpectedNum);
    296 }
    297 
    298 TEST_F(RtpPacketizerVp9Test, TestRefIdx) {
    299   const size_t kFrameSize = 16;
    300   const size_t kPacketSize = 21;
    301 
    302   expected_.inter_pic_predicted = true;  // P
    303   expected_.flexible_mode = true;        // F
    304   expected_.picture_id = 2;
    305   expected_.max_picture_id = kMaxOneBytePictureId;
    306 
    307   expected_.num_ref_pics = 3;
    308   expected_.pid_diff[0] = 1;
    309   expected_.pid_diff[1] = 3;
    310   expected_.pid_diff[2] = 127;
    311   expected_.ref_picture_id[0] = 1;    // 2 - 1 = 1
    312   expected_.ref_picture_id[1] = 127;  // (kMaxPictureId + 1) + 2 - 3 = 127
    313   expected_.ref_picture_id[2] = 3;    // (kMaxPictureId + 1) + 2 - 127 = 3
    314   Init(kFrameSize, kPacketSize);
    315 
    316   // Two packets:
    317   // I:1, P:1, L:0, F:1, B:1, E:1, V:0 (5hdr + 16 payload)
    318   // I:   2
    319   // P,F: P_DIFF:1,   N:1
    320   //      P_DIFF:3,   N:1
    321   //      P_DIFF:127, N:0
    322   const size_t kExpectedHdrSizes[] = {5};
    323   const size_t kExpectedSizes[] = {21};
    324   const size_t kExpectedNum = GTEST_ARRAY_SIZE_(kExpectedSizes);
    325   CreateParseAndCheckPackets(kExpectedHdrSizes, kExpectedSizes, kExpectedNum);
    326 }
    327 
    328 TEST_F(RtpPacketizerVp9Test, TestRefIdxFailsWithoutPictureId) {
    329   const size_t kFrameSize = 16;
    330   const size_t kPacketSize = 21;
    331 
    332   expected_.inter_pic_predicted = true;
    333   expected_.flexible_mode = true;
    334   expected_.num_ref_pics = 1;
    335   expected_.pid_diff[0] = 3;
    336   Init(kFrameSize, kPacketSize);
    337 
    338   const size_t kExpectedNum = 0;
    339   CreateParseAndCheckPackets(NULL, NULL, kExpectedNum);
    340 }
    341 
    342 TEST_F(RtpPacketizerVp9Test, TestSsDataWithoutSpatialResolutionPresent) {
    343   const size_t kFrameSize = 21;
    344   const size_t kPacketSize = 26;
    345 
    346   expected_.ss_data_available = true;
    347   expected_.num_spatial_layers = 1;
    348   expected_.spatial_layer_resolution_present = false;
    349   expected_.gof.num_frames_in_gof = 1;
    350   expected_.gof.temporal_idx[0] = 0;
    351   expected_.gof.temporal_up_switch[0] = true;
    352   expected_.gof.num_ref_pics[0] = 1;
    353   expected_.gof.pid_diff[0][0] = 4;
    354   Init(kFrameSize, kPacketSize);
    355 
    356   // One packet:
    357   // I:0, P:0, L:0, F:0, B:1, E:1, V:1 (5hdr + 21 payload)
    358   // N_S:0, Y:0, G:1
    359   // N_G:1
    360   // T:0, U:1, R:1 | P_DIFF[0][0]:4
    361   const size_t kExpectedHdrSizes[] = {5};
    362   const size_t kExpectedSizes[] = {26};
    363   const size_t kExpectedNum = GTEST_ARRAY_SIZE_(kExpectedSizes);
    364   CreateParseAndCheckPackets(kExpectedHdrSizes, kExpectedSizes, kExpectedNum);
    365 }
    366 
    367 TEST_F(RtpPacketizerVp9Test, TestSsDataWithoutGbitPresent) {
    368   const size_t kFrameSize = 21;
    369   const size_t kPacketSize = 23;
    370 
    371   expected_.ss_data_available = true;
    372   expected_.num_spatial_layers = 1;
    373   expected_.spatial_layer_resolution_present = false;
    374   expected_.gof.num_frames_in_gof = 0;
    375   Init(kFrameSize, kPacketSize);
    376 
    377   // One packet:
    378   // I:0, P:0, L:0, F:0, B:1, E:1, V:1 (2hdr + 21 payload)
    379   // N_S:0, Y:0, G:0
    380   const size_t kExpectedHdrSizes[] = {2};
    381   const size_t kExpectedSizes[] = {23};
    382   const size_t kExpectedNum = GTEST_ARRAY_SIZE_(kExpectedSizes);
    383   CreateParseAndCheckPackets(kExpectedHdrSizes, kExpectedSizes, kExpectedNum);
    384 }
    385 
    386 TEST_F(RtpPacketizerVp9Test, TestSsData) {
    387   const size_t kFrameSize = 21;
    388   const size_t kPacketSize = 40;
    389 
    390   expected_.ss_data_available = true;
    391   expected_.num_spatial_layers = 2;
    392   expected_.spatial_layer_resolution_present = true;
    393   expected_.width[0] = 640;
    394   expected_.width[1] = 1280;
    395   expected_.height[0] = 360;
    396   expected_.height[1] = 720;
    397   expected_.gof.num_frames_in_gof = 3;
    398   expected_.gof.temporal_idx[0] = 0;
    399   expected_.gof.temporal_idx[1] = 1;
    400   expected_.gof.temporal_idx[2] = 2;
    401   expected_.gof.temporal_up_switch[0] = true;
    402   expected_.gof.temporal_up_switch[1] = true;
    403   expected_.gof.temporal_up_switch[2] = false;
    404   expected_.gof.num_ref_pics[0] = 0;
    405   expected_.gof.num_ref_pics[1] = 3;
    406   expected_.gof.num_ref_pics[2] = 2;
    407   expected_.gof.pid_diff[1][0] = 5;
    408   expected_.gof.pid_diff[1][1] = 6;
    409   expected_.gof.pid_diff[1][2] = 7;
    410   expected_.gof.pid_diff[2][0] = 8;
    411   expected_.gof.pid_diff[2][1] = 9;
    412   Init(kFrameSize, kPacketSize);
    413 
    414   // One packet:
    415   // I:0, P:0, L:0, F:0, B:1, E:1, V:1 (19hdr + 21 payload)
    416   // N_S:1, Y:1, G:1
    417   // WIDTH:640   // 2 bytes
    418   // HEIGHT:360  // 2 bytes
    419   // WIDTH:1280  // 2 bytes
    420   // HEIGHT:720  // 2 bytes
    421   // N_G:3
    422   // T:0, U:1, R:0
    423   // T:1, U:1, R:3 | P_DIFF[1][0]:5 | P_DIFF[1][1]:6 | P_DIFF[1][2]:7
    424   // T:2, U:0, R:2 | P_DIFF[2][0]:8 | P_DIFF[2][0]:9
    425   const size_t kExpectedHdrSizes[] = {19};
    426   const size_t kExpectedSizes[] = {40};
    427   const size_t kExpectedNum = GTEST_ARRAY_SIZE_(kExpectedSizes);
    428   CreateParseAndCheckPackets(kExpectedHdrSizes, kExpectedSizes, kExpectedNum);
    429 }
    430 
    431 TEST_F(RtpPacketizerVp9Test, TestBaseLayerProtectionAndStorageType) {
    432   const size_t kFrameSize = 10;
    433   const size_t kPacketSize = 12;
    434 
    435   // I:0, P:0, L:1, F:1, B:1, E:1, V:0 (2hdr + 10 payload)
    436   // L:   T:0, U:0, S:0, D:0
    437   expected_.flexible_mode = true;
    438   expected_.temporal_idx = 0;
    439   Init(kFrameSize, kPacketSize);
    440   EXPECT_EQ(kProtectedPacket, packetizer_->GetProtectionType());
    441   EXPECT_EQ(kAllowRetransmission,
    442             packetizer_->GetStorageType(kRetransmitBaseLayer));
    443   EXPECT_EQ(kDontRetransmit, packetizer_->GetStorageType(kRetransmitOff));
    444 }
    445 
    446 TEST_F(RtpPacketizerVp9Test, TestHigherLayerProtectionAndStorageType) {
    447   const size_t kFrameSize = 10;
    448   const size_t kPacketSize = 12;
    449 
    450   // I:0, P:0, L:1, F:1, B:1, E:1, V:0 (2hdr + 10 payload)
    451   // L:   T:1, U:0, S:0, D:0
    452   expected_.flexible_mode = true;
    453   expected_.temporal_idx = 1;
    454   Init(kFrameSize, kPacketSize);
    455   EXPECT_EQ(kUnprotectedPacket, packetizer_->GetProtectionType());
    456   EXPECT_EQ(kDontRetransmit, packetizer_->GetStorageType(kRetransmitBaseLayer));
    457   EXPECT_EQ(kAllowRetransmission,
    458             packetizer_->GetStorageType(kRetransmitHigherLayers));
    459 }
    460 
    461 
    462 class RtpDepacketizerVp9Test : public ::testing::Test {
    463  protected:
    464   RtpDepacketizerVp9Test()
    465       : depacketizer_(new RtpDepacketizerVp9()) {}
    466 
    467   virtual void SetUp() {
    468     expected_.InitRTPVideoHeaderVP9();
    469   }
    470 
    471   RTPVideoHeaderVP9 expected_;
    472   rtc::scoped_ptr<RtpDepacketizer> depacketizer_;
    473 };
    474 
    475 TEST_F(RtpDepacketizerVp9Test, ParseBasicHeader) {
    476   const uint8_t kHeaderLength = 1;
    477   uint8_t packet[4] = {0};
    478   packet[0] = 0x0C;  // I:0 P:0 L:0 F:0 B:1 E:1 V:0 R:0
    479   expected_.beginning_of_frame = true;
    480   expected_.end_of_frame = true;
    481   ParseAndCheckPacket(packet, expected_, kHeaderLength, sizeof(packet));
    482 }
    483 
    484 TEST_F(RtpDepacketizerVp9Test, ParseOneBytePictureId) {
    485   const uint8_t kHeaderLength = 2;
    486   uint8_t packet[10] = {0};
    487   packet[0] = 0x80;  // I:1 P:0 L:0 F:0 B:0 E:0 V:0 R:0
    488   packet[1] = kMaxOneBytePictureId;
    489 
    490   expected_.picture_id = kMaxOneBytePictureId;
    491   expected_.max_picture_id = kMaxOneBytePictureId;
    492   ParseAndCheckPacket(packet, expected_, kHeaderLength, sizeof(packet));
    493 }
    494 
    495 TEST_F(RtpDepacketizerVp9Test, ParseTwoBytePictureId) {
    496   const uint8_t kHeaderLength = 3;
    497   uint8_t packet[10] = {0};
    498   packet[0] = 0x80;  // I:1 P:0 L:0 F:0 B:0 E:0 V:0 R:0
    499   packet[1] = 0x80 | ((kMaxTwoBytePictureId >> 8) & 0x7F);
    500   packet[2] = kMaxTwoBytePictureId & 0xFF;
    501 
    502   expected_.picture_id = kMaxTwoBytePictureId;
    503   expected_.max_picture_id = kMaxTwoBytePictureId;
    504   ParseAndCheckPacket(packet, expected_, kHeaderLength, sizeof(packet));
    505 }
    506 
    507 TEST_F(RtpDepacketizerVp9Test, ParseLayerInfoWithNonFlexibleMode) {
    508   const uint8_t kHeaderLength = 3;
    509   const uint8_t kTemporalIdx = 2;
    510   const uint8_t kUbit = 1;
    511   const uint8_t kSpatialIdx = 1;
    512   const uint8_t kDbit = 1;
    513   const uint8_t kTl0PicIdx = 17;
    514   uint8_t packet[13] = {0};
    515   packet[0] = 0x20;  // I:0 P:0 L:1 F:0 B:0 E:0 V:0 R:0
    516   packet[1] = (kTemporalIdx << 5) | (kUbit << 4) | (kSpatialIdx << 1) | kDbit;
    517   packet[2] = kTl0PicIdx;
    518 
    519   // T:2 U:1 S:1 D:1
    520   // TL0PICIDX:17
    521   expected_.temporal_idx = kTemporalIdx;
    522   expected_.temporal_up_switch = kUbit ? true : false;
    523   expected_.spatial_idx = kSpatialIdx;
    524   expected_.inter_layer_predicted = kDbit ? true : false;
    525   expected_.tl0_pic_idx = kTl0PicIdx;
    526   ParseAndCheckPacket(packet, expected_, kHeaderLength, sizeof(packet));
    527 }
    528 
    529 TEST_F(RtpDepacketizerVp9Test, ParseLayerInfoWithFlexibleMode) {
    530   const uint8_t kHeaderLength = 2;
    531   const uint8_t kTemporalIdx = 2;
    532   const uint8_t kUbit = 1;
    533   const uint8_t kSpatialIdx = 0;
    534   const uint8_t kDbit = 0;
    535   uint8_t packet[13] = {0};
    536   packet[0] = 0x38;  // I:0 P:0 L:1 F:1 B:1 E:0 V:0 R:0
    537   packet[1] = (kTemporalIdx << 5) | (kUbit << 4) | (kSpatialIdx << 1) | kDbit;
    538 
    539   // I:0 P:0 L:1 F:1 B:1 E:0 V:0
    540   // L:   T:2 U:1 S:0 D:0
    541   expected_.beginning_of_frame = true;
    542   expected_.flexible_mode = true;
    543   expected_.temporal_idx = kTemporalIdx;
    544   expected_.temporal_up_switch = kUbit ? true : false;
    545   expected_.spatial_idx = kSpatialIdx;
    546   expected_.inter_layer_predicted = kDbit ? true : false;
    547   ParseAndCheckPacket(packet, expected_, kHeaderLength, sizeof(packet));
    548 }
    549 
    550 TEST_F(RtpDepacketizerVp9Test, ParseRefIdx) {
    551   const uint8_t kHeaderLength = 6;
    552   const int16_t kPictureId = 17;
    553   const uint8_t kPdiff1 = 17;
    554   const uint8_t kPdiff2 = 18;
    555   const uint8_t kPdiff3 = 127;
    556   uint8_t packet[13] = {0};
    557   packet[0] = 0xD8;  // I:1 P:1 L:0 F:1 B:1 E:0 V:0 R:0
    558   packet[1] = 0x80 | ((kPictureId >> 8) & 0x7F);  // Two byte pictureID.
    559   packet[2] = kPictureId;
    560   packet[3] = (kPdiff1 << 1) | 1;  // P_DIFF N:1
    561   packet[4] = (kPdiff2 << 1) | 1;  // P_DIFF N:1
    562   packet[5] = (kPdiff3 << 1) | 0;  // P_DIFF N:0
    563 
    564   // I:1 P:1 L:0 F:1 B:1 E:0 V:0
    565   // I:    PICTURE ID:17
    566   // I:
    567   // P,F:  P_DIFF:17  N:1 => refPicId = 17 - 17 = 0
    568   // P,F:  P_DIFF:18  N:1 => refPicId = (kMaxPictureId + 1) + 17 - 18 = 0x7FFF
    569   // P,F:  P_DIFF:127 N:0 => refPicId = (kMaxPictureId + 1) + 17 - 127 = 32658
    570   expected_.beginning_of_frame = true;
    571   expected_.inter_pic_predicted = true;
    572   expected_.flexible_mode = true;
    573   expected_.picture_id = kPictureId;
    574   expected_.num_ref_pics = 3;
    575   expected_.pid_diff[0] = kPdiff1;
    576   expected_.pid_diff[1] = kPdiff2;
    577   expected_.pid_diff[2] = kPdiff3;
    578   expected_.ref_picture_id[0] = 0;
    579   expected_.ref_picture_id[1] = 0x7FFF;
    580   expected_.ref_picture_id[2] = 32658;
    581   ParseAndCheckPacket(packet, expected_, kHeaderLength, sizeof(packet));
    582 }
    583 
    584 TEST_F(RtpDepacketizerVp9Test, ParseRefIdxFailsWithNoPictureId) {
    585   const uint8_t kPdiff = 3;
    586   uint8_t packet[13] = {0};
    587   packet[0] = 0x58;            // I:0 P:1 L:0 F:1 B:1 E:0 V:0 R:0
    588   packet[1] = (kPdiff << 1);   // P,F:  P_DIFF:3 N:0
    589 
    590   RtpDepacketizer::ParsedPayload parsed;
    591   EXPECT_FALSE(depacketizer_->Parse(&parsed, packet, sizeof(packet)));
    592 }
    593 
    594 TEST_F(RtpDepacketizerVp9Test, ParseRefIdxFailsWithTooManyRefPics) {
    595   const uint8_t kPdiff = 3;
    596   uint8_t packet[13] = {0};
    597   packet[0] = 0xD8;                  // I:1 P:1 L:0 F:1 B:1 E:0 V:0 R:0
    598   packet[1] = kMaxOneBytePictureId;  // I:    PICTURE ID:127
    599   packet[2] = (kPdiff << 1) | 1;     // P,F:  P_DIFF:3 N:1
    600   packet[3] = (kPdiff << 1) | 1;     // P,F:  P_DIFF:3 N:1
    601   packet[4] = (kPdiff << 1) | 1;     // P,F:  P_DIFF:3 N:1
    602   packet[5] = (kPdiff << 1) | 0;     // P,F:  P_DIFF:3 N:0
    603 
    604   RtpDepacketizer::ParsedPayload parsed;
    605   EXPECT_FALSE(depacketizer_->Parse(&parsed, packet, sizeof(packet)));
    606 }
    607 
    608 TEST_F(RtpDepacketizerVp9Test, ParseSsData) {
    609   const uint8_t kHeaderLength = 6;
    610   const uint8_t kYbit = 0;
    611   const size_t kNs = 2;
    612   const size_t kNg = 2;
    613   uint8_t packet[23] = {0};
    614   packet[0] = 0x0A;  // I:0 P:0 L:0 F:0 B:1 E:0 V:1 R:0
    615   packet[1] = ((kNs - 1) << 5) | (kYbit << 4) | (1 << 3);  // N_S Y G:1 -
    616   packet[2] = kNg;                                         // N_G
    617   packet[3] = (0 << 5) | (1 << 4) | (0 << 2) | 0;          // T:0 U:1 R:0 -
    618   packet[4] = (2 << 5) | (0 << 4) | (1 << 2) | 0;          // T:2 U:0 R:1 -
    619   packet[5] = 33;
    620 
    621   expected_.beginning_of_frame = true;
    622   expected_.ss_data_available = true;
    623   expected_.num_spatial_layers = kNs;
    624   expected_.spatial_layer_resolution_present = kYbit ? true : false;
    625   expected_.gof.num_frames_in_gof = kNg;
    626   expected_.gof.temporal_idx[0] = 0;
    627   expected_.gof.temporal_idx[1] = 2;
    628   expected_.gof.temporal_up_switch[0] = true;
    629   expected_.gof.temporal_up_switch[1] = false;
    630   expected_.gof.num_ref_pics[0] = 0;
    631   expected_.gof.num_ref_pics[1] = 1;
    632   expected_.gof.pid_diff[1][0] = 33;
    633   ParseAndCheckPacket(packet, expected_, kHeaderLength, sizeof(packet));
    634 }
    635 
    636 TEST_F(RtpDepacketizerVp9Test, ParseFirstPacketInKeyFrame) {
    637   uint8_t packet[2] = {0};
    638   packet[0] = 0x08;  // I:0 P:0 L:0 F:0 B:1 E:0 V:0 R:0
    639 
    640   RtpDepacketizer::ParsedPayload parsed;
    641   ASSERT_TRUE(depacketizer_->Parse(&parsed, packet, sizeof(packet)));
    642   EXPECT_EQ(kVideoFrameKey, parsed.frame_type);
    643   EXPECT_TRUE(parsed.type.Video.isFirstPacket);
    644 }
    645 
    646 TEST_F(RtpDepacketizerVp9Test, ParseLastPacketInDeltaFrame) {
    647   uint8_t packet[2] = {0};
    648   packet[0] = 0x44;  // I:0 P:1 L:0 F:0 B:0 E:1 V:0 R:0
    649 
    650   RtpDepacketizer::ParsedPayload parsed;
    651   ASSERT_TRUE(depacketizer_->Parse(&parsed, packet, sizeof(packet)));
    652   EXPECT_EQ(kVideoFrameDelta, parsed.frame_type);
    653   EXPECT_FALSE(parsed.type.Video.isFirstPacket);
    654 }
    655 
    656 TEST_F(RtpDepacketizerVp9Test, ParseResolution) {
    657   const uint16_t kWidth[2] = {640, 1280};
    658   const uint16_t kHeight[2] = {360, 720};
    659   uint8_t packet[20] = {0};
    660   packet[0] = 0x0A;  // I:0 P:0 L:0 F:0 B:1 E:0 V:1 R:0
    661   packet[1] = (1 << 5) | (1 << 4) | 0;  // N_S:1 Y:1 G:0
    662   packet[2] = kWidth[0] >> 8;
    663   packet[3] = kWidth[0] & 0xFF;
    664   packet[4] = kHeight[0] >> 8;
    665   packet[5] = kHeight[0] & 0xFF;
    666   packet[6] = kWidth[1] >> 8;
    667   packet[7] = kWidth[1] & 0xFF;
    668   packet[8] = kHeight[1] >> 8;
    669   packet[9] = kHeight[1] & 0xFF;
    670 
    671   RtpDepacketizer::ParsedPayload parsed;
    672   ASSERT_TRUE(depacketizer_->Parse(&parsed, packet, sizeof(packet)));
    673   EXPECT_EQ(kWidth[0], parsed.type.Video.width);
    674   EXPECT_EQ(kHeight[0], parsed.type.Video.height);
    675 }
    676 
    677 TEST_F(RtpDepacketizerVp9Test, ParseFailsForNoPayloadLength) {
    678   uint8_t packet[1] = {0};
    679   RtpDepacketizer::ParsedPayload parsed;
    680   EXPECT_FALSE(depacketizer_->Parse(&parsed, packet, 0));
    681 }
    682 
    683 TEST_F(RtpDepacketizerVp9Test, ParseFailsForTooShortBufferToFitPayload) {
    684   const uint8_t kHeaderLength = 1;
    685   uint8_t packet[kHeaderLength] = {0};
    686   RtpDepacketizer::ParsedPayload parsed;
    687   EXPECT_FALSE(depacketizer_->Parse(&parsed, packet, sizeof(packet)));
    688 }
    689 
    690 }  // namespace webrtc
    691