知识卡片
Recover有边界
内容
recover 只有在延迟调用中直接执行才有效,它恢复的是当前 panic 展开的流程。把它放在边界层使用,可以隔离崩溃;滥用则会掩盖真正的程序不变量破坏。
参考来源
- 位置:《Go语言底层原理剖析》第11章《异常与异常捕获》11.3节《panic与recover嵌套》及11.5节《recover底层原理》
- 结论依据:原文用嵌套 panic 的例子说明"内层recover不能捕获外层的panic"——"如果panic发生在函数b或函数fb中,则情况会有所不同……内部的recover只能捕获由当前函数或其子函数触发的panic,而不能触发上层的panic";11.5节进一步用 argp==uintptr(p.argp) 说明 recover 是通过比较调用者参数地址判断 panic 是否匹配,因此可以推出"recover 只在直接的 defer 调用中生效、且只能恢复当前层 panic"的结论。
- 原始内容:panic会遍历defer链并调用,那么如果在defer函数中发生了panic会怎么样呢?……如果panic发生在函数b或函数fb中,则情况会有所不同。例如,将函数fb改写如下,内部的recover只能捕获由当前函数或其子函数触发的panic,而不能触发上层的panic……gorecover函数的参数argp为其调用者函数的参数地址,而p.argp为发生panic时defer函数的参数地址。语句argp==uintptr(p.argp)可用于判断panic和recover是否匹配,这是因为内层recover不能捕获外层的panic。