diff --git a/services/init/include/init_cmds.h b/services/init/include/init_cmds.h index bd459c4ac40d4eb6c5a67133823c7db81bf06602..c56bb66087bcc4cf86e3d98038f0cb89830aa564 100755 --- a/services/init/include/init_cmds.h +++ b/services/init/include/init_cmds.h @@ -81,6 +81,7 @@ const struct CmdTable *GetCmdByName(const char *name); void ExecReboot(const char *value); char *BuildStringFromCmdArg(const struct CmdArgs *ctx, int startIndex); void ExecCmd(const struct CmdTable *cmd, const char *cmdContent); +int FileCryptEnable(char *fileCryptOption); #ifdef __cplusplus #if __cplusplus } diff --git a/services/init/init_common_cmds.c b/services/init/init_common_cmds.c index eb567ca8d6a3233184b68e228baad1e58286aeac..f03d9f2b5f25bccb2b71fcad1860cea4e424fad7 100755 --- a/services/init/init_common_cmds.c +++ b/services/init/init_common_cmds.c @@ -38,6 +38,8 @@ #include "init_utils.h" #include "securec.h" +static char *g_fileCryptOptions = NULL; + static char *AddOneArg(const char *param, size_t paramLen) { int valueCount = 1; @@ -385,6 +387,17 @@ static int GetMountFlag(unsigned long *mountflag, const char *targetStr, const c WaitForFile(source, WAIT_MAX_SECOND); return 1; } + const char *fileCryptPre = "filecrypt="; + size_t len = strlen(fileCryptPre); + if (strncmp(targetStr, fileCryptPre, len) == 0) { + size_t maxLen = strlen(targetStr) + 1; + g_fileCryptOptions = calloc(sizeof(char), maxLen); + INIT_ERROR_CHECK(g_fileCryptOptions != NULL, return 0, "Failed to alloc memory"); + int ret = snprintf_s(g_fileCryptOptions, maxLen, maxLen - 1, "%s", targetStr + len); + INIT_ERROR_CHECK(ret >= 0, return 0, "Failed to snprintf"); + return 1; + } + return 0; } @@ -426,6 +439,18 @@ static void DoMount(const struct CmdArgs *ctx) if (ret != 0) { INIT_LOGE("Failed to mount for %s, err %d.", target, errno); } + if ((g_fileCryptOptions != NULL) && (strncmp(target, "/data", strlen("/data")) == 0)) { + ret = FileCryptEnable(g_fileCryptOptions); + if (ret < 0) { + INIT_LOGE("File Crypt enabled failed"); + free(g_fileCryptOptions); + g_fileCryptOptions = NULL; + return; + } + free(g_fileCryptOptions); + g_fileCryptOptions = NULL; + INIT_LOGI("File Crypt enabled success"); + } } static void DoWrite(const struct CmdArgs *ctx) diff --git a/services/init/lite/init_cmds.c b/services/init/lite/init_cmds.c index 4e14ce2453a6e10e60f04a7b43d7e9714ce92506..1005cd19147c274dcdedd35e9dfdb376943ebc57 100755 --- a/services/init/lite/init_cmds.c +++ b/services/init/lite/init_cmds.c @@ -108,6 +108,11 @@ static void DoLoadCfg(const struct CmdArgs *ctx) (void)fclose(fp); } +int FileCryptEnable(char *fileCryptOption) +{ + return 0; +} + static const struct CmdTable g_cmdTable[] = { { "exec ", 1, 10, DoExec }, { "loadcfg ", 1, 1, DoLoadCfg }, diff --git a/services/init/standard/init_cmds.c b/services/init/standard/init_cmds.c index 5542a6269c17320f84b31e9e97f2925b6fdbf483..d8f5470fe681d6403d687af4bf2ddfdceb8be8d3 100755 --- a/services/init/standard/init_cmds.c +++ b/services/init/standard/init_cmds.c @@ -41,6 +41,8 @@ #include #endif +#define ARRAY_LEN(array) (sizeof(array) / (sizeof(array[0]))) + int GetParamValue(const char *symValue, unsigned int symLen, char *paramValue, unsigned int paramLen) { INIT_CHECK_RETURN_VALUE((symValue != NULL) && (paramValue != NULL) && (paramLen != 0), -1); @@ -365,6 +367,89 @@ static void DoTimerStop(const struct CmdArgs*ctx) ServiceStopTimer(service); } +static int SyncExecCommand(int argc, char *const *argv) +{ + if (argc == 0 || argv == NULL || argv[0] == NULL) { + return -1; + } + pid_t pid = fork(); + if (pid < 0) { + INIT_LOGE("Fork new process to format failed: %d", errno); + return -1; + } + if (pid == 0) { + execv(argv[0], argv); + exit(-1); + } + int status; + waitpid(pid, &status, 0); + if (!WIFEXITED(status) || WEXITSTATUS(status) != 0) { + INIT_LOGE("Command %s failed with status %d", argv[0], WEXITSTATUS(status)); + } + return WEXITSTATUS(status); +} + +static void DoInitGlobalKey(const struct CmdArgs *ctx) +{ + INIT_LOGI("DoInitGlobalKey: start"); + if (ctx == NULL || ctx->argc != 1) { + INIT_LOGE("DoInitGlobalKey: para invalid"); + return; + } + const char *dataDir = "/data"; + if (strncmp(ctx->argv[0], dataDir, strlen(dataDir)) != 0) { + INIT_LOGE("DoInitGlobalKey: not data partitation"); + return; + } + char *const argv[] = { + "/system/bin/sdc", + "filecrypt", + "init_global_key", + NULL + }; + int argc = ARRAY_LEN(argv); + int ret = SyncExecCommand(argc, argv); + INIT_LOGI("DoInitGlobalKey: end, ret = %d", ret); +} + +static void DoInitMainUser(const struct CmdArgs *ctx) +{ + INIT_LOGI("DoInitMainUser: start"); + if (ctx == NULL) { + INIT_LOGE("DoInitMainUser: para invalid"); + return; + } + char *const argv[] = { + "/system/bin/sdc", + "filecrypt", + "init_main_user", + NULL + }; + int argc = ARRAY_LEN(argv); + int ret = SyncExecCommand(argc, argv); + INIT_LOGI("DoInitMainUser: end, ret = %d", ret); +} + +int FileCryptEnable(char *fileCryptOption) +{ + INIT_LOGI("FileCryptEnable: start"); + if (fileCryptOption == NULL) { + INIT_LOGE("FileCryptEnable:option null"); + return -EINVAL; + } + char *const argv[] = { + "/system/bin/sdc", + "filecrypt", + "enable", + fileCryptOption, + NULL + }; + int argc = ARRAY_LEN(argv); + int ret = SyncExecCommand(argc, argv); + INIT_LOGI("FileCryptEnable: end, ret = %d", ret); + return ret; +} + static const struct CmdTable g_cmdTable[] = { { "exec ", 1, 10, DoExec }, { "mknode ", 1, 5, DoMakeNode }, @@ -385,6 +470,8 @@ static const struct CmdTable g_cmdTable[] = { { "sync ", 0, 1, DoSync }, { "timer_start", 1, 1, DoTimerStart }, { "timer_stop", 1, 1, DoTimerStop }, + { "init_global_key ", 1, 1, DoInitGlobalKey }, + { "init_main_user ", 0, 1, DoInitMainUser }, }; const struct CmdTable *GetCmdTable(int *number)