Ennio Santacroce / Mbed OS Testomax

Dependencies:   Cayenne-LPP

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers main.cpp Source File

main.cpp

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 #include <stdio.h>
00018 
00019 #include "lorawan/LoRaWANInterface.h"
00020 #include "lorawan/system/lorawan_data_structures.h"
00021 #include "events/EventQueue.h"
00022 
00023 // Application helpers
00024 #include "DummySensor.h"
00025 #include "trace_helper.h"
00026 #include "lora_radio_helper.h"
00027 #include "CayenneLPP.h"
00028 
00029 using namespace events;
00030 
00031 // Max payload size can be LORAMAC_PHY_MAXPAYLOAD.
00032 // This example only communicates with much shorter messages (<30 bytes).
00033 // If longer messages are used, these buffers must be changed accordingly.
00034 uint8_t tx_buffer[30];
00035 uint8_t rx_buffer[30];
00036 
00037 /*
00038  * Sets up an application dependent transmission timer in ms. Used only when Duty Cycling is off for testing
00039  */
00040 #define TX_TIMER                        20000
00041 
00042 /**
00043  * Maximum number of events for the event queue.
00044  * 10 is the safe number for the stack events, however, if application
00045  * also uses the queue for whatever purposes, this number should be increased.
00046  */
00047 #define MAX_NUMBER_OF_EVENTS            10
00048 
00049 /**
00050  * Maximum number of retries for CONFIRMED messages before giving up
00051  */
00052 #define CONFIRMED_MSG_RETRY_COUNTER     3
00053 
00054 /**
00055  * Dummy pin for dummy sensor
00056  */
00057 #define PC_9                            0
00058 
00059 /**
00060  * Dummy sensor class object
00061  */
00062 DS1820  ds1820(PC_9);
00063 CayenneLPP cayenne(100);
00064 AnalogIn lm35(A0);
00065 /**
00066 * This event queue is the global event queue for both the
00067 * application and stack. To conserve memory, the stack is designed to run
00068 * in the same thread as the application and the application is responsible for
00069 * providing an event queue to the stack that will be used for ISR deferment as
00070 * well as application information event queuing.
00071 */
00072 static EventQueue ev_queue(MAX_NUMBER_OF_EVENTS *EVENTS_EVENT_SIZE);
00073 
00074 /**
00075  * Event handler.
00076  *
00077  * This will be passed to the LoRaWAN stack to queue events for the
00078  * application which in turn drive the application.
00079  */
00080 static void lora_event_handler(lorawan_event_t event);
00081 
00082 /**
00083  * Constructing Mbed LoRaWANInterface and passing it the radio object from lora_radio_helper.
00084  */
00085 static LoRaWANInterface lorawan(radio);
00086 
00087 /**
00088  * Application specific callbacks
00089  */
00090 static lorawan_app_callbacks_t callbacks;
00091 
00092 /**
00093  * Entry point for application
00094  */
00095 int main(void)
00096 {
00097     // setup tracing
00098     setup_trace();
00099 
00100     // stores the status of a call to LoRaWAN protocol
00101     lorawan_status_t retcode;
00102 
00103     // Initialize LoRaWAN stack
00104     if (lorawan.initialize(&ev_queue) != LORAWAN_STATUS_OK) {
00105         printf("\r\n LoRa initialization failed! \r\n");
00106         return -1;
00107     }
00108 
00109     printf("\r\n Mbed LoRaWANStack initialized \r\n");
00110 
00111     // prepare application callbacks
00112     callbacks.events = mbed::callback(lora_event_handler);
00113     lorawan.add_app_callbacks(&callbacks);
00114 
00115     // Set number of retries in case of CONFIRMED messages
00116     if (lorawan.set_confirmed_msg_retries(CONFIRMED_MSG_RETRY_COUNTER)
00117             != LORAWAN_STATUS_OK) {
00118         printf("\r\n set_confirmed_msg_retries failed! \r\n\r\n");
00119         return -1;
00120     }
00121 
00122     printf("\r\n CONFIRMED message retries : %d \r\n",
00123            CONFIRMED_MSG_RETRY_COUNTER);
00124 
00125     // Enable adaptive data rate
00126     if (lorawan.enable_adaptive_datarate() != LORAWAN_STATUS_OK) {
00127         printf("\r\n enable_adaptive_datarate failed! \r\n");
00128         return -1;
00129     }
00130 
00131     printf("\r\n Adaptive data  rate (ADR) - Enabled \r\n");
00132 
00133     retcode = lorawan.connect();
00134 
00135     if (retcode == LORAWAN_STATUS_OK ||
00136             retcode == LORAWAN_STATUS_CONNECT_IN_PROGRESS) {
00137     } else {
00138         printf("\r\n Connection error, code = %d \r\n", retcode);
00139         return -1;
00140     }
00141 
00142     printf("\r\n Connection - In Progress ...\r\n");
00143 
00144     // make your event queue dispatching events forever
00145     ev_queue.dispatch_forever();
00146 
00147     return 0;
00148 }
00149 
00150 /**
00151  * Sends a message to the Network Server
00152  */
00153 static void send_message()
00154 {
00155     uint16_t packet_len;
00156     int16_t retcode;
00157     float sensor_value;
00158     float lm35temp;
00159 
00160     if (ds1820.begin()) {
00161         ds1820.startConversion();
00162         sensor_value = ds1820.read();
00163         printf("\r\n Dummy Sensor Value = %f \r\n", sensor_value);
00164         ds1820.startConversion();
00165     } else {
00166         printf("\r\n No sensor found \r\n");
00167         return;
00168     }
00169     lm35temp=lm35.read()*330.0;
00170 
00171     cayenne.reset(); // vidage du payload cayenne
00172     cayenne.addTemperature(2, lm35temp);
00173     cayenne.addTemperature(1, sensor_value); // ajout de la valeur t°
00174     cayenne.copy(tx_buffer); // copie dans le buffer LORA
00175     packet_len=cayenne.getSize();
00176     retcode = lorawan.send(MBED_CONF_LORA_APP_PORT, tx_buffer, packet_len,
00177 MSG_CONFIRMED_FLAG);
00178 
00179     packet_len = sprintf((char *) tx_buffer, "Dummy Sensor Value is %f",sensor_value);
00180 
00181     retcode = lorawan.send(MBED_CONF_LORA_APP_PORT, tx_buffer, packet_len,
00182                            MSG_UNCONFIRMED_FLAG);
00183     printf("\n lm35 : %.2f\n",lm35temp);
00184     printf("\nMessage: ");
00185     for(int i=0;i<packet_len;i++) printf("%02X ",tx_buffer[i]);
00186     printf("\n");
00187 
00188     if (retcode < 0) {
00189         retcode == LORAWAN_STATUS_WOULD_BLOCK ? printf("send - WOULD BLOCK\r\n")
00190         : printf("\r\n send() - Error code %d \r\n", retcode);
00191 
00192         if (retcode == LORAWAN_STATUS_WOULD_BLOCK) {
00193             //retry in 3 seconds
00194             if (MBED_CONF_LORA_DUTY_CYCLE_ON) {
00195                 ev_queue.call_in(3000, send_message);
00196             }
00197         }
00198         return;
00199     }
00200 
00201     printf("\r\n %d bytes scheduled for transmission \r\n", retcode);
00202     memset(tx_buffer, 0, sizeof(tx_buffer));
00203 }
00204 
00205 /**
00206  * Receive a message from the Network Server
00207  */
00208 static void receive_message()
00209 {
00210     uint8_t port;
00211     int flags;
00212     int16_t retcode = lorawan.receive(rx_buffer, sizeof(rx_buffer), port, flags);
00213 
00214     if (retcode < 0) {
00215         printf("\r\n receive() - Error code %d \r\n", retcode);
00216         return;
00217     }
00218 
00219     printf(" RX Data on port %u (%d bytes): ", port, retcode);
00220     for (uint8_t i = 0; i < retcode; i++) {
00221         printf("%02x ", rx_buffer[i]);
00222     }
00223     printf("\r\n");
00224     
00225     memset(rx_buffer, 0, sizeof(rx_buffer));
00226 }
00227 
00228 /**
00229  * Event handler
00230  */
00231 static void lora_event_handler(lorawan_event_t event)
00232 {
00233     switch (event) {
00234         case CONNECTED:
00235             printf("\r\n Connection - Successful \r\n");
00236             if (MBED_CONF_LORA_DUTY_CYCLE_ON) {
00237                 send_message();
00238             } else {
00239                 ev_queue.call_every(TX_TIMER, send_message);
00240             }
00241 
00242             break;
00243         case DISCONNECTED:
00244             ev_queue.break_dispatch();
00245             printf("\r\n Disconnected Successfully \r\n");
00246             break;
00247         case TX_DONE:
00248             printf("\r\n Message Sent to Network Server \r\n");
00249             if (MBED_CONF_LORA_DUTY_CYCLE_ON) {
00250                 send_message();
00251             }
00252             break;
00253         case TX_TIMEOUT:
00254         case TX_ERROR:
00255         case TX_CRYPTO_ERROR:
00256         case TX_SCHEDULING_ERROR:
00257             printf("\r\n Transmission Error - EventCode = %d \r\n", event);
00258             // try again
00259             if (MBED_CONF_LORA_DUTY_CYCLE_ON) {
00260                 send_message();
00261             }
00262             break;
00263         case RX_DONE:
00264             printf("\r\n Received message from Network Server \r\n");
00265             receive_message();
00266             break;
00267         case RX_TIMEOUT:
00268         case RX_ERROR:
00269             printf("\r\n Error in reception - Code = %d \r\n", event);
00270             break;
00271         case JOIN_FAILURE:
00272             printf("\r\n OTAA Failed - Check Keys \r\n");
00273             break;
00274         case UPLINK_REQUIRED:
00275             printf("\r\n Uplink required by NS \r\n");
00276             if (MBED_CONF_LORA_DUTY_CYCLE_ON) {
00277                 send_message();
00278             }
00279             break;
00280         default:
00281             MBED_ASSERT("Unknown Event");
00282     }
00283 }
00284 
00285 // EOF