65 lines
3.1 KiB
Bash
65 lines
3.1 KiB
Bash
BOND=/proc/net/bonding/bond0
|
|
# member_up IF: IF is in bond0 with its link up.
|
|
member_up() { awk -v m="$1" '/^Slave Interface:/ {s = $3} s == m && /^MII Status:/ {print $3; exit}' "$BOND" 2>/dev/null | grep -qx up; }
|
|
# Take the active member's switch end down, ping, and put it back.
|
|
failover() {
|
|
local a rc
|
|
a=$(awk -F': ' '/^Currently Active Slave/ {print $2}' "$BOND")
|
|
[ -n "$a" ] || return 1
|
|
ip -n le-sw link set "${a}s" down
|
|
sleep 1
|
|
ping -c1 -W3 10.96.0.254; rc=$?
|
|
ip -n le-sw link set "${a}s" up
|
|
sleep 1
|
|
return $rc
|
|
}
|
|
if is_rhel; then
|
|
# A saved profile (not one made up for a device set up by hand).
|
|
saved() { nmcli -t -f DEVICE,FILENAME connection show --active | grep -q "^$1:/etc/"; }
|
|
else
|
|
NP=$(mktemp -d)
|
|
trap 'rm -rf "$NP"' EXIT
|
|
mkdir -p "$NP/etc" && cp -a /etc/netplan "$NP/etc/" && netplan generate --root-dir "$NP" >/dev/null 2>&1
|
|
gen() { cat "$NP"/run/systemd/network/*-"$1".$2 2>/dev/null | grep -Eqx "$3"; }
|
|
fi
|
|
in_lan() { ip netns exec le-lan "$@"; }
|
|
|
|
bond_needs() {
|
|
need "bond0 exists" '[ -f "$BOND" ]'
|
|
need "bond0's mode is active-backup" 'grep -q "^Bonding Mode: fault-tolerance (active-backup)" "$BOND"'
|
|
need "bond0 checks its links (miimon)" 'grep -Eq "^MII Polling Interval \(ms\): [1-9]" "$BOND"'
|
|
need "le-b0 and le-b1 are in bond0 and up" 'member_up le-b0 && member_up le-b1'
|
|
need "bond0 has 10.96.0.1/24, set statically" 'ip -4 -o addr show dev bond0 | grep " 10\.96\.0\.1/24 " | grep -vq dynamic'
|
|
need "10.96.0.254 answers through bond0" 'ping -c1 -W2 10.96.0.254'
|
|
need "pings keep working with the active member down" failover
|
|
}
|
|
|
|
task 1 "Active-backup bond0 from le-b0 and le-b1, with NetworkManager" rhel
|
|
bond_needs
|
|
need "bond0 and its members have saved profiles" 'saved bond0 && saved le-b0 && saved le-b1'
|
|
|
|
task 2 "Active-backup bond0 from le-b0 and le-b1, with netplan" debian
|
|
bond_needs
|
|
need "netplan has bond0 in active-backup mode" 'gen bond0 netdev "Kind=bond" && gen bond0 netdev "Mode=active-backup"'
|
|
need "netplan has le-b0 and le-b1 in bond0" 'gen le-b0 network "Bond=bond0" && gen le-b1 network "Bond=bond0"'
|
|
|
|
task 3 "Bridge br0 with le-p0 as its port and 10.95.0.1/24"
|
|
need "le-p0 is a port of br0, forwarding" 'bridge link show dev le-p0 | grep -q "master br0 .*state forwarding"'
|
|
need "br0 has 10.95.0.1/24" 'ip -4 -o addr show dev br0 | grep -q " 10\.95\.0\.1/24 "'
|
|
need "le-p0 has no address of its own" '! ip -4 -o addr show dev le-p0 | grep -q inet'
|
|
need "lan reaches this VM at 10.95.0.1" 'in_lan ping -c1 -W2 10.95.0.1'
|
|
if is_rhel; then
|
|
need "br0 and le-p0 have saved profiles" 'saved br0 && saved le-p0'
|
|
else
|
|
need "netplan has br0 with le-p0 in it" 'gen br0 netdev "Kind=bridge" && gen le-p0 network "Bridge=br0" && gen br0 network "Address=10\.95\.0\.1/24"'
|
|
fi
|
|
|
|
task 4 "The guest on br0, reachable from lan"
|
|
need "le-vnet0 is a port of br0, forwarding" 'bridge link show dev le-vnet0 | grep -q "master br0 .*state forwarding"'
|
|
need "lan reaches the guest at 10.95.0.50" 'in_lan ping -c1 -W2 10.95.0.50'
|
|
if is_rhel; then
|
|
need "le-vnet0 has a saved profile" 'saved le-vnet0'
|
|
else
|
|
need "netplan has le-vnet0 in br0" 'gen le-vnet0 network "Bridge=br0"'
|
|
fi
|