@@ -3,10 +3,11 @@ use crate::gc::ReallocScheme;
33use crate :: validation:: {
44 Import , ImportMap , ValidatedModule , validate_adapter_module, validate_module,
55} ;
6- use anyhow:: { Context , Result } ;
6+ use anyhow:: { Context , Result , bail } ;
77use indexmap:: { IndexMap , IndexSet } ;
88use std:: borrow:: Cow ;
99use std:: collections:: { HashMap , HashSet } ;
10+ use wasmparser:: { FuncType , ValType } ;
1011use wit_parser:: {
1112 Function , InterfaceId , LiveTypes , Resolve , TypeDefKind , TypeId , TypeOwner , WorldId , WorldItem ,
1213 WorldKey ,
@@ -86,17 +87,29 @@ impl<'a> ComponentWorld<'a> {
8687
8788 /// Given that there is no realloc function exported from the main module,
8889 /// returns the realloc scheme we should use.
89- fn fallback_realloc_scheme ( & self ) -> ReallocScheme {
90+ ///
91+ /// Return an error if we need to use an exported malloc() and it wasn't
92+ /// there.
93+ fn fallback_realloc_scheme ( & self ) -> Result < ReallocScheme > {
9094 if self . encoder . module_is_produced_by_tiny_go {
9195 // If it appears the module was emitted by TinyGo, we delegate to
9296 // its `malloc()` function. (TinyGo assumes its GC has rein over the
9397 // whole memory and quickly overwrites the adapter's
9498 // `memory.grow`-allocated State struct, causing a crash. So we use
9599 // `malloc()` to inform TinyGo's GC of the memory we use.)
96- ReallocScheme :: Malloc ( "malloc" )
100+ let malloc_type = FuncType :: new ( [ ValType :: I32 ] , [ ValType :: I32 ] ) ;
101+ match self . info . exports . get_func_type ( "malloc" ) {
102+ Some ( func_type) if * func_type == malloc_type => Ok ( ReallocScheme :: Malloc ( "malloc" ) ) ,
103+ Some ( _) => bail ! (
104+ "TinyGo-derived wasm had a malloc() export, but it lacked the expected type of malloc(i32) -> i32"
105+ ) ,
106+ None => bail ! (
107+ "TinyGo-derived wasm lacked a malloc() export; we don't know how else to reserve space for the adapter's state from its GC"
108+ ) ,
109+ }
97110 } else {
98111 // If it's not TinyGo, use `memory.grow` instead.
99- ReallocScheme :: MemoryGrow
112+ Ok ( ReallocScheme :: MemoryGrow )
100113 }
101114 }
102115
@@ -183,11 +196,11 @@ impl<'a> ComponentWorld<'a> {
183196 let realloc = if self . encoder . realloc_via_memory_grow {
184197 // User explicitly requested memory-grow-based realloc. We
185198 // give them that unless it would definitely crash.
186- self . fallback_realloc_scheme ( )
199+ self . fallback_realloc_scheme ( ) ?
187200 } else {
188201 match self . info . exports . realloc_to_import_into_adapter ( ) {
189202 Some ( name) => ReallocScheme :: Realloc ( name) ,
190- None => self . fallback_realloc_scheme ( ) ,
203+ None => self . fallback_realloc_scheme ( ) ? ,
191204 }
192205 } ;
193206 Cow :: Owned (
0 commit comments