diff --git a/build/build.sh b/build/build.sh index 7ee6891..1cec03a 100644 --- a/build/build.sh +++ b/build/build.sh @@ -122,6 +122,7 @@ function copy_file_output() /bin/cp -f scripts/uninstall.sh run_pkg /bin/cp -f scripts/base.list run_pkg /bin/cp -f scripts/base.list_A500 run_pkg + /bin/cp -f scripts/base.list_A500A2 run_pkg /bin/cp -f scripts/base.list_A200 run_pkg /bin/cp -f scripts/base.list_A200ISoC run_pkg diff --git a/build/scripts/base.list_A500A2 b/build/scripts/base.list_A500A2 new file mode 100644 index 0000000..7e75418 --- /dev/null +++ b/build/scripts/base.list_A500A2 @@ -0,0 +1,38 @@ +/usr/local/Ascend/driver/lib64 +/usr/local/sbin/npu-smi +/etc/sys_version.conf +/etc/ld.so.conf.d/mind_so.conf +/etc/slog.conf +/etc/hdcBasic.cfg +/etc/ascend_install.info +/var/dmp_daemon +/var/davinci/driver/version.info +/var/slogd +/usr/lib64/libsemanage.so.2 +/usr/lib64/libmmpa.so +/usr/lib64/libcrypto.so.1.1 +/usr/lib64/libdrvdsmi.so +/usr/lib64/libdcmi.so +/usr/lib64/libstackcore.so +/usr/lib64/libascend_drvdmp.so +/usr/lib64/libdsmiproduct.so +/usr/lib64/libiam.so.1 +/usr/lib64/libascend_drv_baselib.so +/usr/lib64/libascend_hal.so +/usr/lib64/libslog.so +/usr/lib64/libc_sec.so +/usr/lib64/libascend_drvupgrade.so +/usr/lib64/libeasy_comm.so.1 +/usr/lib64/libfault_event.so.1 +/usr/lib64/libheartbeat.so +/usr/lib64/libxshmem.so.1 +/usr/lib64/libdevmmap.so +/usr/lib64/libmpi_dvpp_adapter.so +/usr/lib64/libaicpu_scheduler.so +/usr/lib64/libaicpu_processer.so +/usr/lib64/libaicpu_prof.so +/usr/lib64/libaicpu_sharder.so +/usr/lib64/libadump.so +/usr/lib64/libtsd_eventclient.so +/usr/lib64/libmsprof.so +/root/hdc_ppc \ No newline at end of file diff --git a/build/scripts/help.info b/build/scripts/help.info index 97e5e23..5f08106 100644 --- a/build/scripts/help.info +++ b/build/scripts/help.info @@ -2,5 +2,5 @@ --install-path Specify the installation path (default: /usr/local/Ascend/Ascend-Docker-Runtime) --uninstall Uninstall the installed ascend-docker-runtime tool --upgrade Upgrade the installed ascend-docker-runtime tool - --install-type= Only A500, A200ISoC and A200 need to specify the installation type of Ascend-docker-runtime (eg: --install-type=A500) + --install-type= Only A500, A500A2, A200ISoC and A200 need to specify the installation type of Ascend-docker-runtime (eg: --install-type=A500) --ce= Only iSula need to specify the container engine(eg: --ce=isula) \ No newline at end of file diff --git a/build/scripts/run_main.sh b/build/scripts/run_main.sh index 110ad24..b713cb8 100644 --- a/build/scripts/run_main.sh +++ b/build/scripts/run_main.sh @@ -33,6 +33,7 @@ function save_install_args() { echo -e "path=${INSTALL_PATH}" echo -e "build=Ascend-docker-runtime_${PACKAGE_VERSION}-$(uname -m)" echo -e "a500=${a500}" + echo -e "a500a2=${a500a2}" echo -e "a200=${a200}" echo -e "a200isoc=${a200isoc}" } >> "${INSTALL_PATH}"/ascend_docker_runtime_install.info @@ -85,6 +86,8 @@ function install() cp -f ./base.list_A200 ${ASCEND_RUNTIME_CONFIG_DIR}/base.list elif [ "${a200isoc}" == "y" ]; then cp -f ./base.list_A200ISoC ${ASCEND_RUNTIME_CONFIG_DIR}/base.list + elif [ "${a500a2}" == "y" ]; then + cp -f ./base.list_A500A2 ${ASCEND_RUNTIME_CONFIG_DIR}/base.list else cp -f ./base.list ${ASCEND_RUNTIME_CONFIG_DIR}/base.list fi @@ -164,6 +167,9 @@ function upgrade() if [ "$(grep "a500=y" "${INSTALL_PATH}"/ascend_docker_runtime_install.info)" == "a500=y" ];then a500=y cp -f ./base.list_A500 ${ASCEND_RUNTIME_CONFIG_DIR}/base.list + elif [ "$(grep "a500a2=y" "${INSTALL_PATH}"/ascend_docker_runtime_install.info)" == "a500a2=y" ]; then + a500a2=y + cp -f ./base.list_A500A2 ${ASCEND_RUNTIME_CONFIG_DIR}/base.list elif [ "$(grep "a200=y" "${INSTALL_PATH}"/ascend_docker_runtime_install.info)" == "a200=y" ]; then a200=y cp -f ./base.list_A200 ${ASCEND_RUNTIME_CONFIG_DIR}/base.list @@ -189,6 +195,7 @@ UPGRADE_FLAG=n a500=n a200=n a200isoc=n +a500a2=n quiet_flag=n ISULA=none @@ -252,7 +259,7 @@ do shift ;; --install-type=*) - if [ "${a500}" == "y" ] || [ "${a200}" == "y" ] || [ "${a200isoc}" == "y" ]; then + if [ "${a500}" == "y" ] || [ "${a200}" == "y" ] || [ "${a200isoc}" == "y" ] || [ "${a500a2}" == "y" ]; then echo "warning :Repeat parameter!" exit 1 fi @@ -263,6 +270,8 @@ do a200=y elif [ "$3" == "--install-type=A200ISoC" ]; then a200isoc=y + elif [ "$3" == "--install-type=A500A2" ]; then + a500a2=y else echo "ERROR :Please check the parameter of --install-type=" exit 1 diff --git a/cli/src/basic.c b/cli/src/basic.c deleted file mode 100644 index fd06d73..0000000 --- a/cli/src/basic.c +++ /dev/null @@ -1,27 +0,0 @@ -/* - * Copyright (c) Huawei Technologies Co., Ltd. 2020-2022. All rights reserved. - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -#include "basic.h" -#include -#include - -void InitParsedConfig(struct ParsedConfig *parsedConfig) -{ - if (parsedConfig == NULL) { - (void)fprintf(stderr, "parsedConfig pointer is null!\n"); - return; - } - - parsedConfig->devicesNr = MAX_DEVICE_NR; -} \ No newline at end of file diff --git a/cli/src/basic.h b/cli/src/basic.h index 36d7065..a5a77b3 100644 --- a/cli/src/basic.h +++ b/cli/src/basic.h @@ -18,12 +18,8 @@ #include #include #include +#include -#define DEVICE_NAME "davinci" -#define VDEVICE_NAME "vdavinci" -#define DAVINCI_MANAGER "davinci_manager" -#define DEVMM_SVM "devmm_svm" -#define HISI_HDC "hisi_hdc" #define DEFAULT_DIR_MODE 0755 #define DEFAULT_LOG_MODE 0600 #define DUMP_LOG_MODE 0400 @@ -31,7 +27,7 @@ #define BUF_SIZE 1024 #define MAX_DEVICE_NR 1024 #define MAX_MOUNT_NR 512 -#define WHITE_LIST_NUM 9 +#define WHITE_LIST_NUM 45 #define ROOT_UID 0 @@ -55,12 +51,13 @@ } \ } while (0) -#define ALLOW_PATH "/devices.allow" #define ROOT_GAP 4 #define FSTYPE_GAP 2 #define MOUNT_SUBSTR_GAP 2 #define ROOT_SUBSTR_GAP 2 +extern bool g_allowLink; + struct PathInfo { char* src; size_t srcLen; @@ -75,8 +72,6 @@ struct MountList { struct ParsedConfig { char rootfs[BUF_SIZE]; - size_t devices[MAX_DEVICE_NR]; - size_t devicesNr; char containerNsPath[BUF_SIZE]; char cgroupPath[BUF_SIZE]; int originNsFd; @@ -84,6 +79,4 @@ struct ParsedConfig { const struct MountList *dirs; }; -void InitParsedConfig(struct ParsedConfig *parsedConfig); - #endif \ No newline at end of file diff --git a/cli/src/cgrp.c b/cli/src/cgrp.c index 16bd9d9..c86ee1f 100644 --- a/cli/src/cgrp.c +++ b/cli/src/cgrp.c @@ -30,372 +30,3 @@ #include "options.h" #include "logger.h" -bool TakeNthWord(char **pLine, unsigned int n, char **word) -{ - if (pLine == NULL || word == NULL) { - (void)fprintf(stderr, "pLine, word pointer is null!\n"); - return false; - } - - char *w = NULL; - for (unsigned int i = 0; i < n; i++) { - w = strsep(pLine, " "); - if (w == NULL || *w == '\0') { - return false; - } - } - - *word = w; - return true; -} - -bool CheckRootDir(char **pLine) -{ - if (pLine == NULL) { - (void)fprintf(stderr, "pLine pointer is null!\n"); - return false; - } - - char *rootDir = NULL; - if (!TakeNthWord(pLine, ROOT_GAP, &rootDir)) { - return false; - } - - return strlen(rootDir) < BUF_SIZE && !StrHasPrefix(rootDir, "/.."); -} - -bool CheckFsType(char **pLine) -{ - if (pLine == NULL) { - (void)fprintf(stderr, "pLine pointer is null!\n"); - return false; - } - - char* fsType = NULL; - if (!TakeNthWord(pLine, FSTYPE_GAP, &fsType)) { - return false; - } - - return IsStrEqual(fsType, "cgroup"); -} - -bool CheckSubStr(char **pLine, const char *subsys) -{ - if (pLine == NULL || subsys == NULL) { - (void)fprintf(stderr, "pLine, subsys pointer is null!\n"); - return false; - } - - char* substr = NULL; - if (!TakeNthWord(pLine, MOUNT_SUBSTR_GAP, &substr)) { - return false; - } - - return strstr(substr, subsys) != NULL; -} - -typedef char *(*ParseFileLine)(char *, const char *); -static bool GetFileInfo(const char* resolvedPath, char* buffer, const int bufferSize, const ParseFileLine fn) -{ - FILE *fp = NULL; - char *line = NULL; - size_t len = 0; - char *result = NULL; - fp = fopen(resolvedPath, "r"); - if (fp == NULL) { - Logger("cannot open file.", LEVEL_ERROR, SCREEN_YES); - return false; - } - - while (getline(&line, &len, fp) != -1) { - result = fn(line, "devices"); - if (result != NULL && strlen(result) < bufferSize) { - break; - } - } - - errno_t ret = strcpy_s(buffer, bufferSize, result); - free(line); - fclose(fp); - if (ret != EOK) { - return false; - } - return true; -} - -int ParseFileByLine(char* buffer, int bufferSize, const ParseFileLine fn, const char* filepath) -{ - if (buffer == NULL || filepath == NULL) { - (void)fprintf(stderr, "buffer, filepath pointer is null!\n"); - return -1; - } - - char resolvedPath[PATH_MAX] = {0x0}; - - if (realpath(filepath, resolvedPath) == NULL && errno != ENOENT) { - Logger("Cannot canonicalize path.", LEVEL_ERROR, SCREEN_YES); - return -1; - } - const size_t maxFileSzieMb = 1024; // max 1G - if (!CheckExternalFile(resolvedPath, strlen(resolvedPath), maxFileSzieMb, true)) { - Logger("Check file legality failed.", LEVEL_ERROR, SCREEN_YES); - return -1; - } - if (!GetFileInfo(resolvedPath, buffer, bufferSize, fn)) { - return -1; - } - - return 0; -} - -char *GetCgroupMount(char *line, const char *subsys) -{ - if (line == NULL || subsys == NULL) { - (void)fprintf(stderr, "line, subsys pointer is null!\n"); - return NULL; - } - - if (!CheckRootDir(&line)) { - return NULL; - } - - char *mountPoint = NULL; - mountPoint = strsep(&line, " "); - line = strchr(line, '-'); - if (mountPoint == NULL || *mountPoint == '\0') { - return NULL; - } - - if (!CheckFsType(&line)) { - return NULL; - } - - if (!CheckSubStr(&line, subsys)) { - return NULL; - } - - return mountPoint; -} - -char *GetCgroupRoot(char *line, const char *subSystem) -{ - if (line == NULL || subSystem == NULL) { - (void)fprintf(stderr, "line, subSystem pointer is null!\n"); - return NULL; - } - - char *token = NULL; - int i; - for (i = 0; i < ROOT_SUBSTR_GAP; ++i) { - token = strsep(&line, ":"); - if (token == NULL || *token == '\0') { - return NULL; - } - } - - char *rootDir = strsep(&line, ":"); - if (rootDir == NULL || *rootDir == '\0') { - return NULL; - } - - if (strlen(rootDir) >= BUF_SIZE || StrHasPrefix(rootDir, "/..")) { - return NULL; - } - if (strstr(token, subSystem) == NULL) { - return NULL; - } - return rootDir; -} - -int SetupDeviceCgroup(FILE *cgroupAllow, const char *devName) -{ - if (cgroupAllow == NULL || devName == NULL) { - (void)fprintf(stderr, "cgroupAllow, devName pointer is null!\n"); - return -1; - } - - int ret; - struct stat devStat; - char devPath[BUF_SIZE]; - - ret = sprintf_s(devPath, BUF_SIZE, "/dev/%s", devName); - if (ret < 0) { - char* str = FormatLogMessage("failed to assemble dev path for %s.", devName); - Logger(str, LEVEL_ERROR, SCREEN_YES); - free(str); - return -1; - } - - ret = stat((const char *)devPath, &devStat); - if (ret < 0) { - Logger("Failed to get stat of devpath.", LEVEL_ERROR, SCREEN_YES); - return -1; - } - - bool isFailed = fprintf(cgroupAllow, "c %u:%u rw", major(devStat.st_rdev), minor(devStat.st_rdev)) < 0 || - fflush(cgroupAllow) == EOF || ferror(cgroupAllow) < 0; - if (isFailed) { - Logger("write devices failed.", LEVEL_ERROR, SCREEN_YES); - return -1; - } - - return 0; -} - -int SetupDriverCgroup(FILE *cgroupAllow) -{ - if (cgroupAllow == NULL) { - (void)fprintf(stderr, "cgroupAllow pointer is null!\n"); - return -1; - } - - int ret; - ret = SetupDeviceCgroup(cgroupAllow, DAVINCI_MANAGER); - if (ret < 0) { - char* str = FormatLogMessage("failed to setup cgroup for %s.", DAVINCI_MANAGER); - Logger(str, LEVEL_ERROR, SCREEN_YES); - free(str); - return -1; - } - - bool is200Rc = false; - if (!DoMounting200RC(&is200Rc)) { - return -1; - } - if (is200Rc) { - return 0; - } - - ret = SetupDeviceCgroup(cgroupAllow, DEVMM_SVM); - if (ret < 0) { - char* str = FormatLogMessage("failed to setup cgroup for %s.", DEVMM_SVM); - Logger(str, LEVEL_ERROR, SCREEN_YES); - free(str); - return -1; - } - - ret = SetupDeviceCgroup(cgroupAllow, HISI_HDC); - if (ret < 0) { - char* str = FormatLogMessage("failed to setup cgroup for %s.", HISI_HDC); - Logger(str, LEVEL_ERROR, SCREEN_YES); - free(str); - return -1; - } - - return 0; -} - -int GetCgroupPath(const long pid, char *effPath, size_t maxSize) -{ - if (effPath == NULL) { - (void)fprintf(stderr, "effPath pointer is null!\n"); - return -1; - } - - int ret; - char mountPath[BUF_SIZE] = {0x0}; - char mount[BUF_SIZE] = {0x0}; - - ret = sprintf_s(mountPath, BUF_SIZE, "/proc/%d/mountinfo", (int)getppid()); - if (ret < 0) { - char* str = FormatLogMessage("assemble mount info path failed: ppid(%d).", getppid()); - Logger(str, LEVEL_ERROR, SCREEN_YES); - free(str); - return -1; - } - - ret = ParseFileByLine(mount, BUF_SIZE, GetCgroupMount, mountPath); - if (ret < 0) { - Logger("cat file content failed.", LEVEL_ERROR, SCREEN_YES); - return -1; - } - - char cgroup[BUF_SIZE] = {0x0}; - char cgroupPath[BUF_SIZE] = {0x0}; - ret = sprintf_s(cgroupPath, BUF_SIZE, "/proc/%d/cgroup", pid); - if (ret < 0) { - char* str = FormatLogMessage("assemble cgroup path failed: pid(%d).", pid); - Logger(str, LEVEL_ERROR, SCREEN_YES); - free(str); - return -1; - } - - ret = ParseFileByLine(cgroup, BUF_SIZE, GetCgroupRoot, cgroupPath); - if (ret < 0) { - Logger("cat file content failed.", LEVEL_ERROR, SCREEN_YES); - return -1; - } - - // cut last '\n' off - cgroup[strcspn(cgroup, "\n")] = '\0'; - - ret = sprintf_s(effPath, maxSize, "%s%s%s", mount, cgroup, ALLOW_PATH); - if (ret < 0) { - Logger("assemble cgroup device path failed.", LEVEL_ERROR, SCREEN_YES); - return -1; - } - - return 0; -} - -static bool SetupCgroupProcess(const char* resolvedCgroupPath, const struct ParsedConfig *config) -{ - char *str = NULL; - FILE *cgroupAllow = NULL; - char deviceName[BUF_SIZE] = {0}; - cgroupAllow = fopen(resolvedCgroupPath, "a"); - if (cgroupAllow == NULL) { - Logger("failed to open cgroup file.", LEVEL_ERROR, SCREEN_YES); - return false; - } - - if (SetupDriverCgroup(cgroupAllow) < 0) { - fclose(cgroupAllow); - Logger("failed to setup driver cgroup.", LEVEL_ERROR, SCREEN_YES); - return false; - } - for (size_t idx = 0; idx < config->devicesNr; idx++) { - if (sprintf_s(deviceName, BUF_SIZE, "%s%u", - (IsVirtual() ? VDEVICE_NAME : DEVICE_NAME), - config->devices[idx]) < 0) { - fclose(cgroupAllow); - str = FormatLogMessage("failed to assemble device path for no.%u.", config->devices[idx]); - Logger(str, LEVEL_ERROR, SCREEN_YES); - free(str); - return false; - } - - if (SetupDeviceCgroup(cgroupAllow, (const char *)deviceName) < 0) { - fclose(cgroupAllow); - Logger("failed to setup cgroup.", LEVEL_ERROR, SCREEN_YES); - return false; - } - } - free(str); - fclose(cgroupAllow); - return true; -} - -int SetupCgroup(const struct ParsedConfig *config) -{ - if (config == NULL) { - (void)fprintf(stderr, "config pointer is null!\n"); - return -1; - } - - char resolvedCgroupPath[PATH_MAX] = {0}; - if (realpath(config->cgroupPath, resolvedCgroupPath) == NULL && errno != ENOENT) { - Logger("cannot canonicalize cgroup.", LEVEL_ERROR, SCREEN_YES); - return -1; - } - const size_t maxFileSzieMb = 1024; // max 1G - if (!CheckExternalFile(resolvedCgroupPath, strlen(resolvedCgroupPath), maxFileSzieMb, true)) { - Logger("Check file legality failed.", LEVEL_ERROR, SCREEN_YES); - return -1; - } - if (!SetupCgroupProcess(resolvedCgroupPath, config)) { - return -1; - } - - return 0; -} \ No newline at end of file diff --git a/cli/src/main.c b/cli/src/main.c index 5048bd2..bf7a6e7 100644 --- a/cli/src/main.c +++ b/cli/src/main.c @@ -37,8 +37,9 @@ #define MAX_ARGC 1024 #define MAX_ARG_LEN 1024 +bool g_allowLink = false; + struct CmdArgs { - char devices[BUF_SIZE]; char rootfs[BUF_SIZE]; long pid; char options[BUF_SIZE]; @@ -47,6 +48,7 @@ struct CmdArgs { }; static struct option g_cmdOpts[] = { + {"allow-link", required_argument, 0, 'l'}, {"devices", required_argument, 0, 'd'}, {"pid", required_argument, 0, 'p'}, {"rootfs", required_argument, 0, 'r'}, @@ -58,33 +60,6 @@ static struct option g_cmdOpts[] = { typedef bool (*CmdArgParser)(struct CmdArgs *args, const char *arg); -static bool DevicesCmdArgParser(struct CmdArgs *args, const char *arg) -{ - if (args == NULL || arg == NULL) { - Logger("args, arg pointer is null!", LEVEL_ERROR, SCREEN_YES); - return false; - } - if (strlen(arg) > MAX_ARG_LEN) { - Logger("argument value too long!", LEVEL_ERROR, SCREEN_YES); - return false; - } - - for (size_t iLoop = 0; iLoop < strlen(arg); iLoop++) { - if ((isdigit(arg[iLoop]) == 0) && (arg[iLoop] != ',')) { - Logger("failed to check devices.", LEVEL_ERROR, SCREEN_YES); - return false; - } - } - - errno_t err = strcpy_s(args->devices, BUF_SIZE, arg); - if (err != EOK) { - Logger("failed to get devices from cmd args.", LEVEL_ERROR, SCREEN_YES); - return false; - } - - return true; -} - static bool PidCmdArgParser(struct CmdArgs *args, const char *arg) { char buff[PATH_MAX] = {0}; @@ -152,7 +127,7 @@ static bool CheckFileLegality(const char* filePath, const size_t filePathLen, Logger("realpath failed!", LEVEL_ERROR, SCREEN_YES); return false; } - if (strcmp(resolvedPath, filePath) != 0) { // 存在软链接 + if (!g_allowLink && strcmp(resolvedPath, filePath) != 0) { // 存在软链接 Logger("filePath has a soft link!", LEVEL_ERROR, SCREEN_YES); return false; } @@ -210,14 +185,21 @@ static bool CheckWhiteList(const char* fileName) } bool fileExists = false; const char mountWhiteList[WHITE_LIST_NUM][PATH_MAX] = {{"/usr/local/Ascend/driver/lib64"}, - {"/usr/local/Ascend/driver/include"}, - {"/usr/local/dcmi"}, - {"/usr/local/bin/npu-smi"}, - {"/home/data/miniD/driver/lib64"}, - {"/usr/local/sbin/npu-smi"}, - {"/usr/local/Ascend/driver/tools"}, - {"/etc/hdcBasic.cfg"}, - {"/etc/sys_version.conf"} + {"/usr/local/Ascend/driver/include"}, {"/usr/local/dcmi"}, {"/usr/local/bin/npu-smi"}, + {"/home/data/miniD/driver/lib64"}, {"/usr/local/sbin/npu-smi"}, + {"/usr/local/Ascend/driver/tools"}, {"/etc/hdcBasic.cfg"}, {"/etc/sys_version.conf"}, + {"/etc/ld.so.conf.d/mind_so.conf"}, {"/etc/slog.conf"}, {"/etc/ascend_install.info"}, + {"/var/dmp_daemon"}, {"/var/davinci/driver/version.info"}, {"/var/slogd"}, + {"/usr/lib64/libsemanage.so.2"}, {"/usr/lib64/libmmpa.so"}, {"/usr/lib64/libcrypto.so.1.1"}, + {"/usr/lib64/libdrvdsmi.so"}, {"/usr/lib64/libdcmi.so"}, {"/usr/lib64/libstackcore.so"}, + {"/usr/lib64/libascend_drvdmp.so"}, {"/usr/lib64/libdsmiproduct.so"}, {"/usr/lib64/libiam.so.1"}, + {"/usr/lib64/libascend_drv_baselib.so"}, {"/usr/lib64/libascend_hal.so"}, {"/usr/lib64/libslog.so"}, + {"/usr/lib64/libc_sec.so"}, {"/usr/lib64/libascend_drvupgrade.so"}, {"/usr/lib64/libeasy_comm.so.1"}, + {"/usr/lib64/libfault_event.so.1"}, {"/usr/lib64/libheartbeat.so"}, {"/usr/lib64/libxshmem.so.1"}, + {"/usr/lib64/libdevmmap.so"}, {"/usr/lib64/libmpi_dvpp_adapter.so"}, {"/usr/lib64/libaicpu_scheduler.so"}, + {"/usr/lib64/libaicpu_processer.so"}, {"/usr/lib64/libaicpu_prof.so"}, {"/usr/lib64/libaicpu_sharder.so"}, + {"/usr/lib64/libadump.so"}, {"/usr/lib64/libtsd_eventclient.so"}, {"/usr/lib64/libmsprof.so"}, + {"/usr/lib64/aicpu_kernels"}, {"/root/hdc_ppc"} }; for (size_t iLoop = 0; iLoop < WHITE_LIST_NUM; iLoop++) { @@ -299,12 +281,33 @@ static bool MountDirCmdArgParser(struct CmdArgs *args, const char *arg) return CheckWhiteList(dst) ? true : false; } +static bool LinkCheckCmdArgParser(const char *argv) +{ + if (argv == NULL) { + Logger("link arg pointer is null!", LEVEL_ERROR, SCREEN_YES); + return false; + } + + if (strcmp(argv, "True") == 0) { + g_allowLink = true; + return true; + } + if (strcmp(argv, "False") == 0) { + g_allowLink = false; + return true; + } + + Logger("invalid link check value!", LEVEL_ERROR, SCREEN_YES); + return false; +} + #define NUM_OF_CMD_ARGS 6 static struct { const char c; CmdArgParser parser; } g_cmdArgParsers[NUM_OF_CMD_ARGS] = { + {'l', LinkCheckCmdArgParser}, {'p', PidCmdArgParser}, {'r', RootfsCmdArgParser}, {'o', OptionsCmdArgParser}, @@ -326,7 +329,13 @@ static int ParseOneCmdArg(struct CmdArgs *args, char indicator, const char *valu } } - bool isOK = g_cmdArgParsers[i].parser(args, value); + bool isOK; + if (i == 0) { + isOK = LinkCheckCmdArgParser(value); + } else { + isOK = g_cmdArgParsers[i].parser(args, value); + } + if (!isOK) { char* str = FormatLogMessage("failed while parsing cmd arg, indicate char: %c, value: %s.", indicator, value); Logger(str, LEVEL_ERROR, SCREEN_YES); @@ -345,44 +354,6 @@ static inline bool IsCmdArgsValid(const struct CmdArgs *args) return (strlen(args->rootfs) > 0) && (args->pid > 0); } -static int ParseDeviceIDs(size_t *idList, size_t *idListSize, char *devices) -{ - if (idList == NULL || idListSize == NULL || devices == NULL) { - Logger("idList, idListSize, devices pointer is null!", LEVEL_ERROR, SCREEN_YES); - return -1; - } - - static const char *sep = ","; - char *token = NULL; - char *context = NULL; - size_t idx = 0; - - token = strtok_s(devices, sep, &context); - while (token != NULL && idx < *idListSize) { - if (idx >= *idListSize) { - char* str = FormatLogMessage("too many devices(%u), support %u devices maximally", idx, *idListSize); - Logger(str, LEVEL_ERROR, SCREEN_YES); - free(str); - return -1; - } - - errno = 0; - idList[idx] = strtoul((const char *)token, NULL, DECIMAL); - if (errno != 0) { - char* str = FormatLogMessage("failed to convert device id (%s) from cmd args", token); - Logger(str, LEVEL_ERROR, SCREEN_YES); - free(str); - return -1; - } - - idx++; - token = strtok_s(NULL, sep, &context); - } - - *idListSize = idx; - return 0; -} - int DoPrepare(const struct CmdArgs *args, struct ParsedConfig *config) { if (args == NULL || config == NULL) { @@ -399,12 +370,6 @@ int DoPrepare(const struct CmdArgs *args, struct ParsedConfig *config) return -1; } - ret = ParseDeviceIDs(config->devices, &config->devicesNr, (char *)args->devices); - if (ret < 0) { - Logger("failed to parse device ids from cmdline argument", LEVEL_ERROR, SCREEN_YES); - return -1; - } - ret = GetNsPath(args->pid, "mnt", config->containerNsPath, BUF_SIZE); if (ret < 0) { char* str = FormatLogMessage("failed to get container mnt ns path: pid(%d).", args->pid); @@ -444,8 +409,6 @@ int SetupContainer(struct CmdArgs *args) int ret; struct ParsedConfig config; - InitParsedConfig(&config); - Logger("prepare necessary config", LEVEL_INFO, SCREEN_YES); ret = DoPrepare(args, &config); if (ret < 0) { @@ -499,7 +462,7 @@ int Process(int argc, char **argv) struct CmdArgs args = {0}; Logger("runc start prestart-hook ...", LEVEL_INFO, SCREEN_YES); - while ((c = getopt_long(argc, argv, "d:p:r:o:f:i", g_cmdOpts, NULL)) != -1) { + while ((c = getopt_long(argc, argv, "l:p:r:o:f:i", g_cmdOpts, NULL)) != -1) { ret = ParseOneCmdArg(&args, (char)c, optarg); if (ret < 0) { Logger("failed to parse cmd args.", LEVEL_ERROR, SCREEN_YES); diff --git a/cli/src/u_mount.c b/cli/src/u_mount.c index 6541af5..03f444f 100644 --- a/cli/src/u_mount.c +++ b/cli/src/u_mount.c @@ -29,7 +29,7 @@ static bool checkSrcFile(const char *src) { struct stat fileStat; - if (stat(src, &fileStat) != 0) { + if (lstat(src, &fileStat) != 0) { return -1; // 待挂载源文件不存在 } if ((S_ISREG(fileStat.st_mode) != 0) || (S_ISDIR(fileStat.st_mode) != 0)) { // 只校验文件和目录 @@ -78,156 +78,6 @@ int Mount(const char *src, const char *dst) return 0; } -static bool GetDeviceCheckParam(const char *rootfs, const char *srcDeviceName, - struct PathInfo* pathInfo) -{ - if (rootfs == NULL || srcDeviceName == NULL || pathInfo == NULL) { - Logger("rootfs, srcDeviceName, pathInfo pointer are null!", LEVEL_ERROR, SCREEN_YES); - return false; - } - return true; -} - -static int GetDeviceMntSrcDstProcess(const char *rootfs, const char *srcDeviceName, - const char *dstDeviceName, struct PathInfo* pathInfo) -{ - if (!GetDeviceCheckParam(rootfs, srcDeviceName, pathInfo)) { - return -1; - } - int ret = 0; - errno_t err; - char unresolvedDst[BUF_SIZE] = {0}; - char resolvedDst[PATH_MAX] = {0}; - size_t srcBufSize = pathInfo->srcLen; - size_t dstBufSize = pathInfo->dstLen; - char *src = pathInfo->src; - char *dst = pathInfo->dst; - - ret = sprintf_s(src, srcBufSize, "/dev/%s", srcDeviceName); - if (ret < 0) { - return -1; - } - ret = sprintf_s(unresolvedDst, BUF_SIZE, "%s%s", rootfs, src); - if (ret < 0) { - return -1; - } - if (realpath(unresolvedDst, resolvedDst) == NULL && errno != ENOENT) { - Logger("cannot canonicalize device dst.", LEVEL_ERROR, SCREEN_YES); - return -1; - } - if (dstDeviceName != NULL) { - ret = sprintf_s(dst, dstBufSize, "%s/dev/%s", rootfs, dstDeviceName); - if (ret < 0) { - return -1; - } - } else { - err = strcpy_s(dst, dstBufSize, resolvedDst); - if (err != EOK) { - Logger("failed to copy resolved device mnt path to dst.", LEVEL_ERROR, SCREEN_YES); - return -1; - } - } - return 0; -} - -static int GetDeviceMntSrcDst(const char *rootfs, const char *srcDeviceName, - const char *dstDeviceName, struct PathInfo* pathInfo) -{ - if (!GetDeviceCheckParam(rootfs, srcDeviceName, pathInfo)) { - return -1; - } - - int ret = VerifyPathInfo(pathInfo); - if (ret < 0) { - return -1; - } - - return GetDeviceMntSrcDstProcess(rootfs, srcDeviceName, dstDeviceName, pathInfo); -} - -static bool MountDeviceProcess(const char* dst, const char* src, const mode_t mode) -{ - int ret; - errno = 0; - struct stat dstStat; - ret = stat(dst, &dstStat); - if (ret == 0 && S_ISCHR(dstStat.st_mode)) { - return true; // 特权容器自动挂载HOST所有设备,故此处跳过 - } else if (ret == 0) { - Logger("dst already exists but not a char device as expected.", LEVEL_ERROR, SCREEN_YES); - return false; - } else if (ret < 0 && errno != ENOENT) { - Logger("failed to check dst stat", LEVEL_ERROR, SCREEN_YES); - return false; - } - ret = MakeMountPoints(dst, mode); - if (ret < 0) { - Logger("failed to create mount dst file.", LEVEL_ERROR, SCREEN_YES); - return false; - } - - ret = Mount(src, dst); - if (ret < 0) { - Logger("failed to mount dev.", LEVEL_ERROR, SCREEN_YES); - return false; - } - return true; -} - -int MountDevice(const char *rootfs, const char *srcDeviceName, const char *dstDeviceName) -{ - int ret; - char src[BUF_SIZE] = {0}; - char dst[BUF_SIZE] = {0}; - struct PathInfo pathInfo = {src, BUF_SIZE, dst, BUF_SIZE}; - ret = GetDeviceMntSrcDst(rootfs, srcDeviceName, dstDeviceName, &pathInfo); - if (ret < 0) { - Logger("failed to get mount src and dst path.", LEVEL_ERROR, SCREEN_YES); - return -1; - } - - struct stat srcStat; - ret = stat((const char *)src, &srcStat); - if (ret < 0) { - Logger("failed to stat src.", LEVEL_ERROR, SCREEN_YES); - return -1; - } - if (!MountDeviceProcess(dst, src, srcStat.st_mode)) { - return -1; - } - - return 0; -} - -int DoDeviceMounting(const char *rootfs, const char *device_name, const size_t ids[], size_t idsNr) -{ - if (rootfs == NULL || device_name == NULL || ids == NULL) { - Logger("rootfs, device_name pointer is null!", LEVEL_ERROR, SCREEN_YES); - return -1; - } - - char srcDeviceName[BUF_SIZE] = {0}; - char dstDeviceName[BUF_SIZE] = {0}; - - for (size_t idx = 0; idx < idsNr; idx++) { - int srcRet = sprintf_s(srcDeviceName, BUF_SIZE, "%s%u", device_name, ids[idx]); - int dstRet = sprintf_s(dstDeviceName, BUF_SIZE, "%s%u", DEVICE_NAME, ids[idx]); - if (srcRet < 0 || dstRet < 0) { - char* str = FormatLogMessage("assemble device name failed, id: %u.", ids[idx]); - Logger(str, LEVEL_ERROR, SCREEN_YES); - free(str); - return -1; - } - int ret = MountDevice(rootfs, srcDeviceName, dstDeviceName); - if (ret < 0) { - Logger("failed to mount device.", LEVEL_ERROR, SCREEN_YES); - return -1; - } - } - - return 0; -} - int MountFile(const char *rootfs, const char *filepath) { if (rootfs == NULL || filepath == NULL) { @@ -301,72 +151,6 @@ int MountDir(const char *rootfs, const char *src) return 0; } -bool DoMounting200RC(bool* is200Rc) -{ - char devmmPath[PATH_MAX] = {0}; - char hisiPath[PATH_MAX] = {0}; - if ((sprintf_s(devmmPath, PATH_MAX, "/dev/%s", DEVMM_SVM) < 0) || - (sprintf_s(hisiPath, PATH_MAX, "/dev/%s", HISI_HDC) < 0)) { - Logger("failed to assemble dev path.", LEVEL_ERROR, SCREEN_YES); - return false; - } - struct stat devStat; // 200 soc 不需要挂载此两个设备 - if ((stat(devmmPath, &devStat) != 0) && (stat(hisiPath, &devStat) != 0)) { - Logger("200 Soc.", LEVEL_ERROR, SCREEN_YES); - *is200Rc = true; - } - return true; -} - -static bool DoMountingDevice(const char *rootfs) -{ - int ret = MountDevice(rootfs, DEVMM_SVM, NULL); - if (ret < 0) { - char* str = FormatLogMessage("failed to mount device %s.", DEVMM_SVM); - Logger(str, LEVEL_ERROR, SCREEN_YES); - free(str); - return false; - } - - ret = MountDevice(rootfs, HISI_HDC, NULL); - if (ret < 0) { - char* str = FormatLogMessage("failed to mount device %s.", HISI_HDC); - Logger(str, LEVEL_ERROR, SCREEN_YES); - free(str); - return false; - } - return true; -} - -int DoCtrlDeviceMounting(const char *rootfs) -{ - if (rootfs == NULL) { - Logger("rootfs pointer is null!", LEVEL_ERROR, SCREEN_YES); - return -1; - } - - /* device */ - int ret = MountDevice(rootfs, DAVINCI_MANAGER, NULL); - if (ret < 0) { - char* str = FormatLogMessage("failed to mount device %s.", DAVINCI_MANAGER); // error1 - Logger(str, LEVEL_ERROR, SCREEN_YES); - free(str); - return -1; - } - bool is200Rc = false; - if (!DoMounting200RC(&is200Rc)) { - return -1; - } - if (is200Rc) { - return 0; - } - if (!DoMountingDevice(rootfs)) { - return -1; - } - - return 0; -} - int DoDirectoryMounting(const char *rootfs, const struct MountList *list) { if (rootfs == NULL || list == NULL) { diff --git a/cli/src/utils.c b/cli/src/utils.c index 94c93e0..8f56b03 100644 --- a/cli/src/utils.c +++ b/cli/src/utils.c @@ -30,6 +30,7 @@ #define LOG_LENGTH 1024 static bool g_checkWgroup = true; +bool g_allowLink; char *FormatLogMessage(char *format, ...) { @@ -252,6 +253,7 @@ static bool CheckLegality(const char* filePath, const size_t filePathLen, } struct stat fileStat; if ((lstat(buf, &fileStat) != 0) || + (!g_allowLink && (S_ISLNK(fileStat.st_mode) != 0)) || ((S_ISREG(fileStat.st_mode) == 0) && (S_ISDIR(fileStat.st_mode) == 0))) { return ShowExceptionInfo("filePath does not exist or is not a file/dir!"); } @@ -324,7 +326,7 @@ static bool CheckFileSubset(const char* filePath, const size_t filePathLen, if (lstat(filePath, &fileStat) != 0) { return ShowExceptionInfo("filePath does not exist!"); } - if (S_ISLNK(fileStat.st_mode) != 0) { // 存在软链接 + if (!g_allowLink && S_ISLNK(fileStat.st_mode) != 0) { // 存在软链接 return ShowExceptionInfo("filePath is symbolic link!"); } if (fileStat.st_size >= maxFileSzieB) { // 文件大小超限 @@ -359,7 +361,7 @@ bool GetFileSubsetAndCheck(const char *basePath, const size_t basePathLen) if (!CheckFileSubset(base, strlen(base), maxFileSzieMb)) { return false; } - } else if (ptr->d_type == DT_LNK) { // 软链接 + } else if (!g_allowLink && ptr->d_type == DT_LNK) { // 软链接 return ShowExceptionInfo("FilePath has a soft link!"); } else if (ptr->d_type == DT_DIR) { // 目录 if (!GetFileSubsetAndCheck(base, strlen(base))) { diff --git a/destroy/src/CMakeLists.txt b/destroy/src/CMakeLists.txt index ad64a49..eb0ca19 100644 --- a/destroy/src/CMakeLists.txt +++ b/destroy/src/CMakeLists.txt @@ -11,6 +11,6 @@ include_directories("${PROJECT_SOURCE_DIR}/../../platform/libboundscheck/include include_directories("${PROJECT_SOURCE_DIR}/../../cli/src") aux_source_directory(. SRC) add_subdirectory(${CMAKE_CURRENT_SOURCE_DIR}/../../build/libboundscheck ${CMAKE_CURRENT_SOURCE_DIR}/../../build/libboundscheck) -add_executable(ascend-docker-destroy ../../cli/src/logger.c ../../cli/src/utils.c ../../cli/src/basic.c ${SRC} ) +add_executable(ascend-docker-destroy ../../cli/src/logger.c ../../cli/src/utils.c ${SRC} ) target_compile_options(ascend-docker-destroy PRIVATE -fstack-protector-all -fpie -ldl -D_FORTIFY_SOURCE=2 -O2) target_link_libraries(ascend-docker-destroy -ldl -pie -Wl,-s,-z,now libboundscheck) diff --git a/hook/main.go b/hook/main.go index f7af535..48381f8 100644 --- a/hook/main.go +++ b/hook/main.go @@ -41,6 +41,7 @@ const ( ascendRuntimeOptions = "ASCEND_RUNTIME_OPTIONS" ascendRuntimeMounts = "ASCEND_RUNTIME_MOUNTS" ascendVisibleDevices = "ASCEND_VISIBLE_DEVICES" + ascendAllowLink = "ASCEND_ALLOW_LINK" ascendDockerCli = "ascend-docker-cli" defaultAscendDockerCli = "/usr/local/bin/ascend-docker-cli" configDir = "/etc/ascend-docker-runtime.d" @@ -151,6 +152,17 @@ func parseRuntimeOptions(runtimeOptions string) ([]string, error) { return parsedOptions, nil } +func parseSoftLinkMode(allowLink string) (string, error) { + if allowLink == "True" { + return "True", nil + } + if allowLink == "" || allowLink == "False" { + return "False", nil + } + + return "", fmt.Errorf("invalid soft link option") +} + func parseOciSpecFile(file string) (*specs.Spec, error) { f, err := os.Open(file) if err != nil { @@ -308,10 +320,10 @@ func readConfigsOfDir(dir string, configs []string) ([]string, []string, error) } func getArgs(cliPath string, containerConfig *containerConfig, fileMountList []string, - dirMountList []string) []string { + dirMountList []string, allowLink string) []string { args := append([]string{cliPath}, - - "--pid", fmt.Sprintf("%d", containerConfig.Pid), "--rootfs", containerConfig.Rootfs) + "--allow-link", allowLink, "--pid", fmt.Sprintf("%d", containerConfig.Pid), + "--rootfs", containerConfig.Rootfs) for _, filePath := range fileMountList { args = append(args, "--mount-file", filePath) } @@ -324,7 +336,11 @@ func getArgs(cliPath string, containerConfig *containerConfig, fileMountList []s func doPrestartHook() error { containerConfig, err := getContainerConfig() if err != nil { - return fmt.Errorf("failed to get container config: %v", err) + return fmt.Errorf("failed to get container config: %#v", err) + } + + if visibleDevices := getValueByKey(containerConfig.Env, ascendVisibleDevices); visibleDevices == "" { + return nil } if visibleDevices := getValueByKey(containerConfig.Env, ascendVisibleDevices); visibleDevices == "" { @@ -335,27 +351,32 @@ func doPrestartHook() error { fileMountList, dirMountList, err := readConfigsOfDir(configDir, mountConfigs) if err != nil { - return fmt.Errorf("failed to read configuration from config directory: %v", err) + return fmt.Errorf("failed to read configuration from config directory: %#v", err) } parsedOptions, err := parseRuntimeOptions(getValueByKey(containerConfig.Env, ascendRuntimeOptions)) if err != nil { - return fmt.Errorf("failed to parse runtime options: %v", err) + return fmt.Errorf("failed to parse runtime options: %#v", err) + } + + allowLink, err := parseSoftLinkMode(getValueByKey(containerConfig.Env, ascendAllowLink)) + if err != nil { + return fmt.Errorf("failed to parse soft link mode: %#v", err) } currentExecPath, err := os.Executable() if err != nil { - return fmt.Errorf("cannot get the path of ascend-docker-hook: %v", err) + return fmt.Errorf("cannot get the path of ascend-docker-hook: %#v", err) } cliPath := path.Join(path.Dir(currentExecPath), ascendDockerCliName) if _, err = os.Stat(cliPath); err != nil { - return fmt.Errorf("cannot find ascend-docker-cli executable file at %s: %v", cliPath, err) + return fmt.Errorf("cannot find ascend-docker-cli executable file at %s: %#v", cliPath, err) } if _, err := mindxcheckutils.RealFileChecker(cliPath, true, false, mindxcheckutils.DefaultSize); err != nil { return err } - args := getArgs(cliPath, containerConfig, fileMountList, dirMountList) + args := getArgs(cliPath, containerConfig, fileMountList, dirMountList, allowLink) if len(parsedOptions) > 0 { args = append(args, "--options", strings.Join(parsedOptions, ",")) } diff --git a/runtime/main.go b/runtime/main.go index 845eb2a..d8bc5b9 100644 --- a/runtime/main.go +++ b/runtime/main.go @@ -47,6 +47,8 @@ const ( davinciManager = "davinci_manager" devmmSvm = "devmm_svm" hisiHdc = "hisi_hdc" + svm0 = "svm0" + tsAisle = "ts_aisle" maxCommandLength = 65535 hookCli = "ascend-docker-hook" destroyHookCli = "ascend-docker-destroy" @@ -337,6 +339,11 @@ func addManagerDevice(spec *specs.Spec) error { if err = addDeviceToSpec(spec, svmPath, false); err != nil { return fmt.Errorf("failed to add devmm_svm to spec : %#v", err) } + } else { + // do nothing when device is not exist. + if !os.IsNotExist(err) { + return fmt.Errorf("stat devmm_svm device err: %#v", err) + } } hdcPath := devicePath + hisiHdc @@ -344,6 +351,32 @@ func addManagerDevice(spec *specs.Spec) error { if err = addDeviceToSpec(spec, hdcPath, false); err != nil { return fmt.Errorf("failed to add hisi_hdc device to spec : %#v", err) } + } else { + if !os.IsNotExist(err) { + return fmt.Errorf("stat hisi_hdc device err: %#v", err) + } + } + + svm0Path := devicePath + svm0 + if _, err := os.Stat(svm0Path); err == nil { + if err = addDeviceToSpec(spec, svm0Path, false); err != nil { + return fmt.Errorf("failed to add svm0 device to spec : %#v", err) + } + } else { + if !os.IsNotExist(err) { + return fmt.Errorf("stat svm0 device err: %#v", err) + } + } + + tsAislePath := devicePath + tsAisle + if _, err := os.Stat(tsAislePath); err == nil { + if err = addDeviceToSpec(spec, tsAislePath, false); err != nil { + return fmt.Errorf("failed to add tsAisle device to spec : %#v", err) + } + } else { + if !os.IsNotExist(err) { + return fmt.Errorf("stat tsAisle device err: %#v", err) + } } return nil