Update wasm-tools crates (#4246)
This commit updates the wasm-tools family of crates, notably pulling in the refactorings and updates from bytecodealliance/wasm-tools#621 for the latest iteration of the component model. This commit additionally updates all support for the component model for these changes, notably: * Many bits and pieces of type information was refactored. Many `FooTypeIndex` namings are now `TypeFooIndex`. Additionally there is now `TypeIndex` as well as `ComponentTypeIndex` for the two type index spaces in a component. * A number of new sections are now processed to handle the core and component variants. * Internal maps were split such as the `funcs` map into `component_funcs` and `funcs` (same for `instances`). * Canonical options are now processed individually instead of one bulk `into` definition. Overall this was not a major update to the internals of handling the component model in Wasmtime. Instead this was mostly a surface-level refactoring to make sure that everything lines up with the new binary format for components. * All text syntax used in tests was updated to the new syntax.
This commit is contained in:
35
Cargo.lock
generated
35
Cargo.lock
generated
@@ -3214,18 +3214,18 @@ checksum = "d554b7f530dee5964d9a9468d95c1f8b8acae4f282807e7d27d4b03099a46744"
|
|||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "wasm-encoder"
|
name = "wasm-encoder"
|
||||||
version = "0.12.0"
|
version = "0.13.0"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "2b47b995b096a689358ca9de6c727b94351b95b390dbbf6b7021c22797d36caa"
|
checksum = "31f0c17267a5ffd6ae3d897589460e21db1673c84fb7016b909c9691369a75ea"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"leb128",
|
"leb128",
|
||||||
]
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "wasm-mutate"
|
name = "wasm-mutate"
|
||||||
version = "0.2.3"
|
version = "0.2.4"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "afc948447bea01d54509cb4a6ccbeb7e572c42c4c84f778d286b7633a1c49e86"
|
checksum = "219c79f95ec42118a63e9df1f8b4858c2092875820d10b4d8e5b324759880212"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"egg",
|
"egg",
|
||||||
"log",
|
"log",
|
||||||
@@ -3237,9 +3237,9 @@ dependencies = [
|
|||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "wasm-smith"
|
name = "wasm-smith"
|
||||||
version = "0.10.1"
|
version = "0.11.0"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "bb87569c81c298836d88405a28a68e8dfcd43b75220a4b4522831a63921b7dbc"
|
checksum = "4f0ed86e26ccdda3c178e557f8f2874e277c8d4f29c88e3c3320c58db12840ed"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"arbitrary",
|
"arbitrary",
|
||||||
"flagset",
|
"flagset",
|
||||||
@@ -3284,18 +3284,18 @@ dependencies = [
|
|||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "wasmparser"
|
name = "wasmparser"
|
||||||
version = "0.85.0"
|
version = "0.86.0"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "570460c58b21e9150d2df0eaaedbb7816c34bcec009ae0dcc976e40ba81463e7"
|
checksum = "4bcbfe95447da2aa7ff171857fc8427513eb57c75a729bb190e974dc695e8f5c"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"indexmap",
|
"indexmap",
|
||||||
]
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "wasmprinter"
|
name = "wasmprinter"
|
||||||
version = "0.2.35"
|
version = "0.2.36"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "ea454634a2a7888d053f7723a26a76024e4f705cf86f7b4d38d5f15b79369c31"
|
checksum = "aa4cca415278da771add7c9ab7f3391f04b8d98719d2cf28a185d38d5206697e"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"anyhow",
|
"anyhow",
|
||||||
"wasmparser",
|
"wasmparser",
|
||||||
@@ -3434,7 +3434,7 @@ dependencies = [
|
|||||||
"wasmtime-wasi-crypto",
|
"wasmtime-wasi-crypto",
|
||||||
"wasmtime-wasi-nn",
|
"wasmtime-wasi-nn",
|
||||||
"wasmtime-wast",
|
"wasmtime-wast",
|
||||||
"wast 41.0.0",
|
"wast 42.0.0",
|
||||||
"wat",
|
"wat",
|
||||||
"winapi",
|
"winapi",
|
||||||
]
|
]
|
||||||
@@ -3648,7 +3648,7 @@ version = "0.39.0"
|
|||||||
dependencies = [
|
dependencies = [
|
||||||
"anyhow",
|
"anyhow",
|
||||||
"wasmtime",
|
"wasmtime",
|
||||||
"wast 41.0.0",
|
"wast 42.0.0",
|
||||||
]
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
@@ -3662,22 +3662,23 @@ dependencies = [
|
|||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "wast"
|
name = "wast"
|
||||||
version = "41.0.0"
|
version = "42.0.0"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "f882898b8b817cc4edc16aa3692fdc087b356edc8cc0c2164f5b5181e31c3870"
|
checksum = "badcb03f976f983ff0daf294da9697be659442f61e6b0942bb37a2b6cbfe9dd4"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"leb128",
|
"leb128",
|
||||||
"memchr",
|
"memchr",
|
||||||
"unicode-width",
|
"unicode-width",
|
||||||
|
"wasm-encoder",
|
||||||
]
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "wat"
|
name = "wat"
|
||||||
version = "1.0.43"
|
version = "1.0.44"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "48b3b9b3e39e66c7fd3f8be785e74444d216260f491e93369e317ed6482ff80f"
|
checksum = "b92f20b742ac527066c8414bc0637352661b68cab07ef42586cefaba71c965cf"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"wast 41.0.0",
|
"wast 42.0.0",
|
||||||
]
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
|
|||||||
@@ -52,13 +52,13 @@ test-programs = { path = "crates/test-programs" }
|
|||||||
wasmtime-runtime = { path = "crates/runtime" }
|
wasmtime-runtime = { path = "crates/runtime" }
|
||||||
tokio = { version = "1.8.0", features = ["rt", "time", "macros", "rt-multi-thread"] }
|
tokio = { version = "1.8.0", features = ["rt", "time", "macros", "rt-multi-thread"] }
|
||||||
tracing-subscriber = "0.3.1"
|
tracing-subscriber = "0.3.1"
|
||||||
wast = "41.0.0"
|
wast = "42.0.0"
|
||||||
criterion = "0.3.4"
|
criterion = "0.3.4"
|
||||||
num_cpus = "1.13.0"
|
num_cpus = "1.13.0"
|
||||||
winapi = { version = "0.3.9", features = ['memoryapi'] }
|
winapi = { version = "0.3.9", features = ['memoryapi'] }
|
||||||
memchr = "2.4"
|
memchr = "2.4"
|
||||||
async-trait = "0.1"
|
async-trait = "0.1"
|
||||||
wat = "1.0.42"
|
wat = "1.0.43"
|
||||||
once_cell = "1.9.0"
|
once_cell = "1.9.0"
|
||||||
rayon = "1.5.0"
|
rayon = "1.5.0"
|
||||||
|
|
||||||
|
|||||||
@@ -12,7 +12,7 @@ keywords = ["webassembly", "wasm"]
|
|||||||
edition = "2021"
|
edition = "2021"
|
||||||
|
|
||||||
[dependencies]
|
[dependencies]
|
||||||
wasmparser = { version = "0.85.0", default-features = false }
|
wasmparser = { version = "0.86.0", default-features = false }
|
||||||
cranelift-codegen = { path = "../codegen", version = "0.86.0", default-features = false }
|
cranelift-codegen = { path = "../codegen", version = "0.86.0", default-features = false }
|
||||||
cranelift-entity = { path = "../entity", version = "0.86.0" }
|
cranelift-entity = { path = "../entity", version = "0.86.0" }
|
||||||
cranelift-frontend = { path = "../frontend", version = "0.86.0", default-features = false }
|
cranelift-frontend = { path = "../frontend", version = "0.86.0", default-features = false }
|
||||||
|
|||||||
@@ -171,7 +171,7 @@ fn parse_local_decls<FE: FuncEnvironment + ?Sized>(
|
|||||||
builder.set_srcloc(cur_srcloc(reader));
|
builder.set_srcloc(cur_srcloc(reader));
|
||||||
let pos = reader.original_position();
|
let pos = reader.original_position();
|
||||||
let count = reader.read_var_u32()?;
|
let count = reader.read_var_u32()?;
|
||||||
let ty = reader.read_type()?;
|
let ty = reader.read_val_type()?;
|
||||||
validator.define_locals(pos, count, ty)?;
|
validator.define_locals(pos, count, ty)?;
|
||||||
declare_locals(builder, count, ty, &mut next_local, environ)?;
|
declare_locals(builder, count, ty, &mut next_local, environ)?;
|
||||||
}
|
}
|
||||||
@@ -187,12 +187,12 @@ fn parse_local_decls<FE: FuncEnvironment + ?Sized>(
|
|||||||
fn declare_locals<FE: FuncEnvironment + ?Sized>(
|
fn declare_locals<FE: FuncEnvironment + ?Sized>(
|
||||||
builder: &mut FunctionBuilder,
|
builder: &mut FunctionBuilder,
|
||||||
count: u32,
|
count: u32,
|
||||||
wasm_type: wasmparser::Type,
|
wasm_type: wasmparser::ValType,
|
||||||
next_local: &mut usize,
|
next_local: &mut usize,
|
||||||
environ: &mut FE,
|
environ: &mut FE,
|
||||||
) -> WasmResult<()> {
|
) -> WasmResult<()> {
|
||||||
// All locals are initialized to 0.
|
// All locals are initialized to 0.
|
||||||
use wasmparser::Type::*;
|
use wasmparser::ValType::*;
|
||||||
let zeroval = match wasm_type {
|
let zeroval = match wasm_type {
|
||||||
I32 => builder.ins().iconst(ir::types::I32, 0),
|
I32 => builder.ins().iconst(ir::types::I32, 0),
|
||||||
I64 => builder.ins().iconst(ir::types::I64, 0),
|
I64 => builder.ins().iconst(ir::types::I64, 0),
|
||||||
|
|||||||
@@ -25,7 +25,7 @@ use wasmparser::{
|
|||||||
ElementSectionReader, Export, ExportSectionReader, ExternalKind, FunctionSectionReader,
|
ElementSectionReader, Export, ExportSectionReader, ExternalKind, FunctionSectionReader,
|
||||||
GlobalSectionReader, GlobalType, ImportSectionReader, MemorySectionReader, MemoryType,
|
GlobalSectionReader, GlobalType, ImportSectionReader, MemorySectionReader, MemoryType,
|
||||||
NameSectionReader, Naming, Operator, TableSectionReader, TableType, TagSectionReader, TagType,
|
NameSectionReader, Naming, Operator, TableSectionReader, TableType, TagSectionReader, TagType,
|
||||||
TypeDef, TypeRef, TypeSectionReader,
|
Type, TypeRef, TypeSectionReader,
|
||||||
};
|
};
|
||||||
|
|
||||||
fn memory(ty: MemoryType) -> Memory {
|
fn memory(ty: MemoryType) -> Memory {
|
||||||
@@ -73,7 +73,7 @@ pub fn parse_type_section<'a>(
|
|||||||
|
|
||||||
for entry in types {
|
for entry in types {
|
||||||
match entry? {
|
match entry? {
|
||||||
TypeDef::Func(wasm_func_ty) => {
|
Type::Func(wasm_func_ty) => {
|
||||||
environ.declare_type_func(wasm_func_ty.clone().try_into()?)?;
|
environ.declare_type_func(wasm_func_ty.clone().try_into()?)?;
|
||||||
module_translation_state
|
module_translation_state
|
||||||
.wasm_types
|
.wasm_types
|
||||||
|
|||||||
@@ -6,7 +6,7 @@ use std::vec::Vec;
|
|||||||
|
|
||||||
/// Map of signatures to a function's parameter and return types.
|
/// Map of signatures to a function's parameter and return types.
|
||||||
pub(crate) type WasmTypes =
|
pub(crate) type WasmTypes =
|
||||||
PrimaryMap<SignatureIndex, (Box<[wasmparser::Type]>, Box<[wasmparser::Type]>)>;
|
PrimaryMap<SignatureIndex, (Box<[wasmparser::ValType]>, Box<[wasmparser::ValType]>)>;
|
||||||
|
|
||||||
/// Contains information decoded from the Wasm module that must be referenced
|
/// Contains information decoded from the Wasm module that must be referenced
|
||||||
/// during each Wasm function's translation.
|
/// during each Wasm function's translation.
|
||||||
@@ -23,13 +23,13 @@ pub struct ModuleTranslationState {
|
|||||||
pub(crate) wasm_types: WasmTypes,
|
pub(crate) wasm_types: WasmTypes,
|
||||||
}
|
}
|
||||||
|
|
||||||
fn cranelift_to_wasmparser_type(ty: Type) -> WasmResult<wasmparser::Type> {
|
fn cranelift_to_wasmparser_type(ty: Type) -> WasmResult<wasmparser::ValType> {
|
||||||
Ok(match ty {
|
Ok(match ty {
|
||||||
types::I32 => wasmparser::Type::I32,
|
types::I32 => wasmparser::ValType::I32,
|
||||||
types::I64 => wasmparser::Type::I64,
|
types::I64 => wasmparser::ValType::I64,
|
||||||
types::F32 => wasmparser::Type::F32,
|
types::F32 => wasmparser::ValType::F32,
|
||||||
types::F64 => wasmparser::Type::F64,
|
types::F64 => wasmparser::ValType::F64,
|
||||||
types::R32 | types::R64 => wasmparser::Type::ExternRef,
|
types::R32 | types::R64 => wasmparser::ValType::ExternRef,
|
||||||
_ => {
|
_ => {
|
||||||
return Err(WasmError::Unsupported(format!(
|
return Err(WasmError::Unsupported(format!(
|
||||||
"Cannot convert Cranelift type to Wasm signature: {:?}",
|
"Cannot convert Cranelift type to Wasm signature: {:?}",
|
||||||
@@ -54,11 +54,11 @@ impl ModuleTranslationState {
|
|||||||
pub fn from_func_sigs(sigs: &[(&[Type], &[Type])]) -> WasmResult<Self> {
|
pub fn from_func_sigs(sigs: &[(&[Type], &[Type])]) -> WasmResult<Self> {
|
||||||
let mut wasm_types = PrimaryMap::with_capacity(sigs.len());
|
let mut wasm_types = PrimaryMap::with_capacity(sigs.len());
|
||||||
for &(ref args, ref results) in sigs {
|
for &(ref args, ref results) in sigs {
|
||||||
let args: Vec<wasmparser::Type> = args
|
let args: Vec<wasmparser::ValType> = args
|
||||||
.iter()
|
.iter()
|
||||||
.map(|&ty| cranelift_to_wasmparser_type(ty))
|
.map(|&ty| cranelift_to_wasmparser_type(ty))
|
||||||
.collect::<Result<_, _>>()?;
|
.collect::<Result<_, _>>()?;
|
||||||
let results: Vec<wasmparser::Type> = results
|
let results: Vec<wasmparser::ValType> = results
|
||||||
.iter()
|
.iter()
|
||||||
.map(|&ty| cranelift_to_wasmparser_type(ty))
|
.map(|&ty| cranelift_to_wasmparser_type(ty))
|
||||||
.collect::<Result<_, _>>()?;
|
.collect::<Result<_, _>>()?;
|
||||||
|
|||||||
@@ -21,16 +21,16 @@ pub enum TableElementType {
|
|||||||
|
|
||||||
/// Helper function translating wasmparser types to Cranelift types when possible.
|
/// Helper function translating wasmparser types to Cranelift types when possible.
|
||||||
pub fn type_to_type<PE: TargetEnvironment + ?Sized>(
|
pub fn type_to_type<PE: TargetEnvironment + ?Sized>(
|
||||||
ty: wasmparser::Type,
|
ty: wasmparser::ValType,
|
||||||
environ: &PE,
|
environ: &PE,
|
||||||
) -> WasmResult<ir::Type> {
|
) -> WasmResult<ir::Type> {
|
||||||
match ty {
|
match ty {
|
||||||
wasmparser::Type::I32 => Ok(ir::types::I32),
|
wasmparser::ValType::I32 => Ok(ir::types::I32),
|
||||||
wasmparser::Type::I64 => Ok(ir::types::I64),
|
wasmparser::ValType::I64 => Ok(ir::types::I64),
|
||||||
wasmparser::Type::F32 => Ok(ir::types::F32),
|
wasmparser::ValType::F32 => Ok(ir::types::F32),
|
||||||
wasmparser::Type::F64 => Ok(ir::types::F64),
|
wasmparser::ValType::F64 => Ok(ir::types::F64),
|
||||||
wasmparser::Type::V128 => Ok(ir::types::I8X16),
|
wasmparser::ValType::V128 => Ok(ir::types::I8X16),
|
||||||
wasmparser::Type::ExternRef | wasmparser::Type::FuncRef => {
|
wasmparser::ValType::ExternRef | wasmparser::ValType::FuncRef => {
|
||||||
Ok(environ.reference_type(ty.try_into()?))
|
Ok(environ.reference_type(ty.try_into()?))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -39,17 +39,17 @@ pub fn type_to_type<PE: TargetEnvironment + ?Sized>(
|
|||||||
/// Helper function translating wasmparser possible table types to Cranelift types when possible,
|
/// Helper function translating wasmparser possible table types to Cranelift types when possible,
|
||||||
/// or None for Func tables.
|
/// or None for Func tables.
|
||||||
pub fn tabletype_to_type<PE: TargetEnvironment + ?Sized>(
|
pub fn tabletype_to_type<PE: TargetEnvironment + ?Sized>(
|
||||||
ty: wasmparser::Type,
|
ty: wasmparser::ValType,
|
||||||
environ: &PE,
|
environ: &PE,
|
||||||
) -> WasmResult<Option<ir::Type>> {
|
) -> WasmResult<Option<ir::Type>> {
|
||||||
match ty {
|
match ty {
|
||||||
wasmparser::Type::I32 => Ok(Some(ir::types::I32)),
|
wasmparser::ValType::I32 => Ok(Some(ir::types::I32)),
|
||||||
wasmparser::Type::I64 => Ok(Some(ir::types::I64)),
|
wasmparser::ValType::I64 => Ok(Some(ir::types::I64)),
|
||||||
wasmparser::Type::F32 => Ok(Some(ir::types::F32)),
|
wasmparser::ValType::F32 => Ok(Some(ir::types::F32)),
|
||||||
wasmparser::Type::F64 => Ok(Some(ir::types::F64)),
|
wasmparser::ValType::F64 => Ok(Some(ir::types::F64)),
|
||||||
wasmparser::Type::V128 => Ok(Some(ir::types::I8X16)),
|
wasmparser::ValType::V128 => Ok(Some(ir::types::I8X16)),
|
||||||
wasmparser::Type::ExternRef => Ok(Some(environ.reference_type(ty.try_into()?))),
|
wasmparser::ValType::ExternRef => Ok(Some(environ.reference_type(ty.try_into()?))),
|
||||||
wasmparser::Type::FuncRef => Ok(None),
|
wasmparser::ValType::FuncRef => Ok(None),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -58,31 +58,31 @@ pub fn blocktype_params_results<'a, T>(
|
|||||||
validator: &'a FuncValidator<T>,
|
validator: &'a FuncValidator<T>,
|
||||||
ty: wasmparser::BlockType,
|
ty: wasmparser::BlockType,
|
||||||
) -> WasmResult<(
|
) -> WasmResult<(
|
||||||
impl ExactSizeIterator<Item = wasmparser::Type> + Clone + 'a,
|
impl ExactSizeIterator<Item = wasmparser::ValType> + Clone + 'a,
|
||||||
impl ExactSizeIterator<Item = wasmparser::Type> + Clone + 'a,
|
impl ExactSizeIterator<Item = wasmparser::ValType> + Clone + 'a,
|
||||||
)>
|
)>
|
||||||
where
|
where
|
||||||
T: WasmModuleResources,
|
T: WasmModuleResources,
|
||||||
{
|
{
|
||||||
return Ok(match ty {
|
return Ok(match ty {
|
||||||
wasmparser::BlockType::Empty => {
|
wasmparser::BlockType::Empty => {
|
||||||
let params: &'static [wasmparser::Type] = &[];
|
let params: &'static [wasmparser::ValType] = &[];
|
||||||
let results: &'static [wasmparser::Type] = &[];
|
let results: &'static [wasmparser::ValType] = &[];
|
||||||
(
|
(
|
||||||
itertools::Either::Left(params.iter().copied()),
|
itertools::Either::Left(params.iter().copied()),
|
||||||
itertools::Either::Left(results.iter().copied()),
|
itertools::Either::Left(results.iter().copied()),
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
wasmparser::BlockType::Type(ty) => {
|
wasmparser::BlockType::Type(ty) => {
|
||||||
let params: &'static [wasmparser::Type] = &[];
|
let params: &'static [wasmparser::ValType] = &[];
|
||||||
let results: &'static [wasmparser::Type] = match ty {
|
let results: &'static [wasmparser::ValType] = match ty {
|
||||||
wasmparser::Type::I32 => &[wasmparser::Type::I32],
|
wasmparser::ValType::I32 => &[wasmparser::ValType::I32],
|
||||||
wasmparser::Type::I64 => &[wasmparser::Type::I64],
|
wasmparser::ValType::I64 => &[wasmparser::ValType::I64],
|
||||||
wasmparser::Type::F32 => &[wasmparser::Type::F32],
|
wasmparser::ValType::F32 => &[wasmparser::ValType::F32],
|
||||||
wasmparser::Type::F64 => &[wasmparser::Type::F64],
|
wasmparser::ValType::F64 => &[wasmparser::ValType::F64],
|
||||||
wasmparser::Type::V128 => &[wasmparser::Type::V128],
|
wasmparser::ValType::V128 => &[wasmparser::ValType::V128],
|
||||||
wasmparser::Type::ExternRef => &[wasmparser::Type::ExternRef],
|
wasmparser::ValType::ExternRef => &[wasmparser::ValType::ExternRef],
|
||||||
wasmparser::Type::FuncRef => &[wasmparser::Type::FuncRef],
|
wasmparser::ValType::FuncRef => &[wasmparser::ValType::FuncRef],
|
||||||
};
|
};
|
||||||
(
|
(
|
||||||
itertools::Either::Left(params.iter().copied()),
|
itertools::Either::Left(params.iter().copied()),
|
||||||
@@ -105,28 +105,28 @@ where
|
|||||||
/// Create a `Block` with the given Wasm parameters.
|
/// Create a `Block` with the given Wasm parameters.
|
||||||
pub fn block_with_params<PE: TargetEnvironment + ?Sized>(
|
pub fn block_with_params<PE: TargetEnvironment + ?Sized>(
|
||||||
builder: &mut FunctionBuilder,
|
builder: &mut FunctionBuilder,
|
||||||
params: impl IntoIterator<Item = wasmparser::Type>,
|
params: impl IntoIterator<Item = wasmparser::ValType>,
|
||||||
environ: &PE,
|
environ: &PE,
|
||||||
) -> WasmResult<ir::Block> {
|
) -> WasmResult<ir::Block> {
|
||||||
let block = builder.create_block();
|
let block = builder.create_block();
|
||||||
for ty in params {
|
for ty in params {
|
||||||
match ty {
|
match ty {
|
||||||
wasmparser::Type::I32 => {
|
wasmparser::ValType::I32 => {
|
||||||
builder.append_block_param(block, ir::types::I32);
|
builder.append_block_param(block, ir::types::I32);
|
||||||
}
|
}
|
||||||
wasmparser::Type::I64 => {
|
wasmparser::ValType::I64 => {
|
||||||
builder.append_block_param(block, ir::types::I64);
|
builder.append_block_param(block, ir::types::I64);
|
||||||
}
|
}
|
||||||
wasmparser::Type::F32 => {
|
wasmparser::ValType::F32 => {
|
||||||
builder.append_block_param(block, ir::types::F32);
|
builder.append_block_param(block, ir::types::F32);
|
||||||
}
|
}
|
||||||
wasmparser::Type::F64 => {
|
wasmparser::ValType::F64 => {
|
||||||
builder.append_block_param(block, ir::types::F64);
|
builder.append_block_param(block, ir::types::F64);
|
||||||
}
|
}
|
||||||
wasmparser::Type::ExternRef | wasmparser::Type::FuncRef => {
|
wasmparser::ValType::ExternRef | wasmparser::ValType::FuncRef => {
|
||||||
builder.append_block_param(block, environ.reference_type(ty.try_into()?));
|
builder.append_block_param(block, environ.reference_type(ty.try_into()?));
|
||||||
}
|
}
|
||||||
wasmparser::Type::V128 => {
|
wasmparser::ValType::V128 => {
|
||||||
builder.append_block_param(block, ir::types::I8X16);
|
builder.append_block_param(block, ir::types::I8X16);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -19,7 +19,7 @@ cranelift-codegen = { path = "../../cranelift/codegen", version = "0.86.0" }
|
|||||||
cranelift-frontend = { path = "../../cranelift/frontend", version = "0.86.0" }
|
cranelift-frontend = { path = "../../cranelift/frontend", version = "0.86.0" }
|
||||||
cranelift-entity = { path = "../../cranelift/entity", version = "0.86.0" }
|
cranelift-entity = { path = "../../cranelift/entity", version = "0.86.0" }
|
||||||
cranelift-native = { path = "../../cranelift/native", version = "0.86.0" }
|
cranelift-native = { path = "../../cranelift/native", version = "0.86.0" }
|
||||||
wasmparser = "0.85.0"
|
wasmparser = "0.86.0"
|
||||||
target-lexicon = "0.12"
|
target-lexicon = "0.12"
|
||||||
gimli = { version = "0.26.0", default-features = false, features = ['read', 'std'] }
|
gimli = { version = "0.26.0", default-features = false, features = ['read', 'std'] }
|
||||||
object = { version = "0.28.0", default-features = false, features = ['write'] }
|
object = { version = "0.28.0", default-features = false, features = ['write'] }
|
||||||
|
|||||||
@@ -11,7 +11,7 @@ use gimli::{self, LineEncoding};
|
|||||||
use std::collections::{HashMap, HashSet};
|
use std::collections::{HashMap, HashSet};
|
||||||
use std::path::PathBuf;
|
use std::path::PathBuf;
|
||||||
use std::sync::atomic::{AtomicUsize, Ordering::SeqCst};
|
use std::sync::atomic::{AtomicUsize, Ordering::SeqCst};
|
||||||
use wasmparser::Type as WasmType;
|
use wasmparser::ValType as WasmType;
|
||||||
use wasmtime_environ::{
|
use wasmtime_environ::{
|
||||||
DebugInfoData, DefinedFuncIndex, EntityRef, FuncIndex, FunctionMetadata, WasmFileInfo,
|
DebugInfoData, DefinedFuncIndex, EntityRef, FuncIndex, FunctionMetadata, WasmFileInfo,
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -14,7 +14,7 @@ edition = "2021"
|
|||||||
anyhow = "1.0"
|
anyhow = "1.0"
|
||||||
cranelift-entity = { path = "../../cranelift/entity", version = "0.86.0" }
|
cranelift-entity = { path = "../../cranelift/entity", version = "0.86.0" }
|
||||||
wasmtime-types = { path = "../types", version = "0.39.0" }
|
wasmtime-types = { path = "../types", version = "0.39.0" }
|
||||||
wasmparser = "0.85.0"
|
wasmparser = "0.86.0"
|
||||||
indexmap = { version = "1.0.2", features = ["serde-1"] }
|
indexmap = { version = "1.0.2", features = ["serde-1"] }
|
||||||
thiserror = "1.0.4"
|
thiserror = "1.0.4"
|
||||||
serde = { version = "1.0.94", features = ["derive"] }
|
serde = { version = "1.0.94", features = ["derive"] }
|
||||||
|
|||||||
@@ -291,7 +291,7 @@ pub enum Export {
|
|||||||
/// function.
|
/// function.
|
||||||
LiftedFunction {
|
LiftedFunction {
|
||||||
/// The component function type of the function being created.
|
/// The component function type of the function being created.
|
||||||
ty: FuncTypeIndex,
|
ty: TypeFuncIndex,
|
||||||
/// Which core WebAssembly export is being lifted.
|
/// Which core WebAssembly export is being lifted.
|
||||||
func: CoreExport<FuncIndex>,
|
func: CoreExport<FuncIndex>,
|
||||||
/// Any options, if present, associated with this lifting.
|
/// Any options, if present, associated with this lifting.
|
||||||
|
|||||||
@@ -41,14 +41,20 @@ pub struct Translation<'data> {
|
|||||||
/// Modules and how they're defined (either closed-over or imported)
|
/// Modules and how they're defined (either closed-over or imported)
|
||||||
modules: PrimaryMap<ModuleIndex, ModuleDef>,
|
modules: PrimaryMap<ModuleIndex, ModuleDef>,
|
||||||
|
|
||||||
/// Instances and how they're defined, either as instantiations of modules
|
/// Instances of components, either direct instantiations or "bundles of
|
||||||
/// or "synthetically created" as a bag of named items from our other index
|
/// exports".
|
||||||
/// spaces.
|
component_instances: PrimaryMap<ComponentInstanceIndex, ComponentInstanceDef<'data>>,
|
||||||
instances: PrimaryMap<InstanceIndex, InstanceDef<'data>>,
|
|
||||||
|
|
||||||
/// Both core wasm and component functions, and how they're defined.
|
/// Instances of core wasm modules, either direct instantiations or
|
||||||
|
/// "bundles of exports".
|
||||||
|
module_instances: PrimaryMap<ModuleInstanceIndex, ModuleInstanceDef<'data>>,
|
||||||
|
|
||||||
|
/// The core wasm function index space.
|
||||||
funcs: PrimaryMap<FuncIndex, Func<'data>>,
|
funcs: PrimaryMap<FuncIndex, Func<'data>>,
|
||||||
|
|
||||||
|
/// The component function index space.
|
||||||
|
component_funcs: PrimaryMap<ComponentFuncIndex, ComponentFunc<'data>>,
|
||||||
|
|
||||||
/// Core wasm globals, always sourced from a previously module instance.
|
/// Core wasm globals, always sourced from a previously module instance.
|
||||||
globals: PrimaryMap<GlobalIndex, CoreSource<'data>>,
|
globals: PrimaryMap<GlobalIndex, CoreSource<'data>>,
|
||||||
|
|
||||||
@@ -100,17 +106,17 @@ enum ModuleDef {
|
|||||||
/// nothing is known about it except for its type. The `import_index`
|
/// nothing is known about it except for its type. The `import_index`
|
||||||
/// provided here indexes into the `Component`'s import list.
|
/// provided here indexes into the `Component`'s import list.
|
||||||
Import {
|
Import {
|
||||||
ty: ModuleTypeIndex,
|
ty: TypeModuleIndex,
|
||||||
import: RuntimeImport,
|
import: RuntimeImport,
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
/// How instances are defined within a component.
|
/// Forms of creation of a core wasm module instance.
|
||||||
#[derive(Debug, Clone)]
|
#[derive(Debug, Clone)]
|
||||||
enum InstanceDef<'data> {
|
enum ModuleInstanceDef<'data> {
|
||||||
/// A module instance created through the instantiation of a previous
|
/// A module instance created through the instantiation of a previous
|
||||||
/// module.
|
/// module.
|
||||||
Module {
|
Instantiated {
|
||||||
/// The runtime index associated with this instance.
|
/// The runtime index associated with this instance.
|
||||||
///
|
///
|
||||||
/// Not to be confused with `InstanceIndex` which counts "synthetic"
|
/// Not to be confused with `InstanceIndex` which counts "synthetic"
|
||||||
@@ -123,41 +129,27 @@ enum InstanceDef<'data> {
|
|||||||
|
|
||||||
/// A "synthetic" module created as a bag of exports from other items
|
/// A "synthetic" module created as a bag of exports from other items
|
||||||
/// already defined within this component.
|
/// already defined within this component.
|
||||||
ModuleSynthetic(HashMap<&'data str, EntityIndex>),
|
Synthetic(HashMap<&'data str, EntityIndex>),
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Forms of creation of a component instance.
|
||||||
|
#[derive(Debug, Clone)]
|
||||||
|
enum ComponentInstanceDef<'data> {
|
||||||
/// An instance which was imported from the host.
|
/// An instance which was imported from the host.
|
||||||
Import {
|
Import {
|
||||||
/// The type of the imported instance
|
/// The type of the imported instance
|
||||||
ty: ComponentInstanceTypeIndex,
|
ty: TypeComponentInstanceIndex,
|
||||||
/// The description of where this import came from.
|
/// The description of where this import came from.
|
||||||
import: RuntimeImport,
|
import: RuntimeImport,
|
||||||
},
|
},
|
||||||
|
|
||||||
/// Same as `ModuleSynthetic` except for component items.
|
/// Same as `ModuleInstanceDef::Synthetic` except for component items.
|
||||||
ComponentSynthetic(HashMap<&'data str, ComponentItem>),
|
Synthetic(HashMap<&'data str, ComponentItem>),
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Description of the function index space and how functions are defined.
|
/// Description of the function index space and how functions are defined.
|
||||||
#[derive(Clone)]
|
#[derive(Clone)]
|
||||||
enum Func<'data> {
|
enum Func<'data> {
|
||||||
// component functions
|
|
||||||
//
|
|
||||||
/// A component function that is imported from the host.
|
|
||||||
Import(RuntimeImport),
|
|
||||||
|
|
||||||
/// A component function that is lifted from core wasm function.
|
|
||||||
Lifted {
|
|
||||||
/// The resulting type of the lifted function
|
|
||||||
ty: FuncTypeIndex,
|
|
||||||
/// Which core wasm function is lifted, currently required to be an
|
|
||||||
/// instance export as opposed to a lowered import.
|
|
||||||
func: CoreSource<'data>,
|
|
||||||
/// The options specified when the function was lifted.
|
|
||||||
options: CanonicalOptions,
|
|
||||||
},
|
|
||||||
|
|
||||||
// core function
|
|
||||||
//
|
|
||||||
/// A core wasm function that's extracted from a core wasm instance.
|
/// A core wasm function that's extracted from a core wasm instance.
|
||||||
Core(CoreSource<'data>),
|
Core(CoreSource<'data>),
|
||||||
/// A core wasm function created by lowering an imported host function.
|
/// A core wasm function created by lowering an imported host function.
|
||||||
@@ -167,6 +159,24 @@ enum Func<'data> {
|
|||||||
Lowered(LoweredIndex),
|
Lowered(LoweredIndex),
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Description of the function index space and how functions are defined.
|
||||||
|
#[derive(Clone)]
|
||||||
|
enum ComponentFunc<'data> {
|
||||||
|
/// A component function that is imported from the host.
|
||||||
|
Import(RuntimeImport),
|
||||||
|
|
||||||
|
/// A component function that is lifted from core wasm function.
|
||||||
|
Lifted {
|
||||||
|
/// The resulting type of the lifted function
|
||||||
|
ty: TypeFuncIndex,
|
||||||
|
/// Which core wasm function is lifted, currently required to be an
|
||||||
|
/// instance export as opposed to a lowered import.
|
||||||
|
func: CoreSource<'data>,
|
||||||
|
/// The options specified when the function was lifted.
|
||||||
|
options: CanonicalOptions,
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
/// Source of truth for where a core wasm item comes from.
|
/// Source of truth for where a core wasm item comes from.
|
||||||
#[derive(Clone)]
|
#[derive(Clone)]
|
||||||
enum CoreSource<'data> {
|
enum CoreSource<'data> {
|
||||||
@@ -278,7 +288,7 @@ impl<'a, 'data> Translator<'a, 'data> {
|
|||||||
|
|
||||||
// Push a new scope for component types so outer aliases know
|
// Push a new scope for component types so outer aliases know
|
||||||
// that the 0th level is this new component.
|
// that the 0th level is this new component.
|
||||||
self.types.push_component_types_scope();
|
self.types.push_type_scope();
|
||||||
}
|
}
|
||||||
|
|
||||||
Payload::End(offset) => {
|
Payload::End(offset) => {
|
||||||
@@ -304,7 +314,7 @@ impl<'a, 'data> Translator<'a, 'data> {
|
|||||||
// When leaving a module be sure to pop the types scope to
|
// When leaving a module be sure to pop the types scope to
|
||||||
// ensure that when we go back to the previous module outer
|
// ensure that when we go back to the previous module outer
|
||||||
// type alias indices work correctly again.
|
// type alias indices work correctly again.
|
||||||
self.types.pop_component_types_scope();
|
self.types.pop_type_scope();
|
||||||
|
|
||||||
match self.parsers.pop() {
|
match self.parsers.pop() {
|
||||||
Some(p) => self.parser = p,
|
Some(p) => self.parser = p,
|
||||||
@@ -323,17 +333,23 @@ impl<'a, 'data> Translator<'a, 'data> {
|
|||||||
Payload::ComponentTypeSection(s) => {
|
Payload::ComponentTypeSection(s) => {
|
||||||
self.validator.component_type_section(&s)?;
|
self.validator.component_type_section(&s)?;
|
||||||
for ty in s {
|
for ty in s {
|
||||||
let ty = self.types.component_type_def(&ty?)?;
|
let ty = self.types.intern_component_type(&ty?)?;
|
||||||
self.types.push_component_typedef(ty);
|
self.types.push_component_typedef(ty);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Payload::CoreTypeSection(s) => {
|
||||||
|
self.validator.core_type_section(&s)?;
|
||||||
|
for ty in s {
|
||||||
|
let ty = self.types.intern_core_type(&ty?)?;
|
||||||
|
self.types.push_core_typedef(ty);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
Payload::ComponentImportSection(s) => {
|
Payload::ComponentImportSection(s) => {
|
||||||
self.validator.component_import_section(&s)?;
|
self.validator.component_import_section(&s)?;
|
||||||
for import in s {
|
for import in s {
|
||||||
let import = import?;
|
let import = import?;
|
||||||
let ty = TypeIndex::from_u32(import.ty);
|
let ty = self.types.component_type_ref(&import.ty);
|
||||||
let ty = self.types.component_outer_type(0, ty);
|
|
||||||
// Record the `ImportIndex` to be associated with this
|
// Record the `ImportIndex` to be associated with this
|
||||||
// import and create the `RuntimeImport` representing the
|
// import and create the `RuntimeImport` representing the
|
||||||
// "root" where it has no extra `exports`
|
// "root" where it has no extra `exports`
|
||||||
@@ -352,11 +368,13 @@ impl<'a, 'data> Translator<'a, 'data> {
|
|||||||
}
|
}
|
||||||
TypeDef::ComponentInstance(ty) => {
|
TypeDef::ComponentInstance(ty) => {
|
||||||
self.result
|
self.result
|
||||||
.instances
|
.component_instances
|
||||||
.push(InstanceDef::Import { ty, import });
|
.push(ComponentInstanceDef::Import { ty, import });
|
||||||
}
|
}
|
||||||
TypeDef::Func(_ty) => {
|
TypeDef::ComponentFunc(_ty) => {
|
||||||
self.result.funcs.push(Func::Import(import));
|
self.result
|
||||||
|
.component_funcs
|
||||||
|
.push(ComponentFunc::Import(import));
|
||||||
}
|
}
|
||||||
TypeDef::Component(_) => {
|
TypeDef::Component(_) => {
|
||||||
unimplemented!("imports of components");
|
unimplemented!("imports of components");
|
||||||
@@ -364,34 +382,38 @@ impl<'a, 'data> Translator<'a, 'data> {
|
|||||||
TypeDef::Interface(_) => {
|
TypeDef::Interface(_) => {
|
||||||
unimplemented!("imports of types");
|
unimplemented!("imports of types");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// not possible with a valid component
|
||||||
|
TypeDef::CoreFunc(_ty) => unreachable!(),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
Payload::ComponentFunctionSection(s) => {
|
Payload::ComponentCanonicalSection(s) => {
|
||||||
self.validator.component_function_section(&s)?;
|
self.validator.component_canonical_section(&s)?;
|
||||||
for func in s {
|
for func in s {
|
||||||
let func = match func? {
|
match func? {
|
||||||
wasmparser::ComponentFunction::Lift {
|
wasmparser::CanonicalFunction::Lift {
|
||||||
type_index,
|
type_index,
|
||||||
|
core_func_index,
|
||||||
|
options,
|
||||||
|
} => {
|
||||||
|
let ty = ComponentTypeIndex::from_u32(type_index);
|
||||||
|
let func = FuncIndex::from_u32(core_func_index);
|
||||||
|
let func = self.lift_function(ty, func, &options);
|
||||||
|
self.result.component_funcs.push(func);
|
||||||
|
}
|
||||||
|
wasmparser::CanonicalFunction::Lower {
|
||||||
func_index,
|
func_index,
|
||||||
options,
|
options,
|
||||||
} => {
|
} => {
|
||||||
let ty = TypeIndex::from_u32(type_index);
|
let func = ComponentFuncIndex::from_u32(func_index);
|
||||||
let func = FuncIndex::from_u32(func_index);
|
let func = self.lower_function(func, &options);
|
||||||
self.lift_function(ty, func, &options)
|
|
||||||
}
|
|
||||||
wasmparser::ComponentFunction::Lower {
|
|
||||||
func_index,
|
|
||||||
options,
|
|
||||||
} => {
|
|
||||||
let func = FuncIndex::from_u32(func_index);
|
|
||||||
self.lower_function(func, &options)
|
|
||||||
}
|
|
||||||
};
|
|
||||||
self.result.funcs.push(func);
|
self.result.funcs.push(func);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// Core wasm modules are translated inline directly here with the
|
// Core wasm modules are translated inline directly here with the
|
||||||
// `ModuleEnvironment` from core wasm compilation. This will return
|
// `ModuleEnvironment` from core wasm compilation. This will return
|
||||||
@@ -425,21 +447,33 @@ impl<'a, 'data> Translator<'a, 'data> {
|
|||||||
self.validator.instance_section(&s)?;
|
self.validator.instance_section(&s)?;
|
||||||
for instance in s {
|
for instance in s {
|
||||||
let instance = match instance? {
|
let instance = match instance? {
|
||||||
wasmparser::Instance::Module { index, args } => {
|
wasmparser::Instance::Instantiate { module_index, args } => {
|
||||||
self.module_instance(ModuleIndex::from_u32(index), &args)
|
self.instantiate_module(ModuleIndex::from_u32(module_index), &args)
|
||||||
}
|
}
|
||||||
wasmparser::Instance::ModuleFromExports(exports) => {
|
wasmparser::Instance::FromExports(exports) => {
|
||||||
self.module_instance_from_exports(&exports)
|
self.instantiate_module_from_exports(&exports)
|
||||||
}
|
}
|
||||||
wasmparser::Instance::Component { index, args } => {
|
};
|
||||||
|
self.result.module_instances.push(instance);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
Payload::ComponentInstanceSection(s) => {
|
||||||
|
self.validator.component_instance_section(&s)?;
|
||||||
|
for instance in s {
|
||||||
|
let instance = match instance? {
|
||||||
|
wasmparser::ComponentInstance::Instantiate {
|
||||||
|
component_index,
|
||||||
|
args,
|
||||||
|
} => {
|
||||||
|
let index = ComponentIndex::from_u32(component_index);
|
||||||
drop((index, args));
|
drop((index, args));
|
||||||
unimplemented!("instantiating a component");
|
unimplemented!("instantiating a component");
|
||||||
}
|
}
|
||||||
wasmparser::Instance::ComponentFromExports(exports) => {
|
wasmparser::ComponentInstance::FromExports(exports) => {
|
||||||
self.component_instance_from_exports(&exports)
|
self.instantiate_component_from_exports(&exports)
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
self.result.instances.push(instance);
|
self.result.component_instances.push(instance);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -458,7 +492,35 @@ impl<'a, 'data> Translator<'a, 'data> {
|
|||||||
Payload::AliasSection(s) => {
|
Payload::AliasSection(s) => {
|
||||||
self.validator.alias_section(&s)?;
|
self.validator.alias_section(&s)?;
|
||||||
for alias in s {
|
for alias in s {
|
||||||
self.alias(&alias?);
|
match alias? {
|
||||||
|
wasmparser::Alias::InstanceExport {
|
||||||
|
kind,
|
||||||
|
instance_index,
|
||||||
|
name,
|
||||||
|
} => {
|
||||||
|
let instance = ModuleInstanceIndex::from_u32(instance_index);
|
||||||
|
self.alias_module_instance_export(kind, instance, name);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
Payload::ComponentAliasSection(s) => {
|
||||||
|
self.validator.component_alias_section(&s)?;
|
||||||
|
for alias in s {
|
||||||
|
match alias? {
|
||||||
|
wasmparser::ComponentAlias::InstanceExport {
|
||||||
|
kind,
|
||||||
|
instance_index,
|
||||||
|
name,
|
||||||
|
} => {
|
||||||
|
let instance = ComponentInstanceIndex::from_u32(instance_index);
|
||||||
|
self.alias_component_instance_export(kind, instance, name);
|
||||||
|
}
|
||||||
|
wasmparser::ComponentAlias::Outer { kind, count, index } => {
|
||||||
|
self.alias_component_outer(kind, count, index);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -482,17 +544,18 @@ impl<'a, 'data> Translator<'a, 'data> {
|
|||||||
Ok(Action::KeepGoing)
|
Ok(Action::KeepGoing)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn module_instance(
|
fn instantiate_module(
|
||||||
&mut self,
|
&mut self,
|
||||||
module: ModuleIndex,
|
module: ModuleIndex,
|
||||||
args: &[wasmparser::ModuleArg<'data>],
|
args: &[wasmparser::InstantiationArg<'data>],
|
||||||
) -> InstanceDef<'data> {
|
) -> ModuleInstanceDef<'data> {
|
||||||
// Map the flat list of `args` to instead a name-to-instance index.
|
// Map the flat list of `args` to instead a name-to-instance index.
|
||||||
let mut instance_by_name = HashMap::new();
|
let mut instance_by_name = HashMap::new();
|
||||||
for arg in args {
|
for arg in args {
|
||||||
match arg.kind {
|
match arg.kind {
|
||||||
wasmparser::ModuleArgKind::Instance(idx) => {
|
wasmparser::InstantiationArgKind::Instance => {
|
||||||
instance_by_name.insert(arg.name, InstanceIndex::from_u32(idx));
|
let idx = ModuleInstanceIndex::from_u32(arg.index);
|
||||||
|
instance_by_name.insert(arg.name, idx);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -544,7 +607,7 @@ impl<'a, 'data> Translator<'a, 'data> {
|
|||||||
|
|
||||||
let instance = RuntimeInstanceIndex::from_u32(self.result.component.num_runtime_instances);
|
let instance = RuntimeInstanceIndex::from_u32(self.result.component.num_runtime_instances);
|
||||||
self.result.component.num_runtime_instances += 1;
|
self.result.component.num_runtime_instances += 1;
|
||||||
InstanceDef::Module { instance, module }
|
ModuleInstanceDef::Instantiated { instance, module }
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Calculate the `CoreDef`, a definition of a core wasm item, corresponding
|
/// Calculate the `CoreDef`, a definition of a core wasm item, corresponding
|
||||||
@@ -555,28 +618,22 @@ impl<'a, 'data> Translator<'a, 'data> {
|
|||||||
/// we know the module), one that must be referred to by name since the
|
/// we know the module), one that must be referred to by name since the
|
||||||
/// module isn't known, or it's a synthesized lowering or adapter of a
|
/// module isn't known, or it's a synthesized lowering or adapter of a
|
||||||
/// component function.
|
/// component function.
|
||||||
fn lookup_core_def(&mut self, instance: InstanceIndex, name: &str) -> CoreDef {
|
fn lookup_core_def(&mut self, instance: ModuleInstanceIndex, name: &str) -> CoreDef {
|
||||||
match &self.result.instances[instance] {
|
match &self.result.module_instances[instance] {
|
||||||
InstanceDef::Module { module, instance } => {
|
ModuleInstanceDef::Instantiated { module, instance } => {
|
||||||
let (src, _ty) = self.lookup_core_source_in_module(*instance, *module, name);
|
let (src, _ty) = self.lookup_core_source_in_module(*instance, *module, name);
|
||||||
src.to_core_def()
|
src.to_core_def()
|
||||||
}
|
}
|
||||||
|
|
||||||
InstanceDef::ModuleSynthetic(defs) => match defs[&name] {
|
ModuleInstanceDef::Synthetic(defs) => match defs[&name] {
|
||||||
EntityIndex::Function(f) => match self.result.funcs[f].clone() {
|
EntityIndex::Function(f) => match self.result.funcs[f].clone() {
|
||||||
Func::Core(c) => c.to_core_def(),
|
Func::Core(c) => c.to_core_def(),
|
||||||
Func::Lowered(i) => CoreDef::Lowered(i),
|
Func::Lowered(i) => CoreDef::Lowered(i),
|
||||||
|
|
||||||
// should not be possible to hit with a valid component
|
|
||||||
Func::Lifted { .. } | Func::Import { .. } => unreachable!(),
|
|
||||||
},
|
},
|
||||||
EntityIndex::Global(g) => self.result.globals[g].to_core_def(),
|
EntityIndex::Global(g) => self.result.globals[g].to_core_def(),
|
||||||
EntityIndex::Table(t) => self.result.tables[t].to_core_def(),
|
EntityIndex::Table(t) => self.result.tables[t].to_core_def(),
|
||||||
EntityIndex::Memory(m) => self.result.memories[m].to_core_def(),
|
EntityIndex::Memory(m) => self.result.memories[m].to_core_def(),
|
||||||
},
|
},
|
||||||
|
|
||||||
// should not be possible to hit with a valid component
|
|
||||||
InstanceDef::Import { .. } | InstanceDef::ComponentSynthetic(_) => unreachable!(),
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -616,10 +673,10 @@ impl<'a, 'data> Translator<'a, 'data> {
|
|||||||
|
|
||||||
/// Creates a synthetic module from the list of items currently in the
|
/// Creates a synthetic module from the list of items currently in the
|
||||||
/// module and their given names.
|
/// module and their given names.
|
||||||
fn module_instance_from_exports(
|
fn instantiate_module_from_exports(
|
||||||
&mut self,
|
&mut self,
|
||||||
exports: &[wasmparser::Export<'data>],
|
exports: &[wasmparser::Export<'data>],
|
||||||
) -> InstanceDef<'data> {
|
) -> ModuleInstanceDef<'data> {
|
||||||
let mut map = HashMap::with_capacity(exports.len());
|
let mut map = HashMap::with_capacity(exports.len());
|
||||||
for export in exports {
|
for export in exports {
|
||||||
let idx = match export.kind {
|
let idx = match export.kind {
|
||||||
@@ -645,51 +702,51 @@ impl<'a, 'data> Translator<'a, 'data> {
|
|||||||
};
|
};
|
||||||
map.insert(export.name, idx);
|
map.insert(export.name, idx);
|
||||||
}
|
}
|
||||||
InstanceDef::ModuleSynthetic(map)
|
ModuleInstanceDef::Synthetic(map)
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Creates a synthetic module from the list of items currently in the
|
/// Creates a synthetic module from the list of items currently in the
|
||||||
/// module and their given names.
|
/// module and their given names.
|
||||||
fn component_instance_from_exports(
|
fn instantiate_component_from_exports(
|
||||||
&mut self,
|
&mut self,
|
||||||
exports: &[wasmparser::ComponentExport<'data>],
|
exports: &[wasmparser::ComponentExport<'data>],
|
||||||
) -> InstanceDef<'data> {
|
) -> ComponentInstanceDef<'data> {
|
||||||
let mut map = HashMap::with_capacity(exports.len());
|
let mut map = HashMap::with_capacity(exports.len());
|
||||||
for export in exports {
|
for export in exports {
|
||||||
let idx = match &export.kind {
|
let idx = match &export.kind {
|
||||||
wasmparser::ComponentArgKind::Function(i) => {
|
wasmparser::ComponentExternalKind::Func => {
|
||||||
let index = FuncIndex::from_u32(*i);
|
let index = FuncIndex::from_u32(export.index);
|
||||||
ComponentItem::Func(index)
|
ComponentItem::Func(index)
|
||||||
}
|
}
|
||||||
wasmparser::ComponentArgKind::Module(i) => {
|
wasmparser::ComponentExternalKind::Module => {
|
||||||
let index = ModuleIndex::from_u32(*i);
|
let index = ModuleIndex::from_u32(export.index);
|
||||||
ComponentItem::Module(index)
|
ComponentItem::Module(index)
|
||||||
}
|
}
|
||||||
wasmparser::ComponentArgKind::Instance(i) => {
|
wasmparser::ComponentExternalKind::Instance => {
|
||||||
let index = InstanceIndex::from_u32(*i);
|
let index = ComponentInstanceIndex::from_u32(export.index);
|
||||||
ComponentItem::Instance(index)
|
ComponentItem::ComponentInstance(index)
|
||||||
}
|
}
|
||||||
wasmparser::ComponentArgKind::Component(i) => {
|
wasmparser::ComponentExternalKind::Component => {
|
||||||
let index = ComponentIndex::from_u32(*i);
|
let index = ComponentIndex::from_u32(export.index);
|
||||||
ComponentItem::Component(index)
|
ComponentItem::Component(index)
|
||||||
}
|
}
|
||||||
wasmparser::ComponentArgKind::Value(_) => {
|
wasmparser::ComponentExternalKind::Value => {
|
||||||
unimplemented!("component values");
|
unimplemented!("component values");
|
||||||
}
|
}
|
||||||
wasmparser::ComponentArgKind::Type(_) => {
|
wasmparser::ComponentExternalKind::Type => {
|
||||||
unimplemented!("component type export");
|
unimplemented!("component type export");
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
map.insert(export.name, idx);
|
map.insert(export.name, idx);
|
||||||
}
|
}
|
||||||
InstanceDef::ComponentSynthetic(map)
|
ComponentInstanceDef::Synthetic(map)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn export(&mut self, export: &wasmparser::ComponentExport<'data>) {
|
fn export(&mut self, export: &wasmparser::ComponentExport<'data>) {
|
||||||
let name = export.name;
|
let name = export.name;
|
||||||
let export = match export.kind {
|
let export = match export.kind {
|
||||||
wasmparser::ComponentExportKind::Module(i) => {
|
wasmparser::ComponentExternalKind::Module => {
|
||||||
let idx = ModuleIndex::from_u32(i);
|
let idx = ModuleIndex::from_u32(export.index);
|
||||||
let init = match self.result.modules[idx].clone() {
|
let init = match self.result.modules[idx].clone() {
|
||||||
ModuleDef::Upvar(idx) => Initializer::SaveModuleUpvar(idx),
|
ModuleDef::Upvar(idx) => Initializer::SaveModuleUpvar(idx),
|
||||||
ModuleDef::Import { import, .. } => {
|
ModuleDef::Import { import, .. } => {
|
||||||
@@ -702,20 +759,20 @@ impl<'a, 'data> Translator<'a, 'data> {
|
|||||||
self.result.component.num_runtime_modules += 1;
|
self.result.component.num_runtime_modules += 1;
|
||||||
Export::Module(runtime_index)
|
Export::Module(runtime_index)
|
||||||
}
|
}
|
||||||
wasmparser::ComponentExportKind::Component(i) => {
|
wasmparser::ComponentExternalKind::Component => {
|
||||||
let idx = ComponentIndex::from_u32(i);
|
let idx = ComponentIndex::from_u32(export.index);
|
||||||
drop(idx);
|
drop(idx);
|
||||||
unimplemented!("exporting a component");
|
unimplemented!("exporting a component");
|
||||||
}
|
}
|
||||||
wasmparser::ComponentExportKind::Instance(i) => {
|
wasmparser::ComponentExternalKind::Instance => {
|
||||||
let idx = InstanceIndex::from_u32(i);
|
let idx = ComponentInstanceIndex::from_u32(export.index);
|
||||||
drop(idx);
|
drop(idx);
|
||||||
unimplemented!("exporting an instance");
|
unimplemented!("exporting an instance");
|
||||||
}
|
}
|
||||||
wasmparser::ComponentExportKind::Function(i) => {
|
wasmparser::ComponentExternalKind::Func => {
|
||||||
let idx = FuncIndex::from_u32(i);
|
let idx = ComponentFuncIndex::from_u32(export.index);
|
||||||
match self.result.funcs[idx].clone() {
|
match self.result.component_funcs[idx].clone() {
|
||||||
Func::Lifted { ty, func, options } => Export::LiftedFunction {
|
ComponentFunc::Lifted { ty, func, options } => Export::LiftedFunction {
|
||||||
ty,
|
ty,
|
||||||
func: func.to_core_export(|i| match i {
|
func: func.to_core_export(|i| match i {
|
||||||
EntityIndex::Function(i) => i,
|
EntityIndex::Function(i) => i,
|
||||||
@@ -741,17 +798,14 @@ impl<'a, 'data> Translator<'a, 'data> {
|
|||||||
// Nevertheless this shouldn't panic, eventually when the
|
// Nevertheless this shouldn't panic, eventually when the
|
||||||
// component model implementation is finished this should do
|
// component model implementation is finished this should do
|
||||||
// something reasonable.
|
// something reasonable.
|
||||||
Func::Import { .. } => unimplemented!("exporting an import"),
|
ComponentFunc::Import { .. } => unimplemented!("exporting an import"),
|
||||||
|
|
||||||
// should not be possible to hit with a valid module.
|
|
||||||
Func::Core(_) | Func::Lowered(_) => unreachable!(),
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
wasmparser::ComponentExportKind::Value(_) => {
|
wasmparser::ComponentExternalKind::Value => {
|
||||||
unimplemented!("exporting a value");
|
unimplemented!("exporting a value");
|
||||||
}
|
}
|
||||||
wasmparser::ComponentExportKind::Type(i) => {
|
wasmparser::ComponentExternalKind::Type => {
|
||||||
let idx = TypeIndex::from_u32(i);
|
let idx = TypeIndex::from_u32(export.index);
|
||||||
drop(idx);
|
drop(idx);
|
||||||
unimplemented!("exporting a type");
|
unimplemented!("exporting a type");
|
||||||
}
|
}
|
||||||
@@ -762,23 +816,132 @@ impl<'a, 'data> Translator<'a, 'data> {
|
|||||||
.insert(name.to_string(), export);
|
.insert(name.to_string(), export);
|
||||||
}
|
}
|
||||||
|
|
||||||
fn alias(&mut self, alias: &wasmparser::Alias<'data>) {
|
fn alias_module_instance_export(
|
||||||
match alias {
|
&mut self,
|
||||||
wasmparser::Alias::InstanceExport {
|
kind: wasmparser::ExternalKind,
|
||||||
kind,
|
instance: ModuleInstanceIndex,
|
||||||
instance,
|
name: &'data str,
|
||||||
name,
|
) {
|
||||||
} => {
|
match &self.result.module_instances[instance] {
|
||||||
let instance = InstanceIndex::from_u32(*instance);
|
// The `instance` points to an instantiated module, meaning we can
|
||||||
self.alias_instance_export(*kind, instance, name);
|
// lookup the `CoreSource` associated with it and use the type
|
||||||
|
// information to insert it into the appropriate namespace.
|
||||||
|
ModuleInstanceDef::Instantiated { instance, module } => {
|
||||||
|
let (src, ty) = self.lookup_core_source_in_module(*instance, *module, name);
|
||||||
|
match ty {
|
||||||
|
EntityType::Function(_) => {
|
||||||
|
assert_eq!(kind, wasmparser::ExternalKind::Func);
|
||||||
|
self.result.funcs.push(Func::Core(src));
|
||||||
}
|
}
|
||||||
wasmparser::Alias::OuterModule { .. } => {
|
EntityType::Global(_) => {
|
||||||
unimplemented!("alias outer module");
|
assert_eq!(kind, wasmparser::ExternalKind::Global);
|
||||||
|
self.result.globals.push(src);
|
||||||
|
}
|
||||||
|
EntityType::Memory(_) => {
|
||||||
|
assert_eq!(kind, wasmparser::ExternalKind::Memory);
|
||||||
|
self.result.memories.push(src);
|
||||||
|
}
|
||||||
|
EntityType::Table(_) => {
|
||||||
|
assert_eq!(kind, wasmparser::ExternalKind::Table);
|
||||||
|
self.result.tables.push(src);
|
||||||
|
}
|
||||||
|
EntityType::Tag(_) => unimplemented!("wasm exceptions"),
|
||||||
}
|
}
|
||||||
wasmparser::Alias::OuterComponent { .. } => {
|
|
||||||
unimplemented!("alias outer component");
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// ... and like above for synthetic components aliasing exports from
|
||||||
|
// synthetic modules is also just copying around the identifying
|
||||||
|
// information.
|
||||||
|
ModuleInstanceDef::Synthetic(exports) => match exports[&name] {
|
||||||
|
EntityIndex::Function(i) => {
|
||||||
|
assert_eq!(kind, wasmparser::ExternalKind::Func);
|
||||||
|
self.result.funcs.push(self.result.funcs[i].clone());
|
||||||
|
}
|
||||||
|
EntityIndex::Global(i) => {
|
||||||
|
assert_eq!(kind, wasmparser::ExternalKind::Global);
|
||||||
|
self.result.globals.push(self.result.globals[i].clone());
|
||||||
|
}
|
||||||
|
EntityIndex::Table(i) => {
|
||||||
|
assert_eq!(kind, wasmparser::ExternalKind::Table);
|
||||||
|
self.result.tables.push(self.result.tables[i].clone());
|
||||||
|
}
|
||||||
|
EntityIndex::Memory(i) => {
|
||||||
|
assert_eq!(kind, wasmparser::ExternalKind::Memory);
|
||||||
|
self.result.memories.push(self.result.memories[i].clone());
|
||||||
|
}
|
||||||
|
},
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn alias_component_instance_export(
|
||||||
|
&mut self,
|
||||||
|
kind: wasmparser::ComponentExternalKind,
|
||||||
|
instance: ComponentInstanceIndex,
|
||||||
|
name: &'data str,
|
||||||
|
) {
|
||||||
|
match &self.result.component_instances[instance] {
|
||||||
|
// The `instance` points to an imported component instance, meaning
|
||||||
|
// that the item we're pushing into our index spaces is effectively
|
||||||
|
// another form of import. The `name` is appended to the `import`
|
||||||
|
// found here and then the appropriate namespace of an import is
|
||||||
|
// recorded as well.
|
||||||
|
ComponentInstanceDef::Import { import, ty } => {
|
||||||
|
let import = import.append(name);
|
||||||
|
match self.types[*ty].exports[name] {
|
||||||
|
TypeDef::Module(ty) => {
|
||||||
|
assert_eq!(kind, wasmparser::ComponentExternalKind::Module);
|
||||||
|
self.result.modules.push(ModuleDef::Import { import, ty });
|
||||||
|
}
|
||||||
|
TypeDef::ComponentInstance(ty) => {
|
||||||
|
assert_eq!(kind, wasmparser::ComponentExternalKind::Instance);
|
||||||
|
self.result
|
||||||
|
.component_instances
|
||||||
|
.push(ComponentInstanceDef::Import { import, ty });
|
||||||
|
}
|
||||||
|
TypeDef::ComponentFunc(_ty) => {
|
||||||
|
assert_eq!(kind, wasmparser::ComponentExternalKind::Func);
|
||||||
|
self.result
|
||||||
|
.component_funcs
|
||||||
|
.push(ComponentFunc::Import(import));
|
||||||
|
}
|
||||||
|
TypeDef::Interface(_) => unimplemented!("alias type export"),
|
||||||
|
TypeDef::Component(_) => unimplemented!("alias component export"),
|
||||||
|
|
||||||
|
// not possible with valid components
|
||||||
|
TypeDef::CoreFunc(_ty) => unreachable!(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// For synthetic component/module instances we can just copy the
|
||||||
|
// definition of the original item into a new slot as well to record
|
||||||
|
// that the index describes the same item.
|
||||||
|
ComponentInstanceDef::Synthetic(exports) => match exports[&name] {
|
||||||
|
ComponentItem::Func(i) => {
|
||||||
|
assert_eq!(kind, wasmparser::ComponentExternalKind::Func);
|
||||||
|
self.result.funcs.push(self.result.funcs[i].clone());
|
||||||
|
}
|
||||||
|
ComponentItem::Module(i) => {
|
||||||
|
assert_eq!(kind, wasmparser::ComponentExternalKind::Module);
|
||||||
|
self.result.modules.push(self.result.modules[i].clone());
|
||||||
|
}
|
||||||
|
ComponentItem::ComponentInstance(i) => {
|
||||||
|
assert_eq!(kind, wasmparser::ComponentExternalKind::Instance);
|
||||||
|
self.result
|
||||||
|
.component_instances
|
||||||
|
.push(self.result.component_instances[i].clone());
|
||||||
|
}
|
||||||
|
ComponentItem::Component(_) => unimplemented!("aliasing a component export"),
|
||||||
|
},
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn alias_component_outer(
|
||||||
|
&mut self,
|
||||||
|
kind: wasmparser::ComponentOuterAliasKind,
|
||||||
|
count: u32,
|
||||||
|
index: u32,
|
||||||
|
) {
|
||||||
|
match kind {
|
||||||
// When aliasing a type the `ComponentTypesBuilder` is used to
|
// When aliasing a type the `ComponentTypesBuilder` is used to
|
||||||
// resolve the outer `count` plus the index, and then once it's
|
// resolve the outer `count` plus the index, and then once it's
|
||||||
// resolved we push the type information into our local index
|
// resolved we push the type information into our local index
|
||||||
@@ -787,125 +950,34 @@ impl<'a, 'data> Translator<'a, 'data> {
|
|||||||
// Note that this is just copying indices around as all type
|
// Note that this is just copying indices around as all type
|
||||||
// information is basically a pointer back into the `TypesBuilder`
|
// information is basically a pointer back into the `TypesBuilder`
|
||||||
// structure (and the eventual `TypeTables` that it produces).
|
// structure (and the eventual `TypeTables` that it produces).
|
||||||
wasmparser::Alias::OuterType { count, index } => {
|
wasmparser::ComponentOuterAliasKind::CoreType => {
|
||||||
let index = TypeIndex::from_u32(*index);
|
let index = TypeIndex::from_u32(index);
|
||||||
let ty = self.types.component_outer_type(*count, index);
|
let ty = self.types.core_outer_type(count, index);
|
||||||
|
self.types.push_core_typedef(ty);
|
||||||
|
}
|
||||||
|
wasmparser::ComponentOuterAliasKind::Type => {
|
||||||
|
let index = ComponentTypeIndex::from_u32(index);
|
||||||
|
let ty = self.types.component_outer_type(count, index);
|
||||||
self.types.push_component_typedef(ty);
|
self.types.push_component_typedef(ty);
|
||||||
}
|
}
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
fn alias_instance_export(
|
wasmparser::ComponentOuterAliasKind::CoreModule => {
|
||||||
&mut self,
|
unimplemented!("outer alias to module");
|
||||||
kind: wasmparser::AliasKind,
|
|
||||||
instance: InstanceIndex,
|
|
||||||
name: &'data str,
|
|
||||||
) {
|
|
||||||
match &self.result.instances[instance] {
|
|
||||||
// The `instance` points to an imported component instance, meaning
|
|
||||||
// that the item we're pushing into our index spaces is effectively
|
|
||||||
// another form of import. The `name` is appended to the `import`
|
|
||||||
// found here and then the appropriate namespace of an import is
|
|
||||||
// recorded as well.
|
|
||||||
InstanceDef::Import { import, ty } => {
|
|
||||||
let import = import.append(name);
|
|
||||||
match self.types[*ty].exports[name] {
|
|
||||||
TypeDef::Module(ty) => {
|
|
||||||
assert_eq!(kind, wasmparser::AliasKind::Module);
|
|
||||||
self.result.modules.push(ModuleDef::Import { import, ty });
|
|
||||||
}
|
}
|
||||||
TypeDef::ComponentInstance(ty) => {
|
wasmparser::ComponentOuterAliasKind::Component => {
|
||||||
assert_eq!(kind, wasmparser::AliasKind::Instance);
|
unimplemented!("outer alias to component");
|
||||||
self.result
|
|
||||||
.instances
|
|
||||||
.push(InstanceDef::Import { import, ty });
|
|
||||||
}
|
}
|
||||||
TypeDef::Func(_ty) => {
|
|
||||||
assert_eq!(kind, wasmparser::AliasKind::ComponentFunc);
|
|
||||||
self.result.funcs.push(Func::Import(import));
|
|
||||||
}
|
|
||||||
TypeDef::Interface(_) => unimplemented!("alias type export"),
|
|
||||||
TypeDef::Component(_) => unimplemented!("alias component export"),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// The `instance` points to an instantiated module, meaning we can
|
|
||||||
// lookup the `CoreSource` associated with it and use the type
|
|
||||||
// information to insert it into the appropriate namespace.
|
|
||||||
InstanceDef::Module { instance, module } => {
|
|
||||||
let (src, ty) = self.lookup_core_source_in_module(*instance, *module, name);
|
|
||||||
match ty {
|
|
||||||
EntityType::Function(_) => {
|
|
||||||
assert_eq!(kind, wasmparser::AliasKind::Func);
|
|
||||||
self.result.funcs.push(Func::Core(src));
|
|
||||||
}
|
|
||||||
EntityType::Global(_) => {
|
|
||||||
assert_eq!(kind, wasmparser::AliasKind::Global);
|
|
||||||
self.result.globals.push(src);
|
|
||||||
}
|
|
||||||
EntityType::Memory(_) => {
|
|
||||||
assert_eq!(kind, wasmparser::AliasKind::Memory);
|
|
||||||
self.result.memories.push(src);
|
|
||||||
}
|
|
||||||
EntityType::Table(_) => {
|
|
||||||
assert_eq!(kind, wasmparser::AliasKind::Table);
|
|
||||||
self.result.tables.push(src);
|
|
||||||
}
|
|
||||||
EntityType::Tag(_) => unimplemented!("wasm exceptions"),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// For synthetic component/module instances we can just copy the
|
|
||||||
// definition of the original item into a new slot as well to record
|
|
||||||
// that the index describes the same item.
|
|
||||||
InstanceDef::ComponentSynthetic(exports) => match exports[&name] {
|
|
||||||
ComponentItem::Func(i) => {
|
|
||||||
assert_eq!(kind, wasmparser::AliasKind::ComponentFunc);
|
|
||||||
self.result.funcs.push(self.result.funcs[i].clone());
|
|
||||||
}
|
|
||||||
ComponentItem::Module(i) => {
|
|
||||||
assert_eq!(kind, wasmparser::AliasKind::Module);
|
|
||||||
self.result.modules.push(self.result.modules[i].clone());
|
|
||||||
}
|
|
||||||
ComponentItem::Instance(i) => {
|
|
||||||
assert_eq!(kind, wasmparser::AliasKind::Instance);
|
|
||||||
self.result.instances.push(self.result.instances[i].clone());
|
|
||||||
}
|
|
||||||
ComponentItem::Component(_) => unimplemented!("aliasing a component export"),
|
|
||||||
},
|
|
||||||
|
|
||||||
// ... and like above for synthetic components aliasing exports from
|
|
||||||
// synthetic modules is also just copying around the identifying
|
|
||||||
// information.
|
|
||||||
InstanceDef::ModuleSynthetic(exports) => match exports[&name] {
|
|
||||||
EntityIndex::Function(i) => {
|
|
||||||
assert_eq!(kind, wasmparser::AliasKind::Func);
|
|
||||||
self.result.funcs.push(self.result.funcs[i].clone());
|
|
||||||
}
|
|
||||||
EntityIndex::Global(i) => {
|
|
||||||
assert_eq!(kind, wasmparser::AliasKind::Global);
|
|
||||||
self.result.globals.push(self.result.globals[i].clone());
|
|
||||||
}
|
|
||||||
EntityIndex::Table(i) => {
|
|
||||||
assert_eq!(kind, wasmparser::AliasKind::Table);
|
|
||||||
self.result.tables.push(self.result.tables[i].clone());
|
|
||||||
}
|
|
||||||
EntityIndex::Memory(i) => {
|
|
||||||
assert_eq!(kind, wasmparser::AliasKind::Memory);
|
|
||||||
self.result.memories.push(self.result.memories[i].clone());
|
|
||||||
}
|
|
||||||
},
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn lift_function(
|
fn lift_function(
|
||||||
&mut self,
|
&mut self,
|
||||||
ty: TypeIndex,
|
ty: ComponentTypeIndex,
|
||||||
func: FuncIndex,
|
func: FuncIndex,
|
||||||
options: &[wasmparser::CanonicalOption],
|
options: &[wasmparser::CanonicalOption],
|
||||||
) -> Func<'data> {
|
) -> ComponentFunc<'data> {
|
||||||
let ty = match self.types.component_outer_type(0, ty) {
|
let ty = match self.types.component_outer_type(0, ty) {
|
||||||
TypeDef::Func(ty) => ty,
|
TypeDef::ComponentFunc(ty) => ty,
|
||||||
// should not be possible after validation
|
// should not be possible after validation
|
||||||
_ => unreachable!(),
|
_ => unreachable!(),
|
||||||
};
|
};
|
||||||
@@ -919,22 +991,19 @@ impl<'a, 'data> Translator<'a, 'data> {
|
|||||||
// memory into core wasm (since nothing is around to call
|
// memory into core wasm (since nothing is around to call
|
||||||
// deallocation/free functions).
|
// deallocation/free functions).
|
||||||
Func::Lowered(_) => unimplemented!("lifting a lowered function"),
|
Func::Lowered(_) => unimplemented!("lifting a lowered function"),
|
||||||
|
|
||||||
// should not be possible after validation
|
|
||||||
Func::Lifted { .. } | Func::Import { .. } => unreachable!(),
|
|
||||||
};
|
};
|
||||||
let options = self.canonical_options(options);
|
let options = self.canonical_options(options);
|
||||||
Func::Lifted { ty, func, options }
|
ComponentFunc::Lifted { ty, func, options }
|
||||||
}
|
}
|
||||||
|
|
||||||
fn lower_function(
|
fn lower_function(
|
||||||
&mut self,
|
&mut self,
|
||||||
func: FuncIndex,
|
func: ComponentFuncIndex,
|
||||||
options: &[wasmparser::CanonicalOption],
|
options: &[wasmparser::CanonicalOption],
|
||||||
) -> Func<'data> {
|
) -> Func<'data> {
|
||||||
let options = self.canonical_options(options);
|
let options = self.canonical_options(options);
|
||||||
match self.result.funcs[func].clone() {
|
match self.result.component_funcs[func].clone() {
|
||||||
Func::Import(import) => {
|
ComponentFunc::Import(import) => {
|
||||||
let import = self.runtime_import_index(import);
|
let import = self.runtime_import_index(import);
|
||||||
let index = LoweredIndex::from_u32(self.result.component.num_lowerings);
|
let index = LoweredIndex::from_u32(self.result.component.num_lowerings);
|
||||||
self.result.component.num_lowerings += 1;
|
self.result.component.num_lowerings += 1;
|
||||||
@@ -961,10 +1030,7 @@ impl<'a, 'data> Translator<'a, 'data> {
|
|||||||
// function that lifts the arguments and then afterwards
|
// function that lifts the arguments and then afterwards
|
||||||
// unconditionally traps. That would mean that this validates the
|
// unconditionally traps. That would mean that this validates the
|
||||||
// arguments within the context of `options` and then traps.
|
// arguments within the context of `options` and then traps.
|
||||||
Func::Lifted { .. } => unimplemented!("lower a lifted function"),
|
ComponentFunc::Lifted { .. } => unimplemented!("lower a lifted function"),
|
||||||
|
|
||||||
// should not be possible after validation
|
|
||||||
Func::Core(_) | Func::Lowered(_) => unreachable!(),
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -981,24 +1047,24 @@ impl<'a, 'data> Translator<'a, 'data> {
|
|||||||
wasmparser::CanonicalOption::CompactUTF16 => {
|
wasmparser::CanonicalOption::CompactUTF16 => {
|
||||||
ret.string_encoding = StringEncoding::CompactUtf16;
|
ret.string_encoding = StringEncoding::CompactUtf16;
|
||||||
}
|
}
|
||||||
wasmparser::CanonicalOption::Into(instance) => {
|
wasmparser::CanonicalOption::Memory(idx) => {
|
||||||
let instance = InstanceIndex::from_u32(*instance);
|
let idx = MemoryIndex::from_u32(*idx);
|
||||||
|
let memory = self.result.memories[idx].to_core_export(|i| match i {
|
||||||
// Note that the `unreachable!()` should not happen for
|
|
||||||
// components which have passed validation.
|
|
||||||
let memory =
|
|
||||||
self.lookup_core_def(instance, "memory")
|
|
||||||
.unwrap_export(|i| match i {
|
|
||||||
EntityIndex::Memory(i) => i,
|
EntityIndex::Memory(i) => i,
|
||||||
_ => unreachable!(),
|
_ => unreachable!(),
|
||||||
});
|
});
|
||||||
let memory = self.runtime_memory(memory);
|
let memory = self.runtime_memory(memory);
|
||||||
ret.memory = Some(memory);
|
ret.memory = Some(memory);
|
||||||
|
}
|
||||||
let realloc = self.lookup_core_def(instance, "canonical_abi_realloc");
|
wasmparser::CanonicalOption::Realloc(idx) => {
|
||||||
|
let idx = FuncIndex::from_u32(*idx);
|
||||||
|
let realloc = self.result.funcs[idx].to_core_def();
|
||||||
let realloc = self.runtime_realloc(realloc);
|
let realloc = self.runtime_realloc(realloc);
|
||||||
ret.realloc = Some(realloc);
|
ret.realloc = Some(realloc);
|
||||||
}
|
}
|
||||||
|
wasmparser::CanonicalOption::PostReturn(_) => {
|
||||||
|
unimplemented!("post-return");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return ret;
|
return ret;
|
||||||
@@ -1065,22 +1131,11 @@ impl CoreSource<'_> {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl CoreDef {
|
impl Func<'_> {
|
||||||
fn unwrap_export<T>(self, get_index: impl FnOnce(EntityIndex) -> T) -> CoreExport<T> {
|
fn to_core_def(&self) -> CoreDef {
|
||||||
let export = match self {
|
match self {
|
||||||
CoreDef::Export(export) => export,
|
Func::Core(src) => src.to_core_def(),
|
||||||
CoreDef::Lowered(_) => unreachable!(),
|
Func::Lowered(idx) => CoreDef::Lowered(*idx),
|
||||||
};
|
|
||||||
let instance = export.instance;
|
|
||||||
match export.item {
|
|
||||||
ExportItem::Index(idx) => CoreExport {
|
|
||||||
instance,
|
|
||||||
item: ExportItem::Index(get_index(idx)),
|
|
||||||
},
|
|
||||||
ExportItem::Name(name) => CoreExport {
|
|
||||||
instance,
|
|
||||||
item: ExportItem::Name(name),
|
|
||||||
},
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -8,6 +8,9 @@ use serde::{Deserialize, Serialize};
|
|||||||
use std::collections::HashMap;
|
use std::collections::HashMap;
|
||||||
use std::hash::Hash;
|
use std::hash::Hash;
|
||||||
use std::ops::Index;
|
use std::ops::Index;
|
||||||
|
use wasmparser::{
|
||||||
|
ComponentAlias, ComponentOuterAliasKind, ComponentTypeDeclaration, InstanceTypeDeclaration,
|
||||||
|
};
|
||||||
|
|
||||||
macro_rules! indices {
|
macro_rules! indices {
|
||||||
($(
|
($(
|
||||||
@@ -31,14 +34,23 @@ indices! {
|
|||||||
// compile phase to when we're actually working with the component at
|
// compile phase to when we're actually working with the component at
|
||||||
// runtime.
|
// runtime.
|
||||||
|
|
||||||
|
/// Index within a component's component type index space.
|
||||||
|
pub struct ComponentTypeIndex(u32);
|
||||||
|
|
||||||
/// Index within a component's module index space.
|
/// Index within a component's module index space.
|
||||||
pub struct ModuleIndex(u32);
|
pub struct ModuleIndex(u32);
|
||||||
|
|
||||||
/// Index within a component's component index space.
|
/// Index within a component's component index space.
|
||||||
pub struct ComponentIndex(u32);
|
pub struct ComponentIndex(u32);
|
||||||
|
|
||||||
/// Index within a component's instance index space.
|
/// Index within a component's module instance index space.
|
||||||
pub struct InstanceIndex(u32);
|
pub struct ModuleInstanceIndex(u32);
|
||||||
|
|
||||||
|
/// Index within a component's component instance index space.
|
||||||
|
pub struct ComponentInstanceIndex(u32);
|
||||||
|
|
||||||
|
/// Index within a component's component function index space.
|
||||||
|
pub struct ComponentFuncIndex(u32);
|
||||||
|
|
||||||
// ========================================================================
|
// ========================================================================
|
||||||
// These indices are used to lookup type information within a `TypeTables`
|
// These indices are used to lookup type information within a `TypeTables`
|
||||||
@@ -47,39 +59,39 @@ indices! {
|
|||||||
|
|
||||||
/// Index pointing to a component's type (exports/imports with
|
/// Index pointing to a component's type (exports/imports with
|
||||||
/// component-model types)
|
/// component-model types)
|
||||||
pub struct ComponentTypeIndex(u32);
|
pub struct TypeComponentIndex(u32);
|
||||||
|
|
||||||
/// Index pointing to a component instance's type (exports with
|
/// Index pointing to a component instance's type (exports with
|
||||||
/// component-model types, no imports)
|
/// component-model types, no imports)
|
||||||
pub struct ComponentInstanceTypeIndex(u32);
|
pub struct TypeComponentInstanceIndex(u32);
|
||||||
|
|
||||||
/// Index pointing to a core wasm module's type (exports/imports with
|
/// Index pointing to a core wasm module's type (exports/imports with
|
||||||
/// core wasm types)
|
/// core wasm types)
|
||||||
pub struct ModuleTypeIndex(u32);
|
pub struct TypeModuleIndex(u32);
|
||||||
|
|
||||||
/// Index pointing to a component model function type with arguments/result
|
/// Index pointing to a component model function type with arguments/result
|
||||||
/// as interface types.
|
/// as interface types.
|
||||||
pub struct FuncTypeIndex(u32);
|
pub struct TypeFuncIndex(u32);
|
||||||
|
|
||||||
/// Index pointing to an interface type, used for recursive types such as
|
/// Index pointing to an interface type, used for recursive types such as
|
||||||
/// `List<T>`.
|
/// `List<T>`.
|
||||||
pub struct InterfaceTypeIndex(u32);
|
pub struct TypeInterfaceIndex(u32);
|
||||||
|
|
||||||
/// Index pointing to a record type in the component model (aka a struct).
|
/// Index pointing to a record type in the component model (aka a struct).
|
||||||
pub struct RecordTypeIndex(u32);
|
pub struct TypeRecordIndex(u32);
|
||||||
/// Index pointing to a variant type in the component model (aka an enum).
|
/// Index pointing to a variant type in the component model (aka an enum).
|
||||||
pub struct VariantTypeIndex(u32);
|
pub struct TypeVariantIndex(u32);
|
||||||
/// Index pointing to a tuple type in the component model.
|
/// Index pointing to a tuple type in the component model.
|
||||||
pub struct TupleTypeIndex(u32);
|
pub struct TypeTupleIndex(u32);
|
||||||
/// Index pointing to a flags type in the component model.
|
/// Index pointing to a flags type in the component model.
|
||||||
pub struct FlagsTypeIndex(u32);
|
pub struct TypeFlagsIndex(u32);
|
||||||
/// Index pointing to an enum type in the component model.
|
/// Index pointing to an enum type in the component model.
|
||||||
pub struct EnumTypeIndex(u32);
|
pub struct TypeEnumIndex(u32);
|
||||||
/// Index pointing to a union type in the component model.
|
/// Index pointing to a union type in the component model.
|
||||||
pub struct UnionTypeIndex(u32);
|
pub struct TypeUnionIndex(u32);
|
||||||
/// Index pointing to an expected type in the component model (aka a
|
/// Index pointing to an expected type in the component model (aka a
|
||||||
/// `Result<T, E>`)
|
/// `Result<T, E>`)
|
||||||
pub struct ExpectedTypeIndex(u32);
|
pub struct TypeExpectedIndex(u32);
|
||||||
|
|
||||||
// ========================================================================
|
// ========================================================================
|
||||||
// These indices are actually used at runtime when managing a component at
|
// These indices are actually used at runtime when managing a component at
|
||||||
@@ -147,8 +159,8 @@ pub use crate::{FuncIndex, GlobalIndex, MemoryIndex, TableIndex, TypeIndex};
|
|||||||
pub enum ComponentItem {
|
pub enum ComponentItem {
|
||||||
Func(FuncIndex),
|
Func(FuncIndex),
|
||||||
Module(ModuleIndex),
|
Module(ModuleIndex),
|
||||||
Instance(InstanceIndex),
|
|
||||||
Component(ComponentIndex),
|
Component(ComponentIndex),
|
||||||
|
ComponentInstance(ComponentInstanceIndex),
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Runtime information about the type information contained within a component.
|
/// Runtime information about the type information contained within a component.
|
||||||
@@ -158,18 +170,18 @@ pub enum ComponentItem {
|
|||||||
/// will have a pointer to this value as well.
|
/// will have a pointer to this value as well.
|
||||||
#[derive(Default, Serialize, Deserialize)]
|
#[derive(Default, Serialize, Deserialize)]
|
||||||
pub struct ComponentTypes {
|
pub struct ComponentTypes {
|
||||||
modules: PrimaryMap<ModuleTypeIndex, ModuleType>,
|
modules: PrimaryMap<TypeModuleIndex, TypeModule>,
|
||||||
components: PrimaryMap<ComponentTypeIndex, ComponentType>,
|
components: PrimaryMap<TypeComponentIndex, TypeComponent>,
|
||||||
component_instances: PrimaryMap<ComponentInstanceTypeIndex, ComponentInstanceType>,
|
component_instances: PrimaryMap<TypeComponentInstanceIndex, TypeComponentInstance>,
|
||||||
functions: PrimaryMap<FuncTypeIndex, FuncType>,
|
functions: PrimaryMap<TypeFuncIndex, TypeFunc>,
|
||||||
interface_types: PrimaryMap<InterfaceTypeIndex, InterfaceType>,
|
interface_types: PrimaryMap<TypeInterfaceIndex, InterfaceType>,
|
||||||
records: PrimaryMap<RecordTypeIndex, RecordType>,
|
records: PrimaryMap<TypeRecordIndex, TypeRecord>,
|
||||||
variants: PrimaryMap<VariantTypeIndex, VariantType>,
|
variants: PrimaryMap<TypeVariantIndex, TypeVariant>,
|
||||||
tuples: PrimaryMap<TupleTypeIndex, TupleType>,
|
tuples: PrimaryMap<TypeTupleIndex, TypeTuple>,
|
||||||
enums: PrimaryMap<EnumTypeIndex, EnumType>,
|
enums: PrimaryMap<TypeEnumIndex, TypeEnum>,
|
||||||
flags: PrimaryMap<FlagsTypeIndex, FlagsType>,
|
flags: PrimaryMap<TypeFlagsIndex, TypeFlags>,
|
||||||
unions: PrimaryMap<UnionTypeIndex, UnionType>,
|
unions: PrimaryMap<TypeUnionIndex, TypeUnion>,
|
||||||
expecteds: PrimaryMap<ExpectedTypeIndex, ExpectedType>,
|
expecteds: PrimaryMap<TypeExpectedIndex, TypeExpected>,
|
||||||
|
|
||||||
module_types: ModuleTypes,
|
module_types: ModuleTypes,
|
||||||
}
|
}
|
||||||
@@ -193,18 +205,18 @@ macro_rules! impl_index {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl_index! {
|
impl_index! {
|
||||||
impl Index<ModuleTypeIndex> for ComponentTypes { ModuleType => modules }
|
impl Index<TypeModuleIndex> for ComponentTypes { TypeModule => modules }
|
||||||
impl Index<ComponentTypeIndex> for ComponentTypes { ComponentType => components }
|
impl Index<TypeComponentIndex> for ComponentTypes { TypeComponent => components }
|
||||||
impl Index<ComponentInstanceTypeIndex> for ComponentTypes { ComponentInstanceType => component_instances }
|
impl Index<TypeComponentInstanceIndex> for ComponentTypes { TypeComponentInstance => component_instances }
|
||||||
impl Index<FuncTypeIndex> for ComponentTypes { FuncType => functions }
|
impl Index<TypeFuncIndex> for ComponentTypes { TypeFunc => functions }
|
||||||
impl Index<InterfaceTypeIndex> for ComponentTypes { InterfaceType => interface_types }
|
impl Index<TypeInterfaceIndex> for ComponentTypes { InterfaceType => interface_types }
|
||||||
impl Index<RecordTypeIndex> for ComponentTypes { RecordType => records }
|
impl Index<TypeRecordIndex> for ComponentTypes { TypeRecord => records }
|
||||||
impl Index<VariantTypeIndex> for ComponentTypes { VariantType => variants }
|
impl Index<TypeVariantIndex> for ComponentTypes { TypeVariant => variants }
|
||||||
impl Index<TupleTypeIndex> for ComponentTypes { TupleType => tuples }
|
impl Index<TypeTupleIndex> for ComponentTypes { TypeTuple => tuples }
|
||||||
impl Index<EnumTypeIndex> for ComponentTypes { EnumType => enums }
|
impl Index<TypeEnumIndex> for ComponentTypes { TypeEnum => enums }
|
||||||
impl Index<FlagsTypeIndex> for ComponentTypes { FlagsType => flags }
|
impl Index<TypeFlagsIndex> for ComponentTypes { TypeFlags => flags }
|
||||||
impl Index<UnionTypeIndex> for ComponentTypes { UnionType => unions }
|
impl Index<TypeUnionIndex> for ComponentTypes { TypeUnion => unions }
|
||||||
impl Index<ExpectedTypeIndex> for ComponentTypes { ExpectedType => expecteds }
|
impl Index<TypeExpectedIndex> for ComponentTypes { TypeExpected => expecteds }
|
||||||
}
|
}
|
||||||
|
|
||||||
// Additionally forward anything that can index `ModuleTypes` to `ModuleTypes`
|
// Additionally forward anything that can index `ModuleTypes` to `ModuleTypes`
|
||||||
@@ -225,21 +237,27 @@ where
|
|||||||
/// managing building up core wasm [`ModuleTypes`] as well.
|
/// managing building up core wasm [`ModuleTypes`] as well.
|
||||||
#[derive(Default)]
|
#[derive(Default)]
|
||||||
pub struct ComponentTypesBuilder {
|
pub struct ComponentTypesBuilder {
|
||||||
type_scopes: Vec<PrimaryMap<TypeIndex, TypeDef>>,
|
type_scopes: Vec<TypeScope>,
|
||||||
functions: HashMap<FuncType, FuncTypeIndex>,
|
functions: HashMap<TypeFunc, TypeFuncIndex>,
|
||||||
interface_types: HashMap<InterfaceType, InterfaceTypeIndex>,
|
interface_types: HashMap<InterfaceType, TypeInterfaceIndex>,
|
||||||
records: HashMap<RecordType, RecordTypeIndex>,
|
records: HashMap<TypeRecord, TypeRecordIndex>,
|
||||||
variants: HashMap<VariantType, VariantTypeIndex>,
|
variants: HashMap<TypeVariant, TypeVariantIndex>,
|
||||||
tuples: HashMap<TupleType, TupleTypeIndex>,
|
tuples: HashMap<TypeTuple, TypeTupleIndex>,
|
||||||
enums: HashMap<EnumType, EnumTypeIndex>,
|
enums: HashMap<TypeEnum, TypeEnumIndex>,
|
||||||
flags: HashMap<FlagsType, FlagsTypeIndex>,
|
flags: HashMap<TypeFlags, TypeFlagsIndex>,
|
||||||
unions: HashMap<UnionType, UnionTypeIndex>,
|
unions: HashMap<TypeUnion, TypeUnionIndex>,
|
||||||
expecteds: HashMap<ExpectedType, ExpectedTypeIndex>,
|
expecteds: HashMap<TypeExpected, TypeExpectedIndex>,
|
||||||
|
|
||||||
component_types: ComponentTypes,
|
component_types: ComponentTypes,
|
||||||
module_types: ModuleTypesBuilder,
|
module_types: ModuleTypesBuilder,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[derive(Default)]
|
||||||
|
struct TypeScope {
|
||||||
|
core: PrimaryMap<TypeIndex, TypeDef>,
|
||||||
|
component: PrimaryMap<ComponentTypeIndex, TypeDef>,
|
||||||
|
}
|
||||||
|
|
||||||
impl ComponentTypesBuilder {
|
impl ComponentTypesBuilder {
|
||||||
/// Finishes this list of component types and returns the finished
|
/// Finishes this list of component types and returns the finished
|
||||||
/// structure.
|
/// structure.
|
||||||
@@ -261,20 +279,36 @@ impl ComponentTypesBuilder {
|
|||||||
///
|
///
|
||||||
/// This happens when a component is recursed into or a module/instance
|
/// This happens when a component is recursed into or a module/instance
|
||||||
/// type is recursed into.
|
/// type is recursed into.
|
||||||
pub fn push_component_types_scope(&mut self) {
|
pub fn push_type_scope(&mut self) {
|
||||||
self.type_scopes.push(PrimaryMap::new());
|
self.type_scopes.push(Default::default());
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Adds a new `TypeDef` definition within the current component types
|
/// Adds a new `TypeDef` definition within the current component types
|
||||||
/// scope.
|
/// scope.
|
||||||
///
|
///
|
||||||
/// Returns the `TypeIndex` associated with the type being pushed..
|
/// Returns the `ComponentTypeIndex` associated with the type being pushed.
|
||||||
///
|
///
|
||||||
/// # Panics
|
/// # Panics
|
||||||
///
|
///
|
||||||
/// Requires that `push_component_types_scope` was called previously.
|
/// Requires that `push_type_scope` was called previously.
|
||||||
pub fn push_component_typedef(&mut self, ty: TypeDef) -> TypeIndex {
|
pub fn push_component_typedef(&mut self, ty: TypeDef) -> ComponentTypeIndex {
|
||||||
self.type_scopes.last_mut().unwrap().push(ty)
|
debug_assert!(!matches!(ty, TypeDef::Module(_) | TypeDef::CoreFunc(_)));
|
||||||
|
self.type_scopes.last_mut().unwrap().component.push(ty)
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Adds a new `TypeDef` definition within the current core types
|
||||||
|
/// scope.
|
||||||
|
///
|
||||||
|
/// Returns the `TypeIndex` associated with the type being pushed. Note that
|
||||||
|
/// this should only be used with core-wasm-related `TypeDef` instances such
|
||||||
|
/// as `TypeDef::Module` and `TypeDef::CoreFunc`.
|
||||||
|
///
|
||||||
|
/// # Panics
|
||||||
|
///
|
||||||
|
/// Requires that `push_type_scope` was called previously.
|
||||||
|
pub fn push_core_typedef(&mut self, ty: TypeDef) -> TypeIndex {
|
||||||
|
debug_assert!(matches!(ty, TypeDef::Module(_) | TypeDef::CoreFunc(_)));
|
||||||
|
self.type_scopes.last_mut().unwrap().core.push(ty)
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Looks up an "outer" type in this builder to handle outer aliases.
|
/// Looks up an "outer" type in this builder to handle outer aliases.
|
||||||
@@ -285,52 +319,89 @@ impl ComponentTypesBuilder {
|
|||||||
/// # Panics
|
/// # Panics
|
||||||
///
|
///
|
||||||
/// Assumes that `count` and `ty` are valid.
|
/// Assumes that `count` and `ty` are valid.
|
||||||
pub fn component_outer_type(&self, count: u32, ty: TypeIndex) -> TypeDef {
|
pub fn component_outer_type(&self, count: u32, ty: ComponentTypeIndex) -> TypeDef {
|
||||||
// Reverse the index and 0 means the "current scope"
|
// Reverse the index and 0 means the "current scope"
|
||||||
let idx = self.type_scopes.len() - (count as usize) - 1;
|
let idx = self.type_scopes.len() - (count as usize) - 1;
|
||||||
self.type_scopes[idx][ty]
|
self.type_scopes[idx].component[ty]
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Pops a scope pushed by `push_component_types_scope`.
|
/// Same as `component_outer_type` but for core wasm types instead.
|
||||||
pub fn pop_component_types_scope(&mut self) {
|
pub fn core_outer_type(&self, count: u32, ty: TypeIndex) -> TypeDef {
|
||||||
|
// Reverse the index and 0 means the "current scope"
|
||||||
|
let idx = self.type_scopes.len() - (count as usize) - 1;
|
||||||
|
self.type_scopes[idx].core[ty]
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Pops a scope pushed by `push_type_scope`.
|
||||||
|
pub fn pop_type_scope(&mut self) {
|
||||||
self.type_scopes.pop().unwrap();
|
self.type_scopes.pop().unwrap();
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Translates a wasmparser `ComponentTypeDef` into a Wasmtime `TypeDef`,
|
/// Translates a wasmparser `TypeComponent` into a Wasmtime `TypeDef`,
|
||||||
/// interning types along the way.
|
/// interning types along the way.
|
||||||
pub fn component_type_def(&mut self, ty: &wasmparser::ComponentTypeDef<'_>) -> Result<TypeDef> {
|
pub fn intern_component_type(&mut self, ty: &wasmparser::ComponentType<'_>) -> Result<TypeDef> {
|
||||||
Ok(match ty {
|
Ok(match ty {
|
||||||
wasmparser::ComponentTypeDef::Module(ty) => TypeDef::Module(self.module_type(ty)?),
|
wasmparser::ComponentType::Defined(ty) => TypeDef::Interface(self.defined_type(ty)),
|
||||||
wasmparser::ComponentTypeDef::Component(ty) => {
|
wasmparser::ComponentType::Func(ty) => TypeDef::ComponentFunc(self.func_type(ty)),
|
||||||
|
wasmparser::ComponentType::Component(ty) => {
|
||||||
TypeDef::Component(self.component_type(ty)?)
|
TypeDef::Component(self.component_type(ty)?)
|
||||||
}
|
}
|
||||||
wasmparser::ComponentTypeDef::Instance(ty) => {
|
wasmparser::ComponentType::Instance(ty) => {
|
||||||
TypeDef::ComponentInstance(self.component_instance_type(ty)?)
|
TypeDef::ComponentInstance(self.component_instance_type(ty)?)
|
||||||
}
|
}
|
||||||
wasmparser::ComponentTypeDef::Function(ty) => TypeDef::Func(self.func_type(ty)),
|
|
||||||
wasmparser::ComponentTypeDef::Value(_ty) => unimplemented!("value types"),
|
|
||||||
wasmparser::ComponentTypeDef::Interface(ty) => {
|
|
||||||
TypeDef::Interface(self.interface_type(ty))
|
|
||||||
}
|
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
fn module_type(&mut self, ty: &[wasmparser::ModuleType<'_>]) -> Result<ModuleTypeIndex> {
|
/// Translates a wasmparser `CoreType` into a Wasmtime `TypeDef`,
|
||||||
let mut result = ModuleType::default();
|
/// interning types along the way.
|
||||||
|
pub fn intern_core_type(&mut self, ty: &wasmparser::CoreType<'_>) -> Result<TypeDef> {
|
||||||
|
Ok(match ty {
|
||||||
|
wasmparser::CoreType::Func(ty) => {
|
||||||
|
TypeDef::CoreFunc(self.module_types.wasm_func_type(ty.clone().try_into()?))
|
||||||
|
}
|
||||||
|
wasmparser::CoreType::Module(ty) => TypeDef::Module(self.module_type(ty)?),
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Translates a wasmparser `ComponentTypeRef` into a Wasmtime `TypeDef`.
|
||||||
|
pub fn component_type_ref(&self, ty: &wasmparser::ComponentTypeRef) -> TypeDef {
|
||||||
|
match ty {
|
||||||
|
wasmparser::ComponentTypeRef::Module(ty) => {
|
||||||
|
self.core_outer_type(0, TypeIndex::from_u32(*ty))
|
||||||
|
}
|
||||||
|
wasmparser::ComponentTypeRef::Func(ty)
|
||||||
|
| wasmparser::ComponentTypeRef::Instance(ty)
|
||||||
|
| wasmparser::ComponentTypeRef::Component(ty) => {
|
||||||
|
self.component_outer_type(0, ComponentTypeIndex::from_u32(*ty))
|
||||||
|
}
|
||||||
|
wasmparser::ComponentTypeRef::Value(..) => {
|
||||||
|
unimplemented!("references to value types");
|
||||||
|
}
|
||||||
|
wasmparser::ComponentTypeRef::Type(..) => {
|
||||||
|
unimplemented!("references to types");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn module_type(
|
||||||
|
&mut self,
|
||||||
|
ty: &[wasmparser::ModuleTypeDeclaration<'_>],
|
||||||
|
) -> Result<TypeModuleIndex> {
|
||||||
|
let mut result = TypeModule::default();
|
||||||
let mut functypes: PrimaryMap<TypeIndex, SignatureIndex> = PrimaryMap::default();
|
let mut functypes: PrimaryMap<TypeIndex, SignatureIndex> = PrimaryMap::default();
|
||||||
|
|
||||||
for item in ty {
|
for item in ty {
|
||||||
match item {
|
match item {
|
||||||
wasmparser::ModuleType::Type(wasmparser::TypeDef::Func(f)) => {
|
wasmparser::ModuleTypeDeclaration::Type(wasmparser::Type::Func(f)) => {
|
||||||
functypes.push(self.module_types.wasm_func_type(f.clone().try_into()?));
|
functypes.push(self.module_types.wasm_func_type(f.clone().try_into()?));
|
||||||
}
|
}
|
||||||
wasmparser::ModuleType::Export { name, ty } => {
|
wasmparser::ModuleTypeDeclaration::Export { name, ty } => {
|
||||||
let prev = result
|
let prev = result
|
||||||
.exports
|
.exports
|
||||||
.insert(name.to_string(), type_ref(ty, &functypes)?);
|
.insert(name.to_string(), type_ref(ty, &functypes)?);
|
||||||
assert!(prev.is_none());
|
assert!(prev.is_none());
|
||||||
}
|
}
|
||||||
wasmparser::ModuleType::Import(import) => {
|
wasmparser::ModuleTypeDeclaration::Import(import) => {
|
||||||
let prev = result.imports.insert(
|
let prev = result.imports.insert(
|
||||||
(import.module.to_string(), import.name.to_string()),
|
(import.module.to_string(), import.name.to_string()),
|
||||||
type_ref(&import.ty, &functypes)?,
|
type_ref(&import.ty, &functypes)?,
|
||||||
@@ -362,112 +433,135 @@ impl ComponentTypesBuilder {
|
|||||||
|
|
||||||
fn component_type(
|
fn component_type(
|
||||||
&mut self,
|
&mut self,
|
||||||
ty: &[wasmparser::ComponentType<'_>],
|
ty: &[ComponentTypeDeclaration<'_>],
|
||||||
) -> Result<ComponentTypeIndex> {
|
) -> Result<TypeComponentIndex> {
|
||||||
let mut result = ComponentType::default();
|
let mut result = TypeComponent::default();
|
||||||
self.push_component_types_scope();
|
self.push_type_scope();
|
||||||
|
|
||||||
for item in ty {
|
for item in ty {
|
||||||
match item {
|
match item {
|
||||||
wasmparser::ComponentType::Type(ty) => {
|
ComponentTypeDeclaration::Type(ty) => self.type_declaration_type(ty)?,
|
||||||
let ty = self.component_type_def(ty)?;
|
ComponentTypeDeclaration::CoreType(ty) => self.type_declaration_core_type(ty)?,
|
||||||
self.push_component_typedef(ty);
|
ComponentTypeDeclaration::Alias(alias) => self.type_declaration_alias(alias)?,
|
||||||
|
ComponentTypeDeclaration::Export { name, ty } => {
|
||||||
|
let ty = self.component_type_ref(ty);
|
||||||
|
result.exports.insert(name.to_string(), ty);
|
||||||
}
|
}
|
||||||
wasmparser::ComponentType::OuterType { count, index } => {
|
ComponentTypeDeclaration::Import(import) => {
|
||||||
let ty = self.component_outer_type(*count, TypeIndex::from_u32(*index));
|
let ty = self.component_type_ref(&import.ty);
|
||||||
self.push_component_typedef(ty);
|
result.imports.insert(import.name.to_string(), ty);
|
||||||
}
|
|
||||||
wasmparser::ComponentType::Export { name, ty } => {
|
|
||||||
result.exports.insert(
|
|
||||||
name.to_string(),
|
|
||||||
self.component_outer_type(0, TypeIndex::from_u32(*ty)),
|
|
||||||
);
|
|
||||||
}
|
|
||||||
wasmparser::ComponentType::Import(import) => {
|
|
||||||
result.imports.insert(
|
|
||||||
import.name.to_string(),
|
|
||||||
self.component_outer_type(0, TypeIndex::from_u32(import.ty)),
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
self.pop_component_types_scope();
|
self.pop_type_scope();
|
||||||
|
|
||||||
Ok(self.component_types.components.push(result))
|
Ok(self.component_types.components.push(result))
|
||||||
}
|
}
|
||||||
|
|
||||||
fn component_instance_type(
|
fn component_instance_type(
|
||||||
&mut self,
|
&mut self,
|
||||||
ty: &[wasmparser::InstanceType<'_>],
|
ty: &[InstanceTypeDeclaration<'_>],
|
||||||
) -> Result<ComponentInstanceTypeIndex> {
|
) -> Result<TypeComponentInstanceIndex> {
|
||||||
let mut result = ComponentInstanceType::default();
|
let mut result = TypeComponentInstance::default();
|
||||||
self.push_component_types_scope();
|
self.push_type_scope();
|
||||||
|
|
||||||
for item in ty {
|
for item in ty {
|
||||||
match item {
|
match item {
|
||||||
wasmparser::InstanceType::Type(ty) => {
|
InstanceTypeDeclaration::Type(ty) => self.type_declaration_type(ty)?,
|
||||||
let ty = self.component_type_def(ty)?;
|
InstanceTypeDeclaration::CoreType(ty) => self.type_declaration_core_type(ty)?,
|
||||||
self.push_component_typedef(ty);
|
InstanceTypeDeclaration::Alias(alias) => self.type_declaration_alias(alias)?,
|
||||||
}
|
InstanceTypeDeclaration::Export { name, ty } => {
|
||||||
wasmparser::InstanceType::OuterType { count, index } => {
|
let ty = self.component_type_ref(ty);
|
||||||
let ty = self.component_outer_type(*count, TypeIndex::from_u32(*index));
|
result.exports.insert(name.to_string(), ty);
|
||||||
self.push_component_typedef(ty);
|
|
||||||
}
|
|
||||||
wasmparser::InstanceType::Export { name, ty } => {
|
|
||||||
result.exports.insert(
|
|
||||||
name.to_string(),
|
|
||||||
self.component_outer_type(0, TypeIndex::from_u32(*ty)),
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
self.pop_component_types_scope();
|
self.pop_type_scope();
|
||||||
|
|
||||||
Ok(self.component_types.component_instances.push(result))
|
Ok(self.component_types.component_instances.push(result))
|
||||||
}
|
}
|
||||||
|
|
||||||
fn func_type(&mut self, ty: &wasmparser::ComponentFuncType<'_>) -> FuncTypeIndex {
|
fn type_declaration_type(&mut self, ty: &wasmparser::ComponentType<'_>) -> Result<()> {
|
||||||
let ty = FuncType {
|
let ty = self.intern_component_type(ty)?;
|
||||||
|
self.push_component_typedef(ty);
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
|
||||||
|
fn type_declaration_core_type(&mut self, ty: &wasmparser::CoreType<'_>) -> Result<()> {
|
||||||
|
let ty = self.intern_core_type(ty)?;
|
||||||
|
self.push_core_typedef(ty);
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
|
||||||
|
fn type_declaration_alias(&mut self, alias: &wasmparser::ComponentAlias<'_>) -> Result<()> {
|
||||||
|
match alias {
|
||||||
|
ComponentAlias::Outer {
|
||||||
|
kind: ComponentOuterAliasKind::CoreType,
|
||||||
|
count,
|
||||||
|
index,
|
||||||
|
} => {
|
||||||
|
let ty = self.core_outer_type(*count, TypeIndex::from_u32(*index));
|
||||||
|
self.push_core_typedef(ty);
|
||||||
|
}
|
||||||
|
ComponentAlias::Outer {
|
||||||
|
kind: ComponentOuterAliasKind::Type,
|
||||||
|
count,
|
||||||
|
index,
|
||||||
|
} => {
|
||||||
|
let ty = self.component_outer_type(*count, ComponentTypeIndex::from_u32(*index));
|
||||||
|
self.push_component_typedef(ty);
|
||||||
|
}
|
||||||
|
a => unreachable!("invalid alias {a:?}"),
|
||||||
|
}
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
|
||||||
|
fn func_type(&mut self, ty: &wasmparser::ComponentFuncType<'_>) -> TypeFuncIndex {
|
||||||
|
let ty = TypeFunc {
|
||||||
params: ty
|
params: ty
|
||||||
.params
|
.params
|
||||||
.iter()
|
.iter()
|
||||||
.map(|(name, ty)| (name.map(|s| s.to_string()), self.interface_type_ref(ty)))
|
.map(|(name, ty)| (name.map(|s| s.to_string()), self.valtype(ty)))
|
||||||
.collect(),
|
.collect(),
|
||||||
result: self.interface_type_ref(&ty.result),
|
result: self.valtype(&ty.result),
|
||||||
};
|
};
|
||||||
intern(&mut self.functions, &mut self.component_types.functions, ty)
|
intern(&mut self.functions, &mut self.component_types.functions, ty)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn interface_type(&mut self, ty: &wasmparser::InterfaceType<'_>) -> InterfaceType {
|
fn defined_type(&mut self, ty: &wasmparser::ComponentDefinedType<'_>) -> InterfaceType {
|
||||||
match ty {
|
match ty {
|
||||||
wasmparser::InterfaceType::Primitive(ty) => ty.into(),
|
wasmparser::ComponentDefinedType::Primitive(ty) => ty.into(),
|
||||||
wasmparser::InterfaceType::Record(e) => InterfaceType::Record(self.record_type(e)),
|
wasmparser::ComponentDefinedType::Record(e) => {
|
||||||
wasmparser::InterfaceType::Variant(e) => InterfaceType::Variant(self.variant_type(e)),
|
InterfaceType::Record(self.record_type(e))
|
||||||
wasmparser::InterfaceType::List(e) => {
|
}
|
||||||
let ty = self.interface_type_ref(e);
|
wasmparser::ComponentDefinedType::Variant(e) => {
|
||||||
|
InterfaceType::Variant(self.variant_type(e))
|
||||||
|
}
|
||||||
|
wasmparser::ComponentDefinedType::List(e) => {
|
||||||
|
let ty = self.valtype(e);
|
||||||
InterfaceType::List(self.intern_interface_type(ty))
|
InterfaceType::List(self.intern_interface_type(ty))
|
||||||
}
|
}
|
||||||
wasmparser::InterfaceType::Tuple(e) => InterfaceType::Tuple(self.tuple_type(e)),
|
wasmparser::ComponentDefinedType::Tuple(e) => InterfaceType::Tuple(self.tuple_type(e)),
|
||||||
wasmparser::InterfaceType::Flags(e) => InterfaceType::Flags(self.flags_type(e)),
|
wasmparser::ComponentDefinedType::Flags(e) => InterfaceType::Flags(self.flags_type(e)),
|
||||||
wasmparser::InterfaceType::Enum(e) => InterfaceType::Enum(self.enum_type(e)),
|
wasmparser::ComponentDefinedType::Enum(e) => InterfaceType::Enum(self.enum_type(e)),
|
||||||
wasmparser::InterfaceType::Union(e) => InterfaceType::Union(self.union_type(e)),
|
wasmparser::ComponentDefinedType::Union(e) => InterfaceType::Union(self.union_type(e)),
|
||||||
wasmparser::InterfaceType::Option(e) => {
|
wasmparser::ComponentDefinedType::Option(e) => {
|
||||||
let ty = self.interface_type_ref(e);
|
let ty = self.valtype(e);
|
||||||
InterfaceType::Option(self.intern_interface_type(ty))
|
InterfaceType::Option(self.intern_interface_type(ty))
|
||||||
}
|
}
|
||||||
wasmparser::InterfaceType::Expected { ok, error } => {
|
wasmparser::ComponentDefinedType::Expected { ok, error } => {
|
||||||
InterfaceType::Expected(self.expected_type(ok, error))
|
InterfaceType::Expected(self.expected_type(ok, error))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn interface_type_ref(&mut self, ty: &wasmparser::InterfaceTypeRef) -> InterfaceType {
|
fn valtype(&mut self, ty: &wasmparser::ComponentValType) -> InterfaceType {
|
||||||
match ty {
|
match ty {
|
||||||
wasmparser::InterfaceTypeRef::Primitive(p) => p.into(),
|
wasmparser::ComponentValType::Primitive(p) => p.into(),
|
||||||
wasmparser::InterfaceTypeRef::Type(idx) => {
|
wasmparser::ComponentValType::Type(idx) => {
|
||||||
let idx = TypeIndex::from_u32(*idx);
|
let idx = ComponentTypeIndex::from_u32(*idx);
|
||||||
match self.component_outer_type(0, idx) {
|
match self.component_outer_type(0, idx) {
|
||||||
TypeDef::Interface(ty) => ty,
|
TypeDef::Interface(ty) => ty,
|
||||||
// this should not be possible if the module validated
|
// this should not be possible if the module validated
|
||||||
@@ -477,7 +571,7 @@ impl ComponentTypesBuilder {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn intern_interface_type(&mut self, ty: InterfaceType) -> InterfaceTypeIndex {
|
fn intern_interface_type(&mut self, ty: InterfaceType) -> TypeInterfaceIndex {
|
||||||
intern(
|
intern(
|
||||||
&mut self.interface_types,
|
&mut self.interface_types,
|
||||||
&mut self.component_types.interface_types,
|
&mut self.component_types.interface_types,
|
||||||
@@ -485,30 +579,30 @@ impl ComponentTypesBuilder {
|
|||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn record_type(&mut self, record: &[(&str, wasmparser::InterfaceTypeRef)]) -> RecordTypeIndex {
|
fn record_type(&mut self, record: &[(&str, wasmparser::ComponentValType)]) -> TypeRecordIndex {
|
||||||
let record = RecordType {
|
let record = TypeRecord {
|
||||||
fields: record
|
fields: record
|
||||||
.iter()
|
.iter()
|
||||||
.map(|(name, ty)| RecordField {
|
.map(|(name, ty)| RecordField {
|
||||||
name: name.to_string(),
|
name: name.to_string(),
|
||||||
ty: self.interface_type_ref(ty),
|
ty: self.valtype(ty),
|
||||||
})
|
})
|
||||||
.collect(),
|
.collect(),
|
||||||
};
|
};
|
||||||
intern(&mut self.records, &mut self.component_types.records, record)
|
intern(&mut self.records, &mut self.component_types.records, record)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn variant_type(&mut self, cases: &[wasmparser::VariantCase<'_>]) -> VariantTypeIndex {
|
fn variant_type(&mut self, cases: &[wasmparser::VariantCase<'_>]) -> TypeVariantIndex {
|
||||||
let variant = VariantType {
|
let variant = TypeVariant {
|
||||||
cases: cases
|
cases: cases
|
||||||
.iter()
|
.iter()
|
||||||
.map(|case| {
|
.map(|case| {
|
||||||
// FIXME: need to implement `default_to`, not sure what that
|
// FIXME: need to implement `refines`, not sure what that
|
||||||
// is at this time.
|
// is at this time.
|
||||||
assert!(case.default_to.is_none());
|
assert!(case.refines.is_none());
|
||||||
VariantCase {
|
VariantCase {
|
||||||
name: case.name.to_string(),
|
name: case.name.to_string(),
|
||||||
ty: self.interface_type_ref(&case.ty),
|
ty: self.valtype(&case.ty),
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
.collect(),
|
.collect(),
|
||||||
@@ -520,42 +614,42 @@ impl ComponentTypesBuilder {
|
|||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn tuple_type(&mut self, types: &[wasmparser::InterfaceTypeRef]) -> TupleTypeIndex {
|
fn tuple_type(&mut self, types: &[wasmparser::ComponentValType]) -> TypeTupleIndex {
|
||||||
let tuple = TupleType {
|
let tuple = TypeTuple {
|
||||||
types: types.iter().map(|ty| self.interface_type_ref(ty)).collect(),
|
types: types.iter().map(|ty| self.valtype(ty)).collect(),
|
||||||
};
|
};
|
||||||
intern(&mut self.tuples, &mut self.component_types.tuples, tuple)
|
intern(&mut self.tuples, &mut self.component_types.tuples, tuple)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn flags_type(&mut self, flags: &[&str]) -> FlagsTypeIndex {
|
fn flags_type(&mut self, flags: &[&str]) -> TypeFlagsIndex {
|
||||||
let flags = FlagsType {
|
let flags = TypeFlags {
|
||||||
names: flags.iter().map(|s| s.to_string()).collect(),
|
names: flags.iter().map(|s| s.to_string()).collect(),
|
||||||
};
|
};
|
||||||
intern(&mut self.flags, &mut self.component_types.flags, flags)
|
intern(&mut self.flags, &mut self.component_types.flags, flags)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn enum_type(&mut self, variants: &[&str]) -> EnumTypeIndex {
|
fn enum_type(&mut self, variants: &[&str]) -> TypeEnumIndex {
|
||||||
let e = EnumType {
|
let e = TypeEnum {
|
||||||
names: variants.iter().map(|s| s.to_string()).collect(),
|
names: variants.iter().map(|s| s.to_string()).collect(),
|
||||||
};
|
};
|
||||||
intern(&mut self.enums, &mut self.component_types.enums, e)
|
intern(&mut self.enums, &mut self.component_types.enums, e)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn union_type(&mut self, types: &[wasmparser::InterfaceTypeRef]) -> UnionTypeIndex {
|
fn union_type(&mut self, types: &[wasmparser::ComponentValType]) -> TypeUnionIndex {
|
||||||
let union = UnionType {
|
let union = TypeUnion {
|
||||||
types: types.iter().map(|ty| self.interface_type_ref(ty)).collect(),
|
types: types.iter().map(|ty| self.valtype(ty)).collect(),
|
||||||
};
|
};
|
||||||
intern(&mut self.unions, &mut self.component_types.unions, union)
|
intern(&mut self.unions, &mut self.component_types.unions, union)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn expected_type(
|
fn expected_type(
|
||||||
&mut self,
|
&mut self,
|
||||||
ok: &wasmparser::InterfaceTypeRef,
|
ok: &wasmparser::ComponentValType,
|
||||||
err: &wasmparser::InterfaceTypeRef,
|
err: &wasmparser::ComponentValType,
|
||||||
) -> ExpectedTypeIndex {
|
) -> TypeExpectedIndex {
|
||||||
let expected = ExpectedType {
|
let expected = TypeExpected {
|
||||||
ok: self.interface_type_ref(ok),
|
ok: self.valtype(ok),
|
||||||
err: self.interface_type_ref(err),
|
err: self.valtype(err),
|
||||||
};
|
};
|
||||||
intern(
|
intern(
|
||||||
&mut self.expecteds,
|
&mut self.expecteds,
|
||||||
@@ -597,16 +691,18 @@ where
|
|||||||
/// through a sibling `ComponentTypes` structure.
|
/// through a sibling `ComponentTypes` structure.
|
||||||
#[derive(Copy, Clone, Debug, Serialize, Deserialize)]
|
#[derive(Copy, Clone, Debug, Serialize, Deserialize)]
|
||||||
pub enum TypeDef {
|
pub enum TypeDef {
|
||||||
/// A core wasm module and its type.
|
|
||||||
Module(ModuleTypeIndex),
|
|
||||||
/// A component and its type.
|
/// A component and its type.
|
||||||
Component(ComponentTypeIndex),
|
Component(TypeComponentIndex),
|
||||||
/// An instance of a component.
|
/// An instance of a component.
|
||||||
ComponentInstance(ComponentInstanceTypeIndex),
|
ComponentInstance(TypeComponentInstanceIndex),
|
||||||
/// A component function, not to be confused with a core wasm function.
|
/// A component function, not to be confused with a core wasm function.
|
||||||
Func(FuncTypeIndex),
|
ComponentFunc(TypeFuncIndex),
|
||||||
/// An interface type.
|
/// An interface type.
|
||||||
Interface(InterfaceType),
|
Interface(InterfaceType),
|
||||||
|
/// A core wasm module and its type.
|
||||||
|
Module(TypeModuleIndex),
|
||||||
|
/// A core wasm function using only core wasm types.
|
||||||
|
CoreFunc(SignatureIndex),
|
||||||
}
|
}
|
||||||
|
|
||||||
// NB: Note that maps below are stored as an `IndexMap` now but the order
|
// NB: Note that maps below are stored as an `IndexMap` now but the order
|
||||||
@@ -616,10 +712,10 @@ pub enum TypeDef {
|
|||||||
|
|
||||||
/// The type of a module in the component model.
|
/// The type of a module in the component model.
|
||||||
///
|
///
|
||||||
/// Note that this is not to be confused with `ComponentType` below. This is
|
/// Note that this is not to be confused with `TypeComponent` below. This is
|
||||||
/// intended only for core wasm modules, not for components.
|
/// intended only for core wasm modules, not for components.
|
||||||
#[derive(Serialize, Deserialize, Default)]
|
#[derive(Serialize, Deserialize, Default)]
|
||||||
pub struct ModuleType {
|
pub struct TypeModule {
|
||||||
/// The values that this module imports.
|
/// The values that this module imports.
|
||||||
///
|
///
|
||||||
/// Note that the value of this map is a core wasm `EntityType`, not a
|
/// Note that the value of this map is a core wasm `EntityType`, not a
|
||||||
@@ -638,7 +734,7 @@ pub struct ModuleType {
|
|||||||
|
|
||||||
/// The type of a component in the component model.
|
/// The type of a component in the component model.
|
||||||
#[derive(Serialize, Deserialize, Default)]
|
#[derive(Serialize, Deserialize, Default)]
|
||||||
pub struct ComponentType {
|
pub struct TypeComponent {
|
||||||
/// The named values that this component imports.
|
/// The named values that this component imports.
|
||||||
pub imports: IndexMap<String, TypeDef>,
|
pub imports: IndexMap<String, TypeDef>,
|
||||||
/// The named values that this component exports.
|
/// The named values that this component exports.
|
||||||
@@ -650,14 +746,14 @@ pub struct ComponentType {
|
|||||||
///
|
///
|
||||||
/// Component instances only have exports of types in the component model.
|
/// Component instances only have exports of types in the component model.
|
||||||
#[derive(Serialize, Deserialize, Default)]
|
#[derive(Serialize, Deserialize, Default)]
|
||||||
pub struct ComponentInstanceType {
|
pub struct TypeComponentInstance {
|
||||||
/// The list of exports that this component has along with their types.
|
/// The list of exports that this component has along with their types.
|
||||||
pub exports: IndexMap<String, TypeDef>,
|
pub exports: IndexMap<String, TypeDef>,
|
||||||
}
|
}
|
||||||
|
|
||||||
/// A component function type in the component model.
|
/// A component function type in the component model.
|
||||||
#[derive(Serialize, Deserialize, Clone, Hash, Eq, PartialEq, Debug)]
|
#[derive(Serialize, Deserialize, Clone, Hash, Eq, PartialEq, Debug)]
|
||||||
pub struct FuncType {
|
pub struct TypeFunc {
|
||||||
/// The list of optionally named parameters for this function, and their
|
/// The list of optionally named parameters for this function, and their
|
||||||
/// types.
|
/// types.
|
||||||
pub params: Box<[(Option<String>, InterfaceType)]>,
|
pub params: Box<[(Option<String>, InterfaceType)]>,
|
||||||
@@ -688,34 +784,34 @@ pub enum InterfaceType {
|
|||||||
Float64,
|
Float64,
|
||||||
Char,
|
Char,
|
||||||
String,
|
String,
|
||||||
Record(RecordTypeIndex),
|
Record(TypeRecordIndex),
|
||||||
Variant(VariantTypeIndex),
|
Variant(TypeVariantIndex),
|
||||||
List(InterfaceTypeIndex),
|
List(TypeInterfaceIndex),
|
||||||
Tuple(TupleTypeIndex),
|
Tuple(TypeTupleIndex),
|
||||||
Flags(FlagsTypeIndex),
|
Flags(TypeFlagsIndex),
|
||||||
Enum(EnumTypeIndex),
|
Enum(TypeEnumIndex),
|
||||||
Union(UnionTypeIndex),
|
Union(TypeUnionIndex),
|
||||||
Option(InterfaceTypeIndex),
|
Option(TypeInterfaceIndex),
|
||||||
Expected(ExpectedTypeIndex),
|
Expected(TypeExpectedIndex),
|
||||||
}
|
}
|
||||||
|
|
||||||
impl From<&wasmparser::PrimitiveInterfaceType> for InterfaceType {
|
impl From<&wasmparser::PrimitiveValType> for InterfaceType {
|
||||||
fn from(ty: &wasmparser::PrimitiveInterfaceType) -> InterfaceType {
|
fn from(ty: &wasmparser::PrimitiveValType) -> InterfaceType {
|
||||||
match ty {
|
match ty {
|
||||||
wasmparser::PrimitiveInterfaceType::Unit => InterfaceType::Unit,
|
wasmparser::PrimitiveValType::Unit => InterfaceType::Unit,
|
||||||
wasmparser::PrimitiveInterfaceType::Bool => InterfaceType::Bool,
|
wasmparser::PrimitiveValType::Bool => InterfaceType::Bool,
|
||||||
wasmparser::PrimitiveInterfaceType::S8 => InterfaceType::S8,
|
wasmparser::PrimitiveValType::S8 => InterfaceType::S8,
|
||||||
wasmparser::PrimitiveInterfaceType::U8 => InterfaceType::U8,
|
wasmparser::PrimitiveValType::U8 => InterfaceType::U8,
|
||||||
wasmparser::PrimitiveInterfaceType::S16 => InterfaceType::S16,
|
wasmparser::PrimitiveValType::S16 => InterfaceType::S16,
|
||||||
wasmparser::PrimitiveInterfaceType::U16 => InterfaceType::U16,
|
wasmparser::PrimitiveValType::U16 => InterfaceType::U16,
|
||||||
wasmparser::PrimitiveInterfaceType::S32 => InterfaceType::S32,
|
wasmparser::PrimitiveValType::S32 => InterfaceType::S32,
|
||||||
wasmparser::PrimitiveInterfaceType::U32 => InterfaceType::U32,
|
wasmparser::PrimitiveValType::U32 => InterfaceType::U32,
|
||||||
wasmparser::PrimitiveInterfaceType::S64 => InterfaceType::S64,
|
wasmparser::PrimitiveValType::S64 => InterfaceType::S64,
|
||||||
wasmparser::PrimitiveInterfaceType::U64 => InterfaceType::U64,
|
wasmparser::PrimitiveValType::U64 => InterfaceType::U64,
|
||||||
wasmparser::PrimitiveInterfaceType::Float32 => InterfaceType::Float32,
|
wasmparser::PrimitiveValType::Float32 => InterfaceType::Float32,
|
||||||
wasmparser::PrimitiveInterfaceType::Float64 => InterfaceType::Float64,
|
wasmparser::PrimitiveValType::Float64 => InterfaceType::Float64,
|
||||||
wasmparser::PrimitiveInterfaceType::Char => InterfaceType::Char,
|
wasmparser::PrimitiveValType::Char => InterfaceType::Char,
|
||||||
wasmparser::PrimitiveInterfaceType::String => InterfaceType::String,
|
wasmparser::PrimitiveValType::String => InterfaceType::String,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -724,7 +820,7 @@ impl From<&wasmparser::PrimitiveInterfaceType> for InterfaceType {
|
|||||||
///
|
///
|
||||||
/// This is equivalent to a `struct` in Rust.
|
/// This is equivalent to a `struct` in Rust.
|
||||||
#[derive(Serialize, Deserialize, Clone, Hash, Eq, PartialEq, Debug)]
|
#[derive(Serialize, Deserialize, Clone, Hash, Eq, PartialEq, Debug)]
|
||||||
pub struct RecordType {
|
pub struct TypeRecord {
|
||||||
/// The fields that are contained within this struct type.
|
/// The fields that are contained within this struct type.
|
||||||
pub fields: Box<[RecordField]>,
|
pub fields: Box<[RecordField]>,
|
||||||
}
|
}
|
||||||
@@ -744,7 +840,7 @@ pub struct RecordField {
|
|||||||
/// cases and each case has a unique name and an optional payload associated
|
/// cases and each case has a unique name and an optional payload associated
|
||||||
/// with it.
|
/// with it.
|
||||||
#[derive(Serialize, Deserialize, Clone, Hash, Eq, PartialEq, Debug)]
|
#[derive(Serialize, Deserialize, Clone, Hash, Eq, PartialEq, Debug)]
|
||||||
pub struct VariantType {
|
pub struct TypeVariant {
|
||||||
/// The list of cases that this variant can take.
|
/// The list of cases that this variant can take.
|
||||||
pub cases: Box<[VariantCase]>,
|
pub cases: Box<[VariantCase]>,
|
||||||
}
|
}
|
||||||
@@ -764,7 +860,7 @@ pub struct VariantCase {
|
|||||||
/// This is largely the same as a tuple in Rust, basically a record with
|
/// This is largely the same as a tuple in Rust, basically a record with
|
||||||
/// unnamed fields.
|
/// unnamed fields.
|
||||||
#[derive(Serialize, Deserialize, Clone, Hash, Eq, PartialEq, Debug)]
|
#[derive(Serialize, Deserialize, Clone, Hash, Eq, PartialEq, Debug)]
|
||||||
pub struct TupleType {
|
pub struct TypeTuple {
|
||||||
/// The types that are contained within this tuple.
|
/// The types that are contained within this tuple.
|
||||||
pub types: Box<[InterfaceType]>,
|
pub types: Box<[InterfaceType]>,
|
||||||
}
|
}
|
||||||
@@ -774,7 +870,7 @@ pub struct TupleType {
|
|||||||
/// This can be thought of as a record-of-bools, although the representation is
|
/// This can be thought of as a record-of-bools, although the representation is
|
||||||
/// more efficient as bitflags.
|
/// more efficient as bitflags.
|
||||||
#[derive(Serialize, Deserialize, Clone, Hash, Eq, PartialEq, Debug)]
|
#[derive(Serialize, Deserialize, Clone, Hash, Eq, PartialEq, Debug)]
|
||||||
pub struct FlagsType {
|
pub struct TypeFlags {
|
||||||
/// The names of all flags, all of which are unique.
|
/// The names of all flags, all of which are unique.
|
||||||
pub names: Box<[String]>,
|
pub names: Box<[String]>,
|
||||||
}
|
}
|
||||||
@@ -785,7 +881,7 @@ pub struct FlagsType {
|
|||||||
/// In interface types enums are simply a bag of names, and can be seen as a
|
/// In interface types enums are simply a bag of names, and can be seen as a
|
||||||
/// variant where all payloads are `Unit`.
|
/// variant where all payloads are `Unit`.
|
||||||
#[derive(Serialize, Deserialize, Clone, Hash, Eq, PartialEq, Debug)]
|
#[derive(Serialize, Deserialize, Clone, Hash, Eq, PartialEq, Debug)]
|
||||||
pub struct EnumType {
|
pub struct TypeEnum {
|
||||||
/// The names of this enum, all of which are unique.
|
/// The names of this enum, all of which are unique.
|
||||||
pub names: Box<[String]>,
|
pub names: Box<[String]>,
|
||||||
}
|
}
|
||||||
@@ -796,14 +892,14 @@ pub struct EnumType {
|
|||||||
/// type where each type here has a name that's numbered. This is still a
|
/// type where each type here has a name that's numbered. This is still a
|
||||||
/// tagged union.
|
/// tagged union.
|
||||||
#[derive(Serialize, Deserialize, Clone, Hash, Eq, PartialEq, Debug)]
|
#[derive(Serialize, Deserialize, Clone, Hash, Eq, PartialEq, Debug)]
|
||||||
pub struct UnionType {
|
pub struct TypeUnion {
|
||||||
/// The list of types this is a union over.
|
/// The list of types this is a union over.
|
||||||
pub types: Box<[InterfaceType]>,
|
pub types: Box<[InterfaceType]>,
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Shape of an "expected" interface type.
|
/// Shape of an "expected" interface type.
|
||||||
#[derive(Serialize, Deserialize, Clone, Hash, Eq, PartialEq, Debug)]
|
#[derive(Serialize, Deserialize, Clone, Hash, Eq, PartialEq, Debug)]
|
||||||
pub struct ExpectedType {
|
pub struct TypeExpected {
|
||||||
/// The `T` in `Result<T, E>`
|
/// The `T` in `Result<T, E>`
|
||||||
pub ok: InterfaceType,
|
pub ok: InterfaceType,
|
||||||
/// The `E` in `Result<T, E>`
|
/// The `E` in `Result<T, E>`
|
||||||
|
|||||||
@@ -15,8 +15,8 @@ use std::path::PathBuf;
|
|||||||
use std::sync::Arc;
|
use std::sync::Arc;
|
||||||
use wasmparser::{
|
use wasmparser::{
|
||||||
CustomSectionReader, DataKind, ElementItem, ElementKind, Encoding, ExternalKind, FuncValidator,
|
CustomSectionReader, DataKind, ElementItem, ElementKind, Encoding, ExternalKind, FuncValidator,
|
||||||
FunctionBody, NameSectionReader, Naming, Operator, Parser, Payload, TypeDef, TypeRef,
|
FunctionBody, NameSectionReader, Naming, Operator, Parser, Payload, Type, TypeRef, Validator,
|
||||||
Validator, ValidatorResources,
|
ValidatorResources,
|
||||||
};
|
};
|
||||||
|
|
||||||
/// Object containing the standalone environment information.
|
/// Object containing the standalone environment information.
|
||||||
@@ -130,8 +130,8 @@ pub struct WasmFileInfo {
|
|||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
#[allow(missing_docs)]
|
#[allow(missing_docs)]
|
||||||
pub struct FunctionMetadata {
|
pub struct FunctionMetadata {
|
||||||
pub params: Box<[wasmparser::Type]>,
|
pub params: Box<[wasmparser::ValType]>,
|
||||||
pub locals: Box<[(u32, wasmparser::Type)]>,
|
pub locals: Box<[(u32, wasmparser::ValType)]>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'a, 'data> ModuleEnvironment<'a, 'data> {
|
impl<'a, 'data> ModuleEnvironment<'a, 'data> {
|
||||||
@@ -216,7 +216,7 @@ impl<'a, 'data> ModuleEnvironment<'a, 'data> {
|
|||||||
|
|
||||||
for ty in types {
|
for ty in types {
|
||||||
match ty? {
|
match ty? {
|
||||||
TypeDef::Func(wasm_func_ty) => {
|
Type::Func(wasm_func_ty) => {
|
||||||
self.declare_type_func(wasm_func_ty.try_into()?)?;
|
self.declare_type_func(wasm_func_ty.try_into()?)?;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -15,13 +15,13 @@ log = "0.4.8"
|
|||||||
rayon = "1.2.1"
|
rayon = "1.2.1"
|
||||||
target-lexicon = "0.12.3"
|
target-lexicon = "0.12.3"
|
||||||
tempfile = "3.3.0"
|
tempfile = "3.3.0"
|
||||||
wasmparser = "0.85.0"
|
wasmparser = "0.86.0"
|
||||||
wasmprinter = "0.2.35"
|
wasmprinter = "0.2.36"
|
||||||
wasmtime = { path = "../wasmtime" }
|
wasmtime = { path = "../wasmtime" }
|
||||||
wasmtime-wast = { path = "../wast" }
|
wasmtime-wast = { path = "../wast" }
|
||||||
wasm-encoder = "0.12.0"
|
wasm-encoder = "0.13.0"
|
||||||
wasm-smith = "0.10.1"
|
wasm-smith = "0.11.0"
|
||||||
wasm-mutate = "0.2.3"
|
wasm-mutate = "0.2.4"
|
||||||
wasm-spec-interpreter = { path = "./wasm-spec-interpreter", optional = true }
|
wasm-spec-interpreter = { path = "./wasm-spec-interpreter", optional = true }
|
||||||
wasmi = "0.7.0"
|
wasmi = "0.7.0"
|
||||||
|
|
||||||
|
|||||||
@@ -3,7 +3,7 @@
|
|||||||
use arbitrary::{Arbitrary, Result, Unstructured};
|
use arbitrary::{Arbitrary, Result, Unstructured};
|
||||||
use std::ops::RangeInclusive;
|
use std::ops::RangeInclusive;
|
||||||
use wasm_encoder::{
|
use wasm_encoder::{
|
||||||
CodeSection, EntityType, Export, ExportSection, Function, FunctionSection, GlobalSection,
|
CodeSection, EntityType, ExportKind, ExportSection, Function, FunctionSection, GlobalSection,
|
||||||
ImportSection, Instruction, Module, TableSection, TableType, TypeSection, ValType,
|
ImportSection, Instruction, Module, TableSection, TableType, TypeSection, ValType,
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -103,7 +103,7 @@ impl TableOps {
|
|||||||
functions.function(1);
|
functions.function(1);
|
||||||
|
|
||||||
let mut exports = ExportSection::new();
|
let mut exports = ExportSection::new();
|
||||||
exports.export("run", Export::Function(3));
|
exports.export("run", ExportKind::Func, 3);
|
||||||
|
|
||||||
// Give ourselves one scratch local that we can use in various `TableOp`
|
// Give ourselves one scratch local that we can use in various `TableOp`
|
||||||
// implementations.
|
// implementations.
|
||||||
|
|||||||
@@ -12,4 +12,4 @@ edition = "2021"
|
|||||||
cranelift-entity = { path = "../../cranelift/entity", version = "0.86.0", features = ['enable-serde'] }
|
cranelift-entity = { path = "../../cranelift/entity", version = "0.86.0", features = ['enable-serde'] }
|
||||||
serde = { version = "1.0.94", features = ["derive"] }
|
serde = { version = "1.0.94", features = ["derive"] }
|
||||||
thiserror = "1.0.4"
|
thiserror = "1.0.4"
|
||||||
wasmparser = { version = "0.85.0", default-features = false }
|
wasmparser = { version = "0.86.0", default-features = false }
|
||||||
|
|||||||
@@ -31,10 +31,10 @@ pub enum WasmType {
|
|||||||
ExternRef,
|
ExternRef,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl TryFrom<wasmparser::Type> for WasmType {
|
impl TryFrom<wasmparser::ValType> for WasmType {
|
||||||
type Error = WasmError;
|
type Error = WasmError;
|
||||||
fn try_from(ty: wasmparser::Type) -> Result<Self, Self::Error> {
|
fn try_from(ty: wasmparser::ValType) -> Result<Self, Self::Error> {
|
||||||
use wasmparser::Type::*;
|
use wasmparser::ValType::*;
|
||||||
match ty {
|
match ty {
|
||||||
I32 => Ok(WasmType::I32),
|
I32 => Ok(WasmType::I32),
|
||||||
I64 => Ok(WasmType::I64),
|
I64 => Ok(WasmType::I64),
|
||||||
@@ -47,16 +47,16 @@ impl TryFrom<wasmparser::Type> for WasmType {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl From<WasmType> for wasmparser::Type {
|
impl From<WasmType> for wasmparser::ValType {
|
||||||
fn from(ty: WasmType) -> wasmparser::Type {
|
fn from(ty: WasmType) -> wasmparser::ValType {
|
||||||
match ty {
|
match ty {
|
||||||
WasmType::I32 => wasmparser::Type::I32,
|
WasmType::I32 => wasmparser::ValType::I32,
|
||||||
WasmType::I64 => wasmparser::Type::I64,
|
WasmType::I64 => wasmparser::ValType::I64,
|
||||||
WasmType::F32 => wasmparser::Type::F32,
|
WasmType::F32 => wasmparser::ValType::F32,
|
||||||
WasmType::F64 => wasmparser::Type::F64,
|
WasmType::F64 => wasmparser::ValType::F64,
|
||||||
WasmType::V128 => wasmparser::Type::V128,
|
WasmType::V128 => wasmparser::ValType::V128,
|
||||||
WasmType::FuncRef => wasmparser::Type::FuncRef,
|
WasmType::FuncRef => wasmparser::ValType::FuncRef,
|
||||||
WasmType::ExternRef => wasmparser::Type::ExternRef,
|
WasmType::ExternRef => wasmparser::ValType::ExternRef,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -20,7 +20,7 @@ wasmtime-cache = { path = "../cache", version = "=0.39.0", optional = true }
|
|||||||
wasmtime-fiber = { path = "../fiber", version = "=0.39.0", optional = true }
|
wasmtime-fiber = { path = "../fiber", version = "=0.39.0", optional = true }
|
||||||
wasmtime-cranelift = { path = "../cranelift", version = "=0.39.0", optional = true }
|
wasmtime-cranelift = { path = "../cranelift", version = "=0.39.0", optional = true }
|
||||||
target-lexicon = { version = "0.12.0", default-features = false }
|
target-lexicon = { version = "0.12.0", default-features = false }
|
||||||
wasmparser = "0.85.0"
|
wasmparser = "0.86.0"
|
||||||
anyhow = "1.0.19"
|
anyhow = "1.0.19"
|
||||||
region = "2.2.0"
|
region = "2.2.0"
|
||||||
libc = "0.2"
|
libc = "0.2"
|
||||||
|
|||||||
@@ -5,7 +5,7 @@ use anyhow::{Context, Result};
|
|||||||
use std::mem::MaybeUninit;
|
use std::mem::MaybeUninit;
|
||||||
use std::ptr::NonNull;
|
use std::ptr::NonNull;
|
||||||
use std::sync::Arc;
|
use std::sync::Arc;
|
||||||
use wasmtime_environ::component::{CanonicalOptions, ComponentTypes, CoreExport, FuncTypeIndex};
|
use wasmtime_environ::component::{CanonicalOptions, ComponentTypes, CoreExport, TypeFuncIndex};
|
||||||
use wasmtime_environ::FuncIndex;
|
use wasmtime_environ::FuncIndex;
|
||||||
use wasmtime_runtime::{Export, ExportFunction, VMTrampoline};
|
use wasmtime_runtime::{Export, ExportFunction, VMTrampoline};
|
||||||
|
|
||||||
@@ -78,7 +78,7 @@ pub struct Func(Stored<FuncData>);
|
|||||||
pub struct FuncData {
|
pub struct FuncData {
|
||||||
trampoline: VMTrampoline,
|
trampoline: VMTrampoline,
|
||||||
export: ExportFunction,
|
export: ExportFunction,
|
||||||
ty: FuncTypeIndex,
|
ty: TypeFuncIndex,
|
||||||
types: Arc<ComponentTypes>,
|
types: Arc<ComponentTypes>,
|
||||||
options: Options,
|
options: Options,
|
||||||
instance: Instance,
|
instance: Instance,
|
||||||
@@ -89,7 +89,7 @@ impl Func {
|
|||||||
store: &mut StoreOpaque,
|
store: &mut StoreOpaque,
|
||||||
instance: &Instance,
|
instance: &Instance,
|
||||||
data: &InstanceData,
|
data: &InstanceData,
|
||||||
ty: FuncTypeIndex,
|
ty: TypeFuncIndex,
|
||||||
func: &CoreExport<FuncIndex>,
|
func: &CoreExport<FuncIndex>,
|
||||||
options: &CanonicalOptions,
|
options: &CanonicalOptions,
|
||||||
) -> Func {
|
) -> Func {
|
||||||
|
|||||||
@@ -7,7 +7,7 @@ use std::mem::MaybeUninit;
|
|||||||
use std::panic::{self, AssertUnwindSafe};
|
use std::panic::{self, AssertUnwindSafe};
|
||||||
use std::ptr::NonNull;
|
use std::ptr::NonNull;
|
||||||
use std::sync::Arc;
|
use std::sync::Arc;
|
||||||
use wasmtime_environ::component::{ComponentTypes, FuncTypeIndex, StringEncoding};
|
use wasmtime_environ::component::{ComponentTypes, StringEncoding, TypeFuncIndex};
|
||||||
use wasmtime_runtime::component::{VMComponentContext, VMLowering, VMLoweringCallee};
|
use wasmtime_runtime::component::{VMComponentContext, VMLowering, VMLoweringCallee};
|
||||||
use wasmtime_runtime::{VMCallerCheckedAnyfunc, VMMemoryDefinition, VMOpaqueContext};
|
use wasmtime_runtime::{VMCallerCheckedAnyfunc, VMMemoryDefinition, VMOpaqueContext};
|
||||||
|
|
||||||
@@ -38,7 +38,7 @@ pub trait IntoComponentFunc<T, Params, Return> {
|
|||||||
|
|
||||||
pub struct HostFunc {
|
pub struct HostFunc {
|
||||||
entrypoint: VMLoweringCallee,
|
entrypoint: VMLoweringCallee,
|
||||||
typecheck: fn(FuncTypeIndex, &ComponentTypes) -> Result<()>,
|
typecheck: fn(TypeFuncIndex, &ComponentTypes) -> Result<()>,
|
||||||
func: Box<dyn Any + Send + Sync>,
|
func: Box<dyn Any + Send + Sync>,
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -56,7 +56,7 @@ impl HostFunc {
|
|||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn typecheck(&self, ty: FuncTypeIndex, types: &ComponentTypes) -> Result<()> {
|
pub fn typecheck(&self, ty: TypeFuncIndex, types: &ComponentTypes) -> Result<()> {
|
||||||
(self.typecheck)(ty, types)
|
(self.typecheck)(ty, types)
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -69,7 +69,7 @@ impl HostFunc {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn typecheck<P, R>(ty: FuncTypeIndex, types: &ComponentTypes) -> Result<()>
|
fn typecheck<P, R>(ty: TypeFuncIndex, types: &ComponentTypes) -> Result<()>
|
||||||
where
|
where
|
||||||
P: ComponentParams + Lift,
|
P: ComponentParams + Lift,
|
||||||
R: Lower,
|
R: Lower,
|
||||||
|
|||||||
@@ -4,7 +4,7 @@ use crate::types::matching;
|
|||||||
use crate::Module;
|
use crate::Module;
|
||||||
use anyhow::{anyhow, bail, Context, Result};
|
use anyhow::{anyhow, bail, Context, Result};
|
||||||
use wasmtime_environ::component::{
|
use wasmtime_environ::component::{
|
||||||
ComponentInstanceType, ComponentTypes, FuncTypeIndex, ModuleType, TypeDef,
|
ComponentTypes, TypeComponentInstance, TypeDef, TypeFuncIndex, TypeModule,
|
||||||
};
|
};
|
||||||
|
|
||||||
pub struct TypeChecker<'a> {
|
pub struct TypeChecker<'a> {
|
||||||
@@ -23,16 +23,19 @@ impl TypeChecker<'_> {
|
|||||||
Definition::Instance(actual) => self.instance(&self.types[t], actual),
|
Definition::Instance(actual) => self.instance(&self.types[t], actual),
|
||||||
_ => bail!("expected instance found {}", actual.desc()),
|
_ => bail!("expected instance found {}", actual.desc()),
|
||||||
},
|
},
|
||||||
TypeDef::Func(t) => match actual {
|
TypeDef::ComponentFunc(t) => match actual {
|
||||||
Definition::Func(actual) => self.func(t, actual),
|
Definition::Func(actual) => self.func(t, actual),
|
||||||
_ => bail!("expected func found {}", actual.desc()),
|
_ => bail!("expected func found {}", actual.desc()),
|
||||||
},
|
},
|
||||||
TypeDef::Component(_) => bail!("expected component found {}", actual.desc()),
|
TypeDef::Component(_) => bail!("expected component found {}", actual.desc()),
|
||||||
TypeDef::Interface(_) => bail!("expected type found {}", actual.desc()),
|
TypeDef::Interface(_) => bail!("expected type found {}", actual.desc()),
|
||||||
|
|
||||||
|
// not possible for valid components to import
|
||||||
|
TypeDef::CoreFunc(_) => unreachable!(),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn module(&self, expected: &ModuleType, actual: &Module) -> Result<()> {
|
fn module(&self, expected: &TypeModule, actual: &Module) -> Result<()> {
|
||||||
let actual_types = actual.types();
|
let actual_types = actual.types();
|
||||||
let actual = actual.env_module();
|
let actual = actual.env_module();
|
||||||
|
|
||||||
@@ -63,7 +66,7 @@ impl TypeChecker<'_> {
|
|||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
fn instance(&self, expected: &ComponentInstanceType, actual: &NameMap) -> Result<()> {
|
fn instance(&self, expected: &TypeComponentInstance, actual: &NameMap) -> Result<()> {
|
||||||
// Like modules, every export in the expected type must be present in
|
// Like modules, every export in the expected type must be present in
|
||||||
// the actual type. It's ok, though, to have extra exports in the actual
|
// the actual type. It's ok, though, to have extra exports in the actual
|
||||||
// type.
|
// type.
|
||||||
@@ -79,7 +82,7 @@ impl TypeChecker<'_> {
|
|||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
fn func(&self, expected: FuncTypeIndex, actual: &HostFunc) -> Result<()> {
|
fn func(&self, expected: TypeFuncIndex, actual: &HostFunc) -> Result<()> {
|
||||||
actual.typecheck(expected, self.types)
|
actual.typecheck(expected, self.types)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -12,7 +12,7 @@ edition = "2021"
|
|||||||
[dependencies]
|
[dependencies]
|
||||||
anyhow = "1.0.19"
|
anyhow = "1.0.19"
|
||||||
wasmtime = { path = "../wasmtime", version = "0.39.0", default-features = false, features = ['cranelift'] }
|
wasmtime = { path = "../wasmtime", version = "0.39.0", default-features = false, features = ['cranelift'] }
|
||||||
wast = "41.0.0"
|
wast = "42.0.0"
|
||||||
|
|
||||||
[badges]
|
[badges]
|
||||||
maintenance = { status = "actively-developed" }
|
maintenance = { status = "actively-developed" }
|
||||||
|
|||||||
@@ -8,7 +8,7 @@ mod import;
|
|||||||
// A simple bump allocator which can be used with modules
|
// A simple bump allocator which can be used with modules
|
||||||
const REALLOC_AND_FREE: &str = r#"
|
const REALLOC_AND_FREE: &str = r#"
|
||||||
(global $last (mut i32) (i32.const 8))
|
(global $last (mut i32) (i32.const 8))
|
||||||
(func $realloc (export "canonical_abi_realloc")
|
(func $realloc (export "realloc")
|
||||||
(param $old_ptr i32)
|
(param $old_ptr i32)
|
||||||
(param $old_size i32)
|
(param $old_size i32)
|
||||||
(param $align i32)
|
(param $align i32)
|
||||||
@@ -62,8 +62,6 @@ const REALLOC_AND_FREE: &str = r#"
|
|||||||
(global.get $last)
|
(global.get $last)
|
||||||
(local.get $new_size)))
|
(local.get $new_size)))
|
||||||
)
|
)
|
||||||
|
|
||||||
(func (export "canonical_abi_free") (param i32 i32 i32))
|
|
||||||
"#;
|
"#;
|
||||||
|
|
||||||
fn engine() -> Engine {
|
fn engine() -> Engine {
|
||||||
@@ -83,7 +81,7 @@ fn components_importing_modules() -> Result<()> {
|
|||||||
&engine,
|
&engine,
|
||||||
r#"
|
r#"
|
||||||
(component
|
(component
|
||||||
(import "" (module))
|
(import "" (core module))
|
||||||
)
|
)
|
||||||
"#,
|
"#,
|
||||||
)?;
|
)?;
|
||||||
@@ -92,7 +90,7 @@ fn components_importing_modules() -> Result<()> {
|
|||||||
&engine,
|
&engine,
|
||||||
r#"
|
r#"
|
||||||
(component
|
(component
|
||||||
(import "" (module $m1
|
(import "" (core module $m1
|
||||||
(import "" "" (func))
|
(import "" "" (func))
|
||||||
(import "" "x" (global i32))
|
(import "" "x" (global i32))
|
||||||
|
|
||||||
@@ -102,21 +100,21 @@ fn components_importing_modules() -> Result<()> {
|
|||||||
(export "d" (global i64))
|
(export "d" (global i64))
|
||||||
))
|
))
|
||||||
|
|
||||||
(module $m2
|
(core module $m2
|
||||||
(func (export ""))
|
(func (export ""))
|
||||||
(global (export "x") i32 i32.const 0)
|
(global (export "x") i32 i32.const 0)
|
||||||
)
|
)
|
||||||
(instance $i2 (instantiate (module $m2)))
|
(core instance $i2 (instantiate (module $m2)))
|
||||||
(instance $i1 (instantiate (module $m1) (with "" (instance $i2))))
|
(core instance $i1 (instantiate (module $m1) (with "" (instance $i2))))
|
||||||
|
|
||||||
(module $m3
|
(core module $m3
|
||||||
(import "mod" "1" (memory 1))
|
(import "mod" "1" (memory 1))
|
||||||
(import "mod" "2" (table 1 funcref))
|
(import "mod" "2" (table 1 funcref))
|
||||||
(import "mod" "3" (global i64))
|
(import "mod" "3" (global i64))
|
||||||
(import "mod" "4" (func (result f32)))
|
(import "mod" "4" (func (result f32)))
|
||||||
)
|
)
|
||||||
|
|
||||||
(instance $i3 (instantiate (module $m3)
|
(core instance $i3 (instantiate (module $m3)
|
||||||
(with "mod" (instance
|
(with "mod" (instance
|
||||||
(export "1" (memory $i1 "b"))
|
(export "1" (memory $i1 "b"))
|
||||||
(export "2" (table $i1 "a"))
|
(export "2" (table $i1 "a"))
|
||||||
|
|||||||
@@ -12,16 +12,16 @@ const CANON_64BIT_NAN: u64 = 0b0111111111111000000000000000000000000000000000000
|
|||||||
fn thunks() -> Result<()> {
|
fn thunks() -> Result<()> {
|
||||||
let component = r#"
|
let component = r#"
|
||||||
(component
|
(component
|
||||||
(module $m
|
(core module $m
|
||||||
(func (export "thunk"))
|
(func (export "thunk"))
|
||||||
(func (export "thunk-trap") unreachable)
|
(func (export "thunk-trap") unreachable)
|
||||||
)
|
)
|
||||||
(instance $i (instantiate (module $m)))
|
(core instance $i (instantiate $m))
|
||||||
(func (export "thunk")
|
(func (export "thunk")
|
||||||
(canon.lift (func) (func $i "thunk"))
|
(canon lift (core func $i "thunk"))
|
||||||
)
|
)
|
||||||
(func (export "thunk-trap")
|
(func (export "thunk-trap")
|
||||||
(canon.lift (func) (func $i "thunk-trap"))
|
(canon lift (core func $i "thunk-trap"))
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
"#;
|
"#;
|
||||||
@@ -46,42 +46,40 @@ fn thunks() -> Result<()> {
|
|||||||
fn typecheck() -> Result<()> {
|
fn typecheck() -> Result<()> {
|
||||||
let component = r#"
|
let component = r#"
|
||||||
(component
|
(component
|
||||||
(module $m
|
(core module $m
|
||||||
(func (export "thunk"))
|
(func (export "thunk"))
|
||||||
(func (export "take-string") (param i32 i32))
|
(func (export "take-string") (param i32 i32))
|
||||||
(func (export "two-args") (param i32 i32 i32))
|
(func (export "two-args") (param i32 i32 i32))
|
||||||
(func (export "ret-one") (result i32) unreachable)
|
(func (export "ret-one") (result i32) unreachable)
|
||||||
|
|
||||||
(memory (export "memory") 1)
|
(memory (export "memory") 1)
|
||||||
(func (export "canonical_abi_realloc") (param i32 i32 i32 i32) (result i32)
|
(func (export "realloc") (param i32 i32 i32 i32) (result i32)
|
||||||
unreachable)
|
|
||||||
(func (export "canonical_abi_free") (param i32 i32 i32)
|
|
||||||
unreachable)
|
unreachable)
|
||||||
)
|
)
|
||||||
(instance $i (instantiate (module $m)))
|
(core instance $i (instantiate (module $m)))
|
||||||
(func (export "thunk")
|
(func (export "thunk")
|
||||||
(canon.lift (func) (func $i "thunk"))
|
(canon lift (core func $i "thunk"))
|
||||||
)
|
)
|
||||||
(func (export "tuple-thunk")
|
(func (export "tuple-thunk") (param (tuple)) (result (tuple))
|
||||||
(canon.lift (func (param (tuple)) (result (tuple))) (func $i "thunk"))
|
(canon lift (core func $i "thunk"))
|
||||||
)
|
)
|
||||||
(func (export "take-string")
|
(func (export "take-string") (param string)
|
||||||
(canon.lift (func (param string)) (into $i) (func $i "take-string"))
|
(canon lift (core func $i "take-string") (memory $i "memory") (realloc (func $i "realloc")))
|
||||||
)
|
)
|
||||||
(func (export "take-two-args")
|
(func (export "take-two-args") (param s32) (param (list u8))
|
||||||
(canon.lift (func (param s32) (param (list u8))) (into $i) (func $i "two-args"))
|
(canon lift (core func $i "two-args") (memory $i "memory") (realloc (func $i "realloc")))
|
||||||
)
|
)
|
||||||
(func (export "ret-tuple")
|
(func (export "ret-tuple") (result (tuple u8 s8))
|
||||||
(canon.lift (func (result (tuple u8 s8))) (into $i) (func $i "ret-one"))
|
(canon lift (core func $i "ret-one") (memory $i "memory") (realloc (func $i "realloc")))
|
||||||
)
|
)
|
||||||
(func (export "ret-tuple1")
|
(func (export "ret-tuple1") (result (tuple u32))
|
||||||
(canon.lift (func (result (tuple u32))) (into $i) (func $i "ret-one"))
|
(canon lift (core func $i "ret-one") (memory $i "memory") (realloc (func $i "realloc")))
|
||||||
)
|
)
|
||||||
(func (export "ret-string")
|
(func (export "ret-string") (result string)
|
||||||
(canon.lift (func (result string)) (into $i) (func $i "ret-one"))
|
(canon lift (core func $i "ret-one") (memory $i "memory") (realloc (func $i "realloc")))
|
||||||
)
|
)
|
||||||
(func (export "ret-list-u8")
|
(func (export "ret-list-u8") (result (list u8))
|
||||||
(canon.lift (func (result (list u8))) (into $i) (func $i "ret-one"))
|
(canon lift (core func $i "ret-one") (memory $i "memory") (realloc (func $i "realloc")))
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
"#;
|
"#;
|
||||||
@@ -129,7 +127,7 @@ fn typecheck() -> Result<()> {
|
|||||||
fn integers() -> Result<()> {
|
fn integers() -> Result<()> {
|
||||||
let component = r#"
|
let component = r#"
|
||||||
(component
|
(component
|
||||||
(module $m
|
(core module $m
|
||||||
(func (export "take-i32-100") (param i32)
|
(func (export "take-i32-100") (param i32)
|
||||||
local.get 0
|
local.get 0
|
||||||
i32.const 100
|
i32.const 100
|
||||||
@@ -150,40 +148,40 @@ fn integers() -> Result<()> {
|
|||||||
(func (export "ret-i64-minus-1") (result i64) i64.const -1)
|
(func (export "ret-i64-minus-1") (result i64) i64.const -1)
|
||||||
(func (export "ret-i32-100000") (result i32) i32.const 100000)
|
(func (export "ret-i32-100000") (result i32) i32.const 100000)
|
||||||
)
|
)
|
||||||
(instance $i (instantiate (module $m)))
|
(core instance $i (instantiate (module $m)))
|
||||||
(func (export "take-u8") (canon.lift (func (param u8)) (func $i "take-i32-100")))
|
(func (export "take-u8") (param u8) (canon lift (core func $i "take-i32-100")))
|
||||||
(func (export "take-s8") (canon.lift (func (param s8)) (func $i "take-i32-100")))
|
(func (export "take-s8") (param s8) (canon lift (core func $i "take-i32-100")))
|
||||||
(func (export "take-u16") (canon.lift (func (param u16)) (func $i "take-i32-100")))
|
(func (export "take-u16") (param u16) (canon lift (core func $i "take-i32-100")))
|
||||||
(func (export "take-s16") (canon.lift (func (param s16)) (func $i "take-i32-100")))
|
(func (export "take-s16") (param s16) (canon lift (core func $i "take-i32-100")))
|
||||||
(func (export "take-u32") (canon.lift (func (param u32)) (func $i "take-i32-100")))
|
(func (export "take-u32") (param u32) (canon lift (core func $i "take-i32-100")))
|
||||||
(func (export "take-s32") (canon.lift (func (param s32)) (func $i "take-i32-100")))
|
(func (export "take-s32") (param s32) (canon lift (core func $i "take-i32-100")))
|
||||||
(func (export "take-u64") (canon.lift (func (param u64)) (func $i "take-i64-100")))
|
(func (export "take-u64") (param u64) (canon lift (core func $i "take-i64-100")))
|
||||||
(func (export "take-s64") (canon.lift (func (param s64)) (func $i "take-i64-100")))
|
(func (export "take-s64") (param s64) (canon lift (core func $i "take-i64-100")))
|
||||||
|
|
||||||
(func (export "ret-u8") (canon.lift (func (result u8)) (func $i "ret-i32-0")))
|
(func (export "ret-u8") (result u8) (canon lift (core func $i "ret-i32-0")))
|
||||||
(func (export "ret-s8") (canon.lift (func (result s8)) (func $i "ret-i32-0")))
|
(func (export "ret-s8") (result s8) (canon lift (core func $i "ret-i32-0")))
|
||||||
(func (export "ret-u16") (canon.lift (func (result u16)) (func $i "ret-i32-0")))
|
(func (export "ret-u16") (result u16) (canon lift (core func $i "ret-i32-0")))
|
||||||
(func (export "ret-s16") (canon.lift (func (result s16)) (func $i "ret-i32-0")))
|
(func (export "ret-s16") (result s16) (canon lift (core func $i "ret-i32-0")))
|
||||||
(func (export "ret-u32") (canon.lift (func (result u32)) (func $i "ret-i32-0")))
|
(func (export "ret-u32") (result u32) (canon lift (core func $i "ret-i32-0")))
|
||||||
(func (export "ret-s32") (canon.lift (func (result s32)) (func $i "ret-i32-0")))
|
(func (export "ret-s32") (result s32) (canon lift (core func $i "ret-i32-0")))
|
||||||
(func (export "ret-u64") (canon.lift (func (result u64)) (func $i "ret-i64-0")))
|
(func (export "ret-u64") (result u64) (canon lift (core func $i "ret-i64-0")))
|
||||||
(func (export "ret-s64") (canon.lift (func (result s64)) (func $i "ret-i64-0")))
|
(func (export "ret-s64") (result s64) (canon lift (core func $i "ret-i64-0")))
|
||||||
|
|
||||||
(func (export "retm1-u8") (canon.lift (func (result u8)) (func $i "ret-i32-minus-1")))
|
(func (export "retm1-u8") (result u8) (canon lift (core func $i "ret-i32-minus-1")))
|
||||||
(func (export "retm1-s8") (canon.lift (func (result s8)) (func $i "ret-i32-minus-1")))
|
(func (export "retm1-s8") (result s8) (canon lift (core func $i "ret-i32-minus-1")))
|
||||||
(func (export "retm1-u16") (canon.lift (func (result u16)) (func $i "ret-i32-minus-1")))
|
(func (export "retm1-u16") (result u16) (canon lift (core func $i "ret-i32-minus-1")))
|
||||||
(func (export "retm1-s16") (canon.lift (func (result s16)) (func $i "ret-i32-minus-1")))
|
(func (export "retm1-s16") (result s16) (canon lift (core func $i "ret-i32-minus-1")))
|
||||||
(func (export "retm1-u32") (canon.lift (func (result u32)) (func $i "ret-i32-minus-1")))
|
(func (export "retm1-u32") (result u32) (canon lift (core func $i "ret-i32-minus-1")))
|
||||||
(func (export "retm1-s32") (canon.lift (func (result s32)) (func $i "ret-i32-minus-1")))
|
(func (export "retm1-s32") (result s32) (canon lift (core func $i "ret-i32-minus-1")))
|
||||||
(func (export "retm1-u64") (canon.lift (func (result u64)) (func $i "ret-i64-minus-1")))
|
(func (export "retm1-u64") (result u64) (canon lift (core func $i "ret-i64-minus-1")))
|
||||||
(func (export "retm1-s64") (canon.lift (func (result s64)) (func $i "ret-i64-minus-1")))
|
(func (export "retm1-s64") (result s64) (canon lift (core func $i "ret-i64-minus-1")))
|
||||||
|
|
||||||
(func (export "retbig-u8") (canon.lift (func (result u8)) (func $i "ret-i32-100000")))
|
(func (export "retbig-u8") (result u8) (canon lift (core func $i "ret-i32-100000")))
|
||||||
(func (export "retbig-s8") (canon.lift (func (result s8)) (func $i "ret-i32-100000")))
|
(func (export "retbig-s8") (result s8) (canon lift (core func $i "ret-i32-100000")))
|
||||||
(func (export "retbig-u16") (canon.lift (func (result u16)) (func $i "ret-i32-100000")))
|
(func (export "retbig-u16") (result u16) (canon lift (core func $i "ret-i32-100000")))
|
||||||
(func (export "retbig-s16") (canon.lift (func (result s16)) (func $i "ret-i32-100000")))
|
(func (export "retbig-s16") (result s16) (canon lift (core func $i "ret-i32-100000")))
|
||||||
(func (export "retbig-u32") (canon.lift (func (result u32)) (func $i "ret-i32-100000")))
|
(func (export "retbig-u32") (result u32) (canon lift (core func $i "ret-i32-100000")))
|
||||||
(func (export "retbig-s32") (canon.lift (func (result s32)) (func $i "ret-i32-100000")))
|
(func (export "retbig-s32") (result s32) (canon lift (core func $i "ret-i32-100000")))
|
||||||
)
|
)
|
||||||
"#;
|
"#;
|
||||||
|
|
||||||
@@ -406,7 +404,7 @@ fn integers() -> Result<()> {
|
|||||||
fn type_layers() -> Result<()> {
|
fn type_layers() -> Result<()> {
|
||||||
let component = r#"
|
let component = r#"
|
||||||
(component
|
(component
|
||||||
(module $m
|
(core module $m
|
||||||
(func (export "take-i32-100") (param i32)
|
(func (export "take-i32-100") (param i32)
|
||||||
local.get 0
|
local.get 0
|
||||||
i32.const 2
|
i32.const 2
|
||||||
@@ -415,8 +413,8 @@ fn type_layers() -> Result<()> {
|
|||||||
unreachable
|
unreachable
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
(instance $i (instantiate (module $m)))
|
(core instance $i (instantiate $m))
|
||||||
(func (export "take-u32") (canon.lift (func (param u32)) (func $i "take-i32-100")))
|
(func (export "take-u32") (param u32) (canon lift (core func $i "take-i32-100")))
|
||||||
)
|
)
|
||||||
"#;
|
"#;
|
||||||
|
|
||||||
@@ -448,7 +446,7 @@ fn type_layers() -> Result<()> {
|
|||||||
fn floats() -> Result<()> {
|
fn floats() -> Result<()> {
|
||||||
let component = r#"
|
let component = r#"
|
||||||
(component
|
(component
|
||||||
(module $m
|
(core module $m
|
||||||
(func (export "i32.reinterpret_f32") (param f32) (result i32)
|
(func (export "i32.reinterpret_f32") (param f32) (result i32)
|
||||||
local.get 0
|
local.get 0
|
||||||
i32.reinterpret_f32
|
i32.reinterpret_f32
|
||||||
@@ -466,19 +464,19 @@ fn floats() -> Result<()> {
|
|||||||
f64.reinterpret_i64
|
f64.reinterpret_i64
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
(instance $i (instantiate (module $m)))
|
(core instance $i (instantiate $m))
|
||||||
|
|
||||||
(func (export "f32-to-u32")
|
(func (export "f32-to-u32") (param float32) (result u32)
|
||||||
(canon.lift (func (param float32) (result u32)) (func $i "i32.reinterpret_f32"))
|
(canon lift (core func $i "i32.reinterpret_f32"))
|
||||||
)
|
)
|
||||||
(func (export "f64-to-u64")
|
(func (export "f64-to-u64") (param float64) (result u64)
|
||||||
(canon.lift (func (param float64) (result u64)) (func $i "i64.reinterpret_f64"))
|
(canon lift (core func $i "i64.reinterpret_f64"))
|
||||||
)
|
)
|
||||||
(func (export "u32-to-f32")
|
(func (export "u32-to-f32") (param u32) (result float32)
|
||||||
(canon.lift (func (param u32) (result float32)) (func $i "f32.reinterpret_i32"))
|
(canon lift (core func $i "f32.reinterpret_i32"))
|
||||||
)
|
)
|
||||||
(func (export "u64-to-f64")
|
(func (export "u64-to-f64") (param u64) (result float64)
|
||||||
(canon.lift (func (param u64) (result float64)) (func $i "f64.reinterpret_i64"))
|
(canon lift (core func $i "f64.reinterpret_i64"))
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
"#;
|
"#;
|
||||||
@@ -526,16 +524,16 @@ fn floats() -> Result<()> {
|
|||||||
fn bools() -> Result<()> {
|
fn bools() -> Result<()> {
|
||||||
let component = r#"
|
let component = r#"
|
||||||
(component
|
(component
|
||||||
(module $m
|
(core module $m
|
||||||
(func (export "pass") (param i32) (result i32) local.get 0)
|
(func (export "pass") (param i32) (result i32) local.get 0)
|
||||||
)
|
)
|
||||||
(instance $i (instantiate (module $m)))
|
(core instance $i (instantiate $m))
|
||||||
|
|
||||||
(func (export "u32-to-bool")
|
(func (export "u32-to-bool") (param u32) (result bool)
|
||||||
(canon.lift (func (param u32) (result bool)) (func $i "pass"))
|
(canon lift (core func $i "pass"))
|
||||||
)
|
)
|
||||||
(func (export "bool-to-u32")
|
(func (export "bool-to-u32") (param bool) (result u32)
|
||||||
(canon.lift (func (param bool) (result u32)) (func $i "pass"))
|
(canon lift (core func $i "pass"))
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
"#;
|
"#;
|
||||||
@@ -560,16 +558,16 @@ fn bools() -> Result<()> {
|
|||||||
fn chars() -> Result<()> {
|
fn chars() -> Result<()> {
|
||||||
let component = r#"
|
let component = r#"
|
||||||
(component
|
(component
|
||||||
(module $m
|
(core module $m
|
||||||
(func (export "pass") (param i32) (result i32) local.get 0)
|
(func (export "pass") (param i32) (result i32) local.get 0)
|
||||||
)
|
)
|
||||||
(instance $i (instantiate (module $m)))
|
(core instance $i (instantiate $m))
|
||||||
|
|
||||||
(func (export "u32-to-char")
|
(func (export "u32-to-char") (param u32) (result char)
|
||||||
(canon.lift (func (param u32) (result char)) (func $i "pass"))
|
(canon lift (core func $i "pass"))
|
||||||
)
|
)
|
||||||
(func (export "char-to-u32")
|
(func (export "char-to-u32") (param char) (result u32)
|
||||||
(canon.lift (func (param char) (result u32)) (func $i "pass"))
|
(canon lift (core func $i "pass"))
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
"#;
|
"#;
|
||||||
@@ -609,7 +607,7 @@ fn chars() -> Result<()> {
|
|||||||
fn tuple_result() -> Result<()> {
|
fn tuple_result() -> Result<()> {
|
||||||
let component = r#"
|
let component = r#"
|
||||||
(component
|
(component
|
||||||
(module $m
|
(core module $m
|
||||||
(memory (export "memory") 1)
|
(memory (export "memory") 1)
|
||||||
(func (export "foo") (param i32 i32 f32 f64) (result i32)
|
(func (export "foo") (param i32 i32 f32 f64) (result i32)
|
||||||
(local $base i32)
|
(local $base i32)
|
||||||
@@ -624,24 +622,16 @@ fn tuple_result() -> Result<()> {
|
|||||||
(func (export "invalid") (result i32)
|
(func (export "invalid") (result i32)
|
||||||
i32.const -8
|
i32.const -8
|
||||||
)
|
)
|
||||||
|
|
||||||
(func (export "canonical_abi_realloc") (param i32 i32 i32 i32) (result i32)
|
|
||||||
unreachable)
|
|
||||||
(func (export "canonical_abi_free") (param i32 i32 i32)
|
|
||||||
unreachable)
|
|
||||||
)
|
)
|
||||||
(instance $i (instantiate (module $m)))
|
(core instance $i (instantiate $m))
|
||||||
|
|
||||||
(type $result (tuple s8 u16 float32 float64))
|
(type $result (tuple s8 u16 float32 float64))
|
||||||
(func (export "tuple")
|
(func (export "tuple")
|
||||||
(canon.lift
|
(param s8) (param u16) (param float32) (param float64) (result $result)
|
||||||
(func (param s8) (param u16) (param float32) (param float64) (result $result))
|
(canon lift (core func $i "foo") (memory $i "memory"))
|
||||||
(into $i)
|
|
||||||
(func $i "foo")
|
|
||||||
)
|
)
|
||||||
)
|
(func (export "invalid") (result $result)
|
||||||
(func (export "invalid")
|
(canon lift (core func $i "invalid") (memory $i "memory"))
|
||||||
(canon.lift (func (result $result)) (into $i) (func $i "invalid"))
|
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
"#;
|
"#;
|
||||||
@@ -673,7 +663,7 @@ fn tuple_result() -> Result<()> {
|
|||||||
fn strings() -> Result<()> {
|
fn strings() -> Result<()> {
|
||||||
let component = format!(
|
let component = format!(
|
||||||
r#"(component
|
r#"(component
|
||||||
(module $m
|
(core module $m
|
||||||
(memory (export "memory") 1)
|
(memory (export "memory") 1)
|
||||||
(func (export "roundtrip") (param i32 i32) (result i32)
|
(func (export "roundtrip") (param i32 i32) (result i32)
|
||||||
(local $base i32)
|
(local $base i32)
|
||||||
@@ -694,36 +684,36 @@ fn strings() -> Result<()> {
|
|||||||
|
|
||||||
{REALLOC_AND_FREE}
|
{REALLOC_AND_FREE}
|
||||||
)
|
)
|
||||||
(instance $i (instantiate (module $m)))
|
(core instance $i (instantiate $m))
|
||||||
|
|
||||||
(func (export "list8-to-str")
|
(func (export "list8-to-str") (param (list u8)) (result string)
|
||||||
(canon.lift
|
(canon lift
|
||||||
(func (param (list u8)) (result string))
|
(core func $i "roundtrip")
|
||||||
(into $i)
|
(memory $i "memory")
|
||||||
(func $i "roundtrip")
|
(realloc (func $i "realloc"))
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
(func (export "str-to-list8")
|
(func (export "str-to-list8") (param string) (result (list u8))
|
||||||
(canon.lift
|
(canon lift
|
||||||
(func (param string) (result (list u8)))
|
(core func $i "roundtrip")
|
||||||
(into $i)
|
(memory $i "memory")
|
||||||
(func $i "roundtrip")
|
(realloc (func $i "realloc"))
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
(func (export "list16-to-str")
|
(func (export "list16-to-str") (param (list u16)) (result string)
|
||||||
(canon.lift
|
(canon lift
|
||||||
(func (param (list u16)) (result string))
|
(core func $i "roundtrip")
|
||||||
string=utf16
|
string-encoding=utf16
|
||||||
(into $i)
|
(memory $i "memory")
|
||||||
(func $i "roundtrip")
|
(realloc (func $i "realloc"))
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
(func (export "str-to-list16")
|
(func (export "str-to-list16") (param string) (result (list u16))
|
||||||
(canon.lift
|
(canon lift
|
||||||
(func (param string) (result (list u16)))
|
(core func $i "roundtrip")
|
||||||
string=utf16
|
string-encoding=utf16
|
||||||
(into $i)
|
(memory $i "memory")
|
||||||
(func $i "roundtrip")
|
(realloc (func $i "realloc"))
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
)"#
|
)"#
|
||||||
@@ -792,7 +782,7 @@ fn strings() -> Result<()> {
|
|||||||
fn many_parameters() -> Result<()> {
|
fn many_parameters() -> Result<()> {
|
||||||
let component = format!(
|
let component = format!(
|
||||||
r#"(component
|
r#"(component
|
||||||
(module $m
|
(core module $m
|
||||||
(memory (export "memory") 1)
|
(memory (export "memory") 1)
|
||||||
(func (export "foo") (param i32) (result i32)
|
(func (export "foo") (param i32) (result i32)
|
||||||
(local $base i32)
|
(local $base i32)
|
||||||
@@ -826,7 +816,7 @@ fn many_parameters() -> Result<()> {
|
|||||||
|
|
||||||
{REALLOC_AND_FREE}
|
{REALLOC_AND_FREE}
|
||||||
)
|
)
|
||||||
(instance $i (instantiate (module $m)))
|
(core instance $i (instantiate $m))
|
||||||
|
|
||||||
(type $result (tuple (list u8) u32))
|
(type $result (tuple (list u8) u32))
|
||||||
(type $t (func
|
(type $t (func
|
||||||
@@ -847,8 +837,12 @@ fn many_parameters() -> Result<()> {
|
|||||||
|
|
||||||
(result $result)
|
(result $result)
|
||||||
))
|
))
|
||||||
(func (export "many-param")
|
(func (export "many-param") (type $t)
|
||||||
(canon.lift (type $t) (into $i) (func $i "foo"))
|
(canon lift
|
||||||
|
(core func $i "foo")
|
||||||
|
(memory $i "memory")
|
||||||
|
(realloc (func $i "realloc"))
|
||||||
|
)
|
||||||
)
|
)
|
||||||
)"#
|
)"#
|
||||||
);
|
);
|
||||||
@@ -950,23 +944,21 @@ fn some_traps() -> Result<()> {
|
|||||||
let middle_of_memory = (i32::MAX / 2) & (!0xff);
|
let middle_of_memory = (i32::MAX / 2) & (!0xff);
|
||||||
let component = format!(
|
let component = format!(
|
||||||
r#"(component
|
r#"(component
|
||||||
(module $m
|
(core module $m
|
||||||
(memory (export "memory") 1)
|
(memory (export "memory") 1)
|
||||||
(func (export "take-many") (param i32))
|
(func (export "take-many") (param i32))
|
||||||
(func (export "take-list") (param i32 i32))
|
(func (export "take-list") (param i32 i32))
|
||||||
|
|
||||||
(func (export "canonical_abi_realloc") (param i32 i32 i32 i32) (result i32)
|
(func (export "realloc") (param i32 i32 i32 i32) (result i32)
|
||||||
unreachable)
|
|
||||||
(func (export "canonical_abi_free") (param i32 i32 i32)
|
|
||||||
unreachable)
|
unreachable)
|
||||||
)
|
)
|
||||||
(instance $i (instantiate (module $m)))
|
(core instance $i (instantiate $m))
|
||||||
|
|
||||||
(func (export "take-list-unreachable")
|
(func (export "take-list-unreachable") (param (list u8))
|
||||||
(canon.lift (func (param (list u8))) (into $i) (func $i "take-list"))
|
(canon lift (core func $i "take-list") (memory $i "memory") (realloc (func $i "realloc")))
|
||||||
)
|
)
|
||||||
(func (export "take-string-unreachable")
|
(func (export "take-string-unreachable") (param string)
|
||||||
(canon.lift (func (param string)) (into $i) (func $i "take-list"))
|
(canon lift (core func $i "take-list") (memory $i "memory") (realloc (func $i "realloc")))
|
||||||
)
|
)
|
||||||
|
|
||||||
(type $t (func
|
(type $t (func
|
||||||
@@ -981,60 +973,56 @@ fn some_traps() -> Result<()> {
|
|||||||
(param string)
|
(param string)
|
||||||
(param string)
|
(param string)
|
||||||
))
|
))
|
||||||
(func (export "take-many-unreachable")
|
(func (export "take-many-unreachable") (type $t)
|
||||||
(canon.lift (type $t) (into $i) (func $i "take-many"))
|
(canon lift (core func $i "take-many") (memory $i "memory") (realloc (func $i "realloc")))
|
||||||
)
|
)
|
||||||
|
|
||||||
(module $m2
|
(core module $m2
|
||||||
(memory (export "memory") 1)
|
(memory (export "memory") 1)
|
||||||
(func (export "take-many") (param i32))
|
(func (export "take-many") (param i32))
|
||||||
(func (export "take-list") (param i32 i32))
|
(func (export "take-list") (param i32 i32))
|
||||||
|
|
||||||
(func (export "canonical_abi_realloc") (param i32 i32 i32 i32) (result i32)
|
(func (export "realloc") (param i32 i32 i32 i32) (result i32)
|
||||||
i32.const {middle_of_memory})
|
i32.const {middle_of_memory})
|
||||||
(func (export "canonical_abi_free") (param i32 i32 i32)
|
|
||||||
unreachable)
|
|
||||||
)
|
)
|
||||||
(instance $i2 (instantiate (module $m2)))
|
(core instance $i2 (instantiate $m2))
|
||||||
|
|
||||||
(func (export "take-list-base-oob")
|
(func (export "take-list-base-oob") (param (list u8))
|
||||||
(canon.lift (func (param (list u8))) (into $i2) (func $i2 "take-list"))
|
(canon lift (core func $i2 "take-list") (memory $i2 "memory") (realloc (func $i2 "realloc")))
|
||||||
)
|
)
|
||||||
(func (export "take-string-base-oob")
|
(func (export "take-string-base-oob") (param string)
|
||||||
(canon.lift (func (param string)) (into $i2) (func $i2 "take-list"))
|
(canon lift (core func $i2 "take-list") (memory $i2 "memory") (realloc (func $i2 "realloc")))
|
||||||
)
|
)
|
||||||
(func (export "take-many-base-oob")
|
(func (export "take-many-base-oob") (type $t)
|
||||||
(canon.lift (type $t) (into $i2) (func $i2 "take-many"))
|
(canon lift (core func $i2 "take-many") (memory $i2 "memory") (realloc (func $i2 "realloc")))
|
||||||
)
|
)
|
||||||
|
|
||||||
(module $m3
|
(core module $m3
|
||||||
(memory (export "memory") 1)
|
(memory (export "memory") 1)
|
||||||
(func (export "take-many") (param i32))
|
(func (export "take-many") (param i32))
|
||||||
(func (export "take-list") (param i32 i32))
|
(func (export "take-list") (param i32 i32))
|
||||||
|
|
||||||
(func (export "canonical_abi_realloc") (param i32 i32 i32 i32) (result i32)
|
(func (export "realloc") (param i32 i32 i32 i32) (result i32)
|
||||||
i32.const 65532)
|
i32.const 65532)
|
||||||
(func (export "canonical_abi_free") (param i32 i32 i32)
|
|
||||||
unreachable)
|
|
||||||
)
|
)
|
||||||
(instance $i3 (instantiate (module $m3)))
|
(core instance $i3 (instantiate $m3))
|
||||||
|
|
||||||
(func (export "take-list-end-oob")
|
(func (export "take-list-end-oob") (param (list u8))
|
||||||
(canon.lift (func (param (list u8))) (into $i3) (func $i3 "take-list"))
|
(canon lift (core func $i3 "take-list") (memory $i3 "memory") (realloc (func $i3 "realloc")))
|
||||||
)
|
)
|
||||||
(func (export "take-string-end-oob")
|
(func (export "take-string-end-oob") (param string)
|
||||||
(canon.lift (func (param string)) (into $i3) (func $i3 "take-list"))
|
(canon lift (core func $i3 "take-list") (memory $i3 "memory") (realloc (func $i3 "realloc")))
|
||||||
)
|
)
|
||||||
(func (export "take-many-end-oob")
|
(func (export "take-many-end-oob") (type $t)
|
||||||
(canon.lift (type $t) (into $i3) (func $i3 "take-many"))
|
(canon lift (core func $i3 "take-many") (memory $i3 "memory") (realloc (func $i3 "realloc")))
|
||||||
)
|
)
|
||||||
|
|
||||||
(module $m4
|
(core module $m4
|
||||||
(memory (export "memory") 1)
|
(memory (export "memory") 1)
|
||||||
(func (export "take-many") (param i32))
|
(func (export "take-many") (param i32))
|
||||||
|
|
||||||
(global $cnt (mut i32) (i32.const 0))
|
(global $cnt (mut i32) (i32.const 0))
|
||||||
(func (export "canonical_abi_realloc") (param i32 i32 i32 i32) (result i32)
|
(func (export "realloc") (param i32 i32 i32 i32) (result i32)
|
||||||
global.get $cnt
|
global.get $cnt
|
||||||
if (result i32)
|
if (result i32)
|
||||||
i32.const 100000
|
i32.const 100000
|
||||||
@@ -1044,13 +1032,11 @@ fn some_traps() -> Result<()> {
|
|||||||
i32.const 0
|
i32.const 0
|
||||||
end
|
end
|
||||||
)
|
)
|
||||||
(func (export "canonical_abi_free") (param i32 i32 i32)
|
|
||||||
unreachable)
|
|
||||||
)
|
)
|
||||||
(instance $i4 (instantiate (module $m4)))
|
(core instance $i4 (instantiate $m4))
|
||||||
|
|
||||||
(func (export "take-many-second-oob")
|
(func (export "take-many-second-oob") (type $t)
|
||||||
(canon.lift (type $t) (into $i4) (func $i4 "take-many"))
|
(canon lift (core func $i4 "take-many") (memory $i4 "memory") (realloc (func $i4 "realloc")))
|
||||||
)
|
)
|
||||||
)"#
|
)"#
|
||||||
);
|
);
|
||||||
@@ -1184,7 +1170,7 @@ fn some_traps() -> Result<()> {
|
|||||||
fn char_bool_memory() -> Result<()> {
|
fn char_bool_memory() -> Result<()> {
|
||||||
let component = format!(
|
let component = format!(
|
||||||
r#"(component
|
r#"(component
|
||||||
(module $m
|
(core module $m
|
||||||
(memory (export "memory") 1)
|
(memory (export "memory") 1)
|
||||||
(func (export "ret-tuple") (param i32 i32) (result i32)
|
(func (export "ret-tuple") (param i32 i32) (result i32)
|
||||||
(local $base i32)
|
(local $base i32)
|
||||||
@@ -1212,10 +1198,12 @@ fn char_bool_memory() -> Result<()> {
|
|||||||
|
|
||||||
{REALLOC_AND_FREE}
|
{REALLOC_AND_FREE}
|
||||||
)
|
)
|
||||||
(instance $i (instantiate (module $m)))
|
(core instance $i (instantiate $m))
|
||||||
|
|
||||||
(func (export "ret-tuple")
|
(func (export "ret-tuple") (param u32) (param u32) (result (tuple bool char))
|
||||||
(canon.lift (func (param u32) (param u32) (result (tuple bool char))) (into $i) (func $i "ret-tuple"))
|
(canon lift (core func $i "ret-tuple")
|
||||||
|
(memory $i "memory")
|
||||||
|
(realloc (func $i "realloc")))
|
||||||
)
|
)
|
||||||
)"#
|
)"#
|
||||||
);
|
);
|
||||||
@@ -1244,7 +1232,7 @@ fn char_bool_memory() -> Result<()> {
|
|||||||
fn string_list_oob() -> Result<()> {
|
fn string_list_oob() -> Result<()> {
|
||||||
let component = format!(
|
let component = format!(
|
||||||
r#"(component
|
r#"(component
|
||||||
(module $m
|
(core module $m
|
||||||
(memory (export "memory") 1)
|
(memory (export "memory") 1)
|
||||||
(func (export "ret-list") (result i32)
|
(func (export "ret-list") (result i32)
|
||||||
(local $base i32)
|
(local $base i32)
|
||||||
@@ -1269,13 +1257,19 @@ fn string_list_oob() -> Result<()> {
|
|||||||
|
|
||||||
{REALLOC_AND_FREE}
|
{REALLOC_AND_FREE}
|
||||||
)
|
)
|
||||||
(instance $i (instantiate (module $m)))
|
(core instance $i (instantiate $m))
|
||||||
|
|
||||||
(func (export "ret-list-u8")
|
(func (export "ret-list-u8") (result (list u8))
|
||||||
(canon.lift (func (result (list u8))) (into $i) (func $i "ret-list"))
|
(canon lift (core func $i "ret-list")
|
||||||
|
(memory $i "memory")
|
||||||
|
(realloc (func $i "realloc"))
|
||||||
|
)
|
||||||
|
)
|
||||||
|
(func (export "ret-string") (result string)
|
||||||
|
(canon lift (core func $i "ret-list")
|
||||||
|
(memory $i "memory")
|
||||||
|
(realloc (func $i "realloc"))
|
||||||
)
|
)
|
||||||
(func (export "ret-string")
|
|
||||||
(canon.lift (func (result string)) (into $i) (func $i "ret-list"))
|
|
||||||
)
|
)
|
||||||
)"#
|
)"#
|
||||||
);
|
);
|
||||||
@@ -1300,7 +1294,7 @@ fn string_list_oob() -> Result<()> {
|
|||||||
fn tuples() -> Result<()> {
|
fn tuples() -> Result<()> {
|
||||||
let component = format!(
|
let component = format!(
|
||||||
r#"(component
|
r#"(component
|
||||||
(module $m
|
(core module $m
|
||||||
(memory (export "memory") 1)
|
(memory (export "memory") 1)
|
||||||
(func (export "foo")
|
(func (export "foo")
|
||||||
(param i32 f64 i32)
|
(param i32 f64 i32)
|
||||||
@@ -1323,23 +1317,14 @@ fn tuples() -> Result<()> {
|
|||||||
|
|
||||||
i32.const 3
|
i32.const 3
|
||||||
)
|
)
|
||||||
|
|
||||||
(func (export "canonical_abi_realloc") (param i32 i32 i32 i32) (result i32)
|
|
||||||
unreachable)
|
|
||||||
(func (export "canonical_abi_free") (param i32 i32 i32)
|
|
||||||
unreachable)
|
|
||||||
)
|
)
|
||||||
(instance $i (instantiate (module $m)))
|
(core instance $i (instantiate $m))
|
||||||
|
|
||||||
(func (export "foo")
|
(func (export "foo")
|
||||||
(canon.lift
|
|
||||||
(func
|
|
||||||
(param (tuple s32 float64))
|
(param (tuple s32 float64))
|
||||||
(param (tuple s8))
|
(param (tuple s8))
|
||||||
(result (tuple u16))
|
(result (tuple u16))
|
||||||
)
|
(canon lift (core func $i "foo"))
|
||||||
(func $i "foo")
|
|
||||||
)
|
|
||||||
)
|
)
|
||||||
)"#
|
)"#
|
||||||
);
|
);
|
||||||
@@ -1358,7 +1343,7 @@ fn tuples() -> Result<()> {
|
|||||||
fn option() -> Result<()> {
|
fn option() -> Result<()> {
|
||||||
let component = format!(
|
let component = format!(
|
||||||
r#"(component
|
r#"(component
|
||||||
(module $m
|
(core module $m
|
||||||
(memory (export "memory") 1)
|
(memory (export "memory") 1)
|
||||||
(func (export "pass0") (param i32) (result i32)
|
(func (export "pass0") (param i32) (result i32)
|
||||||
local.get 0
|
local.get 0
|
||||||
@@ -1405,60 +1390,41 @@ fn option() -> Result<()> {
|
|||||||
|
|
||||||
{REALLOC_AND_FREE}
|
{REALLOC_AND_FREE}
|
||||||
)
|
)
|
||||||
(instance $i (instantiate (module $m)))
|
(core instance $i (instantiate $m))
|
||||||
|
|
||||||
(func (export "option-unit-to-u32")
|
(func (export "option-unit-to-u32") (param (option unit)) (result u32)
|
||||||
(canon.lift
|
(canon lift (core func $i "pass0"))
|
||||||
(func (param (option unit)) (result u32))
|
)
|
||||||
(func $i "pass0")
|
(func (export "option-u8-to-tuple") (param (option u8)) (result (tuple u32 u32))
|
||||||
|
(canon lift (core func $i "pass1") (memory $i "memory"))
|
||||||
|
)
|
||||||
|
(func (export "option-u32-to-tuple") (param (option u32)) (result (tuple u32 u32))
|
||||||
|
(canon lift (core func $i "pass1") (memory $i "memory"))
|
||||||
|
)
|
||||||
|
(func (export "option-string-to-tuple") (param (option string)) (result (tuple u32 string))
|
||||||
|
(canon lift
|
||||||
|
(core func $i "pass2")
|
||||||
|
(memory $i "memory")
|
||||||
|
(realloc (func $i "realloc"))
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
(func (export "option-u8-to-tuple")
|
(func (export "to-option-unit") (param u32) (result (option unit))
|
||||||
(canon.lift
|
(canon lift (core func $i "pass0"))
|
||||||
(func (param (option u8)) (result (tuple u32 u32)))
|
)
|
||||||
(into $i)
|
(func (export "to-option-u8") (param u32) (param u32) (result (option u8))
|
||||||
(func $i "pass1")
|
(canon lift (core func $i "pass1") (memory $i "memory"))
|
||||||
|
)
|
||||||
|
(func (export "to-option-u32") (param u32) (param u32) (result (option u32))
|
||||||
|
(canon lift
|
||||||
|
(core func $i "pass1")
|
||||||
|
(memory $i "memory")
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
(func (export "option-u32-to-tuple")
|
(func (export "to-option-string") (param u32) (param string) (result (option string))
|
||||||
(canon.lift
|
(canon lift
|
||||||
(func (param (option u32)) (result (tuple u32 u32)))
|
(core func $i "pass2")
|
||||||
(into $i)
|
(memory $i "memory")
|
||||||
(func $i "pass1")
|
(realloc (func $i "realloc"))
|
||||||
)
|
|
||||||
)
|
|
||||||
(func (export "option-string-to-tuple")
|
|
||||||
(canon.lift
|
|
||||||
(func (param (option string)) (result (tuple u32 string)))
|
|
||||||
(into $i)
|
|
||||||
(func $i "pass2")
|
|
||||||
)
|
|
||||||
)
|
|
||||||
(func (export "to-option-unit")
|
|
||||||
(canon.lift
|
|
||||||
(func (param u32) (result (option unit)))
|
|
||||||
(func $i "pass0")
|
|
||||||
)
|
|
||||||
)
|
|
||||||
(func (export "to-option-u8")
|
|
||||||
(canon.lift
|
|
||||||
(func (param u32) (param u32) (result (option u8)))
|
|
||||||
(into $i)
|
|
||||||
(func $i "pass1")
|
|
||||||
)
|
|
||||||
)
|
|
||||||
(func (export "to-option-u32")
|
|
||||||
(canon.lift
|
|
||||||
(func (param u32) (param u32) (result (option u32)))
|
|
||||||
(into $i)
|
|
||||||
(func $i "pass1")
|
|
||||||
)
|
|
||||||
)
|
|
||||||
(func (export "to-option-string")
|
|
||||||
(canon.lift
|
|
||||||
(func (param u32) (param string) (result (option string)))
|
|
||||||
(into $i)
|
|
||||||
(func $i "pass2")
|
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
)"#
|
)"#
|
||||||
@@ -1543,7 +1509,7 @@ fn option() -> Result<()> {
|
|||||||
fn expected() -> Result<()> {
|
fn expected() -> Result<()> {
|
||||||
let component = format!(
|
let component = format!(
|
||||||
r#"(component
|
r#"(component
|
||||||
(module $m
|
(core module $m
|
||||||
(memory (export "memory") 1)
|
(memory (export "memory") 1)
|
||||||
(func (export "pass0") (param i32) (result i32)
|
(func (export "pass0") (param i32) (result i32)
|
||||||
local.get 0
|
local.get 0
|
||||||
@@ -1590,40 +1556,30 @@ fn expected() -> Result<()> {
|
|||||||
|
|
||||||
{REALLOC_AND_FREE}
|
{REALLOC_AND_FREE}
|
||||||
)
|
)
|
||||||
(instance $i (instantiate (module $m)))
|
(core instance $i (instantiate $m))
|
||||||
|
|
||||||
(func (export "take-expected-unit")
|
(func (export "take-expected-unit") (param (expected unit unit)) (result u32)
|
||||||
(canon.lift
|
(canon lift (core func $i "pass0"))
|
||||||
(func (param (expected unit unit)) (result u32))
|
|
||||||
(func $i "pass0")
|
|
||||||
)
|
|
||||||
)
|
|
||||||
(func (export "take-expected-u8-f32")
|
|
||||||
(canon.lift
|
|
||||||
(func (param (expected u8 float32)) (result (tuple u32 u32)))
|
|
||||||
(into $i)
|
|
||||||
(func $i "pass1")
|
|
||||||
)
|
)
|
||||||
|
(func (export "take-expected-u8-f32") (param (expected u8 float32)) (result (tuple u32 u32))
|
||||||
|
(canon lift (core func $i "pass1") (memory $i "memory"))
|
||||||
)
|
)
|
||||||
(type $list (list u8))
|
(type $list (list u8))
|
||||||
(func (export "take-expected-string")
|
(func (export "take-expected-string") (param (expected string $list)) (result (tuple u32 string))
|
||||||
(canon.lift
|
(canon lift
|
||||||
(func (param (expected string $list)) (result (tuple u32 string)))
|
(core func $i "pass2")
|
||||||
(into $i)
|
(memory $i "memory")
|
||||||
(func $i "pass2")
|
(realloc (func $i "realloc"))
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
(func (export "to-expected-unit")
|
(func (export "to-expected-unit") (param u32) (result (expected unit unit))
|
||||||
(canon.lift
|
(canon lift (core func $i "pass0"))
|
||||||
(func (param u32) (result (expected unit unit)))
|
|
||||||
(func $i "pass0")
|
|
||||||
)
|
)
|
||||||
)
|
(func (export "to-expected-s16-f32") (param u32) (param u32) (result (expected s16 float32))
|
||||||
(func (export "to-expected-s16-f32")
|
(canon lift
|
||||||
(canon.lift
|
(core func $i "pass1")
|
||||||
(func (param u32) (param u32) (result (expected s16 float32)))
|
(memory $i "memory")
|
||||||
(into $i)
|
(realloc (func $i "realloc"))
|
||||||
(func $i "pass1")
|
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
)"#
|
)"#
|
||||||
@@ -1684,7 +1640,7 @@ fn expected() -> Result<()> {
|
|||||||
fn fancy_list() -> Result<()> {
|
fn fancy_list() -> Result<()> {
|
||||||
let component = format!(
|
let component = format!(
|
||||||
r#"(component
|
r#"(component
|
||||||
(module $m
|
(core module $m
|
||||||
(memory (export "memory") 1)
|
(memory (export "memory") 1)
|
||||||
(func (export "take") (param i32 i32) (result i32)
|
(func (export "take") (param i32 i32) (result i32)
|
||||||
(local $base i32)
|
(local $base i32)
|
||||||
@@ -1715,17 +1671,17 @@ fn fancy_list() -> Result<()> {
|
|||||||
|
|
||||||
{REALLOC_AND_FREE}
|
{REALLOC_AND_FREE}
|
||||||
)
|
)
|
||||||
(instance $i (instantiate (module $m)))
|
(core instance $i (instantiate $m))
|
||||||
|
|
||||||
(type $a (option u8))
|
(type $a (option u8))
|
||||||
(type $b (expected unit string))
|
(type $b (expected unit string))
|
||||||
(type $input (list (tuple $a $b)))
|
(type $input (list (tuple $a $b)))
|
||||||
(type $output (tuple u32 u32 (list u8)))
|
(type $output (tuple u32 u32 (list u8)))
|
||||||
(func (export "take")
|
(func (export "take") (param $input) (result $output)
|
||||||
(canon.lift
|
(canon lift
|
||||||
(func (param $input) (result $output))
|
(core func $i "take")
|
||||||
(into $i)
|
(memory $i "memory")
|
||||||
(func $i "take")
|
(realloc (func $i "realloc"))
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
)"#
|
)"#
|
||||||
@@ -1808,13 +1764,10 @@ impl<'a> SliceExt<'a> for &'a [u8] {
|
|||||||
fn invalid_alignment() -> Result<()> {
|
fn invalid_alignment() -> Result<()> {
|
||||||
let component = format!(
|
let component = format!(
|
||||||
r#"(component
|
r#"(component
|
||||||
(module $m
|
(core module $m
|
||||||
(memory (export "memory") 1)
|
(memory (export "memory") 1)
|
||||||
(func (export "canonical_abi_realloc") (param i32 i32 i32 i32) (result i32)
|
(func (export "realloc") (param i32 i32 i32 i32) (result i32)
|
||||||
i32.const 1)
|
i32.const 1)
|
||||||
(func (export "canonical_abi_free") (param i32 i32 i32)
|
|
||||||
unreachable)
|
|
||||||
|
|
||||||
|
|
||||||
(func (export "take-i32") (param i32))
|
(func (export "take-i32") (param i32))
|
||||||
(func (export "ret-1") (result i32) i32.const 1)
|
(func (export "ret-1") (result i32) i32.const 1)
|
||||||
@@ -1823,24 +1776,31 @@ fn invalid_alignment() -> Result<()> {
|
|||||||
(i32.store offset=4 (i32.const 8) (i32.const 1))
|
(i32.store offset=4 (i32.const 8) (i32.const 1))
|
||||||
i32.const 8)
|
i32.const 8)
|
||||||
)
|
)
|
||||||
(instance $i (instantiate (module $m)))
|
(core instance $i (instantiate $m))
|
||||||
|
|
||||||
(func (export "many-params")
|
(func (export "many-params")
|
||||||
(canon.lift
|
|
||||||
(func
|
|
||||||
(param string) (param string) (param string) (param string)
|
(param string) (param string) (param string) (param string)
|
||||||
(param string) (param string) (param string) (param string)
|
(param string) (param string) (param string) (param string)
|
||||||
(param string) (param string) (param string) (param string)
|
(param string) (param string) (param string) (param string)
|
||||||
)
|
(canon lift
|
||||||
(into $i)
|
(core func $i "take-i32")
|
||||||
(func $i "take-i32")
|
(memory $i "memory")
|
||||||
|
(realloc (func $i "realloc"))
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
(func (export "string-ret")
|
(func (export "string-ret") (result string)
|
||||||
(canon.lift (func (result string)) (into $i) (func $i "ret-1"))
|
(canon lift
|
||||||
|
(core func $i "ret-1")
|
||||||
|
(memory $i "memory")
|
||||||
|
(realloc (func $i "realloc"))
|
||||||
|
)
|
||||||
|
)
|
||||||
|
(func (export "list-u32-ret") (result (list u32))
|
||||||
|
(canon lift
|
||||||
|
(core func $i "ret-unaligned-list")
|
||||||
|
(memory $i "memory")
|
||||||
|
(realloc (func $i "realloc"))
|
||||||
)
|
)
|
||||||
(func (export "list-u32-ret")
|
|
||||||
(canon.lift (func (result (list u32))) (into $i) (func $i "ret-unaligned-list"))
|
|
||||||
)
|
)
|
||||||
)"#
|
)"#
|
||||||
);
|
);
|
||||||
|
|||||||
@@ -7,20 +7,18 @@ use wasmtime::{Store, StoreContextMut, Trap};
|
|||||||
fn can_compile() -> Result<()> {
|
fn can_compile() -> Result<()> {
|
||||||
let engine = super::engine();
|
let engine = super::engine();
|
||||||
let libc = r#"
|
let libc = r#"
|
||||||
(module $libc
|
(core module $libc
|
||||||
(memory (export "memory") 1)
|
(memory (export "memory") 1)
|
||||||
(func (export "canonical_abi_realloc") (param i32 i32 i32 i32) (result i32)
|
(func (export "realloc") (param i32 i32 i32 i32) (result i32)
|
||||||
unreachable)
|
|
||||||
(func (export "canonical_abi_free") (param i32 i32 i32)
|
|
||||||
unreachable)
|
unreachable)
|
||||||
)
|
)
|
||||||
(instance $libc (instantiate (module $libc)))
|
(core instance $libc (instantiate $libc))
|
||||||
"#;
|
"#;
|
||||||
Component::new(
|
Component::new(
|
||||||
&engine,
|
&engine,
|
||||||
r#"(component
|
r#"(component
|
||||||
(import "" (func $f))
|
(import "" (func $f))
|
||||||
(func (canon.lower (func $f)))
|
(core func (canon lower (func $f)))
|
||||||
)"#,
|
)"#,
|
||||||
)?;
|
)?;
|
||||||
Component::new(
|
Component::new(
|
||||||
@@ -29,7 +27,7 @@ fn can_compile() -> Result<()> {
|
|||||||
r#"(component
|
r#"(component
|
||||||
(import "" (func $f (param string)))
|
(import "" (func $f (param string)))
|
||||||
{libc}
|
{libc}
|
||||||
(func (canon.lower (into $libc) (func $f)))
|
(core func (canon lower (func $f) (memory $libc "memory") (realloc (func $libc "realloc"))))
|
||||||
)"#
|
)"#
|
||||||
),
|
),
|
||||||
)?;
|
)?;
|
||||||
@@ -39,14 +37,14 @@ fn can_compile() -> Result<()> {
|
|||||||
r#"(component
|
r#"(component
|
||||||
(import "f1" (func $f1 (param string) (result string)))
|
(import "f1" (func $f1 (param string) (result string)))
|
||||||
{libc}
|
{libc}
|
||||||
(func (canon.lower (into $libc) (func $f1)))
|
(core func (canon lower (func $f1) (memory $libc "memory") (realloc (func $libc "realloc"))))
|
||||||
|
|
||||||
(import "f2" (func $f2 (param u32) (result (list u8))))
|
(import "f2" (func $f2 (param u32) (result (list u8))))
|
||||||
(instance $libc2 (instantiate (module $libc)))
|
(core instance $libc2 (instantiate $libc))
|
||||||
(func (canon.lower (into $libc2) (func $f2)))
|
(core func (canon lower (func $f2) (memory $libc2 "memory") (realloc (func $libc2 "realloc"))))
|
||||||
|
|
||||||
(func (canon.lower (into $libc2) (func $f1)))
|
(core func (canon lower (func $f1) (memory $libc2 "memory") (realloc (func $libc2 "realloc"))))
|
||||||
(func (canon.lower (into $libc) (func $f2)))
|
(core func (canon lower (func $f2) (memory $libc "memory") (realloc (func $libc "realloc"))))
|
||||||
)"#
|
)"#
|
||||||
),
|
),
|
||||||
)?;
|
)?;
|
||||||
@@ -56,9 +54,9 @@ fn can_compile() -> Result<()> {
|
|||||||
r#"(component
|
r#"(component
|
||||||
(import "log" (func $log (param string)))
|
(import "log" (func $log (param string)))
|
||||||
{libc}
|
{libc}
|
||||||
(func $log_lower (canon.lower (into $libc) (func $log)))
|
(core func $log_lower (canon lower (func $log) (memory $libc "memory") (realloc (func $libc "realloc"))))
|
||||||
|
|
||||||
(module $logger
|
(core module $logger
|
||||||
(import "host" "log" (func $log (param i32 i32)))
|
(import "host" "log" (func $log (param i32 i32)))
|
||||||
(import "libc" "memory" (memory 1))
|
(import "libc" "memory" (memory 1))
|
||||||
|
|
||||||
@@ -67,13 +65,13 @@ fn can_compile() -> Result<()> {
|
|||||||
i32.const 0
|
i32.const 0
|
||||||
call $log)
|
call $log)
|
||||||
)
|
)
|
||||||
(instance $logger (instantiate (module $logger)
|
(core instance $logger (instantiate $logger
|
||||||
(with "host" (instance (export "log" (func $log_lower))))
|
(with "host" (instance (export "log" (func $log_lower))))
|
||||||
(with "libc" (instance $libc))
|
(with "libc" (instance $libc))
|
||||||
))
|
))
|
||||||
|
|
||||||
(func (export "call")
|
(func (export "call")
|
||||||
(canon.lift (func) (func $logger "call"))
|
(canon lift (core func $logger "call"))
|
||||||
)
|
)
|
||||||
)"#
|
)"#
|
||||||
),
|
),
|
||||||
@@ -87,19 +85,17 @@ fn simple() -> Result<()> {
|
|||||||
(component
|
(component
|
||||||
(import "" (func $log (param string)))
|
(import "" (func $log (param string)))
|
||||||
|
|
||||||
(module $libc
|
(core module $libc
|
||||||
(memory (export "memory") 1)
|
(memory (export "memory") 1)
|
||||||
|
|
||||||
(func (export "canonical_abi_realloc") (param i32 i32 i32 i32) (result i32)
|
(func (export "realloc") (param i32 i32 i32 i32) (result i32)
|
||||||
unreachable)
|
|
||||||
(func (export "canonical_abi_free") (param i32 i32 i32)
|
|
||||||
unreachable)
|
unreachable)
|
||||||
)
|
)
|
||||||
(instance $libc (instantiate (module $libc)))
|
(core instance $libc (instantiate $libc))
|
||||||
(func $log_lower
|
(core func $log_lower
|
||||||
(canon.lower (into $libc) (func $log))
|
(canon lower (func $log) (memory $libc "memory") (realloc (func $libc "realloc")))
|
||||||
)
|
)
|
||||||
(module $m
|
(core module $m
|
||||||
(import "libc" "memory" (memory 1))
|
(import "libc" "memory" (memory 1))
|
||||||
(import "host" "log" (func $log (param i32 i32)))
|
(import "host" "log" (func $log (param i32 i32)))
|
||||||
|
|
||||||
@@ -110,12 +106,12 @@ fn simple() -> Result<()> {
|
|||||||
|
|
||||||
(data (i32.const 5) "hello world")
|
(data (i32.const 5) "hello world")
|
||||||
)
|
)
|
||||||
(instance $i (instantiate (module $m)
|
(core instance $i (instantiate $m
|
||||||
(with "libc" (instance $libc))
|
(with "libc" (instance $libc))
|
||||||
(with "host" (instance (export "log" (func $log_lower))))
|
(with "host" (instance (export "log" (func $log_lower))))
|
||||||
))
|
))
|
||||||
(func (export "call")
|
(func (export "call")
|
||||||
(canon.lift (func) (func $i "call"))
|
(canon lift (core func $i "call"))
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
"#;
|
"#;
|
||||||
@@ -150,7 +146,7 @@ fn attempt_to_leave_during_malloc() -> Result<()> {
|
|||||||
(import "thunk" (func $thunk))
|
(import "thunk" (func $thunk))
|
||||||
(import "ret-string" (func $ret_string (result string)))
|
(import "ret-string" (func $ret_string (result string)))
|
||||||
|
|
||||||
(module $host_shim
|
(core module $host_shim
|
||||||
(table (export "table") 2 funcref)
|
(table (export "table") 2 funcref)
|
||||||
(func $shim_thunk (export "thunk")
|
(func $shim_thunk (export "thunk")
|
||||||
i32.const 0
|
i32.const 0
|
||||||
@@ -160,21 +156,18 @@ fn attempt_to_leave_during_malloc() -> Result<()> {
|
|||||||
i32.const 1
|
i32.const 1
|
||||||
call_indirect (param i32))
|
call_indirect (param i32))
|
||||||
)
|
)
|
||||||
(instance $host_shim (instantiate (module $host_shim)))
|
(core instance $host_shim (instantiate $host_shim))
|
||||||
|
|
||||||
(module $m
|
(core module $m
|
||||||
(import "host" "thunk" (func $thunk))
|
(import "host" "thunk" (func $thunk))
|
||||||
(import "host" "ret-string" (func $ret_string (param i32)))
|
(import "host" "ret-string" (func $ret_string (param i32)))
|
||||||
|
|
||||||
(memory (export "memory") 1)
|
(memory (export "memory") 1)
|
||||||
|
|
||||||
(func $realloc (export "canonical_abi_realloc") (param i32 i32 i32 i32) (result i32)
|
(func $realloc (export "realloc") (param i32 i32 i32 i32) (result i32)
|
||||||
call $thunk
|
call $thunk
|
||||||
unreachable)
|
unreachable)
|
||||||
|
|
||||||
(func (export "canonical_abi_free") (param i32 i32 i32)
|
|
||||||
unreachable)
|
|
||||||
|
|
||||||
(func $run (export "run")
|
(func $run (export "run")
|
||||||
i32.const 8
|
i32.const 8
|
||||||
call $ret_string)
|
call $ret_string)
|
||||||
@@ -182,24 +175,24 @@ fn attempt_to_leave_during_malloc() -> Result<()> {
|
|||||||
(func (export "take-string") (param i32 i32)
|
(func (export "take-string") (param i32 i32)
|
||||||
unreachable)
|
unreachable)
|
||||||
)
|
)
|
||||||
(instance $m (instantiate (module $m) (with "host" (instance $host_shim))))
|
(core instance $m (instantiate $m (with "host" (instance $host_shim))))
|
||||||
|
|
||||||
(module $host_shim_filler_inner
|
(core module $host_shim_filler_inner
|
||||||
(import "shim" "table" (table 2 funcref))
|
(import "shim" "table" (table 2 funcref))
|
||||||
(import "host" "thunk" (func $thunk))
|
(import "host" "thunk" (func $thunk))
|
||||||
(import "host" "ret-string" (func $ret_string (param i32)))
|
(import "host" "ret-string" (func $ret_string (param i32)))
|
||||||
(elem (i32.const 0) $thunk $ret_string)
|
(elem (i32.const 0) $thunk $ret_string)
|
||||||
)
|
)
|
||||||
|
|
||||||
(func $thunk_lower
|
(core func $thunk_lower
|
||||||
(canon.lower (into $m) (func $thunk))
|
(canon lower (func $thunk) (memory $m "memory") (realloc (func $m "realloc")))
|
||||||
)
|
)
|
||||||
|
|
||||||
(func $ret_string_lower
|
(core func $ret_string_lower
|
||||||
(canon.lower (into $m) (func $ret_string))
|
(canon lower (func $ret_string) (memory $m "memory") (realloc (func $m "realloc")))
|
||||||
)
|
)
|
||||||
|
|
||||||
(instance (instantiate (module $host_shim_filler_inner)
|
(core instance (instantiate $host_shim_filler_inner
|
||||||
(with "shim" (instance $host_shim))
|
(with "shim" (instance $host_shim))
|
||||||
(with "host" (instance
|
(with "host" (instance
|
||||||
(export "thunk" (func $thunk_lower))
|
(export "thunk" (func $thunk_lower))
|
||||||
@@ -208,10 +201,10 @@ fn attempt_to_leave_during_malloc() -> Result<()> {
|
|||||||
))
|
))
|
||||||
|
|
||||||
(func (export "run")
|
(func (export "run")
|
||||||
(canon.lift (func) (func $m "run"))
|
(canon lift (core func $m "run"))
|
||||||
)
|
)
|
||||||
(func (export "take-string")
|
(func (export "take-string") (param string)
|
||||||
(canon.lift (func (param string)) (into $m) (func $m "take-string"))
|
(canon lift (core func $m "take-string") (memory $m "memory") (realloc (func $m "realloc")))
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
"#;
|
"#;
|
||||||
@@ -287,20 +280,20 @@ fn attempt_to_reenter_during_host() -> Result<()> {
|
|||||||
let component = r#"
|
let component = r#"
|
||||||
(component
|
(component
|
||||||
(import "thunk" (func $thunk))
|
(import "thunk" (func $thunk))
|
||||||
(func $thunk_lower (canon.lower (func $thunk)))
|
(core func $thunk_lower (canon lower (func $thunk)))
|
||||||
|
|
||||||
(module $m
|
(core module $m
|
||||||
(import "host" "thunk" (func $thunk))
|
(import "host" "thunk" (func $thunk))
|
||||||
|
|
||||||
(func $run (export "run")
|
(func $run (export "run")
|
||||||
call $thunk)
|
call $thunk)
|
||||||
)
|
)
|
||||||
(instance $m (instantiate (module $m)
|
(core instance $m (instantiate $m
|
||||||
(with "host" (instance (export "thunk" (func $thunk_lower))))
|
(with "host" (instance (export "thunk" (func $thunk_lower))))
|
||||||
))
|
))
|
||||||
|
|
||||||
(func (export "run")
|
(func (export "run")
|
||||||
(canon.lift (func) (func $m "run"))
|
(canon lift (core func $m "run"))
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
"#;
|
"#;
|
||||||
@@ -348,18 +341,18 @@ fn stack_and_heap_args_and_rets() -> Result<()> {
|
|||||||
(import "f3" (func $f3 (param u32) (result string)))
|
(import "f3" (func $f3 (param u32) (result string)))
|
||||||
(import "f4" (func $f4 (param $many_params) (result string)))
|
(import "f4" (func $f4 (param $many_params) (result string)))
|
||||||
|
|
||||||
(module $libc
|
(core module $libc
|
||||||
{REALLOC_AND_FREE}
|
{REALLOC_AND_FREE}
|
||||||
(memory (export "memory") 1)
|
(memory (export "memory") 1)
|
||||||
)
|
)
|
||||||
(instance $libc (instantiate (module $libc)))
|
(core instance $libc (instantiate (module $libc)))
|
||||||
|
|
||||||
(func $f1_lower (canon.lower (into $libc) (func $f1)))
|
(core func $f1_lower (canon lower (func $f1) (memory $libc "memory") (realloc (func $libc "realloc"))))
|
||||||
(func $f2_lower (canon.lower (into $libc) (func $f2)))
|
(core func $f2_lower (canon lower (func $f2) (memory $libc "memory") (realloc (func $libc "realloc"))))
|
||||||
(func $f3_lower (canon.lower (into $libc) (func $f3)))
|
(core func $f3_lower (canon lower (func $f3) (memory $libc "memory") (realloc (func $libc "realloc"))))
|
||||||
(func $f4_lower (canon.lower (into $libc) (func $f4)))
|
(core func $f4_lower (canon lower (func $f4) (memory $libc "memory") (realloc (func $libc "realloc"))))
|
||||||
|
|
||||||
(module $m
|
(core module $m
|
||||||
(import "host" "f1" (func $f1 (param i32) (result i32)))
|
(import "host" "f1" (func $f1 (param i32) (result i32)))
|
||||||
(import "host" "f2" (func $f2 (param i32) (result i32)))
|
(import "host" "f2" (func $f2 (param i32) (result i32)))
|
||||||
(import "host" "f3" (func $f3 (param i32 i32)))
|
(import "host" "f3" (func $f3 (param i32 i32)))
|
||||||
@@ -454,7 +447,7 @@ fn stack_and_heap_args_and_rets() -> Result<()> {
|
|||||||
|
|
||||||
(data (i32.const 1000) "abc")
|
(data (i32.const 1000) "abc")
|
||||||
)
|
)
|
||||||
(instance $m (instantiate (module $m)
|
(core instance $m (instantiate $m
|
||||||
(with "libc" (instance $libc))
|
(with "libc" (instance $libc))
|
||||||
(with "host" (instance
|
(with "host" (instance
|
||||||
(export "f1" (func $f1_lower))
|
(export "f1" (func $f1_lower))
|
||||||
@@ -465,7 +458,7 @@ fn stack_and_heap_args_and_rets() -> Result<()> {
|
|||||||
))
|
))
|
||||||
|
|
||||||
(func (export "run")
|
(func (export "run")
|
||||||
(canon.lift (func) (func $m "run"))
|
(canon lift (core func $m "run"))
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
"#
|
"#
|
||||||
@@ -542,23 +535,21 @@ fn bad_import_alignment() -> Result<()> {
|
|||||||
string
|
string
|
||||||
))
|
))
|
||||||
(import "unaligned-argptr" (func $unaligned_argptr (param $many_arg)))
|
(import "unaligned-argptr" (func $unaligned_argptr (param $many_arg)))
|
||||||
(module $libc_panic
|
(core module $libc_panic
|
||||||
(memory (export "memory") 1)
|
(memory (export "memory") 1)
|
||||||
(func (export "canonical_abi_realloc") (param i32 i32 i32 i32) (result i32)
|
(func (export "realloc") (param i32 i32 i32 i32) (result i32)
|
||||||
unreachable)
|
|
||||||
(func (export "canonical_abi_free") (param i32 i32 i32)
|
|
||||||
unreachable)
|
unreachable)
|
||||||
)
|
)
|
||||||
(instance $libc_panic (instantiate (module $libc_panic)))
|
(core instance $libc_panic (instantiate $libc_panic))
|
||||||
|
|
||||||
(func $unaligned_retptr_lower
|
(core func $unaligned_retptr_lower
|
||||||
(canon.lower (into $libc_panic) (func $unaligned_retptr))
|
(canon lower (func $unaligned_retptr) (memory $libc_panic "memory") (realloc (func $libc_panic "realloc")))
|
||||||
)
|
)
|
||||||
(func $unaligned_argptr_lower
|
(core func $unaligned_argptr_lower
|
||||||
(canon.lower (into $libc_panic) (func $unaligned_argptr))
|
(canon lower (func $unaligned_argptr) (memory $libc_panic "memory") (realloc (func $libc_panic "realloc")))
|
||||||
)
|
)
|
||||||
|
|
||||||
(module $m
|
(core module $m
|
||||||
(import "host" "unaligned-retptr" (func $unaligned_retptr (param i32)))
|
(import "host" "unaligned-retptr" (func $unaligned_retptr (param i32)))
|
||||||
(import "host" "unaligned-argptr" (func $unaligned_argptr (param i32)))
|
(import "host" "unaligned-argptr" (func $unaligned_argptr (param i32)))
|
||||||
|
|
||||||
@@ -567,7 +558,7 @@ fn bad_import_alignment() -> Result<()> {
|
|||||||
(func (export "unaligned-argptr")
|
(func (export "unaligned-argptr")
|
||||||
(call $unaligned_argptr (i32.const 1)))
|
(call $unaligned_argptr (i32.const 1)))
|
||||||
)
|
)
|
||||||
(instance $m (instantiate (module $m)
|
(core instance $m (instantiate $m
|
||||||
(with "host" (instance
|
(with "host" (instance
|
||||||
(export "unaligned-retptr" (func $unaligned_retptr_lower))
|
(export "unaligned-retptr" (func $unaligned_retptr_lower))
|
||||||
(export "unaligned-argptr" (func $unaligned_argptr_lower))
|
(export "unaligned-argptr" (func $unaligned_argptr_lower))
|
||||||
@@ -575,10 +566,10 @@ fn bad_import_alignment() -> Result<()> {
|
|||||||
))
|
))
|
||||||
|
|
||||||
(func (export "unaligned-retptr")
|
(func (export "unaligned-retptr")
|
||||||
(canon.lift (func) (func $m "unaligned-retptr"))
|
(canon lift (core func $m "unaligned-retptr"))
|
||||||
)
|
)
|
||||||
(func (export "unaligned-argptr")
|
(func (export "unaligned-argptr")
|
||||||
(canon.lift (func) (func $m "unaligned-argptr"))
|
(canon lift (core func $m "unaligned-argptr"))
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
"#
|
"#
|
||||||
|
|||||||
@@ -1,54 +1,72 @@
|
|||||||
;; basic function lifting
|
;; basic function lifting
|
||||||
(component
|
(component
|
||||||
(module $m
|
(core module $m
|
||||||
(func (export ""))
|
(func (export ""))
|
||||||
)
|
)
|
||||||
(instance $i (instantiate (module $m)))
|
(core instance $i (instantiate $m))
|
||||||
|
|
||||||
(func (export "thunk")
|
(func (export "thunk")
|
||||||
(canon.lift (func) (func $i ""))
|
(canon lift (core func $i ""))
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
|
||||||
;; use an aliased type
|
;; use an aliased type
|
||||||
(component $c
|
(component $c
|
||||||
(module $m
|
(core module $m
|
||||||
(func (export ""))
|
(func (export ""))
|
||||||
)
|
)
|
||||||
(instance $i (instantiate (module $m)))
|
(core instance $i (instantiate $m))
|
||||||
|
|
||||||
(type $to_alias (func))
|
(type $to_alias (func))
|
||||||
(alias outer $c $to_alias (type $alias))
|
(alias outer $c $to_alias (type $alias))
|
||||||
|
|
||||||
(func (export "thunk")
|
(func (export "thunk") (type $alias)
|
||||||
(canon.lift (type $alias) (func $i ""))
|
(canon lift (core func $i ""))
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
|
||||||
;; test out some various canonical abi
|
;; test out some various canonical abi
|
||||||
(component $c
|
(component $c
|
||||||
(module $m
|
(core module $m
|
||||||
(func (export "") (param i32 i32))
|
(func (export "") (param i32 i32))
|
||||||
(memory (export "memory") 1)
|
(memory (export "memory") 1)
|
||||||
(func (export "canonical_abi_realloc") (param i32 i32 i32 i32) (result i32)
|
(func (export "realloc") (param i32 i32 i32 i32) (result i32)
|
||||||
unreachable)
|
unreachable)
|
||||||
(func (export "canonical_abi_free") (param i32 i32 i32))
|
|
||||||
)
|
)
|
||||||
(instance $i (instantiate (module $m)))
|
(core instance $i (instantiate $m))
|
||||||
|
|
||||||
(func (export "thunk")
|
(func (export "thunk") (param string)
|
||||||
(canon.lift (func (param string)) (into $i) (func $i ""))
|
(canon lift
|
||||||
|
(core func $i "")
|
||||||
|
(memory $i "memory")
|
||||||
|
(realloc (func $i "realloc"))
|
||||||
|
)
|
||||||
)
|
)
|
||||||
|
|
||||||
(func (export "thunk8")
|
(func (export "thunk8") (param string)
|
||||||
(canon.lift (func (param string)) string=utf8 (into $i) (func $i ""))
|
(canon lift
|
||||||
|
(core func $i "")
|
||||||
|
string-encoding=utf8
|
||||||
|
(memory $i "memory")
|
||||||
|
(realloc (func $i "realloc"))
|
||||||
|
)
|
||||||
)
|
)
|
||||||
|
|
||||||
(func (export "thunk16")
|
(func (export "thunk16") (param string)
|
||||||
(canon.lift (func (param string)) string=utf16 (into $i) (func $i ""))
|
(canon lift
|
||||||
|
(core func $i "")
|
||||||
|
string-encoding=utf16
|
||||||
|
(memory $i "memory")
|
||||||
|
(realloc (func $i "realloc"))
|
||||||
|
)
|
||||||
)
|
)
|
||||||
|
|
||||||
(func (export "thunklatin16")
|
(func (export "thunklatin16") (param string)
|
||||||
(canon.lift (func (param string)) string=latin1+utf16 (into $i) (func $i ""))
|
(canon lift
|
||||||
|
(core func $i "")
|
||||||
|
string-encoding=latin1+utf16
|
||||||
|
(memory $i "memory")
|
||||||
|
(realloc (func $i "realloc"))
|
||||||
|
)
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
|||||||
@@ -1,30 +1,30 @@
|
|||||||
(component
|
(component
|
||||||
(module $m)
|
(core module $m)
|
||||||
(instance (instantiate (module $m)))
|
(core instance (instantiate $m))
|
||||||
)
|
)
|
||||||
|
|
||||||
(component
|
(component
|
||||||
(module $m
|
(core module $m
|
||||||
(func (export ""))
|
(func (export ""))
|
||||||
)
|
)
|
||||||
(instance $i (instantiate (module $m)))
|
(core instance $i (instantiate $m))
|
||||||
|
|
||||||
(module $m2
|
(core module $m2
|
||||||
(func (import "" ""))
|
(func (import "" ""))
|
||||||
)
|
)
|
||||||
(instance (instantiate (module $m2) (with "" (instance $i))))
|
(core instance (instantiate $m2 (with "" (instance $i))))
|
||||||
)
|
)
|
||||||
|
|
||||||
(component
|
(component
|
||||||
(module $m
|
(core module $m
|
||||||
(func (export "a"))
|
(func (export "a"))
|
||||||
)
|
)
|
||||||
(instance $i (instantiate (module $m)))
|
(core instance $i (instantiate $m))
|
||||||
|
|
||||||
(module $m2
|
(core module $m2
|
||||||
(func (import "" "b"))
|
(func (import "" "b"))
|
||||||
)
|
)
|
||||||
(instance (instantiate (module $m2)
|
(core instance (instantiate $m2
|
||||||
(with "" (instance (export "b" (func $i "a"))))
|
(with "" (instance (export "b" (func $i "a"))))
|
||||||
))
|
))
|
||||||
)
|
)
|
||||||
@@ -32,15 +32,15 @@
|
|||||||
;; all kinds of imports for core wasm modules, and register a start function on
|
;; all kinds of imports for core wasm modules, and register a start function on
|
||||||
;; one module to ensure that everything is correct
|
;; one module to ensure that everything is correct
|
||||||
(component
|
(component
|
||||||
(module $m
|
(core module $m
|
||||||
(func (export "a"))
|
(func (export "a"))
|
||||||
(table (export "b") 1 funcref)
|
(table (export "b") 1 funcref)
|
||||||
(memory (export "c") 1)
|
(memory (export "c") 1)
|
||||||
(global (export "d") i32 i32.const 1)
|
(global (export "d") i32 i32.const 1)
|
||||||
)
|
)
|
||||||
(instance $i (instantiate (module $m)))
|
(core instance $i (instantiate $m))
|
||||||
|
|
||||||
(module $m2
|
(core module $m2
|
||||||
(import "" "a" (func $f))
|
(import "" "a" (func $f))
|
||||||
(import "" "b" (table 1 funcref))
|
(import "" "b" (table 1 funcref))
|
||||||
(import "" "c" (memory 1))
|
(import "" "c" (memory 1))
|
||||||
@@ -62,7 +62,7 @@
|
|||||||
(data (i32.const 0) "hello")
|
(data (i32.const 0) "hello")
|
||||||
(elem (i32.const 0) $start)
|
(elem (i32.const 0) $start)
|
||||||
)
|
)
|
||||||
(instance (instantiate (module $m2)
|
(core instance (instantiate $m2
|
||||||
(with "" (instance $i))
|
(with "" (instance $i))
|
||||||
))
|
))
|
||||||
)
|
)
|
||||||
@@ -71,12 +71,12 @@
|
|||||||
;; sees the wrong value for the global import
|
;; sees the wrong value for the global import
|
||||||
(assert_trap
|
(assert_trap
|
||||||
(component
|
(component
|
||||||
(module $m
|
(core module $m
|
||||||
(global (export "g") i32 i32.const 1)
|
(global (export "g") i32 i32.const 1)
|
||||||
)
|
)
|
||||||
(instance $i (instantiate (module $m)))
|
(core instance $i (instantiate $m))
|
||||||
|
|
||||||
(module $m2
|
(core module $m2
|
||||||
(import "" "g" (global $g i32))
|
(import "" "g" (global $g i32))
|
||||||
|
|
||||||
(func $start
|
(func $start
|
||||||
@@ -90,27 +90,27 @@
|
|||||||
|
|
||||||
(start $start)
|
(start $start)
|
||||||
)
|
)
|
||||||
(instance (instantiate (module $m2) (with "" (instance $i))))
|
(core instance (instantiate $m2 (with "" (instance $i))))
|
||||||
)
|
)
|
||||||
"unreachable")
|
"unreachable")
|
||||||
|
|
||||||
;; shuffle around imports to get to what the target core wasm module needs
|
;; shuffle around imports to get to what the target core wasm module needs
|
||||||
(component
|
(component
|
||||||
(module $m
|
(core module $m
|
||||||
(func (export "1"))
|
(func (export "1"))
|
||||||
(table (export "2") 1 funcref)
|
(table (export "2") 1 funcref)
|
||||||
(memory (export "3") 1)
|
(memory (export "3") 1)
|
||||||
(global (export "4") i32 i32.const 1)
|
(global (export "4") i32 i32.const 1)
|
||||||
)
|
)
|
||||||
(instance $i (instantiate (module $m)))
|
(core instance $i (instantiate $m))
|
||||||
|
|
||||||
(module $m2
|
(core module $m2
|
||||||
(import "" "a" (func $f))
|
(import "" "a" (func $f))
|
||||||
(import "" "b" (table 1 funcref))
|
(import "" "b" (table 1 funcref))
|
||||||
(import "" "c" (memory 1))
|
(import "" "c" (memory 1))
|
||||||
(import "" "d" (global $g i32))
|
(import "" "d" (global $g i32))
|
||||||
)
|
)
|
||||||
(instance (instantiate (module $m2)
|
(core instance (instantiate $m2
|
||||||
(with "" (instance
|
(with "" (instance
|
||||||
(export "a" (func $i "1"))
|
(export "a" (func $i "1"))
|
||||||
(export "b" (table $i "2"))
|
(export "b" (table $i "2"))
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
(assert_unlinkable
|
(assert_unlinkable
|
||||||
(component
|
(component
|
||||||
(import "undefined-name" (module))
|
(import "undefined-name" (core module))
|
||||||
)
|
)
|
||||||
"import `undefined-name` not defined")
|
"import `undefined-name` not defined")
|
||||||
(component $i)
|
(component $i)
|
||||||
@@ -8,7 +8,7 @@
|
|||||||
(import "i" (instance))
|
(import "i" (instance))
|
||||||
)
|
)
|
||||||
(assert_unlinkable
|
(assert_unlinkable
|
||||||
(component (import "i" (module)))
|
(component (import "i" (core module)))
|
||||||
"expected module found instance")
|
"expected module found instance")
|
||||||
(assert_unlinkable
|
(assert_unlinkable
|
||||||
(component (import "i" (func)))
|
(component (import "i" (func)))
|
||||||
|
|||||||
@@ -1,18 +1,18 @@
|
|||||||
(component $foo
|
(component $foo
|
||||||
(module (export "a-module"))
|
(core module (export "a-module"))
|
||||||
)
|
)
|
||||||
|
|
||||||
;; the above instance can be imported into this component
|
;; the above instance can be imported into this component
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "a-module" (module))
|
(export "a-module" (core module))
|
||||||
))
|
))
|
||||||
)
|
)
|
||||||
|
|
||||||
;; specifying extra imports is ok
|
;; specifying extra imports is ok
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "a-module" (module
|
(export "a-module" (core module
|
||||||
(import "foo" "bar" (func))
|
(import "foo" "bar" (func))
|
||||||
))
|
))
|
||||||
))
|
))
|
||||||
@@ -22,7 +22,7 @@
|
|||||||
(assert_unlinkable
|
(assert_unlinkable
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "a-module" (module
|
(export "a-module" (core module
|
||||||
(export "the-export" (func))
|
(export "the-export" (func))
|
||||||
))
|
))
|
||||||
))
|
))
|
||||||
@@ -30,7 +30,7 @@
|
|||||||
"module export `the-export` not defined")
|
"module export `the-export` not defined")
|
||||||
|
|
||||||
(component $foo
|
(component $foo
|
||||||
(module (export "a-module")
|
(core module (export "a-module")
|
||||||
(import "env" "something" (func))
|
(import "env" "something" (func))
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
@@ -39,14 +39,14 @@
|
|||||||
(assert_unlinkable
|
(assert_unlinkable
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "a-module" (module))
|
(export "a-module" (core module))
|
||||||
))
|
))
|
||||||
)
|
)
|
||||||
"module import `env::something` not defined")
|
"module import `env::something` not defined")
|
||||||
|
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "a-module" (module
|
(export "a-module" (core module
|
||||||
(import "env" "something" (func))
|
(import "env" "something" (func))
|
||||||
))
|
))
|
||||||
))
|
))
|
||||||
@@ -55,7 +55,7 @@
|
|||||||
;; extra imports still ok
|
;; extra imports still ok
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "a-module" (module
|
(export "a-module" (core module
|
||||||
(import "env" "something" (func))
|
(import "env" "something" (func))
|
||||||
(import "env" "other" (global i32))
|
(import "env" "other" (global i32))
|
||||||
))
|
))
|
||||||
@@ -63,7 +63,7 @@
|
|||||||
)
|
)
|
||||||
|
|
||||||
(component $foo
|
(component $foo
|
||||||
(module (export "a-module")
|
(core module (export "a-module")
|
||||||
(func (export "f"))
|
(func (export "f"))
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
@@ -71,13 +71,13 @@
|
|||||||
;; dropping exports is ok
|
;; dropping exports is ok
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "a-module" (module))
|
(export "a-module" (core module))
|
||||||
))
|
))
|
||||||
)
|
)
|
||||||
|
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "a-module" (module
|
(export "a-module" (core module
|
||||||
(export "f" (func))
|
(export "f" (func))
|
||||||
))
|
))
|
||||||
))
|
))
|
||||||
@@ -86,7 +86,7 @@
|
|||||||
(assert_unlinkable
|
(assert_unlinkable
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "a-module" (module
|
(export "a-module" (core module
|
||||||
(export "f" (func (param i32)))
|
(export "f" (func (param i32)))
|
||||||
))
|
))
|
||||||
))
|
))
|
||||||
@@ -96,7 +96,7 @@
|
|||||||
(assert_unlinkable
|
(assert_unlinkable
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "a-module" (module
|
(export "a-module" (core module
|
||||||
(export "f" (global i32))
|
(export "f" (global i32))
|
||||||
))
|
))
|
||||||
))
|
))
|
||||||
@@ -104,7 +104,7 @@
|
|||||||
"expected global found func")
|
"expected global found func")
|
||||||
|
|
||||||
(component $foo
|
(component $foo
|
||||||
(module (export "m")
|
(core module (export "m")
|
||||||
(func (export "f"))
|
(func (export "f"))
|
||||||
(table (export "t") 1 funcref)
|
(table (export "t") 1 funcref)
|
||||||
(memory (export "m") 1)
|
(memory (export "m") 1)
|
||||||
@@ -116,28 +116,28 @@
|
|||||||
(assert_unlinkable
|
(assert_unlinkable
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "m" (module (export "f" (global i32))))
|
(export "m" (core module (export "f" (global i32))))
|
||||||
))
|
))
|
||||||
)
|
)
|
||||||
"expected global found func")
|
"expected global found func")
|
||||||
(assert_unlinkable
|
(assert_unlinkable
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "m" (module (export "t" (func))))
|
(export "m" (core module (export "t" (func))))
|
||||||
))
|
))
|
||||||
)
|
)
|
||||||
"expected func found table")
|
"expected func found table")
|
||||||
(assert_unlinkable
|
(assert_unlinkable
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "m" (module (export "m" (func))))
|
(export "m" (core module (export "m" (func))))
|
||||||
))
|
))
|
||||||
)
|
)
|
||||||
"expected func found memory")
|
"expected func found memory")
|
||||||
(assert_unlinkable
|
(assert_unlinkable
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "m" (module (export "g" (func))))
|
(export "m" (core module (export "g" (func))))
|
||||||
))
|
))
|
||||||
)
|
)
|
||||||
"expected func found global")
|
"expected func found global")
|
||||||
@@ -146,42 +146,42 @@
|
|||||||
(assert_unlinkable
|
(assert_unlinkable
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "m" (module (export "f" (func (param i32)))))
|
(export "m" (core module (export "f" (func (param i32)))))
|
||||||
))
|
))
|
||||||
)
|
)
|
||||||
"export `f` has the wrong type")
|
"export `f` has the wrong type")
|
||||||
(assert_unlinkable
|
(assert_unlinkable
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "m" (module (export "t" (table 1 externref))))
|
(export "m" (core module (export "t" (table 1 externref))))
|
||||||
))
|
))
|
||||||
)
|
)
|
||||||
"export `t` has the wrong type")
|
"export `t` has the wrong type")
|
||||||
(assert_unlinkable
|
(assert_unlinkable
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "m" (module (export "t" (table 2 funcref))))
|
(export "m" (core module (export "t" (table 2 funcref))))
|
||||||
))
|
))
|
||||||
)
|
)
|
||||||
"export `t` has the wrong type")
|
"export `t` has the wrong type")
|
||||||
(assert_unlinkable
|
(assert_unlinkable
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "m" (module (export "m" (memory 2))))
|
(export "m" (core module (export "m" (memory 2))))
|
||||||
))
|
))
|
||||||
)
|
)
|
||||||
"export `m` has the wrong type")
|
"export `m` has the wrong type")
|
||||||
(assert_unlinkable
|
(assert_unlinkable
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "m" (module (export "g" (global f32))))
|
(export "m" (core module (export "g" (global f32))))
|
||||||
))
|
))
|
||||||
)
|
)
|
||||||
"export `g` has the wrong type")
|
"export `g` has the wrong type")
|
||||||
(assert_unlinkable
|
(assert_unlinkable
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "m" (module (export "g" (global (mut i32)))))
|
(export "m" (core module (export "g" (global (mut i32)))))
|
||||||
))
|
))
|
||||||
)
|
)
|
||||||
"export `g` has the wrong type")
|
"export `g` has the wrong type")
|
||||||
@@ -189,7 +189,7 @@
|
|||||||
;; subtyping ok
|
;; subtyping ok
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "m" (module
|
(export "m" (core module
|
||||||
(export "t" (table 0 funcref))
|
(export "t" (table 0 funcref))
|
||||||
(export "m" (memory 0))
|
(export "m" (memory 0))
|
||||||
))
|
))
|
||||||
@@ -197,38 +197,38 @@
|
|||||||
)
|
)
|
||||||
|
|
||||||
(component $foo
|
(component $foo
|
||||||
(module (export "f") (func (import "" "")))
|
(core module (export "f") (func (import "" "")))
|
||||||
(module (export "t") (table (import "" "") 1 funcref))
|
(core module (export "t") (table (import "" "") 1 funcref))
|
||||||
(module (export "m") (memory (import "" "") 1))
|
(core module (export "m") (memory (import "" "") 1))
|
||||||
(module (export "g") (global (import "" "") i32))
|
(core module (export "g") (global (import "" "") i32))
|
||||||
)
|
)
|
||||||
|
|
||||||
;; wrong class of item
|
;; wrong class of item
|
||||||
(assert_unlinkable
|
(assert_unlinkable
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "f" (module (import "" "" (global i32))))
|
(export "f" (core module (import "" "" (global i32))))
|
||||||
))
|
))
|
||||||
)
|
)
|
||||||
"expected func found global")
|
"expected func found global")
|
||||||
(assert_unlinkable
|
(assert_unlinkable
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "t" (module (import "" "" (func))))
|
(export "t" (core module (import "" "" (func))))
|
||||||
))
|
))
|
||||||
)
|
)
|
||||||
"expected table found func")
|
"expected table found func")
|
||||||
(assert_unlinkable
|
(assert_unlinkable
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "m" (module (import "" "" (func))))
|
(export "m" (core module (import "" "" (func))))
|
||||||
))
|
))
|
||||||
)
|
)
|
||||||
"expected memory found func")
|
"expected memory found func")
|
||||||
(assert_unlinkable
|
(assert_unlinkable
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "g" (module (import "" "" (func))))
|
(export "g" (core module (import "" "" (func))))
|
||||||
))
|
))
|
||||||
)
|
)
|
||||||
"expected global found func")
|
"expected global found func")
|
||||||
@@ -237,42 +237,42 @@
|
|||||||
(assert_unlinkable
|
(assert_unlinkable
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "f" (module (import "" "" (func (param i32)))))
|
(export "f" (core module (import "" "" (func (param i32)))))
|
||||||
))
|
))
|
||||||
)
|
)
|
||||||
"module import `::` has the wrong type")
|
"module import `::` has the wrong type")
|
||||||
(assert_unlinkable
|
(assert_unlinkable
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "t" (module (import "" "" (table 1 externref))))
|
(export "t" (core module (import "" "" (table 1 externref))))
|
||||||
))
|
))
|
||||||
)
|
)
|
||||||
"module import `::` has the wrong type")
|
"module import `::` has the wrong type")
|
||||||
(assert_unlinkable
|
(assert_unlinkable
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "t" (module (import "" "" (table 0 funcref))))
|
(export "t" (core module (import "" "" (table 0 funcref))))
|
||||||
))
|
))
|
||||||
)
|
)
|
||||||
"module import `::` has the wrong type")
|
"module import `::` has the wrong type")
|
||||||
(assert_unlinkable
|
(assert_unlinkable
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "m" (module (import "" "" (memory 0))))
|
(export "m" (core module (import "" "" (memory 0))))
|
||||||
))
|
))
|
||||||
)
|
)
|
||||||
"module import `::` has the wrong type")
|
"module import `::` has the wrong type")
|
||||||
(assert_unlinkable
|
(assert_unlinkable
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "g" (module (import "" "" (global f32))))
|
(export "g" (core module (import "" "" (global f32))))
|
||||||
))
|
))
|
||||||
)
|
)
|
||||||
"module import `::` has the wrong type")
|
"module import `::` has the wrong type")
|
||||||
(assert_unlinkable
|
(assert_unlinkable
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "g" (module (import "" "" (global (mut i32)))))
|
(export "g" (core module (import "" "" (global (mut i32)))))
|
||||||
))
|
))
|
||||||
)
|
)
|
||||||
"module import `::` has the wrong type")
|
"module import `::` has the wrong type")
|
||||||
@@ -280,45 +280,45 @@
|
|||||||
;; subtyping ok, but in the opposite direction of imports
|
;; subtyping ok, but in the opposite direction of imports
|
||||||
(component
|
(component
|
||||||
(import "foo" (instance
|
(import "foo" (instance
|
||||||
(export "t" (module (import "" "" (table 2 funcref))))
|
(export "t" (core module (import "" "" (table 2 funcref))))
|
||||||
(export "m" (module (import "" "" (memory 2))))
|
(export "m" (core module (import "" "" (memory 2))))
|
||||||
))
|
))
|
||||||
)
|
)
|
||||||
|
|
||||||
;; An instance can reexport a module, define a module, and everything can be
|
;; An instance can reexport a module, define a module, and everything can be
|
||||||
;; used by something else
|
;; used by something else
|
||||||
(component $src
|
(component $src
|
||||||
(module (export "m")
|
(core module (export "m")
|
||||||
(global (export "g") i32 i32.const 2)
|
(global (export "g") i32 i32.const 2)
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
|
||||||
(component $reexport
|
(component $reexport
|
||||||
(module $m1
|
(core module $m1
|
||||||
(global (export "g") i32 i32.const 1)
|
(global (export "g") i32 i32.const 1)
|
||||||
)
|
)
|
||||||
(import "src" (instance $src
|
(import "src" (instance $src
|
||||||
(export "m" (module (export "g" (global i32))))
|
(export "m" (core module (export "g" (global i32))))
|
||||||
))
|
))
|
||||||
|
|
||||||
(module $m3
|
(core module $m3
|
||||||
(global (export "g") i32 i32.const 3)
|
(global (export "g") i32 i32.const 3)
|
||||||
)
|
)
|
||||||
|
|
||||||
(export "m1" (module $m1))
|
(export "m1" (core module $m1))
|
||||||
(export "m2" (module $src "m"))
|
(export "m2" (core module $src "m"))
|
||||||
(export "m3" (module $m3))
|
(export "m3" (core module $m3))
|
||||||
)
|
)
|
||||||
|
|
||||||
(component
|
(component
|
||||||
(type $modulety (module (export "g" (global i32))))
|
(core type $modulety (module (export "g" (global i32))))
|
||||||
(import "reexport" (instance $reexport
|
(import "reexport" (instance $reexport
|
||||||
(export "m1" (module (type $modulety)))
|
(export "m1" (core module (type $modulety)))
|
||||||
(export "m2" (module (type $modulety)))
|
(export "m2" (core module (type $modulety)))
|
||||||
(export "m3" (module (type $modulety)))
|
(export "m3" (core module (type $modulety)))
|
||||||
))
|
))
|
||||||
|
|
||||||
(module $assert_ok
|
(core module $assert_ok
|
||||||
(import "m1" "g" (global $m1 i32))
|
(import "m1" "g" (global $m1 i32))
|
||||||
(import "m2" "g" (global $m2 i32))
|
(import "m2" "g" (global $m2 i32))
|
||||||
(import "m3" "g" (global $m3 i32))
|
(import "m3" "g" (global $m3 i32))
|
||||||
@@ -350,11 +350,11 @@
|
|||||||
(start $assert_ok)
|
(start $assert_ok)
|
||||||
)
|
)
|
||||||
|
|
||||||
(instance $m1 (instantiate (module $reexport "m1")))
|
(core instance $m1 (instantiate (module $reexport "m1")))
|
||||||
(instance $m2 (instantiate (module $reexport "m2")))
|
(core instance $m2 (instantiate (module $reexport "m2")))
|
||||||
(instance $m3 (instantiate (module $reexport "m3")))
|
(core instance $m3 (instantiate (module $reexport "m3")))
|
||||||
|
|
||||||
(instance (instantiate (module $assert_ok)
|
(core instance (instantiate $assert_ok
|
||||||
(with "m1" (instance $m1))
|
(with "m1" (instance $m1))
|
||||||
(with "m2" (instance $m2))
|
(with "m2" (instance $m2))
|
||||||
(with "m3" (instance $m3))
|
(with "m3" (instance $m3))
|
||||||
@@ -364,7 +364,7 @@
|
|||||||
;; order of imports and exports can be shuffled between definition site and
|
;; order of imports and exports can be shuffled between definition site and
|
||||||
;; use-site
|
;; use-site
|
||||||
(component $provider
|
(component $provider
|
||||||
(module (export "m")
|
(core module (export "m")
|
||||||
(import "" "1" (global $i1 i32))
|
(import "" "1" (global $i1 i32))
|
||||||
(import "" "2" (global $i2 i32))
|
(import "" "2" (global $i2 i32))
|
||||||
(import "" "3" (global $i3 i32))
|
(import "" "3" (global $i3 i32))
|
||||||
@@ -413,7 +413,7 @@
|
|||||||
|
|
||||||
(component
|
(component
|
||||||
(import "provider" (instance $provider
|
(import "provider" (instance $provider
|
||||||
(export "m" (module
|
(export "m" (core module
|
||||||
(import "" "4" (global i32))
|
(import "" "4" (global i32))
|
||||||
(import "" "3" (global i32))
|
(import "" "3" (global i32))
|
||||||
(import "" "2" (global i32))
|
(import "" "2" (global i32))
|
||||||
@@ -426,18 +426,18 @@
|
|||||||
))
|
))
|
||||||
))
|
))
|
||||||
|
|
||||||
(module $imports
|
(core module $imports
|
||||||
(global (export "1") i32 (i32.const 1))
|
(global (export "1") i32 (i32.const 1))
|
||||||
(global (export "3") i32 (i32.const 3))
|
(global (export "3") i32 (i32.const 3))
|
||||||
(global (export "2") i32 (i32.const 2))
|
(global (export "2") i32 (i32.const 2))
|
||||||
(global (export "4") i32 (i32.const 4))
|
(global (export "4") i32 (i32.const 4))
|
||||||
)
|
)
|
||||||
(instance $imports (instantiate (module $imports)))
|
(core instance $imports (instantiate $imports))
|
||||||
(instance $m (instantiate (module $provider "m")
|
(core instance $m (instantiate (module $provider "m")
|
||||||
(with "" (instance $imports))
|
(with "" (instance $imports))
|
||||||
))
|
))
|
||||||
|
|
||||||
(module $import_globals
|
(core module $import_globals
|
||||||
(import "" "g4" (global $g4 i32))
|
(import "" "g4" (global $g4 i32))
|
||||||
(import "" "g3" (global $g3 i32))
|
(import "" "g3" (global $g3 i32))
|
||||||
(import "" "g2" (global $g2 i32))
|
(import "" "g2" (global $g2 i32))
|
||||||
@@ -473,5 +473,5 @@
|
|||||||
(start $assert_imports)
|
(start $assert_imports)
|
||||||
)
|
)
|
||||||
|
|
||||||
(instance (instantiate (module $import_globals) (with "" (instance $m))))
|
(core instance (instantiate $import_globals (with "" (instance $m))))
|
||||||
)
|
)
|
||||||
|
|||||||
@@ -1,21 +1,21 @@
|
|||||||
(component)
|
(component)
|
||||||
|
|
||||||
(component
|
(component
|
||||||
(module)
|
(core module)
|
||||||
)
|
)
|
||||||
|
|
||||||
(component
|
(component
|
||||||
(module)
|
(core module)
|
||||||
(module)
|
(core module)
|
||||||
(module)
|
(core module)
|
||||||
)
|
)
|
||||||
|
|
||||||
(component
|
(component
|
||||||
(module
|
(core module
|
||||||
(func (export "a") (result i32) i32.const 0)
|
(func (export "a") (result i32) i32.const 0)
|
||||||
(func (export "b") (result i64) i64.const 0)
|
(func (export "b") (result i64) i64.const 0)
|
||||||
)
|
)
|
||||||
(module
|
(core module
|
||||||
(func (export "c") (result f32) f32.const 0)
|
(func (export "c") (result f32) f32.const 0)
|
||||||
(func (export "d") (result f64) f64.const 0)
|
(func (export "d") (result f64) f64.const 0)
|
||||||
)
|
)
|
||||||
|
|||||||
@@ -52,7 +52,8 @@
|
|||||||
(type $empty (func))
|
(type $empty (func))
|
||||||
(type (func (param string) (result u32)))
|
(type (func (param string) (result u32)))
|
||||||
(type (component))
|
(type (component))
|
||||||
(type (module))
|
(core type (module))
|
||||||
|
(core type (func))
|
||||||
(type (instance))
|
(type (instance))
|
||||||
|
|
||||||
(type (component
|
(type (component
|
||||||
@@ -62,7 +63,7 @@
|
|||||||
|
|
||||||
(type $t (instance))
|
(type $t (instance))
|
||||||
|
|
||||||
(export "a" (module))
|
(export "a" (core module))
|
||||||
(export "b" (instance (type $t)))
|
(export "b" (instance (type $t)))
|
||||||
))
|
))
|
||||||
|
|
||||||
@@ -73,11 +74,11 @@
|
|||||||
|
|
||||||
(type $t (instance))
|
(type $t (instance))
|
||||||
|
|
||||||
(export "a" (module))
|
(export "a" (core module))
|
||||||
(export "b" (instance (type $t)))
|
(export "b" (instance (type $t)))
|
||||||
))
|
))
|
||||||
|
|
||||||
(type (module
|
(core type (module
|
||||||
(import "" "" (func (param i32)))
|
(import "" "" (func (param i32)))
|
||||||
(import "" "1" (func (result i32)))
|
(import "" "1" (func (result i32)))
|
||||||
(export "1" (global i32))
|
(export "1" (global i32))
|
||||||
|
|||||||
Reference in New Issue
Block a user