1 /*
2 * Copyright (c) 2012 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 #include "webrtc/system_wrappers/include/critical_section_wrapper.h"
12 #include "webrtc/system_wrappers/include/file_wrapper.h"
13 #include "webrtc/system_wrappers/include/trace.h"
14 #include "webrtc/voice_engine/include/voe_errors.h"
15 #include "webrtc/voice_engine/voe_rtp_rtcp_impl.h"
16 #include "webrtc/voice_engine/voice_engine_impl.h"
17
18 #include "webrtc/voice_engine/channel.h"
19 #include "webrtc/voice_engine/transmit_mixer.h"
20
21 namespace webrtc {
22
GetInterface(VoiceEngine * voiceEngine)23 VoERTP_RTCP* VoERTP_RTCP::GetInterface(VoiceEngine* voiceEngine) {
24 #ifndef WEBRTC_VOICE_ENGINE_RTP_RTCP_API
25 return NULL;
26 #else
27 if (NULL == voiceEngine) {
28 return NULL;
29 }
30 VoiceEngineImpl* s = static_cast<VoiceEngineImpl*>(voiceEngine);
31 s->AddRef();
32 return s;
33 #endif
34 }
35
36 #ifdef WEBRTC_VOICE_ENGINE_RTP_RTCP_API
37
VoERTP_RTCPImpl(voe::SharedData * shared)38 VoERTP_RTCPImpl::VoERTP_RTCPImpl(voe::SharedData* shared) : _shared(shared) {
39 WEBRTC_TRACE(kTraceMemory, kTraceVoice, VoEId(_shared->instance_id(), -1),
40 "VoERTP_RTCPImpl::VoERTP_RTCPImpl() - ctor");
41 }
42
~VoERTP_RTCPImpl()43 VoERTP_RTCPImpl::~VoERTP_RTCPImpl() {
44 WEBRTC_TRACE(kTraceMemory, kTraceVoice, VoEId(_shared->instance_id(), -1),
45 "VoERTP_RTCPImpl::~VoERTP_RTCPImpl() - dtor");
46 }
47
SetLocalSSRC(int channel,unsigned int ssrc)48 int VoERTP_RTCPImpl::SetLocalSSRC(int channel, unsigned int ssrc) {
49 WEBRTC_TRACE(kTraceApiCall, kTraceVoice, VoEId(_shared->instance_id(), -1),
50 "SetLocalSSRC(channel=%d, %lu)", channel, ssrc);
51 if (!_shared->statistics().Initialized()) {
52 _shared->SetLastError(VE_NOT_INITED, kTraceError);
53 return -1;
54 }
55 voe::ChannelOwner ch = _shared->channel_manager().GetChannel(channel);
56 voe::Channel* channelPtr = ch.channel();
57 if (channelPtr == NULL) {
58 _shared->SetLastError(VE_CHANNEL_NOT_VALID, kTraceError,
59 "SetLocalSSRC() failed to locate channel");
60 return -1;
61 }
62 return channelPtr->SetLocalSSRC(ssrc);
63 }
64
GetLocalSSRC(int channel,unsigned int & ssrc)65 int VoERTP_RTCPImpl::GetLocalSSRC(int channel, unsigned int& ssrc) {
66 if (!_shared->statistics().Initialized()) {
67 _shared->SetLastError(VE_NOT_INITED, kTraceError);
68 return -1;
69 }
70 voe::ChannelOwner ch = _shared->channel_manager().GetChannel(channel);
71 voe::Channel* channelPtr = ch.channel();
72 if (channelPtr == NULL) {
73 _shared->SetLastError(VE_CHANNEL_NOT_VALID, kTraceError,
74 "GetLocalSSRC() failed to locate channel");
75 return -1;
76 }
77 return channelPtr->GetLocalSSRC(ssrc);
78 }
79
GetRemoteSSRC(int channel,unsigned int & ssrc)80 int VoERTP_RTCPImpl::GetRemoteSSRC(int channel, unsigned int& ssrc) {
81 if (!_shared->statistics().Initialized()) {
82 _shared->SetLastError(VE_NOT_INITED, kTraceError);
83 return -1;
84 }
85 voe::ChannelOwner ch = _shared->channel_manager().GetChannel(channel);
86 voe::Channel* channelPtr = ch.channel();
87 if (channelPtr == NULL) {
88 _shared->SetLastError(VE_CHANNEL_NOT_VALID, kTraceError,
89 "GetRemoteSSRC() failed to locate channel");
90 return -1;
91 }
92 return channelPtr->GetRemoteSSRC(ssrc);
93 }
94
SetSendAudioLevelIndicationStatus(int channel,bool enable,unsigned char id)95 int VoERTP_RTCPImpl::SetSendAudioLevelIndicationStatus(int channel,
96 bool enable,
97 unsigned char id) {
98 WEBRTC_TRACE(kTraceApiCall, kTraceVoice, VoEId(_shared->instance_id(), -1),
99 "SetSendAudioLevelIndicationStatus(channel=%d, enable=%d,"
100 " ID=%u)",
101 channel, enable, id);
102 if (!_shared->statistics().Initialized()) {
103 _shared->SetLastError(VE_NOT_INITED, kTraceError);
104 return -1;
105 }
106 if (enable && (id < kVoiceEngineMinRtpExtensionId ||
107 id > kVoiceEngineMaxRtpExtensionId)) {
108 // [RFC5285] The 4-bit id is the local identifier of this element in
109 // the range 1-14 inclusive.
110 _shared->SetLastError(
111 VE_INVALID_ARGUMENT, kTraceError,
112 "SetSendAudioLevelIndicationStatus() invalid ID parameter");
113 return -1;
114 }
115
116 // Set state and id for the specified channel.
117 voe::ChannelOwner ch = _shared->channel_manager().GetChannel(channel);
118 voe::Channel* channelPtr = ch.channel();
119 if (channelPtr == NULL) {
120 _shared->SetLastError(
121 VE_CHANNEL_NOT_VALID, kTraceError,
122 "SetSendAudioLevelIndicationStatus() failed to locate channel");
123 return -1;
124 }
125 return channelPtr->SetSendAudioLevelIndicationStatus(enable, id);
126 }
127
SetReceiveAudioLevelIndicationStatus(int channel,bool enable,unsigned char id)128 int VoERTP_RTCPImpl::SetReceiveAudioLevelIndicationStatus(int channel,
129 bool enable,
130 unsigned char id) {
131 WEBRTC_TRACE(
132 kTraceApiCall, kTraceVoice, VoEId(_shared->instance_id(), -1),
133 "SetReceiveAudioLevelIndicationStatus(channel=%d, enable=%d, id=%u)",
134 channel, enable, id);
135 if (!_shared->statistics().Initialized()) {
136 _shared->SetLastError(VE_NOT_INITED, kTraceError);
137 return -1;
138 }
139 if (enable && (id < kVoiceEngineMinRtpExtensionId ||
140 id > kVoiceEngineMaxRtpExtensionId)) {
141 // [RFC5285] The 4-bit id is the local identifier of this element in
142 // the range 1-14 inclusive.
143 _shared->SetLastError(
144 VE_INVALID_ARGUMENT, kTraceError,
145 "SetReceiveAbsoluteSenderTimeStatus() invalid id parameter");
146 return -1;
147 }
148 // Set state and id for the specified channel.
149 voe::ChannelOwner ch = _shared->channel_manager().GetChannel(channel);
150 voe::Channel* channel_ptr = ch.channel();
151 if (channel_ptr == NULL) {
152 _shared->SetLastError(
153 VE_CHANNEL_NOT_VALID, kTraceError,
154 "SetReceiveAudioLevelIndicationStatus() failed to locate channel");
155 return -1;
156 }
157 return channel_ptr->SetReceiveAudioLevelIndicationStatus(enable, id);
158 }
159
SetSendAbsoluteSenderTimeStatus(int channel,bool enable,unsigned char id)160 int VoERTP_RTCPImpl::SetSendAbsoluteSenderTimeStatus(int channel,
161 bool enable,
162 unsigned char id) {
163 WEBRTC_TRACE(kTraceApiCall, kTraceVoice, VoEId(_shared->instance_id(), -1),
164 "SetSendAbsoluteSenderTimeStatus(channel=%d, enable=%d, id=%u)",
165 channel, enable, id);
166 if (!_shared->statistics().Initialized()) {
167 _shared->SetLastError(VE_NOT_INITED, kTraceError);
168 return -1;
169 }
170 if (enable && (id < kVoiceEngineMinRtpExtensionId ||
171 id > kVoiceEngineMaxRtpExtensionId)) {
172 // [RFC5285] The 4-bit id is the local identifier of this element in
173 // the range 1-14 inclusive.
174 _shared->SetLastError(
175 VE_INVALID_ARGUMENT, kTraceError,
176 "SetSendAbsoluteSenderTimeStatus() invalid id parameter");
177 return -1;
178 }
179 // Set state and id for the specified channel.
180 voe::ChannelOwner ch = _shared->channel_manager().GetChannel(channel);
181 voe::Channel* channelPtr = ch.channel();
182 if (channelPtr == NULL) {
183 _shared->SetLastError(
184 VE_CHANNEL_NOT_VALID, kTraceError,
185 "SetSendAbsoluteSenderTimeStatus() failed to locate channel");
186 return -1;
187 }
188 return channelPtr->SetSendAbsoluteSenderTimeStatus(enable, id);
189 }
190
SetReceiveAbsoluteSenderTimeStatus(int channel,bool enable,unsigned char id)191 int VoERTP_RTCPImpl::SetReceiveAbsoluteSenderTimeStatus(int channel,
192 bool enable,
193 unsigned char id) {
194 WEBRTC_TRACE(
195 kTraceApiCall, kTraceVoice, VoEId(_shared->instance_id(), -1),
196 "SetReceiveAbsoluteSenderTimeStatus(channel=%d, enable=%d, id=%u)",
197 channel, enable, id);
198 if (!_shared->statistics().Initialized()) {
199 _shared->SetLastError(VE_NOT_INITED, kTraceError);
200 return -1;
201 }
202 if (enable && (id < kVoiceEngineMinRtpExtensionId ||
203 id > kVoiceEngineMaxRtpExtensionId)) {
204 // [RFC5285] The 4-bit id is the local identifier of this element in
205 // the range 1-14 inclusive.
206 _shared->SetLastError(
207 VE_INVALID_ARGUMENT, kTraceError,
208 "SetReceiveAbsoluteSenderTimeStatus() invalid id parameter");
209 return -1;
210 }
211 // Set state and id for the specified channel.
212 voe::ChannelOwner ch = _shared->channel_manager().GetChannel(channel);
213 voe::Channel* channelPtr = ch.channel();
214 if (channelPtr == NULL) {
215 _shared->SetLastError(
216 VE_CHANNEL_NOT_VALID, kTraceError,
217 "SetReceiveAbsoluteSenderTimeStatus() failed to locate channel");
218 return -1;
219 }
220 return channelPtr->SetReceiveAbsoluteSenderTimeStatus(enable, id);
221 }
222
SetRTCPStatus(int channel,bool enable)223 int VoERTP_RTCPImpl::SetRTCPStatus(int channel, bool enable) {
224 WEBRTC_TRACE(kTraceApiCall, kTraceVoice, VoEId(_shared->instance_id(), -1),
225 "SetRTCPStatus(channel=%d, enable=%d)", channel, enable);
226 if (!_shared->statistics().Initialized()) {
227 _shared->SetLastError(VE_NOT_INITED, kTraceError);
228 return -1;
229 }
230 voe::ChannelOwner ch = _shared->channel_manager().GetChannel(channel);
231 voe::Channel* channelPtr = ch.channel();
232 if (channelPtr == NULL) {
233 _shared->SetLastError(VE_CHANNEL_NOT_VALID, kTraceError,
234 "SetRTCPStatus() failed to locate channel");
235 return -1;
236 }
237 channelPtr->SetRTCPStatus(enable);
238 return 0;
239 }
240
GetRTCPStatus(int channel,bool & enabled)241 int VoERTP_RTCPImpl::GetRTCPStatus(int channel, bool& enabled) {
242 if (!_shared->statistics().Initialized()) {
243 _shared->SetLastError(VE_NOT_INITED, kTraceError);
244 return -1;
245 }
246 voe::ChannelOwner ch = _shared->channel_manager().GetChannel(channel);
247 voe::Channel* channelPtr = ch.channel();
248 if (channelPtr == NULL) {
249 _shared->SetLastError(VE_CHANNEL_NOT_VALID, kTraceError,
250 "GetRTCPStatus() failed to locate channel");
251 return -1;
252 }
253 return channelPtr->GetRTCPStatus(enabled);
254 }
255
SetRTCP_CNAME(int channel,const char cName[256])256 int VoERTP_RTCPImpl::SetRTCP_CNAME(int channel, const char cName[256]) {
257 WEBRTC_TRACE(kTraceApiCall, kTraceVoice, VoEId(_shared->instance_id(), -1),
258 "SetRTCP_CNAME(channel=%d, cName=%s)", channel, cName);
259 if (!_shared->statistics().Initialized()) {
260 _shared->SetLastError(VE_NOT_INITED, kTraceError);
261 return -1;
262 }
263 voe::ChannelOwner ch = _shared->channel_manager().GetChannel(channel);
264 voe::Channel* channelPtr = ch.channel();
265 if (channelPtr == NULL) {
266 _shared->SetLastError(VE_CHANNEL_NOT_VALID, kTraceError,
267 "SetRTCP_CNAME() failed to locate channel");
268 return -1;
269 }
270 return channelPtr->SetRTCP_CNAME(cName);
271 }
272
GetRemoteRTCP_CNAME(int channel,char cName[256])273 int VoERTP_RTCPImpl::GetRemoteRTCP_CNAME(int channel, char cName[256]) {
274 if (!_shared->statistics().Initialized()) {
275 _shared->SetLastError(VE_NOT_INITED, kTraceError);
276 return -1;
277 }
278 voe::ChannelOwner ch = _shared->channel_manager().GetChannel(channel);
279 voe::Channel* channelPtr = ch.channel();
280 if (channelPtr == NULL) {
281 _shared->SetLastError(VE_CHANNEL_NOT_VALID, kTraceError,
282 "GetRemoteRTCP_CNAME() failed to locate channel");
283 return -1;
284 }
285 return channelPtr->GetRemoteRTCP_CNAME(cName);
286 }
287
GetRemoteRTCPData(int channel,unsigned int & NTPHigh,unsigned int & NTPLow,unsigned int & timestamp,unsigned int & playoutTimestamp,unsigned int * jitter,unsigned short * fractionLost)288 int VoERTP_RTCPImpl::GetRemoteRTCPData(
289 int channel,
290 unsigned int& NTPHigh, // from sender info in SR
291 unsigned int& NTPLow, // from sender info in SR
292 unsigned int& timestamp, // from sender info in SR
293 unsigned int& playoutTimestamp, // derived locally
294 unsigned int* jitter, // from report block 1 in SR/RR
295 unsigned short* fractionLost) // from report block 1 in SR/RR
296 {
297 if (!_shared->statistics().Initialized()) {
298 _shared->SetLastError(VE_NOT_INITED, kTraceError);
299 return -1;
300 }
301 voe::ChannelOwner ch = _shared->channel_manager().GetChannel(channel);
302 voe::Channel* channelPtr = ch.channel();
303 if (channelPtr == NULL) {
304 _shared->SetLastError(VE_CHANNEL_NOT_VALID, kTraceError,
305 "GetRemoteRTCP_CNAME() failed to locate channel");
306 return -1;
307 }
308 return channelPtr->GetRemoteRTCPData(NTPHigh, NTPLow, timestamp,
309 playoutTimestamp, jitter, fractionLost);
310 }
311
GetRTPStatistics(int channel,unsigned int & averageJitterMs,unsigned int & maxJitterMs,unsigned int & discardedPackets)312 int VoERTP_RTCPImpl::GetRTPStatistics(int channel,
313 unsigned int& averageJitterMs,
314 unsigned int& maxJitterMs,
315 unsigned int& discardedPackets) {
316 if (!_shared->statistics().Initialized()) {
317 _shared->SetLastError(VE_NOT_INITED, kTraceError);
318 return -1;
319 }
320 voe::ChannelOwner ch = _shared->channel_manager().GetChannel(channel);
321 voe::Channel* channelPtr = ch.channel();
322 if (channelPtr == NULL) {
323 _shared->SetLastError(VE_CHANNEL_NOT_VALID, kTraceError,
324 "GetRTPStatistics() failed to locate channel");
325 return -1;
326 }
327 return channelPtr->GetRTPStatistics(averageJitterMs, maxJitterMs,
328 discardedPackets);
329 }
330
GetRTCPStatistics(int channel,CallStatistics & stats)331 int VoERTP_RTCPImpl::GetRTCPStatistics(int channel, CallStatistics& stats) {
332 if (!_shared->statistics().Initialized()) {
333 _shared->SetLastError(VE_NOT_INITED, kTraceError);
334 return -1;
335 }
336 voe::ChannelOwner ch = _shared->channel_manager().GetChannel(channel);
337 voe::Channel* channelPtr = ch.channel();
338 if (channelPtr == NULL) {
339 _shared->SetLastError(VE_CHANNEL_NOT_VALID, kTraceError,
340 "GetRTPStatistics() failed to locate channel");
341 return -1;
342 }
343 return channelPtr->GetRTPStatistics(stats);
344 }
345
GetRemoteRTCPReportBlocks(int channel,std::vector<ReportBlock> * report_blocks)346 int VoERTP_RTCPImpl::GetRemoteRTCPReportBlocks(
347 int channel, std::vector<ReportBlock>* report_blocks) {
348 if (!_shared->statistics().Initialized()) {
349 _shared->SetLastError(VE_NOT_INITED, kTraceError);
350 return -1;
351 }
352 voe::ChannelOwner ch = _shared->channel_manager().GetChannel(channel);
353 voe::Channel* channel_ptr = ch.channel();
354 if (channel_ptr == NULL) {
355 _shared->SetLastError(
356 VE_CHANNEL_NOT_VALID, kTraceError,
357 "GetRemoteRTCPReportBlocks() failed to locate channel");
358 return -1;
359 }
360 return channel_ptr->GetRemoteRTCPReportBlocks(report_blocks);
361 }
362
SetREDStatus(int channel,bool enable,int redPayloadtype)363 int VoERTP_RTCPImpl::SetREDStatus(int channel,
364 bool enable,
365 int redPayloadtype) {
366 WEBRTC_TRACE(kTraceApiCall, kTraceVoice, VoEId(_shared->instance_id(), -1),
367 "SetREDStatus(channel=%d, enable=%d, redPayloadtype=%d)",
368 channel, enable, redPayloadtype);
369 #ifdef WEBRTC_CODEC_RED
370 if (!_shared->statistics().Initialized()) {
371 _shared->SetLastError(VE_NOT_INITED, kTraceError);
372 return -1;
373 }
374 voe::ChannelOwner ch = _shared->channel_manager().GetChannel(channel);
375 voe::Channel* channelPtr = ch.channel();
376 if (channelPtr == NULL) {
377 _shared->SetLastError(VE_CHANNEL_NOT_VALID, kTraceError,
378 "SetREDStatus() failed to locate channel");
379 return -1;
380 }
381 return channelPtr->SetREDStatus(enable, redPayloadtype);
382 #else
383 _shared->SetLastError(VE_FUNC_NOT_SUPPORTED, kTraceError,
384 "SetREDStatus() RED is not supported");
385 return -1;
386 #endif
387 }
388
GetREDStatus(int channel,bool & enabled,int & redPayloadtype)389 int VoERTP_RTCPImpl::GetREDStatus(int channel,
390 bool& enabled,
391 int& redPayloadtype) {
392 #ifdef WEBRTC_CODEC_RED
393 if (!_shared->statistics().Initialized()) {
394 _shared->SetLastError(VE_NOT_INITED, kTraceError);
395 return -1;
396 }
397 voe::ChannelOwner ch = _shared->channel_manager().GetChannel(channel);
398 voe::Channel* channelPtr = ch.channel();
399 if (channelPtr == NULL) {
400 _shared->SetLastError(VE_CHANNEL_NOT_VALID, kTraceError,
401 "GetREDStatus() failed to locate channel");
402 return -1;
403 }
404 return channelPtr->GetREDStatus(enabled, redPayloadtype);
405 #else
406 _shared->SetLastError(VE_FUNC_NOT_SUPPORTED, kTraceError,
407 "GetREDStatus() RED is not supported");
408 return -1;
409 #endif
410 }
411
SetNACKStatus(int channel,bool enable,int maxNoPackets)412 int VoERTP_RTCPImpl::SetNACKStatus(int channel, bool enable, int maxNoPackets) {
413 WEBRTC_TRACE(kTraceApiCall, kTraceVoice, VoEId(_shared->instance_id(), -1),
414 "SetNACKStatus(channel=%d, enable=%d, maxNoPackets=%d)", channel,
415 enable, maxNoPackets);
416
417 voe::ChannelOwner ch = _shared->channel_manager().GetChannel(channel);
418 voe::Channel* channelPtr = ch.channel();
419 if (channelPtr == NULL) {
420 _shared->SetLastError(VE_CHANNEL_NOT_VALID, kTraceError,
421 "SetNACKStatus() failed to locate channel");
422 return -1;
423 }
424 channelPtr->SetNACKStatus(enable, maxNoPackets);
425 return 0;
426 }
427
428 #endif // #ifdef WEBRTC_VOICE_ENGINE_RTP_RTCP_API
429
430 } // namespace webrtc
431