Merge pull request #7664 from zhuoshuguo/lwmac_radio_reinit

LWMAC: add re-initialize radio support.
This commit is contained in:
Martine Lenders 2020-08-26 18:58:56 +02:00 committed by GitHub
commit 4ba5367755
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
5 changed files with 67 additions and 0 deletions

View File

@ -316,6 +316,19 @@ extern "C" {
#endif
/** @} */
/**
* @brief Maximum preamble attempts before re-initialize radio in LWMAC.
*
* After a long period of run time, a radio may be in wrong condition which needs to be
* re-calibrated. This is indicated by having a series of continuous preamble failure (no WA)
* in LWMAC. In case we have @ref CONFIG_GNRC_LWMAC_RADIO_REINIT_THRESHOLD number of preamble
* failure, then we re-initialize the radio, trying to re-calibrate the radio for bringing it
* back to normal condition.
*/
#ifndef CONFIG_GNRC_LWMAC_RADIO_REINIT_THRESHOLD
#define CONFIG_GNRC_LWMAC_RADIO_REINIT_THRESHOLD (10U)
#endif
/**
* @brief Creates an IEEE 802.15.4 LWMAC network interface
*

View File

@ -195,6 +195,7 @@ typedef struct {
uint8_t bcast_seqnr; /**< Sequence number for broadcast data to filter at receiver */
uint8_t tx_burst_count; /**< Count how many consecutive packets have been transmitted */
uint8_t tx_retry_count; /**< Count how many Tx-retrials have been executed before packet drop */
uint8_t preamble_fail_counts; /**< Preamble trial failure count. */
#endif
#ifdef MODULE_GNRC_GOMACH

View File

@ -138,5 +138,16 @@ config GNRC_LWMAC_TIMEOUT_COUNT
help
Configure 'CONFIG_GNRC_LWMAC_TIMEOUT_COUNT', the default value for the
maximum number of parallel timeouts in LWMAC.
config GNRC_LWMAC_RADIO_REINIT_THRESHOLD
int "Maximum preamble attempts before re-initialize radio"
default 10
help
Configure 'CONFIG_GNRC_LWMAC_RADIO_REINIT_THRESHOLD', the maximum preamble
attempts before re-initialize radio. After a long period of run time, a radio
may be in wrong condition which needs to be re-calibrated. This is indicated
by having a series of continuous preamble failure (no WA) in LWMAC. In case
we have @ref GNRC_LWMAC_RADIO_REINI_THRESHOLD number of preamble failure,
then we re-initialize the radio, trying to re-calibrate the radio for bringing
it back to normal condition.
endif # KCONFIG_MODULE_GNRC_LWMAC

View File

@ -83,6 +83,38 @@ int gnrc_netif_lwmac_create(gnrc_netif_t *netif, char *stack, int stacksize,
&lwmac_ops);
}
static void lwmac_reinit_radio(gnrc_netif_t *netif)
{
/* Initialize low-level driver. */
netif->dev->driver->init(netif->dev);
/* Set MAC address length. */
uint16_t src_len = netif->l2addr_len;
netif->dev->driver->set(netif->dev, NETOPT_SRC_LEN, &src_len, sizeof(src_len));
/* Set the MAC address of the device. */
if (netif->l2addr_len == IEEE802154_LONG_ADDRESS_LEN) {
netif->dev->driver->set(netif->dev,
NETOPT_ADDRESS_LONG,
netif->l2addr,
sizeof(netif->l2addr));
}
else {
netif->dev->driver->set(netif->dev,
NETOPT_ADDR_LEN,
netif->l2addr,
sizeof(netif->l2addr));
}
/* Enable RX-start and TX-started and TX-END interrupts. */
netopt_enable_t enable = NETOPT_ENABLE;
netif->dev->driver->set(netif->dev, NETOPT_RX_START_IRQ, &enable, sizeof(enable));
netif->dev->driver->set(netif->dev, NETOPT_RX_END_IRQ, &enable, sizeof(enable));
netif->dev->driver->set(netif->dev, NETOPT_TX_START_IRQ, &enable, sizeof(enable));
netif->dev->driver->set(netif->dev, NETOPT_TX_END_IRQ, &enable, sizeof(enable));
}
static gnrc_pktsnip_t *_make_netif_hdr(uint8_t *mhr)
{
gnrc_pktsnip_t *snip;
@ -328,6 +360,7 @@ void lwmac_set_state(gnrc_netif_t *netif, gnrc_lwmac_state_t newstate)
case GNRC_LWMAC_START: {
rtt_handler(GNRC_LWMAC_EVENT_RTT_START, netif);
lwmac_set_state(netif, GNRC_LWMAC_LISTENING);
netif->mac.tx.preamble_fail_counts = 0;
break;
}
case GNRC_LWMAC_STOP: {
@ -576,6 +609,13 @@ static void _tx_management(gnrc_netif_t *netif)
gnrc_lwmac_set_tx_continue(netif, false);
gnrc_lwmac_set_quit_tx(netif, true);
/* TX packet will be dropped, no automatic resending here. */
/* Re-initialize the radio when needed. */
if (netif->mac.tx.preamble_fail_counts >= CONFIG_GNRC_LWMAC_RADIO_REINIT_THRESHOLD) {
netif->mac.tx.preamble_fail_counts = 0;
LOG_INFO("[LWMAC] Re-initialize radio.");
lwmac_reinit_radio(netif);
}
/* Intentionally falls through */
case GNRC_LWMAC_TX_STATE_SUCCESSFUL:

View File

@ -685,6 +685,7 @@ static bool _lwmac_tx_update(gnrc_netif_t *netif)
LOG_WARNING("WARNING: [LWMAC-tx] No response from destination\n");
netif->mac.tx.state = GNRC_LWMAC_TX_STATE_FAILED;
reschedule = true;
netif->mac.tx.preamble_fail_counts++;
break;
}
@ -735,6 +736,7 @@ static bool _lwmac_tx_update(gnrc_netif_t *netif)
if (tx_info & GNRC_LWMAC_TX_SUCCESS) {
netif->mac.tx.state = GNRC_LWMAC_TX_STATE_SEND_DATA;
reschedule = true;
netif->mac.tx.preamble_fail_counts = 0;
break;
}
else {