1 /*
2 * Copyright (C) 2015-2018 Alibaba Group Holding Limited
3 */
4 #include "dev_bind_internal.h"
5
6 #if defined(__cplusplus) /* If this is a C++ compiler, use C linkage */
7 extern "C" {
8 #endif
9
10 #define AWSS_RESET_PKT_LEN (256)
11 #define AWSS_RESET_TOPIC_LEN (128)
12 #define AWSS_RESET_MSG_ID_LEN (16)
13
14 #define TOPIC_RESET_REPORT "/sys/%s/%s/thing/reset"
15 #define TOPIC_RESET_REPORT_REPLY "/sys/%s/%s/thing/reset_reply"
16 #define METHOD_RESET_REPORT "thing.reset"
17
18 #define AWSS_RESET_REQ_FMT \
19 "{\"id\":%s, \"version\":\"1.0\", \"method\":\"%s\", \"params\":%s}"
20
21 #define AWSS_KV_RST "awss.rst"
22
23 static uint8_t awss_report_reset_suc = 0;
24 static uint16_t awss_report_reset_id = 0;
25 static void *report_reset_timer = NULL;
26 #ifdef DEV_BIND_ENABLED
27 extern int awss_start_bind();
28 #endif
29
30 int awss_report_reset_to_cloud();
awss_report_reset_reply(void * pcontext,void * pclient,void * mesg)31 void awss_report_reset_reply(void *pcontext, void *pclient, void *mesg)
32 {
33 char rst = 0;
34
35 iotx_mqtt_event_msg_pt msg = (iotx_mqtt_event_msg_pt)mesg;
36
37 switch (msg->event_type) {
38 case IOTX_MQTT_EVENT_PUBLISH_RECEIVED:
39 break;
40 default:
41 return;
42 }
43
44 devrst_debug("[RST]", "%s\r\n", __func__);
45
46 awss_report_reset_suc = 1;
47 HAL_Kv_Set(AWSS_KV_RST, &rst, sizeof(rst), 0);
48
49 HAL_Timer_Stop(report_reset_timer);
50 HAL_Timer_Delete(report_reset_timer);
51 report_reset_timer = NULL;
52
53 #ifdef DEV_BIND_ENABLED
54 awss_start_bind();
55 #endif
56
57 #ifdef INFRA_EVENT
58 iotx_event_post(IOTX_RESET); /* for old version of event */
59 do { /* for new version of event */
60 void *cb = NULL;
61 cb = (void *)iotx_event_callback(ITE_AWSS_STATUS);
62 if (cb == NULL) {
63 break;
64 }
65 ((int (*)(int))cb)(IOTX_RESET);
66 } while (0);
67 #endif
68 }
69
awss_report_reset_to_cloud()70 int awss_report_reset_to_cloud()
71 {
72 int ret = -1;
73 int final_len = 0;
74 char *topic = NULL;
75 char *packet = NULL;
76 int packet_len = AWSS_RESET_PKT_LEN;
77 int topic_len = AWSS_RESET_TOPIC_LEN;
78
79 if (awss_report_reset_suc) {
80 return 0;
81 }
82
83 if (report_reset_timer == NULL) {
84 report_reset_timer = HAL_Timer_Create(
85 "report_rst", (void (*)(void *))awss_report_reset_to_cloud, NULL);
86 }
87 HAL_Timer_Stop(report_reset_timer);
88 HAL_Timer_Start(report_reset_timer, 3000);
89 do {
90 char pk[IOTX_PRODUCT_KEY_LEN + 1] = { 0 };
91 char dn[IOTX_DEVICE_NAME_LEN + 1] = { 0 };
92
93 HAL_GetProductKey(pk);
94 HAL_GetDeviceName(dn);
95
96 topic = (char *)devrst_malloc(topic_len + 1);
97 if (topic == NULL) {
98 goto REPORT_RST_ERR;
99 }
100 memset(topic, 0, topic_len + 1);
101
102 HAL_Snprintf(topic, topic_len, TOPIC_RESET_REPORT_REPLY, pk, dn);
103
104 #ifdef MQTT_AUTO_SUBSCRIBE
105 ret = IOT_MQTT_Subscribe(
106 NULL, topic, IOTX_MQTT_QOS3_SUB_LOCAL,
107 (iotx_mqtt_event_handle_func_fpt)awss_report_reset_reply, NULL);
108 #else
109 ret = IOT_MQTT_Subscribe(
110 NULL, topic, IOTX_MQTT_QOS0,
111 (iotx_mqtt_event_handle_func_fpt)awss_report_reset_reply, NULL);
112 #endif
113 if (ret < 0) {
114 goto REPORT_RST_ERR;
115 }
116
117 memset(topic, 0, topic_len + 1);
118 HAL_Snprintf(topic, topic_len, TOPIC_RESET_REPORT, pk, dn);
119 } while (0);
120
121 packet = devrst_malloc(packet_len + 1);
122 if (packet == NULL) {
123 ret = -1;
124 goto REPORT_RST_ERR;
125 }
126 memset(packet, 0, packet_len + 1);
127
128 do {
129 char id_str[AWSS_RESET_MSG_ID_LEN + 1] = { 0 };
130 HAL_Snprintf(id_str, AWSS_RESET_MSG_ID_LEN, "\"%u\"",
131 awss_report_reset_id++);
132 final_len = HAL_Snprintf(packet, packet_len, AWSS_RESET_REQ_FMT, id_str,
133 METHOD_RESET_REPORT, "{}");
134 } while (0);
135
136 devrst_debug("[RST]", "report reset:%s\r\n", packet);
137
138 ret =
139 IOT_MQTT_Publish_Simple(NULL, topic, IOTX_MQTT_QOS0, packet, final_len);
140 devrst_debug("[RST]", "report reset result:%d\r\n", ret);
141
142 REPORT_RST_ERR:
143 if (packet) {
144 devrst_free(packet);
145 }
146 if (topic) {
147 devrst_free(topic);
148 }
149 return ret;
150 }
151
awss_report_reset()152 int awss_report_reset()
153 {
154 char rst = 0x01;
155
156 awss_report_reset_suc = 0;
157
158 HAL_Kv_Set(AWSS_KV_RST, &rst, sizeof(rst), 0);
159
160 return awss_report_reset_to_cloud();
161 }
162
awss_check_reset()163 int awss_check_reset()
164 {
165 int len = 1;
166 char rst = 0;
167
168 if (HAL_Kv_Get(AWSS_KV_RST, &rst, &len) < 0) {
169 devrst_err("[RST]", "get reset state err\r\n");
170 return 0;
171 }
172
173 if (rst != 0x01) { /* reset flag is not set */
174 devrst_debug("[RST]", "no rst\r\n");
175 return 0;
176 }
177
178 awss_report_reset_suc = 0;
179 log_info("[RST]", "need report rst\r\n");
180
181 return 1;
182 }
183
awss_stop_report_reset()184 int awss_stop_report_reset()
185 {
186 if (report_reset_timer == NULL) {
187 return 0;
188 }
189
190 HAL_Timer_Stop(report_reset_timer);
191 HAL_Timer_Delete(report_reset_timer);
192 report_reset_timer = NULL;
193
194 return 0;
195 }
196
197 #if defined(__cplusplus) /* If this is a C++ compiler, use C linkage */
198 }
199 #endif
200