| /****************************************************************************** |
| * Copyright Statement: |
| * -------------------- |
| * This software is protected by Copyright and the information contained |
| * herein is confidential. The software may not be copied and the information |
| * contained herein may not be used or disclosed except with the written |
| * permission of MediaTek Inc. (C) 2020 |
| * |
| * BY OPENING THIS FILE, BUYER HEREBY UNEQUIVOCALLY ACKNOWLEDGES AND AGREES |
| * THAT THE SOFTWARE/FIRMWARE AND ITS DOCUMENTATIONS ("MEDIATEK SOFTWARE") |
| * RECEIVED FROM MEDIATEK AND/OR ITS REPRESENTATIVES ARE PROVIDED TO BUYER ON |
| * AN "AS-IS" BASIS ONLY. MEDIATEK EXPRESSLY DISCLAIMS ANY AND ALL WARRANTIES, |
| * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE IMPLIED WARRANTIES OF |
| * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE OR NONINFRINGEMENT. |
| * NEITHER DOES MEDIATEK PROVIDE ANY WARRANTY WHATSOEVER WITH RESPECT TO THE |
| * SOFTWARE OF ANY THIRD PARTY WHICH MAY BE USED BY, INCORPORATED IN, OR |
| * SUPPLIED WITH THE MEDIATEK SOFTWARE, AND BUYER AGREES TO LOOK ONLY TO SUCH |
| * THIRD PARTY FOR ANY WARRANTY CLAIM RELATING THERETO. MEDIATEK SHALL ALSO |
| * NOT BE RESPONSIBLE FOR ANY MEDIATEK SOFTWARE RELEASES MADE TO BUYER'S |
| * SPECIFICATION OR TO CONFORM TO A PARTICULAR STANDARD OR OPEN FORUM. |
| * |
| * BUYER'S SOLE AND EXCLUSIVE REMEDY AND MEDIATEK'S ENTIRE AND CUMULATIVE |
| * LIABILITY WITH RESPECT TO THE MEDIATEK SOFTWARE RELEASED HEREUNDER WILL BE, |
| * AT MEDIATEK'S OPTION, TO REVISE OR REPLACE THE MEDIATEK SOFTWARE AT ISSUE, |
| * OR REFUND ANY SOFTWARE LICENSE FEES OR SERVICE CHARGE PAID BY BUYER TO |
| * MEDIATEK FOR SUCH MEDIATEK SOFTWARE AT ISSUE. |
| * |
| * THE TRANSACTION CONTEMPLATED HEREUNDER SHALL BE CONSTRUED IN ACCORDANCE |
| * WITH THE LAWS OF THE STATE OF CALIFORNIA, USA, EXCLUDING ITS CONFLICT OF |
| * LAWS PRINCIPLES. ANY DISPUTES, CONTROVERSIES OR CLAIMS ARISING THEREOF AND |
| * RELATED THERETO SHALL BE SETTLED BY ARBITRATION IN SAN FRANCISCO, CA, UNDER |
| * THE RULES OF THE INTERNATIONAL CHAMBER OF COMMERCE (ICC). |
| * |
| *******************************************************************************/ |
| |
| /****************************************************************************** |
| * Filename: |
| * --------- |
| * mcf_cmd.c |
| * |
| * Project: |
| * -------- |
| * Colgin |
| * |
| * Description: |
| * ------------ |
| * MD Configuration Framework, opreation command, send by sAP/openWrt |
| * |
| *******************************************************************************/ |
| |
| /****************************************************************************** |
| * Includes |
| ******************************************************************************/ |
| #include <stdbool.h> |
| #include <unistd.h> |
| #include <pthread.h> |
| #include <sys/time.h> |
| #include "mipc_msg_host.h" |
| |
| /****************************************************************************** |
| * Macro |
| ******************************************************************************/ |
| #define SPECIFIC_MIPC_PORT "/dev/ttyCMIPC9" |
| |
| /****************************************************************************** |
| * Typedefs |
| ******************************************************************************/ |
| typedef enum { |
| MCF_CMD_BIN_TYPE_DEFAULT_BIN = 0, |
| MCF_CMD_BIN_TYPE_CARRIER_BIN = 1, |
| MCF_CMD_BIN_TYPE_GENERAL_CARRIER_BIN = 2, |
| MCF_CMD_BIN_TYPE_MAX |
| } mcf_cmd_bin_type_enum; |
| |
| typedef enum { |
| MCF_CMD_PATH_TYPE_OTA = 0, |
| MCF_CMD_PATH_TYPE_RUNTIME = 1, |
| MCF_CMD_PATH_TYPE_MAX |
| } mcf_cmd_path_type_enum; |
| |
| typedef enum { |
| MCF_CMD_VARIABLE_ACT_READ_OTA = 0, |
| MCF_CMD_VARIABLE_ACT_READ_OPOTA = 1, |
| MCF_CMD_VARIABLE_ACT_WRITE_OTA = 2, |
| MCF_CMD_VARIABLE_ACT_WRITE_OPOTA = 3, |
| MCF_CMD_VARIABLE_ACT_MAX |
| } mcf_cmd_variable_act_enum; |
| |
| typedef enum { |
| MCF_CMD_QUERY_VARIABLE_FORM_PATH = 0, |
| MCF_CMD_QUERY_VARIABLE_FORM_GID = 1, |
| }mcf_cmd_query_variable_form_enum; |
| |
| typedef enum { |
| MCF_CMD_IS_TRIGGER_FALSE = 0, |
| MCF_CMD_IS_TRIGGER_TRUE = 1, |
| |
| MCF_CMD_IS_APPEND_OTA = 0, |
| MCF_CMD_IS_RESET_LID = 1, |
| |
| MCF_CMD_IS_UPDATE_WITH_NO_READ_INI = 0, |
| MCF_CMD_IS_UPDATE_WITH_READ_INI = 1, |
| |
| MCF_PARA_IS_MAX = 2, |
| } mcf_para_is_enum; |
| |
| typedef struct { |
| uint8_t num; |
| char str[7]; |
| } mapping_table_t; |
| |
| typedef struct { |
| /* required parameter */ |
| uint8_t opnum; |
| uint8_t bin_type; |
| uint8_t path_folder_idx; |
| uint8_t appendOTA_resetLID; |
| /* optional parameter */ |
| uint8_t is_trigger; |
| uint8_t is_with; |
| uint8_t record_id; |
| uint8_t data_length; |
| /* internal use variable */ |
| uint8_t write_flag; |
| uint8_t real_write_length; |
| /* required parameter */ |
| uint32_t gid; |
| char* file_name; |
| char* write_value; |
| /* optional parameter */ |
| char* lid_str; |
| char* array_index; |
| /* internal use variable */ |
| uint16_t run_cmd_ret; |
| uint16_t sim_ps_id; |
| } mcf_cmd_parameter_list_t; |
| |
| /****************************************************************************** |
| * Global variables |
| ******************************************************************************/ |
| #define PARA_INT8_ERROE_MAX 0xFF |
| #define RESULT_SUCCESS 0 |
| #define WRITE_FLAG 90 |
| |
| extern char *optarg; |
| extern int optind, optopt, opterr; |
| static mipc_msg_t* msg_req_ptr = NULL; |
| static mipc_msg_t* msg_cnf_ptr = NULL; |
| static mcf_cmd_parameter_list_t mc; |
| |
| /* NOTE: read and write are same opreation code 10 */ |
| static mapping_table_t cmd_map[9] = { |
| {MIPC_SYS_MCF_OP_GET_APPLIED_FILE_PATH, "get"}, |
| {MIPC_SYS_MCF_OP_DUMP_LID_DATA, "dump"}, |
| {MIPC_SYS_MCF_OP_SET_FILE_PATH_AND_AUTO_SELECT_BIN, "set"}, |
| {MIPC_SYS_MCF_OP_UPDATE_OPOTA_FILE, "update"}, |
| {MIPC_SYS_MCF_OP_QUERY_VARIABLE_VALUE, "read"}, |
| {MIPC_SYS_MCF_OP_QUERY_VARIABLE_VALUE + WRITE_FLAG, "write"}, |
| {MIPC_SYS_MCF_OP_ASSIGN_COMBINED_PATH, "merge"}, |
| {99,"reboot"}, |
| }; |
| |
| static mapping_table_t path_map[2] = { |
| {MCF_CMD_PATH_TYPE_OTA, "mdota2"}, |
| {MCF_CMD_PATH_TYPE_RUNTIME, "mdota"} |
| }; |
| |
| #define CMD_MAP_LEN (sizeof(cmd_map)/sizeof(cmd_map[0])) |
| #define PATH_MAP_LEN (sizeof(path_map)/sizeof(path_map[0])) |
| |
| //#define USE_DEBUG_LOG |
| #ifdef USE_DEBUG_LOG |
| #define debug_log(format, ...) printf(format, ##__VA_ARGS__) |
| #else |
| #define debug_log(format, ...) |
| #endif |
| |
| /****************************************************************************** |
| * Feature: wait ind callback by linux signal |
| ******************************************************************************/ |
| #define USE_MCF_THREAD_WAIT_IND_CB |
| |
| #ifdef USE_MCF_THREAD_WAIT_IND_CB |
| #define WAIT_IND_CB_TIMEOUT_SEC 5 |
| static pthread_cond_t g_cond; |
| static pthread_mutex_t g_mutex; |
| static bool g_ind_cb_done = false; |
| |
| static void mcf_thread_wait_ind_cb(void) |
| { |
| struct timeval now_time; |
| struct timespec out_time; |
| |
| if (g_ind_cb_done == false) { |
| pthread_cond_init(&g_cond, NULL); |
| pthread_mutex_init(&g_mutex, NULL); |
| |
| gettimeofday(&now_time, NULL); |
| out_time.tv_sec = now_time.tv_sec + WAIT_IND_CB_TIMEOUT_SEC; |
| out_time.tv_nsec = now_time.tv_usec * 1000; |
| |
| debug_log("wait mcf ind cb\n"); |
| pthread_mutex_lock(&g_mutex); |
| pthread_cond_timedwait(&g_cond, &g_mutex, &out_time); |
| pthread_mutex_unlock(&g_mutex); |
| debug_log("wait done\n"); |
| |
| pthread_cond_destroy(&g_cond); |
| pthread_mutex_destroy(&g_mutex); |
| } |
| } |
| |
| static void mcf_thread_send_signal(void) |
| { |
| if (g_ind_cb_done == false) { |
| pthread_mutex_lock(&g_mutex); |
| pthread_cond_signal(&g_cond); |
| pthread_mutex_unlock(&g_mutex); |
| g_ind_cb_done = true; |
| } |
| } |
| |
| #else |
| #define mcf_thread_wait_ind_cb() |
| #define mcf_thread_send_signal() |
| #endif /* THREAD_WAIT_MCF_IND_CB */ |
| |
| /****************************************************************************** |
| * Functions |
| ******************************************************************************/ |
| static void printf_help(void) |
| { |
| char help_text[] = {"Usage:\n" |
| " mcf_cmd <-o get> <-b bin_type>\n" |
| " mcf_cmd <-o dump> [-d lid1,lid2,...,lid32]\n" |
| " mcf_cmd <-o set> <-b bin_type> <-p path_folder> <-f file_name> <-r appendOTA_resetLID> [-t trigger_dsbp] [-s sim_id]\n" |
| " mcf_cmd <-o update> [-w with_ini]\n" |
| " mcf_cmd <-o read> <-b bin_type> <-g GID> [-i record_id] [-y array_index] [-l length]\n" |
| " mcf_cmd <-o write> <-b bin_type> <-g GID> [-i record_id] [-y array_index] [-l length] <-v write_value>\n" |
| " mcf_cmd <-o merge> <-b bin_type> <-p path_folder> <-f file_name>\n" |
| " <> is required parameter; [] is optional parameter, notice its default value if not set\n" |
| " -o, operation (str): get/dump/set/update/read/write/merge\n" |
| " -b, bin type: 0:OTA, 1:OTA by OP, 2:general OTA by OP\n" |
| " -d, LID list (str): use \",\" to split, max num is 32; default dump all\n" |
| " -p, path folder (str): \"mdota\"/\"mdota2\"\n" |
| " -f, OTA file name (str)\n" |
| " -r, appendOTA_resetLID: Valid after running merge cmd, 0:append OTA file, 1:reset LIDs\n" |
| " -t, trigger dsbp: 0:not trigger, 1:trigger; default 0\n" |
| " -w, update with ini file: 0:no read ini, 1:read ini; default 0\n" |
| " -i, NVRAM item record id: default 1\n" |
| " -g, GID number\n" |
| " -y, array index (str): use \",\" to split; default \"\"\n" |
| " -l, data length\n" |
| " -v, write value (str): hex string, use \"3412\" for 0x1234\n" |
| " -s, send cmd by sim id, support all cmd: 0 for sim1, 1 for sim2, optional, defatul 0\n" |
| " note: if parameter is string, its \"\" can be omitted\n" |
| }; |
| printf("%s", help_text); |
| } |
| |
| static void mcf_ind_cb(mipc_msg_t *msg_ptr, void *priv_ptr) |
| { |
| uint32_t ret; |
| |
| printf("MCF cmd CB type=%u result=%u\n", mipc_msg_get_val_uint8(msg_ptr, MIPC_SYS_MCF_IND_T_TYPE, 0xff), |
| ret = mipc_msg_get_val_uint8(msg_ptr, MIPC_SYS_MCF_IND_T_RESULT, 0xff)); |
| |
| if ((mc.opnum == MIPC_SYS_MCF_OP_DUMP_LID_DATA) && (ret == RESULT_SUCCESS)) { |
| mc.run_cmd_ret = RESULT_SUCCESS; |
| } |
| |
| mcf_thread_send_signal(); |
| } |
| |
| static void mcf_mipc_init(void) |
| { |
| #ifdef SPECIFIC_MIPC_PORT |
| SETCOM(SPECIFIC_MIPC_PORT); |
| printf("MCF cmd SETCOM %s\n", SPECIFIC_MIPC_PORT); |
| #endif |
| |
| mipc_init("mcf_cmd"); |
| mipc_msg_register_ind(mc.sim_ps_id, MIPC_SYS_MCF_IND, mcf_ind_cb, NULL); |
| } |
| |
| static void mcf_mipc_deinit(void) |
| { |
| mipc_msg_deinit(msg_req_ptr); |
| mipc_msg_deinit(msg_cnf_ptr); |
| mipc_deinit(); |
| } |
| |
| static char* mcf_get_map_str(uint8_t num, mapping_table_t *map, uint32_t map_len) |
| { |
| static char* null_str = ""; |
| uint32_t i = 0; |
| |
| for (i=0;i<map_len;i++) { |
| if (num == (map+i)->num) { |
| return (map+i)->str; |
| } |
| } |
| |
| return null_str; |
| } |
| |
| static uint8_t mcf_get_map_num(char* str, mapping_table_t *map, uint32_t map_len) |
| { |
| uint32_t i = 0; |
| |
| for (i=0;i<map_len;i++) { |
| if (strcmp(str, (map+i)->str) == 0) { |
| if (strcmp(str, "write") == 0) { |
| mc.write_flag = WRITE_FLAG; |
| return (map+i)->num - mc.write_flag; |
| } else { |
| return (map+i)->num; |
| } |
| } |
| } |
| |
| return PARA_INT8_ERROE_MAX; |
| } |
| |
| static void log_op_error_parameter(uint8_t num) |
| { |
| printf("MCF op=\"%s\" error parameter, CHECK!\nRun mcf_cmd to see the format!", mcf_get_map_str(num, cmd_map, CMD_MAP_LEN)); |
| } |
| |
| static void log_mipc_result_fail(uint32_t result) |
| { |
| printf("MCF cmd FAIL, mipc result=%u\n", result); |
| } |
| |
| static void mcf_cmd_parameters_init(void) |
| { |
| /* required parameter, will check them */ |
| mc.opnum = PARA_INT8_ERROE_MAX; |
| mc.bin_type = PARA_INT8_ERROE_MAX; |
| mc.path_folder_idx = PARA_INT8_ERROE_MAX; |
| mc.appendOTA_resetLID = PARA_INT8_ERROE_MAX; |
| mc.gid = 0; |
| mc.file_name = NULL; |
| mc.write_value = NULL; |
| /* optional parameter, set default value */ |
| mc.is_trigger = 0; |
| mc.is_with = 0; |
| mc.record_id = 1; |
| mc.data_length = 0; |
| mc.lid_str = ""; |
| mc.array_index = ""; |
| /* internal use variable */ |
| mc.write_flag = 0; |
| mc.real_write_length = 0; |
| mc.run_cmd_ret = PARA_INT8_ERROE_MAX; // linux shell only get 0~255 |
| mc.sim_ps_id = MIPC_MSG_PS0; // set default as MIPC_MSG_PS0 |
| } |
| |
| static void mcf_cmd_hex_string_to_bytes(char *input_string) |
| { |
| uint32_t length = strlen(input_string); |
| uint8_t temp[2]; |
| uint32_t i,j; |
| |
| if (length%2 != 0) { |
| printf("write_value str len need be even\n"); |
| return; |
| } |
| |
| char* pdata = malloc(length/2); |
| if (pdata == NULL) return; |
| |
| for (i=0;i<length/2;i++) { |
| temp[0] = input_string[i*2]; |
| temp[1] = input_string[i*2+1]; |
| |
| for (j=0; j<2; j++) { |
| if (temp[j] >= '0' && temp[j] <= '9') { |
| temp[j] = temp[j] - '0'; |
| } else if (temp[j] >= 'a' && temp[j] <= 'f') { |
| temp[j] = temp[j] - 'a' + 10; |
| } else if (temp[j] >= 'A' && temp[j] <= 'F') { |
| temp[j] = temp[j] - 'A' + 10; |
| } else { |
| free(pdata); |
| return; |
| } |
| } |
| |
| pdata[i] = (temp[0]<<4) | temp[1]; |
| } |
| |
| if (mc.write_value != NULL) free(mc.write_value); |
| mc.write_value = pdata; |
| mc.real_write_length = length/2; |
| } |
| |
| static void mcf_cmd_parameters_parser(int argc, char *argv[]) |
| { |
| uint32_t ch; |
| uint16_t sim_id; |
| char* opstr = ""; |
| |
| if (argc == 1) { |
| printf_help(); |
| mc.run_cmd_ret = RESULT_SUCCESS; |
| return; |
| } |
| |
| while ((ch = getopt(argc, argv, "o:b:d:p:f:t:r:w:g:i:y:l:v:s:")) != -1) { |
| switch(ch) { |
| case 'o': |
| mc.opnum = mcf_get_map_num(optarg, cmd_map, CMD_MAP_LEN); |
| opstr = optarg; |
| break; |
| case 'b': |
| mc.bin_type = atoi(optarg); |
| break; |
| case 'd': |
| mc.lid_str = optarg; |
| break; |
| case 'p': |
| mc.path_folder_idx = mcf_get_map_num(optarg, path_map, PATH_MAP_LEN); |
| break; |
| case 'f': |
| mc.file_name = optarg; |
| break; |
| case 't': |
| mc.is_trigger = atoi(optarg); |
| break; |
| case 'r': |
| mc.appendOTA_resetLID = atoi(optarg); |
| break; |
| case 'w': |
| mc.is_with = atoi(optarg); |
| break; |
| case 'g': |
| mc.gid = atoi(optarg); |
| break; |
| case 'i': |
| mc.record_id = atoi(optarg); |
| break; |
| case 'y': |
| mc.array_index = optarg; |
| break; |
| case 'l': |
| mc.data_length = atoi(optarg); |
| break; |
| case 'v': |
| mcf_cmd_hex_string_to_bytes(optarg); |
| break; |
| case 's': |
| sim_id = atoi(optarg); |
| if (sim_id == 0xFF) { |
| mc.sim_ps_id = MIPC_MSG_ALL; |
| } else if (sim_id <= 7) { |
| mc.sim_ps_id = (mipc_msg_sim_ps_id_enum)(1 << sim_id); |
| } |
| break; |
| default: |
| break; |
| } |
| } |
| |
| if (mc.opnum == PARA_INT8_ERROE_MAX) { |
| printf("MCF unsupport: -o \"%s\"\n", opstr); |
| } |
| } |
| |
| static void mcf_cmd_parameters_free(void) |
| { |
| if(mc.write_value != NULL) |
| free(mc.write_value); |
| } |
| |
| /******************************************************************************* |
| * origin cmd: AT+EMCFC=4,<config_type> |
| * response: +EMCFC:4,<config_type>,<path_type>,<config1 str> |
| * ind cb: none |
| * mcf cmd: mcf_cmd <-o get> <-b bin_type> |
| *******************************************************************************/ |
| static void mcf_cmd_op_get_applied_file_path(int argc, char *argv[]) |
| { |
| uint32_t mipc_ret = 0; |
| |
| if (mc.bin_type >= MCF_CMD_BIN_TYPE_MAX) { |
| log_op_error_parameter(MIPC_SYS_MCF_OP_GET_APPLIED_FILE_PATH); |
| return; |
| } |
| |
| msg_req_ptr = mipc_msg_init(MIPC_SYS_MCF_REQ, mc.sim_ps_id); |
| mipc_msg_add_tlv_uint8(msg_req_ptr, MIPC_SYS_MCF_REQ_T_OP, MIPC_SYS_MCF_OP_GET_APPLIED_FILE_PATH); |
| mipc_msg_add_tlv_uint8(msg_req_ptr, MIPC_SYS_MCF_REQ_T_CONFIG_TYPE, mc.bin_type); |
| msg_cnf_ptr = mipc_msg_sync(msg_req_ptr); |
| |
| mipc_ret = mipc_msg_get_val_uint32(msg_cnf_ptr, MIPC_T_RESULT, MIPC_RESULT_FAILURE); |
| |
| if (mipc_ret == MIPC_RESULT_SUCCESS) { |
| printf("MCF cmd SUCCESS op=\"%s\" bin_type=%u path_folder=\"%s\" config_file=\"%s\"\n", |
| mcf_get_map_str(mipc_msg_get_val_uint8(msg_cnf_ptr, MIPC_SYS_MCF_CNF_T_OP, 0xff), cmd_map, CMD_MAP_LEN), |
| mipc_msg_get_val_uint8(msg_cnf_ptr, MIPC_SYS_MCF_CNF_T_CONFIG_TYPE, 0xff), |
| mcf_get_map_str(mipc_msg_get_val_uint8(msg_cnf_ptr, MIPC_SYS_MCF_CNF_T_PATH_TYPE, 0xff), path_map, PATH_MAP_LEN), |
| (char *)mipc_msg_get_val_ptr(msg_cnf_ptr, MIPC_SYS_MCF_CNF_T_CONFIG1, NULL)); |
| mc.run_cmd_ret = RESULT_SUCCESS; |
| } else { |
| log_mipc_result_fail(mipc_ret); |
| } |
| } |
| |
| /******************************************************************************* |
| * origin cmd: AT+EMCFC=5 [lid1,lid2,...,lid32] |
| * response: +EMCFC:5,<MCF result> |
| * ind cb: +EMCFRPT:<type>,<MCF result> |
| * mcf cmd: mcf_cmd <-o dump> [-d lid1,lid2,...,lid32] |
| *******************************************************************************/ |
| static void mcf_cmd_op_dump_lid_data(int argc, char *argv[]) |
| { |
| uint32_t mipc_ret = 0, mcf_ret = 0xffffffff; |
| |
| msg_req_ptr = mipc_msg_init(MIPC_SYS_MCF_REQ, mc.sim_ps_id); |
| mipc_msg_add_tlv_uint8(msg_req_ptr, MIPC_SYS_MCF_REQ_T_OP, MIPC_SYS_MCF_OP_DUMP_LID_DATA); |
| if (strcmp(mc.lid_str, "") != 0) { |
| mipc_msg_add_tlv(msg_req_ptr, MIPC_SYS_MCF_REQ_T_DUMP_LIDS, strlen(mc.lid_str) + 1, mc.lid_str); |
| } |
| msg_cnf_ptr = mipc_msg_sync(msg_req_ptr); |
| |
| mipc_ret = mipc_msg_get_val_uint32(msg_cnf_ptr, MIPC_T_RESULT, MIPC_RESULT_FAILURE); |
| if (mipc_ret == MIPC_RESULT_SUCCESS) { |
| printf("MCF cmd SUCCESS op=\"%s\" mcf_result=%u\n", |
| mcf_get_map_str(mipc_msg_get_val_uint8(msg_cnf_ptr, MIPC_SYS_MCF_CNF_T_OP, 0xff), cmd_map, CMD_MAP_LEN), |
| mcf_ret = mipc_msg_get_val_uint32(msg_cnf_ptr, MIPC_SYS_MCF_CNF_T_MCF_RESULT, 0xffffffff)); |
| } else { |
| log_mipc_result_fail(mipc_ret); |
| } |
| |
| if(mcf_ret == RESULT_SUCCESS) { |
| mcf_thread_wait_ind_cb(); |
| } |
| } |
| |
| /******************************************************************************* |
| * origin cmd: AT+EMCFC=6,<config_type>,<path_type>,<config1 str>,<trigger_dsbp>,<is_reset> |
| * response: +EMCFC:6,<MCF result>,<DSBP result> |
| * ind cb: (if trigger_dsbp == 1) +EMCFRPT:<type>,<DSBP result> |
| * mcf cmd: mcf_cmd <-o set> <-b bin_type> <-p path_folder> <-f file_name> <-r append_resetLID> [-t trigger_dsbp] |
| *******************************************************************************/ |
| static void mcf_cmd_op_set_file_path_and_auto_select_bin(int argc, char *argv[]) |
| { |
| uint32_t mipc_ret = 0, mcf_ret = 0xffffffff, dsbp_ret = 0xffffffff; |
| |
| if ((mc.bin_type >= MCF_CMD_BIN_TYPE_MAX) || (mc.path_folder_idx >= MCF_CMD_PATH_TYPE_MAX) || (mc.file_name == NULL ) || |
| (mc.is_trigger >= MCF_PARA_IS_MAX )|| (mc.appendOTA_resetLID >= MCF_PARA_IS_MAX)) { |
| log_op_error_parameter(MIPC_SYS_MCF_OP_SET_FILE_PATH_AND_AUTO_SELECT_BIN); |
| return; |
| } |
| |
| msg_req_ptr = mipc_msg_init(MIPC_SYS_MCF_REQ, mc.sim_ps_id); |
| mipc_msg_add_tlv_uint8(msg_req_ptr, MIPC_SYS_MCF_REQ_T_OP, MIPC_SYS_MCF_OP_SET_FILE_PATH_AND_AUTO_SELECT_BIN); |
| mipc_msg_add_tlv_uint8(msg_req_ptr, MIPC_SYS_MCF_REQ_T_CONFIG_TYPE, mc.bin_type); |
| mipc_msg_add_tlv_uint8(msg_req_ptr, MIPC_SYS_MCF_REQ_T_PATH_TYPE, mc.path_folder_idx); |
| mipc_msg_add_tlv(msg_req_ptr, MIPC_SYS_MCF_REQ_T_CONFIG1, strlen(mc.file_name)+1, mc.file_name); |
| mipc_msg_add_tlv_uint8(msg_req_ptr, MIPC_SYS_MCF_REQ_T_TRIGGER_DSBP, mc.is_trigger); |
| mipc_msg_add_tlv_uint8(msg_req_ptr, MIPC_SYS_MCF_REQ_T_IS_RESET, mc.appendOTA_resetLID); |
| msg_cnf_ptr = mipc_msg_sync(msg_req_ptr); |
| |
| mipc_ret = mipc_msg_get_val_uint32(msg_cnf_ptr, MIPC_T_RESULT, MIPC_RESULT_FAILURE); |
| if (mipc_ret == MIPC_RESULT_SUCCESS) { |
| printf("MCF cmd SUCCESS op=\"%s\" mcf_result=%u dsbp_result=%u\n", |
| mcf_get_map_str(mipc_msg_get_val_uint8(msg_cnf_ptr, MIPC_SYS_MCF_CNF_T_OP, 0xff), cmd_map, CMD_MAP_LEN), |
| mcf_ret = mipc_msg_get_val_uint32(msg_cnf_ptr, MIPC_SYS_MCF_CNF_T_MCF_RESULT, 0xffffffff), |
| dsbp_ret = mipc_msg_get_val_uint32(msg_cnf_ptr, MIPC_SYS_MCF_CNF_T_DSBP_RESULT, 0xffffffff)); |
| } else { |
| log_mipc_result_fail(mipc_ret); |
| } |
| |
| if (mcf_ret == RESULT_SUCCESS && dsbp_ret == RESULT_SUCCESS) { |
| mc.run_cmd_ret = RESULT_SUCCESS; |
| if(mc.is_trigger == MCF_CMD_IS_TRIGGER_TRUE) { |
| mcf_thread_wait_ind_cb(); |
| } |
| } |
| } |
| |
| /******************************************************************************* |
| * cmd: AT+EMCFC=7,<action> |
| * response: +EMCFC:7,<MCF result> |
| * ind cb: +EMCFRPT:<type>,<result> |
| * mcf cmd: mcf_cmd <-o update> [-w with_ini] |
| *******************************************************************************/ |
| static void mcf_cmd_op_update_opota_file(int argc, char *argv[]) |
| { |
| uint32_t mipc_ret = 0, mcf_ret = 0xffffffff; |
| |
| if (mc.is_with >= MCF_PARA_IS_MAX) { |
| log_op_error_parameter(MIPC_SYS_MCF_OP_UPDATE_OPOTA_FILE); |
| return; |
| } |
| |
| msg_req_ptr = mipc_msg_init(MIPC_SYS_MCF_REQ, mc.sim_ps_id); |
| mipc_msg_add_tlv_uint8(msg_req_ptr, MIPC_SYS_MCF_REQ_T_OP, MIPC_SYS_MCF_OP_UPDATE_OPOTA_FILE); |
| mipc_msg_add_tlv_uint8(msg_req_ptr, MIPC_SYS_MCF_REQ_T_ACTION, mc.is_with); |
| msg_cnf_ptr = mipc_msg_sync(msg_req_ptr); |
| |
| mipc_ret = mipc_msg_get_val_uint32(msg_cnf_ptr, MIPC_T_RESULT, MIPC_RESULT_FAILURE); |
| if (mipc_ret == MIPC_RESULT_SUCCESS) { |
| printf("MCF cmd SUCCESS op=\"%s\" mcf_result=%u\n", |
| mcf_get_map_str(mipc_msg_get_val_uint8(msg_cnf_ptr, MIPC_SYS_MCF_CNF_T_OP, 0xff), cmd_map, CMD_MAP_LEN), |
| mcf_ret = mipc_msg_get_val_uint32(msg_cnf_ptr, MIPC_SYS_MCF_CNF_T_MCF_RESULT, 0xffffffff)); |
| } else { |
| log_mipc_result_fail(mipc_ret); |
| } |
| |
| if (mcf_ret == RESULT_SUCCESS) { |
| mc.run_cmd_ret = RESULT_SUCCESS; |
| mcf_thread_wait_ind_cb(); |
| } |
| } |
| |
| /******************************************************************************* |
| * cmd: AT+EMCFC=10,<format>,<action>,<record ID>,<number>,<config str>[,<length>],[,<value>]] |
| * response: +EMCFC:10,<format>,<action>,<mcf result>,<length>,<value> |
| * ind cb: none |
| * mcf_cmd <-o read> <-b bin_type> <-g GID> [-i record_id] [-y array_index] [-l length] |
| * mcf_cmd <-o write> <-b bin_type> <-g GID> [-i record_id] [-y array_index] [-l length] <-v write_value> |
| *******************************************************************************/ |
| static void mcf_cmd_op_query_variable_value(int argc, char *argv[]) |
| { |
| uint32_t mipc_ret = 0, mcf_ret = 0xffffffff; |
| uint8_t action, ret_len, i; |
| char *ret_str; |
| |
| if ((mc.bin_type >= MCF_CMD_BIN_TYPE_MAX) || (mc.gid == 0) || (mc.write_flag == WRITE_FLAG && mc.write_value == NULL)) { |
| log_op_error_parameter(MIPC_SYS_MCF_OP_QUERY_VARIABLE_VALUE); |
| return; |
| } |
| |
| if (mc.write_flag != WRITE_FLAG) { |
| action = (mc.bin_type == MCF_CMD_BIN_TYPE_DEFAULT_BIN) ? MCF_CMD_VARIABLE_ACT_READ_OTA : MCF_CMD_VARIABLE_ACT_READ_OPOTA; |
| } else { |
| action = (mc.bin_type == MCF_CMD_BIN_TYPE_DEFAULT_BIN) ? MCF_CMD_VARIABLE_ACT_WRITE_OTA : MCF_CMD_VARIABLE_ACT_WRITE_OPOTA; |
| } |
| |
| msg_req_ptr = mipc_msg_init(MIPC_SYS_MCF_REQ, mc.sim_ps_id); |
| mipc_msg_add_tlv_uint8(msg_req_ptr, MIPC_SYS_MCF_REQ_T_OP, MIPC_SYS_MCF_OP_QUERY_VARIABLE_VALUE); |
| mipc_msg_add_tlv_uint8(msg_req_ptr, MIPC_SYS_MCF_REQ_T_FORMAT, MCF_CMD_QUERY_VARIABLE_FORM_GID); |
| mipc_msg_add_tlv_uint8(msg_req_ptr, MIPC_SYS_MCF_REQ_T_ACTION, action); |
| mipc_msg_add_tlv_uint32(msg_req_ptr, MIPC_SYS_MCF_REQ_T_NUM, mc.gid); |
| mipc_msg_add_tlv_uint16(msg_req_ptr, MIPC_SYS_MCF_REQ_T_REC_ID, mc.record_id); |
| mipc_msg_add_tlv(msg_req_ptr, MIPC_SYS_MCF_REQ_T_CONFIG, strlen(mc.array_index)+1, mc.array_index); |
| mipc_msg_add_tlv_uint8(msg_req_ptr, MIPC_SYS_MCF_REQ_T_LEN, mc.data_length); |
| if (mc.write_flag == WRITE_FLAG) { |
| mipc_msg_add_tlv(msg_req_ptr, MIPC_SYS_MCF_REQ_T_VALUE, mc.real_write_length, mc.write_value); |
| } |
| |
| msg_cnf_ptr = mipc_msg_sync(msg_req_ptr); |
| mipc_ret = mipc_msg_get_val_uint32(msg_cnf_ptr, MIPC_T_RESULT, MIPC_RESULT_FAILURE); |
| if (mipc_ret == MIPC_RESULT_SUCCESS) { |
| printf("MCF cmd SUCCESS op=\"%s\" mcf_result=%u bin_type=%u", |
| mcf_get_map_str(mipc_msg_get_val_uint8(msg_cnf_ptr, MIPC_SYS_MCF_CNF_T_OP, 0xff)+mc.write_flag, cmd_map, CMD_MAP_LEN), |
| mcf_ret = mipc_msg_get_val_uint32(msg_cnf_ptr, MIPC_SYS_MCF_CNF_T_MCF_RESULT, 0xffffffff), |
| (mipc_msg_get_val_uint8(msg_cnf_ptr, MIPC_SYS_MCF_CNF_T_ACTION, 0xff)%2 == 0) ? MCF_CMD_BIN_TYPE_DEFAULT_BIN : MCF_CMD_BIN_TYPE_CARRIER_BIN); |
| if (mcf_ret == RESULT_SUCCESS) { |
| mc.run_cmd_ret = RESULT_SUCCESS; |
| ret_len = mipc_msg_get_val_uint8(msg_cnf_ptr, MIPC_SYS_MCF_CNF_T_LEN, 0xff); |
| printf(" length=%u", ret_len); |
| if (mc.write_flag != WRITE_FLAG) { |
| ret_str = (char*)mipc_msg_get_val_ptr(msg_cnf_ptr, MIPC_SYS_MCF_CNF_T_VALUE, NULL); |
| printf(" value=\""); |
| for (i=0;i<ret_len;i++) { |
| printf("%02X", *(ret_str + i)); |
| } |
| printf("\""); |
| } |
| } |
| printf("\n"); |
| } else { |
| log_mipc_result_fail(mipc_ret); |
| } |
| } |
| |
| /******************************************************************************* |
| * cmd: AT+EMCFC=11,<config_type>,<path_type>,<config1 str> |
| * response: +EMCFC:11,<MCF result> |
| * ind cb: none |
| * mcf cmd: mcf_cmd <-o merge> <-b bin_type> <-p path_folder> <-f file_name> |
| *******************************************************************************/ |
| static void mcf_cmd_op_assign_combined_path(int argc, char *argv[]) |
| { |
| uint32_t mipc_ret = 0, mcf_ret = 0xffffffff; |
| |
| if ((mc.bin_type >= MCF_CMD_BIN_TYPE_MAX) || (mc.path_folder_idx >= MCF_CMD_PATH_TYPE_MAX) || (mc.file_name == NULL)) { |
| log_op_error_parameter(MIPC_SYS_MCF_OP_ASSIGN_COMBINED_PATH); |
| return; |
| } |
| |
| msg_req_ptr = mipc_msg_init(MIPC_SYS_MCF_REQ, mc.sim_ps_id); |
| mipc_msg_add_tlv_uint8(msg_req_ptr, MIPC_SYS_MCF_REQ_T_OP, MIPC_SYS_MCF_OP_ASSIGN_COMBINED_PATH); |
| mipc_msg_add_tlv_uint8(msg_req_ptr, MIPC_SYS_MCF_REQ_T_CONFIG_TYPE, mc.bin_type); |
| mipc_msg_add_tlv_uint8(msg_req_ptr, MIPC_SYS_MCF_REQ_T_PATH_TYPE, mc.path_folder_idx); |
| mipc_msg_add_tlv(msg_req_ptr, MIPC_SYS_MCF_REQ_T_CONFIG1, strlen(mc.file_name)+1, mc.file_name); |
| msg_cnf_ptr = mipc_msg_sync(msg_req_ptr); |
| |
| mipc_ret = mipc_msg_get_val_uint32(msg_cnf_ptr, MIPC_T_RESULT, MIPC_RESULT_FAILURE); |
| if (mipc_ret == MIPC_RESULT_SUCCESS) { |
| printf("MCF cmd SUCCESS op=\"%s\" mcf_result=%u\n", |
| mcf_get_map_str(mipc_msg_get_val_uint8(msg_cnf_ptr, MIPC_SYS_MCF_CNF_T_OP, 0xff), cmd_map, CMD_MAP_LEN), |
| mcf_ret = mipc_msg_get_val_uint32(msg_cnf_ptr, MIPC_SYS_MCF_CNF_T_MCF_RESULT, 0xffffffff)); |
| if (mcf_ret == RESULT_SUCCESS) { |
| mc.run_cmd_ret = RESULT_SUCCESS; |
| } |
| } else { |
| log_mipc_result_fail(mipc_ret); |
| } |
| } |
| |
| static void mcf_system_reboot(void) |
| { |
| printf("MCF system reboot\n"); |
| system("reboot"); |
| } |
| |
| int main(int argc, char *argv[]) |
| { |
| mcf_cmd_parameters_init(); |
| mcf_cmd_parameters_parser(argc, argv); |
| if (mc.opnum != PARA_INT8_ERROE_MAX) |
| { |
| mcf_mipc_init(); |
| switch (mc.opnum) { |
| case MIPC_SYS_MCF_OP_GET_APPLIED_FILE_PATH: |
| mcf_cmd_op_get_applied_file_path(argc, argv); |
| break; |
| case MIPC_SYS_MCF_OP_DUMP_LID_DATA: |
| mcf_cmd_op_dump_lid_data(argc, argv); |
| break; |
| case MIPC_SYS_MCF_OP_SET_FILE_PATH_AND_AUTO_SELECT_BIN: |
| mcf_cmd_op_set_file_path_and_auto_select_bin(argc, argv); |
| break; |
| case MIPC_SYS_MCF_OP_UPDATE_OPOTA_FILE: |
| mcf_cmd_op_update_opota_file(argc, argv); |
| break; |
| case MIPC_SYS_MCF_OP_QUERY_VARIABLE_VALUE: |
| mcf_cmd_op_query_variable_value(argc, argv); |
| break; |
| case MIPC_SYS_MCF_OP_ASSIGN_COMBINED_PATH: |
| mcf_cmd_op_assign_combined_path(argc, argv); |
| break; |
| case 99: |
| mcf_system_reboot(); |
| default: |
| break; |
| } |
| mcf_mipc_deinit(); |
| } |
| mcf_cmd_parameters_free(); |
| return mc.run_cmd_ret; |
| } |
| |