CIS441 Proj MS 2b

Dependencies:   TextLCD MQTT

Committer:
mwgold
Date:
Thu Dec 12 21:51:10 2019 +0000
Revision:
8:c40e805eecba
Parent:
7:15c2ed6e5162
Child:
9:f5981ced0b47
publishes correctly

Who changed what in which revision?

UserRevisionLine numberNew contents of line
mwgold 4:ef8866873df5 1 #include "Communication.h"
mwgold 4:ef8866873df5 2
mwgold 4:ef8866873df5 3 MQTT::Client<MQTTNetwork, Countdown>* Communication::client(MQTT::Client<MQTTNetwork, Countdown>* new_client) {
kchen7 7:15c2ed6e5162 4 static MQTT::Client<MQTTNetwork, Countdown>* client = NULL;
mwgold 4:ef8866873df5 5 if (new_client != NULL) {
mwgold 4:ef8866873df5 6 client = new_client;
mwgold 4:ef8866873df5 7 }
mwgold 4:ef8866873df5 8 return client;
mwgold 4:ef8866873df5 9 }
mwgold 4:ef8866873df5 10
mwgold 4:ef8866873df5 11 const char* Communication::mac_address(const char* new_add) {
mwgold 4:ef8866873df5 12 static const char* mac_address = NULL;
mwgold 4:ef8866873df5 13 if (new_add != NULL) {
mwgold 4:ef8866873df5 14 mac_address = new_add;
mwgold 4:ef8866873df5 15 }
kchen7 7:15c2ed6e5162 16 //printf("mac_address %s\n", mac_address);
mwgold 4:ef8866873df5 17 return mac_address;
mwgold 4:ef8866873df5 18 }
mwgold 4:ef8866873df5 19
mwgold 4:ef8866873df5 20 Communication::Communication() {}
mwgold 4:ef8866873df5 21
mwgold 4:ef8866873df5 22 /*
mwgold 4:ef8866873df5 23 This function sets up the wifi module and connects it to the SSID
mwgold 4:ef8866873df5 24 configured in the configuration file. It also prints out the MAC address
mwgold 4:ef8866873df5 25 of the module, which is needed if you are trying to use campus wifi.
mwgold 4:ef8866873df5 26 This function returns NULL if there are any issues.
mwgold 4:ef8866873df5 27 */
mwgold 4:ef8866873df5 28 WiFiInterface* Communication::setup_wifi() {
mwgold 4:ef8866873df5 29 // Get a handle to the WiFi module
mwgold 4:ef8866873df5 30 WiFiInterface* wifi = WiFiInterface::get_default_instance();
mwgold 4:ef8866873df5 31
mwgold 4:ef8866873df5 32 // Connect the module to the wifi, based on the SSID and password
mwgold 4:ef8866873df5 33 // specified in the mbed_app.json configuration file
mwgold 4:ef8866873df5 34 // If you are using AirPennNet-Device, this will not succeed until the MAC
mwgold 4:ef8866873df5 35 // address (printed shortly after this) is registered
kchen7 7:15c2ed6e5162 36 printf("Connecting to wifi\r\n");
mwgold 4:ef8866873df5 37 int rc = wifi->connect(MBED_CONF_APP_WIFI_SSID, MBED_CONF_APP_WIFI_PASSWORD, NSAPI_SECURITY_WPA_WPA2);
mwgold 4:ef8866873df5 38
mwgold 4:ef8866873df5 39 if (rc != 0) {
kchen7 7:15c2ed6e5162 40 printf("Problem connecting to wifi\r\n");
mwgold 4:ef8866873df5 41 return NULL;
mwgold 4:ef8866873df5 42 }
kchen7 7:15c2ed6e5162 43 printf("Wifi connected\r\n");
mwgold 4:ef8866873df5 44 return wifi;
mwgold 4:ef8866873df5 45 }
mwgold 4:ef8866873df5 46
mwgold 4:ef8866873df5 47 /*
mwgold 4:ef8866873df5 48 This function creates the MQTT client and connects it to the MQTT broker
mwgold 4:ef8866873df5 49 that we have setup for the course. If there are any errors with the
mwgold 4:ef8866873df5 50 connection, it will return NULL
mwgold 4:ef8866873df5 51 */
mwgold 4:ef8866873df5 52 MQTT::Client<MQTTNetwork, Countdown>* Communication::setup_mqtt(MQTTNetwork &network) {
mwgold 4:ef8866873df5 53 // the hostname and port point to a Google Cloud MQTT server we setup for
mwgold 4:ef8866873df5 54 // this project
mwgold 4:ef8866873df5 55 const char* hostname = "34.68.206.11";
mwgold 4:ef8866873df5 56 int port = 1883;
mwgold 4:ef8866873df5 57
mwgold 4:ef8866873df5 58 // Create the underlying network connection to the MQTT server
kchen7 7:15c2ed6e5162 59 printf("Connecting to %s:%d\r\n", hostname, port);
mwgold 4:ef8866873df5 60 int rc = network.connect(hostname, port);
mwgold 4:ef8866873df5 61 if (rc != 0) {
kchen7 7:15c2ed6e5162 62 printf("There was an error with the TCP connect: %d\r\n", rc);
mwgold 4:ef8866873df5 63 return NULL;
mwgold 4:ef8866873df5 64 }
mwgold 4:ef8866873df5 65
kchen7 7:15c2ed6e5162 66 printf("Connected to %s:%d\r\n", hostname, port);
kchen7 7:15c2ed6e5162 67
mwgold 4:ef8866873df5 68 // Connect the MQTT client to the server
mwgold 4:ef8866873df5 69 MQTT::Client<MQTTNetwork, Countdown>* client = new MQTT::Client<MQTTNetwork, Countdown>(network);
mwgold 4:ef8866873df5 70 rc = client->connect();
mwgold 4:ef8866873df5 71 if (rc != 0) {
kchen7 7:15c2ed6e5162 72 printf("There was an error with the MQTT connect: %d\r\n", rc);
mwgold 4:ef8866873df5 73 return NULL;
mwgold 4:ef8866873df5 74 }
kchen7 7:15c2ed6e5162 75
kchen7 7:15c2ed6e5162 76 printf("MQTT connect successful!\r\n");
mwgold 4:ef8866873df5 77
mwgold 4:ef8866873df5 78 return client;
mwgold 4:ef8866873df5 79 }
mwgold 4:ef8866873df5 80
mwgold 4:ef8866873df5 81 //callback for update/control messages
mwgold 4:ef8866873df5 82 void Communication::update_message_arrived(MQTT::MessageData& md)
mwgold 4:ef8866873df5 83 {
mwgold 4:ef8866873df5 84 MQTT::Message &message = md.message;
mwgold 4:ef8866873df5 85 char* payload = (char*)message.payload;
mwgold 4:ef8866873df5 86 int id = payload[0] - 48;
mwgold 4:ef8866873df5 87 int speed = payload[3] - 48;
mwgold 4:ef8866873df5 88 if(message.payloadlen > 3) {
mwgold 4:ef8866873df5 89 speed = speed * 10 + payload[4] - 48;
mwgold 4:ef8866873df5 90 }
mwgold 4:ef8866873df5 91
mwgold 4:ef8866873df5 92 Road::road_in_use(NULL)->update_car_speed(id, speed);
mwgold 4:ef8866873df5 93 }
mwgold 4:ef8866873df5 94
mwgold 4:ef8866873df5 95 //callback for sync messages
mwgold 4:ef8866873df5 96 void Communication::sync_message_arrived(MQTT::MessageData& md)
mwgold 4:ef8866873df5 97 {
mwgold 4:ef8866873df5 98 MQTT::Message &message = md.message;
mwgold 4:ef8866873df5 99 char* payload = (char*)message.payload;
mwgold 4:ef8866873df5 100 if (strcmp (Communication::mac_address(NULL), payload) != 0) {
mwgold 4:ef8866873df5 101 Road::ready(1);
mwgold 4:ef8866873df5 102 }
mwgold 4:ef8866873df5 103 }
mwgold 4:ef8866873df5 104
mwgold 4:ef8866873df5 105 //initialize the client
mwgold 4:ef8866873df5 106 int Communication::init() {
mwgold 4:ef8866873df5 107 WiFiInterface* wifi = setup_wifi();
mwgold 4:ef8866873df5 108
mwgold 4:ef8866873df5 109 // There was a problem connecting the wifi, so exit
mwgold 4:ef8866873df5 110 if (wifi == NULL) {
mwgold 4:ef8866873df5 111 return -1;
mwgold 4:ef8866873df5 112 }
mwgold 4:ef8866873df5 113
mwgold 4:ef8866873df5 114 Communication::mac_address(wifi->get_mac_address());
mwgold 4:ef8866873df5 115
mwgold 4:ef8866873df5 116 // Create the network object needed by the MQTT client
kchen7 7:15c2ed6e5162 117 MQTTNetwork* network = (MQTTNetwork*)malloc(sizeof(MQTTNetwork));
kchen7 7:15c2ed6e5162 118 new (network) MQTTNetwork(wifi);
kchen7 7:15c2ed6e5162 119 //MQTTNetwork network(wifi);
kchen7 7:15c2ed6e5162 120 Communication::client(setup_mqtt(*network));
mwgold 4:ef8866873df5 121
mwgold 4:ef8866873df5 122 // There was a problem connecting the MQTT client, so exit
mwgold 4:ef8866873df5 123 if (Communication::client(NULL) == NULL) {
mwgold 4:ef8866873df5 124 return -1;
mwgold 4:ef8866873df5 125 }
mwgold 4:ef8866873df5 126
mwgold 4:ef8866873df5 127 // Subscribe to topics / register callbacks
mwgold 4:ef8866873df5 128 char buf[100];
mwgold 4:ef8866873df5 129 sprintf(buf, "Chen_Goldsmith_Update/%s", Communication::mac_address(NULL));
mwgold 4:ef8866873df5 130 char* update_topic = (char*) buf;
mwgold 4:ef8866873df5 131 int rc = Communication::client(NULL)->subscribe(update_topic, MQTT::QOS1, update_message_arrived);
mwgold 4:ef8866873df5 132 if (rc != 0) {
mwgold 4:ef8866873df5 133 return -1;
mwgold 4:ef8866873df5 134 }
mwgold 4:ef8866873df5 135 char* sync_topic = "Chen_Goldsmith_Sync";
mwgold 4:ef8866873df5 136 rc = Communication::client(NULL)->subscribe(sync_topic, MQTT::QOS1, sync_message_arrived);
mwgold 4:ef8866873df5 137 if (rc != 0) {
mwgold 4:ef8866873df5 138 return -1;
mwgold 4:ef8866873df5 139 }
mwgold 4:ef8866873df5 140
kchen7 7:15c2ed6e5162 141 printf("Successfully subscribed, init() returning 1\n");
mwgold 4:ef8866873df5 142 return 1;
mwgold 4:ef8866873df5 143 }
mwgold 4:ef8866873df5 144
mwgold 4:ef8866873df5 145 int Communication::publish_car_info(int id, int pos, int speed) {
mwgold 8:c40e805eecba 146 MQTT::Message message;
mwgold 4:ef8866873df5 147
mwgold 4:ef8866873df5 148 char* topic = "Chen_Goldsmith_Car_Info";
mwgold 8:c40e805eecba 149 char buf[50];
kchen7 7:15c2ed6e5162 150 const char* mac = Communication::mac_address(NULL);
mwgold 8:c40e805eecba 151 sprintf(buf, "%d, %d, %d, %s", id, pos, speed, mac);
kchen7 7:15c2ed6e5162 152 printf("publishing... ");
mwgold 8:c40e805eecba 153 int rc = Communication::client(NULL)->publish(topic, (char*) buf, strlen(buf), MQTT::QOS1);
mwgold 8:c40e805eecba 154 printf(" success!\r\n");
mwgold 4:ef8866873df5 155
mwgold 4:ef8866873df5 156 if (rc != 0) {
mwgold 4:ef8866873df5 157 return -1;
mwgold 4:ef8866873df5 158 } else {
mwgold 4:ef8866873df5 159 return 0;
mwgold 4:ef8866873df5 160 }
mwgold 4:ef8866873df5 161 }
mwgold 4:ef8866873df5 162
mwgold 4:ef8866873df5 163 int Communication::publish_road_ready() {
mwgold 4:ef8866873df5 164 MQTT::Message message;
mwgold 4:ef8866873df5 165
mwgold 4:ef8866873df5 166 char* topic = "Chen_Goldsmith_Sync";
mwgold 4:ef8866873df5 167 char buf[100];
mwgold 4:ef8866873df5 168 sprintf(buf, "%s", Communication::mac_address(NULL));
mwgold 4:ef8866873df5 169 int rc = Communication::client(NULL)->publish(topic, (char*) buf, strlen(buf)+1, MQTT::QOS1);
mwgold 8:c40e805eecba 170 printf("successfull publish: ready\r\n");
mwgold 4:ef8866873df5 171 if (rc != 0) {
mwgold 4:ef8866873df5 172 return -1;
mwgold 4:ef8866873df5 173 } else {
mwgold 4:ef8866873df5 174 return 0;
mwgold 4:ef8866873df5 175 }
mwgold 4:ef8866873df5 176 }
mwgold 4:ef8866873df5 177
mwgold 4:ef8866873df5 178 void Communication::disconnect() {
mwgold 4:ef8866873df5 179 Communication::client(NULL)->disconnect();
mwgold 4:ef8866873df5 180 }