Skip to content
Merged
Changes from 1 commit
Commits
Show all changes
19 commits
Select commit Hold shift + click to select a range
ca95d4b
Enable NativeAOT osx-arm64 builds
filipnavara Aug 31, 2022
35a40f0
Restrict alignment in VirtualReserveInner
filipnavara Aug 31, 2022
387b31b
Fix generation and handling of compact unwinding info on osx-arm64
filipnavara Aug 31, 2022
50eb6f6
Fix PC check in findFDE in DWARF CFI unwinding
filipnavara Sep 6, 2022
cb81686
Handle MAP_JIT for P/Invoke on osx-arm64
filipnavara Sep 7, 2022
69fd921
Handle P/Invoke with MAP_JIT on osx-arm64
filipnavara Sep 7, 2022
b05ba08
Fix incorrect OS_PAGE_SIZE definition
filipnavara Sep 7, 2022
8742268
Fix TLS register trashing
filipnavara Sep 8, 2022
92a7164
Fix memory trashing caused by incorrect PREPARE_EXTERNAL_VAR_INDIRECT…
filipnavara Sep 8, 2022
6325ba7
Ignore ESRCH in PalHijack (thread is already gone)
filipnavara Sep 8, 2022
125bed7
Make CompactUnwinder_* parametrized with registry class
filipnavara Sep 8, 2022
817b10c
Remove custom CompactUnwinder
filipnavara Sep 8, 2022
f44843f
Update src/coreclr/nativeaot/Runtime/CommonMacros.h
filipnavara Sep 8, 2022
3308493
Update llvm-libunwind-version.txt
filipnavara Sep 8, 2022
8b9d0dc
Fix initial alignment for __module_initializer. ARM64 requires absolu…
filipnavara Sep 9, 2022
9d73bfa
Allow publishing with the osx-arm64 RID
filipnavara Sep 9, 2022
5244049
Use pointer sized alignment for fat function pointers since they cont…
filipnavara Sep 9, 2022
59b79b3
Remove __builtin___clear_cache, it was already fixed
filipnavara Sep 11, 2022
d8c7ee0
Update src/coreclr/nativeaot/Runtime/unix/PalRedhawkUnix.cpp
jkotas Sep 11, 2022
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Prev Previous commit
Next Next commit
Remove custom CompactUnwinder
  • Loading branch information
filipnavara committed Sep 11, 2022
commit 817b10cea5cb957724eba59c93c71b13b485437a
216 changes: 14 additions & 202 deletions src/coreclr/nativeaot/Runtime/unix/UnwindHelpers.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -28,10 +28,12 @@

#if defined(TARGET_AMD64)
using libunwind::Registers_x86_64;
using libunwind::CompactUnwinder_x86_64;
#elif defined(TARGET_ARM)
using libunwind::Registers_arm;
#elif defined(TARGET_ARM64)
using libunwind::Registers_arm64;
using libunwind::CompactUnwinder_arm64;
#elif defined(TARGET_X86)
using libunwind::Registers_x86;
#else
Expand Down Expand Up @@ -501,6 +503,8 @@ struct Registers_REGDISPLAY : REGDISPLAY
uint64_t getIP() const { return IP;}
void setIP(uint64_t value, uint64_t location)
{ IP = value; pIP = (PTR_UIntNative)location; }
uint64_t getFP() const { return *pFP;}
void setFP(uint64_t value, uint64_t location) { pFP = (PTR_UIntNative)location;}
};

inline bool Registers_REGDISPLAY::validRegister(int num) const {
Expand Down Expand Up @@ -755,206 +759,6 @@ void Registers_REGDISPLAY::setVectorRegister(int num, libunwind::v128 value)
D[num] = (uint64_t)value.vec[2] << 32 | (uint64_t)value.vec[3];
}

