Mbed OS and Pelion Device Management example over WIFI for DISCO_L475VG_IOT01 board

Dependencies:   X_NUCLEO_COMMON ST_INTERFACES

DEPRECATED

This example application is not maintained and not recommended. It uses an old version of Mbed OS, Pelion DM and Arm toolchain. It doesn't work with Mbed Studio.

Please use: https://os.mbed.com/teams/mbed-os-examples/code/mbed-os-example-pelion/

This example is known to work on the following platforms:

DISCO_L475E_IOT01A

Follow the Quick-Start instructions: https://cloud.mbed.com/quick-start

Example functionality

This example showcases the following device functionality:

  • Read onboard temperature and humidity sensors, and report them as Pelion LWM2M resources (see image below).
  • On user button click, increment Pelion LWM2M button resource.
  • Allow the user to change the state of the board LED from Pelion LWM2M led_state resource and PUT request.
  • Uses all onboard sensors and reports them as Pelion LWM2M resources.

/media/uploads/screamer/pelion_st_humidity_reading.png?v=2

Use this example with Mbed CLI

1. Import the application into your desktop:

mbed import https://os.mbed.com/teams/ST/code/pelion-example-disco-iot01

cd pelion-example-disco-iot01

2. Install the CLOUD_SDK_API_KEY

mbed config -G CLOUD_SDK_API_KEY <PELION_DM_API_KEY>

For instructions on how to generate your API key, please see the documentation.

3. Initialize firmware credentials (done once per repository). You can use the following command:

mbed dm init -d "<your company name in Pelion DM>" --model-name "<product model identifier>" -q --force

If above command do not work for your Mbed CLI, please consider upgrading Mbed CLI to version 1.8.x or above.

4. Compile and program:

mbed compile -t <toolchain> -m DISCO_L475VG_IOT01A

(supported toolchains : GCC_ARM / ARM / IAR)

5. You can connect on a virtual terminal/COM port to the platform using:

mbed sterm -b 115200

This should give you an output similar to:

[BOOT] Mbed Bootloader
[BOOT] ARM: 00000000000000000000
[BOOT] OEM: 00000000000000000000
[BOOT] Layout: 0 80096F4
[BOOT] Active firmware integrity check:
[BOOT] SHA256: 0660E360D432225D5251461998FD8617B017098C5F1F90D5FB607BF8C27ED530
[BOOT] Version: 1553615309
[BOOT] Slot 0 is empty
[BOOT] Active firmware up-to-date
[BOOT] Application's start address: 0x8010400
[BOOT] Application's jump address: 0x8011041
[BOOT] Application's stack address: 0x20018000
[BOOT] Forwarding to application...

Starting Simple Pelion Device Management Client example
You can hold the user button during boot to format the storage and change the device identity.

Sensors configuration:
Invalid new address!
HTS221  humidity & temperature    = 0xBC
LPS22HB pressure & temperature    = 0xB1
LIS3MDL magnetometer              = 0x3D
LSM6DSL accelerometer & gyroscope = 0x6A

Connecting to the network using Wifi...
Connected to the network successfully. IP address: 192.168.1.3
Initializing Pelion Device Management Client...
Initialized Pelion Client. Registering...
Registered to Pelion Device Management. Endpoint Name: 0169********************001002d5

ADC temp:     23.0037 C,  vref:      0.3661 V
HTS221 temp:   28.700 C,  humidity:   31.90 %
LPS22HB temp:  29.600 C,  pressure: 1032.01 mbar
LIS3MDL mag:    0.217 x,  -0.284 y,  -0.053 z [gauss]
LSM6DSL acc:    0.005 x,  -0.014 y,   1.029 z [g]
LSM6DSL gyro:   0.910 x,  -0.910 y,   1.120 z [dps]
VL53L0X dist:    1855 mm
Committer:
chris
Date:
Fri Mar 13 13:15:16 2020 +0000
Revision:
35:061bc344e4ec
Parent:
34:a5724eeaaf9d
Child:
36:aaf44d2a6c33
First Rev

Who changed what in which revision?

