2 * AWS IoT Common V1.0.0
\r
3 * Copyright (C) 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
\r
5 * Permission is hereby granted, free of charge, to any person obtaining a copy of
\r
6 * this software and associated documentation files (the "Software"), to deal in
\r
7 * the Software without restriction, including without limitation the rights to
\r
8 * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
\r
9 * the Software, and to permit persons to whom the Software is furnished to do so,
\r
10 * subject to the following conditions:
\r
12 * The above copyright notice and this permission notice shall be included in all
\r
13 * copies or substantial portions of the Software.
\r
15 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
\r
16 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
\r
17 * FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
\r
18 * COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
\r
19 * IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
\r
20 * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
\r
24 * @file aws_iot_subscription.c
\r
25 * @brief Functions for common AWS IoT subscriptions.
\r
28 /* The config header is always included first. */
\r
29 #include "iot_config.h"
\r
31 /* Standard includes. */
\r
34 /* AWS IoT include. */
\r
35 #include "aws_iot.h"
\r
37 /* Error handling include. */
\r
38 #include "iot_error.h"
\r
41 #include "iot_mqtt.h"
\r
44 * @brief Modify subscriptions, either by unsubscribing or subscribing.
\r
46 * @param[in] mqttOperation Either @ref mqtt_function_subscribesync or @ref
\r
47 * mqtt_function_unsubscribesync.
\r
48 * @param[in] pSubscriptionInfo Information needed to process an MQTT
\r
50 * @param[in] pTopicFilter The topic filter to modify.
\r
51 * @param[in] topicFilterLength The length of `pTopicFilter`.
\r
53 * @return See the return values of @ref mqtt_function_subscribesync or
\r
54 * @ref mqtt_function_unsubscribesync.
\r
56 static IotMqttError_t _modifySubscriptions( AwsIotMqttFunction_t mqttOperation,
\r
57 const AwsIotSubscriptionInfo_t * pSubscriptionInfo,
\r
58 const char * pTopicFilter,
\r
59 uint16_t topicFilterLength );
\r
61 /*-----------------------------------------------------------*/
\r
63 static IotMqttError_t _modifySubscriptions( AwsIotMqttFunction_t mqttOperation,
\r
64 const AwsIotSubscriptionInfo_t * pSubscriptionInfo,
\r
65 const char * pTopicFilter,
\r
66 uint16_t topicFilterLength )
\r
68 IotMqttError_t status = IOT_MQTT_STATUS_PENDING;
\r
69 IotMqttSubscription_t subscription = IOT_MQTT_SUBSCRIPTION_INITIALIZER;
\r
71 /* Per the AWS IoT documentation, topic subscriptions are QoS 1. */
\r
72 subscription.qos = IOT_MQTT_QOS_1;
\r
74 /* Set the members of the subscription parameter. */
\r
75 subscription.pTopicFilter = pTopicFilter;
\r
76 subscription.topicFilterLength = topicFilterLength;
\r
77 subscription.callback.pCallbackContext = NULL;
\r
78 subscription.callback.function = pSubscriptionInfo->callbackFunction;
\r
80 /* Call the MQTT operation function.
\r
81 * Subscription count is 1 in this case.
\r
82 * None of the flags are set in this call. Hence 0 is passed for flags.
\r
83 * Please refer to documentation for AwsIotMqttFunction_t for more details.
\r
85 status = mqttOperation( pSubscriptionInfo->mqttConnection,
\r
89 pSubscriptionInfo->timeout );
\r
94 /*-----------------------------------------------------------*/
\r
96 IotMqttError_t AwsIot_ModifySubscriptions( AwsIotMqttFunction_t mqttOperation,
\r
97 const AwsIotSubscriptionInfo_t * pSubscriptionInfo )
\r
99 IOT_FUNCTION_ENTRY( IotMqttError_t, IOT_MQTT_STATUS_PENDING );
\r
100 IotMqttError_t acceptedStatus = IOT_MQTT_STATUS_PENDING;
\r
101 uint16_t topicFilterLength = 0;
\r
103 /* Place the topic "accepted" suffix at the end of the topic buffer. */
\r
104 ( void ) memcpy( pSubscriptionInfo->pTopicFilterBase
\r
105 + pSubscriptionInfo->topicFilterBaseLength,
\r
106 AWS_IOT_ACCEPTED_SUFFIX,
\r
107 AWS_IOT_ACCEPTED_SUFFIX_LENGTH );
\r
108 topicFilterLength = ( uint16_t ) ( pSubscriptionInfo->topicFilterBaseLength
\r
109 + AWS_IOT_ACCEPTED_SUFFIX_LENGTH );
\r
111 /* Modify the subscription to the "accepted" topic. */
\r
112 acceptedStatus = _modifySubscriptions( mqttOperation,
\r
114 pSubscriptionInfo->pTopicFilterBase,
\r
115 topicFilterLength );
\r
117 if( acceptedStatus != IOT_MQTT_SUCCESS )
\r
119 IOT_SET_AND_GOTO_CLEANUP( acceptedStatus );
\r
122 /* Place the topic "rejected" suffix at the end of the topic buffer. */
\r
123 ( void ) memcpy( pSubscriptionInfo->pTopicFilterBase
\r
124 + pSubscriptionInfo->topicFilterBaseLength,
\r
125 AWS_IOT_REJECTED_SUFFIX,
\r
126 AWS_IOT_REJECTED_SUFFIX_LENGTH );
\r
127 topicFilterLength = ( uint16_t ) ( pSubscriptionInfo->topicFilterBaseLength
\r
128 + AWS_IOT_REJECTED_SUFFIX_LENGTH );
\r
130 /* Modify the subscription to the "rejected" topic. */
\r
131 status = _modifySubscriptions( mqttOperation,
\r
133 pSubscriptionInfo->pTopicFilterBase,
\r
134 topicFilterLength );
\r
136 IOT_FUNCTION_CLEANUP_BEGIN();
\r
138 /* Clean up on error. */
\r
139 if( status != IOT_MQTT_SUCCESS )
\r
141 /* Remove the subscription to the "accepted" topic if the subscription
\r
142 * to the "rejected" topic failed. */
\r
143 if( ( mqttOperation == IotMqtt_SubscribeSync ) &&
\r
144 ( acceptedStatus == IOT_MQTT_SUCCESS ) )
\r
146 /* Place the topic "accepted" suffix at the end of the topic buffer. */
\r
147 ( void ) memcpy( pSubscriptionInfo->pTopicFilterBase
\r
148 + pSubscriptionInfo->topicFilterBaseLength,
\r
149 AWS_IOT_ACCEPTED_SUFFIX,
\r
150 AWS_IOT_ACCEPTED_SUFFIX_LENGTH );
\r
151 topicFilterLength = ( uint16_t ) ( pSubscriptionInfo->topicFilterBaseLength
\r
152 + AWS_IOT_ACCEPTED_SUFFIX_LENGTH );
\r
154 ( void ) _modifySubscriptions( IotMqtt_UnsubscribeSync,
\r
156 pSubscriptionInfo->pTopicFilterBase,
\r
157 topicFilterLength );
\r
161 IOT_FUNCTION_CLEANUP_END();
\r
164 /*-----------------------------------------------------------*/
\r