| OLD | NEW |
| (Empty) |
| 1 /* | |
| 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 | |
| 11 #ifndef WEBRTC_MODULES_AUDIO_CODING_MAIN_ACM2_ACM_RECEIVER_H_ | |
| 12 #define WEBRTC_MODULES_AUDIO_CODING_MAIN_ACM2_ACM_RECEIVER_H_ | |
| 13 | |
| 14 #include <map> | |
| 15 #include <vector> | |
| 16 | |
| 17 #include "webrtc/base/array_view.h" | |
| 18 #include "webrtc/base/optional.h" | |
| 19 #include "webrtc/base/scoped_ptr.h" | |
| 20 #include "webrtc/base/thread_annotations.h" | |
| 21 #include "webrtc/common_audio/vad/include/webrtc_vad.h" | |
| 22 #include "webrtc/engine_configurations.h" | |
| 23 #include "webrtc/modules/audio_coding/main/include/audio_coding_module.h" | |
| 24 #include "webrtc/modules/audio_coding/main/acm2/acm_resampler.h" | |
| 25 #include "webrtc/modules/audio_coding/main/acm2/call_statistics.h" | |
| 26 #include "webrtc/modules/audio_coding/main/acm2/initial_delay_manager.h" | |
| 27 #include "webrtc/modules/audio_coding/neteq/include/neteq.h" | |
| 28 #include "webrtc/modules/include/module_common_types.h" | |
| 29 #include "webrtc/typedefs.h" | |
| 30 | |
| 31 namespace webrtc { | |
| 32 | |
| 33 struct CodecInst; | |
| 34 class CriticalSectionWrapper; | |
| 35 class NetEq; | |
| 36 | |
| 37 namespace acm2 { | |
| 38 | |
| 39 class AcmReceiver { | |
| 40 public: | |
| 41 struct Decoder { | |
| 42 int acm_codec_id; | |
| 43 uint8_t payload_type; | |
| 44 // This field is meaningful for codecs where both mono and | |
| 45 // stereo versions are registered under the same ID. | |
| 46 int channels; | |
| 47 int sample_rate_hz; | |
| 48 }; | |
| 49 | |
| 50 // Constructor of the class | |
| 51 explicit AcmReceiver(const AudioCodingModule::Config& config); | |
| 52 | |
| 53 // Destructor of the class. | |
| 54 ~AcmReceiver(); | |
| 55 | |
| 56 // | |
| 57 // Inserts a payload with its associated RTP-header into NetEq. | |
| 58 // | |
| 59 // Input: | |
| 60 // - rtp_header : RTP header for the incoming payload containing | |
| 61 // information about payload type, sequence number, | |
| 62 // timestamp, SSRC and marker bit. | |
| 63 // - incoming_payload : Incoming audio payload. | |
| 64 // - length_payload : Length of incoming audio payload in bytes. | |
| 65 // | |
| 66 // Return value : 0 if OK. | |
| 67 // <0 if NetEq returned an error. | |
| 68 // | |
| 69 int InsertPacket(const WebRtcRTPHeader& rtp_header, | |
| 70 rtc::ArrayView<const uint8_t> incoming_payload); | |
| 71 | |
| 72 // | |
| 73 // Asks NetEq for 10 milliseconds of decoded audio. | |
| 74 // | |
| 75 // Input: | |
| 76 // -desired_freq_hz : specifies the sampling rate [Hz] of the output | |
| 77 // audio. If set -1 indicates to resampling is | |
| 78 // is required and the audio returned at the | |
| 79 // sampling rate of the decoder. | |
| 80 // | |
| 81 // Output: | |
| 82 // -audio_frame : an audio frame were output data and | |
| 83 // associated parameters are written to. | |
| 84 // | |
| 85 // Return value : 0 if OK. | |
| 86 // -1 if NetEq returned an error. | |
| 87 // | |
| 88 int GetAudio(int desired_freq_hz, AudioFrame* audio_frame); | |
| 89 | |
| 90 // | |
| 91 // Adds a new codec to the NetEq codec database. | |
| 92 // | |
| 93 // Input: | |
| 94 // - acm_codec_id : ACM codec ID; -1 means external decoder. | |
| 95 // - payload_type : payload type. | |
| 96 // - sample_rate_hz : sample rate. | |
| 97 // - audio_decoder : pointer to a decoder object. If it's null, then | |
| 98 // NetEq will internally create a decoder object | |
| 99 // based on the value of |acm_codec_id| (which | |
| 100 // mustn't be -1). Otherwise, NetEq will use the | |
| 101 // given decoder for the given payload type. NetEq | |
| 102 // won't take ownership of the decoder; it's up to | |
| 103 // the caller to delete it when it's no longer | |
| 104 // needed. | |
| 105 // | |
| 106 // Providing an existing decoder object here is | |
| 107 // necessary for external decoders, but may also be | |
| 108 // used for built-in decoders if NetEq doesn't have | |
| 109 // all the info it needs to construct them properly | |
| 110 // (e.g. iSAC, where the decoder needs to be paired | |
| 111 // with an encoder). | |
| 112 // | |
| 113 // Return value : 0 if OK. | |
| 114 // <0 if NetEq returned an error. | |
| 115 // | |
| 116 int AddCodec(int acm_codec_id, | |
| 117 uint8_t payload_type, | |
| 118 int channels, | |
| 119 int sample_rate_hz, | |
| 120 AudioDecoder* audio_decoder); | |
| 121 | |
| 122 // | |
| 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 // | |
| 154 // Resets the initial delay to zero. | |
| 155 // | |
| 156 void ResetInitialDelay(); | |
| 157 | |
| 158 // 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 | |
| 164 // Returns last_output_sample_rate_hz from the NetEq instance. | |
| 165 int last_output_sample_rate_hz() const; | |
| 166 | |
| 167 // | |
| 168 // Get the current network statistics from NetEq. | |
| 169 // | |
| 170 // Output: | |
| 171 // - statistics : The current network statistics. | |
| 172 // | |
| 173 void GetNetworkStatistics(NetworkStatistics* statistics); | |
| 174 | |
| 175 // | |
| 176 // Enable post-decoding VAD. | |
| 177 // | |
| 178 void EnableVad(); | |
| 179 | |
| 180 // | |
| 181 // Disable post-decoding VAD. | |
| 182 // | |
| 183 void DisableVad(); | |
| 184 | |
| 185 // | |
| 186 // Returns whether post-decoding VAD is enabled (true) or disabled (false). | |
| 187 // | |
| 188 bool vad_enabled() const { return vad_enabled_; } | |
| 189 | |
| 190 // | |
| 191 // Flushes the NetEq packet and speech buffers. | |
| 192 // | |
| 193 void FlushBuffers(); | |
| 194 | |
| 195 // | |
| 196 // Removes a payload-type from the NetEq codec database. | |
| 197 // | |
| 198 // Input: | |
| 199 // - payload_type : the payload-type to be removed. | |
| 200 // | |
| 201 // Return value : 0 if OK. | |
| 202 // -1 if an error occurred. | |
| 203 // | |
| 204 int RemoveCodec(uint8_t payload_type); | |
| 205 | |
| 206 // | |
| 207 // Remove all registered codecs. | |
| 208 // | |
| 209 int RemoveAllCodecs(); | |
| 210 | |
| 211 // | |
| 212 // Set ID. | |
| 213 // | |
| 214 void set_id(int id); // TODO(turajs): can be inline. | |
| 215 | |
| 216 // | |
| 217 // Gets the RTP timestamp of the last sample delivered by GetAudio(). | |
| 218 // Returns true if the RTP timestamp is valid, otherwise false. | |
| 219 // | |
| 220 bool GetPlayoutTimestamp(uint32_t* timestamp); | |
| 221 | |
| 222 // | |
| 223 // Get the audio codec associated with the last non-CNG/non-DTMF received | |
| 224 // payload. If no non-CNG/non-DTMF packet is received -1 is returned, | |
| 225 // otherwise return 0. | |
| 226 // | |
| 227 int LastAudioCodec(CodecInst* codec) const; | |
| 228 | |
| 229 // | |
| 230 // Get a decoder given its registered payload-type. | |
| 231 // | |
| 232 // Input: | |
| 233 // -payload_type : the payload-type of the codec to be retrieved. | |
| 234 // | |
| 235 // Output: | |
| 236 // -codec : codec associated with the given payload-type. | |
| 237 // | |
| 238 // Return value : 0 if succeeded. | |
| 239 // -1 if failed, e.g. given payload-type is not | |
| 240 // registered. | |
| 241 // | |
| 242 int DecoderByPayloadType(uint8_t payload_type, | |
| 243 CodecInst* codec) const; | |
| 244 | |
| 245 // | |
| 246 // Enable NACK and set the maximum size of the NACK list. If NACK is already | |
| 247 // enabled then the maximum NACK list size is modified accordingly. | |
| 248 // | |
| 249 // Input: | |
| 250 // -max_nack_list_size : maximum NACK list size | |
| 251 // should be positive (none zero) and less than or | |
| 252 // equal to |Nack::kNackListSizeLimit| | |
| 253 // Return value | |
| 254 // : 0 if succeeded. | |
| 255 // -1 if failed | |
| 256 // | |
| 257 int EnableNack(size_t max_nack_list_size); | |
| 258 | |
| 259 // Disable NACK. | |
| 260 void DisableNack(); | |
| 261 | |
| 262 // | |
| 263 // Get a list of packets to be retransmitted. | |
| 264 // | |
| 265 // Input: | |
| 266 // -round_trip_time_ms : estimate of the round-trip-time (in milliseconds). | |
| 267 // Return value : list of packets to be retransmitted. | |
| 268 // | |
| 269 std::vector<uint16_t> GetNackList(int64_t round_trip_time_ms) const; | |
| 270 | |
| 271 // | |
| 272 // Get statistics of calls to GetAudio(). | |
| 273 void GetDecodingCallStatistics(AudioDecodingCallStats* stats) const; | |
| 274 | |
| 275 private: | |
| 276 const Decoder* RtpHeaderToDecoder(const RTPHeader& rtp_header, | |
| 277 uint8_t payload_type) const | |
| 278 EXCLUSIVE_LOCKS_REQUIRED(crit_sect_); | |
| 279 | |
| 280 uint32_t NowInTimestamp(int decoder_sampling_rate) const; | |
| 281 | |
| 282 rtc::scoped_ptr<CriticalSectionWrapper> crit_sect_; | |
| 283 int id_; // TODO(henrik.lundin) Make const. | |
| 284 const Decoder* last_audio_decoder_ GUARDED_BY(crit_sect_); | |
| 285 AudioFrame::VADActivity previous_audio_activity_ GUARDED_BY(crit_sect_); | |
| 286 ACMResampler resampler_ GUARDED_BY(crit_sect_); | |
| 287 // Used in GetAudio, declared as member to avoid allocating every 10ms. | |
| 288 // TODO(henrik.lundin) Stack-allocate in GetAudio instead? | |
| 289 rtc::scoped_ptr<int16_t[]> audio_buffer_ GUARDED_BY(crit_sect_); | |
| 290 rtc::scoped_ptr<int16_t[]> last_audio_buffer_ GUARDED_BY(crit_sect_); | |
| 291 CallStatistics call_stats_ GUARDED_BY(crit_sect_); | |
| 292 NetEq* neteq_; | |
| 293 // Decoders map is keyed by payload type | |
| 294 std::map<uint8_t, Decoder> decoders_ GUARDED_BY(crit_sect_); | |
| 295 bool vad_enabled_; | |
| 296 Clock* clock_; // TODO(henrik.lundin) Make const if possible. | |
| 297 bool resampled_last_output_frame_ GUARDED_BY(crit_sect_); | |
| 298 rtc::Optional<int> last_packet_sample_rate_hz_ GUARDED_BY(crit_sect_); | |
| 299 }; | |
| 300 | |
| 301 } // namespace acm2 | |
| 302 | |
| 303 } // namespace webrtc | |
| 304 | |
| 305 #endif // WEBRTC_MODULES_AUDIO_CODING_MAIN_ACM2_ACM_RECEIVER_H_ | |
| OLD | NEW |