mirror of
https://github.com/brunoherbelin/vimix.git
synced 2025-12-06 16:00:00 +01:00
BugFix improved complete close of session
Wait for all registered pipelines to end when clearing the mixer manager (closing is asynchronous).
This commit is contained in:
@@ -48,7 +48,7 @@
|
||||
#include "RenderingManager.h"
|
||||
#endif
|
||||
|
||||
std::list<MediaPlayer*> MediaPlayer::registered_;
|
||||
std::list<GstElement*> MediaPlayer::registered_;
|
||||
|
||||
MediaPlayer::MediaPlayer()
|
||||
{
|
||||
@@ -100,7 +100,7 @@ MediaPlayer::MediaPlayer()
|
||||
|
||||
MediaPlayer::~MediaPlayer()
|
||||
{
|
||||
close(false);
|
||||
close();
|
||||
|
||||
// cleanup opengl texture
|
||||
if (textureindex_)
|
||||
@@ -497,7 +497,7 @@ void MediaPlayer::execute_open()
|
||||
gst_element_set_name(pipeline_, std::to_string(id_).c_str());
|
||||
|
||||
// register media player
|
||||
MediaPlayer::registered_.push_back(this);
|
||||
MediaPlayer::registered_.push_back(pipeline_);
|
||||
}
|
||||
|
||||
#else
|
||||
@@ -668,7 +668,7 @@ void MediaPlayer::execute_open()
|
||||
gst_element_set_name(pipeline_, std::to_string(id_).c_str());
|
||||
|
||||
// register media player
|
||||
MediaPlayer::registered_.push_back(this);
|
||||
MediaPlayer::registered_.push_back(pipeline_);
|
||||
}
|
||||
|
||||
#endif
|
||||
@@ -714,7 +714,7 @@ void MediaPlayer::Frame::unmap()
|
||||
}
|
||||
|
||||
|
||||
void pipeline_terminate( GstElement *p )
|
||||
void MediaPlayer::pipeline_terminate( GstElement *p )
|
||||
{
|
||||
#ifdef MEDIA_PLAYER_DEBUG
|
||||
g_printerr("MediaPlayer %s close\n", gst_element_get_name(p));
|
||||
@@ -726,9 +726,12 @@ void pipeline_terminate( GstElement *p )
|
||||
|
||||
// unref to free pipeline
|
||||
gst_object_unref ( p );
|
||||
|
||||
// unregister
|
||||
MediaPlayer::registered_.remove(p);
|
||||
}
|
||||
|
||||
void MediaPlayer::close(bool async)
|
||||
void MediaPlayer::close()
|
||||
{
|
||||
// not opened?
|
||||
if (!opened_) {
|
||||
@@ -752,13 +755,8 @@ void MediaPlayer::close(bool async)
|
||||
|
||||
// clean up GST
|
||||
if (pipeline_ != nullptr) {
|
||||
if (async)
|
||||
// end pipeline asynchronously
|
||||
std::thread(pipeline_terminate, pipeline_).detach();
|
||||
else
|
||||
// end pipeline immediately
|
||||
pipeline_terminate(pipeline_);
|
||||
|
||||
// end pipeline asynchronously
|
||||
std::thread(MediaPlayer::pipeline_terminate, pipeline_).detach();
|
||||
pipeline_ = nullptr;
|
||||
}
|
||||
|
||||
@@ -772,8 +770,6 @@ void MediaPlayer::close(bool async)
|
||||
write_index_ = 0;
|
||||
last_index_ = 0;
|
||||
|
||||
// unregister media player
|
||||
MediaPlayer::registered_.remove(this);
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -2,7 +2,6 @@
|
||||
#define __GST_MEDIA_PLAYER_H_
|
||||
|
||||
#include <string>
|
||||
#include <atomic>
|
||||
#include <mutex>
|
||||
#include <future>
|
||||
|
||||
@@ -101,7 +100,7 @@ public:
|
||||
/**
|
||||
* Close the Media
|
||||
* */
|
||||
void close(bool async = true);
|
||||
void close();
|
||||
/**
|
||||
* Update texture with latest frame
|
||||
* Must be called in rendering update loop
|
||||
@@ -300,13 +299,13 @@ public:
|
||||
* Accept visitors
|
||||
* */
|
||||
void accept(Visitor& v);
|
||||
|
||||
/**
|
||||
* @brief registered
|
||||
* @return list of media players currently registered
|
||||
*/
|
||||
static std::list<MediaPlayer*> registered() { return registered_; }
|
||||
static std::list<MediaPlayer*>::const_iterator begin() { return registered_.cbegin(); }
|
||||
static std::list<MediaPlayer*>::const_iterator end() { return registered_.cend(); }
|
||||
static std::list<GstElement*> registered() { return registered_; }
|
||||
|
||||
/**
|
||||
* Discoverer to check uri and get media info
|
||||
* */
|
||||
@@ -423,7 +422,8 @@ private:
|
||||
static GstFlowReturn callback_new_sample (GstAppSink *, gpointer);
|
||||
|
||||
// global list of registered media player
|
||||
static std::list<MediaPlayer*> registered_;
|
||||
static void pipeline_terminate(GstElement *p);
|
||||
static std::list<GstElement*> registered_;
|
||||
};
|
||||
|
||||
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
#include <atomic>
|
||||
#include <iomanip>
|
||||
#include <iostream>
|
||||
#include <thread>
|
||||
|
||||
@@ -19,7 +19,6 @@
|
||||
|
||||
#include <algorithm>
|
||||
#include <thread>
|
||||
#include <atomic>
|
||||
#include <mutex>
|
||||
#include <vector>
|
||||
#include <chrono>
|
||||
@@ -1592,9 +1591,9 @@ void Mixer::clear()
|
||||
while (busy())
|
||||
update();
|
||||
|
||||
// set for an empty session and update to ensure session is deleted
|
||||
// set for an empty session and update to ensure all streams are deleted
|
||||
set(new Session);
|
||||
while (sessionSwapRequested_ || garbage_.size() > 0)
|
||||
while ( !MediaPlayer::registered().empty() || !Stream::registered().empty() )
|
||||
update();
|
||||
|
||||
// all finished, we can clear the back session we just added
|
||||
|
||||
@@ -120,7 +120,7 @@ void MultiFile::execute_open()
|
||||
src_ = gst_bin_get_by_name (GST_BIN (pipeline_), "src");
|
||||
}
|
||||
|
||||
void MultiFile::close (bool)
|
||||
void MultiFile::close ()
|
||||
{
|
||||
if (src_ != nullptr) {
|
||||
gst_object_unref (src_);
|
||||
|
||||
@@ -25,7 +25,7 @@ class MultiFile : public Stream
|
||||
public:
|
||||
MultiFile ();
|
||||
void open (const MultiFileSequence &sequence, uint framerate = 30);
|
||||
void close (bool) override;
|
||||
void close () override;
|
||||
void rewind () override;
|
||||
|
||||
// dynamic change of gstreamer multifile source properties
|
||||
|
||||
@@ -31,6 +31,8 @@
|
||||
|
||||
#include "Stream.h"
|
||||
|
||||
std::list<GstElement*> Stream::registered_;
|
||||
|
||||
#ifndef NDEBUG
|
||||
#define STREAM_DEBUG
|
||||
#endif
|
||||
@@ -73,7 +75,7 @@ Stream::Stream()
|
||||
|
||||
Stream::~Stream()
|
||||
{
|
||||
Stream::close(false);
|
||||
Stream::close();
|
||||
|
||||
// cleanup opengl texture
|
||||
if (textureindex_)
|
||||
@@ -348,9 +350,10 @@ void Stream::Frame::unmap()
|
||||
}
|
||||
|
||||
|
||||
void async_terminate( GstElement *p )
|
||||
void Stream::pipeline_terminate( GstElement *p )
|
||||
{
|
||||
#ifdef STREAM_DEBUG
|
||||
g_printerr("Stream %s close\n", gst_element_get_name(p));
|
||||
Log::Info("Stream %s closed", gst_element_get_name(p));
|
||||
#endif
|
||||
|
||||
@@ -366,9 +369,12 @@ void async_terminate( GstElement *p )
|
||||
|
||||
// unref to free pipeline
|
||||
gst_object_unref ( p );
|
||||
|
||||
// unregister
|
||||
Stream::registered_.remove(p);
|
||||
}
|
||||
|
||||
void Stream::close(bool async)
|
||||
void Stream::close()
|
||||
{
|
||||
// not opened?
|
||||
if (!opened_) {
|
||||
@@ -384,13 +390,8 @@ void Stream::close(bool async)
|
||||
|
||||
// clean up GST
|
||||
if (pipeline_ != nullptr) {
|
||||
|
||||
// end pipeline asynchronously
|
||||
if (async)
|
||||
std::thread(async_terminate, pipeline_).detach();
|
||||
else
|
||||
async_terminate(pipeline_);
|
||||
|
||||
std::thread(Stream::pipeline_terminate, pipeline_).detach();
|
||||
pipeline_ = nullptr;
|
||||
}
|
||||
|
||||
|
||||
13
src/Stream.h
13
src/Stream.h
@@ -2,7 +2,7 @@
|
||||
#define STREAM_H
|
||||
|
||||
#include <string>
|
||||
#include <atomic>
|
||||
#include <list>
|
||||
#include <mutex>
|
||||
#include <future>
|
||||
#include <condition_variable>
|
||||
@@ -74,7 +74,7 @@ public:
|
||||
/**
|
||||
* Close the Media
|
||||
* */
|
||||
virtual void close(bool async = true);
|
||||
virtual void close();
|
||||
/**
|
||||
* Update texture with latest frame
|
||||
* Must be called in rendering update loop
|
||||
@@ -160,7 +160,11 @@ public:
|
||||
* Used for saving session file
|
||||
* */
|
||||
void accept(Visitor& v);
|
||||
|
||||
/**
|
||||
* @brief registered
|
||||
* @return list of streams currently registered
|
||||
*/
|
||||
static std::list<GstElement*> registered() { return registered_; }
|
||||
|
||||
protected:
|
||||
|
||||
@@ -249,6 +253,9 @@ protected:
|
||||
static GstFlowReturn callback_new_preroll (GstAppSink *, gpointer );
|
||||
static GstFlowReturn callback_new_sample (GstAppSink *, gpointer);
|
||||
|
||||
// global list of registered streams
|
||||
static void pipeline_terminate(GstElement *p);
|
||||
static std::list<GstElement*> registered_;
|
||||
};
|
||||
|
||||
|
||||
|
||||
Reference in New Issue
Block a user