From 4f5791ebd03eaec1c7da0865a383175b05102712 Mon Sep 17 00:00:00 2001 From: Daniel Baumann Date: Sun, 5 May 2024 19:47:29 +0200 Subject: Adding upstream version 2:4.17.12+dfsg. Signed-off-by: Daniel Baumann --- ctdb/tests/UNIT/eventscripts/stubs/ctdb | 496 +++++++++++++++ ctdb/tests/UNIT/eventscripts/stubs/ctdb-config | 2 + ctdb/tests/UNIT/eventscripts/stubs/ctdb_killtcp | 9 + ctdb/tests/UNIT/eventscripts/stubs/ctdb_lvs | 52 ++ ctdb/tests/UNIT/eventscripts/stubs/ctdb_natgw | 34 ++ ctdb/tests/UNIT/eventscripts/stubs/date | 7 + ctdb/tests/UNIT/eventscripts/stubs/df | 38 ++ ctdb/tests/UNIT/eventscripts/stubs/ethtool | 12 + ctdb/tests/UNIT/eventscripts/stubs/exportfs | 13 + ctdb/tests/UNIT/eventscripts/stubs/gstack | 19 + ctdb/tests/UNIT/eventscripts/stubs/id | 3 + ctdb/tests/UNIT/eventscripts/stubs/ip | 679 +++++++++++++++++++++ ctdb/tests/UNIT/eventscripts/stubs/ip6tables | 5 + ctdb/tests/UNIT/eventscripts/stubs/iptables | 5 + ctdb/tests/UNIT/eventscripts/stubs/ipvsadm | 126 ++++ ctdb/tests/UNIT/eventscripts/stubs/kill | 7 + ctdb/tests/UNIT/eventscripts/stubs/killall | 7 + ctdb/tests/UNIT/eventscripts/stubs/multipath | 36 ++ ctdb/tests/UNIT/eventscripts/stubs/net | 5 + .../tests/UNIT/eventscripts/stubs/nfs-fake-callout | 15 + ctdb/tests/UNIT/eventscripts/stubs/nfsconf | 5 + ctdb/tests/UNIT/eventscripts/stubs/pidof | 16 + ctdb/tests/UNIT/eventscripts/stubs/pkill | 7 + ctdb/tests/UNIT/eventscripts/stubs/ps | 48 ++ ctdb/tests/UNIT/eventscripts/stubs/rm | 6 + ctdb/tests/UNIT/eventscripts/stubs/rpc.lockd | 6 + ctdb/tests/UNIT/eventscripts/stubs/rpc.mountd | 6 + ctdb/tests/UNIT/eventscripts/stubs/rpc.rquotad | 6 + ctdb/tests/UNIT/eventscripts/stubs/rpc.statd | 6 + ctdb/tests/UNIT/eventscripts/stubs/rpcinfo | 73 +++ ctdb/tests/UNIT/eventscripts/stubs/service | 64 ++ ctdb/tests/UNIT/eventscripts/stubs/sleep | 9 + ctdb/tests/UNIT/eventscripts/stubs/smnotify | 38 ++ ctdb/tests/UNIT/eventscripts/stubs/ss | 193 ++++++ ctdb/tests/UNIT/eventscripts/stubs/stat | 71 +++ ctdb/tests/UNIT/eventscripts/stubs/tdb_mutex_check | 10 + ctdb/tests/UNIT/eventscripts/stubs/tdbdump | 9 + ctdb/tests/UNIT/eventscripts/stubs/tdbtool | 33 + ctdb/tests/UNIT/eventscripts/stubs/testparm | 85 +++ ctdb/tests/UNIT/eventscripts/stubs/timeout | 8 + ctdb/tests/UNIT/eventscripts/stubs/wbinfo | 7 + 41 files changed, 2276 insertions(+) create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/ctdb create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/ctdb-config create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/ctdb_killtcp create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/ctdb_lvs create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/ctdb_natgw create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/date create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/df create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/ethtool create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/exportfs create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/gstack create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/id create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/ip create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/ip6tables create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/iptables create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/ipvsadm create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/kill create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/killall create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/multipath create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/net create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/nfs-fake-callout create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/nfsconf create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/pidof create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/pkill create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/ps create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/rm create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/rpc.lockd create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/rpc.mountd create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/rpc.rquotad create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/rpc.statd create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/rpcinfo create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/service create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/sleep create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/smnotify create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/ss create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/stat create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/tdb_mutex_check create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/tdbdump create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/tdbtool create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/testparm create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/timeout create mode 100755 ctdb/tests/UNIT/eventscripts/stubs/wbinfo (limited to 'ctdb/tests/UNIT/eventscripts/stubs') diff --git a/ctdb/tests/UNIT/eventscripts/stubs/ctdb b/ctdb/tests/UNIT/eventscripts/stubs/ctdb new file mode 100755 index 0000000..fc7bd4f --- /dev/null +++ b/ctdb/tests/UNIT/eventscripts/stubs/ctdb @@ -0,0 +1,496 @@ +#!/bin/sh + +prog="ctdb" + +# Print a message and exit. +die () +{ + echo "$1" >&2 ; exit ${2:-1} +} + +not_implemented_exit_code=1 + +usage () +{ + cat >&2 <&2 + exit $not_implemented_exit_code +} + +verbose=false +machine_readable=false +nodespec="" + +args="" + +# Options and command argument can appear in any order, so when +# getopts thinks it is done, process any non-option arguments and go +# around again. +while [ $# -gt 0 ] ; do + while getopts "Xvhn:?" opt ; do + case "$opt" in + X) machine_readable=true ;; + v) verbose=true ;; + n) nodespec="$OPTARG" ;; + \?|*) usage ;; + esac + done + shift $((OPTIND - 1)) + + # Anything left over must be a non-option arg + if [ $# -gt 0 ] ; then + args="${args}${args:+ }${1}" + shift + fi +done + +[ -n "$args" ] || usage +set -- $args + +setup_tickles () +{ + # Make sure tickles file exists. + tickles_file="${CTDB_TEST_TMP_DIR}/fake-ctdb/tickles" + mkdir -p $(dirname "$tickles_file") + touch "$tickles_file" +} + +ctdb_gettickles () +{ + _ip="$1" + _port="$2" + + setup_tickles + + echo "|source ip|port|destination ip|port|" + while read _src _dst ; do + if [ -z "$_ip" -o "$_ip" = "${_dst%:*}" ] ; then + if [ -z "$_port" -o "$_port" = "${_dst##*:}" ] ; then + echo "|${_src%:*}|${_src##*:}|${_dst%:*}|${_dst##*:}|" + fi + fi + done <"$tickles_file" +} + +ctdb_addtickle () +{ + _src="$1" + _dst="$2" + + setup_tickles + + if [ -n "$_dst" ] ; then + echo "${_src} ${_dst}" >>"$tickles_file" + else + cat >>"$tickles_file" + fi +} + +ctdb_deltickle () +{ + _src="$1" + _dst="$2" + + setup_tickles + + if [ -n "$_dst" ] ; then + _t=$(grep -F -v "${_src} $${_dst}" "$tickles_file") + else + _t=$(cat "$tickles_file") + while read _src _dst ; do + _t=$(echo "$_t" | grep -F -v "${_src} ${_dst}") + done + fi + echo "$_t" >"$tickles_file" +} + +parse_nodespec () +{ + if [ "$nodespec" = "all" ] ; then + nodes="$(seq 0 $((FAKE_CTDB_NUMNODES - 1)) )" + elif [ -n "$nodespec" ] ; then + nodes="$(echo $nodespec | sed -e 's@,@ @g')" + else + node=$(ctdb_pnn) + fi +} + +# For testing backward compatibility... +for i in $CTDB_NOT_IMPLEMENTED ; do + if [ "$i" = "$1" ] ; then + not_implemented "$i" + fi +done + +ctdb_pnn () +{ + # Defaults to 0 + echo "${FAKE_CTDB_PNN:-0}" +} + +###################################################################### + +FAKE_CTDB_NODE_STATE="$FAKE_CTDB_STATE/node-state" +FAKE_CTDB_NODES_DISABLED="$FAKE_CTDB_NODE_STATE/0x4" + +###################################################################### + +# NOTE: all nodes share public addresses file + +FAKE_CTDB_IP_LAYOUT="$FAKE_CTDB_STATE/ip-layout" + +ip_reallocate () +{ + touch "$FAKE_CTDB_IP_LAYOUT" + + ( + flock 0 + + _pa="${CTDB_BASE}/public_addresses" + + if [ ! -s "$FAKE_CTDB_IP_LAYOUT" ] ; then + sed -n -e 's@^\([^#][^/]*\)/.*@\1 -1@p' \ + "$_pa" >"$FAKE_CTDB_IP_LAYOUT" + fi + + _t="${FAKE_CTDB_IP_LAYOUT}.new" + + _flags="" + for _i in $(seq 0 $((FAKE_CTDB_NUMNODES - 1)) ) ; do + if ls "$FAKE_CTDB_STATE/node-state/"*"/$_i" >/dev/null 2>&1 ; then + # Have non-zero flags + _this=0 + for _j in "$FAKE_CTDB_STATE/node-state/"*"/$_i" ; do + _tf="${_j%/*}" # dirname + _f="${_tf##*/}" # basename + _this=$(( $_this | $_f )) + done + else + _this="0" + fi + _flags="${_flags}${_flags:+,}${_this}" + done + CTDB_TEST_LOGLEVEL=NOTICE \ + "ctdb_takeover_tests" \ + "ipalloc" "$_flags" <"$FAKE_CTDB_IP_LAYOUT" | + sort >"$_t" + mv "$_t" "$FAKE_CTDB_IP_LAYOUT" + ) <"$FAKE_CTDB_IP_LAYOUT" +} + +ctdb_ip () +{ + # If nobody has done any IP-fu then generate a layout. + [ -f "$FAKE_CTDB_IP_LAYOUT" ] || ip_reallocate + + _mypnn=$(ctdb_pnn) + + if $machine_readable ; then + if $verbose ; then + echo "|Public IP|Node|ActiveInterface|AvailableInterfaces|ConfiguredInterfaces|" + else + echo "|Public IP|Node|" + fi + else + echo "Public IPs on node ${_mypnn}" + fi + + # Join public addresses file with $FAKE_CTDB_IP_LAYOUT, and + # process output line by line... + _pa="${CTDB_BASE}/public_addresses" + sed -e 's@/@ @' "$_pa" | sort | join - "$FAKE_CTDB_IP_LAYOUT" | + while read _ip _bit _ifaces _pnn ; do + if $verbose ; then + # If more than 1 interface, assume all addresses are on the 1st. + _first_iface="${_ifaces%%,*}" + # Only show interface if address is on this node. + _my_iface="" + if [ "$_pnn" = "$_mypnn" ]; then + _my_iface="$_first_iface" + fi + if $machine_readable ; then + echo "|${_ip}|${_pnn}|${_my_iface}|${_first_iface}|${_ifaces}|" + else + echo "${_ip} node[${_pnn}] active[${_my_iface}] available[${_first_iface}] configured[[${_ifaces}]" + fi + else + if $machine_readable ; then + echo "|${_ip}|${_pnn}|" + else + echo "${_ip} ${_pnn}" + fi + fi + done +} + +ctdb_moveip () +{ + _ip="$1" + _target="$2" + + ip_reallocate # should be harmless and ensures we have good state + + ( + flock 0 + + _t="${FAKE_CTDB_IP_LAYOUT}.new" + + while read _i _pnn ; do + if [ "$_ip" = "$_i" ] ; then + echo "$_i $_target" + else + echo "$_i $_pnn" + fi + done | sort >"$_t" + mv "$_t" "$FAKE_CTDB_IP_LAYOUT" + ) <"$FAKE_CTDB_IP_LAYOUT" +} + +###################################################################### + +ctdb_enable () +{ + parse_nodespec + + for _i in $nodes ; do + rm -f "${FAKE_CTDB_NODES_DISABLED}/${_i}" + done + + ip_reallocate +} + +ctdb_disable () +{ + parse_nodespec + + for _i in $nodes ; do + mkdir -p "$FAKE_CTDB_NODES_DISABLED" + touch "${FAKE_CTDB_NODES_DISABLED}/${_i}" + done + + ip_reallocate +} + +###################################################################### + +ctdb_shutdown () +{ + echo "CTDB says BYE!" +} + +###################################################################### + +# This is only used by the NAT and LVS gateway code at the moment, so +# use a hack. Assume that $CTDB_NATGW_NODES or $CTDB_LVS_NODES +# contains all nodes in the cluster (which is what current tests +# assume). Use the PNN to find the address from this file. The NAT +# gateway code only used the address, so just mark the node healthy. +ctdb_nodestatus () +{ + echo '|Node|IP|Disconnected|Banned|Disabled|Unhealthy|Stopped|Inactive|PartiallyOnline|ThisNode|' + _line=$(( $FAKE_CTDB_PNN + 1 )) + _ip=$(sed -e "${_line}p" "${CTDB_NATGW_NODES:-${CTDB_LVS_NODES}}") + echo "|${FAKE_CTDB_PNN}|${_ip}|0|0|0|0|0|0|0|Y|" +} + +###################################################################### + +ctdb_setvar () +{ + _var="$1" + + for _i in $FAKE_CTDB_TUNABLES_OK ; do + if [ "$_var" = "$_i" ] ; then + return 0 + fi + done + + for _i in $FAKE_CTDB_TUNABLES_OBSOLETE ; do + if [ "$_var" = "$_i" ] ; then + echo "Setting obsolete tunable variable '${_var}'" + return 0 + fi + done + + echo "Unable to set tunable variable '${_var}'" + return 1 +} + +###################################################################### + +_t_setup () +{ + _t_dir="${CTDB_TEST_TMP_DIR}/fake-ctdb/fake-tdb/$1" + mkdir -p "$_t_dir" +} + +_t_put () +{ + echo "$2" >"${_t_dir}/$1" +} + +_t_get () +{ + cat "${_t_dir}/$1" +} + +_t_del () +{ + rm -f "${_t_dir}/$1" +} + +ctdb_pstore () +{ + _t_setup "$1" + _t_put "$2" "$3" +} + +ctdb_pdelete () +{ + _t_setup "$1" + _t_del "$2" +} + +ctdb_pfetch () +{ + _t_setup "$1" + _t_get "$2" >"$3" 2>/dev/null +} + +ctdb_ptrans () +{ + _t_setup "$1" + + while IFS="" read _line ; do + _k=$(echo "$_line" | sed -n -e 's@^"\([^"]*\)" "[^"]*"$@\1@p') + _v=$(echo "$_line" | sed -e 's@^"[^"]*" "\([^"]*\)"$@\1@') + [ -n "$_k" ] || die "ctdb ptrans: bad line \"${line}\"" + if [ -n "$_v" ] ; then + _t_put "$_k" "$_v" + else + _t_del "$_k" + fi + done +} + +ctdb_catdb () +{ + _t_setup "$1" + + # This will break on keys with spaces but we don't have any of + # those yet. + _count=0 + for _i in "${_t_dir}/"* ; do + [ -r "$_i" ] || continue + _k="${_i##*/}" # basename + _v=$(_t_get "$_k") + _kn=$(echo -n "$_k" | wc -c) + _vn=$(echo -n "$_v" | wc -c) + cat </dev/null 2>&1 ; then + "$func" "$@" +else + not_implemented "$cmd" +fi diff --git a/ctdb/tests/UNIT/eventscripts/stubs/ctdb-config b/ctdb/tests/UNIT/eventscripts/stubs/ctdb-config new file mode 100755 index 0000000..818e3db --- /dev/null +++ b/ctdb/tests/UNIT/eventscripts/stubs/ctdb-config @@ -0,0 +1,2 @@ +#!/bin/sh +exec $VALGRIND "${CTDB_SCRIPTS_HELPER_BINDIR}/ctdb-config" "$@" diff --git a/ctdb/tests/UNIT/eventscripts/stubs/ctdb_killtcp b/ctdb/tests/UNIT/eventscripts/stubs/ctdb_killtcp new file mode 100755 index 0000000..cb5b6e5 --- /dev/null +++ b/ctdb/tests/UNIT/eventscripts/stubs/ctdb_killtcp @@ -0,0 +1,9 @@ +#!/bin/sh + +# Only supports reading from stdin + +iface="$1" # ignored + +while read src dst ; do + sed -i -e "/^${dst} ${src}\$/d" "$FAKE_NETSTAT_TCP_ESTABLISHED_FILE" +done diff --git a/ctdb/tests/UNIT/eventscripts/stubs/ctdb_lvs b/ctdb/tests/UNIT/eventscripts/stubs/ctdb_lvs new file mode 100755 index 0000000..85e005c --- /dev/null +++ b/ctdb/tests/UNIT/eventscripts/stubs/ctdb_lvs @@ -0,0 +1,52 @@ +#!/bin/sh + +prog="ctdb_lvs" + +# Print a message and exit. +die () +{ + echo "$1" >&2 ; exit ${2:-1} +} + +not_implemented_exit_code=1 + +usage () +{ + cat >&2 <&2 + exit $not_implemented_exit_code +} + +ctdb_lvs_leader () +{ + if [ -n "$FAKE_CTDB_LVS_LEADER" ] ; then + echo "$FAKE_CTDB_LVS_LEADER" + return 0 + else + return 255 + fi +} + +ctdb_lvs_list () +{ + _pnn=0 + while read _ip _opts ; do + echo "${_pnn} ${_ip}" + _pnn=$(($_pnn + 1)) + done <"$CTDB_LVS_NODES" +} + +###################################################################### + +case "$1" in + leader) ctdb_lvs_leader "$@" ;; + list) ctdb_lvs_list "$@" ;; + *) not_implemented "$1" ;; +esac diff --git a/ctdb/tests/UNIT/eventscripts/stubs/ctdb_natgw b/ctdb/tests/UNIT/eventscripts/stubs/ctdb_natgw new file mode 100755 index 0000000..e64a956 --- /dev/null +++ b/ctdb/tests/UNIT/eventscripts/stubs/ctdb_natgw @@ -0,0 +1,34 @@ +#!/bin/sh + +prog="ctdb_natgw" + +not_implemented_exit_code=1 + +not_implemented () +{ + echo "${prog}: command \"$1\" not implemented in stub" >&2 + exit $not_implemented_exit_code +} + +ctdb_natgw_leader () +{ + [ -r "$CTDB_NATGW_NODES" ] || \ + die "error: missing CTDB_NATGW_NODES=${CTDB_NATGW_NODES}" + + # Determine the leader node + _leader="-1 0.0.0.0" + _pnn=0 + while read _ip ; do + if [ "$FAKE_CTDB_NATGW_LEADER" = "$_ip" ] ; then + _leader="${_pnn} ${_ip}" + break + fi + _pnn=$(($_pnn + 1)) + done <"$CTDB_NATGW_NODES" + echo "$_leader" +} + +case "$1" in + leader) ctdb_natgw_leader "$@" ;; + *) not_implemented "$1" ;; +esac diff --git a/ctdb/tests/UNIT/eventscripts/stubs/date b/ctdb/tests/UNIT/eventscripts/stubs/date new file mode 100755 index 0000000..2f470a8 --- /dev/null +++ b/ctdb/tests/UNIT/eventscripts/stubs/date @@ -0,0 +1,7 @@ +#!/bin/sh + +if [ "$FAKE_DATE_OUTPUT" ] ; then + echo "$FAKE_DATE_OUTPUT" +else + /bin/date "$@" +fi diff --git a/ctdb/tests/UNIT/eventscripts/stubs/df b/ctdb/tests/UNIT/eventscripts/stubs/df new file mode 100755 index 0000000..a2e7093 --- /dev/null +++ b/ctdb/tests/UNIT/eventscripts/stubs/df @@ -0,0 +1,38 @@ +#!/bin/sh + +usage () +{ + echo "usage: df [-kP] []" + exit 1 +} + +if [ "$1" = "-kP" ] ; then + shift +fi + +case "$1" in + -*) usage ;; +esac + +fs="${1:-/}" + +# Anything starting with CTDB_DBDIR_BASE gets canonicalised to +# CTDB_DBDIR_BASE. This helps with the setting of defaults for the +# filesystem checks. +if [ "${fs#${CTDB_DBDIR_BASE}}" != "$fs" ] ; then + fs="$CTDB_DBDIR_BASE" +fi + +# A default, for tests that don't initialise this... +if [ -z "$FAKE_FS_USE" ] ; then + FAKE_FS_USE=10 +fi + +echo "Filesystem 1024-blocks Used Available Capacity Mounted on" + +blocks="1000000" +used=$(($blocks * $FAKE_FS_USE / 100)) +available=$(($blocks - $used)) + +printf "%-36s %10d %10d %10d %10d%% %s\n" \ + "/dev/sda1" "$blocks" "$used" "$available" "$FAKE_FS_USE" "$fs" diff --git a/ctdb/tests/UNIT/eventscripts/stubs/ethtool b/ctdb/tests/UNIT/eventscripts/stubs/ethtool new file mode 100755 index 0000000..bd173f4 --- /dev/null +++ b/ctdb/tests/UNIT/eventscripts/stubs/ethtool @@ -0,0 +1,12 @@ +#!/bin/sh + +link="yes" + +if [ -f "${FAKE_ETHTOOL_LINK_DOWN}/${1}" ] ; then + link="no" +fi + +# Expect to add more fields later. +cat <, argv=) at ${command}.c +EOF diff --git a/ctdb/tests/UNIT/eventscripts/stubs/id b/ctdb/tests/UNIT/eventscripts/stubs/id new file mode 100755 index 0000000..1ecd2f8 --- /dev/null +++ b/ctdb/tests/UNIT/eventscripts/stubs/id @@ -0,0 +1,3 @@ +#!/bin/sh +# Make statd-callout happy +echo 0 diff --git a/ctdb/tests/UNIT/eventscripts/stubs/ip b/ctdb/tests/UNIT/eventscripts/stubs/ip new file mode 100755 index 0000000..630d0e8 --- /dev/null +++ b/ctdb/tests/UNIT/eventscripts/stubs/ip @@ -0,0 +1,679 @@ +#!/bin/sh + +FAKE_IP_STATE="${FAKE_NETWORK_STATE}/ip-state" +mkdir -p "$FAKE_IP_STATE" + +promote_secondaries=true + +not_implemented () +{ + echo "ip stub command: \"$1\" not implemented" + exit 127 +} + +###################################################################### + +ip_link () +{ + case "$1" in + set) + shift + # iface="$1" + case "$2" in + up) ip_link_set_up "$1" ;; + down) ip_link_down_up "$1" ;; + *) not_implemented "\"$2\" in \"$orig_args\"" ;; + esac + ;; + show) shift ; ip_link_show "$@" ;; + add*) shift ; ip_link_add "$@" ;; + del*) shift ; ip_link_delete "$@" ;; + *) not_implemented "$*" ;; + esac +} + +ip_link_add () +{ + _link="" + _name="" + _type="" + + while [ -n "$1" ] ; do + case "$1" in + link) + _link="$2" + shift 2 + ;; + name) + _name="$2" + shift 2 + ;; + type) + if [ "$2" != "vlan" ] ; then + not_implemented "link type $1" + fi + _type="$2" + shift 2 + ;; + id) shift 2 ;; + *) not_implemented "$1" ;; + esac + done + + case "$_type" in + vlan) + if [ -z "$_name" -o -z "$_link" ] ; then + not_implemented "ip link add with null name or link" + fi + + mkdir -p "${FAKE_IP_STATE}/interfaces-vlan" + echo "$_link" >"${FAKE_IP_STATE}/interfaces-vlan/${_name}" + ip_link_set_down "$_name" + ;; + esac +} + +ip_link_delete () +{ + mkdir -p "${FAKE_IP_STATE}/interfaces-deleted" + touch "${FAKE_IP_STATE}/interfaces-deleted/$1" + rm -f "${FAKE_IP_STATE}/interfaces-vlan/$1" +} + +ip_link_set_up () +{ + rm -f "${FAKE_IP_STATE}/interfaces-down/$1" + rm -f "${FAKE_IP_STATE}/interfaces-deleted/$1" +} + +ip_link_set_down () +{ + rm -f "${FAKE_IP_STATE}/interfaces-deleted/$1" + mkdir -p "${FAKE_IP_STATE}/interfaces-down" + touch "${FAKE_IP_STATE}/interfaces-down/$1" +} + +ip_link_show () +{ + dev="$1" + if [ "$dev" = "dev" -a -n "$2" ] ; then + dev="$2" + fi + + if [ -e "${FAKE_IP_STATE}/interfaces-deleted/$dev" ] ; then + echo "Device \"${dev}\" does not exist." >&2 + exit 255 + fi + + if [ -r "${FAKE_IP_STATE}/interfaces-vlan/${dev}" ] ; then + read _link <"${FAKE_IP_STATE}/interfaces-vlan/${dev}" + dev="${dev}@${_link}" + fi + + _state="UP" + _flags=",UP,LOWER_UP" + if [ -e "${FAKE_IP_STATE}/interfaces-down/$dev" ] ; then + _state="DOWN" + _flags="" + fi + case "$dev" in + lo) + _mac="00:00:00:00:00:00" + _brd="00:00:00:00:00:00" + _type="loopback" + _opts=" mtu 65536 qdisc noqueue state UNKNOWN" + ;; + *) + _mac=$(echo $dev | cksum | sed -r -e 's@(..)(..)(..).*@fe:fe:fe:\1:\2:\3@') + _brd="ff:ff:ff:ff:ff:ff" + _type="ether" + _opts=" mtu 1500 qdisc pfifo_fast state ${_state} qlen 1000" + esac + echo "${n:-42}: ${dev}: ${_opts}" + echo " link/${_type} ${_mac} brd ${_brd}" +} + +# This is incomplete because it doesn't actually look up table ids in +# /etc/iproute2/rt_tables. The rules/routes are actually associated +# with the name instead of the number. However, we include a variable +# to fake a bad table id. +[ -n "$IP_ROUTE_BAD_TABLE_ID" ] || IP_ROUTE_BAD_TABLE_ID=false + +ip_check_table () +{ + _cmd="$1" + + if [ "$_cmd" = "route" -a -z "$_table" ] ;then + _table="main" + fi + + [ -n "$_table" ] || not_implemented "ip rule/route without \"table\"" + + # Only allow tables names from 13.per_ip_routing and "main". This + # is a cheap way of avoiding implementing the default/local + # tables. + case "$_table" in + ctdb.*|main) + if $IP_ROUTE_BAD_TABLE_ID ; then + # Ouch. Simulate inconsistent errors from ip. :-( + case "$_cmd" in + route) + echo "Error: argument "${_table}" is wrong: table id value is invalid" >&2 + + ;; + *) + echo "Error: argument "${_table}" is wrong: invalid table ID" >&2 + esac + exit 255 + fi + ;; + *) not_implemented "table=${_table} ${orig_args}" ;; + esac +} + +###################################################################### + +ip_addr () +{ + case "$1" in + show|list|"") shift ; ip_addr_show "$@" ;; + add*) shift ; ip_addr_add "$@" ;; + del*) shift ; ip_addr_del "$@" ;; + *) not_implemented "\"$1\" in \"$orig_args\"" ;; + esac +} + +ip_addr_show () +{ + dev="" + primary=true + secondary=true + _to="" + while [ -n "$1" ] ; do + case "$1" in + dev) + dev="$2" ; shift 2 + ;; + # Do stupid things and stupid things will happen! + primary) + primary=true ; secondary=false ; shift + ;; + secondary) + secondary=true ; primary=false ; shift + ;; + to) + _to="$2" ; shift 2 + ;; + *) + # Assume an interface name + dev="$1" ; shift 1 + esac + done + devices="$dev" + if [ -z "$devices" ] ; then + # No device specified? Get all the primaries... + devices=$(ls "${FAKE_IP_STATE}/addresses/"*-primary 2>/dev/null | \ + sed -e 's@.*/@@' -e 's@-.*-primary$@@' | sort -u) + fi + calc_brd () + { + case "${local#*/}" in + 24) brd="${local%.*}.255" ;; + 32) brd="" ;; + *) not_implemented "list ... fake bits other than 24/32: ${local#*/}" + esac + } + show_iface() + { + ip_link_show "$dev" + + nets=$(ls "${FAKE_IP_STATE}/addresses/${dev}"-*-primary 2>/dev/null | \ + sed -e 's@.*/@@' -e "s@${dev}-\(.*\)-primary\$@\1@") + + for net in $nets ; do + pf="${FAKE_IP_STATE}/addresses/${dev}-${net}-primary" + sf="${FAKE_IP_STATE}/addresses/${dev}-${net}-secondary" + if $primary && [ -r "$pf" ] ; then + read local scope <"$pf" + if [ -z "$_to" -o "${_to%/*}" = "${local%/*}" ] ; then + calc_brd + echo " inet ${local} ${brd:+brd ${brd} }scope ${scope} ${dev}" + fi + fi + if $secondary && [ -r "$sf" ] ; then + while read local scope ; do + if [ -z "$_to" -o "${_to%/*}" = "${local%/*}" ] ; then + calc_brd + echo " inet ${local} ${brd:+brd }${brd} scope ${scope} secondary ${dev}" + fi + done <"$sf" + fi + if [ -z "$_to" ] ; then + echo " valid_lft forever preferred_lft forever" + fi + done + } + n=1 + for dev in $devices ; do + if [ -z "$_to" ] || \ + grep -F "${_to%/*}/" "${FAKE_IP_STATE}/addresses/${dev}-"* >/dev/null ; then + show_iface + fi + n=$(($n + 1)) + done +} + +# Copied from 13.per_ip_routing for now... so this is lazy testing :-( +ipv4_host_addr_to_net () +{ + _host="$1" + _maskbits="$2" + + # Convert the host address to an unsigned long by splitting out + # the octets and doing the math. + _host_ul=0 + for _o in $(export IFS="." ; echo $_host) ; do + _host_ul=$(( ($_host_ul << 8) + $_o)) # work around Emacs color bug + done + + # Calculate the mask and apply it. + _mask_ul=$(( 0xffffffff << (32 - $_maskbits) )) + _net_ul=$(( $_host_ul & $_mask_ul )) + + # Now convert to a network address one byte at a time. + _net="" + for _o in $(seq 1 4) ; do + _net="$(($_net_ul & 255))${_net:+.}${_net}" + _net_ul=$(($_net_ul >> 8)) + done + + echo "${_net}/${_maskbits}" +} + +ip_addr_add () +{ + local="" + dev="" + brd="" + scope="global" + while [ -n "$1" ] ; do + case "$1" in + *.*.*.*/*) + local="$1" ; shift + ;; + local) + local="$2" ; shift 2 + ;; + broadcast|brd) + # For now assume this is always '+'. + if [ "$2" != "+" ] ; then + not_implemented "addr add ... brd $2 ..." + fi + shift 2 + ;; + dev) + dev="$2" ; shift 2 + ;; + scope) + scope="$2" ; shift 2 + ;; + *) + not_implemented "$@" + esac + done + if [ -z "$dev" ] ; then + not_implemented "addr add (without dev)" + fi + mkdir -p "${FAKE_IP_STATE}/addresses" + net_str=$(ipv4_host_addr_to_net $(IFS="/" ; echo $local)) + net_str=$(echo "$net_str" | sed -e 's@/@_@') + pf="${FAKE_IP_STATE}/addresses/${dev}-${net_str}-primary" + sf="${FAKE_IP_STATE}/addresses/${dev}-${net_str}-secondary" + # We could lock here... but we should be the only ones playing + # around here with these stubs. + if [ ! -f "$pf" ] ; then + echo "$local $scope" >"$pf" + elif grep -Fq "$local" "$pf" ; then + echo "RTNETLINK answers: File exists" >&2 + exit 254 + elif [ -f "$sf" ] && grep -Fq "$local" "$sf" ; then + echo "RTNETLINK answers: File exists" >&2 + exit 254 + else + echo "$local $scope" >>"$sf" + fi +} + +ip_addr_del () +{ + local="" + dev="" + while [ -n "$1" ] ; do + case "$1" in + *.*.*.*/*) + local="$1" ; shift + ;; + local) + local="$2" ; shift 2 + ;; + dev) + dev="$2" ; shift 2 + ;; + *) + not_implemented "addr del ... $1 ..." + esac + done + if [ -z "$dev" ] ; then + not_implemented "addr del (without dev)" + fi + mkdir -p "${FAKE_IP_STATE}/addresses" + net_str=$(ipv4_host_addr_to_net $(IFS="/" ; echo $local)) + net_str=$(echo "$net_str" | sed -e 's@/@_@') + pf="${FAKE_IP_STATE}/addresses/${dev}-${net_str}-primary" + sf="${FAKE_IP_STATE}/addresses/${dev}-${net_str}-secondary" + # We could lock here... but we should be the only ones playing + # around here with these stubs. + if [ ! -f "$pf" ] ; then + echo "RTNETLINK answers: Cannot assign requested address" >&2 + exit 254 + elif grep -Fq "$local" "$pf" ; then + if $promote_secondaries && [ -s "$sf" ] ; then + head -n 1 "$sf" >"$pf" + sed -i -e '1d' "$sf" + else + # Remove primaries AND SECONDARIES. + rm -f "$pf" "$sf" + fi + elif [ -f "$sf" ] && grep -Fq "$local" "$sf" ; then + grep -Fv "$local" "$sf" >"${sf}.new" + mv "${sf}.new" "$sf" + else + echo "RTNETLINK answers: Cannot assign requested address" >&2 + exit 254 + fi +} + +###################################################################### + +ip_rule () +{ + case "$1" in + show|list|"") shift ; ip_rule_show "$@" ;; + add) shift ; ip_rule_add "$@" ;; + del*) shift ; ip_rule_del "$@" ;; + *) not_implemented "$1 in \"$orig_args\"" ;; + esac + +} + +# All non-default rules are in $FAKE_IP_STATE_RULES/rules. As with +# the real version, rules can be repeated. Deleting just deletes the +# 1st match. + +ip_rule_show () +{ + ip_rule_show_1 () + { + _pre="$1" + _table="$2" + _selectors="$3" + # potentially more options + + printf "%d:\t%s lookup %s \n" $_pre "$_selectors" "$_table" + } + + ip_rule_show_some () + { + _min="$1" + _max="$2" + + [ -f "${FAKE_IP_STATE}/rules" ] || return + + while read _pre _table _selectors ; do + # Only print those in range + [ $_min -le $_pre -a $_pre -le $_max ] || continue + + ip_rule_show_1 $_pre "$_table" "$_selectors" + done <"${FAKE_IP_STATE}/rules" + } + + ip_rule_show_1 0 "local" "from all" + + ip_rule_show_some 1 32765 + + ip_rule_show_1 32766 "main" "from all" + ip_rule_show_1 32767 "default" "from all" + + ip_rule_show_some 32768 2147483648 +} + +ip_rule_common () +{ + _from="" + _pre="" + _table="" + while [ -n "$1" ] ; do + case "$1" in + from) _from="$2" ; shift 2 ;; + pref) _pre="$2" ; shift 2 ;; + table) _table="$2" ; shift 2 ;; + *) not_implemented "$1 in \"$orig_args\"" ;; + esac + done + + [ -n "$_pre" ] || not_implemented "ip rule without \"pref\"" + ip_check_table "rule" + # Relax this if more selectors added later... + [ -n "$_from" ] || not_implemented "ip rule without \"from\"" +} + +ip_rule_add () +{ + ip_rule_common "$@" + + _f="${FAKE_IP_STATE}/rules" + touch "$_f" + ( + flock 0 + # Filter order must be consistent with the comparison in ip_rule_del() + echo "$_pre $_table${_from:+ from }$_from" >>"$_f" + ) <"$_f" +} + +ip_rule_del () +{ + ip_rule_common "$@" + + _f="${FAKE_IP_STATE}/rules" + touch "$_f" + ( + flock 0 + _tmp="${_f}.new" + : >"$_tmp" + _found=false + while read _p _t _s ; do + if ! $_found && \ + [ "$_p" = "$_pre" -a "$_t" = "$_table" -a \ + "$_s" = "${_from:+from }$_from" ] ; then + # Found. Skip this one but not future ones. + _found=true + else + echo "$_p $_t $_s" >>"$_tmp" + fi + done + if cmp -s "$_tmp" "$_f" ; then + # No changes, must not have found what we wanted to delete + echo "RTNETLINK answers: No such file or directory" >&2 + rm -f "$_tmp" + exit 2 + else + mv "$_tmp" "$_f" + fi + ) <"$_f" || exit $? +} + +###################################################################### + +ip_route () +{ + case "$1" in + show|list) shift ; ip_route_show "$@" ;; + flush) shift ; ip_route_flush "$@" ;; + add) shift ; ip_route_add "$@" ;; + del*) shift ; ip_route_del "$@" ;; + *) not_implemented "$1 in \"ip route\"" ;; + esac +} + +ip_route_common () +{ + if [ "$1" = table ] ; then + _table="$2" + shift 2 + fi + + ip_check_table "route" +} + +# Routes are in a file per table in the directory +# $FAKE_IP_STATE/routes. These routes just use the table ID +# that is passed and don't do any lookup. This could be "improved" if +# necessary. + +ip_route_show () +{ + ip_route_common "$@" + + # Missing file is just an empty table + sort "$FAKE_IP_STATE/routes/${_table}" 2>/dev/null || true +} + +ip_route_flush () +{ + ip_route_common "$@" + + rm -f "$FAKE_IP_STATE/routes/${_table}" +} + +ip_route_add () +{ + _prefix="" + _dev="" + _gw="" + _table="" + _metric="" + + while [ -n "$1" ] ; do + case "$1" in + *.*.*.*/*|*.*.*.*) _prefix="$1" ; shift 1 ;; + local) _prefix="$2" ; shift 2 ;; + dev) _dev="$2" ; shift 2 ;; + via) _gw="$2" ; shift 2 ;; + table) _table="$2" ; shift 2 ;; + metric) _metric="$2" ; shift 2 ;; + *) not_implemented "$1 in \"$orig_args\"" ;; + esac + done + + ip_check_table "route" + [ -n "$_prefix" ] || not_implemented "ip route without inet prefix in \"$orig_args\"" + # This can't be easily deduced, so print some garbage. + [ -n "$_dev" ] || _dev="ethXXX" + + # Alias or add missing bits + case "$_prefix" in + 0.0.0.0/0) _prefix="default" ;; + */*) : ;; + *) _prefix="${_prefix}/32" ;; + esac + + _f="$FAKE_IP_STATE/routes/${_table}" + mkdir -p "$FAKE_IP_STATE/routes" + touch "$_f" + + # Check for duplicate + _prefix_regexp=$(echo "^${_prefix}" | sed -e 's@\.@\\.@g') + if [ -n "$_metric" ] ; then + _prefix_regexp="${_prefix_regexp} .*metric ${_metric} " + fi + if grep -q "$_prefix_regexp" "$_f" ; then + echo "RTNETLINK answers: File exists" >&2 + exit 1 + fi + + ( + flock 0 + + _out="${_prefix} " + [ -z "$_gw" ] || _out="${_out}via ${_gw} " + [ -z "$_dev" ] || _out="${_out}dev ${_dev} " + [ -n "$_gw" ] || _out="${_out} scope link " + [ -z "$_metric" ] || _out="${_out} metric ${_metric} " + echo "$_out" >>"$_f" + ) <"$_f" +} + +ip_route_del () +{ + _prefix="" + _dev="" + _gw="" + _table="" + _metric="" + + while [ -n "$1" ] ; do + case "$1" in + *.*.*.*/*|*.*.*.*) _prefix="$1" ; shift 1 ;; + local) _prefix="$2" ; shift 2 ;; + dev) _dev="$2" ; shift 2 ;; + via) _gw="$2" ; shift 2 ;; + table) _table="$2" ; shift 2 ;; + metric) _metric="$2" ; shift 2 ;; + *) not_implemented "$1 in \"$orig_args\"" ;; + esac + done + + ip_check_table "route" + [ -n "$_prefix" ] || not_implemented "ip route without inet prefix in \"$orig_args\"" + # This can't be easily deduced, so print some garbage. + [ -n "$_dev" ] || _dev="ethXXX" + + # Alias or add missing bits + case "$_prefix" in + 0.0.0.0/0) _prefix="default" ;; + */*) : ;; + *) _prefix="${_prefix}/32" ;; + esac + + _f="$FAKE_IP_STATE/routes/${_table}" + mkdir -p "$FAKE_IP_STATE/routes" + touch "$_f" + + ( + flock 0 + + # Escape some dots + [ -z "$_gw" ] || _gw=$(echo "$_gw" | sed -e 's@\.@\\.@g') + _prefix=$(echo "$_prefix" | sed -e 's@\.@\\.@g' -e 's@/@\\/@') + + _re="^${_prefix}\>.*" + [ -z "$_gw" ] || _re="${_re}\.*" + [ -z "$_dev" ] || _re="${_re}\.*" + [ -z "$_metric" ] || _re="${_re}.*\.*" + sed -i -e "/${_re}/d" "$_f" + ) <"$_f" +} + +###################################################################### + +orig_args="$*" + +case "$1" in + link) shift ; ip_link "$@" ;; + addr*) shift ; ip_addr "$@" ;; + rule) shift ; ip_rule "$@" ;; + route) shift ; ip_route "$@" ;; + *) not_implemented "$1" ;; +esac + +exit 0 diff --git a/ctdb/tests/UNIT/eventscripts/stubs/ip6tables b/ctdb/tests/UNIT/eventscripts/stubs/ip6tables new file mode 100755 index 0000000..2c65f7b --- /dev/null +++ b/ctdb/tests/UNIT/eventscripts/stubs/ip6tables @@ -0,0 +1,5 @@ +#!/bin/sh + +# Always succeed. + +exit 0 diff --git a/ctdb/tests/UNIT/eventscripts/stubs/iptables b/ctdb/tests/UNIT/eventscripts/stubs/iptables new file mode 100755 index 0000000..2c65f7b --- /dev/null +++ b/ctdb/tests/UNIT/eventscripts/stubs/iptables @@ -0,0 +1,5 @@ +#!/bin/sh + +# Always succeed. + +exit 0 diff --git a/ctdb/tests/UNIT/eventscripts/stubs/ipvsadm b/ctdb/tests/UNIT/eventscripts/stubs/ipvsadm new file mode 100755 index 0000000..0567f88 --- /dev/null +++ b/ctdb/tests/UNIT/eventscripts/stubs/ipvsadm @@ -0,0 +1,126 @@ +#!/bin/sh + +die () +{ + echo "$1" >&2 + exit ${2:-1} +} + + +[ -n "$FAKE_LVS_STATE_DIR" ] || die "FAKE_LVS_STATE_DIR not set" + + +service_address="" +scheduling_method="wlc" +persistent_timeout="" +real_server="" +forwarding_method="Route" + +set_service_address () +{ + [ -z "$service_address" ] || + die "multiple 'service-address' options specified" 2 + case "$2" in + *:*) service_address="${1} ${2}" ;; + *) service_address="${1} ${2}:0" ;; + esac +} + +set_real_server () +{ + [ -z "$real_server" ] || + die "multiple 'real-server' options specified" 2 + case "$1" in + *\]:*) real_server="${1}" ;; + *\]) real_server="${1}:0" ;; + *:*) real_server="${1}" ;; + *) real_server="${1}:0" ;; + esac + + case "$real_server" in + 127.0.0.1:*|\[::1\]:*) forwarding_method="Local" ;; + esac +} + +case "$1" in +-A) + shift + while [ -n "$1" ] ; do + case "$1" in + -t) set_service_address "TCP" "$2" ; shift 2 ;; + -u) set_service_address "UDP" "$2" ; shift 2 ;; + -s) scheduling_method="$2" ; shift 2 ;; + -p) persistent_timeout="persistent $2" ; shift 2 ;; + *) die "Unsupported -A option $1" ;; + esac + done + [ -n "$service_address" ] || + die "You need to supply the 'service-address' option for the 'add-service' command" 2 + d="${FAKE_LVS_STATE_DIR}/${service_address}" + mkdir "$d" 2>/dev/null || die "Service already exists" 255 + t="${scheduling_method}${persistent_timeout:+ }${persistent_timeout}" + echo "$t" >"${d}/.info" + ;; +-D) + shift + while [ -n "$1" ] ; do + case "$1" in + -t) set_service_address "TCP" "$2" ; shift 2 ;; + -u) set_service_address "UDP" "$2" ; shift 2 ;; + *) die "Unsupported -D option $1" ;; + esac + done + [ -n "$service_address" ] || + die "You need to supply the 'service-address' option for the 'delete-service' command" 2 + d="${FAKE_LVS_STATE_DIR}/${service_address}" + rm -f "${d}/"* + rm -f "${d}/.info" + rmdir "$d" 2>/dev/null || die "No such service" 255 + ;; +-a) + shift + while [ -n "$1" ] ; do + case "$1" in + -t) set_service_address "TCP" "$2" ; shift 2 ;; + -u) set_service_address "UDP" "$2" ; shift 2 ;; + -r) set_real_server "$2" ; shift 2 ;; + -g) forwarding_method="Route" ; shift 1 ;; + *) die "Unsupported -A option $1" ;; + esac + done + [ -n "$service_address" ] || + die "You need to supply the 'service-address' option for the 'delete-service' command" 2 + d="${FAKE_LVS_STATE_DIR}/${service_address}" + [ -d "$d" ] || die "Service not defined" 255 + [ -n "$real_server" ] || + die "You need to supply the 'real-server' option for the 'add-server' command" 2 + f="${d}/${real_server}" + echo "$forwarding_method" >"$f" + ;; +-l) + cat < RemoteAddress:Port Forward Weight ActiveConn InActConn +EOF + [ -d "$FAKE_LVS_STATE_DIR" ] || exit 0 + ( + cd "$FAKE_LVS_STATE_DIR" + for d in *; do + [ -d "$d" ] || continue + echo -n "$d " + cat "${d}/.info" + for f in "${d}/"* ; do + [ -f "$f" ] || continue + read forwarding_method <"$f" + printf " -> %-28s %-7s %-6s %-10s %-10s\n" \ + "${f##*/}" "$forwarding_method" 1 0 0 + done + done + ) + ;; +*) + die "Unknown option $1" +esac + +exit 0 diff --git a/ctdb/tests/UNIT/eventscripts/stubs/kill b/ctdb/tests/UNIT/eventscripts/stubs/kill new file mode 100755 index 0000000..b69e3e6 --- /dev/null +++ b/ctdb/tests/UNIT/eventscripts/stubs/kill @@ -0,0 +1,7 @@ +#!/bin/sh + +# Always succeed. This means that kill -0 will always find a +# process and anything else will successfully kill. This should +# exercise a good avriety of code paths. + +exit 0 diff --git a/ctdb/tests/UNIT/eventscripts/stubs/killall b/ctdb/tests/UNIT/eventscripts/stubs/killall new file mode 100755 index 0000000..1e182e1 --- /dev/null +++ b/ctdb/tests/UNIT/eventscripts/stubs/killall @@ -0,0 +1,7 @@ +#!/bin/sh + +# Always succeed. This means that killall -0 will always find a +# process and anything else will successfully kill. This should +# exercise a good avriety of code paths. + +exit 0 diff --git a/ctdb/tests/UNIT/eventscripts/stubs/multipath b/ctdb/tests/UNIT/eventscripts/stubs/multipath new file mode 100755 index 0000000..64f95e7 --- /dev/null +++ b/ctdb/tests/UNIT/eventscripts/stubs/multipath @@ -0,0 +1,36 @@ +#!/bin/sh + +usage () +{ + die "usage: ${0} -ll device" +} + +[ "$1" = "-ll" ] || usage +shift +[ $# -eq 1 ] || usage + +device="$1" + +if [ -n "$FAKE_MULTIPATH_HANG" ] ; then + FAKE_SLEEP_REALLY="yes" sleep 999 +fi + +path1_state="active" +path2_state="enabled" + +for i in $FAKE_MULTIPATH_FAILURES ; do + if [ "$device" = "$i" ] ; then + path1_state="inactive" + path2_state="inactive" + break + fi +done + + cat <&2 <&2 + echo "program ${p} version ${v} is not available" + exit 1 + fi + else + for j in $(seq $2 $3) ; do + echo "program ${p} version ${j} ready and waiting" + done + exit 0 + fi + fi +done + +echo "rpcinfo: RPC: Program not registered" >&2 +if [ -n "$v" ] ; then + echo "program ${p} version ${v} is not available" +else + echo "program ${p} is not available" +fi + +exit 1 diff --git a/ctdb/tests/UNIT/eventscripts/stubs/service b/ctdb/tests/UNIT/eventscripts/stubs/service new file mode 100755 index 0000000..3d6ddf4 --- /dev/null +++ b/ctdb/tests/UNIT/eventscripts/stubs/service @@ -0,0 +1,64 @@ +#!/bin/sh + +service_status_dir="${CTDB_TEST_TMP_DIR}/service_fake_status" +mkdir -p "$service_status_dir" + +service="$1" +flag="${service_status_dir}/${service}" + +start() +{ + if [ -f "$flag" ] ; then + echo "service: can't start ${service} - already running" + exit 1 + else + touch "$flag" + echo "Starting ${service}: OK" + fi +} + +stop () +{ + if [ -f "$flag" ] ; then + echo "Stopping ${service}: OK" + rm -f "$flag" + else + echo "service: can't stop ${service} - not running" + exit 1 + fi +} + +case "$2" in + start) + start + ;; + stop) + stop + ;; + restart|reload) + stop + start + ;; + status) + if [ -f "$flag" ] ; then + echo "$service running" + exit 0 + else + echo "$service not running" + exit 3 + fi + ;; + force-started) + # For test setup... + touch "$flag" + ;; + force-stopped) + # For test setup... + rm -f "$flag" + ;; + *) + echo "service $service $2 not supported" + exit 1 +esac + +exit 0 diff --git a/ctdb/tests/UNIT/eventscripts/stubs/sleep b/ctdb/tests/UNIT/eventscripts/stubs/sleep new file mode 100755 index 0000000..e454244 --- /dev/null +++ b/ctdb/tests/UNIT/eventscripts/stubs/sleep @@ -0,0 +1,9 @@ +#!/bin/sh + +if [ "$FAKE_SLEEP_REALLY" = "yes" ] ; then + /bin/sleep "$@" +elif [ -n "$FAKE_SLEEP_FORCE" ] ; then + /bin/sleep "$FAKE_SLEEP_FORCE" +else + : +fi diff --git a/ctdb/tests/UNIT/eventscripts/stubs/smnotify b/ctdb/tests/UNIT/eventscripts/stubs/smnotify new file mode 100755 index 0000000..7871034 --- /dev/null +++ b/ctdb/tests/UNIT/eventscripts/stubs/smnotify @@ -0,0 +1,38 @@ +#!/bin/sh + +usage() +{ + _prog="${0##*/}" # basename + cat < ${cip}, MON_NAME=${mon_name}, STATE=${state}" diff --git a/ctdb/tests/UNIT/eventscripts/stubs/ss b/ctdb/tests/UNIT/eventscripts/stubs/ss new file mode 100755 index 0000000..54ff436 --- /dev/null +++ b/ctdb/tests/UNIT/eventscripts/stubs/ss @@ -0,0 +1,193 @@ +#!/bin/sh + +prog="ss" + +usage () +{ + cat >&2 <&2 + usage +} + +############################################################ + +# +parse_filter () +{ + # Very limited implementation: + # We only expect to find || inside parentheses + # We don't expect to see && - it is implied by juxtaposition + # Operator for port comparison is ignored and assumed to be == + + # Build lists of source ports and source IP addresses where + # each entry is surrounded by '|' characters. These lists can + # be easily "searched" using the POSIX prefix and suffix + # removal operators. + in_parens=false + sports="|" + srcs="|" + + while [ -n "$1" ] ; do + case "$1" in + \() + in_parens=true + shift + ;; + \)) + in_parens=false + shift + ;; + \|\|) + if ! $in_parens ; then + not_supported "|| in parentheses" + fi + shift + ;; + sport) + p="${3#:}" ; sports="${sports}${p}|" + shift 3 + ;; + src) + ip="${2#\[}" ; ip="${ip%\]}" ; srcs="${srcs}${ip}|" + shift 2 + ;; + *) + usage + ;; + esac + done +} + +# Check if socket has matches in both ok_ips and ok_ports +filter_socket () +{ + ok_ips="$1" + ok_ports="$2" + socket="$3" + + ip="${socket%:*}" + port="${socket##*:}" + + if [ "$ok_ports" != "|" -a "${ok_ports#*|${port}|}" = "$ok_ports" ] ; then + return 1 + fi + if [ "$ok_ips" != "|" -a "${ok_ips#*|${ip}|}" = "$ok_ips" ] ; then + return 1 + fi + + return 0 +} + +ss_tcp_established () +{ + if $header ; then + echo "Recv-Q Send-Q Local Address:Port Peer Address:Port" + fi + + parse_filter $* + + for i in $FAKE_NETSTAT_TCP_ESTABLISHED ; do + src="${i%|*}" + dst="${i#*|}" + if filter_socket "$srcs" "$sports" "$src" ; then + echo 0 0 "$src" "$dst" + fi + done + + if [ -z "$FAKE_NETSTAT_TCP_ESTABLISHED_FILE" ] ; then + return + fi + while read src dst ; do + if filter_socket "$srcs" "$sports" "$src" ; then + echo 0 0 "$src" "$dst" + fi + done <"$FAKE_NETSTAT_TCP_ESTABLISHED_FILE" +} + +############################################################ + +unix_listen () +{ + if $header ; then + cat <&2 + exit 2 +} + +error () +{ + cat >&2 <&2 + + cat >&2 <&2 +} + +if [ -n "$FAKE_TESTPARM_FAIL" ] ; then + error +fi + +if [ -n "$FAKE_TIMEOUT" ] ; then + timeout +fi + +# Ensure that testparm always uses our canned configuration instead of +# the global one, unless some other file is specified. + +file="" +parameter="" +for i ; do + case "$i" in + --parameter-name=*) parameter="${i#--parameter-name=}" ;; + -*) : ;; + *) file="$i" ;; + esac +done + +# Just hard-code parameter requests for now. Later on they could be +# parsed out of the file. +case "$parameter" in + security) echo "ADS" ; exit 0 ;; + smb*ports) echo "445, 139" ; exit 0 ;; + ?*) not_implemented "--parameter-name=$parameter" ;; + # Fall through if $parameter not set +esac + +if [ -n "$file" ] ; then + # This should include the shares, since this is used when the + # samba eventscript caches the output. + cat "$file" +else + # We force our own smb.conf and add the shares. + cat "${CTDB_SYS_ETCDIR}/samba/smb.conf" + + for i in $FAKE_SHARES ; do + bi=$(basename "$i") +cat <