Skip to content

Instantly share code, notes, and snippets.

@lukewagner
Last active December 2, 2025 00:02
Show Gist options
  • Select an option

  • Save lukewagner/e18cbfc7b4ef71d4f602613b06716135 to your computer and use it in GitHub Desktop.

Select an option

Save lukewagner/e18cbfc7b4ef71d4f602613b06716135 to your computer and use it in GitHub Desktop.
trapping tests (WIP)
;; This test has two components $C and $D, where $D imports and calls $C.
;; TODO
(component definition $Tester
(component $C
(core module $CM
(func (export "sync-async-func")
unreachable
)
(func (export "async-async-func") (result i32)
unreachable
)
(func (export "async-async-func-cb") (param i32 i32 i32) (result i32)
unreachable
)
)
(core instance $cm (instantiate $CM))
(func (export "sync-async-func") async (canon lift (core func $cm "sync-async-func")))
(func (export "async-async-func") async (canon lift (core func $cm "async-async-func") async (callback (func $cm "async-async-func-cb"))))
)
(component $D
(import "c" (instance $c
(export "sync-async-func" (func async))
(export "async-async-func" (func async))
))
(core module $Memory (memory (export "mem") 1))
(core instance $memory (instantiate $Memory))
(core module $Core
(import "" "mem" (memory 1))
(import "" "task.return" (func $task.return (param i32)))
(import "" "subtask.cancel" (func $subtask.cancel (param i32) (result i32)))
(import "" "waitable.join" (func $waitable.join (param i32 i32)))
(import "" "waitable-set.new" (func $waitable-set.new (result i32)))
(import "" "waitable-set.wait" (func $waitable-set.wait (param i32 i32) (result i32)))
(import "" "waitable-set.poll" (func $waitable-set.poll (param i32 i32) (result i32)))
(import "" "future.read" (func $future.read (param i32 i32) (result i32)))
(import "" "stream.read" (func $stream.read (param i32 i32 i32) (result i32)))
(import "" "await-sync-async-func" (func $await-sync-async-func))
(import "" "await-async-async-func" (func $await-async-async-func))
(func (export "unreachable-cb") (param i32 i32 i32) (result i32)
unreachable
)
(func (export "return-42-cb") (param i32 i32 i32) (result i32)
(call $task.return (i32.const 42))
(i32.const 0 (; EXIT ;))
)
(func (export "trap-if-wait")
(call $waitable-set.wait (call $waitable-set.new) (i32.const 0xdeadbeef))
unreachable
)
(func (export "trap-if-wait-cb") (result i32)
(i32.or
(i32.const 2 (; WAIT ;))
(i32.shl (call $waitable-set.new) (i32.const 4)))
)
(func (export "trap-if-poll")
(call $waitable-set.poll (call $waitable-set.new) (i32.const 0xdeadbeef))
unreachable
)
(func (export "trap-if-poll-cb") (result i32)
(i32.or
(i32.const 3 (; POLL ;))
(i32.shl (call $waitable-set.new) (i32.const 4)))
)
(func (export "yield-is-fine") (result i32)
(i32.or
(i32.const 1 (; YIELD ;))
(i32.shl (i32.const 0xdead) (i32.const 4)))
)
(func (export "trap-if-sync-call-async1")
(call $await-sync-async-func)
)
(func (export "trap-if-sync-call-async2")
(call $await-async-async-func)
)
(func (export "trap-if-sync-cancel")
(call $subtask.cancel (i32.const 0xdeadbeef))
unreachable
)
)
(type $FT (future u8))
(type $ST (stream u8))
(canon task.return (result u32) (core func $task.return))
(canon subtask.cancel (core func $subtask.cancel))
(canon waitable.join (core func $waitable.join))
(canon waitable-set.new (core func $waitable-set.new))
(canon waitable-set.wait (memory $memory "mem") (core func $waitable-set.wait))
(canon waitable-set.poll (memory $memory "mem") (core func $waitable-set.poll))
(canon future.new $FT (core func $future.new))
(canon future.read $FT async (memory $memory "mem") (core func $future.read))
(canon stream.new $ST (core func $stream.new))
(canon stream.read $ST async (memory $memory "mem") (core func $stream.read))
(canon lower (func $c "sync-async-func") (core func $await-sync-async-func'))
(canon lower (func $c "async-async-func") (core func $await-async-async-func'))
(core instance $core (instantiate $Core (with "" (instance
(export "mem" (memory $memory "mem"))
(export "task.return" (func $task.return))
(export "subtask.cancel" (func $subtask.cancel))
(export "waitable.join" (func $waitable.join))
(export "waitable-set.new" (func $waitable-set.new))
(export "waitable-set.wait" (func $waitable-set.wait))
(export "waitable-set.poll" (func $waitable-set.poll))
(export "future.new" (func $future.new))
(export "future.read" (func $future.read))
(export "stream.new" (func $stream.new))
(export "stream.read" (func $stream.read))
(export "await-sync-async-func" (func $await-sync-async-func'))
(export "await-async-async-func" (func $await-async-async-func'))
))))
(func (export "trap-if-wait") (canon lift (core func $core "trap-if-wait")))
(func (export "trap-if-wait-cb") (canon lift (core func $core "trap-if-wait-cb") async (callback (func $core "unreachable-cb"))))
(func (export "trap-if-poll") (canon lift (core func $core "trap-if-poll")))
(func (export "trap-if-poll-cb") (canon lift (core func $core "trap-if-poll-cb") async (callback (func $core "unreachable-cb"))))
(func (export "yield-is-fine") (result u32) (canon lift (core func $core "yield-is-fine") async (callback (func $core "return-42-cb"))))
(func (export "trap-if-sync-call-async1") (canon lift (core func $core "trap-if-sync-call-async1")))
(func (export "trap-if-sync-call-async2") (canon lift (core func $core "trap-if-sync-call-async2")))
(func (export "trap-if-sync-cancel") (canon lift (core func $core "trap-if-sync-cancel")))
)
(instance $c (instantiate $C))
(instance $d (instantiate $D (with "c" (instance $c))))
(func (export "trap-if-wait") (alias export $d "trap-if-wait"))
(func (export "trap-if-wait-cb") (alias export $d "trap-if-wait-cb"))
(func (export "trap-if-poll") (alias export $d "trap-if-poll"))
(func (export "trap-if-poll-cb") (alias export $d "trap-if-poll-cb"))
(func (export "yield-is-fine") (alias export $d "yield-is-fine"))
(func (export "trap-if-sync-call-async1") (alias export $d "trap-if-sync-call-async1"))
(func (export "trap-if-sync-call-async2") (alias export $d "trap-if-sync-call-async2"))
(func (export "trap-if-sync-cancel") (alias export $d "trap-if-sync-cancel"))
)
(component instance $i1 $Tester)
(assert_trap (invoke "trap-if-wait") "cannot block a synchronous task before returning")
(component instance $i2 $Tester)
(assert_trap (invoke "trap-if-wait-cb") "cannot block a synchronous task before returning")
(component instance $i3 $Tester)
(assert_trap (invoke "trap-if-poll") "cannot block a synchronous task before returning")
(component instance $i4 $Tester)
(assert_trap (invoke "trap-if-poll-cb") "cannot block a synchronous task before returning")
(component instance $i5 $Tester)
(assert_return (invoke "yield-is-fine") (u32.const 42))
(component instance $i6 $Tester)
(assert_trap (invoke "trap-if-sync-call-async1") "cannot block a synchronous task before returning")
(component instance $i7 $Tester)
(assert_trap (invoke "trap-if-sync-call-async2") "cannot block a synchronous task before returning")
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment