From 00f9c425c811e6f9aeb46e4242cfa1f46f3245e1 Mon Sep 17 00:00:00 2001
From: Mingming Cao <mmc@linux.vnet.ibm.com>
Date: Tue, 15 Feb 2022 23:29:12 -0800
Subject: [PATCH 1/6] Validate connection manager and add option to trace
 hcnmgr

Check and validate what OS is on the system and what type
 of connection manager is used: Wicked or NetworkManager

This patch also add -x option to trace hcnmgr script execution

Last, check platform/service after getopts parsing

Signed-off-by: Mingming Cao <mmc@linux.vnet.ibm.com>
Signed-off-by: Marius Tomaschewski <mt@suse.com>
---
 scripts/hcnmgr | 116 +++++++++++++++++++++++++++++++++++++++----------
 1 file changed, 92 insertions(+), 24 deletions(-)

diff --git a/scripts/hcnmgr b/scripts/hcnmgr
index 870f544..7a11bd9 100644
--- a/scripts/hcnmgr
+++ b/scripts/hcnmgr
@@ -24,12 +24,14 @@
 FEATURES="vnic"
 PATH=$PATH:/bin:/usr/bin:/sbin:/usr/sbin
 BOND_BASEPATH="/sys/class/net"
+BOND_MODPROBE_OPTS="max_bonds=0"
 BONDOPTIONS="mode=1,miimon=100,fail_over_mac=2"
 IFCONFIG_PATH="/etc/sysconfig/network-scripts"
 PSERIES_PLATFORM=$(dirname "$0")/pseries_platform
 DT_PATH="/proc/device-tree"
 HCNMGR="hcnmgr"
 HCNCMD=""
+HCNTRACE=""
 LOG_FILE="/var/log/hcnmgr"
 HCN_LOGGING_LEVEL=DEBUG
 HCNID=0
@@ -39,6 +41,9 @@ MODE=""
 PHYSLOC=""
 DEVPATH=""
 VIO_TYPE=""
+DISTRO=""
+SERVICE=""
+
 
 # Usage statements
 usage() {
@@ -63,6 +68,7 @@ usage() {
 	echo ""
 	echo "Optional arguments."
 	echo "  -s        scan device-tree and configure HCN"
+	echo "  -x        trace hcnmgr script execution"
 	echo "  -V        Display version information and exit"
 	echo "  -h        Display this help information and exit"
 	echo ""
@@ -83,7 +89,7 @@ E_BUSY=16         # Device busy
 E_ENODEV=19       # Failed get device name
 E_NOMODULE=5      # Failed to load bonding module
 E_INVAL_DEV=6     # Vdevice not supported
-E_ENETUNREACH=101 # No network management command nmcli
+E_ENETUNREACH=101 # No supported network service enabled or management command not found
 
 #
 # err
@@ -93,6 +99,7 @@ E_ENETUNREACH=101 # No network management command nmcli
 err() {
 	local e_mesg
 	local eno=$1
+	local msg=$2
 
 	case $eno in
 	"$E_INVAL")
@@ -114,7 +121,7 @@ err() {
 		e_mesg="$HCNCMD:error code $eno, Failed to load bonding module"
 		;;
 	"$E_ENETUNREACH")
-		e_mesg="$HCNCMD:error code $eno, nmcli command not installed"
+		e_mesg="$HCNCMD:error code $eno, ${msg:-No supported network service enabled or management command not found}"
 		;;
 	*)
 		e_mesg="$HCNCMD:error code $eno"
@@ -627,6 +634,61 @@ scanhcn() {
 
 	hcnlog DEBUG "scanhcn: scan for hybrid virtual network finished"
 }
+# function check_network_service
+#	Check what connection manager is used
+#	On SUSE, it's wicked.sevice (SLES) or NetworkManager.service (SLED)
+#	with the network.service alias pointing to the enabled service.
+#
+check_network_service() {
+
+	DISTRO="Unknown"
+	if test -f /etc/os-release; then
+		DISTRO=$(grep -oP '(?<=^ID=).+' /etc/os-release | tr -d '"')
+	fi
+
+	#Validate distro service CLI packages is installed to manage networking
+	case $DISTRO in
+		sles|sled|*suse*)
+			SERVICE=$(systemctl show -P Id network.service 2>/dev/null)
+			case $SERVICE in
+				wicked.service)
+					source /usr/lib/powerpc-utils/functions.suse || \
+					err $E_EPERM "Unable to source SUSE function library"
+
+					if ! wicked --version >/dev/null 2>&1; then
+						err $E_ENETUNREACH "wicked management command not installed"
+					fi
+					# hcn-init.service starts before wicked
+					;;
+				NetworkManager.service)
+					if ! nmcli --version >/dev/null 2>&1; then
+						err $E_ENETUNREACH "nmcli management command not installed"
+					fi
+					# hcn-init.service starts after network manager
+					if ! systemctl is-active -q "$SERVICE" ; then
+						err $E_ENETUNREACH "NetworkManager.service not active"
+					fi
+					;;
+				*)
+					err $E_ENETUNREACH "HNV is only supported on wicked and NetworkManager"
+					;;
+			esac
+			;;
+		*)
+			if ! nmcli --version >/dev/null 2>&1; then
+				err $E_ENETUNREACH "HNV is only supported on NetworkManager"
+			fi
+
+			# Assume it's NetworkManager.service -- at least the cli is available
+			SERVICE=NetworkManager.service
+			if ! systemctl is-active -q "$SERVICE" ; then
+				err $E_ENETUNREACH "NetworkManager.service not active"
+			fi
+			;;
+	esac
+
+	hcnlog INFO " LPAR is running OS $DISTRO with network service ${SERVICE%.service}"
+}
 
 #
 # Main
