1
0
mirror of https://github.com/f4exb/sdrangel.git synced 2024-11-26 01:39:05 -05:00

Update threading model in AFC feature. Part of #1346

This commit is contained in:
f4exb 2022-09-21 06:01:45 +02:00
parent 6a36043231
commit 008e53104d
5 changed files with 71 additions and 34 deletions

View File

@ -19,6 +19,7 @@
#include <QNetworkAccessManager> #include <QNetworkAccessManager>
#include <QNetworkReply> #include <QNetworkReply>
#include <QBuffer> #include <QBuffer>
#include <QThread>
#include "SWGFeatureSettings.h" #include "SWGFeatureSettings.h"
#include "SWGFeatureReport.h" #include "SWGFeatureReport.h"
@ -48,14 +49,15 @@ const char* const AFC::m_featureId = "AFC";
AFC::AFC(WebAPIAdapterInterface *webAPIAdapterInterface) : AFC::AFC(WebAPIAdapterInterface *webAPIAdapterInterface) :
Feature(m_featureIdURI, webAPIAdapterInterface), Feature(m_featureIdURI, webAPIAdapterInterface),
m_thread(nullptr),
m_mutex(QMutex::Recursive),
m_running(false),
m_trackerDeviceSet(nullptr), m_trackerDeviceSet(nullptr),
m_trackedDeviceSet(nullptr), m_trackedDeviceSet(nullptr),
m_trackerIndexInDeviceSet(-1), m_trackerIndexInDeviceSet(-1),
m_trackerChannelAPI(nullptr) m_trackerChannelAPI(nullptr)
{ {
setObjectName(m_featureId); setObjectName(m_featureId);
m_worker = new AFCWorker(webAPIAdapterInterface);
m_worker->moveToThread(&m_thread);
m_state = StIdle; m_state = StIdle;
m_errorMessage = "AFC error"; m_errorMessage = "AFC error";
m_networkManager = new QNetworkAccessManager(); m_networkManager = new QNetworkAccessManager();
@ -76,36 +78,66 @@ AFC::~AFC()
&AFC::networkManagerFinished &AFC::networkManagerFinished
); );
delete m_networkManager; delete m_networkManager;
if (m_worker->isRunning()) {
stop(); stop();
}
delete m_worker;
removeTrackerFeatureReference(); removeTrackerFeatureReference();
removeTrackedFeatureReferences(); removeTrackedFeatureReferences();
} }
void AFC::start() void AFC::start()
{ {
qDebug("AFC::start"); QMutexLocker m_lock(&m_mutex);
if (m_running) {
return;
}
qDebug("AFC::start");
m_thread = new QThread();
m_worker = new AFCWorker(getWebAPIAdapterInterface());
m_worker->moveToThread(m_thread);
QObject::connect(
m_thread,
&QThread::started,
m_worker,
&AFCWorker::startWork
);
QObject::connect(
m_thread,
&QThread::finished,
m_worker,
&QObject::deleteLater
);
QObject::connect(
m_thread,
&QThread::finished,
m_thread,
&QThread::deleteLater
);
m_worker->reset();
m_worker->setMessageQueueToGUI(getMessageQueueToGUI()); m_worker->setMessageQueueToGUI(getMessageQueueToGUI());
bool ok = m_worker->startWork(); m_thread->start();
m_state = ok ? StRunning : StError;
m_thread.start();
AFCWorker::MsgConfigureAFCWorker *msg = AFCWorker::MsgConfigureAFCWorker::create(m_settings, true); AFCWorker::MsgConfigureAFCWorker *msg = AFCWorker::MsgConfigureAFCWorker::create(m_settings, true);
m_worker->getInputMessageQueue()->push(msg); m_worker->getInputMessageQueue()->push(msg);
m_state = StRunning;
m_running = true;
} }
void AFC::stop() void AFC::stop()
{ {
QMutexLocker m_lock(&m_mutex);
if (!m_running) {
return;
}
qDebug("AFC::stop"); qDebug("AFC::stop");
m_worker->stopWork(); m_running = false;
m_state = StIdle; m_state = StIdle;
m_thread.quit(); m_thread->quit();
m_thread.wait(); m_thread->wait();
} }
bool AFC::handleMessage(const Message& cmd) bool AFC::handleMessage(const Message& cmd)
@ -138,7 +170,7 @@ bool AFC::handleMessage(const Message& cmd)
QString *channelType = swgChannelSettings->getChannelType(); QString *channelType = swgChannelSettings->getChannelType();
qDebug() << "AFC::handleMessage: MainCore::MsgChannelSettings: " << *channelType; qDebug() << "AFC::handleMessage: MainCore::MsgChannelSettings: " << *channelType;
if (m_worker->isRunning()) if (m_running)
{ {
m_worker->getInputMessageQueue()->push(&cfg); m_worker->getInputMessageQueue()->push(&cfg);
} }
@ -150,7 +182,7 @@ bool AFC::handleMessage(const Message& cmd)
} }
else if (MsgDeviceTrack::match(cmd)) else if (MsgDeviceTrack::match(cmd))
{ {
if (m_worker->isRunning()) if (m_running)
{ {
AFCWorker::MsgDeviceTrack *msg = AFCWorker::MsgDeviceTrack::create(); AFCWorker::MsgDeviceTrack *msg = AFCWorker::MsgDeviceTrack::create();
m_worker->getInputMessageQueue()->push(msg); m_worker->getInputMessageQueue()->push(msg);
@ -166,7 +198,7 @@ bool AFC::handleMessage(const Message& cmd)
removeTrackedFeatureReferences(); removeTrackedFeatureReferences();
trackedDeviceChange(m_settings.m_trackedDeviceSetIndex); trackedDeviceChange(m_settings.m_trackedDeviceSetIndex);
if (m_worker->isRunning()) if (m_running)
{ {
AFCWorker::MsgDevicesApply *msg = AFCWorker::MsgDevicesApply::create(); AFCWorker::MsgDevicesApply *msg = AFCWorker::MsgDevicesApply::create();
m_worker->getInputMessageQueue()->push(msg); m_worker->getInputMessageQueue()->push(msg);
@ -262,10 +294,13 @@ void AFC::applySettings(const AFCSettings& settings, bool force)
trackedDeviceChange(settings.m_trackedDeviceSetIndex); trackedDeviceChange(settings.m_trackedDeviceSetIndex);
} }
if (m_running)
{
AFCWorker::MsgConfigureAFCWorker *msg = AFCWorker::MsgConfigureAFCWorker::create( AFCWorker::MsgConfigureAFCWorker *msg = AFCWorker::MsgConfigureAFCWorker::create(
settings, force settings, force
); );
m_worker->getInputMessageQueue()->push(msg); m_worker->getInputMessageQueue()->push(msg);
}
if (settings.m_useReverseAPI) if (settings.m_useReverseAPI)
{ {
@ -536,9 +571,12 @@ void AFC::webapiUpdateFeatureSettings(
void AFC::webapiFormatFeatureReport(SWGSDRangel::SWGFeatureReport& response) void AFC::webapiFormatFeatureReport(SWGSDRangel::SWGFeatureReport& response)
{ {
response.getAfcReport()->setTrackerChannelIndex(m_trackerIndexInDeviceSet); response.getAfcReport()->setTrackerChannelIndex(m_trackerIndexInDeviceSet);
response.getAfcReport()->setRunningState(getState());
if (m_running) {
response.getAfcReport()->setTrackerDeviceFrequency(m_worker->getTrackerDeviceFrequency()); response.getAfcReport()->setTrackerDeviceFrequency(m_worker->getTrackerDeviceFrequency());
response.getAfcReport()->setTrackerChannelOffset(m_worker->getTrackerChannelOffset()); response.getAfcReport()->setTrackerChannelOffset(m_worker->getTrackerChannelOffset());
response.getAfcReport()->setRunningState(getState()); }
} }
void AFC::webapiReverseSendSettings(QList<QString>& channelSettingsKeys, const AFCSettings& settings, bool force) void AFC::webapiReverseSendSettings(QList<QString>& channelSettingsKeys, const AFCSettings& settings, bool force)

View File

@ -18,8 +18,8 @@
#ifndef INCLUDE_FEATURE_AFC_H_ #ifndef INCLUDE_FEATURE_AFC_H_
#define INCLUDE_FEATURE_AFC_H_ #define INCLUDE_FEATURE_AFC_H_
#include <QThread>
#include <QNetworkRequest> #include <QNetworkRequest>
#include <QMutex>
#include "feature/feature.h" #include "feature/feature.h"
#include "util/message.h" #include "util/message.h"
@ -31,6 +31,7 @@ class QNetworkReply;
class WebAPIAdapterInterface; class WebAPIAdapterInterface;
class DeviceSet; class DeviceSet;
class AFCWorker; class AFCWorker;
class QThread;
namespace SWGSDRangel { namespace SWGSDRangel {
class SWGDeviceState; class SWGDeviceState;
@ -201,7 +202,9 @@ public:
static const char* const m_featureId; static const char* const m_featureId;
private: private:
QThread m_thread; QThread *m_thread;
QMutex m_mutex;
bool m_running;
AFCWorker *m_worker; AFCWorker *m_worker;
AFCSettings m_settings; AFCSettings m_settings;
DeviceSet *m_trackerDeviceSet; DeviceSet *m_trackerDeviceSet;

View File

@ -42,7 +42,6 @@ MESSAGE_CLASS_DEFINITION(AFCWorker::MsgDevicesApply, Message)
AFCWorker::AFCWorker(WebAPIAdapterInterface *webAPIAdapterInterface) : AFCWorker::AFCWorker(WebAPIAdapterInterface *webAPIAdapterInterface) :
m_webAPIAdapterInterface(webAPIAdapterInterface), m_webAPIAdapterInterface(webAPIAdapterInterface),
m_msgQueueToGUI(nullptr), m_msgQueueToGUI(nullptr),
m_running(false),
m_freqTracker(nullptr), m_freqTracker(nullptr),
m_trackerDeviceFrequency(0), m_trackerDeviceFrequency(0),
m_trackerChannelOffset(0), m_trackerChannelOffset(0),
@ -59,6 +58,7 @@ AFCWorker::AFCWorker(WebAPIAdapterInterface *webAPIAdapterInterface) :
AFCWorker::~AFCWorker() AFCWorker::~AFCWorker()
{ {
m_inputMessageQueue.clear(); m_inputMessageQueue.clear();
stopWork();
} }
void AFCWorker::reset() void AFCWorker::reset()
@ -67,19 +67,16 @@ void AFCWorker::reset()
m_inputMessageQueue.clear(); m_inputMessageQueue.clear();
} }
bool AFCWorker::startWork() void AFCWorker::startWork()
{ {
QMutexLocker mutexLocker(&m_mutex); QMutexLocker mutexLocker(&m_mutex);
connect(&m_inputMessageQueue, SIGNAL(messageEnqueued()), this, SLOT(handleInputMessages())); connect(&m_inputMessageQueue, SIGNAL(messageEnqueued()), this, SLOT(handleInputMessages()));
m_running = true;
return m_running;
} }
void AFCWorker::stopWork() void AFCWorker::stopWork()
{ {
QMutexLocker mutexLocker(&m_mutex); QMutexLocker mutexLocker(&m_mutex);
disconnect(&m_inputMessageQueue, SIGNAL(messageEnqueued()), this, SLOT(handleInputMessages())); disconnect(&m_inputMessageQueue, SIGNAL(messageEnqueued()), this, SLOT(handleInputMessages()));
m_running = false;
} }
void AFCWorker::handleInputMessages() void AFCWorker::handleInputMessages()

View File

@ -107,9 +107,8 @@ public:
AFCWorker(WebAPIAdapterInterface *webAPIAdapterInterface); AFCWorker(WebAPIAdapterInterface *webAPIAdapterInterface);
~AFCWorker(); ~AFCWorker();
void reset(); void reset();
bool startWork(); void startWork();
void stopWork(); void stopWork();
bool isRunning() const { return m_running; }
MessageQueue *getInputMessageQueue() { return &m_inputMessageQueue; } MessageQueue *getInputMessageQueue() { return &m_inputMessageQueue; }
void setMessageQueueToGUI(MessageQueue *messageQueue) { m_msgQueueToGUI = messageQueue; } void setMessageQueueToGUI(MessageQueue *messageQueue) { m_msgQueueToGUI = messageQueue; }
uint64_t getTrackerDeviceFrequency() const { return m_trackerDeviceFrequency; } uint64_t getTrackerDeviceFrequency() const { return m_trackerDeviceFrequency; }
@ -145,7 +144,6 @@ private:
MessageQueue m_inputMessageQueue; //!< Queue for asynchronous inbound communication MessageQueue m_inputMessageQueue; //!< Queue for asynchronous inbound communication
MessageQueue *m_msgQueueToGUI; //!< Queue to report state to GUI MessageQueue *m_msgQueueToGUI; //!< Queue to report state to GUI
AFCSettings m_settings; AFCSettings m_settings;
bool m_running;
DeviceSet *m_trackerDeviceSet; DeviceSet *m_trackerDeviceSet;
DeviceSet *m_trackedDeviceSet; DeviceSet *m_trackedDeviceSet;
ChannelAPI *m_freqTracker; ChannelAPI *m_freqTracker;

View File

@ -152,6 +152,7 @@ public:
MessageQueue *getMessageQueueToGUI() { return m_guiMessageQueue; } MessageQueue *getMessageQueueToGUI() { return m_guiMessageQueue; }
void setWorkspaceIndex(int index) { m_workspaceIndex = index; } void setWorkspaceIndex(int index) { m_workspaceIndex = index; }
int getWorkspaceIndex() const { return m_workspaceIndex; } int getWorkspaceIndex() const { return m_workspaceIndex; }
WebAPIAdapterInterface *getWebAPIAdapterInterface() { return m_webAPIAdapterInterface; }
protected: protected:
MessageQueue m_inputMessageQueue; MessageQueue m_inputMessageQueue;