1 /**
2 * Copyright (C) 2022 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17 #include <algorithm>
18 #include <RtpSession.h>
19 #include <RtpTrace.h>
20 #include <RtpError.h>
21 #include <RtpStackUtil.h>
22 #include <RtpReceiverInfo.h>
23 #include <RtcpPacket.h>
24 #include <RtcpChunk.h>
25 #include <RtpSessionManager.h>
26 #include <RtcpFbPacket.h>
27
28 extern RtpDt_Void Rtp_RtcpTimerCb(IN RtpDt_Void* pvTimerId, IN RtpDt_Void* pvData);
29
RtpSession()30 RtpSession::RtpSession() :
31 m_pobjTransAddr(nullptr),
32 m_usRtpPort(RTP_ZERO),
33 m_usRtcpPort(RTP_ZERO),
34 m_pobjRtpStack(nullptr),
35 m_usExtHdrLen(RTP_ZERO),
36 m_pobjRtcpCfgInfo(nullptr),
37 m_bEnableRTP(eRTP_FALSE),
38 m_bEnableRTCP(eRTP_FALSE),
39 m_bEnableRTCPBye(eRTP_FALSE),
40 m_usRTCPTimerVal(RTP_ZERO),
41 m_usSeqNum(RTP_ZERO),
42 m_usSeqNumCycles(RTP_ZERO),
43 m_pobjPayloadInfo(nullptr),
44 m_pobjAppInterface(nullptr),
45 m_uiSsrc(RTP_ZERO),
46 m_uiSessionMtu(RTP_DEF_MTU_SIZE),
47 m_uiRtpSendPktCount(RTP_ZERO),
48 m_uiRtpSendOctCount(RTP_ZERO),
49 m_uiRtcpSendPktCount(RTP_ZERO),
50 m_uiRtcpSendOctCount(RTP_ZERO),
51 m_bSelfCollisionByeSent(eRTP_FAILURE),
52 m_pTimerId(nullptr),
53 m_bRtcpSendPkt(eRTP_FALSE),
54 m_bSndRtcpByePkt(eRTP_FALSE),
55 m_lastRTTDelay(RTP_ZERO),
56 m_bisXr(eRTP_FALSE),
57 m_bFirstRtpRecvd(eRTP_FALSE)
58 {
59 m_pobjRtcpCfgInfo = new RtcpConfigInfo();
60 m_pobjRtpRcvrInfoList = new std::list<RtpReceiverInfo*>();
61 m_pobjPayloadInfo = new RtpPayloadInfo();
62 m_pobjUtlRcvrList = nullptr;
63 m_stRtcpXr.m_pBlockBuffer = nullptr;
64 }
65
RtpSession(IN RtpStack * pobjStack)66 RtpSession::RtpSession(IN RtpStack* pobjStack) :
67 m_pobjTransAddr(nullptr),
68 m_usRtpPort(RTP_ZERO),
69 m_usRtcpPort(RTP_ZERO),
70 m_pobjRtpStack(pobjStack),
71 m_usExtHdrLen(RTP_ZERO),
72 m_pobjRtcpCfgInfo(nullptr),
73 m_bEnableRTP(eRTP_FALSE),
74 m_bEnableRTCP(eRTP_FALSE),
75 m_bEnableRTCPBye(eRTP_FALSE),
76 m_usRTCPTimerVal(RTP_ZERO),
77 m_usSeqNum(RTP_ZERO),
78 m_usSeqNumCycles(RTP_ZERO),
79 m_pobjPayloadInfo(nullptr),
80 m_pobjAppInterface(nullptr),
81 m_uiSsrc(RTP_ZERO),
82 m_uiSessionMtu(RTP_DEF_MTU_SIZE),
83 m_uiRtpSendPktCount(RTP_ZERO),
84 m_uiRtpSendOctCount(RTP_ZERO),
85 m_uiRtcpSendPktCount(RTP_ZERO),
86 m_uiRtcpSendOctCount(RTP_ZERO),
87 m_bSelfCollisionByeSent(eRTP_FAILURE),
88 m_pTimerId(nullptr),
89 m_bRtcpSendPkt(eRTP_FALSE),
90 m_bSndRtcpByePkt(eRTP_FALSE),
91 m_lastRTTDelay(RTP_ZERO),
92 m_bisXr(eRTP_FALSE),
93 m_bFirstRtpRecvd(eRTP_FALSE)
94 {
95 m_pobjRtcpCfgInfo = new RtcpConfigInfo();
96 m_pobjPayloadInfo = new RtpPayloadInfo();
97 m_pobjRtpRcvrInfoList = new std::list<RtpReceiverInfo*>();
98 m_pobjUtlRcvrList = nullptr;
99 m_stRtcpXr.m_pBlockBuffer = nullptr;
100 }
101
~RtpSession()102 RtpSession::~RtpSession()
103 {
104 std::lock_guard<std::mutex> guard(m_objRtpSessionLock);
105
106 if (m_pobjTransAddr != nullptr)
107 {
108 delete m_pobjTransAddr;
109 m_pobjTransAddr = nullptr;
110 }
111
112 m_pobjRtpStack = nullptr;
113 if (m_pobjRtcpCfgInfo != nullptr)
114 {
115 delete m_pobjRtcpCfgInfo;
116 m_pobjRtcpCfgInfo = nullptr;
117 }
118
119 if (m_pobjPayloadInfo != nullptr)
120 {
121 delete m_pobjPayloadInfo;
122 m_pobjPayloadInfo = nullptr;
123 }
124
125 if (m_pTimerId != nullptr)
126 {
127 }
128
129 // delete all RTP session objects.
130 RtpDt_UInt16 usSize = RTP_ZERO;
131 usSize = m_pobjRtpRcvrInfoList->size();
132
133 for (RtpDt_UInt32 uiCount = RTP_ZERO; uiCount < usSize; uiCount++)
134 {
135 RtpReceiverInfo* pobjRcvrElm = nullptr;
136 // get the member information
137 pobjRcvrElm = m_pobjRtpRcvrInfoList->front();
138 m_pobjRtpRcvrInfoList->pop_front();
139 delete pobjRcvrElm;
140 } // for
141
142 delete m_pobjRtpRcvrInfoList;
143 delete m_pobjAppInterface;
144 m_pobjRtpRcvrInfoList = nullptr;
145 m_pobjAppInterface = nullptr;
146 }
147
getExtHdrLen()148 RtpDt_UInt16 RtpSession::getExtHdrLen()
149 {
150 return m_usExtHdrLen;
151 }
152
setSsrc(IN RtpDt_UInt32 uiSsrc)153 RtpDt_Void RtpSession::setSsrc(IN RtpDt_UInt32 uiSsrc)
154 {
155 m_uiSsrc = uiSsrc;
156 }
157
getSsrc()158 RtpDt_UInt32 RtpSession::getSsrc()
159 {
160 return m_uiSsrc;
161 }
162
setSequenceNumber(IN RtpDt_UInt16 uiSeqNumber)163 RtpDt_Void RtpSession::setSequenceNumber(IN RtpDt_UInt16 uiSeqNumber)
164 {
165 m_usSeqNum = uiSeqNumber;
166 }
167
getSequenceNumber()168 RtpDt_UInt16 RtpSession::getSequenceNumber()
169 {
170 return m_usSeqNum;
171 }
172
setRtpPort(IN RtpDt_UInt16 usPort)173 RtpDt_Void RtpSession::setRtpPort(IN RtpDt_UInt16 usPort)
174 {
175 m_usRtpPort = usPort;
176 }
177
getRtpPort()178 RtpDt_UInt16 RtpSession::getRtpPort()
179 {
180 return m_usRtpPort;
181 }
182
setRtpTransAddr(IN RtpBuffer * pobjDestTransAddr)183 RtpDt_Void RtpSession::setRtpTransAddr(IN RtpBuffer* pobjDestTransAddr)
184 {
185 if (m_pobjTransAddr != nullptr)
186 delete m_pobjTransAddr;
187
188 m_pobjTransAddr = pobjDestTransAddr;
189 }
190
getRtpTransAddr()191 RtpBuffer* RtpSession::getRtpTransAddr()
192 {
193 return m_pobjTransAddr;
194 }
195
compareRtpSessions(IN RtpSession * pobjSession)196 eRtp_Bool RtpSession::compareRtpSessions(IN RtpSession* pobjSession)
197 {
198 if (pobjSession == nullptr)
199 {
200 RTP_TRACE_WARNING("compareRtpSessions, Input param is Null.", RTP_ZERO, RTP_ZERO);
201 return eRTP_FAILURE;
202 }
203
204 if (m_uiSsrc == pobjSession->getSsrc())
205 {
206 if (m_usRtpPort == pobjSession->getRtpPort())
207 {
208 RtpBuffer* objRtpBuff = pobjSession->getRtpTransAddr();
209 if (m_pobjTransAddr == nullptr && objRtpBuff == nullptr)
210 {
211 return eRTP_SUCCESS;
212 }
213 RtpDt_UChar* pcTranAddr1 = nullptr;
214 if (m_pobjTransAddr != nullptr)
215 {
216 pcTranAddr1 = m_pobjTransAddr->getBuffer();
217 }
218 RtpDt_UChar* pcTranAddr2 = nullptr;
219 if (objRtpBuff != nullptr)
220 {
221 pcTranAddr2 = objRtpBuff->getBuffer();
222 }
223 if (pcTranAddr1 == nullptr || pcTranAddr2 == nullptr)
224 {
225 return eRTP_FAILURE;
226 }
227 if (memcmp(pcTranAddr1, pcTranAddr2, m_pobjTransAddr->getLength()) == RTP_ZERO)
228 {
229 return eRTP_SUCCESS;
230 }
231 }
232 }
233
234 return eRTP_FAILURE;
235 } // compareRtpSessions
236
Rtp_RtcpTimerCb(IN RtpDt_Void * pvTimerId,IN RtpDt_Void * pvData)237 RtpDt_Void Rtp_RtcpTimerCb(IN RtpDt_Void* pvTimerId, IN RtpDt_Void* pvData)
238 {
239 RtpSessionManager* pobjActSesDb = RtpSessionManager::getInstance();
240 RtpSession* pobjRtpSession = static_cast<RtpSession*>(pvData);
241 if (pobjRtpSession == nullptr)
242 {
243 RTP_TRACE_WARNING("Rtp_RtcpTimerCb, pvTimerId is NULL.", RTP_ZERO, RTP_ZERO);
244 return;
245 }
246
247 eRtp_Bool bResult = pobjActSesDb->isValidRtpSession(pvData);
248 if (bResult != eRTP_TRUE)
249 {
250 return;
251 }
252
253 pobjRtpSession->rtcpTimerExpiry(pvTimerId);
254 }
255
estimateRtcpPktSize()256 RtpDt_UInt32 RtpSession::estimateRtcpPktSize()
257 {
258 RtpDt_UInt32 uiEstRtcpSize = RTP_ZERO;
259 RtpDt_UInt32 uiSdesItems = RTP_ZERO;
260
261 uiSdesItems = m_pobjRtcpCfgInfo->getSdesItemCount();
262
263 if ((m_bSelfCollisionByeSent == eRTP_TRUE) || (m_bSndRtcpByePkt == eRTP_TRUE))
264 {
265 uiEstRtcpSize = RTP_DEF_BYE_PKT_SIZE;
266 uiEstRtcpSize += m_pobjRtcpCfgInfo->getByeReasonSize();
267
268 RTP_TRACE_MESSAGE("estimateRtcpPktSize, [Bye packet size : %d]", uiEstRtcpSize, nullptr);
269 }
270 else if (uiSdesItems > RTP_ZERO)
271 {
272 RtpDt_UInt32 uiSdesPktSize = RTP_WORD_SIZE;
273 uiSdesPktSize = uiSdesPktSize + m_pobjRtcpCfgInfo->estimateSdesPktSize();
274
275 RTP_TRACE_MESSAGE("estimateRtcpPktSize, [uiSdesPktSize : %d]", uiSdesPktSize, nullptr);
276
277 uiEstRtcpSize += uiSdesPktSize;
278 }
279
280 if (m_pobjRtcpCfgInfo->isRtcpAppPktSendEnable() == eRTP_TRUE)
281 {
282 uiEstRtcpSize += RTP_DEF_APP_PKT_SIZE;
283 uiEstRtcpSize += m_pobjRtcpCfgInfo->getAppDepDataSize();
284
285 RTP_TRACE_MESSAGE("estimateRtcpPktSize, [after app pkt size: %d]", uiEstRtcpSize, nullptr);
286 }
287
288 return uiEstRtcpSize;
289 }
290
formSrList(IN RtpDt_UInt32 uiSndrCount,OUT RtcpPacket * pobjRtcpPkt)291 eRTP_STATUS_CODE RtpSession::formSrList(IN RtpDt_UInt32 uiSndrCount, OUT RtcpPacket* pobjRtcpPkt)
292 {
293 eRTP_STATUS_CODE eStatus = RTP_SUCCESS;
294 RtpDt_UInt32 uiTmpFlg = RTP_ZERO;
295
296 while (uiSndrCount > RTP_MAX_RECEP_REP_CNT)
297 {
298 RtcpSrPacket* pobjSrPkt = new RtcpSrPacket();
299 if (pobjSrPkt == nullptr)
300 {
301 RTP_TRACE_ERROR("[Memory Error] new returned NULL.", RTP_ZERO, RTP_ZERO);
302 return RTP_MEMORY_FAIL;
303 }
304 // construct SR packet
305 eStatus = pobjRtcpPkt->addSrPacketData(pobjSrPkt);
306 if (eStatus != RTP_SUCCESS)
307 {
308 return eStatus;
309 }
310 eStatus = populateSrpacket(pobjSrPkt, RTP_MAX_RECEP_REP_CNT);
311 if (eStatus != RTP_SUCCESS)
312 {
313 return eStatus;
314 }
315 uiSndrCount = uiSndrCount - RTP_MAX_RECEP_REP_CNT;
316 uiTmpFlg = RTP_ONE;
317 } // while
318 if ((uiSndrCount > RTP_ZERO) || (uiTmpFlg == RTP_ZERO))
319 {
320 RtcpSrPacket* pobjSrPkt = new RtcpSrPacket();
321 if (pobjSrPkt == nullptr)
322 {
323 RTP_TRACE_ERROR("[Memory Error] new returned NULL.", RTP_ZERO, RTP_ZERO);
324 return RTP_MEMORY_FAIL;
325 }
326 // construct SR packet
327 eStatus = pobjRtcpPkt->addSrPacketData(pobjSrPkt);
328 if (eStatus != RTP_SUCCESS)
329 {
330 return eStatus;
331 }
332 eStatus = populateSrpacket(pobjSrPkt, uiSndrCount);
333 if (eStatus != RTP_SUCCESS)
334 {
335 return eStatus;
336 }
337 }
338 return RTP_SUCCESS;
339 } // formSrList
340
formRrList(IN RtpDt_UInt32 uiSndrCount,OUT RtcpPacket * pobjRtcpPkt)341 eRTP_STATUS_CODE RtpSession::formRrList(IN RtpDt_UInt32 uiSndrCount, OUT RtcpPacket* pobjRtcpPkt)
342 {
343 eRTP_STATUS_CODE eStatus = RTP_SUCCESS;
344 RtpDt_UInt32 uiTmpFlg = RTP_ZERO;
345
346 while (uiSndrCount > RTP_MAX_RECEP_REP_CNT)
347 {
348 RtcpRrPacket* pobjRrPkt = new RtcpRrPacket();
349 if (pobjRrPkt == nullptr)
350 {
351 RTP_TRACE_ERROR("[Memory Error] new returned NULL.", RTP_ZERO, RTP_ZERO);
352 return RTP_MEMORY_FAIL;
353 }
354 // construct RR packet
355 eStatus = pobjRtcpPkt->addRrPacketData(pobjRrPkt);
356 if (eStatus != RTP_SUCCESS)
357 {
358 RTP_TRACE_WARNING("formRrList, error in addRrPacketData.", RTP_ZERO, RTP_ZERO);
359 return eStatus;
360 }
361 eStatus = populateReportPacket(pobjRrPkt, eRTP_TRUE, RTP_MAX_RECEP_REP_CNT);
362 if (eStatus != RTP_SUCCESS)
363 {
364 RTP_TRACE_WARNING("formRrList, error in populateReportPacket.", RTP_ZERO, RTP_ZERO);
365 return eStatus;
366 }
367 uiSndrCount = uiSndrCount - RTP_MAX_RECEP_REP_CNT;
368 uiTmpFlg = RTP_ONE;
369 } // while
370 if ((uiSndrCount > RTP_ZERO) || (uiTmpFlg == RTP_ZERO))
371 {
372 RtcpRrPacket* pobjRrPkt = new RtcpRrPacket();
373 if (pobjRrPkt == nullptr)
374 {
375 RTP_TRACE_ERROR("[Memory Error] new returned NULL.", RTP_ZERO, RTP_ZERO);
376 return RTP_MEMORY_FAIL;
377 }
378 // construct RR packet
379 eStatus = pobjRtcpPkt->addRrPacketData(pobjRrPkt);
380 if (eStatus != RTP_SUCCESS)
381 {
382 RTP_TRACE_WARNING("formRrList, error in addRrPacketData.", RTP_ZERO, RTP_ZERO);
383 return eStatus;
384 }
385 eStatus = populateReportPacket(pobjRrPkt, eRTP_TRUE, uiSndrCount);
386 if (eStatus != RTP_SUCCESS)
387 {
388 RTP_TRACE_WARNING("formRrList, error in populateReportPacket.", RTP_ZERO, RTP_ZERO);
389 return eStatus;
390 }
391 }
392
393 return RTP_SUCCESS;
394 } // formSrList
395
numberOfReportBlocks(IN RtpDt_UInt32 uiMtuSize,IN RtpDt_UInt32 uiEstRtcpSize)396 RtpDt_UInt32 RtpSession::numberOfReportBlocks(
397 IN RtpDt_UInt32 uiMtuSize, IN RtpDt_UInt32 uiEstRtcpSize)
398 {
399 RtpDt_UInt32 uiReportDefSize = RTCP_FIXED_HDR_LEN + RTP_DEF_SR_SPEC_SIZE;
400 // determine the sender count
401 RtpDt_UInt32 uiRemTotalSize = uiMtuSize - uiEstRtcpSize;
402 // one SR packet size with 31 report blocks
403 RtpDt_UInt32 uiReportMaxSize = uiReportDefSize + (RTP_MAX_RECEP_REP_CNT * RTP_DEF_REP_BLK_SIZE);
404
405 RtpDt_UInt32 uiTotalNumofReport = uiRemTotalSize / uiReportMaxSize;
406
407 uiRemTotalSize = uiRemTotalSize - (uiReportMaxSize * uiTotalNumofReport);
408 uiRemTotalSize = uiRemTotalSize - uiReportDefSize;
409 RtpDt_UInt32 uiRemRepBlkNum = uiRemTotalSize / RTP_DEF_REP_BLK_SIZE;
410 uiRemRepBlkNum += uiTotalNumofReport * RTP_MAX_RECEP_REP_CNT;
411
412 return uiRemRepBlkNum;
413 }
414
calculateTotalRtcpSize(IN RtpDt_UInt32 uiSndrCount,IN RtpDt_UInt32 uiEstRtcpSize,IN eRtp_Bool isSR)415 RtpDt_UInt32 RtpSession::calculateTotalRtcpSize(
416 IN RtpDt_UInt32 uiSndrCount, IN RtpDt_UInt32 uiEstRtcpSize, IN eRtp_Bool isSR)
417 {
418 RtpDt_UInt32 uiReortDefSize = RTP_ZERO;
419
420 if (isSR == eRTP_TRUE)
421 {
422 uiReortDefSize = RTCP_FIXED_HDR_LEN + RTP_DEF_SR_SPEC_SIZE;
423 }
424 else
425 {
426 uiReortDefSize = RTCP_FIXED_HDR_LEN;
427 }
428
429 RtpDt_UInt32 uiTmpSndrCount = uiSndrCount;
430 RtpDt_UInt32 uiReortFlg = RTP_ZERO;
431 RtpDt_UInt32 uiReportTotalSize = RTP_ZERO;
432
433 while (uiTmpSndrCount > RTP_MAX_RECEP_REP_CNT)
434 {
435 uiReportTotalSize += uiReortDefSize + (RTP_MAX_RECEP_REP_CNT * RTP_DEF_REP_BLK_SIZE);
436
437 uiTmpSndrCount = uiTmpSndrCount - RTP_MAX_RECEP_REP_CNT;
438 uiReportTotalSize += m_usExtHdrLen;
439 uiReortFlg = RTP_ONE;
440 }
441 if ((uiTmpSndrCount > RTP_ZERO) || (uiReortFlg == RTP_ZERO))
442 {
443 uiReportTotalSize += uiReortDefSize + (uiTmpSndrCount * RTP_DEF_REP_BLK_SIZE);
444 }
445
446 RtpDt_UInt32 uiTotalRtcpSize = uiEstRtcpSize + uiReportTotalSize;
447
448 return uiTotalRtcpSize;
449 }
450
rtpSetTimestamp()451 RtpDt_Void RtpSession::rtpSetTimestamp()
452 {
453 RtpOsUtil::GetNtpTime(m_stCurNtpRtcpTs);
454 if (m_bRtcpSendPkt == eRTP_FALSE)
455 {
456 m_bRtcpSendPkt = eRTP_TRUE;
457 }
458
459 RtpDt_UInt32 uiSamplingRate = m_pobjPayloadInfo->getSamplingRate();
460
461 // The RTP timestamp corresponds to the same instant as the NTP timestamp,
462 // but it is expressed inthe units of the RTP media clock.
463 // The value is generally not the same as the RTP timestamp of the previous data packet,
464 // because some time will have elapsed since the data in that packet was samples
465 // RTP Timestamp = Last RTP Pkt timestamp
466 // + timegap between last RTP packet and current RTCP packet
467 m_curRtcpTimestamp = RtpStackUtil::calcRtpTimestamp(
468 m_curRtpTimestamp, &m_stCurNtpRtcpTs, &m_stCurNtpTimestamp, uiSamplingRate);
469 }
470
rtpMakeCompoundRtcpPacket(IN_OUT RtcpPacket * objRtcpPkt)471 eRTP_STATUS_CODE RtpSession::rtpMakeCompoundRtcpPacket(IN_OUT RtcpPacket* objRtcpPkt)
472 {
473 // estimate the size of the RTCP packet
474 RtpDt_UInt32 uiEstRtcpSize = estimateRtcpPktSize();
475 RtpDt_UInt32 uiSndrCount = getSenderCount();
476
477 // get mtu size
478 RtpStackProfile* pobjProfile = m_pobjRtpStack->getStackProfile();
479 RtpDt_UInt32 uiMtuSize = pobjProfile->getMtuSize();
480
481 RtpDt_UInt32 uiSdesItems = m_pobjRtcpCfgInfo->getSdesItemCount();
482
483 eRTP_STATUS_CODE eEncRes = RTP_FAILURE;
484 // check number of packets are sent
485 if ((m_bRtpSendPkt == eRTP_TRUE) || (m_bSelfCollisionByeSent == eRTP_TRUE) ||
486 (m_bSndRtcpByePkt == eRTP_TRUE))
487 {
488 RtpDt_UInt32 uiTotalRtcpSize = RTP_ZERO;
489
490 uiTotalRtcpSize = calculateTotalRtcpSize(uiSndrCount, uiEstRtcpSize, eRTP_TRUE);
491 if (uiTotalRtcpSize < uiMtuSize)
492 {
493 RTP_TRACE_MESSAGE(
494 "rtpMakeCompoundRtcpPacket,[uiTotalRtcpSize : %d] [Estimated Size : %d]",
495 uiTotalRtcpSize, uiEstRtcpSize);
496
497 eEncRes = formSrList(uiSndrCount, objRtcpPkt);
498 if (eEncRes != RTP_SUCCESS)
499 {
500 RTP_TRACE_ERROR("formSrList error: %d", eEncRes, 0);
501 m_pobjAppInterface->rtcpTimerHdlErrorInd(eEncRes);
502 return eEncRes;
503 }
504 }
505 else
506 {
507 RtpDt_UInt32 uiRemRepBlkNum = RTP_ZERO;
508 uiRemRepBlkNum = numberOfReportBlocks(uiMtuSize, uiEstRtcpSize);
509 eEncRes = formSrList(uiRemRepBlkNum, objRtcpPkt);
510 if (eEncRes != RTP_SUCCESS)
511 {
512 RTP_TRACE_ERROR("formSrList error: %d", eEncRes, 0);
513 m_pobjAppInterface->rtcpTimerHdlErrorInd(eEncRes);
514 return eEncRes;
515 }
516 }
517 } // SR
518 else
519 {
520 RtpDt_UInt32 uiTotalRtcpSize = RTP_ZERO;
521
522 uiTotalRtcpSize = calculateTotalRtcpSize(uiSndrCount, uiEstRtcpSize, eRTP_FALSE);
523 if (uiTotalRtcpSize < uiMtuSize)
524 {
525 eEncRes = formRrList(uiSndrCount, objRtcpPkt);
526 if (eEncRes != RTP_SUCCESS)
527 {
528 RTP_TRACE_ERROR("formRrList error: %d", eEncRes, 0);
529 m_pobjAppInterface->rtcpTimerHdlErrorInd(eEncRes);
530 return eEncRes;
531 }
532 }
533 else
534 {
535 RtpDt_UInt32 uiRemRepBlkNum = RTP_ZERO;
536 uiRemRepBlkNum = numberOfReportBlocks(uiMtuSize, uiEstRtcpSize);
537 eEncRes = formRrList(uiRemRepBlkNum, objRtcpPkt);
538 if (eEncRes != RTP_SUCCESS)
539 {
540 RTP_TRACE_ERROR("formRrList error: %d", eEncRes, 0);
541 m_pobjAppInterface->rtcpTimerHdlErrorInd(eEncRes);
542 return eEncRes;
543 }
544 }
545 } // RR
546
547 if ((m_bSelfCollisionByeSent == eRTP_TRUE) || (m_bSndRtcpByePkt == eRTP_TRUE))
548 {
549 eRTP_STATUS_CODE eStatus = RTP_SUCCESS;
550 // construct BYE packet
551 eStatus = populateByePacket(objRtcpPkt);
552 if (eStatus != RTP_SUCCESS)
553 {
554 RTP_TRACE_ERROR("populateByePacket error: %d", eEncRes, 0);
555 m_pobjAppInterface->rtcpTimerHdlErrorInd(eStatus);
556 return eStatus;
557 }
558 }
559 else if (uiSdesItems > RTP_ZERO)
560 {
561 eRTP_STATUS_CODE eStatus = RTP_SUCCESS;
562 eStatus = constructSdesPkt(objRtcpPkt);
563
564 if (eStatus != RTP_SUCCESS)
565 {
566 RTP_TRACE_ERROR("constructSdesPkt error: %d", eEncRes, 0);
567 m_pobjAppInterface->rtcpTimerHdlErrorInd(eStatus);
568 return eStatus;
569 }
570 }
571
572 if (m_bisXr == eRTP_TRUE)
573 {
574 eRTP_STATUS_CODE eStatus = RTP_SUCCESS;
575 eStatus = populateRtcpXrPacket(objRtcpPkt);
576
577 if (eStatus != RTP_SUCCESS)
578 {
579 RTP_TRACE_ERROR("populateRtcpXrPacket error: %d", eEncRes, 0);
580 m_pobjAppInterface->rtcpTimerHdlErrorInd(eStatus);
581 return eStatus;
582 }
583
584 m_bisXr = eRTP_FALSE;
585 }
586
587 return RTP_SUCCESS;
588 }
589
rtpSendRtcpPacket(IN_OUT RtcpPacket * objRtcpPkt)590 eRTP_STATUS_CODE RtpSession::rtpSendRtcpPacket(IN_OUT RtcpPacket* objRtcpPkt)
591 {
592 RtpBuffer* pRtcpBuf = new RtpBuffer();
593
594 if (pRtcpBuf == nullptr)
595 {
596 RTP_TRACE_ERROR("[Memory Error] new returned NULL.", RTP_ZERO, RTP_ZERO);
597 m_pobjAppInterface->rtcpTimerHdlErrorInd(RTP_MEMORY_FAIL);
598 return RTP_FAILURE;
599 }
600
601 RtpDt_UChar* pcBuff = new RtpDt_UChar[RTP_DEF_MTU_SIZE];
602
603 if (pcBuff == nullptr)
604 {
605 RTP_TRACE_ERROR("[Memory Error] new returned NULL.", RTP_ZERO, RTP_ZERO);
606 delete pRtcpBuf;
607 m_pobjAppInterface->rtcpTimerHdlErrorInd(RTP_MEMORY_FAIL);
608 return RTP_FAILURE;
609 }
610
611 pRtcpBuf->setBufferInfo(RTP_DEF_MTU_SIZE, pcBuff);
612
613 // construct the packet
614 eRTP_STATUS_CODE eEncRes = RTP_FAILURE;
615 eEncRes = objRtcpPkt->formRtcpPacket(pRtcpBuf);
616 if (eEncRes == RTP_SUCCESS)
617 {
618 // pass the RTCP buffer to application.
619 eRtp_Bool bStatus = eRTP_FALSE;
620 bStatus = m_pobjAppInterface->rtcpPacketSendInd(pRtcpBuf, this);
621 if (bStatus == eRTP_FALSE)
622 {
623 RTP_TRACE_WARNING("rtpSendRtcpPacket, RTCP send error.", RTP_ZERO, RTP_ZERO);
624 }
625 }
626 else
627 {
628 RTP_TRACE_ERROR("rtpSendRtcpPacket, error in formRtcpPacket.", RTP_ZERO, RTP_ZERO);
629 m_pobjAppInterface->rtcpTimerHdlErrorInd(eEncRes);
630 }
631
632 // update average rtcp size
633 m_objTimerInfo.updateAvgRtcpSize(pRtcpBuf->getLength());
634 delete pRtcpBuf;
635
636 if (m_stRtcpXr.m_pBlockBuffer != nullptr)
637 {
638 delete m_stRtcpXr.m_pBlockBuffer;
639 m_stRtcpXr.m_pBlockBuffer = nullptr;
640 }
641
642 return RTP_SUCCESS;
643 }
644
rtcpTimerExpiry(IN RtpDt_Void * pvTimerId)645 RtpDt_Void RtpSession::rtcpTimerExpiry(IN RtpDt_Void* pvTimerId)
646 {
647 // RtpDt_UInt32 uiSamplingRate = RTP_ZERO;
648 std::lock_guard<std::mutex> guard(m_objRtpSessionLock);
649
650 eRtp_Bool bSessAlive = eRTP_FALSE;
651
652 RtpSessionManager* pobjActSesDb = RtpSessionManager::getInstance();
653 bSessAlive = pobjActSesDb->isValidRtpSession(this);
654
655 if (!bSessAlive)
656 {
657 return;
658 }
659
660 if (m_pTimerId == pvTimerId)
661 {
662 m_pTimerId = nullptr;
663 }
664
665 RtpDt_UInt16 usMembers = m_pobjRtpRcvrInfoList->size();
666 RtpDt_UInt32 uiTempTc = m_objTimerInfo.getTc();
667 RtpDt_Double dTempT = rtcp_interval(usMembers);
668
669 // convert uiTempT to milliseconds
670 dTempT = dTempT * RTP_SEC_TO_MILLISEC;
671 RtpDt_UInt32 uiRoundDiff = (RtpDt_UInt32)dTempT;
672 uiRoundDiff = ((uiRoundDiff / 100) * 100);
673
674 // uiTempTn = m_objTimerInfo.getTp() + (RtpDt_UInt32)dTempT;
675 RtpDt_UInt32 uiTempTn = m_objTimerInfo.getTp() + uiRoundDiff;
676
677 RTP_TRACE_MESSAGE(
678 "rtcpTimerExpiry [Tp : %u] [difference = %u]", m_objTimerInfo.getTp(), uiRoundDiff);
679
680 RTP_TRACE_MESSAGE(
681 "rtcpTimerExpiry [Tp : %u] [difference = %f]", m_objTimerInfo.getTp(), dTempT);
682
683 RTP_TRACE_MESSAGE("rtcpTimerExpiry before processing[Tn : %u] [Tc : %u]", uiTempTn, uiTempTc);
684
685 m_objTimerInfo.setTn(uiTempTn);
686 RtpDt_UInt32 uiTimerVal = RTP_ZERO;
687 RtpDt_Void* pvData = nullptr;
688
689 if ((m_bSelfCollisionByeSent != eRTP_TRUE) || (m_bSndRtcpByePkt != eRTP_TRUE))
690 {
691 if (uiTempTn > uiTempTc)
692 {
693 uiTimerVal = uiTempTn - uiTempTc;
694 if (uiTimerVal > uiRoundDiff)
695 {
696 uiTimerVal = uiRoundDiff;
697 }
698 /*uiTempTn = uiTempTc + uiRoundDiff;
699 m_objTimerInfo.setTn(uiTempTn);
700 m_objTimerInfo.setTp(uiTempTc);*/
701
702 RTP_TRACE_MESSAGE("rtcpTimerExpiry [Tn : %u] [Tc : %u]", uiTempTn, uiTempTc);
703 eRtp_Bool bTSres = eRTP_FALSE;
704
705 bTSres = m_pobjAppInterface->RtpStopTimer(m_pTimerId, &pvData);
706 m_pTimerId = nullptr;
707 if (bTSres == eRTP_FALSE)
708 {
709 return;
710 }
711 if (m_bEnableRTCP == eRTP_TRUE)
712 {
713 RtpDt_Void* pvSTRes = m_pobjAppInterface->RtpStartTimer(
714 uiTimerVal, eRTP_FALSE, m_pfnTimerCb, reinterpret_cast<RtpDt_Void*>(this));
715 if (pvSTRes == nullptr)
716 {
717 return;
718 }
719 m_pTimerId = pvSTRes;
720 }
721 return;
722 }
723 }
724
725 // set timestamp
726 rtpSetTimestamp();
727
728 RtcpPacket objRtcpPkt;
729 eRTP_STATUS_CODE eEncRes = RTP_FAILURE;
730
731 eEncRes = rtpMakeCompoundRtcpPacket(&objRtcpPkt);
732 if (eEncRes != RTP_SUCCESS)
733 {
734 RTP_TRACE_ERROR("MakeCompoundRtcpPacket Error: %d", eEncRes, RTP_ZERO);
735 return;
736 }
737
738 // check number of packets are sent
739 eEncRes = rtpSendRtcpPacket(&objRtcpPkt);
740 if (eEncRes != RTP_SUCCESS)
741 {
742 RTP_TRACE_ERROR("rtpSendRtcpPacket Error: %d", eEncRes, RTP_ZERO);
743 return;
744 }
745 // set Tp with Tc
746 m_objTimerInfo.setTp(uiTempTc);
747
748 // recalculate timer in
749 dTempT = rtcp_interval(usMembers);
750 dTempT = dTempT * RTP_SEC_TO_MILLISEC;
751 uiRoundDiff = (RtpDt_UInt32)dTempT;
752 uiTempTn = uiTempTc + uiRoundDiff;
753 // uiTempTn = uiTempTc + dTempT;
754 m_objTimerInfo.setTn(uiTempTn);
755
756 // restart the timer
757 // uiTimerVal = m_objTimerInfo.getTn() - uiTempTc;
758 if (m_usRTCPTimerVal > RTP_ZERO)
759 {
760 uiTimerVal = m_usRTCPTimerVal * RTP_SEC_TO_MILLISEC;
761 }
762 else
763 {
764 uiTimerVal = uiRoundDiff;
765 }
766
767 // uiTimerVal = (RtpDt_UInt32)dTempT;
768 // Reschedule the next report for time tn
769 if (m_pTimerId != nullptr)
770 {
771 eRtp_Bool bTSres = eRTP_FALSE;
772 bTSres = m_pobjAppInterface->RtpStopTimer(m_pTimerId, &pvData);
773 m_pTimerId = nullptr;
774 if (bTSres == eRTP_FALSE)
775 {
776 return;
777 }
778 }
779
780 if (m_bEnableRTCP == eRTP_TRUE)
781 {
782 RtpDt_Void* pvSTRes = nullptr;
783
784 pvSTRes = m_pobjAppInterface->RtpStartTimer(
785 uiTimerVal, eRTP_FALSE, m_pfnTimerCb, reinterpret_cast<RtpDt_Void*>(this));
786
787 if (pvSTRes == nullptr)
788 {
789 return;
790 }
791 m_pTimerId = pvSTRes;
792 }
793
794 // set m_bInitial = false
795 m_objTimerInfo.setInitial(eRTP_FALSE);
796
797 // update we_sent
798 if (m_objTimerInfo.getWeSent() == RTP_TWO)
799 {
800 m_objTimerInfo.setWeSent(RTP_ONE);
801 }
802 else
803 {
804 m_objTimerInfo.setWeSent(RTP_ZERO);
805 }
806
807 // set pmembers with members
808 m_objTimerInfo.setPmembers(usMembers);
809
810 // set m_bRtpSendPkt to false
811 m_bRtpSendPkt = eRTP_FALSE;
812
813 return;
814 } // rtcpTimerExpiry
815
populateSrpacket(OUT RtcpSrPacket * pobjSrPkt,IN RtpDt_UInt32 uiRecepCount)816 eRTP_STATUS_CODE RtpSession::populateSrpacket(
817 OUT RtcpSrPacket* pobjSrPkt, IN RtpDt_UInt32 uiRecepCount)
818 {
819 tRTP_NTP_TIME* pstNtpTime = pobjSrPkt->getNtpTime();
820
821 // NTP timestamp, most significant word
822 pstNtpTime->m_uiNtpHigh32Bits = m_stCurNtpRtcpTs.m_uiNtpHigh32Bits;
823 // NTP timestamp, least significant word
824 pstNtpTime->m_uiNtpLow32Bits = m_stCurNtpRtcpTs.m_uiNtpLow32Bits;
825 // RTCP timestamp
826 pobjSrPkt->setRtpTimestamp(m_curRtcpTimestamp);
827 // sender's packet count
828 pobjSrPkt->setSendPktCount(m_uiRtpSendPktCount);
829 // sender's octet count
830 pobjSrPkt->setSendOctetCount(m_uiRtpSendOctCount);
831
832 eRTP_STATUS_CODE eRepPktSta = RTP_FAILURE;
833 eRepPktSta = populateReportPacket(pobjSrPkt->getRrPktInfo(), eRTP_FALSE, uiRecepCount);
834
835 if (eRepPktSta != RTP_SUCCESS)
836 {
837 return eRepPktSta;
838 }
839
840 return RTP_SUCCESS;
841 } // populateSrpacket
842
cleanUtlReceiverList()843 RtpDt_Void RtpSession::cleanUtlReceiverList()
844 {
845 // populate report blocks
846 for (const auto& pobjRcvrElm : *m_pobjUtlRcvrList)
847 {
848 delete pobjRcvrElm;
849 }
850 m_pobjUtlRcvrList->clear();
851 } // cleanUtlReceiverList
852
populateReportPacket(OUT RtcpRrPacket * pobjRrPkt,IN eRtp_Bool bRrPkt,IN RtpDt_UInt32 uiRecepCount)853 eRTP_STATUS_CODE RtpSession::populateReportPacket(
854 OUT RtcpRrPacket* pobjRrPkt, IN eRtp_Bool bRrPkt, IN RtpDt_UInt32 uiRecepCount)
855 {
856 RtcpHeader* pRtcpHdr = pobjRrPkt->getRtcpHdrInfo();
857 std::list<RtcpReportBlock*>& pobjRepBlkLst = pobjRrPkt->getReportBlockList();
858
859 // get receiver list size
860 if (bRrPkt == eRTP_TRUE)
861 {
862 pRtcpHdr->populateRtcpHeader((RtpDt_UChar)uiRecepCount, (RtpDt_UChar)RTCP_RR, m_uiSsrc);
863 }
864 else
865 {
866 pRtcpHdr->populateRtcpHeader((RtpDt_UChar)uiRecepCount, (RtpDt_UChar)RTCP_SR, m_uiSsrc);
867 }
868
869 if (uiRecepCount == RTP_ZERO)
870 {
871 return RTP_SUCCESS;
872 }
873
874 std::list<RtpReceiverInfo*>* pobjTmpRcvrList = m_pobjRtpRcvrInfoList;
875 m_pobjUtlRcvrList = new std::list<RtpReceiverInfo*>();
876 if (m_pobjUtlRcvrList == nullptr)
877 {
878 RTP_TRACE_ERROR("[Memory Error] new returned NULL.", RTP_ZERO, RTP_ZERO);
879 return RTP_MEMORY_FAIL;
880 }
881
882 eRtp_Bool bFirstPos = eRTP_TRUE;
883 RtpDt_UInt32 uiTmpRecpCount = RTP_ZERO;
884 std::list<RtpReceiverInfo*>::iterator iter;
885 // populate report blocks
886 for (auto& pobjRcvrElm : *m_pobjRtpRcvrInfoList)
887 {
888 // get the member information
889 if ((pobjRcvrElm->isSender() == eRTP_TRUE) && (uiTmpRecpCount <= uiRecepCount))
890 {
891 RtcpReportBlock* pobjRepBlk = new RtcpReportBlock();
892 if (pobjRepBlk == nullptr)
893 {
894 RTP_TRACE_ERROR("[Memory Error] new returned NULL.", RTP_ZERO, RTP_ZERO);
895 cleanUtlReceiverList();
896 delete m_pobjUtlRcvrList;
897 m_pobjUtlRcvrList = nullptr;
898 return RTP_MEMORY_FAIL;
899 }
900 pobjRcvrElm->populateReportBlock(pobjRepBlk);
901 pobjRepBlkLst.push_back(pobjRepBlk);
902 pobjRcvrElm->setSenderFlag(eRTP_FALSE);
903 m_pobjUtlRcvrList->push_back(pobjRcvrElm);
904 uiTmpRecpCount = uiTmpRecpCount + RTP_ONE;
905 }
906 else
907 {
908 if (pobjRcvrElm->getCsrcFlag() == eRTP_TRUE)
909 {
910 m_pobjUtlRcvrList->push_back(pobjRcvrElm);
911 }
912 else
913 {
914 if (bFirstPos == eRTP_TRUE)
915 {
916 m_pobjUtlRcvrList->push_front(pobjRcvrElm);
917 iter = m_pobjUtlRcvrList->begin();
918 bFirstPos = eRTP_FALSE;
919 }
920 else
921 {
922 m_pobjUtlRcvrList->insert(iter, pobjRcvrElm);
923 }
924 }
925 }
926 }
927
928 m_pobjRtpRcvrInfoList->clear();
929 m_pobjRtpRcvrInfoList = m_pobjUtlRcvrList;
930 delete pobjTmpRcvrList;
931 #ifdef ENABLE_RTCPEXT
932 // Extension header
933 if (m_usExtHdrLen > RTP_ZERO)
934 {
935 RtpBuffer* pobjExtHdrInfo = new RtpBuffer();
936 if (pobjExtHdrInfo == nullptr)
937 {
938 RTP_TRACE_ERROR("[Memory Error] new returned NULL.", RTP_ZERO, RTP_ZERO);
939 return RTP_MEMORY_FAIL;
940 }
941 else
942 {
943 m_pobjAppInterface->getRtpHdrExtInfo(pobjExtHdrInfo);
944 pobjRrPkt->setExtHdrInfo(pobjExtHdrInfo);
945 }
946 }
947 #endif
948
949 return RTP_SUCCESS;
950 } // populateReportPacket
951
populateByePacket(IN_OUT RtcpPacket * pobjRtcpPkt)952 eRTP_STATUS_CODE RtpSession::populateByePacket(IN_OUT RtcpPacket* pobjRtcpPkt)
953 {
954 RtcpByePacket* pobjByePkt = new RtcpByePacket();
955 if (pobjByePkt == nullptr)
956 {
957 RTP_TRACE_ERROR("[Memory Error] new returned NULL.", RTP_ZERO, RTP_ZERO);
958 return RTP_MEMORY_FAIL;
959 }
960 RtcpHeader* pRtcpHdr = pobjByePkt->getRtcpHdrInfo();
961
962 pobjRtcpPkt->setByePacketData(pobjByePkt);
963 // populate App packet header.
964 pRtcpHdr->populateRtcpHeader((RtpDt_UChar)RTP_ONE, RTCP_BYE, m_uiSsrc);
965
966 return RTP_SUCCESS;
967 } // populateByePacket
968
populateAppPacket(IN_OUT RtcpPacket * pobjRtcpPkt)969 eRTP_STATUS_CODE RtpSession::populateAppPacket(IN_OUT RtcpPacket* pobjRtcpPkt)
970 {
971 RtcpAppPacket* pobjAppPkt = new RtcpAppPacket();
972 if (pobjAppPkt == nullptr)
973 {
974 RTP_TRACE_ERROR("[Memory Error] new returned NULL.", RTP_ZERO, RTP_ZERO);
975 return RTP_MEMORY_FAIL;
976 }
977 RtpBuffer* pobjPayload = new RtpBuffer();
978 if (pobjPayload == nullptr)
979 {
980 RTP_TRACE_ERROR("[Memory Error] new returned NULL.", RTP_ZERO, RTP_ZERO);
981 delete pobjAppPkt;
982 return RTP_MEMORY_FAIL;
983 }
984 // fill application dependent data
985 pobjAppPkt->setAppData(pobjPayload);
986 RtcpHeader* pRtcpHdr = pobjAppPkt->getRtcpHdrInfo();
987
988 RtpDt_UInt16 usSubType = RTP_ZERO;
989 RtpDt_UInt32 uiName = RTP_ZERO;
990 eRtp_Bool bStatus = eRTP_FALSE;
991
992 pobjRtcpPkt->setAppPktData(pobjAppPkt);
993 bStatus = m_pobjAppInterface->rtcpAppPayloadReqInd(usSubType, uiName, pobjPayload);
994 if (bStatus != eRTP_TRUE)
995 {
996 return RTP_FAILURE;
997 }
998 // populate App packet header.
999 pRtcpHdr->populateRtcpHeader((RtpDt_UChar)usSubType, RTCP_APP, m_uiSsrc);
1000
1001 // fill name
1002 pobjAppPkt->setName(uiName);
1003
1004 return RTP_SUCCESS;
1005 } // populateAppPacket
1006
populateRtcpFbPacket(IN_OUT RtcpPacket * pobjRtcpPkt,IN RtpDt_UInt32 uiFbType,IN RtpDt_Char * pcBuff,IN RtpDt_UInt32 uiLen,IN RtpDt_UInt32 uiMediaSSRC,IN RtpDt_UInt32 uiPayloadType)1007 eRTP_STATUS_CODE RtpSession::populateRtcpFbPacket(IN_OUT RtcpPacket* pobjRtcpPkt,
1008 IN RtpDt_UInt32 uiFbType, IN RtpDt_Char* pcBuff, IN RtpDt_UInt32 uiLen,
1009 IN RtpDt_UInt32 uiMediaSSRC, IN RtpDt_UInt32 uiPayloadType)
1010 {
1011 // create RtcpFbPacket
1012 RtcpFbPacket* pobjRtcpRtpFbPacket = new RtcpFbPacket();
1013
1014 // create payload FCI buffer
1015 RtpBuffer* pobjPayload = new RtpBuffer(uiLen, reinterpret_cast<RtpDt_UChar*>(pcBuff));
1016
1017 // set Media SSRC
1018 pobjRtcpRtpFbPacket->setMediaSsrc(uiMediaSSRC);
1019
1020 // set FCI data
1021 pobjRtcpRtpFbPacket->setFCI(pobjPayload);
1022
1023 // set feedback type
1024 pobjRtcpRtpFbPacket->setPayloadType((eRTCP_TYPE)uiPayloadType);
1025
1026 // set the RTCP packet
1027 pobjRtcpPkt->addFbPacketData(pobjRtcpRtpFbPacket);
1028
1029 // get and populate the RTCP header
1030 RtcpHeader* pRtcpHdr = pobjRtcpRtpFbPacket->getRtcpHdrInfo();
1031
1032 pRtcpHdr->populateRtcpHeader((RtpDt_UChar)uiFbType, uiPayloadType, m_uiSsrc);
1033
1034 return RTP_SUCCESS;
1035 }
1036
constructSdesPkt(IN_OUT RtcpPacket * pobjRtcpPkt)1037 eRTP_STATUS_CODE RtpSession::constructSdesPkt(IN_OUT RtcpPacket* pobjRtcpPkt)
1038 {
1039 if (m_pobjRtcpCfgInfo == nullptr || pobjRtcpPkt == nullptr)
1040 return RTP_FAILURE;
1041
1042 RtpDt_UInt32 uiSdesItems = m_pobjRtcpCfgInfo->getSdesItemCount();
1043
1044 RtcpSdesPacket* pobjSdesPkt = new RtcpSdesPacket();
1045 if (pobjSdesPkt == nullptr)
1046 {
1047 RTP_TRACE_ERROR("[Memory Error] new returned NULL.", RTP_ZERO, RTP_ZERO);
1048 return RTP_MEMORY_FAIL;
1049 }
1050
1051 RtcpChunk* pobjChunk = new RtcpChunk();
1052 if (pobjChunk == nullptr)
1053 {
1054 RTP_TRACE_ERROR("[Memory Error] new returned NULL.", RTP_ZERO, RTP_ZERO);
1055 delete pobjSdesPkt;
1056 return RTP_MEMORY_FAIL;
1057 }
1058
1059 RtcpHeader* pRtcpHdr = pobjSdesPkt->getRtcpHdrInfo();
1060 if (pRtcpHdr == nullptr)
1061 {
1062 RTP_TRACE_ERROR("Failed to retrieve Rtcp Header Info", RTP_ZERO, RTP_ZERO);
1063 delete pobjSdesPkt;
1064 delete pobjChunk;
1065 return RTP_FAILURE;
1066 }
1067
1068 std::list<RtcpChunk*>& pobjSdesList = pobjSdesPkt->getSdesChunkList();
1069
1070 pobjRtcpPkt->setSdesPacketData(pobjSdesPkt);
1071
1072 // populate SDES packet header.
1073 pRtcpHdr->populateRtcpHeader(RTP_ONE, RTCP_SDES, m_uiSsrc);
1074
1075 pobjSdesList.push_back(pobjChunk);
1076
1077 pobjChunk->setSsrc(m_uiSsrc);
1078 std::list<tRTCP_SDES_ITEM*>& pobjChunkList = pobjChunk->getSdesItemList();
1079
1080 for (RtpDt_UInt32 uiCount = RTP_ZERO; uiCount < uiSdesItems; uiCount++)
1081 {
1082 tRTCP_SDES_ITEM* pstSdesItem = m_pobjRtcpCfgInfo->getRtcpSdesItem(uiCount);
1083
1084 if (pstSdesItem && pstSdesItem->pValue != nullptr)
1085 {
1086 tRTCP_SDES_ITEM* pstTmpSdesItem = new tRTCP_SDES_ITEM();
1087 if (pstTmpSdesItem == nullptr)
1088 {
1089 return RTP_MEMORY_FAIL;
1090 }
1091
1092 RtpDt_UChar* pucSdesBuf = new RtpDt_UChar[pstSdesItem->ucLength];
1093 if (pucSdesBuf == nullptr)
1094 {
1095 delete pstTmpSdesItem;
1096 return RTP_MEMORY_FAIL;
1097 }
1098
1099 pstTmpSdesItem->ucType = pstSdesItem->ucType;
1100 pstTmpSdesItem->ucLength = pstSdesItem->ucLength;
1101 memcpy(pucSdesBuf, pstSdesItem->pValue, pstSdesItem->ucLength);
1102 pstTmpSdesItem->pValue = pucSdesBuf;
1103 pobjChunkList.push_back(pstTmpSdesItem);
1104 }
1105 }
1106
1107 return RTP_SUCCESS;
1108 } // constructSdesPkt
1109
disableRtp()1110 eRTP_STATUS_CODE RtpSession::disableRtp()
1111 {
1112 m_bEnableRTP = eRTP_FALSE;
1113 return RTP_SUCCESS;
1114 }
1115
enableRtp()1116 eRTP_STATUS_CODE RtpSession::enableRtp()
1117 {
1118 m_bEnableRTP = eRTP_TRUE;
1119 return RTP_SUCCESS;
1120 }
1121
isRtpEnabled()1122 eRtp_Bool RtpSession::isRtpEnabled()
1123 {
1124 return m_bEnableRTP;
1125 }
1126
enableRtcp(eRtp_Bool enableRTCPBye)1127 eRTP_STATUS_CODE RtpSession::enableRtcp(eRtp_Bool enableRTCPBye)
1128 {
1129 RtpStackProfile* pobjRtpProfile = m_pobjRtpStack->getStackProfile();
1130 if (pobjRtpProfile == nullptr)
1131 return RTP_FAILURE;
1132
1133 // timer value shall be in milli seconds
1134 RtpDt_UInt32 uiTimerVal = RTP_INIT_TRUE_T_MIN * RTP_SEC_TO_MILLISEC;
1135
1136 if (m_usRTCPTimerVal > RTP_ZERO)
1137 {
1138 uiTimerVal = m_usRTCPTimerVal * RTP_SEC_TO_MILLISEC;
1139 }
1140
1141 if (m_bEnableRTCP == eRTP_TRUE)
1142 {
1143 RTP_TRACE_WARNING("enableRtcp, m_bEnableRTCP is already enabled.", RTP_ZERO, RTP_ZERO);
1144
1145 return RTP_RTCP_ALREADY_RUNNING;
1146 }
1147
1148 m_bEnableRTCP = eRTP_TRUE;
1149 m_bEnableRTCPBye = enableRTCPBye;
1150
1151 RtpSessionManager* pobjActSesDb = RtpSessionManager::getInstance();
1152 pobjActSesDb->addRtpSession(reinterpret_cast<RtpDt_Void*>(this));
1153 RtpDt_Void* pvData = nullptr;
1154
1155 if (m_pTimerId != nullptr && m_pobjAppInterface != nullptr)
1156 {
1157 eRtp_Bool bTSres = eRTP_FALSE;
1158 bTSres = m_pobjAppInterface->RtpStopTimer(m_pTimerId, &pvData);
1159 m_pTimerId = nullptr;
1160 if (bTSres == eRTP_FALSE)
1161 {
1162 RTP_TRACE_WARNING("enableRtcp, Stop timer is returned NULL value.", RTP_ZERO, RTP_ZERO);
1163 return RTP_TIMER_PROC_ERR;
1164 }
1165 }
1166 RtpDt_Void* pvSTRes = nullptr;
1167
1168 if (m_pobjAppInterface != nullptr)
1169 {
1170 m_pfnTimerCb = Rtp_RtcpTimerCb;
1171 // start RTCP timer with default value
1172 pvSTRes = m_pobjAppInterface->RtpStartTimer(
1173 uiTimerVal, eRTP_FALSE, m_pfnTimerCb, reinterpret_cast<RtpDt_Void*>(this));
1174 if (pvSTRes == nullptr)
1175 {
1176 RTP_TRACE_WARNING(
1177 "enableRtcp, start timer is returned NULL value.", RTP_ZERO, RTP_ZERO);
1178 return RTP_TIMER_PROC_ERR;
1179 }
1180 }
1181
1182 m_pTimerId = pvSTRes;
1183 RtpDt_UInt32 uiTempTc = m_objTimerInfo.getTc();
1184 m_objTimerInfo.setTp(uiTempTc);
1185 m_objTimerInfo.setTn(uiTempTc + uiTimerVal);
1186
1187 // RTCP BW
1188 m_objTimerInfo.setRtcpBw(pobjRtpProfile->getRtcpBandwidth());
1189
1190 // AVG RTCP SIZE
1191 m_objTimerInfo.setAvgRtcpSize(pobjRtpProfile->getRtcpBandwidth());
1192
1193 return RTP_SUCCESS;
1194 }
1195
disableRtcp()1196 eRTP_STATUS_CODE RtpSession::disableRtcp()
1197 {
1198 RtpDt_Void* pvData = nullptr;
1199
1200 RtpSessionManager* pobjActSesDb = RtpSessionManager::getInstance();
1201 pobjActSesDb->removeRtpSession(this);
1202
1203 m_bEnableRTCP = eRTP_FALSE;
1204 m_bEnableRTCPBye = eRTP_FALSE;
1205 if (m_pTimerId != nullptr && m_pobjAppInterface != nullptr)
1206 {
1207 m_pobjAppInterface->RtpStopTimer(m_pTimerId, &pvData);
1208 m_pTimerId = nullptr;
1209 }
1210
1211 m_objTimerInfo.cleanUp();
1212
1213 return RTP_SUCCESS;
1214 }
1215
initSession(IN IRtpAppInterface * pobjAppInterface,IN RtcpConfigInfo * pobjRtcpConfigInfo)1216 eRTP_STATUS_CODE RtpSession::initSession(
1217 IN IRtpAppInterface* pobjAppInterface, IN RtcpConfigInfo* pobjRtcpConfigInfo)
1218 {
1219 // set m_pobjAppInterface
1220 if (pobjAppInterface != nullptr)
1221 {
1222 if (m_pobjAppInterface != nullptr)
1223 delete m_pobjAppInterface;
1224
1225 m_pobjAppInterface = pobjAppInterface;
1226 }
1227 else
1228 {
1229 RTP_TRACE_WARNING("initSession, pobjAppInterface is NULL.", RTP_ZERO, RTP_ZERO);
1230
1231 return RTP_INVALID_PARAMS;
1232 }
1233
1234 // set pobjRtcpConfigInfo
1235 if (pobjRtcpConfigInfo != nullptr)
1236 {
1237 if (m_pobjRtcpCfgInfo != nullptr)
1238 delete m_pobjRtcpCfgInfo;
1239
1240 m_pobjRtcpCfgInfo = pobjRtcpConfigInfo;
1241 }
1242
1243 // m_usExtHdrLen = usExtHdrLen;
1244 // generate sequence number
1245 m_usSeqNum = (RtpDt_UInt16)RtpOsUtil::Rand();
1246 m_curRtpTimestamp = (RtpDt_UInt16)RtpOsUtil::Rand();
1247 RtpOsUtil::GetNtpTime(m_stCurNtpTimestamp);
1248 return RTP_SUCCESS;
1249 } // initSession
1250
setPayload(IN RtpPayloadInfo * pstPayloadInfo,IN RtpDt_UInt16 usExtHdrLen)1251 eRTP_STATUS_CODE RtpSession::setPayload(
1252 IN RtpPayloadInfo* pstPayloadInfo, IN RtpDt_UInt16 usExtHdrLen)
1253
1254 {
1255 // set RTP payload information
1256 if (pstPayloadInfo != nullptr)
1257 {
1258 if (m_pobjPayloadInfo == nullptr)
1259 {
1260 RTP_TRACE_ERROR("setPayload, m_pobjPayloadInfo is NULL.", RTP_ZERO, RTP_ZERO);
1261 return RTP_INVALID_PARAMS;
1262 }
1263 m_pobjPayloadInfo->setRtpPayloadInfo(pstPayloadInfo);
1264 }
1265 else
1266 {
1267 RTP_TRACE_ERROR("setPayload, pstPayloadInfo is NULL.", RTP_ZERO, RTP_ZERO);
1268
1269 return RTP_INVALID_PARAMS;
1270 }
1271
1272 m_usExtHdrLen = usExtHdrLen;
1273
1274 return RTP_SUCCESS;
1275 } // setpayload
1276
updatePayload(IN RtpPayloadInfo * pstPayloadInfo)1277 eRTP_STATUS_CODE RtpSession::updatePayload(IN RtpPayloadInfo* pstPayloadInfo)
1278 {
1279 m_pobjPayloadInfo->setRtpPayloadInfo(pstPayloadInfo);
1280
1281 return RTP_SUCCESS;
1282 } // updatePayload
1283
setRTCPTimerValue(IN RtpDt_UInt16 usRTCPTimerVal)1284 eRTP_STATUS_CODE RtpSession::setRTCPTimerValue(IN RtpDt_UInt16 usRTCPTimerVal)
1285 {
1286 m_usRTCPTimerVal = usRTCPTimerVal;
1287 return RTP_SUCCESS;
1288 }
1289
deleteRtpSession()1290 eRTP_STATUS_CODE RtpSession::deleteRtpSession()
1291 {
1292 RtpDt_Void* pvData = nullptr;
1293
1294 std::lock_guard<std::mutex> guard(m_objRtpSessionLock);
1295
1296 RtpSessionManager* pobjActSesDb = RtpSessionManager::getInstance();
1297 pobjActSesDb->removeRtpSession(this);
1298
1299 if (m_pTimerId != nullptr)
1300 {
1301 m_pobjAppInterface->RtpStopTimer(m_pTimerId, &pvData);
1302 m_pTimerId = nullptr;
1303 }
1304
1305 for (auto& pobjRcvrElm : *m_pobjRtpRcvrInfoList)
1306 {
1307 m_pobjAppInterface->deleteRcvrInfo(
1308 pobjRcvrElm->getSsrc(), pobjRcvrElm->getIpAddr(), pobjRcvrElm->getPort());
1309 }
1310
1311 return RTP_SUCCESS;
1312 } // deleteRtpSession
1313
collisionSendRtcpByePkt(IN RtpDt_UInt32 uiReceivedSsrc)1314 eRTP_STATUS_CODE RtpSession::collisionSendRtcpByePkt(IN RtpDt_UInt32 uiReceivedSsrc)
1315 {
1316 (RtpDt_Void) uiReceivedSsrc;
1317
1318 m_bSelfCollisionByeSent = eRTP_TRUE;
1319
1320 return RTP_SUCCESS;
1321 } // collisionSendRtcpByePkt
1322
chkRcvdSsrcStatus(IN RtpBuffer * pobjRtpAddr,IN RtpDt_UInt16 usPort,IN RtpDt_UInt32 uiRcvdSsrc)1323 eRTP_STATUS_CODE RtpSession::chkRcvdSsrcStatus(
1324 IN RtpBuffer* pobjRtpAddr, IN RtpDt_UInt16 usPort, IN RtpDt_UInt32 uiRcvdSsrc)
1325 {
1326 eRTP_STATUS_CODE eResult = RTP_SUCCESS;
1327 checkSsrcCollisionOnRcv(pobjRtpAddr, usPort, uiRcvdSsrc, eResult);
1328 return eResult;
1329 } // chkRcvdSsrcStatus
1330
checkSsrcCollisionOnRcv(IN RtpBuffer * pobjRtpAddr,IN RtpDt_UInt16 usPort,IN RtpDt_UInt32 uiRcvdSsrc,OUT eRTP_STATUS_CODE & eResult)1331 RtpReceiverInfo* RtpSession::checkSsrcCollisionOnRcv(IN RtpBuffer* pobjRtpAddr,
1332 IN RtpDt_UInt16 usPort, IN RtpDt_UInt32 uiRcvdSsrc, OUT eRTP_STATUS_CODE& eResult)
1333 {
1334 if (m_pobjRtpRcvrInfoList == nullptr)
1335 {
1336 eResult = RTP_INVALID_PARAMS;
1337 return nullptr;
1338 }
1339
1340 for (auto& pobjRcvInfo : *m_pobjRtpRcvrInfoList)
1341 {
1342 RtpDt_UInt32 uiTmpSsrc = RTP_ZERO;
1343 if (pobjRcvInfo == nullptr)
1344 break;
1345
1346 uiTmpSsrc = pobjRcvInfo->getSsrc();
1347 if (uiTmpSsrc == uiRcvdSsrc)
1348 {
1349 RtpBuffer* pobjTmpDestAddr = pobjRcvInfo->getIpAddr();
1350 RtpDt_UChar* pcDestAddr = pobjTmpDestAddr->getBuffer();
1351 RtpDt_UChar* pcRcvDestAddr = pobjRtpAddr->getBuffer();
1352 RtpDt_UInt16 usTmpPort = pobjRcvInfo->getPort();
1353 RtpDt_UInt32 uiRcvDestAddrLen = pobjRtpAddr->getLength();
1354
1355 if (pobjRcvInfo->getCsrcFlag() == eRTP_TRUE)
1356 {
1357 eResult = RTP_RCVD_CSRC_ENTRY;
1358 return pobjRcvInfo;
1359 }
1360
1361 if (usTmpPort != usPort)
1362 {
1363 RTP_TRACE_WARNING("checkSsrcCollisionOnRcv - Port prevPort[%d], receivedPort[%d]",
1364 usTmpPort, usPort);
1365 eResult = RTP_REMOTE_SSRC_COLLISION;
1366 return pobjRcvInfo;
1367 }
1368
1369 if (pcDestAddr == nullptr || pcRcvDestAddr == nullptr)
1370 {
1371 eResult = RTP_INVALID_PARAMS;
1372 return nullptr;
1373 }
1374
1375 if (memcmp(pcDestAddr, pcRcvDestAddr, uiRcvDestAddrLen) != RTP_ZERO)
1376 {
1377 eResult = RTP_REMOTE_SSRC_COLLISION;
1378 return pobjRcvInfo;
1379 }
1380
1381 eResult = RTP_OLD_SSRC_RCVD;
1382 return pobjRcvInfo;
1383 }
1384 }
1385
1386 eResult = RTP_NEW_SSRC_RCVD;
1387 return nullptr;
1388 } // checkSsrcCollisionOnRcv
1389
findEntryInCsrcList(IN std::list<RtpDt_UInt32> & pobjCsrcList,IN RtpDt_UInt32 uiSsrc)1390 eRtp_Bool RtpSession::findEntryInCsrcList(
1391 IN std::list<RtpDt_UInt32>& pobjCsrcList, IN RtpDt_UInt32 uiSsrc)
1392 {
1393 if (pobjCsrcList.empty())
1394 {
1395 return eRTP_FALSE;
1396 }
1397
1398 auto result = std::find(pobjCsrcList.begin(), pobjCsrcList.end(), uiSsrc);
1399 return (result != pobjCsrcList.end()) ? eRTP_TRUE : eRTP_FALSE;
1400
1401 } // findEntryInCsrcList
1402
findEntryInRcvrList(IN RtpDt_UInt32 uiSsrc)1403 eRtp_Bool RtpSession::findEntryInRcvrList(IN RtpDt_UInt32 uiSsrc)
1404 {
1405 for (auto& pobjRcvInfo : *m_pobjRtpRcvrInfoList)
1406 {
1407 if (pobjRcvInfo != nullptr && pobjRcvInfo->getSsrc() == uiSsrc)
1408 {
1409 return eRTP_TRUE;
1410 }
1411 }
1412
1413 return eRTP_FALSE;
1414 } // findEntryInRcvrList
1415
processCsrcList(IN RtpHeader * pobjRtpHeader,IN RtpDt_UChar ucCsrcCount)1416 eRTP_STATUS_CODE RtpSession::processCsrcList(
1417 IN RtpHeader* pobjRtpHeader, IN RtpDt_UChar ucCsrcCount)
1418 {
1419 eRtp_Bool bRcvrStatus = eRTP_FALSE;
1420 RtpDt_UInt16 usPos = RTP_ZERO;
1421 std::list<RtpDt_UInt32>& pobjCsrcList = pobjRtpHeader->getCsrcList();
1422
1423 for (std::list<RtpDt_UInt32>::iterator listIterator = pobjCsrcList.begin();
1424 (usPos < ucCsrcCount && listIterator != pobjCsrcList.end()); usPos = usPos + RTP_ONE)
1425 {
1426 RtpDt_UInt32 csrc = (*listIterator);
1427 bRcvrStatus = findEntryInRcvrList(csrc);
1428 if (bRcvrStatus == eRTP_FALSE)
1429 {
1430 RtpReceiverInfo* pobjRcvInfo = nullptr;
1431 pobjRcvInfo = new RtpReceiverInfo();
1432 if (pobjRcvInfo == nullptr)
1433 {
1434 RTP_TRACE_ERROR("[Memory Error] new returned NULL.", RTP_ZERO, RTP_ZERO);
1435 return RTP_MEMORY_FAIL;
1436 }
1437 // fill pobjRcvInfo
1438 // ssrc
1439 pobjRcvInfo->setSsrc(csrc);
1440 // m_bSender
1441 pobjRcvInfo->setSenderFlag(eRTP_FALSE);
1442
1443 pobjRcvInfo->setCsrcFlag(eRTP_TRUE);
1444
1445 // add entry into receiver list.
1446 m_pobjRtpRcvrInfoList->push_back(pobjRcvInfo);
1447 RTP_TRACE_MESSAGE("processCsrcList - added ssrc[%x] from port[%d] to receiver list",
1448 pobjRcvInfo->getSsrc(), pobjRcvInfo->getPort());
1449 }
1450 ++listIterator;
1451 }
1452 return RTP_SUCCESS;
1453 } // processCsrcList
1454
processRcvdRtpPkt(IN RtpBuffer * pobjRtpAddr,IN RtpDt_UInt16 usPort,IN RtpBuffer * pobjRTPPacket,OUT RtpPacket * pobjRtpPkt)1455 eRTP_STATUS_CODE RtpSession::processRcvdRtpPkt(IN RtpBuffer* pobjRtpAddr, IN RtpDt_UInt16 usPort,
1456 IN RtpBuffer* pobjRTPPacket, OUT RtpPacket* pobjRtpPkt)
1457 {
1458 std::lock_guard<std::mutex> guard(m_objRtpSessionLock);
1459
1460 // validation
1461 if ((pobjRTPPacket == nullptr) || (pobjRtpPkt == nullptr) || (pobjRtpAddr == nullptr))
1462 {
1463 RTP_TRACE_WARNING(
1464 "processRcvdRtpPkt, pobjRTPPacket || pobjRtpPkt is NULL.", RTP_ZERO, RTP_ZERO);
1465 return RTP_INVALID_PARAMS;
1466 }
1467
1468 RtpDt_UInt32 uiRcvdOcts = pobjRTPPacket->getLength();
1469
1470 // decode the packet
1471 eRtp_Bool eRtpDecodeRes = eRTP_FAILURE;
1472 eRtpDecodeRes = pobjRtpPkt->decodePacket(pobjRTPPacket);
1473
1474 if (eRtpDecodeRes == eRTP_FAILURE)
1475 {
1476 RTP_TRACE_WARNING("processRcvdRtpPkt -RTP_DECODE_ERROR", RTP_ZERO, RTP_ZERO);
1477 return RTP_DECODE_ERROR;
1478 }
1479
1480 RtpHeader* pobjRtpHeader = pobjRtpPkt->getRtpHeader();
1481
1482 // check received payload type is matching with expected RTP payload types.
1483 if (!checkRtpPayloadType(pobjRtpHeader, m_pobjPayloadInfo))
1484 {
1485 RTP_TRACE_WARNING(
1486 "processRcvdRtpPkt -eRcvdResult == RTP_INVALID_PARAMS.invalid payload type)",
1487 RTP_ZERO, RTP_ZERO);
1488
1489 return RTP_INVALID_PARAMS;
1490 }
1491 // check received ssrc is matching with the current RTP session.
1492
1493 RtpDt_UInt32 uiReceivedSsrc = pobjRtpHeader->getRtpSsrc();
1494 RtpDt_UChar ucCsrcCount = pobjRtpHeader->getCsrcCount();
1495 eRtp_Bool bCsrcStatus = eRTP_FALSE;
1496
1497 if (ucCsrcCount > RTP_ZERO)
1498 {
1499 std::list<RtpDt_UInt32>& pobjCsrcList = pobjRtpHeader->getCsrcList();
1500 bCsrcStatus = findEntryInCsrcList(pobjCsrcList, m_uiSsrc);
1501 }
1502
1503 if ((uiReceivedSsrc == m_uiSsrc) || (bCsrcStatus == eRTP_TRUE))
1504 {
1505 RtpStackProfile* pobjRtpProfile = m_pobjRtpStack->getStackProfile();
1506 RtpDt_UInt32 uiTermNum = pobjRtpProfile->getTermNumber();
1507 eRTP_STATUS_CODE eByeRes = RTP_SUCCESS;
1508
1509 // collision happened.
1510 if ((m_bEnableRTCP == eRTP_TRUE) && (m_bEnableRTCPBye == eRTP_TRUE) &&
1511 (m_bRtpSendPkt == eRTP_TRUE))
1512 {
1513 eByeRes = collisionSendRtcpByePkt(uiReceivedSsrc);
1514 if (eByeRes != RTP_SUCCESS)
1515 {
1516 RTP_TRACE_WARNING("processRcvdRtpPkt -eByeRes", RTP_ZERO, RTP_ZERO);
1517 return eByeRes;
1518 }
1519 }
1520 else
1521 {
1522 // generate SSRC
1523 RtpDt_UInt32 uiNewSsrc = RTP_ZERO;
1524 uiNewSsrc = RtpStackUtil::generateNewSsrc(uiTermNum);
1525 m_uiSsrc = uiNewSsrc;
1526 }
1527 RTP_TRACE_WARNING("processRcvdRtpPkt RTP_OWN_SSRC_COLLISION)", RTP_ZERO, RTP_ZERO);
1528
1529 return RTP_OWN_SSRC_COLLISION;
1530 }
1531
1532 // check SSRC collision on m_objRtpRcvrInfoList
1533 eRTP_STATUS_CODE eRcvdResult = RTP_FAILURE;
1534 RtpReceiverInfo* pobjRcvInfo =
1535 checkSsrcCollisionOnRcv(pobjRtpAddr, usPort, uiReceivedSsrc, eRcvdResult);
1536
1537 if (eRcvdResult == RTP_REMOTE_SSRC_COLLISION)
1538 {
1539 RTP_TRACE_WARNING(
1540 "processRcvdRtpPkt -eRcvdResult == RTP_REMOTE_SSRC_COLLISION)", RTP_ZERO, RTP_ZERO);
1541 return eRcvdResult;
1542 }
1543
1544 if (eRcvdResult != RTP_NEW_SSRC_RCVD && pobjRcvInfo == nullptr)
1545 {
1546 RTP_TRACE_WARNING(
1547 "processRcvdRtpPkt -eRcvdResult == RTP_INVALID_PARAMS. pobjRcvInfo is NULL)",
1548 RTP_ZERO, RTP_ZERO);
1549
1550 return RTP_INVALID_PARAMS;
1551 }
1552
1553 if (eRcvdResult == RTP_NEW_SSRC_RCVD)
1554 {
1555 // add entry into the list.
1556 pobjRcvInfo = new RtpReceiverInfo();
1557 if (pobjRcvInfo == nullptr)
1558 {
1559 RTP_TRACE_ERROR("[Memory Error] new returned NULL.", RTP_ZERO, RTP_ZERO);
1560 return RTP_MEMORY_FAIL;
1561 }
1562
1563 // initialize the rcvr info
1564 pobjRcvInfo->initSeq(pobjRtpHeader->getSequenceNumber());
1565
1566 // populate pobjRcvInfo object
1567 // ip address
1568 pobjRcvInfo->setIpAddr(pobjRtpAddr);
1569 // port
1570 pobjRcvInfo->setPort(usPort);
1571 // ssrc
1572 pobjRcvInfo->setSsrc(uiReceivedSsrc);
1573 // m_bSender
1574 pobjRcvInfo->setSenderFlag(eRTP_TRUE);
1575
1576 pobjRcvInfo->setprevRtpTimestamp(m_curRtpTimestamp);
1577
1578 pobjRcvInfo->setprevNtpTimestamp(&m_stCurNtpTimestamp);
1579
1580 m_pobjRtpRcvrInfoList->push_back(pobjRcvInfo);
1581 RTP_TRACE_MESSAGE("processRcvdRtpPkt - added ssrc[%x] from port[%d] to receiver list",
1582 pobjRcvInfo->getSsrc(), pobjRcvInfo->getPort());
1583
1584 // first RTP packet received
1585 m_bFirstRtpRecvd = eRTP_TRUE;
1586 } // RTP_NEW_SSRC_RCVD
1587 else if (m_bFirstRtpRecvd == eRTP_FALSE)
1588 {
1589 // initialize the receiver info
1590 pobjRcvInfo->initSeq(pobjRtpHeader->getSequenceNumber());
1591 // m_bSender
1592 pobjRcvInfo->setSenderFlag(eRTP_TRUE);
1593 // first RTP packet received
1594 m_bFirstRtpRecvd = eRTP_TRUE;
1595 }
1596
1597 if (eRcvdResult == RTP_RCVD_CSRC_ENTRY)
1598 {
1599 pobjRcvInfo->initSeq(pobjRtpHeader->getSequenceNumber());
1600 // ip address
1601 pobjRcvInfo->setIpAddr(pobjRtpAddr);
1602 // port
1603 pobjRcvInfo->setPort(usPort);
1604 // m_bSender
1605 pobjRcvInfo->setSenderFlag(eRTP_TRUE);
1606 } // RTP_RCVD_CSRC_ENTRY
1607
1608 // process CSRC list
1609 processCsrcList(pobjRtpHeader, ucCsrcCount);
1610
1611 if (pobjRcvInfo == nullptr)
1612 return RTP_SUCCESS;
1613
1614 // calculate interarrival jitter
1615 pobjRcvInfo->calcJitter(pobjRtpHeader->getRtpTimestamp(), m_pobjPayloadInfo->getSamplingRate());
1616
1617 // update ROC
1618 RtpDt_UInt16 usTempSeqNum = pobjRtpHeader->getSequenceNumber();
1619 RtpDt_UInt32 uiUpdateSeqRes = pobjRcvInfo->updateSeq(usTempSeqNum);
1620
1621 // update statistics
1622 // m_uiTotalRcvdRtpPkts
1623 pobjRcvInfo->incrTotalRcvdRtpPkts();
1624 // m_uiTotalRcvdRtpOcts
1625 pobjRcvInfo->incrTotalRcvdRtpOcts(uiRcvdOcts);
1626
1627 // m_bSender
1628 pobjRcvInfo->setSenderFlag(eRTP_TRUE);
1629
1630 if (uiUpdateSeqRes == RTP_ZERO)
1631 {
1632 RTP_TRACE_WARNING(
1633 "processRcvdRtpPkt -uiUpdateSeqRes == RTP_ZERO - RTP_BAD_SEQ)", RTP_ZERO, RTP_ZERO);
1634 return RTP_BAD_SEQ;
1635 }
1636
1637 return RTP_SUCCESS;
1638 } // processRcvdRtpPkt
1639
populateRtpHeader(IN_OUT RtpHeader * pobjRtpHdr,IN eRtp_Bool eSetMarker,IN RtpDt_UChar ucPayloadType)1640 eRTP_STATUS_CODE RtpSession::populateRtpHeader(
1641 IN_OUT RtpHeader* pobjRtpHdr, IN eRtp_Bool eSetMarker, IN RtpDt_UChar ucPayloadType)
1642 {
1643 // version
1644 pobjRtpHdr->setVersion((RtpDt_UChar)RTP_VERSION_NUM);
1645
1646 // marker
1647 if (eSetMarker == eRTP_TRUE)
1648 {
1649 pobjRtpHdr->setMarker();
1650 }
1651
1652 // payload type
1653 pobjRtpHdr->setPayloadType((RtpDt_UChar)ucPayloadType);
1654
1655 // sequence number
1656 if (m_uiRtpSendPktCount == RTP_ZERO)
1657 {
1658 pobjRtpHdr->setSequenceNumber(m_usSeqNum);
1659 }
1660 else
1661 {
1662 m_usSeqNum++;
1663 pobjRtpHdr->setSequenceNumber(m_usSeqNum);
1664 }
1665
1666 // Synchronization source
1667 pobjRtpHdr->setRtpSsrc(m_uiSsrc);
1668
1669 return RTP_SUCCESS;
1670 } // populateRtpHeader
1671
createRtpPacket(IN RtpBuffer * pobjPayload,IN eRtp_Bool eSetMarker,IN RtpDt_UChar ucPayloadType,IN eRtp_Bool bUseLastTimestamp,IN RtpDt_UInt32 uiRtpTimestampDiff,IN RtpBuffer * pobjXHdr,OUT RtpBuffer * pRtpPkt)1672 eRTP_STATUS_CODE RtpSession::createRtpPacket(IN RtpBuffer* pobjPayload, IN eRtp_Bool eSetMarker,
1673 IN RtpDt_UChar ucPayloadType, IN eRtp_Bool bUseLastTimestamp,
1674 IN RtpDt_UInt32 uiRtpTimestampDiff, IN RtpBuffer* pobjXHdr, OUT RtpBuffer* pRtpPkt)
1675 {
1676 RtpPacket objRtpPacket;
1677 RtpHeader* pobjRtpHdr = objRtpPacket.getRtpHeader();
1678
1679 // populate Rtp header information.
1680 populateRtpHeader(pobjRtpHdr, eSetMarker, ucPayloadType);
1681 if (pobjXHdr && pobjXHdr->getLength() > RTP_ZERO)
1682 pobjRtpHdr->setExtension(RTP_ONE);
1683 else
1684 pobjRtpHdr->setExtension(RTP_ZERO);
1685
1686 // set timestamp
1687 m_stPrevNtpTimestamp = m_stCurNtpTimestamp;
1688 m_prevRtpTimestamp = m_curRtpTimestamp;
1689 RtpDt_UInt32 uiSamplingRate = RTP_ZERO;
1690
1691 if (!bUseLastTimestamp)
1692 {
1693 m_stPrevNtpTimestamp = m_stCurNtpTimestamp;
1694 m_prevRtpTimestamp = m_curRtpTimestamp;
1695 RtpOsUtil::GetNtpTime(m_stCurNtpTimestamp);
1696
1697 if (m_uiRtpSendPktCount == RTP_ZERO)
1698 {
1699 m_stPrevNtpTimestamp = m_stCurNtpTimestamp;
1700 }
1701
1702 if (uiRtpTimestampDiff)
1703 {
1704 m_curRtpTimestamp += uiRtpTimestampDiff;
1705 }
1706 else
1707 {
1708 uiSamplingRate = m_pobjPayloadInfo->getSamplingRate();
1709 m_curRtpTimestamp = RtpStackUtil::calcRtpTimestamp(m_prevRtpTimestamp,
1710 &m_stCurNtpTimestamp, &m_stPrevNtpTimestamp, uiSamplingRate);
1711 }
1712 }
1713
1714 pobjRtpHdr->setRtpTimestamp(m_curRtpTimestamp);
1715
1716 // set pobjPayload to RtpPacket
1717 objRtpPacket.setRtpPayload(pobjPayload);
1718
1719 // construct RTP packet
1720 RtpDt_UInt32 uiRtpLength = pobjPayload->getLength();
1721 #ifdef ENABLE_PADDING
1722 RtpDt_UInt32 uiPadLength = uiRtpLength % RTP_FOUR;
1723 if (uiPadLength > RTP_ZERO)
1724 {
1725 uiPadLength = RTP_FOUR - uiPadLength;
1726 uiRtpLength += uiPadLength;
1727
1728 // set padding bit to header
1729 pobjRtpHdr->setPadding();
1730 }
1731 #endif
1732 uiRtpLength += RTP_FIXED_HDR_LEN;
1733 uiRtpLength += (RTP_FOUR * pobjRtpHdr->getCsrcCount());
1734 if (pobjXHdr)
1735 uiRtpLength += pobjXHdr->getLength();
1736
1737 RtpDt_UChar* pucRtpBuffer = new RtpDt_UChar[uiRtpLength];
1738 if (pucRtpBuffer == nullptr)
1739 {
1740 RTP_TRACE_WARNING("createRtpPacket, error in allocating memory ", RTP_ZERO, RTP_ZERO);
1741 // set rtp payload as NULL in RtpPacket
1742 objRtpPacket.setRtpPayload(nullptr);
1743 return RTP_MEMORY_FAIL;
1744 }
1745 memset(pucRtpBuffer, RTP_ZERO, uiRtpLength);
1746
1747 pRtpPkt->setBufferInfo(uiRtpLength, pucRtpBuffer);
1748
1749 if ((pobjXHdr && pobjXHdr->getLength() > RTP_ZERO))
1750 {
1751 objRtpPacket.setExtHeader(pobjXHdr);
1752 }
1753 else
1754 {
1755 delete pobjXHdr;
1756 }
1757
1758 // encode the Rtp packet.
1759 eRtp_Bool bPackRes = eRTP_TRUE;
1760 bPackRes = objRtpPacket.formPacket(pRtpPkt);
1761
1762 // set pobjPayload to NULL in both success and failure case
1763 objRtpPacket.setRtpPayload(nullptr);
1764
1765 if (bPackRes != eRTP_TRUE)
1766 {
1767 RTP_TRACE_WARNING(
1768 "createRtpPacket - formPacket failed!! bPackRes != eRTP_TRUE", RTP_ZERO, RTP_ZERO);
1769 return RTP_ENCODE_ERROR;
1770 }
1771
1772 // update statistics
1773 m_uiRtpSendPktCount++;
1774 m_uiRtpSendOctCount += pobjPayload->getLength();
1775
1776 // set we_sent flag as true
1777 m_objTimerInfo.setWeSent(RTP_TWO);
1778
1779 // set m_bRtpSendPkt to true
1780 m_bRtpSendPkt = eRTP_TRUE;
1781
1782 return RTP_SUCCESS;
1783 } // createRtpPacket
1784
processRtcpPkt(IN RtpDt_UInt32 uiRcvdSsrc,IN RtpBuffer * pobjRtcpAddr,IN RtpDt_UInt16 usPort)1785 RtpReceiverInfo* RtpSession::processRtcpPkt(
1786 IN RtpDt_UInt32 uiRcvdSsrc, IN RtpBuffer* pobjRtcpAddr, IN RtpDt_UInt16 usPort)
1787 {
1788 eRTP_STATUS_CODE eRcvdResult = RTP_SUCCESS;
1789
1790 // check SSRC collision on m_objRtpRcvrInfoList
1791 RtpReceiverInfo* pobjRcvInfo =
1792 checkSsrcCollisionOnRcv(pobjRtcpAddr, usPort, uiRcvdSsrc, eRcvdResult);
1793
1794 if (eRcvdResult == RTP_NEW_SSRC_RCVD)
1795 {
1796 // add entry into the list.
1797 pobjRcvInfo = new RtpReceiverInfo();
1798 if (pobjRcvInfo == nullptr)
1799 {
1800 return nullptr;
1801 }
1802 // populate pobjRcvInfo object
1803 // ip address
1804 pobjRcvInfo->setIpAddr(pobjRtcpAddr);
1805 // port
1806 pobjRcvInfo->setPort(usPort);
1807 // ssrc
1808 pobjRcvInfo->setSsrc(uiRcvdSsrc);
1809 m_pobjRtpRcvrInfoList->push_back(pobjRcvInfo);
1810 RTP_TRACE_MESSAGE("processRtcpPkt - added ssrc[%x] from port[%d] to receiver list",
1811 pobjRcvInfo->getSsrc(), pobjRcvInfo->getPort());
1812 }
1813 else if (eRcvdResult != RTP_INVALID_PARAMS)
1814 {
1815 // m_bSender should be FALSE for RTCP
1816 /* if(pobjRcvInfo != nullptr)
1817 {
1818 pobjRcvInfo->setSenderFlag(eRTP_FALSE);
1819 }
1820 */
1821 }
1822
1823 return pobjRcvInfo;
1824 } // processRtcpPkt
1825
delEntryFromRcvrList(IN RtpDt_UInt32 * puiSsrc)1826 RtpDt_Void RtpSession::delEntryFromRcvrList(IN RtpDt_UInt32* puiSsrc)
1827 {
1828 for (auto it = m_pobjRtpRcvrInfoList->begin(); it != m_pobjRtpRcvrInfoList->end();)
1829 {
1830 if ((*it)->getSsrc() == *puiSsrc)
1831 {
1832 it = m_pobjRtpRcvrInfoList->erase(it);
1833 break;
1834 }
1835 else
1836 {
1837 ++it;
1838 }
1839 }
1840 } // delEntryFromRcvrList
1841
processByePacket(IN RtcpByePacket * pobjByePkt,IN RtpBuffer * pobjRtcpAddr,IN RtpDt_UInt16 usPort)1842 eRTP_STATUS_CODE RtpSession::processByePacket(
1843 IN RtcpByePacket* pobjByePkt, IN RtpBuffer* pobjRtcpAddr, IN RtpDt_UInt16 usPort)
1844 {
1845 (RtpDt_Void) pobjRtcpAddr, (RtpDt_Void)usPort;
1846
1847 RtcpHeader* pobjHdrInfo = pobjByePkt->getRtcpHdrInfo();
1848 RtpDt_UInt16 usNumSsrc = pobjHdrInfo->getReceptionReportCount();
1849 std::list<RtpDt_UInt32*>& pobjSsrcList = pobjByePkt->getSsrcList();
1850 RtpDt_UInt16 usPos = RTP_ZERO;
1851
1852 // delete entry from receiver list
1853 for (std::list<RtpDt_UInt32*>::iterator listIterator = pobjSsrcList.begin();
1854 (usPos < usNumSsrc && listIterator != pobjSsrcList.end()); usPos = usPos + RTP_ONE)
1855 {
1856 if (usPos == RTP_ZERO)
1857 {
1858 RtpDt_UInt32 uiSsrc = pobjHdrInfo->getSsrc();
1859 delEntryFromRcvrList(&uiSsrc);
1860 }
1861 else
1862 {
1863 RtpDt_UInt32* puiSsrc = nullptr;
1864 // get element from list
1865 puiSsrc = (*listIterator);
1866 if (puiSsrc != nullptr)
1867 {
1868 delEntryFromRcvrList(puiSsrc);
1869 }
1870 ++listIterator;
1871 }
1872 } // for
1873
1874 // get size of the pobjSsrcList
1875 eRtp_Bool bByeResult = eRTP_FALSE;
1876 RtpDt_UInt16 usRcvrNum = m_pobjRtpRcvrInfoList->size();
1877 bByeResult = m_objTimerInfo.updateByePktInfo(usRcvrNum);
1878
1879 if ((bByeResult == eRTP_TRUE) && (m_bEnableRTCP == eRTP_TRUE) &&
1880 (m_pobjAppInterface != nullptr))
1881 {
1882 // Reschedule the next report for time tn
1883 RtpDt_UInt32 uiTempTn = m_objTimerInfo.getTn();
1884 RtpDt_UInt32 uiTempTc = m_objTimerInfo.getTc();
1885 RTP_TRACE_MESSAGE(
1886 "processByePacket before processing[Tn : %u] [Tc : %u]", uiTempTn, uiTempTc);
1887
1888 RtpDt_UInt16 usMembers = m_pobjRtpRcvrInfoList->size();
1889 uiTempTc = m_objTimerInfo.getTc();
1890 RtpDt_Double dTempT = rtcp_interval(usMembers);
1891
1892 // convert uiTempT to milliseconds
1893 RtpDt_UInt32 uiTimerVal = RTP_ZERO;
1894
1895 dTempT = dTempT * RTP_SEC_TO_MILLISEC;
1896 RtpDt_UInt32 uiRoundDiff = (RtpDt_UInt32)dTempT;
1897 uiRoundDiff = ((uiRoundDiff / 100) * 100);
1898
1899 if (uiTempTn > uiTempTc)
1900 {
1901 uiTimerVal = uiTempTn - uiTempTc;
1902 if (uiTimerVal > uiRoundDiff)
1903 {
1904 uiTimerVal = uiRoundDiff;
1905 }
1906 }
1907 else
1908 {
1909 uiTimerVal = uiRoundDiff;
1910 }
1911
1912 RTP_TRACE_MESSAGE("processByePacket [uiTimerVal : %u]", uiTimerVal, RTP_ZERO);
1913 RtpDt_Void* pvData = nullptr;
1914 eRtp_Bool bTSres = eRTP_FALSE;
1915
1916 if (m_pTimerId != nullptr)
1917 {
1918 bTSres = m_pobjAppInterface->RtpStopTimer(m_pTimerId, &pvData);
1919 m_pTimerId = nullptr;
1920 if (bTSres == eRTP_FALSE)
1921 {
1922 return RTP_TIMER_PROC_ERR;
1923 }
1924 }
1925 RtpDt_Void* pvSTRes =
1926 m_pobjAppInterface->RtpStartTimer(uiTimerVal, eRTP_FALSE, m_pfnTimerCb, this);
1927 if (pvSTRes == nullptr)
1928 {
1929 return RTP_TIMER_PROC_ERR;
1930 }
1931 m_pTimerId = pvSTRes;
1932 }
1933
1934 return RTP_SUCCESS;
1935 } // processByePacket
1936
processSdesPacket(IN RtcpSdesPacket * pobjSdesPkt)1937 eRTP_STATUS_CODE RtpSession::processSdesPacket(IN RtcpSdesPacket* pobjSdesPkt)
1938 {
1939 (RtpDt_Void) pobjSdesPkt;
1940 return RTP_SUCCESS;
1941 }
1942
processRcvdRtcpPkt(IN RtpBuffer * pobjRtcpAddr,IN RtpDt_UInt16 usPort,IN RtpBuffer * pobjRTCPBuf,OUT RtcpPacket * pobjRtcpPkt)1943 eRTP_STATUS_CODE RtpSession::processRcvdRtcpPkt(IN RtpBuffer* pobjRtcpAddr, IN RtpDt_UInt16 usPort,
1944 IN RtpBuffer* pobjRTCPBuf, OUT RtcpPacket* pobjRtcpPkt)
1945 {
1946 if (m_bEnableRTCP != eRTP_TRUE)
1947 {
1948 RTP_TRACE_WARNING("[ProcessRcvdRtcpPkt], RTCP is not enabled", RTP_ZERO, RTP_ZERO);
1949
1950 return RTP_NO_RTCP_SUPPORT;
1951 }
1952
1953 // validity checking
1954 if (pobjRtcpAddr == nullptr || pobjRTCPBuf == nullptr || pobjRtcpPkt == nullptr)
1955 {
1956 RTP_TRACE_ERROR("[ProcessRcvdRtcpPkt] Invalid params. pobjRtcpAddr[%x] pobjRTCPBuf[%x]",
1957 pobjRtcpAddr, pobjRTCPBuf);
1958 return RTP_INVALID_PARAMS;
1959 }
1960
1961 RtpDt_UInt16 usExtHdrLen = RTP_ZERO;
1962 eRTP_STATUS_CODE eDecodeStatus = RTP_FAILURE;
1963
1964 tRTP_NTP_TIME stNtpTs = {RTP_ZERO, RTP_ZERO};
1965 RtpOsUtil::GetNtpTime(stNtpTs);
1966 RtpDt_UInt32 currentTime = RtpStackUtil::getMidFourOctets(&stNtpTs);
1967 // decode compound packet
1968 eDecodeStatus = pobjRtcpPkt->decodeRtcpPacket(pobjRTCPBuf, usExtHdrLen, m_pobjRtcpCfgInfo);
1969 if (eDecodeStatus != RTP_SUCCESS)
1970 {
1971 RTP_TRACE_ERROR(
1972 "[ProcessRcvdRtcpPkt], Error Decoding compound RTCP packet!", RTP_ZERO, RTP_ZERO);
1973 return eDecodeStatus;
1974 }
1975
1976 // update average rtcp size
1977 RtpDt_UInt32 uiRcvdPktSize = pobjRTCPBuf->getLength();
1978 m_objTimerInfo.updateAvgRtcpSize(uiRcvdPktSize);
1979
1980 std::list<RtcpSrPacket*>& pobjSrList = pobjRtcpPkt->getSrPacketList();
1981
1982 if (pobjSrList.size() > RTP_ZERO)
1983 {
1984 // get key material element from list.
1985 RtcpSrPacket* pobjSrPkt = pobjSrList.front();
1986
1987 RtcpRrPacket* pobjRRPkt = pobjSrPkt->getRrPktInfo();
1988 RtcpHeader* pobjRtcpHdr = pobjRRPkt->getRtcpHdrInfo();
1989 RtpDt_UInt32 uiRcvdSsrc = pobjRtcpHdr->getSsrc();
1990
1991 // calculate RTTD
1992 std::list<RtcpReportBlock*>& pobjReportBlkList = pobjRRPkt->getReportBlockList();
1993 if (pobjReportBlkList.size() > RTP_ZERO)
1994 {
1995 RtcpReportBlock* pobjReportBlk = pobjReportBlkList.front();
1996 if (pobjReportBlk != nullptr)
1997 {
1998 calculateAndSetRTTD(
1999 currentTime, pobjReportBlk->getLastSR(), pobjReportBlk->getDelayLastSR());
2000 }
2001 }
2002 // decrement rtcp port by one
2003 usPort = usPort - RTP_ONE;
2004 RtpReceiverInfo* pobjRcvInfo = processRtcpPkt(uiRcvdSsrc, pobjRtcpAddr, usPort);
2005 if (pobjRcvInfo != nullptr)
2006 {
2007 stNtpTs = {RTP_ZERO, RTP_ZERO};
2008 pobjRcvInfo->setpreSrTimestamp(pobjSrPkt->getNtpTime());
2009 RtpOsUtil::GetNtpTime(stNtpTs);
2010 pobjRcvInfo->setLastSrNtpTimestamp(&stNtpTs);
2011 }
2012 } // RTCP SR
2013
2014 // RTCP RR packet
2015 std::list<RtcpRrPacket*>& pobjRrList = pobjRtcpPkt->getRrPacketList();
2016
2017 if (pobjRrList.size() > RTP_ZERO)
2018 {
2019 // get key material element from list.
2020 RtcpRrPacket* pobjRrPkt = pobjRrList.front();
2021
2022 // calculate RTTD
2023 std::list<RtcpReportBlock*>& pobjReportBlkList = pobjRrPkt->getReportBlockList();
2024 if (pobjReportBlkList.size() > RTP_ZERO)
2025 {
2026 RtcpReportBlock* pobjReportBlk = pobjReportBlkList.front();
2027 if (pobjReportBlk != nullptr)
2028 {
2029 calculateAndSetRTTD(
2030 currentTime, pobjReportBlk->getLastSR(), pobjReportBlk->getDelayLastSR());
2031 }
2032 }
2033
2034 RtcpHeader* pobjRtcpHdr = pobjRrPkt->getRtcpHdrInfo();
2035 RtpDt_UInt32 uiRcvdSsrc = pobjRtcpHdr->getSsrc();
2036
2037 // decrement rtcp port by one
2038 usPort = usPort - RTP_ONE;
2039 processRtcpPkt(uiRcvdSsrc, pobjRtcpAddr, usPort);
2040 } // RTCP RR
2041
2042 // RTCP SDES packet
2043 RtcpSdesPacket* pobjSdesPkt = pobjRtcpPkt->getSdesPacket();
2044 if (pobjSdesPkt != nullptr)
2045 {
2046 // sdes
2047 processSdesPacket(pobjSdesPkt);
2048 }
2049
2050 // RTCP BYE packet
2051 RtcpByePacket* pobjByePkt = pobjRtcpPkt->getByePacket();
2052 if (pobjByePkt != nullptr)
2053 {
2054 // bye
2055 processByePacket(pobjByePkt, pobjRtcpAddr, usPort);
2056 }
2057
2058 return RTP_SUCCESS;
2059 } // processRcvdRtcpPkt
2060
sendRtcpByePacket()2061 eRtp_Bool RtpSession::sendRtcpByePacket()
2062 {
2063 RtcpPacket objRtcpPkt;
2064 std::lock_guard<std::mutex> guard(m_objRtpSessionLock);
2065
2066 if (m_bEnableRTCP == eRTP_TRUE && m_bEnableRTCPBye == eRTP_TRUE)
2067 {
2068 m_bSndRtcpByePkt = eRTP_TRUE;
2069
2070 // set timestamp
2071 rtpSetTimestamp();
2072
2073 if (rtpMakeCompoundRtcpPacket(&objRtcpPkt) != RTP_SUCCESS)
2074 {
2075 return eRTP_FALSE;
2076 }
2077
2078 if (rtpSendRtcpPacket(&objRtcpPkt) == RTP_SUCCESS)
2079 {
2080 if (m_bSelfCollisionByeSent == eRTP_TRUE)
2081 {
2082 // generate SSRC
2083 RtpStackProfile* pobjRtpProfile = m_pobjRtpStack->getStackProfile();
2084 RtpDt_UInt32 uiTermNum = pobjRtpProfile->getTermNumber();
2085 RtpDt_UInt32 uiNewSsrc = RTP_ZERO;
2086 uiNewSsrc = RtpStackUtil::generateNewSsrc(uiTermNum);
2087 m_uiSsrc = uiNewSsrc;
2088 RTP_TRACE_WARNING(
2089 "sendRtcpByePacket::SSRC after collision: %x", m_uiSsrc, RTP_ZERO);
2090 }
2091
2092 return eRTP_TRUE;
2093 }
2094 }
2095
2096 return eRTP_FALSE;
2097 }
2098
sendRtcpRtpFbPacket(IN RtpDt_UInt32 uiFbType,IN RtpDt_Char * pcbuff,IN RtpDt_UInt32 uiLen,IN RtpDt_UInt32 uiMediaSsrc)2099 eRtp_Bool RtpSession::sendRtcpRtpFbPacket(IN RtpDt_UInt32 uiFbType, IN RtpDt_Char* pcbuff,
2100 IN RtpDt_UInt32 uiLen, IN RtpDt_UInt32 uiMediaSsrc)
2101 {
2102 RtcpPacket objRtcpPkt;
2103
2104 std::lock_guard<std::mutex> guard(m_objRtpSessionLock);
2105 // set timestamp
2106 rtpSetTimestamp();
2107
2108 if (rtpMakeCompoundRtcpPacket(&objRtcpPkt) != RTP_SUCCESS)
2109 {
2110 return eRTP_FALSE;
2111 }
2112 populateRtcpFbPacket(&objRtcpPkt, uiFbType, pcbuff, uiLen, uiMediaSsrc, RTCP_RTPFB);
2113
2114 if (rtpSendRtcpPacket(&objRtcpPkt) == RTP_SUCCESS)
2115 {
2116 return eRTP_TRUE;
2117 }
2118
2119 return eRTP_FALSE;
2120 }
2121
sendRtcpPayloadFbPacket(IN RtpDt_UInt32 uiFbType,IN RtpDt_Char * pcbuff,IN RtpDt_UInt32 uiLen,IN RtpDt_UInt32 uiMediaSsrc)2122 eRtp_Bool RtpSession::sendRtcpPayloadFbPacket(IN RtpDt_UInt32 uiFbType, IN RtpDt_Char* pcbuff,
2123 IN RtpDt_UInt32 uiLen, IN RtpDt_UInt32 uiMediaSsrc)
2124 {
2125 RtcpPacket objRtcpPkt;
2126
2127 std::lock_guard<std::mutex> guard(m_objRtpSessionLock);
2128 // set timestamp
2129 rtpSetTimestamp();
2130
2131 if (rtpMakeCompoundRtcpPacket(&objRtcpPkt) != RTP_SUCCESS)
2132 {
2133 return eRTP_FALSE;
2134 }
2135
2136 populateRtcpFbPacket(&objRtcpPkt, uiFbType, pcbuff, uiLen, uiMediaSsrc, RTCP_PSFB);
2137
2138 if (rtpSendRtcpPacket(&objRtcpPkt) == RTP_SUCCESS)
2139 {
2140 return eRTP_TRUE;
2141 }
2142
2143 return eRTP_FALSE;
2144 }
2145
rtcp_interval(IN RtpDt_UInt16 usMembers)2146 RtpDt_Double RtpSession::rtcp_interval(IN RtpDt_UInt16 usMembers)
2147 {
2148 RtpDt_Double const RTCP_MIN_TIME = 5.;
2149
2150 /**
2151 * The target RTCP bandwidth, i.e., the total bandwidth
2152 * that will be used for RTCP packets by all members of this session,
2153 * in octets per second. This will be a specified fraction of the
2154 * "session bandwidth" parameter supplied to the application at
2155 * startup.
2156 */
2157 RtpDt_Double ulRtcp_bw = m_objTimerInfo.getRtcpBw();
2158
2159 RtpDt_Double const RTCP_SENDER_BW_FRACTION = 0.25L;
2160 RtpDt_Double const RTCP_RCVR_BW_FRACTION = (1 - RTCP_SENDER_BW_FRACTION);
2161 RtpDt_Double const COMPENSATION = 2.71828 - 1.5;
2162 RtpDt_Double ulRtcp_min_time = RTCP_MIN_TIME;
2163 RtpDt_Double ulTimerVal = RTP_ZERO;
2164 RtpDt_Double dDefTimerVal = 2.5;
2165
2166 if (usMembers == RTP_ZERO)
2167 {
2168 RTP_TRACE_MESSAGE("rtcp_interval usmebers is equal to 0", nullptr, nullptr);
2169 ulTimerVal = dDefTimerVal;
2170 return ulTimerVal;
2171 }
2172
2173 /*
2174 * Very first call at application start-up uses half the min
2175 * delay for quicker notification while still allowing some time
2176 * before reporting for randomization and to learn about other
2177 * sources so the report interval will converage to the correct
2178 * interval more quickly.
2179 */
2180 if (m_objTimerInfo.isInitial())
2181 {
2182 ulRtcp_min_time /= RTP_TWO;
2183 }
2184 /*
2185 * Dedicate a fraction of the RTCP bandwidth to senders unless
2186 * the number of senders is large enough that their share is
2187 * more than that fraction.
2188 */
2189
2190 RtpDt_Int32 uiNumMemComp = RTP_ZERO;
2191 uiNumMemComp = usMembers;
2192 RtpDt_UInt32 uiSenders = getSenderCount();
2193
2194 if (uiSenders <= usMembers * RTCP_SENDER_BW_FRACTION)
2195 {
2196 if (m_objTimerInfo.getWeSent() != RTP_ZERO)
2197 {
2198 ulRtcp_bw *= RTCP_SENDER_BW_FRACTION;
2199 uiNumMemComp = uiSenders;
2200 }
2201 else
2202 {
2203 ulRtcp_bw *= RTCP_RCVR_BW_FRACTION;
2204 uiNumMemComp -= uiSenders;
2205 }
2206 }
2207 // m_objTimerInfo.setRtcpBw(ulRtcp_bw);
2208
2209 /*
2210 * The effective number of sites times the average packet size is
2211 * the total number of octets sent when each site sends a report.
2212 * Dividing this by the effective bandwidth gives the time
2213 * interval over which those packets must be sent in order to
2214 * meet the bandwidth target, with a minimum enforced. In that
2215 * time interval we send one report so this time is also our
2216 * average time between reports.
2217 */
2218 ulTimerVal = m_objTimerInfo.getAvgRtcpSize() * uiNumMemComp / ulRtcp_bw;
2219 if (ulTimerVal < ulRtcp_min_time)
2220 {
2221 ulTimerVal = ulRtcp_min_time;
2222 }
2223
2224 /*
2225 * To avoid traffic bursts from unintended synchronization with
2226 * other sites, we then pick our actual next report interval as a
2227 * random number uniformly distributed between 0.5*t and 1.5*t.
2228 */
2229
2230 RtpDt_Double ulRRand = RTP_ZERO;
2231 ulRRand = RtpOsUtil::RRand();
2232 ulTimerVal = ulTimerVal * ((ulRRand) + 0.5);
2233 ulTimerVal = ulTimerVal / COMPENSATION;
2234 /*if(dDefTimerVal > ulTimerVal)
2235 {
2236 RTP_TRACE_MESSAGE("rtcp_interval dDefTimerVal > ulTimerVal [gen =%f], [def = %f]",
2237 ulTimerVal, dDefTimerVal);
2238 ulTimerVal = dDefTimerVal;
2239 }*/
2240 if (ulTimerVal < 0)
2241 {
2242 ulTimerVal = RTP_INIT_TRUE_T_MIN;
2243 RTP_TRACE_MESSAGE("Generated a negative timer value. using Default", nullptr, nullptr);
2244 }
2245 return ulTimerVal;
2246 } // rtcp_interval
2247
getSenderCount()2248 RtpDt_UInt32 RtpSession::getSenderCount()
2249 {
2250 RtpDt_UInt32 uiSenderCnt = RTP_ZERO;
2251 for (auto& pobjRcvrElm : *m_pobjRtpRcvrInfoList)
2252 {
2253 // get key material element from list.
2254 if (pobjRcvrElm != nullptr && pobjRcvrElm->isSender() == eRTP_TRUE &&
2255 pobjRcvrElm->getTotalRcvdRtpPkts() != 0)
2256 {
2257 uiSenderCnt = uiSenderCnt + RTP_ONE;
2258 }
2259 }
2260 return uiSenderCnt;
2261 } // getSenderCount
2262
calculateAndSetRTTD(RtpDt_UInt32 currentTime,RtpDt_UInt32 lsr,RtpDt_UInt32 dlsr)2263 RtpDt_Void RtpSession::calculateAndSetRTTD(
2264 RtpDt_UInt32 currentTime, RtpDt_UInt32 lsr, RtpDt_UInt32 dlsr)
2265 {
2266 if (lsr == 0 || dlsr == 0)
2267 {
2268 m_lastRTTDelay = 0;
2269 }
2270 else
2271 {
2272 m_lastRTTDelay = (currentTime - lsr - dlsr);
2273 m_lastRTTDelay =
2274 (m_lastRTTDelay >> 16) * 1000 + ((m_lastRTTDelay & 0x0000ffff) * 1000 / 65536);
2275 }
2276 RTP_TRACE_MESSAGE("calculateAndSetRTTD = %d", m_lastRTTDelay, 0);
2277 }
populateRtcpXrPacket(IN_OUT RtcpPacket * pobjRtcpPkt)2278 eRTP_STATUS_CODE RtpSession::populateRtcpXrPacket(IN_OUT RtcpPacket* pobjRtcpPkt)
2279 {
2280 // create RtcpXrPacket
2281 RtcpXrPacket* pobjRtcpXrPacket = new RtcpXrPacket();
2282 if (pobjRtcpXrPacket == nullptr)
2283 {
2284 RTP_TRACE_ERROR("[Memory Error] new returned NULL.", RTP_ZERO, RTP_ZERO);
2285 return RTP_FAILURE;
2286 }
2287 // set extended report block data
2288 RtpBuffer* pobjPayload = new RtpBuffer(m_stRtcpXr.nlength, m_stRtcpXr.m_pBlockBuffer);
2289 if (pobjPayload == nullptr)
2290 {
2291 RTP_TRACE_ERROR("[Memory Error] new returned NULL.", RTP_ZERO, RTP_ZERO);
2292 delete pobjRtcpXrPacket;
2293 return RTP_FAILURE;
2294 }
2295 pobjRtcpXrPacket->setReportBlk(pobjPayload);
2296
2297 // set the RTCP packet
2298 pobjRtcpPkt->setXrPacket(pobjRtcpXrPacket);
2299
2300 // get and populate the RTCP header
2301 RtcpHeader* pRtcpHdr = pobjRtcpXrPacket->getRtcpHdrInfo();
2302
2303 RtpDt_UInt16 usSubType = RTP_ZERO;
2304 pRtcpHdr->populateRtcpHeader((RtpDt_UChar)usSubType, RTCP_XR, m_uiSsrc);
2305
2306 return RTP_SUCCESS;
2307 }
2308
sendRtcpXrPacket(IN RtpDt_UChar * m_pBlockBuffer,IN RtpDt_UInt16 nblockLength)2309 eRTP_STATUS_CODE RtpSession::sendRtcpXrPacket(
2310 IN RtpDt_UChar* m_pBlockBuffer, IN RtpDt_UInt16 nblockLength)
2311 {
2312 // set timestamp
2313 m_stRtcpXr.m_pBlockBuffer = new RtpDt_UChar[nblockLength];
2314 if (m_stRtcpXr.m_pBlockBuffer == nullptr)
2315 {
2316 RTP_TRACE_ERROR("[Memory Error] new returned NULL.", RTP_ZERO, RTP_ZERO);
2317 return RTP_FAILURE;
2318 }
2319 memcpy(m_stRtcpXr.m_pBlockBuffer, m_pBlockBuffer, nblockLength);
2320
2321 m_stRtcpXr.nlength = nblockLength;
2322 m_bisXr = eRTP_TRUE;
2323
2324 return RTP_SUCCESS;
2325 }
2326
checkRtpPayloadType(IN RtpHeader * pobjRtpHeader,IN RtpPayloadInfo * m_pobjPayloadInfo)2327 eRtp_Bool RtpSession::checkRtpPayloadType(
2328 IN RtpHeader* pobjRtpHeader, IN RtpPayloadInfo* m_pobjPayloadInfo)
2329 {
2330 RtpDt_Int32 i = 0;
2331 for (; i < RTP_MAX_PAYLOAD_TYPE; i++)
2332 {
2333 if (pobjRtpHeader->getPayloadType() == m_pobjPayloadInfo->getPayloadType(i))
2334 break;
2335 RTP_TRACE_MESSAGE("checkRtpPayloadType rcvd payload = %d--- set payload =%d",
2336 pobjRtpHeader->getPayloadType(), m_pobjPayloadInfo->getPayloadType(i));
2337 }
2338
2339 if (i == RTP_MAX_PAYLOAD_TYPE)
2340 return eRTP_FALSE;
2341 else
2342 return eRTP_TRUE;
2343 }
2344
getRTTD()2345 RtpDt_UInt32 RtpSession::getRTTD()
2346 {
2347 return m_lastRTTDelay;
2348 }
2349