A small footprint MQTT library

Dependents:   STM32F746_iothub_client_sample_mqtt FXOS8700CQ_To_Azure_IoT f767zi_mqtt FXOS8700CQ_To_Azure_IoT ... more

Committer:
AzureIoTClient
Date:
Sun Apr 24 16:40:45 2016 -0700
Revision:
1:8dba42ff9701
Parent:
0:ef4901974abc
Child:
3:9b4e7158ca0d
1.0.5

Who changed what in which revision?

UserRevisionLine numberNew contents of line
Azure.IoT Build 0:ef4901974abc 1 // Copyright (c) Microsoft. All rights reserved.
Azure.IoT Build 0:ef4901974abc 2 // Licensed under the MIT license. See LICENSE file in the project root for full license information.
Azure.IoT Build 0:ef4901974abc 3
Azure.IoT Build 0:ef4901974abc 4 #include <stdlib.h>
Azure.IoT Build 0:ef4901974abc 5 #include "azure_c_shared_utility/gballoc.h"
Azure.IoT Build 0:ef4901974abc 6 #include "azure_c_shared_utility/platform.h"
Azure.IoT Build 0:ef4901974abc 7 #include "azure_c_shared_utility/tickcounter.h"
Azure.IoT Build 0:ef4901974abc 8 #include "azure_c_shared_utility/crt_abstractions.h"
Azure.IoT Build 0:ef4901974abc 9
Azure.IoT Build 0:ef4901974abc 10 #include "azure_umqtt_c/mqtt_client.h"
Azure.IoT Build 0:ef4901974abc 11 #include "azure_umqtt_c/mqtt_codec.h"
AzureIoTClient 1:8dba42ff9701 12 #include <time.h>
Azure.IoT Build 0:ef4901974abc 13
Azure.IoT Build 0:ef4901974abc 14 #define KEEP_ALIVE_BUFFER_SEC 10
Azure.IoT Build 0:ef4901974abc 15 #define VARIABLE_HEADER_OFFSET 2
Azure.IoT Build 0:ef4901974abc 16 #define RETAIN_FLAG_MASK 0x1
Azure.IoT Build 0:ef4901974abc 17 #define QOS_LEAST_ONCE_FLAG_MASK 0x2
Azure.IoT Build 0:ef4901974abc 18 #define QOS_EXACTLY_ONCE_FLAG_MASK 0x4
Azure.IoT Build 0:ef4901974abc 19 #define DUPLICATE_FLAG_MASK 0x8
Azure.IoT Build 0:ef4901974abc 20 #define CONNECT_PACKET_MASK 0xf0
AzureIoTClient 1:8dba42ff9701 21 #define TIME_MAX_BUFFER 16
Azure.IoT Build 0:ef4901974abc 22
Azure.IoT Build 0:ef4901974abc 23 static const char* FORMAT_HEX_CHAR = "0x%02x ";
Azure.IoT Build 0:ef4901974abc 24
Azure.IoT Build 0:ef4901974abc 25 typedef struct MQTT_CLIENT_TAG
Azure.IoT Build 0:ef4901974abc 26 {
Azure.IoT Build 0:ef4901974abc 27 XIO_HANDLE xioHandle;
Azure.IoT Build 0:ef4901974abc 28 MQTTCODEC_HANDLE codec_handle;
Azure.IoT Build 0:ef4901974abc 29 CONTROL_PACKET_TYPE packetState;
Azure.IoT Build 0:ef4901974abc 30 LOGGER_LOG logFunc;
Azure.IoT Build 0:ef4901974abc 31 TICK_COUNTER_HANDLE packetTickCntr;
Azure.IoT Build 0:ef4901974abc 32 uint64_t packetSendTimeMs;
Azure.IoT Build 0:ef4901974abc 33 ON_MQTT_OPERATION_CALLBACK fnOperationCallback;
Azure.IoT Build 0:ef4901974abc 34 ON_MQTT_MESSAGE_RECV_CALLBACK fnMessageRecv;
Azure.IoT Build 0:ef4901974abc 35 void* ctx;
Azure.IoT Build 0:ef4901974abc 36 QOS_VALUE qosValue;
Azure.IoT Build 0:ef4901974abc 37 uint16_t keepAliveInterval;
Azure.IoT Build 0:ef4901974abc 38 MQTT_CLIENT_OPTIONS mqttOptions;
Azure.IoT Build 0:ef4901974abc 39 bool clientConnected;
Azure.IoT Build 0:ef4901974abc 40 bool socketConnected;
Azure.IoT Build 0:ef4901974abc 41 bool logTrace;
Azure.IoT Build 0:ef4901974abc 42 bool rawBytesTrace;
Azure.IoT Build 0:ef4901974abc 43 } MQTT_CLIENT;
Azure.IoT Build 0:ef4901974abc 44
Azure.IoT Build 0:ef4901974abc 45 static uint16_t byteutil_read_uint16(uint8_t** buffer)
Azure.IoT Build 0:ef4901974abc 46 {
Azure.IoT Build 0:ef4901974abc 47 uint16_t result = 0;
Azure.IoT Build 0:ef4901974abc 48 if (buffer != NULL)
Azure.IoT Build 0:ef4901974abc 49 {
Azure.IoT Build 0:ef4901974abc 50 result = 256 * ((uint8_t)(**buffer)) + (uint8_t)(*(*buffer + 1));
Azure.IoT Build 0:ef4901974abc 51 *buffer += 2; // Move the ptr
Azure.IoT Build 0:ef4901974abc 52 }
Azure.IoT Build 0:ef4901974abc 53 return result;
Azure.IoT Build 0:ef4901974abc 54 }
Azure.IoT Build 0:ef4901974abc 55
Azure.IoT Build 0:ef4901974abc 56 static char* byteutil_readUTF(uint8_t** buffer, size_t* byteLen)
Azure.IoT Build 0:ef4901974abc 57 {
Azure.IoT Build 0:ef4901974abc 58 char* result = NULL;
Azure.IoT Build 0:ef4901974abc 59 if (buffer != NULL)
Azure.IoT Build 0:ef4901974abc 60 {
Azure.IoT Build 0:ef4901974abc 61 // Get the length of the string
Azure.IoT Build 0:ef4901974abc 62 int len = byteutil_read_uint16(buffer);
Azure.IoT Build 0:ef4901974abc 63 if (len > 0)
Azure.IoT Build 0:ef4901974abc 64 {
Azure.IoT Build 0:ef4901974abc 65 result = (char*)malloc(len + 1);
Azure.IoT Build 0:ef4901974abc 66 if (result != NULL)
Azure.IoT Build 0:ef4901974abc 67 {
Azure.IoT Build 0:ef4901974abc 68 (void)memcpy(result, *buffer, len);
Azure.IoT Build 0:ef4901974abc 69 result[len] = '\0';
Azure.IoT Build 0:ef4901974abc 70 *buffer += len;
Azure.IoT Build 0:ef4901974abc 71 if (byteLen != NULL)
Azure.IoT Build 0:ef4901974abc 72 {
Azure.IoT Build 0:ef4901974abc 73 *byteLen = len;
Azure.IoT Build 0:ef4901974abc 74 }
Azure.IoT Build 0:ef4901974abc 75 }
Azure.IoT Build 0:ef4901974abc 76 }
Azure.IoT Build 0:ef4901974abc 77 }
Azure.IoT Build 0:ef4901974abc 78 return result;
Azure.IoT Build 0:ef4901974abc 79 }
Azure.IoT Build 0:ef4901974abc 80
Azure.IoT Build 0:ef4901974abc 81 static uint8_t byteutil_readByte(uint8_t** buffer)
Azure.IoT Build 0:ef4901974abc 82 {
Azure.IoT Build 0:ef4901974abc 83 uint8_t result = 0;
Azure.IoT Build 0:ef4901974abc 84 if (buffer != NULL)
Azure.IoT Build 0:ef4901974abc 85 {
Azure.IoT Build 0:ef4901974abc 86 result = **buffer;
Azure.IoT Build 0:ef4901974abc 87 (*buffer)++;
Azure.IoT Build 0:ef4901974abc 88 }
Azure.IoT Build 0:ef4901974abc 89 return result;
Azure.IoT Build 0:ef4901974abc 90 }
Azure.IoT Build 0:ef4901974abc 91
Azure.IoT Build 0:ef4901974abc 92 static void sendComplete(void* context, IO_SEND_RESULT send_result)
Azure.IoT Build 0:ef4901974abc 93 {
Azure.IoT Build 0:ef4901974abc 94 MQTT_CLIENT* mqttData = (MQTT_CLIENT*)context;
Azure.IoT Build 0:ef4901974abc 95 if (mqttData != NULL && mqttData->fnOperationCallback != NULL)
Azure.IoT Build 0:ef4901974abc 96 {
Azure.IoT Build 0:ef4901974abc 97 if (mqttData->packetState == DISCONNECT_TYPE)
Azure.IoT Build 0:ef4901974abc 98 {
Azure.IoT Build 0:ef4901974abc 99 /*Codes_SRS_MQTT_CLIENT_07_032: [If the actionResult parameter is of type MQTT_CLIENT_ON_DISCONNECT or MQTT_CLIENT_ON_ERROR the the msgInfo value shall be NULL.]*/
Azure.IoT Build 0:ef4901974abc 100 mqttData->fnOperationCallback(mqttData, MQTT_CLIENT_ON_DISCONNECT, NULL, mqttData->ctx);
Azure.IoT Build 0:ef4901974abc 101
Azure.IoT Build 0:ef4901974abc 102 // close the xio
Azure.IoT Build 0:ef4901974abc 103 (void)xio_close(mqttData->xioHandle, NULL, mqttData->ctx);
Azure.IoT Build 0:ef4901974abc 104 mqttData->socketConnected = false;
Azure.IoT Build 0:ef4901974abc 105 mqttData->clientConnected = false;
Azure.IoT Build 0:ef4901974abc 106 }
Azure.IoT Build 0:ef4901974abc 107 }
Azure.IoT Build 0:ef4901974abc 108 }
Azure.IoT Build 0:ef4901974abc 109
Azure.IoT Build 0:ef4901974abc 110 static const char* retrievePacketType(CONTROL_PACKET_TYPE packet)
Azure.IoT Build 0:ef4901974abc 111 {
Azure.IoT Build 0:ef4901974abc 112 switch (packet&CONNECT_PACKET_MASK)
Azure.IoT Build 0:ef4901974abc 113 {
Azure.IoT Build 0:ef4901974abc 114 case CONNECT_TYPE: return "CONNECT";
Azure.IoT Build 0:ef4901974abc 115 case CONNACK_TYPE: return "CONNACK";
Azure.IoT Build 0:ef4901974abc 116 case PUBLISH_TYPE: return "PUBLISH";
Azure.IoT Build 0:ef4901974abc 117 case PUBACK_TYPE: return "PUBACK";
Azure.IoT Build 0:ef4901974abc 118 case PUBREC_TYPE: return "PUBREC";
Azure.IoT Build 0:ef4901974abc 119 case PUBREL_TYPE: return "PUBREL";
Azure.IoT Build 0:ef4901974abc 120 case SUBSCRIBE_TYPE: return "SUBSCRIBE";
Azure.IoT Build 0:ef4901974abc 121 case SUBACK_TYPE: return "SUBACK";
Azure.IoT Build 0:ef4901974abc 122 case UNSUBSCRIBE_TYPE: return "UNSUBSCRIBE";
Azure.IoT Build 0:ef4901974abc 123 case UNSUBACK_TYPE: return "UNSUBACK";
Azure.IoT Build 0:ef4901974abc 124 case PINGREQ_TYPE: return "PINGREQ";
Azure.IoT Build 0:ef4901974abc 125 case PINGRESP_TYPE: return "PINGRESP";
Azure.IoT Build 0:ef4901974abc 126 case DISCONNECT_TYPE: return "DISCONNECT";
Azure.IoT Build 0:ef4901974abc 127 default:
Azure.IoT Build 0:ef4901974abc 128 case PACKET_TYPE_ERROR:
Azure.IoT Build 0:ef4901974abc 129 case UNKNOWN_TYPE:
Azure.IoT Build 0:ef4901974abc 130 return "UNKNOWN";
Azure.IoT Build 0:ef4901974abc 131 }
Azure.IoT Build 0:ef4901974abc 132 }
Azure.IoT Build 0:ef4901974abc 133
AzureIoTClient 1:8dba42ff9701 134 static void getLogTime(char* timeResult, size_t len)
AzureIoTClient 1:8dba42ff9701 135 {
AzureIoTClient 1:8dba42ff9701 136 if (timeResult != NULL)
AzureIoTClient 1:8dba42ff9701 137 {
AzureIoTClient 1:8dba42ff9701 138 time_t localTime = time(NULL);
AzureIoTClient 1:8dba42ff9701 139 struct tm* tmInfo = localtime(&localTime);
AzureIoTClient 1:8dba42ff9701 140 if (strftime(timeResult, len, "%H:%M:%S", tmInfo) == 0)
AzureIoTClient 1:8dba42ff9701 141 {
AzureIoTClient 1:8dba42ff9701 142 timeResult[0] = '\0';
AzureIoTClient 1:8dba42ff9701 143 }
AzureIoTClient 1:8dba42ff9701 144 }
AzureIoTClient 1:8dba42ff9701 145 }
AzureIoTClient 1:8dba42ff9701 146
Azure.IoT Build 0:ef4901974abc 147 static void logOutgoingingMsgTrace(MQTT_CLIENT* clientData, const uint8_t* data, size_t length)
Azure.IoT Build 0:ef4901974abc 148 {
Azure.IoT Build 0:ef4901974abc 149 if (clientData != NULL && data != NULL && length > 0 && clientData->logTrace)
Azure.IoT Build 0:ef4901974abc 150 {
AzureIoTClient 1:8dba42ff9701 151 char tmBuffer[TIME_MAX_BUFFER];
AzureIoTClient 1:8dba42ff9701 152 getLogTime(tmBuffer, TIME_MAX_BUFFER);
AzureIoTClient 1:8dba42ff9701 153
AzureIoTClient 1:8dba42ff9701 154 LOG(clientData->logFunc, 0, "-> %s %s: ", tmBuffer, retrievePacketType((unsigned char)data[0]));
Azure.IoT Build 0:ef4901974abc 155 for (size_t index = 0; index < length; index++)
Azure.IoT Build 0:ef4901974abc 156 {
AzureIoTClient 1:8dba42ff9701 157 LOG(clientData->logFunc, 0, (char*)FORMAT_HEX_CHAR, data[index]);
Azure.IoT Build 0:ef4901974abc 158 }
Azure.IoT Build 0:ef4901974abc 159 LOG(clientData->logFunc, LOG_LINE, "");
Azure.IoT Build 0:ef4901974abc 160 }
Azure.IoT Build 0:ef4901974abc 161 }
Azure.IoT Build 0:ef4901974abc 162
Azure.IoT Build 0:ef4901974abc 163 static void logIncomingMsgTrace(MQTT_CLIENT* clientData, CONTROL_PACKET_TYPE packet, int flags, const uint8_t* data, size_t length)
Azure.IoT Build 0:ef4901974abc 164 {
Azure.IoT Build 0:ef4901974abc 165 if (clientData != NULL && data != NULL && length > 0 && clientData->logTrace)
Azure.IoT Build 0:ef4901974abc 166 {
AzureIoTClient 1:8dba42ff9701 167 char tmBuffer[TIME_MAX_BUFFER];
AzureIoTClient 1:8dba42ff9701 168 getLogTime(tmBuffer, TIME_MAX_BUFFER);
AzureIoTClient 1:8dba42ff9701 169
AzureIoTClient 1:8dba42ff9701 170 LOG(clientData->logFunc, 0, "<- %s %s: 0x%02x 0x%02x ", tmBuffer, retrievePacketType((unsigned char)packet), (unsigned char)(packet | flags), length);
Azure.IoT Build 0:ef4901974abc 171 for (size_t index = 0; index < length; index++)
Azure.IoT Build 0:ef4901974abc 172 {
AzureIoTClient 1:8dba42ff9701 173 LOG(clientData->logFunc, 0, (char*)FORMAT_HEX_CHAR, data[index]);
Azure.IoT Build 0:ef4901974abc 174 }
Azure.IoT Build 0:ef4901974abc 175 LOG(clientData->logFunc, LOG_LINE, "");
Azure.IoT Build 0:ef4901974abc 176 }
Azure.IoT Build 0:ef4901974abc 177 }
Azure.IoT Build 0:ef4901974abc 178
Azure.IoT Build 0:ef4901974abc 179 static int sendPacketItem(MQTT_CLIENT* clientData, const int8_t* data, size_t length)
Azure.IoT Build 0:ef4901974abc 180 {
Azure.IoT Build 0:ef4901974abc 181 int result;
Azure.IoT Build 0:ef4901974abc 182 logOutgoingingMsgTrace(clientData, data, length);
Azure.IoT Build 0:ef4901974abc 183
Azure.IoT Build 0:ef4901974abc 184 if (tickcounter_get_current_ms(clientData->packetTickCntr, &clientData->packetSendTimeMs) != 0)
Azure.IoT Build 0:ef4901974abc 185 {
Azure.IoT Build 0:ef4901974abc 186 LOG(clientData->logFunc, LOG_LINE, "Failure getting current ms tickcounter");
Azure.IoT Build 0:ef4901974abc 187 result = __LINE__;
Azure.IoT Build 0:ef4901974abc 188 }
Azure.IoT Build 0:ef4901974abc 189 else
Azure.IoT Build 0:ef4901974abc 190 {
Azure.IoT Build 0:ef4901974abc 191 result = xio_send(clientData->xioHandle, data, length, sendComplete, clientData);
Azure.IoT Build 0:ef4901974abc 192 if (result != 0)
Azure.IoT Build 0:ef4901974abc 193 {
Azure.IoT Build 0:ef4901974abc 194 LOG(clientData->logFunc, LOG_LINE, "%d: Failure sending control packet data", result);
Azure.IoT Build 0:ef4901974abc 195 result = __LINE__;
Azure.IoT Build 0:ef4901974abc 196 }
Azure.IoT Build 0:ef4901974abc 197 }
Azure.IoT Build 0:ef4901974abc 198 return result;
Azure.IoT Build 0:ef4901974abc 199 }
Azure.IoT Build 0:ef4901974abc 200
Azure.IoT Build 0:ef4901974abc 201 static void onOpenComplete(void* context, IO_OPEN_RESULT open_result)
Azure.IoT Build 0:ef4901974abc 202 {
Azure.IoT Build 0:ef4901974abc 203 MQTT_CLIENT* mqttData = (MQTT_CLIENT*)context;
Azure.IoT Build 0:ef4901974abc 204 if (mqttData != NULL)
Azure.IoT Build 0:ef4901974abc 205 {
Azure.IoT Build 0:ef4901974abc 206 if (open_result == IO_OPEN_OK && !mqttData->socketConnected)
Azure.IoT Build 0:ef4901974abc 207 {
Azure.IoT Build 0:ef4901974abc 208 mqttData->packetState = CONNECT_TYPE;
Azure.IoT Build 0:ef4901974abc 209 mqttData->socketConnected = true;
Azure.IoT Build 0:ef4901974abc 210 // Send the Connect packet
Azure.IoT Build 0:ef4901974abc 211 BUFFER_HANDLE connPacket = mqtt_codec_connect(&mqttData->mqttOptions);
Azure.IoT Build 0:ef4901974abc 212 if (connPacket == NULL)
Azure.IoT Build 0:ef4901974abc 213 {
Azure.IoT Build 0:ef4901974abc 214 /*Codes_SRS_MQTT_CLIENT_07_007: [If any failure is encountered then mqtt_client_connect shall return a non-zero value.]*/
Azure.IoT Build 0:ef4901974abc 215 LOG(mqttData->logFunc, LOG_LINE, "Error: mqtt_codec_connect failed");
Azure.IoT Build 0:ef4901974abc 216 }
Azure.IoT Build 0:ef4901974abc 217 else
Azure.IoT Build 0:ef4901974abc 218 {
Azure.IoT Build 0:ef4901974abc 219 /*Codes_SRS_MQTT_CLIENT_07_009: [On success mqtt_client_connect shall send the MQTT CONNECT to the endpoint.]*/
Azure.IoT Build 0:ef4901974abc 220 if (sendPacketItem(mqttData, BUFFER_u_char(connPacket), BUFFER_length(connPacket)) != 0)
Azure.IoT Build 0:ef4901974abc 221 {
Azure.IoT Build 0:ef4901974abc 222 /*Codes_SRS_MQTT_CLIENT_07_007: [If any failure is encountered then mqtt_client_connect shall return a non-zero value.]*/
Azure.IoT Build 0:ef4901974abc 223 LOG(mqttData->logFunc, LOG_LINE, "Error: mqtt_codec_connect failed");
Azure.IoT Build 0:ef4901974abc 224 }
Azure.IoT Build 0:ef4901974abc 225 BUFFER_delete(connPacket);
Azure.IoT Build 0:ef4901974abc 226 }
Azure.IoT Build 0:ef4901974abc 227 }
Azure.IoT Build 0:ef4901974abc 228 else if (open_result == IO_OPEN_ERROR)
Azure.IoT Build 0:ef4901974abc 229 {
Azure.IoT Build 0:ef4901974abc 230 (void)mqttData->fnOperationCallback(mqttData, MQTT_CLIENT_ON_ERROR, NULL, mqttData->ctx);
Azure.IoT Build 0:ef4901974abc 231 }
Azure.IoT Build 0:ef4901974abc 232 }
Azure.IoT Build 0:ef4901974abc 233 }
Azure.IoT Build 0:ef4901974abc 234
Azure.IoT Build 0:ef4901974abc 235 static void onBytesReceived(void* context, const unsigned char* buffer, size_t size)
Azure.IoT Build 0:ef4901974abc 236 {
Azure.IoT Build 0:ef4901974abc 237 MQTT_CLIENT* mqttData = (MQTT_CLIENT*)context;
Azure.IoT Build 0:ef4901974abc 238 if (mqttData != NULL)
Azure.IoT Build 0:ef4901974abc 239 {
Azure.IoT Build 0:ef4901974abc 240 if (mqtt_codec_bytesReceived(mqttData->codec_handle, buffer, size) != 0)
Azure.IoT Build 0:ef4901974abc 241 {
Azure.IoT Build 0:ef4901974abc 242 if (mqttData->fnOperationCallback)
Azure.IoT Build 0:ef4901974abc 243 {
Azure.IoT Build 0:ef4901974abc 244 mqttData->fnOperationCallback(mqttData, MQTT_CLIENT_ON_ERROR, NULL, mqttData->ctx);
Azure.IoT Build 0:ef4901974abc 245 }
Azure.IoT Build 0:ef4901974abc 246 }
Azure.IoT Build 0:ef4901974abc 247 }
Azure.IoT Build 0:ef4901974abc 248 }
Azure.IoT Build 0:ef4901974abc 249
Azure.IoT Build 0:ef4901974abc 250 static void onIoError(void* context)
Azure.IoT Build 0:ef4901974abc 251 {
Azure.IoT Build 0:ef4901974abc 252 MQTT_CLIENT* mqttData = (MQTT_CLIENT*)context;
Azure.IoT Build 0:ef4901974abc 253 if (mqttData != NULL && mqttData->fnOperationCallback)
Azure.IoT Build 0:ef4901974abc 254 {
Azure.IoT Build 0:ef4901974abc 255 /*Codes_SRS_MQTT_CLIENT_07_032: [If the actionResult parameter is of type MQTT_CLIENT_ON_DISCONNECT or MQTT_CLIENT_ON_ERROR the the msgInfo value shall be NULL.]*/
Azure.IoT Build 0:ef4901974abc 256 mqttData->fnOperationCallback(mqttData, MQTT_CLIENT_ON_ERROR, NULL, mqttData->ctx);
Azure.IoT Build 0:ef4901974abc 257 mqttData->socketConnected = false;
Azure.IoT Build 0:ef4901974abc 258 }
Azure.IoT Build 0:ef4901974abc 259 }
Azure.IoT Build 0:ef4901974abc 260
Azure.IoT Build 0:ef4901974abc 261 static int cloneMqttOptions(MQTT_CLIENT* mqttData, const MQTT_CLIENT_OPTIONS* mqttOptions)
Azure.IoT Build 0:ef4901974abc 262 {
Azure.IoT Build 0:ef4901974abc 263 int result = 0;
Azure.IoT Build 0:ef4901974abc 264 if (mqttOptions->clientId != NULL)
Azure.IoT Build 0:ef4901974abc 265 {
Azure.IoT Build 0:ef4901974abc 266 if (mallocAndStrcpy_s(&mqttData->mqttOptions.clientId, mqttOptions->clientId) != 0)
Azure.IoT Build 0:ef4901974abc 267 {
Azure.IoT Build 0:ef4901974abc 268 result = __LINE__;
Azure.IoT Build 0:ef4901974abc 269 }
Azure.IoT Build 0:ef4901974abc 270 }
Azure.IoT Build 0:ef4901974abc 271 if (result == 0 && mqttOptions->willTopic != NULL)
Azure.IoT Build 0:ef4901974abc 272 {
Azure.IoT Build 0:ef4901974abc 273 if (mallocAndStrcpy_s(&mqttData->mqttOptions.willTopic, mqttOptions->willTopic) != 0)
Azure.IoT Build 0:ef4901974abc 274 {
Azure.IoT Build 0:ef4901974abc 275 result = __LINE__;
Azure.IoT Build 0:ef4901974abc 276 }
Azure.IoT Build 0:ef4901974abc 277 }
Azure.IoT Build 0:ef4901974abc 278 if (result == 0 && mqttOptions->willMessage != NULL)
Azure.IoT Build 0:ef4901974abc 279 {
Azure.IoT Build 0:ef4901974abc 280 if (mallocAndStrcpy_s(&mqttData->mqttOptions.willMessage, mqttOptions->willMessage) != 0)
Azure.IoT Build 0:ef4901974abc 281 {
Azure.IoT Build 0:ef4901974abc 282 result = __LINE__;
Azure.IoT Build 0:ef4901974abc 283 }
Azure.IoT Build 0:ef4901974abc 284 }
Azure.IoT Build 0:ef4901974abc 285 if (result == 0 && mqttOptions->username != NULL)
Azure.IoT Build 0:ef4901974abc 286 {
Azure.IoT Build 0:ef4901974abc 287 if (mallocAndStrcpy_s(&mqttData->mqttOptions.username, mqttOptions->username) != 0)
Azure.IoT Build 0:ef4901974abc 288 {
Azure.IoT Build 0:ef4901974abc 289 result = __LINE__;
Azure.IoT Build 0:ef4901974abc 290 }
Azure.IoT Build 0:ef4901974abc 291 }
Azure.IoT Build 0:ef4901974abc 292 if (result == 0 && mqttOptions->password != NULL)
Azure.IoT Build 0:ef4901974abc 293 {
Azure.IoT Build 0:ef4901974abc 294 if (mallocAndStrcpy_s(&mqttData->mqttOptions.password, mqttOptions->password) != 0)
Azure.IoT Build 0:ef4901974abc 295 {
Azure.IoT Build 0:ef4901974abc 296 result = __LINE__;
Azure.IoT Build 0:ef4901974abc 297 }
Azure.IoT Build 0:ef4901974abc 298 }
Azure.IoT Build 0:ef4901974abc 299 if (result == 0)
Azure.IoT Build 0:ef4901974abc 300 {
Azure.IoT Build 0:ef4901974abc 301 mqttData->mqttOptions.keepAliveInterval = mqttOptions->keepAliveInterval;
Azure.IoT Build 0:ef4901974abc 302 mqttData->mqttOptions.messageRetain = mqttOptions->messageRetain;
Azure.IoT Build 0:ef4901974abc 303 mqttData->mqttOptions.useCleanSession = mqttOptions->useCleanSession;
Azure.IoT Build 0:ef4901974abc 304 mqttData->mqttOptions.qualityOfServiceValue = mqttOptions->qualityOfServiceValue;
Azure.IoT Build 0:ef4901974abc 305 }
Azure.IoT Build 0:ef4901974abc 306 else
Azure.IoT Build 0:ef4901974abc 307 {
Azure.IoT Build 0:ef4901974abc 308 free(mqttData->mqttOptions.clientId);
Azure.IoT Build 0:ef4901974abc 309 free(mqttData->mqttOptions.willTopic);
Azure.IoT Build 0:ef4901974abc 310 free(mqttData->mqttOptions.willMessage);
Azure.IoT Build 0:ef4901974abc 311 free(mqttData->mqttOptions.username);
Azure.IoT Build 0:ef4901974abc 312 free(mqttData->mqttOptions.password);
Azure.IoT Build 0:ef4901974abc 313 }
Azure.IoT Build 0:ef4901974abc 314 return result;
Azure.IoT Build 0:ef4901974abc 315 }
Azure.IoT Build 0:ef4901974abc 316
Azure.IoT Build 0:ef4901974abc 317 static void recvCompleteCallback(void* context, CONTROL_PACKET_TYPE packet, int flags, BUFFER_HANDLE headerData)
Azure.IoT Build 0:ef4901974abc 318 {
Azure.IoT Build 0:ef4901974abc 319 MQTT_CLIENT* mqttData = (MQTT_CLIENT*)context;
Azure.IoT Build 0:ef4901974abc 320 if (mqttData != NULL && headerData != NULL)
Azure.IoT Build 0:ef4901974abc 321 {
Azure.IoT Build 0:ef4901974abc 322 size_t len = BUFFER_length(headerData);
Azure.IoT Build 0:ef4901974abc 323 uint8_t* iterator = BUFFER_u_char(headerData);
Azure.IoT Build 0:ef4901974abc 324
Azure.IoT Build 0:ef4901974abc 325 logIncomingMsgTrace(mqttData, packet, flags, iterator, len);
Azure.IoT Build 0:ef4901974abc 326
Azure.IoT Build 0:ef4901974abc 327 if (iterator != NULL && len > 0)
Azure.IoT Build 0:ef4901974abc 328 {
Azure.IoT Build 0:ef4901974abc 329 switch (packet)
Azure.IoT Build 0:ef4901974abc 330 {
Azure.IoT Build 0:ef4901974abc 331 case CONNACK_TYPE:
Azure.IoT Build 0:ef4901974abc 332 {
Azure.IoT Build 0:ef4901974abc 333 if (mqttData->fnOperationCallback != NULL)
Azure.IoT Build 0:ef4901974abc 334 {
Azure.IoT Build 0:ef4901974abc 335 /*Codes_SRS_MQTT_CLIENT_07_028: [If the actionResult parameter is of type CONNECT_ACK then the msgInfo value shall be a CONNECT_ACK structure.]*/
Azure.IoT Build 0:ef4901974abc 336 CONNECT_ACK connack = { 0 };
Azure.IoT Build 0:ef4901974abc 337 connack.isSessionPresent = (byteutil_readByte(&iterator) == 0x1) ? true : false;
Azure.IoT Build 0:ef4901974abc 338 connack.returnCode = byteutil_readByte(&iterator);
Azure.IoT Build 0:ef4901974abc 339
Azure.IoT Build 0:ef4901974abc 340 mqttData->fnOperationCallback(mqttData, MQTT_CLIENT_ON_CONNACK, (void*)&connack, mqttData->ctx);
Azure.IoT Build 0:ef4901974abc 341
Azure.IoT Build 0:ef4901974abc 342 if (connack.returnCode == CONNECTION_ACCEPTED)
Azure.IoT Build 0:ef4901974abc 343 {
Azure.IoT Build 0:ef4901974abc 344 mqttData->clientConnected = true;
Azure.IoT Build 0:ef4901974abc 345 }
Azure.IoT Build 0:ef4901974abc 346 }
Azure.IoT Build 0:ef4901974abc 347 break;
Azure.IoT Build 0:ef4901974abc 348 }
Azure.IoT Build 0:ef4901974abc 349 case PUBLISH_TYPE:
Azure.IoT Build 0:ef4901974abc 350 {
Azure.IoT Build 0:ef4901974abc 351 if (mqttData->fnMessageRecv != NULL)
Azure.IoT Build 0:ef4901974abc 352 {
Azure.IoT Build 0:ef4901974abc 353 //uint8_t ctrlPacket = byteutil_readByte(&iterator);
Azure.IoT Build 0:ef4901974abc 354 bool isDuplicateMsg = (flags & DUPLICATE_FLAG_MASK) ? true : false;
Azure.IoT Build 0:ef4901974abc 355 bool isRetainMsg = (flags & RETAIN_FLAG_MASK) ? true : false;
Azure.IoT Build 0:ef4901974abc 356 QOS_VALUE qosValue = (flags == 0) ? DELIVER_AT_MOST_ONCE : (flags & QOS_LEAST_ONCE_FLAG_MASK) ? DELIVER_AT_LEAST_ONCE : DELIVER_EXACTLY_ONCE;
Azure.IoT Build 0:ef4901974abc 357
Azure.IoT Build 0:ef4901974abc 358 uint8_t* initialPos = iterator;
Azure.IoT Build 0:ef4901974abc 359 char* topicName = byteutil_readUTF(&iterator, NULL);
Azure.IoT Build 0:ef4901974abc 360 uint16_t packetId = 0;
Azure.IoT Build 0:ef4901974abc 361 if (qosValue != DELIVER_AT_MOST_ONCE)
Azure.IoT Build 0:ef4901974abc 362 {
Azure.IoT Build 0:ef4901974abc 363 packetId = byteutil_read_uint16(&iterator);
Azure.IoT Build 0:ef4901974abc 364 }
Azure.IoT Build 0:ef4901974abc 365 size_t length = len - (iterator - initialPos);
Azure.IoT Build 0:ef4901974abc 366
Azure.IoT Build 0:ef4901974abc 367 MQTT_MESSAGE_HANDLE msgHandle = mqttmessage_create(packetId, topicName, qosValue, iterator, length);
Azure.IoT Build 0:ef4901974abc 368 if (msgHandle == NULL)
Azure.IoT Build 0:ef4901974abc 369 {
Azure.IoT Build 0:ef4901974abc 370 LOG(mqttData->logFunc, LOG_LINE, "failure in mqttmessage_create");
Azure.IoT Build 0:ef4901974abc 371 }
Azure.IoT Build 0:ef4901974abc 372 else
Azure.IoT Build 0:ef4901974abc 373 {
Azure.IoT Build 0:ef4901974abc 374 (void)mqttmessage_setIsDuplicateMsg(msgHandle, isDuplicateMsg);
Azure.IoT Build 0:ef4901974abc 375 (void)mqttmessage_setIsRetained(msgHandle, isRetainMsg);
Azure.IoT Build 0:ef4901974abc 376 mqttData->fnMessageRecv(msgHandle, mqttData->ctx);
Azure.IoT Build 0:ef4901974abc 377
Azure.IoT Build 0:ef4901974abc 378 BUFFER_HANDLE pubRel = NULL;
Azure.IoT Build 0:ef4901974abc 379 if (qosValue == DELIVER_EXACTLY_ONCE)
Azure.IoT Build 0:ef4901974abc 380 {
Azure.IoT Build 0:ef4901974abc 381 pubRel = mqtt_codec_publishReceived(packetId);
Azure.IoT Build 0:ef4901974abc 382 }
Azure.IoT Build 0:ef4901974abc 383 else if (qosValue == DELIVER_AT_LEAST_ONCE)
Azure.IoT Build 0:ef4901974abc 384 {
Azure.IoT Build 0:ef4901974abc 385 pubRel = mqtt_codec_publishAck(packetId);
Azure.IoT Build 0:ef4901974abc 386 }
Azure.IoT Build 0:ef4901974abc 387 if (pubRel != NULL)
Azure.IoT Build 0:ef4901974abc 388 {
Azure.IoT Build 0:ef4901974abc 389 (void)sendPacketItem(mqttData, BUFFER_u_char(pubRel), BUFFER_length(pubRel));
Azure.IoT Build 0:ef4901974abc 390 BUFFER_delete(pubRel);
Azure.IoT Build 0:ef4901974abc 391 }
Azure.IoT Build 0:ef4901974abc 392 free(topicName);
Azure.IoT Build 0:ef4901974abc 393 mqttmessage_destroy(msgHandle);
Azure.IoT Build 0:ef4901974abc 394 }
Azure.IoT Build 0:ef4901974abc 395 }
Azure.IoT Build 0:ef4901974abc 396 break;
Azure.IoT Build 0:ef4901974abc 397 }
Azure.IoT Build 0:ef4901974abc 398 case PUBACK_TYPE:
Azure.IoT Build 0:ef4901974abc 399 case PUBREC_TYPE:
Azure.IoT Build 0:ef4901974abc 400 case PUBREL_TYPE:
Azure.IoT Build 0:ef4901974abc 401 case PUBCOMP_TYPE:
Azure.IoT Build 0:ef4901974abc 402 {
Azure.IoT Build 0:ef4901974abc 403 if (mqttData->fnOperationCallback)
Azure.IoT Build 0:ef4901974abc 404 {
Azure.IoT Build 0:ef4901974abc 405 /*Codes_SRS_MQTT_CLIENT_07_029: [If the actionResult parameter are of types PUBACK_TYPE, PUBREC_TYPE, PUBREL_TYPE or PUBCOMP_TYPE then the msgInfo value shall be a PUBLISH_ACK structure.]*/
Azure.IoT Build 0:ef4901974abc 406 MQTT_CLIENT_EVENT_RESULT action = (packet == PUBACK_TYPE) ? MQTT_CLIENT_ON_PUBLISH_ACK :
Azure.IoT Build 0:ef4901974abc 407 (packet == PUBREC_TYPE) ? MQTT_CLIENT_ON_PUBLISH_RECV :
Azure.IoT Build 0:ef4901974abc 408 (packet == PUBREL_TYPE) ? MQTT_CLIENT_ON_PUBLISH_REL : MQTT_CLIENT_ON_PUBLISH_COMP;
Azure.IoT Build 0:ef4901974abc 409
Azure.IoT Build 0:ef4901974abc 410 PUBLISH_ACK publish_ack = { 0 };
Azure.IoT Build 0:ef4901974abc 411 publish_ack.packetId = byteutil_read_uint16(&iterator);
Azure.IoT Build 0:ef4901974abc 412
Azure.IoT Build 0:ef4901974abc 413 BUFFER_HANDLE pubRel = NULL;
Azure.IoT Build 0:ef4901974abc 414 mqttData->fnOperationCallback(mqttData, action, (void*)&publish_ack, mqttData->ctx);
Azure.IoT Build 0:ef4901974abc 415 if (packet == PUBREC_TYPE)
Azure.IoT Build 0:ef4901974abc 416 {
Azure.IoT Build 0:ef4901974abc 417 pubRel = mqtt_codec_publishRelease(publish_ack.packetId);
Azure.IoT Build 0:ef4901974abc 418 }
Azure.IoT Build 0:ef4901974abc 419 else if (packet == PUBREL_TYPE)
Azure.IoT Build 0:ef4901974abc 420 {
Azure.IoT Build 0:ef4901974abc 421 pubRel = mqtt_codec_publishComplete(publish_ack.packetId);
Azure.IoT Build 0:ef4901974abc 422 }
Azure.IoT Build 0:ef4901974abc 423 if (pubRel != NULL)
Azure.IoT Build 0:ef4901974abc 424 {
Azure.IoT Build 0:ef4901974abc 425 (void)sendPacketItem(mqttData, BUFFER_u_char(pubRel), BUFFER_length(pubRel));
Azure.IoT Build 0:ef4901974abc 426 BUFFER_delete(pubRel);
Azure.IoT Build 0:ef4901974abc 427 }
Azure.IoT Build 0:ef4901974abc 428 }
Azure.IoT Build 0:ef4901974abc 429 break;
Azure.IoT Build 0:ef4901974abc 430 }
Azure.IoT Build 0:ef4901974abc 431 case SUBACK_TYPE:
Azure.IoT Build 0:ef4901974abc 432 {
Azure.IoT Build 0:ef4901974abc 433 if (mqttData->fnOperationCallback)
Azure.IoT Build 0:ef4901974abc 434 {
Azure.IoT Build 0:ef4901974abc 435 /*Codes_SRS_MQTT_CLIENT_07_030: [If the actionResult parameter is of type SUBACK_TYPE then the msgInfo value shall be a SUBSCRIBE_ACK structure.]*/
Azure.IoT Build 0:ef4901974abc 436 SUBSCRIBE_ACK suback = { 0 };
Azure.IoT Build 0:ef4901974abc 437
Azure.IoT Build 0:ef4901974abc 438 size_t remainLen = len;
Azure.IoT Build 0:ef4901974abc 439 suback.packetId = byteutil_read_uint16(&iterator);
Azure.IoT Build 0:ef4901974abc 440 remainLen -= 2;
Azure.IoT Build 0:ef4901974abc 441
Azure.IoT Build 0:ef4901974abc 442 // Allocate the remaining len
Azure.IoT Build 0:ef4901974abc 443 suback.qosReturn = (QOS_VALUE*)malloc(sizeof(QOS_VALUE)*remainLen);
Azure.IoT Build 0:ef4901974abc 444 if (suback.qosReturn != NULL)
Azure.IoT Build 0:ef4901974abc 445 {
Azure.IoT Build 0:ef4901974abc 446 while (remainLen > 0)
Azure.IoT Build 0:ef4901974abc 447 {
Azure.IoT Build 0:ef4901974abc 448 suback.qosReturn[suback.qosCount++] = byteutil_readByte(&iterator);
Azure.IoT Build 0:ef4901974abc 449 remainLen--;
Azure.IoT Build 0:ef4901974abc 450 }
Azure.IoT Build 0:ef4901974abc 451 (void)mqttData->fnOperationCallback(mqttData, MQTT_CLIENT_ON_SUBSCRIBE_ACK, (void*)&suback, mqttData->ctx);
Azure.IoT Build 0:ef4901974abc 452 free(suback.qosReturn);
Azure.IoT Build 0:ef4901974abc 453 }
Azure.IoT Build 0:ef4901974abc 454 }
Azure.IoT Build 0:ef4901974abc 455 break;
Azure.IoT Build 0:ef4901974abc 456 }
Azure.IoT Build 0:ef4901974abc 457 case UNSUBACK_TYPE:
Azure.IoT Build 0:ef4901974abc 458 {
Azure.IoT Build 0:ef4901974abc 459 if (mqttData->fnOperationCallback)
Azure.IoT Build 0:ef4901974abc 460 {
Azure.IoT Build 0:ef4901974abc 461 /*Codes_SRS_MQTT_CLIENT_07_031: [If the actionResult parameter is of type UNSUBACK_TYPE then the msgInfo value shall be a UNSUBSCRIBE_ACK structure.]*/
Azure.IoT Build 0:ef4901974abc 462 UNSUBSCRIBE_ACK unsuback = { 0 };
Azure.IoT Build 0:ef4901974abc 463 iterator += VARIABLE_HEADER_OFFSET;
Azure.IoT Build 0:ef4901974abc 464 unsuback.packetId = byteutil_read_uint16(&iterator);
Azure.IoT Build 0:ef4901974abc 465
Azure.IoT Build 0:ef4901974abc 466 (void)mqttData->fnOperationCallback(mqttData, MQTT_CLIENT_ON_UNSUBSCRIBE_ACK, (void*)&unsuback, mqttData->ctx);
Azure.IoT Build 0:ef4901974abc 467 }
Azure.IoT Build 0:ef4901974abc 468 break;
Azure.IoT Build 0:ef4901974abc 469 }
Azure.IoT Build 0:ef4901974abc 470 case PINGRESP_TYPE:
Azure.IoT Build 0:ef4901974abc 471 // Ping responses do not get forwarded
Azure.IoT Build 0:ef4901974abc 472 break;
Azure.IoT Build 0:ef4901974abc 473 default:
Azure.IoT Build 0:ef4901974abc 474 break;
Azure.IoT Build 0:ef4901974abc 475 }
Azure.IoT Build 0:ef4901974abc 476 }
Azure.IoT Build 0:ef4901974abc 477 }
Azure.IoT Build 0:ef4901974abc 478 }
Azure.IoT Build 0:ef4901974abc 479
Azure.IoT Build 0:ef4901974abc 480 MQTT_CLIENT_HANDLE mqtt_client_init(ON_MQTT_MESSAGE_RECV_CALLBACK msgRecv, ON_MQTT_OPERATION_CALLBACK opCallback, void* callbackCtx, LOGGER_LOG logger)
Azure.IoT Build 0:ef4901974abc 481 {
Azure.IoT Build 0:ef4901974abc 482 MQTT_CLIENT* result;
Azure.IoT Build 0:ef4901974abc 483 /*Codes_SRS_MQTT_CLIENT_07_001: [If the parameters ON_MQTT_MESSAGE_RECV_CALLBACK is NULL then mqttclient_init shall return NULL.]*/
Azure.IoT Build 0:ef4901974abc 484 if (msgRecv == NULL)
Azure.IoT Build 0:ef4901974abc 485 {
Azure.IoT Build 0:ef4901974abc 486 result = NULL;
Azure.IoT Build 0:ef4901974abc 487 }
Azure.IoT Build 0:ef4901974abc 488 else
Azure.IoT Build 0:ef4901974abc 489 {
Azure.IoT Build 0:ef4901974abc 490 result = malloc(sizeof(MQTT_CLIENT));
Azure.IoT Build 0:ef4901974abc 491 if (result == NULL)
Azure.IoT Build 0:ef4901974abc 492 {
Azure.IoT Build 0:ef4901974abc 493 /*Codes_SRS_MQTT_CLIENT_07_002: [If any failure is encountered then mqttclient_init shall return NULL.]*/
Azure.IoT Build 0:ef4901974abc 494 LOG(logger, LOG_LINE, "mqtt_client_inti failure: Allocation Failure");
Azure.IoT Build 0:ef4901974abc 495 }
Azure.IoT Build 0:ef4901974abc 496 else
Azure.IoT Build 0:ef4901974abc 497 {
Azure.IoT Build 0:ef4901974abc 498 /*Codes_SRS_MQTT_CLIENT_07_003: [mqttclient_init shall allocate MQTTCLIENT_DATA_INSTANCE and return the MQTTCLIENT_HANDLE on success.]*/
Azure.IoT Build 0:ef4901974abc 499 result->xioHandle = NULL;
Azure.IoT Build 0:ef4901974abc 500 result->packetState = UNKNOWN_TYPE;
Azure.IoT Build 0:ef4901974abc 501 result->logFunc = logger;
Azure.IoT Build 0:ef4901974abc 502 result->packetSendTimeMs = 0;
Azure.IoT Build 0:ef4901974abc 503 result->fnOperationCallback = opCallback;
Azure.IoT Build 0:ef4901974abc 504 result->fnMessageRecv = msgRecv;
Azure.IoT Build 0:ef4901974abc 505 result->ctx = callbackCtx;
Azure.IoT Build 0:ef4901974abc 506 result->qosValue = DELIVER_AT_MOST_ONCE;
Azure.IoT Build 0:ef4901974abc 507 result->keepAliveInterval = 0;
Azure.IoT Build 0:ef4901974abc 508 result->packetTickCntr = tickcounter_create();
Azure.IoT Build 0:ef4901974abc 509 result->mqttOptions.clientId = NULL;
Azure.IoT Build 0:ef4901974abc 510 result->mqttOptions.willTopic = NULL;
Azure.IoT Build 0:ef4901974abc 511 result->mqttOptions.willMessage = NULL;
Azure.IoT Build 0:ef4901974abc 512 result->mqttOptions.username = NULL;
Azure.IoT Build 0:ef4901974abc 513 result->mqttOptions.password = NULL;
Azure.IoT Build 0:ef4901974abc 514 result->socketConnected = false;
Azure.IoT Build 0:ef4901974abc 515 result->clientConnected = false;
Azure.IoT Build 0:ef4901974abc 516 result->logTrace = false;
Azure.IoT Build 0:ef4901974abc 517 result->rawBytesTrace = false;
Azure.IoT Build 0:ef4901974abc 518 if (result->packetTickCntr == NULL)
Azure.IoT Build 0:ef4901974abc 519 {
Azure.IoT Build 0:ef4901974abc 520 /*Codes_SRS_MQTT_CLIENT_07_002: [If any failure is encountered then mqttclient_init shall return NULL.]*/
Azure.IoT Build 0:ef4901974abc 521 LOG(logger, LOG_LINE, "mqtt_client_init failure: tickcounter_create failure");
Azure.IoT Build 0:ef4901974abc 522 free(result);
Azure.IoT Build 0:ef4901974abc 523 result = NULL;
Azure.IoT Build 0:ef4901974abc 524 }
Azure.IoT Build 0:ef4901974abc 525 else
Azure.IoT Build 0:ef4901974abc 526 {
Azure.IoT Build 0:ef4901974abc 527 result->codec_handle = mqtt_codec_create(recvCompleteCallback, result);
Azure.IoT Build 0:ef4901974abc 528 if (result->codec_handle == NULL)
Azure.IoT Build 0:ef4901974abc 529 {
Azure.IoT Build 0:ef4901974abc 530 /*Codes_SRS_MQTT_CLIENT_07_002: [If any failure is encountered then mqttclient_init shall return NULL.]*/
Azure.IoT Build 0:ef4901974abc 531 LOG(logger, LOG_LINE, "mqtt_client_init failure: mqtt_codec_create failure");
Azure.IoT Build 0:ef4901974abc 532 tickcounter_destroy(result->packetTickCntr);
Azure.IoT Build 0:ef4901974abc 533 free(result);
Azure.IoT Build 0:ef4901974abc 534 result = NULL;
Azure.IoT Build 0:ef4901974abc 535 }
Azure.IoT Build 0:ef4901974abc 536 }
Azure.IoT Build 0:ef4901974abc 537 }
Azure.IoT Build 0:ef4901974abc 538 }
Azure.IoT Build 0:ef4901974abc 539 return result;
Azure.IoT Build 0:ef4901974abc 540 }
Azure.IoT Build 0:ef4901974abc 541
Azure.IoT Build 0:ef4901974abc 542 void mqtt_client_deinit(MQTT_CLIENT_HANDLE handle)
Azure.IoT Build 0:ef4901974abc 543 {
Azure.IoT Build 0:ef4901974abc 544 /*Codes_SRS_MQTT_CLIENT_07_004: [If the parameter handle is NULL then function mqtt_client_deinit shall do nothing.]*/
Azure.IoT Build 0:ef4901974abc 545 if (handle != NULL)
Azure.IoT Build 0:ef4901974abc 546 {
Azure.IoT Build 0:ef4901974abc 547 /*Codes_SRS_MQTT_CLIENT_07_005: [mqtt_client_deinit shall deallocate all memory allocated in this unit.]*/
Azure.IoT Build 0:ef4901974abc 548 MQTT_CLIENT* mqttData = (MQTT_CLIENT*)handle;
Azure.IoT Build 0:ef4901974abc 549 tickcounter_destroy(mqttData->packetTickCntr);
Azure.IoT Build 0:ef4901974abc 550 mqtt_codec_destroy(mqttData->codec_handle);
Azure.IoT Build 0:ef4901974abc 551 free(mqttData->mqttOptions.clientId);
Azure.IoT Build 0:ef4901974abc 552 free(mqttData->mqttOptions.willTopic);
Azure.IoT Build 0:ef4901974abc 553 free(mqttData->mqttOptions.willMessage);
Azure.IoT Build 0:ef4901974abc 554 free(mqttData->mqttOptions.username);
Azure.IoT Build 0:ef4901974abc 555 free(mqttData->mqttOptions.password);
Azure.IoT Build 0:ef4901974abc 556 free(mqttData);
Azure.IoT Build 0:ef4901974abc 557 }
Azure.IoT Build 0:ef4901974abc 558 }
Azure.IoT Build 0:ef4901974abc 559
Azure.IoT Build 0:ef4901974abc 560 int mqtt_client_connect(MQTT_CLIENT_HANDLE handle, XIO_HANDLE xioHandle, MQTT_CLIENT_OPTIONS* mqttOptions)
Azure.IoT Build 0:ef4901974abc 561 {
Azure.IoT Build 0:ef4901974abc 562 int result;
Azure.IoT Build 0:ef4901974abc 563 /*SRS_MQTT_CLIENT_07_006: [If any of the parameters handle, ioHandle, or mqttOptions are NULL then mqtt_client_connect shall return a non-zero value.]*/
Azure.IoT Build 0:ef4901974abc 564 if (handle == NULL || mqttOptions == NULL)
Azure.IoT Build 0:ef4901974abc 565 {
Azure.IoT Build 0:ef4901974abc 566 result = __LINE__;
Azure.IoT Build 0:ef4901974abc 567 }
Azure.IoT Build 0:ef4901974abc 568 else
Azure.IoT Build 0:ef4901974abc 569 {
Azure.IoT Build 0:ef4901974abc 570 MQTT_CLIENT* mqttData = (MQTT_CLIENT*)handle;
Azure.IoT Build 0:ef4901974abc 571 if (xioHandle == NULL)
Azure.IoT Build 0:ef4901974abc 572 {
Azure.IoT Build 0:ef4901974abc 573 /*Codes_SRS_MQTT_CLIENT_07_007: [If any failure is encountered then mqtt_client_connect shall return a non-zero value.]*/
Azure.IoT Build 0:ef4901974abc 574 LOG(mqttData->logFunc, LOG_LINE, "Error: mqttcodec_connect failed");
Azure.IoT Build 0:ef4901974abc 575 result = __LINE__;
Azure.IoT Build 0:ef4901974abc 576 }
Azure.IoT Build 0:ef4901974abc 577 else
Azure.IoT Build 0:ef4901974abc 578 {
Azure.IoT Build 0:ef4901974abc 579 mqttData->xioHandle = xioHandle;
Azure.IoT Build 0:ef4901974abc 580 mqttData->packetState = UNKNOWN_TYPE;
Azure.IoT Build 0:ef4901974abc 581 mqttData->qosValue = mqttOptions->qualityOfServiceValue;
Azure.IoT Build 0:ef4901974abc 582 mqttData->keepAliveInterval = mqttOptions->keepAliveInterval;
Azure.IoT Build 0:ef4901974abc 583 if (cloneMqttOptions(mqttData, mqttOptions) != 0)
Azure.IoT Build 0:ef4901974abc 584 {
Azure.IoT Build 0:ef4901974abc 585 LOG(mqttData->logFunc, LOG_LINE, "Error: Clone Mqtt Options failed");
Azure.IoT Build 0:ef4901974abc 586 result = __LINE__;
Azure.IoT Build 0:ef4901974abc 587 }
Azure.IoT Build 0:ef4901974abc 588 /*Codes_SRS_MQTT_CLIENT_07_008: [mqtt_client_connect shall open the XIO_HANDLE by calling into the xio_open interface.]*/
Azure.IoT Build 0:ef4901974abc 589 else if (xio_open(xioHandle, onOpenComplete, mqttData, onBytesReceived, mqttData, onIoError, mqttData) != 0)
Azure.IoT Build 0:ef4901974abc 590 {
Azure.IoT Build 0:ef4901974abc 591 /*Codes_SRS_MQTT_CLIENT_07_007: [If any failure is encountered then mqtt_client_connect shall return a non-zero value.]*/
Azure.IoT Build 0:ef4901974abc 592 LOG(mqttData->logFunc, LOG_LINE, "Error: io_open failed");
Azure.IoT Build 0:ef4901974abc 593 result = __LINE__;
Azure.IoT Build 0:ef4901974abc 594 }
Azure.IoT Build 0:ef4901974abc 595 else
Azure.IoT Build 0:ef4901974abc 596 {
Azure.IoT Build 0:ef4901974abc 597 result = 0;
Azure.IoT Build 0:ef4901974abc 598 }
Azure.IoT Build 0:ef4901974abc 599 }
Azure.IoT Build 0:ef4901974abc 600 }
Azure.IoT Build 0:ef4901974abc 601 return result;
Azure.IoT Build 0:ef4901974abc 602 }
Azure.IoT Build 0:ef4901974abc 603
Azure.IoT Build 0:ef4901974abc 604 int mqtt_client_publish(MQTT_CLIENT_HANDLE handle, MQTT_MESSAGE_HANDLE msgHandle)
Azure.IoT Build 0:ef4901974abc 605 {
Azure.IoT Build 0:ef4901974abc 606 int result;
Azure.IoT Build 0:ef4901974abc 607 MQTT_CLIENT* mqttData = (MQTT_CLIENT*)handle;
Azure.IoT Build 0:ef4901974abc 608 if (mqttData == NULL || msgHandle == NULL)
Azure.IoT Build 0:ef4901974abc 609 {
Azure.IoT Build 0:ef4901974abc 610 /*Codes_SRS_MQTT_CLIENT_07_019: [If one of the parameters handle or msgHandle is NULL then mqtt_client_publish shall return a non-zero value.]*/
Azure.IoT Build 0:ef4901974abc 611 result = __LINE__;
Azure.IoT Build 0:ef4901974abc 612 }
Azure.IoT Build 0:ef4901974abc 613 else
Azure.IoT Build 0:ef4901974abc 614 {
Azure.IoT Build 0:ef4901974abc 615 /*Codes_SRS_MQTT_CLIENT_07_021: [mqtt_client_publish shall get the message information from the MQTT_MESSAGE_HANDLE.]*/
Azure.IoT Build 0:ef4901974abc 616 const APP_PAYLOAD* payload = mqttmessage_getApplicationMsg(msgHandle);
Azure.IoT Build 0:ef4901974abc 617 if (payload == NULL)
Azure.IoT Build 0:ef4901974abc 618 {
Azure.IoT Build 0:ef4901974abc 619 /*Codes_SRS_MQTT_CLIENT_07_020: [If any failure is encountered then mqtt_client_unsubscribe shall return a non-zero value.]*/
Azure.IoT Build 0:ef4901974abc 620 LOG(mqttData->logFunc, LOG_LINE, "Error: mqttmessage_getApplicationMsg failed");
Azure.IoT Build 0:ef4901974abc 621 result = __LINE__;
Azure.IoT Build 0:ef4901974abc 622 }
Azure.IoT Build 0:ef4901974abc 623 else
Azure.IoT Build 0:ef4901974abc 624 {
Azure.IoT Build 0:ef4901974abc 625 BUFFER_HANDLE publishPacket = mqtt_codec_publish(mqttmessage_getQosType(msgHandle), mqttmessage_getIsDuplicateMsg(msgHandle),
Azure.IoT Build 0:ef4901974abc 626 mqttmessage_getIsRetained(msgHandle), mqttmessage_getPacketId(msgHandle), mqttmessage_getTopicName(msgHandle), payload->message, payload->length);
Azure.IoT Build 0:ef4901974abc 627 if (publishPacket == NULL)
Azure.IoT Build 0:ef4901974abc 628 {
Azure.IoT Build 0:ef4901974abc 629 /*Codes_SRS_MQTT_CLIENT_07_020: [If any failure is encountered then mqtt_client_unsubscribe shall return a non-zero value.]*/
Azure.IoT Build 0:ef4901974abc 630 LOG(mqttData->logFunc, LOG_LINE, "Error: mqtt_codec_publish failed");
Azure.IoT Build 0:ef4901974abc 631 result = __LINE__;
Azure.IoT Build 0:ef4901974abc 632 }
Azure.IoT Build 0:ef4901974abc 633 else
Azure.IoT Build 0:ef4901974abc 634 {
Azure.IoT Build 0:ef4901974abc 635 mqttData->packetState = PUBLISH_TYPE;
Azure.IoT Build 0:ef4901974abc 636
Azure.IoT Build 0:ef4901974abc 637 /*Codes_SRS_MQTT_CLIENT_07_022: [On success mqtt_client_publish shall send the MQTT SUBCRIBE packet to the endpoint.]*/
Azure.IoT Build 0:ef4901974abc 638 if (sendPacketItem(mqttData, BUFFER_u_char(publishPacket), BUFFER_length(publishPacket)) != 0)
Azure.IoT Build 0:ef4901974abc 639 {
Azure.IoT Build 0:ef4901974abc 640 /*Codes_SRS_MQTT_CLIENT_07_020: [If any failure is encountered then mqtt_client_unsubscribe shall return a non-zero value.]*/
Azure.IoT Build 0:ef4901974abc 641 LOG(mqttData->logFunc, LOG_LINE, "Error: mqtt_client_publish send failed");
Azure.IoT Build 0:ef4901974abc 642 result = __LINE__;
Azure.IoT Build 0:ef4901974abc 643 }
Azure.IoT Build 0:ef4901974abc 644 else
Azure.IoT Build 0:ef4901974abc 645 {
Azure.IoT Build 0:ef4901974abc 646 result = 0;
Azure.IoT Build 0:ef4901974abc 647 }
Azure.IoT Build 0:ef4901974abc 648 BUFFER_delete(publishPacket);
Azure.IoT Build 0:ef4901974abc 649 }
Azure.IoT Build 0:ef4901974abc 650 }
Azure.IoT Build 0:ef4901974abc 651 }
Azure.IoT Build 0:ef4901974abc 652 return result;
Azure.IoT Build 0:ef4901974abc 653 }
Azure.IoT Build 0:ef4901974abc 654
Azure.IoT Build 0:ef4901974abc 655 int mqtt_client_subscribe(MQTT_CLIENT_HANDLE handle, uint16_t packetId, SUBSCRIBE_PAYLOAD* subscribeList, size_t count)
Azure.IoT Build 0:ef4901974abc 656 {
Azure.IoT Build 0:ef4901974abc 657 int result;
Azure.IoT Build 0:ef4901974abc 658 MQTT_CLIENT* mqttData = (MQTT_CLIENT*)handle;
Azure.IoT Build 0:ef4901974abc 659 if (mqttData == NULL || subscribeList == NULL || count == 0)
Azure.IoT Build 0:ef4901974abc 660 {
Azure.IoT Build 0:ef4901974abc 661 /*Codes_SRS_MQTT_CLIENT_07_013: [If any of the parameters handle, subscribeList is NULL or count is 0 then mqtt_client_subscribe shall return a non-zero value.]*/
Azure.IoT Build 0:ef4901974abc 662 result = __LINE__;
Azure.IoT Build 0:ef4901974abc 663 }
Azure.IoT Build 0:ef4901974abc 664 else
Azure.IoT Build 0:ef4901974abc 665 {
Azure.IoT Build 0:ef4901974abc 666 BUFFER_HANDLE subPacket = mqtt_codec_subscribe(packetId, subscribeList, count);
Azure.IoT Build 0:ef4901974abc 667 if (subPacket == NULL)
Azure.IoT Build 0:ef4901974abc 668 {
Azure.IoT Build 0:ef4901974abc 669 /*Codes_SRS_MQTT_CLIENT_07_014: [If any failure is encountered then mqtt_client_subscribe shall return a non-zero value.]*/
Azure.IoT Build 0:ef4901974abc 670 LOG(mqttData->logFunc, LOG_LINE, "Error: mqtt_codec_subscribe failed");
Azure.IoT Build 0:ef4901974abc 671 result = __LINE__;
Azure.IoT Build 0:ef4901974abc 672 }
Azure.IoT Build 0:ef4901974abc 673 else
Azure.IoT Build 0:ef4901974abc 674 {
Azure.IoT Build 0:ef4901974abc 675 mqttData->packetState = SUBSCRIBE_TYPE;
Azure.IoT Build 0:ef4901974abc 676
Azure.IoT Build 0:ef4901974abc 677 /*Codes_SRS_MQTT_CLIENT_07_015: [On success mqtt_client_subscribe shall send the MQTT SUBCRIBE packet to the endpoint.]*/
Azure.IoT Build 0:ef4901974abc 678 if (sendPacketItem(mqttData, BUFFER_u_char(subPacket), BUFFER_length(subPacket)) != 0)
Azure.IoT Build 0:ef4901974abc 679 {
Azure.IoT Build 0:ef4901974abc 680 /*Codes_SRS_MQTT_CLIENT_07_014: [If any failure is encountered then mqtt_client_subscribe shall return a non-zero value.]*/
Azure.IoT Build 0:ef4901974abc 681 LOG(mqttData->logFunc, LOG_LINE, "Error: mqtt_client_subscribe send failed");
Azure.IoT Build 0:ef4901974abc 682 result = __LINE__;
Azure.IoT Build 0:ef4901974abc 683 }
Azure.IoT Build 0:ef4901974abc 684 else
Azure.IoT Build 0:ef4901974abc 685 {
Azure.IoT Build 0:ef4901974abc 686 result = 0;
Azure.IoT Build 0:ef4901974abc 687 }
Azure.IoT Build 0:ef4901974abc 688 BUFFER_delete(subPacket);
Azure.IoT Build 0:ef4901974abc 689 }
Azure.IoT Build 0:ef4901974abc 690 }
Azure.IoT Build 0:ef4901974abc 691 return result;
Azure.IoT Build 0:ef4901974abc 692 }
Azure.IoT Build 0:ef4901974abc 693
Azure.IoT Build 0:ef4901974abc 694 int mqtt_client_unsubscribe(MQTT_CLIENT_HANDLE handle, uint16_t packetId, const char** unsubscribeList, size_t count)
Azure.IoT Build 0:ef4901974abc 695 {
Azure.IoT Build 0:ef4901974abc 696 int result;
Azure.IoT Build 0:ef4901974abc 697 MQTT_CLIENT* mqttData = (MQTT_CLIENT*)handle;
Azure.IoT Build 0:ef4901974abc 698 if (mqttData == NULL || unsubscribeList == NULL || count == 0)
Azure.IoT Build 0:ef4901974abc 699 {
Azure.IoT Build 0:ef4901974abc 700 /*Codes_SRS_MQTT_CLIENT_07_016: [If any of the parameters handle, unsubscribeList is NULL or count is 0 then mqtt_client_unsubscribe shall return a non-zero value.]*/
Azure.IoT Build 0:ef4901974abc 701 result = __LINE__;
Azure.IoT Build 0:ef4901974abc 702 }
Azure.IoT Build 0:ef4901974abc 703 else
Azure.IoT Build 0:ef4901974abc 704 {
Azure.IoT Build 0:ef4901974abc 705 BUFFER_HANDLE unsubPacket = mqtt_codec_unsubscribe(packetId, unsubscribeList, count);
Azure.IoT Build 0:ef4901974abc 706 if (unsubPacket == NULL)
Azure.IoT Build 0:ef4901974abc 707 {
Azure.IoT Build 0:ef4901974abc 708 /*Codes_SRS_MQTT_CLIENT_07_017: [If any failure is encountered then mqtt_client_unsubscribe shall return a non-zero value.]*/
Azure.IoT Build 0:ef4901974abc 709 LOG(mqttData->logFunc, LOG_LINE, "Error: mqtt_codec_unsubscribe failed");
Azure.IoT Build 0:ef4901974abc 710 result = __LINE__;
Azure.IoT Build 0:ef4901974abc 711 }
Azure.IoT Build 0:ef4901974abc 712 else
Azure.IoT Build 0:ef4901974abc 713 {
Azure.IoT Build 0:ef4901974abc 714 mqttData->packetState = UNSUBSCRIBE_TYPE;
Azure.IoT Build 0:ef4901974abc 715
Azure.IoT Build 0:ef4901974abc 716 /*Codes_SRS_MQTT_CLIENT_07_018: [On success mqtt_client_unsubscribe shall send the MQTT SUBCRIBE packet to the endpoint.]*/
Azure.IoT Build 0:ef4901974abc 717 LOG(mqttData->logFunc, LOG_LINE, "MQTT unsubscribe");
Azure.IoT Build 0:ef4901974abc 718 if (sendPacketItem(mqttData, BUFFER_u_char(unsubPacket), BUFFER_length(unsubPacket)) != 0)
Azure.IoT Build 0:ef4901974abc 719 {
Azure.IoT Build 0:ef4901974abc 720 /*Codes_SRS_MQTT_CLIENT_07_017: [If any failure is encountered then mqtt_client_unsubscribe shall return a non-zero value.].]*/
Azure.IoT Build 0:ef4901974abc 721 LOG(mqttData->logFunc, LOG_LINE, "Error: mqtt_client_unsubscribe send failed");
Azure.IoT Build 0:ef4901974abc 722 result = __LINE__;
Azure.IoT Build 0:ef4901974abc 723 }
Azure.IoT Build 0:ef4901974abc 724 else
Azure.IoT Build 0:ef4901974abc 725 {
Azure.IoT Build 0:ef4901974abc 726 result = 0;
Azure.IoT Build 0:ef4901974abc 727 }
Azure.IoT Build 0:ef4901974abc 728 BUFFER_delete(unsubPacket);
Azure.IoT Build 0:ef4901974abc 729 }
Azure.IoT Build 0:ef4901974abc 730 }
Azure.IoT Build 0:ef4901974abc 731 return result;
Azure.IoT Build 0:ef4901974abc 732 }
Azure.IoT Build 0:ef4901974abc 733
Azure.IoT Build 0:ef4901974abc 734 int mqtt_client_disconnect(MQTT_CLIENT_HANDLE handle)
Azure.IoT Build 0:ef4901974abc 735 {
Azure.IoT Build 0:ef4901974abc 736 int result;
Azure.IoT Build 0:ef4901974abc 737 MQTT_CLIENT* mqttData = (MQTT_CLIENT*)handle;
Azure.IoT Build 0:ef4901974abc 738 if (mqttData == NULL)
Azure.IoT Build 0:ef4901974abc 739 {
Azure.IoT Build 0:ef4901974abc 740 /*Codes_SRS_MQTT_CLIENT_07_010: [If the parameters handle is NULL then mqtt_client_disconnect shall return a non-zero value.]*/
Azure.IoT Build 0:ef4901974abc 741 result = __LINE__;
Azure.IoT Build 0:ef4901974abc 742 }
Azure.IoT Build 0:ef4901974abc 743 else
Azure.IoT Build 0:ef4901974abc 744 {
Azure.IoT Build 0:ef4901974abc 745 mqttData->packetState = DISCONNECT_TYPE;
Azure.IoT Build 0:ef4901974abc 746 BUFFER_HANDLE disconnectPacket = mqtt_codec_disconnect();
Azure.IoT Build 0:ef4901974abc 747 if (disconnectPacket == NULL)
Azure.IoT Build 0:ef4901974abc 748 {
Azure.IoT Build 0:ef4901974abc 749 /*Codes_SRS_MQTT_CLIENT_07_011: [If any failure is encountered then mqtt_client_disconnect shall return a non-zero value.]*/
Azure.IoT Build 0:ef4901974abc 750 LOG(mqttData->logFunc, LOG_LINE, "Error: mqtt_client_disconnect failed");
Azure.IoT Build 0:ef4901974abc 751 result = __LINE__;
Azure.IoT Build 0:ef4901974abc 752 }
Azure.IoT Build 0:ef4901974abc 753 else
Azure.IoT Build 0:ef4901974abc 754 {
Azure.IoT Build 0:ef4901974abc 755 mqttData->packetState = DISCONNECT_TYPE;
Azure.IoT Build 0:ef4901974abc 756
Azure.IoT Build 0:ef4901974abc 757 /*Codes_SRS_MQTT_CLIENT_07_012: [On success mqtt_client_disconnect shall send the MQTT DISCONNECT packet to the endpoint.]*/
Azure.IoT Build 0:ef4901974abc 758 if (sendPacketItem(mqttData, BUFFER_u_char(disconnectPacket), BUFFER_length(disconnectPacket)) != 0)
Azure.IoT Build 0:ef4901974abc 759 {
Azure.IoT Build 0:ef4901974abc 760 /*Codes_SRS_MQTT_CLIENT_07_011: [If any failure is encountered then mqtt_client_disconnect shall return a non-zero value.]*/
Azure.IoT Build 0:ef4901974abc 761 LOG(mqttData->logFunc, LOG_LINE, "Error: mqtt_client_disconnect send failed");
Azure.IoT Build 0:ef4901974abc 762 result = __LINE__;
Azure.IoT Build 0:ef4901974abc 763 }
Azure.IoT Build 0:ef4901974abc 764 else
Azure.IoT Build 0:ef4901974abc 765 {
Azure.IoT Build 0:ef4901974abc 766 result = 0;
Azure.IoT Build 0:ef4901974abc 767 }
Azure.IoT Build 0:ef4901974abc 768 BUFFER_delete(disconnectPacket);
Azure.IoT Build 0:ef4901974abc 769 }
Azure.IoT Build 0:ef4901974abc 770 }
Azure.IoT Build 0:ef4901974abc 771 return result;
Azure.IoT Build 0:ef4901974abc 772 }
Azure.IoT Build 0:ef4901974abc 773
Azure.IoT Build 0:ef4901974abc 774 void mqtt_client_dowork(MQTT_CLIENT_HANDLE handle)
Azure.IoT Build 0:ef4901974abc 775 {
Azure.IoT Build 0:ef4901974abc 776 MQTT_CLIENT* mqttData = (MQTT_CLIENT*)handle;
Azure.IoT Build 0:ef4901974abc 777 /*Codes_SRS_MQTT_CLIENT_07_023: [If the parameter handle is NULL then mqtt_client_dowork shall do nothing.]*/
Azure.IoT Build 0:ef4901974abc 778 if (mqttData != NULL)
Azure.IoT Build 0:ef4901974abc 779 {
Azure.IoT Build 0:ef4901974abc 780 /*Codes_SRS_MQTT_CLIENT_07_024: [mqtt_client_dowork shall call the xio_dowork function to complete operations.]*/
Azure.IoT Build 0:ef4901974abc 781 xio_dowork(mqttData->xioHandle);
Azure.IoT Build 0:ef4901974abc 782
Azure.IoT Build 0:ef4901974abc 783 /*Codes_SRS_MQTT_CLIENT_07_025: [mqtt_client_dowork shall retrieve the the last packet send value and ...]*/
Azure.IoT Build 0:ef4901974abc 784 if (mqttData->socketConnected && mqttData->clientConnected && mqttData->keepAliveInterval > 0)
Azure.IoT Build 0:ef4901974abc 785 {
Azure.IoT Build 0:ef4901974abc 786 uint64_t current_ms;
Azure.IoT Build 0:ef4901974abc 787 if (tickcounter_get_current_ms(mqttData->packetTickCntr, &current_ms) != 0)
Azure.IoT Build 0:ef4901974abc 788 {
Azure.IoT Build 0:ef4901974abc 789 LOG(mqttData->logFunc, LOG_LINE, "Error: tickcounter_get_current_ms failed");
Azure.IoT Build 0:ef4901974abc 790 }
Azure.IoT Build 0:ef4901974abc 791 else
Azure.IoT Build 0:ef4901974abc 792 {
Azure.IoT Build 0:ef4901974abc 793 if ((((current_ms - mqttData->packetSendTimeMs) / 1000) + KEEP_ALIVE_BUFFER_SEC) > mqttData->keepAliveInterval)
Azure.IoT Build 0:ef4901974abc 794 {
Azure.IoT Build 0:ef4901974abc 795 /*Codes_SRS_MQTT_CLIENT_07_026: [if keepAliveInternal is > 0 and the send time is greater than the MQTT KeepAliveInterval then it shall construct an MQTT PINGREQ packet.]*/
Azure.IoT Build 0:ef4901974abc 796 BUFFER_HANDLE pingPacket = mqtt_codec_ping();
Azure.IoT Build 0:ef4901974abc 797 if (pingPacket != NULL)
Azure.IoT Build 0:ef4901974abc 798 {
Azure.IoT Build 0:ef4901974abc 799 (void)sendPacketItem(mqttData, BUFFER_u_char(pingPacket), BUFFER_length(pingPacket));
Azure.IoT Build 0:ef4901974abc 800 BUFFER_delete(pingPacket);
Azure.IoT Build 0:ef4901974abc 801 }
Azure.IoT Build 0:ef4901974abc 802 }
Azure.IoT Build 0:ef4901974abc 803 }
Azure.IoT Build 0:ef4901974abc 804 }
Azure.IoT Build 0:ef4901974abc 805 }
Azure.IoT Build 0:ef4901974abc 806 }
Azure.IoT Build 0:ef4901974abc 807
Azure.IoT Build 0:ef4901974abc 808 void mqtt_client_set_trace(MQTT_CLIENT_HANDLE handle, bool traceOn, bool rawBytesOn)
Azure.IoT Build 0:ef4901974abc 809 {
Azure.IoT Build 0:ef4901974abc 810 MQTT_CLIENT* mqttData = (MQTT_CLIENT*)handle;
Azure.IoT Build 0:ef4901974abc 811 if (mqttData != NULL)
Azure.IoT Build 0:ef4901974abc 812 {
Azure.IoT Build 0:ef4901974abc 813 mqttData->logTrace = traceOn;
Azure.IoT Build 0:ef4901974abc 814 mqttData->rawBytesTrace = rawBytesOn;
Azure.IoT Build 0:ef4901974abc 815 }
Azure.IoT Build 0:ef4901974abc 816 }