Is it a strawberry, see boyanio/wasm-wheel#2

This commit is contained in:
dcodeIO
2017-12-13 00:11:45 +01:00
parent 3d544c2fe5
commit ce57820f59
20 changed files with 399 additions and 472 deletions

View File

@ -1,57 +0,0 @@
<canvas id="canvas" width="640" height="480"></canvas>
<script src="../../node_modules/binaryen/index.js"></script><script>
// Fetch the .wast (just because we dont's store the .wasm in git)
fetch("game-of-life.optimized.wast").then(response => response.text()).then(text => {
// Convert it to binary format
var binary = Binaryen.parseText(text).emitBinary();
// Instantiate the module
var module = new WebAssembly.Module(binary);
var instance = new WebAssembly.Instance(module, { /* no imports */ });
// Set up the canvas with a 2D rendering context
var cnv = document.getElementById("canvas");
var ctx = cnv.getContext("2d");
var w = cnv.width,
h = cnv.height,
s = w * h, // memory required to store either input or output
S = s + s; // total memory required to store input and output
// Grow the (exported) memory if its size isn't sufficient
var memory = instance.exports.memory;
if (memory.buffer.byteLength < S)
memory.grow(Math.ceil((S - memory.buffer.byteLength) / 65536));
// Initialize with width and height
instance.exports.init(w, h);
// Fill input at [0, s-1] with random live cells
var mem = new Uint8Array(memory.buffer);
for (var y = 0; y < h; ++y)
for (var x = 0; x < w; ++x)
mem[y * w + x] = Math.random() > 0.1 ? 0 : 1;
// Update about 30 times a second
(function update() {
setTimeout(update, 33);
instance.exports.step();
mem.set(mem.subarray(s, S), 0); // copy output -> input
})();
// Keep rendering the output at [s, 2*s-1]
(function render() {
requestAnimationFrame(render);
ctx.clearRect(0, 0, w, h);
ctx.fillStyle = "#333";
for (var y = 0; y < h; ++y)
for (var x = 0; x < w; ++x)
if (mem[s + y * w + x])
ctx.fillRect(x, y, 1, 1);
})();
}).catch(err => {
throw err;
});
</script>

View File

