blob: 5acb013288e9fdecd214674eba10fc320c0bc4b6 [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
kjellander3e6db232015-11-26 04:44:54 -080011#ifndef WEBRTC_MODULES_AUDIO_CODING_ACM2_ACM_RECEIVER_H_
12#define WEBRTC_MODULES_AUDIO_CODING_ACM2_ACM_RECEIVER_H_
turaj@webrtc.org7959e162013-09-12 18:30:26 +000013
jmarusic@webrtc.orga4bef3e2015-03-23 11:19:35 +000014#include <map>
kwiberg16c5a962016-02-15 02:27:22 -080015#include <memory>
henrik.lundin4cf61dd2015-12-09 06:20:58 -080016#include <string>
turaj@webrtc.org7959e162013-09-12 18:30:26 +000017#include <vector>
18
kwiberg529662a2017-09-04 05:43:17 -070019#include "webrtc/api/array_view.h"
turaj@webrtc.org7959e162013-09-12 18:30:26 +000020#include "webrtc/common_audio/vad/include/webrtc_vad.h"
kjellander3e6db232015-11-26 04:44:54 -080021#include "webrtc/modules/audio_coding/acm2/acm_resampler.h"
22#include "webrtc/modules/audio_coding/acm2/call_statistics.h"
Tommi9090e0b2016-01-20 13:39:36 +010023#include "webrtc/modules/audio_coding/include/audio_coding_module.h"
Henrik Kjellander74640892015-10-29 11:31:02 +010024#include "webrtc/modules/audio_coding/neteq/include/neteq.h"
Henrik Kjellanderff761fb2015-11-04 08:31:52 +010025#include "webrtc/modules/include/module_common_types.h"
Edward Lemurc20978e2017-07-06 19:44:34 +020026#include "webrtc/rtc_base/criticalsection.h"
27#include "webrtc/rtc_base/optional.h"
28#include "webrtc/rtc_base/thread_annotations.h"
turaj@webrtc.org7959e162013-09-12 18:30:26 +000029#include "webrtc/typedefs.h"
30
31namespace webrtc {
32
turaj@webrtc.org6d5d2482013-10-06 04:47:28 +000033struct CodecInst;
turaj@webrtc.org7959e162013-09-12 18:30:26 +000034class NetEq;
turaj@webrtc.org6d5d2482013-10-06 04:47:28 +000035
36namespace acm2 {
37
turaj@webrtc.org7959e162013-09-12 18:30:26 +000038class AcmReceiver {
39 public:
turaj@webrtc.org7959e162013-09-12 18:30:26 +000040 // Constructor of the class
henrik.lundin@webrtc.org0bc9b5a2014-04-29 08:09:31 +000041 explicit AcmReceiver(const AudioCodingModule::Config& config);
turaj@webrtc.org7959e162013-09-12 18:30:26 +000042
43 // Destructor of the class.
44 ~AcmReceiver();
45
46 //
47 // Inserts a payload with its associated RTP-header into NetEq.
48 //
49 // Input:
50 // - rtp_header : RTP header for the incoming payload containing
51 // information about payload type, sequence number,
52 // timestamp, SSRC and marker bit.
53 // - incoming_payload : Incoming audio payload.
54 // - length_payload : Length of incoming audio payload in bytes.
55 //
56 // Return value : 0 if OK.
57 // <0 if NetEq returned an error.
58 //
59 int InsertPacket(const WebRtcRTPHeader& rtp_header,
kwibergee2bac22015-11-11 10:34:00 -080060 rtc::ArrayView<const uint8_t> incoming_payload);
turaj@webrtc.org7959e162013-09-12 18:30:26 +000061
62 //
63 // Asks NetEq for 10 milliseconds of decoded audio.
64 //
65 // Input:
66 // -desired_freq_hz : specifies the sampling rate [Hz] of the output
67 // audio. If set -1 indicates to resampling is
68 // is required and the audio returned at the
69 // sampling rate of the decoder.
70 //
71 // Output:
72 // -audio_frame : an audio frame were output data and
73 // associated parameters are written to.
henrik.lundin834a6ea2016-05-13 03:45:24 -070074 // -muted : if true, the sample data in audio_frame is not
75 // populated, and must be interpreted as all zero.
turaj@webrtc.org7959e162013-09-12 18:30:26 +000076 //
77 // Return value : 0 if OK.
78 // -1 if NetEq returned an error.
79 //
henrik.lundin834a6ea2016-05-13 03:45:24 -070080 int GetAudio(int desired_freq_hz, AudioFrame* audio_frame, bool* muted);
turaj@webrtc.org7959e162013-09-12 18:30:26 +000081
kwiberg1c07c702017-03-27 07:15:49 -070082 // Replace the current set of decoders with the specified set.
83 void SetCodecs(const std::map<int, SdpAudioFormat>& codecs);
84
turaj@webrtc.org7959e162013-09-12 18:30:26 +000085 //
86 // Adds a new codec to the NetEq codec database.
87 //
88 // Input:
kwiberg4e14f092015-08-24 05:27:22 -070089 // - acm_codec_id : ACM codec ID; -1 means external decoder.
turaj@webrtc.org7959e162013-09-12 18:30:26 +000090 // - payload_type : payload type.
Karl Wibergd8399e62015-05-25 14:39:56 +020091 // - sample_rate_hz : sample rate.
kwiberg4e14f092015-08-24 05:27:22 -070092 // - audio_decoder : pointer to a decoder object. If it's null, then
93 // NetEq will internally create a decoder object
94 // based on the value of |acm_codec_id| (which
95 // mustn't be -1). Otherwise, NetEq will use the
96 // given decoder for the given payload type. NetEq
97 // won't take ownership of the decoder; it's up to
98 // the caller to delete it when it's no longer
99 // needed.
100 //
101 // Providing an existing decoder object here is
102 // necessary for external decoders, but may also be
103 // used for built-in decoders if NetEq doesn't have
104 // all the info it needs to construct them properly
105 // (e.g. iSAC, where the decoder needs to be paired
106 // with an encoder).
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000107 //
108 // Return value : 0 if OK.
109 // <0 if NetEq returned an error.
110 //
111 int AddCodec(int acm_codec_id,
112 uint8_t payload_type,
Peter Kasting69558702016-01-12 16:26:35 -0800113 size_t channels,
Karl Wibergd8399e62015-05-25 14:39:56 +0200114 int sample_rate_hz,
henrik.lundin4cf61dd2015-12-09 06:20:58 -0800115 AudioDecoder* audio_decoder,
116 const std::string& name);
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000117
kwiberg5adaf732016-10-04 09:33:27 -0700118 // Adds a new decoder to the NetEq codec database. Returns true iff
119 // successful.
120 bool AddCodec(int rtp_payload_type, const SdpAudioFormat& audio_format);
121
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000122 //
123 // Sets a minimum delay for packet buffer. The given delay is maintained,
124 // unless channel condition dictates a higher delay.
125 //
126 // Input:
127 // - delay_ms : minimum delay in milliseconds.
128 //
129 // Return value : 0 if OK.
130 // <0 if NetEq returned an error.
131 //
132 int SetMinimumDelay(int delay_ms);
133
134 //
135 // Sets a maximum delay [ms] for the packet buffer. The target delay does not
136 // exceed the given value, even if channel condition requires so.
137 //
138 // Input:
139 // - delay_ms : maximum delay in milliseconds.
140 //
141 // Return value : 0 if OK.
142 // <0 if NetEq returned an error.
143 //
144 int SetMaximumDelay(int delay_ms);
145
146 //
147 // Get least required delay computed based on channel conditions. Note that
148 // this is before applying any user-defined limits (specified by calling
149 // (SetMinimumDelay() and/or SetMaximumDelay()).
150 //
151 int LeastRequiredDelayMs() const;
152
153 //
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000154 // Resets the initial delay to zero.
155 //
156 void ResetInitialDelay();
157
henrik.lundin057fb892015-11-23 08:19:52 -0800158 // Returns the sample rate of the decoder associated with the last incoming
159 // packet. If no packet of a registered non-CNG codec has been received, the
160 // return value is empty. Also, if the decoder was unregistered since the last
161 // packet was inserted, the return value is empty.
162 rtc::Optional<int> last_packet_sample_rate_hz() const;
163
henrik.lundind89814b2015-11-23 06:49:25 -0800164 // Returns last_output_sample_rate_hz from the NetEq instance.
165 int last_output_sample_rate_hz() const;
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000166
167 //
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000168 // Get the current network statistics from NetEq.
169 //
170 // Output:
171 // - statistics : The current network statistics.
172 //
minyue@webrtc.orgc0bd7be2015-02-18 15:24:13 +0000173 void GetNetworkStatistics(NetworkStatistics* statistics);
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000174
175 //
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000176 // Flushes the NetEq packet and speech buffers.
177 //
178 void FlushBuffers();
179
180 //
181 // Removes a payload-type from the NetEq codec database.
182 //
183 // Input:
184 // - payload_type : the payload-type to be removed.
185 //
186 // Return value : 0 if OK.
187 // -1 if an error occurred.
188 //
189 int RemoveCodec(uint8_t payload_type);
190
191 //
192 // Remove all registered codecs.
193 //
kwiberg6b19b562016-09-20 04:02:25 -0700194 void RemoveAllCodecs();
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000195
henrik.lundin9a410dd2016-04-06 01:39:22 -0700196 // Returns the RTP timestamp for the last sample delivered by GetAudio().
197 // The return value will be empty if no valid timestamp is available.
198 rtc::Optional<uint32_t> GetPlayoutTimestamp();
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000199
henrik.lundinb3f1c5d2016-08-22 15:39:53 -0700200 // Returns the current total delay from NetEq (packet buffer and sync buffer)
201 // in ms, with smoothing applied to even out short-time fluctuations due to
202 // jitter. The packet buffer part of the delay is not updated during DTX/CNG
203 // periods.
204 //
205 int FilteredCurrentDelayMs() const;
206
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000207 //
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000208 // Get the audio codec associated with the last non-CNG/non-DTMF received
209 // payload. If no non-CNG/non-DTMF packet is received -1 is returned,
210 // otherwise return 0.
211 //
212 int LastAudioCodec(CodecInst* codec) const;
213
ossue280cde2016-10-12 11:04:10 -0700214 rtc::Optional<SdpAudioFormat> LastAudioFormat() const;
215
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000216 //
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000217 // Get a decoder given its registered payload-type.
218 //
219 // Input:
220 // -payload_type : the payload-type of the codec to be retrieved.
221 //
222 // Output:
223 // -codec : codec associated with the given payload-type.
224 //
225 // Return value : 0 if succeeded.
226 // -1 if failed, e.g. given payload-type is not
227 // registered.
228 //
229 int DecoderByPayloadType(uint8_t payload_type,
230 CodecInst* codec) const;
231
232 //
233 // Enable NACK and set the maximum size of the NACK list. If NACK is already
234 // enabled then the maximum NACK list size is modified accordingly.
235 //
236 // Input:
237 // -max_nack_list_size : maximum NACK list size
238 // should be positive (none zero) and less than or
239 // equal to |Nack::kNackListSizeLimit|
240 // Return value
241 // : 0 if succeeded.
242 // -1 if failed
243 //
244 int EnableNack(size_t max_nack_list_size);
245
246 // Disable NACK.
247 void DisableNack();
248
249 //
250 // Get a list of packets to be retransmitted.
251 //
252 // Input:
253 // -round_trip_time_ms : estimate of the round-trip-time (in milliseconds).
254 // Return value : list of packets to be retransmitted.
255 //
pkasting@chromium.org16825b12015-01-12 21:51:21 +0000256 std::vector<uint16_t> GetNackList(int64_t round_trip_time_ms) const;
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000257
258 //
wu@webrtc.org24301a62013-12-13 19:17:43 +0000259 // Get statistics of calls to GetAudio().
260 void GetDecodingCallStatistics(AudioDecodingCallStats* stats) const;
261
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000262 private:
kwiberg6f0f6162016-09-20 03:07:46 -0700263 struct Decoder {
264 int acm_codec_id;
265 uint8_t payload_type;
266 // This field is meaningful for codecs where both mono and
267 // stereo versions are registered under the same ID.
268 size_t channels;
269 int sample_rate_hz;
270 };
271
272 const rtc::Optional<CodecInst> RtpHeaderToDecoder(
273 const RTPHeader& rtp_header,
274 uint8_t first_payload_byte) const EXCLUSIVE_LOCKS_REQUIRED(crit_sect_);
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000275
276 uint32_t NowInTimestamp(int decoder_sampling_rate) const;
277
pbos5ad935c2016-01-25 03:52:44 -0800278 rtc::CriticalSection crit_sect_;
kwiberg6f0f6162016-09-20 03:07:46 -0700279 rtc::Optional<CodecInst> last_audio_decoder_ GUARDED_BY(crit_sect_);
ossue280cde2016-10-12 11:04:10 -0700280 rtc::Optional<SdpAudioFormat> last_audio_format_ GUARDED_BY(crit_sect_);
henrik.lundin@webrtc.orga90abde2014-06-09 18:35:11 +0000281 ACMResampler resampler_ GUARDED_BY(crit_sect_);
kwiberg16c5a962016-02-15 02:27:22 -0800282 std::unique_ptr<int16_t[]> last_audio_buffer_ GUARDED_BY(crit_sect_);
henrik.lundin@webrtc.orga90abde2014-06-09 18:35:11 +0000283 CallStatistics call_stats_ GUARDED_BY(crit_sect_);
Henrik Lundin6af93992017-06-14 14:13:02 +0200284 const std::unique_ptr<NetEq> neteq_; // NetEq is thread-safe; no lock needed.
Henrik Lundin02ed2012017-06-08 09:03:55 +0200285 const Clock* const clock_;
henrik.lundin@webrtc.org913f7b82014-10-21 06:54:23 +0000286 bool resampled_last_output_frame_ GUARDED_BY(crit_sect_);
henrik.lundin057fb892015-11-23 08:19:52 -0800287 rtc::Optional<int> last_packet_sample_rate_hz_ GUARDED_BY(crit_sect_);
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000288};
289
turaj@webrtc.org6d5d2482013-10-06 04:47:28 +0000290} // namespace acm2
291
turaj@webrtc.org7959e162013-09-12 18:30:26 +0000292} // namespace webrtc
293
kjellander3e6db232015-11-26 04:44:54 -0800294#endif // WEBRTC_MODULES_AUDIO_CODING_ACM2_ACM_RECEIVER_H_