mirror of
https://github.com/versity/scoutfs.git
synced 2026-02-03 09:12:05 +00:00
This adds the fenced scripts so that we have a place to track these and get updates out to users. This latest version of scripts has the checks to validate that power off succeeded and not just assume based on power command return status. Signed-off-by: Ben McClelland <ben.mcclelland@versity.com>
141 lines
3.7 KiB
Bash
141 lines
3.7 KiB
Bash
#!/usr/bin/bash
|
|
# /usr/libexec/scoutfs-fenced/run/ipmi-remote-host
|
|
|
|
# ipmi configuration
|
|
SCOUTFS_IPMI_CONFIG_FILE=${SCOUTFS_IPMI_CONFIG_FILE:-/etc/scoutfs/scoutfs-ipmi.conf}
|
|
SCOUTFS_IPMI_HOSTS_FILE=${SCOUTFS_IPMI_HOSTS_FILE:-/etc/scoutfs/scoutfs-ipmi-hosts.conf}
|
|
|
|
## hosts file format
|
|
## SCOUTFS_HOST_IP IPMI_ADDRESS
|
|
## ex:
|
|
# 192.168.1.1 192.168.10.1
|
|
|
|
# command setup
|
|
IPMI_POWER="/sbin/ipmipower"
|
|
SSH_CMD="ssh -o ConnectTimeout=3 -o BatchMode=yes -o StrictHostKeyChecking=no"
|
|
LOGGER="/bin/logger -p local3.crit -t scoutfs-fenced"
|
|
|
|
$LOGGER "ipmi fence script invoked: IP: $SCOUTFS_FENCED_REQ_IP RID: $SCOUTFS_FENCED_REQ_RID TEST: $IPMITEST"
|
|
|
|
echo_fail() {
|
|
echo "$@" >&2
|
|
$LOGGER "fence failed: $@"
|
|
exit 1
|
|
}
|
|
|
|
echo_log() {
|
|
echo "$@" >&2
|
|
$LOGGER "fence info: $@"
|
|
}
|
|
|
|
echo_test_pass() {
|
|
echo -e "\xE2\x9C\x94 $@"
|
|
}
|
|
|
|
echo_test_fail() {
|
|
echo -e "\xE2\x9D\x8C $@"
|
|
}
|
|
|
|
test -n "$SCOUTFS_IPMI_CONFIG_FILE" || \
|
|
echo_fail "SCOUTFS_IPMI_CONFIG_FILE isn't set"
|
|
test -r "$SCOUTFS_IPMI_CONFIG_FILE" || \
|
|
echo_fail "$SCOUTFS_IPMI_CONFIG_FILE isn't readable file"
|
|
. "$SCOUTFS_IPMI_CONFIG_FILE"
|
|
test -n "$SCOUTFS_IPMI_HOSTS_FILE" || \
|
|
echo_fail "SCOUTFS_IPMI_HOSTS_FILE isn't set"
|
|
test -r "$SCOUTFS_IPMI_HOSTS_FILE" || \
|
|
echo_fail "$SCOUTFS_IPMI_HOSTS_FILE isn't readable file"
|
|
test -x "$IPMI_POWER" || \
|
|
echo_fail "$IPMI_POWER not found, need to install freeimpi?"
|
|
|
|
export ip="$SCOUTFS_FENCED_REQ_IP"
|
|
export rid="$SCOUTFS_FENCED_REQ_RID"
|
|
|
|
getIPMIhost () {
|
|
host=$(awk -v ip="$1" '$1 == ip {print $2}' "$SCOUTFS_IPMI_HOSTS_FILE") || \
|
|
echo_fail "lookup ipmi host failed"
|
|
echo "$host"
|
|
}
|
|
|
|
powerOffHost() {
|
|
# older versions of ipmipower inverted wait-until-off/wait-until-on, so specify both
|
|
$IPMI_POWER $IPMI_OPTS -h "$1" --wait-until-off --wait-until-on --off || \
|
|
echo_fail "ipmi power off $1 failed"
|
|
|
|
ipmioutput=$($IPMI_POWER $IPMI_OPTS -h "$1" --stat) || \
|
|
echo_fail "ipmi power stat $1 failed"
|
|
|
|
if [[ ! "$ipmioutput" =~ off ]]; then
|
|
echo_fail "ipmi stat $1 not off"
|
|
fi
|
|
|
|
$LOGGER "ipmi fence power down $1 success"
|
|
|
|
exit 0
|
|
}
|
|
|
|
if [ -n "$IPMITEST" ]; then
|
|
for i in $(awk '!/^($|[[:space:]]*#)/ {print $1}' "$SCOUTFS_IPMI_HOSTS_FILE"); do
|
|
if ! $SSH_CMD "$i" /bin/true; then
|
|
echo_test_fail "ssh $i"
|
|
else
|
|
echo_test_pass "ssh $i"
|
|
fi
|
|
host=$(getIPMIhost "$i")
|
|
if [ -z "$host" ]; then
|
|
echo_test_fail "ipmi config $i $host"
|
|
else
|
|
if ! $IPMI_POWER $IPMI_OPTS -h "$host" --stat; then
|
|
echo_test_fail "ipmi $i"
|
|
else
|
|
echo_test_pass "ipmi $i"
|
|
fi
|
|
fi
|
|
done
|
|
exit 0
|
|
fi
|
|
|
|
if [ -z "$ip" ]; then
|
|
echo_fail "no IP given for fencing"
|
|
fi
|
|
|
|
host=$(getIPMIhost "$ip")
|
|
if [ -z "$host" ]; then
|
|
echo_fail "no IPMI host found for fence IP"
|
|
fi
|
|
|
|
# first check via ssh if the mount still exists
|
|
# if ssh succeeds, we will only power down the node if mounted
|
|
if ! output=$($SSH_CMD "$ip" "echo BEGIN; LC_ALL=C egrep -m 1 '(^0x*|^$rid$)' /sys/kernel/boot_params/version /sys/fs/scoutfs/f*r*/rid; echo END"); then
|
|
# ssh not working, just power down host
|
|
powerOffHost "$host"
|
|
fi
|
|
|
|
if [[ ! "$output" =~ BEGIN ]]; then
|
|
# ssh failure
|
|
echo_log "no BEGIN"
|
|
powerOffHost "$host"
|
|
fi
|
|
|
|
if [[ ! "$output" =~ \/boot_params\/ ]]; then
|
|
# ssh failure
|
|
echo_log "no boot params"
|
|
powerOffHost "$host"
|
|
fi
|
|
|
|
if [[ ! "$output" =~ END ]]; then
|
|
# ssh failure
|
|
echo_log "no END"
|
|
powerOffHost "$host"
|
|
fi
|
|
|
|
if [[ "$output" =~ "rid:$rid" ]]; then
|
|
# rid still mounted, power down
|
|
echo_log "rid $rid still mounted"
|
|
powerOffHost "$host"
|
|
fi
|
|
|
|
$LOGGER "ipmi fence host $ip/$host success (rid $rid not mounted)"
|
|
exit 0
|
|
|