Xin Zhang / azure-iot-c-sdk-f767zi

Dependents:   samplemqtt

Committer:
XinZhangMS
Date:
Thu Aug 23 06:52:14 2018 +0000
Revision:
0:f7f1f0d76dd6
azure-c-sdk for mbed os supporting NUCLEO_F767ZI

Who changed what in which revision?

UserRevisionLine numberNew contents of line
XinZhangMS 0:f7f1f0d76dd6 1 // Copyright (c) Microsoft. All rights reserved.
XinZhangMS 0:f7f1f0d76dd6 2 // Licensed under the MIT license. See LICENSE file in the project root for full license information.
XinZhangMS 0:f7f1f0d76dd6 3
XinZhangMS 0:f7f1f0d76dd6 4 #include <stdlib.h>
XinZhangMS 0:f7f1f0d76dd6 5 #include <ctype.h>
XinZhangMS 0:f7f1f0d76dd6 6 #include "azure_c_shared_utility/optimize_size.h"
XinZhangMS 0:f7f1f0d76dd6 7 #include "azure_c_shared_utility/gballoc.h"
XinZhangMS 0:f7f1f0d76dd6 8 #include "azure_c_shared_utility/crt_abstractions.h"
XinZhangMS 0:f7f1f0d76dd6 9 #include "azure_c_shared_utility/xlogging.h"
XinZhangMS 0:f7f1f0d76dd6 10 #include "azure_c_shared_utility/tlsio.h"
XinZhangMS 0:f7f1f0d76dd6 11 #include "azure_c_shared_utility/platform.h"
XinZhangMS 0:f7f1f0d76dd6 12 #include "azure_c_shared_utility/sastoken.h"
XinZhangMS 0:f7f1f0d76dd6 13
XinZhangMS 0:f7f1f0d76dd6 14 #include "azure_uamqp_c/connection.h"
XinZhangMS 0:f7f1f0d76dd6 15 #include "azure_uamqp_c/message_receiver.h"
XinZhangMS 0:f7f1f0d76dd6 16 #include "azure_uamqp_c/message_sender.h"
XinZhangMS 0:f7f1f0d76dd6 17 #include "azure_uamqp_c/messaging.h"
XinZhangMS 0:f7f1f0d76dd6 18 #include "azure_uamqp_c/sasl_mechanism.h"
XinZhangMS 0:f7f1f0d76dd6 19 #include "azure_uamqp_c/saslclientio.h"
XinZhangMS 0:f7f1f0d76dd6 20 #include "azure_uamqp_c/sasl_plain.h"
XinZhangMS 0:f7f1f0d76dd6 21 #include "azure_uamqp_c/cbs.h"
XinZhangMS 0:f7f1f0d76dd6 22
XinZhangMS 0:f7f1f0d76dd6 23 #include "parson.h"
XinZhangMS 0:f7f1f0d76dd6 24
XinZhangMS 0:f7f1f0d76dd6 25 #include "iothub_messaging_ll.h"
XinZhangMS 0:f7f1f0d76dd6 26 #include "iothub_sc_version.h"
XinZhangMS 0:f7f1f0d76dd6 27
XinZhangMS 0:f7f1f0d76dd6 28 DEFINE_ENUM_STRINGS(IOTHUB_FEEDBACK_STATUS_CODE, IOTHUB_FEEDBACK_STATUS_CODE_VALUES);
XinZhangMS 0:f7f1f0d76dd6 29 DEFINE_ENUM_STRINGS(IOTHUB_MESSAGE_SEND_STATE, IOTHUB_MESSAGE_SEND_STATE_VALUES);
XinZhangMS 0:f7f1f0d76dd6 30 DEFINE_ENUM_STRINGS(IOTHUB_MESSAGING_RESULT, IOTHUB_MESSAGING_RESULT_VALUES);
XinZhangMS 0:f7f1f0d76dd6 31
XinZhangMS 0:f7f1f0d76dd6 32 typedef struct CALLBACK_DATA_TAG
XinZhangMS 0:f7f1f0d76dd6 33 {
XinZhangMS 0:f7f1f0d76dd6 34 IOTHUB_OPEN_COMPLETE_CALLBACK openCompleteCompleteCallback;
XinZhangMS 0:f7f1f0d76dd6 35 IOTHUB_SEND_COMPLETE_CALLBACK sendCompleteCallback;
XinZhangMS 0:f7f1f0d76dd6 36 IOTHUB_FEEDBACK_MESSAGE_RECEIVED_CALLBACK feedbackMessageCallback;
XinZhangMS 0:f7f1f0d76dd6 37 void* openUserContext;
XinZhangMS 0:f7f1f0d76dd6 38 void* sendUserContext;
XinZhangMS 0:f7f1f0d76dd6 39 void* feedbackUserContext;
XinZhangMS 0:f7f1f0d76dd6 40 } CALLBACK_DATA;
XinZhangMS 0:f7f1f0d76dd6 41
XinZhangMS 0:f7f1f0d76dd6 42 typedef struct IOTHUB_MESSAGING_TAG
XinZhangMS 0:f7f1f0d76dd6 43 {
XinZhangMS 0:f7f1f0d76dd6 44 int isOpened;
XinZhangMS 0:f7f1f0d76dd6 45 char* hostname;
XinZhangMS 0:f7f1f0d76dd6 46 char* iothubName;
XinZhangMS 0:f7f1f0d76dd6 47 char* iothubSuffix;
XinZhangMS 0:f7f1f0d76dd6 48 char* sharedAccessKey;
XinZhangMS 0:f7f1f0d76dd6 49 char* keyName;
XinZhangMS 0:f7f1f0d76dd6 50
XinZhangMS 0:f7f1f0d76dd6 51 MESSAGE_SENDER_HANDLE message_sender;
XinZhangMS 0:f7f1f0d76dd6 52 MESSAGE_RECEIVER_HANDLE message_receiver;
XinZhangMS 0:f7f1f0d76dd6 53 CONNECTION_HANDLE connection;
XinZhangMS 0:f7f1f0d76dd6 54 SESSION_HANDLE session;
XinZhangMS 0:f7f1f0d76dd6 55 LINK_HANDLE sender_link;
XinZhangMS 0:f7f1f0d76dd6 56 LINK_HANDLE receiver_link;
XinZhangMS 0:f7f1f0d76dd6 57 SASL_MECHANISM_HANDLE sasl_mechanism_handle;
XinZhangMS 0:f7f1f0d76dd6 58 SASL_PLAIN_CONFIG sasl_plain_config;
XinZhangMS 0:f7f1f0d76dd6 59 XIO_HANDLE tls_io;
XinZhangMS 0:f7f1f0d76dd6 60 XIO_HANDLE sasl_io;
XinZhangMS 0:f7f1f0d76dd6 61
XinZhangMS 0:f7f1f0d76dd6 62 MESSAGE_SENDER_STATE message_sender_state;
XinZhangMS 0:f7f1f0d76dd6 63 MESSAGE_RECEIVER_STATE message_receiver_state;
XinZhangMS 0:f7f1f0d76dd6 64
XinZhangMS 0:f7f1f0d76dd6 65 CALLBACK_DATA* callback_data;
XinZhangMS 0:f7f1f0d76dd6 66 } IOTHUB_MESSAGING;
XinZhangMS 0:f7f1f0d76dd6 67
XinZhangMS 0:f7f1f0d76dd6 68
XinZhangMS 0:f7f1f0d76dd6 69 static const char* const FEEDBACK_RECORD_KEY_DEVICE_ID = "deviceId";
XinZhangMS 0:f7f1f0d76dd6 70 static const char* const FEEDBACK_RECORD_KEY_DEVICE_GENERATION_ID = "deviceGenerationId";
XinZhangMS 0:f7f1f0d76dd6 71 static const char* const FEEDBACK_RECORD_KEY_DESCRIPTION = "description";
XinZhangMS 0:f7f1f0d76dd6 72 static const char* const FEEDBACK_RECORD_KEY_ENQUED_TIME_UTC = "enqueuedTimeUtc";
XinZhangMS 0:f7f1f0d76dd6 73 static const char* const FEEDBACK_RECORD_KEY_ORIGINAL_MESSAGE_ID = "originalMessageId";
XinZhangMS 0:f7f1f0d76dd6 74 static const char* const AMQP_ADDRESS_PATH_FMT = "/devices/%s/messages/deviceBound";
XinZhangMS 0:f7f1f0d76dd6 75 static const char* const AMQP_ADDRESS_PATH_MODULE_FMT = "/devices/%s/modules/%s/messages/deviceBound";
XinZhangMS 0:f7f1f0d76dd6 76
XinZhangMS 0:f7f1f0d76dd6 77 static int setMessageId(IOTHUB_MESSAGE_HANDLE iothub_message_handle, PROPERTIES_HANDLE uamqp_message_properties)
XinZhangMS 0:f7f1f0d76dd6 78 {
XinZhangMS 0:f7f1f0d76dd6 79 int result;
XinZhangMS 0:f7f1f0d76dd6 80 const char* messageId;
XinZhangMS 0:f7f1f0d76dd6 81
XinZhangMS 0:f7f1f0d76dd6 82 if ((messageId = IoTHubMessage_GetMessageId(iothub_message_handle)) != NULL)
XinZhangMS 0:f7f1f0d76dd6 83 {
XinZhangMS 0:f7f1f0d76dd6 84 AMQP_VALUE uamqp_message_id;
XinZhangMS 0:f7f1f0d76dd6 85 if ((uamqp_message_id = amqpvalue_create_string(messageId)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 86 {
XinZhangMS 0:f7f1f0d76dd6 87 /*Codes_SRS_IOTHUBMESSAGING_12_040: [ If any of the uAMQP call fails IoTHubMessaging_LL_SendMessage shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 88 LogError("Failed to create an AMQP_VALUE for the messageId property value.");
XinZhangMS 0:f7f1f0d76dd6 89 result = __FAILURE__;
XinZhangMS 0:f7f1f0d76dd6 90 }
XinZhangMS 0:f7f1f0d76dd6 91 else
XinZhangMS 0:f7f1f0d76dd6 92 {
XinZhangMS 0:f7f1f0d76dd6 93 int api_call_result;
XinZhangMS 0:f7f1f0d76dd6 94
XinZhangMS 0:f7f1f0d76dd6 95 /* Codes_SRS_IOTHUBMESSAGING_12_083: [ The message-id AMQP_VALUE shall be set on the uAMQP message using properties_set_message_id ] */
XinZhangMS 0:f7f1f0d76dd6 96 if ((api_call_result = properties_set_message_id(uamqp_message_properties, uamqp_message_id)) != 0)
XinZhangMS 0:f7f1f0d76dd6 97 {
XinZhangMS 0:f7f1f0d76dd6 98 /*Codes_SRS_IOTHUBMESSAGING_12_040: [ If any of the uAMQP call fails IoTHubMessaging_LL_SendMessage shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 99 LogInfo("Failed to set value of uAMQP message 'message-id' property (%d).", api_call_result);
XinZhangMS 0:f7f1f0d76dd6 100 result = __FAILURE__;
XinZhangMS 0:f7f1f0d76dd6 101 }
XinZhangMS 0:f7f1f0d76dd6 102 else
XinZhangMS 0:f7f1f0d76dd6 103 {
XinZhangMS 0:f7f1f0d76dd6 104 result = 0;
XinZhangMS 0:f7f1f0d76dd6 105 }
XinZhangMS 0:f7f1f0d76dd6 106 amqpvalue_destroy(uamqp_message_id);
XinZhangMS 0:f7f1f0d76dd6 107 }
XinZhangMS 0:f7f1f0d76dd6 108 }
XinZhangMS 0:f7f1f0d76dd6 109 else
XinZhangMS 0:f7f1f0d76dd6 110 {
XinZhangMS 0:f7f1f0d76dd6 111 result = 0;
XinZhangMS 0:f7f1f0d76dd6 112 }
XinZhangMS 0:f7f1f0d76dd6 113
XinZhangMS 0:f7f1f0d76dd6 114 return result;
XinZhangMS 0:f7f1f0d76dd6 115 }
XinZhangMS 0:f7f1f0d76dd6 116
XinZhangMS 0:f7f1f0d76dd6 117 static int setCorrelationId(IOTHUB_MESSAGE_HANDLE iothub_message_handle, PROPERTIES_HANDLE uamqp_message_properties)
XinZhangMS 0:f7f1f0d76dd6 118 {
XinZhangMS 0:f7f1f0d76dd6 119 int result;
XinZhangMS 0:f7f1f0d76dd6 120 const char* correlationId;
XinZhangMS 0:f7f1f0d76dd6 121
XinZhangMS 0:f7f1f0d76dd6 122 if ((correlationId = IoTHubMessage_GetCorrelationId(iothub_message_handle)) != NULL)
XinZhangMS 0:f7f1f0d76dd6 123 {
XinZhangMS 0:f7f1f0d76dd6 124 AMQP_VALUE uamqp_correlation_id;
XinZhangMS 0:f7f1f0d76dd6 125 if ((uamqp_correlation_id = amqpvalue_create_string(correlationId)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 126 {
XinZhangMS 0:f7f1f0d76dd6 127 /*Codes_SRS_IOTHUBMESSAGING_12_040: [ If any of the uAMQP call fails IoTHubMessaging_LL_SendMessage shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 128 LogError("Failed to create an AMQP_VALUE for the messageId property value.");
XinZhangMS 0:f7f1f0d76dd6 129 result = __FAILURE__;
XinZhangMS 0:f7f1f0d76dd6 130 }
XinZhangMS 0:f7f1f0d76dd6 131 else
XinZhangMS 0:f7f1f0d76dd6 132 {
XinZhangMS 0:f7f1f0d76dd6 133 int api_call_result;
XinZhangMS 0:f7f1f0d76dd6 134
XinZhangMS 0:f7f1f0d76dd6 135 /*Codes_SRS_IOTHUBMESSAGING_12_086: [ The correlation-id AMQP_VALUE shall be set on the uAMQP message using properties_set_correlation_id ] */
XinZhangMS 0:f7f1f0d76dd6 136 if ((api_call_result = properties_set_correlation_id(uamqp_message_properties, uamqp_correlation_id)) != 0)
XinZhangMS 0:f7f1f0d76dd6 137 {
XinZhangMS 0:f7f1f0d76dd6 138 /*Codes_SRS_IOTHUBMESSAGING_12_040: [ If any of the uAMQP call fails IoTHubMessaging_LL_SendMessage shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 139 LogInfo("Failed to set value of uAMQP message 'message-id' property (%d).", api_call_result);
XinZhangMS 0:f7f1f0d76dd6 140 result = __FAILURE__;
XinZhangMS 0:f7f1f0d76dd6 141 }
XinZhangMS 0:f7f1f0d76dd6 142 else
XinZhangMS 0:f7f1f0d76dd6 143 {
XinZhangMS 0:f7f1f0d76dd6 144 result = 0;
XinZhangMS 0:f7f1f0d76dd6 145 }
XinZhangMS 0:f7f1f0d76dd6 146 amqpvalue_destroy(uamqp_correlation_id);
XinZhangMS 0:f7f1f0d76dd6 147 }
XinZhangMS 0:f7f1f0d76dd6 148 }
XinZhangMS 0:f7f1f0d76dd6 149 else
XinZhangMS 0:f7f1f0d76dd6 150 {
XinZhangMS 0:f7f1f0d76dd6 151 result = 0;
XinZhangMS 0:f7f1f0d76dd6 152 }
XinZhangMS 0:f7f1f0d76dd6 153
XinZhangMS 0:f7f1f0d76dd6 154 return result;
XinZhangMS 0:f7f1f0d76dd6 155 }
XinZhangMS 0:f7f1f0d76dd6 156
XinZhangMS 0:f7f1f0d76dd6 157 static int addPropertiesToAMQPMessage(IOTHUB_MESSAGE_HANDLE iothub_message_handle, MESSAGE_HANDLE uamqp_message, AMQP_VALUE to_amqp_value)
XinZhangMS 0:f7f1f0d76dd6 158 {
XinZhangMS 0:f7f1f0d76dd6 159 int result;
XinZhangMS 0:f7f1f0d76dd6 160 PROPERTIES_HANDLE uamqp_message_properties = NULL; /* This initialization is forced by Valgrind */
XinZhangMS 0:f7f1f0d76dd6 161 int api_call_result;
XinZhangMS 0:f7f1f0d76dd6 162
XinZhangMS 0:f7f1f0d76dd6 163 /*Codes_SRS_IOTHUBMESSAGING_12_079: [ The uAMQP message properties shall be retrieved using message_get_properties ] */
XinZhangMS 0:f7f1f0d76dd6 164 if ((api_call_result = message_get_properties(uamqp_message, &uamqp_message_properties)) != 0)
XinZhangMS 0:f7f1f0d76dd6 165 {
XinZhangMS 0:f7f1f0d76dd6 166 /*Codes_SRS_IOTHUBMESSAGING_12_040: [ If any of the uAMQP call fails IoTHubMessaging_LL_SendMessage shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 167 LogError("Failed to get properties map from uAMQP message (error code %d).", api_call_result);
XinZhangMS 0:f7f1f0d76dd6 168 result = __FAILURE__;
XinZhangMS 0:f7f1f0d76dd6 169 }
XinZhangMS 0:f7f1f0d76dd6 170 /*Codes_SRS_IOTHUBMESSAGING_12_080: [ If UAMQP message properties were not present then a new properties container shall be created using properties_create ] */
XinZhangMS 0:f7f1f0d76dd6 171 else if (uamqp_message_properties == NULL &&
XinZhangMS 0:f7f1f0d76dd6 172 (uamqp_message_properties = properties_create()) == NULL)
XinZhangMS 0:f7f1f0d76dd6 173 {
XinZhangMS 0:f7f1f0d76dd6 174 /*Codes_SRS_IOTHUBMESSAGING_12_040: [ If any of the uAMQP call fails IoTHubMessaging_LL_SendMessage shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 175 LogError("Failed to create properties map for uAMQP message (error code %d).", api_call_result);
XinZhangMS 0:f7f1f0d76dd6 176 result = __FAILURE__;
XinZhangMS 0:f7f1f0d76dd6 177 }
XinZhangMS 0:f7f1f0d76dd6 178 else
XinZhangMS 0:f7f1f0d76dd6 179 {
XinZhangMS 0:f7f1f0d76dd6 180 /*Codes_SRS_IOTHUBMESSAGING_12_081: [ Message-id from the IOTHUB_MESSAGE shall be read using IoTHubMessage_GetMessageId ] */
XinZhangMS 0:f7f1f0d76dd6 181 /*Codes_SRS_IOTHUBMESSAGING_12_082: [ As message-id is optional field, if it is not set on the IOTHUB_MESSAGE, message_create_from_iothub_message shall ignore it and continue normally ] */
XinZhangMS 0:f7f1f0d76dd6 182 if (setMessageId(iothub_message_handle, uamqp_message_properties) != 0)
XinZhangMS 0:f7f1f0d76dd6 183 {
XinZhangMS 0:f7f1f0d76dd6 184 LogError("Failed to set uampq messageId.");
XinZhangMS 0:f7f1f0d76dd6 185 result = __FAILURE__;
XinZhangMS 0:f7f1f0d76dd6 186 }
XinZhangMS 0:f7f1f0d76dd6 187 /*Codes_SRS_IOTHUBMESSAGING_12_084: [ Correlation-id from the IOTHUB_MESSAGE shall be read using IoTHubMessage_GetCorrelationId ] */
XinZhangMS 0:f7f1f0d76dd6 188 /*Codes_SRS_IOTHUBMESSAGING_12_085: [ As correlation-id is optional field, if it is not set on the IOTHUB_MESSAGE, message_create_from_iothub_message() shall ignore it and continue normally ] */
XinZhangMS 0:f7f1f0d76dd6 189 else if (setCorrelationId(iothub_message_handle, uamqp_message_properties) != 0)
XinZhangMS 0:f7f1f0d76dd6 190 {
XinZhangMS 0:f7f1f0d76dd6 191 LogError("Failed to set uampq correlationId.");
XinZhangMS 0:f7f1f0d76dd6 192 result = __FAILURE__;
XinZhangMS 0:f7f1f0d76dd6 193 }
XinZhangMS 0:f7f1f0d76dd6 194 else
XinZhangMS 0:f7f1f0d76dd6 195 {
XinZhangMS 0:f7f1f0d76dd6 196 /*Codes_SRS_IOTHUBMESSAGING_12_87: [ IoTHubMessaging_LL_SendMessage shall set the uAMQP message TO property to the given message properties by calling properties_set_to ] */
XinZhangMS 0:f7f1f0d76dd6 197 if ((properties_set_to(uamqp_message_properties, to_amqp_value)) != 0)
XinZhangMS 0:f7f1f0d76dd6 198 {
XinZhangMS 0:f7f1f0d76dd6 199 /*Codes_SRS_IOTHUBMESSAGING_12_040: [ If any of the uAMQP call fails IoTHubMessaging_LL_SendMessage shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 200 LogError("Could not create properties for message - properties_set_to failed");
XinZhangMS 0:f7f1f0d76dd6 201 result = __FAILURE__;
XinZhangMS 0:f7f1f0d76dd6 202 }
XinZhangMS 0:f7f1f0d76dd6 203 /*Codes_SRS_IOTHUBMESSAGING_12_038: [ IoTHubMessaging_LL_SendMessage shall set the uAMQP message properties to the given message properties by calling message_set_properties ] */
XinZhangMS 0:f7f1f0d76dd6 204 else if ((api_call_result = message_set_properties(uamqp_message, uamqp_message_properties)) != 0)
XinZhangMS 0:f7f1f0d76dd6 205 {
XinZhangMS 0:f7f1f0d76dd6 206 /*Codes_SRS_IOTHUBMESSAGING_12_040: [ If any of the uAMQP call fails IoTHubMessaging_LL_SendMessage shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 207 LogError("Failed to set properties map on uAMQP message (error code %d).", api_call_result);
XinZhangMS 0:f7f1f0d76dd6 208 result = __FAILURE__;
XinZhangMS 0:f7f1f0d76dd6 209 }
XinZhangMS 0:f7f1f0d76dd6 210 else
XinZhangMS 0:f7f1f0d76dd6 211 {
XinZhangMS 0:f7f1f0d76dd6 212 result = 0;
XinZhangMS 0:f7f1f0d76dd6 213 }
XinZhangMS 0:f7f1f0d76dd6 214 }
XinZhangMS 0:f7f1f0d76dd6 215 properties_destroy(uamqp_message_properties);
XinZhangMS 0:f7f1f0d76dd6 216 }
XinZhangMS 0:f7f1f0d76dd6 217 return result;
XinZhangMS 0:f7f1f0d76dd6 218 }
XinZhangMS 0:f7f1f0d76dd6 219
XinZhangMS 0:f7f1f0d76dd6 220 static int addApplicationPropertiesToAMQPMessage(IOTHUB_MESSAGE_HANDLE iothub_message_handle, MESSAGE_HANDLE uamqp_message)
XinZhangMS 0:f7f1f0d76dd6 221 {
XinZhangMS 0:f7f1f0d76dd6 222 int result;
XinZhangMS 0:f7f1f0d76dd6 223 MAP_HANDLE properties_map;
XinZhangMS 0:f7f1f0d76dd6 224 const char* const* propertyKeys;
XinZhangMS 0:f7f1f0d76dd6 225 const char* const* propertyValues;
XinZhangMS 0:f7f1f0d76dd6 226 size_t propertyCount = 0;
XinZhangMS 0:f7f1f0d76dd6 227
XinZhangMS 0:f7f1f0d76dd6 228 /*Codes_SRS_IOTHUBMESSAGING_12_088: [ The IOTHUB_MESSAGE_HANDLE properties shall be obtained by calling IoTHubMessage_Properties ] */
XinZhangMS 0:f7f1f0d76dd6 229 properties_map = IoTHubMessage_Properties(iothub_message_handle);
XinZhangMS 0:f7f1f0d76dd6 230
XinZhangMS 0:f7f1f0d76dd6 231 /*Codes_SRS_IOTHUBMESSAGING_12_089: [ The actual keys and values, as well as the number of properties shall be obtained by calling Map_GetInternals on the handle obtained from IoTHubMessage_Properties ] */
XinZhangMS 0:f7f1f0d76dd6 232 if (Map_GetInternals(properties_map, &propertyKeys, &propertyValues, &propertyCount) != MAP_OK)
XinZhangMS 0:f7f1f0d76dd6 233 {
XinZhangMS 0:f7f1f0d76dd6 234 /*Codes_SRS_IOTHUBMESSAGING_12_040: [ If any of the uAMQP call fails IoTHubMessaging_LL_SendMessage shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 235 LogError("Failed to get the internals of the property map.");
XinZhangMS 0:f7f1f0d76dd6 236 result = __FAILURE__;
XinZhangMS 0:f7f1f0d76dd6 237 }
XinZhangMS 0:f7f1f0d76dd6 238 else
XinZhangMS 0:f7f1f0d76dd6 239 {
XinZhangMS 0:f7f1f0d76dd6 240 /*Codes_SRS_IOTHUBMESSAGING_12_090: [ If the number of properties is greater than 0, message_create_from_iothub_message() shall iterate through all the properties and add them to the uAMQP message ] */
XinZhangMS 0:f7f1f0d76dd6 241 if (propertyCount != 0)
XinZhangMS 0:f7f1f0d76dd6 242 {
XinZhangMS 0:f7f1f0d76dd6 243 AMQP_VALUE uamqp_map;
XinZhangMS 0:f7f1f0d76dd6 244
XinZhangMS 0:f7f1f0d76dd6 245 /*Codes_SRS_IOTHUBMESSAGING_12_091: [ A uAMQP property map shall be created by calling amqpvalue_create_map ] */
XinZhangMS 0:f7f1f0d76dd6 246 if ((uamqp_map = amqpvalue_create_map()) == NULL)
XinZhangMS 0:f7f1f0d76dd6 247 {
XinZhangMS 0:f7f1f0d76dd6 248 /*Codes_SRS_IOTHUBMESSAGING_12_040: [ If any of the uAMQP call fails IoTHubMessaging_LL_SendMessage shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 249 LogError("Failed to create uAMQP map for the properties.");
XinZhangMS 0:f7f1f0d76dd6 250 result = __FAILURE__;
XinZhangMS 0:f7f1f0d76dd6 251 }
XinZhangMS 0:f7f1f0d76dd6 252 else
XinZhangMS 0:f7f1f0d76dd6 253 {
XinZhangMS 0:f7f1f0d76dd6 254 size_t i = 0;
XinZhangMS 0:f7f1f0d76dd6 255 for (i = 0; i < propertyCount; i++)
XinZhangMS 0:f7f1f0d76dd6 256 {
XinZhangMS 0:f7f1f0d76dd6 257 AMQP_VALUE map_key_value = NULL;
XinZhangMS 0:f7f1f0d76dd6 258 AMQP_VALUE map_value_value = NULL;
XinZhangMS 0:f7f1f0d76dd6 259
XinZhangMS 0:f7f1f0d76dd6 260 /*Codes_SRS_IOTHUBMESSAGING_12_092: [ An AMQP_VALUE instance shall be created using amqpvalue_create_string() to hold each uAMQP property name ] */
XinZhangMS 0:f7f1f0d76dd6 261 if ((map_key_value = amqpvalue_create_string(propertyKeys[i])) == NULL)
XinZhangMS 0:f7f1f0d76dd6 262 {
XinZhangMS 0:f7f1f0d76dd6 263 /*Codes_SRS_IOTHUBMESSAGING_12_040: [ If any of the uAMQP call fails IoTHubMessaging_LL_SendMessage shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 264 LogError("Failed to create uAMQP property key name.");
XinZhangMS 0:f7f1f0d76dd6 265 break;
XinZhangMS 0:f7f1f0d76dd6 266 }
XinZhangMS 0:f7f1f0d76dd6 267 else
XinZhangMS 0:f7f1f0d76dd6 268 {
XinZhangMS 0:f7f1f0d76dd6 269 /*Codes_SRS_IOTHUBMESSAGING_12_093: [ An AMQP_VALUE instance shall be created using amqpvalue_create_string() to hold each uAMQP property value ] */
XinZhangMS 0:f7f1f0d76dd6 270 if ((map_value_value = amqpvalue_create_string(propertyValues[i])) == NULL)
XinZhangMS 0:f7f1f0d76dd6 271 {
XinZhangMS 0:f7f1f0d76dd6 272 /*Codes_SRS_IOTHUBMESSAGING_12_040: [ If any of the uAMQP call fails IoTHubMessaging_LL_SendMessage shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 273 LogError("Failed to create uAMQP property key value.");
XinZhangMS 0:f7f1f0d76dd6 274 break;
XinZhangMS 0:f7f1f0d76dd6 275 }
XinZhangMS 0:f7f1f0d76dd6 276 else
XinZhangMS 0:f7f1f0d76dd6 277 {
XinZhangMS 0:f7f1f0d76dd6 278 /*Codes_SRS_IOTHUBMESSAGING_12_094: [ The property name and value (AMQP_VALUE instances) shall be added to the uAMQP property map by calling amqpvalue_map_set_value ] */
XinZhangMS 0:f7f1f0d76dd6 279 if (amqpvalue_set_map_value(uamqp_map, map_key_value, map_value_value) != 0)
XinZhangMS 0:f7f1f0d76dd6 280 {
XinZhangMS 0:f7f1f0d76dd6 281 /*Codes_SRS_IOTHUBMESSAGING_12_040: [ If any of the uAMQP call fails IoTHubMessaging_LL_SendMessage shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 282 LogError("Failed to set key/value into the the uAMQP property map.");
XinZhangMS 0:f7f1f0d76dd6 283 break;
XinZhangMS 0:f7f1f0d76dd6 284 }
XinZhangMS 0:f7f1f0d76dd6 285 amqpvalue_destroy(map_value_value);
XinZhangMS 0:f7f1f0d76dd6 286 }
XinZhangMS 0:f7f1f0d76dd6 287 /*Codes_SRS_IOTHUBMESSAGING_12_095: [ After adding the property name and value to the uAMQP property map, both AMQP_VALUE instances shall be destroyed using amqpvalue_destroy ] */
XinZhangMS 0:f7f1f0d76dd6 288 amqpvalue_destroy(map_key_value);
XinZhangMS 0:f7f1f0d76dd6 289 }
XinZhangMS 0:f7f1f0d76dd6 290 }
XinZhangMS 0:f7f1f0d76dd6 291
XinZhangMS 0:f7f1f0d76dd6 292 if (i == propertyCount)
XinZhangMS 0:f7f1f0d76dd6 293 {
XinZhangMS 0:f7f1f0d76dd6 294 /*Codes_SRS_IOTHUBMESSAGING_12_096: [ If no errors occurred processing the properties, the uAMQP properties map shall be set on the uAMQP message by calling message_set_application_properties ] */
XinZhangMS 0:f7f1f0d76dd6 295 if (message_set_application_properties(uamqp_message, uamqp_map) != 0)
XinZhangMS 0:f7f1f0d76dd6 296 {
XinZhangMS 0:f7f1f0d76dd6 297 /*Codes_SRS_IOTHUBMESSAGING_12_040: [ If any of the uAMQP call fails IoTHubMessaging_LL_SendMessage shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 298 LogError("Failed to transfer the message properties to the uAMQP message.");
XinZhangMS 0:f7f1f0d76dd6 299 result = __FAILURE__;
XinZhangMS 0:f7f1f0d76dd6 300 }
XinZhangMS 0:f7f1f0d76dd6 301 else
XinZhangMS 0:f7f1f0d76dd6 302 {
XinZhangMS 0:f7f1f0d76dd6 303 result = 0;
XinZhangMS 0:f7f1f0d76dd6 304 }
XinZhangMS 0:f7f1f0d76dd6 305 }
XinZhangMS 0:f7f1f0d76dd6 306 else
XinZhangMS 0:f7f1f0d76dd6 307 {
XinZhangMS 0:f7f1f0d76dd6 308 LogError("Failed to set application property into the the uAMQP property map.");
XinZhangMS 0:f7f1f0d76dd6 309 result = __FAILURE__;
XinZhangMS 0:f7f1f0d76dd6 310 }
XinZhangMS 0:f7f1f0d76dd6 311 amqpvalue_destroy(uamqp_map);
XinZhangMS 0:f7f1f0d76dd6 312 }
XinZhangMS 0:f7f1f0d76dd6 313 }
XinZhangMS 0:f7f1f0d76dd6 314 else
XinZhangMS 0:f7f1f0d76dd6 315 {
XinZhangMS 0:f7f1f0d76dd6 316 /*Codes_SRS_IOTHUBMESSAGING_12_097: [ If the number of properties is 0, no application properties shall be set on the uAMQP message and message_create_from_iothub_message() shall return with success ] */
XinZhangMS 0:f7f1f0d76dd6 317 result = 0;
XinZhangMS 0:f7f1f0d76dd6 318 }
XinZhangMS 0:f7f1f0d76dd6 319 }
XinZhangMS 0:f7f1f0d76dd6 320 return result;
XinZhangMS 0:f7f1f0d76dd6 321 }
XinZhangMS 0:f7f1f0d76dd6 322
XinZhangMS 0:f7f1f0d76dd6 323 static int getMessageContentAndSize(IOTHUB_MESSAGE_HANDLE message, unsigned const char** messageContent, size_t* messageContentSize)
XinZhangMS 0:f7f1f0d76dd6 324 {
XinZhangMS 0:f7f1f0d76dd6 325 int result;
XinZhangMS 0:f7f1f0d76dd6 326 unsigned const char* contentByteArr;
XinZhangMS 0:f7f1f0d76dd6 327 const char* contentStr;
XinZhangMS 0:f7f1f0d76dd6 328 size_t contentSize;
XinZhangMS 0:f7f1f0d76dd6 329
XinZhangMS 0:f7f1f0d76dd6 330 IOTHUBMESSAGE_CONTENT_TYPE contentType = IoTHubMessage_GetContentType(message);
XinZhangMS 0:f7f1f0d76dd6 331
XinZhangMS 0:f7f1f0d76dd6 332 switch (contentType)
XinZhangMS 0:f7f1f0d76dd6 333 {
XinZhangMS 0:f7f1f0d76dd6 334 case IOTHUBMESSAGE_BYTEARRAY:
XinZhangMS 0:f7f1f0d76dd6 335 if (IoTHubMessage_GetByteArray(message, &contentByteArr, &contentSize) != IOTHUB_MESSAGE_OK)
XinZhangMS 0:f7f1f0d76dd6 336 {
XinZhangMS 0:f7f1f0d76dd6 337 LogError("Failed getting the BYTE array representation of the IOTHUB_MESSAGE_HANDLE instance.");
XinZhangMS 0:f7f1f0d76dd6 338 result = __FAILURE__;
XinZhangMS 0:f7f1f0d76dd6 339 }
XinZhangMS 0:f7f1f0d76dd6 340 else
XinZhangMS 0:f7f1f0d76dd6 341 {
XinZhangMS 0:f7f1f0d76dd6 342 *messageContent = contentByteArr;
XinZhangMS 0:f7f1f0d76dd6 343 *messageContentSize = contentSize;
XinZhangMS 0:f7f1f0d76dd6 344 result = 0;
XinZhangMS 0:f7f1f0d76dd6 345 }
XinZhangMS 0:f7f1f0d76dd6 346 break;
XinZhangMS 0:f7f1f0d76dd6 347 case IOTHUBMESSAGE_STRING:
XinZhangMS 0:f7f1f0d76dd6 348 if ((contentStr = IoTHubMessage_GetString(message)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 349 {
XinZhangMS 0:f7f1f0d76dd6 350 LogError("Failed getting the STRING representation of the IOTHUB_MESSAGE_HANDLE instance.");
XinZhangMS 0:f7f1f0d76dd6 351 result = __FAILURE__;
XinZhangMS 0:f7f1f0d76dd6 352 }
XinZhangMS 0:f7f1f0d76dd6 353 else
XinZhangMS 0:f7f1f0d76dd6 354 {
XinZhangMS 0:f7f1f0d76dd6 355 contentSize = strlen(contentStr);
XinZhangMS 0:f7f1f0d76dd6 356 *messageContent = (unsigned const char*)contentStr;
XinZhangMS 0:f7f1f0d76dd6 357 *messageContentSize = contentSize;
XinZhangMS 0:f7f1f0d76dd6 358 result = 0;
XinZhangMS 0:f7f1f0d76dd6 359 }
XinZhangMS 0:f7f1f0d76dd6 360 break;
XinZhangMS 0:f7f1f0d76dd6 361 default:
XinZhangMS 0:f7f1f0d76dd6 362 LogError("Cannot parse IOTHUB_MESSAGE_HANDLE with content type IOTHUBMESSAGE_UNKNOWN.");
XinZhangMS 0:f7f1f0d76dd6 363 result = __FAILURE__;
XinZhangMS 0:f7f1f0d76dd6 364 break;
XinZhangMS 0:f7f1f0d76dd6 365 }
XinZhangMS 0:f7f1f0d76dd6 366 return result;
XinZhangMS 0:f7f1f0d76dd6 367 }
XinZhangMS 0:f7f1f0d76dd6 368
XinZhangMS 0:f7f1f0d76dd6 369 static char* createSasToken(IOTHUB_MESSAGING_HANDLE messagingHandle)
XinZhangMS 0:f7f1f0d76dd6 370 {
XinZhangMS 0:f7f1f0d76dd6 371 char* result;
XinZhangMS 0:f7f1f0d76dd6 372
XinZhangMS 0:f7f1f0d76dd6 373 char* buffer = NULL;
XinZhangMS 0:f7f1f0d76dd6 374 if (messagingHandle->sharedAccessKey == NULL)
XinZhangMS 0:f7f1f0d76dd6 375 {
XinZhangMS 0:f7f1f0d76dd6 376 LogError("createSasPlainConfig failed - sharedAccessKey cannot be NULL");
XinZhangMS 0:f7f1f0d76dd6 377 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 378 }
XinZhangMS 0:f7f1f0d76dd6 379 else if (messagingHandle->hostname == NULL)
XinZhangMS 0:f7f1f0d76dd6 380 {
XinZhangMS 0:f7f1f0d76dd6 381 LogError("createSasPlainConfig failed - hostname cannot be NULL");
XinZhangMS 0:f7f1f0d76dd6 382 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 383 }
XinZhangMS 0:f7f1f0d76dd6 384 else if (messagingHandle->keyName == NULL)
XinZhangMS 0:f7f1f0d76dd6 385 {
XinZhangMS 0:f7f1f0d76dd6 386 LogError("createSasPlainConfig failed - keyName cannot be NULL");
XinZhangMS 0:f7f1f0d76dd6 387 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 388 }
XinZhangMS 0:f7f1f0d76dd6 389 else
XinZhangMS 0:f7f1f0d76dd6 390 {
XinZhangMS 0:f7f1f0d76dd6 391 STRING_HANDLE hostName = NULL;
XinZhangMS 0:f7f1f0d76dd6 392 STRING_HANDLE sharedAccessKey = NULL;
XinZhangMS 0:f7f1f0d76dd6 393 STRING_HANDLE keyName = NULL;
XinZhangMS 0:f7f1f0d76dd6 394
XinZhangMS 0:f7f1f0d76dd6 395 if ((hostName = STRING_construct(messagingHandle->hostname)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 396 {
XinZhangMS 0:f7f1f0d76dd6 397 LogError("STRING_construct failed for hostName");
XinZhangMS 0:f7f1f0d76dd6 398 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 399 }
XinZhangMS 0:f7f1f0d76dd6 400 else if ((sharedAccessKey = STRING_construct(messagingHandle->sharedAccessKey)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 401 {
XinZhangMS 0:f7f1f0d76dd6 402 LogError("STRING_construct failed for sharedAccessKey");
XinZhangMS 0:f7f1f0d76dd6 403 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 404 }
XinZhangMS 0:f7f1f0d76dd6 405 else if ((keyName = STRING_construct(messagingHandle->keyName)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 406 {
XinZhangMS 0:f7f1f0d76dd6 407 LogError("STRING_construct failed for keyName");
XinZhangMS 0:f7f1f0d76dd6 408 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 409 }
XinZhangMS 0:f7f1f0d76dd6 410 else
XinZhangMS 0:f7f1f0d76dd6 411 {
XinZhangMS 0:f7f1f0d76dd6 412 time_t currentTime = time(NULL);
XinZhangMS 0:f7f1f0d76dd6 413 size_t expiry_time = (size_t)(currentTime + (365 * 24 * 60 * 60));
XinZhangMS 0:f7f1f0d76dd6 414 const char* c_buffer = NULL;
XinZhangMS 0:f7f1f0d76dd6 415
XinZhangMS 0:f7f1f0d76dd6 416 STRING_HANDLE sasHandle = SASToken_Create(sharedAccessKey, hostName, keyName, expiry_time);
XinZhangMS 0:f7f1f0d76dd6 417 if (sasHandle == NULL)
XinZhangMS 0:f7f1f0d76dd6 418 {
XinZhangMS 0:f7f1f0d76dd6 419 LogError("SASToken_Create failed");
XinZhangMS 0:f7f1f0d76dd6 420 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 421 }
XinZhangMS 0:f7f1f0d76dd6 422 else if ((c_buffer = (const char*)STRING_c_str(sasHandle)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 423 {
XinZhangMS 0:f7f1f0d76dd6 424 LogError("STRING_c_str returned NULL");
XinZhangMS 0:f7f1f0d76dd6 425 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 426 }
XinZhangMS 0:f7f1f0d76dd6 427 else if (mallocAndStrcpy_s(&buffer, c_buffer) != 0)
XinZhangMS 0:f7f1f0d76dd6 428 {
XinZhangMS 0:f7f1f0d76dd6 429 LogError("mallocAndStrcpy_s failed for sharedAccessToken");
XinZhangMS 0:f7f1f0d76dd6 430 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 431 }
XinZhangMS 0:f7f1f0d76dd6 432 else
XinZhangMS 0:f7f1f0d76dd6 433 {
XinZhangMS 0:f7f1f0d76dd6 434 result = buffer;
XinZhangMS 0:f7f1f0d76dd6 435 }
XinZhangMS 0:f7f1f0d76dd6 436 STRING_delete(sasHandle);
XinZhangMS 0:f7f1f0d76dd6 437 }
XinZhangMS 0:f7f1f0d76dd6 438 STRING_delete(keyName);
XinZhangMS 0:f7f1f0d76dd6 439 STRING_delete(sharedAccessKey);
XinZhangMS 0:f7f1f0d76dd6 440 STRING_delete(hostName);
XinZhangMS 0:f7f1f0d76dd6 441 }
XinZhangMS 0:f7f1f0d76dd6 442 return result;
XinZhangMS 0:f7f1f0d76dd6 443 }
XinZhangMS 0:f7f1f0d76dd6 444
XinZhangMS 0:f7f1f0d76dd6 445 static char* createAuthCid(IOTHUB_MESSAGING_HANDLE messagingHandle)
XinZhangMS 0:f7f1f0d76dd6 446 {
XinZhangMS 0:f7f1f0d76dd6 447 char* result;
XinZhangMS 0:f7f1f0d76dd6 448
XinZhangMS 0:f7f1f0d76dd6 449 char* buffer = NULL;
XinZhangMS 0:f7f1f0d76dd6 450 if (messagingHandle->iothubName == NULL)
XinZhangMS 0:f7f1f0d76dd6 451 {
XinZhangMS 0:f7f1f0d76dd6 452 LogError("createSasPlainConfig failed - iothubName cannot be NULL");
XinZhangMS 0:f7f1f0d76dd6 453 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 454 }
XinZhangMS 0:f7f1f0d76dd6 455 else
XinZhangMS 0:f7f1f0d76dd6 456 {
XinZhangMS 0:f7f1f0d76dd6 457 const char* AMQP_SEND_AUTHCID_FMT = "iothubowner@sas.root.%s";
XinZhangMS 0:f7f1f0d76dd6 458 size_t authCidLen = strlen(AMQP_SEND_AUTHCID_FMT) + strlen(messagingHandle->iothubName);
XinZhangMS 0:f7f1f0d76dd6 459
XinZhangMS 0:f7f1f0d76dd6 460 if ((buffer = (char*)malloc(authCidLen + 1)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 461 {
XinZhangMS 0:f7f1f0d76dd6 462 LogError("Malloc failed for authCid.");
XinZhangMS 0:f7f1f0d76dd6 463 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 464 }
XinZhangMS 0:f7f1f0d76dd6 465 else if ((snprintf(buffer, authCidLen + 1, AMQP_SEND_AUTHCID_FMT, messagingHandle->iothubName)) < 0)
XinZhangMS 0:f7f1f0d76dd6 466 {
XinZhangMS 0:f7f1f0d76dd6 467 LogError("sprintf_s failed for authCid.");
XinZhangMS 0:f7f1f0d76dd6 468 free(buffer);
XinZhangMS 0:f7f1f0d76dd6 469 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 470 }
XinZhangMS 0:f7f1f0d76dd6 471 else
XinZhangMS 0:f7f1f0d76dd6 472 {
XinZhangMS 0:f7f1f0d76dd6 473 result = buffer;
XinZhangMS 0:f7f1f0d76dd6 474 }
XinZhangMS 0:f7f1f0d76dd6 475 }
XinZhangMS 0:f7f1f0d76dd6 476 return result;
XinZhangMS 0:f7f1f0d76dd6 477 }
XinZhangMS 0:f7f1f0d76dd6 478
XinZhangMS 0:f7f1f0d76dd6 479 static char* createReceiveTargetAddress(IOTHUB_MESSAGING_HANDLE messagingHandle)
XinZhangMS 0:f7f1f0d76dd6 480 {
XinZhangMS 0:f7f1f0d76dd6 481 char* result;
XinZhangMS 0:f7f1f0d76dd6 482
XinZhangMS 0:f7f1f0d76dd6 483 char* buffer = NULL;
XinZhangMS 0:f7f1f0d76dd6 484 if (messagingHandle->hostname == NULL)
XinZhangMS 0:f7f1f0d76dd6 485 {
XinZhangMS 0:f7f1f0d76dd6 486 LogError("createSendTargetAddress failed - hostname cannot be NULL");
XinZhangMS 0:f7f1f0d76dd6 487 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 488 }
XinZhangMS 0:f7f1f0d76dd6 489 else
XinZhangMS 0:f7f1f0d76dd6 490 {
XinZhangMS 0:f7f1f0d76dd6 491 const char* AMQP_SEND_TARGET_ADDRESS_FMT = "amqps://%s/messages/servicebound/feedback";
XinZhangMS 0:f7f1f0d76dd6 492 size_t addressLen = strlen(AMQP_SEND_TARGET_ADDRESS_FMT) + strlen(messagingHandle->hostname);
XinZhangMS 0:f7f1f0d76dd6 493
XinZhangMS 0:f7f1f0d76dd6 494 if ((buffer = (char*)malloc(addressLen + 1)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 495 {
XinZhangMS 0:f7f1f0d76dd6 496 LogError("Malloc failed for receiveTargetAddress");
XinZhangMS 0:f7f1f0d76dd6 497 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 498 }
XinZhangMS 0:f7f1f0d76dd6 499 else if ((snprintf(buffer, addressLen + 1, AMQP_SEND_TARGET_ADDRESS_FMT, messagingHandle->hostname)) < 0)
XinZhangMS 0:f7f1f0d76dd6 500 {
XinZhangMS 0:f7f1f0d76dd6 501 LogError("sprintf_s failed for receiveTargetAddress.");
XinZhangMS 0:f7f1f0d76dd6 502 free((char*)buffer);
XinZhangMS 0:f7f1f0d76dd6 503 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 504 }
XinZhangMS 0:f7f1f0d76dd6 505 else
XinZhangMS 0:f7f1f0d76dd6 506 {
XinZhangMS 0:f7f1f0d76dd6 507 result = buffer;
XinZhangMS 0:f7f1f0d76dd6 508 }
XinZhangMS 0:f7f1f0d76dd6 509 }
XinZhangMS 0:f7f1f0d76dd6 510 return result;
XinZhangMS 0:f7f1f0d76dd6 511 }
XinZhangMS 0:f7f1f0d76dd6 512
XinZhangMS 0:f7f1f0d76dd6 513 static char* createSendTargetAddress(IOTHUB_MESSAGING_HANDLE messagingHandle)
XinZhangMS 0:f7f1f0d76dd6 514 {
XinZhangMS 0:f7f1f0d76dd6 515 char* result;
XinZhangMS 0:f7f1f0d76dd6 516
XinZhangMS 0:f7f1f0d76dd6 517 char* buffer = NULL;
XinZhangMS 0:f7f1f0d76dd6 518 if (messagingHandle->hostname == NULL)
XinZhangMS 0:f7f1f0d76dd6 519 {
XinZhangMS 0:f7f1f0d76dd6 520 /*Codes_SRS_IOTHUBMESSAGING_12_077: [ If the messagingHandle->hostname input parameter is NULL IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_INVALID_ARG ] */
XinZhangMS 0:f7f1f0d76dd6 521 LogError("createSendTargetAddress failed - hostname cannot be NULL");
XinZhangMS 0:f7f1f0d76dd6 522 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 523 }
XinZhangMS 0:f7f1f0d76dd6 524 else
XinZhangMS 0:f7f1f0d76dd6 525 {
XinZhangMS 0:f7f1f0d76dd6 526 const char* AMQP_SEND_TARGET_ADDRESS_FMT = "amqps://%s/messages/deviceBound";
XinZhangMS 0:f7f1f0d76dd6 527 size_t addressLen = strlen(AMQP_SEND_TARGET_ADDRESS_FMT) + strlen(messagingHandle->hostname);
XinZhangMS 0:f7f1f0d76dd6 528
XinZhangMS 0:f7f1f0d76dd6 529 if ((buffer = (char*)malloc(addressLen + 1)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 530 {
XinZhangMS 0:f7f1f0d76dd6 531 LogError("Malloc failed for sendTargetAddress");
XinZhangMS 0:f7f1f0d76dd6 532 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 533 }
XinZhangMS 0:f7f1f0d76dd6 534 else if ((snprintf(buffer, addressLen + 1, AMQP_SEND_TARGET_ADDRESS_FMT, messagingHandle->hostname)) < 0)
XinZhangMS 0:f7f1f0d76dd6 535 {
XinZhangMS 0:f7f1f0d76dd6 536 LogError("sprintf_s failed for sendTargetAddress.");
XinZhangMS 0:f7f1f0d76dd6 537 free((char*)buffer);
XinZhangMS 0:f7f1f0d76dd6 538 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 539 }
XinZhangMS 0:f7f1f0d76dd6 540 else
XinZhangMS 0:f7f1f0d76dd6 541 {
XinZhangMS 0:f7f1f0d76dd6 542 result = buffer;
XinZhangMS 0:f7f1f0d76dd6 543 }
XinZhangMS 0:f7f1f0d76dd6 544 }
XinZhangMS 0:f7f1f0d76dd6 545 return result;
XinZhangMS 0:f7f1f0d76dd6 546 }
XinZhangMS 0:f7f1f0d76dd6 547
XinZhangMS 0:f7f1f0d76dd6 548 static char* createDeviceDestinationString(const char* deviceId, const char* moduleId)
XinZhangMS 0:f7f1f0d76dd6 549 {
XinZhangMS 0:f7f1f0d76dd6 550 char* result;
XinZhangMS 0:f7f1f0d76dd6 551
XinZhangMS 0:f7f1f0d76dd6 552 if (deviceId == NULL)
XinZhangMS 0:f7f1f0d76dd6 553 {
XinZhangMS 0:f7f1f0d76dd6 554 LogError("createDeviceDestinationString failed - deviceId cannot be NULL");
XinZhangMS 0:f7f1f0d76dd6 555 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 556 }
XinZhangMS 0:f7f1f0d76dd6 557 else
XinZhangMS 0:f7f1f0d76dd6 558 {
XinZhangMS 0:f7f1f0d76dd6 559 size_t deviceDestLen = strlen(AMQP_ADDRESS_PATH_MODULE_FMT) + strlen(deviceId) + (moduleId == NULL ? 0 : strlen(moduleId)) + 1;
XinZhangMS 0:f7f1f0d76dd6 560
XinZhangMS 0:f7f1f0d76dd6 561 char* buffer = (char*)malloc(deviceDestLen);
XinZhangMS 0:f7f1f0d76dd6 562 if (buffer == NULL)
XinZhangMS 0:f7f1f0d76dd6 563 {
XinZhangMS 0:f7f1f0d76dd6 564 LogError("Could not create device destination string.");
XinZhangMS 0:f7f1f0d76dd6 565 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 566 }
XinZhangMS 0:f7f1f0d76dd6 567 else
XinZhangMS 0:f7f1f0d76dd6 568 {
XinZhangMS 0:f7f1f0d76dd6 569 if ((moduleId == NULL) && (snprintf(buffer, deviceDestLen, AMQP_ADDRESS_PATH_FMT, deviceId)) < 0)
XinZhangMS 0:f7f1f0d76dd6 570 {
XinZhangMS 0:f7f1f0d76dd6 571 LogError("sprintf_s failed for deviceDestinationString.");
XinZhangMS 0:f7f1f0d76dd6 572 free((char*)buffer);
XinZhangMS 0:f7f1f0d76dd6 573 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 574 }
XinZhangMS 0:f7f1f0d76dd6 575 else if ((moduleId != NULL) && (snprintf(buffer, deviceDestLen, AMQP_ADDRESS_PATH_MODULE_FMT, deviceId, moduleId)) < 0)
XinZhangMS 0:f7f1f0d76dd6 576 {
XinZhangMS 0:f7f1f0d76dd6 577 LogError("sprintf_s failed for deviceDestinationString for module.");
XinZhangMS 0:f7f1f0d76dd6 578 free((char*)buffer);
XinZhangMS 0:f7f1f0d76dd6 579 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 580 }
XinZhangMS 0:f7f1f0d76dd6 581 else
XinZhangMS 0:f7f1f0d76dd6 582 {
XinZhangMS 0:f7f1f0d76dd6 583 result = buffer;
XinZhangMS 0:f7f1f0d76dd6 584 }
XinZhangMS 0:f7f1f0d76dd6 585 }
XinZhangMS 0:f7f1f0d76dd6 586 }
XinZhangMS 0:f7f1f0d76dd6 587 return result;
XinZhangMS 0:f7f1f0d76dd6 588 }
XinZhangMS 0:f7f1f0d76dd6 589
XinZhangMS 0:f7f1f0d76dd6 590 static void IoTHubMessaging_LL_SenderStateChanged(void* context, MESSAGE_SENDER_STATE new_state, MESSAGE_SENDER_STATE previous_state)
XinZhangMS 0:f7f1f0d76dd6 591 {
XinZhangMS 0:f7f1f0d76dd6 592 (void)previous_state;
XinZhangMS 0:f7f1f0d76dd6 593 if (context != NULL)
XinZhangMS 0:f7f1f0d76dd6 594 {
XinZhangMS 0:f7f1f0d76dd6 595 /*Codes_SRS_IOTHUBMESSAGING_12_049: [ IoTHubMessaging_LL_SenderStateChanged shall save the new_state to local variable ] */
XinZhangMS 0:f7f1f0d76dd6 596 IOTHUB_MESSAGING* messagingData = (IOTHUB_MESSAGING*)context;
XinZhangMS 0:f7f1f0d76dd6 597 messagingData->message_sender_state = new_state;
XinZhangMS 0:f7f1f0d76dd6 598
XinZhangMS 0:f7f1f0d76dd6 599 if ((messagingData->message_sender_state == MESSAGE_SENDER_STATE_OPEN) && (messagingData->message_receiver_state == MESSAGE_RECEIVER_STATE_OPEN))
XinZhangMS 0:f7f1f0d76dd6 600 {
XinZhangMS 0:f7f1f0d76dd6 601 /*Codes_SRS_IOTHUBMESSAGING_12_050: [ If both sender and receiver state is open IoTHubMessaging_LL_SenderStateChanged shall set the isOpened local variable to true ] */
XinZhangMS 0:f7f1f0d76dd6 602 messagingData->isOpened = true;
XinZhangMS 0:f7f1f0d76dd6 603 if (messagingData->callback_data->openCompleteCompleteCallback != NULL)
XinZhangMS 0:f7f1f0d76dd6 604 {
XinZhangMS 0:f7f1f0d76dd6 605 (messagingData->callback_data->openCompleteCompleteCallback)(messagingData->callback_data->openUserContext);
XinZhangMS 0:f7f1f0d76dd6 606 }
XinZhangMS 0:f7f1f0d76dd6 607 }
XinZhangMS 0:f7f1f0d76dd6 608 else
XinZhangMS 0:f7f1f0d76dd6 609 {
XinZhangMS 0:f7f1f0d76dd6 610 /*Codes_SRS_IOTHUBMESSAGING_12_051: [ If neither sender_state nor receiver_state is open IoTHubMessaging_LL_SenderStateChanged shall set the local isOpened variable to false ] */
XinZhangMS 0:f7f1f0d76dd6 611 messagingData->isOpened = false;
XinZhangMS 0:f7f1f0d76dd6 612 }
XinZhangMS 0:f7f1f0d76dd6 613 }
XinZhangMS 0:f7f1f0d76dd6 614 }
XinZhangMS 0:f7f1f0d76dd6 615
XinZhangMS 0:f7f1f0d76dd6 616 static void IoTHubMessaging_LL_ReceiverStateChanged(const void* context, MESSAGE_RECEIVER_STATE new_state, MESSAGE_RECEIVER_STATE previous_state)
XinZhangMS 0:f7f1f0d76dd6 617 {
XinZhangMS 0:f7f1f0d76dd6 618 (void)previous_state;
XinZhangMS 0:f7f1f0d76dd6 619 if (context != NULL)
XinZhangMS 0:f7f1f0d76dd6 620 {
XinZhangMS 0:f7f1f0d76dd6 621 /*Codes_SRS_IOTHUBMESSAGING_12_052: [ IoTHubMessaging_LL_ReceiverStateChanged shall save the new_state to local variable ] */
XinZhangMS 0:f7f1f0d76dd6 622 IOTHUB_MESSAGING* messagingData = (IOTHUB_MESSAGING*)context;
XinZhangMS 0:f7f1f0d76dd6 623 messagingData->message_receiver_state = new_state;
XinZhangMS 0:f7f1f0d76dd6 624
XinZhangMS 0:f7f1f0d76dd6 625 if ((messagingData->message_sender_state == MESSAGE_SENDER_STATE_OPEN) && (messagingData->message_receiver_state == MESSAGE_RECEIVER_STATE_OPEN))
XinZhangMS 0:f7f1f0d76dd6 626 {
XinZhangMS 0:f7f1f0d76dd6 627 /*Codes_SRS_IOTHUBMESSAGING_12_053: [ If both sender and receiver state is open IoTHubMessaging_LL_ReceiverStateChanged shall set the isOpened local variable to true ] */
XinZhangMS 0:f7f1f0d76dd6 628 messagingData->isOpened = true;
XinZhangMS 0:f7f1f0d76dd6 629 if (messagingData->callback_data->openCompleteCompleteCallback != NULL)
XinZhangMS 0:f7f1f0d76dd6 630 {
XinZhangMS 0:f7f1f0d76dd6 631 (messagingData->callback_data->openCompleteCompleteCallback)(messagingData->callback_data->openUserContext);
XinZhangMS 0:f7f1f0d76dd6 632 }
XinZhangMS 0:f7f1f0d76dd6 633 }
XinZhangMS 0:f7f1f0d76dd6 634 else
XinZhangMS 0:f7f1f0d76dd6 635 {
XinZhangMS 0:f7f1f0d76dd6 636 /*Codes_SRS_IOTHUBMESSAGING_12_054: [ If neither sender_state nor receiver_state is open IoTHubMessaging_LL_ReceiverStateChanged shall set the local isOpened variable to false ] */
XinZhangMS 0:f7f1f0d76dd6 637 messagingData->isOpened = false;
XinZhangMS 0:f7f1f0d76dd6 638 }
XinZhangMS 0:f7f1f0d76dd6 639 }
XinZhangMS 0:f7f1f0d76dd6 640 }
XinZhangMS 0:f7f1f0d76dd6 641
XinZhangMS 0:f7f1f0d76dd6 642 static void IoTHubMessaging_LL_SendMessageComplete(void* context, IOTHUB_MESSAGING_RESULT send_result)
XinZhangMS 0:f7f1f0d76dd6 643 {
XinZhangMS 0:f7f1f0d76dd6 644 /*Codes_SRS_IOTHUBMESSAGING_12_056: [ If context is NULL IoTHubMessaging_LL_SendMessageComplete shall return ] */
XinZhangMS 0:f7f1f0d76dd6 645 if (context != NULL)
XinZhangMS 0:f7f1f0d76dd6 646 {
XinZhangMS 0:f7f1f0d76dd6 647 /*Codes_SRS_IOTHUBMESSAGING_12_055: [ If context is not NULL and IoTHubMessaging_LL_SendMessageComplete shall call user callback with user context and messaging result ] */
XinZhangMS 0:f7f1f0d76dd6 648 IOTHUB_MESSAGING* messagingData = (IOTHUB_MESSAGING*)context;
XinZhangMS 0:f7f1f0d76dd6 649 if (messagingData->callback_data->sendCompleteCallback != NULL)
XinZhangMS 0:f7f1f0d76dd6 650 {
XinZhangMS 0:f7f1f0d76dd6 651 (messagingData->callback_data->sendCompleteCallback)(messagingData->callback_data->sendUserContext, send_result);
XinZhangMS 0:f7f1f0d76dd6 652 }
XinZhangMS 0:f7f1f0d76dd6 653 }
XinZhangMS 0:f7f1f0d76dd6 654 }
XinZhangMS 0:f7f1f0d76dd6 655
XinZhangMS 0:f7f1f0d76dd6 656 static AMQP_VALUE IoTHubMessaging_LL_FeedbackMessageReceived(const void* context, MESSAGE_HANDLE message)
XinZhangMS 0:f7f1f0d76dd6 657 {
XinZhangMS 0:f7f1f0d76dd6 658 AMQP_VALUE result;
XinZhangMS 0:f7f1f0d76dd6 659
XinZhangMS 0:f7f1f0d76dd6 660 /*Codes_SRS_IOTHUBMESSAGING_12_057: [ If context is NULL IoTHubMessaging_LL_FeedbackMessageReceived shall do nothing and return delivery_accepted ] */
XinZhangMS 0:f7f1f0d76dd6 661 if (context == NULL)
XinZhangMS 0:f7f1f0d76dd6 662 {
XinZhangMS 0:f7f1f0d76dd6 663 result = messaging_delivery_accepted();
XinZhangMS 0:f7f1f0d76dd6 664 }
XinZhangMS 0:f7f1f0d76dd6 665 else
XinZhangMS 0:f7f1f0d76dd6 666 {
XinZhangMS 0:f7f1f0d76dd6 667 IOTHUB_MESSAGING* messagingData = (IOTHUB_MESSAGING*)context;
XinZhangMS 0:f7f1f0d76dd6 668
XinZhangMS 0:f7f1f0d76dd6 669 BINARY_DATA binary_data;
XinZhangMS 0:f7f1f0d76dd6 670 JSON_Value* root_value = NULL;
XinZhangMS 0:f7f1f0d76dd6 671 JSON_Object* feedback_object = NULL;
XinZhangMS 0:f7f1f0d76dd6 672 JSON_Array* feedback_array = NULL;
XinZhangMS 0:f7f1f0d76dd6 673
XinZhangMS 0:f7f1f0d76dd6 674 /*Codes_SRS_IOTHUBMESSAGING_12_058: [ If context is not NULL IoTHubMessaging_LL_FeedbackMessageReceived shall get the content string of the message by calling message_get_body_amqp_data ] */
XinZhangMS 0:f7f1f0d76dd6 675 /*Codes_SRS_IOTHUBMESSAGING_12_059: [ IoTHubMessaging_LL_FeedbackMessageReceived shall parse the response JSON to IOTHUB_SERVICE_FEEDBACK_BATCH struct ] */
XinZhangMS 0:f7f1f0d76dd6 676 /*Codes_SRS_IOTHUBMESSAGING_12_060: [ IoTHubMessaging_LL_FeedbackMessageReceived shall use the following parson APIs to parse the response string: json_parse_string, json_value_get_object, json_object_get_string, json_object_dotget_string ] */
XinZhangMS 0:f7f1f0d76dd6 677 if (message_get_body_amqp_data_in_place(message, 0, &binary_data) != 0)
XinZhangMS 0:f7f1f0d76dd6 678 {
XinZhangMS 0:f7f1f0d76dd6 679 /*Codes_SRS_IOTHUBMESSAGING_12_061: [ If any of the parson API fails, IoTHubMessaging_LL_FeedbackMessageReceived shall return IOTHUB_MESSAGING_INVALID_JSON ] */
XinZhangMS 0:f7f1f0d76dd6 680 LogError("Cannot get message data");
XinZhangMS 0:f7f1f0d76dd6 681 result = messaging_delivery_rejected("Rejected due to failure reading AMQP message", "Failed reading message body");
XinZhangMS 0:f7f1f0d76dd6 682 }
XinZhangMS 0:f7f1f0d76dd6 683 else if ((root_value = json_parse_string((const char*)binary_data.bytes)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 684 {
XinZhangMS 0:f7f1f0d76dd6 685 /*Codes_SRS_IOTHUBMESSAGING_12_061: [ If any of the parson API fails, IoTHubMessaging_LL_FeedbackMessageReceived shall return IOTHUB_MESSAGING_INVALID_JSON ] */
XinZhangMS 0:f7f1f0d76dd6 686 LogError("json_parse_string failed");
XinZhangMS 0:f7f1f0d76dd6 687 result = messaging_delivery_rejected("Rejected due to failure reading AMQP message", "Failed parsing json root");
XinZhangMS 0:f7f1f0d76dd6 688 }
XinZhangMS 0:f7f1f0d76dd6 689 else if ((feedback_array = json_value_get_array(root_value)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 690 {
XinZhangMS 0:f7f1f0d76dd6 691 /*Codes_SRS_IOTHUBMESSAGING_12_061: [ If any of the parson API fails, IoTHubMessaging_LL_FeedbackMessageReceived shall return IOTHUB_MESSAGING_INVALID_JSON ] */
XinZhangMS 0:f7f1f0d76dd6 692 LogError("json_parse_string failed");
XinZhangMS 0:f7f1f0d76dd6 693 result = messaging_delivery_rejected("Rejected due to failure reading AMQP message", "Failed parsing json array");
XinZhangMS 0:f7f1f0d76dd6 694 }
XinZhangMS 0:f7f1f0d76dd6 695 else if (json_array_get_count(feedback_array) == 0)
XinZhangMS 0:f7f1f0d76dd6 696 {
XinZhangMS 0:f7f1f0d76dd6 697 /*Codes_SRS_IOTHUBMESSAGING_12_061: [ If any of the parson API fails, IoTHubMessaging_LL_FeedbackMessageReceived shall return IOTHUB_MESSAGING_INVALID_JSON ] */
XinZhangMS 0:f7f1f0d76dd6 698 LogError("json_array_get_count failed");
XinZhangMS 0:f7f1f0d76dd6 699 result = messaging_delivery_rejected("Rejected due to failure reading AMQP message", "json_array_get_count failed");
XinZhangMS 0:f7f1f0d76dd6 700 }
XinZhangMS 0:f7f1f0d76dd6 701 else
XinZhangMS 0:f7f1f0d76dd6 702 {
XinZhangMS 0:f7f1f0d76dd6 703 IOTHUB_SERVICE_FEEDBACK_BATCH* feedbackBatch;
XinZhangMS 0:f7f1f0d76dd6 704
XinZhangMS 0:f7f1f0d76dd6 705 if ((feedbackBatch = (IOTHUB_SERVICE_FEEDBACK_BATCH*)malloc(sizeof(IOTHUB_SERVICE_FEEDBACK_BATCH))) == NULL)
XinZhangMS 0:f7f1f0d76dd6 706 {
XinZhangMS 0:f7f1f0d76dd6 707 /*Codes_SRS_IOTHUBMESSAGING_12_061: [ If any of the parson API fails, IoTHubMessaging_LL_FeedbackMessageReceived shall return IOTHUB_MESSAGING_INVALID_JSON ] */
XinZhangMS 0:f7f1f0d76dd6 708 LogError("json_parse_string failed");
XinZhangMS 0:f7f1f0d76dd6 709 result = messaging_delivery_rejected("Rejected due to failure reading AMQP message", "Failed to allocate memory for feedback batch");
XinZhangMS 0:f7f1f0d76dd6 710 }
XinZhangMS 0:f7f1f0d76dd6 711 else
XinZhangMS 0:f7f1f0d76dd6 712 {
XinZhangMS 0:f7f1f0d76dd6 713 size_t array_count = 0;
XinZhangMS 0:f7f1f0d76dd6 714 if ((array_count = json_array_get_count(feedback_array)) <= 0)
XinZhangMS 0:f7f1f0d76dd6 715 {
XinZhangMS 0:f7f1f0d76dd6 716 /*Codes_SRS_IOTHUBMESSAGING_12_061: [ If any of the parson API fails, IoTHubMessaging_LL_FeedbackMessageReceived shall return IOTHUB_MESSAGING_INVALID_JSON ] */
XinZhangMS 0:f7f1f0d76dd6 717 LogError("json_array_get_count failed");
XinZhangMS 0:f7f1f0d76dd6 718 free(feedbackBatch);
XinZhangMS 0:f7f1f0d76dd6 719 result = messaging_delivery_rejected("Rejected due to failure reading AMQP message", "json_array_get_count failed");
XinZhangMS 0:f7f1f0d76dd6 720 }
XinZhangMS 0:f7f1f0d76dd6 721 else if ((feedbackBatch->feedbackRecordList = singlylinkedlist_create()) == NULL)
XinZhangMS 0:f7f1f0d76dd6 722 {
XinZhangMS 0:f7f1f0d76dd6 723 /*Codes_SRS_IOTHUBMESSAGING_12_061: [ If any of the parson API fails, IoTHubMessaging_LL_FeedbackMessageReceived shall return IOTHUB_MESSAGING_INVALID_JSON ] */
XinZhangMS 0:f7f1f0d76dd6 724 LogError("singlylinkedlist_create failed");
XinZhangMS 0:f7f1f0d76dd6 725 free(feedbackBatch);
XinZhangMS 0:f7f1f0d76dd6 726 result = messaging_delivery_rejected("Rejected due to failure reading AMQP message", "singlylinkedlist_create failed");
XinZhangMS 0:f7f1f0d76dd6 727 }
XinZhangMS 0:f7f1f0d76dd6 728 else
XinZhangMS 0:f7f1f0d76dd6 729 {
XinZhangMS 0:f7f1f0d76dd6 730 bool isLoopFailed = false;
XinZhangMS 0:f7f1f0d76dd6 731 for (size_t i = 0; i < array_count; i++)
XinZhangMS 0:f7f1f0d76dd6 732 {
XinZhangMS 0:f7f1f0d76dd6 733 if ((feedback_object = json_array_get_object(feedback_array, i)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 734 {
XinZhangMS 0:f7f1f0d76dd6 735 isLoopFailed = true;
XinZhangMS 0:f7f1f0d76dd6 736 break;
XinZhangMS 0:f7f1f0d76dd6 737 }
XinZhangMS 0:f7f1f0d76dd6 738 else
XinZhangMS 0:f7f1f0d76dd6 739 {
XinZhangMS 0:f7f1f0d76dd6 740 IOTHUB_SERVICE_FEEDBACK_RECORD* feedbackRecord;
XinZhangMS 0:f7f1f0d76dd6 741 if ((feedbackRecord = (IOTHUB_SERVICE_FEEDBACK_RECORD*)malloc(sizeof(IOTHUB_SERVICE_FEEDBACK_RECORD))) == NULL)
XinZhangMS 0:f7f1f0d76dd6 742 {
XinZhangMS 0:f7f1f0d76dd6 743 isLoopFailed = true;
XinZhangMS 0:f7f1f0d76dd6 744 break;
XinZhangMS 0:f7f1f0d76dd6 745 }
XinZhangMS 0:f7f1f0d76dd6 746 else
XinZhangMS 0:f7f1f0d76dd6 747 {
XinZhangMS 0:f7f1f0d76dd6 748 feedbackRecord->deviceId = (char*)json_object_get_string(feedback_object, FEEDBACK_RECORD_KEY_DEVICE_ID);
XinZhangMS 0:f7f1f0d76dd6 749 feedbackRecord->generationId = (char*)json_object_get_string(feedback_object, FEEDBACK_RECORD_KEY_DEVICE_GENERATION_ID);
XinZhangMS 0:f7f1f0d76dd6 750 feedbackRecord->description = (char*)json_object_get_string(feedback_object, FEEDBACK_RECORD_KEY_DESCRIPTION);
XinZhangMS 0:f7f1f0d76dd6 751 feedbackRecord->enqueuedTimeUtc = (char*)json_object_get_string(feedback_object, FEEDBACK_RECORD_KEY_ENQUED_TIME_UTC);
XinZhangMS 0:f7f1f0d76dd6 752 feedbackRecord->originalMessageId = (char*)json_object_get_string(feedback_object, FEEDBACK_RECORD_KEY_ORIGINAL_MESSAGE_ID);
XinZhangMS 0:f7f1f0d76dd6 753 feedbackRecord->correlationId = "";
XinZhangMS 0:f7f1f0d76dd6 754
XinZhangMS 0:f7f1f0d76dd6 755 if (feedbackRecord->description == NULL)
XinZhangMS 0:f7f1f0d76dd6 756 {
XinZhangMS 0:f7f1f0d76dd6 757 feedbackRecord->statusCode = IOTHUB_FEEDBACK_STATUS_CODE_UNKNOWN;
XinZhangMS 0:f7f1f0d76dd6 758 }
XinZhangMS 0:f7f1f0d76dd6 759 else
XinZhangMS 0:f7f1f0d76dd6 760 {
XinZhangMS 0:f7f1f0d76dd6 761 size_t j;
XinZhangMS 0:f7f1f0d76dd6 762 for (j = 0; feedbackRecord->description[j]; j++)
XinZhangMS 0:f7f1f0d76dd6 763 {
XinZhangMS 0:f7f1f0d76dd6 764 feedbackRecord->description[j] = (char)tolower(feedbackRecord->description[j]);
XinZhangMS 0:f7f1f0d76dd6 765 }
XinZhangMS 0:f7f1f0d76dd6 766
XinZhangMS 0:f7f1f0d76dd6 767 if (strcmp(feedbackRecord->description, "success") == 0)
XinZhangMS 0:f7f1f0d76dd6 768 {
XinZhangMS 0:f7f1f0d76dd6 769 feedbackRecord->statusCode = IOTHUB_FEEDBACK_STATUS_CODE_SUCCESS;
XinZhangMS 0:f7f1f0d76dd6 770 }
XinZhangMS 0:f7f1f0d76dd6 771 else if (strcmp(feedbackRecord->description, "expired") == 0)
XinZhangMS 0:f7f1f0d76dd6 772 {
XinZhangMS 0:f7f1f0d76dd6 773 feedbackRecord->statusCode = IOTHUB_FEEDBACK_STATUS_CODE_EXPIRED;
XinZhangMS 0:f7f1f0d76dd6 774 }
XinZhangMS 0:f7f1f0d76dd6 775 else if (strcmp(feedbackRecord->description, "deliverycountexceeded") == 0)
XinZhangMS 0:f7f1f0d76dd6 776 {
XinZhangMS 0:f7f1f0d76dd6 777 feedbackRecord->statusCode = IOTHUB_FEEDBACK_STATUS_CODE_DELIVER_COUNT_EXCEEDED;
XinZhangMS 0:f7f1f0d76dd6 778 }
XinZhangMS 0:f7f1f0d76dd6 779 else if (strcmp(feedbackRecord->description, "rejected") == 0)
XinZhangMS 0:f7f1f0d76dd6 780 {
XinZhangMS 0:f7f1f0d76dd6 781 feedbackRecord->statusCode = IOTHUB_FEEDBACK_STATUS_CODE_REJECTED;
XinZhangMS 0:f7f1f0d76dd6 782 }
XinZhangMS 0:f7f1f0d76dd6 783 else
XinZhangMS 0:f7f1f0d76dd6 784 {
XinZhangMS 0:f7f1f0d76dd6 785 feedbackRecord->statusCode = IOTHUB_FEEDBACK_STATUS_CODE_UNKNOWN;
XinZhangMS 0:f7f1f0d76dd6 786 }
XinZhangMS 0:f7f1f0d76dd6 787 }
XinZhangMS 0:f7f1f0d76dd6 788 singlylinkedlist_add(feedbackBatch->feedbackRecordList, feedbackRecord);
XinZhangMS 0:f7f1f0d76dd6 789 }
XinZhangMS 0:f7f1f0d76dd6 790 }
XinZhangMS 0:f7f1f0d76dd6 791 }
XinZhangMS 0:f7f1f0d76dd6 792 feedbackBatch->lockToken = "";
XinZhangMS 0:f7f1f0d76dd6 793 feedbackBatch->userId = "";
XinZhangMS 0:f7f1f0d76dd6 794
XinZhangMS 0:f7f1f0d76dd6 795 if (isLoopFailed)
XinZhangMS 0:f7f1f0d76dd6 796 {
XinZhangMS 0:f7f1f0d76dd6 797 LogError("Failed to read feedback records");
XinZhangMS 0:f7f1f0d76dd6 798 result = messaging_delivery_rejected("Rejected due to failure reading AMQP message", "Failed to read feedback records");
XinZhangMS 0:f7f1f0d76dd6 799 }
XinZhangMS 0:f7f1f0d76dd6 800 else
XinZhangMS 0:f7f1f0d76dd6 801 {
XinZhangMS 0:f7f1f0d76dd6 802 if (messagingData->callback_data->feedbackMessageCallback != NULL)
XinZhangMS 0:f7f1f0d76dd6 803 {
XinZhangMS 0:f7f1f0d76dd6 804 /*Codes_SRS_IOTHUBMESSAGING_12_062: [ If context is not NULL IoTHubMessaging_LL_FeedbackMessageReceived shall call IOTHUB_FEEDBACK_MESSAGE_RECEIVED_CALLBACK with the received IOTHUB_SERVICE_FEEDBACK_BATCH ] */
XinZhangMS 0:f7f1f0d76dd6 805 (messagingData->callback_data->feedbackMessageCallback)(messagingData->callback_data->feedbackUserContext, feedbackBatch);
XinZhangMS 0:f7f1f0d76dd6 806 }
XinZhangMS 0:f7f1f0d76dd6 807 result = messaging_delivery_accepted();
XinZhangMS 0:f7f1f0d76dd6 808 }
XinZhangMS 0:f7f1f0d76dd6 809
XinZhangMS 0:f7f1f0d76dd6 810 /*Codes_SRS_IOTHUBMESSAGING_12_078: [** IoTHubMessaging_LL_FeedbackMessageReceived shall do clean up before exits ] */
XinZhangMS 0:f7f1f0d76dd6 811 LIST_ITEM_HANDLE feedbackRecord = singlylinkedlist_get_head_item(feedbackBatch->feedbackRecordList);
XinZhangMS 0:f7f1f0d76dd6 812 while (feedbackRecord != NULL)
XinZhangMS 0:f7f1f0d76dd6 813 {
XinZhangMS 0:f7f1f0d76dd6 814 IOTHUB_SERVICE_FEEDBACK_RECORD* feedback = (IOTHUB_SERVICE_FEEDBACK_RECORD*)singlylinkedlist_item_get_value(feedbackRecord);
XinZhangMS 0:f7f1f0d76dd6 815 feedbackRecord = singlylinkedlist_get_next_item(feedbackRecord);
XinZhangMS 0:f7f1f0d76dd6 816 free(feedback);
XinZhangMS 0:f7f1f0d76dd6 817 }
XinZhangMS 0:f7f1f0d76dd6 818 singlylinkedlist_destroy(feedbackBatch->feedbackRecordList);
XinZhangMS 0:f7f1f0d76dd6 819 free(feedbackBatch);
XinZhangMS 0:f7f1f0d76dd6 820 }
XinZhangMS 0:f7f1f0d76dd6 821 }
XinZhangMS 0:f7f1f0d76dd6 822 }
XinZhangMS 0:f7f1f0d76dd6 823 json_array_clear(feedback_array);
XinZhangMS 0:f7f1f0d76dd6 824 json_value_free(root_value);
XinZhangMS 0:f7f1f0d76dd6 825 }
XinZhangMS 0:f7f1f0d76dd6 826 return result;
XinZhangMS 0:f7f1f0d76dd6 827 }
XinZhangMS 0:f7f1f0d76dd6 828
XinZhangMS 0:f7f1f0d76dd6 829 IOTHUB_MESSAGING_HANDLE IoTHubMessaging_LL_Create(IOTHUB_SERVICE_CLIENT_AUTH_HANDLE serviceClientHandle)
XinZhangMS 0:f7f1f0d76dd6 830 {
XinZhangMS 0:f7f1f0d76dd6 831 IOTHUB_MESSAGING_HANDLE result;
XinZhangMS 0:f7f1f0d76dd6 832 CALLBACK_DATA* callback_data;
XinZhangMS 0:f7f1f0d76dd6 833
XinZhangMS 0:f7f1f0d76dd6 834 /*Codes_SRS_IOTHUBMESSAGING_12_001: [ If the serviceClientHandle input parameter is NULL IoTHubMessaging_LL_Create shall return NULL ] */
XinZhangMS 0:f7f1f0d76dd6 835 if (serviceClientHandle == NULL)
XinZhangMS 0:f7f1f0d76dd6 836 {
XinZhangMS 0:f7f1f0d76dd6 837 LogError("serviceClientHandle input parameter cannot be NULL");
XinZhangMS 0:f7f1f0d76dd6 838 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 839 }
XinZhangMS 0:f7f1f0d76dd6 840 else
XinZhangMS 0:f7f1f0d76dd6 841 {
XinZhangMS 0:f7f1f0d76dd6 842 /*Codes_SRS_IOTHUBMESSAGING_12_064: [ If any member of the serviceClientHandle input parameter is NULL IoTHubMessaging_LL_Create shall return NULL ] */
XinZhangMS 0:f7f1f0d76dd6 843 IOTHUB_SERVICE_CLIENT_AUTH* serviceClientAuth = (IOTHUB_SERVICE_CLIENT_AUTH*)serviceClientHandle;
XinZhangMS 0:f7f1f0d76dd6 844
XinZhangMS 0:f7f1f0d76dd6 845 if (serviceClientAuth->hostname == NULL)
XinZhangMS 0:f7f1f0d76dd6 846 {
XinZhangMS 0:f7f1f0d76dd6 847 LogError("authInfo->hostName input parameter cannot be NULL");
XinZhangMS 0:f7f1f0d76dd6 848 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 849 }
XinZhangMS 0:f7f1f0d76dd6 850 else if (serviceClientAuth->iothubName == NULL)
XinZhangMS 0:f7f1f0d76dd6 851 {
XinZhangMS 0:f7f1f0d76dd6 852 LogError("authInfo->iothubName input parameter cannot be NULL");
XinZhangMS 0:f7f1f0d76dd6 853 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 854 }
XinZhangMS 0:f7f1f0d76dd6 855 else if (serviceClientAuth->iothubSuffix == NULL)
XinZhangMS 0:f7f1f0d76dd6 856 {
XinZhangMS 0:f7f1f0d76dd6 857 LogError("authInfo->iothubSuffix input parameter cannot be NULL");
XinZhangMS 0:f7f1f0d76dd6 858 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 859 }
XinZhangMS 0:f7f1f0d76dd6 860 else if (serviceClientAuth->keyName == NULL)
XinZhangMS 0:f7f1f0d76dd6 861 {
XinZhangMS 0:f7f1f0d76dd6 862 LogError("authInfo->keyName input parameter cannot be NULL");
XinZhangMS 0:f7f1f0d76dd6 863 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 864 }
XinZhangMS 0:f7f1f0d76dd6 865 else if (serviceClientAuth->sharedAccessKey == NULL)
XinZhangMS 0:f7f1f0d76dd6 866 {
XinZhangMS 0:f7f1f0d76dd6 867 LogError("authInfo->sharedAccessKey input parameter cannot be NULL");
XinZhangMS 0:f7f1f0d76dd6 868 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 869 }
XinZhangMS 0:f7f1f0d76dd6 870 else
XinZhangMS 0:f7f1f0d76dd6 871 {
XinZhangMS 0:f7f1f0d76dd6 872 /*Codes_SRS_IOTHUBMESSAGING_12_002: [ IoTHubMessaging_LL_Create shall allocate memory for a new messaging instance ] */
XinZhangMS 0:f7f1f0d76dd6 873 if ((result = (IOTHUB_MESSAGING*)malloc(sizeof(IOTHUB_MESSAGING))) == NULL)
XinZhangMS 0:f7f1f0d76dd6 874 {
XinZhangMS 0:f7f1f0d76dd6 875 /*Codes_SRS_IOTHUBMESSAGING_12_003: [ If the allocation failed, IoTHubMessaging_LL_Create shall return NULL ] */
XinZhangMS 0:f7f1f0d76dd6 876 LogError("Malloc failed for IOTHUB_REGISTRYMANAGER");
XinZhangMS 0:f7f1f0d76dd6 877 }
XinZhangMS 0:f7f1f0d76dd6 878 /*Codes_SRS_IOTHUBMESSAGING_12_004: [ If the allocation and creation is successful, IoTHubMessaging_LL_Create shall return with the messaging instance, a non-NULL value ] */
XinZhangMS 0:f7f1f0d76dd6 879 /*Codes_SRS_IOTHUBMESSAGING_12_065: [ IoTHubMessaging_LL_Create shall allocate memory and copy hostName to result->hostName by calling mallocAndStrcpy_s ] */
XinZhangMS 0:f7f1f0d76dd6 880 else if (mallocAndStrcpy_s(&result->hostname, serviceClientAuth->hostname) != 0)
XinZhangMS 0:f7f1f0d76dd6 881 {
XinZhangMS 0:f7f1f0d76dd6 882 /*Codes_SRS_IOTHUBMESSAGING_12_066: [ If the mallocAndStrcpy_s fails, IoTHubMessaging_LL_Create shall do clean up and return NULL ] */
XinZhangMS 0:f7f1f0d76dd6 883 LogError("mallocAndStrcpy_s failed for hostName");
XinZhangMS 0:f7f1f0d76dd6 884 free(result);
XinZhangMS 0:f7f1f0d76dd6 885 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 886 }
XinZhangMS 0:f7f1f0d76dd6 887 /*Codes_SRS_IOTHUBMESSAGING_12_067: [ IoTHubMessaging_LL_Create shall allocate memory and copy iothubName to result->iothubName by calling mallocAndStrcpy_s ] */
XinZhangMS 0:f7f1f0d76dd6 888 else if (mallocAndStrcpy_s(&result->iothubName, serviceClientAuth->iothubName) != 0)
XinZhangMS 0:f7f1f0d76dd6 889 {
XinZhangMS 0:f7f1f0d76dd6 890 /*Codes_SRS_IOTHUBMESSAGING_12_068: [ If the mallocAndStrcpy_s fails, IoTHubMessaging_LL_Create shall do clean up and return NULL ] */
XinZhangMS 0:f7f1f0d76dd6 891 LogError("mallocAndStrcpy_s failed for iothubName");
XinZhangMS 0:f7f1f0d76dd6 892 free(result->hostname);
XinZhangMS 0:f7f1f0d76dd6 893 free(result);
XinZhangMS 0:f7f1f0d76dd6 894 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 895 }
XinZhangMS 0:f7f1f0d76dd6 896 /*Codes_SRS_IOTHUBMESSAGING_12_069: [ IoTHubMessaging_LL_Create shall allocate memory and copy iothubSuffix to result->iothubSuffix by calling mallocAndStrcpy_s ] */
XinZhangMS 0:f7f1f0d76dd6 897 else if (mallocAndStrcpy_s(&result->iothubSuffix, serviceClientAuth->iothubSuffix) != 0)
XinZhangMS 0:f7f1f0d76dd6 898 {
XinZhangMS 0:f7f1f0d76dd6 899 /*Codes_SRS_IOTHUBMESSAGING_12_070: [ If the mallocAndStrcpy_s fails, IoTHubMessaging_LL_Create shall do clean up and return NULL ] */
XinZhangMS 0:f7f1f0d76dd6 900 LogError("mallocAndStrcpy_s failed for iothubSuffix");
XinZhangMS 0:f7f1f0d76dd6 901 free(result->hostname);
XinZhangMS 0:f7f1f0d76dd6 902 free(result->iothubName);
XinZhangMS 0:f7f1f0d76dd6 903 free(result);
XinZhangMS 0:f7f1f0d76dd6 904 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 905 }
XinZhangMS 0:f7f1f0d76dd6 906 /*Codes_SRS_IOTHUBMESSAGING_12_071: [ IoTHubMessaging_LL_Create shall allocate memory and copy sharedAccessKey to result->sharedAccessKey by calling mallocAndStrcpy_s ] */
XinZhangMS 0:f7f1f0d76dd6 907 else if (mallocAndStrcpy_s(&result->sharedAccessKey, serviceClientAuth->sharedAccessKey) != 0)
XinZhangMS 0:f7f1f0d76dd6 908 {
XinZhangMS 0:f7f1f0d76dd6 909 /*Codes_SRS_IOTHUBMESSAGING_12_072: [ If the mallocAndStrcpy_s fails, IoTHubMessaging_LL_Create shall do clean up and return NULL ] */
XinZhangMS 0:f7f1f0d76dd6 910 LogError("mallocAndStrcpy_s failed for sharedAccessKey");
XinZhangMS 0:f7f1f0d76dd6 911 free(result->hostname);
XinZhangMS 0:f7f1f0d76dd6 912 free(result->iothubName);
XinZhangMS 0:f7f1f0d76dd6 913 free(result->iothubSuffix);
XinZhangMS 0:f7f1f0d76dd6 914 free(result);
XinZhangMS 0:f7f1f0d76dd6 915 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 916 }
XinZhangMS 0:f7f1f0d76dd6 917 /*Codes_SRS_IOTHUBMESSAGING_12_073: [ IoTHubMessaging_LL_Create shall allocate memory and copy keyName to result->keyName by calling mallocAndStrcpy_s ] */
XinZhangMS 0:f7f1f0d76dd6 918 else if (mallocAndStrcpy_s(&result->keyName, serviceClientAuth->keyName) != 0)
XinZhangMS 0:f7f1f0d76dd6 919 {
XinZhangMS 0:f7f1f0d76dd6 920 /*Codes_SRS_IOTHUBMESSAGING_12_074: [ If the mallocAndStrcpy_s fails, IoTHubMessaging_LL_Create shall do clean up and return NULL ] */
XinZhangMS 0:f7f1f0d76dd6 921 LogError("mallocAndStrcpy_s failed for keyName");
XinZhangMS 0:f7f1f0d76dd6 922 free(result->hostname);
XinZhangMS 0:f7f1f0d76dd6 923 free(result->iothubName);
XinZhangMS 0:f7f1f0d76dd6 924 free(result->iothubSuffix);
XinZhangMS 0:f7f1f0d76dd6 925 free(result->sharedAccessKey);
XinZhangMS 0:f7f1f0d76dd6 926 free(result);
XinZhangMS 0:f7f1f0d76dd6 927 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 928 }
XinZhangMS 0:f7f1f0d76dd6 929 /*Codes_SRS_IOTHUBMESSAGING_12_075: [ IoTHubMessaging_LL_Create shall set messaging isOpened flag to false ] */
XinZhangMS 0:f7f1f0d76dd6 930 else if ((callback_data = (CALLBACK_DATA*)malloc(sizeof(CALLBACK_DATA))) == NULL)
XinZhangMS 0:f7f1f0d76dd6 931 {
XinZhangMS 0:f7f1f0d76dd6 932 /*Codes_SRS_IOTHUBMESSAGING_12_074: [ If the mallocAndStrcpy_s fails, IoTHubMessaging_LL_Create shall do clean up and return NULL ] */
XinZhangMS 0:f7f1f0d76dd6 933 LogError("Malloc failed for callback_data");
XinZhangMS 0:f7f1f0d76dd6 934 free(result->hostname);
XinZhangMS 0:f7f1f0d76dd6 935 free(result->iothubName);
XinZhangMS 0:f7f1f0d76dd6 936 free(result->iothubSuffix);
XinZhangMS 0:f7f1f0d76dd6 937 free(result->sharedAccessKey);
XinZhangMS 0:f7f1f0d76dd6 938 free(result->keyName);
XinZhangMS 0:f7f1f0d76dd6 939 free(result);
XinZhangMS 0:f7f1f0d76dd6 940 result = NULL;
XinZhangMS 0:f7f1f0d76dd6 941 }
XinZhangMS 0:f7f1f0d76dd6 942 else
XinZhangMS 0:f7f1f0d76dd6 943 {
XinZhangMS 0:f7f1f0d76dd6 944 /*Codes_SRS_IOTHUBMESSAGING_12_076: [ If create successfull IoTHubMessaging_LL_Create shall save the callback data return the valid messaging handle ] */
XinZhangMS 0:f7f1f0d76dd6 945 callback_data->openCompleteCompleteCallback = NULL;
XinZhangMS 0:f7f1f0d76dd6 946 callback_data->sendCompleteCallback = NULL;
XinZhangMS 0:f7f1f0d76dd6 947 callback_data->feedbackMessageCallback = NULL;
XinZhangMS 0:f7f1f0d76dd6 948 callback_data->openUserContext = NULL;
XinZhangMS 0:f7f1f0d76dd6 949 callback_data->sendUserContext = NULL;
XinZhangMS 0:f7f1f0d76dd6 950 callback_data->feedbackUserContext = NULL;
XinZhangMS 0:f7f1f0d76dd6 951
XinZhangMS 0:f7f1f0d76dd6 952 result->callback_data = callback_data;
XinZhangMS 0:f7f1f0d76dd6 953 result->isOpened = false;
XinZhangMS 0:f7f1f0d76dd6 954 }
XinZhangMS 0:f7f1f0d76dd6 955 }
XinZhangMS 0:f7f1f0d76dd6 956 }
XinZhangMS 0:f7f1f0d76dd6 957 return result;
XinZhangMS 0:f7f1f0d76dd6 958 }
XinZhangMS 0:f7f1f0d76dd6 959
XinZhangMS 0:f7f1f0d76dd6 960 void IoTHubMessaging_LL_Destroy(IOTHUB_MESSAGING_HANDLE messagingHandle)
XinZhangMS 0:f7f1f0d76dd6 961 {
XinZhangMS 0:f7f1f0d76dd6 962 /*Codes_SRS_IOTHUBMESSAGING_12_005: [ If the messagingHandle input parameter is NULL IoTHubMessaging_LL_Destroy shall return ] */
XinZhangMS 0:f7f1f0d76dd6 963 if (messagingHandle != NULL)
XinZhangMS 0:f7f1f0d76dd6 964 {
XinZhangMS 0:f7f1f0d76dd6 965 /*Codes_SRS_IOTHUBMESSAGING_12_006: [ If the messagingHandle input parameter is not NULL IoTHubMessaging_LL_Destroy shall free all resources (memory) allocated by IoTHubMessaging_LL_Create ] */
XinZhangMS 0:f7f1f0d76dd6 966 IOTHUB_MESSAGING* messHandle = (IOTHUB_MESSAGING*)messagingHandle;
XinZhangMS 0:f7f1f0d76dd6 967
XinZhangMS 0:f7f1f0d76dd6 968 free(messHandle->callback_data);
XinZhangMS 0:f7f1f0d76dd6 969 free(messHandle->hostname);
XinZhangMS 0:f7f1f0d76dd6 970 free(messHandle->iothubName);
XinZhangMS 0:f7f1f0d76dd6 971 free(messHandle->iothubSuffix);
XinZhangMS 0:f7f1f0d76dd6 972 free(messHandle->sharedAccessKey);
XinZhangMS 0:f7f1f0d76dd6 973 free(messHandle->keyName);
XinZhangMS 0:f7f1f0d76dd6 974 free(messHandle);
XinZhangMS 0:f7f1f0d76dd6 975 }
XinZhangMS 0:f7f1f0d76dd6 976 }
XinZhangMS 0:f7f1f0d76dd6 977
XinZhangMS 0:f7f1f0d76dd6 978 static int attachServiceClientTypeToLink(LINK_HANDLE link)
XinZhangMS 0:f7f1f0d76dd6 979 {
XinZhangMS 0:f7f1f0d76dd6 980 fields attach_properties;
XinZhangMS 0:f7f1f0d76dd6 981 AMQP_VALUE serviceClientTypeKeyName;
XinZhangMS 0:f7f1f0d76dd6 982 AMQP_VALUE serviceClientTypeValue;
XinZhangMS 0:f7f1f0d76dd6 983 int result;
XinZhangMS 0:f7f1f0d76dd6 984
XinZhangMS 0:f7f1f0d76dd6 985 if ((attach_properties = amqpvalue_create_map()) == NULL)
XinZhangMS 0:f7f1f0d76dd6 986 {
XinZhangMS 0:f7f1f0d76dd6 987 LogError("Failed to create the map for service client type.");
XinZhangMS 0:f7f1f0d76dd6 988 result = __FAILURE__;
XinZhangMS 0:f7f1f0d76dd6 989 }
XinZhangMS 0:f7f1f0d76dd6 990 else
XinZhangMS 0:f7f1f0d76dd6 991 {
XinZhangMS 0:f7f1f0d76dd6 992 if ((serviceClientTypeKeyName = amqpvalue_create_symbol("com.microsoft:client-version")) == NULL)
XinZhangMS 0:f7f1f0d76dd6 993 {
XinZhangMS 0:f7f1f0d76dd6 994 LogError("Failed to create the key name for the service client type.");
XinZhangMS 0:f7f1f0d76dd6 995 result = __FAILURE__;
XinZhangMS 0:f7f1f0d76dd6 996 }
XinZhangMS 0:f7f1f0d76dd6 997 else
XinZhangMS 0:f7f1f0d76dd6 998 {
XinZhangMS 0:f7f1f0d76dd6 999 if ((serviceClientTypeValue = amqpvalue_create_string(IOTHUB_SERVICE_CLIENT_TYPE_PREFIX IOTHUB_SERVICE_CLIENT_BACKSLASH IOTHUB_SERVICE_CLIENT_VERSION)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 1000 {
XinZhangMS 0:f7f1f0d76dd6 1001 LogError("Failed to create the key value for the service client type.");
XinZhangMS 0:f7f1f0d76dd6 1002 result = __FAILURE__;
XinZhangMS 0:f7f1f0d76dd6 1003 }
XinZhangMS 0:f7f1f0d76dd6 1004 else
XinZhangMS 0:f7f1f0d76dd6 1005 {
XinZhangMS 0:f7f1f0d76dd6 1006 if ((result = amqpvalue_set_map_value(attach_properties, serviceClientTypeKeyName, serviceClientTypeValue)) != 0)
XinZhangMS 0:f7f1f0d76dd6 1007 {
XinZhangMS 0:f7f1f0d76dd6 1008 LogError("Failed to set the property map for the service client type. Error code is: %d", result);
XinZhangMS 0:f7f1f0d76dd6 1009 }
XinZhangMS 0:f7f1f0d76dd6 1010 else if ((result = link_set_attach_properties(link, attach_properties)) != 0)
XinZhangMS 0:f7f1f0d76dd6 1011 {
XinZhangMS 0:f7f1f0d76dd6 1012 LogError("Unable to attach the service client type to the link properties. Error code is: %d", result);
XinZhangMS 0:f7f1f0d76dd6 1013 }
XinZhangMS 0:f7f1f0d76dd6 1014 else
XinZhangMS 0:f7f1f0d76dd6 1015 {
XinZhangMS 0:f7f1f0d76dd6 1016 result = 0;
XinZhangMS 0:f7f1f0d76dd6 1017 }
XinZhangMS 0:f7f1f0d76dd6 1018
XinZhangMS 0:f7f1f0d76dd6 1019 amqpvalue_destroy(serviceClientTypeValue);
XinZhangMS 0:f7f1f0d76dd6 1020 }
XinZhangMS 0:f7f1f0d76dd6 1021
XinZhangMS 0:f7f1f0d76dd6 1022 amqpvalue_destroy(serviceClientTypeKeyName);
XinZhangMS 0:f7f1f0d76dd6 1023 }
XinZhangMS 0:f7f1f0d76dd6 1024
XinZhangMS 0:f7f1f0d76dd6 1025 amqpvalue_destroy(attach_properties);
XinZhangMS 0:f7f1f0d76dd6 1026 }
XinZhangMS 0:f7f1f0d76dd6 1027 return result;
XinZhangMS 0:f7f1f0d76dd6 1028 }
XinZhangMS 0:f7f1f0d76dd6 1029
XinZhangMS 0:f7f1f0d76dd6 1030 IOTHUB_MESSAGING_RESULT IoTHubMessaging_LL_Open(IOTHUB_MESSAGING_HANDLE messagingHandle, IOTHUB_OPEN_COMPLETE_CALLBACK openCompleteCallback, void* userContextCallback)
XinZhangMS 0:f7f1f0d76dd6 1031 {
XinZhangMS 0:f7f1f0d76dd6 1032 IOTHUB_MESSAGING_RESULT result;
XinZhangMS 0:f7f1f0d76dd6 1033
XinZhangMS 0:f7f1f0d76dd6 1034 char* send_target_address = NULL;
XinZhangMS 0:f7f1f0d76dd6 1035 char* receive_target_address = NULL;
XinZhangMS 0:f7f1f0d76dd6 1036
XinZhangMS 0:f7f1f0d76dd6 1037 TLSIO_CONFIG tls_io_config;
XinZhangMS 0:f7f1f0d76dd6 1038 SASLCLIENTIO_CONFIG sasl_io_config;
XinZhangMS 0:f7f1f0d76dd6 1039
XinZhangMS 0:f7f1f0d76dd6 1040 AMQP_VALUE sendSource = NULL;
XinZhangMS 0:f7f1f0d76dd6 1041 AMQP_VALUE sendTarget = NULL;
XinZhangMS 0:f7f1f0d76dd6 1042
XinZhangMS 0:f7f1f0d76dd6 1043 AMQP_VALUE receiveSource = NULL;
XinZhangMS 0:f7f1f0d76dd6 1044 AMQP_VALUE receiveTarget = NULL;
XinZhangMS 0:f7f1f0d76dd6 1045
XinZhangMS 0:f7f1f0d76dd6 1046 /*Codes_SRS_IOTHUBMESSAGING_12_007: [ If the messagingHandle input parameter is NULL IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_INVALID_ARG ] */
XinZhangMS 0:f7f1f0d76dd6 1047 if (messagingHandle == NULL)
XinZhangMS 0:f7f1f0d76dd6 1048 {
XinZhangMS 0:f7f1f0d76dd6 1049 LogError("Input parameter cannot be NULL");
XinZhangMS 0:f7f1f0d76dd6 1050 result = IOTHUB_MESSAGING_INVALID_ARG;
XinZhangMS 0:f7f1f0d76dd6 1051 }
XinZhangMS 0:f7f1f0d76dd6 1052 else
XinZhangMS 0:f7f1f0d76dd6 1053 {
XinZhangMS 0:f7f1f0d76dd6 1054 messagingHandle->message_sender = NULL;
XinZhangMS 0:f7f1f0d76dd6 1055 messagingHandle->connection = NULL;
XinZhangMS 0:f7f1f0d76dd6 1056 messagingHandle->session = NULL;
XinZhangMS 0:f7f1f0d76dd6 1057 messagingHandle->sender_link = NULL;
XinZhangMS 0:f7f1f0d76dd6 1058 messagingHandle->sasl_plain_config.authzid = NULL;
XinZhangMS 0:f7f1f0d76dd6 1059 messagingHandle->sasl_mechanism_handle = NULL;
XinZhangMS 0:f7f1f0d76dd6 1060 messagingHandle->tls_io = NULL;
XinZhangMS 0:f7f1f0d76dd6 1061 messagingHandle->sasl_io = NULL;
XinZhangMS 0:f7f1f0d76dd6 1062
XinZhangMS 0:f7f1f0d76dd6 1063 /*Codes_SRS_IOTHUBMESSAGING_12_008: [ If messaging is already opened IoTHubMessaging_LL_Open return shall IOTHUB_MESSAGING_OK ] */
XinZhangMS 0:f7f1f0d76dd6 1064 if (messagingHandle->isOpened != 0)
XinZhangMS 0:f7f1f0d76dd6 1065 {
XinZhangMS 0:f7f1f0d76dd6 1066 LogError("Messaging is already opened");
XinZhangMS 0:f7f1f0d76dd6 1067 result = IOTHUB_MESSAGING_OK;
XinZhangMS 0:f7f1f0d76dd6 1068 }
XinZhangMS 0:f7f1f0d76dd6 1069 /*Codes_SRS_IOTHUBMESSAGING_12_022: [ IoTHubMessaging_LL_Open shall create uAMQP messaging target for sender by calling the messaging_create_target ] */
XinZhangMS 0:f7f1f0d76dd6 1070 else if ((send_target_address = createSendTargetAddress(messagingHandle)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 1071 {
XinZhangMS 0:f7f1f0d76dd6 1072 /*Codes_SRS_IOTHUBMESSAGING_12_077: [ If the messagingHandle->hostname input parameter is NULL IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1073 LogError("Could not create sendTargetAddress");
XinZhangMS 0:f7f1f0d76dd6 1074 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1075 }
XinZhangMS 0:f7f1f0d76dd6 1076 /*Codes_SRS_IOTHUBMESSAGING_12_027: [ IoTHubMessaging_LL_Open shall create uAMQP messaging source for receiver by calling the messaging_create_source ] */
XinZhangMS 0:f7f1f0d76dd6 1077 else if ((receive_target_address = createReceiveTargetAddress(messagingHandle)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 1078 {
XinZhangMS 0:f7f1f0d76dd6 1079 /*Codes_SRS_IOTHUBMESSAGING_12_030: [ If any of the uAMQP call fails IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1080 LogError("Could not create receiveTargetAddress");
XinZhangMS 0:f7f1f0d76dd6 1081 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1082 }
XinZhangMS 0:f7f1f0d76dd6 1083 /*Codes_SRS_IOTHUBMESSAGING_12_010: [ IoTHubMessaging_LL_Open shall create uAMQP PLAIN SASL mechanism by calling saslmechanism_create with the sasl plain interface ] */
XinZhangMS 0:f7f1f0d76dd6 1084 else if ((messagingHandle->sasl_plain_config.authcid = createAuthCid(messagingHandle)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 1085 {
XinZhangMS 0:f7f1f0d76dd6 1086 /*Codes_SRS_IOTHUBMESSAGING_12_030: [ If any of the uAMQP call fails IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1087 LogError("Could not create authCid");
XinZhangMS 0:f7f1f0d76dd6 1088 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1089 }
XinZhangMS 0:f7f1f0d76dd6 1090 /*Codes_SRS_IOTHUBMESSAGING_12_010: [ IoTHubMessaging_LL_Open shall create uAMQP PLAIN SASL mechanism by calling saslmechanism_create with the sasl plain interface ] */
XinZhangMS 0:f7f1f0d76dd6 1091 else if ((messagingHandle->sasl_plain_config.passwd = createSasToken(messagingHandle)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 1092 {
XinZhangMS 0:f7f1f0d76dd6 1093 /*Codes_SRS_IOTHUBMESSAGING_12_030: [ If any of the uAMQP call fails IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1094 LogError("Could not create sasToken");
XinZhangMS 0:f7f1f0d76dd6 1095 free((char*)messagingHandle->sasl_plain_config.authcid);
XinZhangMS 0:f7f1f0d76dd6 1096 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1097 }
XinZhangMS 0:f7f1f0d76dd6 1098 else
XinZhangMS 0:f7f1f0d76dd6 1099 {
XinZhangMS 0:f7f1f0d76dd6 1100 const SASL_MECHANISM_INTERFACE_DESCRIPTION* sasl_mechanism_interface;
XinZhangMS 0:f7f1f0d76dd6 1101
XinZhangMS 0:f7f1f0d76dd6 1102 /*Codes_SRS_IOTHUBMESSAGING_12_010: [ IoTHubMessaging_LL_Open shall create uAMQP PLAIN SASL mechanism by calling saslmechanism_create with the sasl plain interface ] */
XinZhangMS 0:f7f1f0d76dd6 1103 if ((sasl_mechanism_interface = saslplain_get_interface()) == NULL)
XinZhangMS 0:f7f1f0d76dd6 1104 {
XinZhangMS 0:f7f1f0d76dd6 1105 /*Codes_SRS_IOTHUBMESSAGING_12_030: [ If any of the uAMQP call fails IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1106 LogError("Could not get SASL plain mechanism interface.");
XinZhangMS 0:f7f1f0d76dd6 1107 free((char*)messagingHandle->sasl_plain_config.authcid);
XinZhangMS 0:f7f1f0d76dd6 1108 free((char*)messagingHandle->sasl_plain_config.passwd);
XinZhangMS 0:f7f1f0d76dd6 1109 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1110 }
XinZhangMS 0:f7f1f0d76dd6 1111 /*Codes_SRS_IOTHUBMESSAGING_12_010: [ IoTHubMessaging_LL_Open shall create uAMQP PLAIN SASL mechanism by calling saslmechanism_create with the sasl plain interface ] */
XinZhangMS 0:f7f1f0d76dd6 1112 else if ((messagingHandle->sasl_mechanism_handle = saslmechanism_create(sasl_mechanism_interface, &messagingHandle->sasl_plain_config)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 1113 {
XinZhangMS 0:f7f1f0d76dd6 1114 /*Codes_SRS_IOTHUBMESSAGING_12_030: [ If any of the uAMQP call fails IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1115 LogError("Could not create SASL plain mechanism.");
XinZhangMS 0:f7f1f0d76dd6 1116 free((char*)messagingHandle->sasl_plain_config.authcid);
XinZhangMS 0:f7f1f0d76dd6 1117 free((char*)messagingHandle->sasl_plain_config.passwd);
XinZhangMS 0:f7f1f0d76dd6 1118 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1119 }
XinZhangMS 0:f7f1f0d76dd6 1120 else
XinZhangMS 0:f7f1f0d76dd6 1121 {
XinZhangMS 0:f7f1f0d76dd6 1122 tls_io_config.hostname = messagingHandle->hostname;
XinZhangMS 0:f7f1f0d76dd6 1123 tls_io_config.port = 5671;
XinZhangMS 0:f7f1f0d76dd6 1124 tls_io_config.underlying_io_interface = NULL;
XinZhangMS 0:f7f1f0d76dd6 1125 tls_io_config.underlying_io_parameters = NULL;
XinZhangMS 0:f7f1f0d76dd6 1126
XinZhangMS 0:f7f1f0d76dd6 1127 const IO_INTERFACE_DESCRIPTION* tlsio_interface;
XinZhangMS 0:f7f1f0d76dd6 1128
XinZhangMS 0:f7f1f0d76dd6 1129 /*Codes_SRS_IOTHUBMESSAGING_12_011: [ IoTHubMessaging_LL_Open shall create uAMQP TLSIO by calling the xio_create ] */
XinZhangMS 0:f7f1f0d76dd6 1130 if ((tlsio_interface = platform_get_default_tlsio()) == NULL)
XinZhangMS 0:f7f1f0d76dd6 1131 {
XinZhangMS 0:f7f1f0d76dd6 1132 /*Codes_SRS_IOTHUBMESSAGING_12_030: [ If any of the uAMQP call fails IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1133 LogError("Could not get default TLS IO interface.");
XinZhangMS 0:f7f1f0d76dd6 1134 free((char*)messagingHandle->sasl_plain_config.authcid);
XinZhangMS 0:f7f1f0d76dd6 1135 free((char*)messagingHandle->sasl_plain_config.passwd);
XinZhangMS 0:f7f1f0d76dd6 1136 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1137 }
XinZhangMS 0:f7f1f0d76dd6 1138 /*Codes_SRS_IOTHUBMESSAGING_12_011: [ IoTHubMessaging_LL_Open shall create uAMQP TLSIO by calling the xio_create ] */
XinZhangMS 0:f7f1f0d76dd6 1139 else if ((messagingHandle->tls_io = xio_create(tlsio_interface, &tls_io_config)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 1140 {
XinZhangMS 0:f7f1f0d76dd6 1141 /*Codes_SRS_IOTHUBMESSAGING_12_030: [ If any of the uAMQP call fails IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1142 LogError("Could not create TLS IO.");
XinZhangMS 0:f7f1f0d76dd6 1143 free((char*)messagingHandle->sasl_plain_config.authcid);
XinZhangMS 0:f7f1f0d76dd6 1144 free((char*)messagingHandle->sasl_plain_config.passwd);
XinZhangMS 0:f7f1f0d76dd6 1145 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1146 }
XinZhangMS 0:f7f1f0d76dd6 1147 else
XinZhangMS 0:f7f1f0d76dd6 1148 {
XinZhangMS 0:f7f1f0d76dd6 1149 messagingHandle->callback_data->openCompleteCompleteCallback = openCompleteCallback;
XinZhangMS 0:f7f1f0d76dd6 1150 messagingHandle->callback_data->openUserContext = userContextCallback;
XinZhangMS 0:f7f1f0d76dd6 1151
XinZhangMS 0:f7f1f0d76dd6 1152 sasl_io_config.sasl_mechanism = messagingHandle->sasl_mechanism_handle;
XinZhangMS 0:f7f1f0d76dd6 1153 sasl_io_config.underlying_io = messagingHandle->tls_io;
XinZhangMS 0:f7f1f0d76dd6 1154
XinZhangMS 0:f7f1f0d76dd6 1155 const IO_INTERFACE_DESCRIPTION* saslclientio_interface;
XinZhangMS 0:f7f1f0d76dd6 1156
XinZhangMS 0:f7f1f0d76dd6 1157 /*Codes_SRS_IOTHUBMESSAGING_12_012: [ IoTHubMessaging_LL_Open shall create uAMQP SASL IO by calling the xio_create with the previously created SASL mechanism and TLSIO] */
XinZhangMS 0:f7f1f0d76dd6 1158 if ((saslclientio_interface = saslclientio_get_interface_description()) == NULL)
XinZhangMS 0:f7f1f0d76dd6 1159 {
XinZhangMS 0:f7f1f0d76dd6 1160 /*Codes_SRS_IOTHUBMESSAGING_12_030: [ If any of the uAMQP call fails IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1161 LogError("Could not create get SASL IO interface description.");
XinZhangMS 0:f7f1f0d76dd6 1162 free((char*)messagingHandle->sasl_plain_config.authcid);
XinZhangMS 0:f7f1f0d76dd6 1163 free((char*)messagingHandle->sasl_plain_config.passwd);
XinZhangMS 0:f7f1f0d76dd6 1164 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1165 }
XinZhangMS 0:f7f1f0d76dd6 1166 /*Codes_SRS_IOTHUBMESSAGING_12_012: [ IoTHubMessaging_LL_Open shall create uAMQP SASL IO by calling the xio_create with the previously created SASL mechanism and TLSIO] */
XinZhangMS 0:f7f1f0d76dd6 1167 else if ((messagingHandle->sasl_io = xio_create(saslclientio_interface, &sasl_io_config)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 1168 {
XinZhangMS 0:f7f1f0d76dd6 1169 /*Codes_SRS_IOTHUBMESSAGING_12_030: [ If any of the uAMQP call fails IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1170 LogError("Could not create SASL IO.");
XinZhangMS 0:f7f1f0d76dd6 1171 free((char*)messagingHandle->sasl_plain_config.authcid);
XinZhangMS 0:f7f1f0d76dd6 1172 free((char*)messagingHandle->sasl_plain_config.passwd);
XinZhangMS 0:f7f1f0d76dd6 1173 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1174 }
XinZhangMS 0:f7f1f0d76dd6 1175 /*Codes_SRS_IOTHUBMESSAGING_12_013: [ IoTHubMessaging_LL_Open shall create uAMQP connection by calling the connection_create with the previously created SASL IO ] */
XinZhangMS 0:f7f1f0d76dd6 1176 else if ((messagingHandle->connection = connection_create(messagingHandle->sasl_io, messagingHandle->hostname, "some", NULL, NULL)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 1177 {
XinZhangMS 0:f7f1f0d76dd6 1178 /*Codes_SRS_IOTHUBMESSAGING_12_030: [ If any of the uAMQP call fails IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1179 LogError("Could not create connection.");
XinZhangMS 0:f7f1f0d76dd6 1180 free((char*)messagingHandle->sasl_plain_config.authcid);
XinZhangMS 0:f7f1f0d76dd6 1181 free((char*)messagingHandle->sasl_plain_config.passwd);
XinZhangMS 0:f7f1f0d76dd6 1182 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1183 }
XinZhangMS 0:f7f1f0d76dd6 1184 /*Codes_SRS_IOTHUBMESSAGING_12_014: [ IoTHubMessaging_LL_Open shall create uAMQP session by calling the session_create ] */
XinZhangMS 0:f7f1f0d76dd6 1185 else if ((messagingHandle->session = session_create(messagingHandle->connection, NULL, NULL)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 1186 {
XinZhangMS 0:f7f1f0d76dd6 1187 /*Codes_SRS_IOTHUBMESSAGING_12_030: [ If any of the uAMQP call fails IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1188 LogError("Could not create session.");
XinZhangMS 0:f7f1f0d76dd6 1189 free((char*)messagingHandle->sasl_plain_config.authcid);
XinZhangMS 0:f7f1f0d76dd6 1190 free((char*)messagingHandle->sasl_plain_config.passwd);
XinZhangMS 0:f7f1f0d76dd6 1191 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1192 }
XinZhangMS 0:f7f1f0d76dd6 1193 /*Codes_SRS_IOTHUBMESSAGING_12_015: [ IoTHubMessaging_LL_Open shall set the AMQP incoming window to UINT32 maximum value by calling session_set_incoming_window ] */
XinZhangMS 0:f7f1f0d76dd6 1194 else if (session_set_incoming_window(messagingHandle->session, 2147483647) != 0)
XinZhangMS 0:f7f1f0d76dd6 1195 {
XinZhangMS 0:f7f1f0d76dd6 1196 /*Codes_SRS_IOTHUBMESSAGING_12_030: [ If any of the uAMQP call fails IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1197 LogError("Could not set incoming window.");
XinZhangMS 0:f7f1f0d76dd6 1198 free((char*)messagingHandle->sasl_plain_config.authcid);
XinZhangMS 0:f7f1f0d76dd6 1199 free((char*)messagingHandle->sasl_plain_config.passwd);
XinZhangMS 0:f7f1f0d76dd6 1200 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1201 }
XinZhangMS 0:f7f1f0d76dd6 1202 /*Codes_SRS_IOTHUBMESSAGING_12_016: [ IoTHubMessaging_LL_Open shall set the AMQP outgoing window to UINT32 maximum value by calling session_set_outgoing_window ] */
XinZhangMS 0:f7f1f0d76dd6 1203 else if (session_set_outgoing_window(messagingHandle->session, 255 * 1024) != 0)
XinZhangMS 0:f7f1f0d76dd6 1204 {
XinZhangMS 0:f7f1f0d76dd6 1205 /*Codes_SRS_IOTHUBMESSAGING_12_030: [ If any of the uAMQP call fails IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1206 LogError("Could not set outgoing window.");
XinZhangMS 0:f7f1f0d76dd6 1207 free((char*)messagingHandle->sasl_plain_config.authcid);
XinZhangMS 0:f7f1f0d76dd6 1208 free((char*)messagingHandle->sasl_plain_config.passwd);
XinZhangMS 0:f7f1f0d76dd6 1209 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1210 }
XinZhangMS 0:f7f1f0d76dd6 1211 /*Codes_SRS_IOTHUBMESSAGING_12_021: [ IoTHubMessaging_LL_Open shall create uAMQP messaging source for sender by calling the messaging_create_source ] */
XinZhangMS 0:f7f1f0d76dd6 1212 else if ((sendSource = messaging_create_source("ingress")) == NULL)
XinZhangMS 0:f7f1f0d76dd6 1213 {
XinZhangMS 0:f7f1f0d76dd6 1214 /*Codes_SRS_IOTHUBMESSAGING_12_030: [ If any of the uAMQP call fails IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1215 LogError("Could not create source for link.");
XinZhangMS 0:f7f1f0d76dd6 1216 free((char*)messagingHandle->sasl_plain_config.authcid);
XinZhangMS 0:f7f1f0d76dd6 1217 free((char*)messagingHandle->sasl_plain_config.passwd);
XinZhangMS 0:f7f1f0d76dd6 1218 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1219 }
XinZhangMS 0:f7f1f0d76dd6 1220 /*Codes_SRS_IOTHUBMESSAGING_12_022: [ IoTHubMessaging_LL_Open shall create uAMQP messaging target for sender by calling the messaging_create_target ] */
XinZhangMS 0:f7f1f0d76dd6 1221 else if ((sendTarget = messaging_create_target(send_target_address)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 1222 {
XinZhangMS 0:f7f1f0d76dd6 1223 /*Codes_SRS_IOTHUBMESSAGING_12_030: [ If any of the uAMQP call fails IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1224 LogError("Could not create target for link.");
XinZhangMS 0:f7f1f0d76dd6 1225 free((char*)messagingHandle->sasl_plain_config.authcid);
XinZhangMS 0:f7f1f0d76dd6 1226 free((char*)messagingHandle->sasl_plain_config.passwd);
XinZhangMS 0:f7f1f0d76dd6 1227 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1228 }
XinZhangMS 0:f7f1f0d76dd6 1229 /*Codes_SRS_IOTHUBMESSAGING_12_018: [ IoTHubMessaging_LL_Open shall create uAMQP sender link by calling the link_create ] */
XinZhangMS 0:f7f1f0d76dd6 1230 else if ((messagingHandle->sender_link = link_create(messagingHandle->session, "sender-link", role_sender, sendSource, sendTarget)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 1231 {
XinZhangMS 0:f7f1f0d76dd6 1232 /*Codes_SRS_IOTHUBMESSAGING_12_030: [ If any of the uAMQP call fails IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1233 LogError("Could not create link.");
XinZhangMS 0:f7f1f0d76dd6 1234 free((char*)messagingHandle->sasl_plain_config.authcid);
XinZhangMS 0:f7f1f0d76dd6 1235 free((char*)messagingHandle->sasl_plain_config.passwd);
XinZhangMS 0:f7f1f0d76dd6 1236 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1237 }
XinZhangMS 0:f7f1f0d76dd6 1238 /*Codes_SRS_IOTHUBMESSAGING_06_001: [ IoTHubMessaging_LL_Open shall add the version property to the sender link by calling the link_set_attach_properties ] */
XinZhangMS 0:f7f1f0d76dd6 1239 else if (attachServiceClientTypeToLink(messagingHandle->sender_link) != 0)
XinZhangMS 0:f7f1f0d76dd6 1240 {
XinZhangMS 0:f7f1f0d76dd6 1241 /*Codes_SRS_IOTHUBMESSAGING_12_030: [ If any of the uAMQP call fails IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1242 LogError("Could not set the sender attach properties.");
XinZhangMS 0:f7f1f0d76dd6 1243 free((char*)messagingHandle->sasl_plain_config.authcid);
XinZhangMS 0:f7f1f0d76dd6 1244 free((char*)messagingHandle->sasl_plain_config.passwd);
XinZhangMS 0:f7f1f0d76dd6 1245 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1246 }
XinZhangMS 0:f7f1f0d76dd6 1247 /*Codes_SRS_IOTHUBMESSAGING_12_019: [ IoTHubMessaging_LL_Open shall set the AMQP sender link settle mode to sender_settle_mode_unsettled by calling link_set_snd_settle_mode ] */
XinZhangMS 0:f7f1f0d76dd6 1248 else if (link_set_snd_settle_mode(messagingHandle->sender_link, sender_settle_mode_unsettled) != 0)
XinZhangMS 0:f7f1f0d76dd6 1249 {
XinZhangMS 0:f7f1f0d76dd6 1250 /*Codes_SRS_IOTHUBMESSAGING_12_030: [ If any of the uAMQP call fails IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1251 LogError("Could not set the sender settle mode.");
XinZhangMS 0:f7f1f0d76dd6 1252 free((char*)messagingHandle->sasl_plain_config.authcid);
XinZhangMS 0:f7f1f0d76dd6 1253 free((char*)messagingHandle->sasl_plain_config.passwd);
XinZhangMS 0:f7f1f0d76dd6 1254 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1255 }
XinZhangMS 0:f7f1f0d76dd6 1256 /*Codes_SRS_IOTHUBMESSAGING_12_023: [ IoTHubMessaging_LL_Open shall create uAMQP message sender by calling the messagesender_create with the created sender link and the local IoTHubMessaging_LL_SenderStateChanged callback ] */
XinZhangMS 0:f7f1f0d76dd6 1257 else if ((messagingHandle->message_sender = messagesender_create(messagingHandle->sender_link, IoTHubMessaging_LL_SenderStateChanged, messagingHandle)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 1258 {
XinZhangMS 0:f7f1f0d76dd6 1259 /*Codes_SRS_IOTHUBMESSAGING_12_030: [ If any of the uAMQP call fails IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1260 LogError("Could not create message sender.");
XinZhangMS 0:f7f1f0d76dd6 1261 free((char*)messagingHandle->sasl_plain_config.authcid);
XinZhangMS 0:f7f1f0d76dd6 1262 free((char*)messagingHandle->sasl_plain_config.passwd);
XinZhangMS 0:f7f1f0d76dd6 1263 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1264 }
XinZhangMS 0:f7f1f0d76dd6 1265 /*Codes_SRS_IOTHUBMESSAGING_12_023: [ IoTHubMessaging_LL_Open shall create uAMQP message sender by calling the messagesender_create with the created sender link and the local IoTHubMessaging_LL_SenderStateChanged callback ] */
XinZhangMS 0:f7f1f0d76dd6 1266 else if (messagesender_open(messagingHandle->message_sender) != 0)
XinZhangMS 0:f7f1f0d76dd6 1267 {
XinZhangMS 0:f7f1f0d76dd6 1268 /*Codes_SRS_IOTHUBMESSAGING_12_030: [ If any of the uAMQP call fails IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1269 LogError("Could not open the message sender.");
XinZhangMS 0:f7f1f0d76dd6 1270 free((char*)messagingHandle->sasl_plain_config.authcid);
XinZhangMS 0:f7f1f0d76dd6 1271 free((char*)messagingHandle->sasl_plain_config.passwd);
XinZhangMS 0:f7f1f0d76dd6 1272 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1273 }
XinZhangMS 0:f7f1f0d76dd6 1274 /*Codes_SRS_IOTHUBMESSAGING_12_027: [ IoTHubMessaging_LL_Open shall create uAMQP messaging source for receiver by calling the messaging_create_source ] */
XinZhangMS 0:f7f1f0d76dd6 1275 else if ((receiveSource = messaging_create_source(receive_target_address)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 1276 {
XinZhangMS 0:f7f1f0d76dd6 1277 /*Codes_SRS_IOTHUBMESSAGING_12_030: [ If any of the uAMQP call fails IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1278 LogError("Could not create source for link.");
XinZhangMS 0:f7f1f0d76dd6 1279 free((char*)messagingHandle->sasl_plain_config.authcid);
XinZhangMS 0:f7f1f0d76dd6 1280 free((char*)messagingHandle->sasl_plain_config.passwd);
XinZhangMS 0:f7f1f0d76dd6 1281 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1282 }
XinZhangMS 0:f7f1f0d76dd6 1283 /*Codes_SRS_IOTHUBMESSAGING_12_028: [ IoTHubMessaging_LL_Open shall create uAMQP messaging target for receiver by calling the messaging_create_target ] */
XinZhangMS 0:f7f1f0d76dd6 1284 else if ((receiveTarget = messaging_create_target("receiver_001")) == NULL)
XinZhangMS 0:f7f1f0d76dd6 1285 {
XinZhangMS 0:f7f1f0d76dd6 1286 /*Codes_SRS_IOTHUBMESSAGING_12_030: [ If any of the uAMQP call fails IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1287 LogError("Could not create target for link.");
XinZhangMS 0:f7f1f0d76dd6 1288 free((char*)messagingHandle->sasl_plain_config.authcid);
XinZhangMS 0:f7f1f0d76dd6 1289 free((char*)messagingHandle->sasl_plain_config.passwd);
XinZhangMS 0:f7f1f0d76dd6 1290 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1291 }
XinZhangMS 0:f7f1f0d76dd6 1292 /*Codes_SRS_IOTHUBMESSAGING_12_024: [ IoTHubMessaging_LL_Open shall create uAMQP receiver link by calling the link_create ] */
XinZhangMS 0:f7f1f0d76dd6 1293 else if ((messagingHandle->receiver_link = link_create(messagingHandle->session, "receiver-link", role_receiver, receiveSource, receiveTarget)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 1294 {
XinZhangMS 0:f7f1f0d76dd6 1295 /*Codes_SRS_IOTHUBMESSAGING_12_030: [ If any of the uAMQP call fails IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1296 LogError("Could not create link.");
XinZhangMS 0:f7f1f0d76dd6 1297 free((char*)messagingHandle->sasl_plain_config.authcid);
XinZhangMS 0:f7f1f0d76dd6 1298 free((char*)messagingHandle->sasl_plain_config.passwd);
XinZhangMS 0:f7f1f0d76dd6 1299 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1300 }
XinZhangMS 0:f7f1f0d76dd6 1301 /*Codes_SRS_IOTHUBMESSAGING_06_002: [ IoTHubMessaging_LL_Open shall add the version property to the receiver by calling the link_set_attach_properties ] */
XinZhangMS 0:f7f1f0d76dd6 1302 else if (attachServiceClientTypeToLink(messagingHandle->receiver_link) != 0)
XinZhangMS 0:f7f1f0d76dd6 1303 {
XinZhangMS 0:f7f1f0d76dd6 1304 /*Codes_SRS_IOTHUBMESSAGING_12_030: [ If any of the uAMQP call fails IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1305 LogError("Could not create link.");
XinZhangMS 0:f7f1f0d76dd6 1306 free((char*)messagingHandle->sasl_plain_config.authcid);
XinZhangMS 0:f7f1f0d76dd6 1307 free((char*)messagingHandle->sasl_plain_config.passwd);
XinZhangMS 0:f7f1f0d76dd6 1308 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1309 }
XinZhangMS 0:f7f1f0d76dd6 1310 /*Codes_SRS_IOTHUBMESSAGING_12_025: [ IoTHubMessaging_LL_Open shall set the AMQP receiver link settle mode to receiver_settle_mode_first by calling link_set_rcv_settle_mode ] */
XinZhangMS 0:f7f1f0d76dd6 1311 else if (link_set_rcv_settle_mode(messagingHandle->receiver_link, receiver_settle_mode_first) != 0)
XinZhangMS 0:f7f1f0d76dd6 1312 {
XinZhangMS 0:f7f1f0d76dd6 1313 /*Codes_SRS_IOTHUBMESSAGING_12_030: [ If any of the uAMQP call fails IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1314 LogError("Could not set the sender settle mode.");
XinZhangMS 0:f7f1f0d76dd6 1315 free((char*)messagingHandle->sasl_plain_config.authcid);
XinZhangMS 0:f7f1f0d76dd6 1316 free((char*)messagingHandle->sasl_plain_config.passwd);
XinZhangMS 0:f7f1f0d76dd6 1317 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1318 }
XinZhangMS 0:f7f1f0d76dd6 1319 /*Codes_SRS_IOTHUBMESSAGING_12_029: [ IoTHubMessaging_LL_Open shall create uAMQP message receiver by calling the messagereceiver_create with the created sender link and the local IoTHubMessaging_LL_ReceiverStateChanged callback ] */
XinZhangMS 0:f7f1f0d76dd6 1320 else if ((messagingHandle->message_receiver = messagereceiver_create(messagingHandle->receiver_link, IoTHubMessaging_LL_ReceiverStateChanged, messagingHandle)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 1321 {
XinZhangMS 0:f7f1f0d76dd6 1322 /*Codes_SRS_IOTHUBMESSAGING_12_030: [ If any of the uAMQP call fails IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1323 LogError("Could not create message receiver.");
XinZhangMS 0:f7f1f0d76dd6 1324 free((char*)messagingHandle->sasl_plain_config.authcid);
XinZhangMS 0:f7f1f0d76dd6 1325 free((char*)messagingHandle->sasl_plain_config.passwd);
XinZhangMS 0:f7f1f0d76dd6 1326 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1327 }
XinZhangMS 0:f7f1f0d76dd6 1328 /*Codes_SRS_IOTHUBMESSAGING_12_029: [ IoTHubMessaging_LL_Open shall create uAMQP message receiver by calling the messagereceiver_create with the created sender link and the local IoTHubMessaging_LL_ReceiverStateChanged callback ] */
XinZhangMS 0:f7f1f0d76dd6 1329 else if (messagereceiver_open(messagingHandle->message_receiver, IoTHubMessaging_LL_FeedbackMessageReceived, messagingHandle) != 0)
XinZhangMS 0:f7f1f0d76dd6 1330 {
XinZhangMS 0:f7f1f0d76dd6 1331 /*Codes_SRS_IOTHUBMESSAGING_12_030: [ If any of the uAMQP call fails IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1332 LogError("Could not open the message receiver.");
XinZhangMS 0:f7f1f0d76dd6 1333 free((char*)messagingHandle->sasl_plain_config.authcid);
XinZhangMS 0:f7f1f0d76dd6 1334 free((char*)messagingHandle->sasl_plain_config.passwd);
XinZhangMS 0:f7f1f0d76dd6 1335 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1336 }
XinZhangMS 0:f7f1f0d76dd6 1337 else
XinZhangMS 0:f7f1f0d76dd6 1338 {
XinZhangMS 0:f7f1f0d76dd6 1339 /*Codes_SRS_IOTHUBMESSAGING_12_031: [ If all of the uAMQP call return 0 (success) IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_OK ] */
XinZhangMS 0:f7f1f0d76dd6 1340 messagingHandle->isOpened = true;
XinZhangMS 0:f7f1f0d76dd6 1341 result = IOTHUB_MESSAGING_OK;
XinZhangMS 0:f7f1f0d76dd6 1342 }
XinZhangMS 0:f7f1f0d76dd6 1343 }
XinZhangMS 0:f7f1f0d76dd6 1344 }
XinZhangMS 0:f7f1f0d76dd6 1345 }
XinZhangMS 0:f7f1f0d76dd6 1346 }
XinZhangMS 0:f7f1f0d76dd6 1347 amqpvalue_destroy(sendSource);
XinZhangMS 0:f7f1f0d76dd6 1348 amqpvalue_destroy(sendTarget);
XinZhangMS 0:f7f1f0d76dd6 1349 amqpvalue_destroy(receiveSource);
XinZhangMS 0:f7f1f0d76dd6 1350 amqpvalue_destroy(receiveTarget);
XinZhangMS 0:f7f1f0d76dd6 1351
XinZhangMS 0:f7f1f0d76dd6 1352 if (send_target_address != NULL)
XinZhangMS 0:f7f1f0d76dd6 1353 {
XinZhangMS 0:f7f1f0d76dd6 1354 free(send_target_address);
XinZhangMS 0:f7f1f0d76dd6 1355 }
XinZhangMS 0:f7f1f0d76dd6 1356 if (receive_target_address != NULL)
XinZhangMS 0:f7f1f0d76dd6 1357 {
XinZhangMS 0:f7f1f0d76dd6 1358 free(receive_target_address);
XinZhangMS 0:f7f1f0d76dd6 1359 }
XinZhangMS 0:f7f1f0d76dd6 1360 return result;
XinZhangMS 0:f7f1f0d76dd6 1361 }
XinZhangMS 0:f7f1f0d76dd6 1362
XinZhangMS 0:f7f1f0d76dd6 1363 void IoTHubMessaging_LL_Close(IOTHUB_MESSAGING_HANDLE messagingHandle)
XinZhangMS 0:f7f1f0d76dd6 1364 {
XinZhangMS 0:f7f1f0d76dd6 1365 /*Codes_SRS_IOTHUBMESSAGING_12_032: [ If the messagingHandle input parameter is NULL IoTHubMessaging_LL_Close shall return IOTHUB_MESSAGING_INVALID_ARG ] */
XinZhangMS 0:f7f1f0d76dd6 1366 if (messagingHandle == NULL)
XinZhangMS 0:f7f1f0d76dd6 1367 {
XinZhangMS 0:f7f1f0d76dd6 1368 LogError("Input parameter cannot be NULL");
XinZhangMS 0:f7f1f0d76dd6 1369 }
XinZhangMS 0:f7f1f0d76dd6 1370 /*Codes_SRS_IOTHUBMESSAGING_12_033: [ IoTHubMessaging_LL_Close destroy the AMQP transportconnection by calling link_destroy, session_destroy, connection_destroy, xio_destroy, saslmechanism_destroy ] */
XinZhangMS 0:f7f1f0d76dd6 1371 else
XinZhangMS 0:f7f1f0d76dd6 1372 {
XinZhangMS 0:f7f1f0d76dd6 1373 messagesender_destroy(messagingHandle->message_sender);
XinZhangMS 0:f7f1f0d76dd6 1374 messagereceiver_destroy(messagingHandle->message_receiver);
XinZhangMS 0:f7f1f0d76dd6 1375
XinZhangMS 0:f7f1f0d76dd6 1376 link_destroy(messagingHandle->sender_link);
XinZhangMS 0:f7f1f0d76dd6 1377 link_destroy(messagingHandle->receiver_link);
XinZhangMS 0:f7f1f0d76dd6 1378
XinZhangMS 0:f7f1f0d76dd6 1379 session_destroy(messagingHandle->session);
XinZhangMS 0:f7f1f0d76dd6 1380 connection_destroy(messagingHandle->connection);
XinZhangMS 0:f7f1f0d76dd6 1381 xio_destroy(messagingHandle->sasl_io);
XinZhangMS 0:f7f1f0d76dd6 1382 xio_destroy(messagingHandle->tls_io);
XinZhangMS 0:f7f1f0d76dd6 1383 saslmechanism_destroy(messagingHandle->sasl_mechanism_handle);
XinZhangMS 0:f7f1f0d76dd6 1384
XinZhangMS 0:f7f1f0d76dd6 1385 if (messagingHandle->sasl_plain_config.authcid != NULL)
XinZhangMS 0:f7f1f0d76dd6 1386 {
XinZhangMS 0:f7f1f0d76dd6 1387 free((char*)messagingHandle->sasl_plain_config.authcid);
XinZhangMS 0:f7f1f0d76dd6 1388 }
XinZhangMS 0:f7f1f0d76dd6 1389 if (messagingHandle->sasl_plain_config.passwd != NULL)
XinZhangMS 0:f7f1f0d76dd6 1390 {
XinZhangMS 0:f7f1f0d76dd6 1391 free((char*)messagingHandle->sasl_plain_config.passwd);
XinZhangMS 0:f7f1f0d76dd6 1392 }
XinZhangMS 0:f7f1f0d76dd6 1393 if (messagingHandle->sasl_plain_config.authzid != NULL)
XinZhangMS 0:f7f1f0d76dd6 1394 {
XinZhangMS 0:f7f1f0d76dd6 1395 free((char*)messagingHandle->sasl_plain_config.authzid);
XinZhangMS 0:f7f1f0d76dd6 1396 }
XinZhangMS 0:f7f1f0d76dd6 1397 messagingHandle->isOpened = false;
XinZhangMS 0:f7f1f0d76dd6 1398 }
XinZhangMS 0:f7f1f0d76dd6 1399 }
XinZhangMS 0:f7f1f0d76dd6 1400
XinZhangMS 0:f7f1f0d76dd6 1401 IOTHUB_MESSAGING_RESULT IoTHubMessaging_LL_SetFeedbackMessageCallback(IOTHUB_MESSAGING_HANDLE messagingHandle, IOTHUB_FEEDBACK_MESSAGE_RECEIVED_CALLBACK feedbackMessageReceivedCallback, void* userContextCallback)
XinZhangMS 0:f7f1f0d76dd6 1402 {
XinZhangMS 0:f7f1f0d76dd6 1403 IOTHUB_MESSAGING_RESULT result;
XinZhangMS 0:f7f1f0d76dd6 1404
XinZhangMS 0:f7f1f0d76dd6 1405 /*Codes_SRS_IOTHUBMESSAGING_12_042: [ IoTHubMessaging_LL_SetCallbacks shall verify the messagingHandle input parameter and if it is NULL then return NULL ] */
XinZhangMS 0:f7f1f0d76dd6 1406 if (messagingHandle == NULL)
XinZhangMS 0:f7f1f0d76dd6 1407 {
XinZhangMS 0:f7f1f0d76dd6 1408 LogError("Input parameter cannot be NULL");
XinZhangMS 0:f7f1f0d76dd6 1409 result = IOTHUB_MESSAGING_INVALID_ARG;
XinZhangMS 0:f7f1f0d76dd6 1410 }
XinZhangMS 0:f7f1f0d76dd6 1411 else
XinZhangMS 0:f7f1f0d76dd6 1412 {
XinZhangMS 0:f7f1f0d76dd6 1413 /*Codes_SRS_IOTHUBMESSAGING_12_043: [ IoTHubMessaging_LL_SetCallbacks shall save the given feedbackMessageReceivedCallback to use them in local callbacks ] */
XinZhangMS 0:f7f1f0d76dd6 1414 /*Codes_SRS_IOTHUBMESSAGING_12_044: [ IoTHubMessaging_LL_Open shall return IOTHUB_MESSAGING_OK after the callbacks have been set ] */
XinZhangMS 0:f7f1f0d76dd6 1415 messagingHandle->callback_data->feedbackMessageCallback = feedbackMessageReceivedCallback;
XinZhangMS 0:f7f1f0d76dd6 1416 messagingHandle->callback_data->feedbackUserContext = userContextCallback;
XinZhangMS 0:f7f1f0d76dd6 1417 result = IOTHUB_MESSAGING_OK;
XinZhangMS 0:f7f1f0d76dd6 1418 }
XinZhangMS 0:f7f1f0d76dd6 1419 return result;
XinZhangMS 0:f7f1f0d76dd6 1420 }
XinZhangMS 0:f7f1f0d76dd6 1421
XinZhangMS 0:f7f1f0d76dd6 1422
XinZhangMS 0:f7f1f0d76dd6 1423 IOTHUB_MESSAGING_RESULT IoTHubMessaging_LL_Send(IOTHUB_MESSAGING_HANDLE messagingHandle, const char* deviceId, IOTHUB_MESSAGE_HANDLE message, IOTHUB_SEND_COMPLETE_CALLBACK sendCompleteCallback, void* userContextCallback)
XinZhangMS 0:f7f1f0d76dd6 1424 {
XinZhangMS 0:f7f1f0d76dd6 1425 IOTHUB_MESSAGING_RESULT result;
XinZhangMS 0:f7f1f0d76dd6 1426
XinZhangMS 0:f7f1f0d76dd6 1427 // There is no support for module sending message for callers, but most of plumbing is available should this be enabled via a new API.
XinZhangMS 0:f7f1f0d76dd6 1428 const char* moduleId = NULL;
XinZhangMS 0:f7f1f0d76dd6 1429
XinZhangMS 0:f7f1f0d76dd6 1430 char* deviceDestinationString;
XinZhangMS 0:f7f1f0d76dd6 1431
XinZhangMS 0:f7f1f0d76dd6 1432 /*Codes_SRS_IOTHUBMESSAGING_12_034: [ IoTHubMessaging_LL_SendMessage shall verify the messagingHandle, deviceId, message input parameters and if any of them are NULL then return NULL ] */
XinZhangMS 0:f7f1f0d76dd6 1433 if (messagingHandle == NULL)
XinZhangMS 0:f7f1f0d76dd6 1434 {
XinZhangMS 0:f7f1f0d76dd6 1435 LogError("Input parameter messagingHandle cannot be NULL");
XinZhangMS 0:f7f1f0d76dd6 1436 result = IOTHUB_MESSAGING_INVALID_ARG;
XinZhangMS 0:f7f1f0d76dd6 1437 }
XinZhangMS 0:f7f1f0d76dd6 1438 /*Codes_SRS_IOTHUBMESSAGING_12_034: [ IoTHubMessaging_LL_SendMessage shall verify the messagingHandle, deviceId, message input parameters and if any of them are NULL then return NULL ] */
XinZhangMS 0:f7f1f0d76dd6 1439 else if (deviceId == NULL)
XinZhangMS 0:f7f1f0d76dd6 1440 {
XinZhangMS 0:f7f1f0d76dd6 1441 LogError("Input parameter deviceId cannot be NULL");
XinZhangMS 0:f7f1f0d76dd6 1442 result = IOTHUB_MESSAGING_INVALID_ARG;
XinZhangMS 0:f7f1f0d76dd6 1443 }
XinZhangMS 0:f7f1f0d76dd6 1444 /*Codes_SRS_IOTHUBMESSAGING_12_034: [ IoTHubMessaging_LL_SendMessage shall verify the messagingHandle, deviceId, message input parameters and if any of them are NULL then return NULL ] */
XinZhangMS 0:f7f1f0d76dd6 1445 else if (message == NULL)
XinZhangMS 0:f7f1f0d76dd6 1446 {
XinZhangMS 0:f7f1f0d76dd6 1447 LogError("Input parameter message cannot be NULL");
XinZhangMS 0:f7f1f0d76dd6 1448 result = IOTHUB_MESSAGING_INVALID_ARG;
XinZhangMS 0:f7f1f0d76dd6 1449 }
XinZhangMS 0:f7f1f0d76dd6 1450 /*Codes_SRS_IOTHUBMESSAGING_12_035: [ IoTHubMessaging_LL_SendMessage shall verify if the AMQP messaging has been established by a successfull call to _Open and if it is not then return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1451 else if (messagingHandle->isOpened == 0)
XinZhangMS 0:f7f1f0d76dd6 1452 {
XinZhangMS 0:f7f1f0d76dd6 1453 LogError("Messaging is not opened - call IoTHubMessaging_LL_Open to open");
XinZhangMS 0:f7f1f0d76dd6 1454 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1455 }
XinZhangMS 0:f7f1f0d76dd6 1456 /*Codes_SRS_IOTHUBMESSAGING_12_038: [ IoTHubMessaging_LL_SendMessage shall set the uAMQP message properties to the given message properties by calling message_set_properties ] */
XinZhangMS 0:f7f1f0d76dd6 1457 else if ((deviceDestinationString = createDeviceDestinationString(deviceId, moduleId)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 1458 {
XinZhangMS 0:f7f1f0d76dd6 1459 /*Codes_SRS_IOTHUBMESSAGING_12_040: [ If any of the uAMQP call fails IoTHubMessaging_LL_SendMessage shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1460 LogError("Could not create a message.");
XinZhangMS 0:f7f1f0d76dd6 1461 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1462 }
XinZhangMS 0:f7f1f0d76dd6 1463 else
XinZhangMS 0:f7f1f0d76dd6 1464 {
XinZhangMS 0:f7f1f0d76dd6 1465 unsigned const char* messageContent;
XinZhangMS 0:f7f1f0d76dd6 1466 size_t messageContentSize;
XinZhangMS 0:f7f1f0d76dd6 1467
XinZhangMS 0:f7f1f0d76dd6 1468 if (getMessageContentAndSize(message, &messageContent, &messageContentSize) != 0)
XinZhangMS 0:f7f1f0d76dd6 1469 {
XinZhangMS 0:f7f1f0d76dd6 1470 LogError("Failed getting the message content and message size from IOTHUB_MESSAGE_HANDLE instance.");
XinZhangMS 0:f7f1f0d76dd6 1471 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1472 }
XinZhangMS 0:f7f1f0d76dd6 1473 else
XinZhangMS 0:f7f1f0d76dd6 1474 {
XinZhangMS 0:f7f1f0d76dd6 1475 MESSAGE_HANDLE amqpMessage;
XinZhangMS 0:f7f1f0d76dd6 1476 AMQP_VALUE to_amqp_value;
XinZhangMS 0:f7f1f0d76dd6 1477
XinZhangMS 0:f7f1f0d76dd6 1478 /*Codes_SRS_IOTHUBMESSAGING_12_036: [ IoTHubMessaging_LL_SendMessage shall create a uAMQP message by calling message_create ] */
XinZhangMS 0:f7f1f0d76dd6 1479 if ((amqpMessage = message_create()) == NULL)
XinZhangMS 0:f7f1f0d76dd6 1480 {
XinZhangMS 0:f7f1f0d76dd6 1481 /*Codes_SRS_IOTHUBMESSAGING_12_040: [ If any of the uAMQP call fails IoTHubMessaging_LL_SendMessage shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1482 LogError("Could not create a message.");
XinZhangMS 0:f7f1f0d76dd6 1483 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1484 }
XinZhangMS 0:f7f1f0d76dd6 1485 /*Codes_SRS_IOTHUBMESSAGING_12_038: [ IoTHubMessaging_LL_SendMessage shall set the uAMQP message properties to the given message properties by calling message_set_properties ] */
XinZhangMS 0:f7f1f0d76dd6 1486 else if ((to_amqp_value = amqpvalue_create_string(deviceDestinationString)) == NULL)
XinZhangMS 0:f7f1f0d76dd6 1487 {
XinZhangMS 0:f7f1f0d76dd6 1488 /*Codes_SRS_IOTHUBMESSAGING_12_040: [ If any of the uAMQP call fails IoTHubMessaging_LL_SendMessage shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1489 LogError("Could not create properties for message - amqpvalue_create_string");
XinZhangMS 0:f7f1f0d76dd6 1490 message_destroy(amqpMessage);
XinZhangMS 0:f7f1f0d76dd6 1491 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1492 }
XinZhangMS 0:f7f1f0d76dd6 1493 else
XinZhangMS 0:f7f1f0d76dd6 1494 {
XinZhangMS 0:f7f1f0d76dd6 1495 BINARY_DATA binary_data;
XinZhangMS 0:f7f1f0d76dd6 1496
XinZhangMS 0:f7f1f0d76dd6 1497 binary_data.bytes = messageContent;
XinZhangMS 0:f7f1f0d76dd6 1498 binary_data.length = messageContentSize;
XinZhangMS 0:f7f1f0d76dd6 1499
XinZhangMS 0:f7f1f0d76dd6 1500 /*Codes_SRS_IOTHUBMESSAGING_12_037: [ IoTHubMessaging_LL_SendMessage shall set the uAMQP message body to the given message content by calling message_add_body_amqp_data ] */
XinZhangMS 0:f7f1f0d76dd6 1501 if (message_add_body_amqp_data(amqpMessage, binary_data) != 0)
XinZhangMS 0:f7f1f0d76dd6 1502 {
XinZhangMS 0:f7f1f0d76dd6 1503 /*Codes_SRS_IOTHUBMESSAGING_12_040: [ If any of the uAMQP call fails IoTHubMessaging_LL_SendMessage shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1504 LogError("Failed setting the body of the uAMQP message.");
XinZhangMS 0:f7f1f0d76dd6 1505 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1506 }
XinZhangMS 0:f7f1f0d76dd6 1507 /*Codes_SRS_IOTHUBMESSAGING_12_038: [ IoTHubMessaging_LL_SendMessage shall set the uAMQP message properties to the given message properties by calling message_set_properties ] */
XinZhangMS 0:f7f1f0d76dd6 1508 else if (addPropertiesToAMQPMessage(message, amqpMessage, to_amqp_value) != 0)
XinZhangMS 0:f7f1f0d76dd6 1509 {
XinZhangMS 0:f7f1f0d76dd6 1510 /*Codes_SRS_IOTHUBMESSAGING_12_040: [ If any of the uAMQP call fails IoTHubMessaging_LL_SendMessage shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1511 message_destroy(amqpMessage);
XinZhangMS 0:f7f1f0d76dd6 1512 LogError("Failed setting properties of the uAMQP message.");
XinZhangMS 0:f7f1f0d76dd6 1513 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1514 }
XinZhangMS 0:f7f1f0d76dd6 1515 else if (addApplicationPropertiesToAMQPMessage(message, amqpMessage) != 0)
XinZhangMS 0:f7f1f0d76dd6 1516 {
XinZhangMS 0:f7f1f0d76dd6 1517 /*Codes_SRS_IOTHUBMESSAGING_12_040: [ If any of the uAMQP call fails IoTHubMessaging_LL_SendMessage shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1518 message_destroy(amqpMessage);
XinZhangMS 0:f7f1f0d76dd6 1519 LogError("Failed setting application properties of the uAMQP message.");
XinZhangMS 0:f7f1f0d76dd6 1520 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1521 }
XinZhangMS 0:f7f1f0d76dd6 1522 else
XinZhangMS 0:f7f1f0d76dd6 1523 {
XinZhangMS 0:f7f1f0d76dd6 1524 messagingHandle->callback_data->sendCompleteCallback = sendCompleteCallback;
XinZhangMS 0:f7f1f0d76dd6 1525 messagingHandle->callback_data->sendUserContext = userContextCallback;
XinZhangMS 0:f7f1f0d76dd6 1526
XinZhangMS 0:f7f1f0d76dd6 1527 /*Codes_SRS_IOTHUBMESSAGING_12_039: [ IoTHubMessaging_LL_SendMessage shall call uAMQP messagesender_send with the created message with IoTHubMessaging_LL_SendMessageComplete callback by which IoTHubMessaging is notified of completition of send ] */
XinZhangMS 0:f7f1f0d76dd6 1528 if (messagesender_send_async(messagingHandle->message_sender, amqpMessage, (ON_MESSAGE_SEND_COMPLETE)IoTHubMessaging_LL_SendMessageComplete, messagingHandle, 0) == NULL)
XinZhangMS 0:f7f1f0d76dd6 1529 {
XinZhangMS 0:f7f1f0d76dd6 1530 /*Codes_SRS_IOTHUBMESSAGING_12_040: [ If any of the uAMQP call fails IoTHubMessaging_LL_SendMessage shall return IOTHUB_MESSAGING_ERROR ] */
XinZhangMS 0:f7f1f0d76dd6 1531 LogError("Could not set outgoing window.");
XinZhangMS 0:f7f1f0d76dd6 1532 message_destroy(amqpMessage);
XinZhangMS 0:f7f1f0d76dd6 1533 result = IOTHUB_MESSAGING_ERROR;
XinZhangMS 0:f7f1f0d76dd6 1534 }
XinZhangMS 0:f7f1f0d76dd6 1535 else
XinZhangMS 0:f7f1f0d76dd6 1536 {
XinZhangMS 0:f7f1f0d76dd6 1537 /*Codes_SRS_IOTHUBMESSAGING_12_041: [ If all uAMQP call return 0 then IoTHubMessaging_LL_SendMessage shall return IOTHUB_MESSAGING_OK ] */
XinZhangMS 0:f7f1f0d76dd6 1538 result = IOTHUB_MESSAGING_OK;
XinZhangMS 0:f7f1f0d76dd6 1539 }
XinZhangMS 0:f7f1f0d76dd6 1540 }
XinZhangMS 0:f7f1f0d76dd6 1541 message_destroy(amqpMessage);
XinZhangMS 0:f7f1f0d76dd6 1542 amqpvalue_destroy(to_amqp_value);
XinZhangMS 0:f7f1f0d76dd6 1543 }
XinZhangMS 0:f7f1f0d76dd6 1544 }
XinZhangMS 0:f7f1f0d76dd6 1545 free(deviceDestinationString);
XinZhangMS 0:f7f1f0d76dd6 1546 }
XinZhangMS 0:f7f1f0d76dd6 1547 return result;
XinZhangMS 0:f7f1f0d76dd6 1548 }
XinZhangMS 0:f7f1f0d76dd6 1549
XinZhangMS 0:f7f1f0d76dd6 1550
XinZhangMS 0:f7f1f0d76dd6 1551 void IoTHubMessaging_LL_DoWork(IOTHUB_MESSAGING_HANDLE messagingHandle)
XinZhangMS 0:f7f1f0d76dd6 1552 {
XinZhangMS 0:f7f1f0d76dd6 1553 /*Codes_SRS_IOTHUBMESSAGING_12_045: [ IoTHubMessaging_LL_DoWork shall verify if uAMQP transport has been initialized and if it is not then return immediately ] */
XinZhangMS 0:f7f1f0d76dd6 1554 if (messagingHandle != 0)
XinZhangMS 0:f7f1f0d76dd6 1555 {
XinZhangMS 0:f7f1f0d76dd6 1556 /*Codes_SRS_IOTHUBMESSAGING_12_046: [ IoTHubMessaging_LL_DoWork shall call uAMQP connection_dowork ] */
XinZhangMS 0:f7f1f0d76dd6 1557 /*Codes_SRS_IOTHUBMESSAGING_12_047: [ IoTHubMessaging_LL_SendMessageComplete callback given to messagesender_send will be called with MESSAGE_SEND_RESULT ] */
XinZhangMS 0:f7f1f0d76dd6 1558 /*Codes_SRS_IOTHUBMESSAGING_12_048: [ If message has been received the IoTHubMessaging_LL_FeedbackMessageReceived callback given to messagesender_receive will be called with the received MESSAGE_HANDLE ] */
XinZhangMS 0:f7f1f0d76dd6 1559 connection_dowork(messagingHandle->connection);
XinZhangMS 0:f7f1f0d76dd6 1560 }
XinZhangMS 0:f7f1f0d76dd6 1561 }
XinZhangMS 0:f7f1f0d76dd6 1562