989
Dependencies: mbed Servo X_NUCLEO_IKS01A2 X_NUCLEO_IDW01M1v2 NetworkSocketAPI NDefLib MQTT
main.cpp
- Committer:
- fishzhang
- Date:
- 2020-11-04
- Revision:
- 25:d7f1e43736cf
- Parent:
- 24:a59eb8bdc431
File content as of revision 25:d7f1e43736cf:
#include "mbed.h" #include "SpwfInterface.h" #include "TCPSocket.h" #include "MQTTClient.h" #include "MQTTWiFi.h" #include <ctype.h> #include "NDefLib/NDefNfcTag.h" #include "NDefLib/RecordType/RecordURI.h" #include "Servo.h" #include"XNucleoIKS01A2.h" #include "stm32f4xx_hal.h" Servo servo(D10); float range = 0.005; float position = 0.5; Serial pc(SERIAL_TX, SERIAL_RX); bool quickstartMode = true; #define ORG_QUICKSTART 101.132.47.170 // comment to connect to play.internetofthings.ibmcloud.com //#define SUBSCRIBE // uncomment to subscribe to broker msgs (not to be used with IBM broker) #define MQTT_MAX_PACKET_SIZE 250 #define MQTT_MAX_PAYLOAD_SIZE 300 // Configuration values needed to connect to IBM IoT Cloud #define BROKER_URL ".132.47.170"; #ifdef ORG_QUICKSTART #define ORG "101" // connect to quickstart.internetofthings.ibmcloud.com/ For a registered connection, replace with your org #define ID "168" #define AUTH_TOKEN "10" #define DEFAULT_TYPE_NAME "145" #else // not def ORG_QUICKSTART #define ORG "192" // connect to play.internetofthings.ibmcloud.com/ For a registered connection, replace with your org #define ID "168" // For a registered connection, replace with your id #define AUTH_TOKEN "10"// For a registered connection, replace with your auth-token #define DEFAULT_TYPE_NAME "145" #endif #define TOPIC "TempA" #define TOPIC2 "commond" #define TOPICT_hum "hum" #define TOPICT_x "x" #define TOPICT_y "y" #define TOPICT_z "z" #define TOPICT_ax "a_x" #define TOPICT_ay "a_y" #define TOPICT_az "a_z" #define TOPICT_bx "b_x" #define TOPICT_by "b_y" #define TOPICT_bz "b_z" #define TYPE DEFAULT_TYPE_NAME // For a registered connection, replace with your type #define MQTT_PORT 1883 #define MQTT_TLS_PORT 8883 #define IBM_IOT_PORT MQTT_PORT // WiFi network credential #define SSID "LongFreeMoble" // Network must be visible otherwise it can't connect #define PASSW "iots8230" #warning "Wifi SSID & password empty" char* topic = "TempA"; char id[30] = ID; // mac without colons char org[12] = ORG; int connack_rc = 0; // MQTT connack return code const char* ip_addr = ""; char* host_addr = ""; char type[30] = TYPE; char auth_token[30] = AUTH_TOKEN; // Auth_token is only used in non-quickstart mode bool netConnecting = false; int connectTimeout = 1000; bool mqttConnecting = false; bool netConnected = false; bool connected = false; int retryAttempt = 0; char subscription_url[MQTT_MAX_PAYLOAD_SIZE]; static XNucleoIKS01A2 *mems_expansion_board = XNucleoIKS01A2::instance(D14, D15, D4, D5); /* Retrieve the composing elements of the expansion board */ static LSM303AGRMagSensor *magnetometer = mems_expansion_board->magnetometer; static HTS221Sensor *hum_temp = mems_expansion_board->ht_sensor; static LPS22HBSensor *press_temp = mems_expansion_board->pt_sensor; static LSM6DSLSensor *acc_gyro = mems_expansion_board->acc_gyro; static LSM303AGRAccSensor *accelerometer = mems_expansion_board->accelerometer; class WatchDog { private: IWDG_HandleTypeDef hiwdg; public: WatchDog(uint32_t prescaler = IWDG_PRESCALER_256, uint32_t reload = 0xfff) { hiwdg.Instance = IWDG; hiwdg.Init.Prescaler = prescaler; hiwdg.Init.Reload = reload; HAL_IWDG_Init(&hiwdg); } void feed() { HAL_IWDG_Refresh(&hiwdg); } }; /* Retrieve the composing elements of the expansion board */ //PressureSensor *pressure_sensor; //HumiditySensor *humidity_sensor; //TempSensor *temp_sensor1; MQTT::Message message; MQTTString TopicName={TOPIC}; MQTT::MessageData MsgData(TopicName, message); void subscribe_cb(MQTT::MessageData & msgMQTT) { char msg[MQTT_MAX_PAYLOAD_SIZE]; msg[0]='\0'; strncat (msg, (char*)msgMQTT.message.payload, msgMQTT.message.payloadlen); printf ("--->>> subscribe_cb msg: %s\n\r", msg); printf("%d\r\n",strlen(msg)); if(strlen(msg)==2) { printf ("I AM WORKING\n\r"); int i=0; while(i<500) { i++; servo = position; position += range; if(position >= 1) { position = 0; wait(0.5); } wait(0.002); } } } int subscribe(MQTT::Client<MQTTWiFi, Countdown, MQTT_MAX_PACKET_SIZE>* client, MQTTWiFi* ipstack) { char* pubTopic = TOPIC2; printf("subscribe int finished\r\n"); return client->subscribe(pubTopic, MQTT::QOS1, subscribe_cb); } int connect(MQTT::Client<MQTTWiFi, Countdown, MQTT_MAX_PACKET_SIZE>* client, MQTTWiFi* ipstack) { const char* iot_ibm = BROKER_URL; char hostname[strlen(org) + strlen(iot_ibm) + 1]; sprintf(hostname, "%s%s", org, iot_ibm); SpwfSAInterface& WiFi = ipstack->getWiFi(); char clientId[strlen(org) + strlen(type) + strlen(id) + 5]; sprintf(clientId, "d:%s:%s:%s", org, type, id); sprintf(subscription_url, "%s.%s/#/device/%s/sensor/", org, "iots",id); // Network debug statements LOG("\n\r=====================================\n\r"); LOG("Connecting WiFi.\n\r"); LOG("Nucleo IP ADDRESS: %s\n\r", WiFi.get_ip_address()); LOG("Nucleo MAC ADDRESS: %s\n\r", WiFi.get_mac_address()); LOG("Server Hostname: %s port: %d\n\r", hostname, IBM_IOT_PORT); LOG("Client ID: %s\n\r", clientId); LOG("Topic: %s\n\r",TOPIC); LOG("Subscription URL: %s\n\r", subscription_url); LOG("=====================================\n\r"); netConnecting = true; ipstack->open(&ipstack->getWiFi()); int rc = ipstack->connect(hostname, IBM_IOT_PORT, connectTimeout); if (rc != 0) { WARN("IP Stack connect returned: %d\n", rc); return rc; } printf ("--->TCP Connected\n\r"); netConnected = true; netConnecting = false; // MQTT Connect mqttConnecting = true; MQTTPacket_connectData data = MQTTPacket_connectData_initializer; data.MQTTVersion = 4; data.struct_version=0; data.clientID.cstring = clientId; if (!quickstartMode) { data.username.cstring = "use-token-auth"; data.password.cstring = auth_token; } if ((rc = client->connect(data)) == 0) { connected = true; printf ("--->MQTT Connected\n\r"); #ifdef SUBSCRIBE if (!subscribe(client, ipstack)) printf ("--->>>MQTT subscribed to: %s\n\r",TOPIC); #endif } else { WARN("MQTT connect returned %d\n", rc); } if (rc >= 0) connack_rc = rc; mqttConnecting = false; return rc; } int getConnTimeout(int attemptNumber) { // First 10 attempts try within 3 seconds, next 10 attempts retry after every 1 minute // after 20 attempts, retry every 10 minutes return (attemptNumber < 10) ? 3 : (attemptNumber < 20) ? 60 : 600; } void attemptConnect(MQTT::Client<MQTTWiFi, Countdown, MQTT_MAX_PACKET_SIZE>* client, MQTTWiFi* ipstack) { connected = false; while (connect(client, ipstack) != MQTT_CONNECTION_ACCEPTED) { if (connack_rc == MQTT_NOT_AUTHORIZED || connack_rc == MQTT_BAD_USERNAME_OR_PASSWORD) { printf ("File: %s, Line: %d Error: %d\n\r",__FILE__,__LINE__, connack_rc); return; // don't reattempt to connect if credentials are wrong } int timeout = getConnTimeout(++retryAttempt); WARN("Retry attempt number %d waiting %d\n", retryAttempt, timeout); // if ipstack and client were on the heap we could deconstruct and goto a label where they are constructed // or maybe just add the proper members to do this disconnect and call attemptConnect(...) // this works - reset the system when the retry count gets to a threshold if (retryAttempt == 5) NVIC_SystemReset(); else wait(timeout); } } int publish(MQTT::Client<MQTTWiFi, Countdown, MQTT_MAX_PACKET_SIZE>* client, MQTTWiFi* ipstack) { MQTT::Message message; char* pubTopic = TOPIC; char buf[MQTT_MAX_PAYLOAD_SIZE]; float temp, press, hum; printf("%f\r\n",press); hum_temp->get_temperature(&temp); hum_temp->get_humidity(&hum); // temp_sensor1->GetTemperature(&temp); // humidity_sensor->GetHumidity(&hum); // pressure_sensor->GetPressure(&press); sprintf(buf,"%0.4f",temp); message.qos = MQTT::QOS1; message.retained = false; message.dup = false; message.payload = (void*)buf; message.payloadlen = strlen(buf); //message.payloadlen = sizeof(temp); // LOG("Publishing %s\n\r", buf); printf("Publishing hum %s\n\r", buf); return client->publish(pubTopic, message); } int publish2(MQTT::Client<MQTTWiFi, Countdown, MQTT_MAX_PACKET_SIZE>* client, MQTTWiFi* ipstack) { MQTT::Message message; char* pubTopic = TOPICT_hum; uint8_t id; char buf[MQTT_MAX_PAYLOAD_SIZE]; float temp, press, hum; printf("%f\r\n",press); hum_temp->get_temperature(&temp); hum_temp->get_humidity(&hum); // temp_sensor1->GetTemperature(&temp); // humidity_sensor->GetHumidity(&hum); // pressure_sensor->GetPressure(&press); sprintf(buf,"%0.4f",hum); message.qos = MQTT::QOS1; message.retained = false; message.dup = false; message.payload = (void*)buf; message.payloadlen = strlen(buf); //message.payloadlen = sizeof(temp); // LOG("Publishing %s\n\r", buf); printf("Publishing temp %s\n\r", buf); return client->publish(pubTopic, message); } int publish3(MQTT::Client<MQTTWiFi, Countdown, MQTT_MAX_PACKET_SIZE>* client, MQTTWiFi* ipstack) { int32_t axes[3]; MQTT::Message message; char* pubTopic = TOPICT_x; uint8_t id; char buf[MQTT_MAX_PAYLOAD_SIZE]; float temp, press, hum; printf("%f\r\n",press); hum_temp->get_temperature(&temp); hum_temp->get_humidity(&hum); magnetometer->get_m_axes(axes); sprintf(buf,"%0.4d",axes[0]); message.qos = MQTT::QOS1; message.retained = false; message.dup = false; message.payload = (void*)buf; message.payloadlen = strlen(buf); printf("Publishing x %s\n\r", buf); return client->publish(pubTopic, message); } int publish4(MQTT::Client<MQTTWiFi, Countdown, MQTT_MAX_PACKET_SIZE>* client, MQTTWiFi* ipstack) { int32_t axes[3]; MQTT::Message message; char* pubTopic = TOPICT_y; uint8_t id; char buf[MQTT_MAX_PAYLOAD_SIZE]; magnetometer->get_m_axes(axes); printf("axes's number%d\r\n",axes[1]); sprintf(buf,"%0.4d",axes[1]); message.qos = MQTT::QOS1; message.retained = false; message.dup = false; message.payload = (void*)buf; message.payloadlen = strlen(buf); printf("Publishing y %s\n\r", buf); return client->publish(pubTopic, message); } int publish5(MQTT::Client<MQTTWiFi, Countdown, MQTT_MAX_PACKET_SIZE>* client, MQTTWiFi* ipstack) { int32_t axes[3]; MQTT::Message message; char* pubTopic = TOPICT_z; uint8_t id; char buf[MQTT_MAX_PAYLOAD_SIZE]; float temp, press, hum; hum_temp->get_temperature(&temp); hum_temp->get_humidity(&hum); magnetometer->get_m_axes(axes); sprintf(buf,"%0.4d",axes[2]); message.qos = MQTT::QOS1; message.retained = false; message.dup = false; message.payload = (void*)buf; message.payloadlen = strlen(buf); //message.payloadlen = sizeof(temp); // LOG("Publishing %s\n\r", buf); printf("Publishing z %s\n\r", buf); return client->publish(pubTopic, message); } int publish7(MQTT::Client<MQTTWiFi, Countdown, MQTT_MAX_PACKET_SIZE>* client, MQTTWiFi* ipstack) { int32_t axes[3]; MQTT::Message message; char* pubTopic = TOPICT_ax; char buf[MQTT_MAX_PAYLOAD_SIZE]; accelerometer->get_x_axes(axes); sprintf(buf,"%0.4d",axes[0]); message.qos = MQTT::QOS0; message.retained = false; message.dup = false; message.payload = (void*)buf; message.payloadlen = strlen(buf); printf("Publishing %s\n\r", buf); return client->publish(pubTopic, message); } int publish8(MQTT::Client<MQTTWiFi, Countdown, MQTT_MAX_PACKET_SIZE>* client, MQTTWiFi* ipstack) { int32_t axes[3]; MQTT::Message message; char* pubTopic = TOPICT_ay; char buf[MQTT_MAX_PAYLOAD_SIZE]; accelerometer->get_x_axes(axes); sprintf(buf,"%0.4d",axes[1]); message.qos = MQTT::QOS0; message.retained = false; message.dup = false; message.payload = (void*)buf; message.payloadlen = strlen(buf); printf("Publishing %s\n\r", buf); return client->publish(pubTopic, message); } int publish9(MQTT::Client<MQTTWiFi, Countdown, MQTT_MAX_PACKET_SIZE>* client, MQTTWiFi* ipstack) { int32_t axes[3]; MQTT::Message message; char* pubTopic = TOPICT_az; char buf[MQTT_MAX_PAYLOAD_SIZE]; accelerometer->get_x_axes(axes); sprintf(buf,"%0.4d",axes[2]); message.qos = MQTT::QOS0; message.retained = false; message.dup = false; message.payload = (void*)buf; message.payloadlen = strlen(buf); printf("Publishing %s\n\r", buf); return client->publish(pubTopic, message); } int publish10(MQTT::Client<MQTTWiFi, Countdown, MQTT_MAX_PACKET_SIZE>* client, MQTTWiFi* ipstack) { int32_t axes[3]; MQTT::Message message; char* pubTopic = TOPICT_bx; char buf[MQTT_MAX_PAYLOAD_SIZE]; acc_gyro->get_x_axes(axes); sprintf(buf,"%0.4d",axes[0]); message.qos = MQTT::QOS0; message.retained = false; message.dup = false; message.payload = (void*)buf; message.payloadlen = strlen(buf); printf("Publishing %s\n\r", buf); return client->publish(pubTopic, message); } int publish11(MQTT::Client<MQTTWiFi, Countdown, MQTT_MAX_PACKET_SIZE>* client, MQTTWiFi* ipstack) { int32_t axes[3]; MQTT::Message message; char* pubTopic = TOPICT_by; char buf[MQTT_MAX_PAYLOAD_SIZE]; acc_gyro->get_x_axes(axes); sprintf(buf,"%0.4d",axes[1]); message.qos = MQTT::QOS0; message.retained = false; message.dup = false; message.payload = (void*)buf; message.payloadlen = strlen(buf); printf("Publishing %s\n\r", buf); return client->publish(pubTopic, message); } int publish12(MQTT::Client<MQTTWiFi, Countdown, MQTT_MAX_PACKET_SIZE>* client, MQTTWiFi* ipstack) { int32_t axes[3]; MQTT::Message message; char* pubTopic = TOPICT_bz; char buf[MQTT_MAX_PAYLOAD_SIZE]; acc_gyro->get_x_axes(axes); sprintf(buf,"%0.4d",axes[2]); message.qos = MQTT::QOS0; message.retained = false; message.dup = false; message.payload = (void*)buf; message.payloadlen = strlen(buf); printf("Publishing %s\n\r", buf); return client->publish(pubTopic, message); } int main() { const char * ssid = SSID; // Network must be visible otherwise it can't connect const char * seckey = PASSW; SpwfSAInterface spwf(D8, D2, false); DevI2C *i2c = new DevI2C(I2C_SDA, I2C_SCL); i2c->frequency(400000); pc.printf("\r\nX-NUCLEO-IDW01M1 mbed Application\r\n"); pc.printf("\r\nconnecting to AP\r\n"); hum_temp->enable(); press_temp->enable(); magnetometer->enable(); accelerometer->enable(); acc_gyro->enable_x(); acc_gyro->enable_g(); quickstartMode=false; if (strcmp(org, "quickstart") == 0){quickstartMode = true;} MQTTWiFi ipstack(spwf, ssid, seckey, NSAPI_SECURITY_WPA2); MQTT::Client<MQTTWiFi, Countdown, MQTT_MAX_PACKET_SIZE> client(ipstack); if (quickstartMode){ char mac[50]; // remove all : from mac char *digit=NULL; sprintf (id,"%s", ""); sprintf (mac,"%s",ipstack.getWiFi().get_mac_address()); digit = strtok (mac,":"); while (digit != NULL) { strcat (id, digit); digit = strtok (NULL, ":"); } } attemptConnect(&client, &ipstack); if (connack_rc == MQTT_NOT_AUTHORIZED || connack_rc == MQTT_BAD_USERNAME_OR_PASSWORD) { while (true) wait(1.0); // Permanent failures - don't retry } WatchDog wdg(IWDG_PRESCALER_64, 62500); int count = 0; // tyeld.start(); while (true) { wdg.feed(); if (++count == 100) { if(subscribe(&client, &ipstack)>30){ printf("ok \n\r"); } publish2(&client, &ipstack); publish3(&client, &ipstack); publish4(&client, &ipstack); publish5(&client, &ipstack); publish5(&client, &ipstack); publish7(&client, &ipstack); publish8(&client, &ipstack); publish9(&client, &ipstack); publish10(&client, &ipstack); publish11(&client, &ipstack); publish12(&client, &ipstack); if (publish(&client, &ipstack) != 0) { attemptConnect(&client, &ipstack); // if we have lost the connection } count = 0; } client.yield(10); } }