11285115cSWilliam A. Kennington III# Copyright 2021 Google LLC 21285115cSWilliam A. Kennington III# 31285115cSWilliam A. Kennington III# Licensed under the Apache License, Version 2.0 (the "License"); 41285115cSWilliam A. Kennington III# you may not use this file except in compliance with the License. 51285115cSWilliam A. Kennington III# You may obtain a copy of the License at 61285115cSWilliam A. Kennington III# 71285115cSWilliam A. Kennington III# http://www.apache.org/licenses/LICENSE-2.0 81285115cSWilliam A. Kennington III# 91285115cSWilliam A. Kennington III# Unless required by applicable law or agreed to in writing, software 101285115cSWilliam A. Kennington III# distributed under the License is distributed on an "AS IS" BASIS, 111285115cSWilliam A. Kennington III# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 121285115cSWilliam A. Kennington III# See the License for the specific language governing permissions and 131285115cSWilliam A. Kennington III# limitations under the License. 141285115cSWilliam A. Kennington III 151285115cSWilliam A. Kennington III# Internal handler used for signalling child processes that they should 161285115cSWilliam A. Kennington III# terminate. 171285115cSWilliam A. Kennington IIIHandleTerm() { 181285115cSWilliam A. Kennington III GOT_TERM=1 191285115cSWilliam A. Kennington III if ShouldTerm && (( ${#CHILD_PIDS[@]} > 0 )); then 201285115cSWilliam A. Kennington III kill "${!CHILD_PIDS[@]}" 211285115cSWilliam A. Kennington III fi 221285115cSWilliam A. Kennington III} 231285115cSWilliam A. Kennington III 241285115cSWilliam A. Kennington III# Sets up the signal handler and global variables needed to run interruptible 251285115cSWilliam A. Kennington III# services that can be killed gracefully. 261285115cSWilliam A. Kennington IIIInitTerm() { 271285115cSWilliam A. Kennington III declare -g -A CHILD_PIDS=() 281285115cSWilliam A. Kennington III declare -g GOT_TERM=0 291285115cSWilliam A. Kennington III declare -g SUPPRESS_TERM=0 301285115cSWilliam A. Kennington III trap HandleTerm TERM 311285115cSWilliam A. Kennington III} 321285115cSWilliam A. Kennington III 331285115cSWilliam A. Kennington III# Used to suppress the handling of SIGTERM for critical components that should 341285115cSWilliam A. Kennington III# not respect SIGTERM. To finish suppressing, use UnsuppressTerm() 351285115cSWilliam A. Kennington IIISuppressTerm() { 361285115cSWilliam A. Kennington III SUPPRESS_TERM=$((SUPPRESS_TERM + 1)) 371285115cSWilliam A. Kennington III} 381285115cSWilliam A. Kennington III 391285115cSWilliam A. Kennington III# Stops suppressing SIGTERM for a single invocation of SuppresssTerm() 401285115cSWilliam A. Kennington IIIUnsuppressTerm() { 411285115cSWilliam A. Kennington III SUPPRESS_TERM=$((SUPPRESS_TERM - 1)) 421285115cSWilliam A. Kennington III} 431285115cSWilliam A. Kennington III 441285115cSWilliam A. Kennington III# Determines if we got a SIGTERM and should respect it 451285115cSWilliam A. Kennington IIIShouldTerm() { 461285115cSWilliam A. Kennington III (( GOT_TERM == 1 && SUPPRESS_TERM == 0 )) 471285115cSWilliam A. Kennington III} 481285115cSWilliam A. Kennington III 491285115cSWilliam A. Kennington III# Internal, ensures that functions called in a subprocess properly initialize 501285115cSWilliam A. Kennington III# their SIGTERM handling logic 511285115cSWilliam A. Kennington IIIRunInterruptibleFunction() { 521285115cSWilliam A. Kennington III CHILD_PIDS=() 531285115cSWilliam A. Kennington III trap HandleTerm TERM 541285115cSWilliam A. Kennington III "$@" 551285115cSWilliam A. Kennington III} 561285115cSWilliam A. Kennington III 571285115cSWilliam A. Kennington III# Runs the provided commandline in the background, and passes any received 581285115cSWilliam A. Kennington III# SIGTERMS to the child. Can be waited on using WaitInterruptibleBg 591285115cSWilliam A. Kennington IIIRunInterruptibleBg() { 601285115cSWilliam A. Kennington III if ShouldTerm; then 611285115cSWilliam A. Kennington III return 143 621285115cSWilliam A. Kennington III fi 631285115cSWilliam A. Kennington III if [ "$(type -t "$1")" = "function" ]; then 641285115cSWilliam A. Kennington III RunInterruptibleFunction "$@" & 651285115cSWilliam A. Kennington III else 661285115cSWilliam A. Kennington III "$@" & 671285115cSWilliam A. Kennington III fi 681285115cSWilliam A. Kennington III CHILD_PIDS["$!"]=1 691285115cSWilliam A. Kennington III} 701285115cSWilliam A. Kennington III 711285115cSWilliam A. Kennington III# Runs the provided commandline to completion, and passes any received 721285115cSWilliam A. Kennington III# SIGTERMS to the child. 731285115cSWilliam A. Kennington IIIRunInterruptible() { 741285115cSWilliam A. Kennington III RunInterruptibleBg "$@" || return 751285115cSWilliam A. Kennington III local child_pid="$!" 761285115cSWilliam A. Kennington III wait "$child_pid" || true 771285115cSWilliam A. Kennington III unset CHILD_PIDS["$child_pid"] 781285115cSWilliam A. Kennington III wait "$child_pid" 791285115cSWilliam A. Kennington III} 801285115cSWilliam A. Kennington III 811285115cSWilliam A. Kennington III# Waits until all of the RunInterruptibleBg() jobs have terminated 821285115cSWilliam A. Kennington IIIWaitInterruptibleBg() { 831285115cSWilliam A. Kennington III local wait_on=("${!CHILD_PIDS[@]}") 841285115cSWilliam A. Kennington III if (( ${#wait_on[@]} > 0 )); then 851285115cSWilliam A. Kennington III wait "${wait_on[@]}" || true 861285115cSWilliam A. Kennington III CHILD_PIDS=() 871285115cSWilliam A. Kennington III local rc=0 881285115cSWilliam A. Kennington III local id 891285115cSWilliam A. Kennington III for id in "${wait_on[@]}"; do 901285115cSWilliam A. Kennington III wait "$id" || rc=$? 911285115cSWilliam A. Kennington III done 921285115cSWilliam A. Kennington III return $rc 931285115cSWilliam A. Kennington III fi 941285115cSWilliam A. Kennington III} 951285115cSWilliam A. Kennington III 961285115cSWilliam A. Kennington III# Determines if an address could be a valid IPv4 address 971285115cSWilliam A. Kennington III# NOTE: this doesn't sanitize invalid IPv4 addresses 981285115cSWilliam A. Kennington IIIIsIPv4() { 991285115cSWilliam A. Kennington III local ip="$1" 1001285115cSWilliam A. Kennington III 1011285115cSWilliam A. Kennington III [[ "$ip" =~ ^([0-9]{1,3}\.){3}[0-9]{1,3}$ ]] 1021285115cSWilliam A. Kennington III} 1031285115cSWilliam A. Kennington III 1041285115cSWilliam A. Kennington III# Takes lines of text from an application on stdin and parses out a single 1051285115cSWilliam A. Kennington III# MAC address per line of input. 1061285115cSWilliam A. Kennington IIIParseMACFromLine() { 1071285115cSWilliam A. Kennington III sed -n 's,.*\(\([0-9a-fA-F]\{2\}:\)\{5\}[0-9a-fA-F]\{2\}\).*,\1,p' 1081285115cSWilliam A. Kennington III} 1091285115cSWilliam A. Kennington III 1101285115cSWilliam A. Kennington III# Looks up the MAC address of the IPv4 neighbor using ARP 1111285115cSWilliam A. Kennington IIIDetermineNeighbor4() { 1121285115cSWilliam A. Kennington III local netdev="$1" 1131285115cSWilliam A. Kennington III local ip="$2" 1141285115cSWilliam A. Kennington III 1151285115cSWilliam A. Kennington III # Grep intentionally prevented from returning an error to preserve the error 1161285115cSWilliam A. Kennington III # value of arping 1171285115cSWilliam A. Kennington III RunInterruptible arping -f -c 5 -w 5 -I "$netdev" "$ip" | \ 1181285115cSWilliam A. Kennington III { grep 'reply from' || true; } | ParseMACFromLine 1191285115cSWilliam A. Kennington III} 1201285115cSWilliam A. Kennington III 1211285115cSWilliam A. Kennington III# Looks up the MAC address of the IPv6 neighbor using ICMPv6 ND 1221285115cSWilliam A. Kennington IIIDetermineNeighbor6() { 1231285115cSWilliam A. Kennington III local netdev="$1" 1241285115cSWilliam A. Kennington III local ip="$2" 1251285115cSWilliam A. Kennington III 1261285115cSWilliam A. Kennington III RunInterruptible ndisc6 -1 -r 5 -w 1000 -q "$ip" "$netdev" 1271285115cSWilliam A. Kennington III} 1281285115cSWilliam A. Kennington III 1291285115cSWilliam A. Kennington III# Looks up the MAC address of the neighbor regardless of type 1301285115cSWilliam A. Kennington IIIDetermineNeighbor() { 1311285115cSWilliam A. Kennington III local netdev="$1" 1321285115cSWilliam A. Kennington III local ip="$2" 1331285115cSWilliam A. Kennington III 1341285115cSWilliam A. Kennington III if IsIPv4 "$ip"; then 1351285115cSWilliam A. Kennington III DetermineNeighbor4 "$netdev" "$ip" 1361285115cSWilliam A. Kennington III else 1371285115cSWilliam A. Kennington III DetermineNeighbor6 "$netdev" "$ip" 1381285115cSWilliam A. Kennington III fi 1391285115cSWilliam A. Kennington III} 1401285115cSWilliam A. Kennington III 1411285115cSWilliam A. Kennington III# Performs a mapper call to get the subroot for the object root 1421285115cSWilliam A. Kennington III# with a maxdepth and list of required interfaces. Returns a streamed list 1431285115cSWilliam A. Kennington III# of JSON objects that contain an { object, service }. 1441285115cSWilliam A. Kennington IIIGetSubTree() { 1451285115cSWilliam A. Kennington III local root="$1" 1461285115cSWilliam A. Kennington III shift 1471285115cSWilliam A. Kennington III local max_depth="$1" 1481285115cSWilliam A. Kennington III shift 1491285115cSWilliam A. Kennington III 1501285115cSWilliam A. Kennington III busctl --json=short call \ 1511285115cSWilliam A. Kennington III 'xyz.openbmc_project.ObjectMapper' \ 1521285115cSWilliam A. Kennington III '/xyz/openbmc_project/object_mapper' \ 1531285115cSWilliam A. Kennington III 'xyz.openbmc_project.ObjectMapper' \ 1541285115cSWilliam A. Kennington III 'GetSubTree' sias "$root" "$max_depth" "$#" "$@" | \ 1551285115cSWilliam A. Kennington III jq -c '.data[0] | to_entries[] | { object: .key, service: (.value | keys[0]) }' 1561285115cSWilliam A. Kennington III} 1571285115cSWilliam A. Kennington III 1581285115cSWilliam A. Kennington III# Returns all of the properties for a DBus interface on an object as a JSON 1591285115cSWilliam A. Kennington III# object where the keys are the property names 1601285115cSWilliam A. Kennington IIIGetProperties() { 1611285115cSWilliam A. Kennington III local service="$1" 1621285115cSWilliam A. Kennington III local object="$2" 1631285115cSWilliam A. Kennington III local interface="$3" 1641285115cSWilliam A. Kennington III 1651285115cSWilliam A. Kennington III busctl --json=short call \ 1661285115cSWilliam A. Kennington III "$service" \ 1671285115cSWilliam A. Kennington III "$object" \ 1681285115cSWilliam A. Kennington III 'org.freedesktop.DBus.Properties' \ 1691285115cSWilliam A. Kennington III 'GetAll' s "$interface" | \ 1701285115cSWilliam A. Kennington III jq -c '.data[0] | with_entries({ key, value: .value.data })' 1711285115cSWilliam A. Kennington III} 1721285115cSWilliam A. Kennington III 1731285115cSWilliam A. Kennington III# Returns the property for a DBus interface on an object 1741285115cSWilliam A. Kennington IIIGetProperty() { 1751285115cSWilliam A. Kennington III local service="$1" 1761285115cSWilliam A. Kennington III local object="$2" 1771285115cSWilliam A. Kennington III local interface="$3" 1781285115cSWilliam A. Kennington III local property="$4" 1791285115cSWilliam A. Kennington III 1801285115cSWilliam A. Kennington III busctl --json=short call \ 1811285115cSWilliam A. Kennington III "$service" \ 1821285115cSWilliam A. Kennington III "$object" \ 1831285115cSWilliam A. Kennington III 'org.freedesktop.DBus.Properties' \ 1841285115cSWilliam A. Kennington III 'Get' ss "$interface" "$property" | \ 1851285115cSWilliam A. Kennington III jq -r '.data[0].data' 1861285115cSWilliam A. Kennington III} 1871285115cSWilliam A. Kennington III 1881285115cSWilliam A. Kennington III# Deletes any OpenBMC DBus object from a service 1891285115cSWilliam A. Kennington IIIDeleteObject() { 1901285115cSWilliam A. Kennington III local service="$1" 1911285115cSWilliam A. Kennington III local object="$2" 1921285115cSWilliam A. Kennington III 1931285115cSWilliam A. Kennington III busctl call \ 1941285115cSWilliam A. Kennington III "$service" \ 1951285115cSWilliam A. Kennington III "$object" \ 1961285115cSWilliam A. Kennington III 'xyz.openbmc_project.Object.Delete' \ 1971285115cSWilliam A. Kennington III 'Delete' 1981285115cSWilliam A. Kennington III} 1991285115cSWilliam A. Kennington III 2001285115cSWilliam A. Kennington III# Transforms the given JSON dictionary into bash local variable 2011285115cSWilliam A. Kennington III# statements that can be directly evaluated by the interpreter 2021285115cSWilliam A. Kennington IIIJSONToVars() { 2031285115cSWilliam A. Kennington III jq -r 'to_entries[] | @sh "local \(.key)=\(.value)"' 2041285115cSWilliam A. Kennington III} 2051285115cSWilliam A. Kennington III 2061285115cSWilliam A. Kennington III# Returns the DBus object root for the ethernet interface 2071285115cSWilliam A. Kennington IIIEthObjRoot() { 2081285115cSWilliam A. Kennington III local netdev="$1" 2091285115cSWilliam A. Kennington III 2101285115cSWilliam A. Kennington III echo "/xyz/openbmc_project/network/$netdev" 2111285115cSWilliam A. Kennington III} 2121285115cSWilliam A. Kennington III 2131285115cSWilliam A. Kennington III# Returns the DBus object root for the static neighbors of an intrerface 2141285115cSWilliam A. Kennington IIIStaticNeighborObjRoot() { 2151285115cSWilliam A. Kennington III local netdev="$1" 2161285115cSWilliam A. Kennington III 2171285115cSWilliam A. Kennington III echo "$(EthObjRoot "$netdev")/static_neighbor" 2181285115cSWilliam A. Kennington III} 2191285115cSWilliam A. Kennington III 2201285115cSWilliam A. Kennington III# Returns all of the neighbor { service, object } data for an interface as if 2211285115cSWilliam A. Kennington III# a call to GetSubTree() was made 2221285115cSWilliam A. Kennington IIIGetNeighborObjects() { 2231285115cSWilliam A. Kennington III local netdev="$1" 2241285115cSWilliam A. Kennington III 2251285115cSWilliam A. Kennington III GetSubTree "$(StaticNeighborObjRoot "$netdev")" 0 \ 2261285115cSWilliam A. Kennington III 'xyz.openbmc_project.Network.Neighbor' 2271285115cSWilliam A. Kennington III} 2281285115cSWilliam A. Kennington III 2291285115cSWilliam A. Kennington III# Returns the neighbor properties as a JSON object 2301285115cSWilliam A. Kennington IIIGetNeighbor() { 2311285115cSWilliam A. Kennington III local service="$1" 2321285115cSWilliam A. Kennington III local object="$2" 2331285115cSWilliam A. Kennington III 2341285115cSWilliam A. Kennington III GetProperties "$service" "$object" 'xyz.openbmc_project.Network.Neighbor' 2351285115cSWilliam A. Kennington III} 2361285115cSWilliam A. Kennington III 2371285115cSWilliam A. Kennington III# Adds a static neighbor to the system network daemon 2381285115cSWilliam A. Kennington IIIAddNeighbor() { 2391285115cSWilliam A. Kennington III local service="$1" 2401285115cSWilliam A. Kennington III local netdev="$2" 2411285115cSWilliam A. Kennington III local ip="$3" 2421285115cSWilliam A. Kennington III local mac="$4" 2431285115cSWilliam A. Kennington III 2441285115cSWilliam A. Kennington III busctl call \ 2451285115cSWilliam A. Kennington III "$service" \ 2461285115cSWilliam A. Kennington III "$(EthObjRoot "$netdev")" \ 2471285115cSWilliam A. Kennington III 'xyz.openbmc_project.Network.Neighbor.CreateStatic' \ 2481285115cSWilliam A. Kennington III 'Neighbor' ss "$ip" "$mac" >/dev/null 2491285115cSWilliam A. Kennington III} 2501285115cSWilliam A. Kennington III 2511285115cSWilliam A. Kennington III# Returns all of the IP { service, object } data for an interface as if 2521285115cSWilliam A. Kennington III# a call to GetSubTree() was made 2531285115cSWilliam A. Kennington IIIGetIPObjects() { 2541285115cSWilliam A. Kennington III local netdev="$1" 2551285115cSWilliam A. Kennington III 2561285115cSWilliam A. Kennington III GetSubTree "$(EthObjRoot "$netdev")" 0 \ 2571285115cSWilliam A. Kennington III 'xyz.openbmc_project.Network.IP' 2581285115cSWilliam A. Kennington III} 2591285115cSWilliam A. Kennington III 2601285115cSWilliam A. Kennington III# Returns the IP properties as a JSON object 2611285115cSWilliam A. Kennington IIIGetIP() { 2621285115cSWilliam A. Kennington III local service="$1" 2631285115cSWilliam A. Kennington III local object="$2" 2641285115cSWilliam A. Kennington III 2651285115cSWilliam A. Kennington III GetProperties "$service" "$object" 'xyz.openbmc_project.Network.IP' 2661285115cSWilliam A. Kennington III} 2671285115cSWilliam A. Kennington III 268b163a2c1SWilliam A. Kennington III# Returns the Gateway address for the interface and type 269b163a2c1SWilliam A. Kennington IIIGetGateways() { 270b163a2c1SWilliam A. Kennington III local service="$1" 271b163a2c1SWilliam A. Kennington III local netdev="$2" 272b163a2c1SWilliam A. Kennington III 273b163a2c1SWilliam A. Kennington III # We fetch both the system properties and the netdev specific properties 274b163a2c1SWilliam A. Kennington III # as OpenBMC is in the process of transitioning these to the netdev object 275b163a2c1SWilliam A. Kennington III # but the migration is not yet complete. 276b163a2c1SWilliam A. Kennington III { 277b163a2c1SWilliam A. Kennington III GetProperties "$service" '/xyz/openbmc_project/network/config' \ 278b163a2c1SWilliam A. Kennington III 'xyz.openbmc_project.Network.SystemConfiguration' 279b163a2c1SWilliam A. Kennington III GetProperties "$service" "$(EthObjRoot "$netdev")" \ 280b163a2c1SWilliam A. Kennington III 'xyz.openbmc_project.Network.EthernetInterface' 281b163a2c1SWilliam A. Kennington III } | jq -s ' 282b163a2c1SWilliam A. Kennington III . | map( 283b163a2c1SWilliam A. Kennington III if .DefaultGateway != "" then 284b163a2c1SWilliam A. Kennington III {DefaultGateway: .DefaultGateway} 285b163a2c1SWilliam A. Kennington III else 286b163a2c1SWilliam A. Kennington III {} 287b163a2c1SWilliam A. Kennington III end + 288b163a2c1SWilliam A. Kennington III if .DefaultGateway6 != "" then 289b163a2c1SWilliam A. Kennington III {DefaultGateway6: .DefaultGateway6} 290b163a2c1SWilliam A. Kennington III else 291b163a2c1SWilliam A. Kennington III {} 292b163a2c1SWilliam A. Kennington III end 293b163a2c1SWilliam A. Kennington III ) | {DefaultGateway: "", DefaultGateway6: ""} + add' 294b163a2c1SWilliam A. Kennington III} 295b163a2c1SWilliam A. Kennington III 2961285115cSWilliam A. Kennington III# Adds a static IP to the system network daemon 2971285115cSWilliam A. Kennington IIIAddIP() { 2981285115cSWilliam A. Kennington III local service="$1" 2991285115cSWilliam A. Kennington III local netdev="$2" 3001285115cSWilliam A. Kennington III local ip="$3" 3011285115cSWilliam A. Kennington III local prefix="$4" 3021285115cSWilliam A. Kennington III 3031285115cSWilliam A. Kennington III local protocol='xyz.openbmc_project.Network.IP.Protocol.IPv4' 3041285115cSWilliam A. Kennington III if ! IsIPv4 "$ip"; then 3051285115cSWilliam A. Kennington III protocol='xyz.openbmc_project.Network.IP.Protocol.IPv6' 3061285115cSWilliam A. Kennington III fi 3071285115cSWilliam A. Kennington III 3081285115cSWilliam A. Kennington III busctl call \ 3091285115cSWilliam A. Kennington III "$service" \ 3101285115cSWilliam A. Kennington III "$(EthObjRoot "$netdev")" \ 3111285115cSWilliam A. Kennington III 'xyz.openbmc_project.Network.IP.Create' \ 3121285115cSWilliam A. Kennington III 'IP' ssys "$protocol" "$ip" "$prefix" '' >/dev/null 3131285115cSWilliam A. Kennington III} 3141285115cSWilliam A. Kennington III 3151285115cSWilliam A. Kennington III# Determines if two IP addresses have the same address family 3161285115cSWilliam A. Kennington III# IE: Both are IPv4 or both are IPv6 3171285115cSWilliam A. Kennington IIIMatchingAF() { 3181285115cSWilliam A. Kennington III local rc1=0 rc2=0 3191285115cSWilliam A. Kennington III IsIPv4 "$1" || rc1=$? 3201285115cSWilliam A. Kennington III IsIPv4 "$2" || rc2=$? 3211285115cSWilliam A. Kennington III (( rc1 == rc2 )) 3221285115cSWilliam A. Kennington III} 3231285115cSWilliam A. Kennington III 3241285115cSWilliam A. Kennington III# Checks to see if the machine has the provided IP address information 3251285115cSWilliam A. Kennington III# already configured. If not, it deletes all of the information for that 3261285115cSWilliam A. Kennington III# address family and adds the provided IP address. 3271285115cSWilliam A. Kennington IIIUpdateIP() { 3281285115cSWilliam A. Kennington III local service="$1" 3291285115cSWilliam A. Kennington III local netdev="$2" 3301285115cSWilliam A. Kennington III local ip="$3" 3311285115cSWilliam A. Kennington III local prefix="$4" 3321285115cSWilliam A. Kennington III 3331285115cSWilliam A. Kennington III local should_add=1 3341285115cSWilliam A. Kennington III local delete_services=() 3351285115cSWilliam A. Kennington III local delete_objects=() 3361285115cSWilliam A. Kennington III local entry 3371285115cSWilliam A. Kennington III while read entry; do 3381285115cSWilliam A. Kennington III eval "$(echo "$entry" | JSONToVars)" || return $? 3391285115cSWilliam A. Kennington III eval "$(GetIP "$service" "$object" | JSONToVars)" || return $? 3401285115cSWilliam A. Kennington III if [ "$(normalize_ip "$Address")" = "$(normalize_ip "$ip")" ] && \ 3411285115cSWilliam A. Kennington III [ "$PrefixLength" = "$prefix" ]; then 3421285115cSWilliam A. Kennington III should_add=0 3431285115cSWilliam A. Kennington III elif MatchingAF "$ip" "$Address"; then 3441285115cSWilliam A. Kennington III echo "Deleting spurious IP: $Address/$PrefixLength" >&2 3451285115cSWilliam A. Kennington III delete_services+=("$service") 3461285115cSWilliam A. Kennington III delete_objects+=("$object") 3471285115cSWilliam A. Kennington III fi 3481285115cSWilliam A. Kennington III done < <(GetIPObjects "$netdev") 3491285115cSWilliam A. Kennington III 3501285115cSWilliam A. Kennington III local i 3511285115cSWilliam A. Kennington III for (( i=0; i<${#delete_objects[@]}; ++i )); do 3522be0536cSWilliam A. Kennington III DeleteObject "${delete_services[$i]}" "${delete_objects[$i]}" || true 3531285115cSWilliam A. Kennington III done 3541285115cSWilliam A. Kennington III 3551285115cSWilliam A. Kennington III if (( should_add == 0 )); then 3561285115cSWilliam A. Kennington III echo "Not adding IP: $ip/$prefix" >&2 3571285115cSWilliam A. Kennington III else 3581285115cSWilliam A. Kennington III echo "Adding IP: $ip/$prefix" >&2 3591285115cSWilliam A. Kennington III AddIP "$service" "$netdev" "$ip" "$prefix" || return $? 3601285115cSWilliam A. Kennington III fi 3611285115cSWilliam A. Kennington III} 3621285115cSWilliam A. Kennington III 3631285115cSWilliam A. Kennington III# Sets the system gateway property to the provided IP address if not already 3641285115cSWilliam A. Kennington III# set to the current value. 3651285115cSWilliam A. Kennington IIIUpdateGateway() { 3661285115cSWilliam A. Kennington III local service="$1" 367*2d6858ddSWilliam A. Kennington III local netdev="$2" 368*2d6858ddSWilliam A. Kennington III local ip="$3" 3691285115cSWilliam A. Kennington III 370*2d6858ddSWilliam A. Kennington III local object="$(EthObjRoot "$netdev")" 371*2d6858ddSWilliam A. Kennington III local interface='xyz.openbmc_project.Network.EthernetInterface' 3721285115cSWilliam A. Kennington III local property='DefaultGateway' 3731285115cSWilliam A. Kennington III if ! IsIPv4 "$ip"; then 3741285115cSWilliam A. Kennington III property='DefaultGateway6' 3751285115cSWilliam A. Kennington III fi 3761285115cSWilliam A. Kennington III 3771285115cSWilliam A. Kennington III local current_ip 3781285115cSWilliam A. Kennington III current_ip="$(GetProperty "$service" "$object" "$interface" "$property")" || \ 3791285115cSWilliam A. Kennington III return $? 3801285115cSWilliam A. Kennington III if [ -n "$current_ip" ] && \ 3811285115cSWilliam A. Kennington III [ "$(normalize_ip "$ip")" = "$(normalize_ip "$current_ip")" ]; then 3821285115cSWilliam A. Kennington III echo "Not reconfiguring gateway: $ip" >&2 3831285115cSWilliam A. Kennington III return 0 3841285115cSWilliam A. Kennington III fi 3851285115cSWilliam A. Kennington III 3861285115cSWilliam A. Kennington III echo "Setting gateway: $ip" >&2 3871285115cSWilliam A. Kennington III busctl set-property "$service" "$object" "$interface" "$property" s "$ip" 3881285115cSWilliam A. Kennington III} 3891285115cSWilliam A. Kennington III 3901285115cSWilliam A. Kennington III# Checks to see if the machine has the provided neighbor information 3911285115cSWilliam A. Kennington III# already configured. If not, it deletes all of the information for that 3921285115cSWilliam A. Kennington III# address family and adds the provided neighbor entry. 3931285115cSWilliam A. Kennington IIIUpdateNeighbor() { 3941285115cSWilliam A. Kennington III local service="$1" 3951285115cSWilliam A. Kennington III local netdev="$2" 3961285115cSWilliam A. Kennington III local ip="$3" 3971285115cSWilliam A. Kennington III local mac="$4" 3981285115cSWilliam A. Kennington III 3991285115cSWilliam A. Kennington III local should_add=1 4001285115cSWilliam A. Kennington III local delete_services=() 4011285115cSWilliam A. Kennington III local delete_objects=() 4021285115cSWilliam A. Kennington III local entry 4031285115cSWilliam A. Kennington III while read entry; do 4041285115cSWilliam A. Kennington III eval "$(echo "$entry" | JSONToVars)" || return $? 4051285115cSWilliam A. Kennington III eval "$(GetNeighbor "$service" "$object" | JSONToVars)" || return $? 4061285115cSWilliam A. Kennington III if [ "$(normalize_ip "$IPAddress")" = "$(normalize_ip "$ip")" ] && \ 4071285115cSWilliam A. Kennington III [ "$(normalize_mac "$MACAddress")" = "$(normalize_mac "$mac")" ]; then 4081285115cSWilliam A. Kennington III should_add=0 4091285115cSWilliam A. Kennington III elif MatchingAF "$ip" "$IPAddress"; then 4101285115cSWilliam A. Kennington III echo "Deleting spurious neighbor: $IPAddress $MACAddress" >&2 4111285115cSWilliam A. Kennington III delete_services+=("$service") 4121285115cSWilliam A. Kennington III delete_objects+=("$object") 4131285115cSWilliam A. Kennington III fi 4141285115cSWilliam A. Kennington III done < <(GetNeighborObjects "$netdev" 2>/dev/null) 4151285115cSWilliam A. Kennington III 4161285115cSWilliam A. Kennington III local i 4171285115cSWilliam A. Kennington III for (( i=0; i<${#delete_objects[@]}; ++i )); do 4182be0536cSWilliam A. Kennington III DeleteObject "${delete_services[$i]}" "${delete_objects[$i]}" || true 4191285115cSWilliam A. Kennington III done 4201285115cSWilliam A. Kennington III 4211285115cSWilliam A. Kennington III if (( should_add == 0 )); then 4221285115cSWilliam A. Kennington III echo "Not adding neighbor: $ip $mac" >&2 4231285115cSWilliam A. Kennington III else 4241285115cSWilliam A. Kennington III echo "Adding neighbor: $ip $mac" >&2 4251285115cSWilliam A. Kennington III AddNeighbor "$service" "$netdev" "$ip" "$mac" || return $? 4261285115cSWilliam A. Kennington III fi 4271285115cSWilliam A. Kennington III} 428b163a2c1SWilliam A. Kennington III 429b163a2c1SWilliam A. Kennington III# Determines the ip and mac of the IPv6 router 430b163a2c1SWilliam A. Kennington IIIDiscoverRouter6() { 431b163a2c1SWilliam A. Kennington III local netdev="$1" 432b163a2c1SWilliam A. Kennington III local retries="$2" 433b163a2c1SWilliam A. Kennington III local timeout="$3" 434b163a2c1SWilliam A. Kennington III local router="${4-}" 435b163a2c1SWilliam A. Kennington III 436b163a2c1SWilliam A. Kennington III local output 437b163a2c1SWilliam A. Kennington III local st=0 438b163a2c1SWilliam A. Kennington III local args=(-1 -w "$timeout" -n $router "$netdev") 439b163a2c1SWilliam A. Kennington III if (( retries < 0 )); then 440b163a2c1SWilliam A. Kennington III args+=(-d) 441b163a2c1SWilliam A. Kennington III else 442b163a2c1SWilliam A. Kennington III args+=(-r "$retries") 443b163a2c1SWilliam A. Kennington III fi 444b163a2c1SWilliam A. Kennington III output="$(RunInterruptible rdisc6 "${args[@]}")" || st=$? 445b163a2c1SWilliam A. Kennington III if (( st != 0 )); then 446b163a2c1SWilliam A. Kennington III echo "rdisc6 failed with: " >&2 447b163a2c1SWilliam A. Kennington III echo "$output" >&2 448b163a2c1SWilliam A. Kennington III return $st 449b163a2c1SWilliam A. Kennington III fi 450b163a2c1SWilliam A. Kennington III 451b163a2c1SWilliam A. Kennington III local ip="$(echo "$output" | grep 'from' | awk '{print $2}')" 452b163a2c1SWilliam A. Kennington III local mac="$(echo "$output" | grep 'Source link-layer' | ParseMACFromLine)" 453379b061fSWilliam A. Kennington III local staddr="$(echo "$output" | grep 'Stateful address conf.*Yes')" 454379b061fSWilliam A. Kennington III printf '{"router_ip":"%s","router_mac":"%s","stateful_address":"%s"}\n' \ 455379b061fSWilliam A. Kennington III "$ip" "$mac" "$staddr" 456b163a2c1SWilliam A. Kennington III} 457