SDRAngel  4.11.5
Developer docs for <a href="https://github.com/f4exb/sdrangel">SDRangel<\a>, an Open Source Qt5 / OpenGL 3.0+ SDR and signal analyzer frontend to various hardware.
Classes | Public Member Functions | Private Slots | Private Member Functions | Private Attributes | List of all members
BladeRF2Output Class Reference

#include <bladerf2output.h>

+ Inheritance diagram for BladeRF2Output:
+ Collaboration diagram for BladeRF2Output:

Classes

class  MsgConfigureBladeRF2
 
class  MsgReportGainRange
 
class  MsgStartStop
 

Public Member Functions

 BladeRF2Output (DeviceAPI *deviceAPI)
 
virtual ~BladeRF2Output ()
 
virtual void destroy ()
 
virtual void init ()
 initializations to be done when all collaborating objects are created and possibly connected More...
 
virtual bool start ()
 
virtual void stop ()
 
BladeRF2OutputThreadgetThread ()
 
void setThread (BladeRF2OutputThread *thread)
 
virtual QByteArray serialize () const
 
virtual bool deserialize (const QByteArray &data)
 
virtual void setMessageQueueToGUI (MessageQueue *queue)
 
virtual const QString & getDeviceDescription () const
 
virtual int getSampleRate () const
 Sample rate exposed by the sink. More...
 
virtual void setSampleRate (int sampleRate)
 For when the sink sample rate is set externally. More...
 
virtual quint64 getCenterFrequency () const
 Center frequency exposed by the sink. More...
 
virtual void setCenterFrequency (qint64 centerFrequency)
 
void getFrequencyRange (uint64_t &min, uint64_t &max, int &step)
 
void getSampleRateRange (int &min, int &max, int &step)
 
void getBandwidthRange (int &min, int &max, int &step)
 
void getGlobalGainRange (int &min, int &max, int &step)
 
virtual bool handleMessage (const Message &message)
 
virtual int webapiSettingsGet (SWGSDRangel::SWGDeviceSettings &response, QString &errorMessage)
 
virtual int webapiSettingsPutPatch (bool force, const QStringList &deviceSettingsKeys, SWGSDRangel::SWGDeviceSettings &response, QString &errorMessage)
 
virtual int webapiReportGet (SWGSDRangel::SWGDeviceReport &response, QString &errorMessage)
 
virtual int webapiRunGet (SWGSDRangel::SWGDeviceState &response, QString &errorMessage)
 
virtual int webapiRun (bool run, SWGSDRangel::SWGDeviceState &response, QString &errorMessage)
 
- Public Member Functions inherited from DeviceSampleSink
 DeviceSampleSink ()
 
virtual ~DeviceSampleSink ()
 
MessageQueuegetInputMessageQueue ()
 
MessageQueuegetMessageQueueToGUI ()
 
SampleSourceFifogetSampleFifo ()
 

Private Slots

void networkManagerFinished (QNetworkReply *reply)
 

Private Member Functions

bool openDevice ()
 
void closeDevice ()
 
BladeRF2OutputThreadfindThread ()
 
void moveThreadToBuddy ()
 
bool applySettings (const BladeRF2OutputSettings &settings, bool force)
 
int getNbChannels ()
 
bool setDeviceCenterFrequency (struct bladerf *dev, int requestedChannel, quint64 freq_hz, int loPpmTenths)
 
void webapiFormatDeviceSettings (SWGSDRangel::SWGDeviceSettings &response, const BladeRF2OutputSettings &settings)
 
void webapiFormatDeviceReport (SWGSDRangel::SWGDeviceReport &response)
 
void webapiReverseSendSettings (QList< QString > &deviceSettingsKeys, const BladeRF2OutputSettings &settings, bool force)
 
void webapiReverseSendStartStop (bool start)
 

Private Attributes

DeviceAPIm_deviceAPI
 
QMutex m_mutex
 
BladeRF2OutputSettings m_settings
 
struct bladerf * m_dev
 
BladeRF2OutputThreadm_thread
 
QString m_deviceDescription
 
DeviceBladeRF2Shared m_deviceShared
 
bool m_running
 
QNetworkAccessManager * m_networkManager
 
QNetworkRequest m_networkRequest
 

Additional Inherited Members

- Public Types inherited from DeviceSampleSink
enum  fcPos_t { FC_POS_INFRA = 0, FC_POS_SUPRA, FC_POS_CENTER }
 
- Static Public Member Functions inherited from DeviceSampleSink
static qint64 calculateDeviceCenterFrequency (quint64 centerFrequency, qint64 transverterDeltaFrequency, int log2Interp, fcPos_t fcPos, quint32 devSampleRate, bool transverterMode=false)
 
static qint64 calculateCenterFrequency (quint64 deviceCenterFrequency, qint64 transverterDeltaFrequency, int log2Interp, fcPos_t fcPos, quint32 devSampleRate, bool transverterMode=false)
 
static qint32 calculateFrequencyShift (int log2Interp, fcPos_t fcPos, quint32 devSampleRate)
 
- Protected Slots inherited from DeviceSampleSink
void handleInputMessages ()
 
- Protected Attributes inherited from DeviceSampleSink
SampleSourceFifo m_sampleSourceFifo
 
MessageQueue m_inputMessageQueue
 Input queue to the sink. More...
 
MessageQueuem_guiMessageQueue
 Input message queue to the GUI. More...
 

Detailed Description

Definition at line 36 of file bladerf2output.h.

Constructor & Destructor Documentation

◆ BladeRF2Output()

BladeRF2Output::BladeRF2Output ( DeviceAPI deviceAPI)

Definition at line 45 of file bladerf2output.cpp.

Referenced by BladeRF2Output::MsgReportGainRange::MsgReportGainRange().

45  :
46  m_deviceAPI(deviceAPI),
47  m_settings(),
48  m_dev(0),
49  m_thread(0),
50  m_deviceDescription("BladeRF2Output"),
51  m_running(false)
52 {
53  openDevice();
55  m_networkManager = new QNetworkAccessManager();
56  connect(m_networkManager, SIGNAL(finished(QNetworkReply*)), this, SLOT(networkManagerFinished(QNetworkReply*)));
57 }
void networkManagerFinished(QNetworkReply *reply)
BladeRF2OutputThread * m_thread
void setNbSinkStreams(uint32_t nbSinkStreams)
Definition: deviceapi.h:169
DeviceAPI * m_deviceAPI
QString m_deviceDescription
BladeRF2OutputSettings m_settings
struct bladerf * m_dev
QNetworkAccessManager * m_networkManager
+ Here is the caller graph for this function:

◆ ~BladeRF2Output()

BladeRF2Output::~BladeRF2Output ( )
virtual

Definition at line 59 of file bladerf2output.cpp.

References closeDevice(), m_networkManager, m_running, networkManagerFinished(), and stop().

Referenced by BladeRF2Output::MsgReportGainRange::MsgReportGainRange().

60 {
61  disconnect(m_networkManager, SIGNAL(finished(QNetworkReply*)), this, SLOT(networkManagerFinished(QNetworkReply*)));
62  delete m_networkManager;
63 
64  if (m_running) {
65  stop();
66  }
67 
68  closeDevice();
69 }
void networkManagerFinished(QNetworkReply *reply)
virtual void stop()
QNetworkAccessManager * m_networkManager
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

Member Function Documentation

◆ applySettings()

bool BladeRF2Output::applySettings ( const BladeRF2OutputSettings settings,
bool  force 
)
private

Definition at line 699 of file bladerf2output.cpp.

References DeviceBladeRF2Shared::MsgReportBuddyChange::create(), BladeRF2Output::MsgReportGainRange::create(), findThread(), DeviceBladeRF2::getDev(), DeviceAPI::getDeviceEngineInputMessageQueue(), DeviceAPI::getDeviceItemIndex(), BladeRF2OutputThread::getFifo(), getGlobalGainRange(), DeviceSampleSink::getMessageQueueToGUI(), getNbChannels(), DeviceAPI::getSinkBuddies(), DeviceAPI::getSourceBuddies(), BladeRF2OutputSettings::m_bandwidth, BladeRF2OutputSettings::m_biasTee, BladeRF2OutputSettings::m_centerFrequency, DeviceBladeRF2Shared::m_dev, m_deviceAPI, m_deviceShared, BladeRF2OutputSettings::m_devSampleRate, BladeRF2OutputSettings::m_globalGain, BladeRF2OutputSettings::m_log2Interp, BladeRF2OutputSettings::m_LOppmTenths, BladeRF2OutputSettings::m_reverseAPIAddress, BladeRF2OutputSettings::m_reverseAPIDeviceIndex, BladeRF2OutputSettings::m_reverseAPIPort, DeviceBladeRF2Shared::m_sampleFifoLengthInSeconds, DeviceBladeRF2Shared::m_sampleFifoMinSize, DeviceBladeRF2Shared::m_sampleFifoMinSize32, DeviceSampleSink::m_sampleSourceFifo, m_settings, BladeRF2OutputSettings::m_transverterDeltaFrequency, BladeRF2OutputSettings::m_transverterMode, BladeRF2OutputSettings::m_useReverseAPI, leansdr::max(), leansdr::min(), MessageQueue::push(), SampleSourceFifo::resize(), DeviceBladeRF2::setBiasTeeTx(), setDeviceCenterFrequency(), BladeRF2OutputThread::setFifo(), BladeRF2OutputThread::setLog2Interpolation(), and webapiReverseSendSettings().

Referenced by handleMessage(), init(), start(), and stop().

