1; NOTE: Assertions have been autogenerated by utils/update_test_checks.py 2; RUN: opt -passes=gvn -S %s | FileCheck %s 3 4target datalayout = "e-m:e-p270:32:32-p271:32:32-p272:64:64-i64:64-f80:128-n8:16:32:64-S128" 5 6declare void @foo(i64 %v) readonly 7 8define void @non_local_load(ptr %ptr) { 9; CHECK-LABEL: @non_local_load( 10; CHECK-NEXT: entry: 11; CHECK-NEXT: store i32 0, ptr [[PTR:%.*]], align 4 12; CHECK-NEXT: br label [[LOOP:%.*]] 13; CHECK: loop: 14; CHECK-NEXT: [[VAL:%.*]] = phi i32 [ [[VAL_INC:%.*]], [[LOOP]] ], [ 0, [[ENTRY:%.*]] ] 15; CHECK-NEXT: [[IV:%.*]] = phi i32 [ [[IV_NEXT:%.*]], [[LOOP]] ], [ 0, [[ENTRY]] ] 16; CHECK-NEXT: [[VAL_INC]] = add i32 [[VAL]], 1 17; CHECK-NEXT: store i32 [[VAL_INC]], ptr [[PTR]], align 4 18; CHECK-NEXT: [[IV_NEXT]] = add i32 [[IV]], 1 19; CHECK-NEXT: [[LOOP_COND:%.*]] = icmp eq i32 [[IV]], 1000 20; CHECK-NEXT: br i1 [[LOOP_COND]], label [[EXIT:%.*]], label [[LOOP]] 21; CHECK: exit: 22; CHECK-NEXT: ret void 23; 24entry: 25 store i32 0, ptr %ptr 26 br label %loop 27 28loop: 29 %iv = phi i32 [ %iv.next, %loop ], [ 0, %entry ] 30 %val = load i32, ptr %ptr 31 %val.inc = add i32 %val, 1 32 store i32 %val.inc, ptr %ptr 33 %iv.next = add i32 %iv, 1 34 %loop.cond = icmp eq i32 %iv, 1000 35 br i1 %loop.cond, label %exit, label %loop 36 37exit: 38 ret void 39} 40 41define void @non_local_load_with_iv_zext(ptr %ptr) { 42; CHECK-LABEL: @non_local_load_with_iv_zext( 43; CHECK-NEXT: entry: 44; CHECK-NEXT: store i32 0, ptr [[PTR:%.*]], align 4 45; CHECK-NEXT: br label [[LOOP:%.*]] 46; CHECK: loop: 47; CHECK-NEXT: [[VAL:%.*]] = phi i32 [ [[VAL_INC:%.*]], [[LOOP]] ], [ 0, [[ENTRY:%.*]] ] 48; CHECK-NEXT: [[IV:%.*]] = phi i32 [ [[IV_NEXT:%.*]], [[LOOP]] ], [ 0, [[ENTRY]] ] 49; CHECK-NEXT: [[VAL_INC]] = add i32 [[VAL]], 1 50; CHECK-NEXT: store i32 [[VAL_INC]], ptr [[PTR]], align 4 51; CHECK-NEXT: [[IV_WIDE:%.*]] = zext i32 [[IV]] to i64 52; CHECK-NEXT: call void @foo(i64 [[IV_WIDE]]) 53; CHECK-NEXT: [[IV_NEXT]] = add i32 [[IV]], 1 54; CHECK-NEXT: [[LOOP_COND:%.*]] = icmp eq i32 [[IV]], 1000 55; CHECK-NEXT: br i1 [[LOOP_COND]], label [[EXIT:%.*]], label [[LOOP]] 56; CHECK: exit: 57; CHECK-NEXT: ret void 58; 59entry: 60 store i32 0, ptr %ptr 61 br label %loop 62 63loop: 64 %iv = phi i32 [ %iv.next, %loop ], [ 0, %entry ] 65 %val = load i32, ptr %ptr 66 %val.inc = add i32 %val, 1 67 store i32 %val.inc, ptr %ptr 68 %iv.wide = zext i32 %iv to i64 69 call void @foo(i64 %iv.wide) 70 %iv.next = add i32 %iv, 1 71 %loop.cond = icmp eq i32 %iv, 1000 72 br i1 %loop.cond, label %exit, label %loop 73 74exit: 75 ret void 76} 77 78define void @two_non_local_loads(ptr %ptr1) { 79; CHECK-LABEL: @two_non_local_loads( 80; CHECK-NEXT: entry: 81; CHECK-NEXT: [[PTR2:%.*]] = getelementptr inbounds i32, ptr [[PTR1:%.*]], i64 1 82; CHECK-NEXT: store i32 0, ptr [[PTR1]], align 4 83; CHECK-NEXT: store i32 0, ptr [[PTR2]], align 4 84; CHECK-NEXT: br label [[LOOP:%.*]] 85; CHECK: loop: 86; CHECK-NEXT: [[VAL2:%.*]] = phi i32 [ [[VAL2_INC:%.*]], [[LOOP]] ], [ 0, [[ENTRY:%.*]] ] 87; CHECK-NEXT: [[VAL1:%.*]] = phi i32 [ [[VAL1_INC:%.*]], [[LOOP]] ], [ 0, [[ENTRY]] ] 88; CHECK-NEXT: [[IV:%.*]] = phi i32 [ [[IV_NEXT:%.*]], [[LOOP]] ], [ 0, [[ENTRY]] ] 89; CHECK-NEXT: [[VAL1_INC]] = add i32 [[VAL1]], 1 90; CHECK-NEXT: store i32 [[VAL1_INC]], ptr [[PTR1]], align 4 91; CHECK-NEXT: [[VAL2_INC]] = add i32 [[VAL2]], 1 92; CHECK-NEXT: store i32 [[VAL2_INC]], ptr [[PTR2]], align 4 93; CHECK-NEXT: [[IV_WIDE:%.*]] = zext i32 [[IV]] to i64 94; CHECK-NEXT: call void @foo(i64 [[IV_WIDE]]) 95; CHECK-NEXT: [[IV_NEXT]] = add i32 [[IV]], 1 96; CHECK-NEXT: [[LOOP_COND:%.*]] = icmp eq i32 [[IV]], 1000 97; CHECK-NEXT: br i1 [[LOOP_COND]], label [[EXIT:%.*]], label [[LOOP]] 98; CHECK: exit: 99; CHECK-NEXT: ret void 100; 101entry: 102 %ptr2 = getelementptr inbounds i32, ptr %ptr1, i64 1 103 store i32 0, ptr %ptr1 104 store i32 0, ptr %ptr2 105 br label %loop 106 107loop: 108 %iv = phi i32 [ %iv.next, %loop ], [ 0, %entry ] 109 %val1 = load i32, ptr %ptr1 110 %val1.inc = add i32 %val1, 1 111 store i32 %val1.inc, ptr %ptr1 112 %val2 = load i32, ptr %ptr2 113 %val2.inc = add i32 %val2, 1 114 store i32 %val2.inc, ptr %ptr2 115 %iv.wide = zext i32 %iv to i64 116 call void @foo(i64 %iv.wide) 117 %iv.next = add i32 %iv, 1 118 %loop.cond = icmp eq i32 %iv, 1000 119 br i1 %loop.cond, label %exit, label %loop 120 121exit: 122 ret void 123} 124 125