mirror of
https://github.com/kunkundi/crossdesk.git
synced 2025-12-17 04:26:47 +08:00
[feat] introduce fraction lost into congestion control module
This commit is contained in:
@@ -1,5 +0,0 @@
|
|||||||
#include "rtcp_receiver.h"
|
|
||||||
|
|
||||||
RtcpReceiver::RtcpReceiver() {}
|
|
||||||
|
|
||||||
RtcpReceiver::~RtcpReceiver() {}
|
|
||||||
@@ -1,19 +0,0 @@
|
|||||||
/*
|
|
||||||
* @Author: DI JUNKUN
|
|
||||||
* @Date: 2025-02-17
|
|
||||||
* Copyright (c) 2025 by DI JUNKUN, All Rights Reserved.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifndef _RTCP_RECEIVER_H_
|
|
||||||
#define _RTCP_RECEIVER_H_
|
|
||||||
|
|
||||||
class RtcpReceiver {
|
|
||||||
public:
|
|
||||||
RtcpReceiver();
|
|
||||||
~RtcpReceiver();
|
|
||||||
|
|
||||||
public:
|
|
||||||
private:
|
|
||||||
}
|
|
||||||
|
|
||||||
#endif
|
|
||||||
@@ -1,43 +0,0 @@
|
|||||||
#include "rtcp_sender.h"
|
|
||||||
|
|
||||||
RtcpSender::RtcpSender(std::shared_ptr<webrtc::Clock> clock, uint32_t ssrc)
|
|
||||||
: clock_(clock), ssrc_(ssrc) {}
|
|
||||||
|
|
||||||
RtcpSender::~RtcpSender() {}
|
|
||||||
|
|
||||||
void RtcpSender::BuildSR(const RtcpContext& ctx, PacketSender& sender) {
|
|
||||||
// The timestamp of this RTCP packet should be estimated as the timestamp of
|
|
||||||
// the frame being captured at this moment. We are calculating that
|
|
||||||
// timestamp as the last frame's timestamp + the time since the last frame
|
|
||||||
// was captured.
|
|
||||||
int rtp_rate = rtp_clock_rates_khz_[last_payload_type_];
|
|
||||||
if (rtp_rate <= 0) {
|
|
||||||
rtp_rate =
|
|
||||||
(audio_ ? kBogusRtpRateForAudioRtcp : kVideoPayloadTypeFrequency) /
|
|
||||||
1000;
|
|
||||||
}
|
|
||||||
// Round now_us_ to the closest millisecond, because Ntp time is rounded
|
|
||||||
// when converted to milliseconds,
|
|
||||||
uint32_t rtp_timestamp =
|
|
||||||
timestamp_offset_ + last_rtp_timestamp_ +
|
|
||||||
((ctx.now_.us() + 500) / 1000 - last_frame_capture_time_->ms()) *
|
|
||||||
rtp_rate;
|
|
||||||
|
|
||||||
rtcp::SenderReport report;
|
|
||||||
report.SetSenderSsrc(ssrc_);
|
|
||||||
report.SetNtp(env_.clock().ConvertTimestampToNtpTime(ctx.now_));
|
|
||||||
report.SetRtpTimestamp(rtp_timestamp);
|
|
||||||
report.SetPacketCount(ctx.feedback_state_.packets_sent);
|
|
||||||
report.SetOctetCount(ctx.feedback_state_.media_bytes_sent);
|
|
||||||
report.SetReportBlocks(CreateReportBlocks(ctx.feedback_state_));
|
|
||||||
sender.AppendPacket(report);
|
|
||||||
}
|
|
||||||
|
|
||||||
void RtcpSender::BuildRR(const RtcpContext& ctx, PacketSender& sender) {
|
|
||||||
rtcp::ReceiverReport report;
|
|
||||||
report.SetSenderSsrc(ssrc_);
|
|
||||||
report.SetReportBlocks(CreateReportBlocks(ctx.feedback_state_));
|
|
||||||
if (method_ == RtcpMode::kCompound || !report.report_blocks().empty()) {
|
|
||||||
sender.AppendPacket(report);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,26 +0,0 @@
|
|||||||
/*
|
|
||||||
* @Author: DI JUNKUN
|
|
||||||
* @Date: 2025-02-17
|
|
||||||
* Copyright (c) 2025 by DI JUNKUN, All Rights Reserved.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifndef _RTCP_SENDER_H_
|
|
||||||
#define _RTCP_SENDER_H_
|
|
||||||
|
|
||||||
#include <memory>
|
|
||||||
|
|
||||||
#include "api/clock/clock.h"
|
|
||||||
#include "rtcp/rtcp_packet/rtcp_packet.h"
|
|
||||||
|
|
||||||
class RtcpSender {
|
|
||||||
public:
|
|
||||||
RtcpSender(std::shared_ptr<webrtc::Clock> clock, uint32_t ssrc);
|
|
||||||
~RtcpSender();
|
|
||||||
|
|
||||||
public:
|
|
||||||
private:
|
|
||||||
std::shared_ptr<webrtc::Clock> clock_;
|
|
||||||
uint32_t ssrc_;
|
|
||||||
}
|
|
||||||
|
|
||||||
#endif
|
|
||||||
@@ -15,7 +15,7 @@
|
|||||||
#include <windows.h>
|
#include <windows.h>
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
int64_t ConvertToNtpTime(int64_t time_us) {
|
int64_t SystemClock::ConvertToNtpTime(int64_t time_us) {
|
||||||
constexpr int64_t kMicrosecondsPerSecond = 1000000;
|
constexpr int64_t kMicrosecondsPerSecond = 1000000;
|
||||||
constexpr uint64_t kNtpFractionalUnit = 0x100000000; // 2^32
|
constexpr uint64_t kNtpFractionalUnit = 0x100000000; // 2^32
|
||||||
uint32_t seconds = static_cast<uint32_t>(time_us / kMicrosecondsPerSecond);
|
uint32_t seconds = static_cast<uint32_t>(time_us / kMicrosecondsPerSecond);
|
||||||
@@ -120,3 +120,21 @@ int64_t SystemClock::CurrentUtcTimeMs() {
|
|||||||
int64_t SystemClock::CurrentUtcTime() {
|
int64_t SystemClock::CurrentUtcTime() {
|
||||||
return CurrentUtcTimeNs() / 1000000000LL;
|
return CurrentUtcTimeNs() / 1000000000LL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int64_t SystemClock::NtpToUtc(int64_t ntp_time) {
|
||||||
|
constexpr int64_t kNtpEpochOffset =
|
||||||
|
2208988800LL; // NTP epoch starts at 1900-01-01, Unix epoch starts at
|
||||||
|
// 1970-01-01
|
||||||
|
constexpr int64_t kMicrosecondsPerSecond = 1000000;
|
||||||
|
constexpr uint64_t kNtpFractionalUnit = 0x100000000; // 2^32
|
||||||
|
|
||||||
|
uint32_t seconds = static_cast<uint32_t>(ntp_time / kNtpFractionalUnit);
|
||||||
|
uint32_t fractions = static_cast<uint32_t>(ntp_time % kNtpFractionalUnit);
|
||||||
|
|
||||||
|
int64_t unix_seconds = static_cast<int64_t>(seconds) - kNtpEpochOffset;
|
||||||
|
int64_t microseconds =
|
||||||
|
(static_cast<int64_t>(fractions) * kMicrosecondsPerSecond) /
|
||||||
|
kNtpFractionalUnit;
|
||||||
|
|
||||||
|
return unix_seconds * kMicrosecondsPerSecond + microseconds;
|
||||||
|
}
|
||||||
@@ -29,6 +29,10 @@ class SystemClock {
|
|||||||
int64_t CurrentUtcTimeMs();
|
int64_t CurrentUtcTimeMs();
|
||||||
int64_t CurrentUtcTimeUs();
|
int64_t CurrentUtcTimeUs();
|
||||||
int64_t CurrentUtcTimeNs();
|
int64_t CurrentUtcTimeNs();
|
||||||
|
|
||||||
|
int64_t ConvertToNtpTime(int64_t time_us);
|
||||||
|
|
||||||
|
int64_t NtpToUtc(int64_t ntp_time);
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
@@ -72,6 +72,18 @@ CongestionControl::CongestionControl()
|
|||||||
|
|
||||||
CongestionControl::~CongestionControl() {}
|
CongestionControl::~CongestionControl() {}
|
||||||
|
|
||||||
|
NetworkControlUpdate CongestionControl::OnTransportLossReport(
|
||||||
|
TransportLossReport msg) {
|
||||||
|
if (packet_feedback_only_) {
|
||||||
|
return NetworkControlUpdate();
|
||||||
|
}
|
||||||
|
int64_t total_packets_delta =
|
||||||
|
msg.packets_received_delta + msg.packets_lost_delta;
|
||||||
|
bandwidth_estimation_->UpdatePacketsLost(
|
||||||
|
msg.packets_lost_delta, total_packets_delta, msg.receive_time);
|
||||||
|
return NetworkControlUpdate();
|
||||||
|
}
|
||||||
|
|
||||||
NetworkControlUpdate CongestionControl::OnTransportPacketsFeedback(
|
NetworkControlUpdate CongestionControl::OnTransportPacketsFeedback(
|
||||||
TransportPacketsFeedback report) {
|
TransportPacketsFeedback report) {
|
||||||
if (report.packet_feedbacks.empty()) {
|
if (report.packet_feedbacks.empty()) {
|
||||||
|
|||||||
@@ -22,6 +22,8 @@ class CongestionControl {
|
|||||||
~CongestionControl();
|
~CongestionControl();
|
||||||
|
|
||||||
public:
|
public:
|
||||||
|
NetworkControlUpdate OnTransportLossReport(TransportLossReport msg);
|
||||||
|
|
||||||
NetworkControlUpdate OnTransportPacketsFeedback(
|
NetworkControlUpdate OnTransportPacketsFeedback(
|
||||||
TransportPacketsFeedback report);
|
TransportPacketsFeedback report);
|
||||||
|
|
||||||
|
|||||||
@@ -16,13 +16,14 @@
|
|||||||
|
|
||||||
#include "congestion_control_feedback.h"
|
#include "congestion_control_feedback.h"
|
||||||
#include "nack.h"
|
#include "nack.h"
|
||||||
|
#include "report_block_data.h"
|
||||||
|
|
||||||
struct RtcpPacketInfo {
|
struct RtcpPacketInfo {
|
||||||
uint32_t packet_type_flags = 0; // RTCPPacketTypeFlags bit field.
|
uint32_t packet_type_flags = 0; // RTCPPacketTypeFlags bit field.
|
||||||
|
|
||||||
uint32_t remote_ssrc = 0;
|
uint32_t remote_ssrc = 0;
|
||||||
std::vector<uint16_t> nack_sequence_numbers;
|
std::vector<uint16_t> nack_sequence_numbers;
|
||||||
// std::vector<ReportBlockData> report_block_datas;
|
std::vector<RtcpReportBlock> report_block_datas;
|
||||||
std::optional<int64_t> rtt;
|
std::optional<int64_t> rtt;
|
||||||
uint32_t receiver_estimated_max_bitrate_bps = 0;
|
uint32_t receiver_estimated_max_bitrate_bps = 0;
|
||||||
std::optional<webrtc::rtcp::CongestionControlFeedback>
|
std::optional<webrtc::rtcp::CongestionControlFeedback>
|
||||||
|
|||||||
@@ -24,13 +24,19 @@
|
|||||||
// 24 +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+
|
// 24 +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+
|
||||||
|
|
||||||
RtcpReportBlock::RtcpReportBlock()
|
RtcpReportBlock::RtcpReportBlock()
|
||||||
: source_ssrc_(0),
|
: sender_ssrc_(0),
|
||||||
|
source_ssrc_(0),
|
||||||
fraction_lost_(0),
|
fraction_lost_(0),
|
||||||
cumulative_lost_(0),
|
cumulative_lost_(0),
|
||||||
extended_high_seq_num_(0),
|
extended_high_seq_num_(0),
|
||||||
jitter_(0),
|
jitter_(0),
|
||||||
last_sr_(0),
|
last_sr_(0),
|
||||||
delay_since_last_sr_(0) {}
|
delay_since_last_sr_(0),
|
||||||
|
report_block_timestamp_utc_(0),
|
||||||
|
report_block_timestamp_(0),
|
||||||
|
last_rtt_(0),
|
||||||
|
sum_rtt_(0),
|
||||||
|
num_rtts_(0) {}
|
||||||
|
|
||||||
size_t RtcpReportBlock::Create(uint8_t* buffer) const {
|
size_t RtcpReportBlock::Create(uint8_t* buffer) const {
|
||||||
buffer[0] = (source_ssrc_ >> 24) & 0xFF;
|
buffer[0] = (source_ssrc_ >> 24) & 0xFF;
|
||||||
@@ -84,4 +90,24 @@ size_t RtcpReportBlock::Parse(const uint8_t* buffer) {
|
|||||||
delay_since_last_sr_ =
|
delay_since_last_sr_ =
|
||||||
(buffer[20] << 24) | (buffer[21] << 16) | (buffer[22] << 8) | buffer[23];
|
(buffer[20] << 24) | (buffer[21] << 16) | (buffer[22] << 8) | buffer[23];
|
||||||
return RtcpReportBlock::kLength;
|
return RtcpReportBlock::kLength;
|
||||||
|
}
|
||||||
|
|
||||||
|
void RtcpReportBlock::SetReportBlock(uint32_t sender_ssrc,
|
||||||
|
const RtcpReportBlock& report_block,
|
||||||
|
int64_t report_block_timestamp_utc,
|
||||||
|
int64_t report_block_timestamp) {
|
||||||
|
sender_ssrc_ = sender_ssrc;
|
||||||
|
source_ssrc_ = report_block.SourceSsrc();
|
||||||
|
fraction_lost_ = report_block.FractionLost();
|
||||||
|
cumulative_lost_ = report_block.CumulativeLost();
|
||||||
|
extended_high_seq_num_ = report_block.ExtendedHighSeqNum();
|
||||||
|
jitter_ = report_block.Jitter();
|
||||||
|
report_block_timestamp_utc_ = report_block_timestamp_utc;
|
||||||
|
report_block_timestamp_ = report_block_timestamp;
|
||||||
|
}
|
||||||
|
|
||||||
|
void RtcpReportBlock::AddRoundTripTimeSample(int64_t rtt) {
|
||||||
|
last_rtt_ = rtt;
|
||||||
|
sum_rtt_ += rtt;
|
||||||
|
++num_rtts_;
|
||||||
}
|
}
|
||||||
@@ -45,6 +45,10 @@ class RtcpReportBlock {
|
|||||||
public:
|
public:
|
||||||
size_t Create(uint8_t* buffer) const;
|
size_t Create(uint8_t* buffer) const;
|
||||||
size_t Parse(const uint8_t* buffer);
|
size_t Parse(const uint8_t* buffer);
|
||||||
|
void SetReportBlock(uint32_t sender_ssrc, const RtcpReportBlock& report_block,
|
||||||
|
int64_t report_block_timestamp_utc,
|
||||||
|
int64_t report_block_timestamp);
|
||||||
|
void AddRoundTripTimeSample(int64_t rtt);
|
||||||
|
|
||||||
public:
|
public:
|
||||||
uint32_t SourceSsrc() const { return source_ssrc_; }
|
uint32_t SourceSsrc() const { return source_ssrc_; }
|
||||||
@@ -56,6 +60,7 @@ class RtcpReportBlock {
|
|||||||
uint32_t DelaySinceLastSr() const { return delay_since_last_sr_; }
|
uint32_t DelaySinceLastSr() const { return delay_since_last_sr_; }
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
uint32_t sender_ssrc_;
|
||||||
uint32_t source_ssrc_; // 32 bits
|
uint32_t source_ssrc_; // 32 bits
|
||||||
uint8_t fraction_lost_; // 8 bits representing a fixed point value 0..1
|
uint8_t fraction_lost_; // 8 bits representing a fixed point value 0..1
|
||||||
int32_t cumulative_lost_; // Signed 24-bit value
|
int32_t cumulative_lost_; // Signed 24-bit value
|
||||||
@@ -63,6 +68,13 @@ class RtcpReportBlock {
|
|||||||
uint32_t jitter_; // 32 bits
|
uint32_t jitter_; // 32 bits
|
||||||
uint32_t last_sr_; // 32 bits
|
uint32_t last_sr_; // 32 bits
|
||||||
uint32_t delay_since_last_sr_; // 32 bits, units of 1/65536 seconds
|
uint32_t delay_since_last_sr_; // 32 bits, units of 1/65536 seconds
|
||||||
|
|
||||||
|
int64_t report_block_timestamp_utc_;
|
||||||
|
int64_t report_block_timestamp_;
|
||||||
|
|
||||||
|
int64_t last_rtt_;
|
||||||
|
int64_t sum_rtt_;
|
||||||
|
size_t num_rtts_;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
@@ -299,6 +299,38 @@ bool IceTransport::ParseRtcpPacket(const uint8_t *buffer, size_t size,
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void IceTransport::HandleReportBlock(const RtcpReportBlock &rtcp_report_block,
|
||||||
|
RtcpPacketInfo *packet_information,
|
||||||
|
uint32_t remote_ssrc) {
|
||||||
|
int64_t now = clock_->CurrentTime();
|
||||||
|
|
||||||
|
RtcpReportBlock report_block_data;
|
||||||
|
|
||||||
|
int64_t now_ntp = clock_->ConvertToNtpTime(now);
|
||||||
|
// Number of seconds since 1900 January 1 00:00 GMT (see
|
||||||
|
// https://tools.ietf.org/html/rfc868).
|
||||||
|
report_block_data.SetReportBlock(remote_ssrc, rtcp_report_block,
|
||||||
|
clock_->NtpToUtc(now_ntp), now);
|
||||||
|
|
||||||
|
uint32_t send_time_ntp = rtcp_report_block.LastSr();
|
||||||
|
if (send_time_ntp != 0) {
|
||||||
|
uint32_t delay_ntp = rtcp_report_block.DelaySinceLastSr();
|
||||||
|
// Local NTP time.
|
||||||
|
constexpr uint64_t kNtpFractionalUnit = 0x100000000;
|
||||||
|
uint32_t seconds = now_ntp / kNtpFractionalUnit;
|
||||||
|
uint32_t fractions = now_ntp % kNtpFractionalUnit;
|
||||||
|
uint32_t receive_time_ntp = (seconds << 16) | (fractions >> 16);
|
||||||
|
// RTT in 1/(2^16) seconds.
|
||||||
|
uint32_t rtt_ntp = receive_time_ntp - delay_ntp - send_time_ntp;
|
||||||
|
// Convert to 1/1000 seconds (milliseconds).
|
||||||
|
int64_t rtt = static_cast<int64_t>((rtt_ntp * 1000) / (1 << 16));
|
||||||
|
report_block_data.AddRoundTripTimeSample(rtt);
|
||||||
|
packet_information->rtt = rtt;
|
||||||
|
}
|
||||||
|
|
||||||
|
packet_information->report_block_datas.push_back(report_block_data);
|
||||||
|
}
|
||||||
|
|
||||||
bool IceTransport::HandleSenderReport(const RtcpCommonHeader &rtcp_block,
|
bool IceTransport::HandleSenderReport(const RtcpCommonHeader &rtcp_block,
|
||||||
RtcpPacketInfo *rtcp_packet_info) {
|
RtcpPacketInfo *rtcp_packet_info) {
|
||||||
SenderReport sender_report;
|
SenderReport sender_report;
|
||||||
@@ -319,8 +351,17 @@ bool IceTransport::HandleReceiverReport(const RtcpCommonHeader &rtcp_block,
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const uint32_t remote_ssrc = receiver_report.SenderSsrc();
|
||||||
|
rtcp_packet_info->remote_ssrc = remote_ssrc;
|
||||||
|
|
||||||
|
for (const RtcpReportBlock &rtcp_report_block :
|
||||||
|
receiver_report.GetReportBlocks()) {
|
||||||
|
HandleReportBlock(rtcp_report_block, rtcp_packet_info, remote_ssrc);
|
||||||
|
}
|
||||||
|
|
||||||
if (ice_transport_controller_) {
|
if (ice_transport_controller_) {
|
||||||
ice_transport_controller_->OnReceiverReport(receiver_report);
|
ice_transport_controller_->OnReceiverReport(
|
||||||
|
rtcp_packet_info->report_block_datas);
|
||||||
}
|
}
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -130,6 +130,10 @@ class IceTransport {
|
|||||||
bool ParseRtcpPacket(const uint8_t *buffer, size_t size,
|
bool ParseRtcpPacket(const uint8_t *buffer, size_t size,
|
||||||
RtcpPacketInfo *rtcp_packet_info);
|
RtcpPacketInfo *rtcp_packet_info);
|
||||||
|
|
||||||
|
void HandleReportBlock(const RtcpReportBlock &rtcp_report_block,
|
||||||
|
RtcpPacketInfo *packet_information,
|
||||||
|
uint32_t remote_ssrc);
|
||||||
|
|
||||||
bool HandleSenderReport(const RtcpCommonHeader &rtcp_block,
|
bool HandleSenderReport(const RtcpCommonHeader &rtcp_block,
|
||||||
RtcpPacketInfo *rtcp_packet_info);
|
RtcpPacketInfo *rtcp_packet_info);
|
||||||
|
|
||||||
|
|||||||
@@ -6,14 +6,19 @@
|
|||||||
#include "nvcodec_api.h"
|
#include "nvcodec_api.h"
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#include "api/transport/network_types.h"
|
||||||
|
|
||||||
IceTransportController::IceTransportController(
|
IceTransportController::IceTransportController(
|
||||||
std::shared_ptr<SystemClock> clock)
|
std::shared_ptr<SystemClock> clock)
|
||||||
: clock_(clock),
|
: last_report_block_time_(
|
||||||
|
webrtc::Timestamp::Millis(webrtc_clock_->TimeInMilliseconds())),
|
||||||
b_force_i_frame_(true),
|
b_force_i_frame_(true),
|
||||||
video_codec_inited_(false),
|
video_codec_inited_(false),
|
||||||
audio_codec_inited_(false),
|
audio_codec_inited_(false),
|
||||||
load_nvcodec_dll_success_(false),
|
load_nvcodec_dll_success_(false),
|
||||||
hardware_acceleration_(false) {}
|
hardware_acceleration_(false),
|
||||||
|
clock_(clock),
|
||||||
|
webrtc_clock_(webrtc::Clock::GetWebrtcClockShared(clock)) {}
|
||||||
|
|
||||||
IceTransportController::~IceTransportController() {
|
IceTransportController::~IceTransportController() {
|
||||||
user_data_ = nullptr;
|
user_data_ = nullptr;
|
||||||
@@ -339,10 +344,48 @@ void IceTransportController::OnSenderReport(const SenderReport& sender_report) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void IceTransportController::OnReceiverReport(
|
void IceTransportController::OnReceiverReport(
|
||||||
const ReceiverReport& receiver_report) {
|
const std::vector<RtcpReportBlock>& report_block_datas) {
|
||||||
video_channel_send_->OnReceiverReport(receiver_report);
|
webrtc::Timestamp now = webrtc_clock_->CurrentTime();
|
||||||
audio_channel_send_->OnReceiverReport(receiver_report);
|
if (report_block_datas.empty()) return;
|
||||||
data_channel_send_->OnReceiverReport(receiver_report);
|
|
||||||
|
int total_packets_lost_delta = 0;
|
||||||
|
int total_packets_delta = 0;
|
||||||
|
|
||||||
|
for (const RtcpReportBlock& report_block : report_block_datas) {
|
||||||
|
auto [it, inserted] =
|
||||||
|
last_report_blocks_.try_emplace(report_block.SourceSsrc());
|
||||||
|
LossReport& last_loss_report = it->second;
|
||||||
|
if (!inserted) {
|
||||||
|
total_packets_delta += report_block.ExtendedHighSeqNum() -
|
||||||
|
last_loss_report.extended_highest_sequence_number;
|
||||||
|
total_packets_lost_delta +=
|
||||||
|
report_block.CumulativeLost() - last_loss_report.cumulative_lost;
|
||||||
|
}
|
||||||
|
last_loss_report.extended_highest_sequence_number =
|
||||||
|
report_block.ExtendedHighSeqNum();
|
||||||
|
last_loss_report.cumulative_lost = report_block.CumulativeLost();
|
||||||
|
}
|
||||||
|
// Can only compute delta if there has been previous blocks to compare to. If
|
||||||
|
// not, total_packets_delta will be unchanged and there's nothing more to do.
|
||||||
|
if (!total_packets_delta) return;
|
||||||
|
int packets_received_delta = total_packets_delta - total_packets_lost_delta;
|
||||||
|
// To detect lost packets, at least one packet has to be received. This check
|
||||||
|
// is needed to avoid bandwith detection update in
|
||||||
|
// VideoSendStreamTest.SuspendBelowMinBitrate
|
||||||
|
|
||||||
|
if (packets_received_delta < 1) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
webrtc::TransportLossReport msg;
|
||||||
|
msg.packets_lost_delta = total_packets_lost_delta;
|
||||||
|
msg.packets_received_delta = packets_received_delta;
|
||||||
|
msg.receive_time = now;
|
||||||
|
msg.start_time = last_report_block_time_;
|
||||||
|
msg.end_time = now;
|
||||||
|
if (controller_) {
|
||||||
|
PostUpdates(controller_->OnTransportLossReport(msg));
|
||||||
|
}
|
||||||
|
last_report_block_time_ = now;
|
||||||
}
|
}
|
||||||
|
|
||||||
void IceTransportController::OnCongestionControlFeedback(
|
void IceTransportController::OnCongestionControlFeedback(
|
||||||
|
|||||||
@@ -62,7 +62,7 @@ class IceTransportController
|
|||||||
|
|
||||||
public:
|
public:
|
||||||
void OnSenderReport(const SenderReport &sender_report);
|
void OnSenderReport(const SenderReport &sender_report);
|
||||||
void OnReceiverReport(const ReceiverReport& receiver_report);
|
void OnReceiverReport(const std::vector<RtcpReportBlock> &report_block_datas);
|
||||||
void OnCongestionControlFeedback(
|
void OnCongestionControlFeedback(
|
||||||
const webrtc::rtcp::CongestionControlFeedback &feedback);
|
const webrtc::rtcp::CongestionControlFeedback &feedback);
|
||||||
|
|
||||||
@@ -101,6 +101,7 @@ class IceTransportController
|
|||||||
|
|
||||||
private:
|
private:
|
||||||
std::shared_ptr<SystemClock> clock_;
|
std::shared_ptr<SystemClock> clock_;
|
||||||
|
std::shared_ptr<webrtc::Clock> webrtc_clock_ = nullptr;
|
||||||
webrtc::TransportFeedbackAdapter transport_feedback_adapter_;
|
webrtc::TransportFeedbackAdapter transport_feedback_adapter_;
|
||||||
std::unique_ptr<CongestionControl> controller_;
|
std::unique_ptr<CongestionControl> controller_;
|
||||||
|
|
||||||
@@ -119,6 +120,13 @@ class IceTransportController
|
|||||||
|
|
||||||
private:
|
private:
|
||||||
int64_t target_bitrate_ = 0;
|
int64_t target_bitrate_ = 0;
|
||||||
|
|
||||||
|
struct LossReport {
|
||||||
|
uint32_t extended_highest_sequence_number = 0;
|
||||||
|
int cumulative_lost = 0;
|
||||||
|
};
|
||||||
|
std::map<uint32_t, LossReport> last_report_blocks_;
|
||||||
|
webrtc::Timestamp last_report_block_time_;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
@@ -141,8 +141,10 @@ target("qos")
|
|||||||
target("channel")
|
target("channel")
|
||||||
set_kind("object")
|
set_kind("object")
|
||||||
add_deps("log", "rtp", "rtcp", "ice", "qos")
|
add_deps("log", "rtp", "rtcp", "ice", "qos")
|
||||||
add_files("src/channel/*.cpp", "src/channel/rtp_channel/*.cpp")
|
add_files("src/channel/meida_channel/*.cpp",
|
||||||
add_includedirs("src/channel", "src/channel/rtp_channel", {public = true})
|
"src/channel/rtp_channel/*.cpp")
|
||||||
|
add_includedirs("src/channel/meida_channel",
|
||||||
|
"src/channel/rtp_channel", {public = true})
|
||||||
|
|
||||||
target("transport")
|
target("transport")
|
||||||
set_kind("object")
|
set_kind("object")
|
||||||
|
|||||||
Reference in New Issue
Block a user