diff --git a/CMakeLists.txt b/CMakeLists.txt index 6a6fe11b..10148135 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -117,6 +117,7 @@ if(ENABLE_HLS) add_library(mpeg STATIC ${src_mpeg}) list(APPEND LINK_LIB_LIST mpeg) + list(APPEND CXX_API_TARGETS mpeg) if(WIN32) set_target_properties(mpeg PROPERTIES COMPILE_FLAGS ${VS_FALGS} ) @@ -140,6 +141,7 @@ if(ENABLE_MP4) add_library(mov STATIC ${src_mov}) add_library(flv STATIC ${src_flv}) list(APPEND LINK_LIB_LIST mov flv) + list(APPEND CXX_API_TARGETS mov flv) if(WIN32) set_target_properties(mov flv PROPERTIES COMPILE_FLAGS ${VS_FALGS} ) @@ -157,6 +159,7 @@ if(ENABLE_RTPPROXY AND ENABLE_HLS) add_library(rtp STATIC ${src_rtp}) add_definitions(-DENABLE_RTPPROXY) list(APPEND LINK_LIB_LIST rtp) + list(APPEND CXX_API_TARGETS rtp) endif() #收集源代码 @@ -178,6 +181,7 @@ endif () #添加库 add_library(zltoolkit STATIC ${ToolKit_src_list}) add_library(zlmediakit STATIC ${MediaKit_src_list}) +list(APPEND CXX_API_TARGETS zltoolkit zlmediakit) #安装目录 if (WIN32) @@ -192,7 +196,7 @@ if(ENABLE_CXX_API) # 保留目录结构 install(DIRECTORY ${ToolKit_Root}/ DESTINATION ${INSTALL_PATH_INCLUDE}/ZLToolKit REGEX "(.*[.](md|cpp)|win32)$" EXCLUDE) install(DIRECTORY ${MediaKit_Root}/ DESTINATION ${INSTALL_PATH_INCLUDE}/ZLMediaKit REGEX ".*[.](md|cpp)$" EXCLUDE) - install(TARGETS zltoolkit zlmediakit DESTINATION ${INSTALL_PATH_LIB}) + install(TARGETS ${CXX_API_TARGETS} DESTINATION ${INSTALL_PATH_LIB}) endif() if (WIN32) diff --git a/src/Rtmp/RtmpDemuxer.cpp b/src/Rtmp/RtmpDemuxer.cpp index ad4b84b7..6e38b0d7 100644 --- a/src/Rtmp/RtmpDemuxer.cpp +++ b/src/Rtmp/RtmpDemuxer.cpp @@ -106,6 +106,7 @@ void RtmpDemuxer::makeVideoTrack(const AMFValue &videoCodec) { //设置rtmp解码器代理,生成的frame写入该Track _videoRtmpDecoder->addDelegate(_videoTrack); onAddTrack(_videoTrack); + _tryedGetVideoTrack = true; } else { //找不到相应的rtmp解码器,该track无效 _videoTrack.reset(); @@ -123,6 +124,7 @@ void RtmpDemuxer::makeAudioTrack(const AMFValue &audioCodec,int sample_rate, int //设置rtmp解码器代理,生成的frame写入该Track _audioRtmpDecoder->addDelegate(_audioTrack); onAddTrack(_audioTrack); + _tryedGetAudioTrack = true; } else { //找不到相应的rtmp解码器,该track无效 _audioTrack.reset(); diff --git a/src/Rtp/RtpProcess.cpp b/src/Rtp/RtpProcess.cpp index 0693ddae..87812741 100644 --- a/src/Rtp/RtpProcess.cpp +++ b/src/Rtp/RtpProcess.cpp @@ -21,12 +21,6 @@ static string printAddress(const struct sockaddr *addr){ } RtpProcess::RtpProcess(const string &stream_id) { - _track = std::make_shared(); - _track->_interleaved = 0; - _track->_samplerate = 90000; - _track->_type = TrackVideo; - _track->_ssrc = 0; - _media_info._schema = RTP_APP_NAME; _media_info._vhost = DEFAULT_VHOST; _media_info._app = RTP_APP_NAME; @@ -104,7 +98,7 @@ bool RtpProcess::inputRtp(const Socket::Ptr &sock, const char *data, int data_le } _total_bytes += data_len; - bool ret = handleOneRtp(0,_track,(unsigned char *)data,data_len); + bool ret = handleOneRtp(0, TrackVideo, 90000, (unsigned char *) data, data_len); if(dts_out){ *dts_out = _dts; } diff --git a/src/Rtp/RtpProcess.h b/src/Rtp/RtpProcess.h index 81dc7f2f..d2d9c5ee 100644 --- a/src/Rtp/RtpProcess.h +++ b/src/Rtp/RtpProcess.h @@ -78,7 +78,6 @@ private: std::shared_ptr _save_file_rtp; std::shared_ptr _save_file_ps; std::shared_ptr _save_file_video; - SdpTrack::Ptr _track; struct sockaddr *_addr = nullptr; uint16_t _sequence = 0; MultiMediaSourceMuxer::Ptr _muxer; diff --git a/src/Rtsp/RtpReceiver.cpp b/src/Rtsp/RtpReceiver.cpp index e7703de7..0b10063c 100644 --- a/src/Rtsp/RtpReceiver.cpp +++ b/src/Rtsp/RtpReceiver.cpp @@ -27,7 +27,7 @@ namespace mediakit { RtpReceiver::RtpReceiver() {} RtpReceiver::~RtpReceiver() {} -bool RtpReceiver::handleOneRtp(int track_index,SdpTrack::Ptr &track, unsigned char *rtp_raw_ptr, unsigned int rtp_raw_len) { +bool RtpReceiver::handleOneRtp(int track_index, TrackType type, int samplerate, unsigned char *rtp_raw_ptr, unsigned int rtp_raw_len) { if(rtp_raw_len < 12){ WarnL << "rtp包太小:" << rtp_raw_len; return false; @@ -46,8 +46,8 @@ bool RtpReceiver::handleOneRtp(int track_index,SdpTrack::Ptr &track, unsigned ch auto rtp_ptr = _rtp_pool.obtain(); auto &rtp = *rtp_ptr; - rtp.type = track->_type; - rtp.interleaved = 2 * track->_type; + rtp.type = type; + rtp.interleaved = 2 * type; rtp.mark = rtp_raw_ptr[1] >> 7; rtp.PT = rtp_raw_ptr[1] & 0x7F; @@ -59,29 +59,29 @@ bool RtpReceiver::handleOneRtp(int track_index,SdpTrack::Ptr &track, unsigned ch memcpy(&rtp.timeStamp, rtp_raw_ptr + 4, 4); rtp.timeStamp = ntohl(rtp.timeStamp); - if(!track->_samplerate){ + if(!samplerate){ //无法把时间戳转换成毫秒 return false; } //时间戳转换成毫秒 - rtp.timeStamp = rtp.timeStamp * 1000LL / track->_samplerate; + rtp.timeStamp = rtp.timeStamp * 1000LL / samplerate; //ssrc,内存对齐 memcpy(&rtp.ssrc, rtp_raw_ptr + 8, 4); rtp.ssrc = ntohl(rtp.ssrc); - if (track->_ssrc != rtp.ssrc) { - if (track->_ssrc == 0) { + if (_ssrc[track_index] != rtp.ssrc) { + if (_ssrc[track_index] == 0) { //保存SSRC至track对象 - track->_ssrc = rtp.ssrc; + _ssrc[track_index] = rtp.ssrc; }else{ //ssrc错误 - WarnL << "ssrc错误:" << rtp.ssrc << " != " << track->_ssrc; + WarnL << "ssrc错误:" << rtp.ssrc << " != " << _ssrc[track_index]; if (_ssrc_err_count[track_index]++ > 10) { //ssrc切换后清除老数据 - WarnL << "ssrc更换:" << track->_ssrc << " -> " << rtp.ssrc; + WarnL << "ssrc更换:" << _ssrc[track_index] << " -> " << rtp.ssrc; _rtp_sort_cache_map[track_index].clear(); - track->_ssrc = rtp.ssrc; + _ssrc[track_index] = rtp.ssrc; } return false; } @@ -168,11 +168,12 @@ void RtpReceiver::sortRtp(const RtpPacket::Ptr &rtp,int track_index){ } void RtpReceiver::clear() { - CLEAR_ARR(_last_seq) - CLEAR_ARR(_ssrc_err_count) - CLEAR_ARR(_seq_ok_count) - CLEAR_ARR(_sort_started) - CLEAR_ARR(_seq_cycle_count) + CLEAR_ARR(_last_seq); + CLEAR_ARR(_ssrc); + CLEAR_ARR(_ssrc_err_count); + CLEAR_ARR(_seq_ok_count); + CLEAR_ARR(_sort_started); + CLEAR_ARR(_seq_cycle_count); _rtp_sort_cache_map[0].clear(); _rtp_sort_cache_map[1].clear(); diff --git a/src/Rtsp/RtpReceiver.h b/src/Rtsp/RtpReceiver.h index 1631184e..243fef20 100644 --- a/src/Rtsp/RtpReceiver.h +++ b/src/Rtsp/RtpReceiver.h @@ -32,12 +32,13 @@ protected: /** * 输入数据指针生成并排序rtp包 * @param track_index track下标索引 - * @param track sdp track相关信息 + * @param type track类型 + * @param samplerate rtp时间戳基准时钟,视频为90000,音频为采样率 * @param rtp_raw_ptr rtp数据指针 * @param rtp_raw_len rtp数据指针长度 * @return 解析成功返回true */ - bool handleOneRtp(int track_index,SdpTrack::Ptr &track, unsigned char *rtp_raw_ptr, unsigned int rtp_raw_len); + bool handleOneRtp(int track_index, TrackType type, int samplerate, unsigned char *rtp_raw_ptr, unsigned int rtp_raw_len); /** * rtp数据包排序后输出 @@ -49,9 +50,12 @@ protected: void setPoolSize(int size); int getJitterSize(int track_index); int getCycleCount(int track_index); + private: void sortRtp(const RtpPacket::Ptr &rtp , int track_index); + private: + uint32_t _ssrc[2] = { 0, 0 }; //ssrc不匹配计数 uint32_t _ssrc_err_count[2] = { 0, 0 }; //上次seq diff --git a/src/Rtsp/RtspPlayer.cpp b/src/Rtsp/RtspPlayer.cpp index 297266f7..a2ce2b24 100644 --- a/src/Rtsp/RtspPlayer.cpp +++ b/src/Rtsp/RtspPlayer.cpp @@ -319,7 +319,8 @@ void RtspPlayer::handleResSETUP(const Parser &parser, unsigned int uiTrackIndex) WarnL << "收到其他地址的rtp数据:" << SockUtil::inet_ntoa(((struct sockaddr_in *) addr)->sin_addr); return; } - strongSelf->handleOneRtp(uiTrackIndex, strongSelf->_sdp_track[uiTrackIndex], (unsigned char *) buf->data(), buf->size()); + strongSelf->handleOneRtp(uiTrackIndex, strongSelf->_sdp_track[uiTrackIndex]->_type, + strongSelf->_sdp_track[uiTrackIndex]->_samplerate, (unsigned char *) buf->data(), buf->size()); }); if(pRtcpSockRef) { @@ -464,14 +465,10 @@ void RtspPlayer::onRtpPacket(const char *data, uint64_t len) { uint8_t interleaved = data[1]; if(interleaved %2 == 0){ trackIdx = getTrackIndexByInterleaved(interleaved); - if (trackIdx != -1) { - handleOneRtp(trackIdx, _sdp_track[trackIdx], (unsigned char *)data + 4, len - 4); - } + handleOneRtp(trackIdx, _sdp_track[trackIdx]->_type, _sdp_track[trackIdx]->_samplerate, (unsigned char *)data + 4, len - 4); }else{ trackIdx = getTrackIndexByInterleaved(interleaved - 1); - if (trackIdx != -1) { - onRtcpPacket(trackIdx, _sdp_track[trackIdx], (unsigned char *) data + 4, len - 4); - } + onRtcpPacket(trackIdx, _sdp_track[trackIdx], (unsigned char *) data + 4, len - 4); } } @@ -712,10 +709,7 @@ void RtspPlayer::onRecvRTP_l(const RtpPacket::Ptr &pkt, const SdpTrack::Ptr &tra _rtp_recv_ticker.resetTime(); onRecvRTP(pkt, track); - int iTrackIndex = getTrackIndexByInterleaved(pkt->interleaved); - if (iTrackIndex == -1) { - return; - } + int iTrackIndex = getTrackIndexByTrackType(pkt->type); RtcpCounter &counter = _rtcp_counter[iTrackIndex]; counter.pktCnt = pkt->sequence; auto &ticker = _rtcp_send_ticker[iTrackIndex]; @@ -788,7 +782,7 @@ int RtspPlayer::getTrackIndexByInterleaved(int interleaved) const { if (_sdp_track.size() == 1) { return 0; } - return -1; + throw SockException(Err_shutdown, StrPrinter << "no such track with interleaved:" << interleaved); } int RtspPlayer::getTrackIndexByTrackType(TrackType trackType) const { @@ -800,7 +794,7 @@ int RtspPlayer::getTrackIndexByTrackType(TrackType trackType) const { if (_sdp_track.size() == 1) { return 0; } - return -1; + throw SockException(Err_shutdown, StrPrinter << "no such track with type:" << (int) trackType); } } /* namespace mediakit */ diff --git a/src/Rtsp/RtspPusher.cpp b/src/Rtsp/RtspPusher.cpp index f259a0d6..16dd12b7 100644 --- a/src/Rtsp/RtspPusher.cpp +++ b/src/Rtsp/RtspPusher.cpp @@ -347,7 +347,7 @@ inline int RtspPusher::getTrackIndexByTrackType(TrackType type) { if(_aTrackInfo.size() == 1){ return 0; } - return -1; + throw SockException(Err_shutdown, StrPrinter << "no such track with type:" << (int) type); } void RtspPusher::sendRecord() { diff --git a/src/Rtsp/RtspSession.cpp b/src/Rtsp/RtspSession.cpp index 4b2cabe0..8a160e75 100644 --- a/src/Rtsp/RtspSession.cpp +++ b/src/Rtsp/RtspSession.cpp @@ -189,14 +189,10 @@ void RtspSession::onRtpPacket(const char *data, uint64_t len) { uint8_t interleaved = data[1]; if(interleaved %2 == 0){ trackIdx = getTrackIndexByInterleaved(interleaved); - if (trackIdx != -1) { - handleOneRtp(trackIdx,_aTrackInfo[trackIdx],(unsigned char *)data + 4, len - 4); - } + handleOneRtp(trackIdx, _aTrackInfo[trackIdx]->_type, _aTrackInfo[trackIdx]->_samplerate, (unsigned char *) data + 4, len - 4); }else{ trackIdx = getTrackIndexByInterleaved(interleaved - 1); - if (trackIdx != -1) { - onRtcpPacket(trackIdx, _aTrackInfo[trackIdx], (unsigned char *) data + 4, len - 4); - } + onRtcpPacket(trackIdx, _aTrackInfo[trackIdx], (unsigned char *) data + 4, len - 4); } } @@ -624,10 +620,6 @@ void RtspSession::handleReq_Setup(const Parser &parser) { controlSuffix = controlSuffix.substr(1); } int trackIdx = getTrackIndexByControlSuffix(controlSuffix); - if (trackIdx == -1) { - //未找到相应track - throw SockException(Err_shutdown, StrPrinter << "can not find any track by control suffix:" << controlSuffix); - } SdpTrack::Ptr &trackRef = _aTrackInfo[trackIdx]; if (trackRef->_inited) { //已经初始化过该Track @@ -930,7 +922,8 @@ inline void RtspSession::onRcvPeerUdpData(int intervaled, const Buffer::Ptr &pBu if(intervaled % 2 == 0){ if(_pushSrc){ //这是rtsp推流上来的rtp包 - handleOneRtp(intervaled / 2,_aTrackInfo[intervaled / 2],( unsigned char *)pBuf->data(),pBuf->size()); + auto &ref = _aTrackInfo[intervaled / 2]; + handleOneRtp(intervaled / 2, ref->_type, ref->_samplerate, (unsigned char *) pBuf->data(), pBuf->size()); }else if(!_udpSockConnected.count(intervaled)){ //这是rtsp播放器的rtp打洞包 _udpSockConnected.emplace(intervaled); @@ -1077,7 +1070,7 @@ inline int RtspSession::getTrackIndexByTrackType(TrackType type) { if(_aTrackInfo.size() == 1){ return 0; } - return -1; + throw SockException(Err_shutdown, StrPrinter << "no such track with type:" << (int) type); } inline int RtspSession::getTrackIndexByControlSuffix(const string &controlSuffix) { for (unsigned int i = 0; i < _aTrackInfo.size(); i++) { @@ -1088,7 +1081,7 @@ inline int RtspSession::getTrackIndexByControlSuffix(const string &controlSuffix if(_aTrackInfo.size() == 1){ return 0; } - return -1; + throw SockException(Err_shutdown, StrPrinter << "no such track with suffix:" << controlSuffix); } inline int RtspSession::getTrackIndexByInterleaved(int interleaved){ @@ -1100,7 +1093,7 @@ inline int RtspSession::getTrackIndexByInterleaved(int interleaved){ if(_aTrackInfo.size() == 1){ return 0; } - return -1; + throw SockException(Err_shutdown, StrPrinter << "no such track with interleaved:" << interleaved); } bool RtspSession::close(MediaSource &sender,bool force) { @@ -1155,9 +1148,6 @@ void RtspSession::sendRtpPacket(const RtspMediaSource::RingDataType &pkt) { #if RTSP_SERVER_SEND_RTCP int iTrackIndex = getTrackIndexByTrackType(pkt->type); - if(iTrackIndex == -1){ - return; - } RtcpCounter &counter = _aRtcpCnt[iTrackIndex]; counter.pktCnt += 1; counter.octCount += (pkt->length - pkt->offset);