Skip to content

Commit

Permalink
libbladeRF: Added masked XB GPIO write routines and XB GPIO macro def…
Browse files Browse the repository at this point in the history
…initions
  • Loading branch information
jynik committed Sep 1, 2015
1 parent a7c9d64 commit 82191d8
Show file tree
Hide file tree
Showing 11 changed files with 523 additions and 84 deletions.
440 changes: 390 additions & 50 deletions host/libraries/libbladeRF/include/libbladeRF.h

Large diffs are not rendered by default.

11 changes: 8 additions & 3 deletions host/libraries/libbladeRF/src/backend/backend.h
Original file line number Diff line number Diff line change
Expand Up @@ -105,10 +105,15 @@ struct backend_fns {
int (*config_gpio_read)(struct bladerf *dev, uint32_t *val);

/* Expansion GPIO accessors */
int (*expansion_gpio_write)(struct bladerf *dev, uint32_t val);
int (*expansion_gpio_write)(struct bladerf *dev,
uint32_t mask, uint32_t val);

int (*expansion_gpio_read)(struct bladerf *dev, uint32_t *val);
int (*expansion_gpio_dir_write)(struct bladerf *dev, uint32_t val);
int (*expansion_gpio_dir_read)(struct bladerf *dev, uint32_t *val);

int (*expansion_gpio_dir_write)(struct bladerf *dev,
uint32_t mask, uint32_t outputs);

int (*expansion_gpio_dir_read)(struct bladerf *dev, uint32_t *outputs);

/* IQ Correction Settings */
int (*set_iq_gain_correction)(struct bladerf *dev, bladerf_module module,
Expand Down
18 changes: 9 additions & 9 deletions host/libraries/libbladeRF/src/backend/usb/nios_access.c
Original file line number Diff line number Diff line change
Expand Up @@ -598,9 +598,6 @@ int nios_xb200_synth_write(struct bladerf *dev, uint32_t value)
return status;
}

/* The update format for GPIO (and the GPIO direction register) accesses allows
* a bitmask to be provided. For this interface, we just want to read all bits
* of the GPIO bank. */
int nios_expansion_gpio_read(struct bladerf *dev, uint32_t *val)
{
int status = nios_32x32_masked_read(dev, NIOS_PKT_32x32_TARGET_EXP,
Expand All @@ -613,13 +610,14 @@ int nios_expansion_gpio_read(struct bladerf *dev, uint32_t *val)
return status;
}

int nios_expansion_gpio_write(struct bladerf *dev, uint32_t val)
int nios_expansion_gpio_write(struct bladerf *dev, uint32_t mask, uint32_t val)
{
int status = nios_32x32_masked_write(dev, NIOS_PKT_32x32_TARGET_EXP,
0xffffffff, val);
mask, val);

if (status == 0) {
log_verbose("%s: Wrote 0x%08x\n", __FUNCTION__, val);
log_verbose("%s: Wrote 0x%08x (with mask 0x%08x)\n",
__FUNCTION__, val, mask);
}

return status;
Expand All @@ -637,13 +635,15 @@ int nios_expansion_gpio_dir_read(struct bladerf *dev, uint32_t *val)
return status;
}

int nios_expansion_gpio_dir_write(struct bladerf *dev, uint32_t val)
int nios_expansion_gpio_dir_write(struct bladerf *dev,
uint32_t mask, uint32_t val)
{
int status = nios_32x32_masked_write(dev, NIOS_PKT_32x32_TARGET_EXP_DIR,
0xffffffff, val);
mask, val);

if (status == 0) {
log_verbose("%s: Wrote 0x%08x\n", __FUNCTION__, val);
log_verbose("%s: Wrote 0x%08x (with mask 0x%08x)\n",
__FUNCTION__, val, mask);
}

return status;
Expand Down
9 changes: 6 additions & 3 deletions host/libraries/libbladeRF/src/backend/usb/nios_access.h
Original file line number Diff line number Diff line change
Expand Up @@ -218,11 +218,12 @@ int nios_expansion_gpio_read(struct bladerf *dev, uint32_t *val);
* Write to expansion GPIO
*
* @param[in] dev Device handle
* @param[in] mask Mask denoting bits to write
* @param[in] value Write value
*
* @return 0 on success, BLADERF_ERR_* code on error.
*/
int nios_expansion_gpio_write(struct bladerf *dev, uint32_t val);
int nios_expansion_gpio_write(struct bladerf *dev, uint32_t mask, uint32_t val);

/**
* Read from expansion GPIO direction register
Expand All @@ -238,11 +239,13 @@ int nios_expansion_gpio_dir_read(struct bladerf *dev, uint32_t *val);
* Write to expansion GPIO direction register
*
* @param[in] dev Device handle
* @param[in] value Write value
* @param[in] mask Mask denoting bits to configure
* @param[in] output '1' bit denotes output, '0' bit denotes input
*
* @return 0 on success, BLADERF_ERR_* code on error.
*/
int nios_expansion_gpio_dir_write(struct bladerf *dev, uint32_t val);
int nios_expansion_gpio_dir_write(struct bladerf *dev,
uint32_t mask, uint32_t outputs);

/**
* Dummy handler for a retune request, which is not supported on
Expand Down
36 changes: 34 additions & 2 deletions host/libraries/libbladeRF/src/backend/usb/nios_legacy_access.c
Original file line number Diff line number Diff line change
Expand Up @@ -550,8 +550,23 @@ int nios_legacy_expansion_gpio_read(struct bladerf *dev, uint32_t *val)
return status;
}

int nios_legacy_expansion_gpio_write(struct bladerf *dev, uint32_t val)
int nios_legacy_expansion_gpio_write(struct bladerf *dev,
uint32_t mask, uint32_t val)
{
int status;
uint32_t tmp;

if (mask != 0xffffffff) {
status = nios_legacy_pio_read(dev, NIOS_PKT_LEGACY_PIO_ADDR_EXP, &tmp);
if (status != 0) {
return status;
}

tmp &= ~mask;
tmp |= (val & mask);
val = tmp;
}

log_verbose("%s: 0x%08x\n", __FUNCTION__, val);
return nios_legacy_pio_write(dev, NIOS_PKT_LEGACY_PIO_ADDR_EXP, val);
}
Expand All @@ -568,8 +583,25 @@ int nios_legacy_expansion_gpio_dir_read(struct bladerf *dev, uint32_t *val)
return status;
}

int nios_legacy_expansion_gpio_dir_write(struct bladerf *dev, uint32_t val)
int nios_legacy_expansion_gpio_dir_write(struct bladerf *dev,
uint32_t mask, uint32_t val)
{
int status;
uint32_t tmp;

if (mask != 0xffffffff) {
status = nios_legacy_pio_read(dev,
NIOS_PKT_LEGACY_PIO_ADDR_EXP_DIR, &tmp);

if (status != 0) {
return status;
}

tmp &= ~mask;
tmp |= (val & mask);
val = tmp;
}

log_verbose("%s: 0x%08\n", __FUNCTION__, val);
return nios_legacy_pio_write(dev, NIOS_PKT_LEGACY_PIO_ADDR_EXP_DIR, val);
}
12 changes: 8 additions & 4 deletions host/libraries/libbladeRF/src/backend/usb/nios_legacy_access.h
Original file line number Diff line number Diff line change
Expand Up @@ -235,11 +235,13 @@ int nios_legacy_expansion_gpio_read(struct bladerf *dev, uint32_t *val);
* Write to expansion GPIO
*
* @param[in] dev Device handle
* @param[in] value Write value
* @param[in[ mask Mask denoting bits to write
* @param[in] value Value to write
*
* @return 0 on success, BLADERF_ERR_* code on error.
*/
int nios_legacy_expansion_gpio_write(struct bladerf *dev, uint32_t val);
int nios_legacy_expansion_gpio_write(struct bladerf *dev,
uint32_t mask, uint32_t val);

/**
* Read from expansion GPIO direction register
Expand All @@ -255,10 +257,12 @@ int nios_legacy_expansion_gpio_dir_read(struct bladerf *dev, uint32_t *val);
* Write to expansion GPIO direction register
*
* @param[in] dev Device handle
* @param[in] value Write value
* @param[in] mask Mask denoting bits to configure
* @param[in] output '1' bit denotes an output, '0' bit denotes an input
*
* @return 0 on success, BLADERF_ERR_* code on error.
*/
int nios_legacy_expansion_gpio_dir_write(struct bladerf *dev, uint32_t val);
int nios_legacy_expansion_gpio_dir_write(struct bladerf *dev,
uint32_t mask, uint32_t outputs);

#endif
36 changes: 34 additions & 2 deletions host/libraries/libbladeRF/src/bladerf.c
Original file line number Diff line number Diff line change
Expand Up @@ -1542,7 +1542,26 @@ int bladerf_expansion_gpio_write(struct bladerf *dev, uint32_t val)
int status;
MUTEX_LOCK(&dev->ctrl_lock);

status = XB_GPIO_WRITE(dev, val);
status = XB_GPIO_WRITE(dev, 0xffffffff, val);

MUTEX_UNLOCK(&dev->ctrl_lock);
return status;
}

