Fix allocator lookup for anonymous WASM modules#2
Conversation
FunctionDefinition.Name() returns empty string for modules instantiated
with WithName("") (anonymous), causing ExportedFunction("") to return
nil even though cabi_realloc is exported. This silently broke all string
parameter encoding for core WASM modules.
Fix: use the export name map key instead of FunctionDefinition.Name()
when looking up the allocator function.
Also add null pointer guards on cabi_realloc return values to surface
allocation failures early instead of passing ptr=0 to the WASM module,
which causes NonNull::new_unchecked panics in Rust bindings.
There was a problem hiding this comment.
Pull request overview
Fixes allocator resolution for anonymous core WASM module instances (e.g., instantiated with an empty module name) and adds explicit null-pointer guards to fail fast when cabi_realloc returns 0 for non-zero allocations.
Changes:
- Fix allocator caching to look up
cabi_reallocvia the export-map key rather thanFunctionDefinition.Name()(which can be empty for anonymous modules). - Add
ptr==0 && size>0guards in allocator wrappers to surface allocation failures early. - Add regression tests for anonymous-module allocator lookup and null allocator behavior (plus a couple of small builder formatting refactors).
Reviewed changes
Copilot reviewed 7 out of 7 changed files in this pull request and generated 1 comment.
Show a summary per file
| File | Description |
|---|---|
engine/wazero.go |
Fix allocator lookup for anonymous modules; add null-pointer allocation guards. |
engine/allocator_lookup_test.go |
New regression tests covering anonymous-module allocator lookup and null allocator return handling. |
linker/internal/memory/wrapper.go |
Add null-pointer guard in AllocatorWrapper.Alloc. |
linker/internal/memory/wrapper_test.go |
Add test ensuring null allocator return becomes an error for non-zero size. |
errors/errors.go |
Refactor builder formatting to avoid fmt.Sprintf allocation. |
cmd/run/interactive.go |
Refactor builder formatting to avoid fmt.Sprintf allocation. |
transcoder/internal/types/kind_test.go |
Remove //nolint:revive from package declaration. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
| package engine | ||
|
|
||
| import ( | ||
| "context" | ||
| "testing" | ||
|
|
||
| "github.com/wippyai/wasm-runtime/wat" | ||
| "go.bytecodealliance.org/wit" | ||
| ) |
There was a problem hiding this comment.
PR description (Summary/Files Changed) doesn't mention the addition of this new engine-level test file (and there are also unrelated formatting changes in other packages). Please update the PR description to reflect all modified files, or split the non-allocator changes into a separate PR to keep the scope focused.
Summary
cabi_realloclookup returning nil for core WASM modules instantiated withWithName("")(anonymous)Root Cause
When a core WASM module is instantiated anonymously via
wazero.NewModuleConfig().WithName(""), wazero'sFunctionDefinition.Name()returns an empty string instead of the export name. The allocator caching code was doing:This caused
allocFnto be silently nil, making every string parameter encoding fail with "failed to allocate N bytes for string data".Fix
Use the map key (the export name we searched for) for
ExportedFunctionlookup instead ofFunctionDefinition.Name():Also added null pointer checks on
cabi_reallocreturn values in bothwazeroAllocator.AllocandAllocatorWrapper.Allocto surface allocation failures early instead of passing ptr=0 to the WASM guest (which causesNonNull::new_uncheckedpanics in Rust wit-bindgen bindings).Reproduction
Any core WASM module (non-component) with string parameters compiled from Rust using
wit-bindgenwould fail. For example, a module exportinghtml-to-markdown: func(html: string) -> stringbuilt withscraper/html5everwould crash with:Files Changed
engine/wazero.go— allocator lookup fix + null pointer guards inwazeroAllocator.Alloclinker/internal/memory/wrapper.go— null pointer guard inAllocatorWrapper.Alloc