Cleanup / re-factor. Pair audio thread with demod

This commit is contained in:
Charles J. Cliffe 2014-11-30 17:11:29 -05:00
parent be33bbce4c
commit 06513e2064
10 changed files with 87 additions and 65 deletions

View File

@ -108,12 +108,12 @@ void AppFrame::OnIdle(wxIdleEvent& event) {
wxGetApp().getAudioVisualQueue()->pop(demodAudioData);
if (demodAudioData.data.size()) {
if (scopeCanvas->waveform_points.size() != demodAudioData.data.size() * 2) {
scopeCanvas->waveform_points.resize(demodAudioData.data.size() * 2);
if (scopeCanvas->waveform_points.size() != demodAudioData.data.size()) {
scopeCanvas->waveform_points.resize(demodAudioData.data.size());
}
for (int i = 0, iMax = demodAudioData.data.size(); i < iMax; i++) {
scopeCanvas->waveform_points[i * 2 + 1] = demodAudioData.data[i] * 0.5f;
for (int i = 0, iMax = demodAudioData.data.size()/2; i < iMax; i++) {
scopeCanvas->waveform_points[i * 2 + 1] = demodAudioData.data[i*2] * 0.5f;
scopeCanvas->waveform_points[i * 2] = ((double) i / (double) iMax);
}

View File

@ -21,13 +21,7 @@ bool CubicSDR::OnInit() {
frequency = DEFAULT_FREQ;
audioInputQueue = new AudioThreadInputQueue;
audioThread = new AudioThread(audioInputQueue);
threadAudio = new std::thread(&AudioThread::threadMain, audioThread);
demodulatorTest = demodMgr.newThread();
demodulatorTest->getParams().audioInputQueue = audioInputQueue;
demodulatorTest->getParams().frequency = DEFAULT_FREQ;
demodulatorTest->run();
@ -48,8 +42,8 @@ bool CubicSDR::OnInit() {
sdrPostThread->bindDemodulator(demodulatorTest);
threadPostSDR = new std::thread(&SDRPostThread::threadMain, sdrPostThread);
threadSDR = new std::thread(&SDRThread::threadMain, sdrThread);
t_PostSDR = new std::thread(&SDRPostThread::threadMain, sdrPostThread);
t_SDR = new std::thread(&SDRThread::threadMain, sdrThread);
AppFrame *appframe = new AppFrame();
@ -59,26 +53,21 @@ bool CubicSDR::OnInit() {
int CubicSDR::OnExit() {
std::cout << "Terminating SDR thread.." << std::endl;
sdrThread->terminate();
threadSDR->join();
t_SDR->join();
std::cout << "Terminating SDR post-processing thread.." << std::endl;
sdrPostThread->terminate();
threadPostSDR->join();
t_PostSDR->join();
delete sdrThread;
delete threadSDR;
delete t_SDR;
delete sdrPostThread;
delete threadPostSDR;
delete t_PostSDR;
demodMgr.terminateAll();
audioThread->terminate();
threadAudio->join();
delete audioThread;
delete threadAudio;
delete audioInputQueue;
delete threadCmdQueueSDR;
delete iqVisualQueue;

View File

@ -17,8 +17,10 @@
class CubicSDR: public wxApp {
public:
CubicSDR() {
m_glContext = NULL;
CubicSDR() :
m_glContext(NULL), t_PostSDR(NULL), t_SDR(NULL), audioVisualQueue(NULL), threadCmdQueueSDR(NULL), iqVisualQueue(NULL), frequency(
DEFAULT_FREQ), sdrPostThread(NULL), iqPostDataQueue(NULL), sdrThread(NULL), demodulatorTest(NULL) {
}
PrimaryGLContext &GetContext(wxGLCanvas *canvas);
@ -54,19 +56,16 @@ private:
DemodulatorInstance *demodulatorTest;
AudioThreadInputQueue *audioInputQueue;
AudioThread *audioThread;
SDRThread *sdrThread;
SDRPostThread *sdrPostThread;
SDRThreadCommandQueue* threadCmdQueueSDR;
SDRThreadIQDataQueue* iqVisualQueue;
SDRThreadIQDataQueue* iqPostDataQueue;
DemodulatorThreadOutputQueue* audioVisualQueue;
std::thread *threadAudio;
std::thread *threadSDR;
std::thread *threadPostSDR;
std::thread *t_SDR;
std::thread *t_PostSDR;
};
DECLARE_APP(CubicSDR)

View File

@ -8,19 +8,16 @@ AudioThread::AudioThread(AudioThreadInputQueue *inputQueue) :
}
AudioThread::~AudioThread() {
PaError err;
err = Pa_StopStream(stream);
err = Pa_CloseStream(stream);
Pa_Terminate();
std::cout << std::endl << "Audio Thread Done." << std::endl << std::endl;
}
void AudioThread::threadMain() {
std::cout << "Audio thread initializing.." << std::endl;
PaError err;
err = Pa_Initialize();
if (err != paNoError) {
std::cout << "Error starting portaudio :(\n";
std::cout << "Error starting portaudio :(" << std::endl;
return;
}
@ -58,10 +55,15 @@ void AudioThread::threadMain() {
Pa_WriteStream(stream, &inp.data[0], inp.data.size()/2);
}
}
err = Pa_StopStream(stream);
err = Pa_CloseStream(stream);
Pa_Terminate();
std::cout << "Audio thread done." << std::endl;
}
void AudioThread::terminate() {
std::cout << "Terminating audio thread.." << std::endl;
terminated = true;
AudioThreadInput endCond; // push an empty input to bump the queue
inputQueue->push(endCond);

View File

@ -1,16 +1,23 @@
#include <DemodulatorMgr.h>
DemodulatorInstance::DemodulatorInstance() :
t_Demod(NULL), threadQueueDemod(NULL), demodulatorThread(NULL) {
t_Demod(NULL), t_Audio(NULL), threadQueueDemod(NULL), demodulatorThread(NULL) {
threadQueueDemod = new DemodulatorThreadInputQueue;
threadQueueCommand = new DemodulatorThreadCommandQueue;
demodulatorThread = new DemodulatorThread(threadQueueDemod);
demodulatorThread->setCommandQueue(threadQueueCommand);
audioInputQueue = new AudioThreadInputQueue;
audioThread = new AudioThread(audioInputQueue);
demodulatorThread->setAudioInputQueue(audioInputQueue);
}
DemodulatorInstance::~DemodulatorInstance() {
delete audioThread;
delete t_Audio;
delete audioInputQueue;
delete threadQueueDemod;
delete demodulatorThread;
delete t_Demod;
@ -23,16 +30,26 @@ void DemodulatorInstance::setVisualOutputQueue(DemodulatorThreadOutputQueue *tQu
void DemodulatorInstance::run() {
if (t_Demod) {
terminate();
delete threadQueueDemod;
delete demodulatorThread;
delete t_Demod;
delete audioThread;
delete audioInputQueue;
delete t_Audio;
threadQueueDemod = new DemodulatorThreadInputQueue;
threadQueueCommand = new DemodulatorThreadCommandQueue;
demodulatorThread = new DemodulatorThread(threadQueueDemod);
demodulatorThread->setCommandQueue(threadQueueCommand);
audioInputQueue = new AudioThreadInputQueue;
audioThread = new AudioThread(audioInputQueue);
demodulatorThread->setAudioInputQueue(audioInputQueue);
}
t_Audio = new std::thread(&AudioThread::threadMain, audioThread);
t_Demod = new std::thread(&DemodulatorThread::threadMain, demodulatorThread);
}
@ -45,8 +62,13 @@ DemodulatorThreadParameters &DemodulatorInstance::getParams() {
}
void DemodulatorInstance::terminate() {
std::cout << "Terminating demodulator thread.." << std::endl;
demodulatorThread->terminate();
t_Demod->join();
std::cout << "Terminating demodulator audio thread.." << std::endl;
audioThread->terminate();
t_Audio->join();
}
DemodulatorMgr::DemodulatorMgr() {

View File

@ -2,20 +2,27 @@
#include <vector>
#include <map>
#include <thread>
#include "DemodulatorThread.h"
class DemodulatorInstance {
public:
DemodulatorThread *demodulatorThread;
std::thread *t_Demod;
DemodulatorThreadInputQueue* threadQueueDemod;
DemodulatorThreadCommandQueue* threadQueueCommand;
DemodulatorThread *demodulatorThread;
std::thread *t_Demod;
AudioThreadInputQueue *audioInputQueue;
AudioThread *audioThread;
std::thread *t_Audio;
DemodulatorInstance();
~DemodulatorInstance();
void setVisualOutputQueue(DemodulatorThreadOutputQueue *tQueue);
DemodulatorThreadCommandQueue *getCommandQueue();
DemodulatorThreadParameters &getParams();

View File

@ -66,7 +66,6 @@ void DemodulatorThread::initialize() {
}
DemodulatorThread::~DemodulatorThread() {
std::cout << std::endl << "Demodulator Thread Done." << std::endl << std::endl;
}
void DemodulatorThread::threadMain() {
@ -75,6 +74,7 @@ void DemodulatorThread::threadMain() {
initialize();
}
std::cout << "Demodulator thread started.." << std::endl;
while (!terminated) {
DemodulatorThreadIQData inp;
inputQueue->pop(inp);
@ -200,8 +200,8 @@ void DemodulatorThread::threadMain() {
AudioThreadInput ati;
ati.data = newBuffer;
if (params.audioInputQueue != NULL) {
params.audioInputQueue->push(ati);
if (audioInputQueue != NULL) {
audioInputQueue->push(ati);
}
if (visOutQueue != NULL) {
@ -209,10 +209,11 @@ void DemodulatorThread::threadMain() {
}
}
}
std::cout << "Demodulator thread done." << std::endl;
}
void DemodulatorThread::terminate() {
std::cout << "Terminating demodulator thread.." << std::endl;
terminated = true;
DemodulatorThreadIQData inp; // push dummy to nudge queue
inputQueue->push(inp);

View File

@ -19,19 +19,19 @@ enum DemodulatorType {
DEMOD_TYPE_NULL, DEMOD_TYPE_AM, DEMOD_TYPE_FM, DEMOD_TYPE_LSB, DEMOD_TYPE_USB
};
class DemodulatorThreadCommand {
class DemodulatorThreadCommand {
public:
enum DemodulatorThreadCommandEnum {
SDR_THREAD_CMD_NULL,
SDR_THREAD_CMD_SET_BANDWIDTH,
SDR_THREAD_CMD_SET_FREQUENCY
enum DemodulatorThreadCommandEnum {
SDR_THREAD_CMD_NULL, SDR_THREAD_CMD_SET_BANDWIDTH, SDR_THREAD_CMD_SET_FREQUENCY
};
DemodulatorThreadCommand() : cmd(cmd), int_value(SDR_THREAD_CMD_NULL) {
DemodulatorThreadCommand() :
cmd(cmd), int_value(SDR_THREAD_CMD_NULL) {
}
DemodulatorThreadCommand(DemodulatorThreadCommandEnum cmd) : cmd(cmd), int_value(0) {
DemodulatorThreadCommand(DemodulatorThreadCommandEnum cmd) :
cmd(cmd), int_value(0) {
}
@ -39,7 +39,6 @@ public:
int int_value;
};
class DemodulatorThreadIQData {
public:
unsigned int frequency;
@ -90,12 +89,11 @@ public:
unsigned int inputRate;
unsigned int bandwidth; // set equal to disable second stage re-sampling?
unsigned int audioSampleRate;
AudioThreadInputQueue *audioInputQueue;
DemodulatorType demodType;
DemodulatorThreadParameters() :
frequency(0), audioInputQueue(NULL), inputRate(SRATE), bandwidth(200000), audioSampleRate(AUDIO_FREQUENCY), demodType(DEMOD_TYPE_FM) {
frequency(0), inputRate(SRATE), bandwidth(200000), audioSampleRate(AUDIO_FREQUENCY), demodType(DEMOD_TYPE_FM) {
}
@ -125,6 +123,10 @@ public:
commandQueue = tQueue;
}
void setAudioInputQueue(AudioThreadInputQueue *tQueue) {
audioInputQueue = tQueue;
}
DemodulatorThreadParameters &getParams() {
return params;
}
@ -137,6 +139,7 @@ protected:
DemodulatorThreadInputQueue* inputQueue;
DemodulatorThreadOutputQueue* visOutQueue;
DemodulatorThreadCommandQueue* commandQueue;
AudioThreadInputQueue *audioInputQueue;
firfilt_crcf fir_filter;
@ -153,7 +156,6 @@ protected:
nco_crcf nco_shift;
int shift_freq;
std::atomic<bool> terminated;
std::atomic<bool> initialized;
};

View File

@ -10,14 +10,10 @@ SDRPostThread::SDRPostThread() :
}
SDRPostThread::~SDRPostThread() {
std::cout << std::endl << "SDR post-process thread done." << std::endl << std::endl;
rtlsdr_close(dev);
}
void SDRPostThread::threadMain() {
std::cout << "SDR post-process thread starting.." << std::endl;
int n_read;
double seconds = 0.0;
@ -25,7 +21,8 @@ void SDRPostThread::threadMain() {
liquid_float_complex x, y;
std::cout << "Sampling..";
std::cout << "SDR post-processing thread started.." << std::endl;
while (!terminated) {
SDRThreadIQData data_in;
@ -70,9 +67,11 @@ void SDRPostThread::threadMain() {
}
}
}
std::cout << "SDR post-processing thread done." << std::endl;
}
void SDRPostThread::terminate() {
terminated = true;
SDRThreadIQData dummy;
iqDataInQueue.load()->push(dummy);
}

View File

@ -10,7 +10,6 @@ SDRThread::SDRThread(SDRThreadCommandQueue* pQueue) :
}
SDRThread::~SDRThread() {
std::cout << std::endl << "SDR Thread Done." << std::endl << std::endl;
rtlsdr_close(dev);
}
@ -91,6 +90,8 @@ int SDRThread::enumerate_rtl() {
void SDRThread::threadMain() {
std::cout << "SDR thread initializing.." << std::endl;
int dev_count = rtlsdr_get_device_count();
int first_available = enumerate_rtl();
@ -120,7 +121,7 @@ void SDRThread::threadMain() {
int n_read;
double seconds = 0.0;
std::cout << "Sampling..";
std::cout << "SDR thread started.." << std::endl;
while (!terminated) {
SDRThreadCommandQueue *cmdQueue = m_pQueue.load();
@ -167,7 +168,7 @@ void SDRThread::threadMain() {
iqDataOutQueue.load()->push(dataOut);
}
}
std::cout << "SDR thread done." << std::endl;
}
void SDRThread::terminate() {