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.
LoRaWANInterface.h
00001 /** 00002 * Copyright (c) 2017, Arm Limited and affiliates. 00003 * SPDX-License-Identifier: Apache-2.0 00004 * 00005 * Licensed under the Apache License, Version 2.0 (the "License"); 00006 * you may not use this file except in compliance with the License. 00007 * You may obtain a copy of the License at 00008 * 00009 * http://www.apache.org/licenses/LICENSE-2.0 00010 * 00011 * Unless required by applicable law or agreed to in writing, software 00012 * distributed under the License is distributed on an "AS IS" BASIS, 00013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 00014 * See the License for the specific language governing permissions and 00015 * limitations under the License. 00016 */ 00017 00018 #ifndef LORAWANINTERFACE_H_ 00019 #define LORAWANINTERFACE_H_ 00020 00021 #include "platform/Callback.h" 00022 #include "platform/ScopedLock.h" 00023 #include "LoRaWANStack.h" 00024 #include "LoRaRadio.h" 00025 #include "LoRaWANBase.h" 00026 00027 class LoRaWANInterface: public LoRaWANBase { 00028 00029 public: 00030 00031 /** Constructs a LoRaWANInterface using the LoRaWANStack instance underneath. 00032 * 00033 * Currently, LoRaWANStack is a singleton and you should only 00034 * construct a single instance of LoRaWANInterface. 00035 * 00036 */ 00037 LoRaWANInterface(LoRaRadio& radio); 00038 00039 virtual ~LoRaWANInterface(); 00040 00041 /** Initialize the LoRa stack. 00042 * 00043 * You must call this first to be able to use the LoRa stack. 00044 * 00045 * @param ev_queue A pointer to EventQueue provided by the application. 00046 * 00047 * @return 0 on success, a negative error code on failure. 00048 */ 00049 virtual lorawan_status_t initialize(events::EventQueue *ev_queue); 00050 00051 /** Connect OTAA or ABP using Mbed-OS config system 00052 * 00053 * Connect by Over The Air Activation or Activation By Personalization. 00054 * You need to configure the connection properly via the Mbed OS configuration 00055 * system. 00056 * 00057 * When connecting via OTAA, the return code for success (LORAWAN_STATUS_CONNECT_IN_PROGRESS) is negative. 00058 * However, this is not a real error. It tells you that the connection is in progress and you will 00059 * be notified of the completion via an event. By default, after the Join Accept message 00060 * is received, base stations may provide the node with a CF-List that replaces 00061 * all user-configured channels except the Join/Default channels. A CF-List can 00062 * configure a maximum of five channels other than the default channels. 00063 * 00064 * In case of ABP, the CONNECTED event is posted before the call to `connect()` returns. 00065 * To configure more channels, we recommend that you use the `set_channel_plan()` API after the connection. 00066 * By default, the PHY layers configure only the mandatory Join channels. The retransmission back-off restrictions 00067 * on these channels are severe and you may experience long delays or even failures in the confirmed traffic. 00068 * If you add more channels, the aggregated duty cycle becomes much more relaxed as compared to the Join (default) channels only. 00069 * 00070 * **NOTES ON RECONNECTION:** 00071 * Currently, the Mbed OS LoRaWAN implementation does not support non-volatile 00072 * memory storage. Therefore, the state and frame counters cannot be restored after 00073 * a power cycle. However, if you use the `disconnect()` API to shut down the LoRaWAN 00074 * protocol, the state and frame counters are saved. Connecting again would try to 00075 * restore the previous session. According to the LoRaWAN 1.0.2 specification, the frame counters are always reset 00076 * to zero for OTAA and a new Join request lets the network server know 00077 * that the counters need a reset. The same is said about the ABP but there 00078 * is no way to convey this information to the network server. For a network 00079 * server, an ABP device is always connected. That's why storing the frame counters 00080 * is important, at least for ABP. That's why we try to restore frame counters from 00081 * session information after a disconnection. 00082 * 00083 * @return LORAWAN_STATUS_OK or LORAWAN_STATUS_CONNECT_IN_PROGRESS 00084 * on success, or a negative error code on failure. 00085 */ 00086 virtual lorawan_status_t connect(); 00087 00088 /** Connect OTAA or ABP with parameters 00089 * 00090 * All connection parameters are chosen by the user and provided in the 00091 * data structure passed down. 00092 * 00093 * When connecting via OTAA, the return code for success (LORAWAN_STATUS_CONNECT_IN_PROGRESS) is negative. 00094 * However, this is not a real error. It tells you that connection is in progress and you will 00095 * be notified of completion via an event. By default, after Join Accept message 00096 * is received, base stations may provide the node with a CF-List which replaces 00097 * all user-configured channels except the Join/Default channels. A CF-List can 00098 * configure a maximum of five channels other than the default channels. 00099 * 00100 * In case of ABP, the CONNECTED event is posted before the call to `connect()` returns. 00101 * To configure more channels, we recommend that you use the `set_channel_plan()` API after the connection. 00102 * By default, the PHY layers configure only the mandatory Join 00103 * channels. The retransmission back-off restrictions on these channels 00104 * are severe and you may experience long delays or even 00105 * failures in the confirmed traffic. If you add more channels, the aggregated duty 00106 * cycle becomes much more relaxed as compared to the Join (default) channels only. 00107 * 00108 * **NOTES ON RECONNECTION:** 00109 * Currently, the Mbed OS LoRaWAN implementation does not support non-volatile 00110 * memory storage. Therefore, the state and frame counters cannot be restored after 00111 * a power cycle. However, if you use the `disconnect()` API to shut down the LoRaWAN 00112 * protocol, the state and frame counters are saved. Connecting again would try to 00113 * restore the previous session. According to the LoRaWAN 1.0.2 specification, the frame counters are always reset 00114 * to zero for OTAA and a new Join request lets the network server know 00115 * that the counters need a reset. The same is said about the ABP but there 00116 * is no way to convey this information to the network server. For a network 00117 * server, an ABP device is always connected. That's why storing the frame counters 00118 * is important, at least for ABP. That's why we try to restore frame counters from 00119 * session information after a disconnection. 00120 * 00121 * @param connect Options for an end device connection to the gateway. 00122 * 00123 * @return LORAWAN_STATUS_OK or LORAWAN_STATUS_CONNECT_IN_PROGRESS, 00124 * a negative error code on failure. 00125 */ 00126 virtual lorawan_status_t connect(const lorawan_connect_t &connect); 00127 00128 /** Disconnect the current session. 00129 * 00130 * @return LORAWAN_STATUS_DEVICE_OFF on successfully shutdown. 00131 */ 00132 virtual lorawan_status_t disconnect(); 00133 00134 /** Validate the connectivity with the network. 00135 * 00136 * Application may use this API to submit a request to the stack for 00137 * validation of its connectivity to a Network Server. Under the hood, this 00138 * API schedules a Link Check Request command (LinkCheckReq) for the network 00139 * server and once the response, i.e., LinkCheckAns MAC command is received 00140 * from the Network Server, user provided method is called. 00141 * 00142 * One way to use this API may be the validation of connectivity after a long 00143 * deep sleep. Mbed LoRaWANStack piggy-backs the MAC commands with data 00144 * frame payload so the application needs to try sending something and the Network 00145 * Server may respond during the RX slots. 00146 * 00147 * This API is usable only when the 'link_check_resp' callback is set by 00148 * the application. See add_lora_app_callbacks API. If the above mentioned 00149 * callback is not set, a LORAWAN_STATUS_PARAMETER_INVALID error is thrown. 00150 * 00151 * First parameter to callback function is the demodulation margin and 00152 * the second parameter is the number of gateways that successfully received 00153 * the last request. 00154 * 00155 * A 'Link Check Request' MAC command remains set for every subsequent 00156 * transmission, until/unless application explicitly turns it off using 00157 * remove_link_check_request() API. 00158 * 00159 * @return LORAWAN_STATUS_OK on successfully queuing a request, or 00160 * a negative error code on failure. 00161 * 00162 */ 00163 virtual lorawan_status_t add_link_check_request(); 00164 00165 /** Removes link check request sticky MAC command. 00166 * 00167 * Any already queued request may still get entertained. However, no new 00168 * requests will be made. 00169 */ 00170 virtual void remove_link_check_request(); 00171 00172 /** Sets up a particular data rate 00173 * 00174 * `set_datarate()` first verifies whether the data rate given is valid or not. 00175 * If it is valid, the system sets the given data rate to the channel. 00176 * 00177 * @param data_rate The intended data rate, for example DR_0 or DR_1. 00178 * Please note, that the macro DR_* can mean different 00179 * things in different regions. 00180 * @return LORAWAN_STATUS_OK if everything goes well, otherwise 00181 * a negative error code. 00182 */ 00183 virtual lorawan_status_t set_datarate(uint8_t data_rate); 00184 00185 /** Enables adaptive data rate (ADR). 00186 * 00187 * The underlying LoRaPHY and LoRaMac layers handle the data rate automatically 00188 * for the user, based upon the radio conditions (network congestion). 00189 * 00190 * @return LORAWAN_STATUS_OK or negative error code otherwise. 00191 */ 00192 virtual lorawan_status_t enable_adaptive_datarate(); 00193 00194 /** Disables adaptive data rate. 00195 * 00196 * When adaptive data rate (ADR) is disabled, you can either set a certain 00197 * data rate or the MAC layer selects a default value. 00198 * 00199 * @return LORAWAN_STATUS_OK or negative error code otherwise. 00200 */ 00201 virtual lorawan_status_t disable_adaptive_datarate(); 00202 00203 /** Sets up the retry counter for confirmed messages. 00204 * 00205 * Valid for confirmed messages only. 00206 * 00207 * The number of trials to transmit the frame, if the LoRaMAC layer did not 00208 * receive an acknowledgment. The MAC performs a data rate adaptation as in 00209 * the LoRaWAN Specification V1.0.2, chapter 18.4, table on page 64. 00210 * 00211 * Note, that if number of retries is set to 1 or 2, MAC will not decrease 00212 * the datarate, if the LoRaMAC layer did not receive an acknowledgment. 00213 * 00214 * @param count The number of retries for confirmed messages. 00215 * 00216 * @return LORAWAN_STATUS_OK or a negative error code. 00217 */ 00218 virtual lorawan_status_t set_confirmed_msg_retries(uint8_t count); 00219 00220 /** Sets the channel plan. 00221 * 00222 * You can provide a list of channels with appropriate parameters filled 00223 * in. However, this list is not absolute. The stack applies a CF-List whenever 00224 * available, which means that the network can overwrite your channel 00225 * frequency settings right after Join Accept is received. You may try 00226 * to set up any channel or channels after that, and if the channel requested 00227 * is already active, the request is silently ignored. A negative error 00228 * code is returned if there is any problem with parameters. 00229 * 00230 * Please note that this API can also be used to add a single channel to the 00231 * existing channel plan. 00232 * 00233 * There is no reverse mechanism in the 1.0.2 specification for a node to request 00234 * a particular channel. Only the network server can initiate such a request. 00235 * You need to ensure that the corresponding base station supports the channel or channels being added. 00236 * 00237 * If your list includes a default channel (a channel where Join Requests 00238 * are received) you cannot fully configure the channel parameters. 00239 * Either leave the channel settings to default or check your 00240 * corresponding PHY layer implementation. For example, LoRaPHYE868. 00241 * 00242 * @param channel_plan The channel plan to set. 00243 * 00244 * @return LORAWAN_STATUS_OK on success, a negative error 00245 * code on failure. 00246 */ 00247 virtual lorawan_status_t set_channel_plan(const lorawan_channelplan_t &channel_plan); 00248 00249 /** Gets the channel plans from the LoRa stack. 00250 * 00251 * Once you have selected a particular PHY layer, a set of channels 00252 * is automatically activated. Right after connecting, you can use this API 00253 * to see the current plan. Otherwise, this API returns the channel 00254 * plan that you have set using `set_channel_plan()`. 00255 * 00256 * @param channel_plan The current channel plan information. 00257 * 00258 * @return LORAWAN_STATUS_OK on success, a negative error 00259 * code on failure. 00260 */ 00261 virtual lorawan_status_t get_channel_plan(lorawan_channelplan_t &channel_plan); 00262 00263 /** Removes an active channel plan. 00264 * 00265 * You cannot remove default channels (the channels the base stations are listening to). 00266 * When a plan is abolished, only the non-default channels are removed. 00267 * 00268 * @return LORAWAN_STATUS_OK on success, a negative error 00269 * code on failure. 00270 */ 00271 virtual lorawan_status_t remove_channel_plan(); 00272 00273 /** Removes a single channel. 00274 * 00275 * You cannot remove default channels (the channels the base stations are listening to). 00276 * 00277 * @param index The channel index. 00278 * 00279 * @return LORAWAN_STATUS_OK on success, a negative error 00280 * code on failure. 00281 */ 00282 virtual lorawan_status_t remove_channel(uint8_t index); 00283 00284 /** Send message to gateway 00285 * 00286 * @param port The application port number. Port numbers 0 and 224 00287 * are reserved, whereas port numbers from 1 to 223 00288 * (0x01 to 0xDF) are valid port numbers. 00289 * Anything out of this range is illegal. 00290 * 00291 * @param data A pointer to the data being sent. The ownership of the 00292 * buffer is not transferred. The data is copied to the 00293 * internal buffers. 00294 * 00295 * @param length The size of data in bytes. 00296 * 00297 * @param flags A flag used to determine what type of 00298 * message is being sent, for example: 00299 * 00300 * MSG_UNCONFIRMED_FLAG = 0x01 00301 * MSG_CONFIRMED_FLAG = 0x02 00302 * MSG_MULTICAST_FLAG = 0x04 00303 * MSG_PROPRIETARY_FLAG = 0x08 00304 * MSG_MULTICAST_FLAG and MSG_PROPRIETARY_FLAG can be 00305 * used in conjunction with MSG_UNCONFIRMED_FLAG and 00306 * MSG_CONFIRMED_FLAG depending on the intended use. 00307 * 00308 * MSG_PROPRIETARY_FLAG|MSG_CONFIRMED_FLAG mask will set 00309 * a confirmed message flag for a proprietary message. 00310 * MSG_CONFIRMED_FLAG and MSG_UNCONFIRMED_FLAG are 00311 * mutually exclusive. 00312 * 00313 * 00314 * @return The number of bytes sent, or 00315 * LORAWAN_STATUS_WOULD_BLOCK if another TX is 00316 * ongoing, or a negative error code on failure. 00317 */ 00318 virtual int16_t send(uint8_t port, const uint8_t* data, uint16_t length, 00319 int flags); 00320 00321 /** Receives a message from the Network Server on a specific port. 00322 * 00323 * @param port The application port number. Port numbers 0 and 224 00324 * are reserved, whereas port numbers from 1 to 223 00325 * (0x01 to 0xDF) are valid port numbers. 00326 * Anything out of this range is illegal. 00327 * 00328 * @param data A pointer to buffer where the received data will be 00329 * stored. 00330 * 00331 * @param length The size of data in bytes 00332 * 00333 * @param flags A flag is used to determine what type of 00334 * message is being sent, for example: 00335 * 00336 * MSG_UNCONFIRMED_FLAG = 0x01, 00337 * MSG_CONFIRMED_FLAG = 0x02 00338 * MSG_MULTICAST_FLAG = 0x04, 00339 * MSG_PROPRIETARY_FLAG = 0x08 00340 * 00341 * MSG_MULTICAST_FLAG and MSG_PROPRIETARY_FLAG can be 00342 * used in conjunction with MSG_UNCONFIRMED_FLAG and 00343 * MSG_CONFIRMED_FLAG depending on the intended use. 00344 * 00345 * MSG_PROPRIETARY_FLAG|MSG_CONFIRMED_FLAG mask will set 00346 * a confirmed message flag for a proprietary message. 00347 * 00348 * MSG_CONFIRMED_FLAG and MSG_UNCONFIRMED_FLAG are 00349 * not mutually exclusive, i.e., the user can subscribe to 00350 * receive both CONFIRMED AND UNCONFIRMED messages at 00351 * the same time. 00352 * 00353 * @return It could be one of these: 00354 * i) 0 if there is nothing else to read. 00355 * ii) Number of bytes written to user buffer. 00356 * iii) LORAWAN_STATUS_WOULD_BLOCK if there is 00357 * nothing available to read at the moment. 00358 * iv) A negative error code on failure. 00359 */ 00360 virtual int16_t receive(uint8_t port, uint8_t* data, uint16_t length, int flags); 00361 00362 /** Receives a message from the Network Server on any port. 00363 * 00364 * @param data A pointer to buffer where the received data will be 00365 * stored. 00366 * 00367 * @param length The size of data in bytes 00368 * 00369 * @param port Return the number of port to which message was received. 00370 * 00371 * @param flags Return flags to determine what type of message was received. 00372 * MSG_UNCONFIRMED_FLAG = 0x01 00373 * MSG_CONFIRMED_FLAG = 0x02 00374 * MSG_MULTICAST_FLAG = 0x04 00375 * MSG_PROPRIETARY_FLAG = 0x08 00376 * 00377 * @return It could be one of these: 00378 * i) 0 if there is nothing else to read. 00379 * ii) Number of bytes written to user buffer. 00380 * iii) LORAWAN_STATUS_WOULD_BLOCK if there is 00381 * nothing available to read at the moment. 00382 * iv) A negative error code on failure. 00383 */ 00384 virtual int16_t receive(uint8_t* data, uint16_t length, uint8_t& port, int& flags); 00385 00386 /** Add application callbacks to the stack. 00387 * 00388 * An example of using this API with a latch onto 'lorawan_events' could be: 00389 * 00390 * LoRaWANInterface lorawan(radio); 00391 * lorawan_app_callbacks_t cbs; 00392 * static void my_event_handler(); 00393 * 00394 * int main() 00395 * { 00396 * lorawan.initialize(); 00397 * cbs.lorawan_events = mbed::callback(my_event_handler); 00398 * lorawan.add_app_callbacks(&cbs); 00399 * lorawan.connect(); 00400 * } 00401 * 00402 * static void my_event_handler(lorawan_event_t event) 00403 * { 00404 * switch(event) { 00405 * case CONNECTED: 00406 * //do something 00407 * break; 00408 * case DISCONNECTED: 00409 * //do something 00410 * break; 00411 * case TX_DONE: 00412 * //do something 00413 * break; 00414 * default: 00415 * break; 00416 * } 00417 * } 00418 * 00419 * @param callbacks A pointer to the structure containing application 00420 * callbacks. 00421 * 00422 * @return LORAWAN_STATUS_OK on success, a negative error 00423 * code on failure. 00424 */ 00425 virtual lorawan_status_t add_app_callbacks(lorawan_app_callbacks_t *callbacks); 00426 00427 /** Change device class 00428 * 00429 * Change current device class. 00430 * 00431 * @param device_class The device class 00432 * 00433 * @return LORAWAN_STATUS_OK on success, 00434 * LORAWAN_STATUS_UNSUPPORTED is requested class is not supported, 00435 * or other negative error code if request failed. 00436 */ 00437 virtual lorawan_status_t set_device_class(const device_class_t device_class); 00438 00439 void lock(void) { _lw_stack.lock(); } 00440 void unlock(void) { _lw_stack.unlock(); } 00441 00442 00443 private: 00444 typedef mbed::ScopedLock<LoRaWANInterface> Lock; 00445 00446 LoRaWANStack _lw_stack; 00447 }; 00448 00449 #endif /* LORAWANINTERFACE_H_ */
Generated on Tue Jul 12 2022 18:18:38 by