700 {
701  bool forwardChangeOwnDSP = false;
702  bool forwardChangeRxBuddies = false;
703  bool forwardChangeTxBuddies = false;
704  QList<QString> reverseAPIKeys;
705 
706  struct bladerf *dev = m_deviceShared.m_dev->getDev();
707  int requestedChannel = m_deviceAPI->getDeviceItemIndex();
708  int nbChannels = getNbChannels();
709  qint64 deviceCenterFrequency = settings.m_centerFrequency;
710  deviceCenterFrequency -= settings.m_transverterMode ? settings.m_transverterDeltaFrequency : 0;
711  deviceCenterFrequency = deviceCenterFrequency < 0 ? 0 : deviceCenterFrequency;
712 
713  if ((m_settings.m_devSampleRate != settings.m_devSampleRate) || (m_settings.m_log2Interp != settings.m_log2Interp) || force)
714  {
715  reverseAPIKeys.append("devSampleRate");
716  BladeRF2OutputThread *bladeRF2OutputThread = findThread();
717  SampleSourceFifo *fifo = 0;
718 
719  if (bladeRF2OutputThread)
720  {
721  fifo = bladeRF2OutputThread->getFifo(requestedChannel);
722  bladeRF2OutputThread->setFifo(requestedChannel, 0);
723  }
724 
725  int fifoSize;
726 
727  if (settings.m_log2Interp >= 5)
728  {
730  }
731  else
732  {
733  fifoSize = (std::max)(
736  }
737 
738  m_sampleSourceFifo.resize(fifoSize);
739 
740  if (fifo) {
741  bladeRF2OutputThread->setFifo(requestedChannel, &m_sampleSourceFifo);
742  }
743  }
744 
745  if ((m_settings.m_devSampleRate != settings.m_devSampleRate) || force)
746  {
747  forwardChangeOwnDSP = true;
748  forwardChangeRxBuddies = true;
749  forwardChangeTxBuddies = true;
750 
751  if (dev != 0)
752  {
753  unsigned int actualSamplerate;
754 
755  int status = bladerf_set_sample_rate(dev, BLADERF_CHANNEL_TX(requestedChannel),
756  settings.m_devSampleRate,
757  &actualSamplerate);
758 
759  if (status < 0)
760  {
761  qCritical("BladeRF2Output::applySettings: could not set sample rate: %d: %s",
762  settings.m_devSampleRate, bladerf_strerror(status));
763  }
764  else
765  {
766  qDebug() << "BladeRF2Output::applySettings: bladerf_set_sample_rate: actual sample rate is " << actualSamplerate;
767  }
768  }
769  }
770 
771  if ((m_settings.m_bandwidth != settings.m_bandwidth) || force)
772  {
773  reverseAPIKeys.append("bandwidth");
774  forwardChangeTxBuddies = true;
775 
776  if (dev != 0)
777  {
778  unsigned int actualBandwidth;
779  int status = bladerf_set_bandwidth(dev, BLADERF_CHANNEL_TX(requestedChannel), settings.m_bandwidth, &actualBandwidth);
780 
781  if(status < 0)
782  {
783  qCritical("BladeRF2Output::applySettings: could not set bandwidth: %d: %s",
784  settings.m_bandwidth, bladerf_strerror(status));
785  }
786  else
787  {
788  qDebug() << "BladeRF2Output::applySettings: bladerf_set_bandwidth: actual bandwidth is " << actualBandwidth;
789  }
790  }
791  }
792 
793  if ((m_settings.m_log2Interp != settings.m_log2Interp) || force)
794  {
795  reverseAPIKeys.append("log2Interp");
796  forwardChangeOwnDSP = true;
797  BladeRF2OutputThread *outputThread = findThread();
798 
799  if (outputThread != 0)
800  {
801  outputThread->setLog2Interpolation(requestedChannel, settings.m_log2Interp);
802  qDebug() << "BladeRF2Output::applySettings: set interpolation to " << (1<<settings.m_log2Interp);
803  }
804  }
805 
806  if ((m_settings.m_centerFrequency != settings.m_centerFrequency) || force) {
807  reverseAPIKeys.append("centerFrequency");
808  }
809  if ((m_settings.m_transverterMode != settings.m_transverterMode) || force) {
810  reverseAPIKeys.append("transverterMode");
811  }
813  reverseAPIKeys.append("transverterDeltaFrequency");
814  }
815  if ((m_settings.m_LOppmTenths != settings.m_LOppmTenths) || force) {
816  reverseAPIKeys.append("LOppmTenths");
817  }
818 
822  || (m_settings.m_LOppmTenths != settings.m_LOppmTenths)
823  || (m_settings.m_devSampleRate != settings.m_devSampleRate) || force)
824  {
825  forwardChangeOwnDSP = true;
826  forwardChangeTxBuddies = true;
827 
828  if (dev != 0)
829  {
830  if (setDeviceCenterFrequency(dev, requestedChannel, deviceCenterFrequency, settings.m_LOppmTenths))
831  {
832  if (getMessageQueueToGUI())
833  {
834  int min, max, step;
835  getGlobalGainRange(min, max, step);
836  MsgReportGainRange *msg = MsgReportGainRange::create(min, max, step);
837  getMessageQueueToGUI()->push(msg);
838  }
839  }
840  }
841  }
842 
843  if ((m_settings.m_biasTee != settings.m_biasTee) || force)
844  {
845  reverseAPIKeys.append("biasTee");
846  forwardChangeTxBuddies = true;
848  }
849 
850  if ((m_settings.m_globalGain != settings.m_globalGain) || force)
851  {
852  reverseAPIKeys.append("globalGain");
853  forwardChangeTxBuddies = true;
854 
855  if (dev)
856  {
857 // qDebug("BladeRF2Output::applySettings: channel: %d gain: %d", requestedChannel, settings.m_globalGain);
858  int status = bladerf_set_gain(dev, BLADERF_CHANNEL_TX(requestedChannel), settings.m_globalGain);
859 
860  if (status < 0) {
861  qWarning("BladeRF2Output::applySettings: bladerf_set_gain(%d) failed: %s",
862  settings.m_globalGain, bladerf_strerror(status));
863  } else {
864  qDebug("BladeRF2Output::applySettings: bladerf_set_gain(%d)", settings.m_globalGain);
865  }
866  }
867  }
868 
869  if (forwardChangeOwnDSP)
870  {
871  int sampleRate = settings.m_devSampleRate/(1<<settings.m_log2Interp);
872  DSPSignalNotification *notif = new DSPSignalNotification(sampleRate, settings.m_centerFrequency);
874  }
875 
876  if (forwardChangeRxBuddies)
877  {
878  // send to source buddies
879  const std::vector<DeviceAPI*>& sourceBuddies = m_deviceAPI->getSourceBuddies();
880  std::vector<DeviceAPI*>::const_iterator itSource = sourceBuddies.begin();
881 
882  for (; itSource != sourceBuddies.end(); ++itSource)
883  {
885  settings.m_centerFrequency,
886  settings.m_LOppmTenths,
887  2,
888  settings.m_devSampleRate, // need to forward actual rate to the Rx side
889  false);
890  (*itSource)->getSamplingDeviceInputMessageQueue()->push(report);
891  }
892  }
893 
894  if (forwardChangeTxBuddies)
895  {
896  // send to sink buddies
897  const std::vector<DeviceAPI*>& sinkBuddies = m_deviceAPI->getSinkBuddies();
898  std::vector<DeviceAPI*>::const_iterator itSink = sinkBuddies.begin();
899 
900  for (; itSink != sinkBuddies.end(); ++itSink)
901  {
903  settings.m_centerFrequency,
904  settings.m_LOppmTenths,
905  2,
906  settings.m_devSampleRate,
907  false);
908  (*itSink)->getSamplingDeviceInputMessageQueue()->push(report);
909  }
910  }
911 
912  if (settings.m_useReverseAPI)
913  {
914  bool fullUpdate = ((m_settings.m_useReverseAPI != settings.m_useReverseAPI) && settings.m_useReverseAPI) ||
918  webapiReverseSendSettings(reverseAPIKeys, settings, fullUpdate || force);
919  }
920 
921  m_settings = settings;
922 
923  qDebug() << "BladeRF2Output::applySettings: "
924  << " m_transverterMode: " << m_settings.m_transverterMode
925  << " m_transverterDeltaFrequency: " << m_settings.m_transverterDeltaFrequency
926  << " deviceCenterFrequency: " << deviceCenterFrequency
927  << " m_centerFrequency: " << m_settings.m_centerFrequency << " Hz"
928  << " m_LOppmTenths: " << m_settings.m_LOppmTenths
929  << " m_bandwidth: " << m_settings.m_bandwidth
930  << " m_log2Interp: " << m_settings.m_log2Interp
931  << " m_devSampleRate: " << m_settings.m_devSampleRate
932  << " nbChannels: " << nbChannels
933  << " m_globalGain: " << m_settings.m_globalGain
934  << " m_biasTee: " << m_settings.m_biasTee;
935 
936  return true;
937 }
void push(Message *message, bool emitSignal=true)
Push message onto queue.
const std::vector< DeviceAPI * > & getSinkBuddies() const
Definition: deviceapi.h:166
static const float m_sampleFifoLengthInSeconds
static const int m_sampleFifoMinSize
MessageQueue * getDeviceEngineInputMessageQueue()
Device engine message queue.
Definition: deviceapi.cpp:316
SampleSourceFifo * getFifo(unsigned int channel)
uint32_t getDeviceItemIndex() const
Definition: deviceapi.h:129
bool setDeviceCenterFrequency(struct bladerf *dev, int requestedChannel, quint64 freq_hz, int loPpmTenths)
void setBiasTeeTx(bool enable)
static const int m_sampleFifoMinSize32
DeviceAPI * m_deviceAPI
DeviceBladeRF2Shared m_deviceShared
void setFifo(unsigned int channel, SampleSourceFifo *sampleFifo)
void setLog2Interpolation(unsigned int channel, unsigned int log2_interp)
static MsgReportBuddyChange * create(uint64_t centerFrequency, int LOppmTenths, int fcPos, int devSampleRate, bool rxElseTx)
void resize(uint32_t size)
bladerf * getDev()
static MsgReportGainRange * create(int min, int max, int step)
BladeRF2OutputSettings m_settings
void getGlobalGainRange(int &min, int &max, int &step)
SampleSourceFifo m_sampleSourceFifo
const std::vector< DeviceAPI * > & getSourceBuddies() const
Definition: deviceapi.h:165
MessageQueue * getMessageQueueToGUI()
void webapiReverseSendSettings(QList< QString > &deviceSettingsKeys, const BladeRF2OutputSettings &settings, bool force)
T max(const T &x, const T &y)
Definition: framework.h:446
BladeRF2OutputThread * findThread()
T min(const T &x, const T &y)
Definition: framework.h:440
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ closeDevice()

void BladeRF2Output::closeDevice ( )
private

Definition at line 150 of file bladerf2output.cpp.

References DeviceBladeRF2::close(), DeviceAPI::getSinkBuddies(), DeviceAPI::getSourceBuddies(), DeviceBladeRF2Shared::m_channel, DeviceBladeRF2Shared::m_dev, m_deviceAPI, m_deviceShared, m_running, DeviceBladeRF2Shared::m_sink, m_thread, moveThreadToBuddy(), and stop().

Referenced by ~BladeRF2Output().

151 {
152  if (m_deviceShared.m_dev == 0) { // was never open
153  return;
154  }
155 
156  if (m_running) {
157  stop();
158  }
159 
160  if (m_thread) { // stills own the thread => transfer to a buddy
162  }
163 
164  m_deviceShared.m_channel = -1; // publicly release channel
166 
167  // No buddies so effectively close the device
168 
169  if ((m_deviceAPI->getSinkBuddies().size() == 0) && (m_deviceAPI->getSourceBuddies().size() == 0))
170  {
172  delete m_deviceShared.m_dev;
173  m_deviceShared.m_dev = 0;
174  }
175 }
const std::vector< DeviceAPI * > & getSinkBuddies() const
Definition: deviceapi.h:166
BladeRF2OutputThread * m_thread
DeviceAPI * m_deviceAPI
DeviceBladeRF2Shared m_deviceShared
virtual void stop()
int m_channel
allocated channel (-1 if none)
const std::vector< DeviceAPI * > & getSourceBuddies() const
Definition: deviceapi.h:165
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ deserialize()

bool BladeRF2Output::deserialize ( const QByteArray &  data)
virtual

Implements DeviceSampleSink.

Definition at line 487 of file bladerf2output.cpp.

References BladeRF2Output::MsgConfigureBladeRF2::create(), BladeRF2OutputSettings::deserialize(), DeviceSampleSink::m_guiMessageQueue, DeviceSampleSink::m_inputMessageQueue, m_settings, MessageQueue::push(), and BladeRF2OutputSettings::resetToDefaults().

Referenced by setThread().

