diff --git a/features/lorawan/LoRaWANStack.cpp b/features/lorawan/LoRaWANStack.cpp index 418322ed14..7745a07f5a 100644 --- a/features/lorawan/LoRaWANStack.cpp +++ b/features/lorawan/LoRaWANStack.cpp @@ -224,11 +224,6 @@ lorawan_status_t LoRaWANStack::send_compliance_test_frame_to_mac() { loramac_mcps_req_t mcps_req; - get_phy_params_t phy_params; - phy_param_t default_datarate; - phy_params.attribute = PHY_DEF_TX_DR; - default_datarate = _lora_phy.get_phy_params(&phy_params); - prepare_special_tx_frame(_compliance_test.app_port); if (!_compliance_test.is_tx_confirmed) { @@ -236,7 +231,7 @@ lorawan_status_t LoRaWANStack::send_compliance_test_frame_to_mac() mcps_req.req.unconfirmed.fport = _compliance_test.app_port; mcps_req.f_buffer = _tx_msg.f_buffer; mcps_req.f_buffer_size = _tx_msg.f_buffer_size; - mcps_req.req.unconfirmed.data_rate = default_datarate.value; + mcps_req.req.unconfirmed.data_rate = _lora_phy.get_default_tx_datarate(); tr_info("Transmit unconfirmed compliance test frame %d bytes.", mcps_req.f_buffer_size); @@ -249,7 +244,7 @@ lorawan_status_t LoRaWANStack::send_compliance_test_frame_to_mac() mcps_req.f_buffer = _tx_msg.f_buffer; mcps_req.f_buffer_size = _tx_msg.f_buffer_size; mcps_req.req.confirmed.nb_trials = _num_retry; - mcps_req.req.confirmed.data_rate = default_datarate.value; + mcps_req.req.confirmed.data_rate = _lora_phy.get_default_tx_datarate(); tr_info("Transmit confirmed compliance test frame %d bytes.", mcps_req.f_buffer_size); @@ -286,11 +281,6 @@ lorawan_status_t LoRaWANStack::send_frame_to_mac() lorawan_status_t status; loramac_mib_req_confirm_t mib_get_params; - get_phy_params_t phy_params; - phy_param_t default_datarate; - phy_params.attribute = PHY_DEF_TX_DR; - default_datarate = _lora_phy.get_phy_params(&phy_params); - mcps_req.type = _tx_msg.type; if (MCPS_UNCONFIRMED == mcps_req.type) { @@ -302,7 +292,7 @@ lorawan_status_t LoRaWANStack::send_frame_to_mac() mib_get_params.type = MIB_CHANNELS_DATARATE; if(mib_get_request(&mib_get_params) != LORAWAN_STATUS_OK) { tr_debug("Couldn't get MIB parameters: Using default data rate"); - mcps_req.req.unconfirmed.data_rate = default_datarate.value; + mcps_req.req.unconfirmed.data_rate = _lora_phy.get_default_tx_datarate(); } else { mcps_req.req.unconfirmed.data_rate = mib_get_params.param.channel_data_rate; } @@ -316,7 +306,7 @@ lorawan_status_t LoRaWANStack::send_frame_to_mac() mib_get_params.type = MIB_CHANNELS_DATARATE; if(mib_get_request(&mib_get_params) != LORAWAN_STATUS_OK) { tr_debug("Couldn't get MIB parameters: Using default data rate"); - mcps_req.req.confirmed.data_rate = default_datarate.value; + mcps_req.req.confirmed.data_rate = _lora_phy.get_default_tx_datarate(); } else { mcps_req.req.confirmed.data_rate = mib_get_params.param.channel_data_rate; } @@ -328,7 +318,7 @@ lorawan_status_t LoRaWANStack::send_frame_to_mac() mib_get_params.type = MIB_CHANNELS_DATARATE; if(mib_get_request(&mib_get_params) != LORAWAN_STATUS_OK) { tr_debug("Couldn't get MIB parameters: Using default data rate"); - mcps_req.req.proprietary.data_rate = default_datarate.value; + mcps_req.req.proprietary.data_rate = _lora_phy.get_default_tx_datarate(); } else { mcps_req.req.proprietary.data_rate = mib_get_params.param.channel_data_rate; } diff --git a/features/lorawan/lorastack/mac/LoRaMac.cpp b/features/lorawan/lorastack/mac/LoRaMac.cpp index 7a22e61d4e..8a4403e731 100644 --- a/features/lorawan/lorastack/mac/LoRaMac.cpp +++ b/features/lorawan/lorastack/mac/LoRaMac.cpp @@ -218,8 +218,6 @@ void LoRaMac::handle_rx2_timer_event(void) **************************************************************************/ void LoRaMac::on_radio_tx_done( void ) { - get_phy_params_t get_phy; - phy_param_t phy_param; set_band_txdone_params_t tx_done_params; lorawan_time_t cur_time = _lora_time.get_current_time( ); loramac_mlme_confirm_t mlme_confirm = mlme.get_confirmation(); @@ -240,10 +238,8 @@ void LoRaMac::on_radio_tx_done( void ) if ((_params.dev_class == CLASS_C ) || (_params.is_node_ack_requested == true)) { - get_phy.attribute = PHY_ACK_TIMEOUT; - phy_param = lora_phy->get_phy_params(&get_phy); _lora_time.start(_params.timers.ack_timeout_timer, - _params.rx_window2_delay + phy_param.value); + _params.rx_window2_delay + lora_phy->get_ack_timeout()); } } else { mcps.get_confirmation().status = LORAMAC_EVENT_INFO_STATUS_OK; @@ -303,8 +299,6 @@ void LoRaMac::on_radio_rx_done(uint8_t *payload, uint16_t size, int16_t rssi, loramac_mhdr_t mac_hdr; loramac_frame_ctrl_t fctrl; cflist_params_t cflist; - get_phy_params_t get_phy; - phy_param_t phy_param; bool skip_indication = false; uint8_t pkt_header_len = 0; @@ -428,18 +422,9 @@ void LoRaMac::on_radio_rx_done(uint8_t *payload, uint16_t size, int16_t rssi, case FRAME_TYPE_DATA_CONFIRMED_DOWN: case FRAME_TYPE_DATA_UNCONFIRMED_DOWN: { - // Check if the received payload size is valid - get_phy.datarate = mcps.get_indication().rx_datarate; - get_phy.attribute = PHY_MAX_PAYLOAD; + uint8_t value = lora_phy->get_max_payload(mcps.get_indication().rx_datarate, _params.is_repeater_supported); - // Get the maximum payload length - if (_params.is_repeater_supported == true) { - get_phy.attribute = PHY_MAX_PAYLOAD_REPEATER; - } - - phy_param = lora_phy->get_phy_params(&get_phy); - - if (MAX(0, (int16_t) ((int16_t)size - (int16_t)LORA_MAC_FRMPAYLOAD_OVERHEAD )) > (int32_t)phy_param.value) { + if (MAX(0, (int16_t) ((int16_t)size - (int16_t)LORA_MAC_FRMPAYLOAD_OVERHEAD )) > (int32_t)value) { mcps.get_indication().status = LORAMAC_EVENT_INFO_STATUS_ERROR; prepare_rx_done_abort(); return; @@ -516,11 +501,7 @@ void LoRaMac::on_radio_rx_done(uint8_t *payload, uint16_t size, int16_t rssi, } } - // Check for a the maximum allowed counter difference - get_phy.attribute = PHY_MAX_FCNT_GAP; - phy_param = lora_phy->get_phy_params(&get_phy); - - if (sequence_counter_diff >= phy_param.value) { + if (sequence_counter_diff >= lora_phy->get_maximum_frame_counter_gap()) { mcps.get_indication().status = LORAMAC_EVENT_INFO_STATUS_DOWNLINK_TOO_MANY_FRAMES_LOSS; mcps.get_indication().dl_frame_counter = downlink_counter; prepare_rx_done_abort( ); @@ -816,8 +797,6 @@ void LoRaMac::on_radio_rx_timeout(void) **************************************************************************/ void LoRaMac::on_mac_state_check_timer_event(void) { - get_phy_params_t get_phy; - phy_param_t phy_param; bool tx_timeout = false; _lora_time.stop(_params.timers.mac_state_check_timer); @@ -916,10 +895,8 @@ void LoRaMac::on_mac_state_check_timer_event(void) _params.ack_timeout_retry_counter++; if ((_params.ack_timeout_retry_counter % 2) == 1) { - get_phy.attribute = PHY_NEXT_LOWER_TX_DR; - get_phy.datarate = _params.sys_params.channel_data_rate; - phy_param = lora_phy->get_phy_params( &get_phy ); - _params.sys_params.channel_data_rate = phy_param.value; + _params.sys_params.channel_data_rate = lora_phy->get_next_lower_tx_datarate( + _params.sys_params.channel_data_rate); } // Try to send the frame again @@ -1116,21 +1093,10 @@ void LoRaMac::rx_window_setup(bool rx_continuous, uint32_t max_rx_window_time) bool LoRaMac::validate_payload_length(uint8_t length, int8_t datarate, uint8_t fopts_len) { - get_phy_params_t get_phy; - phy_param_t phy_param; uint16_t max_value = 0; uint16_t payloadSize = 0; - // Setup PHY request - get_phy.datarate = datarate; - get_phy.attribute = PHY_MAX_PAYLOAD; - - // Get the maximum payload length - if (_params.is_repeater_supported == true) { - get_phy.attribute = PHY_MAX_PAYLOAD_REPEATER; - } - phy_param = lora_phy->get_phy_params(&get_phy); - max_value = phy_param.value; + max_value = lora_phy->get_max_payload(datarate, _params.is_repeater_supported); // Calculate the resulting payload size payloadSize = (length + fopts_len); @@ -1186,8 +1152,6 @@ lorawan_status_t LoRaMac::schedule_tx(void) { lorawan_time_t dutyCycleTimeOff = 0; channel_selection_params_t nextChan; - get_phy_params_t getPhy; - phy_param_t phyParam; // Check if the device is off if (_params.sys_params.max_duty_cycle == 255) { @@ -1212,10 +1176,7 @@ lorawan_status_t LoRaMac::schedule_tx(void) while (lora_phy->set_next_channel(&nextChan, &_params.channel, &dutyCycleTimeOff, &_params.timers.aggregated_timeoff) == false) { - // Set the default datarate - getPhy.attribute = PHY_DEF_TX_DR; - phyParam = lora_phy->get_phy_params(&getPhy); - _params.sys_params.channel_data_rate = phyParam.value; + _params.sys_params.channel_data_rate = lora_phy->get_default_tx_datarate(); // Update datarate in the function parameters nextChan.current_datarate = _params.sys_params.channel_data_rate; } @@ -1291,9 +1252,6 @@ void LoRaMac::calculate_backOff(uint8_t channel) void LoRaMac::reset_mac_parameters(void) { - get_phy_params_t get_phy; - phy_param_t phy_param; - _params.is_nwk_joined = false; // Counters @@ -1316,37 +1274,21 @@ void LoRaMac::reset_mac_parameters(void) _params.is_rx_window_enabled = true; - get_phy.attribute = PHY_DEF_TX_POWER; - phy_param = lora_phy->get_phy_params(&get_phy); + _params.sys_params.channel_tx_power = lora_phy->get_default_tx_power(); - _params.sys_params.channel_tx_power = phy_param.value; + _params.sys_params.channel_data_rate = lora_phy->get_default_tx_datarate(); - get_phy.attribute = PHY_DEF_TX_DR; - phy_param = lora_phy->get_phy_params(&get_phy); - _params.sys_params.channel_data_rate = phy_param.value; + _params.sys_params.rx1_dr_offset = lora_phy->get_default_datarate1_offset(); - get_phy.attribute = PHY_DEF_DR1_OFFSET; - phy_param = lora_phy->get_phy_params(&get_phy); - _params.sys_params.rx1_dr_offset = phy_param.value; + _params.sys_params.rx2_channel.frequency = lora_phy->get_default_rx2_frequency(); - get_phy.attribute = PHY_DEF_RX2_FREQUENCY; - phy_param = lora_phy->get_phy_params(&get_phy); - _params.sys_params.rx2_channel.frequency = phy_param.value; - get_phy.attribute = PHY_DEF_RX2_DR; - phy_param = lora_phy->get_phy_params(&get_phy); - _params.sys_params.rx2_channel.datarate = phy_param.value; + _params.sys_params.rx2_channel.datarate = lora_phy->get_default_rx2_datarate(); - get_phy.attribute = PHY_DEF_UPLINK_DWELL_TIME; - phy_param = lora_phy->get_phy_params(&get_phy); - _params.sys_params.uplink_dwell_time = phy_param.value; + _params.sys_params.uplink_dwell_time = lora_phy->get_default_uplink_dwell_time(); - get_phy.attribute = PHY_DEF_MAX_EIRP; - phy_param = lora_phy->get_phy_params(&get_phy); - _params.sys_params.max_eirp = phy_param.value; + _params.sys_params.max_eirp = lora_phy->get_default_max_eirp(); - get_phy.attribute = PHY_DEF_ANTENNA_GAIN; - phy_param = lora_phy->get_phy_params(&get_phy); - _params.sys_params.antenna_gain = phy_param.value; + _params.sys_params.antenna_gain = lora_phy->get_default_antenna_gain(); _params.is_node_ack_requested = false; _params.is_srv_ack_requested = false; @@ -1654,9 +1596,6 @@ lorawan_status_t LoRaMac::set_tx_continuous_wave1(uint16_t timeout, lorawan_status_t LoRaMac::initialize(loramac_primitives_t *primitives, LoRaPHY *phy, EventQueue *queue) { - get_phy_params_t get_phy; - phy_param_t phy_param; - //store event queue pointer ev_queue = queue; @@ -1676,7 +1615,7 @@ lorawan_status_t LoRaMac::initialize(loramac_primitives_t *primitives, mib.activate_mib_subsystem(this, lora_phy); // Activate channel planning subsystem - channel_plan.activate_channelplan_subsystem(lora_phy, &mib); + channel_plan.activate_channelplan_subsystem(lora_phy); mac_primitives = primitives; @@ -1693,67 +1632,35 @@ lorawan_status_t LoRaMac::initialize(loramac_primitives_t *primitives, _params.timers.aggregated_last_tx_time = 0; _params.timers.aggregated_timeoff = 0; - // Reset to defaults - get_phy.attribute = PHY_DUTY_CYCLE; - phy_param = lora_phy->get_phy_params(&get_phy); - // load default at this moment. Later can be changed using json - _params.is_dutycycle_on = (bool) phy_param.value; + _params.is_dutycycle_on = lora_phy->duty_cycle_enabled(); - get_phy.attribute = PHY_DEF_TX_POWER; - phy_param = lora_phy->get_phy_params(&get_phy); - _params.sys_params.channel_tx_power = phy_param.value; + _params.sys_params.channel_tx_power = lora_phy->get_default_tx_power(); - get_phy.attribute = PHY_DEF_TX_DR; - phy_param = lora_phy->get_phy_params(&get_phy); - _params.sys_params.channel_data_rate = phy_param.value; + _params.sys_params.channel_data_rate = lora_phy->get_default_tx_datarate(); - get_phy.attribute = PHY_MAX_RX_WINDOW; - phy_param = lora_phy->get_phy_params(&get_phy); - _params.sys_params.max_rx_win_time = phy_param.value; + _params.sys_params.max_rx_win_time = lora_phy->get_maximum_receive_window_duration(); - get_phy.attribute = PHY_RECEIVE_DELAY1; - phy_param = lora_phy->get_phy_params(&get_phy); - _params.sys_params.recv_delay1 = phy_param.value; + _params.sys_params.recv_delay1 = lora_phy->get_window1_receive_delay(); - get_phy.attribute = PHY_RECEIVE_DELAY2; - phy_param = lora_phy->get_phy_params(&get_phy); - _params.sys_params.recv_delay2 = phy_param.value; + _params.sys_params.recv_delay2 = lora_phy->get_window2_receive_delay(); - get_phy.attribute = PHY_JOIN_ACCEPT_DELAY1; - phy_param = lora_phy->get_phy_params(&get_phy); - _params.sys_params.join_accept_delay1 = phy_param.value; + _params.sys_params.join_accept_delay1 = lora_phy->get_window1_join_accept_delay(); - get_phy.attribute = PHY_JOIN_ACCEPT_DELAY2; - phy_param = lora_phy->get_phy_params(&get_phy); - _params.sys_params.join_accept_delay2 = phy_param.value; + _params.sys_params.join_accept_delay2 = lora_phy->get_window2_join_accept_delay(); - get_phy.attribute = PHY_DEF_DR1_OFFSET; - phy_param = lora_phy->get_phy_params(&get_phy); - _params.sys_params.rx1_dr_offset = phy_param.value; + _params.sys_params.rx1_dr_offset = lora_phy->get_default_datarate1_offset(); - get_phy.attribute = PHY_DEF_RX2_FREQUENCY; - phy_param = lora_phy->get_phy_params(&get_phy); - _params.sys_params.rx2_channel.frequency = phy_param.value; + _params.sys_params.rx2_channel.frequency = lora_phy->get_default_rx2_frequency(); - get_phy.attribute = PHY_DEF_RX2_DR; - phy_param = lora_phy->get_phy_params(&get_phy); - _params.sys_params.rx2_channel.datarate = phy_param.value; + _params.sys_params.rx2_channel.datarate = lora_phy->get_default_rx2_datarate(); - get_phy.attribute = PHY_DEF_UPLINK_DWELL_TIME; - phy_param = lora_phy->get_phy_params(&get_phy); - _params.sys_params.uplink_dwell_time = phy_param.value; + _params.sys_params.uplink_dwell_time = lora_phy->get_default_uplink_dwell_time(); - get_phy.attribute = PHY_DEF_DOWNLINK_DWELL_TIME; - phy_param = lora_phy->get_phy_params(&get_phy); - _params.sys_params.downlink_dwell_time = phy_param.value; + _params.sys_params.downlink_dwell_time = lora_phy->get_default_downlink_dwell_time(); - get_phy.attribute = PHY_DEF_MAX_EIRP; - phy_param = lora_phy->get_phy_params(&get_phy); - _params.sys_params.max_eirp = phy_param.f_value; + _params.sys_params.max_eirp = lora_phy->get_default_max_eirp(); - get_phy.attribute = PHY_DEF_ANTENNA_GAIN; - phy_param = lora_phy->get_phy_params(&get_phy); - _params.sys_params.antenna_gain = phy_param.f_value; + _params.sys_params.antenna_gain = lora_phy->get_default_antenna_gain(); // Init parameters which are not set in function ResetMacParameters _params.sys_params.max_sys_rx_error = 10; @@ -1820,9 +1727,6 @@ void LoRaMac::disconnect() lorawan_status_t LoRaMac::query_tx_possible(uint8_t size, loramac_tx_info_t* tx_info) { - get_phy_params_t get_phy; - phy_param_t phy_param; - uint8_t fopt_len = mac_commands.get_mac_cmd_length() + mac_commands.get_repeat_commands_length(); @@ -1837,16 +1741,8 @@ lorawan_status_t LoRaMac::query_tx_possible(uint8_t size, _params.adr_ack_counter); } - // Setup PHY request - get_phy.datarate = _params.sys_params.channel_data_rate; - get_phy.attribute = PHY_MAX_PAYLOAD; + tx_info->current_payload_size = lora_phy->get_max_payload(_params.sys_params.channel_data_rate, _params.is_repeater_supported); - // Change request in case repeater is supported - if (_params.is_repeater_supported == true) { - get_phy.attribute = PHY_MAX_PAYLOAD_REPEATER; - } - phy_param = lora_phy->get_phy_params(&get_phy); - tx_info->current_payload_size = phy_param.value; // Verify if the fOpts fit into the maximum payload if (tx_info->current_payload_size >= fopt_len) { @@ -1894,7 +1790,18 @@ lorawan_status_t LoRaMac::remove_channel_plan() lorawan_status_t LoRaMac::get_channel_plan(lorawan_channelplan_t& plan) { - return channel_plan.get_plan(plan, &_params); + // Request Mib to get channels + loramac_mib_req_confirm_t mib_confirm; + memset(&mib_confirm, 0, sizeof(mib_confirm)); + mib_confirm.type = MIB_CHANNELS; + + lorawan_status_t status = mib.get_request(&mib_confirm, &_params); + + if (status != LORAWAN_STATUS_OK) { + return status; + } + + return channel_plan.get_plan(plan, &mib_confirm); } lorawan_status_t LoRaMac::remove_single_channel(uint8_t id) @@ -1984,7 +1891,9 @@ lorawan_status_t LoRaMac::mcps_request( loramac_mcps_req_t *mcpsRequest ) return LORAWAN_STATUS_BUSY; } - return mcps.set_request(mcpsRequest, &_params); + lorawan_status_t status = mcps.set_request(mcpsRequest, &_params); + + return status; } lorawan_status_t LoRaMac::mib_get_request_confirm( loramac_mib_req_confirm_t *mibGet ) @@ -2038,11 +1947,7 @@ void LoRaMac::LoRaMacTestSetMic( uint16_t txPacketCounter ) void LoRaMac::LoRaMacTestSetDutyCycleOn( bool enable ) { - VerifyParams_t verify; - - verify.DutyCycle = enable; - - if(lora_phy->verify(&verify, PHY_DUTY_CYCLE) == true) + if(lora_phy->verify_duty_cycle(enable) == true) { _params.is_dutycycle_on = enable; } diff --git a/features/lorawan/lorastack/mac/LoRaMacChannelPlan.cpp b/features/lorawan/lorastack/mac/LoRaMacChannelPlan.cpp index 584207de44..4caac0f736 100644 --- a/features/lorawan/lorastack/mac/LoRaMacChannelPlan.cpp +++ b/features/lorawan/lorastack/mac/LoRaMacChannelPlan.cpp @@ -25,7 +25,7 @@ SPDX-License-Identifier: BSD-3-Clause #include "lorastack/mac/LoRaMacChannelPlan.h" -LoRaMacChannelPlan::LoRaMacChannelPlan() : _lora_phy(NULL), _mib(NULL) +LoRaMacChannelPlan::LoRaMacChannelPlan() : _lora_phy(NULL) { } @@ -33,10 +33,9 @@ LoRaMacChannelPlan::~LoRaMacChannelPlan() { } -void LoRaMacChannelPlan::activate_channelplan_subsystem(LoRaPHY *phy, LoRaMacMib *mib) +void LoRaMacChannelPlan::activate_channelplan_subsystem(LoRaPHY *phy) { _lora_phy = phy; - _mib = mib; } lorawan_status_t LoRaMacChannelPlan::set_plan(const lorawan_channelplan_t& plan) @@ -44,22 +43,13 @@ lorawan_status_t LoRaMacChannelPlan::set_plan(const lorawan_channelplan_t& plan) channel_params_t mac_layer_ch_params; lorawan_status_t status; - get_phy_params_t get_phy; - phy_param_t phy_param; uint8_t max_num_channels; - // Check if the PHY layer supports custom channel plans or not. - get_phy.attribute = PHY_CUSTOM_CHANNEL_PLAN_SUPPORT; - phy_param = _lora_phy->get_phy_params(&get_phy); - - if (!phy_param.value) { + if (!_lora_phy->is_custom_channel_plan_supported()) { return LORAWAN_STATUS_SERVICE_UNKNOWN; } - // Check first how many channels the selected PHY layer supports - get_phy.attribute = PHY_MAX_NB_CHANNELS; - phy_param = _lora_phy->get_phy_params(&get_phy); - max_num_channels = (uint8_t) phy_param.value; + max_num_channels = _lora_phy->get_max_nb_channels(); // check if user is setting more channels than supported if (plan.nb_channels > max_num_channels) { @@ -87,48 +77,23 @@ lorawan_status_t LoRaMacChannelPlan::set_plan(const lorawan_channelplan_t& plan) } lorawan_status_t LoRaMacChannelPlan::get_plan(lorawan_channelplan_t& plan, - loramac_protocol_params *params) + const loramac_mib_req_confirm_t* mib_confirm) { - if (params == NULL) { + if (mib_confirm == NULL) { return LORAWAN_STATUS_PARAMETER_INVALID; } - loramac_mib_req_confirm_t mib_confirm; - lorawan_status_t status; - - get_phy_params_t get_phy; - phy_param_t phy_param; uint8_t max_num_channels; uint16_t *channel_mask; uint8_t count = 0; - // Check if the PHY layer supports custom channel plans or not. - get_phy.attribute = PHY_CUSTOM_CHANNEL_PLAN_SUPPORT; - phy_param = _lora_phy->get_phy_params(&get_phy); - - if (!phy_param.value) { + if (!_lora_phy->is_custom_channel_plan_supported()) { return LORAWAN_STATUS_SERVICE_UNKNOWN; } - // Check first how many channels the selected PHY layer supports - get_phy.attribute = PHY_MAX_NB_CHANNELS; - phy_param = _lora_phy->get_phy_params(&get_phy); - max_num_channels = (uint8_t) phy_param.value; + max_num_channels = _lora_phy->get_max_nb_channels(); - // Now check the Default channel mask - get_phy.attribute = PHY_CHANNEL_MASK; - phy_param = _lora_phy->get_phy_params(&get_phy); - channel_mask = phy_param.channel_mask; - - // Request Mib to get channels - memset(&mib_confirm, 0, sizeof(mib_confirm)); - mib_confirm.type = MIB_CHANNELS; - - status = _mib->get_request(&mib_confirm, params); - - if (status != LORAWAN_STATUS_OK) { - return status; - } + channel_mask = _lora_phy->get_channel_mask(false); for (uint8_t i = 0; i < max_num_channels; i++) { // skip the channels which are not enabled @@ -138,12 +103,12 @@ lorawan_status_t LoRaMacChannelPlan::get_plan(lorawan_channelplan_t& plan, // otherwise add them to the channel_plan struct plan.channels[count].id = i; - plan.channels[count].ch_param.frequency = mib_confirm.param.channel_list[i].frequency; - plan.channels[count].ch_param.dr_range.value = mib_confirm.param.channel_list[i].dr_range.value; - plan.channels[count].ch_param.dr_range.fields.min = mib_confirm.param.channel_list[i].dr_range.fields.min; - plan.channels[count].ch_param.dr_range.fields.max = mib_confirm.param.channel_list[i].dr_range.fields.max; - plan.channels[count].ch_param.band = mib_confirm.param.channel_list[i].band; - plan.channels[count].ch_param.rx1_frequency = mib_confirm.param.channel_list[i].rx1_frequency; + plan.channels[count].ch_param.frequency = mib_confirm->param.channel_list[i].frequency; + plan.channels[count].ch_param.dr_range.value = mib_confirm->param.channel_list[i].dr_range.value; + plan.channels[count].ch_param.dr_range.fields.min = mib_confirm->param.channel_list[i].dr_range.fields.min; + plan.channels[count].ch_param.dr_range.fields.max = mib_confirm->param.channel_list[i].dr_range.fields.max; + plan.channels[count].ch_param.band = mib_confirm->param.channel_list[i].band; + plan.channels[count].ch_param.rx1_frequency = mib_confirm->param.channel_list[i].rx1_frequency; count++; } @@ -156,34 +121,19 @@ lorawan_status_t LoRaMacChannelPlan::remove_plan() { lorawan_status_t status = LORAWAN_STATUS_OK; - get_phy_params_t get_phy; - phy_param_t phy_param; uint8_t max_num_channels; uint16_t *channel_mask; uint16_t *default_channel_mask; - // Check if the PHY layer supports custom channel plans or not. - get_phy.attribute = PHY_CUSTOM_CHANNEL_PLAN_SUPPORT; - phy_param = _lora_phy->get_phy_params(&get_phy); - - if (!phy_param.value) { + if (!_lora_phy->is_custom_channel_plan_supported()) { return LORAWAN_STATUS_SERVICE_UNKNOWN; } - // Check first how many channels the selected PHY layer supports - get_phy.attribute = PHY_MAX_NB_CHANNELS; - phy_param = _lora_phy->get_phy_params(&get_phy); - max_num_channels = (uint8_t) phy_param.value; + max_num_channels = _lora_phy->get_max_nb_channels(); - // Now check the channel mask for enabled channels - get_phy.attribute = PHY_CHANNEL_MASK; - phy_param = _lora_phy->get_phy_params(&get_phy); - channel_mask = phy_param.channel_mask; + channel_mask = _lora_phy->get_channel_mask(false); - // Now check the channel mask for default channels - get_phy.attribute = PHY_DEFAULT_CHANNEL_MASK; - phy_param = _lora_phy->get_phy_params(&get_phy); - default_channel_mask = phy_param.channel_mask; + default_channel_mask = _lora_phy->get_channel_mask(true); for (uint8_t i = 0; i < max_num_channels; i++) { // skip any default channels @@ -208,22 +158,13 @@ lorawan_status_t LoRaMacChannelPlan::remove_plan() lorawan_status_t LoRaMacChannelPlan::remove_single_channel(uint8_t channel_id) { - get_phy_params_t get_phy; - phy_param_t phy_param; uint8_t max_num_channels; - // Check if the PHY layer supports custom channel plans or not. - get_phy.attribute = PHY_CUSTOM_CHANNEL_PLAN_SUPPORT; - phy_param = _lora_phy->get_phy_params(&get_phy); - - if (!phy_param.value) { + if (!_lora_phy->is_custom_channel_plan_supported()) { return LORAWAN_STATUS_SERVICE_UNKNOWN; } - // Check first how many channels the selected PHY layer supports - get_phy.attribute = PHY_MAX_NB_CHANNELS; - phy_param = _lora_phy->get_phy_params(&get_phy); - max_num_channels = (uint8_t) phy_param.value; + max_num_channels = _lora_phy->get_max_nb_channels(); // According to specification channel IDs start from 0 and last valid // channel ID is N-1 where N=MAX_NUM_CHANNELS. diff --git a/features/lorawan/lorastack/mac/LoRaMacChannelPlan.h b/features/lorawan/lorastack/mac/LoRaMacChannelPlan.h index adf880de64..66b0b16cc4 100644 --- a/features/lorawan/lorastack/mac/LoRaMacChannelPlan.h +++ b/features/lorawan/lorastack/mac/LoRaMacChannelPlan.h @@ -56,7 +56,7 @@ public: * @param phy pointer to PHY layer * @param mib pointer to MIB subsystem */ - void activate_channelplan_subsystem(LoRaPHY *phy,LoRaMacMib *mib); + void activate_channelplan_subsystem(LoRaPHY *phy); /** Set a given channel plan * @@ -83,7 +83,7 @@ public: * @return LORAWAN_STATUS_OK if everything goes well otherwise * a negative error code is returned. */ - lorawan_status_t get_plan(lorawan_channelplan_t& plan, loramac_protocol_params *params); + lorawan_status_t get_plan(lorawan_channelplan_t& plan, const loramac_mib_req_confirm_t *mib_confirm); /** Remove the active channel plan * @@ -109,7 +109,6 @@ private: * Local handles */ LoRaPHY *_lora_phy; - LoRaMacMib * _mib; }; diff --git a/features/lorawan/lorastack/mac/LoRaMacMcps.cpp b/features/lorawan/lorastack/mac/LoRaMacMcps.cpp index c5331abd16..28832c4af5 100644 --- a/features/lorawan/lorastack/mac/LoRaMacMcps.cpp +++ b/features/lorawan/lorastack/mac/LoRaMacMcps.cpp @@ -35,6 +35,16 @@ LoRaMacMcps::~LoRaMacMcps() { } +loramac_mcps_confirm_t& LoRaMacMcps::get_confirmation() +{ + return confirmation; +} + +loramac_mcps_indication_t& LoRaMacMcps::get_indication() +{ + return indication; +} + void LoRaMacMcps::activate_mcps_subsystem(LoRaMac *mac, LoRaPHY *phy) { _lora_mac = mac; @@ -49,11 +59,8 @@ lorawan_status_t LoRaMacMcps::set_request(loramac_mcps_req_t *mcpsRequest, return LORAWAN_STATUS_PARAMETER_INVALID; } - get_phy_params_t get_phy; - phy_param_t phyParam; lorawan_status_t status = LORAWAN_STATUS_SERVICE_UNKNOWN; loramac_mhdr_t machdr; - verification_params_t verify; uint8_t fport = 0; void *fbuffer; uint16_t fbuffer_size; @@ -114,25 +121,20 @@ lorawan_status_t LoRaMacMcps::set_request(loramac_mcps_req_t *mcpsRequest, // return LORAWAN_STATUS_PARAMETER_INVALID; // } - // Get the minimum possible datarate - get_phy.attribute = PHY_MIN_TX_DR; - phyParam = _lora_phy->get_phy_params(&get_phy); - // Apply the minimum possible datarate. // Some regions have limitations for the minimum datarate. - datarate = MAX(datarate, (int8_t)phyParam.value); + datarate = MAX(datarate, (int8_t)_lora_phy->get_minimum_tx_datarate()); if (ready_to_send == true) { if (params->sys_params.adr_on == false) { - verify.datarate = datarate; - - if (_lora_phy->verify(&verify, PHY_TX_DR) == true) { - params->sys_params.channel_data_rate = verify.datarate; + if (_lora_phy->verify_tx_datarate(datarate, false) == true) { + params->sys_params.channel_data_rate = datarate; } else { return LORAWAN_STATUS_PARAMETER_INVALID; } } + //nämä lora_maciin status = _lora_mac->send(&machdr, fport, fbuffer, fbuffer_size); if (status == LORAWAN_STATUS_OK) { confirmation.req_type = mcpsRequest->type; diff --git a/features/lorawan/lorastack/mac/LoRaMacMcps.h b/features/lorawan/lorastack/mac/LoRaMacMcps.h index 3989c66753..655c94d036 100644 --- a/features/lorawan/lorastack/mac/LoRaMacMcps.h +++ b/features/lorawan/lorastack/mac/LoRaMacMcps.h @@ -76,20 +76,13 @@ public: * * @return a reference to MCPS confirm data structure */ - inline loramac_mcps_confirm_t& get_confirmation() - { - return confirmation; - } + loramac_mcps_confirm_t& get_confirmation(); /** Grants access to MCPS indication data * * @return a reference to MCPS indication data structure */ - inline loramac_mcps_indication_t& get_indication() - { - return indication; - } - + loramac_mcps_indication_t& get_indication(); private: diff --git a/features/lorawan/lorastack/mac/LoRaMacMib.cpp b/features/lorawan/lorastack/mac/LoRaMacMib.cpp index 39172ef569..c32fac9a54 100644 --- a/features/lorawan/lorastack/mac/LoRaMacMib.cpp +++ b/features/lorawan/lorastack/mac/LoRaMacMib.cpp @@ -49,8 +49,6 @@ lorawan_status_t LoRaMacMib::set_request(loramac_mib_req_confirm_t *mibSet, } lorawan_status_t status = LORAWAN_STATUS_OK; - verification_params_t verify; - switch (mibSet->type) { case MIB_DEVICE_CLASS: { @@ -125,9 +123,7 @@ lorawan_status_t LoRaMacMib::set_request(loramac_mib_req_confirm_t *mibSet, break; } case MIB_RX2_CHANNEL: { - verify.datarate = mibSet->param.rx2_channel.datarate; - - if (_lora_phy->verify(&verify, PHY_RX_DR) == true) { + if (_lora_phy->verify_rx_datarate(mibSet->param.rx2_channel.datarate) == true) { params->sys_params.rx2_channel = mibSet->param.rx2_channel; if ((params->dev_class == CLASS_C) @@ -152,9 +148,7 @@ lorawan_status_t LoRaMacMib::set_request(loramac_mib_req_confirm_t *mibSet, break; } case MIB_RX2_DEFAULT_CHANNEL: { - verify.datarate = mibSet->param.rx2_channel.datarate; - - if (_lora_phy->verify(&verify, PHY_RX_DR) == true) { + if (_lora_phy->verify_rx_datarate(mibSet->param.rx2_channel.datarate) == true) { params->sys_params.rx2_channel = mibSet->param.default_rx2_channel; } else { status = LORAWAN_STATUS_PARAMETER_INVALID; @@ -200,40 +194,32 @@ lorawan_status_t LoRaMacMib::set_request(loramac_mib_req_confirm_t *mibSet, break; } case MIB_CHANNELS_DEFAULT_DATARATE: { - verify.datarate = mibSet->param.default_channel_data_rate; - - if (_lora_phy->verify(&verify, PHY_DEF_TX_DR) == true) { - params->sys_params.channel_data_rate = verify.datarate; + if (_lora_phy->verify_tx_datarate(mibSet->param.default_channel_data_rate, true)) { + params->sys_params.channel_data_rate = mibSet->param.default_channel_data_rate; } else { status = LORAWAN_STATUS_PARAMETER_INVALID; } break; } case MIB_CHANNELS_DATARATE: { - verify.datarate = mibSet->param.channel_data_rate; - - if (_lora_phy->verify(&verify, PHY_TX_DR) == true) { - params->sys_params.channel_data_rate = verify.datarate; + if (_lora_phy->verify_tx_datarate(mibSet->param.channel_data_rate, false) == true) { + params->sys_params.channel_data_rate = mibSet->param.channel_data_rate; } else { status = LORAWAN_STATUS_PARAMETER_INVALID; } break; } case MIB_CHANNELS_DEFAULT_TX_POWER: { - verify.tx_power = mibSet->param.default_channel_tx_pwr; - - if (_lora_phy->verify(&verify, PHY_DEF_TX_POWER) == true) { - params->sys_params.channel_tx_power = verify.tx_power; + if (_lora_phy->verify_tx_power(mibSet->param.default_channel_tx_pwr)) { + params->sys_params.channel_tx_power = mibSet->param.default_channel_tx_pwr; } else { status = LORAWAN_STATUS_PARAMETER_INVALID; } break; } case MIB_CHANNELS_TX_POWER: { - verify.tx_power = mibSet->param.channel_tx_pwr; - - if (_lora_phy->verify(&verify, PHY_TX_POWER) == true) { - params->sys_params.channel_tx_power = verify.tx_power; + if (_lora_phy->verify_tx_power(mibSet->param.channel_tx_pwr)) { + params->sys_params.channel_tx_power = mibSet->param.channel_tx_pwr; } else { status = LORAWAN_STATUS_PARAMETER_INVALID; } @@ -271,8 +257,6 @@ lorawan_status_t LoRaMacMib::get_request(loramac_mib_req_confirm_t *mibGet, loramac_protocol_params *params) { lorawan_status_t status = LORAWAN_STATUS_OK; - get_phy_params_t get_phy; - phy_param_t phy_param; rx2_channel_params rx2_channel; if( mibGet == NULL ) @@ -329,10 +313,7 @@ lorawan_status_t LoRaMacMib::get_request(loramac_mib_req_confirm_t *mibGet, } case MIB_CHANNELS: { - get_phy.attribute = PHY_CHANNELS; - phy_param = _lora_phy->get_phy_params( &get_phy ); - - mibGet->param.channel_list = phy_param.channel_params; + mibGet->param.channel_list = _lora_phy->get_phy_channels(); break; } case MIB_RX2_CHANNEL: @@ -342,31 +323,19 @@ lorawan_status_t LoRaMacMib::get_request(loramac_mib_req_confirm_t *mibGet, } case MIB_RX2_DEFAULT_CHANNEL: { - get_phy.attribute = PHY_DEF_RX2_DR; - phy_param = _lora_phy->get_phy_params( &get_phy ); - rx2_channel.datarate = phy_param.value; - - get_phy.attribute = PHY_DEF_RX2_FREQUENCY; - phy_param = _lora_phy->get_phy_params( &get_phy ); - rx2_channel.frequency = phy_param.value; - + rx2_channel.datarate = _lora_phy->get_default_rx2_datarate(); + rx2_channel.frequency = _lora_phy->get_default_rx2_frequency(); mibGet->param.rx2_channel = rx2_channel; break; } case MIB_CHANNELS_DEFAULT_MASK: { - get_phy.attribute = PHY_DEFAULT_CHANNEL_MASK; - phy_param = _lora_phy->get_phy_params( &get_phy ); - - mibGet->param.default_channel_mask = phy_param.channel_mask; + mibGet->param.default_channel_mask = _lora_phy->get_channel_mask(true); break; } case MIB_CHANNELS_MASK: { - get_phy.attribute = PHY_CHANNEL_MASK; - phy_param = _lora_phy->get_phy_params( &get_phy ); - - mibGet->param.channel_mask = phy_param.channel_mask; + mibGet->param.channel_mask = _lora_phy->get_channel_mask(false); break; } case MIB_CHANNELS_NB_REP: @@ -401,9 +370,7 @@ lorawan_status_t LoRaMacMib::get_request(loramac_mib_req_confirm_t *mibGet, } case MIB_CHANNELS_DEFAULT_DATARATE: { - get_phy.attribute = PHY_DEF_TX_DR; - phy_param = _lora_phy->get_phy_params( &get_phy ); - mibGet->param.default_channel_data_rate = phy_param.value; + mibGet->param.default_channel_data_rate = _lora_phy->get_default_tx_datarate(); break; } case MIB_CHANNELS_DATARATE: @@ -413,9 +380,7 @@ lorawan_status_t LoRaMacMib::get_request(loramac_mib_req_confirm_t *mibGet, } case MIB_CHANNELS_DEFAULT_TX_POWER: { - get_phy.attribute = PHY_DEF_TX_POWER; - phy_param = _lora_phy->get_phy_params( &get_phy ); - mibGet->param.default_channel_tx_pwr = phy_param.value; + mibGet->param.default_channel_tx_pwr = _lora_phy->get_default_tx_power(); break; } case MIB_CHANNELS_TX_POWER: diff --git a/features/lorawan/lorastack/mac/LoRaMacMlme.cpp b/features/lorawan/lorastack/mac/LoRaMacMlme.cpp index e9e366dcba..36ea4b23fa 100644 --- a/features/lorawan/lorastack/mac/LoRaMacMlme.cpp +++ b/features/lorawan/lorastack/mac/LoRaMacMlme.cpp @@ -35,6 +35,16 @@ LoRaMacMlme::~LoRaMacMlme() { } +loramac_mlme_confirm_t& LoRaMacMlme::get_confirmation() +{ + return confirmation; +} + +loramac_mlme_indication_t& LoRaMacMlme::get_indication() +{ + return indication; +} + void LoRaMacMlme::activate_mlme_subsystem(LoRaMac *mac, LoRaPHY *phy) { _lora_mac = mac; @@ -49,11 +59,6 @@ lorawan_status_t LoRaMacMlme::set_request(loramac_mlme_req_t *request, lorawan_status_t status = LORAWAN_STATUS_SERVICE_UNKNOWN; loramac_mhdr_t machdr; - verification_params_t verify; - get_phy_params_t get_phy; - phy_param_t phy_param; - - if (params->mac_state != LORAMAC_IDLE) { return LORAWAN_STATUS_BUSY; } @@ -78,14 +83,9 @@ lorawan_status_t LoRaMacMlme::set_request(loramac_mlme_req_t *request, return LORAWAN_STATUS_PARAMETER_INVALID; } - // Verify the parameter NbTrials for the join procedure - verify.nb_join_trials = request->req.join.nb_trials; - - if (_lora_phy->verify(&verify, PHY_NB_JOIN_TRIALS) == false) { + if (false == _lora_phy->verify_nb_join_trials(request->req.join.nb_trials)) { // Value not supported, get default - get_phy.attribute = PHY_DEF_NB_JOIN_TRIALS; - phy_param = _lora_phy->get_phy_params(&get_phy); - request->req.join.nb_trials = (uint8_t) phy_param.value; + request->req.join.nb_trials = _lora_phy->get_nb_join_trials(true); } params->flags.bits.mlme_req = 1; diff --git a/features/lorawan/lorastack/mac/LoRaMacMlme.h b/features/lorawan/lorastack/mac/LoRaMacMlme.h index 82e1146625..2b751058b1 100644 --- a/features/lorawan/lorastack/mac/LoRaMacMlme.h +++ b/features/lorawan/lorastack/mac/LoRaMacMlme.h @@ -76,19 +76,13 @@ public: * * @return a reference to MLME confirm data structure */ - inline loramac_mlme_confirm_t& get_confirmation() - { - return confirmation; - } + loramac_mlme_confirm_t& get_confirmation(); /** Grants access to MLME indication data * * @return a reference to MLME indication data structure */ - inline loramac_mlme_indication_t& get_indication() - { - return indication; - } + loramac_mlme_indication_t& get_indication(); private: diff --git a/features/lorawan/lorastack/phy/LoRaPHY.cpp b/features/lorawan/lorastack/phy/LoRaPHY.cpp index b134da7045..09afff5b6e 100644 --- a/features/lorawan/lorastack/phy/LoRaPHY.cpp +++ b/features/lorawan/lorastack/phy/LoRaPHY.cpp @@ -46,6 +46,18 @@ LoRaPHY::~LoRaPHY() _radio = NULL; } +bool LoRaPHY::mask_bit_test(const uint16_t *mask, unsigned bit) { + return mask[bit/16] & (1U << (bit % 16)); +} + +void LoRaPHY::mask_bit_set(uint16_t *mask, unsigned bit) { + mask[bit/16] |= (1U << (bit % 16)); +} + +void LoRaPHY::mask_bit_clear(uint16_t *mask, unsigned bit) { + mask[bit/16] &= ~(1U << (bit % 16)); +} + void LoRaPHY::set_radio_instance(LoRaRadio& radio) { _radio = &radio; @@ -475,151 +487,163 @@ uint8_t LoRaPHY::enabled_channel_count(bool joined, uint8_t datarate, return count; } -phy_param_t LoRaPHY::get_phy_params(get_phy_params_t* getPhy) +uint32_t LoRaPHY::get_next_lower_tx_datarate(int8_t datarate) { - phy_param_t phyParam = { 0 }; - - switch (getPhy->attribute) { - case PHY_MIN_RX_DR: { - if (phy_params.dl_dwell_time_setting == 0) { - phyParam.value = phy_params.min_rx_datarate; - } else { - phyParam.value = phy_params.dwell_limit_datarate; - } - break; - } - case PHY_MIN_TX_DR: { - if (phy_params.ul_dwell_time_setting == 0) { - phyParam.value = phy_params.min_tx_datarate; - } else { - phyParam.value = phy_params.dwell_limit_datarate; - } - break; - } - case PHY_DEF_TX_DR: { - phyParam.value = phy_params.default_datarate; - break; - } - case PHY_NEXT_LOWER_TX_DR: { - if (phy_params.ul_dwell_time_setting == 0) { - phyParam.value = get_next_lower_dr(getPhy->datarate, - phy_params.min_tx_datarate); - } else { - phyParam.value = get_next_lower_dr( - getPhy->datarate, phy_params.dwell_limit_datarate); - } - break; - } - case PHY_DEF_TX_POWER: { - phyParam.value = phy_params.default_tx_power; - break; - } - case PHY_MAX_PAYLOAD: { - uint8_t *payload_table = (uint8_t *) phy_params.payloads.table; - phyParam.value = payload_table[getPhy->datarate]; - break; - } - case PHY_MAX_PAYLOAD_REPEATER: { - uint8_t *payload_table = (uint8_t *) phy_params.payloads_with_repeater.table; - phyParam.value = payload_table[getPhy->datarate]; - break; - } - case PHY_DUTY_CYCLE: { - phyParam.value = phy_params.duty_cycle_enabled; - break; - } - case PHY_MAX_RX_WINDOW: { - phyParam.value = phy_params.max_rx_window; - break; - } - case PHY_RECEIVE_DELAY1: { - phyParam.value = phy_params.recv_delay1; - break; - } - case PHY_RECEIVE_DELAY2: { - phyParam.value = phy_params.recv_delay2; - break; - } - case PHY_JOIN_ACCEPT_DELAY1: { - phyParam.value = phy_params.join_accept_delay1; - break; - } - case PHY_JOIN_ACCEPT_DELAY2: { - phyParam.value = phy_params.join_accept_delay2; - break; - } - case PHY_MAX_FCNT_GAP: { - phyParam.value = phy_params.max_fcnt_gap; - break; - } - case PHY_ACK_TIMEOUT: { - uint16_t ack_timeout = phy_params.ack_timeout; - uint16_t ack_timeout_rnd = phy_params.ack_timeout_rnd; - phyParam.value = (ack_timeout - + get_random(-ack_timeout_rnd, ack_timeout_rnd)); - break; - } - case PHY_DEF_DR1_OFFSET: { - phyParam.value = phy_params.default_rx1_dr_offset; - break; - } - case PHY_DEF_RX2_FREQUENCY: { - phyParam.value = phy_params.rx_window2_frequency; - break; - } - case PHY_DEF_RX2_DR: { - phyParam.value = phy_params.rx_window2_datarate; - break; - } - case PHY_CHANNEL_MASK: { - phyParam.channel_mask = phy_params.channels.mask; - break; - } - case PHY_DEFAULT_CHANNEL_MASK: { - phyParam.channel_mask = phy_params.channels.default_mask; - break; - } - case PHY_MAX_NB_CHANNELS: { - phyParam.value = phy_params.max_channel_cnt; - break; - } - case PHY_CHANNELS: { - phyParam.channel_params = phy_params.channels.channel_list; - break; - } - case PHY_CUSTOM_CHANNEL_PLAN_SUPPORT: - // 0 if custom channel plans are not supported (in LoRaWAN terms - // the regions who do not support custom channels are called as - // regions with dynamic channel plans) - phyParam.value = (uint32_t) phy_params.custom_channelplans_supported; - break; - case PHY_DEF_UPLINK_DWELL_TIME: { - phyParam.value = phy_params.ul_dwell_time_setting; - break; - } - case PHY_DEF_DOWNLINK_DWELL_TIME: { - phyParam.value = phy_params.dl_dwell_time_setting; - break; - } - case PHY_DEF_MAX_EIRP: { - phyParam.f_value = phy_params.default_max_eirp; - break; - } - case PHY_DEF_ANTENNA_GAIN: { - phyParam.f_value = phy_params.default_antenna_gain; - break; - } - case PHY_NB_JOIN_TRIALS: - case PHY_DEF_NB_JOIN_TRIALS: { - phyParam.value = MBED_CONF_LORA_NB_TRIALS; - break; - } - default: { - break; - } + if (phy_params.ul_dwell_time_setting == 0) { + return get_next_lower_dr(datarate, phy_params.min_tx_datarate); } - return phyParam; + return get_next_lower_dr( + datarate, phy_params.dwell_limit_datarate); + +} + +uint8_t LoRaPHY::get_minimum_rx_datarate() +{ + if (phy_params.dl_dwell_time_setting == 0) { + return phy_params.min_rx_datarate; + } + return phy_params.dwell_limit_datarate; +} + +uint8_t LoRaPHY::get_minimum_tx_datarate() +{ + if (phy_params.ul_dwell_time_setting == 0) { + return phy_params.min_tx_datarate; + } + return phy_params.dwell_limit_datarate; +} + +uint8_t LoRaPHY::get_default_tx_datarate() +{ + return phy_params.default_datarate; +} + +uint8_t LoRaPHY::get_default_tx_power() +{ + return phy_params.default_tx_power; +} + +uint8_t LoRaPHY::get_max_payload(uint8_t datarate, bool use_repeater) +{ + uint8_t *payload_table = NULL; + + if (use_repeater) { +// if (datarate >= phy_params.payloads_with_repeater.size) { +// //TODO: Can this ever happen? If yes, should we return 0? +// } + payload_table = (uint8_t *) phy_params.payloads_with_repeater.table; + } else { + payload_table = (uint8_t *) phy_params.payloads.table; + } + + return payload_table[datarate]; +} + +bool LoRaPHY::duty_cycle_enabled() +{ + return phy_params.duty_cycle_enabled; +} + +uint16_t LoRaPHY::get_maximum_receive_window_duration() +{ + return phy_params.max_rx_window; +} + +uint16_t LoRaPHY::get_window1_receive_delay() +{ + return phy_params.recv_delay1; +} + +uint16_t LoRaPHY::get_window2_receive_delay() +{ + return phy_params.recv_delay2; +} + +uint16_t LoRaPHY::get_window1_join_accept_delay() +{ + return phy_params.join_accept_delay1; +} + +uint16_t LoRaPHY::get_window2_join_accept_delay() +{ + return phy_params.join_accept_delay2; +} + +uint16_t LoRaPHY::get_maximum_frame_counter_gap() +{ + return phy_params.max_fcnt_gap; +} + +uint32_t LoRaPHY::get_ack_timeout() +{ + uint16_t ack_timeout_rnd = phy_params.ack_timeout_rnd; + return (phy_params.ack_timeout + + get_random(-ack_timeout_rnd, ack_timeout_rnd)); +} + +uint8_t LoRaPHY::get_default_datarate1_offset() +{ + return phy_params.default_rx1_dr_offset; +} + +uint32_t LoRaPHY::get_default_rx2_frequency() +{ + return phy_params.rx_window2_frequency; +} + +uint8_t LoRaPHY::get_default_rx2_datarate() +{ + return phy_params.rx_window2_datarate; +} + +uint16_t* LoRaPHY::get_channel_mask(bool get_default) +{ + if (get_default) { + return phy_params.channels.default_mask; + } + return phy_params.channels.mask; +} + +uint8_t LoRaPHY::get_max_nb_channels() +{ + return phy_params.max_channel_cnt; +} + +channel_params_t* LoRaPHY::get_phy_channels() +{ + return phy_params.channels.channel_list; +} + +bool LoRaPHY::is_custom_channel_plan_supported() +{ + return phy_params.custom_channelplans_supported; +} + +uint8_t LoRaPHY::get_default_uplink_dwell_time() +{ + return phy_params.ul_dwell_time_setting; +} + +uint8_t LoRaPHY::get_default_downlink_dwell_time() +{ + return phy_params.dl_dwell_time_setting; +} + +float LoRaPHY::get_default_max_eirp() +{ + return phy_params.default_max_eirp; +} + +float LoRaPHY::get_default_antenna_gain() +{ + return phy_params.default_antenna_gain; +} + +uint8_t LoRaPHY::get_nb_join_trials(bool get_default) +{ + (void)get_default; + return MBED_CONF_LORA_NB_TRIALS; } void LoRaPHY::restore_default_channels() @@ -630,66 +654,53 @@ void LoRaPHY::restore_default_channels() } } -bool LoRaPHY::verify(verification_params_t* verify, phy_attributes_t phy_attribute) +bool LoRaPHY::verify_rx_datarate(uint8_t datarate) { - switch(phy_attribute) { - case PHY_TX_DR: - { - if (phy_params.ul_dwell_time_setting == 0) { - return val_in_range(verify->datarate, - phy_params.min_tx_datarate, - phy_params.max_tx_datarate); - } else { - return val_in_range(verify->datarate, - phy_params.dwell_limit_datarate, - phy_params.max_tx_datarate); - } - - } - case PHY_DEF_TX_DR: - { - return val_in_range(verify->datarate, - phy_params.default_datarate, - phy_params.default_max_datarate); - } - case PHY_RX_DR: - { - if (phy_params.dl_dwell_time_setting == 0) { - return val_in_range(verify->datarate, - phy_params.min_rx_datarate, - phy_params.max_rx_datarate); - } else { - return val_in_range(verify->datarate, - phy_params.dwell_limit_datarate, - phy_params.max_rx_datarate); - } - } - case PHY_DEF_TX_POWER: - case PHY_TX_POWER: - { - // Remark: switched min and max! - return val_in_range(verify->tx_power, phy_params.max_tx_power, - phy_params.min_tx_power); - } - case PHY_DUTY_CYCLE: - { - if (verify->duty_cycle == phy_params.duty_cycle_enabled) { - return true; - } - - return false; - } - case PHY_NB_JOIN_TRIALS: - { - if (verify->nb_join_trials < MBED_CONF_LORA_NB_TRIALS) { - return false; - } - break; - } - default: - return false; + if (phy_params.dl_dwell_time_setting == 0) { + //TODO: Check this! datarate must be same as minimum! Can be compared directly if OK + return val_in_range(datarate, + phy_params.min_rx_datarate, + phy_params.min_rx_datarate); + } else { + return val_in_range(datarate, + phy_params.dwell_limit_datarate, + phy_params.min_rx_datarate ); } +} +bool LoRaPHY::verify_tx_datarate(uint8_t datarate, bool use_default) +{ + if (use_default) { + return val_in_range(datarate, phy_params.default_datarate, + phy_params.default_max_datarate); + } else if (phy_params.ul_dwell_time_setting == 0) { + return val_in_range(datarate, phy_params.min_tx_datarate, + phy_params.max_tx_datarate); + } else { + return val_in_range(datarate, phy_params.dwell_limit_datarate, + phy_params.max_tx_datarate); + } +} + +bool LoRaPHY::verify_tx_power(uint8_t tx_power) +{ + return val_in_range(tx_power, phy_params.max_tx_power, + phy_params.min_tx_power); +} + +bool LoRaPHY::verify_duty_cycle(bool cycle) +{ + if (cycle == phy_params.duty_cycle_enabled) { + return true; + } + return false; +} + +bool LoRaPHY::verify_nb_join_trials(uint8_t nb_join_trials) +{ + if (nb_join_trials < MBED_CONF_LORA_NB_TRIALS) { + return false; + } return true; } @@ -750,8 +761,6 @@ bool LoRaPHY::get_next_ADR(bool restore_channel_mask, int8_t& dr_out, { bool set_adr_ack_bit = false; - get_phy_params_t get_phy; - phy_param_t phy_param; uint16_t ack_limit_plus_delay = phy_params.adr_ack_limit + phy_params.adr_ack_delay; if (dr_out == phy_params.min_tx_datarate) { @@ -770,10 +779,7 @@ bool LoRaPHY::get_next_ADR(bool restore_channel_mask, int8_t& dr_out, if (adr_ack_cnt >= ack_limit_plus_delay) { if ((adr_ack_cnt % phy_params.adr_ack_delay) == 1) { // Decrease the datarate - get_phy.attribute = PHY_NEXT_LOWER_TX_DR; - get_phy.datarate = dr_out; - phy_param = get_phy_params(&get_phy); - dr_out = phy_param.value; + dr_out = get_next_lower_tx_datarate(dr_out); if (dr_out == phy_params.min_tx_datarate) { // We must set adrAckReq to false as soon as we reach the lowest datarate diff --git a/features/lorawan/lorastack/phy/LoRaPHY.h b/features/lorawan/lorastack/phy/LoRaPHY.h index df8f898e7d..c8c413f476 100644 --- a/features/lorawan/lorastack/phy/LoRaPHY.h +++ b/features/lorawan/lorastack/phy/LoRaPHY.h @@ -115,23 +115,17 @@ public: /** * Tests if a channel is on or off in the channel mask */ - inline bool mask_bit_test(const uint16_t *mask, unsigned bit) { - return mask[bit/16] & (1U << (bit % 16)); - } + bool mask_bit_test(const uint16_t *mask, unsigned bit); /** * Tests if a channel is on or off in the channel mask */ - inline void mask_bit_set(uint16_t *mask, unsigned bit) { - mask[bit/16] |= (1U << (bit % 16)); - } + void mask_bit_set(uint16_t *mask, unsigned bit); /** * Tests if a channel is on or off in the channel mask */ - inline void mask_bit_clear(uint16_t *mask, unsigned bit) { - mask[bit/16] &= ~(1U << (bit % 16)); - } + void mask_bit_clear(uint16_t *mask, unsigned bit); /** Entertain a new channel request MAC command. * @@ -145,18 +139,6 @@ public: */ virtual uint8_t request_new_channel(new_channel_req_params_t* new_channel_req); - /** Grants access to PHY layer parameters. - * - * This is essentially a PHY layer parameter retrieval system. - * A request is made for a certain parameter by setting an appropriate - * attribute. - * - * @param [in] get_phy A pointer to get_phy_params_t - * - * @return A structure containing the requested PHY parameter value. - */ - virtual phy_param_t get_phy_params(get_phy_params_t* get_phy); - /** Process PHY layer state after a successful transmission. * * Updates times of the last transmission for the particular channel and @@ -173,17 +155,6 @@ public: */ virtual void restore_default_channels(); - /** Verify if a parameter is eligible. - * - * @param verify A pointer to the verification_params_t that contains - * parameters which we need to check for validity. - * - * @param phy_attr The attribute for which the verification is needed. - * - * @return True, if the parameter is valid. - */ - virtual bool verify(verification_params_t* verify, phy_attributes_t phy_attr); - /** Processes the incoming CF-list. * * Handles the payload containing CF-list and enables channels defined @@ -406,6 +377,71 @@ public: */ virtual uint8_t apply_DR_offset(int8_t dr, int8_t dr_offset); +public: //Getters + uint32_t get_next_lower_tx_datarate(int8_t datarate); + + uint8_t get_minimum_rx_datarate(); + + uint8_t get_minimum_tx_datarate(); + + uint8_t get_default_tx_datarate(); + + uint8_t get_default_tx_power(); + + uint8_t get_max_payload(uint8_t datarate, bool use_repeater = false); + + bool duty_cycle_enabled(); + + uint16_t get_maximum_receive_window_duration(); + + uint16_t get_window1_receive_delay(); + + uint16_t get_window2_receive_delay(); + + uint16_t get_window1_join_accept_delay(); + + uint16_t get_window2_join_accept_delay(); + + uint16_t get_maximum_frame_counter_gap(); + + uint32_t get_ack_timeout(); + + uint8_t get_default_datarate1_offset(); + + uint32_t get_default_rx2_frequency(); + + uint8_t get_default_rx2_datarate(); + + uint16_t* get_channel_mask(bool get_default = false); + + uint8_t get_max_nb_channels(); + + channel_params_t* get_phy_channels(); + + bool is_custom_channel_plan_supported(); + + uint8_t get_default_uplink_dwell_time(); + + uint8_t get_default_downlink_dwell_time(); + + float get_default_max_eirp(); + + float get_default_antenna_gain(); + + uint8_t get_nb_join_trials(bool get_default = false); + +public: //Verifiers + + bool verify_rx_datarate(uint8_t datarate); + + bool verify_tx_datarate(uint8_t datarate, bool use_default = false); + + bool verify_tx_power(uint8_t tx_power); + + bool verify_duty_cycle(bool cycle); + + bool verify_nb_join_trials(uint8_t nb_join_trials); + protected: LoRaRadio *_radio; LoRaWANTimeHandler &_lora_time; diff --git a/features/lorawan/lorastack/phy/LoRaPHYUS915Hybrid.cpp b/features/lorawan/lorastack/phy/LoRaPHYUS915Hybrid.cpp index 2e628908b6..babac4d70f 100644 --- a/features/lorawan/lorastack/phy/LoRaPHYUS915Hybrid.cpp +++ b/features/lorawan/lorastack/phy/LoRaPHYUS915Hybrid.cpp @@ -334,9 +334,6 @@ bool LoRaPHYUS915Hybrid::get_next_ADR(bool restore_channel_mask, int8_t& dr_out, { bool adrAckReq = false; - get_phy_params_t get_phy; - phy_param_t phy_param; - uint16_t ack_limit_plus_delay = phy_params.adr_ack_limit + phy_params.adr_ack_delay; if (dr_out == phy_params.min_tx_datarate) { @@ -356,10 +353,7 @@ bool LoRaPHYUS915Hybrid::get_next_ADR(bool restore_channel_mask, int8_t& dr_out, if (adr_ack_cnt >= ack_limit_plus_delay) { if ((adr_ack_cnt % phy_params.adr_ack_delay) == 1) { // Decrease the datarate - get_phy.attribute = PHY_NEXT_LOWER_TX_DR; - get_phy.datarate = dr_out; - phy_param = get_phy_params(&get_phy); - dr_out = phy_param.value; + dr_out = get_next_lower_tx_datarate(dr_out); if (dr_out == phy_params.min_tx_datarate) { // We must set adrAckReq to false as soon as we reach the lowest datarate diff --git a/features/lorawan/lorastack/phy/lora_phy_ds.h b/features/lorawan/lorastack/phy/lora_phy_ds.h index ebcd0f6ae0..3f00b95355 100644 --- a/features/lorawan/lorastack/phy/lora_phy_ds.h +++ b/features/lorawan/lorastack/phy/lora_phy_ds.h @@ -524,194 +524,6 @@ */ #define TX_POWER_15 15 -/*! - * Enumeration of PHY attributes. - */ -typedef enum phy_attributes__e -{ - /*! - * The minimum RX datarate. - */ - PHY_MIN_RX_DR, - /*! - * The minimum TX datarate. - */ - PHY_MIN_TX_DR, - /*! - * The maximum RX datarate. - */ - PHY_MAX_RX_DR, - /*! - * The maximum TX datarate. - */ - PHY_MAX_TX_DR, - /*! - * The TX datarate. - */ - PHY_TX_DR, - /*! - * The default TX datarate. - */ - PHY_DEF_TX_DR, - /*! - * The RX datarate. - */ - PHY_RX_DR, - /*! - * The TX power. - */ - PHY_TX_POWER, - /*! - * The default TX power. - */ - PHY_DEF_TX_POWER, - /*! - * Maximum payload possible. - */ - PHY_MAX_PAYLOAD, - /*! - * Maximum payload possible when the repeater support is enabled. - */ - PHY_MAX_PAYLOAD_REPEATER, - /*! - * The duty cycle. - */ - PHY_DUTY_CYCLE, - /*! - * The maximum receive window duration. - */ - PHY_MAX_RX_WINDOW, - /*! - * The receive delay for window 1. - */ - PHY_RECEIVE_DELAY1, - /*! - * The receive delay for window 2. - */ - PHY_RECEIVE_DELAY2, - /*! - * The join accept delay for window 1. - */ - PHY_JOIN_ACCEPT_DELAY1, - /*! - * The join accept delay for window 2. - */ - PHY_JOIN_ACCEPT_DELAY2, - /*! - * The maximum frame counter gap. - */ - PHY_MAX_FCNT_GAP, - /*! - * The acknowledgement time out. - */ - PHY_ACK_TIMEOUT, - /*! - * The default datarate offset for window 1. - */ - PHY_DEF_DR1_OFFSET, - /*! - * The default receive window 2 frequency. - */ - PHY_DEF_RX2_FREQUENCY, - /*! - * The default receive window 2 datarate. - */ - PHY_DEF_RX2_DR, - /*! - * The channels mask. - */ - PHY_CHANNEL_MASK, - /*! - * The default channel mask. - */ - PHY_DEFAULT_CHANNEL_MASK, - /*! - * The maximum number of supported channels. - */ - PHY_MAX_NB_CHANNELS, - /*! - * The channels. - */ - PHY_CHANNELS, - /*! - * The PHYs that support dynamic channel plan (non-custom) - * support do not let the user add/remove to the channel plan. - * The network guides the device for the plan. So only - * EU like regions support custom channel planning. - */ - PHY_CUSTOM_CHANNEL_PLAN_SUPPORT, - /*! - * The default value of the uplink dwell time. - */ - PHY_DEF_UPLINK_DWELL_TIME, - /*! - * The default value of the downlink dwell time. - */ - PHY_DEF_DOWNLINK_DWELL_TIME, - /*! - * The default value of the MaxEIRP. - */ - PHY_DEF_MAX_EIRP, - /*! - * The default value of the antenna gain. - */ - PHY_DEF_ANTENNA_GAIN, - /*! - * The value for the number of join trials. - */ - PHY_NB_JOIN_TRIALS, - /*! - * The default value for the number of join trials. - */ - PHY_DEF_NB_JOIN_TRIALS, - /*! - * The next lower datarate. - */ - PHY_NEXT_LOWER_TX_DR -} phy_attributes_t; - -/*! - * Keeps value in response to a call to - * get_phy_params() API. - */ -typedef union phy_param_u -{ - /*! - * A parameter value. - */ - uint32_t value; - /*! - * A floating point value. - */ - float f_value; - /*! - * A pointer to the channels mask. - */ - uint16_t* channel_mask; - /*! - * A pointer to the channels. - */ - channel_params_t* channel_params; -} phy_param_t; - -/** - * The parameter structure for the function RegionGetPhyParam. - */ -typedef struct -{ - /** - * Set up the parameter to get. - */ - phy_attributes_t attribute; - - /** - * The parameter is needed for the following queries: - * PHY_MAX_PAYLOAD, PHY_MAX_PAYLOAD_REPEATER, PHY_NEXT_LOWER_TX_DR. - */ - int8_t datarate; - -} get_phy_params_t; - /** * The parameter structure for the function RegionSetBandTxDone. */ @@ -731,30 +543,6 @@ typedef struct lorawan_time_t last_tx_done_time; } set_band_txdone_params_t; -/** - * The parameter verification structure. - */ -typedef union -{ - /** - * The TX power to verify. - */ - int8_t tx_power; - /** - * Set to true, if the duty cycle is enabled, otherwise false. - */ - bool duty_cycle; - /** - * The number of join trials. - */ - uint8_t nb_join_trials; - /** - * The datarate to verify. - */ - int8_t datarate; - -} verification_params_t; - /** * The parameter structure for the function RegionApplyCFList. */