15ca0bacaSJF Bastien//===- WebAssemblyInstrCall.td-WebAssembly Call codegen support -*- tablegen -*-
25ca0bacaSJF Bastien//
32946cd70SChandler Carruth// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
42946cd70SChandler Carruth// See https://llvm.org/LICENSE.txt for license information.
52946cd70SChandler Carruth// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
65ca0bacaSJF Bastien//
75ca0bacaSJF Bastien//===----------------------------------------------------------------------===//
85ca0bacaSJF Bastien///
95ca0bacaSJF Bastien/// \file
105f8f34e4SAdrian Prantl/// WebAssembly Call operand code-gen constructs.
115ca0bacaSJF Bastien///
125ca0bacaSJF Bastien//===----------------------------------------------------------------------===//
135ca0bacaSJF Bastien
14e2a7a827SDan Gohman// TODO: addr64: These currently assume the callee address is 32-bit.
1548dac310SWouter van Oortmerssen// FIXME: add $type to first call_indirect asmstr (and maybe $flags)
16e2a7a827SDan Gohman
17905bef5cSDan Gohman// Call sequence markers. These have an immediate which represents the amount of
18905bef5cSDan Gohman// stack space to allocate or free, which is used for varargs lowering.
195a143063SDerek Schufflet Uses = [SP32, SP64], Defs = [SP32, SP64], isCodeGenOnly = 1 in {
2048dac310SWouter van Oortmerssendefm ADJCALLSTACKDOWN : NRI<(outs), (ins i32imm:$amt, i32imm:$amt2),
21d526b13eSSerge Pavlov                            [(WebAssemblycallseq_start timm:$amt, timm:$amt2)]>;
2248dac310SWouter van Oortmerssendefm ADJCALLSTACKUP : NRI<(outs), (ins i32imm:$amt, i32imm:$amt2),
238bb5f292SDerek Schuff                          [(WebAssemblycallseq_end timm:$amt, timm:$amt2)]>;
244367587fSHeejin Ahn} // Uses = [SP32, SP64], Defs = [SP32, SP64], isCodeGenOnly = 1
25af111db8SJF Bastien
26d934cb88SDan Gohman
27ca9ba764SThomas Livelylet Uses = [SP32, SP64], isCall = 1 in {
2839bf39f3SDerek Schuff
29d5191096SThomas Lively// CALL should take both variadic arguments and produce variadic results, but
30d5191096SThomas Lively// this is not possible to model directly. Instead, we select calls to a
31*0312b9f5SKazuaki Ishizaki// CALL_PARAMS taking variadic arguments linked with a CALL_RESULTS that handles
32d5191096SThomas Lively// producing the call's variadic results. We recombine the two in a custom
33d5191096SThomas Lively// inserter hook after DAG ISel, so passes over MachineInstrs will only ever
34d5191096SThomas Lively// observe CALL nodes with all of the expected variadic uses and defs.
35d5191096SThomas Livelylet isPseudo = 1 in
36d5191096SThomas Livelydefm CALL_PARAMS :
37d5191096SThomas Lively  I<(outs), (ins function32_op:$callee, variable_ops),
38d5191096SThomas Lively    (outs), (ins function32_op:$callee), [],
39d5191096SThomas Lively    "call_params\t$callee", "call_params\t$callee", -1>;
40d5191096SThomas Lively
41d5191096SThomas Livelylet variadicOpsAreDefs = 1, usesCustomInserter = 1, isPseudo = 1 in
42d5191096SThomas Livelydefm CALL_RESULTS :
43d5191096SThomas Lively  I<(outs), (ins variable_ops), (outs), (ins), [],
44d5191096SThomas Lively     "call_results", "call_results", -1>;
45d5191096SThomas Lively
46ca9ba764SThomas Livelylet variadicOpsAreDefs = 1, usesCustomInserter = 1, isPseudo = 1 in
47ca9ba764SThomas Livelydefm RET_CALL_RESULTS :
48ca9ba764SThomas Lively  I<(outs), (ins variable_ops), (outs), (ins), [],
49ca9ba764SThomas Lively     "return_call_results", "return_call_results", -1>;
507b64a590SThomas Lively
519d37f5afSThomas Livelylet variadicOpsAreDefs = 1 in
527b64a590SThomas Livelydefm CALL :
537b64a590SThomas Lively  I<(outs), (ins function32_op:$callee, variable_ops),
547b64a590SThomas Lively    (outs), (ins function32_op:$callee), [],
55ca9ba764SThomas Lively    "call", "call\t$callee", 0x10>;
567b64a590SThomas Lively
579d37f5afSThomas Livelylet variadicOpsAreDefs = 1 in
589d37f5afSThomas Livelydefm CALL_INDIRECT :
599d37f5afSThomas Lively I<(outs), (ins TypeIndex:$type, i32imm:$flags, variable_ops),
609d37f5afSThomas Lively   (outs), (ins TypeIndex:$type, i32imm:$flags), [],
619d37f5afSThomas Lively   "call_indirect", "call_indirect\t$type", 0x11>;
629d37f5afSThomas Lively
63918e9055SThomas Livelylet isReturn = 1, isTerminator = 1, hasCtrlDep = 1, isBarrier = 1 in
64a1d97a96SThomas Livelydefm RET_CALL :
65a1d97a96SThomas Lively  I<(outs), (ins function32_op:$callee, variable_ops),
66ca9ba764SThomas Lively    (outs), (ins function32_op:$callee), [],
67a1d97a96SThomas Lively    "return_call    \t$callee", "return_call\t$callee", 0x12>,
68a1d97a96SThomas Lively  Requires<[HasTailCall]>;
69a1d97a96SThomas Lively
70a1d97a96SThomas Livelylet isReturn = 1 in
71a1d97a96SThomas Livelydefm RET_CALL_INDIRECT :
72a1d97a96SThomas Lively  I<(outs), (ins TypeIndex:$type, i32imm:$flags, variable_ops),
73ca9ba764SThomas Lively    (outs), (ins TypeIndex:$type, i32imm:$flags), [],
74a1d97a96SThomas Lively    "return_call_indirect\t", "return_call_indirect\t$type",
75a1d97a96SThomas Lively    0x13>,
76a1d97a96SThomas Lively  Requires<[HasTailCall]>;
77a1d97a96SThomas Lively
78af111db8SJF Bastien} // Uses = [SP32,SP64], isCall = 1
79