Executing (exit 1);
is the simplest way of triggering an ERR
trap. It will also trigger immediate exit if set -e
is in effect. (Triggering the error condition requires a command to fail; exit
with a failure value in a subshell causes the subshell to fail.)
exit 1;
will do neither of those things.
So {(exit 1); exit 1;}
can be used to first produce the ERR
trap, which might do something useful for debugging purposes, and then terminate the script with an error indication.
But that's not what is going on in autoconf
files. autoconf
scripts rely on the EXIT
trap in order to clean up temporary files created during the run. Most shells, including bash
will set the status from the value provided in the exit
command before calling the EXIT
trap. That could allow the EXIT
trap to detect whether it was invoked from an error or from normal termination, and it also allows it to ensure that the exit status is correctly set at the end of the trap operation.
However, apparently some shells do not co-operate. Here's a quote from the autoconf
manual:
Some shell scripts, such as those generated by autoconf
, use a trap to clean up before exiting. If the last shell command exited with nonzero status, the trap also exits with nonzero status so that the invoker can tell that an error occurred.
Unfortunately, in some shells, such as Solaris /bin/sh
, an exit trap ignores the exit command's argument. In these shells, a trap cannot determine whether it was invoked by plain exit or by exit 1. Instead of calling exit directly, use the AC_MSG_ERROR
macro that has a workaround for this problem.
The workaround is to make sure that $?
has the exit status before the exit
command is executed, so that it will definitely have that value when the EXIT
trap is executed. And, indeed, it is the AC_MSG_ERROR
macro which inserts that curious code, complete with redundant braces.