488 {
489  bool success = true;
490 
491  if (!m_settings.deserialize(data))
492  {
494  success = false;
495  }
496 
497  MsgConfigureBladeRF2* message = MsgConfigureBladeRF2::create(m_settings, true);
498  m_inputMessageQueue.push(message);
499 
500  if (m_guiMessageQueue)
501  {
502  MsgConfigureBladeRF2* messageToGUI = MsgConfigureBladeRF2::create(m_settings, true);
503  m_guiMessageQueue->push(messageToGUI);
504  }
505 
506  return success;
507 }
void push(Message *message, bool emitSignal=true)
Push message onto queue.
MessageQueue m_inputMessageQueue
Input queue to the sink.
BladeRF2OutputSettings m_settings
MessageQueue * m_guiMessageQueue
Input message queue to the GUI.
static MsgConfigureBladeRF2 * create(const BladeRF2OutputSettings &settings, bool force)
bool deserialize(const QByteArray &data)
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ destroy()

void BladeRF2Output::destroy ( )
virtual

Implements DeviceSampleSink.

Definition at line 71 of file bladerf2output.cpp.

Referenced by BladeRF2Output::MsgReportGainRange::MsgReportGainRange().

72 {
73  delete this;
74 }
+ Here is the caller graph for this function:

◆ findThread()

BladeRF2OutputThread * BladeRF2Output::findThread ( )
private

Definition at line 182 of file bladerf2output.cpp.

References DeviceAPI::getSinkBuddies(), getThread(), m_deviceAPI, and m_thread.

Referenced by applySettings(), getNbChannels(), start(), and stop().

183 {
184  if (m_thread == 0) // this does not own the thread
185  {
186  BladeRF2OutputThread *bladeRF2OutputThread = 0;
187 
188  // find a buddy that has allocated the thread
189  const std::vector<DeviceAPI*>& sinkBuddies = m_deviceAPI->getSinkBuddies();
190  std::vector<DeviceAPI*>::const_iterator it = sinkBuddies.begin();
191 
192  for (; it != sinkBuddies.end(); ++it)
193  {
194  BladeRF2Output *buddySink = ((DeviceBladeRF2Shared*) (*it)->getBuddySharedPtr())->m_sink;
195 
196  if (buddySink)
197  {
198  bladeRF2OutputThread = buddySink->getThread();
199 
200  if (bladeRF2OutputThread) {
201  break;
202  }
203  }
204  }
205 
206  return bladeRF2OutputThread;
207  }
208  else
209  {
210  return m_thread; // own thread
211  }
212 }
const std::vector< DeviceAPI * > & getSinkBuddies() const
Definition: deviceapi.h:166
BladeRF2OutputThread * m_thread
DeviceAPI * m_deviceAPI
BladeRF2OutputThread * getThread()
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ getBandwidthRange()

void BladeRF2Output::getBandwidthRange ( int &  min,
int &  max,
int &  step 
)

Definition at line 573 of file bladerf2output.cpp.

References DeviceBladeRF2::getBandwidthRangeTx(), DeviceBladeRF2Shared::m_dev, and m_deviceShared.

Referenced by BladeRF2OutputGui::BladeRF2OutputGui(), and setSampleRate().

574 {
575  if (m_deviceShared.m_dev) {
577  }
578 }
void getBandwidthRangeTx(int &min, int &max, int &step)
DeviceBladeRF2Shared m_deviceShared
T max(const T &x, const T &y)
Definition: framework.h:446
T min(const T &x, const T &y)
Definition: framework.h:440
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ getCenterFrequency()

quint64 BladeRF2Output::getCenterFrequency ( ) const
virtual

Center frequency exposed by the sink.

Implements DeviceSampleSink.

Definition at line 520 of file bladerf2output.cpp.

References BladeRF2OutputSettings::m_centerFrequency, and m_settings.

Referenced by setSampleRate().

521 {
523 }
BladeRF2OutputSettings m_settings
+ Here is the caller graph for this function:

◆ getDeviceDescription()

const QString & BladeRF2Output::getDeviceDescription ( ) const
virtual

Implements DeviceSampleSink.

Definition at line 509 of file bladerf2output.cpp.

References m_deviceDescription.

Referenced by setMessageQueueToGUI().

510 {
511  return m_deviceDescription;
512 }
QString m_deviceDescription
+ Here is the caller graph for this function:

◆ getFrequencyRange()

void BladeRF2Output::getFrequencyRange ( uint64_t min,
uint64_t max,
int &  step 
)

Definition at line 559 of file bladerf2output.cpp.

References DeviceBladeRF2::getFrequencyRangeTx(), DeviceBladeRF2Shared::m_dev, and m_deviceShared.

Referenced by BladeRF2OutputGui::BladeRF2OutputGui(), setSampleRate(), and BladeRF2OutputGui::updateFrequencyLimits().

560 {
561  if (m_deviceShared.m_dev) {
563  }
564 }
DeviceBladeRF2Shared m_deviceShared
void getFrequencyRangeTx(uint64_t &min, uint64_t &max, int &step)
T max(const T &x, const T &y)
Definition: framework.h:446
T min(const T &x, const T &y)
Definition: framework.h:440
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ getGlobalGainRange()

void BladeRF2Output::getGlobalGainRange ( int &  min,
int &  max,
int &  step 
)

Definition at line 580 of file bladerf2output.cpp.

References DeviceBladeRF2::getGlobalGainRangeTx(), DeviceBladeRF2Shared::m_dev, and m_deviceShared.

Referenced by applySettings(), BladeRF2OutputGui::BladeRF2OutputGui(), BladeRF2OutputGui::handleMessage(), and setSampleRate().

581 {
582  if (m_deviceShared.m_dev) {
584  }
585 }
void getGlobalGainRangeTx(int &min, int &max, int &step)
DeviceBladeRF2Shared m_deviceShared
T max(const T &x, const T &y)
Definition: framework.h:446
T min(const T &x, const T &y)
Definition: framework.h:440
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ getNbChannels()

int BladeRF2Output::getNbChannels ( )
private

Definition at line 939 of file bladerf2output.cpp.

References findThread(), and BladeRF2OutputThread::getNbChannels().

Referenced by applySettings().

940 {
941  BladeRF2OutputThread *bladeRF2OutputThread = findThread();
942 
943  if (bladeRF2OutputThread) {
944  return bladeRF2OutputThread->getNbChannels();
945  } else {
946  return 0;
947  }
948 }
unsigned int getNbChannels() const
BladeRF2OutputThread * findThread()
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ getSampleRate()

int BladeRF2Output::getSampleRate ( ) const
virtual

Sample rate exposed by the sink.

Implements DeviceSampleSink.

Definition at line 514 of file bladerf2output.cpp.

References BladeRF2OutputSettings::m_devSampleRate, BladeRF2OutputSettings::m_log2Interp, and m_settings.

Referenced by setMessageQueueToGUI().

515 {
516  int rate = m_settings.m_devSampleRate;
517  return (rate / (1<<m_settings.m_log2Interp));
518 }
BladeRF2OutputSettings m_settings
+ Here is the caller graph for this function:

◆ getSampleRateRange()

void BladeRF2Output::getSampleRateRange ( int &  min,
int &  max,
int &  step 
)

Definition at line 566 of file bladerf2output.cpp.

References DeviceBladeRF2::getSampleRateRangeTx(), DeviceBladeRF2Shared::m_dev, and m_deviceShared.

Referenced by BladeRF2OutputGui::BladeRF2OutputGui(), BladeRF2OutputGui::displaySampleRate(), and setSampleRate().

567 {
568  if (m_deviceShared.m_dev) {
570  }
571 }
void getSampleRateRangeTx(int &min, int &max, int &step)
DeviceBladeRF2Shared m_deviceShared
T max(const T &x, const T &y)
Definition: framework.h:446
T min(const T &x, const T &y)
Definition: framework.h:440
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ getThread()

BladeRF2OutputThread* BladeRF2Output::getThread ( )
inline

Definition at line 113 of file bladerf2output.h.

References m_thread.

Referenced by findThread().

113 { return m_thread; }
BladeRF2OutputThread * m_thread
+ Here is the caller graph for this function:

◆ handleMessage()

bool BladeRF2Output::handleMessage ( const Message message)
virtual

Implements DeviceSampleSink.

Definition at line 587 of file bladerf2output.cpp.

References applySettings(), BladeRF2Output::MsgConfigureBladeRF2::create(), DeviceBladeRF2Shared::MsgReportBuddyChange::getCenterFrequency(), DeviceBladeRF2::getDev(), DeviceAPI::getDeviceEngineInputMessageQueue(), DeviceAPI::getDeviceItemIndex(), DeviceBladeRF2Shared::MsgReportBuddyChange::getDevSampleRate(), BladeRF2Output::MsgConfigureBladeRF2::getForce(), DeviceBladeRF2Shared::MsgReportBuddyChange::getLOppmTenths(), DeviceSampleSink::getMessageQueueToGUI(), DeviceBladeRF2Shared::MsgReportBuddyChange::getRxElseTx(), BladeRF2Output::MsgConfigureBladeRF2::getSettings(), BladeRF2Output::MsgStartStop::getStartStop(), DeviceAPI::initDeviceEngine(), BladeRF2OutputSettings::m_bandwidth, BladeRF2OutputSettings::m_biasTee, BladeRF2OutputSettings::m_centerFrequency, DeviceBladeRF2Shared::m_dev, m_deviceAPI, m_deviceShared, BladeRF2OutputSettings::m_devSampleRate, BladeRF2OutputSettings::m_log2Interp, BladeRF2OutputSettings::m_LOppmTenths, m_settings, BladeRF2OutputSettings::m_useReverseAPI, Message::match(), MessageQueue::push(), DeviceAPI::startDeviceEngine(), DeviceAPI::stopDeviceEngine(), and webapiReverseSendStartStop().

Referenced by setSampleRate().

