• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /**
2  * Copyright (c) 2020 HiSilicon (Shanghai) Technologies CO., LIMITED.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License. \n
14  * Licensed under the Apache License, Version 2.0 (the "License");
15  * you may not use this file except in compliance with the License.
16  * You may obtain a copy of the License at
17  *
18  *     http://www.apache.org/licenses/LICENSE-2.0
19  *
20  * Unless required by applicable law or agreed to in writing, software
21  * distributed under the License is distributed on an "AS IS" BASIS,
22  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
23  * See the License for the specific language governing permissions and
24  * limitations under the License. *
25  * Description: At plt function \n
26  */
27 
28 #include <string.h>
29 
30 #include "gpio.h"
31 #include "pinctrl.h"
32 #include "pinctrl_porting.h"
33 #include "watchdog.h"
34 #ifdef CONFIG_MIDDLEWARE_SUPPORT_FTM
35 #include "factory.h"
36 #endif
37 #ifdef _PRE_WLAN_FEATURE_MFG_TEST
38 #include "factory.h"
39 #include "sfc.h"
40 #include "xo_trim_porting.h"
41 #endif
42 #ifdef CONFIG_DRIVER_SUPPORT_TSENSOR
43 #include "tsensor.h"
44 #endif
45 #if defined(ENABLE_LOW_POWER) && (ENABLE_LOW_POWER == YES)
46 #include "idle_config.h"
47 #endif
48 #include "at_cmd.h"
49 #include "at_utils.h"
50 #include "at_plt_cmd_register.h"
51 #include "at_plt_cmd_table.h"
52 #include "debug_print.h"
53 #include "time64.h"
54 #include "version_porting.h"
55 #include "hal_reboot.h"
56 #include "at_plt.h"
57 
58 #ifdef CONFIG_MIDDLEWARE_SUPPORT_NV
59 #include "nv.h"
60 #endif
61 #ifdef CONFIG_MIDDLEWARE_SUPPORT_UPG_AB
62 #include "upg_porting.h"
63 #include "upg_ab.h"
64 #endif
65 #include "efuse.h"
66 #include "efuse_porting.h"
67 #ifdef CONFIG_DFX_SUPPORT_PRINT
68 #include "dfx_print.h"
69 #endif
70 #ifdef CONFIG_SUPPORT_CRASHINFO_SAVE_TO_FLASH
71 #include "exception.h"
72 #endif
73 
74 #define CONVERT_HALF 2
at_plt_convert_bin_to_dec(td_s32 pbin)75 static td_s32 at_plt_convert_bin_to_dec(td_s32 pbin)
76 {
77     td_s32 result = 0;
78     td_s32 temp = pbin;
79 
80     while (temp != 0) {
81         result += temp % CONVERT_HALF;
82         temp /= CONVERT_HALF;
83     }
84 
85     return result;
86 }
87 
at_plt_check_mac_elem(TD_CONST td_char elem)88 TD_PRV td_u32 at_plt_check_mac_elem(TD_CONST td_char elem)
89 {
90     if (elem >= '0' && elem <= '9') {
91         return EXT_ERR_SUCCESS;
92     } else if (elem >= 'A' && elem <= 'F') {
93         return EXT_ERR_SUCCESS;
94     } else if (elem >= 'a' && elem <= 'f') {
95         return EXT_ERR_SUCCESS;
96     } else if (elem == ':') {
97         return EXT_ERR_SUCCESS;
98     }
99 
100     return EXT_ERR_FAILURE;
101 }
102 
at_plt_cmd_strtoaddr(TD_CONST td_char * param,td_uchar * mac_addr,td_u32 addr_len)103 static td_u32 at_plt_cmd_strtoaddr(TD_CONST td_char *param, td_uchar *mac_addr, td_u32 addr_len)
104 {
105     td_u32 cnt;
106     td_char *tmp1 = (td_char *)param;
107     td_char *tmp2 = TD_NULL;
108     td_char *tmp3 = TD_NULL;
109 
110     for (cnt = 0; cnt < 17; cnt++) {    /* 17 */
111         if (at_plt_check_mac_elem(param[cnt]) != EXT_ERR_SUCCESS) {
112             return EXT_ERR_FAILURE;
113         }
114     }
115 
116     for (cnt = 0; cnt < (addr_len - 1); cnt++) {
117         tmp2 = (char*)strsep(&tmp1, ":");
118         if (tmp2 == TD_NULL) {
119             return EXT_ERR_AT_INVALID_PARAMETER;
120         }
121         mac_addr[cnt] = (td_uchar)strtoul(tmp2, &tmp3, 16); /* 16 */
122     }
123 
124     if (tmp1 == TD_NULL) {
125         return EXT_ERR_AT_INVALID_PARAMETER;
126     }
127     mac_addr[cnt] = (td_uchar)strtoul(tmp1, &tmp3, 16); /* 16 */
128     return EXT_ERR_SUCCESS;
129 }
130 
131 #ifdef CONFIG_MIDDLEWARE_SUPPORT_NV
132 #define AT_PLT_NV_WRITE_MAX_LENGTH 1024
133 typedef enum {
134     PLT_NV_ATTR_NORMAL = 0,
135     PLT_NV_ATTR_PERMANENT = 1,
136     PLT_NV_ATTR_ENCRYPTED = 2,
137     PLT_NV_ATTR_NON_UPGRADE = 4
138 } plt_nv_attr;
139 STATIC uint32_t plt_nv_get_value(const nvwrite_args_t *args, uint8_t *value);
140 #endif
141 #define  DATE_BASE_YEAR     1900
142 #define  leap_year(y) (((y) % 4) == 0 && (((y) % 100) != 0 || ((y) % 400) == 0))
143 static const int32_t g_mon_lengths[2][12] = { /* 2: 2 Column,Contains leap year; 12: 12 months */
144     {31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31},
145     {31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31}
146 };
147 
148 #define AT_PLT_FUNC_NUM (sizeof(at_plt_cmd_parse_table) / sizeof(at_plt_cmd_parse_table[0]))
149 
los_at_plt_cmd_register(void)150 void los_at_plt_cmd_register(void)
151 {
152     print_str("los_at_plt_cmd_register EXCUTE\r\n");
153     uapi_at_plt_register_cmd(at_plt_cmd_parse_table, AT_PLT_FUNC_NUM);
154 }
155 
plt_nv_read(const nvread_args_t * args)156 at_ret_t plt_nv_read(const nvread_args_t *args)
157 {
158 #ifdef CONFIG_MIDDLEWARE_SUPPORT_NV
159     uint16_t nv_value_length = 0;
160     uint8_t nv_value[AT_PLT_NV_WRITE_MAX_LENGTH] = {0};
161     nv_key_attr_t nv_attr = {0};
162     errcode_t ret = uapi_nv_read_with_attr((uint16_t)args->key_id, AT_PLT_NV_WRITE_MAX_LENGTH, &nv_value_length,
163         nv_value, &nv_attr);
164     if (ret != ERRCODE_SUCC) {
165         print_str("plt_nv_read failed, ret = [0x%x]\r\n", ret);
166         return ret;
167     }
168     if (nv_attr.permanent == true) {
169         print_str("NV[0x%x] is permanent\r\n", args->key_id);
170     }
171     if (nv_attr.encrypted == true) {
172         print_str("NV[0x%x] is encrypted\r\n", args->key_id);
173     }
174     if (nv_attr.non_upgrade == true) {
175         print_str("NV[0x%x] is non_upgrade\r\n", args->key_id);
176     }
177     for (int i = 0; i < nv_value_length; i++) {
178         print_str("nv_value[%d] = [0x%x]\r\n", i, nv_value[i]);
179     }
180 #else
181     unused(args);
182 #endif
183     return AT_RET_OK;
184 }
185 
186 #ifdef CONFIG_MIDDLEWARE_SUPPORT_NV
plt_nv_get_value(const nvwrite_args_t * args,uint8_t * value)187 STATIC uint32_t plt_nv_get_value(const nvwrite_args_t *args, uint8_t *value)
188 {
189     errno_t ret;
190     td_u8 *tmp = TD_NULL;
191     tmp = (td_u8 *)malloc(args->length);
192     if (tmp == TD_NULL) {
193         free(tmp);
194         return AT_RET_SYNTAX_ERROR;
195     }
196 
197     at_str_to_hex((char *)(args->value), args->length + args->length, tmp); /* 2:偏移2个字符 */
198     ret = memcpy_s(value, AT_PLT_NV_WRITE_MAX_LENGTH + 1, tmp, args->length + 1);
199     free(tmp);
200     if (ret != EOK) {
201         return EXT_ERR_MEMCPYS_FAIL;
202     }
203     return EXT_ERR_SUCCESS;
204 }
205 #endif
plt_nv_write(const nvwrite_args_t * args)206 at_ret_t plt_nv_write(const nvwrite_args_t *args)
207 {
208 #ifdef CONFIG_MIDDLEWARE_SUPPORT_NV
209     if (args->length == 0) {
210         return AT_RET_CMD_PARA_ERROR;
211     }
212     uint8_t write_value[AT_PLT_NV_WRITE_MAX_LENGTH] = {0};
213     if (plt_nv_get_value(args, write_value) != EXT_ERR_SUCCESS) {
214         return AT_RET_CMD_PARA_ERROR;
215     }
216     nv_key_attr_t nv_attr = {0};
217     switch (args->attr) {
218         case PLT_NV_ATTR_PERMANENT:
219             nv_attr.permanent = 1;
220             break;
221         case PLT_NV_ATTR_ENCRYPTED:
222             nv_attr.encrypted = 1;
223             break;
224         case PLT_NV_ATTR_NON_UPGRADE:
225             nv_attr.non_upgrade = 1;
226             break;
227         default:
228             break;
229     }
230     errcode_t ret = uapi_nv_write_with_attr((uint16_t)args->key_id, write_value, (uint16_t)args->length, &nv_attr,
231         NULL);
232     if (ret != ERRCODE_SUCC) {
233         print_str("plt_nv_write failed, ret = [0x%x]\r\n", ret);
234         return ret;
235     }
236     for (uint32_t i = 0; i < args->length; i++) {
237         print_str("nv_value[%d] = [0x%x]\r\n", i, write_value[i]);
238     }
239 #else
240     unused(args);
241 #endif
242     return AT_RET_OK;
243 }
244 
245 #ifdef CONFIG_MIDDLEWARE_SUPPORT_UPG_AB
246 #define UPG_AB_REGION_CFG_ADDR 0x3FF000
247 #define UPG_AB_REGION_CFG_SIZE 0x1000
248 #define UPG_AB_CONFIG_CHECK 0x70746C6C
249 typedef struct {
250     uint32_t  check_num;    /* check number */
251     uint32_t  run_region;   /* run region */
252 } upg_ab_config_t;
253 #endif
upg_ab_set_run_region(const absetrun_args_t * args)254 at_ret_t upg_ab_set_run_region(const absetrun_args_t *args)
255 {
256 #ifdef CONFIG_MIDDLEWARE_SUPPORT_UPG_AB
257     errcode_t ret  = ws63_upg_init();
258     if (ret != ERRCODE_SUCC && ret != ERRCODE_UPG_ALREADY_INIT) {
259         print_str("ab upg set run region init failed, ret : 0x%x\r\n", ret);
260     }
261     upg_ab_config_t config = {0};
262     ret = upg_flash_read(UPG_AB_REGION_CFG_ADDR, sizeof(upg_ab_config_t), (uint8_t *)&config);
263     if (ret != ERRCODE_SUCC || config.check_num != UPG_AB_CONFIG_CHECK) {
264         print_str("ab upg set run region read failed, ret : 0x%x\r\n", ret);
265         return AT_RET_PROGRESS_BLOCK;
266     }
267     config.run_region = args->run_region;
268     ret = upg_flash_write(UPG_AB_REGION_CFG_ADDR, sizeof(upg_ab_config_t), (const uint8_t *)&config, true);
269     if (ret != ERRCODE_SUCC) {
270         print_str("ab upg set run region write failed, ret : 0x%x\r\n", ret);
271         return ret;
272     }
273 #else
274     unused(args);
275 #endif
276     return AT_RET_OK;
277 }
278 
279 #define MAC_ADDR_EFUSE 0
280 #define MAC_ADDR_NV 1
281 #define SLE_MAC_ADDR 2
282 #define SET_EFUSE_MAC_PARAM_CNT 2
283 #ifndef WIFI_MAC_LEN
284 #define WIFI_MAC_LEN 6
285 #endif
286 
287 /*****************************************************************************
288  功能描述  :设置efuse mac地址
289 *****************************************************************************/
set_efuse_mac_addr(const efusemac_args_t * args)290 at_ret_t set_efuse_mac_addr(const efusemac_args_t *args)
291 {
292     td_s32 argc = at_plt_convert_bin_to_dec((td_s32)args->para_map);
293     td_uchar mac_addr[WIFI_MAC_LEN] = {0};
294 
295     if (argc != SET_EFUSE_MAC_PARAM_CNT || strlen((const char *)args->mac_addr) != 17) { /* 17 mac string len */
296         return AT_RET_SYNTAX_ERROR;
297     }
298 
299     td_u32 ret = at_plt_cmd_strtoaddr((const char *)args->mac_addr, mac_addr, WIFI_MAC_LEN);
300     if (ret != EXT_ERR_SUCCESS) {
301         return AT_RET_SYNTAX_ERROR;
302     }
303     if ((mac_addr[0] & 0x1) == 0x1) {
304         osal_printk("set mac error: multicast mac addr not aviable!!\r\n");
305         return AT_RET_SYNTAX_ERROR;
306     }
307     switch (args->mac_type) {
308         case MAC_ADDR_EFUSE:
309             ret = efuse_write_mac(mac_addr, WIFI_MAC_LEN);
310             if (ret != ERRCODE_SUCC) {
311                 osal_printk("SET EFUSE MAC ERROR, ret : 0x%x\r\n", ret);
312                 return AT_RET_CMD_PARA_ERROR;
313             }
314             break;
315         case SLE_MAC_ADDR:
316             ret = efuse_write_sle_mac(mac_addr, WIFI_MAC_LEN);
317             if (ret != ERRCODE_SUCC) {
318                 osal_printk("SET SLE EFUSE MAC ERROR, ret : 0x%x\r\n", ret);
319                 return AT_RET_CMD_PARA_ERROR;
320             }
321             break;
322         case MAC_ADDR_NV:
323 #if defined(CONFIG_MIDDLEWARE_SUPPORT_NV)
324             ret = uapi_nv_write(NV_ID_SYSTEM_FACTORY_MAC, mac_addr, WIFI_MAC_LEN);
325             if (ret != ERRCODE_SUCC) {
326                 osal_printk("SET NV MAC ERROR, ret : 0x%x\r\n", ret);
327                 return AT_RET_CMD_PARA_ERROR;
328             }
329 #else
330             return AT_RET_CMD_PARA_ERROR;
331 #endif
332             break;
333         default:
334             return AT_RET_CMD_PARA_ERROR;
335             break;
336     }
337 
338     osal_printk("OK\r\n");
339     return AT_RET_OK;
340 }
341 
342 /*****************************************************************************
343  功能描述  :获取efuse mac地址
344 *****************************************************************************/
get_efuse_mac_addr(void)345 at_ret_t get_efuse_mac_addr(void)
346 {
347     td_uchar mac_addr[WIFI_MAC_LEN] = {0};
348     td_uchar null_mac_addr[WIFI_MAC_LEN] = {0};
349     td_uchar efuse_left_count = 0;
350     errcode_t ret;
351 
352 #if defined(CONFIG_MIDDLEWARE_SUPPORT_NV)
353     uint16_t nv_mac_length;
354     ret = uapi_nv_read(NV_ID_SYSTEM_FACTORY_MAC, WIFI_MAC_LEN, &nv_mac_length, mac_addr);
355     if (ret != ERRCODE_SUCC || nv_mac_length != WIFI_MAC_LEN) {
356         osal_printk("GET NV MAC ERROR, ret : 0x%x\r\n", ret);
357     }
358     osal_printk("+EFUSEMAC: NV MAC " EXT_AT_MACSTR "\r\n", ext_at_mac2str(mac_addr));
359 #endif
360     ret = efuse_read_mac(mac_addr, WIFI_MAC_LEN, &efuse_left_count);
361     if (ret == ERRCODE_SUCC) {
362         osal_printk("+EFUSEMAC: EFUSE MAC " EXT_AT_MACSTR "\r\n", ext_at_mac2str(mac_addr));
363     } else {
364         osal_printk("+EFUSEMAC: EFUSE MAC " EXT_AT_MACSTR "\r\n", ext_at_mac2str(null_mac_addr));
365     }
366     osal_printk("+EFUSEMAC: Efuse mac chance(s) left: %d times.\r\n", efuse_left_count);
367 
368     ret = efuse_read_sle_mac(mac_addr, WIFI_MAC_LEN);
369     if (ret == ERRCODE_SUCC) {
370         osal_printk("+EFUSEMAC: EFUSE SLE MAC " EXT_AT_MACSTR "\r\n", ext_at_mac2str(mac_addr));
371     } else {
372         osal_printk("+EFUSEMAC: EFUSE SLE MAC " EXT_AT_MACSTR "\r\n", ext_at_mac2str(null_mac_addr));
373     }
374     osal_printk("OK\r\n");
375 
376     return AT_RET_OK;
377 }
378 
379 #define BOOT_PORTING_RESET_REG      0x40002110
380 #define BOOT_PORTING_RESET_VALUE    0x4
381 
plt_reboot(void)382 at_ret_t plt_reboot(void)
383 {
384     hal_reboot_chip();
385     return AT_RET_OK;
386 }
387 
at_query_ver_cmd(void)388 at_ret_t at_query_ver_cmd(void)
389 {
390     print_version();
391     return AT_RET_OK;
392 }
393 
at_query_tsensor_temp(void)394 at_ret_t at_query_tsensor_temp(void)
395 {
396 #ifdef CONFIG_DRIVER_SUPPORT_TSENSOR
397     td_u32 ret;
398     td_u32 i;
399     td_s8 temp = 0;
400 
401     for (i = 0; i < 3; i++) { /* loop 3 times */
402         ret = uapi_tsensor_get_current_temp(&temp);
403         if (ret == EXT_ERR_SUCCESS) {
404             break;
405         }
406     }
407 
408     if (ret != EXT_ERR_SUCCESS) {
409         osal_printk("+RDTEMP:ret0x%x.\r\n", ret);
410         return ret;
411     }
412 
413     osal_printk("+RDTEMP:%d\r\n", temp);
414 #endif
415     return AT_RET_OK;
416 }
417 
418 #ifdef _PRE_WLAN_FEATURE_MFG_TEST
get_rf_cmu_pll_param(const td_s16 * high_temp,const td_s16 * low_temp,const td_s16 * compesation)419 static td_u32 get_rf_cmu_pll_param(const td_s16 *high_temp, const td_s16 *low_temp, const td_s16 *compesation)
420 {
421     unused(high_temp);
422     unused(low_temp);
423     unused(compesation);
424     cmu_xo_trim_temp_comp_print();
425     return EXT_ERR_SUCCESS;
426 }
427 #endif
428 
at_query_xtal_compesation(void)429 at_ret_t at_query_xtal_compesation(void)
430 {
431 #ifdef _PRE_WLAN_FEATURE_MFG_TEST
432     td_u32 ret;
433     td_s16 high_temp_threshold = 0;
434     td_s16 low_temp_threshold = 0;
435     td_s16 pll_compesation = 0;
436 
437     ret = get_rf_cmu_pll_param(&high_temp_threshold, &low_temp_threshold, &pll_compesation);
438     if (ret != EXT_ERR_SUCCESS) {
439         return ret;
440     }
441 
442     osal_printk("+XTALCOM:%d,%d,%d\r\n", high_temp_threshold, low_temp_threshold, pll_compesation);
443 #endif
444 
445     return AT_RET_OK;
446 }
447 
at_factory_erase(void)448 at_ret_t at_factory_erase(void)
449 {
450 #ifdef CONFIG_MIDDLEWARE_SUPPORT_FTM
451     errcode_t ret;
452     mfg_factory_config_t factory_mode_cfg;
453 
454     memset_s(&factory_mode_cfg, sizeof(factory_mode_cfg), 0, sizeof(factory_mode_cfg));
455     ret = mfg_flash_read((uint8_t *)(&factory_mode_cfg), sizeof(mfg_factory_config_t));
456     if (ret != EXT_ERR_SUCCESS) {
457         return ret;
458     }
459     if (factory_mode_cfg.factory_mode != 0x0) {
460         osal_printk("factory mode, can not erase\r\n");
461         return AT_RET_SYNTAX_ERROR;
462     }
463     ret = mfg_flash_erase();
464     if (ret != EXT_ERR_SUCCESS) {
465         osal_printk("at_factory_erase:: uapi_flash_erase failed, ret :%x\r\n", ret);
466         return ret;
467     }
468     /* set normal mode after erase factory. inorder to let start success after reboot. */
469     factory_mode_cfg.factory_mode = 0x0;
470     factory_mode_cfg.factory_valid = MFG_FACTORY_INVALID;
471     ret = mfg_flash_write((const uint8_t *)(&factory_mode_cfg), sizeof(factory_mode_cfg));
472     if (ret != EXT_ERR_SUCCESS) {
473         return ret;
474     }
475     osal_printk("+FTMERASE:erase addr:0x%x, size:0x%x OK.\r\n", factory_mode_cfg.factory_addr_start,
476         factory_mode_cfg.factory_size);
477 #endif
478 
479     return AT_RET_OK;
480 }
481 
at_factory_mode_read(void)482 at_ret_t at_factory_mode_read(void)
483 {
484 #ifdef _PRE_WLAN_FEATURE_MFG_TEST
485     osal_printk("factory mode\r\n");
486 #else
487     osal_printk("non_factory mode\r\n");
488 #endif
489     return AT_RET_OK;
490 }
491 
492 #ifdef CONFIG_MIDDLEWARE_SUPPORT_FTM
493 
at_setup_factory_mode_switch(td_s32 argc,const factory_mode_args_t * args)494 static td_u32 at_setup_factory_mode_switch(td_s32 argc, const factory_mode_args_t *args)
495 {
496     errcode_t ret;
497     mfg_factory_config_t factory_mode_cfg;
498     mfg_region_config_t img_info;
499     osal_printk("+FTM SWITCH: start\r\n");
500 
501     if (argc != 1) {
502         return AT_RET_SYNTAX_ERROR;
503     }
504 
505     /* switch_mode:0 normal_mode;  switch_mode:1 factory_test_mode */
506     td_u8 switch_mode = (td_u8)(args->para1);
507     if (switch_mode != 0x0 && switch_mode != 0x1) {
508         return AT_RET_SYNTAX_ERROR;
509     }
510 
511     memset_s(&factory_mode_cfg, sizeof(factory_mode_cfg), 0, sizeof(factory_mode_cfg));
512     memset_s(&img_info, sizeof(img_info), 0, sizeof(img_info));
513     ret = mfg_get_region_config(&img_info);
514     if (ret != ERRCODE_SUCC) {
515         return ret;
516     }
517 
518     ret = mfg_flash_read((uint8_t *)(&factory_mode_cfg), sizeof(mfg_factory_config_t));
519     if (ret != ERRCODE_SUCC) {
520         osal_printk("at_setup_factory_mode_switch:: read failed, ret :%x ", ret);
521         return ERRCODE_FAIL;
522     }
523 
524     ret = mfg_factory_mode_switch(img_info, switch_mode, &factory_mode_cfg);
525     if (ret != ERRCODE_SUCC) {
526         osal_printk("at_setup_factory_mode_switch:: mfg_factory_mode_switch failed, ret :%x ", ret);
527         return ERRCODE_FAIL;
528     }
529 
530     ret = mfg_flash_write((const uint8_t *)(&factory_mode_cfg), sizeof(factory_mode_cfg));
531     if (ret != ERRCODE_SUCC) {
532         osal_printk("ftm config init write failed, ret :%x ", ret);
533         return ERRCODE_FAIL;
534     }
535     osal_printk("FTM SWTICH:0x%x, size:0x%x OK.\r\n", factory_mode_cfg.factory_addr_switch,
536         factory_mode_cfg.factory_switch_size);
537     return AT_RET_OK;
538 }
539 #endif
540 
at_factory_mode_switch(const factory_mode_args_t * args)541 at_ret_t at_factory_mode_switch(const factory_mode_args_t *args)
542 {
543 #ifdef CONFIG_MIDDLEWARE_SUPPORT_FTM
544     td_s32 argc = at_plt_convert_bin_to_dec((td_s32)args->para_map);
545     if (at_setup_factory_mode_switch(argc, args) != AT_RET_OK) {
546         return AT_RET_SYNTAX_ERROR;
547     }
548 #else
549     unused(args);
550 #endif
551 
552     return AT_RET_OK;
553 }
554 
555 #ifdef _PRE_WLAN_FEATURE_MFG_TEST
556 // start of at cmd: uart log level
557 
at_setup_loglevel_cmd(td_s32 argc,const loglevel_args_t * args)558 static td_u32 at_setup_loglevel_cmd(td_s32 argc, const loglevel_args_t *args)
559 {
560 #ifdef CONFIG_DFX_SUPPORT_PRINT
561     td_u8 log_level;
562 
563     if (argc == 0) { /* argc 0 */
564         osal_printk("+LOGL:%u\r\n", dfx_print_get_level());
565         return AT_RET_OK;
566     }
567     if (argc != 1) { /* argc 1 */
568         return AT_RET_SYNTAX_ERROR;
569     }
570 
571     log_level = (td_u8)(args->para1);
572     if (log_level >= DFX_PRINT_LEVEL_MAX) {
573         return AT_RET_SYNTAX_ERROR;
574     }
575 
576     dfx_print_set_level(log_level);
577     osal_printk("+LOGL:%d\r\n", log_level);
578 #else
579     unused(argc);
580     unused(args);
581 #endif
582     return AT_RET_OK;
583 }
584 #endif
585 
at_get_log_level(void)586 at_ret_t at_get_log_level(void)
587 {
588 #ifdef _PRE_WLAN_FEATURE_MFG_TEST
589     if (at_setup_loglevel_cmd(0, NULL) != AT_RET_OK) {
590         return AT_RET_SYNTAX_ERROR;
591     }
592 #endif
593     return AT_RET_OK;
594 }
595 
at_set_log_level(const loglevel_args_t * args)596 at_ret_t at_set_log_level(const loglevel_args_t *args)
597 {
598 #ifdef _PRE_WLAN_FEATURE_MFG_TEST
599     td_s32 argc = at_plt_convert_bin_to_dec((td_s32)args->para_map);
600     if (at_setup_loglevel_cmd(argc, args) != AT_RET_OK) {
601         return AT_RET_SYNTAX_ERROR;
602     }
603 #else
604     unused(args);
605 #endif
606 
607     return AT_RET_OK;
608 }
609 
610 #ifdef _PRE_WLAN_FEATURE_MFG_TEST
611 #define UAPI_MAX_SLEEP_MODE 2
612 
613 td_u8 g_sleep_mode;
614 
uapi_set_sleep_mode(td_u8 sleep_mode)615 static errcode_t uapi_set_sleep_mode(td_u8 sleep_mode)
616 {
617     g_sleep_mode = sleep_mode;
618 #if defined(ENABLE_LOW_POWER) && (ENABLE_LOW_POWER == YES)
619     bool open_pm = (g_sleep_mode == 0) ? false : true;
620     idle_set_open_pm(open_pm);
621 #endif
622     return ERRCODE_SUCC;
623 }
624 
uapi_get_sleep_mode(td_void)625 static td_u8 uapi_get_sleep_mode(td_void)
626 {
627     return g_sleep_mode;
628 }
629 
at_setup_sleepmode_cmd(td_s32 argc,const sleepmode_args_t * args)630 static td_u32 at_setup_sleepmode_cmd(td_s32 argc, const sleepmode_args_t *args)
631 {
632     td_u8 sleep_mode;
633     td_u32 ret;
634 
635     if (argc != 1) { /* argc 2 */
636         osal_printk("+SLP:%d\r\n", uapi_get_sleep_mode());
637         return AT_RET_OK;
638     }
639 
640     sleep_mode = (td_u8)(args->para1);
641     if (sleep_mode > UAPI_MAX_SLEEP_MODE) {
642         return AT_RET_SYNTAX_ERROR;
643     }
644 
645     ret = uapi_set_sleep_mode(sleep_mode);
646     if (ret != EXT_ERR_SUCCESS) {
647         return AT_RET_SYNTAX_ERROR;
648     }
649     osal_printk("+SLP:%d\r\n", sleep_mode);
650 
651     return AT_RET_OK;
652 }
653 #endif
654 
at_get_sleep_mode(void)655 at_ret_t at_get_sleep_mode(void)
656 {
657 #ifdef _PRE_WLAN_FEATURE_MFG_TEST
658     if (at_setup_sleepmode_cmd(0, NULL) != AT_RET_OK) {
659         return AT_RET_SYNTAX_ERROR;
660     }
661 #endif
662     return AT_RET_OK;
663 }
664 
at_set_sleep_mode(const sleepmode_args_t * args)665 at_ret_t at_set_sleep_mode(const sleepmode_args_t *args)
666 {
667 #ifdef _PRE_WLAN_FEATURE_MFG_TEST
668     td_s32 argc = at_plt_convert_bin_to_dec((td_s32)args->para_map);
669     if (at_setup_sleepmode_cmd(argc, args) != AT_RET_OK) {
670         return AT_RET_SYNTAX_ERROR;
671     }
672 #else
673     unused(args);
674 #endif
675 
676     return AT_RET_OK;
677 }
678 
679 #define UAPI_UART_PORT_MAX 2
680 #define UAPI_UART_PORT_NUM 3
681 
at_set_uart_port(const uartport_args_t * args)682 at_ret_t at_set_uart_port(const uartport_args_t *args)
683 {
684 #ifdef _PRE_WLAN_FEATURE_MFG_TEST
685     td_s32 argc = at_plt_convert_bin_to_dec((td_s32)args->para_map);
686 
687     osal_printk("+SETUART :%d\r\n", argc);
688     if (argc != UAPI_UART_PORT_NUM) { /* argc 3 */
689         return AT_RET_SYNTAX_ERROR;
690     }
691 
692     if (args->para1 > UAPI_UART_PORT_MAX) {
693         return AT_RET_SYNTAX_ERROR;
694     }
695 
696     if (args->para2 > UAPI_UART_PORT_MAX) {
697         return AT_RET_SYNTAX_ERROR;
698     }
699 
700     if (args->para3 > UAPI_UART_PORT_MAX) {
701         return AT_RET_SYNTAX_ERROR;
702     }
703     osal_printk("+SETUART:%d,%d,%d\r\n", args->para1, args->para2, args->para3);
704 #else
705     unused(args);
706 #endif
707 
708     return AT_RET_OK;
709 }
710 
711 // gpio ops
712 #ifdef CONFIG_DRIVER_SUPPORT_GPIO
at_setup_gpiodir_cmd(td_s32 argc,const gpiodir_args_t * args)713 static td_u32 at_setup_gpiodir_cmd(td_s32 argc, const gpiodir_args_t *args)
714 {
715     pin_t io_num;
716     gpio_direction_t io_dir;
717     pin_mode_t io_mode;
718     td_u32 ret;
719 
720     if (argc != 2) { /* argc 2 */
721         return AT_RET_SYNTAX_ERROR;
722     }
723 
724     io_num = (pin_t)(args->para1);
725     if (io_num > PIN_NONE) {
726         osal_printk("+RDGPIO:invalid io,%d\r\n", io_num);
727         return AT_RET_SYNTAX_ERROR;
728     }
729 
730     io_mode = uapi_pin_get_mode(io_num);
731     if (io_mode != 0) {
732         return ERRCODE_PIN_INVALID_PARAMETER;
733     }
734 
735     io_dir = (gpio_direction_t)(args->para2);
736     if (io_dir > GPIO_DIRECTION_OUTPUT) {
737         return AT_RET_SYNTAX_ERROR;
738     }
739 
740     ret = uapi_gpio_set_dir((pin_t)io_num, io_dir);
741     if (ret != EXT_ERR_SUCCESS) {
742         return AT_RET_SYNTAX_ERROR;
743     }
744     osal_printk("+GPIODIR:%d,%d\r\n", io_num, io_dir);
745 
746     return AT_RET_OK;
747 }
748 #endif
749 
at_set_gpio_dir(const gpiodir_args_t * args)750 at_ret_t at_set_gpio_dir(const gpiodir_args_t *args)
751 {
752 #ifdef CONFIG_DRIVER_SUPPORT_GPIO
753     td_s32 argc = at_plt_convert_bin_to_dec((td_s32)args->para_map);
754     if (at_setup_gpiodir_cmd(argc, args) != AT_RET_OK) {
755         return AT_RET_SYNTAX_ERROR;
756     }
757 #else
758     unused(args);
759 #endif
760 
761     return AT_RET_OK;
762 }
763 
764 #ifdef CONFIG_DRIVER_SUPPORT_GPIO
at_setup_iogetmode_cmd(td_s32 argc,const getiomode_args_t * args)765 static td_u32 at_setup_iogetmode_cmd(td_s32 argc, const getiomode_args_t *args)
766 {
767     pin_t io_num;
768     pin_mode_t io_mode;
769     pin_pull_t io_pull_stat; /* record io_pull */
770     pin_drive_strength_t io_capalibity; /* record io_driver_strength */
771 
772     if (argc != 1) {
773         return AT_RET_SYNTAX_ERROR;
774     }
775 
776     io_num = (pin_t)(args->para1);
777     if (io_num > PIN_NONE) {
778         osal_printk("+GETIOMODE:invalid io,%d\r\n", io_num);
779         return AT_RET_SYNTAX_ERROR;
780     }
781 
782     io_mode = uapi_pin_get_mode(io_num);
783     if (io_mode >= PIN_MODE_MAX) {
784         return AT_RET_SYNTAX_ERROR;
785     }
786 
787     io_pull_stat = uapi_pin_get_pull(io_num);
788     if (io_pull_stat > PIN_PULL_MAX) { /* HAL_PIO_PULL_MAX */
789         return AT_RET_SYNTAX_ERROR;
790     }
791 
792     io_capalibity = uapi_pin_get_ds(io_num);
793     if (io_capalibity > PIN_DS_MAX) {
794         return AT_RET_SYNTAX_ERROR;
795     }
796 
797     osal_printk("+GETIOMODE:%d,%d,%d,%d\r\n", io_num, io_mode, io_pull_stat, io_capalibity);
798     return AT_RET_OK;
799 }
800 #endif
801 
at_get_iomode(const getiomode_args_t * args)802 at_ret_t at_get_iomode(const getiomode_args_t *args)
803 {
804 #ifdef CONFIG_DRIVER_SUPPORT_GPIO
805     td_s32 argc = at_plt_convert_bin_to_dec((td_s32)args->para_map);
806     if (at_setup_iogetmode_cmd(argc, args) != AT_RET_OK) {
807         return AT_RET_SYNTAX_ERROR;
808     }
809 #else
810     unused(args);
811 #endif
812 
813     return AT_RET_OK;
814 }
815 
816 #ifdef CONFIG_DRIVER_SUPPORT_GPIO
at_setup_iosetmode_cmd(td_s32 argc,const setiomode_args_t * args)817 static td_u32 at_setup_iosetmode_cmd(td_s32 argc, const setiomode_args_t *args)
818 {
819     pin_t io_num;
820     pin_mode_t io_mode;
821     pin_pull_t io_pull_stat; /* record io_pull */
822     pin_drive_strength_t io_capalibity; /* record io_driver_strength */
823     td_u32 ret;
824 
825     if (argc < 3 || argc > 4) { /* argc 3/4 */
826         return AT_RET_SYNTAX_ERROR;
827     }
828 
829     io_num = (pin_t)(args->para1);
830     if (io_num > PIN_NONE) {
831         return AT_RET_SYNTAX_ERROR;
832     }
833 
834     io_mode = (pin_mode_t)(args->para2);
835     if (io_mode >= PIN_MODE_MAX) {
836         return AT_RET_SYNTAX_ERROR;
837     }
838 
839     io_pull_stat = (pin_pull_t)(args->para3); /* argc 2 */
840     if (io_pull_stat >= PIN_PULL_MAX) { /* HAL_PIO_PULL_MAX */
841         return AT_RET_SYNTAX_ERROR;
842     }
843 
844     if (argc == 3) { /* argc 3 */
845         io_capalibity = PIN_DS_MAX - 1;
846     } else {
847         io_capalibity = (pin_drive_strength_t)(args->para4); /* argc 3 */
848     }
849 
850     ret = uapi_pin_set_mode(io_num, io_mode);
851     if (ret != EXT_ERR_SUCCESS) {
852         return AT_RET_CMD_ATTR_NOT_ALLOW;
853     }
854 
855     ret = uapi_pin_get_pull(io_num);
856     if (ret != PIN_PULL_MAX) {
857         ret = uapi_pin_set_pull(io_num, io_pull_stat);
858         if (ret != EXT_ERR_SUCCESS) {
859             return AT_RET_CMD_ATTR_NOT_ALLOW;
860         }
861     }
862 
863     ret = uapi_pin_get_ds(io_num);
864     if (ret != PIN_DS_MAX) {
865         ret = uapi_pin_set_ds(io_num, io_capalibity);
866         if (ret != EXT_ERR_SUCCESS) {
867             return AT_RET_CMD_ATTR_NOT_ALLOW;
868         }
869     }
870 
871     osal_printk("+SETIOMODE:%d,%d,%d,%d\r\n", io_num, io_mode, io_pull_stat, io_capalibity);
872     return AT_RET_OK;
873 }
874 #endif
875 
at_set_iomode(const setiomode_args_t * args)876 at_ret_t at_set_iomode(const setiomode_args_t *args)
877 {
878 #ifdef CONFIG_DRIVER_SUPPORT_GPIO
879     td_s32 argc = at_plt_convert_bin_to_dec((td_s32)args->para_map);
880     if (at_setup_iosetmode_cmd(argc, args) != AT_RET_OK) {
881         return AT_RET_SYNTAX_ERROR;
882     }
883 #else
884     unused(args);
885 #endif
886 
887     return AT_RET_OK;
888 }
889 
890 #ifdef CONFIG_DRIVER_SUPPORT_GPIO
at_setup_gpiowt_cmd(td_s32 argc,const wrgpio_args_t * args)891 static td_u32 at_setup_gpiowt_cmd(td_s32 argc, const wrgpio_args_t *args)
892 {
893     pin_t io_num;
894     gpio_level_t io_level;
895     pin_mode_t io_mode;
896     gpio_direction_t io_dir = GPIO_DIRECTION_OUTPUT;
897     td_u32 ret;
898 
899     if (argc != 2) { /* argc 2 */
900         return AT_RET_SYNTAX_ERROR;
901     }
902 
903     io_num = (pin_t)(args->para1);
904     if (io_num > PIN_NONE) {
905         return AT_RET_SYNTAX_ERROR;
906     }
907 
908     io_level = (gpio_level_t)(args->para2);
909     if (io_level > GPIO_LEVEL_HIGH) {
910         return AT_RET_SYNTAX_ERROR;
911     }
912 
913     io_mode = uapi_pin_get_mode(io_num);
914     if (io_mode >= PIN_MODE_MAX) {
915         return AT_RET_SYNTAX_ERROR;
916     }
917 
918     io_dir = uapi_gpio_get_dir(io_num);
919     if (io_dir != GPIO_DIRECTION_OUTPUT) {
920         return AT_RET_SYNTAX_ERROR;
921     }
922 
923     ret = uapi_gpio_set_val((pin_t)io_num, io_level);
924     if (ret != EXT_ERR_SUCCESS) {
925         return AT_RET_SYNTAX_ERROR;
926     }
927     osal_printk("+WRGPIO:%d,%d,%d\r\n", io_num, io_dir, io_level);
928 
929     return EXT_ERR_SUCCESS;
930 }
931 #endif
932 
at_wrgpio(const wrgpio_args_t * args)933 at_ret_t at_wrgpio(const wrgpio_args_t *args)
934 {
935 #ifdef CONFIG_DRIVER_SUPPORT_GPIO
936     td_s32 argc = at_plt_convert_bin_to_dec((td_s32)args->para_map);
937     if (at_setup_gpiowt_cmd(argc, args) != AT_RET_OK) {
938         return AT_RET_SYNTAX_ERROR;
939     }
940 #else
941     unused(args);
942 #endif
943 
944     return AT_RET_OK;
945 }
946 
947 #ifdef CONFIG_DRIVER_SUPPORT_GPIO
at_setup_gpiord_cmd(td_s32 argc,const rdgpio_args_t * args)948 static td_u32 at_setup_gpiord_cmd(td_s32 argc, const rdgpio_args_t *args)
949 {
950     pin_t io_num;
951     gpio_level_t io_level;
952     pin_mode_t io_mode;
953     gpio_direction_t io_dir;
954 
955     if (argc != 1) {
956         return AT_RET_SYNTAX_ERROR;
957     }
958 
959     io_num = (pin_t)(args->para1);
960     if (io_num > PIN_NONE) {
961         return AT_RET_SYNTAX_ERROR;
962     }
963 
964     io_mode = uapi_pin_get_mode(io_num);
965     if (io_mode >= PIN_MODE_MAX) {
966         return AT_RET_SYNTAX_ERROR;
967     }
968 
969     io_dir = uapi_gpio_get_dir(io_num);
970 
971     io_level = uapi_gpio_get_val((pin_t)io_num);
972 
973     osal_printk("+RDGPIO:%d,%d,%d\r\n", io_num, io_dir, io_level);
974 
975     return EXT_ERR_SUCCESS;
976 }
977 #endif
978 
at_rdgpio(const rdgpio_args_t * args)979 at_ret_t at_rdgpio(const rdgpio_args_t *args)
980 {
981 #ifdef CONFIG_DRIVER_SUPPORT_GPIO
982     td_s32 argc = at_plt_convert_bin_to_dec((td_s32)args->para_map);
983     if (at_setup_gpiord_cmd(argc, args) != AT_RET_OK) {
984         return AT_RET_SYNTAX_ERROR;
985     }
986 #else
987     unused(args);
988 #endif
989 
990     return AT_RET_OK;
991 }
992 
cmd_set_pm(const pm_args_t * args)993 at_ret_t cmd_set_pm(const pm_args_t *args)
994 {
995     unused(args);
996 #if defined(ENABLE_LOW_POWER) && (ENABLE_LOW_POWER == YES)
997     bool open_pm = (args->para1 == 0) ? false : true;
998     idle_set_open_pm(open_pm);
999 #endif
1000     return AT_RET_OK;
1001 }
1002 
1003 // at help dump cmd lists
at_help(void)1004 at_ret_t at_help(void)
1005 {
1006 #ifdef _PRE_WLAN_FEATURE_MFG_TEST
1007     td_u32 i;
1008     td_u32 cnt = at_cmd_get_entry_total();
1009     td_u32 total = 0;
1010     at_cmd_entry_t *cmd_entry = NULL;
1011     at_cmd_entry_t **cmd_tbl = (at_cmd_entry_t **)malloc(sizeof(at_cmd_entry_t *) * cnt);
1012 
1013     if (cmd_tbl == TD_NULL) {
1014         return AT_RET_MALLOC_ERROR;
1015     }
1016     if (at_cmd_get_all_entrys((const at_cmd_entry_t **)cmd_tbl, cnt) != cnt) {
1017         free(cmd_tbl);
1018         return AT_RET_MEM_API_ERROR;
1019     }
1020     osal_printk("+HELP:cmd cnt:%d\r\n", cnt);
1021     for (i = 0; i < cnt; ++i) {
1022         cmd_entry = (at_cmd_entry_t *)cmd_tbl[i];
1023         osal_printk("AT+%-28s ", cmd_entry->name);
1024         total++;
1025         if (total % 3 == 0) {  /* 3 entrys per newline */
1026             osal_printk("\r\n");
1027         }
1028     }
1029     free(cmd_tbl);
1030 #endif
1031     return AT_RET_OK;
1032 }
1033 
1034 // dump last system crash info
at_get_dump(void)1035 at_ret_t at_get_dump(void)
1036 {
1037 #ifdef CONFIG_SUPPORT_CRASHINFO_SAVE_TO_FLASH
1038     bool hascrashinfo = crashinfo_status_get();
1039     if (hascrashinfo == false) {
1040         osal_printk("No crash dump found!\r\n");
1041         return AT_RET_OK;
1042     }
1043     crashinfo_dump();
1044 #else
1045     osal_printk("No crash dump found!\r\n");
1046 #endif
1047     return AT_RET_OK;
1048 }
1049 // reboot system
at_exe_reset_cmd(void)1050 at_ret_t at_exe_reset_cmd(void)
1051 {
1052     uapi_watchdog_disable();
1053     /* Wait for 3000 us until the AT print is complete. */
1054     // call LOS_TaskDelay to wait
1055     plt_reboot();
1056     return AT_RET_OK;
1057 }
1058 
at_set_reset_cmd(const reboot_args_t * args)1059 at_ret_t at_set_reset_cmd(const reboot_args_t *args)
1060 {
1061     UINT32 delay;
1062 
1063     uapi_watchdog_disable();
1064 
1065     delay = strtoul(args->delay_time,NULL, 10);
1066     osal_printk("OK %d \r\n", delay);
1067     LOS_TaskDelay(delay);
1068 
1069     plt_reboot();
1070     return AT_RET_OK;
1071 }
1072 
at_copy_tm(struct tm * dest_tm,const struct tm * src_tm)1073 static void at_copy_tm(struct tm *dest_tm, const struct tm *src_tm)
1074 {
1075     if (src_tm == NULL) {
1076         (void)memset_s(dest_tm, sizeof(struct tm), 0, sizeof(struct tm));
1077     } else {
1078         dest_tm->tm_sec = src_tm->tm_sec;
1079         dest_tm->tm_min = src_tm->tm_min;
1080         dest_tm->tm_hour = src_tm->tm_hour;
1081         dest_tm->tm_mday = src_tm->tm_mday;
1082         dest_tm->tm_mon = src_tm->tm_mon;
1083         dest_tm->tm_year = src_tm->tm_year;
1084         dest_tm->tm_wday = src_tm->tm_wday;
1085         dest_tm->tm_yday = src_tm->tm_yday;
1086         dest_tm->tm_isdst = src_tm->tm_isdst;
1087         dest_tm->tm_gmtoff = src_tm->tm_gmtoff;
1088         dest_tm->tm_zone = src_tm->tm_zone;
1089     }
1090 }
1091 
at_str_to_tm(const char * str,struct tm * tm)1092 static at_ret_t at_str_to_tm(const char *str, struct tm *tm)
1093 {
1094     CHAR *ret = NULL;
1095     size_t para_len = strlen(str);
1096     if (para_len == 8) { /* 8:Time format string length, such as hh:mm:ss or yyyymmdd */
1097         if (str[2] == ':') { /* 2:Index of Eigenvalues */
1098             ret = strptime(str, "%H:%M:%S", tm);
1099         } else {
1100             ret = strptime(str, "%Y%m%d", tm);
1101         }
1102     } else if (para_len == 10) { /* 10:Time format string length,such as yyyy/mm/dd  */
1103         ret = strptime(str, "%Y/%m/%d", tm);
1104     } else if (para_len == 5) { /* 5:Time format string length,such as hh:mm or mm/dd */
1105         if (str[2] == ':') { /* 2:Index of Eigenvalues */
1106             ret = strptime(str, "%H:%M", tm);
1107         } else if (str[2] == '/') { /* 2:Index of Eigenvalues */
1108             ret = strptime(str, "%m/%d", tm);
1109         }
1110     } else if (para_len == 7) { /* 7:Time format string length,such as yyyy/mm */
1111         if (str[4] == '/') { /* 4:Index of Eigenvalues */
1112             ret = strptime(str, "%Y/%m", tm);
1113         }
1114     }
1115 
1116     if (tm->tm_year < 70) { /* 70:the year is starting in 1970,tm_year must be greater than 70 */
1117         osal_printk("\nUsage: date -s set system time range from 1970.\n");
1118         return AT_RET_SYNTAX_ERROR;
1119     }
1120 
1121     if (tm->tm_mday > g_mon_lengths[(INT32)leap_year(tm->tm_year + DATE_BASE_YEAR)][tm->tm_mon]) {
1122         return AT_RET_SYNTAX_ERROR;
1123     }
1124 
1125     if ((tm->tm_sec < 0) || (tm->tm_sec > 59)) { /* Seconds (0-59), leap seconds shall not be used when set time. */
1126         return AT_RET_SYNTAX_ERROR;
1127     }
1128     return (ret == NULL) ? AT_RET_SYNTAX_ERROR : AT_RET_OK;
1129 }
1130 
at_date_cmd(void)1131 at_ret_t at_date_cmd(void)
1132 {
1133     struct timeval64 now_time = {0};
1134 
1135     if (gettimeofday64(&now_time, NULL) != 0) {
1136         return AT_RET_SYNTAX_ERROR;
1137     }
1138     osal_printk("%s\n", ctime64(&now_time.tv_sec));
1139 
1140     return AT_RET_OK;
1141 }
1142 
at_date_set_cmd(const date_args_t * args)1143 at_ret_t at_date_set_cmd(const date_args_t *args)
1144 {
1145     struct tm tm = {0};
1146     struct timeval64 now_time = {0};
1147     struct timeval64 set_time = {0};
1148 
1149     if (gettimeofday64(&now_time, NULL) != 0) {
1150         osal_printk("set_time failed...\n");
1151         return AT_RET_SYNTAX_ERROR;
1152     }
1153 
1154     set_time.tv_usec = now_time.tv_usec;
1155     at_copy_tm(&tm, localtime64(&now_time.tv_sec));
1156 
1157     if (at_str_to_tm(args->para1, &tm) != AT_RET_OK) {
1158         osal_printk("at_str_to_tm failed...\n");
1159         return AT_RET_SYNTAX_ERROR;
1160     }
1161 
1162     set_time.tv_sec = mktime64(&tm);
1163     if (set_time.tv_sec == -1) {
1164         osal_printk("mktime failed...\n");
1165         return AT_RET_SYNTAX_ERROR;
1166     }
1167 
1168     if (settimeofday64(&set_time, NULL) != 0) {
1169         osal_printk("settime failed...\n");
1170         return AT_RET_SYNTAX_ERROR;
1171     }
1172 
1173     at_date_cmd();
1174 
1175     return AT_RET_OK;
1176 }
1177 
1178 #define EFUSE_MFG_FLAG_ID_1 161
1179 #define EFUSE_MFG_FLAG_ID_2 179
1180 #define EFUSE_MFG_FLAG_ID_3 197
1181 #define EFUSE_MFG_FLAG_BIT_POS 7
1182 #define EFUSE_GROUP_MAX 3
cmd_write_mfg_flag(void)1183 at_ret_t cmd_write_mfg_flag(void)
1184 {
1185 #ifdef _PRE_WLAN_FEATURE_MFG_TEST
1186     td_u8 id[EFUSE_GROUP_MAX] = {EFUSE_MFG_FLAG_ID_1, EFUSE_MFG_FLAG_ID_2, EFUSE_MFG_FLAG_ID_3};
1187     td_u8 index;
1188     td_u8 value = 0;
1189     bool writable = false;
1190 
1191     for (index = 0; index < EFUSE_GROUP_MAX; ++index) {
1192         if (uapi_efuse_read_bit(&value, id[index], EFUSE_MFG_FLAG_BIT_POS) != AT_RET_OK) {
1193             return AT_RET_SYNTAX_ERROR;
1194         }
1195         if (value != 0) {
1196             continue;
1197         }
1198         if (uapi_efuse_write_bit(id[index], EFUSE_MFG_FLAG_BIT_POS) != AT_RET_OK) {
1199             return AT_RET_SYNTAX_ERROR;
1200         }
1201         writable = true;
1202         break;
1203     }
1204     if (writable == false) {
1205         osal_printk("mfg flag no remain left\r\n");
1206         return AT_RET_SYNTAX_ERROR;
1207     }
1208 #endif
1209     return AT_RET_OK;
1210 }
1211 #define DIE_ID_LENGTH 21
cmd_get_dieid(void)1212 at_ret_t cmd_get_dieid(void)
1213 {
1214 #ifdef _PRE_WLAN_FEATURE_MFG_TEST
1215     td_u32 index;
1216     td_u8 die_id[DIE_ID_LENGTH] = {0};
1217 
1218     if (uapi_efuse_read_buffer(die_id, 0, sizeof(die_id)) != AT_RET_OK) {
1219         return AT_RET_SYNTAX_ERROR;
1220     }
1221     osal_printk("OK\r\n");
1222     osal_printk("CHIP_ID: 0x%02x\r\n", die_id[0]);
1223     osal_printk("DIE_ID: 0x: ", die_id[0]);
1224     for (index = 1; index < sizeof(die_id); ++index) {
1225         osal_printk("%02x", die_id[index]);
1226     }
1227     osal_printk("OK\r\n");
1228 #endif
1229     return AT_RET_OK;
1230 }
1231 
cmd_set_customer_rsvd_efuse(const customer_rsvd_efuse_args_t * args)1232 at_ret_t cmd_set_customer_rsvd_efuse(const customer_rsvd_efuse_args_t *args)
1233 {
1234 #ifdef _PRE_WLAN_FEATURE_MFG_TEST
1235     td_s32 argc = at_plt_convert_bin_to_dec((td_s32)args->para_map);
1236     errcode_t ret;
1237     td_u8 key[CUSTOM_RESVED_EFUSE_BYTE_LEN];
1238     td_u32 len = 0;
1239     td_u8 tmp_data;
1240 
1241     if (argc != 1) {
1242         return AT_RET_SYNTAX_ERROR;
1243     }
1244     if ((args->para1[0] != '0') && (args->para1[1] != 'x')) {
1245         return AT_RET_CMD_PARA_ERROR;
1246     }
1247 
1248     len = strlen((char *)(args->para1 + 2)); /* 2:偏移2个字符 */
1249     if (len != CUSTOM_RESVED_EFUSE_BYTE_LEN * 2) { /* 2:乘2 */
1250         return AT_RET_CMD_PARA_ERROR;
1251     }
1252     memset_s(key, CUSTOM_RESVED_EFUSE_BYTE_LEN, 0, CUSTOM_RESVED_EFUSE_BYTE_LEN);
1253     at_str_to_hex((char *)(args->para1 + 2), len, key); /* 2:偏移2个字符 */
1254     for (td_u8 index = 0; index < (CUSTOM_RESVED_EFUSE_BYTE_LEN >> 1); index++) {
1255         tmp_data = key[index];
1256         key[index] = key[CUSTOM_RESVED_EFUSE_BYTE_LEN - 1 - index];
1257         key[CUSTOM_RESVED_EFUSE_BYTE_LEN - 1 - index] = tmp_data;
1258     }
1259     ret = efuse_write_customer_rsvd_efuse(key, CUSTOM_RESVED_EFUSE_BYTE_LEN);
1260     if (ret != ERRCODE_SUCC) {
1261         osal_printk("SET CUSTOMER RSVD EFUSE ERROR, ret : 0x%x\r\n", ret);
1262         return AT_RET_CMD_PARA_ERROR;
1263     }
1264     osal_printk("OK\r\n");
1265 #else
1266     unused(args);
1267 #endif
1268     return AT_RET_OK;
1269 }
1270 
cmd_get_customer_rsvd_efuse(void)1271 at_ret_t cmd_get_customer_rsvd_efuse(void)
1272 {
1273 #ifdef _PRE_WLAN_FEATURE_MFG_TEST
1274     errcode_t ret;
1275     td_u8 key[CUSTOM_RESVED_EFUSE_BYTE_LEN];
1276     td_u32 index;
1277 
1278     memset_s(key, CUSTOM_RESVED_EFUSE_BYTE_LEN, 0, CUSTOM_RESVED_EFUSE_BYTE_LEN);
1279     ret = efuse_read_item(EFUSE_CUSTOM_RESVED_ID, key, sizeof(key));
1280     if (ret != EXT_ERR_SUCCESS) {
1281         osal_printk("READ EFUSE CUSTOM RESVED ERROR, ret : 0x%x\r\n", ret);
1282         return AT_RET_SYNTAX_ERROR;
1283     }
1284     osal_printk("OK\r\n");
1285     osal_printk("RESERVED EFUSE:0x");
1286     for (index = sizeof(key); index > 0; index--) {
1287         osal_printk("%02x", key[index - 1]);
1288     }
1289     osal_printk("\r\n");
1290 #endif
1291     return AT_RET_OK;
1292 }
1293 
cmd_disable_ssi_jtag(void)1294 at_ret_t cmd_disable_ssi_jtag(void)
1295 {
1296 #ifdef _PRE_WLAN_FEATURE_MFG_TEST
1297     errcode_t ret;
1298 
1299     ret = efuse_write_jtag_ssi();
1300     if (ret != ERRCODE_SUCC) {
1301         osal_printk("SET EFUSE SSI JTAG ERROR, ret : 0x%x\r\n", ret);
1302         return AT_RET_CMD_PARA_ERROR;
1303     }
1304     osal_printk("OK\r\n");
1305 #endif
1306     return AT_RET_OK;
1307 }
1308 
cmd_get_ssi_jtag_status(void)1309 at_ret_t cmd_get_ssi_jtag_status(void)
1310 {
1311 #ifdef _PRE_WLAN_FEATURE_MFG_TEST
1312     errcode_t ret;
1313     td_u8 ssi_jtag = 0;
1314 
1315     ret = efuse_read_jtag_ssi(&ssi_jtag, sizeof(ssi_jtag));
1316     if (ret != EXT_ERR_SUCCESS) {
1317         osal_printk("READ EFUSE SSI JTAG ERROR, ret : 0x%x\r\n", ret);
1318         return AT_RET_SYNTAX_ERROR;
1319     }
1320     osal_printk("OK\r\n");
1321     osal_printk("SSI JTAG: %d\r\n", ssi_jtag);
1322 #endif
1323     return AT_RET_OK;
1324 }
1325 
cmd_set_hash_root_public_key(const pubkey_args_t * args)1326 at_ret_t cmd_set_hash_root_public_key(const pubkey_args_t *args)
1327 {
1328 #ifdef _PRE_WLAN_FEATURE_MFG_TEST
1329     errcode_t ret;
1330     td_u8 key[HASH_ROOT_PUBLIC_KEY_LEN];
1331     td_u32 len = 0;
1332 
1333     if ((args->para1[0] != '0') && (args->para1[1] != 'x')) {
1334         return AT_RET_CMD_PARA_ERROR;
1335     }
1336 
1337     len = strlen((char *)(args->para1 + 2)); /* 2:偏移2个字符 */
1338     if (len != HASH_ROOT_PUBLIC_KEY_LEN * 2) { /* 2:乘2 */
1339         return AT_RET_CMD_PARA_ERROR;
1340     }
1341     memset_s(key, sizeof(key), 0, sizeof(key));
1342     at_str_to_hex((char *)(args->para1 + 2), len, key); /* 2:偏移2个字符 */
1343     ret = efuse_write_hash_root_public_key(key, sizeof(key));
1344     if (ret != ERRCODE_SUCC) {
1345         osal_printk("SET EFUSE KEY ERROR, ret : 0x%x\r\n", ret);
1346         return AT_RET_CMD_PARA_ERROR;
1347     }
1348     osal_printk("OK\r\n");
1349 #else
1350     unused(args);
1351 #endif
1352     return AT_RET_OK;
1353 }
1354 
cmd_get_hash_root_public_key(void)1355 at_ret_t cmd_get_hash_root_public_key(void)
1356 {
1357 #ifdef _PRE_WLAN_FEATURE_MFG_TEST
1358     errcode_t ret;
1359     td_u8 key[HASH_ROOT_PUBLIC_KEY_LEN];
1360     td_u32 index;
1361 
1362     memset_s(key, sizeof(key), 0, sizeof(key));
1363     ret = efuse_read_hash_root_public_key(key, sizeof(key));
1364     if (ret != EXT_ERR_SUCCESS) {
1365         osal_printk("READ EFUSE HASH ROOT PUBLIC KEY ERROR, ret : 0x%x\r\n", ret);
1366         return AT_RET_SYNTAX_ERROR;
1367     }
1368     osal_printk("OK\r\n");
1369     osal_printk("KEY:");
1370     for (index = 0; index < sizeof(key); index++) {
1371         osal_printk("%02x", key[index]);
1372     }
1373     osal_printk("\r\n");
1374 #endif
1375     return AT_RET_OK;
1376 }
1377 
cmd_sec_verify_enable(void)1378 at_ret_t cmd_sec_verify_enable(void)
1379 {
1380 #ifdef _PRE_WLAN_FEATURE_MFG_TEST
1381     errcode_t ret;
1382 
1383     ret = efuse_write_sec_verify();
1384     if (ret != ERRCODE_SUCC) {
1385         osal_printk("SET EFUSE SEC VERIFY ERROR, ret : 0x%x\r\n", ret);
1386         return AT_RET_CMD_PARA_ERROR;
1387     }
1388     osal_printk("OK\r\n");
1389 #endif
1390     return AT_RET_OK;
1391 }
1392 
cmd_get_sec_verify_status(void)1393 at_ret_t cmd_get_sec_verify_status(void)
1394 {
1395 #ifdef _PRE_WLAN_FEATURE_MFG_TEST
1396     errcode_t ret;
1397     td_u8 sec_verify = 0;
1398 
1399     ret = efuse_read_sec_verify(&sec_verify, sizeof(sec_verify));
1400     if (ret != EXT_ERR_SUCCESS) {
1401         osal_printk("READ EFUSE SEC VERIFY ERROR, ret : 0x%x\r\n", ret);
1402         return AT_RET_SYNTAX_ERROR;
1403     }
1404     osal_printk("OK\r\n");
1405     osal_printk("SEC VERIFY: %d\r\n", sec_verify);
1406 #endif
1407     return AT_RET_OK;
1408 }
1409 
plt_flash_read(const flashread_args_t * args)1410 at_ret_t plt_flash_read(const flashread_args_t *args)
1411 {
1412 #ifdef _PRE_WLAN_FEATURE_MFG_TEST
1413     errcode_t ret;
1414     td_u8 *data = TD_NULL;
1415     td_u32 index;
1416 
1417     data = (td_u8 *)malloc(args->length);
1418     if (data == TD_NULL) {
1419         free(data);
1420         return AT_RET_SYNTAX_ERROR;
1421     }
1422     ret = plt_flash_read_data(args->addr, args->length, data);
1423     if (ret != EXT_ERR_SUCCESS) {
1424         free(data);
1425         osal_printk("plt_flash_read_data error, ret: 0x%x\r\n", ret);
1426         return AT_RET_SYNTAX_ERROR;
1427     }
1428     for (index = 0; index < (td_u32)args->length; ++index) {
1429         print_str("%x ", data[index]);
1430     }
1431     print_str("\r\n", data[index]);
1432     free(data);
1433 #else
1434     unused(args);
1435 #endif
1436     return AT_RET_OK;
1437 }
1438 
1439 #define FLASH_DATA_MAX_LENGTH 3
plt_flash_write(const flashwrite_args_t * args)1440 at_ret_t plt_flash_write(const flashwrite_args_t *args)
1441 {
1442 #ifdef _PRE_WLAN_FEATURE_MFG_TEST
1443     errcode_t ret;
1444     td_u32 len = 0;
1445     td_u32 left = 0;
1446     td_u8 *data = TD_NULL;
1447 
1448     len = strlen((char *)(args->data));
1449     if (len != (td_u32)(args->length * 2)) { /* 2:乘2 */
1450         return AT_RET_CMD_PARA_ERROR;
1451     }
1452     data = (td_u8 *)malloc(args->length);
1453     if (data == TD_NULL) {
1454         free(data);
1455         return AT_RET_SYNTAX_ERROR;
1456     }
1457     at_str_to_hex((char *)(args->data), len, data);
1458     ret = plt_flash_write_data(args->addr, args->length, data, &left);
1459     if (ret != EXT_ERR_SUCCESS) {
1460         free(data);
1461         osal_printk("plt_flash_write error, ret: 0x%x\r\n", ret);
1462         return AT_RET_SYNTAX_ERROR;
1463     }
1464     osal_printk("plt_flash_write left:%d\r\n", left);
1465     free(data);
1466 #else
1467     unused(args);
1468 #endif
1469     return AT_RET_OK;
1470 }
1471 
save_license(const license_args_t * args)1472 at_ret_t save_license(const license_args_t *args)
1473 {
1474 #ifdef _PRE_WLAN_FEATURE_MFG_TEST
1475     uint32_t value_length = 0;
1476     char *tmp = at_parse_string((char *)(args->license), &value_length);
1477     if (tmp == NULL) {
1478         return AT_RET_SYNTAX_ERROR;
1479     }
1480     partition_information_t info;
1481     errcode_t ret_val = uapi_partition_get_info(PARTITION_CUSTOMER_FACTORY, &info);
1482     if (ret_val != ERRCODE_SUCC || info.part_info.addr_info.size == 0) {
1483         return AT_RET_SYNTAX_ERROR;
1484     }
1485     ret_val = uapi_sfc_reg_erase(info.part_info.addr_info.addr, info.part_info.addr_info.size);
1486     if (ret_val != ERRCODE_SUCC) {
1487         return AT_RET_SYNTAX_ERROR;
1488     }
1489     ret_val = uapi_sfc_reg_write(info.part_info.addr_info.addr, (uint8_t *)tmp, value_length);
1490     if (ret_val != ERRCODE_SUCC) {
1491         return AT_RET_SYNTAX_ERROR;
1492     }
1493 #else
1494     unused(args);
1495 #endif
1496     return AT_RET_OK;
1497 }
1498