Skip to content

Files

Latest commit

 

History

History
50 lines (32 loc) · 1.64 KB

SC2181.md

File metadata and controls

50 lines (32 loc) · 1.64 KB

Pattern: Use of indirect exit code check

Issue: -

Description

Running a command and then checking its exit status $? against 0 is redundant.

Instead of just checking the exit code of a command, it checks the exit code of a command (e.g. [) that checks the exit code of a command.

Apart from the redundancy, there are other reasons to avoid this pattern:

  • Since the command and its status test are decoupled, inserting an innocent command like echo "make finished" after make will cause the if statement to silently start comparing echo's status instead.
  • Scripts that run or are called with set -e aka errexit will exit immediately if the command fails, even though they're followed by a clause that handles failure.
  • The value of $? is overwritten by [/[[, so you can't get the original value in the relevant then/else block (e.g. if somecmd; then echo "Success"; else echo "Failed with $?"; fi).

To check that a command returns success, use if somecommand; then ....

To check that a command returns failure, use if ! somecommand; then ....

To additionally capture output with command substitution: if output=$(somecommand); then ...

This also applies to while/until loops.

Example of incorrect code:

make sometarget

if [ $? -ne 0 ]
then
  echo "Build failed"
fi

Example of correct code:

if ! make sometarget
then
  echo "Build failed"
fi

Exceptions

The default Solaris 10 bourne shell does not support '!' outside of the test command (if ! somecommand; then ... returns !: not found)

Further Reading