From c0b0e57a87aa5e52e0a45af75fc1cee78d8f2bc6 Mon Sep 17 00:00:00 2001 From: Bob Wilson Date: Tue, 20 Dec 2011 01:29:27 +0000 Subject: [PATCH] Mark ARM eh_sjlj_dispatchsetup as clobbering all registers. Radar 10567930. We used to rely on the *eh_sjlj_setjmp instructions to mark that a function with setjmp/longjmp exception handling clobbers all the registers. But with the recent reorganization of ARM EH, those eh_sjlj_setjmp instructions are expanded away earlier, before PEI can see them to determine what registers to save and restore. Mark the dispatchsetup instruction in the same way, since that instruction cannot be expanded early. This also more accurately reflects when the registers are clobbered. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@146949 91177308-0d34-0410-b5e6-96231b3b80d8 --- lib/Target/ARM/ARMInstrInfo.td | 7 ++- test/CodeGen/ARM/2011-12-19-sjlj-clobber.ll | 55 +++++++++++++++++++++ 2 files changed, 60 insertions(+), 2 deletions(-) create mode 100644 test/CodeGen/ARM/2011-12-19-sjlj-clobber.ll diff --git a/lib/Target/ARM/ARMInstrInfo.td b/lib/Target/ARM/ARMInstrInfo.td index 516a0801ae3..d4dc5615882 100644 --- a/lib/Target/ARM/ARMInstrInfo.td +++ b/lib/Target/ARM/ARMInstrInfo.td @@ -4741,8 +4741,11 @@ def Int_eh_sjlj_longjmp : PseudoInst<(outs), (ins GPR:$src, GPR:$scratch), // This pseudo is used for ARM, Thumb1 and Thumb2. Any differences are // handled when the pseudo is expanded (which happens before any passes // that need the instruction size). -let isBarrier = 1 in -def eh_sjlj_dispatchsetup : PseudoInst<(outs), (ins), NoItinerary, []>; +let Defs = + [ R0, R1, R2, R3, R4, R5, R6, R7, R8, R9, R10, R11, R12, LR, CPSR, + QQQQ0, QQQQ1, QQQQ2, QQQQ3 ], isBarrier = 1 in { + def eh_sjlj_dispatchsetup : PseudoInst<(outs), (ins), NoItinerary, []>; +} //===----------------------------------------------------------------------===// // Non-Instruction Patterns diff --git a/test/CodeGen/ARM/2011-12-19-sjlj-clobber.ll b/test/CodeGen/ARM/2011-12-19-sjlj-clobber.ll new file mode 100644 index 00000000000..ddb76326947 --- /dev/null +++ b/test/CodeGen/ARM/2011-12-19-sjlj-clobber.ll @@ -0,0 +1,55 @@ +; RUN: llc < %s -O0 -mtriple=thumbv7-apple-ios | FileCheck %s + +; Radar 10567930: Make sure that all the caller-saved registers are saved and +; restored in a function with setjmp/longjmp EH. In particular, r6 was not +; being saved here. +; CHECK: push {r4, r5, r6, r7, lr} + +%0 = type opaque +%struct.NSConstantString = type { i32*, i32, i8*, i32 } + +define i32 @asdf(i32 %a, i32 %b, i8** %c, i8* %d) { +bb: + %tmp = alloca i32, align 4 + %tmp1 = alloca i32, align 4 + %tmp2 = alloca i8*, align 4 + %tmp3 = alloca i1 + %myException = alloca %0*, align 4 + %tmp4 = alloca i8* + %tmp5 = alloca i32 + %exception = alloca %0*, align 4 + store i32 %a, i32* %tmp, align 4 + store i32 %b, i32* %tmp1, align 4 + store i8* %d, i8** %tmp2, align 4 + store i1 false, i1* %tmp3 + %tmp7 = load i8** %c + %tmp10 = invoke %0* bitcast (i8* (i8*, i8*, ...)* @objc_msgSend to %0* (i8*, i8*, %0*)*)(i8* %tmp7, i8* %d, %0* null) + to label %bb11 unwind label %bb15 + +bb11: ; preds = %bb + store %0* %tmp10, %0** %myException, align 4 + %tmp12 = load %0** %myException, align 4 + %tmp13 = bitcast %0* %tmp12 to i8* + invoke void @objc_exception_throw(i8* %tmp13) noreturn + to label %bb14 unwind label %bb15 + +bb14: ; preds = %bb11 + unreachable + +bb15: ; preds = %bb11, %bb + %tmp16 = landingpad { i8*, i32 } personality i8* bitcast (i32 (...)* @__objc_personality_v0 to i8*) + catch i8* null + %tmp17 = extractvalue { i8*, i32 } %tmp16, 0 + store i8* %tmp17, i8** %tmp4 + %tmp18 = extractvalue { i8*, i32 } %tmp16, 1 + store i32 %tmp18, i32* %tmp5 + store i1 true, i1* %tmp3 + br label %bb56 + +bb56: + unreachable +} + +declare i8* @objc_msgSend(i8*, i8*, ...) nonlazybind +declare i32 @__objc_personality_v0(...) +declare void @objc_exception_throw(i8*)