@@ -642,29 +704,8 @@ echo "=======================$NOW============================"
 HCNCMD=$(basename "$0")
 hcnlog DEBUG "$HCNCMD enter"
 
-#Validate this tool is running on powerpc platform
-. "$PSERIES_PLATFORM"
-if [ "$platform" != "$PLATFORM_PSERIES_LPAR" ]; then
-	hcnlog INFO "HNV is only supported on PowerVM LPAR"
-	hcnlog INFO "$HCNCMD exit"
-	exit 0
-fi
-
-#Validate NMCLI packages is install to manage networking
-if ! nmcli --version >/dev/null 2>&1; then
-	err $E_ENETUNREACH
-fi
-
-#Validate bonding module is loaded
-if ! lsmod | grep -q bonding; then
-	hcnlog DEBUG "HCNMGR: Bonding module not loaded, load module ..."
-	if ! modprobe bonding; then
-		err $E_NOMODULE
-	fi
-fi
-
 #getops for help and version
-while getopts "sVhd:" arg; do
+while getopts "sxVhd:" arg; do
 	case "$arg" in
 	V)
 		show_version
@@ -677,6 +718,9 @@ while getopts "sVhd:" arg; do
 	s)
 		HCNCMD="hcnscan"
 		;;
+	x)
+		HCNTRACE="-x"
+		;;
 	d)
 		hcnlog DEBUG "HMC pass log level at $OPTARG"
 		hcnlog DEBUG "$HCNCMD is always log at $HCN_LOGGING_LEVEL level"
@@ -691,6 +735,30 @@ done
 #Log this scripts command line to syslog
 hcnlog INFO "$HCNCMD $*"
 
+#Enable bash -x or -vx call trace if requested
+if [ "X$HCNTRACE" != "X" ] ; then
+	set "$HCNTRACE"
+fi
+
+#Validate this tool is running on powerpc platform
+. "$PSERIES_PLATFORM"
+if [ "$platform" != "$PLATFORM_PSERIES_LPAR" ]; then
+	hcnlog INFO "HNV is only supported on PowerVM LPAR"
+	hcnlog INFO "$HCNCMD exit"
+	exit 0
+fi
+
+#Init the distribution and the network service
+check_network_service
+
+#Validate bonding module is loaded
+if ! lsmod | grep -q bonding; then
+	hcnlog DEBUG "HCNMGR: Bonding module not loaded, load module ..."
+	if ! modprobe bonding $BOND_MODPROBE_OPTS; then
+		err $E_NOMODULE
+	fi
+fi
+
 #Parse the DRC_INDEX and HCN_ID from the arguments
 for param in "$@"; do
 	if [[ $param =~ ^DRC_INDEX=(.+)$ ]]; then
-- 
2.34.1

