mirror of
https://github.com/f4exb/sdrangel.git
synced 2025-09-04 22:27:53 -04:00
Remote input buffer size rework: member name changes. Adjust sample sink fifo size from sample rate
This commit is contained in:
parent
b7284b6b5c
commit
16364d604a
@ -48,13 +48,16 @@ MESSAGE_CLASS_DEFINITION(RemoteInput::MsgStartStop, Message)
|
|||||||
|
|
||||||
RemoteInput::RemoteInput(DeviceAPI *deviceAPI) :
|
RemoteInput::RemoteInput(DeviceAPI *deviceAPI) :
|
||||||
m_deviceAPI(deviceAPI),
|
m_deviceAPI(deviceAPI),
|
||||||
|
m_sampleRate(48000),
|
||||||
|
m_fileSink(nullptr),
|
||||||
m_settings(),
|
m_settings(),
|
||||||
m_remoteInputUDPHandler(0),
|
m_remoteInputUDPHandler(0),
|
||||||
m_deviceDescription(),
|
m_deviceDescription(),
|
||||||
m_startingTimeStamp(0)
|
m_startingTimeStamp(0)
|
||||||
{
|
{
|
||||||
m_sampleFifo.setSize(96000 * 4);
|
m_sampleFifo.setSize(m_sampleRate * 8);
|
||||||
m_remoteInputUDPHandler = new RemoteInputUDPHandler(&m_sampleFifo, m_deviceAPI);
|
m_remoteInputUDPHandler = new RemoteInputUDPHandler(&m_sampleFifo, m_deviceAPI);
|
||||||
|
m_remoteInputUDPHandler->setMessageQueueToInput(&m_inputMessageQueue);
|
||||||
|
|
||||||
m_fileSink = new FileRecord(QString("test_%1.sdriq").arg(m_deviceAPI->getDeviceUID()));
|
m_fileSink = new FileRecord(QString("test_%1.sdriq").arg(m_deviceAPI->getDeviceUID()));
|
||||||
m_deviceAPI->setNbSourceStreams(1);
|
m_deviceAPI->setNbSourceStreams(1);
|
||||||
@ -167,6 +170,21 @@ bool RemoteInput::handleMessage(const Message& message)
|
|||||||
DSPSignalNotification& notif = (DSPSignalNotification&) message;
|
DSPSignalNotification& notif = (DSPSignalNotification&) message;
|
||||||
return m_fileSink->handleMessage(notif); // forward to file sink
|
return m_fileSink->handleMessage(notif); // forward to file sink
|
||||||
}
|
}
|
||||||
|
else if (RemoteInputUDPHandler::MsgReportSampleRateChange::match(message))
|
||||||
|
{
|
||||||
|
RemoteInputUDPHandler::MsgReportSampleRateChange& notif = (RemoteInputUDPHandler::MsgReportSampleRateChange&) message;
|
||||||
|
int sampleRate = notif.getSampleRate();
|
||||||
|
|
||||||
|
if (sampleRate != m_sampleRate)
|
||||||
|
{
|
||||||
|
qDebug("RemoteInput::handleMessage: RemoteInputUDPHandler::MsgReportSampleRateChange: %d", sampleRate);
|
||||||
|
QMutexLocker mutexLocker(&m_mutex);
|
||||||
|
m_sampleFifo.setSize(sampleRate * 8);
|
||||||
|
m_sampleRate = sampleRate;
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
else if (MsgFileRecord::match(message))
|
else if (MsgFileRecord::match(message))
|
||||||
{
|
{
|
||||||
MsgFileRecord& conf = (MsgFileRecord&) message;
|
MsgFileRecord& conf = (MsgFileRecord&) message;
|
||||||
|
@ -329,6 +329,7 @@ public:
|
|||||||
|
|
||||||
private:
|
private:
|
||||||
DeviceAPI *m_deviceAPI;
|
DeviceAPI *m_deviceAPI;
|
||||||
|
int m_sampleRate;
|
||||||
QMutex m_mutex;
|
QMutex m_mutex;
|
||||||
RemoteInputSettings m_settings;
|
RemoteInputSettings m_settings;
|
||||||
RemoteInputUDPHandler* m_remoteInputUDPHandler;
|
RemoteInputUDPHandler* m_remoteInputUDPHandler;
|
||||||
|
@ -27,7 +27,7 @@
|
|||||||
|
|
||||||
|
|
||||||
RemoteInputBuffer::RemoteInputBuffer() :
|
RemoteInputBuffer::RemoteInputBuffer() :
|
||||||
m_decoderIndexHead(nbDecoderSlots/2),
|
m_decoderIndexHead(m_nbDecoderSlots/2),
|
||||||
m_frameHead(0),
|
m_frameHead(0),
|
||||||
m_curNbBlocks(0),
|
m_curNbBlocks(0),
|
||||||
m_minNbBlocks(256),
|
m_minNbBlocks(256),
|
||||||
@ -46,7 +46,7 @@ RemoteInputBuffer::RemoteInputBuffer() :
|
|||||||
m_balCorrLimit(0)
|
m_balCorrLimit(0)
|
||||||
{
|
{
|
||||||
m_currentMeta.init();
|
m_currentMeta.init();
|
||||||
m_framesNbBytes = nbDecoderSlots * sizeof(BufferFrame);
|
m_framesNbBytes = m_nbDecoderSlots * sizeof(BufferFrame);
|
||||||
m_wrDeltaEstimate = m_framesNbBytes / 2;
|
m_wrDeltaEstimate = m_framesNbBytes / 2;
|
||||||
m_tvOut_sec = 0;
|
m_tvOut_sec = 0;
|
||||||
m_tvOut_usec = 0;
|
m_tvOut_usec = 0;
|
||||||
@ -61,8 +61,8 @@ RemoteInputBuffer::RemoteInputBuffer() :
|
|||||||
m_cm256_OK = true;
|
m_cm256_OK = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::fill(m_decoderSlots, m_decoderSlots + nbDecoderSlots, DecoderSlot());
|
std::fill(m_decoderSlots, m_decoderSlots + m_nbDecoderSlots, DecoderSlot());
|
||||||
std::fill(m_frames, m_frames + nbDecoderSlots, BufferFrame());
|
std::fill(m_frames, m_frames + m_nbDecoderSlots, BufferFrame());
|
||||||
}
|
}
|
||||||
|
|
||||||
RemoteInputBuffer::~RemoteInputBuffer()
|
RemoteInputBuffer::~RemoteInputBuffer()
|
||||||
@ -74,7 +74,7 @@ RemoteInputBuffer::~RemoteInputBuffer()
|
|||||||
|
|
||||||
void RemoteInputBuffer::initDecodeAllSlots()
|
void RemoteInputBuffer::initDecodeAllSlots()
|
||||||
{
|
{
|
||||||
for (int i = 0; i < nbDecoderSlots; i++)
|
for (int i = 0; i < m_nbDecoderSlots; i++)
|
||||||
{
|
{
|
||||||
m_decoderSlots[i].m_blockCount = 0;
|
m_decoderSlots[i].m_blockCount = 0;
|
||||||
m_decoderSlots[i].m_originalCount = 0;
|
m_decoderSlots[i].m_originalCount = 0;
|
||||||
@ -124,7 +124,7 @@ void RemoteInputBuffer::initDecodeSlot(int slotIndex)
|
|||||||
|
|
||||||
void RemoteInputBuffer::initReadIndex()
|
void RemoteInputBuffer::initReadIndex()
|
||||||
{
|
{
|
||||||
m_readIndex = ((m_decoderIndexHead + (nbDecoderSlots/2)) % nbDecoderSlots) * sizeof(BufferFrame);
|
m_readIndex = ((m_decoderIndexHead + (m_nbDecoderSlots/2)) % m_nbDecoderSlots) * sizeof(BufferFrame);
|
||||||
m_wrDeltaEstimate = m_framesNbBytes / 2;
|
m_wrDeltaEstimate = m_framesNbBytes / 2;
|
||||||
m_nbReads = 0;
|
m_nbReads = 0;
|
||||||
m_nbWrites = 0;
|
m_nbWrites = 0;
|
||||||
@ -134,20 +134,20 @@ void RemoteInputBuffer::rwCorrectionEstimate(int slotIndex)
|
|||||||
{
|
{
|
||||||
if (m_nbReads >= 40) // check every ~1s as tick is ~50ms
|
if (m_nbReads >= 40) // check every ~1s as tick is ~50ms
|
||||||
{
|
{
|
||||||
int targetPivotSlot = (slotIndex + (nbDecoderSlots/2)) % nbDecoderSlots; // slot at half buffer opposite of current write slot
|
int targetPivotSlot = (slotIndex + (m_nbDecoderSlots/2)) % m_nbDecoderSlots; // slot at half buffer opposite of current write slot
|
||||||
int targetPivotIndex = targetPivotSlot * sizeof(BufferFrame); // buffer index corresponding to start of above slot
|
int targetPivotIndex = targetPivotSlot * sizeof(BufferFrame); // buffer index corresponding to start of above slot
|
||||||
int normalizedReadIndex = (m_readIndex < targetPivotIndex ? m_readIndex + nbDecoderSlots * sizeof(BufferFrame) : m_readIndex)
|
int normalizedReadIndex = (m_readIndex < targetPivotIndex ? m_readIndex + m_nbDecoderSlots * sizeof(BufferFrame) : m_readIndex)
|
||||||
- (targetPivotSlot * sizeof(BufferFrame)); // normalize read index so it is positive and zero at start of pivot slot
|
- (targetPivotSlot * sizeof(BufferFrame)); // normalize read index so it is positive and zero at start of pivot slot
|
||||||
int dBytes;
|
int dBytes;
|
||||||
int rwDelta = (m_nbReads * m_readNbBytes) - (m_nbWrites * sizeof(BufferFrame));
|
int rwDelta = (m_nbReads * m_readNbBytes) - (m_nbWrites * sizeof(BufferFrame));
|
||||||
|
|
||||||
if (normalizedReadIndex < (nbDecoderSlots/ 2) * (int) sizeof(BufferFrame)) // read leads
|
if (normalizedReadIndex < (m_nbDecoderSlots/ 2) * (int) sizeof(BufferFrame)) // read leads
|
||||||
{
|
{
|
||||||
dBytes = - normalizedReadIndex - rwDelta;
|
dBytes = - normalizedReadIndex - rwDelta;
|
||||||
}
|
}
|
||||||
else // read lags
|
else // read lags
|
||||||
{
|
{
|
||||||
int bufSize = (nbDecoderSlots * sizeof(BufferFrame));
|
int bufSize = (m_nbDecoderSlots * sizeof(BufferFrame));
|
||||||
dBytes = bufSize - normalizedReadIndex - rwDelta;
|
dBytes = bufSize - normalizedReadIndex - rwDelta;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -171,7 +171,7 @@ void RemoteInputBuffer::checkSlotData(int slotIndex)
|
|||||||
{
|
{
|
||||||
int pseudoWriteIndex = slotIndex * sizeof(BufferFrame);
|
int pseudoWriteIndex = slotIndex * sizeof(BufferFrame);
|
||||||
m_wrDeltaEstimate = pseudoWriteIndex - m_readIndex;
|
m_wrDeltaEstimate = pseudoWriteIndex - m_readIndex;
|
||||||
int rwDelayBytes = (m_wrDeltaEstimate > 0 ? m_wrDeltaEstimate : sizeof(BufferFrame) * nbDecoderSlots + m_wrDeltaEstimate);
|
int rwDelayBytes = (m_wrDeltaEstimate > 0 ? m_wrDeltaEstimate : sizeof(BufferFrame) * m_nbDecoderSlots + m_wrDeltaEstimate);
|
||||||
int sampleRate = m_currentMeta.m_sampleRate;
|
int sampleRate = m_currentMeta.m_sampleRate;
|
||||||
|
|
||||||
if (sampleRate > 0)
|
if (sampleRate > 0)
|
||||||
@ -195,7 +195,7 @@ void RemoteInputBuffer::writeData(char *array)
|
|||||||
{
|
{
|
||||||
RemoteSuperBlock *superBlock = (RemoteSuperBlock *) array;
|
RemoteSuperBlock *superBlock = (RemoteSuperBlock *) array;
|
||||||
int frameIndex = superBlock->m_header.m_frameIndex;
|
int frameIndex = superBlock->m_header.m_frameIndex;
|
||||||
int decoderIndex = frameIndex % nbDecoderSlots;
|
int decoderIndex = frameIndex % m_nbDecoderSlots;
|
||||||
|
|
||||||
// frame break
|
// frame break
|
||||||
|
|
||||||
@ -338,8 +338,8 @@ uint8_t *RemoteInputBuffer::readData(int32_t length)
|
|||||||
m_nbReads++;
|
m_nbReads++;
|
||||||
|
|
||||||
// SEGFAULT FIX: arbitratily truncate so that it does not exceed buffer length
|
// SEGFAULT FIX: arbitratily truncate so that it does not exceed buffer length
|
||||||
if (length > framesSize) {
|
if (length > m_framesSize) {
|
||||||
length = framesSize;
|
length = m_framesSize;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (m_readIndex + length < m_framesNbBytes) // ends before buffer bound
|
if (m_readIndex + length < m_framesNbBytes) // ends before buffer bound
|
||||||
|
@ -106,10 +106,9 @@ public:
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static const int framesSize = REMOTEINPUT_NBDECODERSLOTS * (RemoteNbOrginalBlocks - 1) * RemoteNbBytesPerBlock;
|
|
||||||
|
|
||||||
private:
|
private:
|
||||||
static const int nbDecoderSlots = REMOTEINPUT_NBDECODERSLOTS;
|
static const int m_framesSize = REMOTEINPUT_NBDECODERSLOTS * (RemoteNbOrginalBlocks - 1) * RemoteNbBytesPerBlock;
|
||||||
|
static const int m_nbDecoderSlots = REMOTEINPUT_NBDECODERSLOTS;
|
||||||
|
|
||||||
#pragma pack(push, 1)
|
#pragma pack(push, 1)
|
||||||
struct BufferFrame
|
struct BufferFrame
|
||||||
@ -133,8 +132,8 @@ private:
|
|||||||
|
|
||||||
RemoteMetaDataFEC m_currentMeta; //!< Stored current meta data
|
RemoteMetaDataFEC m_currentMeta; //!< Stored current meta data
|
||||||
CM256::cm256_encoder_params m_paramsCM256; //!< CM256 decoder parameters block
|
CM256::cm256_encoder_params m_paramsCM256; //!< CM256 decoder parameters block
|
||||||
DecoderSlot m_decoderSlots[nbDecoderSlots]; //!< CM256 decoding control/buffer slots
|
DecoderSlot m_decoderSlots[m_nbDecoderSlots]; //!< CM256 decoding control/buffer slots
|
||||||
BufferFrame m_frames[nbDecoderSlots]; //!< Samples buffer
|
BufferFrame m_frames[m_nbDecoderSlots]; //!< Samples buffer
|
||||||
int m_framesNbBytes; //!< Number of bytes in samples buffer
|
int m_framesNbBytes; //!< Number of bytes in samples buffer
|
||||||
int m_decoderIndexHead; //!< index of the current head frame slot in decoding slots
|
int m_decoderIndexHead; //!< index of the current head frame slot in decoding slots
|
||||||
int m_frameHead; //!< index of the current head frame sent
|
int m_frameHead; //!< index of the current head frame sent
|
||||||
|
@ -26,6 +26,8 @@
|
|||||||
#include "remoteinputudphandler.h"
|
#include "remoteinputudphandler.h"
|
||||||
#include "remoteinput.h"
|
#include "remoteinput.h"
|
||||||
|
|
||||||
|
MESSAGE_CLASS_DEFINITION(RemoteInputUDPHandler::MsgReportSampleRateChange, Message)
|
||||||
|
|
||||||
RemoteInputUDPHandler::RemoteInputUDPHandler(SampleSinkFifo *sampleFifo, DeviceAPI *deviceAPI) :
|
RemoteInputUDPHandler::RemoteInputUDPHandler(SampleSinkFifo *sampleFifo, DeviceAPI *deviceAPI) :
|
||||||
m_deviceAPI(deviceAPI),
|
m_deviceAPI(deviceAPI),
|
||||||
m_masterTimer(deviceAPI->getMasterTimer()),
|
m_masterTimer(deviceAPI->getMasterTimer()),
|
||||||
@ -43,7 +45,7 @@ RemoteInputUDPHandler::RemoteInputUDPHandler(SampleSinkFifo *sampleFifo, DeviceA
|
|||||||
m_samplerate(0),
|
m_samplerate(0),
|
||||||
m_centerFrequency(0),
|
m_centerFrequency(0),
|
||||||
m_tv_msec(0),
|
m_tv_msec(0),
|
||||||
m_outputMessageQueueToGUI(0),
|
m_messageQueueToGUI(0),
|
||||||
m_tickCount(0),
|
m_tickCount(0),
|
||||||
m_samplesCount(0),
|
m_samplesCount(0),
|
||||||
m_timer(0),
|
m_timer(0),
|
||||||
@ -189,6 +191,12 @@ void RemoteInputUDPHandler::processData()
|
|||||||
|
|
||||||
if (m_samplerate != metaData.m_sampleRate)
|
if (m_samplerate != metaData.m_sampleRate)
|
||||||
{
|
{
|
||||||
|
if (m_messageQueueToInput)
|
||||||
|
{
|
||||||
|
MsgReportSampleRateChange *msg = MsgReportSampleRateChange::create(metaData.m_sampleRate);
|
||||||
|
m_messageQueueToInput->push(msg);
|
||||||
|
}
|
||||||
|
|
||||||
m_samplerate = metaData.m_sampleRate;
|
m_samplerate = metaData.m_sampleRate;
|
||||||
change = true;
|
change = true;
|
||||||
}
|
}
|
||||||
@ -200,14 +208,14 @@ void RemoteInputUDPHandler::processData()
|
|||||||
DSPSignalNotification *notif = new DSPSignalNotification(m_samplerate, m_centerFrequency); // Frequency in Hz for the DSP engine
|
DSPSignalNotification *notif = new DSPSignalNotification(m_samplerate, m_centerFrequency); // Frequency in Hz for the DSP engine
|
||||||
m_deviceAPI->getDeviceEngineInputMessageQueue()->push(notif);
|
m_deviceAPI->getDeviceEngineInputMessageQueue()->push(notif);
|
||||||
|
|
||||||
if (m_outputMessageQueueToGUI)
|
if (m_messageQueueToGUI)
|
||||||
{
|
{
|
||||||
RemoteInput::MsgReportRemoteInputStreamData *report = RemoteInput::MsgReportRemoteInputStreamData::create(
|
RemoteInput::MsgReportRemoteInputStreamData *report = RemoteInput::MsgReportRemoteInputStreamData::create(
|
||||||
m_samplerate,
|
m_samplerate,
|
||||||
m_centerFrequency, // Frequency in Hz for the GUI
|
m_centerFrequency, // Frequency in Hz for the GUI
|
||||||
m_tv_msec);
|
m_tv_msec);
|
||||||
|
|
||||||
m_outputMessageQueueToGUI->push(report);
|
m_messageQueueToGUI->push(report);
|
||||||
}
|
}
|
||||||
|
|
||||||
connectTimer();
|
connectTimer();
|
||||||
@ -326,7 +334,7 @@ void RemoteInputUDPHandler::tick()
|
|||||||
{
|
{
|
||||||
m_tickCount = 0;
|
m_tickCount = 0;
|
||||||
|
|
||||||
if (m_outputMessageQueueToGUI)
|
if (m_messageQueueToGUI)
|
||||||
{
|
{
|
||||||
int framesDecodingStatus;
|
int framesDecodingStatus;
|
||||||
int minNbBlocks = m_remoteInputBuffer.getMinNbBlocks();
|
int minNbBlocks = m_remoteInputBuffer.getMinNbBlocks();
|
||||||
@ -362,7 +370,7 @@ void RemoteInputUDPHandler::tick()
|
|||||||
sampleBits,
|
sampleBits,
|
||||||
sampleBytes);
|
sampleBytes);
|
||||||
|
|
||||||
m_outputMessageQueueToGUI->push(report);
|
m_messageQueueToGUI->push(report);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -37,10 +37,31 @@ class RemoteInputUDPHandler : public QObject
|
|||||||
{
|
{
|
||||||
Q_OBJECT
|
Q_OBJECT
|
||||||
public:
|
public:
|
||||||
|
class MsgReportSampleRateChange : public Message {
|
||||||
|
MESSAGE_CLASS_DECLARATION
|
||||||
|
|
||||||
|
public:
|
||||||
|
int getSampleRate() const { return m_sampleRate; }
|
||||||
|
|
||||||
|
static MsgReportSampleRateChange* create(int sampleRate)
|
||||||
|
{
|
||||||
|
return new MsgReportSampleRateChange(sampleRate);
|
||||||
|
}
|
||||||
|
|
||||||
|
protected:
|
||||||
|
int m_sampleRate;
|
||||||
|
|
||||||
|
MsgReportSampleRateChange(int sampleRate) :
|
||||||
|
Message(),
|
||||||
|
m_sampleRate(sampleRate)
|
||||||
|
{ }
|
||||||
|
};
|
||||||
|
|
||||||
RemoteInputUDPHandler(SampleSinkFifo* sampleFifo, DeviceAPI *deviceAPI);
|
RemoteInputUDPHandler(SampleSinkFifo* sampleFifo, DeviceAPI *deviceAPI);
|
||||||
~RemoteInputUDPHandler();
|
~RemoteInputUDPHandler();
|
||||||
void setMessageQueueToGUI(MessageQueue *queue) { m_outputMessageQueueToGUI = queue; }
|
void setMessageQueueToInput(MessageQueue *queue) { m_messageQueueToInput = queue; }
|
||||||
void start();
|
void setMessageQueueToGUI(MessageQueue *queue) { m_messageQueueToGUI = queue; }
|
||||||
|
void start();
|
||||||
void stop();
|
void stop();
|
||||||
void configureUDPLink(const QString& address, quint16 port);
|
void configureUDPLink(const QString& address, quint16 port);
|
||||||
void getRemoteAddress(QString& s) const { s = m_remoteAddress.toString(); }
|
void getRemoteAddress(QString& s) const { s = m_remoteAddress.toString(); }
|
||||||
@ -73,7 +94,8 @@ private:
|
|||||||
uint32_t m_samplerate;
|
uint32_t m_samplerate;
|
||||||
uint64_t m_centerFrequency;
|
uint64_t m_centerFrequency;
|
||||||
uint64_t m_tv_msec;
|
uint64_t m_tv_msec;
|
||||||
MessageQueue *m_outputMessageQueueToGUI;
|
MessageQueue *m_messageQueueToInput;
|
||||||
|
MessageQueue *m_messageQueueToGUI;
|
||||||
uint32_t m_tickCount;
|
uint32_t m_tickCount;
|
||||||
std::size_t m_samplesCount;
|
std::size_t m_samplesCount;
|
||||||
QTimer *m_timer;
|
QTimer *m_timer;
|
||||||
|
Loading…
x
Reference in New Issue
Block a user