588 {
589  if (MsgConfigureBladeRF2::match(message))
590  {
591  MsgConfigureBladeRF2& conf = (MsgConfigureBladeRF2&) message;
592  qDebug() << "BladeRF2Output::handleMessage: MsgConfigureBladeRF2";
593 
594  if (!applySettings(conf.getSettings(), conf.getForce()))
595  {
596  qDebug("BladeRF2Output::handleMessage: MsgConfigureBladeRF2 config error");
597  }
598 
599  return true;
600  }
602  {
604  struct bladerf *dev = m_deviceShared.m_dev->getDev();
606  int status;
607  unsigned int tmp_uint;
608  bool tmp_bool;
609 
610  // evaluate changes that may have been introduced by changes in a buddy
611 
612  if (dev) // The BladeRF device must have been open to do so
613  {
614  int requestedChannel = m_deviceAPI->getDeviceItemIndex();
615 
616  if (report.getRxElseTx()) // Rx buddy change: check for sample rate change only
617  {
618  settings.m_devSampleRate = report.getDevSampleRate();
619 // status = bladerf_get_sample_rate(dev, BLADERF_CHANNEL_TX(requestedChannel), &tmp_uint);
620 //
621 // if (status < 0) {
622 // qCritical("BladeRF2Output::handleMessage: MsgReportBuddyChange: bladerf_get_sample_rate error: %s", bladerf_strerror(status));
623 // } else {
624 // settings.m_devSampleRate = tmp_uint;
625 // }
626  }
627  else // Tx buddy change: check for: frequency, gain mode and value, bias tee, sample rate, bandwidth
628  {
629  settings.m_devSampleRate = report.getDevSampleRate();
630  settings.m_LOppmTenths = report.getLOppmTenths();
631  settings.m_centerFrequency = report.getCenterFrequency();
632 
633  status = bladerf_get_bandwidth(dev, BLADERF_CHANNEL_TX(requestedChannel), &tmp_uint);
634 
635  if (status < 0) {
636  qCritical("BladeRF2Output::handleMessage: MsgReportBuddyChange: bladerf_get_bandwidth error: %s", bladerf_strerror(status));
637  } else {
638  settings.m_bandwidth = tmp_uint;
639  }
640 
641  status = bladerf_get_bias_tee(dev, BLADERF_CHANNEL_TX(requestedChannel), &tmp_bool);
642 
643  if (status < 0) {
644  qCritical("BladeRF2Output::handleMessage: MsgReportBuddyChange: bladerf_get_bias_tee error: %s", bladerf_strerror(status));
645  } else {
646  settings.m_biasTee = tmp_bool;
647  }
648  }
649 
650  // change DSP settings if buddy change introduced a change in center frequency or base rate
652  {
653  int sampleRate = settings.m_devSampleRate/(1<<settings.m_log2Interp);
654  DSPSignalNotification *notif = new DSPSignalNotification(sampleRate, settings.m_centerFrequency);
656  }
657 
658  m_settings = settings; // acknowledge the new settings
659 
660  // propagate settings to GUI if any
661  if (getMessageQueueToGUI())
662  {
663  MsgConfigureBladeRF2 *reportToGUI = MsgConfigureBladeRF2::create(m_settings, false);
664  getMessageQueueToGUI()->push(reportToGUI);
665  }
666  }
667 
668  return true;
669  }
670  else if (MsgStartStop::match(message))
671  {
672  MsgStartStop& cmd = (MsgStartStop&) message;
673  qDebug() << "BladeRF2Input::handleMessage: MsgStartStop: " << (cmd.getStartStop() ? "start" : "stop");
674 
675  if (cmd.getStartStop())
676  {
678  {
680  }
681  }
682  else
683  {
685  }
686 
688  webapiReverseSendStartStop(cmd.getStartStop());
689  }
690 
691  return true;
692  }
693  else
694  {
695  return false;
696  }
697 }
bool startDeviceEngine()
Start the device engine corresponding to the stream type.
Definition: deviceapi.cpp:253
void push(Message *message, bool emitSignal=true)
Push message onto queue.
void stopDeviceEngine()
Stop the device engine corresponding to the stream type.
Definition: deviceapi.cpp:266
MessageQueue * getDeviceEngineInputMessageQueue()
Device engine message queue.
Definition: deviceapi.cpp:316
uint32_t getDeviceItemIndex() const
Definition: deviceapi.h:129
bool initDeviceEngine()
Init the device engine corresponding to the stream type.
Definition: deviceapi.cpp:240
void webapiReverseSendStartStop(bool start)
DeviceAPI * m_deviceAPI
DeviceBladeRF2Shared m_deviceShared
static bool match(const Message *message)
Definition: message.cpp:45
bladerf * getDev()
BladeRF2OutputSettings m_settings
MessageQueue * getMessageQueueToGUI()
static MsgConfigureBladeRF2 * create(const BladeRF2OutputSettings &settings, bool force)
bool applySettings(const BladeRF2OutputSettings &settings, bool force)
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ init()

void BladeRF2Output::init ( )
virtual

initializations to be done when all collaborating objects are created and possibly connected

Implements DeviceSampleSink.

Definition at line 177 of file bladerf2output.cpp.

References applySettings(), and m_settings.

Referenced by BladeRF2Output::MsgReportGainRange::MsgReportGainRange().

178 {
179  applySettings(m_settings, true);
180 }
BladeRF2OutputSettings m_settings
bool applySettings(const BladeRF2OutputSettings &settings, bool force)
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ moveThreadToBuddy()

void BladeRF2Output::moveThreadToBuddy ( )
private

Definition at line 214 of file bladerf2output.cpp.

References DeviceAPI::getSinkBuddies(), m_deviceAPI, m_thread, and setThread().

Referenced by closeDevice().

215 {
216  const std::vector<DeviceAPI*>& sinkBuddies = m_deviceAPI->getSinkBuddies();
217  std::vector<DeviceAPI*>::const_iterator it = sinkBuddies.begin();
218 
219  for (; it != sinkBuddies.end(); ++it)
220  {
221  BladeRF2Output *buddySink = ((DeviceBladeRF2Shared*) (*it)->getBuddySharedPtr())->m_sink;
222 
223  if (buddySink)
224  {
225  buddySink->setThread(m_thread);
226  m_thread = 0; // zero for others
227  }
228  }
229 }
const std::vector< DeviceAPI * > & getSinkBuddies() const
Definition: deviceapi.h:166
BladeRF2OutputThread * m_thread
DeviceAPI * m_deviceAPI
void setThread(BladeRF2OutputThread *thread)
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ networkManagerFinished

void BladeRF2Output::networkManagerFinished ( QNetworkReply *  reply)
privateslot

Definition at line 1208 of file bladerf2output.cpp.

Referenced by ~BladeRF2Output().

1209 {
1210  QNetworkReply::NetworkError replyError = reply->error();
1211 
1212  if (replyError)
1213  {
1214  qWarning() << "BladeRF2Output::networkManagerFinished:"
1215  << " error(" << (int) replyError
1216  << "): " << replyError
1217  << ": " << reply->errorString();
1218  return;
1219  }
1220 
1221  QString answer = reply->readAll();
1222  answer.chop(1); // remove last \n
1223  qDebug("BladeRF2Output::networkManagerFinished: reply:\n%s", answer.toStdString().c_str());
1224 }
+ Here is the caller graph for this function:

◆ openDevice()

bool BladeRF2Output::openDevice ( )
private

Definition at line 76 of file bladerf2output.cpp.

References DeviceAPI::getBuddySharedPtr(), DeviceAPI::getDeviceItemIndex(), DeviceAPI::getSamplingDeviceSerial(), DeviceAPI::getSinkBuddies(), DeviceAPI::getSourceBuddies(), DeviceBladeRF2Shared::m_channel, DeviceBladeRF2Shared::m_dev, m_deviceAPI, m_deviceShared, BladeRF2OutputSettings::m_devSampleRate, BladeRF2OutputSettings::m_log2Interp, DeviceSampleSink::m_sampleSourceFifo, m_settings, DeviceBladeRF2Shared::m_sink, DeviceBladeRF2::open(), SampleSourceFifo::resize(), and DeviceAPI::setBuddySharedPtr().

77 {
79 
80  // look for Tx buddies and get reference to the device object
81  if (m_deviceAPI->getSinkBuddies().size() > 0) // look sink sibling first
82  {
83  qDebug("BladeRF2Output::openDevice: look in Tx buddies");
84 
85  DeviceAPI *sinkBuddy = m_deviceAPI->getSinkBuddies()[0];
86  DeviceBladeRF2Shared *deviceBladeRF2Shared = (DeviceBladeRF2Shared*) sinkBuddy->getBuddySharedPtr();
87 
88  if (deviceBladeRF2Shared == 0)
89  {
90  qCritical("BladeRF2Output::openDevice: the sink buddy shared pointer is null");
91  return false;
92  }
93 
94  DeviceBladeRF2 *device = deviceBladeRF2Shared->m_dev;
95 
96  if (device == 0)
97  {
98  qCritical("BladeRF2Output::openDevice: cannot get device pointer from Tx buddy");
99  return false;
100  }
101 
102  m_deviceShared.m_dev = device;
103  }
104  // look for Rx buddies and get reference to the device object
105  else if (m_deviceAPI->getSourceBuddies().size() > 0) // then source
106  {
107  qDebug("BladeRF2Output::openDevice: look in Rx buddies");
108 
109  DeviceAPI *sourceBuddy = m_deviceAPI->getSourceBuddies()[0];
110  DeviceBladeRF2Shared *deviceBladeRF2Shared = (DeviceBladeRF2Shared*) sourceBuddy->getBuddySharedPtr();
111 
112  if (deviceBladeRF2Shared == 0)
113  {
114  qCritical("BladeRF2Output::openDevice: the source buddy shared pointer is null");
115  return false;
116  }
117 
118  DeviceBladeRF2 *device = deviceBladeRF2Shared->m_dev;
119 
120  if (device == 0)
121  {
122  qCritical("BladeRF2Output::openDevice: cannot get device pointer from Rx buddy");
123  return false;
124  }
125 
126  m_deviceShared.m_dev = device;
127  }
128  // There are no buddies then create the first BladeRF2 device
129  else
130  {
131  qDebug("BladeRF2Output::openDevice: open device here");
132 
134  char serial[256];
135  strcpy(serial, qPrintable(m_deviceAPI->getSamplingDeviceSerial()));
136 
137  if (!m_deviceShared.m_dev->open(serial))
138  {
139  qCritical("BladeRF2Output::openDevice: cannot open BladeRF2 device");
140  return false;
141  }
142  }
143 
144  m_deviceShared.m_channel = m_deviceAPI->getDeviceItemIndex(); // publicly allocate channel
145  m_deviceShared.m_sink = this;
146  m_deviceAPI->setBuddySharedPtr(&m_deviceShared); // propagate common parameters to API
147  return true;
148 }
const std::vector< DeviceAPI * > & getSinkBuddies() const
Definition: deviceapi.h:166
uint32_t getDeviceItemIndex() const
Definition: deviceapi.h:129
void * getBuddySharedPtr() const
Definition: deviceapi.h:161
DeviceAPI * m_deviceAPI
DeviceBladeRF2Shared m_deviceShared
void setBuddySharedPtr(void *ptr)
Definition: deviceapi.h:162
void resize(uint32_t size)
const QString & getSamplingDeviceSerial() const
Definition: deviceapi.h:121
BladeRF2OutputSettings m_settings
int m_channel
allocated channel (-1 if none)
bool open(const char *serial)
SampleSourceFifo m_sampleSourceFifo
const std::vector< DeviceAPI * > & getSourceBuddies() const
Definition: deviceapi.h:165
+ Here is the call graph for this function:

◆ serialize()

QByteArray BladeRF2Output::serialize ( ) const
virtual

Implements DeviceSampleSink.

Definition at line 482 of file bladerf2output.cpp.

References m_settings, and BladeRF2OutputSettings::serialize().

Referenced by setThread().

483 {
484  return m_settings.serialize();
485 }
BladeRF2OutputSettings m_settings
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ setCenterFrequency()

void BladeRF2Output::setCenterFrequency ( qint64  centerFrequency)
virtual

Implements DeviceSampleSink.

Definition at line 525 of file bladerf2output.cpp.

References BladeRF2Output::MsgConfigureBladeRF2::create(), BladeRF2OutputSettings::m_centerFrequency, DeviceSampleSink::m_guiMessageQueue, DeviceSampleSink::m_inputMessageQueue, m_settings, and MessageQueue::push().

Referenced by setSampleRate().

