1
0
mirror of https://github.com/RPCS3/llvm-mirror.git synced 2024-10-23 21:13:02 +02:00
llvm-mirror/test/CodeGen/X86/catchpad-lifetime.ll
David Majnemer a9ac81b53d [X86] Don't give catch objects a displacement of zero
Catch objects with a displacement of zero do not initialize a catch
object.  The displacement is relative to %rsp at the end of the
function's prologue for x86_64 targets.

If we place an object at the top-of-stack, we will end up wit a
displacement of zero resulting in our catch object remaining
uninitialized.

Address this by creating our catch objects as fixed objects.  We will
ensure that the UnwindHelp object is created after the catch objects so
that no catch object will have a displacement of zero.

Differential Revision: http://reviews.llvm.org/D17823

llvm-svn: 262546
2016-03-03 00:01:25 +00:00

92 lines
2.7 KiB
LLVM

; RUN: llc < %s | FileCheck %s
target datalayout = "e-m:x-p:32:32-i64:64-f80:32-n8:16:32-a:0:32-S32"
target triple = "x86_64-pc-windows-msvc"
declare void @throw()
declare i32 @__CxxFrameHandler3(...)
define void @test1() personality i32 (...)* @__CxxFrameHandler3 {
entry:
%alloca2 = alloca i8*, align 4
%alloca1 = alloca i8*, align 4
store volatile i8* null, i8** %alloca1
invoke void @throw()
to label %unreachable unwind label %catch.dispatch
; CHECK-LABEL: test1:
; CHECK: movq $0, -8(%rbp)
; CHECK: callq throw
catch.dispatch: ; preds = %entry
%cs = catchswitch within none [label %catch.pad] unwind to caller
catch.pad: ; preds = %catch.dispatch
%cp = catchpad within %cs [i8* null, i32 0, i8** %alloca1]
store volatile i8* null, i8** %alloca1
%bc1 = bitcast i8** %alloca1 to i8*
call void @llvm.lifetime.end(i64 4, i8* nonnull %bc1)
%bc2 = bitcast i8** %alloca2 to i8*
call void @llvm.lifetime.start(i64 4, i8* %bc2)
store volatile i8* null, i8** %alloca1
unreachable
; CHECK-LABEL: "?catch$2@?0?test1@4HA"
; CHECK: movq $0, -8(%rbp)
; CHECK: movq $0, -8(%rbp)
; CHECK: ud2
unreachable: ; preds = %entry
unreachable
}
; CHECK-LABEL: $cppxdata$test1:
; CHECK: .long 56 # CatchObjOffset
define void @test2() personality i32 (...)* @__CxxFrameHandler3 {
entry:
%alloca2 = alloca i8*, align 4
%alloca1 = alloca i8*, align 4
store volatile i8* null, i8** %alloca1
invoke void @throw()
to label %unreachable unwind label %catch.dispatch
; CHECK-LABEL: test2:
; CHECK: movq $0, -16(%rbp)
; CHECK: callq throw
catch.dispatch: ; preds = %entry
%cs = catchswitch within none [label %catch.pad] unwind to caller
catch.pad: ; preds = %catch.dispatch
%cp = catchpad within %cs [i8* null, i32 0, i8** null]
store volatile i8* null, i8** %alloca1
%bc1 = bitcast i8** %alloca1 to i8*
call void @llvm.lifetime.end(i64 4, i8* nonnull %bc1)
%bc2 = bitcast i8** %alloca2 to i8*
call void @llvm.lifetime.start(i64 4, i8* %bc2)
store volatile i8* null, i8** %alloca1
unreachable
; CHECK-LABEL: "?catch$2@?0?test2@4HA"
; CHECK: movq $0, -16(%rbp)
; CHECK: movq $0, -16(%rbp)
; CHECK: ud2
unreachable: ; preds = %entry
unreachable
}
; CHECK-LABEL: $cppxdata$test2:
; CHECK: .long 0 # CatchObjOffset
; Function Attrs: argmemonly nounwind
declare void @llvm.lifetime.start(i64, i8* nocapture) #0
; Function Attrs: argmemonly nounwind
declare void @llvm.lifetime.end(i64, i8* nocapture) #0
attributes #0 = { argmemonly nounwind }