Files
enginex-ascend-910-vllm/csrc/scripts/package/common/sh/install_common_parser.sh
Sun Ruoxi 7f8a1b1f7a init v0.23.0
Signed-off-by: Sun Ruoxi <sunruoxi@4paradigm.com>
2026-08-27 15:11:51 +08:00

2193 lines
67 KiB
Bash
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

#!/bin/sh
# -----------------------------------------------------------------------------------------------------------
# Copyright (c) 2025 Huawei Technologies Co., Ltd.
# This program is free software, you can redistribute it and/or modify it under the terms and conditions of
# CANN Open Software License Agreement Version 2.0 (the "License").
# Please refer to the License for details. You may not use this file except in compliance with the License.
# THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND, EITHER EXPRESS OR IMPLIED,
# INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT, MERCHANTABILITY, OR FITNESS FOR A PARTICULAR PURPOSE.
# See LICENSE in the root of the software repository for the full text of the License.
# -----------------------------------------------------------------------------------------------------------
# run包安装解析公共脚本
# 解析filelist.csv文件完成目录创建文件复制权限设置文件删除等操作。
# minirc场景下存在使用dash调用该脚本的情况
#export PS4='+ ${FUNCNAME[0]:+${FUNCNAME[0]}():} ${BASH_SOURCE}:${LINENO}: '
#set -x
# 总uninstall.sh文件权限
TOTAL_UNINSTALL_MOD="500"
# db.info文件权限
DB_INFO_MOD="640"
# 包架构
PKG_ARCH="UNKNOWN"
# 复制文件是否并发
PARALLEL=""
# 是否限制并发
PARALLEL_LIMIT=""
# 控制并发的fifo文件路径
PARALLEL_FIFO="none"
COPY_COMMAND="cp -rf"
MOVE_COMMAND="mv -f"
curpath="$(dirname $(readlink -f "${BASH_SOURCE:-$0}"))"
# 导入公共库
common_func_v2_path="${curpath}/common_func_v2.inc"
. "${common_func_v2_path}"
# 导入common_func.inc
# 不一定能source到common_func.inc
# 例如driver包中的install_common_parser.sh与common_func.inc不在同一个目录下
# 需要子包整改才将该if语句移除
common_func_path="${curpath}/common_func.inc"
if [ -f "${common_func_path}" ]; then
. "${common_func_path}"
fi
# 导入script_operator.inc
script_operator_path="${curpath}/script_operator.inc"
if [ -f "${script_operator_path}" ]; then
. "${script_operator_path}"
fi
# 导入version_cfg.inc
version_cfg_path="${curpath}/version_cfg.inc"
if [ -f "${version_cfg_path}" ]; then
. "${version_cfg_path}"
fi
# 导入multi_version.inc
multi_version_path="${curpath}/multi_version.inc"
if [ -f "${multi_version_path}" ]; then
. "${multi_version_path}"
fi
# 导入version_compatiable.inc
version_compatiable_path="${curpath}/version_compatiable.inc"
if [ -f "${version_compatiable_path}" ]; then
. "${version_compatiable_path}"
fi
# 导入config.inc
config_path="${curpath}/config.inc"
if [ -f "${config_path}" ]; then
. "${config_path}"
fi
# 导入cold_patch.sh
cold_patch_path="${curpath}/cold_patch.sh"
if [ -f "${cold_patch_path}" ]; then
. "${cold_patch_path}"
fi
# bash执行时需要展开别名
if [ -n "$BASH_SOURCE" ]; then
shopt -s expand_aliases
fi
__pkg_in_pkgs() {
local matched
__item_in_list "matched" "$@"
echo "${matched}"
}
__block_in_blocks() {
__item_in_list "matched" "$@"
echo "${matched}"
}
# 包列表中移除包
__remove_pkg_in_pkgs() {
__remove_item_in_list "$@"
}
# 冒泡排序O(n**2)
__sort_blocks() {
local blocks="$*"
local block
local sorted_blocks=""
local max
local i=0
__length_list "${blocks}" "len_blocks"
while [ "$i" -lt ${len_blocks} ]; do
max=""
for block in ${blocks}; do
if [ "${block}" \> "${max}" ]; then
max="${block}"
fi
done
if [ "${sorted_blocks}" = "" ]; then
sorted_blocks="${max}"
else
sorted_blocks="${max} ${sorted_blocks}"
fi
blocks="$(__remove_item_in_list "${max}" "${blocks}")"
i=$((i+1))
done
echo "${sorted_blocks}"
}
__unpack_block_item() {
local line="$1"
echo "${line}" | tr '|' ' '
}
__pack_block_item() {
local block_name="$1"
local block_pkgs_str="$2"
echo "${block_name}|${block_pkgs_str}"
}
__unpack_block_pkgs() {
local block_pkgs_str="$1"
echo "${block_pkgs_str}" | tr ',' ' '
}
__pack_block_pkgs() {
echo "$*" | tr ' ' ','
}
check_install_path() {
local install_path="$1"
if [ "${install_path}" = "" ]; then
log "ERROR" "install_path is empty!"
return 1
fi
}
# 添加pkg对应的block_info
add_pkg_blocks_info() {
local install_path="$1"
local pkg="$2"
shift; shift
# blocks为待加入db.info的块列表
local blocks="$*"
local block_idx_value
local db_filepath="${install_path}/${PKG_DB_INFO_RELPATH}"
local db_dirpath="$(dirname "${db_filepath}")"
local db_filepath_new="${install_path}/${PKG_DB_INFO_RELPATH}~"
local block_list
local block_name
local block_pkgs_str
local block_pkgs
local len_block_pkgs
local block_idx=0
local len_blocks
__length_list "${blocks}" "len_blocks"
if [ ${len_blocks} -eq 0 ]; then
return 0
fi
blocks="$(__sort_blocks "${blocks}")"
if [ ! -d "${db_dirpath}" ]; then
mkdir -p "${db_dirpath}"
if [ $? -ne 0 ]; then
log "ERROR" "mkdir ${db_dirpath} failed!"
exit 1
fi
fi
if [ ! -f "${db_filepath}" ]; then
touch "${db_filepath}"
if [ $? -ne 0 ]; then
log "ERROR" "touch ${db_filepath} failed!"
exit 1
fi
change_mod_and_own "${db_filepath}" "${DB_INFO_MOD}" "\$username:\$usergroup" "${INSTALL_FOR_ALL}"
fi
rm -f "${db_filepath_new}"
if [ $? -ne 0 ]; then
log "ERROR" "delete ${db_filepath_new} failed!"
exit 1
fi
while read line; do
block_list="$(__unpack_block_item "${line}")"
__index_list "${block_list}" 0 "block_name"
__index_list "${block_list}" 1 "block_pkgs_str"
# 如果pkgs为空则忽略该条目
if [ "${block_pkgs_str}" = "" ]; then
continue
fi
block_pkgs="$(__unpack_block_pkgs "${block_pkgs_str}")"
__length_list "${block_pkgs}" "len_block_pkgs"
if [ ${len_block_pkgs} -eq 0 ]; then
continue
fi
if [ ${block_idx} -lt ${len_blocks} ]; then
__index_list "${blocks}" ${block_idx} "block_idx_value"
fi
# blocks中的块名小于db中的当前块名直接添加到db中。
# 注意不能continue因为还要处理db的当前条目。
while [ ${block_idx} -lt ${len_blocks} ] && [ "${block_idx_value}" \< "${block_name}" ]; do
__pack_block_item "${block_idx_value}" "${pkg}" >> "${db_filepath_new}"
if [ $? -ne 0 ]; then
log "ERROR" "write ${db_filepath_new} failed!"
exit 1
fi
block_idx=$((block_idx+1))
__index_list "${blocks}" ${block_idx} "block_idx_value"
done
# 已经没有需要添加的块保持db的当前条目。
if [ ${block_idx} -eq ${len_blocks} ]; then
__pack_block_item "${block_name}" "${block_pkgs_str}" >> "${db_filepath_new}"
if [ $? -ne 0 ]; then
log "ERROR" "write ${db_filepath_new} failed!"
exit 1
fi
continue
fi
# blocks中的块名大于db中的当前块名保持db的当前条目。
if [ "${block_idx_value}" \> "${block_name}" ]; then
__pack_block_item "${block_name}" "${block_pkgs_str}" >> "${db_filepath_new}"
if [ $? -ne 0 ]; then
log "ERROR" "write ${db_filepath_new} failed!"
exit 1
fi
continue
fi
# blocks中的块名等于db中的当前块名将pkg添加到当前条目pkg列表中。
in_pkgs="$(__pkg_in_pkgs "${pkg}" "${block_pkgs}")"
if [ "${in_pkgs}" = "true" ]; then
__pack_block_item "${block_name}" "${block_pkgs_str}" >> "${db_filepath_new}"
if [ $? -ne 0 ]; then
log "ERROR" "write ${db_filepath_new} failed!"
exit 1
fi
else
__pack_block_item "${block_name}" "${block_pkgs_str},${pkg}" >> "${db_filepath_new}"
if [ $? -ne 0 ]; then
log "ERROR" "write ${db_filepath_new} failed!"
exit 1
fi
fi
block_idx=$((block_idx+1))
done < "${db_filepath}"
# blocks中剩余的块添加到db中。
while [ ${block_idx} -lt ${len_blocks} ]; do
__index_list "${blocks}" ${block_idx} "block_idx_value"
echo "${block_idx_value}|${pkg}" >> "${db_filepath_new}"
block_idx=$((block_idx+1))
done
cp "${db_filepath_new}" "${db_filepath}"
if [ $? -ne 0 ]; then
log "ERROR" "replace ${db_filepath} failed!"
exit 1
fi
rm -f "${db_filepath_new}"
if [ $? -ne 0 ]; then
log "ERROR" "delete ${db_filepath_new} failed!"
exit 1
fi
}
# 删除block_info中的pkg信息
del_blocks_info_pkg() {
local install_path="$1"
local pkg="$2"
local db_filepath="${install_path}/${PKG_DB_INFO_RELPATH}"
local db_dirpath="$(dirname "${db_filepath}")"
local db_filepath_new="${install_path}/${PKG_DB_INFO_RELPATH}~"
local block_list
local block_name
local block_pkgs_str
local block_pkgs
local len_block_pkgs
if [ ! -f "${db_filepath}" ]; then
return 0
fi
rm -f "${db_filepath_new}"
if [ $? -ne 0 ]; then
log "ERROR" "delete ${db_filepath_new} failed!"
exit 1
fi
while read line; do
block_list="$(__unpack_block_item "${line}")"
__index_list "${block_list}" 0 "block_name"
__index_list "${block_list}" 1 "block_pkgs_str"
block_pkgs="$(__unpack_block_pkgs "${block_pkgs_str}")"
block_pkgs="$(__remove_pkg_in_pkgs "${pkg}" "${block_pkgs}")"
__length_list "${block_pkgs}" "len_block_pkgs"
if [ ${len_block_pkgs} -gt 0 ]; then
block_pkgs_str="$(__pack_block_pkgs "${block_pkgs}")"
__pack_block_item "${block_name}" "${block_pkgs_str}" >> "${db_filepath_new}"
if [ $? -ne 0 ]; then
log "ERROR" "write ${db_filepath_new} failed!"
exit 1
fi
fi
done < "${db_filepath}"
# 当前条目如果没有pkg使用则删除。
if [ ! -f "${db_filepath_new}" ]; then
rm -f "${db_filepath}"
if [ $? -ne 0 ]; then
log "ERROR" "delete ${db_filepath} failed!"
exit 1
fi
else
mv -f "${db_filepath_new}" "${db_filepath}"
if [ $? -ne 0 ]; then
log "ERROR" "replace ${db_filepath} failed!"
exit 1
fi
fi
return 0
}
# 准备并且检查软链接路径
prepare_and_check_softlink_path() {
local softlink_abs="$1"
local softlink_dir="$(dirname "${softlink_abs}")"
if [ ! -d "${softlink_dir}" ]; then
mkdir -p "${softlink_dir}"
fi
# 如果目标路径是个软链接,则移除
if [ -L "${softlink_abs}" ]; then
rm -f "${softlink_abs}"
if [ $? -ne 0 ]; then
log "ERROR" "remove softlink ${softlink_abs} failed! (create relative softlink)"
exit 1
fi
fi
# 不允许目标路径已经是一个目录,防止软链接到错误的位置。
if [ -d "${softlink_abs}" ]; then
log "ERROR" "softlink existed dir ${softlink_abs}!"
exit 1
fi
}
get_file_owner_group() {
local _outvar="$1"
local _path="$2"
local _result
_result="$(stat -c %U "${_path}"):$(stat -c %G "${_path}")"
eval "${_outvar}=\"${_result}\""
}
# 根据pkg_inner_softlink创建软链接
create_pkg_inner_softlink() {
local install_path="$1"
local line="$2"
local array
local target
local pkg_inner_softlink
local pkg_inner_softlink_list
local is_abs_path
__index_list "${line}" 1 "target" 8 "pkg_inner_softlink"
if [ "${pkg_inner_softlink}" != "NA" ]; then
create_softlink_by_install_path "${install_path}" "${target}" "${pkg_inner_softlink}"
fi
return 0
}
# 处理软链路径为已存在目录的情况
# minirc场景install_path目录下存在include目录
# 并且filelist.csv中配置了(x86_64|aarch64)-linux/include目录
# 则将(x86_64|aarch64)-linux/include中的内容软链接至include目录下
deal_with_existed_dir() {
local install_path="$1"
local folder="$2"
local filelist_path="$3"
local install_path_regex="^(x86_64|aarch64)-linux/${folder}$"
local install_sub_path_regex="^(x86_64|aarch64)-linux/${folder}/[^/]+$"
if [ -L "${install_path}/${folder}" ] || [ ! -d "${install_path}/${folder}" ]; then
return 0
fi
target_path=$(awk -v folder="${folder}" -v install_path_regex="${install_path_regex}" '
BEGIN{
FS= ","
}
{
if ($2 != "mkdir") next
if ($4 !~ install_path_regex) next
if ($9 != folder) next
print $4
}' "${filelist_path}")
if [ "${target_path}" = "" ]; then
return 0
fi
awk -v folder="${folder}" -v install_path_regex="${install_path_regex}" -v install_sub_path_regex="${install_sub_path_regex}" '
BEGIN{
FS = ","; OFS = ","
}
{
if ($2 != "mkdir" && $2 != "copy" && $2 != "move") {
print $0
next
}
if ($4 ~ install_path_regex) {
print $1, $2, $3, $4, $5, $6, $7, $8, "NA", $10, $11, $12, $13, $14, $15
next
}
if ($4 !~ install_sub_path_regex) {
print $0
next
}
softlink = $9
if (softlink != "NA") {
print $0
next
}
z = split($4, filepath_list, "/")
softlink = folder "/" filepath_list[z]
print $1, $2, $3, $4, $5, $6, $7, $8, softlink, $10, $11, $12, $13, $14, $15
}' "${filelist_path}" > "${filelist_path}.tmp"
if [ $? -ne 0 ]; then
log "ERROR" "modify filelist for ${install_path}/${folder} failed!"
return 1
fi
mv -f "${filelist_path}.tmp" "${filelist_path}"
if [ $? -ne 0 ]; then
log "ERROR" "replace filelist for ${install_path}/${folder} failed!"
return 1
fi
}
#执行创建目录动作
do_create_dirs() {
local action="$1"
local install_type="$2"
local install_path="$3"
local filelist_path="$4"
local package="$5"
local feature_param="$6"
local ret
if [ "${action}" = "resetmod" ]; then
if [ "${package}" != "" ]; then
del_blocks_info_pkg "${install_path}" "${package}"
ret="$?" && [ $ret -ne 0 ] && return $ret
create_stash_mod "${install_path}"
ret="$?" && [ $ret -ne 0 ] && return $ret
foreach_filelist "NA" "reset_mod_dirs_with_stash_mod" "${install_type}" "${install_path}" "mkdir" "${filelist_path}" "${feature_param}" "no" "normal"
ret="$?" && [ $ret -ne 0 ] && return $ret
else
foreach_filelist "NA" "reset_mod_dirs" "${install_type}" "${install_path}" "mkdir" "${filelist_path}" "${feature_param}" "no" "normal"
ret="$?" && [ $ret -ne 0 ] && return $ret
fi
# 设置copy_entity路径的权限解决删除时权限问题
# filter_by_blocks过滤防止变更不删除的文件目录的权限
foreach_filelist "filter_by_blocks" "reset_mod_dirs_recursive" "${install_type}" "${install_path}" "copy_entity" "${filelist_path}" "${feature_param}" "no" "normal"
ret="$?" && [ $ret -ne 0 ] && return $ret
elif [ "${action}" = "all" ] || [ "${action}" = "mkdir" ]; then
deal_with_existed_dir "$install_path" "include" "$filelist_path"
ret="$?" && [ $ret -ne 0 ] && return $ret
deal_with_existed_dir "$install_path" "lib64" "$filelist_path"
ret="$?" && [ $ret -ne 0 ] && return $ret
# 先重置目录权限配置,防止软链接时缺少权限
foreach_filelist "NA" "reset_mod_dirs" "$install_type" "$install_path" "mkdir" "$filelist_path" "${feature_param}" "no" "normal"
ret="$?" && [ $ret -ne 0 ] && return $ret
# 重置copy_entity权限防止块复用场景复制时缺少权限
foreach_filelist "NA" "reset_mod_dirs_recursive" "$install_type" "$install_path" "copy_entity" "$filelist_path" "${feature_param}" "no" "normal"
ret="$?" && [ $ret -ne 0 ] && return $ret
foreach_filelist "NA" "create_dirs" "$install_type" "$install_path" "mkdir" "$filelist_path" "${feature_param}" "no" "normal"
ret="$?" && [ $ret -ne 0 ] && return $ret
foreach_filelist "filter_by_pkg_inner_softlink" "create_pkg_inner_softlink" "$install_type" "$install_path" "mkdir" "$filelist_path" "${feature_param}" "no" "normal"
ret="$?" && [ $ret -ne 0 ] && return $ret
else
log "ERROR" "action wrong! action is ${action}"
return 1
fi
return 0
}
# 拷贝文件
copy_file() {
local install_path="$1"
local source="$2"
local target="$3"
local softlink="$4"
local pkg_inner_softlink="$5"
local target_abs
local target_dir
__set_abs_path "${install_path}" "${target}" "target_abs"
target_dir="$(dirname "${target_abs}")"
if [ ! -e "${source}" ]; then
log "ERROR" "copy file source file ${source} doesn't exist!"
return 1
fi
${COPY_COMMAND} "${source}" "${target_dir}"
if [ $? -ne 0 ]; then
log "ERROR" "${source} copy failed!"
return 1
fi
if [ "${softlink}" != "NA" ]; then
create_softlink_by_install_path "${install_path}" "${target}" "${softlink}"
ret="$?" && [ ${ret} -ne 0 ] && return ${ret}
fi
if [ "${pkg_inner_softlink}" != "NA" ]; then
create_softlink_by_install_path "${install_path}" "${target}" "${pkg_inner_softlink}"
ret="$?" && [ ${ret} -ne 0 ] && return ${ret}
fi
return 0
}
# 移动文件
move_file() {
local install_path="$1"
local source="$2"
local target="$3"
local softlink="$4"
local pkg_inner_softlink="$5"
local target_abs
local target_dir
__set_abs_path "${install_path}" "${target}" "target_abs"
target_dir="$(dirname "${target_abs}")"
if [ ! -e "${source}" ] && [ ! -L "${source}" ]; then
log "ERROR" "move file source file ${source} doesn't exist!"
return 1
fi
${MOVE_COMMAND} "${source}" "${target_dir}"
if [ $? -ne 0 ]; then
log "ERROR" "${source} move failed!"
return 1
fi
if [ "${softlink}" != "NA" ]; then
create_softlink_by_install_path "${install_path}" "${target}" "${softlink}"
ret="$?" && [ ${ret} -ne 0 ] && return ${ret}
fi
if [ "${pkg_inner_softlink}" != "NA" ]; then
create_softlink_by_install_path "${install_path}" "${target}" "${pkg_inner_softlink}"
ret="$?" && [ ${ret} -ne 0 ] && return ${ret}
fi
return 0
}
# 复制文件
copy_files() {
local install_path="$1"
local line="$2"
local exec_params="$3"
local src_dir="$4"
local src src_abs target target_abs softlink configurable pkg_inner_softlink tmpdir action
local ret
__index_list "${line}" 0 "src" 1 "target" 4 "softlink" 5 "configurable" 8 "pkg_inner_softlink"
if [ "${src_dir}" = "--move" ]; then
src_abs="${src}"
action="move_file"
elif [ "${src_dir}" != "" ]; then
__set_abs_path "${src_dir}" "${src}" "src_abs"
action="copy_file"
else
src_abs="${src}"
action="copy_file"
fi
__set_abs_path "${install_path}" "${target}" "target_abs"
tmpdir="$(dirname "${target_abs}")"
if [ ! -d "${tmpdir}" ]; then
mkdir -p "${tmpdir}"
fi
# 如果目标文件已经存在,而且是配置文件,则不执行覆盖操作
if [ -e "${target_abs}" ] && [ "${configurable}" = "TRUE" ]; then
return 0
fi
# 源文件不是软链,并且目标文件是软链
if [ ! -L "${src_abs}" ] && [ -L "${target_abs}" ] ; then
rm -f "${target_abs}"
log "WARNING" "${target_abs} is an existing softlink in copy files, deleted."
fi
exec_with_param "$exec_params" "$action" "${install_path}" "${src_abs}" "${target}" "${softlink}" "${pkg_inner_softlink}"
ret="$?" && [ ${ret} -ne 0 ] && return ${ret}
return 0
}
__set_total_uninstall_path() {
local install_path="$1"
local varname="$2"
eval "${varname}=\"${install_path}/cann_uninstall.sh\""
}
# 是否为hilinux环境
__is_hilinux() {
local varname="$1"
which lsattr > /dev/null 2>&1
if [ $? -ne 0 ]; then
eval "${varname}=\"true\""
else
eval "${varname}=\"false\""
fi
}
# 移除文件上的不可修改权限
__remove_immutable() {
local file="$1"
local is_hilinux ret
# 文件不存在则退出。
if [ ! -f "${file}" ]; then
return 0
fi
__is_hilinux "is_hilinux"
if [ "${is_hilinux}" = "true" ]; then
return 0
fi
attr="$(lsattr "${file}" | cut -d' ' -f1 | grep -o "i")"
if [ "${attr}" != "" ]; then
chattr -i "${file}"
ret="$?" && [ $ret -ne 0 ] && return $ret
fi
return 0
}
# 创建总uninstall.sh脚本
__create_uninstall() {
local file="$1"
if [ ! -f "${file}" ]; then
cat > ${file} <<EOF
#!/bin/sh
SHELL_DIR="\$(dirname "\${BASH_SOURCE:-\$0}")"
INSTALL_PATH="\$(cd "\${SHELL_DIR}" && pwd)"
TOTAL_RET="0"
uninstall_package() {
local path="\$1"
local cur_date ret
if [ ! -d "\${INSTALL_PATH}/\${path}" ]; then
cur_date=\$(date +"%Y-%m-%d %H:%M:%S")
echo "[\$cur_date] [ERROR]: \${INSTALL_PATH}/\${path}: No such file or directory"
TOTAL_RET="1"
return 1
fi
cd "\${INSTALL_PATH}/\${path}"
./uninstall.sh
ret="\$?" && [ \${ret} -ne 0 ] && TOTAL_RET="1"
return \${ret}
}
if [ ! "\$*" = "" ]; then
cur_date=\$(date +"%Y-%m-%d %H:%M:%S")
echo "[\$cur_date] [ERROR]: \$*, parameter is not supported."
exit 1
fi
exit \${TOTAL_RET}
EOF
fi
}
# 添加uninstall.sh文件中的uninstall_package函数调用
__add_uninstall_package() {
local file="$1"
local script_dirpath="$2"
sed -i "/^exit /i uninstall_package \"${script_dirpath}\"" "${file}"
}
# 删除uninstall.sh文件中的uninstall_package函数调用
__remove_uninstall_package() {
local file="$1"
local script_dirpath="$2"
local path_regex
path_to_regex "path_regex" "${script_dirpath}"
if [ -f "${file}" ]; then
sed -i "/uninstall_package \"${path_regex}\"/d" "${file}"
if [ $? -ne 0 ]; then
log "ERROR" "remove ${file} uninstall_package command failed!"
return 1
fi
fi
return 0
}
# 删除uninstall.sh文件如果已经没有uninstall_package调用
__remove_uninstall_file_if_no_content() {
local file="$1"
local num
if [ ! -f "${file}" ]; then
return 0
fi
# 注意uninstall_package后有一个空格表示函数调用
num=$(grep "^uninstall_package " ${file} | wc -l)
if [ ${num} -eq 0 ]; then
rm -f "${file}" > /dev/null 2>&1
if [ $? -ne 0 ]; then
log "WARNING" "Delete file:${file} failed, please delete it by yourself."
fi
fi
return 0
}
# 向cann_uninstall.sh文件中添加uninstall_package命令
add_cann_uninstall_script_dir() {
local install_path="$1"
local script_dir="$2"
local username="$3"
local usergroup="$4"
local install_for_all="$5"
local oldmod="" ret
__set_total_uninstall_path "${install_path}" "total_uninstall_path"
if [ -f "${install_path}/${script_dir}/uninstall.sh" ]; then
if [ -f "${total_uninstall_path}" ]; then
get_file_mod "oldmod" "${total_uninstall_path}"
else
__create_uninstall "${total_uninstall_path}"
fi
ret="$?" && [ $ret -ne 0 ] && return $ret
__remove_immutable "${total_uninstall_path}"
ret="$?" && [ $ret -ne 0 ] && return $ret
change_own "${total_uninstall_path}" "${username}:${usergroup}"
ret="$?" && [ $ret -ne 0 ] && return $ret
change_mod "${total_uninstall_path}" "${SETENV_WRITEABLE_MOD}" ""
ret="$?" && [ $ret -ne 0 ] && return $ret
__add_uninstall_package "${total_uninstall_path}" "${script_dir}"
ret="$?" && [ $ret -ne 0 ] && return $ret
if [ "${oldmod}" = "" ]; then
change_mod "${total_uninstall_path}" "${TOTAL_UNINSTALL_MOD}" "${install_for_all}"
else
change_mod "${total_uninstall_path}" "${oldmod}" ""
fi
ret="$?" && [ $ret -ne 0 ] && return $ret
fi
return 0
}
# 向cann_uninstall.sh文件中添加子包命令
add_cann_uninstall_package() {
local install_path="$1"
local package="$2"
local username="$3"
local usergroup="$4"
local install_for_all="$5"
local ret package_dirpath script_dir
get_package_dirpath "package_dirpath" "${package}"
script_dir="${package_dirpath}/script"
# opp_kernel包存在同时安装多种芯片包的场景
# 确保cann_uninstall.sh脚本中只有一个opp_kernel的uninstall_package
del_cann_uninstall_script_dir "${install_path}" "${script_dir}"
ret="$?" && [ ${ret} -ne 0 ] && return ${ret}
add_cann_uninstall_script_dir "${install_path}" "${script_dir}" "${username}" "${usergroup}" "${install_for_all}"
ret="$?" && [ ${ret} -ne 0 ] && return ${ret}
return 0
}
# cann_uninstall.sh文件中添加命令命令入口
do_add_cann_uninstall() {
local install_path="$1"
local script_dir="$2"
local username="$3"
local usergroup="$4"
local install_for_all="$5"
local ret
check_param_not_empty "install_path" "need set package parameter in add cann uninstall!"
ret="$?" && [ ${ret} -ne 0 ] && return ${ret}
check_param_not_empty "script_dir" "need set script_dir parameter in add cann uninstall!"
ret="$?" && [ ${ret} -ne 0 ] && return ${ret}
check_param_not_empty "username" "need set username parameter in add cann uninstall!"
ret="$?" && [ ${ret} -ne 0 ] && return ${ret}
check_param_not_empty "usergroup" "need set usergroup parameter in add cann uninstall!"
ret="$?" && [ ${ret} -ne 0 ] && return ${ret}
# 删除cann_uninstall.sh文件中已存在的uninstall_package命令
del_cann_uninstall_script_dir "${install_path}" "${script_dir}"
add_cann_uninstall_script_dir "${install_path}" "${script_dir}" "${username}" "${usergroup}" "${install_for_all}"
ret="$?" && [ ${ret} -ne 0 ] && return ${ret}
return 0
}
# 删除cann_uninstall.sh文件中uninstall_package命令
del_cann_uninstall_script_dir() {
local install_path="$1"
local script_dir="$2"
local oldmod="" ret
__set_total_uninstall_path "${install_path}" "total_uninstall_path"
if [ -f "${total_uninstall_path}" ]; then
__remove_immutable "${total_uninstall_path}"
ret="$?" && [ $ret -ne 0 ] && return $ret
get_file_mod "oldmod" "${total_uninstall_path}"
ret="$?" && [ $ret -ne 0 ] && return $ret
change_mod "${total_uninstall_path}" "${SETENV_WRITEABLE_MOD}" ""
ret="$?" && [ $ret -ne 0 ] && return $ret
__remove_uninstall_package "${total_uninstall_path}" "${script_dir}"
ret="$?" && [ $ret -ne 0 ] && return $ret
change_mod "${total_uninstall_path}" "${oldmod}" ""
ret="$?" && [ $ret -ne 0 ] && return $ret
__remove_uninstall_file_if_no_content "${total_uninstall_path}"
ret="$?" && [ $ret -ne 0 ] && return $ret
fi
return 0
}
# 删除cann_uninstall.sh文件中子包命令
del_cann_uninstall_package() {
local install_path="$1"
local package="$2"
local ret package_dirpath script_dir
get_package_dirpath "package_dirpath" "${package}"
script_dir="${package_dirpath}/script"
del_cann_uninstall_script_dir "${install_path}" "${script_dir}"
ret="$?" && [ ${ret} -ne 0 ] && return ${ret}
return 0
}
# cann_uninstall.sh文件中删除命令命令入口
do_del_cann_uninstall() {
local install_path="$1"
local script_dir="$2"
local ret
check_param_not_empty "install_path" "need set package parameter in del cann uninstall!"
ret="$?" && [ ${ret} -ne 0 ] && return ${ret}
check_param_not_empty "script_dir" "need set script_dir parameter in del cann uninstall!"
ret="$?" && [ ${ret} -ne 0 ] && return ${ret}
del_cann_uninstall_script_dir "${install_path}" "${script_dir}"
ret="$?" && [ ${ret} -ne 0 ] && return ${ret}
return 0
}
# 删除ascend_install.info文件
del_ascend_install_info() {
rm -f "$curpath/../ascend_install.info"
}
# 执行拷贝动作
do_copy_files() {
local install_type="$1"
local install_path="$2"
local filelist_path="$3"
local package="$4"
local feature_param="$5"
local total_uninstall_path exec_mode ret
if [ "$PARALLEL" = "true" ]; then
exec_mode="concurrency"
else
exec_mode="normal"
fi
if [ "${USE_MOVE}" = "true" ]; then
foreach_filelist "NA" "copy_files" "$install_type" "$install_path" "move" "$filelist_path" "${feature_param}" \
"no" "$exec_mode" "--move"
foreach_filelist "NA" "copy_files" "$install_type" "$install_path" "copy copy_entity" "$filelist_path" "${feature_param}" \
"no" "$exec_mode"
else
foreach_filelist "NA" "copy_files" "$install_type" "$install_path" "copy copy_entity move" "$filelist_path" "${feature_param}" \
"no" "$exec_mode"
fi
ret="$?" && [ $ret -ne 0 ] && return $ret
if [ "${package}" != "" ] && [ "${SET_CANN_UNINSTALL}" = "y" ]; then
add_cann_uninstall_package "${install_path}" "${package}" "${USERNAME}" "${USERGROUP}" "${INSTALL_FOR_ALL}"
fi
}
# 修改文件的权限和属组
change_mod_and_own_files() {
local install_path="$1"
local line="$2"
local exec_params="$3"
local target mod own is_abs_path
__index_list "${line}" 1 "target" 2 "mod" 3 "own"
__check_abs_path "${target}"
if [ "${is_abs_path}" != "true" ]; then
target="${install_path}/${target}"
fi
if [ -d "${target}" ]; then
return 0
fi
# 只处理文件,没有处理文件的软链接
exec_with_param "$exec_params" change_mod_and_own "${target}" "${mod}" "${own}" "${INSTALL_FOR_ALL}" "false"
}
# 递归修改文件的权限和属组
change_mod_and_own_files_recursive() {
local install_path="$1"
local line="$2"
local exec_params="$3"
local target mod own is_abs_path
__index_list "${line}" 1 "target" 2 "mod" 3 "own"
__check_abs_path "${target}"
if [ "${is_abs_path}" != "true" ]; then
target="${install_path}/${target}"
fi
if [ ! -e "${target}" ]; then
return 0
fi
exec_with_param "$exec_params" change_mod_and_own "${target}" "${mod}" "${own}" "${INSTALL_FOR_ALL}" "true"
}
# filelist中的使用到的blocks添加到db.info中
add_filelist_blocks_info() {
local install_type="$1"
local install_path="$2"
local filelist_path="$3"
local feature_param="$4"
local package="$5"
local blocks=""
parse_filelist "${install_type}" "copy copy_entity del mkdir move" "${filelist_path}" "${feature_param}" "NA" ""
filelist="$(echo "${filelist}" | cut -d' ' -f8 | sort | uniq)"
while read line; do
block_name="${line}"
if [ "${block_name}" = "" ]; then
continue
fi
if [ "${blocks}" = "" ]; then
blocks="${block_name}"
else
blocks="${blocks} ${block_name}"
fi
done << EOF
${filelist}
EOF
add_pkg_blocks_info "${install_path}" "${package}" "${blocks}"
}
# 修改文件和目录的权限
do_chmod_file_dir() {
local install_type="$1"
local install_path="$2"
local filelist_path="$3"
local feature_param="$4"
local package="$5"
local ret
foreach_filelist "NA" "change_mod_and_own_files" "$install_type" "$install_path" "copy del move" "$filelist_path" "${feature_param}" "no" "concurrency"
ret="$?" && [ $ret -ne 0 ] && return $ret
foreach_filelist "NA" "change_mod_and_own_files_recursive" "$install_type" "$install_path" "copy_entity" "$filelist_path" "${feature_param}" "no" "concurrency"
ret="$?" && [ $ret -ne 0 ] && return $ret
foreach_filelist "NA" "change_mod_and_own_dirs" "$install_type" "$install_path" "mkdir" "$filelist_path" "${feature_param}" "reverse" "normal"
ret="$?" && [ $ret -ne 0 ] && return $ret
if [ "${package}" != "" ]; then
add_filelist_blocks_info "$install_type" "$install_path" "$filelist_path" "${feature_param}" "$package"
ret="$?" && [ $ret -ne 0 ] && return $ret
fi
return 0
}
# 删除安装生成的pkg_inner_softlinks
remove_install_pkg_inner_softlinks() {
local install_path="$1"
local line="$2"
local target
local pkg_inner_softlink
local pkg_inner_softlink_list
local pkg_inner_softlink_abs
local ret
__index_list "${line}" 1 "target" 8 "pkg_inner_softlink"
if [ "${target}" != "NA" ]; then
if [ "${pkg_inner_softlink}" != "NA" ]; then
remove_softlinks "${install_path}" "${pkg_inner_softlink}"
ret="$?" && [ ${ret} -ne 0 ] && return ${ret}
fi
fi
return 0
}
# 删除安装文件,入参为$1: install_type, $2: install_path $3:filelist_path
remove_install_files() {
local install_path="$1"
local line="$2"
local exec_params="$3"
local target softlink configurable hash_value is_abs_path
__index_list "${line}" 1 "target" 4 "softlink" 5 "configurable" 6 "hash_value"
if [ "${target}" != "NA" ]; then
__check_abs_path "${target}"
if [ "${is_abs_path}" != "true" ]; then
target="${install_path}/${target}"
fi
if [ -d "${target}" ] && [ ! -L "${target}" ]; then
return 0
fi
if [ "${softlink}" != "NA" ]; then
__check_abs_path "${softlink}"
if [ "${is_abs_path}" != "true" ]; then
softlink="${install_path}/${softlink}"
fi
fi
# 配置文件不删除
if [ "${configurable}" = "TRUE" ]; then
echo "${hash_value} ${target}" | sha256sum --check > /dev/null 2>&1
if [ $? -ne 0 ]; then
log "WARNING" "${target} user configuration file has been modified, skip deleting."
return 0
fi
fi
exec_with_param "$exec_params" remove_file "${target}" "${softlink}"
fi
return 0
}
# 递归删除安装文件
remove_install_files_recursive() {
local install_path="$1"
local line="$2"
local exec_params="$3"
local target configurable hash_value is_abs_path
__index_list "${line}" 1 "target" 5 "configurable" 6 "hash_value"
if [ "${target}" != "NA" ]; then
__check_abs_path "${target}"
if [ "${is_abs_path}" != "true" ]; then
target="${install_path}/${target}"
fi
# 配置文件不删除
if [ "${configurable}" = "TRUE" ]; then
echo "${hash_value} ${target}" | sha256sum --check > /dev/null 2>&1
if [ $? -ne 0 ]; then
log "WARNING" "${target} user configuration file has been modified, skip deleting."
return 0
fi
fi
exec_with_param "$exec_params" remove_dir_icp "${target}"
fi
return 0
}
# 删除安装文件夹生成的软链接
remove_install_softlink() {
local install_path="$1"
local line="$2"
local target
local softlinks_str
local is_abs_path
__index_list "${line}" 1 "target" 4 "softlinks_str"
if [ "$target" != "NA" ]; then
if [ "${softlinks_str}" != "NA" ]; then
remove_softlinks "${install_path}" "${softlinks_str}"
ret="$?" && [ ${ret} -ne 0 ] && return ${ret}
fi
fi
return 0
}
# 删除安装文件与目录等
do_remove() {
local install_type="$1"
local install_path="$2"
local filelist_path="$3"
local package="$4"
local feature_param="$5"
local tmp_filelist_path
local total_uninstall_path
local oldmod
local func_before_remove
local func_after_remove_01
local func_after_remove_02
local ret
get_tmp_file tmp_filelist_path "filelist"
cp -f "$filelist_path" "$tmp_filelist_path"
if [ $? -ne 0 ]; then
log "ERROR" "cp -f $filelist_path $tmp_filelist_path failed!"
return 1
fi
if [ "${package}" != "" ]; then
# root帐户--uninstall时存在不调用restoremod直接调用remove的场景。toolkit包
func_before_remove="del_blocks_info_pkg \"${install_path}\" \"${package}\""
if [ -f "${install_path}/${STASH_MOD_PATH}" ]; then
# 删除文件后,恢复目录权限配置
func_after_remove_01="foreach_stashmod \"restore_stash_mod\" \"${install_path}\" \"reverse\""
func_after_remove_02="remove_stash_mod \"${install_path}\""
fi
del_cann_uninstall_package "${install_path}" "${package}"
ret="$?" && [ $ret -ne 0 ] && return $ret
if [ "$REMOVE_INSTALL_INFO" = "y" ]; then
del_ascend_install_info
fi
fi
eval "${func_before_remove}"
ret="$?" && [ $ret -ne 0 ] && return $ret
# del元素不会出现pkg_inner_softlink
foreach_filelist "filter_by_pkg_inner_softlink" "remove_install_pkg_inner_softlinks" "$install_type" "$install_path" "mkdir copy copy_entity move" "$tmp_filelist_path" "${feature_param}" "no" "normal"
ret="$?" && [ $ret -ne 0 ] && return $ret
foreach_filelist "filter_by_blocks" "remove_install_softlink" "$install_type" "$install_path" "mkdir copy copy_entity move" "$tmp_filelist_path" "${feature_param}" "no" "normal"
ret="$?" && [ $ret -ne 0 ] && return $ret
foreach_filelist "filter_by_blocks" "remove_install_files" "$install_type" "$install_path" "copy del move" "$tmp_filelist_path" "${feature_param}" "no" "concurrency"
ret="$?" && [ $ret -ne 0 ] && return $ret
foreach_filelist "filter_by_blocks" "remove_install_files_recursive" "$install_type" "$install_path" "copy_entity" "$tmp_filelist_path" "${feature_param}" "no" "concurrency"
ret="$?" && [ $ret -ne 0 ] && return $ret
foreach_filelist "filter_by_blocks" "remove_install_dirs" "$install_type" "$install_path" "mkdir" "$tmp_filelist_path" "${feature_param}" "reverse" "normal"
ret="$?" && [ $ret -ne 0 ] && return $ret
eval "${func_after_remove_01}"
ret="$?" && [ $ret -ne 0 ] && return $ret
eval "${func_after_remove_02}"
ret="$?" && [ $ret -ne 0 ] && return $ret
rm -f "$tmp_filelist_path"
ret="$?" && [ $ret -ne 0 ] && return $ret
return 0
}
# 打印安装信息
print_install_content() {
local install_type="$1"
local install_path="$2"
local operate_type="$3"
local filelist_path="$4"
local feature_param="$5"
local blocks
get_blocks_info "blocks" "$install_path"
parse_filelist "$install_type" "$operate_type" "$filelist_path" "$feature_param" "filter_by_blocks" "$blocks"
# bash与dash的echo有差异需要使用系统的/bin/echo
/bin/echo "$filelist"
exit 0
}
# 包名是否存在于db.info
pkg_in_dbinfo() {
local install_path="$1"
local pkg="$2"
local db_filepath="${install_path}/${PKG_DB_INFO_RELPATH}"
if [ -z "${install_path}" ]; then
echo "false"
exit 1
fi
if [ -z "${pkg}" ]; then
echo "false"
exit 2
fi
if [ ! -f "${db_filepath}" ]; then
echo "false"
return 0
fi
awk -v input_pkg="${pkg}" '
BEGIN {
FS = "|"
found = "false"
}
{
split($2, pkg_list, ",")
for (i in pkg_list) {
if (input_pkg == pkg_list[i]) {
found = "true"
exit
}
}
}
END {
print found
}' "${db_filepath}"
}
# 展开自定义选项
expand_custom_options() {
local _outvar="$1"
local _custom_options="$2"
eval "${_outvar}=\"$(echo "${_custom_options}" | tr "," " ")\""
}
# 调用子包自定义脚本
package_custom_script() {
local script_name="$1"
local install_path="$2"
local version_dir="$3"
local custom_options="$4"
local ret install_options=""
if [ ! -f "${curpath}/${script_name}" ]; then
return 0
fi
install_options="--install-path=${install_path}"
if [ "${version_dir}" != "" ]; then
install_options="${install_options} --version-dir=${version_dir}"
fi
expand_custom_options "custom_options" "${custom_options}"
chmod u+x ${curpath}/${script_name}
${curpath}/${script_name} ${install_options} ${custom_options}
ret="$?" && [ $ret -ne 0 ] && return $ret
return 0
}
# 调用子包自定义安装脚本
package_custom_install() {
local package="$1"
local install_path="$2"
local version_dir="$3"
local custom_options="$4"
local ret
package_custom_script "${package}_custom_install.sh" "${install_path}" "${version_dir}" "${custom_options}"
check_ret_error "$?" "Run ${package} custom install failed!"
ret="$?" && [ ${ret} -ne 0 ] && return ${ret}
return 0
}
# 调用子包自定义卸载脚本
package_custom_uninstall() {
local package="$1"
local install_path="$2"
local version_dir="$3"
local custom_options="$4"
local ret
package_custom_script "${package}_custom_uninstall.sh" "${install_path}" "${version_dir}" "${custom_options}"
check_ret_error "$?" "Run ${package} custom uninstall failed!"
ret="$?" && [ ${ret} -ne 0 ] && return ${ret}
return 0
}
# 版本安装流程函数
version_install() {
local install_type="$1"
local install_path="$2"
local filelist_path="$3"
local package="$4"
local feature_param="$5"
local version_dir="$6"
local username="$7"
local usergroup="$8"
local setenv="$9"
local is_upgrade="${10}"
local docker_root="${11}"
local custom_options="${12}"
local is_simple="${13}"
local install_path_full="" ret
local package_real
if [ "${version_dir}" != "" ]; then
install_path_full="${install_path}/${version_dir}"
else
install_path_full="${install_path}"
fi
if [ "${is_simple}" = "y" ]; then
package_real=""
else
package_real="${package}"
fi
# 创建目录
do_create_dirs "mkdir" "${install_type}" "${install_path_full}" "${filelist_path}" "${package_real}" "${feature_param}"
if [ $? -ne 0 ]; then
log "ERROR" "failed to create folder."
return 1
fi
# 拷贝目录与文件
do_copy_files "${install_type}" "${install_path_full}" "${filelist_path}" "${package_real}" "${feature_param}"
if [ $? -ne 0 ]; then
log "ERROR" "failed to copy files."
return 1
fi
if [ "${is_simple}" != "y" ]; then
# set env
add_setenv "${install_path_full}" "${package_real}" "${setenv}" "${username}" "${usergroup}" "false" "${docker_root}"
ret="$?" && [ $ret -ne 0 ] && return $ret
# 调用组件自定义安装流程
package_custom_install "${package_real}" "${install_path}" "${version_dir}" "${custom_options}"
ret="$?" && [ $ret -ne 0 ] && return $ret
fi
# 文件与目录赋权
do_chmod_file_dir "${install_type}" "${install_path_full}" "${filelist_path}" "${feature_param}" "${package_real}"
if [ $? -ne 0 ]; then
log "ERROR" "failed to chown files."
return 1
fi
return 0
}
# 版本卸载流程函数
version_uninstall() {
local install_type="$1"
local install_path="$2"
local filelist_path="$3"
local package="$4"
local feature_param="$5"
local version_dir="$6"
local username="$7"
local docker_root="$8"
local custom_options="$9"
local is_simple="${10}"
local install_path_full="" ret total_ret=0
local package_real
if [ "${version_dir}" != "" ]; then
install_path_full="${install_path}/${version_dir}"
else
install_path_full="${install_path}"
fi
if [ "${is_simple}" = "y" ]; then
package_real=""
else
package_real="${package}"
fi
# 恢复权限
do_create_dirs "resetmod" "${install_type}" "${install_path_full}" "${filelist_path}" "${package_real}" "${feature_param}"
if [ $? -ne 0 ]; then
log "ERROR" "failed to resetmod chmod."
return 1
fi
if [ "${is_simple}" != "y" ]; then
# unset env
del_setenv "${install_path_full}" "${package_real}" "${username}" "${docker_root}"
ret="$?" && [ $ret -ne 0 ] && return $ret
# 调用组件自定义卸载流程,失败流程不中断
package_custom_uninstall "${package_real}" "${install_path}" "${version_dir}" "${custom_options}"
ret="$?" && [ $ret -ne 0 ] && total_ret="$ret"
fi
# 删除文件和目录
do_remove "${install_type}" "${install_path_full}" "${filelist_path}" "${package_real}" "${feature_param}"
if [ $? -ne 0 ]; then
log "ERROR" "failed to remove files and dirs."
return 1
fi
return ${total_ret}
}
# 版本安装函数
do_install() {
local install_type="$1"
local install_path="$2"
local filelist_path="$3"
local package="$4"
local feature_param="$5"
local docker_root="$6"
local is_simple="$7"
local install_path_real ret
check_param_not_empty "package" "need set package parameter in install!"
ret="$?" && [ ${ret} -ne 0 ] && return ${ret}
_package_to_log_pkg_name "LOG_PKG_NAME" "${package}"
check_ret_error "$?" "Set log package name failed in install!"
ret="$?" && [ ${ret} -ne 0 ] && return ${ret}
expand_version_file
# 获取filelist.csv文件真实路径
get_realpath "filelist_path" "${filelist_path}"
# 获取install_path真实路径
get_realpath "install_path" "${install_path}"
if [ "${docker_root}" != "" ]; then
if [ "${WITH_DOCKER_ROOT_PREFIX}" = "y" ]; then
install_path_real="${install_path}"
else
install_path_real="${docker_root}${install_path}"
fi
else
install_path_real="${install_path}"
fi
if [ "${VERSION}" != "" ] && [ "${VERSION_DIR}" != "" ]; then
multi_version_install "${install_type}" "${install_path_real}" "${filelist_path}" "${package}" "${feature_param}" \
"${VERSION}" "${VERSION_DIR}" "${USERNAME}" "${USERGROUP}" "${SETENV}" "${IS_UPGRADE}" "${docker_root}" "${CUSTOM_OPTIONS}" \
"${INSTALL_FOR_ALL}"
ret="$?" && [ $ret -ne 0 ] && return $ret
else
version_install "${install_type}" "${install_path_real}" "${filelist_path}" "${package}" "${feature_param}" \
"" "${USERNAME}" "${USERGROUP}" "${SETENV}" "${IS_UPGRADE}" "${docker_root}" "${CUSTOM_OPTIONS}" "${is_simple}"
ret="$?" && [ $ret -ne 0 ] && return $ret
fi
return 0
}
# 版本卸载函数
do_uninstall() {
local install_type="$1"
local install_path="$2"
local filelist_path="$3"
local package="$4"
local feature_param="$5"
local docker_root="$6"
local is_simple="$7"
local install_path_real ret
check_param_not_empty "package" "need set package parameter in uninstall!"
ret="$?" && [ ${ret} -ne 0 ] && return ${ret}
_package_to_log_pkg_name "LOG_PKG_NAME" "${package}"
check_ret_error "$?" "Set log package name failed in uninstall!"
ret="$?" && [ ${ret} -ne 0 ] && return ${ret}
expand_version_file
# 获取filelist.csv文件真实路径
get_realpath "filelist_path" "${filelist_path}"
# 获取install_path真实路径
get_realpath "install_path" "${install_path}"
if [ "${docker_root}" != "" ]; then
if [ "${WITH_DOCKER_ROOT_PREFIX}" = "y" ]; then
install_path_real="${install_path}"
else
install_path_real="${docker_root}${install_path}"
fi
else
install_path_real="${install_path}"
fi
if [ "${VERSION}" != "" ] && [ "${VERSION_DIR}" != "" ]; then
multi_version_uninstall "${install_type}" "${install_path_real}" "${filelist_path}" "${package}" "${feature_param}" \
"${VERSION}" "${VERSION_DIR}" "${USERNAME}" "${USERGROUP}" "${docker_root}" "${CUSTOM_OPTIONS}" "${IS_RECREATE_SOFTLINK}"
ret="$?" && [ $ret -ne 0 ] && return $ret
else
version_uninstall "${install_type}" "${install_path_real}" "${filelist_path}" "${package}" "${feature_param}" \
"" "${USERNAME}" "${docker_root}" "${CUSTOM_OPTIONS}" "${is_simple}"
ret="$?" && [ $ret -ne 0 ] && return $ret
fi
return 0
}
help_info() {
echo "Usage:"
echo ""
echo " ----------------------------------------------------------------------------------------------------"
echo ""
echo " $0 {--install,--uninstall,--mkdir,--makedir,--copy,--chmoddir,--restoremod,--remove}"
echo ""
echo " --install : Install package."
echo " --uninstall : Uninstall package."
echo " --mkdir : (Deprecated) Use --install instead. Create the install directories."
echo " --makedir : (Deprecated) Use --install instead. Create the install directories."
echo " --copy : (Deprecated) Use --install instead. Copy install files."
echo " --chmoddir : (Deprecated) Use --install instead. Set installed file's right."
echo " --restoremod : (Deprecated) Use --uninstall instead. Restore directories right."
echo " --remove : (Deprecated) Use --uninstall instead. Remove installed files."
echo ""
echo " Group options:"
echo " --install-path=<install-path> : Specify install path."
echo " --username=<username> : Specify install username."
echo " --usergroup=<usergroup> : Specify install usergroup."
echo " --install_for_all : Install for all users."
echo " Usually specified in root user install scene."
echo " --docker-root=<docker-root> : Specify docker root path."
echo " Install path is not contained docker root path."
echo " --chip=<chip> : Specify chip."
echo " Install files which chip matched or chip is all."
echo " --feature=<feature> : Specify feature. Default is all."
echo " Install files which feature matched or feature is comm."
echo " --feature-exclude-all : Switch feature mode."
echo " Install files which feature matched."
echo ""
echo " $0 --install [options] <install_type> <install_path> <filelist_path>"
echo ""
echo " Command options:"
echo " --package=<package> : Specify package name."
echo " --version=<version> : Specify version. --version-file is recommended."
echo " --version-dir=<version-dir> : Specify version directory. --version-file is recommended."
echo " --version-file=<version-file> : Specify version info file path."
echo " Common script will parse version and version_dir from version_file."
echo " If you specified this option, --version and --version-dir options"
echo " no longer need to be specified."
echo " --custom-options=<args> : Specify custom options for package custom script."
echo " --setenv : Add \"source setenv.\${shell_type}\" to rcfile."
echo " --set-cann-uninstall : Add uninstall command into cann_uninstall.sh."
echo " Always specified this in multi-version install."
echo ""
echo " $0 --uninstall [options] <install_type> <install_path> <filelist_path>"
echo ""
echo " Command options:"
echo " --package=<package> : Specify package name."
echo " --version=<version> : Specify version. --version-file is recommended."
echo " --version-dir=<version-dir> : Specify version directory. --version-file is recommended."
echo " --version-file=<version-file> : Specify version info file path."
echo " Common script will parse version and version_dir from version_file."
echo " If you specified this option, --version and --version-dir options"
echo " no longer need to be specified."
echo " --custom-options=<args> : Specify custom options for package custom script."
echo ""
echo " ----------------------------------------------------------------------------------------------------"
echo ""
echo " $0 {--add-cann-uninstall,--del-cann-uninstall}"
echo ""
echo " --add-cann-uninstall : Add uninstall command in cann_uninstall.sh."
echo " --del-cann-uninstall : Del uninstall command in cann_uninstall.sh."
echo ""
echo " Group options:"
echo " --install-path=<install-path> : Specify install path."
echo ""
echo " $0 --add-cann-uninstall [options] <script_dir>"
echo ""
echo " Command options:"
echo " --username=<username> : Specify install username."
echo " --usergroup=<usergroup> : Specify install usergroup."
echo " --install_for_all : Install for all users."
echo " Usually specified in root user install scene."
echo ""
echo " $0 --del-cann-uninstall [options] <script_dir>"
echo ""
echo " ----------------------------------------------------------------------------------------------------"
echo ""
echo " $0 {--add-env-rc,--del-env-rc}"
echo ""
echo " --add-env-rc : Add \"source setenv.\${shell_type}\" to rcfile."
echo " --del-env-rc : Del \"source setenv.\${shell_type}\" in rcfile."
echo ""
echo " Group options:"
echo " --username=<username> : Specify install username."
echo " --usergroup=<usergroup> : Specify install usergroup."
echo " --docker-root=<docker-root> : Specify docker root path."
echo " Install path is not contained docker root path."
echo ""
echo " $0 --add-env-rc [options] <install_path> <setenv_filepath> <shell_type>"
echo ""
echo " Command options:"
echo " --package=<package> : Specify package name."
echo " --setenv : Add \"source setenv.\${shell_type}\" to rcfile."
echo ""
echo " $0 --del-env-rc [options] <install_path> <setenv_filepath> <shell_type>"
echo ""
echo " ----------------------------------------------------------------------------------------------------"
echo ""
echo " $0 --pkg-in-dbinfo <install_path>"
echo ""
echo " Does package in ascend_package_db.info. Echo true or false."
echo ""
echo " Command options:"
echo " --package=<package> : Specify package name."
echo ""
echo " ----------------------------------------------------------------------------------------------------"
echo ""
echo " $0 --help"
echo ""
echo " Print help messages."
}
# env rc相关命令
env_rc_commands() {
local install_path
local setenv_filepath
local shell_type
case "${OPERATE_TYPE}" in
"add-env-rc")
install_path="$1"
setenv_filepath="$2"
shell_type="$3"
add_env_rc "${install_path}" "${setenv_filepath}" "${PACKAGE}" "${shell_type}" "${SETENV}" "${USERNAME}" "${USERGROUP}" "false" "${DOCKER_ROOT}"
exit 0
;;
"del-env-rc")
install_path="$1"
setenv_filepath="$2"
shell_type="$3"
del_env_rc "${install_path}" "${setenv_filepath}" "${shell_type}" "${USERNAME}" "${DOCKER_ROOT}"
exit 0
;;
esac
}
# db.info相关命令
dbinfo_commands() {
local install_path
case "${OPERATE_TYPE}" in
"pkg-in-dbinfo")
install_path="$1"
pkg_in_dbinfo "${install_path}" "${PACKAGE}"
exit 0
esac
}
# spc相关命令
spc_commands() {
local install_path="$1"
local filelist_path="$2"
local filelist_spc_path="$3"
local version_dir="$4"
local ret
case "${OPERATE_TYPE}" in
"spc_install")
install_patch "${install_path}" "${filelist_path}" "${filelist_spc_path}" "${version_dir}"
exit $?
;;
"spc_rollback")
rollback_patch "${install_path}" "${filelist_path}" "${version_dir}"
exit 0
;;
"spc_uninstall")
uninstall_patch "${install_path}" "${filelist_path}" "${version_dir}"
exit 0
;;
esac
}
# cann_uninstall总卸载脚本相关命令
cann_uninstall_commands() {
local script_dir="$1"
local ret
case "${OPERATE_TYPE}" in
"add-cann-uninstall")
do_add_cann_uninstall "${INSTALL_PATH}" "${script_dir}" "${USERNAME}" "${USERGROUP}" "${INSTALL_FOR_ALL}"
ret="$?" && [ ${ret} -ne 0 ] && exit 1
exit 0
;;
"del-cann-uninstall")
do_del_cann_uninstall "${INSTALL_PATH}" "${script_dir}"
ret="$?" && [ ${ret} -ne 0 ] && exit 1
exit 0
;;
esac
}
# 多版本创建相关命令
multi_version_commands() {
case "${OPERATE_TYPE}" in
"notify_create_softlink")
notify_latest_manager_create_softlink "$INSTALL_PATH/$LATEST_DIR/var" "$PACKAGE" "$VERSION" "$VERSION_DIR" \
"$INSTALL_FOR_ALL" "$DOCKER_ROOT"
ret="$?" && [ $ret -ne 0 ] && exit 1
exit 0
;;
"notify_remove_softlink")
notify_latest_manager_remove_softlink "$INSTALL_PATH/$LATEST_DIR/var" "$PACKAGE" "$VERSION" "$VERSION_DIR" \
"$INSTALL_FOR_ALL" "$DOCKER_ROOT"
ret="$?" && [ $ret -ne 0 ] && exit 1
exit 0
;;
esac
}
# 正式命令
formal_commands() {
local install_type="$1"
local install_path="$2"
local filelist_path="$3"
local input_feature input_chip
local ret docker_root
local feature_param thread_num
if [ "$FEATURE" != "all" ]; then
normalize_feature "input_feature" "$FEATURE" "${OPERATE_TYPE}"
else
if [ $# = 3 ]; then
input_feature="all"
else
normalize_feature "input_feature" "$4" "${OPERATE_TYPE}"
fi
fi
normalize_feature "input_chip" "$CHIP" "${OPERATE_TYPE}"
pack_feature_param "feature_param" "${input_feature}" "${FEATURE_EXCLUDE_ALL}" "${input_chip}"
# 移除docker_root右侧的/
rstrip_path "docker_root" "${DOCKER_ROOT}"
if [ "$PARALLEL_LIMIT" = "true" ]; then
get_thread_num "thread_num"
init_fifo "PARALLEL_FIFO" "$thread_num"
fi
case "${OPERATE_TYPE}" in
"install")
do_install "${install_type}" "${install_path}" "${filelist_path}" "${PACKAGE}" "${feature_param}" "${docker_root}" "n"
ret="$?" && [ $ret -ne 0 ] && return $ret
;;
"uninstall")
# 统一使用full模式卸载文件。两个包共用部分block如opp和opp_kernel以不同的模式安装时run/full
# full模式的包先卸载run模式的包后卸载确保能够完整卸载。
do_uninstall "full" "${install_path}" "${filelist_path}" "${PACKAGE}" "${feature_param}" "${docker_root}"
ret="$?" && [ $ret -ne 0 ] && return $ret
;;
"simple_install")
# 简化安装模式
do_install "${install_type}" "${install_path}" "${filelist_path}" "${PACKAGE}" "${feature_param}" "" "y"
ret="$?" && [ $ret -ne 0 ] && return $ret
;;
"simple_uninstall")
# 简化卸载模式
do_uninstall "full" "${install_path}" "${filelist_path}" "${PACKAGE}" "${feature_param}" "" "y"
ret="$?" && [ $ret -ne 0 ] && return $ret
;;
"mkdir")
do_create_dirs "all" "$1" "$2" "$3" "${PACKAGE}" "${feature_param}"
ret="$?" && [ $ret -ne 0 ] && return $ret
;;
"makedir")
do_create_dirs "mkdir" "$1" "$2" "$3" "${PACKAGE}" "${feature_param}"
ret="$?" && [ $ret -ne 0 ] && return $ret
;;
"copy")
do_copy_files "$1" "$2" "$3" "${PACKAGE}" "${feature_param}"
ret="$?" && [ $ret -ne 0 ] && return $ret
;;
"chmoddir")
do_chmod_file_dir "$install_type" "$2" "$3" "${feature_param}" "${PACKAGE}"
ret="$?" && [ $ret -ne 0 ] && return $ret
;;
"restoremod")
do_create_dirs "resetmod" "$1" "$2" "$3" "${PACKAGE}" "${feature_param}"
ret="$?" && [ $ret -ne 0 ] && return $ret
;;
"remove")
do_remove "$install_type" "$2" "$filelist_path" "${PACKAGE}" "${feature_param}"
ret="$?" && [ $ret -ne 0 ] && return $ret
;;
"print")
print_install_content "$1" "$2" "${PRINT_OPERATE_TYPE}" "$3" "${feature_param}"
ret="$?" && [ $ret -ne 0 ] && return $ret
;;
esac
return 0
}
# 正式命令并加锁
formal_commands_with_lock() {
local install_path="$2"
local lockfile docker_root install_path_real ret
if [ "${OPERATE_TYPE}" = "install" ] || [ "${OPERATE_TYPE}" = "uninstall" ]; then
if [ "${WITH_DOCKER_ROOT_PREFIX}" = "y" ]; then
install_path_real="${install_path}"
else
# 移除docker_root右侧的/
rstrip_path "docker_root" "${DOCKER_ROOT}"
install_path_real="${docker_root}${install_path}"
fi
else
install_path_real="${install_path}"
fi
lockfile="${install_path_real}/ascend.lock"
if [ ! -d "${install_path_real}" ]; then
# 兼容覆盖安装场景,包安装目录被删除情况
mkdir -p "${install_path_real}"
# 安装目录设置合适的权限
change_mod "${install_path_real}" "750" "${INSTALL_FOR_ALL}"
check_ret_error "$?" "Change mod ${install_path_real} failed!"
ret="$?" && [ $ret -ne 0 ] && return $ret
fi
# 使用文件描述符9作为并发锁
(
flock -n 9
if [ $? -ne 0 ]; then
log "ERROR" "Get ${install_path_real} lockfile failed! There may be another process also installing in the directory."
exit 1
fi
formal_commands "$@"
) 9> "${lockfile}"
ret="$?"
rm -f "${lockfile}"
if [ $ret -ne 0 ]; then
exit 1
fi
}
# 第一个参数为source标记为source场景不执行主流程
[ "$1" = "source" ] && return 0
# 全局变量
# change_mod_and_own_files与change_mod_and_own_dirs函数中会使用
INSTALL_FOR_ALL=""
SETENV=""
SET_CANN_UNINSTALL=""
IS_UPGRADE=""
IS_RECREATE_SOFTLINK=""
WITH_DOCKER_ROOT_PREFIX=""
FEATURE_EXCLUDE_ALL="n"
REMOVE_INSTALL_INFO="n" # 卸载时移除ascend_install.info文件
USE_SHARE_INFO="n"
CHIP="all"
FEATURE="all"
INCREMENT="n" # 增量安装
OPERATE_TYPE=""
PACKAGE=""
USERNAME=""
USERGROUP=""
VERSION=""
VERSION_DIR=""
VERSION_FILE=""
CUSTOM_OPTIONS=""
# 宿主机打docker包场景配置docker文件系统根路径
DOCKER_ROOT=""
# 安装路径
INSTALL_PATH=""
# 输入的latest_dir
INPUT_LATEST_DIR=""
while true; do
case "$1" in
--spc-install | -i)
OPERATE_TYPE="spc_install"
shift
;;
--spc-rollback | -l)
OPERATE_TYPE="spc_rollback"
shift
;;
--spc-uninstall | -u)
OPERATE_TYPE="spc_uninstall"
shift
;;
--install)
OPERATE_TYPE="install"
shift
;;
--uninstall)
OPERATE_TYPE="uninstall"
shift
;;
--simple-install)
OPERATE_TYPE="simple_install"
shift
;;
--simple-uninstall)
OPERATE_TYPE="simple_uninstall"
shift
;;
--copy | -c)
OPERATE_TYPE="copy"
shift
;;
--mkdir | -m)
OPERATE_TYPE="mkdir"
shift
;;
--makedir | -d)
OPERATE_TYPE="makedir"
shift
;;
--chmoddir | -o)
OPERATE_TYPE="chmoddir"
shift
;;
--restoremod | -e)
OPERATE_TYPE="restoremod"
shift
;;
--remove | -r)
OPERATE_TYPE="remove"
shift
;;
--add-cann-uninstall)
OPERATE_TYPE="add-cann-uninstall"
shift
;;
--del-cann-uninstall)
OPERATE_TYPE="del-cann-uninstall"
shift
;;
--add-env-rc)
OPERATE_TYPE="add-env-rc"
shift
;;
--del-env-rc)
OPERATE_TYPE="del-env-rc"
shift
;;
--pkg-in-dbinfo)
OPERATE_TYPE="pkg-in-dbinfo"
shift
;;
--add-pkg-blocks)
OPERATE_TYPE="add-pkg-blocks"
shift
;;
--del-pkg-blocks)
OPERATE_TYPE="del-pkg-blocks"
shift
;;
--create-latest-softlink)
OPERATE_TYPE="notify_create_softlink"
shift
;;
--create-package-latest-softlink)
OPERATE_TYPE="notify_create_softlink"
shift
;;
--remove-latest-softlink)
OPERATE_TYPE="notify_remove_softlink"
shift
;;
--remove-package-latest-softlink)
OPERATE_TYPE="notify_remove_softlink"
shift
;;
--print-blocks)
OPERATE_TYPE="print-blocks"
shift
;;
--print=*)
OPERATE_TYPE="print"
PRINT_OPERATE_TYPE="$(echo "$1" | cut -d"=" -f2)"
shift
;;
--print| -p)
OPERATE_TYPE="print"
PRINT_OPERATE_TYPE="copy mkdir move"
shift
;;
--install-path=*)
INSTALL_PATH=$(echo "$1" | cut -d"=" -f2)
shift
;;
--version=*)
VERSION=$(echo "$1" | cut -d"=" -f2)
shift
;;
--version-dir=*)
VERSION_DIR=$(echo "$1" | cut -d"=" -f2)
shift
;;
--version-file=*)
VERSION_FILE=$(echo "$1" | cut -d"=" -f2)
shift
;;
--latest-dir=*)
INPUT_LATEST_DIR=$(echo "$1" | cut -d"=" -f2)
shift
;;
--username=*)
USERNAME=$(echo "$1" | cut -d"=" -f2)
shift
;;
--usergroup=*)
USERGROUP=$(echo "$1" | cut -d"=" -f2)
shift
;;
--custom-options=*)
CUSTOM_OPTIONS=$(echo "$1" | cut -d"=" -f2-)
shift
;;
--arch=*)
PKG_ARCH=$(echo "$1" | cut -d"=" -f2-)
shift
if [ "$PKG_ARCH" = "" ]; then
log "ERROR" "The --arch option should not be an empty string."
exit 1
fi
;;
--upgrade)
IS_UPGRADE="y"
shift
;;
--recreate-softlink)
IS_RECREATE_SOFTLINK="y"
shift
;;
--install_for_all)
INSTALL_FOR_ALL="y"
shift
;;
--setenv)
SETENV="y"
shift
;;
--set-cann-uninstall)
SET_CANN_UNINSTALL="y"
shift
;;
--package=*)
PACKAGE=$(echo "$1" | cut -d"=" -f2)
shift
;;
--docker-root=*)
DOCKER_ROOT=$(echo "$1" | cut -d"=" -f2)
shift
;;
--chip=*)
CHIP="$(echo "$1" | cut -d"=" -f2)"
shift
;;
--feature=*)
FEATURE="$(echo "$1" | cut -d"=" -f2)"
shift
;;
--with-docker-root-prefix)
WITH_DOCKER_ROOT_PREFIX="y"
shift
;;
--feature-exclude-all)
FEATURE_EXCLUDE_ALL="y"
shift
;;
--remove-install-info)
REMOVE_INSTALL_INFO="y"
shift
;;
--use-share-info)
USE_SHARE_INFO="y"
shift
;;
--increment)
INCREMENT="y"
shift
;;
-h | --help)
help_info
exit 0
;;
-*)
echo Unrecognized input options : "$1"
help_info
exit 1
;;
*)
break
;;
esac
done
set_global_vars
env_rc_commands "$@"
dbinfo_commands "$@"
spc_commands "$@"
cann_uninstall_commands "$@"
multi_version_commands "$@"
if [ $# -lt 3 ]; then
log "ERROR" "It's too few input params: $*"
exit 1
fi
formal_commands_with_lock "$@"
exit $?