526 {
528  settings.m_centerFrequency = centerFrequency;
529 
530  MsgConfigureBladeRF2* message = MsgConfigureBladeRF2::create(settings, false);
531  m_inputMessageQueue.push(message);
532 
533  if (m_guiMessageQueue)
534  {
535  MsgConfigureBladeRF2* messageToGUI = MsgConfigureBladeRF2::create(settings, false);
536  m_guiMessageQueue->push(messageToGUI);
537  }
538 }
void push(Message *message, bool emitSignal=true)
Push message onto queue.
MessageQueue m_inputMessageQueue
Input queue to the sink.
BladeRF2OutputSettings m_settings
MessageQueue * m_guiMessageQueue
Input message queue to the GUI.
static MsgConfigureBladeRF2 * create(const BladeRF2OutputSettings &settings, bool force)
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ setDeviceCenterFrequency()

bool BladeRF2Output::setDeviceCenterFrequency ( struct bladerf *  dev,
int  requestedChannel,
quint64  freq_hz,
int  loPpmTenths 
)
private

Definition at line 540 of file bladerf2output.cpp.

Referenced by applySettings().

541 {
542  qint64 df = ((qint64)freq_hz * loPpmTenths) / 10000000LL;
543  freq_hz += df;
544 
545  int status = bladerf_set_frequency(dev, BLADERF_CHANNEL_TX(requestedChannel), freq_hz);
546 
547  if (status < 0) {
548  qWarning("BladeRF2Output::setDeviceCenterFrequency: bladerf_set_frequency(%lld) failed: %s",
549  freq_hz, bladerf_strerror(status));
550  return false;
551  }
552  else
553  {
554  qDebug("BladeRF2Output::setDeviceCenterFrequency: bladerf_set_frequency(%lld)", freq_hz);
555  return true;
556  }
557 }
+ Here is the caller graph for this function:

◆ setMessageQueueToGUI()

virtual void BladeRF2Output::setMessageQueueToGUI ( MessageQueue queue)
inlinevirtual

Implements DeviceSampleSink.

Definition at line 119 of file bladerf2output.h.

References getDeviceDescription(), getSampleRate(), and DeviceSampleSink::m_guiMessageQueue.

Referenced by BladeRF2OutputGui::BladeRF2OutputGui().

119 { m_guiMessageQueue = queue; }
MessageQueue * m_guiMessageQueue
Input message queue to the GUI.
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ setSampleRate()

virtual void BladeRF2Output::setSampleRate ( int  sampleRate)
inlinevirtual

For when the sink sample rate is set externally.

Implements DeviceSampleSink.

Definition at line 122 of file bladerf2output.h.

References getBandwidthRange(), getCenterFrequency(), getFrequencyRange(), getGlobalGainRange(), getSampleRateRange(), handleMessage(), leansdr::max(), leansdr::min(), setCenterFrequency(), webapiReportGet(), webapiRun(), webapiRunGet(), webapiSettingsGet(), and webapiSettingsPutPatch().

122 { (void) sampleRate; }
+ Here is the call graph for this function:

◆ setThread()

void BladeRF2Output::setThread ( BladeRF2OutputThread thread)
inline

Definition at line 114 of file bladerf2output.h.

References deserialize(), m_thread, and serialize().

Referenced by moveThreadToBuddy().

114 { m_thread = thread; }
BladeRF2OutputThread * m_thread
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ start()

bool BladeRF2Output::start ( )
virtual

Implements DeviceSampleSink.

Definition at line 231 of file bladerf2output.cpp.

References applySettings(), DeviceBladeRF2::closeTx(), findThread(), DeviceBladeRF2::getDev(), DeviceAPI::getDeviceItemIndex(), BladeRF2OutputThread::getFifo(), BladeRF2OutputThread::getLog2Interpolation(), BladeRF2OutputThread::getNbChannels(), DeviceAPI::getSinkBuddies(), i, DeviceBladeRF2Shared::m_dev, m_deviceAPI, m_deviceShared, BladeRF2OutputSettings::m_log2Interp, m_running, DeviceSampleSink::m_sampleSourceFifo, m_settings, m_thread, DeviceBladeRF2::openTx(), BladeRF2OutputThread::setFifo(), BladeRF2OutputThread::setLog2Interpolation(), BladeRF2OutputThread::startWork(), and BladeRF2OutputThread::stopWork().

Referenced by BladeRF2Output::MsgReportGainRange::MsgReportGainRange().

232 {
233  // There is a single thread per physical device (Tx side). This thread is unique and referenced by a unique
234  // buddy in the group of sink buddies associated with this physical device.
235  //
236  // This start method is responsible for managing the thread and channel enabling when the streaming of a Tx channel is started
237  //
238  // It checks the following conditions
239  // - the thread is allocated or not (by itself or one of its buddies). If it is it grabs the thread pointer.
240  // - the requested channel is the first (0) or the following (just 1 in BladeRF 2 case)
241  //
242  // The BladeRF support library lets you work in two possible modes:
243  // - Single Output (SO) with only one channel streaming. This HAS to be channel 0.
244  // - Multiple Output (MO) with two channels streaming using interleaved samples. It MUST be in this configuration if channel 1
245  // is used. When we will run with only channel 1 streaming from the client perspective the channel 0 will actually be enabled
246  // and streaming but zero samples will be sent to it.
247  //
248  // It manages the transition form SO where only one channel (the first or channel 0) should be running to the
249  // Multiple Output (MO) if the requested channel is 1. More generally it checks if the requested channel is within the current
250  // channel range allocated in the thread or past it. To perform the transition it stops the thread, deletes it and creates a new one.
251  // It marks the thread as needing start.
252  //
253  // If the requested channel is within the thread channel range (this thread being already allocated) it simply removes its FIFO reference
254  // so that the samples are not taken from the FIFO anymore and leaves the thread unchanged (no stop, no delete/new)
255  //
256  // If there is no thread allocated it creates a new one with a number of channels that fits the requested channel. That is
257  // 1 if channel 0 is requested (SO mode) and 2 if channel 1 is requested (MO mode). It marks the thread as needing start.
258  //
259  // Eventually it registers the FIFO in the thread. If the thread has to be started it enables the channels up to the number of channels
260  // allocated in the thread and starts the thread.
261 
262  if (!m_deviceShared.m_dev)
263  {
264  qDebug("BladeRF2Output::start: no device object");
265  return false;
266  }
267 
268  int requestedChannel = m_deviceAPI->getDeviceItemIndex();
269  BladeRF2OutputThread *bladeRF2OutputThread = findThread();
270  bool needsStart = false;
271 
272  if (bladeRF2OutputThread) // if thread is already allocated
273  {
274  qDebug("BladeRF2Output::start: thread is already allocated");
275 
276  int nbOriginalChannels = bladeRF2OutputThread->getNbChannels();
277 
278  if (requestedChannel+1 > nbOriginalChannels) // expansion by deleting and re-creating the thread
279  {
280  qDebug("BladeRF2Output::start: expand channels. Re-allocate thread and take ownership");
281 
282  SampleSourceFifo **fifos = new SampleSourceFifo*[nbOriginalChannels];
283  unsigned int *log2Interps = new unsigned int[nbOriginalChannels];
284 
285  for (int i = 0; i < nbOriginalChannels; i++) // save original FIFO references and data
286  {
287  fifos[i] = bladeRF2OutputThread->getFifo(i);
288  log2Interps[i] = bladeRF2OutputThread->getLog2Interpolation(i);
289  }
290 
291  bladeRF2OutputThread->stopWork();
292  delete bladeRF2OutputThread;
293  bladeRF2OutputThread = new BladeRF2OutputThread(m_deviceShared.m_dev->getDev(), requestedChannel+1);
294  m_thread = bladeRF2OutputThread; // take ownership
295 
296  for (int i = 0; i < nbOriginalChannels; i++) // restore original FIFO references
297  {
298  bladeRF2OutputThread->setFifo(i, fifos[i]);
299  bladeRF2OutputThread->setLog2Interpolation(i, log2Interps[i]);
300  }
301 
302  // remove old thread address from buddies (reset in all buddies)
303  const std::vector<DeviceAPI*>& sinkBuddies = m_deviceAPI->getSinkBuddies();
304  std::vector<DeviceAPI*>::const_iterator it = sinkBuddies.begin();
305 
306  for (; it != sinkBuddies.end(); ++it) {
307  ((DeviceBladeRF2Shared*) (*it)->getBuddySharedPtr())->m_sink->setThread(0);
308  }
309 
310  // close all channels
311  for (int i = bladeRF2OutputThread->getNbChannels()-1; i >= 0; i--) {
313  }
314 
315  // was used as temporary storage:
316  delete[] fifos;
317  delete[] log2Interps;
318 
319  needsStart = true;
320  }
321  else
322  {
323  qDebug("BladeRF2Output::start: keep buddy thread");
324  }
325  }
326  else // first allocation
327  {
328  qDebug("BladeRF2Output::start: allocate thread and take ownership");
329  bladeRF2OutputThread = new BladeRF2OutputThread(m_deviceShared.m_dev->getDev(), requestedChannel+1);
330  m_thread = bladeRF2OutputThread; // take ownership
331  needsStart = true;
332  }
333 
334  bladeRF2OutputThread->setFifo(requestedChannel, &m_sampleSourceFifo);
335  bladeRF2OutputThread->setLog2Interpolation(requestedChannel, m_settings.m_log2Interp);
336 
337  applySettings(m_settings, true); // re-apply forcibly to set sample rate with the new number of channels
338 
339  if (needsStart)
340  {
341  qDebug("BladeRF2Output::start: enabling channel(s) and (re)starting the thread");
342 
343  for (unsigned int i = 0; i < bladeRF2OutputThread->getNbChannels(); i++) // open all channels
344  {
345  if (!m_deviceShared.m_dev->openTx(i)) {
346  qCritical("BladeRF2Output::start: channel %u cannot be enabled", i);
347  }
348  }
349 
350  bladeRF2OutputThread->startWork();
351  }
352 
353  qDebug("BladeRF2Output::start: started");
354  m_running = true;
355 
356  return true;
357 }
bool openTx(int channel)
const std::vector< DeviceAPI * > & getSinkBuddies() const
Definition: deviceapi.h:166
SampleSourceFifo * getFifo(unsigned int channel)
BladeRF2OutputThread * m_thread
uint32_t getDeviceItemIndex() const
Definition: deviceapi.h:129
unsigned int getLog2Interpolation(unsigned int channel) const
unsigned int getNbChannels() const
DeviceAPI * m_deviceAPI
DeviceBladeRF2Shared m_deviceShared
void setFifo(unsigned int channel, SampleSourceFifo *sampleFifo)
int32_t i
Definition: decimators.h:244
void setLog2Interpolation(unsigned int channel, unsigned int log2_interp)
bladerf * getDev()
BladeRF2OutputSettings m_settings
SampleSourceFifo m_sampleSourceFifo
void closeTx(int channel)
BladeRF2OutputThread * findThread()
bool applySettings(const BladeRF2OutputSettings &settings, bool force)
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ stop()

void BladeRF2Output::stop ( )
virtual

Implements DeviceSampleSink.

Definition at line 359 of file bladerf2output.cpp.

