Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
LoRaPHY.h
00001 /** 00002 * @file LoRaPHY.h 00003 * 00004 * @brief An abstract class providing radio object to children and 00005 * provide base for implementing LoRa PHY layer 00006 * 00007 * \code 00008 * ______ _ 00009 * / _____) _ | | 00010 * ( (____ _____ ____ _| |_ _____ ____| |__ 00011 * \____ \| ___ | (_ _) ___ |/ ___) _ \ 00012 * _____) ) ____| | | || |_| ____( (___| | | | 00013 * (______/|_____)_|_|_| \__)_____)\____)_| |_| 00014 * (C)2013 Semtech 00015 * ___ _____ _ ___ _ _____ ___ ___ ___ ___ 00016 * / __|_ _/_\ / __| |/ / __/ _ \| _ \/ __| __| 00017 * \__ \ | |/ _ \ (__| ' <| _| (_) | / (__| _| 00018 * |___/ |_/_/ \_\___|_|\_\_| \___/|_|_\\___|___| 00019 * embedded.connectivity.solutions=============== 00020 * 00021 * \endcode 00022 * 00023 * Description: LoRa PHY layer 00024 * 00025 * License: Revised BSD License, see LICENSE.TXT file include in the project 00026 * 00027 * Maintainer: Miguel Luis ( Semtech ), Gregory Cristian ( Semtech ) and Daniel Jaeckle ( STACKFORCE ) 00028 * 00029 * Copyright (c) 2017, Arm Limited and affiliates. 00030 * SPDX-License-Identifier: BSD-3-Clause 00031 * 00032 */ 00033 00034 #ifndef MBED_OS_LORAPHY_BASE_ 00035 #define MBED_OS_LORAPHY_BASE_ 00036 00037 #include "lorawan/LoRaRadio.h" 00038 #include "lorawan/system/LoRaWANTimer.h" 00039 #include "lorawan/lorastack/phy/lora_phy_ds.h" 00040 #include "platform/NonCopyable.h" 00041 00042 class LoRaPHY : private mbed::NonCopyable<LoRaPHY> { 00043 00044 public: 00045 virtual ~LoRaPHY(); 00046 00047 /** Stores a reference to Radio object. 00048 * 00049 * Application is responsible for constructing a 'LoRaRadio' object 00050 * which is passed down to the PHY layer. 00051 * 00052 * @param radio a reference to radio driver object 00053 */ 00054 void set_radio_instance(LoRaRadio& radio); 00055 00056 /** Puts radio in sleep mode. 00057 * 00058 * Requests the radio driver to enter sleep mode. 00059 */ 00060 void put_radio_to_sleep(void); 00061 00062 /** Puts radio in standby mode. 00063 * 00064 * Requests the radio driver to enter standby mode. 00065 */ 00066 void put_radio_to_standby(void); 00067 00068 /** Puts radio in receive mode. 00069 * 00070 * Requests the radio driver to enter receive mode for a given time or to 00071 * enter continuous reception mode. 00072 * 00073 * @param is_rx_continuous if true, sets the radio to enter continuous 00074 * reception mode. 00075 * 00076 * @param max_rx_window duration of receive window 00077 */ 00078 void setup_rx_window(bool is_rx_continuous, uint32_t max_rx_window); 00079 00080 /** Delegates MAC layer request to transmit packet. 00081 * 00082 * @param buf a pointer to the data which needs to be transmitted 00083 * 00084 * @param size size of the data in bytes 00085 */ 00086 void handle_send(uint8_t *buf, uint8_t size); 00087 00088 /** Enables/Disables public network mode. 00089 * 00090 * Public and private LoRaWAN network constitute different preambles and 00091 * Net IDs. This API isused to tell the radio which network mode is in use. 00092 * 00093 * @param set true or false 00094 */ 00095 void setup_public_network_mode(bool set); 00096 00097 /** Provides a random number from radio. 00098 * 00099 * Returns a 32-bit random unsigned integer value based upon RSSI 00100 * measurements. 00101 * 00102 * @return a 32-bit long random number 00103 * 00104 */ 00105 uint32_t get_radio_rng(); 00106 00107 /** Calculates and applies duty cycle back-off time. 00108 * 00109 * Explicitly updates the band time-off. 00110 * 00111 * @param [in] backoff_params A pointer to backoff parameters. 00112 */ 00113 void calculate_backoff(backoff_params_t * backoff_params); 00114 00115 /** 00116 * Tests if a channel is on or off in the channel mask 00117 */ 00118 bool mask_bit_test(const uint16_t *mask, unsigned bit); 00119 00120 /** 00121 * Tests if a channel is on or off in the channel mask 00122 */ 00123 void mask_bit_set(uint16_t *mask, unsigned bit); 00124 00125 /** 00126 * Tests if a channel is on or off in the channel mask 00127 */ 00128 void mask_bit_clear(uint16_t *mask, unsigned bit); 00129 00130 /** Entertain a new channel request MAC command. 00131 * 00132 * MAC command subsystem processes the new channel request coming form 00133 * the network server and then MAC layer asks the PHY layer to entertain 00134 * the request. 00135 * 00136 * @param [in] new_channel_req A pointer to the new_channel_req_params_t. 00137 * 00138 * @return bit mask, according to the LoRaWAN spec 1.0.2. 00139 */ 00140 virtual uint8_t request_new_channel(new_channel_req_params_t* new_channel_req); 00141 00142 /** Process PHY layer state after a successful transmission. 00143 * 00144 * Updates times of the last transmission for the particular channel and 00145 * band upon which last transmission took place. 00146 * 00147 * @param [in] tx_done A pointer to set_band_txdone_params_t 00148 */ 00149 virtual void set_last_tx_done(set_band_txdone_params_t* tx_done); 00150 00151 /** Enables default channels only. 00152 * 00153 * Falls back to a channel mask where only default channels are enabled, all 00154 * other channels are disabled. 00155 */ 00156 virtual void restore_default_channels(); 00157 00158 /** Processes the incoming CF-list. 00159 * 00160 * Handles the payload containing CF-list and enables channels defined 00161 * therein. 00162 * 00163 * @param cflist_params A pointer to cflist_params_t. 00164 */ 00165 virtual void apply_cf_list(cflist_params_t* cflist_params); 00166 00167 /** Calculates the next datarate to set, when ADR is on or off. 00168 * 00169 * @param restore_channel_mask A boolean set restore channel mask in case 00170 * of failure. 00171 * 00172 * @param dr_out The calculated datarate for the next TX. 00173 * 00174 * @param tx_power_out The TX power for the next TX. 00175 * 00176 * @param adr_ack_counter The calculated ADR acknowledgement counter. 00177 * 00178 * @return True, if an ADR request should be performed. 00179 */ 00180 bool get_next_ADR(bool restore_channel_mask, int8_t& dr_out, 00181 int8_t& tx_power_out, uint32_t& adr_ack_counter); 00182 00183 /** Configure radio reception. 00184 * 00185 * @param [in] config A pointer to the RX configuration. 00186 * 00187 * @param [out] datarate The datarate index set. 00188 * 00189 * @return True, if the configuration was applied successfully. 00190 */ 00191 virtual bool rx_config(rx_config_params_t * config, int8_t* datarate); 00192 00193 /** Computing Receive Windows 00194 * 00195 * For more details please consult the following document, chapter 3.1.2. 00196 * http://www.semtech.com/images/datasheet/SX1272_settings_for_LoRaWAN_v2.0.pdf 00197 * or 00198 * http://www.semtech.com/images/datasheet/SX1276_settings_for_LoRaWAN_v2.0.pdf 00199 * 00200 * Downlink start: T = Tx + 1s (+/- 20 us) 00201 * | 00202 * TRxEarly | TRxLate 00203 * | | | 00204 * | | +---+---+---+---+---+---+---+---+ 00205 * | | | Latest Rx window | 00206 * | | +---+---+---+---+---+---+---+---+ 00207 * | | | 00208 * +---+---+---+---+---+---+---+---+ 00209 * | Earliest Rx window | 00210 * +---+---+---+---+---+---+---+---+ 00211 * | 00212 * +---+---+---+---+---+---+---+---+ 00213 *Downlink preamble 8 symbols | | | | | | | | | 00214 * +---+---+---+---+---+---+---+---+ 00215 * 00216 * Worst case Rx window timings 00217 * 00218 * TRxLate = DEFAULT_MIN_RX_SYMBOLS * tSymbol - RADIO_WAKEUP_TIME 00219 * TRxEarly = 8 - DEFAULT_MIN_RX_SYMBOLS * tSymbol - RxWindowTimeout - RADIO_WAKEUP_TIME 00220 * 00221 * TRxLate - TRxEarly = 2 * DEFAULT_SYSTEM_MAX_RX_ERROR 00222 * 00223 * RxOffset = ( TRxLate + TRxEarly ) / 2 00224 * 00225 * RxWindowTimeout = ( 2 * DEFAULT_MIN_RX_SYMBOLS - 8 ) * tSymbol + 2 * DEFAULT_SYSTEM_MAX_RX_ERROR 00226 * RxOffset = 4 * tSymbol - RxWindowTimeout / 2 - RADIO_WAKE_UP_TIME 00227 * 00228 * The minimum value of RxWindowTimeout must be 5 symbols which implies that the system always tolerates at least an error of 1.5 * tSymbol. 00229 */ 00230 /*! 00231 * Computes the RX window timeout and offset. 00232 * 00233 * @param [in] datarate The RX window datarate index to be used. 00234 * 00235 * @param [in] min_rx_symbols The minimum number of symbols required to 00236 * detect an RX frame. 00237 * 00238 * @param [in] rx_error The maximum timing error of the receiver 00239 * in milliseconds. The receiver will turn on 00240 * in a [-rxError : +rxError] ms interval around 00241 * RxOffset. 00242 * 00243 * @param [out] rx_conf_params Pointer to the structure that needs to be 00244 * filled with receive window parameters. 00245 * 00246 */ 00247 virtual void compute_rx_win_params(int8_t datarate, uint8_t min_rx_symbols, 00248 uint32_t rx_error, 00249 rx_config_params_t *rx_conf_params); 00250 00251 /** Configure radio transmission. 00252 * 00253 * @param [in] tx_config Structure containing tx parameters. 00254 * 00255 * @param [out] tx_power The TX power which will be set. 00256 * 00257 * @param [out] tx_toa The time-on-air of the frame. 00258 * 00259 * @return True, if the configuration was applied successfully. 00260 */ 00261 virtual bool tx_config(tx_config_params_t* tx_config, int8_t* tx_power, 00262 lorawan_time_t* tx_toa); 00263 00264 /** Processes a Link ADR Request. 00265 * 00266 * @param [in] params A pointer ADR request parameters. 00267 * 00268 * @param [out] dr_out The datarate applied. 00269 * 00270 * @param [out] tx_power_out The TX power applied. 00271 * 00272 * @param [out] nb_rep_out The number of repetitions to apply. 00273 * 00274 * @param [out] nb_bytes_parsed The number of bytes parsed. 00275 * 00276 * @return The status of the operation, according to the LoRaMAC specification. 00277 */ 00278 virtual uint8_t link_ADR_request(adr_req_params_t* params, 00279 int8_t* dr_out, int8_t* tx_power_out, 00280 uint8_t* nb_rep_out, 00281 uint8_t* nb_bytes_parsed); 00282 00283 /** Accept or rejects RxParamSetupReq MAC command 00284 * 00285 * The function processes a RX parameter setup request in response to 00286 * server MAC command for RX setup. 00287 * 00288 * @param [in] params A pointer to rx parameter setup request. 00289 * 00290 * @return The status of the operation, according to the LoRaWAN specification. 00291 */ 00292 virtual uint8_t accept_rx_param_setup_req(rx_param_setup_req_t* params); 00293 00294 /** Makes decision whether to accept or reject TxParamSetupReq MAC command 00295 * 00296 * @param [in] params A pointer to tx parameter setup request. 00297 * 00298 * @return True to let the MAC know that the request is 00299 * accepted and MAC can apply TX parameters received 00300 * form Network Server. Otherwise false is returned. 00301 */ 00302 virtual bool accept_tx_param_setup_req(tx_param_setup_req_t* params); 00303 00304 /** Processes a DlChannelReq MAC command. 00305 * 00306 * @param [in] params A pointer to downlink channel request. 00307 * 00308 * @return The status of the operation, according to the LoRaWAN specification. 00309 */ 00310 virtual uint8_t dl_channel_request(dl_channel_req_params_t* params); 00311 00312 /** Alternates the datarate of the channel for the join request. 00313 * 00314 * @param nb_trials Number of trials to be made on one given data rate. 00315 * 00316 * @return The datarate to apply . 00317 */ 00318 virtual int8_t get_alternate_DR(uint8_t nb_trials); 00319 00320 /** Searches and sets the next available channel. 00321 * 00322 * If there are multiple channels found available, one of them is selected 00323 * randomly. 00324 * 00325 * @param [in] nextChanParams Parameters for the next channel. 00326 * 00327 * @param [out] channel The next channel to use for TX. 00328 * 00329 * @param [out] time The time to wait for the next transmission according to the duty cycle. 00330 * 00331 * @param [out] aggregatedTimeOff Updates the aggregated time off. 00332 * 00333 * @return Function status [1: OK, 0: Unable to find a channel on the current datarate]. 00334 */ 00335 virtual bool set_next_channel(channel_selection_params_t* nextChanParams, 00336 uint8_t* channel, lorawan_time_t* time, 00337 lorawan_time_t* aggregatedTimeOff); 00338 00339 /** Adds a channel to the channel list. 00340 * 00341 * Verifies the channel parameters and if everything is found legitimate, 00342 * adds that particular channel to the channel list and updates the channel 00343 * mask. 00344 * 00345 * @param [in] new_channel A pointer to the parameters for the new channel. 00346 * @param [in] id Channel ID 00347 * 00348 * @return LORAWAN_STATUS_OK if everything goes fine, negative error code 00349 * otherwise. 00350 */ 00351 virtual lorawan_status_t add_channel(channel_params_t * new_channel, uint8_t id); 00352 00353 /** Removes a channel from the channel list. 00354 * 00355 * @param [in] channel_id Index of the channel to be removed 00356 * 00357 * @return True, if the channel was removed successfully. 00358 */ 00359 virtual bool remove_channel(uint8_t channel_id); 00360 00361 /** Puts the radio into continuous wave mode. 00362 * 00363 * @param [in] continuous_wave A pointer to the function parameters. 00364 * 00365 * @param [in] frequency Frequency to transmit at 00366 */ 00367 virtual void set_tx_cont_mode(cw_mode_params_t * continuous_wave, 00368 uint32_t frequency = 0); 00369 00370 /** Computes new data rate according to the given offset 00371 * 00372 * @param [in] dr The current datarate. 00373 * 00374 * @param [in] dr_offset The offset to be applied. 00375 * 00376 * @return The computed datarate. 00377 */ 00378 virtual uint8_t apply_DR_offset(int8_t dr, int8_t dr_offset); 00379 00380 /** 00381 * @brief reset_to_default_values resets some parameters to default values 00382 * @param params Pointer to MAC protocol parameters which will be reset 00383 * @param init If true, most of the values will be modified 00384 */ 00385 void reset_to_default_values(loramac_protocol_params *params, bool init = false); 00386 00387 public: 00388 /** 00389 * @brief get_next_lower_tx_datarate Gets the next lower datarate 00390 * @param datarate Current TX datarate 00391 * @return Lower datarate than given one or minimum if lower cannot be found anymore 00392 */ 00393 int8_t get_next_lower_tx_datarate(int8_t datarate); 00394 00395 /** 00396 * @brief get_minimum_rx_datarate Gets the minimum RX datarate supported by a device 00397 * @return Minimum RX datarate 00398 */ 00399 uint8_t get_minimum_rx_datarate(); 00400 00401 /** 00402 * @brief get_minimum_tx_datarate Gets the minimum TX datarate supported by a device 00403 * @return Minimum TX datarate 00404 */ 00405 uint8_t get_minimum_tx_datarate(); 00406 00407 /** 00408 * @brief get_default_tx_datarate Gets the default TX datarate 00409 * @return default TX datarate 00410 */ 00411 uint8_t get_default_tx_datarate(); 00412 00413 /** 00414 * @brief get_default_tx_power Gets the default TX power 00415 * @return Default TX power 00416 */ 00417 uint8_t get_default_tx_power(); 00418 00419 /** 00420 * @brief get_max_payload Gets maximum amount in bytes which device can send 00421 * @param datarate A datarate to use 00422 * @param use_repeater If true repeater table is used, otherwise payloads table is used 00423 * @return Maximum number of bytes for payload 00424 */ 00425 uint8_t get_max_payload(uint8_t datarate, bool use_repeater = false); 00426 00427 /** 00428 * @brief get_maximum_frame_counter_gap Gets maximum frame counter gap 00429 * @return Maximum frame counter gap 00430 */ 00431 uint16_t get_maximum_frame_counter_gap(); 00432 00433 /** 00434 * @brief get_ack_timeout Gets timeout value for ACK to be received 00435 * @return ACK timeout 00436 */ 00437 uint32_t get_ack_timeout(); 00438 00439 /** 00440 * @brief get_default_rx2_frequency Gets default RX2 frequency 00441 * @return RX2 frequency 00442 */ 00443 uint32_t get_default_rx2_frequency(); 00444 00445 /** 00446 * @brief get_default_rx2_datarate Gets default RX2 datarate 00447 * @return RX2 datarate 00448 */ 00449 uint8_t get_default_rx2_datarate(); 00450 00451 /** 00452 * @brief get_channel_mask Gets the channel mask 00453 * @param get_default If true the default mask is returned, otherwise the current mask is returned 00454 * @return A channel mask 00455 */ 00456 uint16_t* get_channel_mask(bool get_default = false); 00457 00458 /** 00459 * @brief get_max_nb_channels Gets maximum number of channels supported 00460 * @return Number of channels 00461 */ 00462 uint8_t get_max_nb_channels(); 00463 00464 /** 00465 * @brief get_phy_channels Gets PHY channels 00466 * @return PHY channels 00467 */ 00468 channel_params_t * get_phy_channels(); 00469 00470 /** 00471 * @brief is_custom_channel_plan_supported Checks if custom channel plan is supported 00472 * @return True if custom channel plan is supported, false otherwise 00473 */ 00474 bool is_custom_channel_plan_supported(); 00475 00476 public: //Verifiers 00477 00478 /** 00479 * @brief verify_rx_datarate Verifies that given RX datarate is valid 00480 * @param datarate Datarate to check 00481 * @return true if given datarate is valid, false otherwise 00482 */ 00483 bool verify_rx_datarate(uint8_t datarate); 00484 00485 /** 00486 * @brief verify_tx_datarate Verifies that given TX datarate is valid 00487 * @param datarate Datarate to check 00488 * @param use_default If true validation is done against default value 00489 * @return true if given datarate is valid, false otherwise 00490 */ 00491 bool verify_tx_datarate(uint8_t datarate, bool use_default = false); 00492 00493 /** 00494 * @brief verify_tx_power Verifies that given TX power is valid 00495 * @param tx_power Power to check 00496 * @return True if valid, false otherwise 00497 */ 00498 bool verify_tx_power(uint8_t tx_power); 00499 00500 /** 00501 * @brief verify_duty_cycle Verifies that given cycle is valid 00502 * @param cycle Cycle to check 00503 * @return True if valid, false otherwise 00504 */ 00505 bool verify_duty_cycle(bool cycle); 00506 00507 /** 00508 * @brief verify_nb_join_trials Verifies that given number of trials is valid 00509 * @param nb_join_trials Number to check 00510 * @return True if valid, false otherwise 00511 */ 00512 bool verify_nb_join_trials(uint8_t nb_join_trials); 00513 00514 protected: 00515 LoRaRadio *_radio; 00516 LoRaWANTimeHandler &_lora_time; 00517 loraphy_params_t phy_params; 00518 00519 LoRaPHY(LoRaWANTimeHandler &lora_time); 00520 00521 /** 00522 * Verifies the given frequency. 00523 */ 00524 virtual bool verify_frequency(uint32_t freq); 00525 00526 00527 /** 00528 * Verifies, if a value is in a given range. 00529 */ 00530 uint8_t val_in_range(int8_t value, int8_t min, int8_t max); 00531 00532 /** 00533 * Verifies, if a datarate is available on an active channel. 00534 */ 00535 bool verify_channel_DR(uint8_t nbChannels, uint16_t* channelsMask, int8_t dr, 00536 int8_t minDr, int8_t maxDr, channel_params_t * channels); 00537 00538 /** 00539 * Disables a channel in a given channels mask. 00540 */ 00541 bool disable_channel(uint16_t* channel_mask, uint8_t id, uint8_t max_channels); 00542 00543 /** 00544 * Counts number of bits on in a given mask 00545 */ 00546 uint8_t count_bits(uint16_t mask, uint8_t nb_bits); 00547 00548 /** 00549 * Counts the number of active channels in a given channels mask. 00550 */ 00551 uint8_t num_active_channels(uint16_t* channel_mask, uint8_t start_idx, 00552 uint8_t stop_idx); 00553 00554 /** 00555 * Copy channel masks. 00556 */ 00557 void copy_channel_mask(uint16_t* dest_mask, uint16_t* src_mask, uint8_t len); 00558 00559 /** 00560 * Updates the time-offs of the bands. 00561 */ 00562 lorawan_time_t update_band_timeoff(bool joined, bool dutyCycle, band_t * bands, 00563 uint8_t nb_bands); 00564 00565 /** 00566 * Parses the parameter of an LinkAdrRequest. 00567 */ 00568 uint8_t parse_link_ADR_req(uint8_t* payload, link_adr_params_t* adr_params); 00569 00570 /** 00571 * Verifies and updates the datarate, the TX power and the number of repetitions 00572 * of a LinkAdrRequest. 00573 */ 00574 uint8_t verify_link_ADR_req(verify_adr_params_t* verify_params, int8_t* dr, 00575 int8_t* tx_pow, uint8_t* nb_rep); 00576 00577 /** 00578 * Computes the symbol time for LoRa modulation. 00579 */ 00580 double compute_symb_timeout_lora(uint8_t phy_dr, uint32_t bandwidth ); 00581 00582 /** 00583 * Computes the symbol time for FSK modulation. 00584 */ 00585 double compute_symb_timeout_fsk(uint8_t phy_dr); 00586 00587 /** 00588 * Computes the RX window timeout and the RX window offset. 00589 */ 00590 void get_rx_window_params(double t_symbol, uint8_t min_rx_symbols, 00591 uint32_t rx_error, uint32_t wakeup_time, 00592 uint32_t* window_timeout, int32_t* window_offset); 00593 00594 /** 00595 * Computes the txPower, based on the max EIRP and the antenna gain. 00596 */ 00597 int8_t compute_tx_power(int8_t txPowerIndex, float maxEirp, float antennaGain); 00598 00599 /** 00600 * Provides a random number in the range provided. 00601 */ 00602 int32_t get_random(int32_t min, int32_t max); 00603 00604 /** 00605 * Get next lower data rate 00606 */ 00607 int8_t get_next_lower_dr(int8_t dr, int8_t min_dr); 00608 00609 /** 00610 * Get channel bandwidth depending upon data rate table index 00611 */ 00612 uint8_t get_bandwidth(uint8_t dr_index); 00613 00614 uint8_t enabled_channel_count(bool joined, uint8_t datarate, 00615 const uint16_t *mask, uint8_t* enabledChannels, 00616 uint8_t* delayTx); 00617 }; 00618 00619 00620 00621 #endif /* MBED_OS_LORAPHY_BASE_ */
Generated on Tue Jul 12 2022 12:21:58 by
