From b7705a91224208313b36900440e01741ad6e3e5f Mon Sep 17 00:00:00 2001 From: Arto Kinnunen Date: Mon, 8 Jun 2020 09:25:34 +0300 Subject: [PATCH 1/3] components/802.15.4 STM S2LP driver update Sync with master v1.0.5 --- .../stm-s2lp-rf-driver/mbed_lib.json | 72 ++++++++- .../source/NanostackRfPhys2lp.cpp | 30 ++-- .../source/rf_configuration.c | 2 +- .../stm-s2lp-rf-driver/NanostackRfPhys2lp.h | 151 ++++++++++-------- 4 files changed, 163 insertions(+), 92 deletions(-) diff --git a/components/802.15.4_RF/stm-s2lp-rf-driver/mbed_lib.json b/components/802.15.4_RF/stm-s2lp-rf-driver/mbed_lib.json index 80c1ad14b8..55e4bf1748 100644 --- a/components/802.15.4_RF/stm-s2lp-rf-driver/mbed_lib.json +++ b/components/802.15.4_RF/stm-s2lp-rf-driver/mbed_lib.json @@ -1,17 +1,73 @@ { "name": "s2lp", "config": { + "SPI_SDI": { + "help": "SPI_SDI pin for SPI connection. D11 assumed, needs to be set/overwritten otherwise", + "value": null + }, + "SPI_SDO": { + "help": "SPI_SDO pin for SPI connection. D12 assumed, needs to be set/overwritten otherwise", + "value": null + }, + "SPI_SCLK": { + "help": "SPI_SCLK pin for SPI connection, D13 assumed, needs to be set/overwritten otherwise", + "value": null + }, + "SPI_CS": { + "help": "SPI_CS pin for SPI connection, A1 assumed, needs to be set/overwritten otherwise", + "value": null + }, + "SPI_SDN": { + "help": "SPI_SDN pin for SPI connection, D7 assumed, needs to be set/overwritten otherwise", + "value": null + }, + "TEST_PIN_TX": { + "help": "TEST_PIN_TX pin for serial connection, D6 assumed, needs to be set/overwritten otherwise", + "value": null + }, + "TEST_PIN_RX": { + "help": "TEST_PIN_RX pin for serial connection, D5 assumed, needs to be set/overwritten otherwise", + "value": null + }, + "TEST_PIN_CSMA": { + "help": "TEST_PIN_CSMA pin for CSMA, D4 assumed, needs to be set/overwritten otherwise", + "value": null + }, + "TEST_PIN_SPARE_1": { + "help": "TEST_PIN_SPARE_1 pin for testing, D2 assumed, needs to be set/overwritten otherwise", + "value": null + }, + "TEST_PIN_SPARE_2": { + "help": "TEST_PIN_SPARE_2 pin for testing, D8 assumed, needs to be set/overwritten otherwise", + "value": null + }, + "SPI_GPIO0": { + "help": "SPI_GPIO0 pin for GPIO testing, A0 assumed, needs to be set/overwritten otherwise", + "value": null + }, + "SPI_GPIO1": { + "help": "SPI_GPIO1 pin for GPIO testing, A2 assumed, needs to be set/overwritten otherwise", + "value": null + }, + "SPI_GPIO2": { + "help": "SPI_GPIO2 pin for GPIO testing, A3 assumed, needs to be set/overwritten otherwise", + "value": null + }, + "SPI_GPIO3": { + "help": "SPI_GPIO3 pin for GPIO testing, A5 assumed, needs to be set/overwritten otherwise", + "value": null + }, + "I2C_SDA": { + "help": "I2C_SDA pin for I2C SDA, null assumed, needs to be set/overwritten otherwise", + "value": null + }, + "I2C_SCL": { + "help": "I2C_SCL pin for I2C SCL, null assumed, needs to be set/overwritten otherwise", + "value": null + }, "provide-default": { "help": "Provide default NanostackRfpy. [true/false]", "value": false - }, - "target_overrides": { - "MTB_STM_S2LP": { - "s2lp.provide-default": true - }, - "MTB_STM_S2LP_CT": { - "s2lp.provide-default": true - } } } } diff --git a/components/802.15.4_RF/stm-s2lp-rf-driver/source/NanostackRfPhys2lp.cpp b/components/802.15.4_RF/stm-s2lp-rf-driver/source/NanostackRfPhys2lp.cpp index 10d8e86376..720a0535ec 100644 --- a/components/802.15.4_RF/stm-s2lp-rf-driver/source/NanostackRfPhys2lp.cpp +++ b/components/802.15.4_RF/stm-s2lp-rf-driver/source/NanostackRfPhys2lp.cpp @@ -182,7 +182,9 @@ static bool rf_rx_filter(uint8_t *mac_header, uint8_t *mac_64bit_addr, uint8_t * static void rf_cca_timer_start(uint32_t slots); static RFPins *rf; +#ifdef TEST_GPIOS_ENABLED static TestPins_S2LP *test_pins; +#endif static phy_device_driver_s device_driver; static int8_t rf_radio_driver_id = -1; static uint8_t *tx_data_ptr; @@ -707,7 +709,7 @@ static int8_t rf_extension(phy_extension_type_e extension_type, uint8_t *data_pt break; case PHY_EXTENSION_SET_CHANNEL_CCA_THRESHOLD: if ((rssi_threshold != (int8_t)*data_ptr) && (rf_state != RF_RX_STARTED)) { - rssi_threshold = (int8_t)*data_ptr; + rssi_threshold = (int8_t)*data_ptr; // *NOPAD* rf_update_cca_threshold = true; rf_receive(rf_rx_channel); } @@ -760,9 +762,9 @@ static void rf_tx_sent_handler(void) TEST_TX_DONE rf_backup_timer_stop(); rf_disable_interrupt(TX_DATA_SENT); + rf_update_tx_active_time(); if (rf_state != RF_TX_ACK) { tx_finnish_time = rf_get_timestamp(); - rf_update_tx_active_time(); rf_state = RF_IDLE; rf_receive(rf_rx_channel); if (device_driver.phy_tx_done_cb) { @@ -829,7 +831,6 @@ static void rf_cca_timer_interrupt(void) } rf_flush_tx_fifo(); tx_finnish_time = rf_get_timestamp(); - rf_update_tx_active_time(); if (device_driver.phy_tx_done_cb) { device_driver.phy_tx_done_cb(rf_radio_driver_id, mac_tx_handle, PHY_LINK_CCA_FAIL, 0, 0); } @@ -963,7 +964,6 @@ static void rf_handle_ack(uint8_t seq_number, uint8_t pending) phy_link_tx_status_e phy_status; if (tx_sequence == (uint16_t)seq_number) { tx_finnish_time = rf_get_timestamp(); - rf_update_tx_active_time(); if (pending) { phy_status = PHY_LINK_TX_DONE_PENDING; } else { @@ -1294,7 +1294,9 @@ int8_t NanostackRfPhys2lp::rf_register() } rf = _rf; +#ifdef TEST_GPIOS_ENABLED test_pins = _test_pins; +#endif int8_t radio_id = rf_device_register(_mac_addr); if (radio_id < 0) { @@ -1317,18 +1319,18 @@ void NanostackRfPhys2lp::rf_unregister() } NanostackRfPhys2lp::NanostackRfPhys2lp(PinName spi_sdi, PinName spi_sdo, PinName spi_sclk, PinName spi_cs, PinName spi_sdn - ,PinName spi_gpio0, PinName spi_gpio1, PinName spi_gpio2, PinName spi_gpio3 + , PinName spi_gpio0, PinName spi_gpio1, PinName spi_gpio2, PinName spi_gpio3 #ifdef AT24MAC - ,PinName i2c_sda, PinName i2c_scl + , PinName i2c_sda, PinName i2c_scl #endif //AT24MAC - ) + ) : #ifdef AT24MAC - _mac(i2c_sda, i2c_scl), + _mac(i2c_sda, i2c_scl), #endif //AT24MAC - _mac_addr(), _rf(NULL), _mac_set(false), - _spi_sdi(spi_sdi), _spi_sdo(spi_sdo), _spi_sclk(spi_sclk), _spi_cs(spi_cs), _spi_sdn(spi_sdn), - _spi_gpio0(spi_gpio0), _spi_gpio1(spi_gpio1), _spi_gpio2(spi_gpio2), _spi_gpio3(spi_gpio3) + _mac_addr(), _rf(NULL), _mac_set(false), + _spi_sdi(spi_sdi), _spi_sdo(spi_sdo), _spi_sclk(spi_sclk), _spi_cs(spi_cs), _spi_sdn(spi_sdn), + _spi_gpio0(spi_gpio0), _spi_gpio1(spi_gpio1), _spi_gpio2(spi_gpio2), _spi_gpio3(spi_gpio3) { _rf = new RFPins(_spi_sdi, _spi_sdo, _spi_sclk, _spi_cs, _spi_sdn, _spi_gpio0, _spi_gpio1, _spi_gpio2, _spi_gpio3); #ifdef TEST_GPIOS_ENABLED @@ -1438,11 +1440,11 @@ static bool rf_rx_filter(uint8_t *mac_header, uint8_t *mac_64bit_addr, uint8_t * NanostackRfPhy &NanostackRfPhy::get_default_instance() { static NanostackRfPhys2lp rf_phy(S2LP_SPI_SDI, S2LP_SPI_SDO, S2LP_SPI_SCLK, S2LP_SPI_CS, S2LP_SPI_SDN - ,S2LP_SPI_GPIO0, S2LP_SPI_GPIO1, S2LP_SPI_GPIO2, S2LP_SPI_GPIO3 + , S2LP_SPI_GPIO0, S2LP_SPI_GPIO1, S2LP_SPI_GPIO2, S2LP_SPI_GPIO3 #ifdef AT24MAC - ,S2LP_I2C_SDA, S2LP_I2C_SCL + , S2LP_I2C_SDA, S2LP_I2C_SCL #endif //AT24MAC - ); + ); return rf_phy; } #endif // MBED_CONF_S2LP_PROVIDE_DEFAULT diff --git a/components/802.15.4_RF/stm-s2lp-rf-driver/source/rf_configuration.c b/components/802.15.4_RF/stm-s2lp-rf-driver/source/rf_configuration.c index 3cb0c2b6a1..9f261ee02d 100644 --- a/components/802.15.4_RF/stm-s2lp-rf-driver/source/rf_configuration.c +++ b/components/802.15.4_RF/stm-s2lp-rf-driver/source/rf_configuration.c @@ -157,7 +157,7 @@ void rf_conf_calculate_rx_filter_bandwidth_registers(uint32_t rx_bandwidth, uint int16_t rf_conf_cca_threshold_percent_to_rssi(uint8_t percent) { - uint8_t step = (MAX_RSSI_THRESHOLD-MIN_RSSI_THRESHOLD); + uint8_t step = (MAX_RSSI_THRESHOLD - MIN_RSSI_THRESHOLD); return MIN_RSSI_THRESHOLD + (step * percent) / 100; } diff --git a/components/802.15.4_RF/stm-s2lp-rf-driver/stm-s2lp-rf-driver/NanostackRfPhys2lp.h b/components/802.15.4_RF/stm-s2lp-rf-driver/stm-s2lp-rf-driver/NanostackRfPhys2lp.h index d83fb25c8d..280aa3ddba 100644 --- a/components/802.15.4_RF/stm-s2lp-rf-driver/stm-s2lp-rf-driver/NanostackRfPhys2lp.h +++ b/components/802.15.4_RF/stm-s2lp-rf-driver/stm-s2lp-rf-driver/NanostackRfPhys2lp.h @@ -25,87 +25,100 @@ #include "InterruptIn.h" #include "SPI.h" -// Uncomment to use testing gpios attached to TX/RX processes -// #define TEST_GPIOS_ENABLED - -#if defined(TARGET_MTB_STM_S2LP) || defined(TARGET_MTB_STM_S2LP_CT) -#if !defined(S2LP_SPI_SDI) -#define S2LP_SPI_SDI PA_7 -#endif -#if !defined(S2LP_SPI_SDO) -#define S2LP_SPI_SDO PA_6 -#endif -#if !defined(S2LP_SPI_SCLK) -#define S2LP_SPI_SCLK PA_5 -#endif -#if !defined(S2LP_SPI_CS) -#define S2LP_SPI_CS PC_0 -#endif -#if !defined(S2LP_SPI_SDN) -#define S2LP_SPI_SDN PF_13 -#endif -#if !defined(S2LP_SPI_GPIO0) -#define S2LP_SPI_GPIO0 PA_3 -#endif -#if !defined(S2LP_SPI_GPIO1) -#define S2LP_SPI_GPIO1 PC_3 -#endif -#if !defined(S2LP_SPI_GPIO2) -#define S2LP_SPI_GPIO2 PF_3 -#endif -#if !defined(S2LP_SPI_GPIO3) -#define S2LP_SPI_GPIO3 PF_10 -#endif -#if !defined(S2LP_I2C_SDA) -#define S2LP_I2C_SDA PB_7 -#endif -#if !defined(S2LP_I2C_SCL) -#define S2LP_I2C_SCL PB_6 -#endif -#define AT24MAC +#if defined(MBED_CONF_S2LP_SPI_SDI) +#define S2LP_SPI_SDI MBED_CONF_S2LP_SPI_SDI #else -#if !defined(S2LP_SPI_SDI) -#define S2LP_SPI_SDI D11 +#define S2LP_SPI_SDI D11 #endif -#if !defined(S2LP_SPI_SDO) -#define S2LP_SPI_SDO D12 + +#if defined(MBED_CONF_S2LP_SPI_SDO) +#define S2LP_SPI_SDO MBED_CONF_S2LP_SPI_SDO +#else +#define S2LP_SPI_SDO D12 #endif -#if !defined(S2LP_SPI_SCLK) -#define S2LP_SPI_SCLK D13 + +#if defined(MBED_CONF_S2LP_SPI_SCLK) +#define S2LP_SPI_SCLK MBED_CONF_S2LP_SPI_SCLK +#else +#define S2LP_SPI_SCLK D13 #endif -#if !defined(S2LP_SPI_CS) -#define S2LP_SPI_CS A1 + +#if defined(MBED_CONF_S2LP_SPI_CS) +#define S2LP_SPI_CS MBED_CONF_S2LP_SPI_CS +#else +#define S2LP_SPI_CS A1 #endif -#if !defined(S2LP_SPI_SDN) -#define S2LP_SPI_SDN D7 + +#if defined(MBED_CONF_S2LP_SPI_SDN) +#define S2LP_SPI_SDN MBED_CONF_S2LP_SPI_SDN +#else +#define S2LP_SPI_SDN D7 #endif -#if !defined(TEST_PIN_TX) -#define TEST_PIN_TX D6 + +#if defined(MBED_CONF_S2LP_TEST_PIN_TX) +#define S2LP_TEST_PIN_TX MBED_CONF_S2LP_TEST_PIN_TX +#else +#define S2LP_TEST_PIN_TX D6 #endif -#if !defined(TEST_PIN_RX) -#define TEST_PIN_RX D5 + +#if defined(MBED_CONF_S2LP_TEST_PIN_RX) +#define S2LP_TEST_PIN_RX MBED_CONF_S2LP_TEST_PIN_RX +#else +#define S2LP_TEST_PIN_RX D5 #endif -#if !defined(TEST_PIN_CSMA) -#define TEST_PIN_CSMA D4 + +#if defined(MBED_CONF_S2LP_TEST_PIN_CSMA) +#define S2LP_TEST_PIN_CSMA MBED_CONF_S2LP_TEST_PIN_CSMA +#else +#define S2LP_TEST_PIN_CSMA D4 #endif -#if !defined(TEST_PIN_SPARE_1) -#define TEST_PIN_SPARE_1 D2 + +#if defined(MBED_CONF_S2LP_TEST_PIN_SPARE_1) +#define S2LP_TEST_PIN_SPARE_1 MBED_CONF_S2LP_TEST_PIN_SPARE_1 +#else +#define S2LP_TEST_PIN_SPARE_1 D2 #endif -#if !defined(TEST_PIN_SPARE_2) -#define TEST_PIN_SPARE_2 D8 + +#if defined(MBED_CONF_S2LP_TEST_PIN_SPARE_2) +#define S2LP_TEST_PIN_SPARE_2 MBED_CONF_S2LP_TEST_PIN_SPARE_2 +#else +#define S2LP_TEST_PIN_SPARE_2 D8 #endif -#if !defined(S2LP_SPI_GPIO0) -#define S2LP_SPI_GPIO0 A0 + +#if defined(MBED_CONF_S2LP_SPI_GPIO0) +#define S2LP_SPI_GPIO0 MBED_CONF_S2LP_SPI_GPIO0 +#else +#define S2LP_SPI_GPIO0 A0 #endif -#if !defined(S2LP_SPI_GPIO1) -#define S2LP_SPI_GPIO1 A2 + +#if defined(MBED_CONF_S2LP_SPI_GPIO1) +#define S2LP_SPI_GPIO1 MBED_CONF_S2LP_SPI_GPIO1 +#else +#define S2LP_SPI_GPIO1 A2 #endif -#if !defined(S2LP_SPI_GPIO2) -#define S2LP_SPI_GPIO2 A3 + +#if defined(MBED_CONF_S2LP_SPI_GPIO2) +#define S2LP_SPI_GPIO2 MBED_CONF_S2LP_SPI_GPIO2 +#else +#define S2LP_SPI_GPIO2 A3 #endif -#if !defined(S2LP_SPI_GPIO3) -#define S2LP_SPI_GPIO3 A5 + +#if defined(MBED_CONF_S2LP_SPI_GPIO3) +#define S2LP_SPI_GPIO3 MBED_CONF_S2LP_SPI_GPIO3 +#else +#define S2LP_SPI_GPIO3 A5 #endif + +#if defined(MBED_CONF_S2LP_I2C_SDA) +#define S2LP_I2C_SDA MBED_CONF_S2LP_I2C_SDA +#else +#define S2LP_I2C_SDA null +#endif + +#if defined(MBED_CONF_S2LP_I2C_SCL) +#define S2LP_I2C_SCL MBED_CONF_S2LP_I2C_SCL +#else +#define S2LP_I2C_SCL null #endif #include "at24mac_s2lp.h" @@ -116,11 +129,11 @@ class TestPins_S2LP; class NanostackRfPhys2lp : public NanostackRfPhy { public: NanostackRfPhys2lp(PinName spi_sdi, PinName spi_sdo, PinName spi_sclk, PinName spi_cs, PinName spi_sdn - ,PinName spi_gpio0, PinName spi_gpio1, PinName spi_gpio2, PinName spi_gpio3 + , PinName spi_gpio0, PinName spi_gpio1, PinName spi_gpio2, PinName spi_gpio3 #ifdef AT24MAC - ,PinName i2c_sda, PinName i2c_scl + , PinName i2c_sda, PinName i2c_scl #endif //AT24MAC - ); + ); virtual ~NanostackRfPhys2lp(); virtual int8_t rf_register(); virtual void rf_unregister(); From 8a16f4bf6999f06633bba23d5aae16d3d9837aaa Mon Sep 17 00:00:00 2001 From: Arto Kinnunen Date: Mon, 8 Jun 2020 09:37:37 +0300 Subject: [PATCH 2/3] components/802.15.4 Atmel RF driver update Sync with master version v3.3.0 --- .../atmel-rf-driver/NanostackRfPhyAtmel.h | 10 ++++++ .../atmel-rf-driver/source/AT86RF215Reg.h | 18 ++++++++++- .../atmel-rf-driver/source/AT86RFReg.h | 1 + .../source/NanostackRfPhyAT86RF215.cpp | 32 +++++++++++++++++++ .../source/NanostackRfPhyAtmel.cpp | 30 +++++++++++++++-- .../atmel-rf-driver/source/rfbits.h | 8 +++++ 6 files changed, 95 insertions(+), 4 deletions(-) diff --git a/components/802.15.4_RF/atmel-rf-driver/atmel-rf-driver/NanostackRfPhyAtmel.h b/components/802.15.4_RF/atmel-rf-driver/atmel-rf-driver/NanostackRfPhyAtmel.h index 028663f63e..d6fab5cf5d 100644 --- a/components/802.15.4_RF/atmel-rf-driver/atmel-rf-driver/NanostackRfPhyAtmel.h +++ b/components/802.15.4_RF/atmel-rf-driver/atmel-rf-driver/NanostackRfPhyAtmel.h @@ -70,9 +70,16 @@ #if !defined(TEST_PIN_SPARE_2) #define TEST_PIN_SPARE_2 D8 #endif +#if !defined(SE2435L_CSD) +#define SE2435L_CSD D2 +#endif +#if !defined(SE2435L_ANT_SEL) +#define SE2435L_ANT_SEL D8 +#endif class RFBits; class TestPins; +class Se2435Pins; class NanostackRfPhyAtmel : public NanostackRfPhy { public: @@ -86,10 +93,13 @@ public: virtual void set_mac_address(uint8_t *mac); private: +#if !defined(DISABLE_AT24MAC) AT24Mac _mac; +#endif uint8_t _mac_addr[8]; RFBits *_rf; TestPins *_test_pins; + Se2435Pins *_se2435_pa_pins; bool _mac_set; const PinName _spi_mosi; diff --git a/components/802.15.4_RF/atmel-rf-driver/source/AT86RF215Reg.h b/components/802.15.4_RF/atmel-rf-driver/source/AT86RF215Reg.h index 70555ac63f..6836b0cb3f 100644 --- a/components/802.15.4_RF/atmel-rf-driver/source/AT86RF215Reg.h +++ b/components/802.15.4_RF/atmel-rf-driver/source/AT86RF215Reg.h @@ -26,6 +26,7 @@ extern "C" { #define RF24_IRQS 0x01 #define BBC0_IRQS 0x02 #define BBC1_IRQS 0x03 +#define RF_AUXS 0x01 #define RF_CFG 0x06 #define RF_IQIFC1 0x0B #define RF_PN 0x0D @@ -47,6 +48,8 @@ extern "C" { #define RF_EDV 0x10 #define RF_TXCUTC 0x12 #define RF_TXDFE 0x13 +#define RF_PAC 0x14 +#define RF_PADFE 0x16 #define BBC_IRQM 0x00 #define BBC_PC 0x01 #define BBC_RXFLL 0x04 @@ -85,6 +88,20 @@ extern "C" { #define BBC1_FBRXS 0x3000 #define BBC1_FBTXS 0x3800 +// RF_AUXS +#define EXTLNABYP (1 << 7) +#define AGCMAP 0x60 +#define AGCMAP_2 (2 << 5) +#define AVEN (1 << 3) + +// RF_PAC +#define TXPWR 0x1F +#define TXPWR_11 (11 << 0) + +// RF_PADFE +#define PADFE 0xC0 +#define RF_FEMODE3 (3 << 6) + // RF_AGCC #define AGCI (1 << 6) #define AVGS 0x30 @@ -95,7 +112,6 @@ extern "C" { #define TGT_1 (1 << 5) #define TGT_3 (3 << 5) - // RF_RXBWC #define BW 0x0F #define RF_BW2000KHZ_IF2000KHZ (11 << 0) diff --git a/components/802.15.4_RF/atmel-rf-driver/source/AT86RFReg.h b/components/802.15.4_RF/atmel-rf-driver/source/AT86RFReg.h index c53d9fe922..fb86b7119b 100644 --- a/components/802.15.4_RF/atmel-rf-driver/source/AT86RFReg.h +++ b/components/802.15.4_RF/atmel-rf-driver/source/AT86RFReg.h @@ -48,6 +48,7 @@ extern "C" { #define PART_AT86RF212 0x07 #define PART_AT86RF233 0x0B #define PART_AT86RF215 0x34 +#define PART_AT86RF215M 0x36 #define VERSION_AT86RF212 0x01 #define VERSION_AT86RF212B 0x03 diff --git a/components/802.15.4_RF/atmel-rf-driver/source/NanostackRfPhyAT86RF215.cpp b/components/802.15.4_RF/atmel-rf-driver/source/NanostackRfPhyAT86RF215.cpp index a48abf6c90..488b337527 100644 --- a/components/802.15.4_RF/atmel-rf-driver/source/NanostackRfPhyAT86RF215.cpp +++ b/components/802.15.4_RF/atmel-rf-driver/source/NanostackRfPhyAT86RF215.cpp @@ -23,6 +23,7 @@ #include "platform/mbed_wait_api.h" #include "nanostack/platform/arm_hal_phy.h" #include "NanostackRfPhyAtmel.h" +#include "AT86RFReg.h" #include "AT86RF215Reg.h" #include "mbed_trace.h" #include "common_functions.h" @@ -165,6 +166,7 @@ using namespace rtos; #include "rfbits.h" static RFBits *rf; static TestPins *test_pins; +static Se2435Pins *se2435_pa_pins = NULL; #define MAC_FRAME_TYPE_MASK 0x07 #define MAC_TYPE_ACK (2) @@ -464,6 +466,18 @@ static void rf_init_registers(rf_modules_e module) rf_write_rf_register_field(RF_AGCS, module, TGT, TGT_3); } } + if (se2435_pa_pins) { + // Wakeup SE2435L + se2435_pa_pins->CSD = 1; + // Antenna port selection: (0 - port 1, 1 - port 2) + se2435_pa_pins->ANT_SEL = 0; + // Enable external front end with configuration 3 + rf_write_rf_register_field(RF_PADFE, module, PADFE, RF_FEMODE3); + // Output power at 900MHz: 0 dBm with FSK/QPSK, less than -5 dBm with OFDM + rf_write_rf_register_field(RF_PAC, module, TXPWR, TXPWR_11); + } + // Enable analog voltage regulator + rf_write_rf_register_field(RF_AUXS, module, AVEN, AVEN); // Disable filtering FCS rf_write_bbc_register_field(BBC_PC, module, FCSFE, 0); // Set channel spacing @@ -1189,10 +1203,28 @@ int RFBits::init_215_driver(RFBits *_rf, TestPins *_test_pins, const uint8_t mac test_pins = _test_pins; irq_thread_215.start(mbed::callback(this, &RFBits::rf_irq_task)); rf->spi.frequency(25000000); + /* Atmel AT86RF215 Device Family datasheet: + * Errata #9: RF215M device has a wrong part number + * Description: + * The RF215M device part number is 0x34 instead of 0x36 (register RF_PN.PN). + */ +#if !defined(HAVE_AT86RF215M) *rf_part_num = rf_read_common_register(RF_PN); +#else + *rf_part_num = PART_AT86RF215M; + // AT86RF215M is Sub-GHz only transceiver. Change default settings. + rf_module = RF_09; + mac_mode = IEEE_802_15_4G_2012; +#endif rf_version_num = rf_read_common_register(RF_VN); tr_info("RF version number: %x", rf_version_num); return rf_device_register(mac); } +int RFBits::init_se2435_pa(Se2435Pins *_se2435_pa_pins) +{ + se2435_pa_pins = _se2435_pa_pins; + return 0; +} + #endif // MBED_CONF_NANOSTACK_CONFIGURATION && DEVICE_SPI && DEVICE_INTERRUPTIN && defined(MBED_CONF_RTOS_PRESENT) diff --git a/components/802.15.4_RF/atmel-rf-driver/source/NanostackRfPhyAtmel.cpp b/components/802.15.4_RF/atmel-rf-driver/source/NanostackRfPhyAtmel.cpp index e747af742d..ef3ce7f447 100644 --- a/components/802.15.4_RF/atmel-rf-driver/source/NanostackRfPhyAtmel.cpp +++ b/components/802.15.4_RF/atmel-rf-driver/source/NanostackRfPhyAtmel.cpp @@ -275,8 +275,15 @@ TestPins::TestPins(PinName test_pin_1, PinName test_pin_2, PinName test_pin_3, P { } +Se2435Pins::Se2435Pins(PinName csd_pin, PinName ant_sel_pin) + : CSD(csd_pin), + ANT_SEL(ant_sel_pin) +{ +} + static RFBits *rf; static TestPins *test_pins; +static Se2435Pins *se2435_pa_pins; static uint8_t rf_part_num = 0; /*TODO: RSSI Base value setting*/ static int8_t rf_rssi_base_val = -91; @@ -2168,14 +2175,21 @@ static uint8_t rf_scale_lqi(int8_t rssi) NanostackRfPhyAtmel::NanostackRfPhyAtmel(PinName spi_mosi, PinName spi_miso, PinName spi_sclk, PinName spi_cs, PinName spi_rst, PinName spi_slp, PinName spi_irq, PinName i2c_sda, PinName i2c_scl) - : _mac(i2c_sda, i2c_scl), _mac_addr(), _rf(NULL), _test_pins(NULL), _mac_set(false), - _spi_mosi(spi_mosi), _spi_miso(spi_miso), _spi_sclk(spi_sclk), - _spi_cs(spi_cs), _spi_rst(spi_rst), _spi_slp(spi_slp), _spi_irq(spi_irq) + : +#if !defined(DISABLE_AT24MAC) + _mac(i2c_sda, i2c_scl), +#endif + _mac_addr(), _rf(NULL), _test_pins(NULL), _se2435_pa_pins(NULL), _mac_set(false), + _spi_mosi(spi_mosi), _spi_miso(spi_miso), _spi_sclk(spi_sclk), + _spi_cs(spi_cs), _spi_rst(spi_rst), _spi_slp(spi_slp), _spi_irq(spi_irq) { _rf = new RFBits(_spi_mosi, _spi_miso, _spi_sclk, _spi_cs, _spi_rst, _spi_slp, _spi_irq); #ifdef TEST_GPIOS_ENABLED _test_pins = new TestPins(TEST_PIN_TX, TEST_PIN_RX, TEST_PIN_CSMA, TEST_PIN_SPARE_1, TEST_PIN_SPARE_2); #endif +#ifdef SE2435L_PA + _se2435_pa_pins = new Se2435Pins(SE2435L_CSD, SE2435L_ANT_SEL); +#endif } NanostackRfPhyAtmel::~NanostackRfPhyAtmel() @@ -2200,19 +2214,29 @@ int8_t NanostackRfPhyAtmel::rf_register() // Read the mac address if it hasn't been set by a user rf = _rf; test_pins = _test_pins; + se2435_pa_pins = _se2435_pa_pins; if (!_mac_set) { +// Unless AT24MAC is available, using randomly generated MAC address +#if !defined(DISABLE_AT24MAC) int ret = _mac.read_eui64((void *)_mac_addr); if (ret < 0) { rf = NULL; rf_if_unlock(); return -1; } +#else + randLIB_seed_random(); + randLIB_get_n_bytes_random(_mac_addr, 8); + _mac_addr[0] |= 2; //Set Local Bit + _mac_addr[0] &= ~1; //Clear multicast bit +#endif } /*Reset RF module*/ rf_if_reset_radio(); rf_part_num = rf_if_read_part_num(); int8_t radio_id = -1; if (rf_part_num != PART_AT86RF231 && rf_part_num != PART_AT86RF233 && rf_part_num != PART_AT86RF212) { + rf->init_se2435_pa(_se2435_pa_pins); // Register RF type 215. Jumps to AT86RF215 driver. radio_id = rf->init_215_driver(_rf, _test_pins, _mac_addr, &rf_part_num); } else { diff --git a/components/802.15.4_RF/atmel-rf-driver/source/rfbits.h b/components/802.15.4_RF/atmel-rf-driver/source/rfbits.h index 94143e6a8b..e9b17b2ea8 100644 --- a/components/802.15.4_RF/atmel-rf-driver/source/rfbits.h +++ b/components/802.15.4_RF/atmel-rf-driver/source/rfbits.h @@ -51,6 +51,7 @@ public: Timeout cca_timer; Timer tx_timer; int init_215_driver(RFBits *_rf, TestPins *_test_pins, const uint8_t mac[8], uint8_t *rf_part_num); + int init_se2435_pa(Se2435Pins *_se2435_pa_pins); #ifdef MBED_CONF_RTOS_PRESENT Thread irq_thread; Thread irq_thread_215; @@ -70,4 +71,11 @@ public: DigitalOut TEST5; }; +class Se2435Pins { +public: + Se2435Pins(PinName csd_pin, PinName ant_sel_pin); + DigitalOut CSD; + DigitalOut ANT_SEL; +}; + #endif /* RFBITS_H_ */ From 528aa2f96fd4702b02ae9fff3dacd546ee984fde Mon Sep 17 00:00:00 2001 From: Arto Kinnunen Date: Mon, 8 Jun 2020 10:12:05 +0300 Subject: [PATCH 3/3] Squashed 'features/nanostack/sal-stack-nanostack/' changes from 9a2166869f..b3fe5744d1 b3fe5744d1 Remove test files from the release b2bf24ca85 Merge branch 'release_internal' into release_external 0ed25a7485 Fix errors found from coverity scan (#2386) 7a138f7e51 Added IID for border router info structure 4021b0c1ef LLC secure data duplicate check update and EAPOL relay duplicate fix b190a97eeb Remove Thread-protocol from README (#2383) ae8ae32cfe EAPOL relay agent rx filter from joiner side 0d4eb7a46e Removed dead code part fc644f5e5b RPL new parent accept update and NUD operation f5920e2d0c ETX API update and RPL ETX threshold callback update. 1fdee20a40 Wi-sun keep all candidates alive by NUD. bd746da33d Key storage settings are no longer cleared on delete bd388fcb08 Changed EAPOL initial-Key retries from 2 to 4 on large NW a3d80a3235 WS bootstrap: Default CCA threshold to -60dBm (#2377) 72b26a72c2 Created extra large network setup for Wi-SUN 38dd4a6423 Corrected PTK and PMK lifetime handling 64f2a77239 Cleared EAPOL temporary trace print's. 02ec23fa27 Timed parent selection is now imim-imin*2 earlier there was just 5 seconds randomize. 3b2d906b75 Added check for network name and DODAG ID IID (EUI-64) (#2373) ee45f4be32 Updated initial key trickles 184425b038 Fixed parent target address set. 07ec2374a1 Updated Discovery and RPL setup large & medium size network a94d8f2e5d RPL version num update 9e2ac1d855 Double default eapol entry size for test purpose. 6b8beefb51 Clear all neighbors only on eapol next target check faa19e1fba Corrected next address set 8a917fb9a5 Continue trickle on initial EAPOL-key TX failure cfdb193c3e Merge pull request #2368 from ARMmbed/sync_with_mbedos f7a15fa68d (via MbedOS) ws: added support for brazilian regulatory domain c397edb121 Changed large network initial-key trickle parameters 758f5347b5 Added maximum frame counter storing interval b0ea148d41 Corrected key storage configuration setting be3c94e03b WS RPL paret soft filter update 8b1d537a02 Adjusted EAPOL limits and timers git-subtree-dir: features/nanostack/sal-stack-nanostack git-subtree-split: b3fe5744d1ab20792223ff08f08ef97a1f89682b --- README.md | 22 +- docs/img/thread_certified.png | Bin 10158 -> 0 bytes nanostack/ws_bbr_api.h | 2 + nanostack/ws_management_api.h | 20 +- .../Generic/protocol_6lowpan_bootstrap.c | 8 +- source/6LoWPAN/Thread/thread_bootstrap.c | 2 +- source/6LoWPAN/adaptation_interface.c | 2 +- source/6LoWPAN/ws/ws_bbr_api.c | 34 +++- source/6LoWPAN/ws/ws_bootstrap.c | 187 +++++++++-------- source/6LoWPAN/ws/ws_cfg_settings.c | 121 ++++++++--- source/6LoWPAN/ws/ws_cfg_settings.h | 14 +- source/6LoWPAN/ws/ws_common.c | 58 +++++- source/6LoWPAN/ws/ws_common.h | 2 +- source/6LoWPAN/ws/ws_common_defines.h | 3 +- source/6LoWPAN/ws/ws_config.h | 65 ++++-- source/6LoWPAN/ws/ws_eapol_pdu.c | 8 + source/6LoWPAN/ws/ws_eapol_pdu.h | 1 + source/6LoWPAN/ws/ws_eapol_relay.c | 1 + source/6LoWPAN/ws/ws_llc.h | 10 +- source/6LoWPAN/ws/ws_llc_data_service.c | 130 +++++------- source/6LoWPAN/ws/ws_management_api.c | 8 +- source/6LoWPAN/ws/ws_neighbor_class.c | 27 +++ source/6LoWPAN/ws/ws_neighbor_class.h | 3 + source/6LoWPAN/ws/ws_pae_auth.c | 37 ++-- source/6LoWPAN/ws/ws_pae_controller.c | 40 +++- source/6LoWPAN/ws/ws_pae_controller.h | 20 +- source/6LoWPAN/ws/ws_pae_key_storage.c | 13 +- source/6LoWPAN/ws/ws_pae_lib.c | 9 +- source/6LoWPAN/ws/ws_pae_lib.h | 3 +- source/6LoWPAN/ws/ws_pae_nvm_data.c | 20 +- source/6LoWPAN/ws/ws_pae_nvm_data.h | 4 +- source/6LoWPAN/ws/ws_pae_supp.c | 166 +++++++++------- source/6LoWPAN/ws/ws_pae_supp.h | 19 +- source/6LoWPAN/ws/ws_pae_time.c | 7 +- source/6LoWPAN/ws/ws_pae_timers.c | 1 + source/6LoWPAN/ws/ws_pae_timers.h | 12 -- source/MAC/IEEE802_15_4/mac_data_buffer.h | 1 + source/MAC/IEEE802_15_4/mac_mcps_sap.c | 6 +- source/RPL/rpl_control.c | 25 ++- source/Security/kmp/kmp_api.c | 5 +- source/Security/kmp/kmp_api.h | 5 +- .../eap_tls_sec_prot/auth_eap_tls_sec_prot.c | 10 +- .../eap_tls_sec_prot/supp_eap_tls_sec_prot.c | 6 +- .../fwh_sec_prot/auth_fwh_sec_prot.c | 8 +- .../fwh_sec_prot/supp_fwh_sec_prot.c | 10 +- .../gkh_sec_prot/auth_gkh_sec_prot.c | 4 +- source/Security/protocols/sec_prot.h | 3 +- source/Security/protocols/sec_prot_cfg.h | 17 ++ source/Security/protocols/sec_prot_keys.c | 48 +++-- source/Security/protocols/sec_prot_keys.h | 35 +++- .../protocols/tls_sec_prot/tls_sec_prot.c | 4 +- source/Service_Libs/etx/etx.c | 106 ++++++---- source/Service_Libs/etx/etx.h | 15 +- .../unittest/mac/mac_cca_threshold/Makefile | 19 -- .../mac_cca_threshold_test.cpp | 47 ----- .../unittest/mac/mac_cca_threshold/main.cpp | 28 --- .../test_mac_cca_threshold.c | 188 ------------------ .../test_mac_cca_threshold.h | 36 ---- .../unittest/stub/mac_cca_threshold_stub.c | 43 ---- .../nanostack/unittest/stub/ns_monitor_stub.h | 35 ---- 60 files changed, 896 insertions(+), 887 deletions(-) delete mode 100644 docs/img/thread_certified.png delete mode 100644 test/nanostack/unittest/mac/mac_cca_threshold/Makefile delete mode 100644 test/nanostack/unittest/mac/mac_cca_threshold/mac_cca_threshold_test.cpp delete mode 100644 test/nanostack/unittest/mac/mac_cca_threshold/main.cpp delete mode 100644 test/nanostack/unittest/mac/mac_cca_threshold/test_mac_cca_threshold.c delete mode 100644 test/nanostack/unittest/mac/mac_cca_threshold/test_mac_cca_threshold.h delete mode 100644 test/nanostack/unittest/stub/mac_cca_threshold_stub.c delete mode 100644 test/nanostack/unittest/stub/ns_monitor_stub.h diff --git a/README.md b/README.md index f614033fa7..ddddf390c7 100644 --- a/README.md +++ b/README.md @@ -3,37 +3,29 @@ ARM Mesh networking stack This repository contains the ARM mesh networking stack that provides support for the following mesh protocols: - * 6LoWPAN with Neighbor Discovery (ND) and Mesh Link Establishment (MLE) - * Thread - * Wi-SUN +* 6LoWPAN with Neighbor Discovery (ND) and Mesh Link Establishment (MLE) +* Wi-SUN - All networking stacks are using IEEE 802.15.4 based radios. +All networking stacks are using IEEE 802.15.4 based radios. The full documentation is hosted in [Mbed OS documentation](https://os.mbed.com/docs/mbed-os/latest/reference/mesh-tech.html). -On mbed OS, mesh networking stacks can be used through [Mbed Mesh API](https://os.mbed.com/docs/mbed-os/latest/apis/mesh-api.html) and [Network Socket API](https://os.mbed.com/docs/mbed-os/v5.11/apis/network-socket.html). +On mbed OS, mesh networking stacks can be used through [Mbed Mesh API](https://os.mbed.com/docs/mbed-os/latest/apis/mesh-api.html) and [Network Socket API](https://os.mbed.com/docs/mbed-os/latest/apis/network-socket.html). To see, how the mesh networking stack works, check the example application [mbed-os-example-mesh-minimal](https://github.com/ARMmbed/mbed-os-example-mesh-minimal). - -##6LoWPAN with ND and MLE + +## 6LoWPAN with ND and MLE This networking stack is using standard 6LoWPAN and uses: * Neighbor Discovery Protocol ([RFC4861](https://tools.ietf.org/html/rfc4861)) to locate other devices in the mesh network. * Mesh-Link-Establishment ([draft-kelsey-intarea-mesh-link-establishment-06](https://tools.ietf.org/html/draft-kelsey-intarea-mesh-link-establishment-06)) is used for establishing and configuring secure radio links. - -##Thread -Thread is standardized by [Thread group](https://www.threadgroup.org/). -![](docs/img/thread_certified.png) -mbed OS is now a Thread Certified Component. Using IPv6 with 6LoWPAN as the foundation, Thread technology provides a low-power, self-healing mesh network designed for the home. - -##Wi-SUN +## Wi-SUN Wi-SUN (Smart Utility Networks) specification is standardized by [Wi-SUN Alliance](https://www.wi-sun.org/). -Mbed OS release 5.12 contains the initial Mbed Wi-SUN FAN implementation. Functionality of the Mbed Wi-SUN network stack will be updated when the Wi-SUN protocol is specified further. ## License diff --git a/docs/img/thread_certified.png b/docs/img/thread_certified.png deleted file mode 100644 index c86ee53a7e8bd22e2725a12dbf05381e805dc4ea..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 10158 zcmaiabzIZm_y0h0gv1Ex5=VDSjphwFVsws>mPQ1mHc|uxq+>`oNJvOYNl1r;0fNBj zkQ9C|Kab!4-~F-ebsy*4d+s^++}DX`99&O>49oxqfk0$hnyLmM5bnSKH$()$H*NZ> z=fKYcKQ&W7!)H!@fp$KQAZ3SVNJlm;54)$1299-T;99E6M$eaa^W?o& z23KQ}nEbUdUw9vs-OqaCIo3*qh|X_%t>ynfqD3RcJgdfCcTN4>7p}c|&QfuNsb}?c zQSdT^+3xT*ZdF4XkzRcS@45+uo9cKrU>UL-DY`$=!OsKfNO0 z;f>HmsA`1ufju(_lqo?4w$XdYKmoQRipskg(zAQGs0;ytl*lxw$l7e5zlLjC(7V$_ z{ty~?0?5Uvcd}4sZ%R)AUXP3VNMl#u8w&!3-y`>JID7zOf9YLV@PQfx>LK(|SvlQ! ztpxo*N9e;B@=6*YN=Y%5hCxw02$YQLDtdO^WyQ1bpj!&BPw)0h;cnd|77ql{#4{UU zJ^$;7>MK!N9JZk%q#~AkMFawI4eIF&EM|Z0U^$MscK0@e#!3I9&PupBdt^b^?=Ar5 zZO-j}X>K{l!A1oFvH45VW|)N-k9{eE7t4LaikSksO0j2Nl;%r-P1SEd`nR(&h{xL+ zB#jd%B;FJ+4n?*PXev{Lb-7a}Xdz0Jfi}a1-C~6iVEhj+|M z8snHLo&ax^U5wkmp$T)n<=~51=DhpP>UPzbsVOd6@#g3Kgzta%14p~NPrk^F(g9kD zfkr-{Bu*FzyFDo=0VUHnuhg6WJ@*e|krW6#U|Lz}DU!|rd$0ucP!tWs`M#sHq-eq`SvpxW(>J-u%>i+7{r#>>rv?vj0WjK;AE>-(}cy+QG?kqt_VbHhp3AH(|cgP#`QnxrTgWyYc5?NaPi z{Naz@sPa+%A@DptDEyKL4PB>-Rm)^Cql0uPp*29^s%V%X75Oo%&473&6+t6M`J;QN z2vj8Ay(~%)h?p18bKyZ5H~KR{sH+gq7X=M9 z@FoF{Qvp1dV>F_0;35T~Jda*XPH?MCTV7pVwVtOp^r{9EOAaKHszv_Y-K{>pQ@Fc1 z`Bt#(w;Kx29XrD=&>eJL?@yC$@(s_Qd7EIclIcH;oxU2K8C)quF$h^b`@Zm!7vtr~ zl~PZgp!p&AT=0yNW5_fTIT|||DuqB#jE|37cc1UfRV~@i-?b?z_bUvRY%j(XU3&%x zFaH-MRxrfe_r7Yt+;O>#2)=(!`Zi3XPZ_Ckt^_tS!*Yf`Ijl&IMV)dpSv`q_+f`nw zp8u$^XmzG~8WBgFATOzdja^x|zP{F)T|E+n#9Nay#^PnJ*{SjO%=#t-44aD=TCLkWXP!DxTbM`9h28&|CGmhvr8ZQ@ zcgh)NNBP|D;SSeDp6!`!*5}Qen~+Pxjwqf$qV{jx3^J1PCvONY_1z&QInY_CkW@=F5!0hDgxI5KLO71#k@mhUcDu*J>dnkUS~)bU*qs$T63YehbqkM28I!!WrtM37~Au+ zO-`pfOM?qt?2Fqp&qo*Ma}+M(^*_+<5a*B({hf*`{09F1@_G;3_*pVFpM{*qMYnuY zY%o{6jNcvaMCrWA6-RtrWm15geb5wt-1|POg8OQ6Kb7;IB@{A`%A?Q3328KfcIQrKUJEy=t-{2JRq>=c3!Q zvhsw|&7^oBSZ5)erE-1U{;6?-ti$a?E3%L^j(c|d^Qg=kFv0jcf8TOE_|`|Xr3ECi ziF=C!u0BV;huZ(%t!QRcs~W$?7D6cEa;&U`i*nP|?5!-k)WNCNb(`f!!OH!qb)+=w z>4@1?*GJk53)u>4i7X9%kXVxbnU5%aD(_SUGn_ns|8yc!As}Nrg^)eJP!%^J{G%pO z#d?+uw@oOcc-APs2*P63$lI|Z=x9yNr(?5gRd$HMw@oL+1Cl+ccJgI!xz%kw2KhuF zU9Negy(UQ4o@ytk4Fc{x^GlX_+FRbijN7fRd6LD*lH4U0HD^ET`H8NwF5-+h zx`@~&vc+?udY~t;(6hYBjQY>1(>>e9}FLaX$}*|%hTLlU!@mG>PTa?9Qx@3}K&G-=V08nCW! z^?rc^8ur%F;xegblEp_`JWzwgp43s*B*_HdEySqxWVMNKt*|y`5bkF)j))Ct=B96A zFYh2v>t&&%tBv_fQA0dQW~e748M4m}JtFIZj|k19oZR|$R%Rh$5PJgE)DoUw*^Gjy zK4s_1^v;X@eunM3Jk?ZIU!q1Mcmiuk>~bc5prJXnaSb?BLCk3Ob^Gh&gGA-p82(W| z|0rUldxChhR7#xuX54?N2^_JZ{YAr-g^hEng2*FRG`TjvLNal643S*-vW@hUdm= zolmJ&5UviPDzwy#hBWL1s=+5EZVl`ndOQ2_e+y9Vq%K2-rqp8`ihh`+-pa{M+WQ}C z2PrUz3iBvwk%TI&8(YIXM2xMWkZ`Hl#fYS>4xGzvMYXB65Nw3+*F<5wda{|7>1*}6 zA>bM_#0#Ys+QhX~X=I6PfRRf9qP zMIBm1TUnWIE3=tjRoI^@Id{2bs~}@(un!@y(SV)|_n80AcvB{gYFqX(0X($gX4eoB zUCL$9@q4MPkH5_q9Cw3c`uz)axu6%~1PP8d2{2(#!mQlSe)XRaDhxAE-X%$B+)t8~ zZ0|FXQg|;`BuOYfS(x$qJgwSA*Y^KO)W8%$_IuT(V zi3;Pki)v)mfMLPUBH7|+7~3`5O{QM*J!5o|!d3b4U6b>x6lG53wIb6un{izejuxwU zbPw0DcoB7^LL@yV*a(`0Ya1}3AFiTXWN;u%*JPU>FKK-)&IVD)x6w(Bz?3ZR{KiB)6 zA5|e7%A6gr%=2C4AEDZO4mZ}?`2mHjHO*0cb7^!soQOvOr}dr=j)=%)G;Mup&!EwA zW|E_BETGzxd2fY~3*iqeObP;EISi9DwImyy-6)&3;s4VBm#QtijsA5~Qid^VF{;ob z>VcGsw6jjn_K(Vo8B=A;&2J=_+D=@qN zws){dxJ@(mb9NzGmCUv&;jM5Xwy--G8K2D%Z%9;8;Y3Py7L@p>zYe0(0oQ=_w^oWzC)Lcx?^?EQ`7rABUJWQz6N z#g8m;Ku$amSiC-bETZTe&xRaX602hV&C9~?L_jzXJLLLGbrP5-#?DsGK6wPBPR z4u}GLXMfB9J|>I_M^es0V)>)D@z#I-v=i=286yNKL3`XF2}&t>E|Dc|sse^53xv8ZkVn5hrxw2E;mV)~h2L-g^I|dkgpHkwg4iFmMs*K#sAiJT*W9+h z!bL$rJYyZ$#t4HD1NjU(JhM-zW{IegyT@#dlK$1xTJ|u|OD&#u3z*T;jWxqp_ElTC8{nwIg z-iV>xyyV;^alc3?CV#ZlXtwJ+Cg9-3w~qXbBo!~9N+N!3KNNlEYRqD?3 zrM0$bTJ0Hs*X*3C!OHFTev0qeRiUQua@6tDZF2`S@1G?p-fGJH0>OW5ZEtU{0m1sw z3uooU)m5wAy*>YYheQgdcFiV%*D75qFy)Dt%iO&KZHu`%wQ85wAxUazT3TSIBjl;A?Y&R{&J zR>k+Y{ZYBVeYmNI6FoLz|Mzn1v-8GGc8HUc?xf)7b5v)$>FdPVlivkl3KzZ(u-x`w z&JUPpiQv@s%3zt2T{d4EPTEcM{<=l0r@j;+MmSGG*%cwAvzr{LX{y#OG~=P|El)+_ zaqFddo<;GmJn>MWn%JPi6^T*`pG-!SYjbJx|0n+J*|ToDXo(0URcDnTc(3P*zx;dX zdEUA2?lH6fnJgD=W%aX0ad9(72c9$%`(0m;zVwGv60+Rik=6ThetD3m`e&q?{HJ6q zx|BOmh^Bmd3-=a58V^Yd2!l~;81X*^a$SLcHx7wi&>N$}+*_-=X8{&GnJ)hM=Lg@z zup!OKhr6W-Jmu$yKR;b+%i|uEpZRGslNLVp-3xw?g^XT|u7t zl%(4S`q_-hmp4?wpXYZ67#P11tmk0`yA%%aNg9uek}Mp_Sn)h1X!k<;Z%`DLj*P=db=ZpdOLAm8Y8qMxufu?#sEm2ToO;;CeHHGW^J#ZtQmMojI=g zpS6`P1L{Rm4C&Gm6pr8I@=UC|6L2&_QMZ#ERGS*rIC@k=Rop>leWi=?%f?_PP8QXZ zSE?}Ak{sQqW0R92Umt69(RqxoZ?xs^yjn%~sSy!Y#RSHyYg<7HV{ztDaQ(fQx!=RH z2>M`eQV$Vhc$v?(VH4Nz0ZY-v6bI9^Hv+*|@?FCL);rYy${f|UDu>{)<)tV!XsHl* z<8Mq7_s&PZ2`-E{JTdIArK7{ zFTLk*`LMxAP_f1|ac0KQbN4}!o6X!Z#xk53GugAWWZnqtMX;I3ln~TIQ99|}<{dna z#7%Ke#VRU)nvMCZh!Z%H#PbWdvuvXIwGiXiry(=0OJ9oE@?+}dY^TC0CUL2K#r+U% zOLJO=^XNvNZ;*#e-@k|Df%#8DtC77;GlKSRW)ac?M5T|O@U8AEft)C%27|yjF!|Jq*@MGI)DP|m&%ScZX8KtVf9lR5LH~3?BcQ+9Y zBN>MD=K1!wd{HYHc@^sFQm)L9)BTbbeL_LLc=ida?dKfWmngxC++{G6VmIEa^hgep z+*E5GA&WxT*DHQKWef2r{OetK^n zWh(3vRSL_?7o#3}ce1~{Y0@nxK3BaL91{|wV1dNATg`s=aQkoTy=CbfA~b)`^kT6G zD0FrGjKm%@s|=OweZ|WD*;L>rFIm5OcCu*+4e2H-Ty08wiNLSv(tKXN_=+!0mew^2 zDo@{1;yd(#Km@ZY?#T_(g#C*wo~|B?Ma3F=t=`W0t2`>1v+dK)FdEwffvoCjz{(B^ z&XfTj+P*G0$rT35BC+VxL+=9|P%#%IzqGx|m-(lAKW@iF6B`Eu@KPd!l;jE-$i<737704)F0);c@-!4Ri`=9W3`JR~B_E6*x$2e{CAcx+CG#HA*iQ_B1Nrtch*WwecRZuUPEH^ z44J{8(C$?G-U9@B0|B!S@Hj{K?}^O|e)q4&?N3t0_2vea-}>SLee~l~W#LGCnkO3J zB?m+ny{}neGB{=s%ba~0p~8_U5X_S!5{?5@278y5viZS6Dl)_w{&Qp_;m?nM5eE|4 z>H_6H*powG09^ULe1i>=6~)6Y$U&Q}8o6-llvzfTx09F)rr)n4p8-ojq(h{d$Kj7EI( zI9Hi#Tb$mILq4vn)YU3~;Pnw5xpLp^?dQK<0x0UQ%gYw+B$kBi3=M@oW3lK@T^H$f;SzWlfj**4Kut?w~i@jrt^nqA|i=FWv1r6Itgk`jBKnY8r%v<1XdU`9E z*xX;7fY!D@-u?Q1Nk+$8l;Na{)+li_fli1ZF*vAtHm*ghe@iaL^GAC~%$NVHtggRI z8RnYIl@^c6%i&}1g(=dXM>X(XDD4vhkw1Gq_p8Kx8ONU?r&AiE_?<3v?*;}tTc4zg z;U5NEvT$;rTDSeadQ6w?>|d>*8kscVaix%`^8Gn?VhJtJ$I}P8_7y>zzgxPyzjwst zb*<0WSbQFLloi_C@oeW5o++~JAaXg9dHi@cceCnz z>)ZZ&l{dDNc&kIC*cbY&7F^Xu2hAV#r~()Qm)ix}tv9b4kL*(b1lywEG$vrJXTfhFkdNy5LY2F*rK}ibQ-&@GiDB2gOv+< z@A2p_0wzo$gZj5uTxrzPg76L|8>x8x6CdB<0@W4Ri(#p4KKQtLvatZiu_2aa;R(Lw z#}{X=L3M5syg9XJUEG0|shYyxM5TJ4=c-I>&L36m=oU@9IQ*epXUf9qbQLeQ!11%= zpv&!}0t2C$?Z|pzSZY{@he#D4&9gNf@y)CE->MEKH;Z{++6^yeUF$5kkIAxotYeX{ z|AbnX-n?XPS9D)zdD9GqggjW%;wc}HqT&o4iw>8-jDBhAWOF{6^Og^}@M^no>znG% z!nZo_Z1mOPEmMUp2SK?p+FZlDWd~DFcY;rutNv=~>FMzb1YYsSp+)GfdH9J31xiGC zg;cZeFG=z&IU8BoG#4)*izXyV;uUNbW-YHP(dzb-3nMPHbF;34#V@R@PNJ)sIawvCGDFD(5AXRF2W&@5ON5^TeYe6MV)Ak<#Q-mBMc= zlv3Yu6nKQBQLtpk(oo1fMBt#!Z#;C$tyF#H&NaEd61jhDb;VRuvDMPuQ6Q;9s0b{viDADYD1U(Z5rUl~pC$zp&@JD`aOT0T{N3PhesU5sgHWx==> zh#1j*-5$fiT>3D-Adx>m7t*>r_}^Up@?w>9B3i}+=Q`Qc#c2*US6ucRthg@Nr{k@HEG zx$tP|iH~Yno~E$eF^|DoJWQ~nGlG8!Ko zqzVWR1lj3tDN)Wohb$56{fu;mMXIHiTl+jQDlzT-03~2UX}t?!y#QBMFYVpG6r{6% zBm!^lkX$R&;&ProaJ>!W+4<$fZ$T{n+P@Zc?Buv5Vqzt>+@`v2odIL?#d!x903R@| zCEhf&vbxiMhLpH5QhXcB8Qn@(gNY2B^MTWnAUaeysY<^c)gn`~nYHh+F~1*d)Q-)< zRkvR-|Ita+46Qb$(NpPi0U6^vl=utYYRV7T%&8RQo9WRwPCARfei}vd@|g z#OGGM^gsHJxV>2m8t~Mo0K2Y`962~5^%~g0rxyGwK3Z`=PeDrOD|gG_8PfD2aeazv_wwf8dM;j1c^YdBEk5WEW2< zTu(t%jxMItc?%fGc6Tkby1HBDCJh2fjejrXtD1c-9jrJ169qc5O-q6}#Zb-$=C6{q zCSOIJG3}m?_~BzW`!t<%vv~_TJ{3TfA%W?%Z5x?~CICu+Wf#r;kU5+kJC+qn?=^mCwL*qNgzl^KY9bP@*VpVVC@3&o@-5}C+xau4 zOY*_RwWWPo{|?Vg$4xhLaGBGNJWl_8q{zZMjAdbI1Ij<{%S9!(nY*+5eWz-sbb5$+Lu#9 zx(21w*QCwIs%qY=TsU^jMAAr4!bQ&7$uE$!;piV z%1=c+Uf5GfAZkSfC`4tjB?G<1eV_Slnm;(}PX+Jb?wvj`Z>n7L|8+a*Ch@JX($d?E zOUH^pj-ctfE`D!vG23lw<0>2f$yd29bXx5m&;sMLVrf|!AN`i#t3R%o+&FLhN>zL7^4OG<27+#7nVZ}=DP#5P#X{g%q;jMA z)=LHkBF|;J)(Xa_n!nRUv0dG4bR-2Eih?i}R0FFt{S&VK-Q{`Yv{a&@T(DYgU|U&p z4_|CUQj$gYyUypTux_ly#;tc~s1?%kdBvHQ=2>S^J+#_OEG(2Y%Cx63c|M9&&WF)i zUs_(?svUO;_uHv8{@B-cP}7gx++6;^4^~%6nrzTKpJ&gKKKp}wRJIu0#t>qk7S8Pym$w4^eu^o2C7gkZ8Yo{N&K34ZTS$Yevfu$U<6M$S| zoMti!LAGChFsDd_Fd*Dwe(0vrlAmcqF@I20TJ((S z2bDs*0^TeRh>HyZhAdu)zQvhd<19cxKd%4O)%hE6e2xR6q6DiA4CaUks)u%9aX5fp zKF0PDZ5oa@!;Dhae1GUke(&Gr9sxX1aycBDjQGjXf@5eTKaf?bB1ljTgs);0U^Uu) zLJ{(8Z?$9^ky;w%c_w^;HCLd2907;+_noMz@}xSZ(I~U6J~u{9TBzOw6%VIZ+y{() zH`2KKSM3La5u5C<++mr%P~(O}`d3&W$Xg8P=bJ(yP-{ERFpmM*=68qCmMB->{ojq zT#k#Zj(`St^>y6@f(u<2GAwYQ(6)!--dckE&fb=0};{}TKquoe|$s$ zvy1;R_WM7I4@ze=Ewq$RVd9tp1EIEuubd|f3|02&^2+dV_wj-CBmb-F8|5Fp6}nqL zuZYLDcZ8$5t-EiIM-9Y>M+y}=0b2lg1k>mC5fbuT4pzyw(u#^Ux1?W}*hC6<;&O6w z6882y)&MFhq(F4k*Z@%Ai$%-6@=7jIuIp+bGoMV46M=+w$T2Ql(j%95vV0nkPyRZ$xQ03OVlJmpkf|i09bq-j6NfJqWzZ*^5Y`+ zKL7ypBjb$z{tGq!#~W1tW8)ow-M%rEUK0hLOnp+%Dc3agkdO1G%k}AH|jDhgZ~F9d5B+K<~P`8I;nN{Qdu2uLk z#!zE@88IAuYwz&^AOk3q)n+Lcwb3qfPC42*W=dDjk8oRo zNx3+vD8MgOKN+*r|DiPs2EZRj@PJP#*!ybG3mP&ik}zd)z#ba;bR50^-EpA$E{g1) zMg#*!UGXv%mpvtb*)dGjBZvq%nE;!(OY^Gsp$~)r5EeUA0Jyi_?51BA&~_>q4+UH7 zv*WyLKy-c+dda~80&T`2@4r4-*v`bo!B7-D|6oiMow(L)7E5>%2*?c-xt?ctzs%HT zVuMW6P|NX!4S<1K_}4{69d;Qc diff --git a/nanostack/ws_bbr_api.h b/nanostack/ws_bbr_api.h index df40279109..9182ea74fd 100644 --- a/nanostack/ws_bbr_api.h +++ b/nanostack/ws_bbr_api.h @@ -40,6 +40,8 @@ typedef struct bbr_information { uint8_t dodag_id[16]; /** Address prefix given to devices in network set to 0 if not available*/ uint8_t prefix[8]; + /** Address IID of the border router set to 0 if not available*/ + uint8_t IID[8]; /** Amount of devices in the network. */ uint16_t devices_in_network; /** Border router instance identifier defined in RPL */ diff --git a/nanostack/ws_management_api.h b/nanostack/ws_management_api.h index 99092ba5f5..37e66999ab 100644 --- a/nanostack/ws_management_api.h +++ b/nanostack/ws_management_api.h @@ -75,10 +75,16 @@ extern "C" { #define CHANNEL_SPACING_100 0x03 // 100 khz #define CHANNEL_SPACING_250 0x04 // 250 khz -#define NETWORK_SIZE_CERTIFICATE 0x00 -#define NETWORK_SIZE_SMALL 0x01 -#define NETWORK_SIZE_MEDIUM 0x08 -#define NETWORK_SIZE_LARGE 0x10 +/* + * Network Size definitions are device amount in hundreds of devices. + * These definitions are meant to give some estimates of sizes. Any value can be given as parameter + */ + +#define NETWORK_SIZE_CERTIFICATE 0x00 // Network configuration used in Wi-SUN certification +#define NETWORK_SIZE_SMALL 0x01 // Small networks +#define NETWORK_SIZE_MEDIUM 0x08 // 100 - 800 device networks are medium sized +#define NETWORK_SIZE_LARGE 0x0F // 800 - 1500 device networks are large +#define NETWORK_SIZE_XLARGE 0x19 // 2500+ devices #define NETWORK_SIZE_AUTOMATIC 0xFF /** Temporary API change flag. this will be removed when new version of API is implemented on applications @@ -229,9 +235,9 @@ int ws_management_regulatory_domain_validate( * * timing parameters follows the specification example from Wi-SUN specification * - * Default value: medium - * small network size: hundreds of devices - * Large network size: thousands of devices + * Default value: medium 100 - 800 device + * small network size: less than 100 devices + * Large network size: 800 - 1500 devices * automatic: when discovering the network network size is learned * from advertisements and timings adjusted accordingly * diff --git a/source/6LoWPAN/Bootstraps/Generic/protocol_6lowpan_bootstrap.c b/source/6LoWPAN/Bootstraps/Generic/protocol_6lowpan_bootstrap.c index cbe3e12c67..0a21788cc2 100644 --- a/source/6LoWPAN/Bootstraps/Generic/protocol_6lowpan_bootstrap.c +++ b/source/6LoWPAN/Bootstraps/Generic/protocol_6lowpan_bootstrap.c @@ -588,7 +588,7 @@ static void mle_neigh_entry_update_by_mle_tlv_list(int8_t interface_id, mac_neig uint8_t link_idr; uint8_t iop_flags; if (mle_link_quality_tlv_parse(mac64, short_address, mle_tlv_info.dataPtr, mle_tlv_info.tlvLen, &iop_flags, &link_idr)) { - etx_remote_incoming_idr_update(interface_id, link_idr, entry_temp->index); + etx_remote_incoming_idr_update(interface_id, link_idr, entry_temp->index, entry_temp->mac64); if ((iop_flags & MLE_NEIGHBOR_PRIORITY_LINK) == MLE_NEIGHBOR_PRIORITY_LINK) { entry_temp->link_role = CHILD_NEIGHBOUR; @@ -965,9 +965,9 @@ int protocol_6lowpan_router_synch_to_new_router(protocol_interface_info_entry_t static uint8_t mle_calculate_idr(int8_t interface_id, mle_message_t *mle_msg, mac_neighbor_table_entry_t *entry_temp) { if (!entry_temp) { - return etx_lqi_dbm_update(-2, mle_msg->lqi, mle_msg->dbm, 0) >> 3; + return etx_lqi_dbm_update(-2, mle_msg->lqi, mle_msg->dbm, 0, NULL) >> 3; } - return etx_lqi_dbm_update(interface_id, mle_msg->lqi, mle_msg->dbm, entry_temp->index) >> 3; + return etx_lqi_dbm_update(interface_id, mle_msg->lqi, mle_msg->dbm, entry_temp->index, entry_temp->mac64) >> 3; } @@ -1609,7 +1609,7 @@ static void lowpan_neighbor_entry_remove_notify(mac_neighbor_table_entry_t *entr } mac_helper_devicetable_remove(cur_interface->mac_api, entry_ptr->index, entry_ptr->mac64); //Removes ETX neighbor - etx_neighbor_remove(cur_interface->id, entry_ptr->index); + etx_neighbor_remove(cur_interface->id, entry_ptr->index, entry_ptr->mac64); //Remove MLE frame counter info mle_service_frame_counter_entry_delete(cur_interface->id, entry_ptr->index); diff --git a/source/6LoWPAN/Thread/thread_bootstrap.c b/source/6LoWPAN/Thread/thread_bootstrap.c index 07e231c864..1d0537d343 100644 --- a/source/6LoWPAN/Thread/thread_bootstrap.c +++ b/source/6LoWPAN/Thread/thread_bootstrap.c @@ -141,7 +141,7 @@ static void thread_neighbor_remove(mac_neighbor_table_entry_t *entry_ptr, void * thread_reset_neighbour_info(cur, entry_ptr); //Removes ETX neighbor - etx_neighbor_remove(cur->id, entry_ptr->index); + etx_neighbor_remove(cur->id, entry_ptr->index, entry_ptr->mac64); //Remove MLE frame counter info mle_service_frame_counter_entry_delete(cur->id, entry_ptr->index); } diff --git a/source/6LoWPAN/adaptation_interface.c b/source/6LoWPAN/adaptation_interface.c index 99636719d9..87d6657735 100644 --- a/source/6LoWPAN/adaptation_interface.c +++ b/source/6LoWPAN/adaptation_interface.c @@ -155,7 +155,7 @@ static void lowpan_adaptation_etx_update_cb(protocol_interface_info_entry_t *cur // Gets table entry mac_neighbor_table_entry_t *neigh_table_ptr = mac_neighbor_table_address_discover(mac_neighbor_info(cur), buf->dst_sa.address + PAN_ID_LEN, buf->dst_sa.addr_type); if (neigh_table_ptr) { - etx_transm_attempts_update(cur->id, 1 + confirm->tx_retries, success, neigh_table_ptr->index); + etx_transm_attempts_update(cur->id, 1 + confirm->tx_retries, success, neigh_table_ptr->index, neigh_table_ptr->mac64); // Updates ETX statistics etx_storage_t *etx_entry = etx_storage_entry_get(cur->id, neigh_table_ptr->index); if (etx_entry) { diff --git a/source/6LoWPAN/ws/ws_bbr_api.c b/source/6LoWPAN/ws/ws_bbr_api.c index c0a1d00163..f841be8144 100644 --- a/source/6LoWPAN/ws/ws_bbr_api.c +++ b/source/6LoWPAN/ws/ws_bbr_api.c @@ -20,6 +20,7 @@ #include "ns_types.h" #include "ns_trace.h" #include "net_interface.h" +#include "socket_api.h" #include "eventOS_event.h" #include "NWK_INTERFACE/Include/protocol.h" #include "6LoWPAN/Bootstraps/protocol_6lowpan.h" @@ -94,7 +95,16 @@ static void ws_bbr_rpl_version_timer_start(protocol_interface_info_entry_t *cur, //stable version for RPL so slow timer update is ok cur->ws_info->rpl_version_timer = RPL_VERSION_LIFETIME; } else { - cur->ws_info->rpl_version_timer = RPL_VERSION_LIFETIME_RESTART; + if (cur->ws_info->cfg->gen.network_size <= NETWORK_SIZE_SMALL) { + // handles also NETWORK_SIZE_CERTIFICATE + cur->ws_info->rpl_version_timer = RPL_VERSION_LIFETIME_RESTART_SMALL; + } else if (cur->ws_info->cfg->gen.network_size <= NETWORK_SIZE_MEDIUM) { + cur->ws_info->rpl_version_timer = RPL_VERSION_LIFETIME_RESTART_MEDIUM; + } else if (cur->ws_info->cfg->gen.network_size <= NETWORK_SIZE_LARGE) { + cur->ws_info->rpl_version_timer = RPL_VERSION_LIFETIME_RESTART_LARGE; + } else { + cur->ws_info->rpl_version_timer = RPL_VERSION_LIFETIME_RESTART_EXTRA_LARGE; + } } } @@ -232,7 +242,10 @@ static if_address_entry_t *ws_bbr_slaac_generate(protocol_interface_info_entry_t static void ws_bbr_slaac_remove(protocol_interface_info_entry_t *cur, uint8_t *ula_prefix) { - icmpv6_slaac_prefix_update(cur, ula_prefix, 64, 0, 0); + if (cur) { + icmpv6_slaac_prefix_update(cur, ula_prefix, 64, 0, 0); + } + addr_policy_table_delete_entry(ula_prefix, 64); } @@ -361,6 +374,9 @@ static void ws_bbr_dhcp_server_start(protocol_interface_info_entry_t *cur, uint8 } static void ws_bbr_dhcp_server_stop(protocol_interface_info_entry_t *cur, uint8_t *global_id) { + if (!cur) { + return; + } uint8_t temp_address[16]; memcpy(temp_address, global_id, 8); memset(temp_address + 8, 0, 8); @@ -368,7 +384,6 @@ static void ws_bbr_dhcp_server_stop(protocol_interface_info_entry_t *cur, uint8_ DHCPv6_server_service_delete(cur->id, global_id, false); //Delete Client dhcp_client_global_address_delete(cur->id, NULL, temp_address); - } static void ws_bbr_routing_stop(protocol_interface_info_entry_t *cur) @@ -632,6 +647,11 @@ uint16_t test_pan_size_override = 0xffff; uint16_t ws_bbr_pan_size(protocol_interface_info_entry_t *cur) { uint16_t result = 0; + + if (!cur || !cur->rpl_domain) { + return 0; + } + if (test_pan_size_override != 0xffff) { return test_pan_size_override; } @@ -710,7 +730,6 @@ void ws_bbr_stop(int8_t interface_id) protocol_interface_info_entry_t *cur = protocol_stack_interface_info_get_by_id(interface_id); ws_bbr_routing_stop(cur); - backbone_interface_id = -1; current_instance_id++; @@ -764,6 +783,13 @@ int ws_bbr_info_get(int8_t interface_id, bbr_information_t *info_ptr) memcpy(info_ptr->dodag_id, current_dodag_id, 16); memcpy(info_ptr->prefix, current_global_prefix, 8); + // Get the Wi-SUN interface generated address that is used in the RF interface. + const uint8_t *wisun_if_addr = addr_select_with_prefix(cur, current_global_prefix, 64, SOCKET_IPV6_PREFER_SRC_PUBLIC); + + if (wisun_if_addr) { + memcpy(info_ptr->IID, wisun_if_addr + 8, 8); + } + info_ptr->devices_in_network = ws_bbr_pan_size(cur); info_ptr->instance_id = current_instance_id; info_ptr->version = dodag_info.version_num; diff --git a/source/6LoWPAN/ws/ws_bootstrap.c b/source/6LoWPAN/ws/ws_bootstrap.c index e40ed39b88..0d02498a5d 100644 --- a/source/6LoWPAN/ws/ws_bootstrap.c +++ b/source/6LoWPAN/ws/ws_bootstrap.c @@ -97,13 +97,14 @@ static void ws_bootstrap_nw_frame_counter_set(protocol_interface_info_entry_t *c static void ws_bootstrap_nw_frame_counter_read(protocol_interface_info_entry_t *cur, uint32_t *counter, uint8_t slot); static void ws_bootstrap_nw_info_updated(protocol_interface_info_entry_t *interface_ptr, uint16_t pan_id, char *network_name); static void ws_bootstrap_authentication_completed(protocol_interface_info_entry_t *cur, auth_result_e result, uint8_t *target_eui_64); +static const uint8_t *ws_bootstrap_authentication_next_target(protocol_interface_info_entry_t *cur, const uint8_t *previous_eui_64, uint16_t *pan_id); static void ws_bootstrap_pan_version_increment(protocol_interface_info_entry_t *cur); static ws_nud_table_entry_t *ws_nud_entry_discover(protocol_interface_info_entry_t *cur, void *neighbor); static void ws_nud_entry_remove(protocol_interface_info_entry_t *cur, mac_neighbor_table_entry_t *entry_ptr); static bool ws_neighbor_entry_nud_notify(mac_neighbor_table_entry_t *entry_ptr, void *user_data); static void ws_address_registration_update(protocol_interface_info_entry_t *interface, const uint8_t addr[16]); - +static int8_t ws_bootstrap_neighbor_set(protocol_interface_info_entry_t *cur, parent_info_t *parent_ptr, bool clear_list); static void ws_bootstrap_candidate_table_reset(protocol_interface_info_entry_t *cur); static parent_info_t *ws_bootstrap_candidate_parent_get(struct protocol_interface_info_entry *cur, const uint8_t *addr, bool create); @@ -147,7 +148,7 @@ mac_neighbor_table_entry_t *ws_bootstrap_mac_neighbor_add(struct protocol_interf static void ws_bootstrap_neighbor_delete(struct protocol_interface_info_entry *interface, mac_neighbor_table_entry_t *entry_ptr) { mac_helper_devicetable_remove(interface->mac_api, entry_ptr->index, entry_ptr->mac64); - etx_neighbor_remove(interface->id, entry_ptr->index); + etx_neighbor_remove(interface->id, entry_ptr->index, entry_ptr->mac64); ws_neighbor_class_entry_remove(&interface->ws_info->neighbor_storage, entry_ptr->index); } @@ -168,7 +169,6 @@ static void ws_bootstap_eapol_neigh_entry_allocate(struct protocol_interface_inf return; } interface->ws_info->eapol_tx_index = mac_entry->index; - tr_debug("Allocated Eapol Index TX %u", interface->ws_info->eapol_tx_index); } void ws_bootstrap_eapol_rx_temporary_set(struct protocol_interface_info_entry *interface, const uint8_t *src64) @@ -188,8 +188,6 @@ ws_neighbor_class_entry_t *ws_bootstrap_eapol_tx_temporary_set(struct protocol_i } memcpy(mac_entry->mac64, src64, 8); - - tr_debug("EAPOL Temporary TX neighbor %s : index:%u", trace_array(src64, 8), interface->ws_info->eapol_tx_index); mac_helper_device_description_write(interface, &device_desc, src64, 0xffff, 0, false); mac_helper_devicetable_direct_set(interface->mac_api, &device_desc, interface->ws_info->eapol_tx_index); return ws_neighbor_class_entry_get(&interface->ws_info->neighbor_storage, mac_entry->index); @@ -204,7 +202,6 @@ void ws_bootstrap_eapol_tx_temporary_clear(struct protocol_interface_info_entry memset(mac_entry->mac64, 0xff, 8); mac_helper_devicetable_remove(interface->mac_api, interface->ws_info->eapol_tx_index, NULL); - tr_debug("Clear EAPOL-Temporary"); } static void ws_bootstrap_neighbor_list_clean(struct protocol_interface_info_entry *interface) @@ -545,8 +542,8 @@ static uint8_t ws_generate_exluded_channel_list_from_active_channels(ws_excluded static void ws_fhss_configure_channel_masks(protocol_interface_info_entry_t *cur, fhss_ws_configuration_t *fhss_configuration) { - ws_generate_channel_list(fhss_configuration->channel_mask, cur->ws_info->hopping_schdule.number_of_channels, cur->ws_info->hopping_schdule.regulatory_domain); - ws_generate_channel_list(fhss_configuration->unicast_channel_mask, cur->ws_info->hopping_schdule.number_of_channels, cur->ws_info->hopping_schdule.regulatory_domain); + ws_generate_channel_list(fhss_configuration->channel_mask, cur->ws_info->hopping_schdule.number_of_channels, cur->ws_info->hopping_schdule.regulatory_domain, cur->ws_info->hopping_schdule.operating_class); + ws_generate_channel_list(fhss_configuration->unicast_channel_mask, cur->ws_info->hopping_schdule.number_of_channels, cur->ws_info->hopping_schdule.regulatory_domain, cur->ws_info->hopping_schdule.operating_class); // using bitwise AND operation for user set channel mask to remove channels not allowed in this device for (uint8_t n = 0; n < 8; n++) { fhss_configuration->unicast_channel_mask[n] &= cur->ws_info->cfg->fhss.fhss_channel_mask[n]; @@ -1129,7 +1126,7 @@ static parent_info_t *ws_bootstrap_candidate_parent_allocate(protocol_interface_ return entry; } -static void ws_bootstrap_candidate_parent_free(protocol_interface_info_entry_t *cur, uint8_t *addr) +static void ws_bootstrap_candidate_parent_free(protocol_interface_info_entry_t *cur, const uint8_t *addr) { ns_list_foreach_safe(parent_info_t, entry, &cur->ws_info->parent_list_reserved) { if (memcmp(entry->addr, addr, 8) == 0) { @@ -1346,14 +1343,15 @@ static void ws_bootstrap_pan_advertisement_solicit_analyse(struct protocol_inter * a PAN Advertisement Solicit with NETNAME-IE / Network Name matching that configured on the receiving node. */ trickle_consistent_heard(&cur->ws_info->trickle_pan_advertisement_solicit); - /* * Optimized PAN discovery to select faster the parent if we hear solicit from someone else */ - if (ws_bootstrap_state_discovery(cur) && - cur->bootsrap_state_machine_cnt > cur->ws_info->trickle_params_pan_discovery.Imin + 50) { - cur->bootsrap_state_machine_cnt = cur->ws_info->trickle_params_pan_discovery.Imin + randLIB_get_8bit() % 50; + if (ws_bootstrap_state_discovery(cur) && cur->ws_info->cfg->gen.network_size <= NETWORK_SIZE_MEDIUM && + cur->bootsrap_state_machine_cnt > cur->ws_info->trickle_params_pan_discovery.Imin * 2) { + + cur->bootsrap_state_machine_cnt = cur->ws_info->trickle_params_pan_discovery.Imin + randLIB_get_random_in_range(0, cur->ws_info->trickle_params_pan_discovery.Imin); + tr_info("Making parent selection in %u s", (cur->bootsrap_state_machine_cnt / 10)); } } @@ -1423,7 +1421,7 @@ static void ws_bootstrap_pan_config_analyse(struct protocol_interface_info_entry } if (neighbour_pointer_valid) { - etx_lqi_dbm_update(cur->id, data->mpduLinkQuality, data->signal_dbm, neighbor_info.neighbor->index); + etx_lqi_dbm_update(cur->id, data->mpduLinkQuality, data->signal_dbm, neighbor_info.neighbor->index, neighbor_info.neighbor->mac64); //Update Neighbor Broadcast and Unicast Parameters ws_neighbor_class_neighbor_unicast_time_info_update(neighbor_info.ws_neighbor, ws_utt, data->timestamp); ws_neighbor_class_neighbor_unicast_schedule_set(neighbor_info.ws_neighbor, ws_us); @@ -1508,7 +1506,7 @@ static void ws_bootstrap_pan_config_solicit_analyse(struct protocol_interface_in llc_neighbour_req_t neighbor_info; if (ws_bootstrap_neighbor_info_request(cur, data->SrcAddr, &neighbor_info, false)) { - etx_lqi_dbm_update(cur->id, data->mpduLinkQuality, data->signal_dbm, neighbor_info.neighbor->index); + etx_lqi_dbm_update(cur->id, data->mpduLinkQuality, data->signal_dbm, neighbor_info.neighbor->index, neighbor_info.neighbor->mac64); ws_neighbor_class_neighbor_unicast_time_info_update(neighbor_info.ws_neighbor, ws_utt, data->timestamp); ws_neighbor_class_neighbor_unicast_schedule_set(neighbor_info.ws_neighbor, ws_us); } @@ -1823,7 +1821,7 @@ static bool ws_neighbor_entry_nud_notify(mac_neighbor_table_entry_t *entry_ptr, return false; } - if (!rpl_control_is_dodag_parent_candidate(cur, ll_address, WS_NEIGHBOUR_MAX_CANDIDATE_PROBE)) { + if (!rpl_control_is_dodag_parent_candidate(cur, ll_address, cur->ws_info->cfg->gen.rpl_parent_candidate_max)) { //NUD Not needed for if neighbour is not parent candidate return false; } @@ -1986,7 +1984,7 @@ int ws_bootstrap_init(int8_t interface_id, net_6lowpan_mode_e bootstrap_mode) ret_val = -4; goto init_fail; } - if (ws_pae_controller_cb_register(cur, &ws_bootstrap_authentication_completed, &ws_bootstrap_nw_key_set, &ws_bootstrap_nw_key_clear, &ws_bootstrap_nw_key_index_set, &ws_bootstrap_nw_frame_counter_set, &ws_bootstrap_nw_frame_counter_read, &ws_bootstrap_pan_version_increment, &ws_bootstrap_nw_info_updated) < 0) { + if (ws_pae_controller_cb_register(cur, &ws_bootstrap_authentication_completed, &ws_bootstrap_authentication_next_target, &ws_bootstrap_nw_key_set, &ws_bootstrap_nw_key_clear, &ws_bootstrap_nw_key_index_set, &ws_bootstrap_nw_frame_counter_set, &ws_bootstrap_nw_frame_counter_read, &ws_bootstrap_pan_version_increment, &ws_bootstrap_nw_info_updated) < 0) { ret_val = -4; goto init_fail; } @@ -2278,8 +2276,8 @@ static void ws_bootstrap_rpl_callback(rpl_event_t event, void *handle) ws_eapol_relay_start(cur, EAPOL_RELAY_SOCKET_PORT, dodag_info.dodag_id, EAPOL_RELAY_SOCKET_PORT); // Set network information to PAE ws_pae_controller_nw_info_set(cur, cur->ws_info->network_pan_id, cur->ws_info->cfg->gen.network_name); - // Network key is valid - ws_pae_controller_nw_key_valid(cur); + // Network key is valid, indicate border router IID to controller + ws_pae_controller_nw_key_valid(cur, &dodag_info.dodag_id[8]); // After successful DAO ACK connection to border router is verified cur->ws_info->pan_timeout_timer = cur->ws_info->cfg->timing.pan_timeout; @@ -2381,19 +2379,21 @@ static void ws_rpl_prefix_callback(prefix_entry_t *prefix, void *handle, uint8_t static bool ws_rpl_candidate_soft_filtering(protocol_interface_info_entry_t *cur, struct rpl_instance *instance) { - //If bootstrap active we not need any candidate filtering - if ((cur->lowpan_info & INTERFACE_NWK_BOOTSRAP_ACTIVE) && (ws_info(cur)->cfg->gen.network_size == NETWORK_SIZE_CERTIFICATE)) { - return true; - } - //Already many candidates - if (rpl_control_candidate_list_size(cur, instance) > cur->ws_info->cfg->gen.rpl_parent_candidate_max) { + uint16_t candidate_list_size = rpl_control_candidate_list_size(cur, instance); + if (candidate_list_size >= cur->ws_info->cfg->gen.rpl_parent_candidate_max) { return false; } + uint16_t selected_parents = rpl_control_selected_parent_count(cur, instance); + //Already enough selected candidates - if (rpl_control_selected_parent_count(cur, instance) >= cur->ws_info->cfg->gen.rpl_selected_parent_max) { - return false; + if (selected_parents >= cur->ws_info->cfg->gen.rpl_selected_parent_max) { + candidate_list_size -= selected_parents; + if (candidate_list_size >= 2) { + //We have more candidates than selected + return false; + } } return true; @@ -2427,6 +2427,19 @@ static bool ws_rpl_new_parent_callback(uint8_t *ll_parent_address, void *handle, ws_neighbor_temp_class_t *entry = ws_llc_get_multicast_temp_entry(cur, mac64); if (!ws_rpl_candidate_soft_filtering(cur, instance)) { + + //Acept only better than own rank here + if (candidate_rank >= rpl_control_current_rank(instance)) { + //Do not accept no more siblings + return false; + } + + uint16_t candidate_list_size = rpl_control_candidate_list_size(cur, instance); + if (candidate_list_size > cur->ws_info->cfg->gen.rpl_parent_candidate_max + 1) { + //Accept only 1 better 1 time + return false; + } + if (!neigh_buffer.neighbor) { //Do not accept any new in that Place return false; @@ -2459,42 +2472,6 @@ static bool ws_rpl_new_parent_callback(uint8_t *ll_parent_address, void *handle, if (neigh_buffer.neighbor) { return true; } -#if 0 - if (!rpl_control_find_worst_neighbor(cur, instance, replacing)) { - return false; - } - - // +2 Is for PAN ID space - memcpy(mac64 + 2, replacing + 8, 8); - mac64[2] ^= 2; - - if (ws_etx_read(cur, ADDR_802_15_4_LONG, mac64) == 0xffff) { - //Not proped yet because ETX is 0xffff - return false; - } - - uint16_t etx = 0; - if (neigh_buffer.neighbor) { - etx = etx_local_etx_read(cur->id, neigh_buffer.neighbor->index); - } - - // Accept now only better one's when max candidates selected and max candidate list size is reached - if (!rpl_possible_better_candidate(cur, instance, replacing, candidate_rank, etx)) { - return false; - } - //TODO if replacing has poor ETX, put it in blacklist as "poor ETX" to prevent reselection - //Mark That We can try remove replaced link - replace_ok = true; - -neigh_create: - - - if (neigh_buffer.neighbor) { - //Use Already discovered entry - create_ok = true; - goto neigh_create_ok; - } -#endif if (!entry) { //No Multicast Entry Available @@ -2508,7 +2485,7 @@ neigh_create: //Copy fhss temporary data *ws_neigh = entry->neigh_info_list; //ETX Create here - etx_lqi_dbm_update(cur->id, entry->mpduLinkQuality, entry->signal_dbm, neigh_buffer.neighbor->index); + etx_lqi_dbm_update(cur->id, entry->mpduLinkQuality, entry->signal_dbm, neigh_buffer.neighbor->index, neigh_buffer.neighbor->mac64); mac_neighbor_table_trusted_neighbor(mac_neighbor_info(cur), neigh_buffer.neighbor, true); } ws_llc_free_multicast_temp_entry(cur, entry); @@ -2635,7 +2612,7 @@ static void ws_bootstrap_start_discovery(protocol_interface_info_entry_t *cur) } // Discovery statemachine is checkked after we have sent the Solicit - uint16_t time_to_solicit = 0; + uint32_t time_to_solicit = 0; if (cur->ws_info->trickle_pan_advertisement_solicit.t > cur->ws_info->trickle_pan_advertisement_solicit.now) { time_to_solicit = cur->ws_info->trickle_pan_advertisement_solicit.t - cur->ws_info->trickle_pan_advertisement_solicit.now; } @@ -2644,7 +2621,13 @@ static void ws_bootstrap_start_discovery(protocol_interface_info_entry_t *cur) cur->ws_info->trickle_params_pan_discovery.Imin, cur->ws_info->trickle_params_pan_discovery.Imax, cur->ws_info->trickle_params_pan_discovery.TimerExpirations, cur->ws_info->trickle_params_pan_discovery.k, cur->ws_info->trickle_pan_advertisement_solicit.I, cur->ws_info->trickle_pan_advertisement_solicit.t, cur->ws_info->trickle_pan_advertisement_solicit.now, cur->ws_info->trickle_pan_advertisement_solicit.c); - cur->bootsrap_state_machine_cnt = time_to_solicit + cur->ws_info->trickle_params_pan_discovery.Imin + randLIB_get_8bit() % 50; + time_to_solicit += cur->ws_info->trickle_params_pan_discovery.Imin + randLIB_get_random_in_range(0, cur->ws_info->trickle_params_pan_discovery.Imin); + + if (time_to_solicit > 0xffff) { + time_to_solicit = 0xffff; + } + cur->bootsrap_state_machine_cnt = time_to_solicit; + tr_info("Making parent selection in %u s", (cur->bootsrap_state_machine_cnt / 10)); } @@ -2757,6 +2740,24 @@ static void ws_bootstrap_authentication_completed(protocol_interface_info_entry_ } } +static const uint8_t *ws_bootstrap_authentication_next_target(protocol_interface_info_entry_t *cur, const uint8_t *previous_eui_64, uint16_t *pan_id) +{ + ws_bootstrap_candidate_parent_free(cur, previous_eui_64); + + // Gets best target + parent_info_t *parent_info = ws_bootstrap_candidate_parent_get_best(cur); + if (parent_info) { + /* On failure still continues with the new parent, and on next call, + will try to set the neighbor again */ + ws_bootstrap_neighbor_set(cur, parent_info, true); + *pan_id = parent_info->pan_id; + return parent_info->addr; + } + + // If no targets found, retries the last one + return previous_eui_64; +} + // Start configuration learning static void ws_bootstrap_start_configuration_learn(protocol_interface_info_entry_t *cur) { @@ -2830,7 +2831,7 @@ static void ws_set_asynch_channel_list(protocol_interface_info_entry_t *cur, asy uint16_t channel_number = cur->ws_info->cfg->fhss.fhss_uc_fixed_channel; async_req->channel_list.channel_mask[0 + (channel_number / 32)] = (1 << (channel_number % 32)); } else { - ws_generate_channel_list(async_req->channel_list.channel_mask, cur->ws_info->hopping_schdule.number_of_channels, cur->ws_info->hopping_schdule.regulatory_domain); + ws_generate_channel_list(async_req->channel_list.channel_mask, cur->ws_info->hopping_schdule.number_of_channels, cur->ws_info->hopping_schdule.regulatory_domain, cur->ws_info->hopping_schdule.operating_class); } async_req->channel_list.channel_page = CHANNEL_PAGE_10; @@ -3146,6 +3147,36 @@ static void ws_bootstrap_event_handler(arm_event_s *event) } } +static int8_t ws_bootstrap_neighbor_set(protocol_interface_info_entry_t *cur, parent_info_t *parent_ptr, bool clear_list) +{ + uint16_t pan_id = cur->ws_info->network_pan_id; + + // Add EAPOL neighbor + cur->ws_info->network_pan_id = parent_ptr->pan_id; + cur->ws_info->pan_information = parent_ptr->pan_information; + cur->ws_info->pan_information.pan_version = 0; // This is learned from actual configuration + + // If PAN ID changes, clear learned neighbors and activate FHSS + if (pan_id != cur->ws_info->network_pan_id) { + if (clear_list) { + ws_bootstrap_neighbor_list_clean(cur); + } + ws_bootstrap_fhss_activate(cur); + } + + llc_neighbour_req_t neighbor_info; + if (!ws_bootstrap_neighbor_info_request(cur, parent_ptr->addr, &neighbor_info, true)) { + //Remove Neighbour and set Link setup back + ns_list_remove(&cur->ws_info->parent_list_reserved, parent_ptr); + ns_list_add_to_end(&cur->ws_info->parent_list_free, parent_ptr); + return -1; + } + + ws_neighbor_class_neighbor_unicast_time_info_update(neighbor_info.ws_neighbor, &parent_ptr->ws_utt, parent_ptr->timestamp); + ws_neighbor_class_neighbor_unicast_schedule_set(neighbor_info.ws_neighbor, &parent_ptr->ws_us); + return 0; +} + /* * State machine * @@ -3166,29 +3197,21 @@ select_best_candidate: // randomize new channel and start MAC ws_bootstrap_fhss_activate(cur); // Next check will be after one trickle - cur->bootsrap_state_machine_cnt += cur->ws_info->trickle_params_pan_discovery.Imin + randLIB_get_8bit() % 50; + uint32_t random_start = cur->ws_info->trickle_params_pan_discovery.Imin + randLIB_get_random_in_range(0, cur->ws_info->trickle_params_pan_discovery.Imin); + if (random_start > 0xffff) { + random_start = 0xffff; + } + cur->bootsrap_state_machine_cnt = random_start; + tr_info("Making parent selection in %u s", (cur->bootsrap_state_machine_cnt / 10)); return; } tr_info("selected parent:%s panid %u", trace_array(selected_parent_ptr->addr, 8), selected_parent_ptr->pan_id); - // Add EAPOL neighbour - cur->ws_info->network_pan_id = selected_parent_ptr->pan_id; - cur->ws_info->pan_information = selected_parent_ptr->pan_information; - cur->ws_info->pan_information.pan_version = 0; // This is learned from actual configuration - - ws_bootstrap_fhss_activate(cur); - llc_neighbour_req_t neighbor_info; - if (!ws_bootstrap_neighbor_info_request(cur, selected_parent_ptr->addr, &neighbor_info, true)) { - //Remove Neighbour and set Link setup back - ns_list_remove(&cur->ws_info->parent_list_reserved, selected_parent_ptr); - ns_list_add_to_end(&cur->ws_info->parent_list_free, selected_parent_ptr); + if (ws_bootstrap_neighbor_set(cur, selected_parent_ptr, false) < 0) { goto select_best_candidate; } - ws_neighbor_class_neighbor_unicast_time_info_update(neighbor_info.ws_neighbor, &selected_parent_ptr->ws_utt, selected_parent_ptr->timestamp); - ws_neighbor_class_neighbor_unicast_schedule_set(neighbor_info.ws_neighbor, &selected_parent_ptr->ws_us); - ws_pae_controller_set_target(cur, selected_parent_ptr->pan_id, selected_parent_ptr->addr); // temporary!!! store since auth ws_bootstrap_event_authentication_start(cur); return; diff --git a/source/6LoWPAN/ws/ws_cfg_settings.c b/source/6LoWPAN/ws/ws_cfg_settings.c index 9a53e7cebd..8eacf4802d 100644 --- a/source/6LoWPAN/ws/ws_cfg_settings.c +++ b/source/6LoWPAN/ws/ws_cfg_settings.c @@ -82,6 +82,7 @@ static int8_t ws_cfg_to_get(ws_cfgs_t **cfg, ws_cfgs_t *new_cfg, ws_cfg_validate static void ws_cfg_network_size_config_set_small(ws_cfg_nw_size_t *cfg); static void ws_cfg_network_size_config_set_medium(ws_cfg_nw_size_t *cfg); static void ws_cfg_network_size_config_set_large(ws_cfg_nw_size_t *cfg); +static void ws_cfg_network_size_config_set_xlarge(ws_cfg_nw_size_t *cfg); static void ws_cfg_network_size_config_set_certificate(ws_cfg_nw_size_t *cfg); static int8_t ws_cfg_network_size_default_set(ws_gen_cfg_t *cfg); static int8_t ws_cfg_gen_default_set(ws_gen_cfg_t *cfg); @@ -261,8 +262,10 @@ int8_t ws_cfg_network_size_set(protocol_interface_info_entry_t *cur, ws_gen_cfg_ set_function = ws_cfg_network_size_config_set_small; } else if (cfg->network_size <= NETWORK_SIZE_MEDIUM) { set_function = ws_cfg_network_size_config_set_medium; - } else { + } else if (cfg->network_size <= NETWORK_SIZE_LARGE) { set_function = ws_cfg_network_size_config_set_large; + } else { + set_function = ws_cfg_network_size_config_set_xlarge; } // Overrides the values on the new configuration @@ -334,9 +337,12 @@ int8_t ws_cfg_network_size_configure(protocol_interface_info_entry_t *cur, uint1 } else if (network_size < 800) { // Medium ws_cfg_network_size_config_set_medium(&new_nw_size_cfg); + } else if (network_size < 1500) { + // Medium + ws_cfg_network_size_config_set_large(&new_nw_size_cfg); } else { // Large - ws_cfg_network_size_config_set_large(&new_nw_size_cfg); + ws_cfg_network_size_config_set_xlarge(&new_nw_size_cfg); } ws_cfg_gen_set(cur, NULL, &new_nw_size_cfg.gen, &flags); @@ -374,7 +380,13 @@ static void ws_cfg_network_size_config_set_small(ws_cfg_nw_size_t *cfg) cfg->sec_prot.sec_prot_trickle_imax = SEC_PROT_SMALL_IMAX; cfg->sec_prot.sec_prot_trickle_timer_exp = SEC_PROT_TIMER_EXPIRATIONS; cfg->sec_prot.sec_prot_retry_timeout = SEC_PROT_RETRY_TIMEOUT_SMALL; - cfg->sec_prot.sec_max_ongoing_authentication = MAX_SIMULTANEOUS_EAP_TLS_NEGOTIATIONS_SMALL; + + cfg->sec_prot.sec_max_ongoing_authentication = MAX_SIMULTANEOUS_SECURITY_NEGOTIATIONS_SMALL; + + cfg->sec_prot.initial_key_retry_delay = DEFAULT_INITIAL_KEY_RETRY_TIMER; + cfg->sec_prot.initial_key_imin = SMALL_NW_INITIAL_KEY_TRICKLE_IMIN_SECS; + cfg->sec_prot.initial_key_imax = SMALL_NW_INITIAL_KEY_TRICKLE_IMAX_SECS; + cfg->sec_prot.initial_key_retry_cnt = DEFAULT_INITIAL_KEY_RETRY_COUNT; } static void ws_cfg_network_size_config_set_medium(ws_cfg_nw_size_t *cfg) @@ -384,16 +396,16 @@ static void ws_cfg_network_size_config_set_medium(ws_cfg_nw_size_t *cfg) cfg->gen.rpl_selected_parent_max = WS_RPL_SELECTED_PARENT_MAX; // Configure the Wi-SUN timing trickle parameters - cfg->timing.disc_trickle_imin = TRICKLE_IMIN_30_SECS; // 30 seconds - cfg->timing.disc_trickle_imax = TRICKLE_IMIN_30_SECS << 5; // 960 seconds; 16 minutes + cfg->timing.disc_trickle_imin = TRICKLE_IMIN_60_SECS; // 60 seconds + cfg->timing.disc_trickle_imax = TRICKLE_IMIN_60_SECS << 4; // 960 seconds; 16 minutes cfg->timing.disc_trickle_k = 1; cfg->timing.pan_timeout = PAN_VERSION_MEDIUM_NETWORK_TIMEOUT; cfg->timing.temp_link_min_timeout = WS_NEIGHBOR_TEMPORARY_LINK_MIN_TIMEOUT_SMALL; cfg->timing.temp_eapol_min_timeout = WS_EAPOL_TEMPORARY_ENTRY_MEDIUM_TIMEOUT; // RPL configuration - cfg->bbr.dio_interval_min = WS_RPL_DIO_IMIN_MEDIUM; // 15; 32s - cfg->bbr.dio_interval_doublings = WS_RPL_DIO_DOUBLING_MEDIUM; // 2; 1024s + cfg->bbr.dio_interval_min = WS_RPL_DIO_IMIN_MEDIUM; // 17; 128s + cfg->bbr.dio_interval_doublings = WS_RPL_DIO_DOUBLING_MEDIUM; // 3; 1024s cfg->bbr.dio_redundancy_constant = WS_RPL_DIO_REDUNDANCY_MEDIUM; // 10 cfg->bbr.dag_max_rank_increase = WS_RPL_MAX_HOP_RANK_INCREASE; cfg->bbr.min_hop_rank_increase = WS_RPL_MIN_HOP_RANK_INCREASE; @@ -404,7 +416,13 @@ static void ws_cfg_network_size_config_set_medium(ws_cfg_nw_size_t *cfg) cfg->sec_prot.sec_prot_trickle_imax = SEC_PROT_SMALL_IMAX; cfg->sec_prot.sec_prot_trickle_timer_exp = SEC_PROT_TIMER_EXPIRATIONS; cfg->sec_prot.sec_prot_retry_timeout = SEC_PROT_RETRY_TIMEOUT_SMALL; - cfg->sec_prot.sec_max_ongoing_authentication = MAX_SIMULTANEOUS_EAP_TLS_NEGOTIATIONS_MEDIUM; + + cfg->sec_prot.sec_max_ongoing_authentication = MAX_SIMULTANEOUS_SECURITY_NEGOTIATIONS_MEDIUM; + + cfg->sec_prot.initial_key_retry_delay = DEFAULT_INITIAL_KEY_RETRY_TIMER; + cfg->sec_prot.initial_key_imin = MEDIUM_NW_INITIAL_KEY_TRICKLE_IMIN_SECS; + cfg->sec_prot.initial_key_imax = MEDIUM_NW_INITIAL_KEY_TRICKLE_IMAX_SECS; + cfg->sec_prot.initial_key_retry_cnt = DEFAULT_INITIAL_KEY_RETRY_COUNT; } static void ws_cfg_network_size_config_set_large(ws_cfg_nw_size_t *cfg) @@ -414,16 +432,16 @@ static void ws_cfg_network_size_config_set_large(ws_cfg_nw_size_t *cfg) cfg->gen.rpl_selected_parent_max = WS_RPL_SELECTED_PARENT_MAX; // Configure the Wi-SUN timing trickle parameters - cfg->timing.disc_trickle_imin = TRICKLE_IMIN_60_SECS; // 60 seconds - cfg->timing.disc_trickle_imax = TRICKLE_IMIN_60_SECS << 4; // 960 seconds; 16 minutes + cfg->timing.disc_trickle_imin = TRICKLE_IMIN_60_SECS << 2; // 240 seconds + cfg->timing.disc_trickle_imax = 1536; // 1536 seconds; 25 minutes cfg->timing.disc_trickle_k = 1; cfg->timing.pan_timeout = PAN_VERSION_LARGE_NETWORK_TIMEOUT; cfg->timing.temp_link_min_timeout = WS_NEIGHBOR_TEMPORARY_LINK_MIN_TIMEOUT_LARGE; cfg->timing.temp_eapol_min_timeout = WS_EAPOL_TEMPORARY_ENTRY_LARGE_TIMEOUT; // RPL configuration - cfg->bbr.dio_interval_min = WS_RPL_DIO_IMIN_LARGE; // 19; 524s, 9min - cfg->bbr.dio_interval_doublings = WS_RPL_DIO_DOUBLING_LARGE; // 1; 1024s, 17min + cfg->bbr.dio_interval_min = WS_RPL_DIO_IMIN_LARGE; // 18; 262s, 4.5min + cfg->bbr.dio_interval_doublings = WS_RPL_DIO_DOUBLING_LARGE; // 3; 2048s, 34min cfg->bbr.dio_redundancy_constant = WS_RPL_DIO_REDUNDANCY_LARGE; // 10 cfg->bbr.dag_max_rank_increase = WS_RPL_MAX_HOP_RANK_INCREASE; cfg->bbr.min_hop_rank_increase = WS_RPL_MIN_HOP_RANK_INCREASE; @@ -434,7 +452,49 @@ static void ws_cfg_network_size_config_set_large(ws_cfg_nw_size_t *cfg) cfg->sec_prot.sec_prot_trickle_imax = SEC_PROT_LARGE_IMAX; cfg->sec_prot.sec_prot_trickle_timer_exp = SEC_PROT_TIMER_EXPIRATIONS; cfg->sec_prot.sec_prot_retry_timeout = SEC_PROT_RETRY_TIMEOUT_LARGE; - cfg->sec_prot.sec_max_ongoing_authentication = MAX_SIMULTANEOUS_EAP_TLS_NEGOTIATIONS_LARGE; + + cfg->sec_prot.sec_max_ongoing_authentication = MAX_SIMULTANEOUS_SECURITY_NEGOTIATIONS_LARGE; + + cfg->sec_prot.initial_key_retry_delay = NONE_INITIAL_KEY_RETRY_TIMER; + cfg->sec_prot.initial_key_imin = LARGE_NW_INITIAL_KEY_TRICKLE_IMIN_SECS; + cfg->sec_prot.initial_key_imax = LARGE_NW_INITIAL_KEY_TRICKLE_IMAX_SECS; + cfg->sec_prot.initial_key_retry_cnt = LARGE_NW_INITIAL_KEY_RETRY_COUNT; +} + +static void ws_cfg_network_size_config_set_xlarge(ws_cfg_nw_size_t *cfg) +{ + // Configure the Wi-SUN parent configuration + cfg->gen.rpl_parent_candidate_max = WS_RPL_PARENT_CANDIDATE_MAX; + cfg->gen.rpl_selected_parent_max = WS_RPL_SELECTED_PARENT_MAX; + + // Configure the Wi-SUN timing trickle parameters + cfg->timing.disc_trickle_imin = TRICKLE_IMIN_60_SECS << 2; // 240 seconds + cfg->timing.disc_trickle_imax = 1920; // 1920 seconds; 32 minutes + cfg->timing.disc_trickle_k = 1; + cfg->timing.pan_timeout = PAN_VERSION_XLARGE_NETWORK_TIMEOUT; + cfg->timing.temp_link_min_timeout = WS_NEIGHBOR_TEMPORARY_LINK_MIN_TIMEOUT_LARGE; + cfg->timing.temp_eapol_min_timeout = WS_EAPOL_TEMPORARY_ENTRY_LARGE_TIMEOUT; + + // RPL configuration + cfg->bbr.dio_interval_min = WS_RPL_DIO_IMIN_XLARGE; // 18; 262s, 4.5min + cfg->bbr.dio_interval_doublings = WS_RPL_DIO_DOUBLING_XLARGE; // 4; 2048s, 34min + cfg->bbr.dio_redundancy_constant = WS_RPL_DIO_REDUNDANCY_XLARGE; // 10 + cfg->bbr.dag_max_rank_increase = WS_RPL_MAX_HOP_RANK_INCREASE; + cfg->bbr.min_hop_rank_increase = WS_RPL_MIN_HOP_RANK_INCREASE; + cfg->bbr.dhcp_address_lifetime = WS_DHCP_ADDRESS_LIFETIME_LARGE; + + // EAPOL configuration + cfg->sec_prot.sec_prot_trickle_imin = SEC_PROT_LARGE_IMIN; + cfg->sec_prot.sec_prot_trickle_imax = SEC_PROT_LARGE_IMAX; + cfg->sec_prot.sec_prot_trickle_timer_exp = SEC_PROT_TIMER_EXPIRATIONS; + cfg->sec_prot.sec_prot_retry_timeout = SEC_PROT_RETRY_TIMEOUT_LARGE; + + cfg->sec_prot.sec_max_ongoing_authentication = MAX_SIMULTANEOUS_SECURITY_NEGOTIATIONS_LARGE; + + cfg->sec_prot.initial_key_retry_delay = NONE_INITIAL_KEY_RETRY_TIMER; + cfg->sec_prot.initial_key_imin = EXTRA_LARGE_NW_INITIAL_KEY_TRICKLE_IMIN_SECS; + cfg->sec_prot.initial_key_imax = EXTRA_LARGE_NW_INITIAL_KEY_TRICKLE_IMAX_SECS; + cfg->sec_prot.initial_key_retry_cnt = EXTRA_LARGE_NW_INITIAL_KEY_RETRY_COUNT; } static void ws_cfg_network_size_config_set_certificate(ws_cfg_nw_size_t *cfg) @@ -464,7 +524,13 @@ static void ws_cfg_network_size_config_set_certificate(ws_cfg_nw_size_t *cfg) cfg->sec_prot.sec_prot_trickle_imax = SEC_PROT_SMALL_IMAX; cfg->sec_prot.sec_prot_trickle_timer_exp = SEC_PROT_TIMER_EXPIRATIONS; cfg->sec_prot.sec_prot_retry_timeout = SEC_PROT_RETRY_TIMEOUT_SMALL; - cfg->sec_prot.sec_max_ongoing_authentication = MAX_SIMULTANEOUS_EAP_TLS_NEGOTIATIONS_SMALL; + + cfg->sec_prot.sec_max_ongoing_authentication = MAX_SIMULTANEOUS_SECURITY_NEGOTIATIONS_SMALL; + + cfg->sec_prot.initial_key_retry_delay = DEFAULT_INITIAL_KEY_RETRY_TIMER; + cfg->sec_prot.initial_key_imin = SMALL_NW_INITIAL_KEY_TRICKLE_IMIN_SECS; + cfg->sec_prot.initial_key_imax = SMALL_NW_INITIAL_KEY_TRICKLE_IMAX_SECS; + cfg->sec_prot.initial_key_retry_cnt = DEFAULT_INITIAL_KEY_RETRY_COUNT; } static int8_t ws_cfg_gen_default_set(ws_gen_cfg_t *cfg) @@ -617,8 +683,8 @@ int8_t ws_cfg_phy_set(protocol_interface_info_entry_t *cur, ws_phy_cfg_t *cfg, w static int8_t ws_cfg_timing_default_set(ws_timing_cfg_t *cfg) { // Configure the Wi-SUN timing trickle parameters - cfg->disc_trickle_imin = TRICKLE_IMIN_30_SECS; // 30 seconds - cfg->disc_trickle_imax = TRICKLE_IMIN_30_SECS << 5; // 960 seconds; 16 minutes + cfg->disc_trickle_imin = TRICKLE_IMIN_60_SECS; // 60 seconds + cfg->disc_trickle_imax = TRICKLE_IMIN_60_SECS << 4; // 960 seconds; 16 minutes cfg->disc_trickle_k = 1; cfg->pan_timeout = PAN_VERSION_MEDIUM_NETWORK_TIMEOUT; cfg->temp_link_min_timeout = WS_NEIGHBOR_TEMPORARY_LINK_MIN_TIMEOUT_SMALL; @@ -695,13 +761,13 @@ int8_t ws_cfg_timing_set(protocol_interface_info_entry_t *cur, ws_timing_cfg_t * static int8_t ws_cfg_bbr_default_set(ws_bbr_cfg_t *cfg) { // Something in between - // imin: 15 (32s) - // doublings:5 (960s) + // imin: 17 (128s) + // doublings:3 (1024s) // redundancy; 10 - //ws_bbr_rpl_config(cur, 15, 5, 10, WS_RPL_MAX_HOP_RANK_INCREASE, WS_RPL_MIN_HOP_RANK_INCREASE); + //ws_bbr_rpl_config(cur, 17, 3, 10, WS_RPL_MAX_HOP_RANK_INCREASE, WS_RPL_MIN_HOP_RANK_INCREASE); - cfg->dio_interval_min = 15; // 32s - cfg->dio_interval_doublings = 5; // 1024s + cfg->dio_interval_min = WS_RPL_DIO_IMIN_MEDIUM; // 128s + cfg->dio_interval_doublings = WS_RPL_DIO_DOUBLING_MEDIUM; // 1024s cfg->dio_redundancy_constant = 10; cfg->dag_max_rank_increase = WS_RPL_MAX_HOP_RANK_INCREASE; cfg->min_hop_rank_increase = WS_RPL_MIN_HOP_RANK_INCREASE; @@ -1011,7 +1077,12 @@ static int8_t ws_cfg_sec_prot_default_set(ws_sec_prot_cfg_t *cfg) cfg->sec_prot_trickle_imax = SEC_PROT_SMALL_IMAX; cfg->sec_prot_trickle_timer_exp = 2; cfg->sec_prot_retry_timeout = SEC_PROT_RETRY_TIMEOUT_SMALL; - cfg->sec_max_ongoing_authentication = MAX_SIMULTANEOUS_EAP_TLS_NEGOTIATIONS_MEDIUM; + cfg->sec_max_ongoing_authentication = MAX_SIMULTANEOUS_SECURITY_NEGOTIATIONS_MEDIUM; + cfg->initial_key_retry_delay = DEFAULT_INITIAL_KEY_RETRY_TIMER; + cfg->initial_key_imin = MEDIUM_NW_INITIAL_KEY_TRICKLE_IMIN_SECS; + cfg->initial_key_imax = MEDIUM_NW_INITIAL_KEY_TRICKLE_IMAX_SECS; + cfg->initial_key_retry_cnt = DEFAULT_INITIAL_KEY_RETRY_COUNT; + return CFG_SETTINGS_OK; } @@ -1032,7 +1103,11 @@ int8_t ws_cfg_sec_prot_validate(ws_sec_prot_cfg_t *cfg, ws_sec_prot_cfg_t *new_c cfg->sec_prot_trickle_imax != new_cfg->sec_prot_trickle_imax || cfg->sec_prot_trickle_timer_exp != new_cfg->sec_prot_trickle_timer_exp || cfg->sec_prot_retry_timeout != new_cfg->sec_prot_retry_timeout || - cfg->sec_max_ongoing_authentication != new_cfg->sec_max_ongoing_authentication) { + cfg->sec_max_ongoing_authentication != new_cfg->sec_max_ongoing_authentication || + cfg->initial_key_retry_delay != new_cfg->initial_key_retry_delay || + cfg->initial_key_imin != new_cfg->initial_key_retry_delay || + cfg->initial_key_imax != new_cfg->initial_key_retry_delay || + cfg->initial_key_retry_cnt != new_cfg->initial_key_retry_delay) { return CFG_SETTINGS_CHANGED; } diff --git a/source/6LoWPAN/ws/ws_cfg_settings.h b/source/6LoWPAN/ws/ws_cfg_settings.h index 9011d8147b..bc46336229 100644 --- a/source/6LoWPAN/ws/ws_cfg_settings.h +++ b/source/6LoWPAN/ws/ws_cfg_settings.h @@ -108,11 +108,15 @@ typedef struct ws_sec_timer_cfg_s { * \brief Struct ws_sec_prot_cfg_t Security protocols configuration */ typedef struct ws_sec_prot_cfg_s { - uint16_t sec_prot_retry_timeout; /**< Security protocol retry timeout; seconds; default 330 */ - uint16_t sec_prot_trickle_imin; /**< Security protocol trickle parameters Imin; seconds; default 30 */ - uint16_t sec_prot_trickle_imax; /**< Security protocol trickle parameters Imax; seconds; default 90 */ - uint8_t sec_prot_trickle_timer_exp; /**< Security protocol trickle timer expirations; default 2 */ - uint16_t sec_max_ongoing_authentication; /**< Pae authenticator max Accept ongoing authentication count */ + uint16_t sec_prot_retry_timeout; /**< Security protocol retry timeout; seconds; default 330 */ + uint16_t sec_prot_trickle_imin; /**< Security protocol trickle parameters Imin; seconds; default 30 */ + uint16_t sec_prot_trickle_imax; /**< Security protocol trickle parameters Imax; seconds; default 90 */ + uint8_t sec_prot_trickle_timer_exp; /**< Security protocol trickle timer expirations; default 2 */ + uint16_t sec_max_ongoing_authentication; /**< Pae authenticator max Accept ongoing authentication count */ + uint16_t initial_key_retry_delay; /**< Delay before starting initial key trickle; seconds; default 120 */ + uint16_t initial_key_imin; /**< Initial key trickle Imin; seconds; default 360 */ + uint16_t initial_key_imax; /**< Initial key trickle Imax; seconds; default 720 */ + uint8_t initial_key_retry_cnt; /**< Number of initial key retries; default 2 */ } ws_sec_prot_cfg_t; /** diff --git a/source/6LoWPAN/ws/ws_common.c b/source/6LoWPAN/ws/ws_common.c index 169da011ac..010f6c14ac 100644 --- a/source/6LoWPAN/ws/ws_common.c +++ b/source/6LoWPAN/ws/ws_common.c @@ -49,12 +49,34 @@ uint8_t DEVICE_MIN_SENS = 174 - 93; uint16_t test_max_child_count_override = 0xffff; - -int8_t ws_generate_channel_list(uint32_t *channel_mask, uint16_t number_of_channels, uint8_t regulatory_domain) +int8_t ws_generate_channel_list(uint32_t *channel_mask, uint16_t number_of_channels, uint8_t regulatory_domain, uint8_t operating_class) { - (void)regulatory_domain; - for (uint8_t i = 0; i < number_of_channels; i++) { - channel_mask[0 + (i / 32)] |= (1 << (i % 32)); + uint32_t excluded_start_channel = 0xFFFFFFFF; + uint32_t excluded_end_channel = 0xFFFFFFFF; + + if (regulatory_domain == REG_DOMAIN_BZ) { + if (operating_class == 1) { + excluded_start_channel = 26; + excluded_end_channel = 64; + } else if (operating_class == 2) { + excluded_start_channel = 12; + excluded_end_channel = 32; + } else if (operating_class == 3) { + excluded_start_channel = 7; + excluded_end_channel = 21; + } + } + + // Clear channel mask + for (uint8_t i = 0; i < 8; i++) { + channel_mask[i] = 0; + } + + // Set channel maks outside excluded channels + for (uint16_t i = 0; i < number_of_channels; i++) { + if (i < excluded_start_channel || i > excluded_end_channel) { + channel_mask[0 + (i / 32)] |= (1 << (i % 32)); + } } return 0; } @@ -159,6 +181,19 @@ int8_t ws_common_regulatory_domain_config(protocol_interface_info_entry_t *cur, } else { return -1; } + } else if (hopping_schdule->regulatory_domain == REG_DOMAIN_BZ) { + if (hopping_schdule->operating_class == 1) { + hopping_schdule->ch0_freq = 9022; + hopping_schdule->channel_spacing = CHANNEL_SPACING_200; + } else if (hopping_schdule->operating_class == 2) { + hopping_schdule->ch0_freq = 9024; + hopping_schdule->channel_spacing = CHANNEL_SPACING_400; + } else if (hopping_schdule->operating_class == 3) { + hopping_schdule->ch0_freq = 9026; + hopping_schdule->channel_spacing = CHANNEL_SPACING_600; + } else { + return -1; + } } else if (hopping_schdule->regulatory_domain == REG_DOMAIN_JP) { if (hopping_schdule->operating_class == 1) { hopping_schdule->ch0_freq = 9206; @@ -189,6 +224,7 @@ int8_t ws_common_regulatory_domain_config(protocol_interface_info_entry_t *cur, if (!hopping_schdule->number_of_channels) { return -1; } + return 0; } @@ -232,6 +268,14 @@ uint16_t ws_common_channel_number_calc(uint8_t regulatory_domain, uint8_t operat } else if (operating_class == 3) { return 12; } + } else if (regulatory_domain == REG_DOMAIN_BZ) { + if (operating_class == 1) { + return 129; + } else if (operating_class == 2) { + return 64; + } else if (operating_class == 3) { + return 42; + } } else if (regulatory_domain == REG_DOMAIN_WW) { if (operating_class == 1) { // TODO we dont support this yet, but it is used as test value @@ -391,8 +435,10 @@ uint32_t ws_common_latency_estimate_get(protocol_interface_info_entry_t *cur) latency = 4000; } else if (network_size <= NETWORK_SIZE_MEDIUM) { latency = 8000; - } else { + } else if (network_size <= NETWORK_SIZE_LARGE) { latency = 16000; + } else { + latency = 24000; } return latency; diff --git a/source/6LoWPAN/ws/ws_common.h b/source/6LoWPAN/ws/ws_common.h index ec6a7b9955..08d726ee6b 100644 --- a/source/6LoWPAN/ws/ws_common.h +++ b/source/6LoWPAN/ws/ws_common.h @@ -113,7 +113,7 @@ typedef struct ws_info_s { #ifdef HAVE_WS -int8_t ws_generate_channel_list(uint32_t *channel_mask, uint16_t number_of_channels, uint8_t regulatory_domain); +int8_t ws_generate_channel_list(uint32_t *channel_mask, uint16_t number_of_channels, uint8_t regulatory_domain, uint8_t operating_class); uint32_t ws_decode_channel_spacing(uint8_t channel_spacing); diff --git a/source/6LoWPAN/ws/ws_common_defines.h b/source/6LoWPAN/ws/ws_common_defines.h index 2de37bf842..749a5aa1fa 100644 --- a/source/6LoWPAN/ws/ws_common_defines.h +++ b/source/6LoWPAN/ws/ws_common_defines.h @@ -242,7 +242,6 @@ typedef struct ws_bs_ie { #define WS_NEIGHBOR_ETX_SAMPLE_MAX 3 #define WS_NEIGHBOR_FIRST_ETX_SAMPLE_MIN_COUNT 3 //This can't be bigger than WS_NEIGHBOR_ETX_SAMPLE_MAX -#define WS_NEIGHBOUR_MAX_CANDIDATE_PROBE 5 #define WS_PROBE_INIT_BASE_SECONDS 8 @@ -322,7 +321,7 @@ typedef struct ws_bs_ie { /* * Automatic CCA threshold: default threshold and range in dBm. */ -#define CCA_DEFAULT_DBM -85 +#define CCA_DEFAULT_DBM -60 #define CCA_HIGH_LIMIT -60 #define CCA_LOW_LIMIT -100 diff --git a/source/6LoWPAN/ws/ws_config.h b/source/6LoWPAN/ws/ws_config.h index 9b84a5dbfb..6b00d6004c 100644 --- a/source/6LoWPAN/ws/ws_config.h +++ b/source/6LoWPAN/ws/ws_config.h @@ -31,14 +31,18 @@ #define WS_RPL_DIO_DOUBLING_SMALL 2 #define WS_RPL_DIO_REDUNDANCY_SMALL 0 -#define WS_RPL_DIO_IMIN_MEDIUM 15 -#define WS_RPL_DIO_DOUBLING_MEDIUM 5 +#define WS_RPL_DIO_IMIN_MEDIUM 17 +#define WS_RPL_DIO_DOUBLING_MEDIUM 3 #define WS_RPL_DIO_REDUNDANCY_MEDIUM 10 -#define WS_RPL_DIO_IMIN_LARGE 19 -#define WS_RPL_DIO_DOUBLING_LARGE 1 +#define WS_RPL_DIO_IMIN_LARGE 18 +#define WS_RPL_DIO_DOUBLING_LARGE 3 #define WS_RPL_DIO_REDUNDANCY_LARGE 10 // May need some tuning still +#define WS_RPL_DIO_IMIN_XLARGE 18 +#define WS_RPL_DIO_DOUBLING_XLARGE 4 +#define WS_RPL_DIO_REDUNDANCY_XLARGE 10 // May need some tuning still + #define WS_RPL_DIO_IMIN_AUTOMATIC 14 #define WS_RPL_DIO_DOUBLING_AUTOMATIC 3 #define WS_RPL_DIO_REDUNDANCY_AUTOMATIC 0 @@ -68,7 +72,10 @@ // RPL version number update intervall // after restart version numbers are increased faster and then slowed down when network is stable #define RPL_VERSION_LIFETIME 12*3600 -#define RPL_VERSION_LIFETIME_RESTART 3600 +#define RPL_VERSION_LIFETIME_RESTART_SMALL 3600 +#define RPL_VERSION_LIFETIME_RESTART_MEDIUM 2*3600 +#define RPL_VERSION_LIFETIME_RESTART_LARGE 4*3600 +#define RPL_VERSION_LIFETIME_RESTART_EXTRA_LARGE 8*3600 /* Border router connection lost timeout * @@ -85,6 +92,8 @@ #define PAN_VERSION_LARGE_NETWORK_TIMEOUT 90*60 +#define PAN_VERSION_XLARGE_NETWORK_TIMEOUT 120*60 + /* Routing Cost Weighting factor */ #define PRC_WEIGHT_FACTOR 256 @@ -157,10 +166,11 @@ extern uint8_t DEVICE_MIN_SENS; /* * MAC frame counter NVM storing configuration */ -#define FRAME_COUNTER_STORE_INTERVAL 60 // Time interval (on seconds) between frame counter store operations -#define FRAME_COUNTER_STORE_TRIGGER 5 // Delay (on seconds) before storing, when storing of frame counters is triggered -#define FRAME_COUNTER_INCREMENT 1000 // How much frame counter is incremented on start up -#define FRAME_COUNTER_STORE_THRESHOLD 800 // How much frame counter must increment before it is stored +#define FRAME_COUNTER_STORE_INTERVAL 60 // Time interval (on seconds) between checking if frame counter storing is needed +#define FRAME_COUNTER_STORE_FORCE_INTERVAL (3600 * 20) // Time interval (on seconds) before frame counter storing is forced (if no other storing operations triggered) +#define FRAME_COUNTER_STORE_TRIGGER 5 // Delay (on seconds) before storing, when storing of frame counters is triggered +#define FRAME_COUNTER_INCREMENT 1000 // How much frame counter is incremented on start up +#define FRAME_COUNTER_STORE_THRESHOLD 800 // How much frame counter must increment before it is stored /* @@ -203,10 +213,10 @@ extern uint8_t DEVICE_MIN_SENS; #define SEC_PROT_TIMER_EXPIRATIONS 2 // Number of retries -// Maximum number of simultaneous EAP-TLS negotiations -#define MAX_SIMULTANEOUS_EAP_TLS_NEGOTIATIONS_SMALL 3 -#define MAX_SIMULTANEOUS_EAP_TLS_NEGOTIATIONS_MEDIUM 20 -#define MAX_SIMULTANEOUS_EAP_TLS_NEGOTIATIONS_LARGE 50 +// Maximum number of simultaneous security negotiations +#define MAX_SIMULTANEOUS_SECURITY_NEGOTIATIONS_SMALL 3 +#define MAX_SIMULTANEOUS_SECURITY_NEGOTIATIONS_MEDIUM 20 +#define MAX_SIMULTANEOUS_SECURITY_NEGOTIATIONS_LARGE 50 /* * Security protocol timer configuration parameters @@ -222,4 +232,33 @@ extern uint8_t DEVICE_MIN_SENS; #define DEFAULT_GTK_MAX_MISMATCH 64 // 64 minutes #define DEFAULT_GTK_NEW_INSTALL_REQUIRED 80 // 80 percent of GTK lifetime --> 24 days +/* + * Security protocol initial EAPOL-key parameters + */ + +// How long the wait is before the first initial EAPOL-key retry +#define DEFAULT_INITIAL_KEY_RETRY_TIMER 120 +#define NONE_INITIAL_KEY_RETRY_TIMER 0 + +// Small network Default trickle values for sending of initial EAPOL-key +#define SMALL_NW_INITIAL_KEY_TRICKLE_IMIN_SECS 360 /* 6 to 8.3 minutes */ +#define SMALL_NW_INITIAL_KEY_TRICKLE_IMAX_SECS 500 + +// Small network Default trickle values for sending of initial EAPOL-key +#define MEDIUM_NW_INITIAL_KEY_TRICKLE_IMIN_SECS 360 /* 6 to 12 minutes */ +#define MEDIUM_NW_INITIAL_KEY_TRICKLE_IMAX_SECS 720 + +// Large network trickle values for sending of initial EAPOL-key +#define LARGE_NW_INITIAL_KEY_TRICKLE_IMIN_SECS 600 /* 10 to 20 minutes */ +#define LARGE_NW_INITIAL_KEY_TRICKLE_IMAX_SECS 1200 +#define LARGE_NW_INITIAL_KEY_RETRY_COUNT 4 + +// Very slow network values for sending of initial EAPOL-key +#define EXTRA_LARGE_NW_INITIAL_KEY_TRICKLE_IMIN_SECS 600 /* 10 to 20 minutes */ +#define EXTRA_LARGE_NW_INITIAL_KEY_TRICKLE_IMAX_SECS 1200 +#define EXTRA_LARGE_NW_INITIAL_KEY_RETRY_COUNT 4 + +// How many times sending of initial EAPOL-key is retried +#define DEFAULT_INITIAL_KEY_RETRY_COUNT 2 + #endif /* WS_CONFIG_H_ */ diff --git a/source/6LoWPAN/ws/ws_eapol_pdu.c b/source/6LoWPAN/ws/ws_eapol_pdu.c index ffe83c4a48..f20530d466 100644 --- a/source/6LoWPAN/ws/ws_eapol_pdu.c +++ b/source/6LoWPAN/ws/ws_eapol_pdu.c @@ -31,6 +31,7 @@ #include "6LoWPAN/MAC/mpx_api.h" #include "6LoWPAN/ws/ws_config.h" #include "6LoWPAN/ws/ws_eapol_pdu.h" +#include "6LoWPAN/ws/ws_llc.h" #ifdef HAVE_WS @@ -49,6 +50,7 @@ typedef NS_LIST_HEAD(eapol_pdu_msdu_t, link) eapol_pdu_msdu_list_t; typedef struct { uint8_t priority; + bool filter_requsted: 1; ws_eapol_pdu_address_check *addr_check; ws_eapol_pdu_receive *receive; ns_list_link_t link; @@ -147,6 +149,7 @@ int8_t ws_eapol_pdu_cb_register(protocol_interface_info_entry_t *interface_ptr, new_cb->priority = cb_data->priority; new_cb->addr_check = cb_data->addr_check; new_cb->receive = cb_data->receive; + new_cb->filter_requsted = cb_data->filter_requsted; ns_list_foreach(eapol_pdu_recv_cb_t, entry, &eapol_pdu_data->recv_cb_list) { if (new_cb->priority <= entry->priority) { @@ -307,6 +310,11 @@ static void ws_eapol_pdu_mpx_data_indication(const mpx_api_t *api, const struct ns_list_foreach(eapol_pdu_recv_cb_t, entry, &eapol_pdu_data->recv_cb_list) { if (entry->addr_check(eapol_pdu_data->interface_ptr, data->SrcAddr) >= 0) { + if (entry->filter_requsted && !ws_llc_eapol_relay_forward_filter(eapol_pdu_data->interface_ptr, data->SrcAddr, data->DSN, data->timestamp)) { + tr_info("EAPOL relay filter drop"); + return; + } + entry->receive(eapol_pdu_data->interface_ptr, data->SrcAddr, data->msdu_ptr, data->msduLength); break; } diff --git a/source/6LoWPAN/ws/ws_eapol_pdu.h b/source/6LoWPAN/ws/ws_eapol_pdu.h index 75f4ef4074..c385e9313c 100644 --- a/source/6LoWPAN/ws/ws_eapol_pdu.h +++ b/source/6LoWPAN/ws/ws_eapol_pdu.h @@ -99,6 +99,7 @@ typedef enum { typedef struct { eapol_pdu_recv_prior_t priority; /**< Priority: high, medium or low */ + bool filter_requsted: 1; /**< True when EAPOL temporary filter requsted, false for normal functionality */ ws_eapol_pdu_address_check *addr_check; /**< Address check callback */ ws_eapol_pdu_receive *receive; /**< PDU receive callback */ } eapol_pdu_recv_cb_data_t; diff --git a/source/6LoWPAN/ws/ws_eapol_relay.c b/source/6LoWPAN/ws/ws_eapol_relay.c index 367181bfcc..a5a83c3ec3 100644 --- a/source/6LoWPAN/ws/ws_eapol_relay.c +++ b/source/6LoWPAN/ws/ws_eapol_relay.c @@ -53,6 +53,7 @@ static void ws_eapol_relay_socket_cb(void *cb); static const eapol_pdu_recv_cb_data_t eapol_pdu_recv_cb_data = { .priority = EAPOL_PDU_RECV_LOW_PRIORITY, + .filter_requsted = true, .addr_check = ws_eapol_relay_eapol_pdu_address_check, .receive = ws_eapol_relay_eapol_pdu_receive }; diff --git a/source/6LoWPAN/ws/ws_llc.h b/source/6LoWPAN/ws/ws_llc.h index fdb8f946be..fd3b010501 100644 --- a/source/6LoWPAN/ws/ws_llc.h +++ b/source/6LoWPAN/ws/ws_llc.h @@ -78,15 +78,21 @@ typedef struct llc_neighbour_req { struct ws_neighbor_class_entry *ws_neighbor; /**< Wi-sun Neighbor information entry. */ } llc_neighbour_req_t; +typedef struct eapol_temporary_info_s { + uint8_t eapol_rx_relay_filter; /*!< seconds for dropping duplicate id */ + uint8_t last_rx_mac_sequency; /*!< Only compared when Timer is active */ + uint16_t eapol_timeout; /*!< EAPOL relay Temporary entry lifetime */ +} eapol_temporary_info_t; + /** * Neighbor temporary structure for storage FHSS data before create a real Neighbour info */ typedef struct ws_neighbor_temp_class_s { struct ws_neighbor_class_entry neigh_info_list; /*!< Allocated hopping info array*/ + eapol_temporary_info_t eapol_temp_info; uint8_t mac64[8]; uint8_t mpduLinkQuality; int8_t signal_dbm; - uint16_t eapol_timeout; ns_list_link_t link; } ws_neighbor_temp_class_t; @@ -220,6 +226,8 @@ void ws_llc_hopping_schedule_config(struct protocol_interface_info_entry *interf void ws_llc_timer_seconds(struct protocol_interface_info_entry *interface, uint16_t seconds_update); +bool ws_llc_eapol_relay_forward_filter(struct protocol_interface_info_entry *interface, const uint8_t *joiner_eui64, uint8_t mac_sequency, uint32_t rx_timestamp); + ws_neighbor_temp_class_t *ws_llc_get_multicast_temp_entry(struct protocol_interface_info_entry *interface, const uint8_t *mac64); void ws_llc_free_multicast_temp_entry(struct protocol_interface_info_entry *interface, ws_neighbor_temp_class_t *neighbor); diff --git a/source/6LoWPAN/ws/ws_llc_data_service.c b/source/6LoWPAN/ws/ws_llc_data_service.c index d82fc467d1..73f468a27c 100644 --- a/source/6LoWPAN/ws/ws_llc_data_service.c +++ b/source/6LoWPAN/ws/ws_llc_data_service.c @@ -100,7 +100,7 @@ typedef struct { typedef NS_LIST_HEAD(llc_message_t, link) llc_message_list_t; #define MAX_NEIGH_TEMPORARY_MULTICAST_SIZE 5 -#define MAX_NEIGH_TEMPORRY_EAPOL_SIZE 15 +#define MAX_NEIGH_TEMPORRY_EAPOL_SIZE 30 #define MAX_NEIGH_TEMPORAY_LIST_SIZE (MAX_NEIGH_TEMPORARY_MULTICAST_SIZE + MAX_NEIGH_TEMPORRY_EAPOL_SIZE) typedef struct { @@ -431,7 +431,7 @@ static void ws_llc_mac_confirm_cb(const mac_api_t *api, const mcps_data_conf_t * ws_neighbor_temp_class_t *temp_entry = ws_llc_discover_eapol_temp_entry(base->temp_entries, message->dst_address); if (temp_entry) { //Update Temporary Lifetime - temp_entry->eapol_timeout = interface->ws_info->cfg->timing.temp_eapol_min_timeout + 1; + temp_entry->eapol_temp_info.eapol_timeout = interface->ws_info->cfg->timing.temp_eapol_min_timeout + 1; } } } @@ -449,7 +449,7 @@ static void ws_llc_mac_confirm_cb(const mac_api_t *api, const mcps_data_conf_t * } if (message->dst_address_type == MAC_ADDR_MODE_64_BIT && base->ws_neighbor_info_request_cb(interface, message->dst_address, &neighbor_info, false)) { - etx_transm_attempts_update(interface->id, 1 + data->tx_retries, success, neighbor_info.neighbor->index); + etx_transm_attempts_update(interface->id, 1 + data->tx_retries, success, neighbor_info.neighbor->index, neighbor_info.neighbor->mac64); //TODO discover RSL from Enchanced ACK Header IE elements ws_utt_ie_t ws_utt; if (ws_wh_utt_read(conf_data->headerIeList, conf_data->headerIeListLength, &ws_utt)) { @@ -648,6 +648,11 @@ static void ws_llc_data_indication_cb(const mac_api_t *api, const mcps_data_ind_ } } + if (!multicast && !ws_neighbor_class_neighbor_duplicate_packet_check(neighbor_info.ws_neighbor, data->DSN, data->timestamp)) { + tr_info("Drop duplicate message"); + return; + } + ws_neighbor_class_neighbor_unicast_time_info_update(neighbor_info.ws_neighbor, &ws_utt, data->timestamp); if (us_ie_inline) { ws_neighbor_class_neighbor_unicast_schedule_set(neighbor_info.ws_neighbor, &us_ie); @@ -675,7 +680,7 @@ static void ws_llc_data_indication_cb(const mac_api_t *api, const mcps_data_ind_ if (neighbor_info.neighbor) { //Refresh ETX dbm - etx_lqi_dbm_update(interface->id, data->mpduLinkQuality, data->signal_dbm, neighbor_info.neighbor->index); + etx_lqi_dbm_update(interface->id, data->mpduLinkQuality, data->signal_dbm, neighbor_info.neighbor->index, neighbor_info.neighbor->mac64); if (data->Key.SecurityLevel) { //SET trusted state mac_neighbor_table_trusted_neighbor(mac_neighbor_info(interface), neighbor_info.neighbor, true); @@ -740,7 +745,7 @@ static void ws_llc_eapol_indication_cb(const mac_api_t *api, const mcps_data_ind return; } //Update Temporary Lifetime - temp_entry->eapol_timeout = interface->ws_info->cfg->timing.temp_eapol_min_timeout + 1; + temp_entry->eapol_temp_info.eapol_timeout = interface->ws_info->cfg->timing.temp_eapol_min_timeout + 1; neighbor_info.ws_neighbor = &temp_entry->neigh_info_list; //Storage Signal info for future ETX update possibility @@ -838,78 +843,6 @@ static void ws_llc_mac_indication_cb(const mac_api_t *api, const mcps_data_ind_t if (ws_utt.message_type == WS_FT_EAPOL) { ws_llc_eapol_indication_cb(api, data, ie_ext, ws_utt); return; - llc_data_base_t *base = ws_llc_mpx_frame_common_validates(api, data, ws_utt); - if (!base) { - return; - } - - //Discover MPX header and handler - mac_payload_IE_t mpx_ie; - mpx_msg_t mpx_frame; - mpx_user_t *user_cb = ws_llc_mpx_header_parse(base, ie_ext, &mpx_frame, &mpx_ie); - if (!user_cb) { - return; - } - - mac_payload_IE_t ws_wp_nested; - ws_us_ie_t us_ie; - bool us_ie_inline = false; - bool bs_ie_inline = false; - ws_wp_nested.id = WS_WP_NESTED_IE; - ws_bs_ie_t ws_bs_ie; - if (mac_ie_payload_discover(ie_ext->payloadIeList, ie_ext->payloadIeListLength, &ws_wp_nested) > 2) { - us_ie_inline = ws_wp_nested_us_read(ws_wp_nested.content_ptr, ws_wp_nested.length, &us_ie); - bs_ie_inline = ws_wp_nested_bs_read(ws_wp_nested.content_ptr, ws_wp_nested.length, &ws_bs_ie); - } - - //Validate Unicast shedule Channel Plan - if (us_ie_inline && !ws_bootstrap_validate_channel_plan(&us_ie, base->interface_ptr)) { - //Channel plan configuration mismatch - return; - } - - llc_neighbour_req_t neighbor_info; - - if (!base->ws_neighbor_info_request_cb(base->interface_ptr, data->SrcAddr, &neighbor_info, true)) { - //tr_debug("Drop message no neighbor"); - return; - } - - ws_neighbor_class_neighbor_unicast_time_info_update(neighbor_info.ws_neighbor, &ws_utt, data->timestamp); - if (us_ie_inline) { - ws_neighbor_class_neighbor_unicast_schedule_set(neighbor_info.ws_neighbor, &us_ie); - } - //Update BS if it is part of message - if (bs_ie_inline) { - ws_neighbor_class_neighbor_broadcast_schedule_set(neighbor_info.ws_neighbor, &ws_bs_ie); - } - - uint8_t auth_eui64[8]; - //Discover and write Auhtenticator EUI-64 - if (ws_wh_ea_read(ie_ext->headerIeList, ie_ext->headerIeListLength, auth_eui64)) { - ws_pae_controller_border_router_addr_write(base->interface_ptr, auth_eui64); - } - - - //Update BT if it is part of message - ws_bt_ie_t ws_bt; - if (ws_wh_bt_read(ie_ext->headerIeList, ie_ext->headerIeListLength, &ws_bt)) { - ws_neighbor_class_neighbor_broadcast_time_info_update(neighbor_info.ws_neighbor, &ws_bt, data->timestamp); - if (neighbor_info.neighbor) { - if (neighbor_info.neighbor->link_role == PRIORITY_PARENT_NEIGHBOUR) { - // We have broadcast schedule set up set the broadcast parent schedule - ns_fhss_ws_set_parent(base->interface_ptr->ws_info->fhss_api, neighbor_info.neighbor->mac64, &neighbor_info.ws_neighbor->fhss_data.bc_timing_info, false); - } else { - ws_bootstrap_eapol_parent_synch(base->interface_ptr, &neighbor_info); - } - } - } - - mcps_data_ind_t data_ind = *data; - data_ind.msdu_ptr = mpx_frame.frame_ptr; - data_ind.msduLength = mpx_frame.frame_length; - user_cb->data_ind(&base->mpx_data_base.mpx_api, &data_ind); - return; } } @@ -1401,6 +1334,7 @@ static void ws_init_temporary_neigh_data(ws_neighbor_temp_class_t *entry, const entry->neigh_info_list.rsl_in = RSL_UNITITIALIZED; entry->neigh_info_list.rsl_out = RSL_UNITITIALIZED; memcpy(entry->mac64, mac64, 8); + entry->eapol_temp_info.eapol_rx_relay_filter = 0; } @@ -1725,13 +1659,51 @@ void ws_llc_timer_seconds(struct protocol_interface_info_entry *interface, uint1 } ns_list_foreach_safe(ws_neighbor_temp_class_t, entry, &base->temp_entries->active_eapol_temp_neigh) { - if (entry->eapol_timeout <= seconds_update) { + if (entry->eapol_temp_info.eapol_timeout <= seconds_update) { ns_list_remove(&base->temp_entries->active_eapol_temp_neigh, entry); ns_list_add_to_end(&base->temp_entries->free_temp_neigh, entry); } else { - entry->eapol_timeout -= seconds_update; + entry->eapol_temp_info.eapol_timeout -= seconds_update; + if (entry->eapol_temp_info.eapol_rx_relay_filter == 0) { + //No active filter period + continue; + } + + //Update filter time + if (entry->eapol_temp_info.eapol_rx_relay_filter <= seconds_update) { + entry->eapol_temp_info.eapol_rx_relay_filter = 0; + } else { + entry->eapol_temp_info.eapol_rx_relay_filter -= seconds_update; + } } } } +bool ws_llc_eapol_relay_forward_filter(struct protocol_interface_info_entry *interface, const uint8_t *joiner_eui64, uint8_t mac_sequency, uint32_t rx_timestamp) +{ + llc_data_base_t *base = ws_llc_discover_by_interface(interface); + if (!base) { + return false; + } + + ws_neighbor_temp_class_t *neighbor = ws_llc_discover_eapol_temp_entry(base->temp_entries, joiner_eui64); + if (!neighbor) { + llc_neighbour_req_t neighbor_info; + //Discover here Normal Neighbour + if (!base->ws_neighbor_info_request_cb(interface, joiner_eui64, &neighbor_info, false)) { + return false; + } + return ws_neighbor_class_neighbor_duplicate_packet_check(neighbor_info.ws_neighbor, mac_sequency, rx_timestamp); + } + + if (neighbor->eapol_temp_info.eapol_rx_relay_filter && neighbor->eapol_temp_info.last_rx_mac_sequency == mac_sequency) { + return false; + } + neighbor->eapol_temp_info.last_rx_mac_sequency = mac_sequency; + neighbor->eapol_temp_info.eapol_rx_relay_filter = 6; //Activate 5-5.99 seconds filter time + return true; + +} + + #endif diff --git a/source/6LoWPAN/ws/ws_management_api.c b/source/6LoWPAN/ws/ws_management_api.c index cd4ce0cd80..ef9e9cffbd 100644 --- a/source/6LoWPAN/ws/ws_management_api.c +++ b/source/6LoWPAN/ws/ws_management_api.c @@ -41,9 +41,11 @@ int ws_management_node_init( protocol_interface_info_entry_t *cur; cur = protocol_stack_interface_info_get_by_id(interface_id); + if (interface_id >= 0 && (!cur || !ws_info(cur))) { return -1; } + if (!network_name_ptr || !fhss_timer_ptr) { return -2; } @@ -70,7 +72,9 @@ int ws_management_node_init( return -4; } - cur->ws_info->fhss_timer_ptr = fhss_timer_ptr; + if (cur && ws_info(cur)) { + cur->ws_info->fhss_timer_ptr = fhss_timer_ptr; + } return 0; } @@ -398,7 +402,7 @@ int ws_management_channel_plan_set( protocol_interface_info_entry_t *cur; cur = protocol_stack_interface_info_get_by_id(interface_id); - if (interface_id >= 0 && (!cur || !ws_info(cur))) { + if (!cur || !ws_info(cur)) { return -1; } cur->ws_info->hopping_schdule.channel_plan = channel_plan; diff --git a/source/6LoWPAN/ws/ws_neighbor_class.c b/source/6LoWPAN/ws/ws_neighbor_class.c index 7e4e7eedc0..214c46f871 100644 --- a/source/6LoWPAN/ws/ws_neighbor_class.c +++ b/source/6LoWPAN/ws/ws_neighbor_class.c @@ -322,5 +322,32 @@ void ws_neighbor_class_rsl_out_calculate(ws_neighbor_class_entry_t *ws_neighbor, return; } + +bool ws_neighbor_class_neighbor_duplicate_packet_check(ws_neighbor_class_entry_t *ws_neighbor, uint8_t mac_dsn, uint32_t rx_timestamp) +{ + if (ws_neighbor->last_DSN != mac_dsn) { + // New packet allways accepted + ws_neighbor->last_DSN = mac_dsn; + return true; + } + + if (!ws_neighbor->unicast_data_rx) { + // No unicast info stored always accepted + return true; + } + + rx_timestamp -= ws_neighbor->fhss_data.uc_timing_info.utt_rx_timestamp; + rx_timestamp /= 1000000; //Convert to s + + //Compare only when last rx timestamp is less than 5 seconds + if (rx_timestamp < 5) { + //Packet is sent too fast filter it out + return false; + } + + return true; +} + + #endif /* HAVE_WS */ diff --git a/source/6LoWPAN/ws/ws_neighbor_class.h b/source/6LoWPAN/ws/ws_neighbor_class.h index c381b43f50..f470a25a8b 100644 --- a/source/6LoWPAN/ws/ws_neighbor_class.h +++ b/source/6LoWPAN/ws/ws_neighbor_class.h @@ -28,6 +28,7 @@ typedef struct ws_neighbor_class_entry { uint16_t rsl_in; /*!< RSL EWMA heard from neighbour*/ uint16_t rsl_out; /*!< RSL EWMA heard by neighbour*/ uint16_t routing_cost; /*!< ETX to border Router. */ + uint8_t last_DSN; bool candidate_parent: 1; bool broadcast_timing_info_stored: 1; bool broadcast_shedule_info_stored: 1; @@ -181,4 +182,6 @@ void ws_neighbor_class_rsl_in_calculate(ws_neighbor_class_entry_t *ws_neighbor, */ void ws_neighbor_class_rsl_out_calculate(ws_neighbor_class_entry_t *ws_neighbor, uint8_t rsl_reported); +bool ws_neighbor_class_neighbor_duplicate_packet_check(ws_neighbor_class_entry_t *ws_neighbor, uint8_t mac_dsn, uint32_t rx_timestamp); + #endif /* WS_NEIGHBOR_CLASS_H_ */ diff --git a/source/6LoWPAN/ws/ws_pae_auth.c b/source/6LoWPAN/ws/ws_pae_auth.c index b28f929f15..077c3ae580 100644 --- a/source/6LoWPAN/ws/ws_pae_auth.c +++ b/source/6LoWPAN/ws/ws_pae_auth.c @@ -59,19 +59,18 @@ #define PAE_TASKLET_EVENT 2 #define PAE_TASKLET_TIMER 3 -// Wait for for supplicant to indicate activity (e.g. to send a message) -#define WAIT_FOR_AUTHENTICATION_TICKS 5 * 60 * 10 // 5 minutes - +/* Wait for supplicant to indicate activity (e.g. to send a message) when + authentication is ongoing */ +#define WAIT_FOR_AUTHENTICATION_TICKS 2 * 60 * 10 // 2 minutes +// Wait after authentication has completed before supplicant entry goes inactive +#define WAIT_AFTER_AUTHENTICATION_TICKS 15 * 10 // 15 seconds /* If EAP-TLS is delayed due to simultaneous negotiations limit, defines how long to wait for previous negotiation to complete */ #define EAP_TLS_NEGOTIATION_TRIGGER_TIMEOUT 60 * 10 // 60 seconds // Default for maximum number of supplicants -#define SUPPLICANT_MAX_NUMBER 1000 - -// Default for maximum number of active supplicants (making security negotiations) -#define ACTIVE_SUPPLICANT_MAX_NUMBER 100 +#define SUPPLICANT_MAX_NUMBER 5000 /* Default for number of supplicants to purge per garbage collect call from nanostack monitor */ @@ -99,7 +98,6 @@ typedef struct { sec_timer_cfg_t *sec_timer_cfg; /**< Timer configuration */ sec_prot_cfg_t *sec_prot_cfg; /**< Protocol Configuration */ uint16_t supp_max_number; /**< Max number of stored supplicants */ - uint16_t slow_timer_seconds; /**< Slow timer seconds */ bool timer_running : 1; /**< Timer is running */ bool gtk_new_inst_req_exp : 1; /**< GTK new install required timer expired */ bool gtk_new_act_time_exp: 1; /**< GTK new activation time expired */ @@ -128,7 +126,7 @@ static void ws_pae_auth_kmp_api_create_indication(kmp_api_t *kmp, kmp_type_e typ static void ws_pae_auth_kmp_api_finished_indication(kmp_api_t *kmp, kmp_result_e result, kmp_sec_keys_t *sec_keys); static void ws_pae_auth_next_kmp_trigger(pae_auth_t *pae_auth, supp_entry_t *supp_entry); static kmp_type_e ws_pae_auth_next_protocol_get(pae_auth_t *pae_auth, supp_entry_t *supp_entry); -static kmp_api_t *ws_pae_auth_kmp_create_and_start(kmp_service_t *service, kmp_type_e type, supp_entry_t *supp_entry, sec_prot_cfg_t *cfg); +static kmp_api_t *ws_pae_auth_kmp_create_and_start(kmp_service_t *service, kmp_type_e type, supp_entry_t *supp_entry, sec_prot_cfg_t *prot_cfg, sec_timer_cfg_t *timer_cfg); static void ws_pae_auth_kmp_api_finished(kmp_api_t *kmp); static int8_t tasklet_id = -1; @@ -168,7 +166,6 @@ int8_t ws_pae_auth_init(protocol_interface_info_entry_t *interface_ptr, sec_prot pae_auth->sec_prot_cfg = sec_prot_cfg; pae_auth->supp_max_number = SUPPLICANT_MAX_NUMBER; - pae_auth->slow_timer_seconds = 0; pae_auth->gtk_new_inst_req_exp = false; pae_auth->gtk_new_act_time_exp = false; @@ -709,11 +706,7 @@ void ws_pae_auth_slow_timer(uint16_t seconds) } } - pae_auth->slow_timer_seconds += seconds; - if (pae_auth->slow_timer_seconds > 60) { - ws_pae_lib_supp_list_slow_timer_update(&pae_auth->active_supp_list, pae_auth->sec_timer_cfg, pae_auth->slow_timer_seconds); - pae_auth->slow_timer_seconds = 0; - } + ws_pae_lib_supp_list_slow_timer_update(&pae_auth->active_supp_list, seconds); } // Update key storage timer @@ -871,7 +864,7 @@ static kmp_api_t *ws_pae_auth_kmp_incoming_ind(kmp_service_t *service, kmp_type_ if (!supp_entry) { // Checks if active supplicant list has space for new supplicants - if (ws_pae_lib_supp_list_active_limit_reached(&pae_auth->active_supp_list, ACTIVE_SUPPLICANT_MAX_NUMBER)) { + if (ws_pae_lib_supp_list_active_limit_reached(&pae_auth->active_supp_list, pae_auth->sec_prot_cfg->sec_max_ongoing_authentication)) { tr_debug("PAE: active limit reached, eui-64: %s", trace_array(kmp_address_eui_64_get(addr), 8)); return NULL; } @@ -906,7 +899,7 @@ static kmp_api_t *ws_pae_auth_kmp_incoming_ind(kmp_service_t *service, kmp_type_ } // Create a new KMP for initial eapol-key - kmp = kmp_api_create(service, type + IEEE_802_1X_INITIAL_KEY, pae_auth->sec_prot_cfg); + kmp = kmp_api_create(service, type + IEEE_802_1X_INITIAL_KEY, pae_auth->sec_prot_cfg, pae_auth->sec_timer_cfg); if (!kmp) { return 0; @@ -986,6 +979,8 @@ static void ws_pae_auth_next_kmp_trigger(pae_auth_t *pae_auth, supp_entry_t *sup kmp_type_e next_type = ws_pae_auth_next_protocol_get(pae_auth, supp_entry); if (next_type == KMP_TYPE_NONE) { + // Supplicant goes inactive after 15 seconds + ws_pae_lib_supp_timer_ticks_set(supp_entry, WAIT_AFTER_AUTHENTICATION_TICKS); // All done return; } else { @@ -1019,7 +1014,7 @@ static void ws_pae_auth_next_kmp_trigger(pae_auth_t *pae_auth, supp_entry_t *sup } // Create new instance - kmp_api_t *new_kmp = ws_pae_auth_kmp_create_and_start(pae_auth->kmp_service, next_type, supp_entry, pae_auth->sec_prot_cfg); + kmp_api_t *new_kmp = ws_pae_auth_kmp_create_and_start(pae_auth->kmp_service, next_type, supp_entry, pae_auth->sec_prot_cfg, pae_auth->sec_timer_cfg); if (!new_kmp) { return; } @@ -1032,7 +1027,7 @@ static void ws_pae_auth_next_kmp_trigger(pae_auth_t *pae_auth, supp_entry_t *sup return; } // Create TLS instance */ - if (ws_pae_auth_kmp_create_and_start(pae_auth->kmp_service, TLS_PROT, supp_entry, pae_auth->sec_prot_cfg) == NULL) { + if (ws_pae_auth_kmp_create_and_start(pae_auth->kmp_service, TLS_PROT, supp_entry, pae_auth->sec_prot_cfg, pae_auth->sec_timer_cfg) == NULL) { ws_pae_lib_kmp_list_delete(&supp_entry->kmp_list, new_kmp); return; } @@ -1099,10 +1094,10 @@ static kmp_type_e ws_pae_auth_next_protocol_get(pae_auth_t *pae_auth, supp_entry return next_type; } -static kmp_api_t *ws_pae_auth_kmp_create_and_start(kmp_service_t *service, kmp_type_e type, supp_entry_t *supp_entry, sec_prot_cfg_t *cfg) +static kmp_api_t *ws_pae_auth_kmp_create_and_start(kmp_service_t *service, kmp_type_e type, supp_entry_t *supp_entry, sec_prot_cfg_t *prot_cfg, sec_timer_cfg_t *timer_cfg) { // Create KMP instance for new authentication - kmp_api_t *kmp = kmp_api_create(service, type, cfg); + kmp_api_t *kmp = kmp_api_create(service, type, prot_cfg, timer_cfg); if (!kmp) { return NULL; diff --git a/source/6LoWPAN/ws/ws_pae_controller.c b/source/6LoWPAN/ws/ws_pae_controller.c index c040b97bb0..05eb06983b 100644 --- a/source/6LoWPAN/ws/ws_pae_controller.c +++ b/source/6LoWPAN/ws/ws_pae_controller.c @@ -72,7 +72,8 @@ typedef struct { uint8_t gtkhash[32]; /**< GTK hashes */ sec_prot_certs_t certs; /**< Certificates */ nw_key_t nw_key[GTK_NUM]; /**< Currently active network keys (on MAC) */ - uint16_t frame_cnt_store_timer; /**< Timer for storing frame counter value */ + uint16_t frame_cnt_store_timer; /**< Timer to check if storing of frame counter value is needed */ + uint32_t frame_cnt_store_force_timer; /**< Timer to force storing of frame counter, if no other updates */ frame_counters_t frame_counters; /**< Frame counters */ sec_timer_cfg_t sec_timer_cfg; /**< Timer configuration (configuration set values) */ sec_prot_cfg_t sec_prot_cfg; /**< Configuration */ @@ -86,6 +87,7 @@ typedef struct { ws_pae_controller_nw_frame_counter_read *nw_frame_counter_read; /**< Frame counter read callback */ ws_pae_controller_pan_ver_increment *pan_ver_increment; /**< PAN version increment callback */ ws_pae_controller_nw_info_updated *nw_info_updated; /**< Network information updated callback */ + ws_pae_controller_auth_next_target *auth_next_target; /**< Authentication next target callback */ ws_pae_delete *pae_delete; /**< PAE delete callback */ ws_pae_timer *pae_fast_timer; /**< PAE fast timer callback */ ws_pae_timer *pae_slow_timer; /**< PAE slow timer callback */ @@ -164,7 +166,7 @@ int8_t ws_pae_controller_authenticate(protocol_interface_info_entry_t *interface return 0; } - if (ws_pae_supp_authenticate(controller->interface_ptr, controller->target_pan_id, controller->target_eui_64) < 0) { + if (ws_pae_supp_authenticate(controller->interface_ptr, controller->target_pan_id, controller->target_eui_64, controller->sec_keys_nw_info.network_name) < 0) { controller->auth_completed(interface_ptr, AUTH_RESULT_ERR_UNSPEC, controller->target_eui_64); } #endif @@ -220,7 +222,7 @@ int8_t ws_pae_controller_authenticator_start(protocol_interface_info_entry_t *in return 0; } -int8_t ws_pae_controller_cb_register(protocol_interface_info_entry_t *interface_ptr, ws_pae_controller_auth_completed *completed, ws_pae_controller_nw_key_set *nw_key_set, ws_pae_controller_nw_key_clear *nw_key_clear, ws_pae_controller_nw_send_key_index_set *nw_send_key_index_set, ws_pae_controller_nw_frame_counter_set *nw_frame_counter_set, ws_pae_controller_nw_frame_counter_read *nw_frame_counter_read, ws_pae_controller_pan_ver_increment *pan_ver_increment, ws_pae_controller_nw_info_updated *nw_info_updated) +int8_t ws_pae_controller_cb_register(protocol_interface_info_entry_t *interface_ptr, ws_pae_controller_auth_completed *completed, ws_pae_controller_auth_next_target *auth_next_target, ws_pae_controller_nw_key_set *nw_key_set, ws_pae_controller_nw_key_clear *nw_key_clear, ws_pae_controller_nw_send_key_index_set *nw_send_key_index_set, ws_pae_controller_nw_frame_counter_set *nw_frame_counter_set, ws_pae_controller_nw_frame_counter_read *nw_frame_counter_read, ws_pae_controller_pan_ver_increment *pan_ver_increment, ws_pae_controller_nw_info_updated *nw_info_updated) { if (!interface_ptr) { return -1; @@ -239,7 +241,7 @@ int8_t ws_pae_controller_cb_register(protocol_interface_info_entry_t *interface_ controller->nw_frame_counter_read = nw_frame_counter_read; controller->pan_ver_increment = pan_ver_increment; controller->nw_info_updated = nw_info_updated; - + controller->auth_next_target = auth_next_target; return 0; } @@ -325,7 +327,7 @@ static void ws_pae_controller_nw_info_updated_check(protocol_interface_info_entr } } -int8_t ws_pae_controller_nw_key_valid(protocol_interface_info_entry_t *interface_ptr) +int8_t ws_pae_controller_nw_key_valid(protocol_interface_info_entry_t *interface_ptr, uint8_t *br_iid) { if (!interface_ptr) { return -1; @@ -336,7 +338,7 @@ int8_t ws_pae_controller_nw_key_valid(protocol_interface_info_entry_t *interface return -1; } - return ws_pae_supp_nw_key_valid(interface_ptr); + return ws_pae_supp_nw_key_valid(interface_ptr, br_iid); } static int8_t ws_pae_controller_nw_key_check_and_insert(protocol_interface_info_entry_t *interface_ptr, sec_prot_gtk_keys_t *gtks) @@ -601,6 +603,9 @@ int8_t ws_pae_controller_init(protocol_interface_info_entry_t *interface_ptr) controller->nw_send_key_index_set = NULL; controller->nw_frame_counter_set = NULL; controller->pan_ver_increment = NULL; + controller->nw_info_updated = NULL; + controller->auth_next_target = NULL; + memset(&controller->sec_timer_cfg, 0, sizeof(ws_sec_timer_cfg_t)); memset(&controller->sec_prot_cfg, 0, sizeof(sec_prot_cfg_t)); @@ -624,7 +629,15 @@ int8_t ws_pae_controller_configure(protocol_interface_info_entry_t *interface_pt controller->sec_prot_cfg.sec_prot_trickle_params.k = 0; controller->sec_prot_cfg.sec_prot_trickle_params.TimerExpirations = sec_prot_cfg->sec_prot_trickle_timer_exp; controller->sec_prot_cfg.sec_prot_retry_timeout = sec_prot_cfg->sec_prot_retry_timeout * 10; + controller->sec_prot_cfg.sec_max_ongoing_authentication = sec_prot_cfg->sec_max_ongoing_authentication; + + controller->sec_prot_cfg.initial_key_retry_delay = sec_prot_cfg->initial_key_retry_delay; + controller->sec_prot_cfg.initial_key_trickle_params.Imin = sec_prot_cfg->initial_key_imin; + controller->sec_prot_cfg.initial_key_trickle_params.Imax = sec_prot_cfg->initial_key_imax; + controller->sec_prot_cfg.initial_key_trickle_params.k = 0; + controller->sec_prot_cfg.initial_key_trickle_params.TimerExpirations = 2; + controller->sec_prot_cfg.initial_key_retry_cnt = sec_prot_cfg->initial_key_retry_cnt; } if (sec_timer_cfg) { @@ -661,6 +674,7 @@ static void ws_pae_controller_data_init(pae_controller_t *controller) controller->frame_counter_read = false; controller->gtk_index = -1; controller->frame_cnt_store_timer = FRAME_COUNTER_STORE_INTERVAL; + controller->frame_cnt_store_force_timer = FRAME_COUNTER_STORE_FORCE_INTERVAL; controller->restart_cnt = 0; ws_pae_controller_frame_counter_reset(&controller->frame_counters); sec_prot_keys_gtks_init(&controller->gtks); @@ -791,7 +805,7 @@ int8_t ws_pae_controller_supp_init(protocol_interface_info_entry_t *interface_pt controller->pae_nw_key_index_update = ws_pae_supp_nw_key_index_update; controller->pae_nw_info_set = NULL; - ws_pae_supp_cb_register(controller->interface_ptr, controller->auth_completed, ws_pae_controller_nw_key_check_and_insert, ws_pae_controller_active_nw_key_set, ws_pae_controller_gtk_hash_ptr_get, ws_pae_controller_nw_info_updated_check); + ws_pae_supp_cb_register(controller->interface_ptr, controller->auth_completed, controller->auth_next_target, ws_pae_controller_nw_key_check_and_insert, ws_pae_controller_active_nw_key_set, ws_pae_controller_gtk_hash_ptr_get, ws_pae_controller_nw_info_updated_check); ws_pae_controller_frame_counter_read(controller); ws_pae_controller_nw_info_read(controller, controller->sec_keys_nw_info.gtks); @@ -1369,6 +1383,13 @@ static void ws_pae_controller_frame_counter_timer(uint16_t seconds, pae_controll entry->frame_cnt_store_timer = FRAME_COUNTER_STORE_INTERVAL; ws_pae_controller_frame_counter_store(entry, true); } + + if (entry->frame_cnt_store_force_timer > seconds) { + entry->frame_cnt_store_force_timer -= seconds; + } else { + entry->frame_cnt_store_force_timer = 0; + ws_pae_controller_frame_counter_store(entry, true); + } } static void ws_pae_controller_frame_counter_timer_trigger(uint16_t seconds, pae_controller_t *entry) @@ -1422,11 +1443,14 @@ static void ws_pae_controller_frame_counter_store(pae_controller_t *entry, bool } } - if (update_needed) { + if (update_needed || entry->frame_cnt_store_force_timer == 0) { tr_debug("Write frame counters: system time %"PRIu32"", protocol_core_monotonic_time / 10); // Writes modified frame counters ws_pae_nvm_store_frame_counter_tlv_create((nvm_tlv_t *) &entry->pae_nvm_buffer, entry->restart_cnt, &entry->frame_counters); ws_pae_controller_nvm_frame_counter_write((nvm_tlv_t *) &entry->pae_nvm_buffer); + + // Reset force interval when ever values are stored + entry->frame_cnt_store_force_timer = FRAME_COUNTER_STORE_FORCE_INTERVAL; } } diff --git a/source/6LoWPAN/ws/ws_pae_controller.h b/source/6LoWPAN/ws/ws_pae_controller.h index d24ba6319d..2f7e01e6df 100644 --- a/source/6LoWPAN/ws/ws_pae_controller.h +++ b/source/6LoWPAN/ws/ws_pae_controller.h @@ -249,12 +249,13 @@ int8_t ws_pae_controller_nw_info_set(protocol_interface_info_entry_t *interface_ * ws_pae_controller_nw_key_valid network key is valid i.e. used successfully on bootstrap * * \param interface_ptr interface + * \param br_iid border router IID for which the keys are valid * * \return < 0 failure * \return >= 0 success * */ -int8_t ws_pae_controller_nw_key_valid(protocol_interface_info_entry_t *interface_ptr); +int8_t ws_pae_controller_nw_key_valid(protocol_interface_info_entry_t *interface_ptr, uint8_t *br_iid); /** * ws_pae_controller_border_router_addr_write write border router address @@ -278,7 +279,7 @@ int8_t ws_pae_controller_border_router_addr_write(protocol_interface_info_entry_ * \return >= 0 success * */ -int8_t ws_pae_controller_border_router_addr_read(protocol_interface_info_entry_t *interface_ptr, uint8_t *eui_64); +int8_t ws_pae_controller_border_router_addr_read(protocol_interface_info_entry_t *interface_ptr, uint8_t *iid); /** * ws_pae_controller_gtk_update update GTKs (test interface) @@ -492,6 +493,18 @@ typedef void ws_pae_controller_nw_frame_counter_read(protocol_interface_info_ent */ typedef void ws_pae_controller_auth_completed(protocol_interface_info_entry_t *interface_ptr, auth_result_e result, uint8_t *target_eui_64); +/** + * ws_pae_controller_auth_next_target get next target to attempt authentication + * + * \param interface_ptr interface + * \param previous_eui_64 EUI-64 of previous target + * \param pan_id pan id + * + * \return EUI-64 of the next target or previous target if new one not available + * + */ +typedef const uint8_t *ws_pae_controller_auth_next_target(protocol_interface_info_entry_t *interface_ptr, const uint8_t *previous_eui_64, uint16_t *pan_id); + /** * ws_pae_controller_pan_ver_increment PAN version increment callback * @@ -515,6 +528,7 @@ typedef void ws_pae_controller_nw_info_updated(protocol_interface_info_entry_t * * * \param interface_ptr interface * \param completed authentication completed callback + * \param next_target authentication next target callback * \param nw_key_set network key set callback * \param nw_key_clear network key clear callback * \param nw_send_key_index_set network send key index set callback @@ -527,7 +541,7 @@ typedef void ws_pae_controller_nw_info_updated(protocol_interface_info_entry_t * * \return >= 0 success * */ -int8_t ws_pae_controller_cb_register(protocol_interface_info_entry_t *interface_ptr, ws_pae_controller_auth_completed *completed, ws_pae_controller_nw_key_set *nw_key_set, ws_pae_controller_nw_key_clear *nw_key_clear, ws_pae_controller_nw_send_key_index_set *nw_send_key_index_set, ws_pae_controller_nw_frame_counter_set *nw_frame_counter_set, ws_pae_controller_nw_frame_counter_read *nw_frame_counter_read, ws_pae_controller_pan_ver_increment *pan_ver_increment, ws_pae_controller_nw_info_updated *nw_info_updated); +int8_t ws_pae_controller_cb_register(protocol_interface_info_entry_t *interface_ptr, ws_pae_controller_auth_completed *completed, ws_pae_controller_auth_next_target *auth_next_target, ws_pae_controller_nw_key_set *nw_key_set, ws_pae_controller_nw_key_clear *nw_key_clear, ws_pae_controller_nw_send_key_index_set *nw_send_key_index_set, ws_pae_controller_nw_frame_counter_set *nw_frame_counter_set, ws_pae_controller_nw_frame_counter_read *nw_frame_counter_read, ws_pae_controller_pan_ver_increment *pan_ver_increment, ws_pae_controller_nw_info_updated *nw_info_updated); /** * ws_pae_controller_fast_timer PAE controller fast timer call diff --git a/source/6LoWPAN/ws/ws_pae_key_storage.c b/source/6LoWPAN/ws/ws_pae_key_storage.c index 556f6c068c..b50dfb0302 100644 --- a/source/6LoWPAN/ws/ws_pae_key_storage.c +++ b/source/6LoWPAN/ws/ws_pae_key_storage.c @@ -87,6 +87,7 @@ typedef struct { } key_storage_array_t; typedef struct { + uint8_t settings_set; /**< Settings set, do not use defaults */ uint8_t storages_empty; /**< Number of empty i.e. to be allocated storages */ uint16_t storage_default_size; /**< Default size for storages */ uint16_t replace_index; /**< Index to replace when storages are full */ @@ -138,6 +139,7 @@ int8_t ws_pae_key_storage_memory_set(uint8_t key_storages_number, const uint16_t int8_t ws_pae_key_storage_settings_set(uint8_t alloc_max_number, uint16_t alloc_size, uint16_t storing_interval) { + key_storage_params.settings_set = true; key_storage_params.storages_empty = alloc_max_number; key_storage_params.storage_default_size = alloc_size; key_storage_params.store_timer = storing_interval; @@ -148,18 +150,19 @@ int8_t ws_pae_key_storage_settings_set(uint8_t alloc_max_number, uint16_t alloc_ void ws_pae_key_storage_init(void) { - key_storage_params.storages_empty = DEFAULT_NUMBER_OF_STORAGES; - key_storage_params.storage_default_size = STORAGE_ARRAY_HEADER_LEN + (sizeof(sec_prot_keys_storage_t) * DEFAULT_NUMBER_OF_ENTRIES_IN_ONE_STORAGE); + if (!key_storage_params.settings_set) { + key_storage_params.storages_empty = DEFAULT_NUMBER_OF_STORAGES; + key_storage_params.storage_default_size = STORAGE_ARRAY_HEADER_LEN + (sizeof(sec_prot_keys_storage_t) * DEFAULT_NUMBER_OF_ENTRIES_IN_ONE_STORAGE); + key_storage_params.store_timer = DEFAULT_STORING_INTERVAL; + key_storage_params.store_timer_timeout = DEFAULT_STORING_INTERVAL; + } key_storage_params.replace_index = 0; key_storage_params.store_bitfield = 0, - key_storage_params.store_timer_timeout = DEFAULT_STORING_INTERVAL; - key_storage_params.store_timer = DEFAULT_STORING_INTERVAL; key_storage_params.restart_cnt = 0; } void ws_pae_key_storage_delete(void) { - memset(&key_storage_params, 0, sizeof(key_storage_params_t)); ws_pae_key_storage_list_all_free(); } diff --git a/source/6LoWPAN/ws/ws_pae_lib.c b/source/6LoWPAN/ws/ws_pae_lib.c index 697e2f04ea..d47aff8a8f 100644 --- a/source/6LoWPAN/ws/ws_pae_lib.c +++ b/source/6LoWPAN/ws/ws_pae_lib.c @@ -26,8 +26,8 @@ #include "NWK_INTERFACE/Include/protocol.h" #include "6LoWPAN/ws/ws_cfg_settings.h" #include "6LoWPAN/ws/ws_config.h" -#include "6LoWPAN/ws/ws_pae_timers.h" #include "Security/protocols/sec_prot_cfg.h" +#include "6LoWPAN/ws/ws_pae_timers.h" #include "Security/kmp/kmp_addr.h" #include "Security/kmp/kmp_api.h" #include "Security/protocols/sec_prot_certs.h" @@ -242,17 +242,16 @@ bool ws_pae_lib_supp_list_timer_update(void *instance, supp_list_t *active_supp_ return timer_running; } -void ws_pae_lib_supp_list_slow_timer_update(supp_list_t *supp_list, sec_timer_cfg_t *timer_settings, uint16_t seconds) +void ws_pae_lib_supp_list_slow_timer_update(supp_list_t *supp_list, uint16_t seconds) { ns_list_foreach(supp_entry_t, entry, supp_list) { - if (sec_prot_keys_pmk_lifetime_decrement(&entry->sec_keys, timer_settings->pmk_lifetime, seconds)) { + if (sec_prot_keys_pmk_lifetime_decrement(&entry->sec_keys, seconds)) { tr_info("PMK and PTK expired, eui-64: %s, system time: %"PRIu32"", trace_array(entry->addr.eui_64, 8), protocol_core_monotonic_time / 10); } - if (sec_prot_keys_ptk_lifetime_decrement(&entry->sec_keys, timer_settings->ptk_lifetime, seconds)) { + if (sec_prot_keys_ptk_lifetime_decrement(&entry->sec_keys, seconds)) { tr_info("PTK expired, eui-64: %s, system time: %"PRIu32"", trace_array(entry->addr.eui_64, 8), protocol_core_monotonic_time / 10); } } - } void ws_pae_lib_supp_init(supp_entry_t *entry) diff --git a/source/6LoWPAN/ws/ws_pae_lib.h b/source/6LoWPAN/ws/ws_pae_lib.h index d469c4c55a..eed138e74c 100644 --- a/source/6LoWPAN/ws/ws_pae_lib.h +++ b/source/6LoWPAN/ws/ws_pae_lib.h @@ -252,11 +252,10 @@ bool ws_pae_lib_supp_list_timer_update(void *instance, supp_list_t *active_supp_ * ws_pae_lib_supp_list_slow_timer_update updates slow timer on supplicant list * * \param supp_list list of supplicants - * \param timer_settings timer settings * \param seconds seconds * */ -void ws_pae_lib_supp_list_slow_timer_update(supp_list_t *supp_list, sec_timer_cfg_t *timer_settings, uint16_t seconds); +void ws_pae_lib_supp_list_slow_timer_update(supp_list_t *supp_list, uint16_t seconds); /** * ws_pae_lib_supp_list_timer_update updates supplicant timers diff --git a/source/6LoWPAN/ws/ws_pae_nvm_data.c b/source/6LoWPAN/ws/ws_pae_nvm_data.c index 2c0ab29e23..3212240af8 100644 --- a/source/6LoWPAN/ws/ws_pae_nvm_data.c +++ b/source/6LoWPAN/ws/ws_pae_nvm_data.c @@ -204,10 +204,12 @@ void ws_pae_nvm_store_keys_tlv_create(nvm_tlv_t *tlv_entry, sec_prot_keys_t *sec uint8_t *pmk = sec_prot_keys_pmk_get(sec_keys); if (pmk) { *tlv++ = PAE_NVM_FIELD_SET; + uint32_t lifetime = sec_prot_keys_pmk_lifetime_get(sec_keys); + tlv = common_write_32_bit(lifetime, tlv); memcpy(tlv, pmk, PMK_LEN); } else { *tlv++ = PAE_NVM_FIELD_NOT_SET; - memset(tlv, 0, PMK_LEN); + memset(tlv, 0, 4 + PMK_LEN); } tlv += PMK_LEN; @@ -217,10 +219,12 @@ void ws_pae_nvm_store_keys_tlv_create(nvm_tlv_t *tlv_entry, sec_prot_keys_t *sec uint8_t *ptk = sec_prot_keys_ptk_get(sec_keys); if (ptk) { *tlv++ = PAE_NVM_FIELD_SET; + uint32_t lifetime = sec_prot_keys_ptk_lifetime_get(sec_keys); + tlv = common_write_32_bit(lifetime, tlv); memcpy(tlv, ptk, PTK_LEN); } else { *tlv++ = PAE_NVM_FIELD_NOT_SET; - memset(tlv, 0, PTK_LEN); + memset(tlv, 0, 4 + PTK_LEN); } tlv += PTK_LEN; @@ -247,7 +251,11 @@ int8_t ws_pae_nvm_store_keys_tlv_read(nvm_tlv_t *tlv_entry, sec_prot_keys_t *sec // PMK set if (*tlv++ == PAE_NVM_FIELD_SET) { - sec_prot_keys_pmk_write(sec_keys, tlv); + uint32_t lifetime = common_read_32_bit(tlv); + tlv += 4; + sec_prot_keys_pmk_write(sec_keys, tlv, lifetime); + } else { + tlv += 4; } tlv += PMK_LEN; @@ -257,7 +265,11 @@ int8_t ws_pae_nvm_store_keys_tlv_read(nvm_tlv_t *tlv_entry, sec_prot_keys_t *sec // PTK set if (*tlv++ == PAE_NVM_FIELD_SET) { - sec_prot_keys_ptk_write(sec_keys, tlv); + uint32_t lifetime = common_read_32_bit(tlv); + tlv += 4; + sec_prot_keys_ptk_write(sec_keys, tlv, lifetime); + } else { + tlv += 4; } tlv += PTK_LEN; diff --git a/source/6LoWPAN/ws/ws_pae_nvm_data.h b/source/6LoWPAN/ws/ws_pae_nvm_data.h index 438cf508d0..c55d56412b 100644 --- a/source/6LoWPAN/ws/ws_pae_nvm_data.h +++ b/source/6LoWPAN/ws/ws_pae_nvm_data.h @@ -38,8 +38,8 @@ // pan_id (2) + network name (33) + (GTK set (1) + GTK expiry timestamp (8) + status (1) + install order (1) + GTK (16)) * 4 #define PAE_NVM_NW_INFO_LEN 2 + 33 + (1 + 8 + 1 + 1 + GTK_LEN) * GTK_NUM -// PTK EUI-64 set (1) + PTK EUI-64 (8) + PMK set (1) + PMK (32) + PMK replay counter (8) + PTK set (1) + PTK (48) -#define PAE_NVM_KEYS_LEN 1 + 8 + 1 + PMK_LEN + 8 + 1 + PTK_LEN +// PTK EUI-64 set (1) + PTK EUI-64 (8) + PMK set (1) + PMK lifetime (4) + PMK (32) + PMK replay counter (8) + PTK set (1) + PTK lifetime (4) + PTK (48) +#define PAE_NVM_KEYS_LEN 1 + 8 + 1 + 4 + PMK_LEN + 8 + 1 + 4 + PTK_LEN // restart counter + stored time + (frame counter set (1) + GTK (16) + frame counter (4)) * 4 #define PAE_NVM_FRAME_COUNTER_LEN 4 + 8 + (1 + GTK_LEN + 4) * GTK_NUM diff --git a/source/6LoWPAN/ws/ws_pae_supp.c b/source/6LoWPAN/ws/ws_pae_supp.c index a5e03ad86a..7954010d50 100644 --- a/source/6LoWPAN/ws/ws_pae_supp.c +++ b/source/6LoWPAN/ws/ws_pae_supp.c @@ -86,6 +86,7 @@ typedef struct { kmp_service_t *kmp_service; /**< KMP service */ protocol_interface_info_entry_t *interface_ptr; /**< Interface */ ws_pae_supp_auth_completed *auth_completed; /**< Authentication completed callback, continue bootstrap */ + ws_pae_supp_auth_next_target *auth_next_target; /**< Authentication next target callback */ ws_pae_supp_nw_key_insert *nw_key_insert; /**< Key insert callback */ ws_pae_supp_nw_key_index_set *nw_key_index_set; /**< Key index set callback */ ws_pae_supp_gtk_hash_ptr_get *gtk_hash_ptr_get; /**< Get pointer to GTK hash storage callback */ @@ -96,7 +97,8 @@ typedef struct { uint16_t initial_key_retry_timer; /**< Timer to trigger initial EAPOL-Key 1st retry */ trickle_t auth_trickle_timer; /**< Trickle timer for re-sending initial EAPOL-key or for GTK mismatch */ trickle_params_t auth_trickle_params; /**< Trickle parameters for initial EAPOL-key or for GTK mismatch */ - uint8_t new_br_eui_64[8]; /**< Border router EUI-64 indicated by bootstrap */ + uint8_t new_br_eui_64[8]; /**< Border router EUI-64 indicated by bootstrap after bootstrap start */ + uint8_t comp_br_eui_64[8]; /**< Border router EUI-64 indicated by bootstrap after bootstrap completed */ sec_prot_keys_nw_info_t *sec_keys_nw_info; /**< Security keys network information */ sec_timer_cfg_t *sec_timer_cfg; /**< Timer configuration */ sec_prot_cfg_t *sec_prot_cfg; /**< Protocol Configuration */ @@ -105,46 +107,26 @@ typedef struct { bool auth_trickle_running : 1; /**< Initial EAPOL-Key Trickle timer running */ bool auth_requested : 1; /**< Authentication has been requested by the bootstrap */ bool timer_running : 1; /**< Timer is running */ - bool new_br_eui_64_set : 1; /**< Border router address has been set */ + bool new_br_eui_64_set : 1; /**< Border router address has been set after bootstrap start */ bool new_br_eui_64_fresh : 1; /**< Border router address is fresh (set during this authentication attempt) */ - bool entry_address_active: 1; + bool comp_br_eui_64_set : 1; /**< Border router address has been set after bootstrap completed */ + bool entry_address_active: 1; /**< EAPOL target address is set */ + bool tx_failure_on_initial_key: 1; /**< TX failure has happened on initial EAPOL-key sequence */ } pae_supp_t; -// How many times sending of initial EAPOL-key is retried -#define INITIAL_KEY_RETRY_COUNT 2 - // How many times sending of initial EAPOL-key is initiated on key update #define KEY_UPDATE_RETRY_COUNT 3 #define LIFETIME_MISMATCH_RETRY_COUNT 1 /* No retries */ -// How long the wait is before the first initial EAPOL-key retry -#define DEFAULT_INITIAL_KEY_RETRY_TIMER 120 -#define NONE_INITIAL_KEY_RETRY_TIMER 0 - -// Default trickle values for sending of initial EAPOL-key -#define DEFAULT_TRICKLE_IMIN_SECS 360 /* 6 to 12 minutes */ -#define DEFAULT_TRICKLE_IMAX_SECS 720 - -// Very slow network values for sending of initial EAPOL-key -#define VERY_SLOW_NW_TRICKLE_IMIN_SECS 600 /* 10 to 60 minutes */ -#define VERY_SLOW_NW_TRICKLE_IMAX_SECS 3600 - // Trickle timer on how long to wait response after last retry before failing authentication #define LAST_INTERVAL_TRICKLE_IMIN_SECS 240 /* 4 minutes */ #define LAST_INTERVAL_TRICKLE_IMAX_SECS 240 -static trickle_params_t initial_eapol_key_trickle_params = { - .Imin = DEFAULT_TRICKLE_IMIN_SECS, /* 360 second; ticks are 1 second */ - .Imax = DEFAULT_TRICKLE_IMAX_SECS, /* 720 second */ - .k = 0, /* infinity - no consistency checking */ - .TimerExpirations = 2 -}; - static void ws_pae_supp_free(pae_supp_t *pae_supp); static void ws_pae_supp_authenticate_response(pae_supp_t *pae_supp, auth_result_e result); static int8_t ws_pae_supp_initial_key_send(pae_supp_t *pae_supp); static void ws_pae_supp_nvm_update(pae_supp_t *pae_supp); -static int8_t ws_pae_supp_nw_keys_valid_check(pae_supp_t *pae_supp, uint16_t pan_id); +static int8_t ws_pae_supp_nw_keys_valid_check(pae_supp_t *pae_supp, uint16_t pan_id, char *dest_network_name); static int8_t ws_pae_supp_nvm_keys_write(pae_supp_t *pae_supp); static pae_supp_t *ws_pae_supp_get(protocol_interface_info_entry_t *interface_ptr); static int8_t ws_pae_supp_event_send(kmp_service_t *service, void *data); @@ -175,6 +157,7 @@ static void ws_pae_supp_kmp_api_finished(kmp_api_t *kmp); static const eapol_pdu_recv_cb_data_t eapol_pdu_recv_cb_data = { .priority = EAPOL_PDU_RECV_HIGH_PRIORITY, + .filter_requsted = false, .addr_check = ws_pae_supp_eapol_pdu_address_check, .receive = kmp_eapol_pdu_if_receive }; @@ -183,7 +166,6 @@ static const char *KEYS_FILE = KEYS_FILE_NAME; static int8_t tasklet_id = -1; static NS_LIST_DEFINE(pae_supp_list, pae_supp_t, link); -static uint8_t timing_value = 0; // Timing value set based e.g. on network size static void ws_pae_supp_address_set(pae_supp_t *pae_supp, kmp_addr_t *address) { @@ -201,14 +183,14 @@ static bool ws_pae_supp_address_is_set(pae_supp_t *pae_supp) return pae_supp->entry_address_active; } -int8_t ws_pae_supp_authenticate(protocol_interface_info_entry_t *interface_ptr, uint16_t dest_pan_id, uint8_t *dest_eui_64) +int8_t ws_pae_supp_authenticate(protocol_interface_info_entry_t *interface_ptr, uint16_t dest_pan_id, uint8_t *dest_eui_64, char *dest_network_name) { pae_supp_t *pae_supp = ws_pae_supp_get(interface_ptr); if (!pae_supp) { return -1; } - if (ws_pae_supp_nw_keys_valid_check(pae_supp, dest_pan_id) >= 0) { + if (ws_pae_supp_nw_keys_valid_check(pae_supp, dest_pan_id, dest_network_name) >= 0) { pae_supp->auth_completed(interface_ptr, AUTH_RESULT_OK, NULL); return 0; } @@ -216,9 +198,10 @@ int8_t ws_pae_supp_authenticate(protocol_interface_info_entry_t *interface_ptr, // Delete GTKs sec_prot_keys_gtks_init(pae_supp->sec_keys_nw_info->gtks); - /* PAN ID has changed, delete key data associated with border router + /* Network name or PAN ID has changed, delete key data associated with border router i.e PMK, PTK, EA-IE data (border router EUI-64) */ - if (pae_supp->sec_keys_nw_info->key_pan_id != 0xFFFF && pae_supp->sec_keys_nw_info->key_pan_id != dest_pan_id) { + if (strcmp(pae_supp->sec_keys_nw_info->network_name, dest_network_name) != 0 || + (pae_supp->sec_keys_nw_info->key_pan_id != 0xFFFF && pae_supp->sec_keys_nw_info->key_pan_id != dest_pan_id)) { sec_prot_keys_pmk_delete(&pae_supp->entry.sec_keys); sec_prot_keys_ptk_delete(&pae_supp->entry.sec_keys); sec_prot_keys_ptk_eui_64_delete(&pae_supp->entry.sec_keys); @@ -228,6 +211,7 @@ int8_t ws_pae_supp_authenticate(protocol_interface_info_entry_t *interface_ptr, // Prepare to receive new border router address pae_supp->new_br_eui_64_fresh = false; + pae_supp->comp_br_eui_64_set = false; // Stores target/parent address kmp_address_init(KMP_ADDR_EUI_64, &pae_supp->target_addr, dest_eui_64); @@ -268,9 +252,14 @@ int8_t ws_pae_supp_border_router_addr_read(protocol_interface_info_entry_t *inte return -1; } + // Check if there is border router EUI-64 on used on 4WH PTK generation uint8_t *br_eui_64 = sec_prot_keys_ptk_eui_64_get(&pae_supp->entry.sec_keys); if (!br_eui_64) { - return -1; + // Check if there is border router EUI-64 indicated by the bootstrap when bootstrap completed + if (!pae_supp->comp_br_eui_64_set) { + return -1; + } + br_eui_64 = pae_supp->comp_br_eui_64; } memcpy(eui_64, br_eui_64, 8); @@ -278,14 +267,31 @@ int8_t ws_pae_supp_border_router_addr_read(protocol_interface_info_entry_t *inte return 0; } -int8_t ws_pae_supp_nw_key_valid(protocol_interface_info_entry_t *interface_ptr) +int8_t ws_pae_supp_nw_key_valid(protocol_interface_info_entry_t *interface_ptr, uint8_t *br_iid) { pae_supp_t *pae_supp = ws_pae_supp_get(interface_ptr); if (!pae_supp) { return -1; } - tr_info("NW key valid"); + tr_info("NW key valid indication"); + + // Store border router EUI-64 received on bootstrap complete + memcpy(pae_supp->comp_br_eui_64, br_iid, 8); + pae_supp->comp_br_eui_64[0] ^= 0x02; + pae_supp->comp_br_eui_64_set = true; + + // Get the EUI-64 used on 4WH handshake PTK generation + uint8_t *ptk_eui_64 = sec_prot_keys_ptk_eui_64_get(&pae_supp->entry.sec_keys); + + /* If border router EUI-64 received on bootstrap complete does not match to + EUI-64 stored with keys, delete keys */ + if (memcmp(ptk_eui_64, pae_supp->comp_br_eui_64, 8) != 0) { + tr_warn("Delete keys: PTK EUI-64 %s does not match to BR EUI-64 %s", tr_array(ptk_eui_64, 8), tr_array(pae_supp->comp_br_eui_64, 8)); + sec_prot_keys_pmk_delete(&pae_supp->entry.sec_keys); + sec_prot_keys_ptk_delete(&pae_supp->entry.sec_keys); + sec_prot_keys_ptk_eui_64_delete(&pae_supp->entry.sec_keys); + } // Stored keys are valid pae_supp->nw_keys_used_cnt = 0; @@ -482,7 +488,7 @@ static int8_t ws_pae_supp_initial_key_send(pae_supp_t *pae_supp) return 0; } -static int8_t ws_pae_supp_nw_keys_valid_check(pae_supp_t *pae_supp, uint16_t pan_id) +static int8_t ws_pae_supp_nw_keys_valid_check(pae_supp_t *pae_supp, uint16_t pan_id, char *dest_network_name) { // Checks how many times authentication has been tried with current network keys if (pae_supp->nw_keys_used_cnt >= STORED_KEYS_MAXIMUM_USE_COUNT) { @@ -497,9 +503,11 @@ static int8_t ws_pae_supp_nw_keys_valid_check(pae_supp_t *pae_supp, uint16_t pan return -1; } - /* Checks if keys match to PAN ID and that needed keys exists (PMK, PTK and a GTK), - and calls inserts function that will update the network keys as needed */ - if ((pan_id == pae_supp->sec_keys_nw_info->key_pan_id) && + /* Checks if keys match to network name and PAN ID and that needed keys exists (PMK, + PTK and a GTK), and calls inserts function that will update the network keys as + needed */ + if ((strcmp(dest_network_name, pae_supp->sec_keys_nw_info->network_name) == 0 && + pan_id == pae_supp->sec_keys_nw_info->key_pan_id) && (sec_prot_keys_gtk_count(pae_supp->sec_keys_nw_info->gtks) > 0) && (sec_prot_keys_pmk_get(&pae_supp->entry.sec_keys) != NULL) && (sec_prot_keys_ptk_get(&pae_supp->entry.sec_keys) != NULL)) { @@ -515,7 +523,7 @@ static int8_t ws_pae_supp_nw_keys_valid_check(pae_supp_t *pae_supp, uint16_t pan } } -void ws_pae_supp_cb_register(protocol_interface_info_entry_t *interface_ptr, ws_pae_supp_auth_completed *completed, ws_pae_supp_nw_key_insert *nw_key_insert, ws_pae_supp_nw_key_index_set *nw_key_index_set, ws_pae_supp_gtk_hash_ptr_get *gtk_hash_ptr_get, ws_pae_supp_nw_info_updated *nw_info_updated) +void ws_pae_supp_cb_register(protocol_interface_info_entry_t *interface_ptr, ws_pae_supp_auth_completed *completed, ws_pae_supp_auth_next_target *auth_next_target, ws_pae_supp_nw_key_insert *nw_key_insert, ws_pae_supp_nw_key_index_set *nw_key_index_set, ws_pae_supp_gtk_hash_ptr_get *gtk_hash_ptr_get, ws_pae_supp_nw_info_updated *nw_info_updated) { pae_supp_t *pae_supp = ws_pae_supp_get(interface_ptr); if (!pae_supp) { @@ -523,6 +531,7 @@ void ws_pae_supp_cb_register(protocol_interface_info_entry_t *interface_ptr, ws_ } pae_supp->auth_completed = completed; + pae_supp->auth_next_target = auth_next_target; pae_supp->nw_key_insert = nw_key_insert; pae_supp->nw_key_index_set = nw_key_index_set; pae_supp->gtk_hash_ptr_get = gtk_hash_ptr_get; @@ -546,13 +555,14 @@ int8_t ws_pae_supp_init(protocol_interface_info_entry_t *interface_ptr, const se pae_supp->interface_ptr = interface_ptr; pae_supp->auth_completed = NULL; + pae_supp->auth_next_target = NULL; pae_supp->nw_key_insert = NULL; pae_supp->nw_key_index_set = NULL; pae_supp->gtk_hash_ptr_get = NULL; pae_supp->initial_key_timer = 0; pae_supp->initial_key_retry_timer = 0; pae_supp->nw_keys_used_cnt = 0; - pae_supp->initial_key_retry_cnt = INITIAL_KEY_RETRY_COUNT; + pae_supp->initial_key_retry_cnt = DEFAULT_INITIAL_KEY_RETRY_COUNT; pae_supp->sec_keys_nw_info = sec_keys_nw_info; pae_supp->sec_timer_cfg = sec_timer_cfg; pae_supp->sec_prot_cfg = sec_prot_cfg; @@ -561,6 +571,7 @@ int8_t ws_pae_supp_init(protocol_interface_info_entry_t *interface_ptr, const se pae_supp->timer_running = false; pae_supp->new_br_eui_64_set = false; pae_supp->new_br_eui_64_fresh = false; + pae_supp->comp_br_eui_64_set = false; pae_supp->entry_address_active = false; ws_pae_lib_supp_init(&pae_supp->entry); @@ -786,6 +797,15 @@ void ws_pae_supp_slow_timer(uint16_t seconds) // Checks if trickle timer expires if (trickle_timer(&pae_supp->auth_trickle_timer, &pae_supp->auth_trickle_params, seconds)) { if (pae_supp->initial_key_retry_cnt > 0) { + // On initial EAPOL-key TX failure, check for other parents + if (pae_supp->auth_requested && pae_supp->tx_failure_on_initial_key) { + // Returns same target if no other valid targets found + const uint8_t *next_target = pae_supp->auth_next_target(pae_supp->interface_ptr, kmp_address_eui_64_get(&pae_supp->target_addr), &pae_supp->sec_keys_nw_info->key_pan_id); + kmp_address_eui_64_set(&pae_supp->target_addr, next_target); + ws_pae_supp_address_set(pae_supp, &pae_supp->target_addr); + } + pae_supp->tx_failure_on_initial_key = false; + // Sends initial EAPOL-key if (ws_pae_supp_initial_key_send(pae_supp) < 0) { tr_info("EAPOL-Key send failed"); } @@ -800,7 +820,12 @@ void ws_pae_supp_slow_timer(uint16_t seconds) tr_info("GTKs do not match to GTK hash"); retry = true; } - ws_pae_supp_authenticate_response(pae_supp, AUTH_RESULT_ERR_UNSPEC); + auth_result_e result = AUTH_RESULT_ERR_UNSPEC; + if (pae_supp->tx_failure_on_initial_key) { + result = AUTH_RESULT_ERR_TX_NO_ACK; + pae_supp->tx_failure_on_initial_key = false; + } + ws_pae_supp_authenticate_response(pae_supp, result); if (retry) { // Start trickle timer to try re-authentication ws_pae_supp_initial_key_update_trickle_timer_start(pae_supp, KEY_UPDATE_RETRY_COUNT); @@ -838,7 +863,7 @@ void ws_pae_supp_slow_timer(uint16_t seconds) pae_supp->initial_key_timer -= seconds; } else { pae_supp->initial_key_timer = 0; - + pae_supp->tx_failure_on_initial_key = false; // Sends initial EAPOL-Key message if (ws_pae_supp_initial_key_send(pae_supp) < 0) { tr_info("EAPOL-Key send failed"); @@ -852,46 +877,40 @@ void ws_pae_supp_slow_timer(uint16_t seconds) static void ws_pae_supp_initial_trickle_timer_start(pae_supp_t *pae_supp) { - pae_supp->auth_trickle_params = initial_eapol_key_trickle_params; + /* Starts trickle for initial EAPOL-key. Default sequence has fixed delay of 2 minutes, + * one re-transmit interval, last re-transmit interval transmit time and a wait time + * for the authenticator to answer the last re-transmit. + * + * Interval I [6,12] minutes. Sequence: + * + * fixed 2 minutes delay + I + last I transmit time t + wait for answer [2,4] minutes + * + * There are two retries. Minimum time that sequence takes before authentication failure + * is 16 minutes and maximum is 30 minutes. + * + * + * Extremely slow network + * + * Starts trickle for initial EAPOL-key, Interval I [10,60] minutes. Sequence: + * I + last I transmit time t + wait for answer [2,4] minutes + * There are two retries. Minimum time that sequence takes before authentication failure + * is 22 minutes and maximum is 124 minutes. + */ + pae_supp->auth_trickle_params = pae_supp->sec_prot_cfg->initial_key_trickle_params; + pae_supp->initial_key_retry_timer = pae_supp->sec_prot_cfg->initial_key_retry_delay; - // Very fast, medium and slow network - if (timing_value < 25) { - /* Starts trickle for initial EAPOL-key. Sequence has fixed delay of 2 minutes, - * one re-transmit interval, last re-transmit interval transmit time and a wait time - * for the authenticator to answer the last re-transmit. - * - * Interval I [6,12] minutes. Sequence: - * - * fixed 2 minutes delay + I + last I transmit time t + wait for answer [2,4] minutes - * - * There are two retries. Minimum time that sequence takes before authentication failure - * is 16 minutes and maximum is 30 minutes. - */ - pae_supp->initial_key_retry_timer = DEFAULT_INITIAL_KEY_RETRY_TIMER; // 2 minutes - } else { - /* Extremely slow network - * - * Starts trickle for initial EAPOL-key, Interval I [10,60] minutes. Sequence: - * I + last I transmit time t + wait for answer [2,4] minutes - * There are two retries. Minimum time that sequence takes before authentication failure - * is 22 minutes and maximum is 124 minutes. - */ - pae_supp->auth_trickle_params.Imin = VERY_SLOW_NW_TRICKLE_IMIN_SECS; - pae_supp->auth_trickle_params.Imax = VERY_SLOW_NW_TRICKLE_IMAX_SECS; - pae_supp->initial_key_retry_timer = NONE_INITIAL_KEY_RETRY_TIMER; // 0 seconds - } trickle_start(&pae_supp->auth_trickle_timer, &pae_supp->auth_trickle_params); tr_info("Initial EAPOL-Key trickle I: [%i,%i] %i, t: %i", pae_supp->auth_trickle_params.Imin, pae_supp->auth_trickle_params.Imax, pae_supp->auth_trickle_timer.I, pae_supp->auth_trickle_timer.t); pae_supp->auth_trickle_running = true; - pae_supp->initial_key_retry_cnt = INITIAL_KEY_RETRY_COUNT; + pae_supp->initial_key_retry_cnt = pae_supp->sec_prot_cfg->initial_key_retry_cnt; } static void ws_pae_supp_initial_last_interval_trickle_timer_start(pae_supp_t *pae_supp) { // Starts trickle last to wait response after last retry before failing authentication - pae_supp->auth_trickle_params = initial_eapol_key_trickle_params; pae_supp->auth_trickle_params.Imin = LAST_INTERVAL_TRICKLE_IMIN_SECS; pae_supp->auth_trickle_params.Imax = LAST_INTERVAL_TRICKLE_IMAX_SECS; + pae_supp->auth_trickle_params.k = 0; pae_supp->auth_trickle_params.TimerExpirations = 1; // Set I to [iMin,iMax] (4 to 4 minutes) -> t is [I/2 - I] (2 minutes to 4 minutes) trickle_start(&pae_supp->auth_trickle_timer, &pae_supp->auth_trickle_params); @@ -1119,7 +1138,7 @@ static kmp_api_t *ws_pae_supp_kmp_incoming_ind(kmp_service_t *service, kmp_type_ static kmp_api_t *ws_pae_supp_kmp_create_and_start(kmp_service_t *service, kmp_type_e type, pae_supp_t *pae_supp) { // Create new instance - kmp_api_t *kmp = kmp_api_create(service, type, pae_supp->sec_prot_cfg); + kmp_api_t *kmp = kmp_api_create(service, type, pae_supp->sec_prot_cfg, pae_supp->sec_timer_cfg); if (!kmp) { return NULL; } @@ -1217,7 +1236,8 @@ static void ws_pae_supp_kmp_api_finished_indication(kmp_api_t *kmp, kmp_result_e /* Fails authentication only if other authentication protocols are not yet started by authenticator */ if (ws_pae_lib_kmp_list_count(&pae_supp->entry.kmp_list) <= 1) { - ws_pae_supp_authenticate_response(pae_supp, AUTH_RESULT_ERR_TX_NO_ACK); + // Continues with trickle but selects different parent + pae_supp->tx_failure_on_initial_key = true; } } } diff --git a/source/6LoWPAN/ws/ws_pae_supp.h b/source/6LoWPAN/ws/ws_pae_supp.h index d5d6ac3c6b..7bd2017061 100644 --- a/source/6LoWPAN/ws/ws_pae_supp.h +++ b/source/6LoWPAN/ws/ws_pae_supp.h @@ -81,13 +81,14 @@ void ws_pae_supp_slow_timer(uint16_t seconds); * \param interface_ptr interface * \param dest_pan_id EAPOL target PAN ID * \param dest_eui_64 EAPOL target + * \param dest_network_name EAPOL target network name * * \return < 0 failure * \return 0 authentication done, continue * \return > 0 authentication started * */ -int8_t ws_pae_supp_authenticate(protocol_interface_info_entry_t *interface_ptr, uint16_t dest_pan_id, uint8_t *dest_eui_64); +int8_t ws_pae_supp_authenticate(protocol_interface_info_entry_t *interface_ptr, uint16_t dest_pan_id, uint8_t *dest_eui_64, char *dest_network_name); /** * ws_pae_supp_border_router_addr_write write border router address @@ -117,12 +118,13 @@ int8_t ws_pae_supp_border_router_addr_read(protocol_interface_info_entry_t *inte * ws_pae_supp_nw_key_valid network key is valid i.e. used successfully on bootstrap * * \param interface_ptr interface + * \param br_iid border router IID for which the keys are valid * * \return < 0 failure * \return >= 0 success * */ -int8_t ws_pae_supp_nw_key_valid(protocol_interface_info_entry_t *interface_ptr); +int8_t ws_pae_supp_nw_key_valid(protocol_interface_info_entry_t *interface_ptr, uint8_t *br_iid); /** * ws_pae_supp_gtk_hash_update GTK hash has been updated (on PAN configuration) @@ -190,6 +192,17 @@ typedef void ws_pae_supp_nw_key_index_set(protocol_interface_info_entry_t *inter */ typedef void ws_pae_supp_auth_completed(protocol_interface_info_entry_t *interface_ptr, auth_result_e result, uint8_t *target_eui_64); +/** + * ws_pae_supp_auth_next_target get next target to attempt authentication + * + * \param interface_ptr interface + * \param previous_eui_64 EUI-64 of previous target + * + * \return EUI-64 of the next target or previous target if new one not available + * + */ +typedef const uint8_t *ws_pae_supp_auth_next_target(protocol_interface_info_entry_t *interface_ptr, const uint8_t *previous_eui_64, uint16_t *pan_id); + /** * ws_pae_supp_nw_key_insert network key insert callback * @@ -230,7 +243,7 @@ typedef void ws_pae_supp_nw_info_updated(protocol_interface_info_entry_t *interf * \param nw_info_updated security keys network information updated callback * */ -void ws_pae_supp_cb_register(protocol_interface_info_entry_t *interface_ptr, ws_pae_supp_auth_completed *completed, ws_pae_supp_nw_key_insert *nw_key_insert, ws_pae_supp_nw_key_index_set *nw_key_index_set, ws_pae_supp_gtk_hash_ptr_get *gtk_hash_ptr_get, ws_pae_supp_nw_info_updated *nw_info_updated); +void ws_pae_supp_cb_register(protocol_interface_info_entry_t *interface_ptr, ws_pae_supp_auth_completed *completed, ws_pae_supp_auth_next_target *auth_next_target, ws_pae_supp_nw_key_insert *nw_key_insert, ws_pae_supp_nw_key_index_set *nw_key_index_set, ws_pae_supp_gtk_hash_ptr_get *gtk_hash_ptr_get, ws_pae_supp_nw_info_updated *nw_info_updated); #else diff --git a/source/6LoWPAN/ws/ws_pae_time.c b/source/6LoWPAN/ws/ws_pae_time.c index 72482429d5..ad60f3d0e2 100644 --- a/source/6LoWPAN/ws/ws_pae_time.c +++ b/source/6LoWPAN/ws/ws_pae_time.c @@ -31,7 +31,10 @@ #define TRACE_GROUP "wst" // Wednesday, January 1, 2020 0:00:00 GMT -#define CURRENT_TIME_INIT_VALUE 1577836800 +#define CURRENT_TIME_INIT_VALUE 1577836800 + +// Increment two hours in addition to maximum storing interval +#define CURRENT_TIME_INCREMENT_VALUE (2 * 3600) static uint64_t current_time = CURRENT_TIME_INIT_VALUE; static ns_time_api_system_time_callback *system_time_callback = NULL; @@ -171,6 +174,8 @@ int8_t ws_pae_current_time_set(uint64_t time) tr_error("FATAL: system time less than reference time or more than 12 months in future: %"PRIi64" reference time: %"PRIi64, system_time, current_time); return -1; } + } else { + current_time += FRAME_COUNTER_STORE_FORCE_INTERVAL + CURRENT_TIME_INCREMENT_VALUE; } return 0; diff --git a/source/6LoWPAN/ws/ws_pae_timers.c b/source/6LoWPAN/ws/ws_pae_timers.c index fd3f02e621..a07d0e6deb 100644 --- a/source/6LoWPAN/ws/ws_pae_timers.c +++ b/source/6LoWPAN/ws/ws_pae_timers.c @@ -26,6 +26,7 @@ #include "NWK_INTERFACE/Include/protocol.h" #include "6LoWPAN/ws/ws_config.h" #include "6LoWPAN/ws/ws_cfg_settings.h" +#include "Security/protocols/sec_prot_cfg.h" #include "6LoWPAN/ws/ws_pae_timers.h" #ifdef HAVE_WS diff --git a/source/6LoWPAN/ws/ws_pae_timers.h b/source/6LoWPAN/ws/ws_pae_timers.h index ec792996a0..7b8f58052d 100644 --- a/source/6LoWPAN/ws/ws_pae_timers.h +++ b/source/6LoWPAN/ws/ws_pae_timers.h @@ -18,18 +18,6 @@ #ifndef WS_PAE_TIMERS_H_ #define WS_PAE_TIMERS_H_ -typedef struct sec_timer_cfg_s { - uint32_t gtk_expire_offset; /* GTK lifetime; GTK_EXPIRE_OFFSET (seconds) */ - uint32_t pmk_lifetime; /* PMK lifetime (seconds) */ - uint32_t ptk_lifetime; /* PTK lifetime (seconds) */ - uint16_t gtk_new_act_time; /* GTK_NEW_ACTIVATION_TIME (1/X of expire offset) */ - uint16_t revocat_lifetime_reduct; /* REVOCATION_LIFETIME_REDUCTION (reduction of lifetime) */ - uint16_t gtk_request_imin; /* GTK_REQUEST_IMIN (seconds) */ - uint16_t gtk_request_imax; /* GTK_REQUEST_IMAX (seconds) */ - uint16_t gtk_max_mismatch; /* GTK_MAX_MISMATCH (seconds) */ - uint8_t gtk_new_install_req; /* GTK_NEW_INSTALL_REQUIRED (percent of GTK lifetime) */ -} sec_timer_cfg_t; - /** * ws_pae_timers_settings_init initializes timer settings structure * diff --git a/source/MAC/IEEE802_15_4/mac_data_buffer.h b/source/MAC/IEEE802_15_4/mac_data_buffer.h index b285c069de..4888cc816d 100644 --- a/source/MAC/IEEE802_15_4/mac_data_buffer.h +++ b/source/MAC/IEEE802_15_4/mac_data_buffer.h @@ -97,6 +97,7 @@ typedef struct mac_pre_build_frame { bool mac_allocated_payload_ptr: 1; bool asynch_request: 1; bool message_builded: 1; + bool DSN_allocated: 1; unsigned security_mic_len: 5; //Max possible lengths 0, 4, 8, 16 bytes unsigned priority: 2; struct mac_pre_build_frame *next; //Pointer for queue purpose diff --git a/source/MAC/IEEE802_15_4/mac_mcps_sap.c b/source/MAC/IEEE802_15_4/mac_mcps_sap.c index 97613bbeff..ee16dc8670 100644 --- a/source/MAC/IEEE802_15_4/mac_mcps_sap.c +++ b/source/MAC/IEEE802_15_4/mac_mcps_sap.c @@ -1226,6 +1226,7 @@ mac_pre_build_frame_t *mcps_sap_prebuild_frame_buffer_get(uint16_t payload_size) memset(buffer, 0, sizeof(mac_pre_build_frame_t)); buffer->initial_tx_channel = 0xffff; buffer->aux_header.frameCounter = 0xffffffff; + buffer->DSN_allocated = false; if (payload_size) { //Mac interlnal payload allocate buffer->mac_payload = ns_dyn_mem_temporary_alloc(payload_size); @@ -1502,7 +1503,10 @@ static void mcps_generic_sequence_number_allocate(protocol_interface_rf_mac_setu switch (buffer->fcf_dsn.frametype) { case MAC_FRAME_CMD: case MAC_FRAME_DATA: - buffer->fcf_dsn.DSN = mac_mlme_set_new_sqn(rf_ptr); + if (!buffer->DSN_allocated) { + buffer->fcf_dsn.DSN = mac_mlme_set_new_sqn(rf_ptr); + buffer->DSN_allocated = true; + } break; case MAC_FRAME_BEACON: buffer->fcf_dsn.DSN = mac_mlme_set_new_beacon_sqn(rf_ptr); diff --git a/source/RPL/rpl_control.c b/source/RPL/rpl_control.c index 72ef949fc2..37eacc4345 100644 --- a/source/RPL/rpl_control.c +++ b/source/RPL/rpl_control.c @@ -391,7 +391,7 @@ static void rpl_control_addr_notifier(struct protocol_interface_info_entry *inte } } -static void rpl_control_etx_change_callback(int8_t nwk_id, uint16_t previous_etx, uint16_t current_etx, uint8_t attribute_index) +static void rpl_control_etx_change_callback(int8_t nwk_id, uint16_t previous_etx, uint16_t current_etx, uint8_t attribute_index, const uint8_t *mac64) { protocol_interface_info_entry_t *cur = protocol_stack_interface_info_get_by_id(nwk_id); @@ -405,14 +405,29 @@ static void rpl_control_etx_change_callback(int8_t nwk_id, uint16_t previous_et uint16_t delay = rpl_policy_etx_change_parent_selection_delay(domain); tr_debug("Triggering parent selection due to ETX %s on neigh index %u, etx %u", better ? "better" : "worse", attribute_index, current_etx); rpl_dodag_t *dodag = NULL; + //Define Link Local Address + uint8_t ll_parent_address[16]; + memcpy(ll_parent_address, ADDR_LINK_LOCAL_PREFIX, 8); + memcpy(ll_parent_address + 8, mac64, 8); + ll_parent_address[8] ^= 2; ns_list_foreach(rpl_instance_t, instance, &domain->instances) { - if (better) { - dodag = rpl_instance_current_dodag(instance); - } - rpl_instance_trigger_parent_selection(instance, delay, dodag); + if (rpl_instance_am_root(instance)) { rpl_downward_paths_invalidate(instance); + } else { + if (better) { + //Only react here for candidate updates and when DODAG version is configured + if (rpl_instance_address_is_candidate(instance, ll_parent_address, 0)) { + dodag = rpl_instance_current_dodag(instance); + if (dodag) { + rpl_instance_trigger_parent_selection(instance, delay, dodag); + } + } + } else if (rpl_instance_address_is_parent(instance, ll_parent_address)) { + //Quick reaction for selected parent only + rpl_instance_trigger_parent_selection(instance, delay, NULL); + } } } } diff --git a/source/Security/kmp/kmp_api.c b/source/Security/kmp/kmp_api.c index 345e9ba9fc..d3a61fe867 100644 --- a/source/Security/kmp/kmp_api.c +++ b/source/Security/kmp/kmp_api.c @@ -99,7 +99,7 @@ static void kmp_sec_prot_receive_disable(sec_prot_t *prot); #define kmp_api_get_from_prot(prot) (kmp_api_t *)(((uint8_t *)prot) - offsetof(kmp_api_t, sec_prot)); -kmp_api_t *kmp_api_create(kmp_service_t *service, kmp_type_e type, sec_prot_cfg_t *cfg) +kmp_api_t *kmp_api_create(kmp_service_t *service, kmp_type_e type, sec_prot_cfg_t *prot_cfg, sec_timer_cfg_t *timer_cfg) { if (!service) { return 0; @@ -151,7 +151,8 @@ kmp_api_t *kmp_api_create(kmp_service_t *service, kmp_type_e type, sec_prot_cfg_ kmp->sec_prot.addr_get = kmp_sec_prot_eui64_addr_get; kmp->sec_prot.type_get = kmp_sec_prot_by_type_get; kmp->sec_prot.receive_disable = kmp_sec_prot_receive_disable; - kmp->sec_prot.cfg = cfg; + kmp->sec_prot.prot_cfg = prot_cfg; + kmp->sec_prot.timer_cfg = timer_cfg; if (sec_prot->init(&kmp->sec_prot) < 0) { ns_dyn_mem_free(kmp); diff --git a/source/Security/kmp/kmp_api.h b/source/Security/kmp/kmp_api.h index 062b36b4ad..10f36528bd 100644 --- a/source/Security/kmp/kmp_api.h +++ b/source/Security/kmp/kmp_api.h @@ -125,12 +125,13 @@ typedef void kmp_api_finished(kmp_api_t *kmp); * * \param service KMP service * \param type KMP type - * \param cfg configuration + * \param prot_cfg protocol configuration + * \param timer_cfg timer configuration * * \return KMP instance or NULL * */ -kmp_api_t *kmp_api_create(kmp_service_t *service, kmp_type_e type, sec_prot_cfg_t *cfg); +kmp_api_t *kmp_api_create(kmp_service_t *service, kmp_type_e type, sec_prot_cfg_t *prot_cfg, sec_timer_cfg_t *timer_cfg); /** * kmp_api_start start KMP api diff --git a/source/Security/protocols/eap_tls_sec_prot/auth_eap_tls_sec_prot.c b/source/Security/protocols/eap_tls_sec_prot/auth_eap_tls_sec_prot.c index e8118585ad..2fd7d96b65 100644 --- a/source/Security/protocols/eap_tls_sec_prot/auth_eap_tls_sec_prot.c +++ b/source/Security/protocols/eap_tls_sec_prot/auth_eap_tls_sec_prot.c @@ -189,7 +189,7 @@ static int8_t auth_eap_tls_sec_prot_receive(sec_prot_t *prot, void *pdu, uint16_ // Call state machine prot->state_machine(prot); // Resets trickle timer to give time for supplicant to answer - sec_prot_timer_trickle_start(&data->common, &prot->cfg->sec_prot_trickle_params); + sec_prot_timer_trickle_start(&data->common, &prot->prot_cfg->sec_prot_trickle_params); data->init_key_cnt++; } // Filters repeated initial EAPOL-key messages @@ -297,7 +297,7 @@ static void auth_eap_tls_sec_prot_timer_timeout(sec_prot_t *prot, uint16_t ticks } sec_prot_timer_timeout_handle(prot, &data->common, - &prot->cfg->sec_prot_trickle_params, ticks); + &prot->prot_cfg->sec_prot_trickle_params, ticks); } static void auth_eap_tls_sec_prot_tls_create_indication(sec_prot_t *tls_prot) @@ -421,7 +421,7 @@ static void auth_eap_tls_sec_prot_state_machine(sec_prot_t *prot) auth_eap_tls_sec_prot_message_send(prot, EAP_REQ, EAP_IDENTITY, EAP_TLS_EXCHANGE_NONE); // Start trickle timer to re-send if no response - sec_prot_timer_trickle_start(&data->common, &prot->cfg->sec_prot_trickle_params); + sec_prot_timer_trickle_start(&data->common, &prot->prot_cfg->sec_prot_trickle_params); sec_prot_state_set(prot, &data->common, EAP_TLS_STATE_RESPONSE_ID); break; @@ -445,7 +445,7 @@ static void auth_eap_tls_sec_prot_state_machine(sec_prot_t *prot) auth_eap_tls_sec_prot_message_send(prot, EAP_REQ, EAP_TLS, EAP_TLS_EXCHANGE_START); // Start trickle timer to re-send if no response - sec_prot_timer_trickle_start(&data->common, &prot->cfg->sec_prot_trickle_params); + sec_prot_timer_trickle_start(&data->common, &prot->prot_cfg->sec_prot_trickle_params); sec_prot_state_set(prot, &data->common, EAP_TLS_STATE_RESPONSE_START); break; @@ -527,7 +527,7 @@ static void auth_eap_tls_sec_prot_state_machine(sec_prot_t *prot) auth_eap_tls_sec_prot_message_send(prot, EAP_REQ, EAP_TLS, EAP_TLS_EXCHANGE_ONGOING); // Start trickle timer to re-send if no response - sec_prot_timer_trickle_start(&data->common, &prot->cfg->sec_prot_trickle_params); + sec_prot_timer_trickle_start(&data->common, &prot->prot_cfg->sec_prot_trickle_params); } else { // TLS done, indicate success to peer if (data->tls_result == EAP_TLS_RESULT_HANDSHAKE_OVER) { diff --git a/source/Security/protocols/eap_tls_sec_prot/supp_eap_tls_sec_prot.c b/source/Security/protocols/eap_tls_sec_prot/supp_eap_tls_sec_prot.c index c7c935242d..b7df2d6eb6 100644 --- a/source/Security/protocols/eap_tls_sec_prot/supp_eap_tls_sec_prot.c +++ b/source/Security/protocols/eap_tls_sec_prot/supp_eap_tls_sec_prot.c @@ -404,7 +404,7 @@ static void supp_eap_tls_sec_prot_state_machine(sec_prot_t *prot) } // Set retry timeout based on network size - data->common.ticks = prot->cfg->sec_prot_retry_timeout; + data->common.ticks = prot->prot_cfg->sec_prot_retry_timeout; // Store sequence ID supp_eap_tls_sec_prot_seq_id_update(prot); @@ -449,7 +449,7 @@ static void supp_eap_tls_sec_prot_state_machine(sec_prot_t *prot) supp_eap_tls_sec_prot_seq_id_update(prot); sec_prot_state_set(prot, &data->common, EAP_TLS_STATE_REQUEST); - data->common.ticks = prot->cfg->sec_prot_retry_timeout; + data->common.ticks = prot->prot_cfg->sec_prot_retry_timeout; // Initialize TLS protocol if (supp_eap_tls_sec_prot_init_tls(prot) < 0) { @@ -483,7 +483,7 @@ static void supp_eap_tls_sec_prot_state_machine(sec_prot_t *prot) // Store sequence ID if (supp_eap_tls_sec_prot_seq_id_update(prot)) { // When receiving a new sequence number, adds more time for re-send if no response - data->common.ticks = prot->cfg->sec_prot_retry_timeout; + data->common.ticks = prot->prot_cfg->sec_prot_retry_timeout; } // All fragments received for a message diff --git a/source/Security/protocols/fwh_sec_prot/auth_fwh_sec_prot.c b/source/Security/protocols/fwh_sec_prot/auth_fwh_sec_prot.c index 735112eeab..285a75db8e 100644 --- a/source/Security/protocols/fwh_sec_prot/auth_fwh_sec_prot.c +++ b/source/Security/protocols/fwh_sec_prot/auth_fwh_sec_prot.c @@ -313,7 +313,7 @@ static int8_t auth_fwh_sec_prot_message_send(sec_prot_t *prot, fwh_sec_prot_msg_ static void auth_fwh_sec_prot_timer_timeout(sec_prot_t *prot, uint16_t ticks) { fwh_sec_prot_int_t *data = fwh_sec_prot_get(prot); - sec_prot_timer_timeout_handle(prot, &data->common, &prot->cfg->sec_prot_trickle_params, ticks); + sec_prot_timer_timeout_handle(prot, &data->common, &prot->prot_cfg->sec_prot_trickle_params, ticks); } static void auth_fwh_sec_prot_state_machine(sec_prot_t *prot) @@ -350,7 +350,7 @@ static void auth_fwh_sec_prot_state_machine(sec_prot_t *prot) auth_fwh_sec_prot_message_send(prot, FWH_MESSAGE_1); // Start trickle timer to re-send if no response - sec_prot_timer_trickle_start(&data->common, &prot->cfg->sec_prot_trickle_params); + sec_prot_timer_trickle_start(&data->common, &prot->prot_cfg->sec_prot_trickle_params); sec_prot_state_set(prot, &data->common, FWH_STATE_MESSAGE_2); break; @@ -378,7 +378,7 @@ static void auth_fwh_sec_prot_state_machine(sec_prot_t *prot) auth_fwh_sec_prot_message_send(prot, FWH_MESSAGE_3); // Start trickle timer to re-send if no response - sec_prot_timer_trickle_start(&data->common, &prot->cfg->sec_prot_trickle_params); + sec_prot_timer_trickle_start(&data->common, &prot->prot_cfg->sec_prot_trickle_params); sec_prot_state_set(prot, &data->common, FWH_STATE_MESSAGE_4); } @@ -406,7 +406,7 @@ static void auth_fwh_sec_prot_state_machine(sec_prot_t *prot) // Reset PTK mismatch sec_prot_keys_ptk_mismatch_reset(prot->sec_keys); // Update PTK - sec_prot_keys_ptk_write(prot->sec_keys, data->new_ptk); + sec_prot_keys_ptk_write(prot->sec_keys, data->new_ptk, prot->timer_cfg->ptk_lifetime); sec_prot_keys_ptk_eui_64_write(prot->sec_keys, data->remote_eui64); sec_prot_state_set(prot, &data->common, FWH_STATE_FINISH); } diff --git a/source/Security/protocols/fwh_sec_prot/supp_fwh_sec_prot.c b/source/Security/protocols/fwh_sec_prot/supp_fwh_sec_prot.c index e5a44e18b8..ef3e9bd991 100644 --- a/source/Security/protocols/fwh_sec_prot/supp_fwh_sec_prot.c +++ b/source/Security/protocols/fwh_sec_prot/supp_fwh_sec_prot.c @@ -139,7 +139,7 @@ static int8_t supp_fwh_sec_prot_init(sec_prot_t *prot) sec_prot_init(&data->common); sec_prot_state_set(prot, &data->common, FWH_STATE_INIT); - data->common.ticks = prot->cfg->sec_prot_retry_timeout; + data->common.ticks = prot->prot_cfg->sec_prot_retry_timeout; data->msg3_received = false; data->msg3_retry_wait = false; data->recv_replay_cnt = 0; @@ -337,7 +337,7 @@ static void supp_fwh_sec_prot_state_machine(sec_prot_t *prot) if (sec_prot_result_ok_check(&data->common)) { // Send 4WH message 2 supp_fwh_sec_prot_message_send(prot, FWH_MESSAGE_2); - data->common.ticks = prot->cfg->sec_prot_retry_timeout; + data->common.ticks = prot->prot_cfg->sec_prot_retry_timeout; sec_prot_state_set(prot, &data->common, FWH_STATE_MESSAGE_3); } else { // Ready to be deleted @@ -365,7 +365,7 @@ static void supp_fwh_sec_prot_state_machine(sec_prot_t *prot) // Send 4WH message 2 supp_fwh_sec_prot_message_send(prot, FWH_MESSAGE_2); - data->common.ticks = prot->cfg->sec_prot_retry_timeout; + data->common.ticks = prot->prot_cfg->sec_prot_retry_timeout; return; } else if (data->recv_msg != FWH_MESSAGE_3) { return; @@ -392,7 +392,7 @@ static void supp_fwh_sec_prot_state_machine(sec_prot_t *prot) // Sends 4WH Message 4 supp_fwh_sec_prot_message_send(prot, FWH_MESSAGE_4); - data->common.ticks = prot->cfg->sec_prot_retry_timeout; + data->common.ticks = prot->prot_cfg->sec_prot_retry_timeout; sec_prot_state_set(prot, &data->common, FWH_STATE_FINISH); break; @@ -409,7 +409,7 @@ static void supp_fwh_sec_prot_state_machine(sec_prot_t *prot) tr_info("4WH: finish, wait Message 3 retry"); - sec_prot_keys_ptk_write(prot->sec_keys, data->new_ptk); + sec_prot_keys_ptk_write(prot->sec_keys, data->new_ptk, prot->timer_cfg->ptk_lifetime); sec_prot_keys_ptk_eui_64_write(prot->sec_keys, data->remote_eui64); data->common.ticks = 60 * 10; // 60 seconds diff --git a/source/Security/protocols/gkh_sec_prot/auth_gkh_sec_prot.c b/source/Security/protocols/gkh_sec_prot/auth_gkh_sec_prot.c index d39e912c6b..7d736ae95b 100644 --- a/source/Security/protocols/gkh_sec_prot/auth_gkh_sec_prot.c +++ b/source/Security/protocols/gkh_sec_prot/auth_gkh_sec_prot.c @@ -261,7 +261,7 @@ static int8_t auth_gkh_sec_prot_message_send(sec_prot_t *prot, gkh_sec_prot_msg_ static void auth_gkh_sec_prot_timer_timeout(sec_prot_t *prot, uint16_t ticks) { gkh_sec_prot_int_t *data = gkh_sec_prot_get(prot); - sec_prot_timer_timeout_handle(prot, &data->common, &prot->cfg->sec_prot_trickle_params, ticks); + sec_prot_timer_timeout_handle(prot, &data->common, &prot->prot_cfg->sec_prot_trickle_params, ticks); } static void auth_gkh_sec_prot_state_machine(sec_prot_t *prot) @@ -290,7 +290,7 @@ static void auth_gkh_sec_prot_state_machine(sec_prot_t *prot) auth_gkh_sec_prot_message_send(prot, GKH_MESSAGE_1); // Start trickle timer to re-send if no response - sec_prot_timer_trickle_start(&data->common, &prot->cfg->sec_prot_trickle_params); + sec_prot_timer_trickle_start(&data->common, &prot->prot_cfg->sec_prot_trickle_params); sec_prot_state_set(prot, &data->common, GKH_STATE_MESSAGE_2); diff --git a/source/Security/protocols/sec_prot.h b/source/Security/protocols/sec_prot.h index 556d769f6b..c6ebae78a9 100644 --- a/source/Security/protocols/sec_prot.h +++ b/source/Security/protocols/sec_prot.h @@ -268,7 +268,8 @@ struct sec_prot_s { sec_prot_receive_disable *receive_disable; /**< Disable receiving of messages */ sec_prot_keys_t *sec_keys; /**< Security keys storage pointer */ - sec_prot_cfg_t *cfg; /**< Configuration pointer */ + sec_prot_cfg_t *prot_cfg; /**< Security protocol configuration pointer */ + sec_timer_cfg_t *timer_cfg; /**< Security timer configuration pointer */ uint8_t header_size; /**< Header size */ sec_prot_int_data_t *data; /**< Protocol internal data */ }; diff --git a/source/Security/protocols/sec_prot_cfg.h b/source/Security/protocols/sec_prot_cfg.h index fa2a88dafb..f0a118b7c1 100644 --- a/source/Security/protocols/sec_prot_cfg.h +++ b/source/Security/protocols/sec_prot_cfg.h @@ -24,6 +24,23 @@ typedef struct sec_prot_cfg_s { trickle_params_t sec_prot_trickle_params; uint16_t sec_prot_retry_timeout; uint16_t sec_max_ongoing_authentication; + uint16_t initial_key_retry_delay; + trickle_params_t initial_key_trickle_params; + uint8_t initial_key_retry_cnt; } sec_prot_cfg_t; +/* Security timer configuration settings */ + +typedef struct sec_timer_cfg_s { + uint32_t gtk_expire_offset; /* GTK lifetime; GTK_EXPIRE_OFFSET (seconds) */ + uint32_t pmk_lifetime; /* PMK lifetime (seconds) */ + uint32_t ptk_lifetime; /* PTK lifetime (seconds) */ + uint16_t gtk_new_act_time; /* GTK_NEW_ACTIVATION_TIME (1/X of expire offset) */ + uint16_t revocat_lifetime_reduct; /* REVOCATION_LIFETIME_REDUCTION (reduction of lifetime) */ + uint16_t gtk_request_imin; /* GTK_REQUEST_IMIN (seconds) */ + uint16_t gtk_request_imax; /* GTK_REQUEST_IMAX (seconds) */ + uint16_t gtk_max_mismatch; /* GTK_MAX_MISMATCH (seconds) */ + uint8_t gtk_new_install_req; /* GTK_NEW_INSTALL_REQUIRED (percent of GTK lifetime) */ +} sec_timer_cfg_t; + #endif /* SEC_PROT_CONF_H_ */ diff --git a/source/Security/protocols/sec_prot_keys.c b/source/Security/protocols/sec_prot_keys.c index 49fd18758a..d7071e9323 100644 --- a/source/Security/protocols/sec_prot_keys.c +++ b/source/Security/protocols/sec_prot_keys.c @@ -56,8 +56,8 @@ sec_prot_keys_t *sec_prot_keys_create(sec_prot_gtk_keys_t *gtks, const sec_prot_ void sec_prot_keys_init(sec_prot_keys_t *sec_keys, sec_prot_gtk_keys_t *gtks, const sec_prot_certs_t *certs) { memset(sec_keys, 0, sizeof(sec_prot_keys_t)); - sec_keys->pmk_lifetime = PMK_LIFETIME_INSTALL; - sec_keys->ptk_lifetime = PTK_LIFETIME_INSTALL; + sec_keys->pmk_lifetime = 0; + sec_keys->ptk_lifetime = 0; sec_keys->pmk_key_replay_cnt = 0; sec_keys->gtks = gtks; sec_keys->certs = certs; @@ -101,12 +101,12 @@ void sec_prot_keys_gtks_delete(sec_prot_gtk_keys_t *gtks) ns_dyn_mem_free(gtks); } -void sec_prot_keys_pmk_write(sec_prot_keys_t *sec_keys, uint8_t *pmk) +void sec_prot_keys_pmk_write(sec_prot_keys_t *sec_keys, uint8_t *pmk, uint32_t pmk_lifetime) { memcpy(sec_keys->pmk, pmk, PMK_LEN); sec_keys->pmk_key_replay_cnt = 0; sec_keys->pmk_key_replay_cnt_set = false; - sec_keys->pmk_lifetime = PMK_LIFETIME_INSTALL; + sec_keys->pmk_lifetime = pmk_lifetime; sec_keys->pmk_set = true; sec_keys->updated = true; } @@ -116,7 +116,7 @@ void sec_prot_keys_pmk_delete(sec_prot_keys_t *sec_keys) memset(sec_keys->pmk, 0, PMK_LEN); sec_keys->pmk_key_replay_cnt = 0; sec_keys->pmk_key_replay_cnt_set = false; - sec_keys->pmk_lifetime = PMK_LIFETIME_INSTALL; + sec_keys->pmk_lifetime = 0; sec_keys->pmk_set = false; sec_keys->updated = true; } @@ -130,6 +130,15 @@ uint8_t *sec_prot_keys_pmk_get(sec_prot_keys_t *sec_keys) return sec_keys->pmk; } +uint32_t sec_prot_keys_pmk_lifetime_get(sec_prot_keys_t *sec_keys) +{ + if (!sec_keys->pmk_set) { + return 0; + } + + return sec_keys->pmk_lifetime; +} + uint64_t sec_prot_keys_pmk_replay_cnt_get(sec_prot_keys_t *sec_keys) { return sec_keys->pmk_key_replay_cnt; @@ -184,16 +193,12 @@ bool sec_prot_keys_pmk_mismatch_is_set(sec_prot_keys_t *sec_keys) return sec_keys->pmk_mismatch; } -bool sec_prot_keys_pmk_lifetime_decrement(sec_prot_keys_t *sec_keys, uint32_t default_lifetime, uint8_t seconds) +bool sec_prot_keys_pmk_lifetime_decrement(sec_prot_keys_t *sec_keys, uint8_t seconds) { if (!sec_keys->pmk_set) { return false; } - if (sec_keys->pmk_lifetime == PMK_LIFETIME_INSTALL) { - sec_keys->pmk_lifetime = default_lifetime; - } - if (sec_keys->pmk_lifetime > seconds) { sec_keys->pmk_lifetime -= seconds; } else { @@ -207,10 +212,10 @@ bool sec_prot_keys_pmk_lifetime_decrement(sec_prot_keys_t *sec_keys, uint32_t de return false; } -void sec_prot_keys_ptk_write(sec_prot_keys_t *sec_keys, uint8_t *ptk) +void sec_prot_keys_ptk_write(sec_prot_keys_t *sec_keys, uint8_t *ptk, uint32_t ptk_lifetime) { memcpy(sec_keys->ptk, ptk, PTK_LEN); - sec_keys->ptk_lifetime = PTK_LIFETIME_INSTALL; + sec_keys->ptk_lifetime = ptk_lifetime; sec_keys->ptk_set = true; sec_keys->updated = true; } @@ -218,7 +223,7 @@ void sec_prot_keys_ptk_write(sec_prot_keys_t *sec_keys, uint8_t *ptk) void sec_prot_keys_ptk_delete(sec_prot_keys_t *sec_keys) { memset(sec_keys->ptk, 0, PTK_LEN); - sec_keys->ptk_lifetime = PTK_LIFETIME_INSTALL; + sec_keys->ptk_lifetime = 0; sec_keys->ptk_set = false; sec_keys->updated = true; } @@ -232,6 +237,15 @@ uint8_t *sec_prot_keys_ptk_get(sec_prot_keys_t *sec_keys) return sec_keys->ptk; } +uint32_t sec_prot_keys_ptk_lifetime_get(sec_prot_keys_t *sec_keys) +{ + if (!sec_keys->ptk_set) { + return 0; + } + + return sec_keys->ptk_lifetime; +} + void sec_prot_keys_ptk_mismatch_set(sec_prot_keys_t *sec_keys) { sec_keys->ptk_mismatch = true; @@ -270,16 +284,12 @@ void sec_prot_keys_ptk_eui_64_delete(sec_prot_keys_t *sec_keys) sec_keys->updated = true; } -bool sec_prot_keys_ptk_lifetime_decrement(sec_prot_keys_t *sec_keys, uint32_t default_lifetime, uint8_t seconds) +bool sec_prot_keys_ptk_lifetime_decrement(sec_prot_keys_t *sec_keys, uint8_t seconds) { if (!sec_keys->ptk_set) { return false; } - if (sec_keys->ptk_lifetime == PTK_LIFETIME_INSTALL) { - sec_keys->ptk_lifetime = default_lifetime; - } - if (sec_keys->ptk_lifetime > seconds) { sec_keys->ptk_lifetime -= seconds; } else { @@ -913,7 +923,7 @@ uint8_t sec_prot_keys_gtk_count(sec_prot_gtk_keys_t *gtks) void sec_prot_keys_ptk_installed_gtk_hash_clear_all(sec_prot_keys_t *sec_keys) { for (uint8_t index = 0; index < GTK_NUM; index++) { - memset(sec_keys->ins_gtk_hash[sec_keys->gtk_set_index].hash, 0, INS_GTK_HASH_LEN); + memset(sec_keys->ins_gtk_hash[index].hash, 0, INS_GTK_HASH_LEN); } sec_keys->ins_gtk_hash_set = 0; sec_keys->ins_gtk_4wh_hash_set = 0; diff --git a/source/Security/protocols/sec_prot_keys.h b/source/Security/protocols/sec_prot_keys.h index 376a3f4159..06302519d2 100644 --- a/source/Security/protocols/sec_prot_keys.h +++ b/source/Security/protocols/sec_prot_keys.h @@ -56,9 +56,6 @@ #define GTK_ALL_HASHES_LEN GTK_HASH_LEN * GTK_NUM #define INS_GTK_HASH_LEN 2 -#define PMK_LIFETIME_INSTALL 0xFFFFF -#define PTK_LIFETIME_INSTALL 0xFFFFF - // Limit is 60000 (of 65536) #define PMK_KEY_REPLAY_CNT_LIMIT 60000 // Upper limit for PMK replay counter #define PMK_KEY_REPLAY_CNT_LIMIT_MASK 0xFFFF // Upper limit mask @@ -215,9 +212,10 @@ void sec_prot_keys_gtks_delete(sec_prot_gtk_keys_t *gtks); * * \param sec_keys security keys * \param pmk Pairwise Master Key + * \param pmk_lifetime PMK lifetime * */ -void sec_prot_keys_pmk_write(sec_prot_keys_t *sec_keys, uint8_t *pmk); +void sec_prot_keys_pmk_write(sec_prot_keys_t *sec_keys, uint8_t *pmk, uint32_t pmk_lifetime); /** * sec_prot_keys_pmk_delete deletes PMK @@ -237,6 +235,16 @@ void sec_prot_keys_pmk_delete(sec_prot_keys_t *sec_keys); */ uint8_t *sec_prot_keys_pmk_get(sec_prot_keys_t *sec_keys); +/** + * sec_prot_keys_pmk_lifetime_get Pairwise Master Key lifetime + * + * \param sec_keys security keys + * + * \return PMK lifetime + * + */ +uint32_t sec_prot_keys_pmk_lifetime_get(sec_prot_keys_t *sec_keys); + /** * sec_prot_keys_pmk_replay_cnt_get gets PMK replay counter value * @@ -309,23 +317,23 @@ bool sec_prot_keys_pmk_mismatch_is_set(sec_prot_keys_t *sec_keys); * sec_prot_keys_pmk_lifetime_decrement decrements PMK lifetime * * \param sec_keys security keys - * \param default_lifetime default lifetime for PMK * \param seconds elapsed seconds * * \return true PMK expired and deleted both PMK and PTK * \return false PMK not expired * */ -bool sec_prot_keys_pmk_lifetime_decrement(sec_prot_keys_t *sec_keys, uint32_t default_lifetime, uint8_t seconds); +bool sec_prot_keys_pmk_lifetime_decrement(sec_prot_keys_t *sec_keys, uint8_t seconds); /** * sec_prot_keys_ptk_write writes Pairwise Transient Key * * \param sec_keys security keys * \param ptk Pairwise Transient Key + * \param ptk_lifetime PTK lifetime * */ -void sec_prot_keys_ptk_write(sec_prot_keys_t *sec_keys, uint8_t *ptk); +void sec_prot_keys_ptk_write(sec_prot_keys_t *sec_keys, uint8_t *ptk, uint32_t ptk_lifetime); /** * sec_prot_keys_ptk_delete deletes PTK @@ -345,6 +353,16 @@ void sec_prot_keys_ptk_delete(sec_prot_keys_t *sec_keys); */ uint8_t *sec_prot_keys_ptk_get(sec_prot_keys_t *sec_keys); +/** + * sec_prot_keys_ptk_lifetime_get gets Pairwise Transient Key lifetime + * + * \param sec_keys security keys + * + * \return PTK lifetime + * + */ +uint32_t sec_prot_keys_ptk_lifetime_get(sec_prot_keys_t *sec_keys); + /** * sec_prot_keys_ptk_mismatch_set set PTK mismatch * @@ -402,14 +420,13 @@ void sec_prot_keys_ptk_eui_64_delete(sec_prot_keys_t *sec_keys); * sec_prot_keys_ptk_lifetime_decrement decrements PTK lifetime * * \param sec_keys security keys - * \param default_lifetime default lifetime for PTK * \param seconds elapsed seconds * * \return true PTK expired and deleted * \return false PTK not expired * */ -bool sec_prot_keys_ptk_lifetime_decrement(sec_prot_keys_t *sec_keys, uint32_t default_lifetime, uint8_t seconds); +bool sec_prot_keys_ptk_lifetime_decrement(sec_prot_keys_t *sec_keys, uint8_t seconds); /** * sec_prot_keys_are_updated returns security keys have been updated flag diff --git a/source/Security/protocols/tls_sec_prot/tls_sec_prot.c b/source/Security/protocols/tls_sec_prot/tls_sec_prot.c index 330ed6b143..d4b8c549ae 100644 --- a/source/Security/protocols/tls_sec_prot/tls_sec_prot.c +++ b/source/Security/protocols/tls_sec_prot/tls_sec_prot.c @@ -375,7 +375,7 @@ static void client_tls_sec_prot_state_machine(sec_prot_t *prot) data->calculating = false; if (sec_prot_result_ok_check(&data->common)) { - sec_prot_keys_pmk_write(prot->sec_keys, data->new_pmk); + sec_prot_keys_pmk_write(prot->sec_keys, data->new_pmk, prot->timer_cfg->pmk_lifetime); } // KMP-FINISHED.indication, @@ -494,7 +494,7 @@ static void server_tls_sec_prot_state_machine(sec_prot_t *prot) data->calculating = false; if (sec_prot_result_ok_check(&data->common)) { - sec_prot_keys_pmk_write(prot->sec_keys, data->new_pmk); + sec_prot_keys_pmk_write(prot->sec_keys, data->new_pmk, prot->timer_cfg->pmk_lifetime); } // KMP-FINISHED.indication, diff --git a/source/Service_Libs/etx/etx.c b/source/Service_Libs/etx/etx.c index 639490981a..76b7c7d203 100644 --- a/source/Service_Libs/etx/etx.c +++ b/source/Service_Libs/etx/etx.c @@ -37,9 +37,14 @@ #define TRACE_GROUP "etx" +typedef struct { + uint8_t attribute_index; + const uint8_t *mac64; +} ext_neigh_info_t; + static uint16_t etx_current_calc(uint16_t etx, uint8_t accumulated_failures); static uint16_t etx_dbm_lqi_calc(uint8_t lqi, int8_t dbm); -static void etx_value_change_callback_needed_check(uint16_t etx, uint16_t *stored_diff_etx, uint8_t accumulated_failures, uint8_t attribute_index); +static void etx_value_change_callback_needed_check(uint16_t etx, uint16_t *stored_diff_etx, uint8_t accumulated_failures, ext_neigh_info_t *etx_neigh_info); static void etx_accum_failures_callback_needed_check(etx_storage_t *entry, uint8_t attribute_index); static void etx_cache_entry_init(uint8_t attribute_index); @@ -90,7 +95,7 @@ static ext_info_t etx_info = { .interface_id = -1 }; -static void etx_calculation(etx_storage_t *entry, uint16_t attempts, uint8_t acks_rx, uint8_t attribute_index) +static void etx_calculation(etx_storage_t *entry, uint16_t attempts, uint8_t acks_rx, ext_neigh_info_t *etx_neigh_info) { if (etx_info.hysteresis && !entry->stored_diff_etx) { if (entry->etx_samples >= etx_info.init_etx_sample_count) { @@ -130,9 +135,9 @@ static void etx_calculation(etx_storage_t *entry, uint16_t attempts, uint8_t ack entry->etx = etx; if (entry->etx_samples >= etx_info.init_etx_sample_count) { - etx_cache_entry_init(attribute_index); + etx_cache_entry_init(etx_neigh_info->attribute_index); // Checks if ETX value change callback is needed - etx_value_change_callback_needed_check(entry->etx, &(entry->stored_diff_etx), entry->accumulated_failures, attribute_index); + etx_value_change_callback_needed_check(entry->etx, &(entry->stored_diff_etx), entry->accumulated_failures, etx_neigh_info); } } @@ -203,7 +208,7 @@ static etx_sample_storage_t *etx_cache_sample_update(uint8_t attribute_index, ui * \param addr_type address type, ADDR_802_15_4_SHORT or ADDR_802_15_4_LONG * \param addr_ptr PAN ID with 802.15.4 address */ -void etx_transm_attempts_update(int8_t interface_id, uint8_t attempts, bool success, uint8_t attribute_index) +void etx_transm_attempts_update(int8_t interface_id, uint8_t attempts, bool success, uint8_t attribute_index, const uint8_t *mac64_addr_ptr) { uint8_t accumulated_failures; // Gets table entry @@ -212,6 +217,10 @@ void etx_transm_attempts_update(int8_t interface_id, uint8_t attempts, bool succ return; } + ext_neigh_info_t etx_neigh_info; + etx_neigh_info.attribute_index = attribute_index; + etx_neigh_info.mac64 = mac64_addr_ptr; + if (entry->etx_samples < 7) { entry->etx_samples++; } @@ -225,7 +234,7 @@ void etx_transm_attempts_update(int8_t interface_id, uint8_t attempts, bool succ return; } - etx_calculation(entry, storage->attempts_count, storage->received_acks, attribute_index); + etx_calculation(entry, storage->attempts_count, storage->received_acks, &etx_neigh_info); if (entry->etx_samples < 7 && !success) { entry->etx_samples = 7; //Stop Probing to failure @@ -254,7 +263,7 @@ void etx_transm_attempts_update(int8_t interface_id, uint8_t attempts, bool succ if (entry->etx) { if (success) { - etx_calculation(entry, attempts + accumulated_failures, 1, attribute_index); + etx_calculation(entry, attempts + accumulated_failures, 1, &etx_neigh_info); } } } @@ -268,35 +277,42 @@ void etx_transm_attempts_update(int8_t interface_id, uint8_t attempts, bool succ * \param remote_incoming_idr Remote incoming IDR * \param mac64_addr_ptr long MAC address */ -void etx_remote_incoming_idr_update(int8_t interface_id, uint8_t remote_incoming_idr, uint8_t attribute_index) +void etx_remote_incoming_idr_update(int8_t interface_id, uint8_t remote_incoming_idr, uint8_t attribute_index, const uint8_t *mac64_addr_ptr) { etx_storage_t *entry = etx_storage_entry_get(interface_id, attribute_index); - - if (entry) { - // If ETX has been set - if (entry->etx) { - // If hysteresis is set stores ETX value to enable comparison - if (etx_info.hysteresis && !entry->stored_diff_etx) { - entry->stored_diff_etx = entry->etx; - } - // remote EXT = remote incoming IDR^2 (12 bit fraction) - uint32_t remote_ext = ((uint32_t)remote_incoming_idr * remote_incoming_idr) << 2; - - // ETX = 7/8 * current ETX + 1/8 * remote ETX */ - uint32_t etx = entry->etx - (entry->etx >> ETX_MOVING_AVERAGE_FRACTION); - etx += remote_ext >> ETX_MOVING_AVERAGE_FRACTION; - - if (etx > 0xffff) { - entry->etx = 0xffff; - } else { - entry->etx = etx; - } - - // Checks if ETX value change callback is needed - etx_value_change_callback_needed_check(entry->etx, &(entry->stored_diff_etx), entry->accumulated_failures, attribute_index); - } - entry->remote_incoming_idr = remote_incoming_idr; + if (!entry) { + return; } + + ext_neigh_info_t etx_neigh_info; + etx_neigh_info.attribute_index = attribute_index; + etx_neigh_info.mac64 = mac64_addr_ptr; + + + // If ETX has been set + if (entry->etx) { + // If hysteresis is set stores ETX value to enable comparison + if (etx_info.hysteresis && !entry->stored_diff_etx) { + entry->stored_diff_etx = entry->etx; + } + // remote EXT = remote incoming IDR^2 (12 bit fraction) + uint32_t remote_ext = ((uint32_t)remote_incoming_idr * remote_incoming_idr) << 2; + + // ETX = 7/8 * current ETX + 1/8 * remote ETX */ + uint32_t etx = entry->etx - (entry->etx >> ETX_MOVING_AVERAGE_FRACTION); + etx += remote_ext >> ETX_MOVING_AVERAGE_FRACTION; + + if (etx > 0xffff) { + entry->etx = 0xffff; + } else { + entry->etx = etx; + } + + // Checks if ETX value change callback is needed + etx_value_change_callback_needed_check(entry->etx, &(entry->stored_diff_etx), entry->accumulated_failures, &etx_neigh_info); + } + entry->remote_incoming_idr = remote_incoming_idr; + } /** @@ -442,14 +458,18 @@ static uint16_t etx_current_calc(uint16_t etx, uint8_t accumulated_failures) * * \return 0x0100 to 0xFFFF local incoming IDR value (8 bit fraction) */ -uint16_t etx_lqi_dbm_update(int8_t interface_id, uint8_t lqi, int8_t dbm, uint8_t attribute_index) +uint16_t etx_lqi_dbm_update(int8_t interface_id, uint8_t lqi, int8_t dbm, uint8_t attribute_index, const uint8_t *mac64_addr_ptr) { uint32_t local_incoming_idr = 0; uint32_t etx = 0; etx_storage_t *entry = etx_storage_entry_get(interface_id, attribute_index); + if (entry) { + ext_neigh_info_t etx_neigh_info; + etx_neigh_info.attribute_index = attribute_index; + etx_neigh_info.mac64 = mac64_addr_ptr; // If local ETX is not set calculate it based on LQI and dBm if (!entry->etx) { etx = etx_dbm_lqi_calc(lqi, dbm); @@ -458,7 +478,7 @@ uint16_t etx_lqi_dbm_update(int8_t interface_id, uint8_t lqi, int8_t dbm, uint8_ entry->tmp_etx = true; if (etx_info.callback_ptr) { etx_info.callback_ptr(etx_info.interface_id, 0, entry->etx >> 4, - attribute_index); + attribute_index, mac64_addr_ptr); } } // If local ETX has been calculated without remote incoming IDR and @@ -474,7 +494,7 @@ uint16_t etx_lqi_dbm_update(int8_t interface_id, uint8_t lqi, int8_t dbm, uint8_ entry->etx = etx >> 12; local_incoming_idr >>= 4; - etx_value_change_callback_needed_check(entry->etx, &(entry->stored_diff_etx), entry->accumulated_failures, attribute_index); + etx_value_change_callback_needed_check(entry->etx, &(entry->stored_diff_etx), entry->accumulated_failures, &etx_neigh_info); } } @@ -721,7 +741,7 @@ uint8_t etx_accum_failures_callback_register(nwk_interface_id nwk_id, int8_t int * * \return ETX value (12 bit fraction) */ -static void etx_value_change_callback_needed_check(uint16_t etx, uint16_t *stored_diff_etx, uint8_t accumulated_failures, uint8_t attribute_index) +static void etx_value_change_callback_needed_check(uint16_t etx, uint16_t *stored_diff_etx, uint8_t accumulated_failures, ext_neigh_info_t *etx_neigh_info) { uint16_t current_etx; bool callback = false; @@ -747,7 +767,7 @@ static void etx_value_change_callback_needed_check(uint16_t etx, uint16_t *store // Calls callback function if (callback) { - etx_info.callback_ptr(etx_info.interface_id, (*stored_diff_etx) >> 4, current_etx >> 4, attribute_index); + etx_info.callback_ptr(etx_info.interface_id, (*stored_diff_etx) >> 4, current_etx >> 4, etx_neigh_info->attribute_index, etx_neigh_info->mac64); *stored_diff_etx = current_etx; } } @@ -782,7 +802,7 @@ static void etx_accum_failures_callback_needed_check(etx_storage_t *entry, uint8 * \param mac64_addr_ptr long MAC address * */ -void etx_neighbor_remove(int8_t interface_id, uint8_t attribute_index) +void etx_neighbor_remove(int8_t interface_id, uint8_t attribute_index, const uint8_t *mac64_addr_ptr) { //tr_debug("Remove attribute %u", attribute_index); @@ -795,7 +815,8 @@ void etx_neighbor_remove(int8_t interface_id, uint8_t attribute_index) if (!stored_diff_etx) { stored_diff_etx = 0xffff; } - etx_info.callback_ptr(etx_info.interface_id, stored_diff_etx, 0xffff, attribute_index); + + etx_info.callback_ptr(etx_info.interface_id, stored_diff_etx, 0xffff, attribute_index, mac64_addr_ptr); } if (etx_info.cache_sample_requested) { @@ -829,7 +850,10 @@ void etx_cache_timer(int8_t interface_id, uint16_t seconds_update) etx_sample_storage_t *storage = etx_info.etx_cache_storage_list + neighbour->index; if (etx_update_possible(storage, etx_entry, seconds_update)) { - etx_calculation(etx_entry, storage->attempts_count, storage->received_acks, neighbour->index); + ext_neigh_info_t etx_neigh_info; + etx_neigh_info.attribute_index = neighbour->index; + etx_neigh_info.mac64 = neighbour->mac64; + etx_calculation(etx_entry, storage->attempts_count, storage->received_acks, &etx_neigh_info); } } diff --git a/source/Service_Libs/etx/etx.h b/source/Service_Libs/etx/etx.h index c785cc5c98..a1c40b2694 100644 --- a/source/Service_Libs/etx/etx.h +++ b/source/Service_Libs/etx/etx.h @@ -76,8 +76,9 @@ typedef struct etx_sample_storage_s { * \param attempts number of attempts to send message * \param success was message sending successful * \param attribute_index Neighbour attribute index + * \param mac64_addr_ptr Neighbour MAC64 */ -void etx_transm_attempts_update(int8_t interface_id, uint8_t attempts, bool success, uint8_t attribute_index); +void etx_transm_attempts_update(int8_t interface_id, uint8_t attempts, bool success, uint8_t attribute_index, const uint8_t *mac64_addr_ptr); /** * \brief A function to update ETX value based on remote incoming IDR @@ -88,8 +89,9 @@ void etx_transm_attempts_update(int8_t interface_id, uint8_t attempts, bool succ * \param interface_id Interface identifier * \param remote_incoming_idr Remote incoming IDR * \param attribute_index Neighbour attribute index + * \param mac64_addr_ptr Neighbour MAC64 */ -void etx_remote_incoming_idr_update(int8_t interface_id, uint8_t remote_incoming_idr, uint8_t attribute_index); +void etx_remote_incoming_idr_update(int8_t interface_id, uint8_t remote_incoming_idr, uint8_t attribute_index, const uint8_t *mac64_addr_ptr); /** * \brief A function to read ETX value @@ -139,10 +141,11 @@ uint16_t etx_local_etx_read(int8_t interface_id, uint8_t attribute_index); * \param lqi link quality indicator * \param dbm measured dBm * \param attribute_index Neighbour attribute index + * \param mac64_addr_ptr Neighbour MAC64 * * \return 0x0100 to 0xFFFF local incoming IDR value (8 bit fraction) */ -uint16_t etx_lqi_dbm_update(int8_t interface_id, uint8_t lqi, int8_t dbm, uint8_t attribute_index); +uint16_t etx_lqi_dbm_update(int8_t interface_id, uint8_t lqi, int8_t dbm, uint8_t attribute_index, const uint8_t *mac64_addr_ptr); /** * \brief A function callback that indicates ETX value change @@ -154,9 +157,10 @@ uint16_t etx_lqi_dbm_update(int8_t interface_id, uint8_t lqi, int8_t dbm, uint8_ * \param previous_etx ETX value to what the current ETX was compared (8 bit fraction) * \param current_etx current ETX value (8 bit fraction) * \param attribute_index Neighbour attribute index + * \param mac64_addr_ptr Pointer to MAC64 for given etx update * */ -typedef void (etx_value_change_handler_t)(int8_t nwk_id, uint16_t previous_etx, uint16_t current_etx, uint8_t attribute_index); +typedef void (etx_value_change_handler_t)(int8_t nwk_id, uint16_t previous_etx, uint16_t current_etx, uint8_t attribute_index, const uint8_t *mac64_addr_ptr); /** * \brief A function callback that indicates the number of accumulated TX failures @@ -232,9 +236,10 @@ uint8_t etx_accum_failures_callback_register(nwk_interface_id nwk_id, int8_t int * if that is set. * * \param attribute_index Neighbour attribute index + * \param mac64_addr_ptr Neighbour MAC64 * */ -void etx_neighbor_remove(int8_t interface_id, uint8_t attribute_index); +void etx_neighbor_remove(int8_t interface_id, uint8_t attribute_index, const uint8_t *mac64_addr_ptr); /** * \brief A function for update cached ETX calculation diff --git a/test/nanostack/unittest/mac/mac_cca_threshold/Makefile b/test/nanostack/unittest/mac/mac_cca_threshold/Makefile deleted file mode 100644 index a3cec64068..0000000000 --- a/test/nanostack/unittest/mac/mac_cca_threshold/Makefile +++ /dev/null @@ -1,19 +0,0 @@ -include ../../makefile_defines.txt - -COMPONENT_NAME = mac_cca_threshold_unit - -#This must be changed manually -SRC_FILES = \ - ../../../../../source/MAC/IEEE802_15_4/mac_cca_threshold.c - -TEST_SRC_FILES = \ - main.cpp \ - mac_cca_threshold_test.cpp \ - test_mac_cca_threshold.c \ - ../../stub/mbed_trace_stub.c \ - ../../stub/nsdynmemLIB_stub.c \ - -include ../../MakefileWorker.mk - -CPPUTESTFLAGS += -DFEA_TRACE_SUPPORT - diff --git a/test/nanostack/unittest/mac/mac_cca_threshold/mac_cca_threshold_test.cpp b/test/nanostack/unittest/mac/mac_cca_threshold/mac_cca_threshold_test.cpp deleted file mode 100644 index 62a4ea4ff4..0000000000 --- a/test/nanostack/unittest/mac/mac_cca_threshold/mac_cca_threshold_test.cpp +++ /dev/null @@ -1,47 +0,0 @@ -/* - * Copyright (c) 2016-2018, Arm Limited and affiliates. - * SPDX-License-Identifier: Apache-2.0 - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -#include "CppUTest/TestHarness.h" -#include "test_mac_cca_threshold.h" - -TEST_GROUP(mac_cca_threshold) -{ - void setup() { - } - - void teardown() { - } -}; - -TEST(mac_cca_threshold, test_mac_cca_thr_init) -{ - CHECK(test_mac_cca_thr_init()); -} - -TEST(mac_cca_threshold, test_mac_cca_thr_update_channel_threshold) -{ - CHECK(test_mac_cca_thr_update_channel_threshold()); -} - -TEST(mac_cca_threshold, test_mac_cca_thr_channel_failed) -{ - CHECK(test_mac_cca_thr_channel_failed()); -} - -TEST(mac_cca_threshold, test_mac_cca_threshold_update) -{ - CHECK(test_mac_cca_threshold_update()); -} diff --git a/test/nanostack/unittest/mac/mac_cca_threshold/main.cpp b/test/nanostack/unittest/mac/mac_cca_threshold/main.cpp deleted file mode 100644 index e362bd7009..0000000000 --- a/test/nanostack/unittest/mac/mac_cca_threshold/main.cpp +++ /dev/null @@ -1,28 +0,0 @@ -/* - * Copyright (c) 2016-2018, Arm Limited and affiliates. - * SPDX-License-Identifier: Apache-2.0 - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#include "CppUTest/CommandLineTestRunner.h" -#include "CppUTest/TestPlugin.h" -#include "CppUTest/TestRegistry.h" -#include "CppUTestExt/MockSupportPlugin.h" -int main(int ac, char **av) -{ - return CommandLineTestRunner::RunAllTests(ac, av); -} - -IMPORT_TEST_GROUP(mac_cca_threshold); - diff --git a/test/nanostack/unittest/mac/mac_cca_threshold/test_mac_cca_threshold.c b/test/nanostack/unittest/mac/mac_cca_threshold/test_mac_cca_threshold.c deleted file mode 100644 index 5d7f9bffb1..0000000000 --- a/test/nanostack/unittest/mac/mac_cca_threshold/test_mac_cca_threshold.c +++ /dev/null @@ -1,188 +0,0 @@ -/* - * Copyright (c) 2020, Arm Limited and affiliates. - * SPDX-License-Identifier: Apache-2.0 - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -#include "nsconfig.h" -#include "test_mac_cca_threshold.h" -#include "mac_defines.h" -#include "nsdynmemLIB_stub.h" -#include "MAC/IEEE802_15_4/mac_cca_threshold.h" - -static protocol_interface_rf_mac_setup_s setup; - -static void test_free() -{ - if (setup.cca_threshold && setup.cca_threshold->ch_thresholds) { - free(setup.cca_threshold->ch_thresholds); - } - if (setup.cca_threshold) { - free(setup.cca_threshold); - } -} - -static void test_initialize(void) -{ - memset(&setup, 0, sizeof(protocol_interface_rf_mac_setup_s)); -} - -bool test_mac_cca_threshold_update() -{ - uint8_t number_of_channels = 64; - int8_t default_dbm = -60; - int8_t high_limit = -30; - int8_t low_limit = -120; - test_initialize(); - // Initialize CCA threshold - nsdynmemlib_stub.returnCounter = 2; - mac_cca_thr_init(&setup, number_of_channels, default_dbm, high_limit, low_limit); - // Test calling init again - nsdynmemlib_stub.returnCounter = 2; - mac_cca_thr_init(&setup, number_of_channels, default_dbm, high_limit, low_limit); - // Test all channels set to default dBm - for (int i = 0; i < number_of_channels; i++) { - if (mac_cca_thr_get_dbm(&setup, i) != default_dbm) { - return false; - } - } - // Test several CCA fails - for (int i = 0; i < 5; i++) { - mac_cca_threshold_update(&setup, 10, 127); - } - if (mac_cca_thr_get_dbm(&setup, 10) != default_dbm + (5 * CCA_THRESHOLD_STEP)) { - return false; - } - // Test setting to low limit - mac_cca_threshold_update(&setup, 10, -125); - if (mac_cca_thr_get_dbm(&setup, 10) != low_limit) { - return false; - } - mac_cca_threshold_update(&setup, 10, 127); - if (mac_cca_thr_get_dbm(&setup, 10) != (low_limit + CCA_THRESHOLD_STEP)) { - return false; - } - // Test receiving same dBm as low limit - mac_cca_threshold_update(&setup, 10, -120); - if (mac_cca_thr_get_dbm(&setup, 10) != low_limit) { - return false; - } - // Test receiving step above low limit - mac_cca_threshold_update(&setup, 10, -120 + CCA_THRESHOLD_STEP); - if (mac_cca_thr_get_dbm(&setup, 10) != low_limit) { - return false; - } - test_free(); - return true; -} - - -bool test_mac_cca_thr_channel_failed() -{ - uint8_t number_of_channels = 35; - int8_t default_dbm = -31; - int8_t high_limit = -30; - int8_t low_limit = -100; - test_initialize(); - // Initialize CCA threshold - nsdynmemlib_stub.returnCounter = 2; - mac_cca_thr_init(&setup, number_of_channels, default_dbm, high_limit, low_limit); - // Test that default dBm is set - if (setup.cca_threshold->ch_thresholds[10] != default_dbm) { - return false; - } - // Test setting above high limit - if (mac_cca_threshold_update(&setup, 10, 127) || setup.cca_threshold->ch_thresholds[10] != high_limit) { - return false; - } - // Test setting above high limit again - if (!mac_cca_threshold_update(&setup, 10, 127) || setup.cca_threshold->ch_thresholds[10] != high_limit) { - return false; - } - //Set threshold to -65 - CCA_THRESHOLD_STEP - mac_cca_threshold_update(&setup, 10, -65); - // Test setting one step high with CCA fail - if (mac_cca_threshold_update(&setup, 10, 127) || setup.cca_threshold->ch_thresholds[10] != -65) { - return false; - } - test_free(); - return true; -} - -bool test_mac_cca_thr_update_channel_threshold() -{ - uint8_t number_of_channels = 35; - int8_t default_dbm = -50; - int8_t high_limit = -30; - int8_t low_limit = -100; - test_initialize(); - // Initialize CCA threshold - nsdynmemlib_stub.returnCounter = 2; - mac_cca_thr_init(&setup, number_of_channels, default_dbm, high_limit, low_limit); - // Test that default dBm is set - if (setup.cca_threshold->ch_thresholds[10] != default_dbm) { - return false; - } - // Test setting new threshold - if (mac_cca_threshold_update(&setup, 10, -70) || setup.cca_threshold->ch_thresholds[10] != (-70 - CCA_THRESHOLD_STEP)) { - return false; - } - // Test if packet received with higher dBm - if (!mac_cca_threshold_update(&setup, 10, -65) || setup.cca_threshold->ch_thresholds[10] != (-70 - CCA_THRESHOLD_STEP)) { - return false; - } - // Test setting to low limit - if (mac_cca_threshold_update(&setup, 10, -101) || setup.cca_threshold->ch_thresholds[10] != low_limit) { - return false; - } - // Test received lower RSSI than low limit - if (!mac_cca_threshold_update(&setup, 10, -101) || setup.cca_threshold->ch_thresholds[10] != low_limit) { - return false; - } - test_free(); - return true; -} - -bool test_mac_cca_thr_init() -{ - test_initialize(); - // Test default dBm above high limit - if (!mac_cca_thr_init(&setup, 35, -10, -11, -110)) { - return false; - } - // Test default dBm below low limit - if (!mac_cca_thr_init(&setup, 35, -111, -11, -110)) { - return false; - } - // Test high limit below low limit - if (!mac_cca_thr_init(&setup, 35, -50, -110, -11)) { - return false; - } - nsdynmemlib_stub.returnCounter = 0; - // Test allocation failed - if (!mac_cca_thr_init(&setup, 35, -50, -30, -100)) { - return false; - } - nsdynmemlib_stub.returnCounter = 1; - // Test second allocation failed - if (!mac_cca_thr_init(&setup, 35, -50, -30, -100)) { - return false; - } - nsdynmemlib_stub.returnCounter = 2; - // Test success - if (mac_cca_thr_init(&setup, 35, -50, -30, -100)) { - return false; - } - test_free(); - return true; -} diff --git a/test/nanostack/unittest/mac/mac_cca_threshold/test_mac_cca_threshold.h b/test/nanostack/unittest/mac/mac_cca_threshold/test_mac_cca_threshold.h deleted file mode 100644 index 85ca78c556..0000000000 --- a/test/nanostack/unittest/mac/mac_cca_threshold/test_mac_cca_threshold.h +++ /dev/null @@ -1,36 +0,0 @@ -/* - * Copyright (c) 2020, Arm Limited and affiliates. - * SPDX-License-Identifier: Apache-2.0 - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -#ifndef TEST_MAC_CCA_THRESHOLD_H -#define TEST_MAC_CCA_THRESHOLD_H - -#ifdef __cplusplus -extern "C" { -#endif - -#include - -bool test_mac_cca_thr_init(); -bool test_mac_cca_thr_update_channel_threshold(); -bool test_mac_cca_thr_channel_failed(); -bool test_mac_cca_threshold_update(); - -#ifdef __cplusplus -} -#endif - -#endif // TEST_MAC_CCA_THRESHOLD_H - diff --git a/test/nanostack/unittest/stub/mac_cca_threshold_stub.c b/test/nanostack/unittest/stub/mac_cca_threshold_stub.c deleted file mode 100644 index f1c88fb722..0000000000 --- a/test/nanostack/unittest/stub/mac_cca_threshold_stub.c +++ /dev/null @@ -1,43 +0,0 @@ -/* - * Copyright (c) 2020, Arm Limited and affiliates. - * SPDX-License-Identifier: Apache-2.0 - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#include "nsconfig.h" -#include -#include "ns_types.h" -#include "ns_list.h" -#include "ns_trace.h" -#include "mac_defines.h" - -int8_t mac_cca_threshold_update(protocol_interface_rf_mac_setup_s *rf_ptr, uint16_t event_data) -{ - return 0; -} - -int8_t mac_cca_thr_deinit(protocol_interface_rf_mac_setup_s *rf_ptr) -{ - return 0; -} - -int8_t mac_cca_thr_init(protocol_interface_rf_mac_setup_s *rf_ptr, uint8_t number_of_channels, int8_t default_dbm, int8_t high_limit, int8_t low_limit) -{ - return 0; -} - -int8_t mac_cca_thr_get_dbm(protocol_interface_rf_mac_setup_s *rf_ptr, uint8_t channel) -{ - return 0; -} diff --git a/test/nanostack/unittest/stub/ns_monitor_stub.h b/test/nanostack/unittest/stub/ns_monitor_stub.h deleted file mode 100644 index f3fdc22c59..0000000000 --- a/test/nanostack/unittest/stub/ns_monitor_stub.h +++ /dev/null @@ -1,35 +0,0 @@ -/* - * Copyright (c) 2015-2017, Arm Limited and affiliates. - * SPDX-License-Identifier: Apache-2.0 - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -#ifndef __NS_MONITOR_STUB_H__ -#define __NS_MONITOR_STUB_H__ - -#ifdef __cplusplus -extern "C" { -#endif - -typedef struct { - bool return_bool; -} ns_monitor_stub_def; - -extern ns_monitor_stub_def ns_monitor_stub; - - -#ifdef __cplusplus -} -#endif - -#endif // __NS_MONITOR_STUB_H__