@ -1,277 +0,0 @@
(module
(type $iiv (func (param i32 i32)))
(type $v (func))
(global $game-of-life/w (mut i32) (i32.const 0))
(global $game-of-life/h (mut i32) (i32.const 0))
(global $game-of-life/s (mut i32) (i32.const 0))
(memory $0 1)
(export "init" (func $game-of-life/init))
(export "step" (func $game-of-life/step))
(export "memory" (memory $0))
(func $game-of-life/init (; 0 ;) (type $iiv) (param $0 i32) (param $1 i32)
(set_global $game-of-life/w
(get_local $0)
)
(set_global $game-of-life/h
(get_local $1)
)
(set_global $game-of-life/s
(i32.mul
(get_global $game-of-life/w)
(get_global $game-of-life/h)
)
)
)
(func $game-of-life/step (; 1 ;) (type $v)
(local $0 i32)
(local $1 i32)
(local $2 i32)
(local $3 i32)
(local $4 i32)
(local $5 i32)
(local $6 i32)
(local $7 i32)
(set_local $6
(i32.sub
(get_global $game-of-life/h)
(i32.const 1)
)
)
(set_local $7
(i32.sub
(get_global $game-of-life/w)
(i32.const 1)
)
)
(set_local $0
(i32.const 0)
)
(loop $continue|0
(if
(i32.lt_u
(get_local $0)
(get_global $game-of-life/h)
)
(block
(set_local $4
(select
(i32.sub
(get_local $0)
(i32.const 1)
)
(get_local $6)
(get_local $0)
)
)
(set_local $5
(select
(i32.const 0)
(i32.add
(get_local $0)
(i32.const 1)
)
(i32.eq
(get_local $0)
(get_local $6)
)
)
)
(set_local $1
(i32.const 0)
)
(loop $continue|1
(if
(i32.lt_u
(get_local $1)
(get_global $game-of-life/w)
)
(block
(set_local $2
(i32.add
(i32.add
(i32.add
(i32.add
(i32.add
(i32.add
(i32.add
(i32.load8_u
(i32.add
(i32.mul
(get_local $4)
(get_global $game-of-life/w)
)
(tee_local $2
(select
(i32.sub
(get_local $1)
(i32.const 1)
)
(get_local $7)
(get_local $1)
)
)
)
)
(i32.load8_u
(i32.add
(i32.mul
(get_local $4)
(get_global $game-of-life/w)
)
(get_local $1)
)
)
)
(i32.load8_u
(i32.add
(i32.mul
(get_local $4)
(get_global $game-of-life/w)
)
(tee_local $3
(select
(i32.const 0)
(i32.add
(get_local $1)
(i32.const 1)
)
(i32.eq
(get_local $1)
(get_local $7)
)
)
)
)
)
)
(i32.load8_u
(i32.add
(i32.mul
(get_local $0)
(get_global $game-of-life/w)
)
(get_local $2)
)
)
)
(i32.load8_u
(i32.add
(i32.mul
(get_local $0)
(get_global $game-of-life/w)
)
(get_local $3)
)
)
)
(i32.load8_u
(i32.add
(i32.mul
(get_local $5)
(get_global $game-of-life/w)
)
(get_local $2)
)
)
)
(i32.load8_u
(i32.add
(i32.mul
(get_local $5)
(get_global $game-of-life/w)
)
(get_local $1)
)
)
)
(i32.load8_u
(i32.add
(i32.mul
(get_local $5)
(get_global $game-of-life/w)
)
(get_local $3)
)
)
)
)
(if
(i32.load8_u
(i32.add
(i32.mul
(get_local $0)
(get_global $game-of-life/w)
)
(get_local $1)
)
)
(if
(if (result i32)
(tee_local $3
(i32.lt_u
(get_local $2)
(i32.const 2)
)
)
(get_local $3)
(i32.gt_u
(get_local $2)
(i32.const 3)
)
)
(i32.store8
(i32.add
(i32.add
(get_global $game-of-life/s)
(i32.mul
(get_local $0)
(get_global $game-of-life/w)
)
)
(get_local $1)
)
(i32.const 0)
)
)
(if
(i32.eq
(get_local $2)
(i32.const 3)
)
(i32.store8
(i32.add
(i32.add
(get_global $game-of-life/s)
(i32.mul
(get_local $0)
(get_global $game-of-life/w)
)
)
(get_local $1)
)
(i32.const 1)
)
)
)
(set_local $1
(i32.add
(get_local $1)
(i32.const 1)
)
)
(br $continue|1)
)
)
)
(set_local $0
(i32.add
(get_local $0)
(i32.const 1)
)
)
(br $continue|0)
)
)
)
)
)

View File

@ -1,40 +0,0 @@
// A simplified version of the game of life as seen on http://dcode.io
let w: u32; // width
let h: u32; // height
let s: u32; // total size
/** Initializes width and height. */
export function init(w_: u32, h_: u32): void {
w = w_;
h = h_;
s = w * h;
}
/** Performs one step. */
export function step(): void {
let y: u32, ym1: u32, yp1: u32; // y, y-1 and y+1
let x: u32, xm1: u32, xp1: u32; // x, x-1 and x+1
let hm1: u32 = h - 1, wm1: u32 = w - 1;
let n: u32, v: u8, c: u32 = 0;
for (y = 0; y < h; ++y) {
ym1 = select<u32>(hm1, y - 1, y == 0);
yp1 = select<u32>(0, y + 1, y == hm1);
for (x = 0; x < w; ++x) {
xm1 = select<u32>(wm1, x - 1, x == 0);
xp1 = select<u32>(0, x + 1, x == wm1);
n = load<u8>(ym1 * w + xm1) + load<u8>(ym1 * w + x) + load<u8>(ym1 * w + xp1)
+ load<u8>(y * w + xm1) + load<u8>(y * w + xp1)
+ load<u8>(yp1 * w + xm1) + load<u8>(yp1 * w + x) + load<u8>(yp1 * w + xp1);
v = load<u8>(y * w + x);
if (v) {
if (n < 2 || n > 3)
store<u8>(s + y * w + x, 0);
} else if (n == 3)
store<u8>(s + y * w + x, 1);
}
}
}
// Performing a step uses bytes [0, s-1] as the input and writes the output to [s, 2*s-1].
// Note that the code above wastes a lot of space by using one byte per cell.

