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.
bladerf1output.cpp
Go to the documentation of this file.
1 // Copyright (C) 2015 Edouard Griffiths, F4EXB //
3 // //
4 // This program is free software; you can redistribute it and/or modify //
5 // it under the terms of the GNU General Public License as published by //
6 // the Free Software Foundation as version 3 of the License, or //
7 // (at your option) any later version. //
8 // //
9 // This program is distributed in the hope that it will be useful, //
10 // but WITHOUT ANY WARRANTY; without even the implied warranty of //
11 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the //
12 // GNU General Public License V3 for more details. //
13 // //
14 // You should have received a copy of the GNU General Public License //
15 // along with this program. If not, see <http://www.gnu.org/licenses/>. //
17 
18 #include <string.h>
19 #include <errno.h>
20 
21 #include <QDebug>
22 #include <QNetworkReply>
23 #include <QBuffer>
24 
25 #include "SWGDeviceSettings.h"
26 #include "SWGDeviceState.h"
27 
28 #include "dsp/dspcommands.h"
31 #include "dsp/dspengine.h"
32 #include "device/deviceapi.h"
34 #include "bladerf1outputthread.h"
35 #include "bladerf1output.h"
36 
40 
42  m_deviceAPI(deviceAPI),
43  m_settings(),
44  m_dev(0),
45  m_bladerfThread(0),
46  m_deviceDescription("BladeRFOutput"),
47  m_running(false)
48 {
49  m_sampleSourceFifo.resize(16*BLADERFOUTPUT_BLOCKSIZE);
50  openDevice();
51  m_deviceAPI->setNbSinkStreams(1);
52  m_deviceAPI->setBuddySharedPtr(&m_sharedParams);
53  m_networkManager = new QNetworkAccessManager();
54  connect(m_networkManager, SIGNAL(finished(QNetworkReply*)), this, SLOT(networkManagerFinished(QNetworkReply*)));
55 }
56 
58 {
59  disconnect(m_networkManager, SIGNAL(finished(QNetworkReply*)), this, SLOT(networkManagerFinished(QNetworkReply*)));
60  delete m_networkManager;
61 
62  if (m_running) {
63  stop();
64  }
65 
66  closeDevice();
68 }
69 
71 {
72  delete this;
73 }
74 
76 {
77  if (m_dev != 0)
78  {
79  closeDevice();
80  }
81 
82  int res;
83 
85 
86  if (m_deviceAPI->getSourceBuddies().size() > 0)
87  {
88  DeviceAPI *sourceBuddy = m_deviceAPI->getSourceBuddies()[0];
89  DeviceBladeRF1Params *buddySharedParams = (DeviceBladeRF1Params *) sourceBuddy->getBuddySharedPtr();
90 
91  if (buddySharedParams == 0)
92  {
93  qCritical("BladerfOutput::start: could not get shared parameters from buddy");
94  return false;
95  }
96 
97  if (buddySharedParams->m_dev == 0) // device is not opened by buddy
98  {
99  qCritical("BladerfOutput::start: could not get BladeRF handle from buddy");
100  return false;
101  }
102 
103  m_sharedParams = *(buddySharedParams); // copy parameters from buddy
104  m_dev = m_sharedParams.m_dev; // get BladeRF handle
105  }
106  else
107  {
109  {
110  qCritical("BladerfOutput::start: could not open BladeRF %s", qPrintable(m_deviceAPI->getSamplingDeviceSerial()));
111  return false;
112  }
113 
115  }
116 
117  // TODO: adjust USB transfer data according to sample rate
118  if ((res = bladerf_sync_config(m_dev, BLADERF_TX_X1, BLADERF_FORMAT_SC16_Q11, 64, 8192, 32, 10000)) < 0)
119  {
120  qCritical("BladerfOutput::start: bladerf_sync_config with return code %d", res);
121  return false;
122  }
123 
124  if ((res = bladerf_enable_module(m_dev, BLADERF_MODULE_TX, true)) < 0)
125  {
126  qCritical("BladerfOutput::start: bladerf_enable_module with return code %d", res);
127  return false;
128  }
129 
130  return true;
131 }
132 
134 {
135  applySettings(m_settings, true);
136 }
137 
139 {
140 // QMutexLocker mutexLocker(&m_mutex);
141 
142  if (!m_dev) {
143  return false;
144  }
145 
146  if (m_running) stop();
147 
149 
150 // mutexLocker.unlock();
151  applySettings(m_settings, true);
152 
154 
156 
157  qDebug("BladerfOutput::start: started");
158  m_running = true;
159 
160  return true;
161 }
162 
164 {
165  int res;
166 
167  if (m_dev == 0) { // was never open
168  return;
169  }
170 
171  if ((res = bladerf_enable_module(m_dev, BLADERF_MODULE_TX, false)) < 0)
172  {
173  qCritical("BladerfOutput::closeDevice: bladerf_enable_module with return code %d", res);
174  }
175 
176  if (m_deviceAPI->getSourceBuddies().size() == 0)
177  {
178  qDebug("BladerfOutput::closeDevice: closing device since Rx side is not open");
179 
180  if (m_dev != 0) // close BladeRF
181  {
182  bladerf_close(m_dev);
183  }
184  }
185 
186  m_sharedParams.m_dev = 0;
187  m_dev = 0;
188 }
189 
191 {
192 // QMutexLocker mutexLocker(&m_mutex);
193  if (m_bladerfThread != 0)
194  {
196  delete m_bladerfThread;
197  m_bladerfThread = 0;
198  }
199 
200  m_running = false;
201 }
202 
203 QByteArray Bladerf1Output::serialize() const
204 {
205  return m_settings.serialize();
206 }
207 
208 bool Bladerf1Output::deserialize(const QByteArray& data)
209 {
210  bool success = true;
211 
212  if (!m_settings.deserialize(data))
213  {
215  success = false;
216  }
217 
219  m_inputMessageQueue.push(message);
220 
221  if (m_guiMessageQueue)
222  {
224  m_guiMessageQueue->push(messageToGUI);
225  }
226 
227  return success;
228 }
229 
231 {
232  return m_deviceDescription;
233 }
234 
236 {
237  int rate = m_settings.m_devSampleRate;
238  return (rate / (1<<m_settings.m_log2Interp));
239 }
240 
242 {
244 }
245 
246 void Bladerf1Output::setCenterFrequency(qint64 centerFrequency)
247 {
249  settings.m_centerFrequency = centerFrequency;
250 
251  MsgConfigureBladerf1* message = MsgConfigureBladerf1::create(settings, false);
252  m_inputMessageQueue.push(message);
253 
254  if (m_guiMessageQueue)
255  {
256  MsgConfigureBladerf1* messageToGUI = MsgConfigureBladerf1::create(settings, false);
257  m_guiMessageQueue->push(messageToGUI);
258  }
259 }
260 
262 {
263  if (MsgConfigureBladerf1::match(message))
264  {
265  MsgConfigureBladerf1& conf = (MsgConfigureBladerf1&) message;
266  qDebug() << "BladerfOutput::handleMessage: MsgConfigureBladerf";
267 
268  if (!applySettings(conf.getSettings(), conf.getForce()))
269  {
270  qDebug("BladeRF config error");
271  }
272 
273  return true;
274  }
275  else if (MsgStartStop::match(message))
276  {
277  MsgStartStop& cmd = (MsgStartStop&) message;
278  qDebug() << "BladerfOutput::handleMessage: MsgStartStop: " << (cmd.getStartStop() ? "start" : "stop");
279 
280  if (cmd.getStartStop())
281  {
283  {
285  }
286  }
287  else
288  {
290  }
291 
294  }
295 
296  return true;
297  }
298  else
299  {
300  return false;
301  }
302 }
303 
304 bool Bladerf1Output::applySettings(const BladeRF1OutputSettings& settings, bool force)
305 {
306  bool forwardChange = false;
307  bool suspendOwnThread = false;
308  bool threadWasRunning = false;
309  QList<QString> reverseAPIKeys;
310 // QMutexLocker mutexLocker(&m_mutex);
311 
312  qDebug() << "BladerfOutput::applySettings: m_dev: " << m_dev;
313 
314  if ((m_settings.m_centerFrequency != settings.m_centerFrequency) || force) {
315  reverseAPIKeys.append("centerFrequency");
316  }
317  if ((m_settings.m_devSampleRate != settings.m_devSampleRate) || force) {
318  reverseAPIKeys.append("devSampleRate");
319  }
320  if ((m_settings.m_log2Interp != settings.m_log2Interp) || force) {
321  reverseAPIKeys.append("log2Interp");
322  }
323 
324  if ((m_settings.m_devSampleRate != settings.m_devSampleRate) ||
325  (m_settings.m_log2Interp != settings.m_log2Interp) || force)
326  {
327  suspendOwnThread = true;
328  }
329 
330  if (suspendOwnThread)
331  {
332  if (m_bladerfThread)
333  {
334  if (m_bladerfThread->isRunning())
335  {
337  threadWasRunning = true;
338  }
339  }
340  }
341 
342  if ((m_settings.m_devSampleRate != settings.m_devSampleRate) || (m_settings.m_log2Interp != settings.m_log2Interp) || force)
343  {
344  int fifoSize;
345 
346  if (settings.m_log2Interp >= 5)
347  {
349  }
350  else
351  {
352  fifoSize = (std::max)(
355  }
356 
357  m_sampleSourceFifo.resize(fifoSize);
358  }
359 
360  if ((m_settings.m_devSampleRate != settings.m_devSampleRate) || force)
361  {
362  forwardChange = true;
363 
364  if (m_dev != 0)
365  {
366  unsigned int actualSamplerate;
367 
368  if (bladerf_set_sample_rate(m_dev, BLADERF_MODULE_TX, settings.m_devSampleRate, &actualSamplerate) < 0) {
369  qCritical("BladerfOutput::applySettings: could not set sample rate: %d", settings.m_devSampleRate);
370  } else {
371  qDebug() << "BladerfOutput::applySettings: bladerf_set_sample_rate(BLADERF_MODULE_TX) actual sample rate is " << actualSamplerate;
372  }
373  }
374  }
375 
376  if ((m_settings.m_log2Interp != settings.m_log2Interp) || force)
377  {
378  forwardChange = true;
379 
380  if (m_bladerfThread != 0)
381  {
383  qDebug() << "BladerfOutput::applySettings: set interpolation to " << (1<<settings.m_log2Interp);
384  }
385  }
386 
387  if ((m_settings.m_vga1 != settings.m_vga1) || force)
388  {
389  reverseAPIKeys.append("vga1");
390 
391  if (m_dev != 0)
392  {
393  if (bladerf_set_txvga1(m_dev, settings.m_vga1) != 0) {
394  qDebug("BladerfOutput::applySettings: bladerf_set_txvga1() failed");
395  } else {
396  qDebug() << "BladerfOutput::applySettings: VGA1 gain set to " << settings.m_vga1;
397  }
398  }
399  }
400 
401  if ((m_settings.m_vga2 != settings.m_vga2) || force)
402  {
403  reverseAPIKeys.append("vga2");
404 
405  if(m_dev != 0)
406  {
407  if (bladerf_set_txvga2(m_dev, settings.m_vga2) != 0) {
408  qDebug("BladerfOutput::applySettings:bladerf_set_rxvga2() failed");
409  } else {
410  qDebug() << "BladerfOutput::applySettings: VGA2 gain set to " << settings.m_vga2;
411  }
412  }
413  }
414 
415  if ((m_settings.m_xb200 != settings.m_xb200) || force)
416  {
417  reverseAPIKeys.append("xb200");
418 
419  if (m_dev != 0)
420  {
421  bool changeSettings;
422 
423  if (m_deviceAPI->getSourceBuddies().size() > 0)
424  {
425  DeviceAPI *buddy = m_deviceAPI->getSourceBuddies()[0];
426 
427  if (buddy->getDeviceSourceEngine()->state() == DSPDeviceSourceEngine::StRunning) { // Tx side running
428  changeSettings = false;
429  } else {
430  changeSettings = true;
431  }
432  }
433  else // No Rx open
434  {
435  changeSettings = true;
436  }
437 
438  if (changeSettings)
439  {
440  if (settings.m_xb200)
441  {
442  if (bladerf_expansion_attach(m_dev, BLADERF_XB_200) != 0) {
443  qDebug("BladerfOutput::applySettings: bladerf_expansion_attach(xb200) failed");
444  } else {
445  qDebug() << "BladerfOutput::applySettings: Attach XB200";
446  }
447  }
448  else
449  {
450  if (bladerf_expansion_attach(m_dev, BLADERF_XB_NONE) != 0) {
451  qDebug("BladerfOutput::applySettings: bladerf_expansion_attach(none) failed");
452  } else {
453  qDebug() << "BladerfOutput::applySettings: Detach XB200";
454  }
455  }
456 
458  }
459  }
460  }
461 
462  if ((m_settings.m_xb200Path != settings.m_xb200Path) || force)
463  {
464  reverseAPIKeys.append("xb200Path");
465 
466  if (m_dev != 0)
467  {
468  if (bladerf_xb200_set_path(m_dev, BLADERF_MODULE_TX, settings.m_xb200Path) != 0) {
469  qDebug("BladerfOutput::applySettings: bladerf_xb200_set_path(BLADERF_MODULE_TX) failed");
470  } else {
471  qDebug() << "BladerfOutput::applySettings: set xb200 path to " << settings.m_xb200Path;
472  }
473  }
474  }
475 
476  if ((m_settings.m_xb200Filter != settings.m_xb200Filter) || force)
477  {
478  reverseAPIKeys.append("xb200Filter");
479 
480  if (m_dev != 0)
481  {
482  if (bladerf_xb200_set_filterbank(m_dev, BLADERF_MODULE_TX, settings.m_xb200Filter) != 0) {
483  qDebug("BladerfOutput::applySettings: bladerf_xb200_set_filterbank(BLADERF_MODULE_TX) failed");
484  } else {
485  qDebug() << "BladerfOutput::applySettings: set xb200 filter to " << settings.m_xb200Filter;
486  }
487  }
488  }
489 
490  if ((m_settings.m_bandwidth != settings.m_bandwidth) || force)
491  {
492  reverseAPIKeys.append("bandwidth");
493 
494  if (m_dev != 0)
495  {
496  unsigned int actualBandwidth;
497 
498  if (bladerf_set_bandwidth(m_dev, BLADERF_MODULE_TX, settings.m_bandwidth, &actualBandwidth) < 0) {
499  qCritical("BladerfOutput::applySettings: could not set bandwidth: %d", settings.m_bandwidth);
500  } else {
501  qDebug() << "BladerfOutput::applySettings: bladerf_set_bandwidth(BLADERF_MODULE_TX) actual bandwidth is " << actualBandwidth;
502  }
503  }
504  }
505 
507  {
508  forwardChange = true;
509  }
510 
511  if (m_dev != 0)
512  {
513  if (bladerf_set_frequency( m_dev, BLADERF_MODULE_TX, settings.m_centerFrequency ) != 0)
514  {
515  qDebug("BladerfOutput::applySettings: bladerf_set_frequency(%lld) failed", settings.m_centerFrequency);
516  }
517  }
518 
519  if (threadWasRunning)
520  {
522  }
523 
524  if (settings.m_useReverseAPI)
525  {
526  bool fullUpdate = ((m_settings.m_useReverseAPI != settings.m_useReverseAPI) && settings.m_useReverseAPI) ||
530  webapiReverseSendSettings(reverseAPIKeys, settings, fullUpdate || force);
531  }
532 
533  m_settings = settings;
534 
535  if (forwardChange)
536  {
537  int sampleRate = m_settings.m_devSampleRate/(1<<m_settings.m_log2Interp);
540  }
541 
542  qDebug() << "BladerfOutput::applySettings: center freq: " << m_settings.m_centerFrequency << " Hz"
543  << " device sample rate: " << m_settings.m_devSampleRate << "S/s"
544  << " baseband sample rate: " << m_settings.m_devSampleRate/(1<<m_settings.m_log2Interp) << "S/s"
545  << " BW: " << m_settings.m_bandwidth << "Hz";
546 
547  return true;
548 }
549 
552  QString& errorMessage)
553 {
554  (void) errorMessage;
556  response.getBladeRf1OutputSettings()->init();
558  return 200;
559 }
560 
562 {
565  response.getBladeRf1OutputSettings()->setVga1(settings.m_vga1);
566  response.getBladeRf1OutputSettings()->setVga2(settings.m_vga2);
567  response.getBladeRf1OutputSettings()->setBandwidth(settings.m_bandwidth);
569  response.getBladeRf1OutputSettings()->setXb200(settings.m_xb200 ? 1 : 0);
570  response.getBladeRf1OutputSettings()->setXb200Path((int) settings.m_xb200Path);
571  response.getBladeRf1OutputSettings()->setXb200Filter((int) settings.m_xb200Filter);
572 
573  response.getBladeRf1OutputSettings()->setUseReverseApi(settings.m_useReverseAPI ? 1 : 0);
574 
577  } else {
578  response.getBladeRf1OutputSettings()->setReverseApiAddress(new QString(settings.m_reverseAPIAddress));
579  }
580 
583 }
584 
586  bool force,
587  const QStringList& deviceSettingsKeys,
588  SWGSDRangel::SWGDeviceSettings& response, // query + response
589  QString& errorMessage)
590 {
591  (void) errorMessage;
593 
594  if (deviceSettingsKeys.contains("centerFrequency")) {
596  }
597  if (deviceSettingsKeys.contains("devSampleRate")) {
599  }
600  if (deviceSettingsKeys.contains("vga1")) {
601  settings.m_vga1 = response.getBladeRf1OutputSettings()->getVga1();
602  }
603  if (deviceSettingsKeys.contains("vga2")) {
604  settings.m_vga2 = response.getBladeRf1OutputSettings()->getVga2();
605  }
606  if (deviceSettingsKeys.contains("bandwidth")) {
607  settings.m_bandwidth = response.getBladeRf1OutputSettings()->getBandwidth();
608  }
609  if (deviceSettingsKeys.contains("log2Interp")) {
610  settings.m_log2Interp = response.getBladeRf1OutputSettings()->getLog2Interp();
611  }
612  if (deviceSettingsKeys.contains("xb200")) {
613  settings.m_xb200 = response.getBladeRf1OutputSettings()->getXb200() == 0 ? 0 : 1;
614  }
615  if (deviceSettingsKeys.contains("xb200Path")) {
616  settings.m_xb200Path = static_cast<bladerf_xb200_path>(response.getBladeRf1OutputSettings()->getXb200Path());
617  }
618  if (deviceSettingsKeys.contains("xb200Filter")) {
619  settings.m_xb200Filter = static_cast<bladerf_xb200_filter>(response.getBladeRf1OutputSettings()->getXb200Filter());
620  }
621  if (deviceSettingsKeys.contains("useReverseAPI")) {
622  settings.m_useReverseAPI = response.getBladeRf1OutputSettings()->getUseReverseApi() != 0;
623  }
624  if (deviceSettingsKeys.contains("reverseAPIAddress")) {
626  }
627  if (deviceSettingsKeys.contains("reverseAPIPort")) {
629  }
630  if (deviceSettingsKeys.contains("reverseAPIDeviceIndex")) {
632  }
633 
634  MsgConfigureBladerf1 *msg = MsgConfigureBladerf1::create(settings, force);
636 
637  if (m_guiMessageQueue) // forward to GUI if any
638  {
639  MsgConfigureBladerf1 *msgToGUI = MsgConfigureBladerf1::create(settings, force);
640  m_guiMessageQueue->push(msgToGUI);
641  }
642 
643  webapiFormatDeviceSettings(response, settings);
644  return 200;
645 }
646 
648  SWGSDRangel::SWGDeviceState& response,
649  QString& errorMessage)
650 {
651  (void) errorMessage;
653  return 200;
654 }
655 
657  bool run,
658  SWGSDRangel::SWGDeviceState& response,
659  QString& errorMessage)
660 {
661  (void) errorMessage;
663  MsgStartStop *message = MsgStartStop::create(run);
664  m_inputMessageQueue.push(message);
665 
666  if (m_guiMessageQueue)
667  {
668  MsgStartStop *messagetoGui = MsgStartStop::create(run);
669  m_guiMessageQueue->push(messagetoGui);
670  }
671 
672  return 200;
673 }
674 
675 void Bladerf1Output::webapiReverseSendSettings(QList<QString>& deviceSettingsKeys, const BladeRF1OutputSettings& settings, bool force)
676 {
678  swgDeviceSettings->setDirection(1); // single Tx
679  swgDeviceSettings->setOriginatorIndex(m_deviceAPI->getDeviceSetIndex());
680  swgDeviceSettings->setDeviceHwType(new QString("BladeRF1"));
682  SWGSDRangel::SWGBladeRF1OutputSettings *swgBladeRF1OutputSettings = swgDeviceSettings->getBladeRf1OutputSettings();
683 
684  // transfer data that has been modified. When force is on transfer all data except reverse API data
685 
686  if (deviceSettingsKeys.contains("centerFrequency") || force) {
687  swgBladeRF1OutputSettings->setCenterFrequency(settings.m_centerFrequency);
688  }
689  if (deviceSettingsKeys.contains("devSampleRate") || force) {
690  swgBladeRF1OutputSettings->setDevSampleRate(settings.m_devSampleRate);
691  }
692  if (deviceSettingsKeys.contains("vga1") || force) {
693  swgBladeRF1OutputSettings->setVga1(settings.m_vga1);
694  }
695  if (deviceSettingsKeys.contains("vga2") || force) {
696  swgBladeRF1OutputSettings->setVga2(settings.m_vga2);
697  }
698  if (deviceSettingsKeys.contains("bandwidth") || force) {
699  swgBladeRF1OutputSettings->setBandwidth(settings.m_bandwidth);
700  }
701  if (deviceSettingsKeys.contains("log2Interp") || force) {
702  swgBladeRF1OutputSettings->setLog2Interp(settings.m_log2Interp);
703  }
704  if (deviceSettingsKeys.contains("xb200") || force) {
705  swgBladeRF1OutputSettings->setXb200(settings.m_xb200 ? 1 : 0);
706  }
707  if (deviceSettingsKeys.contains("xb200Path") || force) {
708  swgBladeRF1OutputSettings->setXb200Path((int) settings.m_xb200Path);
709  }
710  if (deviceSettingsKeys.contains("xb200Filter") || force) {
711  swgBladeRF1OutputSettings->setXb200Filter((int) settings.m_xb200Filter);
712  }
713 
714  QString deviceSettingsURL = QString("http://%1:%2/sdrangel/deviceset/%3/device/settings")
715  .arg(settings.m_reverseAPIAddress)
716  .arg(settings.m_reverseAPIPort)
717  .arg(settings.m_reverseAPIDeviceIndex);
718  m_networkRequest.setUrl(QUrl(deviceSettingsURL));
719  m_networkRequest.setHeader(QNetworkRequest::ContentTypeHeader, "application/json");
720 
721  QBuffer *buffer=new QBuffer();
722  buffer->open((QBuffer::ReadWrite));
723  buffer->write(swgDeviceSettings->asJson().toUtf8());
724  buffer->seek(0);
725 
726  // Always use PATCH to avoid passing reverse API settings
727  m_networkManager->sendCustomRequest(m_networkRequest, "PATCH", buffer);
728 
729  delete swgDeviceSettings;
730 }
731 
733 {
735  swgDeviceSettings->setDirection(1); // single Tx
736  swgDeviceSettings->setOriginatorIndex(m_deviceAPI->getDeviceSetIndex());
737  swgDeviceSettings->setDeviceHwType(new QString("BladeRF1"));
738 
739  QString deviceSettingsURL = QString("http://%1:%2/sdrangel/deviceset/%3/device/run")
743  m_networkRequest.setUrl(QUrl(deviceSettingsURL));
744  m_networkRequest.setHeader(QNetworkRequest::ContentTypeHeader, "application/json");
745 
746  QBuffer *buffer=new QBuffer();
747  buffer->open((QBuffer::ReadWrite));
748  buffer->write(swgDeviceSettings->asJson().toUtf8());
749  buffer->seek(0);
750 
751  if (start) {
752  m_networkManager->sendCustomRequest(m_networkRequest, "POST", buffer);
753  } else {
754  m_networkManager->sendCustomRequest(m_networkRequest, "DELETE", buffer);
755  }
756 
757  delete swgDeviceSettings;
758 }
759 
760 void Bladerf1Output::networkManagerFinished(QNetworkReply *reply)
761 {
762  QNetworkReply::NetworkError replyError = reply->error();
763 
764  if (replyError)
765  {
766  qWarning() << "Bladerf1Output::networkManagerFinished:"
767  << " error(" << (int) replyError
768  << "): " << replyError
769  << ": " << reply->errorString();
770  return;
771  }
772 
773  QString answer = reply->readAll();
774  answer.chop(1); // remove last \n
775  qDebug("Bladerf1Output::networkManagerFinished: reply:\n%s", answer.toStdString().c_str());
776 }
virtual QByteArray serialize() const
static bool open_bladerf(struct bladerf **dev, const char *serial)
bool m_xb200Attached
true if XB200 is attached and owned by the party
virtual void destroy()
bool startDeviceEngine()
Start the device engine corresponding to the stream type.
Definition: deviceapi.cpp:253
virtual bool handleMessage(const Message &message)
void setBladeRf1OutputSettings(SWGBladeRF1OutputSettings *blade_rf1_output_settings)
virtual void init()
initializations to be done when all collaborating objects are created and possibly connected ...
#define BLADERFOUTPUT_BLOCKSIZE
void push(Message *message, bool emitSignal=true)
Push message onto queue.
bool deserialize(const QByteArray &data)
void stopDeviceEngine()
Stop the device engine corresponding to the stream type.
Definition: deviceapi.cpp:266
virtual int webapiSettingsGet(SWGSDRangel::SWGDeviceSettings &response, QString &errorMessage)
QNetworkRequest m_networkRequest
virtual const QString & getDeviceDescription() const
virtual void setCenterFrequency(qint64 centerFrequency)
virtual void stop()
SWGBladeRF1OutputSettings * getBladeRf1OutputSettings()
virtual QString asJson() override
MessageQueue * getDeviceEngineInputMessageQueue()
Device engine message queue.
Definition: deviceapi.cpp:316
void webapiFormatDeviceSettings(SWGSDRangel::SWGDeviceSettings &response, const BladeRF1OutputSettings &settings)
bladerf_xb200_path m_xb200Path
QString m_deviceDescription
static const int m_sampleFifoMinSize32
bool initDeviceEngine()
Init the device engine corresponding to the stream type.
Definition: deviceapi.cpp:240
virtual bool start()
struct bladerf * m_dev
void setOriginatorIndex(qint32 originator_index)
static const float m_sampleFifoLengthInSeconds
MessageQueue m_inputMessageQueue
Input queue to the sink.
void setReverseApiAddress(QString *reverse_api_address)
virtual bool deserialize(const QByteArray &data)
virtual quint64 getCenterFrequency() const
Center frequency exposed by the sink.
const BladeRF1OutputSettings & getSettings() const
int getDeviceSetIndex() const
Definition: deviceapi.h:131
void * getBuddySharedPtr() const
Definition: deviceapi.h:161
#define MESSAGE_CLASS_DEFINITION(Name, BaseClass)
Definition: message.h:52
DSPDeviceSourceEngine * getDeviceSourceEngine()
Definition: deviceapi.h:153
bool applySettings(const BladeRF1OutputSettings &settings, bool force)
DeviceAPI * m_deviceAPI
void setReverseApiDeviceIndex(qint32 reverse_api_device_index)
void setBuddySharedPtr(void *ptr)
Definition: deviceapi.h:162
static const int m_sampleFifoMinSize
virtual int webapiRun(bool run, SWGSDRangel::SWGDeviceState &response, QString &errorMessage)
static bool match(const Message *message)
Definition: message.cpp:45
virtual int webapiRunGet(SWGSDRangel::SWGDeviceState &response, QString &errorMessage)
void setLog2Interpolation(unsigned int log2_interp)
bladerf_xb200_filter m_xb200Filter
QNetworkAccessManager * m_networkManager
void networkManagerFinished(QNetworkReply *reply)
void getDeviceEngineStateStr(QString &state)
Definition: deviceapi.cpp:389
void resize(uint32_t size)
const QString & getSamplingDeviceSerial() const
Definition: deviceapi.h:121
Bladerf1OutputThread * m_bladerfThread
virtual int getSampleRate() const
Sample rate exposed by the sink.
DeviceBladeRF1Params m_sharedParams
void webapiReverseSendSettings(QList< QString > &deviceSettingsKeys, const BladeRF1OutputSettings &settings, bool force)
struct bladerf * m_dev
device handle if the party has ownership else 0
State state() const
Return DSP engine current state.
SampleSourceFifo m_sampleSourceFifo
const std::vector< DeviceAPI * > & getSourceBuddies() const
Definition: deviceapi.h:165
BladeRF1OutputSettings m_settings
void setDirection(qint32 direction)
static MsgConfigureBladerf1 * create(const BladeRF1OutputSettings &settings, bool force)
MessageQueue * m_guiMessageQueue
Input message queue to the GUI.
virtual int webapiSettingsPutPatch(bool force, const QStringList &deviceSettingsKeys, SWGSDRangel::SWGDeviceSettings &response, QString &errorMessage)
T max(const T &x, const T &y)
Definition: framework.h:446
void setDeviceHwType(QString *device_hw_type)
static MsgStartStop * create(bool startStop)
virtual ~Bladerf1Output()
void webapiReverseSendStartStop(bool start)