1; Test that the pow library call simplifier works correctly. 2; 3; RUN: opt < %s -instcombine -S | FileCheck %s 4; rdar://7251832 5 6; NOTE: The readonly attribute on the pow call should be preserved 7; in the cases below where pow is transformed into another function call. 8 9declare float @powf(float, float) nounwind readonly 10declare double @pow(double, double) nounwind readonly 11 12; Check pow(1.0, x) -> 1.0. 13 14define float @test_simplify1(float %x) { 15; CHECK: @test_simplify1 16 %retval = call float @powf(float 1.0, float %x) 17 ret float %retval 18; CHECK-NEXT: ret float 1.000000e+00 19} 20 21define double @test_simplify2(double %x) { 22; CHECK: @test_simplify2 23 %retval = call double @pow(double 1.0, double %x) 24 ret double %retval 25; CHECK-NEXT: ret double 1.000000e+00 26} 27 28; Check pow(2.0, x) -> exp2(x). 29 30define float @test_simplify3(float %x) { 31; CHECK: @test_simplify3 32 %retval = call float @powf(float 2.0, float %x) 33; CHECK-NEXT: [[EXP2F:%[a-z0-9]+]] = call float @exp2f(float %x) [[NUW_RO:#[0-9]+]] 34 ret float %retval 35; CHECK-NEXT: ret float [[EXP2F]] 36} 37 38define double @test_simplify4(double %x) { 39; CHECK: @test_simplify4 40 %retval = call double @pow(double 2.0, double %x) 41; CHECK-NEXT: [[EXP2:%[a-z0-9]+]] = call double @exp2(double %x) [[NUW_RO]] 42 ret double %retval 43; CHECK-NEXT: ret double [[EXP2]] 44} 45 46; Check pow(x, 0.0) -> 1.0. 47 48define float @test_simplify5(float %x) { 49; CHECK: @test_simplify5 50 %retval = call float @powf(float %x, float 0.0) 51 ret float %retval 52; CHECK-NEXT: ret float 1.000000e+00 53} 54 55define double @test_simplify6(double %x) { 56; CHECK: @test_simplify6 57 %retval = call double @pow(double %x, double 0.0) 58 ret double %retval 59; CHECK-NEXT: ret double 1.000000e+00 60} 61 62; Check pow(x, 0.5) -> fabs(sqrt(x)), where x != -infinity. 63 64define float @test_simplify7(float %x) { 65; CHECK: @test_simplify7 66 %retval = call float @powf(float %x, float 0.5) 67; CHECK-NEXT: [[SQRTF:%[a-z0-9]+]] = call float @sqrtf(float %x) [[NUW_RO]] 68; CHECK-NEXT: [[FABSF:%[a-z0-9]+]] = call float @fabsf(float [[SQRTF]]) [[NUW_RO]] 69; CHECK-NEXT: [[FCMP:%[a-z0-9]+]] = fcmp oeq float %x, 0xFFF0000000000000 70; CHECK-NEXT: [[SELECT:%[a-z0-9]+]] = select i1 [[FCMP]], float 0x7FF0000000000000, float [[FABSF]] 71 ret float %retval 72; CHECK-NEXT: ret float [[SELECT]] 73} 74 75define double @test_simplify8(double %x) { 76; CHECK: @test_simplify8 77 %retval = call double @pow(double %x, double 0.5) 78; CHECK-NEXT: [[SQRT:%[a-z0-9]+]] = call double @sqrt(double %x) [[NUW_RO]] 79; CHECK-NEXT: [[FABS:%[a-z0-9]+]] = call double @fabs(double [[SQRT]]) [[NUW_RO]] 80; CHECK-NEXT: [[FCMP:%[a-z0-9]+]] = fcmp oeq double %x, 0xFFF0000000000000 81; CHECK-NEXT: [[SELECT:%[a-z0-9]+]] = select i1 [[FCMP]], double 0x7FF0000000000000, double [[FABS]] 82 ret double %retval 83; CHECK-NEXT: ret double [[SELECT]] 84} 85 86; Check pow(-infinity, 0.5) -> +infinity. 87 88define float @test_simplify9(float %x) { 89; CHECK: @test_simplify9 90 %retval = call float @powf(float 0xFFF0000000000000, float 0.5) 91 ret float %retval 92; CHECK-NEXT: ret float 0x7FF0000000000000 93} 94 95define double @test_simplify10(double %x) { 96; CHECK: @test_simplify10 97 %retval = call double @pow(double 0xFFF0000000000000, double 0.5) 98 ret double %retval 99; CHECK-NEXT: ret double 0x7FF0000000000000 100} 101 102; Check pow(x, 1.0) -> x. 103 104define float @test_simplify11(float %x) { 105; CHECK: @test_simplify11 106 %retval = call float @powf(float %x, float 1.0) 107 ret float %retval 108; CHECK-NEXT: ret float %x 109} 110 111define double @test_simplify12(double %x) { 112; CHECK: @test_simplify12 113 %retval = call double @pow(double %x, double 1.0) 114 ret double %retval 115; CHECK-NEXT: ret double %x 116} 117 118; Check pow(x, 2.0) -> x*x. 119 120define float @test_simplify13(float %x) { 121; CHECK: @test_simplify13 122 %retval = call float @powf(float %x, float 2.0) 123; CHECK-NEXT: [[SQUARE:%[a-z0-9]+]] = fmul float %x, %x 124 ret float %retval 125; CHECK-NEXT: ret float [[SQUARE]] 126} 127 128define double @test_simplify14(double %x) { 129; CHECK: @test_simplify14 130 %retval = call double @pow(double %x, double 2.0) 131; CHECK-NEXT: [[SQUARE:%[a-z0-9]+]] = fmul double %x, %x 132 ret double %retval 133; CHECK-NEXT: ret double [[SQUARE]] 134} 135 136; Check pow(x, -1.0) -> 1.0/x. 137 138define float @test_simplify15(float %x) { 139; CHECK: @test_simplify15 140 %retval = call float @powf(float %x, float -1.0) 141; CHECK-NEXT: [[RECIPROCAL:%[a-z0-9]+]] = fdiv float 1.000000e+00, %x 142 ret float %retval 143; CHECK-NEXT: ret float [[RECIPROCAL]] 144} 145 146define double @test_simplify16(double %x) { 147; CHECK: @test_simplify16 148 %retval = call double @pow(double %x, double -1.0) 149; CHECK-NEXT: [[RECIPROCAL:%[a-z0-9]+]] = fdiv double 1.000000e+00, %x 150 ret double %retval 151; CHECK-NEXT: ret double [[RECIPROCAL]] 152} 153 154; CHECK: attributes [[NUW_RO]] = { nounwind readonly } 155