Closed pettermahlen closed 2 years ago
You're seeing heap corruption. The heap corruption does not appear to be from the current call to catchExceptionOfKind
shown on the stack or the current machMessageHandler on Thread 3. It is most likely due to a previous call.
My guess – given that the log file includes multiple "Fatal error:" messages – is that you've hit a previous Mach Exception that was successfully caught by CwlPreconditionTesting and this has unwound the stack over your code (i.e. a "catch") but this unwinding has left memory in an inconsistent state.
This might not be a fixable problem. You would need to understand which throw is leaving memory inconsistent and reorder operations around it so it is resilient to an exception being thrown through it.
Hmm... Not sure I quite understand - are you talking about reordering Swift operations in the test code, in the production code, or in the CwlPreconditionTesting library? It doesn't look to me like I'm doing something that should potentially be harmful - this is apparently caused by multiple tests that check for exceptions, and that should be normal.
Is the problem potentially related to fatalError
returning Never
, thus AFAIU permitting the compiler to optimise-away any cleanup happening after it? Would love to dig a little deeper into how CwlPreconditionTesting works if you have a quick pointer to the relevant code to look at.
CwlPreconditionTesting throws an Objective-C exception which unwinds the stack (ignores everything and abruptly jumps to the catch location). Code needs to be "exception safe" for this to work and Swift's automatic reference counting is not exception safe (you can look up problems with exception safe code in Objective-C, Swift or C++, the issues involved are fairly similar). With CwlPreconditionTesting, you will almost always get memory leaks (as the release to balance any retained memory is skipped) but it's double free problems (retains skipped and memory getting freed while still in use) that tends to cause memory corruption. Without careful memory analysis though, I can't precisely guess what's causing your problems.
It's been a while on this and it doesn't look like this is a widespread issue. I'm going to close the issue. It is certainly possible to trigger memory corruption across exception frames. That's why Swift doesn't officially support exceptions. It's just something you need to recode to avoid.
Not entirely sure that this library is the cause, but it seems likely. Here's a partial crash log from one instance:
and another thread:
It feels like
malloc
shouldn't be crashe-able from a pure Swift application like the one that's being tested. And there are two different threads runningCwlCatchBadInstruction
code - is it possible that there's a threading issue somewhere? The code being tested uses a custom concurrent DispatchQueue.