int bladerf_expansion_gpio_masked_write(struct bladerf *dev,
uint32_t mask, uint32_t val)
{
int status;
MUTEX_LOCK(&dev->ctrl_lock);

/* Impose FPGA version requirements to ensure users aren't attempting
* to use a version with a known issue on the masked write */
if (!have_cap(dev, BLADERF_CAP_MASKED_XBIO_WRITE) && val != 0xffffffff) {
log_debug("FPGA >= v0.4.1 is required for masked XB GPIO writes.\n");
status = BLADERF_ERR_UNSUPPORTED;
} else {
status = XB_GPIO_WRITE(dev, mask, val);
}

MUTEX_UNLOCK(&dev->ctrl_lock);
return status;
Expand All @@ -1564,11 +1583,24 @@ int bladerf_expansion_gpio_dir_read(struct bladerf *dev, uint32_t *val)
}

int bladerf_expansion_gpio_dir_write(struct bladerf *dev, uint32_t val)
{
return bladerf_expansion_gpio_dir_masked_write(dev, 0xffffffff, val);
}

int bladerf_expansion_gpio_dir_masked_write(struct bladerf *dev,
uint32_t mask, uint32_t val)
{
int status;
MUTEX_LOCK(&dev->ctrl_lock);

status = XB_GPIO_DIR_WRITE(dev, val);
/* Impose FPGA version requirements to ensure users aren't attempting
* to use a version with a known issue on the masked write */
if (!have_cap(dev, BLADERF_CAP_MASKED_XBIO_WRITE) && val != 0xffffffff) {
log_debug("FPGA >= v0.4.1 is required for masked XB GPIO dir writes.\n");
status = BLADERF_ERR_UNSUPPORTED;
} else {
status = XB_GPIO_DIR_WRITE(dev, mask, val);
}

MUTEX_UNLOCK(&dev->ctrl_lock);
return status;
Expand Down
4 changes: 4 additions & 0 deletions host/libraries/libbladeRF/src/capabilities.c
Original file line number Diff line number Diff line change
Expand Up @@ -72,6 +72,10 @@ void capabilities_init_post_fpga_load(struct bladerf *dev)
dev->capabilities |= BLADERF_CAP_ATOMIC_NINT_NFRAC_WRITE;
}

