This is an archive of the discontinued LLVM Phabricator instance.

[lld/mac] Don't fold UNWIND_X86_64_MODE_STACK_IND unwind entries
ClosedPublic

Authored by thakis on Jun 26 2021, 7:46 AM.

Details

Summary

libunwind uses unwind info to find the function address belonging
to the current instruction pointer. libunwind/src/CompactUnwinder.hpp's
step functions read functionStart for UNWIND_X86_64_MODE_STACK_IND
(and for nothing else), so these encodings need a dedicated entry
per function, so that the runtime can get the stacksize off the
subq instrunction in the function's prologue.

This matches ld64.

(CompactUnwinder.hpp from https://opensource.apple.com/source/libunwind/
also reads functionStart in a few more cases if SUPPORT_OLD_BINARIES is set,
but it defaults to 0, and ld64 seems to not worry about these additional
cases.)

Related upstream bug: https://crbug.com/1220175

Diff Detail

Event Timeline

thakis created this revision.Jun 26 2021, 7:46 AM
Herald added a reviewer: gkm. · View Herald Transcript
Herald added a project: Restricted Project. · View Herald Transcript
Herald added a subscriber: pengfei. · View Herald Transcript
thakis requested review of this revision.Jun 26 2021, 7:46 AM

(While working on this, I realized that xcrun unwinddump stack.o prints incorrect stack sizes for 0x03 encodings because it (understandably) doesn't process relocations in the object file, and then it interprets the wrong bytes as subq instruction. On linked images it works. Maybe it should just say "frame size unknown" instead of printing something wrong.)

thakis updated this revision to Diff 354687.Jun 26 2021, 7:50 AM

whitespace adjustments

int3 accepted this revision.Jun 26 2021, 10:11 PM

Thanks!

lld/test/MachO/compact-unwind-stack-ind.s
9–10
This revision is now accepted and ready to land.Jun 26 2021, 10:11 PM
Herald added a project: Restricted Project. · View Herald TranscriptJun 27 2021, 3:49 AM
thakis marked an inline comment as done.Jun 27 2021, 3:52 AM
uabelho added a subscriber: uabelho.Jul 8 2021, 1:44 AM
uabelho added inline comments.
lld/MachO/UnwindInfoSection.cpp
332–333

gcc warns on the comparisons in the two new static_asserts:

lld/MachO/UnwindInfoSection.cpp:345:44: warning: comparison between 'enum<unnamed>' and 'enum<unnamed>' [-Wenum-compare]
353 |   static_assert(UNWIND_X86_64_MODE_MASK == UNWIND_X86_MODE_MASK, "");
    |                                            ^~~~~~~~~~~~~~~~~~~~
lld/MachO/UnwindInfoSection.cpp:346:49: warning: comparison between 'enum<unnamed>' and 'enum<unnamed>' [-Wenum-compare]
354 |   static_assert(UNWIND_X86_64_MODE_STACK_IND == UNWIND_X86_MODE_STACK_IND, "");
    |                                                 ^~~~~~~~~~~~~~~~~~~~~~~~~

Perhaps cast the enum values to some integer type to silence the warnings if we really do want to compare values from different enums? I'm not sure what type to cast it to make it sufficiently large on all platforms though, perhaps intmax_t?