use crate::func_environ::FuncEnvironment;
use cranelift_codegen::ir;
use cranelift_frontend::FunctionBuilder;
use wasmtime_environ::{GcTypeLayouts, TagIndex, TypeIndex, WasmRefType, WasmResult};
#[cfg(feature = "gc")]
mod enabled;
#[cfg(feature = "gc")]
use enabled as imp;
#[cfg(not(feature = "gc"))]
mod disabled;
#[cfg(not(feature = "gc"))]
use disabled as imp;
pub use imp::*;
#[derive(Clone, Copy)]
#[cfg_attr(not(feature = "gc"), expect(dead_code))]
pub enum ArrayInit<'a> {
Elems(&'a [ir::Value]),
Fill { elem: ir::Value, len: ir::Value },
}
pub trait GcCompiler {
#[cfg_attr(not(feature = "gc"), allow(dead_code))]
fn layouts(&self) -> &dyn GcTypeLayouts;
#[cfg_attr(not(feature = "gc"), allow(dead_code))]
fn alloc_array(
&mut self,
func_env: &mut FuncEnvironment<'_>,
builder: &mut FunctionBuilder<'_>,
array_type_index: TypeIndex,
init: ArrayInit<'_>,
) -> WasmResult<ir::Value>;
#[cfg_attr(not(feature = "gc"), allow(dead_code))]
fn alloc_struct(
&mut self,
func_env: &mut FuncEnvironment<'_>,
builder: &mut FunctionBuilder<'_>,
struct_type_index: TypeIndex,
fields: &[ir::Value],
) -> WasmResult<ir::Value>;
#[cfg_attr(not(feature = "gc"), allow(dead_code))]
fn alloc_exn(
&mut self,
func_env: &mut FuncEnvironment<'_>,
builder: &mut FunctionBuilder<'_>,
tag_index: TagIndex,
fields: &[ir::Value],
instance_id: ir::Value,
tag: ir::Value,
) -> WasmResult<ir::Value>;
fn translate_read_gc_reference(
&mut self,
func_env: &mut FuncEnvironment<'_>,
builder: &mut FunctionBuilder,
ty: WasmRefType,
src: ir::Value,
flags: ir::MemFlags,
) -> WasmResult<ir::Value>;
fn translate_write_gc_reference(
&mut self,
func_env: &mut FuncEnvironment<'_>,
builder: &mut FunctionBuilder,
ty: WasmRefType,
dst: ir::Value,
new_val: ir::Value,
flags: ir::MemFlags,
) -> WasmResult<()>;
}
pub mod builtins {
use super::*;
macro_rules! define_builtin_accessors {
( $( $name:ident , )* ) => {
$(
#[inline]
pub fn $name(
func_env: &mut FuncEnvironment<'_>,
func: &mut ir::Function,
) -> WasmResult<ir::FuncRef> {
#[cfg(feature = "gc")]
{
func_env.needs_gc_heap = true;
return Ok(func_env.builtin_functions.$name(func));
}
#[cfg(not(feature = "gc"))]
{
let _ = (func, func_env);
return Err(wasmtime_environ::wasm_unsupported!(
"support for Wasm GC disabled at compile time because the `gc` cargo \
feature was not enabled"
));
}
}
)*
};
}
define_builtin_accessors! {
table_grow_gc_ref,
table_fill_gc_ref,
array_new_data,
array_new_elem,
array_copy,
array_init_data,
array_init_elem,
}
}