📄 rtpwrap.h
字号:
/* ***** BEGIN LICENSE BLOCK *****
* Version: RCSL 1.0/RPSL 1.0
*
* Portions Copyright (c) 1995-2002 RealNetworks, Inc. All Rights Reserved.
*
* The contents of this file, and the files included with this file, are
* subject to the current version of the RealNetworks Public Source License
* Version 1.0 (the "RPSL") available at
* http://www.helixcommunity.org/content/rpsl unless you have licensed
* the file under the RealNetworks Community Source License Version 1.0
* (the "RCSL") available at http://www.helixcommunity.org/content/rcsl,
* in which case the RCSL will apply. You may also obtain the license terms
* directly from RealNetworks. You may not use this file except in
* compliance with the RPSL or, if you have a valid RCSL with RealNetworks
* applicable to this file, the RCSL. Please see the applicable RPSL or
* RCSL for the rights, obligations and limitations governing use of the
* contents of the file.
*
* This file is part of the Helix DNA Technology. RealNetworks is the
* developer of the Original Code and owns the copyrights in the portions
* it created.
*
* This file, and the files included with this file, is distributed and made
* available on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
* EXPRESS OR IMPLIED, AND REALNETWORKS HEREBY DISCLAIMS ALL SUCH WARRANTIES,
* INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY, FITNESS
* FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT.
*
* Technology Compatibility Kit Test Suite(s) Location:
* http://www.helixcommunity.org/content/tck
*
* Contributor(s):
*
* ***** END LICENSE BLOCK ***** */
#ifndef _RTPWRAP_H_
#define _RTPWRAP_H_
#include "rtppkt.h" // Base class definitions from PMC
#include "hxmap.h"
#include "hxslist.h"
#include "hxassert.h"
#include "hxinline.h"
class RTPPacket : public RTPPacketBase
{
public:
RTPPacket()
{
/*
* XXXST I should be doing this in the initialization parameters
* except the PMC generated class doesn't have a constructor so
* I cannot set them in this constructor.
*/
version_flag = 0;
padding_flag = 0;
extension_flag = 0;
csrc_len = 0;
marker_flag = 0;
payload = 0;
seq_no = 0;
timestamp = 0;
ssrc = 0;
csrc = 0;
op_code = 0;
op_code_data_length = 0;
asm_flags = 0;
asm_rule = 0;
op_code_data = 0;
data.data = 0;
data.len = 0;
}
~RTPPacket()
{
if (csrc)
delete [] csrc;
if (op_code_data)
delete [] op_code_data;
}
void SetCSrc(INT32* pchNewData, UINT32 ulLen)
{
if (csrc)
delete [] csrc;
csrc = new INT32[ulLen];
memcpy(csrc, pchNewData, ulLen * sizeof(INT32)); /* Flawfinder: ignore */
}
void SetOpCodeData(INT32* pchNewData, UINT32 ulLen)
{
if (op_code_data)
delete [] op_code_data;
op_code_data = new INT32[ulLen];
memcpy(op_code_data, pchNewData, ulLen * sizeof(INT32)); /* Flawfinder: ignore */
}
};
class RTCPPacket : public RTCPPacketBase
{
public:
RTCPPacket()
{
version_flag = 0;
padding_flag = 0;
count = 0;
packet_type = 0;
length = 0;
sr_ssrc = 0;
ntp_sec = 0;
ntp_frac = 0;
rtp_ts = 0;
psent = 0;
osent = 0;
sr_data = 0;
rr_ssrc = 0;
rr_data = 0;
sdes_data = 0;
bye_src = 0;
// used for APP
// app_name = 0; // not a pointer...
app_data = 0;
m_pAPPItems = 0;
}
~RTCPPacket()
{
CleanBuffers();
}
UINT8* pack(UINT8* data, UINT32 &len);
UINT8* unpack(UINT8* data, UINT32 len);
void SetSenderReport (ReceptionReport* pNewData, UINT32 ulLen)
{
if (sr_data)
delete [] sr_data;
sr_data = new ReceptionReport[ulLen];
memcpy(sr_data, pNewData, ulLen * sizeof(ReceptionReport)); /* Flawfinder: ignore */
}
void SetReceiverReport(ReceptionReport* pNewData, UINT32 ulLen)
{
if (rr_data)
delete [] rr_data;
rr_data = new ReceptionReport[ulLen];
memcpy(rr_data, pNewData, ulLen * sizeof(ReceptionReport)); /* Flawfinder: ignore */
}
void SetSDES (UINT8* pchNewData, UINT32 ulLen)
{
if (sdes_data)
delete [] sdes_data;
sdes_data = new UINT8[ulLen];
memcpy(sdes_data, pchNewData, ulLen * sizeof(UINT8)); /* Flawfinder: ignore */
}
void SetByeSrc (UINT32* pulNewData, UINT32 ulLen)
{
if (bye_src)
delete [] bye_src;
bye_src = new UINT32[ulLen];
memcpy(bye_src, pulNewData, ulLen * sizeof(UINT32)); /* Flawfinder: ignore */
}
SDESItem* AddSDESItem (UINT32 ulSSrc, SDESItem item)
{
/*
* Attempt to lookup this SSRC id from our map
*/
CHXSimpleList* pList = NULL;
SDESItem* pItem = new SDESItem;
if (!m_mapSDESSources.Lookup(ulSSrc, (void*&)pList))
{
/* Not in map */
pList = new CHXSimpleList;
m_mapSDESSources[ulSSrc] = pList;
}
pItem->sdes_type = item.sdes_type;
pItem->length = item.length;
pItem->data = new UINT8[pItem->length];
memcpy(pItem->data, item.data, item.length * sizeof(UINT8)); /* Flawfinder: ignore */
pList->AddTail(pItem);
return pItem;
}
void SetAPPItem (APPItem* item, UINT32 ulCount)
{
HX_VECTOR_DELETE(m_pAPPItems);
m_pAPPItems = new APPItem[ulCount];
memcpy(m_pAPPItems, item, ulCount * sizeof (APPItem)); /* Flawfinder: ignore */
}
// keys off of source id and contains a pointer to a list
// of SDESItems.
CHXMapLongToObj m_mapSDESSources;
// array of APPItem
APPItem* m_pAPPItems;
void CleanBuffers();
};
#if defined (_DEFINE_INLINE)
HX_INLINE void
RTCPPacket::CleanBuffers()
{
if (sr_data)
delete [] sr_data;
if (rr_data)
delete [] rr_data;
if (sdes_data)
delete [] sdes_data;
if (bye_src)
delete [] bye_src;
if (app_data)
delete [] app_data;
CHXMapLongToObj::Iterator i;
for (i = m_mapSDESSources.Begin(); i != m_mapSDESSources.End(); ++i)
{
CHXSimpleList* pItems = (CHXSimpleList*) *i;
while (!pItems->IsEmpty())
{
SDESItem* pItem = (SDESItem*) pItems->RemoveHead();
delete pItem;
}
delete pItems;
}
if (m_pAPPItems)
{
delete [] m_pAPPItems;
}
}
HX_INLINE UINT8*
RTCPPacket::unpack(UINT8* data, UINT32 len)
{
CleanBuffers();
UINT8* pBaseOff = RTCPPacketBase::unpack(data, len);
// immediate error return
if (!pBaseOff) return 0;
/*
* check to see if this is an SDES message and if it is then
* parse out the SDES source chunks from the sdes_data blob
*/
if (packet_type == RTCP_SDES)
{
HX_ASSERT(sdes_data != NULL);
/*
* the PMC generates code that points the byte pointer into
* the containing buffer rather than copying it out we may
* as well do it all the way here.
*/
UINT8* pOff = new UINT8[length * 4];
memcpy(pOff, sdes_data, length * 4 * sizeof(UINT8)); /* Flawfinder: ignore */
sdes_data = pOff;
for (INT32 iSrc = 0; iSrc < count; iSrc++)
{
INT32 lSrc = 0;
CHXSimpleList* pItems = new CHXSimpleList;
lSrc = GetDwordFromBufAndInc(pOff);
while (pOff && pOff < sdes_data + (length * 4))
{
SDESItem* pItem = new SDESItem;
UINT32 ulItemLen = (length * 4) - (pOff - sdes_data);
pOff = pItem->unpack(pOff, ulItemLen);
if (pItem->sdes_type == 0)
{
/*
* We are done with this list of items within the source
* chunk (null terminated)
*/
delete pItem;
break;
}
pItems->AddTail(pItem);
}
m_mapSDESSources[lSrc] = pItems;
}
}
/*
* Gatta do the same for APP msg!
*/
else if (packet_type == RTCP_APP)
{
HX_ASSERT(app_data != NULL);
/*
* if this is RNWK app, unpack, otherwise, leave it along...
*/
// has to be NULL terminated...
char pc[5] = {0}; /* Flawfinder: ignore */
memcpy(pc, app_name, 4); /* Flawfinder: ignore */
// whether this is ours or not, we have to make own buffer
UINT8* pOff = new UINT8[(length - 2) * 4];
memcpy(pOff, app_data, (length - 2) * 4); /* Flawfinder: ignore */
app_data = pOff;
if ((0 == strncmp((const char*)pc, "RNWK", 4)) ||
(0 == strncmp((const char*)pc, "HELX", 4)))
{
// it's ours
m_pAPPItems = new APPItem[count];
for (UINT32 i = 0; i < count; i++)
{
HX_ASSERT(pOff);
// length is anything other than 0...
pOff = m_pAPPItems[i].unpack(pOff, 1);
}
}
}
return pBaseOff;
}
HX_INLINE UINT8*
RTCPPacket::pack(UINT8* data, UINT32& len)
{
if (packet_type == RTCP_SDES)
{
/*
* revert the m_mapSDESSources back to blob form
*/
if (sdes_data != NULL)
{
delete [] sdes_data;
}
/*
* Order may be important here, using a map will not
* guarentee order
*/
UINT8* pBuf = new UINT8[0x1000];
UINT8* pOff = pBuf;
CHXMapLongToObj::Iterator iSrc = m_mapSDESSources.Begin();
for (; iSrc != m_mapSDESSources.End(); ++iSrc)
{
INT32 lSrc = iSrc.get_key();
CHXSimpleList* pItems = (CHXSimpleList*) *iSrc;
CHXSimpleList::Iterator iItem = pItems->Begin();
*pOff++ = (UINT8) (lSrc>>24); *pOff++ = (UINT8) (lSrc>>16);
*pOff++ = (UINT8) (lSrc>>8); *pOff++ = (UINT8) (lSrc);
for (; iItem != pItems->End(); ++iItem)
{
UINT32 ulItemLen = pBuf - pOff;
SDESItem* pSDESItem = (SDESItem*)*iItem;
pOff = pSDESItem->pack(pOff, ulItemLen);
if (pSDESItem->data)
{
delete [] pSDESItem->data;
}
}
/*
* Terminate the list with an item of type 0 (first byte)
*/
*pOff++ = 0;
/*
* Pad until 4 bytes boundary
*/
int lLength = HX_SAFEINT(pOff - pBuf);
if (lLength % 4)
{
memset(pOff, 0, 4 - (lLength % 4));
pOff += 4 - (lLength % 4);
}
HX_ASSERT((HX_SAFEINT(pOff - pBuf) % 4) == 0);
}
sdes_data = new UINT8[pOff - pBuf];
memcpy(sdes_data, pBuf, (pOff - pBuf) * sizeof(UINT8)); /* Flawfinder: ignore */
length = (pOff - pBuf) / 4;
delete [] pBuf;
}
else if (packet_type == RTCP_APP)
{
/*
* revert the m_mapSDESSources back to blob form
*/
if (app_data != NULL)
{
delete [] app_data;
}
UINT8* pBuf = new UINT8[0x1000];
UINT8* pOff = pBuf;
UINT32 ulDammy = 0;
for (UINT32 i = 0; i < count; i++)
{
pOff = m_pAPPItems[i].pack(pOff, ulDammy);
}
app_data = new UINT8[pOff - pBuf];
memcpy(app_data, pBuf, (pOff - pBuf) * sizeof(UINT8)); /* Flawfinder: ignore */
delete [] pBuf;
}
return RTCPPacketBase::pack(data, len);
}
#endif //_DEFINE_INLINE
#endif /* _RTPWRAP_H_ */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -