Skip to content

Commit

Permalink
Add small cooldown to unsignalled ssrc stream creation.
Browse files Browse the repository at this point in the history
This CL adds a cooldown of 0.5 seconds where if the WebRtcVideoChannel
created an unsignalled receive stream within that amount of time, if we
receive even more unknown ssrcs we simply drop those RTP packets.

This prevents getting into a state of spawning new decoders on every
single packet which could happen e.g. if PT based demuxing is enabled
and MIDs are missing from the packets.

Bug: webrtc:12815
Change-Id: Id7675fb0cbfbc72281dcfe030d1a35629df3eb9f
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/221520
Reviewed-by: Taylor Brandstetter <[email protected]>
Reviewed-by: Harald Alvestrand <[email protected]>
Commit-Queue: Henrik Boström <[email protected]>
Cr-Commit-Position: refs/heads/master@{#34263}
  • Loading branch information
henbos authored and WebRTC LUCI CQ committed Jun 10, 2021
1 parent ba7da8b commit 62ec0f6
Show file tree
Hide file tree
Showing 3 changed files with 120 additions and 48 deletions.
21 changes: 20 additions & 1 deletion media/engine/webrtc_video_engine.cc
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,7 @@ namespace cricket {
namespace {

const int kMinLayerSize = 16;
constexpr int64_t kUnsignaledSsrcCooldownMs = rtc::kNumMillisecsPerSec / 2;

const char* StreamTypeToString(
webrtc::VideoSendStream::StreamStats::StreamType type) {
Expand Down Expand Up @@ -1565,6 +1566,7 @@ void WebRtcVideoChannel::ResetUnsignaledRecvStream() {
RTC_DCHECK_RUN_ON(&thread_checker_);
RTC_LOG(LS_INFO) << "ResetUnsignaledRecvStream.";
unsignaled_stream_params_ = StreamParams();
last_unsignalled_ssrc_creation_time_ms_ = absl::nullopt;

// Delete any created default streams. This is needed to avoid SSRC collisions
// in Call's RtpDemuxer, in the case that |this| has created a default video
Expand Down Expand Up @@ -1767,7 +1769,23 @@ void WebRtcVideoChannel::OnPacketReceived(rtc::CopyOnWriteBuffer packet,
if (demuxer_criteria_id_ != demuxer_criteria_completed_id_) {
return;
}

// Ignore unknown ssrcs if we recently created an unsignalled receive
// stream since this shouldn't happen frequently. Getting into a state
// of creating decoders on every packet eats up processing time (e.g.
// https://crbug.com/1069603) and this cooldown prevents that.
if (last_unsignalled_ssrc_creation_time_ms_.has_value()) {
int64_t now_ms = rtc::TimeMillis();
if (now_ms - last_unsignalled_ssrc_creation_time_ms_.value() <
kUnsignaledSsrcCooldownMs) {
// We've already created an unsignalled ssrc stream within the last
// 0.5 s, ignore with a warning.
RTC_LOG(LS_WARNING)
<< "Another unsignalled ssrc packet arrived shortly after the "
<< "creation of an unsignalled ssrc stream. Dropping packet.";
return;
}
}
// Let the unsignalled ssrc handler decide whether to drop or deliver.
switch (unsignalled_ssrc_handler_->OnUnsignalledSsrc(this, ssrc)) {
case UnsignalledSsrcHandler::kDropPacket:
return;
Expand All @@ -1780,6 +1798,7 @@ void WebRtcVideoChannel::OnPacketReceived(rtc::CopyOnWriteBuffer packet,
webrtc::PacketReceiver::DELIVERY_OK) {
RTC_LOG(LS_WARNING) << "Failed to deliver RTP packet on re-delivery.";
}
last_unsignalled_ssrc_creation_time_ms_ = rtc::TimeMillis();
}));
}

Expand Down
2 changes: 2 additions & 0 deletions media/engine/webrtc_video_engine.h
Original file line number Diff line number Diff line change
Expand Up @@ -588,6 +588,8 @@ class WebRtcVideoChannel : public VideoMediaChannel,
// is a risk of receiving ssrcs for other, recently added m= sections.
uint32_t demuxer_criteria_id_ RTC_GUARDED_BY(thread_checker_) = 0;
uint32_t demuxer_criteria_completed_id_ RTC_GUARDED_BY(thread_checker_) = 0;
absl::optional<int64_t> last_unsignalled_ssrc_creation_time_ms_
RTC_GUARDED_BY(thread_checker_);
std::set<uint32_t> send_ssrcs_ RTC_GUARDED_BY(thread_checker_);
std::set<uint32_t> receive_ssrcs_ RTC_GUARDED_BY(thread_checker_);

Expand Down
Loading

0 comments on commit 62ec0f6

Please sign in to comment.