From 6faba6edc9208c85a935406f4a213ec0773e5197 Mon Sep 17 00:00:00 2001 From: "mikhal@webrtc.org" Date: Tue, 30 Apr 2013 15:39:34 +0000 Subject: [PATCH] VCM: Setting buffering delay in timing Review URL: https://webrtc-codereview.appspot.com/1338004 git-svn-id: http://webrtc.googlecode.com/svn/trunk@3921 4adac7df-926f-26a2-2b94-8c16560cd09d --- .../video_coding/main/source/jitter_buffer.cc | 4 +-- .../video_coding/main/source/jitter_buffer.h | 2 +- .../main/source/jitter_buffer_unittest.cc | 5 +--- .../main/source/jitter_estimator.cc | 19 +++++------- .../main/source/jitter_estimator.h | 7 ++--- .../video_coding/main/source/receiver.cc | 6 ++-- .../video_coding/main/source/timing.cc | 30 ++++++------------- 7 files changed, 26 insertions(+), 47 deletions(-) diff --git a/webrtc/modules/video_coding/main/source/jitter_buffer.cc b/webrtc/modules/video_coding/main/source/jitter_buffer.cc index 6f133b3cad..64ca6a168a 100644 --- a/webrtc/modules/video_coding/main/source/jitter_buffer.cc +++ b/webrtc/modules/video_coding/main/source/jitter_buffer.cc @@ -793,9 +793,9 @@ VCMFrameBufferEnum VCMJitterBuffer::InsertPacket(VCMEncodedFrame* encoded_frame, return ret; } -void VCMJitterBuffer::SetMaxJitterEstimate(uint32_t initial_delay_ms) { +void VCMJitterBuffer::SetMaxJitterEstimate(bool enable) { CriticalSectionScoped cs(crit_sect_); - jitter_estimate_.SetMaxJitterEstimate(initial_delay_ms); + jitter_estimate_.SetMaxJitterEstimate(enable); } uint32_t VCMJitterBuffer::EstimatedJitterMs() { diff --git a/webrtc/modules/video_coding/main/source/jitter_buffer.h b/webrtc/modules/video_coding/main/source/jitter_buffer.h index 81a637a108..21f3db8d7f 100644 --- a/webrtc/modules/video_coding/main/source/jitter_buffer.h +++ b/webrtc/modules/video_coding/main/source/jitter_buffer.h @@ -135,7 +135,7 @@ class VCMJitterBuffer { // Enable a max filter on the jitter estimate by setting an initial // non-zero delay. When set to zero (default), the last jitter // estimate will be used. - void SetMaxJitterEstimate(uint32_t initial_delay_ms); + void SetMaxJitterEstimate(bool enable); // Returns the estimated jitter in milliseconds. uint32_t EstimatedJitterMs(); diff --git a/webrtc/modules/video_coding/main/source/jitter_buffer_unittest.cc b/webrtc/modules/video_coding/main/source/jitter_buffer_unittest.cc index 7971fae340..d2b5a769d2 100644 --- a/webrtc/modules/video_coding/main/source/jitter_buffer_unittest.cc +++ b/webrtc/modules/video_coding/main/source/jitter_buffer_unittest.cc @@ -177,12 +177,9 @@ TEST_F(TestRunningJitterBuffer, JitterEstimateMode) { InsertFrame(kVideoFrameDelta); EXPECT_FALSE(request_key_frame); EXPECT_GT(20u, jitter_buffer_->EstimatedJitterMs()); - // Set kMaxEstimate with a 2 seconds initial delay. - jitter_buffer_->SetMaxJitterEstimate(2000u); - EXPECT_EQ(2000u, jitter_buffer_->EstimatedJitterMs()); + jitter_buffer_->SetMaxJitterEstimate(true); InsertFrame(kVideoFrameDelta); EXPECT_FALSE(request_key_frame); - EXPECT_EQ(2000u, jitter_buffer_->EstimatedJitterMs()); // Jitter cannot decrease. InsertFrames(2, kVideoFrameDelta); EXPECT_FALSE(request_key_frame); diff --git a/webrtc/modules/video_coding/main/source/jitter_estimator.cc b/webrtc/modules/video_coding/main/source/jitter_estimator.cc index 191102a445..45b54225a2 100644 --- a/webrtc/modules/video_coding/main/source/jitter_estimator.cc +++ b/webrtc/modules/video_coding/main/source/jitter_estimator.cc @@ -20,8 +20,6 @@ namespace webrtc { -enum { kInitialMaxJitterEstimate = 0 }; - VCMJitterEstimator::VCMJitterEstimator(int32_t vcmId, int32_t receiverId) : _vcmId(vcmId), _receiverId(receiverId), @@ -37,7 +35,7 @@ _noiseStdDevs(2.33), // ~Less than 1% chance _noiseStdDevOffset(30.0), // ...of getting 30 ms freezes _rttFilter(vcmId, receiverId), _jitterEstimateMode(kLastEstimate), -_maxJitterEstimateMs(kInitialMaxJitterEstimate) +_maxJitterEstimateMs(0) { Reset(); } @@ -407,15 +405,12 @@ VCMJitterEstimator::UpdateMaxFrameSize(uint32_t frameSizeBytes) } } -void VCMJitterEstimator::SetMaxJitterEstimate(uint32_t initial_delay_ms) -{ - if (initial_delay_ms > 0) { - _maxJitterEstimateMs = initial_delay_ms; - _jitterEstimateMode = kMaxEstimate; - } else { - _maxJitterEstimateMs = kInitialMaxJitterEstimate; - _jitterEstimateMode = kLastEstimate; - } +void VCMJitterEstimator::SetMaxJitterEstimate(bool enable) { + if (enable) { + _jitterEstimateMode = kMaxEstimate; + } else { + _jitterEstimateMode = kLastEstimate; + } } // Returns the current filtered estimate if available, diff --git a/webrtc/modules/video_coding/main/source/jitter_estimator.h b/webrtc/modules/video_coding/main/source/jitter_estimator.h index f896c6fdf1..ad09277e0b 100644 --- a/webrtc/modules/video_coding/main/source/jitter_estimator.h +++ b/webrtc/modules/video_coding/main/source/jitter_estimator.h @@ -64,10 +64,9 @@ public: void UpdateMaxFrameSize(uint32_t frameSizeBytes); - // Set a max filter on the jitter estimate by setting an initial - // non-zero delay. When set to zero (default), the last jitter - // estimate will be used. - void SetMaxJitterEstimate(uint32_t initial_delay_ms); + // Set a max filter on the jitter estimate. When disabled (default), the + // last jitter estimate will be used. + void SetMaxJitterEstimate(bool enable); // A constant describing the delay from the jitter buffer // to the delay on the receiving side which is not accounted diff --git a/webrtc/modules/video_coding/main/source/receiver.cc b/webrtc/modules/video_coding/main/source/receiver.cc index ae0f1cec92..c77936c08f 100644 --- a/webrtc/modules/video_coding/main/source/receiver.cc +++ b/webrtc/modules/video_coding/main/source/receiver.cc @@ -430,11 +430,11 @@ int VCMReceiver::SetMinReceiverDelay(int desired_delay_ms) { if (desired_delay_ms < 0 || desired_delay_ms > kMaxReceiverDelayMs) { return -1; } - jitter_buffer_.SetMaxJitterEstimate(desired_delay_ms); + // Enable a max filter on the jitter estimate for non-zero delays. + jitter_buffer_.SetMaxJitterEstimate(desired_delay_ms > 0); max_video_delay_ms_ = desired_delay_ms + kMaxVideoDelayMs; - timing_->SetMaxVideoDelay(max_video_delay_ms_); // Initializing timing to the desired delay. - timing_->SetRequiredDelay(desired_delay_ms); + timing_->SetMinimumTotalDelay(desired_delay_ms); return 0; } diff --git a/webrtc/modules/video_coding/main/source/timing.cc b/webrtc/modules/video_coding/main/source/timing.cc index 1146223482..1e0475b607 100644 --- a/webrtc/modules/video_coding/main/source/timing.cc +++ b/webrtc/modules/video_coding/main/source/timing.cc @@ -120,12 +120,6 @@ void VCMTiming::UpdateCurrentDelay(uint32_t frameTimestamp) CriticalSectionScoped cs(_critSect); uint32_t targetDelayMs = TargetDelayInternal(); - // Make sure we try to sync with audio - if (targetDelayMs < _minTotalDelayMs) - { - targetDelayMs = _minTotalDelayMs; - } - if (_currentDelayMs == 0) { // Not initialized, set current delay to target. @@ -159,14 +153,9 @@ void VCMTiming::UpdateCurrentDelay(uint32_t frameTimestamp) // to reordering and should be ignored. return; } - else if (delayDiffMs < -maxChangeMs) - { - delayDiffMs = -maxChangeMs; - } - else if (delayDiffMs > maxChangeMs) - { - delayDiffMs = maxChangeMs; - } + delayDiffMs = std::max(delayDiffMs, -maxChangeMs); + delayDiffMs = std::min(delayDiffMs, maxChangeMs); + _currentDelayMs = _currentDelayMs + static_cast(delayDiffMs); } _prevFrameTimestamp = frameTimestamp; @@ -177,18 +166,14 @@ void VCMTiming::UpdateCurrentDelay(int64_t renderTimeMs, { CriticalSectionScoped cs(_critSect); uint32_t targetDelayMs = TargetDelayInternal(); - // Make sure we try to sync with audio - if (targetDelayMs < _minTotalDelayMs) - { - targetDelayMs = _minTotalDelayMs; - } + int64_t delayedMs = actualDecodeTimeMs - (renderTimeMs - MaxDecodeTimeMs() - _renderDelayMs); if (delayedMs < 0) { return; } - else if (_currentDelayMs + delayedMs <= targetDelayMs) + if (_currentDelayMs + delayedMs <= targetDelayMs) { _currentDelayMs += static_cast(delayedMs); } @@ -274,7 +259,10 @@ VCMTiming::RenderTimeMsInternal(uint32_t frameTimestamp, int64_t nowMs) const { estimatedCompleteTimeMs = nowMs; } - return estimatedCompleteTimeMs + _currentDelayMs; + + // Make sure that we have at least the total minimum delay. + uint32_t actual_delay = std::max(_currentDelayMs, _minTotalDelayMs); + return estimatedCompleteTimeMs + actual_delay; } // Must be called from inside a critical section