修复FFmpeg拉流代理功能缺陷的问题:#533

This commit is contained in:
xiongziliang 2020-10-24 23:31:58 +08:00
parent 67e49cb66e
commit 38a002646d
11 changed files with 71 additions and 24 deletions

View File

@ -233,7 +233,7 @@ void FFmpegSource::setOnClose(const function<void()> &cb){
} }
bool FFmpegSource::close(MediaSource &sender, bool force) { bool FFmpegSource::close(MediaSource &sender, bool force) {
auto listener = _listener.lock(); auto listener = getDelegate();
if(listener && !listener->close(sender,force)){ if(listener && !listener->close(sender,force)){
//关闭失败 //关闭失败
return false; return false;
@ -258,17 +258,11 @@ std::shared_ptr<SockInfo> FFmpegSource::getOriginSock(MediaSource &sender) const
} }
void FFmpegSource::onGetMediaSource(const MediaSource::Ptr &src) { void FFmpegSource::onGetMediaSource(const MediaSource::Ptr &src) {
auto listener = src->getListener(); auto listener = src->getListener(true);
if (listener.lock().get() != this) { if (listener.lock().get() != this) {
//防止多次进入onGetMediaSource函数导致无递归调用的bug //防止多次进入onGetMediaSource函数导致无递归调用的bug
_listener = listener; setDelegate(listener);
src->setListener(shared_from_this()); src->setListener(shared_from_this());
} else {
WarnL << "多次触发onGetMediaSource事件:"
<< src->getSchema() << "/"
<< src->getVhost() << "/"
<< src->getApp() << "/"
<< src->getId();
} }
} }

View File

@ -92,9 +92,20 @@ void MediaSource::setListener(const std::weak_ptr<MediaSourceEvent> &listener){
_listener = listener; _listener = listener;
} }
const std::weak_ptr<MediaSourceEvent>& MediaSource::getListener() const{ std::weak_ptr<MediaSourceEvent> MediaSource::getListener(bool next) const{
if (!next) {
return _listener; return _listener;
} }
auto listener = dynamic_pointer_cast<MediaSourceEventInterceptor>(_listener.lock());
if (!listener) {
//不是MediaSourceEventInterceptor对象或者对象已经销毁
return _listener;
}
//获取被拦截的对象
auto next_obj = listener->getDelegate();
//有则返回之
return next_obj ? next_obj : _listener;
}
int MediaSource::totalReaderCount(){ int MediaSource::totalReaderCount(){
auto listener = _listener.lock(); auto listener = _listener.lock();
@ -644,6 +655,17 @@ bool MediaSourceEventInterceptor::stopSendRtp(MediaSource &sender){
return false; return false;
} }
void MediaSourceEventInterceptor::setDelegate(const std::weak_ptr<MediaSourceEvent> &listener) {
if (listener.lock().get() == this) {
throw std::invalid_argument("can not set self as a delegate");
}
_listener = listener;
}
std::shared_ptr<MediaSourceEvent> MediaSourceEventInterceptor::getDelegate() const{
return _listener.lock();
}
/////////////////////////////////////FlushPolicy////////////////////////////////////// /////////////////////////////////////FlushPolicy//////////////////////////////////////
static bool isFlushAble_default(bool is_video, uint64_t last_stamp, uint64_t new_stamp, int cache_size) { static bool isFlushAble_default(bool is_video, uint64_t last_stamp, uint64_t new_stamp, int cache_size) {

View File

@ -97,6 +97,9 @@ public:
MediaSourceEventInterceptor(){} MediaSourceEventInterceptor(){}
~MediaSourceEventInterceptor() override {} ~MediaSourceEventInterceptor() override {}
void setDelegate(const std::weak_ptr<MediaSourceEvent> &listener);
std::shared_ptr<MediaSourceEvent> getDelegate() const;
MediaOriginType getOriginType(MediaSource &sender) const override; MediaOriginType getOriginType(MediaSource &sender) const override;
string getOriginUrl(MediaSource &sender) const override; string getOriginUrl(MediaSource &sender) const override;
std::shared_ptr<SockInfo> getOriginSock(MediaSource &sender) const override; std::shared_ptr<SockInfo> getOriginSock(MediaSource &sender) const override;
@ -112,7 +115,7 @@ public:
void startSendRtp(MediaSource &sender, const string &dst_url, uint16_t dst_port, uint32_t ssrc, bool is_udp, const function<void(const SockException &ex)> &cb) override; void startSendRtp(MediaSource &sender, const string &dst_url, uint16_t dst_port, uint32_t ssrc, bool is_udp, const function<void(const SockException &ex)> &cb) override;
bool stopSendRtp(MediaSource &sender) override; bool stopSendRtp(MediaSource &sender) override;
protected: private:
std::weak_ptr<MediaSourceEvent> _listener; std::weak_ptr<MediaSourceEvent> _listener;
}; };
@ -226,9 +229,9 @@ public:
////////////////MediaSourceEvent相关接口实现//////////////// ////////////////MediaSourceEvent相关接口实现////////////////
// 设置监听者 // 设置监听者
void setListener(const std::weak_ptr<MediaSourceEvent> &listener); virtual void setListener(const std::weak_ptr<MediaSourceEvent> &listener);
// 获取监听者 // 获取监听者
const std::weak_ptr<MediaSourceEvent>& getListener() const; std::weak_ptr<MediaSourceEvent> getListener(bool next = false) const;
// 本协议获取观看者个数,可能返回本协议的观看人数,也可能返回总人数 // 本协议获取观看者个数,可能返回本协议的观看人数,也可能返回总人数
virtual int readerCount() = 0; virtual int readerCount() = 0;

View File

@ -291,7 +291,7 @@ MultiMediaSourceMuxer::MultiMediaSourceMuxer(const string &vhost, const string &
} }
void MultiMediaSourceMuxer::setMediaListener(const std::weak_ptr<MediaSourceEvent> &listener) { void MultiMediaSourceMuxer::setMediaListener(const std::weak_ptr<MediaSourceEvent> &listener) {
_listener = listener; setDelegate(listener);
//拦截事件 //拦截事件
_muxer->setMediaListener(shared_from_this()); _muxer->setMediaListener(shared_from_this());
} }
@ -313,7 +313,7 @@ vector<Track::Ptr> MultiMediaSourceMuxer::getTracks(MediaSource &sender, bool tr
} }
int MultiMediaSourceMuxer::totalReaderCount(MediaSource &sender) { int MultiMediaSourceMuxer::totalReaderCount(MediaSource &sender) {
auto listener = _listener.lock(); auto listener = getDelegate();
if (!listener) { if (!listener) {
return totalReaderCount(); return totalReaderCount();
} }

View File

@ -32,7 +32,7 @@ public:
~FMP4MediaSourceMuxer() override = default; ~FMP4MediaSourceMuxer() override = default;
void setListener(const std::weak_ptr<MediaSourceEvent> &listener){ void setListener(const std::weak_ptr<MediaSourceEvent> &listener){
_listener = listener; setDelegate(listener);
_media_src->setListener(shared_from_this()); _media_src->setListener(shared_from_this());
} }

View File

@ -34,7 +34,7 @@ public:
} }
void setListener(const std::weak_ptr<MediaSourceEvent> &listener) { void setListener(const std::weak_ptr<MediaSourceEvent> &listener) {
_listener = listener; setDelegate(listener);
_hls->getMediaSource()->setListener(shared_from_this()); _hls->getMediaSource()->setListener(shared_from_this());
//先注册媒体流,后续可以按需生成 //先注册媒体流,后续可以按需生成
_hls->getMediaSource()->registHls(false); _hls->getMediaSource()->registHls(false);

View File

@ -86,7 +86,7 @@ public:
_muxer->setMediaListener(getListener()); _muxer->setMediaListener(getListener());
_muxer->setTrackListener(static_pointer_cast<RtmpMediaSourceImp>(shared_from_this())); _muxer->setTrackListener(static_pointer_cast<RtmpMediaSourceImp>(shared_from_this()));
//让_muxer对象拦截一部分事件(比如说录像相关事件) //让_muxer对象拦截一部分事件(比如说录像相关事件)
setListener(_muxer); MediaSource::setListener(_muxer);
for(auto &track : _demuxer->getTracks(false)){ for(auto &track : _demuxer->getTracks(false)){
_muxer->addTrack(track); _muxer->addTrack(track);
@ -119,6 +119,20 @@ public:
} }
} }
/**
*
* @param listener
*/
void setListener(const std::weak_ptr<MediaSourceEvent> &listener) override{
if (_muxer) {
//_muxer对象不能处理的事件再给listener处理
_muxer->setMediaListener(listener);
} else {
//未创建_muxer对象事件全部给listener处理
MediaSource::setListener(listener);
}
}
private: private:
bool _all_track_ready = false; bool _all_track_ready = false;
bool _recreate_metadata = false; bool _recreate_metadata = false;

