| ; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --version 4 |
| ; RUN: opt -passes=inline -mtriple=aarch64--linux-gnu -S -o - < %s -inline-threshold=0 | FileCheck %s |
| |
| target datalayout = "e-m:e-i8:8:32-i16:16:32-i64:64-i128:128-n32:64-S128" |
| target triple = "aarch64--linux-gnu" |
| |
| declare void @pad() |
| @glbl = external global i32 |
| |
| define i32 @outer_add1(i32 %a) { |
| ; CHECK-LABEL: define i32 @outer_add1( |
| ; CHECK-SAME: i32 [[A:%.*]]) { |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: store i32 0, ptr @glbl, align 4 |
| ; CHECK-NEXT: ret i32 [[A]] |
| ; |
| %C = call i32 @add(i32 %a, i32 0) |
| ret i32 %C |
| } |
| |
| define i32 @outer_add2(i32 %a) { |
| ; CHECK-LABEL: define i32 @outer_add2( |
| ; CHECK-SAME: i32 [[A:%.*]]) { |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: store i32 0, ptr @glbl, align 4 |
| ; CHECK-NEXT: ret i32 [[A]] |
| ; |
| %C = call i32 @add(i32 0, i32 %a) |
| ret i32 %C |
| } |
| |
| define i32 @add(i32 %a, i32 %b) { |
| ; CHECK-LABEL: define i32 @add( |
| ; CHECK-SAME: i32 [[A:%.*]], i32 [[B:%.*]]) { |
| ; CHECK-NEXT: [[ADD:%.*]] = add i32 [[A]], [[B]] |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: store i32 0, ptr @glbl, align 4 |
| ; CHECK-NEXT: ret i32 [[ADD]] |
| ; |
| %add = add i32 %a, %b |
| call void @pad() |
| store i32 0, ptr @glbl |
| ret i32 %add |
| } |
| |
| |
| |
| define i32 @outer_sub1(i32 %a) { |
| ; CHECK-LABEL: define i32 @outer_sub1( |
| ; CHECK-SAME: i32 [[A:%.*]]) { |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: store i32 0, ptr @glbl, align 4 |
| ; CHECK-NEXT: ret i32 [[A]] |
| ; |
| %C = call i32 @sub1(i32 %a, i32 0) |
| ret i32 %C |
| } |
| |
| define i32 @sub1(i32 %a, i32 %b) { |
| ; CHECK-LABEL: define i32 @sub1( |
| ; CHECK-SAME: i32 [[A:%.*]], i32 [[B:%.*]]) { |
| ; CHECK-NEXT: [[SUB:%.*]] = sub i32 [[A]], [[B]] |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: store i32 0, ptr @glbl, align 4 |
| ; CHECK-NEXT: ret i32 [[SUB]] |
| ; |
| %sub = sub i32 %a, %b |
| call void @pad() |
| store i32 0, ptr @glbl |
| ret i32 %sub |
| } |
| |
| |
| define i32 @outer_sub2(i32 %a) { |
| ; CHECK-LABEL: define i32 @outer_sub2( |
| ; CHECK-SAME: i32 [[A:%.*]]) { |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: ret i32 0 |
| ; |
| %C = call i32 @sub2(i32 %a) |
| ret i32 %C |
| } |
| |
| define i32 @sub2(i32 %a) { |
| ; CHECK-LABEL: define i32 @sub2( |
| ; CHECK-SAME: i32 [[A:%.*]]) { |
| ; CHECK-NEXT: [[SUB:%.*]] = sub i32 [[A]], [[A]] |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: ret i32 [[SUB]] |
| ; |
| %sub = sub i32 %a, %a |
| call void @pad() |
| ret i32 %sub |
| } |
| |
| |
| |
| define i32 @outer_mul1(i32 %a) { |
| ; CHECK-LABEL: define i32 @outer_mul1( |
| ; CHECK-SAME: i32 [[A:%.*]]) { |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: store i32 0, ptr @glbl, align 4 |
| ; CHECK-NEXT: ret i32 0 |
| ; |
| %C = call i32 @mul(i32 %a, i32 0) |
| ret i32 %C |
| } |
| |
| define i32 @outer_mul2(i32 %a) { |
| ; CHECK-LABEL: define i32 @outer_mul2( |
| ; CHECK-SAME: i32 [[A:%.*]]) { |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: store i32 0, ptr @glbl, align 4 |
| ; CHECK-NEXT: ret i32 [[A]] |
| ; |
| %C = call i32 @mul(i32 %a, i32 1) |
| ret i32 %C |
| } |
| |
| define i32 @mul(i32 %a, i32 %b) { |
| ; CHECK-LABEL: define i32 @mul( |
| ; CHECK-SAME: i32 [[A:%.*]], i32 [[B:%.*]]) { |
| ; CHECK-NEXT: [[MUL:%.*]] = mul i32 [[A]], [[B]] |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: store i32 0, ptr @glbl, align 4 |
| ; CHECK-NEXT: ret i32 [[MUL]] |
| ; |
| %mul = mul i32 %a, %b |
| call void @pad() |
| store i32 0, ptr @glbl |
| ret i32 %mul |
| } |
| |
| |
| |
| define i32 @outer_div1(i32 %a) { |
| ; CHECK-LABEL: define i32 @outer_div1( |
| ; CHECK-SAME: i32 [[A:%.*]]) { |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: store i32 0, ptr @glbl, align 4 |
| ; CHECK-NEXT: ret i32 0 |
| ; |
| %C = call i32 @div1(i32 0, i32 %a) |
| ret i32 %C |
| } |
| |
| define i32 @outer_div2(i32 %a) { |
| ; CHECK-LABEL: define i32 @outer_div2( |
| ; CHECK-SAME: i32 [[A:%.*]]) { |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: store i32 0, ptr @glbl, align 4 |
| ; CHECK-NEXT: ret i32 [[A]] |
| ; |
| %C = call i32 @div1(i32 %a, i32 1) |
| ret i32 %C |
| } |
| |
| define i32 @div1(i32 %a, i32 %b) { |
| ; CHECK-LABEL: define i32 @div1( |
| ; CHECK-SAME: i32 [[A:%.*]], i32 [[B:%.*]]) { |
| ; CHECK-NEXT: [[DIV:%.*]] = sdiv i32 [[A]], [[B]] |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: store i32 0, ptr @glbl, align 4 |
| ; CHECK-NEXT: ret i32 [[DIV]] |
| ; |
| %div = sdiv i32 %a, %b |
| call void @pad() |
| store i32 0, ptr @glbl |
| ret i32 %div |
| } |
| |
| |
| define i32 @outer_div3(i32 %a) { |
| ; CHECK-LABEL: define i32 @outer_div3( |
| ; CHECK-SAME: i32 [[A:%.*]]) { |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: ret i32 1 |
| ; |
| %C = call i32 @div2(i32 %a) |
| ret i32 %C |
| } |
| |
| define i32 @div2(i32 %a) { |
| ; CHECK-LABEL: define i32 @div2( |
| ; CHECK-SAME: i32 [[A:%.*]]) { |
| ; CHECK-NEXT: [[DIV:%.*]] = sdiv i32 [[A]], [[A]] |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: ret i32 [[DIV]] |
| ; |
| %div = sdiv i32 %a, %a |
| call void @pad() |
| ret i32 %div |
| } |
| |
| |
| |
| define i32 @outer_rem1(i32 %a) { |
| ; CHECK-LABEL: define i32 @outer_rem1( |
| ; CHECK-SAME: i32 [[A:%.*]]) { |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: store i32 0, ptr @glbl, align 4 |
| ; CHECK-NEXT: ret i32 0 |
| ; |
| %C = call i32 @rem1(i32 0, i32 %a) |
| ret i32 %C |
| } |
| |
| define i32 @outer_rem2(i32 %a) { |
| ; CHECK-LABEL: define i32 @outer_rem2( |
| ; CHECK-SAME: i32 [[A:%.*]]) { |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: store i32 0, ptr @glbl, align 4 |
| ; CHECK-NEXT: ret i32 0 |
| ; |
| %C = call i32 @rem1(i32 %a, i32 1) |
| ret i32 %C |
| } |
| |
| define i32 @rem1(i32 %a, i32 %b) { |
| ; CHECK-LABEL: define i32 @rem1( |
| ; CHECK-SAME: i32 [[A:%.*]], i32 [[B:%.*]]) { |
| ; CHECK-NEXT: [[REM:%.*]] = urem i32 [[A]], [[B]] |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: store i32 0, ptr @glbl, align 4 |
| ; CHECK-NEXT: ret i32 [[REM]] |
| ; |
| %rem = urem i32 %a, %b |
| call void @pad() |
| store i32 0, ptr @glbl |
| ret i32 %rem |
| } |
| |
| |
| define i32 @outer_rem3(i32 %a) { |
| ; CHECK-LABEL: define i32 @outer_rem3( |
| ; CHECK-SAME: i32 [[A:%.*]]) { |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: ret i32 0 |
| ; |
| %C = call i32 @rem2(i32 %a) |
| ret i32 %C |
| } |
| |
| define i32 @rem2(i32 %a) { |
| ; CHECK-LABEL: define i32 @rem2( |
| ; CHECK-SAME: i32 [[A:%.*]]) { |
| ; CHECK-NEXT: [[REM:%.*]] = urem i32 [[A]], [[A]] |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: ret i32 [[REM]] |
| ; |
| %rem = urem i32 %a, %a |
| call void @pad() |
| ret i32 %rem |
| } |
| |
| |
| |
| define i32 @outer_shl1(i32 %a) { |
| ; CHECK-LABEL: define i32 @outer_shl1( |
| ; CHECK-SAME: i32 [[A:%.*]]) { |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: store i32 0, ptr @glbl, align 4 |
| ; CHECK-NEXT: ret i32 [[A]] |
| ; |
| %C = call i32 @shl(i32 %a, i32 0) |
| ret i32 %C |
| } |
| |
| define i32 @shl(i32 %a, i32 %b) { |
| ; CHECK-LABEL: define i32 @shl( |
| ; CHECK-SAME: i32 [[A:%.*]], i32 [[B:%.*]]) { |
| ; CHECK-NEXT: [[SHL:%.*]] = shl i32 [[A]], [[B]] |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: store i32 0, ptr @glbl, align 4 |
| ; CHECK-NEXT: ret i32 [[SHL]] |
| ; |
| %shl = shl i32 %a, %b |
| call void @pad() |
| store i32 0, ptr @glbl |
| ret i32 %shl |
| } |
| |
| |
| |
| define i32 @outer_shr1(i32 %a) { |
| ; CHECK-LABEL: define i32 @outer_shr1( |
| ; CHECK-SAME: i32 [[A:%.*]]) { |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: store i32 0, ptr @glbl, align 4 |
| ; CHECK-NEXT: ret i32 [[A]] |
| ; |
| %C = call i32 @shr(i32 %a, i32 0) |
| ret i32 %C |
| } |
| |
| define i32 @shr(i32 %a, i32 %b) { |
| ; CHECK-LABEL: define i32 @shr( |
| ; CHECK-SAME: i32 [[A:%.*]], i32 [[B:%.*]]) { |
| ; CHECK-NEXT: [[SHR:%.*]] = ashr i32 [[A]], [[B]] |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: store i32 0, ptr @glbl, align 4 |
| ; CHECK-NEXT: ret i32 [[SHR]] |
| ; |
| %shr = ashr i32 %a, %b |
| call void @pad() |
| store i32 0, ptr @glbl |
| ret i32 %shr |
| } |
| |
| |
| |
| define i1 @outer_and1(i1 %a) { |
| ; CHECK-LABEL: define i1 @outer_and1( |
| ; CHECK-SAME: i1 [[A:%.*]]) { |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: store i32 0, ptr @glbl, align 4 |
| ; CHECK-NEXT: ret i1 false |
| ; |
| %c = call i1 @and1(i1 %a, i1 false) |
| ret i1 %c |
| } |
| |
| define i1 @outer_and2(i1 %a) { |
| ; CHECK-LABEL: define i1 @outer_and2( |
| ; CHECK-SAME: i1 [[A:%.*]]) { |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: store i32 0, ptr @glbl, align 4 |
| ; CHECK-NEXT: ret i1 [[A]] |
| ; |
| %c = call i1 @and1(i1 %a, i1 true) |
| ret i1 %c |
| } |
| |
| define i1 @and1(i1 %a, i1 %b) { |
| ; CHECK-LABEL: define i1 @and1( |
| ; CHECK-SAME: i1 [[A:%.*]], i1 [[B:%.*]]) { |
| ; CHECK-NEXT: [[AND:%.*]] = and i1 [[A]], [[B]] |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: store i32 0, ptr @glbl, align 4 |
| ; CHECK-NEXT: ret i1 [[AND]] |
| ; |
| %and = and i1 %a, %b |
| call void @pad() |
| store i32 0, ptr @glbl |
| ret i1 %and |
| } |
| |
| |
| define i1 @outer_and3(i1 %a) { |
| ; CHECK-LABEL: define i1 @outer_and3( |
| ; CHECK-SAME: i1 [[A:%.*]]) { |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: ret i1 [[A]] |
| ; |
| %c = call i1 @and2(i1 %a) |
| ret i1 %c |
| } |
| |
| define i1 @and2(i1 %a) { |
| ; CHECK-LABEL: define i1 @and2( |
| ; CHECK-SAME: i1 [[A:%.*]]) { |
| ; CHECK-NEXT: [[AND:%.*]] = and i1 [[A]], [[A]] |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: ret i1 [[AND]] |
| ; |
| %and = and i1 %a, %a |
| call void @pad() |
| ret i1 %and |
| } |
| |
| |
| |
| define i1 @outer_or1(i1 %a) { |
| ; CHECK-LABEL: define i1 @outer_or1( |
| ; CHECK-SAME: i1 [[A:%.*]]) { |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: store i32 0, ptr @glbl, align 4 |
| ; CHECK-NEXT: ret i1 [[A]] |
| ; |
| %c = call i1 @or1(i1 %a, i1 false) |
| ret i1 %c |
| } |
| |
| define i1 @outer_or2(i1 %a) { |
| ; CHECK-LABEL: define i1 @outer_or2( |
| ; CHECK-SAME: i1 [[A:%.*]]) { |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: store i32 0, ptr @glbl, align 4 |
| ; CHECK-NEXT: ret i1 true |
| ; |
| %c = call i1 @or1(i1 %a, i1 true) |
| ret i1 %c |
| } |
| |
| define i1 @or1(i1 %a, i1 %b) { |
| ; CHECK-LABEL: define i1 @or1( |
| ; CHECK-SAME: i1 [[A:%.*]], i1 [[B:%.*]]) { |
| ; CHECK-NEXT: [[OR:%.*]] = or i1 [[A]], [[B]] |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: store i32 0, ptr @glbl, align 4 |
| ; CHECK-NEXT: ret i1 [[OR]] |
| ; |
| %or = or i1 %a, %b |
| call void @pad() |
| store i32 0, ptr @glbl |
| ret i1 %or |
| } |
| |
| |
| define i1 @outer_or3(i1 %a) { |
| ; CHECK-LABEL: define i1 @outer_or3( |
| ; CHECK-SAME: i1 [[A:%.*]]) { |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: ret i1 [[A]] |
| ; |
| %c = call i1 @or2(i1 %a) |
| ret i1 %c |
| } |
| |
| define i1 @or2(i1 %a) { |
| ; CHECK-LABEL: define i1 @or2( |
| ; CHECK-SAME: i1 [[A:%.*]]) { |
| ; CHECK-NEXT: [[OR:%.*]] = or i1 [[A]], [[A]] |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: ret i1 [[OR]] |
| ; |
| %or = or i1 %a, %a |
| call void @pad() |
| ret i1 %or |
| } |
| |
| |
| |
| define i1 @outer_xor1(i1 %a) { |
| ; CHECK-LABEL: define i1 @outer_xor1( |
| ; CHECK-SAME: i1 [[A:%.*]]) { |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: store i32 0, ptr @glbl, align 4 |
| ; CHECK-NEXT: ret i1 [[A]] |
| ; |
| %c = call i1 @xor1(i1 %a, i1 false) |
| ret i1 %c |
| } |
| |
| define i1 @xor1(i1 %a, i1 %b) { |
| ; CHECK-LABEL: define i1 @xor1( |
| ; CHECK-SAME: i1 [[A:%.*]], i1 [[B:%.*]]) { |
| ; CHECK-NEXT: [[XOR:%.*]] = xor i1 [[A]], [[B]] |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: store i32 0, ptr @glbl, align 4 |
| ; CHECK-NEXT: ret i1 [[XOR]] |
| ; |
| %xor = xor i1 %a, %b |
| call void @pad() |
| store i32 0, ptr @glbl |
| ret i1 %xor |
| } |
| |
| |
| define i1 @outer_xor3(i1 %a) { |
| ; CHECK-LABEL: define i1 @outer_xor3( |
| ; CHECK-SAME: i1 [[A:%.*]]) { |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: ret i1 false |
| ; |
| %c = call i1 @xor2(i1 %a) |
| ret i1 %c |
| } |
| |
| define i1 @xor2(i1 %a) { |
| ; CHECK-LABEL: define i1 @xor2( |
| ; CHECK-SAME: i1 [[A:%.*]]) { |
| ; CHECK-NEXT: [[XOR:%.*]] = xor i1 [[A]], [[A]] |
| ; CHECK-NEXT: call void @pad() |
| ; CHECK-NEXT: ret i1 [[XOR]] |
| ; |
| %xor = xor i1 %a, %a |
| call void @pad() |
| ret i1 %xor |
| } |