blob: 25105ec1ca26be77012bca09acc931002b0720cd [file] [log] [blame]
turaj@webrtc.org7959e162013-09-12 18:30:26 +00001/*
2 * Copyright (c) 2013 The WebRTC project authors. All Rights Reserved.
3 *
4 * Use of this source code is governed by a BSD-style license
5 * that can be found in the LICENSE file in the root of the source
6 * tree. An additional intellectual property rights grant can be found
7 * in the file PATENTS. All contributing project authors may
8 * be found in the AUTHORS file in the root of the source tree.
9 */
10
Mirko Bonadei92ea95e2017-09-15 06:47:31 +020011#ifndef MODULES_AUDIO_CODING_ACM2_ACM_RECEIVER_H_
12#define MODULES_AUDIO_CODING_ACM2_ACM_RECEIVER_H_
turaj@webrtc.org7959e162013-09-12 18:30:26 +000013
Yves Gerey988cc082018-10-23 12:03:01 +020014#include <stdint.h>
Jonas Olssona4d87372019-07-05 19:08:33 +020015
jmarusic@webrtc.orga4bef3e2015-03-23 11:19:35 +000016#include <map>
kwiberg16c5a962016-02-15 02:27:22 -080017#include <memory>
henrik.lundin4cf61dd2015-12-09 06:20:58 -080018#include <string>
Fredrik Solenbergf693bfa2018-12-11 12:22:10 +010019#include <utility>
turaj@webrtc.org7959e162013-09-12 18:30:26 +000020#include <vector>
21
Danil Chapovalovb6021232018-06-19 13:26:36 +020022#include "absl/types/optional.h"
Mirko Bonadei92ea95e2017-09-15 06:47:31 +020023#include "api/array_view.h"
Yves Gerey988cc082018-10-23 12:03:01 +020024#include "api/audio_codecs/audio_decoder.h"
Henrik Lundin35417322023-01-31 08:40:56 +000025#include "api/audio_codecs/audio_decoder_factory.h"
Yves Gerey988cc082018-10-23 12:03:01 +020026#include "api/audio_codecs/audio_format.h"
Henrik Lundin35417322023-01-31 08:40:56 +000027#include "api/neteq/neteq.h"
28#include "api/neteq/neteq_factory.h"
Mirko Bonadei92ea95e2017-09-15 06:47:31 +020029#include "modules/audio_coding/acm2/acm_resampler.h"
30#include "modules/audio_coding/acm2/call_statistics.h"
31#include "modules/audio_coding/include/audio_coding_module.h"
Henrik Lundin35417322023-01-31 08:40:56 +000032#include "modules/audio_coding/include/audio_coding_module_typedefs.h"
Markus Handell0df0fae2020-07-07 15:53:34 +020033#include "rtc_base/synchronization/mutex.h"
Mirko Bonadei92ea95e2017-09-15 06:47:31 +020034#include "rtc_base/thread_annotations.h"
turaj@webrtc.org7959e162013-09-12 18:30:26 +000035
36namespace webrtc {
37
Yves Gerey988cc082018-10-23 12:03:01 +020038class Clock;
turaj@webrtc.org7959e162013-09-12 18:30:26 +000039class NetEq;
Yves Gerey988cc082018-10-23 12:03:01 +020040struct RTPHeader;
turaj@webrtc.org6d5d2482013-10-06 04:47:28 +000041
42namespace acm2 {
43
turaj@webrtc.org7959e162013-09-12 18:30:26 +000044class AcmReceiver {
45 public:
Henrik Lundin35417322023-01-31 08:40:56 +000046 struct Config {
47 explicit Config(
48 rtc::scoped_refptr<AudioDecoderFactory> decoder_factory = nullptr);
49 explicit Config(const AudioCodingModule::Config& acm_config);
50 Config(const Config&);
51 ~Config();
52
53 NetEq::Config neteq_config;
54 Clock& clock;
55 rtc::scoped_refptr<AudioDecoderFactory> decoder_factory;
56 NetEqFactory* neteq_factory = nullptr;
57 };
58
turaj@webrtc.org7959e162013-09-12 18:30:26 +000059 // Constructor of the class
Henrik Lundin35417322023-01-31 08:40:56 +000060 explicit AcmReceiver(const Config& config);
61 // Deprecated constructor.
62 // TODO(webrtc:14867): Remove when downstream projects are ready.
63 explicit AcmReceiver(const AudioCodingModule::Config& acm_config);
turaj@webrtc.org7959e162013-09-12 18:30:26 +000064
65 // Destructor of the class.
66 ~AcmReceiver();
67
68 //
69 // Inserts a payload with its associated RTP-header into NetEq.
70 //
71 // Input:
72 // - rtp_header : RTP header for the incoming payload containing
73 // information about payload type, sequence number,
74 // timestamp, SSRC and marker bit.
75 // - incoming_payload : Incoming audio payload.
76 // - length_payload : Length of incoming audio payload in bytes.
77 //
78 // Return value : 0 if OK.
79 // <0 if NetEq returned an error.
80 //
Niels Möllerafb5dbb2019-02-15 15:21:47 +010081 int InsertPacket(const RTPHeader& rtp_header,
kwibergee2bac22015-11-11 10:34:00 -080082 rtc::ArrayView<const uint8_t> incoming_payload);
turaj@webrtc.org7959e162013-09-12 18:30:26 +000083
84 //
85 // Asks NetEq for 10 milliseconds of decoded audio.
86 //
87 // Input:
88 // -desired_freq_hz : specifies the sampling rate [Hz] of the output
89 // audio. If set -1 indicates to resampling is
90 // is required and the audio returned at the
91 // sampling rate of the decoder.
92 //
93 // Output:
94 // -audio_frame : an audio frame were output data and
95 // associated parameters are written to.
henrik.lundin834a6ea2016-05-13 03:45:24 -070096 // -muted : if true, the sample data in audio_frame is not
97 // populated, and must be interpreted as all zero.
turaj@webrtc.org7959e162013-09-12 18:30:26 +000098 //
99 // Return value : 0 if OK.
100 // -1 if NetEq returned an error.
101 //
henrik.lundin834a6ea2016-05-13 03:45:24 -0700102 int GetAudio(int desired_freq_hz, AudioFrame* audio_frame, bool* muted);
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000103
kwiberg1c07c702017-03-27 07:15:49 -0700104 // Replace the current set of decoders with the specified set.
105 void SetCodecs(const std::map<int, SdpAudioFormat>& codecs);
106
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000107 //
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000108 // Sets a minimum delay for packet buffer. The given delay is maintained,
109 // unless channel condition dictates a higher delay.
110 //
111 // Input:
112 // - delay_ms : minimum delay in milliseconds.
113 //
114 // Return value : 0 if OK.
115 // <0 if NetEq returned an error.
116 //
117 int SetMinimumDelay(int delay_ms);
118
119 //
120 // Sets a maximum delay [ms] for the packet buffer. The target delay does not
121 // exceed the given value, even if channel condition requires so.
122 //
123 // Input:
124 // - delay_ms : maximum delay in milliseconds.
125 //
126 // Return value : 0 if OK.
127 // <0 if NetEq returned an error.
128 //
129 int SetMaximumDelay(int delay_ms);
130
Ruslan Burakov9bee67c2019-02-05 13:49:26 +0100131 // Sets a base minimum delay in milliseconds for the packet buffer.
132 // Base minimum delay sets lower bound minimum delay value which
133 // is set via SetMinimumDelay.
134 //
135 // Returns true if value was successfully set, false overwise.
136 bool SetBaseMinimumDelayMs(int delay_ms);
137
138 // Returns current value of base minimum delay in milliseconds.
139 int GetBaseMinimumDelayMs() const;
140
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000141 //
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000142 // Resets the initial delay to zero.
143 //
144 void ResetInitialDelay();
145
henrik.lundin057fb892015-11-23 08:19:52 -0800146 // Returns the sample rate of the decoder associated with the last incoming
147 // packet. If no packet of a registered non-CNG codec has been received, the
148 // return value is empty. Also, if the decoder was unregistered since the last
149 // packet was inserted, the return value is empty.
Danil Chapovalovb6021232018-06-19 13:26:36 +0200150 absl::optional<int> last_packet_sample_rate_hz() const;
henrik.lundin057fb892015-11-23 08:19:52 -0800151
henrik.lundind89814b2015-11-23 06:49:25 -0800152 // Returns last_output_sample_rate_hz from the NetEq instance.
153 int last_output_sample_rate_hz() const;
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000154
155 //
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000156 // Get the current network statistics from NetEq.
157 //
158 // Output:
159 // - statistics : The current network statistics.
160 //
Niels Möller6b4d9622020-09-14 10:47:50 +0200161 void GetNetworkStatistics(NetworkStatistics* statistics,
162 bool get_and_clear_legacy_stats = true) const;
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000163
164 //
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000165 // Flushes the NetEq packet and speech buffers.
166 //
167 void FlushBuffers();
168
169 //
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000170 // Remove all registered codecs.
171 //
kwiberg6b19b562016-09-20 04:02:25 -0700172 void RemoveAllCodecs();
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000173
henrik.lundin9a410dd2016-04-06 01:39:22 -0700174 // Returns the RTP timestamp for the last sample delivered by GetAudio().
175 // The return value will be empty if no valid timestamp is available.
Danil Chapovalovb6021232018-06-19 13:26:36 +0200176 absl::optional<uint32_t> GetPlayoutTimestamp();
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000177
henrik.lundinb3f1c5d2016-08-22 15:39:53 -0700178 // Returns the current total delay from NetEq (packet buffer and sync buffer)
179 // in ms, with smoothing applied to even out short-time fluctuations due to
180 // jitter. The packet buffer part of the delay is not updated during DTX/CNG
181 // periods.
182 //
183 int FilteredCurrentDelayMs() const;
184
Henrik Lundinabbff892017-11-29 09:14:04 +0100185 // Returns the current target delay for NetEq in ms.
186 //
187 int TargetDelayMs() const;
188
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000189 //
Fredrik Solenbergf693bfa2018-12-11 12:22:10 +0100190 // Get payload type and format of the last non-CNG/non-DTMF received payload.
191 // If no non-CNG/non-DTMF packet is received absl::nullopt is returned.
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000192 //
Fredrik Solenbergf693bfa2018-12-11 12:22:10 +0100193 absl::optional<std::pair<int, SdpAudioFormat>> LastDecoder() const;
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000194
195 //
196 // Enable NACK and set the maximum size of the NACK list. If NACK is already
197 // enabled then the maximum NACK list size is modified accordingly.
198 //
Niels Möllerdc5ed5c2019-08-09 09:29:48 +0200199 // If the sequence number of last received packet is N, the sequence numbers
Artem Titovd00ce742021-07-28 20:00:17 +0200200 // of NACK list are in the range of [N - `max_nack_list_size`, N).
Niels Möllerdc5ed5c2019-08-09 09:29:48 +0200201 //
Artem Titovd00ce742021-07-28 20:00:17 +0200202 // `max_nack_list_size` should be positive (none zero) and less than or
Artem Titovcfea2182021-08-10 01:22:31 +0200203 // equal to `Nack::kNackListSizeLimit`. Otherwise, No change is applied and -1
Niels Möllerdc5ed5c2019-08-09 09:29:48 +0200204 // is returned. 0 is returned at success.
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000205 //
206 int EnableNack(size_t max_nack_list_size);
207
208 // Disable NACK.
209 void DisableNack();
210
211 //
Artem Titovd00ce742021-07-28 20:00:17 +0200212 // Get a list of packets to be retransmitted. `round_trip_time_ms` is an
Niels Möllerdc5ed5c2019-08-09 09:29:48 +0200213 // estimate of the round-trip-time (in milliseconds). Missing packets which
214 // will be playout in a shorter time than the round-trip-time (with respect
215 // to the time this API is called) will not be included in the list.
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000216 //
Artem Titovd00ce742021-07-28 20:00:17 +0200217 // Negative `round_trip_time_ms` results is an error message and empty list
Niels Möllerdc5ed5c2019-08-09 09:29:48 +0200218 // is returned.
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000219 //
pkasting@chromium.org16825b12015-01-12 21:51:21 +0000220 std::vector<uint16_t> GetNackList(int64_t round_trip_time_ms) const;
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000221
222 //
wu@webrtc.org24301a62013-12-13 19:17:43 +0000223 // Get statistics of calls to GetAudio().
224 void GetDecodingCallStatistics(AudioDecodingCallStats* stats) const;
225
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000226 private:
Karl Wiberg4b644112019-10-11 09:37:42 +0200227 struct DecoderInfo {
228 int payload_type;
229 int sample_rate_hz;
230 int num_channels;
231 SdpAudioFormat sdp_format;
232 };
233
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000234 uint32_t NowInTimestamp(int decoder_sampling_rate) const;
235
Markus Handell0df0fae2020-07-07 15:53:34 +0200236 mutable Mutex mutex_;
237 absl::optional<DecoderInfo> last_decoder_ RTC_GUARDED_BY(mutex_);
238 ACMResampler resampler_ RTC_GUARDED_BY(mutex_);
239 std::unique_ptr<int16_t[]> last_audio_buffer_ RTC_GUARDED_BY(mutex_);
240 CallStatistics call_stats_ RTC_GUARDED_BY(mutex_);
Henrik Lundin6af93992017-06-14 14:13:02 +0200241 const std::unique_ptr<NetEq> neteq_; // NetEq is thread-safe; no lock needed.
Henrik Lundin35417322023-01-31 08:40:56 +0000242 Clock& clock_;
Markus Handell0df0fae2020-07-07 15:53:34 +0200243 bool resampled_last_output_frame_ RTC_GUARDED_BY(mutex_);
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000244};
245
turaj@webrtc.org6d5d2482013-10-06 04:47:28 +0000246} // namespace acm2
247
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000248} // namespace webrtc
249
Mirko Bonadei92ea95e2017-09-15 06:47:31 +0200250#endif // MODULES_AUDIO_CODING_ACM2_ACM_RECEIVER_H_