mirror of
https://github.com/RIOT-OS/RIOT.git
synced 2024-12-29 04:50:03 +01:00
Merge pull request #14010 from benpicco/at86rf215-mr-ofdm
drivers/at86rf215: implement MR-OFDM
This commit is contained in:
commit
3a1ee4983c
@ -74,6 +74,7 @@ ifneq (,$(filter at86rf215%,$(USEMODULE)))
|
||||
|
||||
DEFAULT_MODULE += netdev_ieee802154_oqpsk
|
||||
DEFAULT_MODULE += netdev_ieee802154_mr_oqpsk
|
||||
DEFAULT_MODULE += netdev_ieee802154_mr_ofdm
|
||||
|
||||
ifeq (,$(filter at86rf215m,$(USEMODULE)))
|
||||
DEFAULT_MODULE += at86rf215_24ghz
|
||||
|
@ -151,6 +151,10 @@ if (!IS_ACTIVE(CONFIG_AT86RF215_USE_CLOCK_OUTPUT)){
|
||||
at86rf215_configure_OQPSK(dev, AT86RF215_DEFAULT_MR_OQPSK_CHIPS,
|
||||
AT86RF215_DEFAULT_MR_OQPSK_RATE);
|
||||
}
|
||||
if (AT86RF215_DEFAULT_PHY_MODE == IEEE802154_PHY_MR_OFDM) {
|
||||
at86rf215_configure_OFDM(dev, CONFIG_AT86RF215_DEFAULT_MR_OFDM_OPT,
|
||||
CONFIG_AT86RF215_DEFAULT_MR_OFDM_MCS);
|
||||
}
|
||||
|
||||
/* set default channel */
|
||||
at86rf215_set_chan(dev, dev->netdev.chan);
|
||||
|
@ -394,6 +394,18 @@ static int _get(netdev_t *netdev, netopt_t opt, void *val, size_t max_len)
|
||||
res = max_len;
|
||||
break;
|
||||
|
||||
case NETOPT_MR_OFDM_OPTION:
|
||||
assert(max_len >= sizeof(int8_t));
|
||||
*((int8_t *)val) = at86rf215_OFDM_get_option(dev);
|
||||
res = max_len;
|
||||
break;
|
||||
|
||||
case NETOPT_MR_OFDM_MCS:
|
||||
assert(max_len >= sizeof(int8_t));
|
||||
*((int8_t *)val) = at86rf215_OFDM_get_scheme(dev);
|
||||
res = max_len;
|
||||
break;
|
||||
|
||||
case NETOPT_MR_OQPSK_CHIPS:
|
||||
assert(max_len >= sizeof(int16_t));
|
||||
switch (at86rf215_OQPSK_get_chips(dev)) {
|
||||
@ -574,11 +586,43 @@ static int _set(netdev_t *netdev, netopt_t opt, const void *val, size_t len)
|
||||
at86rf215_OQPSK_get_mode(dev));
|
||||
res = sizeof(uint8_t);
|
||||
break;
|
||||
case IEEE802154_PHY_MR_OFDM:
|
||||
at86rf215_configure_OFDM(dev,
|
||||
at86rf215_OFDM_get_option(dev),
|
||||
at86rf215_OFDM_get_scheme(dev));
|
||||
res = sizeof(uint8_t);
|
||||
break;
|
||||
default:
|
||||
return -ENOTSUP;
|
||||
}
|
||||
break;
|
||||
|
||||
case NETOPT_MR_OFDM_OPTION:
|
||||
if (at86rf215_get_phy_mode(dev) != IEEE802154_PHY_MR_OFDM) {
|
||||
return -ENOTSUP;
|
||||
}
|
||||
|
||||
assert(len <= sizeof(uint8_t));
|
||||
if (at86rf215_OFDM_set_option(dev, *((const uint8_t *)val)) == 0) {
|
||||
res = sizeof(uint8_t);
|
||||
} else {
|
||||
res = -ERANGE;
|
||||
}
|
||||
break;
|
||||
|
||||
case NETOPT_MR_OFDM_MCS:
|
||||
if (at86rf215_get_phy_mode(dev) != IEEE802154_PHY_MR_OFDM) {
|
||||
return -ENOTSUP;
|
||||
}
|
||||
|
||||
assert(len <= sizeof(uint8_t));
|
||||
if (at86rf215_OFDM_set_scheme(dev, *((const uint8_t *)val)) == 0) {
|
||||
res = sizeof(uint8_t);
|
||||
} else {
|
||||
res = -ERANGE;
|
||||
}
|
||||
break;
|
||||
|
||||
case NETOPT_MR_OQPSK_CHIPS:
|
||||
if (at86rf215_get_phy_mode(dev) != IEEE802154_PHY_MR_OQPSK) {
|
||||
return -ENOTSUP;
|
||||
|
325
drivers/at86rf215/at86rf215_ofdm.c
Normal file
325
drivers/at86rf215/at86rf215_ofdm.c
Normal file
@ -0,0 +1,325 @@
|
||||
/*
|
||||
* Copyright (C) 2019 ML!PA Consulting GmbH
|
||||
*
|
||||
* This file is subject to the terms and conditions of the GNU Lesser
|
||||
* General Public License v2.1. See the file LICENSE in the top level
|
||||
* directory for more details.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @ingroup drivers_at86rf215
|
||||
* @{
|
||||
*
|
||||
* @file
|
||||
* @brief Configuration of the MR-OFDM PHY on the AT86RF215 chip
|
||||
*
|
||||
* @author Benjamin Valentin <benjamin.valentin@ml-pa.com>
|
||||
* @}
|
||||
*/
|
||||
|
||||
#include "at86rf215.h"
|
||||
#include "at86rf215_internal.h"
|
||||
|
||||
#define ENABLE_DEBUG (0)
|
||||
#include "debug.h"
|
||||
|
||||
/* symbol time is always 120 µs for MR-OFDM */
|
||||
#define OFDM_SYMBOL_TIME_US 120
|
||||
|
||||
/* IEEE Std 802.15.4g™-2012 Amendment 3
|
||||
* Table 68d—Total number of channels and first channel center frequencies for SUN PHYs */
|
||||
static uint32_t _channel_spacing_kHz(uint8_t option)
|
||||
{
|
||||
switch (option) {
|
||||
case 1: return 1200;
|
||||
case 2: return 800;
|
||||
case 3: return 400;
|
||||
case 4: return 200;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* IEEE Std 802.15.4g™-2012 Amendment 3
|
||||
* Table 68d—Total number of channels and first channel center frequencies for SUN PHYs */
|
||||
static uint32_t _channel_center_freq_kHz_868MHz(uint8_t option)
|
||||
{
|
||||
switch (option) {
|
||||
case 1: return 863625;
|
||||
case 2: return 863425;
|
||||
case 3: return 863225;
|
||||
case 4: return 863125;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* IEEE Std 802.15.4g™-2012 Amendment 3
|
||||
* Table 68d—Total number of channels and first channel center frequencies for SUN PHYs */
|
||||
static uint32_t _channel_center_freq_kHz_2400MHz(uint8_t option)
|
||||
{
|
||||
return 2400000 + _channel_spacing_kHz(option) - CCF0_24G_OFFSET;
|
||||
}
|
||||
|
||||
/* IEEE Std 802.15.4g™-2012 Amendment 3
|
||||
* Table 68d—Total number of channels and first channel center frequencies for SUN PHYs */
|
||||
static uint16_t _get_max_chan(at86rf215_t *dev, uint8_t option)
|
||||
{
|
||||
if (is_subGHz(dev)) {
|
||||
switch (option) {
|
||||
case 1: return 5;
|
||||
case 2: return 8;
|
||||
case 3: return 17;
|
||||
case 4: return 34;
|
||||
}
|
||||
}
|
||||
else {
|
||||
switch (option) {
|
||||
case 1: return 64;
|
||||
case 2: return 97;
|
||||
case 3: return 207;
|
||||
case 4: return 416;
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Table 6-90. Recommended Transmitter Frontend Configuration */
|
||||
static uint32_t _TXCUTC_LPFCUT(uint8_t option)
|
||||
{
|
||||
switch (option) {
|
||||
case 1: return 10 << TXCUTC_LPFCUT_SHIFT;
|
||||
case 2: return 8 << TXCUTC_LPFCUT_SHIFT;
|
||||
case 3: return 5 << TXCUTC_LPFCUT_SHIFT;
|
||||
case 4: return 3 << TXCUTC_LPFCUT_SHIFT;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Table 6-90. Recommended Transmitter Frontend Configuration */
|
||||
static uint32_t _TXDFE_SR(uint8_t option)
|
||||
{
|
||||
switch (option) {
|
||||
case 1:
|
||||
case 2: return 3 << TXDFE_SR_SHIFT;
|
||||
case 3:
|
||||
case 4: return 6 << TXDFE_SR_SHIFT;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Table 6-90. Recommended Transmitter Frontend Configuration */
|
||||
static uint32_t _TXDFE_RCUT(uint8_t option)
|
||||
{
|
||||
switch (option) {
|
||||
case 1: return 3 << TXDFE_RCUT_SHIFT;
|
||||
case 2:
|
||||
case 3: return 3 << TXDFE_RCUT_SHIFT;
|
||||
case 4: return 2 << TXDFE_RCUT_SHIFT;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Table 6-93. Recommended PHY Receiver and Digital Frontend Configuration */
|
||||
static uint32_t _RXDFE_RCUT(uint8_t option, bool superGHz)
|
||||
{
|
||||
switch (option) {
|
||||
case 1: return 4 << RXDFE_RCUT_SHIFT;
|
||||
case 2: return 2 << RXDFE_RCUT_SHIFT;
|
||||
case 3: return (2 + superGHz) << RXDFE_RCUT_SHIFT;
|
||||
case 4: return 1 << RXDFE_RCUT_SHIFT;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Table 6-93. Recommended PHY Receiver and Digital Frontend Configuration */
|
||||
static uint32_t _RXBWC_BW(uint8_t option, bool superGHz)
|
||||
{
|
||||
switch (option) {
|
||||
case 1: return (9 + superGHz) << RXBWC_BW_SHIFT;
|
||||
case 2: return 7 << RXBWC_BW_SHIFT;
|
||||
case 3: return (4 + superGHz) << RXBWC_BW_SHIFT;
|
||||
case 4: return (2 + superGHz) << RXBWC_BW_SHIFT;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Table 6-93. Recommended PHY Receiver and Digital Frontend Configuration */
|
||||
static uint32_t _RXBWC_IFS(uint8_t option, bool superGHz)
|
||||
{
|
||||
switch (option) {
|
||||
case 1:
|
||||
case 2: return 1;
|
||||
case 3: return superGHz;
|
||||
case 4: return !superGHz;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void _set_option(at86rf215_t *dev, uint8_t option)
|
||||
{
|
||||
const bool superGHz = !is_subGHz(dev);
|
||||
|
||||
/* Set Receiver Bandwidth */
|
||||
at86rf215_reg_write(dev, dev->RF->RG_RXBWC,
|
||||
_RXBWC_BW(option, superGHz) | _RXBWC_IFS(option, superGHz));
|
||||
/* Set fS (same as TX); fCUT for RX */
|
||||
at86rf215_reg_write(dev, dev->RF->RG_RXDFE,
|
||||
_TXDFE_SR(option) | _RXDFE_RCUT(option, superGHz));
|
||||
/* Set Power Amplifier Ramp Time; fLPCUT */
|
||||
at86rf215_reg_write(dev, dev->RF->RG_TXCUTC,
|
||||
RF_PARAMP8U | _TXCUTC_LPFCUT(option));
|
||||
/* Set fS; fCUT for TX */
|
||||
at86rf215_reg_write(dev, dev->RF->RG_TXDFE,
|
||||
_TXDFE_SR(option) | _TXDFE_RCUT(option));
|
||||
|
||||
/* set channel spacing with 25 kHz resolution */
|
||||
at86rf215_reg_write(dev, dev->RF->RG_CS, _channel_spacing_kHz(option) / 25);
|
||||
|
||||
/* set channel center frequency with 25 kHz resolution */
|
||||
if (superGHz) {
|
||||
at86rf215_reg_write16(dev, dev->RF->RG_CCF0L,
|
||||
1 + _channel_center_freq_kHz_2400MHz(option) / 25);
|
||||
}
|
||||
else {
|
||||
at86rf215_reg_write16(dev, dev->RF->RG_CCF0L,
|
||||
1 + _channel_center_freq_kHz_868MHz(option) / 25);
|
||||
}
|
||||
|
||||
at86rf215_reg_write(dev, dev->BBC->RG_OFDMC, option - 1);
|
||||
|
||||
/* make sure channel config is still valid */
|
||||
dev->num_chans = _get_max_chan(dev, option);
|
||||
dev->netdev.chan = at86rf215_chan_valid(dev, dev->netdev.chan);
|
||||
at86rf215_reg_write16(dev, dev->RF->RG_CNL, dev->netdev.chan);
|
||||
}
|
||||
|
||||
static unsigned _get_frame_duration(uint8_t option, uint8_t scheme,
|
||||
uint8_t bytes)
|
||||
{
|
||||
/* Table 150 - phySymbolsPerOctet values for MR-OFDM PHY, IEEE 802.15.4g-2012 */
|
||||
static const uint8_t quot[] = { 3, 3, 6, 12, 18, 24, 36 };
|
||||
|
||||
--option;
|
||||
/* phyMaxFrameDuration = phySHRDuration + phyPHRDuration + ceiling [(aMaxPHYPacketSize + 1) x phySymbolsPerOctet] */
|
||||
const unsigned phySHRDuration = 6;
|
||||
const unsigned phyPHRDuration = option ? 6 : 3;
|
||||
const unsigned phyPDUDuration = ((bytes + 1) * (1 << option) + quot[scheme] - 1)
|
||||
/ quot[scheme];
|
||||
|
||||
return (phySHRDuration + phyPHRDuration + phyPDUDuration) * OFDM_SYMBOL_TIME_US;
|
||||
}
|
||||
|
||||
static void _set_ack_timeout(at86rf215_t *dev, uint8_t option, uint8_t scheme)
|
||||
{
|
||||
dev->ack_timeout_usec = dev->csma_backoff_period
|
||||
+ IEEE802154G_ATURNAROUNDTIME_US
|
||||
+ _get_frame_duration(option, scheme,
|
||||
AT86RF215_ACK_PSDU_BYTES);
|
||||
DEBUG("[%s] ACK timeout: %" PRIu32 " µs\n", "OFDM", dev->ack_timeout_usec);
|
||||
}
|
||||
|
||||
static bool _option_mcs_valid(uint8_t option, uint8_t mcs)
|
||||
{
|
||||
if (option < 1 || option > 4) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (mcs > BB_MCS_16QAM_3BY4) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (mcs == BB_MCS_BPSK_REP4 && option > 2) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (mcs == BB_MCS_BPSK_REP2 && option == 4) {
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
int at86rf215_configure_OFDM(at86rf215_t *dev, uint8_t option, uint8_t scheme)
|
||||
{
|
||||
if (!_option_mcs_valid(option, scheme)) {
|
||||
DEBUG("[%s] invalid option/MCS: %d | %d\n", __func__, option, scheme);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
at86rf215_await_state_end(dev, RF_STATE_TX);
|
||||
|
||||
/* disable radio */
|
||||
at86rf215_reg_write(dev, dev->BBC->RG_PC, 0);
|
||||
|
||||
/* set receiver gain target according to data sheet */
|
||||
at86rf215_reg_write(dev, dev->RF->RG_AGCS, 3 << AGCS_TGT_SHIFT);
|
||||
/* enable automatic receiver gain */
|
||||
at86rf215_reg_write(dev, dev->RF->RG_AGCC, AGCC_EN_MASK);
|
||||
|
||||
_set_option(dev, option);
|
||||
|
||||
at86rf215_reg_write(dev, dev->BBC->RG_OFDMPHRTX, scheme);
|
||||
|
||||
dev->csma_backoff_period = AT86RF215_BACKOFF_PERIOD_IN_SYMBOLS *
|
||||
OFDM_SYMBOL_TIME_US;
|
||||
DEBUG("[%s] CSMA BACKOFF: %" PRIu32 " µs\n", "OFDM",
|
||||
dev->csma_backoff_period);
|
||||
|
||||
_set_ack_timeout(dev, option, scheme);
|
||||
|
||||
at86rf215_enable_radio(dev, BB_MROFDM);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int at86rf215_OFDM_set_scheme(at86rf215_t *dev, uint8_t scheme)
|
||||
{
|
||||
uint8_t option = at86rf215_OFDM_get_option(dev);
|
||||
|
||||
if (!_option_mcs_valid(option, scheme)) {
|
||||
DEBUG("[%s] invalid MCS: %d\n", __func__, scheme);
|
||||
return -1;
|
||||
}
|
||||
|
||||
at86rf215_await_state_end(dev, RF_STATE_TX);
|
||||
|
||||
at86rf215_reg_write(dev, dev->BBC->RG_OFDMPHRTX, scheme);
|
||||
_set_ack_timeout(dev, at86rf215_OFDM_get_option(dev), scheme);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
uint8_t at86rf215_OFDM_get_scheme(at86rf215_t *dev)
|
||||
{
|
||||
return at86rf215_reg_read(dev, dev->BBC->RG_OFDMPHRTX) & OFDMPHRTX_MCS_MASK;
|
||||
}
|
||||
|
||||
int at86rf215_OFDM_set_option(at86rf215_t *dev, uint8_t option)
|
||||
{
|
||||
uint8_t mcs = at86rf215_OFDM_get_scheme(dev);
|
||||
|
||||
if (!_option_mcs_valid(option, mcs)) {
|
||||
DEBUG("[%s] invalid option: %d\n", __func__, option);
|
||||
return -1;
|
||||
}
|
||||
|
||||
at86rf215_await_state_end(dev, RF_STATE_TX);
|
||||
|
||||
_set_option(dev, option);
|
||||
_set_ack_timeout(dev, option, mcs);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
uint8_t at86rf215_OFDM_get_option(at86rf215_t *dev)
|
||||
{
|
||||
return 1 + (at86rf215_reg_read(dev, dev->BBC->RG_OFDMC) & OFDMC_OPT_MASK);
|
||||
}
|
@ -137,6 +137,64 @@ void at86rf215_filter_ack(at86rf215_t *dev, bool on);
|
||||
*/
|
||||
void at86rf215_get_random(at86rf215_t *dev, void *data, size_t len);
|
||||
|
||||
/**
|
||||
* @brief Configure the radio to make use of OFDM modulation.
|
||||
* There are 4 OFDM options, each with a different number of active tones.
|
||||
* The device supports BPSK, QPSK and 16-QAM modulation and coding schemes (MCS)
|
||||
*
|
||||
* @param[in] dev device to configure
|
||||
* @param[in] option modulation option, each increment halves the data rate
|
||||
* @param[in] mcs modulation scheme, `BB_MCS_BPSK_REP4` … `BB_MCS_16QAM_3BY4`
|
||||
*
|
||||
* @return 0 on success, error otherwise
|
||||
*/
|
||||
int at86rf215_configure_OFDM(at86rf215_t *dev, uint8_t option, uint8_t mcs);
|
||||
|
||||
/**
|
||||
* @brief Set the current modulation and coding scheme (MCS)
|
||||
*
|
||||
* @param[in] dev device to configure
|
||||
* @param[in] mcs modulation and coding scheme
|
||||
*
|
||||
* @return 0 on success, error otherwise
|
||||
*/
|
||||
int at86rf215_OFDM_set_scheme(at86rf215_t *dev, uint8_t mcs);
|
||||
|
||||
/**
|
||||
* @brief Get the current modulation and coding scheme (MCS)
|
||||
*
|
||||
* @param[in] dev device to read from
|
||||
*
|
||||
* @return the current modulation & coding scheme
|
||||
*/
|
||||
uint8_t at86rf215_OFDM_get_scheme(at86rf215_t *dev);
|
||||
|
||||
/**
|
||||
* @brief Set the current OFDM option
|
||||
*
|
||||
* @param[in] dev device to configure
|
||||
* @param[in] option OFDM option
|
||||
*
|
||||
* @return 0 on success, error otherwise
|
||||
*/
|
||||
int at86rf215_OFDM_set_option(at86rf215_t *dev, uint8_t option);
|
||||
|
||||
/**
|
||||
* @brief Get the current OFDM option
|
||||
*
|
||||
* @param[in] dev device to read from
|
||||
*
|
||||
* @return the current OFDM option
|
||||
*/
|
||||
uint8_t at86rf215_OFDM_get_option(at86rf215_t *dev);
|
||||
|
||||
/** @} */
|
||||
|
||||
/**
|
||||
* @defgroup drivers_at86rf215_oqpsk AT86RF215 MR-O-QPSK PHY
|
||||
* @{
|
||||
*/
|
||||
|
||||
/**
|
||||
* @brief Configure the radio to make use of O-QPSK modulation.
|
||||
* The rate mode may be
|
||||
@ -455,15 +513,6 @@ void at86rf215_disable_rpc(at86rf215_t *dev);
|
||||
*/
|
||||
void at86rf215_enable_rpc(at86rf215_t *dev);
|
||||
|
||||
/**
|
||||
* @brief Notify the driver and stack about a change in transmission mode
|
||||
* which may result in a change of PDU.
|
||||
*
|
||||
* @param[in] dev device that changed it's mode
|
||||
* @param[in] new_mode the new transmission mode
|
||||
*/
|
||||
bool at86rf215_switch_mode(at86rf215_t *dev, uint8_t new_mode);
|
||||
|
||||
/**
|
||||
* @brief Checks whether the device operates in the sub-GHz band.
|
||||
*
|
||||
|
@ -137,6 +137,24 @@ enum {
|
||||
#endif
|
||||
/** @} */
|
||||
|
||||
/**
|
||||
* @name Default MR-OFDM Option
|
||||
* @{
|
||||
*/
|
||||
#ifndef CONFIG_AT86RF215_DEFAULT_MR_OFDM_OPT
|
||||
#define CONFIG_AT86RF215_DEFAULT_MR_OFDM_OPT (2)
|
||||
#endif
|
||||
/** @} */
|
||||
|
||||
/**
|
||||
* @name Default MR-OFDM Modulation & Coding Scheme
|
||||
* @{
|
||||
*/
|
||||
#ifndef CONFIG_AT86RF215_DEFAULT_MR_OFDM_MCS
|
||||
#define CONFIG_AT86RF215_DEFAULT_MR_OFDM_MCS (2)
|
||||
#endif
|
||||
/** @} */
|
||||
|
||||
/**
|
||||
* @brief Default TX power (0dBm)
|
||||
*/
|
||||
|
@ -673,6 +673,16 @@ typedef enum {
|
||||
*/
|
||||
NETOPT_MR_OQPSK_RATE,
|
||||
|
||||
/**
|
||||
* @brief (uint8_t) MR-OFDM PHY Option (Values: 1-4)
|
||||
*/
|
||||
NETOPT_MR_OFDM_OPTION,
|
||||
|
||||
/**
|
||||
* @brief (uint8_t) MR-OFDM PHY Modulation and Coding Scheme (Values: 0-6)
|
||||
*/
|
||||
NETOPT_MR_OFDM_MCS,
|
||||
|
||||
/**
|
||||
* @brief (uint8_t) PHY Channel Spacing (kHz)
|
||||
*/
|
||||
|
@ -110,6 +110,8 @@ static const char *_netopt_strmap[] = {
|
||||
[NETOPT_OQPSK_RATE] = "NETOPT_O-QPSK_RATE",
|
||||
[NETOPT_MR_OQPSK_CHIPS] = "NETOPT_MR-O-QPSK_CHIPS",
|
||||
[NETOPT_MR_OQPSK_RATE] = "NETOPT_MR-O-QPSK_RATE",
|
||||
[NETOPT_MR_OFDM_OPTION] = "NETOPT_MR-OFDM_OPTION",
|
||||
[NETOPT_MR_OFDM_MCS] = "NETOPT_MR-OFDM_MCS",
|
||||
[NETOPT_CHANNEL_SPACING] = "NETOPT_CHANNEL_SPACING",
|
||||
[NETOPT_SYNCWORD] = "NETOPT_SYNCWORD",
|
||||
[NETOPT_RANDOM] = "NETOPT_RANDOM",
|
||||
|
@ -190,6 +190,10 @@ static void _set_usage(char *cmd_name)
|
||||
#ifdef MODULE_NETDEV_IEEE802154_MR_OQPSK
|
||||
" * \"chip_rate\" - BPSK/QPSK chip rate in kChip/s\n"
|
||||
" * \"rate_mode\" - BPSK/QPSK rate mode\n"
|
||||
#endif
|
||||
#ifdef MODULE_NETDEV_IEEE802154_MR_OFDM
|
||||
" * \"option\" - OFDM option\n"
|
||||
" * \"scheme\" - OFDM modulation & coding scheme\n"
|
||||
#endif
|
||||
" * \"power\" - TX power in dBm\n"
|
||||
" * \"retrans\" - max. number of retransmissions\n"
|
||||
@ -346,6 +350,17 @@ static void _print_netopt(netopt_t opt)
|
||||
break;
|
||||
|
||||
#endif /* MODULE_NETDEV_IEEE802154_MR_OQPSK */
|
||||
#ifdef MODULE_NETDEV_IEEE802154_MR_OFDM
|
||||
|
||||
case NETOPT_MR_OFDM_OPTION:
|
||||
printf("OFDM option");
|
||||
break;
|
||||
|
||||
case NETOPT_MR_OFDM_MCS:
|
||||
printf("modulation/coding scheme");
|
||||
break;
|
||||
|
||||
#endif /* MODULE_NETDEV_IEEE802154_MR_OFDM */
|
||||
|
||||
case NETOPT_CHECKSUM:
|
||||
printf("checksum");
|
||||
@ -414,6 +429,18 @@ static const char *_netopt_ieee802154_phy_str[] = {
|
||||
};
|
||||
#endif
|
||||
|
||||
#ifdef MODULE_NETDEV_IEEE802154_MR_OFDM
|
||||
static const char *_netopt_ofdm_mcs_str[] = {
|
||||
[0] = "BPSK, rate 1/2, 4x frequency repetition",
|
||||
[1] = "BPSK, rate 1/2, 2x frequency repetition",
|
||||
[2] = "QPSK, rate 1/2, 2x frequency repetition",
|
||||
[3] = "QPSK, rate 1/2",
|
||||
[4] = "QPSK, rate 3/4",
|
||||
[5] = "16-QAM, rate 1/2",
|
||||
[6] = "16-QAM, rate 3/4",
|
||||
};
|
||||
#endif
|
||||
|
||||
/* for some lines threshold might just be 0, so we can't use _LINE_THRESHOLD
|
||||
* here */
|
||||
static unsigned _newline(unsigned threshold, unsigned line_thresh)
|
||||
@ -580,6 +607,20 @@ static void _netif_list(netif_t *iface)
|
||||
break;
|
||||
|
||||
#endif /* MODULE_NETDEV_IEEE802154_MR_OQPSK */
|
||||
#ifdef MODULE_NETDEV_IEEE802154_MR_OFDM
|
||||
case IEEE802154_PHY_MR_OFDM:
|
||||
printf("\n ");
|
||||
res = netif_get_opt(iface, NETOPT_MR_OFDM_OPTION, 0, &u8, sizeof(u8));
|
||||
if (res >= 0) {
|
||||
printf(" Option: %u ", u8);
|
||||
}
|
||||
res = netif_get_opt(iface, NETOPT_MR_OFDM_MCS, 0, &u8, sizeof(u8));
|
||||
if (res >= 0) {
|
||||
printf(" MCS: %u (%s) ", u8, _netopt_ofdm_mcs_str[u8]);
|
||||
}
|
||||
|
||||
break;
|
||||
#endif /* MODULE_NETDEV_IEEE802154_MR_OFDM */
|
||||
}
|
||||
}
|
||||
#endif /* MODULE_NETDEV_IEEE802154 */
|
||||
@ -1300,6 +1341,14 @@ static int _netif_set(char *cmd_name, netif_t *iface, char *key, char *value)
|
||||
return _netif_set_u8(iface, NETOPT_MR_OQPSK_RATE, 0, value);
|
||||
}
|
||||
#endif /* MODULE_NETDEV_IEEE802154_MR_OQPSK */
|
||||
#ifdef MODULE_NETDEV_IEEE802154_MR_OFDM
|
||||
else if ((strcmp("option", key) == 0) || (strcmp("opt", key) == 0)) {
|
||||
return _netif_set_u8(iface, NETOPT_MR_OFDM_OPTION, 0, value);
|
||||
}
|
||||
else if ((strcmp("scheme", key) == 0) || (strcmp("mcs", key) == 0)) {
|
||||
return _netif_set_u8(iface, NETOPT_MR_OFDM_MCS, 0, value);
|
||||
}
|
||||
#endif /* MODULE_NETDEV_IEEE802154_MR_OFDM */
|
||||
else if ((strcmp("channel", key) == 0) || (strcmp("chan", key) == 0)) {
|
||||
return _netif_set_u16(iface, NETOPT_CHANNEL, 0, value);
|
||||
}
|
||||
|
@ -5,7 +5,9 @@ BOARD_INSUFFICIENT_MEMORY := \
|
||||
arduino-nano \
|
||||
arduino-uno \
|
||||
atmega328p \
|
||||
derfmega128 \
|
||||
i-nucleo-lrwan1 \
|
||||
microduino-corerf \
|
||||
nucleo-f031k6 \
|
||||
nucleo-f042k6 \
|
||||
nucleo-f303k8 \
|
||||
|
Loading…
Reference in New Issue
Block a user