1
0
mirror of https://github.com/f4exb/sdrangel.git synced 2025-05-29 05:22:25 -04:00

FileSinkOutput: refactored Thread to Worker object moved to thread. Equivalent to FileInput changes

This commit is contained in:
f4exb 2020-07-12 10:22:24 +02:00
parent 8babeb87a7
commit fb1c748d1d
5 changed files with 60 additions and 81 deletions

View File

@ -4,14 +4,14 @@ set(filesink_SOURCES
filesinkoutput.cpp filesinkoutput.cpp
filesinkplugin.cpp filesinkplugin.cpp
filesinksettings.cpp filesinksettings.cpp
filesinkthread.cpp filesinkworker.cpp
) )
set(filesink_HEADERS set(filesink_HEADERS
filesinkoutput.h filesinkoutput.h
filesinkplugin.h filesinkplugin.h
filesinksettings.h filesinksettings.h
filesinkthread.h filesinkworker.h
) )
include_directories( include_directories(

View File

@ -15,7 +15,6 @@
// along with this program. If not, see <http://www.gnu.org/licenses/>. // // along with this program. If not, see <http://www.gnu.org/licenses/>. //
/////////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////////
#include <string.h>
#include <errno.h> #include <errno.h>
#include <QDebug> #include <QDebug>
@ -30,7 +29,7 @@
#include "device/deviceapi.h" #include "device/deviceapi.h"
#include "filesinkoutput.h" #include "filesinkoutput.h"
#include "filesinkthread.h" #include "filesinkworker.h"
MESSAGE_CLASS_DEFINITION(FileSinkOutput::MsgConfigureFileSink, Message) MESSAGE_CLASS_DEFINITION(FileSinkOutput::MsgConfigureFileSink, Message)
MESSAGE_CLASS_DEFINITION(FileSinkOutput::MsgStartStop, Message) MESSAGE_CLASS_DEFINITION(FileSinkOutput::MsgStartStop, Message)
@ -43,7 +42,7 @@ MESSAGE_CLASS_DEFINITION(FileSinkOutput::MsgReportFileSinkStreamTiming, Message)
FileSinkOutput::FileSinkOutput(DeviceAPI *deviceAPI) : FileSinkOutput::FileSinkOutput(DeviceAPI *deviceAPI) :
m_deviceAPI(deviceAPI), m_deviceAPI(deviceAPI),
m_settings(), m_settings(),
m_fileSinkThread(0), m_fileSinkWorker(nullptr),
m_deviceDescription("FileSink"), m_deviceDescription("FileSink"),
m_fileName("./test.sdriq"), m_fileName("./test.sdriq"),
m_startingTimeStamp(0), m_startingTimeStamp(0),
@ -95,11 +94,12 @@ bool FileSinkOutput::start()
openFileStream(); openFileStream();
m_fileSinkThread = new FileSinkThread(&m_ofstream, &m_sampleSourceFifo); m_fileSinkWorker = new FileSinkWorker(&m_ofstream, &m_sampleSourceFifo);
m_fileSinkThread->setSamplerate(m_settings.m_sampleRate); m_fileSinkWorker->moveToThread(&m_fileSinkWorkerThread);
m_fileSinkThread->setLog2Interpolation(m_settings.m_log2Interp); m_fileSinkWorker->setSamplerate(m_settings.m_sampleRate);
m_fileSinkThread->connectTimer(m_masterTimer); m_fileSinkWorker->setLog2Interpolation(m_settings.m_log2Interp);
m_fileSinkThread->startWork(); m_fileSinkWorker->connectTimer(m_masterTimer);
startWorker();
mutexLocker.unlock(); mutexLocker.unlock();
//applySettings(m_generalSettings, m_settings, true); //applySettings(m_generalSettings, m_settings, true);
@ -119,11 +119,11 @@ void FileSinkOutput::stop()
qDebug() << "FileSourceInput::stop"; qDebug() << "FileSourceInput::stop";
QMutexLocker mutexLocker(&m_mutex); QMutexLocker mutexLocker(&m_mutex);
if(m_fileSinkThread != 0) if (m_fileSinkWorker)
{ {
m_fileSinkThread->stopWork(); stopWorker();
delete m_fileSinkThread; delete m_fileSinkWorker;
m_fileSinkThread = 0; m_fileSinkWorker = nullptr;
} }
if (m_ofstream.is_open()) { if (m_ofstream.is_open()) {
@ -239,15 +239,12 @@ bool FileSinkOutput::handleMessage(const Message& message)
MsgConfigureFileSinkWork& conf = (MsgConfigureFileSinkWork&) message; MsgConfigureFileSinkWork& conf = (MsgConfigureFileSinkWork&) message;
bool working = conf.isWorking(); bool working = conf.isWorking();
if (m_fileSinkThread != 0) if (m_fileSinkWorker != 0)
{ {
if (working) if (working) {
{ startWorker();
m_fileSinkThread->startWork(); } else {
} stopWorker();
else
{
m_fileSinkThread->stopWork();
} }
} }
@ -257,9 +254,9 @@ bool FileSinkOutput::handleMessage(const Message& message)
{ {
MsgReportFileSinkStreamTiming *report; MsgReportFileSinkStreamTiming *report;
if (m_fileSinkThread != 0 && getMessageQueueToGUI()) if (m_fileSinkWorker != 0 && getMessageQueueToGUI())
{ {
report = MsgReportFileSinkStreamTiming::create(m_fileSinkThread->getSamplesCount()); report = MsgReportFileSinkStreamTiming::create(m_fileSinkWorker->getSamplesCount());
getMessageQueueToGUI()->push(report); getMessageQueueToGUI()->push(report);
} }
@ -286,9 +283,9 @@ void FileSinkOutput::applySettings(const FileSinkSettings& settings, bool force)
{ {
m_settings.m_sampleRate = settings.m_sampleRate; m_settings.m_sampleRate = settings.m_sampleRate;
if (m_fileSinkThread != 0) if (m_fileSinkWorker != 0)
{ {
m_fileSinkThread->setSamplerate(m_settings.m_sampleRate); m_fileSinkWorker->setSamplerate(m_settings.m_sampleRate);
} }
forwardChange = true; forwardChange = true;
@ -298,9 +295,9 @@ void FileSinkOutput::applySettings(const FileSinkSettings& settings, bool force)
{ {
m_settings.m_log2Interp = settings.m_log2Interp; m_settings.m_log2Interp = settings.m_log2Interp;
if (m_fileSinkThread != 0) if (m_fileSinkWorker != 0)
{ {
m_fileSinkThread->setLog2Interpolation(m_settings.m_log2Interp); m_fileSinkWorker->setLog2Interpolation(m_settings.m_log2Interp);
} }
forwardChange = true; forwardChange = true;

View File

@ -20,6 +20,8 @@
#include <QString> #include <QString>
#include <QTimer> #include <QTimer>
#include <QThread>
#include <ctime> #include <ctime>
#include <iostream> #include <iostream>
#include <fstream> #include <fstream>
@ -27,7 +29,7 @@
#include "dsp/devicesamplesink.h" #include "dsp/devicesamplesink.h"
#include "filesinksettings.h" #include "filesinksettings.h"
class FileSinkThread; class FileSinkWorker;
class DeviceAPI; class DeviceAPI;
class FileSinkOutput : public DeviceSampleSink { class FileSinkOutput : public DeviceSampleSink {
@ -206,12 +208,15 @@ private:
QMutex m_mutex; QMutex m_mutex;
FileSinkSettings m_settings; FileSinkSettings m_settings;
std::ofstream m_ofstream; std::ofstream m_ofstream;
FileSinkThread* m_fileSinkThread; FileSinkWorker* m_fileSinkWorker;
QThread m_fileSinkWorkerThread;
QString m_deviceDescription; QString m_deviceDescription;
QString m_fileName; QString m_fileName;
std::time_t m_startingTimeStamp; std::time_t m_startingTimeStamp;
const QTimer& m_masterTimer; const QTimer& m_masterTimer;
void startWorker();
void stopWorker();
void openFileStream(); void openFileStream();
void applySettings(const FileSinkSettings& settings, bool force = false); void applySettings(const FileSinkSettings& settings, bool force = false);
}; };

View File

@ -22,10 +22,10 @@
#include <QDebug> #include <QDebug>
#include "dsp/samplesourcefifo.h" #include "dsp/samplesourcefifo.h"
#include "filesinkthread.h" #include "filesinkworker.h"
FileSinkThread::FileSinkThread(std::ofstream *samplesStream, SampleSourceFifo* sampleFifo, QObject* parent) : FileSinkWorker::FileSinkWorker(std::ofstream *samplesStream, SampleSourceFifo* sampleFifo, QObject* parent) :
QThread(parent), QObject(parent),
m_running(false), m_running(false),
m_ofstream(samplesStream), m_ofstream(samplesStream),
m_bufsize(0), m_bufsize(0),
@ -37,12 +37,12 @@ FileSinkThread::FileSinkThread(std::ofstream *samplesStream, SampleSourceFifo* s
m_throttlems(FILESINK_THROTTLE_MS), m_throttlems(FILESINK_THROTTLE_MS),
m_maxThrottlems(50), m_maxThrottlems(50),
m_throttleToggle(false), m_throttleToggle(false),
m_buf(0) m_buf(nullptr)
{ {
assert(m_ofstream != 0); assert(m_ofstream != nullptr);
} }
FileSinkThread::~FileSinkThread() FileSinkWorker::~FileSinkWorker()
{ {
if (m_running) { if (m_running) {
stopWork(); stopWork();
@ -51,39 +51,34 @@ FileSinkThread::~FileSinkThread()
if (m_buf) delete[] m_buf; if (m_buf) delete[] m_buf;
} }
void FileSinkThread::startWork() void FileSinkWorker::startWork()
{ {
qDebug() << "FileSinkThread::startWork: "; qDebug() << "FileSinkWorker::startWork: ";
if (m_ofstream->is_open()) if (m_ofstream->is_open())
{ {
qDebug() << "FileSinkThread::startWork: file stream open, starting..."; qDebug() << "FileSinkWorker::startWork: file stream open, starting...";
m_maxThrottlems = 0; m_maxThrottlems = 0;
m_startWaitMutex.lock();
m_elapsedTimer.start(); m_elapsedTimer.start();
start(); m_running = true;
while(!m_running)
m_startWaiter.wait(&m_startWaitMutex, 100);
m_startWaitMutex.unlock();
} }
else else
{ {
qDebug() << "FileSinkThread::startWork: file stream closed, not starting."; qDebug() << "FileSinkWorker::startWork: file stream closed, not starting.";
m_running = false;
} }
} }
void FileSinkThread::stopWork() void FileSinkWorker::stopWork()
{ {
qDebug() << "FileSinkThread::stopWork";
m_running = false; m_running = false;
wait();
} }
void FileSinkThread::setSamplerate(int samplerate) void FileSinkWorker::setSamplerate(int samplerate)
{ {
if (samplerate != m_samplerate) if (samplerate != m_samplerate)
{ {
qDebug() << "FileSinkThread::setSamplerate:" qDebug() << "FileSinkWorker::setSamplerate:"
<< " new:" << samplerate << " new:" << samplerate
<< " old:" << m_samplerate; << " old:" << m_samplerate;
@ -113,7 +108,7 @@ void FileSinkThread::setSamplerate(int samplerate)
} }
} }
void FileSinkThread::setLog2Interpolation(int log2Interpolation) void FileSinkWorker::setLog2Interpolation(int log2Interpolation)
{ {
if ((log2Interpolation < 0) || (log2Interpolation > 6)) if ((log2Interpolation < 0) || (log2Interpolation > 6))
{ {
@ -122,7 +117,7 @@ void FileSinkThread::setLog2Interpolation(int log2Interpolation)
if (log2Interpolation != m_log2Interpolation) if (log2Interpolation != m_log2Interpolation)
{ {
qDebug() << "FileSinkThread::setLog2Interpolation:" qDebug() << "FileSinkWorker::setLog2Interpolation:"
<< " new:" << log2Interpolation << " new:" << log2Interpolation
<< " old:" << m_log2Interpolation; << " old:" << m_log2Interpolation;
@ -146,26 +141,13 @@ void FileSinkThread::setLog2Interpolation(int log2Interpolation)
} }
} }
void FileSinkThread::run() void FileSinkWorker::connectTimer(const QTimer& timer)
{ {
m_running = true; qDebug() << "FileSinkWorker::connectTimer";
m_startWaiter.wakeAll();
while(m_running) // actual work is in the tick() function
{
sleep(1);
}
m_running = false;
}
void FileSinkThread::connectTimer(const QTimer& timer)
{
qDebug() << "FileSinkThread::connectTimer";
connect(&timer, SIGNAL(timeout()), this, SLOT(tick())); connect(&timer, SIGNAL(timeout()), this, SLOT(tick()));
} }
void FileSinkThread::tick() void FileSinkWorker::tick()
{ {
if (m_running) if (m_running)
{ {
@ -193,7 +175,7 @@ void FileSinkThread::tick()
} }
} }
void FileSinkThread::callbackPart(SampleVector& data, unsigned int iBegin, unsigned int iEnd) void FileSinkWorker::callbackPart(SampleVector& data, unsigned int iBegin, unsigned int iEnd)
{ {
SampleVector::iterator beginRead = data.begin() + iBegin; SampleVector::iterator beginRead = data.begin() + iBegin;
unsigned int chunkSize = iEnd - iBegin; unsigned int chunkSize = iEnd - iBegin;

View File

@ -15,12 +15,10 @@
// along with this program. If not, see <http://www.gnu.org/licenses/>. // // along with this program. If not, see <http://www.gnu.org/licenses/>. //
/////////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////////
#ifndef INCLUDE_FILESINKTHREAD_H #ifndef INCLUDE_FILESINKWORKER_H
#define INCLUDE_FILESINKTHREAD_H #define INCLUDE_FILESINKWORKER_H
#include <QThread> #include <QObject>
#include <QMutex>
#include <QWaitCondition>
#include <QTimer> #include <QTimer>
#include <QElapsedTimer> #include <QElapsedTimer>
#include <iostream> #include <iostream>
@ -35,12 +33,12 @@
class SampleSourceFifo; class SampleSourceFifo;
class FileSinkThread : public QThread { class FileSinkWorker : public QObject {
Q_OBJECT Q_OBJECT
public: public:
FileSinkThread(std::ofstream *samplesStream, SampleSourceFifo* sampleFifo, QObject* parent = 0); FileSinkWorker(std::ofstream *samplesStream, SampleSourceFifo* sampleFifo, QObject* parent = 0);
~FileSinkThread(); ~FileSinkWorker();
void startWork(); void startWork();
void stopWork(); void stopWork();
@ -54,8 +52,6 @@ public:
void connectTimer(const QTimer& timer); void connectTimer(const QTimer& timer);
private: private:
QMutex m_startWaitMutex;
QWaitCondition m_startWaiter;
volatile bool m_running; volatile bool m_running;
std::ofstream* m_ofstream; std::ofstream* m_ofstream;
@ -74,11 +70,10 @@ private:
Interpolators<qint16, SDR_TX_SAMP_SZ, 16> m_interpolators; Interpolators<qint16, SDR_TX_SAMP_SZ, 16> m_interpolators;
int16_t *m_buf; int16_t *m_buf;
void run();
void callbackPart(SampleVector& data, unsigned int iBegin, unsigned int iEnd); void callbackPart(SampleVector& data, unsigned int iBegin, unsigned int iEnd);
private slots: private slots:
void tick(); void tick();
}; };
#endif // INCLUDE_FILESINKTHREAD_H #endif // INCLUDE_FILESINKWORKER_H