/// CompactUnwinder_arm64 uses a compact unwind info to virtually "step" (aka
/// unwind) by modifying a Registers_arm64 register set
template <typename A>
class CompactUnwinder_arm64 {
public:

static int stepWithCompactEncoding(compact_unwind_encoding_t compactEncoding,
uint64_t functionStart, A &addressSpace,
Registers_REGDISPLAY &registers);

private:
typename A::pint_t pint_t;

static int
stepWithCompactEncodingFrame(compact_unwind_encoding_t compactEncoding,
uint64_t functionStart, A &addressSpace,
Registers_REGDISPLAY &registers);
static int stepWithCompactEncodingFrameless(
compact_unwind_encoding_t compactEncoding, uint64_t functionStart,
A &addressSpace, Registers_REGDISPLAY &registers);
};

template <typename A>
int CompactUnwinder_arm64<A>::stepWithCompactEncoding(
compact_unwind_encoding_t compactEncoding, uint64_t functionStart,
A &addressSpace, Registers_REGDISPLAY &registers) {
switch (compactEncoding & UNWIND_ARM64_MODE_MASK) {
case UNWIND_ARM64_MODE_FRAME:
return stepWithCompactEncodingFrame(compactEncoding, functionStart,
addressSpace, registers);
case UNWIND_ARM64_MODE_FRAMELESS:
return stepWithCompactEncodingFrameless(compactEncoding, functionStart,
addressSpace, registers);
}
_LIBUNWIND_ABORT("invalid compact unwind encoding");
}

template <typename A>
int CompactUnwinder_arm64<A>::stepWithCompactEncodingFrameless(
compact_unwind_encoding_t encoding, uint64_t, A &addressSpace,
Registers_REGDISPLAY &registers) {
uint32_t stackSize =
16 * EXTRACT_BITS(encoding, UNWIND_ARM64_FRAMELESS_STACK_SIZE_MASK);

uint64_t savedRegisterLoc = registers.getSP() + stackSize;

if (encoding & UNWIND_ARM64_FRAME_X19_X20_PAIR) {
registers.setRegister(UNW_AARCH64_X19, addressSpace.get64(savedRegisterLoc), savedRegisterLoc);
savedRegisterLoc -= 8;
registers.setRegister(UNW_AARCH64_X20, addressSpace.get64(savedRegisterLoc), savedRegisterLoc);
savedRegisterLoc -= 8;
}
if (encoding & UNWIND_ARM64_FRAME_X21_X22_PAIR) {
registers.setRegister(UNW_AARCH64_X21, addressSpace.get64(savedRegisterLoc), savedRegisterLoc);
savedRegisterLoc -= 8;
registers.setRegister(UNW_AARCH64_X22, addressSpace.get64(savedRegisterLoc), savedRegisterLoc);
savedRegisterLoc -= 8;
}
if (encoding & UNWIND_ARM64_FRAME_X23_X24_PAIR) {
registers.setRegister(UNW_AARCH64_X23, addressSpace.get64(savedRegisterLoc), savedRegisterLoc);
savedRegisterLoc -= 8;
registers.setRegister(UNW_AARCH64_X24, addressSpace.get64(savedRegisterLoc), savedRegisterLoc);
savedRegisterLoc -= 8;
}
if (encoding & UNWIND_ARM64_FRAME_X25_X26_PAIR) {
registers.setRegister(UNW_AARCH64_X25, addressSpace.get64(savedRegisterLoc), savedRegisterLoc);
savedRegisterLoc -= 8;
registers.setRegister(UNW_AARCH64_X26, addressSpace.get64(savedRegisterLoc), savedRegisterLoc);
savedRegisterLoc -= 8;
}
if (encoding & UNWIND_ARM64_FRAME_X27_X28_PAIR) {
registers.setRegister(UNW_AARCH64_X27, addressSpace.get64(savedRegisterLoc), savedRegisterLoc);
savedRegisterLoc -= 8;
registers.setRegister(UNW_AARCH64_X28, addressSpace.get64(savedRegisterLoc), savedRegisterLoc);
savedRegisterLoc -= 8;
}

if (encoding & UNWIND_ARM64_FRAME_D8_D9_PAIR) {
registers.setFloatRegister(UNW_AARCH64_V8,
addressSpace.getDouble(savedRegisterLoc));
savedRegisterLoc -= 8;
registers.setFloatRegister(UNW_AARCH64_V9,
addressSpace.getDouble(savedRegisterLoc));
savedRegisterLoc -= 8;
}
if (encoding & UNWIND_ARM64_FRAME_D10_D11_PAIR) {
registers.setFloatRegister(UNW_AARCH64_V10,
addressSpace.getDouble(savedRegisterLoc));
savedRegisterLoc -= 8;
registers.setFloatRegister(UNW_AARCH64_V11,
addressSpace.getDouble(savedRegisterLoc));
savedRegisterLoc -= 8;
}
if (encoding & UNWIND_ARM64_FRAME_D12_D13_PAIR) {
registers.setFloatRegister(UNW_AARCH64_V12,
addressSpace.getDouble(savedRegisterLoc));
savedRegisterLoc -= 8;
registers.setFloatRegister(UNW_AARCH64_V13,
addressSpace.getDouble(savedRegisterLoc));
savedRegisterLoc -= 8;
}
if (encoding & UNWIND_ARM64_FRAME_D14_D15_PAIR) {
registers.setFloatRegister(UNW_AARCH64_V14,
addressSpace.getDouble(savedRegisterLoc));
savedRegisterLoc -= 8;
registers.setFloatRegister(UNW_AARCH64_V15,
addressSpace.getDouble(savedRegisterLoc));
savedRegisterLoc -= 8;
}

// subtract stack size off of sp
registers.setSP(savedRegisterLoc, 0);

// set pc to be value in lr
registers.setIP(registers.getRegister(UNW_AARCH64_LR), 0);

return UNW_STEP_SUCCESS;
}

