Home | History | Annotate | Download | only in rtcp
      1 // Copyright 2013 The Chromium Authors. All rights reserved.
      2 // Use of this source code is governed by a BSD-style license that can be
      3 // found in the LICENSE file.
      4 
      5 #include "media/cast/rtcp/rtcp_utility.h"
      6 
      7 #include "base/logging.h"
      8 #include "net/base/big_endian.h"
      9 
     10 namespace media {
     11 namespace cast {
     12 
     13 RtcpParser::RtcpParser(const uint8* rtcpData, size_t rtcpDataLength)
     14     : rtcp_data_begin_(rtcpData),
     15       rtcp_data_end_(rtcpData + rtcpDataLength),
     16       valid_packet_(false),
     17       rtcp_data_(rtcpData),
     18       rtcp_block_end_(NULL),
     19       state_(kStateTopLevel),
     20       number_of_blocks_(0),
     21       field_type_(kRtcpNotValidCode) {
     22   Validate();
     23 }
     24 
     25 RtcpParser::~RtcpParser() {}
     26 
     27 RtcpFieldTypes RtcpParser::FieldType() const {
     28   return field_type_;
     29 }
     30 
     31 const RtcpField& RtcpParser::Field() const {
     32   return field_;
     33 }
     34 
     35 RtcpFieldTypes RtcpParser::Begin() {
     36   rtcp_data_ = rtcp_data_begin_;
     37   return Iterate();
     38 }
     39 
     40 RtcpFieldTypes RtcpParser::Iterate() {
     41   // Reset packet type
     42   field_type_ = kRtcpNotValidCode;
     43 
     44   if (!IsValid()) return kRtcpNotValidCode;
     45 
     46   switch (state_) {
     47     case kStateTopLevel:
     48       IterateTopLevel();
     49       break;
     50     case kStateReportBlock:
     51       IterateReportBlockItem();
     52       break;
     53     case kStateSdes:
     54       IterateSdesItem();
     55       break;
     56     case kStateBye:
     57       IterateByeItem();
     58       break;
     59     case kStateApplicationSpecificCastReceiverFrameLog:
     60       IterateCastReceiverLogFrame();
     61       break;
     62     case kStateApplicationSpecificCastReceiverEventLog:
     63       IterateCastReceiverLogEvent();
     64       break;
     65     case kStateApplicationSpecificCastSenderLog:
     66       IterateCastSenderLog();
     67       break;
     68     case kStateExtendedReportBlock:
     69       IterateExtendedReportItem();
     70       break;
     71     case kStateExtendedReportDelaySinceLastReceiverReport:
     72       IterateExtendedReportDelaySinceLastReceiverReportItem();
     73       break;
     74     case kStateGenericRtpFeedbackNack:
     75       IterateNackItem();
     76       break;
     77     case kStatePayloadSpecificRpsi:
     78       IterateRpsiItem();
     79       break;
     80     case kStatePayloadSpecificFir:
     81       IterateFirItem();
     82       break;
     83     case kStatePayloadSpecificApplication:
     84       IteratePayloadSpecificAppItem();
     85       break;
     86     case kStatePayloadSpecificRemb:
     87       IteratePayloadSpecificRembItem();
     88       break;
     89     case kStatePayloadSpecificCast:
     90       IteratePayloadSpecificCastItem();
     91       break;
     92     case kStatePayloadSpecificCastNack:
     93       IteratePayloadSpecificCastNackItem();
     94       break;
     95   }
     96   return field_type_;
     97 }
     98 
     99 void RtcpParser::IterateTopLevel() {
    100   for (;;) {
    101     RtcpCommonHeader header;
    102 
    103     bool success = RtcpParseCommonHeader(rtcp_data_, rtcp_data_end_, &header);
    104     if (!success) return;
    105 
    106     rtcp_block_end_ = rtcp_data_ + header.length_in_octets;
    107 
    108     if (rtcp_block_end_ > rtcp_data_end_) return;  // Bad block!
    109 
    110     switch (header.PT) {
    111       case kPacketTypeSenderReport:
    112         // number of Report blocks
    113         number_of_blocks_ = header.IC;
    114         ParseSR();
    115         return;
    116       case kPacketTypeReceiverReport:
    117         // number of Report blocks
    118         number_of_blocks_ = header.IC;
    119         ParseRR();
    120         return;
    121       case kPacketTypeSdes:
    122         // number of Sdes blocks
    123         number_of_blocks_ = header.IC;
    124         if (!ParseSdes()) {
    125           break;  // Nothing supported found, continue to next block!
    126         }
    127         return;
    128       case kPacketTypeBye:
    129         number_of_blocks_ = header.IC;
    130         if (!ParseBye()) {
    131           // Nothing supported found, continue to next block!
    132           break;
    133         }
    134         return;
    135       case kPacketTypeApplicationDefined:
    136         if (!ParseApplicationDefined(header.IC)) {
    137           // Nothing supported found, continue to next block!
    138           break;
    139         }
    140         return;
    141       case kPacketTypeGenericRtpFeedback:  // Fall through!
    142       case kPacketTypePayloadSpecific:
    143         if (!ParseFeedBackCommon(header)) {
    144           // Nothing supported found, continue to next block!
    145           break;
    146         }
    147         return;
    148       case kPacketTypeXr:
    149         if (!ParseExtendedReport()) {
    150           break;  // Nothing supported found, continue to next block!
    151         }
    152         return;
    153       default:
    154         // Not supported! Skip!
    155         EndCurrentBlock();
    156         break;
    157     }
    158   }
    159 }
    160 
    161 void RtcpParser::IterateReportBlockItem() {
    162   bool success = ParseReportBlockItem();
    163   if (!success) Iterate();
    164 }
    165 
    166 void RtcpParser::IterateSdesItem() {
    167   bool success = ParseSdesItem();
    168   if (!success) Iterate();
    169 }
    170 
    171 void RtcpParser::IterateByeItem() {
    172   bool success = ParseByeItem();
    173   if (!success) Iterate();
    174 }
    175 
    176 void RtcpParser::IterateExtendedReportItem() {
    177   bool success = ParseExtendedReportItem();
    178   if (!success) Iterate();
    179 }
    180 
    181 void RtcpParser::IterateExtendedReportDelaySinceLastReceiverReportItem() {
    182   bool success = ParseExtendedReportDelaySinceLastReceiverReport();
    183   if (!success) Iterate();
    184 }
    185 
    186 void RtcpParser::IterateNackItem() {
    187   bool success = ParseNackItem();
    188   if (!success) Iterate();
    189 }
    190 
    191 void RtcpParser::IterateRpsiItem() {
    192   bool success = ParseRpsiItem();
    193   if (!success) Iterate();
    194 }
    195 
    196 void RtcpParser::IterateFirItem() {
    197   bool success = ParseFirItem();
    198   if (!success) Iterate();
    199 }
    200 
    201 void RtcpParser::IteratePayloadSpecificAppItem() {
    202   bool success = ParsePayloadSpecificAppItem();
    203   if (!success) Iterate();
    204 }
    205 
    206 void RtcpParser::IteratePayloadSpecificRembItem() {
    207   bool success = ParsePayloadSpecificRembItem();
    208   if (!success) Iterate();
    209 }
    210 
    211 void RtcpParser::IteratePayloadSpecificCastItem() {
    212   bool success = ParsePayloadSpecificCastItem();
    213   if (!success) Iterate();
    214 }
    215 
    216 void RtcpParser::IteratePayloadSpecificCastNackItem() {
    217   bool success = ParsePayloadSpecificCastNackItem();
    218   if (!success) Iterate();
    219 }
    220 
    221 void RtcpParser::IterateCastReceiverLogFrame() {
    222   bool success = ParseCastReceiverLogFrameItem();
    223   if (!success) Iterate();
    224 }
    225 
    226 void RtcpParser::IterateCastReceiverLogEvent() {
    227   bool success = ParseCastReceiverLogEventItem();
    228   if (!success) Iterate();
    229 }
    230 
    231 void RtcpParser::IterateCastSenderLog() {
    232   bool success = ParseCastSenderLogItem();
    233   if (!success) Iterate();
    234 }
    235 
    236 void RtcpParser::Validate() {
    237   if (rtcp_data_ == NULL) return;  // NOT VALID
    238 
    239   RtcpCommonHeader header;
    240   bool success = RtcpParseCommonHeader(rtcp_data_begin_, rtcp_data_end_,
    241                                        &header);
    242 
    243   if (!success) return;  // NOT VALID!
    244 
    245   valid_packet_ = true;
    246 }
    247 
    248 bool RtcpParser::IsValid() const {
    249   return valid_packet_;
    250 }
    251 
    252 void RtcpParser::EndCurrentBlock() {
    253   rtcp_data_ = rtcp_block_end_;
    254 }
    255 
    256 bool RtcpParser::RtcpParseCommonHeader(const uint8* data_begin,
    257                                        const uint8* data_end,
    258                                        RtcpCommonHeader* parsed_header) const {
    259   if (!data_begin || !data_end) return false;
    260 
    261   //  0                   1                   2                   3
    262   //  0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
    263   // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
    264   // |V=2|P|    IC   |      PT       |             length            |
    265   // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
    266   //
    267   // Common header for all Rtcp packets, 4 octets.
    268 
    269   if ((data_end - data_begin) < 4) return false;
    270 
    271   parsed_header->V  = data_begin[0] >> 6;
    272   parsed_header->P  = ((data_begin[0] & 0x20) == 0) ? false : true;
    273   parsed_header->IC = data_begin[0] & 0x1f;
    274   parsed_header->PT = data_begin[1];
    275 
    276   parsed_header->length_in_octets =
    277       ((data_begin[2] << 8) + data_begin[3] + 1) * 4;
    278 
    279   if (parsed_header->length_in_octets == 0) return false;
    280 
    281   // Check if RTP version field == 2.
    282   if (parsed_header->V != 2) return false;
    283 
    284   return true;
    285 }
    286 
    287 bool RtcpParser::ParseRR() {
    288   ptrdiff_t length = rtcp_block_end_ - rtcp_data_;
    289   if (length < 8) return false;
    290 
    291   field_type_ = kRtcpRrCode;
    292 
    293   net::BigEndianReader big_endian_reader(rtcp_data_, length);
    294   big_endian_reader.Skip(4);  // Skip header
    295   big_endian_reader.ReadU32(&field_.receiver_report.sender_ssrc);
    296   field_.receiver_report.number_of_report_blocks = number_of_blocks_;
    297   rtcp_data_ += 8;
    298 
    299   // State transition
    300   state_ = kStateReportBlock;
    301   return true;
    302 }
    303 
    304 bool RtcpParser::ParseSR() {
    305   ptrdiff_t length = rtcp_block_end_ - rtcp_data_;
    306   if (length < 28) {
    307     EndCurrentBlock();
    308     return false;
    309   }
    310   field_type_ = kRtcpSrCode;
    311 
    312   net::BigEndianReader big_endian_reader(rtcp_data_, length);
    313   big_endian_reader.Skip(4);  // Skip header
    314   big_endian_reader.ReadU32(&field_.sender_report.sender_ssrc);
    315   big_endian_reader.ReadU32(&field_.sender_report.ntp_most_significant);
    316   big_endian_reader.ReadU32(&field_.sender_report.ntp_least_significant);
    317   big_endian_reader.ReadU32(&field_.sender_report.rtp_timestamp);
    318   big_endian_reader.ReadU32(&field_.sender_report.sender_packet_count);
    319   big_endian_reader.ReadU32(&field_.sender_report.sender_octet_count);
    320   field_.sender_report.number_of_report_blocks = number_of_blocks_;
    321   rtcp_data_ += 28;
    322 
    323   if (number_of_blocks_ != 0) {
    324     // State transition.
    325     state_ = kStateReportBlock;
    326   } else {
    327     // Don't go to state report block item if 0 report blocks.
    328     state_ = kStateTopLevel;
    329     EndCurrentBlock();
    330   }
    331   return true;
    332 }
    333 
    334 bool RtcpParser::ParseReportBlockItem() {
    335   ptrdiff_t length = rtcp_block_end_ - rtcp_data_;
    336   if (length < 24 || number_of_blocks_ <= 0) {
    337     state_ = kStateTopLevel;
    338     EndCurrentBlock();
    339     return false;
    340   }
    341 
    342   net::BigEndianReader big_endian_reader(rtcp_data_, length);
    343   big_endian_reader.ReadU32(&field_.report_block_item.ssrc);
    344   big_endian_reader.ReadU8(&field_.report_block_item.fraction_lost);
    345 
    346   uint8 temp_number_of_packets_lost;
    347   big_endian_reader.ReadU8(&temp_number_of_packets_lost);
    348   field_.report_block_item.cumulative_number_of_packets_lost =
    349       temp_number_of_packets_lost << 16;
    350   big_endian_reader.ReadU8(&temp_number_of_packets_lost);
    351   field_.report_block_item.cumulative_number_of_packets_lost +=
    352       temp_number_of_packets_lost << 8;
    353   big_endian_reader.ReadU8(&temp_number_of_packets_lost);
    354   field_.report_block_item.cumulative_number_of_packets_lost +=
    355       temp_number_of_packets_lost;
    356 
    357   big_endian_reader.ReadU32(
    358       &field_.report_block_item.extended_highest_sequence_number);
    359   big_endian_reader.ReadU32(&field_.report_block_item.jitter);
    360   big_endian_reader.ReadU32(&field_.report_block_item.last_sender_report);
    361   big_endian_reader.ReadU32(&field_.report_block_item.delay_last_sender_report);
    362   rtcp_data_ += 24;
    363 
    364   number_of_blocks_--;
    365   field_type_ = kRtcpReportBlockItemCode;
    366   return true;
    367 }
    368 
    369 bool RtcpParser::ParseSdes() {
    370   ptrdiff_t length = rtcp_block_end_ - rtcp_data_;
    371 
    372   if (length < 8) {
    373     state_ = kStateTopLevel;
    374     EndCurrentBlock();
    375     return false;
    376   }
    377   rtcp_data_ += 4;  // Skip header
    378 
    379   state_ = kStateSdes;
    380   field_type_ = kRtcpSdesCode;
    381   return true;
    382 }
    383 
    384 bool RtcpParser::ParseSdesItem() {
    385   if (number_of_blocks_ <= 0) {
    386     state_ = kStateTopLevel;
    387     EndCurrentBlock();
    388     return false;
    389   }
    390   number_of_blocks_--;
    391 
    392   // Find c_name item in a Sdes chunk.
    393   while (rtcp_data_ < rtcp_block_end_) {
    394     ptrdiff_t data_length = rtcp_block_end_ - rtcp_data_;
    395     if (data_length < 4) {
    396       state_ = kStateTopLevel;
    397       EndCurrentBlock();
    398       return false;
    399     }
    400 
    401     uint32 ssrc;
    402     net::BigEndianReader big_endian_reader(rtcp_data_, data_length);
    403     big_endian_reader.ReadU32(&ssrc);
    404     rtcp_data_ += 4;
    405 
    406     bool found_c_name = ParseSdesTypes();
    407     if (found_c_name) {
    408       field_.c_name.sender_ssrc = ssrc;
    409       return true;
    410     }
    411   }
    412   state_ = kStateTopLevel;
    413   EndCurrentBlock();
    414   return false;
    415 }
    416 
    417 bool RtcpParser::ParseSdesTypes() {
    418   // Only the c_name item is mandatory. RFC 3550 page 46.
    419   bool found_c_name = false;
    420   ptrdiff_t length = rtcp_block_end_ - rtcp_data_;
    421   net::BigEndianReader big_endian_reader(rtcp_data_, length);
    422 
    423   while (big_endian_reader.remaining() > 0) {
    424     uint8 tag;
    425     big_endian_reader.ReadU8(&tag);
    426 
    427     if (tag == 0) {
    428       // End tag! 4 octet aligned.
    429       rtcp_data_ = rtcp_block_end_;
    430       return found_c_name;
    431     }
    432 
    433     if (big_endian_reader.remaining() > 0) {
    434       uint8 len;
    435       big_endian_reader.ReadU8(&len);
    436 
    437       if (tag == 1) {  // c_name.
    438         // Sanity check.
    439         if (big_endian_reader.remaining() < len) {
    440           state_ = kStateTopLevel;
    441           EndCurrentBlock();
    442           return false;
    443         }
    444         int i = 0;
    445         for (; i < len; ++i) {
    446           uint8 c;
    447           big_endian_reader.ReadU8(&c);
    448           if ((c < ' ') || (c > '{') || (c == '%') || (c == '\\')) {
    449             // Illegal char.
    450             state_ = kStateTopLevel;
    451             EndCurrentBlock();
    452             return false;
    453           }
    454           field_.c_name.name[i] = c;
    455         }
    456         // Make sure we are null terminated.
    457         field_.c_name.name[i] = 0;
    458         field_type_ = kRtcpSdesChunkCode;
    459         found_c_name = true;
    460       } else {
    461         big_endian_reader.Skip(len);
    462       }
    463     }
    464   }
    465   // No end tag found!
    466   state_ = kStateTopLevel;
    467   EndCurrentBlock();
    468   return false;
    469 }
    470 
    471 bool RtcpParser::ParseBye() {
    472   rtcp_data_ += 4;  // Skip header.
    473   state_ = kStateBye;
    474   return ParseByeItem();
    475 }
    476 
    477 bool RtcpParser::ParseByeItem() {
    478   ptrdiff_t length = rtcp_block_end_ - rtcp_data_;
    479   if (length < 4 || number_of_blocks_ == 0) {
    480     state_ = kStateTopLevel;
    481     EndCurrentBlock();
    482     return false;
    483   }
    484 
    485   field_type_ = kRtcpByeCode;
    486 
    487   net::BigEndianReader big_endian_reader(rtcp_data_, length);
    488   big_endian_reader.ReadU32(&field_.bye.sender_ssrc);
    489   rtcp_data_ += 4;
    490 
    491   // We can have several CSRCs attached.
    492   if (length >= 4 * number_of_blocks_) {
    493     rtcp_data_ += (number_of_blocks_ - 1) * 4;
    494   }
    495   number_of_blocks_ = 0;
    496   return true;
    497 }
    498 
    499 bool RtcpParser::ParseApplicationDefined(uint8 subtype) {
    500   ptrdiff_t length = rtcp_block_end_ - rtcp_data_;
    501   if (length < 16 ||
    502       !(subtype == kSenderLogSubtype || subtype == kReceiverLogSubtype)) {
    503     state_ = kStateTopLevel;
    504     EndCurrentBlock();
    505     return false;
    506   }
    507 
    508   uint32 sender_ssrc;
    509   uint32 name;
    510 
    511   net::BigEndianReader big_endian_reader(rtcp_data_, length);
    512   big_endian_reader.Skip(4);  // Skip header.
    513   big_endian_reader.ReadU32(&sender_ssrc);
    514   big_endian_reader.ReadU32(&name);
    515 
    516   if (name != kCast) {
    517     state_ = kStateTopLevel;
    518     EndCurrentBlock();
    519     return false;
    520   }
    521   rtcp_data_ += 12;
    522   switch (subtype) {
    523     case kSenderLogSubtype:
    524       state_ = kStateApplicationSpecificCastSenderLog;
    525       field_type_ = kRtcpApplicationSpecificCastSenderLogCode;
    526       field_.cast_sender_log.sender_ssrc = sender_ssrc;
    527       break;
    528     case kReceiverLogSubtype:
    529       state_ = kStateApplicationSpecificCastReceiverFrameLog;
    530       field_type_ = kRtcpApplicationSpecificCastReceiverLogCode;
    531       field_.cast_receiver_log.sender_ssrc = sender_ssrc;
    532       break;
    533     default:
    534       NOTREACHED();
    535   }
    536   return true;
    537 }
    538 
    539 bool RtcpParser::ParseCastReceiverLogFrameItem() {
    540   ptrdiff_t length = rtcp_block_end_ - rtcp_data_;
    541   if (length < 12) {
    542     state_ = kStateTopLevel;
    543     EndCurrentBlock();
    544     return false;
    545   }
    546   uint32 rtp_timestamp;
    547   uint32 data;
    548   net::BigEndianReader big_endian_reader(rtcp_data_, length);
    549   big_endian_reader.ReadU32(&rtp_timestamp);
    550   big_endian_reader.ReadU32(&data);
    551 
    552   rtcp_data_ += 8;
    553 
    554   field_.cast_receiver_log.rtp_timestamp = rtp_timestamp;
    555   // We have 24 LSB of the event timestamp base on the wire.
    556   field_.cast_receiver_log.event_timestamp_base = data & 0xffffff;
    557 
    558   number_of_blocks_ = 1 + static_cast<uint8>(data >> 24);
    559   state_ = kStateApplicationSpecificCastReceiverEventLog;
    560   field_type_ = kRtcpApplicationSpecificCastReceiverLogFrameCode;
    561   return true;
    562 }
    563 
    564 bool RtcpParser::ParseCastReceiverLogEventItem() {
    565   ptrdiff_t length = rtcp_block_end_ - rtcp_data_;
    566   if (length < 4) {
    567     state_ = kStateTopLevel;
    568     EndCurrentBlock();
    569     return false;
    570   }
    571   if (number_of_blocks_ == 0) {
    572     // Continue parsing the next receiver frame event.
    573     state_ = kStateApplicationSpecificCastReceiverFrameLog;
    574     return false;
    575   }
    576   number_of_blocks_--;
    577 
    578   uint16 delay_delta_or_packet_id;
    579   uint16 event_type_and_timestamp_delta;
    580   net::BigEndianReader big_endian_reader(rtcp_data_, length);
    581   big_endian_reader.ReadU16(&delay_delta_or_packet_id);
    582   big_endian_reader.ReadU16(&event_type_and_timestamp_delta);
    583 
    584   rtcp_data_ += 4;
    585 
    586   field_.cast_receiver_log.event =
    587       static_cast<uint8>(event_type_and_timestamp_delta >> 12);
    588   field_.cast_receiver_log.delay_delta_or_packet_id = delay_delta_or_packet_id;
    589   field_.cast_receiver_log.event_timestamp_delta =
    590       event_type_and_timestamp_delta & 0xfff;
    591 
    592   field_type_ = kRtcpApplicationSpecificCastReceiverLogEventCode;
    593   return true;
    594 }
    595 
    596 bool RtcpParser::ParseCastSenderLogItem() {
    597   ptrdiff_t length = rtcp_block_end_ - rtcp_data_;
    598 
    599   if (length < 4) {
    600     state_ = kStateTopLevel;
    601     EndCurrentBlock();
    602     return false;
    603   }
    604   uint32 data;
    605   net::BigEndianReader big_endian_reader(rtcp_data_, length);
    606   big_endian_reader.ReadU32(&data);
    607 
    608   rtcp_data_ += 4;
    609 
    610   field_.cast_sender_log.status = static_cast<uint8>(data >> 24);
    611   // We have 24 LSB of the RTP timestamp on the wire.
    612   field_.cast_sender_log.rtp_timestamp = data & 0xffffff;
    613   field_type_ = kRtcpApplicationSpecificCastSenderLogCode;
    614   return true;
    615 }
    616 
    617 bool RtcpParser::ParseFeedBackCommon(const RtcpCommonHeader& header) {
    618   DCHECK((header.PT == kPacketTypeGenericRtpFeedback) ||
    619          (header.PT == kPacketTypePayloadSpecific)) << "Invalid state";
    620 
    621   ptrdiff_t length = rtcp_block_end_ - rtcp_data_;
    622 
    623   if (length < 12) {  // 4 * 3, RFC4585 section 6.1
    624     EndCurrentBlock();
    625     return false;
    626   }
    627 
    628   uint32 sender_ssrc;
    629   uint32 media_ssrc;
    630   net::BigEndianReader big_endian_reader(rtcp_data_, length);
    631   big_endian_reader.Skip(4);  // Skip header.
    632   big_endian_reader.ReadU32(&sender_ssrc);
    633   big_endian_reader.ReadU32(&media_ssrc);
    634 
    635   rtcp_data_ += 12;
    636 
    637   if (header.PT == kPacketTypeGenericRtpFeedback) {
    638     // Transport layer feedback
    639     switch (header.IC) {
    640       case 1:
    641         // Nack
    642         field_type_ = kRtcpGenericRtpFeedbackNackCode;
    643         field_.nack.sender_ssrc = sender_ssrc;
    644         field_.nack.media_ssrc  = media_ssrc;
    645         state_ = kStateGenericRtpFeedbackNack;
    646         return true;
    647       case 2:
    648         // Used to be ACK is this code point, which is removed conficts with
    649         // http://tools.ietf.org/html/draft-levin-avt-rtcp-burst-00
    650         break;
    651       case 3:
    652         // Tmmbr
    653         break;
    654       case 4:
    655         // Tmmbn
    656         break;
    657       case 5:
    658         // RFC 6051 RTCP-sender_report-REQ Rapid Synchronisation of RTP Flows
    659         // Trigger a new Rtcp sender_report
    660         field_type_ = kRtcpGenericRtpFeedbackSrReqCode;
    661 
    662         // Note: No state transition, sender report REQ is empty!
    663         return true;
    664       default:
    665         break;
    666     }
    667     EndCurrentBlock();
    668     return false;
    669 
    670   } else if (header.PT == kPacketTypePayloadSpecific) {
    671     // Payload specific feedback
    672     switch (header.IC) {
    673       case 1:
    674         // PLI
    675         field_type_ = kRtcpPayloadSpecificPliCode;
    676         field_.pli.sender_ssrc = sender_ssrc;
    677         field_.pli.media_ssrc  = media_ssrc;
    678 
    679         // Note: No state transition, PLI FCI is empty!
    680         return true;
    681       case 2:
    682         // Sli
    683         break;
    684       case 3:
    685         field_type_ = kRtcpPayloadSpecificRpsiCode;
    686         field_.rpsi.sender_ssrc = sender_ssrc;
    687         field_.rpsi.media_ssrc  = media_ssrc;
    688         state_ = kStatePayloadSpecificRpsi;
    689         return true;
    690       case 4:
    691         // fir
    692         break;
    693       case 15:
    694         field_type_ = kRtcpPayloadSpecificAppCode;
    695         field_.application_specific.sender_ssrc = sender_ssrc;
    696         field_.application_specific.media_ssrc  = media_ssrc;
    697         state_ = kStatePayloadSpecificApplication;
    698         return true;
    699       default:
    700         break;
    701     }
    702 
    703     EndCurrentBlock();
    704     return false;
    705   } else {
    706     DCHECK(false) << "Invalid state";
    707     EndCurrentBlock();
    708     return false;
    709   }
    710 }
    711 
    712 bool RtcpParser::ParseRpsiItem() {
    713   // RFC 4585 6.3.3.  Reference Picture Selection Indication (rpsi)
    714   /*
    715     0                   1                   2                   3
    716     0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
    717     +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
    718     |      PB       |0| Payload Type|    Native rpsi bit string     |
    719     +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
    720     |   defined per codec          ...                | Padding (0) |
    721     +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
    722    */
    723   ptrdiff_t length = rtcp_block_end_ - rtcp_data_;
    724 
    725   if (length < 4) {
    726     state_ = kStateTopLevel;
    727     EndCurrentBlock();
    728     return false;
    729   }
    730   if (length > 2 + kRtcpRpsiDataSize) {
    731     state_ = kStateTopLevel;
    732     EndCurrentBlock();
    733     return false;
    734   }
    735 
    736   field_type_ = kRtcpPayloadSpecificRpsiCode;
    737 
    738   uint8 padding_bits;
    739   net::BigEndianReader big_endian_reader(rtcp_data_, length);
    740   big_endian_reader.ReadU8(&padding_bits);
    741   big_endian_reader.ReadU8(&field_.rpsi.payload_type);
    742   big_endian_reader.ReadBytes(&field_.rpsi.native_bit_string, length - 2);
    743   field_.rpsi.number_of_valid_bits =
    744       static_cast<uint16>(length - 2) * 8 - padding_bits;
    745 
    746   rtcp_data_ += length;
    747   return true;
    748 }
    749 
    750 bool RtcpParser::ParseNackItem() {
    751   // RFC 4585 6.2.1. Generic Nack
    752 
    753   ptrdiff_t length = rtcp_block_end_ - rtcp_data_;
    754   if (length < 4) {
    755     state_ = kStateTopLevel;
    756     EndCurrentBlock();
    757     return false;
    758   }
    759 
    760   field_type_ = kRtcpGenericRtpFeedbackNackItemCode;
    761 
    762   net::BigEndianReader big_endian_reader(rtcp_data_, length);
    763   big_endian_reader.ReadU16(&field_.nack_item.packet_id);
    764   big_endian_reader.ReadU16(&field_.nack_item.bitmask);
    765   rtcp_data_ += 4;
    766   return true;
    767 }
    768 
    769 bool RtcpParser::ParsePayloadSpecificAppItem() {
    770   ptrdiff_t length = rtcp_block_end_ - rtcp_data_;
    771 
    772   if (length < 4) {
    773     state_ = kStateTopLevel;
    774     EndCurrentBlock();
    775     return false;
    776   }
    777   uint32 name;
    778   net::BigEndianReader big_endian_reader(rtcp_data_, length);
    779   big_endian_reader.ReadU32(&name);
    780   rtcp_data_ += 4;
    781 
    782   if (name == kRemb) {
    783     field_type_ = kRtcpPayloadSpecificRembCode;
    784     state_ = kStatePayloadSpecificRemb;
    785     return true;
    786   } else if (name == kCast) {
    787     field_type_ = kRtcpPayloadSpecificCastCode;
    788     state_ = kStatePayloadSpecificCast;
    789     return true;
    790   }
    791   state_ = kStateTopLevel;
    792   EndCurrentBlock();
    793   return false;
    794 }
    795 
    796 bool RtcpParser::ParsePayloadSpecificRembItem() {
    797   ptrdiff_t length = rtcp_block_end_ - rtcp_data_;
    798 
    799   if (length < 4) {
    800     state_ = kStateTopLevel;
    801     EndCurrentBlock();
    802     return false;
    803   }
    804 
    805   net::BigEndianReader big_endian_reader(rtcp_data_, length);
    806   big_endian_reader.ReadU8(&field_.remb_item.number_of_ssrcs);
    807 
    808   uint8 byte_1;
    809   uint8 byte_2;
    810   uint8 byte_3;
    811   big_endian_reader.ReadU8(&byte_1);
    812   big_endian_reader.ReadU8(&byte_2);
    813   big_endian_reader.ReadU8(&byte_3);
    814   rtcp_data_ += 4;
    815 
    816   uint8 br_exp = (byte_1 >> 2) & 0x3F;
    817   uint32 br_mantissa = ((byte_1 & 0x03) << 16) + (byte_2 << 8) + byte_3;
    818   field_.remb_item.bitrate = (br_mantissa << br_exp);
    819 
    820   ptrdiff_t length_ssrcs = rtcp_block_end_ - rtcp_data_;
    821   if (length_ssrcs < 4 * field_.remb_item.number_of_ssrcs) {
    822     state_ = kStateTopLevel;
    823     EndCurrentBlock();
    824     return false;
    825   }
    826 
    827   field_type_ = kRtcpPayloadSpecificRembItemCode;
    828 
    829   for (int i = 0; i < field_.remb_item.number_of_ssrcs; i++) {
    830     big_endian_reader.ReadU32(&field_.remb_item.ssrcs[i]);
    831   }
    832   return true;
    833 }
    834 
    835 bool RtcpParser::ParsePayloadSpecificCastItem() {
    836   ptrdiff_t length = rtcp_block_end_ - rtcp_data_;
    837   if (length < 4) {
    838     state_ = kStateTopLevel;
    839     EndCurrentBlock();
    840     return false;
    841   }
    842   field_type_ = kRtcpPayloadSpecificCastCode;
    843 
    844   net::BigEndianReader big_endian_reader(rtcp_data_, length);
    845   big_endian_reader.ReadU8(&field_.cast_item.last_frame_id);
    846   big_endian_reader.ReadU8(&field_.cast_item.number_of_lost_fields);
    847 
    848   rtcp_data_ += 4;
    849 
    850   if (field_.cast_item.number_of_lost_fields != 0) {
    851     // State transition
    852     state_ = kStatePayloadSpecificCastNack;
    853   } else {
    854     // Don't go to state cast nack item if got 0 fields.
    855     state_ = kStateTopLevel;
    856     EndCurrentBlock();
    857   }
    858   return true;
    859 }
    860 
    861 bool RtcpParser::ParsePayloadSpecificCastNackItem() {
    862   ptrdiff_t length = rtcp_block_end_ - rtcp_data_;
    863   if (length < 4) {
    864     state_ = kStateTopLevel;
    865     EndCurrentBlock();
    866     return false;
    867   }
    868   field_type_ = kRtcpPayloadSpecificCastNackItemCode;
    869 
    870   net::BigEndianReader big_endian_reader(rtcp_data_, length);
    871   big_endian_reader.ReadU8(&field_.cast_nack_item.frame_id);
    872   big_endian_reader.ReadU16(&field_.cast_nack_item.packet_id);
    873   big_endian_reader.ReadU8(&field_.cast_nack_item.bitmask);
    874 
    875   rtcp_data_ += 4;
    876   return true;
    877 }
    878 
    879 bool RtcpParser::ParseFirItem() {
    880   // RFC 5104 4.3.1. Full Intra Request (fir)
    881   ptrdiff_t length = rtcp_block_end_ - rtcp_data_;
    882 
    883   if (length < 8) {
    884     state_ = kStateTopLevel;
    885     EndCurrentBlock();
    886     return false;
    887   }
    888   field_type_ = kRtcpPayloadSpecificFirItemCode;
    889 
    890   net::BigEndianReader big_endian_reader(rtcp_data_, length);
    891   big_endian_reader.ReadU32(&field_.fir_item.ssrc);
    892   big_endian_reader.ReadU8(&field_.fir_item.command_sequence_number);
    893 
    894   rtcp_data_ += 8;
    895   return true;
    896 }
    897 
    898 bool RtcpParser::ParseExtendedReport() {
    899   ptrdiff_t length = rtcp_block_end_ - rtcp_data_;
    900   if (length < 8) return false;
    901 
    902   field_type_ = kRtcpXrCode;
    903 
    904   net::BigEndianReader big_endian_reader(rtcp_data_, length);
    905   big_endian_reader.Skip(4);  // Skip header.
    906   big_endian_reader.ReadU32(&field_.extended_report.sender_ssrc);
    907 
    908   rtcp_data_ += 8;
    909 
    910   state_ = kStateExtendedReportBlock;
    911   return true;
    912 }
    913 
    914 bool RtcpParser::ParseExtendedReportItem() {
    915   ptrdiff_t length = rtcp_block_end_ - rtcp_data_;
    916   if (length < 4) {
    917     state_ = kStateTopLevel;
    918     EndCurrentBlock();
    919     return false;
    920   }
    921 
    922   uint8 block_type;
    923   uint16 block_length;
    924   net::BigEndianReader big_endian_reader(rtcp_data_, length);
    925   big_endian_reader.ReadU8(&block_type);
    926   big_endian_reader.Skip(1);  // Ignore reserved.
    927   big_endian_reader.ReadU16(&block_length);
    928 
    929   rtcp_data_ += 4;
    930 
    931   switch (block_type) {
    932     case 4:
    933       if (block_length != 2) {
    934         // Invalid block length.
    935         state_ = kStateTopLevel;
    936         EndCurrentBlock();
    937         return false;
    938       }
    939       return ParseExtendedReportReceiverReferenceTimeReport();
    940     case 5:
    941       if (block_length % 3 != 0) {
    942         // Invalid block length.
    943         state_ = kStateTopLevel;
    944         EndCurrentBlock();
    945         return false;
    946       }
    947       if (block_length >= 3) {
    948         number_of_blocks_ = block_length / 3;
    949         state_ = kStateExtendedReportDelaySinceLastReceiverReport;
    950         return ParseExtendedReportDelaySinceLastReceiverReport();
    951       }
    952       return true;
    953     default:
    954       if (length < block_length * 4) {
    955         state_ = kStateTopLevel;
    956         EndCurrentBlock();
    957         return false;
    958       }
    959       field_type_ = kRtcpXrUnknownItemCode;
    960       rtcp_data_ += block_length * 4;
    961       return true;
    962   }
    963 }
    964 
    965 bool RtcpParser::ParseExtendedReportReceiverReferenceTimeReport() {
    966   ptrdiff_t length = rtcp_block_end_ - rtcp_data_;
    967   if (length < 8) {
    968     state_ = kStateTopLevel;
    969     EndCurrentBlock();
    970     return false;
    971   }
    972 
    973   net::BigEndianReader big_endian_reader(rtcp_data_, length);
    974   big_endian_reader.ReadU32(&field_.rrtr.ntp_most_significant);
    975   big_endian_reader.ReadU32(&field_.rrtr.ntp_least_significant);
    976 
    977   rtcp_data_ += 8;
    978 
    979   field_type_ = kRtcpXrRrtrCode;
    980   return true;
    981 }
    982 
    983 bool RtcpParser::ParseExtendedReportDelaySinceLastReceiverReport() {
    984   ptrdiff_t length = rtcp_block_end_ - rtcp_data_;
    985   if (length < 12) {
    986     state_ = kStateTopLevel;
    987     EndCurrentBlock();
    988     return false;
    989   }
    990   if (number_of_blocks_ == 0) {
    991     // Continue parsing the extended report block.
    992     state_ = kStateExtendedReportBlock;
    993     return false;
    994   }
    995 
    996   net::BigEndianReader big_endian_reader(rtcp_data_, length);
    997   big_endian_reader.ReadU32(&field_.dlrr.receivers_ssrc);
    998   big_endian_reader.ReadU32(&field_.dlrr.last_receiver_report);
    999   big_endian_reader.ReadU32(&field_.dlrr.delay_last_receiver_report);
   1000 
   1001   rtcp_data_ += 12;
   1002 
   1003   number_of_blocks_--;
   1004   field_type_ = kRtcpXrDlrrCode;
   1005   return true;
   1006 }
   1007 
   1008 }  // namespace cast
   1009 }  // namespace media
   1010