179f697e0SAnthony Wilson#!/bin/sh -e 279f697e0SAnthony Wilson 379f697e0SAnthony Wilsonset -euo pipefail 479f697e0SAnthony Wilson 5189cf248SAnthony WilsonOPTS="bmcstate,bootprogress,chassiskill,chassisoff,chassison,chassisstate,hoststate,\ 6*a65d30d1SVishwanatha Subbannaosstate,power,poweroff,poweron,state,status,hostrebootoff,hostrebooton,recoveryoff,recoveryon,\ 7*a65d30d1SVishwanatha Subbannabmcrebootoff, bmcrebooton" 80f35983dSAnthony Wilson 960c3ac8cSAndrew JefferyUSAGE="Usage: obmcutil [-h] [--wait] [--verbose] 100f35983dSAnthony Wilson {$OPTS}" 1179f697e0SAnthony Wilson 1279f697e0SAnthony WilsonINTERFACE_ROOT=xyz.openbmc_project 1379f697e0SAnthony WilsonSTATE_INTERFACE=$INTERFACE_ROOT.State 146d3a2c54SVishwanatha SubbannaCONTROL_INTERFACE=$INTERFACE_ROOT.Control 1579f697e0SAnthony Wilson 1679f697e0SAnthony WilsonOBJECT_ROOT=/xyz/openbmc_project 1779f697e0SAnthony WilsonSTATE_OBJECT=$OBJECT_ROOT/state 186d3a2c54SVishwanatha SubbannaCONTROL_OBJECT=$OBJECT_ROOT/control 1979f697e0SAnthony Wilson 207a787dd7SVishwanatha SubbannaHOST_TIMEOUT_TARGET=obmc-host-timeout@0.target 2184b3b29eSVishwanatha SubbannaHOST_CRASH_TARGET=obmc-host-crash@0.target 227a787dd7SVishwanatha Subbanna 23acf54d08SAnthony Wilson## NOTE: The following global variables are used only in the run_timeout cmd. 24acf54d08SAnthony Wilson## By declaring these globally instead of passing them through the 25acf54d08SAnthony Wilson## intermediary functions, which may not be "best practice", the readability 26acf54d08SAnthony Wilson## and cleanliness of the code should at least be increased. 27acf54d08SAnthony Wilson 28acf54d08SAnthony Wilson# The command passed in to be executed (e.g. poweron/off, status, etc.) 29acf54d08SAnthony Wilson# This will be be used in some instances of error reporting 30acf54d08SAnthony WilsonG_ORIG_CMD= 31acf54d08SAnthony Wilson# The state an interface should be in after executing the requested command. 32acf54d08SAnthony WilsonG_REQUESTED_STATE= 33acf54d08SAnthony Wilson# The query to run during a poweron/off or chassison/off to check that 34acf54d08SAnthony Wilson# the requested state (G_REQUESTED_STATE) of the interface has been reached. 35acf54d08SAnthony WilsonG_QUERY= 36acf54d08SAnthony Wilson# Wait the set period of time for state transitions to be successful before 37acf54d08SAnthony Wilson# continuing on with the program or reporting an error if timeout reached. 38acf54d08SAnthony WilsonG_WAIT= 3960c3ac8cSAndrew Jeffery# Print the journal to the console 4060c3ac8cSAndrew JefferyG_VERBOSE= 41acf54d08SAnthony Wilson 42f3f16fa9SAnthony Wilsonprint_help () 43f3f16fa9SAnthony Wilson{ 44f3f16fa9SAnthony Wilson echo "$USAGE" 45f3f16fa9SAnthony Wilson echo "" 46f3f16fa9SAnthony Wilson echo "positional arguments:" 470f35983dSAnthony Wilson echo " {$OPTS}" 48f3f16fa9SAnthony Wilson echo "" 496d3a2c54SVishwanatha Subbanna echo "Examples:" 506d3a2c54SVishwanatha Subbanna echo "" 51*a65d30d1SVishwanatha Subbanna echo "obmcutil hostrebootoff Disable auto reboot of Host from Quiesce state" 52*a65d30d1SVishwanatha Subbanna echo "obmcutil hostrebooton Enable auto reboot of Host from Quiesce state" 53*a65d30d1SVishwanatha Subbanna echo "" 54*a65d30d1SVishwanatha Subbanna echo "obmcutil bmcrebootoff Disable reboot of BMC" 55*a65d30d1SVishwanatha Subbanna echo "obmcutil bmcrebooton Enable reboot of BMC" 566d3a2c54SVishwanatha Subbanna echo "" 5784b3b29eSVishwanatha Subbanna echo "obmcutil recoveryoff Disable handling boot watchdog timeout and host crash" 58*a65d30d1SVishwanatha Subbanna echo " Also, disable BMC and Host auto reboots" 59*a65d30d1SVishwanatha Subbanna echo "" 6084b3b29eSVishwanatha Subbanna echo "obmcutil recoveryon Enable handling boot watchdog timeout and host crash" 61*a65d30d1SVishwanatha Subbanna echo " Also, enable BMC and Host auto reboots" 627a787dd7SVishwanatha Subbanna echo "" 63f3f16fa9SAnthony Wilson echo "optional arguments:" 64f3f16fa9SAnthony Wilson echo " -h, --help show this help message and exit" 65acf54d08SAnthony Wilson echo " -w, --wait block until state transition succeeds or fails" 6660c3ac8cSAndrew Jeffery echo " -v, --verbose print the journal to stdout if --wait is supplied" 67f3f16fa9SAnthony Wilson exit 0 68f3f16fa9SAnthony Wilson} 69f3f16fa9SAnthony Wilson 70acf54d08SAnthony Wilsonrun_timeout () 71acf54d08SAnthony Wilson{ 72acf54d08SAnthony Wilson local timeout="$1"; shift 73acf54d08SAnthony Wilson local cmd="$@" 7460c3ac8cSAndrew Jeffery local verbose_child= 7560c3ac8cSAndrew Jeffery 762869a926SAndrew Jeffery if [ -n "$G_VERBOSE" ]; then 7760c3ac8cSAndrew Jeffery journalctl -f & 7860c3ac8cSAndrew Jeffery verbose_child=$! 7960c3ac8cSAndrew Jeffery fi 80acf54d08SAnthony Wilson 81acf54d08SAnthony Wilson $cmd 82acf54d08SAnthony Wilson 83acf54d08SAnthony Wilson # Run a background query for the transition to the expected state 84acf54d08SAnthony Wilson # This will be killed if the transition doesn't succeed within 85acf54d08SAnthony Wilson # a timeout period. 86acf54d08SAnthony Wilson ( 87acf54d08SAnthony Wilson while ! grep -q $G_REQUESTED_STATE <<< $(handle_cmd $G_QUERY) ; do 88acf54d08SAnthony Wilson sleep 1 89acf54d08SAnthony Wilson done 90acf54d08SAnthony Wilson ) & 9160c3ac8cSAndrew Jeffery wait_child=$! 92acf54d08SAnthony Wilson 93acf54d08SAnthony Wilson # Could be bad if process is killed before 'timeout' occurs if 94acf54d08SAnthony Wilson # transition doesn't succeed. 95acf54d08SAnthony Wilson trap -- "" SIGTERM 96acf54d08SAnthony Wilson 97acf54d08SAnthony Wilson # Workaround for lack of 'timeout' command. 98acf54d08SAnthony Wilson ( 99acf54d08SAnthony Wilson sleep $timeout 10060c3ac8cSAndrew Jeffery kill $wait_child 101acf54d08SAnthony Wilson ) > /dev/null 2>&1 & 102acf54d08SAnthony Wilson 10360c3ac8cSAndrew Jeffery if ! wait $wait_child; then 104acf54d08SAnthony Wilson echo "Unable to confirm '$G_ORIG_CMD' success" \ 105acf54d08SAnthony Wilson "within timeout period (${timeout}s)" 106acf54d08SAnthony Wilson fi 10760c3ac8cSAndrew Jeffery 1088be70293SAndrew Jeffery if [ -n "$verbose_child" ]; then 10960c3ac8cSAndrew Jeffery kill $verbose_child 11060c3ac8cSAndrew Jeffery fi 111acf54d08SAnthony Wilson} 112acf54d08SAnthony Wilson 113acf54d08SAnthony Wilsonrun_cmd () 114acf54d08SAnthony Wilson{ 115acf54d08SAnthony Wilson local cmd="$@"; 116acf54d08SAnthony Wilson 117acf54d08SAnthony Wilson if [ -n "$G_WAIT" ]; then 118acf54d08SAnthony Wilson run_timeout $G_WAIT "$cmd" 119acf54d08SAnthony Wilson else 120acf54d08SAnthony Wilson $cmd 121acf54d08SAnthony Wilson fi 122acf54d08SAnthony Wilson} 123acf54d08SAnthony Wilson 1243ae0a354SAnthony Wilsonset_property () 1253ae0a354SAnthony Wilson{ 126acf54d08SAnthony Wilson run_cmd busctl set-property "$@" 1273ae0a354SAnthony Wilson} 1283ae0a354SAnthony Wilson 12979f697e0SAnthony Wilsonget_property () 13079f697e0SAnthony Wilson{ 131acf54d08SAnthony Wilson G_WAIT="" 132acf54d08SAnthony Wilson run_cmd busctl get-property "$@" 13379f697e0SAnthony Wilson} 13479f697e0SAnthony Wilson 13579f697e0SAnthony Wilsonstate_query () 13679f697e0SAnthony Wilson{ 13779f697e0SAnthony Wilson local state=$(get_property "$@" | cut -d '"' -f2) 13879f697e0SAnthony Wilson printf "%-20s: %s\n" $4 $state 13979f697e0SAnthony Wilson} 14079f697e0SAnthony Wilson 141ea87db40SAnthony Wilsonprint_usage_err () 142ea87db40SAnthony Wilson{ 143ea87db40SAnthony Wilson echo "ERROR: $1" >&2 144ea87db40SAnthony Wilson echo "$USAGE" 145ea87db40SAnthony Wilson exit 1 146ea87db40SAnthony Wilson} 147ea87db40SAnthony Wilson 1487a787dd7SVishwanatha Subbannamask_systemd_target () 1497a787dd7SVishwanatha Subbanna{ 1507a787dd7SVishwanatha Subbanna target="$@" 1517a787dd7SVishwanatha Subbanna systemctl mask $target 1527a787dd7SVishwanatha Subbanna} 1537a787dd7SVishwanatha Subbanna 1547a787dd7SVishwanatha Subbannaunmask_systemd_target () 1557a787dd7SVishwanatha Subbanna{ 1567a787dd7SVishwanatha Subbanna target="$@" 1577a787dd7SVishwanatha Subbanna systemctl unmask $target 1587a787dd7SVishwanatha Subbanna} 1597a787dd7SVishwanatha Subbanna 160*a65d30d1SVishwanatha Subbannadisable_bmc_reboot () 161*a65d30d1SVishwanatha Subbanna{ 162*a65d30d1SVishwanatha Subbanna dir="/run/systemd/system/" 163*a65d30d1SVishwanatha Subbanna file="reboot-guard.conf" 164*a65d30d1SVishwanatha Subbanna units=("reboot" "poweroff" "halt") 165*a65d30d1SVishwanatha Subbanna 166*a65d30d1SVishwanatha Subbanna for unit in "${units[@]}"; do 167*a65d30d1SVishwanatha Subbanna mkdir -p ${dir}${unit}.target.d 168*a65d30d1SVishwanatha Subbanna echo -e "[Unit]\nRefuseManualStart=yes" >> ${dir}${unit}.target.d/${file} 169*a65d30d1SVishwanatha Subbanna done 170*a65d30d1SVishwanatha Subbanna} 171*a65d30d1SVishwanatha Subbanna 172*a65d30d1SVishwanatha Subbannaenable_bmc_reboot () 173*a65d30d1SVishwanatha Subbanna{ 174*a65d30d1SVishwanatha Subbanna dir="/run/systemd/system/" 175*a65d30d1SVishwanatha Subbanna file="reboot-guard.conf" 176*a65d30d1SVishwanatha Subbanna units=("reboot" "poweroff" "halt") 177*a65d30d1SVishwanatha Subbanna 178*a65d30d1SVishwanatha Subbanna for unit in "${units[@]}"; do 179*a65d30d1SVishwanatha Subbanna rm -rf ${dir}${unit}.target.d/${file} 180*a65d30d1SVishwanatha Subbanna rm -rf ${dir}${unit}.target.d 181*a65d30d1SVishwanatha Subbanna done 182*a65d30d1SVishwanatha Subbanna} 183*a65d30d1SVishwanatha Subbanna 18479f697e0SAnthony Wilsonhandle_cmd () 18579f697e0SAnthony Wilson{ 18679f697e0SAnthony Wilson case "$1" in 1873ae0a354SAnthony Wilson chassisoff) 1883ae0a354SAnthony Wilson OBJECT=$STATE_OBJECT/chassis0 1893ae0a354SAnthony Wilson SERVICE=$(mapper get-service $OBJECT) 1903ae0a354SAnthony Wilson INTERFACE=$STATE_INTERFACE.Chassis 1913ae0a354SAnthony Wilson PROPERTY=RequestedPowerTransition 1923ae0a354SAnthony Wilson VALUE=$INTERFACE.Transition.Off 193acf54d08SAnthony Wilson G_REQUESTED_STATE=$INTERFACE.PowerState.Off 194acf54d08SAnthony Wilson G_QUERY="chassisstate" 1953ae0a354SAnthony Wilson set_property $SERVICE $OBJECT $INTERFACE $PROPERTY "s" $VALUE 1963ae0a354SAnthony Wilson ;; 1973ae0a354SAnthony Wilson chassison) 1983ae0a354SAnthony Wilson OBJECT=$STATE_OBJECT/chassis0 1993ae0a354SAnthony Wilson SERVICE=$(mapper get-service $OBJECT) 2003ae0a354SAnthony Wilson INTERFACE=$STATE_INTERFACE.Chassis 2013ae0a354SAnthony Wilson PROPERTY=RequestedPowerTransition 2023ae0a354SAnthony Wilson VALUE=$INTERFACE.Transition.On 203acf54d08SAnthony Wilson G_REQUESTED_STATE=$INTERFACE.PowerState.On 204acf54d08SAnthony Wilson G_QUERY="chassisstate" 2053ae0a354SAnthony Wilson set_property $SERVICE $OBJECT $INTERFACE $PROPERTY "s" $VALUE 2063ae0a354SAnthony Wilson ;; 2073ae0a354SAnthony Wilson poweroff) 2083ae0a354SAnthony Wilson OBJECT=$STATE_OBJECT/host0 2093ae0a354SAnthony Wilson SERVICE=$(mapper get-service $OBJECT) 2103ae0a354SAnthony Wilson INTERFACE=$STATE_INTERFACE.Host 2113ae0a354SAnthony Wilson PROPERTY=RequestedHostTransition 2123ae0a354SAnthony Wilson VALUE=$INTERFACE.Transition.Off 213acf54d08SAnthony Wilson G_REQUESTED_STATE=$INTERFACE.HostState.Off 214acf54d08SAnthony Wilson G_QUERY="hoststate" 2153ae0a354SAnthony Wilson set_property $SERVICE $OBJECT $INTERFACE $PROPERTY "s" $VALUE 2163ae0a354SAnthony Wilson ;; 2173ae0a354SAnthony Wilson poweron) 2183ae0a354SAnthony Wilson OBJECT=$STATE_OBJECT/host0 2193ae0a354SAnthony Wilson SERVICE=$(mapper get-service $OBJECT) 2203ae0a354SAnthony Wilson INTERFACE=$STATE_INTERFACE.Host 2213ae0a354SAnthony Wilson PROPERTY=RequestedHostTransition 2223ae0a354SAnthony Wilson VALUE=$INTERFACE.Transition.On 223acf54d08SAnthony Wilson G_REQUESTED_STATE=$INTERFACE.HostState.Running 224acf54d08SAnthony Wilson G_QUERY="hoststate" 2253ae0a354SAnthony Wilson set_property $SERVICE $OBJECT $INTERFACE $PROPERTY "s" $VALUE 2263ae0a354SAnthony Wilson ;; 22779f697e0SAnthony Wilson bmcstate) 22879f697e0SAnthony Wilson OBJECT=$STATE_OBJECT/bmc0 22979f697e0SAnthony Wilson SERVICE=$(mapper get-service $OBJECT) 23079f697e0SAnthony Wilson INTERFACE=$STATE_INTERFACE.BMC 23179f697e0SAnthony Wilson PROPERTY=CurrentBMCState 23279f697e0SAnthony Wilson state_query $SERVICE $OBJECT $INTERFACE $PROPERTY 23379f697e0SAnthony Wilson ;; 23479f697e0SAnthony Wilson chassisstate) 23579f697e0SAnthony Wilson OBJECT=$STATE_OBJECT/chassis0 23679f697e0SAnthony Wilson SERVICE=$(mapper get-service $OBJECT) 23779f697e0SAnthony Wilson INTERFACE=$STATE_INTERFACE.Chassis 23879f697e0SAnthony Wilson PROPERTY=CurrentPowerState 23979f697e0SAnthony Wilson state_query $SERVICE $OBJECT $INTERFACE $PROPERTY 24079f697e0SAnthony Wilson ;; 24179f697e0SAnthony Wilson hoststate) 24279f697e0SAnthony Wilson OBJECT=$STATE_OBJECT/host0 24379f697e0SAnthony Wilson SERVICE=$(mapper get-service $OBJECT) 24479f697e0SAnthony Wilson INTERFACE=$STATE_INTERFACE.Host 24579f697e0SAnthony Wilson PROPERTY=CurrentHostState 24679f697e0SAnthony Wilson state_query $SERVICE $OBJECT $INTERFACE $PROPERTY 24779f697e0SAnthony Wilson ;; 24886cffd9cSAlexander Filippov osstate) 24986cffd9cSAlexander Filippov OBJECT=$STATE_OBJECT/host0 25086cffd9cSAlexander Filippov SERVICE=$(mapper get-service $OBJECT) 25186cffd9cSAlexander Filippov INTERFACE=$STATE_INTERFACE.OperatingSystem.Status 25286cffd9cSAlexander Filippov PROPERTY=OperatingSystemState 25386cffd9cSAlexander Filippov state_query $SERVICE $OBJECT $INTERFACE $PROPERTY 25486cffd9cSAlexander Filippov ;; 25579f697e0SAnthony Wilson state|status) 25686cffd9cSAlexander Filippov for query in bmcstate chassisstate hoststate bootprogress osstate 25779f697e0SAnthony Wilson do 25879f697e0SAnthony Wilson handle_cmd $query 25979f697e0SAnthony Wilson done 26079f697e0SAnthony Wilson ;; 26150c5f88dSAnthony Wilson bootprogress) 26250c5f88dSAnthony Wilson OBJECT=$STATE_OBJECT/host0 26350c5f88dSAnthony Wilson SERVICE=$(mapper get-service $OBJECT) 26450c5f88dSAnthony Wilson INTERFACE=$STATE_INTERFACE.Boot.Progress 26550c5f88dSAnthony Wilson PROPERTY=BootProgress 26650c5f88dSAnthony Wilson state_query $SERVICE $OBJECT $INTERFACE $PROPERTY 26750c5f88dSAnthony Wilson ;; 2680f35983dSAnthony Wilson power) 2690f35983dSAnthony Wilson OBJECT=/org/openbmc/control/power0 2700f35983dSAnthony Wilson SERVICE=$(mapper get-service $OBJECT) 2710f35983dSAnthony Wilson INTERFACE=org.openbmc.control.Power 2720f35983dSAnthony Wilson for property in pgood state pgood_timeout 2730f35983dSAnthony Wilson do 2740f35983dSAnthony Wilson # get_property can potentially return several 2750f35983dSAnthony Wilson # different formats of values, so we do the parsing outside 2760f35983dSAnthony Wilson # of get_property depending on the query. These queries 2770f35983dSAnthony Wilson # return 'i VALUE' formatted strings. 2780f35983dSAnthony Wilson STATE=$(get_property $SERVICE $OBJECT $INTERFACE $property \ 2790f35983dSAnthony Wilson | sed 's/i[ ^I]*//') 2800f35983dSAnthony Wilson printf "%s = %s\n" $property $STATE 2810f35983dSAnthony Wilson done 2820f35983dSAnthony Wilson ;; 283189cf248SAnthony Wilson chassiskill) 284189cf248SAnthony Wilson /usr/libexec/chassiskill 285189cf248SAnthony Wilson ;; 286*a65d30d1SVishwanatha Subbanna hostrebootoff) 2876d3a2c54SVishwanatha Subbanna OBJECT=$CONTROL_OBJECT/host0/auto_reboot 2886d3a2c54SVishwanatha Subbanna SERVICE=$(mapper get-service $OBJECT) 2896d3a2c54SVishwanatha Subbanna INTERFACE=$CONTROL_INTERFACE.Boot.RebootPolicy 2906d3a2c54SVishwanatha Subbanna PROPERTY=AutoReboot 2916d3a2c54SVishwanatha Subbanna VALUE=false 2926d3a2c54SVishwanatha Subbanna set_property $SERVICE $OBJECT $INTERFACE $PROPERTY "b" $VALUE 2936d3a2c54SVishwanatha Subbanna ;; 294*a65d30d1SVishwanatha Subbanna hostrebooton) 2956d3a2c54SVishwanatha Subbanna OBJECT=$CONTROL_OBJECT/host0/auto_reboot 2966d3a2c54SVishwanatha Subbanna SERVICE=$(mapper get-service $OBJECT) 2976d3a2c54SVishwanatha Subbanna INTERFACE=$CONTROL_INTERFACE.Boot.RebootPolicy 2986d3a2c54SVishwanatha Subbanna PROPERTY=AutoReboot 2996d3a2c54SVishwanatha Subbanna VALUE=true 3006d3a2c54SVishwanatha Subbanna set_property $SERVICE $OBJECT $INTERFACE $PROPERTY "b" $VALUE 3016d3a2c54SVishwanatha Subbanna ;; 302*a65d30d1SVishwanatha Subbanna bmcrebootoff) 303*a65d30d1SVishwanatha Subbanna disable_bmc_reboot 304*a65d30d1SVishwanatha Subbanna ;; 305*a65d30d1SVishwanatha Subbanna bmcrebooton) 306*a65d30d1SVishwanatha Subbanna enable_bmc_reboot 307*a65d30d1SVishwanatha Subbanna ;; 3087a787dd7SVishwanatha Subbanna recoveryoff) 309*a65d30d1SVishwanatha Subbanna handle_cmd hostrebootoff 310*a65d30d1SVishwanatha Subbanna handle_cmd bmcrebootoff 3117a787dd7SVishwanatha Subbanna mask_systemd_target $HOST_TIMEOUT_TARGET 31284b3b29eSVishwanatha Subbanna mask_systemd_target $HOST_CRASH_TARGET 3137a787dd7SVishwanatha Subbanna ;; 3147a787dd7SVishwanatha Subbanna recoveryon) 315*a65d30d1SVishwanatha Subbanna handle_cmd hostrebooton 316*a65d30d1SVishwanatha Subbanna handle_cmd bmcrebooton 3177a787dd7SVishwanatha Subbanna unmask_systemd_target $HOST_TIMEOUT_TARGET 31884b3b29eSVishwanatha Subbanna unmask_systemd_target $HOST_CRASH_TARGET 3197a787dd7SVishwanatha Subbanna ;; 32079f697e0SAnthony Wilson *) 321ea87db40SAnthony Wilson print_usage_err "Invalid command '$1'" 32279f697e0SAnthony Wilson ;; 32379f697e0SAnthony Wilson esac 32479f697e0SAnthony Wilson} 32579f697e0SAnthony Wilson 326ea87db40SAnthony Wilsonfor arg in "$@"; do 327ea87db40SAnthony Wilson case $arg in 328acf54d08SAnthony Wilson -w|--wait) 329acf54d08SAnthony Wilson G_WAIT=30 330acf54d08SAnthony Wilson continue 331acf54d08SAnthony Wilson ;; 332ea87db40SAnthony Wilson -h|--help) 333ea87db40SAnthony Wilson print_help 334ea87db40SAnthony Wilson ;; 33560c3ac8cSAndrew Jeffery -v|--verbose) 33660c3ac8cSAndrew Jeffery G_VERBOSE=y 33760c3ac8cSAndrew Jeffery ;; 338ea87db40SAnthony Wilson -*) 339ea87db40SAnthony Wilson print_usage_err "Unknown option: $arg" 340ea87db40SAnthony Wilson ;; 341ea87db40SAnthony Wilson *) 342acf54d08SAnthony Wilson G_ORIG_CMD=$arg 343ea87db40SAnthony Wilson handle_cmd $arg 344ea87db40SAnthony Wilson break 345ea87db40SAnthony Wilson ;; 346ea87db40SAnthony Wilson esac 347ea87db40SAnthony Wilsondone 348