OLD | NEW |
1 ; Test that for calls returning a floating-point value, the calling | 1 ; Test that for calls returning a floating-point value, the calling |
2 ; ABI with respect to the x87 floating point stack is honored. In | 2 ; ABI with respect to the x87 floating point stack is honored. In |
3 ; particular, the top-of-stack must be popped regardless of whether | 3 ; particular, the top-of-stack must be popped regardless of whether |
4 ; its value is used. | 4 ; its value is used. |
5 | 5 |
6 ; RUN: %p2i -i %s --args -O2 --verbose none \ | 6 ; RUN: %p2i --assemble --disassemble -i %s --args -O2 --verbose none \ |
7 ; RUN: | llvm-mc -triple=i686-none-nacl -filetype=obj \ | 7 ; RUN: | FileCheck %s |
8 ; RUN: | llvm-objdump -d --symbolize -x86-asm-syntax=intel - | FileCheck %s | 8 ; RUN: %p2i --assemble --disassemble -i %s --args -Om1 --verbose none \ |
9 ; RUN: %p2i -i %s --args -Om1 --verbose none \ | 9 ; RUN: | FileCheck %s |
10 ; RUN: | llvm-mc -triple=i686-none-nacl -filetype=obj \ | |
11 ; RUN: | llvm-objdump -d --symbolize -x86-asm-syntax=intel - | FileCheck %s | |
12 | 10 |
13 define float @dummy() { | 11 define float @dummy() { |
14 entry: | 12 entry: |
15 ret float 0.000000e+00 | 13 ret float 0.000000e+00 |
16 } | 14 } |
17 ; CHECK-LABEL: dummy | 15 ; CHECK-LABEL: dummy |
18 | 16 |
19 ; The call is ignored, but the top of the FP stack still needs to be | 17 ; The call is ignored, but the top of the FP stack still needs to be |
20 ; popped. | 18 ; popped. |
21 define i32 @ignored_fp_call() { | 19 define i32 @ignored_fp_call() { |
22 entry: | 20 entry: |
23 %ignored = call float @dummy() | 21 %ignored = call float @dummy() |
24 ret i32 0 | 22 ret i32 0 |
25 } | 23 } |
26 ; CHECK-LABEL: ignored_fp_call | 24 ; CHECK-LABEL: ignored_fp_call |
27 ; CHECK: call dummy | 25 ; CHECK: call |
| 26 ; CHECK-NEXT: R_{{.*}} dummy |
28 ; CHECK: fstp | 27 ; CHECK: fstp |
29 | 28 |
30 ; The top of the FP stack is popped and subsequently used. | 29 ; The top of the FP stack is popped and subsequently used. |
31 define i32 @converted_fp_call() { | 30 define i32 @converted_fp_call() { |
32 entry: | 31 entry: |
33 %fp = call float @dummy() | 32 %fp = call float @dummy() |
34 %ret = fptosi float %fp to i32 | 33 %ret = fptosi float %fp to i32 |
35 ret i32 %ret | 34 ret i32 %ret |
36 } | 35 } |
37 ; CHECK-LABEL: converted_fp_call | 36 ; CHECK-LABEL: converted_fp_call |
38 ; CHECK: call dummy | 37 ; CHECK: call |
| 38 ; CHECK-NEXT: R_{{.*}} dummy |
39 ; CHECK: fstp | 39 ; CHECK: fstp |
40 ; CHECK: cvttss2si | 40 ; CHECK: cvttss2si |
41 | 41 |
42 ; The top of the FP stack is ultimately passed through as the return | 42 ; The top of the FP stack is ultimately passed through as the return |
43 ; value. Note: the translator could optimized by not popping and | 43 ; value. Note: the translator could optimized by not popping and |
44 ; re-pushing, in which case the test would need to be changed. | 44 ; re-pushing, in which case the test would need to be changed. |
45 define float @returned_fp_call() { | 45 define float @returned_fp_call() { |
46 entry: | 46 entry: |
47 %fp = call float @dummy() | 47 %fp = call float @dummy() |
48 ret float %fp | 48 ret float %fp |
49 } | 49 } |
50 ; CHECK-LABEL: returned_fp_call | 50 ; CHECK-LABEL: returned_fp_call |
51 ; CHECK: call dummy | 51 ; CHECK: call |
| 52 ; CHECK-NEXT: R_{{.*}} dummy |
52 ; CHECK: fstp | 53 ; CHECK: fstp |
53 ; CHECK: fld | 54 ; CHECK: fld |
OLD | NEW |