| 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 declare float @dummy() |
| 14 entry: | |
| 15 ret float 0.000000e+00 | |
| 16 } | |
| 17 ; CHECK-LABEL: dummy | |
| 18 | 12 |
| 19 ; The call is ignored, but the top of the FP stack still needs to be | 13 ; The call is ignored, but the top of the FP stack still needs to be |
| 20 ; popped. | 14 ; popped. |
| 21 define i32 @ignored_fp_call() { | 15 define i32 @ignored_fp_call() { |
| 22 entry: | 16 entry: |
| 23 %ignored = call float @dummy() | 17 %ignored = call float @dummy() |
| 24 ret i32 0 | 18 ret i32 0 |
| 25 } | 19 } |
| 26 ; CHECK-LABEL: ignored_fp_call | 20 ; CHECK-LABEL: ignored_fp_call |
| 27 ; CHECK: call dummy | 21 ; CHECK: call {{.*}} R_{{.*}} dummy |
| 28 ; CHECK: fstp | 22 ; CHECK: fstp |
| 29 | 23 |
| 30 ; The top of the FP stack is popped and subsequently used. | 24 ; The top of the FP stack is popped and subsequently used. |
| 31 define i32 @converted_fp_call() { | 25 define i32 @converted_fp_call() { |
| 32 entry: | 26 entry: |
| 33 %fp = call float @dummy() | 27 %fp = call float @dummy() |
| 34 %ret = fptosi float %fp to i32 | 28 %ret = fptosi float %fp to i32 |
| 35 ret i32 %ret | 29 ret i32 %ret |
| 36 } | 30 } |
| 37 ; CHECK-LABEL: converted_fp_call | 31 ; CHECK-LABEL: converted_fp_call |
| 38 ; CHECK: call dummy | 32 ; CHECK: call {{.*}} R_{{.*}} dummy |
| 39 ; CHECK: fstp | 33 ; CHECK: fstp |
| 40 ; CHECK: cvttss2si | 34 ; CHECK: cvttss2si |
| 41 | 35 |
| 42 ; The top of the FP stack is ultimately passed through as the return | 36 ; The top of the FP stack is ultimately passed through as the return |
| 43 ; value. Note: the translator could optimized by not popping and | 37 ; value. Note: the translator could optimized by not popping and |
| 44 ; re-pushing, in which case the test would need to be changed. | 38 ; re-pushing, in which case the test would need to be changed. |
| 45 define float @returned_fp_call() { | 39 define float @returned_fp_call() { |
| 46 entry: | 40 entry: |
| 47 %fp = call float @dummy() | 41 %fp = call float @dummy() |
| 48 ret float %fp | 42 ret float %fp |
| 49 } | 43 } |
| 50 ; CHECK-LABEL: returned_fp_call | 44 ; CHECK-LABEL: returned_fp_call |
| 51 ; CHECK: call dummy | 45 ; CHECK: call {{.*}} R_{{.*}} dummy |
| 52 ; CHECK: fstp | 46 ; CHECK: fstp |
| 53 ; CHECK: fld | 47 ; CHECK: fld |
| OLD | NEW |