1
0
mirror of https://bitbucket.org/librepilot/librepilot.git synced 2024-12-01 09:24:10 +01:00

RFM22B: Modified the method of tracking RX errors, and now reporting Good, Corrected, Error, and Missed packets to the GCS. Also removed some less useful fields from the PipXStatus.

This commit is contained in:
Brian Webb 2012-10-13 12:06:17 -07:00 committed by Brian Webb
parent 5a66f64551
commit 4b90f81f6f
7 changed files with 400 additions and 393 deletions

View File

@ -80,11 +80,8 @@ typedef struct {
#define PH_STATUS_DATA_SIZE(p) ((uint8_t*)((p)->ecc) - (uint8_t*)(((PHPacketHandle)(p))->data))
typedef struct {
PHPacketHeader header;
uint16_t retries;
uint16_t errors;
uint16_t uavtalk_errors;
uint16_t dropped;
uint16_t resets;
uint8_t link_quality;
int8_t received_rssi;
uint8_t ecc[RS_ECC_NPARITY];
} PHStatusPacket, *PHStatusPacketHandle;

View File

@ -62,11 +62,6 @@
typedef struct {
uint32_t pairID;
uint16_t retries;
uint16_t errors;
uint16_t uavtalk_errors;
uint16_t resets;
uint16_t dropped;
int8_t rssi;
uint8_t lastContact;
} PairStats;
@ -271,11 +266,6 @@ static int32_t RadioInitialize(void)
{
data->pairStats[i].pairID = 0;
data->pairStats[i].rssi = -127;
data->pairStats[i].retries = 0;
data->pairStats[i].errors = 0;
data->pairStats[i].uavtalk_errors = 0;
data->pairStats[i].resets = 0;
data->pairStats[i].dropped = 0;
data->pairStats[i].lastContact = 0;
}
// The first slot is reserved for our current pairID
@ -355,11 +345,6 @@ static void StatusHandler(PHStatusPacketHandle status, int8_t rssi, int8_t afc)
if(found)
{
data->pairStats[id_idx].rssi = rssi;
data->pairStats[id_idx].retries = status->retries;
data->pairStats[id_idx].errors = status->errors;
data->pairStats[id_idx].uavtalk_errors = status->uavtalk_errors;
data->pairStats[id_idx].resets = status->resets;
data->pairStats[id_idx].dropped = status->dropped;
data->pairStats[id_idx].lastContact = 0;
}
@ -384,11 +369,6 @@ static void StatusHandler(PHStatusPacketHandle status, int8_t rssi, int8_t afc)
}
data->pairStats[min_idx].pairID = id;
data->pairStats[min_idx].rssi = rssi;
data->pairStats[min_idx].retries = status->retries;
data->pairStats[min_idx].errors = status->errors;
data->pairStats[min_idx].uavtalk_errors = status->uavtalk_errors;
data->pairStats[min_idx].resets = status->resets;
data->pairStats[min_idx].dropped = status->dropped;
data->pairStats[min_idx].lastContact = 0;
}
}
@ -406,19 +386,27 @@ static void radioStatusTask(void *parameters)
PipXStatusGet(&pipxStatus);
PipXSettingsPairIDGet(&pairID);
// Get the stats from the radio device
struct rfm22b_stats radio_stats;
PIOS_RFM22B_GetStats(pios_rfm22b_id, &radio_stats);
// Update the status
pipxStatus.DeviceID = PIOS_RFM22B_DeviceID(pios_rfm22b_id);
pipxStatus.Retries = data->comTxRetries;
pipxStatus.LinkQuality = PIOS_RFM22B_LinkQuality(pios_rfm22b_id);
pipxStatus.UAVTalkErrors = data->UAVTalkErrors;
pipxStatus.Dropped = data->droppedPackets;
pipxStatus.Resets = PIOS_RFM22B_Resets(pios_rfm22b_id);
pipxStatus.RxGood = radio_stats.rx_good;
pipxStatus.RxCorrected = radio_stats.rx_corrected;
pipxStatus.RxErrors = radio_stats.rx_error;
pipxStatus.RxMissed = radio_stats.rx_missed;
pipxStatus.TxDropped = radio_stats.tx_dropped; // + data->droppedPackets;
pipxStatus.Resets = radio_stats.resets;
pipxStatus.Timeouts = radio_stats.timeouts;
pipxStatus.RSSI = radio_stats.rssi;
pipxStatus.LinkQuality = radio_stats.link_quality;
pipxStatus.TXRate = (uint16_t)((float)(data->txBytes * 1000) / STATS_UPDATE_PERIOD_MS);
data->txBytes = 0;
pipxStatus.RXRate = (uint16_t)((float)(data->rxBytes * 1000) / STATS_UPDATE_PERIOD_MS);
data->rxBytes = 0;
pipxStatus.LinkState = PIPXSTATUS_LINKSTATE_DISCONNECTED;
pipxStatus.RSSI = PIOS_RFM22B_LinkQuality(pios_rfm22b_id);
LINK_LED_OFF;
// Update the potential pairing contacts
@ -432,21 +420,11 @@ static void radioStatusTask(void *parameters)
{
data->pairStats[i].pairID = 0;
data->pairStats[i].rssi = -127;
data->pairStats[i].retries = 0;
data->pairStats[i].errors = 0;
data->pairStats[i].uavtalk_errors = 0;
data->pairStats[i].resets = 0;
data->pairStats[i].dropped = 0;
data->pairStats[i].lastContact = 0;
}
// Add the paired devices statistics to ours.
if(pairID && (data->pairStats[i].pairID == pairID) && (data->pairStats[i].rssi > -127))
{
pipxStatus.Retries += data->pairStats[i].retries;
pipxStatus.UAVTalkErrors += data->pairStats[i].uavtalk_errors;
pipxStatus.Dropped += data->pairStats[i].dropped;
pipxStatus.Resets += data->pairStats[i].resets;
pipxStatus.Dropped += data->pairStats[i].dropped;
pipxStatus.LinkState = PIPXSTATUS_LINKSTATE_CONNECTED;
LINK_LED_ON;
}

View File