View File

@ -1,349 +0,0 @@
(module
(type $iiv (func (param i32 i32)))
(type $v (func))
(global $game-of-life/w (mut i32) (i32.const 0))
(global $game-of-life/h (mut i32) (i32.const 0))
(global $game-of-life/s (mut i32) (i32.const 0))
(global $HEAP_START i32 (i32.const 4))
(memory $0 1)
(export "init" (func $game-of-life/init))
(export "step" (func $game-of-life/step))
(export "memory" (memory $0))
(func $game-of-life/init (; 0 ;) (type $iiv) (param $0 i32) (param $1 i32)
(set_global $game-of-life/w
(get_local $0)
)
(set_global $game-of-life/h
(get_local $1)
)
(set_global $game-of-life/s
(i32.mul
(get_global $game-of-life/w)
(get_global $game-of-life/h)
)
)
)
(func $game-of-life/step (; 1 ;) (type $v)
(local $0 i32)
(local $1 i32)
(local $2 i32)
(local $3 i32)
(local $4 i32)
(local $5 i32)
(local $6 i32)
(local $7 i32)
(local $8 i32)
(local $9 i32)
(local $10 i32)
(local $11 i32)
(nop)
(nop)
(block
(set_local $6
(i32.sub
(get_global $game-of-life/h)
(i32.const 1)
)
)
(set_local $7
(i32.sub
(get_global $game-of-life/w)
(i32.const 1)
)
)
)
(block
(set_local $10
(i32.const 0)
)
)
(block $break|0
(set_local $0
(i32.const 0)
)
(loop $continue|0
(if
(i32.lt_u
(get_local $0)
(get_global $game-of-life/h)
)
(block
(block
(set_local $1
(select
(get_local $6)
(i32.sub
(get_local $0)
(i32.const 1)
)
(i32.eq
(get_local $0)
(i32.const 0)
)
)
)
(set_local $2
(select
(i32.const 0)
(i32.add
(get_local $0)
(i32.const 1)
)
(i32.eq
(get_local $0)
(get_local $6)
)
)
)
(block $break|1
(set_local $3
(i32.const 0)
)
(loop $continue|1
(if
(i32.lt_u
(get_local $3)
(get_global $game-of-life/w)
)
(block
(block
(set_local $4
(select
(get_local $7)
(i32.sub
(get_local $3)
(i32.const 1)
)
(i32.eq
(get_local $3)
(i32.const 0)
)
)
)
(set_local $5
(select
(i32.const 0)
(i32.add
(get_local $3)
(i32.const 1)
)
(i32.eq
(get_local $3)
(get_local $7)
)
)
)
(set_local $8
(i32.add
(i32.add
(i32.add
(i32.add
(i32.add
(i32.add
(i32.add
(i32.load8_u
(i32.add
(i32.mul
(get_local $1)
(get_global $game-of-life/w)
)
(get_local $4)
)
)
(i32.load8_u
(i32.add
(i32.mul
(get_local $1)
(get_global $game-of-life/w)
)
(get_local $3)
)
)
)
(i32.load8_u
(i32.add
(i32.mul
(get_local $1)
(get_global $game-of-life/w)
)
(get_local $5)
)
)
)
(i32.load8_u
(i32.add
(i32.mul
(get_local $0)
(get_global $game-of-life/w)
)
(get_local $4)
)
)
)
(i32.load8_u
(i32.add
(i32.mul
(get_local $0)
(get_global $game-of-life/w)
)
(get_local $5)
)
)
)
(i32.load8_u
(i32.add
(i32.mul
(get_local $2)
(get_global $game-of-life/w)
)
(get_local $4)
)
)
)
(i32.load8_u
(i32.add
(i32.mul
(get_local $2)
(get_global $game-of-life/w)
)
(get_local $3)
)
)
)
(i32.load8_u
(i32.add
(i32.mul
(get_local $2)
(get_global $game-of-life/w)
)
(get_local $5)
)
)
)
)
(set_local $9
(i32.load8_u
(i32.add
(i32.mul
(get_local $0)
(get_global $game-of-life/w)
)
(get_local $3)
)
)
)
(if
(get_local $9)
(if
(if (result i32)
(tee_local $11
(i32.lt_u
(get_local $8)
(i32.const 2)
)
)
(get_local $11)
(i32.gt_u
(get_local $8)
(i32.const 3)
)
)
(i32.store8
(i32.add
(i32.add
(get_global $game-of-life/s)
(i32.mul
(get_local $0)
(get_global $game-of-life/w)
)
)
(get_local $3)
)
(i32.const 0)
)
)
(if
(i32.eq
(get_local $8)
(i32.const 3)
)
(i32.store8
(i32.add
(i32.add
(get_global $game-of-life/s)
(i32.mul
(get_local $0)
(get_global $game-of-life/w)
)
)
(get_local $3)
)
(i32.const 1)
)
)
)
)
(set_local $3
(i32.add
(get_local $3)
(i32.const 1)
)
)
(br $continue|1)
)
)
)
)
)
(set_local $0
(i32.add
(get_local $0)
(i32.const 1)
)
)
(br $continue|0)
)
)
)
)
)
)
(;
[program.elements]
clz
ctz
popcnt
rotl
rotr
abs
ceil
copysign
floor
max
min
nearest
sqrt
trunc
current_memory
grow_memory
unreachable
load
store
reinterpret
select
sizeof
changetype
isNaN
isFinite
assert
parseInt
parseFloat
game-of-life/w
game-of-life/h
game-of-life/s
game-of-life/init
game-of-life/step
[program.exports]
game-of-life/init
game-of-life/step
;)

