Files
Jeaye Wilkerson 7d23f0d618 [ORC] Fix malformed Mach-O __unwind_info tables (#217781)
The malformed tables are produced by `JITLink` after compact-unwind
record merging.

`CompactUnwindManager::mergeRecords()` coalesces adjacent function
records with identical mergeable encodings. When the final raw record is
merged away, `writeIndexes()` generates the top-level index terminator
from the final remaining record instead of the final original function.
This truncates the final index range.

On macOS arm64, libunwind resolves a PC in the merged-away final
function through the terminator entry. Its second-level-page offset is
zero by design, causing libunwind to interpret the `__unwind_info`
header as a second-level page and report:

```
libunwind: malformed __unwind_info ... bad second level page
```

The fix retains the final raw function symbol before records are merged
and uses its post-allocation range end when writing the terminator index
entry. This keeps the compact-unwind index range valid for all merged
functions.

To test this, there's a new ORC Darwin test that:

1. Creates adjacent mergeable compact-unwind records.
2. Throws from the final merged function.
3. Catches the exception in `main`.

The test reproduces the malformed table failure before the fix and exits
successfully with the fix.

----
Note that I used Github copilot to diagnose and fix this issue. I am not
familiar with this code and so I don't know for certain that this change
makes sense. However, I do know that it fixes the issues I'm seeing with
jank on macOS and that the provided test fails on main and passes with
this change.

(cherry picked from commit 3700e7cebbae20566f84025ecf5a40ab7e7b658b)
2026-09-05 09:12:04 +02:00
..