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.
devicebladerf2.cpp
Go to the documentation of this file.
1 // Copyright (C) 2016-2017 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 <cstdio>
19 #include <cstring>
20 #include <algorithm>
21 
22 #include <QtGlobal>
23 
24 #include "devicebladerf2.h"
25 
27  m_dev(0),
28  m_nbRxChannels(0),
29  m_nbTxChannels(0),
30  m_rxOpen(0),
31  m_txOpen(0)
32 {}
33 
35 {
36  if (m_dev)
37  {
38  bladerf_close(m_dev);
39  m_dev = 0;
40  }
41 
42  if (m_rxOpen) {
43  delete[] m_rxOpen;
44  }
45 
46  if (m_txOpen) {
47  delete[] m_txOpen;
48  }
49 }
50 
51 bool DeviceBladeRF2::open(const char *serial)
52 {
53  int fpga_loaded;
54 
55  if ((m_dev = open_bladerf_from_serial(serial)) == 0)
56  {
57  qCritical("DeviceBladeRF2::open: could not open BladeRF");
58  return false;
59  }
60 
61  fpga_loaded = bladerf_is_fpga_configured(m_dev);
62 
63  if (fpga_loaded < 0)
64  {
65  qCritical("DeviceBladeRF2::open: failed to check FPGA state: %s",
66  bladerf_strerror(fpga_loaded));
67  return false;
68  }
69  else if (fpga_loaded == 0)
70  {
71  qCritical("DeviceBladeRF2::open: the device's FPGA is not loaded.");
72  return false;
73  }
74 
75  m_nbRxChannels = bladerf_get_channel_count(m_dev, BLADERF_RX);
76  m_nbTxChannels = bladerf_get_channel_count(m_dev, BLADERF_TX);
77 
78  m_rxOpen = new bool[m_nbRxChannels];
79  m_txOpen = new bool[m_nbTxChannels];
80  std::fill(m_rxOpen, m_rxOpen + m_nbRxChannels, false);
81  std::fill(m_txOpen, m_txOpen + m_nbTxChannels, false);
82 
83  return true;
84 }
85 
87 {
88  if (m_dev)
89  {
90  bladerf_close(m_dev);
91  m_dev = 0;
92  }
93 }
94 
95 struct bladerf *DeviceBladeRF2::open_bladerf_from_serial(const char *serial)
96 {
97  int status;
98  struct bladerf *dev;
99  struct bladerf_devinfo info;
100 
101  /* Initialize all fields to "don't care" wildcard values.
102  *
103  * Immediately passing this to bladerf_open_with_devinfo() would cause
104  * libbladeRF to open any device on any available backend. */
105  bladerf_init_devinfo(&info);
106 
107  /* Specify the desired device's serial number, while leaving all other
108  * fields in the info structure wildcard values */
109  if (serial != 0)
110  {
111  strncpy(info.serial, serial, BLADERF_SERIAL_LENGTH - 1);
112  info.serial[BLADERF_SERIAL_LENGTH - 1] = '\0';
113  }
114 
115  status = bladerf_open_with_devinfo(&dev, &info);
116 
117  if (status == BLADERF_ERR_NODEV)
118  {
119  qCritical("DeviceBladeRF2::open_bladerf_from_serial: No devices available with serial %s", serial);
120  return 0;
121  }
122  else if (status != 0)
123  {
124  qCritical("DeviceBladeRF2::open_bladerf_from_serial: Failed to open device with serial %s (%s)",
125  serial, bladerf_strerror(status));
126  return 0;
127  }
128  else
129  {
130  return dev;
131  }
132 }
133 
134 bool DeviceBladeRF2::openRx(int channel)
135 {
136  if (!m_dev) {
137  return false;
138  }
139 
140  if ((channel < 0) || (channel >= m_nbRxChannels))
141  {
142  qCritical("DeviceBladeRF2::openRx: invalid Rx channel index %d", channel);
143  return false;
144  }
145 
146  int status;
147 
148  if (!m_rxOpen[channel])
149  {
150  status = bladerf_enable_module(m_dev, BLADERF_CHANNEL_RX(channel), true);
151 
152  if (status < 0)
153  {
154  qCritical("DeviceBladeRF2::openRx: failed to enable Rx channel %d: %s",
155  channel, bladerf_strerror(status));
156  return false;
157  }
158  else
159  {
160  qDebug("DeviceBladeRF2::openRx: Rx channel %d enabled", channel);
161  m_rxOpen[channel] = true;
162  return true;
163  }
164  }
165  else
166  {
167  qDebug("DeviceBladeRF2::openRx: Rx channel %d already opened", channel);
168  return true;
169  }
170 }
171 
172 bool DeviceBladeRF2::openTx(int channel)
173 {
174  if (!m_dev) {
175  return false;
176  }
177 
178  if ((channel < 0) || (channel >= m_nbTxChannels))
179  {
180  qCritical("DeviceBladeRF2::openTx: invalid Tx channel index %d", channel);
181  return false;
182  }
183 
184  int status;
185 
186  if (!m_txOpen[channel])
187  {
188  status = bladerf_enable_module(m_dev, BLADERF_CHANNEL_TX(channel), true);
189 
190  if (status < 0)
191  {
192  qCritical("DeviceBladeRF2::openTx: Failed to enable Tx channel %d: %s",
193  channel, bladerf_strerror(status));
194  return false;
195  }
196  else
197  {
198  qDebug("DeviceBladeRF2::openTx: Tx channel %d enabled", channel);
199  m_txOpen[channel] = true;
200  return true;
201  }
202  }
203  else
204  {
205  qDebug("DeviceBladeRF2::openTx: Tx channel %d already opened", channel);
206  return true;
207  }
208 }
209 
210 void DeviceBladeRF2::closeRx(int channel)
211 {
212  if (!m_dev) {
213  return;
214  }
215 
216  if ((channel < 0) || (channel >= m_nbRxChannels))
217  {
218  qCritical("DeviceBladeRF2::closeRx: invalid Rx channel index %d", channel);
219  return;
220  }
221 
222  if (m_rxOpen[channel])
223  {
224  int status = bladerf_enable_module(m_dev, BLADERF_CHANNEL_RX(channel), false);
225  m_rxOpen[channel] = false;
226 
227  if (status < 0) {
228  qCritical("DeviceBladeRF2::closeRx: failed to disable Rx channel %d: %s", channel, bladerf_strerror(status));
229  } else {
230  qDebug("DeviceBladeRF2::closeRx: Rx channel %d disabled", channel);
231  }
232  }
233  else
234  {
235  qDebug("DeviceBladeRF2::closeRx: Rx channel %d already closed", channel);
236  }
237 }
238 
239 void DeviceBladeRF2::closeTx(int channel)
240 {
241  if (!m_dev) {
242  return;
243  }
244 
245  if ((channel < 0) || (channel >= m_nbTxChannels))
246  {
247  qCritical("DeviceBladeRF2::closeTx: invalid Tx channel index %d", channel);
248  return;
249  }
250 
251  if (m_txOpen[channel])
252  {
253  int status = bladerf_enable_module(m_dev, BLADERF_CHANNEL_TX(channel), false);
254  m_txOpen[channel] = false;
255 
256  if (status < 0) {
257  qCritical("DeviceBladeRF2::closeTx: failed to disable Tx channel %d: %s", channel, bladerf_strerror(status));
258  } else {
259  qDebug("DeviceBladeRF2::closeTx: Tx channel %d disabled", channel);
260  }
261  }
262  else
263  {
264  qDebug("DeviceBladeRF2::closeTx: Rx channel %d already closed", channel);
265  }
266 }
267 
269 {
270  if (m_dev)
271  {
272  const struct bladerf_range *range;
273  int status;
274 
275  status = bladerf_get_frequency_range(m_dev, BLADERF_CHANNEL_RX(0), &range);
276 
277  if (status < 0)
278  {
279  qCritical("DeviceBladeRF2::getFrequencyRangeRx: Failed to get Rx frequency range: %s",
280  bladerf_strerror(status));
281  }
282  else
283  {
284  min = range->min;
285  max = range->max;
286  step = range->step;
287  }
288  }
289 }
290 
292 {
293  if (m_dev)
294  {
295  const struct bladerf_range *range;
296  int status;
297 
298  status = bladerf_get_frequency_range(m_dev, BLADERF_CHANNEL_TX(0), &range);
299 
300  if (status < 0)
301  {
302  qCritical("DeviceBladeRF2::getFrequencyRangeTx: Failed to get Tx frequency range: %s",
303  bladerf_strerror(status));
304  }
305  else
306  {
307  min = range->min;
308  max = range->max;
309  step = range->step;
310  }
311  }
312 }
313 
314 void DeviceBladeRF2::getSampleRateRangeRx(int& min, int& max, int& step)
315 {
316  if (m_dev)
317  {
318  const struct bladerf_range *range;
319  int status;
320 
321  status = bladerf_get_sample_rate_range(m_dev, BLADERF_CHANNEL_RX(0), &range);
322 
323  if (status < 0)
324  {
325  qCritical("DeviceBladeRF2::getSampleRateRangeRx: Failed to get Rx sample rate range: %s",
326  bladerf_strerror(status));
327  }
328  else
329  {
330  min = range->min;
331  max = range->max;
332  step = range->step;
333  }
334  }
335 }
336 
337 void DeviceBladeRF2::getSampleRateRangeTx(int& min, int& max, int& step)
338 {
339  if (m_dev)
340  {
341  const struct bladerf_range *range;
342  int status;
343 
344  status = bladerf_get_sample_rate_range(m_dev, BLADERF_CHANNEL_TX(0), &range);
345 
346  if (status < 0)
347  {
348  qCritical("DeviceBladeRF2::getSampleRateRangeTx: Failed to get Tx sample rate range: %s",
349  bladerf_strerror(status));
350  }
351  else
352  {
353  min = range->min;
354  max = range->max;
355  step = range->step;
356  }
357  }
358 
359 }
360 
361 void DeviceBladeRF2::getBandwidthRangeRx(int& min, int& max, int& step)
362 {
363  if (m_dev)
364  {
365  const struct bladerf_range *range;
366  int status;
367 
368  status = bladerf_get_bandwidth_range(m_dev, BLADERF_CHANNEL_RX(0), &range);
369 
370  if (status < 0)
371  {
372  qCritical("DeviceBladeRF2::getBandwidthRangeRx: Failed to get Rx bandwidth range: %s",
373  bladerf_strerror(status));
374  }
375  else
376  {
377  min = range->min;
378  max = range->max;
379  step = range->step;
380  }
381  }
382 }
383 
384 void DeviceBladeRF2::getBandwidthRangeTx(int& min, int& max, int& step)
385 {
386  if (m_dev)
387  {
388  const struct bladerf_range *range;
389  int status;
390 
391  status = bladerf_get_bandwidth_range(m_dev, BLADERF_CHANNEL_TX(0), &range);
392 
393  if (status < 0)
394  {
395  qCritical("DeviceBladeRF2::getBandwidthRangeTx: Failed to get Tx bandwidth range: %s",
396  bladerf_strerror(status));
397  }
398  else
399  {
400  min = range->min;
401  max = range->max;
402  step = range->step;
403  }
404  }
405 }
406 
407 void DeviceBladeRF2::getGlobalGainRangeRx(int& min, int& max, int& step)
408 {
409  if (m_dev)
410  {
411  const struct bladerf_range *range;
412  int status;
413 
414  status = bladerf_get_gain_range(m_dev, BLADERF_CHANNEL_RX(0), &range);
415 
416  if (status < 0)
417  {
418  qCritical("DeviceBladeRF2::getGlobalGainRangeRx: Failed to get Rx global gain range: %s",
419  bladerf_strerror(status));
420  }
421  else
422  {
423  min = range->min;
424  max = range->max;
425  step = range->step;
426  }
427  }
428 }
429 
430 void DeviceBladeRF2::getGlobalGainRangeTx(int& min, int& max, int& step)
431 {
432  if (m_dev)
433  {
434  const struct bladerf_range *range;
435  int status;
436 
437  status = bladerf_get_gain_range(m_dev, BLADERF_CHANNEL_TX(0), &range);
438 
439  if (status < 0)
440  {
441  qCritical("DeviceBladeRF2::getGlobalGainRangeTx: Failed to get Tx global gain range: %s",
442  bladerf_strerror(status));
443  }
444  else
445  {
446  min = range->min;
447  max = range->max;
448  step = range->step;
449  }
450  }
451 }
452 
453 int DeviceBladeRF2::getGainModesRx(const bladerf_gain_modes **modes)
454 {
455  if (m_dev)
456  {
457  int n = bladerf_get_gain_modes(m_dev, BLADERF_CHANNEL_RX(0), 0);
458 
459  if (n < 0)
460  {
461  qCritical("DeviceBladeRF2::getGainModesRx: Failed to get the number of Rx gain modes: %s", bladerf_strerror(n));
462  return 0;
463  }
464 
465  int status = bladerf_get_gain_modes(m_dev, BLADERF_CHANNEL_RX(0), modes);
466 
467  if (status < 0)
468  {
469  qCritical("DeviceBladeRF2::getGainModesRx: Failed to get Rx gain modes: %s", bladerf_strerror(status));
470  return 0;
471  }
472  else
473  {
474  return n;
475  }
476  }
477  else
478  {
479  return 0;
480  }
481 }
482 
484 {
485  if (m_dev)
486  {
487  int status = bladerf_set_bias_tee(m_dev, BLADERF_CHANNEL_RX(0), enable);
488 
489  if (status < 0) {
490  qCritical("DeviceBladeRF2::setBiasTeeRx: Failed to set Rx bias tee: %s", bladerf_strerror(status));
491  }
492  }
493 }
494 
496 {
497  if (m_dev)
498  {
499  int status = bladerf_set_bias_tee(m_dev, BLADERF_CHANNEL_TX(0), enable);
500 
501  if (status < 0) {
502  qCritical("DeviceBladeRF2::setBiasTeeTx: Failed to set Tx bias tee: %s", bladerf_strerror(status));
503  }
504  }
505 }
static struct bladerf * open_bladerf_from_serial(const char *serial)
bool openTx(int channel)
void getGlobalGainRangeTx(int &min, int &max, int &step)
void getBandwidthRangeRx(int &min, int &max, int &step)
void setBiasTeeTx(bool enable)
void getBandwidthRangeTx(int &min, int &max, int &step)
void getSampleRateRangeTx(int &min, int &max, int &step)
void getFrequencyRangeRx(uint64_t &min, uint64_t &max, int &step)
void getSampleRateRangeRx(int &min, int &max, int &step)
void setBiasTeeRx(bool enable)
void getFrequencyRangeTx(uint64_t &min, uint64_t &max, int &step)
bool openRx(int channel)
bladerf * m_dev
bool open(const char *serial)
void closeRx(int channel)
void getGlobalGainRangeRx(int &min, int &max, int &step)
int getGainModesRx(const bladerf_gain_modes **)
void closeTx(int channel)
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