@ -158,6 +158,14 @@ enum pios_rfm22b_event {
RFM22B_EVENT_NUM_EVENTS // Must be last
};
#define RFM22B_RX_PACKET_STATS_LEN 4
enum pios_rfm22b_rx_packet_status {
RFM22B_GOOD_RX_PACKET = 0x00,
RFM22B_CORRECTED_RX_PACKET = 0x01,
RFM22B_ERROR_RX_PACKET = 0x2,
RFM22B_MISSED_RX_PACKET = 0x3
};
struct pios_rfm22b_dev {
enum pios_rfm22b_dev_magic magic;
struct pios_rfm22b_cfg cfg;
@ -210,24 +218,17 @@ struct pios_rfm22b_dev {
uint32_t tx_packet_count;
uint32_t rx_packet_count;
// The dropped packet counters
uint8_t slow_block;
uint8_t fast_block;
uint8_t slow_good_packets;
uint8_t fast_good_packets;
uint8_t slow_corrected_packets;
uint8_t fast_corrected_packets;
uint8_t slow_error_packets;
uint8_t fast_error_packets;
uint8_t slow_link_quality;
uint8_t fast_link_quality;
// The error statistics counters
uint16_t prev_rx_seq_num;
uint32_t rx_packet_stats[RFM22B_RX_PACKET_STATS_LEN];
// The packet statistics
struct rfm22b_stats stats;
// Stats
uint16_t resets;
uint16_t timeouts;
uint16_t errors;
// the current RSSI (register value)
uint8_t rssi;
// RSSI in dBm
int8_t rssi_dBm;
@ -316,6 +317,7 @@ static enum pios_rfm22b_event rfm22_timeout(struct pios_rfm22b_dev *rfm22b_dev);
static enum pios_rfm22b_event rfm22_error(struct pios_rfm22b_dev *rfm22b_dev);
static enum pios_rfm22b_event rfm22_fatal_error(struct pios_rfm22b_dev *rfm22b_dev);
static bool rfm22_sendStatus(struct pios_rfm22b_dev *rfm22b_dev);
static void rfm22b_add_rx_status(struct pios_rfm22b_dev *rfm22b_dev, enum pios_rfm22b_rx_packet_status status);
// SPI read/write functions
static void rfm22_assertCs();
@ -574,25 +576,26 @@ int32_t PIOS_RFM22B_Init(uint32_t *rfm22b_id, uint32_t spi_id, uint32_t slave_nu
rfm22b_dev->ezmac_status = 0;
// Initlize the link stats.
rfm22b_dev->slow_block = 0;
rfm22b_dev->fast_block = 0;
rfm22b_dev->slow_good_packets = 0;
rfm22b_dev->fast_good_packets = 0;
rfm22b_dev->slow_corrected_packets = 0;
rfm22b_dev->fast_corrected_packets = 0;
rfm22b_dev->slow_error_packets = 0;
rfm22b_dev->fast_error_packets = 0;
rfm22b_dev->slow_link_quality = 255;
rfm22b_dev->fast_link_quality = 255;
rfm22b_dev->prev_rx_seq_num = 0;
for (uint8_t i = 0; i < RFM22B_RX_PACKET_STATS_LEN; ++i)
rfm22b_dev->rx_packet_stats[i] = 0;
rfm22b_dev->stats.packets_per_sec = 0;
rfm22b_dev->stats.tx_count = 0;
rfm22b_dev->stats.rx_count = 0;
rfm22b_dev->stats.rx_good = 0;
rfm22b_dev->stats.rx_corrected = 0;
rfm22b_dev->stats.rx_error = 0;
rfm22b_dev->stats.rx_missed = 0;
rfm22b_dev->stats.tx_dropped = 0;
rfm22b_dev->stats.resets = 0;
rfm22b_dev->stats.timeouts = 0;
rfm22b_dev->stats.link_quality = 0;
rfm22b_dev->stats.rssi = 0;
// Initialize the stats.
rfm22b_dev->resets = 0;
rfm22b_dev->timeouts = 0;
rfm22b_dev->errors = 0;
rfm22b_dev->tx_packet_count = 0;
rfm22b_dev->rx_packet_count = 0;
rfm22b_dev->rssi = 0;
rfm22b_dev->rssi_dBm = -127;
// Bind the configuration to the device instance
rfm22b_dev->cfg = *cfg;
@ -697,7 +700,7 @@ static void PIOS_RFM22B_InjectEvent(struct pios_rfm22b_dev *rfm22b_dev, enum pio
}
/**
* Returns the unique device ID for th RFM22B device.
* Returns the unique device ID for the RFM22B device.
* \param[in] rfm22b_id The RFM22B device index.
* \return The unique device ID
*/
@ -726,36 +729,52 @@ void PIOS_RFM22B_SetDestinationId(uint32_t rfm22b_id, uint32_t dest_id)
rfm22b_dev->destination_id = (dest_id == 0) ? 0xffffffff : dest_id;
}
uint16_t PIOS_RFM22B_Resets(uint32_t rfm22b_id)
{
/**
* Returns the device statistics RFM22B device.
* \param[in] rfm22b_id The RFM22B device index.
* \param[out] stats The stats are returned in this structure
*/
void PIOS_RFM22B_GetStats(uint32_t rfm22b_id, struct rfm22b_stats *stats) {
struct pios_rfm22b_dev *rfm22b_dev = (struct pios_rfm22b_dev *)rfm22b_id;
if(!PIOS_RFM22B_validate(rfm22b_dev))
return 0;
return rfm22b_dev->resets;
}
return;
*stats = rfm22b_dev->stats;
uint16_t PIOS_RFM22B_Timeouts(uint32_t rfm22b_id)
{
struct pios_rfm22b_dev *rfm22b_dev = (struct pios_rfm22b_dev *)rfm22b_id;
if(!PIOS_RFM22B_validate(rfm22b_dev))
return 0;
return rfm22b_dev->timeouts;
}
// Add the RX packet statistics
stats->rx_count = rfm22b_dev->prev_rx_seq_num;
stats->tx_count = rfm22b_dev->tx_packet_count;
stats->rx_good = 0;
stats->rx_corrected = 0;
stats->rx_error = 0;
stats->rx_missed = 0;
for (uint8_t i = 0; i < RFM22B_RX_PACKET_STATS_LEN; ++i)
{
uint32_t val = rfm22b_dev->rx_packet_stats[i];
for (uint8_t j = 0; j < 16; ++j)
{
switch ((val >> (j * 2)) & 0x3)
{
case RFM22B_GOOD_RX_PACKET:
stats->rx_good++;
break;
case RFM22B_CORRECTED_RX_PACKET:
stats->rx_corrected++;
break;
case RFM22B_ERROR_RX_PACKET:
stats->rx_error++;
break;
case RFM22B_MISSED_RX_PACKET:
stats->rx_missed++;
break;
}
}
}
uint8_t PIOS_RFM22B_LinkQuality(uint32_t rfm22b_id)
{
struct pios_rfm22b_dev *rfm22b_dev = (struct pios_rfm22b_dev *)rfm22b_id;
if(!PIOS_RFM22B_validate(rfm22b_dev))
return 0;
return rfm22b_dev->slow_link_quality;
}
int8_t PIOS_RFM22B_RSSI(uint32_t rfm22b_id)
{
struct pios_rfm22b_dev *rfm22b_dev = (struct pios_rfm22b_dev *)rfm22b_id;
if(!PIOS_RFM22B_validate(rfm22b_dev))
return 0;
return rfm22b_dev->rssi_dBm;
// Calculate the link quality metric, which is related to the number of good packets in relation to the number of bad packets.
// Note: This assumes that the number of packets sampled for the stats is 64.
// Using this equation, error and missed packets are counted as -2, and corrected packets are counted as -1.
// The rage is 0 (all error or missed packets) to 128 (all good packets).
stats->link_quality = 64 + stats->rx_good - stats->rx_error - stats->rx_missed;
}
static void PIOS_RFM22B_RxStart(uint32_t rfm22b_id, uint16_t rx_bytes_avail)
@ -767,6 +786,24 @@ static void PIOS_RFM22B_RxStart(uint32_t rfm22b_id, uint16_t rx_bytes_avail)
}
static void PIOS_RFM22B_TxStart(uint32_t rfm22b_id, uint16_t tx_bytes_avail)
{
struct pios_rfm22b_dev * rfm22b_dev = (struct pios_rfm22b_dev *)rfm22b_id;
bool valid = PIOS_RFM22B_validate(rfm22b_dev);
PIOS_Assert(valid);
#ifdef NEVER
// Get some data to send
bool need_yield = false;
if(tx_pre_buffer_size == 0)
tx_pre_buffer_size = (rfm22b_dev->tx_out_cb)(rfm22b_dev->tx_out_context, tx_pre_buffer,
TX_BUFFER_SIZE, NULL, &need_yield);
// Inject a send packet event
PIOS_RFM22B_InjectEvent(g_rfm22b_dev, RFM22B_EVENT_TX_START, false);
#endif
}
/**
* Insert a packet on the packet queue for sending.
* Note: If this finction succedds, the packet will be released by the driver, so no release is necessary.
@ -820,6 +857,14 @@ uint32_t PIOS_RFM22B_Receive_Packet(uint32_t rfm22b_id, PHPacketHandle *pret, ui
{
PHPacketHandle p = rfm22b_dev->rx_packet_prev;
uint16_t len = PHPacketSizeECC(p);
uint16_t seq_num = p->header.seq_num;
uint16_t prev_seq_num = rfm22b_dev->prev_rx_seq_num;
uint16_t missed_packets = ((seq_num < prev_seq_num) ? (0xffff - prev_seq_num + seq_num) : (seq_num - prev_seq_num)) - 1;
rfm22b_dev->prev_rx_seq_num = seq_num;
// Add any missed packets into the stats.
for ( ; missed_packets > 0; --missed_packets)
rfm22b_add_rx_status(rfm22b_dev, RFM22B_MISSED_RX_PACKET);
// Attempt to correct any errors in the packet.
decode_data((unsigned char*)p, len);
@ -833,43 +878,24 @@ uint32_t PIOS_RFM22B_Receive_Packet(uint32_t rfm22b_id, PHPacketHandle *pret, ui
if (correct_errors_erasures((unsigned char*)p, len, 0, 0) == 0)
{
// We couldn't correct the error, so drop the packet.
rfm22b_dev->fast_error_packets++;
rfm22b_add_rx_status(rfm22b_dev, RFM22B_ERROR_RX_PACKET);
PHReleaseRXPacket(pios_packet_handler, p);
}
else
{
// We corrected the error.
rfm22b_dev->fast_corrected_packets++;
rfm22b_add_rx_status(rfm22b_dev, RFM22B_CORRECTED_RX_PACKET);
rx_error = false;
}
}
} else
rfm22b_add_rx_status(rfm22b_dev, RFM22B_GOOD_RX_PACKET);
// Return the packet if there were not uncorrectable errors.
if (!rx_error)
{
rfm22b_dev->fast_good_packets++;
*pret = p;
rx_len = rfm22b_dev->rx_packet_len;
// Update the link statistics if necessary.
uint8_t fast_block = (p->header.seq_num >> 2) & 0xff;
uint8_t slow_block = (p->header.seq_num >> 4) & 0xff;
if (rfm22b_dev->fast_block != fast_block)
{
rfm22b_dev->fast_link_quality = (uint8_t)(((4 + (uint16_t)rfm22b_dev->fast_good_packets - rfm22b_dev->fast_error_packets) << 5) - 1);
rfm22b_dev->slow_good_packets += rfm22b_dev->fast_good_packets;
rfm22b_dev->slow_corrected_packets += rfm22b_dev->fast_corrected_packets;
rfm22b_dev->slow_error_packets += rfm22b_dev->fast_error_packets;
rfm22b_dev->fast_good_packets = rfm22b_dev->fast_corrected_packets = rfm22b_dev->fast_error_packets = 0;
rfm22b_dev->fast_block = fast_block;
}
if (rfm22b_dev->slow_block != slow_block)
{
rfm22b_dev->slow_link_quality = (uint8_t)(((16 + (uint16_t)rfm22b_dev->slow_good_packets - rfm22b_dev->slow_error_packets) << 3) - 1);
rfm22b_dev->slow_good_packets = rfm22b_dev->slow_corrected_packets = rfm22b_dev->slow_error_packets = 0;
rfm22b_dev->slow_block = slow_block;
}
}
rfm22b_dev->rx_packet_prev = NULL;
}
@ -962,24 +988,6 @@ static void PIOS_RFM22B_Task(void *parameters)
}
}
static void PIOS_RFM22B_TxStart(uint32_t rfm22b_id, uint16_t tx_bytes_avail)
{
struct pios_rfm22b_dev * rfm22b_dev = (struct pios_rfm22b_dev *)rfm22b_id;
bool valid = PIOS_RFM22B_validate(rfm22b_dev);
PIOS_Assert(valid);
#ifdef NEVER
// Get some data to send
bool need_yield = false;
if(tx_pre_buffer_size == 0)
tx_pre_buffer_size = (rfm22b_dev->tx_out_cb)(rfm22b_dev->tx_out_context, tx_pre_buffer,
TX_BUFFER_SIZE, NULL, &need_yield);
// Inject a send packet event
PIOS_RFM22B_InjectEvent(g_rfm22b_dev, RFM22B_EVENT_TX_START, false);
#endif
}
/**
* Changes the baud rate of the RFM22B peripheral without re-initialising.
* \param[in] rfm22b_id RFM22B name (GPS, TELEM, AUX)
@ -1431,11 +1439,6 @@ static bool rfm22_sendStatus(struct pios_rfm22b_dev *rfm22b_dev)
rfm22b_dev->status_packet.header.destination_id = 0xffffffff; // Broadcast
rfm22b_dev->status_packet.header.type = PACKET_TYPE_STATUS;
rfm22b_dev->status_packet.header.data_size = PH_STATUS_DATA_SIZE(&(rfm22b_dev->status_packet));
rfm22b_dev->status_packet.errors = rfm22b_dev->errors;
rfm22b_dev->status_packet.resets = rfm22b_dev->resets;
rfm22b_dev->status_packet.retries = 0;
rfm22b_dev->status_packet.uavtalk_errors = 0;
rfm22b_dev->status_packet.dropped = 0;
if (xQueueSend(rfm22b_dev->packetQueue, &sph, 0) != pdTRUE)
return false;
@ -1447,8 +1450,6 @@ static bool rfm22_sendStatus(struct pios_rfm22b_dev *rfm22b_dev)
return true;
}
// ************************************
/**
* Read the RFM22B interrupt and device status registers
* \param[in] rfm22b_dev The device structure
@ -1482,6 +1483,21 @@ static bool rfm22_readStatus(struct pios_rfm22b_dev *rfm22b_dev)
return true;
}
/**
* Add a status value to the RX packet status array.
* \param[in] rfm22b_dev The device structure
* \param[in] status The packet status value
*/
static void rfm22b_add_rx_status(struct pios_rfm22b_dev *rfm22b_dev, enum pios_rfm22b_rx_packet_status status)
{
// Shift the status registers
for (uint8_t i = RFM22B_RX_PACKET_STATS_LEN - 1; i > 0; --i)
{
rfm22b_dev->rx_packet_stats[i] = (rfm22b_dev->rx_packet_stats[i] << 2) | (rfm22b_dev->rx_packet_stats[i - 1] >> 30);
}
rfm22b_dev->rx_packet_stats[0] = (rfm22b_dev->rx_packet_stats[0] << 2) | status;
}
static enum pios_rfm22b_event rfm22_detectPreamble(struct pios_rfm22b_dev *rfm22b_dev)
{
@ -1524,9 +1540,9 @@ static enum pios_rfm22b_event rfm22_detectSync(struct pios_rfm22b_dev *rfm22b_de
rfm22b_dev->afc_correction_Hz = (int32_t)(rfm22b_dev->frequency_step_size * afc_correction + 0.5f);
// read rx signal strength .. 45 = -100dBm, 205 = -20dBm
rfm22b_dev->rssi = rfm22_read(RFM22_rssi);
uint8_t rssi = rfm22_read(RFM22_rssi);
// convert to dBm
rfm22b_dev->rssi_dBm = (int8_t)(rfm22b_dev->rssi >> 1) - 122;
rfm22b_dev->rssi_dBm = (int8_t)(rssi >> 1) - 122;
// remember the afc value for this packet
rfm22b_dev->rx_packet_start_afc_Hz = rfm22b_dev->afc_correction_Hz;

View File

@ -77,16 +77,28 @@ enum rfm22b_datarate {
RFM22_datarate_256000 = 13,
};
struct rfm22b_stats {
uint16_t packets_per_sec;
uint16_t tx_count;
uint16_t rx_count;
uint8_t rx_good;
uint8_t rx_corrected;
uint8_t rx_error;
uint8_t rx_missed;
uint8_t tx_dropped;
uint8_t resets;
uint8_t timeouts;
uint8_t link_quality;
int8_t rssi;
};
/* Public Functions */
extern int32_t PIOS_RFM22B_Init(uint32_t *rfb22b_id, uint32_t spi_id, uint32_t slave_num, const struct pios_rfm22b_cfg *cfg);
extern void PIOS_RFM22B_SetTxPower(uint32_t rfm22b_id, enum rfm22b_tx_power tx_pwr);
extern void RFM22_SetDatarate(uint32_t rfm22b_id, enum rfm22b_datarate datarate, bool data_whitening);
extern void PIOS_RFM22B_SetDestinationId(uint32_t rfm22b_id, uint32_t dest_id);
extern uint32_t PIOS_RFM22B_DeviceID(uint32_t rfb22b_id);
extern uint16_t PIOS_RFM22B_Resets(uint32_t rfm22b_id);
extern uint16_t PIOS_RFM22B_Timeouts(uint32_t rfm22b_id);
extern uint8_t PIOS_RFM22B_LinkQuality(uint32_t rfm22b_id);
extern int8_t PIOS_RFM22B_RSSI(uint32_t rfm22b_id);
extern void PIOS_RFM22B_GetStats(uint32_t rfm22b_id, struct rfm22b_stats *stats);
extern bool PIOS_RFM22B_Send_Packet(uint32_t rfm22b_id, PHPacketHandle p, uint32_t max_delay);
extern uint32_t PIOS_RFM22B_Receive_Packet(uint32_t rfm22b_id, PHPacketHandle *p, uint32_t max_delay);

View File

@ -68,17 +68,16 @@ ConfigPipXtremeWidget::ConfigPipXtremeWidget(QWidget *parent) : ConfigTaskWidget
addUAVObjectToWidgetRelation("PipXSettings", "FrequencyCalibration", m_pipx->FrequencyCalibration);
addUAVObjectToWidgetRelation("PipXSettings", "Frequency", m_pipx->Frequency);
addUAVObjectToWidgetRelation("PipXStatus", "MinFrequency", m_pipx->MinFrequency);
addUAVObjectToWidgetRelation("PipXStatus", "MaxFrequency", m_pipx->MaxFrequency);
addUAVObjectToWidgetRelation("PipXStatus", "FrequencyStepSize", m_pipx->FrequencyStepSize);
addUAVObjectToWidgetRelation("PipXStatus", "FrequencyBand", m_pipx->FreqBand);
addUAVObjectToWidgetRelation("PipXStatus", "RSSI", m_pipx->RSSI);
addUAVObjectToWidgetRelation("PipXStatus", "AFC", m_pipx->RxAFC);
addUAVObjectToWidgetRelation("PipXStatus", "Retries", m_pipx->Retries);
addUAVObjectToWidgetRelation("PipXStatus", "LinkQuality", m_pipx->LinkQuality);
addUAVObjectToWidgetRelation("PipXStatus", "RxGood", m_pipx->Good);
addUAVObjectToWidgetRelation("PipXStatus", "RxCorrected", m_pipx->Corrected);
addUAVObjectToWidgetRelation("PipXStatus", "RxErrors", m_pipx->Errors);
addUAVObjectToWidgetRelation("PipXStatus", "RxMissed", m_pipx->Missed);
addUAVObjectToWidgetRelation("PipXStatus", "UAVTalkErrors", m_pipx->UAVTalkErrors);
addUAVObjectToWidgetRelation("PipXStatus", "TxDropped", m_pipx->Dropped);
addUAVObjectToWidgetRelation("PipXStatus", "Resets", m_pipx->Resets);
addUAVObjectToWidgetRelation("PipXStatus", "Dropped", m_pipx->Dropped);
addUAVObjectToWidgetRelation("PipXStatus", "Timeouts", m_pipx->Timeouts);
addUAVObjectToWidgetRelation("PipXStatus", "RSSI", m_pipx->RSSI);
addUAVObjectToWidgetRelation("PipXStatus", "LinkQuality", m_pipx->LinkQuality);
addUAVObjectToWidgetRelation("PipXStatus", "RXRate", m_pipx->RXRate);
addUAVObjectToWidgetRelation("PipXStatus", "TXRate", m_pipx->TXRate);
@ -97,7 +96,6 @@ ConfigPipXtremeWidget::ConfigPipXtremeWidget(QWidget *parent) : ConfigTaskWidget
// Request and update of the setting object.
settingsUpdated = false;
//pipxSettingsObj->requestUpdate();
disableMouseWheelEvents();
}
@ -182,15 +180,15 @@ void ConfigPipXtremeWidget::updateStatus(UAVObject *object)
}
UAVObjectField* pairRssiField = object->getField("PairSignalStrengths");
if (pairRssiField) {
m_pipx->PairSignalStrengthBar1->setValue(pairRssiField->getValue(0).toInt());
m_pipx->PairSignalStrengthBar2->setValue(pairRssiField->getValue(1).toInt());
m_pipx->PairSignalStrengthBar3->setValue(pairRssiField->getValue(2).toInt());
m_pipx->PairSignalStrengthBar4->setValue(pairRssiField->getValue(3).toInt());
m_pipx->PairSignalStrengthLabel1->setText(QString("%1dB").arg(pairRssiField->getValue(0).toInt()));
m_pipx->PairSignalStrengthLabel2->setText(QString("%1dB").arg(pairRssiField->getValue(1).toInt()));
m_pipx->PairSignalStrengthLabel3->setText(QString("%1dB").arg(pairRssiField->getValue(2).toInt()));
m_pipx->PairSignalStrengthLabel4->setText(QString("%1dB").arg(pairRssiField->getValue(3).toInt()));
} else {
m_pipx->PairSignalStrengthBar1->setValue(pairRssiField->getValue(0).toInt());
m_pipx->PairSignalStrengthBar2->setValue(pairRssiField->getValue(1).toInt());
m_pipx->PairSignalStrengthBar3->setValue(pairRssiField->getValue(2).toInt());
m_pipx->PairSignalStrengthBar4->setValue(pairRssiField->getValue(3).toInt());
m_pipx->PairSignalStrengthLabel1->setText(QString("%1dB").arg(pairRssiField->getValue(0).toInt()));
m_pipx->PairSignalStrengthLabel2->setText(QString("%1dB").arg(pairRssiField->getValue(1).toInt()));
m_pipx->PairSignalStrengthLabel3->setText(QString("%1dB").arg(pairRssiField->getValue(2).toInt()));
m_pipx->PairSignalStrengthLabel4->setText(QString("%1dB").arg(pairRssiField->getValue(3).toInt()));
} else {
qDebug() << "PipXtremeGadgetWidget: Count not read PairID field.";
}
@ -269,10 +267,10 @@ void ConfigPipXtremeWidget::updateSettings(UAVObject *object)
Q_UNUSED(object);
if (!settingsUpdated)
{
settingsUpdated = true;
enableControls(true);
}
{
settingsUpdated = true;
enableControls(true);
}
}
void ConfigPipXtremeWidget::disconnected()

View File

@ -434,7 +434,7 @@
</property>
</widget>
</item>
<item row="2" column="0">
<item row="1" column="0">
<widget class="QLabel" name="label_2">
<property name="text">
<string>Serial Number</string>
@ -444,7 +444,7 @@
</property>
</widget>
</item>
<item row="2" column="1" colspan="3">
<item row="1" column="1" colspan="3">
<widget class="QLineEdit" name="SerialNumber">
<property name="sizePolicy">
<sizepolicy hsizetype="Preferred" vsizetype="Fixed">
@ -498,7 +498,7 @@
</property>
</widget>
</item>
<item row="3" column="0">
<item row="2" column="0">
<widget class="QLabel" name="DeviceIDLabel">
<property name="text">
<string>Device ID</string>
@ -508,7 +508,7 @@
</property>
</widget>
</item>
<item row="3" column="1">
<item row="2" column="1">
<widget class="QLineEdit" name="DeviceID">
<property name="minimumSize">
<size>
@ -552,7 +552,7 @@
</property>
</widget>
</item>
<item row="3" column="2">
<item row="3" column="0">
<widget class="QLabel" name="PairIDLabel">
<property name="text">
<string>Pair ID</string>
@ -562,7 +562,7 @@
</property>
</widget>
</item>
<item row="3" column="3">
<item row="3" column="1">
<widget class="QLineEdit" name="PairID">
<property name="maximumSize">
<size>
@ -601,9 +601,9 @@
</widget>
</item>
<item row="4" column="0">
<widget class="QLabel" name="label_3">
<widget class="QLabel" name="label_11">
<property name="text">
<string>Min Frequency</string>
<string>Link State</string>
</property>
<property name="alignment">
<set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
@ -611,9 +611,9 @@
</widget>
</item>
<item row="4" column="1">
<widget class="QLineEdit" name="MinFrequency">
<widget class="QLineEdit" name="LinkState">
<property name="sizePolicy">
<sizepolicy hsizetype="Preferred" vsizetype="Fixed">
<sizepolicy hsizetype="Expanding" vsizetype="Fixed">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
@ -637,13 +637,13 @@
</font>
</property>
<property name="toolTip">
<string>The modems minimum allowed frequency</string>
<string>The modems current state</string>
</property>
<property name="styleSheet">
<string notr="true">QLineEdit {
border: none;
border-radius: 1px;
padding: 0 4px;
padding: 0 3px;
background: rgba(0, 0, 0, 16);
/* background: transparent; */
/* selection-background-color: darkgray;*/
@ -655,63 +655,15 @@
<property name="readOnly">
<bool>true</bool>
</property>
</widget>
</item>
<item row="4" column="2">
<widget class="QLabel" name="label_4">
<property name="text">
<string>Max Frequency</string>
</property>
<property name="alignment">
<set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
</property>
</widget>
</item>
<item row="4" column="3">
<widget class="QLineEdit" name="MaxFrequency">
<property name="sizePolicy">
<sizepolicy hsizetype="Preferred" vsizetype="Fixed">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
</property>
<property name="maximumSize">
<size>
<width>101</width>
<height>16777215</height>
</size>
</property>
<property name="font">
<font>
<weight>75</weight>
<bold>true</bold>
</font>
</property>
<property name="toolTip">
<string>The modems maximum allowed frequency</string>
</property>
<property name="styleSheet">
<string notr="true">QLineEdit {
border: none;
border-radius: 1px;
padding: 0 4px;
background: rgba(0, 0, 0, 16);
/* background: transparent; */
/* selection-background-color: darkgray;*/
}</string>
</property>
<property name="alignment">
<set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter</set>
</property>
<property name="readOnly">
<bool>true</bool>
<property name="placeholderText">
<string>Disconnected</string>
</property>
</widget>
</item>
<item row="5" column="0">
<widget class="QLabel" name="label_12">
<widget class="QLabel" name="LinkQualityLabel">
<property name="text">
<string>Freq. Step Size</string>
<string>Link Quality</string>
</property>
<property name="alignment">
<set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
@ -719,19 +671,7 @@
</widget>
</item>
<item row="5" column="1">
<widget class="QLineEdit" name="FrequencyStepSize">
<property name="sizePolicy">
<sizepolicy hsizetype="Preferred" vsizetype="Fixed">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
</property>
<property name="minimumSize">
<size>
<width>0</width>
<height>0</height>
</size>
</property>
<widget class="QLineEdit" name="LinkQuality">
<property name="maximumSize">
<size>
<width>101</width>
@ -744,9 +684,6 @@
<bold>true</bold>
</font>
</property>
<property name="toolTip">
<string>The modems minimum frequency step size</string>
</property>
<property name="styleSheet">
<string notr="true">QLineEdit {
border: none;
@ -757,59 +694,8 @@
/* selection-background-color: darkgray;*/
}</string>
</property>
<property name="alignment">
<set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter</set>
</property>
<property name="readOnly">
<bool>true</bool>
</property>
</widget>
</item>
<item row="5" column="2">
<widget class="QLabel" name="FreqBandLabel">
<property name="text">
<string>Freq. Band</string>
</property>
<property name="alignment">
<set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
</property>
</widget>
</item>
<item row="5" column="3">
<widget class="QLineEdit" name="FreqBand">
<property name="sizePolicy">
<sizepolicy hsizetype="Preferred" vsizetype="Fixed">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
</property>
<property name="maximumSize">
<size>
<width>101</width>
<height>16777215</height>
</size>
</property>
<property name="font">
<font>
<weight>75</weight>
<bold>true</bold>
</font>
</property>
<property name="toolTip">
<string>The current frequency band</string>
</property>
<property name="styleSheet">
<string notr="true">QLineEdit {
border: none;
border-radius: 1px;
padding: 0 4px;
background: rgba(0, 0, 0, 16);
/* background: transparent; */
/* selection-background-color: darkgray;*/
}</string>
</property>
<property name="alignment">
<set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter</set>
<property name="frame">
<bool>false</bool>
</property>
<property name="readOnly">
<bool>true</bool>
@ -861,7 +747,7 @@
</property>
</widget>
</item>
<item row="6" column="2">
<item row="7" column="0">
<widget class="QLabel" name="RxAFCLabel">
<property name="text">
<string>Rx AFC</string>
@ -871,7 +757,7 @@
</property>
</widget>
</item>
<item row="6" column="3">
<item row="7" column="1">
<widget class="QLineEdit" name="RxAFC">
<property name="maximumSize">
<size>
@ -900,7 +786,7 @@
</property>
</widget>
</item>
<item row="7" column="0">
<item row="8" column="0">
<widget class="QLabel" name="TXRateLabel">
<property name="text">
<string>TX Rate (B/s)</string>
@ -910,7 +796,7 @@
</property>
</widget>
</item>
<item row="7" column="1">
<item row="8" column="1">
<widget class="QLineEdit" name="TXRate">
<property name="minimumSize">
<size>
@ -948,7 +834,7 @@
</property>
</widget>
</item>
<item row="7" column="2">
<item row="9" column="0">
<widget class="QLabel" name="RXRateLabel">
<property name="text">
<string>RX Rate (B/s)</string>
@ -958,7 +844,7 @@
</property>
</widget>
</item>
<item row="7" column="3">
<item row="9" column="1">
<widget class="QLineEdit" name="RXRate">
<property name="maximumSize">
<size>
@ -990,20 +876,20 @@
</property>
</widget>
</item>
<item row="8" column="0">
<widget class="QLabel" name="label_11">
<item row="2" column="2">
<widget class="QLabel" name="GoodLabel">
<property name="text">
<string>Link State</string>
<string>RX Good</string>
</property>
<property name="alignment">
<set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
</property>
</widget>
</item>
<item row="8" column="1">
<widget class="QLineEdit" name="LinkState">
<item row="2" column="3">
<widget class="QLineEdit" name="Good">
<property name="sizePolicy">
<sizepolicy hsizetype="Expanding" vsizetype="Fixed">
<sizepolicy hsizetype="Preferred" vsizetype="Fixed">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
@ -1027,52 +913,7 @@
</font>
</property>
<property name="toolTip">
<string>The modems current state</string>
</property>
<property name="styleSheet">
<string notr="true">QLineEdit {
border: none;
border-radius: 1px;
padding: 0 3px;
background: rgba(0, 0, 0, 16);
/* background: transparent; */
/* selection-background-color: darkgray;*/
}</string>
</property>
<property name="alignment">
<set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter</set>
</property>
<property name="readOnly">
<bool>true</bool>
</property>
<property name="placeholderText">
<string>Disconnected</string>
</property>
</widget>
</item>
<item row="8" column="2">
<widget class="QLabel" name="LinkQualityLabel">
<property name="text">
<string>Link Quality</string>
</property>
<property name="alignment">
<set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
</property>
</widget>
</item>
<item row="8" column="3">
<widget class="QLineEdit" name="LinkQuality">
<property name="maximumSize">
<size>
<width>101</width>
<height>16777215</height>
</size>
</property>
<property name="font">
<font>
<weight>75</weight>
<bold>true</bold>
</font>
<string>The percentage of packets that were corrected with error correction</string>
</property>
<property name="styleSheet">
<string notr="true">QLineEdit {
@ -1084,26 +925,32 @@
/* selection-background-color: darkgray;*/
}</string>
</property>
<property name="frame">
<bool>false</bool>
<property name="alignment">
<set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter</set>
</property>
<property name="readOnly">
<bool>true</bool>
</property>
</widget>
</item>
<item row="9" column="0">
<widget class="QLabel" name="RetriesLabel">
<item row="3" column="2">
<widget class="QLabel" name="CorrectedLabel">
<property name="text">
<string>Retries</string>
<string>RX Corrected</string>
</property>
<property name="alignment">
<set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
</property>
</widget>
</item>
<item row="9" column="1">
<widget class="QLineEdit" name="Retries">
<item row="3" column="3">
<widget class="QLineEdit" name="Corrected">
<property name="sizePolicy">
<sizepolicy hsizetype="Preferred" vsizetype="Fixed">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
</property>
<property name="minimumSize">
<size>
<width>0</width>
@ -1122,6 +969,9 @@
<bold>true</bold>
</font>
</property>
<property name="toolTip">
<string>The percentage of packets that were corrected with error correction</string>
</property>
<property name="styleSheet">
<string notr="true">QLineEdit {
border: none;
@ -1132,15 +982,174 @@
/* selection-background-color: darkgray;*/
}</string>
</property>
<property name="frame">
<bool>false</bool>
<property name="alignment">
<set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter</set>
</property>
<property name="readOnly">
<bool>true</bool>
</property>
</widget>
</item>
<item row="9" column="2">
<item row="4" column="2">
<widget class="QLabel" name="ErrorsLabel">
<property name="text">
<string>RX Errors</string>
</property>
<property name="alignment">
<set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
</property>
</widget>
</item>
<item row="4" column="3">
<widget class="QLineEdit" name="Errors">
<property name="sizePolicy">
<sizepolicy hsizetype="Preferred" vsizetype="Fixed">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
</property>
<property name="maximumSize">
<size>
<width>101</width>
<height>16777215</height>
</size>
</property>
<property name="font">
<font>
<weight>75</weight>
<bold>true</bold>
</font>
</property>
<property name="toolTip">
<string>The percentage of packets that could not be corrected with error correction</string>
</property>
<property name="styleSheet">
<string notr="true">QLineEdit {
border: none;
border-radius: 1px;
padding: 0 4px;
background: rgba(0, 0, 0, 16);
/* background: transparent; */
/* selection-background-color: darkgray;*/
}</string>
</property>
<property name="alignment">
<set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter</set>
</property>
<property name="readOnly">
<bool>true</bool>
</property>
</widget>
</item>
<item row="5" column="2">
<widget class="QLabel" name="MissedPacketsLabel">
<property name="text">
<string>RX Missed</string>
</property>
<property name="alignment">
<set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
</property>
</widget>
</item>
<item row="5" column="3">
<widget class="QLineEdit" name="Missed">
<property name="sizePolicy">
<sizepolicy hsizetype="Preferred" vsizetype="Fixed">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
</property>
<property name="minimumSize">
<size>
<width>0</width>
<height>0</height>
</size>
</property>
<property name="maximumSize">
<size>
<width>101</width>
<height>16777215</height>
</size>
</property>
<property name="font">
<font>
<weight>75</weight>
<bold>true</bold>
</font>
</property>
<property name="toolTip">
<string>The percentage of packets that were not received at all</string>
</property>
<property name="styleSheet">
<string notr="true">QLineEdit {
border: none;
border-radius: 1px;
padding: 0 4px;
background: rgba(0, 0, 0, 16);
/* background: transparent; */
/* selection-background-color: darkgray;*/
}</string>
</property>
<property name="alignment">
<set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter</set>
</property>
<property name="readOnly">
<bool>true</bool>
</property>
</widget>
</item>
<item row="6" column="2">
<widget class="QLabel" name="DroppedLabel">
<property name="text">
<string>TX Dropped</string>
</property>
<property name="alignment">
<set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
</property>
</widget>
</item>
<item row="6" column="3">
<widget class="QLineEdit" name="Dropped">
<property name="sizePolicy">
<sizepolicy hsizetype="Preferred" vsizetype="Fixed">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
</property>
<property name="maximumSize">
<size>
<width>101</width>
<height>16777215</height>
</size>
</property>
<property name="font">
<font>
<weight>75</weight>
<bold>true</bold>
</font>
</property>
<property name="toolTip">
<string>The number of packets that were unable to be transmitted</string>
</property>
<property name="styleSheet">
<string notr="true">QLineEdit {
border: none;
border-radius: 1px;
padding: 0 4px;
background: rgba(0, 0, 0, 16);
/* background: transparent; */
/* selection-background-color: darkgray;*/
}</string>
</property>
<property name="alignment">
<set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter</set>
</property>
<property name="readOnly">
<bool>true</bool>
</property>
</widget>
</item>
<item row="7" column="2">
<widget class="QLabel" name="UAVTalkErrorsLabel">
<property name="text">
<string>UAVTalk Errors</string>
@ -1150,7 +1159,7 @@
</property>
</widget>
</item>
<item row="9" column="3">
<item row="7" column="3">
<widget class="QLineEdit" name="UAVTalkErrors">
<property name="maximumSize">
<size>
@ -1182,7 +1191,7 @@
</property>
</widget>
</item>
<item row="10" column="0">
<item row="8" column="2">
<widget class="QLabel" name="ResetsLabel">
<property name="text">
<string>Resets</string>
@ -1192,7 +1201,7 @@
</property>
</widget>
</item>
<item row="10" column="1">
<item row="8" column="3">
<widget class="QLineEdit" name="Resets">
<property name="minimumSize">
<size>
@ -1230,18 +1239,18 @@
</property>
</widget>
</item>
<item row="10" column="2">
<widget class="QLabel" name="DroppedLabel">
<item row="9" column="2">
<widget class="QLabel" name="TimeoutsLabel">
<property name="text">
<string>Dropped</string>
<string>Timeouts</string>
</property>
<property name="alignment">
<set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
</property>
</widget>
</item>
<item row="10" column="3">
<widget class="QLineEdit" name="Dropped">
<item row="9" column="3">
<widget class="QLineEdit" name="Timeouts">
<property name="maximumSize">
<size>
<width>101</width>
@ -1747,9 +1756,6 @@
<tabstop>FirmwareVersion</tabstop>
<tabstop>SerialNumber</tabstop>
<tabstop>DeviceID</tabstop>
<tabstop>MinFrequency</tabstop>
<tabstop>MaxFrequency</tabstop>
<tabstop>FrequencyStepSize</tabstop>
<tabstop>LinkState</tabstop>
<tabstop>RxAFC</tabstop>
<tabstop>Retries</tabstop>

View File

@ -5,19 +5,19 @@
<field name="CPUSerial" units="" type="uint8" elements="12" />
<field name="BoardRevision" units="" type="uint16" elements="1"/>
<field name="BoardType" units="" type="uint8" elements="1"/>
<field name="MinFrequency" units="Hz" type="uint32" elements="1" defaultvalue="0"/>
<field name="MaxFrequency" units="Hz" type="uint32" elements="1" defaultvalue="0"/>
<field name="FrequencyBand" units="" type="uint8" elements="1" defaultvalue="0"/>
<field name="FrequencyStepSize" units="" type="float" elements="1" defaultvalue="0"/>
<field name="DeviceID" units="" type="uint32" elements="1" defaultvalue="0"/>
<field name="Retries" units="" type="uint16" elements="1" defaultvalue="0"/>
<field name="RxGood" units="%" type="uint8" elements="1" defaultvalue="0"/>
<field name="RxCorrected" units="%" type="uint8" elements="1" defaultvalue="0"/>
<field name="RxErrors" units="%" type="uint8" elements="1" defaultvalue="0"/>
<field name="RxMissed" units="%" type="uint8" elements="1" defaultvalue="0"/>
<field name="UAVTalkErrors" units="" type="uint16" elements="1" defaultvalue="0"/>
<field name="Dropped" units="" type="uint16" elements="1" defaultvalue="0"/>
<field name="Resets" units="" type="uint16" elements="1" defaultvalue="0"/>
<field name="TXRate" units="Bps" type="uint16" elements="1" defaultvalue="0"/>
<field name="RXRate" units="Bps" type="uint16" elements="1" defaultvalue="0"/>
<field name="TxDropped" units="%" type="uint8" elements="1" defaultvalue="0"/>
<field name="Resets" units="" type="uint8" elements="1" defaultvalue="0"/>
<field name="Timeouts" units="" type="uint8" elements="1" defaultvalue="0"/>
<field name="RSSI" units="dBm" type="int8" elements="1" defaultvalue="0"/>
<field name="LinkQuality" units="" type="uint8" elements="1" defaultvalue="0"/>
<field name="TXRate" units="Bps" type="uint16" elements="1" defaultvalue="0"/>
<field name="RXRate" units="Bps" type="uint16" elements="1" defaultvalue="0"/>
<field name="LinkState" units="function" type="enum" elements="1" options="Disconnected,Connecting,Connected" defaultvalue="Disconnected"/>
<field name="PairIDs" units="" type="uint32" elements="4" defaultvalue="0"/>
<field name="PairSignalStrengths" units="dBm" type="int8" elements="4" defaultvalue="-127"/>