tor-browser

The Tor Browser
git clone https://git.dasho.dev/tor-browser.git
Log | Files | Refs | README | LICENSE

litmus3.js (1355B)


      1 // Mutually recursive functions implement a multi-entry loop using tail calls,
      2 // with exception handling.
      3 //
      4 // The functions do not have the same signatures, so if all arguments are stack
      5 // arguments then these use different amounts of stack space.
      6 //
      7 // The "even" function will throw when the input is zero, so when an exception
      8 // bubbles out of return_call it must not be caught by the exception handler in
      9 // "odd", but must instead be delegated to the caller, which is JS code.
     10 
     11 var ins = wasmEvalText(`
     12 (module
     13  (tag $t)
     14  (func $odd (export "odd") (param $n i32) (param $dummy i32) (result i32)
     15    try (result i32)
     16    (if (result i32) (i32.eqz (local.get $n))
     17        (then (return (i32.const 0)))
     18        (else (return_call $even (i32.sub (local.get $n) (i32.const 1)))))
     19    catch_all
     20      unreachable
     21    end)
     22 
     23  (func $even (export "even") (param $n i32) (result i32)
     24    (if (result i32) (i32.eqz (local.get $n))
     25        (then (throw $t))
     26        (else (return_call $odd (i32.sub (local.get $n) (i32.const 1)) (i32.const 33)))))
     27 )
     28 `);
     29 
     30 assertErrorMessage(() => ins.exports.even(TailCallIterations), WebAssembly.Exception, /.*/);
     31 assertEq(ins.exports.odd(TailCallIterations, 33), 0);
     32 
     33 assertEq(ins.exports.even(TailCallIterations+1), 0);
     34 assertErrorMessage(() => ins.exports.odd(TailCallIterations+1, 33), WebAssembly.Exception, /.*/);