Introduce helpers to RtpSender to propagate RtpPacketToSend.
The helpers intended to replace and deprecate BuildRtpHeader when RtpSenderAudio/RtpSenderVideo will be updated to pass RtpPacket class instead of raw buffer for sending. BUG=webrtc:5261 R=sprang@webrtc.org Review URL: https://codereview.webrtc.org/2303283002 . Cr-Commit-Position: refs/heads/master@{#14051}
This commit is contained in:
parent
ba6f7be234
commit
5e57b17283
@ -83,6 +83,9 @@ class Packet {
|
||||
void SetCsrcs(const std::vector<uint32_t>& csrcs);
|
||||
|
||||
// Header extensions.
|
||||
template <typename Extension>
|
||||
bool HasExtension() const;
|
||||
|
||||
template <typename Extension, typename... Values>
|
||||
bool GetExtension(Values...) const;
|
||||
|
||||
@ -160,6 +163,12 @@ class Packet {
|
||||
Packet() = delete;
|
||||
};
|
||||
|
||||
template <typename Extension>
|
||||
bool Packet::HasExtension() const {
|
||||
uint16_t offset = 0;
|
||||
return FindExtension(Extension::kId, Extension::kValueSizeBytes, &offset);
|
||||
}
|
||||
|
||||
template <typename Extension, typename... Values>
|
||||
bool Packet::GetExtension(Values... values) const {
|
||||
uint16_t offset = 0;
|
||||
|
||||
@ -1072,6 +1072,36 @@ size_t RTPSender::CreateRtpHeader(uint8_t* header,
|
||||
return rtp_header_length;
|
||||
}
|
||||
|
||||
std::unique_ptr<RtpPacketToSend> RTPSender::AllocatePacket() const {
|
||||
rtc::CritScope lock(&send_critsect_);
|
||||
std::unique_ptr<RtpPacketToSend> packet(
|
||||
new RtpPacketToSend(&rtp_header_extension_map_, max_payload_length_));
|
||||
packet->SetSsrc(ssrc_);
|
||||
packet->SetCsrcs(csrcs_);
|
||||
// Reserve extensions, if registered, RtpSender set in SendToNetwork.
|
||||
packet->ReserveExtension<AbsoluteSendTime>();
|
||||
packet->ReserveExtension<TransmissionOffset>();
|
||||
packet->ReserveExtension<TransportSequenceNumber>();
|
||||
return packet;
|
||||
}
|
||||
|
||||
bool RTPSender::AssignSequenceNumber(RtpPacketToSend* packet) {
|
||||
rtc::CritScope lock(&send_critsect_);
|
||||
if (!sending_media_)
|
||||
return false;
|
||||
RTC_DCHECK_EQ(packet->Ssrc(), ssrc_);
|
||||
packet->SetSequenceNumber(sequence_number_++);
|
||||
|
||||
// Remember marker bit to determine if padding can be inserted with
|
||||
// sequence number following |packet|.
|
||||
last_packet_marker_bit_ = packet->Marker();
|
||||
// Save timestamps to generate timestamp field and extensions for the padding.
|
||||
last_rtp_timestamp_ = packet->Timestamp();
|
||||
last_timestamp_time_ms_ = clock_->TimeInMilliseconds();
|
||||
capture_time_ms_ = packet->capture_time_ms();
|
||||
return true;
|
||||
}
|
||||
|
||||
int32_t RTPSender::BuildRTPheader(uint8_t* data_buffer,
|
||||
int8_t payload_type,
|
||||
bool marker_bit,
|
||||
|
||||
@ -203,6 +203,14 @@ class RTPSender {
|
||||
|
||||
void SetRtxPayloadType(int payload_type, int associated_payload_type);
|
||||
|
||||
// Create empty packet, fills ssrc, csrcs and reserve place for header
|
||||
// extensions RtpSender updates before sending.
|
||||
std::unique_ptr<RtpPacketToSend> AllocatePacket() const;
|
||||
// Allocate sequence number for provided packet.
|
||||
// Save packet's fields to generate padding that doesn't break media stream.
|
||||
// Return false if sending was turned off.
|
||||
bool AssignSequenceNumber(RtpPacketToSend* packet);
|
||||
|
||||
// Functions wrapping RTPSenderInterface.
|
||||
int32_t BuildRTPheader(uint8_t* data_buffer,
|
||||
int8_t payload_type,
|
||||
|
||||
@ -22,6 +22,8 @@
|
||||
#include "webrtc/modules/rtp_rtcp/source/rtcp_packet/transport_feedback.h"
|
||||
#include "webrtc/modules/rtp_rtcp/source/rtp_format_video_generic.h"
|
||||
#include "webrtc/modules/rtp_rtcp/source/rtp_header_extension.h"
|
||||
#include "webrtc/modules/rtp_rtcp/source/rtp_header_extensions.h"
|
||||
#include "webrtc/modules/rtp_rtcp/source/rtp_packet_to_send.h"
|
||||
#include "webrtc/modules/rtp_rtcp/source/rtp_sender.h"
|
||||
#include "webrtc/modules/rtp_rtcp/source/rtp_sender_video.h"
|
||||
#include "webrtc/modules/rtp_rtcp/source/rtp_utility.h"
|
||||
@ -53,7 +55,8 @@ const VideoRotation kRotation = kVideoRotation_270;
|
||||
const size_t kGenericHeaderLength = 1;
|
||||
const uint8_t kPayloadData[] = {47, 11, 32, 93, 89};
|
||||
|
||||
using testing::_;
|
||||
using ::testing::_;
|
||||
using ::testing::ElementsAreArray;
|
||||
|
||||
const uint8_t* GetPayloadData(const RTPHeader& rtp_header,
|
||||
const uint8_t* packet) {
|
||||
@ -372,6 +375,101 @@ TEST_F(RtpSenderTestWithoutPacer, RegisterRtpVideoRotationHeaderExtension) {
|
||||
EXPECT_EQ(0u, rtp_sender_->RtpHeaderExtensionLength());
|
||||
}
|
||||
|
||||
TEST_F(RtpSenderTestWithoutPacer, AllocatePacketSetCsrc) {
|
||||
// Configure rtp_sender with csrc.
|
||||
std::vector<uint32_t> csrcs;
|
||||
csrcs.push_back(0x23456789);
|
||||
rtp_sender_->SetCsrcs(csrcs);
|
||||
|
||||
auto packet = rtp_sender_->AllocatePacket();
|
||||
|
||||
ASSERT_TRUE(packet);
|
||||
EXPECT_EQ(rtp_sender_->SSRC(), packet->Ssrc());
|
||||
EXPECT_EQ(csrcs, packet->Csrcs());
|
||||
}
|
||||
|
||||
TEST_F(RtpSenderTestWithoutPacer, AllocatePacketReserveExtensions) {
|
||||
// Configure rtp_sender with extensions.
|
||||
ASSERT_EQ(0, rtp_sender_->RegisterRtpHeaderExtension(
|
||||
kRtpExtensionTransmissionTimeOffset,
|
||||
kTransmissionTimeOffsetExtensionId));
|
||||
ASSERT_EQ(
|
||||
0, rtp_sender_->RegisterRtpHeaderExtension(kRtpExtensionAbsoluteSendTime,
|
||||
kAbsoluteSendTimeExtensionId));
|
||||
ASSERT_EQ(0, rtp_sender_->RegisterRtpHeaderExtension(kRtpExtensionAudioLevel,
|
||||
kAudioLevelExtensionId));
|
||||
ASSERT_EQ(0, rtp_sender_->RegisterRtpHeaderExtension(
|
||||
kRtpExtensionTransportSequenceNumber,
|
||||
kTransportSequenceNumberExtensionId));
|
||||
ASSERT_EQ(0, rtp_sender_->RegisterRtpHeaderExtension(
|
||||
kRtpExtensionVideoRotation, kVideoRotationExtensionId));
|
||||
|
||||
auto packet = rtp_sender_->AllocatePacket();
|
||||
|
||||
ASSERT_TRUE(packet);
|
||||
// Preallocate BWE extensions RtpSender set itself.
|
||||
EXPECT_TRUE(packet->HasExtension<TransmissionOffset>());
|
||||
EXPECT_TRUE(packet->HasExtension<AbsoluteSendTime>());
|
||||
EXPECT_TRUE(packet->HasExtension<TransportSequenceNumber>());
|
||||
// Do not allocate media specific extensions.
|
||||
EXPECT_FALSE(packet->HasExtension<AudioLevel>());
|
||||
EXPECT_FALSE(packet->HasExtension<VideoOrientation>());
|
||||
}
|
||||
|
||||
TEST_F(RtpSenderTestWithoutPacer, AssignSequenceNumberAdvanceSequenceNumber) {
|
||||
auto packet = rtp_sender_->AllocatePacket();
|
||||
ASSERT_TRUE(packet);
|
||||
const uint16_t sequence_number = rtp_sender_->SequenceNumber();
|
||||
|
||||
EXPECT_TRUE(rtp_sender_->AssignSequenceNumber(packet.get()));
|
||||
|
||||
EXPECT_EQ(sequence_number, packet->SequenceNumber());
|
||||
EXPECT_EQ(sequence_number + 1, rtp_sender_->SequenceNumber());
|
||||
}
|
||||
|
||||
TEST_F(RtpSenderTestWithoutPacer, AssignSequenceNumberFailsOnNotSending) {
|
||||
auto packet = rtp_sender_->AllocatePacket();
|
||||
ASSERT_TRUE(packet);
|
||||
|
||||
rtp_sender_->SetSendingMediaStatus(false);
|
||||
EXPECT_FALSE(rtp_sender_->AssignSequenceNumber(packet.get()));
|
||||
}
|
||||
|
||||
TEST_F(RtpSenderTestWithoutPacer, AssignSequenceNumberMayAllowPadding) {
|
||||
constexpr size_t kPaddingSize = 100;
|
||||
auto packet = rtp_sender_->AllocatePacket();
|
||||
ASSERT_TRUE(packet);
|
||||
|
||||
ASSERT_FALSE(rtp_sender_->SendPadData(kPaddingSize, false, 0, 0, -1));
|
||||
packet->SetMarker(false);
|
||||
ASSERT_TRUE(rtp_sender_->AssignSequenceNumber(packet.get()));
|
||||
// Packet without marker bit doesn't allow padding.
|
||||
EXPECT_FALSE(rtp_sender_->SendPadData(kPaddingSize, false, 0, 0, -1));
|
||||
|
||||
packet->SetMarker(true);
|
||||
ASSERT_TRUE(rtp_sender_->AssignSequenceNumber(packet.get()));
|
||||
// Packet with marker bit allows send padding.
|
||||
EXPECT_TRUE(rtp_sender_->SendPadData(kPaddingSize, false, 0, 0, -1));
|
||||
}
|
||||
|
||||
TEST_F(RtpSenderTestWithoutPacer, AssignSequenceNumberSetPaddingTimestamps) {
|
||||
constexpr size_t kPaddingSize = 100;
|
||||
auto packet = rtp_sender_->AllocatePacket();
|
||||
ASSERT_TRUE(packet);
|
||||
packet->SetMarker(true);
|
||||
packet->SetTimestamp(kTimestamp);
|
||||
|
||||
ASSERT_TRUE(rtp_sender_->AssignSequenceNumber(packet.get()));
|
||||
ASSERT_TRUE(rtp_sender_->SendPadData(kPaddingSize, false, 0, 0, -1));
|
||||
|
||||
ASSERT_EQ(1u, transport_.sent_packets_.size());
|
||||
// Parse the padding packet and verify its timestamp.
|
||||
RtpPacketToSend padding_packet(nullptr);
|
||||
ASSERT_TRUE(padding_packet.Parse(transport_.sent_packets_[0]->data(),
|
||||
transport_.sent_packets_[0]->size()));
|
||||
EXPECT_EQ(kTimestamp, padding_packet.Timestamp());
|
||||
}
|
||||
|
||||
TEST_F(RtpSenderTestWithoutPacer, BuildRTPPacket) {
|
||||
size_t length = static_cast<size_t>(rtp_sender_->BuildRtpHeader(
|
||||
packet_, kPayload, kMarkerBit, kTimestamp, 0));
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user