While loops are a common control flow pattern in programming languages. Lately I've been studying a new language called WebAssembly (WASM). It took me a while to wrap my head around how while loops can be translated to WASM. So I thought it might be helpful to share what I've learned in case someone else runs into similar confusion.
In WASM, there are two types of blocks. A standard
block and a
loop block. Both
loop have a label and a set of instructions to execute. They also both only execute
their instructions once. That's right. A
loop block does not actually loop on its own. Instead,
we use branch instructions.
A branch instruction, such as
br_if, is similar goto statement. Branch instructions are called
with a block label. If the label points to a
loop, the branch will act as a
continue and begin
executing instructions at the top of the loop. If the label points to a
block, the branch will act
break and jump to the end of the
block without executing any instructions.
With that knowledge, a while loop can be described in pseudo wasm like this:
;; Labels start with a $ block $while loop $loop ;; If the while condition is NOT true, we br to the $while block ;; Because $while is a block, this breaks the loop br_if $while <NOT WHILE CONDITION> <LOOP INSTRUCTIONS...> ;; Jump back to the beginning of the loop body br $loop end end
Translating that to binaryen.js, we get this:
import binaryen from "binaryen"; const mod = new binaryen.Module(); mod.block("while", [ mod.loop("loop", [ // Break out of the loop to the bottom of the while block, if the while condition is false mod.br("while", mod.i32.ne( compileSomeCondition(), mod.i32.const(1) )), /* Loop body instructions here */ // Continue at the top of the loop body mod.br("loop") ]) ]); console.log(mod.emitText());
If you found this post helpful, consider following me on twitter @DrewYoungwerth. I'll post links to any new blog posts there, so you can stay up to date.
At the time of writing, the binaryen.js docs
break can be called and mean the same thing to binaryen. Although
I find their usage of the word
break confusing here, so I prefer