Add a "Smart flushing" feature to NetEq.

Instead of flushing all packets, it makes sense to flush down to the target level instead. This CL also initiates a flush when the packet buffer is a multiple of the target level, instead of waiting until it is completely full.

Bug: webrtc:12201
Change-Id: I8775147624536824eb88752f6e8ffe57ec6199cb
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/193941
Commit-Queue: Ivo Creusen <ivoc@webrtc.org>
Reviewed-by: Jakob Ivarsson <jakobi@webrtc.org>
Cr-Commit-Position: refs/heads/master@{#32701}
diff --git a/modules/audio_coding/neteq/packet_buffer.h b/modules/audio_coding/neteq/packet_buffer.h
index c00db29..cd2adf7 100644
--- a/modules/audio_coding/neteq/packet_buffer.h
+++ b/modules/audio_coding/neteq/packet_buffer.h
@@ -22,6 +22,14 @@
 class DecoderDatabase;
 class StatisticsCalculator;
 class TickTimer;
+struct SmartFlushingConfig {
+  // When calculating the flushing threshold, the maximum between the target
+  // level and this value is used.
+  int target_level_threshold_ms = 500;
+  // A smart flush is triggered when the packet buffer contains a multiple of
+  // the target level.
+  int target_level_multiplier = 3;
+};
 
 // This is the actual buffer holding the packets before decoding.
 class PacketBuffer {
@@ -29,6 +37,7 @@
   enum BufferReturnCodes {
     kOK = 0,
     kFlushed,
+    kPartialFlush,
     kNotFound,
     kBufferEmpty,
     kInvalidPacket,
@@ -43,7 +52,13 @@
   virtual ~PacketBuffer();
 
   // Flushes the buffer and deletes all packets in it.
-  virtual void Flush();
+  virtual void Flush(StatisticsCalculator* stats);
+
+  // Partial flush. Flush packets but leave some packets behind.
+  virtual void PartialFlush(int target_level_ms,
+                            size_t sample_rate,
+                            size_t last_decoded_length,
+                            StatisticsCalculator* stats);
 
   // Returns true for an empty buffer.
   virtual bool Empty() const;
@@ -52,7 +67,12 @@
   // the packet object.
   // Returns PacketBuffer::kOK on success, PacketBuffer::kFlushed if the buffer
   // was flushed due to overfilling.
-  virtual int InsertPacket(Packet&& packet, StatisticsCalculator* stats);
+  virtual int InsertPacket(Packet&& packet,
+                           StatisticsCalculator* stats,
+                           size_t last_decoded_length,
+                           size_t sample_rate,
+                           int target_level_ms,
+                           const DecoderDatabase& decoder_database);
 
   // Inserts a list of packets into the buffer. The buffer will take over
   // ownership of the packet objects.
@@ -67,7 +87,10 @@
       const DecoderDatabase& decoder_database,
       absl::optional<uint8_t>* current_rtp_payload_type,
       absl::optional<uint8_t>* current_cng_rtp_payload_type,
-      StatisticsCalculator* stats);
+      StatisticsCalculator* stats,
+      size_t last_decoded_length,
+      size_t sample_rate,
+      int target_level_ms);
 
   // Gets the timestamp for the first packet in the buffer and writes it to the
   // output variable |next_timestamp|.
@@ -146,6 +169,7 @@
   }
 
  private:
+  absl::optional<SmartFlushingConfig> smart_flushing_config_;
   size_t max_number_of_packets_;
   PacketList buffer_;
   const TickTimer* tick_timer_;