References applySettings(), DeviceBladeRF2::closeTx(), findThread(), DeviceBladeRF2::getDev(), DeviceAPI::getDeviceItemIndex(), BladeRF2OutputThread::getFifo(), BladeRF2OutputThread::getLog2Interpolation(), BladeRF2OutputThread::getNbChannels(), DeviceAPI::getSinkBuddies(), i, DeviceBladeRF2Shared::m_dev, m_deviceAPI, m_deviceShared, m_running, m_settings, m_thread, DeviceBladeRF2::openTx(), BladeRF2OutputThread::setFifo(), BladeRF2OutputThread::setLog2Interpolation(), BladeRF2OutputThread::startWork(), and BladeRF2OutputThread::stopWork().

Referenced by closeDevice(), BladeRF2Output::MsgReportGainRange::MsgReportGainRange(), and ~BladeRF2Output().

360 {
361  // This stop method is responsible for managing the thread and channel disabling when the streaming of
362  // a Tx channel is stopped
363  //
364  // If the thread is currently managing only one channel (SO mode). The thread can be just stopped and deleted.
365  // Then the channel is closed (disabled).
366  //
367  // If the thread is currently managing many channels (MO mode) and we are removing the last channel. The transition
368  // from MO to SO or reduction of MO size is handled by stopping the thread, deleting it and creating a new one
369  // with one channel less if (and only if) there is still a channel active.
370  //
371  // If the thread is currently managing many channels (MO mode) but the channel being stopped is not the last
372  // channel then the FIFO reference is simply removed from the thread so that this FIFO will not be used anymore.
373  // In this case the channel is not closed (disabled) so that other channels can continue with the
374  // same configuration. The device continues streaming on this channel but the samples are set to all zeros.
375 
376  if (!m_running) {
377  return;
378  }
379 
380  int requestedChannel = m_deviceAPI->getDeviceItemIndex();
381  BladeRF2OutputThread *bladeRF2OutputThread = findThread();
382 
383  if (bladeRF2OutputThread == 0) { // no thread allocated
384  return;
385  }
386 
387  int nbOriginalChannels = bladeRF2OutputThread->getNbChannels();
388 
389  if (nbOriginalChannels == 1) // SO mode => just stop and delete the thread
390  {
391  qDebug("BladeRF2Output::stop: SO mode. Just stop and delete the thread");
392  bladeRF2OutputThread->stopWork();
393  delete bladeRF2OutputThread;
394  m_thread = 0;
395 
396  // remove old thread address from buddies (reset in all buddies)
397  const std::vector<DeviceAPI*>& sinkBuddies = m_deviceAPI->getSinkBuddies();
398  std::vector<DeviceAPI*>::const_iterator it = sinkBuddies.begin();
399 
400  for (; it != sinkBuddies.end(); ++it) {
401  ((DeviceBladeRF2Shared*) (*it)->getBuddySharedPtr())->m_sink->setThread(0);
402  }
403 
404  m_deviceShared.m_dev->closeTx(0); // close the unique channel
405  }
406  else if (requestedChannel == nbOriginalChannels - 1) // remove last MO channel => reduce by deleting and re-creating the thread
407  {
408  qDebug("BladeRF2Output::stop: MO mode. Reduce by deleting and re-creating the thread");
409  bladeRF2OutputThread->stopWork();
410  SampleSourceFifo **fifos = new SampleSourceFifo*[nbOriginalChannels-1];
411  unsigned int *log2Interps = new unsigned int[nbOriginalChannels-1];
412  bool stillActiveFIFO = false;
413 
414  for (int i = 0; i < nbOriginalChannels-1; i++) // save original FIFO references
415  {
416  fifos[i] = bladeRF2OutputThread->getFifo(i);
417  stillActiveFIFO = stillActiveFIFO || (bladeRF2OutputThread->getFifo(i) != 0);
418  log2Interps[i] = bladeRF2OutputThread->getLog2Interpolation(i);
419  }
420 
421  delete bladeRF2OutputThread;
422  m_thread = 0;
423 
424  if (stillActiveFIFO)
425  {
426  bladeRF2OutputThread = new BladeRF2OutputThread(m_deviceShared.m_dev->getDev(), nbOriginalChannels-1);
427  m_thread = bladeRF2OutputThread; // take ownership
428 
429  for (int i = 0; i < nbOriginalChannels-1; i++) // restore original FIFO references
430  {
431  bladeRF2OutputThread->setFifo(i, fifos[i]);
432  bladeRF2OutputThread->setLog2Interpolation(i, log2Interps[i]);
433  }
434  }
435  else
436  {
437  qDebug("BladeRF2Output::stop: do not re-create thread as there are no more FIFOs active");
438  }
439 
440  // remove old thread address from buddies (reset in all buddies)
441  const std::vector<DeviceAPI*>& sinkBuddies = m_deviceAPI->getSinkBuddies();
442  std::vector<DeviceAPI*>::const_iterator it = sinkBuddies.begin();
443 
444  for (; it != sinkBuddies.end(); ++it) {
445  ((DeviceBladeRF2Shared*) (*it)->getBuddySharedPtr())->m_sink->setThread(0);
446  }
447 
448  // close all channels
449  for (int i = nbOriginalChannels-1; i >= 0; i--) {
451  }
452 
453  if (stillActiveFIFO)
454  {
455  qDebug("BladeRF2Output::stop: enabling channel(s) and restarting the thread");
456 
457  for (unsigned int i = 0; i < bladeRF2OutputThread->getNbChannels(); i++) // open all channels
458  {
459  if (!m_deviceShared.m_dev->openTx(i)) {
460  qCritical("BladeRF2Output::start: channel %u cannot be enabled", i);
461  }
462  }
463 
464  bladeRF2OutputThread->startWork();
465  }
466 
467  // was used as temporary storage:
468  delete[] fifos;
469  delete[] log2Interps;
470  }
471  else // remove channel from existing thread
472  {
473  qDebug("BladeRF2Output::stop: MO mode. Not changing MO configuration. Just remove FIFO reference");
474  bladeRF2OutputThread->setFifo(requestedChannel, 0); // remove FIFO
475  }
476 
477  applySettings(m_settings, true); // re-apply forcibly to set sample rate with the new number of channels
478 
479  m_running = false;
480 }
bool openTx(int channel)
const std::vector< DeviceAPI * > & getSinkBuddies() const
Definition: deviceapi.h:166
SampleSourceFifo * getFifo(unsigned int channel)
BladeRF2OutputThread * m_thread
uint32_t getDeviceItemIndex() const
Definition: deviceapi.h:129
unsigned int getLog2Interpolation(unsigned int channel) const
unsigned int getNbChannels() const
DeviceAPI * m_deviceAPI
DeviceBladeRF2Shared m_deviceShared
void setFifo(unsigned int channel, SampleSourceFifo *sampleFifo)
int32_t i
Definition: decimators.h:244
void setLog2Interpolation(unsigned int channel, unsigned int log2_interp)
bladerf * getDev()
BladeRF2OutputSettings m_settings
void closeTx(int channel)
BladeRF2OutputThread * findThread()
bool applySettings(const BladeRF2OutputSettings &settings, bool force)
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ webapiFormatDeviceReport()

void BladeRF2Output::webapiFormatDeviceReport ( SWGSDRangel::SWGDeviceReport response)
private

Definition at line 1056 of file bladerf2output.cpp.

References SWGSDRangel::SWGBladeRF2OutputReport::getBandwidthRange(), DeviceBladeRF2::getBandwidthRangeTx(), SWGSDRangel::SWGDeviceReport::getBladeRf2OutputReport(), SWGSDRangel::SWGBladeRF2OutputReport::getFrequencyRange(), DeviceBladeRF2::getFrequencyRangeTx(), SWGSDRangel::SWGBladeRF2OutputReport::getGlobalGainRange(), DeviceBladeRF2::getGlobalGainRangeTx(), SWGSDRangel::SWGBladeRF2OutputReport::getSampleRateRange(), DeviceBladeRF2::getSampleRateRangeTx(), DeviceBladeRF2Shared::m_dev, m_deviceShared, leansdr::max(), leansdr::min(), SWGSDRangel::SWGBladeRF2OutputReport::setBandwidthRange(), SWGSDRangel::SWGBladeRF2OutputReport::setFrequencyRange(), SWGSDRangel::SWGBladeRF2OutputReport::setGlobalGainRange(), SWGSDRangel::SWGFrequencyRange::setMax(), SWGSDRangel::SWGRange::setMax(), SWGSDRangel::SWGFrequencyRange::setMin(), SWGSDRangel::SWGRange::setMin(), SWGSDRangel::SWGBladeRF2OutputReport::setSampleRateRange(), SWGSDRangel::SWGRange::setStep(), and SWGSDRangel::SWGFrequencyRange::setStep().

Referenced by webapiReportGet().

1057 {
1059 
1060  if (device)
1061  {
1062  int min, max, step;
1063  uint64_t f_min, f_max;
1064 
1065  device->getBandwidthRangeTx(min, max, step);
1066 
1068  response.getBladeRf2OutputReport()->getBandwidthRange()->setMin(min);
1069  response.getBladeRf2OutputReport()->getBandwidthRange()->setMax(max);
1070  response.getBladeRf2OutputReport()->getBandwidthRange()->setStep(step);
1071 
1072  device->getFrequencyRangeTx(f_min, f_max, step);
1073 
1075  response.getBladeRf2OutputReport()->getFrequencyRange()->setMin(f_min);
1076  response.getBladeRf2OutputReport()->getFrequencyRange()->setMax(f_max);
1077  response.getBladeRf2OutputReport()->getFrequencyRange()->setStep(step);
1078 
1079  device->getGlobalGainRangeTx(min, max, step);
1080 
1084  response.getBladeRf2OutputReport()->getGlobalGainRange()->setStep(step);
1085 
1086  device->getSampleRateRangeTx(min, max, step);
1087 
1091  response.getBladeRf2OutputReport()->getSampleRateRange()->setStep(step);
1092  }
1093 }
void getGlobalGainRangeTx(int &min, int &max, int &step)
void setStep(qint32 step)
Definition: SWGRange.cpp:131
void setMax(qint32 max)
Definition: SWGRange.cpp:121
void getBandwidthRangeTx(int &min, int &max, int &step)
void setFrequencyRange(SWGFrequencyRange *frequency_range)
void getSampleRateRangeTx(int &min, int &max, int &step)
DeviceBladeRF2Shared m_deviceShared
void setGlobalGainRange(SWGRange *global_gain_range)
void getFrequencyRangeTx(uint64_t &min, uint64_t &max, int &step)
void setMin(qint32 min)
Definition: SWGRange.cpp:111
SWGBladeRF2OutputReport * getBladeRf2OutputReport()
void setSampleRateRange(SWGRange *sample_rate_range)
void setBandwidthRange(SWGRange *bandwidth_range)
T max(const T &x, const T &y)
Definition: framework.h:446
T min(const T &x, const T &y)
Definition: framework.h:440
unsigned __int64 uint64_t
Definition: rtptypes_win.h:48
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ webapiFormatDeviceSettings()

void BladeRF2Output::webapiFormatDeviceSettings ( SWGSDRangel::SWGDeviceSettings response,
const BladeRF2OutputSettings settings 
)
private

Definition at line 1032 of file bladerf2output.cpp.

