Breaking out RTP header parsing from the RTP module.
This is the first step in order to move bandwidth estimation closer to the network. The goal is to have RTP header parsing and bandwidth estimation before voice and video engine, and have a joint estimate for audio and video. Moving bandwidth estimation before the RTP module is also required for RTX. TEST=vie_auto_test, voe_auto_test, trybots. BUG=1811 R=andresp@webrtc.org, henrika@webrtc.org, mflodman@webrtc.org Review URL: https://webrtc-codereview.appspot.com/1545004 git-svn-id: http://webrtc.googlecode.com/svn/trunk@4129 4adac7df-926f-26a2-2b94-8c16560cd09d
This commit is contained in:
@ -15,8 +15,10 @@
|
||||
|
||||
#include "testing/gtest/include/gtest/gtest.h"
|
||||
#include "webrtc/common_types.h"
|
||||
#include "webrtc/modules/rtp_rtcp/interface/rtp_header_parser.h"
|
||||
#include "webrtc/modules/rtp_rtcp/interface/rtp_rtcp.h"
|
||||
#include "webrtc/modules/rtp_rtcp/interface/rtp_rtcp_defines.h"
|
||||
#include "webrtc/system_wrappers/interface/scoped_ptr.h"
|
||||
|
||||
using namespace webrtc;
|
||||
|
||||
@ -87,14 +89,20 @@ class RtxLoopBackTransport : public webrtc::Transport {
|
||||
count_ < consecutive_drop_end_) {
|
||||
return len;
|
||||
}
|
||||
if (module_->IncomingPacket((const uint8_t*)data, len) == 0) {
|
||||
return len;
|
||||
RTPHeader header;
|
||||
scoped_ptr<RtpHeaderParser> parser(RtpHeaderParser::Create());
|
||||
if (!parser->Parse(static_cast<const uint8_t*>(data), len, &header)) {
|
||||
return -1;
|
||||
}
|
||||
return -1;
|
||||
if (module_->IncomingRtpPacket(static_cast<const uint8_t*>(data), len,
|
||||
header) < 0) {
|
||||
return -1;
|
||||
}
|
||||
return len;
|
||||
}
|
||||
|
||||
virtual int SendRTCPPacket(int channel, const void *data, int len) {
|
||||
if (module_->IncomingPacket((const uint8_t*)data, len) == 0) {
|
||||
if (module_->IncomingRtcpPacket((const uint8_t*)data, len) == 0) {
|
||||
return len;
|
||||
}
|
||||
return -1;
|
||||
|
||||
@ -252,7 +252,7 @@ int ReceiverFEC::ParseAndReceivePacket(
|
||||
WebRtcRTPHeader header;
|
||||
memset(&header, 0, sizeof(header));
|
||||
ModuleRTPUtility::RTPHeaderParser parser(packet->data, packet->length);
|
||||
if (!parser.Parse(header)) {
|
||||
if (!parser.Parse(header.header)) {
|
||||
return -1;
|
||||
}
|
||||
if (owner_->ReceiveRecoveredPacketCallback(
|
||||
|
||||
@ -16,13 +16,14 @@
|
||||
#include <gmock/gmock.h>
|
||||
#include <gtest/gtest.h>
|
||||
|
||||
#include "common_types.h"
|
||||
#include "modules/remote_bitrate_estimator/include/remote_bitrate_estimator.h"
|
||||
#include "modules/remote_bitrate_estimator/include/mock/mock_remote_bitrate_observer.h"
|
||||
#include "modules/rtp_rtcp/source/rtcp_receiver.h"
|
||||
#include "modules/rtp_rtcp/source/rtcp_sender.h"
|
||||
#include "modules/rtp_rtcp/source/rtp_utility.h"
|
||||
#include "modules/rtp_rtcp/source/rtp_rtcp_impl.h"
|
||||
#include "webrtc/common_types.h"
|
||||
#include "webrtc/modules/remote_bitrate_estimator/include/remote_bitrate_estimator.h"
|
||||
#include "webrtc/modules/remote_bitrate_estimator/include/mock/mock_remote_bitrate_observer.h"
|
||||
#include "webrtc/modules/rtp_rtcp/interface/rtp_header_parser.h"
|
||||
#include "webrtc/modules/rtp_rtcp/source/rtcp_receiver.h"
|
||||
#include "webrtc/modules/rtp_rtcp/source/rtcp_sender.h"
|
||||
#include "webrtc/modules/rtp_rtcp/source/rtp_utility.h"
|
||||
#include "webrtc/modules/rtp_rtcp/source/rtp_rtcp_impl.h"
|
||||
|
||||
namespace webrtc {
|
||||
|
||||
@ -353,7 +354,11 @@ TEST_F(RtcpSenderTest, TestCompound) {
|
||||
EXPECT_EQ(0, rtp_rtcp_impl_->RegisterReceivePayload(codec_inst));
|
||||
|
||||
// Make sure RTP packet has been received.
|
||||
EXPECT_EQ(0, rtp_rtcp_impl_->IncomingPacket(packet_, packet_length));
|
||||
scoped_ptr<RtpHeaderParser> parser(RtpHeaderParser::Create());
|
||||
RTPHeader header;
|
||||
EXPECT_TRUE(parser->Parse(packet_, packet_length, &header));
|
||||
EXPECT_EQ(0, rtp_rtcp_impl_->IncomingRtpPacket(packet_, packet_length,
|
||||
header));
|
||||
|
||||
EXPECT_EQ(0, rtcp_sender_->SetIJStatus(true));
|
||||
EXPECT_EQ(0, rtcp_sender_->SetRTCPStatus(kRtcpCompound));
|
||||
|
||||
79
webrtc/modules/rtp_rtcp/source/rtp_header_parser.cc
Normal file
79
webrtc/modules/rtp_rtcp/source/rtp_header_parser.cc
Normal file
@ -0,0 +1,79 @@
|
||||
/*
|
||||
* Copyright (c) 2013 The WebRTC project authors. All Rights Reserved.
|
||||
*
|
||||
* Use of this source code is governed by a BSD-style license
|
||||
* that can be found in the LICENSE file in the root of the source
|
||||
* tree. An additional intellectual property rights grant can be found
|
||||
* in the file PATENTS. All contributing project authors may
|
||||
* be found in the AUTHORS file in the root of the source tree.
|
||||
*/
|
||||
#include "webrtc/modules/rtp_rtcp/interface/rtp_header_parser.h"
|
||||
|
||||
#include "webrtc/modules/rtp_rtcp/source/rtp_header_extension.h"
|
||||
#include "webrtc/modules/rtp_rtcp/source/rtp_utility.h"
|
||||
#include "webrtc/system_wrappers/interface/critical_section_wrapper.h"
|
||||
#include "webrtc/system_wrappers/interface/scoped_ptr.h"
|
||||
#include "webrtc/system_wrappers/interface/trace.h"
|
||||
|
||||
namespace webrtc {
|
||||
|
||||
class RtpHeaderParserImpl : public RtpHeaderParser {
|
||||
public:
|
||||
RtpHeaderParserImpl();
|
||||
virtual ~RtpHeaderParserImpl() {}
|
||||
|
||||
virtual bool Parse(const uint8_t* packet, int length,
|
||||
RTPHeader* header) const;
|
||||
|
||||
virtual bool RegisterRtpHeaderExtension(RTPExtensionType type, uint8_t id);
|
||||
|
||||
virtual bool DeregisterRtpHeaderExtension(RTPExtensionType type);
|
||||
|
||||
private:
|
||||
scoped_ptr<CriticalSectionWrapper> critical_section_;
|
||||
RtpHeaderExtensionMap rtp_header_extension_map_;
|
||||
};
|
||||
|
||||
RtpHeaderParser* RtpHeaderParser::Create() {
|
||||
return new RtpHeaderParserImpl;
|
||||
}
|
||||
|
||||
RtpHeaderParserImpl::RtpHeaderParserImpl()
|
||||
: critical_section_(CriticalSectionWrapper::CreateCriticalSection()) {}
|
||||
|
||||
bool RtpHeaderParser::IsRtcp(const uint8_t* packet, int length) {
|
||||
ModuleRTPUtility::RTPHeaderParser rtp_parser(packet, length);
|
||||
return rtp_parser.RTCP();
|
||||
}
|
||||
|
||||
bool RtpHeaderParserImpl::Parse(const uint8_t* packet, int length,
|
||||
RTPHeader* header) const {
|
||||
ModuleRTPUtility::RTPHeaderParser rtp_parser(packet, length);
|
||||
memset(header, 0, sizeof(*header));
|
||||
|
||||
RtpHeaderExtensionMap map;
|
||||
{
|
||||
CriticalSectionScoped cs(critical_section_.get());
|
||||
rtp_header_extension_map_.GetCopy(&map);
|
||||
}
|
||||
|
||||
const bool valid_rtpheader = rtp_parser.Parse(*header, &map);
|
||||
if (!valid_rtpheader) {
|
||||
WEBRTC_TRACE(kTraceDebug, kTraceRtpRtcp, -1,
|
||||
"IncomingPacket invalid RTP header");
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool RtpHeaderParserImpl::RegisterRtpHeaderExtension(RTPExtensionType type,
|
||||
uint8_t id) {
|
||||
CriticalSectionScoped cs(critical_section_.get());
|
||||
return rtp_header_extension_map_.Register(type, id) == 0;
|
||||
}
|
||||
|
||||
bool RtpHeaderParserImpl::DeregisterRtpHeaderExtension(RTPExtensionType type) {
|
||||
CriticalSectionScoped cs(critical_section_.get());
|
||||
return rtp_header_extension_map_.Deregister(type) == 0;
|
||||
}
|
||||
} // namespace webrtc
|
||||
@ -54,7 +54,6 @@ RTPReceiver::RTPReceiver(const int32_t id,
|
||||
|
||||
packet_timeout_ms_(0),
|
||||
|
||||
rtp_header_extension_map_(),
|
||||
ssrc_(0),
|
||||
num_csrcs_(0),
|
||||
current_remote_csrc_(),
|
||||
@ -251,24 +250,6 @@ int32_t RTPReceiver::ReceivePayloadType(
|
||||
payload_name, frequency, channels, rate, payload_type);
|
||||
}
|
||||
|
||||
int32_t RTPReceiver::RegisterRtpHeaderExtension(
|
||||
const RTPExtensionType type,
|
||||
const uint8_t id) {
|
||||
CriticalSectionScoped cs(critical_section_rtp_receiver_);
|
||||
return rtp_header_extension_map_.Register(type, id);
|
||||
}
|
||||
|
||||
int32_t RTPReceiver::DeregisterRtpHeaderExtension(
|
||||
const RTPExtensionType type) {
|
||||
CriticalSectionScoped cs(critical_section_rtp_receiver_);
|
||||
return rtp_header_extension_map_.Deregister(type);
|
||||
}
|
||||
|
||||
void RTPReceiver::GetHeaderExtensionMapCopy(RtpHeaderExtensionMap* map) const {
|
||||
CriticalSectionScoped cs(critical_section_rtp_receiver_);
|
||||
rtp_header_extension_map_.GetCopy(map);
|
||||
}
|
||||
|
||||
NACKMethod RTPReceiver::NACK() const {
|
||||
CriticalSectionScoped lock(critical_section_rtp_receiver_);
|
||||
return nack_method_;
|
||||
@ -341,32 +322,32 @@ int32_t RTPReceiver::Energy(
|
||||
}
|
||||
|
||||
int32_t RTPReceiver::IncomingRTPPacket(
|
||||
WebRtcRTPHeader* rtp_header,
|
||||
RTPHeader* rtp_header,
|
||||
const uint8_t* packet,
|
||||
const uint16_t packet_length) {
|
||||
TRACE_EVENT0("webrtc_rtp", "RTPRecv::Packet");
|
||||
// The rtp_header argument contains the parsed RTP header.
|
||||
int length = packet_length - rtp_header->header.paddingLength;
|
||||
int length = packet_length - rtp_header->paddingLength;
|
||||
|
||||
// Sanity check.
|
||||
if ((length - rtp_header->header.headerLength) < 0) {
|
||||
if ((length - rtp_header->headerLength) < 0) {
|
||||
WEBRTC_TRACE(kTraceError, kTraceRtpRtcp, id_,
|
||||
"%s invalid argument",
|
||||
__FUNCTION__);
|
||||
return -1;
|
||||
}
|
||||
if (rtx_) {
|
||||
if (ssrc_rtx_ == rtp_header->header.ssrc) {
|
||||
if (ssrc_rtx_ == rtp_header->ssrc) {
|
||||
// Sanity check, RTX packets has 2 extra header bytes.
|
||||
if (rtp_header->header.headerLength + kRtxHeaderSize > packet_length) {
|
||||
if (rtp_header->headerLength + kRtxHeaderSize > packet_length) {
|
||||
return -1;
|
||||
}
|
||||
// If a specific RTX payload type is negotiated, set back to the media
|
||||
// payload type and treat it like a media packet from here.
|
||||
if (payload_type_rtx_ != -1) {
|
||||
if (payload_type_rtx_ == rtp_header->header.payloadType &&
|
||||
if (payload_type_rtx_ == rtp_header->payloadType &&
|
||||
rtp_payload_registry_->last_received_media_payload_type() != -1) {
|
||||
rtp_header->header.payloadType =
|
||||
rtp_header->payloadType =
|
||||
rtp_payload_registry_->last_received_media_payload_type();
|
||||
} else {
|
||||
WEBRTC_TRACE(kTraceWarning, kTraceRtpRtcp, id_,
|
||||
@ -374,16 +355,16 @@ int32_t RTPReceiver::IncomingRTPPacket(
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
rtp_header->header.ssrc = ssrc_;
|
||||
rtp_header->header.sequenceNumber =
|
||||
(packet[rtp_header->header.headerLength] << 8) +
|
||||
packet[1 + rtp_header->header.headerLength];
|
||||
// Count the RTX header as part of the RTP header.
|
||||
rtp_header->header.headerLength += 2;
|
||||
rtp_header->ssrc = ssrc_;
|
||||
rtp_header->sequenceNumber =
|
||||
(packet[rtp_header->headerLength] << 8) +
|
||||
packet[1 + rtp_header->headerLength];
|
||||
// Count the RTX header as part of the RTP
|
||||
rtp_header->headerLength += 2;
|
||||
}
|
||||
}
|
||||
if (use_ssrc_filter_) {
|
||||
if (rtp_header->header.ssrc != ssrc_filter_) {
|
||||
if (rtp_header->ssrc != ssrc_filter_) {
|
||||
WEBRTC_TRACE(kTraceWarning, kTraceRtpRtcp, id_,
|
||||
"%s drop packet due to SSRC filter",
|
||||
__FUNCTION__);
|
||||
@ -392,7 +373,7 @@ int32_t RTPReceiver::IncomingRTPPacket(
|
||||
}
|
||||
if (last_receive_time_ == 0) {
|
||||
// Trigger only once.
|
||||
if (length - rtp_header->header.headerLength == 0) {
|
||||
if (length - rtp_header->headerLength == 0) {
|
||||
// Keep-alive packet.
|
||||
cb_rtp_feedback_->OnReceivedPacket(id_, kPacketKeepAlive);
|
||||
} else {
|
||||
@ -401,7 +382,7 @@ int32_t RTPReceiver::IncomingRTPPacket(
|
||||
}
|
||||
int8_t first_payload_byte = 0;
|
||||
if (length > 0) {
|
||||
first_payload_byte = packet[rtp_header->header.headerLength];
|
||||
first_payload_byte = packet[rtp_header->headerLength];
|
||||
}
|
||||
// Trigger our callbacks.
|
||||
CheckSSRCChanged(rtp_header);
|
||||
@ -413,7 +394,7 @@ int32_t RTPReceiver::IncomingRTPPacket(
|
||||
first_payload_byte,
|
||||
is_red,
|
||||
&specific_payload) == -1) {
|
||||
if (length - rtp_header->header.headerLength == 0) {
|
||||
if (length - rtp_header->headerLength == 0) {
|
||||
// OK, keep-alive packet.
|
||||
WEBRTC_TRACE(kTraceStream, kTraceRtpRtcp, id_,
|
||||
"%s received keepalive",
|
||||
@ -425,18 +406,21 @@ int32_t RTPReceiver::IncomingRTPPacket(
|
||||
__FUNCTION__);
|
||||
return -1;
|
||||
}
|
||||
CheckCSRC(rtp_header);
|
||||
WebRtcRTPHeader webrtc_rtp_header;
|
||||
memset(&webrtc_rtp_header, 0, sizeof(webrtc_rtp_header));
|
||||
webrtc_rtp_header.header = *rtp_header;
|
||||
CheckCSRC(&webrtc_rtp_header);
|
||||
|
||||
uint16_t payload_data_length =
|
||||
ModuleRTPUtility::GetPayloadDataLength(rtp_header, packet_length);
|
||||
ModuleRTPUtility::GetPayloadDataLength(*rtp_header, packet_length);
|
||||
|
||||
bool is_first_packet_in_frame =
|
||||
SequenceNumber() + 1 == rtp_header->header.sequenceNumber &&
|
||||
TimeStamp() != rtp_header->header.timestamp;
|
||||
SequenceNumber() + 1 == rtp_header->sequenceNumber &&
|
||||
TimeStamp() != rtp_header->timestamp;
|
||||
bool is_first_packet = is_first_packet_in_frame || HaveNotReceivedPackets();
|
||||
|
||||
int32_t ret_val = rtp_media_receiver_->ParseRtpPacket(
|
||||
rtp_header, specific_payload, is_red, packet, packet_length,
|
||||
&webrtc_rtp_header, specific_payload, is_red, packet, packet_length,
|
||||
clock_->TimeInMilliseconds(), is_first_packet);
|
||||
|
||||
if (ret_val < 0) {
|
||||
@ -447,8 +431,8 @@ int32_t RTPReceiver::IncomingRTPPacket(
|
||||
|
||||
// This compares to received_seq_max_. We store the last received after we
|
||||
// have done the callback.
|
||||
bool old_packet = RetransmitOfOldPacket(rtp_header->header.sequenceNumber,
|
||||
rtp_header->header.timestamp);
|
||||
bool old_packet = RetransmitOfOldPacket(rtp_header->sequenceNumber,
|
||||
rtp_header->timestamp);
|
||||
|
||||
// This updates received_seq_max_ and other members.
|
||||
UpdateStatistics(rtp_header, payload_data_length, old_packet);
|
||||
@ -459,11 +443,11 @@ int32_t RTPReceiver::IncomingRTPPacket(
|
||||
last_received_payload_length_ = payload_data_length;
|
||||
|
||||
if (!old_packet) {
|
||||
if (last_received_timestamp_ != rtp_header->header.timestamp) {
|
||||
last_received_timestamp_ = rtp_header->header.timestamp;
|
||||
if (last_received_timestamp_ != rtp_header->timestamp) {
|
||||
last_received_timestamp_ = rtp_header->timestamp;
|
||||
last_received_frame_time_ms_ = clock_->TimeInMilliseconds();
|
||||
}
|
||||
last_received_sequence_number_ = rtp_header->header.sequenceNumber;
|
||||
last_received_sequence_number_ = rtp_header->sequenceNumber;
|
||||
last_received_transmission_time_offset_ =
|
||||
rtp_header->extension.transmissionTimeOffset;
|
||||
}
|
||||
@ -472,7 +456,7 @@ int32_t RTPReceiver::IncomingRTPPacket(
|
||||
|
||||
// Implementation note: we expect to have the critical_section_rtp_receiver_
|
||||
// critsect when we call this.
|
||||
void RTPReceiver::UpdateStatistics(const WebRtcRTPHeader* rtp_header,
|
||||
void RTPReceiver::UpdateStatistics(const RTPHeader* rtp_header,
|
||||
const uint16_t bytes,
|
||||
const bool old_packet) {
|
||||
uint32_t frequency_hz = rtp_media_receiver_->GetFrequencyHz();
|
||||
@ -483,8 +467,8 @@ void RTPReceiver::UpdateStatistics(const WebRtcRTPHeader* rtp_header,
|
||||
|
||||
if (received_seq_max_ == 0 && received_seq_wraps_ == 0) {
|
||||
// This is the first received report.
|
||||
received_seq_first_ = rtp_header->header.sequenceNumber;
|
||||
received_seq_max_ = rtp_header->header.sequenceNumber;
|
||||
received_seq_first_ = rtp_header->sequenceNumber;
|
||||
received_seq_max_ = rtp_header->sequenceNumber;
|
||||
received_inorder_packet_count_ = 1;
|
||||
local_time_last_received_timestamp_ =
|
||||
GetCurrentRTP(clock_, frequency_hz); // Time in samples.
|
||||
@ -492,26 +476,26 @@ void RTPReceiver::UpdateStatistics(const WebRtcRTPHeader* rtp_header,
|
||||
}
|
||||
|
||||
// Count only the new packets received.
|
||||
if (InOrderPacket(rtp_header->header.sequenceNumber)) {
|
||||
if (InOrderPacket(rtp_header->sequenceNumber)) {
|
||||
const uint32_t RTPtime =
|
||||
GetCurrentRTP(clock_, frequency_hz); // Time in samples.
|
||||
received_inorder_packet_count_++;
|
||||
|
||||
// Wrong if we use RetransmitOfOldPacket.
|
||||
int32_t seq_diff =
|
||||
rtp_header->header.sequenceNumber - received_seq_max_;
|
||||
rtp_header->sequenceNumber - received_seq_max_;
|
||||
if (seq_diff < 0) {
|
||||
// Wrap around detected.
|
||||
received_seq_wraps_++;
|
||||
}
|
||||
// new max
|
||||
received_seq_max_ = rtp_header->header.sequenceNumber;
|
||||
received_seq_max_ = rtp_header->sequenceNumber;
|
||||
|
||||
if (rtp_header->header.timestamp != last_received_timestamp_ &&
|
||||
if (rtp_header->timestamp != last_received_timestamp_ &&
|
||||
received_inorder_packet_count_ > 1) {
|
||||
int32_t time_diff_samples =
|
||||
(RTPtime - local_time_last_received_timestamp_) -
|
||||
(rtp_header->header.timestamp - last_received_timestamp_);
|
||||
(rtp_header->timestamp - last_received_timestamp_);
|
||||
|
||||
time_diff_samples = abs(time_diff_samples);
|
||||
|
||||
@ -528,7 +512,7 @@ void RTPReceiver::UpdateStatistics(const WebRtcRTPHeader* rtp_header,
|
||||
// Actual network jitter, excluding the source-introduced jitter.
|
||||
int32_t time_diff_samples_ext =
|
||||
(RTPtime - local_time_last_received_timestamp_) -
|
||||
((rtp_header->header.timestamp +
|
||||
((rtp_header->timestamp +
|
||||
rtp_header->extension.transmissionTimeOffset) -
|
||||
(last_received_timestamp_ +
|
||||
last_received_transmission_time_offset_));
|
||||
@ -552,7 +536,7 @@ void RTPReceiver::UpdateStatistics(const WebRtcRTPHeader* rtp_header,
|
||||
}
|
||||
|
||||
uint16_t packet_oh =
|
||||
rtp_header->header.headerLength + rtp_header->header.paddingLength;
|
||||
rtp_header->headerLength + rtp_header->paddingLength;
|
||||
|
||||
// Our measured overhead. Filter from RFC 5104 4.2.1.2:
|
||||
// avg_OH (new) = 15/16*avg_OH (old) + 1/16*pckt_OH,
|
||||
@ -676,7 +660,7 @@ int32_t RTPReceiver::SetSSRCFilter(
|
||||
}
|
||||
|
||||
// Implementation note: must not hold critsect when called.
|
||||
void RTPReceiver::CheckSSRCChanged(const WebRtcRTPHeader* rtp_header) {
|
||||
void RTPReceiver::CheckSSRCChanged(const RTPHeader* rtp_header) {
|
||||
bool new_ssrc = false;
|
||||
bool re_initialize_decoder = false;
|
||||
char payload_name[RTP_PAYLOAD_NAME_SIZE];
|
||||
@ -689,7 +673,7 @@ void RTPReceiver::CheckSSRCChanged(const WebRtcRTPHeader* rtp_header) {
|
||||
|
||||
int8_t last_received_payload_type =
|
||||
rtp_payload_registry_->last_received_payload_type();
|
||||
if (ssrc_ != rtp_header->header.ssrc ||
|
||||
if (ssrc_ != rtp_header->ssrc ||
|
||||
(last_received_payload_type == -1 && ssrc_ == 0)) {
|
||||
// We need the payload_type_ to make the call if the remote SSRC is 0.
|
||||
new_ssrc = true;
|
||||
@ -704,12 +688,12 @@ void RTPReceiver::CheckSSRCChanged(const WebRtcRTPHeader* rtp_header) {
|
||||
// Do we have a SSRC? Then the stream is restarted.
|
||||
if (ssrc_) {
|
||||
// Do we have the same codec? Then re-initialize coder.
|
||||
if (rtp_header->header.payloadType == last_received_payload_type) {
|
||||
if (rtp_header->payloadType == last_received_payload_type) {
|
||||
re_initialize_decoder = true;
|
||||
|
||||
Payload* payload;
|
||||
if (rtp_payload_registry_->PayloadTypeToPayload(
|
||||
rtp_header->header.payloadType, payload) != 0) {
|
||||
rtp_header->payloadType, payload) != 0) {
|
||||
return;
|
||||
}
|
||||
assert(payload);
|
||||
@ -724,23 +708,23 @@ void RTPReceiver::CheckSSRCChanged(const WebRtcRTPHeader* rtp_header) {
|
||||
}
|
||||
}
|
||||
}
|
||||
ssrc_ = rtp_header->header.ssrc;
|
||||
ssrc_ = rtp_header->ssrc;
|
||||
}
|
||||
}
|
||||
if (new_ssrc) {
|
||||
// We need to get this to our RTCP sender and receiver.
|
||||
// We need to do this outside critical section.
|
||||
rtp_rtcp_.SetRemoteSSRC(rtp_header->header.ssrc);
|
||||
cb_rtp_feedback_->OnIncomingSSRCChanged(id_, rtp_header->header.ssrc);
|
||||
rtp_rtcp_.SetRemoteSSRC(rtp_header->ssrc);
|
||||
cb_rtp_feedback_->OnIncomingSSRCChanged(id_, rtp_header->ssrc);
|
||||
}
|
||||
if (re_initialize_decoder) {
|
||||
if (-1 == cb_rtp_feedback_->OnInitializeDecoder(
|
||||
id_, rtp_header->header.payloadType, payload_name, frequency,
|
||||
id_, rtp_header->payloadType, payload_name, frequency,
|
||||
channels, rate)) {
|
||||
// New stream, same codec.
|
||||
WEBRTC_TRACE(kTraceError, kTraceRtpRtcp, id_,
|
||||
"Failed to create decoder for payload type:%d",
|
||||
rtp_header->header.payloadType);
|
||||
rtp_header->payloadType);
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -753,14 +737,14 @@ void RTPReceiver::CheckSSRCChanged(const WebRtcRTPHeader* rtp_header) {
|
||||
// media_specific interface (such as CheckPayloadChange, possibly get/set
|
||||
// last known payload).
|
||||
int32_t RTPReceiver::CheckPayloadChanged(
|
||||
const WebRtcRTPHeader* rtp_header,
|
||||
const RTPHeader* rtp_header,
|
||||
const int8_t first_payload_byte,
|
||||
bool& is_red,
|
||||
ModuleRTPUtility::PayloadUnion* specific_payload) {
|
||||
bool re_initialize_decoder = false;
|
||||
|
||||
char payload_name[RTP_PAYLOAD_NAME_SIZE];
|
||||
int8_t payload_type = rtp_header->header.payloadType;
|
||||
int8_t payload_type = rtp_header->payloadType;
|
||||
|
||||
{
|
||||
CriticalSectionScoped lock(critical_section_rtp_receiver_);
|
||||
|
||||
@ -75,7 +75,7 @@ class RTPReceiver : public Bitrate {
|
||||
int8_t* payload_type) const;
|
||||
|
||||
int32_t IncomingRTPPacket(
|
||||
WebRtcRTPHeader* rtpheader,
|
||||
RTPHeader* rtpheader,
|
||||
const uint8_t* incoming_rtp_packet,
|
||||
const uint16_t incoming_rtp_packet_length);
|
||||
|
||||
@ -154,7 +154,7 @@ class RTPReceiver : public Bitrate {
|
||||
virtual bool RetransmitOfOldPacket(const uint16_t sequence_number,
|
||||
const uint32_t rtp_time_stamp) const;
|
||||
|
||||
void UpdateStatistics(const WebRtcRTPHeader* rtp_header,
|
||||
void UpdateStatistics(const RTPHeader* rtp_header,
|
||||
const uint16_t bytes,
|
||||
const bool old_packet);
|
||||
|
||||
@ -164,9 +164,9 @@ class RTPReceiver : public Bitrate {
|
||||
|
||||
bool InOrderPacket(const uint16_t sequence_number) const;
|
||||
|
||||
void CheckSSRCChanged(const WebRtcRTPHeader* rtp_header);
|
||||
void CheckSSRCChanged(const RTPHeader* rtp_header);
|
||||
void CheckCSRC(const WebRtcRTPHeader* rtp_header);
|
||||
int32_t CheckPayloadChanged(const WebRtcRTPHeader* rtp_header,
|
||||
int32_t CheckPayloadChanged(const RTPHeader* rtp_header,
|
||||
const int8_t first_payload_byte,
|
||||
bool& isRED,
|
||||
ModuleRTPUtility::PayloadUnion* payload);
|
||||
@ -188,8 +188,6 @@ class RTPReceiver : public Bitrate {
|
||||
|
||||
uint32_t packet_timeout_ms_;
|
||||
|
||||
RtpHeaderExtensionMap rtp_header_extension_map_;
|
||||
|
||||
// SSRCs.
|
||||
uint32_t ssrc_;
|
||||
uint8_t num_csrcs_;
|
||||
|
||||
@ -194,10 +194,11 @@ int32_t RTPReceiverAudio::ParseRtpPacket(
|
||||
TRACE_EVENT2("webrtc_rtp", "Audio::ParseRtp",
|
||||
"seqnum", rtp_header->header.sequenceNumber,
|
||||
"timestamp", rtp_header->header.timestamp);
|
||||
rtp_header->type.Audio.numEnergy = rtp_header->header.numCSRCs;
|
||||
const uint8_t* payload_data =
|
||||
ModuleRTPUtility::GetPayloadData(rtp_header, packet);
|
||||
ModuleRTPUtility::GetPayloadData(rtp_header->header, packet);
|
||||
const uint16_t payload_data_length =
|
||||
ModuleRTPUtility::GetPayloadDataLength(rtp_header, packet_length);
|
||||
ModuleRTPUtility::GetPayloadDataLength(rtp_header->header, packet_length);
|
||||
|
||||
return ParseAudioCodecSpecific(rtp_header,
|
||||
payload_data,
|
||||
|
||||
@ -79,9 +79,9 @@ int32_t RTPReceiverVideo::ParseRtpPacket(
|
||||
"seqnum", rtp_header->header.sequenceNumber,
|
||||
"timestamp", rtp_header->header.timestamp);
|
||||
const uint8_t* payload_data =
|
||||
ModuleRTPUtility::GetPayloadData(rtp_header, packet);
|
||||
ModuleRTPUtility::GetPayloadData(rtp_header->header, packet);
|
||||
const uint16_t payload_data_length =
|
||||
ModuleRTPUtility::GetPayloadDataLength(rtp_header, packet_length);
|
||||
ModuleRTPUtility::GetPayloadDataLength(rtp_header->header, packet_length);
|
||||
return ParseVideoCodecSpecific(rtp_header,
|
||||
payload_data,
|
||||
payload_data_length,
|
||||
|
||||
@ -28,10 +28,12 @@
|
||||
},
|
||||
'sources': [
|
||||
# Common
|
||||
'../interface/rtp_header_parser.h',
|
||||
'../interface/rtp_rtcp.h',
|
||||
'../interface/rtp_rtcp_defines.h',
|
||||
'bitrate.cc',
|
||||
'bitrate.h',
|
||||
'rtp_header_parser.cc',
|
||||
'rtp_rtcp_config.h',
|
||||
'rtp_rtcp_impl.cc',
|
||||
'rtp_rtcp_impl.h',
|
||||
|
||||
@ -565,77 +565,56 @@ void ModuleRtpRtcpImpl::SetRtxReceivePayloadType(int payload_type) {
|
||||
}
|
||||
|
||||
// Called by the network module when we receive a packet.
|
||||
int32_t ModuleRtpRtcpImpl::IncomingPacket(
|
||||
int32_t ModuleRtpRtcpImpl::IncomingRtpPacket(
|
||||
const uint8_t* incoming_packet,
|
||||
const uint16_t incoming_packet_length) {
|
||||
const uint16_t incoming_packet_length,
|
||||
const RTPHeader& parsed_rtp_header) {
|
||||
WEBRTC_TRACE(kTraceStream,
|
||||
kTraceRtpRtcp,
|
||||
id_,
|
||||
"IncomingPacket(packet_length:%u)",
|
||||
"IncomingRtpPacket(packet_length:%u)",
|
||||
incoming_packet_length);
|
||||
RTPHeader rtp_header_copy = parsed_rtp_header;
|
||||
return rtp_receiver_->IncomingRTPPacket(&rtp_header_copy,
|
||||
incoming_packet,
|
||||
incoming_packet_length);
|
||||
}
|
||||
|
||||
int32_t ModuleRtpRtcpImpl::IncomingRtcpPacket(
|
||||
const uint8_t* rtcp_packet,
|
||||
const uint16_t length) {
|
||||
WEBRTC_TRACE(kTraceStream, kTraceRtpRtcp, -1,
|
||||
"IncomingRtcpPacket(packet_length:%u)", length);
|
||||
// Minimum RTP is 12 bytes.
|
||||
// Minimum RTCP is 8 bytes (RTCP BYE).
|
||||
if (incoming_packet_length < 8 || incoming_packet == NULL) {
|
||||
WEBRTC_TRACE(kTraceDebug,
|
||||
kTraceRtpRtcp,
|
||||
id_,
|
||||
"IncomingPacket invalid buffer or length");
|
||||
return -1;
|
||||
if (length == 8) {
|
||||
WEBRTC_TRACE(kTraceDebug, kTraceRtpRtcp, -1,
|
||||
"IncomingRtcpPacket invalid length");
|
||||
return false;
|
||||
}
|
||||
// Check RTP version.
|
||||
const uint8_t version = incoming_packet[0] >> 6;
|
||||
const uint8_t version = rtcp_packet[0] >> 6;
|
||||
if (version != 2) {
|
||||
WEBRTC_TRACE(kTraceDebug,
|
||||
kTraceRtpRtcp,
|
||||
id_,
|
||||
"IncomingPacket invalid RTP version");
|
||||
WEBRTC_TRACE(kTraceDebug, kTraceRtpRtcp, -1,
|
||||
"IncomingRtcpPacket invalid RTP version");
|
||||
return false;
|
||||
}
|
||||
// Allow receive of non-compound RTCP packets.
|
||||
RTCPUtility::RTCPParserV2 rtcp_parser(rtcp_packet, length, true);
|
||||
|
||||
const bool valid_rtcpheader = rtcp_parser.IsValid();
|
||||
if (!valid_rtcpheader) {
|
||||
WEBRTC_TRACE(kTraceDebug, kTraceRtpRtcp, id_,
|
||||
"IncomingRtcpPacket invalid RTCP packet");
|
||||
return -1;
|
||||
}
|
||||
|
||||
ModuleRTPUtility::RTPHeaderParser rtp_parser(incoming_packet,
|
||||
incoming_packet_length);
|
||||
|
||||
if (rtp_parser.RTCP()) {
|
||||
// Allow receive of non-compound RTCP packets.
|
||||
RTCPUtility::RTCPParserV2 rtcp_parser(incoming_packet,
|
||||
incoming_packet_length,
|
||||
true);
|
||||
|
||||
const bool valid_rtcpheader = rtcp_parser.IsValid();
|
||||
if (!valid_rtcpheader) {
|
||||
WEBRTC_TRACE(kTraceDebug,
|
||||
kTraceRtpRtcp,
|
||||
id_,
|
||||
"IncomingPacket invalid RTCP packet");
|
||||
return -1;
|
||||
}
|
||||
RTCPHelp::RTCPPacketInformation rtcp_packet_information;
|
||||
int32_t ret_val = rtcp_receiver_.IncomingRTCPPacket(
|
||||
rtcp_packet_information, &rtcp_parser);
|
||||
if (ret_val == 0) {
|
||||
rtcp_receiver_.TriggerCallbacksFromRTCPPacket(rtcp_packet_information);
|
||||
}
|
||||
return ret_val;
|
||||
|
||||
} else {
|
||||
WebRtcRTPHeader rtp_header;
|
||||
memset(&rtp_header, 0, sizeof(rtp_header));
|
||||
|
||||
RtpHeaderExtensionMap map;
|
||||
rtp_receiver_->GetHeaderExtensionMapCopy(&map);
|
||||
|
||||
const bool valid_rtpheader = rtp_parser.Parse(rtp_header, &map);
|
||||
if (!valid_rtpheader) {
|
||||
WEBRTC_TRACE(kTraceDebug,
|
||||
kTraceRtpRtcp,
|
||||
id_,
|
||||
"IncomingPacket invalid RTP header");
|
||||
return -1;
|
||||
}
|
||||
return rtp_receiver_->IncomingRTPPacket(&rtp_header,
|
||||
incoming_packet,
|
||||
incoming_packet_length);
|
||||
RTCPHelp::RTCPPacketInformation rtcp_packet_information;
|
||||
int32_t ret_val = rtcp_receiver_.IncomingRTCPPacket(
|
||||
rtcp_packet_information, &rtcp_parser);
|
||||
if (ret_val == 0) {
|
||||
rtcp_receiver_.TriggerCallbacksFromRTCPPacket(rtcp_packet_information);
|
||||
}
|
||||
return ret_val;
|
||||
}
|
||||
|
||||
int32_t ModuleRtpRtcpImpl::RegisterSendPayload(
|
||||
@ -1434,17 +1413,6 @@ int32_t ModuleRtpRtcpImpl::DeregisterSendRtpHeaderExtension(
|
||||
return rtp_sender_.DeregisterRtpHeaderExtension(type);
|
||||
}
|
||||
|
||||
int32_t ModuleRtpRtcpImpl::RegisterReceiveRtpHeaderExtension(
|
||||
const RTPExtensionType type,
|
||||
const uint8_t id) {
|
||||
return rtp_receiver_->RegisterRtpHeaderExtension(type, id);
|
||||
}
|
||||
|
||||
int32_t ModuleRtpRtcpImpl::DeregisterReceiveRtpHeaderExtension(
|
||||
const RTPExtensionType type) {
|
||||
return rtp_receiver_->DeregisterRtpHeaderExtension(type);
|
||||
}
|
||||
|
||||
// (TMMBR) Temporary Max Media Bit Rate.
|
||||
bool ModuleRtpRtcpImpl::TMMBR() const {
|
||||
WEBRTC_TRACE(kTraceModuleCall, kTraceRtpRtcp, id_, "TMMBR()");
|
||||
@ -1682,11 +1650,6 @@ int32_t ModuleRtpRtcpImpl::SetRTPAudioLevelIndicationStatus(
|
||||
enable,
|
||||
id);
|
||||
|
||||
if (enable) {
|
||||
rtp_receiver_->RegisterRtpHeaderExtension(kRtpExtensionAudioLevel, id);
|
||||
} else {
|
||||
rtp_receiver_->DeregisterRtpHeaderExtension(kRtpExtensionAudioLevel);
|
||||
}
|
||||
return rtp_sender_.SetAudioLevelIndicationStatus(enable, id);
|
||||
}
|
||||
|
||||
|
||||
@ -70,14 +70,6 @@ class ModuleRtpRtcpImpl : public RtpRtcp {
|
||||
virtual int32_t DeRegisterReceivePayload(
|
||||
const int8_t payload_type);
|
||||
|
||||
// Register RTP header extension.
|
||||
virtual int32_t RegisterReceiveRtpHeaderExtension(
|
||||
const RTPExtensionType type,
|
||||
const uint8_t id);
|
||||
|
||||
virtual int32_t DeregisterReceiveRtpHeaderExtension(
|
||||
const RTPExtensionType type);
|
||||
|
||||
// Get the currently configured SSRC filter.
|
||||
virtual int32_t SSRCFilter(uint32_t& allowed_ssrc) const;
|
||||
|
||||
@ -108,9 +100,14 @@ class ModuleRtpRtcpImpl : public RtpRtcp {
|
||||
|
||||
virtual void SetRtxReceivePayloadType(int payload_type);
|
||||
|
||||
// Called by the network module when we receive a packet.
|
||||
virtual int32_t IncomingPacket(const uint8_t* incoming_packet,
|
||||
const uint16_t packet_length);
|
||||
// Called when we receive an RTP packet.
|
||||
virtual int32_t IncomingRtpPacket(const uint8_t* incoming_packet,
|
||||
const uint16_t packet_length,
|
||||
const RTPHeader& parsed_rtp_header);
|
||||
|
||||
// Called when we receive an RTCP packet.
|
||||
virtual int32_t IncomingRtcpPacket(const uint8_t* incoming_packet,
|
||||
uint16_t incoming_packet_length);
|
||||
|
||||
// Sender part.
|
||||
|
||||
|
||||
@ -492,8 +492,8 @@ int32_t RTPSender::ReSendPacket(uint16_t packet_id, uint32_t min_resend_time) {
|
||||
}
|
||||
|
||||
ModuleRTPUtility::RTPHeaderParser rtp_parser(data_buffer, length);
|
||||
WebRtcRTPHeader rtp_header;
|
||||
rtp_parser.Parse(rtp_header);
|
||||
RTPHeader header;
|
||||
rtp_parser.Parse(header);
|
||||
|
||||
// Store the time when the packet was last sent or added to pacer.
|
||||
packet_history_->UpdateResendTime(packet_id);
|
||||
@ -508,12 +508,13 @@ int32_t RTPSender::ReSendPacket(uint16_t packet_id, uint32_t min_resend_time) {
|
||||
}
|
||||
|
||||
TRACE_EVENT_INSTANT2("webrtc_rtp", "RTPSender::ReSendPacket",
|
||||
"timestamp", rtp_header.header.timestamp,
|
||||
"seqnum", rtp_header.header.sequenceNumber);
|
||||
"timestamp", header.timestamp,
|
||||
"seqnum", header.sequenceNumber);
|
||||
|
||||
if (paced_sender_) {
|
||||
if (!paced_sender_->SendPacket(PacedSender::kHighPriority,
|
||||
rtp_header.header.ssrc,
|
||||
rtp_header.header.sequenceNumber,
|
||||
header.ssrc,
|
||||
header.sequenceNumber,
|
||||
capture_time_ms,
|
||||
length)) {
|
||||
// We can't send the packet right now.
|
||||
@ -678,10 +679,10 @@ void RTPSender::TimeToSendPacket(uint16_t sequence_number,
|
||||
assert(length > 0);
|
||||
|
||||
ModuleRTPUtility::RTPHeaderParser rtp_parser(data_buffer, length);
|
||||
WebRtcRTPHeader rtp_header;
|
||||
RTPHeader rtp_header;
|
||||
rtp_parser.Parse(rtp_header);
|
||||
TRACE_EVENT_INSTANT2("webrtc_rtp", "RTPSender::TimeToSendPacket",
|
||||
"timestamp", rtp_header.header.timestamp,
|
||||
"timestamp", rtp_header.timestamp,
|
||||
"seqnum", sequence_number);
|
||||
|
||||
int64_t now_ms = clock_->TimeInMilliseconds();
|
||||
@ -693,8 +694,8 @@ void RTPSender::TimeToSendPacket(uint16_t sequence_number,
|
||||
if (updated_transmission_time_offset || updated_abs_send_time) {
|
||||
// Update stored packet in case of receiving a re-transmission request.
|
||||
packet_history_->ReplaceRTPHeader(data_buffer,
|
||||
rtp_header.header.sequenceNumber,
|
||||
rtp_header.header.headerLength);
|
||||
rtp_header.sequenceNumber,
|
||||
rtp_header.headerLength);
|
||||
}
|
||||
SendPacketToNetwork(data_buffer, length);
|
||||
}
|
||||
@ -705,7 +706,7 @@ int32_t RTPSender::SendToNetwork(
|
||||
int64_t capture_time_ms, StorageType storage) {
|
||||
ModuleRTPUtility::RTPHeaderParser rtp_parser(
|
||||
buffer, payload_length + rtp_header_length);
|
||||
WebRtcRTPHeader rtp_header;
|
||||
RTPHeader rtp_header;
|
||||
rtp_parser.Parse(rtp_header);
|
||||
|
||||
int64_t now_ms = clock_->TimeInMilliseconds();
|
||||
@ -753,8 +754,8 @@ int32_t RTPSender::SendToNetwork(
|
||||
|
||||
if (paced_sender_ && storage != kDontStore) {
|
||||
if (!paced_sender_->SendPacket(
|
||||
PacedSender::kNormalPriority, rtp_header.header.ssrc,
|
||||
rtp_header.header.sequenceNumber, capture_time_ms,
|
||||
PacedSender::kNormalPriority, rtp_header.ssrc,
|
||||
rtp_header.sequenceNumber, capture_time_ms,
|
||||
payload_length + rtp_header_length)) {
|
||||
// We can't send the packet right now.
|
||||
// We will be called when it is time.
|
||||
@ -991,7 +992,7 @@ uint8_t RTPSender::BuildAbsoluteSendTimeExtension(
|
||||
|
||||
bool RTPSender::UpdateTransmissionTimeOffset(
|
||||
uint8_t *rtp_packet, const uint16_t rtp_packet_length,
|
||||
const WebRtcRTPHeader &rtp_header, const int64_t time_diff_ms) const {
|
||||
const RTPHeader &rtp_header, const int64_t time_diff_ms) const {
|
||||
CriticalSectionScoped cs(send_critsect_);
|
||||
|
||||
// Get length until start of header extension block.
|
||||
@ -1003,17 +1004,17 @@ bool RTPSender::UpdateTransmissionTimeOffset(
|
||||
"Failed to update transmission time offset, not registered.");
|
||||
return false;
|
||||
}
|
||||
int block_pos = 12 + rtp_header.header.numCSRCs + extension_block_pos;
|
||||
int block_pos = 12 + rtp_header.numCSRCs + extension_block_pos;
|
||||
if (rtp_packet_length < block_pos + kTransmissionTimeOffsetLength ||
|
||||
rtp_header.header.headerLength <
|
||||
rtp_header.headerLength <
|
||||
block_pos + kTransmissionTimeOffsetLength) {
|
||||
WEBRTC_TRACE(kTraceStream, kTraceRtpRtcp, id_,
|
||||
"Failed to update transmission time offset, invalid length.");
|
||||
return false;
|
||||
}
|
||||
// Verify that header contains extension.
|
||||
if (!((rtp_packet[12 + rtp_header.header.numCSRCs] == 0xBE) &&
|
||||
(rtp_packet[12 + rtp_header.header.numCSRCs + 1] == 0xDE))) {
|
||||
if (!((rtp_packet[12 + rtp_header.numCSRCs] == 0xBE) &&
|
||||
(rtp_packet[12 + rtp_header.numCSRCs + 1] == 0xDE))) {
|
||||
WEBRTC_TRACE(
|
||||
kTraceStream, kTraceRtpRtcp, id_,
|
||||
"Failed to update transmission time offset, hdr extension not found.");
|
||||
@ -1042,7 +1043,7 @@ bool RTPSender::UpdateTransmissionTimeOffset(
|
||||
|
||||
bool RTPSender::UpdateAbsoluteSendTime(
|
||||
uint8_t *rtp_packet, const uint16_t rtp_packet_length,
|
||||
const WebRtcRTPHeader &rtp_header, const int64_t now_ms) const {
|
||||
const RTPHeader &rtp_header, const int64_t now_ms) const {
|
||||
CriticalSectionScoped cs(send_critsect_);
|
||||
|
||||
// Get length until start of header extension block.
|
||||
@ -1054,16 +1055,16 @@ bool RTPSender::UpdateAbsoluteSendTime(
|
||||
"Failed to update absolute send time, not registered.");
|
||||
return false;
|
||||
}
|
||||
int block_pos = 12 + rtp_header.header.numCSRCs + extension_block_pos;
|
||||
int block_pos = 12 + rtp_header.numCSRCs + extension_block_pos;
|
||||
if (rtp_packet_length < block_pos + kAbsoluteSendTimeLength ||
|
||||
rtp_header.header.headerLength < block_pos + kAbsoluteSendTimeLength) {
|
||||
rtp_header.headerLength < block_pos + kAbsoluteSendTimeLength) {
|
||||
WEBRTC_TRACE(kTraceStream, kTraceRtpRtcp, id_,
|
||||
"Failed to update absolute send time, invalid length.");
|
||||
return false;
|
||||
}
|
||||
// Verify that header contains extension.
|
||||
if (!((rtp_packet[12 + rtp_header.header.numCSRCs] == 0xBE) &&
|
||||
(rtp_packet[12 + rtp_header.header.numCSRCs + 1] == 0xDE))) {
|
||||
if (!((rtp_packet[12 + rtp_header.numCSRCs] == 0xBE) &&
|
||||
(rtp_packet[12 + rtp_header.numCSRCs + 1] == 0xDE))) {
|
||||
WEBRTC_TRACE(
|
||||
kTraceStream, kTraceRtpRtcp, id_,
|
||||
"Failed to update absolute send time, hdr extension not found.");
|
||||
@ -1352,16 +1353,16 @@ void RTPSender::BuildRtxPacket(uint8_t* buffer, uint16_t* length,
|
||||
ModuleRTPUtility::RTPHeaderParser rtp_parser(
|
||||
reinterpret_cast<const uint8_t *>(buffer), *length);
|
||||
|
||||
WebRtcRTPHeader rtp_header;
|
||||
RTPHeader rtp_header;
|
||||
rtp_parser.Parse(rtp_header);
|
||||
|
||||
// Add original RTP header.
|
||||
memcpy(data_buffer_rtx, buffer, rtp_header.header.headerLength);
|
||||
memcpy(data_buffer_rtx, buffer, rtp_header.headerLength);
|
||||
|
||||
// Replace payload type, if a specific type is set for RTX.
|
||||
if (payload_type_rtx_ != -1) {
|
||||
data_buffer_rtx[1] = static_cast<uint8_t>(payload_type_rtx_);
|
||||
if (rtp_header.header.markerBit)
|
||||
if (rtp_header.markerBit)
|
||||
data_buffer_rtx[1] |= kRtpMarkerBitMask;
|
||||
}
|
||||
|
||||
@ -1374,14 +1375,13 @@ void RTPSender::BuildRtxPacket(uint8_t* buffer, uint16_t* length,
|
||||
ModuleRTPUtility::AssignUWord32ToBuffer(ptr, ssrc_rtx_);
|
||||
|
||||
// Add OSN (original sequence number).
|
||||
ptr = data_buffer_rtx + rtp_header.header.headerLength;
|
||||
ModuleRTPUtility::AssignUWord16ToBuffer(ptr,
|
||||
rtp_header.header.sequenceNumber);
|
||||
ptr = data_buffer_rtx + rtp_header.headerLength;
|
||||
ModuleRTPUtility::AssignUWord16ToBuffer(ptr, rtp_header.sequenceNumber);
|
||||
ptr += 2;
|
||||
|
||||
// Add original payload data.
|
||||
memcpy(ptr, buffer + rtp_header.header.headerLength,
|
||||
*length - rtp_header.header.headerLength);
|
||||
memcpy(ptr, buffer + rtp_header.headerLength,
|
||||
*length - rtp_header.headerLength);
|
||||
*length += 2;
|
||||
}
|
||||
|
||||
|
||||
@ -155,11 +155,11 @@ class RTPSender : public Bitrate, public RTPSenderInterface {
|
||||
|
||||
bool UpdateTransmissionTimeOffset(uint8_t *rtp_packet,
|
||||
const uint16_t rtp_packet_length,
|
||||
const WebRtcRTPHeader &rtp_header,
|
||||
const RTPHeader &rtp_header,
|
||||
const int64_t time_diff_ms) const;
|
||||
bool UpdateAbsoluteSendTime(uint8_t *rtp_packet,
|
||||
const uint16_t rtp_packet_length,
|
||||
const WebRtcRTPHeader &rtp_header,
|
||||
const RTPHeader &rtp_header,
|
||||
const int64_t now_ms) const;
|
||||
|
||||
void TimeToSendPacket(uint16_t sequence_number, int64_t capture_time_ms);
|
||||
|
||||
@ -88,14 +88,14 @@ class RtpSenderTest : public ::testing::Test {
|
||||
const bool kMarkerBit;
|
||||
uint8_t packet_[kMaxPacketLength];
|
||||
|
||||
void VerifyRTPHeaderCommon(const WebRtcRTPHeader& rtp_header) {
|
||||
EXPECT_EQ(kMarkerBit, rtp_header.header.markerBit);
|
||||
EXPECT_EQ(payload_, rtp_header.header.payloadType);
|
||||
EXPECT_EQ(kSeqNum, rtp_header.header.sequenceNumber);
|
||||
EXPECT_EQ(kTimestamp, rtp_header.header.timestamp);
|
||||
EXPECT_EQ(rtp_sender_->SSRC(), rtp_header.header.ssrc);
|
||||
EXPECT_EQ(0, rtp_header.header.numCSRCs);
|
||||
EXPECT_EQ(0, rtp_header.header.paddingLength);
|
||||
void VerifyRTPHeaderCommon(const RTPHeader& rtp_header) {
|
||||
EXPECT_EQ(kMarkerBit, rtp_header.markerBit);
|
||||
EXPECT_EQ(payload_, rtp_header.payloadType);
|
||||
EXPECT_EQ(kSeqNum, rtp_header.sequenceNumber);
|
||||
EXPECT_EQ(kTimestamp, rtp_header.timestamp);
|
||||
EXPECT_EQ(rtp_sender_->SSRC(), rtp_header.ssrc);
|
||||
EXPECT_EQ(0, rtp_header.numCSRCs);
|
||||
EXPECT_EQ(0, rtp_header.paddingLength);
|
||||
}
|
||||
};
|
||||
|
||||
@ -170,7 +170,7 @@ TEST_F(RtpSenderTest, BuildRTPPacket) {
|
||||
|
||||
// Verify
|
||||
webrtc::ModuleRTPUtility::RTPHeaderParser rtp_parser(packet_, length);
|
||||
webrtc::WebRtcRTPHeader rtp_header;
|
||||
webrtc::RTPHeader rtp_header;
|
||||
|
||||
RtpHeaderExtensionMap map;
|
||||
map.Register(kRtpExtensionTransmissionTimeOffset,
|
||||
@ -180,7 +180,7 @@ TEST_F(RtpSenderTest, BuildRTPPacket) {
|
||||
ASSERT_TRUE(valid_rtp_header);
|
||||
ASSERT_FALSE(rtp_parser.RTCP());
|
||||
VerifyRTPHeaderCommon(rtp_header);
|
||||
EXPECT_EQ(length, rtp_header.header.headerLength);
|
||||
EXPECT_EQ(length, rtp_header.headerLength);
|
||||
EXPECT_EQ(0, rtp_header.extension.transmissionTimeOffset);
|
||||
EXPECT_EQ(0u, rtp_header.extension.absoluteSendTime);
|
||||
}
|
||||
@ -198,7 +198,7 @@ TEST_F(RtpSenderTest, BuildRTPPacketWithTransmissionOffsetExtension) {
|
||||
|
||||
// Verify
|
||||
webrtc::ModuleRTPUtility::RTPHeaderParser rtp_parser(packet_, length);
|
||||
webrtc::WebRtcRTPHeader rtp_header;
|
||||
webrtc::RTPHeader rtp_header;
|
||||
|
||||
RtpHeaderExtensionMap map;
|
||||
map.Register(kRtpExtensionTransmissionTimeOffset,
|
||||
@ -208,16 +208,16 @@ TEST_F(RtpSenderTest, BuildRTPPacketWithTransmissionOffsetExtension) {
|
||||
ASSERT_TRUE(valid_rtp_header);
|
||||
ASSERT_FALSE(rtp_parser.RTCP());
|
||||
VerifyRTPHeaderCommon(rtp_header);
|
||||
EXPECT_EQ(length, rtp_header.header.headerLength);
|
||||
EXPECT_EQ(length, rtp_header.headerLength);
|
||||
EXPECT_EQ(kTimeOffset, rtp_header.extension.transmissionTimeOffset);
|
||||
|
||||
// Parse without map extension
|
||||
webrtc::WebRtcRTPHeader rtp_header2;
|
||||
webrtc::RTPHeader rtp_header2;
|
||||
const bool valid_rtp_header2 = rtp_parser.Parse(rtp_header2, NULL);
|
||||
|
||||
ASSERT_TRUE(valid_rtp_header2);
|
||||
VerifyRTPHeaderCommon(rtp_header2);
|
||||
EXPECT_EQ(length, rtp_header2.header.headerLength);
|
||||
EXPECT_EQ(length, rtp_header2.headerLength);
|
||||
EXPECT_EQ(0, rtp_header2.extension.transmissionTimeOffset);
|
||||
}
|
||||
|
||||
@ -235,7 +235,7 @@ TEST_F(RtpSenderTest, BuildRTPPacketWithNegativeTransmissionOffsetExtension) {
|
||||
|
||||
// Verify
|
||||
webrtc::ModuleRTPUtility::RTPHeaderParser rtp_parser(packet_, length);
|
||||
webrtc::WebRtcRTPHeader rtp_header;
|
||||
webrtc::RTPHeader rtp_header;
|
||||
|
||||
RtpHeaderExtensionMap map;
|
||||
map.Register(kRtpExtensionTransmissionTimeOffset,
|
||||
@ -245,7 +245,7 @@ TEST_F(RtpSenderTest, BuildRTPPacketWithNegativeTransmissionOffsetExtension) {
|
||||
ASSERT_TRUE(valid_rtp_header);
|
||||
ASSERT_FALSE(rtp_parser.RTCP());
|
||||
VerifyRTPHeaderCommon(rtp_header);
|
||||
EXPECT_EQ(length, rtp_header.header.headerLength);
|
||||
EXPECT_EQ(length, rtp_header.headerLength);
|
||||
EXPECT_EQ(kNegTimeOffset, rtp_header.extension.transmissionTimeOffset);
|
||||
}
|
||||
|
||||
@ -262,7 +262,7 @@ TEST_F(RtpSenderTest, BuildRTPPacketWithAbsoluteSendTimeExtension) {
|
||||
|
||||
// Verify
|
||||
webrtc::ModuleRTPUtility::RTPHeaderParser rtp_parser(packet_, length);
|
||||
webrtc::WebRtcRTPHeader rtp_header;
|
||||
webrtc::RTPHeader rtp_header;
|
||||
|
||||
RtpHeaderExtensionMap map;
|
||||
map.Register(kRtpExtensionAbsoluteSendTime, kAbsoluteSendTimeExtensionId);
|
||||
@ -271,16 +271,16 @@ TEST_F(RtpSenderTest, BuildRTPPacketWithAbsoluteSendTimeExtension) {
|
||||
ASSERT_TRUE(valid_rtp_header);
|
||||
ASSERT_FALSE(rtp_parser.RTCP());
|
||||
VerifyRTPHeaderCommon(rtp_header);
|
||||
EXPECT_EQ(length, rtp_header.header.headerLength);
|
||||
EXPECT_EQ(length, rtp_header.headerLength);
|
||||
EXPECT_EQ(kAbsoluteSendTime, rtp_header.extension.absoluteSendTime);
|
||||
|
||||
// Parse without map extension
|
||||
webrtc::WebRtcRTPHeader rtp_header2;
|
||||
webrtc::RTPHeader rtp_header2;
|
||||
const bool valid_rtp_header2 = rtp_parser.Parse(rtp_header2, NULL);
|
||||
|
||||
ASSERT_TRUE(valid_rtp_header2);
|
||||
VerifyRTPHeaderCommon(rtp_header2);
|
||||
EXPECT_EQ(length, rtp_header2.header.headerLength);
|
||||
EXPECT_EQ(length, rtp_header2.headerLength);
|
||||
EXPECT_EQ(0u, rtp_header2.extension.absoluteSendTime);
|
||||
}
|
||||
|
||||
@ -300,7 +300,7 @@ TEST_F(RtpSenderTest, BuildRTPPacketWithHeaderExtensions) {
|
||||
|
||||
// Verify
|
||||
webrtc::ModuleRTPUtility::RTPHeaderParser rtp_parser(packet_, length);
|
||||
webrtc::WebRtcRTPHeader rtp_header;
|
||||
webrtc::RTPHeader rtp_header;
|
||||
|
||||
RtpHeaderExtensionMap map;
|
||||
map.Register(kRtpExtensionTransmissionTimeOffset,
|
||||
@ -311,17 +311,17 @@ TEST_F(RtpSenderTest, BuildRTPPacketWithHeaderExtensions) {
|
||||
ASSERT_TRUE(valid_rtp_header);
|
||||
ASSERT_FALSE(rtp_parser.RTCP());
|
||||
VerifyRTPHeaderCommon(rtp_header);
|
||||
EXPECT_EQ(length, rtp_header.header.headerLength);
|
||||
EXPECT_EQ(length, rtp_header.headerLength);
|
||||
EXPECT_EQ(kTimeOffset, rtp_header.extension.transmissionTimeOffset);
|
||||
EXPECT_EQ(kAbsoluteSendTime, rtp_header.extension.absoluteSendTime);
|
||||
|
||||
// Parse without map extension
|
||||
webrtc::WebRtcRTPHeader rtp_header2;
|
||||
webrtc::RTPHeader rtp_header2;
|
||||
const bool valid_rtp_header2 = rtp_parser.Parse(rtp_header2, NULL);
|
||||
|
||||
ASSERT_TRUE(valid_rtp_header2);
|
||||
VerifyRTPHeaderCommon(rtp_header2);
|
||||
EXPECT_EQ(length, rtp_header2.header.headerLength);
|
||||
EXPECT_EQ(length, rtp_header2.headerLength);
|
||||
EXPECT_EQ(0, rtp_header2.extension.transmissionTimeOffset);
|
||||
EXPECT_EQ(0u, rtp_header2.extension.absoluteSendTime);
|
||||
}
|
||||
@ -364,7 +364,7 @@ TEST_F(RtpSenderTest, TrafficSmoothingWithExtensions) {
|
||||
// Parse sent packet.
|
||||
webrtc::ModuleRTPUtility::RTPHeaderParser rtp_parser(
|
||||
transport_.last_sent_packet_, rtp_length);
|
||||
webrtc::WebRtcRTPHeader rtp_header;
|
||||
webrtc::RTPHeader rtp_header;
|
||||
RtpHeaderExtensionMap map;
|
||||
map.Register(kRtpExtensionTransmissionTimeOffset,
|
||||
kTransmissionTimeOffsetExtensionId);
|
||||
@ -425,7 +425,7 @@ TEST_F(RtpSenderTest, TrafficSmoothingRetransmits) {
|
||||
// Parse sent packet.
|
||||
webrtc::ModuleRTPUtility::RTPHeaderParser rtp_parser(
|
||||
transport_.last_sent_packet_, rtp_length);
|
||||
webrtc::WebRtcRTPHeader rtp_header;
|
||||
webrtc::RTPHeader rtp_header;
|
||||
RtpHeaderExtensionMap map;
|
||||
map.Register(kRtpExtensionTransmissionTimeOffset,
|
||||
kTransmissionTimeOffsetExtensionId);
|
||||
@ -454,15 +454,15 @@ TEST_F(RtpSenderTest, SendGenericVideo) {
|
||||
|
||||
ModuleRTPUtility::RTPHeaderParser rtp_parser(transport_.last_sent_packet_,
|
||||
transport_.last_sent_packet_len_);
|
||||
webrtc::WebRtcRTPHeader rtp_header;
|
||||
webrtc::RTPHeader rtp_header;
|
||||
ASSERT_TRUE(rtp_parser.Parse(rtp_header));
|
||||
|
||||
const uint8_t* payload_data = ModuleRTPUtility::GetPayloadData(&rtp_header,
|
||||
const uint8_t* payload_data = ModuleRTPUtility::GetPayloadData(rtp_header,
|
||||
transport_.last_sent_packet_);
|
||||
uint8_t generic_header = *payload_data++;
|
||||
|
||||
ASSERT_EQ(sizeof(payload) + sizeof(generic_header),
|
||||
ModuleRTPUtility::GetPayloadDataLength(&rtp_header,
|
||||
ModuleRTPUtility::GetPayloadDataLength(rtp_header,
|
||||
transport_.last_sent_packet_len_));
|
||||
|
||||
EXPECT_TRUE(generic_header & RtpFormatVideoGeneric::kKeyFrameBit);
|
||||
@ -483,7 +483,7 @@ TEST_F(RtpSenderTest, SendGenericVideo) {
|
||||
transport_.last_sent_packet_len_);
|
||||
ASSERT_TRUE(rtp_parser.Parse(rtp_header));
|
||||
|
||||
payload_data = ModuleRTPUtility::GetPayloadData(&rtp_header,
|
||||
payload_data = ModuleRTPUtility::GetPayloadData(rtp_header,
|
||||
transport_.last_sent_packet_);
|
||||
generic_header = *payload_data++;
|
||||
|
||||
@ -491,7 +491,7 @@ TEST_F(RtpSenderTest, SendGenericVideo) {
|
||||
EXPECT_TRUE(generic_header & RtpFormatVideoGeneric::kFirstPacketBit);
|
||||
|
||||
ASSERT_EQ(sizeof(payload) + sizeof(generic_header),
|
||||
ModuleRTPUtility::GetPayloadDataLength(&rtp_header,
|
||||
ModuleRTPUtility::GetPayloadDataLength(rtp_header,
|
||||
transport_.last_sent_packet_len_));
|
||||
|
||||
EXPECT_EQ(0, memcmp(payload, payload_data, sizeof(payload)));
|
||||
@ -527,7 +527,7 @@ TEST_F(RtpSenderAudioTest, BuildRTPPacketWithAudioLevelExtension) {
|
||||
|
||||
// Verify
|
||||
webrtc::ModuleRTPUtility::RTPHeaderParser rtp_parser(packet_, length);
|
||||
webrtc::WebRtcRTPHeader rtp_header;
|
||||
webrtc::RTPHeader rtp_header;
|
||||
|
||||
RtpHeaderExtensionMap map;
|
||||
map.Register(kRtpExtensionAudioLevel, kAudioLevelExtensionId);
|
||||
@ -536,16 +536,16 @@ TEST_F(RtpSenderAudioTest, BuildRTPPacketWithAudioLevelExtension) {
|
||||
ASSERT_TRUE(valid_rtp_header);
|
||||
ASSERT_FALSE(rtp_parser.RTCP());
|
||||
VerifyRTPHeaderCommon(rtp_header);
|
||||
EXPECT_EQ(length, rtp_header.header.headerLength);
|
||||
EXPECT_EQ(length, rtp_header.headerLength);
|
||||
// TODO(solenberg): Should verify that we got audio level in header extension.
|
||||
|
||||
// Parse without map extension
|
||||
webrtc::WebRtcRTPHeader rtp_header2;
|
||||
webrtc::RTPHeader rtp_header2;
|
||||
const bool valid_rtp_header2 = rtp_parser.Parse(rtp_header2, NULL);
|
||||
|
||||
ASSERT_TRUE(valid_rtp_header2);
|
||||
VerifyRTPHeaderCommon(rtp_header2);
|
||||
EXPECT_EQ(length, rtp_header2.header.headerLength);
|
||||
EXPECT_EQ(length, rtp_header2.headerLength);
|
||||
// TODO(solenberg): Should verify that we didn't get audio level.
|
||||
}
|
||||
|
||||
@ -562,13 +562,13 @@ TEST_F(RtpSenderAudioTest, SendAudio) {
|
||||
|
||||
ModuleRTPUtility::RTPHeaderParser rtp_parser(transport_.last_sent_packet_,
|
||||
transport_.last_sent_packet_len_);
|
||||
webrtc::WebRtcRTPHeader rtp_header;
|
||||
webrtc::RTPHeader rtp_header;
|
||||
ASSERT_TRUE(rtp_parser.Parse(rtp_header));
|
||||
|
||||
const uint8_t* payload_data = ModuleRTPUtility::GetPayloadData(&rtp_header,
|
||||
const uint8_t* payload_data = ModuleRTPUtility::GetPayloadData(rtp_header,
|
||||
transport_.last_sent_packet_);
|
||||
|
||||
ASSERT_EQ(sizeof(payload), ModuleRTPUtility::GetPayloadDataLength(&rtp_header,
|
||||
ASSERT_EQ(sizeof(payload), ModuleRTPUtility::GetPayloadDataLength(rtp_header,
|
||||
transport_.last_sent_packet_len_));
|
||||
|
||||
EXPECT_EQ(0, memcmp(payload, payload_data, sizeof(payload)));
|
||||
@ -593,13 +593,13 @@ TEST_F(RtpSenderAudioTest, SendAudioWithAudioLevelExtension) {
|
||||
|
||||
ModuleRTPUtility::RTPHeaderParser rtp_parser(transport_.last_sent_packet_,
|
||||
transport_.last_sent_packet_len_);
|
||||
webrtc::WebRtcRTPHeader rtp_header;
|
||||
webrtc::RTPHeader rtp_header;
|
||||
ASSERT_TRUE(rtp_parser.Parse(rtp_header));
|
||||
|
||||
const uint8_t* payload_data = ModuleRTPUtility::GetPayloadData(&rtp_header,
|
||||
const uint8_t* payload_data = ModuleRTPUtility::GetPayloadData(rtp_header,
|
||||
transport_.last_sent_packet_);
|
||||
|
||||
ASSERT_EQ(sizeof(payload), ModuleRTPUtility::GetPayloadDataLength(&rtp_header,
|
||||
ASSERT_EQ(sizeof(payload), ModuleRTPUtility::GetPayloadDataLength(rtp_header,
|
||||
transport_.last_sent_packet_len_));
|
||||
|
||||
EXPECT_EQ(0, memcmp(payload, payload_data, sizeof(payload)));
|
||||
|
||||
@ -86,15 +86,15 @@ uint32_t ConvertNTPTimeToMS(uint32_t NTPsec, uint32_t NTPfrac) {
|
||||
* Misc utility routines
|
||||
*/
|
||||
|
||||
const uint8_t* GetPayloadData(const WebRtcRTPHeader* rtp_header,
|
||||
const uint8_t* GetPayloadData(const RTPHeader& rtp_header,
|
||||
const uint8_t* packet) {
|
||||
return packet + rtp_header->header.headerLength;
|
||||
return packet + rtp_header.headerLength;
|
||||
}
|
||||
|
||||
uint16_t GetPayloadDataLength(const WebRtcRTPHeader* rtp_header,
|
||||
uint16_t GetPayloadDataLength(const RTPHeader& rtp_header,
|
||||
const uint16_t packet_length) {
|
||||
uint16_t length = packet_length - rtp_header->header.paddingLength -
|
||||
rtp_header->header.headerLength;
|
||||
uint16_t length = packet_length - rtp_header.paddingLength -
|
||||
rtp_header.headerLength;
|
||||
return static_cast<uint16_t>(length);
|
||||
}
|
||||
|
||||
@ -288,7 +288,7 @@ bool RTPHeaderParser::RTCP() const {
|
||||
return RTCP;
|
||||
}
|
||||
|
||||
bool RTPHeaderParser::Parse(WebRtcRTPHeader& parsedPacket,
|
||||
bool RTPHeaderParser::Parse(RTPHeader& header,
|
||||
RtpHeaderExtensionMap* ptrExtensionMap) const {
|
||||
const ptrdiff_t length = _ptrRTPDataEnd - _ptrRTPDataBegin;
|
||||
|
||||
@ -332,31 +332,30 @@ bool RTPHeaderParser::Parse(WebRtcRTPHeader& parsedPacket,
|
||||
return false;
|
||||
}
|
||||
|
||||
parsedPacket.header.markerBit = M;
|
||||
parsedPacket.header.payloadType = PT;
|
||||
parsedPacket.header.sequenceNumber = sequenceNumber;
|
||||
parsedPacket.header.timestamp = RTPTimestamp;
|
||||
parsedPacket.header.ssrc = SSRC;
|
||||
parsedPacket.header.numCSRCs = CC;
|
||||
parsedPacket.header.paddingLength = P ? *(_ptrRTPDataEnd - 1) : 0;
|
||||
header.markerBit = M;
|
||||
header.payloadType = PT;
|
||||
header.sequenceNumber = sequenceNumber;
|
||||
header.timestamp = RTPTimestamp;
|
||||
header.ssrc = SSRC;
|
||||
header.numCSRCs = CC;
|
||||
header.paddingLength = P ? *(_ptrRTPDataEnd - 1) : 0;
|
||||
|
||||
for (unsigned int i = 0; i < CC; ++i) {
|
||||
uint32_t CSRC = *ptr++ << 24;
|
||||
CSRC += *ptr++ << 16;
|
||||
CSRC += *ptr++ << 8;
|
||||
CSRC += *ptr++;
|
||||
parsedPacket.header.arrOfCSRCs[i] = CSRC;
|
||||
header.arrOfCSRCs[i] = CSRC;
|
||||
}
|
||||
parsedPacket.type.Audio.numEnergy = parsedPacket.header.numCSRCs;
|
||||
|
||||
parsedPacket.header.headerLength = 12 + CSRCocts;
|
||||
header.headerLength = 12 + CSRCocts;
|
||||
|
||||
// If in effect, MAY be omitted for those packets for which the offset
|
||||
// is zero.
|
||||
parsedPacket.extension.transmissionTimeOffset = 0;
|
||||
header.extension.transmissionTimeOffset = 0;
|
||||
|
||||
// May not be present in packet.
|
||||
parsedPacket.extension.absoluteSendTime = 0;
|
||||
header.extension.absoluteSendTime = 0;
|
||||
|
||||
if (X) {
|
||||
/* RTP header extension, RFC 3550.
|
||||
@ -373,7 +372,7 @@ bool RTPHeaderParser::Parse(WebRtcRTPHeader& parsedPacket,
|
||||
return false;
|
||||
}
|
||||
|
||||
parsedPacket.header.headerLength += 4;
|
||||
header.headerLength += 4;
|
||||
|
||||
uint16_t definedByProfile = *ptr++ << 8;
|
||||
definedByProfile += *ptr++;
|
||||
@ -387,18 +386,18 @@ bool RTPHeaderParser::Parse(WebRtcRTPHeader& parsedPacket,
|
||||
}
|
||||
if (definedByProfile == kRtpOneByteHeaderExtensionId) {
|
||||
const uint8_t* ptrRTPDataExtensionEnd = ptr + XLen;
|
||||
ParseOneByteExtensionHeader(parsedPacket,
|
||||
ParseOneByteExtensionHeader(header,
|
||||
ptrExtensionMap,
|
||||
ptrRTPDataExtensionEnd,
|
||||
ptr);
|
||||
}
|
||||
parsedPacket.header.headerLength += XLen;
|
||||
header.headerLength += XLen;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
void RTPHeaderParser::ParseOneByteExtensionHeader(
|
||||
WebRtcRTPHeader& parsedPacket,
|
||||
RTPHeader& header,
|
||||
const RtpHeaderExtensionMap* ptrExtensionMap,
|
||||
const uint8_t* ptrRTPDataExtensionEnd,
|
||||
const uint8_t* ptr) const {
|
||||
@ -446,10 +445,11 @@ void RTPHeaderParser::ParseOneByteExtensionHeader(
|
||||
int32_t transmissionTimeOffset = *ptr++ << 16;
|
||||
transmissionTimeOffset += *ptr++ << 8;
|
||||
transmissionTimeOffset += *ptr++;
|
||||
parsedPacket.extension.transmissionTimeOffset = transmissionTimeOffset;
|
||||
header.extension.transmissionTimeOffset =
|
||||
transmissionTimeOffset;
|
||||
if (transmissionTimeOffset & 0x800000) {
|
||||
// Negative offset, correct sign for Word24 to Word32.
|
||||
parsedPacket.extension.transmissionTimeOffset |= 0xFF000000;
|
||||
header.extension.transmissionTimeOffset |= 0xFF000000;
|
||||
}
|
||||
break;
|
||||
}
|
||||
@ -484,7 +484,7 @@ void RTPHeaderParser::ParseOneByteExtensionHeader(
|
||||
uint32_t absoluteSendTime = *ptr++ << 16;
|
||||
absoluteSendTime += *ptr++ << 8;
|
||||
absoluteSendTime += *ptr++;
|
||||
parsedPacket.extension.absoluteSendTime = absoluteSendTime;
|
||||
header.extension.absoluteSendTime = absoluteSendTime;
|
||||
break;
|
||||
}
|
||||
default: {
|
||||
|
||||
@ -73,11 +73,11 @@ namespace ModuleRTPUtility
|
||||
uint32_t pow2(uint8_t exp);
|
||||
|
||||
// Returns a pointer to the payload data given a packet.
|
||||
const uint8_t* GetPayloadData(const WebRtcRTPHeader* rtp_header,
|
||||
const uint8_t* GetPayloadData(const RTPHeader& rtp_header,
|
||||
const uint8_t* packet);
|
||||
|
||||
// Returns payload length given a packet.
|
||||
uint16_t GetPayloadDataLength(const WebRtcRTPHeader* rtp_header,
|
||||
uint16_t GetPayloadDataLength(const RTPHeader& rtp_header,
|
||||
const uint16_t packet_length);
|
||||
|
||||
// Returns true if |newTimestamp| is older than |existingTimestamp|.
|
||||
@ -124,12 +124,12 @@ namespace ModuleRTPUtility
|
||||
~RTPHeaderParser();
|
||||
|
||||
bool RTCP() const;
|
||||
bool Parse(WebRtcRTPHeader& parsedPacket,
|
||||
bool Parse(RTPHeader& parsedPacket,
|
||||
RtpHeaderExtensionMap* ptrExtensionMap = NULL) const;
|
||||
|
||||
private:
|
||||
void ParseOneByteExtensionHeader(
|
||||
WebRtcRTPHeader& parsedPacket,
|
||||
RTPHeader& parsedPacket,
|
||||
const RtpHeaderExtensionMap* ptrExtensionMap,
|
||||
const uint8_t* ptrRTPDataExtensionEnd,
|
||||
const uint8_t* ptr) const;
|
||||
|
||||
Reference in New Issue
Block a user