UserRevisionLine numberNew contents of line
adustm 1:e86b1cffc402 1 // ----------------------------------------------------------------------------
adustm 4:cf7342047b4d 2 // Copyright 2016-2018 ARM Ltd.
adustm 1:e86b1cffc402 3 //
adustm 1:e86b1cffc402 4 // SPDX-License-Identifier: Apache-2.0
adustm 1:e86b1cffc402 5 //
adustm 1:e86b1cffc402 6 // Licensed under the Apache License, Version 2.0 (the "License");
adustm 1:e86b1cffc402 7 // you may not use this file except in compliance with the License.
adustm 1:e86b1cffc402 8 // You may obtain a copy of the License at
adustm 1:e86b1cffc402 9 //
adustm 1:e86b1cffc402 10 // http://www.apache.org/licenses/LICENSE-2.0
adustm 1:e86b1cffc402 11 //
adustm 1:e86b1cffc402 12 // Unless required by applicable law or agreed to in writing, software
adustm 1:e86b1cffc402 13 // distributed under the License is distributed on an "AS IS" BASIS,
adustm 1:e86b1cffc402 14 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
adustm 1:e86b1cffc402 15 // See the License for the specific language governing permissions and
adustm 1:e86b1cffc402 16 // limitations under the License.
adustm 1:e86b1cffc402 17 // ----------------------------------------------------------------------------
MarceloSalazar 9:265744785d33 18 #ifndef MBED_TEST_MODE
screamer 28:0e774865873d 19
adustm 1:e86b1cffc402 20 #include "mbed.h"
adustm 1:e86b1cffc402 21 #include "simple-mbed-cloud-client.h"
screamer 10:b27c962b3c3f 22 #include "LittleFileSystem.h"
screamer 33:cfd9430e7d1e 23
screamer 33:cfd9430e7d1e 24 // Default network interface object. Don't forget to change the WiFi SSID/password in mbed_app.json if you're using WiFi.
chris 35:061bc344e4ec 25 // NetworkInterface *net;
chris 35:061bc344e4ec 26 static WiFiInterface *net = NULL;
chris 35:061bc344e4ec 27
chris 35:061bc344e4ec 28 //#define WIFI_SSID "Chris iPhone 6P"
chris 35:061bc344e4ec 29 //#define WIFI_PASSWORD "mbed1234"
chris 35:061bc344e4ec 30
chris 35:061bc344e4ec 31 // #define WIFI_SSID "mbed_pe"
chris 35:061bc344e4ec 32 // #define WIFI_PASSWORD "ilovembed"
chris 35:061bc344e4ec 33
chris 35:061bc344e4ec 34 //#define WIFI_SSID "DJ iPhone"
chris 35:061bc344e4ec 35 //#define WIFI_PASSWORD "zjvcj8o4d5qs9"
chris 35:061bc344e4ec 36
chris 35:061bc344e4ec 37 //#define WIFI_SSID "vodafoneC17B87"
chris 35:061bc344e4ec 38 //#define WIFI_PASSWORD "hTesxMG6H6Ym7xdr"
chris 35:061bc344e4ec 39
chris 35:061bc344e4ec 40 #define WIFI_SSID "madhouse"
chris 35:061bc344e4ec 41 #define WIFI_PASSWORD "d86marmj"
screamer 33:cfd9430e7d1e 42
screamer 33:cfd9430e7d1e 43 // Default block device available on the target board
screamer 33:cfd9430e7d1e 44 BlockDevice* bd = BlockDevice::get_default_instance();
screamer 33:cfd9430e7d1e 45 SlicingBlockDevice sd(bd, 0, 2*1024*1024);
screamer 33:cfd9430e7d1e 46
screamer 33:cfd9430e7d1e 47 #if COMPONENT_SD || COMPONENT_NUSD
screamer 33:cfd9430e7d1e 48 // Use FATFileSystem for SD card type blockdevices
screamer 33:cfd9430e7d1e 49 FATFileSystem fs("fs");
screamer 33:cfd9430e7d1e 50 #else
screamer 33:cfd9430e7d1e 51 // Use LittleFileSystem for non-SD block devices to enable wear leveling and other functions
screamer 33:cfd9430e7d1e 52 LittleFileSystem fs("fs");
screamer 33:cfd9430e7d1e 53 #endif
screamer 33:cfd9430e7d1e 54
screamer 33:cfd9430e7d1e 55 // Default User button for GET example and for resetting the storage
screamer 33:cfd9430e7d1e 56 InterruptIn button(BUTTON1);
screamer 33:cfd9430e7d1e 57 // Default LED to use for PUT/POST example
screamer 33:cfd9430e7d1e 58 DigitalOut led(LED1, 1);
screamer 33:cfd9430e7d1e 59
screamer 33:cfd9430e7d1e 60 // How often to fetch sensor data (in seconds)
screamer 33:cfd9430e7d1e 61 #define SENSORS_POLL_INTERVAL 3.0
screamer 33:cfd9430e7d1e 62
screamer 33:cfd9430e7d1e 63 // Send all sensor data or just limited (useful for when running out of memory)
screamer 33:cfd9430e7d1e 64 #define SEND_ALL_SENSORS
screamer 33:cfd9430e7d1e 65
screamer 33:cfd9430e7d1e 66 // Sensors related includes and initialization
screamer 10:b27c962b3c3f 67 #include "HTS221Sensor.h"
screamer 10:b27c962b3c3f 68 #include "LPS22HBSensor.h"
screamer 10:b27c962b3c3f 69 #include "LSM6DSLSensor.h"
screamer 10:b27c962b3c3f 70 #include "lis3mdl_class.h"
screamer 28:0e774865873d 71 #include "VL53L0X.h"
screamer 10:b27c962b3c3f 72
screamer 10:b27c962b3c3f 73 static DevI2C devI2c(PB_11,PB_10);
screamer 12:1f1a50e973db 74 static HTS221Sensor sen_hum_temp(&devI2c);
screamer 12:1f1a50e973db 75 static LPS22HBSensor sen_press_temp(&devI2c);
screamer 12:1f1a50e973db 76 static LSM6DSLSensor sen_acc_gyro(&devI2c,LSM6DSL_ACC_GYRO_I2C_ADDRESS_LOW,PD_11); // low address
screamer 12:1f1a50e973db 77 static LIS3MDL sen_mag(&devI2c);
screamer 28:0e774865873d 78 static DigitalOut shutdown_pin(PC_6);
screamer 28:0e774865873d 79 static VL53L0X sen_distance(&devI2c, &shutdown_pin, PC_7);
screamer 33:cfd9430e7d1e 80 // Temperature reading from microcontroller
screamer 33:cfd9430e7d1e 81 AnalogIn adc_temp(ADC_TEMP);
screamer 33:cfd9430e7d1e 82 // Voltage reference reading from microcontroller
screamer 33:cfd9430e7d1e 83 AnalogIn adc_vref(ADC_VREF);
screamer 11:8df4529f060d 84
MarceloSalazar 9:265744785d33 85 // Declaring pointers for access to Pelion Client resources outside of main()
screamer 12:1f1a50e973db 86 MbedCloudClientResource *res_button;
screamer 12:1f1a50e973db 87 MbedCloudClientResource *res_led;
adustm 1:e86b1cffc402 88
screamer 33:cfd9430e7d1e 89 // Additional resources for sensor readings
screamer 28:0e774865873d 90 #ifdef SEND_ALL_SENSORS
screamer 12:1f1a50e973db 91 MbedCloudClientResource *res_humidity;
screamer 12:1f1a50e973db 92 MbedCloudClientResource *res_temperature;
screamer 12:1f1a50e973db 93 MbedCloudClientResource *res_pressure;
screamer 12:1f1a50e973db 94 MbedCloudClientResource *res_temperature2;
screamer 28:0e774865873d 95 MbedCloudClientResource *res_magnometer_x;
screamer 28:0e774865873d 96 MbedCloudClientResource *res_magnometer_y;
screamer 28:0e774865873d 97 MbedCloudClientResource *res_magnometer_z;
screamer 28:0e774865873d 98 MbedCloudClientResource *res_accelerometer_x;
screamer 28:0e774865873d 99 MbedCloudClientResource *res_accelerometer_y;
screamer 28:0e774865873d 100 MbedCloudClientResource *res_accelerometer_z;
screamer 13:42b49a0caade 101 MbedCloudClientResource *res_gyroscope_x;
screamer 13:42b49a0caade 102 MbedCloudClientResource *res_gyroscope_y;
screamer 13:42b49a0caade 103 MbedCloudClientResource *res_gyroscope_z;
screamer 12:1f1a50e973db 104 MbedCloudClientResource *res_distance;
screamer 28:0e774865873d 105 MbedCloudClientResource *res_adc_temp;
screamer 28:0e774865873d 106 MbedCloudClientResource *res_adc_voltage;
screamer 13:42b49a0caade 107 #endif /* SEND_ALL_SENSORS */
adustm 1:e86b1cffc402 108
screamer 33:cfd9430e7d1e 109 // An event queue is a very useful structure to debounce information between contexts (e.g. ISR and normal threads)
screamer 33:cfd9430e7d1e 110 // This is great because things such as network operations are illegal in ISR, so updating a resource in a button's fall() function is not allowed
screamer 33:cfd9430e7d1e 111 EventQueue eventQueue;
screamer 33:cfd9430e7d1e 112
screamer 10:b27c962b3c3f 113 // When the device is registered, this variable will be used to access various useful information, like device ID etc.
screamer 10:b27c962b3c3f 114 static const ConnectorClientEndpointInfo* endpointInfo;
adustm 1:e86b1cffc402 115
screamer 10:b27c962b3c3f 116 /**
adustm 4:cf7342047b4d 117 * PUT handler
adustm 4:cf7342047b4d 118 * @param resource The resource that triggered the callback
adustm 4:cf7342047b4d 119 * @param newValue Updated value for the resource
adustm 4:cf7342047b4d 120 */
screamer 32:2871fbeb627d 121 void put_callback(MbedCloudClientResource *resource, m2m::String newValue) {
screamer 29:6ff737b67e7d 122 printf("*** PUT received, new value: %s \n", newValue.c_str());
screamer 11:8df4529f060d 123 led = atoi(newValue.c_str());
adustm 1:e86b1cffc402 124 }
adustm 1:e86b1cffc402 125
adustm 4:cf7342047b4d 126 /**
adustm 4:cf7342047b4d 127 * POST handler
adustm 4:cf7342047b4d 128 * @param resource The resource that triggered the callback
adustm 4:cf7342047b4d 129 * @param buffer If a body was passed to the POST function, this contains the data.
adustm 4:cf7342047b4d 130 * Note that the buffer is deallocated after leaving this function, so copy it if you need it longer.
adustm 4:cf7342047b4d 131 * @param size Size of the body
adustm 4:cf7342047b4d 132 */
screamer 32:2871fbeb627d 133 void post_callback(MbedCloudClientResource *resource, const uint8_t *buffer, uint16_t size) {
screamer 32:2871fbeb627d 134 printf("*** POST received (length %u). Payload: ", size);
screamer 32:2871fbeb627d 135 for (size_t ix = 0; ix < size; ix++) {
screamer 32:2871fbeb627d 136 printf("%02x ", buffer[ix]);
screamer 32:2871fbeb627d 137 }
screamer 32:2871fbeb627d 138 printf("\n");
screamer 11:8df4529f060d 139 }
adustm 1:e86b1cffc402 140
screamer 11:8df4529f060d 141 /**
screamer 13:42b49a0caade 142 * Button function triggered by the physical button press.
screamer 11:8df4529f060d 143 */
screamer 11:8df4529f060d 144 void button_press() {
screamer 12:1f1a50e973db 145 int v = res_button->get_value_int() + 1;
screamer 12:1f1a50e973db 146 res_button->set_value(v);
screamer 29:6ff737b67e7d 147 printf("*** Button clicked %d times \n", v);
adustm 1:e86b1cffc402 148 }
adustm 1:e86b1cffc402 149
adustm 4:cf7342047b4d 150 /**
adustm 4:cf7342047b4d 151 * Notification callback handler
adustm 4:cf7342047b4d 152 * @param resource The resource that triggered the callback
adustm 4:cf7342047b4d 153 * @param status The delivery status of the notification
adustm 4:cf7342047b4d 154 */
adustm 4:cf7342047b4d 155 void button_callback(MbedCloudClientResource *resource, const NoticationDeliveryStatus status) {
screamer 29:6ff737b67e7d 156 printf("*** Button notification, status %s (%d) \n", MbedCloudClientResource::delivery_status_to_string(status), status);
adustm 4:cf7342047b4d 157 }
adustm 1:e86b1cffc402 158
adustm 4:cf7342047b4d 159 /**
adustm 4:cf7342047b4d 160 * Registration callback handler
adustm 4:cf7342047b4d 161 * @param endpoint Information about the registered endpoint such as the name (so you can find it back in portal)
adustm 4:cf7342047b4d 162 */
adustm 4:cf7342047b4d 163 void registered(const ConnectorClientEndpointInfo *endpoint) {
screamer 17:fc98adcf835a 164 printf("Registered to Pelion Device Management. Endpoint Name: %s\n", endpoint->internal_endpoint_name.c_str());
screamer 10:b27c962b3c3f 165 endpointInfo = endpoint;
adustm 4:cf7342047b4d 166 }
adustm 1:e86b1cffc402 167
screamer 10:b27c962b3c3f 168 /**
screamer 10:b27c962b3c3f 169 * Initialize sensors
screamer 10:b27c962b3c3f 170 */
screamer 10:b27c962b3c3f 171 void sensors_init() {
screamer 29:6ff737b67e7d 172 uint8_t id1, id2, id3, id4;
screamer 10:b27c962b3c3f 173
screamer 29:6ff737b67e7d 174 printf ("\nSensors configuration:\n");
screamer 10:b27c962b3c3f 175 // Initialize sensors
screamer 12:1f1a50e973db 176 sen_hum_temp.init(NULL);
screamer 12:1f1a50e973db 177 sen_press_temp.init(NULL);
screamer 12:1f1a50e973db 178 sen_acc_gyro.init(NULL);
screamer 12:1f1a50e973db 179 sen_mag.init(NULL);
screamer 28:0e774865873d 180 sen_distance.init_sensor(VL53L0X_DEFAULT_ADDRESS);
screamer 10:b27c962b3c3f 181
screamer 10:b27c962b3c3f 182 /// Call sensors enable routines
screamer 12:1f1a50e973db 183 sen_hum_temp.enable();
screamer 12:1f1a50e973db 184 sen_press_temp.enable();
screamer 12:1f1a50e973db 185 sen_acc_gyro.enable_x();
screamer 12:1f1a50e973db 186 sen_acc_gyro.enable_g();
screamer 10:b27c962b3c3f 187
screamer 29:6ff737b67e7d 188 sen_hum_temp.read_id(&id1);
screamer 29:6ff737b67e7d 189 sen_press_temp.read_id(&id2);
screamer 29:6ff737b67e7d 190 sen_mag.read_id(&id3);
screamer 29:6ff737b67e7d 191 sen_acc_gyro.read_id(&id4);
screamer 10:b27c962b3c3f 192
screamer 29:6ff737b67e7d 193 printf("HTS221 humidity & temperature = 0x%X\n", id1);
screamer 29:6ff737b67e7d 194 printf("LPS22HB pressure & temperature = 0x%X\n", id2);
screamer 29:6ff737b67e7d 195 printf("LIS3MDL magnetometer = 0x%X\n", id3);
screamer 29:6ff737b67e7d 196 printf("LSM6DSL accelerometer & gyroscope = 0x%X\n", id4);
screamer 10:b27c962b3c3f 197
screamer 17:fc98adcf835a 198 printf("\n"); ;
screamer 10:b27c962b3c3f 199 }
screamer 10:b27c962b3c3f 200
screamer 10:b27c962b3c3f 201 /**
screamer 10:b27c962b3c3f 202 * Update sensors and report their values.
screamer 10:b27c962b3c3f 203 * This function is called periodically.
screamer 10:b27c962b3c3f 204 */
screamer 10:b27c962b3c3f 205 void sensors_update() {
screamer 32:2871fbeb627d 206 float temp1_value, temp2_value, temp3_value, humid_value, pressure_value, volt_value = 0.0;
screamer 28:0e774865873d 207 int32_t m_axes[3], a_axes[3], g_axes[3];
screamer 32:2871fbeb627d 208 uint32_t distance_value, distance_reading;
screamer 10:b27c962b3c3f 209
screamer 32:2871fbeb627d 210 sen_hum_temp.get_humidity(&humid_value);
screamer 32:2871fbeb627d 211 sen_hum_temp.get_temperature(&temp1_value);
screamer 32:2871fbeb627d 212 sen_press_temp.get_pressure(&pressure_value);
screamer 32:2871fbeb627d 213 sen_press_temp.get_temperature(&temp2_value);
screamer 28:0e774865873d 214 sen_mag.get_m_axes(m_axes);
screamer 28:0e774865873d 215 sen_acc_gyro.get_x_axes(a_axes);
screamer 28:0e774865873d 216 sen_acc_gyro.get_g_axes(g_axes);
screamer 32:2871fbeb627d 217 distance_reading = sen_distance.get_distance(&distance_value);
screamer 32:2871fbeb627d 218 temp3_value = adc_temp.read()*100;
screamer 32:2871fbeb627d 219 volt_value = adc_vref.read();
screamer 32:2871fbeb627d 220
screamer 32:2871fbeb627d 221 float mag_x = (double)m_axes[0] / 1000.0, mag_y = (double)m_axes[1] / 1000.0, mag_z = (double)m_axes[2] / 1000.0;
screamer 32:2871fbeb627d 222 float acc_x = (double)a_axes[0] / 1000.0, acc_y = (double)a_axes[1] / 1000.0, acc_z = (double)a_axes[2] / 1000.0;
screamer 32:2871fbeb627d 223 float gyro_x = (double)g_axes[0] / 1000.0, gyro_y = (double)g_axes[1] / 1000.0, gyro_z = (double)g_axes[2] / 1000.0;
screamer 28:0e774865873d 224
screamer 32:2871fbeb627d 225 printf(" \n");
screamer 32:2871fbeb627d 226 printf("ADC temp: %5.4f C, vref: %5.4f V \n", temp3_value, volt_value);
screamer 32:2871fbeb627d 227 printf("HTS221 temp: %7.3f C, humidity: %7.2f %% \n", temp1_value, humid_value);
screamer 32:2871fbeb627d 228 printf("LPS22HB temp: %7.3f C, pressure: %7.2f mbar \n", temp2_value, pressure_value);
screamer 32:2871fbeb627d 229 printf("LIS3MDL mag: %7.3f x, %7.3f y, %7.3f z [gauss] \n", mag_x, mag_y, mag_z);
screamer 32:2871fbeb627d 230 printf("LSM6DSL acc: %7.3f x, %7.3f y, %7.3f z [g] \n", acc_x, acc_y, acc_z);
screamer 32:2871fbeb627d 231 printf("LSM6DSL gyro: %7.3f x, %7.3f y, %7.3f z [dps] \n", gyro_x, gyro_y, gyro_z);
screamer 32:2871fbeb627d 232 if (distance_reading == VL53L0X_ERROR_NONE) {
screamer 32:2871fbeb627d 233 printf("VL53L0X dist: %7ld mm\n", distance_value);
screamer 28:0e774865873d 234 } else {
screamer 28:0e774865873d 235 printf("VL53L0X dist: -- \n");
screamer 32:2871fbeb627d 236 distance_value = 999;
screamer 10:b27c962b3c3f 237 }
screamer 10:b27c962b3c3f 238
screamer 28:0e774865873d 239 printf("\r\033[8A");
screamer 28:0e774865873d 240
screamer 13:42b49a0caade 241 if (endpointInfo) {
screamer 33:cfd9430e7d1e 242 #ifdef SEND_ALL_SENSORS
screamer 32:2871fbeb627d 243 res_humidity->set_value(humid_value);
screamer 32:2871fbeb627d 244 res_temperature->set_value(temp1_value);
screamer 32:2871fbeb627d 245 res_pressure->set_value(pressure_value);
screamer 32:2871fbeb627d 246 res_temperature2->set_value(temp2_value);
screamer 32:2871fbeb627d 247 res_magnometer_x->set_value(mag_x);
screamer 32:2871fbeb627d 248 res_magnometer_y->set_value(mag_y);
screamer 32:2871fbeb627d 249 res_magnometer_z->set_value(mag_z);
screamer 32:2871fbeb627d 250 res_accelerometer_x->set_value(acc_x);
screamer 32:2871fbeb627d 251 res_accelerometer_y->set_value(acc_y);
screamer 32:2871fbeb627d 252 res_accelerometer_z->set_value(acc_z);
screamer 32:2871fbeb627d 253 res_gyroscope_x->set_value(gyro_x);
screamer 32:2871fbeb627d 254 res_gyroscope_y->set_value(gyro_y);
screamer 32:2871fbeb627d 255 res_gyroscope_z->set_value(gyro_z);
screamer 32:2871fbeb627d 256 res_distance->set_value((int)distance_value);
screamer 32:2871fbeb627d 257 res_adc_temp->set_value(temp3_value);
screamer 32:2871fbeb627d 258 res_adc_voltage->set_value(volt_value);
screamer 13:42b49a0caade 259 #endif /* SEND_ALL_SENSORS */
screamer 28:0e774865873d 260 }
screamer 10:b27c962b3c3f 261 }
screamer 10:b27c962b3c3f 262
chris 35:061bc344e4ec 263
adustm 4:cf7342047b4d 264 int main(void) {
screamer 17:fc98adcf835a 265 printf("\nStarting Simple Pelion Device Management Client example\n");
chris 35:061bc344e4ec 266 printf("\nSSID : %s, PWD : %s\n",WIFI_SSID, WIFI_PASSWORD);
adustm 4:cf7342047b4d 267
screamer 29:6ff737b67e7d 268 int storage_status = fs.mount(&sd);
screamer 29:6ff737b67e7d 269 if (storage_status != 0) {
screamer 29:6ff737b67e7d 270 printf("Storage mounting failed.\n");
screamer 29:6ff737b67e7d 271 }
screamer 30:15743b79c6cb 272 // If the User button is pressed ons start, then format storage.
screamer 29:6ff737b67e7d 273 bool btn_pressed = (button.read() == MBED_CONF_APP_BUTTON_PRESSED_STATE);
screamer 29:6ff737b67e7d 274 if (btn_pressed) {
screamer 29:6ff737b67e7d 275 printf("User button is pushed on start...\n");
screamer 29:6ff737b67e7d 276 }
screamer 30:15743b79c6cb 277
screamer 29:6ff737b67e7d 278 if (storage_status || btn_pressed) {
screamer 29:6ff737b67e7d 279 printf("Formatting the storage...\n");
screamer 30:15743b79c6cb 280 int storage_status = StorageHelper::format(&fs, &sd);
screamer 10:b27c962b3c3f 281 if (storage_status != 0) {
screamer 13:42b49a0caade 282 printf("ERROR: Failed to reformat the storage (%d).\n", storage_status);
screamer 10:b27c962b3c3f 283 }
screamer 28:0e774865873d 284 } else {
screamer 28:0e774865873d 285 printf("You can hold the user button during boot to format the storage and change the device identity.\n");
screamer 10:b27c962b3c3f 286 }
screamer 10:b27c962b3c3f 287
screamer 10:b27c962b3c3f 288 sensors_init();
screamer 10:b27c962b3c3f 289
adustm 4:cf7342047b4d 290 // Connect to the internet (DHCP is expected to be on)
screamer 13:42b49a0caade 291 printf("Connecting to the network using Wifi...\n");
chris 35:061bc344e4ec 292 // net = NetworkInterface::get_default_instance();
chris 35:061bc344e4ec 293 net = WiFiInterface::get_default_instance();
adustm 4:cf7342047b4d 294
screamer 10:b27c962b3c3f 295 nsapi_error_t net_status = -1;
chris 35:061bc344e4ec 296
screamer 10:b27c962b3c3f 297 for (int tries = 0; tries < 3; tries++) {
chris 35:061bc344e4ec 298
chris 35:061bc344e4ec 299 //net_status = net->connect();
chris 35:061bc344e4ec 300 net_status = net->connect(WIFI_SSID, WIFI_PASSWORD, NSAPI_SECURITY_WPA_WPA2);
chris 35:061bc344e4ec 301
screamer 10:b27c962b3c3f 302 if (net_status == NSAPI_ERROR_OK) {
screamer 10:b27c962b3c3f 303 break;
screamer 10:b27c962b3c3f 304 } else {
screamer 13:42b49a0caade 305 printf("Unable to connect to network. Retrying...\n");
screamer 10:b27c962b3c3f 306 }
screamer 10:b27c962b3c3f 307 }
MarceloSalazar 9:265744785d33 308
screamer 10:b27c962b3c3f 309 if (net_status != NSAPI_ERROR_OK) {
screamer 13:42b49a0caade 310 printf("ERROR: Connecting to the network failed (%d)!\n", net_status);
adustm 1:e86b1cffc402 311 return -1;
adustm 1:e86b1cffc402 312 }
adustm 1:e86b1cffc402 313
MarceloSalazar 9:265744785d33 314 printf("Connected to the network successfully. IP address: %s\n", net->get_ip_address());
adustm 1:e86b1cffc402 315
screamer 17:fc98adcf835a 316 printf("Initializing Pelion Device Management Client...\n");
screamer 17:fc98adcf835a 317
MarceloSalazar 9:265744785d33 318 // SimpleMbedCloudClient handles registering over LwM2M to Pelion DM
MarceloSalazar 9:265744785d33 319 SimpleMbedCloudClient client(net, bd, &fs);
adustm 4:cf7342047b4d 320 int client_status = client.init();
adustm 4:cf7342047b4d 321 if (client_status != 0) {
screamer 13:42b49a0caade 322 printf("ERROR: Pelion Client initialization failed (%d)\n", client_status);
adustm 1:e86b1cffc402 323 return -1;
adustm 1:e86b1cffc402 324 }
adustm 1:e86b1cffc402 325
adustm 4:cf7342047b4d 326 // Creating resources, which can be written or read from the cloud
screamer 32:2871fbeb627d 327 res_button = client.create_resource("3200/0/5501", "Button Count");
screamer 12:1f1a50e973db 328 res_button->set_value(0);
screamer 12:1f1a50e973db 329 res_button->methods(M2MMethod::GET);
screamer 12:1f1a50e973db 330 res_button->observable(true);
screamer 12:1f1a50e973db 331 res_button->attach_notification_callback(button_callback);
adustm 1:e86b1cffc402 332
screamer 33:cfd9430e7d1e 333 res_led = client.create_resource("3201/0/5853", "LED State");
screamer 33:cfd9430e7d1e 334 res_led->set_value(1);
screamer 33:cfd9430e7d1e 335 res_led->methods(M2MMethod::GET | M2MMethod::PUT);
screamer 33:cfd9430e7d1e 336 res_led->attach_put_callback(put_callback);
screamer 33:cfd9430e7d1e 337
screamer 33:cfd9430e7d1e 338 #ifdef SEND_ALL_SENSORS
screamer 10:b27c962b3c3f 339 // Sensor resources
screamer 32:2871fbeb627d 340 res_temperature = client.create_resource("3303/0/5700", "Temperature HTS221 (C)");
screamer 12:1f1a50e973db 341 res_temperature->set_value(0);
screamer 12:1f1a50e973db 342 res_temperature->methods(M2MMethod::GET);
screamer 12:1f1a50e973db 343 res_temperature->observable(true);
screamer 10:b27c962b3c3f 344
screamer 32:2871fbeb627d 345 res_humidity = client.create_resource("3304/0/5700", "Humidity");
screamer 12:1f1a50e973db 346 res_humidity->set_value(0);
screamer 12:1f1a50e973db 347 res_humidity->methods(M2MMethod::GET);
screamer 12:1f1a50e973db 348 res_humidity->observable(true);
screamer 10:b27c962b3c3f 349
screamer 32:2871fbeb627d 350 res_temperature2 = client.create_resource("3303/1/5700", "Temperature LPS22HB (C)");
screamer 13:42b49a0caade 351 res_temperature2->set_value(0);
screamer 13:42b49a0caade 352 res_temperature2->methods(M2MMethod::GET);
screamer 13:42b49a0caade 353 res_temperature2->observable(true);
screamer 13:42b49a0caade 354
screamer 32:2871fbeb627d 355 res_adc_temp = client.create_resource("3303/2/5700", "Temperature ADC (C)");
screamer 28:0e774865873d 356 res_adc_temp->set_value(0);
screamer 28:0e774865873d 357 res_adc_temp->methods(M2MMethod::GET);
screamer 28:0e774865873d 358 res_adc_temp->observable(true);
screamer 28:0e774865873d 359
screamer 32:2871fbeb627d 360 res_accelerometer_x = client.create_resource("3313/0/5702", "Accelerometer X");
screamer 28:0e774865873d 361 res_accelerometer_x->set_value(0);
screamer 28:0e774865873d 362 res_accelerometer_x->methods(M2MMethod::GET);
screamer 28:0e774865873d 363 res_accelerometer_x->observable(true);
screamer 28:0e774865873d 364
screamer 32:2871fbeb627d 365 res_accelerometer_y = client.create_resource("3313/0/5703", "Accelerometer Y");
screamer 28:0e774865873d 366 res_accelerometer_y->set_value(0);
screamer 28:0e774865873d 367 res_accelerometer_y->methods(M2MMethod::GET);
screamer 28:0e774865873d 368 res_accelerometer_y->observable(true);
screamer 28:0e774865873d 369
screamer 32:2871fbeb627d 370 res_accelerometer_z = client.create_resource("3313/0/5704", "Accelerometer Z");
screamer 28:0e774865873d 371 res_accelerometer_z->set_value(0);
screamer 28:0e774865873d 372 res_accelerometer_z->methods(M2MMethod::GET);
screamer 28:0e774865873d 373 res_accelerometer_z->observable(true);
screamer 28:0e774865873d 374
screamer 32:2871fbeb627d 375 res_magnometer_x = client.create_resource("3314/0/5702", "Magnometer X");
screamer 28:0e774865873d 376 res_magnometer_x->set_value(0);
screamer 28:0e774865873d 377 res_magnometer_x->methods(M2MMethod::GET);
screamer 28:0e774865873d 378 res_magnometer_x->observable(true);
screamer 28:0e774865873d 379
screamer 32:2871fbeb627d 380 res_magnometer_y = client.create_resource("3314/0/5703", "Magnometer Y");
screamer 28:0e774865873d 381 res_magnometer_y->set_value(0);
screamer 28:0e774865873d 382 res_magnometer_y->methods(M2MMethod::GET);
screamer 28:0e774865873d 383 res_magnometer_y->observable(true);
screamer 28:0e774865873d 384
screamer 32:2871fbeb627d 385 res_magnometer_z = client.create_resource("3314/0/5704", "Magnometer Z");
screamer 28:0e774865873d 386 res_magnometer_z->set_value(0);
screamer 28:0e774865873d 387 res_magnometer_z->methods(M2MMethod::GET);
screamer 28:0e774865873d 388 res_magnometer_z->observable(true);
screamer 28:0e774865873d 389
screamer 32:2871fbeb627d 390 res_gyroscope_x = client.create_resource("3334/0/5702", "Gyroscope X");
screamer 13:42b49a0caade 391 res_gyroscope_x->set_value(0);
screamer 13:42b49a0caade 392 res_gyroscope_x->methods(M2MMethod::GET);
screamer 13:42b49a0caade 393 res_gyroscope_x->observable(true);
screamer 10:b27c962b3c3f 394
screamer 32:2871fbeb627d 395 res_gyroscope_y = client.create_resource("3334/0/5703", "Gyroscope Y");
screamer 13:42b49a0caade 396 res_gyroscope_y->set_value(0);
screamer 13:42b49a0caade 397 res_gyroscope_y->methods(M2MMethod::GET);
screamer 13:42b49a0caade 398 res_gyroscope_y->observable(true);
screamer 13:42b49a0caade 399
screamer 32:2871fbeb627d 400 res_gyroscope_z = client.create_resource("3334/0/5704", "Gyroscope Z");
screamer 13:42b49a0caade 401 res_gyroscope_z->set_value(0);
screamer 13:42b49a0caade 402 res_gyroscope_z->methods(M2MMethod::GET);
screamer 13:42b49a0caade 403 res_gyroscope_z->observable(true);
screamer 13:42b49a0caade 404
screamer 32:2871fbeb627d 405 res_adc_voltage = client.create_resource("3316/0/5700", "Voltage");
screamer 28:0e774865873d 406 res_adc_voltage->set_value(0);
screamer 28:0e774865873d 407 res_adc_voltage->methods(M2MMethod::GET);
screamer 28:0e774865873d 408 res_adc_voltage->observable(true);
screamer 28:0e774865873d 409
screamer 32:2871fbeb627d 410 res_pressure = client.create_resource("3323/0/5700", "Pressure");
screamer 28:0e774865873d 411 res_pressure->set_value(0);
screamer 28:0e774865873d 412 res_pressure->methods(M2MMethod::GET);
screamer 28:0e774865873d 413 res_pressure->observable(true);
screamer 28:0e774865873d 414
screamer 32:2871fbeb627d 415 res_distance = client.create_resource("3330/0/5700", "Distance");
screamer 28:0e774865873d 416 res_distance->set_value((float)999.9);
screamer 13:42b49a0caade 417 res_distance->methods(M2MMethod::GET);
screamer 13:42b49a0caade 418 res_distance->observable(true);
screamer 13:42b49a0caade 419 #endif /* SEND_ALL_SENSORS */
screamer 11:8df4529f060d 420
MarceloSalazar 9:265744785d33 421 printf("Initialized Pelion Client. Registering...\n");
adustm 1:e86b1cffc402 422
adustm 4:cf7342047b4d 423 // Callback that fires when registering is complete
adustm 4:cf7342047b4d 424 client.on_registered(&registered);
adustm 1:e86b1cffc402 425
MarceloSalazar 9:265744785d33 426 // Register with Pelion DM
adustm 4:cf7342047b4d 427 client.register_and_connect();
adustm 1:e86b1cffc402 428
screamer 17:fc98adcf835a 429 int i = 600; // wait up 60 seconds before attaching sensors and button events
screamer 12:1f1a50e973db 430 while (i-- > 0 && !client.is_client_registered()) {
screamer 12:1f1a50e973db 431 wait_ms(100);
screamer 12:1f1a50e973db 432 }
screamer 12:1f1a50e973db 433
screamer 11:8df4529f060d 434 button.fall(eventQueue.event(&button_press));
screamer 10:b27c962b3c3f 435
screamer 15:a0430d40a918 436 // The timer fires on an interrupt context, but debounces it to the eventqueue, so it's safe to do network operations
adustm 4:cf7342047b4d 437 Ticker timer;
screamer 11:8df4529f060d 438 timer.attach(eventQueue.event(&sensors_update), SENSORS_POLL_INTERVAL);
adustm 1:e86b1cffc402 439
adustm 4:cf7342047b4d 440 // You can easily run the eventQueue in a separate thread if required
adustm 4:cf7342047b4d 441 eventQueue.dispatch_forever();
adustm 1:e86b1cffc402 442 }
screamer 28:0e774865873d 443
MarceloSalazar 9:265744785d33 444 #endif