BASH:更改陷阱中的退出状态

BASH:更改陷阱中的退出状态

我可以为陷阱处理程序中的 shell 脚本分配不同的退出状态吗?

通过反复试验,我发现调用exit退出trap状态是可以改变的。普通命令,无论失败还是成功,都不会改变退出状态。

现在我想知道,我是否可以依赖这种行为,或者这是一些实现怪癖?

我一直试图找到一些关于此的文档,但无济于事。

测试脚本:

#!/bin/bash
function handler {
    # a successful command won't change script exit status
    echo handler, status=$1
    # badcommand won't change script exit status
    #badcommand
    # exit will change script exit status
    #exit 23
}
trap 'handler $?' EXIT
#badcommand

用法:

./trap_test.sh; echo status_out=$?

答案1

我发现[通过]调用exittrap 可以改变退出状态。普通命令,无论失败还是成功,都不会改变退出状态。现在我想知道,我是否可以依赖这种行为,或者这是一些实现怪癖?

是的,您可以依赖它,并且它已记录在 shell 中标准:

名称
exit- 导致 shell 退出
...
描述
...
陷阱EXIT应在 shell 终止之前执行,除非exit在该陷阱本身中调用该实用程序,在这种情况下 shell 应立即退出。
...
退出状态如果指定,
退出状态应为,但如果不是无符号十进制整数或大于 ,则n行为未指定。否则,该值应为最后执行的命令的退出值,如果没有执行命令则为零。n255exit在陷阱操作中执行时,最后一个命令被认为是紧接在陷阱操作之前执行的命令。

(同样的事情return

当没有exit命令但exit设置了陷阱时,应应用以下内容:

除非另有说明,命令的退出状态应为该命令执行的最后一个简单命令的退出状态。

以及关于复合命令、顺序列表等的所有规则,这些规则对于EXIT陷阱的存在没有特殊的例外。

答案2

我没有看到手册页提到它,所以除了查看代码之外,实验似乎是弄清楚会发生什么的最好方法。

对我来说,退出陷阱并不总是改变退出状态是有意义的:脚本可能希望在退出时通过陷阱进行一些清理,但不会让清理扰乱主脚本设置的退出状态。而且,正如您所说,陷阱可以exit再次运行以设置所需的值。

例如,如果你有这个:

tmpfile=$(mktemp)
trap 'rm -f "$tmpfile"' EXIT
# something
exit 1

可能rm会将退出状态重置为零,这似乎没什么用。

相关内容