Lora Personalized device for Everynet

Dependencies:   LMiCPersonalizedforEverynet SX1276Lib X_NUCLEO_IKS01A1 cantcoap lwip mbed-rtos mbed

Fork of LoRaWAN-test-10secs by Alcatel-Lucent IoT Development

Committer:
pnysten
Date:
Tue Jan 19 14:22:28 2016 +0000
Revision:
11:59c160a8926d
Parent:
10:155dc60fce79
Child:
12:f28b629d8a6e
Last version

Who changed what in which revision?

UserRevisionLine numberNew contents of line
sam_grove 3:ce28e3313a88 1 /*
mluis 0:a2929fa6e4f0 2 / _____) _ | |
mluis 0:a2929fa6e4f0 3 ( (____ _____ ____ _| |_ _____ ____| |__
mluis 0:a2929fa6e4f0 4 \____ \| ___ | (_ _) ___ |/ ___) _ \
mluis 0:a2929fa6e4f0 5 _____) ) ____| | | || |_| ____( (___| | | |
mluis 0:a2929fa6e4f0 6 (______/|_____)_|_|_| \__)_____)\____)_| |_|
mluis 1:60184eda0066 7 (C)2015 Semtech
mluis 0:a2929fa6e4f0 8
mluis 1:60184eda0066 9 Description: MBED LoRaWAN example application
mluis 0:a2929fa6e4f0 10
mluis 0:a2929fa6e4f0 11 License: Revised BSD License, see LICENSE.TXT file include in the project
mluis 0:a2929fa6e4f0 12
mluis 0:a2929fa6e4f0 13 Maintainer: Miguel Luis and Gregory Cristian
mluis 0:a2929fa6e4f0 14 */
pnysten 6:540c5d907c90 15
pnysten 4:5e274bf85bf0 16 #include <cstdio>
pnysten 4:5e274bf85bf0 17 #include <string>
pnysten 4:5e274bf85bf0 18 #include <cassert>
pnysten 4:5e274bf85bf0 19
mluis 1:60184eda0066 20 #include "mbed.h"
pnysten 6:540c5d907c90 21 //#include "Node.h"
pnysten 4:5e274bf85bf0 22 #include "cantcoap.h"
pnysten 10:155dc60fce79 23 #include "x_nucleo_iks01a1.h"
pnysten 10:155dc60fce79 24 #include "rtos.h"
mluis 1:60184eda0066 25
mluis 0:a2929fa6e4f0 26 #include "lmic.h"
mluis 1:60184eda0066 27 #include "debug.h"
mluis 0:a2929fa6e4f0 28
pnysten 10:155dc60fce79 29 /* Instantiate the expansion board */
pnysten 10:155dc60fce79 30 static X_NUCLEO_IKS01A1 *mems_expansion_board = X_NUCLEO_IKS01A1::Instance(D14, D15);
pnysten 10:155dc60fce79 31
pnysten 10:155dc60fce79 32 /* Retrieve the composing elements of the expansion board */
pnysten 10:155dc60fce79 33 static GyroSensor *gyroscope = mems_expansion_board->GetGyroscope();
pnysten 10:155dc60fce79 34 static MotionSensor *accelerometer = mems_expansion_board->GetAccelerometer();
pnysten 10:155dc60fce79 35 static MagneticSensor *magnetometer = mems_expansion_board->magnetometer;
pnysten 10:155dc60fce79 36 static HumiditySensor *humidity_sensor = mems_expansion_board->ht_sensor;
pnysten 10:155dc60fce79 37 static PressureSensor *pressure_sensor = mems_expansion_board->pt_sensor;
pnysten 10:155dc60fce79 38 static TempSensor *temp_sensor1 = mems_expansion_board->ht_sensor;
pnysten 10:155dc60fce79 39 static TempSensor *temp_sensor2 = mems_expansion_board->pt_sensor;
pnysten 10:155dc60fce79 40
pnysten 10:155dc60fce79 41 uint8_t id;
pnysten 10:155dc60fce79 42 float value1, value2;
pnysten 10:155dc60fce79 43 char buffer1[32], buffer2[32], buffer3[32];
pnysten 10:155dc60fce79 44 int32_t axes[3];
pnysten 10:155dc60fce79 45
pnysten 10:155dc60fce79 46 static bool temp_sent = false;
pnysten 10:155dc60fce79 47 static bool hum_sent = false;
pnysten 10:155dc60fce79 48 static bool press_sent = false;
pnysten 10:155dc60fce79 49 static bool gyro_sent = false;
pnysten 10:155dc60fce79 50 static bool motion_sent = false;
pnysten 10:155dc60fce79 51 static bool magn_sent = false;
pnysten 10:155dc60fce79 52
pnysten 4:5e274bf85bf0 53 const std::string REGISTRATION_SEGMENT ="/rd";
pnysten 4:5e274bf85bf0 54 const std::string ENDPOINT_SEGMENT = "?ep=";
pnysten 4:5e274bf85bf0 55 const std::string LIFETIME ="&lt=";
pnysten 4:5e274bf85bf0 56 const std::string BINDING ="&b=";
pnysten 6:540c5d907c90 57
pnysten 4:5e274bf85bf0 58 const std::string REGISTRATION_OPEN = "<";
pnysten 4:5e274bf85bf0 59 const std::string REGISTRATION_CLOSE = ">";
pnysten 4:5e274bf85bf0 60 const std::string REGISTRATION_SEPARATOR ="/";
pnysten 6:540c5d907c90 61
pnysten 4:5e274bf85bf0 62 int _node_Id=0;
pnysten 6:540c5d907c90 63
pnysten 4:5e274bf85bf0 64 const std::string endPoint_Name = "loraDevice";
pnysten 4:5e274bf85bf0 65 const int lifeTime = 300;
pnysten 4:5e274bf85bf0 66 const std::string binding = "U";
pnysten 6:540c5d907c90 67
pnysten 4:5e274bf85bf0 68 unsigned char * _payload;
pnysten 4:5e274bf85bf0 69 long _payload_size;
pnysten 6:540c5d907c90 70
mluis 0:a2929fa6e4f0 71 /*!
mluis 0:a2929fa6e4f0 72 * When set to 1 the application uses the Over-the-Air activation procedure
mluis 0:a2929fa6e4f0 73 * When set to 0 the application uses the Personalization activation procedure
mluis 0:a2929fa6e4f0 74 */
mluis 0:a2929fa6e4f0 75 #define OVER_THE_AIR_ACTIVATION 0
mluis 0:a2929fa6e4f0 76
mluis 1:60184eda0066 77 #if( OVER_THE_AIR_ACTIVATION == 0 )
mluis 1:60184eda0066 78
mluis 1:60184eda0066 79 /*!
mluis 1:60184eda0066 80 * Defines the network ID when using personalization activation procedure
mluis 1:60184eda0066 81 */
mluis 1:60184eda0066 82 #define LORAWAN_NET_ID ( uint32_t )0x00000000
mluis 1:60184eda0066 83
mluis 1:60184eda0066 84 /*!
mluis 1:60184eda0066 85 * Defines the device address when using personalization activation procedure
mluis 1:60184eda0066 86 */
pnysten 9:84a69ca4d35a 87 //To be changed when switching from one to another
pnysten 7:f1521b0ecf08 88 #define LORAWAN_DEV_ADDR ( uint32_t )0x12345678
pnysten 6:540c5d907c90 89 //#define LORAWAN_DEV_ADDR ( uint32_t )0x12341111
mluis 1:60184eda0066 90
mluis 1:60184eda0066 91 #endif
mluis 1:60184eda0066 92
mluis 1:60184eda0066 93 /*!
mluis 1:60184eda0066 94 * Defines the application data transmission duty cycle
mluis 1:60184eda0066 95 */
mluis 1:60184eda0066 96 #define APP_TX_DUTYCYCLE 5000 // 5 [s] value in ms
mluis 1:60184eda0066 97 #define APP_TX_DUTYCYCLE_RND 1000 // 1 [s] value in ms
mluis 1:60184eda0066 98
mluis 1:60184eda0066 99 /*!
mluis 1:60184eda0066 100 * LoRaWAN Adaptative Data Rate
mluis 1:60184eda0066 101 */
mluis 1:60184eda0066 102 #define LORAWAN_ADR_ON 1
mluis 1:60184eda0066 103
mluis 1:60184eda0066 104 /*!
mluis 1:60184eda0066 105 * LoRaWAN confirmed messages
mluis 1:60184eda0066 106 */
pnysten 9:84a69ca4d35a 107 #define LORAWAN_CONFIRMED_MSG_ON 0
mluis 1:60184eda0066 108
mluis 1:60184eda0066 109 /*!
mluis 1:60184eda0066 110 * LoRaWAN application port
mluis 1:60184eda0066 111 */
mluis 1:60184eda0066 112 #define LORAWAN_APP_PORT 15
mluis 1:60184eda0066 113
mluis 1:60184eda0066 114 /*!
mluis 1:60184eda0066 115 * User application data buffer size
mluis 1:60184eda0066 116 */
mluis 1:60184eda0066 117 #if ( LORAWAN_CONFIRMED_MSG_ON == 1 )
mluis 1:60184eda0066 118 #define LORAWAN_APP_DATA_SIZE 6
mluis 1:60184eda0066 119
mluis 1:60184eda0066 120 #else
mluis 1:60184eda0066 121 #define LORAWAN_APP_DATA_SIZE 1
mluis 1:60184eda0066 122
mluis 1:60184eda0066 123 #endif
mluis 0:a2929fa6e4f0 124
pnysten 4:5e274bf85bf0 125 #define UINT16_MAX (65535U)
pnysten 4:5e274bf85bf0 126 #define UINT64_MAX (18446744073709551615ULL)
pnysten 6:540c5d907c90 127
pnysten 6:540c5d907c90 128 //Node lwm2mNode("LR-test0");;
pnysten 6:540c5d907c90 129 unsigned int LoRaWAN_data_size = 0;
pnysten 4:5e274bf85bf0 130
pnysten 10:155dc60fce79 131 /* Helper function for printing floats & doubles */
pnysten 10:155dc60fce79 132 static char *printDouble(char* str, double v, int decimalDigits=2)
pnysten 10:155dc60fce79 133 {
pnysten 10:155dc60fce79 134 int i = 1;
pnysten 10:155dc60fce79 135 int intPart, fractPart;
pnysten 10:155dc60fce79 136 int len;
pnysten 10:155dc60fce79 137 char *ptr;
pnysten 10:155dc60fce79 138
pnysten 10:155dc60fce79 139 /* prepare decimal digits multiplicator */
pnysten 10:155dc60fce79 140 for (;decimalDigits!=0; i*=10, decimalDigits--);
pnysten 10:155dc60fce79 141
pnysten 10:155dc60fce79 142 /* calculate integer & fractinal parts */
pnysten 10:155dc60fce79 143 intPart = (int)v;
pnysten 10:155dc60fce79 144 fractPart = (int)((v-(double)(int)v)*i);
pnysten 10:155dc60fce79 145
pnysten 10:155dc60fce79 146 /* fill in integer part */
pnysten 10:155dc60fce79 147 sprintf(str, "%i.", intPart);
pnysten 10:155dc60fce79 148
pnysten 10:155dc60fce79 149 /* prepare fill in of fractional part */
pnysten 10:155dc60fce79 150 len = strlen(str);
pnysten 10:155dc60fce79 151 ptr = &str[len];
pnysten 10:155dc60fce79 152
pnysten 10:155dc60fce79 153 /* fill in leading fractional zeros */
pnysten 10:155dc60fce79 154 for (i/=10;i>1; i/=10, ptr++) {
pnysten 10:155dc60fce79 155 if(fractPart >= i) break;
pnysten 10:155dc60fce79 156 *ptr = '0';
pnysten 10:155dc60fce79 157 }
pnysten 10:155dc60fce79 158
pnysten 10:155dc60fce79 159 /* fill in (rest of) fractional part */
pnysten 10:155dc60fce79 160 sprintf(ptr, "%i", fractPart);
pnysten 10:155dc60fce79 161
pnysten 10:155dc60fce79 162 return str;
pnysten 10:155dc60fce79 163 }
pnysten 10:155dc60fce79 164
pnysten 10:155dc60fce79 165 /* Helper function for printing integers */
pnysten 10:155dc60fce79 166 static char *printInt(char* str, int v)
pnysten 10:155dc60fce79 167 {
pnysten 10:155dc60fce79 168 /* fill in integer part */
pnysten 10:155dc60fce79 169 sprintf(str, "%i", v);
pnysten 10:155dc60fce79 170
pnysten 10:155dc60fce79 171 return str;
pnysten 10:155dc60fce79 172 }
pnysten 10:155dc60fce79 173
pnysten 10:155dc60fce79 174 /* Thread for calling libNsdl exec function (cleanup, resendings etc..) */
pnysten 10:155dc60fce79 175 /* Node updates accelerometer every 60 seconds. Notification sending is done here. */
pnysten 10:155dc60fce79 176 static void exec_call_thread(void const *args)
pnysten 10:155dc60fce79 177 {
pnysten 10:155dc60fce79 178 uint8_t id;
pnysten 10:155dc60fce79 179 float value1, value2;
pnysten 10:155dc60fce79 180 char buffer1[32], buffer2[32];
pnysten 10:155dc60fce79 181 int32_t axes[3];
pnysten 10:155dc60fce79 182
pnysten 10:155dc60fce79 183 debug_str("--- Starting new run ---\r\n");
pnysten 10:155dc60fce79 184
pnysten 10:155dc60fce79 185 humidity_sensor->ReadID(&id);
pnysten 10:155dc60fce79 186 debug_str("HTS221 humidity & temperature = ");
pnysten 10:155dc60fce79 187 debug_uint(id);
pnysten 10:155dc60fce79 188 debug_str("\r\n");
pnysten 10:155dc60fce79 189 pressure_sensor->ReadID(&id);
pnysten 10:155dc60fce79 190 debug_str("LPS25H pressure & temperature = ");
pnysten 10:155dc60fce79 191 debug_uint(id);
pnysten 10:155dc60fce79 192 debug_str("\r\n");
pnysten 10:155dc60fce79 193 magnetometer->ReadID(&id);
pnysten 10:155dc60fce79 194 debug_str("LIS3MDL magnetometer = ");
pnysten 10:155dc60fce79 195 debug_uint(id);
pnysten 10:155dc60fce79 196 debug_str("\r\n");
pnysten 10:155dc60fce79 197 gyroscope->ReadID(&id);
pnysten 10:155dc60fce79 198 debug_str("LSM6DS0 accelerometer & gyroscope = ");
pnysten 10:155dc60fce79 199 debug_uint(id);
pnysten 10:155dc60fce79 200 debug_str("\r\n");
pnysten 10:155dc60fce79 201
pnysten 10:155dc60fce79 202 wait(3);
pnysten 10:155dc60fce79 203
pnysten 10:155dc60fce79 204 while(1) {
pnysten 10:155dc60fce79 205 debug_str("\r\n");
pnysten 10:155dc60fce79 206
pnysten 10:155dc60fce79 207 temp_sensor1->GetTemperature(&value1);
pnysten 10:155dc60fce79 208 humidity_sensor->GetHumidity(&value2);
pnysten 10:155dc60fce79 209 debug_str("HTS221: [temp] ");
pnysten 10:155dc60fce79 210 debug_str(printDouble(buffer1, value1));
pnysten 10:155dc60fce79 211 debug_str("°C, [hum] ");
pnysten 10:155dc60fce79 212 debug_str(printDouble(buffer2, value2));
pnysten 10:155dc60fce79 213 debug_str("%\r\n");
pnysten 10:155dc60fce79 214 //pc.printf("HTS221: [temp] %7s°C, [hum] %s%%\r\n", printDouble(buffer1, value1), printDouble(buffer2, value2));
pnysten 10:155dc60fce79 215
pnysten 10:155dc60fce79 216 temp_sensor2->GetFahrenheit(&value1);
pnysten 10:155dc60fce79 217 pressure_sensor->GetPressure(&value2);
pnysten 10:155dc60fce79 218 debug_str("LPS25H: [temp] ");
pnysten 10:155dc60fce79 219 debug_str(printDouble(buffer1, value1));
pnysten 10:155dc60fce79 220 debug_str("°F, [press] ");
pnysten 10:155dc60fce79 221 debug_str(printDouble(buffer2, value2));
pnysten 10:155dc60fce79 222 debug_str("mbar\r\n");
pnysten 10:155dc60fce79 223 //pc.printf("LPS25H: [temp] %7s°F, [press] %smbar\r\n", printDouble(buffer1, value1), printDouble(buffer2, value2));
pnysten 10:155dc60fce79 224
pnysten 10:155dc60fce79 225 debug_str("---\r\n");
pnysten 10:155dc60fce79 226
pnysten 10:155dc60fce79 227 magnetometer->Get_M_Axes(axes);
pnysten 10:155dc60fce79 228 debug_str("LIS3MDL [mag/mgauss]: ");
pnysten 10:155dc60fce79 229 debug_uint(axes[0]);
pnysten 10:155dc60fce79 230 debug_str(", ");
pnysten 10:155dc60fce79 231 debug_uint(axes[1]);
pnysten 10:155dc60fce79 232 debug_str(", ");
pnysten 10:155dc60fce79 233 debug_uint(axes[2]);
pnysten 10:155dc60fce79 234 debug_str("\r\n");
pnysten 10:155dc60fce79 235 //pc.printf("LIS3MDL [mag/mgauss]: %6ld, %6ld, %6ld\r\n", axes[0], axes[1], axes[2]);
pnysten 10:155dc60fce79 236
pnysten 10:155dc60fce79 237 accelerometer->Get_X_Axes(axes);
pnysten 10:155dc60fce79 238 debug_str("LSM6DS0 [acc/mg]: ");
pnysten 10:155dc60fce79 239 debug_uint(axes[0]);
pnysten 10:155dc60fce79 240 debug_str(", ");
pnysten 10:155dc60fce79 241 debug_uint(axes[1]);
pnysten 10:155dc60fce79 242 debug_str(", ");
pnysten 10:155dc60fce79 243 debug_uint(axes[2]);
pnysten 10:155dc60fce79 244 debug_str("\r\n");
pnysten 10:155dc60fce79 245 //pc.printf("LSM6DS0 [acc/mg]: %6ld, %6ld, %6ld\r\n", axes[0], axes[1], axes[2]);
pnysten 10:155dc60fce79 246
pnysten 10:155dc60fce79 247 gyroscope->Get_G_Axes(axes);
pnysten 10:155dc60fce79 248 debug_str("LSM6DS0 [gyro/mdps]: ");
pnysten 10:155dc60fce79 249 debug_uint(axes[0]);
pnysten 10:155dc60fce79 250 debug_str(", ");
pnysten 10:155dc60fce79 251 debug_uint(axes[1]);
pnysten 10:155dc60fce79 252 debug_str(", ");
pnysten 10:155dc60fce79 253 debug_uint(axes[2]);
pnysten 10:155dc60fce79 254 debug_str("\r\n");
pnysten 10:155dc60fce79 255 //pc.printf("LSM6DS0 [gyro/mdps]: %6ld, %6ld, %6ld\r\n", axes[0], axes[1], axes[2]);
pnysten 10:155dc60fce79 256
pnysten 10:155dc60fce79 257 wait(1.5);
pnysten 10:155dc60fce79 258 }
pnysten 10:155dc60fce79 259 }
pnysten 10:155dc60fce79 260
pnysten 4:5e274bf85bf0 261 std::string to_string( int x ) {
pnysten 4:5e274bf85bf0 262 int length = snprintf( NULL, 0, "%d", x );
pnysten 4:5e274bf85bf0 263 assert( length >= 0 );
pnysten 4:5e274bf85bf0 264 char* buf = new char[length + 1];
pnysten 4:5e274bf85bf0 265 snprintf( buf, length + 1, "%d", x );
pnysten 4:5e274bf85bf0 266 std::string str( buf );
pnysten 4:5e274bf85bf0 267 delete[] buf;
pnysten 4:5e274bf85bf0 268 return str;
pnysten 4:5e274bf85bf0 269 }
pnysten 10:155dc60fce79 270
pnysten 4:5e274bf85bf0 271 unsigned char * get_Registration_Payload(long *payload_size){
pnysten 6:540c5d907c90 272
pnysten 4:5e274bf85bf0 273 string registration_Payload ="";
pnysten 6:540c5d907c90 274
pnysten 4:5e274bf85bf0 275 string s="";
pnysten 6:540c5d907c90 276
pnysten 4:5e274bf85bf0 277 s.append(REGISTRATION_OPEN);
pnysten 4:5e274bf85bf0 278 s.append(REGISTRATION_SEPARATOR);
pnysten 4:5e274bf85bf0 279 s.append("3/0/0");
pnysten 4:5e274bf85bf0 280 s.append(REGISTRATION_CLOSE);
pnysten 4:5e274bf85bf0 281 s.append(",");
pnysten 4:5e274bf85bf0 282 s.append(REGISTRATION_OPEN);
pnysten 4:5e274bf85bf0 283 s.append(REGISTRATION_SEPARATOR);
pnysten 4:5e274bf85bf0 284 s.append("3/0/1");
pnysten 4:5e274bf85bf0 285 s.append(REGISTRATION_CLOSE);
pnysten 4:5e274bf85bf0 286 s.append(",");
pnysten 4:5e274bf85bf0 287 s.append(REGISTRATION_OPEN);
pnysten 4:5e274bf85bf0 288 s.append(REGISTRATION_SEPARATOR);
pnysten 4:5e274bf85bf0 289 s.append("3/0/2");
pnysten 4:5e274bf85bf0 290 s.append(REGISTRATION_CLOSE);
pnysten 6:540c5d907c90 291
pnysten 4:5e274bf85bf0 292 registration_Payload.append(s);
pnysten 4:5e274bf85bf0 293
pnysten 4:5e274bf85bf0 294 unsigned char *c = new unsigned char[registration_Payload.size()+1];
pnysten 4:5e274bf85bf0 295 copy(registration_Payload.begin(),registration_Payload.end(),c);
pnysten 4:5e274bf85bf0 296 c[registration_Payload.size()]='\0';
pnysten 4:5e274bf85bf0 297 *payload_size=registration_Payload.size();
pnysten 4:5e274bf85bf0 298
pnysten 4:5e274bf85bf0 299 return c;
pnysten 6:540c5d907c90 300
pnysten 4:5e274bf85bf0 301 }
pnysten 4:5e274bf85bf0 302 uint8_t * get_Token(int * size){
pnysten 4:5e274bf85bf0 303 srand(time(0)+_node_Id);
pnysten 4:5e274bf85bf0 304 long test=0;
pnysten 4:5e274bf85bf0 305 bool exist=false;
pnysten 4:5e274bf85bf0 306
pnysten 4:5e274bf85bf0 307 do{
pnysten 4:5e274bf85bf0 308 test=(rand() % UINT64_MAX);
pnysten 4:5e274bf85bf0 309
pnysten 4:5e274bf85bf0 310 }while (exist==true);
pnysten 4:5e274bf85bf0 311 uint8_t ones = 0xFF;
pnysten 4:5e274bf85bf0 312 *size=1;
pnysten 4:5e274bf85bf0 313 for (int i=0; i<8; ++i) {
pnysten 4:5e274bf85bf0 314 if ( (test>>8*i & ones) =='\0' || i==8) {
pnysten 4:5e274bf85bf0 315 *size=i;
pnysten 4:5e274bf85bf0 316 break;
pnysten 4:5e274bf85bf0 317 }
pnysten 4:5e274bf85bf0 318 }
pnysten 4:5e274bf85bf0 319 uint8_t * token =new uint8_t[*size];
pnysten 4:5e274bf85bf0 320 for (int i=0; i<*size; ++i){
pnysten 4:5e274bf85bf0 321 token[*size-1-i]=test>>8*i & ones;
pnysten 4:5e274bf85bf0 322 }
pnysten 4:5e274bf85bf0 323 return token;
pnysten 4:5e274bf85bf0 324 }
pnysten 6:540c5d907c90 325
pnysten 4:5e274bf85bf0 326 uint16_t get_Message_ID(){
pnysten 4:5e274bf85bf0 327 srand(time(0)+_node_Id);
pnysten 4:5e274bf85bf0 328 int test=0;
pnysten 4:5e274bf85bf0 329 bool exist=false;
pnysten 4:5e274bf85bf0 330 do{
pnysten 4:5e274bf85bf0 331
pnysten 4:5e274bf85bf0 332 exist=false;
pnysten 4:5e274bf85bf0 333 test=(rand() % UINT16_MAX);
pnysten 4:5e274bf85bf0 334
pnysten 4:5e274bf85bf0 335 }while (exist==true);
pnysten 4:5e274bf85bf0 336
pnysten 4:5e274bf85bf0 337
pnysten 4:5e274bf85bf0 338 return (uint16_t) test;
pnysten 4:5e274bf85bf0 339
pnysten 4:5e274bf85bf0 340 }
pnysten 6:540c5d907c90 341
pnysten 4:5e274bf85bf0 342 char * get_Registration_Query(){
pnysten 4:5e274bf85bf0 343
pnysten 4:5e274bf85bf0 344 string buffer;
pnysten 4:5e274bf85bf0 345 buffer.append(REGISTRATION_SEGMENT);
pnysten 4:5e274bf85bf0 346 buffer.append(ENDPOINT_SEGMENT);
pnysten 4:5e274bf85bf0 347 buffer.append(endPoint_Name);
pnysten 4:5e274bf85bf0 348 buffer.append(LIFETIME);
pnysten 4:5e274bf85bf0 349 buffer.append(to_string(lifeTime));
pnysten 4:5e274bf85bf0 350 buffer.append(BINDING);
pnysten 4:5e274bf85bf0 351 buffer.append(binding);
pnysten 4:5e274bf85bf0 352
pnysten 4:5e274bf85bf0 353 char *c = new char[buffer.size()+1];
pnysten 4:5e274bf85bf0 354 copy(buffer.begin(),buffer.end(),c);
pnysten 4:5e274bf85bf0 355 c[buffer.size()]='\0';
pnysten 4:5e274bf85bf0 356 return c;
pnysten 4:5e274bf85bf0 357
pnysten 6:540c5d907c90 358
pnysten 4:5e274bf85bf0 359 }
pnysten 6:540c5d907c90 360
mluis 0:a2929fa6e4f0 361 //////////////////////////////////////////////////
mluis 0:a2929fa6e4f0 362 // CONFIGURATION (FOR APPLICATION CALLBACKS BELOW)
mluis 0:a2929fa6e4f0 363 //////////////////////////////////////////////////
mluis 0:a2929fa6e4f0 364
mluis 0:a2929fa6e4f0 365 // application router ID (LSBF)
pnysten 9:84a69ca4d35a 366 //To be changed when switching from one to another
mluis 1:60184eda0066 367 static const uint8_t AppEui[8] =
mluis 0:a2929fa6e4f0 368 {
mluis 1:60184eda0066 369 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
pnysten 6:540c5d907c90 370 // 0x01, 0x02, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00
mluis 0:a2929fa6e4f0 371 };
mluis 0:a2929fa6e4f0 372
mluis 0:a2929fa6e4f0 373 // unique device ID (LSBF)
pnysten 9:84a69ca4d35a 374 //To be changed when switching from one to another
mluis 0:a2929fa6e4f0 375 static const u1_t DevEui[8] =
mluis 0:a2929fa6e4f0 376 {
pnysten 6:540c5d907c90 377 // 0x00, 0x00, 0x00, 0x00, 0x08, 0x06, 0x02, 0x48
pnysten 6:540c5d907c90 378
pnysten 9:84a69ca4d35a 379 0x30, 0x74, 0x73, 0x65, 0x74, 0x2D, 0x52, 0x4C // 4c522d7465737430 = "LR-test0"
pnysten 6:540c5d907c90 380 // 0x00, 0x80, 0x00, 0x00, 0x00, 0x00, 0x99, 0xF7
pnysten 9:84a69ca4d35a 381 // 0x32, 0x74, 0x73, 0x65, 0x74, 0x2D, 0x52, 0x4C // 4c522d7465737430 = "LR-test2"
pnysten 6:540c5d907c90 382
pnysten 6:540c5d907c90 383
pnysten 4:5e274bf85bf0 384 // 0x01, 0x23, 0x45, 0x67, 0x89, 0xAB, 0xCD, 0xEF
pnysten 4:5e274bf85bf0 385 // 0x00, 0x80, 0x00, 0x00, 0x00, 0x00, 0x099, 0xF7
mluis 0:a2929fa6e4f0 386 };
mluis 0:a2929fa6e4f0 387
mluis 0:a2929fa6e4f0 388 // device-specific AES key (derived from device EUI)
mluis 1:60184eda0066 389 static const uint8_t DevKey[16] =
mluis 0:a2929fa6e4f0 390 {
pnysten 6:540c5d907c90 391 // 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
pnysten 6:540c5d907c90 392 // 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01
mluis 1:60184eda0066 393 0x2B, 0x7E, 0x15, 0x16, 0x28, 0xAE, 0xD2, 0xA6,
mluis 1:60184eda0066 394 0xAB, 0xF7, 0x15, 0x88, 0x09, 0xCF, 0x4F, 0x3C
mluis 0:a2929fa6e4f0 395 };
mluis 0:a2929fa6e4f0 396
mluis 1:60184eda0066 397 #if( OVER_THE_AIR_ACTIVATION == 0 )
mluis 1:60184eda0066 398 // network session key
pnysten 9:84a69ca4d35a 399 //To be changed when switching from one to another
mluis 0:a2929fa6e4f0 400 static uint8_t NwkSKey[] =
mluis 0:a2929fa6e4f0 401 {
mluis 0:a2929fa6e4f0 402 0x2B, 0x7E, 0x15, 0x16, 0x28, 0xAE, 0xD2, 0xA6,
mluis 0:a2929fa6e4f0 403 0xAB, 0xF7, 0x15, 0x88, 0x09, 0xCF, 0x4F, 0x3C
pnysten 6:540c5d907c90 404 // 0xAB, 0xF7, 0x15, 0x88, 0x09, 0xCF, 0x4F, 0x3D
mluis 0:a2929fa6e4f0 405 };
mluis 0:a2929fa6e4f0 406
mluis 1:60184eda0066 407 // application session key
pnysten 9:84a69ca4d35a 408 //To be changed when switching from one to another
mluis 0:a2929fa6e4f0 409 static uint8_t ArtSKey[] =
mluis 0:a2929fa6e4f0 410 {
mluis 0:a2929fa6e4f0 411 0x2B, 0x7E, 0x15, 0x16, 0x28, 0xAE, 0xD2, 0xA6,
mluis 0:a2929fa6e4f0 412 0xAB, 0xF7, 0x15, 0x88, 0x09, 0xCF, 0x4F, 0x3C
pnysten 6:540c5d907c90 413 // 0xAB, 0xF7, 0x15, 0x88, 0x09, 0xCF, 0x4F, 0x3D
mluis 0:a2929fa6e4f0 414 };
mluis 0:a2929fa6e4f0 415
mluis 1:60184eda0066 416 #endif
mluis 1:60184eda0066 417
mluis 0:a2929fa6e4f0 418 // LEDs and Frame jobs
mluis 0:a2929fa6e4f0 419 osjob_t rxLedJob;
mluis 0:a2929fa6e4f0 420 osjob_t txLedJob;
mluis 0:a2929fa6e4f0 421 osjob_t sendFrameJob;
mluis 0:a2929fa6e4f0 422
mluis 1:60184eda0066 423 // LED state
mluis 0:a2929fa6e4f0 424 static bool AppLedStateOn = false;
mluis 0:a2929fa6e4f0 425
mluis 0:a2929fa6e4f0 426 //////////////////////////////////////////////////
mluis 1:60184eda0066 427 // Utility functions
mluis 1:60184eda0066 428 //////////////////////////////////////////////////
mluis 1:60184eda0066 429 /*!
mluis 1:60184eda0066 430 * \brief Computes a random number between min and max
mluis 1:60184eda0066 431 *
mluis 1:60184eda0066 432 * \param [IN] min range minimum value
mluis 1:60184eda0066 433 * \param [IN] max range maximum value
mluis 1:60184eda0066 434 * \retval random random value in range min..max
mluis 1:60184eda0066 435 */
mluis 1:60184eda0066 436 int32_t randr( int32_t min, int32_t max )
mluis 1:60184eda0066 437 {
mluis 1:60184eda0066 438 return ( int32_t )rand( ) % ( max - min + 1 ) + min;
mluis 1:60184eda0066 439 }
mluis 1:60184eda0066 440
mluis 1:60184eda0066 441 //////////////////////////////////////////////////
mluis 0:a2929fa6e4f0 442 // APPLICATION CALLBACKS
mluis 0:a2929fa6e4f0 443 //////////////////////////////////////////////////
mluis 0:a2929fa6e4f0 444
mluis 0:a2929fa6e4f0 445 // provide application router ID (8 bytes, LSBF)
mluis 1:60184eda0066 446 void os_getArtEui( uint8_t *buf )
mluis 0:a2929fa6e4f0 447 {
mluis 0:a2929fa6e4f0 448 memcpy( buf, AppEui, 8 );
mluis 0:a2929fa6e4f0 449 }
mluis 0:a2929fa6e4f0 450
mluis 0:a2929fa6e4f0 451 // provide device ID (8 bytes, LSBF)
mluis 1:60184eda0066 452 void os_getDevEui( uint8_t *buf )
mluis 0:a2929fa6e4f0 453 {
mluis 0:a2929fa6e4f0 454 memcpy( buf, DevEui, 8 );
mluis 0:a2929fa6e4f0 455 }
mluis 0:a2929fa6e4f0 456
mluis 0:a2929fa6e4f0 457 // provide device key (16 bytes)
mluis 1:60184eda0066 458 void os_getDevKey( uint8_t *buf )
mluis 0:a2929fa6e4f0 459 {
mluis 0:a2929fa6e4f0 460 memcpy( buf, DevKey, 16 );
mluis 0:a2929fa6e4f0 461 }
mluis 0:a2929fa6e4f0 462
mluis 0:a2929fa6e4f0 463 //////////////////////////////////////////////////
mluis 0:a2929fa6e4f0 464 // MAIN - INITIALIZATION AND STARTUP
mluis 0:a2929fa6e4f0 465 //////////////////////////////////////////////////
mluis 0:a2929fa6e4f0 466
mluis 0:a2929fa6e4f0 467 static void onRxLed( osjob_t* j )
mluis 0:a2929fa6e4f0 468 {
mluis 1:60184eda0066 469 debug_val("LED2 = ", 0 );
mluis 0:a2929fa6e4f0 470 }
mluis 0:a2929fa6e4f0 471
mluis 0:a2929fa6e4f0 472 static void onTxLed( osjob_t* j )
mluis 0:a2929fa6e4f0 473 {
mluis 1:60184eda0066 474 debug_val("LED1 = ", 0 );
mluis 0:a2929fa6e4f0 475 }
mluis 0:a2929fa6e4f0 476
pnysten 6:540c5d907c90 477 static void prepareTxCoapFrame( void )
pnysten 6:540c5d907c90 478 {
pnysten 6:540c5d907c90 479 // Create Registration PDU :
pnysten 6:540c5d907c90 480
pnysten 6:540c5d907c90 481 CoapPDU *pdu = new CoapPDU();
pnysten 6:540c5d907c90 482
pnysten 6:540c5d907c90 483 pdu->setCode(CoapPDU::COAP_POST);
pnysten 6:540c5d907c90 484 pdu->setType(CoapPDU::COAP_CONFIRMABLE);
pnysten 6:540c5d907c90 485 int size;
pnysten 6:540c5d907c90 486 uint8_t * token = get_Token(&size);
pnysten 6:540c5d907c90 487 pdu->setToken(token,size);
pnysten 6:540c5d907c90 488 pdu->setMessageID(get_Message_ID());
pnysten 6:540c5d907c90 489 pdu->setURI(get_Registration_Query());
pnysten 6:540c5d907c90 490
pnysten 6:540c5d907c90 491 _payload=get_Registration_Payload(&_payload_size);
pnysten 6:540c5d907c90 492 pdu->setPayload(_payload, (int) _payload_size);
pnysten 6:540c5d907c90 493 int PDUlength = pdu->getPDULength();
pnysten 6:540c5d907c90 494
pnysten 6:540c5d907c90 495 // strncpy((char*) LMIC.frame, (const char*)pdu->getPDUPointer(), PDUlength);
pnysten 6:540c5d907c90 496 memcpy(LMIC.frame, pdu->getPDUPointer(), PDUlength * sizeof(uint8_t));
pnysten 6:540c5d907c90 497
pnysten 6:540c5d907c90 498 #if ( LORAWAN_CONFIRMED_MSG_ON == 1 )
pnysten 6:540c5d907c90 499 LMIC.frame[PDUlength] = LMIC.seqnoDn >> 8;
pnysten 6:540c5d907c90 500 LMIC.frame[PDUlength+1] = LMIC.seqnoDn;
pnysten 6:540c5d907c90 501 LMIC.frame[PDUlength+2] = LMIC.rssi >> 8;
pnysten 6:540c5d907c90 502 LMIC.frame[PDUlength+3] = LMIC.rssi;
pnysten 6:540c5d907c90 503 LMIC.frame[PDUlength+4] = LMIC.snr;
pnysten 6:540c5d907c90 504 #endif
pnysten 6:540c5d907c90 505 debug_str("Frame to be sent: ");
pnysten 6:540c5d907c90 506 debug_buf(LMIC.frame, PDUlength + 5);
pnysten 6:540c5d907c90 507
pnysten 6:540c5d907c90 508 LoRaWAN_data_size = PDUlength + 5;
pnysten 6:540c5d907c90 509 }
pnysten 6:540c5d907c90 510
pnysten 8:8d9a49aaa323 511 static void prepareTxLoraFrame( void )
pnysten 8:8d9a49aaa323 512 {
pnysten 8:8d9a49aaa323 513 const char *frame = "LoRa";
pnysten 9:84a69ca4d35a 514 // const char *frame = "Test";
pnysten 8:8d9a49aaa323 515
pnysten 8:8d9a49aaa323 516 strncpy((char*) LMIC.frame, frame, strlen(frame));
pnysten 8:8d9a49aaa323 517
pnysten 8:8d9a49aaa323 518 #if ( LORAWAN_CONFIRMED_MSG_ON == 1 )
pnysten 8:8d9a49aaa323 519 LMIC.frame[strlen(frame)] = LMIC.seqnoDn >> 8;
pnysten 8:8d9a49aaa323 520 LMIC.frame[strlen(frame)+1] = LMIC.seqnoDn;
pnysten 8:8d9a49aaa323 521 LMIC.frame[strlen(frame)+2] = LMIC.rssi >> 8;
pnysten 8:8d9a49aaa323 522 LMIC.frame[strlen(frame)+3] = LMIC.rssi;
pnysten 8:8d9a49aaa323 523 LMIC.frame[strlen(frame)+4] = LMIC.snr;
pnysten 8:8d9a49aaa323 524 #endif
pnysten 8:8d9a49aaa323 525 debug_str("Frame to be sent: ");
pnysten 9:84a69ca4d35a 526 // debug_buf(LMIC.frame, strlen(frame) + 5);
pnysten 9:84a69ca4d35a 527 debug_buf(LMIC.frame, strlen(frame));
pnysten 8:8d9a49aaa323 528
pnysten 9:84a69ca4d35a 529 // LoRaWAN_data_size = strlen(frame) + 5;
pnysten 9:84a69ca4d35a 530 LoRaWAN_data_size = strlen(frame);
pnysten 8:8d9a49aaa323 531 }
pnysten 8:8d9a49aaa323 532
pnysten 10:155dc60fce79 533 static void prepareTxSensorsFrame( void )
pnysten 10:155dc60fce79 534 {
pnysten 10:155dc60fce79 535 std::string frame = "";
pnysten 10:155dc60fce79 536 std::string tmp;
pnysten 10:155dc60fce79 537 debug_str("\r\n");
pnysten 10:155dc60fce79 538
pnysten 10:155dc60fce79 539 temp_sensor1->GetTemperature(&value1);
pnysten 10:155dc60fce79 540 humidity_sensor->GetHumidity(&value2);
pnysten 10:155dc60fce79 541 debug_str("HTS221: [temp] ");
pnysten 10:155dc60fce79 542 debug_str(printDouble(buffer1, value1));
pnysten 10:155dc60fce79 543 tmp = "0,";
pnysten 10:155dc60fce79 544 tmp += buffer1;
pnysten 10:155dc60fce79 545 tmp += ",";
pnysten 10:155dc60fce79 546
pnysten 10:155dc60fce79 547 if ((!temp_sent) && (frame.length() + tmp.length() < 50))
pnysten 10:155dc60fce79 548 {
pnysten 10:155dc60fce79 549 temp_sent = true;
pnysten 10:155dc60fce79 550 frame += tmp;
pnysten 10:155dc60fce79 551 }
pnysten 10:155dc60fce79 552
pnysten 10:155dc60fce79 553 debug_str("Celsius, [hum] ");
pnysten 10:155dc60fce79 554 debug_str(printDouble(buffer2, value2));
pnysten 10:155dc60fce79 555 tmp = "1,";
pnysten 10:155dc60fce79 556 tmp += buffer2;
pnysten 10:155dc60fce79 557 tmp += ",";
pnysten 10:155dc60fce79 558
pnysten 10:155dc60fce79 559 if ((!hum_sent) && (frame.length() + tmp.length() < 50))
pnysten 10:155dc60fce79 560 {
pnysten 10:155dc60fce79 561 hum_sent = true;
pnysten 10:155dc60fce79 562 frame += tmp;
pnysten 10:155dc60fce79 563 }
pnysten 10:155dc60fce79 564
pnysten 10:155dc60fce79 565 debug_str("%\r\n");
pnysten 10:155dc60fce79 566 //pc.printf("HTS221: [temp] %7s°C, [hum] %s%%\r\n", printDouble(buffer1, value1), printDouble(buffer2, value2));
pnysten 10:155dc60fce79 567
pnysten 10:155dc60fce79 568 temp_sensor2->GetFahrenheit(&value1);
pnysten 10:155dc60fce79 569 pressure_sensor->GetPressure(&value2);
pnysten 10:155dc60fce79 570 debug_str("LPS25H: [temp] ");
pnysten 10:155dc60fce79 571 debug_str(printDouble(buffer1, value1));
pnysten 10:155dc60fce79 572 debug_str("Farenheit, [press] ");
pnysten 10:155dc60fce79 573 debug_str(printDouble(buffer2, value2));
pnysten 10:155dc60fce79 574 tmp = "2,";
pnysten 10:155dc60fce79 575 tmp += buffer2;
pnysten 10:155dc60fce79 576 tmp += ",";
pnysten 10:155dc60fce79 577
pnysten 10:155dc60fce79 578 if ((!press_sent) && (frame.length() + tmp.length() < 50))
pnysten 10:155dc60fce79 579 {
pnysten 10:155dc60fce79 580 press_sent = true;
pnysten 10:155dc60fce79 581 frame += tmp;
pnysten 10:155dc60fce79 582 }
pnysten 10:155dc60fce79 583
pnysten 10:155dc60fce79 584 debug_str("mbar\r\n");
pnysten 10:155dc60fce79 585 //pc.printf("LPS25H: [temp] %7s°F, [press] %smbar\r\n", printDouble(buffer1, value1), printDouble(buffer2, value2));
pnysten 10:155dc60fce79 586
pnysten 10:155dc60fce79 587 debug_str("---\r\n");
pnysten 10:155dc60fce79 588
pnysten 10:155dc60fce79 589 magnetometer->Get_M_Axes(axes);
pnysten 10:155dc60fce79 590 debug_str("LIS3MDL [mag/mgauss]: ");
pnysten 10:155dc60fce79 591 debug_str(printInt(buffer1, axes[0]));
pnysten 10:155dc60fce79 592 debug_str(", ");
pnysten 10:155dc60fce79 593 debug_str(printInt(buffer2, axes[1]));
pnysten 10:155dc60fce79 594 debug_str(", ");
pnysten 10:155dc60fce79 595 debug_str(printInt(buffer3, axes[2]));
pnysten 10:155dc60fce79 596 debug_str("\r\n");
pnysten 10:155dc60fce79 597 tmp = "3,";
pnysten 10:155dc60fce79 598 tmp += buffer1;
pnysten 10:155dc60fce79 599 tmp += ";";
pnysten 10:155dc60fce79 600 tmp += buffer2;
pnysten 10:155dc60fce79 601 tmp += ";";
pnysten 10:155dc60fce79 602 tmp += buffer3;
pnysten 10:155dc60fce79 603 tmp += ",";
pnysten 10:155dc60fce79 604
pnysten 10:155dc60fce79 605 if ((!magn_sent) && (frame.length() + tmp.length() < 50))
pnysten 10:155dc60fce79 606 {
pnysten 10:155dc60fce79 607 magn_sent = true;
pnysten 10:155dc60fce79 608 frame += tmp;
pnysten 10:155dc60fce79 609 }
pnysten 10:155dc60fce79 610
pnysten 10:155dc60fce79 611 //pc.printf("LIS3MDL [mag/mgauss]: %6ld, %6ld, %6ld\r\n", axes[0], axes[1], axes[2]);
pnysten 10:155dc60fce79 612
pnysten 10:155dc60fce79 613 accelerometer->Get_X_Axes(axes);
pnysten 10:155dc60fce79 614 debug_str("LSM6DS0 [acc/mg]: ");
pnysten 10:155dc60fce79 615 debug_str(printInt(buffer1, axes[0]));
pnysten 10:155dc60fce79 616 debug_str(", ");
pnysten 10:155dc60fce79 617 debug_str(printInt(buffer2, axes[1]));
pnysten 10:155dc60fce79 618 debug_str(", ");
pnysten 10:155dc60fce79 619 debug_str(printInt(buffer3, axes[2]));
pnysten 10:155dc60fce79 620 tmp = "4,";
pnysten 10:155dc60fce79 621 tmp += buffer1;
pnysten 10:155dc60fce79 622 tmp += ";";
pnysten 10:155dc60fce79 623 tmp += buffer2;
pnysten 10:155dc60fce79 624 tmp += ";";
pnysten 10:155dc60fce79 625 tmp += buffer3;
pnysten 10:155dc60fce79 626 tmp += ",";
pnysten 10:155dc60fce79 627
pnysten 10:155dc60fce79 628 if ((!motion_sent) && (frame.length() + tmp.length() < 50))
pnysten 10:155dc60fce79 629 {
pnysten 10:155dc60fce79 630 motion_sent = true;
pnysten 10:155dc60fce79 631 frame += tmp;
pnysten 10:155dc60fce79 632 }
pnysten 10:155dc60fce79 633
pnysten 10:155dc60fce79 634 debug_str("\r\n");
pnysten 10:155dc60fce79 635 //pc.printf("LSM6DS0 [acc/mg]: %6ld, %6ld, %6ld\r\n", axes[0], axes[1], axes[2]);
pnysten 10:155dc60fce79 636
pnysten 10:155dc60fce79 637 gyroscope->Get_G_Axes(axes);
pnysten 10:155dc60fce79 638 debug_str("LSM6DS0 [gyro/mdps]: ");
pnysten 10:155dc60fce79 639 debug_str(printInt(buffer1, axes[0]));
pnysten 10:155dc60fce79 640 debug_str(", ");
pnysten 10:155dc60fce79 641 debug_str(printInt(buffer2, axes[1]));
pnysten 10:155dc60fce79 642 debug_str(", ");
pnysten 10:155dc60fce79 643 debug_str(printInt(buffer3, axes[2]));
pnysten 10:155dc60fce79 644 tmp = "5,";
pnysten 10:155dc60fce79 645 tmp += buffer1;
pnysten 10:155dc60fce79 646 tmp += ";";
pnysten 10:155dc60fce79 647 tmp += buffer2;
pnysten 10:155dc60fce79 648 tmp += ";";
pnysten 10:155dc60fce79 649 tmp += buffer3;
pnysten 10:155dc60fce79 650
pnysten 10:155dc60fce79 651 if ((!gyro_sent) && (frame.length() + tmp.length() < 50))
pnysten 10:155dc60fce79 652 {
pnysten 10:155dc60fce79 653 gyro_sent = false;
pnysten 10:155dc60fce79 654 temp_sent = false;
pnysten 10:155dc60fce79 655 press_sent = false;
pnysten 10:155dc60fce79 656 motion_sent = false;
pnysten 10:155dc60fce79 657 magn_sent = false;
pnysten 11:59c160a8926d 658 hum_sent = false;
pnysten 10:155dc60fce79 659
pnysten 10:155dc60fce79 660 frame += tmp;
pnysten 10:155dc60fce79 661 }
pnysten 10:155dc60fce79 662
pnysten 10:155dc60fce79 663 debug_str("\r\n Frame: ");
pnysten 10:155dc60fce79 664 debug_str(frame.c_str());
pnysten 10:155dc60fce79 665 debug_str("\r\n");
pnysten 10:155dc60fce79 666 //pc.printf("LSM6DS0 [gyro/mdps]: %6ld, %6ld, %6ld\r\n", axes[0], axes[1], axes[2]);
pnysten 10:155dc60fce79 667
pnysten 10:155dc60fce79 668 strncpy((char*) LMIC.frame, frame.c_str(), strlen(frame.c_str()));
pnysten 10:155dc60fce79 669
pnysten 10:155dc60fce79 670 #if ( LORAWAN_CONFIRMED_MSG_ON == 1 )
pnysten 10:155dc60fce79 671 LMIC.frame[strlen(frame.c_str())] = LMIC.seqnoDn >> 8;
pnysten 10:155dc60fce79 672 LMIC.frame[strlen(frame.c_str())+1] = LMIC.seqnoDn;
pnysten 10:155dc60fce79 673 LMIC.frame[strlen(frame.c_str())+2] = LMIC.rssi >> 8;
pnysten 10:155dc60fce79 674 LMIC.frame[strlen(frame.c_str())+3] = LMIC.rssi;
pnysten 10:155dc60fce79 675 LMIC.frame[strlen(frame.c_str())+4] = LMIC.snr;
pnysten 10:155dc60fce79 676 #endif
pnysten 10:155dc60fce79 677 debug_str("Frame to be sent: ");
pnysten 10:155dc60fce79 678 // debug_buf(LMIC.frame, strlen(frame) + 5);
pnysten 10:155dc60fce79 679 debug_buf(LMIC.frame, strlen(frame.c_str()));
pnysten 10:155dc60fce79 680
pnysten 10:155dc60fce79 681 // LoRaWAN_data_size = strlen(frame) + 5;
pnysten 10:155dc60fce79 682 LoRaWAN_data_size = strlen(frame.c_str());
pnysten 10:155dc60fce79 683 }
pnysten 10:155dc60fce79 684
mluis 0:a2929fa6e4f0 685 static void prepareTxFrame( void )
mluis 0:a2929fa6e4f0 686 {
mluis 0:a2929fa6e4f0 687 LMIC.frame[0] = AppLedStateOn;
mluis 1:60184eda0066 688 #if ( LORAWAN_CONFIRMED_MSG_ON == 1 )
mluis 1:60184eda0066 689 LMIC.frame[1] = LMIC.seqnoDn >> 8;
mluis 1:60184eda0066 690 LMIC.frame[2] = LMIC.seqnoDn;
mluis 1:60184eda0066 691 LMIC.frame[3] = LMIC.rssi >> 8;
mluis 1:60184eda0066 692 LMIC.frame[4] = LMIC.rssi;
mluis 1:60184eda0066 693 LMIC.frame[5] = LMIC.snr;
mluis 1:60184eda0066 694 #endif
pnysten 6:540c5d907c90 695 debug_str("Frame to be sent: ");
pnysten 6:540c5d907c90 696 debug_buf(LMIC.frame, LORAWAN_APP_DATA_SIZE);
pnysten 6:540c5d907c90 697
pnysten 6:540c5d907c90 698 LoRaWAN_data_size = LORAWAN_APP_DATA_SIZE;
mluis 0:a2929fa6e4f0 699 }
mluis 0:a2929fa6e4f0 700
mluis 0:a2929fa6e4f0 701 void processRxFrame( void )
mluis 0:a2929fa6e4f0 702 {
pnysten 8:8d9a49aaa323 703
pnysten 8:8d9a49aaa323 704 char* frameToDisplay = (char*) (LMIC.frame + LMIC.dataBeg);
pnysten 8:8d9a49aaa323 705 frameToDisplay[LMIC.dataLen] = '\0';
pnysten 4:5e274bf85bf0 706
mluis 0:a2929fa6e4f0 707 switch( LMIC.frame[LMIC.dataBeg - 1] ) // Check Rx port number
mluis 0:a2929fa6e4f0 708 {
pnysten 4:5e274bf85bf0 709 case 0:
pnysten 4:5e274bf85bf0 710 // debug_str("Port 0!!!\r\n");
pnysten 4:5e274bf85bf0 711 // debug_val("Data Len: ", LMIC.dataLen);
pnysten 4:5e274bf85bf0 712
mluis 0:a2929fa6e4f0 713 case 1: // The application LED can be controlled on port 1 or 2
pnysten 8:8d9a49aaa323 714 debug_str("Data received on port 1: ");
pnysten 8:8d9a49aaa323 715 debug_str("Data in hexa: ");
pnysten 8:8d9a49aaa323 716 debug_buf( LMIC.frame + LMIC.dataBeg, LMIC.dataLen );
pnysten 8:8d9a49aaa323 717 debug_str("Data in string: ");
pnysten 8:8d9a49aaa323 718
pnysten 8:8d9a49aaa323 719 debug_str( frameToDisplay );
pnysten 8:8d9a49aaa323 720 debug_str("\r\n");
pnysten 8:8d9a49aaa323 721
pnysten 8:8d9a49aaa323 722 break;
mluis 0:a2929fa6e4f0 723 case 2:
pnysten 8:8d9a49aaa323 724 debug_str("Data received on port 2: ");
pnysten 8:8d9a49aaa323 725 debug_str("Data in hexa: ");
pnysten 8:8d9a49aaa323 726 debug_buf( LMIC.frame + LMIC.dataBeg, LMIC.dataLen );
pnysten 8:8d9a49aaa323 727 debug_str("Data in string: ");
pnysten 8:8d9a49aaa323 728
pnysten 8:8d9a49aaa323 729 debug_str( frameToDisplay );
pnysten 8:8d9a49aaa323 730 debug_str("\r\n");
pnysten 8:8d9a49aaa323 731
mluis 0:a2929fa6e4f0 732 if( LMIC.dataLen == 1 )
mluis 0:a2929fa6e4f0 733 {
pnysten 4:5e274bf85bf0 734 debug_str("Data received on port 2: ");
pnysten 4:5e274bf85bf0 735 debug_hex(LMIC.frame[LMIC.dataBeg]);
pnysten 4:5e274bf85bf0 736 debug_str("\r\n");
mluis 0:a2929fa6e4f0 737 AppLedStateOn = LMIC.frame[LMIC.dataBeg] & 0x01;
mluis 1:60184eda0066 738 debug_val( "LED3 = ", AppLedStateOn );
mluis 0:a2929fa6e4f0 739 }
mluis 0:a2929fa6e4f0 740 break;
mluis 0:a2929fa6e4f0 741 default:
mluis 0:a2929fa6e4f0 742 break;
mluis 0:a2929fa6e4f0 743 }
mluis 0:a2929fa6e4f0 744 }
mluis 0:a2929fa6e4f0 745
mluis 0:a2929fa6e4f0 746 static void onSendFrame( osjob_t* j )
mluis 0:a2929fa6e4f0 747 {
pnysten 6:540c5d907c90 748 //prepareTxFrame( );
pnysten 8:8d9a49aaa323 749 //prepareTxCoapFrame();
pnysten 10:155dc60fce79 750 prepareTxSensorsFrame();
pnysten 10:155dc60fce79 751 //prepareTxLoraFrame();
pnysten 4:5e274bf85bf0 752
pnysten 6:540c5d907c90 753 LMIC_setTxData2( LORAWAN_APP_PORT, LMIC.frame, LoRaWAN_data_size, LORAWAN_CONFIRMED_MSG_ON );
mluis 1:60184eda0066 754
mluis 1:60184eda0066 755 // Blink Tx LED
mluis 1:60184eda0066 756 debug_val( "LED1 = ", 1 );
mluis 1:60184eda0066 757 os_setTimedCallback( &txLedJob, os_getTime( ) + ms2osticks( 25 ), onTxLed );
mluis 0:a2929fa6e4f0 758 }
mluis 0:a2929fa6e4f0 759
mluis 1:60184eda0066 760 // Initialization job
mluis 1:60184eda0066 761 static void onInit( osjob_t* j )
mluis 1:60184eda0066 762 {
pnysten 10:155dc60fce79 763 debug_str("--- Starting new run ---\r\n");
pnysten 10:155dc60fce79 764
pnysten 10:155dc60fce79 765 humidity_sensor->ReadID(&id);
pnysten 10:155dc60fce79 766 debug_str("HTS221 humidity & temperature = ");
pnysten 10:155dc60fce79 767 debug_uint(id);
pnysten 10:155dc60fce79 768 debug_str("\r\n");
pnysten 10:155dc60fce79 769 pressure_sensor->ReadID(&id);
pnysten 10:155dc60fce79 770 debug_str("LPS25H pressure & temperature = ");
pnysten 10:155dc60fce79 771 debug_uint(id);
pnysten 10:155dc60fce79 772 debug_str("\r\n");
pnysten 10:155dc60fce79 773 magnetometer->ReadID(&id);
pnysten 10:155dc60fce79 774 debug_str("LIS3MDL magnetometer = ");
pnysten 10:155dc60fce79 775 debug_uint(id);
pnysten 10:155dc60fce79 776 debug_str("\r\n");
pnysten 10:155dc60fce79 777 gyroscope->ReadID(&id);
pnysten 10:155dc60fce79 778 debug_str("LSM6DS0 accelerometer & gyroscope = ");
pnysten 10:155dc60fce79 779 debug_uint(id);
pnysten 10:155dc60fce79 780 debug_str("\r\n");
pnysten 10:155dc60fce79 781
mluis 1:60184eda0066 782 // reset MAC state
mluis 1:60184eda0066 783 LMIC_reset( );
mluis 1:60184eda0066 784 LMIC_setAdrMode( LORAWAN_ADR_ON );
mluis 1:60184eda0066 785 LMIC_setDrTxpow( DR_SF12, 14 );
mluis 1:60184eda0066 786
mluis 1:60184eda0066 787 // start joining
mluis 1:60184eda0066 788 #if( OVER_THE_AIR_ACTIVATION != 0 )
mluis 1:60184eda0066 789 LMIC_startJoining( );
mluis 1:60184eda0066 790 #else
mluis 1:60184eda0066 791 LMIC_setSession( LORAWAN_NET_ID, LORAWAN_DEV_ADDR, NwkSKey, ArtSKey );
mluis 1:60184eda0066 792 onSendFrame( NULL );
mluis 1:60184eda0066 793 #endif
mluis 1:60184eda0066 794 // init done - onEvent( ) callback will be invoked...
mluis 1:60184eda0066 795 }
mluis 1:60184eda0066 796
mluis 1:60184eda0066 797 int main( void )
mluis 0:a2929fa6e4f0 798 {
pnysten 4:5e274bf85bf0 799 debug_init();
mluis 0:a2929fa6e4f0 800 osjob_t initjob;
pnysten 6:540c5d907c90 801
mluis 0:a2929fa6e4f0 802 // initialize runtime env
mluis 0:a2929fa6e4f0 803 os_init( );
mluis 0:a2929fa6e4f0 804 // setup initial job
mluis 0:a2929fa6e4f0 805 os_setCallback( &initjob, onInit );
mluis 0:a2929fa6e4f0 806 // execute scheduled jobs and events
pnysten 10:155dc60fce79 807
pnysten 10:155dc60fce79 808 //static Thread exec_thread(exec_call_thread);
pnysten 10:155dc60fce79 809
mluis 0:a2929fa6e4f0 810 os_runloop( );
mluis 0:a2929fa6e4f0 811 // (not reached)
mluis 0:a2929fa6e4f0 812 }
mluis 0:a2929fa6e4f0 813
mluis 0:a2929fa6e4f0 814 //////////////////////////////////////////////////
mluis 0:a2929fa6e4f0 815 // LMIC EVENT CALLBACK
mluis 0:a2929fa6e4f0 816 //////////////////////////////////////////////////
mluis 0:a2929fa6e4f0 817 void onEvent( ev_t ev )
mluis 0:a2929fa6e4f0 818 {
mluis 0:a2929fa6e4f0 819 bool txOn = false;
mluis 1:60184eda0066 820 debug_event( ev );
mluis 0:a2929fa6e4f0 821
mluis 0:a2929fa6e4f0 822 switch( ev )
mluis 0:a2929fa6e4f0 823 {
mluis 0:a2929fa6e4f0 824 // network joined, session established
mluis 0:a2929fa6e4f0 825 case EV_JOINED:
mluis 1:60184eda0066 826 debug_val( "Net ID = ", LMIC.netid );
mluis 0:a2929fa6e4f0 827 txOn = true;
mluis 0:a2929fa6e4f0 828 break;
mluis 0:a2929fa6e4f0 829 // scheduled data sent (optionally data received)
mluis 0:a2929fa6e4f0 830 case EV_TXCOMPLETE:
mluis 1:60184eda0066 831 debug_val( "Datarate = ", LMIC.datarate );
mluis 0:a2929fa6e4f0 832 // Check if we have a downlink on either Rx1 or Rx2 windows
mluis 1:60184eda0066 833 if( ( LMIC.txrxFlags & ( TXRX_DNW1 | TXRX_DNW2 ) ) != 0 )
mluis 0:a2929fa6e4f0 834 {
mluis 1:60184eda0066 835 debug_val( "LED2 = ", 1 );
mluis 1:60184eda0066 836 os_setTimedCallback( &rxLedJob, os_getTime( ) + ms2osticks( 25 ), onRxLed );
mluis 0:a2929fa6e4f0 837
mluis 1:60184eda0066 838 if( LMIC.dataLen != 0 )
mluis 0:a2929fa6e4f0 839 { // data received in rx slot after tx
pnysten 4:5e274bf85bf0 840 //debug_buf( LMIC.frame + LMIC.dataBeg, LMIC.dataLen );
mluis 0:a2929fa6e4f0 841 processRxFrame( );
mluis 0:a2929fa6e4f0 842 }
mluis 0:a2929fa6e4f0 843 }
mluis 0:a2929fa6e4f0 844 txOn = true;
mluis 0:a2929fa6e4f0 845 break;
mluis 0:a2929fa6e4f0 846 default:
mluis 0:a2929fa6e4f0 847 break;
mluis 0:a2929fa6e4f0 848 }
mluis 0:a2929fa6e4f0 849 if( txOn == true )
mluis 0:a2929fa6e4f0 850 {
mluis 1:60184eda0066 851 //Sends frame every APP_TX_DUTYCYCLE +/- APP_TX_DUTYCYCLE_RND random time (if not duty cycle limited)
mluis 1:60184eda0066 852 os_setTimedCallback( &sendFrameJob,
mluis 1:60184eda0066 853 os_getTime( ) + ms2osticks( APP_TX_DUTYCYCLE + randr( -APP_TX_DUTYCYCLE_RND, APP_TX_DUTYCYCLE_RND ) ),
mluis 1:60184eda0066 854 onSendFrame );
mluis 0:a2929fa6e4f0 855
mluis 1:60184eda0066 856 ////Sends frame as soon as possible (duty cylce limitations)
mluis 1:60184eda0066 857 //onSendFrame( NULL );
mluis 0:a2929fa6e4f0 858 }
mluis 0:a2929fa6e4f0 859 }
pnysten 10:155dc60fce79 860
pnysten 10:155dc60fce79 861