Home | History | Annotate | Download | only in WebAssembly
      1 ; RUN: llc < %s -asm-verbose=false -disable-wasm-fallthrough-return-opt | FileCheck %s
      2 ; RUN: llc < %s -asm-verbose=false -disable-wasm-fallthrough-return-opt -fast-isel -fast-isel-abort=1 | FileCheck %s
      3 
      4 ; Test that basic call operations assemble as expected.
      5 
      6 target datalayout = "e-m:e-p:32:32-i64:64-n32:64-S128"
      7 target triple = "wasm32-unknown-unknown"
      8 
      9 declare i32 @i32_nullary()
     10 declare i32 @i32_unary(i32)
     11 declare i32 @i32_binary(i32, i32)
     12 declare i64 @i64_nullary()
     13 declare float @float_nullary()
     14 declare double @double_nullary()
     15 declare void @void_nullary()
     16 
     17 ; CHECK-LABEL: call_i32_nullary:
     18 ; CHECK-NEXT: .result i32{{$}}
     19 ; CHECK-NEXT: {{^}} i32.call $push[[NUM:[0-9]+]]=, i32_nullary@FUNCTION{{$}}
     20 ; CHECK-NEXT: return $pop[[NUM]]{{$}}
     21 define i32 @call_i32_nullary() {
     22   %r = call i32 @i32_nullary()
     23   ret i32 %r
     24 }
     25 
     26 ; CHECK-LABEL: call_i64_nullary:
     27 ; CHECK-NEXT: .result i64{{$}}
     28 ; CHECK-NEXT: {{^}} i64.call $push[[NUM:[0-9]+]]=, i64_nullary@FUNCTION{{$}}
     29 ; CHECK-NEXT: return $pop[[NUM]]{{$}}
     30 define i64 @call_i64_nullary() {
     31   %r = call i64 @i64_nullary()
     32   ret i64 %r
     33 }
     34 
     35 ; CHECK-LABEL: call_float_nullary:
     36 ; CHECK-NEXT: .result f32{{$}}
     37 ; CHECK-NEXT: {{^}} f32.call $push[[NUM:[0-9]+]]=, float_nullary@FUNCTION{{$}}
     38 ; CHECK-NEXT: return $pop[[NUM]]{{$}}
     39 define float @call_float_nullary() {
     40   %r = call float @float_nullary()
     41   ret float %r
     42 }
     43 
     44 ; CHECK-LABEL: call_double_nullary:
     45 ; CHECK-NEXT: .result f64{{$}}
     46 ; CHECK-NEXT: {{^}} f64.call $push[[NUM:[0-9]+]]=, double_nullary@FUNCTION{{$}}
     47 ; CHECK-NEXT: return $pop[[NUM]]{{$}}
     48 define double @call_double_nullary() {
     49   %r = call double @double_nullary()
     50   ret double %r
     51 }
     52 
     53 ; CHECK-LABEL: call_void_nullary:
     54 ; CHECK-NEXT: {{^}} call void_nullary@FUNCTION{{$}}
     55 ; CHECK-NEXT: return{{$}}
     56 define void @call_void_nullary() {
     57   call void @void_nullary()
     58   ret void
     59 }
     60 
     61 ; CHECK-LABEL: call_i32_unary:
     62 ; CHECK-NEXT: .param i32{{$}}
     63 ; CHECK-NEXT: .result i32{{$}}
     64 ; CHECK-NEXT: {{^}} i32.call $push[[NUM:[0-9]+]]=, i32_unary@FUNCTION, $0{{$}}
     65 ; CHECK-NEXT: return $pop[[NUM]]{{$}}
     66 define i32 @call_i32_unary(i32 %a) {
     67   %r = call i32 @i32_unary(i32 %a)
     68   ret i32 %r
     69 }
     70 
     71 ; CHECK-LABEL: call_i32_binary:
     72 ; CHECK-NEXT: .param i32, i32{{$}}
     73 ; CHECK-NEXT: .result i32{{$}}
     74 ; CHECK-NEXT: {{^}} i32.call $push[[NUM:[0-9]+]]=, i32_binary@FUNCTION, $0, $1{{$}}
     75 ; CHECK-NEXT: return $pop[[NUM]]{{$}}
     76 define i32 @call_i32_binary(i32 %a, i32 %b) {
     77   %r = call i32 @i32_binary(i32 %a, i32 %b)
     78   ret i32 %r
     79 }
     80 
     81 ; CHECK-LABEL: call_indirect_void:
     82 ; CHECK-NEXT: .param i32{{$}}
     83 ; CHECK-NEXT: {{^}} call_indirect $0{{$}}
     84 ; CHECK-NEXT: return{{$}}
     85 define void @call_indirect_void(void ()* %callee) {
     86   call void %callee()
     87   ret void
     88 }
     89 
     90 ; CHECK-LABEL: call_indirect_i32:
     91 ; CHECK-NEXT: .param i32{{$}}
     92 ; CHECK-NEXT: .result i32{{$}}
     93 ; CHECK-NEXT: {{^}} i32.call_indirect $push[[NUM:[0-9]+]]=, $0{{$}}
     94 ; CHECK-NEXT: return $pop[[NUM]]{{$}}
     95 define i32 @call_indirect_i32(i32 ()* %callee) {
     96   %t = call i32 %callee()
     97   ret i32 %t
     98 }
     99 
    100 ; CHECK-LABEL: tail_call_void_nullary:
    101 ; CHECK-NEXT: {{^}} call void_nullary@FUNCTION{{$}}
    102 ; CHECK-NEXT: return{{$}}
    103 define void @tail_call_void_nullary() {
    104   tail call void @void_nullary()
    105   ret void
    106 }
    107 
    108 ; CHECK-LABEL: fastcc_tail_call_void_nullary:
    109 ; CHECK-NEXT: {{^}} call void_nullary@FUNCTION{{$}}
    110 ; CHECK-NEXT: return{{$}}
    111 define void @fastcc_tail_call_void_nullary() {
    112   tail call fastcc void @void_nullary()
    113   ret void
    114 }
    115 
    116 ; CHECK-LABEL: coldcc_tail_call_void_nullary:
    117 ; CHECK-NEXT: {{^}} call void_nullary@FUNCTION{{$}}
    118 ; CHECK-NEXT: return{{$}}
    119 define void @coldcc_tail_call_void_nullary() {
    120   tail call coldcc void @void_nullary()
    121   ret void
    122 }
    123 
    124 ; TODO: test the following:
    125 ;  - More argument combinations.
    126 ;  - Tail call.
    127 ;  - Interesting returns (struct, multiple).
    128 ;  - Vararg.
    129