pub struct Module { /* private fields */ }
Expand description
A compiled WebAssembly module, ready to be instantiated.
A Module
is a compiled in-memory representation of an input WebAssembly
binary. A Module
is then used to create an Instance
through an instantiation process. You cannot call functions or fetch
globals, for example, on a Module
because it’s purely a code
representation. Instead you’ll need to create an
Instance
to interact with the wasm module.
Creating a Module
currently involves compiling code, meaning that it can
be an expensive operation. All Module
instances are compiled according to
the configuration in Config
, but typically they’re JIT-compiled. If
you’d like to instantiate a module multiple times you can do so with
compiling the original wasm module only once with a single Module
instance.
The Module
is threadsafe and safe to share accross threads.
Modules and Clone
Using clone
on a Module
is a cheap operation. It will not create an
entirely new module, but rather just a new reference to the existing module.
In other words it’s a shallow copy, not a deep copy.
Examples
There are a number of ways you can create a Module
, for example pulling
the bytes from a number of locations. One example is loading a module from
the filesystem:
let engine = Engine::default();
let module = Module::from_file(&engine, "path/to/foo.wasm")?;
You can also load the wasm text format if more convenient too:
let engine = Engine::default();
// Now we're using the WebAssembly text extension: `.wat`!
let module = Module::from_file(&engine, "path/to/foo.wat")?;
And if you’ve already got the bytes in-memory you can use the
Module::new
constructor:
let engine = Engine::default();
let module = Module::new(&engine, &wasm_bytes)?;
// It also works with the text format!
let module = Module::new(&engine, "(module (func))")?;
Implementations
sourceimpl Module
impl Module
sourcepub fn new(engine: &Engine, bytes: impl AsRef<[u8]>) -> Result<Module>
pub fn new(engine: &Engine, bytes: impl AsRef<[u8]>) -> Result<Module>
Creates a new WebAssembly Module
from the given in-memory bytes
.
The bytes
provided must be in one of two formats:
- It can be a binary-encoded WebAssembly module. This is always supported.
- It may also be a text-encoded instance of the WebAssembly
text format. This is only supported when the
wat
feature of this crate is enabled. If this is supplied then the text format will be parsed before validation. Note that thewat
feature is enabled by default.
The data for the wasm module must be loaded in-memory if it’s present elsewhere, for example on disk. This requires that the entire binary is loaded into memory all at once, this API does not support streaming compilation of a module.
The WebAssembly binary will be decoded and validated. It will also be
compiled according to the configuration of the provided engine
.
Errors
This function may fail and return an error. Errors may include situations such as:
- The binary provided could not be decoded because it’s not a valid WebAssembly binary
- The WebAssembly binary may not validate (e.g. contains type errors)
- Implementation-specific limits were exceeded with a valid binary (for example too many locals)
- The wasm binary may use features that are not enabled in the
configuration of
enging
- If the
wat
feature is enabled and the input is text, then it may be rejected if it fails to parse.
The error returned should contain full information about why module creation failed if one is returned.
Examples
The new
function can be invoked with a in-memory array of bytes:
let module = Module::new(&engine, &wasm_bytes)?;
Or you can also pass in a string to be parsed as the wasm text format:
let module = Module::new(&engine, "(module (func))")?;
sourcepub fn new_with_name(
engine: &Engine,
bytes: impl AsRef<[u8]>,
name: &str
) -> Result<Module>
pub fn new_with_name(
engine: &Engine,
bytes: impl AsRef<[u8]>,
name: &str
) -> Result<Module>
Creates a new WebAssembly Module
from the given in-memory binary
data. The provided name
will be used in traps/backtrace details.
See Module::new
for other details.
sourcepub fn from_file(engine: &Engine, file: impl AsRef<Path>) -> Result<Module>
pub fn from_file(engine: &Engine, file: impl AsRef<Path>) -> Result<Module>
Creates a new WebAssembly Module
from the contents of the given
file
on disk.
This is a convenience function that will read the file
provided and
pass the bytes to the Module::new
function. For more information
see Module::new
Examples
let engine = Engine::default();
let module = Module::from_file(&engine, "./path/to/foo.wasm")?;
The .wat
text format is also supported:
let module = Module::from_file(&engine, "./path/to/foo.wat")?;
sourcepub fn from_binary(engine: &Engine, binary: &[u8]) -> Result<Module>
pub fn from_binary(engine: &Engine, binary: &[u8]) -> Result<Module>
Creates a new WebAssembly Module
from the given in-memory binary
data.
This is similar to Module::new
except that it requires that the
binary
input is a WebAssembly binary, the text format is not supported
by this function. It’s generally recommended to use Module::new
,
but if it’s required to not support the text format this function can be
used instead.
Examples
let wasm = b"\0asm\x01\0\0\0";
let module = Module::from_binary(&engine, wasm)?;
Note that the text format is not accepted by this function:
assert!(Module::from_binary(&engine, b"(module)").is_err());
sourcepub fn validate(engine: &Engine, binary: &[u8]) -> Result<()>
pub fn validate(engine: &Engine, binary: &[u8]) -> Result<()>
Validates binary
input data as a WebAssembly binary given the
configuration in engine
.
This function will perform a speedy validation of the binary
input
WebAssembly module (which is in binary form, the text format
is not accepted by this function) and return either Ok
or Err
depending on the results of validation. The engine
argument indicates
configuration for WebAssembly features, for example, which are used to
indicate what should be valid and what shouldn’t be.
Validation automatically happens as part of Module::new
.
Errors
If validation fails for any reason (type check error, usage of a feature that wasn’t enabled, etc) then an error with a description of the validation issue will be returned.
sourcepub fn ty(&self) -> ModuleType
pub fn ty(&self) -> ModuleType
Returns the type signature of this module.
sourcepub fn serialize(&self) -> Result<Vec<u8>>
pub fn serialize(&self) -> Result<Vec<u8>>
Serialize compilation artifacts to the buffer. See also deseriaize
.
sourcepub fn deserialize(engine: &Engine, serialized: &[u8]) -> Result<Module>
pub fn deserialize(engine: &Engine, serialized: &[u8]) -> Result<Module>
Deserializes and creates a module from the compilation artifacts.
The serialize
saves the compilation artifacts along with the host
fingerprint, which consists of target, compiler flags, and wasmtime
package version.
The method will fail if fingerprints of current host and serialized one are different. The method does not verify the serialized artifacts for modifications or curruptions. All responsibily of signing and its verification falls on the embedder.
sourcepub fn name(&self) -> Option<&str>
pub fn name(&self) -> Option<&str>
Returns identifier/name that this Module
has. This name
is used in traps/backtrace details.
Note that most LLVM/clang/Rust-produced modules do not have a name associated with them, but other wasm tooling can be used to inject or add a name.
Examples
let module = Module::new(&engine, "(module $foo)")?;
assert_eq!(module.name(), Some("foo"));
let module = Module::new(&engine, "(module)")?;
assert_eq!(module.name(), None);
let module = Module::new_with_name(&engine, "(module)", "bar")?;
assert_eq!(module.name(), Some("bar"));
sourcepub fn imports<'module>(
&'module self
) -> impl ExactSizeIterator<Item = ImportType<'module>> + 'module
pub fn imports<'module>(
&'module self
) -> impl ExactSizeIterator<Item = ImportType<'module>> + 'module
Returns the list of imports that this Module
has and must be
satisfied.
This function returns the list of imports that the wasm module has, but
only the types of each import. The type of each import is used to
typecheck the Instance::new
method’s imports
argument. The arguments to that function must match up 1-to-1 with the
entries in the array returned here.
The imports returned reflect the order of the imports in the wasm module itself, and note that no form of deduplication happens.
Examples
Modules with no imports return an empty list here:
let module = Module::new(&engine, "(module)")?;
assert_eq!(module.imports().len(), 0);
and modules with imports will have a non-empty list:
let wat = r#"
(module
(import "host" "foo" (func))
)
"#;
let module = Module::new(&engine, wat)?;
assert_eq!(module.imports().len(), 1);
let import = module.imports().next().unwrap();
assert_eq!(import.module(), "host");
assert_eq!(import.name(), Some("foo"));
match import.ty() {
ExternType::Func(_) => { /* ... */ }
_ => panic!("unexpected import type!"),
}
sourcepub fn exports<'module>(
&'module self
) -> impl ExactSizeIterator<Item = ExportType<'module>> + 'module
pub fn exports<'module>(
&'module self
) -> impl ExactSizeIterator<Item = ExportType<'module>> + 'module
Returns the list of exports that this Module
has and will be
available after instantiation.
This function will return the type of each item that will be returned
from Instance::exports
. Each entry in this
list corresponds 1-to-1 with that list, and the entries here will
indicate the name of the export along with the type of the export.
Examples
Modules might not have any exports:
let module = Module::new(&engine, "(module)")?;
assert!(module.exports().next().is_none());
When the exports are not empty, you can inspect each export:
let wat = r#"
(module
(func (export "foo"))
(memory (export "memory") 1)
)
"#;
let module = Module::new(&engine, wat)?;
assert_eq!(module.exports().len(), 2);
let mut exports = module.exports();
let foo = exports.next().unwrap();
assert_eq!(foo.name(), "foo");
match foo.ty() {
ExternType::Func(_) => { /* ... */ }
_ => panic!("unexpected export type!"),
}
let memory = exports.next().unwrap();
assert_eq!(memory.name(), "memory");
match memory.ty() {
ExternType::Memory(_) => { /* ... */ }
_ => panic!("unexpected export type!"),
}
sourcepub fn get_export<'module>(
&'module self,
name: &'module str
) -> Option<ExternType>
pub fn get_export<'module>(
&'module self,
name: &'module str
) -> Option<ExternType>
Looks up an export in this Module
by name.
This function will return the type of an export with the given name.
Examples
There may be no export with that name:
let module = Module::new(&engine, "(module)")?;
assert!(module.get_export("foo").is_none());
When there is an export with that name, it is returned:
let wat = r#"
(module
(func (export "foo"))
(memory (export "memory") 1)
)
"#;
let module = Module::new(&engine, wat)?;
let foo = module.get_export("foo");
assert!(foo.is_some());
let foo = foo.unwrap();
match foo {
ExternType::Func(_) => { /* ... */ }
_ => panic!("unexpected export type!"),
}
Trait Implementations
Auto Trait Implementations
impl !RefUnwindSafe for Module
impl Send for Module
impl Sync for Module
impl Unpin for Module
impl !UnwindSafe for Module
Blanket Implementations
sourceimpl<T> BorrowMut<T> for T where
T: ?Sized,
impl<T> BorrowMut<T> for T where
T: ?Sized,
const: unstable · sourcepub fn borrow_mut(&mut self) -> &mut T
pub fn borrow_mut(&mut self) -> &mut T
Mutably borrows from an owned value. Read more
sourceimpl<T> Pointable for T
impl<T> Pointable for T
sourceimpl<T> ToOwned for T where
T: Clone,
impl<T> ToOwned for T where
T: Clone,
type Owned = T
type Owned = T
The resulting type after obtaining ownership.
sourcepub fn to_owned(&self) -> T
pub fn to_owned(&self) -> T
Creates owned data from borrowed data, usually by cloning. Read more
sourcepub fn clone_into(&self, target: &mut T)
pub fn clone_into(&self, target: &mut T)
toowned_clone_into
)Uses borrowed data to replace owned data, usually by cloning. Read more