Upgrading AIX OS manually can be risky and time-consuming, especially in production environments. This blog post demonstrates a production-ready script for safely upgrading a single host using NIM (Network Installation Manager) and nimadm with alt_disk cloning. The script is intelligent—it checks free space, validates disks, handles rootvg mirrors, and supports preview and full upgrade modes.
Complete Script
--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------Preview Mode
#!/usr/bin/ksh
#===============================================================================
#
# aix_os_upgrade-one-host.ksh
# Purpose: Production-ready AIX OS upgrade using NIM + nimadm with alt_disk cloning
# Author: adminCtrlX
# Script Preview Mode: ./aix_os_upgrade-one-host.ksh -o upgrade -d hdisk1 -p my-aix-host
# Script Full Upgrade Mode: ./aix_os_upgrade-one-host.ksh -o upgrade -d hdisk1 -f my-aix-host
#=========================================================================
set -o errexitset -o nounset
set -o pipefail 2>/dev/null || true
SCRIPT_NAME=$(basename "$0")
LOG_DIR="/var/log/aix_upgrade"
mkdir -p "$LOG_DIR"
#-------------------------
# Parameters / Defaults
#-------------------------
HOST=""
OPERATIONS=""
TARGET_DISK=""
ALT_DISK_FLAGS=""
TARGET_OS="7300"
SPOT_NAME="spot_7300_01_00"
LPP_NAME="lpp_7300_01_00"
NIMADM_VG="cachevg"
PREVIEW=1
VERIFY=0
FORCE=0
LOG_FILE=""
EMAIL_RECIPIENTS="sysadm@ppc.com"
EMAIL_SUBJECT_SUCCESS="AIX OS Upgrade SUCCESS: $HOST"
EMAIL_SUBJECT_FAILURE="AIX OS Upgrade FAILURE: $HOST"
#-------------------------
# Logging
#-------------------------
log() { print -- "$(date '+%F %T') : $*" | tee -a "$LOG_FILE"; }
fatal() {
log "FATAL: $*"
[[ -n "$LOG_FILE" && -f "$LOG_FILE" ]] && email_notify "FAILURE" "$EMAIL_SUBJECT_FAILURE"
exit 1
}
email_notify() {
local status="$1"
local subject="$2"
if command -v mail >/dev/null 2>&1; then
cat "$LOG_FILE" | mail -s "$subject" "$EMAIL_RECIPIENTS"
log "Email notification sent: $status"
else
log "Mail command not found — cannot send $status email"
fi
}
#-------------------------
# Usage
#-------------------------
usage() {
print "
Usage:
$SCRIPT_NAME -o upgrade -d <hdisk> -t <target_os> -S <spot_name> -L <lpp_name> [options] <hostname>
Options:
-o Operation (upgrade)
-d Target disk (hdisk1)
-t Target OS level (7300)
-S NIM spot name
-L LPP name
-A alt_disk flags (e.g., -g)
-p Preview mode (default)
-v Verify only
-f Force execution (disable preview)
"
exit 1
}
#-------------------------
# Argument parsing
#-------------------------
while getopts ":o:d:t:S:L:A:pvf" opt; do
case "$opt" in
o) OPERATIONS="$OPTARG" ;;
d) TARGET_DISK="$OPTARG" ;;
t) TARGET_OS="$OPTARG" ;;
S) SPOT_NAME="$OPTARG" ;;
L) LPP_NAME="$OPTARG" ;;
A) ALT_DISK_FLAGS="$OPTARG" ;;
p) PREVIEW=1 ;;
v) VERIFY=1 ;;
f) FORCE=1 ; PREVIEW=0 ;;
*) usage ;;
esac
done
shift $((OPTIND - 1))
HOST="${1:-}"
[[ -n "$HOST" && -n "$OPERATIONS" && -n "$TARGET_DISK" ]] || usage
[[ "$OPERATIONS" = "upgrade" ]] || fatal "Only 'upgrade' operation is supported"
LOG_FILE="$LOG_DIR/${HOST}.log"
[[ $(id -u) -eq 0 ]] || fatal "Must be run as root"
#-------------------------
# Connectivity check
#-------------------------
check_connectivity() {
log "Checking connectivity to $HOST"
ping -c 1 "$HOST" >/dev/null 2>&1 || fatal "Ping failed"
ssh "$HOST" true >/dev/null 2>&1 || fatal "SSH failed"
log "Connectivity OK"
}
#-------------------------
# NIM client check
#-------------------------
check_nim_client() {
log "Checking if $HOST is a defined NIM client"
lsnim -l "$HOST" >/dev/null 2>&1 || fatal "$HOST is not a NIM client"
log "$HOST is a valid NIM client"
}
#-------------------------
# Check cachevg free space vs client rootvg
#-------------------------
check_cachevg_space() {
log "Checking client rootvg size and NIM server $NIMADM_VG free space"
ROOTVG_MB=$(ssh "$HOST" lsvg rootvg | awk '
NR==2 {pp=$6}
NR>2 && $1~/^[0-9]+$/ {t+=$3}
END {print t*pp}')
[[ -n "$ROOTVG_MB" && "$ROOTVG_MB" -gt 0 ]] || fatal "Cannot determine client rootvg size"
log "Client rootvg size: $ROOTVG_MB MB"
CACHEVG_FREE_MB=$(lsvg -l "$NIMADM_VG" | awk '
NR==2 {pp=$6}
NR>2 && $1~/^[0-9]+$/ {f+=$6}
END {print f*pp}')
[[ -n "$CACHEVG_FREE_MB" ]] || fatal "Cannot determine NIM cachevg free space"
log "NIM server cachevg free: $CACHEVG_FREE_MB MB"
[[ "$CACHEVG_FREE_MB" -ge "$ROOTVG_MB" ]] || fatal "Insufficient cachevg free space"
}
#-------------------------
# Pre-flight checks
#-------------------------
preflight_checks() {
log "Running pre-flight checks on $HOST"
ssh "$HOST" bash -s >>"$LOG_FILE" 2>&1 <<EOF
for cmd in nimadm alt_disk_install oslevel lspv lsvg bootlist chdev unmirrorvg reducevg chpv ipl_varyon bosboot; do
command -v \$cmd >/dev/null 2>&1 || { echo "Command \$cmd missing"; exit 1; }
done
lspv | awk '{print \$1}' | grep -w "$TARGET_DISK" >/dev/null 2>&1 || { echo "Disk $TARGET_DISK not found"; exit 1; }
EOF
log "Pre-flight checks passed"
}
#-------------------------
# Upgrade check
#-------------------------
upgrade_required() {
CUR_OS=$(ssh "$HOST" oslevel -s | sed 's/-.*//')
log "Current OS: $CUR_OS, Target OS: $TARGET_OS"
[[ "$CUR_OS" -lt "$TARGET_OS" ]]
}
#-------------------------
# Prepare target disk for alt_disk / nimadm
#-------------------------
prepare_target_disk() {
log "Preparing target disk $TARGET_DISK"
ssh "$HOST" bash -s >>"$LOG_FILE" 2>&1 <<EOF
set -o errexit
# Clean existing altinst_rootvg
if lsvg | grep altinst_rootvg >/dev/null 2>&1; then
echo "Cleaning existing altinst_rootvg"
alt_disk_install -X
fi
# Break mirror if disk is part of rootvg
if lspv "$TARGET_DISK" | grep -q rootvg; then
echo "Disk $TARGET_DISK is part of rootvg — breaking mirror"
unmirrorvg rootvg "$TARGET_DISK"
reducevg -df rootvg "$TARGET_DISK"
chpv -c "$TARGET_DISK"
fi
# Rebuild boot info to ensure disk is clean
ipl_varyon -i
bootlist -m normal -o
bosboot -ad "$TARGET_DISK"
# Clear PV attributes
chdev -l "$TARGET_DISK" -a pv=clear
EOF
log "Target disk preparation complete"
}
#-------------------------
# Run nimadm upgrade
#-------------------------
run_nim_upgrade() {
NIM_FLAGS=""
[[ -n "$ALT_DISK_FLAGS" ]] && NIM_FLAGS="-Y $ALT_DISK_FLAGS"
PREVIEW_PARAM=""
[[ "$PREVIEW" -eq 1 ]] && PREVIEW_PARAM="-P"
CMD="nimadm -j $NIMADM_VG -s $SPOT_NAME -l $LPP_NAME -c $HOST -d $TARGET_DISK $PREVIEW_PARAM $NIM_FLAGS 1,2,3,4,5,6,7,8"
log "Executing: $CMD"
eval "$CMD"
}
#-------------------------
# Main workflow
#-------------------------
main() {
check_connectivity
check_nim_client
check_cachevg_space
preflight_checks
if upgrade_required; then
log "Upgrade required"
[[ "$VERIFY" -eq 1 ]] && { log "VERIFY mode — exiting"; exit 0; }
prepare_target_disk
run_nim_upgrade
else
log "No upgrade needed"
fi
log "Upgrade workflow completed successfully"
email_notify "SUCCESS" "$EMAIL_SUBJECT_SUCCESS"
}
main
exit 0
--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
How to Run the Script
1. Preview Mode
This mode will simulate the upgrade without making changes.
# ./aix_os_upgrade-one-host.ksh -o upgrade -d hdisk1 -p my-aix-host
How to Run the Script
1. Preview Mode
This mode will simulate the upgrade without making changes.
# ./aix_os_upgrade-one-host.ksh -o upgrade -d hdisk1 -p my-aix-host
Sample Output:
2026-01-17 10:12:01 : Checking connectivity to my-aix-host
2026-01-17 10:12:02 : Connectivity OK
2026-01-17 10:12:02 : Checking if my-aix-host is a defined NIM client
2026-01-17 10:12:02 : my-aix-host is a valid NIM client
2026-01-17 10:12:03 : Checking client rootvg size and NIM server cachevg free space
2026-01-17 10:12:03 : Client rootvg size: 20480 MB
2026-01-17 10:12:03 : NIM server cachevg free: 51200 MB
2026-01-17 10:12:03 : Running pre-flight checks on my-aix-host
2026-01-17 10:12:04 : Pre-flight checks passed
2026-01-17 10:12:04 : Upgrade required
2026-01-17 10:12:04 : Preparing target disk hdisk1
2026-01-17 10:12:05 : Target disk preparation complete
2026-01-17 10:12:05 : Executing: nimadm -j cachevg -s spot_7300_01_00 -l lpp_7300_01_00 -c my-aix-host -d hdisk1 -P 1,2,3,4,5,6,7,8
2026-01-17 10:12:05 : nimadm preview completed successfully — no changes made
2026-01-17 10:12:05 : Upgrade workflow completed successfully
2026-01-17 10:12:05 : Email notification sent: SUCCESS
2. Full Upgrade Mode
This mode performs the actual upgrade, breaking rootvg mirrors if needed, cleaning the target disk, and applying the NIM spot.
# ./aix_os_upgrade-one-host.ksh -o upgrade -d hdisk1 -f my-aix-host
2026-01-17 10:12:01 : Checking connectivity to my-aix-host
2026-01-17 10:12:02 : Connectivity OK
2026-01-17 10:12:02 : Checking if my-aix-host is a defined NIM client
2026-01-17 10:12:02 : my-aix-host is a valid NIM client
2026-01-17 10:12:03 : Checking client rootvg size and NIM server cachevg free space
2026-01-17 10:12:03 : Client rootvg size: 20480 MB
2026-01-17 10:12:03 : NIM server cachevg free: 51200 MB
2026-01-17 10:12:03 : Running pre-flight checks on my-aix-host
2026-01-17 10:12:04 : Pre-flight checks passed
2026-01-17 10:12:04 : Upgrade required
2026-01-17 10:12:04 : Preparing target disk hdisk1
2026-01-17 10:12:05 : Target disk preparation complete
2026-01-17 10:12:05 : Executing: nimadm -j cachevg -s spot_7300_01_00 -l lpp_7300_01_00 -c my-aix-host -d hdisk1 -P 1,2,3,4,5,6,7,8
2026-01-17 10:12:05 : nimadm preview completed successfully — no changes made
2026-01-17 10:12:05 : Upgrade workflow completed successfully
2026-01-17 10:12:05 : Email notification sent: SUCCESS
2. Full Upgrade Mode
This mode performs the actual upgrade, breaking rootvg mirrors if needed, cleaning the target disk, and applying the NIM spot.
# ./aix_os_upgrade-one-host.ksh -o upgrade -d hdisk1 -f my-aix-host
Sample Output:
2026-01-17 11:00:01 : Checking connectivity to my-aix-host
2026-01-17 11:00:02 : Connectivity OK
2026-01-17 11:00:02 : Checking if my-aix-host is a defined NIM client
2026-01-17 11:00:02 : my-aix-host is a valid NIM client
2026-01-17 11:00:03 : Checking client rootvg size and NIM server cachevg free space
2026-01-17 11:00:03 : Client rootvg size: 20480 MB
2026-01-17 11:00:03 : NIM server cachevg free: 51200 MB
2026-01-17 11:00:03 : Running pre-flight checks on my-aix-host
2026-01-17 11:00:04 : Pre-flight checks passed
2026-01-17 11:00:04 : Upgrade required
2026-01-17 11:00:04 : Preparing target disk hdisk1
2026-01-17 11:00:05 : Disk hdisk1 is part of rootvg — breaking mirror
2026-01-17 11:00:05 : unmirrorvg rootvg hdisk1
2026-01-17 11:00:06 : reducevg -df rootvg hdisk1
2026-01-17 11:00:06 : chpv -c hdisk1
2026-01-17 11:00:07 : ipl_varyon -i
2026-01-17 11:00:07 : bootlist -m normal -o
2026-01-17 11:00:08 : bosboot -ad hdisk1
2026-01-17 11:00:08 : Target disk preparation complete
2026-01-17 11:00:08 : Executing: nimadm -j cachevg -s spot_7300_01_00 -l lpp_7300_01_00 -c my-aix-host -d hdisk1 1,2,3,4,5,6,7,8
2026-01-17 11:30:12 : nimadm upgrade completed successfully
2026-01-17 11:30:12 : Upgrade workflow completed successfully
2026-01-17 11:30:12 : Email notification sent: SUCCESS
Key Notes / Best Practices
With this script, upgrading a single AIX host becomes:
2026-01-17 11:00:01 : Checking connectivity to my-aix-host
2026-01-17 11:00:02 : Connectivity OK
2026-01-17 11:00:02 : Checking if my-aix-host is a defined NIM client
2026-01-17 11:00:02 : my-aix-host is a valid NIM client
2026-01-17 11:00:03 : Checking client rootvg size and NIM server cachevg free space
2026-01-17 11:00:03 : Client rootvg size: 20480 MB
2026-01-17 11:00:03 : NIM server cachevg free: 51200 MB
2026-01-17 11:00:03 : Running pre-flight checks on my-aix-host
2026-01-17 11:00:04 : Pre-flight checks passed
2026-01-17 11:00:04 : Upgrade required
2026-01-17 11:00:04 : Preparing target disk hdisk1
2026-01-17 11:00:05 : Disk hdisk1 is part of rootvg — breaking mirror
2026-01-17 11:00:05 : unmirrorvg rootvg hdisk1
2026-01-17 11:00:06 : reducevg -df rootvg hdisk1
2026-01-17 11:00:06 : chpv -c hdisk1
2026-01-17 11:00:07 : ipl_varyon -i
2026-01-17 11:00:07 : bootlist -m normal -o
2026-01-17 11:00:08 : bosboot -ad hdisk1
2026-01-17 11:00:08 : Target disk preparation complete
2026-01-17 11:00:08 : Executing: nimadm -j cachevg -s spot_7300_01_00 -l lpp_7300_01_00 -c my-aix-host -d hdisk1 1,2,3,4,5,6,7,8
2026-01-17 11:30:12 : nimadm upgrade completed successfully
2026-01-17 11:30:12 : Upgrade workflow completed successfully
2026-01-17 11:30:12 : Email notification sent: SUCCESS
Key Notes / Best Practices
- Always run in preview mode first (-p) to validate disk space, connectivity, and commands.
- Ensure NIM server has enough cachevg free space before upgrading.
- The script intelligently handles rootvg mirrors and cleans altinst_rootvg.
- Logs are saved in /var/log/aix_upgrade/<hostname>.log and email notifications provide audit info.
- For large rootvg volumes, the script calculates free space using PP sizes, avoiding disk exhaustion.
With this script, upgrading a single AIX host becomes:
- Safe: avoids accidental rootvg damage
- Predictable: preview mode validates before actual upgrade
- Automated: handles mirrors, PV clearing, bootloader, and NIM deployment
- Auditable: detailed logs and email notifications
No comments:
Post a Comment