diff --git a/devices/limesdr/devicelimesdrshared.h b/devices/limesdr/devicelimesdrshared.h index e10855442..24fd4e2c6 100644 --- a/devices/limesdr/devicelimesdrshared.h +++ b/devices/limesdr/devicelimesdrshared.h @@ -52,6 +52,7 @@ public: public: virtual void startWork() = 0; virtual void stopWork() = 0; + virtual void setDeviceSampleRate(int sampleRate) = 0; }; DeviceLimeSDRParams *m_deviceParams; //!< unique hardware device parameters diff --git a/plugins/samplesink/limesdroutput/limesdroutput.cpp b/plugins/samplesink/limesdroutput/limesdroutput.cpp index 368891b25..a3e732aa1 100644 --- a/plugins/samplesink/limesdroutput/limesdroutput.cpp +++ b/plugins/samplesink/limesdroutput/limesdroutput.cpp @@ -164,8 +164,8 @@ bool LimeSDROutput::openDevice() // set up the stream m_streamId.channel = m_deviceShared.m_channel; // channel number - m_streamId.fifoSize = 1024 * 128; // fifo size in samples - m_streamId.throughputVsLatency = 1.0; // optimize for max throughput + m_streamId.fifoSize = 5000000; // fifo size in samples + m_streamId.throughputVsLatency = 0.0; // optimize for max throughput m_streamId.isTx = true; // TX channel m_streamId.dataFmt = lms_stream_t::LMS_FMT_I12; // 12-bit integers @@ -576,6 +576,23 @@ bool LimeSDROutput::applySettings(const LimeSDROutputSettings& settings, bool fo m_settings.m_devSampleRate, 1<setDeviceSampleRate(m_settings.m_devSampleRate); + } + + const std::vector& sinkBuddies = m_deviceAPI->getSinkBuddies(); + std::vector::const_iterator itSink = sinkBuddies.begin(); + + for (; itSink != sinkBuddies.end(); ++itSink) + { + DeviceLimeSDRShared *buddySharedPtr = (DeviceLimeSDRShared *) (*itSink)->getBuddySharedPtr(); + + if (buddySharedPtr->m_thread) { + buddySharedPtr->m_thread->setDeviceSampleRate(m_settings.m_devSampleRate); + } + } } } @@ -703,11 +720,11 @@ bool LimeSDROutput::applySettings(const LimeSDROutputSettings& settings, bool fo m_settings.m_lpfBW, 0) < 0) { - qCritical("LimeSDROutput::applySettings: calibration failed on Rx channel %lu", m_deviceShared.m_channel); + qCritical("LimeSDROutput::applySettings: calibration failed on Tx channel %lu", m_deviceShared.m_channel); } else { - qDebug("LimeSDROutput::applySettings: calibration successful on Rx channel %lu", m_deviceShared.m_channel); + qDebug("LimeSDROutput::applySettings: calibration successful on Tx channel %lu", m_deviceShared.m_channel); } } diff --git a/plugins/samplesink/limesdroutput/limesdroutputgui.cpp b/plugins/samplesink/limesdroutput/limesdroutputgui.cpp index 73d1b5bba..def425a94 100644 --- a/plugins/samplesink/limesdroutput/limesdroutputgui.cpp +++ b/plugins/samplesink/limesdroutput/limesdroutputgui.cpp @@ -225,7 +225,7 @@ void LimeSDROutputGUI::handleMessagesToGUI() ui->fifoBar->setMaximum(report->getFifoSize()); ui->fifoBar->setValue(report->getFifoFilledCount()); - ui->fifoBar->setToolTip(tr("FIFO fill %1/%2 bytes").arg(QString::number(report->getFifoFilledCount())).arg(QString::number(report->getFifoSize()))); + ui->fifoBar->setToolTip(tr("FIFO fill %1/%2 samples").arg(QString::number(report->getFifoFilledCount())).arg(QString::number(report->getFifoSize()))); } else { @@ -382,7 +382,7 @@ void LimeSDROutputGUI::on_sampleRate_changed(quint64 value) setNCODisplay(); sendSettings();} -void LimeSDROutputGUI::on_hwDecim_currentIndexChanged(int index) +void LimeSDROutputGUI::on_hwInterp_currentIndexChanged(int index) { if ((index <0) || (index > 5)) return; @@ -391,7 +391,7 @@ void LimeSDROutputGUI::on_hwDecim_currentIndexChanged(int index) sendSettings(); } -void LimeSDROutputGUI::on_swDecim_currentIndexChanged(int index) +void LimeSDROutputGUI::on_swInterp_currentIndexChanged(int index) { if ((index <0) || (index > 5)) return; diff --git a/plugins/samplesink/limesdroutput/limesdroutputgui.h b/plugins/samplesink/limesdroutput/limesdroutputgui.h index 3cbd96f78..f47893579 100644 --- a/plugins/samplesink/limesdroutput/limesdroutputgui.h +++ b/plugins/samplesink/limesdroutput/limesdroutputgui.h @@ -79,8 +79,8 @@ private slots: void on_ncoEnable_toggled(bool checked); void on_ncoReset_clicked(bool checked); void on_sampleRate_changed(quint64 value); - void on_hwDecim_currentIndexChanged(int index); - void on_swDecim_currentIndexChanged(int index); + void on_hwInterp_currentIndexChanged(int index); + void on_swInterp_currentIndexChanged(int index); void on_lpf_changed(quint64 value); void on_lpFIREnable_toggled(bool checked); void on_lpFIR_changed(quint64 value); diff --git a/plugins/samplesink/limesdroutput/limesdroutputthread.cpp b/plugins/samplesink/limesdroutput/limesdroutputthread.cpp index 7a5d3c7e0..1f242ec7d 100644 --- a/plugins/samplesink/limesdroutput/limesdroutputthread.cpp +++ b/plugins/samplesink/limesdroutput/limesdroutputthread.cpp @@ -24,6 +24,7 @@ LimeSDROutputThread::LimeSDROutputThread(lms_stream_t* stream, SampleSourceFifo* m_running(false), m_stream(stream), m_sampleFifo(sampleFifo), + m_sampleRate(5000000), m_log2Interp(0), m_fcPos(LimeSDROutputSettings::FC_POS_CENTER) { @@ -66,7 +67,8 @@ void LimeSDROutputThread::setFcPos(int fcPos) void LimeSDROutputThread::run() { - int res; + int res, count, msleep, mdelta; + lms_stream_status_t streamStatus; lms_stream_meta_t metadata; //Use metadata for additional control over sample receive function behaviour metadata.flushPartialPacket = false; //Do not discard data remainder when read size differs from packet size @@ -81,15 +83,46 @@ void LimeSDROutputThread::run() qDebug("LimeSDROutputThread::run: stream started"); } + count = 0; + msleep = LIMESDROUTPUT_BLOCKSIZE/(m_sampleRate/1e6f); + mdelta = msleep/100; + msleep = (3*msleep)/4; // to start faster + while (m_running) { callback(m_buf, LIMESDROUTPUT_BLOCKSIZE); - if ((res = LMS_SendStream(m_stream, (void *) m_buf, LIMESDROUTPUT_BLOCKSIZE, &metadata, 1000)) < 0) + res = LMS_SendStream(m_stream, (void *) m_buf, LIMESDROUTPUT_BLOCKSIZE, &metadata, 1000); + + if (res < 0) { qCritical("LimeSDROutputThread::run write error: %s", strerror(errno)); break; } + else if (res != LIMESDROUTPUT_BLOCKSIZE) + { + qDebug("LimeSDROutputThread::run written %d/%d samples", res, LIMESDROUTPUT_BLOCKSIZE); + } + + usleep(msleep); + + if (count < 10) + { + count++; + } + else + { + if (LMS_GetStreamStatus(m_stream, &streamStatus) == 0) + { + if (streamStatus.fifoFilledCount < (4*streamStatus.fifoSize)/5) { // FIFO at 80% + msleep -= mdelta; + } else { + msleep += mdelta; + } + } + + count = 0; + } } if (LMS_StopStream(m_stream) < 0) { diff --git a/plugins/samplesink/limesdroutput/limesdroutputthread.h b/plugins/samplesink/limesdroutput/limesdroutputthread.h index 173caf7a9..a212d3b9b 100644 --- a/plugins/samplesink/limesdroutput/limesdroutputthread.h +++ b/plugins/samplesink/limesdroutput/limesdroutputthread.h @@ -27,7 +27,7 @@ #include "dsp/interpolators.h" #include "limesdr/devicelimesdrshared.h" -#define LIMESDROUTPUT_BLOCKSIZE (1<<14) //complex samples per buffer ~10k (16k) +#define LIMESDROUTPUT_BLOCKSIZE (1<<15) //complex samples per buffer ~10k (16k) class LimeSDROutputThread : public QThread, public DeviceLimeSDRShared::ThreadInterface { @@ -39,6 +39,7 @@ public: virtual void startWork(); virtual void stopWork(); + virtual void setDeviceSampleRate(int sampleRate) { m_sampleRate = sampleRate; } void setLog2Interpolation(unsigned int log2_ioterp); void setFcPos(int fcPos); @@ -51,6 +52,7 @@ private: qint16 m_buf[2*LIMESDROUTPUT_BLOCKSIZE]; //must hold I+Q values of each sample hence 2xcomplex size SampleSourceFifo* m_sampleFifo; + int m_sampleRate; unsigned int m_log2Interp; // soft decimation int m_fcPos; diff --git a/plugins/samplesource/limesdrinput/limesdrinputgui.cpp b/plugins/samplesource/limesdrinput/limesdrinputgui.cpp index 274104104..135f5a1e5 100644 --- a/plugins/samplesource/limesdrinput/limesdrinputgui.cpp +++ b/plugins/samplesource/limesdrinput/limesdrinputgui.cpp @@ -228,7 +228,7 @@ void LimeSDRInputGUI::handleMessagesToGUI() ui->fifoBar->setMaximum(report->getFifoSize()); ui->fifoBar->setValue(report->getFifoFilledCount()); - ui->fifoBar->setToolTip(tr("FIFO fill %1/%2 bytes").arg(QString::number(report->getFifoFilledCount())).arg(QString::number(report->getFifoSize()))); + ui->fifoBar->setToolTip(tr("FIFO fill %1/%2 samples").arg(QString::number(report->getFifoFilledCount())).arg(QString::number(report->getFifoSize()))); } else { diff --git a/plugins/samplesource/limesdrinput/limesdrinputthread.h b/plugins/samplesource/limesdrinput/limesdrinputthread.h index f01b80649..8237b5ca9 100644 --- a/plugins/samplesource/limesdrinput/limesdrinputthread.h +++ b/plugins/samplesource/limesdrinput/limesdrinputthread.h @@ -39,6 +39,7 @@ public: virtual void startWork(); virtual void stopWork(); + virtual void setDeviceSampleRate(int sampleRate) {} void setLog2Decimation(unsigned int log2_decim); void setFcPos(int fcPos);