diff --git a/tests/compiler/declare.ts b/tests/compiler/declare.ts
index f0c8f543..f74e909a 100644
--- a/tests/compiler/declare.ts
+++ b/tests/compiler/declare.ts
@@ -1,4 +1,5 @@
declare function external(): void;
-// FIXME: "unexpected false: module function exports must be found"
+// "unexpected false: module function exports must be found"
+// see: https://github.com/WebAssembly/binaryen/issues/1325
export { external };
diff --git a/tests/compiler/tlsf.optimized.wast b/tests/compiler/tlsf.optimized.wast
new file mode 100644
index 00000000..5f0c8b56
--- /dev/null
+++ b/tests/compiler/tlsf.optimized.wast
@@ -0,0 +1,313 @@
+(module
+ (type $ii (func (param i32) (result i32)))
+ (type $iiv (func (param i32 i32)))
+ (type $iiiv (func (param i32 i32 i32)))
+ (type $iiiiv (func (param i32 i32 i32 i32)))
+ (type $iv (func (param i32)))
+ (type $v (func))
+ (global $tlsf/ALIGN_SIZE_LOG2 i32 (i32.const 3))
+ (global $tlsf/ALIGN_SIZE (mut i32) (i32.const 0))
+ (global $tlsf/BLOCK_PREV_PHYS_OFFSET i32 (i32.const 0))
+ (global $tlsf/BLOCK_SIZE_OFFSET (mut i32) (i32.const 0))
+ (global $tlsf/BLOCK_NEXT_FREE_OFFSET (mut i32) (i32.const 0))
+ (global $tlsf/BLOCK_PREV_FREE_OFFSET (mut i32) (i32.const 0))
+ (global $tlsf/CONTROL_FL_BITMAP_OFFSET (mut i32) (i32.const 0))
+ (global $tlsf/FL_INDEX_MAX i32 (i32.const 30))
+ (global $tlsf/SL_INDEX_COUNT_LOG2 i32 (i32.const 5))
+ (global $tlsf/FL_INDEX_SHIFT (mut i32) (i32.const 0))
+ (global $tlsf/FL_INDEX_COUNT (mut i32) (i32.const 0))
+ (global $tlsf/SL_INDEX_COUNT (mut i32) (i32.const 0))
+ (memory $0 1)
+ (data (i32.const 4) "\08")
+ (export "control_construct" (func $tlsf/control_construct))
+ (export "memory" (memory $0))
+ (start $start)
+ (func $tlsf/fls (; 0 ;) (type $ii) (param $0 i32) (result i32)
+ (if (result i32)
+ (get_local $0)
+ (i32.sub
+ (i32.const 31)
+ (i32.clz
+ (get_local $0)
+ )
+ )
+ (i32.const -1)
+ )
+ )
+ (func $tlsf/ffs (; 1 ;) (type $ii) (param $0 i32) (result i32)
+ (if (result i32)
+ (get_local $0)
+ (i32.ctz
+ (get_local $0)
+ )
+ (i32.const -1)
+ )
+ )
+ (func $tlsf/block_set_next_free (; 2 ;) (type $iiv) (param $0 i32) (param $1 i32)
+ (i32.store
+ (i32.add
+ (get_local $0)
+ (get_global $tlsf/BLOCK_NEXT_FREE_OFFSET)
+ )
+ (get_local $1)
+ )
+ )
+ (func $tlsf/block_set_prev_free (; 3 ;) (type $iiv) (param $0 i32) (param $1 i32)
+ (i32.store
+ (i32.add
+ (get_local $0)
+ (get_global $tlsf/BLOCK_PREV_FREE_OFFSET)
+ )
+ (get_local $1)
+ )
+ )
+ (func $tlsf/control_set_fl (; 4 ;) (type $iiv) (param $0 i32) (param $1 i32)
+ (i32.store
+ (i32.add
+ (get_local $0)
+ (get_global $tlsf/CONTROL_FL_BITMAP_OFFSET)
+ )
+ (get_local $1)
+ )
+ )
+ (func $tlsf/control_set_sl (; 5 ;) (type $iiiv) (param $0 i32) (param $1 i32) (param $2 i32)
+ (if
+ (i32.ge_s
+ (get_local $1)
+ (get_global $tlsf/FL_INDEX_COUNT)
+ )
+ (unreachable)
+ )
+ (i32.store
+ (i32.add
+ (get_local $0)
+ (i32.mul
+ (get_local $1)
+ (i32.const 4)
+ )
+ )
+ (get_local $2)
+ )
+ )
+ (func $tlsf/control_set_block (; 6 ;) (type $iiiiv) (param $0 i32) (param $1 i32) (param $2 i32) (param $3 i32)
+ (if
+ (i32.ge_s
+ (get_local $1)
+ (get_global $tlsf/FL_INDEX_COUNT)
+ )
+ (unreachable)
+ )
+ (if
+ (i32.ge_s
+ (get_local $2)
+ (get_global $tlsf/SL_INDEX_COUNT)
+ )
+ (unreachable)
+ )
+ (i32.store
+ (i32.add
+ (get_local $0)
+ (i32.mul
+ (i32.add
+ (i32.mul
+ (get_local $1)
+ (get_global $tlsf/SL_INDEX_COUNT)
+ )
+ (get_local $2)
+ )
+ (i32.const 4)
+ )
+ )
+ (get_local $3)
+ )
+ )
+ (func $tlsf/control_construct (; 7 ;) (type $iv) (param $0 i32)
+ (local $1 i32)
+ (local $2 i32)
+ (call $tlsf/block_set_next_free
+ (get_local $0)
+ (get_local $0)
+ )
+ (call $tlsf/block_set_prev_free
+ (get_local $0)
+ (get_local $0)
+ )
+ (call $tlsf/control_set_fl
+ (get_local $0)
+ (i32.const 0)
+ )
+ (set_local $1
+ (i32.const 0)
+ )
+ (loop $continue|1.1
+ (if
+ (i32.lt_s
+ (get_local $1)
+ (get_global $tlsf/FL_INDEX_COUNT)
+ )
+ (block
+ (call $tlsf/control_set_sl
+ (get_local $0)
+ (get_local $1)
+ (i32.const 0)
+ )
+ (set_local $2
+ (i32.const 0)
+ )
+ (loop $continue|1.2
+ (if
+ (i32.lt_s
+ (get_local $2)
+ (get_global $tlsf/SL_INDEX_COUNT)
+ )
+ (block
+ (call $tlsf/control_set_block
+ (get_local $0)
+ (get_local $1)
+ (get_local $2)
+ (get_local $0)
+ )
+ (set_local $2
+ (i32.add
+ (get_local $2)
+ (i32.const 1)
+ )
+ )
+ (br $continue|1.2)
+ )
+ )
+ )
+ (set_local $1
+ (i32.add
+ (get_local $1)
+ (i32.const 1)
+ )
+ )
+ (br $continue|1.1)
+ )
+ )
+ )
+ )
+ (func $start (; 8 ;) (type $v)
+ (if
+ (i32.ne
+ (call $tlsf/fls
+ (i32.const 0)
+ )
+ (i32.const -1)
+ )
+ (unreachable)
+ )
+ (if
+ (call $tlsf/fls
+ (i32.const 1)
+ )
+ (unreachable)
+ )
+ (if
+ (i32.ne
+ (call $tlsf/fls
+ (i32.const -2147483640)
+ )
+ (i32.const 31)
+ )
+ (unreachable)
+ )
+ (if
+ (i32.ne
+ (call $tlsf/fls
+ (i32.const 2147483647)
+ )
+ (i32.const 30)
+ )
+ (unreachable)
+ )
+ (if
+ (i32.ne
+ (call $tlsf/ffs
+ (i32.const 0)
+ )
+ (i32.const -1)
+ )
+ (unreachable)
+ )
+ (if
+ (call $tlsf/ffs
+ (i32.const 1)
+ )
+ (unreachable)
+ )
+ (if
+ (i32.ne
+ (call $tlsf/ffs
+ (i32.const -2147483648)
+ )
+ (i32.const 31)
+ )
+ (unreachable)
+ )
+ (set_global $tlsf/ALIGN_SIZE
+ (i32.shl
+ (i32.const 1)
+ (get_global $tlsf/ALIGN_SIZE_LOG2)
+ )
+ )
+ (if
+ (i32.ne
+ (get_global $tlsf/ALIGN_SIZE)
+ (i32.const 8)
+ )
+ (unreachable)
+ )
+ (set_global $tlsf/BLOCK_SIZE_OFFSET
+ (i32.add
+ (get_global $tlsf/BLOCK_PREV_PHYS_OFFSET)
+ (i32.const 4)
+ )
+ )
+ (set_global $tlsf/BLOCK_NEXT_FREE_OFFSET
+ (i32.add
+ (get_global $tlsf/BLOCK_SIZE_OFFSET)
+ (i32.const 4)
+ )
+ )
+ (set_global $tlsf/BLOCK_PREV_FREE_OFFSET
+ (i32.add
+ (get_global $tlsf/BLOCK_NEXT_FREE_OFFSET)
+ (i32.const 4)
+ )
+ )
+ (set_global $tlsf/CONTROL_FL_BITMAP_OFFSET
+ (i32.add
+ (get_global $tlsf/BLOCK_PREV_FREE_OFFSET)
+ (i32.const 4)
+ )
+ )
+ (set_global $tlsf/FL_INDEX_SHIFT
+ (i32.add
+ (get_global $tlsf/SL_INDEX_COUNT_LOG2)
+ (get_global $tlsf/ALIGN_SIZE_LOG2)
+ )
+ )
+ (set_global $tlsf/FL_INDEX_COUNT
+ (i32.add
+ (i32.sub
+ (get_global $tlsf/FL_INDEX_MAX)
+ (get_global $tlsf/FL_INDEX_SHIFT)
+ )
+ (i32.const 1)
+ )
+ )
+ (set_global $tlsf/SL_INDEX_COUNT
+ (i32.shl
+ (i32.const 1)
+ (get_global $tlsf/SL_INDEX_COUNT_LOG2)
+ )
+ )
+ (call $tlsf/control_construct
+ (i32.load
+ (i32.const 8)
+ )
+ )
+ )
+)
diff --git a/tests/compiler/tlsf.ts b/tests/compiler/tlsf.ts
new file mode 100644
index 00000000..e5fa4e16
--- /dev/null
+++ b/tests/compiler/tlsf.ts
@@ -0,0 +1,139 @@
+// An unfinished implementation of tlsf in low-level AssemblyScript.
+// Useful as a compiler test in this state, but nothing more.
+// based upon: https://github.com/mattconte/tlsf/blob/master/tlsf.c (BSD)
+
+///
+
+/** Finds the index of the least bit set. */
+function fls(word: u32): i32 {
+ return !word ? -1: 31 - clz(word);
+}
+
+assert(fls(0) == -1);
+assert(fls(1) == 0);
+assert(fls(0x80000008) == 31);
+assert(fls(0x7FFFFFFF) == 30);
+
+/** Finds the index of the first bit set. */
+function ffs(word: u32): i32 {
+ return !word ? -1 : ctz(word);
+}
+
+assert(ffs(0) == -1);
+assert(ffs(1) == 0);
+assert(ffs(0x80000000) == 31);
+
+// Align allocated blocks to 8 bytes so that any native type is aligned
+
+const ALIGN_SIZE_LOG2: i32 = 3;
+const ALIGN_SIZE: i32 = 1 << ALIGN_SIZE_LOG2;
+
+assert(ALIGN_SIZE == 8);
+
+// Define bitmap constants
+
+const SL_INDEX_COUNT_LOG2: i32 = 5;
+const FL_INDEX_MAX: i32 = 30;
+const SL_INDEX_COUNT: i32 = 1 << SL_INDEX_COUNT_LOG2;
+const FL_INDEX_SHIFT: i32 = SL_INDEX_COUNT_LOG2 + ALIGN_SIZE_LOG2;
+const FL_INDEX_COUNT: i32 = FL_INDEX_MAX - FL_INDEX_SHIFT + 1;
+const SMALL_BLOCK_SIZE: i32 = 1 << FL_INDEX_SHIFT;
+
+// struct block_header_t {
+// struct block_header_t* prev_phys_block;
+// size_t size;
+// struct block_header_t* next_free;
+// struct block_header_t* prev_free;
+// }
+
+const BLOCK_PREV_PHYS_OFFSET: usize = 0;
+const BLOCK_SIZE_OFFSET: usize = BLOCK_PREV_PHYS_OFFSET + sizeof();
+const BLOCK_NEXT_FREE_OFFSET: usize = BLOCK_SIZE_OFFSET + sizeof();
+const BLOCK_PREV_FREE_OFFSET: usize = BLOCK_NEXT_FREE_OFFSET + sizeof();
+
+function block_get_prev_phys_block(ptr: usize): usize {
+ return load(ptr + BLOCK_PREV_PHYS_OFFSET);
+}
+
+function block_set_prev_phys_block(ptr: usize, value: usize): void {
+ store(ptr + BLOCK_PREV_PHYS_OFFSET, value);
+}
+
+function block_get_size(ptr: usize): usize {
+ return load(ptr + BLOCK_SIZE_OFFSET);
+}
+
+function block_set_size(ptr: usize, value: usize): void {
+ store(ptr + BLOCK_SIZE_OFFSET, value);
+}
+
+function block_get_next_free(ptr: usize): usize {
+ return load(ptr + BLOCK_NEXT_FREE_OFFSET);
+}
+
+function block_set_next_free(ptr: usize, value: usize): void {
+ store(ptr + BLOCK_NEXT_FREE_OFFSET, value);
+}
+
+function block_get_prev_free(ptr: usize): usize {
+ return load(ptr + BLOCK_PREV_FREE_OFFSET);
+}
+
+function block_set_prev_free(ptr: usize, value: usize): void {
+ store(ptr + BLOCK_PREV_FREE_OFFSET, value);
+}
+
+// struct control_t {
+// block_header_t block_null;
+// unsigned int fl_bitmap;
+// unsigned int sl_bitmap[FL_INDEX_COUNT];
+// block_header_t* blocks[FL_INDEX_COUNT][SL_INDEX_COUNT];
+// }
+
+const CONTROL_FL_BITMAP_OFFSET: usize = BLOCK_PREV_FREE_OFFSET + sizeof();
+const CONTROL_SL_BITMAP_OFFSET: usize = CONTROL_FL_BITMAP_OFFSET + sizeof();
+const CONTROL_BLOCKS_OFFSET: usize = CONTROL_SL_BITMAP_OFFSET + FL_INDEX_COUNT * sizeof();
+
+function control_get_fl(ptr: usize): u32 {
+ return load(ptr + CONTROL_FL_BITMAP_OFFSET);
+}
+
+function control_set_fl(ptr: usize, value: u32): void {
+ store(ptr + CONTROL_FL_BITMAP_OFFSET, value);
+}
+
+function control_get_sl(ptr: usize, flIndex: usize): u32 {
+ assert(flIndex < FL_INDEX_COUNT);
+ return load(ptr + flIndex * sizeof());
+}
+
+function control_set_sl(ptr: usize, flIndex: usize, value: u32): void {
+ assert(flIndex < FL_INDEX_COUNT);
+ store(ptr + flIndex * sizeof(), value);
+}
+
+function control_get_block(ptr: usize, flIndex: usize, slIndex: usize): usize {
+ assert(flIndex < FL_INDEX_COUNT);
+ assert(slIndex < SL_INDEX_COUNT);
+ return load(ptr + (flIndex * SL_INDEX_COUNT + slIndex) * sizeof());
+}
+
+function control_set_block(ptr: usize, flIndex: usize, slIndex: usize, value: usize): void {
+ assert(flIndex < FL_INDEX_COUNT);
+ assert(slIndex < SL_INDEX_COUNT);
+ store(ptr + (flIndex * SL_INDEX_COUNT + slIndex) * sizeof(), value);
+}
+
+/* Clear structure and point all empty lists at the null block. */
+export function control_construct(ptr: usize): void {
+ block_set_next_free(ptr, ptr);
+ block_set_prev_free(ptr, ptr);
+ control_set_fl(ptr, 0);
+ for (let flIndex: usize = 0; flIndex < FL_INDEX_COUNT; ++flIndex) {
+ control_set_sl(ptr, flIndex, 0);
+ for (let slIndex: usize = 0; slIndex < SL_INDEX_COUNT; ++slIndex)
+ control_set_block(ptr, flIndex, slIndex, ptr);
+ }
+}
+
+control_construct(load(8));
diff --git a/tests/compiler/tlsf.wast b/tests/compiler/tlsf.wast
new file mode 100644
index 00000000..c595249f
--- /dev/null
+++ b/tests/compiler/tlsf.wast
@@ -0,0 +1,433 @@
+(module
+ (type $ii (func (param i32) (result i32)))
+ (type $iiv (func (param i32 i32)))
+ (type $iiiv (func (param i32 i32 i32)))
+ (type $iiiiv (func (param i32 i32 i32 i32)))
+ (type $iv (func (param i32)))
+ (type $v (func))
+ (global $tlsf/ALIGN_SIZE_LOG2 i32 (i32.const 3))
+ (global $tlsf/ALIGN_SIZE (mut i32) (i32.const 0))
+ (global $tlsf/BLOCK_PREV_PHYS_OFFSET i32 (i32.const 0))
+ (global $tlsf/BLOCK_SIZE_OFFSET (mut i32) (i32.const 0))
+ (global $tlsf/BLOCK_NEXT_FREE_OFFSET (mut i32) (i32.const 0))
+ (global $tlsf/BLOCK_PREV_FREE_OFFSET (mut i32) (i32.const 0))
+ (global $tlsf/CONTROL_FL_BITMAP_OFFSET (mut i32) (i32.const 0))
+ (global $tlsf/FL_INDEX_MAX i32 (i32.const 30))
+ (global $tlsf/SL_INDEX_COUNT_LOG2 i32 (i32.const 5))
+ (global $tlsf/FL_INDEX_SHIFT (mut i32) (i32.const 0))
+ (global $tlsf/FL_INDEX_COUNT (mut i32) (i32.const 0))
+ (global $tlsf/SL_INDEX_COUNT (mut i32) (i32.const 0))
+ (memory $0 1)
+ (data (i32.const 4) "\08\00\00\00")
+ (export "control_construct" (func $tlsf/control_construct))
+ (export "memory" (memory $0))
+ (start $start)
+ (func $tlsf/fls (; 0 ;) (type $ii) (param $0 i32) (result i32)
+ (return
+ (if (result i32)
+ (i32.eqz
+ (get_local $0)
+ )
+ (i32.sub
+ (i32.const 0)
+ (i32.const 1)
+ )
+ (i32.sub
+ (i32.const 31)
+ (i32.clz
+ (get_local $0)
+ )
+ )
+ )
+ )
+ )
+ (func $tlsf/ffs (; 1 ;) (type $ii) (param $0 i32) (result i32)
+ (return
+ (if (result i32)
+ (i32.eqz
+ (get_local $0)
+ )
+ (i32.sub
+ (i32.const 0)
+ (i32.const 1)
+ )
+ (i32.ctz
+ (get_local $0)
+ )
+ )
+ )
+ )
+ (func $tlsf/block_set_next_free (; 2 ;) (type $iiv) (param $0 i32) (param $1 i32)
+ (i32.store
+ (i32.add
+ (get_local $0)
+ (get_global $tlsf/BLOCK_NEXT_FREE_OFFSET)
+ )
+ (get_local $1)
+ )
+ )
+ (func $tlsf/block_set_prev_free (; 3 ;) (type $iiv) (param $0 i32) (param $1 i32)
+ (i32.store
+ (i32.add
+ (get_local $0)
+ (get_global $tlsf/BLOCK_PREV_FREE_OFFSET)
+ )
+ (get_local $1)
+ )
+ )
+ (func $tlsf/control_set_fl (; 4 ;) (type $iiv) (param $0 i32) (param $1 i32)
+ (i32.store
+ (i32.add
+ (get_local $0)
+ (get_global $tlsf/CONTROL_FL_BITMAP_OFFSET)
+ )
+ (get_local $1)
+ )
+ )
+ (func $tlsf/control_set_sl (; 5 ;) (type $iiiv) (param $0 i32) (param $1 i32) (param $2 i32)
+ (if
+ (i32.eqz
+ (i32.lt_s
+ (get_local $1)
+ (get_global $tlsf/FL_INDEX_COUNT)
+ )
+ )
+ (unreachable)
+ )
+ (i32.store
+ (i32.add
+ (get_local $0)
+ (i32.mul
+ (get_local $1)
+ (i32.const 4)
+ )
+ )
+ (get_local $2)
+ )
+ )
+ (func $tlsf/control_set_block (; 6 ;) (type $iiiiv) (param $0 i32) (param $1 i32) (param $2 i32) (param $3 i32)
+ (if
+ (i32.eqz
+ (i32.lt_s
+ (get_local $1)
+ (get_global $tlsf/FL_INDEX_COUNT)
+ )
+ )
+ (unreachable)
+ )
+ (if
+ (i32.eqz
+ (i32.lt_s
+ (get_local $2)
+ (get_global $tlsf/SL_INDEX_COUNT)
+ )
+ )
+ (unreachable)
+ )
+ (i32.store
+ (i32.add
+ (get_local $0)
+ (i32.mul
+ (i32.add
+ (i32.mul
+ (get_local $1)
+ (get_global $tlsf/SL_INDEX_COUNT)
+ )
+ (get_local $2)
+ )
+ (i32.const 4)
+ )
+ )
+ (get_local $3)
+ )
+ )
+ (func $tlsf/control_construct (; 7 ;) (type $iv) (param $0 i32)
+ (local $1 i32)
+ (local $2 i32)
+ (call $tlsf/block_set_next_free
+ (get_local $0)
+ (get_local $0)
+ )
+ (call $tlsf/block_set_prev_free
+ (get_local $0)
+ (get_local $0)
+ )
+ (call $tlsf/control_set_fl
+ (get_local $0)
+ (i32.const 0)
+ )
+ (block $break|1.1
+ (block
+ (set_local $1
+ (i32.const 0)
+ )
+ )
+ (loop $continue|1.1
+ (if
+ (i32.lt_s
+ (get_local $1)
+ (get_global $tlsf/FL_INDEX_COUNT)
+ )
+ (block
+ (block
+ (call $tlsf/control_set_sl
+ (get_local $0)
+ (get_local $1)
+ (i32.const 0)
+ )
+ (block $break|1.2
+ (block
+ (set_local $2
+ (i32.const 0)
+ )
+ )
+ (loop $continue|1.2
+ (if
+ (i32.lt_s
+ (get_local $2)
+ (get_global $tlsf/SL_INDEX_COUNT)
+ )
+ (block
+ (call $tlsf/control_set_block
+ (get_local $0)
+ (get_local $1)
+ (get_local $2)
+ (get_local $0)
+ )
+ (set_local $2
+ (i32.add
+ (get_local $2)
+ (i32.const 1)
+ )
+ )
+ (br $continue|1.2)
+ )
+ )
+ )
+ )
+ )
+ (set_local $1
+ (i32.add
+ (get_local $1)
+ (i32.const 1)
+ )
+ )
+ (br $continue|1.1)
+ )
+ )
+ )
+ )
+ )
+ (func $start (; 8 ;) (type $v)
+ (if
+ (i32.eqz
+ (i32.eq
+ (call $tlsf/fls
+ (i32.const 0)
+ )
+ (i32.sub
+ (i32.const 0)
+ (i32.const 1)
+ )
+ )
+ )
+ (unreachable)
+ )
+ (if
+ (i32.eqz
+ (i32.eq
+ (call $tlsf/fls
+ (i32.const 1)
+ )
+ (i32.const 0)
+ )
+ )
+ (unreachable)
+ )
+ (if
+ (i32.eqz
+ (i32.eq
+ (call $tlsf/fls
+ (i32.const -2147483640)
+ )
+ (i32.const 31)
+ )
+ )
+ (unreachable)
+ )
+ (if
+ (i32.eqz
+ (i32.eq
+ (call $tlsf/fls
+ (i32.const 2147483647)
+ )
+ (i32.const 30)
+ )
+ )
+ (unreachable)
+ )
+ (if
+ (i32.eqz
+ (i32.eq
+ (call $tlsf/ffs
+ (i32.const 0)
+ )
+ (i32.sub
+ (i32.const 0)
+ (i32.const 1)
+ )
+ )
+ )
+ (unreachable)
+ )
+ (if
+ (i32.eqz
+ (i32.eq
+ (call $tlsf/ffs
+ (i32.const 1)
+ )
+ (i32.const 0)
+ )
+ )
+ (unreachable)
+ )
+ (if
+ (i32.eqz
+ (i32.eq
+ (call $tlsf/ffs
+ (i32.const -2147483648)
+ )
+ (i32.const 31)
+ )
+ )
+ (unreachable)
+ )
+ (set_global $tlsf/ALIGN_SIZE
+ (i32.shl
+ (i32.const 1)
+ (get_global $tlsf/ALIGN_SIZE_LOG2)
+ )
+ )
+ (if
+ (i32.eqz
+ (i32.eq
+ (get_global $tlsf/ALIGN_SIZE)
+ (i32.const 8)
+ )
+ )
+ (unreachable)
+ )
+ (set_global $tlsf/BLOCK_SIZE_OFFSET
+ (i32.add
+ (get_global $tlsf/BLOCK_PREV_PHYS_OFFSET)
+ (i32.const 4)
+ )
+ )
+ (set_global $tlsf/BLOCK_NEXT_FREE_OFFSET
+ (i32.add
+ (get_global $tlsf/BLOCK_SIZE_OFFSET)
+ (i32.const 4)
+ )
+ )
+ (set_global $tlsf/BLOCK_PREV_FREE_OFFSET
+ (i32.add
+ (get_global $tlsf/BLOCK_NEXT_FREE_OFFSET)
+ (i32.const 4)
+ )
+ )
+ (set_global $tlsf/CONTROL_FL_BITMAP_OFFSET
+ (i32.add
+ (get_global $tlsf/BLOCK_PREV_FREE_OFFSET)
+ (i32.const 4)
+ )
+ )
+ (set_global $tlsf/FL_INDEX_SHIFT
+ (i32.add
+ (get_global $tlsf/SL_INDEX_COUNT_LOG2)
+ (get_global $tlsf/ALIGN_SIZE_LOG2)
+ )
+ )
+ (set_global $tlsf/FL_INDEX_COUNT
+ (i32.add
+ (i32.sub
+ (get_global $tlsf/FL_INDEX_MAX)
+ (get_global $tlsf/FL_INDEX_SHIFT)
+ )
+ (i32.const 1)
+ )
+ )
+ (set_global $tlsf/SL_INDEX_COUNT
+ (i32.shl
+ (i32.const 1)
+ (get_global $tlsf/SL_INDEX_COUNT_LOG2)
+ )
+ )
+ (call $tlsf/control_construct
+ (i32.load
+ (i32.const 8)
+ )
+ )
+ )
+)
+(;
+[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
+ isNaN
+ isFinite
+ assert
+ tlsf/fls
+ tlsf/ffs
+ tlsf/ALIGN_SIZE_LOG2
+ tlsf/ALIGN_SIZE
+ tlsf/SL_INDEX_COUNT_LOG2
+ tlsf/FL_INDEX_MAX
+ tlsf/SL_INDEX_COUNT
+ tlsf/FL_INDEX_SHIFT
+ tlsf/FL_INDEX_COUNT
+ tlsf/SMALL_BLOCK_SIZE
+ tlsf/BLOCK_PREV_PHYS_OFFSET
+ tlsf/BLOCK_SIZE_OFFSET
+ tlsf/BLOCK_NEXT_FREE_OFFSET
+ tlsf/BLOCK_PREV_FREE_OFFSET
+ tlsf/block_get_prev_phys_block
+ tlsf/block_set_prev_phys_block
+ tlsf/block_get_size
+ tlsf/block_set_size
+ tlsf/block_get_next_free
+ tlsf/block_set_next_free
+ tlsf/block_get_prev_free
+ tlsf/block_set_prev_free
+ tlsf/CONTROL_FL_BITMAP_OFFSET
+ tlsf/CONTROL_SL_BITMAP_OFFSET
+ tlsf/CONTROL_BLOCKS_OFFSET
+ tlsf/control_get_fl
+ tlsf/control_set_fl
+ tlsf/control_get_sl
+ tlsf/control_set_sl
+ tlsf/control_get_block
+ tlsf/control_set_block
+ tlsf/control_construct
+[program.exports]
+ tlsf/control_construct
+;)