References SWGSDRangel::SWGDeviceSettings::getBladeRf2OutputSettings(), SWGSDRangel::SWGBladeRF2OutputSettings::getReverseApiAddress(), BladeRF2OutputSettings::m_bandwidth, BladeRF2OutputSettings::m_biasTee, BladeRF2OutputSettings::m_centerFrequency, BladeRF2OutputSettings::m_devSampleRate, BladeRF2OutputSettings::m_globalGain, BladeRF2OutputSettings::m_log2Interp, BladeRF2OutputSettings::m_LOppmTenths, BladeRF2OutputSettings::m_reverseAPIAddress, BladeRF2OutputSettings::m_reverseAPIDeviceIndex, BladeRF2OutputSettings::m_reverseAPIPort, BladeRF2OutputSettings::m_transverterDeltaFrequency, BladeRF2OutputSettings::m_transverterMode, BladeRF2OutputSettings::m_useReverseAPI, SWGSDRangel::SWGBladeRF2OutputSettings::setBandwidth(), SWGSDRangel::SWGBladeRF2OutputSettings::setBiasTee(), SWGSDRangel::SWGBladeRF2OutputSettings::setCenterFrequency(), SWGSDRangel::SWGBladeRF2OutputSettings::setDevSampleRate(), SWGSDRangel::SWGBladeRF2OutputSettings::setGlobalGain(), SWGSDRangel::SWGBladeRF2OutputSettings::setLog2Interp(), SWGSDRangel::SWGBladeRF2OutputSettings::setLOppmTenths(), SWGSDRangel::SWGBladeRF2OutputSettings::setReverseApiAddress(), SWGSDRangel::SWGBladeRF2OutputSettings::setReverseApiDeviceIndex(), SWGSDRangel::SWGBladeRF2OutputSettings::setReverseApiPort(), SWGSDRangel::SWGBladeRF2OutputSettings::setTransverterDeltaFrequency(), SWGSDRangel::SWGBladeRF2OutputSettings::setTransverterMode(), and SWGSDRangel::SWGBladeRF2OutputSettings::setUseReverseApi().

Referenced by webapiSettingsGet(), and webapiSettingsPutPatch().

1033 {
1037  response.getBladeRf2OutputSettings()->setBandwidth(settings.m_bandwidth);
1039  response.getBladeRf2OutputSettings()->setBiasTee(settings.m_biasTee ? 1 : 0);
1042  response.getBladeRf2OutputSettings()->setTransverterMode(settings.m_transverterMode ? 1 : 0);
1043 
1044  response.getBladeRf2OutputSettings()->setUseReverseApi(settings.m_useReverseAPI ? 1 : 0);
1045 
1046  if (response.getBladeRf2OutputSettings()->getReverseApiAddress()) {
1048  } else {
1049  response.getBladeRf2OutputSettings()->setReverseApiAddress(new QString(settings.m_reverseAPIAddress));
1050  }
1051 
1054 }
SWGBladeRF2OutputSettings * getBladeRf2OutputSettings()
void setReverseApiAddress(QString *reverse_api_address)
void setReverseApiDeviceIndex(qint32 reverse_api_device_index)
void setTransverterDeltaFrequency(qint64 transverter_delta_frequency)
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ webapiReportGet()

int BladeRF2Output::webapiReportGet ( SWGSDRangel::SWGDeviceReport response,
QString &  errorMessage 
)
virtual

Reimplemented from DeviceSampleSink.

Definition at line 1023 of file bladerf2output.cpp.

References SWGSDRangel::SWGDeviceReport::getBladeRf2OutputReport(), SWGSDRangel::SWGBladeRF2OutputReport::init(), SWGSDRangel::SWGDeviceReport::setBladeRf2OutputReport(), and webapiFormatDeviceReport().

Referenced by setSampleRate().

1024 {
1025  (void) errorMessage;
1027  response.getBladeRf2OutputReport()->init();
1028  webapiFormatDeviceReport(response);
1029  return 200;
1030 }
void webapiFormatDeviceReport(SWGSDRangel::SWGDeviceReport &response)
SWGBladeRF2OutputReport * getBladeRf2OutputReport()
void setBladeRf2OutputReport(SWGBladeRF2OutputReport *blade_rf2_output_report)
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ webapiReverseSendSettings()

void BladeRF2Output::webapiReverseSendSettings ( QList< QString > &  deviceSettingsKeys,
const BladeRF2OutputSettings settings,
bool  force 
)
private

Definition at line 1123 of file bladerf2output.cpp.

References SWGSDRangel::SWGDeviceSettings::asJson(), SWGSDRangel::SWGDeviceSettings::getBladeRf2OutputSettings(), DeviceAPI::getDeviceSetIndex(), BladeRF2OutputSettings::m_bandwidth, BladeRF2OutputSettings::m_biasTee, BladeRF2OutputSettings::m_centerFrequency, m_deviceAPI, BladeRF2OutputSettings::m_devSampleRate, BladeRF2OutputSettings::m_globalGain, BladeRF2OutputSettings::m_log2Interp, BladeRF2OutputSettings::m_LOppmTenths, m_networkManager, m_networkRequest, BladeRF2OutputSettings::m_reverseAPIAddress, BladeRF2OutputSettings::m_reverseAPIDeviceIndex, BladeRF2OutputSettings::m_reverseAPIPort, BladeRF2OutputSettings::m_transverterDeltaFrequency, BladeRF2OutputSettings::m_transverterMode, SWGSDRangel::SWGBladeRF2OutputSettings::setBandwidth(), SWGSDRangel::SWGBladeRF2OutputSettings::setBiasTee(), SWGSDRangel::SWGDeviceSettings::setBladeRf2OutputSettings(), SWGSDRangel::SWGBladeRF2OutputSettings::setCenterFrequency(), SWGSDRangel::SWGDeviceSettings::setDeviceHwType(), SWGSDRangel::SWGBladeRF2OutputSettings::setDevSampleRate(), SWGSDRangel::SWGDeviceSettings::setDirection(), SWGSDRangel::SWGBladeRF2OutputSettings::setGlobalGain(), SWGSDRangel::SWGBladeRF2OutputSettings::setLog2Interp(), SWGSDRangel::SWGBladeRF2OutputSettings::setLOppmTenths(), SWGSDRangel::SWGDeviceSettings::setOriginatorIndex(), SWGSDRangel::SWGBladeRF2OutputSettings::setTransverterDeltaFrequency(), and SWGSDRangel::SWGBladeRF2OutputSettings::setTransverterMode().

Referenced by applySettings().

1124 {
1126  swgDeviceSettings->setDirection(1); // single Tx
1127  swgDeviceSettings->setOriginatorIndex(m_deviceAPI->getDeviceSetIndex());
1128  swgDeviceSettings->setDeviceHwType(new QString("BladeRF2"));
1130  SWGSDRangel::SWGBladeRF2OutputSettings *swgBladeRF2OutputSettings = swgDeviceSettings->getBladeRf2OutputSettings();
1131 
1132  // transfer data that has been modified. When force is on transfer all data except reverse API data
1133 
1134  if (deviceSettingsKeys.contains("centerFrequency") || force) {
1135  swgBladeRF2OutputSettings->setCenterFrequency(settings.m_centerFrequency);
1136  }
1137  if (deviceSettingsKeys.contains("LOppmTenths") || force) {
1138  swgBladeRF2OutputSettings->setLOppmTenths(settings.m_LOppmTenths);
1139  }
1140  if (deviceSettingsKeys.contains("devSampleRate") || force) {
1141  swgBladeRF2OutputSettings->setDevSampleRate(settings.m_devSampleRate);
1142  }
1143  if (deviceSettingsKeys.contains("bandwidth") || force) {
1144  swgBladeRF2OutputSettings->setBandwidth(settings.m_bandwidth);
1145  }
1146  if (deviceSettingsKeys.contains("log2Interp") || force) {
1147  swgBladeRF2OutputSettings->setLog2Interp(settings.m_log2Interp);
1148  }
1149  if (deviceSettingsKeys.contains("biasTee") || force) {
1150  swgBladeRF2OutputSettings->setBiasTee(settings.m_biasTee ? 1 : 0);
1151  }
1152  if (deviceSettingsKeys.contains("globalGain") || force) {
1153  swgBladeRF2OutputSettings->setGlobalGain(settings.m_globalGain);
1154  }
1155  if (deviceSettingsKeys.contains("transverterDeltaFrequency") || force) {
1156  swgBladeRF2OutputSettings->setTransverterDeltaFrequency(settings.m_transverterDeltaFrequency);
1157  }
1158  if (deviceSettingsKeys.contains("transverterMode") || force) {
1159  swgBladeRF2OutputSettings->setTransverterMode(settings.m_transverterMode ? 1 : 0);
1160  }
1161 
1162  QString deviceSettingsURL = QString("http://%1:%2/sdrangel/deviceset/%3/device/settings")
1163  .arg(settings.m_reverseAPIAddress)
1164  .arg(settings.m_reverseAPIPort)
1165  .arg(settings.m_reverseAPIDeviceIndex);
1166  m_networkRequest.setUrl(QUrl(deviceSettingsURL));
1167  m_networkRequest.setHeader(QNetworkRequest::ContentTypeHeader, "application/json");
1168 
1169  QBuffer *buffer=new QBuffer();
1170  buffer->open((QBuffer::ReadWrite));
1171  buffer->write(swgDeviceSettings->asJson().toUtf8());
1172  buffer->seek(0);
1173 
1174  // Always use PATCH to avoid passing reverse API settings
1175  m_networkManager->sendCustomRequest(m_networkRequest, "PATCH", buffer);
1176 
1177  delete swgDeviceSettings;
1178 }
QNetworkRequest m_networkRequest
SWGBladeRF2OutputSettings * getBladeRf2OutputSettings()
virtual QString asJson() override
void setOriginatorIndex(qint32 originator_index)
int getDeviceSetIndex() const
Definition: deviceapi.h:131
DeviceAPI * m_deviceAPI
QNetworkAccessManager * m_networkManager
void setDirection(qint32 direction)
void setTransverterDeltaFrequency(qint64 transverter_delta_frequency)
void setDeviceHwType(QString *device_hw_type)
void setBladeRf2OutputSettings(SWGBladeRF2OutputSettings *blade_rf2_output_settings)
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ webapiReverseSendStartStop()

void BladeRF2Output::webapiReverseSendStartStop ( bool  start)
private

Definition at line 1180 of file bladerf2output.cpp.

References SWGSDRangel::SWGDeviceSettings::asJson(), DeviceAPI::getDeviceSetIndex(), m_deviceAPI, m_networkManager, m_networkRequest, BladeRF2OutputSettings::m_reverseAPIAddress, BladeRF2OutputSettings::m_reverseAPIDeviceIndex, BladeRF2OutputSettings::m_reverseAPIPort, m_settings, SWGSDRangel::SWGDeviceSettings::setDeviceHwType(), SWGSDRangel::SWGDeviceSettings::setDirection(), and SWGSDRangel::SWGDeviceSettings::setOriginatorIndex().

Referenced by handleMessage().

