From 2a1b3e194db927c3ec260bd5f540e82b6423b563 Mon Sep 17 00:00:00 2001 From: aler9 <46489434+aler9@users.noreply.github.com> Date: Sun, 3 Oct 2021 16:05:37 +0200 Subject: [PATCH] avoid deadlock when a runOnDemand command is used and a path is deleted --- internal/core/path.go | 30 ++++++++++++++++++++---------- 1 file changed, 20 insertions(+), 10 deletions(-) diff --git a/internal/core/path.go b/internal/core/path.go index 9ad8d73c..47f7b92f 100644 --- a/internal/core/path.go +++ b/internal/core/path.go @@ -438,11 +438,6 @@ outer: rp.Close() } - if pa.onDemandCmd != nil { - pa.onDemandCmd.Close() - pa.Log(logger.Info, "runOnDemand command stopped") - } - if pa.stream != nil { pa.stream.close() } @@ -459,6 +454,16 @@ outer: } } + // close onDemandCmd after the source has been closed. + // this avoids a deadlock in which onDemandCmd is a + // RTSP publisher that sends a TEARDOWN request and waits + // for the response (like FFmpeg), but it can't since + /// the path is already waiting for the command to close. + if pa.onDemandCmd != nil { + pa.onDemandCmd.Close() + pa.Log(logger.Info, "runOnDemand command stopped") + } + pa.parent.OnPathClose(pa) } @@ -520,16 +525,21 @@ func (pa *path) onDemandCloseSource() { pa.source.(sourceStatic).Close() pa.source = nil } else { + if pa.source != nil { + pa.source.(publisher).Close() + pa.doPublisherRemove() + } + + // close onDemandCmd after the source has been closed. + // this avoids a deadlock in which onDemandCmd is a + // RTSP publisher that sends a TEARDOWN request and waits + // for the response (like FFmpeg), but it can't since + /// the path is already waiting for the command to close. if pa.onDemandCmd != nil { pa.onDemandCmd.Close() pa.onDemandCmd = nil pa.Log(logger.Info, "runOnDemand command stopped") } - - if pa.source != nil { - pa.source.(publisher).Close() - pa.doPublisherRemove() - } } }