![](/media/cache/profiles/profile2.jpg.50x50_q85.jpg)
This software setup a central node of a star topology network
Dependencies: MQTT target_st_bluenrg
Fork of ble-star-mbed by
source/main.cpp@5:5cfb069b2587, 2018-04-04 (annotated)
- Committer:
- lorevee
- Date:
- Wed Apr 04 14:42:35 2018 +0000
- Revision:
- 5:5cfb069b2587
- Parent:
- 4:4af40af2530e
default id
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
lorevee | 0:1902469bdd2d | 1 | #include <events/mbed_events.h> |
lorevee | 0:1902469bdd2d | 2 | #include <mbed.h> |
lorevee | 0:1902469bdd2d | 3 | #include "ble/BLE.h" |
lorevee | 0:1902469bdd2d | 4 | #include "ble/DiscoveredCharacteristic.h" |
lorevee | 0:1902469bdd2d | 5 | #include "ble/DiscoveredService.h" |
lorevee | 0:1902469bdd2d | 6 | #include <UUID.h> |
lorevee | 0:1902469bdd2d | 7 | #include <BleMasterService.h> |
lorevee | 0:1902469bdd2d | 8 | #include <BleSlaveService.h> |
lorevee | 4:4af40af2530e | 9 | #include <string.h> |
lorevee | 4:4af40af2530e | 10 | #include "easy-connect.h" |
lorevee | 4:4af40af2530e | 11 | #include "MQTTClient.h" |
lorevee | 4:4af40af2530e | 12 | #include "MQTTmbed.h" |
lorevee | 4:4af40af2530e | 13 | #include "MQTTNetwork.h" |
lorevee | 4:4af40af2530e | 14 | |
lorevee | 4:4af40af2530e | 15 | /*----------------------------------------------------------------------------*/ |
lorevee | 4:4af40af2530e | 16 | |
lorevee | 4:4af40af2530e | 17 | /* Enable/Disable WiFi (1 = WiFi Enabled, 0 = WiFi Disabled) */ |
lorevee | 4:4af40af2530e | 18 | #define ENABLE_WIFI 1 |
lorevee | 4:4af40af2530e | 19 | |
lorevee | 4:4af40af2530e | 20 | /**** System configuration define ****/ |
lorevee | 4:4af40af2530e | 21 | #define ORG_QUICKSTART // comment to connect to play.internetofthings.ibmcloud.com |
lorevee | 4:4af40af2530e | 22 | #ifndef ORG_QUICKSTART |
lorevee | 4:4af40af2530e | 23 | //#define TLS_EN // uncomment to add TLS to NON quickstart connections |
lorevee | 4:4af40af2530e | 24 | #endif |
lorevee | 4:4af40af2530e | 25 | |
lorevee | 4:4af40af2530e | 26 | #ifdef TLS_EN // Digicert Root Certificate in PEM format (from IBM website) |
lorevee | 4:4af40af2530e | 27 | const char SSL_CA_PEM[] ="-----BEGIN CERTIFICATE-----\n" |
lorevee | 4:4af40af2530e | 28 | "MIIDrzCCApegAwIBAgIQCDvgVpBCRrGhdWrJWZHHSjANBgkqhkiG9w0BAQUFADBh\n" |
lorevee | 4:4af40af2530e | 29 | "MQswCQYDVQQGEwJVUzEVMBMGA1UEChMMRGlnaUNlcnQgSW5jMRkwFwYDVQQLExB3\n" |
lorevee | 4:4af40af2530e | 30 | "d3cuZGlnaWNlcnQuY29tMSAwHgYDVQQDExdEaWdpQ2VydCBHbG9iYWwgUm9vdCBD\n" |
lorevee | 4:4af40af2530e | 31 | "QTAeFw0wNjExMTAwMDAwMDBaFw0zMTExMTAwMDAwMDBaMGExCzAJBgNVBAYTAlVT\n" |
lorevee | 4:4af40af2530e | 32 | "MRUwEwYDVQQKEwxEaWdpQ2VydCBJbmMxGTAXBgNVBAsTEHd3dy5kaWdpY2VydC5j\n" |
lorevee | 4:4af40af2530e | 33 | "b20xIDAeBgNVBAMTF0RpZ2lDZXJ0IEdsb2JhbCBSb290IENBMIIBIjANBgkqhkiG\n" |
lorevee | 4:4af40af2530e | 34 | "9w0BAQEFAAOCAQ8AMIIBCgKCAQEA4jvhEXLeqKTTo1eqUKKPC3eQyaKl7hLOllsB\n" |
lorevee | 4:4af40af2530e | 35 | "CSDMAZOnTjC3U/dDxGkAV53ijSLdhwZAAIEJzs4bg7/fzTtxRuLWZscFs3YnFo97\n" |
lorevee | 4:4af40af2530e | 36 | "nh6Vfe63SKMI2tavegw5BmV/Sl0fvBf4q77uKNd0f3p4mVmFaG5cIzJLv07A6Fpt\n" |
lorevee | 4:4af40af2530e | 37 | "43C/dxC//AH2hdmoRBBYMql1GNXRor5H4idq9Joz+EkIYIvUX7Q6hL+hqkpMfT7P\n" |
lorevee | 4:4af40af2530e | 38 | "T19sdl6gSzeRntwi5m3OFBqOasv+zbMUZBfHWymeMr/y7vrTC0LUq7dBMtoM1O/4\n" |
lorevee | 4:4af40af2530e | 39 | "gdW7jVg/tRvoSSiicNoxBN33shbyTApOB6jtSj1etX+jkMOvJwIDAQABo2MwYTAO\n" |
lorevee | 4:4af40af2530e | 40 | "BgNVHQ8BAf8EBAMCAYYwDwYDVR0TAQH/BAUwAwEB/zAdBgNVHQ4EFgQUA95QNVbR\n" |
lorevee | 4:4af40af2530e | 41 | "TLtm8KPiGxvDl7I90VUwHwYDVR0jBBgwFoAUA95QNVbRTLtm8KPiGxvDl7I90VUw\n" |
lorevee | 4:4af40af2530e | 42 | "DQYJKoZIhvcNAQEFBQADggEBAMucN6pIExIK+t1EnE9SsPTfrgT1eXkIoyQY/Esr\n" |
lorevee | 4:4af40af2530e | 43 | "hMAtudXH/vTBH1jLuG2cenTnmCmrEbXjcKChzUyImZOMkXDiqw8cvpOp/2PV5Adg\n" |
lorevee | 4:4af40af2530e | 44 | "06O/nVsJ8dWO41P0jmP6P6fbtGbfYmbW0W5BjfIttep3Sp+dWOIrWcBAI+0tKIJF\n" |
lorevee | 4:4af40af2530e | 45 | "PnlUkiaY4IBIqDfv8NZ5YBberOgOzW6sRBc4L0na4UU+Krk2U886UAb3LujEV0ls\n" |
lorevee | 4:4af40af2530e | 46 | "YSEY1QSteDwsOoBrp+uvFRTp2InBuThs4pFsiv9kuXclVzDAGySj4dzp30d8tbQk\n" |
lorevee | 4:4af40af2530e | 47 | "CAUw7C29C79Fv1C5qfPrmAESrciIxpg0X40KPMbp1ZWVbd4=\n" |
lorevee | 4:4af40af2530e | 48 | "-----END CERTIFICATE-----\n"; |
lorevee | 4:4af40af2530e | 49 | #endif |
lorevee | 4:4af40af2530e | 50 | |
lorevee | 4:4af40af2530e | 51 | |
lorevee | 4:4af40af2530e | 52 | |
lorevee | 4:4af40af2530e | 53 | static bool quickstartMode = true; // set to false to connect with authentication tocken |
lorevee | 4:4af40af2530e | 54 | |
lorevee | 4:4af40af2530e | 55 | #define MQTT_MAX_PACKET_SIZE 400 |
lorevee | 4:4af40af2530e | 56 | #define MQTT_MAX_PAYLOAD_SIZE 300 |
lorevee | 4:4af40af2530e | 57 | |
lorevee | 4:4af40af2530e | 58 | |
lorevee | 4:4af40af2530e | 59 | |
lorevee | 4:4af40af2530e | 60 | // Configuration values needed to connect to IBM IoT Cloud |
lorevee | 4:4af40af2530e | 61 | #ifdef ORG_QUICKSTART |
lorevee | 4:4af40af2530e | 62 | #define ORG "quickstart" // connect to quickstart.internetofthings.ibmcloud.com/ For a registered connection, replace with your org |
lorevee | 4:4af40af2530e | 63 | #define ID "" |
lorevee | 4:4af40af2530e | 64 | #define AUTH_TOKEN "" |
lorevee | 4:4af40af2530e | 65 | #define DEFAULT_TYPE_NAME "sensor" |
lorevee | 4:4af40af2530e | 66 | #define DEFAULT_PORT MQTT_PORT |
lorevee | 4:4af40af2530e | 67 | |
lorevee | 4:4af40af2530e | 68 | #else // not def ORG_QUICKSTART |
lorevee | 4:4af40af2530e | 69 | #define ORG MQTT_ORG_ID // connect to ORG.internetofthings.ibmcloud.com/ For a registered connection, replace with your org |
lorevee | 4:4af40af2530e | 70 | #define ID MQTT_DEVICE_ID // For a registered connection is your device id |
lorevee | 4:4af40af2530e | 71 | #define AUTH_TOKEN MQTT_DEVICE_PASSWORD // For a registered connection is a device auth-token |
lorevee | 4:4af40af2530e | 72 | #define DEFAULT_TYPE_NAME MQTT_DEVICE_TYPE // For a registered connection is device type |
lorevee | 4:4af40af2530e | 73 | |
lorevee | 4:4af40af2530e | 74 | #ifdef TLS_EN |
lorevee | 4:4af40af2530e | 75 | #define DEFAULT_PORT MQTT_TLS_PORT |
lorevee | 4:4af40af2530e | 76 | #else |
lorevee | 4:4af40af2530e | 77 | #define DEFAULT_PORT MQTT_PORT |
lorevee | 4:4af40af2530e | 78 | |
lorevee | 4:4af40af2530e | 79 | #endif |
lorevee | 4:4af40af2530e | 80 | #endif |
lorevee | 4:4af40af2530e | 81 | |
lorevee | 4:4af40af2530e | 82 | |
lorevee | 4:4af40af2530e | 83 | |
lorevee | 4:4af40af2530e | 84 | #define TYPE DEFAULT_TYPE_NAME // For a registered connection, replace with your type |
lorevee | 4:4af40af2530e | 85 | #define IBM_IOT_PORT DEFAULT_PORT |
lorevee | 4:4af40af2530e | 86 | |
lorevee | 4:4af40af2530e | 87 | #define MAXLEN_MBED_CONF_APP_WIFI_SSID 32 // same as WIFI_SSID_MAX_LEN in easy_connect |
lorevee | 4:4af40af2530e | 88 | #define MAXLEN_MBED_CONF_APP_WIFI_PASSWORD 64 // same as WIFI_PASSWORD_MAX_LEN |
lorevee | 4:4af40af2530e | 89 | |
lorevee | 4:4af40af2530e | 90 | static char id[30] = ID; // mac without colons |
lorevee | 4:4af40af2530e | 91 | static char org[12] = ORG; |
lorevee | 4:4af40af2530e | 92 | static int connack_rc = 0; // MQTT connack return code |
lorevee | 4:4af40af2530e | 93 | static char type[30] = TYPE; |
lorevee | 4:4af40af2530e | 94 | static char auth_token[30] = AUTH_TOKEN; // Auth_token is only used in non-quickstart mode |
lorevee | 4:4af40af2530e | 95 | static bool netConnecting = false; |
lorevee | 4:4af40af2530e | 96 | static bool mqttConnecting = false; |
lorevee | 4:4af40af2530e | 97 | static bool netConnected = false; |
lorevee | 4:4af40af2530e | 98 | static bool connected = false; |
lorevee | 4:4af40af2530e | 99 | static int retryAttempt = 0; |
lorevee | 4:4af40af2530e | 100 | static char subscription_url[MQTT_MAX_PAYLOAD_SIZE]; |
lorevee | 4:4af40af2530e | 101 | static char ssid[MAXLEN_MBED_CONF_APP_WIFI_SSID]; // Network must be visible otherwise it can't connect |
lorevee | 4:4af40af2530e | 102 | static char seckey[MAXLEN_MBED_CONF_APP_WIFI_PASSWORD]; |
lorevee | 4:4af40af2530e | 103 | |
lorevee | 4:4af40af2530e | 104 | MQTT::Client<MQTTNetwork, Countdown, MQTT_MAX_PACKET_SIZE> *pClient; |
lorevee | 0:1902469bdd2d | 105 | |
lorevee | 0:1902469bdd2d | 106 | const char NAME_BLESTAR1[] = "BleStar1"; |
lorevee | 0:1902469bdd2d | 107 | |
lorevee | 4:4af40af2530e | 108 | uint8_t wifi_status; |
lorevee | 4:4af40af2530e | 109 | |
lorevee | 4:4af40af2530e | 110 | uint8_t wifi_data[256]; |
lorevee | 4:4af40af2530e | 111 | uint8_t new_data = 0; |
lorevee | 4:4af40af2530e | 112 | uint8_t *data; |
lorevee | 4:4af40af2530e | 113 | uint8_t wifi_present; |
lorevee | 4:4af40af2530e | 114 | uint8_t start_bnrg; |
lorevee | 4:4af40af2530e | 115 | extern PeripheralDevices_t perDevs; |
lorevee | 4:4af40af2530e | 116 | uint8_t json_buffer[512]; |
lorevee | 4:4af40af2530e | 117 | |
lorevee | 4:4af40af2530e | 118 | /*----------------------------------------------------------------------------*/ |
lorevee | 4:4af40af2530e | 119 | |
lorevee | 4:4af40af2530e | 120 | |
lorevee | 4:4af40af2530e | 121 | |
lorevee | 4:4af40af2530e | 122 | /* Prepare JSON packet with sensors data */ |
lorevee | 4:4af40af2530e | 123 | void prepare_json_pkt (uint8_t * buffer){ |
lorevee | 4:4af40af2530e | 124 | char tempbuff[256]; |
lorevee | 4:4af40af2530e | 125 | |
lorevee | 4:4af40af2530e | 126 | strcpy((char *)buffer,"{\"d\":{\"ST\":\"BLEStar\""); |
lorevee | 4:4af40af2530e | 127 | sprintf(tempbuff, ",%s", data); |
lorevee | 4:4af40af2530e | 128 | strcat((char *)buffer,tempbuff); |
lorevee | 4:4af40af2530e | 129 | strcat((char *)buffer,"}}"); |
lorevee | 4:4af40af2530e | 130 | |
lorevee | 4:4af40af2530e | 131 | return; |
lorevee | 4:4af40af2530e | 132 | } |
lorevee | 0:1902469bdd2d | 133 | /*----------------------------------------------------------------------------*/ |
lorevee | 0:1902469bdd2d | 134 | |
lorevee | 0:1902469bdd2d | 135 | |
lorevee | 0:1902469bdd2d | 136 | |
lorevee | 4:4af40af2530e | 137 | /* Connect the broker - return the CONNACK*/ |
lorevee | 4:4af40af2530e | 138 | int connect(MQTT::Client<MQTTNetwork, Countdown, MQTT_MAX_PACKET_SIZE> * client, MQTTNetwork *mqttNetwork, NetworkInterface* network) |
lorevee | 4:4af40af2530e | 139 | { |
lorevee | 4:4af40af2530e | 140 | const char* iot_ibm = MQTT_BROKER_URL; |
lorevee | 4:4af40af2530e | 141 | char hostname[strlen(org) + strlen(iot_ibm) + 1]; |
lorevee | 4:4af40af2530e | 142 | |
lorevee | 4:4af40af2530e | 143 | sprintf(hostname, "%s%s", org, iot_ibm); |
lorevee | 4:4af40af2530e | 144 | // Construct clientId - d:org:type:id |
lorevee | 4:4af40af2530e | 145 | char clientId[strlen(org) + strlen(type) + strlen(id) + 5]; |
lorevee | 4:4af40af2530e | 146 | sprintf(clientId, "d:%s:%s:%s", org, type, id); |
lorevee | 4:4af40af2530e | 147 | sprintf(subscription_url, "%s.%s/#/device/%s/%s/", org, "internetofthings.ibmcloud.com", id, TYPE); |
lorevee | 4:4af40af2530e | 148 | |
lorevee | 4:4af40af2530e | 149 | // Network debug statements |
lorevee | 4:4af40af2530e | 150 | printf("\r\n====================================="); |
lorevee | 4:4af40af2530e | 151 | printf("\r\nNucleo IP ADDRESS: %s\n", network->get_ip_address()); |
lorevee | 4:4af40af2530e | 152 | printf("\r\nNucleo MAC ADDRESS: %s\n", network->get_mac_address()); |
lorevee | 4:4af40af2530e | 153 | printf("\r\nServer Hostname: %s port: %d\n", hostname, IBM_IOT_PORT); |
lorevee | 4:4af40af2530e | 154 | printf("\r\nClient ID: %s\n", clientId); |
lorevee | 4:4af40af2530e | 155 | printf("\r\nTopic: %s\n",MQTT_TOPIC); |
lorevee | 4:4af40af2530e | 156 | printf("\r\nSubscription URL: %s", subscription_url); |
lorevee | 4:4af40af2530e | 157 | printf("\r\n=====================================\r\n"); |
lorevee | 4:4af40af2530e | 158 | netConnecting = true; |
lorevee | 4:4af40af2530e | 159 | |
lorevee | 4:4af40af2530e | 160 | |
lorevee | 4:4af40af2530e | 161 | |
lorevee | 4:4af40af2530e | 162 | #ifdef ORG_QUICKSTART |
lorevee | 4:4af40af2530e | 163 | int tls = TLS_OFF; |
lorevee | 4:4af40af2530e | 164 | const char * cert = NULL; |
lorevee | 4:4af40af2530e | 165 | unsigned int sizeof_cert = 0; |
lorevee | 4:4af40af2530e | 166 | |
lorevee | 4:4af40af2530e | 167 | #else // if !QUICKSTART possible to connect with TLS or not |
lorevee | 4:4af40af2530e | 168 | #ifdef TLS_EN |
lorevee | 4:4af40af2530e | 169 | int tls = TLS_ON; |
lorevee | 4:4af40af2530e | 170 | const char * cert = SSL_CA_PEM; |
lorevee | 4:4af40af2530e | 171 | unsigned int sizeof_cert = sizeof(SSL_CA_PEM); |
lorevee | 4:4af40af2530e | 172 | |
lorevee | 4:4af40af2530e | 173 | #else |
lorevee | 4:4af40af2530e | 174 | int tls = TLS_OFF; |
lorevee | 4:4af40af2530e | 175 | const char * cert = 0; |
lorevee | 4:4af40af2530e | 176 | unsigned int sizeof_cert = 0; |
lorevee | 4:4af40af2530e | 177 | |
lorevee | 4:4af40af2530e | 178 | #endif |
lorevee | 4:4af40af2530e | 179 | #endif |
lorevee | 4:4af40af2530e | 180 | |
lorevee | 4:4af40af2530e | 181 | |
lorevee | 4:4af40af2530e | 182 | //Return code |
lorevee | 4:4af40af2530e | 183 | int rc = mqttNetwork->connect(hostname, IBM_IOT_PORT, tls, cert, sizeof_cert); |
lorevee | 4:4af40af2530e | 184 | if (rc != 0) |
lorevee | 4:4af40af2530e | 185 | { |
lorevee | 4:4af40af2530e | 186 | printf("\r\nrc from TCP connect is %d\n", rc); |
lorevee | 4:4af40af2530e | 187 | return rc; |
lorevee | 4:4af40af2530e | 188 | } |
lorevee | 4:4af40af2530e | 189 | netConnected = true; |
lorevee | 4:4af40af2530e | 190 | netConnecting = false; |
lorevee | 4:4af40af2530e | 191 | |
lorevee | 4:4af40af2530e | 192 | |
lorevee | 4:4af40af2530e | 193 | // MQTT Connect |
lorevee | 4:4af40af2530e | 194 | mqttConnecting = true; |
lorevee | 4:4af40af2530e | 195 | MQTTPacket_connectData data = MQTTPacket_connectData_initializer; |
lorevee | 4:4af40af2530e | 196 | data.MQTTVersion = 4; |
lorevee | 4:4af40af2530e | 197 | data.struct_version=0; |
lorevee | 4:4af40af2530e | 198 | data.clientID.cstring = clientId; |
lorevee | 4:4af40af2530e | 199 | data.keepAliveInterval = 0; //MQTT_KEEPALIVE; // in Sec |
lorevee | 4:4af40af2530e | 200 | if (!quickstartMode){ |
lorevee | 4:4af40af2530e | 201 | data.username.cstring = "use-token-auth"; |
lorevee | 4:4af40af2530e | 202 | data.password.cstring = auth_token; |
lorevee | 4:4af40af2530e | 203 | printf ("\r\nAutToken: %s\n", auth_token); |
lorevee | 4:4af40af2530e | 204 | } |
lorevee | 4:4af40af2530e | 205 | if ((rc = client->connect(data)) != MQTT::SUCCESS) { |
lorevee | 4:4af40af2530e | 206 | printf("\r\nrc from MQTT connect is %d\n", rc); |
lorevee | 4:4af40af2530e | 207 | connack_rc = rc; |
lorevee | 4:4af40af2530e | 208 | return rc; |
lorevee | 4:4af40af2530e | 209 | } |
lorevee | 4:4af40af2530e | 210 | connected = true; |
lorevee | 4:4af40af2530e | 211 | printf ("\r\n--->MQTT Connected\n"); |
lorevee | 4:4af40af2530e | 212 | |
lorevee | 4:4af40af2530e | 213 | mqttConnecting = false; |
lorevee | 4:4af40af2530e | 214 | connack_rc = rc; |
lorevee | 4:4af40af2530e | 215 | return rc; |
lorevee | 4:4af40af2530e | 216 | } |
lorevee | 4:4af40af2530e | 217 | /*----------------------------------------------------------------------------*/ |
lorevee | 4:4af40af2530e | 218 | |
lorevee | 4:4af40af2530e | 219 | |
lorevee | 4:4af40af2530e | 220 | |
lorevee | 4:4af40af2530e | 221 | int getConnTimeout(int attemptNumber) |
lorevee | 4:4af40af2530e | 222 | { // First 10 attempts try within 3 seconds, next 10 attempts retry after every 1 minute |
lorevee | 4:4af40af2530e | 223 | // after 20 attempts, retry every 10 minutes |
lorevee | 4:4af40af2530e | 224 | return (attemptNumber < 10) ? 3 : (attemptNumber < 20) ? 60 : 600; |
lorevee | 4:4af40af2530e | 225 | } |
lorevee | 4:4af40af2530e | 226 | /*----------------------------------------------------------------------------*/ |
lorevee | 4:4af40af2530e | 227 | |
lorevee | 4:4af40af2530e | 228 | |
lorevee | 4:4af40af2530e | 229 | |
lorevee | 4:4af40af2530e | 230 | void attemptConnect(MQTT::Client<MQTTNetwork, Countdown, MQTT_MAX_PACKET_SIZE>* client, MQTTNetwork *mqttNetwork, NetworkInterface* network) |
lorevee | 4:4af40af2530e | 231 | { |
lorevee | 4:4af40af2530e | 232 | connected = false; |
lorevee | 4:4af40af2530e | 233 | |
lorevee | 4:4af40af2530e | 234 | while (connect(client, mqttNetwork, network) != MQTT_CONNECTION_ACCEPTED) |
lorevee | 4:4af40af2530e | 235 | { |
lorevee | 4:4af40af2530e | 236 | if (connack_rc == MQTT_NOT_AUTHORIZED || connack_rc == MQTT_BAD_USERNAME_OR_PASSWORD) { |
lorevee | 4:4af40af2530e | 237 | printf ("\r\nError MQTT_BAD_USERNAME_OR_PASSWORDFile: %s, Line: %d Error: %d \n",__FILE__,__LINE__, connack_rc); |
lorevee | 4:4af40af2530e | 238 | return; // don't reattempt to connect if credentials are wrong |
lorevee | 4:4af40af2530e | 239 | } |
lorevee | 4:4af40af2530e | 240 | int timeout = getConnTimeout(++retryAttempt); |
lorevee | 4:4af40af2530e | 241 | WARN("Retry attempt number %d waiting %d\n", retryAttempt, timeout); |
lorevee | 4:4af40af2530e | 242 | |
lorevee | 4:4af40af2530e | 243 | // if ipstack and client were on the heap we could deconstruct and goto a label where they are constructed |
lorevee | 4:4af40af2530e | 244 | // or maybe just add the proper members to do this disconnect and call attemptConnect(...) |
lorevee | 4:4af40af2530e | 245 | // this works - reset the system when the retry count gets to a threshold |
lorevee | 4:4af40af2530e | 246 | if (retryAttempt == 5) |
lorevee | 4:4af40af2530e | 247 | NVIC_SystemReset(); |
lorevee | 4:4af40af2530e | 248 | else |
lorevee | 4:4af40af2530e | 249 | wait(timeout); |
lorevee | 4:4af40af2530e | 250 | } |
lorevee | 4:4af40af2530e | 251 | } |
lorevee | 4:4af40af2530e | 252 | /*----------------------------------------------------------------------------*/ |
lorevee | 4:4af40af2530e | 253 | |
lorevee | 4:4af40af2530e | 254 | |
lorevee | 4:4af40af2530e | 255 | /* Method to publish data to client (sending data to broker) */ |
lorevee | 4:4af40af2530e | 256 | int publish(MQTT::Client<MQTTNetwork, Countdown, MQTT_MAX_PACKET_SIZE>* client){ |
lorevee | 4:4af40af2530e | 257 | //printf("\r\npublish");//DEBUG |
lorevee | 4:4af40af2530e | 258 | |
lorevee | 4:4af40af2530e | 259 | MQTT::Message message; |
lorevee | 4:4af40af2530e | 260 | const char* pubTopic = MQTT_TOPIC; |
lorevee | 4:4af40af2530e | 261 | |
lorevee | 4:4af40af2530e | 262 | |
lorevee | 4:4af40af2530e | 263 | if (!client->isConnected()){ |
lorevee | 4:4af40af2530e | 264 | printf ("\r\npublish failed: MQTT disconnected\n"); |
lorevee | 4:4af40af2530e | 265 | return MQTT::FAILURE; |
lorevee | 4:4af40af2530e | 266 | } |
lorevee | 4:4af40af2530e | 267 | |
lorevee | 4:4af40af2530e | 268 | |
lorevee | 4:4af40af2530e | 269 | message.qos = MQTT::QOS0; // quality of service 0 default |
lorevee | 4:4af40af2530e | 270 | message.retained = false; // (false) new clients will not receive past data |
lorevee | 4:4af40af2530e | 271 | message.dup = false; // (false) no duplicated message |
lorevee | 4:4af40af2530e | 272 | message.payload = (void*)json_buffer; // DATA to be sent |
lorevee | 4:4af40af2530e | 273 | message.payloadlen = strlen((const char *)(json_buffer)); |
lorevee | 4:4af40af2530e | 274 | |
lorevee | 4:4af40af2530e | 275 | |
lorevee | 4:4af40af2530e | 276 | return client->publish(pubTopic, message); |
lorevee | 4:4af40af2530e | 277 | } |
lorevee | 4:4af40af2530e | 278 | /*----------------------------------------------------------------------------*/ |
lorevee | 4:4af40af2530e | 279 | |
lorevee | 4:4af40af2530e | 280 | |
lorevee | 0:1902469bdd2d | 281 | |
lorevee | 0:1902469bdd2d | 282 | /* scheduleBleEventsProcessing */ |
lorevee | 0:1902469bdd2d | 283 | void scheduleBleEventsProcessing(BLE::OnEventsToProcessCallbackContext* context) { |
lorevee | 0:1902469bdd2d | 284 | BLE &ble = BLE::Instance(); |
lorevee | 0:1902469bdd2d | 285 | eventQ.call(Callback<void()>(&ble, &BLE::processEvents)); |
lorevee | 0:1902469bdd2d | 286 | } |
lorevee | 0:1902469bdd2d | 287 | /*----------------------------------------------------------------------------*/ |
lorevee | 4:4af40af2530e | 288 | |
lorevee | 4:4af40af2530e | 289 | |
lorevee | 4:4af40af2530e | 290 | |
lorevee | 4:4af40af2530e | 291 | |
lorevee | 0:1902469bdd2d | 292 | /* Complete the initialization of ble module */ |
lorevee | 0:1902469bdd2d | 293 | void bleInitComplete(BLE::InitializationCompleteCallbackContext *params){ |
lorevee | 0:1902469bdd2d | 294 | |
lorevee | 0:1902469bdd2d | 295 | |
lorevee | 0:1902469bdd2d | 296 | initProcess(); |
lorevee | 0:1902469bdd2d | 297 | ble_error_t a0, a1, a2, a3; |
lorevee | 0:1902469bdd2d | 298 | |
lorevee | 0:1902469bdd2d | 299 | BLE& ble = params->ble; |
lorevee | 0:1902469bdd2d | 300 | ble_error_t error = params->error; |
lorevee | 0:1902469bdd2d | 301 | |
lorevee | 0:1902469bdd2d | 302 | if (error != BLE_ERROR_NONE) { |
lorevee | 0:1902469bdd2d | 303 | /* In case of error, forward the error handling to onBleInitError */ |
lorevee | 0:1902469bdd2d | 304 | onBleInitError(ble, error); |
lorevee | 0:1902469bdd2d | 305 | return; |
lorevee | 0:1902469bdd2d | 306 | } |
lorevee | 0:1902469bdd2d | 307 | |
lorevee | 0:1902469bdd2d | 308 | |
lorevee | 0:1902469bdd2d | 309 | |
lorevee | 0:1902469bdd2d | 310 | /* Ensure that it is the default instance of BLE */ |
lorevee | 0:1902469bdd2d | 311 | if (ble.getInstanceID() != BLE::DEFAULT_INSTANCE) { |
lorevee | 0:1902469bdd2d | 312 | return; |
lorevee | 0:1902469bdd2d | 313 | } |
lorevee | 0:1902469bdd2d | 314 | |
lorevee | 0:1902469bdd2d | 315 | |
lorevee | 0:1902469bdd2d | 316 | /* notification + attr writing */ |
lorevee | 0:1902469bdd2d | 317 | ble.gattServer().onDataWritten(AttributeModified_CB); |
lorevee | 0:1902469bdd2d | 318 | /* data read */ |
lorevee | 0:1902469bdd2d | 319 | ble.gattClient().onDataRead(readCharacteristicCallback); |
lorevee | 0:1902469bdd2d | 320 | /* when a peripheral node characteristics change */ |
lorevee | 0:1902469bdd2d | 321 | ble.gattClient().onHVX(onNotificationCallback); |
lorevee | 0:1902469bdd2d | 322 | /* when a peripheral descriptor is written */ |
lorevee | 0:1902469bdd2d | 323 | ble.gattClient().onDataWritten(perDescriptorWrittenCallback); |
lorevee | 0:1902469bdd2d | 324 | |
lorevee | 0:1902469bdd2d | 325 | |
lorevee | 0:1902469bdd2d | 326 | /* disconnection */ |
lorevee | 0:1902469bdd2d | 327 | ble.gap().onDisconnection(disconnectionCallback); |
lorevee | 0:1902469bdd2d | 328 | /* connection */ |
lorevee | 0:1902469bdd2d | 329 | ble.gap().onConnection(connectionCallback); |
lorevee | 4:4af40af2530e | 330 | ble.gap().setScanParams(200, 200); //(scanInterval,scanWindow)ms |
lorevee | 1:110b5e896bc9 | 331 | ble.gap().setScanTimeout(0x0004); //stop scanning after N sec |
lorevee | 0:1902469bdd2d | 332 | ble.gap().onTimeout(onStopScan); //callback when scan stops |
lorevee | 0:1902469bdd2d | 333 | |
lorevee | 0:1902469bdd2d | 334 | |
lorevee | 0:1902469bdd2d | 335 | |
lorevee | 0:1902469bdd2d | 336 | |
lorevee | 0:1902469bdd2d | 337 | /* Setup adv */ |
lorevee | 0:1902469bdd2d | 338 | ble.gap().accumulateAdvertisingPayload(GapAdvertisingData::BREDR_NOT_SUPPORTED | GapAdvertisingData::LE_GENERAL_DISCOVERABLE); |
lorevee | 0:1902469bdd2d | 339 | a0 = ble.gap().accumulateScanResponse(GapAdvertisingData::MANUFACTURER_SPECIFIC_DATA, manuf_data, sizeof(manuf_data)); |
lorevee | 0:1902469bdd2d | 340 | a1 = ble.gap().accumulateAdvertisingPayload(GapAdvertisingData::UNKNOWN); |
lorevee | 0:1902469bdd2d | 341 | a2 = ble.gap().accumulateAdvertisingPayload(GapAdvertisingData::COMPLETE_LOCAL_NAME, (uint8_t *)NAME_BLESTAR1, sizeof(NAME_BLESTAR1)); |
lorevee | 0:1902469bdd2d | 342 | ble.gap().setAdvertisingType(GapAdvertisingParams::ADV_CONNECTABLE_UNDIRECTED); //Advertising_Event_Type |
lorevee | 0:1902469bdd2d | 343 | ble.gap().setAdvertisingInterval(1000); //Adv_Interval |
lorevee | 0:1902469bdd2d | 344 | a3 = ble.gap().setAdvertisingPolicyMode(Gap::ADV_POLICY_IGNORE_WHITELIST); //Adv_Filter_Policy |
lorevee | 0:1902469bdd2d | 345 | if ((a0 != BLE_ERROR_NONE) || (a1 != BLE_ERROR_NONE) || (a2 != BLE_ERROR_NONE) || (a3 != BLE_ERROR_NONE)){ |
lorevee | 0:1902469bdd2d | 346 | printf("\r\nError setup ADV\n"); |
lorevee | 0:1902469bdd2d | 347 | } |
lorevee | 0:1902469bdd2d | 348 | |
lorevee | 0:1902469bdd2d | 349 | |
lorevee | 0:1902469bdd2d | 350 | addAllServices(); |
lorevee | 0:1902469bdd2d | 351 | printMacAddress(); |
lorevee | 0:1902469bdd2d | 352 | |
lorevee | 0:1902469bdd2d | 353 | } |
lorevee | 0:1902469bdd2d | 354 | /*----------------------------------------------------------------------------*/ |
lorevee | 0:1902469bdd2d | 355 | |
lorevee | 0:1902469bdd2d | 356 | |
lorevee | 0:1902469bdd2d | 357 | |
lorevee | 4:4af40af2530e | 358 | void onBleInitError(BLE &ble, ble_error_t error){} |
lorevee | 4:4af40af2530e | 359 | /*----------------------------------------------------------------------------*/ |
lorevee | 4:4af40af2530e | 360 | |
lorevee | 4:4af40af2530e | 361 | |
lorevee | 4:4af40af2530e | 362 | |
lorevee | 4:4af40af2530e | 363 | void mainFunc(void){ |
lorevee | 4:4af40af2530e | 364 | |
lorevee | 4:4af40af2530e | 365 | if ((wifi_present) && (perDevs.status != NOTIFICATIONS_DATA_READ)){ |
lorevee | 4:4af40af2530e | 366 | |
lorevee | 4:4af40af2530e | 367 | if((new_data)){ |
lorevee | 4:4af40af2530e | 368 | prepare_json_pkt(json_buffer); |
lorevee | 4:4af40af2530e | 369 | }//if-new_data |
lorevee | 4:4af40af2530e | 370 | start_bnrg = 1; |
lorevee | 4:4af40af2530e | 371 | |
lorevee | 4:4af40af2530e | 372 | }else{ |
lorevee | 4:4af40af2530e | 373 | start_bnrg = 1; |
lorevee | 4:4af40af2530e | 374 | if (perDevs.status != NOTIFICATIONS_DATA_READ) { |
lorevee | 4:4af40af2530e | 375 | HAL_Delay(1000); |
lorevee | 4:4af40af2530e | 376 | } |
lorevee | 4:4af40af2530e | 377 | }//if-else |
lorevee | 4:4af40af2530e | 378 | |
lorevee | 4:4af40af2530e | 379 | |
lorevee | 4:4af40af2530e | 380 | if (start_bnrg){ |
lorevee | 4:4af40af2530e | 381 | eventQ.call(connectionProcess); |
lorevee | 4:4af40af2530e | 382 | } |
lorevee | 4:4af40af2530e | 383 | } |
lorevee | 4:4af40af2530e | 384 | /*----------------------------------------------------------------------------*/ |
lorevee | 4:4af40af2530e | 385 | |
lorevee | 4:4af40af2530e | 386 | |
lorevee | 4:4af40af2530e | 387 | void MQTTpublish(){ |
lorevee | 4:4af40af2530e | 388 | |
lorevee | 4:4af40af2530e | 389 | if((new_data)){ |
lorevee | 4:4af40af2530e | 390 | /* publish every 5 seconds */ |
lorevee | 4:4af40af2530e | 391 | publish(pClient); |
lorevee | 4:4af40af2530e | 392 | }//if-new_data |
lorevee | 4:4af40af2530e | 393 | } |
lorevee | 0:1902469bdd2d | 394 | /*----------------------------------------------------------------------------*/ |
lorevee | 0:1902469bdd2d | 395 | |
lorevee | 0:1902469bdd2d | 396 | |
lorevee | 0:1902469bdd2d | 397 | |
lorevee | 0:1902469bdd2d | 398 | int main() |
lorevee | 0:1902469bdd2d | 399 | { |
lorevee | 0:1902469bdd2d | 400 | printf("\r\n\n/*******************************************************\n"); |
lorevee | 0:1902469bdd2d | 401 | printf("\r* *\n"); |
lorevee | 4:4af40af2530e | 402 | printf("\r* BLESTAR1 MBED Expansion Software *\n"); |
lorevee | 0:1902469bdd2d | 403 | printf("\r* *\n"); |
lorevee | 0:1902469bdd2d | 404 | printf("\r*******************************************************/\n\n\n"); |
lorevee | 0:1902469bdd2d | 405 | |
lorevee | 4:4af40af2530e | 406 | |
lorevee | 4:4af40af2530e | 407 | #if ENABLE_WIFI |
lorevee | 4:4af40af2530e | 408 | wifi_present = ENABLE_WIFI; |
lorevee | 4:4af40af2530e | 409 | printf("\r\nWi-Fi Enabled!\n"); |
lorevee | 4:4af40af2530e | 410 | printf("\rTo edit SSID and/or Password please refer to mbed_app.json file\n"); |
lorevee | 4:4af40af2530e | 411 | |
lorevee | 4:4af40af2530e | 412 | /* QUICK START MODE */ |
lorevee | 4:4af40af2530e | 413 | quickstartMode=false; |
lorevee | 4:4af40af2530e | 414 | if (strcmp(org, "quickstart") == 0){ |
lorevee | 4:4af40af2530e | 415 | quickstartMode = true; |
lorevee | 4:4af40af2530e | 416 | } |
lorevee | 4:4af40af2530e | 417 | |
lorevee | 4:4af40af2530e | 418 | /* Connect network */ |
lorevee | 4:4af40af2530e | 419 | printf("\r\nConnecting to Access Point...\n\n"); |
lorevee | 4:4af40af2530e | 420 | NetworkInterface * network = easy_connect(true); // SSID and pw in .jason |
lorevee | 4:4af40af2530e | 421 | if (!network){ |
lorevee | 4:4af40af2530e | 422 | printf("\r\nError easy_connect\n"); |
lorevee | 4:4af40af2530e | 423 | } |
lorevee | 4:4af40af2530e | 424 | |
lorevee | 4:4af40af2530e | 425 | /* MQTT CONFIG*/ |
lorevee | 4:4af40af2530e | 426 | printf("\r\nConfiguring MQTT network...\n"); |
lorevee | 4:4af40af2530e | 427 | MQTTNetwork mqttNetwork(network); |
lorevee | 4:4af40af2530e | 428 | MQTT::Client<MQTTNetwork, Countdown, MQTT_MAX_PACKET_SIZE> client(mqttNetwork); |
lorevee | 4:4af40af2530e | 429 | pClient = &client; |
lorevee | 4:4af40af2530e | 430 | |
lorevee | 4:4af40af2530e | 431 | |
lorevee | 4:4af40af2530e | 432 | if (quickstartMode){ |
lorevee | 4:4af40af2530e | 433 | char mac[50]; // remove all : from mac |
lorevee | 4:4af40af2530e | 434 | char *digit=NULL; |
lorevee | 4:4af40af2530e | 435 | sprintf (id,"%s", ""); |
lorevee | 4:4af40af2530e | 436 | sprintf (mac,"%s",network->get_mac_address()); |
lorevee | 4:4af40af2530e | 437 | digit = strtok (mac,":"); |
lorevee | 4:4af40af2530e | 438 | while (digit != NULL) |
lorevee | 4:4af40af2530e | 439 | { |
lorevee | 4:4af40af2530e | 440 | strcat (id, digit); |
lorevee | 4:4af40af2530e | 441 | digit = strtok (NULL, ":"); |
lorevee | 4:4af40af2530e | 442 | } |
lorevee | 4:4af40af2530e | 443 | }//if-quickstart |
lorevee | 4:4af40af2530e | 444 | |
lorevee | 4:4af40af2530e | 445 | /* Connect MQTT broker */ |
lorevee | 4:4af40af2530e | 446 | printf("\r\nConnecting MQTT broker...\n"); |
lorevee | 4:4af40af2530e | 447 | attemptConnect(&client, &mqttNetwork, network); |
lorevee | 4:4af40af2530e | 448 | |
lorevee | 4:4af40af2530e | 449 | #else |
lorevee | 4:4af40af2530e | 450 | printf("\r\nWi-Fi Disabled!\n"); |
lorevee | 4:4af40af2530e | 451 | |
lorevee | 4:4af40af2530e | 452 | #endif |
lorevee | 4:4af40af2530e | 453 | |
lorevee | 4:4af40af2530e | 454 | printf("\r\n\nStarting the BLE module...\n"); |
lorevee | 4:4af40af2530e | 455 | |
lorevee | 0:1902469bdd2d | 456 | /* Create the ble instance */ |
lorevee | 0:1902469bdd2d | 457 | BLE &ble = BLE::Instance(); |
lorevee | 0:1902469bdd2d | 458 | |
lorevee | 0:1902469bdd2d | 459 | ble.onEventsToProcess(scheduleBleEventsProcessing); |
lorevee | 0:1902469bdd2d | 460 | |
lorevee | 4:4af40af2530e | 461 | /* Uncomment to debug the status*/ |
lorevee | 0:1902469bdd2d | 462 | //eventQ.call_every(20000, checkStatus); |
lorevee | 0:1902469bdd2d | 463 | |
lorevee | 0:1902469bdd2d | 464 | ble.init(bleInitComplete); |
lorevee | 0:1902469bdd2d | 465 | |
lorevee | 4:4af40af2530e | 466 | /* Start main method */ |
lorevee | 4:4af40af2530e | 467 | eventQ.call_every(100, mainFunc); |
lorevee | 4:4af40af2530e | 468 | eventQ.call_every(1000, MQTTpublish); |
lorevee | 0:1902469bdd2d | 469 | |
lorevee | 0:1902469bdd2d | 470 | //dispatch events |
lorevee | 0:1902469bdd2d | 471 | eventQ.dispatch_forever(); |
lorevee | 0:1902469bdd2d | 472 | |
lorevee | 0:1902469bdd2d | 473 | return 0; |
lorevee | 0:1902469bdd2d | 474 | } |
lorevee | 0:1902469bdd2d | 475 | /*----------------------------------------------------------------------------*/ |
lorevee | 0:1902469bdd2d | 476 | |
lorevee | 0:1902469bdd2d | 477 | |
lorevee | 0:1902469bdd2d | 478 | |
lorevee | 0:1902469bdd2d | 479 | |
lorevee | 0:1902469bdd2d | 480 |