Why not(panic = "unwind") instead of panic = "abort"?

I stumbled upon the implementation of PoisonError<T> in the standard library and am curious about the motivation for writing the conditional compilation as #[cfg(not(panic = "unwind"))] instead of #[cfg(panic = "abort")]:

Given that more panic strategies may be added:

Key-value option set depending on the panic strategy. Note that more values may be added in the future.

The _never: !, field suggests that poisoning should not occur when the panic strategy is abort, given that it prevents creation of the PoisonError type.

There is an implicit assumption that no new unwind-like panic strategies will be added. While likely, this is not guaranteed. Wouldn't the code be better written with #[cfg(panic = "abort")]?

What would one do when writing a library today where this matters?

1 Like

There is also an "immediate abort" that's unstable. My guess is it's to include that as well.

1 Like

One reason might be that, if such strategy is added, one would like to look at PoisonError to check if it needs to be changed somehow. Currently, it will be forced by compiler errors. With cfg(panic = "abort), it could be missed.

I can find a feature for the standard library called panic_immediate_abort that avoids printing the error on panic. It is not clear to me wheter it is (going to be) a different panic strategy.

I would also say there should be a compilation error. Looking at the following however:

The error message in the panic doesn't agree with the code. If we add a strategy "unwind-2", it seems like the code here panics at run-time. There might be another place in the code that won't compile that I am not seeing.

panic_immediate_abort doesn't affect cfg(panic). You normally use it together with -Cpanic=abort. I think you could technically use it with -Cpanic=unwind, but if that is indeed allowed, that would be unsound as catch_unwind wouldn't catch foreign exceptions.

2 Likes

The standard library is allowed to be sloppier with stuff like this, because it can assume that the PoisonError code will be changed at the same time that a new cfg value gets added.