
Add Debian packaging infrastructure for platform-kickstarts Test Plan: PASS: Verify CentOS package build and iso create PASS: Verify Debian package build and iso create PASS: Verify PXE Boot install with kickstart (single disk) PASS: Verify kickstart xxxPLATFORM_RELEASExxx variable replacement PASS: Verify platform backup partition creation and persistence PASS: Verify single disk vg and lv setup ; log and scratch PASS: Verify install traits=controller,worker boot paramter handling PASS: Verify disk boot kernel parameter cmdline update (aio) PASS: Verify platform.conf setup PASS: Verify INSTALL_UUID setup PASS: Verify boot interface setup, dhcp and login support PASS: Verify install script and logs preserved over an install PASS: Verify instdev with by-path notation PASS: Verify ostree repo pull to feed dir Limitations: - Single Disk install - Currently investigating lv leaking to other disks - Do not specify lowlatency trait without low latency kernel - USB install does not use this kickstart yet ; its not in the iso Story: 2009101 Task: 44658 Depends-On: https://review.opendev.org/c/starlingx/tools/+/834375 Co-authored-by: Eric MacDonald <Eric.Macdonald@windriver.com> Co-authored-by: Leonardo Fagundes Luz Serrano <Leonardo.FagundesLuzSerrano@windriver.com> Signed-off-by: emacdona <eric.macdonald@windriver.com> Change-Id: I50bb797bedd9fb7f7ab1bbdae6e6f22b1023f1fb
1991 lines
68 KiB
INI
1991 lines
68 KiB
INI
#
|
|
# Copyright (c) 2022 Wind River Systems, Inc.
|
|
# SPDX-License-Identifier: Apache-2.0
|
|
#
|
|
############################################################################
|
|
#
|
|
# StarlingX Debian Unified System Node Install Kickstart
|
|
#
|
|
############################################################################
|
|
#
|
|
# This is the unified kickstart for Debian installation of system nodes.
|
|
#
|
|
# The Linux Assembly Tool (LAT) performs a unified install for all system
|
|
# nodes and exposes boot loader environment variables to this kickstart.
|
|
#
|
|
# This kickstart must be called with the 'traits=' boot parameter.
|
|
# Valid traits are:
|
|
#
|
|
# controller ... the controller function
|
|
# storage ... the storage function
|
|
# worker ... the worker function
|
|
# lowlatency ... the low latency function
|
|
# miniboot ... redfish subcloud install function
|
|
#
|
|
# Valid node personality trait groupings ... set configuration function
|
|
#
|
|
# traits=controller ... Controller
|
|
# traits=controller,worker ... All-in-one
|
|
# traits=controller,worker,lowlatency ... All-in-one Low Latency
|
|
# traits=storage ... Storage
|
|
# traits=worker ... Worker
|
|
# traits=worker,lowlatency ... Worker Low Latency
|
|
#
|
|
# Kickstart Stages
|
|
#
|
|
# Pre Partition - Common Functions Script
|
|
# Pre Partition - Volume Remove & Wipe Disk
|
|
# Partition - Partition Disks & Create Volumes
|
|
# Mkfs - Create Volume Groups & Logical Volumes
|
|
# Post - Logical Volume Config
|
|
# Post - Traits & Platform Config File update
|
|
# Post - Set Kernel Args
|
|
# Post - Interface Setup
|
|
# Post - Kickstart Finalize Install UUID
|
|
# Post - Log Filesystem Setup
|
|
# Post Nochroot - Save Install scripts and Logs
|
|
#
|
|
############################################################################
|
|
#
|
|
# LAT disk install override debug tool interface.
|
|
#
|
|
# lat-disk --install-device=${instdev} \
|
|
# --fat-size=${FSZ} \
|
|
# --boot-size=${BSZ} \
|
|
# --root-size=${RSZ} \
|
|
# --var-size=${VSZ} \
|
|
# --inst-flux=0
|
|
#
|
|
# Notes: exported environment variables changed in 'post' sections
|
|
# do not change the original value.
|
|
#
|
|
###########################################################################
|
|
#
|
|
# The first kickstart script creates '/tmp/lat/functions' common functions
|
|
# file that can be loaded from any of the other hook sections.
|
|
#
|
|
###########################################################################
|
|
# Pre Partition - Common Functions Script
|
|
%pre-part --interpreter=/bin/bash
|
|
|
|
cat << EOF >> /tmp/lat/ks_functions.sh
|
|
|
|
[ "\${HOOK_LABEL}" = "" ] && HOOK_LABEL="unknown"
|
|
|
|
export LOG_DIR="var/log"
|
|
export LAT_DIR="tmp/lat"
|
|
export LOGFILE="/\${LAT_DIR}/kickstart.log"
|
|
|
|
############################################################################
|
|
# log utils
|
|
############################################################################
|
|
function log()
|
|
{
|
|
local dt="\$(date "+%Y-%m-%d %H:%M:%S.%3N")"
|
|
echo "\$dt kickstart \${HOOK_LABEL} info: \$1" >>\${LOGFILE}
|
|
}
|
|
|
|
function ilog()
|
|
{
|
|
[ -z "$stdout" ] && stdout=1
|
|
local dt="$(date "+%Y-%m-%d %H:%M:%S.%3N")"
|
|
echo "\$dt kickstart \${HOOK_LABEL} info: \$1" >&\${stdout}
|
|
echo "\$dt kickstart \${HOOK_LABEL} info: \$1" >>\${LOGFILE}
|
|
}
|
|
|
|
function dlog()
|
|
{
|
|
if [ "\${debug}" ] ; then
|
|
[ -z "\$stdout" ] && stdout=1
|
|
local dt="\$(date "+%Y-%m-%d %H:%M:%S.%3N")"
|
|
echo "\$dt kickstart \${HOOK_LABEL} debug: \$1" >&\${stdout}
|
|
echo "\$dt kickstart \${HOOK_LABEL} debug: \$1" >>\${LOGFILE}
|
|
fi
|
|
}
|
|
|
|
function wlog()
|
|
{
|
|
[ -z "\$stdout" ] && stdout=1
|
|
local dt="\$(date "+%Y-%m-%d %H:%M:%S.%3N")"
|
|
echo "\$dt kickstart \${HOOK_LABEL} warn: \$1" >&\${stdout}
|
|
echo "\$dt kickstart \${HOOK_LABEL} warn: \$1" >>\${LOGFILE}
|
|
}
|
|
|
|
function elog()
|
|
{
|
|
[ -z "\$stdout" ] && stdout=1
|
|
local dt="\$(date "+%Y-%m-%d %H:%M:%S.%3N")"
|
|
echo "\$dt kickstart \${HOOK_LABEL} error: \$1" >&\${stdout}
|
|
echo "\$dt kickstart \${HOOK_LABEL} error: \$1" >>\${LOGFILE}
|
|
}
|
|
|
|
function report_failure_with_msg()
|
|
{
|
|
local msg=\${1}
|
|
echo -e '\n\nInstallation failed.\n'
|
|
wlog "Installation Failed: ERROR: \${msg}"
|
|
shell_start
|
|
exit 1
|
|
}
|
|
|
|
########################################################################
|
|
# Name : get_disk
|
|
# Parameters: \$1 - ??????
|
|
# Returns : No return but common disk name is echo's to stdio
|
|
#########################################################################
|
|
function get_disk()
|
|
{
|
|
echo "\$(cd /dev ; readlink -f \$1)"
|
|
}
|
|
|
|
#########################################################################
|
|
# Name : get_by_path
|
|
# Parameters: \$1 - device name i.e. /dev/sda
|
|
# Returns : echo of device name by-path
|
|
# example: /dev/disk/by-path/pci-0000:03:00.0-scsi-0:2:0:0
|
|
#########################################################################
|
|
function get_by_path()
|
|
{
|
|
# log "Function: get_by_path '\${1}'"
|
|
local disk=\$(cd /dev ; readlink -f \$1)
|
|
for p in /dev/disk/by-path/*; do
|
|
if [ "\$disk" = "\$(readlink -f \$p)" ]; then
|
|
echo "\$p"
|
|
return
|
|
fi
|
|
done
|
|
}
|
|
|
|
#########################################################################
|
|
# Name : get_disk_dev
|
|
# Purpose : get the disk name
|
|
# Returns : echo of the first disk name found ; base on coded priority
|
|
#########################################################################
|
|
function get_disk_dev()
|
|
{
|
|
local disk
|
|
# Detect HDD
|
|
for blk_dev in vda vdb sda sdb dda ddb hda hdb; do
|
|
if [ -d /sys/block/\$blk_dev ]; then
|
|
disk=\$(ls -l /sys/block/\$blk_dev | grep -v usb | head -n1 | sed 's/^.*\([vsdh]d[a-z]\+\).*\$/\1/');
|
|
if [ -n "\$disk" ]; then
|
|
echo "\$disk"
|
|
return
|
|
fi
|
|
fi
|
|
done
|
|
for blk_dev in nvme0n1 nvme1n1; do
|
|
if [ -d /sys/block/\$blk_dev ]; then
|
|
disk=\$(ls -l /sys/block/\$blk_dev | grep -v usb | head -n1 | sed 's/^.*\(nvme[01]n1\).*\$/\1/');
|
|
if [ -n "\$disk" ]; then
|
|
echo "\$disk"
|
|
return
|
|
fi
|
|
fi
|
|
done
|
|
}
|
|
|
|
#########################################################################
|
|
# Name : exec_retry
|
|
# Purpose : Retry operations up to a caller specified ...
|
|
# Parameters: $1 - retries - up to number of retries before giving up
|
|
# $2 - time in seconds between each retry
|
|
# $3 - the command string to execute
|
|
# Returns : exit code from last command operation
|
|
#########################################################################
|
|
function exec_retry()
|
|
{
|
|
local retries=\${1}
|
|
local interval=\${2}
|
|
local command=\${3}
|
|
|
|
# local variables
|
|
retry_count=1
|
|
local ret_code=0
|
|
local ret_stdout=""
|
|
|
|
command="\${command}" # 2>&\$stdout"
|
|
while [ \$retry_count -le \$retries ]; do
|
|
# dlog "Running command: '\${command}'."
|
|
ret_stdout=\$(eval \${command})
|
|
ret_code=\${?}
|
|
[ \$ret_code -eq 0 ] && break
|
|
wlog "Error running command '\${command}'. Try \${retry_count} of \${retries} retry in \${interval}s."
|
|
wlog "ret_code: \${ret_code}, stdout: '\${ret_stdout}'."
|
|
sleep \${interval}
|
|
retry_count=\$((retry_count+1))
|
|
done
|
|
echo "\${ret_stdout}"
|
|
return \${ret_code}
|
|
}
|
|
|
|
#########################################################################
|
|
# Name : exec_no_fds
|
|
# Purpose : Execute command (with retries) after closing fds
|
|
# Parameters: $1 - List of volume file descriptors
|
|
# $2 - the command string to execute
|
|
# $3 - up to number of retries before giving up
|
|
# $4 - time in seconds between each retry
|
|
# Returns : exit code from last command operation
|
|
#########################################################################
|
|
|
|
function exec_no_fds()
|
|
{
|
|
# Close open FDs when executing commands that complain about leaked FDs.
|
|
local fds=\${1}
|
|
local cmd=\${2}
|
|
local retries=\${3}
|
|
local interval=\${4}
|
|
|
|
local ret_code=0
|
|
local ret_stdout=""
|
|
for fd in \$fds
|
|
do
|
|
local cmd="\$cmd \$fd>&-"
|
|
done
|
|
if [ -z "\$retries" ]; then
|
|
#wlog "Running command: '\$cmd'."
|
|
eval "\$cmd"
|
|
else
|
|
ret_stdout=\$(exec_retry "\$retries" "\$interval" "\$cmd")
|
|
ret_code=\$?
|
|
echo "\${ret_stdout}"
|
|
return \${ret_code}
|
|
fi
|
|
}
|
|
|
|
#########################################################################
|
|
# Name : is_system_node_install
|
|
# Returns : 1 if yes 'pxecontroller' is in $insturl boot arg ; else 0
|
|
#########################################################################
|
|
function is_system_node_install()
|
|
{
|
|
if [[ "\$insturl" == *"pxecontroller"* ]] ; then
|
|
return 0
|
|
else
|
|
return 1
|
|
fi
|
|
}
|
|
|
|
#########################################################################
|
|
# Name : update_platform_conf
|
|
# Purpose : Update the platform.conf file with logging
|
|
#########################################################################
|
|
|
|
PLATFORM_CONF="/etc/platform/platform.conf"
|
|
function update_platform_conf()
|
|
{
|
|
ilog "update \${PLATFORM_CONF} : \${1}"
|
|
echo "\${1}" >> \${PLATFORM_CONF}
|
|
}
|
|
|
|
#########################################################################
|
|
# Name : get_iface_from_ethname
|
|
# Purpose : Translate eth# interface to the alternate predicitive
|
|
# interface name'altname'.
|
|
# Parameter: eth# name interface string to translate
|
|
# Return : echo's of altname interface string
|
|
#########################################################################
|
|
# TODO: Move to where its used if there is only one section caller
|
|
function get_iface_from_ethname()
|
|
{
|
|
iface=\${1}
|
|
|
|
# convert to predictive name
|
|
altname=\$(udevadm info --export --query=property --path=/sys/class/net/\${iface} | grep ID_NET_NAME_ONBOARD)
|
|
altname=\${altname#ID_NET_NAME_ONBOARD=}
|
|
|
|
# The altname is seen enveloped with tick's ; 'eno1'
|
|
# Handle with and without tick's just in case
|
|
if [ -z "\${altname}" ] ; then
|
|
log "Failed to translate \${iface} to predictive name"
|
|
elif [ "\${altname::1}" = "'" ] ; then
|
|
echo "\${altname:1:-1}"
|
|
else
|
|
echo "\${altname}"
|
|
fi
|
|
}
|
|
|
|
function display_volume_info ()
|
|
{
|
|
ilog "Volume Info:\${1}"
|
|
|
|
pvscan 2>/dev/null
|
|
pvscan 2>/dev/null >> \${LOGFILE}
|
|
|
|
lvscan 2>/dev/null
|
|
lvscan 2>/dev/null >> \${LOGFILE}
|
|
|
|
pvdisplay 2>/dev/null
|
|
pvdisplay 2>/dev/null >> \${LOGFILE}
|
|
|
|
lvdisplay 2>/dev/null
|
|
lvdisplay 2>/dev/null >> \${LOGFILE}
|
|
}
|
|
|
|
display_mount_info()
|
|
{
|
|
if [ \${debug} -ne 0 ] ; then
|
|
echo "~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"
|
|
lsblk -o name,mountpoint,label,size,uuid
|
|
echo "~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"
|
|
fi
|
|
}
|
|
|
|
function log_lvm_conf ()
|
|
{
|
|
lvm_global_filter=\$(cat /etc/lvm/lvm.conf | grep "global_filter =")
|
|
ilog "LVM 'global_filter' Config: \${lvm_global_filter}"
|
|
lvm_preferred_names=\$(cat /etc/lvm/lvm.conf | grep "preferred_names =")
|
|
ilog "LVM 'lvm_preferred_names' Config: \${lvm_preferred_names}"
|
|
}
|
|
|
|
function breakpoint()
|
|
{
|
|
echo "*** BREAKPOINT ***: \${1} ; type exit to continue"
|
|
bash
|
|
echo "continuing from breakpoint: \${1}"
|
|
}
|
|
|
|
function set_variable()
|
|
{
|
|
touch "/\${LAT_DIR}/\${1}"
|
|
}
|
|
|
|
function get_variable()
|
|
{
|
|
[ -e "/\${LAT_DIR}/\${1}" ] && return 1
|
|
return 0
|
|
}
|
|
|
|
function clr_variable()
|
|
{
|
|
rm -f "/\${LAT_DIR}/\${1}"
|
|
}
|
|
|
|
##########################################################################
|
|
# Global Kickstart Constants #
|
|
##########################################################################
|
|
#
|
|
# NOTE: exported Variables from other segments are NOT visible from functions
|
|
#
|
|
|
|
BACKUP_PART_LABEL="Platform Backup"
|
|
BACKUP_PART_NO=6
|
|
BACKUP_PART=\${instdev}\${BACKUP_PART_NO}
|
|
|
|
DEFAULT_PERSISTENT_SIZE=30000
|
|
|
|
# Note that the BA5EBA11-0000-1111-2222- is the prefix used by STX and it's defined in sysinv constants.py.
|
|
# Since the 000000000001 suffix is used by custom stx LVM partitions,
|
|
# the next suffix is used for the persistent backup partition (000000000002)
|
|
BACKUP_PART_GUID="BA5EBA11-0000-1111-2222-000000000002"
|
|
|
|
# Node Personality Trait
|
|
TRAIT__CONTROLLER="controller"
|
|
TRAIT__STORAGE="storage"
|
|
TRAIT__WORKER="worker"
|
|
TRAIT__LOWLATENCY="lowlatency"
|
|
|
|
# System Types
|
|
SYSTEM_TYPE__AIO="All-in-one"
|
|
SYSTEM_TYPE__STANDARD="Standard"
|
|
|
|
# Node Subfunctions
|
|
SUBFUNCTION__CONTROLLER="\${TRAIT__CONTROLLER}"
|
|
SUBFUNCTION__STORAGE="\${TRAIT__STORAGE}"
|
|
SUBFUNCTION__WORKER="\${TRAIT__WORKER}"
|
|
SUBFUNCTION__AIO="\${TRAIT__CONTROLLER},\${TRAIT__WORKER}"
|
|
SUBFUNCTION__AIO_LOWLATENCY="\${TRAIT__CONTROLLER},\${TRAIT__WORKER},\${TRAIT__LOWLATENCY}"
|
|
VOLUME_GROUPS="cgts-vg"
|
|
|
|
ROOTFS_SIZE=\${RSZ} # 20000
|
|
BOOT_SIZE=\${BSZ} # 500
|
|
EFI_SIZE=300
|
|
LOG_VOL_SIZE=8000
|
|
SCRATCH_VOL_SIZE=16000
|
|
EOF
|
|
|
|
chmod 755 /tmp/lat/ks_functions.sh
|
|
HOOK_LABEL="pre-part"
|
|
. /tmp/lat/ks_functions.sh
|
|
|
|
##########################################################################
|
|
# Global Kickstart variables #
|
|
##########################################################################
|
|
|
|
export debug=0
|
|
|
|
export PLATFORM_BACKUP_SIZE=${DEFAULT_PERSISTENT_SIZE}
|
|
|
|
# Assume there is no Platform Backup (persistent) Partition
|
|
export BACKUP_CREATED=0
|
|
export BACKUP_PERSISTED=0
|
|
|
|
# Platform Backup Partition Info
|
|
export BACKUP_PART_GUID=0
|
|
export BACKUP_PART_FIRST=0
|
|
export BACKUP_PART_END=0
|
|
export BACKUP_PART_SIZE=0
|
|
export BACKUP_PART_FLAGS=0
|
|
export BACKUP_PART_NAME=""
|
|
|
|
export STOR_DEV_FDS=""
|
|
|
|
##########################################################################
|
|
|
|
ilog "***********************************************"
|
|
ilog "** Pre Partition - Volume Remove & Wipe Disk **"
|
|
ilog "***********************************************"
|
|
|
|
# Default traits to AIO if missing
|
|
if [ -z "${traits}" ] ; then
|
|
traits="controller,worker"
|
|
wlog "traits option missing ; defaulting to \${traits}"
|
|
fi
|
|
|
|
export controller=false
|
|
export storage=false
|
|
export worker=false
|
|
export lowlatency=false
|
|
export miniboot=false
|
|
export aio=false
|
|
for trait in ${traits//,/ }; do
|
|
# dlog "trait:${trait}"
|
|
case ${trait} in
|
|
"controller") controller=true ;;
|
|
"storage") storage=true ;;
|
|
"worker") worker=true ;;
|
|
"lowlatency") lowlatency=true ;;
|
|
"miniboot") miniboot=true ;;
|
|
*) wlog "unknown trait '${trait}'" ;;
|
|
esac
|
|
done
|
|
|
|
[ "${controller}" = true -a "${worker}" = true ] && aio=true
|
|
|
|
grep -q 'debug_kickstart' /proc/cmdline
|
|
if [ $? -eq 0 ]; then
|
|
debug=1
|
|
fi
|
|
|
|
ilog "LAT size parameters: FSZ=${FSZ} BSZ=${BSZ} RSZ=${RSZ} VSZ=${VSZ}"
|
|
|
|
# First, parse /proc/cmdline to find the boot args
|
|
set -- `cat /proc/cmdline`
|
|
ilog "/proc/cmdline:$*"
|
|
|
|
# for I in $*; do case "$I" in *=*) eval $I 2>/dev/null;; esac; done
|
|
for arg in $*; do
|
|
case "$arg" in
|
|
*=*)
|
|
eval $arg 2>/dev/null
|
|
log "arg : $arg"
|
|
;;
|
|
esac
|
|
done
|
|
|
|
# Note: This is equivalent to pre_disk_setup_common.cfg
|
|
|
|
# Name : check_execs
|
|
# Purpose: Confirm all the executables required by the kickstart are present
|
|
# Returns: 1 of one or more executable are missing
|
|
REQUIRED_EXECS="bc blkid dd lvcreate mkfs.ext4 partprobe pvremove pvs sgdisk vgcreate wipefs"
|
|
|
|
function check_execs()
|
|
{
|
|
missing_exec=0
|
|
for x in ${REQUIRED_EXECS} ; do
|
|
which ${x} > /dev/null 2>&1
|
|
if [ ${?} -ne 0 ] ; then
|
|
elog "dependency check failed ; required '${x}' exec is missing"
|
|
missing_exec=1
|
|
fi
|
|
done
|
|
return ${missing_exec}
|
|
}
|
|
|
|
# Log Traits
|
|
[ "${controller}" = true ] && ilog "Controller Function"
|
|
[ "${storage}" = true ] && ilog "Storage Function"
|
|
[ "${worker}" = true ] && ilog "Worker Function"
|
|
[ "${lowlatency}" = true ] && ilog "Low Latency Function"
|
|
[ "${miniboot}" = true ] && ilog "Zero Touch Install Function"
|
|
|
|
# Log System Type
|
|
if [ ${aio} = true ] ; then
|
|
ilog "${SYSTEM_TYPE__AIO} system"
|
|
else
|
|
ilog "${SYSTEM_TYPE__STANDARD} system"
|
|
fi
|
|
|
|
# Verify that all the required executables are presenty
|
|
check_execs
|
|
[ $? -ne 0 ] && report_failure_with_msg "Required executables are missing"
|
|
|
|
####################################################
|
|
# pre_common_head (obsolete with lat)
|
|
####################################################
|
|
# TODO: The installer does not have 'timezone'
|
|
# Does LAT handle this ?
|
|
wlog "timezone not set ; 'timezone --nontp --utc UTC'"
|
|
|
|
#####################################################
|
|
# From pre_disk_setup_common.cfg
|
|
#####################################################
|
|
|
|
if [ -n "$instdev" ] ; then
|
|
instdev_by_path=$(get_by_path $instdev)
|
|
if [ -z ${instdev_by_path} ] ; then
|
|
report_failure_with_msg "invalid install device ${instdev}"
|
|
else
|
|
ilog "Install device: ${instdev} : ${instdev_by_path}"
|
|
fi
|
|
fi
|
|
|
|
# Get all block devices of type disk in the system.
|
|
# This includes solid state devices.
|
|
# Note: /dev/* are managed by kernel tmpdevfs while links in
|
|
# /dev/disk/by-path/ are managed by udev which updates them
|
|
# asynchronously so avoid using them while performing partition
|
|
# operations.
|
|
ilog "Detected storage devices:"
|
|
STOR_DEVS=""
|
|
for f in /dev/disk/by-path/*; do
|
|
dev=$(readlink -f $f)
|
|
# dlog "found device ${f}"
|
|
exec_retry 2 0.5 "lsblk --nodeps --pairs $dev" | grep -q 'TYPE="disk"'
|
|
if [ $? -eq 0 ] ; then
|
|
# ISSUE: Do /dev/sda only otherwise with sda,sdb,sdc the LAT boot
|
|
# partitions show up on /dev/sdc even if instdev = /dev/sda
|
|
# This issue is being investigated, Jira pending
|
|
if [ "${dev}" = "/dev/sda" ] ; then
|
|
STOR_DEVS="$STOR_DEVS $dev"
|
|
ilog "Adding ${f} -> ${dev} to managed device list"
|
|
fi
|
|
fi
|
|
done
|
|
|
|
# Filter STOR_DEVS variable for any duplicates as on some systems udev
|
|
# creates multiple links to the same device. This causes issues due to
|
|
# attempting to acquire a flock on the same device multiple times.
|
|
STOR_DEVS=$(echo "$STOR_DEVS" | xargs -n 1 | sort -u | xargs)
|
|
ilog "Unique storage devices: $STOR_DEVS"
|
|
if [ -z "$STOR_DEVS" ] ; then
|
|
report_failure_with_msg "No storage devices available."
|
|
fi
|
|
|
|
|
|
# Lock all devices so that udev doesn't trigger a kernel partition table
|
|
# rescan that removes and recreates all /dev nodes for partitions on those
|
|
# devices. Since udev events are asynchronous this could lead to a case
|
|
# where /dev/ links for existing partitions are briefly missing.
|
|
# Missing /dev links leads to command execution failures.
|
|
#STOR_DEV_FDS="$stdout"
|
|
#for dev in $STOR_DEVS; do
|
|
# exec {fd}>$dev || report_failure_with_msg "Error creating file descriptor for $dev."
|
|
# flock -n "$fd" || report_failure_with_msg "Can't get a lock on fd $fd of device $dev."
|
|
# STOR_DEV_FDS="$STOR_DEV_FDS $fd"
|
|
# ilog "Locked ${dev} fd:${fd}"
|
|
#done
|
|
|
|
# Log info about system state at beginning of partitioning operation
|
|
for dev in $STOR_DEVS; do
|
|
ilog "Initial partition table for $dev is:"
|
|
# log "Initial partition table for $dev is:"
|
|
parted -s $dev unit mib print
|
|
# parted -s $dev unit mib print >> ${LOGFILE}
|
|
done
|
|
|
|
display_volume_info "before"
|
|
display_mount_info
|
|
|
|
# Consider removing since LAT already handles this failure mode
|
|
# Ensure specified device is not a USB drive
|
|
udevadm info --query=property --name=${instdev} |grep -q '^ID_BUS=usb'
|
|
if [ $? -eq 0 ]; then
|
|
report_failure_with_msg "Specified installation ($instdev) device is a USB drive."
|
|
fi
|
|
|
|
# Log the disk setup
|
|
ilog "Volume Groups : ${VOLUME_GROUPS} ; $STOR_DEV_FDS"
|
|
|
|
# Deactivate existing volume groups to avoid Anaconda issues with pre-existing groups
|
|
# TODO: May not need this Anaconda specific behavior work around
|
|
vgs=$(exec_no_fds "$STOR_DEV_FDS" "vgs --noheadings -o vg_name 2>/dev/null")
|
|
for vg in $vgs; do
|
|
wlog "Disabling $vg"
|
|
exec_no_fds "$STOR_DEV_FDS" "vgchange -an $vg 2>/dev/null" 5 0.5
|
|
[ $? -ne 0 ] && report_failure_with_msg "Failed to disable $vg."
|
|
done
|
|
|
|
# Remove the volume groups that have physical volumes on the root disk
|
|
for vg in $(exec_no_fds "$STOR_DEV_FDS" "vgs --noheadings -o vg_name 2>/dev/null"); do
|
|
exec_no_fds "$STOR_DEV_FDS" "pvs --select \"vg_name=$vg\" --noheadings -o pv_name 2>/dev/null" | grep -q "${instdev}"
|
|
rc=$?
|
|
if [ $rc -ne 0 ]; then
|
|
wlog "Found $vg with no PV on rootfs, ignoring ; rc=${rc}"
|
|
# continue
|
|
fi
|
|
|
|
# wlog "Removing LVs on $vg."
|
|
# exec_no_fds "$STOR_DEV_FDS" "lvremove --force $vg 2>/dev/null" 5 0.5 || wlog "WARNING: Failed to remove lvs on $vg."
|
|
# pvs=$(exec_no_fds "$STOR_DEV_FDS" "pvs --select \"vg_name=$vg\" --noheadings -o pv_name 2>/dev/null")
|
|
# wlog "VG $vg has PVs: $(echo $pvs), removing them."
|
|
# for pv in $pvs; do
|
|
# wlog "Removing PV $pv."
|
|
# exec_no_fds "$STOR_DEV_FDS" "pvremove --force --force --yes $pv 2>/dev/null" 5 0.5
|
|
# [ $? -ne 0 ] && report_failure_with_msg "Failed to remove PV."
|
|
# done
|
|
|
|
# Just delete the Volume Group , the logical volumes will be deleted under the covers
|
|
vg_check=$(exec_no_fds "$STOR_DEV_FDS" "vgs --select \"vg_name=$vg\" --noheadings -o vg_name 2>/dev/null")
|
|
if [ -n "$vg_check" ]; then
|
|
wlog "Removing volume group $vg"
|
|
exec_no_fds "$STOR_DEV_FDS" "vgremove --force $vg 2>/dev/null" 5 0.5
|
|
[ $? -ne 0 ] && report_failure_with_msg "Failed to remove VG."
|
|
fi
|
|
done
|
|
|
|
|
|
# Log info about system state after partitioning removal operation.
|
|
for dev in $STOR_DEVS; do
|
|
log "After partition removal for $dev is:"
|
|
parted -s $dev unit mib print >> ${LOGFILE}
|
|
done
|
|
|
|
display_volume_info "after"
|
|
display_mount_info
|
|
|
|
ONLYUSE_HDD=""
|
|
|
|
part_type_guid_str="Partition GUID code"
|
|
part_type_name_str="Partition name"
|
|
part_type_size_str="Partition size"
|
|
part_type_first_str="First sector"
|
|
part_type_end_str="Last sector"
|
|
part_type_flags_str="Attribute flags"
|
|
|
|
if [ "$(curl -sf http://pxecontroller:6385/v1/upgrade/$(hostname)/in_upgrade 2>/dev/null)" = "true" ]; then
|
|
|
|
# In an upgrade, only wipe the disk with the rootfs and boot partition
|
|
wlog "In upgrade, wiping only ${instdev}"
|
|
WIPE_HDD=${instdev}
|
|
ONLYUSE_HDD="$(basename ${instdev})"
|
|
|
|
else
|
|
|
|
# Make a list of all the hard drives that are to be wiped.
|
|
# Never put the LAT install disk '${instdev}' in that list.
|
|
WIPE_HDD=""
|
|
|
|
# Partition type OSD has a unique globally identifier
|
|
CEPH_OSD_GUID="4FBD7E29-9D25-41B8-AFD0-062C0CEFF05D"
|
|
CEPH_JOURNAL_GUID="45B0969E-9B03-4F30-B4C6-B4B80CEFF106"
|
|
|
|
# Check if we wipe OSDs
|
|
if [ "$(curl -sf http://pxecontroller:6385/v1/ihosts/wipe_osds 2>/dev/null)" = "true" ]; then
|
|
wlog "Wipe OSD data"
|
|
WIPE_CEPH_OSDS="true"
|
|
else
|
|
wlog "Skip Ceph OSD data wipe."
|
|
WIPE_CEPH_OSDS="false"
|
|
fi
|
|
|
|
for dev in $STOR_DEVS
|
|
do
|
|
# TODO: Allowing the install dev 'in' results in a failure mode where
|
|
# every second install fails with the following error string
|
|
# and unrecoverable mount failure.
|
|
#
|
|
# Logs:
|
|
#
|
|
# Warning: The kernel is still using the old partition table.
|
|
# The new table will be used at the next reboot or after you
|
|
# run partprobe(8) or kpartx(8)
|
|
# and then
|
|
#
|
|
# Failure:
|
|
#
|
|
# mount: /sysroot: can't find LABEL=otaroot.
|
|
#
|
|
# Action: Find correct place to put partprobe
|
|
#
|
|
# Avoid wiping the install root disk
|
|
# [ ${dev} == ${instdev} ] && continue
|
|
|
|
# Avoid wiping USB drives
|
|
udevadm info --query=property --name=$dev |grep -q '^ID_BUS=usb' && continue
|
|
|
|
# Avoid wiping ceph osds if sysinv tells us so
|
|
if [ ${WIPE_CEPH_OSDS} == "false" ]; then
|
|
wipe_dev="true"
|
|
|
|
pvs | grep -q "$dev *ceph"
|
|
if [ $? -eq 0 ]; then
|
|
wlog "skip rook provisoned disk $dev"
|
|
continue
|
|
fi
|
|
|
|
part_numbers=( `parted -s $dev print | awk '$1 == "Number" {i=1; next}; i {print $1}'` )
|
|
# Scanning the partitions looking for CEPH OSDs and
|
|
# skipping any disk found with such partitions
|
|
for part_number in "${part_numbers[@]}"; do
|
|
sgdisk_part_info=$(sgdisk -i $part_number $dev)
|
|
part_type_guid=$(echo "$sgdisk_part_info" | grep "$part_type_guid_str" | awk '{print $4;}')
|
|
if [ "$part_type_guid" == $CEPH_OSD_GUID ]; then
|
|
wlog "OSD found on $dev, skipping wipe"
|
|
wipe_dev="false"
|
|
break
|
|
fi
|
|
|
|
pvs | grep -q -e "${dev}${part_number} *ceph" -e "${dev}p${part_number} *ceph"
|
|
if [ $? -eq 0 ]; then
|
|
wlog "Rook OSD found on $dev$part_number, skip wipe"
|
|
wipe_dev="false"
|
|
break
|
|
fi
|
|
done
|
|
|
|
if [ "$wipe_dev" == "false" ]; then
|
|
ilog "Bypassing Wipe of ${dev}${part_number} ; reason: wipe_dev=false"
|
|
continue
|
|
else
|
|
ilog "Allowing Wipe of ${dev}${part_number} ; reason: wipe_dev=true"
|
|
fi
|
|
fi
|
|
|
|
# Add device to the wipe list
|
|
devname=$(basename $dev)
|
|
if [ -e $dev -a "$ISO_DEV" != "../../$devname" -a "$USB_DEV" != "../../$devname" ]; then
|
|
ilog "Adding ${dev} to list of disks to be wipped"
|
|
if [ -n "$WIPE_HDD" ]; then
|
|
ilog "WIPE_HDD=$WIPE_HDD,$dev"
|
|
WIPE_HDD=$WIPE_HDD,$dev
|
|
else
|
|
ilog "WIPE_HDD=$dev"
|
|
WIPE_HDD=$dev
|
|
fi
|
|
fi
|
|
done
|
|
ilog "Not in upgrade"
|
|
fi
|
|
|
|
ilog "***************************************************"
|
|
ilog "WIPE DISKs: ${WIPE_HDD}"
|
|
ilog "***************************************************"
|
|
by_dev=${instdev}
|
|
# TODO: Avoid this loop if the instdev does not have by-path in its name
|
|
for f in /dev/disk/by-path/*; do
|
|
if [ "${f}" == "${instdev}" ] ; then
|
|
by_dev=$(get_disk "${instdev}")
|
|
break
|
|
fi
|
|
done
|
|
for dev in ${WIPE_HDD//,/ }
|
|
do
|
|
ilog "Wiping $dev"
|
|
|
|
# Clear previous GPT tables or LVM data on each disk.
|
|
#
|
|
# Rule: Exclude the persistent 'Platform backup' partition.
|
|
# Note: Delete the first few bytes at the start and end of the partition.
|
|
# This is required with GPT partitions because they save partition
|
|
# info at both the start and the end of the block.
|
|
|
|
# Get a list of partitions for this disk
|
|
part_numbers=( $(parted -s $dev print | awk '$1 == "Number" {i=1; next}; i {print $1}') )
|
|
|
|
# For each '/dev/${dev}${part_number} apply wipe rules
|
|
for part_number in "${part_numbers[@]}"; do
|
|
sgdisk_part_info=$(sgdisk -i $part_number $dev)
|
|
part_name=$(echo "$sgdisk_part_info" | grep "$part_type_name_str" | awk '{print $3;}')
|
|
|
|
# special handling for the install device '${instdev}'
|
|
if [ "${dev}" == "${by_dev}" ] ; then
|
|
|
|
# Skip over the bios, efi and boot partitions that got us here.
|
|
# LAT handles these partitions
|
|
case ${part_name} in
|
|
"'bios'")
|
|
ilog "skipping ${part_name} on ${dev}${part_number}"
|
|
continue
|
|
;;
|
|
"'otaefi'")
|
|
ilog "skipping ${part_name} on ${dev}${part_number}"
|
|
continue
|
|
;;
|
|
"'otaboot'")
|
|
ilog "skipping ${part_name} on ${dev}${part_number}"
|
|
continue
|
|
;;
|
|
"'otaboot_b'")
|
|
ilog "skipping ${part_name} on ${dev}${part_number}"
|
|
continue
|
|
;;
|
|
"'otaroot'")
|
|
ilog "skipping ${part_name} on ${dev}${part_number}"
|
|
continue
|
|
;;
|
|
"'fluxdata'")
|
|
ilog "skipping ${part_name} on ${dev}${part_number}"
|
|
continue
|
|
;;
|
|
*)
|
|
dlog "wipe candidate ${part_name} on ${dev}${part_number}"
|
|
;;
|
|
esac
|
|
fi
|
|
|
|
# Deal with ssd's which have different partition labelling convention
|
|
part=$dev$part_number
|
|
case $part in
|
|
*"nvme"*)
|
|
part=${dev}p${part_number}
|
|
;;
|
|
esac
|
|
|
|
# ISSUE: ERIK: These are never the same when the by-path instdev is used.
|
|
# dev = /dev/sda instdev = by path string
|
|
ilog "Checking platform-backup partition ... $dev : ${instdev} ${by_dev}"
|
|
sgdisk_part_info=$(sgdisk -i $part_number $dev)
|
|
part_type_guid=$(echo "$sgdisk_part_info" | grep "$part_type_guid_str" | awk '{print $4;}')
|
|
BACKUP_PART_GUID=${part_type_guid}
|
|
if [ "$dev" == "${by_dev}" -a "$part_type_guid" == $BACKUP_PART_GUID ] ; then
|
|
BACKUP_PART_GUID=${part_type_guid}
|
|
|
|
part_type_name=$(echo "$sgdisk_part_info" | grep "$part_type_name_str" | awk '{print $3,$4;}')
|
|
BACKUP_PART_NAME=${part_type_name:1:-1}
|
|
|
|
part_type_first=$(echo "$sgdisk_part_info" | grep "$part_type_first_str" | awk '{print $3;}')
|
|
BACKUP_PART_FIRST=${part_type_first}
|
|
|
|
part_type_end=$(echo "$sgdisk_part_info" | grep "$part_type_end_str" | awk '{print $3;}')
|
|
BACKUP_PART_END=${part_type_end}
|
|
|
|
part_type_size=$(echo "$sgdisk_part_info" | grep "$part_type_size_str" | awk '{print $3;}')
|
|
BACKUP_PART_SIZE=${part_type_size}
|
|
|
|
part_type_flags=$(echo "$sgdisk_part_info" | grep "$part_type_flags_str" | awk '{print $3;}')
|
|
BACKUP_PART_FLAGS=${part_type_flags}
|
|
|
|
# dlog "Platform Backup: ${BACKUP_PART_NAME}:${BACKUP_PART_FIRST}:${BACKUP_PART_END}:${BACKUP_PART_SIZE}:${BACKUP_PART_GUID}"
|
|
|
|
part_fstype=$(exec_retry 5 0.5 "blkid -s TYPE -o value $part")
|
|
if [ "${part_fstype}" == "ext4" ]; then
|
|
ilog "Skipping wipe of persistent partition $part"
|
|
BACKUP_CREATED=1
|
|
continue
|
|
else
|
|
ilog "Wipe Partition: part:${part} dev:${dev} pn:${part_number}"
|
|
# dlog ".... guid:$part_type_guid:$BACKUP_PART_GUID - fs:${part_fstype}"
|
|
fi
|
|
fi
|
|
|
|
if [ $WIPE_CEPH_OSDS == "true" -a "$part_type_guid" == $CEPH_JOURNAL_GUID ]; then
|
|
# Journal partitions require additional wiping. Based on the ceph-manage-journal.py
|
|
# script in the integ repo (at the ceph/ceph/files/ceph-manage-journal.py location)
|
|
# wiping 100MB of data at the beginning of the partition should be enough. We also
|
|
# wipe 100MB at the end, just to be safe.
|
|
ilog "Wiping Ceph ${part_name} on ${part} start and end with dd"
|
|
dd if=/dev/zero of=$part bs=1M count=100 2>/dev/null
|
|
dd if=/dev/zero of=$part bs=1M count=100 seek=$(( `blockdev --getsz $part` / (1024 * 2) - 100 )) 2>/dev/null
|
|
else
|
|
ilog "STUBBED Wiping ${part_name} on ${part} start and end with dd"
|
|
# dd if=/dev/zero of=$part bs=512 count=34 2>/dev/null
|
|
# dd if=/dev/zero of=$part bs=512 count=34 seek=$((`blockdev --getsz $part` - 34)) 2>/dev/null
|
|
fi
|
|
done
|
|
|
|
if [ ${BACKUP_CREATED} -eq 0 -o "${dev}" != "${by_dev}" ]; then
|
|
ilog "Creating disk label for $dev"
|
|
parted -s $dev mktable gpt
|
|
ilog "... done"
|
|
fi
|
|
done
|
|
|
|
# Zap all disks except for the install disk
|
|
for dev in $STOR_DEVS; do
|
|
if [ ${dev} != "${by_dev}" ] ; then
|
|
ilog "Zapping ${dev}"
|
|
sgdisk -Z ${dev}
|
|
fi
|
|
done
|
|
|
|
wlog "Destroy otaroot partitions on root disk"
|
|
for oldrootlabel in otaroot otaroot_1 otaroot_b otaroot_b_1
|
|
do
|
|
oldrootpart=$(blkid --label $oldrootlabel)
|
|
[ -z "$oldrootpart" ] && continue
|
|
|
|
oldinstdev=/dev/$(lsblk $oldrootpart -n -o pkname)
|
|
ilog "... destroying ${oldrootpart} on ${oldinstdev}"
|
|
|
|
# sgdisk - Command-line GUID partition table (GPT) manipulator
|
|
# Zap the entire partition
|
|
ilog "... zapping ${oldinstdev}"
|
|
sgdisk -Z ${oldinstdev}
|
|
|
|
# partprobe - inform the OS of partition table changes
|
|
# root@(none):/# partprobe /dev/sda -s
|
|
# /dev/sda: gpt partitions 1 2 3 4 5 6
|
|
ilog "... probing ${oldinstdev}"
|
|
partprobe ${oldinstdev}
|
|
|
|
# wipefs - wipe a signature from a device
|
|
ilog "... wiping ${oldinstdev}"
|
|
wipefs --all --backup ${oldinstdev}
|
|
done
|
|
true
|
|
%end
|
|
|
|
###########################################################################
|
|
|
|
%part --interpreter=/bin/bash
|
|
HOOK_LABEL=" part"
|
|
. /tmp/lat/ks_functions.sh
|
|
ilog "****************************************************"
|
|
ilog "*** Partition - Partition Disks & Create Volumes ***"
|
|
ilog "****************************************************"
|
|
|
|
ilog "Allocate host partitions (MB) first:$first"
|
|
|
|
## NOTE: updates to partition sizes need to be also reflected in
|
|
## _controller_filesystem_limits() in sysinv/api/controllers/v1/istorconfig.py
|
|
|
|
ROOTFS_PART_PREFIX=${instdev}
|
|
#check if disk is nvme
|
|
case $instdev in
|
|
*"nvme"*)
|
|
ROOTFS_PART_PREFIX=${instdev}p
|
|
;;
|
|
esac
|
|
|
|
###########################################################
|
|
# From pre_disk_controller.cfg
|
|
###########################################################
|
|
|
|
# Only controllers have a persistent partition
|
|
if [ "${controller}" = true ] ; then
|
|
|
|
PLATFORM_BACKUP_SIZE=${DEFAULT_PERSISTENT_SIZE}
|
|
|
|
if [ -z "$persistent_size" ]; then
|
|
# Default backup partition size in MiB
|
|
ilog "Platform Backup persistent size not on command line ; defaulting to ${DEFAULT_PERSISTENT_SIZE}"
|
|
persistent_size=${DEFAULT_PERSISTENT_SIZE}
|
|
fi
|
|
|
|
if [ ${persistent_size} -lt ${DEFAULT_PERSISTENT_SIZE} ] ; then
|
|
wlog "Cannot set persistent_size smaller than default size of ${DEFAULT_PERSISTENT_SIZE} KB"
|
|
else
|
|
PLATFORM_BACKUP_SIZE=${persistent_size}
|
|
fi
|
|
ilog "Platform Backup partition size: ${PLATFORM_BACKUP_SIZE}"
|
|
|
|
if [ -d /sys/firmware/efi ] ; then
|
|
ilog "UEFI Firmware"
|
|
else
|
|
ilog "BIOS Firmware"
|
|
fi
|
|
if [ ${BACKUP_CREATED} -eq 0 ] ; then
|
|
ilog "Platform Backup partition CREATED"
|
|
else
|
|
BACKUP_PERSISTED=1
|
|
ilog "Platform Backup Partition PERSISTED"
|
|
fi
|
|
grub_pt_update
|
|
end=$(($first+($PLATFORM_BACKUP_SIZE*1024*1024/$lsz)-1))
|
|
a="$a -n $p:$first:$end -c $p:platform_backup"
|
|
fi
|
|
|
|
# Auto expand
|
|
grub_pt_update
|
|
end=$last
|
|
a="$a -n $p:$first:$end -c $p:plat_pv -t $p:8E00"
|
|
|
|
dlog "Partition Table: ${a}"
|
|
|
|
STOR_DEVS=$(echo "$STOR_DEVS" | xargs -n 1 | sort -u | xargs)
|
|
[ -z "$STOR_DEVS" ] && report_failure_with_msg "No storage devices available."
|
|
STOR_DEV_FDS="$stdout"
|
|
for dev in $STOR_DEVS; do
|
|
exec {fd}>$dev || report_failure_with_msg "Error creating file descriptor for $dev."
|
|
STOR_DEV_FDS="$STOR_DEV_FDS $fd"
|
|
done
|
|
ilog "STOR_DEV_FDS Updated ; $STOR_DEV_FDS"
|
|
#####################################################################
|
|
# From pre_disk_setup_tail.cfg
|
|
#####################################################################
|
|
|
|
# Log info about system state at end of partitioning operation.
|
|
# From pre_disk_setup_tail.cfg
|
|
for dev in $STOR_DEVS; do
|
|
log "Partition table at end of script for $dev is:"
|
|
parted -s $dev unit mib print >> ${LOGFILE}
|
|
done
|
|
|
|
# Close all FDs and wait for udev to reshuffle all partitions.
|
|
# wlog "Releasing storage device locks and FDs."
|
|
#for fd in $STOR_DEV_FDS
|
|
#do
|
|
# flock -u "$fd"
|
|
# exec {fd}>&-
|
|
#done
|
|
|
|
sleep 2
|
|
udevadm settle --timeout=300 || report_failure_with_msg "udevadm settle failed"
|
|
|
|
lsblk -o name,mountpoint,label,size,uuid
|
|
|
|
# Rescan LVM cache to avoid warnings for VGs that were recreated.
|
|
pvscan --cache 2>/dev/null
|
|
|
|
true
|
|
%end
|
|
|
|
###########################################################################
|
|
|
|
%mkfs --interpreter=/bin/bash
|
|
HOOK_LABEL="mkfs"
|
|
. /tmp/lat/ks_functions.sh
|
|
ilog "****************************************************"
|
|
ilog "** Mkfs - Create Volume Groups & Logical Volumes **"
|
|
ilog "****************************************************"
|
|
|
|
#######################################################
|
|
# From pre_disk_aio
|
|
######################################################
|
|
|
|
# TODO: Remove this duplicate for next update
|
|
BACKUP_PART_GUID="BA5EBA11-0000-1111-2222-000000000002"
|
|
|
|
# TODO: This causes a kernel panic
|
|
# Action: Reverify
|
|
# let -i gb=1024*1024*1024
|
|
gb=1073741824
|
|
|
|
ilog "LAT size parameters: FSZ=${FSZ} BSZ=${BSZ} RSZ=${RSZ} VSZ=${VSZ} gb:${gb}"
|
|
|
|
if [ "${controller}" = true ] ; then
|
|
LOG_VOL_SIZE=8000
|
|
SCRATCH_VOL_SIZE=16000
|
|
|
|
if [ ! -z "$persistent_size" ]; then
|
|
# Default backup partition size in MiB
|
|
persistent_size=${DEFAULT_PERSISTENT_SIZE}
|
|
fi
|
|
# PLATFORM_BACKUP_SIZE=${persistent_size}
|
|
ilog "Persistent Size: $persistent_size ${PLATFORM_BACKUP_SIZE}"
|
|
fi
|
|
|
|
if [ "${aio}" = true ] ; then
|
|
##
|
|
## NOTE: updates to partition sizes need to be also reflected in
|
|
## - config/.../sysinv/conductor/manager.py:create_controller_filesystems()
|
|
## - config/.../sysinv/common/constants.py
|
|
##
|
|
## NOTE: When adding partitions, we currently have a max of 4 primary partitions.
|
|
## If more than 4 partitions are required, we can use a max of 3 --asprimary,
|
|
## to allow 1 primary logical partition with extended partitions
|
|
##
|
|
## NOTE: Max default PV size must align with the default controllerfs sizes
|
|
##
|
|
##
|
|
## NOTE TO REVIEWERS:
|
|
## This section was talen from CentOS and needs to be updated for Debian.
|
|
##
|
|
##***********************************************************************
|
|
## Large disk install (for disks over 240GB)
|
|
## - DB size is doubled to allow for upgrades
|
|
##
|
|
## BACKUP_OVERHEAD = 5GiB
|
|
## DEFAULT_PLATFORM_STOR_SIZE = 10GiB
|
|
## DEFAULT_DATABASE_STOR_SIZE = 10GiB
|
|
## BACKUP = DEFAULT_DATABASE_STOR_SIZE +
|
|
## DEFAULT_PLATFORM_STOR_SIZE +
|
|
## BACKUP_OVERHEAD = 25GiB
|
|
## LOG_VOL_SIZE = 8GiB
|
|
## SCRATCH_VOL_SIZE = 16GiB
|
|
## RABBIT_LV = 2GiB
|
|
## DEFAULT_EXTENSION_STOR_SIZE = 1GiB
|
|
## KUBERNETES_DOCKER_STOR_SIZE = 30GiB
|
|
## DOCKER_DISTRIBUTION_STOR_SIZE = 16GiB
|
|
## ETCD_STOR_SIZE = 5GiB
|
|
## CEPH_MON_SIZE = 20GiB
|
|
## KUBELET_STOR_SIZE = 10GiB
|
|
## DC_VAULT_SIZE = 15GiB
|
|
## RESERVED_PE = 16MiB (based on pesize=32768)
|
|
##
|
|
## CGCS_PV_SIZE = (10 + 2*10 + 25 + 8 + 16 + 2 + 1 + 30 + 16 + 5 + 20 + 10 + 15)GiB + 16MiB/1024 = 178.02GiB
|
|
##
|
|
##***********************************************************************
|
|
## Small disk install - (for disks below 240GB)
|
|
## - DB size is doubled to allow for upgrades
|
|
##
|
|
## DEFAULT_PLATFORM_STOR_SIZE = 10GiB
|
|
## DEFAULT_SMALL_DATABASE_STOR_SIZE = 5GiB
|
|
## DEFAULT_SMALL_BACKUP_STOR_SIZE = 20GiB
|
|
##
|
|
## LOG_VOL_SIZE = 8GiB
|
|
## SCRATCH_VOL_SIZE = 16GiB
|
|
## RABBIT_LV = 2GiB
|
|
## DEFAULT_EXTENSION_STOR_SIZE = 1GiB
|
|
## KUBERNETES_DOCKER_STOR_SIZE = 30GiB
|
|
## DOCKER_DISTRIBUTION_STOR_SIZE = 16GiB
|
|
## ETCD_STOR_SIZE = 5GiB
|
|
## CEPH_MON_SIZE = 20GiB
|
|
## KUBELET_STOR_SIZE = 10GiB
|
|
## DC_VAULT_SIZE = 15GiB
|
|
## RESERVED_PE = 16MiB (based on pesize=32768)
|
|
##
|
|
## CGCS_PV_SIZE = (10 + 2*5 + 20 + 8 + 16 + 2 + 1 + 30 + 16 + 5 + 20 + 10 + 15)GiB + 16MiB/1024 = 163.02GiB
|
|
##
|
|
##***********************************************************************
|
|
## Tiny disk install - (for disks below 154GB)
|
|
##
|
|
## NOTE: Tiny disk setup is mainly for StarlingX running in QEMU/KVM VM.
|
|
##
|
|
## DEFAULT_TINY_PLATFORM_STOR_SIZE = 1GiB
|
|
## DEFAULT_TINY_DATABASE_STOR_SIZE = 1GiB
|
|
## DEFAULT_TINY_BACKUP_STOR_SIZE = 1GiB
|
|
##
|
|
## LOG_VOL_SIZE = 3GiB
|
|
## SCRATCH_VOL_SIZE = 2GiB
|
|
## RABBIT_LV = 2GiB
|
|
## DEFAULT_EXTENSION_STOR_SIZE = 1GiB
|
|
## TINY_KUBERNETES_DOCKER_STOR_SIZE = 20GiB
|
|
## TINY_DOCKER_DISTRIBUTION_STOR_SIZE = 8GiB
|
|
## TINY_ETCD_STOR_SIZE = 1GiB
|
|
## TINY_KUBELET_STOR_SIZE = 2GiB
|
|
##
|
|
## CGCS_PV_SIZE = (1 + 2*1 + 1 + 3 + 2 + 2 + 1 + 20 + 8 + 1 + 2)GiB = 43GiB
|
|
##
|
|
## MINIMUM_TINY_DISK_SIZE = CGCS_PV_SIZE + ROOTFS_SIZE + EFI_SIZE + BOOT_SIZE + PLATFORM_BACKUP_SIZE
|
|
## = 43 + 15 + 0.3 + 0.5 + 1 = 60GiB
|
|
|
|
# TODO: create a log representing 'free space" on self expand partition.
|
|
|
|
# TODO: Do the math for this new environment
|
|
|
|
# The default disk size thresholds must align with the ones in
|
|
# config/.../sysinv/common/constants.py
|
|
# which are DEFAULT_SMALL_DISK_SIZE
|
|
# MINIMUM_SMALL_DISK_SIZE
|
|
default_small_disk_size=240
|
|
minimum_small_disk_size=196
|
|
sz=$(blockdev --getsize64 ${instdev})
|
|
ilog "install disk size:$sz gb:$gb"
|
|
|
|
# Round CGCS_PV_SIZE to the closest upper value that can be divided by 1024.
|
|
if [ $sz -gt $(($default_small_disk_size*$gb)) ] ; then
|
|
ilog "Large disk: CGCS_PV_SIZE=179GiB*1024=183296"
|
|
CGCS_PV_SIZE=183296
|
|
|
|
elif [ $sz -ge $(($minimum_small_disk_size*$gb)) ] ; then
|
|
ilog "Small disk: CGCS_PV_SIZE=164GiB*1024=167936"
|
|
CGCS_PV_SIZE=167936
|
|
|
|
else
|
|
ilog "Tiny disk: CGCS_PV_SIZE=43GiB*1024=44032"
|
|
# Using a disk with a size under 60GiB will fail.
|
|
CGCS_PV_SIZE=44032
|
|
LOG_VOL_SIZE=3000
|
|
SCRATCH_VOL_SIZE=2000
|
|
PLATFORM_BACKUP_SIZE=1000
|
|
fi
|
|
|
|
elif [ "${controller}" = true ] ; then
|
|
LOG_VOL_SIZE=8000
|
|
SCRATCH_VOL_SIZE=16000
|
|
fi
|
|
|
|
ilog "CGCS_PV_SIZE : ${CGCS_PV_SIZE}"
|
|
ilog "SCRATCH_VOL_SIZE : ${SCRATCH_VOL_SIZE}"
|
|
ilog "ROOTFS_SIZE : ${ROOTFS_SIZE}"
|
|
ilog "LOG_VOL_SIZE : ${LOG_VOL_SIZE}"
|
|
ilog "PLATFORM_BACKUP_SIZE : ${PLATFORM_BACKUP_SIZE}"
|
|
|
|
ilog "BACKUP_PART : ${BACKUP_PART}"
|
|
ilog "BACKUP_PART_NO : ${BACKUP_PART_NO}"
|
|
ilog "BACKUP_PART_LABEL : ${BACKUP_PART_LABEL}"
|
|
ilog "BACKUP_PART_GUID : ${BACKUP_PART_GUID}"
|
|
|
|
if [ "${controller}" = true ] ; then
|
|
ilog "Backup Partition : ${BACKUP_PART}"
|
|
if [ ${BACKUP_PERSISTED} -eq 0 ] ; then
|
|
# TODO: Was hanging when the flock <device> preceeded the sgdisk.
|
|
# Action: Reverify
|
|
# flock ${instdev} sgdisk --change-name=${BACKUP_PART_NO}:"${BACKUP_PART_LABEL}" --typecode=${BACKUP_PART_NO}:"${BACKUP_PART_GUID}" ${instdev} || exit 1
|
|
cat<<EOF>/tmp/backup-guid-change.sh
|
|
ilog "Updating backup partition GUID"
|
|
sgdisk --change-name=${BACKUP_PART_NO}:"${BACKUP_PART_LABEL}" --typecode=${BACKUP_PART_NO}:"${BACKUP_PART_GUID}" ${instdev} || exit 1
|
|
EOF
|
|
fi
|
|
fi
|
|
|
|
ilog "cgts--vg-log--lv size: ${LOG_VOL_SIZE} MB"
|
|
ilog "cgts--vg-scratch--lv : ${SCRATCH_VOL_SIZE} MB"
|
|
ilog "Install disk: ${instdev} ; current partition index:$pi"
|
|
|
|
vg="volume group"
|
|
lv="logical volume"
|
|
dev=$(get_disk "${instdev}")
|
|
|
|
# Only init Platform Backup partition filesystem if the partition was just created
|
|
pi=$((pi+1))
|
|
if [ ${BACKUP_PERSISTED} -eq 0 ] ; then
|
|
ilog "Platform Backup filesystem init ${dev}${pi}"
|
|
mkfs.ext4 -F -L platform_backup ${dev}${pi}
|
|
[ ${?} -ne 0 ] && report_failure_with_msg "Failed Platform Backup partition filesystem init ${dev}${pi}"
|
|
fi
|
|
|
|
# Create Volume Group
|
|
pi=$((pi+1))
|
|
|
|
# Log important LVM config settings
|
|
log_lvm_conf
|
|
|
|
ilog "Create ${vg} 'cgts-vg' ${dev}${pi} ; $STOR_DEV_FDS"
|
|
exec_no_fds "$STOR_DEV_FDS" "vgcreate -y --force cgts-vg ${dev}${pi} 2>/dev/null" 5 0.5
|
|
[ ${?} -ne 0 ] && report_failure_with_msg "Failed to create ${vg} 'cgts-vg' ${dev}${pi}"
|
|
|
|
# Create and Init the '/var/log' logical volume
|
|
ilog "Create ${lv} 'log-lv' ; $STOR_DEV_FDS"
|
|
exec_no_fds "$STOR_DEV_FDS" "lvcreate -y -n log-lv -L ${LOG_VOL_SIZE}MB cgts-vg 2>/dev/null" 5 0.5
|
|
[ ${?} -ne 0 ] && report_failure_with_msg "Failed to create ${lv} 'log-lv'"
|
|
|
|
ilog "InitFs ${lv} 'log-lv'"
|
|
mkfs.ext4 -F /dev/cgts-vg/log-lv
|
|
[ ${?} -ne 0 ] && report_failure_with_msg "Failed to init ${lv} 'log-lv'"
|
|
|
|
# Create and init the '/scratch' logical volume
|
|
ilog "Create ${lv} 'scratch-lv' ; $STOR_DEV_FDS"
|
|
exec_no_fds "$STOR_DEV_FDS" "lvcreate -y -n scratch-lv -L ${SCRATCH_VOL_SIZE}MB cgts-vg 2>/dev/null" 5 0.5
|
|
[ ${?} -ne 0 ] && report_failure_with_msg "Failed to create ${lv} 'scratch-lv'"
|
|
|
|
ilog "InitFs ${lv} 'scratch-lv'"
|
|
mkfs.ext4 -F /dev/cgts-vg/scratch-lv
|
|
[ ${?} -ne 0 ] && report_failure_with_msg "Failed to init ${lv} 'scratch-lv'"
|
|
|
|
#######################################################################
|
|
# From post_lvm_on_rootfs.cfg (all hosts)
|
|
#######################################################################
|
|
|
|
# uncomment the global_filter line in lvm.conf
|
|
perl -0777 -i.bak -pe 's:(# This configuration option has an automatic default value\.\n)\t# global_filter:$1 global_filter:m' /etc/lvm/lvm.conf
|
|
perl -0777 -i -pe 's:(# Example\n)\t# preferred_names:$1 preferred_names:m' /etc/lvm/lvm.conf
|
|
|
|
# Get the LVM disk partition and add it to the lvm.conf file
|
|
LV_ROOTDISK=$(pvdisplay --select 'vg_name=cgts-vg' -C -o pv_name --noheadings)
|
|
[ -z ${LV_ROOTDISK} ] && report_failure_with_msg "Failed to identify logical volume rootdisk via pvdisplay"
|
|
|
|
# Edit the LVM config so LVM only looks for LVs on ${LV_ROOTDISK}
|
|
ilog "Edit the LVM config so LVM only looks for LVs on the root disk"
|
|
sed -i "s#^\( *\)global_filter = \[.*#\1global_filter = [ \"a|${LV_ROOTDISK}|\", \"r|.*|\" ]#" /etc/lvm/lvm.conf
|
|
|
|
# Log important LVM config settings
|
|
log_lvm_conf
|
|
|
|
true
|
|
%end
|
|
|
|
###########################################################################
|
|
|
|
%post --interpreter=/bin/bash
|
|
HOOK_LABEL="post"
|
|
. /tmp/lat/ks_functions.sh
|
|
ilog "****************************************************"
|
|
ilog "**** Post - Traits & Platform Config File update **"
|
|
ilog "****************************************************"
|
|
|
|
set -- `env`
|
|
dlog "env: $*"
|
|
|
|
if false ; then
|
|
# TODO: Why does LAT break into prompt when I do this
|
|
for e in $*; do
|
|
case "$e" in
|
|
*=*)
|
|
eval $e 2>/dev/null
|
|
log "env : $e"
|
|
;;
|
|
esac
|
|
done
|
|
fi
|
|
|
|
ilog "Install traits: $traits"
|
|
|
|
# Set node traits' state
|
|
[ "${controller}" = true ] && ilog "Controller Function"
|
|
[ "${storage}" = true ] && ilog "Storage Function"
|
|
[ "${worker}" = true ] && ilog "Worker Function"
|
|
[ "${lowlatency}" = true ] && ilog "Low Latency Function"
|
|
[ "${controller}" = true -a ${worker} = true ] && aio=true
|
|
|
|
# Parse traits to nodetype, subfunction and system_type
|
|
# -----------------------------------------------------
|
|
|
|
# Set nodetype from traits
|
|
if [ "${controller}" = true ] ; then
|
|
nodetype=${TRAIT__CONTROLLER}
|
|
ilog "Controller Function"
|
|
elif [ "${storage}" = true ] ; then
|
|
nodetype=${TRAIT__STORAGE}
|
|
ilog "Storage Function"
|
|
elif [ "${worker}" = true ] ; then
|
|
nodetype=${TRAIT__WORKER}
|
|
else
|
|
elog "No personality traits specified ; defaulting to All-In-One"
|
|
controller=true
|
|
worker=true
|
|
nodetype=${TRAIT__CONTROLLER}
|
|
fi
|
|
ilog "nodetype=${nodetype}"
|
|
|
|
# Set system type and subfunction
|
|
subfunction=""
|
|
system_type=""
|
|
system_mode="simplex"
|
|
[ "${controller}" = true -a "${worker}" = true ] && aio=true
|
|
if [ "${aio}" = true ] ; then
|
|
ilog "${SYSTEM_TYPE__AIO} System"
|
|
system_type="${SYSTEM_TYPE__AIO}"
|
|
if [ "${rt}" = true ] ; then
|
|
subfunction="${SUBFUNCTION__AIO_LOWLATENCY}"
|
|
else
|
|
subfunction="${SUBFUNCTION__AIO}"
|
|
fi
|
|
else
|
|
ilog "${SYSTEM_TYPE__STANDARD} System"
|
|
system_type="${SYSTEM_TYPE__STANDARD}"
|
|
if [ "${worker}" = true ] ; then
|
|
subfunction=${SUBFUNCTION__WORKER}
|
|
elif [ "${storage}" = true ] ; then
|
|
subfunction=${SUBFUNCTION__STORAGE}
|
|
else
|
|
subfunction=${SUBFUNCTION__CONTROLLER}
|
|
fi
|
|
fi
|
|
ilog "subfunction=${subfunction}"
|
|
ilog "system_type=${system_type}"
|
|
ilog "system_mode=${system_mode}"
|
|
|
|
# Create and Update /etc/platform/platform.conf
|
|
# ---------------------------------------------
|
|
|
|
if [ -e "${PLATFORM_CONF}" ] ; then
|
|
wlog "removing temp platform.conf"
|
|
fi
|
|
|
|
#################################################################
|
|
# From post_platform_conf_controller.cfg
|
|
# From post_platform_conf_aio.cfg
|
|
# From post_platform_conf_aio_lowlatency.cfg
|
|
#################################################################
|
|
|
|
ilog "create platform.conf and set personality traits"
|
|
[ ! -d "/etc/platform" ] && mkdir -p -m 0775 /etc/platform
|
|
cat <<EOF > ${PLATFORM_CONF}
|
|
nodetype=${nodetype}
|
|
subfunction=${subfunction}
|
|
system_type=${system_type}
|
|
system_mode=${system_mode}
|
|
EOF
|
|
|
|
# Set http port
|
|
# Persist the default http port number to platform configuration.
|
|
# This will get overwritten when by manifest during sw configuration phase.
|
|
http_port=$(echo $(cat /proc/cmdline |xargs -n1 echo |grep '^insturl=' | sed -r 's#^[^/]*://[^/]*:([0-9]*)/.*#\1#'))
|
|
update_platform_conf "http_port=${http_port}"
|
|
|
|
# TODO: Set sw release
|
|
update_platform_conf "sw_release=xxxPLATFORM_RELEASExxx"
|
|
|
|
#############################################################
|
|
# From post_common.cfg (all hosts)
|
|
#############################################################
|
|
|
|
# Should handle controller-0 install from external server and USB
|
|
is_system_node_install
|
|
if [ ${?} -ne 0 ] ; then
|
|
# Unset the hostname
|
|
rm /etc/hostname
|
|
if [ "${controller}" = true ] ; then
|
|
echo "controller-0" > /etc/hostname
|
|
fi
|
|
fi
|
|
|
|
# TODO: is this needed with LAT ??
|
|
# If using a serial install make sure to add a getty on the tty1
|
|
conarg=`cat /proc/cmdline |xargs -n1 echo |grep console= |grep ttyS`
|
|
if [ -n "$conarg" ] ; then
|
|
echo "1:2345:respawn:/sbin/mingetty tty1" >> /etc/inittab
|
|
fi
|
|
|
|
if [ "${controller}" = true ] ; then
|
|
# Add the WRCP GUID to the Platform backup partition.
|
|
BACKUP_PART_CHANGE_FILE="/tmp/backup-guid-change.sh"
|
|
if [ -f "${BACKUP_PART_CHANGE_FILE}" ] ; then
|
|
ilog "Found ${BACKUP_PART_CHANGE_FILE} ; running to set Platform backup to persist"
|
|
chmod 744 ${BACKUP_PART_CHANGE_FILE}
|
|
# ISSUE: This hangs LAT with 'flock /dev/sda'
|
|
# TODO : Discuss with Architects
|
|
#
|
|
# flock /dev/sda sgdisk --change-name=6:"Platform Backup" --typecode=6:"BA5EBA11-0000-1111-2222-000000000002" /dev/sda
|
|
. ${BACKUP_PART_CHANGE_FILE} 2>/dev/null
|
|
sleep 2
|
|
parted -l 2>/dev/null
|
|
fi
|
|
fi
|
|
blkid >> ${LOGFILE}
|
|
|
|
# TODO: See if other post_common.cfg content is needed
|
|
|
|
true
|
|
%end
|
|
|
|
###########################################################################
|
|
|
|
%post --interpreter=/bin/bash
|
|
HOOK_LABEL="post"
|
|
. /tmp/lat/ks_functions.sh
|
|
ilog "****************************************************"
|
|
ilog "*** Post - Set Kernel Args ****"
|
|
ilog "****************************************************"
|
|
|
|
###########################################################
|
|
# From post_kernel_controller.cfg
|
|
# From post_kernel_aio_worker.cfg
|
|
###########################################################
|
|
|
|
. /etc/platform/platform.conf
|
|
|
|
# Prepare the disk boot kernel comand line
|
|
# ----------------------------------------
|
|
export KERN_OPTS=""
|
|
ilog "Building KERN_OPTS"
|
|
|
|
function add_kernel_option()
|
|
{
|
|
option="${1}"
|
|
ilog "... adding: ${option}"
|
|
|
|
# avoid adding leading space on first option
|
|
if [ "${KERN_OPTS}" = "" ] ; then
|
|
KERN_OPTS="${option}"
|
|
else
|
|
KERN_OPTS="${KERN_OPTS} ${option}"
|
|
fi
|
|
}
|
|
|
|
# If the installer asked us to use security related kernel params, use
|
|
# them in the grub line as well (until they can be configured via puppet)
|
|
security_feature=""
|
|
|
|
# Handle security options
|
|
# TODO: Create a list and loop over it
|
|
security_options="nopti nospectre_v2 nospectre_v1"
|
|
for o in ${security_options}
|
|
do
|
|
grep -q ${o} /proc/cmdline
|
|
if [ $? -eq 0 ]; then
|
|
add_kernel_option "${o}"
|
|
if [ "${security_feature}" = "" ] ; then
|
|
security_feature="${o}"
|
|
else
|
|
security_feature="${security_feature} ${o}"
|
|
fi
|
|
fi
|
|
done
|
|
|
|
# TODO: Remove as it turns out that this is not added by kickstarts.
|
|
# Remove all reference to 'security_feature' above as well.
|
|
#
|
|
# add security_feature to platform.conf ; be sure not to add as empty.
|
|
# [ -z "${security_feature}" ] && security_feature=none
|
|
# update_platform_conf "security_feature=${security_feature}"
|
|
|
|
[ "${KERN_OPTS}" != "" ] && ilog "Learned kernel params: ${KERN_OPTS}"
|
|
|
|
if [ "${aio}" = true ] ; then
|
|
|
|
ilog "Adding ${SYSTEM_TYPE__AIO} kernel options"
|
|
if [ -e /etc/init.d/cpumap_functions.sh ] ; then
|
|
|
|
# Update grub with custom kernel bootargs
|
|
source /etc/init.d/cpumap_functions.sh
|
|
|
|
n_cpus=$(cat /proc/cpuinfo 2>/dev/null | \
|
|
awk '/^[pP]rocessor/ { n +=1 } END { print (n>0) ? n : 1}')
|
|
ilog "cpumap: n_cpus:${n_cpus}"
|
|
|
|
n_numa=$(ls -d /sys/devices/system/node/node* 2>/dev/null | wc -l)
|
|
ilog "cpumap: n_numa:${n_numa}"
|
|
|
|
KERN_OPTS="${KERN_OPTS} iommu=pt"
|
|
KERN_OPTS="${KERN_OPTS} hugepagesz=2M hugepages=0 default_hugepagesz=2M"
|
|
|
|
# If this is an all-in-one system, we need at least 4 CPUs
|
|
if [ "${aio}" = true -a ${n_cpus} -lt 4 ]; then
|
|
report_failure_with_msg "At least 4 CPUs are required for ${SYSTEM_TYPE__AIO} node."
|
|
fi
|
|
|
|
# Add kernel options for cpu isolation / affinity
|
|
if [ ${n_cpus} -gt 1 ] ; then
|
|
|
|
base_cpulist=$(platform_expanded_cpu_list)
|
|
ilog "cpumap: base_cpulist: ${base_cpulist}"
|
|
|
|
base_cpumap=$(cpulist_to_cpumap ${base_cpulist} ${n_cpus})
|
|
ilog "cpumap: base_cpumap: ${base_cpumap}"
|
|
|
|
avp_cpulist=$(vswitch_expanded_cpu_list)
|
|
ilog "cpumap: avp_cpulist:${avp_cpulist}"
|
|
if [ -e /etc/vswitch/vswitch.conf ] ; then
|
|
# Update vswitch.conf
|
|
sed -i "s/^VSWITCH_CPU_LIST=.*/VSWITCH_CPU_LIST=\"${avp_cpulist}\"/" /etc/vswitch/vswitch.conf
|
|
else
|
|
wlog "Missing /etc/vswitch/vswitch.conf ; update bypassed"
|
|
fi
|
|
|
|
norcu_cpumap=$(invert_cpumap ${base_cpumap} ${n_cpus})
|
|
ilog "cpumap: norcu_cpumap:${norcu_cpumap}"
|
|
|
|
norcu_cpulist=$(cpumap_to_cpulist ${norcu_cpumap} ${n_cpus})
|
|
ilog "cpumap: norcu_cpulist:${norcu_cpulist}"
|
|
|
|
if [ "${lowlatency}" = true ]; then
|
|
KERN_OPTS="${KERN_OPTS} nohz_full=${norcu_cpulist}"
|
|
fi
|
|
|
|
KERN_OPTS="${KERN_OPTS} rcu_nocbs=${norcu_cpulist}"
|
|
KERN_OPTS="${KERN_OPTS} kthread_cpus=${base_cpulist}"
|
|
KERN_OPTS="${KERN_OPTS} irqaffinity=${norcu_cpulist}"
|
|
fi
|
|
else
|
|
wlog "Missing /etc/init.d/cpumap_functions.sh ; cpumap setup bypassed"
|
|
fi
|
|
|
|
# Add kernel options to set NMI watchdog
|
|
if [ "${lowlatency}" = true ] ; then
|
|
add_kernel_option "nmi_watchdog=0 softlockup_panic=0"
|
|
else
|
|
add_kernel_option "nmi_watchdog=panic,1 softlockup_panic=1"
|
|
fi
|
|
|
|
if [[ "$(dmidecode -s system-product-name)" =~ ^ProLiant.*Gen8$ ]]; then
|
|
add_kernel_option "intel_iommu=on,eth_no_rmrr"
|
|
else
|
|
add_kernel_option "intel_iommu=on"
|
|
fi
|
|
|
|
# Add kernel option to disable biosdevname if enabled
|
|
# As this may already be in GRUB_CMDLINE_LINUX, only add if it is not already present
|
|
grep -q '^GRUB_CMDLINE_LINUX=.*biosdevname=0' /etc/default/grub
|
|
if [ $? -ne 0 ]; then
|
|
add_kernel_option "biosdevname=0"
|
|
fi
|
|
|
|
# Add kernel options to disable kvm-intel.eptad on Broadwell
|
|
# Broadwell: Model: 79, Model name: Intel(R) Xeon(R) CPU E5-2699 v4 @ 2.20GHz
|
|
if grep -q -E "^model\s+:\s+79$" /proc/cpuinfo
|
|
then
|
|
add_kernel_option "kvm-intel.eptad=0"
|
|
fi
|
|
|
|
# k8s updates:
|
|
#KERN_OPTS="${KERN_OPTS} cgroup_disable=memory"
|
|
add_kernel_option "user_namespace.enable=1"
|
|
|
|
# Add kernel option to avoid jiffies_lock contention on real-time kernel
|
|
if [ "${lowlatency}" = true ] ; then
|
|
add_kernel_option "skew_tick=1"
|
|
fi
|
|
|
|
elif [ "${controller}" = true ] ; then
|
|
|
|
ilog "Adding ${TRAIT__CONTROLLER} function kernel options"
|
|
|
|
## Custom kernel options
|
|
add_kernel_option "intel_iommu=off usbcore.autosuspend=-1"
|
|
|
|
## Setup the loop module to support up to 15 partitions so that we
|
|
## can enable the customer to manually resize images if needed.
|
|
##
|
|
add_kernel_option "loop.max_part=15"
|
|
|
|
## Add kernel options to ensure an selinux is disabled
|
|
add_kernel_option "selinux=0 enforcing=0"
|
|
|
|
# Add kernel options to ensure NMI watchdog is enabled, if supported
|
|
add_kernel_option "nmi_watchdog=panic,1 softlockup_panic=1"
|
|
|
|
# Add kernel option to panic on a softdog timeout
|
|
add_kernel_option "softdog.soft_panic=1"
|
|
|
|
# Add kernel option to disable biosdevname if enabled
|
|
# As this may already be in GRUB_CMDLINE_LINUX, only add if it is not already present
|
|
grep -q '^GRUB_CMDLINE_LINUX=.*biosdevname=0' /etc/default/grub
|
|
[ $? -ne 0 ] && add_kernel_option "biosdevname=0"
|
|
|
|
# k8s updates
|
|
add_kernel_option "user_namespace.enable=1"
|
|
else
|
|
wlog "TODO: system node install type kernel parameters, worker and storage"
|
|
fi
|
|
|
|
# TODO: Is this needed ? Certainlty not the Centos part
|
|
# perl -pi -e 's/(GRUB_CMDLINE_LINUX=.*)\"/\1'"$KERN_OPTS"'\"/g' /etc/default/grub
|
|
|
|
# if [ -d /sys/firmware/efi ] ; then
|
|
# grub2-mkconfig -o /boot/efi/EFI/centos/grub.cfg
|
|
# else
|
|
# grub2-mkconfig -o /boot/grub2/grub.cfg
|
|
# fi
|
|
# The uncommented code below updates the disk boot command for LAT
|
|
|
|
ilog "Adding these kernel params to disk boot: ${KERN_OPTS}"
|
|
if [ -n "${KERN_OPTS}" ] ; then
|
|
# Add 'set kernel_params="${kernel_params} ${KERN_OPTS}"' to disk
|
|
# boot command line by /boot/efi/EFI/BOOT/grub.cfg update
|
|
grep -q "set kernel_params=.*${KERN_OPTS}" /boot/efi/EFI/BOOT/grub.cfg
|
|
if [ ${?} -ne 0 ]; then
|
|
sed -i "/set kernel_params=.*/a set kernel_params=\"\${kernel_params} ${KERN_OPTS}\"" /boot/efi/EFI/BOOT/grub.cfg
|
|
fi
|
|
else
|
|
wlog "no kernel options added"
|
|
fi
|
|
|
|
######################################################################
|
|
# From post_system_aio
|
|
######################################################################
|
|
if [ "${aio}" = true ] ; then
|
|
|
|
## Reserve more memory for base processes since the controller has higher
|
|
## memory requirements but cap it to better handle systems with large
|
|
## amounts of memory
|
|
TOTALMEM=$(grep MemTotal /proc/meminfo | awk '{print int($2/1024)}')
|
|
ilog "${SYSTEM_TYPE__AIO} MemTotal:${TOTALMEM}"
|
|
|
|
if [ -e /sys/devices/system/node/node0 ]; then
|
|
RESERVEDMEM=$(grep MemTotal /sys/devices/system/node/node0/meminfo | awk '{printf "%d\n", $4/1024}')
|
|
else
|
|
RESERVEDMEM=$(grep MemTotal /proc/meminfo | awk '{print int($2/1024/4)}')
|
|
fi
|
|
|
|
if [ ${RESERVEDMEM} -lt 6144 ]; then
|
|
RESERVEDMEM=6144
|
|
elif [ ${RESERVEDMEM} -gt 14500 ]; then
|
|
RESERVEDMEM=14500
|
|
elif [ ${RESERVEDMEM} -gt 8192 ]; then
|
|
RESERVEDMEM=8192
|
|
fi
|
|
|
|
ilog "${SYSTEM_TYPE__AIO} Reserved Memory: ${RESERVEDMEM}"
|
|
sed -i -e "s#\(WORKER_BASE_RESERVED\)=.*#\1=(\"node0:${RESERVEDMEM}MB:1\" \"node1:2000MB:0\" \"node2:2000MB:0\" \"node3:2000MB:0\")#g" /etc/platform/worker_reserved.conf
|
|
worker_reserved=$(grep WORKER_BASE_RESERVED /etc/platform/worker_reserved.conf)
|
|
ilog "${SYSTEM_TYPE__AIO} '${worker_reserved}'"
|
|
|
|
# Update WORKER_CPU_LIST
|
|
N_CPUS=$(cat /proc/cpuinfo 2>/dev/null | awk '/^[pP]rocessor/ { n +=1 } END { print (n>0) ? n : 1}')
|
|
sed -i "s/^WORKER_CPU_LIST=.*/WORKER_CPU_LIST=\"0-$((N_CPUS-1))\"/" /etc/platform/worker_reserved.conf
|
|
|
|
worker_cpu_list=$(grep WORKER_CPU_LIST /etc/platform/worker_reserved.conf)
|
|
ilog "${SYSTEM_TYPE__AIO} '${worker_cpu_list}'"
|
|
fi
|
|
|
|
true
|
|
%end
|
|
|
|
###########################################################################
|
|
|
|
%post --interpreter=/bin/bash
|
|
HOOK_LABEL="post"
|
|
. /tmp/lat/ks_functions.sh
|
|
|
|
ilog "****************************************************"
|
|
ilog "*** Post - Interface Setup ***"
|
|
ilog "****************************************************"
|
|
|
|
###########################################################
|
|
# From post_pxeboot_controller
|
|
# From post_net_common.cfg
|
|
###########################################################
|
|
|
|
# TODO: Not needed on a USB install.
|
|
# TODO: Need to adjust fault handling or condition on USB install.
|
|
|
|
# Obtain the boot interface from the PXE boot
|
|
BOOTIF=$(cat /proc/cmdline |xargs -n1 echo |grep BOOTIF=)
|
|
BOOTIF=${BOOTIF#BOOTIF=}
|
|
mgmt_dev=lo
|
|
mgmt_vlan=0
|
|
if [ -n "$BOOTIF" ] ; then
|
|
BOOTIF=$(echo $BOOTIF | sed -r -e 's/.*(..-..-..-..-..-..)$/\1/' -e 's/-/:/g')
|
|
ndev=`ip link show |grep -B 1 $BOOTIF |head -1 |awk '{print $2}' |sed -e 's/://'`
|
|
if [ -n "$ndev" ] ; then
|
|
# convert to predictive name
|
|
mgmt_dev=$(get_iface_from_ethname $ndev)
|
|
if [ "${mgmt_dev}" == "" ] ; then
|
|
elog "failed to get predictive altname from ${ndev}"
|
|
mgmt_dev=${ndev}
|
|
|
|
# get vlan info for system node installs
|
|
system_node=$(is_system_node_install)
|
|
if [ "${system_node}" = true ] ; then
|
|
# Retrieve the management VLAN from sysinv if it exists
|
|
ilog "Querying system inventory for management vlan id"
|
|
mgmt_vlan=`curl -sf http://pxecontroller:6385/v1/isystems/mgmtvlan`
|
|
if [ ${?} -ne 0 ] ; then
|
|
# TODO: uncomment to force install failure for product
|
|
# report_failure_with_msg "Unable to communicate with System Inventory REST API. Aborting installation."
|
|
wlog "ERROR: Unable to communicate with System Inventory REST API."
|
|
fi
|
|
fi
|
|
else
|
|
ilog "Management Interface: ${ndev} -> ${mgmt_dev}"
|
|
fi
|
|
else
|
|
elog "ERROR:POST: Unable to determine mgmt interface from BOOTIF=$BOOTIF."
|
|
# TODO: MAKE Default - Should not get here without BOOTIF set ; LAT guarantees that.
|
|
# report_failure_with_msg "Unable to determine mgmt interface from BOOTIF=$BOOTIF."
|
|
fi
|
|
else
|
|
elog "ERROR:POST: BOOTIF is not set. Unable to determine mgmt interface."
|
|
# TODO: MAKE Default - Should not get here without BOOTIF set ; LAT guarantees that.
|
|
fi
|
|
|
|
if [ ! -e "/etc/network/interfaces" ] ; then
|
|
cat << EOF >> /etc/network/interfaces
|
|
# This file describes the network interfaces available on the system
|
|
# and how to activate them. For more information , see interfaces(5)
|
|
source /etc/network/interfaces.d/*
|
|
EOF
|
|
fi
|
|
|
|
if [ ! -d "/etc/network/interfaces.d" ] ; then
|
|
mkdir -p -m 0775 /etc/network/interfaces.d
|
|
fi
|
|
|
|
# Build networking scripts, starting with the localhost interface
|
|
cat << EOF >> /etc/network/interfaces
|
|
|
|
# The loopback network interface
|
|
auto lo
|
|
iface lo inet loopback
|
|
EOF
|
|
|
|
cat << EOF >> /etc/network/interfaces
|
|
|
|
# management network interface
|
|
allow-hotplug $mgmt_dev
|
|
auto $mgmt_dev
|
|
iface $mgmt_dev inet dhcp
|
|
|
|
EOF
|
|
|
|
ilog "Setup network scripts"
|
|
|
|
if [ $mgmt_vlan -eq 0 ] ; then
|
|
|
|
# Persist the boot device to the platform configuration. This will get
|
|
# overwritten later if the management_interface is on a bonded interface.
|
|
update_platform_conf "management_interface=$mgmt_dev"
|
|
|
|
# Build networking scripts
|
|
cat << EOF > /etc/network/interfaces.d/ifcfg-lo
|
|
auto lo
|
|
iface lo inet static
|
|
address 127.0.0.1
|
|
netmask 255.0.0.0
|
|
post-up echo 0 > /proc/sys/net/ipv6/conf/lo/autoconf; echo 0 > /proc/sys/net/ipv6/conf/lo/accept_ra; echo 0 > /proc/sys/net/ipv6/conf/lo/accept_redirects
|
|
EOF
|
|
|
|
|
|
cat << EOF > /etc/network/interfaces.d/ifcfg-$mgmt_dev
|
|
auto $mgmt_dev
|
|
iface $mgmt_dev inet manual
|
|
pre-up sleep 20
|
|
post-up echo 0 > /proc/sys/net/ipv6/conf/lo/autoconf; echo 0 > /proc/sys/net/ipv6/conf/lo/accept_ra; echo 0 > /proc/sys/net/ipv6/conf/lo/accept_redirects
|
|
EOF
|
|
|
|
else
|
|
|
|
# Check whether to use inet or inet6
|
|
ipv6_addr=$(dig +short AAAA controller)
|
|
if [[ -n "$ipv6_addr" ]]
|
|
then
|
|
mgmt_address_family=inet6
|
|
ipv6init=yes
|
|
dhcpv6c=yes
|
|
dhclientargs=-1
|
|
else
|
|
mgmt_address_family=inet
|
|
ipv6init=no
|
|
dhcpv6c=no
|
|
dhclientargs=
|
|
fi
|
|
|
|
# Persist the boot device to the platform configuration. This will get
|
|
# overwritten later if the management_interface is on a bonded interface.
|
|
update_platform_conf "management_interface=vlan$mgmt_vlan"
|
|
|
|
# Build networking scripts
|
|
cat << EOF > /etc/network/interfaces.d/ifcfg-lo
|
|
auto lo
|
|
iface lo $mgmt_address_family static
|
|
address 127.0.0.1
|
|
netmask 255.0.0.0
|
|
post-up echo 0 > /proc/sys/net/ipv6/conf/lo/autoconf; echo 0 > /proc/sys/net/ipv6/conf/lo/accept_ra; echo 0 > /proc/sys/net/ipv6/conf/lo/accept_redirects
|
|
EOF
|
|
|
|
cat << EOF > /etc/network/interfaces.d/ifcfg-$mgmt_dev
|
|
auto $mgmt_dev
|
|
iface $mgmt_dev $mgmt_address_family manual
|
|
pre-up sleep 20
|
|
post-up echo 0 > /proc/sys/net/ipv6/conf/lo/autoconf; echo 0 > /proc/sys/net/ipv6/conf/lo/accept_ra; echo 0 > /proc/sys/net/ipv6/conf/lo/accept_redirects
|
|
EOF
|
|
|
|
cat << EOF > /etc/network/interfaces.d/ifcfg-vlan$mgmt_vlan
|
|
auto vlan$mgmt_vlan
|
|
iface vlan$mgmt_vlan $mgmt_address_family dhcp
|
|
vlan-raw-device $mgmt_dev
|
|
pre-up sleep 20
|
|
post-up echo 0 > /proc/sys/net/ipv6/conf/lo/autoconf; echo 0 > /proc/sys/net/ipv6/conf/lo/accept_ra; echo 0 > /proc/sys/net/ipv6/conf/lo/accept_redirects
|
|
EOF
|
|
fi
|
|
|
|
true
|
|
|
|
%end
|
|
|
|
##########################################################################
|
|
|
|
%post --interpreter=/bin/bash
|
|
HOOK_LABEL="post"
|
|
. /tmp/lat/ks_functions.sh
|
|
ilog "****************************************************"
|
|
ilog "*** Post - Kickstart Finalize Install UUID ***"
|
|
ilog "****************************************************"
|
|
|
|
# Create a uuid specific to this installation
|
|
ilog "Add install uuid to feed and platform.conf"
|
|
|
|
INSTALL_UUID=`uuidgen`
|
|
|
|
[ ! -d "/var/www/pages/feed/rel-xxxPLATFORM_RELEASExxx" ] && mkdir -p -m 0755 /var/www/pages/feed/rel-xxxPLATFORM_RELEASExxx
|
|
echo ${INSTALL_UUID} > /var/www/pages/feed/rel-xxxPLATFORM_RELEASExxx/install_uuid
|
|
update_platform_conf "INSTALL_UUID=${INSTALL_UUID}"
|
|
|
|
# Create first_boot flag
|
|
touch /etc/platform/.first_boot
|
|
|
|
true
|
|
%end
|
|
|
|
##########################################################################
|
|
|
|
%post --interpreter=/bin/bash
|
|
HOOK_LABEL="post"
|
|
. /tmp/lat/ks_functions.sh
|
|
ilog "****************************************************"
|
|
ilog "*** Post - Log Filesystem Setup ***"
|
|
ilog "****************************************************"
|
|
|
|
display_volume_info "final"
|
|
|
|
true
|
|
%end
|
|
|
|
##########################################################################
|
|
|
|
%post --interpreter=/bin/bash --nochroot
|
|
HOOK_LABEL="post_nochroot"
|
|
. /tmp/lat/ks_functions.sh
|
|
ilog "****************************************************"
|
|
ilog "*** Post Nochroot - Save Install Scripts and Logs **"
|
|
ilog "****************************************************"
|
|
ilog "IMAGE_ROOTFS=${IMAGE_ROOTFS}"
|
|
|
|
get_variable "ostree_repo_fetched"
|
|
OSTREE_REPO_FETCHED=$?
|
|
|
|
# Fetch ostree
|
|
if [ "${controller}" = true -a ${OSTREE_REPO_FETCHED} -eq 0 ] ; then
|
|
$(is_system_node_install)
|
|
if [ $? -ne 0 ] ; then
|
|
sw_release="xxxPLATFORM_RELEASExxx"
|
|
pxeurl=$(echo $insturl | sed -e s/ostree_repo//)
|
|
|
|
# -1 is all commits, positive number is that number of last commits
|
|
commits="--depth=-1"
|
|
pull_options="${commits} --mirror"
|
|
feed="${IMAGE_ROOTFS}/var/www/pages/feed/rel-${sw_release}"
|
|
repo="${feed}/ostree_repo"
|
|
mkdir -p "${repo}"
|
|
|
|
ilog "Pull ostree_repo to ${repo}"
|
|
ostree --repo=${repo} init --mode=archive
|
|
ostree --repo=${repo} remote add ${instbr} ${insturl}
|
|
ostree --repo=${repo} pull ${pull_options} ${instbr}:${instbr}
|
|
|
|
# TODO: Figure out a way on the second run /sysroot/ostree/2
|
|
# to avoid this error string
|
|
#
|
|
# error: Remote configuration for "starlingx" already exists: (in config)
|
|
|
|
# Check for noverifyssl
|
|
if grep -q noverifyssl /proc/cmdline; then
|
|
NOVERIFYSSL_WGET_OPT="--no-check-certificate"
|
|
else
|
|
NOVERIFYSSL_WGET_OPT=""
|
|
fi
|
|
|
|
pushd ${feed}
|
|
|
|
# TODO: Remove ; This is temporary until the kernel and initrd are fetched from ostree_repo
|
|
wget ${NOVERIFYSSL_WGET_OPT} --spider --quiet ${pxeurl}/bzImage
|
|
[ $? -ne 0 ] && report_failure_with_msg "Failed to find bzImage on pxeboot server ; ${sw_release} ${pxeurl}"
|
|
wget ${NOVERIFYSSL_WGET_OPT} --reject 'index.html*' --quiet ${pxeurl}/bzImage
|
|
[ $? -ne 0 ] && report_failure_with_msg "Failed to get bzImage from pxeboot server ; ${sw_release} ${pxeurl}"
|
|
|
|
wget ${NOVERIFYSSL_WGET_OPT} --spider --quiet ${pxeurl}/initrd
|
|
[ $? -ne 0 ] && report_failure_with_msg "Failed to find initrd on pxeboot server ; ${sw_release} ${pxeurl}"
|
|
wget ${NOVERIFYSSL_WGET_OPT} --reject 'index.html*' --quiet ${pxeurl}/initrd
|
|
[ $? -ne 0 ] && report_failure_with_msg "Failed to get initrd from pxeboot server ; ${sw_release} ${pxeurl}"
|
|
|
|
# TODO: Not neeed once the kickstart is in the iso
|
|
# Save the kickstart
|
|
cp /${LAT_DIR}/lat-installer.ks ${feed}/kickstart.cfg
|
|
|
|
# This fetch is only needed once because the repo is stored in /var
|
|
set_variable "ostree_repo_fetched"
|
|
|
|
popd
|
|
fi
|
|
fi
|
|
|
|
# Save the install scripts and kickstart logs
|
|
mount /dev/mapper/cgts--vg-log--lv "${IMAGE_ROOTFS}/${LOG_DIR}"
|
|
if [ ${?} -ne 0 ] ; then
|
|
elog "Failed to mount /dev/mapper/cgts--vg-log--lv"
|
|
else
|
|
if [ -e "${IMAGE_ROOTFS}/${LOG_DIR}" ]; then
|
|
ilog "Saving installer data to /${LOG_DIR}"
|
|
cp -a /${LAT_DIR} ${IMAGE_ROOTFS}/${LOG_DIR}
|
|
cp /install ${IMAGE_ROOTFS}/${LOG_DIR}/lat
|
|
else
|
|
wlog "Could not save installer data"
|
|
fi
|
|
umount "${IMAGE_ROOTFS}/${LOG_DIR}"
|
|
fi
|
|
|
|
# uncomment the global_filter line in lvm.conf
|
|
#perl -0777 -i.bak -pe 's:(# This configuration option has an automatic default value\.\n)\t# global_filter:$1 global_filter:m' ${IMAGE_ROOTFS}/etc/lvm/lvm.conf
|
|
#perl -0777 -i -pe 's:(# Example\n)\t# preferred_names:$1 preferred_names:m' ${IMAGE_ROOTFS}/etc/lvm/lvm.conf
|
|
#sed -i "s#^\( *\)global_filter = \[.*#\1global_filter = [ \"a|${LV_ROOTDISK}|\", \"r|.*|\" ]#" ${IMAGE_ROOTFS}/etc/lvm/lvm.conf
|
|
|
|
true
|
|
%end
|