template <typename A>
int CompactUnwinder_arm64<A>::stepWithCompactEncodingFrame(
compact_unwind_encoding_t encoding, uint64_t, A &addressSpace,
Registers_REGDISPLAY &registers) {
uint64_t savedRegisterLoc = registers.GetFP() - 8;

if (encoding & UNWIND_ARM64_FRAME_X19_X20_PAIR) {
registers.setRegister(UNW_AARCH64_X19, addressSpace.get64(savedRegisterLoc), savedRegisterLoc);
savedRegisterLoc -= 8;
registers.setRegister(UNW_AARCH64_X20, addressSpace.get64(savedRegisterLoc), savedRegisterLoc);
savedRegisterLoc -= 8;
}
if (encoding & UNWIND_ARM64_FRAME_X21_X22_PAIR) {
registers.setRegister(UNW_AARCH64_X21, addressSpace.get64(savedRegisterLoc), savedRegisterLoc);
savedRegisterLoc -= 8;
registers.setRegister(UNW_AARCH64_X22, addressSpace.get64(savedRegisterLoc), savedRegisterLoc);
savedRegisterLoc -= 8;
}
if (encoding & UNWIND_ARM64_FRAME_X23_X24_PAIR) {
registers.setRegister(UNW_AARCH64_X23, addressSpace.get64(savedRegisterLoc), savedRegisterLoc);
savedRegisterLoc -= 8;
registers.setRegister(UNW_AARCH64_X24, addressSpace.get64(savedRegisterLoc), savedRegisterLoc);
savedRegisterLoc -= 8;
}
if (encoding & UNWIND_ARM64_FRAME_X25_X26_PAIR) {
registers.setRegister(UNW_AARCH64_X25, addressSpace.get64(savedRegisterLoc), savedRegisterLoc);
savedRegisterLoc -= 8;
registers.setRegister(UNW_AARCH64_X26, addressSpace.get64(savedRegisterLoc), savedRegisterLoc);
savedRegisterLoc -= 8;
}
if (encoding & UNWIND_ARM64_FRAME_X27_X28_PAIR) {
registers.setRegister(UNW_AARCH64_X27, addressSpace.get64(savedRegisterLoc), savedRegisterLoc);
savedRegisterLoc -= 8;
registers.setRegister(UNW_AARCH64_X28, addressSpace.get64(savedRegisterLoc), savedRegisterLoc);
savedRegisterLoc -= 8;
}

if (encoding & UNWIND_ARM64_FRAME_D8_D9_PAIR) {
registers.setFloatRegister(UNW_AARCH64_V8,
addressSpace.getDouble(savedRegisterLoc));
savedRegisterLoc -= 8;
registers.setFloatRegister(UNW_AARCH64_V9,
addressSpace.getDouble(savedRegisterLoc));
savedRegisterLoc -= 8;
}
if (encoding & UNWIND_ARM64_FRAME_D10_D11_PAIR) {
registers.setFloatRegister(UNW_AARCH64_V10,
addressSpace.getDouble(savedRegisterLoc));
savedRegisterLoc -= 8;
registers.setFloatRegister(UNW_AARCH64_V11,
addressSpace.getDouble(savedRegisterLoc));
savedRegisterLoc -= 8;
}
if (encoding & UNWIND_ARM64_FRAME_D12_D13_PAIR) {
registers.setFloatRegister(UNW_AARCH64_V12,
addressSpace.getDouble(savedRegisterLoc));
savedRegisterLoc -= 8;
registers.setFloatRegister(UNW_AARCH64_V13,
addressSpace.getDouble(savedRegisterLoc));
savedRegisterLoc -= 8;
}
if (encoding & UNWIND_ARM64_FRAME_D14_D15_PAIR) {
registers.setFloatRegister(UNW_AARCH64_V14,
addressSpace.getDouble(savedRegisterLoc));
savedRegisterLoc -= 8;
registers.setFloatRegister(UNW_AARCH64_V15,
addressSpace.getDouble(savedRegisterLoc));
savedRegisterLoc -= 8;
}

uint64_t fp = registers.GetFP();
// fp points to old fp
registers.setRegister(UNW_ARM64_FP, addressSpace.get64(fp), fp);
// old sp is fp less saved fp and lr
registers.setSP(fp + 16, 0);
// pop return address into pc
registers.setIP(addressSpace.get64(fp + 8), fp + 8);

return UNW_STEP_SUCCESS;
}

