diff --git a/lib/MC/MCWin64EH.cpp b/lib/MC/MCWin64EH.cpp index 5268d2752d8..0724b109e1a 100644 --- a/lib/MC/MCWin64EH.cpp +++ b/lib/MC/MCWin64EH.cpp @@ -468,10 +468,10 @@ static void ARM64EmitUnwindInfo(MCStreamer &streamer, WinEH::FrameInfo *info) { info->Symbol = Label; uint32_t FuncLength = 0x0; - FuncLength = (uint32_t)GetAbsDifference(streamer, info->FuncletOrFuncEnd, - info->Begin); - if (FuncLength) - FuncLength /= 4; + if (info->FuncletOrFuncEnd) + FuncLength = (uint32_t)GetAbsDifference(streamer, info->FuncletOrFuncEnd, + info->Begin); + FuncLength /= 4; uint32_t PrologCodeBytes = ARM64CountOfUnwindCodes(info->Instructions); uint32_t TotalCodeBytes = PrologCodeBytes; diff --git a/test/MC/AArch64/seh.s b/test/MC/AArch64/seh.s new file mode 100644 index 00000000000..ca862cb4e54 --- /dev/null +++ b/test/MC/AArch64/seh.s @@ -0,0 +1,84 @@ +// This test checks that the SEH directives emit the correct unwind data. + +// RUN: llvm-mc -triple aarch64-pc-win32 -filetype=obj %s | llvm-readobj -s -r | FileCheck %s + +// CHECK: Sections [ +// CHECK: Section { +// CHECK: Name: .text +// CHECK: RelocationCount: 0 +// CHECK: Characteristics [ +// CHECK-NEXT: ALIGN_4BYTES +// CHECK-NEXT: CNT_CODE +// CHECK-NEXT: MEM_EXECUTE +// CHECK-NEXT: MEM_READ +// CHECK-NEXT: ] +// CHECK-NEXT: } +// CHECK: Section { +// CHECK: Name: .xdata +// CHECK: RawDataSize: 24 +// CHECK: RelocationCount: 1 +// CHECK: Characteristics [ +// CHECK-NEXT: ALIGN_4BYTES +// CHECK-NEXT: CNT_INITIALIZED_DATA +// CHECK-NEXT: MEM_READ +// CHECK-NEXT: ] +// CHECK-NEXT: } +// CHECK: Section { +// CHECK: Name: .pdata +// CHECK: RelocationCount: 6 +// CHECK: Characteristics [ +// CHECK-NEXT: ALIGN_4BYTES +// CHECK-NEXT: CNT_INITIALIZED_DATA +// CHECK-NEXT: MEM_READ +// CHECK-NEXT: ] +// CHECK-NEXT: } +// CHECK-NEXT: ] + +// CHECK-NEXT: Relocations [ +// CHECK-NEXT: Section (4) .xdata { +// CHECK-NEXT: 0x8 IMAGE_REL_ARM64_ADDR32NB __C_specific_handler +// CHECK-NEXT: } +// CHECK-NEXT: Section (5) .pdata { +// CHECK-NEXT: 0x0 IMAGE_REL_ARM64_ADDR32NB func +// CHECK-NEXT: 0x4 IMAGE_REL_ARM64_ADDR32NB .xdata +// CHECK-NEXT: 0x8 IMAGE_REL_ARM64_ADDR32NB func +// CHECK-NEXT: 0xC IMAGE_REL_ARM64_ADDR32NB .xdata +// CHECK-NEXT: 0x10 IMAGE_REL_ARM64_ADDR32NB smallFunc +// CHECK-NEXT: 0x14 IMAGE_REL_ARM64_ADDR32NB .xdata +// CHECK-NEXT: } +// CHECK-NEXT: ] + + + .text + .globl func + .def func + .scl 2 + .type 32 + .endef + .seh_proc func +func: + sub sp, sp, #24 + .seh_stackalloc 24 + mov x29, sp + .seh_endprologue + .seh_handler __C_specific_handler, @except + .seh_handlerdata + .long 0 + .text + .seh_startchained + .seh_endprologue + .seh_endchained + add sp, sp, #24 + ret + .seh_endproc + +// Test emission of small functions. + .globl smallFunc + .def smallFunc + .scl 2 + .type 32 + .endef + .seh_proc smallFunc +smallFunc: + ret + .seh_endproc