Fix export encoder race condition

The CmdPipeWriter::Terminated signal is used to trigger the FileWritten
callback, which invokes ExportGraphBuilder::Encoder::copy_files

Encoder::filenames must not be destroyed before the callback
arrives. This is now guaranteed by the Encoder d'tor waiting
for for the encode process to terminate.
This commit is contained in:
Robin Gareus
2024-12-15 16:31:43 +01:00
parent bae7c52f01
commit 91d91eac0d
3 changed files with 16 additions and 1 deletions

View File

@@ -120,7 +120,8 @@ class LIBARDOUR_API ExportGraphBuilder
void add_split_config (FileSpec const & config);
class Encoder {
public:
public:
~Encoder ();
template <typename T> std::shared_ptr<AudioGrapher::Sink<T> > init (FileSpec const & new_config);
void add_child (FileSpec const & new_config);
void remove_children ();

View File

@@ -380,6 +380,13 @@ ExportGraphBuilder::Encoder::add_child (FileSpec const & new_config)
filenames.push_back (new_config.filename);
}
ExportGraphBuilder::Encoder::~Encoder ()
{
if (pipe_writer) {
pipe_writer->flush ();
}
}
void
ExportGraphBuilder::Encoder::destroy_writer (bool delete_out_file)
{

View File

@@ -59,6 +59,12 @@ public:
samplecnt_t get_samples_written() const { return samples_written; }
void reset_samples_written_count() { samples_written = 0; }
void flush (void)
{
_proc->close_stdin ();
_proc->wait ();
}
void close (void)
{
_proc->terminate ();
@@ -93,6 +99,7 @@ public:
if (_proc->start (ARDOUR::SystemExec::ShareWithParent)) {
throw ARDOUR::ExportFailed ("External encoder (ffmpeg) cannot be started.");
}
assert (_proc->is_running ());
} else {
_proc->close_stdin ();
}