⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 rtphint.cpp

📁 6410BSP1
💻 CPP
📖 第 1 页 / 共 3 页
字号:
/* * The contents of this file are subject to the Mozilla Public * License Version 1.1 (the "License"); you may not use this file * except in compliance with the License. You may obtain a copy of * the License at http://www.mozilla.org/MPL/ *  * Software distributed under the License is distributed on an "AS * IS" basis, WITHOUT WARRANTY OF ANY KIND, either express or * implied. See the License for the specific language governing * rights and limitations under the License. *  * The Original Code is MPEG4IP. *  * The Initial Developer of the Original Code is Cisco Systems Inc. * Portions created by Cisco Systems Inc. are * Copyright (C) Cisco Systems Inc. 2001.  All Rights Reserved. *  * Contributor(s):  *        Dave Mackie        dmackie@cisco.com */#include "mp4common.h"/* rtp hint track operations */MP4RtpHintTrack::MP4RtpHintTrack(MP4File* pFile, MP4Atom* pTrakAtom)    : MP4Track(pFile, pTrakAtom){    m_pRefTrack = NULL;    m_pRtpMapProperty = NULL;    m_pPayloadNumberProperty = NULL;    m_pMaxPacketSizeProperty = NULL;    m_pSnroProperty = NULL;    m_pTsroProperty = NULL;    m_pReadHint = NULL;    m_pReadHintSample = NULL;    m_readHintSampleSize = 0;    m_pWriteHint = NULL;    m_writeHintId = MP4_INVALID_SAMPLE_ID;    m_writePacketId = 0;    m_pTrpy = NULL;    m_pNump = NULL;    m_pTpyl = NULL;    m_pMaxr = NULL;    m_pDmed = NULL;    m_pDimm = NULL;    m_pPmax = NULL;    m_pDmax = NULL;    m_pMaxPdu = NULL;    m_pAvgPdu = NULL;    m_pMaxBitRate = NULL;    m_pAvgBitRate = NULL;    m_thisSec = 0;    m_bytesThisSec = 0;    m_bytesThisHint = 0;    m_bytesThisPacket = 0;}MP4RtpHintTrack::~MP4RtpHintTrack(){    delete m_pReadHint;    delete m_pReadHintSample;    delete m_pWriteHint;}void MP4RtpHintTrack::InitRefTrack(){    if (m_pRefTrack == NULL) {        MP4Integer32Property* pRefTrackIdProperty = NULL;        m_pTrakAtom->FindProperty(            "trak.tref.hint.entries[0].trackId",            (MP4Property**)&pRefTrackIdProperty);        ASSERT(pRefTrackIdProperty);        m_pRefTrack = m_pFile->GetTrack(pRefTrackIdProperty->GetValue());    }}void MP4RtpHintTrack::InitRtpStart() {#ifdef SIMON_CHANGED    srand(GetTickCount());    ASSERT(m_pTrakAtom);    m_pTrakAtom->FindProperty(        "trak.udta.hnti.rtp .snro.offset",        (MP4Property**)&m_pSnroProperty);    if (m_pSnroProperty) {        m_rtpSequenceStart = m_pSnroProperty->GetValue();    } else {        m_rtpSequenceStart = rand();    }    m_pTrakAtom->FindProperty(        "trak.udta.hnti.rtp .tsro.offset",        (MP4Property**)&m_pTsroProperty);    if (m_pTsroProperty) {        m_rtpTimestampStart = m_pTsroProperty->GetValue();    } else {        m_rtpTimestampStart = rand();    }#else    struct timeval tv;    gettimeofday(&tv, NULL);    srandom((tv.tv_usec << 12) | (tv.tv_sec & 0xFFF));    ASSERT(m_pTrakAtom);    m_pTrakAtom->FindProperty(        "trak.udta.hnti.rtp .snro.offset",        (MP4Property**)&m_pSnroProperty);    if (m_pSnroProperty) {        m_rtpSequenceStart = m_pSnroProperty->GetValue();    } else {        m_rtpSequenceStart = random();    }    m_pTrakAtom->FindProperty(        "trak.udta.hnti.rtp .tsro.offset",        (MP4Property**)&m_pTsroProperty);    if (m_pTsroProperty) {        m_rtpTimestampStart = m_pTsroProperty->GetValue();    } else {        m_rtpTimestampStart = random();    }#endif}void MP4RtpHintTrack::ReadHint(    MP4SampleId hintSampleId,    u_int16_t* pNumPackets){    if (m_pRefTrack == NULL) {        InitRefTrack();        InitRtpStart();    }    // dispose of any old hint    delete m_pReadHint;    m_pReadHint = NULL;    delete m_pReadHintSample;    m_pReadHintSample = NULL;    m_readHintSampleSize = 0;    // read the desired hint sample into memory    ReadSample(        hintSampleId,         &m_pReadHintSample,         &m_readHintSampleSize,        &m_readHintTimestamp);    m_pFile->EnableMemoryBuffer(m_pReadHintSample, m_readHintSampleSize);    m_pReadHint = new MP4RtpHint(this);    m_pReadHint->Read(m_pFile);    m_pFile->DisableMemoryBuffer();    if (pNumPackets) {        *pNumPackets = GetHintNumberOfPackets();    }}u_int16_t MP4RtpHintTrack::GetHintNumberOfPackets(){    if (m_pReadHint == NULL) {        throw new MP4Error("no hint has been read",            "MP4GetRtpHintNumberOfPackets");    }    return m_pReadHint->GetNumberOfPackets();}bool MP4RtpHintTrack::GetPacketBFrame(u_int16_t packetIndex){    if (m_pReadHint == NULL) {        throw new MP4Error("no hint has been read",            "MP4GetRtpPacketBFrame");    }    MP4RtpPacket* pPacket =        m_pReadHint->GetPacket(packetIndex);    return pPacket->IsBFrame();}u_int16_t MP4RtpHintTrack::GetPacketTransmitOffset(u_int16_t packetIndex){    if (m_pReadHint == NULL) {        throw new MP4Error("no hint has been read",            "MP4GetRtpPacketTransmitOffset");    }    MP4RtpPacket* pPacket =        m_pReadHint->GetPacket(packetIndex);    return pPacket->GetTransmitOffset();}void MP4RtpHintTrack::ReadPacket(    u_int16_t packetIndex,    u_int8_t** ppBytes,     u_int32_t* pNumBytes,    u_int32_t ssrc,    bool addHeader,    bool addPayload){    if (m_pReadHint == NULL) {        throw new MP4Error("no hint has been read",            "MP4ReadRtpPacket");    }    if (!addHeader && !addPayload) {        throw new MP4Error("no data requested",            "MP4ReadRtpPacket");    }    MP4RtpPacket* pPacket =        m_pReadHint->GetPacket(packetIndex);    *pNumBytes = 0;    if (addHeader) {        *pNumBytes += 12;    }    if (addPayload) {        *pNumBytes += pPacket->GetDataSize();    }    // if needed, allocate the packet memory    bool buffer_malloc = false;    if (*ppBytes == NULL) {        *ppBytes = (u_int8_t*)MP4Malloc(*pNumBytes);        buffer_malloc = true;    }    try {        u_int8_t* pDest = *ppBytes;        if (addHeader) {            *pDest++ =                0x80 | (pPacket->GetPBit() << 5) | (pPacket->GetXBit() << 4);            *pDest++ =                (pPacket->GetMBit() << 7) | pPacket->GetPayload();            *((u_int16_t*)pDest) =                 htons(m_rtpSequenceStart + pPacket->GetSequenceNumber());            pDest += 2;             *((u_int32_t*)pDest) =                 htonl(m_rtpTimestampStart + (u_int32_t)m_readHintTimestamp);            pDest += 4;             *((u_int32_t*)pDest) =                 htonl(ssrc);            pDest += 4;        }        if (addPayload) {            pPacket->GetData(pDest);        }    }    catch (MP4Error* e) {        if (buffer_malloc) {            MP4Free(*ppBytes);            *ppBytes = NULL;        }        throw e;    }    VERBOSE_READ_HINT(m_pFile->GetVerbosity(),        printf("ReadPacket: %u ", packetIndex);        MP4HexDump(*ppBytes, *pNumBytes););}MP4Timestamp MP4RtpHintTrack::GetRtpTimestampStart(){    if (m_pRefTrack == NULL) {        InitRefTrack();        InitRtpStart();    }    return m_rtpTimestampStart;}void MP4RtpHintTrack::SetRtpTimestampStart(MP4Timestamp start){    if (!m_pTsroProperty) {        MP4Atom* pTsroAtom =            m_pFile->AddDescendantAtoms(m_pTrakAtom, "udta.hnti.rtp .tsro");        ASSERT(pTsroAtom);        pTsroAtom->FindProperty("offset",            (MP4Property**)&m_pTsroProperty);        ASSERT(m_pTsroProperty);    }    m_pTsroProperty->SetValue(start);    m_rtpTimestampStart = start;}void MP4RtpHintTrack::InitPayload(){    ASSERT(m_pTrakAtom);    if (m_pRtpMapProperty == NULL) {        m_pTrakAtom->FindProperty(            "trak.udta.hinf.payt.rtpMap",            (MP4Property**)&m_pRtpMapProperty);    }    if (m_pPayloadNumberProperty == NULL) {        m_pTrakAtom->FindProperty(            "trak.udta.hinf.payt.payloadNumber",            (MP4Property**)&m_pPayloadNumberProperty);    }    if (m_pMaxPacketSizeProperty == NULL) {        m_pTrakAtom->FindProperty(            "trak.mdia.minf.stbl.stsd.rtp .maxPacketSize",            (MP4Property**)&m_pMaxPacketSizeProperty);    }}void MP4RtpHintTrack::GetPayload(    char** ppPayloadName,    u_int8_t* pPayloadNumber,    u_int16_t* pMaxPayloadSize,    char **ppEncodingParams){  const char* pRtpMap;  char* pSlash;  u_int32_t length;    InitPayload();    if (ppPayloadName || ppEncodingParams) {      if (ppPayloadName)         *ppPayloadName = NULL;      if (ppEncodingParams)        *ppEncodingParams = NULL;        if (m_pRtpMapProperty) {            pRtpMap = m_pRtpMapProperty->GetValue();#if SIMON_CHANGED            pSlash = (char *) strchr(pRtpMap, '/');#else            pSlash = strchr(pRtpMap, '/');#endif            if (pSlash) {                length = pSlash - pRtpMap;            } else {                length = strlen(pRtpMap);            }            if (ppPayloadName) {              *ppPayloadName = (char*)MP4Calloc(length + 1);              strncpy(*ppPayloadName, pRtpMap, length);             }            if (pSlash && ppEncodingParams) {              pSlash++;              pSlash = strchr(pSlash, '/');              if (pSlash != NULL) {                pSlash++;                if (pSlash != '\0') {                  length = strlen(pRtpMap) - (pSlash - pRtpMap);                  *ppEncodingParams = (char *)MP4Calloc(length + 1);                  strncpy(*ppEncodingParams, pSlash, length);                }              }            }        }     }    if (pPayloadNumber) {        if (m_pPayloadNumberProperty) {            *pPayloadNumber = m_pPayloadNumberProperty->GetValue();        } else {            *pPayloadNumber = 0;        }    }    if (pMaxPayloadSize) {        if (m_pMaxPacketSizeProperty) {            *pMaxPayloadSize = m_pMaxPacketSizeProperty->GetValue();        } else {            *pMaxPayloadSize = 0;        }    }}void MP4RtpHintTrack::SetPayload(    const char* payloadName,    u_int8_t payloadNumber,    u_int16_t maxPayloadSize,     const char *encoding_parms,    bool include_rtp_map,    bool include_mpeg4_esid){    InitRefTrack();    InitPayload();    ASSERT(m_pRtpMapProperty);    ASSERT(m_pPayloadNumberProperty);    ASSERT(m_pMaxPacketSizeProperty);        size_t len = strlen(payloadName) + 16;    if (encoding_parms != NULL) {      size_t temp = strlen(encoding_parms);      if (temp == 0) {        encoding_parms = NULL;      } else {        len += temp;      }    }    char* rtpMapBuf = (char*)MP4Malloc(len);    sprintf(rtpMapBuf, "%s/%u%c%s",         payloadName,         GetTimeScale(),        encoding_parms != NULL ? '/' : '\0',        encoding_parms == NULL ? "" : encoding_parms);    m_pRtpMapProperty->SetValue(rtpMapBuf);        m_pPayloadNumberProperty->SetValue(payloadNumber);    if (maxPayloadSize == 0) {        maxPayloadSize = 1460;    }     m_pMaxPacketSizeProperty->SetValue(maxPayloadSize);    // set sdp media type    const char* sdpMediaType;    if (!strcmp(m_pRefTrack->GetType(), MP4_AUDIO_TRACK_TYPE)) {        sdpMediaType = "audio";    } else if (!strcmp(m_pRefTrack->GetType(), MP4_VIDEO_TRACK_TYPE)) {        sdpMediaType = "video";    } else if (!strcmp(m_pRefTrack->GetType(), MP4_CNTL_TRACK_TYPE)) {      sdpMediaType = "control";    } else {        sdpMediaType = "application";    }    char* sdpBuf = (char*)MP4Malloc(        strlen(sdpMediaType) + strlen(rtpMapBuf) + 256);    uint32_t buflen;    buflen = sprintf(sdpBuf,              "m=%s 0 RTP/AVP %u\015\012"             "a=control:trackID=%u\015\012",             sdpMediaType, payloadNumber,             m_trackId);    if (include_rtp_map) {      buflen += sprintf(sdpBuf + buflen,                 "a=rtpmap:%u %s\015\012",                payloadNumber, rtpMapBuf);

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -