1296417Sdim//=- WebAssemblyInstrFormats.td - WebAssembly Instr. Formats -*- tablegen -*-=// 2285163Sdim// 3353358Sdim// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4353358Sdim// See https://llvm.org/LICENSE.txt for license information. 5353358Sdim// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6285163Sdim// 7285163Sdim//===----------------------------------------------------------------------===// 8286684Sdim/// 9286684Sdim/// \file 10341825Sdim/// WebAssembly instruction format definitions. 11286684Sdim/// 12285163Sdim//===----------------------------------------------------------------------===// 13285163Sdim 14296417Sdim// WebAssembly Instruction Format. 15341825Sdim// We instantiate 2 of these for every actual instruction (register based 16341825Sdim// and stack based), see below. 17344779Sdimclass WebAssemblyInst<bits<32> inst, string asmstr, string stack> : StackRel, 18344779Sdim Instruction { 19344779Sdim bits<32> Inst = inst; // Instruction encoding. 20344779Sdim string StackBased = stack; 21344779Sdim string BaseName = NAME; 22285163Sdim let Namespace = "WebAssembly"; 23285163Sdim let Pattern = []; 24296417Sdim let AsmString = asmstr; 25353358Sdim // When there are multiple instructions that map to the same encoding (in 26353358Sdim // e.g. the disassembler use case) prefer the one where IsCanonical == 1. 27353358Sdim bit IsCanonical = 0; 28285163Sdim} 29285163Sdim 30341825Sdim// Normal instructions. Default instantiation of a WebAssemblyInst. 31344779Sdimclass NI<dag oops, dag iops, list<dag> pattern, string stack, 32344779Sdim string asmstr = "", bits<32> inst = -1> 33341825Sdim : WebAssemblyInst<inst, asmstr, stack> { 34285163Sdim dag OutOperandList = oops; 35285163Sdim dag InOperandList = iops; 36285163Sdim let Pattern = pattern; 37344779Sdim let Defs = [ARGUMENTS]; 38285163Sdim} 39286684Sdim 40341825Sdim// Generates both register and stack based versions of one actual instruction. 41341825Sdim// We have 2 sets of operands (oops & iops) for the register and stack 42341825Sdim// based version of this instruction, as well as the corresponding asmstr. 43341825Sdim// The register versions have virtual-register operands which correspond to wasm 44341825Sdim// locals or stack locations. Each use and def of the register corresponds to an 45344779Sdim// implicit local.get / local.set or access of stack operands in wasm. These 46341825Sdim// instructions are used for ISel and all MI passes. The stack versions of the 47341825Sdim// instructions do not have register operands (they implicitly operate on the 48344779Sdim// stack), and local.gets and local.sets are explicit. The register instructions 49341825Sdim// are converted to their corresponding stack instructions before lowering to 50341825Sdim// MC. 51341825Sdim// Every instruction should want to be based on this multi-class to guarantee 52341825Sdim// there is always an equivalent pair of instructions. 53341825Sdimmulticlass I<dag oops_r, dag iops_r, dag oops_s, dag iops_s, 54341825Sdim list<dag> pattern_r, string asmstr_r = "", string asmstr_s = "", 55341825Sdim bits<32> inst = -1> { 56344779Sdim let isCodeGenOnly = 1 in 57344779Sdim def "" : NI<oops_r, iops_r, pattern_r, "false", asmstr_r, inst>; 58344779Sdim let BaseName = NAME in 59344779Sdim def _S : NI<oops_s, iops_s, [], "true", asmstr_s, inst>; 60341825Sdim} 61314564Sdim 62341825Sdim// For instructions that have no register ops, so both sets are the same. 63341825Sdimmulticlass NRI<dag oops, dag iops, list<dag> pattern, string asmstr = "", 64341825Sdim bits<32> inst = -1> { 65341825Sdim defm "": I<oops, iops, oops, iops, pattern, asmstr, asmstr, inst>; 66341825Sdim} 67