More subtle locking and unlocking of mutexes in stopstream
Some checks failed
Building, testing and releasing LASP if it has a tag / Build-Test-Ubuntu (push) Failing after 2m1s
Building, testing and releasing LASP if it has a tag / Release-Ubuntu (push) Has been skipped

This commit is contained in:
Anne de Jong 2024-03-14 08:25:47 +01:00
parent 3c16e33453
commit 83c7aa6ade

View File

@ -2,13 +2,13 @@
#include "lasp_streammgr.h" #include "lasp_streammgr.h"
#include <assert.h> #include <assert.h>
#include <thread>
#include <algorithm> #include <algorithm>
#include <functional> #include <functional>
#include <iostream> #include <iostream>
#include <memory> #include <memory>
#include <mutex> #include <mutex>
#include <thread>
#include "debugtrace.hpp" #include "debugtrace.hpp"
#include "lasp_biquadbank.h" #include "lasp_biquadbank.h"
@ -87,7 +87,7 @@ void StreamMgr::rescanDAQDevices(bool background,
std::function<void()> callback) { std::function<void()> callback) {
DEBUGTRACE_ENTER; DEBUGTRACE_ENTER;
DEBUGTRACE_PRINT(background); DEBUGTRACE_PRINT(background);
if(_scanningDevices) { if (_scanningDevices) {
throw rte("A background device scan is already busy"); throw rte("A background device scan is already busy");
} }
@ -148,7 +148,6 @@ void StreamMgr::inCallback(const DaqData &data) {
for (auto &handler : _inDataHandlers) { for (auto &handler : _inDataHandlers) {
handler->inCallback(input_filtered); handler->inCallback(input_filtered);
} }
} else { } else {
/// No input filters /// No input filters
DEBUGTRACE_PRINT("Calling incallback for handlers..."); DEBUGTRACE_PRINT("Calling incallback for handlers...");
@ -276,16 +275,18 @@ StreamMgr::~StreamMgr() {
} }
void StreamMgr::stopAllStreams() { void StreamMgr::stopAllStreams() {
DEBUGTRACE_ENTER; DEBUGTRACE_ENTER;
// No lock here! {
// Lck lck(_mtx); Lck lck(_mtx);
checkRightThread(); checkRightThread();
}
// No lock here!
_inputStream.reset(); _inputStream.reset();
_outputStream.reset(); _outputStream.reset();
} }
void StreamMgr::startStream(const DaqConfiguration &config) { void StreamMgr::startStream(const DaqConfiguration &config) {
DEBUGTRACE_ENTER; DEBUGTRACE_ENTER;
if(_scanningDevices) { if (_scanningDevices) {
throw rte("DAQ device scan is busy. Cannot start stream."); throw rte("DAQ device scan is busy. Cannot start stream.");
} }
Lck lck(_mtx); Lck lck(_mtx);
@ -424,32 +425,42 @@ void StreamMgr::startStream(const DaqConfiguration &config) {
void StreamMgr::stopStream(const StreamType t) { void StreamMgr::stopStream(const StreamType t) {
DEBUGTRACE_ENTER; DEBUGTRACE_ENTER;
checkRightThread(); checkRightThread();
bool resetHandlers = false;
std::unique_ptr<Daq> *streamToStop = nullptr;
{ // Mutex locked in this scope
Lck lck(_mtx);
if (t == StreamType::input) { if (t == StreamType::input) {
if (!_inputStream) { if (!_inputStream) {
throw rte("Input stream is not running"); throw rte("Input stream is not running");
} }
/// Kills input stream streamToStop = std::addressof(_inputStream);
_inputStream.reset(); resetHandlers = true;
/// Send reset to all in data handlers
Lck lck(_mtx);
for (auto &handler : _inDataHandlers) {
handler->reset(nullptr);
}
} else { } else {
/// t == output /// t == output
/// Kill input stream in case that one is a duplex stream /// Kill input stream in case that one is a duplex stream
if (_inputStream && _inputStream->duplexMode()) { if (_inputStream && _inputStream->duplexMode()) {
_inputStream.reset(); streamToStop = std::addressof(_inputStream);
} else { } else {
if (!_outputStream) { if (!_outputStream) {
throw rte("Output stream is not running"); throw rte("Output stream is not running");
} }
_outputStream.reset(); streamToStop = std::addressof(_outputStream);
} // end else } // end else
} }
} // End of mutex lock. When stopping stream, mutex should be unlocked.
// If we arrive here, we should have a stream to stop.
assert(streamToStop != nullptr);
streamToStop->reset();
/// Send reset to all in data handlers
if (resetHandlers) {
Lck lck(_mtx);
for (auto &handler : _inDataHandlers) {
handler->reset(nullptr);
}
}
} }
void StreamMgr::addInDataHandler(InDataHandler *handler) { void StreamMgr::addInDataHandler(InDataHandler *handler) {