#!/usr/bin/env bash # # Initial script for UBLinux # This script are launching before starting init from initrd script # Current dir allways must be set to root (/) # All system path must be relative, except initrd dirs ENABLED=yes [[ ${ENABLED} == "yes" ]] || exit 0 DEBUGMODE=no PATH=.:/:/usr/bin:/usr/local/bin:/usr/local/sbin CMD_CHROOT= ; [[ -d /usr/lib/ublinux ]] || { [[ -d /sysroot ]] && ROOTFS="/sysroot" || ROOTFS="."; CMD_CHROOT="chroot ${ROOTFS}"; } SOURCE=${ROOTFS}/usr/lib/ublinux/functions; [[ -f ${SOURCE} ]] && . ${SOURCE} 2>/dev/null || exit 0 SOURCE=${ROOTFS}/usr/lib/ublinux/default; [[ -f ${SOURCE} ]] && . ${SOURCE} 2>/dev/null || exit 0 debug_mode "$0" "$@" SYSCONF="${ROOTFS}${SYSCONF}" SOURCE=${SYSCONF}/config; [[ -f ${SOURCE} ]] && . ${SOURCE} 2>/dev/null SOURCE=${SYSCONF}/users; [[ -f ${SOURCE} ]] && . ${SOURCE} 2>/dev/null SOURCE=${SYSCONF}/system; [[ -f ${SOURCE} ]] && . ${SOURCE} 2>/dev/null FILE_ROOT_USERS="${SYSCONF}/.users_credential" SOURCE=${FILE_ROOT_USERS}; [[ -f ${SOURCE} ]] && . ${SOURCE} 2>/dev/null FILE_PASSWD="${ROOTFS}/etc/passwd" FILE_SHADOW="${ROOTFS}/etc/shadow" FILE_GROUP="${ROOTFS}/etc/group" FILE_GSHADOW="${ROOTFS}/etc/gshadow" PATH_HOME="/home" NAME_REGEX="^[a-z_][-a-z0-9_]*\$" # Задать пароль пользователю # $1 # Имя пользователя # $2 # Зашифрованный пароля, если не указан, то пароль '!*' запрет авторизации set_passwd(){ USER_NAME="${1}" USER_PASS="${2}" [[ ${USER_NAME} != "" ]] || return 1 [[ ${USER_PASS} != "" ]] || USER_PASS='!*' if [[ -x ${ROOTFS}/usr/bin/chpasswd ]]; then echo "${USER_NAME}:${USER_PASS}" | ${CMD_CHROOT} /usr/bin/chpasswd --encrypted else ESC_USER_PASS=$(sed 's/[^a-zA-Z0-9,_@%-]/\\&/g' <<< "${USER_PASS}") EPOCH_DAY=$(( $(date +%s)/(60*60*24) )) # (60*60*24)=18400 second on day USER_FROM_SHADOW=$(grep "^${USER_NAME}:" "${FILE_SHADOW}") if [[ -z ${USER_FROM_SHADOW} ]]; then echo "${USER_NAME}:${USER_PASS}:${EPOCH_DAY}:0:99999:7:::" >> "${FILE_SHADOW}" elif [[ ! ${USER_FROM_SHADOW} =~ ^"${USER_NAME}:${USER_PASS}:" ]]; then sed -E "s/^${USER_NAME}:[^:]+:[0-9]+:/${USER_NAME}:${ESC_USER_PASS}:${EPOCH_DAY}:/" -i "${FILE_SHADOW}" sed -E "s/${USER_NAME}:[!]*:/${USER_NAME}:\!\*:/" -i "${FILE_SHADOW}" #sed /^${USER_NAME}:/d -i "${FILE_SHADOW}" #echo "${USER_NAME}:${USER_PASS}:${EPOCH_DAY}:0:99999:7:::" >> "${FILE_SHADOW}" fi fi } # Задать пароль группе # $1 # Имя группы # $2 # Зашифрованный пароля, если не указан, то пароль '!*' запрет авторизации #set_gpasswd(){ # GROUP_NAME="${1}" # GROUP_PASS="${2}" # [[ ${GROUP_NAME} != "" ]] || return 1 # [[ ${GROUP_PASS} != "" ]] || GROUP_PASS="!*" # if [[ -x ${ROOTFS}/usr/bin/chgpasswd ]]; then # echo "${GROUP_NAME}:${GROUP_PASS}" | ${CMD_CHROOT} /usr/bin/chgpasswd --encrypted # else # ESC_GROUP_PASS=$(sed 's/[^a-zA-Z0-9,_@%-]/\\&/g' <<< "${GROUP_PASS}") # GROUP_FROM_SHADOW=$(grep "^${GROUP_NAME}:" "${FILE_GSHADOW}") # if [[ -z ${GROUP_FROM_SHADOW} ]]; then # echo "${GROUP_NAME}:${GROUP_PASS}::" >> "${FILE_GSHADOW}" # elif [[ ! ${GROUP_FROM_SHADOW} =~ ^"${GROUP_NAME}:${GROUP_PASS}:" ]]; then # sed -E "s/^${GROUP_NAME}:[^:]*:/${GROUP_NAME}:${ESC_GROUP_PASS}:/" -i "${FILE_GSHADOW}" # fi # fi #} # Создать домашний каталог и копировать /etc/skel в домашний каталог пользователя # $1 # Имя пользователя # $2 # Основная группа пользователя, если не указана, то соответствует имени пользователя # $3 # Если указано, то принудительно копировать /etc/skel в домашний каталог пользователя create_home(){ local SELECT_USERNAME="${1}" local SELECT_GROUP="${2}" local SELECT_FORCESKEL="${3}" local ARG_RECURSIVE= [[ ${SELECT_GROUP} == "" || ${SELECT_GROUP} == "-" ]] && SELECT_GROUP=${SELECT_USERNAME} [[ ${SELECT_USERNAME} != "" ]] || return 1 if [[ -d "${ROOTFS}${PATH_HOME}/${SELECT_USERNAME}" ]]; then ${CMD_CHROOT} /usr/bin/chmod -f u+rw,g-rwx,o-rwx "${PATH_HOME}/${SELECT_USERNAME}" [[ -z ${SELECT_FORCESKEL} ]] || cp -Taf ${ROOTFS}/etc/skel "${ROOTFS}${PATH_HOME}/${SELECT_USERNAME}" else install -dm700 "${ROOTFS}${PATH_HOME}/${SELECT_USERNAME}" cp -Taf ${ROOTFS}/etc/skel "${ROOTFS}${PATH_HOME}/${SELECT_USERNAME}" fi #rsync -rlpt --ignore-existing etc/skel/ "${ROOTFS}${PATH_HOME}/${SELECT_USERNAME}" [[ -n ${ROOTFS} ]] && ARG_RECURSIVE="-R" || ARG_RECURSIVE= ${CMD_CHROOT} /usr/bin/chown -f ${ARG_RECURSIVE} "${SELECT_USERNAME}" ${PATH_HOME}/"${SELECT_USERNAME}" ${CMD_CHROOT} /usr/bin/chown -f ${ARG_RECURSIVE} :"${SELECT_GROUP}" "${PATH_HOME}/${SELECT_USERNAME}" } # Задаём пароль root пользователю exec_00_defaultrootpasswd(){ #echo "exec_00_defaultrootpasswd" [[ $1 == @("set="|"set+="|"set++="|"set-="|"set--="|"remove") ]] && COMMAND=$1 && shift [[ -n ${COMMAND} ]] || COMMAND="set=" local PARAM="$@" if [[ -n ${PARAM} ]]; then [[ ${PARAM%%=*} =~ [!\$%\&()*+,/\;\<\=\>?\^\{|\}~] ]] || eval "${PARAM%%=*}=\${PARAM#*=}" fi if [[ ${COMMAND} == @("set="|"set+="|"set++=") ]] && [[ -n ${DEFAULTROOTPASSWD} && ! ${DEFAULTROOTPASSWD,,} == @(no|none|disable) ]]; then # Добавить параметр в ${FILE_ROOT_USERS}=.users_credential и удалить параметр DEFAULTROOTPASSWD из '/etc/ublinux/users if [[ -n ${PARAM} && -z ${ROOTFS} ]]; then if [[ -f ${FILE_ROOT_USERS} ]]; then sed "/DEFAULTROOTPASSWD=/d" -i "${FILE_ROOT_USERS}" echo "DEFAULTROOTPASSWD='${DEFAULTROOTPASSWD}'" >> ${FILE_ROOT_USERS} fi [[ -f "${SYSCONF}/users" ]] && sed "/DEFAULTROOTPASSWD=/d" -i "${SYSCONF}/users" fi [[ -n ${DEFAULTROOTPASSWD} ]] && DEFAULTROOTPASSWD=$(return_hash_password hash ${HASHPASSWD} ${DEFAULTROOTPASSWD}) set_passwd root "${DEFAULTROOTPASSWD}" elif [[ ${COMMAND} == @("set-="|"set--="|"remove") ]]; then if [[ -n ${PARAM} && -z ${ROOTFS} ]]; then [[ -f ${FILE_ROOT_USERS} ]] && sed "/DEFAULTROOTPASSWD=/d" -i "${FILE_ROOT_USERS}" [[ -f "${SYSCONF}/users" ]] && sed "/DEFAULTROOTPASSWD=/d" -i "${SYSCONF}/users" fi fi } # Задаём пароль по умолчанию пользователю exec_00_defaultpasswd(){ #echo "exec_00_defaultpasswd" [[ $1 == @("set="|"set+="|"set++="|"set-="|"set--="|"remove") ]] && COMMAND=$1 && shift [[ -n ${COMMAND} ]] || COMMAND="set=" local PARAM="$@" if [[ -n ${PARAM} ]]; then [[ ${PARAM%%=*} =~ [!\$%\&()*+,/\;\<\=\>?\^\{|\}~] ]] || eval "${PARAM%%=*}=\${PARAM#*=}" fi if [[ ${COMMAND} == @("set="|"set+="|"set++=") ]] && [[ -n ${DEFAULTPASSWD} ]]; then # Добавить параметр в ${FILE_ROOT_USERS}=.users_credential и удалить параметр DEFAULTROOTPASSWD из '/etc/ublinux/users if [[ -n ${PARAM} && -z ${ROOTFS} ]]; then if [[ -f ${FILE_ROOT_USERS} ]]; then sed "/DEFAULTPASSWD=/d" -i "${FILE_ROOT_USERS}" echo "DEFAULTPASSWD='${DEFAULTPASSWD}'" >> ${FILE_ROOT_USERS} fi [[ -f "${SYSCONF}/users" ]] && sed "/DEFAULTPASSWD=/d" -i "${SYSCONF}/users" fi elif [[ ${COMMAND} == @("set-="|"set--="|"remove") ]]; then if [[ -n ${PARAM} && -z ${ROOTFS} ]]; then [[ -f ${FILE_ROOT_USERS} ]] && sed "/DEFAULTPASSWD=/d" -i "${FILE_ROOT_USERS}" [[ -f "${SYSCONF}/users" ]] && sed "/DEFAULTPASSWD=/d" -i "${SYSCONF}/users" fi fi } # Создаём группы из ${DEFAULTGROUP},${ADMGROUPS},${USERGROUPS} c ID из /usr/share/ublinux-sysusers/*.sysusers exec_01_add_groups(){ #echo "exec_01_add_groups" [[ $1 == @("set="|"set+="|"set++="|"set-="|"set--="|"remove") ]] && COMMAND=$1 && shift [[ -n ${COMMAND} ]] || COMMAND="set=" local PARAM="$@" local GROUPADD_GROUPS SELECT_GROUP ARG_FINDGROUP_ID FINDGROUP_ID DATA_FILE_GROUP=$(cat ${FILE_GROUP}) # Загрузить файлы которые совпадают в каталогах /usr/lib/sysusers.d/ и /usr/share/ublinux-sysusers/. И загрузить которые уникальные в /usr/lib/sysusers.d/ DATA_SYSUSERS=$(cat ${ROOTFS}/usr/lib/sysusers.d/*.conf ${ROOTFS}/usr/share/ublinux-sysusers/*.sysusers) if [[ -n ${PARAM} ]]; then GROUPADD_GROUPS=${PARAM} else GROUPADD_GROUPS="${DEFAULTGROUP},${ADMGROUPS},${USERGROUPS}" fi if [[ ${COMMAND} == @("set="|"set+="|"set++=") ]] && [[ -n ${GROUPADD_GROUPS} ]]; then GROUPADD_GROUPS=${GROUPADD_GROUPS//;/,}; GROUPADD_GROUPS="${GROUPADD_GROUPS//,,/,}" [[ ${GROUPADD_GROUPS:0:1} == ',' ]] && GROUPADD_GROUPS=${GROUPADD_GROUPS:1} [[ ${GROUPADD_GROUPS} =~ ','$ ]] && GROUPADD_GROUPS=${GROUPADD_GROUPS%*,} [[ -n ${GROUPADD_GROUPS} ]] && while IFS= read -u3 SELECT_GROUP; do local ARG_FINDGROUP_ID= # Найти группу по имени [[ ${DATA_SYSUSERS} =~ ($'\n'|^)+'g'[[:blank:]]+"${SELECT_GROUP}"[[:blank:]]+([[:digit:]]+)[^$'\n']*($'\n'|$)+ ]] && FINDGROUP_ID=${BASH_REMATCH[2]} || FINDGROUP_ID= # Найти группу по GID #[[ ${DATA_SYSUSERS} =~ ($'\n'|^)+'g'[[:blank:]]+([^$'\n']+)[[:blank:]]+"${SELECT_GROUP}"[^$'\n']*($'\n'|$)+ ]] && FINDGROUP_NAME=${BASH_REMATCH[2]} if [[ ${FINDGROUP_ID} != "" && ${DATA_FILE_GROUP} =~ ($'\n'|^)+${SELECT_GROUP}:[^$'\n']*:${FINDGROUP_ID}:[^$'\n']*($'\n'|$)+ ]]; then # Группа найдена, имя и id совпадают, пропускаем добавление continue elif [[ ${FINDGROUP_ID} != "" && ${DATA_FILE_GROUP} =~ ($'\n'|^)+${SELECT_GROUP}:[^$'\n']*($'\n'|$)+ ]]; then # Группа найдена, имя и id не совпадают, удаляем группу echo "WARNING: the group '${SELECT_GROUP}' has an id different from the template /usr/share/ublinux-sysusers/*.sysusers and the id will be changed to '${SELECT_GROUP}:${FINDGROUP_ID}'" ${CMD_CHROOT} /usr/bin/groupdel -f ${SELECT_GROUP} fi [[ ${FINDGROUP_ID} == @(""|"-") ]] || ARG_FINDGROUP_ID="--gid ${FINDGROUP_ID}" if [[ ${SELECT_GROUP} =~ ${NAME_REGEX} ]]; then ${CMD_CHROOT} /usr/bin/groupadd --force ${ARG_FINDGROUP_ID} ${SELECT_GROUP} else >&2 echo "ERROR: '${SELECT_GROUP}' cannot be a group name" fi done 3<<< "${GROUPADD_GROUPS//,/$'\n'}" fi } # Создаем пользователей из ${NEEDEDUSERS} и добавляем в группы # $1 Команды set или remove с режимом, варианты: set=|set+=|set++=|set-=|set--=|remove # $2 Для команды set=|set+=|set++= параметр со значением, пример: # Для команды set-=|set--=|remove параметр только с именем, пример: # null Если отсутствует $@, то применяем из системной конфигурации exec_02_neededusers(){ #echo "exec_02_neededusers" [[ $1 == @("set="|"set+="|"set++="|"set-="|"set--="|"remove") ]] && COMMAND=$1 && shift [[ -n ${COMMAND} ]] || COMMAND="set=" local PARAM="$@" local SELECT_USERNAME SELECT_UID SELECT_PASSWORD SELECT_GECOS NULL ADDGROUPS local ARG_DEFAULTGROUP ARG_SELECT_UID ARG_SELECT_GECOS if [[ -n ${PARAM} ]]; then [[ ${PARAM%%=*} =~ [!\$%\&()*+,/\;\<\=\>?\^\{|\}~] ]] || eval "${PARAM%%=*}=\${PARAM#*=}" fi # Если по умолчанию нет ни одного пользователя, то создаём администратора #[[ -z ${NEEDEDUSERS} ]] && NEEDEDUSERS="${DEFAULTUSER}:${ADMUID}:${DEFAULTPASSWD}:Administrator" [[ -z $(cmdline_value users) ]] || NEEDEDUSERS=$(cmdline_value users) [[ ${NOSECUREROOTPASSWD} == ${DEFAULTROOTPASSWD} ]] && ADDADM=yes if [[ -n ${NEEDEDUSERS} ]]; then while IFS= read -ru3 SELECT_USER; do # Добавить параметр в ${FILE_ROOT_USERS}=.users_credential и удалить параметр NEEDEDUSERS из '/etc/ublinux/users if [[ -n ${PARAM} && -z ${ROOTFS} ]]; then if [[ -f ${FILE_ROOT_USERS} ]]; then sed "/NEEDEDUSERS=/d" -i "${FILE_ROOT_USERS}" echo "NEEDEDUSERS='${SELECT_USER}'" >> ${FILE_ROOT_USERS} fi [[ -f "${SYSCONF}/users" ]] && sed "/NEEDEDUSERS=/d" -i "${SYSCONF}/users" fi IFS=: read -r SELECT_USERNAME SELECT_UID SELECT_PASSWORD SELECT_GECOS NULL <<< "${SELECT_USER}" [[ ${SELECT_PASSWORD} == "x" ]] && SELECT_PASSWORD="${DEFAULTPASSWD}" ADDGROUPS="${USERGROUPS}" [[ ${SELECT_UID} == ${ADMUID} && ${ADDADM} == "yes" ]] && ADDGROUPS="${USERGROUPS},${ADMGROUPS}" # Если указана обязательная синхронизация при каждом запуске, то пользователя удалить и создать нового if [[ ${USERADD_SYNC} =~ 'boot' || ${USERADD_SYNC[${SELECT_USERNAME}]} =~ 'boot' ]]; then if [[ -x ${ROOTFS}/usr/bin/userdel ]]; then ${CMD_CHROOT} /usr/bin/userdel -f ${SELECT_USERNAME} elif [[ -x ${ROOTFS}/usr/bin/busybox ]]; then # busybox deluser ${CMD_CHROOT} /usr/bin/busybox deluser ${SELECT_USERNAME} fi fi # Создаём пользователя if ! grep -q ^"${SELECT_USERNAME}": ${FILE_PASSWD} 2>/dev/null; then [[ -n ${SELECT_UID} ]] && ARG_SELECT_UID="-u ${SELECT_UID}" || ARG_SELECT_UID= if [[ -x ${ROOTFS}/usr/bin/useradd ]]; then [[ -n ${SELECT_GECOS} ]] && ARG_SELECT_GECOS="-c '${SELECT_GECOS}'" || ARG_SELECT_GECOS= [[ -n ${DEFAULTGROUP} ]] && ARG_DEFAULTGROUP="-G ${DEFAULTGROUP}" || ARG_DEFAULTGROUP= eval ${CMD_CHROOT} /usr/bin/useradd -M ${ARG_DEFAULTGROUP} ${ARG_SELECT_UID} ${ARG_SELECT_GECOS} ${SELECT_USERNAME} #>/dev/null 2>&1 elif [[ -x ${ROOTFS}/usr/bin/busybox ]]; then # busybox adduser [[ -n ${SELECT_GECOS} ]] && ARG_SELECT_GECOS="-g '${SELECT_GECOS}'" || ARG_SELECT_GECOS= [[ -n ${SELECT_GROUP} ]] && ARG_SELECT_GROUP="-G ${SELECT_GROUP}" || ARG_SELECT_GROUP="-G ${SELECT_USERNAME}" eval ${CMD_CHROOT} /usr/bin/busybox adduser -D -H ${ARG_DEFAULTGROUP} ${ARG_SELECT_UID} ${ARG_SELECT_GECOS} ${SELECT_USERNAME} #>/dev/null 2>&1 fi # Добавляем пользователя в группу USER_GROUPS="${ADDGROUPS//;/,}" ${CMD_CHROOT} /usr/bin/usermod -a -G ${USER_GROUPS%*,} ${SELECT_USERNAME} #>/dev/null 2>&1 # Задаём пароль пользователю #[[ -n ${SELECT_PASSWORD} ]] && return_hash_password "${SELECT_PASSWORD}" && [[ -n ${HASH_PASSWORD_NEW} ]] && SELECT_PASSWORD="${HASH_PASSWORD_NEW}" [[ -n ${SELECT_PASSWORD} ]] && SELECT_PASSWORD=$(return_hash_password hash ${HASHPASSWD} ${SELECT_PASSWORD}) set_passwd "${SELECT_USERNAME}" "${SELECT_PASSWORD}" fi # Создаём домашний каталог принудительно и копируем /etc/skel if [[ ! -d ${ROOTFS}${PATH_HOME}/"${SELECT_USERNAME}" \ || ${UPDATEHOME[${SELECT_USERNAME}],,} == @(yes|y|enable) \ || ${UPDATEHOME,,} == @(yes|y|enable) ]]; then create_home "${SELECT_USERNAME}" - force fi done 3< <(tr ",;" "\n" <<< "${NEEDEDUSERS}") fi } # Добавить пользователя системы в /etc/passwd. Если пользователь существует, то без изменений # $1 Команды set или remove с режимом, варианты: set=|set+=|set++=|set-=|set--=|remove # $2 Для команды set=|set+=|set++= параметр со значением, пример: USERADD[user-1]='Пользователь-1:x:x:vboxusers,libvirt:-s /usr/bin/bash:%%plain_password' # Для команды set-=|set--=|remove параметр только с именем, пример: USERADD[superadmin] # null Если отсутствует $@, то применяем из системной конфигурации USERADD[*] ## ## USERADD=no|none|disable # Отключить управление прользователями конфигурации ## USERADD[user_name]='gecos:uid:user_group:extra_groups:optional:password|x' ## user_name # Имя пользователя, обязательное поле ## gecos # Поле GECOS, с подробным описанием пользователя, можно локализованное, не обязательное ## uid # UID пользователя, если необходимо автоматически рассчитывать, то оставить пустым или 'x' ## user_group # Основная группа пользователя, номер или имя, если выбрано пусто или 'x', то 'user_group=user_name' ## extra_groups # Дополнительные группы пользователя. Дополнительные к USERGROUPS ## # Если группа отсутствует или 'x', то 'extra_groups=users'. Если группа не существует, то будет создана. Перечисление через запятую. ## optional # Дополнительные параметры, например: '--shell /usr/bin/bash --create-home --no-create-home --no-user-group --non-unique' ## --home-dir <ДОМ_КАТ> # Домашний каталог новой учётной записи ## -s, --shell /usr/bin/bash # Регистрационная оболочка новой учётной записи ## -r, --system # Создавать системную группу ## -M, --no-create-home # Не создавать домашний каталог пользователя ## -N, --no-user-group # Не создавать группу с тем же именем что и у пользователя ## -o, --non-unique # Разрешить создание пользователей с повторяющимися (не уникальными) UID, использовать только совместно с параметром ## --badnames # Не проверять имя на несоответствие правилам использования символов ## password|x # Хеш пароля пользователя, если пусто или 'x', то 'password=${DEFAULTPASSWD}', ## # Если первые символы (%%), то пароль хранится в нешифрованном виде ## # Если первые символы (!*), то аутентификация запрещена ## # Если первый символ (*) или (!), то аутентификация по паролю заблокирована. Но другие методы входа, ## # такие как аутентификация на основе ключей или переключение на пользователя, по-прежнему разрешены ## USERADD[superadmin]='Администратор:1000:x:x:x:$6$E7stRhRS8fCKk7UU$Qoqw62AUaUa5uLIc2KC7WV3MUThhrR8kjXtCODmnKCzKe2zHu1/wmsiWBHZEIk/IQnk/aELQYbUK93OUtrwg60' ## USERADD[user-1]=x ## USERADD[user-1]='Пользователь-1:x:x:vboxusers,libvirt:-s /usr/bin/bash:%%plain_password' ## ## Синхронизация пользователей системы /etc/passwd с глобальной конфигурацией ## USERADD_SYNC[user_name]='boot,shutdown' ## user_name # Имя пользователя, необязательное поле. Если не указано, то применяется для всех пользователей ## boot # При загрузке системы принудительно применить глобальную конфигурацию на пользователя ## shutdown # При завершении работы системы синхронизировать указанных пользователей в системе с глобальной конфигурацией exec_03_useradd(){ #echo "exec_03_useradd" [[ $1 == @("set="|"set+="|"set++="|"set-="|"set--="|"remove") ]] && COMMAND=$1 && shift [[ -n ${COMMAND} ]] || COMMAND="set=" [[ ${USERADD} != @(none|no|disable) ]] || return 0 [[ -n ${USERADD_SYNC} ]] || declare -gA USERADD_SYNC [[ -n ${UPDATEHOME} ]] || declare -gA UPDATEHOME [[ -n ${USERADD} ]] || declare -gA USERADD declare -gA USERSHADOW local SELECT_USERNAME SELECT_GECOS SELECT_UID SELECT_GROUP SELECT_EXTRAGROUP SELECT_OPTIONAL SELECT_PASSWORD NULL local ARG_SELECT_UID ARG_SELECT_GROUP ARG_SELECT_GECOS ARG_SELECT_PASSWORD ARG_SELECT_OPTIONAL local ARG_GROUPADD_GID ARG_GROUPADD_GROUPNAME local STATUS= local PARAM="$@" if [[ -n ${PARAM} ]]; then local USERADD= declare -A USERADD [[ ${PARAM%%=*} =~ [!\$%\&()*+,/\;\<\=\>?\^\{|\}~] ]] || eval "${PARAM%%=*}=\${PARAM#*=}" fi # Если в GRUB указан параметр useradd, то создать пользователя while IFS=':' read -u3 SELECT_USERNAME SELECT_UID SELECT_GROUP SELECT_EXTRAGROUP SELECT_PASSWORD NULL; do [[ ${SELECT_USERNAME} != "" ]] && USERADD[${SELECT_USERNAME}]=":${SELECT_UID}:${SELECT_GROUP}:${SELECT_EXTRAGROUP}:x:${SELECT_PASSWORD}" done 3< <(tr ';' '\n' <<< $(cmdline_value useradd)) if [[ ${COMMAND} == @("set="|"set+="|"set++=") ]]; then [[ ${#USERADD[@]} == 0 ]] && USERADD[${DEFAULTUSER}]="Administrator:${ADMUID}:x:x:x:${DEFAULTPASSWD}" [[ ${NOSECUREROOTPASSWD} == ${DEFAULTROOTPASSWD} ]] && ADDADM=yes useradd_local(){ DATA_FILE_PASSWD=$(cat ${FILE_PASSWD}) DATA_FILE_GROUP=$(cat ${FILE_GROUP}) local SELECT_USERNAME=$1 # Вызов как исполнителя после ubconfig # Добавить параметр в ${FILE_ROOT_USERS}=.users_credential и удалить хеш пароля параметра USERADD[.*] в /etc/ublinux/users if [[ -n ${PARAM} && -z ${ROOTFS} ]]; then if [[ -f ${FILE_ROOT_USERS} ]]; then sed "/USERADD\[${SELECT_USERNAME}\]=/d" -i "${FILE_ROOT_USERS}" echo "USERADD[${SELECT_USERNAME}]='${USERADD[${SELECT_USERNAME}]}'" >> ${FILE_ROOT_USERS} fi [[ -f "${SYSCONF}/users" ]] && sed -E "s/(USERADD\[${SELECT_USERNAME}\]=[\'\"]?)([^:]*:[^:]*:[^:]*:[^:]*:[^:]*:)[^\'\"]*([\'\"]?)/\1\2\3/g" -i "${SYSCONF}/users" fi # Проверяем существует ли пользователь в системе [[ ${DATA_FILE_PASSWD} =~ ($'\n'|^)+"${SELECT_USERNAME}": ]] && IS_USERNAME_PASSWD=yes || IS_USERNAME_PASSWD= # Проверяем отсутствие пользователя в системе или параметр принудительного обновления if [[ ${IS_USERNAME_PASSWD} == "" || ${USERADD_SYNC} =~ 'boot' || ${USERADD_SYNC[${SELECT_USERNAME}]} =~ 'boot' ]]; then IFS=: read -r SELECT_GECOS SELECT_UID SELECT_GROUP SELECT_EXTRAGROUPS SELECT_OPTIONAL SELECT_PASSWORD NULL <<< "${USERADD[${SELECT_USERNAME}]}" #echo -e "\n===> exec_03_useradd: ${SELECT_USERNAME}=${SELECT_GECOS}:${SELECT_UID}:${SELECT_GROUP}:${SELECT_EXTRAGROUPS}:${SELECT_OPTIONAL}:${SELECT_PASSWORD}" [[ ${SELECT_GECOS,,} == "x" ]] && SELECT_GECOS= [[ ${SELECT_OPTIONAL,,} == "x" ]] && SELECT_OPTIONAL= [[ ${SELECT_OPTIONAL} =~ ("--home-dir "|"-d ")([^' ']*)(' '|$) ]] && HOME_DIR_SELECT_USERNAME="${BASH_REMATCH[2]}" || HOME_DIR_SELECT_USERNAME="${PATH_HOME}/${SELECT_USERNAME}" [[ ${SELECT_UID,,} == "x" || ${SELECT_UID} =~ ^[^0-9]+$ ]] && SELECT_UID= # Если существует домашний каталог пользователя, то UID берём от каталога if [[ -z ${SELECT_UID} && -d "${ROOTFS}${HOME_DIR_SELECT_USERNAME}" ]]; then SELECT_UID=$(stat -c %u "${ROOTFS}${HOME_DIR_SELECT_USERNAME}") [[ ${DATA_FILE_PASSWD} =~ ($'\n'|^)+[^:]*:[^:]*:"${SELECT_UID}": ]] && SELECT_UID= fi [[ ${SELECT_GROUP,,} == "x" ]] && SELECT_GROUP= # Если существует домашний каталог пользователя, то GID берём от каталога if [[ -z ${SELECT_GROUP} && -d "${ROOTFS}${HOME_DIR_SELECT_USERNAME}" ]]; then SELECT_GROUP=$(stat -c %g "${ROOTFS}${HOME_DIR_SELECT_USERNAME}") [[ ${DATA_FILE_PASSWD} =~ ($'\n'|^)+[^:]*:[^:]*:[^:]*:"${SELECT_GROUP}": ]] && SELECT_GROUP= fi [[ ${SELECT_PASSWORD} == @(""|"x") ]] && SELECT_PASSWORD="${DEFAULTPASSWD}" [[ ${SELECT_PASSWORD} != @(""|'!*'|'!'|'*') ]] && SELECT_PASSWORD="$(return_hash_password hash ${HASHPASSWD} ${SELECT_PASSWORD})" [[ ${SELECT_EXTRAGROUPS,,} == "x" ]] && SELECT_EXTRAGROUPS= # Если в дополнительных группа присутствует группа по имени пользователя, то удалить её из списка SELECT_EXTRAGROUPS=${SELECT_EXTRAGROUPS//${SELECT_USERNAME}/} # Создадать группы из параметра SELECT_EXTRAGROUPS local SELECT_EXTRAGROUPS_TO_EXEC_01= local SELECT_EXTRAGROUPS_TO_EXEC_05= [[ -n ${SELECT_EXTRAGROUPS} ]] && while IFS= read -u4 ITEM_SELECT_EXTRAGROUP; do [[ ${ITEM_SELECT_EXTRAGROUP} != "" ]] || continue if [[ -n ${GROUPADD[${ITEM_SELECT_EXTRAGROUP}]} ]]; then #exec_05_groupadd "GROUPADD[${ITEM_SELECT_EXTRAGROUP}]=${GROUPADD[${ITEM_SELECT_EXTRAGROUP}]}" SELECT_EXTRAGROUPS_TO_EXEC_05+="exec_05_groupadd GROUPADD[${ITEM_SELECT_EXTRAGROUP}]=${GROUPADD[${ITEM_SELECT_EXTRAGROUP}]}; " else SELECT_EXTRAGROUPS_TO_EXEC_01+="${ITEM_SELECT_EXTRAGROUP}," fi done 4<<< "${SELECT_EXTRAGROUPS//,/$'\n'}" #[[ ${SELECT_EXTRAGROUPS_TO_EXEC_01} != "" ]] && echo "exec_01_add_groups ${SELECT_EXTRAGROUPS_TO_EXEC_01%*,}" # [[ ${SELECT_EXTRAGROUPS_TO_EXEC_01} != "" ]] && exec_01_add_groups "${SELECT_EXTRAGROUPS_TO_EXEC_01%*,}" #[[ ${SELECT_EXTRAGROUPS_TO_EXEC_05} != "" ]] && echo "eval ${SELECT_EXTRAGROUPS_TO_EXEC_05}" # [[ ${SELECT_EXTRAGROUPS_TO_EXEC_05} != "" ]] && eval "${SELECT_EXTRAGROUPS_TO_EXEC_05}" SELECT_EXTRAGROUPS="${SELECT_EXTRAGROUPS},${USERGROUPS}" [[ ${SELECT_UID} == ${ADMUID} && ${ADDADM} == "yes" ]] && SELECT_EXTRAGROUPS="${SELECT_EXTRAGROUPS},${ADMGROUPS}" SELECT_EXTRAGROUPS="${SELECT_EXTRAGROUPS//;/,}"; SELECT_EXTRAGROUPS="${SELECT_EXTRAGROUPS//,,/,}" [[ ${SELECT_EXTRAGROUPS:0:1} == "," ]] && SELECT_EXTRAGROUPS="${SELECT_EXTRAGROUPS:1}" #echo "===> ${SELECT_USERNAME}=${SELECT_GECOS}:${SELECT_UID}:${SELECT_GROUP}:${SELECT_EXTRAGROUPS}:${SELECT_OPTIONAL}:${SELECT_PASSWORD}" #echo "===> ${SELECT_USERNAME}=${SELECT_GECOS}:${SELECT_UID}:${SELECT_GROUP}:${SELECT_EXTRAGROUPS}:${SELECT_OPTIONAL}" ARG_SELECT_UID=; ARG_SELECT_GROUP=; ARG_SELECT_GECOS=; ARG_SELECT_PASSWORD=; ARG_SELECT_OPTIONAL=; STATUS=; IS_USERNAME_PASSWD= [[ -n ${SELECT_UID} && ${SELECT_UID} != 0 ]] && ARG_SELECT_UID="--uid ${SELECT_UID}" || ARG_SELECT_UID= # Если указана основная группа, но она не создана, то создать local ARG_GROUPADD_GID= ARG_GROUPADD_GROUPNAME= if [[ -n ${SELECT_GROUP} && -n ${GROUPADD[${SELECT_GROUP}]} ]]; then # Если группа указана и присутствует в списке групп GROUPADD[.] #echo 0:${SELECT_GROUP} #echo "exec_05_groupadd GROUPADD[${SELECT_GROUP}]=${GROUPADD[${SELECT_GROUP}]}" exec_05_groupadd "GROUPADD[${SELECT_GROUP}]=${GROUPADD[${SELECT_GROUP}]}" elif [[ -n ${SELECT_GROUP} && ! ${DATA_FILE_GROUP} =~ ($'\n'|^)+(${SELECT_GROUP}:|[^$'\n']*:${SELECT_GROUP}:) ]]; then # Если группа указана и не найдена в файле shadow # Группа имет цифровой GID и номер GID=UID if [[ ${SELECT_GROUP} =~ ^[[:digit:]]+$ && ${SELECT_GROUP} == ${SELECT_UID} ]]; then #echo 1:${SELECT_GROUP} ARG_GROUPADD_GID="${SELECT_GROUP}" ARG_GROUPADD_GROUPNAME=${SELECT_USERNAME} elif [[ ${SELECT_GROUP} =~ ^[[:digit:]]+$ && ${SELECT_GROUP} != ${SELECT_UID} ]]; then #echo 2:${SELECT_GROUP} # Группа имет цифровой GID и номер GID!=UID ARG_GROUPADD_GID="${SELECT_GROUP}" ARG_GROUPADD_GROUPNAME=${SELECT_USERNAME} elif [[ ${SELECT_GROUP} =~ ${NAME_REGEX} ]]; then #echo 3:${SELECT_GROUP} # Группа имет буквенный GID ARG_GROUPADD_GROUPNAME=${SELECT_USERNAME} else #echo 4:${SELECT_GROUP} # Если группа не имеет цифры и буквы SELECT_GROUP= fi if [[ -n ${ARG_GROUPADD_GROUPNAME} ]]; then [[ ${ARG_GROUPADD_GROUPNAME} =~ ${NAME_REGEX} ]] || ARG_GROUPADD_GROUPNAME="_${ARG_GROUPADD_GROUPNAME}" #echo "exec_05_groupadd GROUPADD[${ARG_GROUPADD_GROUPNAME}]=x:${ARG_GROUPADD_GID}" exec_05_groupadd "GROUPADD[${ARG_GROUPADD_GROUPNAME}]=x:${ARG_GROUPADD_GID}" fi fi if [[ ${IS_USERNAME_PASSWD} == "" ]]; then # Создаём пользователя if [[ -x ${ROOTFS}/usr/bin/useradd ]]; then [[ -n ${SELECT_GECOS} ]] && ARG_SELECT_GECOS="--comment '${SELECT_GECOS}'" || ARG_SELECT_GECOS= [[ -n ${SELECT_GROUP} ]] && ARG_SELECT_GROUP="--gid ${SELECT_GROUP}" || ARG_SELECT_GROUP= [[ -n ${SELECT_PASSWORD} ]] && ARG_SELECT_PASSWORD="--password '${SELECT_PASSWORD}'" || ARG_SELECT_PASSWORD= ARG_SELECT_OPTIONAL="${SELECT_OPTIONAL}" [[ ${SELECT_OPTIONAL} =~ ("-o"|"--non-unique") ]] && [[ -n ${ARG_SELECT_UID} ]] || { ARG_SELECT_OPTIONAL=${ARG_SELECT_OPTIONAL//-o/}; ARG_SELECT_OPTIONAL=${ARG_SELECT_OPTIONAL//--non-unique/}; } [[ ${SELECT_OPTIONAL} =~ ("-M"|"--no-create-home") ]] || { [[ -d "${ROOTFS}${HOME_DIR_SELECT_USERNAME}" ]] || ARG_SELECT_OPTIONAL+=" --create-home"; } [[ ${SELECT_OPTIONAL} =~ ("-N"|"--no-user-group") ]] || { [[ -z ${SELECT_GROUP} ]] && ARG_SELECT_OPTIONAL+=" --user-group"; } eval ${CMD_CHROOT} /usr/bin/useradd ${ARG_SELECT_UID} ${ARG_SELECT_GROUP} ${ARG_SELECT_GECOS} ${ARG_SELECT_OPTIONAL} ${ARG_SELECT_PASSWORD} ${SELECT_USERNAME}; STATUS=$? [[ ${STATUS} -eq 0 ]] || { echo "WARNING: Attempt 1 to use 'useradd ${ARG_SELECT_UID} ${ARG_SELECT_GROUP} ${ARG_SELECT_GECOS} ${ARG_SELECT_OPTIONAL} ${SELECT_USERNAME}' failed, try attempt 2"; \ eval ${CMD_CHROOT} /usr/bin/useradd ${ARG_SELECT_UID} ${ARG_SELECT_GROUP} ${ARG_SELECT_GECOS} ${ARG_SELECT_PASSWORD} ${SELECT_USERNAME}; STATUS=$?; } [[ ${STATUS} -eq 0 ]] || { echo "WARNING: Attempt 2 to use 'useradd ${ARG_SELECT_UID} ${ARG_SELECT_GROUP} ${ARG_SELECT_GECOS} ${SELECT_USERNAME}' failed, try attempt 3"; \ eval ${CMD_CHROOT} /usr/bin/useradd ${ARG_SELECT_UID} ${ARG_SELECT_GROUP} ${ARG_SELECT_PASSWORD} ${SELECT_USERNAME}; STATUS=$?; } [[ ${STATUS} -eq 0 ]] || { echo "WARNING: Attempt 3 to use 'useradd ${ARG_SELECT_UID} ${ARG_SELECT_GROUP} ${SELECT_USERNAME}' failed, try attempt 4"; \ eval ${CMD_CHROOT} /usr/bin/useradd ${ARG_SELECT_UID} ${ARG_SELECT_PASSWORD} ${SELECT_USERNAME}; STATUS=$?; } [[ ${STATUS} -eq 0 ]] || { echo "WARNING: Attempt 4 to use 'useradd ${ARG_SELECT_UID} ${SELECT_USERNAME}' failed, try attempt 5"; \ eval ${CMD_CHROOT} /usr/bin/useradd ${ARG_SELECT_PASSWORD} ${SELECT_USERNAME}; STATUS=$?; } [[ ${STATUS} -eq 0 ]] || { echo "WARNING: Attempt 5 to use 'useradd ${SELECT_USERNAME}' failed, try attempt 6"; \ eval ${CMD_CHROOT} /usr/bin/useradd ${SELECT_USERNAME}; STATUS=$?; } [[ ${STATUS} -eq 0 ]] || { >&2 echo "ERROR: Attempt 6 to use 'useradd ${SELECT_USERNAME}' failed, exit"; return 1; } elif [[ -x ${ROOTFS}/usr/bin/busybox ]]; then # busybox adduser [[ -n ${SELECT_GECOS} ]] && ARG_SELECT_GECOS="-g '${SELECT_GECOS}'" || ARG_SELECT_GECOS= [[ -n ${SELECT_GROUP} ]] && ARG_SELECT_GROUP="-G ${SELECT_GROUP}" || ARG_SELECT_GROUP="-G ${SELECT_USERNAME}" [[ ${SELECT_OPTIONAL} =~ ("-M"|"--no-create-home") ]] && ARG_SELECT_OPTIONAL+=" -H" eval ${CMD_CHROOT} /usr/bin/busybox adduser -D ${ARG_SELECT_UID} ${ARG_SELECT_GROUP} ${ARG_SELECT_GECOS} ${ARG_SELECT_OPTIONAL} ${SELECT_USERNAME} #>/dev/null 2>&1 # Задаём пароль пользователю set_passwd "${SELECT_USERNAME}" "${SELECT_PASSWORD}" fi else # Изменяем пользователя if [[ -x ${ROOTFS}/usr/bin/usermod ]]; then [[ -n ${SELECT_GECOS} ]] && ARG_SELECT_GECOS="--comment '${SELECT_GECOS}'" || ARG_SELECT_GECOS= [[ -n ${SELECT_GROUP} ]] && ARG_SELECT_GROUP="--gid ${SELECT_GROUP}" || ARG_SELECT_GROUP= [[ -n ${SELECT_PASSWORD} ]] && ARG_SELECT_PASSWORD="--password '${SELECT_PASSWORD}'" || ARG_SELECT_PASSWORD= ARG_SELECT_OPTIONAL= [[ ${SELECT_OPTIONAL} =~ ("-o"|"--non-unique") ]] && [[ -n ${ARG_SELECT_UID} ]] && ARG_SELECT_OPTIONAL+=" --non-unique" [[ ${SELECT_OPTIONAL} =~ ("--shell "|"-s ")([^' ']*)(' '|$) ]] && ARG_SELECT_OPTIONAL+=" --shell ${BASH_REMATCH[2]}" [[ ${SELECT_OPTIONAL} =~ ("--home-dir "|"-d ")([^' ']*)(' '|$) ]] && ARG_SELECT_OPTIONAL+=" --home ${BASH_REMATCH[2]} --move-home" eval ${CMD_CHROOT} /usr/bin/usermod ${ARG_SELECT_UID} ${ARG_SELECT_GROUP} ${ARG_SELECT_GECOS} ${ARG_SELECT_OPTIONAL} ${ARG_SELECT_PASSWORD} ${SELECT_USERNAME}; STATUS=$? [[ ${STATUS} -eq 0 ]] || { echo "WARNING: Attempt 1 to use 'usermod ${ARG_SELECT_UID} ${ARG_SELECT_GROUP} ${ARG_SELECT_GECOS} ${ARG_SELECT_OPTIONAL} ${SELECT_USERNAME}' failed, try attempt 2"; \ eval ${CMD_CHROOT} /usr/bin/usermod ${ARG_SELECT_UID} ${ARG_SELECT_GROUP} ${ARG_SELECT_GECOS} ${ARG_SELECT_PASSWORD} ${SELECT_USERNAME}; STATUS=$?; } [[ ${STATUS} -eq 0 ]] || { >&2 echo "ERROR: Attempt 2 to use 'usermod ${ARG_SELECT_UID} ${ARG_SELECT_GROUP} ${ARG_SELECT_GECOS} ${ARG_SELECT_PASSWORD} ${SELECT_USERNAME}' failed, exit"; return 1; } elif [[ -x ${ROOTFS}/usr/bin/busybox ]]; then true fi fi # Создаём дополнитеьные группы #[[ ${SELECT_EXTRAGROUPS_TO_EXEC_01} != "" ]] && echo "exec_01_add_groups ${SELECT_EXTRAGROUPS_TO_EXEC_01%*,}" [[ ${SELECT_EXTRAGROUPS_TO_EXEC_01} != "" ]] && exec_01_add_groups "${SELECT_EXTRAGROUPS_TO_EXEC_01%*,}" #[[ ${SELECT_EXTRAGROUPS_TO_EXEC_05} != "" ]] && echo "eval ${SELECT_EXTRAGROUPS_TO_EXEC_05}" [[ ${SELECT_EXTRAGROUPS_TO_EXEC_05} != "" ]] && eval "${SELECT_EXTRAGROUPS_TO_EXEC_05}" # Добавляем пользователя в основную группу if [[ -x ${ROOTFS}/usr/bin/usermod ]]; then # Добавляем пользователя в дополнительные группы ${CMD_CHROOT} /usr/bin/usermod -a -G ${SELECT_EXTRAGROUPS%*,} ${SELECT_USERNAME} #>/dev/null 2>&1 elif [[ -x ${ROOTFS}/usr/bin/busybox ]]; then true fi # Задаём параметры пароля пользователю /etc/shadow из USERSHADOW[user]. Только если запущено отдельно с параметром [[ -n ${PARAM} && -n ${USERSHADOW[${SELECT_USERNAME}]} ]] && exec_04_usershadow "USERSHADOW[${SELECT_USERNAME}]=${USERSHADOW[${SELECT_USERNAME}]}" # Проверим права на домашний каталог пользователя совпадают с указанным польователем, если нет, то переназначим if [[ -d ${ROOTFS}${HOME_DIR_SELECT_USERNAME} ]]; then GET_UID_GID_HOME=$(${CMD_CHROOT} /usr/bin/stat -c "%U:%G" ${HOME_DIR_SELECT_USERNAME}) GET_UID_GID_SELECT="$(${CMD_CHROOT} /usr/bin/id -u ${SELECT_USERNAME} 2>/dev/null):$(${CMD_CHROOT} /usr/bin/id -g ${SELECT_GROUP:-${SELECT_USERNAME}} 2>/dev/null)" if [[ ${GET_UID_GID_HOME} != ${GET_UID_GID_SELECT} ]]; then eval ${CMD_CHROOT} /usr/bin/chown -f -h "${SELECT_USERNAME}:" \ $(${CMD_CHROOT} find ${HOME_DIR_SELECT_USERNAME} -maxdepth 1 -printf '"%p"\n') \ $(cat ${ROOTFS}/etc/xdg/user-dirs.defaults 2>/dev/null | grep -v "^\s*#" | sed -E "s|.*=(.*)|${HOME_DIR_SELECT_USERNAME}/\1|") \ $(cat ${ROOTFS}${HOME_DIR_SELECT_USERNAME}/.config/user-dirs.dirs 2>/dev/null | grep -v "^\s*#"| sed -E "s|.*HOME/(.*)|${HOME_DIR_SELECT_USERNAME}/\"\1|") ARG_RECURSIVE="-hRP" eval ${CMD_CHROOT} /usr/bin/chown -f ${ARG_RECURSIVE} "${SELECT_USERNAME}:" \ $(${CMD_CHROOT} find ${HOME_DIR_SELECT_USERNAME} -maxdepth 1 -name ".*" -printf '"%p"\n') fi fi else echo "INFO: The user '${SELECT_USERNAME}' exists in the system, the settings are not applied. To force the settings, enable the '[users] USERADD_SYNC[${SELECT_USERNAME}]=boot' option" fi # Создаём домашний каталог принудительно и копируем /etc/skel if [[ ${UPDATEHOME,,} == @(yes|y|enable) \ || ${UPDATEHOME[${SELECT_USERNAME}],,} == @(yes|y|enable) ]]; then create_home "${SELECT_USERNAME}" "${SELECT_GROUP}" force fi } # Обработать всех пользователей у которых указан UID local LIST_USERADD_UID= LIST_USERADD_NOUID= while IFS= read -ru3 SELECT_USERNAME; do IFS=: read -r SELECT_GECOS SELECT_UID SELECT_GROUP SELECT_EXTRAGROUPS SELECT_OPTIONAL SELECT_PASSWORD NULL <<< "${USERADD[${SELECT_USERNAME}]}" if [[ ${SELECT_UID} =~ ^[0-9]+$ ]] ; then LIST_USERADD_UID+="useradd_local ${SELECT_USERNAME}; " else LIST_USERADD_NOUID+="useradd_local ${SELECT_USERNAME}; " fi done 3< <(printf "%s\n" "${!USERADD[@]}") eval "${LIST_USERADD_UID}" eval "${LIST_USERADD_NOUID}" elif [[ ${COMMAND} == @("set-="|"set--="|"remove") ]]; then if [[ ${PARAM%%=*} =~ ^.*'['(.*)']' ]]; then # Удалим пользователей только тех кто содержиться в файле учетных данных ${FILE_ROOT_USERS} SELECT_USERNAME=${BASH_REMATCH[1]} delete_select_username(){ local SELECT_USERNAME=$1 if [[ -n ${SELECT_USERNAME} ]] && ${CMD_CHROOT} /usr/bin/getent passwd ${SELECT_USERNAME} &>/dev/null; then ${CMD_CHROOT} /usr/bin/userdel --force ${SELECT_USERNAME} fi [[ -f ${FILE_ROOT_USERS} ]] && sed "/USERADD\[${SELECT_USERNAME}\]/d" -i "${FILE_ROOT_USERS}" 2>/dev/null ${CMD_CHROOT} /usr/bin/ubconfig --target system --noexecute remove [users] "USERSHADOW[${SELECT_USERNAME}]" } if [[ ${SELECT_USERNAME} == @("*"|"**"|"/"|"//") ]]; then [[ -f ${FILE_ROOT_USERS} ]] && while IFS= read -ru3 LINE_USERADD; do [[ ${LINE_USERADD} =~ ^.*'['(.*)']' ]] && delete_select_username ${BASH_REMATCH[1]} done 3< <(grep -E "USERADD\[.*\]" ${FILE_ROOT_USERS} 2>/dev/null) else delete_select_username ${SELECT_USERNAME} fi fi fi # echo -e "\nEND\n" } # Параметры пользователя системы /etc/shadow. Если пользователь существует, то без изменений # $1 Команды set или remove с режимом, варианты: set=|set+=|set++=|set-=|set--=|remove # $2 Для команды set=|set+=|set++= параметр со значением, пример: USERSHADOW[superadmin]=2023-01-01:0:99999:7::2025-01-01 # Для команды set-=|set--=|remove параметр только с именем, пример: USERSHADOW[superadmin] # null Если отсутствует $@, то применяем из системной конфигурации USERSHADOW[*] ## USERSHADOW[user_name]='lastchanged:minday:maxday:warn:inactive:expire' ## user_name # Имя пользователя, обязательное поле ## lastchanged # Дата последнего изменения пароля. Указывается количество дней, исчисляется с 1 января 1970 года (дата эпохи). Возможно указать дату формата: YYYY-MM-DD ## minday # Минимальное количество дней действия пароля, прежде чем пароль пользователя может быть изменен. По умолчанию 0 означает отсутствие минимального срока действия парол ## maxday # Максимальное количество дней действия пароля после смены пароля пользователя. По умолчанию этот номер установлен на 99999 ## warn # Количество дней предупреждения, в течение которого пользователь получает предупреждение о необходимости изменения пароля. По умолчанию 7 ## inactive # Количество дней не активности пароля до отключения учетной записи пользователя. По умолчанию пустое ## expire # Дата, когда учетная запись была отключена. Указывается количество дней, исчисляется с 1 января 1970 года (дата эпохи). Возможно указать дату формата: YYYY-MM-DD ## # Если один из параметров не задан, содержит пустое значение, то исходное значение не изменяется ## # Конвертировать кол-во дней от эпохи в понятную дату: date --date=@$(( DDDDD*(60*60*24) )); date --date=@EPOCH ## USERSHADOW[superadmin]=2023-01-01:0:99999:7::2025-01-01 ## USERSHADOW[superadmin]=18009:0:120:7:14: exec_04_usershadow(){ #echo "exec_04_usershadow" [[ $1 == @("set="|"set+="|"set++="|"set-="|"set--="|"remove") ]] && COMMAND=$1 && shift [[ -n ${COMMAND} ]] || COMMAND="set=" local SELECT_USERNAME SELECT_LASTCHANGED SELECT_MINDAY SELECT_MAXDAY SELECT_WARN SELECT_INACTIVE SELECT_EXPIRE NULL local ARG_SELECT_LASTCHANGED ARG_SELECT_MINDAY ARG_SELECT_MAXDAY ARG_SELECT_WARN ARG_SELECT_INACTIVE ARG_SELECT_EXPIRE local PARAM="$@" if [[ -n ${PARAM} ]]; then local USERSHADOW declare -A USERSHADOW [[ ${PARAM%%=*} =~ [!\$%\&()*+,/\;\<\=\>?\^\{|\}~] ]] || eval "${PARAM%%=*}=\${PARAM#*=}" fi if [[ ${COMMAND} == @("set="|"set+="|"set++=") ]] && [[ ${#USERSHADOW[@]} != 0 ]]; then while IFS= read -ru3 SELECT_USERNAME; do # Если пользователь не существует, то пропустить if [[ -n ${SELECT_USERNAME} ]]; then if ! ${CMD_CHROOT} /usr/bin/getent shadow ${SELECT_USERNAME} &>/dev/null; then ${CMD_CHROOT} /usr/bin/ubconfig --quiet --noexecute remove [users] "USERSHADOW[${SELECT_USERNAME}]" continue fi else continue fi IFS=: read -r SELECT_LASTCHANGED SELECT_MINDAY SELECT_MAXDAY SELECT_WARN SELECT_INACTIVE SELECT_EXPIRE NULL <<< "${USERSHADOW[${SELECT_USERNAME}]}" # Получить из секунд от эпохи текущую дату: date -d @1705841503 # Получить от эпохи количество дней: $(( $(date +%s)/(60*60*24) )). В дне 86400 секунд (60*60*24) #[[ ${SELECT_LASTCHANGED} =~ ^[0-9]{4,4}'-'[0-9]{1,2}'-'[0-9]{1,2}$ ]] && SELECT_LASTCHANGED_EPOH=$(date --date=${SELECT_LASTCHANGED} +"%s") #[[ -z ${SELECT_LASTCHANGED_EPOH} && -x /bin/busybox && ${SELECT_LASTCHANGED} =~ ^[0-9]{4,4}'.'[0-9]{1,2}'.'[0-9]{1,2}$ ]] && SELECT_LASTCHANGED_EPOH=$(busybox date --date="${SELECT_LASTCHANGED//./}0000" +"%s") #[[ -z ${SELECT_LASTCHANGED_EPOH} && -x ${ROOTFS}/usr/bin//date && ${SELECT_LASTCHANGED} =~ ^[0-9]{4,4}'.'[0-9]{1,2}'.'[0-9]{1,2}$ ]] && SELECT_LASTCHANGED_EPOH=$(${ROOTFS}/usr/bin/date --date="${SELECT_LASTCHANGED//./} 0000" +"%s") #[[ -n ${SELECT_LASTCHANGED_EPOH} ]] && SELECT_LASTCHANGED=$(( ${SELECT_LASTCHANGED_EPOH}/(60*60*24) )) #[[ ${SELECT_LASTCHANGED,,} == @(""|"x") || ${SELECT_LASTCHANGED} =~ ^[^0-9]*$ || ! ${SELECT_LASTCHANGED} =~ ^[0-9]{4,4}'-'[0-9]{1,2}'-'[0-9]{1,2}$ ]] && SELECT_LASTCHANGED= [[ ${SELECT_LASTCHANGED} =~ (^[0-9]*$|^[0-9]{4,4}'-'[0-9]{1,2}'-'[0-9]{1,2}$) ]] || SELECT_LASTCHANGED= [[ ${SELECT_MINDAY} =~ ^[0-9]*$ ]] || SELECT_MINDAY= [[ ${SELECT_MAXDAY} =~ ^[0-9]*$ ]] || SELECT_MAXDAY= [[ ${SELECT_WARN} =~ ^[0-9]*$ ]] || SELECT_WARN= [[ ${SELECT_INACTIVE} =~ (-1|^[0-9]*$) ]] || SELECT_INACTIVE= #[[ ${SELECT_EXPIRE} =~ ^[0-9]{4,4}'-'[0-9]{1,2}'-'[0-9]{1,2}$ ]] && SELECT_EXPIRE_EPOH=$(date --date=${SELECT_EXPIRE} +"%s") #[[ -z ${SELECT_EXPIRE_EPOH} && -x /bin/busybox && ${SELECT_EXPIRE} =~ ^[0-9]{4,4}'.'[0-9]{1,2}'.'[0-9]{1,2}$ ]] && SELECT_EXPIRE_EPOH=$(busybox date --date="${SELECT_EXPIRE//./}0000" +"%s") #[[ -z ${SELECT_EXPIRE_EPOH} && -x ${ROOTFS}/usr/bin/date && ${SELECT_EXPIRE} =~ ^[0-9]{4,4}'.'[0-9]{1,2}'.'[0-9]{1,2}$ ]] && SELECT_EXPIRE_EPOH=$(${ROOTFS}/usr/bin/date --date="${SELECT_EXPIRE//./} 0000" +"%s") #[[ -n ${SELECT_EXPIRE_EPOH} ]] && SELECT_EXPIRE=$(( ${SELECT_EXPIRE_EPOH}/(60*60*24) )) [[ ${SELECT_EXPIRE} =~ (-1|^[0-9]*$|^[0-9]{4,4}'-'[0-9]{1,2}'-'[0-9]{1,2}$) ]] || SELECT_EXPIRE= if [[ -z ${SELECT_LASTCHANGED} && -z ${SELECT_MINDAY} && -z ${SELECT_MAXDAY} && -z ${SELECT_WARN} && -z ${SELECT_INACTIVE} && -z ${SELECT_EXPIRE} ]]; then SELECT_LASTCHANGED= SELECT_MINDAY="0" SELECT_MAXDAY="99999" SELECT_WARN="7" SELECT_INACTIVE="-1" SELECT_EXPIRE="-1" fi [[ -n ${SELECT_LASTCHANGED} ]] && ARG_SELECT_LASTCHANGED="--lastday ${SELECT_LASTCHANGED}" || ARG_SELECT_LASTCHANGED= [[ -n ${SELECT_MINDAY} ]] && ARG_SELECT_MINDAY="--mindays ${SELECT_MINDAY}" || ARG_SELECT_MINDAY= [[ -n ${SELECT_MAXDAY} ]] && ARG_SELECT_MAXDAY="--maxdays ${SELECT_MAXDAY}" || ARG_SELECT_MAXDAY= [[ -n ${SELECT_WARN} ]] && ARG_SELECT_WARN="--warndays ${SELECT_WARN}" || ARG_SELECT_WARN= [[ -n ${SELECT_INACTIVE} ]] && ARG_SELECT_INACTIVE="--inactive ${SELECT_INACTIVE}" || ARG_SELECT_INACTIVE= [[ -n ${SELECT_EXPIRE} ]] && ARG_SELECT_EXPIRE="--expiredate ${SELECT_EXPIRE}" || ARG_SELECT_EXPIRE= # Задаём параметры пароля пользователя if [[ -x ${ROOTFS}/usr/bin/chage ]]; then ${CMD_CHROOT} /usr/bin/chage ${ARG_SELECT_LASTCHANGED} ${ARG_SELECT_MINDAY} ${ARG_SELECT_MAXDAY} ${ARG_SELECT_WARN} ${ARG_SELECT_INACTIVE} ${ARG_SELECT_EXPIRE} "${SELECT_USERNAME}" #>/dev/null 2>&1 fi done 3< <(printf "%s\n" "${!USERSHADOW[@]}") elif [[ ${COMMAND} == @("set-="|"set--="|"remove") ]]; then if [[ ${PARAM%%=*} =~ ^.*'['(.*)']' ]]; then SELECT_USERNAME=${BASH_REMATCH[1]} if [[ -n ${SELECT_USERNAME} ]] && ${CMD_CHROOT} /usr/bin/getent shadow ${SELECT_USERNAME} &>/dev/null; then if [[ -x ${ROOTFS}/usr/bin/chage ]]; then ${CMD_CHROOT} /usr/bin/chage --mindays 0 --maxdays 99999 --warndays 7 --inactive -1 --expiredate -1 ${SELECT_USERNAME} fi fi fi fi } # Функция добавление/удаление групп в систему. Если группа существует, то изменить под параметры # $1 Команды set или remove с режимом, варианты: set=|set+=|set++=|set-=|set--=|remove # $2 Для команды set=|set+=|set++= параметр со значением, пример: GROUPADD[g_department_1]=ob.ivanov,rv.smirnov # Для команды set-=|set--=|remove параметр только с именем, пример: GROUPADD[g_department_1] # null Если отсутствует $@, то применяем из системной конфигурации GROUPADD[*] ## GROUPADD[group_name]='group_users:gid:optional:password|x' ## group_name # Имя группы ## group_users # Пользователи группы, перечисление через запятую. Может быть пусто. ## gid # GID группы, если необходимо автоматически рассчитывать, то оставить пустым или 'x' ## optional # Дополнительные параметры, например: '--system --non-unique' ## -o, --non-unique # Разрешить создание групп с повторяющимися (не уникальными) GID ## -r, --system # Cоздавать системную группу ## administrators # Администраторы группы которые могут менять пароль группы и добавлять членов ## password|x # Хеш пароля группа, если выбрано 'x' или пусто, то группа без пароля ## GROUPADD[g_department_1]=ob.ivanov,rv.smirnov ## GROUPADD[g_department_2]='ob.ivanov,rv.smirnov:1001:x:superadmin:$6$E7stRhRS8fCKk7UU$Qoqw62AUaUa5uLIc2KC7WV3MUThhrR8kjXtCODmnKCzKe2zHu1/wmsiWBHZEIk/IQnk/aELQYbUK93OUtrwg60' exec_05_groupadd(){ #echo "exec_05_groupadd" [[ $1 == @("set="|"set+="|"set++="|"set-="|"set--="|"remove") ]] && COMMAND=$1 && shift [[ -n ${COMMAND} ]] || COMMAND="set=" local PARAM="$@" local SELECT_GROUP SELECT_USERS SELECT_GID SELECT_OPTIONAL SELECT_ADMINISTRATORS SELECT_PASSWORD NULL local ARG_SELECT_USERS ARG_SELECT_GID SELECT_OPTIONAL ARG_SELECT_PASSWORD ARG_NON_UNIQUE local DATA_FILE_PASSWD REAL_SELECT_USERS REAL_SELECT_ADMINISTRATORS DATA_SYSUSERS=$(cat ${ROOTFS}/usr/lib/sysusers.d/*.conf ${ROOTFS}/usr/share/ublinux-sysusers/*.sysusers) if [[ -n ${PARAM} ]]; then local GROUPADD= declare -A GROUPADD [[ ${PARAM%%=*} =~ [!\$%\&()*+,/\;\<\=\>?\^\{|\}~] ]] || eval "${PARAM%%=*}=\${PARAM#*=}" fi if [[ ${COMMAND} == @("set="|"set+="|"set++=") ]] && [[ ${#GROUPADD[@]} != 0 ]]; then groupadd_local(){ local SELECT_GROUP=$1 # Добавить параметр в ${FILE_ROOT_USERS}=.users_credential и удалить параметр GROUPADD[.*] из '/etc/ublinux/users if [[ -n ${PARAM} && -z ${ROOTFS} ]]; then if [[ -f ${FILE_ROOT_USERS} ]]; then sed "/GROUPADD\[${SELECT_GROUP}\]=/d" -i "${FILE_ROOT_USERS}" echo "GROUPADD[${SELECT_GROUP}]='${GROUPADD[${SELECT_GROUP}]}'" >> ${FILE_ROOT_USERS} fi [[ -f "${SYSCONF}/users" ]] && sed -E "s/(GROUPADD\[${SELECT_GROUP}\]=[\'\"]?)([^:]*:[^:]*:[^:]*:[^:]*:)[^\'\"]*([\'\"]?)/\1\2\3/g" -i "${SYSCONF}/users" fi IFS=: read -r SELECT_USERS SELECT_GID SELECT_OPTIONAL SELECT_ADMINISTRATORS SELECT_PASSWORD NULL <<< "${GROUPADD[${SELECT_GROUP}]}" [[ ${SELECT_USERS} == "x" ]] && SELECT_USERS= [[ ${SELECT_GID,,} == "x" || ${SELECT_GID} =~ ^[^0-9]*$ ]] && SELECT_GID= #echo "==> exec_05_groupadd: ${SELECT_GROUP}:${SELECT_USERS}:${SELECT_GID}:${SELECT_OPTIONAL}:${SELECT_ADMINISTRATORS}:${SELECT_PASSWORD}" [[ ${SELECT_OPTIONAL} == "x" ]] && SELECT_OPTIONAL= [[ ${SELECT_PASSWORD} == @(""|"x") ]] && SELECT_PASSWORD= [[ ${SELECT_PASSWORD} != @(""|'!*'|'!'|'*') ]] && SELECT_PASSWORD=$(return_hash_password hash ${HASHPASSWD} ${SELECT_PASSWORD}) # Поиск по имени в шаблонах пользователей/групп systemd [[ ${DATA_SYSUSERS} =~ ($'\n'|^)+'g'[[:blank:]]+"${SELECT_GROUP}"[[:blank:]]+([[:digit:]]+)[^$'\n']*($'\n'|$)+ ]] && FINDGROUP_ID=${BASH_REMATCH[2]} || FINDGROUP_ID= # Поиск по GID в шаблонах пользователей/групп systemd [[ -z ${FINDGROUP_ID} ]] \ && [[ ${DATA_SYSUSERS} =~ ($'\n'|^)+'g'[[:blank:]]+([^$'\n']+)[[:blank:]]+"${SELECT_GROUP}"[^$'\n']*($'\n'|$)+ ]] && FINDGROUP_NAME=${BASH_REMATCH[2]} || FINDGROUP_NAME= [[ -n ${FINDGROUP_ID} ]] && SELECT_GID="${FINDGROUP_ID}" [[ -n ${FINDGROUP_NAME} ]] && SELECT_GID="${FINDGROUP_NAME}" DATA_FILE_GROUP=$(cat ${FILE_GROUP}) # Добавляем аргументы к опциям, при условии что такого GID не существует [[ -n ${SELECT_GID} ]] && [[ ! ${DATA_FILE_GROUP} =~ :${SELECT_GID}: ]] && ARG_SELECT_GID="--gid ${SELECT_GID}" || ARG_SELECT_GID= #[[ -n ${SELECT_USERS} ]] && ARG_SELECT_USERS="--users ${SELECT_USERS}" || ARG_SELECT_USERS= [[ -n ${SELECT_PASSWORD} ]] && ARG_SELECT_PASSWORD="--password '${SELECT_PASSWORD}'" || ARG_SELECT_PASSWORD= [[ ${SELECT_OPTIONAL} =~ ("-o"|"--non-unique") ]] && [[ -n ${ARG_SELECT_GID} ]] || { SELECT_OPTIONAL=${SELECT_OPTIONAL//-o/}; SELECT_OPTIONAL=${SELECT_OPTIONAL//--non-unique/}; } # Создаём группу, если создана то изменяем под установленные параметры if [[ ! ${DATA_FILE_GROUP} =~ ($'\n'|^)+${SELECT_GROUP}: ]]; then if [[ -x ${ROOTFS}/usr/bin/groupadd ]]; then #${CMD_CHROOT} /usr/bin/groupadd --force ${ARG_SELECT_USERS} ${ARG_SELECT_GID} ${SELECT_OPTIONAL} ${ARG_SELECT_PASSWORD} ${SELECT_GROUP} #echo "eval ${CMD_CHROOT} /usr/bin/groupadd --force ${ARG_SELECT_GID} ${SELECT_OPTIONAL} ${ARG_SELECT_PASSWORD} ${SELECT_GROUP}" eval ${CMD_CHROOT} /usr/bin/groupadd --force ${ARG_SELECT_GID} ${SELECT_OPTIONAL} ${ARG_SELECT_PASSWORD} ${SELECT_GROUP} [[ $? -eq 0 ]] || { echo "WARNING: Attempt 1 to use 'groupadd ${ARG_SELECT_GID} ${SELECT_OPTIONAL} ${SELECT_GROUP}' failed, try attempt 2"; \ eval ${CMD_CHROOT} /usr/bin/groupadd --force ${ARG_SELECT_GID} ${ARG_SELECT_PASSWORD} ${SELECT_GROUP} ; } [[ $? -eq 0 ]] || { echo "WARNING: Attempt 2 to use 'groupadd ${ARG_SELECT_GID} ${SELECT_GROUP}' failed, try attempt 3"; \ eval ${CMD_CHROOT} /usr/bin/groupadd --force ${ARG_SELECT_PASSWORD} ${SELECT_GROUP} ; } [[ $? -eq 0 ]] || { echo "WARNING: Attempt 3 to use 'groupadd ${SELECT_GROUP}' failed, try attempt 4"; \ ${CMD_CHROOT} /usr/bin/groupadd --force ${SELECT_GROUP} ; } [[ $? -eq 0 ]] || { >&2 echo "ERROR: Attempt 4 to use 'groupadd ${SELECT_GROUP}' failed, exit"; return 1; } elif [[ -x ${ROOTFS}/usr/bin/busybox ]]; then true # Задаём пароль группе # set_gpasswd "${SELECT_GROUP}" "${SELECT_PASSWORD}" fi elif [[ -n ${ARG_SELECT_GID} ]]; then if [[ -x ${ROOTFS}/usr/bin/groupmod ]]; then # т.к. groupmod принимет не все возможные аргументы совместимы с groupadd, то фильтруем [[ ${SELECT_OPTIONAL} =~ ("--non-unique"|"-o") ]] && [[ -n ${ARG_SELECT_GID} ]] && ARG_NON_UNIQUE="--non-unique" || ARG_NON_UNIQUE= [[ -n ${SELECT_PASSWORD} ]] && ARG_SELECT_PASSWORD="--password '${SELECT_PASSWORD}'" || ARG_SELECT_PASSWORD= #eval ${CMD_CHROOT} /usr/bin/groupmod --append ${ARG_SELECT_USERS} ${ARG_SELECT_GID} ${ARG_NON_UNIQUE} ${ARG_SELECT_PASSWORD} ${SELECT_GROUP} #echo "eval ${CMD_CHROOT} /usr/bin/groupmod ${ARG_SELECT_GID} ${ARG_NON_UNIQUE} ${ARG_SELECT_PASSWORD} ${SELECT_GROUP}" eval ${CMD_CHROOT} /usr/bin/groupmod ${ARG_SELECT_GID} ${ARG_NON_UNIQUE} ${ARG_SELECT_PASSWORD} ${SELECT_GROUP} elif [[ -x ${ROOTFS}/usr/bin/busybox ]]; then true # Задаём пароль группе # set_gpasswd "${SELECT_GROUP}" "${SELECT_PASSWORD}" fi fi DATA_FILE_PASSWD=$(cat ${FILE_PASSWD}) local REAL_SELECT_USERS= REAL_SELECT_ADMINISTRATORS= # Если пользователь не существуют то убрать из списка SELECT_USERS while IFS= read -r ITEM_SELECT_USERS; do [[ ${DATA_FILE_PASSWD} =~ ($'\n'|^)+${ITEM_SELECT_USERS}: ]] && REAL_SELECT_USERS+=",${ITEM_SELECT_USERS}" done <<< ${SELECT_USERS//,/$'\n'} [[ ${REAL_SELECT_USERS:0:1} == "," ]] && REAL_SELECT_USERS=${REAL_SELECT_USERS:1} [[ ${REAL_SELECT_USERS} != "" ]] && SELECT_USERS=${REAL_SELECT_USERS} || SELECT_USERS= # Если пользователь не существуют то убрать из списка REAL_SELECT_ADMINISTRATORS while IFS= read -r ITEM_SELECT_ADMINISTRATORS; do [[ ${DATA_FILE_PASSWD} =~ ($'\n'|^)+${ITEM_SELECT_ADMINISTRATORS}: ]] && REAL_SELECT_ADMINISTRATORS+=",${ITEM_SELECT_ADMINISTRATORS}" done <<< ${SELECT_ADMINISTRATORS//,/$'\n'} [[ ${REAL_SELECT_ADMINISTRATORS:0:1} == "," ]] && REAL_SELECT_ADMINISTRATORS=${REAL_SELECT_ADMINISTRATORS:1} [[ ${REAL_SELECT_ADMINISTRATORS} != "" ]] && SELECT_ADMINISTRATORS=${REAL_SELECT_ADMINISTRATORS} || SELECT_ADMINISTRATORS= # Добавляем пользователей в группу, т.к. groupadd не добавил пользователей в /etc/gshadow if [[ -n ${SELECT_USERS} || -n ${SELECT_ADMINISTRATORS} ]]; then if [[ -x ${ROOTFS}/usr/bin/gpasswd ]]; then [[ -n ${SELECT_USERS} ]] && ARG_SELECT_USERS="-M ${SELECT_USERS}" || ARG_SELECT_USERS= [[ -n ${SELECT_ADMINISTRATORS} ]] && ARG_SELECT_ADMINISTRATORS="-A ${SELECT_ADMINISTRATORS}" || ARG_SELECT_ADMINISTRATORS= #echo "${CMD_CHROOT} /usr/bin/gpasswd ${ARG_SELECT_ADMINISTRATORS} ${ARG_SELECT_USERS} ${SELECT_GROUP}" ${CMD_CHROOT} /usr/bin/gpasswd ${ARG_SELECT_ADMINISTRATORS} ${ARG_SELECT_USERS} ${SELECT_GROUP} #>/dev/null 2>&1 elif [[ -x ${ROOTFS}/usr/bin/busybox ]]; then true fi fi } local LIST_GROUPADD_GID= LIST_GROUPADD_NOGID= while IFS= read -ru3 SELECT_GROUP; do [[ ${SELECT_GROUP} =~ ${NAME_REGEX} ]] || { >&2 echo "ERROR: '${SELECT_GROUP}' cannot be a group name"; continue; } IFS=: read -r SELECT_USERS SELECT_GID SELECT_OPTIONAL SELECT_ADMINISTRATORS SELECT_PASSWORD NULL <<< "${GROUPADD[${SELECT_GROUP}]}" if [[ ${SELECT_GID} =~ ^[0-9]+$ ]] ; then LIST_GROUPADD_GID+="groupadd_local ${SELECT_GROUP}; " else LIST_GROUPADD_NOGID+="groupadd_local ${SELECT_GROUP}; " fi done 3< <(printf "%s\n" "${!GROUPADD[@]}") [[ -n ${LIST_GROUPADD_GID} ]] && eval "${LIST_GROUPADD_GID}" [[ -n ${LIST_GROUPADD_NOGID} ]] && eval "${LIST_GROUPADD_NOGID}" elif [[ ${COMMAND} == @("set-="|"set--="|"remove") ]]; then if [[ ${PARAM%%=*} =~ ^.*'['(.*)']' ]]; then SELECT_GROUP=${BASH_REMATCH[1]} delete_select_group(){ local SELECT_GROUP=$1 if [[ -n ${SELECT_GROUP} ]] && ${CMD_CHROOT} /usr/bin/getent group ${SELECT_GROUP} &>/dev/null; then ${CMD_CHROOT} /usr/bin/groupdel --force ${SELECT_GROUP} fi [[ -f ${FILE_ROOT_USERS} ]] && sed "/GROUPADD\[${SELECT_GROUP}\]/d" -i "${FILE_ROOT_USERS}" 2>/dev/null } if [[ ${SELECT_GROUP} == @("*"|"**"|"/"|"//") ]]; then [[ -f ${FILE_ROOT_USERS} ]] && while IFS= read -ru3 LINE_GROUPADD; do [[ ${LINE_GROUPADD} =~ ^.*'['(.*)']' ]] && delete_select_group ${BASH_REMATCH[1]} done 3< <(grep -E "GROUPADD\[.*\]" ${FILE_ROOT_USERS} 2>/dev/null) else delete_select_group ${SELECT_GROUP} fi fi fi } # Autodetect firststart # Если пароли по умолчанию, то firststart exec_99_firststart(){ #echo "exec_99_firststart" [[ $1 == @("set="|"set+="|"set++="|"set-="|"set--="|"remove") ]] && COMMAND=$1 && shift [[ -n ${COMMAND} ]] || COMMAND="set=" local PARAM="$@" if [[ -n ${PARAM} ]]; then local FIRSTSTART= [[ ${PARAM%%=*} =~ [!\$%\&()*+,/\;\<\=\>?\^\{|\}~] ]] || eval "${PARAM%%=*}=\${PARAM#*=}" fi if [[ -n ${ROOTFS} ]]; then if [[ ${NOSECUREROOTPASSWD} == ${DEFAULTROOTPASSWD} ]] \ && grep -q "^$(grep ".*:x:${ADMUID}:" ${ROOTFS}/etc/passwd | cut -d: -f1):${NOSECUREROOTPASSWD}:" ${ROOTFS}/etc/shadow; then [[ $(cat ${SYSCONF}/config 2>/dev/null) =~ ($'\n'|^)+'FIRSTSTART=' ]] || echo "FIRSTSTART=yes" >> ${SYSCONF}/config fi elif [[ ${COMMAND} == @("set="|"set+="|"set++=") ]] && [[ -n ${FIRSTSTART} ]]; then [[ $(cat ${SYSCONF}/config 2>/dev/null) =~ ($'\n'|^)+'FIRSTSTART=' ]] || echo "FIRSTSTART=yes" >> ${SYSCONF}/config elif [[ ${COMMAND} == @("set-="|"set--="|"remove") ]]; then sed "/FIRSTSTART=/d" -i ${SYSCONF}/config fi } ################ ##### MAIN ##### ################ # Если файл подключен как ресурс с функциями, то выйти return 0 2>/dev/null && return 0 #rm -f "${FILE_ROOT_USERS}" if [[ -z $@ ]]; then while read -ru3 FUNCTION; do $"${FUNCTION##* }" done 3< <(declare -F | grep "declare -f exec_") else FUNCTION= while [[ $# -gt 0 ]]; do [[ -z ${1} ]] || { declare -f ${1} &>/dev/null && FUNCTION+="; ${1}" || FUNCTION+=" '${1}'"; } shift done eval ${FUNCTION#*; } fi