Changeset 725


Ignore:
Timestamp:
01/17/12 12:42:54 (4 months ago)
Author:
shiretu
Message:

-- support for multi-NAL RTSP to RTMP

Files:
4 edited

Legend:

Unmodified
Added
Removed
  • branches/1.0/sources/thelib/src/protocols/rtmp/streaming/outnetrtmp4tsstream.cpp

    r668 r725  
    1 /*  
     1/* 
    22 *  Copyright (c) 2010, 
    33 *  Gavriloaie Eugen-Andrei (shiretu@gmail.com) 
     
    2222#include "streaming/streamstypes.h" 
    2323#include "streaming/nalutypes.h" 
     24#include "protocols/http/basehttpprotocol.h" 
    2425 
    2526#define SPSPPS_MAX_LENGTH 1024 
     
    153154} 
    154155 
     156//void checkData(IOBuffer &buffer); 
     157 
    155158bool OutNetRTMP4TSStream::FeedVideoData(uint8_t *pData, uint32_t dataLength, 
    156159                double absoluteTimestamp) { 
    157         switch (NALU_TYPE(pData[0])) { 
     160        uint8_t nalType = NALU_TYPE(pData[0]); 
     161        switch (nalType) { 
    158162                case NALU_TYPE_SPS: 
    159163                { 
     
    204208                        return true; 
    205209                } 
    206                 case NALU_TYPE_IDR: 
    207                 case NALU_TYPE_SLICE: 
    208                 { 
    209                         //10. Make room for the RTMP header 
    210                         _videoBuffer.ReadFromRepeat(0, 9); 
    211  
    212                         //11. Add the raw data 
    213                         _videoBuffer.ReadFromBuffer(pData, dataLength); 
    214  
    215                         uint8_t *pBuffer = GETIBPOINTER(_videoBuffer); 
    216  
    217                         //12. Setup the RTMP header 
    218                         pBuffer[0] = (NALU_TYPE(pData[0]) == NALU_TYPE_IDR) ? 0x17 : 0x27; 
    219                         pBuffer[1] = 0x01; 
    220                         pBuffer[2] = pBuffer[3] = pBuffer[4] = 0; 
    221                         EHTONLP(pBuffer + 5, dataLength); //----MARKED-LONG--- 
    222  
    223                         //13. Send it 
    224                         if (!BaseOutNetRTMPStream::FeedData( 
    225                                         pBuffer, //pData 
    226                                         dataLength + 9, //dataLength 
    227                                         0, //processedLength 
    228                                         dataLength + 9, //totalLength 
    229                                         absoluteTimestamp, //absoluteTimestamp 
    230                                         false //isAudio 
    231                                         )) { 
    232                                 FATAL("Unable to send video"); 
    233                                 return false; 
    234                         } 
    235  
    236                         //14. Cleanup 
    237                         _videoBuffer.IgnoreAll(); 
    238  
    239                         return true; 
    240                 } 
    241                 case NALU_TYPE_PD: 
    242                 case NALU_TYPE_SEI: 
    243                 case NALU_TYPE_FILL: 
    244                 { 
    245                         return true; 
    246                 } 
    247210                default: 
    248211                { 
    249                         WARN("Ignoring NAL: %s", STR(NALUToString(pData[0]))); 
     212                        uint8_t *pTemp = NULL; 
     213 
     214                        //put the 5 bytes header 
     215                        if (GETAVAILABLEBYTESCOUNT(_videoBuffer) == 0) { 
     216                                _videoBuffer.ReadFromRepeat(0, 5); 
     217                                pTemp = GETIBPOINTER(_videoBuffer); 
     218                                pTemp[1] = 0x01; 
     219                                pTemp[2] = pTemp[3] = pTemp[4] = 0; 
     220                        } 
     221 
     222                        if ((nalType == NALU_TYPE_IDR) 
     223                                        || (nalType == NALU_TYPE_SLICE) 
     224                                        || (nalType == NALU_TYPE_SEI) 
     225                                        ) { 
     226                                //put the length 
     227                                _videoBuffer.ReadFromRepeat(0, 4); 
     228                                pTemp = GETIBPOINTER(_videoBuffer) + GETAVAILABLEBYTESCOUNT(_videoBuffer) - 4; 
     229                                EHTONLP(pTemp, dataLength); 
     230 
     231                                //put the data 
     232                                _videoBuffer.ReadFromBuffer(pData, dataLength); 
     233 
     234                                //setup the frame type 
     235                                if (NALU_TYPE(pData[0]) == NALU_TYPE_IDR) { 
     236                                        //FINEST("HERE"); 
     237                                        GETIBPOINTER(_videoBuffer)[0] = 0x17; 
     238                                } else { 
     239                                        //FINEST("HERE"); 
     240                                        GETIBPOINTER(_videoBuffer)[0] = 0x27; 
     241                                } 
     242                        } 
     243 
     244                        //break if this is not a M bit on a RTSP 
     245                        if (_inboundStreamIsRTP) { 
     246                                if ((*(pData - 1)) == 0) { 
     247                                        //check the size of _videoBuffer and watch out for HUGE frames 
     248                                        if (GETAVAILABLEBYTESCOUNT(_videoBuffer) >= 4 * 1024 * 1024) { 
     249                                                WARN("Big video frame. Discard it"); 
     250                                                _videoBuffer.IgnoreAll(); 
     251                                        } 
     252                                        return true; 
     253                                } 
     254                        } 
     255 
     256                        if (GETAVAILABLEBYTESCOUNT(_videoBuffer) > 5) { 
     257                                //checkData(_videoBuffer); 
     258 
     259                                //send the data 
     260                                if (!BaseOutNetRTMPStream::FeedData( 
     261                                                GETIBPOINTER(_videoBuffer), //pData 
     262                                                GETAVAILABLEBYTESCOUNT(_videoBuffer), //dataLength 
     263                                                0, //processedLength 
     264                                                GETAVAILABLEBYTESCOUNT(_videoBuffer), //totalLength 
     265                                                absoluteTimestamp, //absoluteTimestamp 
     266                                                false //isAudio 
     267                                                )) { 
     268                                        FATAL("Unable to send video"); 
     269                                        return false; 
     270                                } 
     271                        } 
     272 
     273                        //cleanup 
     274                        _videoBuffer.IgnoreAll(); 
     275 
     276                        //done 
    250277                        return true; 
    251278                } 
    252279        } 
    253280} 
     281 
     282//void checkData(IOBuffer &buffer) { 
     283//      uint8_t *pBuffer = GETIBPOINTER(buffer); 
     284//      uint32_t length = GETAVAILABLEBYTESCOUNT(buffer); 
     285//      uint32_t cursor = 5; 
     286//      uint32_t computed = 5; 
     287//      string dbg; 
     288//      dbg += format("5 bytes: %02"PRIx8" %02"PRIx8" %02"PRIx8" %02"PRIx8" %02"PRIx8"\n", 
     289//                      pBuffer[0], pBuffer[1], pBuffer[2], pBuffer[3], pBuffer[4]); 
     290//      while (cursor < length) { 
     291//              uint32_t size = ENTOHLP(pBuffer + cursor); 
     292//              dbg += format("%s(%08"PRIx32")(%02"PRIx8"), ", 
     293//                              STR(NALUToString(pBuffer[cursor + 4])), 
     294//                              size, 
     295//                              pBuffer[cursor + 4 + size - 1]); 
     296//              cursor += 4 + size; 
     297//              computed += 4 + size; 
     298//      } 
     299//      dbg += format("\ncomputed: %"PRIu32"; available: %"PRIu32"; ok: %"PRIu8"\n", 
     300//                      computed, length, computed == length); 
     301//      fprintf(stdout, "%s\n", STR(dbg)); 
     302//} 
    254303#endif /* HAS_PROTOCOL_RTMP */ 
    255304 
  • branches/1.0/sources/thelib/src/protocols/rtp/streaming/innetrtpstream.cpp

    r711 r725  
    235235 
    236236        if (lastTs * 100.00 > absoluteTimestamp * 100.00) { 
    237                 WARN("Back time on %s. ATS: %.08f LTS: %.08f; D: %.8f; isAudio: %hhu", 
     237                WARN("Back time on %s. ATS: %.08f LTS: %.08f; D: %.8f; isAudio: %"PRIu8, 
    238238                                STR(GetName()), 
    239239                                absoluteTimestamp, 
     
    290290        } else { 
    291291                if ((uint16_t) (_videoSequence + 1) != (uint16_t) GET_RTP_SEQ(rtpHeader)) { 
    292                         WARN("Missing video packet. Wanted: %hu; got: %hu on stream: %s", 
     292                        WARN("Missing video packet. Wanted: %"PRIu16"; got: %"PRIu16" on stream: %s", 
    293293                                        (uint16_t) (_videoSequence + 1), 
    294294                                        (uint16_t) GET_RTP_SEQ(rtpHeader), 
     
    312312                _videoPacketsCount++; 
    313313                _videoBytesCount += dataLength; 
     314                *(pData - 1) = GET_RTP_M(rtpHeader); 
    314315                return FeedData(pData, dataLength, 0, dataLength, ts, false); 
    315316        } else if (naluType == NALU_TYPE_FUA) { 
     
    324325                        } 
    325326                        pData[1] = (pData[0]&0xe0) | (pData[1]&0x1f); 
     327                        _currentNalu.ReadFromByte(0); 
    326328                        _currentNalu.ReadFromBuffer(pData + 1, dataLength - 1); 
    327329                        return true; 
     
    333335                                _videoPacketsCount++; 
    334336                                _videoBytesCount += GETAVAILABLEBYTESCOUNT(_currentNalu); 
    335                                 if (!FeedData(GETIBPOINTER(_currentNalu), 
    336                                                 GETAVAILABLEBYTESCOUNT(_currentNalu), 0, 
    337                                                 GETAVAILABLEBYTESCOUNT(_currentNalu), 
     337                                GETIBPOINTER(_currentNalu)[0] = GET_RTP_M(rtpHeader); 
     338                                if (!FeedData(GETIBPOINTER(_currentNalu) + 1, 
     339                                                GETAVAILABLEBYTESCOUNT(_currentNalu) - 1, 0, 
     340                                                GETAVAILABLEBYTESCOUNT(_currentNalu) - 1, 
    338341                                                ts, 
    339342                                                false)) { 
     
    358361                        _videoPacketsCount++; 
    359362                        _videoBytesCount += length; 
     363                        if (index + length >= dataLength) { 
     364                                *(pData + index - 1) = 1; 
     365                        } else { 
     366                                *(pData + index - 1) = 0; 
     367                        } 
    360368                        if (!FeedData(pData + index, 
    361369                                        length, 0, 
     
    387395        } else { 
    388396                if ((uint16_t) (_audioSequence + 1) != (uint16_t) GET_RTP_SEQ(rtpHeader)) { 
    389                         WARN("Missing audio packet. Wanted: %hu; got: %hu on stream: %s", 
     397                        WARN("Missing audio packet. Wanted: %"PRIu16"; got: %"PRIu16" on stream: %s", 
    390398                                        (uint16_t) (_audioSequence + 1), 
    391399                                        (uint16_t) GET_RTP_SEQ(rtpHeader), 
     
    402410        uint16_t chunksCount = ENTOHSP(pData); 
    403411        if ((chunksCount % 16) != 0) { 
    404                 FATAL("Invalid AU headers length: %hx", chunksCount); 
     412                FATAL("Invalid AU headers length: %"PRIx16, chunksCount); 
    405413                return false; 
    406414        } 
     
    420428                ts = (double) (rtpTs + i * 1024) / (double) _capabilities.aac._sampleRate * 1000.00; 
    421429                if ((cursor + chunkSize) > dataLength) { 
    422                         FATAL("Unable to feed data: cursor: %u; chunkSize: %hu; dataLength: %u; chunksCount: %hu", 
     430                        FATAL("Unable to feed data: cursor: %"PRIu32"; chunkSize: %"PRIu16"; dataLength: %"PRIu32"; chunksCount: %"PRIu16, 
    423431                                        cursor, chunkSize, dataLength, chunksCount); 
    424432                        return false; 
  • trunk/sources/thelib/src/protocols/rtmp/streaming/outnetrtmp4tsstream.cpp

    r721 r725  
    1 /*  
     1/* 
    22 *  Copyright (c) 2010, 
    33 *  Gavriloaie Eugen-Andrei (shiretu@gmail.com) 
     
    2222#include "streaming/streamstypes.h" 
    2323#include "streaming/nalutypes.h" 
     24#include "protocols/http/basehttpprotocol.h" 
    2425 
    2526#define SPSPPS_MAX_LENGTH 1024 
     
    153154} 
    154155 
     156//void checkData(IOBuffer &buffer); 
     157 
    155158bool OutNetRTMP4TSStream::FeedVideoData(uint8_t *pData, uint32_t dataLength, 
    156159                double absoluteTimestamp) { 
    157         switch (NALU_TYPE(pData[0])) { 
     160        uint8_t nalType = NALU_TYPE(pData[0]); 
     161        switch (nalType) { 
    158162                case NALU_TYPE_SPS: 
    159163                { 
     
    204208                        return true; 
    205209                } 
    206                 case NALU_TYPE_IDR: 
    207                 case NALU_TYPE_SLICE: 
    208                 { 
    209                         //10. Make room for the RTMP header 
    210                         _videoBuffer.ReadFromRepeat(0, 9); 
    211  
    212                         //11. Add the raw data 
    213                         _videoBuffer.ReadFromBuffer(pData, dataLength); 
    214  
    215                         uint8_t *pBuffer = GETIBPOINTER(_videoBuffer); 
    216  
    217                         //12. Setup the RTMP header 
    218                         pBuffer[0] = (NALU_TYPE(pData[0]) == NALU_TYPE_IDR) ? 0x17 : 0x27; 
    219                         pBuffer[1] = 0x01; 
    220                         pBuffer[2] = pBuffer[3] = pBuffer[4] = 0; 
    221                         EHTONLP(pBuffer + 5, dataLength); //----MARKED-LONG--- 
    222  
    223                         //13. Send it 
    224                         if (!BaseOutNetRTMPStream::FeedData( 
    225                                         pBuffer, //pData 
    226                                         dataLength + 9, //dataLength 
    227                                         0, //processedLength 
    228                                         dataLength + 9, //totalLength 
    229                                         absoluteTimestamp, //absoluteTimestamp 
    230                                         false //isAudio 
    231                                         )) { 
    232                                 FATAL("Unable to send video"); 
    233                                 return false; 
    234                         } 
    235  
    236                         //14. Cleanup 
    237                         _videoBuffer.IgnoreAll(); 
    238  
    239                         return true; 
    240                 } 
    241                 case NALU_TYPE_PD: 
    242                 case NALU_TYPE_SEI: 
    243                 case NALU_TYPE_FILL: 
    244                 { 
    245                         return true; 
    246                 } 
    247210                default: 
    248211                { 
    249                         WARN("Ignoring NAL: %s", STR(NALUToString(pData[0]))); 
     212                        uint8_t *pTemp = NULL; 
     213 
     214                        //put the 5 bytes header 
     215                        if (GETAVAILABLEBYTESCOUNT(_videoBuffer) == 0) { 
     216                                _videoBuffer.ReadFromRepeat(0, 5); 
     217                                pTemp = GETIBPOINTER(_videoBuffer); 
     218                                pTemp[1] = 0x01; 
     219                                pTemp[2] = pTemp[3] = pTemp[4] = 0; 
     220                        } 
     221 
     222                        if ((nalType == NALU_TYPE_IDR) 
     223                                        || (nalType == NALU_TYPE_SLICE) 
     224                                        || (nalType == NALU_TYPE_SEI) 
     225                                        ) { 
     226                                //put the length 
     227                                _videoBuffer.ReadFromRepeat(0, 4); 
     228                                pTemp = GETIBPOINTER(_videoBuffer) + GETAVAILABLEBYTESCOUNT(_videoBuffer) - 4; 
     229                                EHTONLP(pTemp, dataLength); 
     230 
     231                                //put the data 
     232                                _videoBuffer.ReadFromBuffer(pData, dataLength); 
     233 
     234                                //setup the frame type 
     235                                if (NALU_TYPE(pData[0]) == NALU_TYPE_IDR) { 
     236                                        //FINEST("HERE"); 
     237                                        GETIBPOINTER(_videoBuffer)[0] = 0x17; 
     238                                } else { 
     239                                        //FINEST("HERE"); 
     240                                        GETIBPOINTER(_videoBuffer)[0] = 0x27; 
     241                                } 
     242                        } 
     243 
     244                        //break if this is not a M bit on a RTSP 
     245                        if (_inboundStreamIsRTP) { 
     246                                if ((*(pData - 1)) == 0) { 
     247                                        //check the size of _videoBuffer and watch out for HUGE frames 
     248                                        if (GETAVAILABLEBYTESCOUNT(_videoBuffer) >= 4 * 1024 * 1024) { 
     249                                                WARN("Big video frame. Discard it"); 
     250                                                _videoBuffer.IgnoreAll(); 
     251                                        } 
     252                                        return true; 
     253                                } 
     254                        } 
     255 
     256                        if (GETAVAILABLEBYTESCOUNT(_videoBuffer) > 5) { 
     257                                //checkData(_videoBuffer); 
     258 
     259                                //send the data 
     260                                if (!BaseOutNetRTMPStream::FeedData( 
     261                                                GETIBPOINTER(_videoBuffer), //pData 
     262                                                GETAVAILABLEBYTESCOUNT(_videoBuffer), //dataLength 
     263                                                0, //processedLength 
     264                                                GETAVAILABLEBYTESCOUNT(_videoBuffer), //totalLength 
     265                                                absoluteTimestamp, //absoluteTimestamp 
     266                                                false //isAudio 
     267                                                )) { 
     268                                        FATAL("Unable to send video"); 
     269                                        return false; 
     270                                } 
     271                        } 
     272 
     273                        //cleanup 
     274                        _videoBuffer.IgnoreAll(); 
     275 
     276                        //done 
    250277                        return true; 
    251278                } 
    252279        } 
    253280} 
     281 
     282//void checkData(IOBuffer &buffer) { 
     283//      uint8_t *pBuffer = GETIBPOINTER(buffer); 
     284//      uint32_t length = GETAVAILABLEBYTESCOUNT(buffer); 
     285//      uint32_t cursor = 5; 
     286//      uint32_t computed = 5; 
     287//      string dbg; 
     288//      dbg += format("5 bytes: %02"PRIx8" %02"PRIx8" %02"PRIx8" %02"PRIx8" %02"PRIx8"\n", 
     289//                      pBuffer[0], pBuffer[1], pBuffer[2], pBuffer[3], pBuffer[4]); 
     290//      while (cursor < length) { 
     291//              uint32_t size = ENTOHLP(pBuffer + cursor); 
     292//              dbg += format("%s(%08"PRIx32")(%02"PRIx8"), ", 
     293//                              STR(NALUToString(pBuffer[cursor + 4])), 
     294//                              size, 
     295//                              pBuffer[cursor + 4 + size - 1]); 
     296//              cursor += 4 + size; 
     297//              computed += 4 + size; 
     298//      } 
     299//      dbg += format("\ncomputed: %"PRIu32"; available: %"PRIu32"; ok: %"PRIu8"\n", 
     300//                      computed, length, computed == length); 
     301//      fprintf(stdout, "%s\n", STR(dbg)); 
     302//} 
    254303#endif /* HAS_PROTOCOL_RTMP */ 
    255304 
  • trunk/sources/thelib/src/protocols/rtp/streaming/innetrtpstream.cpp

    r711 r725  
    235235 
    236236        if (lastTs * 100.00 > absoluteTimestamp * 100.00) { 
    237                 WARN("Back time on %s. ATS: %.08f LTS: %.08f; D: %.8f; isAudio: %hhu", 
     237                WARN("Back time on %s. ATS: %.08f LTS: %.08f; D: %.8f; isAudio: %"PRIu8, 
    238238                                STR(GetName()), 
    239239                                absoluteTimestamp, 
     
    290290        } else { 
    291291                if ((uint16_t) (_videoSequence + 1) != (uint16_t) GET_RTP_SEQ(rtpHeader)) { 
    292                         WARN("Missing video packet. Wanted: %hu; got: %hu on stream: %s", 
     292                        WARN("Missing video packet. Wanted: %"PRIu16"; got: %"PRIu16" on stream: %s", 
    293293                                        (uint16_t) (_videoSequence + 1), 
    294294                                        (uint16_t) GET_RTP_SEQ(rtpHeader), 
     
    312312                _videoPacketsCount++; 
    313313                _videoBytesCount += dataLength; 
     314                *(pData - 1) = GET_RTP_M(rtpHeader); 
    314315                return FeedData(pData, dataLength, 0, dataLength, ts, false); 
    315316        } else if (naluType == NALU_TYPE_FUA) { 
     
    324325                        } 
    325326                        pData[1] = (pData[0]&0xe0) | (pData[1]&0x1f); 
     327                        _currentNalu.ReadFromByte(0); 
    326328                        _currentNalu.ReadFromBuffer(pData + 1, dataLength - 1); 
    327329                        return true; 
     
    333335                                _videoPacketsCount++; 
    334336                                _videoBytesCount += GETAVAILABLEBYTESCOUNT(_currentNalu); 
    335                                 if (!FeedData(GETIBPOINTER(_currentNalu), 
    336                                                 GETAVAILABLEBYTESCOUNT(_currentNalu), 0, 
    337                                                 GETAVAILABLEBYTESCOUNT(_currentNalu), 
     337                                GETIBPOINTER(_currentNalu)[0] = GET_RTP_M(rtpHeader); 
     338                                if (!FeedData(GETIBPOINTER(_currentNalu) + 1, 
     339                                                GETAVAILABLEBYTESCOUNT(_currentNalu) - 1, 0, 
     340                                                GETAVAILABLEBYTESCOUNT(_currentNalu) - 1, 
    338341                                                ts, 
    339342                                                false)) { 
     
    358361                        _videoPacketsCount++; 
    359362                        _videoBytesCount += length; 
     363                        if (index + length >= dataLength) { 
     364                                *(pData + index - 1) = 1; 
     365                        } else { 
     366                                *(pData + index - 1) = 0; 
     367                        } 
    360368                        if (!FeedData(pData + index, 
    361369                                        length, 0, 
     
    387395        } else { 
    388396                if ((uint16_t) (_audioSequence + 1) != (uint16_t) GET_RTP_SEQ(rtpHeader)) { 
    389                         WARN("Missing audio packet. Wanted: %hu; got: %hu on stream: %s", 
     397                        WARN("Missing audio packet. Wanted: %"PRIu16"; got: %"PRIu16" on stream: %s", 
    390398                                        (uint16_t) (_audioSequence + 1), 
    391399                                        (uint16_t) GET_RTP_SEQ(rtpHeader), 
     
    402410        uint16_t chunksCount = ENTOHSP(pData); 
    403411        if ((chunksCount % 16) != 0) { 
    404                 FATAL("Invalid AU headers length: %hx", chunksCount); 
     412                FATAL("Invalid AU headers length: %"PRIx16, chunksCount); 
    405413                return false; 
    406414        } 
     
    420428                ts = (double) (rtpTs + i * 1024) / (double) _capabilities.aac._sampleRate * 1000.00; 
    421429                if ((cursor + chunkSize) > dataLength) { 
    422                         FATAL("Unable to feed data: cursor: %u; chunkSize: %hu; dataLength: %u; chunksCount: %hu", 
     430                        FATAL("Unable to feed data: cursor: %"PRIu32"; chunkSize: %"PRIu16"; dataLength: %"PRIu32"; chunksCount: %"PRIu16, 
    423431                                        cursor, chunkSize, dataLength, chunksCount); 
    424432                        return false; 
Note: See TracChangeset for help on using the changeset viewer.