1 | // RUN: %clang_cc1 -O3 -triple %itanium_abi_triple -emit-llvm -o - %s | FileCheck %s |
2 | |
3 | // Is FP_CONTRACT honored in a simple case? |
4 | float fp_contract_1(float a, float b, float c) { |
5 | // CHECK: _Z13fp_contract_1fff |
6 | // CHECK: %[[M:.+]] = fmul contract float %a, %b |
7 | // CHECK-NEXT: fadd contract float %[[M]], %c |
8 | #pragma clang fp contract(fast) |
9 | return a * b + c; |
10 | } |
11 | |
12 | // Is FP_CONTRACT state cleared on exiting compound statements? |
13 | float fp_contract_2(float a, float b, float c) { |
14 | // CHECK: _Z13fp_contract_2fff |
15 | // CHECK: %[[M:.+]] = fmul float %a, %b |
16 | // CHECK-NEXT: fadd float %[[M]], %c |
17 | { |
18 | #pragma clang fp contract(fast) |
19 | } |
20 | return a * b + c; |
21 | } |
22 | |
23 | // Does FP_CONTRACT survive template instantiation? |
24 | class Foo {}; |
25 | Foo operator+(Foo, Foo); |
26 | |
27 | template <typename T> |
28 | T template_muladd(T a, T b, T c) { |
29 | #pragma clang fp contract(fast) |
30 | return a * b + c; |
31 | } |
32 | |
33 | float fp_contract_3(float a, float b, float c) { |
34 | // CHECK: _Z13fp_contract_3fff |
35 | // CHECK: %[[M:.+]] = fmul contract float %a, %b |
36 | // CHECK-NEXT: fadd contract float %[[M]], %c |
37 | return template_muladd<float>(a, b, c); |
38 | } |
39 | |
40 | template <typename T> |
41 | class fp_contract_4 { |
42 | float method(float a, float b, float c) { |
43 | #pragma clang fp contract(fast) |
44 | return a * b + c; |
45 | } |
46 | }; |
47 | |
48 | template class fp_contract_4<int>; |
49 | // CHECK: _ZN13fp_contract_4IiE6methodEfff |
50 | // CHECK: %[[M:.+]] = fmul contract float %a, %b |
51 | // CHECK-NEXT: fadd contract float %[[M]], %c |
52 | |
53 | // Check file-scoped FP_CONTRACT |
54 | #pragma clang fp contract(fast) |
55 | float fp_contract_5(float a, float b, float c) { |
56 | // CHECK: _Z13fp_contract_5fff |
57 | // CHECK: %[[M:.+]] = fmul contract float %a, %b |
58 | // CHECK-NEXT: fadd contract float %[[M]], %c |
59 | return a * b + c; |
60 | } |
61 | |
62 | // Verify that we can handle multiple flags on the same pragma |
63 | #pragma clang fp contract(fast) contract(off) |
64 | float fp_contract_6(float a, float b, float c) { |
65 | // CHECK: _Z13fp_contract_6fff |
66 | // CHECK: %[[M:.+]] = fmul float %a, %b |
67 | // CHECK-NEXT: fadd float %[[M]], %c |
68 | return a * b + c; |
69 | } |
70 | |