Masa Kovacevic 2020/0229

Dependencies:   19E042PIM_MB_PINS

Committer:
tzwell
Date:
Thu Nov 25 18:58:24 2021 +0000
Revision:
0:6380a1c94d6c
Child:
1:c994530bdb3d
first publish first commit

Who changed what in which revision?

UserRevisionLine numberNew contents of line
tzwell 0:6380a1c94d6c 1 /*
tzwell 0:6380a1c94d6c 2 * Program implements MQTT client on a NUCLEO-L476RG board
tzwell 0:6380a1c94d6c 3 * using arm mbed-mqtt library and ESP-WROOM-02 WiFi modem.
tzwell 0:6380a1c94d6c 4 *
tzwell 0:6380a1c94d6c 5 * University of Belgrade - School of Electrical Engineering
tzwell 0:6380a1c94d6c 6 * Department of Electronics
tzwell 0:6380a1c94d6c 7 * Bulevar Kralja Aleksandra 73, 11120 Belgrade, Serbia
tzwell 0:6380a1c94d6c 8 *
tzwell 0:6380a1c94d6c 9 * November 2021.
tzwell 0:6380a1c94d6c 10 *
tzwell 0:6380a1c94d6c 11 */
tzwell 0:6380a1c94d6c 12
tzwell 0:6380a1c94d6c 13 #include "mbed.h"
tzwell 0:6380a1c94d6c 14 #include "mb_pins.h"
tzwell 0:6380a1c94d6c 15 #include "platform/mbed_thread.h"
tzwell 0:6380a1c94d6c 16 #include "MQTTClientMbedOs.h"
tzwell 0:6380a1c94d6c 17
tzwell 0:6380a1c94d6c 18
tzwell 0:6380a1c94d6c 19 // LED2 blinking rate:
tzwell 0:6380a1c94d6c 20 #define BLINKING_RATE_MS 250
tzwell 0:6380a1c94d6c 21 // Scaler to 3v3L
tzwell 0:6380a1c94d6c 22 #define VOLTAGE_SCALER 3.3f
tzwell 0:6380a1c94d6c 23 // Client yield timeout in miliseconds:
tzwell 0:6380a1c94d6c 24 #define YIELD_TIMEOUT_MS 1000
tzwell 0:6380a1c94d6c 25 // Maximum number of networks to scan for:
tzwell 0:6380a1c94d6c 26 #define MAX_NETWORKS 15
tzwell 0:6380a1c94d6c 27 // Small delay for network information printing:
tzwell 0:6380a1c94d6c 28 #define PRINTF_DELAY_MS 10
tzwell 0:6380a1c94d6c 29
tzwell 0:6380a1c94d6c 30
tzwell 0:6380a1c94d6c 31 // Left potentiometer:
tzwell 0:6380a1c94d6c 32 AnalogIn pot1(MB_POT1);
tzwell 0:6380a1c94d6c 33 // Left button on the motherboard:
tzwell 0:6380a1c94d6c 34 InterruptIn sw1(MB_SW1);
tzwell 0:6380a1c94d6c 35 // Right LED on the motherboard:
tzwell 0:6380a1c94d6c 36 DigitalOut led2(MB_LED2);
tzwell 0:6380a1c94d6c 37 // WiFi network handler:
tzwell 0:6380a1c94d6c 38 WiFiInterface *wifi;
tzwell 0:6380a1c94d6c 39 // Creating TCP socket:
tzwell 0:6380a1c94d6c 40 TCPSocket socket;
tzwell 0:6380a1c94d6c 41 // Creating MQTT client using the TCP socket;
tzwell 0:6380a1c94d6c 42 MQTTClient client(&socket);
tzwell 0:6380a1c94d6c 43 // Message handler:
tzwell 0:6380a1c94d6c 44 MQTT::Message message;
tzwell 0:6380a1c94d6c 45
tzwell 0:6380a1c94d6c 46 char* topic = "mbed-sample-pub";
tzwell 0:6380a1c94d6c 47 char* topic_sub = "mbed-sample-sub";
tzwell 0:6380a1c94d6c 48 // Counter of arrived messages:
tzwell 0:6380a1c94d6c 49 int arrivedcount = 0;
tzwell 0:6380a1c94d6c 50 // Flag indicating that button is not pressed:
tzwell 0:6380a1c94d6c 51 int button_pressed=0;
tzwell 0:6380a1c94d6c 52
tzwell 0:6380a1c94d6c 53 // Returning a string for a provided network encryption:
tzwell 0:6380a1c94d6c 54 const char *sec2str(nsapi_security_t sec)
tzwell 0:6380a1c94d6c 55 {
tzwell 0:6380a1c94d6c 56 switch (sec)
tzwell 0:6380a1c94d6c 57 {
tzwell 0:6380a1c94d6c 58 case NSAPI_SECURITY_NONE:
tzwell 0:6380a1c94d6c 59 return "None";
tzwell 0:6380a1c94d6c 60 case NSAPI_SECURITY_WEP:
tzwell 0:6380a1c94d6c 61 return "WEP";
tzwell 0:6380a1c94d6c 62 case NSAPI_SECURITY_WPA:
tzwell 0:6380a1c94d6c 63 return "WPA";
tzwell 0:6380a1c94d6c 64 case NSAPI_SECURITY_WPA2:
tzwell 0:6380a1c94d6c 65 return "WPA2";
tzwell 0:6380a1c94d6c 66 case NSAPI_SECURITY_WPA_WPA2:
tzwell 0:6380a1c94d6c 67 return "WPA/WPA2";
tzwell 0:6380a1c94d6c 68 case NSAPI_SECURITY_UNKNOWN:
tzwell 0:6380a1c94d6c 69 default:
tzwell 0:6380a1c94d6c 70 return "Unknown";
tzwell 0:6380a1c94d6c 71 }
tzwell 0:6380a1c94d6c 72 }
tzwell 0:6380a1c94d6c 73
tzwell 0:6380a1c94d6c 74 int scan_demo(WiFiInterface *wifi)
tzwell 0:6380a1c94d6c 75 {
tzwell 0:6380a1c94d6c 76 // Creating an access point
tzwell 0:6380a1c94d6c 77 WiFiAccessPoint *ap;
tzwell 0:6380a1c94d6c 78
tzwell 0:6380a1c94d6c 79 printf("Scan:\n");
tzwell 0:6380a1c94d6c 80
tzwell 0:6380a1c94d6c 81 int count = wifi->scan(NULL,0);
tzwell 0:6380a1c94d6c 82
tzwell 0:6380a1c94d6c 83 if (count <= 0)
tzwell 0:6380a1c94d6c 84 {
tzwell 0:6380a1c94d6c 85 printf("scan() failed with return value: %d\n", count);
tzwell 0:6380a1c94d6c 86 return 0;
tzwell 0:6380a1c94d6c 87 }
tzwell 0:6380a1c94d6c 88
tzwell 0:6380a1c94d6c 89 // Limit number of network arbitrary to 15
tzwell 0:6380a1c94d6c 90 count = count < MAX_NETWORKS ? count : MAX_NETWORKS;
tzwell 0:6380a1c94d6c 91
tzwell 0:6380a1c94d6c 92 // Create a new object, array of WiFi APs, and assign it to ap variable:
tzwell 0:6380a1c94d6c 93 ap = new WiFiAccessPoint[count];
tzwell 0:6380a1c94d6c 94 count = wifi->scan(ap, count);
tzwell 0:6380a1c94d6c 95
tzwell 0:6380a1c94d6c 96 if (count <= 0)
tzwell 0:6380a1c94d6c 97 {
tzwell 0:6380a1c94d6c 98 printf("scan() failed with return value: %d\n", count);
tzwell 0:6380a1c94d6c 99 return 0;
tzwell 0:6380a1c94d6c 100 }
tzwell 0:6380a1c94d6c 101
tzwell 0:6380a1c94d6c 102 // Print network information:
tzwell 0:6380a1c94d6c 103 for (int i = 0; i < count; i++)
tzwell 0:6380a1c94d6c 104 {
tzwell 0:6380a1c94d6c 105 printf("Network: %s secured: %s BSSID: %hhX:%hhX:%hhX:%hhx:%hhx:%hhx RSSI: %hhd Ch: %hhd\n", ap[i].get_ssid(),
tzwell 0:6380a1c94d6c 106 sec2str(ap[i].get_security()), ap[i].get_bssid()[0], ap[i].get_bssid()[1], ap[i].get_bssid()[2],
tzwell 0:6380a1c94d6c 107 ap[i].get_bssid()[3], ap[i].get_bssid()[4], ap[i].get_bssid()[5], ap[i].get_rssi(), ap[i].get_channel());
tzwell 0:6380a1c94d6c 108 thread_sleep_for(PRINTF_DELAY_MS);
tzwell 0:6380a1c94d6c 109 }
tzwell 0:6380a1c94d6c 110 printf("%d networks available.\n", count);
tzwell 0:6380a1c94d6c 111
tzwell 0:6380a1c94d6c 112 delete[] ap;
tzwell 0:6380a1c94d6c 113 return count;
tzwell 0:6380a1c94d6c 114 }
tzwell 0:6380a1c94d6c 115
tzwell 0:6380a1c94d6c 116 void messageArrived(MQTT::MessageData& md)
tzwell 0:6380a1c94d6c 117 {
tzwell 0:6380a1c94d6c 118 MQTT::Message &message = md.message;
tzwell 0:6380a1c94d6c 119 //printf("Message arrived: qos %d, retained %d, dup %d, packetid %d\r\n", message.qos, message.retained, message.dup, message.id);
tzwell 0:6380a1c94d6c 120 printf("Message from the browser: %.*s\r\n", message.payloadlen, (char*)message.payload);
tzwell 0:6380a1c94d6c 121 ++arrivedcount;
tzwell 0:6380a1c94d6c 122 }
tzwell 0:6380a1c94d6c 123
tzwell 0:6380a1c94d6c 124 void buttonFunction() {
tzwell 0:6380a1c94d6c 125
tzwell 0:6380a1c94d6c 126 button_pressed=1;
tzwell 0:6380a1c94d6c 127
tzwell 0:6380a1c94d6c 128 }
tzwell 0:6380a1c94d6c 129
tzwell 0:6380a1c94d6c 130 int main()
tzwell 0:6380a1c94d6c 131 {
tzwell 0:6380a1c94d6c 132 sw1.fall(&buttonFunction);
tzwell 0:6380a1c94d6c 133 const char* hostname = "broker.hivemq.com";
tzwell 0:6380a1c94d6c 134 int port = 1883;
tzwell 0:6380a1c94d6c 135 // Network interface
tzwell 0:6380a1c94d6c 136
tzwell 0:6380a1c94d6c 137 wifi = WiFiInterface::get_default_instance();
tzwell 0:6380a1c94d6c 138 if (!wifi) {
tzwell 0:6380a1c94d6c 139 printf("ERROR: No WiFiInterface found.\n");
tzwell 0:6380a1c94d6c 140 return -1;
tzwell 0:6380a1c94d6c 141 }
tzwell 0:6380a1c94d6c 142
tzwell 0:6380a1c94d6c 143 int count = scan_demo(wifi);
tzwell 0:6380a1c94d6c 144 if (count == 0) {
tzwell 0:6380a1c94d6c 145 printf("No WIFI APs found - can't continue further.\n");
tzwell 0:6380a1c94d6c 146 return -1;
tzwell 0:6380a1c94d6c 147 }
tzwell 0:6380a1c94d6c 148
tzwell 0:6380a1c94d6c 149 printf("\nConnecting to %s...\n", MBED_CONF_APP_WIFI_SSID);
tzwell 0:6380a1c94d6c 150 int ret = wifi->connect(MBED_CONF_APP_WIFI_SSID, MBED_CONF_APP_WIFI_PASSWORD, NSAPI_SECURITY_WPA_WPA2);
tzwell 0:6380a1c94d6c 151 if (ret != 0) {
tzwell 0:6380a1c94d6c 152 printf("\nConnection error: %d\n", ret);
tzwell 0:6380a1c94d6c 153 return -1;
tzwell 0:6380a1c94d6c 154 }
tzwell 0:6380a1c94d6c 155
tzwell 0:6380a1c94d6c 156 printf("Success\n\n");
tzwell 0:6380a1c94d6c 157 printf("MAC: %s\n", wifi->get_mac_address());
tzwell 0:6380a1c94d6c 158 printf("IP: %s\n", wifi->get_ip_address());
tzwell 0:6380a1c94d6c 159 printf("Netmask: %s\n", wifi->get_netmask());
tzwell 0:6380a1c94d6c 160 printf("Gateway: %s\n", wifi->get_gateway());
tzwell 0:6380a1c94d6c 161 printf("RSSI: %d\n\n", wifi->get_rssi());
tzwell 0:6380a1c94d6c 162
tzwell 0:6380a1c94d6c 163 socket.open(wifi);
tzwell 0:6380a1c94d6c 164 socket.connect(hostname, port);
tzwell 0:6380a1c94d6c 165
tzwell 0:6380a1c94d6c 166 MQTTPacket_connectData data = MQTTPacket_connectData_initializer;
tzwell 0:6380a1c94d6c 167 data.MQTTVersion = 3;
tzwell 0:6380a1c94d6c 168 data.clientID.cstring = "NUCLEO-L476RG-60";
tzwell 0:6380a1c94d6c 169
tzwell 0:6380a1c94d6c 170 int rc=0;
tzwell 0:6380a1c94d6c 171 if ((rc = client.connect(data)) != 0)
tzwell 0:6380a1c94d6c 172 printf("rc from MQTT connect is %d\r\n", rc);
tzwell 0:6380a1c94d6c 173
tzwell 0:6380a1c94d6c 174 if ((rc = client.subscribe(topic_sub, MQTT::QOS2, messageArrived)) != 0)
tzwell 0:6380a1c94d6c 175 printf("rc from MQTT subscribe is %d\r\n", rc);
tzwell 0:6380a1c94d6c 176
tzwell 0:6380a1c94d6c 177 while (true) {
tzwell 0:6380a1c94d6c 178 // Show that the loop is running by switching motherboard LED2:
tzwell 0:6380a1c94d6c 179 led2 = !led2;
tzwell 0:6380a1c94d6c 180 thread_sleep_for(BLINKING_RATE_MS);
tzwell 0:6380a1c94d6c 181 if (button_pressed==1) {
tzwell 0:6380a1c94d6c 182 button_pressed=0;
tzwell 0:6380a1c94d6c 183 // QoS 0
tzwell 0:6380a1c94d6c 184 char buf[100];
tzwell 0:6380a1c94d6c 185 sprintf(buf, "V(POT1) = %1.2f\r\n", pot1*VOLTAGE_SCALER);
tzwell 0:6380a1c94d6c 186 message.qos = MQTT::QOS0;
tzwell 0:6380a1c94d6c 187 message.retained = false;
tzwell 0:6380a1c94d6c 188 message.dup = false;
tzwell 0:6380a1c94d6c 189 message.payload = (void*)buf;
tzwell 0:6380a1c94d6c 190 message.payloadlen = strlen(buf)+1;
tzwell 0:6380a1c94d6c 191 client.publish(topic, message);
tzwell 0:6380a1c94d6c 192 }
tzwell 0:6380a1c94d6c 193 // Need to call yield API to maintain connection:
tzwell 0:6380a1c94d6c 194 client.yield(YIELD_TIMEOUT_MS);
tzwell 0:6380a1c94d6c 195 }
tzwell 0:6380a1c94d6c 196 }