[Feature]Merge MP1_MR1 from MTK
Change-Id: I3fc364555acf14f1c308b6be7b05f21f92757fd0
diff --git a/src/telephonyware/3.0/mcf_cmd/LICENSE b/src/telephonyware/3.0/mcf_cmd/LICENSE
new file mode 100755
index 0000000..10f9164
--- /dev/null
+++ b/src/telephonyware/3.0/mcf_cmd/LICENSE
@@ -0,0 +1,31 @@
+Copyright Statement:
+
+This software/firmware and related documentation ("MediaTek Software") are
+protected under relevant copyright laws. The information contained herein is
+confidential and proprietary to MediaTek Inc. and/or its licensors. Without
+the prior written permission of MediaTek inc. and/or its licensors, any
+reproduction, modification, use or disclosure of MediaTek Software, and
+information contained herein, in whole or in part, shall be strictly
+prohibited.
+
+Copyright  (C) 2021 MediaTek Inc. All rights reserved.
+
+BY OPENING THIS FILE, RECEIVER HEREBY UNEQUIVOCALLY ACKNOWLEDGES AND AGREES
+THAT THE SOFTWARE/FIRMWARE AND ITS DOCUMENTATIONS ("MEDIATEK SOFTWARE")
+RECEIVED FROM MEDIATEK AND/OR ITS REPRESENTATIVES ARE PROVIDED TO RECEIVER
+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 RECEIVER AGREES
+TO LOOK ONLY TO SUCH THIRD PARTY FOR ANY WARRANTY CLAIM RELATING THERETO.
+RECEIVER EXPRESSLY ACKNOWLEDGES THAT IT IS RECEIVER'S SOLE RESPONSIBILITY TO
+OBTAIN FROM ANY THIRD PARTY ALL PROPER LICENSES CONTAINED IN MEDIATEK
+SOFTWARE. MEDIATEK SHALL ALSO NOT BE RESPONSIBLE FOR ANY MEDIATEK SOFTWARE
+RELEASES MADE TO RECEIVER'S SPECIFICATION OR TO CONFORM TO A PARTICULAR
+STANDARD OR OPEN FORUM. RECEIVER'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 RECEIVER TO MEDIATEK FOR SUCH MEDIATEK SOFTWARE AT ISSUE.
diff --git a/src/telephonyware/3.0/mcf_cmd/Makefile b/src/telephonyware/3.0/mcf_cmd/Makefile
new file mode 100755
index 0000000..98b4167
--- /dev/null
+++ b/src/telephonyware/3.0/mcf_cmd/Makefile
@@ -0,0 +1,13 @@
+TARGET := mcf_cmd
+SRCS := ./mcf_cmd.c
+
+.PHONY: all clean
+
+all: mcf_cmd
+
+mcf_cmd:
+	$(CC) $(CFLAGS) -o $@ $(SRCS) $(LDFLAGS) $(LIBS)
+
+clean:
+	$(warning "makefile mcf_cmd clean")
+	rm -f $(TARGET)
\ No newline at end of file
diff --git a/src/telephonyware/3.0/mcf_cmd/mcf_cmd.c b/src/telephonyware/3.0/mcf_cmd/mcf_cmd.c
new file mode 100755
index 0000000..3248e0d
--- /dev/null
+++ b/src/telephonyware/3.0/mcf_cmd/mcf_cmd.c
@@ -0,0 +1,758 @@
+/******************************************************************************
+*  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;
+}
+