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