1181 {
1183  swgDeviceSettings->setDirection(1); // single Tx
1184  swgDeviceSettings->setOriginatorIndex(m_deviceAPI->getDeviceSetIndex());
1185  swgDeviceSettings->setDeviceHwType(new QString("BladeRF2"));
1186 
1187  QString deviceSettingsURL = QString("http://%1:%2/sdrangel/deviceset/%3/device/run")
1191  m_networkRequest.setUrl(QUrl(deviceSettingsURL));
1192  m_networkRequest.setHeader(QNetworkRequest::ContentTypeHeader, "application/json");
1193 
1194  QBuffer *buffer=new QBuffer();
1195  buffer->open((QBuffer::ReadWrite));
1196  buffer->write(swgDeviceSettings->asJson().toUtf8());
1197  buffer->seek(0);
1198 
1199  if (start) {
1200  m_networkManager->sendCustomRequest(m_networkRequest, "POST", buffer);
1201  } else {
1202  m_networkManager->sendCustomRequest(m_networkRequest, "DELETE", buffer);
1203  }
1204 
1205  delete swgDeviceSettings;
1206 }
QNetworkRequest m_networkRequest
virtual QString asJson() override
void setOriginatorIndex(qint32 originator_index)
int getDeviceSetIndex() const
Definition: deviceapi.h:131
virtual bool start()
DeviceAPI * m_deviceAPI
BladeRF2OutputSettings m_settings
QNetworkAccessManager * m_networkManager
void setDirection(qint32 direction)
void setDeviceHwType(QString *device_hw_type)
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ webapiRun()

int BladeRF2Output::webapiRun ( bool  run,
SWGSDRangel::SWGDeviceState response,
QString &  errorMessage 
)
virtual

Reimplemented from DeviceSampleSink.

Definition at line 1104 of file bladerf2output.cpp.

References BladeRF2Output::MsgStartStop::create(), DeviceAPI::getDeviceEngineStateStr(), SWGSDRangel::SWGDeviceState::getState(), m_deviceAPI, DeviceSampleSink::m_guiMessageQueue, DeviceSampleSink::m_inputMessageQueue, and MessageQueue::push().

Referenced by setSampleRate().

1108 {
1109  (void) errorMessage;
1111  MsgStartStop *message = MsgStartStop::create(run);
1112  m_inputMessageQueue.push(message);
1113 
1114  if (m_guiMessageQueue) // forward to GUI if any
1115  {
1116  MsgStartStop *msgToGUI = MsgStartStop::create(run);
1117  m_guiMessageQueue->push(msgToGUI);
1118  }
1119 
1120  return 200;
1121 }
void push(Message *message, bool emitSignal=true)
Push message onto queue.
MessageQueue m_inputMessageQueue
Input queue to the sink.
DeviceAPI * m_deviceAPI
static MsgStartStop * create(bool startStop)
void getDeviceEngineStateStr(QString &state)
Definition: deviceapi.cpp:389
MessageQueue * m_guiMessageQueue
Input message queue to the GUI.
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ webapiRunGet()

int BladeRF2Output::webapiRunGet ( SWGSDRangel::SWGDeviceState response,
QString &  errorMessage 
)
virtual

Reimplemented from DeviceSampleSink.

Definition at line 1095 of file bladerf2output.cpp.

References DeviceAPI::getDeviceEngineStateStr(), SWGSDRangel::SWGDeviceState::getState(), and m_deviceAPI.

Referenced by setSampleRate().

1098 {
1099  (void) errorMessage;
1101  return 200;
1102 }
DeviceAPI * m_deviceAPI
void getDeviceEngineStateStr(QString &state)
Definition: deviceapi.cpp:389
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ webapiSettingsGet()

int BladeRF2Output::webapiSettingsGet ( SWGSDRangel::SWGDeviceSettings response,
QString &  errorMessage 
)
virtual

Reimplemented from DeviceSampleSink.

Definition at line 950 of file bladerf2output.cpp.

References SWGSDRangel::SWGDeviceSettings::getBladeRf2OutputSettings(), SWGSDRangel::SWGBladeRF2OutputSettings::init(), m_settings, SWGSDRangel::SWGDeviceSettings::setBladeRf2OutputSettings(), and webapiFormatDeviceSettings().

Referenced by setSampleRate().

953 {
954  (void) errorMessage;
956  response.getBladeRf2OutputSettings()->init();
958  return 200;
959 }
SWGBladeRF2OutputSettings * getBladeRf2OutputSettings()
BladeRF2OutputSettings m_settings
void webapiFormatDeviceSettings(SWGSDRangel::SWGDeviceSettings &response, const BladeRF2OutputSettings &settings)
void setBladeRf2OutputSettings(SWGBladeRF2OutputSettings *blade_rf2_output_settings)
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ webapiSettingsPutPatch()

int BladeRF2Output::webapiSettingsPutPatch ( bool  force,
const QStringList &  deviceSettingsKeys,
SWGSDRangel::SWGDeviceSettings response,
QString &  errorMessage 
)
virtual

Reimplemented from DeviceSampleSink.

Definition at line 961 of file bladerf2output.cpp.

References BladeRF2Output::MsgConfigureBladeRF2::create(), SWGSDRangel::SWGBladeRF2OutputSettings::getBandwidth(), SWGSDRangel::SWGBladeRF2OutputSettings::getBiasTee(), SWGSDRangel::SWGDeviceSettings::getBladeRf2OutputSettings(), SWGSDRangel::SWGBladeRF2OutputSettings::getCenterFrequency(), SWGSDRangel::SWGBladeRF2OutputSettings::getDevSampleRate(), SWGSDRangel::SWGBladeRF2OutputSettings::getGlobalGain(), SWGSDRangel::SWGBladeRF2OutputSettings::getLog2Interp(), SWGSDRangel::SWGBladeRF2OutputSettings::getLOppmTenths(), SWGSDRangel::SWGBladeRF2OutputSettings::getReverseApiAddress(), SWGSDRangel::SWGBladeRF2OutputSettings::getReverseApiDeviceIndex(), SWGSDRangel::SWGBladeRF2OutputSettings::getReverseApiPort(), SWGSDRangel::SWGBladeRF2OutputSettings::getTransverterDeltaFrequency(), SWGSDRangel::SWGBladeRF2OutputSettings::getTransverterMode(), SWGSDRangel::SWGBladeRF2OutputSettings::getUseReverseApi(), BladeRF2OutputSettings::m_bandwidth, BladeRF2OutputSettings::m_biasTee, BladeRF2OutputSettings::m_centerFrequency, BladeRF2OutputSettings::m_devSampleRate, BladeRF2OutputSettings::m_globalGain, DeviceSampleSink::m_guiMessageQueue, DeviceSampleSink::m_inputMessageQueue, BladeRF2OutputSettings::m_log2Interp, BladeRF2OutputSettings::m_LOppmTenths, BladeRF2OutputSettings::m_reverseAPIAddress, BladeRF2OutputSettings::m_reverseAPIDeviceIndex, BladeRF2OutputSettings::m_reverseAPIPort, m_settings, BladeRF2OutputSettings::m_transverterDeltaFrequency, BladeRF2OutputSettings::m_transverterMode, BladeRF2OutputSettings::m_useReverseAPI, MessageQueue::push(), and webapiFormatDeviceSettings().

Referenced by setSampleRate().

966 {
967  (void) errorMessage;
969 
970  if (deviceSettingsKeys.contains("centerFrequency")) {
972  }
973  if (deviceSettingsKeys.contains("LOppmTenths")) {
974  settings.m_LOppmTenths = response.getBladeRf2OutputSettings()->getLOppmTenths();
975  }
976  if (deviceSettingsKeys.contains("devSampleRate")) {
978  }
979  if (deviceSettingsKeys.contains("bandwidth")) {
980  settings.m_bandwidth = response.getBladeRf2OutputSettings()->getBandwidth();
981  }
982  if (deviceSettingsKeys.contains("log2Interp")) {
983  settings.m_log2Interp = response.getBladeRf2OutputSettings()->getLog2Interp();
984  }
985  if (deviceSettingsKeys.contains("biasTee")) {
986  settings.m_biasTee = response.getBladeRf2OutputSettings()->getBiasTee() != 0;
987  }
988  if (deviceSettingsKeys.contains("globalGain")) {
989  settings.m_globalGain = response.getBladeRf2OutputSettings()->getGlobalGain();
990  }
991  if (deviceSettingsKeys.contains("transverterDeltaFrequency")) {
993  }
994  if (deviceSettingsKeys.contains("transverterMode")) {
995  settings.m_transverterMode = response.getBladeRf2OutputSettings()->getTransverterMode() != 0;
996  }
997  if (deviceSettingsKeys.contains("useReverseAPI")) {
998  settings.m_useReverseAPI = response.getBladeRf2OutputSettings()->getUseReverseApi() != 0;
999  }
1000  if (deviceSettingsKeys.contains("reverseAPIAddress")) {
1002  }
1003  if (deviceSettingsKeys.contains("reverseAPIPort")) {
1005  }
1006  if (deviceSettingsKeys.contains("reverseAPIDeviceIndex")) {
1008  }
1009 
1010  MsgConfigureBladeRF2 *msg = MsgConfigureBladeRF2::create(settings, force);
1012 
1013  if (m_guiMessageQueue) // forward to GUI if any
1014  {
1015  MsgConfigureBladeRF2 *msgToGUI = MsgConfigureBladeRF2::create(settings, force);
1016  m_guiMessageQueue->push(msgToGUI);
1017  }
1018 
1019  webapiFormatDeviceSettings(response, settings);
1020  return 200;
1021 }
void push(Message *message, bool emitSignal=true)
Push message onto queue.
SWGBladeRF2OutputSettings * getBladeRf2OutputSettings()
MessageQueue m_inputMessageQueue
Input queue to the sink.
BladeRF2OutputSettings m_settings
void webapiFormatDeviceSettings(SWGSDRangel::SWGDeviceSettings &response, const BladeRF2OutputSettings &settings)
MessageQueue * m_guiMessageQueue
Input message queue to the GUI.
static MsgConfigureBladeRF2 * create(const BladeRF2OutputSettings &settings, bool force)
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

Member Data Documentation

◆ m_dev

struct bladerf* BladeRF2Output::m_dev
private

Definition at line 160 of file bladerf2output.h.

◆ m_deviceAPI

DeviceAPI* BladeRF2Output::m_deviceAPI
private

◆ m_deviceDescription

QString BladeRF2Output::m_deviceDescription
private

Definition at line 162 of file bladerf2output.h.

Referenced by getDeviceDescription().

◆ m_deviceShared

DeviceBladeRF2Shared BladeRF2Output::m_deviceShared
private

◆ m_mutex

QMutex BladeRF2Output::m_mutex
private

Definition at line 158 of file bladerf2output.h.

◆ m_networkManager

QNetworkAccessManager* BladeRF2Output::m_networkManager
private

◆ m_networkRequest

QNetworkRequest BladeRF2Output::m_networkRequest
private

Definition at line 166 of file bladerf2output.h.

Referenced by webapiReverseSendSettings(), and webapiReverseSendStartStop().

◆ m_running

bool BladeRF2Output::m_running
private

Definition at line 164 of file bladerf2output.h.

Referenced by closeDevice(), start(), stop(), and ~BladeRF2Output().

◆ m_settings

BladeRF2OutputSettings BladeRF2Output::m_settings
private

◆ m_thread

BladeRF2OutputThread* BladeRF2Output::m_thread
private

The documentation for this class was generated from the following files: