skip to content
==> include/wasm/instr.h <==
1/* @ajax/wasm-instr: one instruction at a time from a body or a constant expression.
2 *
3 * wasm_rd_instr reads the opcode (and the sub-opcode of a prefixed one), looks it up in
4 * @ajax/wasm-opcodes and reads its immediates into a wasm_instr. It checks encodings only (an
5 * unknown opcode, a malformed LEB, a bad block type byte); typing is @ajax/wasm-validate's. */
6#ifndef WASM_INSTR_H
7#define WASM_INSTR_H
8
9#include "wasm/opcodes.h"
10#include "wasm/reader.h"
11
12#include <stdbool.h>
13#include <stdint.h>
14
15/* Block types: WASM_BT_EMPTY, a value type (the byte), or a type index (>= 0). */
16#define WASM_BT_EMPTY (-64)
17
18typedef struct {
19    uint32_t op;
20    wasm_opinfo info;
21    size_t offset;          /* of the opcode */
22    uint32_t a, b;          /* indices: label, function, local, global, table, type, data, element */
23    uint32_t align, mem;    /* memarg: log2 alignment, memory index */
24    uint64_t moffset;       /* memarg offset */
25    int64_t i;              /* i32.const (sign-extended) and i64.const */
26    uint32_t f32;           /* f32.const bits */
27    uint64_t f64;           /* f64.const bits */
28    int64_t blocktype;      /* WASM_BT_EMPTY, -(0x80 - valtype) for a value type, or a type index */
29    wasm_valtype bt_val;    /* the value type when blocktype is one */
30    uint32_t ntargets;      /* br_table: targets before the default */
31    const uint8_t *targets; /* br_table: the encoded targets (wasm_instr_target reads them) */
32    uint32_t nselect;       /* select t*: how many types (1 in practice) */
33    wasm_valtype select_type;
34    wasm_valtype reftype;   /* ref.null */
35    uint8_t lane;           /* SIMD lane immediate */
36    const uint8_t *v128;    /* SIMD 16-byte immediate */
37} wasm_instr;
38
39/* Reads one instruction. false (and the reader's failure set) on a malformed or unknown one. */
40bool wasm_rd_instr(wasm_reader *r, wasm_instr *out);
41
42/* br_table's targets: out must hold ntargets + 1 (the default last). */
43void wasm_instr_targets(const wasm_instr *in, uint32_t *out);
44
45/* Whether a block type is a value type (and which), empty, or a type index. */
46static inline bool wasm_bt_is_index(const wasm_instr *in) { return in->blocktype >= 0; }
47
48#endif