1 /*
2 * Copyright (C) 2015-2020 Alibaba Group Holding Limited
3 */
4 #include <stdlib.h>
5
6 //#include <aos/aos.h>
7 #include <aos/kernel.h>
8 #include <port/mesh_hal_ble.h>
9 #include "mesh.h"
10 #include "common/log.h"
11 #include "flash.h"
12 #include "genie_service.h"
13 #include "genie_sal_uart.h"
14
15 #define at_debug printf
16
17 static const at_cmd_t genie_at_commands[] = {
18 //AT+CMD AT+CMD=? AT+CMD?
19 {BLE_MESH_ADV, genie_at_cmd_adv_start, "AT+" BLE_MESH_ADV "=<mode>", genie_at_cmd_adv_query},
20 {BLE_MESH_RESET, genie_at_cmd_mesh_reset, "AT+" BLE_MESH_RESET, NULL},
21 {BLE_MESH_REBOOT, genie_at_cmd_reboot, "AT+" BLE_MESH_REBOOT, NULL},
22 {BLE_MESH_INFO, NULL, "AT+" BLE_MESH_INFO, genie_at_cmd_mesh_info},
23 {BLE_MESH_VER, NULL, "AT+" BLE_MESH_VER, genie_at_cmd_mesh_ver},
24 {BLE_MESH_MAC, NULL, "AT+" BLE_MESH_MAC, genie_at_cmd_mesh_mac},
25 {BLE_MESH_FACTY_TEST, genie_at_cmd_facty_test, "AT+" BLE_MESH_FACTY_TEST, NULL},
26 {BLE_MESH_LOG, genie_at_cmd_mesh_log, "AT+" BLE_MESH_LOG "=<mode>", genie_at_cmd_mesh_log_query},
27 {BLE_MESH_TEST, genie_at_cmd_mesh_test, "AT+" BLE_MESH_TEST "=<opcode>,[param]", NULL},
28 {BLE_MESH_GROUP, genie_at_cmd_mesh_group, "AT+" BLE_MESH_GROUP "=<addr1>,[addr2]...", genie_at_cmd_mesh_group_query},
29 {BLE_MESH_MSG_TX, genie_at_cmd_mesh_trans_send, "AT+" BLE_MESH_MSG_TX "=<data>", NULL},
30 {BLE_MESH_EVENT, NULL, "+" BLE_MESH_EVENT ":<state>", NULL},
31 {BLE_MESH_MSG_RX, NULL, "+" BLE_MESH_MSG_RX ":<len>,<data>", NULL},
32 {NULL, NULL, NULL, NULL},
33 };
34
35 static u8_t g_current_adv_mode = MESH_ADV_START;
36 static uint8_t test_dev_mac[6] = {0};
37
str_chr(char * d,char * s,int c)38 static char *str_chr(char *d, char *s, int c)
39 {
40 int i = 0;
41 char *q = d;
42 char *p = s;
43
44 for (i = 0; *(s + i) != (char)c; i++)
45 {
46 *(q++) = *(p++);
47
48 if (*(s + i) == '\0')
49 {
50 return NULL;
51 }
52 }
53
54 *(q++) = '\0';
55 return d;
56 }
57
char_cut(char * d,char * s,int b,int e)58 static char *char_cut(char *d, char *s, int b, int e)
59 {
60 char *stc;
61
62 if (b == '\0')
63 {
64 return NULL;
65 }
66
67 stc = strchr(s, b);
68
69 if (stc == NULL)
70 {
71 at_debug("not execute\r\n");
72 return NULL;
73 }
74
75 stc++;
76 str_chr(d, stc, e);
77
78 return d; //(char *)d;
79 }
80
char2_hex(const char * c,uint8_t * x)81 static int char2_hex(const char *c, uint8_t *x)
82 {
83 if (*c >= '0' && *c <= '9')
84 {
85 *x = *c - '0';
86 }
87 else if (*c >= 'a' && *c <= 'f')
88 {
89 *x = *c - 'a' + 10;
90 }
91 else if (*c >= 'A' && *c <= 'F')
92 {
93 *x = *c - 'A' + 10;
94 }
95 else
96 {
97 return -EINVAL;
98 }
99
100 return 0;
101 }
102
str2_char(const char * str,uint8_t * addr)103 static int str2_char(const char *str, uint8_t *addr)
104 {
105 int i, j;
106 uint8_t tmp;
107
108 if (strlen(str) != 17)
109 {
110 return -EINVAL;
111 }
112
113 for (i = 0, j = 1; *str != '\0'; str++, j++)
114 {
115 if (!(j % 3) && (*str != ':'))
116 {
117 return -EINVAL;
118 }
119 else if (*str == ':')
120 {
121 i++;
122 continue;
123 }
124
125 addr[i] = addr[i] << 4;
126
127 if (char2_hex(str, &tmp) < 0)
128 {
129 return -EINVAL;
130 }
131
132 addr[i] |= tmp;
133 }
134
135 return 0;
136 }
137
argv_type(char * s)138 static int argv_type(char *s)
139 {
140 int flag = 0;
141
142 flag |= AT_CMD_NO_ADD;
143
144 for (int i = 0; *(s + i) != '\0'; i++)
145 {
146 if (*(s + i) == '+')
147 {
148 flag = flag & (~0x1);
149 flag |= AT_CMD_ADD; //+ no =
150 }
151
152 if (*(s + i) == '=')
153 { //, or not ,
154 if (*(s + i + 1) == '?')
155 {
156 return AT_CMD_FIND;
157 }
158 else if (*(s + i + 1) != '\0')
159 {
160 return AT_CMD_DOU;
161 }
162 else
163 {
164 return 0;
165 }
166 }
167
168 if (*(s + i) == '?')
169 {
170 flag = flag & (~0x2); //no +
171 flag |= AT_CMD_QUERY;
172 }
173 }
174
175 return flag;
176 }
177
argc_len(char * s)178 static int argc_len(char *s)
179 {
180 int i = 0;
181 int j = 0;
182
183 for (i = 0; *(s + i) != '\0'; i++)
184 {
185 if ((*(s + i) == ',') || (*(s + i) == '?') || (*(s + i) == '='))
186 {
187 j++;
188 }
189 }
190
191 return j;
192 }
193
cmd_cli_func(int type,int argc,char ** argv)194 static void cmd_cli_func(int type, int argc, char **argv)
195 {
196 int i = 0;
197 int err;
198
199 if (argc < 2)
200 {
201 genie_sal_uart_send_str("AT support commands\r\n");
202 for (i = 0; genie_at_commands[i].cmd_name != NULL; i++)
203 {
204 genie_sal_uart_send_str("%s %s\r\n", genie_at_commands[i].cmd_name, genie_at_commands[i].help);
205 }
206 return;
207 }
208
209 for (i = 0; genie_at_commands[i].cmd_name != NULL; i++)
210 {
211 if (strlen(genie_at_commands[i].cmd_name) == strlen(argv[1]) &&
212 !strncmp(genie_at_commands[i].cmd_name, argv[1], strlen(genie_at_commands[i].cmd_name)))
213 {
214 if (type == AT_OP_EXECUTE)
215 {
216 if (genie_at_commands[i].cb)
217 {
218 err = genie_at_commands[i].cb(argc - 1, &argv[1]);
219 if (err == 0)
220 {
221 genie_sal_uart_send_str(AT_OK_STR);
222 }
223 else
224 {
225 genie_sal_uart_send_str(AT_CME_ERROR_STR, err);
226 }
227 }
228 else
229 {
230 genie_sal_uart_send_str(AT_CME_ERROR_STR, AT_ERR_NOT_FOUND);
231 }
232 }
233 else if (type == AT_OP_FCURRENT)
234 {
235 if (genie_at_commands[i].fcb)
236 {
237 err = genie_at_commands[i].fcb(argc - 1, &argv[1]);
238 if (err == 0)
239 {
240 genie_sal_uart_send_str(AT_OK_STR);
241 }
242 else
243 {
244 genie_sal_uart_send_str(AT_CME_ERROR_STR, err);
245 }
246 }
247 else
248 {
249 genie_sal_uart_send_str(AT_CME_ERROR_STR, AT_ERR_NOT_FOUND);
250 }
251 }
252 else
253 { //HLOOKUP
254 if (genie_at_commands[i].help)
255 {
256 genie_sal_uart_send_str("%s\n", genie_at_commands[i].help);
257 genie_sal_uart_send_str(AT_OK_STR);
258 }
259 }
260
261 break;
262 }
263 }
264
265 if ((i + 1) == ARRAY_SIZE(genie_at_commands))
266 {
267 genie_sal_uart_send_str(AT_CME_ERROR_STR, AT_ERR_NOT_FOUND);
268 }
269 }
270
is_at_cmd(char * data)271 static int is_at_cmd(char *data)
272 {
273 if (strlen(data) < 2)
274 {
275 return 1;
276 }
277
278 if (((*data == 'A') || (*data == 'a')) && ((*(data + 1) == 'T') || (*(data + 1) == 't')))
279 {
280 return 0;
281 }
282
283 return 1;
284 }
285
genie_at_cmd_parser(char data[])286 int genie_at_cmd_parser(char data[])
287 {
288 char argv[AT_MAX_ARGC][AT_MAX_ARGV_LEN];
289 char *hcc;
290 char *argqv[AT_MAX_ARGC];
291
292 if (is_at_cmd(data))
293 {
294 return -1;
295 }
296
297 memset(argv, 0, sizeof(argv));
298 int ustype = argv_type(data);
299 argv[0][0] = 'A';
300 argv[0][1] = 'T';
301 argv[0][2] = '\0';
302
303 //at_debug("ustype: %d, data: %s\n", ustype, data);
304 switch (ustype)
305 {
306 case AT_CMD_NO_ADD:
307 cmd_cli_func(AT_OP_HELP, 1, NULL);
308 genie_sal_uart_send_str(AT_OK_STR);
309 break;
310
311 case AT_CMD_ADD: //execute
312 if (char_cut(argv[1], data, '+', '\0') == NULL)
313 {
314 return -1;
315 }
316
317 argqv[0] = (char *)(&argv[0]);
318 argqv[1] = (char *)(&argv[1]);
319 cmd_cli_func(AT_OP_EXECUTE, 2, (char **)(&argqv));
320 break;
321
322 case AT_CMD_QUERY: //?
323 if (char_cut((char *)argv[1], data, '+', '?') == NULL)
324 {
325 return -1;
326 }
327
328 argqv[0] = (char *)(&argv[0]);
329 argqv[1] = (char *)(&argv[1]);
330 cmd_cli_func(AT_OP_FCURRENT, 2, (char **)(&argqv));
331 break;
332
333 case AT_CMD_DOU:
334 if (char_cut((char *)argv[1], data, '+', '=') == NULL)
335 {
336 return -1;
337 }
338
339 hcc = strchr(data, '=');
340 int num = argc_len(hcc);
341 //at_debug("num:%d, len:%d\n", num, strlen(hcc));
342 if ((num > AT_MAX_ARGC - 2) || (strlen(hcc) > (AT_MAX_ARGC * AT_MAX_ARGV_LEN)))
343 {
344 at_debug("argv out of the max len\r\n");
345 return -1;
346 }
347
348 if (num == 0)
349 {
350 at_debug("num:err 0\r\n");
351 return -1;
352 }
353
354 if (num == 1)
355 {
356 char_cut((char *)argv[2], hcc, '=', '\0');
357 argqv[2] = (char *)(&argv[2]);
358 }
359 else
360 {
361 char_cut((char *)argv[2], hcc, '=', ',');
362 argqv[2] = (char *)(&argv[2]);
363
364 for (int i = 1; i < num; i++)
365 {
366 hcc = strchr(hcc, ',');
367 char_cut((char *)argv[2 + i], hcc, ',', ',');
368 argqv[2 + i] = (char *)(&argv[2 + i]);
369 hcc++;
370 }
371 }
372
373 argqv[0] = (char *)(&argv[0]);
374 argqv[1] = (char *)(&argv[1]);
375 cmd_cli_func(AT_OP_EXECUTE, num + 2, (char **)(&argqv));
376 break;
377
378 case AT_CMD_FIND: //=?
379 hcc = strrchr(data, '+');
380 hcc++;
381 str_chr(argv[1], hcc, '=');
382 argqv[0] = (char *)(&argv[0]);
383 argqv[1] = (char *)(&argv[1]);
384 cmd_cli_func(AT_OP_HLOOKUP, 2, (char **)(&argqv));
385 break;
386
387 default:
388 at_debug("unknow type:%d\r\n", ustype);
389 return -1;
390 }
391
392 return 0;
393 }
394
genie_at_cmd_reboot(int argc,char * argv[])395 int genie_at_cmd_reboot(int argc, char *argv[])
396 {
397 /* AT+REBOOT */
398 if (argc > 1)
399 {
400 return AT_ERR_FORMAT;
401 }
402
403 genie_sal_uart_send_str("OK\r\n");
404 aos_msleep(30);
405 aos_reboot();
406 return 0;
407 }
408
genie_at_cmd_mesh_reset(int argc,char * argv[])409 int genie_at_cmd_mesh_reset(int argc, char *argv[])
410 {
411 /* AT+MESHRST */
412 if (argc > 1)
413 {
414 return AT_ERR_FORMAT;
415 }
416
417 genie_sal_uart_send_str("OK\r\n");
418 genie_event(GENIE_EVT_HW_RESET_START, NULL);
419 return 0;
420 }
421
genie_at_cmd_adv_start(int argc,char * argv[])422 int genie_at_cmd_adv_start(int argc, char *argv[])
423 {
424 /* AT+MESHADV=<mode> */
425 uint8_t mode = 0;
426
427 if (argc != 2)
428 {
429 return AT_ERR_FORMAT;
430 }
431
432 mode = strtoul(argv[1], NULL, 0);
433 if (mode == MESH_ADV_CLOSE)
434 {
435 /* close adv */
436 bt_mesh_adv_stop();
437 bt_mesh_prov_disable(BT_MESH_PROV_GATT | BT_MESH_PROV_ADV);
438 }
439 else if (mode == MESH_ADV_START)
440 {
441 /* start adv */
442 bt_mesh_adv_stop();
443 bt_mesh_prov_enable(BT_MESH_PROV_GATT | BT_MESH_PROV_ADV);
444 genie_event(GENIE_EVT_SDK_MESH_PBADV_START, NULL);
445 }
446 else if (mode == MESH_ADV_SILENT)
447 {
448 /* start silent adv */
449 genie_event(GENIE_EVT_SDK_MESH_PBADV_TIMEOUT, NULL);
450 }
451 else
452 {
453 return AT_ERR_FORMAT;
454 }
455
456 g_current_adv_mode = mode;
457 return 0;
458 }
459
genie_at_cmd_adv_query(int argc,char * argv[])460 int genie_at_cmd_adv_query(int argc, char *argv[])
461 {
462 /* AT+MESHADV? */
463 if (argc > 1)
464 {
465 return AT_ERR_FORMAT;
466 }
467
468 genie_sal_uart_send_str(AT_RESPONSE_STR "%d\r\n", BLE_MESH_ADV, g_current_adv_mode);
469 return 0;
470 }
471
genie_at_cmd_mesh_log(int argc,char * argv[])472 int genie_at_cmd_mesh_log(int argc, char *argv[])
473 {
474 /* AT+MESHLOG=<mode> */
475 uint8_t mode = 0;
476
477 if (argc != 2)
478 {
479 return AT_ERR_FORMAT;
480 }
481
482 mode = strtoul(argv[1], NULL, 0);
483 if ((mode == 1) || (mode == 0))
484 {
485 g_mesh_log_mode = mode;
486 if (!g_mesh_log_mode)
487 {
488 genie_sal_uart_send_str("OK\r\n");
489 aos_set_log_level(LOG_EMERG);
490 }
491 else
492 {
493 aos_set_log_level(GENIE_MESH_DEFAULT_LOG_LEVEL);
494 }
495 return 0;
496 }
497 else
498 {
499 return AT_ERR_FORMAT;
500 }
501 }
502
genie_at_cmd_mesh_log_query(int argc,char * argv[])503 int genie_at_cmd_mesh_log_query(int argc, char *argv[])
504 {
505 /* AT+MESHLOG? */
506 if (argc > 1)
507 {
508 return AT_ERR_FORMAT;
509 }
510
511 genie_sal_uart_send_str("+%s:%d\r\n", BLE_MESH_LOG, g_mesh_log_mode);
512 return 0;
513 }
514
genie_at_cmd_mesh_info(int argc,char * argv[])515 int genie_at_cmd_mesh_info(int argc, char *argv[])
516 {
517 bool status;
518
519 /* AT+MESHINF? */
520 if (argc > 1)
521 {
522 return AT_ERR_FORMAT;
523 }
524
525 status = bt_mesh_is_provisioned();
526 genie_sal_uart_send_str(AT_RESPONSE_STR "%d\r\n", BLE_MESH_INFO, status);
527 return 0;
528 }
529
genie_at_cmd_mesh_ver(int argc,char * argv[])530 int genie_at_cmd_mesh_ver(int argc, char *argv[])
531 {
532 /* AT+MESHVER? */
533 if (argc > 1)
534 {
535 return AT_ERR_FORMAT;
536 }
537
538 genie_sal_uart_send_str(AT_RESPONSE_STR "%08x\r\n", BLE_MESH_VER, genie_version_appver_get());
539 return 0;
540 }
541
genie_at_cmd_mesh_mac(int argc,char * argv[])542 int genie_at_cmd_mesh_mac(int argc, char *argv[])
543 {
544 uint8_t addr[6] = {0};
545
546 /* AT+MESHMAC? */
547 if (argc > 1)
548 {
549 return AT_ERR_FORMAT;
550 }
551
552 hal_flash_read_mac_params(addr, sizeof(addr));
553 genie_sal_uart_send_str(AT_RESPONSE_STR " %02x:%02x:%02x:%02x:%02x:%02x\r\n", BLE_MESH_MAC, addr[0], addr[1], addr[2], addr[3], addr[4], addr[5]);
554 return 0;
555 }
556
genie_at_cmd_facty_test(int argc,char * argv[])557 int genie_at_cmd_facty_test(int argc, char *argv[])
558 {
559 int ret = -1;
560
561 /* AT+FACTYTEST */
562 if (argc > 1)
563 {
564 return AT_ERR_FORMAT;
565 }
566
567 ret = genie_sal_ble_set_factory_flag();
568 if (ret != 0)
569 {
570 return AT_ERR_EXE;
571 }
572
573 genie_sal_uart_send_str("OK\r\n");
574 aos_reboot();
575 return 0;
576 }
577
578 static int8_t get_rssi_result = 0;
get_ble_rssi_cb(uint8_t mac[6],int16_t rssi)579 static void get_ble_rssi_cb(uint8_t mac[6], int16_t rssi)
580 {
581 if (memcmp(test_dev_mac, mac, sizeof(test_dev_mac)) == 0)
582 {
583 get_rssi_result = 0;
584 memset(test_dev_mac, 0, sizeof(test_dev_mac));
585 genie_sal_uart_send_str(AT_RESPONSE_STR "%d,%d\r\n", BLE_MESH_TEST, MESH_TEST_RSSI, rssi);
586 }
587 else
588 {
589 get_rssi_result = -1;
590 at_debug("cann't find mac: %s rssi\n", bt_hex(test_dev_mac, sizeof(test_dev_mac)));
591 }
592 }
593
genie_at_cmd_mesh_test(int argc,char * argv[])594 int genie_at_cmd_mesh_test(int argc, char *argv[])
595 {
596 uint32_t opcode;
597 int err;
598
599 /* AT+MESHTEST=<opcode>,[param] */
600 if (argc < 2)
601 {
602 return AT_ERR_FORMAT;
603 }
604
605 opcode = strtoul(argv[1], NULL, 0);
606 switch (opcode)
607 {
608 case MESH_TEST_RSSI:
609 err = str2_char(argv[2], test_dev_mac);
610 //at_debug("test_dev_mac: %s\n", bt_hex(test_dev_mac, sizeof(test_dev_mac)));
611 if (err != 0)
612 {
613 at_debug("invalid address\n");
614 return AT_ERR_FORMAT;
615 }
616
617 /* start scan,find the dev and get rssi */
618 err = genie_sal_ble_get_rssi(test_dev_mac, (genie_sal_ble_get_rssi_cb)get_ble_rssi_cb, 5000);
619 if (err != 0)
620 {
621 at_debug("start scan error\n");
622 return AT_ERR_EXE;
623 }
624 break;
625
626 default:
627 return AT_ERR_FORMAT;
628 }
629
630 return get_rssi_result;
631 }
632
genie_at_cmd_mesh_group(int argc,char * argv[])633 int genie_at_cmd_mesh_group(int argc, char *argv[])
634 {
635 u16_t group_list[CONFIG_BT_MESH_MODEL_GROUP_COUNT] = {0};
636 int group_num = argc - 1;
637
638 /* AT+MESHGRP=<addr1>,[addr2]... */
639 if (argc > (CONFIG_BT_MESH_MODEL_GROUP_COUNT + 1) || argc < 2)
640 {
641 return AT_ERR_FORMAT;
642 }
643
644 for (int i = 0; i < group_num; i++)
645 {
646 group_list[i] = strtoul(argv[i + 1], NULL, 0);
647 if (group_list[i] < GENIE_ADDR_MIN || group_list[i] > GENIE_ADDR_MAX)
648 {
649 return AT_ERR_FORMAT;
650 }
651 }
652
653 /* set group addr */
654 if (genie_storage_write_sub(group_list) != GENIE_STORAGE_SUCCESS)
655 {
656 return AT_ERR_EXE;
657 }
658
659 /* get group addr */
660 if (genie_storage_read_sub(g_sub_list) != GENIE_STORAGE_SUCCESS)
661 {
662 return AT_ERR_EXE;
663 }
664
665 return 0;
666 }
667
genie_at_cmd_mesh_group_query(int argc,char * argv[])668 int genie_at_cmd_mesh_group_query(int argc, char *argv[])
669 {
670 u16_t group_list[CONFIG_BT_MESH_MODEL_GROUP_COUNT] = {0};
671 char result[100] = {0};
672 int len = 0;
673
674 /* AT+MESHGRP? */
675 if (argc > 2)
676 {
677 return AT_ERR_FORMAT;
678 }
679
680 /* get group addr */
681 if (genie_storage_read_sub(group_list) != GENIE_STORAGE_SUCCESS)
682 {
683 return AT_ERR_EXE;
684 }
685
686 len = snprintf(result, sizeof(result), AT_RESPONSE_STR, BLE_MESH_GROUP);
687 for (int i = 0; i < CONFIG_BT_MESH_MODEL_GROUP_COUNT; i++)
688 {
689 if (len < (sizeof(result) - 5) && group_list[i] != 0x0000)
690 {
691 len += snprintf(result + len, sizeof(result) - len, "0x%04X,", group_list[i]);
692 }
693 }
694
695 result[len - 1] = '\0';
696 genie_sal_uart_send_str("%s\r\n", result);
697
698 return 0;
699 }
700
_send_trans_msg(char * data)701 static int _send_trans_msg(char *data)
702 {
703 uint8_t count = 0;
704 uint8_t msg_b[GENIE_HAL_BLE_SEND_MAX_DATA_LEN];
705 uint8_t ret = 0;
706
707 count = strlen(data) >> 1;
708 if (count > GENIE_HAL_BLE_SEND_MAX_DATA_LEN)
709 {
710 at_debug("data out of the max len\n");
711 return AT_ERR_FORMAT;
712 }
713 memset(msg_b, 0x0, sizeof(msg_b));
714 ret = stringtohex(data, msg_b, count);
715 if (ret == 0)
716 {
717 at_debug("stringtohex error\n");
718 return AT_ERR_FORMAT;
719 }
720
721 if (genie_sal_ble_send_msg(0, msg_b, count))
722 {
723 return AT_ERR_EXE;
724 }
725
726 return 0;
727 }
728
genie_at_cmd_mesh_trans_send(int argc,char * argv[])729 int genie_at_cmd_mesh_trans_send(int argc, char *argv[])
730 {
731 /* AT+MESHMSGTX=<data> */
732 if (argc < 2)
733 {
734 return AT_ERR_FORMAT;
735 }
736
737 return _send_trans_msg(argv[1]);
738 }
739
genie_at_cmd_send_data_to_mcu(uint8_t * p_data,uint16_t data_len)740 int genie_at_cmd_send_data_to_mcu(uint8_t *p_data, uint16_t data_len)
741 {
742 int i = 0;
743 int len = 0;
744 char *p_send_buff = NULL;
745 uint16_t send_buff_len = 0;
746
747 send_buff_len = strlen(BLE_MESH_MSG_RX) + 2 * data_len + 10;
748
749 p_send_buff = (char *)aos_malloc(send_buff_len);
750 if (NULL == p_send_buff)
751 {
752 return -1;
753 }
754 memset(p_send_buff, '\0', send_buff_len);
755
756 len = snprintf(p_send_buff, send_buff_len, "\r\n" AT_RESPONSE_STR "%d,", BLE_MESH_MSG_RX, data_len);
757 for (i = 0; i < data_len; i++)
758 {
759 len += snprintf(p_send_buff + len, send_buff_len - len, "%02X", p_data[i]);
760 }
761
762 genie_sal_uart_send_str("%s\r\n", p_send_buff);
763 aos_free(p_send_buff);
764
765 return 0;
766 }
767
genie_at_output_event(genie_event_e event,void * p_arg)768 int genie_at_output_event(genie_event_e event, void *p_arg)
769 {
770 char result[100] = {0};
771 int len = 0;
772
773 /* +MESHEVT:<state> */
774 len = snprintf(result, sizeof(result), AT_RESPONSE_STR, BLE_MESH_EVENT);
775
776 if (event == GENIE_EVT_MESH_READY)
777 {
778 len += snprintf(result + len, sizeof(result) - len, "0x%02X", MESH_EVENT_DEV_READY);
779 }
780 else if (event == GENIE_EVT_SDK_MESH_PROV_SUCCESS)
781 {
782 len += snprintf(result + len, sizeof(result) - len, "0x%02X", MESH_EVENT_PROV_SUCCESS);
783 g_current_adv_mode = MESH_ADV_CLOSE;
784 }
785 else if (event == GENIE_EVT_SDK_MESH_PROV_FAIL)
786 {
787 len += snprintf(result + len, sizeof(result) - len, "0x%02X", MESH_EVENT_PROV_FAILED);
788 }
789 else
790 {
791 if (event == GENIE_EVT_SDK_MESH_SILENT_START)
792 {
793 g_current_adv_mode = MESH_ADV_SILENT;
794 }
795 return 0;
796 }
797
798 genie_sal_uart_send_str("%s\r\n", result);
799
800 return 0;
801 }
802