#endif // TARGET_ARM64

bool DoTheStep(uintptr_t pc, UnwindInfoSections uwInfoSections, REGDISPLAY *regs)
Expand All @@ -980,9 +784,17 @@ bool DoTheStep(uintptr_t pc, UnwindInfoSections uwInfoSections, REGDISPLAY *regs
unw_proc_info_t procInfo;
uc.getInfo(&procInfo);

#if defined(_LIBUNWIND_TARGET_AARCH64)
#if defined(TARGET_ARM64)
if ((procInfo.format & UNWIND_ARM64_MODE_MASK) != UNWIND_ARM64_MODE_DWARF) {
CompactUnwinder_arm64<LocalAddressSpace> compactInst;
CompactUnwinder_arm64<LocalAddressSpace, Registers_REGDISPLAY> compactInst;
int stepRet = compactInst.stepWithCompactEncoding(procInfo.format, pc, _addressSpace, *(Registers_REGDISPLAY*)regs);
return stepRet == UNW_STEP_SUCCESS;
} else {
dwarfOffsetHint = procInfo.format & UNWIND_ARM64_DWARF_SECTION_OFFSET;
}
#elif defined(TARGET_AMD64)
if ((procInfo.format & UNWIND_X86_64_MODE_MASK) != UNWIND_X86_64_MODE_DWARF) {
CompactUnwinder_x86_64<LocalAddressSpace, Registers_REGDISPLAY> compactInst;
int stepRet = compactInst.stepWithCompactEncoding(procInfo.format, pc, _addressSpace, *(Registers_REGDISPLAY*)regs);
return stepRet == UNW_STEP_SUCCESS;
} else {
Expand Down