1 | //==- WebAssemblyMCTargetDesc.h - WebAssembly Target Descriptions -*- C++ -*-=// |
2 | // |
3 | // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. |
4 | // See https://llvm.org/LICENSE.txt for license information. |
5 | // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception |
6 | // |
7 | //===----------------------------------------------------------------------===// |
8 | /// |
9 | /// \file |
10 | /// This file provides WebAssembly-specific target descriptions. |
11 | /// |
12 | //===----------------------------------------------------------------------===// |
13 | |
14 | #ifndef LLVM_LIB_TARGET_WEBASSEMBLY_MCTARGETDESC_WEBASSEMBLYMCTARGETDESC_H |
15 | #define LLVM_LIB_TARGET_WEBASSEMBLY_MCTARGETDESC_WEBASSEMBLYMCTARGETDESC_H |
16 | |
17 | #include "llvm/BinaryFormat/Wasm.h" |
18 | #include "llvm/MC/MCContext.h" |
19 | #include "llvm/MC/MCInstrDesc.h" |
20 | #include "llvm/Support/CommandLine.h" |
21 | #include "llvm/Support/DataTypes.h" |
22 | #include <memory> |
23 | |
24 | namespace llvm { |
25 | |
26 | class MCAsmBackend; |
27 | class MCCodeEmitter; |
28 | class MCInstrInfo; |
29 | class MCObjectTargetWriter; |
30 | class Triple; |
31 | |
32 | MCCodeEmitter *createWebAssemblyMCCodeEmitter(const MCInstrInfo &MCII, |
33 | MCContext &Ctx); |
34 | |
35 | MCAsmBackend *createWebAssemblyAsmBackend(const Triple &TT); |
36 | |
37 | std::unique_ptr<MCObjectTargetWriter> |
38 | createWebAssemblyWasmObjectWriter(bool Is64Bit, bool IsEmscripten); |
39 | |
40 | namespace WebAssembly { |
41 | |
42 | // Exception handling / setjmp-longjmp handling command-line options |
43 | extern cl::opt<bool> WasmEnableEmEH; // asm.js-style EH |
44 | extern cl::opt<bool> WasmEnableEmSjLj; // asm.js-style SjLJ |
45 | extern cl::opt<bool> WasmEnableEH; // EH using Wasm EH instructions |
46 | extern cl::opt<bool> WasmEnableSjLj; // SjLj using Wasm EH instructions |
47 | extern cl::opt<bool> WasmUseLegacyEH; // Legacy Wasm EH |
48 | |
49 | enum OperandType { |
50 | /// Basic block label in a branch construct. |
51 | OPERAND_BASIC_BLOCK = MCOI::OPERAND_FIRST_TARGET, |
52 | /// Local index. |
53 | OPERAND_LOCAL, |
54 | /// Global index. |
55 | OPERAND_GLOBAL, |
56 | /// 32-bit integer immediates. |
57 | OPERAND_I32IMM, |
58 | /// 64-bit integer immediates. |
59 | OPERAND_I64IMM, |
60 | /// 32-bit floating-point immediates. |
61 | OPERAND_F32IMM, |
62 | /// 64-bit floating-point immediates. |
63 | OPERAND_F64IMM, |
64 | /// 8-bit vector lane immediate |
65 | OPERAND_VEC_I8IMM, |
66 | /// 16-bit vector lane immediate |
67 | OPERAND_VEC_I16IMM, |
68 | /// 32-bit vector lane immediate |
69 | OPERAND_VEC_I32IMM, |
70 | /// 64-bit vector lane immediate |
71 | OPERAND_VEC_I64IMM, |
72 | /// 32-bit unsigned function indices. |
73 | OPERAND_FUNCTION32, |
74 | /// 32-bit unsigned memory offsets. |
75 | OPERAND_OFFSET32, |
76 | /// 64-bit unsigned memory offsets. |
77 | OPERAND_OFFSET64, |
78 | /// p2align immediate for load and store address alignment. |
79 | OPERAND_P2ALIGN, |
80 | /// signature immediate for block/loop. |
81 | OPERAND_SIGNATURE, |
82 | /// type signature immediate for call_indirect. |
83 | OPERAND_TYPEINDEX, |
84 | /// Tag index. |
85 | OPERAND_TAG, |
86 | /// A list of branch targets for br_list. |
87 | OPERAND_BRLIST, |
88 | /// 32-bit unsigned table number. |
89 | OPERAND_TABLE, |
90 | /// A list of catch clauses for try_table. |
91 | OPERAND_CATCH_LIST, |
92 | }; |
93 | } // end namespace WebAssembly |
94 | |
95 | namespace WebAssemblyII { |
96 | |
97 | /// Target Operand Flag enum. |
98 | enum TOF { |
99 | MO_NO_FLAG = 0, |
100 | |
101 | // On a symbol operand this indicates that the immediate is a wasm global |
102 | // index. The value of the wasm global will be set to the symbol address at |
103 | // runtime. This adds a level of indirection similar to the GOT on native |
104 | // platforms. |
105 | MO_GOT, |
106 | |
107 | // Same as MO_GOT but the address stored in the global is a TLS address. |
108 | MO_GOT_TLS, |
109 | |
110 | // On a symbol operand this indicates that the immediate is the symbol |
111 | // address relative the __memory_base wasm global. |
112 | // Only applicable to data symbols. |
113 | MO_MEMORY_BASE_REL, |
114 | |
115 | // On a symbol operand this indicates that the immediate is the symbol |
116 | // address relative the __tls_base wasm global. |
117 | // Only applicable to data symbols. |
118 | MO_TLS_BASE_REL, |
119 | |
120 | // On a symbol operand this indicates that the immediate is the symbol |
121 | // address relative the __table_base wasm global. |
122 | // Only applicable to function symbols. |
123 | MO_TABLE_BASE_REL, |
124 | |
125 | // On a block signature operand this indicates that this is a destination |
126 | // block of a (catch_ref) clause in try_table. |
127 | MO_CATCH_BLOCK_SIG, |
128 | }; |
129 | |
130 | } // end namespace WebAssemblyII |
131 | |
132 | } // end namespace llvm |
133 | |
134 | // Defines symbolic names for WebAssembly registers. This defines a mapping from |
135 | // register name to register number. |
136 | // |
137 | #define GET_REGINFO_ENUM |
138 | #include "WebAssemblyGenRegisterInfo.inc" |
139 | |
140 | // Defines symbolic names for the WebAssembly instructions. |
141 | // |
142 | #define GET_INSTRINFO_ENUM |
143 | #define GET_INSTRINFO_MC_HELPER_DECLS |
144 | #include "WebAssemblyGenInstrInfo.inc" |
145 | |
146 | namespace llvm { |
147 | namespace WebAssembly { |
148 | |
149 | /// Instruction opcodes emitted via means other than CodeGen. |
150 | static const unsigned Nop = 0x01; |
151 | static const unsigned End = 0x0b; |
152 | |
153 | /// Return the default p2align value for a load or store with the given opcode. |
154 | inline unsigned GetDefaultP2AlignAny(unsigned Opc) { |
155 | switch (Opc) { |
156 | #define WASM_LOAD_STORE(NAME) \ |
157 | case WebAssembly::NAME##_A32: \ |
158 | case WebAssembly::NAME##_A64: \ |
159 | case WebAssembly::NAME##_A32_S: \ |
160 | case WebAssembly::NAME##_A64_S: |
161 | WASM_LOAD_STORE(LOAD8_S_I32) |
162 | WASM_LOAD_STORE(LOAD8_U_I32) |
163 | WASM_LOAD_STORE(LOAD8_S_I64) |
164 | WASM_LOAD_STORE(LOAD8_U_I64) |
165 | WASM_LOAD_STORE(ATOMIC_LOAD8_U_I32) |
166 | WASM_LOAD_STORE(ATOMIC_LOAD8_U_I64) |
167 | WASM_LOAD_STORE(STORE8_I32) |
168 | WASM_LOAD_STORE(STORE8_I64) |
169 | WASM_LOAD_STORE(ATOMIC_STORE8_I32) |
170 | WASM_LOAD_STORE(ATOMIC_STORE8_I64) |
171 | WASM_LOAD_STORE(ATOMIC_RMW8_U_ADD_I32) |
172 | WASM_LOAD_STORE(ATOMIC_RMW8_U_ADD_I64) |
173 | WASM_LOAD_STORE(ATOMIC_RMW8_U_SUB_I32) |
174 | WASM_LOAD_STORE(ATOMIC_RMW8_U_SUB_I64) |
175 | WASM_LOAD_STORE(ATOMIC_RMW8_U_AND_I32) |
176 | WASM_LOAD_STORE(ATOMIC_RMW8_U_AND_I64) |
177 | WASM_LOAD_STORE(ATOMIC_RMW8_U_OR_I32) |
178 | WASM_LOAD_STORE(ATOMIC_RMW8_U_OR_I64) |
179 | WASM_LOAD_STORE(ATOMIC_RMW8_U_XOR_I32) |
180 | WASM_LOAD_STORE(ATOMIC_RMW8_U_XOR_I64) |
181 | WASM_LOAD_STORE(ATOMIC_RMW8_U_XCHG_I32) |
182 | WASM_LOAD_STORE(ATOMIC_RMW8_U_XCHG_I64) |
183 | WASM_LOAD_STORE(ATOMIC_RMW8_U_CMPXCHG_I32) |
184 | WASM_LOAD_STORE(ATOMIC_RMW8_U_CMPXCHG_I64) |
185 | WASM_LOAD_STORE(LOAD8_SPLAT) |
186 | WASM_LOAD_STORE(LOAD_LANE_8) |
187 | WASM_LOAD_STORE(STORE_LANE_I8x16) |
188 | return 0; |
189 | WASM_LOAD_STORE(LOAD16_S_I32) |
190 | WASM_LOAD_STORE(LOAD16_U_I32) |
191 | WASM_LOAD_STORE(LOAD16_S_I64) |
192 | WASM_LOAD_STORE(LOAD16_U_I64) |
193 | WASM_LOAD_STORE(ATOMIC_LOAD16_U_I32) |
194 | WASM_LOAD_STORE(ATOMIC_LOAD16_U_I64) |
195 | WASM_LOAD_STORE(STORE16_I32) |
196 | WASM_LOAD_STORE(STORE16_I64) |
197 | WASM_LOAD_STORE(ATOMIC_STORE16_I32) |
198 | WASM_LOAD_STORE(ATOMIC_STORE16_I64) |
199 | WASM_LOAD_STORE(ATOMIC_RMW16_U_ADD_I32) |
200 | WASM_LOAD_STORE(ATOMIC_RMW16_U_ADD_I64) |
201 | WASM_LOAD_STORE(ATOMIC_RMW16_U_SUB_I32) |
202 | WASM_LOAD_STORE(ATOMIC_RMW16_U_SUB_I64) |
203 | WASM_LOAD_STORE(ATOMIC_RMW16_U_AND_I32) |
204 | WASM_LOAD_STORE(ATOMIC_RMW16_U_AND_I64) |
205 | WASM_LOAD_STORE(ATOMIC_RMW16_U_OR_I32) |
206 | WASM_LOAD_STORE(ATOMIC_RMW16_U_OR_I64) |
207 | WASM_LOAD_STORE(ATOMIC_RMW16_U_XOR_I32) |
208 | WASM_LOAD_STORE(ATOMIC_RMW16_U_XOR_I64) |
209 | WASM_LOAD_STORE(ATOMIC_RMW16_U_XCHG_I32) |
210 | WASM_LOAD_STORE(ATOMIC_RMW16_U_XCHG_I64) |
211 | WASM_LOAD_STORE(ATOMIC_RMW16_U_CMPXCHG_I32) |
212 | WASM_LOAD_STORE(ATOMIC_RMW16_U_CMPXCHG_I64) |
213 | WASM_LOAD_STORE(LOAD16_SPLAT) |
214 | WASM_LOAD_STORE(LOAD_LANE_16) |
215 | WASM_LOAD_STORE(STORE_LANE_I16x8) |
216 | WASM_LOAD_STORE(LOAD_F16_F32) |
217 | WASM_LOAD_STORE(STORE_F16_F32) |
218 | return 1; |
219 | WASM_LOAD_STORE(LOAD_I32) |
220 | WASM_LOAD_STORE(LOAD_F32) |
221 | WASM_LOAD_STORE(STORE_I32) |
222 | WASM_LOAD_STORE(STORE_F32) |
223 | WASM_LOAD_STORE(LOAD32_S_I64) |
224 | WASM_LOAD_STORE(LOAD32_U_I64) |
225 | WASM_LOAD_STORE(STORE32_I64) |
226 | WASM_LOAD_STORE(ATOMIC_LOAD_I32) |
227 | WASM_LOAD_STORE(ATOMIC_LOAD32_U_I64) |
228 | WASM_LOAD_STORE(ATOMIC_STORE_I32) |
229 | WASM_LOAD_STORE(ATOMIC_STORE32_I64) |
230 | WASM_LOAD_STORE(ATOMIC_RMW_ADD_I32) |
231 | WASM_LOAD_STORE(ATOMIC_RMW32_U_ADD_I64) |
232 | WASM_LOAD_STORE(ATOMIC_RMW_SUB_I32) |
233 | WASM_LOAD_STORE(ATOMIC_RMW32_U_SUB_I64) |
234 | WASM_LOAD_STORE(ATOMIC_RMW_AND_I32) |
235 | WASM_LOAD_STORE(ATOMIC_RMW32_U_AND_I64) |
236 | WASM_LOAD_STORE(ATOMIC_RMW_OR_I32) |
237 | WASM_LOAD_STORE(ATOMIC_RMW32_U_OR_I64) |
238 | WASM_LOAD_STORE(ATOMIC_RMW_XOR_I32) |
239 | WASM_LOAD_STORE(ATOMIC_RMW32_U_XOR_I64) |
240 | WASM_LOAD_STORE(ATOMIC_RMW_XCHG_I32) |
241 | WASM_LOAD_STORE(ATOMIC_RMW32_U_XCHG_I64) |
242 | WASM_LOAD_STORE(ATOMIC_RMW_CMPXCHG_I32) |
243 | WASM_LOAD_STORE(ATOMIC_RMW32_U_CMPXCHG_I64) |
244 | WASM_LOAD_STORE(MEMORY_ATOMIC_NOTIFY) |
245 | WASM_LOAD_STORE(MEMORY_ATOMIC_WAIT32) |
246 | WASM_LOAD_STORE(LOAD32_SPLAT) |
247 | WASM_LOAD_STORE(LOAD_ZERO_32) |
248 | WASM_LOAD_STORE(LOAD_LANE_32) |
249 | WASM_LOAD_STORE(STORE_LANE_I32x4) |
250 | return 2; |
251 | WASM_LOAD_STORE(LOAD_I64) |
252 | WASM_LOAD_STORE(LOAD_F64) |
253 | WASM_LOAD_STORE(STORE_I64) |
254 | WASM_LOAD_STORE(STORE_F64) |
255 | WASM_LOAD_STORE(ATOMIC_LOAD_I64) |
256 | WASM_LOAD_STORE(ATOMIC_STORE_I64) |
257 | WASM_LOAD_STORE(ATOMIC_RMW_ADD_I64) |
258 | WASM_LOAD_STORE(ATOMIC_RMW_SUB_I64) |
259 | WASM_LOAD_STORE(ATOMIC_RMW_AND_I64) |
260 | WASM_LOAD_STORE(ATOMIC_RMW_OR_I64) |
261 | WASM_LOAD_STORE(ATOMIC_RMW_XOR_I64) |
262 | WASM_LOAD_STORE(ATOMIC_RMW_XCHG_I64) |
263 | WASM_LOAD_STORE(ATOMIC_RMW_CMPXCHG_I64) |
264 | WASM_LOAD_STORE(MEMORY_ATOMIC_WAIT64) |
265 | WASM_LOAD_STORE(LOAD64_SPLAT) |
266 | WASM_LOAD_STORE(LOAD_EXTEND_S_I16x8) |
267 | WASM_LOAD_STORE(LOAD_EXTEND_U_I16x8) |
268 | WASM_LOAD_STORE(LOAD_EXTEND_S_I32x4) |
269 | WASM_LOAD_STORE(LOAD_EXTEND_U_I32x4) |
270 | WASM_LOAD_STORE(LOAD_EXTEND_S_I64x2) |
271 | WASM_LOAD_STORE(LOAD_EXTEND_U_I64x2) |
272 | WASM_LOAD_STORE(LOAD_ZERO_64) |
273 | WASM_LOAD_STORE(LOAD_LANE_64) |
274 | WASM_LOAD_STORE(STORE_LANE_I64x2) |
275 | return 3; |
276 | WASM_LOAD_STORE(LOAD_V128) |
277 | WASM_LOAD_STORE(STORE_V128) |
278 | return 4; |
279 | default: |
280 | return -1; |
281 | } |
282 | #undef WASM_LOAD_STORE |
283 | } |
284 | |
285 | inline unsigned GetDefaultP2Align(unsigned Opc) { |
286 | auto Align = GetDefaultP2AlignAny(Opc); |
287 | if (Align == -1U) { |
288 | llvm_unreachable("Only loads and stores have p2align values" ); |
289 | } |
290 | return Align; |
291 | } |
292 | |
293 | inline bool isConst(unsigned Opc) { |
294 | switch (Opc) { |
295 | case WebAssembly::CONST_I32: |
296 | case WebAssembly::CONST_I32_S: |
297 | case WebAssembly::CONST_I64: |
298 | case WebAssembly::CONST_I64_S: |
299 | case WebAssembly::CONST_F32: |
300 | case WebAssembly::CONST_F32_S: |
301 | case WebAssembly::CONST_F64: |
302 | case WebAssembly::CONST_F64_S: |
303 | case WebAssembly::CONST_V128_I8x16: |
304 | case WebAssembly::CONST_V128_I8x16_S: |
305 | case WebAssembly::CONST_V128_I16x8: |
306 | case WebAssembly::CONST_V128_I16x8_S: |
307 | case WebAssembly::CONST_V128_I32x4: |
308 | case WebAssembly::CONST_V128_I32x4_S: |
309 | case WebAssembly::CONST_V128_I64x2: |
310 | case WebAssembly::CONST_V128_I64x2_S: |
311 | case WebAssembly::CONST_V128_F32x4: |
312 | case WebAssembly::CONST_V128_F32x4_S: |
313 | case WebAssembly::CONST_V128_F64x2: |
314 | case WebAssembly::CONST_V128_F64x2_S: |
315 | return true; |
316 | default: |
317 | return false; |
318 | } |
319 | } |
320 | |
321 | inline bool isScalarConst(unsigned Opc) { |
322 | switch (Opc) { |
323 | case WebAssembly::CONST_I32: |
324 | case WebAssembly::CONST_I32_S: |
325 | case WebAssembly::CONST_I64: |
326 | case WebAssembly::CONST_I64_S: |
327 | case WebAssembly::CONST_F32: |
328 | case WebAssembly::CONST_F32_S: |
329 | case WebAssembly::CONST_F64: |
330 | case WebAssembly::CONST_F64_S: |
331 | return true; |
332 | default: |
333 | return false; |
334 | } |
335 | } |
336 | |
337 | inline bool isArgument(unsigned Opc) { |
338 | switch (Opc) { |
339 | case WebAssembly::ARGUMENT_i32: |
340 | case WebAssembly::ARGUMENT_i32_S: |
341 | case WebAssembly::ARGUMENT_i64: |
342 | case WebAssembly::ARGUMENT_i64_S: |
343 | case WebAssembly::ARGUMENT_f32: |
344 | case WebAssembly::ARGUMENT_f32_S: |
345 | case WebAssembly::ARGUMENT_f64: |
346 | case WebAssembly::ARGUMENT_f64_S: |
347 | case WebAssembly::ARGUMENT_v16i8: |
348 | case WebAssembly::ARGUMENT_v16i8_S: |
349 | case WebAssembly::ARGUMENT_v8i16: |
350 | case WebAssembly::ARGUMENT_v8i16_S: |
351 | case WebAssembly::ARGUMENT_v4i32: |
352 | case WebAssembly::ARGUMENT_v4i32_S: |
353 | case WebAssembly::ARGUMENT_v2i64: |
354 | case WebAssembly::ARGUMENT_v2i64_S: |
355 | case WebAssembly::ARGUMENT_v8f16: |
356 | case WebAssembly::ARGUMENT_v8f16_S: |
357 | case WebAssembly::ARGUMENT_v4f32: |
358 | case WebAssembly::ARGUMENT_v4f32_S: |
359 | case WebAssembly::ARGUMENT_v2f64: |
360 | case WebAssembly::ARGUMENT_v2f64_S: |
361 | case WebAssembly::ARGUMENT_funcref: |
362 | case WebAssembly::ARGUMENT_funcref_S: |
363 | case WebAssembly::ARGUMENT_externref: |
364 | case WebAssembly::ARGUMENT_externref_S: |
365 | case WebAssembly::ARGUMENT_exnref: |
366 | case WebAssembly::ARGUMENT_exnref_S: |
367 | return true; |
368 | default: |
369 | return false; |
370 | } |
371 | } |
372 | |
373 | inline bool isCopy(unsigned Opc) { |
374 | switch (Opc) { |
375 | case WebAssembly::COPY_I32: |
376 | case WebAssembly::COPY_I32_S: |
377 | case WebAssembly::COPY_I64: |
378 | case WebAssembly::COPY_I64_S: |
379 | case WebAssembly::COPY_F32: |
380 | case WebAssembly::COPY_F32_S: |
381 | case WebAssembly::COPY_F64: |
382 | case WebAssembly::COPY_F64_S: |
383 | case WebAssembly::COPY_V128: |
384 | case WebAssembly::COPY_V128_S: |
385 | case WebAssembly::COPY_FUNCREF: |
386 | case WebAssembly::COPY_FUNCREF_S: |
387 | case WebAssembly::COPY_EXTERNREF: |
388 | case WebAssembly::COPY_EXTERNREF_S: |
389 | case WebAssembly::COPY_EXNREF: |
390 | case WebAssembly::COPY_EXNREF_S: |
391 | return true; |
392 | default: |
393 | return false; |
394 | } |
395 | } |
396 | |
397 | inline bool isTee(unsigned Opc) { |
398 | switch (Opc) { |
399 | case WebAssembly::TEE_I32: |
400 | case WebAssembly::TEE_I32_S: |
401 | case WebAssembly::TEE_I64: |
402 | case WebAssembly::TEE_I64_S: |
403 | case WebAssembly::TEE_F32: |
404 | case WebAssembly::TEE_F32_S: |
405 | case WebAssembly::TEE_F64: |
406 | case WebAssembly::TEE_F64_S: |
407 | case WebAssembly::TEE_V128: |
408 | case WebAssembly::TEE_V128_S: |
409 | case WebAssembly::TEE_FUNCREF: |
410 | case WebAssembly::TEE_FUNCREF_S: |
411 | case WebAssembly::TEE_EXTERNREF: |
412 | case WebAssembly::TEE_EXTERNREF_S: |
413 | case WebAssembly::TEE_EXNREF: |
414 | case WebAssembly::TEE_EXNREF_S: |
415 | return true; |
416 | default: |
417 | return false; |
418 | } |
419 | } |
420 | |
421 | inline bool isCallDirect(unsigned Opc) { |
422 | switch (Opc) { |
423 | case WebAssembly::CALL: |
424 | case WebAssembly::CALL_S: |
425 | case WebAssembly::RET_CALL: |
426 | case WebAssembly::RET_CALL_S: |
427 | return true; |
428 | default: |
429 | return false; |
430 | } |
431 | } |
432 | |
433 | inline bool isCallIndirect(unsigned Opc) { |
434 | switch (Opc) { |
435 | case WebAssembly::CALL_INDIRECT: |
436 | case WebAssembly::CALL_INDIRECT_S: |
437 | case WebAssembly::RET_CALL_INDIRECT: |
438 | case WebAssembly::RET_CALL_INDIRECT_S: |
439 | return true; |
440 | default: |
441 | return false; |
442 | } |
443 | } |
444 | |
445 | inline bool isBrTable(unsigned Opc) { |
446 | switch (Opc) { |
447 | case WebAssembly::BR_TABLE_I32: |
448 | case WebAssembly::BR_TABLE_I32_S: |
449 | case WebAssembly::BR_TABLE_I64: |
450 | case WebAssembly::BR_TABLE_I64_S: |
451 | return true; |
452 | default: |
453 | return false; |
454 | } |
455 | } |
456 | |
457 | inline bool isMarker(unsigned Opc) { |
458 | switch (Opc) { |
459 | case WebAssembly::BLOCK: |
460 | case WebAssembly::BLOCK_S: |
461 | case WebAssembly::END_BLOCK: |
462 | case WebAssembly::END_BLOCK_S: |
463 | case WebAssembly::LOOP: |
464 | case WebAssembly::LOOP_S: |
465 | case WebAssembly::END_LOOP: |
466 | case WebAssembly::END_LOOP_S: |
467 | case WebAssembly::TRY: |
468 | case WebAssembly::TRY_S: |
469 | case WebAssembly::END_TRY: |
470 | case WebAssembly::END_TRY_S: |
471 | case WebAssembly::TRY_TABLE: |
472 | case WebAssembly::TRY_TABLE_S: |
473 | case WebAssembly::END_TRY_TABLE: |
474 | case WebAssembly::END_TRY_TABLE_S: |
475 | return true; |
476 | default: |
477 | return false; |
478 | } |
479 | } |
480 | |
481 | inline bool isEndMarker(unsigned Opc) { |
482 | switch (Opc) { |
483 | case WebAssembly::END_BLOCK: |
484 | case WebAssembly::END_BLOCK_S: |
485 | case WebAssembly::END_LOOP: |
486 | case WebAssembly::END_LOOP_S: |
487 | case WebAssembly::END_TRY: |
488 | case WebAssembly::END_TRY_S: |
489 | case WebAssembly::END_TRY_TABLE: |
490 | case WebAssembly::END_TRY_TABLE_S: |
491 | return true; |
492 | default: |
493 | return false; |
494 | } |
495 | } |
496 | |
497 | inline bool isTry(unsigned Opc) { |
498 | switch (Opc) { |
499 | case WebAssembly::TRY: |
500 | case WebAssembly::TRY_S: |
501 | case WebAssembly::TRY_TABLE: |
502 | case WebAssembly::TRY_TABLE_S: |
503 | return true; |
504 | default: |
505 | return false; |
506 | } |
507 | } |
508 | |
509 | inline bool isCatch(unsigned Opc) { |
510 | switch (Opc) { |
511 | case WebAssembly::CATCH_LEGACY: |
512 | case WebAssembly::CATCH_LEGACY_S: |
513 | case WebAssembly::CATCH_ALL_LEGACY: |
514 | case WebAssembly::CATCH_ALL_LEGACY_S: |
515 | case WebAssembly::CATCH: |
516 | case WebAssembly::CATCH_S: |
517 | case WebAssembly::CATCH_REF: |
518 | case WebAssembly::CATCH_REF_S: |
519 | case WebAssembly::CATCH_ALL: |
520 | case WebAssembly::CATCH_ALL_S: |
521 | case WebAssembly::CATCH_ALL_REF: |
522 | case WebAssembly::CATCH_ALL_REF_S: |
523 | return true; |
524 | default: |
525 | return false; |
526 | } |
527 | } |
528 | |
529 | inline bool isCatchAll(unsigned Opc) { |
530 | switch (Opc) { |
531 | case WebAssembly::CATCH_ALL_LEGACY: |
532 | case WebAssembly::CATCH_ALL_LEGACY_S: |
533 | case WebAssembly::CATCH_ALL: |
534 | case WebAssembly::CATCH_ALL_S: |
535 | case WebAssembly::CATCH_ALL_REF: |
536 | case WebAssembly::CATCH_ALL_REF_S: |
537 | return true; |
538 | default: |
539 | return false; |
540 | } |
541 | } |
542 | |
543 | inline bool isLocalGet(unsigned Opc) { |
544 | switch (Opc) { |
545 | case WebAssembly::LOCAL_GET_I32: |
546 | case WebAssembly::LOCAL_GET_I32_S: |
547 | case WebAssembly::LOCAL_GET_I64: |
548 | case WebAssembly::LOCAL_GET_I64_S: |
549 | case WebAssembly::LOCAL_GET_F32: |
550 | case WebAssembly::LOCAL_GET_F32_S: |
551 | case WebAssembly::LOCAL_GET_F64: |
552 | case WebAssembly::LOCAL_GET_F64_S: |
553 | case WebAssembly::LOCAL_GET_V128: |
554 | case WebAssembly::LOCAL_GET_V128_S: |
555 | case WebAssembly::LOCAL_GET_FUNCREF: |
556 | case WebAssembly::LOCAL_GET_FUNCREF_S: |
557 | case WebAssembly::LOCAL_GET_EXTERNREF: |
558 | case WebAssembly::LOCAL_GET_EXTERNREF_S: |
559 | case WebAssembly::LOCAL_GET_EXNREF: |
560 | case WebAssembly::LOCAL_GET_EXNREF_S: |
561 | return true; |
562 | default: |
563 | return false; |
564 | } |
565 | } |
566 | |
567 | inline bool isLocalSet(unsigned Opc) { |
568 | switch (Opc) { |
569 | case WebAssembly::LOCAL_SET_I32: |
570 | case WebAssembly::LOCAL_SET_I32_S: |
571 | case WebAssembly::LOCAL_SET_I64: |
572 | case WebAssembly::LOCAL_SET_I64_S: |
573 | case WebAssembly::LOCAL_SET_F32: |
574 | case WebAssembly::LOCAL_SET_F32_S: |
575 | case WebAssembly::LOCAL_SET_F64: |
576 | case WebAssembly::LOCAL_SET_F64_S: |
577 | case WebAssembly::LOCAL_SET_V128: |
578 | case WebAssembly::LOCAL_SET_V128_S: |
579 | case WebAssembly::LOCAL_SET_FUNCREF: |
580 | case WebAssembly::LOCAL_SET_FUNCREF_S: |
581 | case WebAssembly::LOCAL_SET_EXTERNREF: |
582 | case WebAssembly::LOCAL_SET_EXTERNREF_S: |
583 | case WebAssembly::LOCAL_SET_EXNREF: |
584 | case WebAssembly::LOCAL_SET_EXNREF_S: |
585 | return true; |
586 | default: |
587 | return false; |
588 | } |
589 | } |
590 | |
591 | inline bool isLocalTee(unsigned Opc) { |
592 | switch (Opc) { |
593 | case WebAssembly::LOCAL_TEE_I32: |
594 | case WebAssembly::LOCAL_TEE_I32_S: |
595 | case WebAssembly::LOCAL_TEE_I64: |
596 | case WebAssembly::LOCAL_TEE_I64_S: |
597 | case WebAssembly::LOCAL_TEE_F32: |
598 | case WebAssembly::LOCAL_TEE_F32_S: |
599 | case WebAssembly::LOCAL_TEE_F64: |
600 | case WebAssembly::LOCAL_TEE_F64_S: |
601 | case WebAssembly::LOCAL_TEE_V128: |
602 | case WebAssembly::LOCAL_TEE_V128_S: |
603 | case WebAssembly::LOCAL_TEE_FUNCREF: |
604 | case WebAssembly::LOCAL_TEE_FUNCREF_S: |
605 | case WebAssembly::LOCAL_TEE_EXTERNREF: |
606 | case WebAssembly::LOCAL_TEE_EXTERNREF_S: |
607 | case WebAssembly::LOCAL_TEE_EXNREF: |
608 | case WebAssembly::LOCAL_TEE_EXNREF_S: |
609 | return true; |
610 | default: |
611 | return false; |
612 | } |
613 | } |
614 | |
615 | static const unsigned UnusedReg = -1u; |
616 | |
617 | // For a given stackified WAReg, return the id number to print with push/pop. |
618 | unsigned inline getWARegStackId(unsigned Reg) { |
619 | assert(Reg & INT32_MIN); |
620 | return Reg & INT32_MAX; |
621 | } |
622 | |
623 | } // end namespace WebAssembly |
624 | } // end namespace llvm |
625 | |
626 | #define GET_SUBTARGETINFO_ENUM |
627 | #include "WebAssemblyGenSubtargetInfo.inc" |
628 | |
629 | #endif |
630 | |