aboutsummaryrefslogtreecommitdiff
path: root/test/Transforms
diff options
context:
space:
mode:
authorDimitry Andric <dim@FreeBSD.org>2016-08-17 19:33:52 +0000
committerDimitry Andric <dim@FreeBSD.org>2016-08-17 19:33:52 +0000
commita7fe922b98bb45be7dce7c1cfe668ec27eeddc74 (patch)
treee9648f5bddc775b842e53141d7c9748482f7115a /test/Transforms
parentc3aee98e721333f265a88d6bf348e6e468f027d4 (diff)
Notes
Diffstat (limited to 'test/Transforms')
-rw-r--r--test/Transforms/ConstProp/calls.ll88
-rw-r--r--test/Transforms/EarlyCSE/basic.ll14
-rw-r--r--test/Transforms/GlobalOpt/metadata.ll2
-rw-r--r--test/Transforms/IndVarSimplify/pr28935.ll20
-rw-r--r--test/Transforms/Inline/inalloca-not-static.ll63
-rw-r--r--test/Transforms/Inline/inline_constprop.ll43
-rw-r--r--test/Transforms/InstCombine/call.ll11
-rw-r--r--test/Transforms/InstCombine/log-pow.ll3
-rw-r--r--test/Transforms/InstCombine/select.ll23
-rw-r--r--test/Transforms/LCSSA/pr28424.ll87
-rw-r--r--test/Transforms/LCSSA/pr28608.ll35
-rw-r--r--test/Transforms/LoopSimplify/pr28272.ll76
-rw-r--r--test/Transforms/LoopStrengthReduce/X86/pr28719.ll47
-rw-r--r--test/Transforms/LoopVectorize/pr28541.ll71
-rw-r--r--test/Transforms/SafeStack/coloring-ssp.ll34
-rw-r--r--test/Transforms/SafeStack/layout-region-split.ll84
16 files changed, 656 insertions, 45 deletions
diff --git a/test/Transforms/ConstProp/calls.ll b/test/Transforms/ConstProp/calls.ll
index a445ac81ff27..d9a884a4a7bc 100644
--- a/test/Transforms/ConstProp/calls.ll
+++ b/test/Transforms/ConstProp/calls.ll
@@ -1,47 +1,47 @@
; RUN: opt < %s -constprop -S | FileCheck %s
; RUN: opt < %s -constprop -disable-simplify-libcalls -S | FileCheck %s --check-prefix=FNOBUILTIN
-declare double @acos(double)
-declare double @asin(double)
-declare double @atan(double)
-declare double @atan2(double, double)
-declare double @ceil(double)
-declare double @cos(double)
-declare double @cosh(double)
-declare double @exp(double)
-declare double @exp2(double)
-declare double @fabs(double)
-declare double @floor(double)
-declare double @fmod(double, double)
-declare double @log(double)
-declare double @log10(double)
-declare double @pow(double, double)
-declare double @sin(double)
-declare double @sinh(double)
-declare double @sqrt(double)
-declare double @tan(double)
-declare double @tanh(double)
+declare double @acos(double) readnone nounwind
+declare double @asin(double) readnone nounwind
+declare double @atan(double) readnone nounwind
+declare double @atan2(double, double) readnone nounwind
+declare double @ceil(double) readnone nounwind
+declare double @cos(double) readnone nounwind
+declare double @cosh(double) readnone nounwind
+declare double @exp(double) readnone nounwind
+declare double @exp2(double) readnone nounwind
+declare double @fabs(double) readnone nounwind
+declare double @floor(double) readnone nounwind
+declare double @fmod(double, double) readnone nounwind
+declare double @log(double) readnone nounwind
+declare double @log10(double) readnone nounwind
+declare double @pow(double, double) readnone nounwind
+declare double @sin(double) readnone nounwind
+declare double @sinh(double) readnone nounwind
+declare double @sqrt(double) readnone nounwind
+declare double @tan(double) readnone nounwind
+declare double @tanh(double) readnone nounwind
-declare float @acosf(float)
-declare float @asinf(float)
-declare float @atanf(float)
-declare float @atan2f(float, float)
-declare float @ceilf(float)
-declare float @cosf(float)
-declare float @coshf(float)
-declare float @expf(float)
-declare float @exp2f(float)
-declare float @fabsf(float)
-declare float @floorf(float)
-declare float @fmodf(float, float)
-declare float @logf(float)
-declare float @log10f(float)
-declare float @powf(float, float)
-declare float @sinf(float)
-declare float @sinhf(float)
-declare float @sqrtf(float)
-declare float @tanf(float)
-declare float @tanhf(float)
+declare float @acosf(float) readnone nounwind
+declare float @asinf(float) readnone nounwind
+declare float @atanf(float) readnone nounwind
+declare float @atan2f(float, float) readnone nounwind
+declare float @ceilf(float) readnone nounwind
+declare float @cosf(float) readnone nounwind
+declare float @coshf(float) readnone nounwind
+declare float @expf(float) readnone nounwind
+declare float @exp2f(float) readnone nounwind
+declare float @fabsf(float) readnone nounwind
+declare float @floorf(float) readnone nounwind
+declare float @fmodf(float, float) readnone nounwind
+declare float @logf(float) readnone nounwind
+declare float @log10f(float) readnone nounwind
+declare float @powf(float, float) readnone nounwind
+declare float @sinf(float) readnone nounwind
+declare float @sinhf(float) readnone nounwind
+declare float @sqrtf(float) readnone nounwind
+declare float @tanf(float) readnone nounwind
+declare float @tanhf(float) readnone nounwind
define double @T() {
; CHECK-LABEL: @T(
@@ -193,11 +193,13 @@ entry:
ret i1 %b
}
-; TODO: Inexact values should not fold as they are dependent on rounding mode
+; Inexact values should not fold as they are dependent on rounding mode
define i1 @test_sse_cvts_inexact() nounwind readnone {
; CHECK-LABEL: @test_sse_cvts_inexact(
-; CHECK-NOT: call
-; CHECK: ret i1 true
+; CHECK: call
+; CHECK: call
+; CHECK: call
+; CHECK: call
entry:
%i0 = tail call i32 @llvm.x86.sse.cvtss2si(<4 x float> <float 1.75, float undef, float undef, float undef>) nounwind
%i1 = tail call i64 @llvm.x86.sse.cvtss2si64(<4 x float> <float 1.75, float undef, float undef, float undef>) nounwind
diff --git a/test/Transforms/EarlyCSE/basic.ll b/test/Transforms/EarlyCSE/basic.ll
index fa1a7059db95..3c427d899f68 100644
--- a/test/Transforms/EarlyCSE/basic.ll
+++ b/test/Transforms/EarlyCSE/basic.ll
@@ -276,3 +276,17 @@ define void @dse_neg2(i32 *%P) {
ret void
}
+@c = external global i32, align 4
+declare i32 @reads_c(i32 returned)
+define void @pr28763() {
+entry:
+; CHECK-LABEL: @pr28763(
+; CHECK: store i32 0, i32* @c, align 4
+; CHECK: call i32 @reads_c(i32 0)
+; CHECK: store i32 2, i32* @c, align 4
+ %load = load i32, i32* @c, align 4
+ store i32 0, i32* @c, align 4
+ %call = call i32 @reads_c(i32 0)
+ store i32 2, i32* @c, align 4
+ ret void
+}
diff --git a/test/Transforms/GlobalOpt/metadata.ll b/test/Transforms/GlobalOpt/metadata.ll
index 152d58e6e320..b766349d506b 100644
--- a/test/Transforms/GlobalOpt/metadata.ll
+++ b/test/Transforms/GlobalOpt/metadata.ll
@@ -28,5 +28,5 @@ declare void @llvm.foo(metadata, metadata) nounwind readnone
; CHECK: !named = !{![[NULL:[0-9]+]]}
!0 = !{i8*** @G}
-; CHECK-DAG: ![[NULL]] = !{null}
+; CHECK-DAG: ![[NULL]] = distinct !{null}
; CHECK-DAG: ![[EMPTY]] = !{}
diff --git a/test/Transforms/IndVarSimplify/pr28935.ll b/test/Transforms/IndVarSimplify/pr28935.ll
new file mode 100644
index 000000000000..0cfd1d31a41d
--- /dev/null
+++ b/test/Transforms/IndVarSimplify/pr28935.ll
@@ -0,0 +1,20 @@
+; RUN: opt -S -indvars < %s | FileCheck %s
+
+target datalayout = "e-m:e-i64:64-f80:128-n8:16:32:64-S128"
+target triple = "x86_64-unknown-linux-gnu"
+
+declare i16 @fn1(i16 returned, i64)
+
+define void @fn2() {
+; CHECK-LABEL: @fn2(
+entry:
+ br label %for.cond
+
+for.cond:
+ %f.0 = phi i64 [ undef, %entry ], [ %inc, %for.cond ]
+ %conv = trunc i64 %f.0 to i16
+ %call = tail call i16 @fn1(i16 %conv, i64 %f.0)
+ %conv2 = zext i16 %call to i32
+ %inc = add nsw i64 %f.0, 1
+ br label %for.cond
+}
diff --git a/test/Transforms/Inline/inalloca-not-static.ll b/test/Transforms/Inline/inalloca-not-static.ll
new file mode 100644
index 000000000000..e70e30d1a7ed
--- /dev/null
+++ b/test/Transforms/Inline/inalloca-not-static.ll
@@ -0,0 +1,63 @@
+; RUN: opt -always-inline -S < %s | FileCheck %s
+
+; We used to misclassify inalloca as a static alloca in the inliner. This only
+; arose with for alwaysinline functions, because the normal inliner refuses to
+; inline such things.
+
+; Generated using this C++ source:
+; struct Foo {
+; Foo();
+; Foo(const Foo &o);
+; ~Foo();
+; int a;
+; };
+; __forceinline void h(Foo o) {}
+; __forceinline void g() { h(Foo()); }
+; void f() { g(); }
+
+; ModuleID = 't.cpp'
+source_filename = "t.cpp"
+target datalayout = "e-m:x-p:32:32-i64:64-f80:32-n8:16:32-a:0:32-S32"
+target triple = "i386-pc-windows-msvc19.0.24210"
+
+%struct.Foo = type { i32 }
+
+declare i8* @llvm.stacksave()
+declare void @llvm.stackrestore(i8*)
+
+declare x86_thiscallcc %struct.Foo* @"\01??0Foo@@QAE@XZ"(%struct.Foo* returned) unnamed_addr
+declare x86_thiscallcc void @"\01??1Foo@@QAE@XZ"(%struct.Foo*) unnamed_addr
+
+define void @f() {
+entry:
+ call void @g()
+ ret void
+}
+
+define internal void @g() alwaysinline {
+entry:
+ %inalloca.save = call i8* @llvm.stacksave()
+ %argmem = alloca inalloca <{ %struct.Foo }>, align 4
+ %0 = getelementptr inbounds <{ %struct.Foo }>, <{ %struct.Foo }>* %argmem, i32 0, i32 0
+ %call = call x86_thiscallcc %struct.Foo* @"\01??0Foo@@QAE@XZ"(%struct.Foo* %0)
+ call void @h(<{ %struct.Foo }>* inalloca %argmem)
+ call void @llvm.stackrestore(i8* %inalloca.save)
+ ret void
+}
+
+; Function Attrs: alwaysinline inlinehint nounwind
+define internal void @h(<{ %struct.Foo }>* inalloca) alwaysinline {
+entry:
+ %o = getelementptr inbounds <{ %struct.Foo }>, <{ %struct.Foo }>* %0, i32 0, i32 0
+ call x86_thiscallcc void @"\01??1Foo@@QAE@XZ"(%struct.Foo* %o)
+ ret void
+}
+
+; CHECK: define void @f()
+; CHECK: %inalloca.save.i = call i8* @llvm.stacksave()
+; CHECK: alloca inalloca <{ %struct.Foo }>, align 4
+; CHECK: %call.i = call x86_thiscallcc %struct.Foo* @"\01??0Foo@@QAE@XZ"(%struct.Foo* %0)
+; CHECK: %o.i.i = getelementptr inbounds <{ %struct.Foo }>, <{ %struct.Foo }>* %argmem.i, i32 0, i32 0
+; CHECK: call x86_thiscallcc void @"\01??1Foo@@QAE@XZ"(%struct.Foo* %o.i.i)
+; CHECK: call void @llvm.stackrestore(i8* %inalloca.save.i)
+; CHECK: ret void
diff --git a/test/Transforms/Inline/inline_constprop.ll b/test/Transforms/Inline/inline_constprop.ll
index de23b6157a71..ab9e90ca27c6 100644
--- a/test/Transforms/Inline/inline_constprop.ll
+++ b/test/Transforms/Inline/inline_constprop.ll
@@ -279,3 +279,46 @@ return:
%retval.0 = phi i32* [ %b, %if.end3 ], [ %a, %if.then ]
ret i32* %retval.0
}
+
+declare i32 @PR28802.external(i32 returned %p1)
+
+define internal i32 @PR28802.callee() {
+entry:
+ br label %cont
+
+cont:
+ %0 = phi i32 [ 0, %entry ]
+ %call = call i32 @PR28802.external(i32 %0)
+ ret i32 %call
+}
+
+define i32 @PR28802() {
+entry:
+ %call = call i32 @PR28802.callee()
+ ret i32 %call
+}
+
+; CHECK-LABEL: define i32 @PR28802(
+; CHECK: call i32 @PR28802.external(i32 0)
+; CHECK: ret i32 0
+
+define internal i32 @PR28848.callee(i32 %p2, i1 %c) {
+entry:
+ br i1 %c, label %cond.end, label %cond.true
+
+cond.true:
+ br label %cond.end
+
+cond.end:
+ %cond = phi i32 [ 0, %cond.true ], [ %p2, %entry ]
+ %or = or i32 %cond, %p2
+ ret i32 %or
+}
+
+define i32 @PR28848() {
+entry:
+ %call = call i32 @PR28848.callee(i32 0, i1 false)
+ ret i32 %call
+}
+; CHECK-LABEL: define i32 @PR28848(
+; CHECK: ret i32 0
diff --git a/test/Transforms/InstCombine/call.ll b/test/Transforms/InstCombine/call.ll
index ea338f0bf581..5307dcb6df72 100644
--- a/test/Transforms/InstCombine/call.ll
+++ b/test/Transforms/InstCombine/call.ll
@@ -276,3 +276,14 @@ define <2 x i16> @test16() {
%X = call <2 x i16> bitcast (i32 ()* @test16a to <2 x i16> ()*)( )
ret <2 x i16> %X
}
+
+declare i32 @pr28655(i32 returned %V)
+
+define i32 @test17() {
+entry:
+ %C = call i32 @pr28655(i32 0)
+ ret i32 %C
+}
+; CHECK-LABEL: @test17(
+; CHECK: call i32 @pr28655(i32 0)
+; CHECK: ret i32 0
diff --git a/test/Transforms/InstCombine/log-pow.ll b/test/Transforms/InstCombine/log-pow.ll
index a0c10d0a0b8c..4e4a2b2612c7 100644
--- a/test/Transforms/InstCombine/log-pow.ll
+++ b/test/Transforms/InstCombine/log-pow.ll
@@ -55,7 +55,8 @@ define double @log_exp2_not_fast(double %x) {
; CHECK-NEXT: %call3 = call fast double @log(double %call2)
; CHECK-NEXT: ret double %call3
-declare double @log(double)
+declare double @log(double) #0
declare double @exp2(double)
declare double @llvm.pow.f64(double, double)
+attributes #0 = { nounwind readnone }
diff --git a/test/Transforms/InstCombine/select.ll b/test/Transforms/InstCombine/select.ll
index e0e7bfccff93..413be89c42e7 100644
--- a/test/Transforms/InstCombine/select.ll
+++ b/test/Transforms/InstCombine/select.ll
@@ -1737,3 +1737,26 @@ define i32 @PR27137(i32 %a) {
%s1 = select i1 %c1, i32 %s0, i32 -1
ret i32 %s1
}
+
+define i32 @select_icmp_slt0_xor(i32 %x) {
+; CHECK-LABEL: @select_icmp_slt0_xor(
+; CHECK-NEXT: [[TMP1:%.*]] = or i32 %x, -2147483648
+; CHECK-NEXT: ret i32 [[TMP1]]
+;
+ %cmp = icmp slt i32 %x, zeroinitializer
+ %xor = xor i32 %x, 2147483648
+ %x.xor = select i1 %cmp, i32 %x, i32 %xor
+ ret i32 %x.xor
+}
+
+define <2 x i32> @select_icmp_slt0_xor_vec(<2 x i32> %x) {
+; CHECK-LABEL: @select_icmp_slt0_xor_vec(
+; CHECK-NEXT: [[TMP1:%.*]] = or <2 x i32> %x, <i32 -2147483648, i32 -2147483648>
+; CHECK-NEXT: ret <2 x i32> [[TMP1]]
+;
+ %cmp = icmp slt <2 x i32> %x, zeroinitializer
+ %xor = xor <2 x i32> %x, <i32 2147483648, i32 2147483648>
+ %x.xor = select <2 x i1> %cmp, <2 x i32> %x, <2 x i32> %xor
+ ret <2 x i32> %x.xor
+}
+
diff --git a/test/Transforms/LCSSA/pr28424.ll b/test/Transforms/LCSSA/pr28424.ll
new file mode 100644
index 000000000000..cd7969009fbb
--- /dev/null
+++ b/test/Transforms/LCSSA/pr28424.ll
@@ -0,0 +1,87 @@
+; RUN: opt < %s -lcssa -S -o - | FileCheck %s
+target triple = "x86_64-unknown-linux-gnu"
+
+; PR28424
+; Here LCSSA adds phi-nodes for %x into the loop exits. Then, SSAUpdater needs
+; to insert phi-nodes to merge these values. That creates a new def, which in
+; its turn needs another LCCSA phi-node, and this test ensures that we insert
+; it.
+
+; CHECK-LABEL: @foo1
+define internal i32 @foo1() {
+entry:
+ br label %header
+
+header:
+ %x = add i32 0, 1
+ br i1 undef, label %if, label %loopexit1
+
+if:
+ br i1 undef, label %latch, label %loopexit2
+
+latch:
+ br i1 undef, label %header, label %loopexit3
+
+; CHECK: loopexit1:
+; CHECK: %x.lcssa = phi i32 [ %x, %header ]
+loopexit1:
+ br label %loop_with_insert_point
+
+; CHECK: loopexit2:
+; CHECK: %x.lcssa1 = phi i32 [ %x, %if ]
+loopexit2:
+ br label %exit
+
+; CHECK: loopexit3:
+; CHECK: %x.lcssa2 = phi i32 [ %x, %latch ]
+loopexit3:
+ br label %loop_with_insert_point
+
+; CHECK: loop_with_insert_point:
+; CHECK: %x4 = phi i32 [ %x4, %loop_with_insert_point ], [ %x.lcssa2, %loopexit3 ], [ %x.lcssa, %loopexit1 ]
+loop_with_insert_point:
+ br i1 undef, label %loop_with_insert_point, label %bb
+
+; CHECK: bb:
+; CHECK: %x4.lcssa = phi i32 [ %x4, %loop_with_insert_point ]
+bb:
+ br label %exit
+
+; CHECK: exit:
+; CHECK: %x3 = phi i32 [ %x4.lcssa, %bb ], [ %x.lcssa1, %loopexit2 ]
+exit:
+ ret i32 %x
+}
+
+; CHECK-LABEL: @foo2
+define internal i32 @foo2() {
+entry:
+ br label %header
+
+header:
+ %x = add i32 0, 1
+ br i1 undef, label %latch, label %loopexit1
+
+latch:
+ br i1 undef, label %header, label %loopexit2
+
+; CHECK: loopexit1:
+; CHECK: %x.lcssa = phi i32 [ %x, %header ]
+loopexit1:
+ br label %loop_with_insert_point
+
+; CHECK: loopexit2:
+; CHECK: %x.lcssa1 = phi i32 [ %x, %latch ]
+loopexit2:
+ br label %loop_with_insert_point
+
+; CHECK: loop_with_insert_point:
+; CHECK: %x2 = phi i32 [ %x2, %loop_with_insert_point ], [ %x.lcssa1, %loopexit2 ], [ %x.lcssa, %loopexit1 ]
+loop_with_insert_point:
+ br i1 undef, label %loop_with_insert_point, label %exit
+
+; CHECK: exit:
+; CHECK: %x2.lcssa = phi i32 [ %x2, %loop_with_insert_point ]
+exit:
+ ret i32 %x
+}
diff --git a/test/Transforms/LCSSA/pr28608.ll b/test/Transforms/LCSSA/pr28608.ll
new file mode 100644
index 000000000000..3ba3fe8cda11
--- /dev/null
+++ b/test/Transforms/LCSSA/pr28608.ll
@@ -0,0 +1,35 @@
+; RUN: opt < %s -lcssa -disable-output
+target datalayout = "e-m:e-i64:64-f80:128-n8:16:32:64-S128"
+target triple = "x86_64-unknown-linux-gnu"
+
+; PR28608
+; Check that we don't crash on this test.
+
+define void @foo() {
+entry:
+ br label %bb1
+
+bb1:
+ br label %bb2
+
+bb2:
+ %x = phi i32 [ undef, %bb5 ], [ undef, %bb1 ]
+ br i1 undef, label %bb3, label %bb6
+
+bb3:
+ br i1 undef, label %bb5, label %bb4
+
+bb4:
+ br label %bb6
+
+bb5:
+ br label %bb2
+
+bb6:
+ br label %bb1
+
+exit:
+ %y = add i32 0, %x
+ ret void
+}
+
diff --git a/test/Transforms/LoopSimplify/pr28272.ll b/test/Transforms/LoopSimplify/pr28272.ll
new file mode 100644
index 000000000000..49990f92cabe
--- /dev/null
+++ b/test/Transforms/LoopSimplify/pr28272.ll
@@ -0,0 +1,76 @@
+; RUN: opt < %s -lcssa -loop-unroll -S | FileCheck %s
+target triple = "x86_64-unknown-linux-gnu"
+
+; PR28272
+; When LoopSimplify separates nested loops, it might break LCSSA form: values
+; from the original loop might be used in the outer loop. This test invokes
+; loop-unroll, which calls loop-simplify before itself. If LCSSA is broken
+; after loop-simplify, we crash on assertion.
+
+; CHECK-LABEL: @foo
+define void @foo() {
+entry:
+ br label %header
+
+header:
+ br label %loop1
+
+loop1:
+ br i1 true, label %loop1, label %bb43
+
+bb43:
+ %a = phi i32 [ undef, %loop1 ], [ 0, %bb45 ], [ %a, %bb54 ]
+ %b = phi i32 [ 0, %loop1 ], [ 1, %bb54 ], [ %c, %bb45 ]
+ br i1 true, label %bb114, label %header
+
+bb114:
+ %c = add i32 0, 1
+ %d = add i32 0, 1
+ br i1 true, label %bb45, label %bb54
+
+bb45:
+ %x = add i32 %d, 0
+ br label %bb43
+
+bb54:
+ br label %bb43
+}
+
+; CHECK-LABEL: @foo2
+define void @foo2() {
+entry:
+ br label %outer
+
+outer.loopexit:
+ br label %outer
+
+outer:
+ br label %loop1
+
+loop1:
+ br i1 true, label %loop1, label %loop2.preheader
+
+loop2.preheader:
+ %a.ph = phi i32 [ undef, %loop1 ]
+ %b.ph = phi i32 [ 0, %loop1 ]
+ br label %loop2
+
+loop2:
+ %a = phi i32 [ 0, %loop2.if.true ], [ %a, %loop2.if.false ], [ %a.ph, %loop2.preheader ], [0, %bb]
+ %b = phi i32 [ 1, %loop2.if.false ], [ %c, %loop2.if.true ], [ %b.ph, %loop2.preheader ], [%c, %bb]
+ br i1 true, label %loop2.if, label %outer.loopexit
+
+loop2.if:
+ %c = add i32 0, 1
+ switch i32 undef, label %loop2.if.false [i32 0, label %loop2.if.true
+ i32 1, label %bb]
+
+loop2.if.true:
+ br i1 undef, label %loop2, label %bb
+
+loop2.if.false:
+ br label %loop2
+
+bb:
+ br label %loop2
+}
diff --git a/test/Transforms/LoopStrengthReduce/X86/pr28719.ll b/test/Transforms/LoopStrengthReduce/X86/pr28719.ll
new file mode 100644
index 000000000000..0e74ff20073b
--- /dev/null
+++ b/test/Transforms/LoopStrengthReduce/X86/pr28719.ll
@@ -0,0 +1,47 @@
+; RUN: opt < %s -loop-reduce -S | FileCheck %s
+
+target datalayout = "e-m:e-i64:64-f80:128-n8:16:32:64-S128"
+target triple = "x86_64-unknown-linux-gnu"
+
+@a = global i32 0, align 4
+@b = global i8 0, align 1
+@c = global [4 x i8] zeroinitializer, align 1
+
+; Just make sure we don't generate code with uses not dominated by defs.
+; CHECK-LABEL: @main(
+define i32 @main() {
+entry:
+ %a0 = load i32, i32* @a, align 4
+ %cmpa = icmp slt i32 %a0, 4
+ br i1 %cmpa, label %preheader, label %for.end
+
+preheader:
+ %b0 = load i8, i8* @b, align 1
+ %b0sext = sext i8 %b0 to i64
+ br label %for.body
+
+for.body:
+ %iv = phi i64 [ 0, %preheader ], [ %iv.next, %lor.false ]
+ %mul = mul nsw i64 %b0sext, %iv
+ %multrunc = trunc i64 %mul to i32
+ %cmp = icmp eq i32 %multrunc, 0
+ br i1 %cmp, label %lor.false, label %if.then
+
+lor.false:
+ %cgep = getelementptr inbounds [4 x i8], [4 x i8]* @c, i64 0, i64 %iv
+ %ci = load i8, i8* %cgep, align 1
+ %cisext = sext i8 %ci to i32
+ %ivtrunc = trunc i64 %iv to i32
+ %cmp2 = icmp eq i32 %cisext, %ivtrunc
+ %iv.next = add i64 %iv, 1
+ br i1 %cmp2, label %for.body, label %if.then
+
+if.then:
+ tail call void @abort()
+ unreachable
+
+for.end:
+ ret i32 0
+}
+
+declare void @abort()
diff --git a/test/Transforms/LoopVectorize/pr28541.ll b/test/Transforms/LoopVectorize/pr28541.ll
new file mode 100644
index 000000000000..7bb7f0987fdf
--- /dev/null
+++ b/test/Transforms/LoopVectorize/pr28541.ll
@@ -0,0 +1,71 @@
+; RUN: opt -loop-vectorize -pass-remarks=loop-vectorize -S < %s 2>&1 | FileCheck %s
+
+; FIXME: Check for -pass-remarks-missed and -pass-remarks-analysis output when
+; addAcyclicInnerLoop emits analysis.
+
+; Check that opt does not crash on such input:
+;
+; a, b, c;
+; fn1() {
+; while (b--) {
+; c = a;
+; switch (a & 3)
+; case 0:
+; do
+; case 3:
+; case 2:
+; case 1:
+; ;
+; while (--c)
+; ;
+; }
+; }
+
+@b = common global i32 0, align 4
+@a = common global i32 0, align 4
+@c = common global i32 0, align 4
+
+; CHECK-NOT: vectorized loop
+; CHECK-LABEL: fn1
+
+define i32 @fn1() {
+entry:
+ %tmp2 = load i32, i32* @b, align 4
+ %dec3 = add nsw i32 %tmp2, -1
+ store i32 %dec3, i32* @b, align 4
+ %tobool4 = icmp eq i32 %tmp2, 0
+ br i1 %tobool4, label %while.end, label %while.body.lr.ph
+
+while.body.lr.ph: ; preds = %entry
+ %tmp1 = load i32, i32* @a, align 4
+ %and = and i32 %tmp1, 3
+ %switch = icmp eq i32 %and, 0
+ br label %while.body
+
+while.cond: ; preds = %do.cond
+ %dec = add nsw i32 %dec7, -1
+ %tobool = icmp eq i32 %dec7, 0
+ br i1 %tobool, label %while.cond.while.end_crit_edge, label %while.body
+
+while.body: ; preds = %while.body.lr.ph, %while.cond
+ %dec7 = phi i32 [ %dec3, %while.body.lr.ph ], [ %dec, %while.cond ]
+ br i1 %switch, label %do.body, label %do.cond
+
+do.body: ; preds = %do.cond, %while.body
+ %dec25 = phi i32 [ %dec2, %do.cond ], [ %tmp1, %while.body ]
+ br label %do.cond
+
+do.cond: ; preds = %do.body, %while.body
+ %dec26 = phi i32 [ %dec25, %do.body ], [ %tmp1, %while.body ]
+ %dec2 = add nsw i32 %dec26, -1
+ %tobool3 = icmp eq i32 %dec2, 0
+ br i1 %tobool3, label %while.cond, label %do.body
+
+while.cond.while.end_crit_edge: ; preds = %while.cond
+ store i32 0, i32* @c, align 4
+ store i32 -1, i32* @b, align 4
+ br label %while.end
+
+while.end: ; preds = %while.cond.while.end_crit_edge, %entry
+ ret i32 undef
+}
diff --git a/test/Transforms/SafeStack/coloring-ssp.ll b/test/Transforms/SafeStack/coloring-ssp.ll
new file mode 100644
index 000000000000..d71babe200df
--- /dev/null
+++ b/test/Transforms/SafeStack/coloring-ssp.ll
@@ -0,0 +1,34 @@
+; RUN: opt -safe-stack -S -mtriple=x86_64-pc-linux-gnu < %s -o - | FileCheck %s
+
+; %x and %y share a stack slot between them, but not with the stack guard.
+define void @f() safestack sspreq {
+; CHECK-LABEL: define void @f
+entry:
+; CHECK: %[[USP:.*]] = load i8*, i8** @__safestack_unsafe_stack_ptr
+; CHECK: getelementptr i8, i8* %[[USP]], i32 -16
+
+; CHECK: %[[A:.*]] = getelementptr i8, i8* %[[USP]], i32 -8
+; CHECK: %[[StackGuardSlot:.*]] = bitcast i8* %[[A]] to i8**
+; CHECK: store i8* %{{.*}}, i8** %[[StackGuardSlot]]
+
+ %x = alloca i64, align 8
+ %y = alloca i64, align 8
+ %x0 = bitcast i64* %x to i8*
+ %y0 = bitcast i64* %y to i8*
+
+ call void @llvm.lifetime.start(i64 -1, i8* %x0)
+; CHECK: getelementptr i8, i8* %[[USP]], i32 -16
+ call void @capture64(i64* %x)
+ call void @llvm.lifetime.end(i64 -1, i8* %x0)
+
+ call void @llvm.lifetime.start(i64 -1, i8* %y0)
+; CHECK: getelementptr i8, i8* %[[USP]], i32 -16
+ call void @capture64(i64* %y)
+ call void @llvm.lifetime.end(i64 -1, i8* %y0)
+
+ ret void
+}
+
+declare void @llvm.lifetime.start(i64, i8* nocapture)
+declare void @llvm.lifetime.end(i64, i8* nocapture)
+declare void @capture64(i64*)
diff --git a/test/Transforms/SafeStack/layout-region-split.ll b/test/Transforms/SafeStack/layout-region-split.ll
new file mode 100644
index 000000000000..ceb18bb70c20
--- /dev/null
+++ b/test/Transforms/SafeStack/layout-region-split.ll
@@ -0,0 +1,84 @@
+; Regression test for safestack layout. Used to fail with asan.
+; RUN: opt -safe-stack -S -mtriple=x86_64-pc-linux-gnu < %s -o - | FileCheck %s
+
+define void @f() safestack {
+; CHECK-LABEL: define void @f
+entry:
+; CHECK: %[[USP:.*]] = load i8*, i8** @__safestack_unsafe_stack_ptr
+; CHECK: getelementptr i8, i8* %[[USP]], i32 -224
+
+ %x0 = alloca i8, align 16
+ %x1 = alloca i8, align 16
+ %x2 = alloca i8, align 16
+ %x3 = alloca i8, align 16
+ %x4 = alloca i8, align 16
+ %x5 = alloca i8, align 16
+ %x6 = alloca i8, align 16
+ %x7 = alloca i8, align 16
+ %x8 = alloca i8, align 16
+ %x9 = alloca i8, align 16
+ %x10 = alloca i8, align 16
+ %x11 = alloca i8, align 16
+ %x12 = alloca i8, align 16
+ %x13 = alloca i8, align 16
+ %y0 = alloca i8, align 2
+ %y1 = alloca i8, align 2
+ %y2 = alloca i8, align 2
+ %y3 = alloca i8, align 2
+ %y4 = alloca i8, align 2
+ %y5 = alloca i8, align 2
+ %y6 = alloca i8, align 2
+ %y7 = alloca i8, align 2
+ %y8 = alloca i8, align 2
+
+; CHECK: getelementptr i8, i8* %[[USP]], i32 -16
+ call void @capture8(i8* %x0)
+; CHECK: getelementptr i8, i8* %[[USP]], i32 -32
+ call void @capture8(i8* %x1)
+; CHECK: getelementptr i8, i8* %[[USP]], i32 -48
+ call void @capture8(i8* %x2)
+; CHECK: getelementptr i8, i8* %[[USP]], i32 -64
+ call void @capture8(i8* %x3)
+; CHECK: getelementptr i8, i8* %[[USP]], i32 -80
+ call void @capture8(i8* %x4)
+; CHECK: getelementptr i8, i8* %[[USP]], i32 -96
+ call void @capture8(i8* %x5)
+; CHECK: getelementptr i8, i8* %[[USP]], i32 -112
+ call void @capture8(i8* %x6)
+; CHECK: getelementptr i8, i8* %[[USP]], i32 -128
+ call void @capture8(i8* %x7)
+; CHECK: getelementptr i8, i8* %[[USP]], i32 -144
+ call void @capture8(i8* %x8)
+; CHECK: getelementptr i8, i8* %[[USP]], i32 -160
+ call void @capture8(i8* %x9)
+; CHECK: getelementptr i8, i8* %[[USP]], i32 -176
+ call void @capture8(i8* %x10)
+; CHECK: getelementptr i8, i8* %[[USP]], i32 -192
+ call void @capture8(i8* %x11)
+; CHECK: getelementptr i8, i8* %[[USP]], i32 -208
+ call void @capture8(i8* %x12)
+; CHECK: getelementptr i8, i8* %[[USP]], i32 -224
+ call void @capture8(i8* %x13)
+; CHECK: getelementptr i8, i8* %[[USP]], i32 -2
+ call void @capture8(i8* %y0)
+; CHECK: getelementptr i8, i8* %[[USP]], i32 -4
+ call void @capture8(i8* %y1)
+; CHECK: getelementptr i8, i8* %[[USP]], i32 -6
+ call void @capture8(i8* %y2)
+; CHECK: getelementptr i8, i8* %[[USP]], i32 -8
+ call void @capture8(i8* %y3)
+; CHECK: getelementptr i8, i8* %[[USP]], i32 -10
+ call void @capture8(i8* %y4)
+; CHECK: getelementptr i8, i8* %[[USP]], i32 -12
+ call void @capture8(i8* %y5)
+; CHECK: getelementptr i8, i8* %[[USP]], i32 -14
+ call void @capture8(i8* %y6)
+; CHECK: getelementptr i8, i8* %[[USP]], i32 -18
+ call void @capture8(i8* %y7)
+; CHECK: getelementptr i8, i8* %[[USP]], i32 -20
+ call void @capture8(i8* %y8)
+
+ ret void
+}
+
+declare void @capture8(i8*)