if (version_greater_or_equal(&dev->fpga_version, 0, 4, 1)) {
dev->capabilities |= BLADERF_CAP_MASKED_XBIO_WRITE;
}

log_verbose("Capability mask after FPGA load: 0x%016"PRIx64"\n",
dev->capabilities);
}
10 changes: 10 additions & 0 deletions host/libraries/libbladeRF/src/capabilities.h
Original file line number Diff line number Diff line change
Expand Up @@ -79,6 +79,16 @@
*/
#define BLADERF_CAP_ATOMIC_NINT_NFRAC_WRITE (1 << 6)

/**
* FPGA v0.4.1 fixed an issue with masked writes to the expansion GPIO
* and expansion GPIO direction registers.
*
* To help users avoid getting bitten by this bug, we'll mark this
* as a capability and disallow masked writes unless an FPGA with the
* fix is being used.
*/
#define BLADERF_CAP_MASKED_XBIO_WRITE (1 << 7)

/**
* Firmware 1.7.1 introduced firmware-based loopback
*/
Expand Down
12 changes: 6 additions & 6 deletions host/libraries/libbladeRF/src/xb.c
Original file line number Diff line number Diff line change
Expand Up @@ -91,10 +91,10 @@ static int xb200_attach(struct bladerf *dev) {
if ((status = XB_GPIO_READ(dev, &val)))
return status;

if ((status = XB_GPIO_DIR_WRITE(dev, 0x3C00383E)))
if ((status = XB_GPIO_DIR_WRITE(dev, 0xffffffff, 0x3C00383E)))
return status;

if ((status = XB_GPIO_WRITE(dev, 0x800)))
if ((status = XB_GPIO_WRITE(dev, 0xffffffff, 0x800)))
return status;

// Load ADF4351 registers via SPI
Expand Down Expand Up @@ -122,7 +122,7 @@ static int xb200_attach(struct bladerf *dev) {
else {
log_debug(" MUXOUT Bit not set: FAIL\n");
}
status = XB_GPIO_WRITE(dev, 0x3C000800);
status = XB_GPIO_WRITE(dev, 0xffffffff, 0x3C000800);

return status;
}
Expand All @@ -144,7 +144,7 @@ int xb200_enable(struct bladerf *dev, bool enable) {
if (status || (val == orig))
return status;

return XB_GPIO_WRITE(dev, val);
return XB_GPIO_WRITE(dev, 0xffffffff, val);
}

int xb_attach(struct bladerf *dev, bladerf_xb xb) {
Expand Down Expand Up @@ -301,7 +301,7 @@ static int set_filterbank_mux(struct bladerf *dev, bladerf_module module, blader
log_debug("Engaging %s band XB-200 %s filter\n", filters[filter],
mask == BLADERF_XB_TX_MASK ? "TX" : "RX");

status = XB_GPIO_WRITE(dev, val);
status = XB_GPIO_WRITE(dev, 0xffffffff, val);
if (status != 0) {
return status;
}
Expand Down Expand Up @@ -467,7 +467,7 @@ int xb200_set_path(struct bladerf *dev,
}
}

return XB_GPIO_WRITE(dev, val);
return XB_GPIO_WRITE(dev, 0xffffffff, val);
}

int xb200_get_path(struct bladerf *dev,
Expand Down
19 changes: 14 additions & 5 deletions host/libraries/libbladeRF/src/xb.h
Original file line number Diff line number Diff line change
Expand Up @@ -28,11 +28,20 @@
#include <libbladeRF.h>
#include "bladerf_priv.h"

#define XB_SPI_WRITE(dev, val) dev->fn->xb_spi(dev, val)
#define XB_GPIO_READ(dev, val) dev->fn->expansion_gpio_read(dev, val)
#define XB_GPIO_WRITE(dev, val) dev->fn->expansion_gpio_write(dev, val)
#define XB_GPIO_DIR_READ(dev, val) dev->fn->expansion_gpio_dir_read(dev, val)
#define XB_GPIO_DIR_WRITE(dev, val) dev->fn->expansion_gpio_dir_write(dev, val)
#define XB_SPI_WRITE(dev, val) \
dev->fn->xb_spi(dev, val)

#define XB_GPIO_READ(dev, val) \
dev->fn->expansion_gpio_read(dev, val)

#define XB_GPIO_WRITE(dev, mask, val) \
dev->fn->expansion_gpio_write(dev, mask, val)

#define XB_GPIO_DIR_READ(dev, val) \
dev->fn->expansion_gpio_dir_read(dev, val)

#define XB_GPIO_DIR_WRITE(dev, mask, val) \
dev->fn->expansion_gpio_dir_write(dev, mask, val)

/**
* Attach and enable an expansion board's features
Expand Down

0 comments on commit 82191d8

Please sign in to comment.