Restricting NetEq postpone decoding after expand.
Bug: webrtc:9289 Change-Id: I923f304e6c12423fe5323c62484a27346033b19a Reviewed-on: https://webrtc-review.googlesource.com/c/98320 Commit-Queue: Minyue Li <minyue@webrtc.org> Reviewed-by: Henrik Lundin <henrik.lundin@webrtc.org> Reviewed-by: Ivo Creusen <ivoc@webrtc.org> Cr-Commit-Position: refs/heads/master@{#24966}
This commit is contained in:
@ -21,8 +21,38 @@
|
||||
#include "modules/audio_coding/neteq/packet_buffer.h"
|
||||
#include "modules/audio_coding/neteq/sync_buffer.h"
|
||||
#include "modules/include/module_common_types.h"
|
||||
#include "rtc_base/logging.h"
|
||||
#include "system_wrappers/include/field_trial.h"
|
||||
|
||||
namespace {
|
||||
constexpr char kPostponeDecodingFieldTrial[] =
|
||||
"WebRTC-Audio-NetEqPostponeDecodingAfterExpand";
|
||||
|
||||
int GetPostponeDecodingLevel() {
|
||||
const bool enabled =
|
||||
webrtc::field_trial::IsEnabled(kPostponeDecodingFieldTrial);
|
||||
if (!enabled)
|
||||
return 0;
|
||||
|
||||
constexpr int kDefaultPostponeDecodingLevel = 50;
|
||||
const std::string field_trial_string =
|
||||
webrtc::field_trial::FindFullName(kPostponeDecodingFieldTrial);
|
||||
int value = -1;
|
||||
if (sscanf(field_trial_string.c_str(), "Enabled-%d", &value) == 1) {
|
||||
if (value >= 0 && value <= 100) {
|
||||
return value;
|
||||
} else {
|
||||
RTC_LOG(LS_WARNING)
|
||||
<< "Wrong value (" << value
|
||||
<< ") for postpone decoding after expand, using default ("
|
||||
<< kDefaultPostponeDecodingLevel << ")";
|
||||
}
|
||||
}
|
||||
return kDefaultPostponeDecodingLevel;
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
||||
namespace webrtc {
|
||||
|
||||
DecisionLogic* DecisionLogic::Create(int fs_hz,
|
||||
@ -59,8 +89,7 @@ DecisionLogic::DecisionLogic(int fs_hz,
|
||||
timescale_countdown_(
|
||||
tick_timer_->GetNewCountdown(kMinTimescaleInterval + 1)),
|
||||
num_consecutive_expands_(0),
|
||||
postpone_decoding_after_expand_(field_trial::IsEnabled(
|
||||
"WebRTC-Audio-NetEqPostponeDecodingAfterExpand")) {
|
||||
postpone_decoding_level_(GetPostponeDecodingLevel()) {
|
||||
delay_manager_->set_streaming_mode(false);
|
||||
SetSampleRate(fs_hz, output_size_samples);
|
||||
}
|
||||
@ -164,12 +193,13 @@ Operations DecisionLogic::GetDecision(const SyncBuffer& sync_buffer,
|
||||
// if the mute factor is low enough (otherwise the expansion was short enough
|
||||
// to not be noticable).
|
||||
// Note that the MuteFactor is in Q14, so a value of 16384 corresponds to 1.
|
||||
if (postpone_decoding_after_expand_ &&
|
||||
(prev_mode == kModeExpand || prev_mode == kModeCodecPlc) &&
|
||||
!packet_buffer_.ContainsDtxOrCngPacket(decoder_database_) &&
|
||||
cur_size_samples<static_cast<size_t>(delay_manager_->TargetLevel() *
|
||||
packet_length_samples_)>> 8 &&
|
||||
expand.MuteFactor(0) < 16384 / 2) {
|
||||
if ((prev_mode == kModeExpand || prev_mode == kModeCodecPlc) &&
|
||||
expand.MuteFactor(0) < 16384 / 2 &&
|
||||
cur_size_samples < static_cast<size_t>(
|
||||
delay_manager_->TargetLevel() * packet_length_samples_ *
|
||||
postpone_decoding_level_ / 100) >> 8 &&
|
||||
!packet_buffer_.ContainsDtxOrCngPacket(decoder_database_)) {
|
||||
RTC_DCHECK(webrtc::field_trial::IsEnabled(kPostponeDecodingFieldTrial));
|
||||
return kExpand;
|
||||
}
|
||||
|
||||
|
@ -109,6 +109,10 @@ class DecisionLogic final {
|
||||
}
|
||||
void set_prev_time_scale(bool value) { prev_time_scale_ = value; }
|
||||
|
||||
int postpone_decoding_level_for_test() const {
|
||||
return postpone_decoding_level_;
|
||||
}
|
||||
|
||||
private:
|
||||
// The value 5 sets maximum time-stretch rate to about 100 ms/s.
|
||||
static const int kMinTimescaleInterval = 5;
|
||||
@ -181,7 +185,7 @@ class DecisionLogic final {
|
||||
bool disallow_time_stretching_;
|
||||
std::unique_ptr<TickTimer::Countdown> timescale_countdown_;
|
||||
int num_consecutive_expands_;
|
||||
const bool postpone_decoding_after_expand_;
|
||||
const int postpone_decoding_level_;
|
||||
|
||||
RTC_DISALLOW_COPY_AND_ASSIGN(DecisionLogic);
|
||||
};
|
||||
|
@ -17,6 +17,7 @@
|
||||
#include "modules/audio_coding/neteq/delay_peak_detector.h"
|
||||
#include "modules/audio_coding/neteq/packet_buffer.h"
|
||||
#include "modules/audio_coding/neteq/tick_timer.h"
|
||||
#include "test/field_trial.h"
|
||||
#include "test/gtest.h"
|
||||
#include "test/mock_audio_decoder_factory.h"
|
||||
|
||||
@ -38,6 +39,62 @@ TEST(DecisionLogic, CreateAndDestroy) {
|
||||
delete logic;
|
||||
}
|
||||
|
||||
TEST(DecisionLogic, PostponeDecodingAfterExpansionSettings) {
|
||||
constexpr int kDefaultPostponeDecodingLevel = 50;
|
||||
constexpr int kFsHz = 8000;
|
||||
constexpr int kOutputSizeSamples = kFsHz / 100; // Samples per 10 ms.
|
||||
DecoderDatabase decoder_database(
|
||||
new rtc::RefCountedObject<MockAudioDecoderFactory>, absl::nullopt);
|
||||
TickTimer tick_timer;
|
||||
PacketBuffer packet_buffer(10, &tick_timer);
|
||||
DelayPeakDetector delay_peak_detector(&tick_timer);
|
||||
DelayManager delay_manager(240, &delay_peak_detector, &tick_timer);
|
||||
BufferLevelFilter buffer_level_filter;
|
||||
{
|
||||
test::ScopedFieldTrials field_trial(
|
||||
"WebRTC-Audio-NetEqPostponeDecodingAfterExpand/Enabled/");
|
||||
DecisionLogic logic(kFsHz, kOutputSizeSamples, false, &decoder_database,
|
||||
packet_buffer, &delay_manager, &buffer_level_filter,
|
||||
&tick_timer);
|
||||
EXPECT_EQ(kDefaultPostponeDecodingLevel,
|
||||
logic.postpone_decoding_level_for_test());
|
||||
}
|
||||
{
|
||||
test::ScopedFieldTrials field_trial(
|
||||
"WebRTC-Audio-NetEqPostponeDecodingAfterExpand/Enabled-65/");
|
||||
DecisionLogic logic(kFsHz, kOutputSizeSamples, false, &decoder_database,
|
||||
packet_buffer, &delay_manager, &buffer_level_filter,
|
||||
&tick_timer);
|
||||
EXPECT_EQ(65, logic.postpone_decoding_level_for_test());
|
||||
}
|
||||
{
|
||||
test::ScopedFieldTrials field_trial(
|
||||
"WebRTC-Audio-NetEqPostponeDecodingAfterExpand/Disabled/");
|
||||
DecisionLogic logic(kFsHz, kOutputSizeSamples, false, &decoder_database,
|
||||
packet_buffer, &delay_manager, &buffer_level_filter,
|
||||
&tick_timer);
|
||||
EXPECT_EQ(0, logic.postpone_decoding_level_for_test());
|
||||
}
|
||||
{
|
||||
test::ScopedFieldTrials field_trial(
|
||||
"WebRTC-Audio-NetEqPostponeDecodingAfterExpand/Enabled--1/");
|
||||
DecisionLogic logic(kFsHz, kOutputSizeSamples, false, &decoder_database,
|
||||
packet_buffer, &delay_manager, &buffer_level_filter,
|
||||
&tick_timer);
|
||||
EXPECT_EQ(kDefaultPostponeDecodingLevel,
|
||||
logic.postpone_decoding_level_for_test());
|
||||
}
|
||||
{
|
||||
test::ScopedFieldTrials field_trial(
|
||||
"WebRTC-Audio-NetEqPostponeDecodingAfterExpand/Enabled-101/");
|
||||
DecisionLogic logic(kFsHz, kOutputSizeSamples, false, &decoder_database,
|
||||
packet_buffer, &delay_manager, &buffer_level_filter,
|
||||
&tick_timer);
|
||||
EXPECT_EQ(kDefaultPostponeDecodingLevel,
|
||||
logic.postpone_decoding_level_for_test());
|
||||
}
|
||||
}
|
||||
|
||||
// TODO(hlundin): Write more tests.
|
||||
|
||||
} // namespace webrtc
|
||||
|
Reference in New Issue
Block a user