From 6a7c76be06a5ce9f36449a79f75cfdda4ab7a4ba Mon Sep 17 00:00:00 2001 From: xiongziliang <771730766@qq.com> Date: Thu, 25 Oct 2018 22:57:59 +0800 Subject: [PATCH] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=E6=96=B0=E7=9A=84sdp?= =?UTF-8?q?=E8=A7=A3=E6=9E=90=E7=AE=97=E6=B3=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/Player/Frame.h | 1 + src/RtmpMuxer/RtmpMetedata.h | 2 +- src/Rtsp/Rtsp.cpp | 119 ++++++++++++++++++++++++----------- src/Rtsp/Rtsp.h | 38 ++++++++++- src/RtspMuxer/RtspSdp.h | 2 +- 5 files changed, 124 insertions(+), 38 deletions(-) diff --git a/src/Player/Frame.h b/src/Player/Frame.h index 53afbb2c..ff48c672 100644 --- a/src/Player/Frame.h +++ b/src/Player/Frame.h @@ -44,6 +44,7 @@ typedef enum { TrackInvalid = -1, TrackVideo = 0, TrackAudio, + TrackTitle, TrackMax } TrackType; diff --git a/src/RtmpMuxer/RtmpMetedata.h b/src/RtmpMuxer/RtmpMetedata.h index ea0b8114..fa193b8b 100644 --- a/src/RtmpMuxer/RtmpMetedata.h +++ b/src/RtmpMuxer/RtmpMetedata.h @@ -75,7 +75,7 @@ public: * @return */ TrackType getTrackType() const override { - return TrackInvalid; + return TrackTitle; } /** diff --git a/src/Rtsp/Rtsp.cpp b/src/Rtsp/Rtsp.cpp index 721dee4e..b17b7513 100644 --- a/src/Rtsp/Rtsp.cpp +++ b/src/Rtsp/Rtsp.cpp @@ -49,78 +49,124 @@ string FindField(const char* buf, const char* start, const char *end ,int bufSiz } return string(msg_start, msg_end); } -int parserSDP(const string& sdp, RtspTrack Track[2]) { - map > > sdpAttr; - string sdpTrack = ""; + + +void SdpAttr::load(const string &sdp) { + _track_map.clear(); + string key; + SdpTrack::Ptr track = std::make_shared(); auto lines = split(sdp,"\n"); for (auto &line : lines){ trim(line); - if(line.size() < 2){ - continue; - } - if(line[1] != '='){ + if(line.size() < 2 || line[1] != '='){ continue; } char opt = line[0]; string opt_val = line.substr(2); switch (opt){ case 'o': + track->_o = opt_val; + break; case 's': + track->_s = opt_val; + break; case 'i': + track->_i = opt_val; + break; case 'c': - case 't':{ - sdpAttr[sdpTrack][opt][""] = opt_val; - } + track->_c = opt_val; + break; + case 't': + track->_t = opt_val; + break; + case 'b': + track->_b = opt_val; break; case 'm':{ - sdpTrack = FindField(opt_val.data(), nullptr," "); - sdpAttr[sdpTrack][opt][""] = opt_val; + _track_map[key] = track; + track = std::make_shared(); + key = FindField(opt_val.data(), nullptr," ");; + track->_m = opt_val; } break; case 'a':{ string attr = FindField(opt_val.data(), nullptr,":"); if(attr.empty()){ - sdpAttr[sdpTrack][opt][opt_val] = opt_val; + track->_attr[opt_val] = ""; }else{ - sdpAttr[sdpTrack][opt][attr] = FindField(opt_val.data(),":", nullptr); + track->_attr[attr] = FindField(opt_val.data(),":", nullptr); } } break; default: + track->_other[opt] = opt_val; break; } } + _track_map[key] = track; - for (auto &pr : sdpAttr) { - TrackType trackType = TrackInvalid; - if (pr.first == "video") { - trackType = TrackVideo; + + for (auto &pr : _track_map) { + auto &track = *pr.second; + if (pr.first == "") { + track._type = TrackTitle; + } else if (pr.first == "video") { + track._type = TrackVideo; } else if (pr.first == "audio") { - trackType = TrackAudio; - } else if (pr.first == "") { - //title - auto range = pr.second['a']["range"]; - char name[16] = {0},start[16] = {0},end[16] = {0}; - if (2 == sscanf(range.data(), "%15[^=]=%15[^-]-%15s", name, start, end)) { - - } - DebugL << range; - continue; + track._type = TrackAudio; } else { - continue; + track._type = TrackInvalid; } - auto rtpmap = pr.second['a']["rtpmap"]; - int pt, samplerate; - char codec[16] = {0}; - if (3 == sscanf(rtpmap.data(), "%d %15[^/]/%d", &pt, codec, &samplerate)) { - + auto it = track._attr.find("range"); + if (it != track._attr.end()) { + char name[16] = {0}, start[16] = {0}, end[16] = {0}; + int ret = sscanf(it->second.data(), "%15[^=]=%15[^-]-%15s", name, start, end); + if (3 == ret || 2 == ret) { + if (strcmp(start, "now") == 0) { + strcpy(start, "0"); + } + track._start = atof(start); + track._end = atof(end); + track._duration = track._end - track._start; + } + } + + it = track._attr.find("rtpmap"); + if(it != track._attr.end()){ + auto rtpmap = it->second; + int pt, samplerate; + char codec[16] = {0}; + if (3 == sscanf(rtpmap.data(), "%d %15[^/]/%d", &pt, codec, &samplerate)) { + track._pt = pt; + track._codec = codec; + track._samplerate = samplerate; + } + } + + it = track._attr.find("fmtp"); + if(it != track._attr.end()) { + track._fmtp = it->second; + } + + it = track._attr.find("control"); + if(it != track._attr.end()) { + track._control = it->second; } - DebugL << codec; } +} +SdpTrack::Ptr SdpAttr::getTrack(TrackType type) { + for (auto &pr : _track_map){ + if(pr.second->_type == type){ + return pr.second; + } + } + return nullptr; +} +int parserSDP(const string& sdp, RtspTrack Track[2]) { int track_cnt = 0; string::size_type pos_head = 0; while ((pos_head = sdp.find("m=",pos_head)) != string::npos ) { @@ -169,6 +215,7 @@ static onceToken s_token([](){ "a=recvonly"; RtspTrack track[2]; parserSDP(str,track); + SdpAttr attr(str); track[0].inited=true; }); bool MakeNalu(uint8_t in, NALU &nal) { @@ -190,3 +237,5 @@ bool MakeFU(uint8_t in, FU &fu) { } return true; } + + diff --git a/src/Rtsp/Rtsp.h b/src/Rtsp/Rtsp.h index a5d66a7c..9120b993 100644 --- a/src/Rtsp/Rtsp.h +++ b/src/Rtsp/Rtsp.h @@ -38,6 +38,43 @@ using namespace std; using namespace toolkit; using namespace mediakit; +class SdpTrack{ +public: + typedef std::shared_ptr Ptr; + + string _m; + string _o; + string _s; + string _i; + string _c; + string _t; + string _b; + + float _duration = 0; + float _start = 0; + float _end = 0; + + map _other; + map _attr; +public: + int _pt; + string _codec; + int _samplerate; + string _fmtp; + string _control; + TrackType _type; +}; +class SdpAttr { +public: + typedef std::shared_ptr Ptr; + SdpAttr(const string &sdp){load(sdp);}; + ~SdpAttr(){} + + void load(const string &sdp); + SdpTrack::Ptr getTrack(TrackType type); +private: + map _track_map; +}; class RtspTrack{ public: @@ -63,7 +100,6 @@ public: string FindField(const char* buf, const char* start, const char *end,int bufSize = 0 ); int parserSDP(const string& sdp, RtspTrack Track[2]); - struct StrCaseCompare { bool operator()(const string& __x, const string& __y) const diff --git a/src/RtspMuxer/RtspSdp.h b/src/RtspMuxer/RtspSdp.h index ce766658..37ddd0e5 100644 --- a/src/RtspMuxer/RtspSdp.h +++ b/src/RtspMuxer/RtspSdp.h @@ -115,7 +115,7 @@ public: * @return */ TrackType getTrackType() const override { - return TrackInvalid; + return TrackTitle; } /**