diff --git a/webrtc/modules/audio_coding/BUILD.gn b/webrtc/modules/audio_coding/BUILD.gn index d1f70cf105..f072f31a58 100644 --- a/webrtc/modules/audio_coding/BUILD.gn +++ b/webrtc/modules/audio_coding/BUILD.gn @@ -813,8 +813,8 @@ source_set("neteq") { "neteq/include/neteq.h", "neteq/merge.cc", "neteq/merge.h", - "neteq/nack.cc", - "neteq/nack.h", + "neteq/nack_tracker.cc", + "neteq/nack_tracker.h", "neteq/neteq.cc", "neteq/neteq_impl.cc", "neteq/neteq_impl.h", diff --git a/webrtc/modules/audio_coding/neteq/nack.cc b/webrtc/modules/audio_coding/neteq/nack_tracker.cc similarity index 83% rename from webrtc/modules/audio_coding/neteq/nack.cc rename to webrtc/modules/audio_coding/neteq/nack_tracker.cc index 011914b3d9..62cb2ec958 100644 --- a/webrtc/modules/audio_coding/neteq/nack.cc +++ b/webrtc/modules/audio_coding/neteq/nack_tracker.cc @@ -8,7 +8,7 @@ * be found in the AUTHORS file in the root of the source tree. */ -#include "webrtc/modules/audio_coding/neteq/nack.h" +#include "webrtc/modules/audio_coding/neteq/nack_tracker.h" #include // For assert. @@ -26,7 +26,7 @@ const int kDefaultPacketSizeMs = 20; } // namespace -Nack::Nack(int nack_threshold_packets) +NackTracker::NackTracker(int nack_threshold_packets) : nack_threshold_packets_(nack_threshold_packets), sequence_num_last_received_rtp_(0), timestamp_last_received_rtp_(0), @@ -38,19 +38,19 @@ Nack::Nack(int nack_threshold_packets) samples_per_packet_(sample_rate_khz_ * kDefaultPacketSizeMs), max_nack_list_size_(kNackListSizeLimit) {} -Nack::~Nack() = default; +NackTracker::~NackTracker() = default; -Nack* Nack::Create(int nack_threshold_packets) { - return new Nack(nack_threshold_packets); +NackTracker* NackTracker::Create(int nack_threshold_packets) { + return new NackTracker(nack_threshold_packets); } -void Nack::UpdateSampleRate(int sample_rate_hz) { +void NackTracker::UpdateSampleRate(int sample_rate_hz) { assert(sample_rate_hz > 0); sample_rate_khz_ = sample_rate_hz / 1000; } -void Nack::UpdateLastReceivedPacket(uint16_t sequence_number, - uint32_t timestamp) { +void NackTracker::UpdateLastReceivedPacket(uint16_t sequence_number, + uint32_t timestamp) { // Just record the value of sequence number and timestamp if this is the // first packet. if (!any_rtp_received_) { @@ -85,8 +85,9 @@ void Nack::UpdateLastReceivedPacket(uint16_t sequence_number, LimitNackListSize(); } -void Nack::UpdateSamplesPerPacket(uint16_t sequence_number_current_received_rtp, - uint32_t timestamp_current_received_rtp) { +void NackTracker::UpdateSamplesPerPacket( + uint16_t sequence_number_current_received_rtp, + uint32_t timestamp_current_received_rtp) { uint32_t timestamp_increase = timestamp_current_received_rtp - timestamp_last_received_rtp_; uint16_t sequence_num_increase = @@ -95,7 +96,7 @@ void Nack::UpdateSamplesPerPacket(uint16_t sequence_number_current_received_rtp, samples_per_packet_ = timestamp_increase / sequence_num_increase; } -void Nack::UpdateList(uint16_t sequence_number_current_received_rtp) { +void NackTracker::UpdateList(uint16_t sequence_number_current_received_rtp) { // Some of the packets which were considered late, now are considered missing. ChangeFromLateToMissing(sequence_number_current_received_rtp); @@ -104,7 +105,7 @@ void Nack::UpdateList(uint16_t sequence_number_current_received_rtp) { AddToList(sequence_number_current_received_rtp); } -void Nack::ChangeFromLateToMissing( +void NackTracker::ChangeFromLateToMissing( uint16_t sequence_number_current_received_rtp) { NackList::const_iterator lower_bound = nack_list_.lower_bound(static_cast( @@ -114,12 +115,12 @@ void Nack::ChangeFromLateToMissing( it->second.is_missing = true; } -uint32_t Nack::EstimateTimestamp(uint16_t sequence_num) { +uint32_t NackTracker::EstimateTimestamp(uint16_t sequence_num) { uint16_t sequence_num_diff = sequence_num - sequence_num_last_received_rtp_; return sequence_num_diff * samples_per_packet_ + timestamp_last_received_rtp_; } -void Nack::AddToList(uint16_t sequence_number_current_received_rtp) { +void NackTracker::AddToList(uint16_t sequence_number_current_received_rtp) { assert(!any_rtp_decoded_ || IsNewerSequenceNumber(sequence_number_current_received_rtp, sequence_num_last_decoded_rtp_)); @@ -138,7 +139,7 @@ void Nack::AddToList(uint16_t sequence_number_current_received_rtp) { } } -void Nack::UpdateEstimatedPlayoutTimeBy10ms() { +void NackTracker::UpdateEstimatedPlayoutTimeBy10ms() { while (!nack_list_.empty() && nack_list_.begin()->second.time_to_play_ms <= 10) nack_list_.erase(nack_list_.begin()); @@ -147,8 +148,8 @@ void Nack::UpdateEstimatedPlayoutTimeBy10ms() { it->second.time_to_play_ms -= 10; } -void Nack::UpdateLastDecodedPacket(uint16_t sequence_number, - uint32_t timestamp) { +void NackTracker::UpdateLastDecodedPacket(uint16_t sequence_number, + uint32_t timestamp) { if (IsNewerSequenceNumber(sequence_number, sequence_num_last_decoded_rtp_) || !any_rtp_decoded_) { sequence_num_last_decoded_rtp_ = sequence_number; @@ -177,11 +178,11 @@ void Nack::UpdateLastDecodedPacket(uint16_t sequence_number, any_rtp_decoded_ = true; } -Nack::NackList Nack::GetNackList() const { +NackTracker::NackList NackTracker::GetNackList() const { return nack_list_; } -void Nack::Reset() { +void NackTracker::Reset() { nack_list_.clear(); sequence_num_last_received_rtp_ = 0; @@ -194,29 +195,30 @@ void Nack::Reset() { samples_per_packet_ = sample_rate_khz_ * kDefaultPacketSizeMs; } -void Nack::SetMaxNackListSize(size_t max_nack_list_size) { +void NackTracker::SetMaxNackListSize(size_t max_nack_list_size) { RTC_CHECK_GT(max_nack_list_size, 0u); // Ugly hack to get around the problem of passing static consts by reference. - const size_t kNackListSizeLimitLocal = Nack::kNackListSizeLimit; + const size_t kNackListSizeLimitLocal = NackTracker::kNackListSizeLimit; RTC_CHECK_LE(max_nack_list_size, kNackListSizeLimitLocal); max_nack_list_size_ = max_nack_list_size; LimitNackListSize(); } -void Nack::LimitNackListSize() { +void NackTracker::LimitNackListSize() { uint16_t limit = sequence_num_last_received_rtp_ - static_cast(max_nack_list_size_) - 1; nack_list_.erase(nack_list_.begin(), nack_list_.upper_bound(limit)); } -int64_t Nack::TimeToPlay(uint32_t timestamp) const { +int64_t NackTracker::TimeToPlay(uint32_t timestamp) const { uint32_t timestamp_increase = timestamp - timestamp_last_decoded_rtp_; return timestamp_increase / sample_rate_khz_; } // We don't erase elements with time-to-play shorter than round-trip-time. -std::vector Nack::GetNackList(int64_t round_trip_time_ms) const { +std::vector NackTracker::GetNackList( + int64_t round_trip_time_ms) const { RTC_DCHECK_GE(round_trip_time_ms, 0); std::vector sequence_numbers; for (NackList::const_iterator it = nack_list_.begin(); it != nack_list_.end(); diff --git a/webrtc/modules/audio_coding/neteq/nack.h b/webrtc/modules/audio_coding/neteq/nack_tracker.h similarity index 88% rename from webrtc/modules/audio_coding/neteq/nack.h rename to webrtc/modules/audio_coding/neteq/nack_tracker.h index c46a85a770..de97d91cf2 100644 --- a/webrtc/modules/audio_coding/neteq/nack.h +++ b/webrtc/modules/audio_coding/neteq/nack_tracker.h @@ -8,8 +8,8 @@ * be found in the AUTHORS file in the root of the source tree. */ -#ifndef WEBRTC_MODULES_AUDIO_CODING_NETEQ_NACK_H_ -#define WEBRTC_MODULES_AUDIO_CODING_NETEQ_NACK_H_ +#ifndef WEBRTC_MODULES_AUDIO_CODING_NETEQ_NACK_TRACKER_H_ +#define WEBRTC_MODULES_AUDIO_CODING_NETEQ_NACK_TRACKER_H_ #include #include @@ -18,8 +18,8 @@ #include "webrtc/modules/audio_coding/include/audio_coding_module_typedefs.h" // -// The Nack class keeps track of the lost packets, an estimate of time-to-play -// for each packet is also given. +// The NackTracker class keeps track of the lost packets, an estimate of +// time-to-play for each packet is also given. // // Every time a packet is pushed into NetEq, LastReceivedPacket() has to be // called to update the NACK list. @@ -34,12 +34,12 @@ // "late." A "late" packet with sequence number K is changed to "missing" any // time a packet with sequence number newer than |K + NackList| is arrived. // -// The Nack class has to know about the sample rate of the packets to compute -// time-to-play. So sample rate should be set as soon as the first packet is -// received. If there is a change in the receive codec (sender changes codec) -// then Nack should be reset. This is because NetEQ would flush its buffer and -// re-transmission is meaning less for old packet. Therefore, in that case, -// after reset the sampling rate has to be updated. +// The NackTracker class has to know about the sample rate of the packets to +// compute time-to-play. So sample rate should be set as soon as the first +// packet is received. If there is a change in the receive codec (sender changes +// codec) then NackTracker should be reset. This is because NetEQ would flush +// its buffer and re-transmission is meaning less for old packet. Therefore, in +// that case, after reset the sampling rate has to be updated. // // Thread Safety // ============= @@ -48,15 +48,15 @@ // namespace webrtc { -class Nack { +class NackTracker { public: // A limit for the size of the NACK list. static const size_t kNackListSizeLimit = 500; // 10 seconds for 20 ms frame // packets. // Factory method. - static Nack* Create(int nack_threshold_packets); + static NackTracker* Create(int nack_threshold_packets); - ~Nack(); + ~NackTracker(); // Set a maximum for the size of the NACK list. If the last received packet // has sequence number of N, then NACK list will not contain any element @@ -92,7 +92,7 @@ class Nack { private: // This test need to access the private method GetNackList(). - FRIEND_TEST_ALL_PREFIXES(NackTest, EstimateTimestampAndTimeToPlay); + FRIEND_TEST_ALL_PREFIXES(NackTrackerTest, EstimateTimestampAndTimeToPlay); struct NackElement { NackElement(int64_t initial_time_to_play_ms, @@ -130,7 +130,7 @@ class Nack { typedef std::map NackList; // Constructor. - explicit Nack(int nack_threshold_packets); + explicit NackTracker(int nack_threshold_packets); // This API is used only for testing to assess whether time-to-play is // computed correctly. @@ -205,4 +205,4 @@ class Nack { } // namespace webrtc -#endif // WEBRTC_MODULES_AUDIO_CODING_NETEQ_NACK_H_ +#endif // WEBRTC_MODULES_AUDIO_CODING_NETEQ_NACK_TRACKER_H_ diff --git a/webrtc/modules/audio_coding/neteq/nack_unittest.cc b/webrtc/modules/audio_coding/neteq/nack_tracker_unittest.cc similarity index 91% rename from webrtc/modules/audio_coding/neteq/nack_unittest.cc rename to webrtc/modules/audio_coding/neteq/nack_tracker_unittest.cc index fe76e08401..e5c0c3bc4d 100644 --- a/webrtc/modules/audio_coding/neteq/nack_unittest.cc +++ b/webrtc/modules/audio_coding/neteq/nack_tracker_unittest.cc @@ -8,7 +8,7 @@ * be found in the AUTHORS file in the root of the source tree. */ -#include "webrtc/modules/audio_coding/neteq/nack.h" +#include "webrtc/modules/audio_coding/neteq/nack_tracker.h" #include @@ -54,8 +54,8 @@ bool IsNackListCorrect(const std::vector& nack_list, } // namespace -TEST(NackTest, EmptyListWhenNoPacketLoss) { - std::unique_ptr nack(Nack::Create(kNackThreshold)); +TEST(NackTrackerTest, EmptyListWhenNoPacketLoss) { + std::unique_ptr nack(NackTracker::Create(kNackThreshold)); nack->UpdateSampleRate(kSampleRateHz); int seq_num = 1; @@ -72,8 +72,8 @@ TEST(NackTest, EmptyListWhenNoPacketLoss) { } } -TEST(NackTest, NoNackIfReorderWithinNackThreshold) { - std::unique_ptr nack(Nack::Create(kNackThreshold)); +TEST(NackTrackerTest, NoNackIfReorderWithinNackThreshold) { + std::unique_ptr nack(NackTracker::Create(kNackThreshold)); nack->UpdateSampleRate(kSampleRateHz); int seq_num = 1; @@ -96,13 +96,13 @@ TEST(NackTest, NoNackIfReorderWithinNackThreshold) { } } -TEST(NackTest, LatePacketsMovedToNackThenNackListDoesNotChange) { +TEST(NackTrackerTest, LatePacketsMovedToNackThenNackListDoesNotChange) { const uint16_t kSequenceNumberLostPackets[] = {2, 3, 4, 5, 6, 7, 8, 9}; static const int kNumAllLostPackets = sizeof(kSequenceNumberLostPackets) / sizeof(kSequenceNumberLostPackets[0]); for (int k = 0; k < 2; k++) { // Two iteration with/without wrap around. - std::unique_ptr nack(Nack::Create(kNackThreshold)); + std::unique_ptr nack(NackTracker::Create(kNackThreshold)); nack->UpdateSampleRate(kSampleRateHz); uint16_t sequence_num_lost_packets[kNumAllLostPackets]; @@ -145,13 +145,13 @@ TEST(NackTest, LatePacketsMovedToNackThenNackListDoesNotChange) { } } -TEST(NackTest, ArrivedPacketsAreRemovedFromNackList) { +TEST(NackTrackerTest, ArrivedPacketsAreRemovedFromNackList) { const uint16_t kSequenceNumberLostPackets[] = {2, 3, 4, 5, 6, 7, 8, 9}; static const int kNumAllLostPackets = sizeof(kSequenceNumberLostPackets) / sizeof(kSequenceNumberLostPackets[0]); for (int k = 0; k < 2; ++k) { // Two iteration with/without wrap around. - std::unique_ptr nack(Nack::Create(kNackThreshold)); + std::unique_ptr nack(NackTracker::Create(kNackThreshold)); nack->UpdateSampleRate(kSampleRateHz); uint16_t sequence_num_lost_packets[kNumAllLostPackets]; @@ -206,14 +206,14 @@ TEST(NackTest, ArrivedPacketsAreRemovedFromNackList) { // Assess if estimation of timestamps and time-to-play is correct. Introduce all // combinations that timestamps and sequence numbers might have wrap around. -TEST(NackTest, EstimateTimestampAndTimeToPlay) { +TEST(NackTrackerTest, EstimateTimestampAndTimeToPlay) { const uint16_t kLostPackets[] = {2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15}; static const int kNumAllLostPackets = sizeof(kLostPackets) / sizeof(kLostPackets[0]); for (int k = 0; k < 4; ++k) { - std::unique_ptr nack(Nack::Create(kNackThreshold)); + std::unique_ptr nack(NackTracker::Create(kNackThreshold)); nack->UpdateSampleRate(kSampleRateHz); // Sequence number wrap around if |k| is 2 or 3; @@ -250,14 +250,14 @@ TEST(NackTest, EstimateTimestampAndTimeToPlay) { timestamp_lost_packets[kNumAllLostPackets - 1] + kTimestampIncrement; nack->UpdateLastReceivedPacket(seq_num, timestamp); - Nack::NackList nack_list = nack->GetNackList(); + NackTracker::NackList nack_list = nack->GetNackList(); EXPECT_EQ(static_cast(kNumAllLostPackets), nack_list.size()); // Pretend the first packet is decoded. nack->UpdateLastDecodedPacket(first_seq_num, first_timestamp); nack_list = nack->GetNackList(); - Nack::NackList::iterator it = nack_list.begin(); + NackTracker::NackList::iterator it = nack_list.begin(); while (it != nack_list.end()) { seq_num = it->first - seq_num_offset; int index = seq_num - kLostPackets[0]; @@ -281,10 +281,11 @@ TEST(NackTest, EstimateTimestampAndTimeToPlay) { } } -TEST(NackTest, MissingPacketsPriorToLastDecodedRtpShouldNotBeInNackList) { +TEST(NackTrackerTest, + MissingPacketsPriorToLastDecodedRtpShouldNotBeInNackList) { for (int m = 0; m < 2; ++m) { uint16_t seq_num_offset = (m == 0) ? 0 : 65531; // Wrap around if |m| is 1. - std::unique_ptr nack(Nack::Create(kNackThreshold)); + std::unique_ptr nack(NackTracker::Create(kNackThreshold)); nack->UpdateSampleRate(kSampleRateHz); // Two consecutive packets to have a correct estimate of timestamp increase. @@ -334,8 +335,8 @@ TEST(NackTest, MissingPacketsPriorToLastDecodedRtpShouldNotBeInNackList) { } } -TEST(NackTest, Reset) { - std::unique_ptr nack(Nack::Create(kNackThreshold)); +TEST(NackTrackerTest, Reset) { + std::unique_ptr nack(NackTracker::Create(kNackThreshold)); nack->UpdateSampleRate(kSampleRateHz); // Two consecutive packets to have a correct estimate of timestamp increase. @@ -358,11 +359,11 @@ TEST(NackTest, Reset) { EXPECT_TRUE(nack_list.empty()); } -TEST(NackTest, ListSizeAppliedFromBeginning) { +TEST(NackTrackerTest, ListSizeAppliedFromBeginning) { const size_t kNackListSize = 10; for (int m = 0; m < 2; ++m) { uint16_t seq_num_offset = (m == 0) ? 0 : 65525; // Wrap around if |m| is 1. - std::unique_ptr nack(Nack::Create(kNackThreshold)); + std::unique_ptr nack(NackTracker::Create(kNackThreshold)); nack->UpdateSampleRate(kSampleRateHz); nack->SetMaxNackListSize(kNackListSize); @@ -382,11 +383,11 @@ TEST(NackTest, ListSizeAppliedFromBeginning) { } } -TEST(NackTest, ChangeOfListSizeAppliedAndOldElementsRemoved) { +TEST(NackTrackerTest, ChangeOfListSizeAppliedAndOldElementsRemoved) { const size_t kNackListSize = 10; for (int m = 0; m < 2; ++m) { uint16_t seq_num_offset = (m == 0) ? 0 : 65525; // Wrap around if |m| is 1. - std::unique_ptr nack(Nack::Create(kNackThreshold)); + std::unique_ptr nack(NackTracker::Create(kNackThreshold)); nack->UpdateSampleRate(kSampleRateHz); uint16_t seq_num = seq_num_offset; @@ -450,9 +451,9 @@ TEST(NackTest, ChangeOfListSizeAppliedAndOldElementsRemoved) { } } -TEST(NackTest, RoudTripTimeIsApplied) { +TEST(NackTrackerTest, RoudTripTimeIsApplied) { const int kNackListSize = 200; - std::unique_ptr nack(Nack::Create(kNackThreshold)); + std::unique_ptr nack(NackTracker::Create(kNackThreshold)); nack->UpdateSampleRate(kSampleRateHz); nack->SetMaxNackListSize(kNackListSize); diff --git a/webrtc/modules/audio_coding/neteq/neteq.gypi b/webrtc/modules/audio_coding/neteq/neteq.gypi index e92567eef5..4eed4e3283 100644 --- a/webrtc/modules/audio_coding/neteq/neteq.gypi +++ b/webrtc/modules/audio_coding/neteq/neteq.gypi @@ -100,8 +100,8 @@ 'expand.h', 'merge.cc', 'merge.h', - 'nack.h', - 'nack.cc', + 'nack_tracker.h', + 'nack_tracker.cc', 'neteq_impl.cc', 'neteq_impl.h', 'neteq.cc', diff --git a/webrtc/modules/audio_coding/neteq/neteq_impl.cc b/webrtc/modules/audio_coding/neteq/neteq_impl.cc index b8e8c71d34..15eb51b72c 100644 --- a/webrtc/modules/audio_coding/neteq/neteq_impl.cc +++ b/webrtc/modules/audio_coding/neteq/neteq_impl.cc @@ -35,7 +35,7 @@ #include "webrtc/modules/audio_coding/neteq/dtmf_tone_generator.h" #include "webrtc/modules/audio_coding/neteq/expand.h" #include "webrtc/modules/audio_coding/neteq/merge.h" -#include "webrtc/modules/audio_coding/neteq/nack.h" +#include "webrtc/modules/audio_coding/neteq/nack_tracker.h" #include "webrtc/modules/audio_coding/neteq/normal.h" #include "webrtc/modules/audio_coding/neteq/packet_buffer.h" #include "webrtc/modules/audio_coding/neteq/packet.h" @@ -476,7 +476,7 @@ void NetEqImpl::EnableNack(size_t max_nack_list_size) { rtc::CritScope lock(&crit_sect_); if (!nack_enabled_) { const int kNackThresholdPackets = 2; - nack_.reset(Nack::Create(kNackThresholdPackets)); + nack_.reset(NackTracker::Create(kNackThresholdPackets)); nack_enabled_ = true; nack_->UpdateSampleRate(fs_hz_); } diff --git a/webrtc/modules/audio_coding/neteq/neteq_impl.h b/webrtc/modules/audio_coding/neteq/neteq_impl.h index 58b705b408..2b10f97e47 100644 --- a/webrtc/modules/audio_coding/neteq/neteq_impl.h +++ b/webrtc/modules/audio_coding/neteq/neteq_impl.h @@ -42,7 +42,7 @@ class DtmfBuffer; class DtmfToneGenerator; class Expand; class Merge; -class Nack; +class NackTracker; class Normal; class PacketBuffer; class PayloadSplitter; @@ -405,7 +405,7 @@ class NetEqImpl : public webrtc::NetEq { const BackgroundNoiseMode background_noise_mode_ GUARDED_BY(crit_sect_); NetEqPlayoutMode playout_mode_ GUARDED_BY(crit_sect_); bool enable_fast_accelerate_ GUARDED_BY(crit_sect_); - std::unique_ptr nack_ GUARDED_BY(crit_sect_); + std::unique_ptr nack_ GUARDED_BY(crit_sect_); bool nack_enabled_ GUARDED_BY(crit_sect_); const bool enable_muted_state_ GUARDED_BY(crit_sect_); AudioFrame::VADActivity last_vad_activity_ GUARDED_BY(crit_sect_) = diff --git a/webrtc/modules/modules.gyp b/webrtc/modules/modules.gyp index 15d50008a2..3f3105504b 100644 --- a/webrtc/modules/modules.gyp +++ b/webrtc/modules/modules.gyp @@ -200,7 +200,7 @@ 'audio_coding/neteq/dtmf_tone_generator_unittest.cc', 'audio_coding/neteq/expand_unittest.cc', 'audio_coding/neteq/merge_unittest.cc', - 'audio_coding/neteq/nack_unittest.cc', + 'audio_coding/neteq/nack_tracker_unittest.cc', 'audio_coding/neteq/neteq_external_decoder_unittest.cc', 'audio_coding/neteq/neteq_impl_unittest.cc', 'audio_coding/neteq/neteq_network_stats_unittest.cc',