File diff suppressed because it is too large Load Diff

View File

@ -1,189 +0,0 @@
let lo: u32;
let hi: u32;
export function getLo(): u32 {
return lo;
}
export function getHi(): u32 {
return hi;
}
function clz_(loLeft: u32, hiLeft: u32): void {
const ret: u64 = clz<u64>(<u64>loLeft | <u64>hiLeft << 32);
lo = <u32>ret;
hi = 0;
}
export { clz_ as clz };
function ctz_(loLeft: u32, hiLeft: u32): void {
const ret: u64 = ctz<u64>(<u64>loLeft | <u64>hiLeft << 32);
lo = <u32>ret;
hi = 0;
}
export { ctz_ as ctz };
function popcnt_(loLeft: u32, hiLeft: u32): void {
const ret: u64 = popcnt<u64>(<u64>loLeft | <u64>hiLeft << 32);
lo = <u32>ret;
hi = 0;
}
export { popcnt_ as popcnt };
export function eqz(loLeft: u32, hiLeft: u32): void {
const ret: bool = !(<u64>loLeft | <u64>hiLeft << 32);
lo = <u32>ret;
hi = 0;
}
export function add(loLeft: u32, hiLeft: u32, loRight: u32, hiRight: u32): void {
const ret: u64 = (<u64>loLeft | <u64>hiLeft << 32) + (<u64>loRight | <u64>hiRight << 32);
lo = <u32>ret;
hi = <u32>(ret >> 32);
}
export function sub(loLeft: u32, hiLeft: u32, loRight: u32, hiRight: u32): void {
const ret: u64 = (<u64>loLeft | <u64>hiLeft << 32) - (<u64>loRight | <u64>hiRight << 32);
lo = <u32>ret;
hi = <u32>(ret >> 32);
}
export function mul(loLeft: u32, hiLeft: u32, loRight: u32, hiRight: u32): void {
const ret: u64 = (<u64>loLeft | <u64>hiLeft << 32) * (<u64>loRight | <u64>hiRight << 32);
lo = <u32>ret;
hi = <u32>(ret >> 32);
}
export function div_s(loLeft: u32, hiLeft: u32, loRight: u32, hiRight: u32): void {
const ret: u64 = <u64>(<i64>(<u64>loLeft | <u64>hiLeft << 32) / <i64>(<u64>loRight | <u64>hiRight << 32));
lo = <u32>ret;
hi = <u32>(ret >> 32);
}
export function div_u(loLeft: u32, hiLeft: u32, loRight: u32, hiRight: u32): void {
const ret: u64 = (<u64>loLeft | <u64>hiLeft << 32) / (<u64>loRight | <u64>hiRight << 32);
lo = <u32>ret;
hi = <u32>(ret >> 32);
}
export function rem_s(loLeft: u32, hiLeft: u32, loRight: u32, hiRight: u32): void {
const ret: u64 = <u64>(<i64>(<u64>loLeft | <u64>hiLeft << 32) % <i64>(<u64>loRight | <u64>hiRight << 32));
lo = <u32>ret;
hi = <u32>(ret >> 32);
}
export function rem_u(loLeft: u32, hiLeft: u32, loRight: u32, hiRight: u32): void {
const ret: u64 = (<u64>loLeft | <u64>hiLeft << 32) % (<u64>loRight | <u64>hiRight << 32);
lo = <u32>ret;
hi = <u32>(ret >>> 32);
}
export function and(loLeft: u32, hiLeft: u32, loRight: u32, hiRight: u32): void {
const ret: u64 = (<u64>loLeft | <u64>hiLeft << 32) & (<u64>loRight | <u64>hiRight << 32);
lo = <u32>ret;
hi = <u32>(ret >>> 32);
}
export function or(loLeft: u32, hiLeft: u32, loRight: u32, hiRight: u32): void {
const ret: u64 = (<u64>loLeft | <u64>hiLeft << 32) | (<u64>loRight | <u64>hiRight << 32);
lo = <u32>ret;
hi = <u32>(ret >>> 32);
}
export function xor(loLeft: u32, hiLeft: u32, loRight: u32, hiRight: u32): void {
const ret: u64 = (<u64>loLeft | <u64>hiLeft << 32) ^ (<u64>loRight | <u64>hiRight << 32);
lo = <u32>ret;
hi = <u32>(ret >>> 32);
}
export function shl(loLeft: u32, hiLeft: u32, loRight: u32, hiRight: u32): void {
const ret: u64 = (<u64>loLeft | <u64>hiLeft << 32) << (<u64>loRight | <u64>hiRight << 32);
lo = <u32>ret;
hi = <u32>(ret >>> 32);
}
export function shr_s(loLeft: u32, hiLeft: u32, loRight: u32, hiRight: u32): void {
const ret: u64 = <u64>(<i64>(<u64>loLeft | <u64>hiLeft << 32) >> <i64>(<u64>loRight | <u64>hiRight << 32));
lo = <u32>ret;
hi = <u32>(ret >>> 32);
}
export function shr_u(loLeft: u32, hiLeft: u32, loRight: u32, hiRight: u32): void {
const ret: u64 = (<u64>loLeft | <u64>hiLeft << 32) >> (<u64>loRight | <u64>hiRight << 32);
lo = <u32>ret;
hi = <u32>(ret >>> 32);
}
function rotl_(loLeft: u32, hiLeft: u32, loRight: u32, hiRight: u32): void {
const ret: u64 = rotl<u64>(<u64>loLeft | <u64>hiLeft << 32, <u64>loRight | <u64>hiRight << 32);
lo = <u32>ret;
hi = <u32>(ret >>> 32);
}
export { rotl_ as rotl };
function rotr_(loLeft: u32, hiLeft: u32, loRight: u32, hiRight: u32): void {
const ret: u64 = rotr<u64>(<u64>loLeft | <u64>hiLeft << 32, <u64>loRight | <u64>hiRight << 32);
lo = <u32>ret;
hi = <u32>(ret >>> 32);
}
export { rotr_ as rotr };
export function eq(loLeft: u32, hiLeft: u32, loRight: u32, hiRight: u32): void {
const ret: bool = (<u64>loLeft | <u64>hiLeft << 32) == (<u64>loRight | <u64>hiRight << 32);
lo = <u32>ret;
hi = 0;
}
export function ne(loLeft: u32, hiLeft: u32, loRight: u32, hiRight: u32): void {
const ret: bool = (<u64>loLeft | <u64>hiLeft << 32) != (<u64>loRight | <u64>hiRight << 32);
lo = <u32>ret;
hi = 0;
}
export function lt_s(loLeft: u32, hiLeft: u32, loRight: u32, hiRight: u32): void {
const ret: bool = <i64>(<u64>loLeft | <u64>hiLeft << 32) < <i64>(<u64>loRight | <u64>hiRight << 32);
lo = <u32>ret;
hi = 0;
}
export function lt_u(loLeft: u32, hiLeft: u32, loRight: u32, hiRight: u32): void {
const ret: bool = (<u64>loLeft | <u64>hiLeft << 32) < (<u64>loRight | <u64>hiRight << 32);
lo = <u32>ret;
hi = 0;
}
export function le_s(loLeft: u32, hiLeft: u32, loRight: u32, hiRight: u32): void {
const ret: bool = <i64>(<u64>loLeft | <u64>hiLeft << 32) <= <i64>(<u64>loRight | <u64>hiRight << 32);
lo = <u32>ret;
hi = 0;
}
export function le_u(loLeft: u32, hiLeft: u32, loRight: u32, hiRight: u32): void {
const ret: bool = (<u64>loLeft | <u64>hiLeft << 32) <= (<u64>loRight | <u64>hiRight << 32);
lo = <u32>ret;
hi = 0;
}
export function gt_s(loLeft: u32, hiLeft: u32, loRight: u32, hiRight: u32): void {
const ret: bool = <i64>(<u64>loLeft | <u64>hiLeft << 32) > <i64>(<u64>loRight | <u64>hiRight << 32);
lo = <u32>ret;
hi = 0;
}
export function gt_u(loLeft: u32, hiLeft: u32, loRight: u32, hiRight: u32): void {
const ret: bool = (<u64>loLeft | <u64>hiLeft << 32) > (<u64>loRight | <u64>hiRight << 32);
lo = <u32>ret;
hi = 0;
}
export function ge_s(loLeft: u32, hiLeft: u32, loRight: u32, hiRight: u32): void {
const ret: bool = <i64>(<u64>loLeft | <u64>hiLeft << 32) >= <i64>(<u64>loRight | <u64>hiRight << 32);
lo = <u32>ret;
hi = 0;
}
export function ge_u(loLeft: u32, hiLeft: u32, loRight: u32, hiRight: u32): void {
const ret: bool = (<u64>loLeft | <u64>hiLeft << 32) >= (<u64>loRight | <u64>hiRight << 32);
lo = <u32>ret;
hi = 0;
}

File diff suppressed because it is too large Load Diff