View File

@ -32,7 +32,7 @@ public:
~RtmpMediaSourceMuxer() override{} ~RtmpMediaSourceMuxer() override{}
void setListener(const std::weak_ptr<MediaSourceEvent> &listener){ void setListener(const std::weak_ptr<MediaSourceEvent> &listener){
_listener = listener; setDelegate(listener);
_media_src->setListener(shared_from_this()); _media_src->setListener(shared_from_this());
} }

View File

@ -77,7 +77,7 @@ public:
_muxer->setMediaListener(getListener()); _muxer->setMediaListener(getListener());
_muxer->setTrackListener(static_pointer_cast<RtspMediaSourceImp>(shared_from_this())); _muxer->setTrackListener(static_pointer_cast<RtspMediaSourceImp>(shared_from_this()));
//让_muxer对象拦截一部分事件(比如说录像相关事件) //让_muxer对象拦截一部分事件(比如说录像相关事件)
setListener(_muxer); MediaSource::setListener(_muxer);
for(auto &track : _demuxer->getTracks(false)){ for(auto &track : _demuxer->getTracks(false)){
_muxer->addTrack(track); _muxer->addTrack(track);
@ -102,6 +102,20 @@ public:
_all_track_ready = true; _all_track_ready = true;
} }
/**
*
* @param listener
*/
void setListener(const std::weak_ptr<MediaSourceEvent> &listener) override{
if (_muxer) {
//_muxer对象不能处理的事件再给listener处理
_muxer->setMediaListener(listener);
} else {
//未创建_muxer对象事件全部给listener处理
MediaSource::setListener(listener);
}
}
private: private:
RtspDemuxer::Ptr _demuxer; RtspDemuxer::Ptr _demuxer;
MultiMediaSourceMuxer::Ptr _muxer; MultiMediaSourceMuxer::Ptr _muxer;

View File

@ -32,7 +32,7 @@ public:
~RtspMediaSourceMuxer() override{} ~RtspMediaSourceMuxer() override{}
void setListener(const std::weak_ptr<MediaSourceEvent> &listener){ void setListener(const std::weak_ptr<MediaSourceEvent> &listener){
_listener = listener; setDelegate(listener);
_media_src->setListener(shared_from_this()); _media_src->setListener(shared_from_this());
} }

View File

@ -31,7 +31,7 @@ public:
~TSMediaSourceMuxer() override = default; ~TSMediaSourceMuxer() override = default;
void setListener(const std::weak_ptr<MediaSourceEvent> &listener){ void setListener(const std::weak_ptr<MediaSourceEvent> &listener){
_listener = listener; setDelegate(listener);
_media_src->setListener(shared_from_this()); _media_src->setListener(shared_from_this());
} }